ec981012a66d0d312d79abb9da9b654ed8fdd01988fe5525de8a5f2c9c565362.json raw

   1  {"ast":null,"code":"\"use strict\";\n\nObject.defineProperty(exports, \"__esModule\", {\n  value: true\n});\nexports.HDKey = exports.HARDENED_OFFSET = void 0;\n/**\n * @module BIP32 hierarchical deterministic (HD) wallets over secp256k1.\n * @example\n * ```js\n * import { HDKey } from \"@scure/bip32\";\n * const hdkey1 = HDKey.fromMasterSeed(seed);\n * const hdkey2 = HDKey.fromExtendedKey(base58key);\n * const hdkey3 = HDKey.fromJSON({ xpriv: string });\n *\n * // props\n * [hdkey1.depth, hdkey1.index, hdkey1.chainCode];\n * console.log(hdkey2.privateKey, hdkey2.publicKey);\n * console.log(hdkey3.derive(\"m/0/2147483647'/1\"));\n * const sig = hdkey3.sign(hash);\n * hdkey3.verify(hash, sig);\n * ```\n */\n/*! scure-bip32 - MIT License (c) 2022 Patricio Palladino, Paul Miller (paulmillr.com) */\nconst modular_1 = require(\"@noble/curves/abstract/modular\");\nconst secp256k1_1 = require(\"@noble/curves/secp256k1\");\nconst hmac_1 = require(\"@noble/hashes/hmac\");\nconst legacy_1 = require(\"@noble/hashes/legacy\");\nconst sha2_1 = require(\"@noble/hashes/sha2\");\nconst utils_1 = require(\"@noble/hashes/utils\");\nconst base_1 = require(\"@scure/base\");\nconst Point = secp256k1_1.secp256k1.ProjectivePoint;\nconst base58check = (0, base_1.createBase58check)(sha2_1.sha256);\nfunction bytesToNumber(bytes) {\n  (0, utils_1.abytes)(bytes);\n  const h = bytes.length === 0 ? '0' : (0, utils_1.bytesToHex)(bytes);\n  return BigInt('0x' + h);\n}\nfunction numberToBytes(num) {\n  if (typeof num !== 'bigint') throw new Error('bigint expected');\n  return (0, utils_1.hexToBytes)(num.toString(16).padStart(64, '0'));\n}\nconst MASTER_SECRET = (0, utils_1.utf8ToBytes)('Bitcoin seed');\n// Bitcoin hardcoded by default\nconst BITCOIN_VERSIONS = {\n  private: 0x0488ade4,\n  public: 0x0488b21e\n};\nexports.HARDENED_OFFSET = 0x80000000;\nconst hash160 = data => (0, legacy_1.ripemd160)((0, sha2_1.sha256)(data));\nconst fromU32 = data => (0, utils_1.createView)(data).getUint32(0, false);\nconst toU32 = n => {\n  if (!Number.isSafeInteger(n) || n < 0 || n > 2 ** 32 - 1) {\n    throw new Error('invalid number, should be from 0 to 2**32-1, got ' + n);\n  }\n  const buf = new Uint8Array(4);\n  (0, utils_1.createView)(buf).setUint32(0, n, false);\n  return buf;\n};\nclass HDKey {\n  get fingerprint() {\n    if (!this.pubHash) {\n      throw new Error('No publicKey set!');\n    }\n    return fromU32(this.pubHash);\n  }\n  get identifier() {\n    return this.pubHash;\n  }\n  get pubKeyHash() {\n    return this.pubHash;\n  }\n  get privateKey() {\n    return this.privKeyBytes || null;\n  }\n  get publicKey() {\n    return this.pubKey || null;\n  }\n  get privateExtendedKey() {\n    const priv = this.privateKey;\n    if (!priv) {\n      throw new Error('No private key');\n    }\n    return base58check.encode(this.serialize(this.versions.private, (0, utils_1.concatBytes)(new Uint8Array([0]), priv)));\n  }\n  get publicExtendedKey() {\n    if (!this.pubKey) {\n      throw new Error('No public key');\n    }\n    return base58check.encode(this.serialize(this.versions.public, this.pubKey));\n  }\n  static fromMasterSeed(seed, versions = BITCOIN_VERSIONS) {\n    (0, utils_1.abytes)(seed);\n    if (8 * seed.length < 128 || 8 * seed.length > 512) {\n      throw new Error('HDKey: seed length must be between 128 and 512 bits; 256 bits is advised, got ' + seed.length);\n    }\n    const I = (0, hmac_1.hmac)(sha2_1.sha512, MASTER_SECRET, seed);\n    return new HDKey({\n      versions,\n      chainCode: I.slice(32),\n      privateKey: I.slice(0, 32)\n    });\n  }\n  static fromExtendedKey(base58key, versions = BITCOIN_VERSIONS) {\n    // => version(4) || depth(1) || fingerprint(4) || index(4) || chain(32) || key(33)\n    const keyBuffer = base58check.decode(base58key);\n    const keyView = (0, utils_1.createView)(keyBuffer);\n    const version = keyView.getUint32(0, false);\n    const opt = {\n      versions,\n      depth: keyBuffer[4],\n      parentFingerprint: keyView.getUint32(5, false),\n      index: keyView.getUint32(9, false),\n      chainCode: keyBuffer.slice(13, 45)\n    };\n    const key = keyBuffer.slice(45);\n    const isPriv = key[0] === 0;\n    if (version !== versions[isPriv ? 'private' : 'public']) {\n      throw new Error('Version mismatch');\n    }\n    if (isPriv) {\n      return new HDKey({\n        ...opt,\n        privateKey: key.slice(1)\n      });\n    } else {\n      return new HDKey({\n        ...opt,\n        publicKey: key\n      });\n    }\n  }\n  static fromJSON(json) {\n    return HDKey.fromExtendedKey(json.xpriv);\n  }\n  constructor(opt) {\n    this.depth = 0;\n    this.index = 0;\n    this.chainCode = null;\n    this.parentFingerprint = 0;\n    if (!opt || typeof opt !== 'object') {\n      throw new Error('HDKey.constructor must not be called directly');\n    }\n    this.versions = opt.versions || BITCOIN_VERSIONS;\n    this.depth = opt.depth || 0;\n    this.chainCode = opt.chainCode || null;\n    this.index = opt.index || 0;\n    this.parentFingerprint = opt.parentFingerprint || 0;\n    if (!this.depth) {\n      if (this.parentFingerprint || this.index) {\n        throw new Error('HDKey: zero depth with non-zero index/parent fingerprint');\n      }\n    }\n    if (opt.publicKey && opt.privateKey) {\n      throw new Error('HDKey: publicKey and privateKey at same time.');\n    }\n    if (opt.privateKey) {\n      if (!secp256k1_1.secp256k1.utils.isValidPrivateKey(opt.privateKey)) {\n        throw new Error('Invalid private key');\n      }\n      this.privKey = typeof opt.privateKey === 'bigint' ? opt.privateKey : bytesToNumber(opt.privateKey);\n      this.privKeyBytes = numberToBytes(this.privKey);\n      this.pubKey = secp256k1_1.secp256k1.getPublicKey(opt.privateKey, true);\n    } else if (opt.publicKey) {\n      this.pubKey = Point.fromHex(opt.publicKey).toRawBytes(true); // force compressed point\n    } else {\n      throw new Error('HDKey: no public or private key provided');\n    }\n    this.pubHash = hash160(this.pubKey);\n  }\n  derive(path) {\n    if (!/^[mM]'?/.test(path)) {\n      throw new Error('Path must start with \"m\" or \"M\"');\n    }\n    if (/^[mM]'?$/.test(path)) {\n      return this;\n    }\n    const parts = path.replace(/^[mM]'?\\//, '').split('/');\n    // tslint:disable-next-line\n    let child = this;\n    for (const c of parts) {\n      const m = /^(\\d+)('?)$/.exec(c);\n      const m1 = m && m[1];\n      if (!m || m.length !== 3 || typeof m1 !== 'string') throw new Error('invalid child index: ' + c);\n      let idx = +m1;\n      if (!Number.isSafeInteger(idx) || idx >= exports.HARDENED_OFFSET) {\n        throw new Error('Invalid index');\n      }\n      // hardened key\n      if (m[2] === \"'\") {\n        idx += exports.HARDENED_OFFSET;\n      }\n      child = child.deriveChild(idx);\n    }\n    return child;\n  }\n  deriveChild(index) {\n    if (!this.pubKey || !this.chainCode) {\n      throw new Error('No publicKey or chainCode set');\n    }\n    let data = toU32(index);\n    if (index >= exports.HARDENED_OFFSET) {\n      // Hardened\n      const priv = this.privateKey;\n      if (!priv) {\n        throw new Error('Could not derive hardened child key');\n      }\n      // Hardened child: 0x00 || ser256(kpar) || ser32(index)\n      data = (0, utils_1.concatBytes)(new Uint8Array([0]), priv, data);\n    } else {\n      // Normal child: serP(point(kpar)) || ser32(index)\n      data = (0, utils_1.concatBytes)(this.pubKey, data);\n    }\n    const I = (0, hmac_1.hmac)(sha2_1.sha512, this.chainCode, data);\n    const childTweak = bytesToNumber(I.slice(0, 32));\n    const chainCode = I.slice(32);\n    if (!secp256k1_1.secp256k1.utils.isValidPrivateKey(childTweak)) {\n      throw new Error('Tweak bigger than curve order');\n    }\n    const opt = {\n      versions: this.versions,\n      chainCode,\n      depth: this.depth + 1,\n      parentFingerprint: this.fingerprint,\n      index\n    };\n    try {\n      // Private parent key -> private child key\n      if (this.privateKey) {\n        const added = (0, modular_1.mod)(this.privKey + childTweak, secp256k1_1.secp256k1.CURVE.n);\n        if (!secp256k1_1.secp256k1.utils.isValidPrivateKey(added)) {\n          throw new Error('The tweak was out of range or the resulted private key is invalid');\n        }\n        opt.privateKey = added;\n      } else {\n        const added = Point.fromHex(this.pubKey).add(Point.fromPrivateKey(childTweak));\n        // Cryptographically impossible: hmac-sha512 preimage would need to be found\n        if (added.equals(Point.ZERO)) {\n          throw new Error('The tweak was equal to negative P, which made the result key invalid');\n        }\n        opt.publicKey = added.toRawBytes(true);\n      }\n      return new HDKey(opt);\n    } catch (err) {\n      return this.deriveChild(index + 1);\n    }\n  }\n  sign(hash) {\n    if (!this.privateKey) {\n      throw new Error('No privateKey set!');\n    }\n    (0, utils_1.abytes)(hash, 32);\n    return secp256k1_1.secp256k1.sign(hash, this.privKey).toCompactRawBytes();\n  }\n  verify(hash, signature) {\n    (0, utils_1.abytes)(hash, 32);\n    (0, utils_1.abytes)(signature, 64);\n    if (!this.publicKey) {\n      throw new Error('No publicKey set!');\n    }\n    let sig;\n    try {\n      sig = secp256k1_1.secp256k1.Signature.fromCompact(signature);\n    } catch (error) {\n      return false;\n    }\n    return secp256k1_1.secp256k1.verify(sig, hash, this.publicKey);\n  }\n  wipePrivateData() {\n    this.privKey = undefined;\n    if (this.privKeyBytes) {\n      this.privKeyBytes.fill(0);\n      this.privKeyBytes = undefined;\n    }\n    return this;\n  }\n  toJSON() {\n    return {\n      xpriv: this.privateExtendedKey,\n      xpub: this.publicExtendedKey\n    };\n  }\n  serialize(version, key) {\n    if (!this.chainCode) {\n      throw new Error('No chainCode set');\n    }\n    (0, utils_1.abytes)(key, 33);\n    // version(4) || depth(1) || fingerprint(4) || index(4) || chain(32) || key(33)\n    return (0, utils_1.concatBytes)(toU32(version), new Uint8Array([this.depth]), toU32(this.parentFingerprint), toU32(this.index), this.chainCode, key);\n  }\n}\nexports.HDKey = HDKey;\n//# sourceMappingURL=index.js.map","map":null,"metadata":{},"sourceType":"script","externalDependencies":[]}