This patch contains the first set of instrumentations for latencytop;
each instrumentation needs to be evaluated for usefulness before this
can go into mainline; posting here just to show how the infrastructure
can be used

---
 arch/x86/mm/fault_64.c    |    4 ++++
 block/ll_rw_blk.c         |    3 +++
 drivers/scsi/hosts.c      |    1 -
 drivers/scsi/scsi_error.c |    6 +++++-
 drivers/scsi/scsi_lib.c   |    4 ++++
 drivers/scsi/sd.c         |    5 +++++
 drivers/scsi/sr.c         |   12 +++++++++++-
 fs/buffer.c               |   22 +++++++++++++++++++++-
 fs/eventpoll.c            |    5 +++++
 fs/ext3/inode.c           |   30 ++++++++++++++++++++++++++++--
 fs/inode.c                |   13 +++++++++++++
 fs/jbd/checkpoint.c       |    6 ++++++
 fs/jbd/commit.c           |    5 +++++
 fs/jbd/journal.c          |    5 +++++
 fs/jbd/transaction.c      |   13 +++++++++++++
 fs/pipe.c                 |    5 +++++
 fs/select.c               |    3 +++
 fs/sync.c                 |   19 +++++++++++++++++--
 kernel/fork.c             |    4 ++++
 kernel/futex.c            |    8 +++++++-
 kernel/mutex.c            |   13 +++++++++++++
 kernel/rwsem.c            |   12 +++++++++++-
 mm/filemap.c              |    6 ++++++
 mm/slub.c                 |    7 ++++++-
 24 files changed, 200 insertions(+), 11 deletions(-)

