From 97f0f1e4ea9232e86ee839d5d9e5e6d029f3700c Mon Sep 17 00:00:00 2001 From: Yurii Zubrytskyi Date: Tue, 2 Jul 2024 15:31:01 -0700 Subject: [aapt2] Improve dump chunks for string pools, fix diff - `dump chunks` command now prints extra header data for the string pool, and outputs all style information for styled strings. - `diff` command used to only correctly compare the first span in the StyledString data type, making them appear different if there was a string with more than one span Flag: EXEMPT bugfix Test: atest aapt2_tests Change-Id: I377718c03d6a464cb4db22399b0f067e6a6e04d6 --- libs/androidfw/StringPool.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'libs/androidfw/StringPool.cpp') diff --git a/libs/androidfw/StringPool.cpp b/libs/androidfw/StringPool.cpp index 1cb8df311c89..ad445c042e63 100644 --- a/libs/androidfw/StringPool.cpp +++ b/libs/androidfw/StringPool.cpp @@ -132,7 +132,7 @@ bool StringPool::StyleRef::operator==(const StyleRef& rhs) const { auto rhs_iter = rhs.entry_->spans.begin(); for (const Span& span : entry_->spans) { - const Span& rhs_span = *rhs_iter; + const Span& rhs_span = *rhs_iter++; if (span.first_char != rhs_span.first_char || span.last_char != rhs_span.last_char || span.name != rhs_span.name) { return false; -- cgit v1.2.3-59-g8ed1b From 1d6d8ac9feb221f47692250647269f3753bdee60 Mon Sep 17 00:00:00 2001 From: Yurii Zubrytskyi Date: Wed, 3 Jul 2024 16:10:17 -0700 Subject: [res] Simplify XmlPullParser::FindAttribute() and StringPool::Sort 1. FindAttribute used to do lots of work that C++17 does automatically 2. Use function_ref for a more efficient callback passing Test: aapt2_tests Flag: EXEMPT minor refactor Change-Id: I4f172cca16c05422992b107e347ed01479fff898 --- libs/androidfw/StringPool.cpp | 26 ++++++++++++------------- libs/androidfw/include/androidfw/StringPool.h | 5 +++-- tools/aapt2/xml/XmlPullParser.cpp | 19 ++++++++++++++++-- tools/aapt2/xml/XmlPullParser.h | 28 +-------------------------- 4 files changed, 33 insertions(+), 45 deletions(-) (limited to 'libs/androidfw/StringPool.cpp') diff --git a/libs/androidfw/StringPool.cpp b/libs/androidfw/StringPool.cpp index ad445c042e63..629f14683b19 100644 --- a/libs/androidfw/StringPool.cpp +++ b/libs/androidfw/StringPool.cpp @@ -297,24 +297,22 @@ void StringPool::Prune() { template static void SortEntries( std::vector>& entries, - const std::function& cmp) { + base::function_ref cmp) { using UEntry = std::unique_ptr; + std::sort(entries.begin(), entries.end(), [cmp](const UEntry& a, const UEntry& b) -> bool { + int r = cmp(a->context, b->context); + if (r == 0) { + r = a->value.compare(b->value); + } + return r < 0; + }); +} - if (cmp != nullptr) { - std::sort(entries.begin(), entries.end(), [&cmp](const UEntry& a, const UEntry& b) -> bool { - int r = cmp(a->context, b->context); - if (r == 0) { - r = a->value.compare(b->value); - } - return r < 0; - }); - } else { - std::sort(entries.begin(), entries.end(), - [](const UEntry& a, const UEntry& b) -> bool { return a->value < b->value; }); - } +void StringPool::Sort() { + Sort([](auto&&, auto&&) { return 0; }); } -void StringPool::Sort(const std::function& cmp) { +void StringPool::Sort(base::function_ref cmp) { SortEntries(styles_, cmp); SortEntries(strings_, cmp); ReAssignIndices(); diff --git a/libs/androidfw/include/androidfw/StringPool.h b/libs/androidfw/include/androidfw/StringPool.h index 0190ab57bf23..9b2c72a29f48 100644 --- a/libs/androidfw/include/androidfw/StringPool.h +++ b/libs/androidfw/include/androidfw/StringPool.h @@ -17,7 +17,6 @@ #ifndef _ANDROID_STRING_POOL_H #define _ANDROID_STRING_POOL_H -#include #include #include #include @@ -25,6 +24,7 @@ #include "BigBuffer.h" #include "IDiagnostics.h" +#include "android-base/function_ref.h" #include "android-base/macros.h" #include "androidfw/ConfigDescription.h" #include "androidfw/StringPiece.h" @@ -205,7 +205,8 @@ class StringPool { // Sorts the strings according to their Context using some comparison function. // Equal Contexts are further sorted by string value, lexicographically. // If no comparison function is provided, values are only sorted lexicographically. - void Sort(const std::function& cmp = nullptr); + void Sort(); + void Sort(base::function_ref cmp); // Removes any strings that have no references. void Prune(); diff --git a/tools/aapt2/xml/XmlPullParser.cpp b/tools/aapt2/xml/XmlPullParser.cpp index 203832d2dbe8..8abc26d67c1f 100644 --- a/tools/aapt2/xml/XmlPullParser.cpp +++ b/tools/aapt2/xml/XmlPullParser.cpp @@ -14,11 +14,13 @@ * limitations under the License. */ -#include +#include "xml/XmlPullParser.h" + +#include #include +#include #include "util/Util.h" -#include "xml/XmlPullParser.h" #include "xml/XmlUtil.h" using ::android::InputStream; @@ -325,5 +327,18 @@ std::optional FindNonEmptyAttribute(const XmlPullParser* parser, St return {}; } +XmlPullParser::const_iterator XmlPullParser::FindAttribute(android::StringPiece namespace_uri, + android::StringPiece name) const { + const auto end_iter = end_attributes(); + const auto iter = std::lower_bound(begin_attributes(), end_iter, std::tuple(namespace_uri, name), + [](const Attribute& attr, const auto& rhs) { + return std::tie(attr.namespace_uri, attr.name) < rhs; + }); + if (iter != end_iter && namespace_uri == iter->namespace_uri && name == iter->name) { + return iter; + } + return end_iter; +} + } // namespace xml } // namespace aapt diff --git a/tools/aapt2/xml/XmlPullParser.h b/tools/aapt2/xml/XmlPullParser.h index 655e6dc93e75..64274d032c61 100644 --- a/tools/aapt2/xml/XmlPullParser.h +++ b/tools/aapt2/xml/XmlPullParser.h @@ -19,8 +19,7 @@ #include -#include -#include +#include #include #include #include @@ -302,31 +301,6 @@ inline bool XmlPullParser::Attribute::operator!=(const Attribute& rhs) const { return compare(rhs) != 0; } -inline XmlPullParser::const_iterator XmlPullParser::FindAttribute( - android::StringPiece namespace_uri, android::StringPiece name) const { - const auto end_iter = end_attributes(); - const auto iter = std::lower_bound( - begin_attributes(), end_iter, - std::pair(namespace_uri, name), - [](const Attribute& attr, - const std::pair& rhs) -> bool { - int cmp = attr.namespace_uri.compare( - 0, attr.namespace_uri.size(), rhs.first.data(), rhs.first.size()); - if (cmp < 0) return true; - if (cmp > 0) return false; - cmp = attr.name.compare(0, attr.name.size(), rhs.second.data(), - rhs.second.size()); - if (cmp < 0) return true; - return false; - }); - - if (iter != end_iter && namespace_uri == iter->namespace_uri && - name == iter->name) { - return iter; - } - return end_iter; -} - } // namespace xml } // namespace aapt -- cgit v1.2.3-59-g8ed1b