iBotPeaches/Apktool · critical · IOException
Unexpected chunk:
Error message
Unexpected chunk:
What it means
BinaryXmlResourceParser requires the first chunk of its input to be RES_XML_TYPE (0x0003). Any other leading chunk type throws this error, naming the offending chunk — the usual meaning is 'this file is not compiled binary XML'.
Source
Thrown at brut.apktool/apktool-lib/src/main/java/brut/androlib/res/decoder/BinaryXmlResourceParser.java:119
public void setInput(Reader in) throws XmlPullParserException {
throw new XmlPullParserException(NOT_SUPPORTED);
}
@Override
public void setInput(InputStream inputStream, String inputEncoding) throws XmlPullParserException {
if (inputEncoding != null) {
throw new XmlPullParserException(NOT_SUPPORTED);
}
reset();
mIn = new BinaryDataInputStream(new BufferedInputStream(inputStream));
mParser = new ResChunkPullParser(mIn);
try {
if (!nextChunk()) {
throw new IOException("Input file is empty.");
}
if (mParser.chunkType() != ResChunkHeader.RES_XML_TYPE) {
throw new IOException("Unexpected chunk: " + mParser.chunkName() + " (expected: RES_XML_TYPE)");
}
} catch (IOException ex) {
mIn = null;
mParser = null;
throw new XmlPullParserException("Could not initialize parser.", this, ex);
}
mParser = new ResChunkPullParser(mIn, mParser.dataSize());
}
@Override
public String getInputEncoding() {
return null;
}
@Override
public void defineEntityReplacementText(String entityName, String replacementText) throws XmlPullParserException {
throw new XmlPullParserException(NOT_SUPPORTED);View on GitHub (pinned to 79b63384d7)
Solutions
- Check the first two bytes: 0x0003 = binary XML, 0x0002 = resource table, '<' (0x3C) = plain text XML.
- If the file is plain text XML, parse it with a standard XmlPullParser instead — it never needed the binary parser.
- If it should be AXML but isn't, the APK build/extract step is broken — recompile with aapt2 or re-extract.
- For plain XML inside an APK from a non-standard packager, pre-detect the magic and route to the right parser.
Example fix
// before
parser.setInput(in, null); // throws if `in` is plain-text XML
// after
PushbackInputStream pb = new PushbackInputStream(in, 2);
int b0 = pb.read(), b1 = pb.read();
if (b0 == 0x03 && b1 == 0x00) {
pb.unread(b1); pb.unread(b0);
binParser.setInput(pb, null);
} else {
pb.unread(b1); pb.unread(b0);
textParser.setInput(pb, null); // plain-text XML path
} Defensive patterns
Strategy: validation
Validate before calling
byte[] magic = new byte[2];
try (InputStream s = new FileInputStream(xmlFile)) { s.read(magic); }
boolean isBinaryXml = (magic[0] & 0xFF) == 0x03 && magic[1] == 0x00;
boolean isPlainText = magic[0] == '<';
if (!isBinaryXml) {
// route to a standard text XmlPullParser if isPlainText, else reject
} Try / catch
try {
binParser.setInput(in, null);
} catch (XmlPullParserException e) {
if (String.valueOf(e.getCause()).contains("Unexpected chunk")) {
// wrong parser for this file — check magic and reroute
}
} Prevention
- Sniff first bytes to choose binary vs text parser.
- Don't assume all XML inside an APK is compiled AXML.
When it happens
Trigger: Feeding the AXML parser a plain-text XML file (not compiled), an arsc (starts with 0x0002), or any non-AXML binary. Also fires on AXML files whose header was corrupted.
Common situations: Parsing XML that was never compiled with aapt/aapt2 (source res XML); mixed-up streams in extraction code; tools that store plain XML in APKs (some non-standard build chains); hex-corrupted manifest files.
Related errors
- Input file is empty.
- Unexpected chunk:
- Could not initialize parser.
- Input file is empty.
- Could not decode arsc file.
AI-assisted analysis of iBotPeaches/Apktool@79b63384d7 (2026-08-14).
Data as JSON: /api/errors/ce623fcbc50c8f08.
Report an issue: GitHub.