@omnituum/pqc-shared 0.2.6
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 +22 -0
- package/README.md +543 -0
- package/dist/crypto/index.cjs +807 -0
- package/dist/crypto/index.d.cts +641 -0
- package/dist/crypto/index.d.ts +641 -0
- package/dist/crypto/index.js +716 -0
- package/dist/decrypt-eSHlbh1j.d.cts +321 -0
- package/dist/decrypt-eSHlbh1j.d.ts +321 -0
- package/dist/fs/index.cjs +1168 -0
- package/dist/fs/index.d.cts +400 -0
- package/dist/fs/index.d.ts +400 -0
- package/dist/fs/index.js +1091 -0
- package/dist/index.cjs +2160 -0
- package/dist/index.d.cts +282 -0
- package/dist/index.d.ts +282 -0
- package/dist/index.js +2031 -0
- package/dist/integrity-CCYjrap3.d.ts +31 -0
- package/dist/integrity-Dx9jukMH.d.cts +31 -0
- package/dist/types-61c7Q9ri.d.ts +134 -0
- package/dist/types-Ch0y-n7K.d.cts +134 -0
- package/dist/utils/index.cjs +129 -0
- package/dist/utils/index.d.cts +49 -0
- package/dist/utils/index.d.ts +49 -0
- package/dist/utils/index.js +114 -0
- package/dist/vault/index.cjs +713 -0
- package/dist/vault/index.d.cts +237 -0
- package/dist/vault/index.d.ts +237 -0
- package/dist/vault/index.js +677 -0
- package/dist/version-BygzPVGs.d.cts +55 -0
- package/dist/version-BygzPVGs.d.ts +55 -0
- package/package.json +86 -0
- package/src/crypto/dilithium.ts +233 -0
- package/src/crypto/hybrid.ts +358 -0
- package/src/crypto/index.ts +181 -0
- package/src/crypto/kyber.ts +199 -0
- package/src/crypto/nacl.ts +204 -0
- package/src/crypto/primitives/blake3.ts +141 -0
- package/src/crypto/primitives/chacha.ts +211 -0
- package/src/crypto/primitives/hkdf.ts +192 -0
- package/src/crypto/primitives/index.ts +54 -0
- package/src/crypto/primitives.ts +144 -0
- package/src/crypto/x25519.ts +134 -0
- package/src/fs/aes.ts +343 -0
- package/src/fs/argon2.ts +184 -0
- package/src/fs/browser.ts +408 -0
- package/src/fs/decrypt.ts +320 -0
- package/src/fs/encrypt.ts +324 -0
- package/src/fs/format.ts +425 -0
- package/src/fs/index.ts +144 -0
- package/src/fs/types.ts +304 -0
- package/src/index.ts +414 -0
- package/src/kdf/index.ts +311 -0
- package/src/runtime/crypto.ts +16 -0
- package/src/security/index.ts +345 -0
- package/src/tunnel/index.ts +39 -0
- package/src/tunnel/session.ts +229 -0
- package/src/tunnel/types.ts +115 -0
- package/src/utils/entropy.ts +128 -0
- package/src/utils/index.ts +25 -0
- package/src/utils/integrity.ts +95 -0
- package/src/vault/decrypt.ts +167 -0
- package/src/vault/encrypt.ts +207 -0
- package/src/vault/index.ts +71 -0
- package/src/vault/manager.ts +327 -0
- package/src/vault/migrate.ts +190 -0
- package/src/vault/types.ts +177 -0
- package/src/version.ts +304 -0
|
@@ -0,0 +1,358 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Omnituum PQC Shared - Hybrid Encryption
|
|
3
|
+
*
|
|
4
|
+
* Post-quantum secure hybrid encryption combining:
|
|
5
|
+
* - X25519 ECDH (classical, proven security)
|
|
6
|
+
* - Kyber ML-KEM-768 (post-quantum, NIST Level 3)
|
|
7
|
+
*
|
|
8
|
+
* Both key exchanges must succeed for decryption, providing
|
|
9
|
+
* security against both classical and quantum attacks.
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
import nacl from 'tweetnacl';
|
|
13
|
+
import {
|
|
14
|
+
rand32,
|
|
15
|
+
rand24,
|
|
16
|
+
b64,
|
|
17
|
+
ub64,
|
|
18
|
+
toHex,
|
|
19
|
+
fromHex,
|
|
20
|
+
hkdfSha256,
|
|
21
|
+
textEncoder,
|
|
22
|
+
textDecoder,
|
|
23
|
+
u8,
|
|
24
|
+
} from './primitives';
|
|
25
|
+
import { generateX25519Keypair } from './x25519';
|
|
26
|
+
import {
|
|
27
|
+
generateKyberKeypair,
|
|
28
|
+
kyberEncapsulate,
|
|
29
|
+
kyberDecapsulate,
|
|
30
|
+
isKyberAvailable,
|
|
31
|
+
} from './kyber';
|
|
32
|
+
import {
|
|
33
|
+
ENVELOPE_VERSION,
|
|
34
|
+
ENVELOPE_SUITE,
|
|
35
|
+
ENVELOPE_AEAD,
|
|
36
|
+
assertEnvelopeVersion,
|
|
37
|
+
} from '../version';
|
|
38
|
+
|
|
39
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
40
|
+
// TYPES
|
|
41
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
42
|
+
|
|
43
|
+
export interface HybridIdentity {
|
|
44
|
+
/** Unique identifier */
|
|
45
|
+
id: string;
|
|
46
|
+
/** Display name */
|
|
47
|
+
name: string;
|
|
48
|
+
/** X25519 public key (hex) */
|
|
49
|
+
x25519PubHex: string;
|
|
50
|
+
/** X25519 secret key (hex) - keep private! */
|
|
51
|
+
x25519SecHex: string;
|
|
52
|
+
/** Kyber public key (base64) */
|
|
53
|
+
kyberPubB64: string;
|
|
54
|
+
/** Kyber secret key (base64) - keep private! */
|
|
55
|
+
kyberSecB64: string;
|
|
56
|
+
/** Creation timestamp */
|
|
57
|
+
createdAt: string;
|
|
58
|
+
/** Last rotation timestamp */
|
|
59
|
+
lastRotatedAt?: string;
|
|
60
|
+
/** Key rotation count */
|
|
61
|
+
rotationCount: number;
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
export interface HybridPublicKeys {
|
|
65
|
+
/** X25519 public key (hex) */
|
|
66
|
+
x25519PubHex: string;
|
|
67
|
+
/** Kyber public key (base64) */
|
|
68
|
+
kyberPubB64: string;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
export interface HybridSecretKeys {
|
|
72
|
+
/** X25519 secret key (hex) */
|
|
73
|
+
x25519SecHex: string;
|
|
74
|
+
/** Kyber secret key (base64) */
|
|
75
|
+
kyberSecB64: string;
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
export interface HybridEnvelope {
|
|
79
|
+
/** Version identifier (FROZEN - see pqc-docs/specs/envelope.v1.md) */
|
|
80
|
+
v: typeof ENVELOPE_VERSION;
|
|
81
|
+
/** Algorithm suite */
|
|
82
|
+
suite: typeof ENVELOPE_SUITE;
|
|
83
|
+
/** AEAD algorithm */
|
|
84
|
+
aead: typeof ENVELOPE_AEAD;
|
|
85
|
+
/** X25519 ephemeral public key (hex) */
|
|
86
|
+
x25519Epk: string;
|
|
87
|
+
/** X25519 wrapped content key */
|
|
88
|
+
x25519Wrap: {
|
|
89
|
+
nonce: string;
|
|
90
|
+
wrapped: string;
|
|
91
|
+
};
|
|
92
|
+
/** Kyber KEM ciphertext (base64) */
|
|
93
|
+
kyberKemCt: string;
|
|
94
|
+
/** Kyber wrapped content key */
|
|
95
|
+
kyberWrap: {
|
|
96
|
+
nonce: string;
|
|
97
|
+
wrapped: string;
|
|
98
|
+
};
|
|
99
|
+
/** Content encryption nonce (base64) */
|
|
100
|
+
contentNonce: string;
|
|
101
|
+
/** Encrypted content (base64) */
|
|
102
|
+
ciphertext: string;
|
|
103
|
+
/** Metadata */
|
|
104
|
+
meta: {
|
|
105
|
+
createdAt: string;
|
|
106
|
+
senderName?: string;
|
|
107
|
+
senderId?: string;
|
|
108
|
+
};
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
112
|
+
// HELPERS
|
|
113
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
114
|
+
|
|
115
|
+
function hkdfFlex(ikm: Uint8Array, salt: string, info: string): Uint8Array {
|
|
116
|
+
return hkdfSha256(ikm, { salt: u8(salt), info: u8(info), length: 32 });
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
function generateId(): string {
|
|
120
|
+
const bytes = globalThis.crypto.getRandomValues(new Uint8Array(16));
|
|
121
|
+
return Array.from(bytes).map(b => b.toString(16).padStart(2, '0')).join('');
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
125
|
+
// IDENTITY GENERATION
|
|
126
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
127
|
+
|
|
128
|
+
/**
|
|
129
|
+
* Generate a new hybrid identity with both X25519 and Kyber keys.
|
|
130
|
+
*/
|
|
131
|
+
export async function generateHybridIdentity(name: string): Promise<HybridIdentity | null> {
|
|
132
|
+
// Generate X25519 keypair
|
|
133
|
+
const x25519 = generateX25519Keypair();
|
|
134
|
+
|
|
135
|
+
// Generate Kyber keypair
|
|
136
|
+
const kyber = await generateKyberKeypair();
|
|
137
|
+
if (!kyber) {
|
|
138
|
+
console.error('Kyber key generation failed - library not available');
|
|
139
|
+
return null;
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
return {
|
|
143
|
+
id: generateId(),
|
|
144
|
+
name,
|
|
145
|
+
x25519PubHex: x25519.publicHex,
|
|
146
|
+
x25519SecHex: x25519.secretHex,
|
|
147
|
+
kyberPubB64: kyber.publicB64,
|
|
148
|
+
kyberSecB64: kyber.secretB64,
|
|
149
|
+
createdAt: new Date().toISOString(),
|
|
150
|
+
rotationCount: 0,
|
|
151
|
+
};
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
/**
|
|
155
|
+
* Rotate keys for an existing identity.
|
|
156
|
+
*/
|
|
157
|
+
export async function rotateHybridIdentity(identity: HybridIdentity): Promise<HybridIdentity | null> {
|
|
158
|
+
// Generate new X25519 keypair
|
|
159
|
+
const x25519 = generateX25519Keypair();
|
|
160
|
+
|
|
161
|
+
// Generate new Kyber keypair
|
|
162
|
+
const kyber = await generateKyberKeypair();
|
|
163
|
+
if (!kyber) {
|
|
164
|
+
return null;
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
return {
|
|
168
|
+
...identity,
|
|
169
|
+
x25519PubHex: x25519.publicHex,
|
|
170
|
+
x25519SecHex: x25519.secretHex,
|
|
171
|
+
kyberPubB64: kyber.publicB64,
|
|
172
|
+
kyberSecB64: kyber.secretB64,
|
|
173
|
+
lastRotatedAt: new Date().toISOString(),
|
|
174
|
+
rotationCount: identity.rotationCount + 1,
|
|
175
|
+
};
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
/**
|
|
179
|
+
* Extract public keys from identity.
|
|
180
|
+
*/
|
|
181
|
+
export function getPublicKeys(identity: HybridIdentity): HybridPublicKeys {
|
|
182
|
+
return {
|
|
183
|
+
x25519PubHex: identity.x25519PubHex,
|
|
184
|
+
kyberPubB64: identity.kyberPubB64,
|
|
185
|
+
};
|
|
186
|
+
}
|
|
187
|
+
|
|
188
|
+
/**
|
|
189
|
+
* Extract secret keys from identity.
|
|
190
|
+
*/
|
|
191
|
+
export function getSecretKeys(identity: HybridIdentity): HybridSecretKeys {
|
|
192
|
+
return {
|
|
193
|
+
x25519SecHex: identity.x25519SecHex,
|
|
194
|
+
kyberSecB64: identity.kyberSecB64,
|
|
195
|
+
};
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
199
|
+
// ENCRYPTION
|
|
200
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
201
|
+
|
|
202
|
+
/**
|
|
203
|
+
* Encrypt a message using hybrid X25519 + Kyber encryption.
|
|
204
|
+
*
|
|
205
|
+
* @param plaintext - Message to encrypt (string or bytes)
|
|
206
|
+
* @param recipientPublicKeys - Recipient's public keys
|
|
207
|
+
* @param sender - Optional sender identity for metadata
|
|
208
|
+
*/
|
|
209
|
+
export async function hybridEncrypt(
|
|
210
|
+
plaintext: string | Uint8Array,
|
|
211
|
+
recipientPublicKeys: HybridPublicKeys,
|
|
212
|
+
sender?: { name?: string; id?: string }
|
|
213
|
+
): Promise<HybridEnvelope> {
|
|
214
|
+
const pt = typeof plaintext === 'string' ? textEncoder.encode(plaintext) : plaintext;
|
|
215
|
+
|
|
216
|
+
// 1. Generate random content key (32 bytes)
|
|
217
|
+
const CK = rand32();
|
|
218
|
+
|
|
219
|
+
// 2. Encrypt content with content key
|
|
220
|
+
const contentNonce = rand24();
|
|
221
|
+
const ciphertext = nacl.secretbox(pt, contentNonce, CK);
|
|
222
|
+
|
|
223
|
+
// 3. Wrap content key with X25519 ECDH
|
|
224
|
+
const x25519EphKp = nacl.box.keyPair();
|
|
225
|
+
const recipientX25519Pk = fromHex(recipientPublicKeys.x25519PubHex);
|
|
226
|
+
|
|
227
|
+
const x25519Shared = nacl.scalarMult(x25519EphKp.secretKey, recipientX25519Pk);
|
|
228
|
+
const x25519Kek = hkdfFlex(x25519Shared, 'omnituum/x25519', 'wrap-ck');
|
|
229
|
+
const x25519WrapNonce = rand24();
|
|
230
|
+
const x25519Wrapped = nacl.secretbox(CK, x25519WrapNonce, x25519Kek);
|
|
231
|
+
|
|
232
|
+
// 4. Wrap content key with Kyber KEM
|
|
233
|
+
const kyberResult = await kyberEncapsulate(recipientPublicKeys.kyberPubB64);
|
|
234
|
+
const kyberKek = hkdfFlex(kyberResult.sharedSecret, 'omnituum/kyber', 'wrap-ck');
|
|
235
|
+
const kyberWrapNonce = rand24();
|
|
236
|
+
const kyberWrapped = nacl.secretbox(CK, kyberWrapNonce, kyberKek);
|
|
237
|
+
|
|
238
|
+
return {
|
|
239
|
+
v: ENVELOPE_VERSION,
|
|
240
|
+
suite: ENVELOPE_SUITE,
|
|
241
|
+
aead: ENVELOPE_AEAD,
|
|
242
|
+
x25519Epk: toHex(x25519EphKp.publicKey),
|
|
243
|
+
x25519Wrap: {
|
|
244
|
+
nonce: b64(x25519WrapNonce),
|
|
245
|
+
wrapped: b64(x25519Wrapped),
|
|
246
|
+
},
|
|
247
|
+
kyberKemCt: b64(kyberResult.ciphertext),
|
|
248
|
+
kyberWrap: {
|
|
249
|
+
nonce: b64(kyberWrapNonce),
|
|
250
|
+
wrapped: b64(kyberWrapped),
|
|
251
|
+
},
|
|
252
|
+
contentNonce: b64(contentNonce),
|
|
253
|
+
ciphertext: b64(ciphertext),
|
|
254
|
+
meta: {
|
|
255
|
+
createdAt: new Date().toISOString(),
|
|
256
|
+
senderName: sender?.name,
|
|
257
|
+
senderId: sender?.id,
|
|
258
|
+
},
|
|
259
|
+
};
|
|
260
|
+
}
|
|
261
|
+
|
|
262
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
263
|
+
// DECRYPTION
|
|
264
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
265
|
+
|
|
266
|
+
/**
|
|
267
|
+
* Decrypt a hybrid envelope.
|
|
268
|
+
*
|
|
269
|
+
* Tries Kyber first (post-quantum), falls back to X25519 (classical).
|
|
270
|
+
* Both must be valid for the envelope to be considered secure.
|
|
271
|
+
*
|
|
272
|
+
* @param envelope - Encrypted envelope
|
|
273
|
+
* @param secretKeys - Recipient's secret keys
|
|
274
|
+
* @returns Decrypted plaintext as bytes
|
|
275
|
+
*/
|
|
276
|
+
export async function hybridDecrypt(
|
|
277
|
+
envelope: HybridEnvelope,
|
|
278
|
+
secretKeys: HybridSecretKeys
|
|
279
|
+
): Promise<Uint8Array> {
|
|
280
|
+
// Validate envelope version (throws VersionMismatchError if unsupported)
|
|
281
|
+
const version = envelope.v as string;
|
|
282
|
+
assertEnvelopeVersion(version);
|
|
283
|
+
|
|
284
|
+
let CK: Uint8Array | null = null;
|
|
285
|
+
|
|
286
|
+
// Determine HKDF salt based on envelope version
|
|
287
|
+
const saltPrefix = version === 'pqc-demo.hybrid.v1' ? 'pqc-demo' : 'omnituum';
|
|
288
|
+
|
|
289
|
+
// Try Kyber decapsulation first (post-quantum)
|
|
290
|
+
try {
|
|
291
|
+
const kyberShared = await kyberDecapsulate(envelope.kyberKemCt, secretKeys.kyberSecB64);
|
|
292
|
+
const kyberKek = hkdfFlex(kyberShared, `${saltPrefix}/kyber`, 'wrap-ck');
|
|
293
|
+
CK = nacl.secretbox.open(
|
|
294
|
+
ub64(envelope.kyberWrap.wrapped),
|
|
295
|
+
ub64(envelope.kyberWrap.nonce),
|
|
296
|
+
kyberKek
|
|
297
|
+
);
|
|
298
|
+
if (CK) {
|
|
299
|
+
console.log('[Hybrid] Decrypted using Kyber (post-quantum)');
|
|
300
|
+
}
|
|
301
|
+
} catch (e) {
|
|
302
|
+
console.warn('[Hybrid] Kyber decapsulation failed:', e);
|
|
303
|
+
}
|
|
304
|
+
|
|
305
|
+
// Try X25519 if Kyber failed
|
|
306
|
+
if (!CK) {
|
|
307
|
+
try {
|
|
308
|
+
const ephPk = fromHex(envelope.x25519Epk);
|
|
309
|
+
const sk = fromHex(secretKeys.x25519SecHex);
|
|
310
|
+
const x25519Shared = nacl.scalarMult(sk, ephPk);
|
|
311
|
+
const x25519Kek = hkdfFlex(x25519Shared, `${saltPrefix}/x25519`, 'wrap-ck');
|
|
312
|
+
CK = nacl.secretbox.open(
|
|
313
|
+
ub64(envelope.x25519Wrap.wrapped),
|
|
314
|
+
ub64(envelope.x25519Wrap.nonce),
|
|
315
|
+
x25519Kek
|
|
316
|
+
);
|
|
317
|
+
if (CK) {
|
|
318
|
+
console.log('[Hybrid] Decrypted using X25519 (classical)');
|
|
319
|
+
}
|
|
320
|
+
} catch (e) {
|
|
321
|
+
console.warn('[Hybrid] X25519 decryption failed:', e);
|
|
322
|
+
}
|
|
323
|
+
}
|
|
324
|
+
|
|
325
|
+
if (!CK) {
|
|
326
|
+
throw new Error('Could not unwrap content key with either algorithm');
|
|
327
|
+
}
|
|
328
|
+
|
|
329
|
+
// Decrypt content
|
|
330
|
+
const pt = nacl.secretbox.open(
|
|
331
|
+
ub64(envelope.ciphertext),
|
|
332
|
+
ub64(envelope.contentNonce),
|
|
333
|
+
CK
|
|
334
|
+
);
|
|
335
|
+
|
|
336
|
+
if (!pt) {
|
|
337
|
+
throw new Error('Content authentication failed');
|
|
338
|
+
}
|
|
339
|
+
|
|
340
|
+
return pt;
|
|
341
|
+
}
|
|
342
|
+
|
|
343
|
+
/**
|
|
344
|
+
* Decrypt and decode as UTF-8 string.
|
|
345
|
+
*/
|
|
346
|
+
export async function hybridDecryptToString(
|
|
347
|
+
envelope: HybridEnvelope,
|
|
348
|
+
secretKeys: HybridSecretKeys
|
|
349
|
+
): Promise<string> {
|
|
350
|
+
const pt = await hybridDecrypt(envelope, secretKeys);
|
|
351
|
+
return textDecoder.decode(pt);
|
|
352
|
+
}
|
|
353
|
+
|
|
354
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
355
|
+
// UTILITY EXPORTS
|
|
356
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
357
|
+
|
|
358
|
+
export { isKyberAvailable };
|
|
@@ -0,0 +1,181 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Omnituum PQC Shared - Crypto Exports
|
|
3
|
+
*
|
|
4
|
+
* Unified cryptographic primitives for both Loggie and Omnituum.
|
|
5
|
+
* Browser-compatible, no Node.js dependencies.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
9
|
+
// PRIMITIVES
|
|
10
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
11
|
+
|
|
12
|
+
export {
|
|
13
|
+
textEncoder,
|
|
14
|
+
textDecoder,
|
|
15
|
+
toB64,
|
|
16
|
+
fromB64,
|
|
17
|
+
toHex,
|
|
18
|
+
fromHex,
|
|
19
|
+
b64,
|
|
20
|
+
ub64,
|
|
21
|
+
assertLen,
|
|
22
|
+
rand32,
|
|
23
|
+
rand24,
|
|
24
|
+
rand12,
|
|
25
|
+
randN,
|
|
26
|
+
sha256,
|
|
27
|
+
sha256String,
|
|
28
|
+
hkdfSha256,
|
|
29
|
+
u8,
|
|
30
|
+
} from './primitives';
|
|
31
|
+
|
|
32
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
33
|
+
// NaCl SECRETBOX / BOX
|
|
34
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
35
|
+
|
|
36
|
+
export type { SecretboxPayload, BoxPayload } from './nacl';
|
|
37
|
+
|
|
38
|
+
export {
|
|
39
|
+
secretboxEncrypt,
|
|
40
|
+
secretboxEncryptString,
|
|
41
|
+
secretboxDecrypt,
|
|
42
|
+
secretboxDecryptString,
|
|
43
|
+
secretboxRaw,
|
|
44
|
+
secretboxOpenRaw,
|
|
45
|
+
boxEncrypt,
|
|
46
|
+
boxDecrypt,
|
|
47
|
+
SECRETBOX_KEY_SIZE,
|
|
48
|
+
SECRETBOX_NONCE_SIZE,
|
|
49
|
+
SECRETBOX_OVERHEAD,
|
|
50
|
+
BOX_KEY_SIZE,
|
|
51
|
+
BOX_NONCE_SIZE,
|
|
52
|
+
} from './nacl';
|
|
53
|
+
|
|
54
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
55
|
+
// X25519 (Classical ECDH)
|
|
56
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
57
|
+
|
|
58
|
+
export type {
|
|
59
|
+
X25519Keypair,
|
|
60
|
+
X25519KeypairHex,
|
|
61
|
+
ClassicalWrap,
|
|
62
|
+
} from './x25519';
|
|
63
|
+
|
|
64
|
+
export {
|
|
65
|
+
generateX25519Keypair,
|
|
66
|
+
generateX25519KeypairFromSeed,
|
|
67
|
+
boxWrapWithX25519,
|
|
68
|
+
boxUnwrapWithX25519,
|
|
69
|
+
x25519SharedSecret,
|
|
70
|
+
deriveKeyFromShared,
|
|
71
|
+
} from './x25519';
|
|
72
|
+
|
|
73
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
74
|
+
// KYBER ML-KEM-768 (Post-Quantum KEM)
|
|
75
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
76
|
+
|
|
77
|
+
export type {
|
|
78
|
+
KyberKeypair,
|
|
79
|
+
KyberKeypairB64,
|
|
80
|
+
KyberEncapsulation,
|
|
81
|
+
} from './kyber';
|
|
82
|
+
|
|
83
|
+
export {
|
|
84
|
+
isKyberAvailable,
|
|
85
|
+
generateKyberKeypair,
|
|
86
|
+
kyberEncapsulate,
|
|
87
|
+
kyberDecapsulate,
|
|
88
|
+
kyberWrapKey,
|
|
89
|
+
kyberUnwrapKey,
|
|
90
|
+
} from './kyber';
|
|
91
|
+
|
|
92
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
93
|
+
// DILITHIUM ML-DSA-65 (Post-Quantum Signatures)
|
|
94
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
95
|
+
|
|
96
|
+
export type {
|
|
97
|
+
DilithiumKeypair,
|
|
98
|
+
DilithiumKeypairB64,
|
|
99
|
+
DilithiumSignature,
|
|
100
|
+
} from './dilithium';
|
|
101
|
+
|
|
102
|
+
export {
|
|
103
|
+
isDilithiumAvailable,
|
|
104
|
+
generateDilithiumKeypair,
|
|
105
|
+
generateDilithiumKeypairFromSeed,
|
|
106
|
+
dilithiumSign,
|
|
107
|
+
dilithiumSignRaw,
|
|
108
|
+
dilithiumVerify,
|
|
109
|
+
dilithiumVerifyRaw,
|
|
110
|
+
DILITHIUM_PUBLIC_KEY_SIZE,
|
|
111
|
+
DILITHIUM_SECRET_KEY_SIZE,
|
|
112
|
+
DILITHIUM_SIGNATURE_SIZE,
|
|
113
|
+
DILITHIUM_ALGORITHM,
|
|
114
|
+
} from './dilithium';
|
|
115
|
+
|
|
116
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
117
|
+
// HYBRID ENCRYPTION (X25519 + Kyber768)
|
|
118
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
119
|
+
|
|
120
|
+
export type {
|
|
121
|
+
HybridIdentity,
|
|
122
|
+
HybridPublicKeys,
|
|
123
|
+
HybridSecretKeys,
|
|
124
|
+
HybridEnvelope,
|
|
125
|
+
} from './hybrid';
|
|
126
|
+
|
|
127
|
+
export {
|
|
128
|
+
generateHybridIdentity,
|
|
129
|
+
rotateHybridIdentity,
|
|
130
|
+
getPublicKeys,
|
|
131
|
+
getSecretKeys,
|
|
132
|
+
hybridEncrypt,
|
|
133
|
+
hybridDecrypt,
|
|
134
|
+
hybridDecryptToString,
|
|
135
|
+
} from './hybrid';
|
|
136
|
+
|
|
137
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
138
|
+
// PRIMITIVES (for protocol implementations like noise-kyber)
|
|
139
|
+
// ═══════════════════════════════════════════════════════════════════════════
|
|
140
|
+
|
|
141
|
+
// BLAKE3 hash function
|
|
142
|
+
export {
|
|
143
|
+
blake3,
|
|
144
|
+
blake3Hex,
|
|
145
|
+
blake3Mac,
|
|
146
|
+
blake3DeriveKey,
|
|
147
|
+
BLAKE3_OUTPUT_LENGTH,
|
|
148
|
+
BLAKE3_KEY_LENGTH,
|
|
149
|
+
BLAKE3_BLOCK_SIZE,
|
|
150
|
+
type Blake3Options,
|
|
151
|
+
} from './primitives/blake3';
|
|
152
|
+
|
|
153
|
+
// ChaCha20-Poly1305 AEAD
|
|
154
|
+
export {
|
|
155
|
+
chaCha20Poly1305Encrypt,
|
|
156
|
+
chaCha20Poly1305Decrypt,
|
|
157
|
+
xChaCha20Poly1305Encrypt,
|
|
158
|
+
xChaCha20Poly1305Decrypt,
|
|
159
|
+
createChaCha20Poly1305,
|
|
160
|
+
createXChaCha20Poly1305,
|
|
161
|
+
CHACHA20_KEY_SIZE,
|
|
162
|
+
CHACHA20_NONCE_SIZE,
|
|
163
|
+
XCHACHA20_NONCE_SIZE,
|
|
164
|
+
POLY1305_TAG_SIZE,
|
|
165
|
+
type ChaChaPayload,
|
|
166
|
+
} from './primitives/chacha';
|
|
167
|
+
|
|
168
|
+
// HKDF key derivation
|
|
169
|
+
export {
|
|
170
|
+
hkdfDerive,
|
|
171
|
+
hkdfExtract,
|
|
172
|
+
hkdfExpand,
|
|
173
|
+
hkdfSplitForNoise,
|
|
174
|
+
hkdfTripleSplitForNoise,
|
|
175
|
+
HKDF_SHA256_OUTPUT_SIZE,
|
|
176
|
+
HKDF_SHA512_OUTPUT_SIZE,
|
|
177
|
+
HKDF_SHA256_MAX_OUTPUT,
|
|
178
|
+
HKDF_SHA512_MAX_OUTPUT,
|
|
179
|
+
type HkdfHash,
|
|
180
|
+
type HkdfOptions,
|
|
181
|
+
} from './primitives/hkdf';
|