System_Property_Get: Allow specifying multiple prop file paths

Some OEMs include prop files in custom locations. Add these to
a list and parse when setting properties.

Use the flag TW_SYSTEM_BUILD_PROP_ADDITIONAL_PATHS followed
by a semi-colon-separated list of paths (relative to /system)
where the additional prop files can be found.

The standard build.prop file does not need to be specified and
will always be parsed.

Example:
TW_SYSTEM_BUILD_PROP_ADDITIONAL_PATHS := etc/buildinfo/oem_build.prop;etc/prop.default

Change-Id: Ie0e25c7d2575d928310ff1b4fc1aef44a83784ca
diff --git a/Android.mk b/Android.mk
index cdbfe2a..30efc38 100755
--- a/Android.mk
+++ b/Android.mk
@@ -203,6 +203,10 @@
     TWRP_REQUIRED_MODULES += libhardware
 endif
 
+ifneq ($(TW_SYSTEM_BUILD_PROP_ADDITIONAL_PATHS),)
+    LOCAL_CFLAGS += -DTW_SYSTEM_BUILD_PROP_ADDITIONAL_PATHS='"$(TW_SYSTEM_BUILD_PROP_ADDITIONAL_PATHS)"'
+endif
+
 LOCAL_MODULE_PATH := $(TARGET_RECOVERY_ROOT_OUT)/sbin
 
 #ifeq ($(TARGET_RECOVERY_UI_LIB),)
diff --git a/twrp-functions.cpp b/twrp-functions.cpp
index 463f77c..4ab6299 100755
--- a/twrp-functions.cpp
+++ b/twrp-functions.cpp
@@ -899,20 +899,20 @@
 }
 
 string TWFunc::System_Property_Get(string Prop_Name) {
-	return System_Property_Get(Prop_Name, PartitionManager, PartitionManager.Get_Android_Root_Path());
+	return System_Property_Get(Prop_Name, PartitionManager, PartitionManager.Get_Android_Root_Path(), "build.prop");
 }
 
-string TWFunc::System_Property_Get(string Prop_Name, TWPartitionManager &PartitionManager, string Mount_Point) {
+string TWFunc::System_Property_Get(string Prop_Name, TWPartitionManager &PartitionManager, string Mount_Point, string prop_file_name) {
 	bool mount_state = PartitionManager.Is_Mounted_By_Path(Mount_Point);
 	std::vector<string> buildprop;
 	string propvalue;
 	if (!PartitionManager.Mount_By_Path(Mount_Point, true))
 		return propvalue;
-	string prop_file = Mount_Point + "/build.prop";
+	string prop_file = Mount_Point + "/" + prop_file_name;
 	if (!TWFunc::Path_Exists(prop_file))
-		prop_file = Mount_Point + "/system/build.prop"; // for devices with system as a root file system (e.g. Pixel)
+		prop_file = Mount_Point + "/system/" + prop_file_name; // for devices with system as a root file system (e.g. Pixel)
 	if (TWFunc::read_file(prop_file, buildprop) != 0) {
-		LOGINFO("Unable to open build.prop for getting '%s'.\n", Prop_Name.c_str());
+		LOGINFO("Unable to open %s for getting '%s'.\n", prop_file_name.c_str(), Prop_Name.c_str());
 		DataManager::SetValue(TW_BACKUP_NAME, Get_Current_Date());
 		if (!mount_state)
 			PartitionManager.UnMount_By_Path(Mount_Point, false);
diff --git a/twrp-functions.hpp b/twrp-functions.hpp
index e61038e..b04447b 100755
--- a/twrp-functions.hpp
+++ b/twrp-functions.hpp
@@ -101,7 +101,7 @@
 	static int write_to_file(const string& fn, const string& line);             //write to file
 	static bool Try_Decrypting_Backup(string Restore_Path, string Password); // true for success, false for failed to decrypt
 	static string System_Property_Get(string Prop_Name);                // Returns value of Prop_Name from reading /system/build.prop
-	static string System_Property_Get(string Prop_Name, TWPartitionManager &PartitionManager, string Mount_Point);                // Returns value of Prop_Name from reading /system/build.prop
+	static string System_Property_Get(string Prop_Name, TWPartitionManager &PartitionManager, string Mount_Point, string prop_file_name);     // Returns value of Prop_Name from reading provided prop file
 	static string Get_Current_Date(void);                               // Returns the current date in ccyy-m-dd--hh-nn-ss format
 	static void Auto_Generate_Backup_Name();                            // Populates TW_BACKUP_NAME with a backup name based on current date and ro.build.display.id from /system/build.prop
 	static void Fixup_Time_On_Boot(const string& time_paths = ""); // Fixes time on devices which need it (time_paths is a space separated list of paths to check for ats_* files)
diff --git a/twrp.cpp b/twrp.cpp
index 96d9958..ce3b99a 100755
--- a/twrp.cpp
+++ b/twrp.cpp
@@ -161,6 +161,11 @@
 #if defined(TW_INCLUDE_LIBRESETPROP) && defined(TW_OVERRIDE_SYSTEM_PROPS)
 			stringstream override_props(EXPAND(TW_OVERRIDE_SYSTEM_PROPS));
 			string current_prop;
+			std::vector<std::string> build_prop_list = {"build.prop"};
+#ifdef TW_SYSTEM_BUILD_PROP_ADDITIONAL_PATHS
+			std::vector<std::string> additional_build_prop_list = TWFunc::Split_String(TW_SYSTEM_BUILD_PROP_ADDITIONAL_PATHS, ";");
+			build_prop_list.insert(build_prop_list.end(), additional_build_prop_list.begin(), additional_build_prop_list.end());
+#endif
 			while (getline(override_props, current_prop, ';')) {
 				string other_prop;
 				if (current_prop.find("=") != string::npos) {
@@ -171,15 +176,19 @@
 				}
 				other_prop = android::base::Trim(other_prop);
 				current_prop = android::base::Trim(current_prop);
-				string sys_val = TWFunc::System_Property_Get(other_prop, SarPartitionManager, "/s");
-				if (!sys_val.empty()) {
-					LOGINFO("Overriding %s with value: \"%s\" from system property %s\n", current_prop.c_str(), sys_val.c_str(), other_prop.c_str());
-					int error = TWFunc::Property_Override(current_prop, sys_val);
-					if (error) {
-						LOGERR("Failed overriding property %s, error_code: %d\n", current_prop.c_str(), error);
+
+				for (auto&& prop_file:build_prop_list) {
+					string sys_val = TWFunc::System_Property_Get(other_prop, SarPartitionManager, "/s", prop_file);
+					if (!sys_val.empty()) {
+						LOGINFO("Overriding %s with value: \"%s\" from system property %s from %s\n", current_prop.c_str(), sys_val.c_str(), other_prop.c_str(), prop_file.c_str());
+						int error = TWFunc::Property_Override(current_prop, sys_val);
+						if (error) {
+							LOGERR("Failed overriding property %s, error_code: %d\n", current_prop.c_str(), error);
+						}
+						break;
+					} else {
+						LOGINFO("Not overriding %s with empty value from system property %s from %s\n", current_prop.c_str(), other_prop.c_str(), prop_file.c_str());
 					}
-				} else {
-					LOGINFO("Not overriding %s with empty value from system property %s\n", current_prop.c_str(), other_prop.c_str());
 				}
 			}
 #endif