anyterm 0.1.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.
- package/LICENSE +168 -0
- package/dist/chunk-QLH3UIZ5.js +327 -0
- package/dist/chunk-S66ZF6IR.js +296 -0
- package/dist/index.js +3484 -0
- package/dist/migrate-F4NHB5VX.js +9 -0
- package/dist/migrate-OR6DL5TQ.js +9 -0
- package/package.json +34 -0
package/dist/index.js
ADDED
|
@@ -0,0 +1,3484 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
#!/usr/bin/env node
|
|
3
|
+
import {
|
|
4
|
+
DEFAULT_SERVER_URL,
|
|
5
|
+
config,
|
|
6
|
+
deleteSecret,
|
|
7
|
+
deleteServerConfig,
|
|
8
|
+
getActiveServer,
|
|
9
|
+
getConfig,
|
|
10
|
+
getMachineId,
|
|
11
|
+
getMachineName,
|
|
12
|
+
getSecret,
|
|
13
|
+
migrateConfigIfNeeded,
|
|
14
|
+
normalizeServerUrl,
|
|
15
|
+
setActiveServer,
|
|
16
|
+
setMachineName,
|
|
17
|
+
setSecret,
|
|
18
|
+
setServerConfig
|
|
19
|
+
} from "./chunk-QLH3UIZ5.js";
|
|
20
|
+
|
|
21
|
+
// src/index.ts
|
|
22
|
+
import { Command as Command7 } from "commander";
|
|
23
|
+
|
|
24
|
+
// src/commands/login.ts
|
|
25
|
+
import { Command } from "commander";
|
|
26
|
+
import { createInterface } from "readline/promises";
|
|
27
|
+
import { stdin, stdout } from "process";
|
|
28
|
+
|
|
29
|
+
// ../../node_modules/.pnpm/@noble+hashes@2.0.1/node_modules/@noble/hashes/_u64.js
|
|
30
|
+
var U32_MASK64 = /* @__PURE__ */ BigInt(2 ** 32 - 1);
|
|
31
|
+
var _32n = /* @__PURE__ */ BigInt(32);
|
|
32
|
+
function fromBig(n, le = false) {
|
|
33
|
+
if (le)
|
|
34
|
+
return { h: Number(n & U32_MASK64), l: Number(n >> _32n & U32_MASK64) };
|
|
35
|
+
return { h: Number(n >> _32n & U32_MASK64) | 0, l: Number(n & U32_MASK64) | 0 };
|
|
36
|
+
}
|
|
37
|
+
var rotrSH = (h, l, s) => h >>> s | l << 32 - s;
|
|
38
|
+
var rotrSL = (h, l, s) => h << 32 - s | l >>> s;
|
|
39
|
+
var rotrBH = (h, l, s) => h << 64 - s | l >>> s - 32;
|
|
40
|
+
var rotrBL = (h, l, s) => h >>> s - 32 | l << 64 - s;
|
|
41
|
+
var rotr32H = (_h, l) => l;
|
|
42
|
+
var rotr32L = (h, _l) => h;
|
|
43
|
+
function add(Ah, Al, Bh, Bl) {
|
|
44
|
+
const l = (Al >>> 0) + (Bl >>> 0);
|
|
45
|
+
return { h: Ah + Bh + (l / 2 ** 32 | 0) | 0, l: l | 0 };
|
|
46
|
+
}
|
|
47
|
+
var add3L = (Al, Bl, Cl) => (Al >>> 0) + (Bl >>> 0) + (Cl >>> 0);
|
|
48
|
+
var add3H = (low, Ah, Bh, Ch) => Ah + Bh + Ch + (low / 2 ** 32 | 0) | 0;
|
|
49
|
+
|
|
50
|
+
// ../../node_modules/.pnpm/@noble+hashes@2.0.1/node_modules/@noble/hashes/utils.js
|
|
51
|
+
function isBytes(a) {
|
|
52
|
+
return a instanceof Uint8Array || ArrayBuffer.isView(a) && a.constructor.name === "Uint8Array";
|
|
53
|
+
}
|
|
54
|
+
function anumber(n, title = "") {
|
|
55
|
+
if (!Number.isSafeInteger(n) || n < 0) {
|
|
56
|
+
const prefix = title && `"${title}" `;
|
|
57
|
+
throw new Error(`${prefix}expected integer >= 0, got ${n}`);
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
function abytes(value, length, title = "") {
|
|
61
|
+
const bytes = isBytes(value);
|
|
62
|
+
const len = value?.length;
|
|
63
|
+
const needsLen = length !== void 0;
|
|
64
|
+
if (!bytes || needsLen && len !== length) {
|
|
65
|
+
const prefix = title && `"${title}" `;
|
|
66
|
+
const ofLen = needsLen ? ` of length ${length}` : "";
|
|
67
|
+
const got = bytes ? `length=${len}` : `type=${typeof value}`;
|
|
68
|
+
throw new Error(prefix + "expected Uint8Array" + ofLen + ", got " + got);
|
|
69
|
+
}
|
|
70
|
+
return value;
|
|
71
|
+
}
|
|
72
|
+
function aexists(instance, checkFinished = true) {
|
|
73
|
+
if (instance.destroyed)
|
|
74
|
+
throw new Error("Hash instance has been destroyed");
|
|
75
|
+
if (checkFinished && instance.finished)
|
|
76
|
+
throw new Error("Hash#digest() has already been called");
|
|
77
|
+
}
|
|
78
|
+
function aoutput(out, instance) {
|
|
79
|
+
abytes(out, void 0, "digestInto() output");
|
|
80
|
+
const min = instance.outputLen;
|
|
81
|
+
if (out.length < min) {
|
|
82
|
+
throw new Error('"digestInto() output" expected to be of length >=' + min);
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
function u8(arr) {
|
|
86
|
+
return new Uint8Array(arr.buffer, arr.byteOffset, arr.byteLength);
|
|
87
|
+
}
|
|
88
|
+
function u32(arr) {
|
|
89
|
+
return new Uint32Array(arr.buffer, arr.byteOffset, Math.floor(arr.byteLength / 4));
|
|
90
|
+
}
|
|
91
|
+
function clean(...arrays) {
|
|
92
|
+
for (let i = 0; i < arrays.length; i++) {
|
|
93
|
+
arrays[i].fill(0);
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
var isLE = /* @__PURE__ */ (() => new Uint8Array(new Uint32Array([287454020]).buffer)[0] === 68)();
|
|
97
|
+
function byteSwap(word) {
|
|
98
|
+
return word << 24 & 4278190080 | word << 8 & 16711680 | word >>> 8 & 65280 | word >>> 24 & 255;
|
|
99
|
+
}
|
|
100
|
+
var swap8IfBE = isLE ? (n) => n : (n) => byteSwap(n);
|
|
101
|
+
function byteSwap32(arr) {
|
|
102
|
+
for (let i = 0; i < arr.length; i++) {
|
|
103
|
+
arr[i] = byteSwap(arr[i]);
|
|
104
|
+
}
|
|
105
|
+
return arr;
|
|
106
|
+
}
|
|
107
|
+
var swap32IfBE = isLE ? (u) => u : byteSwap32;
|
|
108
|
+
var hasHexBuiltin = /* @__PURE__ */ (() => (
|
|
109
|
+
// @ts-ignore
|
|
110
|
+
typeof Uint8Array.from([]).toHex === "function" && typeof Uint8Array.fromHex === "function"
|
|
111
|
+
))();
|
|
112
|
+
var hexes = /* @__PURE__ */ Array.from({ length: 256 }, (_, i) => i.toString(16).padStart(2, "0"));
|
|
113
|
+
function bytesToHex(bytes) {
|
|
114
|
+
abytes(bytes);
|
|
115
|
+
if (hasHexBuiltin)
|
|
116
|
+
return bytes.toHex();
|
|
117
|
+
let hex = "";
|
|
118
|
+
for (let i = 0; i < bytes.length; i++) {
|
|
119
|
+
hex += hexes[bytes[i]];
|
|
120
|
+
}
|
|
121
|
+
return hex;
|
|
122
|
+
}
|
|
123
|
+
var asciis = { _0: 48, _9: 57, A: 65, F: 70, a: 97, f: 102 };
|
|
124
|
+
function asciiToBase16(ch) {
|
|
125
|
+
if (ch >= asciis._0 && ch <= asciis._9)
|
|
126
|
+
return ch - asciis._0;
|
|
127
|
+
if (ch >= asciis.A && ch <= asciis.F)
|
|
128
|
+
return ch - (asciis.A - 10);
|
|
129
|
+
if (ch >= asciis.a && ch <= asciis.f)
|
|
130
|
+
return ch - (asciis.a - 10);
|
|
131
|
+
return;
|
|
132
|
+
}
|
|
133
|
+
function hexToBytes(hex) {
|
|
134
|
+
if (typeof hex !== "string")
|
|
135
|
+
throw new Error("hex string expected, got " + typeof hex);
|
|
136
|
+
if (hasHexBuiltin)
|
|
137
|
+
return Uint8Array.fromHex(hex);
|
|
138
|
+
const hl = hex.length;
|
|
139
|
+
const al = hl / 2;
|
|
140
|
+
if (hl % 2)
|
|
141
|
+
throw new Error("hex string expected, got unpadded hex of length " + hl);
|
|
142
|
+
const array = new Uint8Array(al);
|
|
143
|
+
for (let ai = 0, hi = 0; ai < al; ai++, hi += 2) {
|
|
144
|
+
const n1 = asciiToBase16(hex.charCodeAt(hi));
|
|
145
|
+
const n2 = asciiToBase16(hex.charCodeAt(hi + 1));
|
|
146
|
+
if (n1 === void 0 || n2 === void 0) {
|
|
147
|
+
const char = hex[hi] + hex[hi + 1];
|
|
148
|
+
throw new Error('hex string expected, got non-hex character "' + char + '" at index ' + hi);
|
|
149
|
+
}
|
|
150
|
+
array[ai] = n1 * 16 + n2;
|
|
151
|
+
}
|
|
152
|
+
return array;
|
|
153
|
+
}
|
|
154
|
+
function utf8ToBytes(str) {
|
|
155
|
+
if (typeof str !== "string")
|
|
156
|
+
throw new Error("string expected");
|
|
157
|
+
return new Uint8Array(new TextEncoder().encode(str));
|
|
158
|
+
}
|
|
159
|
+
function kdfInputToBytes(data, errorTitle = "") {
|
|
160
|
+
if (typeof data === "string")
|
|
161
|
+
return utf8ToBytes(data);
|
|
162
|
+
return abytes(data, void 0, errorTitle);
|
|
163
|
+
}
|
|
164
|
+
function createHasher(hashCons, info = {}) {
|
|
165
|
+
const hashC = (msg, opts) => hashCons(opts).update(msg).digest();
|
|
166
|
+
const tmp = hashCons(void 0);
|
|
167
|
+
hashC.outputLen = tmp.outputLen;
|
|
168
|
+
hashC.blockLen = tmp.blockLen;
|
|
169
|
+
hashC.create = (opts) => hashCons(opts);
|
|
170
|
+
Object.assign(hashC, info);
|
|
171
|
+
return Object.freeze(hashC);
|
|
172
|
+
}
|
|
173
|
+
function randomBytes(bytesLength = 32) {
|
|
174
|
+
const cr = typeof globalThis === "object" ? globalThis.crypto : null;
|
|
175
|
+
if (typeof cr?.getRandomValues !== "function")
|
|
176
|
+
throw new Error("crypto.getRandomValues must be defined");
|
|
177
|
+
return cr.getRandomValues(new Uint8Array(bytesLength));
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
// ../../node_modules/.pnpm/@noble+hashes@2.0.1/node_modules/@noble/hashes/_blake.js
|
|
181
|
+
var BSIGMA = /* @__PURE__ */ Uint8Array.from([
|
|
182
|
+
0,
|
|
183
|
+
1,
|
|
184
|
+
2,
|
|
185
|
+
3,
|
|
186
|
+
4,
|
|
187
|
+
5,
|
|
188
|
+
6,
|
|
189
|
+
7,
|
|
190
|
+
8,
|
|
191
|
+
9,
|
|
192
|
+
10,
|
|
193
|
+
11,
|
|
194
|
+
12,
|
|
195
|
+
13,
|
|
196
|
+
14,
|
|
197
|
+
15,
|
|
198
|
+
14,
|
|
199
|
+
10,
|
|
200
|
+
4,
|
|
201
|
+
8,
|
|
202
|
+
9,
|
|
203
|
+
15,
|
|
204
|
+
13,
|
|
205
|
+
6,
|
|
206
|
+
1,
|
|
207
|
+
12,
|
|
208
|
+
0,
|
|
209
|
+
2,
|
|
210
|
+
11,
|
|
211
|
+
7,
|
|
212
|
+
5,
|
|
213
|
+
3,
|
|
214
|
+
11,
|
|
215
|
+
8,
|
|
216
|
+
12,
|
|
217
|
+
0,
|
|
218
|
+
5,
|
|
219
|
+
2,
|
|
220
|
+
15,
|
|
221
|
+
13,
|
|
222
|
+
10,
|
|
223
|
+
14,
|
|
224
|
+
3,
|
|
225
|
+
6,
|
|
226
|
+
7,
|
|
227
|
+
1,
|
|
228
|
+
9,
|
|
229
|
+
4,
|
|
230
|
+
7,
|
|
231
|
+
9,
|
|
232
|
+
3,
|
|
233
|
+
1,
|
|
234
|
+
13,
|
|
235
|
+
12,
|
|
236
|
+
11,
|
|
237
|
+
14,
|
|
238
|
+
2,
|
|
239
|
+
6,
|
|
240
|
+
5,
|
|
241
|
+
10,
|
|
242
|
+
4,
|
|
243
|
+
0,
|
|
244
|
+
15,
|
|
245
|
+
8,
|
|
246
|
+
9,
|
|
247
|
+
0,
|
|
248
|
+
5,
|
|
249
|
+
7,
|
|
250
|
+
2,
|
|
251
|
+
4,
|
|
252
|
+
10,
|
|
253
|
+
15,
|
|
254
|
+
14,
|
|
255
|
+
1,
|
|
256
|
+
11,
|
|
257
|
+
12,
|
|
258
|
+
6,
|
|
259
|
+
8,
|
|
260
|
+
3,
|
|
261
|
+
13,
|
|
262
|
+
2,
|
|
263
|
+
12,
|
|
264
|
+
6,
|
|
265
|
+
10,
|
|
266
|
+
0,
|
|
267
|
+
11,
|
|
268
|
+
8,
|
|
269
|
+
3,
|
|
270
|
+
4,
|
|
271
|
+
13,
|
|
272
|
+
7,
|
|
273
|
+
5,
|
|
274
|
+
15,
|
|
275
|
+
14,
|
|
276
|
+
1,
|
|
277
|
+
9,
|
|
278
|
+
12,
|
|
279
|
+
5,
|
|
280
|
+
1,
|
|
281
|
+
15,
|
|
282
|
+
14,
|
|
283
|
+
13,
|
|
284
|
+
4,
|
|
285
|
+
10,
|
|
286
|
+
0,
|
|
287
|
+
7,
|
|
288
|
+
6,
|
|
289
|
+
3,
|
|
290
|
+
9,
|
|
291
|
+
2,
|
|
292
|
+
8,
|
|
293
|
+
11,
|
|
294
|
+
13,
|
|
295
|
+
11,
|
|
296
|
+
7,
|
|
297
|
+
14,
|
|
298
|
+
12,
|
|
299
|
+
1,
|
|
300
|
+
3,
|
|
301
|
+
9,
|
|
302
|
+
5,
|
|
303
|
+
0,
|
|
304
|
+
15,
|
|
305
|
+
4,
|
|
306
|
+
8,
|
|
307
|
+
6,
|
|
308
|
+
2,
|
|
309
|
+
10,
|
|
310
|
+
6,
|
|
311
|
+
15,
|
|
312
|
+
14,
|
|
313
|
+
9,
|
|
314
|
+
11,
|
|
315
|
+
3,
|
|
316
|
+
0,
|
|
317
|
+
8,
|
|
318
|
+
12,
|
|
319
|
+
2,
|
|
320
|
+
13,
|
|
321
|
+
7,
|
|
322
|
+
1,
|
|
323
|
+
4,
|
|
324
|
+
10,
|
|
325
|
+
5,
|
|
326
|
+
10,
|
|
327
|
+
2,
|
|
328
|
+
8,
|
|
329
|
+
4,
|
|
330
|
+
7,
|
|
331
|
+
6,
|
|
332
|
+
1,
|
|
333
|
+
5,
|
|
334
|
+
15,
|
|
335
|
+
11,
|
|
336
|
+
9,
|
|
337
|
+
14,
|
|
338
|
+
3,
|
|
339
|
+
12,
|
|
340
|
+
13,
|
|
341
|
+
0,
|
|
342
|
+
0,
|
|
343
|
+
1,
|
|
344
|
+
2,
|
|
345
|
+
3,
|
|
346
|
+
4,
|
|
347
|
+
5,
|
|
348
|
+
6,
|
|
349
|
+
7,
|
|
350
|
+
8,
|
|
351
|
+
9,
|
|
352
|
+
10,
|
|
353
|
+
11,
|
|
354
|
+
12,
|
|
355
|
+
13,
|
|
356
|
+
14,
|
|
357
|
+
15,
|
|
358
|
+
14,
|
|
359
|
+
10,
|
|
360
|
+
4,
|
|
361
|
+
8,
|
|
362
|
+
9,
|
|
363
|
+
15,
|
|
364
|
+
13,
|
|
365
|
+
6,
|
|
366
|
+
1,
|
|
367
|
+
12,
|
|
368
|
+
0,
|
|
369
|
+
2,
|
|
370
|
+
11,
|
|
371
|
+
7,
|
|
372
|
+
5,
|
|
373
|
+
3,
|
|
374
|
+
// Blake1, unused in others
|
|
375
|
+
11,
|
|
376
|
+
8,
|
|
377
|
+
12,
|
|
378
|
+
0,
|
|
379
|
+
5,
|
|
380
|
+
2,
|
|
381
|
+
15,
|
|
382
|
+
13,
|
|
383
|
+
10,
|
|
384
|
+
14,
|
|
385
|
+
3,
|
|
386
|
+
6,
|
|
387
|
+
7,
|
|
388
|
+
1,
|
|
389
|
+
9,
|
|
390
|
+
4,
|
|
391
|
+
7,
|
|
392
|
+
9,
|
|
393
|
+
3,
|
|
394
|
+
1,
|
|
395
|
+
13,
|
|
396
|
+
12,
|
|
397
|
+
11,
|
|
398
|
+
14,
|
|
399
|
+
2,
|
|
400
|
+
6,
|
|
401
|
+
5,
|
|
402
|
+
10,
|
|
403
|
+
4,
|
|
404
|
+
0,
|
|
405
|
+
15,
|
|
406
|
+
8,
|
|
407
|
+
9,
|
|
408
|
+
0,
|
|
409
|
+
5,
|
|
410
|
+
7,
|
|
411
|
+
2,
|
|
412
|
+
4,
|
|
413
|
+
10,
|
|
414
|
+
15,
|
|
415
|
+
14,
|
|
416
|
+
1,
|
|
417
|
+
11,
|
|
418
|
+
12,
|
|
419
|
+
6,
|
|
420
|
+
8,
|
|
421
|
+
3,
|
|
422
|
+
13,
|
|
423
|
+
2,
|
|
424
|
+
12,
|
|
425
|
+
6,
|
|
426
|
+
10,
|
|
427
|
+
0,
|
|
428
|
+
11,
|
|
429
|
+
8,
|
|
430
|
+
3,
|
|
431
|
+
4,
|
|
432
|
+
13,
|
|
433
|
+
7,
|
|
434
|
+
5,
|
|
435
|
+
15,
|
|
436
|
+
14,
|
|
437
|
+
1,
|
|
438
|
+
9
|
|
439
|
+
]);
|
|
440
|
+
|
|
441
|
+
// ../../node_modules/.pnpm/@noble+hashes@2.0.1/node_modules/@noble/hashes/blake2.js
|
|
442
|
+
var B2B_IV = /* @__PURE__ */ Uint32Array.from([
|
|
443
|
+
4089235720,
|
|
444
|
+
1779033703,
|
|
445
|
+
2227873595,
|
|
446
|
+
3144134277,
|
|
447
|
+
4271175723,
|
|
448
|
+
1013904242,
|
|
449
|
+
1595750129,
|
|
450
|
+
2773480762,
|
|
451
|
+
2917565137,
|
|
452
|
+
1359893119,
|
|
453
|
+
725511199,
|
|
454
|
+
2600822924,
|
|
455
|
+
4215389547,
|
|
456
|
+
528734635,
|
|
457
|
+
327033209,
|
|
458
|
+
1541459225
|
|
459
|
+
]);
|
|
460
|
+
var BBUF = /* @__PURE__ */ new Uint32Array(32);
|
|
461
|
+
function G1b(a, b, c, d, msg, x) {
|
|
462
|
+
const Xl = msg[x], Xh = msg[x + 1];
|
|
463
|
+
let Al = BBUF[2 * a], Ah = BBUF[2 * a + 1];
|
|
464
|
+
let Bl = BBUF[2 * b], Bh = BBUF[2 * b + 1];
|
|
465
|
+
let Cl = BBUF[2 * c], Ch = BBUF[2 * c + 1];
|
|
466
|
+
let Dl = BBUF[2 * d], Dh = BBUF[2 * d + 1];
|
|
467
|
+
let ll = add3L(Al, Bl, Xl);
|
|
468
|
+
Ah = add3H(ll, Ah, Bh, Xh);
|
|
469
|
+
Al = ll | 0;
|
|
470
|
+
({ Dh, Dl } = { Dh: Dh ^ Ah, Dl: Dl ^ Al });
|
|
471
|
+
({ Dh, Dl } = { Dh: rotr32H(Dh, Dl), Dl: rotr32L(Dh, Dl) });
|
|
472
|
+
({ h: Ch, l: Cl } = add(Ch, Cl, Dh, Dl));
|
|
473
|
+
({ Bh, Bl } = { Bh: Bh ^ Ch, Bl: Bl ^ Cl });
|
|
474
|
+
({ Bh, Bl } = { Bh: rotrSH(Bh, Bl, 24), Bl: rotrSL(Bh, Bl, 24) });
|
|
475
|
+
BBUF[2 * a] = Al, BBUF[2 * a + 1] = Ah;
|
|
476
|
+
BBUF[2 * b] = Bl, BBUF[2 * b + 1] = Bh;
|
|
477
|
+
BBUF[2 * c] = Cl, BBUF[2 * c + 1] = Ch;
|
|
478
|
+
BBUF[2 * d] = Dl, BBUF[2 * d + 1] = Dh;
|
|
479
|
+
}
|
|
480
|
+
function G2b(a, b, c, d, msg, x) {
|
|
481
|
+
const Xl = msg[x], Xh = msg[x + 1];
|
|
482
|
+
let Al = BBUF[2 * a], Ah = BBUF[2 * a + 1];
|
|
483
|
+
let Bl = BBUF[2 * b], Bh = BBUF[2 * b + 1];
|
|
484
|
+
let Cl = BBUF[2 * c], Ch = BBUF[2 * c + 1];
|
|
485
|
+
let Dl = BBUF[2 * d], Dh = BBUF[2 * d + 1];
|
|
486
|
+
let ll = add3L(Al, Bl, Xl);
|
|
487
|
+
Ah = add3H(ll, Ah, Bh, Xh);
|
|
488
|
+
Al = ll | 0;
|
|
489
|
+
({ Dh, Dl } = { Dh: Dh ^ Ah, Dl: Dl ^ Al });
|
|
490
|
+
({ Dh, Dl } = { Dh: rotrSH(Dh, Dl, 16), Dl: rotrSL(Dh, Dl, 16) });
|
|
491
|
+
({ h: Ch, l: Cl } = add(Ch, Cl, Dh, Dl));
|
|
492
|
+
({ Bh, Bl } = { Bh: Bh ^ Ch, Bl: Bl ^ Cl });
|
|
493
|
+
({ Bh, Bl } = { Bh: rotrBH(Bh, Bl, 63), Bl: rotrBL(Bh, Bl, 63) });
|
|
494
|
+
BBUF[2 * a] = Al, BBUF[2 * a + 1] = Ah;
|
|
495
|
+
BBUF[2 * b] = Bl, BBUF[2 * b + 1] = Bh;
|
|
496
|
+
BBUF[2 * c] = Cl, BBUF[2 * c + 1] = Ch;
|
|
497
|
+
BBUF[2 * d] = Dl, BBUF[2 * d + 1] = Dh;
|
|
498
|
+
}
|
|
499
|
+
function checkBlake2Opts(outputLen, opts = {}, keyLen, saltLen, persLen) {
|
|
500
|
+
anumber(keyLen);
|
|
501
|
+
if (outputLen < 0 || outputLen > keyLen)
|
|
502
|
+
throw new Error("outputLen bigger than keyLen");
|
|
503
|
+
const { key, salt, personalization } = opts;
|
|
504
|
+
if (key !== void 0 && (key.length < 1 || key.length > keyLen))
|
|
505
|
+
throw new Error('"key" expected to be undefined or of length=1..' + keyLen);
|
|
506
|
+
if (salt !== void 0)
|
|
507
|
+
abytes(salt, saltLen, "salt");
|
|
508
|
+
if (personalization !== void 0)
|
|
509
|
+
abytes(personalization, persLen, "personalization");
|
|
510
|
+
}
|
|
511
|
+
var _BLAKE2 = class {
|
|
512
|
+
buffer;
|
|
513
|
+
buffer32;
|
|
514
|
+
finished = false;
|
|
515
|
+
destroyed = false;
|
|
516
|
+
length = 0;
|
|
517
|
+
pos = 0;
|
|
518
|
+
blockLen;
|
|
519
|
+
outputLen;
|
|
520
|
+
constructor(blockLen, outputLen) {
|
|
521
|
+
anumber(blockLen);
|
|
522
|
+
anumber(outputLen);
|
|
523
|
+
this.blockLen = blockLen;
|
|
524
|
+
this.outputLen = outputLen;
|
|
525
|
+
this.buffer = new Uint8Array(blockLen);
|
|
526
|
+
this.buffer32 = u32(this.buffer);
|
|
527
|
+
}
|
|
528
|
+
update(data) {
|
|
529
|
+
aexists(this);
|
|
530
|
+
abytes(data);
|
|
531
|
+
const { blockLen, buffer, buffer32 } = this;
|
|
532
|
+
const len = data.length;
|
|
533
|
+
const offset = data.byteOffset;
|
|
534
|
+
const buf = data.buffer;
|
|
535
|
+
for (let pos = 0; pos < len; ) {
|
|
536
|
+
if (this.pos === blockLen) {
|
|
537
|
+
swap32IfBE(buffer32);
|
|
538
|
+
this.compress(buffer32, 0, false);
|
|
539
|
+
swap32IfBE(buffer32);
|
|
540
|
+
this.pos = 0;
|
|
541
|
+
}
|
|
542
|
+
const take = Math.min(blockLen - this.pos, len - pos);
|
|
543
|
+
const dataOffset = offset + pos;
|
|
544
|
+
if (take === blockLen && !(dataOffset % 4) && pos + take < len) {
|
|
545
|
+
const data32 = new Uint32Array(buf, dataOffset, Math.floor((len - pos) / 4));
|
|
546
|
+
swap32IfBE(data32);
|
|
547
|
+
for (let pos32 = 0; pos + blockLen < len; pos32 += buffer32.length, pos += blockLen) {
|
|
548
|
+
this.length += blockLen;
|
|
549
|
+
this.compress(data32, pos32, false);
|
|
550
|
+
}
|
|
551
|
+
swap32IfBE(data32);
|
|
552
|
+
continue;
|
|
553
|
+
}
|
|
554
|
+
buffer.set(data.subarray(pos, pos + take), this.pos);
|
|
555
|
+
this.pos += take;
|
|
556
|
+
this.length += take;
|
|
557
|
+
pos += take;
|
|
558
|
+
}
|
|
559
|
+
return this;
|
|
560
|
+
}
|
|
561
|
+
digestInto(out) {
|
|
562
|
+
aexists(this);
|
|
563
|
+
aoutput(out, this);
|
|
564
|
+
const { pos, buffer32 } = this;
|
|
565
|
+
this.finished = true;
|
|
566
|
+
clean(this.buffer.subarray(pos));
|
|
567
|
+
swap32IfBE(buffer32);
|
|
568
|
+
this.compress(buffer32, 0, true);
|
|
569
|
+
swap32IfBE(buffer32);
|
|
570
|
+
const out32 = u32(out);
|
|
571
|
+
this.get().forEach((v, i) => out32[i] = swap8IfBE(v));
|
|
572
|
+
}
|
|
573
|
+
digest() {
|
|
574
|
+
const { buffer, outputLen } = this;
|
|
575
|
+
this.digestInto(buffer);
|
|
576
|
+
const res = buffer.slice(0, outputLen);
|
|
577
|
+
this.destroy();
|
|
578
|
+
return res;
|
|
579
|
+
}
|
|
580
|
+
_cloneInto(to) {
|
|
581
|
+
const { buffer, length, finished, destroyed, outputLen, pos } = this;
|
|
582
|
+
to ||= new this.constructor({ dkLen: outputLen });
|
|
583
|
+
to.set(...this.get());
|
|
584
|
+
to.buffer.set(buffer);
|
|
585
|
+
to.destroyed = destroyed;
|
|
586
|
+
to.finished = finished;
|
|
587
|
+
to.length = length;
|
|
588
|
+
to.pos = pos;
|
|
589
|
+
to.outputLen = outputLen;
|
|
590
|
+
return to;
|
|
591
|
+
}
|
|
592
|
+
clone() {
|
|
593
|
+
return this._cloneInto();
|
|
594
|
+
}
|
|
595
|
+
};
|
|
596
|
+
var _BLAKE2b = class extends _BLAKE2 {
|
|
597
|
+
// Same as SHA-512, but LE
|
|
598
|
+
v0l = B2B_IV[0] | 0;
|
|
599
|
+
v0h = B2B_IV[1] | 0;
|
|
600
|
+
v1l = B2B_IV[2] | 0;
|
|
601
|
+
v1h = B2B_IV[3] | 0;
|
|
602
|
+
v2l = B2B_IV[4] | 0;
|
|
603
|
+
v2h = B2B_IV[5] | 0;
|
|
604
|
+
v3l = B2B_IV[6] | 0;
|
|
605
|
+
v3h = B2B_IV[7] | 0;
|
|
606
|
+
v4l = B2B_IV[8] | 0;
|
|
607
|
+
v4h = B2B_IV[9] | 0;
|
|
608
|
+
v5l = B2B_IV[10] | 0;
|
|
609
|
+
v5h = B2B_IV[11] | 0;
|
|
610
|
+
v6l = B2B_IV[12] | 0;
|
|
611
|
+
v6h = B2B_IV[13] | 0;
|
|
612
|
+
v7l = B2B_IV[14] | 0;
|
|
613
|
+
v7h = B2B_IV[15] | 0;
|
|
614
|
+
constructor(opts = {}) {
|
|
615
|
+
const olen = opts.dkLen === void 0 ? 64 : opts.dkLen;
|
|
616
|
+
super(128, olen);
|
|
617
|
+
checkBlake2Opts(olen, opts, 64, 16, 16);
|
|
618
|
+
let { key, personalization, salt } = opts;
|
|
619
|
+
let keyLength = 0;
|
|
620
|
+
if (key !== void 0) {
|
|
621
|
+
abytes(key, void 0, "key");
|
|
622
|
+
keyLength = key.length;
|
|
623
|
+
}
|
|
624
|
+
this.v0l ^= this.outputLen | keyLength << 8 | 1 << 16 | 1 << 24;
|
|
625
|
+
if (salt !== void 0) {
|
|
626
|
+
abytes(salt, void 0, "salt");
|
|
627
|
+
const slt = u32(salt);
|
|
628
|
+
this.v4l ^= swap8IfBE(slt[0]);
|
|
629
|
+
this.v4h ^= swap8IfBE(slt[1]);
|
|
630
|
+
this.v5l ^= swap8IfBE(slt[2]);
|
|
631
|
+
this.v5h ^= swap8IfBE(slt[3]);
|
|
632
|
+
}
|
|
633
|
+
if (personalization !== void 0) {
|
|
634
|
+
abytes(personalization, void 0, "personalization");
|
|
635
|
+
const pers = u32(personalization);
|
|
636
|
+
this.v6l ^= swap8IfBE(pers[0]);
|
|
637
|
+
this.v6h ^= swap8IfBE(pers[1]);
|
|
638
|
+
this.v7l ^= swap8IfBE(pers[2]);
|
|
639
|
+
this.v7h ^= swap8IfBE(pers[3]);
|
|
640
|
+
}
|
|
641
|
+
if (key !== void 0) {
|
|
642
|
+
const tmp = new Uint8Array(this.blockLen);
|
|
643
|
+
tmp.set(key);
|
|
644
|
+
this.update(tmp);
|
|
645
|
+
}
|
|
646
|
+
}
|
|
647
|
+
// prettier-ignore
|
|
648
|
+
get() {
|
|
649
|
+
let { v0l, v0h, v1l, v1h, v2l, v2h, v3l, v3h, v4l, v4h, v5l, v5h, v6l, v6h, v7l, v7h } = this;
|
|
650
|
+
return [v0l, v0h, v1l, v1h, v2l, v2h, v3l, v3h, v4l, v4h, v5l, v5h, v6l, v6h, v7l, v7h];
|
|
651
|
+
}
|
|
652
|
+
// prettier-ignore
|
|
653
|
+
set(v0l, v0h, v1l, v1h, v2l, v2h, v3l, v3h, v4l, v4h, v5l, v5h, v6l, v6h, v7l, v7h) {
|
|
654
|
+
this.v0l = v0l | 0;
|
|
655
|
+
this.v0h = v0h | 0;
|
|
656
|
+
this.v1l = v1l | 0;
|
|
657
|
+
this.v1h = v1h | 0;
|
|
658
|
+
this.v2l = v2l | 0;
|
|
659
|
+
this.v2h = v2h | 0;
|
|
660
|
+
this.v3l = v3l | 0;
|
|
661
|
+
this.v3h = v3h | 0;
|
|
662
|
+
this.v4l = v4l | 0;
|
|
663
|
+
this.v4h = v4h | 0;
|
|
664
|
+
this.v5l = v5l | 0;
|
|
665
|
+
this.v5h = v5h | 0;
|
|
666
|
+
this.v6l = v6l | 0;
|
|
667
|
+
this.v6h = v6h | 0;
|
|
668
|
+
this.v7l = v7l | 0;
|
|
669
|
+
this.v7h = v7h | 0;
|
|
670
|
+
}
|
|
671
|
+
compress(msg, offset, isLast) {
|
|
672
|
+
this.get().forEach((v, i) => BBUF[i] = v);
|
|
673
|
+
BBUF.set(B2B_IV, 16);
|
|
674
|
+
let { h, l } = fromBig(BigInt(this.length));
|
|
675
|
+
BBUF[24] = B2B_IV[8] ^ l;
|
|
676
|
+
BBUF[25] = B2B_IV[9] ^ h;
|
|
677
|
+
if (isLast) {
|
|
678
|
+
BBUF[28] = ~BBUF[28];
|
|
679
|
+
BBUF[29] = ~BBUF[29];
|
|
680
|
+
}
|
|
681
|
+
let j = 0;
|
|
682
|
+
const s = BSIGMA;
|
|
683
|
+
for (let i = 0; i < 12; i++) {
|
|
684
|
+
G1b(0, 4, 8, 12, msg, offset + 2 * s[j++]);
|
|
685
|
+
G2b(0, 4, 8, 12, msg, offset + 2 * s[j++]);
|
|
686
|
+
G1b(1, 5, 9, 13, msg, offset + 2 * s[j++]);
|
|
687
|
+
G2b(1, 5, 9, 13, msg, offset + 2 * s[j++]);
|
|
688
|
+
G1b(2, 6, 10, 14, msg, offset + 2 * s[j++]);
|
|
689
|
+
G2b(2, 6, 10, 14, msg, offset + 2 * s[j++]);
|
|
690
|
+
G1b(3, 7, 11, 15, msg, offset + 2 * s[j++]);
|
|
691
|
+
G2b(3, 7, 11, 15, msg, offset + 2 * s[j++]);
|
|
692
|
+
G1b(0, 5, 10, 15, msg, offset + 2 * s[j++]);
|
|
693
|
+
G2b(0, 5, 10, 15, msg, offset + 2 * s[j++]);
|
|
694
|
+
G1b(1, 6, 11, 12, msg, offset + 2 * s[j++]);
|
|
695
|
+
G2b(1, 6, 11, 12, msg, offset + 2 * s[j++]);
|
|
696
|
+
G1b(2, 7, 8, 13, msg, offset + 2 * s[j++]);
|
|
697
|
+
G2b(2, 7, 8, 13, msg, offset + 2 * s[j++]);
|
|
698
|
+
G1b(3, 4, 9, 14, msg, offset + 2 * s[j++]);
|
|
699
|
+
G2b(3, 4, 9, 14, msg, offset + 2 * s[j++]);
|
|
700
|
+
}
|
|
701
|
+
this.v0l ^= BBUF[0] ^ BBUF[16];
|
|
702
|
+
this.v0h ^= BBUF[1] ^ BBUF[17];
|
|
703
|
+
this.v1l ^= BBUF[2] ^ BBUF[18];
|
|
704
|
+
this.v1h ^= BBUF[3] ^ BBUF[19];
|
|
705
|
+
this.v2l ^= BBUF[4] ^ BBUF[20];
|
|
706
|
+
this.v2h ^= BBUF[5] ^ BBUF[21];
|
|
707
|
+
this.v3l ^= BBUF[6] ^ BBUF[22];
|
|
708
|
+
this.v3h ^= BBUF[7] ^ BBUF[23];
|
|
709
|
+
this.v4l ^= BBUF[8] ^ BBUF[24];
|
|
710
|
+
this.v4h ^= BBUF[9] ^ BBUF[25];
|
|
711
|
+
this.v5l ^= BBUF[10] ^ BBUF[26];
|
|
712
|
+
this.v5h ^= BBUF[11] ^ BBUF[27];
|
|
713
|
+
this.v6l ^= BBUF[12] ^ BBUF[28];
|
|
714
|
+
this.v6h ^= BBUF[13] ^ BBUF[29];
|
|
715
|
+
this.v7l ^= BBUF[14] ^ BBUF[30];
|
|
716
|
+
this.v7h ^= BBUF[15] ^ BBUF[31];
|
|
717
|
+
clean(BBUF);
|
|
718
|
+
}
|
|
719
|
+
destroy() {
|
|
720
|
+
this.destroyed = true;
|
|
721
|
+
clean(this.buffer32);
|
|
722
|
+
this.set(0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
|
|
723
|
+
}
|
|
724
|
+
};
|
|
725
|
+
var blake2b = /* @__PURE__ */ createHasher((opts) => new _BLAKE2b(opts));
|
|
726
|
+
|
|
727
|
+
// ../../node_modules/.pnpm/@noble+hashes@2.0.1/node_modules/@noble/hashes/argon2.js
|
|
728
|
+
var AT = { Argond2d: 0, Argon2i: 1, Argon2id: 2 };
|
|
729
|
+
var ARGON2_SYNC_POINTS = 4;
|
|
730
|
+
var abytesOrZero = (buf, errorTitle = "") => {
|
|
731
|
+
if (buf === void 0)
|
|
732
|
+
return Uint8Array.of();
|
|
733
|
+
return kdfInputToBytes(buf, errorTitle);
|
|
734
|
+
};
|
|
735
|
+
function mul(a, b) {
|
|
736
|
+
const aL = a & 65535;
|
|
737
|
+
const aH = a >>> 16;
|
|
738
|
+
const bL = b & 65535;
|
|
739
|
+
const bH = b >>> 16;
|
|
740
|
+
const ll = Math.imul(aL, bL);
|
|
741
|
+
const hl = Math.imul(aH, bL);
|
|
742
|
+
const lh = Math.imul(aL, bH);
|
|
743
|
+
const hh = Math.imul(aH, bH);
|
|
744
|
+
const carry = (ll >>> 16) + (hl & 65535) + lh;
|
|
745
|
+
const high = hh + (hl >>> 16) + (carry >>> 16) | 0;
|
|
746
|
+
const low = carry << 16 | ll & 65535;
|
|
747
|
+
return { h: high, l: low };
|
|
748
|
+
}
|
|
749
|
+
function mul2(a, b) {
|
|
750
|
+
const { h, l } = mul(a, b);
|
|
751
|
+
return { h: (h << 1 | l >>> 31) & 4294967295, l: l << 1 & 4294967295 };
|
|
752
|
+
}
|
|
753
|
+
function blamka(Ah, Al, Bh, Bl) {
|
|
754
|
+
const { h: Ch, l: Cl } = mul2(Al, Bl);
|
|
755
|
+
const Rll = add3L(Al, Bl, Cl);
|
|
756
|
+
return { h: add3H(Rll, Ah, Bh, Ch), l: Rll | 0 };
|
|
757
|
+
}
|
|
758
|
+
var A2_BUF = new Uint32Array(256);
|
|
759
|
+
function G(a, b, c, d) {
|
|
760
|
+
let Al = A2_BUF[2 * a], Ah = A2_BUF[2 * a + 1];
|
|
761
|
+
let Bl = A2_BUF[2 * b], Bh = A2_BUF[2 * b + 1];
|
|
762
|
+
let Cl = A2_BUF[2 * c], Ch = A2_BUF[2 * c + 1];
|
|
763
|
+
let Dl = A2_BUF[2 * d], Dh = A2_BUF[2 * d + 1];
|
|
764
|
+
({ h: Ah, l: Al } = blamka(Ah, Al, Bh, Bl));
|
|
765
|
+
({ Dh, Dl } = { Dh: Dh ^ Ah, Dl: Dl ^ Al });
|
|
766
|
+
({ Dh, Dl } = { Dh: rotr32H(Dh, Dl), Dl: rotr32L(Dh, Dl) });
|
|
767
|
+
({ h: Ch, l: Cl } = blamka(Ch, Cl, Dh, Dl));
|
|
768
|
+
({ Bh, Bl } = { Bh: Bh ^ Ch, Bl: Bl ^ Cl });
|
|
769
|
+
({ Bh, Bl } = { Bh: rotrSH(Bh, Bl, 24), Bl: rotrSL(Bh, Bl, 24) });
|
|
770
|
+
({ h: Ah, l: Al } = blamka(Ah, Al, Bh, Bl));
|
|
771
|
+
({ Dh, Dl } = { Dh: Dh ^ Ah, Dl: Dl ^ Al });
|
|
772
|
+
({ Dh, Dl } = { Dh: rotrSH(Dh, Dl, 16), Dl: rotrSL(Dh, Dl, 16) });
|
|
773
|
+
({ h: Ch, l: Cl } = blamka(Ch, Cl, Dh, Dl));
|
|
774
|
+
({ Bh, Bl } = { Bh: Bh ^ Ch, Bl: Bl ^ Cl });
|
|
775
|
+
({ Bh, Bl } = { Bh: rotrBH(Bh, Bl, 63), Bl: rotrBL(Bh, Bl, 63) });
|
|
776
|
+
A2_BUF[2 * a] = Al, A2_BUF[2 * a + 1] = Ah;
|
|
777
|
+
A2_BUF[2 * b] = Bl, A2_BUF[2 * b + 1] = Bh;
|
|
778
|
+
A2_BUF[2 * c] = Cl, A2_BUF[2 * c + 1] = Ch;
|
|
779
|
+
A2_BUF[2 * d] = Dl, A2_BUF[2 * d + 1] = Dh;
|
|
780
|
+
}
|
|
781
|
+
function P(v00, v01, v02, v03, v04, v05, v06, v07, v08, v09, v10, v11, v12, v13, v14, v15) {
|
|
782
|
+
G(v00, v04, v08, v12);
|
|
783
|
+
G(v01, v05, v09, v13);
|
|
784
|
+
G(v02, v06, v10, v14);
|
|
785
|
+
G(v03, v07, v11, v15);
|
|
786
|
+
G(v00, v05, v10, v15);
|
|
787
|
+
G(v01, v06, v11, v12);
|
|
788
|
+
G(v02, v07, v08, v13);
|
|
789
|
+
G(v03, v04, v09, v14);
|
|
790
|
+
}
|
|
791
|
+
function block(x, xPos, yPos, outPos, needXor) {
|
|
792
|
+
for (let i = 0; i < 256; i++)
|
|
793
|
+
A2_BUF[i] = x[xPos + i] ^ x[yPos + i];
|
|
794
|
+
for (let i = 0; i < 128; i += 16) {
|
|
795
|
+
P(i, i + 1, i + 2, i + 3, i + 4, i + 5, i + 6, i + 7, i + 8, i + 9, i + 10, i + 11, i + 12, i + 13, i + 14, i + 15);
|
|
796
|
+
}
|
|
797
|
+
for (let i = 0; i < 16; i += 2) {
|
|
798
|
+
P(i, i + 1, i + 16, i + 17, i + 32, i + 33, i + 48, i + 49, i + 64, i + 65, i + 80, i + 81, i + 96, i + 97, i + 112, i + 113);
|
|
799
|
+
}
|
|
800
|
+
if (needXor)
|
|
801
|
+
for (let i = 0; i < 256; i++)
|
|
802
|
+
x[outPos + i] ^= A2_BUF[i] ^ x[xPos + i] ^ x[yPos + i];
|
|
803
|
+
else
|
|
804
|
+
for (let i = 0; i < 256; i++)
|
|
805
|
+
x[outPos + i] = A2_BUF[i] ^ x[xPos + i] ^ x[yPos + i];
|
|
806
|
+
clean(A2_BUF);
|
|
807
|
+
}
|
|
808
|
+
function Hp(A, dkLen) {
|
|
809
|
+
const A8 = u8(A);
|
|
810
|
+
const T = new Uint32Array(1);
|
|
811
|
+
const T8 = u8(T);
|
|
812
|
+
T[0] = dkLen;
|
|
813
|
+
if (dkLen <= 64)
|
|
814
|
+
return blake2b.create({ dkLen }).update(T8).update(A8).digest();
|
|
815
|
+
const out = new Uint8Array(dkLen);
|
|
816
|
+
let V = blake2b.create({}).update(T8).update(A8).digest();
|
|
817
|
+
let pos = 0;
|
|
818
|
+
out.set(V.subarray(0, 32));
|
|
819
|
+
pos += 32;
|
|
820
|
+
for (; dkLen - pos > 64; pos += 32) {
|
|
821
|
+
const Vh = blake2b.create({}).update(V);
|
|
822
|
+
Vh.digestInto(V);
|
|
823
|
+
Vh.destroy();
|
|
824
|
+
out.set(V.subarray(0, 32), pos);
|
|
825
|
+
}
|
|
826
|
+
out.set(blake2b(V, { dkLen: dkLen - pos }), pos);
|
|
827
|
+
clean(V, T);
|
|
828
|
+
return u32(out);
|
|
829
|
+
}
|
|
830
|
+
function indexAlpha(r, s, laneLen, segmentLen, index, randL, sameLane = false) {
|
|
831
|
+
let area;
|
|
832
|
+
if (r === 0) {
|
|
833
|
+
if (s === 0)
|
|
834
|
+
area = index - 1;
|
|
835
|
+
else if (sameLane)
|
|
836
|
+
area = s * segmentLen + index - 1;
|
|
837
|
+
else
|
|
838
|
+
area = s * segmentLen + (index == 0 ? -1 : 0);
|
|
839
|
+
} else if (sameLane)
|
|
840
|
+
area = laneLen - segmentLen + index - 1;
|
|
841
|
+
else
|
|
842
|
+
area = laneLen - segmentLen + (index == 0 ? -1 : 0);
|
|
843
|
+
const startPos = r !== 0 && s !== ARGON2_SYNC_POINTS - 1 ? (s + 1) * segmentLen : 0;
|
|
844
|
+
const rel = area - 1 - mul(area, mul(randL, randL).h).h;
|
|
845
|
+
return (startPos + rel) % laneLen;
|
|
846
|
+
}
|
|
847
|
+
var maxUint32 = Math.pow(2, 32);
|
|
848
|
+
function isU32(num) {
|
|
849
|
+
return Number.isSafeInteger(num) && num >= 0 && num < maxUint32;
|
|
850
|
+
}
|
|
851
|
+
function argon2Opts(opts) {
|
|
852
|
+
const merged = {
|
|
853
|
+
version: 19,
|
|
854
|
+
dkLen: 32,
|
|
855
|
+
maxmem: maxUint32 - 1,
|
|
856
|
+
asyncTick: 10
|
|
857
|
+
};
|
|
858
|
+
for (let [k, v] of Object.entries(opts))
|
|
859
|
+
if (v !== void 0)
|
|
860
|
+
merged[k] = v;
|
|
861
|
+
const { dkLen, p, m, t, version, onProgress, asyncTick } = merged;
|
|
862
|
+
if (!isU32(dkLen) || dkLen < 4)
|
|
863
|
+
throw new Error('"dkLen" must be 4..');
|
|
864
|
+
if (!isU32(p) || p < 1 || p >= Math.pow(2, 24))
|
|
865
|
+
throw new Error('"p" must be 1..2^24');
|
|
866
|
+
if (!isU32(m))
|
|
867
|
+
throw new Error('"m" must be 0..2^32');
|
|
868
|
+
if (!isU32(t) || t < 1)
|
|
869
|
+
throw new Error('"t" (iterations) must be 1..2^32');
|
|
870
|
+
if (onProgress !== void 0 && typeof onProgress !== "function")
|
|
871
|
+
throw new Error('"progressCb" must be a function');
|
|
872
|
+
anumber(asyncTick, "asyncTick");
|
|
873
|
+
if (!isU32(m) || m < 8 * p)
|
|
874
|
+
throw new Error('"m" (memory) must be at least 8*p bytes');
|
|
875
|
+
if (version !== 16 && version !== 19)
|
|
876
|
+
throw new Error('"version" must be 0x10 or 0x13, got ' + version);
|
|
877
|
+
return merged;
|
|
878
|
+
}
|
|
879
|
+
function argon2Init(password, salt, type, opts) {
|
|
880
|
+
password = kdfInputToBytes(password, "password");
|
|
881
|
+
salt = kdfInputToBytes(salt, "salt");
|
|
882
|
+
if (!isU32(password.length))
|
|
883
|
+
throw new Error('"password" must be less of length 1..4Gb');
|
|
884
|
+
if (!isU32(salt.length) || salt.length < 8)
|
|
885
|
+
throw new Error('"salt" must be of length 8..4Gb');
|
|
886
|
+
if (!Object.values(AT).includes(type))
|
|
887
|
+
throw new Error('"type" was invalid');
|
|
888
|
+
let { p, dkLen, m, t, version, key, personalization, maxmem, onProgress, asyncTick } = argon2Opts(opts);
|
|
889
|
+
key = abytesOrZero(key, "key");
|
|
890
|
+
personalization = abytesOrZero(personalization, "personalization");
|
|
891
|
+
const h = blake2b.create();
|
|
892
|
+
const BUF = new Uint32Array(1);
|
|
893
|
+
const BUF8 = u8(BUF);
|
|
894
|
+
for (let item of [p, dkLen, m, t, version, type]) {
|
|
895
|
+
BUF[0] = item;
|
|
896
|
+
h.update(BUF8);
|
|
897
|
+
}
|
|
898
|
+
for (let i of [password, salt, key, personalization]) {
|
|
899
|
+
BUF[0] = i.length;
|
|
900
|
+
h.update(BUF8).update(i);
|
|
901
|
+
}
|
|
902
|
+
const H0 = new Uint32Array(18);
|
|
903
|
+
const H0_8 = u8(H0);
|
|
904
|
+
h.digestInto(H0_8);
|
|
905
|
+
const lanes = p;
|
|
906
|
+
const mP = 4 * p * Math.floor(m / (ARGON2_SYNC_POINTS * p));
|
|
907
|
+
const laneLen = Math.floor(mP / p);
|
|
908
|
+
const segmentLen = Math.floor(laneLen / ARGON2_SYNC_POINTS);
|
|
909
|
+
const memUsed = mP * 256;
|
|
910
|
+
if (!isU32(maxmem) || memUsed > maxmem)
|
|
911
|
+
throw new Error('"maxmem" expected <2**32, got: maxmem=' + maxmem + ", memused=" + memUsed);
|
|
912
|
+
const B = new Uint32Array(memUsed);
|
|
913
|
+
for (let l = 0; l < p; l++) {
|
|
914
|
+
const i = 256 * laneLen * l;
|
|
915
|
+
H0[17] = l;
|
|
916
|
+
H0[16] = 0;
|
|
917
|
+
B.set(Hp(H0, 1024), i);
|
|
918
|
+
H0[16] = 1;
|
|
919
|
+
B.set(Hp(H0, 1024), i + 256);
|
|
920
|
+
}
|
|
921
|
+
let perBlock = () => {
|
|
922
|
+
};
|
|
923
|
+
if (onProgress) {
|
|
924
|
+
const totalBlock = t * ARGON2_SYNC_POINTS * p * segmentLen;
|
|
925
|
+
const callbackPer = Math.max(Math.floor(totalBlock / 1e4), 1);
|
|
926
|
+
let blockCnt = 0;
|
|
927
|
+
perBlock = () => {
|
|
928
|
+
blockCnt++;
|
|
929
|
+
if (onProgress && (!(blockCnt % callbackPer) || blockCnt === totalBlock))
|
|
930
|
+
onProgress(blockCnt / totalBlock);
|
|
931
|
+
};
|
|
932
|
+
}
|
|
933
|
+
clean(BUF, H0);
|
|
934
|
+
return { type, mP, p, t, version, B, laneLen, lanes, segmentLen, dkLen, perBlock, asyncTick };
|
|
935
|
+
}
|
|
936
|
+
function argon2Output(B, p, laneLen, dkLen) {
|
|
937
|
+
const B_final = new Uint32Array(256);
|
|
938
|
+
for (let l = 0; l < p; l++)
|
|
939
|
+
for (let j = 0; j < 256; j++)
|
|
940
|
+
B_final[j] ^= B[256 * (laneLen * l + laneLen - 1) + j];
|
|
941
|
+
const res = u8(Hp(B_final, dkLen));
|
|
942
|
+
clean(B_final);
|
|
943
|
+
return res;
|
|
944
|
+
}
|
|
945
|
+
function processBlock(B, address, l, r, s, index, laneLen, segmentLen, lanes, offset, prev, dataIndependent, needXor) {
|
|
946
|
+
if (offset % laneLen)
|
|
947
|
+
prev = offset - 1;
|
|
948
|
+
let randL, randH;
|
|
949
|
+
if (dataIndependent) {
|
|
950
|
+
let i128 = index % 128;
|
|
951
|
+
if (i128 === 0) {
|
|
952
|
+
address[256 + 12]++;
|
|
953
|
+
block(address, 256, 2 * 256, 0, false);
|
|
954
|
+
block(address, 0, 2 * 256, 0, false);
|
|
955
|
+
}
|
|
956
|
+
randL = address[2 * i128];
|
|
957
|
+
randH = address[2 * i128 + 1];
|
|
958
|
+
} else {
|
|
959
|
+
const T = 256 * prev;
|
|
960
|
+
randL = B[T];
|
|
961
|
+
randH = B[T + 1];
|
|
962
|
+
}
|
|
963
|
+
const refLane = r === 0 && s === 0 ? l : randH % lanes;
|
|
964
|
+
const refPos = indexAlpha(r, s, laneLen, segmentLen, index, randL, refLane == l);
|
|
965
|
+
const refBlock = laneLen * refLane + refPos;
|
|
966
|
+
block(B, 256 * prev, 256 * refBlock, offset * 256, needXor);
|
|
967
|
+
}
|
|
968
|
+
function argon2(type, password, salt, opts) {
|
|
969
|
+
const { mP, p, t, version, B, laneLen, lanes, segmentLen, dkLen, perBlock } = argon2Init(password, salt, type, opts);
|
|
970
|
+
const address = new Uint32Array(3 * 256);
|
|
971
|
+
address[256 + 6] = mP;
|
|
972
|
+
address[256 + 8] = t;
|
|
973
|
+
address[256 + 10] = type;
|
|
974
|
+
for (let r = 0; r < t; r++) {
|
|
975
|
+
const needXor = r !== 0 && version === 19;
|
|
976
|
+
address[256 + 0] = r;
|
|
977
|
+
for (let s = 0; s < ARGON2_SYNC_POINTS; s++) {
|
|
978
|
+
address[256 + 4] = s;
|
|
979
|
+
const dataIndependent = type == AT.Argon2i || type == AT.Argon2id && r === 0 && s < 2;
|
|
980
|
+
for (let l = 0; l < p; l++) {
|
|
981
|
+
address[256 + 2] = l;
|
|
982
|
+
address[256 + 12] = 0;
|
|
983
|
+
let startPos = 0;
|
|
984
|
+
if (r === 0 && s === 0) {
|
|
985
|
+
startPos = 2;
|
|
986
|
+
if (dataIndependent) {
|
|
987
|
+
address[256 + 12]++;
|
|
988
|
+
block(address, 256, 2 * 256, 0, false);
|
|
989
|
+
block(address, 0, 2 * 256, 0, false);
|
|
990
|
+
}
|
|
991
|
+
}
|
|
992
|
+
let offset = l * laneLen + s * segmentLen + startPos;
|
|
993
|
+
let prev = offset % laneLen ? offset - 1 : offset + laneLen - 1;
|
|
994
|
+
for (let index = startPos; index < segmentLen; index++, offset++, prev++) {
|
|
995
|
+
perBlock();
|
|
996
|
+
processBlock(B, address, l, r, s, index, laneLen, segmentLen, lanes, offset, prev, dataIndependent, needXor);
|
|
997
|
+
}
|
|
998
|
+
}
|
|
999
|
+
}
|
|
1000
|
+
}
|
|
1001
|
+
clean(address);
|
|
1002
|
+
return argon2Output(B, p, laneLen, dkLen);
|
|
1003
|
+
}
|
|
1004
|
+
var argon2id = (password, salt, opts) => argon2(AT.Argon2id, password, salt, opts);
|
|
1005
|
+
|
|
1006
|
+
// ../../node_modules/.pnpm/@noble+curves@2.0.1/node_modules/@noble/curves/utils.js
|
|
1007
|
+
var _0n = /* @__PURE__ */ BigInt(0);
|
|
1008
|
+
function abignumber(n) {
|
|
1009
|
+
if (typeof n === "bigint") {
|
|
1010
|
+
if (!isPosBig(n))
|
|
1011
|
+
throw new Error("positive bigint expected, got " + n);
|
|
1012
|
+
} else
|
|
1013
|
+
anumber(n);
|
|
1014
|
+
return n;
|
|
1015
|
+
}
|
|
1016
|
+
function hexToNumber(hex) {
|
|
1017
|
+
if (typeof hex !== "string")
|
|
1018
|
+
throw new Error("hex string expected, got " + typeof hex);
|
|
1019
|
+
return hex === "" ? _0n : BigInt("0x" + hex);
|
|
1020
|
+
}
|
|
1021
|
+
function bytesToNumberLE(bytes) {
|
|
1022
|
+
return hexToNumber(bytesToHex(copyBytes(abytes(bytes)).reverse()));
|
|
1023
|
+
}
|
|
1024
|
+
function numberToBytesBE(n, len) {
|
|
1025
|
+
anumber(len);
|
|
1026
|
+
n = abignumber(n);
|
|
1027
|
+
const res = hexToBytes(n.toString(16).padStart(len * 2, "0"));
|
|
1028
|
+
if (res.length !== len)
|
|
1029
|
+
throw new Error("number too large");
|
|
1030
|
+
return res;
|
|
1031
|
+
}
|
|
1032
|
+
function numberToBytesLE(n, len) {
|
|
1033
|
+
return numberToBytesBE(n, len).reverse();
|
|
1034
|
+
}
|
|
1035
|
+
function copyBytes(bytes) {
|
|
1036
|
+
return Uint8Array.from(bytes);
|
|
1037
|
+
}
|
|
1038
|
+
var isPosBig = (n) => typeof n === "bigint" && _0n <= n;
|
|
1039
|
+
function inRange(n, min, max) {
|
|
1040
|
+
return isPosBig(n) && isPosBig(min) && isPosBig(max) && min <= n && n < max;
|
|
1041
|
+
}
|
|
1042
|
+
function aInRange(title, n, min, max) {
|
|
1043
|
+
if (!inRange(n, min, max))
|
|
1044
|
+
throw new Error("expected valid " + title + ": " + min + " <= n < " + max + ", got " + n);
|
|
1045
|
+
}
|
|
1046
|
+
function validateObject(object, fields = {}, optFields = {}) {
|
|
1047
|
+
if (!object || typeof object !== "object")
|
|
1048
|
+
throw new Error("expected valid options object");
|
|
1049
|
+
function checkField(fieldName, expectedType, isOpt) {
|
|
1050
|
+
const val = object[fieldName];
|
|
1051
|
+
if (isOpt && val === void 0)
|
|
1052
|
+
return;
|
|
1053
|
+
const current = typeof val;
|
|
1054
|
+
if (current !== expectedType || val === null)
|
|
1055
|
+
throw new Error(`param "${fieldName}" is invalid: expected ${expectedType}, got ${current}`);
|
|
1056
|
+
}
|
|
1057
|
+
const iter = (f, isOpt) => Object.entries(f).forEach(([k, v]) => checkField(k, v, isOpt));
|
|
1058
|
+
iter(fields, false);
|
|
1059
|
+
iter(optFields, true);
|
|
1060
|
+
}
|
|
1061
|
+
|
|
1062
|
+
// ../../node_modules/.pnpm/@noble+curves@2.0.1/node_modules/@noble/curves/abstract/modular.js
|
|
1063
|
+
var _0n2 = /* @__PURE__ */ BigInt(0);
|
|
1064
|
+
function mod(a, b) {
|
|
1065
|
+
const result = a % b;
|
|
1066
|
+
return result >= _0n2 ? result : b + result;
|
|
1067
|
+
}
|
|
1068
|
+
function pow2(x, power, modulo) {
|
|
1069
|
+
let res = x;
|
|
1070
|
+
while (power-- > _0n2) {
|
|
1071
|
+
res *= res;
|
|
1072
|
+
res %= modulo;
|
|
1073
|
+
}
|
|
1074
|
+
return res;
|
|
1075
|
+
}
|
|
1076
|
+
|
|
1077
|
+
// ../../node_modules/.pnpm/@noble+curves@2.0.1/node_modules/@noble/curves/abstract/curve.js
|
|
1078
|
+
function createKeygen(randomSecretKey, getPublicKey) {
|
|
1079
|
+
return function keygen(seed) {
|
|
1080
|
+
const secretKey = randomSecretKey(seed);
|
|
1081
|
+
return { secretKey, publicKey: getPublicKey(secretKey) };
|
|
1082
|
+
};
|
|
1083
|
+
}
|
|
1084
|
+
|
|
1085
|
+
// ../../node_modules/.pnpm/@noble+curves@2.0.1/node_modules/@noble/curves/abstract/montgomery.js
|
|
1086
|
+
var _0n3 = BigInt(0);
|
|
1087
|
+
var _1n = BigInt(1);
|
|
1088
|
+
var _2n = BigInt(2);
|
|
1089
|
+
function validateOpts(curve) {
|
|
1090
|
+
validateObject(curve, {
|
|
1091
|
+
adjustScalarBytes: "function",
|
|
1092
|
+
powPminus2: "function"
|
|
1093
|
+
});
|
|
1094
|
+
return Object.freeze({ ...curve });
|
|
1095
|
+
}
|
|
1096
|
+
function montgomery(curveDef) {
|
|
1097
|
+
const CURVE = validateOpts(curveDef);
|
|
1098
|
+
const { P: P2, type, adjustScalarBytes: adjustScalarBytes2, powPminus2, randomBytes: rand } = CURVE;
|
|
1099
|
+
const is25519 = type === "x25519";
|
|
1100
|
+
if (!is25519 && type !== "x448")
|
|
1101
|
+
throw new Error("invalid type");
|
|
1102
|
+
const randomBytes_ = rand || randomBytes;
|
|
1103
|
+
const montgomeryBits = is25519 ? 255 : 448;
|
|
1104
|
+
const fieldLen = is25519 ? 32 : 56;
|
|
1105
|
+
const Gu = is25519 ? BigInt(9) : BigInt(5);
|
|
1106
|
+
const a24 = is25519 ? BigInt(121665) : BigInt(39081);
|
|
1107
|
+
const minScalar = is25519 ? _2n ** BigInt(254) : _2n ** BigInt(447);
|
|
1108
|
+
const maxAdded = is25519 ? BigInt(8) * _2n ** BigInt(251) - _1n : BigInt(4) * _2n ** BigInt(445) - _1n;
|
|
1109
|
+
const maxScalar = minScalar + maxAdded + _1n;
|
|
1110
|
+
const modP = (n) => mod(n, P2);
|
|
1111
|
+
const GuBytes = encodeU(Gu);
|
|
1112
|
+
function encodeU(u) {
|
|
1113
|
+
return numberToBytesLE(modP(u), fieldLen);
|
|
1114
|
+
}
|
|
1115
|
+
function decodeU(u) {
|
|
1116
|
+
const _u = copyBytes(abytes(u, fieldLen, "uCoordinate"));
|
|
1117
|
+
if (is25519)
|
|
1118
|
+
_u[31] &= 127;
|
|
1119
|
+
return modP(bytesToNumberLE(_u));
|
|
1120
|
+
}
|
|
1121
|
+
function decodeScalar(scalar) {
|
|
1122
|
+
return bytesToNumberLE(adjustScalarBytes2(copyBytes(abytes(scalar, fieldLen, "scalar"))));
|
|
1123
|
+
}
|
|
1124
|
+
function scalarMult(scalar, u) {
|
|
1125
|
+
const pu = montgomeryLadder(decodeU(u), decodeScalar(scalar));
|
|
1126
|
+
if (pu === _0n3)
|
|
1127
|
+
throw new Error("invalid private or public key received");
|
|
1128
|
+
return encodeU(pu);
|
|
1129
|
+
}
|
|
1130
|
+
function scalarMultBase(scalar) {
|
|
1131
|
+
return scalarMult(scalar, GuBytes);
|
|
1132
|
+
}
|
|
1133
|
+
const getPublicKey = scalarMultBase;
|
|
1134
|
+
const getSharedSecret = scalarMult;
|
|
1135
|
+
function cswap(swap, x_2, x_3) {
|
|
1136
|
+
const dummy = modP(swap * (x_2 - x_3));
|
|
1137
|
+
x_2 = modP(x_2 - dummy);
|
|
1138
|
+
x_3 = modP(x_3 + dummy);
|
|
1139
|
+
return { x_2, x_3 };
|
|
1140
|
+
}
|
|
1141
|
+
function montgomeryLadder(u, scalar) {
|
|
1142
|
+
aInRange("u", u, _0n3, P2);
|
|
1143
|
+
aInRange("scalar", scalar, minScalar, maxScalar);
|
|
1144
|
+
const k = scalar;
|
|
1145
|
+
const x_1 = u;
|
|
1146
|
+
let x_2 = _1n;
|
|
1147
|
+
let z_2 = _0n3;
|
|
1148
|
+
let x_3 = u;
|
|
1149
|
+
let z_3 = _1n;
|
|
1150
|
+
let swap = _0n3;
|
|
1151
|
+
for (let t = BigInt(montgomeryBits - 1); t >= _0n3; t--) {
|
|
1152
|
+
const k_t = k >> t & _1n;
|
|
1153
|
+
swap ^= k_t;
|
|
1154
|
+
({ x_2, x_3 } = cswap(swap, x_2, x_3));
|
|
1155
|
+
({ x_2: z_2, x_3: z_3 } = cswap(swap, z_2, z_3));
|
|
1156
|
+
swap = k_t;
|
|
1157
|
+
const A = x_2 + z_2;
|
|
1158
|
+
const AA = modP(A * A);
|
|
1159
|
+
const B = x_2 - z_2;
|
|
1160
|
+
const BB = modP(B * B);
|
|
1161
|
+
const E = AA - BB;
|
|
1162
|
+
const C = x_3 + z_3;
|
|
1163
|
+
const D = x_3 - z_3;
|
|
1164
|
+
const DA = modP(D * A);
|
|
1165
|
+
const CB = modP(C * B);
|
|
1166
|
+
const dacb = DA + CB;
|
|
1167
|
+
const da_cb = DA - CB;
|
|
1168
|
+
x_3 = modP(dacb * dacb);
|
|
1169
|
+
z_3 = modP(x_1 * modP(da_cb * da_cb));
|
|
1170
|
+
x_2 = modP(AA * BB);
|
|
1171
|
+
z_2 = modP(E * (AA + modP(a24 * E)));
|
|
1172
|
+
}
|
|
1173
|
+
({ x_2, x_3 } = cswap(swap, x_2, x_3));
|
|
1174
|
+
({ x_2: z_2, x_3: z_3 } = cswap(swap, z_2, z_3));
|
|
1175
|
+
const z2 = powPminus2(z_2);
|
|
1176
|
+
return modP(x_2 * z2);
|
|
1177
|
+
}
|
|
1178
|
+
const lengths = {
|
|
1179
|
+
secretKey: fieldLen,
|
|
1180
|
+
publicKey: fieldLen,
|
|
1181
|
+
seed: fieldLen
|
|
1182
|
+
};
|
|
1183
|
+
const randomSecretKey = (seed = randomBytes_(fieldLen)) => {
|
|
1184
|
+
abytes(seed, lengths.seed, "seed");
|
|
1185
|
+
return seed;
|
|
1186
|
+
};
|
|
1187
|
+
const utils = { randomSecretKey };
|
|
1188
|
+
return Object.freeze({
|
|
1189
|
+
keygen: createKeygen(randomSecretKey, getPublicKey),
|
|
1190
|
+
getSharedSecret,
|
|
1191
|
+
getPublicKey,
|
|
1192
|
+
scalarMult,
|
|
1193
|
+
scalarMultBase,
|
|
1194
|
+
utils,
|
|
1195
|
+
GuBytes: GuBytes.slice(),
|
|
1196
|
+
lengths
|
|
1197
|
+
});
|
|
1198
|
+
}
|
|
1199
|
+
|
|
1200
|
+
// ../../node_modules/.pnpm/@noble+curves@2.0.1/node_modules/@noble/curves/ed25519.js
|
|
1201
|
+
var _1n2 = BigInt(1);
|
|
1202
|
+
var _2n2 = BigInt(2);
|
|
1203
|
+
var _3n = /* @__PURE__ */ BigInt(3);
|
|
1204
|
+
var _5n = BigInt(5);
|
|
1205
|
+
var _8n = BigInt(8);
|
|
1206
|
+
var ed25519_CURVE_p = BigInt("0x7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffed");
|
|
1207
|
+
function ed25519_pow_2_252_3(x) {
|
|
1208
|
+
const _10n = BigInt(10), _20n = BigInt(20), _40n = BigInt(40), _80n = BigInt(80);
|
|
1209
|
+
const P2 = ed25519_CURVE_p;
|
|
1210
|
+
const x2 = x * x % P2;
|
|
1211
|
+
const b2 = x2 * x % P2;
|
|
1212
|
+
const b4 = pow2(b2, _2n2, P2) * b2 % P2;
|
|
1213
|
+
const b5 = pow2(b4, _1n2, P2) * x % P2;
|
|
1214
|
+
const b10 = pow2(b5, _5n, P2) * b5 % P2;
|
|
1215
|
+
const b20 = pow2(b10, _10n, P2) * b10 % P2;
|
|
1216
|
+
const b40 = pow2(b20, _20n, P2) * b20 % P2;
|
|
1217
|
+
const b80 = pow2(b40, _40n, P2) * b40 % P2;
|
|
1218
|
+
const b160 = pow2(b80, _80n, P2) * b80 % P2;
|
|
1219
|
+
const b240 = pow2(b160, _80n, P2) * b80 % P2;
|
|
1220
|
+
const b250 = pow2(b240, _10n, P2) * b10 % P2;
|
|
1221
|
+
const pow_p_5_8 = pow2(b250, _2n2, P2) * x % P2;
|
|
1222
|
+
return { pow_p_5_8, b2 };
|
|
1223
|
+
}
|
|
1224
|
+
function adjustScalarBytes(bytes) {
|
|
1225
|
+
bytes[0] &= 248;
|
|
1226
|
+
bytes[31] &= 127;
|
|
1227
|
+
bytes[31] |= 64;
|
|
1228
|
+
return bytes;
|
|
1229
|
+
}
|
|
1230
|
+
var x25519 = /* @__PURE__ */ (() => {
|
|
1231
|
+
const P2 = ed25519_CURVE_p;
|
|
1232
|
+
return montgomery({
|
|
1233
|
+
P: P2,
|
|
1234
|
+
type: "x25519",
|
|
1235
|
+
powPminus2: (x) => {
|
|
1236
|
+
const { pow_p_5_8, b2 } = ed25519_pow_2_252_3(x);
|
|
1237
|
+
return mod(pow2(pow_p_5_8, _3n, P2) * b2, P2);
|
|
1238
|
+
},
|
|
1239
|
+
adjustScalarBytes
|
|
1240
|
+
});
|
|
1241
|
+
})();
|
|
1242
|
+
|
|
1243
|
+
// ../../node_modules/.pnpm/@noble+ciphers@2.1.1/node_modules/@noble/ciphers/utils.js
|
|
1244
|
+
function isBytes2(a) {
|
|
1245
|
+
return a instanceof Uint8Array || ArrayBuffer.isView(a) && a.constructor.name === "Uint8Array";
|
|
1246
|
+
}
|
|
1247
|
+
function abool(b) {
|
|
1248
|
+
if (typeof b !== "boolean")
|
|
1249
|
+
throw new Error(`boolean expected, not ${b}`);
|
|
1250
|
+
}
|
|
1251
|
+
function anumber2(n) {
|
|
1252
|
+
if (!Number.isSafeInteger(n) || n < 0)
|
|
1253
|
+
throw new Error("positive integer expected, got " + n);
|
|
1254
|
+
}
|
|
1255
|
+
function abytes2(value, length, title = "") {
|
|
1256
|
+
const bytes = isBytes2(value);
|
|
1257
|
+
const len = value?.length;
|
|
1258
|
+
const needsLen = length !== void 0;
|
|
1259
|
+
if (!bytes || needsLen && len !== length) {
|
|
1260
|
+
const prefix = title && `"${title}" `;
|
|
1261
|
+
const ofLen = needsLen ? ` of length ${length}` : "";
|
|
1262
|
+
const got = bytes ? `length=${len}` : `type=${typeof value}`;
|
|
1263
|
+
throw new Error(prefix + "expected Uint8Array" + ofLen + ", got " + got);
|
|
1264
|
+
}
|
|
1265
|
+
return value;
|
|
1266
|
+
}
|
|
1267
|
+
function aexists2(instance, checkFinished = true) {
|
|
1268
|
+
if (instance.destroyed)
|
|
1269
|
+
throw new Error("Hash instance has been destroyed");
|
|
1270
|
+
if (checkFinished && instance.finished)
|
|
1271
|
+
throw new Error("Hash#digest() has already been called");
|
|
1272
|
+
}
|
|
1273
|
+
function aoutput2(out, instance) {
|
|
1274
|
+
abytes2(out, void 0, "output");
|
|
1275
|
+
const min = instance.outputLen;
|
|
1276
|
+
if (out.length < min) {
|
|
1277
|
+
throw new Error("digestInto() expects output buffer of length at least " + min);
|
|
1278
|
+
}
|
|
1279
|
+
}
|
|
1280
|
+
function u322(arr) {
|
|
1281
|
+
return new Uint32Array(arr.buffer, arr.byteOffset, Math.floor(arr.byteLength / 4));
|
|
1282
|
+
}
|
|
1283
|
+
function clean2(...arrays) {
|
|
1284
|
+
for (let i = 0; i < arrays.length; i++) {
|
|
1285
|
+
arrays[i].fill(0);
|
|
1286
|
+
}
|
|
1287
|
+
}
|
|
1288
|
+
function createView(arr) {
|
|
1289
|
+
return new DataView(arr.buffer, arr.byteOffset, arr.byteLength);
|
|
1290
|
+
}
|
|
1291
|
+
var isLE2 = /* @__PURE__ */ (() => new Uint8Array(new Uint32Array([287454020]).buffer)[0] === 68)();
|
|
1292
|
+
function checkOpts(defaults, opts) {
|
|
1293
|
+
if (opts == null || typeof opts !== "object")
|
|
1294
|
+
throw new Error("options must be defined");
|
|
1295
|
+
const merged = Object.assign(defaults, opts);
|
|
1296
|
+
return merged;
|
|
1297
|
+
}
|
|
1298
|
+
function equalBytes(a, b) {
|
|
1299
|
+
if (a.length !== b.length)
|
|
1300
|
+
return false;
|
|
1301
|
+
let diff = 0;
|
|
1302
|
+
for (let i = 0; i < a.length; i++)
|
|
1303
|
+
diff |= a[i] ^ b[i];
|
|
1304
|
+
return diff === 0;
|
|
1305
|
+
}
|
|
1306
|
+
var wrapCipher = /* @__NO_SIDE_EFFECTS__ */ (params, constructor) => {
|
|
1307
|
+
function wrappedCipher(key, ...args) {
|
|
1308
|
+
abytes2(key, void 0, "key");
|
|
1309
|
+
if (!isLE2)
|
|
1310
|
+
throw new Error("Non little-endian hardware is not yet supported");
|
|
1311
|
+
if (params.nonceLength !== void 0) {
|
|
1312
|
+
const nonce = args[0];
|
|
1313
|
+
abytes2(nonce, params.varSizeNonce ? void 0 : params.nonceLength, "nonce");
|
|
1314
|
+
}
|
|
1315
|
+
const tagl = params.tagLength;
|
|
1316
|
+
if (tagl && args[1] !== void 0)
|
|
1317
|
+
abytes2(args[1], void 0, "AAD");
|
|
1318
|
+
const cipher = constructor(key, ...args);
|
|
1319
|
+
const checkOutput = (fnLength, output) => {
|
|
1320
|
+
if (output !== void 0) {
|
|
1321
|
+
if (fnLength !== 2)
|
|
1322
|
+
throw new Error("cipher output not supported");
|
|
1323
|
+
abytes2(output, void 0, "output");
|
|
1324
|
+
}
|
|
1325
|
+
};
|
|
1326
|
+
let called = false;
|
|
1327
|
+
const wrCipher = {
|
|
1328
|
+
encrypt(data, output) {
|
|
1329
|
+
if (called)
|
|
1330
|
+
throw new Error("cannot encrypt() twice with same key + nonce");
|
|
1331
|
+
called = true;
|
|
1332
|
+
abytes2(data);
|
|
1333
|
+
checkOutput(cipher.encrypt.length, output);
|
|
1334
|
+
return cipher.encrypt(data, output);
|
|
1335
|
+
},
|
|
1336
|
+
decrypt(data, output) {
|
|
1337
|
+
abytes2(data);
|
|
1338
|
+
if (tagl && data.length < tagl)
|
|
1339
|
+
throw new Error('"ciphertext" expected length bigger than tagLength=' + tagl);
|
|
1340
|
+
checkOutput(cipher.decrypt.length, output);
|
|
1341
|
+
return cipher.decrypt(data, output);
|
|
1342
|
+
}
|
|
1343
|
+
};
|
|
1344
|
+
return wrCipher;
|
|
1345
|
+
}
|
|
1346
|
+
Object.assign(wrappedCipher, params);
|
|
1347
|
+
return wrappedCipher;
|
|
1348
|
+
};
|
|
1349
|
+
function getOutput(expectedLength, out, onlyAligned = true) {
|
|
1350
|
+
if (out === void 0)
|
|
1351
|
+
return new Uint8Array(expectedLength);
|
|
1352
|
+
if (out.length !== expectedLength)
|
|
1353
|
+
throw new Error('"output" expected Uint8Array of length ' + expectedLength + ", got: " + out.length);
|
|
1354
|
+
if (onlyAligned && !isAligned32(out))
|
|
1355
|
+
throw new Error("invalid output, must be aligned");
|
|
1356
|
+
return out;
|
|
1357
|
+
}
|
|
1358
|
+
function u64Lengths(dataLength, aadLength, isLE3) {
|
|
1359
|
+
abool(isLE3);
|
|
1360
|
+
const num = new Uint8Array(16);
|
|
1361
|
+
const view = createView(num);
|
|
1362
|
+
view.setBigUint64(0, BigInt(aadLength), isLE3);
|
|
1363
|
+
view.setBigUint64(8, BigInt(dataLength), isLE3);
|
|
1364
|
+
return num;
|
|
1365
|
+
}
|
|
1366
|
+
function isAligned32(bytes) {
|
|
1367
|
+
return bytes.byteOffset % 4 === 0;
|
|
1368
|
+
}
|
|
1369
|
+
function copyBytes2(bytes) {
|
|
1370
|
+
return Uint8Array.from(bytes);
|
|
1371
|
+
}
|
|
1372
|
+
function randomBytes2(bytesLength = 32) {
|
|
1373
|
+
const cr = typeof globalThis === "object" ? globalThis.crypto : null;
|
|
1374
|
+
if (typeof cr?.getRandomValues !== "function")
|
|
1375
|
+
throw new Error("crypto.getRandomValues must be defined");
|
|
1376
|
+
return cr.getRandomValues(new Uint8Array(bytesLength));
|
|
1377
|
+
}
|
|
1378
|
+
|
|
1379
|
+
// ../../node_modules/.pnpm/@noble+ciphers@2.1.1/node_modules/@noble/ciphers/_arx.js
|
|
1380
|
+
var encodeStr = (str) => Uint8Array.from(str.split(""), (c) => c.charCodeAt(0));
|
|
1381
|
+
var sigma16 = encodeStr("expand 16-byte k");
|
|
1382
|
+
var sigma32 = encodeStr("expand 32-byte k");
|
|
1383
|
+
var sigma16_32 = u322(sigma16);
|
|
1384
|
+
var sigma32_32 = u322(sigma32);
|
|
1385
|
+
function rotl(a, b) {
|
|
1386
|
+
return a << b | a >>> 32 - b;
|
|
1387
|
+
}
|
|
1388
|
+
function isAligned322(b) {
|
|
1389
|
+
return b.byteOffset % 4 === 0;
|
|
1390
|
+
}
|
|
1391
|
+
var BLOCK_LEN = 64;
|
|
1392
|
+
var BLOCK_LEN32 = 16;
|
|
1393
|
+
var MAX_COUNTER = 2 ** 32 - 1;
|
|
1394
|
+
var U32_EMPTY = Uint32Array.of();
|
|
1395
|
+
function runCipher(core, sigma, key, nonce, data, output, counter, rounds) {
|
|
1396
|
+
const len = data.length;
|
|
1397
|
+
const block2 = new Uint8Array(BLOCK_LEN);
|
|
1398
|
+
const b32 = u322(block2);
|
|
1399
|
+
const isAligned = isAligned322(data) && isAligned322(output);
|
|
1400
|
+
const d32 = isAligned ? u322(data) : U32_EMPTY;
|
|
1401
|
+
const o32 = isAligned ? u322(output) : U32_EMPTY;
|
|
1402
|
+
for (let pos = 0; pos < len; counter++) {
|
|
1403
|
+
core(sigma, key, nonce, b32, counter, rounds);
|
|
1404
|
+
if (counter >= MAX_COUNTER)
|
|
1405
|
+
throw new Error("arx: counter overflow");
|
|
1406
|
+
const take = Math.min(BLOCK_LEN, len - pos);
|
|
1407
|
+
if (isAligned && take === BLOCK_LEN) {
|
|
1408
|
+
const pos32 = pos / 4;
|
|
1409
|
+
if (pos % 4 !== 0)
|
|
1410
|
+
throw new Error("arx: invalid block position");
|
|
1411
|
+
for (let j = 0, posj; j < BLOCK_LEN32; j++) {
|
|
1412
|
+
posj = pos32 + j;
|
|
1413
|
+
o32[posj] = d32[posj] ^ b32[j];
|
|
1414
|
+
}
|
|
1415
|
+
pos += BLOCK_LEN;
|
|
1416
|
+
continue;
|
|
1417
|
+
}
|
|
1418
|
+
for (let j = 0, posj; j < take; j++) {
|
|
1419
|
+
posj = pos + j;
|
|
1420
|
+
output[posj] = data[posj] ^ block2[j];
|
|
1421
|
+
}
|
|
1422
|
+
pos += take;
|
|
1423
|
+
}
|
|
1424
|
+
}
|
|
1425
|
+
function createCipher(core, opts) {
|
|
1426
|
+
const { allowShortKeys, extendNonceFn, counterLength, counterRight, rounds } = checkOpts({ allowShortKeys: false, counterLength: 8, counterRight: false, rounds: 20 }, opts);
|
|
1427
|
+
if (typeof core !== "function")
|
|
1428
|
+
throw new Error("core must be a function");
|
|
1429
|
+
anumber2(counterLength);
|
|
1430
|
+
anumber2(rounds);
|
|
1431
|
+
abool(counterRight);
|
|
1432
|
+
abool(allowShortKeys);
|
|
1433
|
+
return (key, nonce, data, output, counter = 0) => {
|
|
1434
|
+
abytes2(key, void 0, "key");
|
|
1435
|
+
abytes2(nonce, void 0, "nonce");
|
|
1436
|
+
abytes2(data, void 0, "data");
|
|
1437
|
+
const len = data.length;
|
|
1438
|
+
if (output === void 0)
|
|
1439
|
+
output = new Uint8Array(len);
|
|
1440
|
+
abytes2(output, void 0, "output");
|
|
1441
|
+
anumber2(counter);
|
|
1442
|
+
if (counter < 0 || counter >= MAX_COUNTER)
|
|
1443
|
+
throw new Error("arx: counter overflow");
|
|
1444
|
+
if (output.length < len)
|
|
1445
|
+
throw new Error(`arx: output (${output.length}) is shorter than data (${len})`);
|
|
1446
|
+
const toClean = [];
|
|
1447
|
+
let l = key.length;
|
|
1448
|
+
let k;
|
|
1449
|
+
let sigma;
|
|
1450
|
+
if (l === 32) {
|
|
1451
|
+
toClean.push(k = copyBytes2(key));
|
|
1452
|
+
sigma = sigma32_32;
|
|
1453
|
+
} else if (l === 16 && allowShortKeys) {
|
|
1454
|
+
k = new Uint8Array(32);
|
|
1455
|
+
k.set(key);
|
|
1456
|
+
k.set(key, 16);
|
|
1457
|
+
sigma = sigma16_32;
|
|
1458
|
+
toClean.push(k);
|
|
1459
|
+
} else {
|
|
1460
|
+
abytes2(key, 32, "arx key");
|
|
1461
|
+
throw new Error("invalid key size");
|
|
1462
|
+
}
|
|
1463
|
+
if (!isAligned322(nonce))
|
|
1464
|
+
toClean.push(nonce = copyBytes2(nonce));
|
|
1465
|
+
const k32 = u322(k);
|
|
1466
|
+
if (extendNonceFn) {
|
|
1467
|
+
if (nonce.length !== 24)
|
|
1468
|
+
throw new Error(`arx: extended nonce must be 24 bytes`);
|
|
1469
|
+
extendNonceFn(sigma, k32, u322(nonce.subarray(0, 16)), k32);
|
|
1470
|
+
nonce = nonce.subarray(16);
|
|
1471
|
+
}
|
|
1472
|
+
const nonceNcLen = 16 - counterLength;
|
|
1473
|
+
if (nonceNcLen !== nonce.length)
|
|
1474
|
+
throw new Error(`arx: nonce must be ${nonceNcLen} or 16 bytes`);
|
|
1475
|
+
if (nonceNcLen !== 12) {
|
|
1476
|
+
const nc = new Uint8Array(12);
|
|
1477
|
+
nc.set(nonce, counterRight ? 0 : 12 - nonce.length);
|
|
1478
|
+
nonce = nc;
|
|
1479
|
+
toClean.push(nonce);
|
|
1480
|
+
}
|
|
1481
|
+
const n32 = u322(nonce);
|
|
1482
|
+
runCipher(core, sigma, k32, n32, data, output, counter, rounds);
|
|
1483
|
+
clean2(...toClean);
|
|
1484
|
+
return output;
|
|
1485
|
+
};
|
|
1486
|
+
}
|
|
1487
|
+
|
|
1488
|
+
// ../../node_modules/.pnpm/@noble+ciphers@2.1.1/node_modules/@noble/ciphers/_poly1305.js
|
|
1489
|
+
function u8to16(a, i) {
|
|
1490
|
+
return a[i++] & 255 | (a[i++] & 255) << 8;
|
|
1491
|
+
}
|
|
1492
|
+
var Poly1305 = class {
|
|
1493
|
+
blockLen = 16;
|
|
1494
|
+
outputLen = 16;
|
|
1495
|
+
buffer = new Uint8Array(16);
|
|
1496
|
+
r = new Uint16Array(10);
|
|
1497
|
+
// Allocating 1 array with .subarray() here is slower than 3
|
|
1498
|
+
h = new Uint16Array(10);
|
|
1499
|
+
pad = new Uint16Array(8);
|
|
1500
|
+
pos = 0;
|
|
1501
|
+
finished = false;
|
|
1502
|
+
// Can be speed-up using BigUint64Array, at the cost of complexity
|
|
1503
|
+
constructor(key) {
|
|
1504
|
+
key = copyBytes2(abytes2(key, 32, "key"));
|
|
1505
|
+
const t0 = u8to16(key, 0);
|
|
1506
|
+
const t1 = u8to16(key, 2);
|
|
1507
|
+
const t2 = u8to16(key, 4);
|
|
1508
|
+
const t3 = u8to16(key, 6);
|
|
1509
|
+
const t4 = u8to16(key, 8);
|
|
1510
|
+
const t5 = u8to16(key, 10);
|
|
1511
|
+
const t6 = u8to16(key, 12);
|
|
1512
|
+
const t7 = u8to16(key, 14);
|
|
1513
|
+
this.r[0] = t0 & 8191;
|
|
1514
|
+
this.r[1] = (t0 >>> 13 | t1 << 3) & 8191;
|
|
1515
|
+
this.r[2] = (t1 >>> 10 | t2 << 6) & 7939;
|
|
1516
|
+
this.r[3] = (t2 >>> 7 | t3 << 9) & 8191;
|
|
1517
|
+
this.r[4] = (t3 >>> 4 | t4 << 12) & 255;
|
|
1518
|
+
this.r[5] = t4 >>> 1 & 8190;
|
|
1519
|
+
this.r[6] = (t4 >>> 14 | t5 << 2) & 8191;
|
|
1520
|
+
this.r[7] = (t5 >>> 11 | t6 << 5) & 8065;
|
|
1521
|
+
this.r[8] = (t6 >>> 8 | t7 << 8) & 8191;
|
|
1522
|
+
this.r[9] = t7 >>> 5 & 127;
|
|
1523
|
+
for (let i = 0; i < 8; i++)
|
|
1524
|
+
this.pad[i] = u8to16(key, 16 + 2 * i);
|
|
1525
|
+
}
|
|
1526
|
+
process(data, offset, isLast = false) {
|
|
1527
|
+
const hibit = isLast ? 0 : 1 << 11;
|
|
1528
|
+
const { h, r } = this;
|
|
1529
|
+
const r0 = r[0];
|
|
1530
|
+
const r1 = r[1];
|
|
1531
|
+
const r2 = r[2];
|
|
1532
|
+
const r3 = r[3];
|
|
1533
|
+
const r4 = r[4];
|
|
1534
|
+
const r5 = r[5];
|
|
1535
|
+
const r6 = r[6];
|
|
1536
|
+
const r7 = r[7];
|
|
1537
|
+
const r8 = r[8];
|
|
1538
|
+
const r9 = r[9];
|
|
1539
|
+
const t0 = u8to16(data, offset + 0);
|
|
1540
|
+
const t1 = u8to16(data, offset + 2);
|
|
1541
|
+
const t2 = u8to16(data, offset + 4);
|
|
1542
|
+
const t3 = u8to16(data, offset + 6);
|
|
1543
|
+
const t4 = u8to16(data, offset + 8);
|
|
1544
|
+
const t5 = u8to16(data, offset + 10);
|
|
1545
|
+
const t6 = u8to16(data, offset + 12);
|
|
1546
|
+
const t7 = u8to16(data, offset + 14);
|
|
1547
|
+
let h0 = h[0] + (t0 & 8191);
|
|
1548
|
+
let h1 = h[1] + ((t0 >>> 13 | t1 << 3) & 8191);
|
|
1549
|
+
let h2 = h[2] + ((t1 >>> 10 | t2 << 6) & 8191);
|
|
1550
|
+
let h3 = h[3] + ((t2 >>> 7 | t3 << 9) & 8191);
|
|
1551
|
+
let h4 = h[4] + ((t3 >>> 4 | t4 << 12) & 8191);
|
|
1552
|
+
let h5 = h[5] + (t4 >>> 1 & 8191);
|
|
1553
|
+
let h6 = h[6] + ((t4 >>> 14 | t5 << 2) & 8191);
|
|
1554
|
+
let h7 = h[7] + ((t5 >>> 11 | t6 << 5) & 8191);
|
|
1555
|
+
let h8 = h[8] + ((t6 >>> 8 | t7 << 8) & 8191);
|
|
1556
|
+
let h9 = h[9] + (t7 >>> 5 | hibit);
|
|
1557
|
+
let c = 0;
|
|
1558
|
+
let d0 = c + h0 * r0 + h1 * (5 * r9) + h2 * (5 * r8) + h3 * (5 * r7) + h4 * (5 * r6);
|
|
1559
|
+
c = d0 >>> 13;
|
|
1560
|
+
d0 &= 8191;
|
|
1561
|
+
d0 += h5 * (5 * r5) + h6 * (5 * r4) + h7 * (5 * r3) + h8 * (5 * r2) + h9 * (5 * r1);
|
|
1562
|
+
c += d0 >>> 13;
|
|
1563
|
+
d0 &= 8191;
|
|
1564
|
+
let d1 = c + h0 * r1 + h1 * r0 + h2 * (5 * r9) + h3 * (5 * r8) + h4 * (5 * r7);
|
|
1565
|
+
c = d1 >>> 13;
|
|
1566
|
+
d1 &= 8191;
|
|
1567
|
+
d1 += h5 * (5 * r6) + h6 * (5 * r5) + h7 * (5 * r4) + h8 * (5 * r3) + h9 * (5 * r2);
|
|
1568
|
+
c += d1 >>> 13;
|
|
1569
|
+
d1 &= 8191;
|
|
1570
|
+
let d2 = c + h0 * r2 + h1 * r1 + h2 * r0 + h3 * (5 * r9) + h4 * (5 * r8);
|
|
1571
|
+
c = d2 >>> 13;
|
|
1572
|
+
d2 &= 8191;
|
|
1573
|
+
d2 += h5 * (5 * r7) + h6 * (5 * r6) + h7 * (5 * r5) + h8 * (5 * r4) + h9 * (5 * r3);
|
|
1574
|
+
c += d2 >>> 13;
|
|
1575
|
+
d2 &= 8191;
|
|
1576
|
+
let d3 = c + h0 * r3 + h1 * r2 + h2 * r1 + h3 * r0 + h4 * (5 * r9);
|
|
1577
|
+
c = d3 >>> 13;
|
|
1578
|
+
d3 &= 8191;
|
|
1579
|
+
d3 += h5 * (5 * r8) + h6 * (5 * r7) + h7 * (5 * r6) + h8 * (5 * r5) + h9 * (5 * r4);
|
|
1580
|
+
c += d3 >>> 13;
|
|
1581
|
+
d3 &= 8191;
|
|
1582
|
+
let d4 = c + h0 * r4 + h1 * r3 + h2 * r2 + h3 * r1 + h4 * r0;
|
|
1583
|
+
c = d4 >>> 13;
|
|
1584
|
+
d4 &= 8191;
|
|
1585
|
+
d4 += h5 * (5 * r9) + h6 * (5 * r8) + h7 * (5 * r7) + h8 * (5 * r6) + h9 * (5 * r5);
|
|
1586
|
+
c += d4 >>> 13;
|
|
1587
|
+
d4 &= 8191;
|
|
1588
|
+
let d5 = c + h0 * r5 + h1 * r4 + h2 * r3 + h3 * r2 + h4 * r1;
|
|
1589
|
+
c = d5 >>> 13;
|
|
1590
|
+
d5 &= 8191;
|
|
1591
|
+
d5 += h5 * r0 + h6 * (5 * r9) + h7 * (5 * r8) + h8 * (5 * r7) + h9 * (5 * r6);
|
|
1592
|
+
c += d5 >>> 13;
|
|
1593
|
+
d5 &= 8191;
|
|
1594
|
+
let d6 = c + h0 * r6 + h1 * r5 + h2 * r4 + h3 * r3 + h4 * r2;
|
|
1595
|
+
c = d6 >>> 13;
|
|
1596
|
+
d6 &= 8191;
|
|
1597
|
+
d6 += h5 * r1 + h6 * r0 + h7 * (5 * r9) + h8 * (5 * r8) + h9 * (5 * r7);
|
|
1598
|
+
c += d6 >>> 13;
|
|
1599
|
+
d6 &= 8191;
|
|
1600
|
+
let d7 = c + h0 * r7 + h1 * r6 + h2 * r5 + h3 * r4 + h4 * r3;
|
|
1601
|
+
c = d7 >>> 13;
|
|
1602
|
+
d7 &= 8191;
|
|
1603
|
+
d7 += h5 * r2 + h6 * r1 + h7 * r0 + h8 * (5 * r9) + h9 * (5 * r8);
|
|
1604
|
+
c += d7 >>> 13;
|
|
1605
|
+
d7 &= 8191;
|
|
1606
|
+
let d8 = c + h0 * r8 + h1 * r7 + h2 * r6 + h3 * r5 + h4 * r4;
|
|
1607
|
+
c = d8 >>> 13;
|
|
1608
|
+
d8 &= 8191;
|
|
1609
|
+
d8 += h5 * r3 + h6 * r2 + h7 * r1 + h8 * r0 + h9 * (5 * r9);
|
|
1610
|
+
c += d8 >>> 13;
|
|
1611
|
+
d8 &= 8191;
|
|
1612
|
+
let d9 = c + h0 * r9 + h1 * r8 + h2 * r7 + h3 * r6 + h4 * r5;
|
|
1613
|
+
c = d9 >>> 13;
|
|
1614
|
+
d9 &= 8191;
|
|
1615
|
+
d9 += h5 * r4 + h6 * r3 + h7 * r2 + h8 * r1 + h9 * r0;
|
|
1616
|
+
c += d9 >>> 13;
|
|
1617
|
+
d9 &= 8191;
|
|
1618
|
+
c = (c << 2) + c | 0;
|
|
1619
|
+
c = c + d0 | 0;
|
|
1620
|
+
d0 = c & 8191;
|
|
1621
|
+
c = c >>> 13;
|
|
1622
|
+
d1 += c;
|
|
1623
|
+
h[0] = d0;
|
|
1624
|
+
h[1] = d1;
|
|
1625
|
+
h[2] = d2;
|
|
1626
|
+
h[3] = d3;
|
|
1627
|
+
h[4] = d4;
|
|
1628
|
+
h[5] = d5;
|
|
1629
|
+
h[6] = d6;
|
|
1630
|
+
h[7] = d7;
|
|
1631
|
+
h[8] = d8;
|
|
1632
|
+
h[9] = d9;
|
|
1633
|
+
}
|
|
1634
|
+
finalize() {
|
|
1635
|
+
const { h, pad } = this;
|
|
1636
|
+
const g = new Uint16Array(10);
|
|
1637
|
+
let c = h[1] >>> 13;
|
|
1638
|
+
h[1] &= 8191;
|
|
1639
|
+
for (let i = 2; i < 10; i++) {
|
|
1640
|
+
h[i] += c;
|
|
1641
|
+
c = h[i] >>> 13;
|
|
1642
|
+
h[i] &= 8191;
|
|
1643
|
+
}
|
|
1644
|
+
h[0] += c * 5;
|
|
1645
|
+
c = h[0] >>> 13;
|
|
1646
|
+
h[0] &= 8191;
|
|
1647
|
+
h[1] += c;
|
|
1648
|
+
c = h[1] >>> 13;
|
|
1649
|
+
h[1] &= 8191;
|
|
1650
|
+
h[2] += c;
|
|
1651
|
+
g[0] = h[0] + 5;
|
|
1652
|
+
c = g[0] >>> 13;
|
|
1653
|
+
g[0] &= 8191;
|
|
1654
|
+
for (let i = 1; i < 10; i++) {
|
|
1655
|
+
g[i] = h[i] + c;
|
|
1656
|
+
c = g[i] >>> 13;
|
|
1657
|
+
g[i] &= 8191;
|
|
1658
|
+
}
|
|
1659
|
+
g[9] -= 1 << 13;
|
|
1660
|
+
let mask = (c ^ 1) - 1;
|
|
1661
|
+
for (let i = 0; i < 10; i++)
|
|
1662
|
+
g[i] &= mask;
|
|
1663
|
+
mask = ~mask;
|
|
1664
|
+
for (let i = 0; i < 10; i++)
|
|
1665
|
+
h[i] = h[i] & mask | g[i];
|
|
1666
|
+
h[0] = (h[0] | h[1] << 13) & 65535;
|
|
1667
|
+
h[1] = (h[1] >>> 3 | h[2] << 10) & 65535;
|
|
1668
|
+
h[2] = (h[2] >>> 6 | h[3] << 7) & 65535;
|
|
1669
|
+
h[3] = (h[3] >>> 9 | h[4] << 4) & 65535;
|
|
1670
|
+
h[4] = (h[4] >>> 12 | h[5] << 1 | h[6] << 14) & 65535;
|
|
1671
|
+
h[5] = (h[6] >>> 2 | h[7] << 11) & 65535;
|
|
1672
|
+
h[6] = (h[7] >>> 5 | h[8] << 8) & 65535;
|
|
1673
|
+
h[7] = (h[8] >>> 8 | h[9] << 5) & 65535;
|
|
1674
|
+
let f = h[0] + pad[0];
|
|
1675
|
+
h[0] = f & 65535;
|
|
1676
|
+
for (let i = 1; i < 8; i++) {
|
|
1677
|
+
f = (h[i] + pad[i] | 0) + (f >>> 16) | 0;
|
|
1678
|
+
h[i] = f & 65535;
|
|
1679
|
+
}
|
|
1680
|
+
clean2(g);
|
|
1681
|
+
}
|
|
1682
|
+
update(data) {
|
|
1683
|
+
aexists2(this);
|
|
1684
|
+
abytes2(data);
|
|
1685
|
+
data = copyBytes2(data);
|
|
1686
|
+
const { buffer, blockLen } = this;
|
|
1687
|
+
const len = data.length;
|
|
1688
|
+
for (let pos = 0; pos < len; ) {
|
|
1689
|
+
const take = Math.min(blockLen - this.pos, len - pos);
|
|
1690
|
+
if (take === blockLen) {
|
|
1691
|
+
for (; blockLen <= len - pos; pos += blockLen)
|
|
1692
|
+
this.process(data, pos);
|
|
1693
|
+
continue;
|
|
1694
|
+
}
|
|
1695
|
+
buffer.set(data.subarray(pos, pos + take), this.pos);
|
|
1696
|
+
this.pos += take;
|
|
1697
|
+
pos += take;
|
|
1698
|
+
if (this.pos === blockLen) {
|
|
1699
|
+
this.process(buffer, 0, false);
|
|
1700
|
+
this.pos = 0;
|
|
1701
|
+
}
|
|
1702
|
+
}
|
|
1703
|
+
return this;
|
|
1704
|
+
}
|
|
1705
|
+
destroy() {
|
|
1706
|
+
clean2(this.h, this.r, this.buffer, this.pad);
|
|
1707
|
+
}
|
|
1708
|
+
digestInto(out) {
|
|
1709
|
+
aexists2(this);
|
|
1710
|
+
aoutput2(out, this);
|
|
1711
|
+
this.finished = true;
|
|
1712
|
+
const { buffer, h } = this;
|
|
1713
|
+
let { pos } = this;
|
|
1714
|
+
if (pos) {
|
|
1715
|
+
buffer[pos++] = 1;
|
|
1716
|
+
for (; pos < 16; pos++)
|
|
1717
|
+
buffer[pos] = 0;
|
|
1718
|
+
this.process(buffer, 0, true);
|
|
1719
|
+
}
|
|
1720
|
+
this.finalize();
|
|
1721
|
+
let opos = 0;
|
|
1722
|
+
for (let i = 0; i < 8; i++) {
|
|
1723
|
+
out[opos++] = h[i] >>> 0;
|
|
1724
|
+
out[opos++] = h[i] >>> 8;
|
|
1725
|
+
}
|
|
1726
|
+
return out;
|
|
1727
|
+
}
|
|
1728
|
+
digest() {
|
|
1729
|
+
const { buffer, outputLen } = this;
|
|
1730
|
+
this.digestInto(buffer);
|
|
1731
|
+
const res = buffer.slice(0, outputLen);
|
|
1732
|
+
this.destroy();
|
|
1733
|
+
return res;
|
|
1734
|
+
}
|
|
1735
|
+
};
|
|
1736
|
+
function wrapConstructorWithKey(hashCons) {
|
|
1737
|
+
const hashC = (msg, key) => hashCons(key).update(msg).digest();
|
|
1738
|
+
const tmp = hashCons(new Uint8Array(32));
|
|
1739
|
+
hashC.outputLen = tmp.outputLen;
|
|
1740
|
+
hashC.blockLen = tmp.blockLen;
|
|
1741
|
+
hashC.create = (key) => hashCons(key);
|
|
1742
|
+
return hashC;
|
|
1743
|
+
}
|
|
1744
|
+
var poly1305 = /* @__PURE__ */ (() => wrapConstructorWithKey((key) => new Poly1305(key)))();
|
|
1745
|
+
|
|
1746
|
+
// ../../node_modules/.pnpm/@noble+ciphers@2.1.1/node_modules/@noble/ciphers/chacha.js
|
|
1747
|
+
function chachaCore(s, k, n, out, cnt, rounds = 20) {
|
|
1748
|
+
let y00 = s[0], y01 = s[1], y02 = s[2], y03 = s[3], y04 = k[0], y05 = k[1], y06 = k[2], y07 = k[3], y08 = k[4], y09 = k[5], y10 = k[6], y11 = k[7], y12 = cnt, y13 = n[0], y14 = n[1], y15 = n[2];
|
|
1749
|
+
let x00 = y00, x01 = y01, x02 = y02, x03 = y03, x04 = y04, x05 = y05, x06 = y06, x07 = y07, x08 = y08, x09 = y09, x10 = y10, x11 = y11, x12 = y12, x13 = y13, x14 = y14, x15 = y15;
|
|
1750
|
+
for (let r = 0; r < rounds; r += 2) {
|
|
1751
|
+
x00 = x00 + x04 | 0;
|
|
1752
|
+
x12 = rotl(x12 ^ x00, 16);
|
|
1753
|
+
x08 = x08 + x12 | 0;
|
|
1754
|
+
x04 = rotl(x04 ^ x08, 12);
|
|
1755
|
+
x00 = x00 + x04 | 0;
|
|
1756
|
+
x12 = rotl(x12 ^ x00, 8);
|
|
1757
|
+
x08 = x08 + x12 | 0;
|
|
1758
|
+
x04 = rotl(x04 ^ x08, 7);
|
|
1759
|
+
x01 = x01 + x05 | 0;
|
|
1760
|
+
x13 = rotl(x13 ^ x01, 16);
|
|
1761
|
+
x09 = x09 + x13 | 0;
|
|
1762
|
+
x05 = rotl(x05 ^ x09, 12);
|
|
1763
|
+
x01 = x01 + x05 | 0;
|
|
1764
|
+
x13 = rotl(x13 ^ x01, 8);
|
|
1765
|
+
x09 = x09 + x13 | 0;
|
|
1766
|
+
x05 = rotl(x05 ^ x09, 7);
|
|
1767
|
+
x02 = x02 + x06 | 0;
|
|
1768
|
+
x14 = rotl(x14 ^ x02, 16);
|
|
1769
|
+
x10 = x10 + x14 | 0;
|
|
1770
|
+
x06 = rotl(x06 ^ x10, 12);
|
|
1771
|
+
x02 = x02 + x06 | 0;
|
|
1772
|
+
x14 = rotl(x14 ^ x02, 8);
|
|
1773
|
+
x10 = x10 + x14 | 0;
|
|
1774
|
+
x06 = rotl(x06 ^ x10, 7);
|
|
1775
|
+
x03 = x03 + x07 | 0;
|
|
1776
|
+
x15 = rotl(x15 ^ x03, 16);
|
|
1777
|
+
x11 = x11 + x15 | 0;
|
|
1778
|
+
x07 = rotl(x07 ^ x11, 12);
|
|
1779
|
+
x03 = x03 + x07 | 0;
|
|
1780
|
+
x15 = rotl(x15 ^ x03, 8);
|
|
1781
|
+
x11 = x11 + x15 | 0;
|
|
1782
|
+
x07 = rotl(x07 ^ x11, 7);
|
|
1783
|
+
x00 = x00 + x05 | 0;
|
|
1784
|
+
x15 = rotl(x15 ^ x00, 16);
|
|
1785
|
+
x10 = x10 + x15 | 0;
|
|
1786
|
+
x05 = rotl(x05 ^ x10, 12);
|
|
1787
|
+
x00 = x00 + x05 | 0;
|
|
1788
|
+
x15 = rotl(x15 ^ x00, 8);
|
|
1789
|
+
x10 = x10 + x15 | 0;
|
|
1790
|
+
x05 = rotl(x05 ^ x10, 7);
|
|
1791
|
+
x01 = x01 + x06 | 0;
|
|
1792
|
+
x12 = rotl(x12 ^ x01, 16);
|
|
1793
|
+
x11 = x11 + x12 | 0;
|
|
1794
|
+
x06 = rotl(x06 ^ x11, 12);
|
|
1795
|
+
x01 = x01 + x06 | 0;
|
|
1796
|
+
x12 = rotl(x12 ^ x01, 8);
|
|
1797
|
+
x11 = x11 + x12 | 0;
|
|
1798
|
+
x06 = rotl(x06 ^ x11, 7);
|
|
1799
|
+
x02 = x02 + x07 | 0;
|
|
1800
|
+
x13 = rotl(x13 ^ x02, 16);
|
|
1801
|
+
x08 = x08 + x13 | 0;
|
|
1802
|
+
x07 = rotl(x07 ^ x08, 12);
|
|
1803
|
+
x02 = x02 + x07 | 0;
|
|
1804
|
+
x13 = rotl(x13 ^ x02, 8);
|
|
1805
|
+
x08 = x08 + x13 | 0;
|
|
1806
|
+
x07 = rotl(x07 ^ x08, 7);
|
|
1807
|
+
x03 = x03 + x04 | 0;
|
|
1808
|
+
x14 = rotl(x14 ^ x03, 16);
|
|
1809
|
+
x09 = x09 + x14 | 0;
|
|
1810
|
+
x04 = rotl(x04 ^ x09, 12);
|
|
1811
|
+
x03 = x03 + x04 | 0;
|
|
1812
|
+
x14 = rotl(x14 ^ x03, 8);
|
|
1813
|
+
x09 = x09 + x14 | 0;
|
|
1814
|
+
x04 = rotl(x04 ^ x09, 7);
|
|
1815
|
+
}
|
|
1816
|
+
let oi = 0;
|
|
1817
|
+
out[oi++] = y00 + x00 | 0;
|
|
1818
|
+
out[oi++] = y01 + x01 | 0;
|
|
1819
|
+
out[oi++] = y02 + x02 | 0;
|
|
1820
|
+
out[oi++] = y03 + x03 | 0;
|
|
1821
|
+
out[oi++] = y04 + x04 | 0;
|
|
1822
|
+
out[oi++] = y05 + x05 | 0;
|
|
1823
|
+
out[oi++] = y06 + x06 | 0;
|
|
1824
|
+
out[oi++] = y07 + x07 | 0;
|
|
1825
|
+
out[oi++] = y08 + x08 | 0;
|
|
1826
|
+
out[oi++] = y09 + x09 | 0;
|
|
1827
|
+
out[oi++] = y10 + x10 | 0;
|
|
1828
|
+
out[oi++] = y11 + x11 | 0;
|
|
1829
|
+
out[oi++] = y12 + x12 | 0;
|
|
1830
|
+
out[oi++] = y13 + x13 | 0;
|
|
1831
|
+
out[oi++] = y14 + x14 | 0;
|
|
1832
|
+
out[oi++] = y15 + x15 | 0;
|
|
1833
|
+
}
|
|
1834
|
+
function hchacha(s, k, i, out) {
|
|
1835
|
+
let x00 = s[0], x01 = s[1], x02 = s[2], x03 = s[3], x04 = k[0], x05 = k[1], x06 = k[2], x07 = k[3], x08 = k[4], x09 = k[5], x10 = k[6], x11 = k[7], x12 = i[0], x13 = i[1], x14 = i[2], x15 = i[3];
|
|
1836
|
+
for (let r = 0; r < 20; r += 2) {
|
|
1837
|
+
x00 = x00 + x04 | 0;
|
|
1838
|
+
x12 = rotl(x12 ^ x00, 16);
|
|
1839
|
+
x08 = x08 + x12 | 0;
|
|
1840
|
+
x04 = rotl(x04 ^ x08, 12);
|
|
1841
|
+
x00 = x00 + x04 | 0;
|
|
1842
|
+
x12 = rotl(x12 ^ x00, 8);
|
|
1843
|
+
x08 = x08 + x12 | 0;
|
|
1844
|
+
x04 = rotl(x04 ^ x08, 7);
|
|
1845
|
+
x01 = x01 + x05 | 0;
|
|
1846
|
+
x13 = rotl(x13 ^ x01, 16);
|
|
1847
|
+
x09 = x09 + x13 | 0;
|
|
1848
|
+
x05 = rotl(x05 ^ x09, 12);
|
|
1849
|
+
x01 = x01 + x05 | 0;
|
|
1850
|
+
x13 = rotl(x13 ^ x01, 8);
|
|
1851
|
+
x09 = x09 + x13 | 0;
|
|
1852
|
+
x05 = rotl(x05 ^ x09, 7);
|
|
1853
|
+
x02 = x02 + x06 | 0;
|
|
1854
|
+
x14 = rotl(x14 ^ x02, 16);
|
|
1855
|
+
x10 = x10 + x14 | 0;
|
|
1856
|
+
x06 = rotl(x06 ^ x10, 12);
|
|
1857
|
+
x02 = x02 + x06 | 0;
|
|
1858
|
+
x14 = rotl(x14 ^ x02, 8);
|
|
1859
|
+
x10 = x10 + x14 | 0;
|
|
1860
|
+
x06 = rotl(x06 ^ x10, 7);
|
|
1861
|
+
x03 = x03 + x07 | 0;
|
|
1862
|
+
x15 = rotl(x15 ^ x03, 16);
|
|
1863
|
+
x11 = x11 + x15 | 0;
|
|
1864
|
+
x07 = rotl(x07 ^ x11, 12);
|
|
1865
|
+
x03 = x03 + x07 | 0;
|
|
1866
|
+
x15 = rotl(x15 ^ x03, 8);
|
|
1867
|
+
x11 = x11 + x15 | 0;
|
|
1868
|
+
x07 = rotl(x07 ^ x11, 7);
|
|
1869
|
+
x00 = x00 + x05 | 0;
|
|
1870
|
+
x15 = rotl(x15 ^ x00, 16);
|
|
1871
|
+
x10 = x10 + x15 | 0;
|
|
1872
|
+
x05 = rotl(x05 ^ x10, 12);
|
|
1873
|
+
x00 = x00 + x05 | 0;
|
|
1874
|
+
x15 = rotl(x15 ^ x00, 8);
|
|
1875
|
+
x10 = x10 + x15 | 0;
|
|
1876
|
+
x05 = rotl(x05 ^ x10, 7);
|
|
1877
|
+
x01 = x01 + x06 | 0;
|
|
1878
|
+
x12 = rotl(x12 ^ x01, 16);
|
|
1879
|
+
x11 = x11 + x12 | 0;
|
|
1880
|
+
x06 = rotl(x06 ^ x11, 12);
|
|
1881
|
+
x01 = x01 + x06 | 0;
|
|
1882
|
+
x12 = rotl(x12 ^ x01, 8);
|
|
1883
|
+
x11 = x11 + x12 | 0;
|
|
1884
|
+
x06 = rotl(x06 ^ x11, 7);
|
|
1885
|
+
x02 = x02 + x07 | 0;
|
|
1886
|
+
x13 = rotl(x13 ^ x02, 16);
|
|
1887
|
+
x08 = x08 + x13 | 0;
|
|
1888
|
+
x07 = rotl(x07 ^ x08, 12);
|
|
1889
|
+
x02 = x02 + x07 | 0;
|
|
1890
|
+
x13 = rotl(x13 ^ x02, 8);
|
|
1891
|
+
x08 = x08 + x13 | 0;
|
|
1892
|
+
x07 = rotl(x07 ^ x08, 7);
|
|
1893
|
+
x03 = x03 + x04 | 0;
|
|
1894
|
+
x14 = rotl(x14 ^ x03, 16);
|
|
1895
|
+
x09 = x09 + x14 | 0;
|
|
1896
|
+
x04 = rotl(x04 ^ x09, 12);
|
|
1897
|
+
x03 = x03 + x04 | 0;
|
|
1898
|
+
x14 = rotl(x14 ^ x03, 8);
|
|
1899
|
+
x09 = x09 + x14 | 0;
|
|
1900
|
+
x04 = rotl(x04 ^ x09, 7);
|
|
1901
|
+
}
|
|
1902
|
+
let oi = 0;
|
|
1903
|
+
out[oi++] = x00;
|
|
1904
|
+
out[oi++] = x01;
|
|
1905
|
+
out[oi++] = x02;
|
|
1906
|
+
out[oi++] = x03;
|
|
1907
|
+
out[oi++] = x12;
|
|
1908
|
+
out[oi++] = x13;
|
|
1909
|
+
out[oi++] = x14;
|
|
1910
|
+
out[oi++] = x15;
|
|
1911
|
+
}
|
|
1912
|
+
var chacha20 = /* @__PURE__ */ createCipher(chachaCore, {
|
|
1913
|
+
counterRight: false,
|
|
1914
|
+
counterLength: 4,
|
|
1915
|
+
allowShortKeys: false
|
|
1916
|
+
});
|
|
1917
|
+
var xchacha20 = /* @__PURE__ */ createCipher(chachaCore, {
|
|
1918
|
+
counterRight: false,
|
|
1919
|
+
counterLength: 8,
|
|
1920
|
+
extendNonceFn: hchacha,
|
|
1921
|
+
allowShortKeys: false
|
|
1922
|
+
});
|
|
1923
|
+
var ZEROS16 = /* @__PURE__ */ new Uint8Array(16);
|
|
1924
|
+
var updatePadded = (h, msg) => {
|
|
1925
|
+
h.update(msg);
|
|
1926
|
+
const leftover = msg.length % 16;
|
|
1927
|
+
if (leftover)
|
|
1928
|
+
h.update(ZEROS16.subarray(leftover));
|
|
1929
|
+
};
|
|
1930
|
+
var ZEROS32 = /* @__PURE__ */ new Uint8Array(32);
|
|
1931
|
+
function computeTag(fn, key, nonce, ciphertext, AAD) {
|
|
1932
|
+
if (AAD !== void 0)
|
|
1933
|
+
abytes2(AAD, void 0, "AAD");
|
|
1934
|
+
const authKey = fn(key, nonce, ZEROS32);
|
|
1935
|
+
const lengths = u64Lengths(ciphertext.length, AAD ? AAD.length : 0, true);
|
|
1936
|
+
const h = poly1305.create(authKey);
|
|
1937
|
+
if (AAD)
|
|
1938
|
+
updatePadded(h, AAD);
|
|
1939
|
+
updatePadded(h, ciphertext);
|
|
1940
|
+
h.update(lengths);
|
|
1941
|
+
const res = h.digest();
|
|
1942
|
+
clean2(authKey, lengths);
|
|
1943
|
+
return res;
|
|
1944
|
+
}
|
|
1945
|
+
var _poly1305_aead = (xorStream) => (key, nonce, AAD) => {
|
|
1946
|
+
const tagLength = 16;
|
|
1947
|
+
return {
|
|
1948
|
+
encrypt(plaintext, output) {
|
|
1949
|
+
const plength = plaintext.length;
|
|
1950
|
+
output = getOutput(plength + tagLength, output, false);
|
|
1951
|
+
output.set(plaintext);
|
|
1952
|
+
const oPlain = output.subarray(0, -tagLength);
|
|
1953
|
+
xorStream(key, nonce, oPlain, oPlain, 1);
|
|
1954
|
+
const tag = computeTag(xorStream, key, nonce, oPlain, AAD);
|
|
1955
|
+
output.set(tag, plength);
|
|
1956
|
+
clean2(tag);
|
|
1957
|
+
return output;
|
|
1958
|
+
},
|
|
1959
|
+
decrypt(ciphertext, output) {
|
|
1960
|
+
output = getOutput(ciphertext.length - tagLength, output, false);
|
|
1961
|
+
const data = ciphertext.subarray(0, -tagLength);
|
|
1962
|
+
const passedTag = ciphertext.subarray(-tagLength);
|
|
1963
|
+
const tag = computeTag(xorStream, key, nonce, data, AAD);
|
|
1964
|
+
if (!equalBytes(passedTag, tag))
|
|
1965
|
+
throw new Error("invalid tag");
|
|
1966
|
+
output.set(ciphertext.subarray(0, -tagLength));
|
|
1967
|
+
xorStream(key, nonce, output, output, 1);
|
|
1968
|
+
clean2(tag);
|
|
1969
|
+
return output;
|
|
1970
|
+
}
|
|
1971
|
+
};
|
|
1972
|
+
};
|
|
1973
|
+
var chacha20poly1305 = /* @__PURE__ */ wrapCipher({ blockSize: 64, nonceLength: 12, tagLength: 16 }, _poly1305_aead(chacha20));
|
|
1974
|
+
var xchacha20poly1305 = /* @__PURE__ */ wrapCipher({ blockSize: 64, nonceLength: 24, tagLength: 16 }, _poly1305_aead(xchacha20));
|
|
1975
|
+
|
|
1976
|
+
// ../utils/dist/chunk-36F4CWBM.js
|
|
1977
|
+
function deriveKeysFromPassword(password, salt) {
|
|
1978
|
+
const keySalt = salt ?? randomBytes2(16);
|
|
1979
|
+
const masterKey = argon2id(new TextEncoder().encode(password), keySalt, {
|
|
1980
|
+
t: 3,
|
|
1981
|
+
m: 65536,
|
|
1982
|
+
p: 1,
|
|
1983
|
+
dkLen: 32
|
|
1984
|
+
});
|
|
1985
|
+
return { masterKey, salt: keySalt };
|
|
1986
|
+
}
|
|
1987
|
+
function decryptPrivateKey(packed, masterKey) {
|
|
1988
|
+
const nonce = packed.slice(0, 24);
|
|
1989
|
+
const ciphertext = packed.slice(24);
|
|
1990
|
+
const cipher = xchacha20poly1305(masterKey, nonce);
|
|
1991
|
+
return cipher.decrypt(ciphertext);
|
|
1992
|
+
}
|
|
1993
|
+
function generateSessionKey() {
|
|
1994
|
+
return randomBytes2(32);
|
|
1995
|
+
}
|
|
1996
|
+
function encryptSessionKey(sessionKey, recipientPublicKey) {
|
|
1997
|
+
const ephemeralPrivateKey = x25519.utils.randomSecretKey();
|
|
1998
|
+
const ephemeralPublicKey = x25519.getPublicKey(ephemeralPrivateKey);
|
|
1999
|
+
const sharedSecret = x25519.getSharedSecret(
|
|
2000
|
+
ephemeralPrivateKey,
|
|
2001
|
+
recipientPublicKey
|
|
2002
|
+
);
|
|
2003
|
+
const encryptionKey = blake2b(sharedSecret, { dkLen: 32 });
|
|
2004
|
+
const nonceInput = new Uint8Array(
|
|
2005
|
+
ephemeralPublicKey.length + recipientPublicKey.length
|
|
2006
|
+
);
|
|
2007
|
+
nonceInput.set(ephemeralPublicKey, 0);
|
|
2008
|
+
nonceInput.set(recipientPublicKey, ephemeralPublicKey.length);
|
|
2009
|
+
const nonce = blake2b(nonceInput, { dkLen: 24 });
|
|
2010
|
+
const cipher = xchacha20poly1305(encryptionKey, nonce);
|
|
2011
|
+
const ciphertext = cipher.encrypt(sessionKey);
|
|
2012
|
+
const packed = new Uint8Array(
|
|
2013
|
+
ephemeralPublicKey.length + ciphertext.length
|
|
2014
|
+
);
|
|
2015
|
+
packed.set(ephemeralPublicKey, 0);
|
|
2016
|
+
packed.set(ciphertext, ephemeralPublicKey.length);
|
|
2017
|
+
return packed;
|
|
2018
|
+
}
|
|
2019
|
+
function encryptChunk(plaintext, sessionKey) {
|
|
2020
|
+
const nonce = randomBytes2(24);
|
|
2021
|
+
const cipher = xchacha20poly1305(sessionKey, nonce);
|
|
2022
|
+
const ciphertext = cipher.encrypt(plaintext);
|
|
2023
|
+
const packed = new Uint8Array(nonce.length + ciphertext.length);
|
|
2024
|
+
packed.set(nonce, 0);
|
|
2025
|
+
packed.set(ciphertext, nonce.length);
|
|
2026
|
+
return packed;
|
|
2027
|
+
}
|
|
2028
|
+
function decryptChunk(packed, sessionKey) {
|
|
2029
|
+
const nonce = packed.slice(0, 24);
|
|
2030
|
+
const ciphertext = packed.slice(24);
|
|
2031
|
+
const cipher = xchacha20poly1305(sessionKey, nonce);
|
|
2032
|
+
return cipher.decrypt(ciphertext);
|
|
2033
|
+
}
|
|
2034
|
+
function openMessage(packed, publicKey, privateKey) {
|
|
2035
|
+
const ephemeralPublicKey = packed.slice(0, 32);
|
|
2036
|
+
const nonce = packed.slice(32, 56);
|
|
2037
|
+
const ciphertext = packed.slice(56);
|
|
2038
|
+
const sharedSecret = x25519.getSharedSecret(privateKey, ephemeralPublicKey);
|
|
2039
|
+
const encryptionKey = blake2b(sharedSecret, { dkLen: 32 });
|
|
2040
|
+
const cipher = xchacha20poly1305(encryptionKey, nonce);
|
|
2041
|
+
return cipher.decrypt(ciphertext);
|
|
2042
|
+
}
|
|
2043
|
+
function toBase64(data) {
|
|
2044
|
+
if (typeof Buffer !== "undefined") {
|
|
2045
|
+
return Buffer.from(data).toString("base64");
|
|
2046
|
+
}
|
|
2047
|
+
let binary = "";
|
|
2048
|
+
for (let i = 0; i < data.length; i++) {
|
|
2049
|
+
binary += String.fromCharCode(data[i]);
|
|
2050
|
+
}
|
|
2051
|
+
return btoa(binary);
|
|
2052
|
+
}
|
|
2053
|
+
var BASE64_RE = /^[A-Za-z0-9+/]*={0,2}$/;
|
|
2054
|
+
function fromBase64(b64) {
|
|
2055
|
+
if (typeof b64 !== "string") {
|
|
2056
|
+
throw new Error("Invalid base64: non-string input");
|
|
2057
|
+
}
|
|
2058
|
+
if (b64.length === 0) {
|
|
2059
|
+
return new Uint8Array(0);
|
|
2060
|
+
}
|
|
2061
|
+
if (!BASE64_RE.test(b64)) {
|
|
2062
|
+
throw new Error("Invalid base64: contains illegal characters");
|
|
2063
|
+
}
|
|
2064
|
+
if (typeof Buffer !== "undefined") {
|
|
2065
|
+
return new Uint8Array(Buffer.from(b64, "base64"));
|
|
2066
|
+
}
|
|
2067
|
+
const binary = atob(b64);
|
|
2068
|
+
const bytes = new Uint8Array(binary.length);
|
|
2069
|
+
for (let i = 0; i < binary.length; i++) {
|
|
2070
|
+
bytes[i] = binary.charCodeAt(i);
|
|
2071
|
+
}
|
|
2072
|
+
return bytes;
|
|
2073
|
+
}
|
|
2074
|
+
|
|
2075
|
+
// src/graphql.ts
|
|
2076
|
+
var GraphQLError = class extends Error {
|
|
2077
|
+
constructor(message, errors) {
|
|
2078
|
+
super(message);
|
|
2079
|
+
this.errors = errors;
|
|
2080
|
+
this.name = "GraphQLError";
|
|
2081
|
+
}
|
|
2082
|
+
};
|
|
2083
|
+
async function gql(serverUrl, authToken, query, variables) {
|
|
2084
|
+
const res = await fetch(`${serverUrl}/api/graphql`, {
|
|
2085
|
+
method: "POST",
|
|
2086
|
+
headers: {
|
|
2087
|
+
"Content-Type": "application/json",
|
|
2088
|
+
Authorization: `Bearer ${authToken}`
|
|
2089
|
+
},
|
|
2090
|
+
body: JSON.stringify({ query, variables })
|
|
2091
|
+
});
|
|
2092
|
+
const json = await res.json();
|
|
2093
|
+
if (json.errors?.length) {
|
|
2094
|
+
throw new GraphQLError(json.errors[0].message, json.errors);
|
|
2095
|
+
}
|
|
2096
|
+
return json.data;
|
|
2097
|
+
}
|
|
2098
|
+
|
|
2099
|
+
// src/shared/auth.ts
|
|
2100
|
+
async function readPassword(prompt) {
|
|
2101
|
+
return new Promise((resolve) => {
|
|
2102
|
+
process.stdout.write(prompt);
|
|
2103
|
+
const buf = [];
|
|
2104
|
+
if (process.stdin.isTTY) {
|
|
2105
|
+
process.stdin.setRawMode(true);
|
|
2106
|
+
}
|
|
2107
|
+
process.stdin.resume();
|
|
2108
|
+
process.stdin.setEncoding("utf8");
|
|
2109
|
+
const onData = (ch) => {
|
|
2110
|
+
if (ch === "\n" || ch === "\r" || ch === "") {
|
|
2111
|
+
if (process.stdin.isTTY) process.stdin.setRawMode(false);
|
|
2112
|
+
process.stdin.pause();
|
|
2113
|
+
process.stdin.removeListener("data", onData);
|
|
2114
|
+
process.stdout.write("\n");
|
|
2115
|
+
resolve(Buffer.concat(buf).toString("utf8"));
|
|
2116
|
+
} else if (ch === "") {
|
|
2117
|
+
if (process.stdin.isTTY) process.stdin.setRawMode(false);
|
|
2118
|
+
process.exit(130);
|
|
2119
|
+
} else if (ch === "\x7F" || ch === "\b") {
|
|
2120
|
+
buf.pop();
|
|
2121
|
+
} else {
|
|
2122
|
+
buf.push(Buffer.from(ch, "utf8"));
|
|
2123
|
+
}
|
|
2124
|
+
};
|
|
2125
|
+
process.stdin.on("data", onData);
|
|
2126
|
+
});
|
|
2127
|
+
}
|
|
2128
|
+
async function decryptPrivateKeyFromConfig(cfg) {
|
|
2129
|
+
if (cfg.masterKey) {
|
|
2130
|
+
try {
|
|
2131
|
+
const mk = fromBase64(cfg.masterKey);
|
|
2132
|
+
return await decryptPrivateKey(fromBase64(cfg.encryptedPrivateKey), mk);
|
|
2133
|
+
} catch {
|
|
2134
|
+
console.error("Cached master key is invalid. Please run: anyterm login");
|
|
2135
|
+
process.exit(1);
|
|
2136
|
+
}
|
|
2137
|
+
}
|
|
2138
|
+
const password = await readPassword("Password (to unlock keys): ");
|
|
2139
|
+
try {
|
|
2140
|
+
const salt = fromBase64(cfg.keySalt);
|
|
2141
|
+
const { masterKey } = await deriveKeysFromPassword(password, salt);
|
|
2142
|
+
return await decryptPrivateKey(
|
|
2143
|
+
fromBase64(cfg.encryptedPrivateKey),
|
|
2144
|
+
masterKey
|
|
2145
|
+
);
|
|
2146
|
+
} catch {
|
|
2147
|
+
console.error("Incorrect password.");
|
|
2148
|
+
process.exit(1);
|
|
2149
|
+
}
|
|
2150
|
+
}
|
|
2151
|
+
|
|
2152
|
+
// src/commands/login.ts
|
|
2153
|
+
var loginCommand = new Command("login").description("Authenticate with anyterm server").option("-s, --server <url>", "Server URL (default: anyterm.dev)").action(async (opts) => {
|
|
2154
|
+
const rl = createInterface({ input: stdin, output: stdout });
|
|
2155
|
+
try {
|
|
2156
|
+
const serverUrl = normalizeServerUrl(
|
|
2157
|
+
opts.server || DEFAULT_SERVER_URL
|
|
2158
|
+
);
|
|
2159
|
+
if (opts.server && opts.server !== DEFAULT_SERVER_URL) {
|
|
2160
|
+
console.log(`\x1B[33mConnecting to self-hosted server: ${serverUrl}\x1B[0m`);
|
|
2161
|
+
console.log(`\x1B[33mNote: For the official cloud service, use: anyterm login\x1B[0m
|
|
2162
|
+
`);
|
|
2163
|
+
}
|
|
2164
|
+
const email = await rl.question("Email: ");
|
|
2165
|
+
rl.close();
|
|
2166
|
+
const password = await readPassword("Password: ");
|
|
2167
|
+
console.log("Signing in...");
|
|
2168
|
+
const res = await fetch(`${serverUrl}/api/auth/sign-in/email`, {
|
|
2169
|
+
method: "POST",
|
|
2170
|
+
headers: {
|
|
2171
|
+
"Content-Type": "application/json",
|
|
2172
|
+
Origin: serverUrl
|
|
2173
|
+
},
|
|
2174
|
+
body: JSON.stringify({ email, password })
|
|
2175
|
+
});
|
|
2176
|
+
if (!res.ok) {
|
|
2177
|
+
console.error("Login failed:", res.statusText);
|
|
2178
|
+
process.exit(1);
|
|
2179
|
+
}
|
|
2180
|
+
const data = await res.json();
|
|
2181
|
+
const token = data.session?.token ?? data.token;
|
|
2182
|
+
const userId = data.user?.id;
|
|
2183
|
+
if (!token || !userId) {
|
|
2184
|
+
console.error("Login failed: invalid response");
|
|
2185
|
+
process.exit(1);
|
|
2186
|
+
}
|
|
2187
|
+
const keysData = await gql(serverUrl, token, `query { userKeys { publicKey encryptedPrivateKey keySalt } }`);
|
|
2188
|
+
if (!keysData.userKeys?.keySalt) {
|
|
2189
|
+
console.error("Failed to fetch encryption keys");
|
|
2190
|
+
process.exit(1);
|
|
2191
|
+
}
|
|
2192
|
+
const salt = fromBase64(keysData.userKeys.keySalt);
|
|
2193
|
+
const { masterKey } = await deriveKeysFromPassword(password, salt);
|
|
2194
|
+
const encPk = fromBase64(keysData.userKeys.encryptedPrivateKey);
|
|
2195
|
+
await decryptPrivateKey(encPk, masterKey);
|
|
2196
|
+
let wsUrl = serverUrl.replace(/^http/, "ws");
|
|
2197
|
+
try {
|
|
2198
|
+
const configRes = await fetch(`${serverUrl}/api/config`);
|
|
2199
|
+
if (configRes.ok) {
|
|
2200
|
+
const configData = await configRes.json();
|
|
2201
|
+
if (configData.wsUrl) wsUrl = configData.wsUrl;
|
|
2202
|
+
}
|
|
2203
|
+
} catch {
|
|
2204
|
+
}
|
|
2205
|
+
await setSecret("authToken", token, serverUrl);
|
|
2206
|
+
await setSecret("masterKey", toBase64(masterKey), serverUrl);
|
|
2207
|
+
setServerConfig(serverUrl, {
|
|
2208
|
+
wsUrl,
|
|
2209
|
+
userId,
|
|
2210
|
+
publicKey: keysData.userKeys.publicKey,
|
|
2211
|
+
encryptedPrivateKey: keysData.userKeys.encryptedPrivateKey,
|
|
2212
|
+
keySalt: keysData.userKeys.keySalt
|
|
2213
|
+
});
|
|
2214
|
+
setActiveServer(serverUrl);
|
|
2215
|
+
try {
|
|
2216
|
+
const orgsRes = await fetch(
|
|
2217
|
+
`${serverUrl}/api/auth/organization/list`,
|
|
2218
|
+
{
|
|
2219
|
+
headers: {
|
|
2220
|
+
Authorization: `Bearer ${token}`
|
|
2221
|
+
}
|
|
2222
|
+
}
|
|
2223
|
+
);
|
|
2224
|
+
if (orgsRes.ok) {
|
|
2225
|
+
const orgsData = await orgsRes.json();
|
|
2226
|
+
const orgs = orgsData ?? [];
|
|
2227
|
+
const personalOrg = orgs.find((o) => {
|
|
2228
|
+
const org = o;
|
|
2229
|
+
return org.slug === userId;
|
|
2230
|
+
});
|
|
2231
|
+
if (personalOrg) {
|
|
2232
|
+
await fetch(`${serverUrl}/api/auth/organization/set-active`, {
|
|
2233
|
+
method: "POST",
|
|
2234
|
+
headers: {
|
|
2235
|
+
"Content-Type": "application/json",
|
|
2236
|
+
Authorization: `Bearer ${token}`
|
|
2237
|
+
},
|
|
2238
|
+
body: JSON.stringify({ organizationId: personalOrg.id })
|
|
2239
|
+
});
|
|
2240
|
+
}
|
|
2241
|
+
}
|
|
2242
|
+
} catch {
|
|
2243
|
+
}
|
|
2244
|
+
console.log("Logged in successfully. Credentials stored in system keychain.");
|
|
2245
|
+
} catch (err) {
|
|
2246
|
+
console.error("Login failed:", err instanceof Error ? err.message : String(err));
|
|
2247
|
+
process.exit(1);
|
|
2248
|
+
} finally {
|
|
2249
|
+
rl.close();
|
|
2250
|
+
}
|
|
2251
|
+
});
|
|
2252
|
+
|
|
2253
|
+
// src/commands/logout.ts
|
|
2254
|
+
import { Command as Command2 } from "commander";
|
|
2255
|
+
var logoutCommand = new Command2("logout").description("Clear saved credentials").action(async () => {
|
|
2256
|
+
await migrateConfigIfNeeded();
|
|
2257
|
+
const serverUrl = getActiveServer();
|
|
2258
|
+
const authToken = serverUrl ? await getSecret("authToken", serverUrl) : null;
|
|
2259
|
+
if (serverUrl && authToken) {
|
|
2260
|
+
try {
|
|
2261
|
+
await fetch(`${serverUrl}/api/auth/sign-out`, {
|
|
2262
|
+
method: "POST",
|
|
2263
|
+
headers: { Authorization: `Bearer ${authToken}` }
|
|
2264
|
+
});
|
|
2265
|
+
} catch {
|
|
2266
|
+
}
|
|
2267
|
+
}
|
|
2268
|
+
if (serverUrl) {
|
|
2269
|
+
await deleteSecret("authToken", serverUrl);
|
|
2270
|
+
await deleteSecret("masterKey", serverUrl);
|
|
2271
|
+
deleteServerConfig(serverUrl);
|
|
2272
|
+
const store = config.store;
|
|
2273
|
+
delete store["activeServer"];
|
|
2274
|
+
config.store = store;
|
|
2275
|
+
}
|
|
2276
|
+
console.log("Logged out. Credentials cleared.");
|
|
2277
|
+
});
|
|
2278
|
+
|
|
2279
|
+
// src/commands/run.ts
|
|
2280
|
+
import { Command as Command3 } from "commander";
|
|
2281
|
+
import * as os from "os";
|
|
2282
|
+
import WebSocket2 from "ws";
|
|
2283
|
+
|
|
2284
|
+
// ../utils/dist/chunk-2ACXBPZM.js
|
|
2285
|
+
var MAX_HTTP_TUNNEL_PAYLOAD = 2 * 1024 * 1024;
|
|
2286
|
+
var FRAME_MAGIC = new Uint8Array([86, 67]);
|
|
2287
|
+
var FRAME_VERSION = 1;
|
|
2288
|
+
var MAX_CHUNK_SIZE = 64 * 1024;
|
|
2289
|
+
var PTY_BATCH_INTERVAL_MS = 100;
|
|
2290
|
+
|
|
2291
|
+
// ../utils/dist/chunk-VO4VOY2N.js
|
|
2292
|
+
var FrameType = /* @__PURE__ */ ((FrameType2) => {
|
|
2293
|
+
FrameType2[FrameType2["SUBSCRIBE"] = 1] = "SUBSCRIBE";
|
|
2294
|
+
FrameType2[FrameType2["UNSUBSCRIBE"] = 2] = "UNSUBSCRIBE";
|
|
2295
|
+
FrameType2[FrameType2["ENCRYPTED_CHUNK"] = 3] = "ENCRYPTED_CHUNK";
|
|
2296
|
+
FrameType2[FrameType2["ENCRYPTED_INPUT"] = 4] = "ENCRYPTED_INPUT";
|
|
2297
|
+
FrameType2[FrameType2["EVENT"] = 5] = "EVENT";
|
|
2298
|
+
FrameType2[FrameType2["RESIZE"] = 6] = "RESIZE";
|
|
2299
|
+
FrameType2[FrameType2["PING"] = 7] = "PING";
|
|
2300
|
+
FrameType2[FrameType2["PONG"] = 8] = "PONG";
|
|
2301
|
+
FrameType2[FrameType2["ERROR"] = 9] = "ERROR";
|
|
2302
|
+
FrameType2[FrameType2["SESSION_ENDED"] = 10] = "SESSION_ENDED";
|
|
2303
|
+
FrameType2[FrameType2["HTTP_REQUEST"] = 11] = "HTTP_REQUEST";
|
|
2304
|
+
FrameType2[FrameType2["HTTP_RESPONSE"] = 12] = "HTTP_RESPONSE";
|
|
2305
|
+
FrameType2[FrameType2["CLI_CONNECTED"] = 13] = "CLI_CONNECTED";
|
|
2306
|
+
FrameType2[FrameType2["CLI_DISCONNECTED"] = 14] = "CLI_DISCONNECTED";
|
|
2307
|
+
FrameType2[FrameType2["SNAPSHOT"] = 15] = "SNAPSHOT";
|
|
2308
|
+
FrameType2[FrameType2["SPAWN_REQUEST"] = 16] = "SPAWN_REQUEST";
|
|
2309
|
+
FrameType2[FrameType2["SPAWN_RESPONSE"] = 17] = "SPAWN_RESPONSE";
|
|
2310
|
+
FrameType2[FrameType2["HANDSHAKE_OK"] = 18] = "HANDSHAKE_OK";
|
|
2311
|
+
return FrameType2;
|
|
2312
|
+
})(FrameType || {});
|
|
2313
|
+
var encoder = new TextEncoder();
|
|
2314
|
+
var decoder = new TextDecoder();
|
|
2315
|
+
var SESSION_ID_RE = /^[A-Za-z0-9_-]*$/;
|
|
2316
|
+
function encodeFrame(frame) {
|
|
2317
|
+
const sessionIdBytes = encoder.encode(frame.sessionId);
|
|
2318
|
+
const totalLen = 2 + 1 + 1 + 4 + sessionIdBytes.length + 4 + frame.payload.length;
|
|
2319
|
+
const buf = new Uint8Array(totalLen);
|
|
2320
|
+
const view = new DataView(buf.buffer);
|
|
2321
|
+
let offset = 0;
|
|
2322
|
+
buf[offset++] = FRAME_MAGIC[0];
|
|
2323
|
+
buf[offset++] = FRAME_MAGIC[1];
|
|
2324
|
+
buf[offset++] = FRAME_VERSION;
|
|
2325
|
+
buf[offset++] = frame.type;
|
|
2326
|
+
view.setUint32(offset, sessionIdBytes.length, false);
|
|
2327
|
+
offset += 4;
|
|
2328
|
+
buf.set(sessionIdBytes, offset);
|
|
2329
|
+
offset += sessionIdBytes.length;
|
|
2330
|
+
view.setUint32(offset, frame.payload.length, false);
|
|
2331
|
+
offset += 4;
|
|
2332
|
+
buf.set(frame.payload, offset);
|
|
2333
|
+
return buf;
|
|
2334
|
+
}
|
|
2335
|
+
function decodeFrame(data) {
|
|
2336
|
+
if (data.byteLength < 12) {
|
|
2337
|
+
throw new Error("Frame too short");
|
|
2338
|
+
}
|
|
2339
|
+
const view = new DataView(
|
|
2340
|
+
data.buffer,
|
|
2341
|
+
data.byteOffset,
|
|
2342
|
+
data.byteLength
|
|
2343
|
+
);
|
|
2344
|
+
let offset = 0;
|
|
2345
|
+
if (data[offset] !== FRAME_MAGIC[0] || data[offset + 1] !== FRAME_MAGIC[1]) {
|
|
2346
|
+
throw new Error("Invalid frame magic");
|
|
2347
|
+
}
|
|
2348
|
+
offset += 2;
|
|
2349
|
+
const version = data[offset++];
|
|
2350
|
+
const type = data[offset++];
|
|
2351
|
+
const sessionIdLen = view.getUint32(offset, false);
|
|
2352
|
+
if (sessionIdLen > 256) {
|
|
2353
|
+
throw new Error("sessionId too long");
|
|
2354
|
+
}
|
|
2355
|
+
offset += 4;
|
|
2356
|
+
if (offset + sessionIdLen + 4 > data.byteLength) {
|
|
2357
|
+
throw new Error("Frame truncated: sessionId extends beyond buffer");
|
|
2358
|
+
}
|
|
2359
|
+
const sessionId = decoder.decode(data.slice(offset, offset + sessionIdLen));
|
|
2360
|
+
if (sessionId.length > 0 && !SESSION_ID_RE.test(sessionId)) {
|
|
2361
|
+
throw new Error("Invalid sessionId: must be alphanumeric");
|
|
2362
|
+
}
|
|
2363
|
+
offset += sessionIdLen;
|
|
2364
|
+
const payloadLen = view.getUint32(offset, false);
|
|
2365
|
+
offset += 4;
|
|
2366
|
+
if (offset + payloadLen > data.byteLength) {
|
|
2367
|
+
throw new Error("Frame truncated: payload extends beyond buffer");
|
|
2368
|
+
}
|
|
2369
|
+
const payload = data.slice(offset, offset + payloadLen);
|
|
2370
|
+
return { version, type, sessionId, payload };
|
|
2371
|
+
}
|
|
2372
|
+
var EMPTY_PAYLOAD = new Uint8Array(0);
|
|
2373
|
+
function createSubscribeFrame(sessionId) {
|
|
2374
|
+
return encodeFrame({
|
|
2375
|
+
version: FRAME_VERSION,
|
|
2376
|
+
type: 1,
|
|
2377
|
+
sessionId,
|
|
2378
|
+
payload: EMPTY_PAYLOAD
|
|
2379
|
+
});
|
|
2380
|
+
}
|
|
2381
|
+
function createUnsubscribeFrame(sessionId) {
|
|
2382
|
+
return encodeFrame({
|
|
2383
|
+
version: FRAME_VERSION,
|
|
2384
|
+
type: 2,
|
|
2385
|
+
sessionId,
|
|
2386
|
+
payload: EMPTY_PAYLOAD
|
|
2387
|
+
});
|
|
2388
|
+
}
|
|
2389
|
+
function createEncryptedChunkFrame(sessionId, payload) {
|
|
2390
|
+
return encodeFrame({
|
|
2391
|
+
version: FRAME_VERSION,
|
|
2392
|
+
type: 3,
|
|
2393
|
+
sessionId,
|
|
2394
|
+
payload
|
|
2395
|
+
});
|
|
2396
|
+
}
|
|
2397
|
+
var MAX_COLS = 1e3;
|
|
2398
|
+
var MAX_ROWS = 500;
|
|
2399
|
+
function createResizeFrame(sessionId, cols, rows) {
|
|
2400
|
+
const clampedCols = Math.max(1, Math.min(cols, MAX_COLS));
|
|
2401
|
+
const clampedRows = Math.max(1, Math.min(rows, MAX_ROWS));
|
|
2402
|
+
const payload = new Uint8Array(8);
|
|
2403
|
+
const view = new DataView(payload.buffer);
|
|
2404
|
+
view.setUint32(0, clampedCols, false);
|
|
2405
|
+
view.setUint32(4, clampedRows, false);
|
|
2406
|
+
return encodeFrame({
|
|
2407
|
+
version: FRAME_VERSION,
|
|
2408
|
+
type: 6,
|
|
2409
|
+
sessionId,
|
|
2410
|
+
payload
|
|
2411
|
+
});
|
|
2412
|
+
}
|
|
2413
|
+
function createPongFrame() {
|
|
2414
|
+
return encodeFrame({
|
|
2415
|
+
version: FRAME_VERSION,
|
|
2416
|
+
type: 8,
|
|
2417
|
+
sessionId: "",
|
|
2418
|
+
payload: EMPTY_PAYLOAD
|
|
2419
|
+
});
|
|
2420
|
+
}
|
|
2421
|
+
function createSessionEndedFrame(sessionId) {
|
|
2422
|
+
return encodeFrame({
|
|
2423
|
+
version: FRAME_VERSION,
|
|
2424
|
+
type: 10,
|
|
2425
|
+
sessionId,
|
|
2426
|
+
payload: EMPTY_PAYLOAD
|
|
2427
|
+
});
|
|
2428
|
+
}
|
|
2429
|
+
function createHttpResponseFrame(sessionId, payload) {
|
|
2430
|
+
return encodeFrame({
|
|
2431
|
+
version: FRAME_VERSION,
|
|
2432
|
+
type: 12,
|
|
2433
|
+
sessionId,
|
|
2434
|
+
payload
|
|
2435
|
+
});
|
|
2436
|
+
}
|
|
2437
|
+
function createSnapshotFrame(sessionId, payload) {
|
|
2438
|
+
return encodeFrame({
|
|
2439
|
+
version: FRAME_VERSION,
|
|
2440
|
+
type: 15,
|
|
2441
|
+
sessionId,
|
|
2442
|
+
payload
|
|
2443
|
+
});
|
|
2444
|
+
}
|
|
2445
|
+
function createSpawnResponseFrame(payload) {
|
|
2446
|
+
return encodeFrame({
|
|
2447
|
+
version: FRAME_VERSION,
|
|
2448
|
+
type: 17,
|
|
2449
|
+
sessionId: "",
|
|
2450
|
+
payload
|
|
2451
|
+
});
|
|
2452
|
+
}
|
|
2453
|
+
|
|
2454
|
+
// ../utils/dist/chunk-U6HI2VN7.js
|
|
2455
|
+
function detectAgentType(command) {
|
|
2456
|
+
const cmd = command.toLowerCase();
|
|
2457
|
+
const agents = [
|
|
2458
|
+
["claude", "claude-code"],
|
|
2459
|
+
["cursor", "cursor"],
|
|
2460
|
+
["codex", "codex"],
|
|
2461
|
+
["copilot", "copilot"],
|
|
2462
|
+
["aider", "aider"],
|
|
2463
|
+
["devin", "devin"],
|
|
2464
|
+
["cline", "cline"],
|
|
2465
|
+
["continue", "continue"]
|
|
2466
|
+
];
|
|
2467
|
+
for (const [pattern, type] of agents) {
|
|
2468
|
+
if (cmd.includes(pattern)) return type;
|
|
2469
|
+
}
|
|
2470
|
+
return null;
|
|
2471
|
+
}
|
|
2472
|
+
|
|
2473
|
+
// src/shared/terminal.ts
|
|
2474
|
+
var CLEAR_PATTERNS = ["\x1B[2J", "\x1B[3J", "\x1Bc"];
|
|
2475
|
+
function containsClear(data) {
|
|
2476
|
+
return CLEAR_PATTERNS.some((p) => data.includes(p));
|
|
2477
|
+
}
|
|
2478
|
+
var SNAPSHOT_CHUNK_THRESHOLD = 100;
|
|
2479
|
+
var SNAPSHOT_INTERVAL_MS = 6e4;
|
|
2480
|
+
var SAFE_ENV_KEYS = /* @__PURE__ */ new Set([
|
|
2481
|
+
"PATH",
|
|
2482
|
+
"HOME",
|
|
2483
|
+
"USER",
|
|
2484
|
+
"LOGNAME",
|
|
2485
|
+
"SHELL",
|
|
2486
|
+
"TERM",
|
|
2487
|
+
"TERM_PROGRAM",
|
|
2488
|
+
"LANG",
|
|
2489
|
+
"LC_ALL",
|
|
2490
|
+
"LC_CTYPE",
|
|
2491
|
+
"EDITOR",
|
|
2492
|
+
"VISUAL",
|
|
2493
|
+
"PAGER",
|
|
2494
|
+
"COLORTERM",
|
|
2495
|
+
"TMPDIR",
|
|
2496
|
+
"XDG_RUNTIME_DIR",
|
|
2497
|
+
"XDG_CONFIG_HOME",
|
|
2498
|
+
"XDG_DATA_HOME",
|
|
2499
|
+
"XDG_CACHE_HOME"
|
|
2500
|
+
]);
|
|
2501
|
+
function getSafeEnv() {
|
|
2502
|
+
const env = {};
|
|
2503
|
+
for (const key of SAFE_ENV_KEYS) {
|
|
2504
|
+
if (process.env[key]) {
|
|
2505
|
+
env[key] = process.env[key];
|
|
2506
|
+
}
|
|
2507
|
+
}
|
|
2508
|
+
env.TERM = env.TERM || "xterm-256color";
|
|
2509
|
+
return env;
|
|
2510
|
+
}
|
|
2511
|
+
async function loadHeadlessTerminal() {
|
|
2512
|
+
try {
|
|
2513
|
+
const headlessMod = await import("@xterm/headless");
|
|
2514
|
+
const serializeMod = await import("@xterm/addon-serialize");
|
|
2515
|
+
const Terminal = headlessMod.Terminal ?? headlessMod.default?.Terminal;
|
|
2516
|
+
const SerializeAddon = serializeMod.SerializeAddon ?? serializeMod.default?.SerializeAddon;
|
|
2517
|
+
if (Terminal && SerializeAddon) {
|
|
2518
|
+
return { Terminal, SerializeAddon };
|
|
2519
|
+
}
|
|
2520
|
+
return null;
|
|
2521
|
+
} catch {
|
|
2522
|
+
return null;
|
|
2523
|
+
}
|
|
2524
|
+
}
|
|
2525
|
+
|
|
2526
|
+
// src/shared/http-proxy.ts
|
|
2527
|
+
import * as http from "http";
|
|
2528
|
+
|
|
2529
|
+
// src/shared/constants.ts
|
|
2530
|
+
var INITIAL_RECONNECT_DELAY = 1e3;
|
|
2531
|
+
var MAX_RECONNECT_DELAY = 3e4;
|
|
2532
|
+
var HTTP_PROXY_TIMEOUT = 25e3;
|
|
2533
|
+
var SNAPSHOT_DEBOUNCE = 500;
|
|
2534
|
+
var RESIZE_DB_DEBOUNCE = 500;
|
|
2535
|
+
var WS_CLOSE_TIMEOUT = 500;
|
|
2536
|
+
var MAX_COMMAND_LENGTH = 4096;
|
|
2537
|
+
|
|
2538
|
+
// src/shared/http-proxy.ts
|
|
2539
|
+
async function proxyLocalHttp(req) {
|
|
2540
|
+
try {
|
|
2541
|
+
return await tryProxy(req, "localhost");
|
|
2542
|
+
} catch {
|
|
2543
|
+
try {
|
|
2544
|
+
return await tryProxy(req, "127.0.0.1");
|
|
2545
|
+
} catch (err) {
|
|
2546
|
+
const isTimeout = err instanceof Error && err.message === "timeout";
|
|
2547
|
+
return {
|
|
2548
|
+
reqId: req.reqId,
|
|
2549
|
+
status: isTimeout ? 504 : 502,
|
|
2550
|
+
headers: { "content-type": "text/plain" },
|
|
2551
|
+
body: Buffer.from(
|
|
2552
|
+
isTimeout ? "Gateway Timeout" : "Bad Gateway \u2014 connection refused on localhost:" + req.port
|
|
2553
|
+
).toString("base64")
|
|
2554
|
+
};
|
|
2555
|
+
}
|
|
2556
|
+
}
|
|
2557
|
+
}
|
|
2558
|
+
function tryProxy(req, hostname) {
|
|
2559
|
+
return new Promise((resolve, reject) => {
|
|
2560
|
+
const body = req.body ? Buffer.from(req.body, "base64") : void 0;
|
|
2561
|
+
const pathAndQuery = req.path;
|
|
2562
|
+
const options = {
|
|
2563
|
+
hostname,
|
|
2564
|
+
port: req.port,
|
|
2565
|
+
path: pathAndQuery,
|
|
2566
|
+
method: req.method,
|
|
2567
|
+
headers: req.headers,
|
|
2568
|
+
timeout: HTTP_PROXY_TIMEOUT
|
|
2569
|
+
};
|
|
2570
|
+
const proxyReq = http.request(options, (proxyRes) => {
|
|
2571
|
+
const chunks = [];
|
|
2572
|
+
proxyRes.on("data", (chunk) => chunks.push(chunk));
|
|
2573
|
+
proxyRes.on("end", () => {
|
|
2574
|
+
const bodyBuf = Buffer.concat(chunks);
|
|
2575
|
+
const headers = {};
|
|
2576
|
+
for (const [key, value] of Object.entries(proxyRes.headers)) {
|
|
2577
|
+
if (typeof value === "string") headers[key] = value;
|
|
2578
|
+
else if (Array.isArray(value)) headers[key] = value.join(", ");
|
|
2579
|
+
}
|
|
2580
|
+
resolve({
|
|
2581
|
+
reqId: req.reqId,
|
|
2582
|
+
status: proxyRes.statusCode ?? 502,
|
|
2583
|
+
headers,
|
|
2584
|
+
body: bodyBuf.length > 0 ? bodyBuf.toString("base64") : void 0
|
|
2585
|
+
});
|
|
2586
|
+
});
|
|
2587
|
+
});
|
|
2588
|
+
proxyReq.on("error", (err) => {
|
|
2589
|
+
reject(err);
|
|
2590
|
+
});
|
|
2591
|
+
proxyReq.on("timeout", () => {
|
|
2592
|
+
proxyReq.destroy();
|
|
2593
|
+
reject(new Error("timeout"));
|
|
2594
|
+
});
|
|
2595
|
+
if (body) proxyReq.write(body);
|
|
2596
|
+
proxyReq.end();
|
|
2597
|
+
});
|
|
2598
|
+
}
|
|
2599
|
+
|
|
2600
|
+
// src/shared/pty-session.ts
|
|
2601
|
+
import WebSocket from "ws";
|
|
2602
|
+
function createPtySessionState(init) {
|
|
2603
|
+
return {
|
|
2604
|
+
...init,
|
|
2605
|
+
chunksSinceSnapshot: 0,
|
|
2606
|
+
snapshotInFlight: false,
|
|
2607
|
+
periodicSnapshotTimer: null,
|
|
2608
|
+
snapshotTimer: null,
|
|
2609
|
+
ptyBuffer: "",
|
|
2610
|
+
ptyBatchTimer: null,
|
|
2611
|
+
hasClearInBatch: false
|
|
2612
|
+
};
|
|
2613
|
+
}
|
|
2614
|
+
function createPtySessionManager(getWs) {
|
|
2615
|
+
async function createAndSendSnapshot(session) {
|
|
2616
|
+
if (!session.headless || !session.serializer) return false;
|
|
2617
|
+
if (session.snapshotInFlight) return false;
|
|
2618
|
+
const ws = getWs();
|
|
2619
|
+
if (!ws || ws.readyState !== WebSocket.OPEN) return false;
|
|
2620
|
+
session.snapshotInFlight = true;
|
|
2621
|
+
try {
|
|
2622
|
+
const serialized = session.serializer.serialize();
|
|
2623
|
+
const encoded = new TextEncoder().encode(serialized);
|
|
2624
|
+
const packed = await encryptChunk(encoded, session.sessionKey);
|
|
2625
|
+
ws.send(createSnapshotFrame(session.id, packed));
|
|
2626
|
+
session.chunksSinceSnapshot = 0;
|
|
2627
|
+
return true;
|
|
2628
|
+
} catch {
|
|
2629
|
+
return false;
|
|
2630
|
+
} finally {
|
|
2631
|
+
session.snapshotInFlight = false;
|
|
2632
|
+
}
|
|
2633
|
+
}
|
|
2634
|
+
function resetPeriodicSnapshotTimer(session) {
|
|
2635
|
+
if (session.periodicSnapshotTimer) clearTimeout(session.periodicSnapshotTimer);
|
|
2636
|
+
if (!session.headless || !session.serializer) return;
|
|
2637
|
+
session.periodicSnapshotTimer = setTimeout(async () => {
|
|
2638
|
+
if (session.chunksSinceSnapshot > 0) {
|
|
2639
|
+
await createAndSendSnapshot(session);
|
|
2640
|
+
}
|
|
2641
|
+
resetPeriodicSnapshotTimer(session);
|
|
2642
|
+
}, SNAPSHOT_INTERVAL_MS);
|
|
2643
|
+
}
|
|
2644
|
+
async function flushPtyBuffer(session) {
|
|
2645
|
+
if (!session.ptyBuffer) return;
|
|
2646
|
+
const batch = session.ptyBuffer;
|
|
2647
|
+
const hadClear = session.hasClearInBatch;
|
|
2648
|
+
session.ptyBuffer = "";
|
|
2649
|
+
session.hasClearInBatch = false;
|
|
2650
|
+
session.ptyBatchTimer = null;
|
|
2651
|
+
if (session.headless) session.headless.write(batch);
|
|
2652
|
+
const encoded = new TextEncoder().encode(batch);
|
|
2653
|
+
const packed = await encryptChunk(encoded, session.sessionKey);
|
|
2654
|
+
const frame = createEncryptedChunkFrame(session.id, packed);
|
|
2655
|
+
const ws = getWs();
|
|
2656
|
+
if (ws?.readyState === WebSocket.OPEN) {
|
|
2657
|
+
ws.send(frame);
|
|
2658
|
+
}
|
|
2659
|
+
session.chunksSinceSnapshot++;
|
|
2660
|
+
if (session.headless && session.serializer && hadClear) {
|
|
2661
|
+
if (session.snapshotTimer) clearTimeout(session.snapshotTimer);
|
|
2662
|
+
session.snapshotTimer = setTimeout(async () => {
|
|
2663
|
+
session.snapshotTimer = null;
|
|
2664
|
+
await createAndSendSnapshot(session);
|
|
2665
|
+
resetPeriodicSnapshotTimer(session);
|
|
2666
|
+
}, SNAPSHOT_DEBOUNCE);
|
|
2667
|
+
}
|
|
2668
|
+
if (session.headless && session.serializer && session.chunksSinceSnapshot >= SNAPSHOT_CHUNK_THRESHOLD && !session.snapshotTimer) {
|
|
2669
|
+
await createAndSendSnapshot(session);
|
|
2670
|
+
resetPeriodicSnapshotTimer(session);
|
|
2671
|
+
}
|
|
2672
|
+
}
|
|
2673
|
+
function setupPtyOutput(session, opts) {
|
|
2674
|
+
session.ptyProcess.onData((data) => {
|
|
2675
|
+
if (opts?.onData) opts.onData(data);
|
|
2676
|
+
session.ptyBuffer += data;
|
|
2677
|
+
if (containsClear(data)) session.hasClearInBatch = true;
|
|
2678
|
+
if (Buffer.byteLength(session.ptyBuffer) >= MAX_CHUNK_SIZE) {
|
|
2679
|
+
if (session.ptyBatchTimer) {
|
|
2680
|
+
clearTimeout(session.ptyBatchTimer);
|
|
2681
|
+
session.ptyBatchTimer = null;
|
|
2682
|
+
}
|
|
2683
|
+
flushPtyBuffer(session);
|
|
2684
|
+
return;
|
|
2685
|
+
}
|
|
2686
|
+
if (!session.ptyBatchTimer) {
|
|
2687
|
+
session.ptyBatchTimer = setTimeout(() => flushPtyBuffer(session), PTY_BATCH_INTERVAL_MS);
|
|
2688
|
+
}
|
|
2689
|
+
});
|
|
2690
|
+
}
|
|
2691
|
+
async function cleanupPtySession(session, opts) {
|
|
2692
|
+
if (session.ptyBatchTimer) clearTimeout(session.ptyBatchTimer);
|
|
2693
|
+
await flushPtyBuffer(session);
|
|
2694
|
+
if (session.snapshotTimer) clearTimeout(session.snapshotTimer);
|
|
2695
|
+
if (session.periodicSnapshotTimer) clearTimeout(session.periodicSnapshotTimer);
|
|
2696
|
+
await createAndSendSnapshot(session);
|
|
2697
|
+
try {
|
|
2698
|
+
await gql(opts.serverUrl, opts.authToken, `
|
|
2699
|
+
mutation ($input: UpdateSessionInput!) {
|
|
2700
|
+
updateSession(input: $input) { id }
|
|
2701
|
+
}
|
|
2702
|
+
`, {
|
|
2703
|
+
input: {
|
|
2704
|
+
id: session.id,
|
|
2705
|
+
status: "stopped",
|
|
2706
|
+
endedAt: (/* @__PURE__ */ new Date()).toISOString()
|
|
2707
|
+
}
|
|
2708
|
+
});
|
|
2709
|
+
} catch {
|
|
2710
|
+
}
|
|
2711
|
+
}
|
|
2712
|
+
return {
|
|
2713
|
+
createAndSendSnapshot,
|
|
2714
|
+
resetPeriodicSnapshotTimer,
|
|
2715
|
+
flushPtyBuffer,
|
|
2716
|
+
setupPtyOutput,
|
|
2717
|
+
cleanupPtySession
|
|
2718
|
+
};
|
|
2719
|
+
}
|
|
2720
|
+
|
|
2721
|
+
// src/commands/run.ts
|
|
2722
|
+
function resolveRunArgs(commandArgs, opts, platform3 = os.platform(), shell = process.env.SHELL) {
|
|
2723
|
+
const defaultShell = platform3 === "win32" ? "powershell.exe" : shell || "/bin/bash";
|
|
2724
|
+
const isInteractiveShell = commandArgs.length === 0;
|
|
2725
|
+
const command = commandArgs.join(" ") || defaultShell;
|
|
2726
|
+
const name = opts.name || (isInteractiveShell ? "shell" : command.split(" ")[0]);
|
|
2727
|
+
return { isInteractiveShell, command, name, defaultShell };
|
|
2728
|
+
}
|
|
2729
|
+
function parseForwardedPorts(raw) {
|
|
2730
|
+
if (!raw) return [];
|
|
2731
|
+
const ports = [];
|
|
2732
|
+
for (const p of raw.split(",")) {
|
|
2733
|
+
const port = parseInt(p.trim(), 10);
|
|
2734
|
+
if (isNaN(port) || port < 1 || port > 65535) {
|
|
2735
|
+
return { error: `Invalid port: ${p.trim()}` };
|
|
2736
|
+
}
|
|
2737
|
+
ports.push(port);
|
|
2738
|
+
}
|
|
2739
|
+
return ports;
|
|
2740
|
+
}
|
|
2741
|
+
var runCommand = new Command3("run").description("Run a command and stream to server (no command = interactive shell)").argument("[command...]", "Command to run (defaults to your shell)").option("-n, --name <name>", "Session name").option("--forward <ports>", "Forward local ports (comma-separated, e.g. 3000,8080)").action(async (commandArgs, opts) => {
|
|
2742
|
+
const cfg = await getConfig();
|
|
2743
|
+
const { serverUrl, wsUrl, authToken, publicKey, encryptedPrivateKey, keySalt } = cfg;
|
|
2744
|
+
const { isInteractiveShell, command, name, defaultShell } = resolveRunArgs(commandArgs, opts);
|
|
2745
|
+
if (command.length > MAX_COMMAND_LENGTH) {
|
|
2746
|
+
console.error(`Command too long (${command.length} chars, max ${MAX_COMMAND_LENGTH})`);
|
|
2747
|
+
process.exit(1);
|
|
2748
|
+
}
|
|
2749
|
+
const parsedPorts = parseForwardedPorts(opts.forward);
|
|
2750
|
+
if ("error" in parsedPorts) {
|
|
2751
|
+
console.error(parsedPorts.error);
|
|
2752
|
+
process.exit(1);
|
|
2753
|
+
}
|
|
2754
|
+
const forwardedPortsList = parsedPorts;
|
|
2755
|
+
const forwardedPorts = forwardedPortsList.length > 0 ? forwardedPortsList.join(",") : void 0;
|
|
2756
|
+
const privateKey = await decryptPrivateKeyFromConfig(cfg);
|
|
2757
|
+
const pty = await import("node-pty");
|
|
2758
|
+
let orgKeysData = null;
|
|
2759
|
+
try {
|
|
2760
|
+
orgKeysData = await gql(serverUrl, authToken, `
|
|
2761
|
+
query { orgKeys { orgPublicKey isPersonalOrg } }
|
|
2762
|
+
`);
|
|
2763
|
+
} catch {
|
|
2764
|
+
}
|
|
2765
|
+
const sealingKey = orgKeysData?.orgKeys?.orgPublicKey ?? publicKey;
|
|
2766
|
+
const sessionKey = await generateSessionKey();
|
|
2767
|
+
const pubKey = fromBase64(sealingKey);
|
|
2768
|
+
const encryptedSessionKey = await encryptSessionKey(sessionKey, pubKey);
|
|
2769
|
+
let createData;
|
|
2770
|
+
try {
|
|
2771
|
+
createData = await gql(serverUrl, authToken, `
|
|
2772
|
+
mutation ($input: CreateSessionInput!) {
|
|
2773
|
+
createSession(input: $input) { id }
|
|
2774
|
+
}
|
|
2775
|
+
`, {
|
|
2776
|
+
input: {
|
|
2777
|
+
name,
|
|
2778
|
+
command,
|
|
2779
|
+
encryptedSessionKey: toBase64(encryptedSessionKey),
|
|
2780
|
+
cols: process.stdout.columns || 80,
|
|
2781
|
+
rows: process.stdout.rows || 24,
|
|
2782
|
+
agentType: detectAgentType(command),
|
|
2783
|
+
machineId: getMachineId(),
|
|
2784
|
+
machineName: getMachineName(),
|
|
2785
|
+
...forwardedPorts ? { forwardedPorts } : {}
|
|
2786
|
+
}
|
|
2787
|
+
});
|
|
2788
|
+
} catch (err) {
|
|
2789
|
+
console.error("Failed to create session:", err instanceof Error ? err.message : String(err));
|
|
2790
|
+
process.exit(1);
|
|
2791
|
+
}
|
|
2792
|
+
const sessionId = createData.createSession.id;
|
|
2793
|
+
console.log(`Session: ${sessionId}`);
|
|
2794
|
+
console.log(`Web: ${serverUrl}/s/${sessionId}`);
|
|
2795
|
+
if (isInteractiveShell) {
|
|
2796
|
+
console.log(`Mode: interactive shell (${command})`);
|
|
2797
|
+
}
|
|
2798
|
+
if (forwardedPorts) {
|
|
2799
|
+
for (const port of forwardedPortsList) {
|
|
2800
|
+
console.log(`Tunnel: ${serverUrl}/tunnel/${sessionId}/${port}/`);
|
|
2801
|
+
}
|
|
2802
|
+
}
|
|
2803
|
+
console.log();
|
|
2804
|
+
const shell = defaultShell;
|
|
2805
|
+
const args = isInteractiveShell ? [] : ["-c", command];
|
|
2806
|
+
const ptyProcess = pty.spawn(shell, args, {
|
|
2807
|
+
name: "xterm-256color",
|
|
2808
|
+
cols: process.stdout.columns || 80,
|
|
2809
|
+
rows: process.stdout.rows || 24,
|
|
2810
|
+
cwd: process.cwd(),
|
|
2811
|
+
env: getSafeEnv()
|
|
2812
|
+
});
|
|
2813
|
+
let headless = null;
|
|
2814
|
+
let serializer = null;
|
|
2815
|
+
const headlessClasses = await loadHeadlessTerminal();
|
|
2816
|
+
if (headlessClasses) {
|
|
2817
|
+
headless = new headlessClasses.Terminal({
|
|
2818
|
+
cols: process.stdout.columns || 80,
|
|
2819
|
+
rows: process.stdout.rows || 24
|
|
2820
|
+
});
|
|
2821
|
+
serializer = new headlessClasses.SerializeAddon();
|
|
2822
|
+
headless.loadAddon(serializer);
|
|
2823
|
+
}
|
|
2824
|
+
let ws = null;
|
|
2825
|
+
let wsClosing = false;
|
|
2826
|
+
let handshakeCompleted = false;
|
|
2827
|
+
const session = createPtySessionState({
|
|
2828
|
+
id: sessionId,
|
|
2829
|
+
sessionKey,
|
|
2830
|
+
ptyProcess,
|
|
2831
|
+
headless,
|
|
2832
|
+
serializer,
|
|
2833
|
+
forwardedPorts: forwardedPortsList
|
|
2834
|
+
});
|
|
2835
|
+
const ptyManager = createPtySessionManager(() => ws);
|
|
2836
|
+
const wsConnUrl = `${wsUrl}/ws`;
|
|
2837
|
+
let reconnectDelay = INITIAL_RECONNECT_DELAY;
|
|
2838
|
+
function connectWS() {
|
|
2839
|
+
const socket = new WebSocket2(wsConnUrl);
|
|
2840
|
+
ws = socket;
|
|
2841
|
+
handshakeCompleted = false;
|
|
2842
|
+
socket.on("open", () => {
|
|
2843
|
+
reconnectDelay = INITIAL_RECONNECT_DELAY;
|
|
2844
|
+
socket.send(JSON.stringify({
|
|
2845
|
+
version: FRAME_VERSION,
|
|
2846
|
+
token: authToken,
|
|
2847
|
+
source: "cli"
|
|
2848
|
+
}));
|
|
2849
|
+
});
|
|
2850
|
+
socket.on("close", (code, reason) => {
|
|
2851
|
+
if (wsClosing) return;
|
|
2852
|
+
if (code === 4001) {
|
|
2853
|
+
console.error("\x1B[31mUnauthorized. Please run: anyterm login\x1B[0m");
|
|
2854
|
+
ptyProcess.kill();
|
|
2855
|
+
return;
|
|
2856
|
+
}
|
|
2857
|
+
if (code === 4010) {
|
|
2858
|
+
console.error(`\x1B[31m${reason.toString() || "Protocol version mismatch. Please update your CLI: npm update -g anyterm"}\x1B[0m`);
|
|
2859
|
+
ptyProcess.kill();
|
|
2860
|
+
return;
|
|
2861
|
+
}
|
|
2862
|
+
setTimeout(() => {
|
|
2863
|
+
if (!wsClosing) connectWS();
|
|
2864
|
+
}, reconnectDelay);
|
|
2865
|
+
reconnectDelay = Math.min(reconnectDelay * 2, MAX_RECONNECT_DELAY);
|
|
2866
|
+
});
|
|
2867
|
+
socket.on("error", () => {
|
|
2868
|
+
});
|
|
2869
|
+
setupWsHandlers(socket);
|
|
2870
|
+
}
|
|
2871
|
+
connectWS();
|
|
2872
|
+
function setupWsHandlers(socket) {
|
|
2873
|
+
socket.on("message", async (raw) => {
|
|
2874
|
+
try {
|
|
2875
|
+
const frame = decodeFrame(new Uint8Array(raw));
|
|
2876
|
+
if (!handshakeCompleted) {
|
|
2877
|
+
if (frame.type === FrameType.HANDSHAKE_OK) {
|
|
2878
|
+
handshakeCompleted = true;
|
|
2879
|
+
socket.send(createSubscribeFrame(sessionId));
|
|
2880
|
+
ptyManager.resetPeriodicSnapshotTimer(session);
|
|
2881
|
+
return;
|
|
2882
|
+
}
|
|
2883
|
+
if (frame.type === FrameType.ERROR) {
|
|
2884
|
+
const msg = new TextDecoder().decode(frame.payload);
|
|
2885
|
+
try {
|
|
2886
|
+
const err = JSON.parse(msg);
|
|
2887
|
+
console.error(`\x1B[31m${err.message || msg}\x1B[0m`);
|
|
2888
|
+
} catch {
|
|
2889
|
+
console.error(`\x1B[31m${msg}\x1B[0m`);
|
|
2890
|
+
}
|
|
2891
|
+
return;
|
|
2892
|
+
}
|
|
2893
|
+
return;
|
|
2894
|
+
}
|
|
2895
|
+
if (frame.type === FrameType.PING) {
|
|
2896
|
+
socket.send(createPongFrame());
|
|
2897
|
+
} else if (frame.type === FrameType.ENCRYPTED_INPUT) {
|
|
2898
|
+
const plaintext = await decryptChunk(frame.payload, sessionKey);
|
|
2899
|
+
const text = new TextDecoder().decode(plaintext);
|
|
2900
|
+
ptyProcess.write(text);
|
|
2901
|
+
} else if (frame.type === FrameType.HTTP_REQUEST && forwardedPorts) {
|
|
2902
|
+
const json = new TextDecoder().decode(frame.payload);
|
|
2903
|
+
const req = JSON.parse(json);
|
|
2904
|
+
if (!forwardedPortsList.includes(req.port)) return;
|
|
2905
|
+
const response = await proxyLocalHttp(req);
|
|
2906
|
+
const responsePayload = new TextEncoder().encode(JSON.stringify(response));
|
|
2907
|
+
const responseFrame = createHttpResponseFrame(sessionId, responsePayload);
|
|
2908
|
+
if (socket.readyState === WebSocket2.OPEN) {
|
|
2909
|
+
socket.send(responseFrame);
|
|
2910
|
+
}
|
|
2911
|
+
} else if (frame.type === FrameType.SESSION_ENDED) {
|
|
2912
|
+
console.log("\n\x1B[33mSession ended remotely.\x1B[0m");
|
|
2913
|
+
ptyProcess.kill();
|
|
2914
|
+
}
|
|
2915
|
+
} catch (err) {
|
|
2916
|
+
console.error("[WS] Frame handling error:", err instanceof Error ? err.message : String(err));
|
|
2917
|
+
if (process.env.DEBUG) {
|
|
2918
|
+
console.debug(err);
|
|
2919
|
+
}
|
|
2920
|
+
}
|
|
2921
|
+
});
|
|
2922
|
+
}
|
|
2923
|
+
ptyManager.setupPtyOutput(session, {
|
|
2924
|
+
onData: (data) => process.stdout.write(data)
|
|
2925
|
+
});
|
|
2926
|
+
ptyProcess.onExit(async ({ exitCode }) => {
|
|
2927
|
+
wsClosing = true;
|
|
2928
|
+
await ptyManager.cleanupPtySession(session, { serverUrl, authToken });
|
|
2929
|
+
if (ws && ws.readyState === WebSocket2.OPEN) {
|
|
2930
|
+
ws.close();
|
|
2931
|
+
await new Promise((resolve) => {
|
|
2932
|
+
ws.once("close", resolve);
|
|
2933
|
+
setTimeout(resolve, WS_CLOSE_TIMEOUT);
|
|
2934
|
+
});
|
|
2935
|
+
}
|
|
2936
|
+
process.exit(exitCode);
|
|
2937
|
+
});
|
|
2938
|
+
let resizeDbTimer = null;
|
|
2939
|
+
process.stdout.on("resize", () => {
|
|
2940
|
+
const cols = process.stdout.columns;
|
|
2941
|
+
const rows = process.stdout.rows;
|
|
2942
|
+
ptyProcess.resize(cols, rows);
|
|
2943
|
+
if (session.headless) session.headless.resize(cols, rows);
|
|
2944
|
+
if (ws?.readyState === WebSocket2.OPEN) {
|
|
2945
|
+
ws.send(createResizeFrame(sessionId, cols, rows));
|
|
2946
|
+
}
|
|
2947
|
+
if (resizeDbTimer) clearTimeout(resizeDbTimer);
|
|
2948
|
+
resizeDbTimer = setTimeout(async () => {
|
|
2949
|
+
try {
|
|
2950
|
+
await gql(serverUrl, authToken, `
|
|
2951
|
+
mutation ($input: UpdateSessionInput!) {
|
|
2952
|
+
updateSession(input: $input) { id }
|
|
2953
|
+
}
|
|
2954
|
+
`, { input: { id: sessionId, cols, rows } });
|
|
2955
|
+
} catch {
|
|
2956
|
+
}
|
|
2957
|
+
}, RESIZE_DB_DEBOUNCE);
|
|
2958
|
+
});
|
|
2959
|
+
if (process.stdin.isTTY) {
|
|
2960
|
+
process.stdin.setRawMode(true);
|
|
2961
|
+
}
|
|
2962
|
+
process.stdin.resume();
|
|
2963
|
+
process.stdin.on("data", (data) => {
|
|
2964
|
+
ptyProcess.write(data.toString());
|
|
2965
|
+
});
|
|
2966
|
+
const cleanup = () => {
|
|
2967
|
+
if (process.stdin.isTTY) {
|
|
2968
|
+
try {
|
|
2969
|
+
process.stdin.setRawMode(false);
|
|
2970
|
+
} catch {
|
|
2971
|
+
}
|
|
2972
|
+
}
|
|
2973
|
+
if (session.periodicSnapshotTimer) clearTimeout(session.periodicSnapshotTimer);
|
|
2974
|
+
ptyProcess.kill();
|
|
2975
|
+
sessionKey.fill(0);
|
|
2976
|
+
privateKey.fill(0);
|
|
2977
|
+
};
|
|
2978
|
+
process.on("SIGINT", cleanup);
|
|
2979
|
+
process.on("SIGTERM", cleanup);
|
|
2980
|
+
process.on("SIGHUP", cleanup);
|
|
2981
|
+
});
|
|
2982
|
+
|
|
2983
|
+
// src/commands/list.ts
|
|
2984
|
+
import { Command as Command4 } from "commander";
|
|
2985
|
+
var ANSI_RE = /\x1b\[[0-9;]*m/g;
|
|
2986
|
+
var STATUS_COL_WIDTH = 18;
|
|
2987
|
+
function formatStatus(status) {
|
|
2988
|
+
return status === "running" ? "\x1B[32m\u25CF\x1B[0m running" : status === "disconnected" ? "\x1B[33m\u25CF\x1B[0m disconnected" : "\u25CB stopped";
|
|
2989
|
+
}
|
|
2990
|
+
function formatRow(s) {
|
|
2991
|
+
const status = formatStatus(s.status);
|
|
2992
|
+
const visibleLen = status.replace(ANSI_RE, "").length;
|
|
2993
|
+
const paddedStatus = status + " ".repeat(Math.max(0, STATUS_COL_WIDTH - visibleLen));
|
|
2994
|
+
return s.id.padEnd(15) + s.name.slice(0, 22).padEnd(25) + paddedStatus + s.command.slice(0, 30);
|
|
2995
|
+
}
|
|
2996
|
+
var listCommand = new Command4("list").alias("ls").description("List terminal sessions").action(async () => {
|
|
2997
|
+
const { serverUrl, authToken } = await getConfig();
|
|
2998
|
+
let sessions;
|
|
2999
|
+
try {
|
|
3000
|
+
const data = await gql(serverUrl, authToken, `
|
|
3001
|
+
query { sessions { id name status command } }
|
|
3002
|
+
`);
|
|
3003
|
+
sessions = data.sessions;
|
|
3004
|
+
} catch {
|
|
3005
|
+
console.error("Failed to fetch sessions");
|
|
3006
|
+
process.exit(1);
|
|
3007
|
+
}
|
|
3008
|
+
if (sessions.length === 0) {
|
|
3009
|
+
console.log("No sessions.");
|
|
3010
|
+
return;
|
|
3011
|
+
}
|
|
3012
|
+
console.log(
|
|
3013
|
+
"\n" + "ID".padEnd(15) + "NAME".padEnd(25) + "STATUS".padEnd(STATUS_COL_WIDTH) + "COMMAND"
|
|
3014
|
+
);
|
|
3015
|
+
console.log("-".repeat(70));
|
|
3016
|
+
for (const s of sessions) {
|
|
3017
|
+
console.log(formatRow(s));
|
|
3018
|
+
}
|
|
3019
|
+
console.log();
|
|
3020
|
+
});
|
|
3021
|
+
|
|
3022
|
+
// src/commands/daemon.ts
|
|
3023
|
+
import { Command as Command5 } from "commander";
|
|
3024
|
+
import * as os2 from "os";
|
|
3025
|
+
import WebSocket3 from "ws";
|
|
3026
|
+
var MAX_ACTIVE_SESSIONS = 20;
|
|
3027
|
+
function parseSpawnForwardedPorts(raw) {
|
|
3028
|
+
if (!Array.isArray(raw)) return [];
|
|
3029
|
+
return raw.map(Number).filter((p) => Number.isInteger(p) && p >= 1 && p <= 65535);
|
|
3030
|
+
}
|
|
3031
|
+
function extractCommandName(command) {
|
|
3032
|
+
const cmdBase = command.split(" ")[0];
|
|
3033
|
+
return cmdBase.split("/").pop() || cmdBase;
|
|
3034
|
+
}
|
|
3035
|
+
function deriveSessionName(spawnName, command) {
|
|
3036
|
+
const cmdName = extractCommandName(command);
|
|
3037
|
+
return spawnName || cmdName.slice(0, 256);
|
|
3038
|
+
}
|
|
3039
|
+
function parseAllowedCommands(raw) {
|
|
3040
|
+
if (!raw) return null;
|
|
3041
|
+
const patterns = raw.split(",").map((s) => s.trim()).filter(Boolean);
|
|
3042
|
+
return patterns.length > 0 ? patterns : null;
|
|
3043
|
+
}
|
|
3044
|
+
function isCommandAllowed(command, allowedPatterns) {
|
|
3045
|
+
if (!allowedPatterns) return true;
|
|
3046
|
+
return allowedPatterns.some((pattern) => command.includes(pattern));
|
|
3047
|
+
}
|
|
3048
|
+
var daemonCommand = new Command5("daemon").description("Run background daemon for web-initiated terminals").option("-d, --debug", "Enable debug logging").option("-n, --name <name>", "Display name for this machine (defaults to hostname)").option("--allow <patterns>", "Restrict spawnable commands (comma-separated patterns, e.g. claude,npm,node)").action(async (opts) => {
|
|
3049
|
+
const debug = opts.debug || !!process.env.DEBUG;
|
|
3050
|
+
const log = (...args) => console.log("[daemon]", ...args);
|
|
3051
|
+
const dbg = debug ? (...args) => console.debug("[daemon]", ...args) : () => {
|
|
3052
|
+
};
|
|
3053
|
+
const allowedCommands = parseAllowedCommands(opts.allow);
|
|
3054
|
+
if (allowedCommands) {
|
|
3055
|
+
log(`Command allowlist: ${allowedCommands.join(", ")}`);
|
|
3056
|
+
}
|
|
3057
|
+
const machineId = getMachineId();
|
|
3058
|
+
if (opts.name) {
|
|
3059
|
+
setMachineName(opts.name);
|
|
3060
|
+
}
|
|
3061
|
+
const machineName = opts.name || getMachineName();
|
|
3062
|
+
log(`Machine: ${machineName} (${machineId})`);
|
|
3063
|
+
const cfg = await getConfig();
|
|
3064
|
+
const { serverUrl, wsUrl, authToken, publicKey, encryptedPrivateKey, keySalt } = cfg;
|
|
3065
|
+
const privateKey = await decryptPrivateKeyFromConfig(cfg);
|
|
3066
|
+
const pubKey = fromBase64(publicKey);
|
|
3067
|
+
const headlessClasses = await loadHeadlessTerminal();
|
|
3068
|
+
if (!headlessClasses) {
|
|
3069
|
+
log("Headless terminal unavailable \u2014 snapshots disabled");
|
|
3070
|
+
}
|
|
3071
|
+
const pty = await import("node-pty");
|
|
3072
|
+
const activeSessions = /* @__PURE__ */ new Map();
|
|
3073
|
+
let ws = null;
|
|
3074
|
+
let shuttingDown = false;
|
|
3075
|
+
const ptyManager = createPtySessionManager(() => ws);
|
|
3076
|
+
const wsConnUrl = `${wsUrl}/ws`;
|
|
3077
|
+
let reconnectDelay = INITIAL_RECONNECT_DELAY;
|
|
3078
|
+
let handshakeCompleted = false;
|
|
3079
|
+
function connectWS() {
|
|
3080
|
+
const socket = new WebSocket3(wsConnUrl);
|
|
3081
|
+
ws = socket;
|
|
3082
|
+
handshakeCompleted = false;
|
|
3083
|
+
socket.on("open", () => {
|
|
3084
|
+
reconnectDelay = INITIAL_RECONNECT_DELAY;
|
|
3085
|
+
socket.send(JSON.stringify({
|
|
3086
|
+
version: FRAME_VERSION,
|
|
3087
|
+
token: authToken,
|
|
3088
|
+
source: "daemon",
|
|
3089
|
+
machineId,
|
|
3090
|
+
machineName
|
|
3091
|
+
}));
|
|
3092
|
+
});
|
|
3093
|
+
socket.on("close", (code, reason) => {
|
|
3094
|
+
if (shuttingDown) return;
|
|
3095
|
+
if (code === 4001) {
|
|
3096
|
+
console.error("[daemon] Unauthorized. Run: anyterm login");
|
|
3097
|
+
process.exit(1);
|
|
3098
|
+
}
|
|
3099
|
+
if (code === 4002) {
|
|
3100
|
+
console.error("[daemon] Server rejected connection: missing machine ID.");
|
|
3101
|
+
process.exit(1);
|
|
3102
|
+
}
|
|
3103
|
+
if (code === 4003) {
|
|
3104
|
+
console.error(
|
|
3105
|
+
"[daemon] Another daemon with the same machine ID is already connected.\n Stop the other daemon first, or run on a different machine."
|
|
3106
|
+
);
|
|
3107
|
+
process.exit(1);
|
|
3108
|
+
}
|
|
3109
|
+
if (code === 4010) {
|
|
3110
|
+
console.error("[daemon] Protocol version mismatch. Please update your CLI: npm update -g anyterm");
|
|
3111
|
+
process.exit(1);
|
|
3112
|
+
}
|
|
3113
|
+
log(`Disconnected (code ${code}), reconnecting in ${reconnectDelay}ms...`);
|
|
3114
|
+
setTimeout(() => {
|
|
3115
|
+
if (!shuttingDown) connectWS();
|
|
3116
|
+
}, reconnectDelay);
|
|
3117
|
+
reconnectDelay = Math.min(reconnectDelay * 2, MAX_RECONNECT_DELAY);
|
|
3118
|
+
});
|
|
3119
|
+
socket.on("error", () => {
|
|
3120
|
+
});
|
|
3121
|
+
setupWsHandlers(socket);
|
|
3122
|
+
}
|
|
3123
|
+
async function spawnSession(request2, socket) {
|
|
3124
|
+
const { requestId, command, name, forwardedPorts: fwdPorts } = request2;
|
|
3125
|
+
const cols = process.stdout.columns || 80;
|
|
3126
|
+
const rows = process.stdout.rows || 24;
|
|
3127
|
+
dbg(`Spawn request: ${command} (${cols}x${rows})`);
|
|
3128
|
+
if (activeSessions.size >= MAX_ACTIVE_SESSIONS) {
|
|
3129
|
+
log(`Rejected spawn: active session limit reached (${MAX_ACTIVE_SESSIONS})`);
|
|
3130
|
+
const response = { requestId, error: `Daemon session limit reached (max ${MAX_ACTIVE_SESSIONS})` };
|
|
3131
|
+
const responsePayload = new TextEncoder().encode(JSON.stringify(response));
|
|
3132
|
+
socket.send(createSpawnResponseFrame(responsePayload));
|
|
3133
|
+
return;
|
|
3134
|
+
}
|
|
3135
|
+
try {
|
|
3136
|
+
const sessionKey = await generateSessionKey();
|
|
3137
|
+
const encryptedSessionKey = await encryptSessionKey(sessionKey, pubKey);
|
|
3138
|
+
const createData = await gql(
|
|
3139
|
+
serverUrl,
|
|
3140
|
+
authToken,
|
|
3141
|
+
`
|
|
3142
|
+
mutation ($input: CreateSessionInput!) {
|
|
3143
|
+
createSession(input: $input) { id }
|
|
3144
|
+
}
|
|
3145
|
+
`,
|
|
3146
|
+
{
|
|
3147
|
+
input: {
|
|
3148
|
+
name,
|
|
3149
|
+
command,
|
|
3150
|
+
encryptedSessionKey: toBase64(encryptedSessionKey),
|
|
3151
|
+
cols,
|
|
3152
|
+
rows,
|
|
3153
|
+
agentType: detectAgentType(command),
|
|
3154
|
+
machineId,
|
|
3155
|
+
machineName,
|
|
3156
|
+
...fwdPorts && fwdPorts.length > 0 ? { forwardedPorts: fwdPorts.join(",") } : {}
|
|
3157
|
+
}
|
|
3158
|
+
}
|
|
3159
|
+
);
|
|
3160
|
+
const sessionId = createData.createSession.id;
|
|
3161
|
+
log(`Spawned session ${sessionId}: ${command}`);
|
|
3162
|
+
socket.send(createSubscribeFrame(sessionId));
|
|
3163
|
+
let headless = null;
|
|
3164
|
+
let serializer = null;
|
|
3165
|
+
if (headlessClasses) {
|
|
3166
|
+
headless = new headlessClasses.Terminal({ cols, rows });
|
|
3167
|
+
serializer = new headlessClasses.SerializeAddon();
|
|
3168
|
+
headless.loadAddon(serializer);
|
|
3169
|
+
}
|
|
3170
|
+
const shell = os2.platform() === "win32" ? "powershell.exe" : process.env.SHELL || "/bin/bash";
|
|
3171
|
+
const args = command !== shell ? ["-c", command] : [];
|
|
3172
|
+
const ptyProcess = pty.spawn(shell, args, {
|
|
3173
|
+
name: "xterm-256color",
|
|
3174
|
+
cols,
|
|
3175
|
+
rows,
|
|
3176
|
+
cwd: process.env.HOME || process.cwd(),
|
|
3177
|
+
env: getSafeEnv()
|
|
3178
|
+
});
|
|
3179
|
+
const session = createPtySessionState({
|
|
3180
|
+
id: sessionId,
|
|
3181
|
+
sessionKey,
|
|
3182
|
+
ptyProcess,
|
|
3183
|
+
headless,
|
|
3184
|
+
serializer,
|
|
3185
|
+
forwardedPorts: fwdPorts ?? []
|
|
3186
|
+
});
|
|
3187
|
+
activeSessions.set(sessionId, session);
|
|
3188
|
+
ptyManager.resetPeriodicSnapshotTimer(session);
|
|
3189
|
+
ptyManager.setupPtyOutput(session);
|
|
3190
|
+
ptyProcess.onExit(async ({ exitCode }) => {
|
|
3191
|
+
log(`Session ${sessionId} ended (exit ${exitCode})`);
|
|
3192
|
+
await ptyManager.cleanupPtySession(session, { serverUrl, authToken });
|
|
3193
|
+
if (ws?.readyState === WebSocket3.OPEN) {
|
|
3194
|
+
ws.send(createSessionEndedFrame(sessionId));
|
|
3195
|
+
ws.send(createUnsubscribeFrame(sessionId));
|
|
3196
|
+
}
|
|
3197
|
+
activeSessions.delete(sessionId);
|
|
3198
|
+
});
|
|
3199
|
+
const response = { requestId, sessionId };
|
|
3200
|
+
const responsePayload = new TextEncoder().encode(JSON.stringify(response));
|
|
3201
|
+
socket.send(createSpawnResponseFrame(responsePayload));
|
|
3202
|
+
} catch (err) {
|
|
3203
|
+
const errorMsg = err instanceof Error ? err.message : "Unknown error";
|
|
3204
|
+
log(`Spawn failed: ${errorMsg}`);
|
|
3205
|
+
const response = { requestId, error: errorMsg };
|
|
3206
|
+
const responsePayload = new TextEncoder().encode(JSON.stringify(response));
|
|
3207
|
+
socket.send(createSpawnResponseFrame(responsePayload));
|
|
3208
|
+
}
|
|
3209
|
+
}
|
|
3210
|
+
function setupWsHandlers(socket) {
|
|
3211
|
+
socket.on("message", async (raw) => {
|
|
3212
|
+
try {
|
|
3213
|
+
const frame = decodeFrame(new Uint8Array(raw));
|
|
3214
|
+
if (!handshakeCompleted) {
|
|
3215
|
+
if (frame.type === FrameType.HANDSHAKE_OK) {
|
|
3216
|
+
handshakeCompleted = true;
|
|
3217
|
+
log("Connected to server");
|
|
3218
|
+
for (const [sessionId] of activeSessions) {
|
|
3219
|
+
socket.send(createSubscribeFrame(sessionId));
|
|
3220
|
+
}
|
|
3221
|
+
return;
|
|
3222
|
+
}
|
|
3223
|
+
if (frame.type === FrameType.ERROR) {
|
|
3224
|
+
const msg = new TextDecoder().decode(frame.payload);
|
|
3225
|
+
try {
|
|
3226
|
+
const err = JSON.parse(msg);
|
|
3227
|
+
console.error(`[daemon] ${err.message || msg}`);
|
|
3228
|
+
} catch {
|
|
3229
|
+
console.error(`[daemon] ${msg}`);
|
|
3230
|
+
}
|
|
3231
|
+
return;
|
|
3232
|
+
}
|
|
3233
|
+
return;
|
|
3234
|
+
}
|
|
3235
|
+
switch (frame.type) {
|
|
3236
|
+
case FrameType.PING: {
|
|
3237
|
+
socket.send(createPongFrame());
|
|
3238
|
+
break;
|
|
3239
|
+
}
|
|
3240
|
+
case FrameType.SPAWN_REQUEST: {
|
|
3241
|
+
const json = new TextDecoder().decode(frame.payload);
|
|
3242
|
+
const outer = JSON.parse(json);
|
|
3243
|
+
const sealed = fromBase64(outer.encryptedPayload);
|
|
3244
|
+
const decrypted = openMessage(sealed, pubKey, privateKey);
|
|
3245
|
+
const inner = JSON.parse(new TextDecoder().decode(decrypted));
|
|
3246
|
+
const defaultShell = os2.platform() === "win32" ? "powershell.exe" : process.env.SHELL || "/bin/bash";
|
|
3247
|
+
const rawCommand = typeof inner.command === "string" ? inner.command.trim() : "";
|
|
3248
|
+
const command = rawCommand || defaultShell;
|
|
3249
|
+
const spawnName = typeof inner.name === "string" ? inner.name.trim() : "";
|
|
3250
|
+
if (command.length > MAX_COMMAND_LENGTH) {
|
|
3251
|
+
const response = { requestId: outer.requestId, error: "Invalid command" };
|
|
3252
|
+
socket.send(createSpawnResponseFrame(new TextEncoder().encode(JSON.stringify(response))));
|
|
3253
|
+
break;
|
|
3254
|
+
}
|
|
3255
|
+
if (!isCommandAllowed(command, allowedCommands)) {
|
|
3256
|
+
log(`Rejected spawn: "${command}" not in allowlist`);
|
|
3257
|
+
const response = { requestId: outer.requestId, error: "Command not in allowlist" };
|
|
3258
|
+
socket.send(createSpawnResponseFrame(new TextEncoder().encode(JSON.stringify(response))));
|
|
3259
|
+
break;
|
|
3260
|
+
}
|
|
3261
|
+
const forwardedPorts = parseSpawnForwardedPorts(inner.forwardedPorts);
|
|
3262
|
+
const request2 = {
|
|
3263
|
+
requestId: outer.requestId,
|
|
3264
|
+
command,
|
|
3265
|
+
name: deriveSessionName(spawnName, command),
|
|
3266
|
+
forwardedPorts
|
|
3267
|
+
};
|
|
3268
|
+
await spawnSession(request2, socket);
|
|
3269
|
+
break;
|
|
3270
|
+
}
|
|
3271
|
+
case FrameType.ENCRYPTED_INPUT: {
|
|
3272
|
+
const session = activeSessions.get(frame.sessionId);
|
|
3273
|
+
if (!session) break;
|
|
3274
|
+
const plaintext = await decryptChunk(frame.payload, session.sessionKey);
|
|
3275
|
+
const text = new TextDecoder().decode(plaintext);
|
|
3276
|
+
session.ptyProcess.write(text);
|
|
3277
|
+
break;
|
|
3278
|
+
}
|
|
3279
|
+
case FrameType.HTTP_REQUEST: {
|
|
3280
|
+
const session = activeSessions.get(frame.sessionId);
|
|
3281
|
+
if (!session) break;
|
|
3282
|
+
const json = new TextDecoder().decode(frame.payload);
|
|
3283
|
+
const req = JSON.parse(json);
|
|
3284
|
+
if (!session.forwardedPorts.includes(req.port)) break;
|
|
3285
|
+
const response = await proxyLocalHttp(req);
|
|
3286
|
+
const responsePayload = new TextEncoder().encode(JSON.stringify(response));
|
|
3287
|
+
const responseFrame = createHttpResponseFrame(frame.sessionId, responsePayload);
|
|
3288
|
+
if (socket.readyState === WebSocket3.OPEN) {
|
|
3289
|
+
socket.send(responseFrame);
|
|
3290
|
+
}
|
|
3291
|
+
break;
|
|
3292
|
+
}
|
|
3293
|
+
case FrameType.SESSION_ENDED: {
|
|
3294
|
+
const session = activeSessions.get(frame.sessionId);
|
|
3295
|
+
if (session) {
|
|
3296
|
+
log(`Session ${frame.sessionId} ended remotely`);
|
|
3297
|
+
session.ptyProcess.kill();
|
|
3298
|
+
}
|
|
3299
|
+
break;
|
|
3300
|
+
}
|
|
3301
|
+
}
|
|
3302
|
+
} catch (err) {
|
|
3303
|
+
console.error("[daemon] Frame handling error:", err instanceof Error ? err.message : String(err));
|
|
3304
|
+
if (debug) {
|
|
3305
|
+
console.debug(err);
|
|
3306
|
+
}
|
|
3307
|
+
}
|
|
3308
|
+
});
|
|
3309
|
+
}
|
|
3310
|
+
connectWS();
|
|
3311
|
+
log("Daemon started, waiting for spawn requests...");
|
|
3312
|
+
log(`Ctrl+C to stop`);
|
|
3313
|
+
async function shutdown() {
|
|
3314
|
+
if (shuttingDown) return;
|
|
3315
|
+
shuttingDown = true;
|
|
3316
|
+
log("Shutting down...");
|
|
3317
|
+
const shutdownPromises = [];
|
|
3318
|
+
for (const [, session] of activeSessions) {
|
|
3319
|
+
shutdownPromises.push(
|
|
3320
|
+
(async () => {
|
|
3321
|
+
await ptyManager.cleanupPtySession(session, { serverUrl, authToken });
|
|
3322
|
+
session.ptyProcess.kill();
|
|
3323
|
+
})()
|
|
3324
|
+
);
|
|
3325
|
+
}
|
|
3326
|
+
await Promise.allSettled(shutdownPromises);
|
|
3327
|
+
privateKey.fill(0);
|
|
3328
|
+
for (const [, session] of activeSessions) {
|
|
3329
|
+
session.sessionKey.fill(0);
|
|
3330
|
+
}
|
|
3331
|
+
if (ws && ws.readyState === WebSocket3.OPEN) {
|
|
3332
|
+
ws.close();
|
|
3333
|
+
await new Promise((resolve) => {
|
|
3334
|
+
ws.once("close", resolve);
|
|
3335
|
+
setTimeout(resolve, WS_CLOSE_TIMEOUT);
|
|
3336
|
+
});
|
|
3337
|
+
}
|
|
3338
|
+
process.exit(0);
|
|
3339
|
+
}
|
|
3340
|
+
process.on("SIGINT", shutdown);
|
|
3341
|
+
process.on("SIGTERM", shutdown);
|
|
3342
|
+
process.on("SIGHUP", shutdown);
|
|
3343
|
+
});
|
|
3344
|
+
|
|
3345
|
+
// src/commands/org.ts
|
|
3346
|
+
import { Command as Command6 } from "commander";
|
|
3347
|
+
import { createInterface as createInterface2 } from "readline/promises";
|
|
3348
|
+
import { stdin as stdin2, stdout as stdout2 } from "process";
|
|
3349
|
+
function isPersonalOrg(slug, userId) {
|
|
3350
|
+
return slug === userId;
|
|
3351
|
+
}
|
|
3352
|
+
function orgBadge(slug, userId) {
|
|
3353
|
+
return isPersonalOrg(slug, userId) ? " (Personal)" : "";
|
|
3354
|
+
}
|
|
3355
|
+
function validateSwitchIndex(answer, orgCount) {
|
|
3356
|
+
const idx = parseInt(answer, 10) - 1;
|
|
3357
|
+
if (isNaN(idx) || idx < 0 || idx >= orgCount) return null;
|
|
3358
|
+
return idx;
|
|
3359
|
+
}
|
|
3360
|
+
var orgCommand = new Command6("org").description("Manage organizations");
|
|
3361
|
+
orgCommand.command("list").description("List your organizations").action(async () => {
|
|
3362
|
+
const { serverUrl, authToken, userId } = await getConfig();
|
|
3363
|
+
const res = await fetch(
|
|
3364
|
+
`${serverUrl}/api/auth/organization/list`,
|
|
3365
|
+
{
|
|
3366
|
+
headers: { Authorization: `Bearer ${authToken}` }
|
|
3367
|
+
}
|
|
3368
|
+
);
|
|
3369
|
+
if (!res.ok) {
|
|
3370
|
+
console.error("Failed to list organizations:", res.statusText);
|
|
3371
|
+
process.exit(1);
|
|
3372
|
+
}
|
|
3373
|
+
const orgs = await res.json();
|
|
3374
|
+
if (!orgs || orgs.length === 0) {
|
|
3375
|
+
console.log("No organizations found.");
|
|
3376
|
+
return;
|
|
3377
|
+
}
|
|
3378
|
+
console.log("\nOrganizations:\n");
|
|
3379
|
+
for (const org of orgs) {
|
|
3380
|
+
const badge = orgBadge(org.slug, userId);
|
|
3381
|
+
console.log(` ${org.name}${badge}`);
|
|
3382
|
+
console.log(` Slug: ${org.slug}`);
|
|
3383
|
+
console.log(` ID: ${org.id}`);
|
|
3384
|
+
console.log();
|
|
3385
|
+
}
|
|
3386
|
+
});
|
|
3387
|
+
orgCommand.command("current").description("Show currently active organization").action(async () => {
|
|
3388
|
+
const { serverUrl, authToken, userId } = await getConfig();
|
|
3389
|
+
const res = await fetch(
|
|
3390
|
+
`${serverUrl}/api/auth/organization/get-active-organization`,
|
|
3391
|
+
{
|
|
3392
|
+
headers: { Authorization: `Bearer ${authToken}` }
|
|
3393
|
+
}
|
|
3394
|
+
);
|
|
3395
|
+
if (!res.ok) {
|
|
3396
|
+
console.error("Failed to get active organization:", res.statusText);
|
|
3397
|
+
process.exit(1);
|
|
3398
|
+
}
|
|
3399
|
+
const org = await res.json();
|
|
3400
|
+
if (!org) {
|
|
3401
|
+
console.log("No active organization. Run: anyterm org switch");
|
|
3402
|
+
return;
|
|
3403
|
+
}
|
|
3404
|
+
console.log(`Active: ${org.name}${orgBadge(org.slug, userId)}`);
|
|
3405
|
+
console.log(` Slug: ${org.slug}`);
|
|
3406
|
+
console.log(` ID: ${org.id}`);
|
|
3407
|
+
});
|
|
3408
|
+
orgCommand.command("switch").description("Switch active organization").action(async () => {
|
|
3409
|
+
const { serverUrl, authToken, userId } = await getConfig();
|
|
3410
|
+
const res = await fetch(
|
|
3411
|
+
`${serverUrl}/api/auth/organization/list`,
|
|
3412
|
+
{
|
|
3413
|
+
headers: { Authorization: `Bearer ${authToken}` }
|
|
3414
|
+
}
|
|
3415
|
+
);
|
|
3416
|
+
if (!res.ok) {
|
|
3417
|
+
console.error("Failed to list organizations:", res.statusText);
|
|
3418
|
+
process.exit(1);
|
|
3419
|
+
}
|
|
3420
|
+
const orgs = await res.json();
|
|
3421
|
+
if (!orgs || orgs.length === 0) {
|
|
3422
|
+
console.log("No organizations found.");
|
|
3423
|
+
return;
|
|
3424
|
+
}
|
|
3425
|
+
console.log("\nSelect an organization:\n");
|
|
3426
|
+
for (let i = 0; i < orgs.length; i++) {
|
|
3427
|
+
const org = orgs[i];
|
|
3428
|
+
console.log(` [${i + 1}] ${org.name}${orgBadge(org.slug, userId)}`);
|
|
3429
|
+
}
|
|
3430
|
+
console.log();
|
|
3431
|
+
const rl = createInterface2({ input: stdin2, output: stdout2 });
|
|
3432
|
+
try {
|
|
3433
|
+
const answer = await rl.question("Enter number: ");
|
|
3434
|
+
const idx = validateSwitchIndex(answer, orgs.length);
|
|
3435
|
+
if (idx === null) {
|
|
3436
|
+
console.error("Invalid selection");
|
|
3437
|
+
process.exit(1);
|
|
3438
|
+
}
|
|
3439
|
+
const selected = orgs[idx];
|
|
3440
|
+
const setRes = await fetch(
|
|
3441
|
+
`${serverUrl}/api/auth/organization/set-active`,
|
|
3442
|
+
{
|
|
3443
|
+
method: "POST",
|
|
3444
|
+
headers: {
|
|
3445
|
+
"Content-Type": "application/json",
|
|
3446
|
+
Authorization: `Bearer ${authToken}`
|
|
3447
|
+
},
|
|
3448
|
+
body: JSON.stringify({ organizationId: selected.id })
|
|
3449
|
+
}
|
|
3450
|
+
);
|
|
3451
|
+
if (!setRes.ok) {
|
|
3452
|
+
console.error("Failed to switch organization:", setRes.statusText);
|
|
3453
|
+
process.exit(1);
|
|
3454
|
+
}
|
|
3455
|
+
console.log(`Switched to: ${selected.name}`);
|
|
3456
|
+
} finally {
|
|
3457
|
+
rl.close();
|
|
3458
|
+
}
|
|
3459
|
+
});
|
|
3460
|
+
|
|
3461
|
+
// src/index.ts
|
|
3462
|
+
var program = new Command7().name("anyterm").description("E2E encrypted remote terminal streaming").version("0.1.0");
|
|
3463
|
+
program.addCommand(loginCommand);
|
|
3464
|
+
program.addCommand(logoutCommand);
|
|
3465
|
+
program.addCommand(runCommand);
|
|
3466
|
+
program.addCommand(listCommand);
|
|
3467
|
+
program.addCommand(daemonCommand);
|
|
3468
|
+
program.addCommand(orgCommand);
|
|
3469
|
+
program.parse();
|
|
3470
|
+
/*! Bundled license information:
|
|
3471
|
+
|
|
3472
|
+
@noble/hashes/utils.js:
|
|
3473
|
+
(*! noble-hashes - MIT License (c) 2022 Paul Miller (paulmillr.com) *)
|
|
3474
|
+
|
|
3475
|
+
@noble/curves/utils.js:
|
|
3476
|
+
@noble/curves/abstract/modular.js:
|
|
3477
|
+
@noble/curves/abstract/curve.js:
|
|
3478
|
+
@noble/curves/abstract/montgomery.js:
|
|
3479
|
+
@noble/curves/ed25519.js:
|
|
3480
|
+
(*! noble-curves - MIT License (c) 2022 Paul Miller (paulmillr.com) *)
|
|
3481
|
+
|
|
3482
|
+
@noble/ciphers/utils.js:
|
|
3483
|
+
(*! noble-ciphers - MIT License (c) 2023 Paul Miller (paulmillr.com) *)
|
|
3484
|
+
*/
|