diff --git a/lib/net/peer.js b/lib/net/peer.js index 5a7cd1e7..23d2fdd0 100644 --- a/lib/net/peer.js +++ b/lib/net/peer.js @@ -1611,7 +1611,7 @@ Peer.prototype.handleVersion = co(function* handleVersion(packet) { this.noRelay = packet.noRelay; if (!this.network.selfConnect) { - if (this.options.hasNonce(packet.nonce, this.hostname())) + if (this.options.hasNonce(packet.nonce)) throw new Error('We connected to ourself. Oops.'); } @@ -2301,11 +2301,10 @@ PeerOptions.createNonce = function createNonce(hostname) { * Test whether version nonce is ours. * @private * @param {Buffer} nonce - * @param {String} hostname * @returns {Boolean} */ -PeerOptions.hasNonce = function hasNonce(nonce, hostname) { +PeerOptions.hasNonce = function hasNonce(nonce) { return false; }; diff --git a/lib/net/pool.js b/lib/net/pool.js index 4b63e19f..589e71e2 100644 --- a/lib/net/pool.js +++ b/lib/net/pool.js @@ -1198,6 +1198,7 @@ Pool.prototype.handleVersion = co(function* handleVersion(peer, packet) { packet.agent); this.network.time.add(peer.hostname(), packet.ts); + this.nonces.remove(peer.hostname()); }); /** @@ -3454,12 +3455,11 @@ PoolOptions.prototype.createNonce = function createNonce(hostname) { * Test whether version nonce is ours. * @private * @param {Buffer} nonce - * @param {String} hostname * @returns {Boolean} */ -PoolOptions.prototype.hasNonce = function hasNonce(nonce, hostname) { - return this.nonces.has(nonce, hostname); +PoolOptions.prototype.hasNonce = function hasNonce(nonce) { + return this.nonces.has(nonce); }; /** @@ -3799,23 +3799,44 @@ BroadcastItem.prototype.inspect = function inspect() { */ function NonceList() { - this.seed1 = util.random(0, 0x100000000); - this.seed2 = util.random(0, 0x100000000); + this.map = {}; + this.hosts = {}; } NonceList.prototype.alloc = function alloc(hostname) { - var nonce = new Buffer(8); - var data = new Buffer(hostname, 'ascii'); - var lo = murmur3(data, this.seed1); - var hi = murmur3(data, this.seed2); - nonce.writeUInt32LE(lo, 0, true); - nonce.writeUInt32LE(hi, 4, true); + var nonce, key; + + for (;;) { + nonce = util.nonce(); + key = nonce.toString('hex'); + if (!this.map[key]) { + this.map[key] = hostname; + assert(!this.hosts[hostname]); + this.hosts[hostname] = key; + break; + } + } + return nonce; }; -NonceList.prototype.has = function has(nonce, hostname) { - var item = this.alloc(hostname); - return crypto.ccmp(nonce, item); +NonceList.prototype.has = function has(nonce) { + var key = nonce.toString('hex'); + return this.map[key] != null; +}; + +NonceList.prototype.remove = function remove(hostname) { + var key = this.hosts[hostname]; + + if (!key) + return false; + + delete this.hosts[hostname]; + + assert(this.map[key]); + delete this.map[key]; + + return true; }; /**