diff --git a/fs_mgr/fs_mgr_overlayfs.cpp b/fs_mgr/fs_mgr_overlayfs.cpp index b508b5648..df1e32688 100644 --- a/fs_mgr/fs_mgr_overlayfs.cpp +++ b/fs_mgr/fs_mgr_overlayfs.cpp @@ -565,26 +565,6 @@ std::vector fs_mgr_candidate_list(Fstab* fstab, const char* mount_p if (!duplicate_or_more_specific) mounts.emplace_back(new_mount_point); } - // if not itemized /system or /, system as root, fake one up? - - // do we want or need to? - if (mount_point && ("/system"s != mount_point)) return mounts; - if (std::find(mounts.begin(), mounts.end(), "/system") != mounts.end()) return mounts; - - // fs_mgr_overlayfs_verity_enabled_list says not to? - if (std::find(verity.begin(), verity.end(), "system") != verity.end()) return mounts; - - // confirm that fstab is missing system - if (GetEntryForMountPoint(fstab, "/") != nullptr || - GetEntryForMountPoint(fstab, "/system") != nullptr) { - return mounts; - } - - // We have a stunted fstab (w/o system or / ) passed in by the caller, - // verity claims are assumed accurate because they are collected internally - // from fs_mgr_fstab_default() from within fs_mgr_update_verity_state(), - // Can (re)evaluate /system with impunity since we know it is ever-present. - mounts.emplace_back("/system"); return mounts; } diff --git a/init/first_stage_mount.cpp b/init/first_stage_mount.cpp index 7d5bf5754..1b077bc6c 100644 --- a/init/first_stage_mount.cpp +++ b/init/first_stage_mount.cpp @@ -157,6 +157,37 @@ static Fstab ReadFirstStageFstab() { return fstab; } +static bool GetRootEntry(FstabEntry* root_entry) { + Fstab proc_mounts; + if (!ReadFstabFromFile("/proc/mounts", &proc_mounts)) { + LOG(ERROR) << "Could not read /proc/mounts and /system not in fstab, /system will not be " + "available for overlayfs"; + return false; + } + + auto entry = std::find_if(proc_mounts.begin(), proc_mounts.end(), [](const auto& entry) { + return entry.mount_point == "/" && entry.fs_type != "rootfs"; + }); + + if (entry == proc_mounts.end()) { + LOG(ERROR) << "Could not get mount point for '/' in /proc/mounts, /system will not be " + "available for overlayfs"; + return false; + } + + *root_entry = std::move(*entry); + + // We don't know if we're avb or not, so we query device mapper as if we are avb. If we get a + // success, then mark as avb, otherwise default to verify. + auto& dm = android::dm::DeviceMapper::Instance(); + if (dm.GetState("vroot") != android::dm::DmDeviceState::INVALID) { + root_entry->fs_mgr_flags.avb = true; + } else { + root_entry->fs_mgr_flags.verify = true; + } + return true; +} + // Class Definitions // ----------------- FirstStageMount::FirstStageMount(Fstab fstab) @@ -443,7 +474,7 @@ bool FirstStageMount::TrySwitchSystemAsRoot() { if (system_partition == fstab_.end()) return true; - if (MountPartition(system_partition, true /* erase_used_fstab_entry */)) { + if (MountPartition(system_partition, false)) { SwitchRoot("/system"); } else { PLOG(ERROR) << "Failed to mount /system"; @@ -487,6 +518,12 @@ bool FirstStageMount::MountPartitions() { if (!TrySkipMountingPartitions()) return false; for (auto current = fstab_.begin(); current != fstab_.end();) { + // We've already mounted /system above. + if (current->mount_point == "/system") { + ++current; + continue; + } + Fstab::iterator end; if (!MountPartition(current, false, &end)) { if (current->fs_mgr_flags.no_fail) { @@ -503,6 +540,15 @@ bool FirstStageMount::MountPartitions() { current = end; } + // If we don't see /system or / in the fstab, then we need to create an root entry for + // overlayfs. + if (!GetEntryForMountPoint(&fstab_, "/system") && !GetEntryForMountPoint(&fstab_, "/")) { + FstabEntry root_entry; + if (GetRootEntry(&root_entry)) { + fstab_.emplace_back(std::move(root_entry)); + } + } + // heads up for instantiating required device(s) for overlayfs logic const auto devices = fs_mgr_overlayfs_required_devices(&fstab_); for (auto const& device : devices) {