Apktool
Apktool copied to clipboard
[BUG] java.lang.StringIndexOutOfBoundsException: String index out of range: 24
Information
- Apktool Version (
apktool -version) - 2.6 - Operating System (Mac, Linux, Windows) - Mac
- APK From? (Playstore, ROM, Other) - Other
Stacktrace/Logcat
Exception in thread "main" java.lang.StringIndexOutOfBoundsException: String index out of range: 24
at java.lang.String.substring(String.java:1963)
at brut.androlib.res.decoder.StringBlock.processStyledString(StringBlock.java:259)
at brut.androlib.res.decoder.StringBlock.getHTML(StringBlock.java:288)
at brut.androlib.res.decoder.ARSCDecoder.readValue(ARSCDecoder.java:366)
at brut.androlib.res.decoder.ARSCDecoder.readEntryData(ARSCDecoder.java:285)
at brut.androlib.res.decoder.ARSCDecoder.readTableType(ARSCDecoder.java:261)
at brut.androlib.res.decoder.ARSCDecoder.readTableTypeSpec(ARSCDecoder.java:184)
at brut.androlib.res.decoder.ARSCDecoder.readTablePackage(ARSCDecoder.java:135)
at brut.androlib.res.decoder.ARSCDecoder.readTableHeader(ARSCDecoder.java:84)
at brut.androlib.res.decoder.ARSCDecoder.decode(ARSCDecoder.java:50)
at brut.androlib.res.AndrolibResources.getResPackagesFromApk(AndrolibResources.java:783)
at brut.androlib.res.AndrolibResources.loadMainPkg(AndrolibResources.java:64)
at brut.androlib.res.AndrolibResources.getResTable(AndrolibResources.java:56)
at brut.androlib.Androlib.getResTable(Androlib.java:70)
at brut.androlib.ApkDecoder.getResTable(ApkDecoder.java:247)
at brut.androlib.ApkDecoder.decode(ApkDecoder.java:109)
at brut.apktool.Main.cmdDecode(Main.java:175)
at brut.apktool.Main.main(Main.java:79)
Questions to ask before submission
- Have you tried
apktool dwithout changing anything? Yes - If you are trying to install a modified apk, did you resign it? Yes
- Are you using the latest apktool version? Yes
- Version 2.5 is working fine but 2.6, 2.6.1 is not.
Can you supply the APK?
Just checking with the team to provide APK, I will upload it in a day or two.
https://drive.google.com/file/d/1iB8XPwSXFBx6pYiThhtNLdy_rYXxgIBj/view?usp=sharing
Thanks for supplying the APK. I could re-produce the issue with apktool version 2.6 and 2.6.1. I could also successfully decode the APK using version 2.5.1:
> Task :brut.apktool:apktool-cli:Main.main()
I: Using Apktool 2.5.1-eec0f4-SNAPSHOT on EmailPlus-ACe-4.1.0.0.74-9.3.0.0.p.apk
I: Loading resource table...
I: Decoding AndroidManifest.xml with resources...
I: Loading resource table from file: C:\Users\Michael\AppData\Local\apktool\framework\1.apk
I: Renamed manifest package found! Replacing forgepond.com.mobileiron.android.emailplus with com.mobileiron.android.emailplus
I: Decoding file-resources...
I: Decoding values */* XMLs...
I: Baksmaling classes.dex...
I: Baksmaling classes2.dex...
I: Baksmaling classes3.dex...
I: Baksmaling classes4.dex...
I: Baksmaling classes5.dex...
I: Copying assets and libs...
I: Copying unknown files...
I: Copying original files...
I: Copying META-INF/services directory
But building again the APK fails:
W: Failed to generate resource table for split ''
W: C:\Users\Michael\git\Apktool\EmailPlus-ACe-4.1.0.0.74-9.3.0.0.p\res\values\bools.xml:25: error: Error: String types not allowed (at 'APKTOOL_DUMMY_b' with value '').
Thanks for checking. May be resolved after https://github.com/iBotPeaches/Apktool/pull/2816 - haven't checked.
Unfortunately not:
> Task :brut.apktool:apktool-cli:Main.main() FAILED
I: Using Apktool 2.6.2-7e71ad-SNAPSHOT on EmailPlus-ACe-4.1.0.0.74-9.3.0.0.p.apk
I: Loading resource table...
Exception in thread "main" java.lang.StringIndexOutOfBoundsException: begin 0, end 24, length 13
at java.base/java.lang.String.checkBoundsBeginEnd(String.java:3734)
at java.base/java.lang.String.substring(String.java:1903)
at brut.androlib.res.decoder.StyledString$Decoder.decodeIterate(StyledString.java:161)
at brut.androlib.res.decoder.StyledString$Decoder.decode(StyledString.java:116)
at brut.androlib.res.decoder.StyledString.toString(StyledString.java:48)
at brut.androlib.res.decoder.StringBlock.getHTML(StringBlock.java:131)
at brut.androlib.res.decoder.ARSCDecoder.readValue(ARSCDecoder.java:393)
at brut.androlib.res.decoder.ARSCDecoder.readEntryData(ARSCDecoder.java:312)
at brut.androlib.res.decoder.ARSCDecoder.readTableType(ARSCDecoder.java:288)
at brut.androlib.res.decoder.ARSCDecoder.readTableTypeSpec(ARSCDecoder.java:211)
at brut.androlib.res.decoder.ARSCDecoder.readTablePackage(ARSCDecoder.java:132)
at brut.androlib.res.decoder.ARSCDecoder.readTableHeader(ARSCDecoder.java:84)
at brut.androlib.res.decoder.ARSCDecoder.decode(ARSCDecoder.java:50)
at brut.androlib.res.AndrolibResources.getResPackagesFromApk(AndrolibResources.java:787)
at brut.androlib.res.AndrolibResources.loadMainPkg(AndrolibResources.java:64)
at brut.androlib.res.AndrolibResources.getResTable(AndrolibResources.java:56)
at brut.androlib.Androlib.getResTable(Androlib.java:74)
at brut.androlib.ApkDecoder.getResTable(ApkDecoder.java:247)
at brut.androlib.ApkDecoder.decode(ApkDecoder.java:109)
at brut.apktool.Main.cmdDecode(Main.java:175)
at brut.apktool.Main.main(Main.java:79)
Confirmed. The rewritten string/style decoder bites again.
「%1$s」「 %2$s」
This string has style information of a u tag starting at 0, ending at 23. text.length() is only reporting 13. Not quite sure what is happening here yet. It must be the encoded span information is miscounting character length and maybe like byte length? Or maybe the Java length counts when you are messing with CESU-8, UTF-8 and UTF-16 is leading to some oddities.
So there is a hacky workaround by just checking if the span end is within the length of the string and proceeding with a same subset value. However, this is easy to see in this specific circumstance, but may lead to bugged strings in greater picture.
I wrote a little debug helper to dump out these strings that violated this.
I: Using Apktool v2.8.1-37-50226e50-SNAPSHOT on 2829.apk
I: Loading resource table...
W: Span brut.androlib.res.decoder.StyledString$Span@49798e84 exceeds text length 13
W: Span brut.androlib.res.decoder.StyledString$Span@6ed06f69 exceeds text length 11
W: Span brut.androlib.res.decoder.StyledString$Span@3015db78 exceeds text length 11
W: Span brut.androlib.res.decoder.StyledString$Span@515ebef3 exceeds text length 11
W: Span brut.androlib.res.decoder.StyledString$Span@6a2eea2a exceeds text length 13
W: Span brut.androlib.res.decoder.StyledString$Span@b967222 exceeds text length 11
W: Span brut.androlib.res.decoder.StyledString$Span@3b0ee03a exceeds text length 11
It does look right when decoded now
res/values-ja/strings.xml: <string name="multiple_new_message_notification_item"><u>「%1$s」「 %2$s」</u></string>
So I grabbed the original and rebuilt string.
So what we built and the original match 1-1. So I believe we can find a tweak the encoder to take the remaining string after the offset if our ending offset exceeds the length of the string.
So I've got a draft up and working to see if I can make some tests for this - https://github.com/iBotPeaches/Apktool/pull/3254