From 6bcabc03d3f16bf267963758552bfcb648107b6a Mon Sep 17 00:00:00 2001 From: Yi-Yo Chiang Date: Fri, 18 Feb 2022 22:54:50 +0800 Subject: [PATCH] TransformFstabForDsu: Insert synthesised entry at end of mount group The intention of inserting this synthesised mount entry is for the FirstStageMount() procedure to eventually fallback to this entry if all previous mount lines failed. In order for FirstStageMount() to retry mount, the mount lines have to be grouped together. This change ensures that would happen and add test. Bug: 220074274 Test: atest CtsFsMgrTestCases Change-Id: Id042a6a6738d27c06a397ef7f4e0977907371c05 --- fs_mgr/fs_mgr_fstab.cpp | 7 +++- fs_mgr/tests/fs_mgr_test.cpp | 73 ++++++++++++++++++++++++++++++++++++ 2 files changed, 79 insertions(+), 1 deletion(-) diff --git a/fs_mgr/fs_mgr_fstab.cpp b/fs_mgr/fs_mgr_fstab.cpp index 0ca1946ad..143e980e4 100644 --- a/fs_mgr/fs_mgr_fstab.cpp +++ b/fs_mgr/fs_mgr_fstab.cpp @@ -657,7 +657,12 @@ void TransformFstabForDsu(Fstab* fstab, const std::string& dsu_slot, if (partition_ext4 == fstab->end()) { auto new_entry = *GetEntryForMountPoint(fstab, mount_point); new_entry.fs_type = "ext4"; - fstab->emplace_back(new_entry); + auto it = std::find_if(fstab->rbegin(), fstab->rend(), + [&mount_point](const auto& entry) { + return entry.mount_point == mount_point; + }); + auto end_of_mount_point_group = fstab->begin() + std::distance(it, fstab->rend()); + fstab->insert(end_of_mount_point_group, new_entry); } } } diff --git a/fs_mgr/tests/fs_mgr_test.cpp b/fs_mgr/tests/fs_mgr_test.cpp index eccb902c0..1dbee75ae 100644 --- a/fs_mgr/tests/fs_mgr_test.cpp +++ b/fs_mgr/tests/fs_mgr_test.cpp @@ -1104,3 +1104,76 @@ source none6 swap defaults readahead_size_kb=0 EXPECT_TRUE(CompareFlags(flags, entry->fs_mgr_flags)); EXPECT_EQ(0, entry->readahead_size_kb); } + +TEST(fs_mgr, TransformFstabForDsu) { + TemporaryFile tf; + ASSERT_TRUE(tf.fd != -1); + std::string fstab_contents = R"fs( +system /system erofs ro wait,logical,first_stage_mount +system /system ext4 ro wait,logical,first_stage_mount +vendor /vendor ext4 ro wait,logical,first_stage_mount +data /data f2fs noatime wait +)fs"; + + ASSERT_TRUE(android::base::WriteStringToFile(fstab_contents, tf.path)); + + Fstab fstab; + EXPECT_TRUE(ReadFstabFromFile(tf.path, &fstab)); + TransformFstabForDsu(&fstab, "dsu", {"system_gsi", "userdata_gsi"}); + ASSERT_EQ(4U, fstab.size()); + + auto entry = fstab.begin(); + + EXPECT_EQ("/system", entry->mount_point); + EXPECT_EQ("system_gsi", entry->blk_device); + entry++; + + EXPECT_EQ("/system", entry->mount_point); + EXPECT_EQ("system_gsi", entry->blk_device); + entry++; + + EXPECT_EQ("/vendor", entry->mount_point); + EXPECT_EQ("vendor", entry->blk_device); + entry++; + + EXPECT_EQ("/data", entry->mount_point); + EXPECT_EQ("userdata_gsi", entry->blk_device); + entry++; +} + +TEST(fs_mgr, TransformFstabForDsu_synthesisExt4Entry) { + TemporaryFile tf; + ASSERT_TRUE(tf.fd != -1); + std::string fstab_contents = R"fs( +system /system erofs ro wait,logical,first_stage_mount +vendor /vendor ext4 ro wait,logical,first_stage_mount +data /data f2fs noatime wait +)fs"; + + ASSERT_TRUE(android::base::WriteStringToFile(fstab_contents, tf.path)); + + Fstab fstab; + EXPECT_TRUE(ReadFstabFromFile(tf.path, &fstab)); + TransformFstabForDsu(&fstab, "dsu", {"system_gsi", "userdata_gsi"}); + ASSERT_EQ(4U, fstab.size()); + + auto entry = fstab.begin(); + + EXPECT_EQ("/system", entry->mount_point); + EXPECT_EQ("system_gsi", entry->blk_device); + EXPECT_EQ("erofs", entry->fs_type); + entry++; + + EXPECT_EQ("/system", entry->mount_point); + EXPECT_EQ("system_gsi", entry->blk_device); + EXPECT_EQ("ext4", entry->fs_type); + entry++; + + EXPECT_EQ("/vendor", entry->mount_point); + EXPECT_EQ("vendor", entry->blk_device); + entry++; + + EXPECT_EQ("/data", entry->mount_point); + EXPECT_EQ("userdata_gsi", entry->blk_device); + entry++; +}