Lines Matching +full:skip +full:- +full:recall

1 // SPDX-License-Identifier: GPL-2.0
3 * Copyright (c) 2000-2005 Silicon Graphics, Inc.
72 if (ip->i_af.if_format == XFS_DINODE_FMT_EXTENTS && in xfs_inode_hasattr()
73 ip->i_af.if_nextents == 0) in xfs_inode_hasattr()
86 struct xfs_ifork *ifp = &ip->i_af; in xfs_attr_is_leaf()
92 if (ifp->if_nextents != 1 || ifp->if_format != XFS_DINODE_FMT_EXTENTS) in xfs_attr_is_leaf()
125 trace_xfs_attr_fillstate(state->args);
128 * Roll down the "path" in the state structure, storing the on-disk
131 path = &state->path;
132 ASSERT((path->active >= 0) && (path->active < XFS_DA_NODE_MAXDEPTH));
133 for (blk = path->blk, level = 0; level < path->active; blk++, level++) {
134 if (blk->bp) {
135 blk->disk_blkno = xfs_buf_daddr(blk->bp);
136 blk->bp = NULL;
138 blk->disk_blkno = 0;
143 * Roll down the "altpath" in the state structure, storing the on-disk
146 path = &state->altpath;
147 ASSERT((path->active >= 0) && (path->active < XFS_DA_NODE_MAXDEPTH));
148 for (blk = path->blk, level = 0; level < path->active; blk++, level++) {
149 if (blk->bp) {
150 blk->disk_blkno = xfs_buf_daddr(blk->bp);
151 blk->bp = NULL;
153 blk->disk_blkno = 0;
173 trace_xfs_attr_refillstate(state->args);
176 * Roll down the "path" in the state structure, storing the on-disk
179 path = &state->path;
180 ASSERT((path->active >= 0) && (path->active < XFS_DA_NODE_MAXDEPTH));
181 for (blk = path->blk, level = 0; level < path->active; blk++, level++) {
182 if (blk->disk_blkno) {
183 error = xfs_da3_node_read_mapped(state->args->trans,
184 state->args->dp, blk->disk_blkno,
185 &blk->bp, XFS_ATTR_FORK);
189 blk->bp = NULL;
194 * Roll down the "altpath" in the state structure, storing the on-disk
197 path = &state->altpath;
198 ASSERT((path->active >= 0) && (path->active < XFS_DA_NODE_MAXDEPTH));
199 for (blk = path->blk, level = 0; level < path->active; blk++, level++) {
200 if (blk->disk_blkno) {
201 error = xfs_da3_node_read_mapped(state->args->trans,
202 state->args->dp, blk->disk_blkno,
203 &blk->bp, XFS_ATTR_FORK);
207 blk->bp = NULL;
231 xfs_assert_ilocked(args->dp, XFS_ILOCK_SHARED | XFS_ILOCK_EXCL); in xfs_attr_get_ilocked()
233 if (!xfs_inode_hasattr(args->dp)) in xfs_attr_get_ilocked()
234 return -ENOATTR; in xfs_attr_get_ilocked()
240 error = xfs_iread_extents(args->trans, args->dp, XFS_ATTR_FORK); in xfs_attr_get_ilocked()
244 if (args->dp->i_af.if_format == XFS_DINODE_FMT_LOCAL) in xfs_attr_get_ilocked()
246 if (xfs_attr_is_leaf(args->dp)) in xfs_attr_get_ilocked()
254 * If args->valuelen is zero, then the caller does not want the value, just an
258 * If args->value is NULL but args->valuelen is non-zero, allocate the buffer
260 * caller always has to free args->value if it is set, no matter if this
264 * args->valuelen, return -ERANGE with the size of the attribute that was found
265 * in args->valuelen.
274 XFS_STATS_INC(args->dp->i_mount, xs_attr_get); in xfs_attr_get()
276 if (xfs_is_shutdown(args->dp->i_mount)) in xfs_attr_get()
277 return -EIO; in xfs_attr_get()
279 if (!args->owner) in xfs_attr_get()
280 args->owner = args->dp->i_ino; in xfs_attr_get()
281 args->geo = args->dp->i_mount->m_attr_geo; in xfs_attr_get()
282 args->whichfork = XFS_ATTR_FORK; in xfs_attr_get()
286 args->op_flags = XFS_DA_OP_OKNOENT; in xfs_attr_get()
288 lock_mode = xfs_ilock_attr_map_shared(args->dp); in xfs_attr_get()
290 xfs_iunlock(args->dp, lock_mode); in xfs_attr_get()
303 struct xfs_mount *mp = args->dp->i_mount; in xfs_attr_calc_size()
314 if (size > (args->geo->blksize / 2)) { in xfs_attr_calc_size()
323 uint dblocks = xfs_attr3_rmt_blocks(mp, args->valuelen); in xfs_attr_calc_size()
336 struct xfs_mount *mp = args->dp->i_mount; in xfs_attr_set_resv()
338 .tr_logres = M_RES(mp)->tr_attrsetm.tr_logres + in xfs_attr_set_resv()
339 M_RES(mp)->tr_attrsetrt.tr_logres * args->total, in xfs_attr_set_resv()
349 * xfs_attr_shortform_addname() will convert to leaf format and return -ENOSPC.
363 if (dp->i_af.if_format == XFS_DINODE_FMT_EXTENTS) in xfs_attr_try_sf_addname()
367 if (error == -ENOSPC) in xfs_attr_try_sf_addname()
375 xfs_trans_ichgtime(args->trans, dp, XFS_ICHGTIME_CHG); in xfs_attr_try_sf_addname()
377 if (xfs_has_wsync(dp->i_mount)) in xfs_attr_try_sf_addname()
378 xfs_trans_set_sync(args->trans); in xfs_attr_try_sf_addname()
387 struct xfs_da_args *args = attr->xattri_da_args; in xfs_attr_sf_addname()
388 struct xfs_inode *dp = args->dp; in xfs_attr_sf_addname()
392 if (error != -ENOSPC) { in xfs_attr_sf_addname()
393 ASSERT(!error || error == -EEXIST); in xfs_attr_sf_addname()
394 attr->xattri_dela_state = XFS_DAS_DONE; in xfs_attr_sf_addname()
400 * another possible req'mt for a double-split btree op. in xfs_attr_sf_addname()
406 attr->xattri_dela_state = XFS_DAS_LEAF_ADD; in xfs_attr_sf_addname()
408 trace_xfs_attr_sf_addname_return(attr->xattri_dela_state, args->dp); in xfs_attr_sf_addname()
444 args->blkno2 = args->blkno; in xfs_attr_save_rmt_blk()
445 args->index2 = args->index; in xfs_attr_save_rmt_blk()
446 args->rmtblkno2 = args->rmtblkno; in xfs_attr_save_rmt_blk()
447 args->rmtblkcnt2 = args->rmtblkcnt; in xfs_attr_save_rmt_blk()
448 args->rmtvaluelen2 = args->rmtvaluelen; in xfs_attr_save_rmt_blk()
449 args->rmtblkno = 0; in xfs_attr_save_rmt_blk()
450 args->rmtblkcnt = 0; in xfs_attr_save_rmt_blk()
451 args->rmtvaluelen = 0; in xfs_attr_save_rmt_blk()
459 args->blkno = args->blkno2; in xfs_attr_restore_rmt_blk()
460 args->index = args->index2; in xfs_attr_restore_rmt_blk()
461 args->rmtblkno = args->rmtblkno2; in xfs_attr_restore_rmt_blk()
462 args->rmtblkcnt = args->rmtblkcnt2; in xfs_attr_restore_rmt_blk()
463 args->rmtvaluelen = args->rmtvaluelen2; in xfs_attr_restore_rmt_blk()
475 ASSERT(args->new_namelen > 0); in xfs_attr_update_pptr_replace_args()
476 args->name = args->new_name; in xfs_attr_update_pptr_replace_args()
477 args->namelen = args->new_namelen; in xfs_attr_update_pptr_replace_args()
478 args->value = args->new_value; in xfs_attr_update_pptr_replace_args()
479 args->valuelen = args->new_valuelen; in xfs_attr_update_pptr_replace_args()
484 * Handle the state change on completion of a multi-state attr operation.
499 struct xfs_da_args *args = attr->xattri_da_args; in xfs_attr_complete_op()
501 if (!(args->op_flags & XFS_DA_OP_REPLACE)) in xfs_attr_complete_op()
506 args->op_flags &= ~XFS_DA_OP_REPLACE; in xfs_attr_complete_op()
507 args->attr_filter &= ~XFS_ATTR_INCOMPLETE; in xfs_attr_complete_op()
518 struct xfs_da_args *args = attr->xattri_da_args; in xfs_attr_leaf_addname()
522 ASSERT(xfs_attr_is_leaf(args->dp)); in xfs_attr_leaf_addname()
524 error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, 0, &bp); in xfs_attr_leaf_addname()
533 case -ENOATTR: in xfs_attr_leaf_addname()
534 if (args->op_flags & XFS_DA_OP_REPLACE) in xfs_attr_leaf_addname()
537 case -EEXIST: in xfs_attr_leaf_addname()
538 if (!(args->op_flags & XFS_DA_OP_REPLACE)) in xfs_attr_leaf_addname()
565 attr->xattri_dela_state = XFS_DAS_NODE_ADD; in xfs_attr_leaf_addname()
566 } else if (args->rmtblkno) { in xfs_attr_leaf_addname()
567 attr->xattri_dela_state = XFS_DAS_LEAF_SET_RMT; in xfs_attr_leaf_addname()
569 attr->xattri_dela_state = in xfs_attr_leaf_addname()
573 trace_xfs_attr_leaf_addname_return(attr->xattri_dela_state, args->dp); in xfs_attr_leaf_addname()
577 xfs_trans_brelse(args->trans, bp); in xfs_attr_leaf_addname()
584 * Note that we might still have a leaf here - xfs_attr_is_leaf() cannot tell
592 struct xfs_da_args *args = attr->xattri_da_args; in xfs_attr_node_addname()
613 if (args->rmtblkno) in xfs_attr_node_addname()
614 attr->xattri_dela_state = XFS_DAS_NODE_SET_RMT; in xfs_attr_node_addname()
616 attr->xattri_dela_state = xfs_attr_complete_op(attr, in xfs_attr_node_addname()
619 trace_xfs_attr_node_addname_return(attr->xattri_dela_state, args->dp); in xfs_attr_node_addname()
627 struct xfs_da_args *args = attr->xattri_da_args; in xfs_attr_rmtval_alloc()
631 * If there was an out-of-line value, allocate the blocks we in xfs_attr_rmtval_alloc()
636 if (attr->xattri_blkcnt > 0) { in xfs_attr_rmtval_alloc()
641 if (attr->xattri_blkcnt > 0) in xfs_attr_rmtval_alloc()
649 attr->xattri_dela_state = xfs_attr_complete_op(attr, in xfs_attr_rmtval_alloc()
650 ++attr->xattri_dela_state); in xfs_attr_rmtval_alloc()
656 if (attr->xattri_dela_state == XFS_DAS_DONE) in xfs_attr_rmtval_alloc()
659 trace_xfs_attr_rmtval_alloc(attr->xattri_dela_state, args->dp); in xfs_attr_rmtval_alloc()
694 struct xfs_da_args *args = attr->xattri_da_args; in xfs_attr_item_init_da_state()
696 if (!attr->xattri_da_state) in xfs_attr_item_init_da_state()
697 attr->xattri_da_state = xfs_da_state_alloc(args); in xfs_attr_item_init_da_state()
699 xfs_da_state_reset(attr->xattri_da_state, args); in xfs_attr_item_init_da_state()
711 struct xfs_da_args *args = attr->xattri_da_args; in xfs_attr_node_removename_setup()
716 error = xfs_attr_node_lookup(args, attr->xattri_da_state); in xfs_attr_node_removename_setup()
717 if (error != -EEXIST) in xfs_attr_node_removename_setup()
721 state = attr->xattri_da_state; in xfs_attr_node_removename_setup()
722 ASSERT(state->path.blk[state->path.active - 1].bp != NULL); in xfs_attr_node_removename_setup()
723 ASSERT(state->path.blk[state->path.active - 1].magic == in xfs_attr_node_removename_setup()
729 if (args->rmtblkno > 0) in xfs_attr_node_removename_setup()
733 xfs_da_state_free(attr->xattri_da_state); in xfs_attr_node_removename_setup()
734 attr->xattri_da_state = NULL; in xfs_attr_node_removename_setup()
742 * original lookup and insert placing the old attr in args->blkno/args->index
743 * and the new attr in args->blkno2/args->index2.
749 struct xfs_da_args *args = attr->xattri_da_args; in xfs_attr_leaf_remove_attr()
750 struct xfs_inode *dp = args->dp; in xfs_attr_leaf_remove_attr()
755 error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, in xfs_attr_leaf_remove_attr()
756 args->blkno, &bp); in xfs_attr_leaf_remove_attr()
779 struct xfs_inode *dp = args->dp; in xfs_attr_leaf_shrink()
787 error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, 0, &bp); in xfs_attr_leaf_shrink()
796 xfs_trans_brelse(args->trans, bp); in xfs_attr_leaf_shrink()
807 * need to handle this, and recall the function until either an error or
814 struct xfs_da_args *args = attr->xattri_da_args; in xfs_attr_set_iter()
819 switch (attr->xattri_dela_state) { in xfs_attr_set_iter()
822 return -EFSCORRUPTED; in xfs_attr_set_iter()
832 attr->xattri_dela_state = xfs_attr_complete_op(attr, in xfs_attr_set_iter()
837 attr->xattri_dela_state = xfs_attr_complete_op(attr, in xfs_attr_set_iter()
842 if (error == -ENOATTR && in xfs_attr_set_iter()
843 (args->op_flags & XFS_DA_OP_RECOVERY)) { in xfs_attr_set_iter()
844 attr->xattri_dela_state = xfs_attr_complete_op(attr, in xfs_attr_set_iter()
851 attr->xattri_dela_state = XFS_DAS_NODE_REMOVE_RMT; in xfs_attr_set_iter()
852 if (args->rmtblkno == 0) in xfs_attr_set_iter()
853 attr->xattri_dela_state++; in xfs_attr_set_iter()
861 attr->xattri_dela_state++; in xfs_attr_set_iter()
869 if (attr->xattri_dela_state == XFS_DAS_DONE) in xfs_attr_set_iter()
887 attr->xattri_dela_state++; in xfs_attr_set_iter()
896 * If we don't have a remote attr, we skip the remote block in xfs_attr_set_iter()
900 if (args->rmtblkno) { in xfs_attr_set_iter()
905 attr->xattri_dela_state++; in xfs_attr_set_iter()
908 attr->xattri_dela_state++; in xfs_attr_set_iter()
914 if (error == -EAGAIN) { in xfs_attr_set_iter()
929 attr->xattri_dela_state++; in xfs_attr_set_iter()
934 attr->xattri_dela_state = xfs_attr_complete_op(attr, in xfs_attr_set_iter()
942 attr->xattri_dela_state = xfs_attr_complete_op(attr, in xfs_attr_set_iter()
950 trace_xfs_attr_set_iter_return(attr->xattri_dela_state, args->dp); in xfs_attr_set_iter()
962 struct xfs_inode *dp = args->dp; in xfs_attr_lookup()
968 return -ENOATTR; in xfs_attr_lookup()
970 if (dp->i_af.if_format == XFS_DINODE_FMT_LOCAL) { in xfs_attr_lookup()
972 return -EEXIST; in xfs_attr_lookup()
973 return -ENOATTR; in xfs_attr_lookup()
977 error = xfs_iread_extents(args->trans, args->dp, XFS_ATTR_FORK); in xfs_attr_lookup()
985 xfs_trans_brelse(args->trans, bp); in xfs_attr_lookup()
1002 struct xfs_mount *mp = ip->i_mount; in xfs_attr_add_fork()
1012 error = xfs_trans_alloc_inode(ip, &M_RES(mp)->tr_addafork, blks, 0, in xfs_attr_add_fork()
1040 * Returns -EEXIST for XFS_ATTRUPDATE_CREATE if the name already exists.
1041 * Returns -ENOATTR for XFS_ATTRUPDATE_REMOVE if the name does not exist.
1050 struct xfs_inode *dp = args->dp; in xfs_attr_set()
1051 struct xfs_mount *mp = dp->i_mount; in xfs_attr_set()
1057 ASSERT(!args->trans); in xfs_attr_set()
1064 args->total = xfs_attr_calc_size(args, &local); in xfs_attr_set()
1072 xfs_attr_sf_entsize_byname(args->namelen, in xfs_attr_set()
1073 args->valuelen); in xfs_attr_set()
1081 rmt_blks = xfs_attr3_rmt_blocks(mp, args->valuelen); in xfs_attr_set()
1084 total = args->total; in xfs_attr_set()
1089 tres = M_RES(mp)->tr_attrrm; in xfs_attr_set()
1098 error = xfs_trans_alloc_inode(dp, &tres, total, 0, rsvd, &args->trans); in xfs_attr_set()
1103 error = xfs_iext_count_extend(args->trans, dp, XFS_ATTR_FORK, in xfs_attr_set()
1111 case -EEXIST: in xfs_attr_set()
1123 case -ENOATTR: in xfs_attr_set()
1142 xfs_trans_set_sync(args->trans); in xfs_attr_set()
1144 xfs_trans_ichgtime(args->trans, dp, XFS_ICHGTIME_CHG); in xfs_attr_set()
1149 xfs_trans_log_inode(args->trans, dp, XFS_ILOG_CORE); in xfs_attr_set()
1150 error = xfs_trans_commit(args->trans); in xfs_attr_set()
1153 args->trans = NULL; in xfs_attr_set()
1157 if (args->trans) in xfs_attr_set()
1158 xfs_trans_cancel(args->trans); in xfs_attr_set()
1168 struct xfs_attr_sf_hdr *sf = dp->i_af.if_data; in xfs_attr_sf_totsize()
1170 return be16_to_cpu(sf->totsize); in xfs_attr_sf_totsize()
1188 ASSERT(args->op_flags & XFS_DA_OP_REPLACE); in xfs_attr_shortform_addname()
1200 args->op_flags &= ~XFS_DA_OP_REPLACE; in xfs_attr_shortform_addname()
1202 ASSERT(!(args->op_flags & XFS_DA_OP_REPLACE)); in xfs_attr_shortform_addname()
1205 if (args->namelen >= XFS_ATTR_SF_ENTSIZE_MAX || in xfs_attr_shortform_addname()
1206 args->valuelen >= XFS_ATTR_SF_ENTSIZE_MAX) in xfs_attr_shortform_addname()
1207 return -ENOSPC; in xfs_attr_shortform_addname()
1209 newsize = xfs_attr_sf_totsize(args->dp); in xfs_attr_shortform_addname()
1210 newsize += xfs_attr_sf_entsize_byname(args->namelen, args->valuelen); in xfs_attr_shortform_addname()
1212 forkoff = xfs_attr_shortform_bytesfit(args->dp, newsize); in xfs_attr_shortform_addname()
1214 return -ENOSPC; in xfs_attr_shortform_addname()
1235 error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, 0, bp); in xfs_attr_leaf_hasname()
1240 if (error != -ENOATTR && error != -EEXIST) in xfs_attr_leaf_hasname()
1241 xfs_trans_brelse(args->trans, *bp); in xfs_attr_leaf_hasname()
1265 dp = args->dp; in xfs_attr_leaf_removename()
1268 if (error == -ENOATTR) { in xfs_attr_leaf_removename()
1269 xfs_trans_brelse(args->trans, bp); in xfs_attr_leaf_removename()
1270 if (args->op_flags & XFS_DA_OP_RECOVERY) in xfs_attr_leaf_removename()
1273 } else if (error != -EEXIST) in xfs_attr_leaf_removename()
1307 if (error == -ENOATTR) { in xfs_attr_leaf_get()
1308 xfs_trans_brelse(args->trans, bp); in xfs_attr_leaf_get()
1310 } else if (error != -EEXIST) in xfs_attr_leaf_get()
1315 xfs_trans_brelse(args->trans, bp); in xfs_attr_leaf_get()
1338 * External routines when attribute list size > geo->blksize
1345 struct xfs_da_args *args = attr->xattri_da_args; in xfs_attr_node_addname_find_attr()
1353 error = xfs_attr_node_lookup(args, attr->xattri_da_state); in xfs_attr_node_addname_find_attr()
1355 case -ENOATTR: in xfs_attr_node_addname_find_attr()
1356 if (args->op_flags & XFS_DA_OP_REPLACE) in xfs_attr_node_addname_find_attr()
1359 case -EEXIST: in xfs_attr_node_addname_find_attr()
1360 if (!(args->op_flags & XFS_DA_OP_REPLACE)) in xfs_attr_node_addname_find_attr()
1380 if (attr->xattri_da_state) { in xfs_attr_node_addname_find_attr()
1381 xfs_da_state_free(attr->xattri_da_state); in xfs_attr_node_addname_find_attr()
1382 attr->xattri_da_state = NULL; in xfs_attr_node_addname_find_attr()
1388 * Add a name to a Btree-format attribute list.
1401 struct xfs_da_state *state = attr->xattri_da_state; in xfs_attr_node_try_addname()
1405 trace_xfs_attr_node_addname(state->args); in xfs_attr_node_try_addname()
1407 blk = &state->path.blk[state->path.active-1]; in xfs_attr_node_try_addname()
1408 ASSERT(blk->magic == XFS_ATTR_LEAF_MAGIC); in xfs_attr_node_try_addname()
1410 if (!xfs_attr3_leaf_add(blk->bp, state->args)) { in xfs_attr_node_try_addname()
1411 if (state->path.active == 1) { in xfs_attr_node_try_addname()
1414 * out-of-line values so it looked like it *might* in xfs_attr_node_try_addname()
1415 * have been a b-tree. Let the caller deal with this. in xfs_attr_node_try_addname()
1434 xfs_da3_fixhashpath(state, &state->path); in xfs_attr_node_try_addname()
1439 attr->xattri_da_state = NULL; in xfs_attr_node_try_addname()
1454 blk = &state->path.blk[state->path.active-1]; in xfs_attr_node_removename()
1455 ASSERT(blk->magic == XFS_ATTR_LEAF_MAGIC); in xfs_attr_node_removename()
1456 retval = xfs_attr3_leaf_remove(blk->bp, args); in xfs_attr_node_removename()
1457 xfs_da3_fixhashpath(state, &state->path); in xfs_attr_node_removename()
1466 struct xfs_da_args *args = attr->xattri_da_args; in xfs_attr_node_remove_attr()
1473 * we need to set the filter appropriately to re-find the "old" in xfs_attr_node_remove_attr()
1476 args->attr_filter |= XFS_ATTR_INCOMPLETE; in xfs_attr_node_remove_attr()
1486 if (retval && (state->path.active > 1)) { in xfs_attr_node_remove_attr()
1504 * block, ie: both true Btree attr lists and for single-leaf-blocks with
1525 if (error != -EEXIST) in xfs_attr_node_get()
1531 blk = &state->path.blk[state->path.active - 1]; in xfs_attr_node_get()
1532 error = xfs_attr3_leaf_getvalue(blk->bp, args); in xfs_attr_node_get()
1538 for (i = 0; i < state->path.active; i++) { in xfs_attr_node_get()
1539 xfs_trans_brelse(args->trans, state->path.blk[i].bp); in xfs_attr_node_get()
1540 state->path.blk[i].bp = NULL; in xfs_attr_node_get()
1586 return xfs_attr_intent_cache != NULL ? 0 : -ENOMEM; in xfs_attr_intent_init_cache()