@ethereumjs/ethash
Advanced tools
Comparing version 2.1.0 to 3.0.0-rc.1
{ | ||
"name": "@ethereumjs/ethash", | ||
"version": "2.1.0", | ||
"description": "An ethash implementation in JavaScript", | ||
"version": "3.0.0-rc.1", | ||
"description": "An implementation of the Ethash consensus algorithm in JavaScript", | ||
"keywords": [ | ||
@@ -20,4 +20,11 @@ "ethash", | ||
"author": "mjbecze <mjbecze@gmail.com>", | ||
"main": "dist/index.js", | ||
"types": "dist/index.d.ts", | ||
"type": "module", | ||
"main": "dist/cjs/index.js", | ||
"module": "dist/esm/index.js", | ||
"exports": { | ||
".": { | ||
"import": "./dist/esm/index.js", | ||
"require": "./dist/cjs/index.js" | ||
} | ||
}, | ||
"files": [ | ||
@@ -30,4 +37,5 @@ "dist", | ||
"clean": "../../config/cli/clean-package.sh", | ||
"coverage": "../../config/cli/coverage.sh", | ||
"docs:build": "typedoc --options typedoc.js", | ||
"coverage": "npx vitest run --coverage.enabled --coverage.reporter=lcov", | ||
"docs:build": "typedoc --options typedoc.cjs", | ||
"examples": "ts-node ../../scripts/examples-runner.ts -- ethash", | ||
"lint": "../../config/cli/lint.sh", | ||
@@ -37,20 +45,18 @@ "lint:diff": "../../config/cli/lint-diff.sh", | ||
"prepublishOnly": "../../config/cli/prepublish.sh", | ||
"test": "tape -r ts-node/register test/*.spec.ts", | ||
"test": "npx vitest run", | ||
"tsc": "../../config/cli/ts-compile.sh" | ||
}, | ||
"dependencies": { | ||
"@ethereumjs/block": "^4.3.0", | ||
"@ethereumjs/rlp": "^4.0.1", | ||
"@ethereumjs/util": "^8.1.0", | ||
"abstract-level": "^1.0.3", | ||
"@ethereumjs/block": "5.0.0-rc.1", | ||
"@ethereumjs/rlp": "5.0.0-rc.1", | ||
"@ethereumjs/util": "9.0.0-rc.1", | ||
"bigint-crypto-utils": "^3.2.2", | ||
"ethereum-cryptography": "^2.0.0" | ||
"ethereum-cryptography": "^2.1.2" | ||
}, | ||
"devDependencies": { | ||
"@ethereumjs/common": "^3.2.0", | ||
"memory-level": "^1.0.0" | ||
"@ethereumjs/common": "4.0.0-rc.1" | ||
}, | ||
"engines": { | ||
"node": ">=14" | ||
"node": ">=18" | ||
} | ||
} |
@@ -9,2 +9,4 @@ # @ethereumjs/ethash | ||
Note: this README has been updated containing the changes from our next breaking release round [UNRELEASED] targeted for Summer 2023. See the README files from the [maintenance-v6](https://github.com/ethereumjs/ethereumjs-monorepo/tree/maintenance-v6/) branch for documentation matching our latest releases. | ||
| [Ethash](https://github.com/ethereum/wiki/wiki/Ethash) implementation in TypeScript. | | ||
@@ -30,11 +32,11 @@ | ------------------------------------------------------------------------------------ | | ||
import { Block } from '@ethereumjs/block' | ||
import { MemoryLevel } from 'memory-level' | ||
import { hexToBytes, MapDB } from '@ethereumjs/util' | ||
const cacheDB = level() | ||
const cacheDb = new MapDB<number, DBObject>() | ||
const ethash = new Ethash(cacheDB) | ||
const validblockRlp = | ||
'f90667f905fba0a8d5b7a4793baaede98b5236954f634a0051842df6a252f6a80492fd888678bda01dcc4de8dec75d7aab85b567b6ccd41ad312451b948a7413f0a142fd40d49347948888f1f195afa192cfee860698584c030f4c9db1a0f93c8db1e931daa2e22e39b5d2da6fb4074e3d544094857608536155e3521bc1a0bb7495628f9160ddbcf6354380ee32c300d594e833caec3a428041a66e7bade1a0c7778a7376099ee2e5c455791c1885b5c361b95713fddcbe32d97fd01334d296b90100000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000200000000000000000008000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000200000000000400000000000000000000000000000000000000000000000000000008302000001832fefd882560b84559c17b9b9040001020304050607080910111213141516171819202122232410000000000000000000200000000000000000003000000000000000000040000000000000000000500000000000000000006000000000000000000070000000000000000000800000000000000000009000000000000000000010000000000000000000100000000000000000002000000000000000000030000000000000000000400000000000000000005000000000000000000060000000000000000000700000000000000000008000000000000000000090000000000000000000100000000000000000001000000000000000000020000000000000000000300000000000000000004000000000000000000050000000000000000000600000000000000000007000000000000000000080000000000000000000900000000000000000001000000000000000000010000000000000000000200000000000000000003000000000000000000040000000000000000000500000000000000000006000000000000000000070000000000000000000800000000000000000009000000000000000000010000000000000000000100000000000000000002000000000000000000030000000000000000000400000000000000000005000000000000000000060000000000000000000700000000000000000008000000000000000000090000000000000000000100000000000000000001000000000000000000020000000000000000000300000000000000000004000000000000000000050000000000000000000600000000000000000007000000000000000000080000000000000000000900000000000000000001000000000000000000010000000000000000000200000000000000000003000000000000000000040000000000000000000500000000000000000006000000000000000000070000000000000000000800000000000000000009000000000000000000010000000000000000000100000000000000000002000000000000000000030000000000000000000400000000000000000005000000000000000000060000000000000000000700000000000000000008000000000000000000090000000000000000000100000000000000000001000000000000000000020000000000000000000300000000000000000004000000000000000000050000000000000000000600000000000000000007000000000000000000080000000000000000000900000000000000000001000000000000000000010000000000000000000200000000000000000003000000000000000000040000000000000000000500000000000000000006000000000000000000070000000000000000000800000000000000000009000000000000000000010000000000000000000a09c7b47112a3afb385c12924bf6280d273c106eea7caeaf5131d8776f61056c148876ae05d46b58d1fff866f864800a82c35094095e7baea6a6c7c4c2dfeb977efac326af552d8785012a05f200801ba01d2c92cfaeb04e53acdff2b5d42005ff6aacdb0105e64eb8c30c273f445d2782a01e7d50ffce57840360c57d94977b8cdebde614da23e8d1e77dc07928763cfe21c0' | ||
'0xf90667f905fba0a8d5b7a4793baaede98b5236954f634a0051842df6a252f6a80492fd888678bda01dcc4de8dec75d7aab85b567b6ccd41ad312451b948a7413f0a142fd40d49347948888f1f195afa192cfee860698584c030f4c9db1a0f93c8db1e931daa2e22e39b5d2da6fb4074e3d544094857608536155e3521bc1a0bb7495628f9160ddbcf6354380ee32c300d594e833caec3a428041a66e7bade1a0c7778a7376099ee2e5c455791c1885b5c361b95713fddcbe32d97fd01334d296b90100000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000200000000000000000008000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000200000000000400000000000000000000000000000000000000000000000000000008302000001832fefd882560b84559c17b9b9040001020304050607080910111213141516171819202122232410000000000000000000200000000000000000003000000000000000000040000000000000000000500000000000000000006000000000000000000070000000000000000000800000000000000000009000000000000000000010000000000000000000100000000000000000002000000000000000000030000000000000000000400000000000000000005000000000000000000060000000000000000000700000000000000000008000000000000000000090000000000000000000100000000000000000001000000000000000000020000000000000000000300000000000000000004000000000000000000050000000000000000000600000000000000000007000000000000000000080000000000000000000900000000000000000001000000000000000000010000000000000000000200000000000000000003000000000000000000040000000000000000000500000000000000000006000000000000000000070000000000000000000800000000000000000009000000000000000000010000000000000000000100000000000000000002000000000000000000030000000000000000000400000000000000000005000000000000000000060000000000000000000700000000000000000008000000000000000000090000000000000000000100000000000000000001000000000000000000020000000000000000000300000000000000000004000000000000000000050000000000000000000600000000000000000007000000000000000000080000000000000000000900000000000000000001000000000000000000010000000000000000000200000000000000000003000000000000000000040000000000000000000500000000000000000006000000000000000000070000000000000000000800000000000000000009000000000000000000010000000000000000000100000000000000000002000000000000000000030000000000000000000400000000000000000005000000000000000000060000000000000000000700000000000000000008000000000000000000090000000000000000000100000000000000000001000000000000000000020000000000000000000300000000000000000004000000000000000000050000000000000000000600000000000000000007000000000000000000080000000000000000000900000000000000000001000000000000000000010000000000000000000200000000000000000003000000000000000000040000000000000000000500000000000000000006000000000000000000070000000000000000000800000000000000000009000000000000000000010000000000000000000a09c7b47112a3afb385c12924bf6280d273c106eea7caeaf5131d8776f61056c148876ae05d46b58d1fff866f864800a82c35094095e7baea6a6c7c4c2dfeb977efac326af552d8785012a05f200801ba01d2c92cfaeb04e53acdff2b5d42005ff6aacdb0105e64eb8c30c273f445d2782a01e7d50ffce57840360c57d94977b8cdebde614da23e8d1e77dc07928763cfe21c0' | ||
const validBlock = Block.fromRLPSerializedBlock(Buffer.from(validblockRlp, 'hex')) | ||
const validBlock = Block.fromRLPSerializedBlock(hexToBytes(validblockRlp)) | ||
@@ -55,6 +57,4 @@ const result = await ethash.verifyPOW(validBlock) | ||
import { Common } from '@ethereumjs/common' | ||
import { BN } from 'ethereumjs-util' | ||
import { MemoryLevel } from 'memory-level' | ||
import { MapDB } from 'ethereumjs-util' | ||
const cacheDB = new MemoryLevel() | ||
const block = Block.fromBlockData({ | ||
@@ -67,2 +67,4 @@ header: { | ||
const cacheDb = new MapDB<number, DBObject>() | ||
const e = new Ethash(cacheDB) | ||
@@ -79,2 +81,26 @@ const miner = e.getMiner(block.header) | ||
### Hybrid CJS/ESM Builds | ||
With the breaking releases from Summer 2023 we have started to ship our libraries with both CommonJS (`cjs` folder) and ESM builds (`esm` folder), see `package.json` for the detailed setup. | ||
If you use an ES6-style `import` in your code files from the ESM build will be used: | ||
```typescript | ||
import { EthereumJSClass } from '@ethereumjs/[PACKAGE_NAME]' | ||
``` | ||
If you use Node.js specific `require` the CJS build will be used: | ||
```typescript | ||
const { EthereumJSClass } = require('@ethereumjs/[PACKAGE_NAME]') | ||
``` | ||
Using ESM will give you additional advantages over CJS beyond browser usage like static code analysis / Tree Shaking which CJS can not provide. | ||
### Buffer -> Uint8Array | ||
With the breaking releases from Summer 2023 we have removed all Node.js specific `Buffer` usages from our libraries and replace these with [Uint8Array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Uint8Array) representations, which are available both in Node.js and the browser (`Buffer` is a subclass of `Uint8Array`). | ||
We have converted existing Buffer conversion methods to Uint8Array conversion methods in the [@ethereumjs/util](https://github.com/ethereumjs/ethereumjs-monorepo/tree/master/packages/util) `bytes` module, see the respective README section for guidance. | ||
### BigInt Support | ||
@@ -81,0 +107,0 @@ |
192
src/index.ts
import { Block, BlockHeader } from '@ethereumjs/block' | ||
import { RLP } from '@ethereumjs/rlp' | ||
import { | ||
KeyEncoding, | ||
TWO_POW256, | ||
bigIntToBuffer, | ||
bufArrToArr, | ||
bufferToBigInt, | ||
ValueEncoding, | ||
bigIntToBytes, | ||
bytesToBigInt, | ||
bytesToHex, | ||
concatBytes, | ||
equalsBytes, | ||
hexToBytes, | ||
setLengthLeft, | ||
zeros, | ||
} from '@ethereumjs/util' | ||
import { keccak256, keccak512 } from 'ethereum-cryptography/keccak' | ||
import { keccak256, keccak512 } from 'ethereum-cryptography/keccak.js' | ||
import { | ||
bufReverse, | ||
bytesReverse, | ||
fnv, | ||
fnvBuffer, | ||
fnvBytes, | ||
getCacheSize, | ||
@@ -22,10 +27,10 @@ getEpoc, | ||
params, | ||
} from './util' | ||
} from './util.js' | ||
import type { BlockData, HeaderData } from '@ethereumjs/block' | ||
import type { AbstractLevel } from 'abstract-level' | ||
import type { DB, DBObject } from '@ethereumjs/util' | ||
function xor(a: Buffer, b: Buffer) { | ||
function xor(a: Uint8Array, b: Uint8Array) { | ||
const len = Math.max(a.length, b.length) | ||
const res = Buffer.alloc(len) | ||
const res = new Uint8Array(len) | ||
for (let i = 0; i < len; i++) { | ||
@@ -38,4 +43,4 @@ res[i] = a[i] ^ b[i] | ||
export type Solution = { | ||
mixHash: Buffer | ||
nonce: Buffer | ||
mixHash: Uint8Array | ||
nonce: Uint8Array | ||
} | ||
@@ -51,3 +56,3 @@ | ||
private currentNonce: bigint | ||
private headerHash?: Buffer | ||
private headerHash?: Uint8Array | ||
private stopMining: boolean | ||
@@ -96,3 +101,3 @@ | ||
data.header!.nonce = solution.nonce | ||
return Block.fromBlockData(data, { common: this.block._common }) | ||
return Block.fromBlockData(data, { common: this.block.common }) | ||
} else { | ||
@@ -102,3 +107,3 @@ const data = <HeaderData>this.blockHeader.toJSON() | ||
data.nonce = solution.nonce | ||
return BlockHeader.fromHeaderData(data, { common: this.blockHeader._common }) | ||
return BlockHeader.fromHeaderData(data, { common: this.blockHeader.common }) | ||
} | ||
@@ -130,6 +135,6 @@ } | ||
setTimeout(() => { | ||
const nonce = setLengthLeft(bigIntToBuffer(this.currentNonce), 8) | ||
const nonce = setLengthLeft(bigIntToBytes(this.currentNonce), 8) | ||
const a = this.ethash.run(headerHash, nonce) | ||
const result = bufferToBigInt(a.hash) | ||
const result = bytesToBigInt(a.hash) | ||
@@ -160,23 +165,12 @@ if (TWO_POW256 / difficulty > result) { | ||
export type EthashCacheDB = AbstractLevel< | ||
string | Buffer | Uint8Array, | ||
string | Buffer, | ||
{ | ||
cache: Buffer[] | ||
fullSize: number | ||
cacheSize: number | ||
seed: Buffer | ||
} | ||
> | ||
export class Ethash { | ||
dbOpts: Object | ||
cacheDB?: EthashCacheDB | ||
cache: Buffer[] | ||
cacheDB?: DB<number, DBObject> | ||
cache: Uint8Array[] | ||
epoc?: number | ||
fullSize?: number | ||
cacheSize?: number | ||
seed?: Buffer | ||
seed?: Uint8Array | ||
constructor(cacheDB?: EthashCacheDB) { | ||
constructor(cacheDB?: DB<number, DBObject>) { | ||
this.dbOpts = { | ||
@@ -189,10 +183,9 @@ valueEncoding: 'json', | ||
mkcache(cacheSize: number, seed: Buffer) { | ||
// console.log(`generating cache\nsize: ${cacheSize}\nseed: ${seed.toString('hex')}`) | ||
mkcache(cacheSize: number, seed: Uint8Array) { | ||
const n = Math.floor(cacheSize / params.HASH_BYTES) | ||
const o = [Buffer.from(keccak512(seed))] | ||
const o = [keccak512(seed)] | ||
let i | ||
for (i = 1; i < n; i++) { | ||
o.push(Buffer.from(keccak512(o[o.length - 1]))) | ||
o.push(keccak512(o[o.length - 1])) | ||
} | ||
@@ -202,4 +195,4 @@ | ||
for (i = 0; i < n; i++) { | ||
const v = o[i].readUInt32LE(0) % n | ||
o[i] = Buffer.from(keccak512(xor(o[(i - 1 + n) % n], o[v]))) | ||
const v = new DataView(o[i].buffer).getUint32(0, true) % n | ||
o[i] = keccak512(xor(o[(i - 1 + n) % n], o[v])) | ||
} | ||
@@ -212,16 +205,17 @@ } | ||
calcDatasetItem(i: number): Buffer { | ||
calcDatasetItem(i: number): Uint8Array { | ||
const n = this.cache.length | ||
const r = Math.floor(params.HASH_BYTES / params.WORD_BYTES) | ||
let mix = Buffer.from(this.cache[i % n]) | ||
mix.writeInt32LE(mix.readUInt32LE(0) ^ i, 0) | ||
mix = Buffer.from(keccak512(mix)) | ||
let mix = new Uint8Array(this.cache[i % n]) | ||
const mixView = new DataView(mix.buffer) | ||
mixView.setUint32(0, mixView.getUint32(0, true) ^ i, true) | ||
mix = keccak512(mix) | ||
for (let j = 0; j < params.DATASET_PARENTS; j++) { | ||
const cacheIndex = fnv(i ^ j, mix.readUInt32LE((j % r) * 4)) | ||
mix = fnvBuffer(mix, this.cache[cacheIndex % n]) | ||
const cacheIndex = fnv(i ^ j, new DataView(mix.buffer).getUint32((j % r) * 4, true)) | ||
mix = fnvBytes(mix, this.cache[cacheIndex % n]) | ||
} | ||
return Buffer.from(keccak512(mix)) | ||
return keccak512(mix) | ||
} | ||
run(val: Buffer, nonce: Buffer, fullSize?: number) { | ||
run(val: Uint8Array, nonce: Uint8Array, fullSize?: number) { | ||
if (fullSize === undefined) { | ||
@@ -236,5 +230,5 @@ if (this.fullSize === undefined) { | ||
const w = Math.floor(params.MIX_BYTES / params.WORD_BYTES) | ||
const s = Buffer.from(keccak512(Buffer.concat([val, bufReverse(nonce)]))) | ||
const s = keccak512(concatBytes(val, bytesReverse(nonce))) | ||
const mixhashes = Math.floor(params.MIX_BYTES / params.HASH_BYTES) | ||
let mix = Buffer.concat(Array(mixhashes).fill(s)) | ||
let mix = concatBytes(...Array(mixhashes).fill(s)) | ||
@@ -244,17 +238,23 @@ let i | ||
const p = | ||
(fnv(i ^ s.readUInt32LE(0), mix.readUInt32LE((i % w) * 4)) % Math.floor(n / mixhashes)) * | ||
(fnv( | ||
i ^ new DataView(s.buffer).getUint32(0, true), | ||
new DataView(mix.buffer).getUint32((i % w) * 4, true) | ||
) % | ||
Math.floor(n / mixhashes)) * | ||
mixhashes | ||
const newdata = [] | ||
const newdata: Uint8Array[] = [] | ||
for (let j = 0; j < mixhashes; j++) { | ||
newdata.push(this.calcDatasetItem(p + j)) | ||
} | ||
mix = fnvBuffer(mix, Buffer.concat(newdata)) | ||
mix = fnvBytes(mix, concatBytes(...newdata)) | ||
} | ||
const cmix = Buffer.alloc(mix.length / 4) | ||
const cmix = new Uint8Array(mix.length / 4) | ||
const cmixView = new DataView(cmix.buffer) | ||
const mixView = new DataView(mix.buffer) | ||
for (i = 0; i < mix.length / 4; i = i + 4) { | ||
const a = fnv(mix.readUInt32LE(i * 4), mix.readUInt32LE((i + 1) * 4)) | ||
const b = fnv(a, mix.readUInt32LE((i + 2) * 4)) | ||
const c = fnv(b, mix.readUInt32LE((i + 3) * 4)) | ||
cmix.writeUInt32LE(c, i) | ||
const a = fnv(mixView.getUint32(i * 4, true), mixView.getUint32((i + 1) * 4, true)) | ||
const b = fnv(a, mixView.getUint32((i + 2) * 4, true)) | ||
const c = fnv(b, mixView.getUint32((i + 3) * 4, true)) | ||
cmixView.setUint32(i, c, true) | ||
} | ||
@@ -264,3 +264,3 @@ | ||
mix: cmix, | ||
hash: Buffer.from(keccak256(Buffer.concat([s, cmix]))), | ||
hash: keccak256(concatBytes(s, cmix)), | ||
} | ||
@@ -270,7 +270,18 @@ } | ||
cacheHash() { | ||
return Buffer.from(keccak256(Buffer.concat(this.cache))) | ||
// Concatenate all the cache bytes together | ||
// We can't use `concatBytes` because calling `concatBytes(...this.cache)` results | ||
// in a `Max call stack size exceeded` error due to the spread operator pushing all | ||
// of the array elements onto the stack and the ethash cache can be quite large | ||
const length = this.cache.reduce((a, arr) => a + arr.length, 0) | ||
const result = new Uint8Array(length) | ||
for (let i = 0, pad = 0; i < this.cache.length; i++) { | ||
const arr = this.cache[i] | ||
result.set(arr, pad) | ||
pad += arr.length | ||
} | ||
return keccak256(result) | ||
} | ||
headerHash(rawHeader: Buffer[]) { | ||
return Buffer.from(keccak256(RLP.encode(bufArrToArr(rawHeader.slice(0, -2))))) | ||
headerHash(rawHeader: Uint8Array[]) { | ||
return keccak256(RLP.encode(rawHeader.slice(0, -2))) | ||
} | ||
@@ -295,15 +306,18 @@ | ||
// gives the seed the first epoc found | ||
const findLastSeed = async (epoc: number): Promise<[Buffer, number]> => { | ||
const findLastSeed = async (epoc: number): Promise<[Uint8Array, number]> => { | ||
if (epoc === 0) { | ||
return [zeros(32), 0] | ||
} | ||
let data | ||
try { | ||
data = await this.cacheDB!.get(epoc, this.dbOpts) | ||
} catch (error: any) { | ||
if (error.code !== 'LEVEL_NOT_FOUND') { | ||
throw error | ||
const dbData = await this.cacheDB!.get(epoc, { | ||
keyEncoding: KeyEncoding.Number, | ||
valueEncoding: ValueEncoding.JSON, | ||
}) | ||
if (dbData !== undefined) { | ||
const data = { | ||
cache: (dbData.cache as string[]).map((el: string) => hexToBytes(el)), | ||
fullSize: dbData.fullSize, | ||
cacheSize: dbData.cacheSize, | ||
seed: hexToBytes(dbData.seed as string), | ||
} | ||
} | ||
if (data) { | ||
return [data.seed, epoc] | ||
@@ -316,10 +330,14 @@ } else { | ||
let data | ||
try { | ||
data = await this.cacheDB!.get(epoc, this.dbOpts) | ||
} catch (error: any) { | ||
if (error.code !== 'LEVEL_NOT_FOUND') { | ||
throw error | ||
const dbData = await this.cacheDB!.get(epoc, { | ||
keyEncoding: KeyEncoding.Number, | ||
valueEncoding: ValueEncoding.JSON, | ||
}) | ||
if (dbData !== undefined) { | ||
data = { | ||
cache: (dbData.cache as string[]).map((el: string) => hexToBytes(el)), | ||
fullSize: dbData.fullSize, | ||
cacheSize: dbData.cacheSize, | ||
seed: hexToBytes(dbData.seed as string), | ||
} | ||
} | ||
if (!data) { | ||
@@ -338,14 +356,17 @@ this.cacheSize = await getCacheSize(epoc) | ||
fullSize: this.fullSize, | ||
seed: this.seed, | ||
cache, | ||
seed: bytesToHex(this.seed), | ||
cache: cache.map((el) => bytesToHex(el)), | ||
}, | ||
this.dbOpts | ||
{ | ||
keyEncoding: KeyEncoding.Number, | ||
valueEncoding: ValueEncoding.JSON, | ||
} | ||
) | ||
} else { | ||
this.cache = data.cache.map((a: Buffer) => { | ||
return Buffer.from(a) | ||
this.cache = data.cache.map((a: Uint8Array) => { | ||
return Uint8Array.from(a) | ||
}) | ||
this.cacheSize = data.cacheSize | ||
this.fullSize = data.fullSize | ||
this.seed = Buffer.from(data.seed) | ||
this.cacheSize = data.cacheSize as number | ||
this.fullSize = data.fullSize as number | ||
this.seed = Uint8Array.from(data.seed) | ||
} | ||
@@ -370,5 +391,4 @@ } | ||
const a = this.run(headerHash, nonce) | ||
const result = bufferToBigInt(a.hash) | ||
return a.mix.equals(mixHash) && TWO_POW256 / difficulty > result | ||
const result = bytesToBigInt(a.hash) | ||
return equalsBytes(a.mix, mixHash) && TWO_POW256 / difficulty > result | ||
} | ||
@@ -375,0 +395,0 @@ |
import { isProbablyPrime } from 'bigint-crypto-utils' | ||
import { keccak256 } from 'ethereum-cryptography/keccak' | ||
import { keccak256 } from 'ethereum-cryptography/keccak.js' | ||
@@ -47,9 +47,9 @@ export const params = { | ||
* @method getSeed | ||
* @param seed Buffer | ||
* @param seed Uint8Array | ||
* @param begin Number | ||
* @param end Number | ||
*/ | ||
export function getSeed(seed: Buffer, begin: number, end: number) { | ||
export function getSeed(seed: Uint8Array, begin: number, end: number) { | ||
for (let i = begin; i < end; i++) { | ||
seed = Buffer.from(keccak256(seed)) | ||
seed = keccak256(seed) | ||
} | ||
@@ -63,6 +63,11 @@ return seed | ||
export function fnvBuffer(a: Buffer, b: Buffer) { | ||
const r = Buffer.alloc(a.length) | ||
export function fnvBytes(a: Uint8Array, b: Uint8Array) { | ||
const r = new Uint8Array(a.length) | ||
const rView = new DataView(r.buffer) | ||
for (let i = 0; i < a.length; i = i + 4) { | ||
r.writeUInt32LE(fnv(a.readUInt32LE(i), b.readUInt32LE(i)), i) | ||
rView.setUint32( | ||
i, | ||
fnv(new DataView(a.buffer).getUint32(i, true), new DataView(b.buffer).getUint32(i, true)), | ||
true | ||
) | ||
} | ||
@@ -72,5 +77,5 @@ return r | ||
export function bufReverse(a: Buffer) { | ||
export function bytesReverse(a: Uint8Array) { | ||
const length = a.length | ||
const b = Buffer.alloc(length) | ||
const b = new Uint8Array(length) | ||
for (let i = 0; i < length; i++) { | ||
@@ -77,0 +82,0 @@ b[i] = a[length - i - 1] |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
No v1
QualityPackage is not semver >=1. This means it is not stable and does not support ^ ranges.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
181074
5
1
25
1389
125
Yes
1
1
+ Added@ethereumjs/block@5.0.0-rc.1(transitive)
+ Added@ethereumjs/common@4.0.0-rc.1(transitive)
+ Added@ethereumjs/rlp@5.0.0-rc.1(transitive)
+ Added@ethereumjs/trie@6.0.0-rc.1(transitive)
+ Added@ethereumjs/tx@5.0.0-rc.1(transitive)
+ Added@ethereumjs/util@9.0.0-rc.1(transitive)
+ Addedcrc@4.3.2(transitive)
+ Addedlru-cache@10.4.3(transitive)
- Removedabstract-level@^1.0.3
- Removed@ethereumjs/block@4.3.0(transitive)
- Removed@ethereumjs/common@3.2.0(transitive)
- Removed@ethereumjs/rlp@4.0.1(transitive)
- Removed@ethereumjs/trie@5.1.0(transitive)
- Removed@ethereumjs/tx@4.2.0(transitive)
- Removed@ethereumjs/util@8.1.0(transitive)
- Removedabstract-level@1.0.4(transitive)
- Removedbase64-js@1.5.1(transitive)
- Removedbuffer@6.0.3(transitive)
- Removedcatering@2.1.1(transitive)
- Removedcrc-32@1.2.2(transitive)
- Removedieee754@1.2.1(transitive)
- Removedis-buffer@2.0.5(transitive)
- Removedlevel-supports@4.0.1(transitive)
- Removedlevel-transcoder@1.0.1(transitive)
- Removedmicro-ftch@0.3.1(transitive)
- Removedmodule-error@1.0.2(transitive)
- Removedqueue-microtask@1.2.3(transitive)
Updated@ethereumjs/block@5.0.0-rc.1
Updated@ethereumjs/rlp@5.0.0-rc.1
Updated@ethereumjs/util@9.0.0-rc.1
Updatedethereum-cryptography@^2.1.2