int xfs_attrmulti_attr_get( struct inode *inode, unsigned char *name, unsigned char __user *ubuf, __uint32_t *len, __uint32_t flags) { unsigned char *kbuf; int error = -EFAULT; if (*len > XATTR_SIZE_MAX) return -EINVAL; kbuf = kmem_zalloc_large(*len, KM_SLEEP); if (!kbuf) return -ENOMEM; error = xfs_attr_get(XFS_I(inode), name, kbuf, (int *)len, flags); if (error) goto out_kfree; if (copy_to_user(ubuf, kbuf, *len)) error = -EFAULT; out_kfree: kmem_free(kbuf); return error; }
int xfs_attrmulti_attr_get( struct inode *inode, char *name, char __user *ubuf, __uint32_t *len, __uint32_t flags) { char *kbuf; int error = EFAULT; if (*len > XATTR_SIZE_MAX) return EINVAL; kbuf = kmalloc(*len, GFP_KERNEL); if (!kbuf) return ENOMEM; error = xfs_attr_get(XFS_I(inode), name, kbuf, (int *)len, flags); if (error) goto out_kfree; if (copy_to_user(ubuf, kbuf, *len)) error = EFAULT; out_kfree: kfree(kbuf); return error; }
struct posix_acl * xfs_get_acl(struct inode *inode, int type) { struct xfs_inode *ip = XFS_I(inode); struct posix_acl *acl; struct xfs_acl *xfs_acl; int len = sizeof(struct xfs_acl); unsigned char *ea_name; int error; acl = get_cached_acl(inode, type); if (acl != ACL_NOT_CACHED) return acl; switch (type) { case ACL_TYPE_ACCESS: ea_name = SGI_ACL_FILE; break; case ACL_TYPE_DEFAULT: ea_name = SGI_ACL_DEFAULT; break; default: BUG(); } /* * If we have a cached ACLs value just return it, not need to * go out to the disk. */ xfs_acl = kzalloc(sizeof(struct xfs_acl), GFP_KERNEL); if (!xfs_acl) return ERR_PTR(-ENOMEM); error = -xfs_attr_get(ip, ea_name, (unsigned char *)xfs_acl, &len, ATTR_ROOT); if (error) { /* * If the attribute doesn't exist make sure we have a negative * cache entry, for any other error assume it is transient and * leave the cache entry as ACL_NOT_CACHED. */ if (error == -ENOATTR) { acl = NULL; goto out_update_cache; } goto out; } acl = xfs_acl_from_disk(xfs_acl); if (IS_ERR(acl)) goto out; out_update_cache: set_cached_acl(inode, type, acl); out: kfree(xfs_acl); return acl; }
static int xfs_acl_exists(struct inode *inode, unsigned char *name) { int len = XFS_ACL_MAX_SIZE(XFS_M(inode->i_sb)); return (xfs_attr_get(XFS_I(inode), name, NULL, &len, ATTR_ROOT|ATTR_KERNOVAL) == 0); }
static int xfs_acl_exists(struct inode *inode, char *name) { int len = sizeof(struct xfs_acl); return (xfs_attr_get(XFS_I(inode), name, NULL, &len, ATTR_ROOT|ATTR_KERNOVAL) == 0); }
static int xfs_xattr_get(const struct xattr_handler *handler, struct dentry *unused, struct inode *inode, const char *name, void *value, size_t size) { int xflags = handler->flags; struct xfs_inode *ip = XFS_I(inode); int error, asize = size; /* Convert Linux syscall to XFS internal ATTR flags */ if (!size) { xflags |= ATTR_KERNOVAL; value = NULL; } error = xfs_attr_get(ip, (unsigned char *)name, value, &asize, xflags); if (error) return error; return asize; }
/* * Get the ACL from the EA and do endian conversion. */ STATIC void xfs_acl_get_attr( bhv_vnode_t *vp, xfs_acl_t *aclp, int kind, int flags, int *error) { int len = sizeof(xfs_acl_t); ASSERT((flags & ATTR_KERNOVAL) ? (aclp == NULL) : 1); flags |= ATTR_ROOT; *error = xfs_attr_get(xfs_vtoi(vp), kind == _ACL_TYPE_ACCESS ? SGI_ACL_FILE : SGI_ACL_DEFAULT, (char *)aclp, &len, flags, sys_cred); if (*error || (flags & ATTR_KERNOVAL)) return; xfs_acl_get_endian(aclp); }
static int xfs_xattr_get(struct dentry *dentry, const char *name, void *value, size_t size, int xflags) { struct xfs_inode *ip = XFS_I(dentry->d_inode); int error, asize = size; if (strcmp(name, "") == 0) return -EINVAL; /* Convert Linux syscall to XFS internal ATTR flags */ if (!size) { xflags |= ATTR_KERNOVAL; value = NULL; } error = -xfs_attr_get(ip, (unsigned char *)name, value, &asize, xflags); if (error) return error; return asize; }