Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Unable to decode AndroidManifest.xml #1976

Closed
sebras opened this issue Jan 8, 2019 · 1 comment

Comments

@sebras
Copy link
Contributor

commented Jan 8, 2019

Information

  1. Apktool Version (apktool -version) - v2.4.0-261e16-SNAPSHOT
  2. Operating System (Mac, Linux, Windows) - Linux
  3. APK From? (Playstore, ROM, Other) - Xiaomi store

Stacktrace/Logcat

I: Using Apktool 2.4.0-261e16-SNAPSHOT on com.unionpay.apk
I: Loading resource table...
I: Decoding AndroidManifest.xml with resources...
Exception in thread "main" brut.androlib.AndrolibException: Could not decode XML
        at brut.androlib.res.decoder.XmlPullStreamDecoder.decode(XmlPullStreamDecoder.java:147)
        at brut.androlib.res.decoder.XmlPullStreamDecoder.decodeManifest(XmlPullStreamDecoder.java:153)
        at brut.androlib.res.decoder.ResFileDecoder.decodeManifest(ResFileDecoder.java:155)
        at brut.androlib.res.AndrolibResources.decodeManifestWithResources(AndrolibResources.java:204)
        at brut.androlib.Androlib.decodeManifestWithResources(Androlib.java:136)
        at brut.androlib.ApkDecoder.decode(ApkDecoder.java:122)
        at brut.apktool.Main.cmdDecode(Main.java:164)
        at brut.apktool.Main.main(Main.java:73)
Caused by: java.io.IOException: Expected: 0x00080003, got: 0x00080001
        at brut.util.ExtDataInput.skipCheckInt(ExtDataInput.java:48)
        at brut.androlib.res.decoder.AXmlResourceParser.doNext(AXmlResourceParser.java:855)
        at brut.androlib.res.decoder.AXmlResourceParser.next(AXmlResourceParser.java:102)
        at brut.androlib.res.decoder.AXmlResourceParser.nextToken(AXmlResourceParser.java:112)
        at org.xmlpull.v1.wrapper.classic.XmlPullParserDelegate.nextToken(XmlPullParserDelegate.java:105)
        at brut.androlib.res.decoder.XmlPullStreamDecoder.decode(XmlPullStreamDecoder.java:140)
        ... 7 more

Steps to Reproduce

  1. apktool d com.unionpay.apk

Frameworks

This APK is not from an OEM ROM.

APK

If this APK can be freely shared, please upload/attach a link to it.

Questions to ask before submission

  1. Have you tried apktool d, apktool b without changing anything?
    Yes, the very first step fails.
  2. If you are trying to install a modified apk, did you resign it?
    No, the APK has not been modified.
  3. Are you using the latest apktool version?
    Yes, the very latest I can get from git, 261e163bc9ace48555c515b87662eccb0725a073.

I did some investigation as to why this fails.

According to the aapt source code an AndroidManifest.xml ought to start with a 16 bit RES_XML_TYPE which is 0x0003, followed by a 16 bit size (describing the size of a
struct ResXMLTree_header which is really a struct ResChunk_header which is 8 bytes large, hence should be 0x0008). And then a total size fo the chunk in bytes.

After the initial here there might be StringPool which is created by a call to createStringPool() which calls writeStringBlock() which eventually writes its header consisting of a 16 bit RES_STRING_POOL_TYPE which is 0x0001 followed by a 16 bit size (describing the size of a ResStringPool_header which in total is 28 bytes large, hence should be 0x001C).

apktool's AXmlResourceParser correctly assumes that an AndroidManifest.xml starts with this same 0x0003 followed by 0x0008, however they have been concatenate into a 32bit CHUNK_AXML_FILE with the value 0x00080003. This is then followed by a StringBlock

Now, the AndroidManifest.xml in the APK begins like this

00000000: 01 00 08 00 a4 09 01 00 01 00 1c 00 f4 75 00 00  .............u..
00000010: 71 01 00 00 00 00 00 00 00 00 00 00 e0 05 00 00  q...............
00000020: 00 00 00 00 00 00 00 00 1a 00 00 00 34 00 00 00  ............4...
...
00010990: 18 00 00 00 c2 01 00 00 ff ff ff ff 1f 00 00 00  ................
000109a0: 20 00 00 00                                       ...

The bytes at offset 0 are almost identical with a RES_XML_TYPE followed by a size and a chunk size, but it should begin with 03 00 08 00, not 01 00 08 00. The chunksize of 0x000109a4 also seems reasonable given the size of the file. At offset 8 I do find a RES_STRING_POOL_TYPE followed by a size as it starts with 01 00 1c 00.

This leads me to believe that the AndroidManifest.xml in the downloaded APK is actually faulty, but running unzip -t com.unionpay.apk reports no errors. The APK may have been processed by some tool at or after build time that incorrectly wrote a RES_STRING_POOL_TYPE at the beginning of the file instead of a RES_XML_TYPE. I'm not sure what that tool would be though.

@iBotPeaches

This comment has been minimized.

Copy link
Owner

commented Jan 8, 2019

Thanks for the detailed research and attached PR! I'll do some digging with those magic values and see what I can find.

In the middle of investigating the broken aapt builds for windows, but I'll loop back to this when done.

@iBotPeaches iBotPeaches added this to the 2.4.0 milestone Jan 8, 2019

iBotPeaches added a commit that referenced this issue Jan 9, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
2 participants
You can’t perform that action at this time.