diff -urN 2.2.14pre12-set_blocksize/fs/buffer.c 2.2.14pre12-set_blocksize-debug/fs/buffer.c --- 2.2.14pre12-set_blocksize/fs/buffer.c Sun Dec 12 17:25:18 1999 +++ 2.2.14pre12-set_blocksize-debug/fs/buffer.c Tue Dec 14 17:01:22 1999 @@ -641,6 +641,14 @@ } } +static void show_stack_trace(struct buffer_head * bh) +{ + int i; + + for (i = 0; i < BH_TRACE_SIZE; i++) + printk("[<%08lu>]\n", bh->b_trace[i]); +} + void set_blocksize(kdev_t dev, int size) { extern int *blksize_size[]; @@ -697,6 +705,7 @@ "b_count %d, dev %s, block %lu, from %p\n", bh->b_count, bdevname(bh->b_dev), bh->b_blocknr, __builtin_return_address(0)); + show_stack_trace(bh); } if (slept) goto again; @@ -734,6 +743,22 @@ unlock_buffer(bh); } +static void fill_stack_trace(struct buffer_head * bh) +{ + unsigned long *stack; + extern char *get_options(char *str, int *ints); + int i, j; + + stack = (unsigned long *) &stack; + for (j = i = 0; j < 300 && i < BH_TRACE_SIZE; j++) + { + unsigned long x = *++stack; + if (x > (unsigned long) &get_options && + x < (unsigned long) &vsprintf) + bh->b_trace[i++] = x; + } +} + /* * Ok, this is getblk, and it isn't very clear, again to hinder * race-conditions. Most of the code is seldom used, (ie repeating), @@ -770,6 +795,7 @@ */ init_buffer(bh, dev, block, end_buffer_io_sync, NULL); bh->b_state=0; + fill_stack_trace(bh); insert_into_queues(bh); return bh; diff -urN 2.2.14pre12-set_blocksize/include/linux/fs.h 2.2.14pre12-set_blocksize-debug/include/linux/fs.h --- 2.2.14pre12-set_blocksize/include/linux/fs.h Sun Dec 12 17:45:06 1999 +++ 2.2.14pre12-set_blocksize-debug/include/linux/fs.h Tue Dec 14 16:51:58 1999 @@ -222,6 +222,8 @@ */ void (*b_end_io)(struct buffer_head *bh, int uptodate); void *b_dev_id; +#define BH_TRACE_SIZE 15 + unsigned long b_trace[BH_TRACE_SIZE]; }; typedef void (bh_end_io_t)(struct buffer_head *bh, int uptodate);