]> git.ipfire.org Git - thirdparty/xfsprogs-dev.git/commitdiff
libxfs: create attr log item opcodes and formats for parent pointers
authorDarrick J. Wong <djwong@kernel.org>
Mon, 29 Jul 2024 23:23:19 +0000 (16:23 -0700)
committerDarrick J. Wong <djwong@kernel.org>
Tue, 30 Jul 2024 00:01:11 +0000 (17:01 -0700)
Update xfs_attr_defer_add to use the pptr-specific opcodes if it's
reading or writing parent pointers.

Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
libxfs/defer_item.c

index 9955e189dfe12e57c547c90f78426175e4fbf1a3..8cdf57eac90062e42d61a35dbb9653ac96f608ef 100644 (file)
@@ -676,21 +676,61 @@ xfs_attr_defer_add(
        enum xfs_attr_defer_op  op)
 {
        struct xfs_attr_intent  *new;
+       unsigned int            log_op = 0;
+       bool                    is_pptr = args->attr_filter & XFS_ATTR_PARENT;
+
+       if (is_pptr) {
+               ASSERT(xfs_has_parent(args->dp->i_mount));
+               ASSERT((args->attr_filter & ~XFS_ATTR_PARENT) != 0);
+               ASSERT(args->op_flags & XFS_DA_OP_LOGGED);
+               ASSERT(args->valuelen == sizeof(struct xfs_parent_rec));
+       }
 
-       new = kmem_cache_zalloc(xfs_attr_intent_cache, GFP_NOFS | __GFP_NOFAIL);
+       new = kmem_cache_zalloc(xfs_attr_intent_cache,
+                       GFP_NOFS | __GFP_NOFAIL);
        new->xattri_da_args = args;
 
+       /* Compute log operation from the higher level op and namespace. */
        switch (op) {
        case XFS_ATTR_DEFER_SET:
-               new->xattri_op_flags = XFS_ATTRI_OP_FLAGS_SET;
-               new->xattri_dela_state = xfs_attr_init_add_state(args);
+               if (is_pptr)
+                       log_op = XFS_ATTRI_OP_FLAGS_PPTR_SET;
+               else
+                       log_op = XFS_ATTRI_OP_FLAGS_SET;
                break;
        case XFS_ATTR_DEFER_REPLACE:
-               new->xattri_op_flags = XFS_ATTRI_OP_FLAGS_REPLACE;
-               new->xattri_dela_state = xfs_attr_init_replace_state(args);
+               if (is_pptr)
+                       log_op = XFS_ATTRI_OP_FLAGS_PPTR_REPLACE;
+               else
+                       log_op = XFS_ATTRI_OP_FLAGS_REPLACE;
                break;
        case XFS_ATTR_DEFER_REMOVE:
-               new->xattri_op_flags = XFS_ATTRI_OP_FLAGS_REMOVE;
+               if (is_pptr)
+                       log_op = XFS_ATTRI_OP_FLAGS_PPTR_REMOVE;
+               else
+                       log_op = XFS_ATTRI_OP_FLAGS_REMOVE;
+               break;
+       default:
+               ASSERT(0);
+               break;
+       }
+       new->xattri_op_flags = log_op;
+
+       /* Set up initial attr operation state. */
+       switch (log_op) {
+       case XFS_ATTRI_OP_FLAGS_PPTR_SET:
+       case XFS_ATTRI_OP_FLAGS_SET:
+               new->xattri_dela_state = xfs_attr_init_add_state(args);
+               break;
+       case XFS_ATTRI_OP_FLAGS_PPTR_REPLACE:
+               ASSERT(args->new_valuelen == args->valuelen);
+               new->xattri_dela_state = xfs_attr_init_replace_state(args);
+               break;
+       case XFS_ATTRI_OP_FLAGS_REPLACE:
+               new->xattri_dela_state = xfs_attr_init_replace_state(args);
+               break;
+       case XFS_ATTRI_OP_FLAGS_PPTR_REMOVE:
+       case XFS_ATTRI_OP_FLAGS_REMOVE:
                new->xattri_dela_state = xfs_attr_init_remove_state(args);
                break;
        }