#include "btrfs_inode.h"
 #include "transaction.h"
 #include "compression.h"
+#include "xattr.h"
 
 /*
  * Maximum number of references an extent can have in order for us to attempt to
        struct fs_path *p;
        struct posix_acl_xattr_header dummy_acl;
 
+       /* Capabilities are emitted by finish_inode_if_needed */
+       if (!strncmp(name, XATTR_NAME_CAPS, name_len))
+               return 0;
+
        p = fs_path_alloc();
        if (!p)
                return -ENOMEM;
        return 0;
 }
 
+/*
+ * Search for a capability xattr related to sctx->cur_ino. If the capability is
+ * found, call send_set_xattr function to emit it.
+ *
+ * Return 0 if there isn't a capability, or when the capability was emitted
+ * successfully, or < 0 if an error occurred.
+ */
+static int send_capabilities(struct send_ctx *sctx)
+{
+       struct fs_path *fspath = NULL;
+       struct btrfs_path *path;
+       struct btrfs_dir_item *di;
+       struct extent_buffer *leaf;
+       unsigned long data_ptr;
+       char *buf = NULL;
+       int buf_len;
+       int ret = 0;
+
+       path = alloc_path_for_send();
+       if (!path)
+               return -ENOMEM;
+
+       di = btrfs_lookup_xattr(NULL, sctx->send_root, path, sctx->cur_ino,
+                               XATTR_NAME_CAPS, strlen(XATTR_NAME_CAPS), 0);
+       if (!di) {
+               /* There is no xattr for this inode */
+               goto out;
+       } else if (IS_ERR(di)) {
+               ret = PTR_ERR(di);
+               goto out;
+       }
+
+       leaf = path->nodes[0];
+       buf_len = btrfs_dir_data_len(leaf, di);
+
+       fspath = fs_path_alloc();
+       buf = kmalloc(buf_len, GFP_KERNEL);
+       if (!fspath || !buf) {
+               ret = -ENOMEM;
+               goto out;
+       }
+
+       ret = get_cur_path(sctx, sctx->cur_ino, sctx->cur_inode_gen, fspath);
+       if (ret < 0)
+               goto out;
+
+       data_ptr = (unsigned long)(di + 1) + btrfs_dir_name_len(leaf, di);
+       read_extent_buffer(leaf, buf, data_ptr, buf_len);
+
+       ret = send_set_xattr(sctx, fspath, XATTR_NAME_CAPS,
+                       strlen(XATTR_NAME_CAPS), buf, buf_len);
+out:
+       kfree(buf);
+       fs_path_free(fspath);
+       btrfs_free_path(path);
+       return ret;
+}
+
 static int clone_range(struct send_ctx *sctx,
                       struct clone_root *clone_root,
                       const u64 disk_byte,
                        goto out;
        }
 
+       ret = send_capabilities(sctx);
+       if (ret < 0)
+               goto out;
+
        /*
         * If other directory inodes depended on our current directory
         * inode's move/rename, now do their move/rename operations.