Loading tools/aapt2/Diagnostics.h +8 −0 Original line number Diff line number Diff line Loading @@ -133,11 +133,19 @@ class SourcePathDiagnostics : public IDiagnostics { void Log(Level level, DiagMessageActual& actual_msg) override { actual_msg.source.path = source_.path; diag_->Log(level, actual_msg); if (level == Level::Error) { error = true; } } bool HadError() { return error; } private: Source source_; IDiagnostics* diag_; bool error = false; DISALLOW_COPY_AND_ASSIGN(SourcePathDiagnostics); }; Loading tools/aapt2/compile/XmlIdCollector.cpp +18 −10 Original line number Diff line number Diff line Loading @@ -21,6 +21,7 @@ #include "ResourceUtils.h" #include "ResourceValues.h" #include "text/Unicode.h" #include "xml/XmlDom.h" namespace aapt { Loading @@ -35,8 +36,9 @@ struct IdCollector : public xml::Visitor { public: using xml::Visitor::Visit; explicit IdCollector(std::vector<SourcedResourceName>* out_symbols) : out_symbols_(out_symbols) {} explicit IdCollector(std::vector<SourcedResourceName>* out_symbols, SourcePathDiagnostics* source_diag) : out_symbols_(out_symbols), source_diag_(source_diag) {} void Visit(xml::Element* element) override { for (xml::Attribute& attr : element->attributes) { Loading @@ -44,31 +46,37 @@ struct IdCollector : public xml::Visitor { bool create = false; if (ResourceUtils::ParseReference(attr.value, &name, &create, nullptr)) { if (create && name.type == ResourceType::kId) { if (!text::IsValidResourceEntryName(name.entry)) { source_diag_->Error(DiagMessage(element->line_number) << "id '" << name << "' has an invalid entry name"); } else { auto iter = std::lower_bound(out_symbols_->begin(), out_symbols_->end(), name, cmp_name); if (iter == out_symbols_->end() || iter->name != name) { out_symbols_->insert(iter, SourcedResourceName{name.ToResourceName(), out_symbols_->insert(iter, SourcedResourceName{name.ToResourceName(), element->line_number}); } } } } } xml::Visitor::Visit(element); } private: std::vector<SourcedResourceName>* out_symbols_; SourcePathDiagnostics* source_diag_; }; } // namespace bool XmlIdCollector::Consume(IAaptContext* context, xml::XmlResource* xmlRes) { xmlRes->file.exported_symbols.clear(); IdCollector collector(&xmlRes->file.exported_symbols); SourcePathDiagnostics source_diag(xmlRes->file.source, context->GetDiagnostics()); IdCollector collector(&xmlRes->file.exported_symbols, &source_diag); xmlRes->root->Accept(&collector); return true; return !source_diag.HadError(); } } // namespace aapt tools/aapt2/compile/XmlIdCollector_test.cpp +10 −0 Original line number Diff line number Diff line Loading @@ -64,4 +64,14 @@ TEST(XmlIdCollectorTest, DontCollectNonIds) { EXPECT_TRUE(doc->file.exported_symbols.empty()); } TEST(XmlIdCollectorTest, ErrorOnInvalidIds) { std::unique_ptr<IAaptContext> context = test::ContextBuilder().Build(); std::unique_ptr<xml::XmlResource> doc = test::BuildXmlDom("<View foo=\"@+id/foo$bar\"/>"); XmlIdCollector collector; ASSERT_FALSE(collector.Consume(context.get(), doc.get())); } } // namespace aapt Loading
tools/aapt2/Diagnostics.h +8 −0 Original line number Diff line number Diff line Loading @@ -133,11 +133,19 @@ class SourcePathDiagnostics : public IDiagnostics { void Log(Level level, DiagMessageActual& actual_msg) override { actual_msg.source.path = source_.path; diag_->Log(level, actual_msg); if (level == Level::Error) { error = true; } } bool HadError() { return error; } private: Source source_; IDiagnostics* diag_; bool error = false; DISALLOW_COPY_AND_ASSIGN(SourcePathDiagnostics); }; Loading
tools/aapt2/compile/XmlIdCollector.cpp +18 −10 Original line number Diff line number Diff line Loading @@ -21,6 +21,7 @@ #include "ResourceUtils.h" #include "ResourceValues.h" #include "text/Unicode.h" #include "xml/XmlDom.h" namespace aapt { Loading @@ -35,8 +36,9 @@ struct IdCollector : public xml::Visitor { public: using xml::Visitor::Visit; explicit IdCollector(std::vector<SourcedResourceName>* out_symbols) : out_symbols_(out_symbols) {} explicit IdCollector(std::vector<SourcedResourceName>* out_symbols, SourcePathDiagnostics* source_diag) : out_symbols_(out_symbols), source_diag_(source_diag) {} void Visit(xml::Element* element) override { for (xml::Attribute& attr : element->attributes) { Loading @@ -44,31 +46,37 @@ struct IdCollector : public xml::Visitor { bool create = false; if (ResourceUtils::ParseReference(attr.value, &name, &create, nullptr)) { if (create && name.type == ResourceType::kId) { if (!text::IsValidResourceEntryName(name.entry)) { source_diag_->Error(DiagMessage(element->line_number) << "id '" << name << "' has an invalid entry name"); } else { auto iter = std::lower_bound(out_symbols_->begin(), out_symbols_->end(), name, cmp_name); if (iter == out_symbols_->end() || iter->name != name) { out_symbols_->insert(iter, SourcedResourceName{name.ToResourceName(), out_symbols_->insert(iter, SourcedResourceName{name.ToResourceName(), element->line_number}); } } } } } xml::Visitor::Visit(element); } private: std::vector<SourcedResourceName>* out_symbols_; SourcePathDiagnostics* source_diag_; }; } // namespace bool XmlIdCollector::Consume(IAaptContext* context, xml::XmlResource* xmlRes) { xmlRes->file.exported_symbols.clear(); IdCollector collector(&xmlRes->file.exported_symbols); SourcePathDiagnostics source_diag(xmlRes->file.source, context->GetDiagnostics()); IdCollector collector(&xmlRes->file.exported_symbols, &source_diag); xmlRes->root->Accept(&collector); return true; return !source_diag.HadError(); } } // namespace aapt
tools/aapt2/compile/XmlIdCollector_test.cpp +10 −0 Original line number Diff line number Diff line Loading @@ -64,4 +64,14 @@ TEST(XmlIdCollectorTest, DontCollectNonIds) { EXPECT_TRUE(doc->file.exported_symbols.empty()); } TEST(XmlIdCollectorTest, ErrorOnInvalidIds) { std::unique_ptr<IAaptContext> context = test::ContextBuilder().Build(); std::unique_ptr<xml::XmlResource> doc = test::BuildXmlDom("<View foo=\"@+id/foo$bar\"/>"); XmlIdCollector collector; ASSERT_FALSE(collector.Consume(context.get(), doc.get())); } } // namespace aapt