Accept --overlay-name flag in idmap2
To support allowing for multiple <overlay> tags in one package, idmap2
must be able to generate an idmap for an individual <overlay> tag.
`idmap2 create` now accepts a --overlay-name flag that specifies which
tag to use to generate the idmap. The value of --overlay-name should be
set to the value of the android:name attribute on the <overlay> tag to
use.
If the flag is not present, idmap2 will look for an <overlay> tag with
no value for android:name.
Bug: 162841629
Test: libandroidfw_tests
Test: libidmap2_tests
Change-Id: I02316d0b88773f02c04a5d462be9825016fa496d
diff --git a/cmds/idmap2/libidmap2/ResourceUtils.cpp b/cmds/idmap2/libidmap2/ResourceUtils.cpp
index e817140..5283741 100644
--- a/cmds/idmap2/libidmap2/ResourceUtils.cpp
+++ b/cmds/idmap2/libidmap2/ResourceUtils.cpp
@@ -92,7 +92,7 @@
}
Result<OverlayManifestInfo> ExtractOverlayManifestInfo(const std::string& path,
- bool assert_overlay) {
+ const std::string& name) {
std::unique_ptr<const ZipFile> zip = ZipFile::Open(path);
if (!zip) {
return Error("failed to open %s as a zip file", path.c_str());
@@ -113,65 +113,49 @@
return Error("root element tag is not <manifest> in AndroidManifest.xml of %s", path.c_str());
}
- auto overlay_it = std::find_if(manifest_it.begin(), manifest_it.end(), [](const auto& it) {
- return it.event() == XmlParser::Event::START_TAG && it.name() == "overlay";
- });
-
- OverlayManifestInfo info{};
- if (overlay_it == manifest_it.end()) {
- if (!assert_overlay) {
- return info;
+ for (auto&& it : manifest_it) {
+ if (it.event() != XmlParser::Event::START_TAG || it.name() != "overlay") {
+ continue;
}
- return Error("<overlay> missing from AndroidManifest.xml of %s", path.c_str());
- }
- if (auto result_str = overlay_it->GetAttributeStringValue("targetPackage")) {
- info.target_package = *result_str;
- } else {
- return Error("android:targetPackage missing from <overlay> of %s: %s", path.c_str(),
- result_str.GetErrorMessage().c_str());
- }
+ OverlayManifestInfo info{};
+ if (auto result_str = it.GetAttributeStringValue("name")) {
+ if (*result_str != name) {
+ // A value for android:name was found, but either a the name does not match the requested
+ // name, or an <overlay> tag with no name was requested.
+ continue;
+ }
+ info.name = *result_str;
+ } else if (!name.empty()) {
+ // This tag does not have a value for android:name, but an <overlay> tag with a specific name
+ // has been requested.
+ continue;
+ }
- if (auto result_str = overlay_it->GetAttributeStringValue("targetName")) {
- info.target_name = *result_str;
- }
-
- if (auto result_value = overlay_it->GetAttributeValue("resourcesMap")) {
- if (IsReference((*result_value).dataType)) {
- info.resource_mapping = (*result_value).data;
+ if (auto result_str = it.GetAttributeStringValue("targetPackage")) {
+ info.target_package = *result_str;
} else {
- return Error("android:resourcesMap is not a reference in AndroidManifest.xml of %s",
- path.c_str());
+ return Error("android:targetPackage missing from <overlay> of %s: %s", path.c_str(),
+ result_str.GetErrorMessage().c_str());
}
- }
- if (auto result_value = overlay_it->GetAttributeValue("isStatic")) {
- if ((*result_value).dataType >= Res_value::TYPE_FIRST_INT &&
- (*result_value).dataType <= Res_value::TYPE_LAST_INT) {
- info.is_static = (*result_value).data != 0U;
- } else {
- return Error("android:isStatic is not a boolean in AndroidManifest.xml of %s", path.c_str());
+ if (auto result_str = it.GetAttributeStringValue("targetName")) {
+ info.target_name = *result_str;
}
- }
- if (auto result_value = overlay_it->GetAttributeValue("priority")) {
- if ((*result_value).dataType >= Res_value::TYPE_FIRST_INT &&
- (*result_value).dataType <= Res_value::TYPE_LAST_INT) {
- info.priority = (*result_value).data;
- } else {
- return Error("android:priority is not an integer in AndroidManifest.xml of %s", path.c_str());
+ if (auto result_value = it.GetAttributeValue("resourcesMap")) {
+ if (IsReference((*result_value).dataType)) {
+ info.resource_mapping = (*result_value).data;
+ } else {
+ return Error("android:resourcesMap is not a reference in AndroidManifest.xml of %s",
+ path.c_str());
+ }
}
+ return info;
}
- if (auto result_str = overlay_it->GetAttributeStringValue("requiredSystemPropertyName")) {
- info.requiredSystemPropertyName = *result_str;
- }
-
- if (auto result_str = overlay_it->GetAttributeStringValue("requiredSystemPropertyValue")) {
- info.requiredSystemPropertyValue = *result_str;
- }
-
- return info;
+ return Error("<overlay> with android:name \"%s\" missing from AndroidManifest.xml of %s",
+ name.c_str(), path.c_str());
}
} // namespace android::idmap2::utils