From mboxrd@z Thu Jan 1 00:00:00 1970 From: Andy Adamson Subject: [PATCH 6 of 10] RESEND lease interfaces for version 4 NFSD Date: Tue, 21 Sep 2004 18:36:06 -0400 Sender: linux-fsdevel-owner@vger.kernel.org Message-ID: <1095804047.21441d5b.6@citi.umich.edu> Cc: nfsv4@linux-nfs.org, willy@debian.org Return-path: Received: from thnk.citi.umich.edu ([141.211.133.95]:18565 "EHLO thnk.citi.umich.edu") by vger.kernel.org with ESMTP id S266793AbUIUWgh (ORCPT ); Tue, 21 Sep 2004 18:36:37 -0400 To: linux-fsdevel@vger.kernel.org List-Id: linux-fsdevel.vger.kernel.org VFS: nfsd will not have a file descriptor, nor an owner on the filp. nfsd also will not use signals. Seperate the lease processsing coe from fcntl_setlease() into a __setlease() call. Signed-off-by: Andy Adamson --- linux-2.6.9-rc2-andros/fs/locks.c | 99 ++++++++++++++++++++++++++------------ 1 files changed, 68 insertions(+), 31 deletions(-) diff -puN fs/locks.c~fcntl_setlease fs/locks.c --- linux-2.6.9-rc2/fs/locks.c~fcntl_setlease 2004-09-21 18:00:29.034553256 -0400 +++ linux-2.6.9-rc2-andros/fs/locks.c 2004-09-21 18:00:29.040552344 -0400 @@ -1255,37 +1255,29 @@ int fcntl_getlease(struct file *filp) } /** - * fcntl_setlease - sets a lease on an open file - * @fd: open file descriptor + * __setlease - sets a lease on an open file * @filp: file pointer * @arg: type of lease to obtain + * @flp: input - file_lock to use, output - file_lock inserted * - * Call this fcntl to establish a lease on the file. - * Note that you also need to call %F_SETSIG to - * receive a signal when the lease is broken. + * The (input) flp->fl_lmops->fl_break function is required + * by break_lease(). + * + * Called with kernel lock held. */ -int fcntl_setlease(unsigned int fd, struct file *filp, long arg) +int __setlease(struct file *filp, long arg, struct file_lock **flp) { - struct file_lock *fl, **before, **my_before = NULL; - struct dentry *dentry; - struct inode *inode; + struct file_lock *fl, **before, **my_before = NULL, *lease = *flp; + struct dentry *dentry = filp->f_dentry; + struct inode *inode = dentry->d_inode; int error, rdlease_count = 0, wrlease_count = 0; - dentry = filp->f_dentry; - inode = dentry->d_inode; - - if ((current->fsuid != inode->i_uid) && !capable(CAP_LEASE)) - return -EACCES; - if (!S_ISREG(inode->i_mode)) - return -EINVAL; - error = security_file_lock(filp, arg); - if (error) - return error; - - lock_kernel(); - time_out_leases(inode); + error = -EINVAL; + if (!flp || !(*flp) || !(*flp)->fl_lmops || !(*flp)->fl_lmops->fl_break) + goto out; + /* * FIXME: What about F_RDLCK and files open for writing? */ @@ -1293,7 +1285,7 @@ int fcntl_setlease(unsigned int fd, stru if ((arg == F_WRLCK) && ((atomic_read(&dentry->d_count) > 1) || (atomic_read(&inode->i_count) > 1))) - goto out_unlock; + goto out; /* * At this point, we know that if there is an exclusive @@ -1321,33 +1313,78 @@ int fcntl_setlease(unsigned int fd, stru if ((arg == F_RDLCK && (wrlease_count > 0)) || (arg == F_WRLCK && ((rdlease_count + wrlease_count) > 0))) - goto out_unlock; + goto out; if (my_before != NULL) { error = lease_modify(my_before, arg); - goto out_unlock; + goto out; } error = 0; if (arg == F_UNLCK) - goto out_unlock; + goto out; error = -EINVAL; if (!leases_enable) - goto out_unlock; + goto out; error = lease_alloc(filp, arg, &fl); if (error) + goto out; + + locks_copy_lock(fl, lease); + + locks_insert_lock(before, fl); + +out: + return error; +} + +/** + * fcntl_setlease - sets a lease on an open file + * @fd: open file descriptor + * @filp: file pointer + * @arg: type of lease to obtain + * + * Call this fcntl to establish a lease on the file. + * Note that you also need to call %F_SETSIG to + * receive a signal when the lease is broken. + */ +int fcntl_setlease(unsigned int fd, struct file *filp, long arg) +{ + struct file_lock fl, *flp = &fl; + struct dentry *dentry = filp->f_dentry; + struct inode *inode = dentry->d_inode; + int error; + + if ((current->fsuid != inode->i_uid) && !capable(CAP_LEASE)) + return -EACCES; + if (!S_ISREG(inode->i_mode)) + return -EINVAL; + error = security_file_lock(filp, arg); + if (error) + return error; + + locks_init_lock(&fl); + error = lease_init(filp, arg, &fl); + if (error) + return error; + + lock_kernel(); + + error = __setlease(filp, arg, &flp); + if (error) goto out_unlock; - error = fasync_helper(fd, filp, 1, &fl->fl_fasync); + error = fasync_helper(fd, filp, 1, &flp->fl_fasync); if (error < 0) { - locks_free_lock(fl); + /* remove lease just inserted by __setlease */ + flp->fl_type = F_UNLCK | F_INPROGRESS; + flp->fl_break_time = jiffies- 10; + time_out_leases(inode); goto out_unlock; } - locks_insert_lock(before, fl); - error = f_setown(filp, current->pid, 0); out_unlock: unlock_kernel(); _