From e68bf85fd6b8a2a9f78c3535e022aa29104a5afa Mon Sep 17 00:00:00 2001 From: Tom Cherry Date: Thu, 25 Oct 2018 16:10:23 -0700 Subject: [PATCH] init: allow first stage mount to read an fstab Now that we have a first stage ramdisk (or use recovery in its place), it's possible to place a vendor specific fstab along with first stage init, removing the need for device tree modifications to have an fstab. Bug: 117933812 Test: hikey boots with only an fstab in first stage ramdisk Test: blueline mainline boots with a disabled DT fstab and an fstab in recovery Change-Id: I4460b88851557a75ba06ff795cd842e7dfb6da46 --- fs_mgr/fs_mgr.cpp | 5 +++-- fs_mgr/fs_mgr_fstab.cpp | 7 ++++++- fs_mgr/fs_mgr_overlayfs.cpp | 9 ++++----- fs_mgr/fs_mgr_priv.h | 2 ++ fs_mgr/include/fs_mgr_overlayfs.h | 5 ++--- fs_mgr/include_fstab/fstab/fstab.h | 1 + init/first_stage_mount.cpp | 32 ++++++++++++++++++++---------- 7 files changed, 40 insertions(+), 21 deletions(-) diff --git a/fs_mgr/fs_mgr.cpp b/fs_mgr/fs_mgr.cpp index 750ed71d7..4e8ab0bc2 100644 --- a/fs_mgr/fs_mgr.cpp +++ b/fs_mgr/fs_mgr.cpp @@ -1032,8 +1032,9 @@ int fs_mgr_mount_all(fstab* fstab, int mount_mode) { for (i = 0; i < fstab->num_entries; i++) { /* Don't mount entries that are managed by vold or not for the mount mode*/ if ((fstab->recs[i].fs_mgr_flags & (MF_VOLDMANAGED | MF_RECOVERYONLY)) || - ((mount_mode == MOUNT_MODE_LATE) && !fs_mgr_is_latemount(&fstab->recs[i])) || - ((mount_mode == MOUNT_MODE_EARLY) && fs_mgr_is_latemount(&fstab->recs[i]))) { + ((mount_mode == MOUNT_MODE_LATE) && !fs_mgr_is_latemount(&fstab->recs[i])) || + ((mount_mode == MOUNT_MODE_EARLY) && fs_mgr_is_latemount(&fstab->recs[i])) || + fs_mgr_is_first_stage_mount(&fstab->recs[i])) { continue; } diff --git a/fs_mgr/fs_mgr_fstab.cpp b/fs_mgr/fs_mgr_fstab.cpp index 31b09448d..0fde22e2c 100644 --- a/fs_mgr/fs_mgr_fstab.cpp +++ b/fs_mgr/fs_mgr_fstab.cpp @@ -57,7 +57,7 @@ struct fs_mgr_flag_values { struct flag_list { const char *name; - int flag; + unsigned int flag; }; static struct flag_list mount_flags[] = { @@ -102,6 +102,7 @@ static struct flag_list fs_mgr_flags[] = { {"formattable", MF_FORMATTABLE}, {"slotselect", MF_SLOTSELECT}, {"nofail", MF_NOFAIL}, + {"first_stage_mount", MF_FIRST_STAGE_MOUNT}, {"latemount", MF_LATEMOUNT}, {"reservedsize=", MF_RESERVEDSIZE}, {"quota", MF_QUOTA}, @@ -998,6 +999,10 @@ int fs_mgr_is_nofail(const struct fstab_rec* fstab) { return fstab->fs_mgr_flags & MF_NOFAIL; } +int fs_mgr_is_first_stage_mount(const struct fstab_rec* fstab) { + return fstab->fs_mgr_flags & MF_FIRST_STAGE_MOUNT; +} + int fs_mgr_is_latemount(const struct fstab_rec* fstab) { return fstab->fs_mgr_flags & MF_LATEMOUNT; } diff --git a/fs_mgr/fs_mgr_overlayfs.cpp b/fs_mgr/fs_mgr_overlayfs.cpp index 57e984d18..5945236cd 100644 --- a/fs_mgr/fs_mgr_overlayfs.cpp +++ b/fs_mgr/fs_mgr_overlayfs.cpp @@ -74,7 +74,7 @@ bool fs_mgr_overlayfs_mount_all(fstab*) { return false; } -bool fs_mgr_overlayfs_mount_all(const std::vector&) { +bool fs_mgr_overlayfs_mount_all(const std::vector&) { return false; } @@ -82,7 +82,7 @@ std::vector fs_mgr_overlayfs_required_devices(fstab*) { return {}; } -std::vector fs_mgr_overlayfs_required_devices(const std::vector&) { +std::vector fs_mgr_overlayfs_required_devices(const std::vector&) { return {}; } @@ -805,7 +805,7 @@ bool fs_mgr_overlayfs_mount_all(fstab* fstab) { return ret; } -bool fs_mgr_overlayfs_mount_all(const std::vector& fsrecs) { +bool fs_mgr_overlayfs_mount_all(const std::vector& fsrecs) { std::vector recs; for (const auto& rec : fsrecs) recs.push_back(*rec); fstab fstab = {static_cast(fsrecs.size()), &recs[0]}; @@ -828,8 +828,7 @@ std::vector fs_mgr_overlayfs_required_devices(fstab* fstab) { return {}; } -std::vector fs_mgr_overlayfs_required_devices( - const std::vector& fsrecs) { +std::vector fs_mgr_overlayfs_required_devices(const std::vector& fsrecs) { std::vector recs; for (const auto& rec : fsrecs) recs.push_back(*rec); fstab fstab = {static_cast(fsrecs.size()), &recs[0]}; diff --git a/fs_mgr/fs_mgr_priv.h b/fs_mgr/fs_mgr_priv.h index 711446c91..11df255f3 100644 --- a/fs_mgr/fs_mgr_priv.h +++ b/fs_mgr/fs_mgr_priv.h @@ -118,6 +118,8 @@ #define MF_LOGICAL 0x10000000 #define MF_CHECKPOINT_BLK 0x20000000 #define MF_CHECKPOINT_FS 0x40000000 +#define MF_FIRST_STAGE_MOUNT \ + 0x80000000 // clang-format on #define DM_BUF_SIZE 4096 diff --git a/fs_mgr/include/fs_mgr_overlayfs.h b/fs_mgr/include/fs_mgr_overlayfs.h index deaf4cb1c..b60f04260 100644 --- a/fs_mgr/include/fs_mgr_overlayfs.h +++ b/fs_mgr/include/fs_mgr_overlayfs.h @@ -22,10 +22,9 @@ #include bool fs_mgr_overlayfs_mount_all(fstab* fstab); -bool fs_mgr_overlayfs_mount_all(const std::vector& fstab); +bool fs_mgr_overlayfs_mount_all(const std::vector& fstab); std::vector fs_mgr_overlayfs_required_devices(fstab* fstab); -std::vector fs_mgr_overlayfs_required_devices( - const std::vector& fstab); +std::vector fs_mgr_overlayfs_required_devices(const std::vector& fstab); bool fs_mgr_overlayfs_setup(const char* backing = nullptr, const char* mount_point = nullptr, bool* change = nullptr); bool fs_mgr_overlayfs_teardown(const char* mount_point = nullptr, bool* change = nullptr); diff --git a/fs_mgr/include_fstab/fstab/fstab.h b/fs_mgr/include_fstab/fstab/fstab.h index 80bdb8780..470602828 100644 --- a/fs_mgr/include_fstab/fstab/fstab.h +++ b/fs_mgr/include_fstab/fstab/fstab.h @@ -84,6 +84,7 @@ int fs_mgr_is_notrim(const struct fstab_rec* fstab); int fs_mgr_is_formattable(const struct fstab_rec* fstab); int fs_mgr_is_slotselect(const struct fstab_rec* fstab); int fs_mgr_is_nofail(const struct fstab_rec* fstab); +int fs_mgr_is_first_stage_mount(const struct fstab_rec* fstab); int fs_mgr_is_latemount(const struct fstab_rec* fstab); int fs_mgr_is_quota(const struct fstab_rec* fstab); int fs_mgr_is_logical(const struct fstab_rec* fstab); diff --git a/init/first_stage_mount.cpp b/init/first_stage_mount.cpp index d35329ed7..432aa622c 100644 --- a/init/first_stage_mount.cpp +++ b/init/first_stage_mount.cpp @@ -84,7 +84,7 @@ class FirstStageMount { bool need_dm_verity_; - std::unique_ptr device_tree_fstab_; + std::unique_ptr fstab_; std::string lp_metadata_partition_; std::vector mount_fstab_recs_; std::set required_devices_partition_names_; @@ -132,15 +132,27 @@ static bool IsRecoveryMode() { // Class Definitions // ----------------- FirstStageMount::FirstStageMount() - : need_dm_verity_(false), device_tree_fstab_(fs_mgr_read_fstab_dt(), fs_mgr_free_fstab) { - if (device_tree_fstab_) { - // Stores device_tree_fstab_->recs[] into mount_fstab_recs_ (vector) - // for easier manipulation later, e.g., range-base for loop. - for (int i = 0; i < device_tree_fstab_->num_entries; i++) { - mount_fstab_recs_.push_back(&device_tree_fstab_->recs[i]); + : need_dm_verity_(false), fstab_(fs_mgr_read_fstab_dt(), fs_mgr_free_fstab) { + // Stores fstab_->recs[] into mount_fstab_recs_ (vector) + // for easier manipulation later, e.g., range-base for loop. + if (fstab_) { + // DT Fstab predated having a first_stage_mount fs_mgr flag, so if it exists, we use it. + for (int i = 0; i < fstab_->num_entries; i++) { + mount_fstab_recs_.push_back(&fstab_->recs[i]); } } else { - LOG(INFO) << "Failed to read fstab from device tree"; + // Fstab found in first stage ramdisk, which should be a copy of the normal fstab. + // Mounts intended for first stage are explicitly flagged as such. + fstab_.reset(fs_mgr_read_fstab_default()); + if (fstab_) { + for (int i = 0; i < fstab_->num_entries; i++) { + if (fs_mgr_is_first_stage_mount(&fstab_->recs[i])) { + mount_fstab_recs_.push_back(&fstab_->recs[i]); + } + } + } else { + LOG(INFO) << "Failed to read fstab from device tree"; + } } auto boot_devices = fs_mgr_get_boot_devices(); @@ -411,7 +423,7 @@ bool FirstStageMount::MountPartitions() { } // heads up for instantiating required device(s) for overlayfs logic - const auto devices = fs_mgr_overlayfs_required_devices(device_tree_fstab_.get()); + const auto devices = fs_mgr_overlayfs_required_devices(mount_fstab_recs_); for (auto const& device : devices) { if (android::base::StartsWith(device, "/dev/block/by-name/")) { required_devices_partition_names_.emplace(basename(device.c_str())); @@ -423,7 +435,7 @@ bool FirstStageMount::MountPartitions() { } } - fs_mgr_overlayfs_mount_all(device_tree_fstab_.get()); + fs_mgr_overlayfs_mount_all(mount_fstab_recs_); return true; }