@cortexkit/aft-bridge 0.18.5 → 0.19.0

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.
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,0BAA0B;AAC1B,OAAO,EAAE,eAAe,EAAE,MAAM,oBAAoB,CAAC;AAQrD,oBAAoB;AACpB,OAAO,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAC1D,4BAA4B;AAC5B,OAAO,EACL,cAAc,EACd,YAAY,EACZ,aAAa,EACb,WAAW,EACX,mBAAmB,GACpB,MAAM,iBAAiB,CAAC;AAEzB,uBAAuB;AACvB,OAAO,EACL,kBAAkB,EAClB,iBAAiB,EACjB,oBAAoB,EACpB,0BAA0B,GAC3B,MAAM,mBAAmB,CAAC;AAC3B,2BAA2B;AAC3B,OAAO,EAAE,iBAAiB,EAAE,kBAAkB,EAAE,MAAM,eAAe,CAAC;AAEtE,OAAO,EAAE,UAAU,EAAE,MAAM,WAAW,CAAC;AAcvC,OAAO,EAAE,UAAU,EAAE,cAAc,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AACxE,mEAAmE;AACnE,OAAO,EAAE,cAAc,EAAE,eAAe,EAAE,kBAAkB,EAAE,MAAM,gBAAgB,CAAC"}
package/dist/logger.js ADDED
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=logger.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.js","sourceRoot":"","sources":["../src/logger.ts"],"names":[],"mappings":""}
@@ -0,0 +1,631 @@
1
+ /**
2
+ * Auto-download and manage ONNX Runtime shared library for semantic search.
3
+ *
4
+ * Downloads the CPU-only ONNX Runtime from Microsoft's GitHub releases.
5
+ * The library is cached in the storage directory alongside semantic index data.
6
+ *
7
+ * Audit-3 v0.17 #1 hardening (v0.17.1): the previous implementation used
8
+ * `curl` with no size cap, no archive containment validation, no install
9
+ * lock, and no integrity verification — leaving an entire parallel install
10
+ * path that bypassed every defense the LSP GitHub installer had earned in
11
+ * Phase A through Phase E. This rewrite brings ONNX onto the same security
12
+ * floor:
13
+ *
14
+ * - Streaming size cap via fetch + ReadableStream transformer (`MAX_DOWNLOAD_BYTES`).
15
+ * - Streaming SHA-256 of the downloaded archive, persisted in `.aft-onnx-installed`.
16
+ * - Atomic O_EXCL install lock with PID-aware stale-lock recovery.
17
+ * - Containment-checked extraction: every file under the staging dir
18
+ * must be inside the staging root, no symlinks allowed before move.
19
+ * - Total extracted size cap (`MAX_EXTRACT_BYTES`) to defeat decompression
20
+ * bombs.
21
+ * - TOFU verification: if `.aft-onnx-installed` already records a hash for
22
+ * this version, refuse to use a binary that doesn't match.
23
+ *
24
+ * Supported platforms:
25
+ * - macOS ARM64 (osx-arm64)
26
+ * - Linux x64 (linux-x64)
27
+ * - Linux ARM64 (linux-aarch64)
28
+ * - Windows x64 (win-x64)
29
+ * - Windows ARM64 (win-arm64)
30
+ *
31
+ * macOS x64 (Intel) is not provided by Microsoft — users must install via:
32
+ * brew install onnxruntime
33
+ */
34
+ import { execFileSync } from "node:child_process";
35
+ import { createHash } from "node:crypto";
36
+ import { chmodSync, closeSync, copyFileSync, createWriteStream, existsSync, lstatSync, mkdirSync, openSync, readdirSync, readFileSync, readlinkSync, realpathSync, rmSync, statSync, symlinkSync, unlinkSync, writeFileSync, } from "node:fs";
37
+ import { dirname, join, relative, resolve } from "node:path";
38
+ import { Readable } from "node:stream";
39
+ import { pipeline } from "node:stream/promises";
40
+ import { error, log, warn } from "./active-logger.js";
41
+ const ORT_VERSION = "1.24.4";
42
+ const ORT_REPO = "microsoft/onnxruntime";
43
+ // Audit-3 v0.17 #1: streaming + extraction size caps.
44
+ //
45
+ // ONNX Runtime archives are around 60–80 MB on most platforms and 250 MB
46
+ // extracted (Windows ships extra debug binaries). 256 MB and 1 GiB give
47
+ // generous headroom while preventing a malicious or corrupted CDN response
48
+ // from filling the user's disk. Same numbers as the GitHub LSP installer.
49
+ const MAX_DOWNLOAD_BYTES = 256 * 1024 * 1024;
50
+ const MAX_EXTRACT_BYTES = 1 * 1024 * 1024 * 1024;
51
+ const ONNX_LOCK_FILE = ".aft-onnx-installing";
52
+ const ONNX_INSTALLED_META_FILE = ".aft-onnx-installed";
53
+ const STALE_LOCK_MS = 30 * 60 * 1000;
54
+ const ORT_PLATFORM_MAP = {
55
+ darwin: {
56
+ arm64: {
57
+ assetName: `onnxruntime-osx-arm64-${ORT_VERSION}`,
58
+ libName: "libonnxruntime.dylib",
59
+ archiveType: "tgz",
60
+ },
61
+ // x64 not available from Microsoft — users need brew install onnxruntime
62
+ },
63
+ linux: {
64
+ x64: {
65
+ assetName: `onnxruntime-linux-x64-${ORT_VERSION}`,
66
+ libName: "libonnxruntime.so",
67
+ archiveType: "tgz",
68
+ },
69
+ arm64: {
70
+ assetName: `onnxruntime-linux-aarch64-${ORT_VERSION}`,
71
+ libName: "libonnxruntime.so",
72
+ archiveType: "tgz",
73
+ },
74
+ },
75
+ win32: {
76
+ x64: {
77
+ assetName: `onnxruntime-win-x64-${ORT_VERSION}`,
78
+ libName: "onnxruntime.dll",
79
+ archiveType: "zip",
80
+ },
81
+ arm64: {
82
+ assetName: `onnxruntime-win-arm64-${ORT_VERSION}`,
83
+ libName: "onnxruntime.dll",
84
+ archiveType: "zip",
85
+ },
86
+ },
87
+ };
88
+ /** Get platform info for the current system, or null if unsupported */
89
+ function getPlatformInfo() {
90
+ const platformMap = ORT_PLATFORM_MAP[process.platform];
91
+ if (!platformMap)
92
+ return null;
93
+ return platformMap[process.arch] || null;
94
+ }
95
+ /** Check if this platform can auto-download ONNX Runtime */
96
+ export function isOrtAutoDownloadSupported() {
97
+ return getPlatformInfo() !== null;
98
+ }
99
+ /** Get the install hint for platforms where auto-download isn't available */
100
+ export function getManualInstallHint() {
101
+ if (process.platform === "darwin" && process.arch === "x64") {
102
+ return "brew install onnxruntime";
103
+ }
104
+ if (process.platform === "linux") {
105
+ return "apt install libonnxruntime or download from https://github.com/microsoft/onnxruntime/releases";
106
+ }
107
+ return "Download from https://github.com/microsoft/onnxruntime/releases";
108
+ }
109
+ /**
110
+ * Ensure ONNX Runtime is available. Returns the directory containing the library,
111
+ * or null if unavailable.
112
+ *
113
+ * Resolution order:
114
+ * 1. Cached in storageDir/onnxruntime/<version>/ (with TOFU verification)
115
+ * 2. System install (brew, apt, etc.)
116
+ * 3. Auto-download from GitHub releases (if platform supported)
117
+ * 4. null (user needs manual install)
118
+ */
119
+ export async function ensureOnnxRuntime(storageDir) {
120
+ const info = getPlatformInfo();
121
+ // 1. Cached location with TOFU.
122
+ const ortDir = join(storageDir, "onnxruntime", ORT_VERSION);
123
+ const libPath = join(ortDir, info?.libName ?? "libonnxruntime.dylib");
124
+ if (existsSync(libPath)) {
125
+ // Audit-3 v0.17 #1 (TOFU): if we recorded a hash for this version,
126
+ // verify the library still matches. A mismatch means tampering or
127
+ // partial install corruption. Refuse to use it and let the caller
128
+ // either retry the download (after the user clears the cache) or
129
+ // fall back to system install.
130
+ const meta = readOnnxInstalledMeta(ortDir);
131
+ if (meta?.sha256) {
132
+ try {
133
+ const currentHash = sha256File(libPath);
134
+ if (currentHash !== meta.sha256) {
135
+ error(`ONNX Runtime at ${ortDir}: TOFU sha256 mismatch — refusing to use ` +
136
+ `tampered binary. Recorded ${meta.sha256}, current ${currentHash}. ` +
137
+ `Run \`aft doctor --clear\` to re-download from scratch.`);
138
+ // Fall through to system path / re-download attempt below.
139
+ }
140
+ else {
141
+ log(`ONNX Runtime found at ${ortDir} (TOFU verified)`);
142
+ return ortDir;
143
+ }
144
+ }
145
+ catch (err) {
146
+ warn(`Could not verify ONNX Runtime hash at ${ortDir}: ${err}`);
147
+ // Treat unreadable hash as "trust on existence" since we already
148
+ // owned this install — better than blocking semantic search.
149
+ return ortDir;
150
+ }
151
+ }
152
+ else {
153
+ log(`ONNX Runtime found at ${ortDir} (no recorded hash, accepting)`);
154
+ return ortDir;
155
+ }
156
+ }
157
+ // 2. System locations.
158
+ const systemPath = findSystemOnnxRuntime(info?.libName);
159
+ if (systemPath) {
160
+ log(`ONNX Runtime found at system path: ${systemPath}`);
161
+ return systemPath;
162
+ }
163
+ // 3. Auto-download.
164
+ if (!info) {
165
+ warn(`ONNX Runtime auto-download not available for ${process.platform}/${process.arch}. Install manually: ${getManualInstallHint()}`);
166
+ return null;
167
+ }
168
+ // Audit-3 v0.17 #1: serialize concurrent installs.
169
+ //
170
+ // Two AFT plugin instances starting at the same time would otherwise both
171
+ // download and extract into overlapping temp dirs and clobber each other.
172
+ // The lock is held for the full install duration via the manual try/finally
173
+ // below (we don't reuse withInstallLock from lsp-cache because that helper
174
+ // is keyed on lspPackageDir, while ONNX lives in storageDir).
175
+ const onnxBaseDir = join(storageDir, "onnxruntime");
176
+ mkdirSync(onnxBaseDir, { recursive: true });
177
+ const lockPath = join(onnxBaseDir, ONNX_LOCK_FILE);
178
+ if (!acquireLock(lockPath)) {
179
+ warn(`ONNX Runtime install already in progress in another process (lock: ${lockPath}). Skipping.`);
180
+ return null;
181
+ }
182
+ try {
183
+ return await downloadOnnxRuntime(info, ortDir);
184
+ }
185
+ finally {
186
+ releaseLock(lockPath);
187
+ }
188
+ }
189
+ /** Check common system locations for ONNX Runtime */
190
+ function findSystemOnnxRuntime(libName) {
191
+ if (!libName)
192
+ return null;
193
+ const searchPaths = [];
194
+ if (process.platform === "darwin") {
195
+ // Homebrew locations
196
+ searchPaths.push("/opt/homebrew/lib", "/usr/local/lib");
197
+ }
198
+ else if (process.platform === "linux") {
199
+ searchPaths.push("/usr/lib", "/usr/lib/x86_64-linux-gnu", "/usr/lib/aarch64-linux-gnu", "/usr/local/lib");
200
+ }
201
+ for (const dir of searchPaths) {
202
+ if (existsSync(join(dir, libName))) {
203
+ return dir;
204
+ }
205
+ }
206
+ return null;
207
+ }
208
+ /**
209
+ * Streaming download with size cap. Mirrors the hardened path in
210
+ * `lsp-github-install.ts:downloadFile` so ONNX gets the same defenses
211
+ * the LSP installer already has.
212
+ *
213
+ * The URL is hardcoded to `https://github.com/${ORT_REPO}/...` so we don't
214
+ * need a hostname allowlist — the constant cannot be attacker-influenced.
215
+ */
216
+ async function downloadFileWithCap(url, destPath) {
217
+ const controller = new AbortController();
218
+ const timeout = setTimeout(() => controller.abort(), 300_000);
219
+ try {
220
+ const res = await fetch(url, {
221
+ headers: { accept: "application/octet-stream" },
222
+ redirect: "follow",
223
+ signal: controller.signal,
224
+ });
225
+ if (!res.ok || !res.body) {
226
+ throw new Error(`download failed (HTTP ${res.status})`);
227
+ }
228
+ const advertised = Number.parseInt(res.headers.get("content-length") ?? "", 10);
229
+ if (Number.isFinite(advertised) && advertised > MAX_DOWNLOAD_BYTES) {
230
+ throw new Error(`Content-Length ${advertised} exceeds max ${MAX_DOWNLOAD_BYTES}`);
231
+ }
232
+ mkdirSync(dirname(destPath), { recursive: true });
233
+ let bytesWritten = 0;
234
+ const guard = new TransformStream({
235
+ transform(chunk, transformController) {
236
+ bytesWritten += chunk.byteLength;
237
+ if (bytesWritten > MAX_DOWNLOAD_BYTES) {
238
+ transformController.error(new Error(`download exceeded ${MAX_DOWNLOAD_BYTES} bytes after streaming (server lied about size or sent unbounded body)`));
239
+ return;
240
+ }
241
+ transformController.enqueue(chunk);
242
+ },
243
+ });
244
+ const guarded = res.body.pipeThrough(guard);
245
+ // biome-ignore lint/suspicious/noExplicitAny: ReadableStream→Node stream conversion
246
+ const nodeStream = Readable.fromWeb(guarded);
247
+ await pipeline(nodeStream, createWriteStream(destPath), { signal: controller.signal });
248
+ }
249
+ catch (err) {
250
+ try {
251
+ unlinkSync(destPath);
252
+ }
253
+ catch {
254
+ // partial file may not exist — fine
255
+ }
256
+ throw err;
257
+ }
258
+ finally {
259
+ clearTimeout(timeout);
260
+ }
261
+ }
262
+ /**
263
+ * Validate that every file/dir under `stagingRoot` is contained inside it
264
+ * AND that the total extracted bytes do not exceed `MAX_EXTRACT_BYTES`.
265
+ *
266
+ * Audit-3 v0.17 #1: zip-slip + symlink containment + decompression-bomb
267
+ * defense. tar and unzip both can produce paths like `../../etc/passwd`;
268
+ * Windows tar.exe and unzip can also produce symlinks that point outside
269
+ * the destination. We walk the tree post-extraction and reject anything
270
+ * suspicious before moving files into the final cache.
271
+ */
272
+ function validateExtractedTree(stagingRoot) {
273
+ const realRoot = realpathSync(stagingRoot);
274
+ let totalBytes = 0;
275
+ const walk = (dir) => {
276
+ const entries = readdirSync(dir);
277
+ for (const entry of entries) {
278
+ const fullPath = join(dir, entry);
279
+ const lst = lstatSync(fullPath);
280
+ if (lst.isSymbolicLink()) {
281
+ // Symlinks must be either rejected outright or contained. Tarballs
282
+ // from Microsoft's official ONNX Runtime release ship with versioned
283
+ // .so symlinks (libonnxruntime.so → libonnxruntime.so.1.24.4), so
284
+ // we cannot simply reject all of them. Instead resolve the link
285
+ // target (relative to the symlink's directory) and verify it stays
286
+ // inside the staging root.
287
+ const linkTarget = readlinkSync(fullPath);
288
+ const resolvedTarget = resolve(dirname(fullPath), linkTarget);
289
+ const rel = relative(realRoot, resolvedTarget);
290
+ if (rel.startsWith("..") || (process.platform !== "win32" && rel.startsWith("/"))) {
291
+ throw new Error(`extracted symlink ${fullPath} points outside staging root: ${linkTarget}`);
292
+ }
293
+ continue;
294
+ }
295
+ const rel = relative(realRoot, fullPath);
296
+ if (rel.startsWith("..") || (process.platform !== "win32" && rel.startsWith("/"))) {
297
+ throw new Error(`extracted entry ${fullPath} escapes staging root`);
298
+ }
299
+ if (lst.isDirectory()) {
300
+ walk(fullPath);
301
+ continue;
302
+ }
303
+ if (lst.isFile()) {
304
+ totalBytes += lst.size;
305
+ if (totalBytes > MAX_EXTRACT_BYTES) {
306
+ throw new Error(`extracted size ${totalBytes} exceeds max ${MAX_EXTRACT_BYTES} (decompression bomb defense)`);
307
+ }
308
+ }
309
+ }
310
+ };
311
+ walk(realRoot);
312
+ }
313
+ /** Download and extract ONNX Runtime from GitHub releases */
314
+ async function downloadOnnxRuntime(info, targetDir) {
315
+ const url = `https://github.com/${ORT_REPO}/releases/download/v${ORT_VERSION}/${info.assetName}.${info.archiveType === "tgz" ? "tgz" : "zip"}`;
316
+ log(`Downloading ONNX Runtime v${ORT_VERSION} for ${process.platform}/${process.arch}...`);
317
+ // Use a parent-of-targetDir staging path so the validation walk can compare
318
+ // resolved paths via realpathSync without rejecting symlinks that happen to
319
+ // resolve into the parent (e.g. when storageDir is itself behind a symlink).
320
+ const tmpDir = `${targetDir}.tmp.${process.pid}.${Date.now().toString(36)}`;
321
+ try {
322
+ mkdirSync(tmpDir, { recursive: true });
323
+ const archivePath = join(tmpDir, `onnxruntime.${info.archiveType}`);
324
+ // Audit-3 v0.17 #1: download with streaming size cap (no more curl).
325
+ await downloadFileWithCap(url, archivePath);
326
+ // Audit-3 v0.17 #1: hash the archive for TOFU.
327
+ const archiveSha256 = sha256File(archivePath);
328
+ log(`ONNX Runtime archive sha256=${archiveSha256}`);
329
+ // Extract.
330
+ if (info.archiveType === "tgz") {
331
+ execFileSync("tar", ["xzf", archivePath, "-C", tmpDir], {
332
+ stdio: "pipe",
333
+ timeout: 120_000,
334
+ });
335
+ }
336
+ else {
337
+ await extractZipArchive(archivePath, tmpDir);
338
+ }
339
+ // Drop the archive itself before validation so it doesn't double-count
340
+ // toward the extracted-size budget.
341
+ try {
342
+ unlinkSync(archivePath);
343
+ }
344
+ catch {
345
+ // ignore
346
+ }
347
+ // Audit-3 v0.17 #1: containment + size-bomb check.
348
+ validateExtractedTree(tmpDir);
349
+ // Find and copy the library file.
350
+ const extractedDir = join(tmpDir, info.assetName, "lib");
351
+ if (!existsSync(extractedDir)) {
352
+ throw new Error(`Expected directory not found: ${extractedDir}`);
353
+ }
354
+ // Create target directory and copy library files.
355
+ mkdirSync(targetDir, { recursive: true });
356
+ // Copy all library files (main + versioned symlinks).
357
+ // On Linux, .so files are often symlinks (libonnxruntime.so → libonnxruntime.so.1.24.4).
358
+ // Process real files first, then recreate symlinks in the target directory to avoid
359
+ // ENOENT when renaming a symlink whose target was already moved.
360
+ const libFiles = readdirSync(extractedDir).filter((f) => f.startsWith("libonnxruntime") || f.startsWith("onnxruntime"));
361
+ // Separate real files from symlinks
362
+ const realFiles = [];
363
+ const symlinks = [];
364
+ for (const libFile of libFiles) {
365
+ const src = join(extractedDir, libFile);
366
+ try {
367
+ const stat = lstatSync(src);
368
+ log(`ORT extract: ${libFile} — isSymlink=${stat.isSymbolicLink()}, isFile=${stat.isFile()}, size=${stat.size}`);
369
+ if (stat.isSymbolicLink()) {
370
+ symlinks.push({ name: libFile, target: readlinkSync(src) });
371
+ }
372
+ else {
373
+ realFiles.push(libFile);
374
+ }
375
+ }
376
+ catch (e) {
377
+ log(`ORT extract: ${libFile} — stat failed: ${e}`);
378
+ realFiles.push(libFile);
379
+ }
380
+ }
381
+ // Copy real files first
382
+ for (const libFile of realFiles) {
383
+ const src = join(extractedDir, libFile);
384
+ const dst = join(targetDir, libFile);
385
+ try {
386
+ copyFileSync(src, dst);
387
+ if (process.platform !== "win32") {
388
+ chmodSync(dst, 0o755);
389
+ }
390
+ }
391
+ catch (copyErr) {
392
+ log(`ORT extract: failed to copy ${libFile}: ${copyErr}`);
393
+ }
394
+ }
395
+ // Recreate symlinks in target directory
396
+ for (const link of symlinks) {
397
+ const dst = join(targetDir, link.name);
398
+ try {
399
+ unlinkSync(dst); // remove if exists from a previous partial install
400
+ }
401
+ catch {
402
+ // ignore
403
+ }
404
+ symlinkSync(link.target, dst);
405
+ }
406
+ // Audit-3 v0.17 #1: persist version + archive sha256 for TOFU on
407
+ // future sessions. Hash the actual main library file (not the
408
+ // archive) because that's what we'll re-hash on the next ensure call.
409
+ const libPath = join(targetDir, info.libName);
410
+ let libHash = null;
411
+ try {
412
+ libHash = sha256File(libPath);
413
+ }
414
+ catch (err) {
415
+ // If we can't even hash our just-installed library, skip TOFU rather
416
+ // than blocking semantic search. Future sessions will trust the path.
417
+ warn(`Could not hash newly-installed ONNX library at ${libPath}: ${err}`);
418
+ }
419
+ writeOnnxInstalledMeta(targetDir, ORT_VERSION, libHash, archiveSha256);
420
+ // Cleanup temp directory
421
+ rmSync(tmpDir, { recursive: true, force: true });
422
+ log(`ONNX Runtime v${ORT_VERSION} installed to ${targetDir}`);
423
+ return targetDir;
424
+ }
425
+ catch (err) {
426
+ error(`Failed to download ONNX Runtime: ${err}`);
427
+ // Cleanup on failure — both the staging dir and any partially populated
428
+ // target dir, so the next attempt starts from a clean slate.
429
+ try {
430
+ rmSync(tmpDir, { recursive: true, force: true });
431
+ }
432
+ catch {
433
+ // ignore cleanup errors
434
+ }
435
+ try {
436
+ rmSync(targetDir, { recursive: true, force: true });
437
+ }
438
+ catch {
439
+ // ignore
440
+ }
441
+ return null;
442
+ }
443
+ }
444
+ async function extractZipArchive(archivePath, destinationDir) {
445
+ if (process.platform === "win32") {
446
+ // Audit-2 v0.17 #12: drop PowerShell. Even via execFileSync, PowerShell
447
+ // applies its own quoting rules to `$args[N]` lookups that could allow
448
+ // attacker-controlled fragments to escape into command interpretation.
449
+ // tar.exe ships in System32 on Windows 10 build 17063+ — execFileSync
450
+ // with argv has no shell parser in the chain.
451
+ execFileSync("tar.exe", ["-xf", archivePath, "-C", destinationDir], {
452
+ stdio: "pipe",
453
+ timeout: 120_000,
454
+ });
455
+ return;
456
+ }
457
+ execFileSync("unzip", ["-q", archivePath, "-d", destinationDir], {
458
+ stdio: "pipe",
459
+ timeout: 120_000,
460
+ });
461
+ }
462
+ function writeOnnxInstalledMeta(installDir, version, sha256, archiveSha256) {
463
+ try {
464
+ const meta = {
465
+ version,
466
+ installedAt: new Date().toISOString(),
467
+ ...(sha256 ? { sha256 } : {}),
468
+ archiveSha256,
469
+ };
470
+ writeFileSync(join(installDir, ONNX_INSTALLED_META_FILE), JSON.stringify(meta), "utf8");
471
+ }
472
+ catch (err) {
473
+ log(`[onnx] failed to write installed-meta in ${installDir}: ${err}`);
474
+ }
475
+ }
476
+ function readOnnxInstalledMeta(installDir) {
477
+ const path = join(installDir, ONNX_INSTALLED_META_FILE);
478
+ try {
479
+ if (!statSync(path).isFile())
480
+ return null;
481
+ const raw = readFileSync(path, "utf8");
482
+ const parsed = JSON.parse(raw);
483
+ if (typeof parsed.version !== "string" || parsed.version.length === 0)
484
+ return null;
485
+ return {
486
+ version: parsed.version,
487
+ installedAt: typeof parsed.installedAt === "string" ? parsed.installedAt : "",
488
+ ...(typeof parsed.sha256 === "string" && parsed.sha256.length > 0
489
+ ? { sha256: parsed.sha256 }
490
+ : {}),
491
+ ...(typeof parsed.archiveSha256 === "string" && parsed.archiveSha256.length > 0
492
+ ? { archiveSha256: parsed.archiveSha256 }
493
+ : {}),
494
+ };
495
+ }
496
+ catch {
497
+ return null;
498
+ }
499
+ }
500
+ /**
501
+ * Synchronous SHA-256 of a file. ONNX libs are ~50 MB so a single
502
+ * `readFileSync` is fine — we accept the brief blocking read in exchange
503
+ * for keeping the call sites simple (no awaits inside the path-resolution
504
+ * fast path that runs every plugin start).
505
+ */
506
+ function sha256File(path) {
507
+ const hash = createHash("sha256");
508
+ hash.update(readFileSync(path));
509
+ return hash.digest("hex");
510
+ }
511
+ /* ─────────────────────────── install lock ─────────────────────────── */
512
+ /**
513
+ * Acquire a process-exclusive lock. Atomic O_EXCL create with PID-aware
514
+ * stale-lock recovery. Mirrors `acquireInstallLock` in lsp-cache.ts but
515
+ * lives here because the ONNX install dir is keyed on `storageDir`,
516
+ * not `lspPackageDir`.
517
+ */
518
+ function acquireLock(lockPath) {
519
+ const tryClaim = () => {
520
+ try {
521
+ const fd = openSync(lockPath, "wx");
522
+ try {
523
+ writeFileSync(fd, `${process.pid}\n${new Date().toISOString()}\n`);
524
+ }
525
+ finally {
526
+ closeSync(fd);
527
+ }
528
+ return true;
529
+ }
530
+ catch (err) {
531
+ const code = err.code;
532
+ if (code === "EEXIST")
533
+ return false;
534
+ warn(`[onnx] unexpected error acquiring lock ${lockPath}: ${err}`);
535
+ return false;
536
+ }
537
+ };
538
+ if (tryClaim())
539
+ return true;
540
+ let owningPid = null;
541
+ let lockMtimeMs = 0;
542
+ try {
543
+ const raw = readFileSync(lockPath, "utf8");
544
+ const firstLine = raw.split(/\r?\n/, 1)[0]?.trim() ?? "";
545
+ const parsed = Number.parseInt(firstLine, 10);
546
+ if (Number.isFinite(parsed) && parsed > 0)
547
+ owningPid = parsed;
548
+ lockMtimeMs = statSync(lockPath).mtimeMs;
549
+ }
550
+ catch {
551
+ return tryClaim();
552
+ }
553
+ const age = Date.now() - lockMtimeMs;
554
+ const ageWithinFresh = Math.abs(age) < STALE_LOCK_MS;
555
+ const skipLiveness = process.platform === "win32";
556
+ const ownerAlive = !skipLiveness && owningPid !== null && isProcessAlive(owningPid);
557
+ if (skipLiveness ? ageWithinFresh : ownerAlive && ageWithinFresh) {
558
+ return false;
559
+ }
560
+ log(`[onnx] reclaiming install lock (owner_pid=${owningPid ?? "unknown"}, alive=${ownerAlive}, age_ms=${age})`);
561
+ try {
562
+ unlinkSync(lockPath);
563
+ }
564
+ catch {
565
+ // ignore
566
+ }
567
+ return tryClaim();
568
+ }
569
+ function releaseLock(lockPath) {
570
+ // Same TOCTOU-safe release as releaseInstallLock — only unlink if our PID owns it.
571
+ try {
572
+ let owningPid = null;
573
+ try {
574
+ const raw = readFileSync(lockPath, "utf8");
575
+ const firstLine = raw.split(/\r?\n/, 1)[0]?.trim() ?? "";
576
+ const parsed = Number.parseInt(firstLine, 10);
577
+ if (Number.isFinite(parsed) && parsed > 0)
578
+ owningPid = parsed;
579
+ }
580
+ catch (readErr) {
581
+ const code = readErr.code;
582
+ if (code === "ENOENT")
583
+ return;
584
+ warn(`[onnx] could not read lock ${lockPath} during release: ${readErr}`);
585
+ return;
586
+ }
587
+ if (owningPid !== process.pid) {
588
+ log(`[onnx] not releasing lock ${lockPath}: owned by pid ${owningPid ?? "unknown"} (we are ${process.pid})`);
589
+ return;
590
+ }
591
+ try {
592
+ unlinkSync(lockPath);
593
+ }
594
+ catch (unlinkErr) {
595
+ const code = unlinkErr.code;
596
+ if (code !== "ENOENT") {
597
+ warn(`[onnx] failed to release lock ${lockPath}: ${unlinkErr}`);
598
+ }
599
+ }
600
+ }
601
+ catch (err) {
602
+ warn(`[onnx] unexpected error releasing lock ${lockPath}: ${err}`);
603
+ }
604
+ }
605
+ function isProcessAlive(pid) {
606
+ try {
607
+ process.kill(pid, 0);
608
+ return true;
609
+ }
610
+ catch (err) {
611
+ const code = err.code;
612
+ if (code === "ESRCH")
613
+ return false;
614
+ return true;
615
+ }
616
+ }
617
+ /**
618
+ * Remove ONNX Runtime from temp files. Cleanup helper for test isolation.
619
+ */
620
+ export function cleanupOnnxRuntime(storageDir) {
621
+ try {
622
+ const ortBase = join(storageDir, "onnxruntime");
623
+ if (existsSync(ortBase)) {
624
+ rmSync(ortBase, { recursive: true, force: true });
625
+ }
626
+ }
627
+ catch {
628
+ // ignore
629
+ }
630
+ }
631
+ //# sourceMappingURL=onnx-runtime.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"onnx-runtime.js","sourceRoot":"","sources":["../src/onnx-runtime.ts"],"names":[],"mappings":"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"}