From b8c23259b15b85feec119e4e770e232c5cc74fcd Mon Sep 17 00:00:00 2001 From: Yi-Yo Chiang Date: Tue, 25 Jul 2023 22:08:55 +0800 Subject: [PATCH] init: Unify duplicated get_android_dt_dir with libfs_mgr init and libfs_mgr both defines get_android_dt_dir() with subtle differences. Merge the two implementations into libfs_mgr to reduce code duplication (in terms of source code and code gen) Note: init's implementation checks the kernel cmdline first and then the kernel bootconfig, while libfs_mgr's order is the opposite. Realistically I don't think this order matter much though. If any, we should prioritize bootconfig over kernel cmdline most of the time. Bug: 293695109 Test: Presubmit Merged-In: Ic8d2c965c62f9e873ccdaf77d67c7708f25a7b56 Change-Id: Ic8d2c965c62f9e873ccdaf77d67c7708f25a7b56 --- fs_mgr/libfstab/boot_config.cpp | 29 +++++++++++++++++++- fs_mgr/libfstab/fstab.cpp | 29 ++++---------------- fs_mgr/libfstab/fstab_priv.h | 1 - fs_mgr/libfstab/include/fstab/fstab.h | 4 +++ init/Android.bp | 1 + init/property_service.cpp | 6 +++-- init/util.cpp | 39 +++++---------------------- init/util.h | 3 --- 8 files changed, 49 insertions(+), 63 deletions(-) diff --git a/fs_mgr/libfstab/boot_config.cpp b/fs_mgr/libfstab/boot_config.cpp index 8fb28c607..fee40158b 100644 --- a/fs_mgr/libfstab/boot_config.cpp +++ b/fs_mgr/libfstab/boot_config.cpp @@ -27,6 +27,33 @@ #include "fstab_priv.h" #include "logging_macros.h" +namespace android { +namespace fs_mgr { + +const std::string& GetAndroidDtDir() { + // Set once and saves time for subsequent calls to this function + static const std::string kAndroidDtDir = [] { + std::string android_dt_dir; + if ((fs_mgr_get_boot_config_from_bootconfig_source("android_dt_dir", &android_dt_dir) || + fs_mgr_get_boot_config_from_kernel_cmdline("android_dt_dir", &android_dt_dir)) && + !android_dt_dir.empty()) { + // Ensure the returned path ends with a / + if (android_dt_dir.back() != '/') { + android_dt_dir.push_back('/'); + } + } else { + // Fall back to the standard procfs-based path + android_dt_dir = "/proc/device-tree/firmware/android/"; + } + LINFO << "Using Android DT directory " << android_dt_dir; + return android_dt_dir; + }(); + return kAndroidDtDir; +} + +} // namespace fs_mgr +} // namespace android + std::vector> fs_mgr_parse_cmdline(const std::string& cmdline) { static constexpr char quote = '"'; @@ -145,7 +172,7 @@ bool fs_mgr_get_boot_config(const std::string& key, std::string* out_val) { // firstly, check the device tree if (is_dt_compatible()) { - std::string file_name = get_android_dt_dir() + "/" + key; + std::string file_name = android::fs_mgr::GetAndroidDtDir() + key; if (android::base::ReadFileToString(file_name, out_val)) { if (!out_val->empty()) { out_val->pop_back(); // Trims the trailing '\0' out. diff --git a/fs_mgr/libfstab/fstab.cpp b/fs_mgr/libfstab/fstab.cpp index 5b5c3d26c..86ba03148 100644 --- a/fs_mgr/libfstab/fstab.cpp +++ b/fs_mgr/libfstab/fstab.cpp @@ -51,7 +51,6 @@ namespace android { namespace fs_mgr { namespace { -constexpr char kDefaultAndroidDtDir[] = "/proc/device-tree/firmware/android"; constexpr char kProcMountsPath[] = "/proc/mounts"; struct FlagList { @@ -337,25 +336,14 @@ bool ParseFsMgrFlags(const std::string& flags, FstabEntry* entry) { return true; } -std::string InitAndroidDtDir() { - std::string android_dt_dir; - // The platform may specify a custom Android DT path in kernel cmdline - if (!fs_mgr_get_boot_config_from_bootconfig_source("android_dt_dir", &android_dt_dir) && - !fs_mgr_get_boot_config_from_kernel_cmdline("android_dt_dir", &android_dt_dir)) { - // Fall back to the standard procfs-based path - android_dt_dir = kDefaultAndroidDtDir; - } - return android_dt_dir; -} - bool IsDtFstabCompatible() { std::string dt_value; - std::string file_name = get_android_dt_dir() + "/fstab/compatible"; + std::string file_name = GetAndroidDtDir() + "fstab/compatible"; if (ReadDtFile(file_name, &dt_value) && dt_value == "android,fstab") { // If there's no status property or its set to "ok" or "okay", then we use the DT fstab. std::string status_value; - std::string status_file_name = get_android_dt_dir() + "/fstab/status"; + std::string status_file_name = GetAndroidDtDir() + "fstab/status"; return !ReadDtFile(status_file_name, &status_value) || status_value == "ok" || status_value == "okay"; } @@ -368,7 +356,7 @@ std::string ReadFstabFromDt() { return {}; } - std::string fstabdir_name = get_android_dt_dir() + "/fstab"; + std::string fstabdir_name = GetAndroidDtDir() + "fstab"; std::unique_ptr fstabdir(opendir(fstabdir_name.c_str()), closedir); if (!fstabdir) return {}; @@ -876,7 +864,7 @@ const FstabEntry* GetEntryForMountPoint(const Fstab* fstab, const std::string& p std::set GetBootDevices() { // First check bootconfig, then kernel commandline, then the device tree - std::string dt_file_name = get_android_dt_dir() + "/boot_devices"; + std::string dt_file_name = GetAndroidDtDir() + "boot_devices"; std::string value; if (fs_mgr_get_boot_config_from_bootconfig_source("boot_devices", &value) || fs_mgr_get_boot_config_from_bootconfig_source("boot_device", &value)) { @@ -948,15 +936,8 @@ bool InRecovery() { } // namespace fs_mgr } // namespace android -// FIXME: The same logic is duplicated in system/core/init/ -const std::string& get_android_dt_dir() { - // Set once and saves time for subsequent calls to this function - static const std::string kAndroidDtDir = android::fs_mgr::InitAndroidDtDir(); - return kAndroidDtDir; -} - bool is_dt_compatible() { - std::string file_name = get_android_dt_dir() + "/compatible"; + std::string file_name = android::fs_mgr::GetAndroidDtDir() + "compatible"; std::string dt_value; if (android::fs_mgr::ReadDtFile(file_name, &dt_value)) { if (dt_value == "android,firmware") { diff --git a/fs_mgr/libfstab/fstab_priv.h b/fs_mgr/libfstab/fstab_priv.h index fb12b9fb1..5d226f879 100644 --- a/fs_mgr/libfstab/fstab_priv.h +++ b/fs_mgr/libfstab/fstab_priv.h @@ -36,7 +36,6 @@ bool fs_mgr_get_boot_config_from_bootconfig(const std::string& bootconfig, const bool fs_mgr_get_boot_config_from_bootconfig_source(const std::string& key, std::string* out_val); bool fs_mgr_update_for_slotselect(android::fs_mgr::Fstab* fstab); -const std::string& get_android_dt_dir(); bool is_dt_compatible(); namespace android { diff --git a/fs_mgr/libfstab/include/fstab/fstab.h b/fs_mgr/libfstab/include/fstab/fstab.h index e0683ac28..0a45fe87a 100644 --- a/fs_mgr/libfstab/include/fstab/fstab.h +++ b/fs_mgr/libfstab/include/fstab/fstab.h @@ -124,5 +124,9 @@ std::set GetBootDevices(); // expected name. std::string GetVerityDeviceName(const FstabEntry& entry); +// Returns the Android Device Tree directory as specified in the kernel bootconfig or cmdline. +// If the platform does not configure a custom DT path, returns the standard one (based in procfs). +const std::string& GetAndroidDtDir(); + } // namespace fs_mgr } // namespace android diff --git a/init/Android.bp b/init/Android.bp index ee34215d7..d4852d648 100644 --- a/init/Android.bp +++ b/init/Android.bp @@ -539,6 +539,7 @@ cc_defaults { "libprotobuf-cpp-lite", ], static_libs: [ + "libfs_mgr", "libhidl-gen-utils", ], } diff --git a/init/property_service.cpp b/init/property_service.cpp index 8da69822c..0e82022a0 100644 --- a/init/property_service.cpp +++ b/init/property_service.cpp @@ -57,6 +57,7 @@ #include #include #include +#include #include #include #include @@ -1317,7 +1318,8 @@ static void ProcessKernelDt() { return; } - std::unique_ptr dir(opendir(get_android_dt_dir().c_str()), closedir); + std::unique_ptr dir(opendir(android::fs_mgr::GetAndroidDtDir().c_str()), + closedir); if (!dir) return; std::string dt_file; @@ -1328,7 +1330,7 @@ static void ProcessKernelDt() { continue; } - std::string file_name = get_android_dt_dir() + dp->d_name; + std::string file_name = android::fs_mgr::GetAndroidDtDir() + dp->d_name; android::base::ReadFileToString(file_name, &dt_file); std::replace(dt_file.begin(), dt_file.end(), ',', '.'); diff --git a/init/util.cpp b/init/util.cpp index d0478e80d..61d59a480 100644 --- a/init/util.cpp +++ b/init/util.cpp @@ -42,6 +42,10 @@ #include #include +#if defined(__ANDROID__) +#include +#endif + #ifdef INIT_FULL_SOURCES #include #include @@ -60,8 +64,6 @@ using namespace std::literals::string_literals; namespace android { namespace init { -const std::string kDefaultAndroidDtDir("/proc/device-tree/firmware/android/"); - const std::string kDataDirPrefix("/data/"); void (*trigger_shutdown)(const std::string& command) = nullptr; @@ -375,45 +377,18 @@ Result ExpandProps(const std::string& src) { return dst; } -static std::string init_android_dt_dir() { - // Use the standard procfs-based path by default - std::string android_dt_dir = kDefaultAndroidDtDir; - // The platform may specify a custom Android DT path in kernel cmdline - ImportKernelCmdline([&](const std::string& key, const std::string& value) { - if (key == "androidboot.android_dt_dir") { - android_dt_dir = value; - } - }); - // ..Or bootconfig - if (android_dt_dir == kDefaultAndroidDtDir) { - ImportBootconfig([&](const std::string& key, const std::string& value) { - if (key == "androidboot.android_dt_dir") { - android_dt_dir = value; - } - }); - } - - LOG(INFO) << "Using Android DT directory " << android_dt_dir; - return android_dt_dir; -} - -// FIXME: The same logic is duplicated in system/core/fs_mgr/ -const std::string& get_android_dt_dir() { - // Set once and saves time for subsequent calls to this function - static const std::string kAndroidDtDir = init_android_dt_dir(); - return kAndroidDtDir; -} - // Reads the content of device tree file under the platform's Android DT directory. // Returns true if the read is success, false otherwise. bool read_android_dt_file(const std::string& sub_path, std::string* dt_content) { - const std::string file_name = get_android_dt_dir() + sub_path; +#if defined(__ANDROID__) + const std::string file_name = android::fs_mgr::GetAndroidDtDir() + sub_path; if (android::base::ReadFileToString(file_name, dt_content)) { if (!dt_content->empty()) { dt_content->pop_back(); // Trims the trailing '\0' out. return true; } } +#endif return false; } diff --git a/init/util.h b/init/util.h index 3f0a4e023..1c00a3efc 100644 --- a/init/util.h +++ b/init/util.h @@ -60,9 +60,6 @@ bool make_dir(const std::string& path, mode_t mode); bool is_dir(const char* pathname); Result ExpandProps(const std::string& src); -// Returns the platform's Android DT directory as specified in the kernel cmdline. -// If the platform does not configure a custom DT path, returns the standard one (based in procfs). -const std::string& get_android_dt_dir(); // Reads or compares the content of device tree file under the platform's Android DT directory. bool read_android_dt_file(const std::string& sub_path, std::string* dt_content); bool is_android_dt_value_expected(const std::string& sub_path, const std::string& expected_content);