Index: linux-2.6.24-rc7/arch/x86/mm/fault_64.c
===================================================================
--- linux-2.6.24-rc7.orig/arch/x86/mm/fault_64.c
+++ linux-2.6.24-rc7/arch/x86/mm/fault_64.c
@@ -303,6 +303,7 @@ asmlinkage void __kprobes do_page_fault(
        int write, fault;
        unsigned long flags;
        siginfo_t info;
+       struct latency_entry reason;
 
        /*
         * We can fault from pretty much anywhere, with unknown IRQ state.
@@ -441,7 +442,10 @@ good_area:
         * make sure we exit gracefully rather than endlessly redo
         * the fault.
         */
+
+       set_latency_reason("page fault", &reason);
        fault = handle_mm_fault(mm, vma, address, write);
+       restore_latency_reason(&reason);
        if (unlikely(fault & VM_FAULT_ERROR)) {
                if (fault & VM_FAULT_OOM)
                        goto out_of_memory;
Index: linux-2.6.24-rc7/block/ll_rw_blk.c
===================================================================
--- linux-2.6.24-rc7.orig/block/ll_rw_blk.c
+++ linux-2.6.24-rc7/block/ll_rw_blk.c
@@ -2190,7 +2190,9 @@ static struct request *get_request_wait(
 {
        const int rw = rw_flags & 0x01;
        struct request *rq;
+       struct latency_entry reason;
 
+       set_latency_reason("Waiting for a block layer request", &reason);
        rq = get_request(q, rw_flags, bio, GFP_NOIO);
        while (!rq) {
                DEFINE_WAIT(wait);
@@ -2224,6 +2226,7 @@ static struct request *get_request_wait(
                finish_wait(&rl->wait[rw], &wait);
        }
 
+       restore_latency_reason(&reason);
        return rq;
 }
 
Index: linux-2.6.24-rc7/drivers/scsi/scsi_error.c
===================================================================
--- linux-2.6.24-rc7.orig/drivers/scsi/scsi_error.c
+++ linux-2.6.24-rc7/drivers/scsi/scsi_error.c
@@ -228,11 +227,16 @@ void scsi_times_out(struct scsi_cmnd *sc
 int scsi_block_when_processing_errors(struct scsi_device *sdev)
 {
        int online;
+       struct latency_entry reason;
+
+       set_latency_reason("SCSI block due to error recovery", &reason);
 
        wait_event(sdev->host->host_wait, !scsi_host_in_recovery(sdev->host));
 
        online = scsi_device_online(sdev);
 
+       restore_latency_reason(&reason);
+
        SCSI_LOG_ERROR_RECOVERY(5, printk("%s: rtn: %d\n", __FUNCTION__,
                                          online));
 
Index: linux-2.6.24-rc7/drivers/scsi/scsi_lib.c
===================================================================
--- linux-2.6.24-rc7.orig/drivers/scsi/scsi_lib.c
+++ linux-2.6.24-rc7/drivers/scsi/scsi_lib.c
@@ -183,6 +183,9 @@ int scsi_execute(struct scsi_device *sde
        struct request *req;
        int write = (data_direction == DMA_TO_DEVICE);
        int ret = DRIVER_ERROR << 24;
+       struct latency_entry reason;
+
+       set_latency_reason("SCSI layer command execute", &reason);
 
        req = blk_get_request(sdev->request_queue, write, __GFP_WAIT);
 
@@ -208,6 +211,7 @@ int scsi_execute(struct scsi_device *sde
  out:
        blk_put_request(req);
 
+       restore_latency_reason(&reason);
        return ret;
 }
 EXPORT_SYMBOL(scsi_execute);
Index: linux-2.6.24-rc7/drivers/scsi/sd.c
===================================================================
--- linux-2.6.24-rc7.orig/drivers/scsi/sd.c
+++ linux-2.6.24-rc7/drivers/scsi/sd.c
@@ -47,6 +47,7 @@
 #include <linux/blkpg.h>
 #include <linux/delay.h>
 #include <linux/mutex.h>
+#include <linux/latencytop.h>
 #include <asm/uaccess.h>
 
 #include <scsi/scsi.h>
@@ -796,10 +797,13 @@ static int sd_sync_cache(struct scsi_dis
        int retries, res;
        struct scsi_device *sdp = sdkp->device;
        struct scsi_sense_hdr sshdr;
+       struct latency_entry reason;
 
        if (!scsi_device_online(sdp))
                return -ENODEV;
 
+       set_latency_reason("SCSI disk cache synchronize", &reason);
+
 
        for (retries = 3; retries > 0; --retries) {
                unsigned char cmd[10] = { 0 };
@@ -821,6 +825,7 @@ static int sd_sync_cache(struct scsi_dis
                        sd_print_sense_hdr(sdkp, &sshdr);
        }
 
+       restore_latency_reason(&reason);
        if (res)
                return -EIO;
        return 0;
Index: linux-2.6.24-rc7/drivers/scsi/sr.c
===================================================================
--- linux-2.6.24-rc7.orig/drivers/scsi/sr.c
+++ linux-2.6.24-rc7/drivers/scsi/sr.c
@@ -44,6 +44,7 @@
 #include <linux/init.h>
 #include <linux/blkdev.h>
 #include <linux/mutex.h>
+#include <linux/latencytop.h>
 #include <asm/uaccess.h>
 
 #include <scsi/scsi.h>
@@ -468,6 +469,7 @@ static int sr_block_ioctl(struct inode *
        struct scsi_device *sdev = cd->device;
        void __user *argp = (void __user *)arg;
        int ret;
+       struct latency_entry reason;
 
        /*
         * Send SCSI addressing ioctls directly to mid level, send other
@@ -479,7 +481,9 @@ static int sr_block_ioctl(struct inode *
                return scsi_ioctl(sdev, cmd, argp);
        }
 
+       set_latency_reason("SCSI cdrom ioctl", &reason);
        ret = cdrom_ioctl(file, &cd->cdi, inode, cmd, arg);
+       restore_latency_reason(&reason);
        if (ret != -ENOSYS)
                return ret;
 
@@ -489,10 +493,16 @@ static int sr_block_ioctl(struct inode *
         * case fall through to scsi_ioctl, which will return ENDOEV again
         * if it doesn't recognise the ioctl
         */
+       set_latency_reason("SCSI nonblockable ioctl", &reason);
        ret = scsi_nonblockable_ioctl(sdev, cmd, argp, NULL);
+       restore_latency_reason(&reason);
        if (ret != -ENODEV)
                return ret;
-       return scsi_ioctl(sdev, cmd, argp);
+       set_latency_reason("SCSI ioctl", &reason);
+       ret = scsi_ioctl(sdev, cmd, argp);
+       restore_latency_reason(&reason);
+
+       return ret;
 }
 
 static int sr_block_media_changed(struct gendisk *disk)
Index: linux-2.6.24-rc7/fs/buffer.c
===================================================================
--- linux-2.6.24-rc7.orig/fs/buffer.c
+++ linux-2.6.24-rc7/fs/buffer.c
@@ -41,6 +41,7 @@
 #include <linux/bitops.h>
 #include <linux/mpage.h>
 #include <linux/bit_spinlock.h>
+#include <linux/latencytop.h>
 
 static int fsync_buffers_list(spinlock_t *lock, struct list_head *list);
 
@@ -69,8 +70,11 @@ static int sync_buffer(void *word)
 
 void fastcall __lock_buffer(struct buffer_head *bh)
 {
+       struct latency_entry reason;
+       set_latency_reason("Locking buffer head", &reason);
        wait_on_bit_lock(&bh->b_state, BH_Lock, sync_buffer,
                                                        TASK_UNINTERRUPTIBLE);
+       restore_latency_reason(&reason);
 }
 EXPORT_SYMBOL(__lock_buffer);
 
@@ -89,7 +93,10 @@ void fastcall unlock_buffer(struct buffe
  */
 void __wait_on_buffer(struct buffer_head * bh)
 {
+       struct latency_entry reason;
+       set_latency_reason("Waiting for buffer IO", &reason);
        wait_on_bit(&bh->b_state, BH_Lock, sync_buffer, TASK_UNINTERRUPTIBLE);
+       restore_latency_reason(&reason);
 }
 
 static void
@@ -606,6 +613,9 @@ static int osync_buffers_list(spinlock_t
        struct buffer_head *bh;
        struct list_head *p;
        int err = 0;
+       struct latency_entry reason;
+
+       set_latency_reason("(O)sync the buffer list", &reason);
 
        spin_lock(lock);
 repeat:
@@ -623,6 +633,7 @@ repeat:
                }
        }
        spin_unlock(lock);
+       restore_latency_reason(&reason);
        return err;
 }
 
@@ -1208,19 +1219,25 @@ void __bforget(struct buffer_head *bh)
 
 static struct buffer_head *__bread_slow(struct buffer_head *bh)
 {
+       struct latency_entry reason;
+       set_latency_reason("Synchronous bufferhead read", &reason);
        lock_buffer(bh);
        if (buffer_uptodate(bh)) {
                unlock_buffer(bh);
+               restore_latency_reason(&reason);
                return bh;
        } else {
                get_bh(bh);
                bh->b_end_io = end_buffer_read_sync;
                submit_bh(READ, bh);
                wait_on_buffer(bh);
-               if (buffer_uptodate(bh))
+               if (buffer_uptodate(bh)) {
+                       restore_latency_reason(&reason);
                        return bh;
+               }
        }
        brelse(bh);
+       restore_latency_reason(&reason);
        return NULL;
 }
 
@@ -2973,6 +2990,8 @@ void ll_rw_block(int rw, int nr, struct 
 int sync_dirty_buffer(struct buffer_head *bh)
 {
        int ret = 0;
+       struct latency_entry reason;
+       set_latency_reason("syncing diry buffer", &reason);
 
        WARN_ON(atomic_read(&bh->b_count) < 1);
        lock_buffer(bh);
@@ -2990,6 +3009,7 @@ int sync_dirty_buffer(struct buffer_head
        } else {
                unlock_buffer(bh);
        }
+       restore_latency_reason(&reason);
        return ret;
 }
 
Index: linux-2.6.24-rc7/fs/eventpoll.c
===================================================================
--- linux-2.6.24-rc7.orig/fs/eventpoll.c
+++ linux-2.6.24-rc7/fs/eventpoll.c
@@ -33,6 +33,7 @@
 #include <linux/bitops.h>
 #include <linux/mutex.h>
 #include <linux/anon_inodes.h>
+#include <linux/latencytop.h>
 #include <asm/uaccess.h>
 #include <asm/system.h>
 #include <asm/io.h>
@@ -1219,6 +1220,7 @@ asmlinkage long sys_epoll_wait(int epfd,
        int error;
        struct file *file;
        struct eventpoll *ep;
+       struct latency_entry reason;
 
        DNPRINTK(3, (KERN_INFO "[%p] eventpoll: sys_epoll_wait(%d, %p, %d, 
%d)\n",
                     current, epfd, events, maxevents, timeout));
@@ -1227,6 +1229,8 @@ asmlinkage long sys_epoll_wait(int epfd,
        if (maxevents <= 0 || maxevents > EP_MAX_EVENTS)
                return -EINVAL;
 
+       set_latency_reason_user("Waiting for event (epoll)", &reason, 5000);
+
        /* Verify that the area passed by the user is writeable */
        if (!access_ok(VERIFY_WRITE, events, maxevents * sizeof(struct 
epoll_event))) {
                error = -EFAULT;
@@ -1262,6 +1266,7 @@ error_return:
        DNPRINTK(3, (KERN_INFO "[%p] eventpoll: sys_epoll_wait(%d, %p, %d, %d) 
= %d\n",
                     current, epfd, events, maxevents, timeout, error));
 
+       restore_latency_reason(&reason);
        return error;
 }
 
Index: linux-2.6.24-rc7/fs/ext3/inode.c
===================================================================
--- linux-2.6.24-rc7.orig/fs/ext3/inode.c
+++ linux-2.6.24-rc7/fs/ext3/inode.c
@@ -36,6 +36,7 @@
 #include <linux/mpage.h>
 #include <linux/uio.h>
 #include <linux/bio.h>
+#include <linux/latencytop.h>
 #include "xattr.h"
 #include "acl.h"
 
@@ -357,7 +358,9 @@ static Indirect *ext3_get_branch(struct 
        struct super_block *sb = inode->i_sb;
        Indirect *p = chain;
        struct buffer_head *bh;
+       struct latency_entry reason;
 
+       set_latency_reason("EXT3 - reading indirect blocks", &reason);
        *err = 0;
        /* i_data is not going away, no lock needed */
        add_chain (chain, NULL, EXT3_I(inode)->i_data + *offsets);
@@ -375,6 +378,7 @@ static Indirect *ext3_get_branch(struct 
                if (!p->key)
                        goto no_block;
        }
+       restore_latency_reason(&reason);
        return NULL;
 
 changed:
@@ -384,6 +388,7 @@ changed:
 failure:
        *err = -EIO;
 no_block:
+       restore_latency_reason(&reason);
        return p;
 }
 
@@ -1255,6 +1260,9 @@ static int ext3_ordered_write_end(struct
        struct inode *inode = file->f_mapping->host;
        unsigned from, to;
        int ret = 0, ret2;
+       struct latency_entry reason;
+
+       set_latency_reason("EXT3 ordered write", &reason);
 
        from = pos & (PAGE_CACHE_SIZE - 1);
        to = from + len;
@@ -1284,6 +1292,8 @@ static int ext3_ordered_write_end(struct
        unlock_page(page);
        page_cache_release(page);
 
+       restore_latency_reason(&reason);
+
        return ret ? ret : copied;
 }
 
@@ -1641,14 +1651,25 @@ out_unlock:
 
 static int ext3_readpage(struct file *file, struct page *page)
 {
-       return mpage_readpage(page, ext3_get_block);
+       int ret;
+       struct latency_entry reason;
+       set_latency_reason("EXT3 readpage", &reason);
+       ret = mpage_readpage(page, ext3_get_block);
+       restore_latency_reason(&reason);
+       return ret;
 }
 
 static int
 ext3_readpages(struct file *file, struct address_space *mapping,
                struct list_head *pages, unsigned nr_pages)
 {
-       return mpage_readpages(mapping, pages, nr_pages, ext3_get_block);
+       int ret;
+       struct latency_entry reason;
+       set_latency_reason("EXT3 readpages", &reason);
+       ret = mpage_readpages(mapping, pages, nr_pages, ext3_get_block);
+       restore_latency_reason(&reason);
+
+       return ret;
 }
 
 static void ext3_invalidatepage(struct page *page, unsigned long offset)
@@ -2665,6 +2686,9 @@ void ext3_read_inode(struct inode * inod
        struct ext3_inode_info *ei = EXT3_I(inode);
        struct buffer_head *bh;
        int block;
+       struct latency_entry reason;
+
+       set_latency_reason("EXT3 reading inode", &reason);
 
 #ifdef CONFIG_EXT3_FS_POSIX_ACL
        ei->i_acl = EXT3_ACL_NOT_CACHED;
@@ -2787,10 +2811,12 @@ void ext3_read_inode(struct inode * inod
        }
        brelse (iloc.bh);
        ext3_set_inode_flags(inode);
+       restore_latency_reason(&reason);
        return;
 
 bad_inode:
        make_bad_inode(inode);
+       restore_latency_reason(&reason);
        return;
 }
 
Index: linux-2.6.24-rc7/fs/inode.c
===================================================================
--- linux-2.6.24-rc7.orig/fs/inode.c
+++ linux-2.6.24-rc7/fs/inode.c
@@ -22,6 +22,7 @@
 #include <linux/bootmem.h>
 #include <linux/inotify.h>
 #include <linux/mount.h>
+#include <linux/latencytop.h>
 
 /*
  * This is needed for the following functions:
@@ -1202,6 +1203,7 @@ void touch_atime(struct vfsmount *mnt, s
 {
        struct inode *inode = dentry->d_inode;
        struct timespec now;
+       struct latency_entry reason;
 
        if (inode->i_flags & S_NOATIME)
                return;
@@ -1237,8 +1239,10 @@ void touch_atime(struct vfsmount *mnt, s
        if (timespec_equal(&inode->i_atime, &now))
                return;
 
+       set_latency_reason("updating atime", &reason);
        inode->i_atime = now;
        mark_inode_dirty_sync(inode);
+       restore_latency_reason(&reason);
 }
 EXPORT_SYMBOL(touch_atime);
 
@@ -1314,13 +1318,22 @@ int inode_wait(void *word)
 static void __wait_on_freeing_inode(struct inode *inode)
 {
        wait_queue_head_t *wq;
+       char buffer[32];
+       struct latency_entry reason;
        DEFINE_WAIT_BIT(wait, &inode->i_state, __I_LOCK);
+
+       sprintf(buffer, "%x:%x %lu %lx", MAJOR(inode->i_sb->s_dev),
+               MINOR(inode->i_sb->s_dev), inode->i_ino, inode->i_state);
+
+       set_latency_reason_param("Waiting for file delete to complete",
+                                                       buffer, &reason);
        wq = bit_waitqueue(&inode->i_state, __I_LOCK);
        prepare_to_wait(wq, &wait.wait, TASK_UNINTERRUPTIBLE);
        spin_unlock(&inode_lock);
        schedule();
        finish_wait(wq, &wait.wait);
        spin_lock(&inode_lock);
+       restore_latency_reason(&reason);
 }
 
 /*
Index: linux-2.6.24-rc7/fs/jbd/checkpoint.c
===================================================================
--- linux-2.6.24-rc7.orig/fs/jbd/checkpoint.c
+++ linux-2.6.24-rc7/fs/jbd/checkpoint.c
@@ -301,9 +301,11 @@ int log_do_checkpoint(journal_t *journal
        transaction_t *transaction;
        tid_t this_tid;
        int result;
+       struct latency_entry reason;
 
        jbd_debug(1, "Start checkpoint\n");
 
+
        /*
         * First thing: if there are any transactions in the log which
         * don't need checkpointing, just eliminate them from the
@@ -314,6 +316,8 @@ int log_do_checkpoint(journal_t *journal
        if (result <= 0)
                return result;
 
+       set_latency_reason("EXT3 (jbd) checkpointing", &reason);
+
        /*
         * OK, we need to start writing disk blocks.  Take one transaction
         * and write it.
@@ -375,6 +379,8 @@ restart:
 out:
        spin_unlock(&journal->j_list_lock);
        result = cleanup_journal_tail(journal);
+
+       restore_latency_reason(&reason);
        if (result < 0)
                return result;
        return 0;
Index: linux-2.6.24-rc7/fs/jbd/commit.c
===================================================================
--- linux-2.6.24-rc7.orig/fs/jbd/commit.c
+++ linux-2.6.24-rc7/fs/jbd/commit.c
@@ -104,6 +104,7 @@ static int journal_write_commit_record(j
 {
        struct journal_head *descriptor;
        struct buffer_head *bh;
+       struct latency_entry reason;
        int i, ret;
        int barrier_done = 0;
 
@@ -129,6 +130,9 @@ static int journal_write_commit_record(j
        if (journal->j_flags & JFS_BARRIER) {
                set_buffer_ordered(bh);
                barrier_done = 1;
+               set_latency_reason("Writing commit block (barrier)", &reason);
+       } else {
+               set_latency_reason("Writing commit block", &reason);
        }
        ret = sync_dirty_buffer(bh);
        /* is it possible for another commit to fail at roughly
@@ -156,6 +160,7 @@ static int journal_write_commit_record(j
        put_bh(bh);             /* One for getblk() */
        journal_put_journal_head(descriptor);
 
+       restore_latency_reason(&reason);
        return (ret == -EIO);
 }
 
Index: linux-2.6.24-rc7/fs/jbd/journal.c
===================================================================
--- linux-2.6.24-rc7.orig/fs/jbd/journal.c
+++ linux-2.6.24-rc7/fs/jbd/journal.c
@@ -36,6 +36,7 @@
 #include <linux/poison.h>
 #include <linux/proc_fs.h>
 #include <linux/debugfs.h>
+#include <linux/ioprio.h>
 
 #include <asm/uaccess.h>
 #include <asm/page.h>
@@ -1335,6 +1336,9 @@ int journal_flush(journal_t *journal)
        int err = 0;
        transaction_t *transaction = NULL;
        unsigned long old_tail;
+       struct latency_entry reason;
+
+       set_latency_reason("EXT3 (jbd) flushing journal", &reason);
 
        spin_lock(&journal->j_state_lock);
 
@@ -1384,6 +1388,7 @@ int journal_flush(journal_t *journal)
        J_ASSERT(journal->j_head == journal->j_tail);
        J_ASSERT(journal->j_tail_sequence == journal->j_transaction_sequence);
        spin_unlock(&journal->j_state_lock);
+       restore_latency_reason(&reason);
        return err;
 }
 
Index: linux-2.6.24-rc7/fs/jbd/transaction.c
===================================================================
--- linux-2.6.24-rc7.orig/fs/jbd/transaction.c
+++ linux-2.6.24-rc7/fs/jbd/transaction.c
@@ -25,6 +25,7 @@
 #include <linux/timer.h>
 #include <linux/mm.h>
 #include <linux/highmem.h>
+#include <linux/latencytop.h>
 
 static void __journal_temp_unlink_buffer(struct journal_head *jh);
 
@@ -85,6 +86,9 @@ static int start_this_handle(journal_t *
        int nblocks = handle->h_buffer_credits;
        transaction_t *new_transaction = NULL;
        int ret = 0;
+       struct latency_entry reason;
+
+       set_latency_reason("EXT3 (jbd) journal transaction", &reason);
 
        if (nblocks > journal->j_max_transaction_buffers) {
                printk(KERN_ERR "JBD: %s wants too many credits (%d > %d)\n",
@@ -229,6 +233,7 @@ repeat_locked:
 out:
        if (unlikely(new_transaction))          /* It's usually NULL */
                kfree(new_transaction);
+       restore_latency_reason(&reason);
        return ret;
 }
 
@@ -431,6 +436,9 @@ int journal_restart(handle_t *handle, in
 void journal_lock_updates(journal_t *journal)
 {
        DEFINE_WAIT(wait);
+       struct latency_entry reason;
+
+       set_latency_reason("EXT3 (jbd) transaction barrier", &reason);
 
        spin_lock(&journal->j_state_lock);
        ++journal->j_barrier_count;
@@ -464,6 +472,7 @@ void journal_lock_updates(journal_t *jou
         * too.
         */
        mutex_lock(&journal->j_barrier);
+       restore_latency_reason(&reason);
 }
 
 /**
@@ -535,10 +544,13 @@ do_get_write_access(handle_t *handle, st
        int error;
        char *frozen_buffer = NULL;
        int need_copy = 0;
+       struct latency_entry reason;
 
        if (is_handle_aborted(handle))
                return -EROFS;
 
+       set_latency_reason("EXT3 (jbd) do_get_write_access", &reason);
+
        transaction = handle->h_transaction;
        journal = transaction->t_journal;
 
@@ -737,6 +749,7 @@ out:
                jbd_free(frozen_buffer, bh->b_size);
 
        JBUFFER_TRACE(jh, "exit");
+       restore_latency_reason(&reason);
        return error;
 }
 
Index: linux-2.6.24-rc7/fs/pipe.c
===================================================================
--- linux-2.6.24-rc7.orig/fs/pipe.c
+++ linux-2.6.24-rc7/fs/pipe.c
@@ -17,6 +17,7 @@
 #include <linux/highmem.h>
 #include <linux/pagemap.h>
 #include <linux/audit.h>
+#include <linux/latencytop.h>
 
 #include <asm/uaccess.h>
 #include <asm/ioctls.h>
@@ -402,12 +403,15 @@ pipe_write(struct kiocb *iocb, const str
        struct iovec *iov = (struct iovec *)_iov;
        size_t total_len;
        ssize_t chars;
+       struct latency_entry reason;
 
        total_len = iov_length(iov, nr_segs);
        /* Null write succeeds. */
        if (unlikely(total_len == 0))
                return 0;
 
+       set_latency_reason("writing to a pipe", &reason);
+
        do_wakeup = 0;
        ret = 0;
        mutex_lock(&inode->i_mutex);
@@ -560,6 +564,7 @@ out:
        }
        if (ret > 0)
                file_update_time(filp);
+       restore_latency_reason(&reason);
        return ret;
 }
 
Index: linux-2.6.24-rc7/fs/select.c
===================================================================
--- linux-2.6.24-rc7.orig/fs/select.c
+++ linux-2.6.24-rc7/fs/select.c
@@ -186,6 +186,7 @@ int do_select(int n, fd_set_bits *fds, s
        struct poll_wqueues table;
        poll_table *wait;
        int retval, i;
+       struct latency_entry reason;
 
        rcu_read_lock();
        retval = max_select_fd(n, fds);
@@ -195,6 +196,7 @@ int do_select(int n, fd_set_bits *fds, s
                return retval;
        n = retval;
 
+       set_latency_reason_user("Waiting for event (select)", &reason, 5000);
        poll_initwait(&table);
        wait = &table.pt;
        if (!*timeout)
@@ -284,6 +286,7 @@ int do_select(int n, fd_set_bits *fds, s
 
        poll_freewait(&table);
 
+       restore_latency_reason(&reason);
        return retval;
 }
 
Index: linux-2.6.24-rc7/fs/sync.c
===================================================================
--- linux-2.6.24-rc7.orig/fs/sync.c
+++ linux-2.6.24-rc7/fs/sync.c
@@ -13,6 +13,7 @@
 #include <linux/pagemap.h>
 #include <linux/quotaops.h>
 #include <linux/buffer_head.h>
+#include <linux/latencytop.h>
 
 #define VALID_FLAGS (SYNC_FILE_RANGE_WAIT_BEFORE|SYNC_FILE_RANGE_WRITE| \
                        SYNC_FILE_RANGE_WAIT_AFTER)
@@ -38,7 +39,11 @@ static void do_sync(unsigned long wait)
 
 asmlinkage long sys_sync(void)
 {
+       struct latency_entry reason;
+       set_latency_reason("sync system call", &reason);
        do_sync(1);
+       restore_latency_reason(&reason);
+
        return 0;
 }
 
@@ -120,12 +125,22 @@ static long __do_fsync(unsigned int fd, 
 
 asmlinkage long sys_fsync(unsigned int fd)
 {
-       return __do_fsync(fd, 0);
+       long ret;
+       struct latency_entry reason;
+       set_latency_reason("fsync system call", &reason);
+       ret = __do_fsync(fd, 0);
+       restore_latency_reason(&reason);
+       return ret;
 }
 
 asmlinkage long sys_fdatasync(unsigned int fd)
 {
-       return __do_fsync(fd, 1);
+       long ret;
+       struct latency_entry reason;
+       set_latency_reason("fdatasync system call", &reason);
+       ret = __do_fsync(fd, 1);
+       restore_latency_reason(&reason);
+       return ret;
 }
 
 /*
Index: linux-2.6.24-rc7/kernel/fork.c
===================================================================
--- linux-2.6.24-rc7.orig/kernel/fork.c
+++ linux-2.6.24-rc7/kernel/fork.c
@@ -1411,6 +1411,9 @@ long do_fork(unsigned long clone_flags,
        struct task_struct *p;
        int trace = 0;
        long nr;
+       struct latency_entry reason;
+
+       set_latency_reason("process fork", &reason);
 
        if (unlikely(current->ptrace)) {
                trace = fork_traceflag (clone_flags);
@@ -1473,6 +1476,7 @@ long do_fork(unsigned long clone_flags,
        } else {
                nr = PTR_ERR(p);
        }
+       restore_latency_reason(&reason);
        return nr;
 }
 
Index: linux-2.6.24-rc7/kernel/futex.c
===================================================================
--- linux-2.6.24-rc7.orig/kernel/futex.c
+++ linux-2.6.24-rc7/kernel/futex.c
@@ -2051,9 +2051,11 @@ asmlinkage long sys_futex(u32 __user *ua
                          u32 val3)
 {
        struct timespec ts;
+       long ret;
        ktime_t t, *tp = NULL;
        u32 val2 = 0;
        int cmd = op & FUTEX_CMD_MASK;
+       struct latency_entry reason;
 
        if (utime && (cmd == FUTEX_WAIT || cmd == FUTEX_LOCK_PI)) {
                if (copy_from_user(&ts, utime, sizeof(ts)) != 0)
@@ -2074,7 +2076,11 @@ asmlinkage long sys_futex(u32 __user *ua
            cmd == FUTEX_WAKE_OP)
                val2 = (u32) (unsigned long) utime;
 
-       return do_futex(uaddr, op, val, tp, uaddr2, val2, val3);
+       set_latency_reason_user("Userspace lock contention (futex)",
+                               &reason, 5000);
+       ret = do_futex(uaddr, op, val, tp, uaddr2, val2, val3);
+       restore_latency_reason(&reason);
+       return ret;
 }
 
 static int futexfs_get_sb(struct file_system_type *fs_type,
Index: linux-2.6.24-rc7/kernel/mutex.c
===================================================================
--- linux-2.6.24-rc7.orig/kernel/mutex.c
+++ linux-2.6.24-rc7/kernel/mutex.c
@@ -18,6 +18,7 @@
 #include <linux/spinlock.h>
 #include <linux/interrupt.h>
 #include <linux/debug_locks.h>
+#include <linux/latencytop.h>
 
 /*
  * In the DEBUG case we are using the "NULL fastpath" for mutexes,
@@ -298,8 +299,20 @@ static void fastcall noinline __sched
 __mutex_lock_slowpath(atomic_t *lock_count)
 {
        struct mutex *lock = container_of(lock_count, struct mutex, count);
+       struct latency_entry reason;
 
+#ifdef CONFIG_DEBUG_MUTEXES
+       /* do something with ->owner here */
+#endif
+#ifdef CONFIG_DEBUG_LOCK_ALLOC
+       char *name;
+       name = lock->dep_map.name;
+       set_latency_reason_param("mutex lock", name, &reason);
+#else
+       set_latency_reason("mutex lock", &reason);
+#endif
        __mutex_lock_common(lock, TASK_UNINTERRUPTIBLE, 0, _RET_IP_);
+       restore_latency_reason(&reason);
 }
 
 static int fastcall noinline __sched
Index: linux-2.6.24-rc7/kernel/rwsem.c
===================================================================
--- linux-2.6.24-rc7.orig/kernel/rwsem.c
+++ linux-2.6.24-rc7/kernel/rwsem.c
@@ -9,6 +9,7 @@
 #include <linux/sched.h>
 #include <linux/module.h>
 #include <linux/rwsem.h>
+#include <linux/latencytop.h>
 
 #include <asm/system.h>
 #include <asm/atomic.h>
@@ -18,10 +19,15 @@
  */
 void __sched down_read(struct rw_semaphore *sem)
 {
+       struct latency_entry reason;
+
        might_sleep();
-       rwsem_acquire_read(&sem->dep_map, 0, 0, _RET_IP_);
+       set_latency_reason("rwsem read lock", &reason);
 
+       rwsem_acquire_read(&sem->dep_map, 0, 0, _RET_IP_);
        LOCK_CONTENDED(sem, __down_read_trylock, __down_read);
+
+       restore_latency_reason(&reason);
 }
 
 EXPORT_SYMBOL(down_read);
@@ -45,10 +51,14 @@ EXPORT_SYMBOL(down_read_trylock);
  */
 void __sched down_write(struct rw_semaphore *sem)
 {
+       struct latency_entry reason;
+       set_latency_reason("rwsem write lock", &reason);
        might_sleep();
+
        rwsem_acquire(&sem->dep_map, 0, 0, _RET_IP_);
 
        LOCK_CONTENDED(sem, __down_write_trylock, __down_write);
+       restore_latency_reason(&reason);
 }
 
 EXPORT_SYMBOL(down_write);
Index: linux-2.6.24-rc7/mm/filemap.c
===================================================================
--- linux-2.6.24-rc7.orig/mm/filemap.c
+++ linux-2.6.24-rc7/mm/filemap.c
@@ -525,10 +525,13 @@ static inline void wake_up_page(struct p
 void fastcall wait_on_page_bit(struct page *page, int bit_nr)
 {
        DEFINE_WAIT_BIT(wait, &page->flags, bit_nr);
+       struct latency_entry reason;
+       set_latency_reason("Waiting for page IO/lock", &reason);
 
        if (test_bit(bit_nr, &page->flags))
                __wait_on_bit(page_waitqueue(page), &wait, sync_page,
                                                        TASK_UNINTERRUPTIBLE);
+       restore_latency_reason(&reason);
 }
 EXPORT_SYMBOL(wait_on_page_bit);
 
@@ -583,9 +586,12 @@ EXPORT_SYMBOL(end_page_writeback);
 void fastcall __lock_page(struct page *page)
 {
        DEFINE_WAIT_BIT(wait, &page->flags, PG_locked);
+       struct latency_entry reason;
+       set_latency_reason("locking page", &reason);
 
        __wait_on_bit_lock(page_waitqueue(page), &wait, sync_page,
                                                        TASK_UNINTERRUPTIBLE);
+       restore_latency_reason(&reason);
 }
 EXPORT_SYMBOL(__lock_page);
 
Index: linux-2.6.24-rc7/mm/slub.c
===================================================================
--- linux-2.6.24-rc7.orig/mm/slub.c
+++ linux-2.6.24-rc7/mm/slub.c
@@ -1566,7 +1566,12 @@ static void __always_inline *slab_alloc(
 
 void *kmem_cache_alloc(struct kmem_cache *s, gfp_t gfpflags)
 {
-       return slab_alloc(s, gfpflags, -1, __builtin_return_address(0));
+       void *ptr;
+       struct latency_entry reason;
+       set_latency_reason("Allocating slab memory", &reason);
+       ptr = slab_alloc(s, gfpflags, -1, __builtin_return_address(0));
+       restore_latency_reason(&reason);
+       return ptr;
 }
 EXPORT_SYMBOL(kmem_cache_alloc);
 
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

Reply via email to