diff --git a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/ResTypeSpec.java b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/ResTypeSpec.java index 72a97d508d..f1b0cd243d 100644 --- a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/ResTypeSpec.java +++ b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/ResTypeSpec.java @@ -23,9 +23,11 @@ public final class ResTypeSpec { public static final String RES_TYPE_NAME_ARRAY = "array"; + public static final String RES_TYPE_NAME_ATTR = "attr"; + public static final String RES_TYPE_NAME_ATTR_PRIVATE = "^attr-private"; public static final String RES_TYPE_NAME_PLURALS = "plurals"; + public static final String RES_TYPE_NAME_STRING = "string"; public static final String RES_TYPE_NAME_STYLES = "style"; - public static final String RES_TYPE_NAME_ATTR = "attr"; private final String mName; private final Map mResSpecs = new LinkedHashMap<>(); @@ -46,7 +48,7 @@ public int getId() { } public boolean isString() { - return mName.equalsIgnoreCase("string"); + return mName.equalsIgnoreCase(RES_TYPE_NAME_STRING); } public ResResSpec getResSpec(String name) throws AndrolibException { diff --git a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResArrayValue.java b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResArrayValue.java index 732d2e2d72..2b1e2046b3 100644 --- a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResArrayValue.java +++ b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResArrayValue.java @@ -91,6 +91,4 @@ public String getType() throws AndrolibException { private final ResScalarValue[] mItems; private final String[] AllowedArrayTypes = {"string", "integer"}; - - public static final int BAG_KEY_ARRAY_START = 0x02000000; } diff --git a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResAttr.java b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResAttr.java index f47b224314..c732433321 100644 --- a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResAttr.java +++ b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResAttr.java @@ -64,38 +64,39 @@ public void serializeToResValuesXml(XmlSerializer serializer, ResResource res) t public static ResAttr factory(ResReferenceValue parent, Duo[] items, ResValueFactory factory, ResPackage pkg) throws AndrolibException { - - int type = ((ResIntValue) items[0].m2).getValue(); - int scalarType = type & 0xffff; Integer min = null, max = null; Boolean l10n = null; int i; for (i = 1; i < items.length; i++) { switch (items[i].m1) { case BAG_KEY_ATTR_MIN: - min = ((ResIntValue) items[i].m2).getValue(); + min = (items[i].m2).getRawIntValue(); continue; case BAG_KEY_ATTR_MAX: - max = ((ResIntValue) items[i].m2).getValue(); + max = (items[i].m2).getRawIntValue(); continue; case BAG_KEY_ATTR_L10N: - l10n = ((ResIntValue) items[i].m2).getValue() != 0; + l10n = (items[i].m2).getRawIntValue() != 0; continue; } break; } + // #2806 - Make sure we handle int-based values and not just ResIntValue + int rawValue = items[0].m2.getRawIntValue(); + int scalarType = rawValue & 0xffff; + if (i == items.length) { return new ResAttr(parent, scalarType, min, max, l10n); } - Duo[] attrItems = new Duo[items.length - i]; + Duo[] attrItems = new Duo[items.length - i]; int j = 0; for (; i < items.length; i++) { int resId = items[i].m1; pkg.addSynthesizedRes(resId); - attrItems[j++] = new Duo<>(factory.newReference(resId, null), (ResIntValue) items[i].m2); + attrItems[j++] = new Duo<>(factory.newReference(resId, null), items[i].m2); } - switch (type & 0xff0000) { + switch (rawValue & 0xff0000) { case TYPE_ENUM: return new ResEnumAttr(parent, scalarType, min, max, l10n, attrItems); case TYPE_FLAGS: @@ -145,7 +146,6 @@ protected String getTypeAsString() { private final Integer mMax; private final Boolean mL10n; - public static final int BAG_KEY_ATTR_TYPE = 0x01000000; private static final int BAG_KEY_ATTR_MIN = 0x01000001; private static final int BAG_KEY_ATTR_MAX = 0x01000002; private static final int BAG_KEY_ATTR_L10N = 0x01000003; diff --git a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResEnumAttr.java b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResEnumAttr.java index ed755e2efb..d8ffced4b8 100644 --- a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResEnumAttr.java +++ b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResEnumAttr.java @@ -29,7 +29,7 @@ public class ResEnumAttr extends ResAttr { ResEnumAttr(ResReferenceValue parent, int type, Integer min, Integer max, - Boolean l10n, Duo[] items) { + Boolean l10n, Duo[] items) { super(parent, type, min, max, l10n); mItems = items; } @@ -48,8 +48,8 @@ public String convertToResXmlFormat(ResScalarValue value) @Override protected void serializeBody(XmlSerializer serializer, ResResource res) throws AndrolibException, IOException { - for (Duo duo : mItems) { - int intVal = duo.m2.getValue(); + for (Duo duo : mItems) { + int intVal = duo.m2.getRawIntValue(); // #2836 - Support skipping items if the resource cannot be identified. ResResSpec m1Referent = duo.m1.getReferent(); @@ -72,8 +72,8 @@ private String decodeValue(int value) throws AndrolibException { String value2 = mItemsCache.get(value); if (value2 == null) { ResReferenceValue ref = null; - for (Duo duo : mItems) { - if (duo.m2.getValue() == value) { + for (Duo duo : mItems) { + if (duo.m2.getRawIntValue() == value) { ref = duo.m1; break; } @@ -86,7 +86,7 @@ private String decodeValue(int value) throws AndrolibException { return value2; } - private final Duo[] mItems; + private final Duo[] mItems; private final Map mItemsCache = new HashMap<>(); private static final Logger LOGGER = Logger.getLogger(ResEnumAttr.class.getName()); diff --git a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResFlagsAttr.java b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResFlagsAttr.java index cb8f89c0ed..c37519f66e 100644 --- a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResFlagsAttr.java +++ b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResFlagsAttr.java @@ -29,12 +29,12 @@ public class ResFlagsAttr extends ResAttr { ResFlagsAttr(ResReferenceValue parent, int type, Integer min, Integer max, - Boolean l10n, Duo[] items) { + Boolean l10n, Duo[] items) { super(parent, type, min, max, l10n); mItems = new FlagItem[items.length]; for (int i = 0; i < items.length; i++) { - mItems[i] = new FlagItem(items[i].m1, items[i].m2.getValue()); + mItems[i] = new FlagItem(items[i].m1, items[i].m2.getRawIntValue()); } } diff --git a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResPluralsValue.java b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResPluralsValue.java index 50b3cda516..3be81bdd12 100644 --- a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResPluralsValue.java +++ b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResPluralsValue.java @@ -59,6 +59,5 @@ public void serializeToResValuesXml(XmlSerializer serializer, private final ResScalarValue[] mItems; public static final int BAG_KEY_PLURALS_START = 0x01000004; - public static final int BAG_KEY_PLURALS_END = 0x01000009; private static final String[] QUANTITY_MAP = new String[] { "other", "zero", "one", "two", "few", "many" }; } diff --git a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResValueFactory.java b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResValueFactory.java index 99e6811c65..052621e0f4 100644 --- a/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResValueFactory.java +++ b/brut.apktool/apktool-lib/src/main/java/brut/androlib/res/data/value/ResValueFactory.java @@ -80,39 +80,29 @@ public ResIntBasedValue factory(String value, int rawValue) { return new ResStringValue(value, rawValue); } - public ResBagValue bagFactory(int parent, Duo[] items, ResTypeSpec resTypeSpec) throws AndrolibException { + public ResBagValue bagFactory(int parent, Duo[] items, ResTypeSpec resTypeSpec) + throws AndrolibException { ResReferenceValue parentVal = newReference(parent, null); if (items.length == 0) { return new ResBagValue(parentVal); } - int key = items[0].m1; - if (key == ResAttr.BAG_KEY_ATTR_TYPE) { - return ResAttr.factory(parentVal, items, this, mPackage); - } - String resTypeName = resTypeSpec.getName(); - // Android O Preview added an unknown enum for c. This is hardcoded as 0 for now. - if (ResTypeSpec.RES_TYPE_NAME_ARRAY.equals(resTypeName) - || key == ResArrayValue.BAG_KEY_ARRAY_START || key == 0) { - return new ResArrayValue(parentVal, items); - } - - if (ResTypeSpec.RES_TYPE_NAME_PLURALS.equals(resTypeName) || - (key >= ResPluralsValue.BAG_KEY_PLURALS_START && key <= ResPluralsValue.BAG_KEY_PLURALS_END)) { - return new ResPluralsValue(parentVal, items); - } - - if (ResTypeSpec.RES_TYPE_NAME_ATTR.equals(resTypeName)) { - return new ResAttr(parentVal, 0, null, null, null); - } - - if (resTypeName.startsWith(ResTypeSpec.RES_TYPE_NAME_STYLES)) { - return new ResStyleValue(parentVal, items, this); + switch (resTypeName) { + case ResTypeSpec.RES_TYPE_NAME_ATTR: + case ResTypeSpec.RES_TYPE_NAME_ATTR_PRIVATE: + return ResAttr.factory(parentVal, items, this, mPackage); + case ResTypeSpec.RES_TYPE_NAME_ARRAY: + return new ResArrayValue(parentVal, items); + case ResTypeSpec.RES_TYPE_NAME_PLURALS: + return new ResPluralsValue(parentVal, items); + default: + if (resTypeName.startsWith(ResTypeSpec.RES_TYPE_NAME_STYLES)) { + return new ResStyleValue(parentVal, items, this); + } + throw new AndrolibException("unsupported res type name for bags. Found: " + resTypeName); } - - throw new AndrolibException("unsupported res type name for bags. Found: " + resTypeName); } public ResReferenceValue newReference(int resID, String rawValue) { diff --git a/brut.apktool/apktool-lib/src/test/resources/aapt1/testapp/res/values-mcc001/arrays.xml b/brut.apktool/apktool-lib/src/test/resources/aapt1/testapp/res/values-mcc001/arrays.xml index 141babbee0..697a79d5cb 100644 --- a/brut.apktool/apktool-lib/src/test/resources/aapt1/testapp/res/values-mcc001/arrays.xml +++ b/brut.apktool/apktool-lib/src/test/resources/aapt1/testapp/res/values-mcc001/arrays.xml @@ -35,4 +35,7 @@ res/ view/ + + MIICXAIBAAKBgQCjcGqTkOq0CR3rTx0ZSQSIdTrDrFAYl29611xN8aVgMQIWtDB/lD0W5TpKPuU9iaiG/sSn/VYt6EzN7Sr332jj7cyl2WrrHI6ujRswNy4HojMuqtfab5FFDpRmCuvl35fge18OvoQTJELhhJ1EvJ5KUeZiuJ3u3YyMnxxXzLuKbQIDAQABAoGAPrNDz7TKtaLBvaIuMaMXgBopHyQd3jFKbT/tg2Fu5kYm3PrnmCoQfZYXFKCoZUFIS/G1FBVWWGpD/MQ9tbYZkKpwuH+t2rGndMnLXiTC296/s9uix7gsjnT4Naci5N6EN9pVUBwQmGrYUTHFc58ThtelSiPARX7LSU2ibtJSv8ECQQDWBRrrAYmbCUN7ra0DFT6SppaDtvvuKtb+mUeKbg0B8U4y4wCIK5GH8EyQSwUWcXnNBO05rlUPbifsDLv/u82lAkEAw39sTJ0KmJJyaChqvqAJ8guulKlgucQJ0Et9ppZyet9iVwNKX/aW9UlwGBMQdafQ36nd1QMEA8AbAw4D+hw/KQJBANJbHDUGQtk2hrSmZNoV5HXB9Uiq7v4N71k5ER8XwgM5yVGs2tX8dMM3RhnBEtQXXs9LW1uJZSOQcv7JGXNnhN0CQBZenzrJAWxh3XtznHtBfsHWelyCYRIAj4rpCHCmaGUM6IjCVKFUawOYKp5mmAyObkUZf8ue87emJLEdynC1CLkCQHduNjP1hemAGWrd6v8BHhE3kKtcK6KHsPvJR5dOfzbdHAqVePERhISfN6cwZt5p8B3/JUwSR8el66DF7Jm57BM= +