• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2015 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 #ifndef AAPT_TEST_BUILDERS_H
18 #define AAPT_TEST_BUILDERS_H
19 
20 #include "ResourceTable.h"
21 #include "ResourceValues.h"
22 #include "test/Common.h"
23 #include "util/Util.h"
24 #include "xml/XmlDom.h"
25 
26 #include <memory>
27 
28 namespace aapt {
29 namespace test {
30 
31 class ResourceTableBuilder {
32 private:
33     DummyDiagnosticsImpl mDiagnostics;
34     std::unique_ptr<ResourceTable> mTable = util::make_unique<ResourceTable>();
35 
36 public:
37     ResourceTableBuilder() = default;
38 
getStringPool()39     StringPool* getStringPool() {
40         return &mTable->stringPool;
41     }
42 
setPackageId(const StringPiece16 & packageName,uint8_t id)43     ResourceTableBuilder& setPackageId(const StringPiece16& packageName, uint8_t id) {
44         ResourceTablePackage* package = mTable->createPackage(packageName, id);
45         assert(package);
46         return *this;
47     }
48 
49     ResourceTableBuilder& addSimple(const StringPiece16& name, const ResourceId id = {}) {
50         return addValue(name, id, util::make_unique<Id>());
51     }
52 
addReference(const StringPiece16 & name,const StringPiece16 & ref)53     ResourceTableBuilder& addReference(const StringPiece16& name, const StringPiece16& ref) {
54         return addReference(name, {}, ref);
55     }
56 
addReference(const StringPiece16 & name,const ResourceId id,const StringPiece16 & ref)57     ResourceTableBuilder& addReference(const StringPiece16& name, const ResourceId id,
58                                        const StringPiece16& ref) {
59         return addValue(name, id, util::make_unique<Reference>(parseNameOrDie(ref)));
60     }
61 
addString(const StringPiece16 & name,const StringPiece16 & str)62     ResourceTableBuilder& addString(const StringPiece16& name, const StringPiece16& str) {
63         return addString(name, {}, str);
64     }
65 
addString(const StringPiece16 & name,const ResourceId id,const StringPiece16 & str)66     ResourceTableBuilder& addString(const StringPiece16& name, const ResourceId id,
67                                     const StringPiece16& str) {
68         return addValue(name, id, util::make_unique<String>(mTable->stringPool.makeRef(str)));
69     }
70 
addString(const StringPiece16 & name,const ResourceId id,const ConfigDescription & config,const StringPiece16 & str)71     ResourceTableBuilder& addString(const StringPiece16& name, const ResourceId id,
72                                     const ConfigDescription& config, const StringPiece16& str) {
73         return addValue(name, id, config,
74                         util::make_unique<String>(mTable->stringPool.makeRef(str)));
75     }
76 
addFileReference(const StringPiece16 & name,const StringPiece16 & path)77     ResourceTableBuilder& addFileReference(const StringPiece16& name, const StringPiece16& path) {
78         return addFileReference(name, {}, path);
79     }
80 
addFileReference(const StringPiece16 & name,const ResourceId id,const StringPiece16 & path)81     ResourceTableBuilder& addFileReference(const StringPiece16& name, const ResourceId id,
82                                            const StringPiece16& path) {
83         return addValue(name, id,
84                         util::make_unique<FileReference>(mTable->stringPool.makeRef(path)));
85     }
86 
addFileReference(const StringPiece16 & name,const StringPiece16 & path,const ConfigDescription & config)87     ResourceTableBuilder& addFileReference(const StringPiece16& name, const StringPiece16& path,
88                                            const ConfigDescription& config) {
89         return addValue(name, {}, config,
90                         util::make_unique<FileReference>(mTable->stringPool.makeRef(path)));
91     }
92 
addValue(const StringPiece16 & name,std::unique_ptr<Value> value)93     ResourceTableBuilder& addValue(const StringPiece16& name,
94                                    std::unique_ptr<Value> value) {
95         return addValue(name, {}, std::move(value));
96     }
97 
addValue(const StringPiece16 & name,const ResourceId id,std::unique_ptr<Value> value)98     ResourceTableBuilder& addValue(const StringPiece16& name, const ResourceId id,
99                                        std::unique_ptr<Value> value) {
100         return addValue(name, id, {}, std::move(value));
101     }
102 
addValue(const StringPiece16 & name,const ResourceId id,const ConfigDescription & config,std::unique_ptr<Value> value)103     ResourceTableBuilder& addValue(const StringPiece16& name, const ResourceId id,
104                                    const ConfigDescription& config,
105                                    std::unique_ptr<Value> value) {
106         ResourceName resName = parseNameOrDie(name);
107         bool result = mTable->addResourceAllowMangled(resName, id, config, std::string(),
108                                                       std::move(value), &mDiagnostics);
109         assert(result);
110         return *this;
111     }
112 
setSymbolState(const StringPiece16 & name,ResourceId id,SymbolState state)113     ResourceTableBuilder& setSymbolState(const StringPiece16& name, ResourceId id,
114                                          SymbolState state) {
115         ResourceName resName = parseNameOrDie(name);
116         Symbol symbol;
117         symbol.state = state;
118         bool result = mTable->setSymbolStateAllowMangled(resName, id, symbol, &mDiagnostics);
119         assert(result);
120         return *this;
121     }
122 
build()123     std::unique_ptr<ResourceTable> build() {
124         return std::move(mTable);
125     }
126 };
127 
128 inline std::unique_ptr<Reference> buildReference(const StringPiece16& ref,
129                                                  Maybe<ResourceId> id = {}) {
130     std::unique_ptr<Reference> reference = util::make_unique<Reference>(parseNameOrDie(ref));
131     reference->id = id;
132     return reference;
133 }
134 
buildPrimitive(uint8_t type,uint32_t data)135 inline std::unique_ptr<BinaryPrimitive> buildPrimitive(uint8_t type, uint32_t data) {
136     android::Res_value value = {};
137     value.size = sizeof(value);
138     value.dataType = type;
139     value.data = data;
140     return util::make_unique<BinaryPrimitive>(value);
141 }
142 
143 template <typename T>
144 class ValueBuilder {
145 private:
146     std::unique_ptr<Value> mValue;
147 
148 public:
149     template <typename... Args>
ValueBuilder(Args &&...args)150     ValueBuilder(Args&&... args) : mValue(new T{ std::forward<Args>(args)... }) {
151     }
152 
153     template <typename... Args>
setSource(Args &&...args)154     ValueBuilder& setSource(Args&&... args) {
155         mValue->setSource(Source{ std::forward<Args>(args)... });
156         return *this;
157     }
158 
setComment(const StringPiece16 & str)159     ValueBuilder& setComment(const StringPiece16& str) {
160         mValue->setComment(str);
161         return *this;
162     }
163 
build()164     std::unique_ptr<Value> build() {
165         return std::move(mValue);
166     }
167 };
168 
169 class AttributeBuilder {
170 private:
171     std::unique_ptr<Attribute> mAttr;
172 
173 public:
mAttr(util::make_unique<Attribute> (weak))174     AttributeBuilder(bool weak = false) : mAttr(util::make_unique<Attribute>(weak)) {
175         mAttr->typeMask = android::ResTable_map::TYPE_ANY;
176     }
177 
setTypeMask(uint32_t typeMask)178     AttributeBuilder& setTypeMask(uint32_t typeMask) {
179         mAttr->typeMask = typeMask;
180         return *this;
181     }
182 
addItem(const StringPiece16 & name,uint32_t value)183     AttributeBuilder& addItem(const StringPiece16& name, uint32_t value) {
184         mAttr->symbols.push_back(Attribute::Symbol{
185                 Reference(ResourceName{ {}, ResourceType::kId, name.toString()}),
186                 value});
187         return *this;
188     }
189 
build()190     std::unique_ptr<Attribute> build() {
191         return std::move(mAttr);
192     }
193 };
194 
195 class StyleBuilder {
196 private:
197     std::unique_ptr<Style> mStyle = util::make_unique<Style>();
198 
199 public:
setParent(const StringPiece16 & str)200     StyleBuilder& setParent(const StringPiece16& str) {
201         mStyle->parent = Reference(parseNameOrDie(str));
202         return *this;
203     }
204 
addItem(const StringPiece16 & str,std::unique_ptr<Item> value)205     StyleBuilder& addItem(const StringPiece16& str, std::unique_ptr<Item> value) {
206         mStyle->entries.push_back(Style::Entry{ Reference(parseNameOrDie(str)), std::move(value) });
207         return *this;
208     }
209 
addItem(const StringPiece16 & str,ResourceId id,std::unique_ptr<Item> value)210     StyleBuilder& addItem(const StringPiece16& str, ResourceId id, std::unique_ptr<Item> value) {
211         addItem(str, std::move(value));
212         mStyle->entries.back().key.id = id;
213         return *this;
214     }
215 
build()216     std::unique_ptr<Style> build() {
217         return std::move(mStyle);
218     }
219 };
220 
221 class StyleableBuilder {
222 private:
223     std::unique_ptr<Styleable> mStyleable = util::make_unique<Styleable>();
224 
225 public:
226     StyleableBuilder& addItem(const StringPiece16& str, Maybe<ResourceId> id = {}) {
227         mStyleable->entries.push_back(Reference(parseNameOrDie(str)));
228         mStyleable->entries.back().id = id;
229         return *this;
230     }
231 
build()232     std::unique_ptr<Styleable> build() {
233         return std::move(mStyleable);
234     }
235 };
236 
buildXmlDom(const StringPiece & str)237 inline std::unique_ptr<xml::XmlResource> buildXmlDom(const StringPiece& str) {
238     std::stringstream in;
239     in << "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n" << str;
240     StdErrDiagnostics diag;
241     std::unique_ptr<xml::XmlResource> doc = xml::inflate(&in, &diag, Source("test.xml"));
242     assert(doc);
243     return doc;
244 }
245 
buildXmlDomForPackageName(IAaptContext * context,const StringPiece & str)246 inline std::unique_ptr<xml::XmlResource> buildXmlDomForPackageName(IAaptContext* context,
247                                                                    const StringPiece& str) {
248     std::unique_ptr<xml::XmlResource> doc = buildXmlDom(str);
249     doc->file.name.package = context->getCompilationPackage();
250     return doc;
251 }
252 
253 } // namespace test
254 } // namespace aapt
255 
256 #endif /* AAPT_TEST_BUILDERS_H */
257