logger.info('inv message lists %s objects. Of those %s are new to me. It took %s seconds to figure that out.',numberOfItemsInInv,len(objectsNewToMe),time.time()-startTime)
'''select payload from inventory where hash=? and expirestime>=?''',
hash,
int(time.time()))
ifqueryreturn!=[]:
forrowinqueryreturn:
payload,=row
self.sendObject(payload)
ifhashinshared.inventory:
self.sendObject(shared.inventory[hash].payload)
else:
self.antiIntersectionDelay()
logger.warning('%s asked for an object with a getdata which is not in either our memory inventory or our SQL inventory. We probably cleaned it out after advertising it but before they got around to asking for it.'%(self.peer,))
'''UPDATE sent SET status='doingmsgpow', retrynumber=0 WHERE toaddress=? AND (status='msgqueued' or status='awaitingpubkey' or status='doingpubkeypow')''',
toaddress)
delshared.neededPubkeys[tag]
break
#else: # There was something wrong with this pubkey object even
# though it had the correct tag- almost certainly because
# of malicious behavior or a badly programmed client. If
# there are any other pubkeys in our inventory with the correct
# tag then we'll try to decrypt those.
ifneedToRequestPubkey:# Obviously we had no success looking in the sql inventory. Let's look through the memory inventory.
ifshared.decryptAndCheckPubkeyPayload(payload,toaddress)=='successful':#if valid, this function also puts it in the pubkeys table.
needToRequestPubkey=False
sqlExecute(
'''UPDATE sent SET status='doingmsgpow', retrynumber=0 WHERE toaddress=? AND (status='msgqueued' or status='awaitingpubkey' or status='doingpubkeypow')''',
ifshared.decryptAndCheckPubkeyPayload(value.payload,toaddress)=='successful':#if valid, this function also puts it in the pubkeys table.
needToRequestPubkey=False
sqlExecute(
'''UPDATE sent SET status='doingmsgpow', retrynumber=0 WHERE toaddress=? AND (status='msgqueued' or status='awaitingpubkey' or status='doingpubkeypow')''',
toaddress)
delshared.neededPubkeys[tag]
break
#else: # There was something wrong with this pubkey object even
# though it had the correct tag- almost certainly because
# of malicious behavior or a badly programmed client. If
# there are any other pubkeys in our inventory with the correct
# tag then we'll try to decrypt those.
ifneedToRequestPubkey:
sqlExecute(
'''UPDATE sent SET status='doingpubkeypow' WHERE toaddress=? AND status='msgqueued'''',
@ -811,7 +790,6 @@ class singleWorker(threading.Thread, StoppableThread):
shared.UISignalQueue.put(('updateSentItemStatusByAckdata',(ackdata,tr.translateText("MainWindow","Message sent. Sent at %1").arg(l10n.formatTimestamp()))))
else:
@ -921,7 +899,6 @@ class singleWorker(threading.Thread, StoppableThread):
sendDataQueues=[]#each sendData thread puts its queue in this list.
inventory={}#of objects (like msg payloads and pubkey payloads) Does not include protocol headers (the first 24 bytes of each packet).
inventoryLock=threading.Lock()#Guarantees that two receiveDataThreads don't receive and process the same message concurrently (probably sent by a malicious individual)
inventoryLock=threading.RLock()#Guarantees that two receiveDataThreads don't receive and process the same message concurrently (probably sent by a malicious individual)
printLock=threading.Lock()
appdata=''#holds the location of the application data storage directory
statusIconColor='red'
@ -85,7 +84,6 @@ lastTimeWeResetBytesSent = 0 # used for the bandwidth rate limit
sendDataLock=threading.Lock()# used for the bandwidth rate limit
receiveDataLock=threading.Lock()# used for the bandwidth rate limit
daemon=False
inventorySets={1:set()}# key = streamNumer, value = a set which holds the inventory object hashes that we are aware of. This is used whenever we receive an inv message from a peer to check to see what items are new to us. We don't delete things out of it; instead, the singleCleaner thread clears and refills it every couple hours.
needToWriteKnownNodesToDisk=False# If True, the singleCleaner will write it to disk eventually.
maximumLengthOfTimeToBotherResendingMessages=0
objectProcessorQueue=ObjectProcessorQueue()# receiveDataThreads dump objects they hear on the network into this queue to be processed.
self._inventory={}#of objects (like msg payloads and pubkey payloads) Does not include protocol headers (the first 24 bytes of each packet).
self._streams=collections.defaultdict(set)# key = streamNumer, value = a set which holds the inventory object hashes that we are aware of. This is used whenever we receive an inv message from a peer to check to see what items are new to us. We don't delete things out of it; instead, the singleCleaner thread clears and refills it every couple hours.
def__contains__(self,hash):
globalnumberOfInventoryLookupsPerformed
withinventoryLock:
numberOfInventoryLookupsPerformed+=1
ifhashinself._inventory:
returnTrue
returnbool(sqlQuery('SELECT 1 FROM inventory WHERE hash=?',hash))
def__getitem__(self,hash):
withinventoryLock:
ifhashinself._inventory:
returnself._inventory[hash]
rows=sqlQuery('SELECT objecttype, streamnumber, payload, expirestime, tag FROM inventory WHERE hash=?',hash)
ifnotrows:
raiseKeyError(hash)
returnInventoryItem(*rows[0])
def__setitem__(self,hash,value):
withinventoryLock:
value=InventoryItem(*value)
self._inventory[hash]=value
self._streams[value.stream].add(hash)
def__delitem__(self,hash):
raiseNotImplementedError
def__iter__(self):
withinventoryLock:
hashes=self._inventory.keys()[:]
hashes+=(hashforhash,insqlQuery('SELECT hash FROM inventory'))
returnhashes.__iter__()
def__len__(self):
withinventoryLock:
returnlen(self._inventory)+sqlQuery('SELECT count(*) FROM inventory')[0][0]
values+=(InventoryItem(*value)forvalueinsqlQuery('SELECT objecttype, streamnumber, payload, expirestime, tag FROM inventory WHERE objecttype=? AND tag=?',type,tag))
#Note that the singleCleanerThread clears out the inventory dictionary from time to time, although it only clears things that have been in the dictionary for a long time. This clears the inventory dictionary Now.