11cb0ef41Sopenharmony_ci'use strict'; 21cb0ef41Sopenharmony_ci 31cb0ef41Sopenharmony_ciconst { 41cb0ef41Sopenharmony_ci ArrayBufferIsView, 51cb0ef41Sopenharmony_ci ArrayBufferPrototypeGetByteLength, 61cb0ef41Sopenharmony_ci ArrayPrototypeIncludes, 71cb0ef41Sopenharmony_ci ArrayPrototypePush, 81cb0ef41Sopenharmony_ci BigInt, 91cb0ef41Sopenharmony_ci DataViewPrototypeGetBuffer, 101cb0ef41Sopenharmony_ci DataViewPrototypeGetByteLength, 111cb0ef41Sopenharmony_ci DataViewPrototypeGetByteOffset, 121cb0ef41Sopenharmony_ci FunctionPrototypeBind, 131cb0ef41Sopenharmony_ci Number, 141cb0ef41Sopenharmony_ci ObjectKeys, 151cb0ef41Sopenharmony_ci ObjectPrototypeHasOwnProperty, 161cb0ef41Sopenharmony_ci Promise, 171cb0ef41Sopenharmony_ci StringPrototypeToUpperCase, 181cb0ef41Sopenharmony_ci Symbol, 191cb0ef41Sopenharmony_ci TypedArrayPrototypeGetBuffer, 201cb0ef41Sopenharmony_ci TypedArrayPrototypeGetByteLength, 211cb0ef41Sopenharmony_ci TypedArrayPrototypeGetByteOffset, 221cb0ef41Sopenharmony_ci TypedArrayPrototypeSlice, 231cb0ef41Sopenharmony_ci Uint8Array, 241cb0ef41Sopenharmony_ci} = primordials; 251cb0ef41Sopenharmony_ci 261cb0ef41Sopenharmony_ciconst { 271cb0ef41Sopenharmony_ci getCiphers: _getCiphers, 281cb0ef41Sopenharmony_ci getCurves: _getCurves, 291cb0ef41Sopenharmony_ci getHashes: _getHashes, 301cb0ef41Sopenharmony_ci setEngine: _setEngine, 311cb0ef41Sopenharmony_ci secureHeapUsed: _secureHeapUsed, 321cb0ef41Sopenharmony_ci} = internalBinding('crypto'); 331cb0ef41Sopenharmony_ci 341cb0ef41Sopenharmony_ciconst { getOptionValue } = require('internal/options'); 351cb0ef41Sopenharmony_ci 361cb0ef41Sopenharmony_ciconst { 371cb0ef41Sopenharmony_ci crypto: { 381cb0ef41Sopenharmony_ci ENGINE_METHOD_ALL, 391cb0ef41Sopenharmony_ci }, 401cb0ef41Sopenharmony_ci} = internalBinding('constants'); 411cb0ef41Sopenharmony_ci 421cb0ef41Sopenharmony_ciconst normalizeHashName = require('internal/crypto/hashnames'); 431cb0ef41Sopenharmony_ci 441cb0ef41Sopenharmony_ciconst { 451cb0ef41Sopenharmony_ci hideStackFrames, 461cb0ef41Sopenharmony_ci codes: { 471cb0ef41Sopenharmony_ci ERR_CRYPTO_CUSTOM_ENGINE_NOT_SUPPORTED, 481cb0ef41Sopenharmony_ci ERR_CRYPTO_ENGINE_UNKNOWN, 491cb0ef41Sopenharmony_ci ERR_INVALID_ARG_TYPE, 501cb0ef41Sopenharmony_ci ERR_INVALID_ARG_VALUE, 511cb0ef41Sopenharmony_ci ERR_OUT_OF_RANGE, 521cb0ef41Sopenharmony_ci }, 531cb0ef41Sopenharmony_ci} = require('internal/errors'); 541cb0ef41Sopenharmony_ci 551cb0ef41Sopenharmony_ciconst { 561cb0ef41Sopenharmony_ci validateArray, 571cb0ef41Sopenharmony_ci validateNumber, 581cb0ef41Sopenharmony_ci validateString, 591cb0ef41Sopenharmony_ci} = require('internal/validators'); 601cb0ef41Sopenharmony_ci 611cb0ef41Sopenharmony_ciconst { Buffer } = require('buffer'); 621cb0ef41Sopenharmony_ci 631cb0ef41Sopenharmony_ciconst { 641cb0ef41Sopenharmony_ci cachedResult, 651cb0ef41Sopenharmony_ci filterDuplicateStrings, 661cb0ef41Sopenharmony_ci lazyDOMException, 671cb0ef41Sopenharmony_ci} = require('internal/util'); 681cb0ef41Sopenharmony_ci 691cb0ef41Sopenharmony_ciconst { 701cb0ef41Sopenharmony_ci isDataView, 711cb0ef41Sopenharmony_ci isArrayBufferView, 721cb0ef41Sopenharmony_ci isAnyArrayBuffer, 731cb0ef41Sopenharmony_ci} = require('internal/util/types'); 741cb0ef41Sopenharmony_ci 751cb0ef41Sopenharmony_ciconst kHandle = Symbol('kHandle'); 761cb0ef41Sopenharmony_ciconst kKeyObject = Symbol('kKeyObject'); 771cb0ef41Sopenharmony_ci 781cb0ef41Sopenharmony_cilet defaultEncoding = 'buffer'; 791cb0ef41Sopenharmony_ci 801cb0ef41Sopenharmony_cifunction setDefaultEncoding(val) { 811cb0ef41Sopenharmony_ci defaultEncoding = val; 821cb0ef41Sopenharmony_ci} 831cb0ef41Sopenharmony_ci 841cb0ef41Sopenharmony_cifunction getDefaultEncoding() { 851cb0ef41Sopenharmony_ci return defaultEncoding; 861cb0ef41Sopenharmony_ci} 871cb0ef41Sopenharmony_ci 881cb0ef41Sopenharmony_ci// This is here because many functions accepted binary strings without 891cb0ef41Sopenharmony_ci// any explicit encoding in older versions of node, and we don't want 901cb0ef41Sopenharmony_ci// to break them unnecessarily. 911cb0ef41Sopenharmony_cifunction toBuf(val, encoding) { 921cb0ef41Sopenharmony_ci if (typeof val === 'string') { 931cb0ef41Sopenharmony_ci if (encoding === 'buffer') 941cb0ef41Sopenharmony_ci encoding = 'utf8'; 951cb0ef41Sopenharmony_ci return Buffer.from(val, encoding); 961cb0ef41Sopenharmony_ci } 971cb0ef41Sopenharmony_ci return val; 981cb0ef41Sopenharmony_ci} 991cb0ef41Sopenharmony_ci 1001cb0ef41Sopenharmony_ciconst getCiphers = cachedResult(() => filterDuplicateStrings(_getCiphers())); 1011cb0ef41Sopenharmony_ciconst getHashes = cachedResult(() => filterDuplicateStrings(_getHashes())); 1021cb0ef41Sopenharmony_ciconst getCurves = cachedResult(() => filterDuplicateStrings(_getCurves())); 1031cb0ef41Sopenharmony_ci 1041cb0ef41Sopenharmony_cifunction setEngine(id, flags) { 1051cb0ef41Sopenharmony_ci validateString(id, 'id'); 1061cb0ef41Sopenharmony_ci if (flags) 1071cb0ef41Sopenharmony_ci validateNumber(flags, 'flags'); 1081cb0ef41Sopenharmony_ci flags = flags >>> 0; 1091cb0ef41Sopenharmony_ci 1101cb0ef41Sopenharmony_ci // Use provided engine for everything by default 1111cb0ef41Sopenharmony_ci if (flags === 0) 1121cb0ef41Sopenharmony_ci flags = ENGINE_METHOD_ALL; 1131cb0ef41Sopenharmony_ci 1141cb0ef41Sopenharmony_ci if (typeof _setEngine !== 'function') 1151cb0ef41Sopenharmony_ci throw new ERR_CRYPTO_CUSTOM_ENGINE_NOT_SUPPORTED(); 1161cb0ef41Sopenharmony_ci if (!_setEngine(id, flags)) 1171cb0ef41Sopenharmony_ci throw new ERR_CRYPTO_ENGINE_UNKNOWN(id); 1181cb0ef41Sopenharmony_ci} 1191cb0ef41Sopenharmony_ci 1201cb0ef41Sopenharmony_ciconst getArrayBufferOrView = hideStackFrames((buffer, name, encoding) => { 1211cb0ef41Sopenharmony_ci if (isAnyArrayBuffer(buffer)) 1221cb0ef41Sopenharmony_ci return buffer; 1231cb0ef41Sopenharmony_ci if (typeof buffer === 'string') { 1241cb0ef41Sopenharmony_ci if (encoding === 'buffer') 1251cb0ef41Sopenharmony_ci encoding = 'utf8'; 1261cb0ef41Sopenharmony_ci return Buffer.from(buffer, encoding); 1271cb0ef41Sopenharmony_ci } 1281cb0ef41Sopenharmony_ci if (!isArrayBufferView(buffer)) { 1291cb0ef41Sopenharmony_ci throw new ERR_INVALID_ARG_TYPE( 1301cb0ef41Sopenharmony_ci name, 1311cb0ef41Sopenharmony_ci [ 1321cb0ef41Sopenharmony_ci 'string', 1331cb0ef41Sopenharmony_ci 'ArrayBuffer', 1341cb0ef41Sopenharmony_ci 'Buffer', 1351cb0ef41Sopenharmony_ci 'TypedArray', 1361cb0ef41Sopenharmony_ci 'DataView', 1371cb0ef41Sopenharmony_ci ], 1381cb0ef41Sopenharmony_ci buffer, 1391cb0ef41Sopenharmony_ci ); 1401cb0ef41Sopenharmony_ci } 1411cb0ef41Sopenharmony_ci return buffer; 1421cb0ef41Sopenharmony_ci}); 1431cb0ef41Sopenharmony_ci 1441cb0ef41Sopenharmony_ci// The maximum buffer size that we'll support in the WebCrypto impl 1451cb0ef41Sopenharmony_ciconst kMaxBufferLength = (2 ** 31) - 1; 1461cb0ef41Sopenharmony_ci 1471cb0ef41Sopenharmony_ci// The EC named curves that we currently support via the Web Crypto API. 1481cb0ef41Sopenharmony_ciconst kNamedCurveAliases = { 1491cb0ef41Sopenharmony_ci 'P-256': 'prime256v1', 1501cb0ef41Sopenharmony_ci 'P-384': 'secp384r1', 1511cb0ef41Sopenharmony_ci 'P-521': 'secp521r1', 1521cb0ef41Sopenharmony_ci}; 1531cb0ef41Sopenharmony_ci 1541cb0ef41Sopenharmony_ciconst kAesKeyLengths = [128, 192, 256]; 1551cb0ef41Sopenharmony_ci 1561cb0ef41Sopenharmony_ci// These are the only hash algorithms we currently support via 1571cb0ef41Sopenharmony_ci// the Web Crypto API. 1581cb0ef41Sopenharmony_ciconst kHashTypes = [ 1591cb0ef41Sopenharmony_ci 'SHA-1', 1601cb0ef41Sopenharmony_ci 'SHA-256', 1611cb0ef41Sopenharmony_ci 'SHA-384', 1621cb0ef41Sopenharmony_ci 'SHA-512', 1631cb0ef41Sopenharmony_ci]; 1641cb0ef41Sopenharmony_ci 1651cb0ef41Sopenharmony_ciconst kSupportedAlgorithms = { 1661cb0ef41Sopenharmony_ci 'digest': { 1671cb0ef41Sopenharmony_ci 'SHA-1': null, 1681cb0ef41Sopenharmony_ci 'SHA-256': null, 1691cb0ef41Sopenharmony_ci 'SHA-384': null, 1701cb0ef41Sopenharmony_ci 'SHA-512': null, 1711cb0ef41Sopenharmony_ci }, 1721cb0ef41Sopenharmony_ci 'generateKey': { 1731cb0ef41Sopenharmony_ci 'RSASSA-PKCS1-v1_5': 'RsaHashedKeyGenParams', 1741cb0ef41Sopenharmony_ci 'RSA-PSS': 'RsaHashedKeyGenParams', 1751cb0ef41Sopenharmony_ci 'RSA-OAEP': 'RsaHashedKeyGenParams', 1761cb0ef41Sopenharmony_ci 'ECDSA': 'EcKeyGenParams', 1771cb0ef41Sopenharmony_ci 'ECDH': 'EcKeyGenParams', 1781cb0ef41Sopenharmony_ci 'AES-CTR': 'AesKeyGenParams', 1791cb0ef41Sopenharmony_ci 'AES-CBC': 'AesKeyGenParams', 1801cb0ef41Sopenharmony_ci 'AES-GCM': 'AesKeyGenParams', 1811cb0ef41Sopenharmony_ci 'AES-KW': 'AesKeyGenParams', 1821cb0ef41Sopenharmony_ci 'HMAC': 'HmacKeyGenParams', 1831cb0ef41Sopenharmony_ci 'X25519': null, 1841cb0ef41Sopenharmony_ci 'Ed25519': null, 1851cb0ef41Sopenharmony_ci 'X448': null, 1861cb0ef41Sopenharmony_ci 'Ed448': null, 1871cb0ef41Sopenharmony_ci }, 1881cb0ef41Sopenharmony_ci 'sign': { 1891cb0ef41Sopenharmony_ci 'RSASSA-PKCS1-v1_5': null, 1901cb0ef41Sopenharmony_ci 'RSA-PSS': 'RsaPssParams', 1911cb0ef41Sopenharmony_ci 'ECDSA': 'EcdsaParams', 1921cb0ef41Sopenharmony_ci 'HMAC': null, 1931cb0ef41Sopenharmony_ci 'Ed25519': null, 1941cb0ef41Sopenharmony_ci 'Ed448': 'Ed448Params', 1951cb0ef41Sopenharmony_ci }, 1961cb0ef41Sopenharmony_ci 'verify': { 1971cb0ef41Sopenharmony_ci 'RSASSA-PKCS1-v1_5': null, 1981cb0ef41Sopenharmony_ci 'RSA-PSS': 'RsaPssParams', 1991cb0ef41Sopenharmony_ci 'ECDSA': 'EcdsaParams', 2001cb0ef41Sopenharmony_ci 'HMAC': null, 2011cb0ef41Sopenharmony_ci 'Ed25519': null, 2021cb0ef41Sopenharmony_ci 'Ed448': 'Ed448Params', 2031cb0ef41Sopenharmony_ci }, 2041cb0ef41Sopenharmony_ci 'importKey': { 2051cb0ef41Sopenharmony_ci 'RSASSA-PKCS1-v1_5': 'RsaHashedImportParams', 2061cb0ef41Sopenharmony_ci 'RSA-PSS': 'RsaHashedImportParams', 2071cb0ef41Sopenharmony_ci 'RSA-OAEP': 'RsaHashedImportParams', 2081cb0ef41Sopenharmony_ci 'ECDSA': 'EcKeyImportParams', 2091cb0ef41Sopenharmony_ci 'ECDH': 'EcKeyImportParams', 2101cb0ef41Sopenharmony_ci 'HMAC': 'HmacImportParams', 2111cb0ef41Sopenharmony_ci 'HKDF': null, 2121cb0ef41Sopenharmony_ci 'PBKDF2': null, 2131cb0ef41Sopenharmony_ci 'AES-CTR': null, 2141cb0ef41Sopenharmony_ci 'AES-CBC': null, 2151cb0ef41Sopenharmony_ci 'AES-GCM': null, 2161cb0ef41Sopenharmony_ci 'AES-KW': null, 2171cb0ef41Sopenharmony_ci 'Ed25519': null, 2181cb0ef41Sopenharmony_ci 'X25519': null, 2191cb0ef41Sopenharmony_ci 'Ed448': null, 2201cb0ef41Sopenharmony_ci 'X448': null, 2211cb0ef41Sopenharmony_ci }, 2221cb0ef41Sopenharmony_ci 'deriveBits': { 2231cb0ef41Sopenharmony_ci 'HKDF': 'HkdfParams', 2241cb0ef41Sopenharmony_ci 'PBKDF2': 'Pbkdf2Params', 2251cb0ef41Sopenharmony_ci 'ECDH': 'EcdhKeyDeriveParams', 2261cb0ef41Sopenharmony_ci 'X25519': 'EcdhKeyDeriveParams', 2271cb0ef41Sopenharmony_ci 'X448': 'EcdhKeyDeriveParams', 2281cb0ef41Sopenharmony_ci }, 2291cb0ef41Sopenharmony_ci 'encrypt': { 2301cb0ef41Sopenharmony_ci 'RSA-OAEP': 'RsaOaepParams', 2311cb0ef41Sopenharmony_ci 'AES-CBC': 'AesCbcParams', 2321cb0ef41Sopenharmony_ci 'AES-GCM': 'AesGcmParams', 2331cb0ef41Sopenharmony_ci 'AES-CTR': 'AesCtrParams', 2341cb0ef41Sopenharmony_ci }, 2351cb0ef41Sopenharmony_ci 'decrypt': { 2361cb0ef41Sopenharmony_ci 'RSA-OAEP': 'RsaOaepParams', 2371cb0ef41Sopenharmony_ci 'AES-CBC': 'AesCbcParams', 2381cb0ef41Sopenharmony_ci 'AES-GCM': 'AesGcmParams', 2391cb0ef41Sopenharmony_ci 'AES-CTR': 'AesCtrParams', 2401cb0ef41Sopenharmony_ci }, 2411cb0ef41Sopenharmony_ci 'get key length': { 2421cb0ef41Sopenharmony_ci 'AES-CBC': 'AesDerivedKeyParams', 2431cb0ef41Sopenharmony_ci 'AES-CTR': 'AesDerivedKeyParams', 2441cb0ef41Sopenharmony_ci 'AES-GCM': 'AesDerivedKeyParams', 2451cb0ef41Sopenharmony_ci 'AES-KW': 'AesDerivedKeyParams', 2461cb0ef41Sopenharmony_ci 'HMAC': 'HmacImportParams', 2471cb0ef41Sopenharmony_ci 'HKDF': null, 2481cb0ef41Sopenharmony_ci 'PBKDF2': null, 2491cb0ef41Sopenharmony_ci }, 2501cb0ef41Sopenharmony_ci 'wrapKey': { 2511cb0ef41Sopenharmony_ci 'AES-KW': null, 2521cb0ef41Sopenharmony_ci }, 2531cb0ef41Sopenharmony_ci 'unwrapKey': { 2541cb0ef41Sopenharmony_ci 'AES-KW': null, 2551cb0ef41Sopenharmony_ci }, 2561cb0ef41Sopenharmony_ci}; 2571cb0ef41Sopenharmony_ci 2581cb0ef41Sopenharmony_ciconst simpleAlgorithmDictionaries = { 2591cb0ef41Sopenharmony_ci AesGcmParams: { iv: 'BufferSource', additionalData: 'BufferSource' }, 2601cb0ef41Sopenharmony_ci RsaHashedKeyGenParams: { hash: 'HashAlgorithmIdentifier' }, 2611cb0ef41Sopenharmony_ci EcKeyGenParams: {}, 2621cb0ef41Sopenharmony_ci HmacKeyGenParams: { hash: 'HashAlgorithmIdentifier' }, 2631cb0ef41Sopenharmony_ci RsaPssParams: {}, 2641cb0ef41Sopenharmony_ci EcdsaParams: { hash: 'HashAlgorithmIdentifier' }, 2651cb0ef41Sopenharmony_ci HmacImportParams: { hash: 'HashAlgorithmIdentifier' }, 2661cb0ef41Sopenharmony_ci HkdfParams: { 2671cb0ef41Sopenharmony_ci hash: 'HashAlgorithmIdentifier', 2681cb0ef41Sopenharmony_ci salt: 'BufferSource', 2691cb0ef41Sopenharmony_ci info: 'BufferSource', 2701cb0ef41Sopenharmony_ci }, 2711cb0ef41Sopenharmony_ci Ed448Params: { context: 'BufferSource' }, 2721cb0ef41Sopenharmony_ci Pbkdf2Params: { hash: 'HashAlgorithmIdentifier', salt: 'BufferSource' }, 2731cb0ef41Sopenharmony_ci RsaOaepParams: { label: 'BufferSource' }, 2741cb0ef41Sopenharmony_ci RsaHashedImportParams: { hash: 'HashAlgorithmIdentifier' }, 2751cb0ef41Sopenharmony_ci EcKeyImportParams: {}, 2761cb0ef41Sopenharmony_ci}; 2771cb0ef41Sopenharmony_ci 2781cb0ef41Sopenharmony_cifunction validateMaxBufferLength(data, name) { 2791cb0ef41Sopenharmony_ci if (data.byteLength > kMaxBufferLength) { 2801cb0ef41Sopenharmony_ci throw lazyDOMException( 2811cb0ef41Sopenharmony_ci `${name} must be less than ${kMaxBufferLength + 1} bits`, 2821cb0ef41Sopenharmony_ci 'OperationError'); 2831cb0ef41Sopenharmony_ci } 2841cb0ef41Sopenharmony_ci} 2851cb0ef41Sopenharmony_ci 2861cb0ef41Sopenharmony_cilet webidl; 2871cb0ef41Sopenharmony_ci 2881cb0ef41Sopenharmony_ci// https://w3c.github.io/webcrypto/#algorithm-normalization-normalize-an-algorithm 2891cb0ef41Sopenharmony_ci// adapted for Node.js from Deno's implementation 2901cb0ef41Sopenharmony_ci// https://github.com/denoland/deno/blob/v1.29.1/ext/crypto/00_crypto.js#L195 2911cb0ef41Sopenharmony_cifunction normalizeAlgorithm(algorithm, op) { 2921cb0ef41Sopenharmony_ci if (typeof algorithm === 'string') 2931cb0ef41Sopenharmony_ci return normalizeAlgorithm({ name: algorithm }, op); 2941cb0ef41Sopenharmony_ci 2951cb0ef41Sopenharmony_ci webidl ??= require('internal/crypto/webidl'); 2961cb0ef41Sopenharmony_ci 2971cb0ef41Sopenharmony_ci // 1. 2981cb0ef41Sopenharmony_ci const registeredAlgorithms = kSupportedAlgorithms[op]; 2991cb0ef41Sopenharmony_ci // 2. 3. 3001cb0ef41Sopenharmony_ci const initialAlg = webidl.converters.Algorithm(algorithm, { 3011cb0ef41Sopenharmony_ci prefix: 'Failed to normalize algorithm', 3021cb0ef41Sopenharmony_ci context: 'passed algorithm', 3031cb0ef41Sopenharmony_ci }); 3041cb0ef41Sopenharmony_ci // 4. 3051cb0ef41Sopenharmony_ci let algName = initialAlg.name; 3061cb0ef41Sopenharmony_ci 3071cb0ef41Sopenharmony_ci // 5. 3081cb0ef41Sopenharmony_ci let desiredType; 3091cb0ef41Sopenharmony_ci for (const key in registeredAlgorithms) { 3101cb0ef41Sopenharmony_ci if (!ObjectPrototypeHasOwnProperty(registeredAlgorithms, key)) { 3111cb0ef41Sopenharmony_ci continue; 3121cb0ef41Sopenharmony_ci } 3131cb0ef41Sopenharmony_ci if ( 3141cb0ef41Sopenharmony_ci StringPrototypeToUpperCase(key) === StringPrototypeToUpperCase(algName) 3151cb0ef41Sopenharmony_ci ) { 3161cb0ef41Sopenharmony_ci algName = key; 3171cb0ef41Sopenharmony_ci desiredType = registeredAlgorithms[key]; 3181cb0ef41Sopenharmony_ci } 3191cb0ef41Sopenharmony_ci } 3201cb0ef41Sopenharmony_ci if (desiredType === undefined) 3211cb0ef41Sopenharmony_ci throw lazyDOMException('Unrecognized algorithm name', 'NotSupportedError'); 3221cb0ef41Sopenharmony_ci 3231cb0ef41Sopenharmony_ci // Fast path everything below if the registered dictionary is null 3241cb0ef41Sopenharmony_ci if (desiredType === null) 3251cb0ef41Sopenharmony_ci return { name: algName }; 3261cb0ef41Sopenharmony_ci 3271cb0ef41Sopenharmony_ci // 6. 3281cb0ef41Sopenharmony_ci const normalizedAlgorithm = webidl.converters[desiredType](algorithm, { 3291cb0ef41Sopenharmony_ci prefix: 'Failed to normalize algorithm', 3301cb0ef41Sopenharmony_ci context: 'passed algorithm', 3311cb0ef41Sopenharmony_ci }); 3321cb0ef41Sopenharmony_ci // 7. 3331cb0ef41Sopenharmony_ci normalizedAlgorithm.name = algName; 3341cb0ef41Sopenharmony_ci 3351cb0ef41Sopenharmony_ci // 9. 3361cb0ef41Sopenharmony_ci const dict = simpleAlgorithmDictionaries[desiredType]; 3371cb0ef41Sopenharmony_ci // 10. 3381cb0ef41Sopenharmony_ci const dictKeys = dict ? ObjectKeys(dict) : []; 3391cb0ef41Sopenharmony_ci for (let i = 0; i < dictKeys.length; i++) { 3401cb0ef41Sopenharmony_ci const member = dictKeys[i]; 3411cb0ef41Sopenharmony_ci if (!ObjectPrototypeHasOwnProperty(dict, member)) 3421cb0ef41Sopenharmony_ci continue; 3431cb0ef41Sopenharmony_ci const idlType = dict[member]; 3441cb0ef41Sopenharmony_ci const idlValue = normalizedAlgorithm[member]; 3451cb0ef41Sopenharmony_ci // 3. 3461cb0ef41Sopenharmony_ci if (idlType === 'BufferSource' && idlValue) { 3471cb0ef41Sopenharmony_ci const isView = ArrayBufferIsView(idlValue); 3481cb0ef41Sopenharmony_ci normalizedAlgorithm[member] = TypedArrayPrototypeSlice( 3491cb0ef41Sopenharmony_ci new Uint8Array( 3501cb0ef41Sopenharmony_ci isView ? getDataViewOrTypedArrayBuffer(idlValue) : idlValue, 3511cb0ef41Sopenharmony_ci isView ? getDataViewOrTypedArrayByteOffset(idlValue) : 0, 3521cb0ef41Sopenharmony_ci isView ? getDataViewOrTypedArrayByteLength(idlValue) : ArrayBufferPrototypeGetByteLength(idlValue), 3531cb0ef41Sopenharmony_ci ), 3541cb0ef41Sopenharmony_ci ); 3551cb0ef41Sopenharmony_ci } else if (idlType === 'HashAlgorithmIdentifier') { 3561cb0ef41Sopenharmony_ci normalizedAlgorithm[member] = normalizeAlgorithm(idlValue, 'digest'); 3571cb0ef41Sopenharmony_ci } else if (idlType === 'AlgorithmIdentifier') { 3581cb0ef41Sopenharmony_ci // This extension point is not used by any supported algorithm (yet?) 3591cb0ef41Sopenharmony_ci throw lazyDOMException('Not implemented.', 'NotSupportedError'); 3601cb0ef41Sopenharmony_ci } 3611cb0ef41Sopenharmony_ci } 3621cb0ef41Sopenharmony_ci 3631cb0ef41Sopenharmony_ci return normalizedAlgorithm; 3641cb0ef41Sopenharmony_ci} 3651cb0ef41Sopenharmony_ci 3661cb0ef41Sopenharmony_cifunction getDataViewOrTypedArrayBuffer(V) { 3671cb0ef41Sopenharmony_ci return isDataView(V) ? 3681cb0ef41Sopenharmony_ci DataViewPrototypeGetBuffer(V) : TypedArrayPrototypeGetBuffer(V); 3691cb0ef41Sopenharmony_ci} 3701cb0ef41Sopenharmony_ci 3711cb0ef41Sopenharmony_cifunction getDataViewOrTypedArrayByteOffset(V) { 3721cb0ef41Sopenharmony_ci return isDataView(V) ? 3731cb0ef41Sopenharmony_ci DataViewPrototypeGetByteOffset(V) : TypedArrayPrototypeGetByteOffset(V); 3741cb0ef41Sopenharmony_ci} 3751cb0ef41Sopenharmony_ci 3761cb0ef41Sopenharmony_cifunction getDataViewOrTypedArrayByteLength(V) { 3771cb0ef41Sopenharmony_ci return isDataView(V) ? 3781cb0ef41Sopenharmony_ci DataViewPrototypeGetByteLength(V) : TypedArrayPrototypeGetByteLength(V); 3791cb0ef41Sopenharmony_ci} 3801cb0ef41Sopenharmony_ci 3811cb0ef41Sopenharmony_cifunction hasAnyNotIn(set, checks) { 3821cb0ef41Sopenharmony_ci for (const s of set) 3831cb0ef41Sopenharmony_ci if (!ArrayPrototypeIncludes(checks, s)) 3841cb0ef41Sopenharmony_ci return true; 3851cb0ef41Sopenharmony_ci return false; 3861cb0ef41Sopenharmony_ci} 3871cb0ef41Sopenharmony_ci 3881cb0ef41Sopenharmony_cifunction validateBitLength(length, name, required = false) { 3891cb0ef41Sopenharmony_ci if (length !== undefined || required) { 3901cb0ef41Sopenharmony_ci validateNumber(length, name); 3911cb0ef41Sopenharmony_ci if (length < 0) 3921cb0ef41Sopenharmony_ci throw new ERR_OUT_OF_RANGE(name, '> 0'); 3931cb0ef41Sopenharmony_ci if (length % 8) { 3941cb0ef41Sopenharmony_ci throw new ERR_INVALID_ARG_VALUE( 3951cb0ef41Sopenharmony_ci name, 3961cb0ef41Sopenharmony_ci length, 3971cb0ef41Sopenharmony_ci 'must be a multiple of 8'); 3981cb0ef41Sopenharmony_ci } 3991cb0ef41Sopenharmony_ci } 4001cb0ef41Sopenharmony_ci} 4011cb0ef41Sopenharmony_ci 4021cb0ef41Sopenharmony_cifunction validateByteLength(buf, name, target) { 4031cb0ef41Sopenharmony_ci if (buf.byteLength !== target) { 4041cb0ef41Sopenharmony_ci throw lazyDOMException( 4051cb0ef41Sopenharmony_ci `${name} must contain exactly ${target} bytes`, 4061cb0ef41Sopenharmony_ci 'OperationError'); 4071cb0ef41Sopenharmony_ci } 4081cb0ef41Sopenharmony_ci} 4091cb0ef41Sopenharmony_ci 4101cb0ef41Sopenharmony_ciconst validateByteSource = hideStackFrames((val, name) => { 4111cb0ef41Sopenharmony_ci val = toBuf(val); 4121cb0ef41Sopenharmony_ci 4131cb0ef41Sopenharmony_ci if (isAnyArrayBuffer(val) || isArrayBufferView(val)) 4141cb0ef41Sopenharmony_ci return val; 4151cb0ef41Sopenharmony_ci 4161cb0ef41Sopenharmony_ci throw new ERR_INVALID_ARG_TYPE( 4171cb0ef41Sopenharmony_ci name, 4181cb0ef41Sopenharmony_ci [ 4191cb0ef41Sopenharmony_ci 'string', 4201cb0ef41Sopenharmony_ci 'ArrayBuffer', 4211cb0ef41Sopenharmony_ci 'TypedArray', 4221cb0ef41Sopenharmony_ci 'DataView', 4231cb0ef41Sopenharmony_ci 'Buffer', 4241cb0ef41Sopenharmony_ci ], 4251cb0ef41Sopenharmony_ci val); 4261cb0ef41Sopenharmony_ci}); 4271cb0ef41Sopenharmony_ci 4281cb0ef41Sopenharmony_cifunction onDone(resolve, reject, err, result) { 4291cb0ef41Sopenharmony_ci if (err) { 4301cb0ef41Sopenharmony_ci return reject(lazyDOMException( 4311cb0ef41Sopenharmony_ci 'The operation failed for an operation-specific reason', 4321cb0ef41Sopenharmony_ci { name: 'OperationError', cause: err })); 4331cb0ef41Sopenharmony_ci } 4341cb0ef41Sopenharmony_ci resolve(result); 4351cb0ef41Sopenharmony_ci} 4361cb0ef41Sopenharmony_ci 4371cb0ef41Sopenharmony_cifunction jobPromise(getJob) { 4381cb0ef41Sopenharmony_ci return new Promise((resolve, reject) => { 4391cb0ef41Sopenharmony_ci try { 4401cb0ef41Sopenharmony_ci const job = getJob(); 4411cb0ef41Sopenharmony_ci job.ondone = FunctionPrototypeBind(onDone, job, resolve, reject); 4421cb0ef41Sopenharmony_ci job.run(); 4431cb0ef41Sopenharmony_ci } catch (err) { 4441cb0ef41Sopenharmony_ci onDone(resolve, reject, err); 4451cb0ef41Sopenharmony_ci } 4461cb0ef41Sopenharmony_ci }); 4471cb0ef41Sopenharmony_ci} 4481cb0ef41Sopenharmony_ci 4491cb0ef41Sopenharmony_ci// In WebCrypto, the publicExponent option in RSA is represented as a 4501cb0ef41Sopenharmony_ci// WebIDL "BigInteger"... that is, a Uint8Array that allows an arbitrary 4511cb0ef41Sopenharmony_ci// number of leading zero bits. Our conventional APIs for reading 4521cb0ef41Sopenharmony_ci// an unsigned int from a Buffer are not adequate. The implementation 4531cb0ef41Sopenharmony_ci// here is adapted from the chromium implementation here: 4541cb0ef41Sopenharmony_ci// https://github.com/chromium/chromium/blob/HEAD/third_party/blink/public/platform/web_crypto_algorithm_params.h, but ported to JavaScript 4551cb0ef41Sopenharmony_ci// Returns undefined if the conversion was unsuccessful. 4561cb0ef41Sopenharmony_cifunction bigIntArrayToUnsignedInt(input) { 4571cb0ef41Sopenharmony_ci let result = 0; 4581cb0ef41Sopenharmony_ci 4591cb0ef41Sopenharmony_ci for (let n = 0; n < input.length; ++n) { 4601cb0ef41Sopenharmony_ci const n_reversed = input.length - n - 1; 4611cb0ef41Sopenharmony_ci if (n_reversed >= 4 && input[n]) 4621cb0ef41Sopenharmony_ci return; // Too large 4631cb0ef41Sopenharmony_ci result |= input[n] << 8 * n_reversed; 4641cb0ef41Sopenharmony_ci } 4651cb0ef41Sopenharmony_ci 4661cb0ef41Sopenharmony_ci return result; 4671cb0ef41Sopenharmony_ci} 4681cb0ef41Sopenharmony_ci 4691cb0ef41Sopenharmony_cifunction bigIntArrayToUnsignedBigInt(input) { 4701cb0ef41Sopenharmony_ci let result = 0n; 4711cb0ef41Sopenharmony_ci 4721cb0ef41Sopenharmony_ci for (let n = 0; n < input.length; ++n) { 4731cb0ef41Sopenharmony_ci const n_reversed = input.length - n - 1; 4741cb0ef41Sopenharmony_ci result |= BigInt(input[n]) << 8n * BigInt(n_reversed); 4751cb0ef41Sopenharmony_ci } 4761cb0ef41Sopenharmony_ci 4771cb0ef41Sopenharmony_ci return result; 4781cb0ef41Sopenharmony_ci} 4791cb0ef41Sopenharmony_ci 4801cb0ef41Sopenharmony_cifunction getStringOption(options, key) { 4811cb0ef41Sopenharmony_ci let value; 4821cb0ef41Sopenharmony_ci if (options && (value = options[key]) != null) 4831cb0ef41Sopenharmony_ci validateString(value, `options.${key}`); 4841cb0ef41Sopenharmony_ci return value; 4851cb0ef41Sopenharmony_ci} 4861cb0ef41Sopenharmony_ci 4871cb0ef41Sopenharmony_cifunction getUsagesUnion(usageSet, ...usages) { 4881cb0ef41Sopenharmony_ci const newset = []; 4891cb0ef41Sopenharmony_ci for (let n = 0; n < usages.length; n++) { 4901cb0ef41Sopenharmony_ci if (usageSet.has(usages[n])) 4911cb0ef41Sopenharmony_ci ArrayPrototypePush(newset, usages[n]); 4921cb0ef41Sopenharmony_ci } 4931cb0ef41Sopenharmony_ci return newset; 4941cb0ef41Sopenharmony_ci} 4951cb0ef41Sopenharmony_ci 4961cb0ef41Sopenharmony_cifunction getBlockSize(name) { 4971cb0ef41Sopenharmony_ci switch (name) { 4981cb0ef41Sopenharmony_ci case 'SHA-1': return 512; 4991cb0ef41Sopenharmony_ci case 'SHA-256': return 512; 5001cb0ef41Sopenharmony_ci case 'SHA-384': return 1024; 5011cb0ef41Sopenharmony_ci case 'SHA-512': return 1024; 5021cb0ef41Sopenharmony_ci } 5031cb0ef41Sopenharmony_ci} 5041cb0ef41Sopenharmony_ci 5051cb0ef41Sopenharmony_ciconst kKeyOps = { 5061cb0ef41Sopenharmony_ci sign: 1, 5071cb0ef41Sopenharmony_ci verify: 2, 5081cb0ef41Sopenharmony_ci encrypt: 3, 5091cb0ef41Sopenharmony_ci decrypt: 4, 5101cb0ef41Sopenharmony_ci wrapKey: 5, 5111cb0ef41Sopenharmony_ci unwrapKey: 6, 5121cb0ef41Sopenharmony_ci deriveKey: 7, 5131cb0ef41Sopenharmony_ci deriveBits: 8, 5141cb0ef41Sopenharmony_ci}; 5151cb0ef41Sopenharmony_ci 5161cb0ef41Sopenharmony_cifunction validateKeyOps(keyOps, usagesSet) { 5171cb0ef41Sopenharmony_ci if (keyOps === undefined) return; 5181cb0ef41Sopenharmony_ci validateArray(keyOps, 'keyData.key_ops'); 5191cb0ef41Sopenharmony_ci let flags = 0; 5201cb0ef41Sopenharmony_ci for (let n = 0; n < keyOps.length; n++) { 5211cb0ef41Sopenharmony_ci const op = keyOps[n]; 5221cb0ef41Sopenharmony_ci const op_flag = kKeyOps[op]; 5231cb0ef41Sopenharmony_ci // Skipping unknown key ops 5241cb0ef41Sopenharmony_ci if (op_flag === undefined) 5251cb0ef41Sopenharmony_ci continue; 5261cb0ef41Sopenharmony_ci // Have we seen it already? if so, error 5271cb0ef41Sopenharmony_ci if (flags & (1 << op_flag)) 5281cb0ef41Sopenharmony_ci throw lazyDOMException('Duplicate key operation', 'DataError'); 5291cb0ef41Sopenharmony_ci flags |= (1 << op_flag); 5301cb0ef41Sopenharmony_ci 5311cb0ef41Sopenharmony_ci // TODO(@jasnell): RFC7517 section 4.3 strong recommends validating 5321cb0ef41Sopenharmony_ci // key usage combinations. Specifically, it says that unrelated key 5331cb0ef41Sopenharmony_ci // ops SHOULD NOT be used together. We're not yet validating that here. 5341cb0ef41Sopenharmony_ci } 5351cb0ef41Sopenharmony_ci 5361cb0ef41Sopenharmony_ci if (usagesSet !== undefined) { 5371cb0ef41Sopenharmony_ci for (const use of usagesSet) { 5381cb0ef41Sopenharmony_ci if (!ArrayPrototypeIncludes(keyOps, use)) { 5391cb0ef41Sopenharmony_ci throw lazyDOMException( 5401cb0ef41Sopenharmony_ci 'Key operations and usage mismatch', 5411cb0ef41Sopenharmony_ci 'DataError'); 5421cb0ef41Sopenharmony_ci } 5431cb0ef41Sopenharmony_ci } 5441cb0ef41Sopenharmony_ci } 5451cb0ef41Sopenharmony_ci} 5461cb0ef41Sopenharmony_ci 5471cb0ef41Sopenharmony_cifunction secureHeapUsed() { 5481cb0ef41Sopenharmony_ci const val = _secureHeapUsed(); 5491cb0ef41Sopenharmony_ci if (val === undefined) 5501cb0ef41Sopenharmony_ci return { total: 0, used: 0, utilization: 0, min: 0 }; 5511cb0ef41Sopenharmony_ci const used = Number(_secureHeapUsed()); 5521cb0ef41Sopenharmony_ci const total = Number(getOptionValue('--secure-heap')); 5531cb0ef41Sopenharmony_ci const min = Number(getOptionValue('--secure-heap-min')); 5541cb0ef41Sopenharmony_ci const utilization = used / total; 5551cb0ef41Sopenharmony_ci return { total, used, utilization, min }; 5561cb0ef41Sopenharmony_ci} 5571cb0ef41Sopenharmony_ci 5581cb0ef41Sopenharmony_cimodule.exports = { 5591cb0ef41Sopenharmony_ci getArrayBufferOrView, 5601cb0ef41Sopenharmony_ci getCiphers, 5611cb0ef41Sopenharmony_ci getCurves, 5621cb0ef41Sopenharmony_ci getDataViewOrTypedArrayBuffer, 5631cb0ef41Sopenharmony_ci getDefaultEncoding, 5641cb0ef41Sopenharmony_ci getHashes, 5651cb0ef41Sopenharmony_ci kHandle, 5661cb0ef41Sopenharmony_ci kKeyObject, 5671cb0ef41Sopenharmony_ci setDefaultEncoding, 5681cb0ef41Sopenharmony_ci setEngine, 5691cb0ef41Sopenharmony_ci toBuf, 5701cb0ef41Sopenharmony_ci 5711cb0ef41Sopenharmony_ci kHashTypes, 5721cb0ef41Sopenharmony_ci kNamedCurveAliases, 5731cb0ef41Sopenharmony_ci kAesKeyLengths, 5741cb0ef41Sopenharmony_ci normalizeAlgorithm, 5751cb0ef41Sopenharmony_ci normalizeHashName, 5761cb0ef41Sopenharmony_ci hasAnyNotIn, 5771cb0ef41Sopenharmony_ci validateBitLength, 5781cb0ef41Sopenharmony_ci validateByteLength, 5791cb0ef41Sopenharmony_ci validateByteSource, 5801cb0ef41Sopenharmony_ci validateKeyOps, 5811cb0ef41Sopenharmony_ci jobPromise, 5821cb0ef41Sopenharmony_ci validateMaxBufferLength, 5831cb0ef41Sopenharmony_ci bigIntArrayToUnsignedBigInt, 5841cb0ef41Sopenharmony_ci bigIntArrayToUnsignedInt, 5851cb0ef41Sopenharmony_ci getBlockSize, 5861cb0ef41Sopenharmony_ci getStringOption, 5871cb0ef41Sopenharmony_ci getUsagesUnion, 5881cb0ef41Sopenharmony_ci secureHeapUsed, 5891cb0ef41Sopenharmony_ci}; 590