aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDave Chinner <dchinner@redhat.com>2017-12-06 17:27:50 -0600
committerEric Sandeen <sandeen@redhat.com>2017-12-06 17:27:50 -0600
commitbefcd76898cf974d3e7244a2f406088f8ba7a634 (patch)
tree2efa3a847e624215dd26844d9efce0b61aaec28d
parentd7240c965389e1e864ea0213af94259e54ad2b23 (diff)
downloadxfsprogs-dev-befcd76898cf974d3e7244a2f406088f8ba7a634.tar.gz
mkfs: factor initial mount setup
Signed-Off-By: Dave Chinner <dchinner@redhat.com> Reviewed-by: Eric Sandeen <sandeen@redhat.com> Signed-off-by: Eric Sandeen <sandeen@sandeen.net>
-rw-r--r--mkfs/xfs_mkfs.c265
1 files changed, 141 insertions, 124 deletions
diff --git a/mkfs/xfs_mkfs.c b/mkfs/xfs_mkfs.c
index 0e3169f309..0ab6221dcf 100644
--- a/mkfs/xfs_mkfs.c
+++ b/mkfs/xfs_mkfs.c
@@ -1234,96 +1234,6 @@ discard_blocks(dev_t dev, uint64_t nsectors)
platform_discard_blocks(fd, 0, nsectors << 9);
}
-static void
-sb_set_features(
- struct xfs_sb *sbp,
- struct sb_feat_args *fp,
- int sectsize,
- int lsectsize,
- int dsunit)
-{
-
- sbp->sb_versionnum = XFS_DFL_SB_VERSION_BITS;
- if (fp->crcs_enabled)
- sbp->sb_versionnum |= XFS_SB_VERSION_5;
- else
- sbp->sb_versionnum |= XFS_SB_VERSION_4;
-
- if (fp->inode_align)
- sbp->sb_versionnum |= XFS_SB_VERSION_ALIGNBIT;
- if (dsunit)
- sbp->sb_versionnum |= XFS_SB_VERSION_DALIGNBIT;
- if (fp->log_version == 2)
- sbp->sb_versionnum |= XFS_SB_VERSION_LOGV2BIT;
- if (fp->attr_version == 1)
- sbp->sb_versionnum |= XFS_SB_VERSION_ATTRBIT;
- if (sectsize > BBSIZE || lsectsize > BBSIZE)
- sbp->sb_versionnum |= XFS_SB_VERSION_SECTORBIT;
- if (fp->nci)
- sbp->sb_versionnum |= XFS_SB_VERSION_BORGBIT;
-
-
- sbp->sb_features2 = 0;
- if (fp->lazy_sb_counters)
- sbp->sb_features2 |= XFS_SB_VERSION2_LAZYSBCOUNTBIT;
- if (!fp->projid16bit)
- sbp->sb_features2 |= XFS_SB_VERSION2_PROJID32BIT;
- if (fp->parent_pointers)
- sbp->sb_features2 |= XFS_SB_VERSION2_PARENTBIT;
- if (fp->crcs_enabled)
- sbp->sb_features2 |= XFS_SB_VERSION2_CRCBIT;
- if (fp->attr_version == 2)
- sbp->sb_features2 |= XFS_SB_VERSION2_ATTR2BIT;
-
- /* v5 superblocks have their own feature bit for dirftype */
- if (fp->dirftype && !fp->crcs_enabled)
- sbp->sb_features2 |= XFS_SB_VERSION2_FTYPE;
-
- /* update whether extended features are in use */
- if (sbp->sb_features2 != 0)
- sbp->sb_versionnum |= XFS_SB_VERSION_MOREBITSBIT;
-
- /*
- * Due to a structure alignment issue, sb_features2 ended up in one
- * of two locations, the second "incorrect" location represented by
- * the sb_bad_features2 field. To avoid older kernels mounting
- * filesystems they shouldn't, set both field to the same value.
- */
- sbp->sb_bad_features2 = sbp->sb_features2;
-
- if (!fp->crcs_enabled)
- return;
-
- /* default features for v5 filesystems */
- sbp->sb_features_compat = 0;
- sbp->sb_features_ro_compat = 0;
- sbp->sb_features_incompat = XFS_SB_FEAT_INCOMPAT_FTYPE;
- sbp->sb_features_log_incompat = 0;
-
- if (fp->finobt)
- sbp->sb_features_ro_compat = XFS_SB_FEAT_RO_COMPAT_FINOBT;
- if (fp->rmapbt)
- sbp->sb_features_ro_compat |= XFS_SB_FEAT_RO_COMPAT_RMAPBT;
- if (fp->reflink)
- sbp->sb_features_ro_compat |= XFS_SB_FEAT_RO_COMPAT_REFLINK;
-
- /*
- * Sparse inode chunk support has two main inode alignment requirements.
- * First, sparse chunk alignment must match the cluster size. Second,
- * full chunk alignment must match the inode chunk size.
- *
- * Copy the already calculated/scaled inoalignmt to spino_align and
- * update the former to the full inode chunk size.
- */
- if (fp->spinodes) {
- sbp->sb_spino_align = sbp->sb_inoalignmt;
- sbp->sb_inoalignmt = XFS_INODES_PER_CHUNK *
- sbp->sb_inodesize >> sbp->sb_blocklog;
- sbp->sb_features_incompat |= XFS_SB_FEAT_INCOMPAT_SPINODES;
- }
-
-}
-
static __attribute__((noreturn)) void
illegal_option(
const char *value,
@@ -2893,6 +2803,137 @@ calculate_imaxpct(
cfg->imaxpct = 1;
}
+/*
+ * Set up the initial state of the superblock so we can start using the
+ * libxfs geometry macros.
+ */
+static void
+sb_set_features(
+ struct mkfs_params *cfg,
+ struct xfs_sb *sbp)
+{
+ struct sb_feat_args *fp = &cfg->sb_feat;
+
+ sbp->sb_versionnum = XFS_DFL_SB_VERSION_BITS;
+ if (fp->crcs_enabled)
+ sbp->sb_versionnum |= XFS_SB_VERSION_5;
+ else
+ sbp->sb_versionnum |= XFS_SB_VERSION_4;
+
+ if (fp->inode_align) {
+ int cluster_size = XFS_INODE_BIG_CLUSTER_SIZE;
+
+ sbp->sb_versionnum |= XFS_SB_VERSION_ALIGNBIT;
+ if (cfg->sb_feat.crcs_enabled)
+ cluster_size *= cfg->inodesize / XFS_DINODE_MIN_SIZE;
+ sbp->sb_inoalignmt = cluster_size >> cfg->blocklog;
+ } else
+ sbp->sb_inoalignmt = 0;
+
+ if (cfg->dsunit)
+ sbp->sb_versionnum |= XFS_SB_VERSION_DALIGNBIT;
+ if (fp->log_version == 2)
+ sbp->sb_versionnum |= XFS_SB_VERSION_LOGV2BIT;
+ if (fp->attr_version == 1)
+ sbp->sb_versionnum |= XFS_SB_VERSION_ATTRBIT;
+ if (fp->nci)
+ sbp->sb_versionnum |= XFS_SB_VERSION_BORGBIT;
+
+ if (cfg->sectorsize > BBSIZE || cfg->lsectorsize > BBSIZE) {
+ sbp->sb_versionnum |= XFS_SB_VERSION_SECTORBIT;
+ sbp->sb_logsectlog = (uint8_t)cfg->lsectorlog;
+ sbp->sb_logsectsize = (uint16_t)cfg->lsectorsize;
+ } else {
+ sbp->sb_logsectlog = 0;
+ sbp->sb_logsectsize = 0;
+ }
+
+ sbp->sb_features2 = 0;
+ if (fp->lazy_sb_counters)
+ sbp->sb_features2 |= XFS_SB_VERSION2_LAZYSBCOUNTBIT;
+ if (!fp->projid16bit)
+ sbp->sb_features2 |= XFS_SB_VERSION2_PROJID32BIT;
+ if (fp->parent_pointers)
+ sbp->sb_features2 |= XFS_SB_VERSION2_PARENTBIT;
+ if (fp->crcs_enabled)
+ sbp->sb_features2 |= XFS_SB_VERSION2_CRCBIT;
+ if (fp->attr_version == 2)
+ sbp->sb_features2 |= XFS_SB_VERSION2_ATTR2BIT;
+
+ /* v5 superblocks have their own feature bit for dirftype */
+ if (fp->dirftype && !fp->crcs_enabled)
+ sbp->sb_features2 |= XFS_SB_VERSION2_FTYPE;
+
+ /* update whether extended features are in use */
+ if (sbp->sb_features2 != 0)
+ sbp->sb_versionnum |= XFS_SB_VERSION_MOREBITSBIT;
+
+ /*
+ * Due to a structure alignment issue, sb_features2 ended up in one
+ * of two locations, the second "incorrect" location represented by
+ * the sb_bad_features2 field. To avoid older kernels mounting
+ * filesystems they shouldn't, set both field to the same value.
+ */
+ sbp->sb_bad_features2 = sbp->sb_features2;
+
+ if (!fp->crcs_enabled)
+ return;
+
+ /* default features for v5 filesystems */
+ sbp->sb_features_compat = 0;
+ sbp->sb_features_ro_compat = 0;
+ sbp->sb_features_incompat = XFS_SB_FEAT_INCOMPAT_FTYPE;
+ sbp->sb_features_log_incompat = 0;
+
+ if (fp->finobt)
+ sbp->sb_features_ro_compat = XFS_SB_FEAT_RO_COMPAT_FINOBT;
+ if (fp->rmapbt)
+ sbp->sb_features_ro_compat |= XFS_SB_FEAT_RO_COMPAT_RMAPBT;
+ if (fp->reflink)
+ sbp->sb_features_ro_compat |= XFS_SB_FEAT_RO_COMPAT_REFLINK;
+
+ /*
+ * Sparse inode chunk support has two main inode alignment requirements.
+ * First, sparse chunk alignment must match the cluster size. Second,
+ * full chunk alignment must match the inode chunk size.
+ *
+ * Copy the already calculated/scaled inoalignmt to spino_align and
+ * update the former to the full inode chunk size.
+ */
+ if (fp->spinodes) {
+ sbp->sb_spino_align = sbp->sb_inoalignmt;
+ sbp->sb_inoalignmt = XFS_INODES_PER_CHUNK *
+ cfg->inodesize >> cfg->blocklog;
+ sbp->sb_features_incompat |= XFS_SB_FEAT_INCOMPAT_SPINODES;
+ }
+
+}
+
+/*
+ * Set up mount and superblock with the minimum parameters required for
+ * the libxfs macros needed by the log sizing code to run successfully.
+ */
+static void
+initialise_mount(
+ struct mkfs_params *cfg,
+ struct xfs_mount *mp,
+ struct xfs_sb *sbp)
+{
+ sbp->sb_blocklog = (uint8_t)cfg->blocklog;
+ sbp->sb_sectlog = (uint8_t)cfg->sectorlog;
+ sbp->sb_agblklog = (uint8_t)log2_roundup(cfg->agsize);
+ sbp->sb_agblocks = (xfs_agblock_t)cfg->agsize;
+ sbp->sb_agcount = (xfs_agnumber_t)cfg->agcount;
+ mp->m_blkbb_log = sbp->sb_blocklog - BBSHIFT;
+ mp->m_sectbb_log = sbp->sb_sectlog - BBSHIFT;
+
+ /*
+ * sb_versionnum, finobt and rmapbt flags must be set before we use
+ * libxfs_prealloc_blocks().
+ */
+ sb_set_features(cfg, sbp);
+}
+
static void
print_mkfs_cfg(
struct mkfs_params *cfg,
@@ -2989,21 +3030,6 @@ setup_superblock(
} else
sbp->sb_logsunit = 0;
- if (cfg->sb_feat.inode_align) {
- int cluster_size = XFS_INODE_BIG_CLUSTER_SIZE;
- if (cfg->sb_feat.crcs_enabled)
- cluster_size *= cfg->inodesize / XFS_DINODE_MIN_SIZE;
- sbp->sb_inoalignmt = cluster_size >> cfg->blocklog;
- } else
- sbp->sb_inoalignmt = 0;
-
- if (cfg->lsectorsize != BBSIZE || cfg->sectorsize != BBSIZE) {
- sbp->sb_logsectlog = (uint8_t)cfg->lsectorlog;
- sbp->sb_logsectsize = (uint16_t)cfg->lsectorsize;
- } else {
- sbp->sb_logsectlog = 0;
- sbp->sb_logsectsize = 0;
- }
}
/*
@@ -3556,8 +3582,6 @@ main(
int lsectorsize;
int lsunit;
int min_logblocks;
- xfs_mount_t *mp;
- xfs_mount_t mbuf;
xfs_extlen_t nbmblocks;
int dry_run = 0;
int discard = 1;
@@ -3568,11 +3592,13 @@ main(
xfs_extlen_t rtextblocks;
xfs_rtblock_t rtextents;
char *rtfile;
- xfs_sb_t *sbp;
int sectorlog;
uuid_t uuid;
int worst_freelist;
libxfs_init_t xi;
+ struct xfs_mount mbuf = {};
+ struct xfs_mount *mp = &mbuf;
+ struct xfs_sb *sbp = &mp->m_sb;
struct fs_topology ft;
struct sb_feat_args sb_feat;
/* build time defaults */
@@ -3773,6 +3799,13 @@ main(
calculate_imaxpct(&cfg, &cli);
+ /*
+ * Set up the basic superblock parameters now so that we can use
+ * the geometry information we've already validated in libxfs
+ * provided functions to determine on-disk format information.
+ */
+ initialise_mount(&cfg, mp, sbp);
+
/* temp don't break code */
sectorsize = cfg.sectorsize;
sectorlog = cfg.sectorlog;
@@ -3852,22 +3885,6 @@ main(
validate_log_size(logblocks, blocklog, min_logblocks);
protostring = setup_proto(protofile);
- mp = &mbuf;
- sbp = &mp->m_sb;
- memset(mp, 0, sizeof(xfs_mount_t));
- sbp->sb_blocklog = (uint8_t)blocklog;
- sbp->sb_sectlog = (uint8_t)sectorlog;
- sbp->sb_agblklog = (uint8_t)log2_roundup((unsigned int)agsize);
- sbp->sb_agblocks = (xfs_agblock_t)agsize;
- mp->m_blkbb_log = sbp->sb_blocklog - BBSHIFT;
- mp->m_sectbb_log = sbp->sb_sectlog - BBSHIFT;
-
- /*
- * sb_versionnum, finobt and rmapbt flags must be set before we use
- * libxfs_prealloc_blocks().
- */
- sb_set_features(&mp->m_sb, &sb_feat, sectorsize, lsectorsize, dsunit);
-
if (loginternal) {
/*