Commit 8b60785c authored by Martin Brandenburg's avatar Martin Brandenburg Committed by Mike Marshall
Browse files

orangefs: simplify orangefs_inode_getattr interface



No need to store the received mask.  It is either STATX_BASIC_STATS or
STATX_BASIC_STATS & ~STATX_SIZE.  If STATX_SIZE is requested, the cache
is bypassed anyway, so the cached mask is unnecessary to decide whether
to do a real getattr.

This is a change.  Previously a getattr would want size and use the
cached size.  All of the in-kernel callers that wanted size did not want
a cached size.  Now a getattr cannot use the cached size if it wants
size at all.

Signed-off-by: default avatarMartin Brandenburg <martin@omnibond.com>
Signed-off-by: default avatarMike Marshall <hubcap@omnibond.com>
parent 66d5477d
Loading
Loading
Loading
Loading
+8 −9
Original line number Diff line number Diff line
@@ -420,8 +420,8 @@ static ssize_t orangefs_file_write_iter(struct kiocb *iocb, struct iov_iter *ite

	/* Make sure generic_write_checks sees an up to date inode size. */
	if (file->f_flags & O_APPEND) {
		rc = orangefs_inode_getattr(file->f_mapping->host, 0, 1,
		    STATX_SIZE);
		rc = orangefs_inode_getattr(file->f_mapping->host,
		    ORANGEFS_GETATTR_SIZE);
		if (rc == -ESTALE)
			rc = -EIO;
		if (rc) {
@@ -528,14 +528,13 @@ static vm_fault_t orangefs_fault(struct vm_fault *vmf)
{
	struct file *file = vmf->vma->vm_file;
	int ret;

	ret = orangefs_inode_getattr(file->f_mapping->host, 0, 1,
	    STATX_SIZE);
	ret = orangefs_inode_getattr(file->f_mapping->host,
	    ORANGEFS_GETATTR_SIZE);
	if (ret == -ESTALE)
		ret = -EIO;
	if (ret) {
		gossip_err("%s: orangefs_inode_getattr failed, ret:%d:.\n",
				__func__, ret);
		gossip_err("%s: orangefs_inode_getattr failed, "
		    "ret:%d:.\n", __func__, ret);
		return VM_FAULT_SIGBUS;
	}
	return filemap_fault(vmf);
@@ -656,8 +655,8 @@ static loff_t orangefs_file_llseek(struct file *file, loff_t offset, int origin)
		 * NOTE: We are only interested in file size here,
		 * so we set mask accordingly.
		 */
		ret = orangefs_inode_getattr(file->f_mapping->host, 0, 1,
		    STATX_SIZE);
		ret = orangefs_inode_getattr(file->f_mapping->host,
		    ORANGEFS_GETATTR_SIZE);
		if (ret == -ESTALE)
			ret = -EIO;
		if (ret) {
+6 −5
Original line number Diff line number Diff line
@@ -162,7 +162,7 @@ static int orangefs_setattr_size(struct inode *inode, struct iattr *iattr)
		     iattr->ia_size);

	/* Ensure that we have a up to date size, so we know if it changed. */
	ret = orangefs_inode_getattr(inode, 0, 1, STATX_SIZE);
	ret = orangefs_inode_getattr(inode, ORANGEFS_GETATTR_SIZE);
	if (ret == -ESTALE)
		ret = -EIO;
	if (ret) {
@@ -256,7 +256,8 @@ int orangefs_getattr(const struct path *path, struct kstat *stat,
		     "orangefs_getattr: called on %pd\n",
		     path->dentry);

	ret = orangefs_inode_getattr(inode, 0, 0, request_mask);
	ret = orangefs_inode_getattr(inode,
	    request_mask & STATX_SIZE ? ORANGEFS_GETATTR_SIZE : 0);
	if (ret == 0) {
		generic_fillattr(inode, stat);

@@ -284,7 +285,7 @@ int orangefs_permission(struct inode *inode, int mask)
	gossip_debug(GOSSIP_INODE_DEBUG, "%s: refreshing\n", __func__);

	/* Make sure the permission (and other common attrs) are up to date. */
	ret = orangefs_inode_getattr(inode, 0, 0, STATX_MODE);
	ret = orangefs_inode_getattr(inode, 0);
	if (ret < 0)
		return ret;

@@ -410,7 +411,7 @@ struct inode *orangefs_iget(struct super_block *sb,
	if (!(inode->i_state & I_NEW))
		return inode;

	error = orangefs_inode_getattr(inode, 1, 1, STATX_ALL);
	error = orangefs_inode_getattr(inode, ORANGEFS_GETATTR_NEW);
	if (error) {
		iget_failed(inode);
		return ERR_PTR(error);
@@ -455,7 +456,7 @@ struct inode *orangefs_new_inode(struct super_block *sb, struct inode *dir,
	orangefs_set_inode(inode, ref);
	inode->i_ino = hash;	/* needed for stat etc */

	error = orangefs_inode_getattr(inode, 1, 1, STATX_ALL);
	error = orangefs_inode_getattr(inode, ORANGEFS_GETATTR_NEW);
	if (error)
		goto out_iput;

+4 −3
Original line number Diff line number Diff line
@@ -193,7 +193,6 @@ struct orangefs_inode_s {
	sector_t last_failed_block_index_read;

	unsigned long getattr_time;
	u32 getattr_mask;

	DECLARE_HASHTABLE(xattr_cache, 4);
};
@@ -397,8 +396,10 @@ int orangefs_inode_setxattr(struct inode *inode,
			 size_t size,
			 int flags);

int orangefs_inode_getattr(struct inode *inode, int new, int bypass,
    u32 request_mask);
#define ORANGEFS_GETATTR_NEW 1
#define ORANGEFS_GETATTR_SIZE 2

int orangefs_inode_getattr(struct inode *, int);

int orangefs_inode_check_changed(struct inode *inode);

+10 −21
Original line number Diff line number Diff line
// SPDX-License-Identifier: GPL-2.0
/*
 * (C) 2001 Clemson University and The University of Chicago
 * Copyright 2018 Omnibond Systems, L.L.C.
 *
 * See COPYING in top-level directory.
 */
@@ -272,8 +273,7 @@ static int orangefs_inode_is_stale(struct inode *inode,
	return 0;
}

int orangefs_inode_getattr(struct inode *inode, int new, int bypass,
    u32 request_mask)
int orangefs_inode_getattr(struct inode *inode, int flags)
{
	struct orangefs_inode_s *orangefs_inode = ORANGEFS_I(inode);
	struct orangefs_kernel_op_s *new_op;
@@ -283,16 +283,9 @@ int orangefs_inode_getattr(struct inode *inode, int new, int bypass,
	gossip_debug(GOSSIP_UTILS_DEBUG, "%s: called on inode %pU\n", __func__,
	    get_khandle_from_ino(inode));

	if (!new && !bypass) {
		/*
		 * Must have all the attributes in the mask and be within cache
		 * time.
		 */
		if ((request_mask & orangefs_inode->getattr_mask) ==
		    request_mask &&
		    time_before(jiffies, orangefs_inode->getattr_time))
	/* Must have all the attributes in the mask and be within cache time. */
	if (!flags && time_before(jiffies, orangefs_inode->getattr_time))
		return 0;
	}

	new_op = op_alloc(ORANGEFS_VFS_OP_GETATTR);
	if (!new_op)
@@ -302,7 +295,7 @@ int orangefs_inode_getattr(struct inode *inode, int new, int bypass,
	 * Size is the hardest attribute to get.  The incremental cost of any
	 * other attribute is essentially zero.
	 */
	if (request_mask & STATX_SIZE || new)
	if (flags)
		new_op->upcall.req.getattr.mask = ORANGEFS_ATTR_SYS_ALL_NOHINT;
	else
		new_op->upcall.req.getattr.mask =
@@ -313,7 +306,7 @@ int orangefs_inode_getattr(struct inode *inode, int new, int bypass,
	if (ret != 0)
		goto out;

	if (!new) {
	if (!(flags & ORANGEFS_GETATTR_NEW)) {
		ret = orangefs_inode_is_stale(inode,
		    &new_op->downcall.resp.getattr.attributes,
		    new_op->downcall.resp.getattr.link_target);
@@ -329,7 +322,7 @@ int orangefs_inode_getattr(struct inode *inode, int new, int bypass,
	case S_IFREG:
		inode->i_flags = orangefs_inode_flags(&new_op->
		    downcall.resp.getattr.attributes);
		if (request_mask & STATX_SIZE || new) {
		if (flags) {
			inode_size = (loff_t)new_op->
			    downcall.resp.getattr.attributes.size;
			inode->i_size = inode_size;
@@ -343,7 +336,7 @@ int orangefs_inode_getattr(struct inode *inode, int new, int bypass,
		}
		break;
	case S_IFDIR:
		if (request_mask & STATX_SIZE || new) {
		if (flags) {
			inode->i_size = PAGE_SIZE;
			spin_lock(&inode->i_lock);
			inode_set_bytes(inode, inode->i_size);
@@ -352,7 +345,7 @@ int orangefs_inode_getattr(struct inode *inode, int new, int bypass,
		set_nlink(inode, 1);
		break;
	case S_IFLNK:
		if (new) {
		if (flags & ORANGEFS_GETATTR_NEW) {
			inode->i_size = (loff_t)strlen(new_op->
			    downcall.resp.getattr.link_target);
			ret = strscpy(orangefs_inode->link_target,
@@ -393,10 +386,6 @@ int orangefs_inode_getattr(struct inode *inode, int new, int bypass,

	orangefs_inode->getattr_time = jiffies +
	    orangefs_getattr_timeout_msecs*HZ/1000;
	if (request_mask & STATX_SIZE || new)
		orangefs_inode->getattr_mask = STATX_BASIC_STATS;
	else
		orangefs_inode->getattr_mask = STATX_BASIC_STATS & ~STATX_SIZE;
	ret = 0;
out:
	op_release(new_op);