@naylence/advanced-security 0.3.3 → 0.3.5
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/dist/browser/index.js +7514 -7041
- package/dist/browser/index.js.map +1 -1
- package/dist/cjs/naylence/fame/security/cert/default-ca-service.js +33 -3
- package/dist/cjs/naylence/fame/security/cert/default-ca-service.js.map +1 -1
- package/dist/cjs/naylence/fame/security/cert/index.js.map +1 -1
- package/dist/cjs/naylence/fame/security/cert/util.js +481 -81
- package/dist/cjs/naylence/fame/security/cert/util.js.map +1 -1
- package/dist/cjs/naylence/fame/security/signing/eddsa-envelope-verifier.js +69 -3
- package/dist/cjs/naylence/fame/security/signing/eddsa-envelope-verifier.js.map +1 -1
- package/dist/esm/naylence/fame/security/cert/default-ca-service.js +33 -3
- package/dist/esm/naylence/fame/security/cert/default-ca-service.js.map +1 -1
- package/dist/esm/naylence/fame/security/cert/index.js.map +1 -1
- package/dist/esm/naylence/fame/security/cert/util.js +481 -81
- package/dist/esm/naylence/fame/security/cert/util.js.map +1 -1
- package/dist/esm/naylence/fame/security/signing/eddsa-envelope-verifier.js +36 -3
- package/dist/esm/naylence/fame/security/signing/eddsa-envelope-verifier.js.map +1 -1
- package/dist/types/naylence/fame/security/cert/default-ca-service.d.ts.map +1 -1
- package/dist/types/naylence/fame/security/cert/index.d.ts +1 -1
- package/dist/types/naylence/fame/security/cert/index.d.ts.map +1 -1
- package/dist/types/naylence/fame/security/cert/util.d.ts +13 -23
- package/dist/types/naylence/fame/security/cert/util.d.ts.map +1 -1
- package/dist/types/naylence/fame/security/signing/eddsa-envelope-verifier.d.ts.map +1 -1
- package/package.json +2 -2
|
@@ -1,15 +1,58 @@
|
|
|
1
1
|
import { AsnConvert } from "@peculiar/asn1-schema";
|
|
2
|
-
import { Certificate } from "@peculiar/asn1-x509";
|
|
2
|
+
import { Certificate, NameConstraints, SubjectAlternativeName, id_ce_nameConstraints, id_ce_subjectAltName, } from "@peculiar/asn1-x509";
|
|
3
|
+
import { sha256 } from "@noble/hashes/sha256";
|
|
4
|
+
import { sha512 } from "@noble/hashes/sha2.js";
|
|
5
|
+
import { etc as edEtc, verify as ed25519Verify } from "@noble/ed25519";
|
|
3
6
|
import { getLogger } from "@naylence/runtime";
|
|
4
7
|
const logger = getLogger("naylence.fame.security.cert.util");
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
8
|
+
const CACHE_LIMIT = 512;
|
|
9
|
+
const OID_ED25519 = "1.3.101.112";
|
|
10
|
+
const textEncoder = new TextEncoder();
|
|
11
|
+
const trustCache = new Map();
|
|
12
|
+
export function publicKeyFromX5c(x5c, options = {}) {
|
|
13
|
+
if (!Array.isArray(x5c) || x5c.length === 0) {
|
|
14
|
+
throw new Error("Empty certificate chain");
|
|
15
|
+
}
|
|
16
|
+
const callId = generateCallId();
|
|
17
|
+
const enforceNameConstraints = options.enforceNameConstraints ?? true;
|
|
18
|
+
const trustStorePem = normalizeTrustStoreOption(options.trustStorePem ?? null);
|
|
19
|
+
const returnCertificate = options.returnCertificate ?? false;
|
|
20
|
+
const { parsed, chainBytes } = parseCertificateChain(x5c);
|
|
21
|
+
logger.debug("public_key_from_x5c_called", {
|
|
22
|
+
call_id: callId,
|
|
23
|
+
x5c_count: parsed.length,
|
|
24
|
+
enforce_name_constraints: enforceNameConstraints,
|
|
25
|
+
has_trust_store: Boolean(trustStorePem),
|
|
26
|
+
return_cert: returnCertificate,
|
|
27
|
+
});
|
|
28
|
+
let cacheKey = null;
|
|
29
|
+
if (!returnCertificate) {
|
|
30
|
+
cacheKey = buildCacheKey(chainBytes, trustStorePem, enforceNameConstraints);
|
|
31
|
+
const cached = getCachedPublicKey(cacheKey);
|
|
32
|
+
if (cached) {
|
|
33
|
+
logger.debug("certificate_cache_hit", {
|
|
34
|
+
call_id: callId,
|
|
35
|
+
cache_key: cacheKey,
|
|
36
|
+
});
|
|
37
|
+
return cached;
|
|
38
|
+
}
|
|
39
|
+
logger.debug("certificate_cache_miss", {
|
|
40
|
+
call_id: callId,
|
|
41
|
+
cache_key: cacheKey,
|
|
42
|
+
});
|
|
43
|
+
}
|
|
44
|
+
const validation = validateCertificateChain(parsed, enforceNameConstraints, trustStorePem);
|
|
45
|
+
if (cacheKey) {
|
|
46
|
+
setCachedPublicKey(cacheKey, validation.publicKey, validation.notAfter);
|
|
47
|
+
}
|
|
48
|
+
if (returnCertificate) {
|
|
49
|
+
return {
|
|
50
|
+
publicKey: validation.publicKey.slice(),
|
|
51
|
+
certificate: validation.certificate,
|
|
52
|
+
};
|
|
53
|
+
}
|
|
54
|
+
return validation.publicKey.slice();
|
|
55
|
+
}
|
|
13
56
|
export function validateJwkX5cCertificate(options) {
|
|
14
57
|
const { jwk, trustStorePem = null, enforceNameConstraints = true, strict = true, } = options;
|
|
15
58
|
if (!jwk || typeof jwk !== "object") {
|
|
@@ -32,85 +75,442 @@ export function validateJwkX5cCertificate(options) {
|
|
|
32
75
|
}
|
|
33
76
|
return { isValid: false, error };
|
|
34
77
|
}
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
78
|
+
try {
|
|
79
|
+
publicKeyFromX5c(x5c, {
|
|
80
|
+
trustStorePem,
|
|
81
|
+
enforceNameConstraints,
|
|
82
|
+
});
|
|
83
|
+
return { isValid: true };
|
|
84
|
+
}
|
|
85
|
+
catch (error) {
|
|
86
|
+
const message = error instanceof Error ? error.message : String(error ?? "unknown");
|
|
87
|
+
const normalized = `Certificate validation failed: ${message}`;
|
|
88
|
+
if (strict) {
|
|
89
|
+
throw new Error(normalized);
|
|
90
|
+
}
|
|
91
|
+
return { isValid: false, error: normalized };
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
function validateCertificateChain(parsed, enforceNameConstraints, trustStorePem) {
|
|
95
|
+
const leaf = parsed[0];
|
|
96
|
+
const nowMs = Date.now();
|
|
97
|
+
const notBefore = leaf.certificate.tbsCertificate.validity.notBefore.getTime();
|
|
98
|
+
const notAfter = leaf.certificate.tbsCertificate.validity.notAfter.getTime();
|
|
99
|
+
const notBeforeMs = notBefore.getTime();
|
|
100
|
+
const notAfterMs = notAfter.getTime();
|
|
101
|
+
if (nowMs < notBeforeMs || nowMs > notAfterMs) {
|
|
102
|
+
throw new Error(`Certificate is not currently valid (notBefore: ${notBefore.toISOString()}, notAfter: ${notAfter.toISOString()}, now: ${new Date(nowMs).toISOString()})`);
|
|
103
|
+
}
|
|
104
|
+
const issuers = parsed.slice(1);
|
|
105
|
+
if (enforceNameConstraints && issuers.length > 0) {
|
|
106
|
+
const leafUris = extractUrisFromCert(leaf.certificate);
|
|
107
|
+
validateNameConstraints(issuers, leafUris);
|
|
108
|
+
}
|
|
109
|
+
if (trustStorePem) {
|
|
110
|
+
validateTrustAnchor(parsed, trustStorePem);
|
|
111
|
+
}
|
|
112
|
+
validateChainContinuity(parsed);
|
|
113
|
+
const publicKey = leaf.subjectPublicKey.slice();
|
|
114
|
+
return {
|
|
115
|
+
publicKey,
|
|
116
|
+
certificate: leaf.certificate,
|
|
117
|
+
notAfter,
|
|
118
|
+
};
|
|
119
|
+
}
|
|
120
|
+
function parseCertificateChain(x5c) {
|
|
121
|
+
const parsed = [];
|
|
122
|
+
const derChunks = [];
|
|
123
|
+
for (let index = 0; index < x5c.length; index += 1) {
|
|
124
|
+
const entry = x5c[index];
|
|
125
|
+
if (typeof entry !== "string" || entry.trim().length === 0) {
|
|
126
|
+
throw new Error(`Invalid certificate at index ${index}`);
|
|
127
|
+
}
|
|
128
|
+
let der;
|
|
129
|
+
try {
|
|
130
|
+
der = decodeBase64(entry);
|
|
131
|
+
}
|
|
132
|
+
catch (error) {
|
|
133
|
+
const reason = error instanceof Error ? error.message : String(error);
|
|
134
|
+
throw new Error(`Failed to decode certificate at index ${index}: ${reason}`);
|
|
135
|
+
}
|
|
136
|
+
let certificate;
|
|
137
|
+
try {
|
|
138
|
+
certificate = AsnConvert.parse(der, Certificate);
|
|
139
|
+
}
|
|
140
|
+
catch (error) {
|
|
141
|
+
const reason = error instanceof Error ? error.message : String(error);
|
|
142
|
+
throw new Error(`Failed to parse certificate at index ${index}: ${reason}`);
|
|
143
|
+
}
|
|
144
|
+
parsed.push(createParsedCertificate(certificate, der));
|
|
145
|
+
derChunks.push(der);
|
|
146
|
+
}
|
|
147
|
+
return { parsed, chainBytes: concatBytes(derChunks) };
|
|
148
|
+
}
|
|
149
|
+
function createParsedCertificate(certificate, raw) {
|
|
150
|
+
return {
|
|
151
|
+
raw,
|
|
152
|
+
certificate,
|
|
153
|
+
serialNumber: toHex(new Uint8Array(certificate.tbsCertificate.serialNumber)).toUpperCase(),
|
|
154
|
+
subjectName: serializeName(certificate.tbsCertificate.subject),
|
|
155
|
+
issuerName: serializeName(certificate.tbsCertificate.issuer),
|
|
156
|
+
subjectPublicKey: new Uint8Array(certificate.tbsCertificate.subjectPublicKeyInfo.subjectPublicKey).slice(),
|
|
157
|
+
};
|
|
158
|
+
}
|
|
159
|
+
function extractUrisFromCert(cert) {
|
|
160
|
+
const extension = findExtension(cert, id_ce_subjectAltName);
|
|
161
|
+
if (!extension) {
|
|
162
|
+
return [];
|
|
163
|
+
}
|
|
164
|
+
const subjectAlternativeName = AsnConvert.parse(extension.extnValue.buffer, SubjectAlternativeName);
|
|
165
|
+
const uris = [];
|
|
166
|
+
for (const generalName of subjectAlternativeName) {
|
|
167
|
+
if (generalName.uniformResourceIdentifier) {
|
|
168
|
+
uris.push(generalName.uniformResourceIdentifier);
|
|
169
|
+
}
|
|
170
|
+
}
|
|
171
|
+
return uris;
|
|
172
|
+
}
|
|
173
|
+
function validateNameConstraints(issuers, leafUris) {
|
|
174
|
+
for (const issuer of issuers) {
|
|
175
|
+
const extension = findExtension(issuer.certificate, id_ce_nameConstraints);
|
|
176
|
+
if (!extension) {
|
|
177
|
+
continue;
|
|
178
|
+
}
|
|
179
|
+
const constraints = AsnConvert.parse(extension.extnValue.buffer, NameConstraints);
|
|
180
|
+
if (!constraints.permittedSubtrees) {
|
|
181
|
+
continue;
|
|
182
|
+
}
|
|
183
|
+
const permittedUris = collectPermittedUris(Array.from(constraints.permittedSubtrees));
|
|
184
|
+
if (permittedUris.length === 0) {
|
|
185
|
+
continue;
|
|
186
|
+
}
|
|
187
|
+
for (const uri of leafUris) {
|
|
188
|
+
const allowed = permittedUris.some((prefix) => uri.startsWith(prefix));
|
|
189
|
+
if (!allowed) {
|
|
190
|
+
throw new Error(`URI '${uri}' violates name constraints - not in permitted subtrees: ${permittedUris.join(", ")}`);
|
|
191
|
+
}
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
}
|
|
195
|
+
function collectPermittedUris(subtrees) {
|
|
196
|
+
const uris = [];
|
|
197
|
+
for (const subtree of subtrees) {
|
|
198
|
+
if (subtree.base.uniformResourceIdentifier &&
|
|
199
|
+
subtree.base.uniformResourceIdentifier.length > 0) {
|
|
200
|
+
uris.push(subtree.base.uniformResourceIdentifier);
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
return uris;
|
|
204
|
+
}
|
|
205
|
+
function validateTrustAnchor(chain, trustStorePem) {
|
|
206
|
+
const trustedCerts = parseTrustStore(trustStorePem);
|
|
207
|
+
if (trustedCerts.length === 0) {
|
|
208
|
+
throw new Error("No valid certificates found in trust store");
|
|
209
|
+
}
|
|
210
|
+
logger.debug("trust_anchor_validation_start", {
|
|
211
|
+
chain_length: chain.length,
|
|
212
|
+
trust_store_cert_count: trustedCerts.length,
|
|
42
213
|
});
|
|
43
|
-
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
214
|
+
const chainInfo = chain.map((cert, index) => `[${index}] ${cert.subjectName} (Serial: ${cert.serialNumber})`);
|
|
215
|
+
const trustedInfo = trustedCerts.map((cert, index) => `[${index}] ${cert.subjectName} (Serial: ${cert.serialNumber})`);
|
|
216
|
+
logger.debug("certificate_chain_validation", {
|
|
217
|
+
chain_certificates: chainInfo,
|
|
218
|
+
trust_store_certificates: trustedInfo,
|
|
219
|
+
});
|
|
220
|
+
// Strategy 1: direct trust (exact certificate match)
|
|
221
|
+
for (let i = 0; i < chain.length; i += 1) {
|
|
222
|
+
const cert = chain[i];
|
|
223
|
+
const match = trustedCerts.find((trusted) => trusted.serialNumber === cert.serialNumber &&
|
|
224
|
+
namesEqual(trusted.certificate.tbsCertificate.subject, cert.certificate.tbsCertificate.subject));
|
|
225
|
+
if (match) {
|
|
226
|
+
logger.debug("certificate_chain_trust_validation_passed", {
|
|
227
|
+
matching_serial: match.serialNumber,
|
|
228
|
+
validation_strategy: `direct_trust_cert_${i}`,
|
|
229
|
+
});
|
|
230
|
+
return;
|
|
231
|
+
}
|
|
59
232
|
}
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
233
|
+
const leaf = chain[0];
|
|
234
|
+
// Strategy 2: leaf issuer in trust store
|
|
235
|
+
for (const trusted of trustedCerts) {
|
|
236
|
+
if (namesEqual(trusted.certificate.tbsCertificate.subject, leaf.certificate.tbsCertificate.issuer) &&
|
|
237
|
+
trusted.serialNumber !== leaf.serialNumber) {
|
|
238
|
+
verifyCertificateSignature(leaf.certificate, trusted.certificate);
|
|
239
|
+
logger.debug("certificate_chain_trust_validation_passed", {
|
|
240
|
+
matching_serial: trusted.serialNumber,
|
|
241
|
+
validation_strategy: "leaf_issuer_trust",
|
|
242
|
+
});
|
|
243
|
+
return;
|
|
244
|
+
}
|
|
64
245
|
}
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
246
|
+
// Strategy 3: any intermediate issuer in trust store
|
|
247
|
+
for (let index = 1; index < chain.length; index += 1) {
|
|
248
|
+
const intermediate = chain[index];
|
|
249
|
+
for (const trusted of trustedCerts) {
|
|
250
|
+
if (namesEqual(trusted.certificate.tbsCertificate.subject, intermediate.certificate.tbsCertificate.issuer) &&
|
|
251
|
+
trusted.serialNumber !== intermediate.serialNumber) {
|
|
252
|
+
verifyCertificateSignature(intermediate.certificate, trusted.certificate);
|
|
253
|
+
logger.debug("certificate_chain_trust_validation_passed", {
|
|
254
|
+
matching_serial: trusted.serialNumber,
|
|
255
|
+
validation_strategy: `intermediate_issuer_trust_cert_${index}`,
|
|
256
|
+
});
|
|
257
|
+
return;
|
|
258
|
+
}
|
|
259
|
+
}
|
|
68
260
|
}
|
|
69
|
-
|
|
70
|
-
|
|
261
|
+
logger.warning("certificate_chain_trust_validation_failed", {
|
|
262
|
+
leaf_subject: leaf.subjectName,
|
|
263
|
+
leaf_issuer: leaf.issuerName,
|
|
264
|
+
leaf_serial: leaf.serialNumber,
|
|
265
|
+
trusted_certificates: trustedInfo,
|
|
266
|
+
chain_certificates: chainInfo,
|
|
267
|
+
reason: "no_matching_trust_anchor",
|
|
268
|
+
});
|
|
269
|
+
throw new Error("Certificate chain is not rooted in a trusted anchor");
|
|
270
|
+
}
|
|
271
|
+
function parseTrustStore(trustStorePem) {
|
|
272
|
+
const normalized = normalizePem(trustStorePem);
|
|
273
|
+
const blocks = extractPemBlocks(normalized);
|
|
274
|
+
const parsed = [];
|
|
275
|
+
for (const block of blocks) {
|
|
276
|
+
try {
|
|
277
|
+
const der = decodeBase64(block);
|
|
278
|
+
const certificate = AsnConvert.parse(der, Certificate);
|
|
279
|
+
parsed.push(createParsedCertificate(certificate, der));
|
|
280
|
+
}
|
|
281
|
+
catch (error) {
|
|
282
|
+
const reason = error instanceof Error ? error.message : String(error);
|
|
283
|
+
logger.debug("trust_store_certificate_parse_failed", { reason });
|
|
284
|
+
}
|
|
71
285
|
}
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
286
|
+
return parsed;
|
|
287
|
+
}
|
|
288
|
+
function extractPemBlocks(pem) {
|
|
289
|
+
const blocks = [];
|
|
290
|
+
const regex = /-----BEGIN CERTIFICATE-----([\s\S]*?)-----END CERTIFICATE-----/gu;
|
|
291
|
+
let match;
|
|
292
|
+
// eslint-disable-next-line no-cond-assign
|
|
293
|
+
while ((match = regex.exec(pem)) !== null) {
|
|
294
|
+
const body = match[1] ?? "";
|
|
295
|
+
blocks.push(body.replace(/\s+/gu, ""));
|
|
76
296
|
}
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
const notBefore = cert.tbsCertificate.validity.notBefore;
|
|
83
|
-
const notAfter = cert.tbsCertificate.validity.notAfter;
|
|
84
|
-
// Time from ASN.1 has getTime() method returning Date object
|
|
85
|
-
const notBeforeDate = notBefore.getTime();
|
|
86
|
-
const notAfterDate = notAfter.getTime();
|
|
87
|
-
const notBeforeMs = notBeforeDate instanceof Date
|
|
88
|
-
? notBeforeDate.getTime()
|
|
89
|
-
: Number(notBeforeDate);
|
|
90
|
-
const notAfterMs = notAfterDate instanceof Date
|
|
91
|
-
? notAfterDate.getTime()
|
|
92
|
-
: Number(notAfterDate);
|
|
93
|
-
if (now < notBeforeMs || now > notAfterMs) {
|
|
94
|
-
throw new Error(`Certificate is not currently valid (notBefore: ${new Date(notBeforeMs).toISOString()}, notAfter: ${new Date(notAfterMs).toISOString()}, now: ${new Date(now).toISOString()})`);
|
|
95
|
-
}
|
|
96
|
-
// TODO: Implement name constraints validation when enforceNameConstraints is true
|
|
97
|
-
if (options.enforceNameConstraints) {
|
|
98
|
-
logger.debug("name_constraints_validation_not_implemented", {
|
|
99
|
-
enforcement_requested: true,
|
|
100
|
-
});
|
|
297
|
+
return blocks;
|
|
298
|
+
}
|
|
299
|
+
function validateChainContinuity(chain) {
|
|
300
|
+
if (chain.length <= 1) {
|
|
301
|
+
return;
|
|
101
302
|
}
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
303
|
+
logger.debug("validating_chain_continuity", { chain_length: chain.length });
|
|
304
|
+
for (let index = 0; index < chain.length - 1; index += 1) {
|
|
305
|
+
const cert = chain[index];
|
|
306
|
+
const issuer = chain[index + 1];
|
|
307
|
+
if (!namesEqual(cert.certificate.tbsCertificate.issuer, issuer.certificate.tbsCertificate.subject)) {
|
|
308
|
+
logger.warning("certificate_chain_continuity_failed", {
|
|
309
|
+
cert_index: index,
|
|
310
|
+
cert_subject: cert.subjectName,
|
|
311
|
+
cert_issuer: cert.issuerName,
|
|
312
|
+
expected_issuer_subject: issuer.subjectName,
|
|
313
|
+
reason: "issuer_name_mismatch",
|
|
314
|
+
});
|
|
315
|
+
throw new Error(`Certificate chain continuity broken: certificate at index ${index} issuer does not match next certificate subject`);
|
|
316
|
+
}
|
|
317
|
+
try {
|
|
318
|
+
verifyCertificateSignature(cert.certificate, issuer.certificate);
|
|
319
|
+
logger.debug("chain_continuity_verification_success", {
|
|
320
|
+
cert_index: index,
|
|
321
|
+
cert_serial: cert.serialNumber,
|
|
322
|
+
issuer_serial: issuer.serialNumber,
|
|
323
|
+
});
|
|
324
|
+
}
|
|
325
|
+
catch (error) {
|
|
326
|
+
const reason = error instanceof Error ? error.message : String(error);
|
|
327
|
+
logger.warning("certificate_chain_continuity_failed", {
|
|
328
|
+
cert_index: index,
|
|
329
|
+
cert_subject: cert.subjectName,
|
|
330
|
+
issuer_subject: issuer.subjectName,
|
|
331
|
+
cert_serial: cert.serialNumber,
|
|
332
|
+
issuer_serial: issuer.serialNumber,
|
|
333
|
+
error: reason,
|
|
334
|
+
reason: "signature_verification_failed",
|
|
335
|
+
});
|
|
336
|
+
throw new Error(`Certificate chain continuity broken: certificate at index ${index} was not signed by certificate at index ${index + 1}: ${reason}`);
|
|
337
|
+
}
|
|
338
|
+
}
|
|
339
|
+
logger.debug("chain_continuity_validation_passed", {
|
|
340
|
+
chain_length: chain.length,
|
|
341
|
+
});
|
|
342
|
+
}
|
|
343
|
+
function verifyCertificateSignature(certificate, issuer) {
|
|
344
|
+
ensureEd25519Support();
|
|
345
|
+
const signatureAlgorithm = certificate.signatureAlgorithm.algorithm;
|
|
346
|
+
const issuerAlgorithm = issuer.tbsCertificate.subjectPublicKeyInfo.algorithm.algorithm;
|
|
347
|
+
if (signatureAlgorithm !== OID_ED25519 || issuerAlgorithm !== OID_ED25519) {
|
|
348
|
+
throw new Error(`Unsupported signature algorithm (certificate: ${signatureAlgorithm}, issuer: ${issuerAlgorithm})`);
|
|
349
|
+
}
|
|
350
|
+
const signatureBytes = new Uint8Array(certificate.signatureValue);
|
|
351
|
+
const tbsBytes = new Uint8Array(AsnConvert.serialize(certificate.tbsCertificate));
|
|
352
|
+
const issuerKey = new Uint8Array(issuer.tbsCertificate.subjectPublicKeyInfo.subjectPublicKey);
|
|
353
|
+
if (issuerKey.length !== 32) {
|
|
354
|
+
throw new Error("Issuer Ed25519 public key must be 32 bytes");
|
|
355
|
+
}
|
|
356
|
+
const valid = ed25519Verify(signatureBytes, tbsBytes, issuerKey);
|
|
357
|
+
if (!valid) {
|
|
358
|
+
throw new Error("Certificate signature verification failed");
|
|
359
|
+
}
|
|
360
|
+
}
|
|
361
|
+
function ensureEd25519Support() {
|
|
362
|
+
const etcPatch = edEtc;
|
|
363
|
+
if (!etcPatch.sha512) {
|
|
364
|
+
etcPatch.sha512 = (message) => sha512(message);
|
|
365
|
+
}
|
|
366
|
+
if (!etcPatch.sha512Sync) {
|
|
367
|
+
etcPatch.sha512Sync = (...messages) => {
|
|
368
|
+
if (messages.length === 1) {
|
|
369
|
+
return sha512(messages[0]);
|
|
370
|
+
}
|
|
371
|
+
const combined = edEtc.concatBytes(...messages);
|
|
372
|
+
return sha512(combined);
|
|
373
|
+
};
|
|
374
|
+
}
|
|
375
|
+
}
|
|
376
|
+
function findExtension(certificate, oid) {
|
|
377
|
+
const extensions = certificate.tbsCertificate.extensions;
|
|
378
|
+
if (!extensions) {
|
|
379
|
+
return null;
|
|
380
|
+
}
|
|
381
|
+
for (const extension of extensions) {
|
|
382
|
+
if (extension.extnID === oid) {
|
|
383
|
+
return extension;
|
|
384
|
+
}
|
|
385
|
+
}
|
|
386
|
+
return null;
|
|
387
|
+
}
|
|
388
|
+
function namesEqual(a, b) {
|
|
389
|
+
const left = new Uint8Array(AsnConvert.serialize(a));
|
|
390
|
+
const right = new Uint8Array(AsnConvert.serialize(b));
|
|
391
|
+
if (left.length !== right.length) {
|
|
392
|
+
return false;
|
|
107
393
|
}
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
394
|
+
for (let i = 0; i < left.length; i += 1) {
|
|
395
|
+
if (left[i] !== right[i]) {
|
|
396
|
+
return false;
|
|
397
|
+
}
|
|
398
|
+
}
|
|
399
|
+
return true;
|
|
400
|
+
}
|
|
401
|
+
function serializeName(name) {
|
|
402
|
+
const rdns = Array.from(name);
|
|
403
|
+
return rdns
|
|
404
|
+
.map((rdn) => Array.from(rdn)
|
|
405
|
+
.map((attr) => `${oidToLabel(attr.type)}=${attr.value.toString()}`)
|
|
406
|
+
.join("+"))
|
|
407
|
+
.join(",");
|
|
408
|
+
}
|
|
409
|
+
function oidToLabel(oid) {
|
|
410
|
+
switch (oid) {
|
|
411
|
+
case "2.5.4.3":
|
|
412
|
+
return "CN";
|
|
413
|
+
case "2.5.4.6":
|
|
414
|
+
return "C";
|
|
415
|
+
case "2.5.4.7":
|
|
416
|
+
return "L";
|
|
417
|
+
case "2.5.4.8":
|
|
418
|
+
return "ST";
|
|
419
|
+
case "2.5.4.10":
|
|
420
|
+
return "O";
|
|
421
|
+
case "2.5.4.11":
|
|
422
|
+
return "OU";
|
|
423
|
+
default:
|
|
424
|
+
return oid;
|
|
425
|
+
}
|
|
426
|
+
}
|
|
427
|
+
function concatBytes(chunks) {
|
|
428
|
+
const totalLength = chunks.reduce((sum, chunk) => sum + chunk.length, 0);
|
|
429
|
+
const result = new Uint8Array(totalLength);
|
|
430
|
+
let offset = 0;
|
|
431
|
+
for (const chunk of chunks) {
|
|
432
|
+
result.set(chunk, offset);
|
|
433
|
+
offset += chunk.length;
|
|
434
|
+
}
|
|
435
|
+
return result;
|
|
436
|
+
}
|
|
437
|
+
function decodeBase64(input) {
|
|
438
|
+
if (typeof Buffer !== "undefined") {
|
|
439
|
+
const normalized = input.replace(/\s+/gu, "");
|
|
440
|
+
return new Uint8Array(Buffer.from(normalized, "base64"));
|
|
441
|
+
}
|
|
442
|
+
if (typeof atob === "function") {
|
|
443
|
+
const normalized = input.replace(/\s+/gu, "");
|
|
444
|
+
const binary = atob(normalized);
|
|
445
|
+
const bytes = new Uint8Array(binary.length);
|
|
446
|
+
for (let i = 0; i < binary.length; i += 1) {
|
|
447
|
+
bytes[i] = binary.charCodeAt(i);
|
|
448
|
+
}
|
|
449
|
+
return bytes;
|
|
450
|
+
}
|
|
451
|
+
throw new Error("No base64 decoder available in this environment");
|
|
452
|
+
}
|
|
453
|
+
function toHex(data) {
|
|
454
|
+
return Array.from(data)
|
|
455
|
+
.map((byte) => byte.toString(16).padStart(2, "0"))
|
|
456
|
+
.join("");
|
|
457
|
+
}
|
|
458
|
+
function buildCacheKey(chainBytes, trustStorePem, enforceNameConstraints) {
|
|
459
|
+
const chainHash = toHex(sha256(chainBytes));
|
|
460
|
+
const trustHash = trustStorePem
|
|
461
|
+
? toHex(sha256(textEncoder.encode(trustStorePem)))
|
|
462
|
+
: "no-trust";
|
|
463
|
+
const constraintFlag = enforceNameConstraints ? "nc1" : "nc0";
|
|
464
|
+
return `${chainHash}|${trustHash}|${constraintFlag}`;
|
|
465
|
+
}
|
|
466
|
+
function getCachedPublicKey(cacheKey) {
|
|
467
|
+
const entry = trustCache.get(cacheKey);
|
|
468
|
+
if (!entry) {
|
|
469
|
+
return null;
|
|
470
|
+
}
|
|
471
|
+
if (Date.now() > entry.expiresAt) {
|
|
472
|
+
trustCache.delete(cacheKey);
|
|
473
|
+
logger.debug("certificate_cache_expired", { cache_key: cacheKey });
|
|
474
|
+
return null;
|
|
475
|
+
}
|
|
476
|
+
return entry.value.slice();
|
|
477
|
+
}
|
|
478
|
+
function setCachedPublicKey(cacheKey, value, notAfter) {
|
|
479
|
+
while (trustCache.size >= CACHE_LIMIT) {
|
|
480
|
+
const firstKey = trustCache.keys().next().value;
|
|
481
|
+
if (firstKey === undefined) {
|
|
482
|
+
break;
|
|
483
|
+
}
|
|
484
|
+
trustCache.delete(firstKey);
|
|
485
|
+
logger.debug("certificate_cache_evicted", { cache_key: firstKey });
|
|
486
|
+
}
|
|
487
|
+
trustCache.set(cacheKey, {
|
|
488
|
+
value: value.slice(),
|
|
489
|
+
expiresAt: notAfter.getTime(),
|
|
490
|
+
});
|
|
491
|
+
logger.debug("certificate_cache_stored", {
|
|
492
|
+
cache_key: cacheKey,
|
|
493
|
+
expires_at: notAfter.toISOString(),
|
|
494
|
+
cache_size: trustCache.size,
|
|
495
|
+
});
|
|
496
|
+
}
|
|
497
|
+
function normalizeTrustStoreOption(value) {
|
|
498
|
+
if (!value) {
|
|
499
|
+
return null;
|
|
500
|
+
}
|
|
501
|
+
const trimmed = value.trim();
|
|
502
|
+
if (trimmed.length === 0) {
|
|
503
|
+
return null;
|
|
504
|
+
}
|
|
505
|
+
if (!trimmed.includes("-----BEGIN CERTIFICATE-----")) {
|
|
506
|
+
throw new Error("trustStorePem must contain PEM-encoded certificates when provided");
|
|
507
|
+
}
|
|
508
|
+
return normalizePem(trimmed);
|
|
509
|
+
}
|
|
510
|
+
function normalizePem(pem) {
|
|
511
|
+
return pem.replace(/\r/gu, "").trim();
|
|
512
|
+
}
|
|
513
|
+
function generateCallId() {
|
|
514
|
+
return Math.random().toString(36).slice(2, 10);
|
|
115
515
|
}
|
|
116
516
|
//# sourceMappingURL=util.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"util.js","sourceRoot":"","sources":["../../../../../../src/naylence/fame/security/cert/util.ts"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"util.js","sourceRoot":"","sources":["../../../../../../src/naylence/fame/security/cert/util.ts"],"names":[],"mappings":"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"}
|