can1357/oh-my-pi · error · Error

Embedded addon size mismatch for ${filename}: expected ${fil

Error message

Embedded addon size mismatch for ${filename}: expected ${file.size}, got ${size}

What it means

The loader cross-checks each archive entry against the embedded manifest: when a pending manifest file declares a numeric size, the tar entry's actual size must match exactly. A mismatch means the archive bytes and the manifest metadata disagree, so writing the entry could produce a corrupt addon; the loader aborts.

Source

Thrown at packages/natives/native/loader-state.js:536

		const size = readTarOctal(header, 124, 12);
		const typeflag = header[156] === 0 ? "0" : String.fromCharCode(header[156]);
		offset += 512;

		if (offset + size > archive.length) {
			throw new Error(`Truncated embedded addon archive entry: ${filename}`);
		}

		if (!isSafeEmbeddedAddonFilename(filename)) {
			throw new Error(`Unsafe embedded addon archive entry: ${filename}`);
		}
		if (typeflag !== "0") {
			throw new Error(`Unsupported embedded addon archive entry type ${typeflag}: ${filename}`);
		}

		const file = pending.get(filename);
		if (file) {
			if (typeof file.size === "number" && file.size !== size) {
				throw new Error(`Embedded addon size mismatch for ${filename}: expected ${file.size}, got ${size}`);
			}
			const targetPath = path.join(targetDir, filename);
			writeEmbeddedAddonFile(targetPath, archive.subarray(offset, offset + size));
			pending.delete(filename);
			writtenPaths.push(targetPath);
		}

		offset += Math.ceil(size / 512) * 512;
	}

	if (pending.size > 0) {
		throw new Error(`Embedded addon archive missing: ${[...pending.keys()].join(", ")}`);
	}

	return writtenPaths;
}

function maybeExtractEmbeddedAddon(ctx, errors) {

View on GitHub (pinned to 9690622007)

Solutions

  1. Rebuild the compiled binary so the manifest and archive are regenerated together from the same artifacts.
  2. Reinstall omp to replace the inconsistent embedded addon data.
  3. If maintaining the packaging script, ensure the manifest's files[].size is computed from the exact bytes packed into the tar.
Defensive patterns

Strategy: validation

Validate before calling

import { execFileSync } from "node:child_process";
function assertManifestSizesMatchArchive(archivePath, files) {
  const listing = execFileSync("tar", ["-tvzf", archivePath], { encoding: "utf8" });
  const sizes = new Map(listing.split("\n").filter(Boolean).map(line => {
    const parts = line.split(/\s+/);
    return [parts[parts.length - 1], Number(parts[2])];
  }));
  for (const f of files) {
    if (typeof f.size === "number" && sizes.get(f.filename) !== f.size) {
      throw new Error(`size mismatch for ${f.filename}`);
    }
  }
}

Try / catch

try {
  extractEmbeddedAddonArchive({ archivePath, files, targetDir });
} catch (err) {
  if (err.message.includes("Embedded addon size mismatch for")) {
    // discard extracted files and force a clean reinstall/re-extract
  } else throw err;
}

Prevention

When it happens

Trigger: extractEmbeddedAddonArchive finds a pending entry (manifest said the on-disk file is missing or stale) whose tar header size differs from file.size in the manifest — e.g. manifest says 1048576 bytes but the tar entry holds 1048500.

Common situations: The embedded .tar.gz and the embedded manifest were generated from different build artifacts (partial/re-run build); the archive was repacked after the manifest was baked; byte-level corruption of the binary.

Related errors


AI-assisted analysis of can1357/oh-my-pi@9690622007 (2026-08-31). Data as JSON: /api/errors/4b68179bdbe61bd2. Report an issue: GitHub.