commit 5d723401f851a07129620addceb0f1f2d80f7b95
parent fdaf6e775cdbe461a8466d1d7e46360c8a90e4d7
Author: SomberNight <somber.night@protonmail.com>
Date: Thu, 27 Aug 2020 17:57:19 +0200
util.NetworkRetryManager: fix potential overflow
e.g. consider:
>>> 1.5 * 2 ** 2000
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
OverflowError: int too large to convert to float
Diffstat:
1 file changed, 17 insertions(+), 6 deletions(-)
diff --git a/electrum/util.py b/electrum/util.py
@@ -1380,20 +1380,31 @@ class NetworkRetryManager(Generic[_NetAddrType]):
def _on_connection_successfully_established(self, addr: _NetAddrType) -> None:
self._last_tried_addr[addr] = time.time(), 0
- def _can_retry_addr(self, peer: _NetAddrType, *,
+ def _can_retry_addr(self, addr: _NetAddrType, *,
now: float = None, urgent: bool = False) -> bool:
if now is None:
now = time.time()
- last_time, num_attempts = self._last_tried_addr.get(peer, (0, 0))
+ last_time, num_attempts = self._last_tried_addr.get(addr, (0, 0))
if urgent:
- delay = min(self._max_retry_delay_urgent,
- self._init_retry_delay_urgent * 2 ** num_attempts)
+ max_delay = self._max_retry_delay_urgent
+ init_delay = self._init_retry_delay_urgent
else:
- delay = min(self._max_retry_delay_normal,
- self._init_retry_delay_normal * 2 ** num_attempts)
+ max_delay = self._max_retry_delay_normal
+ init_delay = self._init_retry_delay_normal
+ delay = self.__calc_delay(multiplier=init_delay, max_delay=max_delay, num_attempts=num_attempts)
next_time = last_time + delay
return next_time < now
+ @classmethod
+ def __calc_delay(cls, *, multiplier: float, max_delay: float,
+ num_attempts: int) -> float:
+ num_attempts = min(num_attempts, 100_000)
+ try:
+ res = multiplier * 2 ** num_attempts
+ except OverflowError:
+ return max_delay
+ return max(0, min(max_delay, res))
+
def _clear_addr_retry_times(self) -> None:
self._last_tried_addr.clear()