Beispiel #1
0
ssize_t nfs3_getxattr(struct dentry *dentry, const char *name,
		void *buffer, size_t size)
{
	struct inode *inode = dentry->d_inode;
	struct posix_acl *acl;
	int type, error = 0;

	if (strcmp(name, POSIX_ACL_XATTR_ACCESS) == 0)
		type = ACL_TYPE_ACCESS;
	else if (strcmp(name, POSIX_ACL_XATTR_DEFAULT) == 0)
		type = ACL_TYPE_DEFAULT;
	else
		return -EOPNOTSUPP;

	acl = nfs3_proc_getacl(inode, type);
	if (IS_ERR(acl))
		return PTR_ERR(acl);
	else if (acl) {
		if (type == ACL_TYPE_ACCESS && acl->a_count == 0)
			error = -ENODATA;
		else
			error = posix_acl_to_xattr(acl, buffer, size);
		posix_acl_release(acl);
	} else
		error = -ENODATA;

	return error;
}
Beispiel #2
0
int nfs3_proc_set_default_acl(struct inode *dir, struct inode *inode,
		mode_t mode)
{
	struct posix_acl *dfacl, *acl;
	int error = 0;

	dfacl = nfs3_proc_getacl(dir, ACL_TYPE_DEFAULT);
	if (IS_ERR(dfacl)) {
		error = PTR_ERR(dfacl);
		return (error == -EOPNOTSUPP) ? 0 : error;
	}
	if (!dfacl)
		return 0;
	acl = posix_acl_clone(dfacl, GFP_KERNEL);
	error = -ENOMEM;
	if (!acl)
		goto out_release_dfacl;
	error = posix_acl_create_masq(acl, &mode);
	if (error < 0)
		goto out_release_acl;
	error = nfs3_proc_setacls(inode, acl, S_ISDIR(inode->i_mode) ?
						      dfacl : NULL);
out_release_acl:
	posix_acl_release(acl);
out_release_dfacl:
	posix_acl_release(dfacl);
	return error;
}
Beispiel #3
0
int nfs3_proc_setacl(struct inode *inode, int type, struct posix_acl *acl)
{
	struct posix_acl *alloc = NULL, *dfacl = NULL;
	int status;

	if (S_ISDIR(inode->i_mode)) {
		switch(type) {
			case ACL_TYPE_ACCESS:
				alloc = dfacl = nfs3_proc_getacl(inode,
						ACL_TYPE_DEFAULT);
				if (IS_ERR(alloc))
					goto fail;
				break;

			case ACL_TYPE_DEFAULT:
				dfacl = acl;
				alloc = acl = nfs3_proc_getacl(inode,
						ACL_TYPE_ACCESS);
				if (IS_ERR(alloc))
					goto fail;
				break;

			default:
				return -EINVAL;
		}
	} else if (type != ACL_TYPE_ACCESS)
			return -EINVAL;

	if (acl == NULL) {
		alloc = acl = posix_acl_from_mode(inode->i_mode, GFP_KERNEL);
		if (IS_ERR(alloc))
			goto fail;
	}
	status = nfs3_proc_setacls(inode, acl, dfacl);
	posix_acl_release(alloc);
	return status;

fail:
	return PTR_ERR(alloc);
}
Beispiel #4
0
ssize_t nfs3_listxattr(struct dentry *dentry, char *buffer, size_t size)
{
	struct inode *inode = dentry->d_inode;
	struct posix_acl *acl;
	int pos=0, len=0;

#	define output(s) do {						\
			if (pos + sizeof(s) <= size) {			\
				memcpy(buffer + pos, s, sizeof(s));	\
				pos += sizeof(s);			\
			}						\
			len += sizeof(s);				\
		} while(0)

	acl = nfs3_proc_getacl(inode, ACL_TYPE_ACCESS);
	if (IS_ERR(acl))
		return PTR_ERR(acl);
	if (acl) {
		output("system.posix_acl_access");
		posix_acl_release(acl);
	}

	if (S_ISDIR(inode->i_mode)) {
		acl = nfs3_proc_getacl(inode, ACL_TYPE_DEFAULT);
		if (IS_ERR(acl))
			return PTR_ERR(acl);
		if (acl) {
			output("system.posix_acl_default");
			posix_acl_release(acl);
		}
	}

#	undef output

	if (!buffer || len <= size)
		return len;
	return -ERANGE;
}