Bandwidth limit optimisation

- should be slightly more accurate and use slightly fewer resources
This commit is contained in:
Peter Šurda 2018-01-02 15:24:47 +01:00
parent 8788f2d349
commit 4086253730
Signed by untrusted user: PeterSurda
GPG Key ID: 0C5F50C0B5F37D87
2 changed files with 16 additions and 6 deletions

View File

@ -75,7 +75,7 @@ class AdvancedDispatcher(asyncore.dispatcher):
def writable(self): def writable(self):
self.uploadChunk = AdvancedDispatcher._buf_len self.uploadChunk = AdvancedDispatcher._buf_len
if asyncore.maxUploadRate > 0: if asyncore.maxUploadRate > 0:
self.uploadChunk = asyncore.uploadBucket self.uploadChunk = int(asyncore.uploadBucket)
self.uploadChunk = min(self.uploadChunk, len(self.write_buf)) self.uploadChunk = min(self.uploadChunk, len(self.write_buf))
return asyncore.dispatcher.writable(self) and \ return asyncore.dispatcher.writable(self) and \
(self.connecting or (self.connected and self.uploadChunk > 0)) (self.connecting or (self.connected and self.uploadChunk > 0))
@ -83,7 +83,7 @@ class AdvancedDispatcher(asyncore.dispatcher):
def readable(self): def readable(self):
self.downloadChunk = AdvancedDispatcher._buf_len self.downloadChunk = AdvancedDispatcher._buf_len
if asyncore.maxDownloadRate > 0: if asyncore.maxDownloadRate > 0:
self.downloadChunk = asyncore.downloadBucket self.downloadChunk = int(asyncore.downloadBucket)
try: try:
if self.expectBytes > 0 and not self.fullyEstablished: if self.expectBytes > 0 and not self.fullyEstablished:
self.downloadChunk = min(self.downloadChunk, self.expectBytes - len(self.read_buf)) self.downloadChunk = min(self.downloadChunk, self.expectBytes - len(self.read_buf))

View File

@ -112,6 +112,8 @@ uploadBucket = 0
sentBytes = 0 sentBytes = 0
def read(obj): def read(obj):
if not can_receive():
return
try: try:
obj.handle_read_event() obj.handle_read_event()
except _reraised_exceptions: except _reraised_exceptions:
@ -120,6 +122,8 @@ def read(obj):
obj.handle_error() obj.handle_error()
def write(obj): def write(obj):
if not can_send():
return
try: try:
obj.handle_write_event() obj.handle_write_event()
except _reraised_exceptions: except _reraised_exceptions:
@ -136,12 +140,18 @@ def set_rates(download, upload):
downloadTimestamp = time.time() downloadTimestamp = time.time()
uploadTimestamp = time.time() uploadTimestamp = time.time()
def can_receive():
return maxDownloadRate == 0 or downloadBucket > 0
def can_send():
return maxUploadRate == 0 or uploadBucket > 0
def update_received(download=0): def update_received(download=0):
global receivedBytes, downloadBucket, downloadTimestamp global receivedBytes, downloadBucket, downloadTimestamp
currentTimestamp = time.time() currentTimestamp = time.time()
receivedBytes += download receivedBytes += download
if maxDownloadRate > 0: if maxDownloadRate > 0:
bucketIncrease = int(maxDownloadRate * (currentTimestamp - downloadTimestamp)) bucketIncrease = maxDownloadRate * (currentTimestamp - downloadTimestamp)
downloadBucket += bucketIncrease downloadBucket += bucketIncrease
if downloadBucket > maxDownloadRate: if downloadBucket > maxDownloadRate:
downloadBucket = int(maxDownloadRate) downloadBucket = int(maxDownloadRate)
@ -153,7 +163,7 @@ def update_sent(upload=0):
currentTimestamp = time.time() currentTimestamp = time.time()
sentBytes += upload sentBytes += upload
if maxUploadRate > 0: if maxUploadRate > 0:
bucketIncrease = int(maxUploadRate * (currentTimestamp - uploadTimestamp)) bucketIncrease = maxUploadRate * (currentTimestamp - uploadTimestamp)
uploadBucket += bucketIncrease uploadBucket += bucketIncrease
if uploadBucket > maxUploadRate: if uploadBucket > maxUploadRate:
uploadBucket = int(maxUploadRate) uploadBucket = int(maxUploadRate)
@ -170,9 +180,9 @@ def _exception(obj):
def readwrite(obj, flags): def readwrite(obj, flags):
try: try:
if flags & select.POLLIN: if flags & select.POLLIN and can_receive():
obj.handle_read_event() obj.handle_read_event()
if flags & select.POLLOUT: if flags & select.POLLOUT and can_send():
obj.handle_write_event() obj.handle_write_event()
if flags & select.POLLPRI: if flags & select.POLLPRI:
obj.handle_expt_event() obj.handle_expt_event()