work on user connections
parent
716fb7335c
commit
1b16c809fd
|
@ -51,6 +51,8 @@ class OnionrCommunicatorDaemon:
|
|||
# lists of connected peers and peers we know we can't reach currently
|
||||
self.onlinePeers = []
|
||||
self.offlinePeers = []
|
||||
self.cooldownPeer = {}
|
||||
self.connectTimes = {}
|
||||
self.peerProfiles = [] # list of peer's profiles (onionrpeers.PeerProfile instances)
|
||||
|
||||
# amount of threads running by name, used to prevent too many
|
||||
|
@ -84,13 +86,14 @@ class OnionrCommunicatorDaemon:
|
|||
# requiresPeer True means the timer function won't fire if we have no connected peers
|
||||
OnionrCommunicatorTimers(self, self.daemonCommands, 5)
|
||||
OnionrCommunicatorTimers(self, self.detectAPICrash, 5)
|
||||
peerPoolTimer = OnionrCommunicatorTimers(self, self.getOnlinePeers, 60)
|
||||
peerPoolTimer = OnionrCommunicatorTimers(self, self.getOnlinePeers, 60, maxThreads=1)
|
||||
OnionrCommunicatorTimers(self, self.lookupBlocks, self._core.config.get('timers.lookupBlocks'), requiresPeer=True, maxThreads=1)
|
||||
OnionrCommunicatorTimers(self, self.getBlocks, self._core.config.get('timers.getBlocks'), requiresPeer=True)
|
||||
OnionrCommunicatorTimers(self, self.clearOfflinePeer, 58)
|
||||
OnionrCommunicatorTimers(self, self.daemonTools.cleanOldBlocks, 65)
|
||||
OnionrCommunicatorTimers(self, self.lookupKeys, 60, requiresPeer=True)
|
||||
OnionrCommunicatorTimers(self, self.lookupAdders, 60, requiresPeer=True)
|
||||
OnionrCommunicatorTimers(self, self.daemonTools.cooldownPeer, 30, requiresPeer=True)
|
||||
netCheckTimer = OnionrCommunicatorTimers(self, self.daemonTools.netCheck, 600)
|
||||
announceTimer = OnionrCommunicatorTimers(self, self.daemonTools.announceNode, 305, requiresPeer=True, maxThreads=1)
|
||||
cleanupTimer = OnionrCommunicatorTimers(self, self.peerCleanup, 300, requiresPeer=True)
|
||||
|
@ -295,7 +298,7 @@ class OnionrCommunicatorDaemon:
|
|||
'''Manages the self.onlinePeers attribute list, connects to more peers if we have none connected'''
|
||||
|
||||
logger.info('Refreshing peer pool.')
|
||||
maxPeers = config.get('peers.maxConnect')
|
||||
maxPeers = int(config.get('peers.maxConnect'))
|
||||
needed = maxPeers - len(self.onlinePeers)
|
||||
|
||||
for i in range(needed):
|
||||
|
@ -338,7 +341,7 @@ class OnionrCommunicatorDaemon:
|
|||
for address in peerList:
|
||||
if not config.get('tor.v3onions') and len(address) == 62:
|
||||
continue
|
||||
if len(address) == 0 or address in tried or address in self.onlinePeers:
|
||||
if len(address) == 0 or address in tried or address in self.onlinePeers or address in self.cooldownPeer:
|
||||
continue
|
||||
if self.shutdown:
|
||||
return
|
||||
|
@ -347,6 +350,7 @@ class OnionrCommunicatorDaemon:
|
|||
time.sleep(0.1)
|
||||
if address not in self.onlinePeers:
|
||||
self.onlinePeers.append(address)
|
||||
self.connectTimes[address] = self._core._utils.getEpoch()
|
||||
retData = address
|
||||
|
||||
# add peer to profile list if they're not in it
|
||||
|
@ -361,6 +365,17 @@ class OnionrCommunicatorDaemon:
|
|||
logger.debug('Failed to connect to ' + address)
|
||||
return retData
|
||||
|
||||
def removeOnlinePeer(self, peer):
|
||||
'''Remove an online peer'''
|
||||
try:
|
||||
del self.connectTimes[peer]
|
||||
except KeyError:
|
||||
pass
|
||||
try:
|
||||
self.onlinePeers.remove(peer)
|
||||
except ValueError:
|
||||
pass
|
||||
|
||||
def peerCleanup(self):
|
||||
'''This just calls onionrpeers.cleanupPeers, which removes dead or bad peers (offline too long, too slow)'''
|
||||
onionrpeers.peerCleanup(self._core)
|
||||
|
@ -392,7 +407,7 @@ class OnionrCommunicatorDaemon:
|
|||
if retData == False:
|
||||
try:
|
||||
self.getPeerProfileInstance(peer).addScore(-10)
|
||||
self.onlinePeers.remove(peer)
|
||||
self.removeOnlinePeer(peer)
|
||||
self.getOnlinePeers() # Will only add a new peer to pool if needed
|
||||
except ValueError:
|
||||
pass
|
||||
|
|
|
@ -17,7 +17,7 @@
|
|||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
'''
|
||||
import onionrexceptions, onionrpeers, onionrproofs, base64, logger
|
||||
import onionrexceptions, onionrpeers, onionrproofs, base64, logger, secrets
|
||||
class DaemonTools:
|
||||
def __init__(self, daemon):
|
||||
self.daemon = daemon
|
||||
|
@ -71,3 +71,34 @@ class DaemonTools:
|
|||
self.daemon._core.removeBlock(oldest)
|
||||
logger.info('Deleted block: %s' % (oldest,))
|
||||
self.daemon.decrementThreadCount('cleanOldBlocks')
|
||||
|
||||
def cooldownPeer(self):
|
||||
'''Randomly add an online peer to cooldown, so we can connect a new one'''
|
||||
onlinePeerAmount = len(self.daemon.onlinePeers)
|
||||
minTime = 300
|
||||
cooldownTime = 600
|
||||
toCool = ''
|
||||
tempConnectTimes = dict(self.daemon.connectTimes)
|
||||
|
||||
# Remove peers from cooldown that have been there long enough
|
||||
tempCooldown = dict(self.daemon.cooldownPeer)
|
||||
for peer in tempCooldown:
|
||||
if (self.daemon._core._utils.getEpoch() - tempCooldown[peer]) >= cooldownTime:
|
||||
del self.daemon.cooldownPeer[peer]
|
||||
|
||||
# Cool down a peer, if we have max connections alive for long enough
|
||||
if onlinePeerAmount >= self.daemon._core.config.get('peers.maxConnect'):
|
||||
finding = True
|
||||
while finding:
|
||||
try:
|
||||
toCool = min(tempConnectTimes, key=tempConnectTimes.get)
|
||||
if (self.daemon._core._utils.getEpoch() - tempConnectTimes[toCool]) < minTime:
|
||||
del tempConnectTimes[toCool]
|
||||
else:
|
||||
finding = False
|
||||
except ValueError:
|
||||
break
|
||||
else:
|
||||
self.daemon.removeOnlinePeer(toCool)
|
||||
self.daemon.cooldownPeer[toCool] = self.daemon._core._utils.getEpoch()
|
||||
self.daemon.decrementThreadCount('cooldownPeer')
|
|
@ -90,13 +90,15 @@ def peerCleanup(coreInst):
|
|||
if PeerProfiles(address, coreInst).score < minScore:
|
||||
coreInst.removeAddress(address)
|
||||
try:
|
||||
if (coreInst._utils.getEpoch() - coreInst.getPeerInfo(address, 'dateSeen')) >= 600:
|
||||
if (int(coreInst._utils.getEpoch()) - int(coreInst.getPeerInfo(address, 'dateSeen'))) >= 600:
|
||||
expireTime = 600
|
||||
else:
|
||||
expireTime = 86400
|
||||
coreInst._blacklist.addToDB(address, dataType=1, expire=expireTime)
|
||||
except sqlite3.IntegrityError: #TODO just make sure its not a unique constraint issue
|
||||
pass
|
||||
except ValueError:
|
||||
pass
|
||||
logger.warn('Removed address ' + address + '.')
|
||||
|
||||
# Unban probably not malicious peers TODO improve
|
||||
|
|
Loading…
Reference in New Issue