diff options
author | Darrick J. Wong <darrick.wong@oracle.com> | 2016-08-02 21:36:08 -0400 |
---|---|---|
committer | Dave Chinner <david@fromorbit.com> | 2016-08-02 21:36:08 -0400 |
commit | e70d829f8d288cd062d265085420f001828b0683 (patch) | |
tree | 86ed11884190378f161cd1443bc8d7ba33668d38 | |
parent | 035e00acb5c719bd003639b90716a7e94e023b73 (diff) |
xfs: add rmap btree growfs support
Originally-From: Dave Chinner <dchinner@redhat.com>
Now we can read and write rmap btree blocks, we can add support to
the growfs code to initialise new rmap btree blocks.
[darrick.wong@oracle.com: fill out the rmap offset fields]
Signed-off-by: Dave Chinner <dchinner@redhat.com>
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
Reviewed-by: Dave Chinner <dchinner@redhat.com>
Signed-off-by: Dave Chinner <david@fromorbit.com>
-rw-r--r-- | fs/xfs/xfs_fsops.c | 73 |
1 files changed, 73 insertions, 0 deletions
diff --git a/fs/xfs/xfs_fsops.c b/fs/xfs/xfs_fsops.c index b625b61d1244..27e6e8cdd431 100644 --- a/fs/xfs/xfs_fsops.c +++ b/fs/xfs/xfs_fsops.c | |||
@@ -33,6 +33,7 @@ | |||
33 | #include "xfs_btree.h" | 33 | #include "xfs_btree.h" |
34 | #include "xfs_alloc_btree.h" | 34 | #include "xfs_alloc_btree.h" |
35 | #include "xfs_alloc.h" | 35 | #include "xfs_alloc.h" |
36 | #include "xfs_rmap_btree.h" | ||
36 | #include "xfs_ialloc.h" | 37 | #include "xfs_ialloc.h" |
37 | #include "xfs_fsops.h" | 38 | #include "xfs_fsops.h" |
38 | #include "xfs_itable.h" | 39 | #include "xfs_itable.h" |
@@ -241,6 +242,12 @@ xfs_growfs_data_private( | |||
241 | agf->agf_roots[XFS_BTNUM_CNTi] = cpu_to_be32(XFS_CNT_BLOCK(mp)); | 242 | agf->agf_roots[XFS_BTNUM_CNTi] = cpu_to_be32(XFS_CNT_BLOCK(mp)); |
242 | agf->agf_levels[XFS_BTNUM_BNOi] = cpu_to_be32(1); | 243 | agf->agf_levels[XFS_BTNUM_BNOi] = cpu_to_be32(1); |
243 | agf->agf_levels[XFS_BTNUM_CNTi] = cpu_to_be32(1); | 244 | agf->agf_levels[XFS_BTNUM_CNTi] = cpu_to_be32(1); |
245 | if (xfs_sb_version_hasrmapbt(&mp->m_sb)) { | ||
246 | agf->agf_roots[XFS_BTNUM_RMAPi] = | ||
247 | cpu_to_be32(XFS_RMAP_BLOCK(mp)); | ||
248 | agf->agf_levels[XFS_BTNUM_RMAPi] = cpu_to_be32(1); | ||
249 | } | ||
250 | |||
244 | agf->agf_flfirst = cpu_to_be32(1); | 251 | agf->agf_flfirst = cpu_to_be32(1); |
245 | agf->agf_fllast = 0; | 252 | agf->agf_fllast = 0; |
246 | agf->agf_flcount = 0; | 253 | agf->agf_flcount = 0; |
@@ -380,6 +387,72 @@ xfs_growfs_data_private( | |||
380 | if (error) | 387 | if (error) |
381 | goto error0; | 388 | goto error0; |
382 | 389 | ||
390 | /* RMAP btree root block */ | ||
391 | if (xfs_sb_version_hasrmapbt(&mp->m_sb)) { | ||
392 | struct xfs_rmap_rec *rrec; | ||
393 | struct xfs_btree_block *block; | ||
394 | |||
395 | bp = xfs_growfs_get_hdr_buf(mp, | ||
396 | XFS_AGB_TO_DADDR(mp, agno, XFS_RMAP_BLOCK(mp)), | ||
397 | BTOBB(mp->m_sb.sb_blocksize), 0, | ||
398 | &xfs_rmapbt_buf_ops); | ||
399 | if (!bp) { | ||
400 | error = -ENOMEM; | ||
401 | goto error0; | ||
402 | } | ||
403 | |||
404 | xfs_btree_init_block(mp, bp, XFS_RMAP_CRC_MAGIC, 0, 0, | ||
405 | agno, XFS_BTREE_CRC_BLOCKS); | ||
406 | block = XFS_BUF_TO_BLOCK(bp); | ||
407 | |||
408 | |||
409 | /* | ||
410 | * mark the AG header regions as static metadata The BNO | ||
411 | * btree block is the first block after the headers, so | ||
412 | * it's location defines the size of region the static | ||
413 | * metadata consumes. | ||
414 | * | ||
415 | * Note: unlike mkfs, we never have to account for log | ||
416 | * space when growing the data regions | ||
417 | */ | ||
418 | rrec = XFS_RMAP_REC_ADDR(block, 1); | ||
419 | rrec->rm_startblock = 0; | ||
420 | rrec->rm_blockcount = cpu_to_be32(XFS_BNO_BLOCK(mp)); | ||
421 | rrec->rm_owner = cpu_to_be64(XFS_RMAP_OWN_FS); | ||
422 | rrec->rm_offset = 0; | ||
423 | be16_add_cpu(&block->bb_numrecs, 1); | ||
424 | |||
425 | /* account freespace btree root blocks */ | ||
426 | rrec = XFS_RMAP_REC_ADDR(block, 2); | ||
427 | rrec->rm_startblock = cpu_to_be32(XFS_BNO_BLOCK(mp)); | ||
428 | rrec->rm_blockcount = cpu_to_be32(2); | ||
429 | rrec->rm_owner = cpu_to_be64(XFS_RMAP_OWN_AG); | ||
430 | rrec->rm_offset = 0; | ||
431 | be16_add_cpu(&block->bb_numrecs, 1); | ||
432 | |||
433 | /* account inode btree root blocks */ | ||
434 | rrec = XFS_RMAP_REC_ADDR(block, 3); | ||
435 | rrec->rm_startblock = cpu_to_be32(XFS_IBT_BLOCK(mp)); | ||
436 | rrec->rm_blockcount = cpu_to_be32(XFS_RMAP_BLOCK(mp) - | ||
437 | XFS_IBT_BLOCK(mp)); | ||
438 | rrec->rm_owner = cpu_to_be64(XFS_RMAP_OWN_INOBT); | ||
439 | rrec->rm_offset = 0; | ||
440 | be16_add_cpu(&block->bb_numrecs, 1); | ||
441 | |||
442 | /* account for rmap btree root */ | ||
443 | rrec = XFS_RMAP_REC_ADDR(block, 4); | ||
444 | rrec->rm_startblock = cpu_to_be32(XFS_RMAP_BLOCK(mp)); | ||
445 | rrec->rm_blockcount = cpu_to_be32(1); | ||
446 | rrec->rm_owner = cpu_to_be64(XFS_RMAP_OWN_AG); | ||
447 | rrec->rm_offset = 0; | ||
448 | be16_add_cpu(&block->bb_numrecs, 1); | ||
449 | |||
450 | error = xfs_bwrite(bp); | ||
451 | xfs_buf_relse(bp); | ||
452 | if (error) | ||
453 | goto error0; | ||
454 | } | ||
455 | |||
383 | /* | 456 | /* |
384 | * INO btree root block | 457 | * INO btree root block |
385 | */ | 458 | */ |