pompelmi 0.35.0 → 0.35.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +55 -87
- package/dist/pompelmi.browser.cjs +45 -58
- package/dist/pompelmi.browser.cjs.map +1 -1
- package/dist/pompelmi.browser.esm.js +45 -58
- package/dist/pompelmi.browser.esm.js.map +1 -1
- package/dist/pompelmi.cjs +52 -61
- package/dist/pompelmi.cjs.map +1 -1
- package/dist/pompelmi.esm.js +52 -61
- package/dist/pompelmi.esm.js.map +1 -1
- package/dist/pompelmi.react.cjs +45 -58
- package/dist/pompelmi.react.cjs.map +1 -1
- package/dist/pompelmi.react.esm.js +45 -58
- package/dist/pompelmi.react.esm.js.map +1 -1
- package/package.json +2 -2
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"pompelmi.browser.cjs","sources":["../../src/policy.ts","../../src/policy-packs.ts","../../src/scanners/common-heuristics.ts","../../src/presets.ts","../../src/utils/advanced-detection.ts","../../src/utils/cache-manager.ts","../../src/utils/performance-metrics.ts","../../src/scan.ts","../../src/scanners/zip-bomb-guard.ts","../../src/utils/export.ts","../../src/validate.ts","../../src/verdict.ts"],"sourcesContent":["export interface Policy {\n includeExtensions: string[];\n allowedMimeTypes: string[];\n maxFileSizeBytes: number;\n timeoutMs: number;\n concurrency: number;\n failClosed: boolean;\n onScanEvent?: (ev: unknown) => void;\n}\nexport type PolicyInput = Partial<Policy>;\n\nconst MB = 1024 * 1024;\n\nexport const DEFAULT_POLICY: Policy = {\n includeExtensions: [\"zip\", \"png\", \"jpg\", \"jpeg\", \"pdf\"],\n allowedMimeTypes: [\"application/zip\", \"image/png\", \"image/jpeg\", \"application/pdf\", \"text/plain\"],\n maxFileSizeBytes: 20 * MB,\n timeoutMs: 5000,\n concurrency: 4,\n failClosed: true,\n};\n\nexport function definePolicy(input: PolicyInput = {}): Policy {\n const p: Policy = { ...DEFAULT_POLICY, ...input };\n if (!Array.isArray(p.includeExtensions))\n throw new TypeError(\"includeExtensions must be string[]\");\n if (!Array.isArray(p.allowedMimeTypes)) throw new TypeError(\"allowedMimeTypes must be string[]\");\n if (!(Number.isFinite(p.maxFileSizeBytes) && p.maxFileSizeBytes > 0))\n throw new TypeError(\"maxFileSizeBytes must be > 0\");\n if (!(Number.isFinite(p.timeoutMs) && p.timeoutMs > 0))\n throw new TypeError(\"timeoutMs must be > 0\");\n if (!(Number.isInteger(p.concurrency) && p.concurrency > 0))\n throw new TypeError(\"concurrency must be > 0\");\n return p;\n}\n","/**\n * Policy packs for Pompelmi.\n *\n * Pre-configured, named policies for common upload scenarios. Each pack\n * defines the file type allowlist, size limits, and timeout appropriate for\n * its use case.\n *\n * All packs are built on `definePolicy` and are fully overridable:\n *\n * ```ts\n * import { POLICY_PACKS } from 'pompelmi/policy-packs';\n *\n * // Use a pack as-is:\n * const policy = POLICY_PACKS['images-only'];\n *\n * // Or override individual fields:\n * import { definePolicy } from 'pompelmi';\n * const custom = definePolicy({ ...POLICY_PACKS['documents-only'], maxFileSizeBytes: 5 * 1024 * 1024 });\n * ```\n *\n * These packs are *deterministic* and *descriptor-based* — they do not\n * depend on any external threat intelligence feed.\n *\n * @module policy-packs\n */\n\nimport { definePolicy, type Policy } from \"./policy\";\n\nconst KB = 1024;\nconst MB = 1024 * KB;\n\n// ── Policy packs ──────────────────────────────────────────────────────────────\n\n/**\n * Documents-only policy.\n *\n * Appropriate for: document management APIs, PDF/Office file upload endpoints,\n * data import pipelines.\n *\n * Allowed: PDF, Word (.docx/.doc), Excel (.xlsx/.xls), PowerPoint (.pptx/.ppt),\n * CSV, plain text, JSON, YAML, ODT/ODS/ODP (OpenDocument).\n * Max size: 25 MB.\n */\nexport const DOCUMENTS_ONLY: Policy = definePolicy({\n includeExtensions: [\n \"pdf\",\n \"doc\",\n \"docx\",\n \"xls\",\n \"xlsx\",\n \"ppt\",\n \"pptx\",\n \"odt\",\n \"ods\",\n \"odp\",\n \"csv\",\n \"txt\",\n \"json\",\n \"yaml\",\n \"yml\",\n \"md\",\n ],\n allowedMimeTypes: [\n \"application/pdf\",\n \"application/msword\",\n \"application/vnd.openxmlformats-officedocument.wordprocessingml.document\",\n \"application/vnd.ms-excel\",\n \"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet\",\n \"application/vnd.ms-powerpoint\",\n \"application/vnd.openxmlformats-officedocument.presentationml.presentation\",\n \"application/vnd.oasis.opendocument.text\",\n \"application/vnd.oasis.opendocument.spreadsheet\",\n \"application/vnd.oasis.opendocument.presentation\",\n \"text/csv\",\n \"text/plain\",\n \"application/json\",\n \"text/yaml\",\n \"text/markdown\",\n ],\n maxFileSizeBytes: 25 * MB,\n timeoutMs: 10_000,\n concurrency: 4,\n failClosed: true,\n});\n\n/**\n * Images-only policy.\n *\n * Appropriate for: avatar uploads, product image APIs, content platforms with\n * user-generated imagery.\n *\n * Allowed: JPEG, PNG, GIF, WebP, AVIF, TIFF, BMP, ICO.\n * Max size: 10 MB.\n * Note: SVG is intentionally excluded — inline SVGs can contain scripts.\n */\nexport const IMAGES_ONLY: Policy = definePolicy({\n includeExtensions: [\"jpg\", \"jpeg\", \"png\", \"gif\", \"webp\", \"avif\", \"tiff\", \"tif\", \"bmp\", \"ico\"],\n allowedMimeTypes: [\n \"image/jpeg\",\n \"image/png\",\n \"image/gif\",\n \"image/webp\",\n \"image/avif\",\n \"image/tiff\",\n \"image/bmp\",\n \"image/x-icon\",\n \"image/vnd.microsoft.icon\",\n ],\n maxFileSizeBytes: 10 * MB,\n timeoutMs: 5_000,\n concurrency: 8,\n failClosed: true,\n});\n\n/**\n * Strict public-upload policy.\n *\n * Appropriate for: anonymous or low-trust upload endpoints, public APIs,\n * any surface exposed to untrusted users.\n *\n * Aggressive size limit (5 MB), short timeout, fail-closed, narrow MIME\n * allowlist. Only allows plain images and PDF.\n */\nexport const STRICT_PUBLIC_UPLOAD: Policy = definePolicy({\n includeExtensions: [\"jpg\", \"jpeg\", \"png\", \"webp\", \"pdf\"],\n allowedMimeTypes: [\"image/jpeg\", \"image/png\", \"image/webp\", \"application/pdf\"],\n maxFileSizeBytes: 5 * MB,\n timeoutMs: 4_000,\n concurrency: 2,\n failClosed: true,\n});\n\n/**\n * Conservative default policy.\n *\n * A hardened version of the built-in `DEFAULT_POLICY` suitable for\n * production without further customisation. Stricter size limit and\n * shorter timeout than the permissive default.\n */\nexport const CONSERVATIVE_DEFAULT: Policy = definePolicy({\n includeExtensions: [\"zip\", \"png\", \"jpg\", \"jpeg\", \"pdf\", \"txt\", \"csv\", \"docx\", \"xlsx\"],\n allowedMimeTypes: [\n \"application/zip\",\n \"image/png\",\n \"image/jpeg\",\n \"application/pdf\",\n \"text/plain\",\n \"text/csv\",\n \"application/vnd.openxmlformats-officedocument.wordprocessingml.document\",\n \"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet\",\n ],\n maxFileSizeBytes: 10 * MB,\n timeoutMs: 8_000,\n concurrency: 4,\n failClosed: true,\n});\n\n/**\n * Archives policy.\n *\n * Appropriate for: endpoints that accept ZIP, tar, or compressed archives.\n * Combines a generous size allowance with a longer timeout for deep inspection.\n *\n * NOTE: Pair this policy with `createZipBombGuard()` to defend against\n * decompression-bomb attacks:\n *\n * ```ts\n * import { composeScanners, createZipBombGuard, CommonHeuristicsScanner } from 'pompelmi';\n * const scanner = composeScanners(\n * [['zipGuard', createZipBombGuard()], ['heuristics', CommonHeuristicsScanner]]\n * );\n * ```\n */\nexport const ARCHIVES: Policy = definePolicy({\n includeExtensions: [\"zip\", \"tar\", \"gz\", \"tgz\", \"bz2\", \"xz\", \"7z\", \"rar\"],\n allowedMimeTypes: [\n \"application/zip\",\n \"application/x-tar\",\n \"application/gzip\",\n \"application/x-bzip2\",\n \"application/x-xz\",\n \"application/x-7z-compressed\",\n \"application/x-rar-compressed\",\n ],\n maxFileSizeBytes: 100 * MB,\n timeoutMs: 30_000,\n concurrency: 2,\n failClosed: true,\n});\n\n// ── Named map ────────────────────────────────────────────────────────────────\n\nexport type PolicyPackName =\n | \"documents-only\"\n | \"images-only\"\n | \"strict-public-upload\"\n | \"conservative-default\"\n | \"archives\";\n\n/**\n * Named map of all built-in policy packs.\n *\n * ```ts\n * import { POLICY_PACKS } from 'pompelmi/policy-packs';\n * const policy = POLICY_PACKS['strict-public-upload'];\n * ```\n */\nexport const POLICY_PACKS: Record<PolicyPackName, Policy> = {\n \"documents-only\": DOCUMENTS_ONLY,\n \"images-only\": IMAGES_ONLY,\n \"strict-public-upload\": STRICT_PUBLIC_UPLOAD,\n \"conservative-default\": CONSERVATIVE_DEFAULT,\n archives: ARCHIVES,\n};\n\n/**\n * Look up a policy pack by name.\n * Throws if the name is not recognised.\n */\nexport function getPolicyPack(name: PolicyPackName): Policy {\n const policy = POLICY_PACKS[name];\n if (!policy)\n throw new Error(\n `Unknown policy pack: '${name}'. Valid names: ${Object.keys(POLICY_PACKS).join(\", \")}`,\n );\n return policy;\n}\n","/**\n * CommonHeuristicsScanner\n * Lightweight, no-deps heuristics for common risky file patterns.\n * Returns matches as [{ rule, severity?, meta? }].\n */\nexport type HeuristicMatch = {\n rule: string;\n severity?: \"info\" | \"low\" | \"medium\" | \"high\" | \"critical\" | \"suspicious\" | \"malicious\";\n meta?: Record<string, unknown>;\n};\n\nexport interface SimpleScanner {\n scan(bytes: Uint8Array): Promise<HeuristicMatch[]>;\n}\n\nfunction hasAsciiToken(buf: Buffer, token: string): boolean {\n // Use latin1 so we can safely search binary\n return buf.indexOf(token, 0, \"latin1\") !== -1;\n}\nfunction startsWith(buf: Buffer, bytes: number[]): boolean {\n if (buf.length < bytes.length) return false;\n for (let i = 0; i < bytes.length; i++) if (buf[i] !== bytes[i]) return false;\n return true;\n}\n\nfunction isPDF(buf: Buffer): boolean {\n // %PDF-\n return startsWith(buf, [0x25, 0x50, 0x44, 0x46, 0x2d]);\n}\nfunction isOleCfb(buf: Buffer): boolean {\n // D0 CF 11 E0 A1 B1 1A E1\n const sig = [0xd0, 0xcf, 0x11, 0xe0, 0xa1, 0xb1, 0x1a, 0xe1];\n return startsWith(buf, sig);\n}\nfunction isZipLike(buf: Buffer): boolean {\n // PK\\x03\\x04\n return startsWith(buf, [0x50, 0x4b, 0x03, 0x04]);\n}\nfunction isPeExecutable(buf: Buffer): boolean {\n // \"MZ\"\n return startsWith(buf, [0x4d, 0x5a]);\n}\n\n/** OOXML macro hint via filename token in ZIP container */\nfunction hasOoxmlMacros(buf: Buffer): boolean {\n if (!isZipLike(buf)) return false;\n return hasAsciiToken(buf, \"vbaProject.bin\");\n}\n\n/** PDF risky features (/JavaScript, /OpenAction, /AA, /Launch) */\nfunction pdfRiskTokens(buf: Buffer): string[] {\n const tokens = [\"/JavaScript\", \"/OpenAction\", \"/AA\", \"/Launch\"];\n return tokens.filter((t) => hasAsciiToken(buf, t));\n}\n\nexport const CommonHeuristicsScanner: SimpleScanner = {\n async scan(input: Uint8Array) {\n const buf = Buffer.from(input);\n const matches: HeuristicMatch[] = [];\n\n // Office macros (OLE / OOXML)\n if (isOleCfb(buf)) {\n matches.push({ rule: \"office_ole_container\", severity: \"suspicious\" });\n }\n if (hasOoxmlMacros(buf)) {\n matches.push({ rule: \"office_ooxml_macros\", severity: \"suspicious\" });\n }\n\n // PDF risky tokens\n if (isPDF(buf)) {\n const toks = pdfRiskTokens(buf);\n if (toks.length) {\n matches.push({\n rule: \"pdf_risky_actions\",\n severity: \"suspicious\",\n meta: { tokens: toks },\n });\n }\n }\n\n // Executable header\n if (isPeExecutable(buf)) {\n matches.push({ rule: \"pe_executable_signature\", severity: \"suspicious\" });\n }\n\n // EICAR test file\n const EICAR_NEEDLE = \"X5O!P%@AP[4\\\\PZX54(P^)7CC)7}$EICAR-STANDARD-ANTIVIRUS-TEST-FILE!\";\n if (hasAsciiToken(buf, EICAR_NEEDLE)) {\n matches.push({\n rule: \"eicar_test_file\",\n severity: \"high\",\n meta: { note: \"EICAR standard antivirus test file detected\" },\n });\n }\n\n return matches;\n },\n};\n","import { CommonHeuristicsScanner } from \"./scanners/common-heuristics\";\nimport type { AnalysisDepth, DecompilationScanner, Match, ScanFn, Scanner, Verdict } from \"./types\";\n\nexport type PresetName =\n | \"basic\"\n | \"advanced\"\n | \"malware-analysis\"\n | \"decompilation-basic\"\n | \"decompilation-deep\"\n | string;\n\nexport interface PresetOptions {\n // YARA options\n yaraRules?: string | string[];\n yaraTimeout?: number;\n\n // Decompilation options\n enableDecompilation?: boolean;\n decompilationEngine?: \"binaryninja-hlil\" | \"ghidra-pcode\" | \"both\";\n decompilationDepth?: AnalysisDepth;\n decompilationTimeout?: number;\n\n // Binary Ninja specific\n binaryNinjaPath?: string;\n pythonPath?: string;\n\n // Ghidra specific\n ghidraPath?: string;\n analyzeHeadless?: string;\n\n // General options\n timeout?: number;\n [key: string]: unknown;\n}\n\n/**\n * A named scanner entry used with the array form of `composeScanners`.\n * The first element is a display name for the scanner (used when\n * `tagSourceName: true`), and the second element is the scanner itself.\n *\n * @example\n * const entry: NamedScanner = ['zipGuard', createZipBombGuard({ ... })];\n */\nexport type NamedScanner = [name: string, scanner: Scanner];\n\n/**\n * Options for `composeScanners` when using the named-scanner array form.\n */\nexport interface ComposeScannerOptions {\n /**\n * When `true` scanners run concurrently (Promise.all).\n * When `false` (default) they run sequentially in order.\n */\n parallel?: boolean;\n /**\n * Stop scanning as soon as a match at this severity level (or higher) is\n * found. Severity order: `'malicious'` > `'suspicious'` > `'clean'`.\n * Only effective when `parallel` is `false`.\n */\n stopOn?: Verdict;\n /** Maximum time in milliseconds to wait for each individual scanner. */\n timeoutMsPerScanner?: number;\n /**\n * When `true`, each match is tagged with the scanner's display name via\n * `match.meta._sourceName`. Useful for tracing which scanner produced a\n * given result.\n */\n tagSourceName?: boolean;\n}\n\nfunction toScanFn(s: Scanner): (input: any, ctx?: any) => Promise<Match[]> {\n return (typeof s === \"function\" ? s : s.scan) as (input: any, ctx?: any) => Promise<Match[]>;\n}\n\n/** Map a Match's severity field to a Verdict for stopOn comparison. */\nfunction matchToVerdict(m: Match): Verdict {\n const s = m.severity;\n if (s === \"critical\" || s === \"high\" || s === \"malicious\") return \"malicious\";\n if (s === \"medium\" || s === \"low\" || s === \"suspicious\" || s === \"info\") return \"suspicious\";\n return \"clean\";\n}\n\n/** Highest verdict across all matches in the list. */\nfunction highestSeverity(matches: Match[]): Verdict | null {\n if (matches.length === 0) return null;\n if (matches.some((m) => matchToVerdict(m) === \"malicious\")) return \"malicious\";\n if (matches.some((m) => matchToVerdict(m) === \"suspicious\")) return \"suspicious\";\n return \"clean\";\n}\n\nconst SEVERITY_RANK: Record<Verdict, number> = { malicious: 2, suspicious: 1, clean: 0 };\n\nfunction shouldStop(matches: Match[], stopOn: Verdict | undefined): boolean {\n if (!stopOn) return false;\n const highest = highestSeverity(matches);\n if (!highest) return false;\n return SEVERITY_RANK[highest] >= SEVERITY_RANK[stopOn];\n}\n\nasync function runWithTimeout<T>(fn: () => Promise<T>, timeoutMs: number | undefined): Promise<T> {\n if (!timeoutMs) return fn();\n return new Promise<T>((resolve, reject) => {\n const timer = setTimeout(() => reject(new Error(\"scanner timeout\")), timeoutMs);\n fn().then(\n (v) => {\n clearTimeout(timer);\n resolve(v);\n },\n (e) => {\n clearTimeout(timer);\n reject(e);\n },\n );\n });\n}\n\n/**\n * Compose multiple scanners into a single scanner.\n *\n * **Named-scanner array form** (recommended — matches the README examples):\n * ```ts\n * const scanner = composeScanners(\n * [\n * ['zipGuard', createZipBombGuard({ maxEntries: 512, maxCompressionRatio: 12 })],\n * ['heuristics', CommonHeuristicsScanner],\n * ],\n * { parallel: false, stopOn: 'malicious', timeoutMsPerScanner: 5000, tagSourceName: true }\n * );\n * ```\n *\n * **Variadic form** (backward-compatible):\n * ```ts\n * const scanner = composeScanners(scannerA, scannerB, scannerC);\n * ```\n */\nexport function composeScanners(\n namedScanners: NamedScanner[],\n opts?: ComposeScannerOptions,\n): ScanFn;\nexport function composeScanners(...scanners: Scanner[]): ScanFn;\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\nexport function composeScanners(...args: any[]): ScanFn {\n const first: NamedScanner[] | Scanner = args[0];\n const rest: Array<Scanner | ComposeScannerOptions> = args.slice(1);\n // ── Named-scanner array form ──────────────────────────────────────────────\n if (\n Array.isArray(first) &&\n (first.length === 0 || (Array.isArray(first[0]) && typeof first[0][0] === \"string\"))\n ) {\n const entries = first as NamedScanner[];\n const opts: ComposeScannerOptions =\n rest.length > 0 &&\n !Array.isArray(rest[0]) &&\n typeof rest[0] !== \"function\" &&\n !(typeof rest[0] === \"object\" && rest[0] !== null && \"scan\" in (rest[0] as object))\n ? (rest[0] as ComposeScannerOptions)\n : {};\n\n return async (input: any, ctx?: any) => {\n const all: Match[] = [];\n\n if (opts.parallel) {\n // Parallel execution — collect all results then return\n const results = await Promise.allSettled(\n entries.map(([name, scanner]) =>\n runWithTimeout(() => toScanFn(scanner)(input, ctx), opts.timeoutMsPerScanner),\n ),\n );\n for (let i = 0; i < results.length; i++) {\n const result = results[i];\n if (result.status === \"fulfilled\" && Array.isArray(result.value)) {\n const matches = opts.tagSourceName\n ? result.value.map((m: Match) => ({\n ...m,\n meta: { ...m.meta, _sourceName: entries[i][0] },\n }))\n : result.value;\n all.push(...matches);\n }\n }\n } else {\n // Sequential execution with optional stopOn short-circuit\n for (const [name, scanner] of entries) {\n try {\n const out = await runWithTimeout(\n () => toScanFn(scanner)(input, ctx),\n opts.timeoutMsPerScanner,\n );\n if (Array.isArray(out)) {\n const matches = opts.tagSourceName\n ? out.map((m: Match) => ({ ...m, meta: { ...m.meta, _sourceName: name } }))\n : out;\n all.push(...matches);\n if (shouldStop(all, opts.stopOn)) break;\n }\n } catch {\n // individual scanner failure is non-fatal\n }\n }\n }\n\n return all;\n };\n }\n\n // ── Variadic form (backward-compatible) ───────────────────────────────────\n const scanners = [first as Scanner, ...(rest as Scanner[])].filter(Boolean);\n return async (input: any, ctx?: any) => {\n const all: Match[] = [];\n for (const s of scanners) {\n try {\n const out = await toScanFn(s)(input, ctx);\n if (Array.isArray(out)) all.push(...out);\n } catch {\n // ignore individual scanner failures\n }\n }\n return all;\n };\n}\n\nexport function createPresetScanner(preset: PresetName, opts: PresetOptions = {}): Scanner {\n const scanners: Scanner[] = [];\n\n // Always include heuristics (EICAR, PHP webshells, JS obfuscation, PE hints, etc.)\n scanners.push(CommonHeuristicsScanner);\n\n // Add decompilation scanners based on preset\n if (\n preset === \"decompilation-basic\" ||\n preset === \"decompilation-deep\" ||\n preset === \"malware-analysis\" ||\n opts.enableDecompilation\n ) {\n const depth =\n preset === \"decompilation-deep\"\n ? \"deep\"\n : preset === \"decompilation-basic\"\n ? \"basic\"\n : opts.decompilationDepth || \"basic\";\n\n if (\n !opts.decompilationEngine ||\n opts.decompilationEngine === \"binaryninja-hlil\" ||\n opts.decompilationEngine === \"both\"\n ) {\n try {\n // Dynamic import to avoid bundling issues - using Function to bypass TypeScript type checking\n const importModule = new Function(\"specifier\", \"return import(specifier)\");\n importModule(\"@pompelmi/engine-binaryninja\")\n .then((mod: any) => {\n const binjaScanner = mod.createBinaryNinjaScanner({\n timeout: opts.decompilationTimeout || opts.timeout || 30000,\n depth,\n pythonPath: opts.pythonPath,\n binaryNinjaPath: opts.binaryNinjaPath,\n });\n scanners.push(binjaScanner);\n })\n .catch(() => {\n // Binary Ninja engine not available - silently skip\n });\n } catch {\n // Engine not installed\n }\n }\n\n if (\n !opts.decompilationEngine ||\n opts.decompilationEngine === \"ghidra-pcode\" ||\n opts.decompilationEngine === \"both\"\n ) {\n try {\n // Dynamic import for Ghidra engine (when implemented) - using Function to bypass TypeScript type checking\n const importModule = new Function(\"specifier\", \"return import(specifier)\");\n importModule(\"@pompelmi/engine-ghidra\")\n .then((mod: any) => {\n const ghidraScanner = mod.createGhidraScanner({\n timeout: opts.decompilationTimeout || opts.timeout || 30000,\n depth,\n ghidraPath: opts.ghidraPath,\n analyzeHeadless: opts.analyzeHeadless,\n });\n scanners.push(ghidraScanner);\n })\n .catch(() => {\n // Ghidra engine not available - silently skip\n });\n } catch {\n // Engine not installed\n }\n }\n }\n\n // Add other scanners for advanced presets\n if (preset === \"advanced\" || preset === \"malware-analysis\") {\n // CommonHeuristicsScanner is already added above for all presets\n }\n\n if (scanners.length === 0) {\n // Fallback scanner that returns no matches\n return async (_input: any, _ctx?: any) => {\n return [] as Match[];\n };\n }\n\n return composeScanners(...scanners);\n}\n\n// Preset configurations\nexport const PRESET_CONFIGS: Record<string, PresetOptions> = {\n basic: {\n timeout: 10000,\n },\n advanced: {\n timeout: 30000,\n enableDecompilation: false,\n },\n \"malware-analysis\": {\n timeout: 60000,\n enableDecompilation: true,\n decompilationEngine: \"both\",\n decompilationDepth: \"deep\",\n },\n \"decompilation-basic\": {\n timeout: 30000,\n enableDecompilation: true,\n decompilationDepth: \"basic\",\n },\n \"decompilation-deep\": {\n timeout: 120000,\n enableDecompilation: true,\n decompilationDepth: \"deep\",\n },\n};\n","/**\n * Advanced threat detection utilities\n * @module utils/advanced-detection\n */\n\nimport type { Match } from \"../types\";\n\n/**\n * Enhanced polyglot file detection\n * Detects files that can be interpreted as multiple formats\n */\nexport function detectPolyglot(bytes: Uint8Array): Match[] {\n const matches: Match[] = [];\n\n // Check for PDF/ZIP polyglot\n if (isPDFZipPolyglot(bytes)) {\n matches.push({\n rule: \"polyglot_pdf_zip\",\n severity: \"high\",\n meta: { description: \"File can be interpreted as both PDF and ZIP\" },\n });\n }\n\n // Check for image/script polyglot\n if (isImageScriptPolyglot(bytes)) {\n matches.push({\n rule: \"polyglot_image_script\",\n severity: \"high\",\n meta: { description: \"Image file contains executable script content\" },\n });\n }\n\n // Check for GIFAR (GIF/JAR polyglot)\n if (isGIFAR(bytes)) {\n matches.push({\n rule: \"polyglot_gifar\",\n severity: \"critical\",\n meta: { description: \"GIF file contains Java archive\" },\n });\n }\n\n return matches;\n}\n\n/**\n * Detect obfuscated JavaScript/VBScript\n */\nexport function detectObfuscatedScripts(bytes: Uint8Array): Match[] {\n const matches: Match[] = [];\n const text = new TextDecoder(\"utf-8\", { fatal: false }).decode(\n bytes.slice(0, Math.min(64 * 1024, bytes.length)),\n );\n\n // Check for common obfuscation patterns\n const obfuscationPatterns = [\n /eval\\s*\\(\\s*unescape\\s*\\(/gi,\n /eval\\s*\\(\\s*atob\\s*\\(/gi,\n /String\\.fromCharCode\\s*\\(\\s*\\d+(?:\\s*,\\s*\\d+){10,}/gi,\n /[a-z0-9]{100,}/gi, // Long encoded strings\n /\\\\x[0-9a-f]{2}/gi, // Hex escapes\n ];\n\n for (const pattern of obfuscationPatterns) {\n if (pattern.test(text)) {\n matches.push({\n rule: \"obfuscated_script\",\n severity: \"medium\",\n meta: {\n description: \"Detected obfuscated script content\",\n pattern: pattern.source,\n },\n });\n break;\n }\n }\n\n return matches;\n}\n\n/**\n * Enhanced nested archive detection with depth limits\n */\nexport function analyzeNestedArchives(\n bytes: Uint8Array,\n maxDepth = 10,\n): { depth: number; hasExcessiveNesting: boolean } {\n let depth = 0;\n let currentBytes = bytes;\n\n while (depth < maxDepth) {\n if (isArchive(currentBytes)) {\n depth++;\n // In a real implementation, we would extract and check the nested content\n // For now, we just check if it looks like an archive\n const extracted = extractFirstEntry(currentBytes);\n if (extracted && isArchive(extracted)) {\n currentBytes = extracted;\n } else {\n break;\n }\n } else {\n break;\n }\n }\n\n return {\n depth,\n hasExcessiveNesting: depth >= 5,\n };\n}\n\n// Helper functions\n\nfunction isPDFZipPolyglot(bytes: Uint8Array): boolean {\n if (bytes.length < 8) return false;\n\n // Check for PDF signature\n const hasPDF = bytes[0] === 0x25 && bytes[1] === 0x50 && bytes[2] === 0x44 && bytes[3] === 0x46;\n\n // Check for ZIP signature anywhere in the file\n let hasZIP = false;\n for (let i = 0; i < Math.min(bytes.length - 4, 1024); i++) {\n if (\n bytes[i] === 0x50 &&\n bytes[i + 1] === 0x4b &&\n bytes[i + 2] === 0x03 &&\n bytes[i + 3] === 0x04\n ) {\n hasZIP = true;\n break;\n }\n }\n\n return hasPDF && hasZIP;\n}\n\nfunction isImageScriptPolyglot(bytes: Uint8Array): boolean {\n if (bytes.length < 100) return false;\n\n // Check for image signatures\n const isImage =\n (bytes[0] === 0xff && bytes[1] === 0xd8) || // JPEG\n (bytes[0] === 0x89 && bytes[1] === 0x50 && bytes[2] === 0x4e && bytes[3] === 0x47) || // PNG\n (bytes[0] === 0x47 && bytes[1] === 0x49 && bytes[2] === 0x46); // GIF\n\n if (!isImage) return false;\n\n // Check for script content\n const text = new TextDecoder(\"utf-8\", { fatal: false }).decode(bytes);\n return /<script|javascript:|eval\\(|function\\s*\\(/i.test(text);\n}\n\nfunction isGIFAR(bytes: Uint8Array): boolean {\n if (bytes.length < 100) return false;\n\n // Check for GIF signature\n const isGIF = bytes[0] === 0x47 && bytes[1] === 0x49 && bytes[2] === 0x46;\n\n // Check for ZIP/JAR signature\n let hasZIP = false;\n for (let i = 0; i < Math.min(bytes.length - 4, 1024); i++) {\n if (\n bytes[i] === 0x50 &&\n bytes[i + 1] === 0x4b &&\n bytes[i + 2] === 0x03 &&\n bytes[i + 3] === 0x04\n ) {\n hasZIP = true;\n break;\n }\n }\n\n return isGIF && hasZIP;\n}\n\nfunction isArchive(bytes: Uint8Array): boolean {\n if (bytes.length < 4) return false;\n\n return (\n // ZIP\n (bytes[0] === 0x50 && bytes[1] === 0x4b && bytes[2] === 0x03 && bytes[3] === 0x04) ||\n // RAR\n (bytes[0] === 0x52 && bytes[1] === 0x61 && bytes[2] === 0x72 && bytes[3] === 0x21) ||\n // 7z\n (bytes[0] === 0x37 && bytes[1] === 0x7a && bytes[2] === 0xbc && bytes[3] === 0xaf) ||\n // tar.gz\n (bytes[0] === 0x1f && bytes[1] === 0x8b)\n );\n}\n\nfunction extractFirstEntry(bytes: Uint8Array): Uint8Array | null {\n // Simplified extraction - in real implementation would properly parse archive\n // This is a placeholder\n return null;\n}\n","/**\n * Cache management system for scan results\n * @module utils/cache-manager\n */\n\nimport { createHash } from \"crypto\";\nimport type { ScanReport } from \"../types\";\n\nexport interface CacheEntry {\n /** Scan report */\n report: ScanReport;\n /** Timestamp when cached */\n timestamp: number;\n /** Number of times this entry was accessed */\n accessCount: number;\n}\n\nexport interface CacheOptions {\n /** Maximum cache size in number of entries (default: 1000) */\n maxSize?: number;\n /** Time-to-live in milliseconds (default: 3600000 = 1 hour) */\n ttl?: number;\n /** Enable LRU eviction (default: true) */\n enableLRU?: boolean;\n /** Enable cache statistics (default: false) */\n enableStats?: boolean;\n}\n\nexport interface CacheStats {\n /** Total cache hits */\n hits: number;\n /** Total cache misses */\n misses: number;\n /** Current cache size */\n size: number;\n /** Hit rate percentage */\n hitRate: number;\n /** Total evictions */\n evictions: number;\n}\n\n/**\n * LRU cache for scan results with TTL support\n */\nexport class ScanCacheManager {\n private cache: Map<string, CacheEntry> = new Map();\n private readonly maxSize: number;\n private readonly ttl: number;\n private readonly enableLRU: boolean;\n private readonly enableStats: boolean;\n\n // Statistics\n private stats = {\n hits: 0,\n misses: 0,\n evictions: 0,\n };\n\n constructor(options: CacheOptions = {}) {\n this.maxSize = options.maxSize ?? 1000;\n this.ttl = options.ttl ?? 3600000; // 1 hour default\n this.enableLRU = options.enableLRU ?? true;\n this.enableStats = options.enableStats ?? false;\n }\n\n /**\n * Generate cache key from file content\n */\n private generateKey(content: Uint8Array, preset?: string): string {\n const hash = createHash(\"sha256\")\n .update(content)\n .update(preset || \"default\")\n .digest(\"hex\");\n return hash;\n }\n\n /**\n * Check if cache entry is still valid\n */\n private isValid(entry: CacheEntry): boolean {\n return Date.now() - entry.timestamp < this.ttl;\n }\n\n /**\n * Evict oldest or least-used entry when cache is full\n */\n private evict(): void {\n if (this.cache.size === 0) return;\n\n let targetKey: string | null = null;\n let oldestTime = Infinity;\n let lowestAccess = Infinity;\n\n for (const [key, entry] of this.cache.entries()) {\n if (this.enableLRU) {\n // LRU: evict least recently used\n if (entry.timestamp < oldestTime) {\n oldestTime = entry.timestamp;\n targetKey = key;\n }\n } else {\n // LFU: evict least frequently used\n if (entry.accessCount < lowestAccess) {\n lowestAccess = entry.accessCount;\n targetKey = key;\n }\n }\n }\n\n if (targetKey) {\n this.cache.delete(targetKey);\n if (this.enableStats) this.stats.evictions++;\n }\n }\n\n /**\n * Store scan result in cache\n */\n set(content: Uint8Array, report: ScanReport, preset?: string): void {\n const key = this.generateKey(content, preset);\n\n // Evict if necessary\n if (this.cache.size >= this.maxSize) {\n this.evict();\n }\n\n this.cache.set(key, {\n report,\n timestamp: Date.now(),\n accessCount: 0,\n });\n }\n\n /**\n * Retrieve scan result from cache\n */\n get(content: Uint8Array, preset?: string): ScanReport | null {\n const key = this.generateKey(content, preset);\n const entry = this.cache.get(key);\n\n if (!entry) {\n if (this.enableStats) this.stats.misses++;\n return null;\n }\n\n if (!this.isValid(entry)) {\n this.cache.delete(key);\n if (this.enableStats) this.stats.misses++;\n return null;\n }\n\n // Update access tracking\n entry.accessCount++;\n entry.timestamp = Date.now(); // Update for LRU\n\n if (this.enableStats) this.stats.hits++;\n return entry.report;\n }\n\n /**\n * Check if result exists in cache\n */\n has(content: Uint8Array, preset?: string): boolean {\n const key = this.generateKey(content, preset);\n const entry = this.cache.get(key);\n return entry !== undefined && this.isValid(entry);\n }\n\n /**\n * Clear entire cache\n */\n clear(): void {\n this.cache.clear();\n if (this.enableStats) {\n this.stats.hits = 0;\n this.stats.misses = 0;\n this.stats.evictions = 0;\n }\n }\n\n /**\n * Remove expired entries\n */\n prune(): number {\n let removed = 0;\n for (const [key, entry] of this.cache.entries()) {\n if (!this.isValid(entry)) {\n this.cache.delete(key);\n removed++;\n }\n }\n return removed;\n }\n\n /**\n * Get cache statistics\n */\n getStats(): CacheStats {\n const total = this.stats.hits + this.stats.misses;\n const hitRate = total > 0 ? (this.stats.hits / total) * 100 : 0;\n\n return {\n hits: this.stats.hits,\n misses: this.stats.misses,\n size: this.cache.size,\n hitRate,\n evictions: this.stats.evictions,\n };\n }\n\n /**\n * Get current cache size\n */\n get size(): number {\n return this.cache.size;\n }\n}\n\n// Export singleton instance for convenience\nlet defaultCache: ScanCacheManager | null = null;\n\n/**\n * Get or create the default cache instance\n */\nexport function getDefaultCache(options?: CacheOptions): ScanCacheManager {\n if (!defaultCache) {\n defaultCache = new ScanCacheManager(options);\n }\n return defaultCache;\n}\n\n/**\n * Reset the default cache instance\n */\nexport function resetDefaultCache(): void {\n defaultCache = null;\n}\n","/**\n * Performance monitoring utilities for pompelmi scans\n * @module utils/performance-metrics\n */\n\nexport interface PerformanceMetrics {\n /** Total scan duration in milliseconds */\n totalDurationMs: number;\n /** Time spent in heuristic analysis */\n heuristicsDurationMs?: number;\n /** Time spent in YARA scanning */\n yaraDurationMs?: number;\n /** Time spent reading/preparing file */\n prepDurationMs?: number;\n /** Throughput in bytes per second */\n throughputBps?: number;\n /** Number of bytes scanned */\n bytesScanned: number;\n /** Timestamp when scan started */\n startedAt: number;\n /** Timestamp when scan completed */\n completedAt: number;\n}\n\nexport interface ScanStatistics {\n /** Total number of scans performed */\n totalScans: number;\n /** Number of clean files */\n cleanCount: number;\n /** Number of suspicious files */\n suspiciousCount: number;\n /** Number of malicious files */\n maliciousCount: number;\n /** Average scan duration */\n avgDurationMs: number;\n /** Average throughput */\n avgThroughputBps: number;\n /** Total bytes scanned */\n totalBytesScanned: number;\n}\n\n/**\n * Track performance metrics for a scan operation\n */\nexport class PerformanceTracker {\n private startTime: number;\n private checkpoints: Map<string, number> = new Map();\n\n constructor() {\n this.startTime = Date.now();\n }\n\n /**\n * Mark a checkpoint in the scan process\n */\n checkpoint(name: string): void {\n this.checkpoints.set(name, Date.now());\n }\n\n /**\n * Get duration since start or since a specific checkpoint\n */\n getDuration(since?: string): number {\n const now = Date.now();\n if (since && this.checkpoints.has(since)) {\n return now - (this.checkpoints.get(since) ?? now);\n }\n return now - this.startTime;\n }\n\n /**\n * Generate final metrics report\n */\n getMetrics(bytesScanned: number): PerformanceMetrics {\n const totalDuration = this.getDuration();\n const throughput = totalDuration > 0 ? (bytesScanned / totalDuration) * 1000 : 0;\n\n return {\n totalDurationMs: totalDuration,\n heuristicsDurationMs: this.checkpoints.has(\"heuristics_end\")\n ? (this.checkpoints.get(\"heuristics_end\") ?? 0) -\n (this.checkpoints.get(\"heuristics_start\") ?? 0)\n : undefined,\n yaraDurationMs: this.checkpoints.has(\"yara_end\")\n ? (this.checkpoints.get(\"yara_end\") ?? 0) - (this.checkpoints.get(\"yara_start\") ?? 0)\n : undefined,\n prepDurationMs: this.checkpoints.has(\"prep_end\")\n ? (this.checkpoints.get(\"prep_end\") ?? 0) - this.startTime\n : undefined,\n throughputBps: throughput,\n bytesScanned,\n startedAt: this.startTime,\n completedAt: Date.now(),\n };\n }\n}\n\n/**\n * Aggregate statistics from multiple scan reports\n */\nexport function aggregateScanStats(\n reports: Array<{ verdict: string; durationMs?: number; file?: { size?: number } }>,\n): ScanStatistics {\n let cleanCount = 0;\n let suspiciousCount = 0;\n let maliciousCount = 0;\n let totalDuration = 0;\n let totalBytes = 0;\n let validDurationCount = 0;\n\n for (const report of reports) {\n if (report.verdict === \"clean\") cleanCount++;\n else if (report.verdict === \"suspicious\") suspiciousCount++;\n else if (report.verdict === \"malicious\") maliciousCount++;\n\n if (report.durationMs !== undefined) {\n totalDuration += report.durationMs;\n validDurationCount++;\n }\n\n if (report.file?.size !== undefined) {\n totalBytes += report.file.size;\n }\n }\n\n const avgDuration = validDurationCount > 0 ? totalDuration / validDurationCount : 0;\n const avgThroughput = totalDuration > 0 ? (totalBytes / totalDuration) * 1000 : 0;\n\n return {\n totalScans: reports.length,\n cleanCount,\n suspiciousCount,\n maliciousCount,\n avgDurationMs: avgDuration,\n avgThroughputBps: avgThroughput,\n totalBytesScanned: totalBytes,\n };\n}\n","import type { ScannerConfig } from \"./config\";\nimport { createPresetScanner, type PresetName } from \"./presets\";\nimport type { Match, ScanContext, ScanReport, Verdict, YaraMatch } from \"./types\";\nimport {\n analyzeNestedArchives,\n detectObfuscatedScripts,\n detectPolyglot,\n} from \"./utils/advanced-detection\";\nimport { getDefaultCache } from \"./utils/cache-manager\";\nimport { PerformanceTracker } from \"./utils/performance-metrics\";\n\n/** Mappa veloce estensione -> mime (basic) */\nfunction guessMimeByExt(name?: string): string | undefined {\n if (!name) return;\n const ext = name.toLowerCase().split(\".\").pop();\n switch (ext) {\n case \"zip\":\n return \"application/zip\";\n case \"png\":\n return \"image/png\";\n case \"jpg\":\n case \"jpeg\":\n return \"image/jpeg\";\n case \"pdf\":\n return \"application/pdf\";\n case \"txt\":\n return \"text/plain\";\n default:\n return;\n }\n}\n\n/** Heuristica semplice per verdetto */\nfunction computeVerdict(matches: YaraMatch[]): Verdict {\n if (!matches.length) return \"clean\";\n // se la regola contiene 'zip_' lo marchiamo \"suspicious\"\n const anyHigh = matches.some(\n (m) => (m.tags ?? []).includes(\"critical\") || (m.tags ?? []).includes(\"high\"),\n );\n return anyHigh ? \"malicious\" : \"suspicious\";\n}\n\n/** Converte i Match (heuristics) in YaraMatch-like per uniformare l'output */\nfunction toYaraMatches(ms: Match[]): YaraMatch[] {\n return ms.map((m) => ({\n rule: m.rule,\n namespace: \"heuristics\",\n tags: [\"heuristics\"].concat(m.severity ? [m.severity] : []),\n meta: m.meta,\n }));\n}\n\nexport type ScanOptions = {\n preset?: PresetName; // default: 'zip-basic'\n ctx?: ScanContext; // filename/mime/size ecc.\n enableAdvancedDetection?: boolean; // Enable polyglot & obfuscation detection (default: true)\n enablePerformanceTracking?: boolean; // Track detailed performance metrics (default: false)\n enableCache?: boolean; // Enable result caching (default: false)\n config?: Partial<ScannerConfig>; // Configuration overrides\n};\n\n/** Scan di bytes (browser/node) usando preset (default: zip-basic) */\nexport async function scanBytes(input: Uint8Array, opts: ScanOptions = {}): Promise<ScanReport> {\n // Check cache first if enabled\n if (opts.enableCache || opts.config?.performance?.enableCache) {\n const cache = getDefaultCache(opts.config?.performance?.cacheOptions);\n const cached = cache.get(input, opts.preset);\n if (cached) {\n return cached;\n }\n }\n\n const perfTracker =\n opts.enablePerformanceTracking || opts.config?.performance?.enablePerformanceTracking\n ? new PerformanceTracker()\n : null;\n perfTracker?.checkpoint(\"prep_start\");\n\n const preset = opts.preset ?? opts.config?.defaultPreset ?? \"zip-basic\";\n const ctx: ScanContext = {\n ...opts.ctx,\n mimeType: opts.ctx?.mimeType ?? guessMimeByExt(opts.ctx?.filename),\n size: opts.ctx?.size ?? input.byteLength,\n };\n\n perfTracker?.checkpoint(\"prep_end\");\n perfTracker?.checkpoint(\"heuristics_start\");\n\n const scanFn = createPresetScanner(preset);\n const matchesH = await (typeof (scanFn as any) === \"function\"\n ? (scanFn as any)\n : (scanFn as any).scan)(input, ctx);\n const allMatches = [...matchesH];\n\n perfTracker?.checkpoint(\"heuristics_end\");\n\n // Advanced detection (enabled by default, can be overridden by config)\n const advancedEnabled =\n opts.enableAdvancedDetection ?? opts.config?.advanced?.enablePolyglotDetection ?? true;\n if (advancedEnabled) {\n perfTracker?.checkpoint(\"advanced_start\");\n\n // Detect polyglot files\n if (opts.config?.advanced?.enablePolyglotDetection !== false) {\n const polyglotMatches = detectPolyglot(input);\n allMatches.push(...polyglotMatches);\n }\n\n // Detect obfuscated scripts\n if (opts.config?.advanced?.enableObfuscationDetection !== false) {\n const obfuscatedMatches = detectObfuscatedScripts(input);\n allMatches.push(...obfuscatedMatches);\n }\n\n // Check for excessive nesting in archives\n if (opts.config?.advanced?.enableNestedArchiveAnalysis !== false) {\n const nestingAnalysis = analyzeNestedArchives(input);\n const maxDepth = opts.config?.advanced?.maxArchiveDepth ?? 5;\n if (nestingAnalysis.hasExcessiveNesting || nestingAnalysis.depth > maxDepth) {\n allMatches.push({\n rule: \"excessive_archive_nesting\",\n severity: \"high\",\n meta: {\n description: \"Excessive archive nesting detected\",\n depth: nestingAnalysis.depth,\n maxAllowed: maxDepth,\n },\n });\n }\n }\n\n perfTracker?.checkpoint(\"advanced_end\");\n }\n\n const matches = toYaraMatches(allMatches);\n const verdict = computeVerdict(matches);\n const t0 = perfTracker ? perfTracker.getDuration() : Date.now();\n const durationMs = perfTracker ? perfTracker.getDuration() : 0;\n\n const report: ScanReport = {\n ok: verdict === \"clean\",\n verdict,\n matches,\n reasons: matches.map((m) => m.rule),\n file: { name: ctx.filename, mimeType: ctx.mimeType, size: ctx.size },\n durationMs,\n engine: \"heuristics\",\n truncated: false,\n timedOut: false,\n };\n\n // Add performance metrics if tracking enabled\n if (\n perfTracker &&\n (opts.enablePerformanceTracking || opts.config?.performance?.enablePerformanceTracking)\n ) {\n (report as any).performanceMetrics = perfTracker.getMetrics(input.byteLength);\n }\n\n // Cache result if enabled\n if (opts.enableCache || opts.config?.performance?.enableCache) {\n const cache = getDefaultCache(opts.config?.performance?.cacheOptions);\n cache.set(input, report, opts.preset);\n }\n\n // Invoke callbacks if configured\n opts.config?.callbacks?.onScanComplete?.(report);\n\n return report;\n}\n\n/** Scan di un file su disco (Node). Import dinamico per non vincolare il bundle browser. */\nexport async function scanFile(\n filePath: string,\n opts: Omit<ScanOptions, \"ctx\"> = {},\n): Promise<ScanReport> {\n const [{ readFile, stat }, path] = await Promise.all([import(\"fs/promises\"), import(\"path\")]);\n\n const [buf, st] = await Promise.all([readFile(filePath), stat(filePath)]);\n const ctx: ScanContext = {\n filename: path.basename(filePath),\n mimeType: guessMimeByExt(filePath),\n size: st.size,\n };\n return scanBytes(new Uint8Array(buf.buffer, buf.byteOffset, buf.byteLength), { ...opts, ctx });\n}\n\n/** Scan multipli File (browser) usando scanBytes + preset di default */\nexport async function scanFiles(\n files: ArrayLike<File>,\n opts: Omit<ScanOptions, \"ctx\"> = {},\n): Promise<ScanReport[]> {\n const list = Array.from(files as ArrayLike<File>) as File[];\n const out: ScanReport[] = [];\n for (const f of list) {\n const buf = new Uint8Array(await f.arrayBuffer());\n const rep = await scanBytes(buf, {\n ...opts,\n ctx: { filename: f.name, mimeType: f.type || guessMimeByExt(f.name), size: f.size },\n });\n out.push(rep);\n }\n return out;\n}\n","import type { Match, Scanner } from \"../types\";\n\nexport type ZipBombGuardOptions = {\n maxEntries?: number; // default 1000\n maxTotalUncompressedBytes?: number; // default 500 * 1024 * 1024 (500MB)\n maxEntryNameLength?: number; // default 255\n maxCompressionRatio?: number; // default 1000 (uncompressed/ compressed)\n // Search window for EOCD; ZIP spec says comment <= 65535 bytes.\n eocdSearchWindow?: number; // default 70_000\n};\n\nconst SIG_LFH = 0x04034b50; // not used (we parse CD)\nconst SIG_CEN = 0x02014b50;\nconst SIG_EOCD = 0x06054b50;\n\nconst DEFAULTS: Required<ZipBombGuardOptions> = {\n maxEntries: 1000,\n maxTotalUncompressedBytes: 500 * 1024 * 1024,\n maxEntryNameLength: 255,\n maxCompressionRatio: 1000,\n eocdSearchWindow: 70_000,\n};\n\nfunction r16(buf: Buffer, off: number) {\n return buf.readUInt16LE(off);\n}\nfunction r32(buf: Buffer, off: number) {\n return buf.readUInt32LE(off);\n}\nfunction isZipLike(buf: Buffer) {\n // local file header at start is common\n return (\n buf.length >= 4 && buf[0] === 0x50 && buf[1] === 0x4b && buf[2] === 0x03 && buf[3] === 0x04\n );\n}\n\nfunction lastIndexOfEOCD(buf: Buffer, window: number): number {\n const sig = Buffer.from([0x50, 0x4b, 0x05, 0x06]);\n const start = Math.max(0, buf.length - window);\n const idx = buf.lastIndexOf(sig, Math.min(buf.length - sig.length, buf.length - 1));\n return idx >= start ? idx : -1;\n}\n\nfunction hasTraversal(name: string): boolean {\n return (\n name.includes(\"../\") || name.includes(\"..\\\\\") || name.startsWith(\"/\") || /^[A-Za-z]:/.test(name)\n );\n}\n\nexport function createZipBombGuard(opts: ZipBombGuardOptions = {}): Scanner {\n const cfg = { ...DEFAULTS, ...opts };\n\n return {\n async scan(input: Uint8Array): Promise<Match[]> {\n const buf = Buffer.from(input);\n const matches: Match[] = [];\n\n if (!isZipLike(buf)) return matches;\n\n // Find EOCD near the end\n const eocdPos = lastIndexOfEOCD(buf, cfg.eocdSearchWindow);\n if (eocdPos < 0 || eocdPos + 22 > buf.length) {\n // ZIP but no EOCD — malformed or polyglot → suspicious\n matches.push({ rule: \"zip_eocd_not_found\", severity: \"medium\" });\n return matches;\n }\n\n const totalEntries = r16(buf, eocdPos + 10);\n const cdSize = r32(buf, eocdPos + 12);\n const cdOffset = r32(buf, eocdPos + 16);\n\n // Bounds check\n if (cdOffset + cdSize > buf.length) {\n matches.push({ rule: \"zip_cd_out_of_bounds\", severity: \"medium\" });\n return matches;\n }\n\n // Iterate central directory entries\n let ptr = cdOffset;\n let seen = 0;\n let sumComp = 0;\n let sumUnc = 0;\n\n while (ptr + 46 <= cdOffset + cdSize && seen < totalEntries) {\n const sig = r32(buf, ptr);\n if (sig !== SIG_CEN) break; // stop if structure breaks\n\n const compSize = r32(buf, ptr + 20);\n const uncSize = r32(buf, ptr + 24);\n const fnLen = r16(buf, ptr + 28);\n const exLen = r16(buf, ptr + 30);\n const cmLen = r16(buf, ptr + 32);\n\n const nameStart = ptr + 46;\n const nameEnd = nameStart + fnLen;\n if (nameEnd > buf.length) break;\n\n const name = buf.toString(\"utf8\", nameStart, nameEnd);\n\n sumComp += compSize;\n sumUnc += uncSize;\n seen++;\n\n if (name.length > cfg.maxEntryNameLength) {\n matches.push({\n rule: \"zip_entry_name_too_long\",\n severity: \"medium\",\n meta: { name, length: name.length },\n });\n }\n if (hasTraversal(name)) {\n matches.push({ rule: \"zip_path_traversal_entry\", severity: \"medium\", meta: { name } });\n }\n\n // move to next entry\n ptr = nameEnd + exLen + cmLen;\n }\n\n if (seen !== totalEntries) {\n // central dir truncated/odd, still report what we found\n matches.push({\n rule: \"zip_cd_truncated\",\n severity: \"medium\",\n meta: { seen, totalEntries },\n });\n }\n\n // Heuristics thresholds\n if (seen > cfg.maxEntries) {\n matches.push({\n rule: \"zip_too_many_entries\",\n severity: \"medium\",\n meta: { seen, limit: cfg.maxEntries },\n });\n }\n if (sumUnc > cfg.maxTotalUncompressedBytes) {\n matches.push({\n rule: \"zip_total_uncompressed_too_large\",\n severity: \"medium\",\n meta: { totalUncompressed: sumUnc, limit: cfg.maxTotalUncompressedBytes },\n });\n }\n\n if (sumComp === 0 && sumUnc > 0) {\n matches.push({\n rule: \"zip_suspicious_ratio\",\n severity: \"medium\",\n meta: { ratio: Infinity },\n });\n } else if (sumComp > 0) {\n const ratio = sumUnc / Math.max(1, sumComp);\n if (ratio >= cfg.maxCompressionRatio) {\n matches.push({\n rule: \"zip_suspicious_ratio\",\n severity: \"medium\",\n meta: { ratio, limit: cfg.maxCompressionRatio },\n });\n }\n }\n\n return matches;\n },\n };\n}\n","/**\n * Export utilities for scan results\n * @module utils/export\n */\n\nimport type { ScanReport } from \"../types\";\n\nexport type ExportFormat = \"json\" | \"csv\" | \"markdown\" | \"html\" | \"sarif\";\n\nexport interface ExportOptions {\n /** Include detailed match information */\n includeDetails?: boolean;\n /** Include performance metrics if available */\n includeMetrics?: boolean;\n /** Pretty print JSON output */\n prettyPrint?: boolean;\n}\n\n/**\n * Export scan results to various formats\n */\nexport class ScanResultExporter {\n /**\n * Export to JSON format\n */\n toJSON(reports: ScanReport | ScanReport[], options: ExportOptions = {}): string {\n const data = Array.isArray(reports) ? reports : [reports];\n\n if (!options.includeDetails) {\n // Simplified output\n const simplified = data.map((r) => ({\n verdict: r.verdict,\n file: r.file?.name,\n matches: r.matches.length,\n durationMs: r.durationMs,\n }));\n return options.prettyPrint ? JSON.stringify(simplified, null, 2) : JSON.stringify(simplified);\n }\n\n return options.prettyPrint ? JSON.stringify(data, null, 2) : JSON.stringify(data);\n }\n\n /**\n * Export to CSV format\n */\n toCSV(reports: ScanReport | ScanReport[], options: ExportOptions = {}): string {\n const data = Array.isArray(reports) ? reports : [reports];\n\n const headers = [\n \"filename\",\n \"verdict\",\n \"matches_count\",\n \"file_size\",\n \"mime_type\",\n \"duration_ms\",\n \"engine\",\n ];\n\n if (options.includeDetails) {\n headers.push(\"reasons\", \"match_rules\");\n }\n\n const rows = data.map((report) => {\n const row = [\n this.escapeCsv(report.file?.name || \"unknown\"),\n report.verdict,\n report.matches.length.toString(),\n (report.file?.size || 0).toString(),\n this.escapeCsv(report.file?.mimeType || \"unknown\"),\n (report.durationMs || 0).toString(),\n report.engine || \"unknown\",\n ];\n\n if (options.includeDetails) {\n row.push(\n this.escapeCsv((report.reasons || []).join(\"; \")),\n this.escapeCsv(report.matches.map((m) => m.rule).join(\"; \")),\n );\n }\n\n return row.join(\",\");\n });\n\n return [headers.join(\",\"), ...rows].join(\"\\n\");\n }\n\n /**\n * Export to Markdown format\n */\n toMarkdown(reports: ScanReport | ScanReport[], options: ExportOptions = {}): string {\n const data = Array.isArray(reports) ? reports : [reports];\n\n let md = \"# Scan Results\\n\\n\";\n md += `**Total Scans:** ${data.length}\\n\\n`;\n\n const clean = data.filter((r) => r.verdict === \"clean\").length;\n const suspicious = data.filter((r) => r.verdict === \"suspicious\").length;\n const malicious = data.filter((r) => r.verdict === \"malicious\").length;\n\n md += \"## Summary\\n\\n\";\n md += `- ✅ Clean: ${clean}\\n`;\n md += `- ⚠️ Suspicious: ${suspicious}\\n`;\n md += `- ❌ Malicious: ${malicious}\\n\\n`;\n\n md += \"## Detailed Results\\n\\n\";\n\n for (const report of data) {\n const icon = report.verdict === \"clean\" ? \"✅\" : report.verdict === \"suspicious\" ? \"⚠️\" : \"❌\";\n md += `### ${icon} ${report.file?.name || \"Unknown\"}\\n\\n`;\n md += `- **Verdict:** ${report.verdict}\\n`;\n md += `- **Size:** ${this.formatBytes(report.file?.size || 0)}\\n`;\n md += `- **MIME Type:** ${report.file?.mimeType || \"unknown\"}\\n`;\n md += `- **Duration:** ${report.durationMs || 0}ms\\n`;\n md += `- **Matches:** ${report.matches.length}\\n`;\n\n if (options.includeDetails && report.matches.length > 0) {\n md += \"\\n**Match Details:**\\n\";\n for (const match of report.matches) {\n md += `- ${match.rule}`;\n if (match.tags && match.tags.length > 0) {\n md += ` (${match.tags.join(\", \")})`;\n }\n md += \"\\n\";\n }\n }\n md += \"\\n\";\n }\n\n return md;\n }\n\n /**\n * Export to SARIF format (Static Analysis Results Interchange Format)\n * Useful for CI/CD integration\n */\n toSARIF(reports: ScanReport | ScanReport[], options: ExportOptions = {}): string {\n const data = Array.isArray(reports) ? reports : [reports];\n\n const results = data.flatMap((report) => {\n if (report.verdict === \"clean\") return [];\n\n return report.matches.map((match) => ({\n ruleId: match.rule,\n level: report.verdict === \"malicious\" ? \"error\" : \"warning\",\n message: {\n text: `${match.rule} detected in ${report.file?.name || \"unknown file\"}`,\n },\n locations: [\n {\n physicalLocation: {\n artifactLocation: {\n uri: report.file?.name || \"unknown\",\n },\n },\n },\n ],\n properties: {\n tags: match.tags,\n metadata: match.meta,\n },\n }));\n });\n\n const sarif = {\n version: \"2.1.0\",\n $schema:\n \"https://raw.githubusercontent.com/oasis-tcs/sarif-spec/master/Schemata/sarif-schema-2.1.0.json\",\n runs: [\n {\n tool: {\n driver: {\n name: \"Pompelmi\",\n version: \"0.29.0\",\n informationUri: \"https://pompelmi.github.io/pompelmi/\",\n },\n },\n results,\n },\n ],\n };\n\n return options.prettyPrint ? JSON.stringify(sarif, null, 2) : JSON.stringify(sarif);\n }\n\n /**\n * Export to HTML format\n */\n toHTML(reports: ScanReport | ScanReport[], options: ExportOptions = {}): string {\n const data = Array.isArray(reports) ? reports : [reports];\n\n const clean = data.filter((r) => r.verdict === \"clean\").length;\n const suspicious = data.filter((r) => r.verdict === \"suspicious\").length;\n const malicious = data.filter((r) => r.verdict === \"malicious\").length;\n\n let html = `<!DOCTYPE html>\n<html lang=\"en\">\n<head>\n <meta charset=\"UTF-8\">\n <meta name=\"viewport\" content=\"width=device-width, initial-scale=1.0\">\n <title>Pompelmi Scan Results</title>\n <style>\n body { font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif; max-width: 1200px; margin: 0 auto; padding: 20px; }\n .summary { display: grid; grid-template-columns: repeat(3, 1fr); gap: 20px; margin: 20px 0; }\n .card { padding: 20px; border-radius: 8px; text-align: center; }\n .clean { background: #d4edda; color: #155724; }\n .suspicious { background: #fff3cd; color: #856404; }\n .malicious { background: #f8d7da; color: #721c24; }\n .result { border: 1px solid #ddd; border-radius: 8px; padding: 15px; margin: 10px 0; }\n .result h3 { margin-top: 0; }\n .badge { display: inline-block; padding: 4px 8px; border-radius: 4px; font-size: 0.8em; margin: 2px; }\n table { width: 100%; border-collapse: collapse; }\n th, td { padding: 8px; text-align: left; border-bottom: 1px solid #ddd; }\n </style>\n</head>\n<body>\n <h1>🛡️ Pompelmi Scan Results</h1>\n <div class=\"summary\">\n <div class=\"card clean\"><h2>${clean}</h2><p>Clean Files</p></div>\n <div class=\"card suspicious\"><h2>${suspicious}</h2><p>Suspicious Files</p></div>\n <div class=\"card malicious\"><h2>${malicious}</h2><p>Malicious Files</p></div>\n </div>\n <h2>Detailed Results</h2>`;\n\n for (const report of data) {\n const statusClass = report.verdict;\n html += `<div class=\"result ${statusClass}\">`;\n html += `<h3>${this.escapeHtml(report.file?.name || \"Unknown\")}</h3>`;\n html += `<table>`;\n html += `<tr><th>Verdict</th><td>${report.verdict.toUpperCase()}</td></tr>`;\n html += `<tr><th>Size</th><td>${this.formatBytes(report.file?.size || 0)}</td></tr>`;\n html += `<tr><th>MIME Type</th><td>${this.escapeHtml(report.file?.mimeType || \"unknown\")}</td></tr>`;\n html += `<tr><th>Duration</th><td>${report.durationMs || 0}ms</td></tr>`;\n html += `<tr><th>Matches</th><td>${report.matches.length}</td></tr>`;\n html += `</table>`;\n\n if (options.includeDetails && report.matches.length > 0) {\n html += `<h4>Match Details:</h4><ul>`;\n for (const match of report.matches) {\n html += `<li><strong>${this.escapeHtml(match.rule)}</strong>`;\n if (match.tags && match.tags.length > 0) {\n html += ` ${match.tags.map((tag) => `<span class=\"badge\">${this.escapeHtml(tag)}</span>`).join(\"\")}`;\n }\n html += `</li>`;\n }\n html += `</ul>`;\n }\n html += `</div>`;\n }\n\n html += `</body></html>`;\n return html;\n }\n\n /**\n * Export to specified format\n */\n export(\n reports: ScanReport | ScanReport[],\n format: ExportFormat,\n options: ExportOptions = {},\n ): string {\n switch (format) {\n case \"json\":\n return this.toJSON(reports, options);\n case \"csv\":\n return this.toCSV(reports, options);\n case \"markdown\":\n return this.toMarkdown(reports, options);\n case \"html\":\n return this.toHTML(reports, options);\n case \"sarif\":\n return this.toSARIF(reports, options);\n default:\n throw new Error(`Unsupported export format: ${format}`);\n }\n }\n\n private escapeCsv(value: string): string {\n if (value.includes(\",\") || value.includes('\"') || value.includes(\"\\n\")) {\n return `\"${value.replace(/\"/g, '\"\"')}\"`;\n }\n return value;\n }\n\n private escapeHtml(value: string): string {\n return value\n .replace(/&/g, \"&\")\n .replace(/</g, \"<\")\n .replace(/>/g, \">\")\n .replace(/\"/g, \""\")\n .replace(/'/g, \"'\");\n }\n\n private formatBytes(bytes: number): string {\n if (bytes === 0) return \"0 Bytes\";\n const k = 1024;\n const sizes = [\"Bytes\", \"KB\", \"MB\", \"GB\"];\n const i = Math.floor(Math.log(bytes) / Math.log(k));\n return Math.round((bytes / k ** i) * 100) / 100 + \" \" + sizes[i];\n }\n}\n\n/**\n * Quick export helper\n */\nexport function exportScanResults(\n reports: ScanReport | ScanReport[],\n format: ExportFormat,\n options?: ExportOptions,\n): string {\n const exporter = new ScanResultExporter();\n return exporter.export(reports, format, options);\n}\n","/**\n * Validates a File by MIME type and size (max 5 MB).\n */\nexport function validateFile(file: File): { valid: boolean; error?: string } {\n const maxSize = 5 * 1024 * 1024;\n const allowedTypes = [\"text/plain\", \"application/json\", \"text/csv\"];\n\n if (!allowedTypes.includes(file.type)) {\n return { valid: false, error: \"Unsupported file type\" };\n }\n if (file.size > maxSize) {\n return { valid: false, error: \"File too large (max 5 MB)\" };\n }\n return { valid: true };\n}\n","// src/verdict.ts\nimport type { Verdict, YaraMatch } from \"./types\";\nexport function mapMatchesToVerdict(matches: YaraMatch[] = []): Verdict {\n if (!matches.length) return \"clean\";\n const malHints = [\"trojan\", \"ransom\", \"worm\", \"spy\", \"rootkit\", \"keylog\", \"botnet\"];\n const tagSet = new Set(matches.flatMap((m) => (m.tags ?? []).map((t) => t.toLowerCase())));\n const nameHit = (r: string) => malHints.some((h) => r.toLowerCase().includes(h));\n const isMal =\n matches.some((m) => nameHit(m.rule)) || tagSet.has(\"malware\") || tagSet.has(\"critical\");\n return isMal ? \"malicious\" : \"suspicious\";\n}\n"],"names":["MB","isZipLike","createHash"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"pompelmi.browser.cjs","sources":["../../src/policy.ts","../../src/policy-packs.ts","../../src/scanners/common-heuristics.ts","../../src/presets.ts","../../src/utils/advanced-detection.ts","../../src/utils/cache-manager.ts","../../src/utils/performance-metrics.ts","../../src/scan.ts","../../src/scanners/zip-bomb-guard.ts","../../src/utils/export.ts","../../src/validate.ts","../../src/verdict.ts"],"sourcesContent":["export interface Policy {\n includeExtensions: string[];\n allowedMimeTypes: string[];\n maxFileSizeBytes: number;\n timeoutMs: number;\n concurrency: number;\n failClosed: boolean;\n onScanEvent?: (ev: unknown) => void;\n}\nexport type PolicyInput = Partial<Policy>;\n\nconst MB = 1024 * 1024;\n\nexport const DEFAULT_POLICY: Policy = {\n includeExtensions: [\"zip\", \"png\", \"jpg\", \"jpeg\", \"pdf\"],\n allowedMimeTypes: [\"application/zip\", \"image/png\", \"image/jpeg\", \"application/pdf\", \"text/plain\"],\n maxFileSizeBytes: 20 * MB,\n timeoutMs: 5000,\n concurrency: 4,\n failClosed: true,\n};\n\nexport function definePolicy(input: PolicyInput = {}): Policy {\n const p: Policy = { ...DEFAULT_POLICY, ...input };\n if (!Array.isArray(p.includeExtensions))\n throw new TypeError(\"includeExtensions must be string[]\");\n if (!Array.isArray(p.allowedMimeTypes)) throw new TypeError(\"allowedMimeTypes must be string[]\");\n if (!(Number.isFinite(p.maxFileSizeBytes) && p.maxFileSizeBytes > 0))\n throw new TypeError(\"maxFileSizeBytes must be > 0\");\n if (!(Number.isFinite(p.timeoutMs) && p.timeoutMs > 0))\n throw new TypeError(\"timeoutMs must be > 0\");\n if (!(Number.isInteger(p.concurrency) && p.concurrency > 0))\n throw new TypeError(\"concurrency must be > 0\");\n return p;\n}\n","/**\n * Policy packs for Pompelmi.\n *\n * Pre-configured, named policies for common upload scenarios. Each pack\n * defines the file type allowlist, size limits, and timeout appropriate for\n * its use case.\n *\n * All packs are built on `definePolicy` and are fully overridable:\n *\n * ```ts\n * import { POLICY_PACKS } from 'pompelmi/policy-packs';\n *\n * // Use a pack as-is:\n * const policy = POLICY_PACKS['images-only'];\n *\n * // Or override individual fields:\n * import { definePolicy } from 'pompelmi';\n * const custom = definePolicy({ ...POLICY_PACKS['documents-only'], maxFileSizeBytes: 5 * 1024 * 1024 });\n * ```\n *\n * These packs are *deterministic* and *descriptor-based* — they do not\n * depend on any external threat intelligence feed.\n *\n * @module policy-packs\n */\n\nimport { definePolicy, type Policy } from \"./policy\";\n\nconst KB = 1024;\nconst MB = 1024 * KB;\n\n// ── Policy packs ──────────────────────────────────────────────────────────────\n\n/**\n * Documents-only policy.\n *\n * Appropriate for: document management APIs, PDF/Office file upload endpoints,\n * data import pipelines.\n *\n * Allowed: PDF, Word (.docx/.doc), Excel (.xlsx/.xls), PowerPoint (.pptx/.ppt),\n * CSV, plain text, JSON, YAML, ODT/ODS/ODP (OpenDocument).\n * Max size: 25 MB.\n */\nexport const DOCUMENTS_ONLY: Policy = definePolicy({\n includeExtensions: [\n \"pdf\",\n \"doc\",\n \"docx\",\n \"xls\",\n \"xlsx\",\n \"ppt\",\n \"pptx\",\n \"odt\",\n \"ods\",\n \"odp\",\n \"csv\",\n \"txt\",\n \"json\",\n \"yaml\",\n \"yml\",\n \"md\",\n ],\n allowedMimeTypes: [\n \"application/pdf\",\n \"application/msword\",\n \"application/vnd.openxmlformats-officedocument.wordprocessingml.document\",\n \"application/vnd.ms-excel\",\n \"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet\",\n \"application/vnd.ms-powerpoint\",\n \"application/vnd.openxmlformats-officedocument.presentationml.presentation\",\n \"application/vnd.oasis.opendocument.text\",\n \"application/vnd.oasis.opendocument.spreadsheet\",\n \"application/vnd.oasis.opendocument.presentation\",\n \"text/csv\",\n \"text/plain\",\n \"application/json\",\n \"text/yaml\",\n \"text/markdown\",\n ],\n maxFileSizeBytes: 25 * MB,\n timeoutMs: 10_000,\n concurrency: 4,\n failClosed: true,\n});\n\n/**\n * Images-only policy.\n *\n * Appropriate for: avatar uploads, product image APIs, content platforms with\n * user-generated imagery.\n *\n * Allowed: JPEG, PNG, GIF, WebP, AVIF, TIFF, BMP, ICO.\n * Max size: 10 MB.\n * Note: SVG is intentionally excluded — inline SVGs can contain scripts.\n */\nexport const IMAGES_ONLY: Policy = definePolicy({\n includeExtensions: [\"jpg\", \"jpeg\", \"png\", \"gif\", \"webp\", \"avif\", \"tiff\", \"tif\", \"bmp\", \"ico\"],\n allowedMimeTypes: [\n \"image/jpeg\",\n \"image/png\",\n \"image/gif\",\n \"image/webp\",\n \"image/avif\",\n \"image/tiff\",\n \"image/bmp\",\n \"image/x-icon\",\n \"image/vnd.microsoft.icon\",\n ],\n maxFileSizeBytes: 10 * MB,\n timeoutMs: 5_000,\n concurrency: 8,\n failClosed: true,\n});\n\n/**\n * Strict public-upload policy.\n *\n * Appropriate for: anonymous or low-trust upload endpoints, public APIs,\n * any surface exposed to untrusted users.\n *\n * Aggressive size limit (5 MB), short timeout, fail-closed, narrow MIME\n * allowlist. Only allows plain images and PDF.\n */\nexport const STRICT_PUBLIC_UPLOAD: Policy = definePolicy({\n includeExtensions: [\"jpg\", \"jpeg\", \"png\", \"webp\", \"pdf\"],\n allowedMimeTypes: [\"image/jpeg\", \"image/png\", \"image/webp\", \"application/pdf\"],\n maxFileSizeBytes: 5 * MB,\n timeoutMs: 4_000,\n concurrency: 2,\n failClosed: true,\n});\n\n/**\n * Conservative default policy.\n *\n * A hardened version of the built-in `DEFAULT_POLICY` suitable for\n * production without further customisation. Stricter size limit and\n * shorter timeout than the permissive default.\n */\nexport const CONSERVATIVE_DEFAULT: Policy = definePolicy({\n includeExtensions: [\"zip\", \"png\", \"jpg\", \"jpeg\", \"pdf\", \"txt\", \"csv\", \"docx\", \"xlsx\"],\n allowedMimeTypes: [\n \"application/zip\",\n \"image/png\",\n \"image/jpeg\",\n \"application/pdf\",\n \"text/plain\",\n \"text/csv\",\n \"application/vnd.openxmlformats-officedocument.wordprocessingml.document\",\n \"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet\",\n ],\n maxFileSizeBytes: 10 * MB,\n timeoutMs: 8_000,\n concurrency: 4,\n failClosed: true,\n});\n\n/**\n * Archives policy.\n *\n * Appropriate for: endpoints that accept ZIP, tar, or compressed archives.\n * Combines a generous size allowance with a longer timeout for deep inspection.\n *\n * NOTE: Pair this policy with `createZipBombGuard()` to defend against\n * decompression-bomb attacks:\n *\n * ```ts\n * import { composeScanners, createZipBombGuard, CommonHeuristicsScanner } from 'pompelmi';\n * const scanner = composeScanners(\n * [['zipGuard', createZipBombGuard()], ['heuristics', CommonHeuristicsScanner]]\n * );\n * ```\n */\nexport const ARCHIVES: Policy = definePolicy({\n includeExtensions: [\"zip\", \"tar\", \"gz\", \"tgz\", \"bz2\", \"xz\", \"7z\", \"rar\"],\n allowedMimeTypes: [\n \"application/zip\",\n \"application/x-tar\",\n \"application/gzip\",\n \"application/x-bzip2\",\n \"application/x-xz\",\n \"application/x-7z-compressed\",\n \"application/x-rar-compressed\",\n ],\n maxFileSizeBytes: 100 * MB,\n timeoutMs: 30_000,\n concurrency: 2,\n failClosed: true,\n});\n\n// ── Named map ────────────────────────────────────────────────────────────────\n\nexport type PolicyPackName =\n | \"documents-only\"\n | \"images-only\"\n | \"strict-public-upload\"\n | \"conservative-default\"\n | \"archives\";\n\n/**\n * Named map of all built-in policy packs.\n *\n * ```ts\n * import { POLICY_PACKS } from 'pompelmi/policy-packs';\n * const policy = POLICY_PACKS['strict-public-upload'];\n * ```\n */\nexport const POLICY_PACKS: Record<PolicyPackName, Policy> = {\n \"documents-only\": DOCUMENTS_ONLY,\n \"images-only\": IMAGES_ONLY,\n \"strict-public-upload\": STRICT_PUBLIC_UPLOAD,\n \"conservative-default\": CONSERVATIVE_DEFAULT,\n archives: ARCHIVES,\n};\n\n/**\n * Look up a policy pack by name.\n * Throws if the name is not recognised.\n */\nexport function getPolicyPack(name: PolicyPackName): Policy {\n const policy = POLICY_PACKS[name];\n if (!policy)\n throw new Error(\n `Unknown policy pack: '${name}'. Valid names: ${Object.keys(POLICY_PACKS).join(\", \")}`,\n );\n return policy;\n}\n","/**\n * CommonHeuristicsScanner\n * Lightweight, no-deps heuristics for common risky file patterns.\n * Returns matches as [{ rule, severity?, meta? }].\n */\nexport type HeuristicMatch = {\n rule: string;\n severity?: \"info\" | \"low\" | \"medium\" | \"high\" | \"critical\" | \"suspicious\" | \"malicious\";\n meta?: Record<string, unknown>;\n};\n\nexport interface SimpleScanner {\n scan(bytes: Uint8Array): Promise<HeuristicMatch[]>;\n}\n\nfunction hasAsciiToken(buf: Buffer, token: string): boolean {\n // Use latin1 so we can safely search binary\n return buf.indexOf(token, 0, \"latin1\") !== -1;\n}\nfunction startsWith(buf: Buffer, bytes: number[]): boolean {\n if (buf.length < bytes.length) return false;\n for (let i = 0; i < bytes.length; i++) if (buf[i] !== bytes[i]) return false;\n return true;\n}\n\nfunction isPDF(buf: Buffer): boolean {\n // %PDF-\n return startsWith(buf, [0x25, 0x50, 0x44, 0x46, 0x2d]);\n}\nfunction isOleCfb(buf: Buffer): boolean {\n // D0 CF 11 E0 A1 B1 1A E1\n const sig = [0xd0, 0xcf, 0x11, 0xe0, 0xa1, 0xb1, 0x1a, 0xe1];\n return startsWith(buf, sig);\n}\nfunction isZipLike(buf: Buffer): boolean {\n // PK\\x03\\x04\n return startsWith(buf, [0x50, 0x4b, 0x03, 0x04]);\n}\nfunction isPeExecutable(buf: Buffer): boolean {\n // \"MZ\"\n return startsWith(buf, [0x4d, 0x5a]);\n}\n\n/** OOXML macro hint via filename token in ZIP container */\nfunction hasOoxmlMacros(buf: Buffer): boolean {\n if (!isZipLike(buf)) return false;\n return hasAsciiToken(buf, \"vbaProject.bin\");\n}\n\n/** PDF risky features (/JavaScript, /OpenAction, /AA, /Launch) */\nfunction pdfRiskTokens(buf: Buffer): string[] {\n const tokens = [\"/JavaScript\", \"/OpenAction\", \"/AA\", \"/Launch\"];\n return tokens.filter((t) => hasAsciiToken(buf, t));\n}\n\nexport const CommonHeuristicsScanner: SimpleScanner = {\n async scan(input: Uint8Array) {\n const buf = Buffer.from(input);\n const matches: HeuristicMatch[] = [];\n\n // Office macros (OLE / OOXML)\n if (isOleCfb(buf)) {\n matches.push({ rule: \"office_ole_container\", severity: \"suspicious\" });\n }\n if (hasOoxmlMacros(buf)) {\n matches.push({ rule: \"office_ooxml_macros\", severity: \"suspicious\" });\n }\n\n // PDF risky tokens\n if (isPDF(buf)) {\n const toks = pdfRiskTokens(buf);\n if (toks.length) {\n matches.push({\n rule: \"pdf_risky_actions\",\n severity: \"suspicious\",\n meta: { tokens: toks },\n });\n }\n }\n\n // Executable header\n if (isPeExecutable(buf)) {\n matches.push({ rule: \"pe_executable_signature\", severity: \"suspicious\" });\n }\n\n // EICAR test file\n const EICAR_NEEDLE = \"X5O!P%@AP[4\\\\PZX54(P^)7CC)7}$EICAR-STANDARD-ANTIVIRUS-TEST-FILE!\";\n if (hasAsciiToken(buf, EICAR_NEEDLE)) {\n matches.push({\n rule: \"eicar_test_file\",\n severity: \"high\",\n meta: { note: \"EICAR standard antivirus test file detected\" },\n });\n }\n\n return matches;\n },\n};\n","import { CommonHeuristicsScanner } from \"./scanners/common-heuristics\";\nimport type { AnalysisDepth, DecompilationScanner, Match, ScanFn, Scanner, Verdict } from \"./types\";\n\nexport type PresetName =\n | \"basic\"\n | \"advanced\"\n | \"malware-analysis\"\n | \"decompilation-basic\"\n | \"decompilation-deep\"\n | string;\n\nexport interface PresetOptions {\n // YARA options\n yaraRules?: string | string[];\n yaraTimeout?: number;\n\n // Decompilation options\n enableDecompilation?: boolean;\n decompilationEngine?: \"binaryninja-hlil\" | \"ghidra-pcode\" | \"both\";\n decompilationDepth?: AnalysisDepth;\n decompilationTimeout?: number;\n\n // Binary Ninja specific\n binaryNinjaPath?: string;\n pythonPath?: string;\n\n // Ghidra specific\n ghidraPath?: string;\n analyzeHeadless?: string;\n\n // General options\n timeout?: number;\n [key: string]: unknown;\n}\n\n/**\n * A named scanner entry used with the array form of `composeScanners`.\n * The first element is a display name for the scanner (used when\n * `tagSourceName: true`), and the second element is the scanner itself.\n *\n * @example\n * const entry: NamedScanner = ['zipGuard', createZipBombGuard({ ... })];\n */\nexport type NamedScanner = [name: string, scanner: Scanner];\n\n/**\n * Options for `composeScanners` when using the named-scanner array form.\n */\nexport interface ComposeScannerOptions {\n /**\n * When `true` scanners run concurrently (Promise.all).\n * When `false` (default) they run sequentially in order.\n */\n parallel?: boolean;\n /**\n * Stop scanning as soon as a match at this severity level (or higher) is\n * found. Severity order: `'malicious'` > `'suspicious'` > `'clean'`.\n * Only effective when `parallel` is `false`.\n */\n stopOn?: Verdict;\n /** Maximum time in milliseconds to wait for each individual scanner. */\n timeoutMsPerScanner?: number;\n /**\n * When `true`, each match is tagged with the scanner's display name via\n * `match.meta._sourceName`. Useful for tracing which scanner produced a\n * given result.\n */\n tagSourceName?: boolean;\n}\n\nfunction toScanFn(s: Scanner): (input: any, ctx?: any) => Promise<Match[]> {\n return (typeof s === \"function\" ? s : s.scan) as (input: any, ctx?: any) => Promise<Match[]>;\n}\n\n/** Map a Match's severity field to a Verdict for stopOn comparison. */\nfunction matchToVerdict(m: Match): Verdict {\n const s = m.severity;\n if (s === \"critical\" || s === \"high\" || s === \"malicious\") return \"malicious\";\n if (s === \"medium\" || s === \"low\" || s === \"suspicious\" || s === \"info\") return \"suspicious\";\n return \"clean\";\n}\n\n/** Highest verdict across all matches in the list. */\nfunction highestSeverity(matches: Match[]): Verdict | null {\n if (matches.length === 0) return null;\n if (matches.some((m) => matchToVerdict(m) === \"malicious\")) return \"malicious\";\n if (matches.some((m) => matchToVerdict(m) === \"suspicious\")) return \"suspicious\";\n return \"clean\";\n}\n\nconst SEVERITY_RANK: Record<Verdict, number> = { malicious: 2, suspicious: 1, clean: 0 };\n\nfunction shouldStop(matches: Match[], stopOn: Verdict | undefined): boolean {\n if (!stopOn) return false;\n const highest = highestSeverity(matches);\n if (!highest) return false;\n return SEVERITY_RANK[highest] >= SEVERITY_RANK[stopOn];\n}\n\nasync function runWithTimeout<T>(fn: () => Promise<T>, timeoutMs: number | undefined): Promise<T> {\n if (!timeoutMs) return fn();\n return new Promise<T>((resolve, reject) => {\n const timer = setTimeout(() => reject(new Error(\"scanner timeout\")), timeoutMs);\n fn().then(\n (v) => {\n clearTimeout(timer);\n resolve(v);\n },\n (e) => {\n clearTimeout(timer);\n reject(e);\n },\n );\n });\n}\n\n/**\n * Compose multiple scanners into a single scanner.\n *\n * **Named-scanner array form** (recommended — matches the README examples):\n * ```ts\n * const scanner = composeScanners(\n * [\n * ['zipGuard', createZipBombGuard({ maxEntries: 512, maxCompressionRatio: 12 })],\n * ['heuristics', CommonHeuristicsScanner],\n * ],\n * { parallel: false, stopOn: 'malicious', timeoutMsPerScanner: 5000, tagSourceName: true }\n * );\n * ```\n *\n * **Variadic form** (backward-compatible):\n * ```ts\n * const scanner = composeScanners(scannerA, scannerB, scannerC);\n * ```\n */\nexport function composeScanners(\n namedScanners: NamedScanner[],\n opts?: ComposeScannerOptions,\n): ScanFn;\nexport function composeScanners(...scanners: Scanner[]): ScanFn;\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\nexport function composeScanners(...args: any[]): ScanFn {\n const first: NamedScanner[] | Scanner = args[0];\n const rest: Array<Scanner | ComposeScannerOptions> = args.slice(1);\n // ── Named-scanner array form ──────────────────────────────────────────────\n if (\n Array.isArray(first) &&\n (first.length === 0 || (Array.isArray(first[0]) && typeof first[0][0] === \"string\"))\n ) {\n const entries = first as NamedScanner[];\n const opts: ComposeScannerOptions =\n rest.length > 0 &&\n !Array.isArray(rest[0]) &&\n typeof rest[0] !== \"function\" &&\n !(typeof rest[0] === \"object\" && rest[0] !== null && \"scan\" in (rest[0] as object))\n ? (rest[0] as ComposeScannerOptions)\n : {};\n\n return async (input: any, ctx?: any) => {\n const all: Match[] = [];\n\n if (opts.parallel) {\n // Parallel execution — collect all results then return\n const results = await Promise.allSettled(\n entries.map(([_name, scanner]) =>\n runWithTimeout(() => toScanFn(scanner)(input, ctx), opts.timeoutMsPerScanner),\n ),\n );\n for (let i = 0; i < results.length; i++) {\n const result = results[i];\n if (result.status === \"fulfilled\" && Array.isArray(result.value)) {\n const matches = opts.tagSourceName\n ? result.value.map((m: Match) => ({\n ...m,\n meta: { ...m.meta, _sourceName: entries[i][0] },\n }))\n : result.value;\n all.push(...matches);\n }\n }\n } else {\n // Sequential execution with optional stopOn short-circuit\n for (const [name, scanner] of entries) {\n try {\n const out = await runWithTimeout(\n () => toScanFn(scanner)(input, ctx),\n opts.timeoutMsPerScanner,\n );\n if (Array.isArray(out)) {\n const matches = opts.tagSourceName\n ? out.map((m: Match) => ({ ...m, meta: { ...m.meta, _sourceName: name } }))\n : out;\n all.push(...matches);\n if (shouldStop(all, opts.stopOn)) break;\n }\n } catch {\n // individual scanner failure is non-fatal\n }\n }\n }\n\n return all;\n };\n }\n\n // ── Variadic form (backward-compatible) ───────────────────────────────────\n const scanners = [first as Scanner, ...(rest as Scanner[])].filter(Boolean);\n return async (input: any, ctx?: any) => {\n const all: Match[] = [];\n for (const s of scanners) {\n try {\n const out = await toScanFn(s)(input, ctx);\n if (Array.isArray(out)) all.push(...out);\n } catch {\n // ignore individual scanner failures\n }\n }\n return all;\n };\n}\n\nexport function createPresetScanner(preset: PresetName, opts: PresetOptions = {}): Scanner {\n const baseScanners: Scanner[] = [CommonHeuristicsScanner];\n const dynamicScannerPromises: Array<Promise<Scanner | null>> = [];\n\n // Add decompilation scanners based on preset\n if (\n preset === \"decompilation-basic\" ||\n preset === \"decompilation-deep\" ||\n preset === \"malware-analysis\" ||\n opts.enableDecompilation\n ) {\n const depth =\n preset === \"decompilation-deep\" || preset === \"malware-analysis\"\n ? \"deep\"\n : preset === \"decompilation-basic\"\n ? \"basic\"\n : opts.decompilationDepth || \"basic\";\n let importModule: ((specifier: string) => Promise<any>) | undefined;\n\n try {\n // Dynamic import to avoid bundling issues - using Function to bypass TypeScript type checking\n importModule = new Function(\"specifier\", \"return import(specifier)\") as (\n specifier: string,\n ) => Promise<any>;\n } catch {\n importModule = undefined;\n }\n\n if (\n importModule &&\n (!opts.decompilationEngine ||\n opts.decompilationEngine === \"binaryninja-hlil\" ||\n opts.decompilationEngine === \"both\")\n ) {\n dynamicScannerPromises.push(\n importModule(\"@pompelmi/engine-binaryninja\")\n .then(\n (mod: any) =>\n mod.createBinaryNinjaScanner({\n timeout: opts.decompilationTimeout || opts.timeout || 30000,\n depth,\n pythonPath: opts.pythonPath,\n binaryNinjaPath: opts.binaryNinjaPath,\n }) as Scanner,\n )\n .catch(() => null),\n );\n }\n\n if (\n importModule &&\n (!opts.decompilationEngine ||\n opts.decompilationEngine === \"ghidra-pcode\" ||\n opts.decompilationEngine === \"both\")\n ) {\n dynamicScannerPromises.push(\n importModule(\"@pompelmi/engine-ghidra\")\n .then(\n (mod: any) =>\n mod.createGhidraScanner({\n timeout: opts.decompilationTimeout || opts.timeout || 30000,\n depth,\n ghidraPath: opts.ghidraPath,\n analyzeHeadless: opts.analyzeHeadless,\n }) as Scanner,\n )\n .catch(() => null),\n );\n }\n }\n\n // Add other scanners for advanced presets\n if (preset === \"advanced\" || preset === \"malware-analysis\") {\n // CommonHeuristicsScanner is already added above for all presets\n }\n\n let composedScannerPromise: Promise<ScanFn> | undefined;\n\n const getComposedScanner = async (): Promise<ScanFn> => {\n composedScannerPromise ??= Promise.all(dynamicScannerPromises).then((dynamicScanners) =>\n composeScanners(\n ...baseScanners,\n ...dynamicScanners.filter((scanner): scanner is Scanner => scanner !== null),\n ),\n );\n return composedScannerPromise;\n };\n\n return async (input, ctx) => {\n const scanner = await getComposedScanner();\n return scanner(input, ctx);\n };\n}\n\n// Preset configurations\nexport const PRESET_CONFIGS: Record<string, PresetOptions> = {\n basic: {\n timeout: 10000,\n },\n advanced: {\n timeout: 30000,\n enableDecompilation: false,\n },\n \"malware-analysis\": {\n timeout: 60000,\n enableDecompilation: true,\n decompilationEngine: \"both\",\n decompilationDepth: \"deep\",\n },\n \"decompilation-basic\": {\n timeout: 30000,\n enableDecompilation: true,\n decompilationDepth: \"basic\",\n },\n \"decompilation-deep\": {\n timeout: 120000,\n enableDecompilation: true,\n decompilationDepth: \"deep\",\n },\n};\n","/**\n * Advanced threat detection utilities\n * @module utils/advanced-detection\n */\n\nimport type { Match } from \"../types\";\n\n/**\n * Enhanced polyglot file detection\n * Detects files that can be interpreted as multiple formats\n */\nexport function detectPolyglot(bytes: Uint8Array): Match[] {\n const matches: Match[] = [];\n\n // Check for PDF/ZIP polyglot\n if (isPDFZipPolyglot(bytes)) {\n matches.push({\n rule: \"polyglot_pdf_zip\",\n severity: \"high\",\n meta: { description: \"File can be interpreted as both PDF and ZIP\" },\n });\n }\n\n // Check for image/script polyglot\n if (isImageScriptPolyglot(bytes)) {\n matches.push({\n rule: \"polyglot_image_script\",\n severity: \"high\",\n meta: { description: \"Image file contains executable script content\" },\n });\n }\n\n // Check for GIFAR (GIF/JAR polyglot)\n if (isGIFAR(bytes)) {\n matches.push({\n rule: \"polyglot_gifar\",\n severity: \"critical\",\n meta: { description: \"GIF file contains Java archive\" },\n });\n }\n\n return matches;\n}\n\n/**\n * Detect obfuscated JavaScript/VBScript\n */\nexport function detectObfuscatedScripts(bytes: Uint8Array): Match[] {\n const matches: Match[] = [];\n const text = new TextDecoder(\"utf-8\", { fatal: false }).decode(\n bytes.slice(0, Math.min(64 * 1024, bytes.length)),\n );\n\n // Check for common obfuscation patterns\n const obfuscationPatterns = [\n /eval\\s*\\(\\s*unescape\\s*\\(/gi,\n /eval\\s*\\(\\s*atob\\s*\\(/gi,\n /String\\.fromCharCode\\s*\\(\\s*\\d+(?:\\s*,\\s*\\d+){10,}/gi,\n /[a-z0-9]{100,}/gi, // Long encoded strings\n /\\\\x[0-9a-f]{2}/gi, // Hex escapes\n ];\n\n for (const pattern of obfuscationPatterns) {\n if (pattern.test(text)) {\n matches.push({\n rule: \"obfuscated_script\",\n severity: \"medium\",\n meta: {\n description: \"Detected obfuscated script content\",\n pattern: pattern.source,\n },\n });\n break;\n }\n }\n\n return matches;\n}\n\n/**\n * Enhanced nested archive detection with depth limits\n */\nexport function analyzeNestedArchives(\n bytes: Uint8Array,\n maxDepth = 10,\n): { depth: number; hasExcessiveNesting: boolean } {\n let depth = 0;\n let currentBytes = bytes;\n\n while (depth < maxDepth) {\n if (isArchive(currentBytes)) {\n depth++;\n // In a real implementation, we would extract and check the nested content\n // For now, we just check if it looks like an archive\n const extracted = extractFirstEntry(currentBytes);\n if (extracted && isArchive(extracted)) {\n currentBytes = extracted;\n } else {\n break;\n }\n } else {\n break;\n }\n }\n\n return {\n depth,\n hasExcessiveNesting: depth >= 5,\n };\n}\n\n// Helper functions\n\nfunction isPDFZipPolyglot(bytes: Uint8Array): boolean {\n if (bytes.length < 8) return false;\n\n // Check for PDF signature\n const hasPDF = bytes[0] === 0x25 && bytes[1] === 0x50 && bytes[2] === 0x44 && bytes[3] === 0x46;\n\n // Check for ZIP signature anywhere in the file\n let hasZIP = false;\n for (let i = 0; i < Math.min(bytes.length - 4, 1024); i++) {\n if (\n bytes[i] === 0x50 &&\n bytes[i + 1] === 0x4b &&\n bytes[i + 2] === 0x03 &&\n bytes[i + 3] === 0x04\n ) {\n hasZIP = true;\n break;\n }\n }\n\n return hasPDF && hasZIP;\n}\n\nfunction isImageScriptPolyglot(bytes: Uint8Array): boolean {\n if (bytes.length < 100) return false;\n\n // Check for image signatures\n const isImage =\n (bytes[0] === 0xff && bytes[1] === 0xd8) || // JPEG\n (bytes[0] === 0x89 && bytes[1] === 0x50 && bytes[2] === 0x4e && bytes[3] === 0x47) || // PNG\n (bytes[0] === 0x47 && bytes[1] === 0x49 && bytes[2] === 0x46); // GIF\n\n if (!isImage) return false;\n\n // Check for script content\n const text = new TextDecoder(\"utf-8\", { fatal: false }).decode(bytes);\n return /<script|javascript:|eval\\(|function\\s*\\(/i.test(text);\n}\n\nfunction isGIFAR(bytes: Uint8Array): boolean {\n if (bytes.length < 100) return false;\n\n // Check for GIF signature\n const isGIF = bytes[0] === 0x47 && bytes[1] === 0x49 && bytes[2] === 0x46;\n\n // Check for ZIP/JAR signature\n let hasZIP = false;\n for (let i = 0; i < Math.min(bytes.length - 4, 1024); i++) {\n if (\n bytes[i] === 0x50 &&\n bytes[i + 1] === 0x4b &&\n bytes[i + 2] === 0x03 &&\n bytes[i + 3] === 0x04\n ) {\n hasZIP = true;\n break;\n }\n }\n\n return isGIF && hasZIP;\n}\n\nfunction isArchive(bytes: Uint8Array): boolean {\n if (bytes.length < 4) return false;\n\n return (\n // ZIP\n (bytes[0] === 0x50 && bytes[1] === 0x4b && bytes[2] === 0x03 && bytes[3] === 0x04) ||\n // RAR\n (bytes[0] === 0x52 && bytes[1] === 0x61 && bytes[2] === 0x72 && bytes[3] === 0x21) ||\n // 7z\n (bytes[0] === 0x37 && bytes[1] === 0x7a && bytes[2] === 0xbc && bytes[3] === 0xaf) ||\n // tar.gz\n (bytes[0] === 0x1f && bytes[1] === 0x8b)\n );\n}\n\nfunction extractFirstEntry(bytes: Uint8Array): Uint8Array | null {\n // Simplified extraction - in real implementation would properly parse archive\n // This is a placeholder\n return null;\n}\n","/**\n * Cache management system for scan results\n * @module utils/cache-manager\n */\n\nimport { createHash } from \"crypto\";\nimport type { ScanReport } from \"../types\";\n\nexport interface CacheEntry {\n /** Scan report */\n report: ScanReport;\n /** Timestamp when cached */\n timestamp: number;\n /** Number of times this entry was accessed */\n accessCount: number;\n}\n\nexport interface CacheOptions {\n /** Maximum cache size in number of entries (default: 1000) */\n maxSize?: number;\n /** Time-to-live in milliseconds (default: 3600000 = 1 hour) */\n ttl?: number;\n /** Enable LRU eviction (default: true) */\n enableLRU?: boolean;\n /** Enable cache statistics (default: false) */\n enableStats?: boolean;\n}\n\nexport interface CacheStats {\n /** Total cache hits */\n hits: number;\n /** Total cache misses */\n misses: number;\n /** Current cache size */\n size: number;\n /** Hit rate percentage */\n hitRate: number;\n /** Total evictions */\n evictions: number;\n}\n\n/**\n * LRU cache for scan results with TTL support\n */\nexport class ScanCacheManager {\n private cache: Map<string, CacheEntry> = new Map();\n private readonly maxSize: number;\n private readonly ttl: number;\n private readonly enableLRU: boolean;\n private readonly enableStats: boolean;\n\n // Statistics\n private stats = {\n hits: 0,\n misses: 0,\n evictions: 0,\n };\n\n constructor(options: CacheOptions = {}) {\n this.maxSize = options.maxSize ?? 1000;\n this.ttl = options.ttl ?? 3600000; // 1 hour default\n this.enableLRU = options.enableLRU ?? true;\n this.enableStats = options.enableStats ?? false;\n }\n\n /**\n * Generate cache key from file content\n */\n private generateKey(content: Uint8Array, preset?: string): string {\n const hash = createHash(\"sha256\")\n .update(content)\n .update(preset || \"default\")\n .digest(\"hex\");\n return hash;\n }\n\n /**\n * Check if cache entry is still valid\n */\n private isValid(entry: CacheEntry): boolean {\n return Date.now() - entry.timestamp < this.ttl;\n }\n\n /**\n * Evict oldest or least-used entry when cache is full\n */\n private evict(): void {\n if (this.cache.size === 0) return;\n\n let targetKey: string | null = null;\n let oldestTime = Infinity;\n let lowestAccess = Infinity;\n\n for (const [key, entry] of this.cache.entries()) {\n if (this.enableLRU) {\n // LRU: evict least recently used\n if (entry.timestamp < oldestTime) {\n oldestTime = entry.timestamp;\n targetKey = key;\n }\n } else {\n // LFU: evict least frequently used\n if (entry.accessCount < lowestAccess) {\n lowestAccess = entry.accessCount;\n targetKey = key;\n }\n }\n }\n\n if (targetKey) {\n this.cache.delete(targetKey);\n if (this.enableStats) this.stats.evictions++;\n }\n }\n\n /**\n * Store scan result in cache\n */\n set(content: Uint8Array, report: ScanReport, preset?: string): void {\n const key = this.generateKey(content, preset);\n\n // Evict if necessary\n if (this.cache.size >= this.maxSize) {\n this.evict();\n }\n\n this.cache.set(key, {\n report,\n timestamp: Date.now(),\n accessCount: 0,\n });\n }\n\n /**\n * Retrieve scan result from cache\n */\n get(content: Uint8Array, preset?: string): ScanReport | null {\n const key = this.generateKey(content, preset);\n const entry = this.cache.get(key);\n\n if (!entry) {\n if (this.enableStats) this.stats.misses++;\n return null;\n }\n\n if (!this.isValid(entry)) {\n this.cache.delete(key);\n if (this.enableStats) this.stats.misses++;\n return null;\n }\n\n // Update access tracking\n entry.accessCount++;\n entry.timestamp = Date.now(); // Update for LRU\n\n if (this.enableStats) this.stats.hits++;\n return entry.report;\n }\n\n /**\n * Check if result exists in cache\n */\n has(content: Uint8Array, preset?: string): boolean {\n const key = this.generateKey(content, preset);\n const entry = this.cache.get(key);\n return entry !== undefined && this.isValid(entry);\n }\n\n /**\n * Clear entire cache\n */\n clear(): void {\n this.cache.clear();\n if (this.enableStats) {\n this.stats.hits = 0;\n this.stats.misses = 0;\n this.stats.evictions = 0;\n }\n }\n\n /**\n * Remove expired entries\n */\n prune(): number {\n let removed = 0;\n for (const [key, entry] of this.cache.entries()) {\n if (!this.isValid(entry)) {\n this.cache.delete(key);\n removed++;\n }\n }\n return removed;\n }\n\n /**\n * Get cache statistics\n */\n getStats(): CacheStats {\n const total = this.stats.hits + this.stats.misses;\n const hitRate = total > 0 ? (this.stats.hits / total) * 100 : 0;\n\n return {\n hits: this.stats.hits,\n misses: this.stats.misses,\n size: this.cache.size,\n hitRate,\n evictions: this.stats.evictions,\n };\n }\n\n /**\n * Get current cache size\n */\n get size(): number {\n return this.cache.size;\n }\n}\n\n// Export singleton instance for convenience\nlet defaultCache: ScanCacheManager | null = null;\n\n/**\n * Get or create the default cache instance\n */\nexport function getDefaultCache(options?: CacheOptions): ScanCacheManager {\n if (!defaultCache) {\n defaultCache = new ScanCacheManager(options);\n }\n return defaultCache;\n}\n\n/**\n * Reset the default cache instance\n */\nexport function resetDefaultCache(): void {\n defaultCache = null;\n}\n","/**\n * Performance monitoring utilities for pompelmi scans\n * @module utils/performance-metrics\n */\n\nexport interface PerformanceMetrics {\n /** Total scan duration in milliseconds */\n totalDurationMs: number;\n /** Time spent in heuristic analysis */\n heuristicsDurationMs?: number;\n /** Time spent in YARA scanning */\n yaraDurationMs?: number;\n /** Time spent reading/preparing file */\n prepDurationMs?: number;\n /** Throughput in bytes per second */\n throughputBps?: number;\n /** Number of bytes scanned */\n bytesScanned: number;\n /** Timestamp when scan started */\n startedAt: number;\n /** Timestamp when scan completed */\n completedAt: number;\n}\n\nexport interface ScanStatistics {\n /** Total number of scans performed */\n totalScans: number;\n /** Number of clean files */\n cleanCount: number;\n /** Number of suspicious files */\n suspiciousCount: number;\n /** Number of malicious files */\n maliciousCount: number;\n /** Average scan duration */\n avgDurationMs: number;\n /** Average throughput */\n avgThroughputBps: number;\n /** Total bytes scanned */\n totalBytesScanned: number;\n}\n\n/**\n * Track performance metrics for a scan operation\n */\nexport class PerformanceTracker {\n private startTime: number;\n private checkpoints: Map<string, number> = new Map();\n\n constructor() {\n this.startTime = Date.now();\n }\n\n /**\n * Mark a checkpoint in the scan process\n */\n checkpoint(name: string): void {\n this.checkpoints.set(name, Date.now());\n }\n\n /**\n * Get duration since start or since a specific checkpoint\n */\n getDuration(since?: string): number {\n const now = Date.now();\n if (since && this.checkpoints.has(since)) {\n return now - (this.checkpoints.get(since) ?? now);\n }\n return now - this.startTime;\n }\n\n /**\n * Generate final metrics report\n */\n getMetrics(bytesScanned: number): PerformanceMetrics {\n const totalDuration = this.getDuration();\n const throughput = totalDuration > 0 ? (bytesScanned / totalDuration) * 1000 : 0;\n\n return {\n totalDurationMs: totalDuration,\n heuristicsDurationMs: this.checkpoints.has(\"heuristics_end\")\n ? (this.checkpoints.get(\"heuristics_end\") ?? 0) -\n (this.checkpoints.get(\"heuristics_start\") ?? 0)\n : undefined,\n yaraDurationMs: this.checkpoints.has(\"yara_end\")\n ? (this.checkpoints.get(\"yara_end\") ?? 0) - (this.checkpoints.get(\"yara_start\") ?? 0)\n : undefined,\n prepDurationMs: this.checkpoints.has(\"prep_end\")\n ? (this.checkpoints.get(\"prep_end\") ?? 0) - this.startTime\n : undefined,\n throughputBps: throughput,\n bytesScanned,\n startedAt: this.startTime,\n completedAt: Date.now(),\n };\n }\n}\n\n/**\n * Aggregate statistics from multiple scan reports\n */\nexport function aggregateScanStats(\n reports: Array<{ verdict: string; durationMs?: number; file?: { size?: number } }>,\n): ScanStatistics {\n let cleanCount = 0;\n let suspiciousCount = 0;\n let maliciousCount = 0;\n let totalDuration = 0;\n let totalBytes = 0;\n let validDurationCount = 0;\n\n for (const report of reports) {\n if (report.verdict === \"clean\") cleanCount++;\n else if (report.verdict === \"suspicious\") suspiciousCount++;\n else if (report.verdict === \"malicious\") maliciousCount++;\n\n if (report.durationMs !== undefined) {\n totalDuration += report.durationMs;\n validDurationCount++;\n }\n\n if (report.file?.size !== undefined) {\n totalBytes += report.file.size;\n }\n }\n\n const avgDuration = validDurationCount > 0 ? totalDuration / validDurationCount : 0;\n const avgThroughput = totalDuration > 0 ? (totalBytes / totalDuration) * 1000 : 0;\n\n return {\n totalScans: reports.length,\n cleanCount,\n suspiciousCount,\n maliciousCount,\n avgDurationMs: avgDuration,\n avgThroughputBps: avgThroughput,\n totalBytesScanned: totalBytes,\n };\n}\n","import type { ScannerConfig } from \"./config\";\nimport { createPresetScanner, type PresetName } from \"./presets\";\nimport type { Match, ScanContext, ScanReport, Verdict, YaraMatch } from \"./types\";\nimport {\n analyzeNestedArchives,\n detectObfuscatedScripts,\n detectPolyglot,\n} from \"./utils/advanced-detection\";\nimport { getDefaultCache } from \"./utils/cache-manager\";\nimport { PerformanceTracker } from \"./utils/performance-metrics\";\n\n/** Mappa veloce estensione -> mime (basic) */\nfunction guessMimeByExt(name?: string): string | undefined {\n if (!name) return;\n const ext = name.toLowerCase().split(\".\").pop();\n switch (ext) {\n case \"zip\":\n return \"application/zip\";\n case \"png\":\n return \"image/png\";\n case \"jpg\":\n case \"jpeg\":\n return \"image/jpeg\";\n case \"pdf\":\n return \"application/pdf\";\n case \"txt\":\n return \"text/plain\";\n default:\n return;\n }\n}\n\n/** Heuristica semplice per verdetto */\nfunction computeVerdict(matches: YaraMatch[]): Verdict {\n if (!matches.length) return \"clean\";\n // se la regola contiene 'zip_' lo marchiamo \"suspicious\"\n const anyHigh = matches.some(\n (m) => (m.tags ?? []).includes(\"critical\") || (m.tags ?? []).includes(\"high\"),\n );\n return anyHigh ? \"malicious\" : \"suspicious\";\n}\n\n/** Converte i Match (heuristics) in YaraMatch-like per uniformare l'output */\nfunction toYaraMatches(ms: Match[]): YaraMatch[] {\n return ms.map((m) => ({\n rule: m.rule,\n namespace: \"heuristics\",\n tags: [\"heuristics\"].concat(m.severity ? [m.severity] : []),\n meta: m.meta,\n }));\n}\n\nexport type ScanOptions = {\n preset?: PresetName; // default: 'zip-basic'\n ctx?: ScanContext; // filename/mime/size ecc.\n enableAdvancedDetection?: boolean; // Enable polyglot & obfuscation detection (default: true)\n enablePerformanceTracking?: boolean; // Track detailed performance metrics (default: false)\n enableCache?: boolean; // Enable result caching (default: false)\n config?: Partial<ScannerConfig>; // Configuration overrides\n};\n\n/** Scan di bytes (browser/node) usando preset (default: zip-basic) */\nexport async function scanBytes(input: Uint8Array, opts: ScanOptions = {}): Promise<ScanReport> {\n // Check cache first if enabled\n if (opts.enableCache || opts.config?.performance?.enableCache) {\n const cache = getDefaultCache(opts.config?.performance?.cacheOptions);\n const cached = cache.get(input, opts.preset);\n if (cached) {\n return cached;\n }\n }\n\n const perfTracker =\n opts.enablePerformanceTracking || opts.config?.performance?.enablePerformanceTracking\n ? new PerformanceTracker()\n : null;\n perfTracker?.checkpoint(\"prep_start\");\n\n const preset = opts.preset ?? opts.config?.defaultPreset ?? \"zip-basic\";\n const ctx: ScanContext = {\n ...opts.ctx,\n mimeType: opts.ctx?.mimeType ?? guessMimeByExt(opts.ctx?.filename),\n size: opts.ctx?.size ?? input.byteLength,\n };\n\n perfTracker?.checkpoint(\"prep_end\");\n perfTracker?.checkpoint(\"heuristics_start\");\n\n const scanFn = createPresetScanner(preset);\n const matchesH = await (typeof (scanFn as any) === \"function\"\n ? (scanFn as any)\n : (scanFn as any).scan)(input, ctx);\n const allMatches = [...matchesH];\n\n perfTracker?.checkpoint(\"heuristics_end\");\n\n // Advanced detection (enabled by default, can be overridden by config)\n const advancedEnabled =\n opts.enableAdvancedDetection ?? opts.config?.advanced?.enablePolyglotDetection ?? true;\n if (advancedEnabled) {\n perfTracker?.checkpoint(\"advanced_start\");\n\n // Detect polyglot files\n if (opts.config?.advanced?.enablePolyglotDetection !== false) {\n const polyglotMatches = detectPolyglot(input);\n allMatches.push(...polyglotMatches);\n }\n\n // Detect obfuscated scripts\n if (opts.config?.advanced?.enableObfuscationDetection !== false) {\n const obfuscatedMatches = detectObfuscatedScripts(input);\n allMatches.push(...obfuscatedMatches);\n }\n\n // Check for excessive nesting in archives\n if (opts.config?.advanced?.enableNestedArchiveAnalysis !== false) {\n const nestingAnalysis = analyzeNestedArchives(input);\n const maxDepth = opts.config?.advanced?.maxArchiveDepth ?? 5;\n if (nestingAnalysis.hasExcessiveNesting || nestingAnalysis.depth > maxDepth) {\n allMatches.push({\n rule: \"excessive_archive_nesting\",\n severity: \"high\",\n meta: {\n description: \"Excessive archive nesting detected\",\n depth: nestingAnalysis.depth,\n maxAllowed: maxDepth,\n },\n });\n }\n }\n\n perfTracker?.checkpoint(\"advanced_end\");\n }\n\n const matches = toYaraMatches(allMatches);\n const verdict = computeVerdict(matches);\n const t0 = perfTracker ? perfTracker.getDuration() : Date.now();\n const durationMs = perfTracker ? perfTracker.getDuration() : 0;\n\n const report: ScanReport = {\n ok: verdict === \"clean\",\n verdict,\n matches,\n reasons: matches.map((m) => m.rule),\n file: { name: ctx.filename, mimeType: ctx.mimeType, size: ctx.size },\n durationMs,\n engine: \"heuristics\",\n truncated: false,\n timedOut: false,\n };\n\n // Add performance metrics if tracking enabled\n if (\n perfTracker &&\n (opts.enablePerformanceTracking || opts.config?.performance?.enablePerformanceTracking)\n ) {\n (report as any).performanceMetrics = perfTracker.getMetrics(input.byteLength);\n }\n\n // Cache result if enabled\n if (opts.enableCache || opts.config?.performance?.enableCache) {\n const cache = getDefaultCache(opts.config?.performance?.cacheOptions);\n cache.set(input, report, opts.preset);\n }\n\n // Invoke callbacks if configured\n opts.config?.callbacks?.onScanComplete?.(report);\n\n return report;\n}\n\n/** Scan di un file su disco (Node). Import dinamico per non vincolare il bundle browser. */\nexport async function scanFile(\n filePath: string,\n opts: Omit<ScanOptions, \"ctx\"> = {},\n): Promise<ScanReport> {\n const [{ readFile, stat }, path] = await Promise.all([import(\"fs/promises\"), import(\"path\")]);\n\n const [buf, st] = await Promise.all([readFile(filePath), stat(filePath)]);\n const ctx: ScanContext = {\n filename: path.basename(filePath),\n mimeType: guessMimeByExt(filePath),\n size: st.size,\n };\n return scanBytes(new Uint8Array(buf.buffer, buf.byteOffset, buf.byteLength), { ...opts, ctx });\n}\n\n/** Scan multipli File (browser) usando scanBytes + preset di default */\nexport async function scanFiles(\n files: ArrayLike<File>,\n opts: Omit<ScanOptions, \"ctx\"> = {},\n): Promise<ScanReport[]> {\n const list = Array.from(files as ArrayLike<File>) as File[];\n const out: ScanReport[] = [];\n for (const f of list) {\n const buf = new Uint8Array(await f.arrayBuffer());\n const rep = await scanBytes(buf, {\n ...opts,\n ctx: { filename: f.name, mimeType: f.type || guessMimeByExt(f.name), size: f.size },\n });\n out.push(rep);\n }\n return out;\n}\n","import type { Match, Scanner } from \"../types\";\n\nexport type ZipBombGuardOptions = {\n maxEntries?: number; // default 1000\n maxTotalUncompressedBytes?: number; // default 500 * 1024 * 1024 (500MB)\n maxEntryNameLength?: number; // default 255\n maxCompressionRatio?: number; // default 1000 (uncompressed/ compressed)\n // Search window for EOCD; ZIP spec says comment <= 65535 bytes.\n eocdSearchWindow?: number; // default 70_000\n};\n\nconst SIG_LFH = 0x04034b50; // not used (we parse CD)\nconst SIG_CEN = 0x02014b50;\nconst SIG_EOCD = 0x06054b50;\n\nconst DEFAULTS: Required<ZipBombGuardOptions> = {\n maxEntries: 1000,\n maxTotalUncompressedBytes: 500 * 1024 * 1024,\n maxEntryNameLength: 255,\n maxCompressionRatio: 1000,\n eocdSearchWindow: 70_000,\n};\n\nfunction r16(buf: Buffer, off: number) {\n return buf.readUInt16LE(off);\n}\nfunction r32(buf: Buffer, off: number) {\n return buf.readUInt32LE(off);\n}\nfunction isZipLike(buf: Buffer) {\n // local file header at start is common\n return (\n buf.length >= 4 && buf[0] === 0x50 && buf[1] === 0x4b && buf[2] === 0x03 && buf[3] === 0x04\n );\n}\n\nfunction lastIndexOfEOCD(buf: Buffer, window: number): number {\n const sig = Buffer.from([0x50, 0x4b, 0x05, 0x06]);\n const start = Math.max(0, buf.length - window);\n const idx = buf.lastIndexOf(sig, Math.min(buf.length - sig.length, buf.length - 1));\n return idx >= start ? idx : -1;\n}\n\nfunction hasTraversal(name: string): boolean {\n return (\n name.includes(\"../\") || name.includes(\"..\\\\\") || name.startsWith(\"/\") || /^[A-Za-z]:/.test(name)\n );\n}\n\nexport function createZipBombGuard(opts: ZipBombGuardOptions = {}): Scanner {\n const cfg = { ...DEFAULTS, ...opts };\n\n return {\n async scan(input: Uint8Array): Promise<Match[]> {\n const buf = Buffer.from(input);\n const matches: Match[] = [];\n\n if (!isZipLike(buf)) return matches;\n\n // Find EOCD near the end\n const eocdPos = lastIndexOfEOCD(buf, cfg.eocdSearchWindow);\n if (eocdPos < 0 || eocdPos + 22 > buf.length) {\n // ZIP but no EOCD — malformed or polyglot → suspicious\n matches.push({ rule: \"zip_eocd_not_found\", severity: \"medium\" });\n return matches;\n }\n\n const totalEntries = r16(buf, eocdPos + 10);\n const cdSize = r32(buf, eocdPos + 12);\n const cdOffset = r32(buf, eocdPos + 16);\n\n // Bounds check\n if (cdOffset + cdSize > buf.length) {\n matches.push({ rule: \"zip_cd_out_of_bounds\", severity: \"medium\" });\n return matches;\n }\n\n // Iterate central directory entries\n let ptr = cdOffset;\n let seen = 0;\n let sumComp = 0;\n let sumUnc = 0;\n\n while (ptr + 46 <= cdOffset + cdSize && seen < totalEntries) {\n const sig = r32(buf, ptr);\n if (sig !== SIG_CEN) break; // stop if structure breaks\n\n const compSize = r32(buf, ptr + 20);\n const uncSize = r32(buf, ptr + 24);\n const fnLen = r16(buf, ptr + 28);\n const exLen = r16(buf, ptr + 30);\n const cmLen = r16(buf, ptr + 32);\n\n const nameStart = ptr + 46;\n const nameEnd = nameStart + fnLen;\n if (nameEnd > buf.length) break;\n\n const name = buf.toString(\"utf8\", nameStart, nameEnd);\n\n sumComp += compSize;\n sumUnc += uncSize;\n seen++;\n\n if (name.length > cfg.maxEntryNameLength) {\n matches.push({\n rule: \"zip_entry_name_too_long\",\n severity: \"medium\",\n meta: { name, length: name.length },\n });\n }\n if (hasTraversal(name)) {\n matches.push({ rule: \"zip_path_traversal_entry\", severity: \"medium\", meta: { name } });\n }\n\n // move to next entry\n ptr = nameEnd + exLen + cmLen;\n }\n\n if (seen !== totalEntries) {\n // central dir truncated/odd, still report what we found\n matches.push({\n rule: \"zip_cd_truncated\",\n severity: \"medium\",\n meta: { seen, totalEntries },\n });\n }\n\n // Heuristics thresholds\n if (seen > cfg.maxEntries) {\n matches.push({\n rule: \"zip_too_many_entries\",\n severity: \"medium\",\n meta: { seen, limit: cfg.maxEntries },\n });\n }\n if (sumUnc > cfg.maxTotalUncompressedBytes) {\n matches.push({\n rule: \"zip_total_uncompressed_too_large\",\n severity: \"medium\",\n meta: { totalUncompressed: sumUnc, limit: cfg.maxTotalUncompressedBytes },\n });\n }\n\n if (sumComp === 0 && sumUnc > 0) {\n matches.push({\n rule: \"zip_suspicious_ratio\",\n severity: \"medium\",\n meta: { ratio: Infinity },\n });\n } else if (sumComp > 0) {\n const ratio = sumUnc / Math.max(1, sumComp);\n if (ratio >= cfg.maxCompressionRatio) {\n matches.push({\n rule: \"zip_suspicious_ratio\",\n severity: \"medium\",\n meta: { ratio, limit: cfg.maxCompressionRatio },\n });\n }\n }\n\n return matches;\n },\n };\n}\n","/**\n * Export utilities for scan results\n * @module utils/export\n */\n\nimport type { ScanReport } from \"../types\";\n\nexport type ExportFormat = \"json\" | \"csv\" | \"markdown\" | \"html\" | \"sarif\";\n\nexport interface ExportOptions {\n /** Include detailed match information */\n includeDetails?: boolean;\n /** Include performance metrics if available */\n includeMetrics?: boolean;\n /** Pretty print JSON output */\n prettyPrint?: boolean;\n}\n\n/**\n * Export scan results to various formats\n */\nexport class ScanResultExporter {\n /**\n * Export to JSON format\n */\n toJSON(reports: ScanReport | ScanReport[], options: ExportOptions = {}): string {\n const data = Array.isArray(reports) ? reports : [reports];\n\n if (!options.includeDetails) {\n // Simplified output\n const simplified = data.map((r) => ({\n verdict: r.verdict,\n file: r.file?.name,\n matches: r.matches.length,\n durationMs: r.durationMs,\n }));\n return options.prettyPrint ? JSON.stringify(simplified, null, 2) : JSON.stringify(simplified);\n }\n\n return options.prettyPrint ? JSON.stringify(data, null, 2) : JSON.stringify(data);\n }\n\n /**\n * Export to CSV format\n */\n toCSV(reports: ScanReport | ScanReport[], options: ExportOptions = {}): string {\n const data = Array.isArray(reports) ? reports : [reports];\n\n const headers = [\n \"filename\",\n \"verdict\",\n \"matches_count\",\n \"file_size\",\n \"mime_type\",\n \"duration_ms\",\n \"engine\",\n ];\n\n if (options.includeDetails) {\n headers.push(\"reasons\", \"match_rules\");\n }\n\n const rows = data.map((report) => {\n const row = [\n this.escapeCsv(report.file?.name || \"unknown\"),\n report.verdict,\n report.matches.length.toString(),\n (report.file?.size || 0).toString(),\n this.escapeCsv(report.file?.mimeType || \"unknown\"),\n (report.durationMs || 0).toString(),\n report.engine || \"unknown\",\n ];\n\n if (options.includeDetails) {\n row.push(\n this.escapeCsv((report.reasons || []).join(\"; \")),\n this.escapeCsv(report.matches.map((m) => m.rule).join(\"; \")),\n );\n }\n\n return row.join(\",\");\n });\n\n return [headers.join(\",\"), ...rows].join(\"\\n\");\n }\n\n /**\n * Export to Markdown format\n */\n toMarkdown(reports: ScanReport | ScanReport[], options: ExportOptions = {}): string {\n const data = Array.isArray(reports) ? reports : [reports];\n\n let md = \"# Scan Results\\n\\n\";\n md += `**Total Scans:** ${data.length}\\n\\n`;\n\n const clean = data.filter((r) => r.verdict === \"clean\").length;\n const suspicious = data.filter((r) => r.verdict === \"suspicious\").length;\n const malicious = data.filter((r) => r.verdict === \"malicious\").length;\n\n md += \"## Summary\\n\\n\";\n md += `- ✅ Clean: ${clean}\\n`;\n md += `- ⚠️ Suspicious: ${suspicious}\\n`;\n md += `- ❌ Malicious: ${malicious}\\n\\n`;\n\n md += \"## Detailed Results\\n\\n\";\n\n for (const report of data) {\n const icon = report.verdict === \"clean\" ? \"✅\" : report.verdict === \"suspicious\" ? \"⚠️\" : \"❌\";\n md += `### ${icon} ${report.file?.name || \"Unknown\"}\\n\\n`;\n md += `- **Verdict:** ${report.verdict}\\n`;\n md += `- **Size:** ${this.formatBytes(report.file?.size || 0)}\\n`;\n md += `- **MIME Type:** ${report.file?.mimeType || \"unknown\"}\\n`;\n md += `- **Duration:** ${report.durationMs || 0}ms\\n`;\n md += `- **Matches:** ${report.matches.length}\\n`;\n\n if (options.includeDetails && report.matches.length > 0) {\n md += \"\\n**Match Details:**\\n\";\n for (const match of report.matches) {\n md += `- ${match.rule}`;\n if (match.tags && match.tags.length > 0) {\n md += ` (${match.tags.join(\", \")})`;\n }\n md += \"\\n\";\n }\n }\n md += \"\\n\";\n }\n\n return md;\n }\n\n /**\n * Export to SARIF format (Static Analysis Results Interchange Format)\n * Useful for CI/CD integration\n */\n toSARIF(reports: ScanReport | ScanReport[], options: ExportOptions = {}): string {\n const data = Array.isArray(reports) ? reports : [reports];\n\n const results = data.flatMap((report) => {\n if (report.verdict === \"clean\") return [];\n\n return report.matches.map((match) => ({\n ruleId: match.rule,\n level: report.verdict === \"malicious\" ? \"error\" : \"warning\",\n message: {\n text: `${match.rule} detected in ${report.file?.name || \"unknown file\"}`,\n },\n locations: [\n {\n physicalLocation: {\n artifactLocation: {\n uri: report.file?.name || \"unknown\",\n },\n },\n },\n ],\n properties: {\n tags: match.tags,\n metadata: match.meta,\n },\n }));\n });\n\n const sarif = {\n version: \"2.1.0\",\n $schema:\n \"https://raw.githubusercontent.com/oasis-tcs/sarif-spec/master/Schemata/sarif-schema-2.1.0.json\",\n runs: [\n {\n tool: {\n driver: {\n name: \"Pompelmi\",\n version: \"0.29.0\",\n informationUri: \"https://pompelmi.github.io/pompelmi/\",\n },\n },\n results,\n },\n ],\n };\n\n return options.prettyPrint ? JSON.stringify(sarif, null, 2) : JSON.stringify(sarif);\n }\n\n /**\n * Export to HTML format\n */\n toHTML(reports: ScanReport | ScanReport[], options: ExportOptions = {}): string {\n const data = Array.isArray(reports) ? reports : [reports];\n\n const clean = data.filter((r) => r.verdict === \"clean\").length;\n const suspicious = data.filter((r) => r.verdict === \"suspicious\").length;\n const malicious = data.filter((r) => r.verdict === \"malicious\").length;\n\n let html = `<!DOCTYPE html>\n<html lang=\"en\">\n<head>\n <meta charset=\"UTF-8\">\n <meta name=\"viewport\" content=\"width=device-width, initial-scale=1.0\">\n <title>Pompelmi Scan Results</title>\n <style>\n body { font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif; max-width: 1200px; margin: 0 auto; padding: 20px; }\n .summary { display: grid; grid-template-columns: repeat(3, 1fr); gap: 20px; margin: 20px 0; }\n .card { padding: 20px; border-radius: 8px; text-align: center; }\n .clean { background: #d4edda; color: #155724; }\n .suspicious { background: #fff3cd; color: #856404; }\n .malicious { background: #f8d7da; color: #721c24; }\n .result { border: 1px solid #ddd; border-radius: 8px; padding: 15px; margin: 10px 0; }\n .result h3 { margin-top: 0; }\n .badge { display: inline-block; padding: 4px 8px; border-radius: 4px; font-size: 0.8em; margin: 2px; }\n table { width: 100%; border-collapse: collapse; }\n th, td { padding: 8px; text-align: left; border-bottom: 1px solid #ddd; }\n </style>\n</head>\n<body>\n <h1>🛡️ Pompelmi Scan Results</h1>\n <div class=\"summary\">\n <div class=\"card clean\"><h2>${clean}</h2><p>Clean Files</p></div>\n <div class=\"card suspicious\"><h2>${suspicious}</h2><p>Suspicious Files</p></div>\n <div class=\"card malicious\"><h2>${malicious}</h2><p>Malicious Files</p></div>\n </div>\n <h2>Detailed Results</h2>`;\n\n for (const report of data) {\n const statusClass = report.verdict;\n html += `<div class=\"result ${statusClass}\">`;\n html += `<h3>${this.escapeHtml(report.file?.name || \"Unknown\")}</h3>`;\n html += `<table>`;\n html += `<tr><th>Verdict</th><td>${report.verdict.toUpperCase()}</td></tr>`;\n html += `<tr><th>Size</th><td>${this.formatBytes(report.file?.size || 0)}</td></tr>`;\n html += `<tr><th>MIME Type</th><td>${this.escapeHtml(report.file?.mimeType || \"unknown\")}</td></tr>`;\n html += `<tr><th>Duration</th><td>${report.durationMs || 0}ms</td></tr>`;\n html += `<tr><th>Matches</th><td>${report.matches.length}</td></tr>`;\n html += `</table>`;\n\n if (options.includeDetails && report.matches.length > 0) {\n html += `<h4>Match Details:</h4><ul>`;\n for (const match of report.matches) {\n html += `<li><strong>${this.escapeHtml(match.rule)}</strong>`;\n if (match.tags && match.tags.length > 0) {\n html += ` ${match.tags.map((tag) => `<span class=\"badge\">${this.escapeHtml(tag)}</span>`).join(\"\")}`;\n }\n html += `</li>`;\n }\n html += `</ul>`;\n }\n html += `</div>`;\n }\n\n html += `</body></html>`;\n return html;\n }\n\n /**\n * Export to specified format\n */\n export(\n reports: ScanReport | ScanReport[],\n format: ExportFormat,\n options: ExportOptions = {},\n ): string {\n switch (format) {\n case \"json\":\n return this.toJSON(reports, options);\n case \"csv\":\n return this.toCSV(reports, options);\n case \"markdown\":\n return this.toMarkdown(reports, options);\n case \"html\":\n return this.toHTML(reports, options);\n case \"sarif\":\n return this.toSARIF(reports, options);\n default:\n throw new Error(`Unsupported export format: ${format}`);\n }\n }\n\n private escapeCsv(value: string): string {\n if (value.includes(\",\") || value.includes('\"') || value.includes(\"\\n\")) {\n return `\"${value.replace(/\"/g, '\"\"')}\"`;\n }\n return value;\n }\n\n private escapeHtml(value: string): string {\n return value\n .replace(/&/g, \"&\")\n .replace(/</g, \"<\")\n .replace(/>/g, \">\")\n .replace(/\"/g, \""\")\n .replace(/'/g, \"'\");\n }\n\n private formatBytes(bytes: number): string {\n if (bytes === 0) return \"0 Bytes\";\n const k = 1024;\n const sizes = [\"Bytes\", \"KB\", \"MB\", \"GB\"];\n const i = Math.floor(Math.log(bytes) / Math.log(k));\n return Math.round((bytes / k ** i) * 100) / 100 + \" \" + sizes[i];\n }\n}\n\n/**\n * Quick export helper\n */\nexport function exportScanResults(\n reports: ScanReport | ScanReport[],\n format: ExportFormat,\n options?: ExportOptions,\n): string {\n const exporter = new ScanResultExporter();\n return exporter.export(reports, format, options);\n}\n","/**\n * Validates a File by MIME type and size (max 5 MB).\n */\nexport function validateFile(file: File): { valid: boolean; error?: string } {\n const maxSize = 5 * 1024 * 1024;\n const allowedTypes = [\"text/plain\", \"application/json\", \"text/csv\"];\n\n if (!allowedTypes.includes(file.type)) {\n return { valid: false, error: \"Unsupported file type\" };\n }\n if (file.size > maxSize) {\n return { valid: false, error: \"File too large (max 5 MB)\" };\n }\n return { valid: true };\n}\n","// src/verdict.ts\nimport type { Verdict, YaraMatch } from \"./types\";\nexport function mapMatchesToVerdict(matches: YaraMatch[] = []): Verdict {\n if (!matches.length) return \"clean\";\n const malHints = [\"trojan\", \"ransom\", \"worm\", \"spy\", \"rootkit\", \"keylog\", \"botnet\"];\n const tagSet = new Set(matches.flatMap((m) => (m.tags ?? []).map((t) => t.toLowerCase())));\n const nameHit = (r: string) => malHints.some((h) => r.toLowerCase().includes(h));\n const isMal =\n matches.some((m) => nameHit(m.rule)) || tagSet.has(\"malware\") || tagSet.has(\"critical\");\n return isMal ? \"malicious\" : \"suspicious\";\n}\n"],"names":["MB","isZipLike","createHash"],"mappings":";;;;AAWA,MAAMA,IAAE,GAAG,IAAI,GAAG,IAAI;AAEf,MAAM,cAAc,GAAW;IACpC,iBAAiB,EAAE,CAAC,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,MAAM,EAAE,KAAK,CAAC;IACvD,gBAAgB,EAAE,CAAC,iBAAiB,EAAE,WAAW,EAAE,YAAY,EAAE,iBAAiB,EAAE,YAAY,CAAC;IACjG,gBAAgB,EAAE,EAAE,GAAGA,IAAE;AACzB,IAAA,SAAS,EAAE,IAAI;AACf,IAAA,WAAW,EAAE,CAAC;AACd,IAAA,UAAU,EAAE,IAAI;;AAGZ,SAAU,YAAY,CAAC,KAAA,GAAqB,EAAE,EAAA;IAClD,MAAM,CAAC,GAAW,EAAE,GAAG,cAAc,EAAE,GAAG,KAAK,EAAE;IACjD,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,iBAAiB,CAAC;AACrC,QAAA,MAAM,IAAI,SAAS,CAAC,oCAAoC,CAAC;IAC3D,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,gBAAgB,CAAC;AAAE,QAAA,MAAM,IAAI,SAAS,CAAC,mCAAmC,CAAC;AAChG,IAAA,IAAI,EAAE,MAAM,CAAC,QAAQ,CAAC,CAAC,CAAC,gBAAgB,CAAC,IAAI,CAAC,CAAC,gBAAgB,GAAG,CAAC,CAAC;AAClE,QAAA,MAAM,IAAI,SAAS,CAAC,8BAA8B,CAAC;AACrD,IAAA,IAAI,EAAE,MAAM,CAAC,QAAQ,CAAC,CAAC,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC,SAAS,GAAG,CAAC,CAAC;AACpD,QAAA,MAAM,IAAI,SAAS,CAAC,uBAAuB,CAAC;AAC9C,IAAA,IAAI,EAAE,MAAM,CAAC,SAAS,CAAC,CAAC,CAAC,WAAW,CAAC,IAAI,CAAC,CAAC,WAAW,GAAG,CAAC,CAAC;AACzD,QAAA,MAAM,IAAI,SAAS,CAAC,yBAAyB,CAAC;AAChD,IAAA,OAAO,CAAC;AACV;;AClCA;;;;;;;;;;;;;;;;;;;;;;;;AAwBG;AAIH,MAAM,EAAE,GAAG,IAAI;AACf,MAAM,EAAE,GAAG,IAAI,GAAG,EAAE;AAEpB;AAEA;;;;;;;;;AASG;AACI,MAAM,cAAc,GAAW,YAAY,CAAC;AACjD,IAAA,iBAAiB,EAAE;QACjB,KAAK;QACL,KAAK;QACL,MAAM;QACN,KAAK;QACL,MAAM;QACN,KAAK;QACL,MAAM;QACN,KAAK;QACL,KAAK;QACL,KAAK;QACL,KAAK;QACL,KAAK;QACL,MAAM;QACN,MAAM;QACN,KAAK;QACL,IAAI;AACL,KAAA;AACD,IAAA,gBAAgB,EAAE;QAChB,iBAAiB;QACjB,oBAAoB;QACpB,yEAAyE;QACzE,0BAA0B;QAC1B,mEAAmE;QACnE,+BAA+B;QAC/B,2EAA2E;QAC3E,yCAAyC;QACzC,gDAAgD;QAChD,iDAAiD;QACjD,UAAU;QACV,YAAY;QACZ,kBAAkB;QAClB,WAAW;QACX,eAAe;AAChB,KAAA;IACD,gBAAgB,EAAE,EAAE,GAAG,EAAE;AACzB,IAAA,SAAS,EAAE,KAAM;AACjB,IAAA,WAAW,EAAE,CAAC;AACd,IAAA,UAAU,EAAE,IAAI;AACjB,CAAA;AAED;;;;;;;;;AASG;AACI,MAAM,WAAW,GAAW,YAAY,CAAC;IAC9C,iBAAiB,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,KAAK,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,KAAK,EAAE,KAAK,EAAE,KAAK,CAAC;AAC7F,IAAA,gBAAgB,EAAE;QAChB,YAAY;QACZ,WAAW;QACX,WAAW;QACX,YAAY;QACZ,YAAY;QACZ,YAAY;QACZ,WAAW;QACX,cAAc;QACd,0BAA0B;AAC3B,KAAA;IACD,gBAAgB,EAAE,EAAE,GAAG,EAAE;AACzB,IAAA,SAAS,EAAE,IAAK;AAChB,IAAA,WAAW,EAAE,CAAC;AACd,IAAA,UAAU,EAAE,IAAI;AACjB,CAAA;AAED;;;;;;;;AAQG;AACI,MAAM,oBAAoB,GAAW,YAAY,CAAC;IACvD,iBAAiB,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,KAAK,CAAC;IACxD,gBAAgB,EAAE,CAAC,YAAY,EAAE,WAAW,EAAE,YAAY,EAAE,iBAAiB,CAAC;IAC9E,gBAAgB,EAAE,CAAC,GAAG,EAAE;AACxB,IAAA,SAAS,EAAE,IAAK;AAChB,IAAA,WAAW,EAAE,CAAC;AACd,IAAA,UAAU,EAAE,IAAI;AACjB,CAAA;AAED;;;;;;AAMG;AACI,MAAM,oBAAoB,GAAW,YAAY,CAAC;AACvD,IAAA,iBAAiB,EAAE,CAAC,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,MAAM,EAAE,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,CAAC;AACrF,IAAA,gBAAgB,EAAE;QAChB,iBAAiB;QACjB,WAAW;QACX,YAAY;QACZ,iBAAiB;QACjB,YAAY;QACZ,UAAU;QACV,yEAAyE;QACzE,mEAAmE;AACpE,KAAA;IACD,gBAAgB,EAAE,EAAE,GAAG,EAAE;AACzB,IAAA,SAAS,EAAE,IAAK;AAChB,IAAA,WAAW,EAAE,CAAC;AACd,IAAA,UAAU,EAAE,IAAI;AACjB,CAAA;AAED;;;;;;;;;;;;;;;AAeG;AACI,MAAM,QAAQ,GAAW,YAAY,CAAC;AAC3C,IAAA,iBAAiB,EAAE,CAAC,KAAK,EAAE,KAAK,EAAE,IAAI,EAAE,KAAK,EAAE,KAAK,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK,CAAC;AACxE,IAAA,gBAAgB,EAAE;QAChB,iBAAiB;QACjB,mBAAmB;QACnB,kBAAkB;QAClB,qBAAqB;QACrB,kBAAkB;QAClB,6BAA6B;QAC7B,8BAA8B;AAC/B,KAAA;IACD,gBAAgB,EAAE,GAAG,GAAG,EAAE;AAC1B,IAAA,SAAS,EAAE,KAAM;AACjB,IAAA,WAAW,EAAE,CAAC;AACd,IAAA,UAAU,EAAE,IAAI;AACjB,CAAA;AAWD;;;;;;;AAOG;AACI,MAAM,YAAY,GAAmC;AAC1D,IAAA,gBAAgB,EAAE,cAAc;AAChC,IAAA,aAAa,EAAE,WAAW;AAC1B,IAAA,sBAAsB,EAAE,oBAAoB;AAC5C,IAAA,sBAAsB,EAAE,oBAAoB;AAC5C,IAAA,QAAQ,EAAE,QAAQ;;AAGpB;;;AAGG;AACG,SAAU,aAAa,CAAC,IAAoB,EAAA;AAChD,IAAA,MAAM,MAAM,GAAG,YAAY,CAAC,IAAI,CAAC;AACjC,IAAA,IAAI,CAAC,MAAM;AACT,QAAA,MAAM,IAAI,KAAK,CACb,yBAAyB,IAAI,CAAA,gBAAA,EAAmB,MAAM,CAAC,IAAI,CAAC,YAAY,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAA,CAAE,CACvF;AACH,IAAA,OAAO,MAAM;AACf;;ACnNA,SAAS,aAAa,CAAC,GAAW,EAAE,KAAa,EAAA;;AAE/C,IAAA,OAAO,GAAG,CAAC,OAAO,CAAC,KAAK,EAAE,CAAC,EAAE,QAAQ,CAAC,KAAK,EAAE;AAC/C;AACA,SAAS,UAAU,CAAC,GAAW,EAAE,KAAe,EAAA;AAC9C,IAAA,IAAI,GAAG,CAAC,MAAM,GAAG,KAAK,CAAC,MAAM;AAAE,QAAA,OAAO,KAAK;AAC3C,IAAA,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,KAAK,CAAC,MAAM,EAAE,CAAC,EAAE;QAAE,IAAI,GAAG,CAAC,CAAC,CAAC,KAAK,KAAK,CAAC,CAAC,CAAC;AAAE,YAAA,OAAO,KAAK;AAC5E,IAAA,OAAO,IAAI;AACb;AAEA,SAAS,KAAK,CAAC,GAAW,EAAA;;AAExB,IAAA,OAAO,UAAU,CAAC,GAAG,EAAE,CAAC,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,CAAC,CAAC;AACxD;AACA,SAAS,QAAQ,CAAC,GAAW,EAAA;;AAE3B,IAAA,MAAM,GAAG,GAAG,CAAC,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,CAAC;AAC5D,IAAA,OAAO,UAAU,CAAC,GAAG,EAAE,GAAG,CAAC;AAC7B;AACA,SAASC,WAAS,CAAC,GAAW,EAAA;;AAE5B,IAAA,OAAO,UAAU,CAAC,GAAG,EAAE,CAAC,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,CAAC,CAAC;AAClD;AACA,SAAS,cAAc,CAAC,GAAW,EAAA;;IAEjC,OAAO,UAAU,CAAC,GAAG,EAAE,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC;AACtC;AAEA;AACA,SAAS,cAAc,CAAC,GAAW,EAAA;AACjC,IAAA,IAAI,CAACA,WAAS,CAAC,GAAG,CAAC;AAAE,QAAA,OAAO,KAAK;AACjC,IAAA,OAAO,aAAa,CAAC,GAAG,EAAE,gBAAgB,CAAC;AAC7C;AAEA;AACA,SAAS,aAAa,CAAC,GAAW,EAAA;IAChC,MAAM,MAAM,GAAG,CAAC,aAAa,EAAE,aAAa,EAAE,KAAK,EAAE,SAAS,CAAC;AAC/D,IAAA,OAAO,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,KAAK,aAAa,CAAC,GAAG,EAAE,CAAC,CAAC,CAAC;AACpD;AAEO,MAAM,uBAAuB,GAAkB;IACpD,MAAM,IAAI,CAAC,KAAiB,EAAA;QAC1B,MAAM,GAAG,GAAG,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC;QAC9B,MAAM,OAAO,GAAqB,EAAE;;AAGpC,QAAA,IAAI,QAAQ,CAAC,GAAG,CAAC,EAAE;AACjB,YAAA,OAAO,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,sBAAsB,EAAE,QAAQ,EAAE,YAAY,EAAE,CAAC;QACxE;AACA,QAAA,IAAI,cAAc,CAAC,GAAG,CAAC,EAAE;AACvB,YAAA,OAAO,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,qBAAqB,EAAE,QAAQ,EAAE,YAAY,EAAE,CAAC;QACvE;;AAGA,QAAA,IAAI,KAAK,CAAC,GAAG,CAAC,EAAE;AACd,YAAA,MAAM,IAAI,GAAG,aAAa,CAAC,GAAG,CAAC;AAC/B,YAAA,IAAI,IAAI,CAAC,MAAM,EAAE;gBACf,OAAO,CAAC,IAAI,CAAC;AACX,oBAAA,IAAI,EAAE,mBAAmB;AACzB,oBAAA,QAAQ,EAAE,YAAY;AACtB,oBAAA,IAAI,EAAE,EAAE,MAAM,EAAE,IAAI,EAAE;AACvB,iBAAA,CAAC;YACJ;QACF;;AAGA,QAAA,IAAI,cAAc,CAAC,GAAG,CAAC,EAAE;AACvB,YAAA,OAAO,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,yBAAyB,EAAE,QAAQ,EAAE,YAAY,EAAE,CAAC;QAC3E;;QAGA,MAAM,YAAY,GAAG,kEAAkE;AACvF,QAAA,IAAI,aAAa,CAAC,GAAG,EAAE,YAAY,CAAC,EAAE;YACpC,OAAO,CAAC,IAAI,CAAC;AACX,gBAAA,IAAI,EAAE,iBAAiB;AACvB,gBAAA,QAAQ,EAAE,MAAM;AAChB,gBAAA,IAAI,EAAE,EAAE,IAAI,EAAE,6CAA6C,EAAE;AAC9D,aAAA,CAAC;QACJ;AAEA,QAAA,OAAO,OAAO;IAChB,CAAC;;;AC1BH,SAAS,QAAQ,CAAC,CAAU,EAAA;AAC1B,IAAA,QAAQ,OAAO,CAAC,KAAK,UAAU,GAAG,CAAC,GAAG,CAAC,CAAC,IAAI;AAC9C;AAEA;AACA,SAAS,cAAc,CAAC,CAAQ,EAAA;AAC9B,IAAA,MAAM,CAAC,GAAG,CAAC,CAAC,QAAQ;IACpB,IAAI,CAAC,KAAK,UAAU,IAAI,CAAC,KAAK,MAAM,IAAI,CAAC,KAAK,WAAW;AAAE,QAAA,OAAO,WAAW;AAC7E,IAAA,IAAI,CAAC,KAAK,QAAQ,IAAI,CAAC,KAAK,KAAK,IAAI,CAAC,KAAK,YAAY,IAAI,CAAC,KAAK,MAAM;AAAE,QAAA,OAAO,YAAY;AAC5F,IAAA,OAAO,OAAO;AAChB;AAEA;AACA,SAAS,eAAe,CAAC,OAAgB,EAAA;AACvC,IAAA,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC;AAAE,QAAA,OAAO,IAAI;AACrC,IAAA,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,cAAc,CAAC,CAAC,CAAC,KAAK,WAAW,CAAC;AAAE,QAAA,OAAO,WAAW;AAC9E,IAAA,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,cAAc,CAAC,CAAC,CAAC,KAAK,YAAY,CAAC;AAAE,QAAA,OAAO,YAAY;AAChF,IAAA,OAAO,OAAO;AAChB;AAEA,MAAM,aAAa,GAA4B,EAAE,SAAS,EAAE,CAAC,EAAE,UAAU,EAAE,CAAC,EAAE,KAAK,EAAE,CAAC,EAAE;AAExF,SAAS,UAAU,CAAC,OAAgB,EAAE,MAA2B,EAAA;AAC/D,IAAA,IAAI,CAAC,MAAM;AAAE,QAAA,OAAO,KAAK;AACzB,IAAA,MAAM,OAAO,GAAG,eAAe,CAAC,OAAO,CAAC;AACxC,IAAA,IAAI,CAAC,OAAO;AAAE,QAAA,OAAO,KAAK;IAC1B,OAAO,aAAa,CAAC,OAAO,CAAC,IAAI,aAAa,CAAC,MAAM,CAAC;AACxD;AAEA,eAAe,cAAc,CAAI,EAAoB,EAAE,SAA6B,EAAA;AAClF,IAAA,IAAI,CAAC,SAAS;QAAE,OAAO,EAAE,EAAE;IAC3B,OAAO,IAAI,OAAO,CAAI,CAAC,OAAO,EAAE,MAAM,KAAI;AACxC,QAAA,MAAM,KAAK,GAAG,UAAU,CAAC,MAAM,MAAM,CAAC,IAAI,KAAK,CAAC,iBAAiB,CAAC,CAAC,EAAE,SAAS,CAAC;AAC/E,QAAA,EAAE,EAAE,CAAC,IAAI,CACP,CAAC,CAAC,KAAI;YACJ,YAAY,CAAC,KAAK,CAAC;YACnB,OAAO,CAAC,CAAC,CAAC;AACZ,QAAA,CAAC,EACD,CAAC,CAAC,KAAI;YACJ,YAAY,CAAC,KAAK,CAAC;YACnB,MAAM,CAAC,CAAC,CAAC;AACX,QAAA,CAAC,CACF;AACH,IAAA,CAAC,CAAC;AACJ;AA0BA;AACM,SAAU,eAAe,CAAC,GAAG,IAAW,EAAA;AAC5C,IAAA,MAAM,KAAK,GAA6B,IAAI,CAAC,CAAC,CAAC;IAC/C,MAAM,IAAI,GAA2C,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC;;AAElE,IAAA,IACE,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC;AACpB,SAAC,KAAK,CAAC,MAAM,KAAK,CAAC,KAAK,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,IAAI,OAAO,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,KAAK,QAAQ,CAAC,CAAC,EACpF;QACA,MAAM,OAAO,GAAG,KAAuB;AACvC,QAAA,MAAM,IAAI,GACR,IAAI,CAAC,MAAM,GAAG,CAAC;YACf,CAAC,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AACvB,YAAA,OAAO,IAAI,CAAC,CAAC,CAAC,KAAK,UAAU;YAC7B,EAAE,OAAO,IAAI,CAAC,CAAC,CAAC,KAAK,QAAQ,IAAI,IAAI,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,MAAM,IAAK,IAAI,CAAC,CAAC,CAAY;AAChF,cAAG,IAAI,CAAC,CAAC;cACP,EAAE;AAER,QAAA,OAAO,OAAO,KAAU,EAAE,GAAS,KAAI;YACrC,MAAM,GAAG,GAAY,EAAE;AAEvB,YAAA,IAAI,IAAI,CAAC,QAAQ,EAAE;;AAEjB,gBAAA,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,UAAU,CACtC,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,KAAK,EAAE,OAAO,CAAC,KAC3B,cAAc,CAAC,MAAM,QAAQ,CAAC,OAAO,CAAC,CAAC,KAAK,EAAE,GAAG,CAAC,EAAE,IAAI,CAAC,mBAAmB,CAAC,CAC9E,CACF;AACD,gBAAA,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE;AACvC,oBAAA,MAAM,MAAM,GAAG,OAAO,CAAC,CAAC,CAAC;AACzB,oBAAA,IAAI,MAAM,CAAC,MAAM,KAAK,WAAW,IAAI,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE;AAChE,wBAAA,MAAM,OAAO,GAAG,IAAI,CAAC;AACnB,8BAAE,MAAM,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAQ,MAAM;AAC9B,gCAAA,GAAG,CAAC;AACJ,gCAAA,IAAI,EAAE,EAAE,GAAG,CAAC,CAAC,IAAI,EAAE,WAAW,EAAE,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;AAChD,6BAAA,CAAC;AACJ,8BAAE,MAAM,CAAC,KAAK;AAChB,wBAAA,GAAG,CAAC,IAAI,CAAC,GAAG,OAAO,CAAC;oBACtB;gBACF;YACF;iBAAO;;gBAEL,KAAK,MAAM,CAAC,IAAI,EAAE,OAAO,CAAC,IAAI,OAAO,EAAE;AACrC,oBAAA,IAAI;wBACF,MAAM,GAAG,GAAG,MAAM,cAAc,CAC9B,MAAM,QAAQ,CAAC,OAAO,CAAC,CAAC,KAAK,EAAE,GAAG,CAAC,EACnC,IAAI,CAAC,mBAAmB,CACzB;AACD,wBAAA,IAAI,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,EAAE;AACtB,4BAAA,MAAM,OAAO,GAAG,IAAI,CAAC;AACnB,kCAAE,GAAG,CAAC,GAAG,CAAC,CAAC,CAAQ,MAAM,EAAE,GAAG,CAAC,EAAE,IAAI,EAAE,EAAE,GAAG,CAAC,CAAC,IAAI,EAAE,WAAW,EAAE,IAAI,EAAE,EAAE,CAAC;kCACxE,GAAG;AACP,4BAAA,GAAG,CAAC,IAAI,CAAC,GAAG,OAAO,CAAC;AACpB,4BAAA,IAAI,UAAU,CAAC,GAAG,EAAE,IAAI,CAAC,MAAM,CAAC;gCAAE;wBACpC;oBACF;AAAE,oBAAA,MAAM;;oBAER;gBACF;YACF;AAEA,YAAA,OAAO,GAAG;AACZ,QAAA,CAAC;IACH;;AAGA,IAAA,MAAM,QAAQ,GAAG,CAAC,KAAgB,EAAE,GAAI,IAAkB,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC;AAC3E,IAAA,OAAO,OAAO,KAAU,EAAE,GAAS,KAAI;QACrC,MAAM,GAAG,GAAY,EAAE;AACvB,QAAA,KAAK,MAAM,CAAC,IAAI,QAAQ,EAAE;AACxB,YAAA,IAAI;AACF,gBAAA,MAAM,GAAG,GAAG,MAAM,QAAQ,CAAC,CAAC,CAAC,CAAC,KAAK,EAAE,GAAG,CAAC;AACzC,gBAAA,IAAI,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC;AAAE,oBAAA,GAAG,CAAC,IAAI,CAAC,GAAG,GAAG,CAAC;YAC1C;AAAE,YAAA,MAAM;;YAER;QACF;AACA,QAAA,OAAO,GAAG;AACZ,IAAA,CAAC;AACH;SAEgB,mBAAmB,CAAC,MAAkB,EAAE,OAAsB,EAAE,EAAA;AAC9E,IAAA,MAAM,YAAY,GAAc,CAAC,uBAAuB,CAAC;IACzD,MAAM,sBAAsB,GAAmC,EAAE;;IAGjE,IACE,MAAM,KAAK,qBAAqB;AAChC,QAAA,MAAM,KAAK,oBAAoB;AAC/B,QAAA,MAAM,KAAK,kBAAkB;QAC7B,IAAI,CAAC,mBAAmB,EACxB;QACA,MAAM,KAAK,GACT,MAAM,KAAK,oBAAoB,IAAI,MAAM,KAAK;AAC5C,cAAE;cACA,MAAM,KAAK;AACX,kBAAE;AACF,kBAAE,IAAI,CAAC,kBAAkB,IAAI,OAAO;AAC1C,QAAA,IAAI,YAA+D;AAEnE,QAAA,IAAI;;YAEF,YAAY,GAAG,IAAI,QAAQ,CAAC,WAAW,EAAE,0BAA0B,CAElD;QACnB;AAAE,QAAA,MAAM;YACN,YAAY,GAAG,SAAS;QAC1B;AAEA,QAAA,IACE,YAAY;aACX,CAAC,IAAI,CAAC,mBAAmB;gBACxB,IAAI,CAAC,mBAAmB,KAAK,kBAAkB;AAC/C,gBAAA,IAAI,CAAC,mBAAmB,KAAK,MAAM,CAAC,EACtC;AACA,YAAA,sBAAsB,CAAC,IAAI,CACzB,YAAY,CAAC,8BAA8B;iBACxC,IAAI,CACH,CAAC,GAAQ,KACP,GAAG,CAAC,wBAAwB,CAAC;gBAC3B,OAAO,EAAE,IAAI,CAAC,oBAAoB,IAAI,IAAI,CAAC,OAAO,IAAI,KAAK;gBAC3D,KAAK;gBACL,UAAU,EAAE,IAAI,CAAC,UAAU;gBAC3B,eAAe,EAAE,IAAI,CAAC,eAAe;AACtC,aAAA,CAAY;AAEhB,iBAAA,KAAK,CAAC,MAAM,IAAI,CAAC,CACrB;QACH;AAEA,QAAA,IACE,YAAY;aACX,CAAC,IAAI,CAAC,mBAAmB;gBACxB,IAAI,CAAC,mBAAmB,KAAK,cAAc;AAC3C,gBAAA,IAAI,CAAC,mBAAmB,KAAK,MAAM,CAAC,EACtC;AACA,YAAA,sBAAsB,CAAC,IAAI,CACzB,YAAY,CAAC,yBAAyB;iBACnC,IAAI,CACH,CAAC,GAAQ,KACP,GAAG,CAAC,mBAAmB,CAAC;gBACtB,OAAO,EAAE,IAAI,CAAC,oBAAoB,IAAI,IAAI,CAAC,OAAO,IAAI,KAAK;gBAC3D,KAAK;gBACL,UAAU,EAAE,IAAI,CAAC,UAAU;gBAC3B,eAAe,EAAE,IAAI,CAAC,eAAe;AACtC,aAAA,CAAY;AAEhB,iBAAA,KAAK,CAAC,MAAM,IAAI,CAAC,CACrB;QACH;IACF;AAOA,IAAA,IAAI,sBAAmD;AAEvD,IAAA,MAAM,kBAAkB,GAAG,YAA4B;AACrD,QAAA,sBAAsB,KAAtB,sBAAsB,GAAK,OAAO,CAAC,GAAG,CAAC,sBAAsB,CAAC,CAAC,IAAI,CAAC,CAAC,eAAe,KAClF,eAAe,CACb,GAAG,YAAY,EACf,GAAG,eAAe,CAAC,MAAM,CAAC,CAAC,OAAO,KAAyB,OAAO,KAAK,IAAI,CAAC,CAC7E,CACF,CAAA;AACD,QAAA,OAAO,sBAAsB;AAC/B,IAAA,CAAC;AAED,IAAA,OAAO,OAAO,KAAK,EAAE,GAAG,KAAI;AAC1B,QAAA,MAAM,OAAO,GAAG,MAAM,kBAAkB,EAAE;AAC1C,QAAA,OAAO,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC;AAC5B,IAAA,CAAC;AACH;;ACzTA;;;AAGG;AAIH;;;AAGG;AACG,SAAU,cAAc,CAAC,KAAiB,EAAA;IAC9C,MAAM,OAAO,GAAY,EAAE;;AAG3B,IAAA,IAAI,gBAAgB,CAAC,KAAK,CAAC,EAAE;QAC3B,OAAO,CAAC,IAAI,CAAC;AACX,YAAA,IAAI,EAAE,kBAAkB;AACxB,YAAA,QAAQ,EAAE,MAAM;AAChB,YAAA,IAAI,EAAE,EAAE,WAAW,EAAE,6CAA6C,EAAE;AACrE,SAAA,CAAC;IACJ;;AAGA,IAAA,IAAI,qBAAqB,CAAC,KAAK,CAAC,EAAE;QAChC,OAAO,CAAC,IAAI,CAAC;AACX,YAAA,IAAI,EAAE,uBAAuB;AAC7B,YAAA,QAAQ,EAAE,MAAM;AAChB,YAAA,IAAI,EAAE,EAAE,WAAW,EAAE,+CAA+C,EAAE;AACvE,SAAA,CAAC;IACJ;;AAGA,IAAA,IAAI,OAAO,CAAC,KAAK,CAAC,EAAE;QAClB,OAAO,CAAC,IAAI,CAAC;AACX,YAAA,IAAI,EAAE,gBAAgB;AACtB,YAAA,QAAQ,EAAE,UAAU;AACpB,YAAA,IAAI,EAAE,EAAE,WAAW,EAAE,gCAAgC,EAAE;AACxD,SAAA,CAAC;IACJ;AAEA,IAAA,OAAO,OAAO;AAChB;AAEA;;AAEG;AACG,SAAU,uBAAuB,CAAC,KAAiB,EAAA;IACvD,MAAM,OAAO,GAAY,EAAE;AAC3B,IAAA,MAAM,IAAI,GAAG,IAAI,WAAW,CAAC,OAAO,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC,CAAC,MAAM,CAC5D,KAAK,CAAC,KAAK,CAAC,CAAC,EAAE,IAAI,CAAC,GAAG,CAAC,EAAE,GAAG,IAAI,EAAE,KAAK,CAAC,MAAM,CAAC,CAAC,CAClD;;AAGD,IAAA,MAAM,mBAAmB,GAAG;QAC1B,6BAA6B;QAC7B,yBAAyB;QACzB,sDAAsD;AACtD,QAAA,kBAAkB;AAClB,QAAA,kBAAkB;KACnB;AAED,IAAA,KAAK,MAAM,OAAO,IAAI,mBAAmB,EAAE;AACzC,QAAA,IAAI,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE;YACtB,OAAO,CAAC,IAAI,CAAC;AACX,gBAAA,IAAI,EAAE,mBAAmB;AACzB,gBAAA,QAAQ,EAAE,QAAQ;AAClB,gBAAA,IAAI,EAAE;AACJ,oBAAA,WAAW,EAAE,oCAAoC;oBACjD,OAAO,EAAE,OAAO,CAAC,MAAM;AACxB,iBAAA;AACF,aAAA,CAAC;YACF;QACF;IACF;AAEA,IAAA,OAAO,OAAO;AAChB;AAEA;;AAEG;SACa,qBAAqB,CACnC,KAAiB,EACjB,QAAQ,GAAG,EAAE,EAAA;IAEb,IAAI,KAAK,GAAG,CAAC;IACb,IAAI,YAAY,GAAG,KAAK;AAExB,IAAA,OAAO,KAAK,GAAG,QAAQ,EAAE;AACvB,QAAA,IAAI,SAAS,CAAC,YAAY,CAAC,EAAE;AAC3B,YAAA,KAAK,EAAE;AAIP,YAEO;gBACL;YACF;QACF;aAAO;YACL;QACF;IACF;IAEA,OAAO;QACL,KAAK;QACL,mBAAmB,EAAE,KAAK,IAAI,CAAC;KAChC;AACH;AAEA;AAEA,SAAS,gBAAgB,CAAC,KAAiB,EAAA;AACzC,IAAA,IAAI,KAAK,CAAC,MAAM,GAAG,CAAC;AAAE,QAAA,OAAO,KAAK;;AAGlC,IAAA,MAAM,MAAM,GAAG,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI;;IAG/F,IAAI,MAAM,GAAG,KAAK;IAClB,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,EAAE,IAAI,CAAC,EAAE,CAAC,EAAE,EAAE;AACzD,QAAA,IACE,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI;AACjB,YAAA,KAAK,CAAC,CAAC,GAAG,CAAC,CAAC,KAAK,IAAI;AACrB,YAAA,KAAK,CAAC,CAAC,GAAG,CAAC,CAAC,KAAK,IAAI;YACrB,KAAK,CAAC,CAAC,GAAG,CAAC,CAAC,KAAK,IAAI,EACrB;YACA,MAAM,GAAG,IAAI;YACb;QACF;IACF;IAEA,OAAO,MAAM,IAAI,MAAM;AACzB;AAEA,SAAS,qBAAqB,CAAC,KAAiB,EAAA;AAC9C,IAAA,IAAI,KAAK,CAAC,MAAM,GAAG,GAAG;AAAE,QAAA,OAAO,KAAK;;AAGpC,IAAA,MAAM,OAAO,GACX,CAAC,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI;AACvC,SAAC,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,CAAC;SACjF,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,CAAC,CAAC;AAEhE,IAAA,IAAI,CAAC,OAAO;AAAE,QAAA,OAAO,KAAK;;AAG1B,IAAA,MAAM,IAAI,GAAG,IAAI,WAAW,CAAC,OAAO,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC;AACrE,IAAA,OAAO,2CAA2C,CAAC,IAAI,CAAC,IAAI,CAAC;AAC/D;AAEA,SAAS,OAAO,CAAC,KAAiB,EAAA;AAChC,IAAA,IAAI,KAAK,CAAC,MAAM,GAAG,GAAG;AAAE,QAAA,OAAO,KAAK;;IAGpC,MAAM,KAAK,GAAG,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI;;IAGzE,IAAI,MAAM,GAAG,KAAK;IAClB,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,EAAE,IAAI,CAAC,EAAE,CAAC,EAAE,EAAE;AACzD,QAAA,IACE,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI;AACjB,YAAA,KAAK,CAAC,CAAC,GAAG,CAAC,CAAC,KAAK,IAAI;AACrB,YAAA,KAAK,CAAC,CAAC,GAAG,CAAC,CAAC,KAAK,IAAI;YACrB,KAAK,CAAC,CAAC,GAAG,CAAC,CAAC,KAAK,IAAI,EACrB;YACA,MAAM,GAAG,IAAI;YACb;QACF;IACF;IAEA,OAAO,KAAK,IAAI,MAAM;AACxB;AAEA,SAAS,SAAS,CAAC,KAAiB,EAAA;AAClC,IAAA,IAAI,KAAK,CAAC,MAAM,GAAG,CAAC;AAAE,QAAA,OAAO,KAAK;IAElC;;IAEE,CAAC,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI;;SAEhF,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,CAAC;;SAEjF,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,CAAC;;AAElF,SAAC,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,IAAI,CAAC;AAE5C;;AC5LA;;;AAGG;AAsCH;;AAEG;MACU,gBAAgB,CAAA;AAc3B,IAAA,WAAA,CAAY,UAAwB,EAAE,EAAA;AAb9B,QAAA,IAAA,CAAA,KAAK,GAA4B,IAAI,GAAG,EAAE;;AAO1C,QAAA,IAAA,CAAA,KAAK,GAAG;AACd,YAAA,IAAI,EAAE,CAAC;AACP,YAAA,MAAM,EAAE,CAAC;AACT,YAAA,SAAS,EAAE,CAAC;SACb;QAGC,IAAI,CAAC,OAAO,GAAG,OAAO,CAAC,OAAO,IAAI,IAAI;QACtC,IAAI,CAAC,GAAG,GAAG,OAAO,CAAC,GAAG,IAAI,OAAO,CAAC;QAClC,IAAI,CAAC,SAAS,GAAG,OAAO,CAAC,SAAS,IAAI,IAAI;QAC1C,IAAI,CAAC,WAAW,GAAG,OAAO,CAAC,WAAW,IAAI,KAAK;IACjD;AAEA;;AAEG;IACK,WAAW,CAAC,OAAmB,EAAE,MAAe,EAAA;AACtD,QAAA,MAAM,IAAI,GAAGC,iBAAU,CAAC,QAAQ;aAC7B,MAAM,CAAC,OAAO;AACd,aAAA,MAAM,CAAC,MAAM,IAAI,SAAS;aAC1B,MAAM,CAAC,KAAK,CAAC;AAChB,QAAA,OAAO,IAAI;IACb;AAEA;;AAEG;AACK,IAAA,OAAO,CAAC,KAAiB,EAAA;AAC/B,QAAA,OAAO,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,CAAC,SAAS,GAAG,IAAI,CAAC,GAAG;IAChD;AAEA;;AAEG;IACK,KAAK,GAAA;AACX,QAAA,IAAI,IAAI,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC;YAAE;QAE3B,IAAI,SAAS,GAAkB,IAAI;QACnC,IAAI,UAAU,GAAG,QAAQ;QACzB,IAAI,YAAY,GAAG,QAAQ;AAE3B,QAAA,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,EAAE;AAC/C,YAAA,IAAI,IAAI,CAAC,SAAS,EAAE;;AAElB,gBAAA,IAAI,KAAK,CAAC,SAAS,GAAG,UAAU,EAAE;AAChC,oBAAA,UAAU,GAAG,KAAK,CAAC,SAAS;oBAC5B,SAAS,GAAG,GAAG;gBACjB;YACF;iBAAO;;AAEL,gBAAA,IAAI,KAAK,CAAC,WAAW,GAAG,YAAY,EAAE;AACpC,oBAAA,YAAY,GAAG,KAAK,CAAC,WAAW;oBAChC,SAAS,GAAG,GAAG;gBACjB;YACF;QACF;QAEA,IAAI,SAAS,EAAE;AACb,YAAA,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,SAAS,CAAC;YAC5B,IAAI,IAAI,CAAC,WAAW;AAAE,gBAAA,IAAI,CAAC,KAAK,CAAC,SAAS,EAAE;QAC9C;IACF;AAEA;;AAEG;AACH,IAAA,GAAG,CAAC,OAAmB,EAAE,MAAkB,EAAE,MAAe,EAAA;QAC1D,MAAM,GAAG,GAAG,IAAI,CAAC,WAAW,CAAC,OAAO,EAAE,MAAM,CAAC;;QAG7C,IAAI,IAAI,CAAC,KAAK,CAAC,IAAI,IAAI,IAAI,CAAC,OAAO,EAAE;YACnC,IAAI,CAAC,KAAK,EAAE;QACd;AAEA,QAAA,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,GAAG,EAAE;YAClB,MAAM;AACN,YAAA,SAAS,EAAE,IAAI,CAAC,GAAG,EAAE;AACrB,YAAA,WAAW,EAAE,CAAC;AACf,SAAA,CAAC;IACJ;AAEA;;AAEG;IACH,GAAG,CAAC,OAAmB,EAAE,MAAe,EAAA;QACtC,MAAM,GAAG,GAAG,IAAI,CAAC,WAAW,CAAC,OAAO,EAAE,MAAM,CAAC;QAC7C,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC;QAEjC,IAAI,CAAC,KAAK,EAAE;YACV,IAAI,IAAI,CAAC,WAAW;AAAE,gBAAA,IAAI,CAAC,KAAK,CAAC,MAAM,EAAE;AACzC,YAAA,OAAO,IAAI;QACb;QAEA,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE;AACxB,YAAA,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC;YACtB,IAAI,IAAI,CAAC,WAAW;AAAE,gBAAA,IAAI,CAAC,KAAK,CAAC,MAAM,EAAE;AACzC,YAAA,OAAO,IAAI;QACb;;QAGA,KAAK,CAAC,WAAW,EAAE;QACnB,KAAK,CAAC,SAAS,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;QAE7B,IAAI,IAAI,CAAC,WAAW;AAAE,YAAA,IAAI,CAAC,KAAK,CAAC,IAAI,EAAE;QACvC,OAAO,KAAK,CAAC,MAAM;IACrB;AAEA;;AAEG;IACH,GAAG,CAAC,OAAmB,EAAE,MAAe,EAAA;QACtC,MAAM,GAAG,GAAG,IAAI,CAAC,WAAW,CAAC,OAAO,EAAE,MAAM,CAAC;QAC7C,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC;QACjC,OAAO,KAAK,KAAK,SAAS,IAAI,IAAI,CAAC,OAAO,CAAC,KAAK,CAAC;IACnD;AAEA;;AAEG;IACH,KAAK,GAAA;AACH,QAAA,IAAI,CAAC,KAAK,CAAC,KAAK,EAAE;AAClB,QAAA,IAAI,IAAI,CAAC,WAAW,EAAE;AACpB,YAAA,IAAI,CAAC,KAAK,CAAC,IAAI,GAAG,CAAC;AACnB,YAAA,IAAI,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC;AACrB,YAAA,IAAI,CAAC,KAAK,CAAC,SAAS,GAAG,CAAC;QAC1B;IACF;AAEA;;AAEG;IACH,KAAK,GAAA;QACH,IAAI,OAAO,GAAG,CAAC;AACf,QAAA,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,EAAE;YAC/C,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE;AACxB,gBAAA,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC;AACtB,gBAAA,OAAO,EAAE;YACX;QACF;AACA,QAAA,OAAO,OAAO;IAChB;AAEA;;AAEG;IACH,QAAQ,GAAA;AACN,QAAA,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,MAAM;QACjD,MAAM,OAAO,GAAG,KAAK,GAAG,CAAC,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,GAAG,KAAK,IAAI,GAAG,GAAG,CAAC;QAE/D,OAAO;AACL,YAAA,IAAI,EAAE,IAAI,CAAC,KAAK,CAAC,IAAI;AACrB,YAAA,MAAM,EAAE,IAAI,CAAC,KAAK,CAAC,MAAM;AACzB,YAAA,IAAI,EAAE,IAAI,CAAC,KAAK,CAAC,IAAI;YACrB,OAAO;AACP,YAAA,SAAS,EAAE,IAAI,CAAC,KAAK,CAAC,SAAS;SAChC;IACH;AAEA;;AAEG;AACH,IAAA,IAAI,IAAI,GAAA;AACN,QAAA,OAAO,IAAI,CAAC,KAAK,CAAC,IAAI;IACxB;AACD;AAED;AACA,IAAI,YAAY,GAA4B,IAAI;AAEhD;;AAEG;AACG,SAAU,eAAe,CAAC,OAAsB,EAAA;IACpD,IAAI,CAAC,YAAY,EAAE;AACjB,QAAA,YAAY,GAAG,IAAI,gBAAgB,CAAC,OAAO,CAAC;IAC9C;AACA,IAAA,OAAO,YAAY;AACrB;;ACrOA;;;AAGG;AAsCH;;AAEG;MACU,kBAAkB,CAAA;AAI7B,IAAA,WAAA,GAAA;AAFQ,QAAA,IAAA,CAAA,WAAW,GAAwB,IAAI,GAAG,EAAE;AAGlD,QAAA,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC,GAAG,EAAE;IAC7B;AAEA;;AAEG;AACH,IAAA,UAAU,CAAC,IAAY,EAAA;AACrB,QAAA,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,IAAI,EAAE,IAAI,CAAC,GAAG,EAAE,CAAC;IACxC;AAEA;;AAEG;AACH,IAAA,WAAW,CAAC,KAAc,EAAA;AACxB,QAAA,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,EAAE;QACtB,IAAI,KAAK,IAAI,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,KAAK,CAAC,EAAE;AACxC,YAAA,OAAO,GAAG,IAAI,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,KAAK,CAAC,IAAI,GAAG,CAAC;QACnD;AACA,QAAA,OAAO,GAAG,GAAG,IAAI,CAAC,SAAS;IAC7B;AAEA;;AAEG;AACH,IAAA,UAAU,CAAC,YAAoB,EAAA;AAC7B,QAAA,MAAM,aAAa,GAAG,IAAI,CAAC,WAAW,EAAE;AACxC,QAAA,MAAM,UAAU,GAAG,aAAa,GAAG,CAAC,GAAG,CAAC,YAAY,GAAG,aAAa,IAAI,IAAI,GAAG,CAAC;QAEhF,OAAO;AACL,YAAA,eAAe,EAAE,aAAa;YAC9B,oBAAoB,EAAE,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,gBAAgB;AACzD,kBAAE,CAAC,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,gBAAgB,CAAC,IAAI,CAAC;qBAC3C,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,kBAAkB,CAAC,IAAI,CAAC;AAChD,kBAAE,SAAS;YACb,cAAc,EAAE,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,UAAU;kBAC3C,CAAC,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,UAAU,CAAC,IAAI,CAAC,KAAK,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,YAAY,CAAC,IAAI,CAAC;AACpF,kBAAE,SAAS;YACb,cAAc,EAAE,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,UAAU;AAC7C,kBAAE,CAAC,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,IAAI,CAAC;AACjD,kBAAE,SAAS;AACb,YAAA,aAAa,EAAE,UAAU;YACzB,YAAY;YACZ,SAAS,EAAE,IAAI,CAAC,SAAS;AACzB,YAAA,WAAW,EAAE,IAAI,CAAC,GAAG,EAAE;SACxB;IACH;AACD;AAED;;AAEG;AACG,SAAU,kBAAkB,CAChC,OAAkF,EAAA;IAElF,IAAI,UAAU,GAAG,CAAC;IAClB,IAAI,eAAe,GAAG,CAAC;IACvB,IAAI,cAAc,GAAG,CAAC;IACtB,IAAI,aAAa,GAAG,CAAC;IACrB,IAAI,UAAU,GAAG,CAAC;IAClB,IAAI,kBAAkB,GAAG,CAAC;AAE1B,IAAA,KAAK,MAAM,MAAM,IAAI,OAAO,EAAE;AAC5B,QAAA,IAAI,MAAM,CAAC,OAAO,KAAK,OAAO;AAAE,YAAA,UAAU,EAAE;AACvC,aAAA,IAAI,MAAM,CAAC,OAAO,KAAK,YAAY;AAAE,YAAA,eAAe,EAAE;AACtD,aAAA,IAAI,MAAM,CAAC,OAAO,KAAK,WAAW;AAAE,YAAA,cAAc,EAAE;AAEzD,QAAA,IAAI,MAAM,CAAC,UAAU,KAAK,SAAS,EAAE;AACnC,YAAA,aAAa,IAAI,MAAM,CAAC,UAAU;AAClC,YAAA,kBAAkB,EAAE;QACtB;QAEA,IAAI,MAAM,CAAC,IAAI,EAAE,IAAI,KAAK,SAAS,EAAE;AACnC,YAAA,UAAU,IAAI,MAAM,CAAC,IAAI,CAAC,IAAI;QAChC;IACF;AAEA,IAAA,MAAM,WAAW,GAAG,kBAAkB,GAAG,CAAC,GAAG,aAAa,GAAG,kBAAkB,GAAG,CAAC;AACnF,IAAA,MAAM,aAAa,GAAG,aAAa,GAAG,CAAC,GAAG,CAAC,UAAU,GAAG,aAAa,IAAI,IAAI,GAAG,CAAC;IAEjF,OAAO;QACL,UAAU,EAAE,OAAO,CAAC,MAAM;QAC1B,UAAU;QACV,eAAe;QACf,cAAc;AACd,QAAA,aAAa,EAAE,WAAW;AAC1B,QAAA,gBAAgB,EAAE,aAAa;AAC/B,QAAA,iBAAiB,EAAE,UAAU;KAC9B;AACH;;AC9HA;AACA,SAAS,cAAc,CAAC,IAAa,EAAA;AACnC,IAAA,IAAI,CAAC,IAAI;QAAE;AACX,IAAA,MAAM,GAAG,GAAG,IAAI,CAAC,WAAW,EAAE,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE;IAC/C,QAAQ,GAAG;AACT,QAAA,KAAK,KAAK;AACR,YAAA,OAAO,iBAAiB;AAC1B,QAAA,KAAK,KAAK;AACR,YAAA,OAAO,WAAW;AACpB,QAAA,KAAK,KAAK;AACV,QAAA,KAAK,MAAM;AACT,YAAA,OAAO,YAAY;AACrB,QAAA,KAAK,KAAK;AACR,YAAA,OAAO,iBAAiB;AAC1B,QAAA,KAAK,KAAK;AACR,YAAA,OAAO,YAAY;AACrB,QAAA;YACE;;AAEN;AAEA;AACA,SAAS,cAAc,CAAC,OAAoB,EAAA;IAC1C,IAAI,CAAC,OAAO,CAAC,MAAM;AAAE,QAAA,OAAO,OAAO;;AAEnC,IAAA,MAAM,OAAO,GAAG,OAAO,CAAC,IAAI,CAC1B,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,IAAI,EAAE,EAAE,QAAQ,CAAC,UAAU,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,IAAI,EAAE,EAAE,QAAQ,CAAC,MAAM,CAAC,CAC9E;IACD,OAAO,OAAO,GAAG,WAAW,GAAG,YAAY;AAC7C;AAEA;AACA,SAAS,aAAa,CAAC,EAAW,EAAA;IAChC,OAAO,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC,MAAM;QACpB,IAAI,EAAE,CAAC,CAAC,IAAI;AACZ,QAAA,SAAS,EAAE,YAAY;QACvB,IAAI,EAAE,CAAC,YAAY,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,QAAQ,GAAG,CAAC,CAAC,CAAC,QAAQ,CAAC,GAAG,EAAE,CAAC;QAC3D,IAAI,EAAE,CAAC,CAAC,IAAI;AACb,KAAA,CAAC,CAAC;AACL;AAWA;AACO,eAAe,SAAS,CAAC,KAAiB,EAAE,OAAoB,EAAE,EAAA;;AAEvE,IAAA,IAAI,IAAI,CAAC,WAAW,IAAI,IAAI,CAAC,MAAM,EAAE,WAAW,EAAE,WAAW,EAAE;AAC7D,QAAA,MAAM,KAAK,GAAG,eAAe,CAAC,IAAI,CAAC,MAAM,EAAE,WAAW,EAAE,YAAY,CAAC;AACrE,QAAA,MAAM,MAAM,GAAG,KAAK,CAAC,GAAG,CAAC,KAAK,EAAE,IAAI,CAAC,MAAM,CAAC;QAC5C,IAAI,MAAM,EAAE;AACV,YAAA,OAAO,MAAM;QACf;IACF;AAEA,IAAA,MAAM,WAAW,GACf,IAAI,CAAC,yBAAyB,IAAI,IAAI,CAAC,MAAM,EAAE,WAAW,EAAE;UACxD,IAAI,kBAAkB;UACtB,IAAI;AACV,IAAA,WAAW,EAAE,UAAU,CAAC,YAAY,CAAC;AAErC,IAAA,MAAM,MAAM,GAAG,IAAI,CAAC,MAAM,IAAI,IAAI,CAAC,MAAM,EAAE,aAAa,IAAI,WAAW;AACvE,IAAA,MAAM,GAAG,GAAgB;QACvB,GAAG,IAAI,CAAC,GAAG;AACX,QAAA,QAAQ,EAAE,IAAI,CAAC,GAAG,EAAE,QAAQ,IAAI,cAAc,CAAC,IAAI,CAAC,GAAG,EAAE,QAAQ,CAAC;QAClE,IAAI,EAAE,IAAI,CAAC,GAAG,EAAE,IAAI,IAAI,KAAK,CAAC,UAAU;KACzC;AAED,IAAA,WAAW,EAAE,UAAU,CAAC,UAAU,CAAC;AACnC,IAAA,WAAW,EAAE,UAAU,CAAC,kBAAkB,CAAC;AAE3C,IAAA,MAAM,MAAM,GAAG,mBAAmB,CAAC,MAAM,CAAC;AAC1C,IAAA,MAAM,QAAQ,GAAG,MAAM,CAAC,OAAQ,MAAc,KAAK;AACjD,UAAG;UACA,MAAc,CAAC,IAAI,EAAE,KAAK,EAAE,GAAG,CAAC;AACrC,IAAA,MAAM,UAAU,GAAG,CAAC,GAAG,QAAQ,CAAC;AAEhC,IAAA,WAAW,EAAE,UAAU,CAAC,gBAAgB,CAAC;;AAGzC,IAAA,MAAM,eAAe,GACnB,IAAI,CAAC,uBAAuB,IAAI,IAAI,CAAC,MAAM,EAAE,QAAQ,EAAE,uBAAuB,IAAI,IAAI;IACxF,IAAI,eAAe,EAAE;AACnB,QAAA,WAAW,EAAE,UAAU,CAAC,gBAAgB,CAAC;;QAGzC,IAAI,IAAI,CAAC,MAAM,EAAE,QAAQ,EAAE,uBAAuB,KAAK,KAAK,EAAE;AAC5D,YAAA,MAAM,eAAe,GAAG,cAAc,CAAC,KAAK,CAAC;AAC7C,YAAA,UAAU,CAAC,IAAI,CAAC,GAAG,eAAe,CAAC;QACrC;;QAGA,IAAI,IAAI,CAAC,MAAM,EAAE,QAAQ,EAAE,0BAA0B,KAAK,KAAK,EAAE;AAC/D,YAAA,MAAM,iBAAiB,GAAG,uBAAuB,CAAC,KAAK,CAAC;AACxD,YAAA,UAAU,CAAC,IAAI,CAAC,GAAG,iBAAiB,CAAC;QACvC;;QAGA,IAAI,IAAI,CAAC,MAAM,EAAE,QAAQ,EAAE,2BAA2B,KAAK,KAAK,EAAE;AAChE,YAAA,MAAM,eAAe,GAAG,qBAAqB,CAAC,KAAK,CAAC;YACpD,MAAM,QAAQ,GAAG,IAAI,CAAC,MAAM,EAAE,QAAQ,EAAE,eAAe,IAAI,CAAC;YAC5D,IAAI,eAAe,CAAC,mBAAmB,IAAI,eAAe,CAAC,KAAK,GAAG,QAAQ,EAAE;gBAC3E,UAAU,CAAC,IAAI,CAAC;AACd,oBAAA,IAAI,EAAE,2BAA2B;AACjC,oBAAA,QAAQ,EAAE,MAAM;AAChB,oBAAA,IAAI,EAAE;AACJ,wBAAA,WAAW,EAAE,oCAAoC;wBACjD,KAAK,EAAE,eAAe,CAAC,KAAK;AAC5B,wBAAA,UAAU,EAAE,QAAQ;AACrB,qBAAA;AACF,iBAAA,CAAC;YACJ;QACF;AAEA,QAAA,WAAW,EAAE,UAAU,CAAC,cAAc,CAAC;IACzC;AAEA,IAAA,MAAM,OAAO,GAAG,aAAa,CAAC,UAAU,CAAC;AACzC,IAAA,MAAM,OAAO,GAAG,cAAc,CAAC,OAAO,CAAC;AACvC,IAAW,WAAW,GAAG,WAAW,CAAC,WAAW,EAAE,GAAG,IAAI,CAAC,GAAG;AAC7D,IAAA,MAAM,UAAU,GAAG,WAAW,GAAG,WAAW,CAAC,WAAW,EAAE,GAAG,CAAC;AAE9D,IAAA,MAAM,MAAM,GAAe;QACzB,EAAE,EAAE,OAAO,KAAK,OAAO;QACvB,OAAO;QACP,OAAO;AACP,QAAA,OAAO,EAAE,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,IAAI,CAAC;AACnC,QAAA,IAAI,EAAE,EAAE,IAAI,EAAE,GAAG,CAAC,QAAQ,EAAE,QAAQ,EAAE,GAAG,CAAC,QAAQ,EAAE,IAAI,EAAE,GAAG,CAAC,IAAI,EAAE;QACpE,UAAU;AACV,QAAA,MAAM,EAAE,YAAY;AACpB,QAAA,SAAS,EAAE,KAAK;AAChB,QAAA,QAAQ,EAAE,KAAK;KAChB;;AAGD,IAAA,IACE,WAAW;AACX,SAAC,IAAI,CAAC,yBAAyB,IAAI,IAAI,CAAC,MAAM,EAAE,WAAW,EAAE,yBAAyB,CAAC,EACvF;QACC,MAAc,CAAC,kBAAkB,GAAG,WAAW,CAAC,UAAU,CAAC,KAAK,CAAC,UAAU,CAAC;IAC/E;;AAGA,IAAA,IAAI,IAAI,CAAC,WAAW,IAAI,IAAI,CAAC,MAAM,EAAE,WAAW,EAAE,WAAW,EAAE;AAC7D,QAAA,MAAM,KAAK,GAAG,eAAe,CAAC,IAAI,CAAC,MAAM,EAAE,WAAW,EAAE,YAAY,CAAC;QACrE,KAAK,CAAC,GAAG,CAAC,KAAK,EAAE,MAAM,EAAE,IAAI,CAAC,MAAM,CAAC;IACvC;;IAGA,IAAI,CAAC,MAAM,EAAE,SAAS,EAAE,cAAc,GAAG,MAAM,CAAC;AAEhD,IAAA,OAAO,MAAM;AACf;AAEA;AACO,eAAe,QAAQ,CAC5B,QAAgB,EAChB,OAAiC,EAAE,EAAA;IAEnC,MAAM,CAAC,EAAE,QAAQ,EAAE,IAAI,EAAE,EAAE,IAAI,CAAC,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC,CAAC,OAAO,aAAa,CAAC,EAAE,OAAO,MAAM,CAAC,CAAC,CAAC;IAE7F,MAAM,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAC,CAAC;AACzE,IAAA,MAAM,GAAG,GAAgB;AACvB,QAAA,QAAQ,EAAE,IAAI,CAAC,QAAQ,CAAC,QAAQ,CAAC;AACjC,QAAA,QAAQ,EAAE,cAAc,CAAC,QAAQ,CAAC;QAClC,IAAI,EAAE,EAAE,CAAC,IAAI;KACd;IACD,OAAO,SAAS,CAAC,IAAI,UAAU,CAAC,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,UAAU,EAAE,GAAG,CAAC,UAAU,CAAC,EAAE,EAAE,GAAG,IAAI,EAAE,GAAG,EAAE,CAAC;AAChG;AAEA;AACO,eAAe,SAAS,CAC7B,KAAsB,EACtB,OAAiC,EAAE,EAAA;IAEnC,MAAM,IAAI,GAAG,KAAK,CAAC,IAAI,CAAC,KAAwB,CAAW;IAC3D,MAAM,GAAG,GAAiB,EAAE;AAC5B,IAAA,KAAK,MAAM,CAAC,IAAI,IAAI,EAAE;QACpB,MAAM,GAAG,GAAG,IAAI,UAAU,CAAC,MAAM,CAAC,CAAC,WAAW,EAAE,CAAC;AACjD,QAAA,MAAM,GAAG,GAAG,MAAM,SAAS,CAAC,GAAG,EAAE;AAC/B,YAAA,GAAG,IAAI;YACP,GAAG,EAAE,EAAE,QAAQ,EAAE,CAAC,CAAC,IAAI,EAAE,QAAQ,EAAE,CAAC,CAAC,IAAI,IAAI,cAAc,CAAC,CAAC,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE;AACpF,SAAA,CAAC;AACF,QAAA,GAAG,CAAC,IAAI,CAAC,GAAG,CAAC;IACf;AACA,IAAA,OAAO,GAAG;AACZ;;AC/LA,MAAM,OAAO,GAAG,UAAU;AAG1B,MAAM,QAAQ,GAAkC;AAC9C,IAAA,UAAU,EAAE,IAAI;AAChB,IAAA,yBAAyB,EAAE,GAAG,GAAG,IAAI,GAAG,IAAI;AAC5C,IAAA,kBAAkB,EAAE,GAAG;AACvB,IAAA,mBAAmB,EAAE,IAAI;AACzB,IAAA,gBAAgB,EAAE,KAAM;CACzB;AAED,SAAS,GAAG,CAAC,GAAW,EAAE,GAAW,EAAA;AACnC,IAAA,OAAO,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC;AAC9B;AACA,SAAS,GAAG,CAAC,GAAW,EAAE,GAAW,EAAA;AACnC,IAAA,OAAO,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC;AAC9B;AACA,SAAS,SAAS,CAAC,GAAW,EAAA;;AAE5B,IAAA,QACE,GAAG,CAAC,MAAM,IAAI,CAAC,IAAI,GAAG,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,GAAG,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,GAAG,CAAC,CAAC,CAAC,KAAK,IAAI,IAAI,GAAG,CAAC,CAAC,CAAC,KAAK,IAAI;AAE/F;AAEA,SAAS,eAAe,CAAC,GAAW,EAAE,MAAc,EAAA;AAClD,IAAA,MAAM,GAAG,GAAG,MAAM,CAAC,IAAI,CAAC,CAAC,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,CAAC,CAAC;AACjD,IAAA,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,GAAG,CAAC,MAAM,GAAG,MAAM,CAAC;IAC9C,MAAM,GAAG,GAAG,GAAG,CAAC,WAAW,CAAC,GAAG,EAAE,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,MAAM,GAAG,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC;AACnF,IAAA,OAAO,GAAG,IAAI,KAAK,GAAG,GAAG,GAAG,EAAE;AAChC;AAEA,SAAS,YAAY,CAAC,IAAY,EAAA;AAChC,IAAA,QACE,IAAI,CAAC,QAAQ,CAAC,KAAK,CAAC,IAAI,IAAI,CAAC,QAAQ,CAAC,MAAM,CAAC,IAAI,IAAI,CAAC,UAAU,CAAC,GAAG,CAAC,IAAI,YAAY,CAAC,IAAI,CAAC,IAAI,CAAC;AAEpG;AAEM,SAAU,kBAAkB,CAAC,IAAA,GAA4B,EAAE,EAAA;IAC/D,MAAM,GAAG,GAAG,EAAE,GAAG,QAAQ,EAAE,GAAG,IAAI,EAAE;IAEpC,OAAO;QACL,MAAM,IAAI,CAAC,KAAiB,EAAA;YAC1B,MAAM,GAAG,GAAG,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC;YAC9B,MAAM,OAAO,GAAY,EAAE;AAE3B,YAAA,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC;AAAE,gBAAA,OAAO,OAAO;;YAGnC,MAAM,OAAO,GAAG,eAAe,CAAC,GAAG,EAAE,GAAG,CAAC,gBAAgB,CAAC;AAC1D,YAAA,IAAI,OAAO,GAAG,CAAC,IAAI,OAAO,GAAG,EAAE,GAAG,GAAG,CAAC,MAAM,EAAE;;AAE5C,gBAAA,OAAO,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,oBAAoB,EAAE,QAAQ,EAAE,QAAQ,EAAE,CAAC;AAChE,gBAAA,OAAO,OAAO;YAChB;YAEA,MAAM,YAAY,GAAG,GAAG,CAAC,GAAG,EAAE,OAAO,GAAG,EAAE,CAAC;YAC3C,MAAM,MAAM,GAAG,GAAG,CAAC,GAAG,EAAE,OAAO,GAAG,EAAE,CAAC;YACrC,MAAM,QAAQ,GAAG,GAAG,CAAC,GAAG,EAAE,OAAO,GAAG,EAAE,CAAC;;YAGvC,IAAI,QAAQ,GAAG,MAAM,GAAG,GAAG,CAAC,MAAM,EAAE;AAClC,gBAAA,OAAO,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,sBAAsB,EAAE,QAAQ,EAAE,QAAQ,EAAE,CAAC;AAClE,gBAAA,OAAO,OAAO;YAChB;;YAGA,IAAI,GAAG,GAAG,QAAQ;YAClB,IAAI,IAAI,GAAG,CAAC;YACZ,IAAI,OAAO,GAAG,CAAC;YACf,IAAI,MAAM,GAAG,CAAC;AAEd,YAAA,OAAO,GAAG,GAAG,EAAE,IAAI,QAAQ,GAAG,MAAM,IAAI,IAAI,GAAG,YAAY,EAAE;gBAC3D,MAAM,GAAG,GAAG,GAAG,CAAC,GAAG,EAAE,GAAG,CAAC;gBACzB,IAAI,GAAG,KAAK,OAAO;AAAE,oBAAA,MAAM;gBAE3B,MAAM,QAAQ,GAAG,GAAG,CAAC,GAAG,EAAE,GAAG,GAAG,EAAE,CAAC;gBACnC,MAAM,OAAO,GAAG,GAAG,CAAC,GAAG,EAAE,GAAG,GAAG,EAAE,CAAC;gBAClC,MAAM,KAAK,GAAG,GAAG,CAAC,GAAG,EAAE,GAAG,GAAG,EAAE,CAAC;gBAChC,MAAM,KAAK,GAAG,GAAG,CAAC,GAAG,EAAE,GAAG,GAAG,EAAE,CAAC;gBAChC,MAAM,KAAK,GAAG,GAAG,CAAC,GAAG,EAAE,GAAG,GAAG,EAAE,CAAC;AAEhC,gBAAA,MAAM,SAAS,GAAG,GAAG,GAAG,EAAE;AAC1B,gBAAA,MAAM,OAAO,GAAG,SAAS,GAAG,KAAK;AACjC,gBAAA,IAAI,OAAO,GAAG,GAAG,CAAC,MAAM;oBAAE;AAE1B,gBAAA,MAAM,IAAI,GAAG,GAAG,CAAC,QAAQ,CAAC,MAAM,EAAE,SAAS,EAAE,OAAO,CAAC;gBAErD,OAAO,IAAI,QAAQ;gBACnB,MAAM,IAAI,OAAO;AACjB,gBAAA,IAAI,EAAE;gBAEN,IAAI,IAAI,CAAC,MAAM,GAAG,GAAG,CAAC,kBAAkB,EAAE;oBACxC,OAAO,CAAC,IAAI,CAAC;AACX,wBAAA,IAAI,EAAE,yBAAyB;AAC/B,wBAAA,QAAQ,EAAE,QAAQ;wBAClB,IAAI,EAAE,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,CAAC,MAAM,EAAE;AACpC,qBAAA,CAAC;gBACJ;AACA,gBAAA,IAAI,YAAY,CAAC,IAAI,CAAC,EAAE;AACtB,oBAAA,OAAO,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,0BAA0B,EAAE,QAAQ,EAAE,QAAQ,EAAE,IAAI,EAAE,EAAE,IAAI,EAAE,EAAE,CAAC;gBACxF;;AAGA,gBAAA,GAAG,GAAG,OAAO,GAAG,KAAK,GAAG,KAAK;YAC/B;AAEA,YAAA,IAAI,IAAI,KAAK,YAAY,EAAE;;gBAEzB,OAAO,CAAC,IAAI,CAAC;AACX,oBAAA,IAAI,EAAE,kBAAkB;AACxB,oBAAA,QAAQ,EAAE,QAAQ;AAClB,oBAAA,IAAI,EAAE,EAAE,IAAI,EAAE,YAAY,EAAE;AAC7B,iBAAA,CAAC;YACJ;;AAGA,YAAA,IAAI,IAAI,GAAG,GAAG,CAAC,UAAU,EAAE;gBACzB,OAAO,CAAC,IAAI,CAAC;AACX,oBAAA,IAAI,EAAE,sBAAsB;AAC5B,oBAAA,QAAQ,EAAE,QAAQ;oBAClB,IAAI,EAAE,EAAE,IAAI,EAAE,KAAK,EAAE,GAAG,CAAC,UAAU,EAAE;AACtC,iBAAA,CAAC;YACJ;AACA,YAAA,IAAI,MAAM,GAAG,GAAG,CAAC,yBAAyB,EAAE;gBAC1C,OAAO,CAAC,IAAI,CAAC;AACX,oBAAA,IAAI,EAAE,kCAAkC;AACxC,oBAAA,QAAQ,EAAE,QAAQ;oBAClB,IAAI,EAAE,EAAE,iBAAiB,EAAE,MAAM,EAAE,KAAK,EAAE,GAAG,CAAC,yBAAyB,EAAE;AAC1E,iBAAA,CAAC;YACJ;YAEA,IAAI,OAAO,KAAK,CAAC,IAAI,MAAM,GAAG,CAAC,EAAE;gBAC/B,OAAO,CAAC,IAAI,CAAC;AACX,oBAAA,IAAI,EAAE,sBAAsB;AAC5B,oBAAA,QAAQ,EAAE,QAAQ;AAClB,oBAAA,IAAI,EAAE,EAAE,KAAK,EAAE,QAAQ,EAAE;AAC1B,iBAAA,CAAC;YACJ;AAAO,iBAAA,IAAI,OAAO,GAAG,CAAC,EAAE;AACtB,gBAAA,MAAM,KAAK,GAAG,MAAM,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,OAAO,CAAC;AAC3C,gBAAA,IAAI,KAAK,IAAI,GAAG,CAAC,mBAAmB,EAAE;oBACpC,OAAO,CAAC,IAAI,CAAC;AACX,wBAAA,IAAI,EAAE,sBAAsB;AAC5B,wBAAA,QAAQ,EAAE,QAAQ;wBAClB,IAAI,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,GAAG,CAAC,mBAAmB,EAAE;AAChD,qBAAA,CAAC;gBACJ;YACF;AAEA,YAAA,OAAO,OAAO;QAChB,CAAC;KACF;AACH;;ACnKA;;;AAGG;AAeH;;AAEG;MACU,kBAAkB,CAAA;AAC7B;;AAEG;AACH,IAAA,MAAM,CAAC,OAAkC,EAAE,OAAA,GAAyB,EAAE,EAAA;AACpE,QAAA,MAAM,IAAI,GAAG,KAAK,CAAC,OAAO,CAAC,OAAO,CAAC,GAAG,OAAO,GAAG,CAAC,OAAO,CAAC;AAEzD,QAAA,IAAI,CAAC,OAAO,CAAC,cAAc,EAAE;;YAE3B,MAAM,UAAU,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,MAAM;gBAClC,OAAO,EAAE,CAAC,CAAC,OAAO;AAClB,gBAAA,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,IAAI;AAClB,gBAAA,OAAO,EAAE,CAAC,CAAC,OAAO,CAAC,MAAM;gBACzB,UAAU,EAAE,CAAC,CAAC,UAAU;AACzB,aAAA,CAAC,CAAC;YACH,OAAO,OAAO,CAAC,WAAW,GAAG,IAAI,CAAC,SAAS,CAAC,UAAU,EAAE,IAAI,EAAE,CAAC,CAAC,GAAG,IAAI,CAAC,SAAS,CAAC,UAAU,CAAC;QAC/F;QAEA,OAAO,OAAO,CAAC,WAAW,GAAG,IAAI,CAAC,SAAS,CAAC,IAAI,EAAE,IAAI,EAAE,CAAC,CAAC,GAAG,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC;IACnF;AAEA;;AAEG;AACH,IAAA,KAAK,CAAC,OAAkC,EAAE,OAAA,GAAyB,EAAE,EAAA;AACnE,QAAA,MAAM,IAAI,GAAG,KAAK,CAAC,OAAO,CAAC,OAAO,CAAC,GAAG,OAAO,GAAG,CAAC,OAAO,CAAC;AAEzD,QAAA,MAAM,OAAO,GAAG;YACd,UAAU;YACV,SAAS;YACT,eAAe;YACf,WAAW;YACX,WAAW;YACX,aAAa;YACb,QAAQ;SACT;AAED,QAAA,IAAI,OAAO,CAAC,cAAc,EAAE;AAC1B,YAAA,OAAO,CAAC,IAAI,CAAC,SAAS,EAAE,aAAa,CAAC;QACxC;QAEA,MAAM,IAAI,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,MAAM,KAAI;AAC/B,YAAA,MAAM,GAAG,GAAG;gBACV,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC,IAAI,EAAE,IAAI,IAAI,SAAS,CAAC;AAC9C,gBAAA,MAAM,CAAC,OAAO;AACd,gBAAA,MAAM,CAAC,OAAO,CAAC,MAAM,CAAC,QAAQ,EAAE;gBAChC,CAAC,MAAM,CAAC,IAAI,EAAE,IAAI,IAAI,CAAC,EAAE,QAAQ,EAAE;gBACnC,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC,IAAI,EAAE,QAAQ,IAAI,SAAS,CAAC;gBAClD,CAAC,MAAM,CAAC,UAAU,IAAI,CAAC,EAAE,QAAQ,EAAE;gBACnC,MAAM,CAAC,MAAM,IAAI,SAAS;aAC3B;AAED,YAAA,IAAI,OAAO,CAAC,cAAc,EAAE;gBAC1B,GAAG,CAAC,IAAI,CACN,IAAI,CAAC,SAAS,CAAC,CAAC,MAAM,CAAC,OAAO,IAAI,EAAE,EAAE,IAAI,CAAC,IAAI,CAAC,CAAC,EACjD,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAC7D;YACH;AAEA,YAAA,OAAO,GAAG,CAAC,IAAI,CAAC,GAAG,CAAC;AACtB,QAAA,CAAC,CAAC;AAEF,QAAA,OAAO,CAAC,OAAO,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,GAAG,IAAI,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC;IAChD;AAEA;;AAEG;AACH,IAAA,UAAU,CAAC,OAAkC,EAAE,OAAA,GAAyB,EAAE,EAAA;AACxE,QAAA,MAAM,IAAI,GAAG,KAAK,CAAC,OAAO,CAAC,OAAO,CAAC,GAAG,OAAO,GAAG,CAAC,OAAO,CAAC;QAEzD,IAAI,EAAE,GAAG,oBAAoB;AAC7B,QAAA,EAAE,IAAI,CAAA,iBAAA,EAAoB,IAAI,CAAC,MAAM,MAAM;AAE3C,QAAA,MAAM,KAAK,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,OAAO,KAAK,OAAO,CAAC,CAAC,MAAM;AAC9D,QAAA,MAAM,UAAU,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,OAAO,KAAK,YAAY,CAAC,CAAC,MAAM;AACxE,QAAA,MAAM,SAAS,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,OAAO,KAAK,WAAW,CAAC,CAAC,MAAM;QAEtE,EAAE,IAAI,gBAAgB;AACtB,QAAA,EAAE,IAAI,CAAA,WAAA,EAAc,KAAK,CAAA,EAAA,CAAI;AAC7B,QAAA,EAAE,IAAI,CAAA,iBAAA,EAAoB,UAAU,CAAA,EAAA,CAAI;AACxC,QAAA,EAAE,IAAI,CAAA,eAAA,EAAkB,SAAS,CAAA,IAAA,CAAM;QAEvC,EAAE,IAAI,yBAAyB;AAE/B,QAAA,KAAK,MAAM,MAAM,IAAI,IAAI,EAAE;YACzB,MAAM,IAAI,GAAG,MAAM,CAAC,OAAO,KAAK,OAAO,GAAG,GAAG,GAAG,MAAM,CAAC,OAAO,KAAK,YAAY,GAAG,IAAI,GAAG,GAAG;AAC5F,YAAA,EAAE,IAAI,CAAA,IAAA,EAAO,IAAI,CAAA,CAAA,EAAI,MAAM,CAAC,IAAI,EAAE,IAAI,IAAI,SAAS,CAAA,IAAA,CAAM;AACzD,YAAA,EAAE,IAAI,CAAA,eAAA,EAAkB,MAAM,CAAC,OAAO,IAAI;AAC1C,YAAA,EAAE,IAAI,CAAA,YAAA,EAAe,IAAI,CAAC,WAAW,CAAC,MAAM,CAAC,IAAI,EAAE,IAAI,IAAI,CAAC,CAAC,IAAI;YACjE,EAAE,IAAI,CAAA,iBAAA,EAAoB,MAAM,CAAC,IAAI,EAAE,QAAQ,IAAI,SAAS,CAAA,EAAA,CAAI;YAChE,EAAE,IAAI,mBAAmB,MAAM,CAAC,UAAU,IAAI,CAAC,MAAM;YACrD,EAAE,IAAI,kBAAkB,MAAM,CAAC,OAAO,CAAC,MAAM,IAAI;AAEjD,YAAA,IAAI,OAAO,CAAC,cAAc,IAAI,MAAM,CAAC,OAAO,CAAC,MAAM,GAAG,CAAC,EAAE;gBACvD,EAAE,IAAI,wBAAwB;AAC9B,gBAAA,KAAK,MAAM,KAAK,IAAI,MAAM,CAAC,OAAO,EAAE;AAClC,oBAAA,EAAE,IAAI,CAAA,EAAA,EAAK,KAAK,CAAC,IAAI,EAAE;AACvB,oBAAA,IAAI,KAAK,CAAC,IAAI,IAAI,KAAK,CAAC,IAAI,CAAC,MAAM,GAAG,CAAC,EAAE;wBACvC,EAAE,IAAI,CAAA,EAAA,EAAK,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,CAAA,CAAA,CAAG;oBACrC;oBACA,EAAE,IAAI,IAAI;gBACZ;YACF;YACA,EAAE,IAAI,IAAI;QACZ;AAEA,QAAA,OAAO,EAAE;IACX;AAEA;;;AAGG;AACH,IAAA,OAAO,CAAC,OAAkC,EAAE,OAAA,GAAyB,EAAE,EAAA;AACrE,QAAA,MAAM,IAAI,GAAG,KAAK,CAAC,OAAO,CAAC,OAAO,CAAC,GAAG,OAAO,GAAG,CAAC,OAAO,CAAC;QAEzD,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,CAAC,MAAM,KAAI;AACtC,YAAA,IAAI,MAAM,CAAC,OAAO,KAAK,OAAO;AAAE,gBAAA,OAAO,EAAE;YAEzC,OAAO,MAAM,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,KAAK,MAAM;gBACpC,MAAM,EAAE,KAAK,CAAC,IAAI;AAClB,gBAAA,KAAK,EAAE,MAAM,CAAC,OAAO,KAAK,WAAW,GAAG,OAAO,GAAG,SAAS;AAC3D,gBAAA,OAAO,EAAE;AACP,oBAAA,IAAI,EAAE,CAAA,EAAG,KAAK,CAAC,IAAI,CAAA,aAAA,EAAgB,MAAM,CAAC,IAAI,EAAE,IAAI,IAAI,cAAc,CAAA,CAAE;AACzE,iBAAA;AACD,gBAAA,SAAS,EAAE;AACT,oBAAA;AACE,wBAAA,gBAAgB,EAAE;AAChB,4BAAA,gBAAgB,EAAE;AAChB,gCAAA,GAAG,EAAE,MAAM,CAAC,IAAI,EAAE,IAAI,IAAI,SAAS;AACpC,6BAAA;AACF,yBAAA;AACF,qBAAA;AACF,iBAAA;AACD,gBAAA,UAAU,EAAE;oBACV,IAAI,EAAE,KAAK,CAAC,IAAI;oBAChB,QAAQ,EAAE,KAAK,CAAC,IAAI;AACrB,iBAAA;AACF,aAAA,CAAC,CAAC;AACL,QAAA,CAAC,CAAC;AAEF,QAAA,MAAM,KAAK,GAAG;AACZ,YAAA,OAAO,EAAE,OAAO;AAChB,YAAA,OAAO,EACL,gGAAgG;AAClG,YAAA,IAAI,EAAE;AACJ,gBAAA;AACE,oBAAA,IAAI,EAAE;AACJ,wBAAA,MAAM,EAAE;AACN,4BAAA,IAAI,EAAE,UAAU;AAChB,4BAAA,OAAO,EAAE,QAAQ;AACjB,4BAAA,cAAc,EAAE,sCAAsC;AACvD,yBAAA;AACF,qBAAA;oBACD,OAAO;AACR,iBAAA;AACF,aAAA;SACF;QAED,OAAO,OAAO,CAAC,WAAW,GAAG,IAAI,CAAC,SAAS,CAAC,KAAK,EAAE,IAAI,EAAE,CAAC,CAAC,GAAG,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC;IACrF;AAEA;;AAEG;AACH,IAAA,MAAM,CAAC,OAAkC,EAAE,OAAA,GAAyB,EAAE,EAAA;AACpE,QAAA,MAAM,IAAI,GAAG,KAAK,CAAC,OAAO,CAAC,OAAO,CAAC,GAAG,OAAO,GAAG,CAAC,OAAO,CAAC;AAEzD,QAAA,MAAM,KAAK,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,OAAO,KAAK,OAAO,CAAC,CAAC,MAAM;AAC9D,QAAA,MAAM,UAAU,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,OAAO,KAAK,YAAY,CAAC,CAAC,MAAM;AACxE,QAAA,MAAM,SAAS,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,OAAO,KAAK,WAAW,CAAC,CAAC,MAAM;AAEtE,QAAA,IAAI,IAAI,GAAG,CAAA;;;;;;;;;;;;;;;;;;;;;;;kCAuBmB,KAAK,CAAA;uCACA,UAAU,CAAA;sCACX,SAAS,CAAA;;4BAEnB;AAExB,QAAA,KAAK,MAAM,MAAM,IAAI,IAAI,EAAE;AACzB,YAAA,MAAM,WAAW,GAAG,MAAM,CAAC,OAAO;AAClC,YAAA,IAAI,IAAI,CAAA,mBAAA,EAAsB,WAAW,CAAA,EAAA,CAAI;AAC7C,YAAA,IAAI,IAAI,CAAA,IAAA,EAAO,IAAI,CAAC,UAAU,CAAC,MAAM,CAAC,IAAI,EAAE,IAAI,IAAI,SAAS,CAAC,OAAO;YACrE,IAAI,IAAI,SAAS;YACjB,IAAI,IAAI,2BAA2B,MAAM,CAAC,OAAO,CAAC,WAAW,EAAE,CAAA,UAAA,CAAY;AAC3E,YAAA,IAAI,IAAI,CAAA,qBAAA,EAAwB,IAAI,CAAC,WAAW,CAAC,MAAM,CAAC,IAAI,EAAE,IAAI,IAAI,CAAC,CAAC,YAAY;AACpF,YAAA,IAAI,IAAI,CAAA,0BAAA,EAA6B,IAAI,CAAC,UAAU,CAAC,MAAM,CAAC,IAAI,EAAE,QAAQ,IAAI,SAAS,CAAC,YAAY;YACpG,IAAI,IAAI,4BAA4B,MAAM,CAAC,UAAU,IAAI,CAAC,cAAc;YACxE,IAAI,IAAI,2BAA2B,MAAM,CAAC,OAAO,CAAC,MAAM,YAAY;YACpE,IAAI,IAAI,UAAU;AAElB,YAAA,IAAI,OAAO,CAAC,cAAc,IAAI,MAAM,CAAC,OAAO,CAAC,MAAM,GAAG,CAAC,EAAE;gBACvD,IAAI,IAAI,6BAA6B;AACrC,gBAAA,KAAK,MAAM,KAAK,IAAI,MAAM,CAAC,OAAO,EAAE;oBAClC,IAAI,IAAI,CAAA,YAAA,EAAe,IAAI,CAAC,UAAU,CAAC,KAAK,CAAC,IAAI,CAAC,CAAA,SAAA,CAAW;AAC7D,oBAAA,IAAI,KAAK,CAAC,IAAI,IAAI,KAAK,CAAC,IAAI,CAAC,MAAM,GAAG,CAAC,EAAE;AACvC,wBAAA,IAAI,IAAI,CAAA,CAAA,EAAI,KAAK,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,GAAG,KAAK,CAAA,oBAAA,EAAuB,IAAI,CAAC,UAAU,CAAC,GAAG,CAAC,CAAA,OAAA,CAAS,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAA,CAAE;oBACtG;oBACA,IAAI,IAAI,OAAO;gBACjB;gBACA,IAAI,IAAI,OAAO;YACjB;YACA,IAAI,IAAI,QAAQ;QAClB;QAEA,IAAI,IAAI,gBAAgB;AACxB,QAAA,OAAO,IAAI;IACb;AAEA;;AAEG;AACH,IAAA,MAAM,CACJ,OAAkC,EAClC,MAAoB,EACpB,UAAyB,EAAE,EAAA;QAE3B,QAAQ,MAAM;AACZ,YAAA,KAAK,MAAM;gBACT,OAAO,IAAI,CAAC,MAAM,CAAC,OAAO,EAAE,OAAO,CAAC;AACtC,YAAA,KAAK,KAAK;gBACR,OAAO,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC;AACrC,YAAA,KAAK,UAAU;gBACb,OAAO,IAAI,CAAC,UAAU,CAAC,OAAO,EAAE,OAAO,CAAC;AAC1C,YAAA,KAAK,MAAM;gBACT,OAAO,IAAI,CAAC,MAAM,CAAC,OAAO,EAAE,OAAO,CAAC;AACtC,YAAA,KAAK,OAAO;gBACV,OAAO,IAAI,CAAC,OAAO,CAAC,OAAO,EAAE,OAAO,CAAC;AACvC,YAAA;AACE,gBAAA,MAAM,IAAI,KAAK,CAAC,8BAA8B,MAAM,CAAA,CAAE,CAAC;;IAE7D;AAEQ,IAAA,SAAS,CAAC,KAAa,EAAA;QAC7B,IAAI,KAAK,CAAC,QAAQ,CAAC,GAAG,CAAC,IAAI,KAAK,CAAC,QAAQ,CAAC,GAAG,CAAC,IAAI,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,EAAE;YACtE,OAAO,CAAA,CAAA,EAAI,KAAK,CAAC,OAAO,CAAC,IAAI,EAAE,IAAI,CAAC,CAAA,CAAA,CAAG;QACzC;AACA,QAAA,OAAO,KAAK;IACd;AAEQ,IAAA,UAAU,CAAC,KAAa,EAAA;AAC9B,QAAA,OAAO;AACJ,aAAA,OAAO,CAAC,IAAI,EAAE,OAAO;AACrB,aAAA,OAAO,CAAC,IAAI,EAAE,MAAM;AACpB,aAAA,OAAO,CAAC,IAAI,EAAE,MAAM;AACpB,aAAA,OAAO,CAAC,IAAI,EAAE,QAAQ;AACtB,aAAA,OAAO,CAAC,IAAI,EAAE,QAAQ,CAAC;IAC5B;AAEQ,IAAA,WAAW,CAAC,KAAa,EAAA;QAC/B,IAAI,KAAK,KAAK,CAAC;AAAE,YAAA,OAAO,SAAS;QACjC,MAAM,CAAC,GAAG,IAAI;QACd,MAAM,KAAK,GAAG,CAAC,OAAO,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,CAAC;QACzC,MAAM,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,GAAG,CAAC,KAAK,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC;QACnD,OAAO,IAAI,CAAC,KAAK,CAAC,CAAC,KAAK,GAAG,CAAC,IAAI,CAAC,IAAI,GAAG,CAAC,GAAG,GAAG,GAAG,GAAG,GAAG,KAAK,CAAC,CAAC,CAAC;IAClE;AACD;AAED;;AAEG;SACa,iBAAiB,CAC/B,OAAkC,EAClC,MAAoB,EACpB,OAAuB,EAAA;AAEvB,IAAA,MAAM,QAAQ,GAAG,IAAI,kBAAkB,EAAE;IACzC,OAAO,QAAQ,CAAC,MAAM,CAAC,OAAO,EAAE,MAAM,EAAE,OAAO,CAAC;AAClD;;ACxTA;;AAEG;AACG,SAAU,YAAY,CAAC,IAAU,EAAA;AACrC,IAAA,MAAM,OAAO,GAAG,CAAC,GAAG,IAAI,GAAG,IAAI;IAC/B,MAAM,YAAY,GAAG,CAAC,YAAY,EAAE,kBAAkB,EAAE,UAAU,CAAC;IAEnE,IAAI,CAAC,YAAY,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE;QACrC,OAAO,EAAE,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,uBAAuB,EAAE;IACzD;AACA,IAAA,IAAI,IAAI,CAAC,IAAI,GAAG,OAAO,EAAE;QACvB,OAAO,EAAE,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,2BAA2B,EAAE;IAC7D;AACA,IAAA,OAAO,EAAE,KAAK,EAAE,IAAI,EAAE;AACxB;;ACZM,SAAU,mBAAmB,CAAC,OAAA,GAAuB,EAAE,EAAA;IAC3D,IAAI,CAAC,OAAO,CAAC,MAAM;AAAE,QAAA,OAAO,OAAO;AACnC,IAAA,MAAM,QAAQ,GAAG,CAAC,QAAQ,EAAE,QAAQ,EAAE,MAAM,EAAE,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,QAAQ,CAAC;AACnF,IAAA,MAAM,MAAM,GAAG,IAAI,GAAG,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,IAAI,EAAE,EAAE,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,WAAW,EAAE,CAAC,CAAC,CAAC;IAC1F,MAAM,OAAO,GAAG,CAAC,CAAS,KAAK,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,WAAW,EAAE,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC;AAChF,IAAA,MAAM,KAAK,GACT,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,OAAO,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,IAAI,MAAM,CAAC,GAAG,CAAC,SAAS,CAAC,IAAI,MAAM,CAAC,GAAG,CAAC,UAAU,CAAC;IACzF,OAAO,KAAK,GAAG,WAAW,GAAG,YAAY;AAC3C;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
|