Loading fs/xfs/libxfs/xfs_attr.c +5 −5 Original line number Diff line number Diff line Loading @@ -649,8 +649,8 @@ xfs_attr_leaf_remove_attr( int forkoff; int error; error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, &bp); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, args->blkno, &bp); if (error) return error; Loading Loading @@ -681,7 +681,7 @@ xfs_attr_leaf_shrink( if (!xfs_attr_is_leaf(dp)) return 0; error = xfs_attr3_leaf_read(args->trans, args->dp, 0, &bp); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, 0, &bp); if (error) return error; Loading Loading @@ -1158,7 +1158,7 @@ xfs_attr_leaf_try_add( struct xfs_buf *bp; int error; error = xfs_attr3_leaf_read(args->trans, args->dp, 0, &bp); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, 0, &bp); if (error) return error; Loading Loading @@ -1206,7 +1206,7 @@ xfs_attr_leaf_hasname( { int error = 0; error = xfs_attr3_leaf_read(args->trans, args->dp, 0, bp); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, 0, bp); if (error) return error; Loading fs/xfs/libxfs/xfs_attr_leaf.c +47 −9 Original line number Diff line number Diff line Loading @@ -388,6 +388,27 @@ xfs_attr3_leaf_verify( return NULL; } xfs_failaddr_t xfs_attr3_leaf_header_check( struct xfs_buf *bp, xfs_ino_t owner) { struct xfs_mount *mp = bp->b_mount; if (xfs_has_crc(mp)) { struct xfs_attr3_leafblock *hdr3 = bp->b_addr; if (hdr3->hdr.info.hdr.magic != cpu_to_be16(XFS_ATTR3_LEAF_MAGIC)) return __this_address; if (be64_to_cpu(hdr3->hdr.info.owner) != owner) return __this_address; } return NULL; } static void xfs_attr3_leaf_write_verify( struct xfs_buf *bp) Loading Loading @@ -448,16 +469,30 @@ int xfs_attr3_leaf_read( struct xfs_trans *tp, struct xfs_inode *dp, xfs_ino_t owner, xfs_dablk_t bno, struct xfs_buf **bpp) { xfs_failaddr_t fa; int err; err = xfs_da_read_buf(tp, dp, bno, 0, bpp, XFS_ATTR_FORK, &xfs_attr3_leaf_buf_ops); if (!err && tp && *bpp) xfs_trans_buf_set_type(tp, *bpp, XFS_BLFT_ATTR_LEAF_BUF); if (err || !(*bpp)) return err; fa = xfs_attr3_leaf_header_check(*bpp, owner); if (fa) { __xfs_buf_mark_corrupt(*bpp, fa); xfs_trans_brelse(tp, *bpp); *bpp = NULL; xfs_dirattr_mark_sick(dp, XFS_ATTR_FORK); return -EFSCORRUPTED; } if (tp) xfs_trans_buf_set_type(tp, *bpp, XFS_BLFT_ATTR_LEAF_BUF); return 0; } /*======================================================================== Loading Loading @@ -1160,7 +1195,7 @@ xfs_attr3_leaf_to_node( error = xfs_da_grow_inode(args, &blkno); if (error) goto out; error = xfs_attr3_leaf_read(args->trans, dp, 0, &bp1); error = xfs_attr3_leaf_read(args->trans, dp, args->owner, 0, &bp1); if (error) goto out; Loading Loading @@ -1995,7 +2030,7 @@ xfs_attr3_leaf_toosmall( if (blkno == 0) continue; error = xfs_attr3_leaf_read(state->args->trans, state->args->dp, blkno, &bp); state->args->owner, blkno, &bp); if (error) return error; Loading Loading @@ -2717,7 +2752,8 @@ xfs_attr3_leaf_clearflag( /* * Set up the operation. */ error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, &bp); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, args->blkno, &bp); if (error) return error; Loading Loading @@ -2781,7 +2817,8 @@ xfs_attr3_leaf_setflag( /* * Set up the operation. */ error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, &bp); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, args->blkno, &bp); if (error) return error; Loading Loading @@ -2840,7 +2877,8 @@ xfs_attr3_leaf_flipflags( /* * Read the block containing the "old" attr */ error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, &bp1); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, args->blkno, &bp1); if (error) return error; Loading @@ -2848,8 +2886,8 @@ xfs_attr3_leaf_flipflags( * Read the block containing the "new" attr, if it is different */ if (args->blkno2 != args->blkno) { error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno2, &bp2); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, args->blkno2, &bp2); if (error) return error; } else { Loading fs/xfs/libxfs/xfs_attr_leaf.h +3 −1 Original line number Diff line number Diff line Loading @@ -98,12 +98,14 @@ int xfs_attr_leaf_order(struct xfs_buf *leaf1_bp, struct xfs_buf *leaf2_bp); int xfs_attr_leaf_newentsize(struct xfs_da_args *args, int *local); int xfs_attr3_leaf_read(struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t bno, struct xfs_buf **bpp); xfs_ino_t owner, xfs_dablk_t bno, struct xfs_buf **bpp); void xfs_attr3_leaf_hdr_from_disk(struct xfs_da_geometry *geo, struct xfs_attr3_icleaf_hdr *to, struct xfs_attr_leafblock *from); void xfs_attr3_leaf_hdr_to_disk(struct xfs_da_geometry *geo, struct xfs_attr_leafblock *to, struct xfs_attr3_icleaf_hdr *from); xfs_failaddr_t xfs_attr3_leaf_header_check(struct xfs_buf *bp, xfs_ino_t owner); #endif /* __XFS_ATTR_LEAF_H__ */ fs/xfs/libxfs/xfs_da_btree.c +42 −0 Original line number Diff line number Diff line Loading @@ -252,6 +252,25 @@ xfs_da3_node_verify( return NULL; } xfs_failaddr_t xfs_da3_header_check( struct xfs_buf *bp, xfs_ino_t owner) { struct xfs_mount *mp = bp->b_mount; struct xfs_da_blkinfo *hdr = bp->b_addr; if (!xfs_has_crc(mp)) return NULL; switch (hdr->magic) { case cpu_to_be16(XFS_ATTR3_LEAF_MAGIC): return xfs_attr3_leaf_header_check(bp, owner); } return NULL; } static void xfs_da3_node_write_verify( struct xfs_buf *bp) Loading Loading @@ -1591,6 +1610,7 @@ xfs_da3_node_lookup_int( struct xfs_da_node_entry *btree; struct xfs_da3_icnode_hdr nodehdr; struct xfs_da_args *args; xfs_failaddr_t fa; xfs_dablk_t blkno; xfs_dahash_t hashval; xfs_dahash_t btreehashval; Loading Loading @@ -1629,6 +1649,12 @@ xfs_da3_node_lookup_int( if (magic == XFS_ATTR_LEAF_MAGIC || magic == XFS_ATTR3_LEAF_MAGIC) { fa = xfs_attr3_leaf_header_check(blk->bp, args->owner); if (fa) { __xfs_buf_mark_corrupt(blk->bp, fa); xfs_da_mark_sick(args); return -EFSCORRUPTED; } blk->magic = XFS_ATTR_LEAF_MAGIC; blk->hashval = xfs_attr_leaf_lasthash(blk->bp, NULL); break; Loading Loading @@ -1996,6 +2022,7 @@ xfs_da3_path_shift( struct xfs_da_node_entry *btree; struct xfs_da3_icnode_hdr nodehdr; struct xfs_buf *bp; xfs_failaddr_t fa; xfs_dablk_t blkno = 0; int level; int error; Loading Loading @@ -2087,6 +2114,12 @@ xfs_da3_path_shift( break; case XFS_ATTR_LEAF_MAGIC: case XFS_ATTR3_LEAF_MAGIC: fa = xfs_attr3_leaf_header_check(blk->bp, args->owner); if (fa) { __xfs_buf_mark_corrupt(blk->bp, fa); xfs_da_mark_sick(args); return -EFSCORRUPTED; } blk->magic = XFS_ATTR_LEAF_MAGIC; ASSERT(level == path->active-1); blk->index = 0; Loading Loading @@ -2290,6 +2323,7 @@ xfs_da3_swap_lastblock( struct xfs_buf *last_buf; struct xfs_buf *sib_buf; struct xfs_buf *par_buf; xfs_failaddr_t fa; xfs_dahash_t dead_hash; xfs_fileoff_t lastoff; xfs_dablk_t dead_blkno; Loading Loading @@ -2326,6 +2360,14 @@ xfs_da3_swap_lastblock( error = xfs_da3_node_read(tp, dp, last_blkno, &last_buf, w); if (error) return error; fa = xfs_da3_header_check(last_buf, args->owner); if (fa) { __xfs_buf_mark_corrupt(last_buf, fa); xfs_trans_brelse(tp, last_buf); xfs_da_mark_sick(args); return -EFSCORRUPTED; } /* * Copy the last block into the dead buffer and log it. */ Loading fs/xfs/libxfs/xfs_da_btree.h +1 −0 Original line number Diff line number Diff line Loading @@ -236,6 +236,7 @@ void xfs_da3_node_hdr_from_disk(struct xfs_mount *mp, struct xfs_da3_icnode_hdr *to, struct xfs_da_intnode *from); void xfs_da3_node_hdr_to_disk(struct xfs_mount *mp, struct xfs_da_intnode *to, struct xfs_da3_icnode_hdr *from); xfs_failaddr_t xfs_da3_header_check(struct xfs_buf *bp, xfs_ino_t owner); extern struct kmem_cache *xfs_da_state_cache; Loading Loading
fs/xfs/libxfs/xfs_attr.c +5 −5 Original line number Diff line number Diff line Loading @@ -649,8 +649,8 @@ xfs_attr_leaf_remove_attr( int forkoff; int error; error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, &bp); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, args->blkno, &bp); if (error) return error; Loading Loading @@ -681,7 +681,7 @@ xfs_attr_leaf_shrink( if (!xfs_attr_is_leaf(dp)) return 0; error = xfs_attr3_leaf_read(args->trans, args->dp, 0, &bp); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, 0, &bp); if (error) return error; Loading Loading @@ -1158,7 +1158,7 @@ xfs_attr_leaf_try_add( struct xfs_buf *bp; int error; error = xfs_attr3_leaf_read(args->trans, args->dp, 0, &bp); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, 0, &bp); if (error) return error; Loading Loading @@ -1206,7 +1206,7 @@ xfs_attr_leaf_hasname( { int error = 0; error = xfs_attr3_leaf_read(args->trans, args->dp, 0, bp); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, 0, bp); if (error) return error; Loading
fs/xfs/libxfs/xfs_attr_leaf.c +47 −9 Original line number Diff line number Diff line Loading @@ -388,6 +388,27 @@ xfs_attr3_leaf_verify( return NULL; } xfs_failaddr_t xfs_attr3_leaf_header_check( struct xfs_buf *bp, xfs_ino_t owner) { struct xfs_mount *mp = bp->b_mount; if (xfs_has_crc(mp)) { struct xfs_attr3_leafblock *hdr3 = bp->b_addr; if (hdr3->hdr.info.hdr.magic != cpu_to_be16(XFS_ATTR3_LEAF_MAGIC)) return __this_address; if (be64_to_cpu(hdr3->hdr.info.owner) != owner) return __this_address; } return NULL; } static void xfs_attr3_leaf_write_verify( struct xfs_buf *bp) Loading Loading @@ -448,16 +469,30 @@ int xfs_attr3_leaf_read( struct xfs_trans *tp, struct xfs_inode *dp, xfs_ino_t owner, xfs_dablk_t bno, struct xfs_buf **bpp) { xfs_failaddr_t fa; int err; err = xfs_da_read_buf(tp, dp, bno, 0, bpp, XFS_ATTR_FORK, &xfs_attr3_leaf_buf_ops); if (!err && tp && *bpp) xfs_trans_buf_set_type(tp, *bpp, XFS_BLFT_ATTR_LEAF_BUF); if (err || !(*bpp)) return err; fa = xfs_attr3_leaf_header_check(*bpp, owner); if (fa) { __xfs_buf_mark_corrupt(*bpp, fa); xfs_trans_brelse(tp, *bpp); *bpp = NULL; xfs_dirattr_mark_sick(dp, XFS_ATTR_FORK); return -EFSCORRUPTED; } if (tp) xfs_trans_buf_set_type(tp, *bpp, XFS_BLFT_ATTR_LEAF_BUF); return 0; } /*======================================================================== Loading Loading @@ -1160,7 +1195,7 @@ xfs_attr3_leaf_to_node( error = xfs_da_grow_inode(args, &blkno); if (error) goto out; error = xfs_attr3_leaf_read(args->trans, dp, 0, &bp1); error = xfs_attr3_leaf_read(args->trans, dp, args->owner, 0, &bp1); if (error) goto out; Loading Loading @@ -1995,7 +2030,7 @@ xfs_attr3_leaf_toosmall( if (blkno == 0) continue; error = xfs_attr3_leaf_read(state->args->trans, state->args->dp, blkno, &bp); state->args->owner, blkno, &bp); if (error) return error; Loading Loading @@ -2717,7 +2752,8 @@ xfs_attr3_leaf_clearflag( /* * Set up the operation. */ error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, &bp); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, args->blkno, &bp); if (error) return error; Loading Loading @@ -2781,7 +2817,8 @@ xfs_attr3_leaf_setflag( /* * Set up the operation. */ error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, &bp); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, args->blkno, &bp); if (error) return error; Loading Loading @@ -2840,7 +2877,8 @@ xfs_attr3_leaf_flipflags( /* * Read the block containing the "old" attr */ error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno, &bp1); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, args->blkno, &bp1); if (error) return error; Loading @@ -2848,8 +2886,8 @@ xfs_attr3_leaf_flipflags( * Read the block containing the "new" attr, if it is different */ if (args->blkno2 != args->blkno) { error = xfs_attr3_leaf_read(args->trans, args->dp, args->blkno2, &bp2); error = xfs_attr3_leaf_read(args->trans, args->dp, args->owner, args->blkno2, &bp2); if (error) return error; } else { Loading
fs/xfs/libxfs/xfs_attr_leaf.h +3 −1 Original line number Diff line number Diff line Loading @@ -98,12 +98,14 @@ int xfs_attr_leaf_order(struct xfs_buf *leaf1_bp, struct xfs_buf *leaf2_bp); int xfs_attr_leaf_newentsize(struct xfs_da_args *args, int *local); int xfs_attr3_leaf_read(struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t bno, struct xfs_buf **bpp); xfs_ino_t owner, xfs_dablk_t bno, struct xfs_buf **bpp); void xfs_attr3_leaf_hdr_from_disk(struct xfs_da_geometry *geo, struct xfs_attr3_icleaf_hdr *to, struct xfs_attr_leafblock *from); void xfs_attr3_leaf_hdr_to_disk(struct xfs_da_geometry *geo, struct xfs_attr_leafblock *to, struct xfs_attr3_icleaf_hdr *from); xfs_failaddr_t xfs_attr3_leaf_header_check(struct xfs_buf *bp, xfs_ino_t owner); #endif /* __XFS_ATTR_LEAF_H__ */
fs/xfs/libxfs/xfs_da_btree.c +42 −0 Original line number Diff line number Diff line Loading @@ -252,6 +252,25 @@ xfs_da3_node_verify( return NULL; } xfs_failaddr_t xfs_da3_header_check( struct xfs_buf *bp, xfs_ino_t owner) { struct xfs_mount *mp = bp->b_mount; struct xfs_da_blkinfo *hdr = bp->b_addr; if (!xfs_has_crc(mp)) return NULL; switch (hdr->magic) { case cpu_to_be16(XFS_ATTR3_LEAF_MAGIC): return xfs_attr3_leaf_header_check(bp, owner); } return NULL; } static void xfs_da3_node_write_verify( struct xfs_buf *bp) Loading Loading @@ -1591,6 +1610,7 @@ xfs_da3_node_lookup_int( struct xfs_da_node_entry *btree; struct xfs_da3_icnode_hdr nodehdr; struct xfs_da_args *args; xfs_failaddr_t fa; xfs_dablk_t blkno; xfs_dahash_t hashval; xfs_dahash_t btreehashval; Loading Loading @@ -1629,6 +1649,12 @@ xfs_da3_node_lookup_int( if (magic == XFS_ATTR_LEAF_MAGIC || magic == XFS_ATTR3_LEAF_MAGIC) { fa = xfs_attr3_leaf_header_check(blk->bp, args->owner); if (fa) { __xfs_buf_mark_corrupt(blk->bp, fa); xfs_da_mark_sick(args); return -EFSCORRUPTED; } blk->magic = XFS_ATTR_LEAF_MAGIC; blk->hashval = xfs_attr_leaf_lasthash(blk->bp, NULL); break; Loading Loading @@ -1996,6 +2022,7 @@ xfs_da3_path_shift( struct xfs_da_node_entry *btree; struct xfs_da3_icnode_hdr nodehdr; struct xfs_buf *bp; xfs_failaddr_t fa; xfs_dablk_t blkno = 0; int level; int error; Loading Loading @@ -2087,6 +2114,12 @@ xfs_da3_path_shift( break; case XFS_ATTR_LEAF_MAGIC: case XFS_ATTR3_LEAF_MAGIC: fa = xfs_attr3_leaf_header_check(blk->bp, args->owner); if (fa) { __xfs_buf_mark_corrupt(blk->bp, fa); xfs_da_mark_sick(args); return -EFSCORRUPTED; } blk->magic = XFS_ATTR_LEAF_MAGIC; ASSERT(level == path->active-1); blk->index = 0; Loading Loading @@ -2290,6 +2323,7 @@ xfs_da3_swap_lastblock( struct xfs_buf *last_buf; struct xfs_buf *sib_buf; struct xfs_buf *par_buf; xfs_failaddr_t fa; xfs_dahash_t dead_hash; xfs_fileoff_t lastoff; xfs_dablk_t dead_blkno; Loading Loading @@ -2326,6 +2360,14 @@ xfs_da3_swap_lastblock( error = xfs_da3_node_read(tp, dp, last_blkno, &last_buf, w); if (error) return error; fa = xfs_da3_header_check(last_buf, args->owner); if (fa) { __xfs_buf_mark_corrupt(last_buf, fa); xfs_trans_brelse(tp, last_buf); xfs_da_mark_sick(args); return -EFSCORRUPTED; } /* * Copy the last block into the dead buffer and log it. */ Loading
fs/xfs/libxfs/xfs_da_btree.h +1 −0 Original line number Diff line number Diff line Loading @@ -236,6 +236,7 @@ void xfs_da3_node_hdr_from_disk(struct xfs_mount *mp, struct xfs_da3_icnode_hdr *to, struct xfs_da_intnode *from); void xfs_da3_node_hdr_to_disk(struct xfs_mount *mp, struct xfs_da_intnode *to, struct xfs_da3_icnode_hdr *from); xfs_failaddr_t xfs_da3_header_check(struct xfs_buf *bp, xfs_ino_t owner); extern struct kmem_cache *xfs_da_state_cache; Loading