@@ -813,6 +813,50 @@ rtsummary_create(
libxfs_imeta_end_update(mp, &upd, 0);
}
+/* Initialize block headers of rt free space files. */
+static int
+init_rtblock_headers(
+ struct xfs_inode *ip,
+ xfs_fileoff_t nrblocks,
+ const struct xfs_buf_ops *ops,
+ uint32_t magic)
+{
+ struct xfs_bmbt_irec map;
+ struct xfs_mount *mp = ip->i_mount;
+ struct xfs_rtbuf_blkinfo *hdr;
+ xfs_fileoff_t off = 0;
+ int error;
+
+ while (off < nrblocks) {
+ struct xfs_buf *bp;
+ xfs_daddr_t daddr;
+ int nimaps = 1;
+
+ error = -libxfs_bmapi_read(ip, off, 1, &map, &nimaps, 0);
+ if (error)
+ return error;
+
+ daddr = XFS_FSB_TO_DADDR(mp, map.br_startblock);
+ error = -libxfs_buf_get(mp->m_ddev_targp, daddr,
+ XFS_FSB_TO_BB(mp, map.br_blockcount), &bp);
+ if (error)
+ return error;
+
+ bp->b_ops = ops;
+ hdr = bp->b_addr;
+ hdr->rt_magic = cpu_to_be32(magic);
+ hdr->rt_owner = cpu_to_be64(ip->i_ino);
+ hdr->rt_blkno = cpu_to_be64(daddr);
+ platform_uuid_copy(&hdr->rt_uuid, &mp->m_sb.sb_meta_uuid);
+ libxfs_buf_mark_dirty(bp);
+ libxfs_buf_relse(bp);
+
+ off = map.br_startoff + map.br_blockcount;
+ }
+
+ return 0;
+}
+
/* Zero the realtime bitmap. */
static void
rtbitmap_init(
@@ -856,6 +900,13 @@ rtbitmap_init(
if (error)
fail(_("Block allocation of the realtime bitmap inode failed"),
error);
+
+ if (xfs_has_rtgroups(mp)) {
+ error = init_rtblock_headers(mp->m_rbmip, mp->m_sb.sb_rbmblocks,
+ &xfs_rtbitmap_buf_ops, XFS_RTBITMAP_MAGIC);
+ if (error)
+ fail(_("Initialization of rtbitmap failed"), error);
+ }
}
/* Zero the realtime summary file. */
@@ -870,6 +870,7 @@ struct sb_feat_args {
bool nodalign;
bool nortalign;
bool nrext64;
+ bool rtgroups; /* XFS_SB_FEAT_COMPAT_RTGROUPS */
};
struct cli_params {
@@ -3065,6 +3066,7 @@ validate_rtdev(
char **devname)
{
struct libxfs_xinit *xi = cli->xi;
+ unsigned int rbmblocksize = cfg->blocksize;
*devname = NULL;
@@ -3112,8 +3114,10 @@ reported by the device (%u).\n"),
}
cfg->rtextents = cfg->rtblocks / cfg->rtextblocks;
+ if (cfg->sb_feat.rtgroups)
+ rbmblocksize -= sizeof(struct xfs_rtbuf_blkinfo);
cfg->rtbmblocks = (xfs_extlen_t)howmany(cfg->rtextents,
- NBBY * cfg->blocksize);
+ NBBY * rbmblocksize);
}
static bool