{"record":{"id":"f822e2a15e1fcf7d","repo":"paperclipai/paperclip","slug":"heif-box-exceeds-file-bounds","errorCode":null,"errorMessage":"HEIF box exceeds file bounds","messagePattern":"HEIF box exceeds file bounds","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"server/src/services/photon/media.ts","lineNumber":33,"sourceCode":"/** Validate bounded ISO-BMFF structure before invoking any native decoder. */\nexport function validateHeifDimensions(body: Buffer): void {\n  let boxes = 0;\n  let dimensions = 0;\n  let totalPixels = 0;\n  let branded = false;\n  const visit = (start: number, end: number, depth: number) => {\n    if (depth > 8) throw new Error(\"HEIF metadata nesting is too deep\");\n    for (let at = start; at < end; ) {\n      if (++boxes > 4096 || end - at < 8)\n        throw new Error(\"Invalid HEIF box structure\");\n      let size = body.readUInt32BE(at);\n      const type = body.toString(\"ascii\", at + 4, at + 8);\n      let header = 8;\n      if (size === 1) {\n        if (end - at < 16) throw new Error(\"Invalid HEIF box length\");\n        const extended = body.readBigUInt64BE(at + 8);\n        if (extended > BigInt(body.length))\n          throw new Error(\"HEIF box exceeds file bounds\");\n        size = Number(extended);\n        header = 16;\n      } else if (size === 0) size = end - at;\n      if (size < header || at + size > end)\n        throw new Error(\"HEIF box exceeds file bounds\");\n      const content = at + header;\n      if (type === \"ftyp\") {\n        if (size < header + 8) throw new Error(\"HEIF file type is missing\");\n        const brands = body.toString(\"ascii\", content, at + size);\n        branded = /heic|heix|hevc|hevx|mif1|msf1/.test(brands);\n      } else if (type === \"ispe\") {\n        if (size !== header + 12)\n          throw new Error(\"Invalid HEIF image dimensions\");\n        const width = body.readUInt32BE(content + 4);\n        const height = body.readUInt32BE(content + 8);\n        if (\n          !width ||\n          !height ||","sourceCodeStart":15,"sourceCodeEnd":51,"githubUrl":"https://github.com/paperclipai/paperclip/blob/3f1d897a7c018d76563a21c6e39c3c9b03933622/server/src/services/photon/media.ts#L15-L51","documentation":"The ISO-BMFF walker validates every box's size: with a standard header a box must be at least 8 bytes, and the box must not extend past the end of its container range (at + size > end). Violating either throws \"HEIF box exceeds file bounds\". For extended-size boxes this also fires when the 64-bit largesize exceeds the whole buffer (media.ts:32-33, 37-38).","triggerScenarios":"Any box whose declared size is smaller than its header or whose at+size exceeds the enclosing container end; or an extended (largesize) box whose 64-bit size is greater than the total buffer length.","commonSituations":"Corrupted or maliciously crafted HEIC claiming absurd sizes (classic parser-overflow pattern); truncated download where a parent container's declared size exceeds the bytes received; bit rot in stored files.","solutions":["Treat the file as corrupt/malicious and reject it; obtain a fresh copy and re-upload.","Verify integrity: compare checksums if the source provides them; run `ffprobe` locally.","Re-export the image from the original app (e.g. Photos export) instead of repairing bytes.","Keep the guard in place — it protects native decoders from out-of-bounds reads."],"exampleFix":"// before: heic whose mdat declares size beyond EOF\n// after: re-export the image\nheif-convert good.heic out.jpg  # verify a known-good copy first","handlingStrategy":"validation","validationCode":"function boxWithinBounds(buf: Buffer, at: number, size: number, header: number, end: number): boolean {\n  return size >= header && at + size <= end;\n}","typeGuard":"function isBoundedBox(b: Buffer, extendedSize: bigint): boolean {\n  return extendedSize <= BigInt(b.length);\n}","tryCatchPattern":"try {\n  validateHeifDimensions(body);\n} catch (e) {\n  if (e instanceof Error && e.message === \"HEIF box exceeds file bounds\") {\n    return rejectUpload(\"HEIF declares boxes beyond the file; file is corrupt or hostile\");\n  }\n  throw e;\n}","preventionTips":["Never process user HEIFs with parsers that lack bound checks — keep validateHeifDimensions in front of native decoders.","Verify file integrity (checksum) for machine-to-machine transfers.","Re-export images rather than attempting byte-level repair.","Quarantine files that trigger bound errors; repeated hits suggest malicious traffic."],"tags":["heif","isobmff","malformed-file","security"],"backgroundTag":"invalid-argument-format","analyzedSha":"3f1d897a7c018d76563a21c6e39c3c9b03933622","analyzedAt":"2026-09-18T08:03:59.046Z","contentChangedAt":"2026-09-18T08:03:59.046Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}