Tencent/tinker · error · ZipException
STORED entry missing CRC
Error message
STORED entry missing CRC
What it means
For STORED (uncompressed) entries the zip format stores the CRC in the local header before the data, so the writer cannot compute it on the fly. putNextEntry() therefore throws ZipException("STORED entry missing CRC") when the entry's method resolves to STORED and ze.getCrc() == -1. Note that -1 is also the value CRC32 computed for empty input would never legitimately produce, so it doubles as the 'unset' sentinel.
Source
Thrown at third-party/tinker-ziputils/src/main/java/com/tencent/tinker/ziputils/ziputil/TinkerZipOutputStream.java:461
*/
public void putNextEntry(TinkerZipEntry ze) throws IOException {
if (currentEntry != null) {
closeEntry();
}
// Did this ZipEntry specify a method, or should we use the default?
int method = ze.getMethod();
if (method == -1) {
method = defaultCompressionMethod;
}
// If the method is STORED, check that the ZipEntry was configured appropriately.
if (method == STORED) {
if (ze.getCompressedSize() == -1) {
ze.setCompressedSize(ze.getSize());
} else if (ze.getSize() == -1) {
ze.setSize(ze.getCompressedSize());
}
if (ze.getCrc() == -1) {
throw new ZipException("STORED entry missing CRC");
}
if (ze.getSize() == -1) {
throw new ZipException("STORED entry missing size");
}
if (ze.size != ze.compressedSize) {
throw new ZipException("STORED entry size/compressed size mismatch");
}
}
checkOpen();
// checkAndSetZip64Requirements(ze);
//zhangshaowen edit here, we just want the same time and modDate
ze.comment = null;
ze.extra = null;
ze.time = TIME_CONST;
ze.modDate = MOD_DATE_CONST;
nameBytes = ze.name.getBytes(StandardCharsets.UTF_8);View on GitHub (pinned to 1b7ea02c23)
Solutions
- Compute the CRC32 of the entry data first and call ze.setCrc(crc.getValue()) before putNextEntry().
- Also set ze.setSize(len) and ze.setCompressedSize(len) (they must be equal for STORED) to avoid the follow-up exceptions at lines 464/467.
- If you cannot precompute sizes (streaming data of unknown length), use DEFLATED instead of STORED.
Example fix
// before
TinkerZipEntry e = new TinkerZipEntry("res.bin");
e.setMethod(TinkerZipEntry.STORED);
zos.putNextEntry(e); // throws: missing CRC
// after
byte[] data = Files.readAllBytes(path);
CRC32 crc = new CRC32();
crc.update(data);
TinkerZipEntry e = new TinkerZipEntry("res.bin");
e.setMethod(TinkerZipEntry.STORED);
e.setCrc(crc.getValue());
e.setSize(data.length);
e.setCompressedSize(data.length);
zos.putNextEntry(e);
zos.write(data); Defensive patterns
Strategy: validation
Validate before calling
void putStored(TinkerZipOutputStream zos, String name, byte[] data) throws IOException {
if (data == null) throw new IllegalArgumentException("data null for " + name);
CRC32 crc = new CRC32();
crc.update(data);
TinkerZipEntry e = new TinkerZipEntry(name);
e.setMethod(TinkerZipEntry.STORED);
e.setCrc(crc.getValue());
e.setSize(data.length);
e.setCompressedSize(data.length);
zos.putNextEntry(e);
zos.write(data, 0, data.length);
zos.closeEntry();
} Prevention
- Centralize STORED-entry creation in one helper that always sets crc+size+compressedSize
- Never call putNextEntry with method STORED unless all three metadata fields are set
- Prefer DEFLATED for streamed/unknown-length data
When it happens
Trigger: Calling putNextEntry(entry) where entry.setMethod(TinkerZipEntry.STORED) (or the stream's defaultCompressionMethod was set to STORED) without first calling entry.setCrc(...) with a computed CRC32 value.
Common situations: Switching a repack pipeline from DEFLATED to STORED to make entries byte-identical (common in Tinker/Android patch tooling to keep alignment) but forgetting that STORED requires precomputed crc, size, and compressedSize; copying entries from another zip without copying their crc field.
Related errors
- CRC mismatch
- STORED entry missing size
- STORED entry size/compressed size mismatch
- Size mismatch
- Bad CRC32: ${value}
AI-assisted analysis of Tencent/tinker@1b7ea02c23 (2026-08-14).
Data as JSON: /api/errors/af323babaace390d.
Report an issue: GitHub.