diff options
author | Jeff Layton <jlayton@poochiereds.net> | 2014-05-09 14:13:05 -0400 |
---|---|---|
committer | Jeff Layton <jlayton@poochiereds.net> | 2014-06-02 08:09:30 -0400 |
commit | 62af4f1f7df44ea0bb1a11c94ac9fb384bf1c564 (patch) | |
tree | 5fdc044c1d7eed924a90d101a306ba53617ebac2 /fs/locks.c | |
parent | 5315c26a6c557f44733725004fc7dc25c8a94cd5 (diff) |
locks: add some tracepoints in the lease handling code
v2: add a __break_lease tracepoint for non-blocking case
Recently, I needed these to help track down a softlockup when recalling a
delegation, but they might be helpful in other situations as well.
Cc: "J. Bruce Fields" <bfields@fieldses.org>
Signed-off-by: Jeff Layton <jlayton@poochiereds.net>
Diffstat (limited to 'fs/locks.c')
-rw-r--r-- | fs/locks.c | 11 |
1 files changed, 11 insertions, 0 deletions
diff --git a/fs/locks.c b/fs/locks.c index facf76d9fcb4..da57c9b7e844 100644 --- a/fs/locks.c +++ b/fs/locks.c | |||
@@ -130,6 +130,9 @@ | |||
130 | #include <linux/percpu.h> | 130 | #include <linux/percpu.h> |
131 | #include <linux/lglock.h> | 131 | #include <linux/lglock.h> |
132 | 132 | ||
133 | #define CREATE_TRACE_POINTS | ||
134 | #include <trace/events/filelock.h> | ||
135 | |||
133 | #include <asm/uaccess.h> | 136 | #include <asm/uaccess.h> |
134 | 137 | ||
135 | #define IS_POSIX(fl) (fl->fl_flags & FL_POSIX) | 138 | #define IS_POSIX(fl) (fl->fl_flags & FL_POSIX) |
@@ -1287,6 +1290,7 @@ static void time_out_leases(struct inode *inode) | |||
1287 | 1290 | ||
1288 | before = &inode->i_flock; | 1291 | before = &inode->i_flock; |
1289 | while ((fl = *before) && IS_LEASE(fl) && lease_breaking(fl)) { | 1292 | while ((fl = *before) && IS_LEASE(fl) && lease_breaking(fl)) { |
1293 | trace_time_out_leases(inode, fl); | ||
1290 | if (past_time(fl->fl_downgrade_time)) | 1294 | if (past_time(fl->fl_downgrade_time)) |
1291 | lease_modify(before, F_RDLCK); | 1295 | lease_modify(before, F_RDLCK); |
1292 | if (past_time(fl->fl_break_time)) | 1296 | if (past_time(fl->fl_break_time)) |
@@ -1374,6 +1378,7 @@ int __break_lease(struct inode *inode, unsigned int mode, unsigned int type) | |||
1374 | } | 1378 | } |
1375 | 1379 | ||
1376 | if (i_have_this_lease || (mode & O_NONBLOCK)) { | 1380 | if (i_have_this_lease || (mode & O_NONBLOCK)) { |
1381 | trace_break_lease_noblock(inode, new_fl); | ||
1377 | error = -EWOULDBLOCK; | 1382 | error = -EWOULDBLOCK; |
1378 | goto out; | 1383 | goto out; |
1379 | } | 1384 | } |
@@ -1385,10 +1390,12 @@ restart: | |||
1385 | if (break_time == 0) | 1390 | if (break_time == 0) |
1386 | break_time++; | 1391 | break_time++; |
1387 | locks_insert_block(flock, new_fl); | 1392 | locks_insert_block(flock, new_fl); |
1393 | trace_break_lease_block(inode, new_fl); | ||
1388 | spin_unlock(&inode->i_lock); | 1394 | spin_unlock(&inode->i_lock); |
1389 | error = wait_event_interruptible_timeout(new_fl->fl_wait, | 1395 | error = wait_event_interruptible_timeout(new_fl->fl_wait, |
1390 | !new_fl->fl_next, break_time); | 1396 | !new_fl->fl_next, break_time); |
1391 | spin_lock(&inode->i_lock); | 1397 | spin_lock(&inode->i_lock); |
1398 | trace_break_lease_unblock(inode, new_fl); | ||
1392 | locks_delete_block(new_fl); | 1399 | locks_delete_block(new_fl); |
1393 | if (error >= 0) { | 1400 | if (error >= 0) { |
1394 | if (error == 0) | 1401 | if (error == 0) |
@@ -1510,6 +1517,8 @@ static int generic_add_lease(struct file *filp, long arg, struct file_lock **flp | |||
1510 | int error; | 1517 | int error; |
1511 | 1518 | ||
1512 | lease = *flp; | 1519 | lease = *flp; |
1520 | trace_generic_add_lease(inode, lease); | ||
1521 | |||
1513 | /* | 1522 | /* |
1514 | * In the delegation case we need mutual exclusion with | 1523 | * In the delegation case we need mutual exclusion with |
1515 | * a number of operations that take the i_mutex. We trylock | 1524 | * a number of operations that take the i_mutex. We trylock |
@@ -1599,6 +1608,8 @@ static int generic_delete_lease(struct file *filp, struct file_lock **flp) | |||
1599 | struct dentry *dentry = filp->f_path.dentry; | 1608 | struct dentry *dentry = filp->f_path.dentry; |
1600 | struct inode *inode = dentry->d_inode; | 1609 | struct inode *inode = dentry->d_inode; |
1601 | 1610 | ||
1611 | trace_generic_delete_lease(inode, *flp); | ||
1612 | |||
1602 | for (before = &inode->i_flock; | 1613 | for (before = &inode->i_flock; |
1603 | ((fl = *before) != NULL) && IS_LEASE(fl); | 1614 | ((fl = *before) != NULL) && IS_LEASE(fl); |
1604 | before = &fl->fl_next) { | 1615 | before = &fl->fl_next) { |