1 /* 2 * Copyright (C) 2017 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #include "test/Builders.h" 18 19 #include "android-base/logging.h" 20 #include "androidfw/StringPiece.h" 21 22 #include "io/StringInputStream.h" 23 #include "test/Common.h" 24 #include "util/Util.h" 25 26 using ::aapt::io::StringInputStream; 27 using ::android::StringPiece; 28 29 namespace aapt { 30 namespace test { 31 32 ResourceTableBuilder& ResourceTableBuilder::SetPackageId(const StringPiece& package_name, 33 uint8_t id) { 34 ResourceTablePackage* package = table_->CreatePackage(package_name, id); 35 CHECK(package != nullptr); 36 return *this; 37 } 38 39 ResourceTableBuilder& ResourceTableBuilder::AddSimple(const StringPiece& name, 40 const ResourceId& id) { 41 return AddValue(name, id, util::make_unique<Id>()); 42 } 43 44 ResourceTableBuilder& ResourceTableBuilder::AddSimple(const StringPiece& name, 45 const ConfigDescription& config, 46 const ResourceId& id) { 47 return AddValue(name, config, id, util::make_unique<Id>()); 48 } 49 50 ResourceTableBuilder& ResourceTableBuilder::AddReference(const StringPiece& name, 51 const StringPiece& ref) { 52 return AddReference(name, {}, ref); 53 } 54 55 ResourceTableBuilder& ResourceTableBuilder::AddReference(const StringPiece& name, 56 const ResourceId& id, 57 const StringPiece& ref) { 58 return AddValue(name, id, util::make_unique<Reference>(ParseNameOrDie(ref))); 59 } 60 61 ResourceTableBuilder& ResourceTableBuilder::AddString(const StringPiece& name, 62 const StringPiece& str) { 63 return AddString(name, {}, str); 64 } 65 66 ResourceTableBuilder& ResourceTableBuilder::AddString(const StringPiece& name, const ResourceId& id, 67 const StringPiece& str) { 68 return AddValue(name, id, util::make_unique<String>(table_->string_pool.MakeRef(str))); 69 } 70 71 ResourceTableBuilder& ResourceTableBuilder::AddString(const StringPiece& name, const ResourceId& id, 72 const ConfigDescription& config, 73 const StringPiece& str) { 74 return AddValue(name, config, id, util::make_unique<String>(table_->string_pool.MakeRef(str))); 75 } 76 77 ResourceTableBuilder& ResourceTableBuilder::AddFileReference(const StringPiece& name, 78 const StringPiece& path) { 79 return AddFileReference(name, {}, path); 80 } 81 82 ResourceTableBuilder& ResourceTableBuilder::AddFileReference(const StringPiece& name, 83 const ResourceId& id, 84 const StringPiece& path) { 85 return AddValue(name, id, util::make_unique<FileReference>(table_->string_pool.MakeRef(path))); 86 } 87 88 ResourceTableBuilder& ResourceTableBuilder::AddFileReference(const StringPiece& name, 89 const StringPiece& path, 90 const ConfigDescription& config) { 91 return AddValue(name, config, {}, 92 util::make_unique<FileReference>(table_->string_pool.MakeRef(path))); 93 } 94 95 ResourceTableBuilder& ResourceTableBuilder::AddValue(const StringPiece& name, 96 std::unique_ptr<Value> value) { 97 return AddValue(name, {}, std::move(value)); 98 } 99 100 ResourceTableBuilder& ResourceTableBuilder::AddValue(const StringPiece& name, const ResourceId& id, 101 std::unique_ptr<Value> value) { 102 return AddValue(name, {}, id, std::move(value)); 103 } 104 105 ResourceTableBuilder& ResourceTableBuilder::AddValue(const StringPiece& name, 106 const ConfigDescription& config, 107 const ResourceId& id, 108 std::unique_ptr<Value> value) { 109 ResourceName res_name = ParseNameOrDie(name); 110 CHECK(table_->AddResourceAllowMangled(res_name, id, config, {}, std::move(value), 111 GetDiagnostics())); 112 return *this; 113 } 114 115 ResourceTableBuilder& ResourceTableBuilder::SetSymbolState(const StringPiece& name, 116 const ResourceId& id, SymbolState state, 117 bool allow_new) { 118 ResourceName res_name = ParseNameOrDie(name); 119 Symbol symbol; 120 symbol.state = state; 121 symbol.allow_new = allow_new; 122 CHECK(table_->SetSymbolStateAllowMangled(res_name, id, symbol, GetDiagnostics())); 123 return *this; 124 } 125 126 StringPool* ResourceTableBuilder::string_pool() { 127 return &table_->string_pool; 128 } 129 130 std::unique_ptr<ResourceTable> ResourceTableBuilder::Build() { 131 return std::move(table_); 132 } 133 134 std::unique_ptr<Reference> BuildReference(const StringPiece& ref, const Maybe<ResourceId>& id) { 135 std::unique_ptr<Reference> reference = util::make_unique<Reference>(ParseNameOrDie(ref)); 136 reference->id = id; 137 return reference; 138 } 139 140 std::unique_ptr<BinaryPrimitive> BuildPrimitive(uint8_t type, uint32_t data) { 141 android::Res_value value = {}; 142 value.size = sizeof(value); 143 value.dataType = type; 144 value.data = data; 145 return util::make_unique<BinaryPrimitive>(value); 146 } 147 148 AttributeBuilder::AttributeBuilder(bool weak) : attr_(util::make_unique<Attribute>(weak)) { 149 attr_->type_mask = android::ResTable_map::TYPE_ANY; 150 } 151 152 AttributeBuilder& AttributeBuilder::SetTypeMask(uint32_t typeMask) { 153 attr_->type_mask = typeMask; 154 return *this; 155 } 156 157 AttributeBuilder& AttributeBuilder::AddItem(const StringPiece& name, uint32_t value) { 158 attr_->symbols.push_back( 159 Attribute::Symbol{Reference(ResourceName({}, ResourceType::kId, name)), value}); 160 return *this; 161 } 162 163 std::unique_ptr<Attribute> AttributeBuilder::Build() { 164 return std::move(attr_); 165 } 166 167 StyleBuilder& StyleBuilder::SetParent(const StringPiece& str) { 168 style_->parent = Reference(ParseNameOrDie(str)); 169 return *this; 170 } 171 172 StyleBuilder& StyleBuilder::AddItem(const StringPiece& str, std::unique_ptr<Item> value) { 173 style_->entries.push_back(Style::Entry{Reference(ParseNameOrDie(str)), std::move(value)}); 174 return *this; 175 } 176 177 StyleBuilder& StyleBuilder::AddItem(const StringPiece& str, const ResourceId& id, 178 std::unique_ptr<Item> value) { 179 AddItem(str, std::move(value)); 180 style_->entries.back().key.id = id; 181 return *this; 182 } 183 184 std::unique_ptr<Style> StyleBuilder::Build() { 185 return std::move(style_); 186 } 187 188 StyleableBuilder& StyleableBuilder::AddItem(const StringPiece& str, const Maybe<ResourceId>& id) { 189 styleable_->entries.push_back(Reference(ParseNameOrDie(str))); 190 styleable_->entries.back().id = id; 191 return *this; 192 } 193 194 std::unique_ptr<Styleable> StyleableBuilder::Build() { 195 return std::move(styleable_); 196 } 197 198 std::unique_ptr<xml::XmlResource> BuildXmlDom(const StringPiece& str) { 199 std::string input = "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n"; 200 input.append(str.data(), str.size()); 201 StringInputStream in(input); 202 StdErrDiagnostics diag; 203 std::unique_ptr<xml::XmlResource> doc = xml::Inflate(&in, &diag, Source("test.xml")); 204 CHECK(doc != nullptr && doc->root != nullptr) << "failed to parse inline XML string"; 205 return doc; 206 } 207 208 std::unique_ptr<xml::XmlResource> BuildXmlDomForPackageName(IAaptContext* context, 209 const StringPiece& str) { 210 std::unique_ptr<xml::XmlResource> doc = BuildXmlDom(str); 211 doc->file.name.package = context->GetCompilationPackage(); 212 return doc; 213 } 214 215 } // namespace test 216 } // namespace aapt 217