Added jobRebroadcastTimeout configuration
This commit is contained in:
parent
a6e38a6bb0
commit
a50beb1932
@ -138,6 +138,11 @@ var pool = Stratum.createPool({
|
||||
job broadcast. */
|
||||
"txRefreshInterval": 20000,
|
||||
|
||||
/* Some miner software is bugged and will consider the pool offline if it doesn't receive
|
||||
anything for around a minute, so every time we broadcast jobs, set a timeout to rebroadcast
|
||||
in this many seconds unless we find a new job. Set to zero or remove to disable this. */
|
||||
"jobRebroadcastTimeout": 55,
|
||||
|
||||
//instanceId: 37, //Recommend not using this because a crypto-random one will be generated
|
||||
|
||||
/* Some attackers will create thousands of workers that use up all available socket connections,
|
||||
|
||||
@ -10,7 +10,7 @@ var algos = module.exports = global.algos = {
|
||||
multiplier: Math.pow(2, 32),
|
||||
hash: function(){
|
||||
return function(){
|
||||
return util.doublesha.apply(this, arguments);
|
||||
return util.sha256d.apply(this, arguments);
|
||||
}
|
||||
}
|
||||
},
|
||||
@ -99,8 +99,9 @@ var algos = module.exports = global.algos = {
|
||||
shift: 24,
|
||||
multiplier: Math.pow(2, 8),
|
||||
hash: function(){
|
||||
return function(){
|
||||
return multiHashing.keccak.apply(this, arguments);
|
||||
return function(data, nTime){
|
||||
var f = Buffer.concat([data, new Buffer(nTime.toString(16), 'hex')]);
|
||||
return multiHashing.keccak(f);
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
@ -65,6 +65,8 @@ var JobManager = module.exports = function JobManager(maxDifficulty, hashDigest,
|
||||
|
||||
var lastTransactionUpdateCheck = Date.now();
|
||||
|
||||
var coinbaseHasher = options.coin.algorithm === 'keccak' ? util.sha256 : util.sha256d;
|
||||
|
||||
//returns true if processed a new block
|
||||
this.processTemplate = function(rpcData, publicKey){
|
||||
|
||||
@ -168,12 +170,12 @@ var JobManager = module.exports = function JobManager(maxDifficulty, hashDigest,
|
||||
var extraNonce2Buffer = new Buffer(extraNonce2, 'hex');
|
||||
|
||||
var coinbaseBuffer = job.serializeCoinbase(extraNonce1Buffer, extraNonce2Buffer);
|
||||
var coinbaseHash = util.doublesha(coinbaseBuffer);
|
||||
var coinbaseHash = coinbaseHasher(coinbaseBuffer);
|
||||
|
||||
var merkleRoot = util.reverseBuffer(job.merkleTree.withFirst(coinbaseHash)).toString('hex');
|
||||
|
||||
var headerBuffer = job.serializeHeader(merkleRoot, nTime, nonce);
|
||||
var headerHash = hashDigest(headerBuffer, nTimeInt);
|
||||
var headerHash = hashDigest(headerBuffer, nTimeInt);
|
||||
var headerBigNum = bignum.fromBuffer(headerHash, {endian: 'little', size: 32});
|
||||
|
||||
var blockHash;
|
||||
@ -181,14 +183,13 @@ var JobManager = module.exports = function JobManager(maxDifficulty, hashDigest,
|
||||
|
||||
|
||||
if (job.target.ge(headerBigNum)){
|
||||
|
||||
blockHex = job.serializeBlock(headerBuffer, coinbaseBuffer).toString('hex');
|
||||
blockHash = util.reverseBuffer(util.doublesha(headerBuffer)).toString('hex');
|
||||
blockHash = util.reverseBuffer(util.sha256d(headerBuffer)).toString('hex');
|
||||
}
|
||||
else {
|
||||
var targetUser = maxDifficulty.div(difficulty);
|
||||
if (headerBigNum.gt(targetUser)){
|
||||
var lowPercent = targetUser.div(headerBigNum).mul(100).toNumber().toFixed(10);
|
||||
var lowPercent = headerBigNum.sub(targetUser).div(headerBigNum).mul(100).toNumber().toFixed(10);
|
||||
return shareError([23, 'low difficulty share, need to be ' + lowPercent + '% higher']);
|
||||
}
|
||||
}
|
||||
|
||||
@ -10,7 +10,7 @@ var MerkleTree = module.exports = function MerkleTree(data){
|
||||
|
||||
function merkleJoin(h1, h2){
|
||||
var joined = Buffer.concat([h1, h2]);
|
||||
var dhashed = util.doublesha(joined);
|
||||
var dhashed = util.sha256d(joined);
|
||||
return dhashed;
|
||||
}
|
||||
|
||||
@ -51,7 +51,7 @@ var MerkleTree = module.exports = function MerkleTree(data){
|
||||
MerkleTree.prototype = {
|
||||
withFirst: function(f){
|
||||
this.steps.forEach(function(s){
|
||||
f = util.doublesha(Buffer.concat([f, s]));
|
||||
f = util.sha256d(Buffer.concat([f, s]));
|
||||
});
|
||||
return f;
|
||||
}
|
||||
|
||||
@ -102,7 +102,7 @@ var Peer = module.exports = function(options){
|
||||
var msgLength = header.readUInt32LE(16);
|
||||
var msgChecksum = header.readUInt32LE(20);
|
||||
readFlowingBytes(client, msgLength, lopped, function(payload, lopped){
|
||||
if (util.doublesha(payload).readUInt32LE(0) !== msgChecksum){
|
||||
if (util.sha256d(payload).readUInt32LE(0) !== msgChecksum){
|
||||
_this.emit('error', 'bad payload - failed checksum');
|
||||
beginReadingMessage(null);
|
||||
return;
|
||||
@ -154,7 +154,7 @@ var Peer = module.exports = function(options){
|
||||
magic,
|
||||
command,
|
||||
util.packUInt32LE(payload.length),
|
||||
util.doublesha(payload).slice(0, 4),
|
||||
util.sha256d(payload).slice(0, 4),
|
||||
payload
|
||||
]);
|
||||
client.write(message);
|
||||
|
||||
@ -517,7 +517,7 @@ var pool = module.exports = function pool(options, authorizeFn){
|
||||
|
||||
|
||||
function StartStratumServer(finishedCallback){
|
||||
_this.stratumServer = new stratum.Server(options.ports, options.connectionTimeout, options.banning, authorizeFn);
|
||||
_this.stratumServer = new stratum.Server(options.ports, options.connectionTimeout, options.jobRebroadcastTimeout, options.banning, authorizeFn);
|
||||
|
||||
_this.stratumServer.on('started', function(){
|
||||
options.initStats.stratumPorts = Object.keys(options.ports);
|
||||
|
||||
@ -287,18 +287,18 @@ StratumClient.prototype.__proto__ = events.EventEmitter.prototype;
|
||||
* - 'client.disconnected'(StratumClientInstance) - when a miner disconnects. Be aware that the socket cannot be used anymore.
|
||||
* - 'started' - when the server is up and running
|
||||
**/
|
||||
var StratumServer = exports.Server = function StratumServer(ports, connectionTimeout, banning, authorizeFn){
|
||||
var StratumServer = exports.Server = function StratumServer(ports, connectionTimeout, jobRebroadcastTimeout, banning, authorizeFn){
|
||||
|
||||
//private members
|
||||
|
||||
var socketTimeout = connectionTimeout * 1000;
|
||||
var bannedMS = banning ? banning.time * 1000 : null;
|
||||
var socketTimeout = connectionTimeout * 1000;
|
||||
var bannedMS = banning ? banning.time * 1000 : null;
|
||||
|
||||
var _this = this;
|
||||
var stratumClients = {};
|
||||
var _this = this;
|
||||
var stratumClients = {};
|
||||
var subscriptionCounter = SubscriptionCounter();
|
||||
var rebroadcastTimeout;
|
||||
var bannedIPs = {};
|
||||
var bannedIPs = {};
|
||||
|
||||
//Interval to look through bannedIPs for old bans and remove them in order to prevent a memory leak
|
||||
var purgeOldBans = (!banning || !banning.enabled) ? null : setInterval(function(){
|
||||
@ -376,14 +376,15 @@ var StratumServer = exports.Server = function StratumServer(ports, connectionTim
|
||||
}
|
||||
}
|
||||
|
||||
/* Some miners will consider the pool dead if it doesn't receive a job at least every 30 seconds.
|
||||
So every time broadcast jobs, we set a timeout to rebroadcast in 30 seconds unless cleared. */
|
||||
/* Some miners will consider the pool dead if it doesn't receive a job for around a minute.
|
||||
So every time we broadcast jobs, set a timeout to rebroadcast in X seconds unless cleared. */
|
||||
if (isNaN(jobRebroadcastTimeout) || jobRebroadcastTimeout <= 0) return;
|
||||
clearTimeout(rebroadcastTimeout);
|
||||
rebroadcastTimeout = setTimeout(function(){
|
||||
var resendParams = jobParams;
|
||||
resendParams[8] = false;
|
||||
_this.broadcastMiningJobs(resendParams);
|
||||
}, 30000);
|
||||
}, jobRebroadcastTimeout * 1000);
|
||||
};
|
||||
|
||||
this.getStratumClients = function () {
|
||||
|
||||
14
lib/util.js
14
lib/util.js
@ -22,16 +22,14 @@ exports.bignumFromBits = function(bitsString){
|
||||
return target;
|
||||
};
|
||||
|
||||
exports.doublesha = function(buffer){
|
||||
exports.sha256 = function(buffer){
|
||||
var hash1 = crypto.createHash('sha256');
|
||||
hash1.update(buffer);
|
||||
hash1 = hash1.digest();
|
||||
return hash1.digest();
|
||||
};
|
||||
|
||||
var hash2 = crypto.createHash('sha256');
|
||||
hash2.update(hash1);
|
||||
hash2 = hash2.digest();
|
||||
|
||||
return hash2;
|
||||
exports.sha256d = function(buffer){
|
||||
return exports.sha256(exports.sha256(buffer));
|
||||
};
|
||||
|
||||
exports.reverseBuffer = function(buff){
|
||||
@ -257,7 +255,7 @@ exports.addressToPubkey = function(addr){
|
||||
/* We already do rpc.validateaddress so we don't need this
|
||||
var ver = decoded[0];
|
||||
var cksumA = decoded.slice(-4);
|
||||
var cksumB = exports.doublesha(decoded.slice(0, -4)).slice(0, 4);
|
||||
var cksumB = exports.sha256d(decoded.slice(0, -4)).slice(0, 4);
|
||||
|
||||
if (cksumA.toString('hex') != cksumB.toString('hex')){
|
||||
console.error('checksum did not match for ' + addr)
|
||||
|
||||
Loading…
Reference in New Issue
Block a user