11cb0ef41Sopenharmony_ci'use strict'; 21cb0ef41Sopenharmony_ci 31cb0ef41Sopenharmony_ciconst { 41cb0ef41Sopenharmony_ci FunctionPrototypeCall, 51cb0ef41Sopenharmony_ci} = primordials; 61cb0ef41Sopenharmony_ci 71cb0ef41Sopenharmony_ciconst { Buffer } = require('buffer'); 81cb0ef41Sopenharmony_ci 91cb0ef41Sopenharmony_ciconst { 101cb0ef41Sopenharmony_ci PBKDF2Job, 111cb0ef41Sopenharmony_ci kCryptoJobAsync, 121cb0ef41Sopenharmony_ci kCryptoJobSync, 131cb0ef41Sopenharmony_ci} = internalBinding('crypto'); 141cb0ef41Sopenharmony_ci 151cb0ef41Sopenharmony_ciconst { 161cb0ef41Sopenharmony_ci validateFunction, 171cb0ef41Sopenharmony_ci validateInt32, 181cb0ef41Sopenharmony_ci validateString, 191cb0ef41Sopenharmony_ci} = require('internal/validators'); 201cb0ef41Sopenharmony_ci 211cb0ef41Sopenharmony_ciconst { 221cb0ef41Sopenharmony_ci getArrayBufferOrView, 231cb0ef41Sopenharmony_ci getDefaultEncoding, 241cb0ef41Sopenharmony_ci normalizeHashName, 251cb0ef41Sopenharmony_ci kKeyObject, 261cb0ef41Sopenharmony_ci} = require('internal/crypto/util'); 271cb0ef41Sopenharmony_ci 281cb0ef41Sopenharmony_ciconst { 291cb0ef41Sopenharmony_ci lazyDOMException, 301cb0ef41Sopenharmony_ci promisify, 311cb0ef41Sopenharmony_ci} = require('internal/util'); 321cb0ef41Sopenharmony_ci 331cb0ef41Sopenharmony_cifunction pbkdf2(password, salt, iterations, keylen, digest, callback) { 341cb0ef41Sopenharmony_ci if (typeof digest === 'function') { 351cb0ef41Sopenharmony_ci callback = digest; 361cb0ef41Sopenharmony_ci digest = undefined; 371cb0ef41Sopenharmony_ci } 381cb0ef41Sopenharmony_ci 391cb0ef41Sopenharmony_ci ({ password, salt, iterations, keylen, digest } = 401cb0ef41Sopenharmony_ci check(password, salt, iterations, keylen, digest)); 411cb0ef41Sopenharmony_ci 421cb0ef41Sopenharmony_ci validateFunction(callback, 'callback'); 431cb0ef41Sopenharmony_ci 441cb0ef41Sopenharmony_ci const job = new PBKDF2Job( 451cb0ef41Sopenharmony_ci kCryptoJobAsync, 461cb0ef41Sopenharmony_ci password, 471cb0ef41Sopenharmony_ci salt, 481cb0ef41Sopenharmony_ci iterations, 491cb0ef41Sopenharmony_ci keylen, 501cb0ef41Sopenharmony_ci digest); 511cb0ef41Sopenharmony_ci 521cb0ef41Sopenharmony_ci const encoding = getDefaultEncoding(); 531cb0ef41Sopenharmony_ci job.ondone = (err, result) => { 541cb0ef41Sopenharmony_ci if (err !== undefined) 551cb0ef41Sopenharmony_ci return FunctionPrototypeCall(callback, job, err); 561cb0ef41Sopenharmony_ci const buf = Buffer.from(result); 571cb0ef41Sopenharmony_ci if (encoding === 'buffer') 581cb0ef41Sopenharmony_ci return FunctionPrototypeCall(callback, job, null, buf); 591cb0ef41Sopenharmony_ci FunctionPrototypeCall(callback, job, null, buf.toString(encoding)); 601cb0ef41Sopenharmony_ci }; 611cb0ef41Sopenharmony_ci 621cb0ef41Sopenharmony_ci job.run(); 631cb0ef41Sopenharmony_ci} 641cb0ef41Sopenharmony_ci 651cb0ef41Sopenharmony_cifunction pbkdf2Sync(password, salt, iterations, keylen, digest) { 661cb0ef41Sopenharmony_ci ({ password, salt, iterations, keylen, digest } = 671cb0ef41Sopenharmony_ci check(password, salt, iterations, keylen, digest)); 681cb0ef41Sopenharmony_ci 691cb0ef41Sopenharmony_ci const job = new PBKDF2Job( 701cb0ef41Sopenharmony_ci kCryptoJobSync, 711cb0ef41Sopenharmony_ci password, 721cb0ef41Sopenharmony_ci salt, 731cb0ef41Sopenharmony_ci iterations, 741cb0ef41Sopenharmony_ci keylen, 751cb0ef41Sopenharmony_ci digest); 761cb0ef41Sopenharmony_ci 771cb0ef41Sopenharmony_ci const { 0: err, 1: result } = job.run(); 781cb0ef41Sopenharmony_ci if (err !== undefined) 791cb0ef41Sopenharmony_ci throw err; 801cb0ef41Sopenharmony_ci 811cb0ef41Sopenharmony_ci const buf = Buffer.from(result); 821cb0ef41Sopenharmony_ci const encoding = getDefaultEncoding(); 831cb0ef41Sopenharmony_ci return encoding === 'buffer' ? buf : buf.toString(encoding); 841cb0ef41Sopenharmony_ci} 851cb0ef41Sopenharmony_ci 861cb0ef41Sopenharmony_cifunction check(password, salt, iterations, keylen, digest) { 871cb0ef41Sopenharmony_ci validateString(digest, 'digest'); 881cb0ef41Sopenharmony_ci 891cb0ef41Sopenharmony_ci password = getArrayBufferOrView(password, 'password'); 901cb0ef41Sopenharmony_ci salt = getArrayBufferOrView(salt, 'salt'); 911cb0ef41Sopenharmony_ci // OpenSSL uses a signed int to represent these values, so we are restricted 921cb0ef41Sopenharmony_ci // to the 31-bit range here (which is plenty). 931cb0ef41Sopenharmony_ci validateInt32(iterations, 'iterations', 1); 941cb0ef41Sopenharmony_ci validateInt32(keylen, 'keylen', 0); 951cb0ef41Sopenharmony_ci 961cb0ef41Sopenharmony_ci return { password, salt, iterations, keylen, digest }; 971cb0ef41Sopenharmony_ci} 981cb0ef41Sopenharmony_ci 991cb0ef41Sopenharmony_ciconst pbkdf2Promise = promisify(pbkdf2); 1001cb0ef41Sopenharmony_ciasync function pbkdf2DeriveBits(algorithm, baseKey, length) { 1011cb0ef41Sopenharmony_ci const { iterations, hash, salt } = algorithm; 1021cb0ef41Sopenharmony_ci if (iterations === 0) 1031cb0ef41Sopenharmony_ci throw lazyDOMException( 1041cb0ef41Sopenharmony_ci 'iterations cannot be zero', 1051cb0ef41Sopenharmony_ci 'OperationError'); 1061cb0ef41Sopenharmony_ci 1071cb0ef41Sopenharmony_ci const raw = baseKey[kKeyObject].export(); 1081cb0ef41Sopenharmony_ci 1091cb0ef41Sopenharmony_ci if (length === 0) 1101cb0ef41Sopenharmony_ci throw lazyDOMException('length cannot be zero', 'OperationError'); 1111cb0ef41Sopenharmony_ci if (length === null) 1121cb0ef41Sopenharmony_ci throw lazyDOMException('length cannot be null', 'OperationError'); 1131cb0ef41Sopenharmony_ci if (length % 8) { 1141cb0ef41Sopenharmony_ci throw lazyDOMException( 1151cb0ef41Sopenharmony_ci 'length must be a multiple of 8', 1161cb0ef41Sopenharmony_ci 'OperationError'); 1171cb0ef41Sopenharmony_ci } 1181cb0ef41Sopenharmony_ci 1191cb0ef41Sopenharmony_ci let result; 1201cb0ef41Sopenharmony_ci try { 1211cb0ef41Sopenharmony_ci result = await pbkdf2Promise( 1221cb0ef41Sopenharmony_ci raw, salt, iterations, length / 8, normalizeHashName(hash.name), 1231cb0ef41Sopenharmony_ci ); 1241cb0ef41Sopenharmony_ci } catch (err) { 1251cb0ef41Sopenharmony_ci throw lazyDOMException( 1261cb0ef41Sopenharmony_ci 'The operation failed for an operation-specific reason', 1271cb0ef41Sopenharmony_ci { name: 'OperationError', cause: err }); 1281cb0ef41Sopenharmony_ci } 1291cb0ef41Sopenharmony_ci 1301cb0ef41Sopenharmony_ci return result.buffer; 1311cb0ef41Sopenharmony_ci} 1321cb0ef41Sopenharmony_ci 1331cb0ef41Sopenharmony_cimodule.exports = { 1341cb0ef41Sopenharmony_ci pbkdf2, 1351cb0ef41Sopenharmony_ci pbkdf2Sync, 1361cb0ef41Sopenharmony_ci pbkdf2DeriveBits, 1371cb0ef41Sopenharmony_ci}; 138