8 #include <linux/xattr.h>
9 #include <linux/slab.h>
11 #define XATTR_CEPH_PREFIX "ceph."
12 #define XATTR_CEPH_PREFIX_LEN (sizeof (XATTR_CEPH_PREFIX) - 1)
14 static bool ceph_is_valid_xattr(
const char *
name)
86 #define CEPH_XATTR_NAME(_type, _name) XATTR_CEPH_PREFIX #_type "." #_name
88 #define XATTR_NAME_CEPH(_type, _name) \
90 .name = CEPH_XATTR_NAME(_type, _name), \
91 .name_size = sizeof (CEPH_XATTR_NAME(_type, _name)), \
92 .getxattr_cb = ceph_vxattrcb_ ## _type ## _ ## _name, \
107 static size_t ceph_dir_vxattrs_name_size;
111 static size_t ceph_vxattrcb_file_layout(
struct ceph_inode_info *ci,
char *val,
117 "chunk_bytes=%lld\nstripe_count=%lld\nobject_size=%lld\n",
135 static size_t ceph_file_vxattrs_name_size;
140 return ceph_dir_vxattrs;
142 return ceph_file_vxattrs;
146 static size_t ceph_vxattrs_name_size(
struct ceph_vxattr *vxattrs)
148 if (vxattrs == ceph_dir_vxattrs)
149 return ceph_dir_vxattrs_name_size;
150 if (vxattrs == ceph_file_vxattrs)
151 return ceph_file_vxattrs_name_size;
166 for (vxattr = vxattrs; vxattr->
name; vxattr++)
176 ceph_dir_vxattrs_name_size = vxattrs_name_size(ceph_dir_vxattrs);
177 ceph_file_vxattrs_name_size = vxattrs_name_size(ceph_file_vxattrs);
182 ceph_dir_vxattrs_name_size = 0;
183 ceph_file_vxattrs_name_size = 0;
186 static struct ceph_vxattr *ceph_match_vxattr(
struct inode *inode,
189 struct ceph_vxattr *vxattr = ceph_inode_vxattrs(inode);
192 while (vxattr->
name) {
204 const char *val,
int val_len,
206 int should_free_name,
int should_free_val,
227 else if (name_len < xattr->name_len)
250 if (should_free_name) {
269 rb_link_node(&xattr->
node, parent, p);
271 dout(
"__set_xattr_val p=%p\n", p);
274 dout(
"__set_xattr_val added %llx.%llx xattr %p %s=%.*s\n",
286 int name_len =
strlen(name);
294 if (c == 0 && name_len > xattr->
name_len)
301 dout(
"__get_xattr %s: found %.*s\n", name,
307 dout(
"__get_xattr %s: not found\n", name);
353 xattr = __get_xattr(ci, name);
354 err = __remove_xattr(ci, xattr);
365 dout(
"__copy_xattr_names count=%d\n", ci->
i_xattrs.count);
372 dout(
"dest=%s %p (%s) (%d/%d)\n", dest, xattr, xattr->
name,
389 dout(
"__ceph_destroy_xattrs p=%p\n", p);
395 dout(
"__ceph_destroy_xattrs next p=%p (%.*s)\n", p,
409 static int __build_xattrs(
struct inode *inode)
424 dout(
"__build_xattrs() len=%d\n",
435 p = ci->
i_xattrs.blob->vec.iov_base;
436 end = p + ci->
i_xattrs.blob->vec.iov_len;
438 xattr_version = ci->
i_xattrs.version;
441 xattrs = kcalloc(numattr,
sizeof(
struct ceph_xattr *),
446 memset(xattrs, 0, numattr*
sizeof(
struct ceph_xattr *));
447 for (i = 0; i < numattr; i++) {
455 if (ci->
i_xattrs.version != xattr_version) {
457 for (i = 0; i < numattr; i++)
473 err = __set_xattr(ci, name, namelen, val, len,
474 0, 0, 0, &xattrs[numattr]);
489 for (i = 0; i < numattr; i++)
497 static int __get_required_blob_size(
struct ceph_inode_info *ci,
int name_size,
504 int size = 4 + ci->
i_xattrs.count*(4 + 4) +
507 dout(
"__get_required_blob_size c=%d names.size=%d vals.size=%d\n",
512 size += 4 + 4 + name_size + val_size;
529 int need = __get_required_blob_size(ci, 0, 0);
534 dest = ci->
i_xattrs.prealloc_blob->vec.iov_base;
536 ceph_encode_32(&dest, ci->
i_xattrs.count);
540 ceph_encode_32(&dest, xattr->
name_len);
543 ceph_encode_32(&dest, xattr->
val_len);
551 ci->
i_xattrs.prealloc_blob->vec.iov_len =
552 dest - ci->
i_xattrs.prealloc_blob->vec.iov_base;
566 struct inode *inode = dentry->
d_inode;
572 if (!ceph_is_valid_xattr(name))
576 vxattr = ceph_match_vxattr(inode, name);
579 dout(
"getxattr %p ver=%lld index_ver=%lld\n", inode,
600 err = __build_xattrs(inode);
606 xattr = __get_xattr(ci, name);
614 if (size && size < xattr->val_len)
630 struct inode *inode = dentry->
d_inode;
632 struct ceph_vxattr *vxattrs = ceph_inode_vxattrs(inode);
640 dout(
"listxattr %p ver=%lld index_ver=%lld\n", inode,
655 err = __build_xattrs(inode);
664 vir_namelen = ceph_vxattrs_name_size(vxattrs);
669 if (size && namelen > size)
676 names = __copy_xattr_names(ci, names);
680 for (i = 0; vxattrs[
i].
name; i++) {
681 len =
sprintf(names,
"%s", vxattrs[i].name);
690 static int ceph_sync_setxattr(
struct dentry *
dentry,
const char *name,
694 struct inode *inode = dentry->
d_inode;
696 struct inode *parent_inode;
705 nr_pages = calc_pages_for(0, size);
711 for (i = 0; i < nr_pages; i++) {
717 kaddr =
kmap(pages[i]);
719 min(PAGE_CACHE_SIZE, size-i*PAGE_CACHE_SIZE));
723 dout(
"setxattr value=%.*s\n", (
int)size, value);
743 dout(
"xattr.ver (before): %lld\n", ci->
i_xattrs.version);
747 ceph_mdsc_put_request(req);
748 dout(
"xattr.ver (after): %lld\n", ci->
i_xattrs.version);
752 for (i = 0; i < nr_pages; i++)
760 const void *value,
size_t size,
int flags)
762 struct inode *inode = dentry->
d_inode;
768 int name_len =
strlen(name);
770 char *newname =
NULL;
773 int required_blob_size;
778 if (!ceph_is_valid_xattr(name))
781 vxattr = ceph_match_vxattr(inode, name);
807 __build_xattrs(inode);
809 required_blob_size = __get_required_blob_size(ci, name_len, val_len);
812 required_blob_size > ci->
i_xattrs.prealloc_blob->alloc_len) {
816 dout(
" preaallocating new blob size=%d\n", required_blob_size);
822 ceph_buffer_put(ci->
i_xattrs.prealloc_blob);
827 err = __set_xattr(ci, newname, name_len, newval,
828 val_len, 1, 1, 1, &xattr);
841 err = ceph_sync_setxattr(dentry, name, value, size, flags);
849 static int ceph_send_removexattr(
struct dentry *dentry,
const char *name)
853 struct inode *inode = dentry->
d_inode;
854 struct inode *parent_inode;
871 ceph_mdsc_put_request(req);
877 struct inode *inode = dentry->
d_inode;
882 int required_blob_size;
888 if (!ceph_is_valid_xattr(name))
891 vxattr = ceph_match_vxattr(inode, name);
903 __build_xattrs(inode);
905 required_blob_size = __get_required_blob_size(ci, 0, 0);
908 required_blob_size > ci->
i_xattrs.prealloc_blob->alloc_len) {
912 dout(
" preaallocating new blob size=%d\n", required_blob_size);
918 ceph_buffer_put(ci->
i_xattrs.prealloc_blob);
923 err = __remove_xattr_by_name(ceph_inode(inode), name);
934 err = ceph_send_removexattr(dentry, name);