Commit 71680c18 authored by Martin Brandenburg's avatar Martin Brandenburg

orangefs: Cache getattr results.

The userspace component attempts to do this, but this will prevent
us from even needing to go into userspace to satisfy certain getattr
requests.
Signed-off-by: default avatarMartin Brandenburg <martin@omnibond.com>
parent 31b7c1ab
...@@ -262,7 +262,7 @@ int orangefs_getattr(struct vfsmount *mnt, ...@@ -262,7 +262,7 @@ int orangefs_getattr(struct vfsmount *mnt,
"orangefs_getattr: called on %s\n", "orangefs_getattr: called on %s\n",
dentry->d_name.name); dentry->d_name.name);
ret = orangefs_inode_getattr(inode, 0, 1); ret = orangefs_inode_getattr(inode, 0, 0);
if (ret == 0) { if (ret == 0) {
generic_fillattr(inode, kstat); generic_fillattr(inode, kstat);
...@@ -384,7 +384,7 @@ struct inode *orangefs_iget(struct super_block *sb, struct orangefs_object_kref ...@@ -384,7 +384,7 @@ struct inode *orangefs_iget(struct super_block *sb, struct orangefs_object_kref
if (!inode || !(inode->i_state & I_NEW)) if (!inode || !(inode->i_state & I_NEW))
return inode; return inode;
error = orangefs_inode_getattr(inode, 1, 0); error = orangefs_inode_getattr(inode, 1, 1);
if (error) { if (error) {
iget_failed(inode); iget_failed(inode);
return ERR_PTR(error); return ERR_PTR(error);
...@@ -429,7 +429,7 @@ struct inode *orangefs_new_inode(struct super_block *sb, struct inode *dir, ...@@ -429,7 +429,7 @@ struct inode *orangefs_new_inode(struct super_block *sb, struct inode *dir,
orangefs_set_inode(inode, ref); orangefs_set_inode(inode, ref);
inode->i_ino = hash; /* needed for stat etc */ inode->i_ino = hash; /* needed for stat etc */
error = orangefs_inode_getattr(inode, 1, 0); error = orangefs_inode_getattr(inode, 1, 1);
if (error) if (error)
goto out_iput; goto out_iput;
......
...@@ -73,6 +73,7 @@ static int orangefs_create(struct inode *dir, ...@@ -73,6 +73,7 @@ static int orangefs_create(struct inode *dir,
d_instantiate(dentry, inode); d_instantiate(dentry, inode);
unlock_new_inode(inode); unlock_new_inode(inode);
dentry->d_time = jiffies + HZ; dentry->d_time = jiffies + HZ;
ORANGEFS_I(inode)->getattr_time = 0;
gossip_debug(GOSSIP_NAME_DEBUG, gossip_debug(GOSSIP_NAME_DEBUG,
"%s: dentry instantiated for %s\n", "%s: dentry instantiated for %s\n",
...@@ -192,6 +193,8 @@ static struct dentry *orangefs_lookup(struct inode *dir, struct dentry *dentry, ...@@ -192,6 +193,8 @@ static struct dentry *orangefs_lookup(struct inode *dir, struct dentry *dentry,
goto out; goto out;
} }
ORANGEFS_I(inode)->getattr_time = 0;
gossip_debug(GOSSIP_NAME_DEBUG, gossip_debug(GOSSIP_NAME_DEBUG,
"%s:%s:%d " "%s:%s:%d "
"Found good inode [%lu] with count [%d]\n", "Found good inode [%lu] with count [%d]\n",
...@@ -320,6 +323,7 @@ static int orangefs_symlink(struct inode *dir, ...@@ -320,6 +323,7 @@ static int orangefs_symlink(struct inode *dir,
d_instantiate(dentry, inode); d_instantiate(dentry, inode);
unlock_new_inode(inode); unlock_new_inode(inode);
dentry->d_time = jiffies + HZ; dentry->d_time = jiffies + HZ;
ORANGEFS_I(inode)->getattr_time = 0;
gossip_debug(GOSSIP_NAME_DEBUG, gossip_debug(GOSSIP_NAME_DEBUG,
"Inode (Symlink) %pU -> %s\n", "Inode (Symlink) %pU -> %s\n",
...@@ -383,6 +387,7 @@ static int orangefs_mkdir(struct inode *dir, struct dentry *dentry, umode_t mode ...@@ -383,6 +387,7 @@ static int orangefs_mkdir(struct inode *dir, struct dentry *dentry, umode_t mode
d_instantiate(dentry, inode); d_instantiate(dentry, inode);
unlock_new_inode(inode); unlock_new_inode(inode);
dentry->d_time = jiffies + HZ; dentry->d_time = jiffies + HZ;
ORANGEFS_I(inode)->getattr_time = 0;
gossip_debug(GOSSIP_NAME_DEBUG, gossip_debug(GOSSIP_NAME_DEBUG,
"Inode (Directory) %pU -> %s\n", "Inode (Directory) %pU -> %s\n",
...@@ -413,6 +418,8 @@ static int orangefs_rename(struct inode *old_dir, ...@@ -413,6 +418,8 @@ static int orangefs_rename(struct inode *old_dir,
"orangefs_rename: called (%pd2 => %pd2) ct=%d\n", "orangefs_rename: called (%pd2 => %pd2) ct=%d\n",
old_dentry, new_dentry, d_count(new_dentry)); old_dentry, new_dentry, d_count(new_dentry));
ORANGEFS_I(new_dentry->d_parent->d_inode)->getattr_time = 0;
new_op = op_alloc(ORANGEFS_VFS_OP_RENAME); new_op = op_alloc(ORANGEFS_VFS_OP_RENAME);
if (!new_op) if (!new_op)
return -EINVAL; return -EINVAL;
......
...@@ -246,6 +246,8 @@ struct orangefs_inode_s { ...@@ -246,6 +246,8 @@ struct orangefs_inode_s {
* with this object * with this object
*/ */
unsigned long pinode_flags; unsigned long pinode_flags;
unsigned long getattr_time;
}; };
#define P_ATIME_FLAG 0 #define P_ATIME_FLAG 0
...@@ -527,7 +529,7 @@ int orangefs_inode_setxattr(struct inode *inode, ...@@ -527,7 +529,7 @@ int orangefs_inode_setxattr(struct inode *inode,
size_t size, size_t size,
int flags); int flags);
int orangefs_inode_getattr(struct inode *inode, int new, int size); int orangefs_inode_getattr(struct inode *inode, int new, int bypass);
int orangefs_inode_check_changed(struct inode *inode); int orangefs_inode_check_changed(struct inode *inode);
......
...@@ -251,7 +251,7 @@ static int orangefs_inode_is_stale(struct inode *inode, int new, ...@@ -251,7 +251,7 @@ static int orangefs_inode_is_stale(struct inode *inode, int new,
return 0; return 0;
} }
int orangefs_inode_getattr(struct inode *inode, int new, int size) int orangefs_inode_getattr(struct inode *inode, int new, int bypass)
{ {
struct orangefs_inode_s *orangefs_inode = ORANGEFS_I(inode); struct orangefs_inode_s *orangefs_inode = ORANGEFS_I(inode);
struct orangefs_kernel_op_s *new_op; struct orangefs_kernel_op_s *new_op;
...@@ -261,12 +261,16 @@ int orangefs_inode_getattr(struct inode *inode, int new, int size) ...@@ -261,12 +261,16 @@ int orangefs_inode_getattr(struct inode *inode, int new, int size)
gossip_debug(GOSSIP_UTILS_DEBUG, "%s: called on inode %pU\n", __func__, gossip_debug(GOSSIP_UTILS_DEBUG, "%s: called on inode %pU\n", __func__,
get_khandle_from_ino(inode)); get_khandle_from_ino(inode));
if (!new && !bypass) {
if (orangefs_inode->getattr_time > jiffies)
return 0;
}
new_op = op_alloc(ORANGEFS_VFS_OP_GETATTR); new_op = op_alloc(ORANGEFS_VFS_OP_GETATTR);
if (!new_op) if (!new_op)
return -ENOMEM; return -ENOMEM;
new_op->upcall.req.getattr.refn = orangefs_inode->refn; new_op->upcall.req.getattr.refn = orangefs_inode->refn;
new_op->upcall.req.getattr.mask = size ? new_op->upcall.req.getattr.mask = ORANGEFS_ATTR_SYS_ALL_NOHINT;
ORANGEFS_ATTR_SYS_ALL_NOHINT : ORANGEFS_ATTR_SYS_ALL_NOHINT_NOSIZE;
ret = service_operation(new_op, __func__, ret = service_operation(new_op, __func__,
get_interruptible_flag(inode)); get_interruptible_flag(inode));
...@@ -287,7 +291,6 @@ int orangefs_inode_getattr(struct inode *inode, int new, int size) ...@@ -287,7 +291,6 @@ int orangefs_inode_getattr(struct inode *inode, int new, int size)
case S_IFREG: case S_IFREG:
inode->i_flags = orangefs_inode_flags(&new_op-> inode->i_flags = orangefs_inode_flags(&new_op->
downcall.resp.getattr.attributes); downcall.resp.getattr.attributes);
if (size) {
inode_size = (loff_t)new_op-> inode_size = (loff_t)new_op->
downcall.resp.getattr.attributes.size; downcall.resp.getattr.attributes.size;
rounded_up_size = rounded_up_size =
...@@ -300,7 +303,6 @@ int orangefs_inode_getattr(struct inode *inode, int new, int size) ...@@ -300,7 +303,6 @@ int orangefs_inode_getattr(struct inode *inode, int new, int size)
inode->i_blocks = inode->i_blocks =
(unsigned long)(rounded_up_size / 512); (unsigned long)(rounded_up_size / 512);
spin_unlock(&inode->i_lock); spin_unlock(&inode->i_lock);
}
break; break;
case S_IFDIR: case S_IFDIR:
inode->i_size = PAGE_SIZE; inode->i_size = PAGE_SIZE;
...@@ -345,6 +347,7 @@ int orangefs_inode_getattr(struct inode *inode, int new, int size) ...@@ -345,6 +347,7 @@ int orangefs_inode_getattr(struct inode *inode, int new, int size)
inode->i_mode = type | (is_root_handle(inode) ? S_ISVTX : 0) | inode->i_mode = type | (is_root_handle(inode) ? S_ISVTX : 0) |
orangefs_inode_perms(&new_op->downcall.resp.getattr.attributes); orangefs_inode_perms(&new_op->downcall.resp.getattr.attributes);
orangefs_inode->getattr_time = jiffies + HZ;
ret = 0; ret = 0;
out: out:
op_release(new_op); op_release(new_op);
...@@ -418,6 +421,7 @@ int orangefs_inode_setattr(struct inode *inode, struct iattr *iattr) ...@@ -418,6 +421,7 @@ int orangefs_inode_setattr(struct inode *inode, struct iattr *iattr)
ClearMtimeFlag(orangefs_inode); ClearMtimeFlag(orangefs_inode);
ClearCtimeFlag(orangefs_inode); ClearCtimeFlag(orangefs_inode);
ClearModeFlag(orangefs_inode); ClearModeFlag(orangefs_inode);
orangefs_inode->getattr_time = 0;
} }
return ret; return ret;
......
...@@ -207,14 +207,6 @@ typedef __s64 ORANGEFS_offset; ...@@ -207,14 +207,6 @@ typedef __s64 ORANGEFS_offset;
ORANGEFS_ATTR_SYS_DIRENT_COUNT | \ ORANGEFS_ATTR_SYS_DIRENT_COUNT | \
ORANGEFS_ATTR_SYS_BLKSIZE) ORANGEFS_ATTR_SYS_BLKSIZE)
#define ORANGEFS_ATTR_SYS_ALL_NOHINT_NOSIZE \
(ORANGEFS_ATTR_SYS_COMMON_ALL | \
ORANGEFS_ATTR_SYS_LNK_TARGET | \
ORANGEFS_ATTR_SYS_DFILE_COUNT | \
ORANGEFS_ATTR_SYS_MIRROR_COPIES_COUNT | \
ORANGEFS_ATTR_SYS_DIRENT_COUNT | \
ORANGEFS_ATTR_SYS_BLKSIZE)
#define ORANGEFS_XATTR_REPLACE 0x2 #define ORANGEFS_XATTR_REPLACE 0x2
#define ORANGEFS_XATTR_CREATE 0x1 #define ORANGEFS_XATTR_CREATE 0x1
#define ORANGEFS_MAX_SERVER_ADDR_LEN 256 #define ORANGEFS_MAX_SERVER_ADDR_LEN 256
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment