93 lines
2.1 KiB
JavaScript
93 lines
2.1 KiB
JavaScript
import { Worker } from "worker_threads";
|
|
import os from "os";
|
|
|
|
const workerBlob = new Blob(
|
|
[
|
|
`
|
|
import crypto from "crypto";
|
|
import { parentPort, workerData } from "worker_threads";
|
|
|
|
const { salt, target } = workerData;
|
|
|
|
const saltBuffer = Buffer.from(salt);
|
|
const targetLen = target.length;
|
|
const targetBytes = Math.ceil(targetLen / 2);
|
|
|
|
let nonce = 0;
|
|
|
|
while (true) {
|
|
const nonceStr = nonce.toString();
|
|
|
|
const hash = crypto.createHash("sha256");
|
|
|
|
hash.update(saltBuffer);
|
|
hash.update(nonceStr);
|
|
|
|
const hashBuffer = hash.digest();
|
|
|
|
const hashPrefixHex = hashBuffer.toString("hex", 0, targetBytes);
|
|
|
|
if (hashPrefixHex.startsWith(target)) {
|
|
parentPort.postMessage({
|
|
nonce: Number(nonce),
|
|
salt,
|
|
target,
|
|
});
|
|
break;
|
|
}
|
|
|
|
nonce++;
|
|
}`,
|
|
],
|
|
{
|
|
type: "application/typescript",
|
|
}
|
|
);
|
|
const workerUrl = URL.createObjectURL(workerBlob);
|
|
|
|
export default function solver(challenges, config) {
|
|
const totalChallenges = challenges.length;
|
|
const numWorkers =
|
|
config?.workerCount || Math.min(totalChallenges, 14, os.cpus().length);
|
|
|
|
let challengesProcessed = 0;
|
|
let nextChallengeIndex = 0;
|
|
let activeWorkers = 0;
|
|
const results = [];
|
|
|
|
return new Promise((resolve) => {
|
|
function startWorker() {
|
|
if (nextChallengeIndex < totalChallenges && activeWorkers < numWorkers) {
|
|
const currentChallengeIndex = nextChallengeIndex;
|
|
const [salt, target] = challenges[currentChallengeIndex];
|
|
nextChallengeIndex++;
|
|
activeWorkers++;
|
|
|
|
const worker = new Worker(workerUrl, {
|
|
workerData: { salt, target, challengeIndex: currentChallengeIndex },
|
|
});
|
|
|
|
worker.on("message", (result) => {
|
|
results.push([result.salt, result.target, result.nonce]);
|
|
challengesProcessed++;
|
|
activeWorkers--;
|
|
|
|
if (challengesProcessed === totalChallenges) {
|
|
resolve(results);
|
|
} else {
|
|
startWorker();
|
|
}
|
|
});
|
|
}
|
|
}
|
|
|
|
for (let i = 0; i < numWorkers; i++) {
|
|
startWorker();
|
|
}
|
|
|
|
if (totalChallenges === 0) {
|
|
resolve([]);
|
|
}
|
|
});
|
|
}
|