can1357/oh-my-pi · error · ArchiveError
Unsupported CAB compression method: ${description.method}
Error message
Unsupported CAB compression method: ${description.method} What it means
Any CFFOLDER compression method value greater than 3 is unknown to this library (known: 0=none, 1=deflate, 2=quantum, 3=LZX), so #decode refuses it rather than guessing. This usually means the archive is corrupt or uses a proprietary/undocumented method code. The raw method number is included in the message for diagnosis.
Source
Thrown at packages/utils/src/ar/cab.ts:133
constructor(source: ByteSource, description: CabFolderDescription, dataReserveSize: number, limits: ArchiveLimits) {
this.#source = source;
this.#description = description;
this.#dataReserveSize = dataReserveSize;
this.#limits = limits;
}
readAll(): Promise<Uint8Array> {
this.#decoded ??= this.#decode();
return this.#decoded;
}
async #decode(): Promise<Uint8Array> {
const description = this.#description;
if (description.method === 2) {
throw new ArchiveError(`Unsupported CAB compression method: Quantum (level ${description.parameter})`);
}
if (description.method > 3) {
throw new ArchiveError(`Unsupported CAB compression method: ${description.method}`);
}
if (description.method === 3 && (description.parameter < 15 || description.parameter > 21)) {
throw new ArchiveError(`Unsupported CAB LZX window size: ${description.parameter} bits (expected 15-21)`);
}
const compressedSize = description.dataEnd - description.dataStart;
assertInMemorySize(compressedSize, this.#limits);
const bytes = await readExact(this.#source, description.dataStart, description.dataEnd);
let position = 0;
let outputSize = 0;
for (let block = 0; block < description.blockCount; block++) {
if (position + DATA_BLOCK_SIZE + this.#dataReserveSize > bytes.byteLength) {
throw new ArchiveError("Invalid CAB archive: truncated CFDATA header");
}
const compressed = readUInt16LE(bytes, position + 4);
const uncompressed = readUInt16LE(bytes, position + 6);
if (uncompressed === 0) throw new ArchiveError("Unsupported multi-volume CAB archive: split CFDATA block");
if (uncompressed > MAX_DATA_OUTPUT) {View on GitHub (pinned to 9690622007)
Solutions
- Log the reported method number and check it against the CAB spec; if it is far beyond 3, suspect corruption — re-download/re-copy the archive.
- Validate the archive with `cabextract -t file.cab` to distinguish real unsupported methods from header corruption.
- Re-create the CAB with a standard tool using Deflate (method 1) or LZX (method 3).
- If the input is user-supplied, add an upfront signature/structure sanity check and reject such files with a clear message before invoking readAll().
- If the method is genuinely needed, extend the decoder with a new branch (as done for LZX) rather than letting it fall into this error.
Example fix
// before: trusting arbitrary uploaded .cab files
await readCabArchive(userUpload); // Unsupported CAB compression method: 17
// after: pre-validate structure with an independent tool or reject early
if (!looksLikeValidCab(await Bun.file(uploadPath).arrayBuffer()))
throw new Error('Not a structurally valid CAB file');
await readCabArchive(userUpload); Defensive patterns
Strategy: validation
Validate before calling
const method = readFolderCompressionMethod(cabBytes);
if (method === undefined || method > 3)
throw new Error(`CAB folder has unknown compression method ${method} — file is corrupt or nonstandard`); Type guard
function isKnownCabMethod(m: number | undefined): m is 0 | 1 | 2 | 3 {
return m !== undefined && m >= 0 && m <= 3;
} Try / catch
try {
return await readCabArchive(bytes);
} catch (err) {
if (err instanceof ArchiveError && /compression method: \d+$/.test(err.message)) {
throw new Error('Unknown CAB compression method — verify the archive is not corrupted');
}
throw err;
} Prevention
- Validate CAB structure at ingestion boundaries for user-supplied files.
- Re-checksum transferred CABs; method bytes are small and easily corrupted.
- Only produce CABs with mainstream tooling (makecab, lcab).
- Treat unknown method values as corruption, not as a feature gap.
When it happens
Trigger: readAll() on a CAB whose folder typeCompress field contains a value > 3 — from corruption, a maliciously crafted file, or a nonstandard producer writing custom method codes.
Common situations: Hand-crafted or fuzzed CAB inputs; corrupted headers where adjacent bytes bled into typeCompress; proprietary archivers that abused reserved method fields; wrong endianness assumptions in files produced by buggy tools.
Related errors
- Unsupported CAB compression method: Quantum (level ${descrip
- Unsupported CAB LZX window size: ${description.parameter} bi
- Invalid CAB archive: truncated data
- Invalid CAB archive: file has an invalid DOS timestamp
- Unsupported multi-volume CAB archive: split CFDATA block
AI-assisted analysis of can1357/oh-my-pi@9690622007 (2026-08-31).
Data as JSON: /api/errors/06e06d29e06d8e07.
Report an issue: GitHub.