ResourceTable.h revision a96cbb435d7b2197ab2b61fd98d14cbd6e0c5c3d
1// 2// Copyright 2006 The Android Open Source Project 3// 4// Build resource files from raw assets. 5// 6 7#ifndef RESOURCE_TABLE_H 8#define RESOURCE_TABLE_H 9 10#include "StringPool.h" 11#include "SourcePos.h" 12 13#include <set> 14#include <map> 15 16using namespace std; 17 18class XMLNode; 19class ResourceTable; 20 21enum { 22 XML_COMPILE_STRIP_COMMENTS = 1<<0, 23 XML_COMPILE_ASSIGN_ATTRIBUTE_IDS = 1<<1, 24 XML_COMPILE_COMPACT_WHITESPACE = 1<<2, 25 XML_COMPILE_STRIP_WHITESPACE = 1<<3, 26 XML_COMPILE_STRIP_RAW_VALUES = 1<<4, 27 28 XML_COMPILE_STANDARD_RESOURCE = 29 XML_COMPILE_STRIP_COMMENTS | XML_COMPILE_ASSIGN_ATTRIBUTE_IDS 30 | XML_COMPILE_STRIP_WHITESPACE | XML_COMPILE_STRIP_RAW_VALUES 31}; 32 33status_t compileXmlFile(const sp<AaptAssets>& assets, 34 const sp<AaptFile>& target, 35 ResourceTable* table, 36 int options = XML_COMPILE_STANDARD_RESOURCE); 37 38status_t compileXmlFile(const sp<AaptAssets>& assets, 39 const sp<XMLNode>& xmlTree, 40 const sp<AaptFile>& target, 41 ResourceTable* table, 42 int options = XML_COMPILE_STANDARD_RESOURCE); 43 44status_t compileResourceFile(Bundle* bundle, 45 const sp<AaptAssets>& assets, 46 const sp<AaptFile>& in, 47 const ResTable_config& defParams, 48 const bool overwrite, 49 ResourceTable* outTable); 50 51struct AccessorCookie 52{ 53 SourcePos sourcePos; 54 String8 attr; 55 String8 value; 56 57 AccessorCookie(const SourcePos&p, const String8& a, const String8& v) 58 :sourcePos(p), 59 attr(a), 60 value(v) 61 { 62 } 63}; 64 65class ResourceTable : public ResTable::Accessor 66{ 67public: 68 class Package; 69 class Type; 70 class Entry; 71 72 ResourceTable(Bundle* bundle, const String16& assetsPackage); 73 74 status_t addIncludedResources(Bundle* bundle, const sp<AaptAssets>& assets); 75 76 status_t addPublic(const SourcePos& pos, 77 const String16& package, 78 const String16& type, 79 const String16& name, 80 const uint32_t ident); 81 82 status_t addEntry(const SourcePos& pos, 83 const String16& package, 84 const String16& type, 85 const String16& name, 86 const String16& value, 87 const Vector<StringPool::entry_style_span>* style = NULL, 88 const ResTable_config* params = NULL, 89 const bool doSetIndex = false, 90 const int32_t format = ResTable_map::TYPE_ANY, 91 const bool overwrite = false); 92 93 status_t startBag(const SourcePos& pos, 94 const String16& package, 95 const String16& type, 96 const String16& name, 97 const String16& bagParent, 98 const ResTable_config* params = NULL, 99 bool replace = false, 100 bool isId = false); 101 102 status_t addBag(const SourcePos& pos, 103 const String16& package, 104 const String16& type, 105 const String16& name, 106 const String16& bagParent, 107 const String16& bagKey, 108 const String16& value, 109 const Vector<StringPool::entry_style_span>* style = NULL, 110 const ResTable_config* params = NULL, 111 bool replace = false, 112 bool isId = false, 113 const int32_t format = ResTable_map::TYPE_ANY); 114 115 bool hasBagOrEntry(const String16& package, 116 const String16& type, 117 const String16& name) const; 118 119 bool hasBagOrEntry(const String16& ref, 120 const String16* defType = NULL, 121 const String16* defPackage = NULL); 122 123 bool appendComment(const String16& package, 124 const String16& type, 125 const String16& name, 126 const String16& comment, 127 bool onlyIfEmpty = false); 128 129 bool appendTypeComment(const String16& package, 130 const String16& type, 131 const String16& name, 132 const String16& comment); 133 134 size_t size() const; 135 size_t numLocalResources() const; 136 bool hasResources() const; 137 138 sp<AaptFile> flatten(Bundle*); 139 140 static inline uint32_t makeResId(uint32_t packageId, 141 uint32_t typeId, 142 uint32_t nameId) 143 { 144 return nameId | (typeId<<16) | (packageId<<24); 145 } 146 147 static inline uint32_t getResId(const sp<Package>& p, 148 const sp<Type>& t, 149 uint32_t nameId); 150 151 uint32_t getResId(const String16& package, 152 const String16& type, 153 const String16& name, 154 bool onlyPublic = false) const; 155 156 uint32_t getResId(const String16& ref, 157 const String16* defType = NULL, 158 const String16* defPackage = NULL, 159 const char** outErrorMsg = NULL, 160 bool onlyPublic = false) const; 161 162 static bool isValidResourceName(const String16& s); 163 164 bool stringToValue(Res_value* outValue, StringPool* pool, 165 const String16& str, 166 bool preserveSpaces, bool coerceType, 167 uint32_t attrID, 168 const Vector<StringPool::entry_style_span>* style = NULL, 169 String16* outStr = NULL, void* accessorCookie = NULL, 170 uint32_t attrType = ResTable_map::TYPE_ANY); 171 172 status_t assignResourceIds(); 173 status_t addSymbols(const sp<AaptSymbols>& outSymbols = NULL); 174 void addLocalization(const String16& name, const String8& locale); 175 status_t validateLocalizations(void); 176 177 status_t flatten(Bundle*, const sp<AaptFile>& dest); 178 179 void writePublicDefinitions(const String16& package, FILE* fp); 180 181 virtual uint32_t getCustomResource(const String16& package, 182 const String16& type, 183 const String16& name) const; 184 virtual uint32_t getCustomResourceWithCreation(const String16& package, 185 const String16& type, 186 const String16& name, 187 const bool createIfNeeded); 188 virtual uint32_t getRemappedPackage(uint32_t origPackage) const; 189 virtual bool getAttributeType(uint32_t attrID, uint32_t* outType); 190 virtual bool getAttributeMin(uint32_t attrID, uint32_t* outMin); 191 virtual bool getAttributeMax(uint32_t attrID, uint32_t* outMax); 192 virtual bool getAttributeKeys(uint32_t attrID, Vector<String16>* outKeys); 193 virtual bool getAttributeEnum(uint32_t attrID, 194 const char16_t* name, size_t nameLen, 195 Res_value* outValue); 196 virtual bool getAttributeFlags(uint32_t attrID, 197 const char16_t* name, size_t nameLen, 198 Res_value* outValue); 199 virtual uint32_t getAttributeL10N(uint32_t attrID); 200 201 virtual bool getLocalizationSetting(); 202 virtual void reportError(void* accessorCookie, const char* fmt, ...); 203 204 void setCurrentXmlPos(const SourcePos& pos) { mCurrentXmlPos = pos; } 205 206 class Item { 207 public: 208 Item() : isId(false), format(ResTable_map::TYPE_ANY), bagKeyId(0), evaluating(false) 209 { memset(&parsedValue, 0, sizeof(parsedValue)); } 210 Item(const SourcePos& pos, 211 bool _isId, 212 const String16& _value, 213 const Vector<StringPool::entry_style_span>* _style = NULL, 214 int32_t format = ResTable_map::TYPE_ANY); 215 Item(const Item& o) : sourcePos(o.sourcePos), 216 isId(o.isId), value(o.value), style(o.style), 217 format(o.format), bagKeyId(o.bagKeyId), evaluating(false) { 218 memset(&parsedValue, 0, sizeof(parsedValue)); 219 } 220 ~Item() { } 221 222 Item& operator=(const Item& o) { 223 sourcePos = o.sourcePos; 224 isId = o.isId; 225 value = o.value; 226 style = o.style; 227 format = o.format; 228 bagKeyId = o.bagKeyId; 229 parsedValue = o.parsedValue; 230 return *this; 231 } 232 233 SourcePos sourcePos; 234 mutable bool isId; 235 String16 value; 236 Vector<StringPool::entry_style_span> style; 237 int32_t format; 238 uint32_t bagKeyId; 239 mutable bool evaluating; 240 Res_value parsedValue; 241 }; 242 243 class Entry : public RefBase { 244 public: 245 Entry(const String16& name, const SourcePos& pos) 246 : mName(name), mType(TYPE_UNKNOWN), 247 mItemFormat(ResTable_map::TYPE_ANY), mNameIndex(-1), mPos(pos) 248 { } 249 virtual ~Entry() { } 250 251 enum type { 252 TYPE_UNKNOWN = 0, 253 TYPE_ITEM, 254 TYPE_BAG 255 }; 256 257 String16 getName() const { return mName; } 258 type getType() const { return mType; } 259 260 void setParent(const String16& parent) { mParent = parent; } 261 String16 getParent() const { return mParent; } 262 263 status_t makeItABag(const SourcePos& sourcePos); 264 265 status_t emptyBag(const SourcePos& sourcePos); 266 267 status_t setItem(const SourcePos& pos, 268 const String16& value, 269 const Vector<StringPool::entry_style_span>* style = NULL, 270 int32_t format = ResTable_map::TYPE_ANY, 271 const bool overwrite = false); 272 273 status_t addToBag(const SourcePos& pos, 274 const String16& key, const String16& value, 275 const Vector<StringPool::entry_style_span>* style = NULL, 276 bool replace=false, bool isId = false, 277 int32_t format = ResTable_map::TYPE_ANY); 278 279 // Index of the entry's name string in the key pool. 280 int32_t getNameIndex() const { return mNameIndex; } 281 void setNameIndex(int32_t index) { mNameIndex = index; } 282 283 const Item* getItem() const { return mType == TYPE_ITEM ? &mItem : NULL; } 284 const KeyedVector<String16, Item>& getBag() const { return mBag; } 285 286 status_t generateAttributes(ResourceTable* table, 287 const String16& package); 288 289 status_t assignResourceIds(ResourceTable* table, 290 const String16& package); 291 292 status_t prepareFlatten(StringPool* strings, ResourceTable* table); 293 294 ssize_t flatten(Bundle*, const sp<AaptFile>& data, bool isPublic); 295 296 const SourcePos& getPos() const { return mPos; } 297 298 private: 299 String16 mName; 300 String16 mParent; 301 type mType; 302 Item mItem; 303 int32_t mItemFormat; 304 KeyedVector<String16, Item> mBag; 305 int32_t mNameIndex; 306 uint32_t mParentId; 307 SourcePos mPos; 308 }; 309 310 struct ConfigDescription : public ResTable_config { 311 ConfigDescription() { 312 memset(this, 0, sizeof(*this)); 313 size = sizeof(ResTable_config); 314 } 315 ConfigDescription(const ResTable_config&o) { 316 *static_cast<ResTable_config*>(this) = o; 317 size = sizeof(ResTable_config); 318 } 319 ConfigDescription(const ConfigDescription&o) { 320 *static_cast<ResTable_config*>(this) = o; 321 } 322 323 ConfigDescription& operator=(const ResTable_config& o) { 324 *static_cast<ResTable_config*>(this) = o; 325 size = sizeof(ResTable_config); 326 return *this; 327 } 328 ConfigDescription& operator=(const ConfigDescription& o) { 329 *static_cast<ResTable_config*>(this) = o; 330 return *this; 331 } 332 333 inline bool operator<(const ConfigDescription& o) const { return compare(o) < 0; } 334 inline bool operator<=(const ConfigDescription& o) const { return compare(o) <= 0; } 335 inline bool operator==(const ConfigDescription& o) const { return compare(o) == 0; } 336 inline bool operator!=(const ConfigDescription& o) const { return compare(o) != 0; } 337 inline bool operator>=(const ConfigDescription& o) const { return compare(o) >= 0; } 338 inline bool operator>(const ConfigDescription& o) const { return compare(o) > 0; } 339 }; 340 341 class ConfigList : public RefBase { 342 public: 343 ConfigList(const String16& name, const SourcePos& pos) 344 : mName(name), mPos(pos), mPublic(false), mEntryIndex(-1) { } 345 virtual ~ConfigList() { } 346 347 String16 getName() const { return mName; } 348 const SourcePos& getPos() const { return mPos; } 349 350 void appendComment(const String16& comment, bool onlyIfEmpty = false); 351 const String16& getComment() const { return mComment; } 352 353 void appendTypeComment(const String16& comment); 354 const String16& getTypeComment() const { return mTypeComment; } 355 356 // Index of this entry in its Type. 357 int32_t getEntryIndex() const { return mEntryIndex; } 358 void setEntryIndex(int32_t index) { mEntryIndex = index; } 359 360 void setPublic(bool pub) { mPublic = pub; } 361 bool getPublic() const { return mPublic; } 362 void setPublicSourcePos(const SourcePos& pos) { mPublicSourcePos = pos; } 363 const SourcePos& getPublicSourcePos() { return mPublicSourcePos; } 364 365 void addEntry(const ResTable_config& config, const sp<Entry>& entry) { 366 mEntries.add(config, entry); 367 } 368 369 const DefaultKeyedVector<ConfigDescription, sp<Entry> >& getEntries() const { return mEntries; } 370 private: 371 const String16 mName; 372 const SourcePos mPos; 373 String16 mComment; 374 String16 mTypeComment; 375 bool mPublic; 376 SourcePos mPublicSourcePos; 377 int32_t mEntryIndex; 378 DefaultKeyedVector<ConfigDescription, sp<Entry> > mEntries; 379 }; 380 381 class Public { 382 public: 383 Public() : sourcePos(), ident(0) { } 384 Public(const SourcePos& pos, 385 const String16& _comment, 386 uint32_t _ident) 387 : sourcePos(pos), 388 comment(_comment), ident(_ident) { } 389 Public(const Public& o) : sourcePos(o.sourcePos), 390 comment(o.comment), ident(o.ident) { } 391 ~Public() { } 392 393 Public& operator=(const Public& o) { 394 sourcePos = o.sourcePos; 395 comment = o.comment; 396 ident = o.ident; 397 return *this; 398 } 399 400 SourcePos sourcePos; 401 String16 comment; 402 uint32_t ident; 403 }; 404 405 class Type : public RefBase { 406 public: 407 Type(const String16& name, const SourcePos& pos) 408 : mName(name), mFirstPublicSourcePos(NULL), mPublicIndex(-1), mIndex(-1), mPos(pos) 409 { } 410 virtual ~Type() { delete mFirstPublicSourcePos; } 411 412 status_t addPublic(const SourcePos& pos, 413 const String16& name, 414 const uint32_t ident); 415 416 String16 getName() const { return mName; } 417 sp<Entry> getEntry(const String16& entry, 418 const SourcePos& pos, 419 const ResTable_config* config = NULL, 420 bool doSetIndex = false); 421 422 const SourcePos& getFirstPublicSourcePos() const { return *mFirstPublicSourcePos; } 423 424 int32_t getPublicIndex() const { return mPublicIndex; } 425 426 int32_t getIndex() const { return mIndex; } 427 void setIndex(int32_t index) { mIndex = index; } 428 429 status_t applyPublicEntryOrder(); 430 431 const SortedVector<ConfigDescription>& getUniqueConfigs() const { return mUniqueConfigs; } 432 433 const DefaultKeyedVector<String16, sp<ConfigList> >& getConfigs() const { return mConfigs; } 434 const Vector<sp<ConfigList> >& getOrderedConfigs() const { return mOrderedConfigs; } 435 436 const SourcePos& getPos() const { return mPos; } 437 private: 438 String16 mName; 439 SourcePos* mFirstPublicSourcePos; 440 DefaultKeyedVector<String16, Public> mPublic; 441 SortedVector<ConfigDescription> mUniqueConfigs; 442 DefaultKeyedVector<String16, sp<ConfigList> > mConfigs; 443 Vector<sp<ConfigList> > mOrderedConfigs; 444 int32_t mPublicIndex; 445 int32_t mIndex; 446 SourcePos mPos; 447 }; 448 449 class Package : public RefBase { 450 public: 451 Package(const String16& name, ssize_t includedId=-1); 452 virtual ~Package() { } 453 454 String16 getName() const { return mName; } 455 sp<Type> getType(const String16& type, 456 const SourcePos& pos, 457 bool doSetIndex = false); 458 459 ssize_t getAssignedId() const { return mIncludedId; } 460 461 const ResStringPool& getTypeStrings() const { return mTypeStrings; } 462 uint32_t indexOfTypeString(const String16& s) const { return mTypeStringsMapping.valueFor(s); } 463 const sp<AaptFile> getTypeStringsData() const { return mTypeStringsData; } 464 status_t setTypeStrings(const sp<AaptFile>& data); 465 466 const ResStringPool& getKeyStrings() const { return mKeyStrings; } 467 uint32_t indexOfKeyString(const String16& s) const { return mKeyStringsMapping.valueFor(s); } 468 const sp<AaptFile> getKeyStringsData() const { return mKeyStringsData; } 469 status_t setKeyStrings(const sp<AaptFile>& data); 470 471 status_t applyPublicTypeOrder(); 472 473 const DefaultKeyedVector<String16, sp<Type> >& getTypes() const { return mTypes; } 474 const Vector<sp<Type> >& getOrderedTypes() const { return mOrderedTypes; } 475 476 private: 477 status_t setStrings(const sp<AaptFile>& data, 478 ResStringPool* strings, 479 DefaultKeyedVector<String16, uint32_t>* mappings); 480 481 const String16 mName; 482 const ssize_t mIncludedId; 483 DefaultKeyedVector<String16, sp<Type> > mTypes; 484 Vector<sp<Type> > mOrderedTypes; 485 sp<AaptFile> mTypeStringsData; 486 sp<AaptFile> mKeyStringsData; 487 ResStringPool mTypeStrings; 488 ResStringPool mKeyStrings; 489 DefaultKeyedVector<String16, uint32_t> mTypeStringsMapping; 490 DefaultKeyedVector<String16, uint32_t> mKeyStringsMapping; 491 }; 492 493private: 494 void writePublicDefinitions(const String16& package, FILE* fp, bool pub); 495 sp<Package> getPackage(const String16& package); 496 sp<Type> getType(const String16& package, 497 const String16& type, 498 const SourcePos& pos, 499 bool doSetIndex = false); 500 sp<Entry> getEntry(const String16& package, 501 const String16& type, 502 const String16& name, 503 const SourcePos& pos, 504 const ResTable_config* config = NULL, 505 bool doSetIndex = false); 506 sp<const Entry> getEntry(uint32_t resID, 507 const ResTable_config* config = NULL) const; 508 const Item* getItem(uint32_t resID, uint32_t attrID) const; 509 bool getItemValue(uint32_t resID, uint32_t attrID, 510 Res_value* outValue); 511 512 513 String16 mAssetsPackage; 514 sp<AaptAssets> mAssets; 515 DefaultKeyedVector<String16, sp<Package> > mPackages; 516 Vector<sp<Package> > mOrderedPackages; 517 uint32_t mNextPackageId; 518 bool mHaveAppPackage; 519 bool mIsAppPackage; 520 size_t mNumLocal; 521 SourcePos mCurrentXmlPos; 522 Bundle* mBundle; 523 524 // key = string resource name, value = set of locales in which that name is defined 525 map<String16, set<String8> > mLocalizations; 526}; 527 528class ResourceFilter 529{ 530public: 531 ResourceFilter() : mData(), mContainsPseudo(false) {} 532 status_t parse(const char* arg); 533 bool match(int axis, uint32_t value); 534 bool match(const ResTable_config& config); 535 inline bool containsPseudo() { return mContainsPseudo; } 536 537private: 538 KeyedVector<int,SortedVector<uint32_t> > mData; 539 bool mContainsPseudo; 540}; 541 542 543#endif 544