def patchkey(key, i, rsakey, fp): # find signature packet offset=0 # must be secret/public key packet type if ((key[0] & 0x3f) >> 2) not in [5, 6]: print "data does not start with a key packet" sys.exit(1) o2, l = old_tag_length(key,offset) datestart=offset+2+o2 offset+=1 + o2 + l # next must be keyid packet type if ((key[offset] & 0x3f) >> 2) !=13: print "packet is not a keyid" sys.exit(1) # nothing to see here - skip to next o2, l = old_tag_length(key,offset) offset+=1 + o2 + l # next packet must be signature packet type if ((key[offset] & 0x3f) >> 2)!=2: print "packet is not a signature" sys.exit(1) # skip to end of hashed data o2, l = old_tag_length(key,offset) offset+=struct.unpack('!H', str(key[offset+5+o2:offset+7+o2]))[0]+7+o2 #print "end of hashed data:", offset #print ' '.join(["%02x" % x for x in key[offset:offset+32]]) if not key[offset+2:offset+4]==bytearray([9,0x10]): print "issuer not found" sys.exit(1) # calculate hash of data to be signed hash=hashlib.sha1(str(key[:offset])).digest() # find out offset to store the keys hstart=offset+struct.unpack('!H', str(key[offset:offset+2]))[0]+2 # patch date key[datestart:datestart+4]=struct.pack('!i',i) # patch issuer id key[offset+4:offset+12]=fp[-8:] # sign and patch the key sig = rsakey.sign(hash, Random.get_random_bytes(20)) sig=utils.get_int_bytes(sig) siglen=len(sig)*8 patch=''.join([hash[-2:], struct.pack('!H',siglen), str(sig)]) key[hstart:hstart+len(patch)]=patch
def test_old_tag_length(self): data = [ ((1, 2), [0xb0, 0x02]), ((1, 70), [0x88, 0x46]), ((2, 284), [0x89, 0x01, 0x1c]), ((2, 525), [0xb9, 0x02, 0x0d]), ((2, 1037), [0xb9, 0x04, 0x0d]), ] for expected, invals in data: self.assertEqual(expected, old_tag_length(invals, 0))
def getnewfp(key, i): # patch date offset, length = old_tag_length(key,0) buffer=bytearray(''.join(['\x99', struct.pack('!H', length), str(key[offset+1:offset+1+length])])) buffer[4:8]=struct.pack('!i',i) #print "%02x %02x %02x %02x" % tuple(map(int,key[4:8])) m = hashlib.sha1() m.update(str(buffer)) print 'setting new fingerprint:', m.hexdigest()[-16:], i, datetime.datetime.fromtimestamp(i) return m.digest()
def test_old_tag_length(self): data = [ ((1, 2), [0xb0, 0x02]), ((1, 70), [0x88, 0x46]), ((2, 284), [0x89, 0x01, 0x1c]), ((2, 525), [0xb9, 0x02, 0x0d]), ((2, 1037), [0xb9, 0x04, 0x0d]), ((2, 1037), bytearray(b'\xb9\x04\x0d')), ((2, 5119), [0xb9, 0x13, 0xff]), ((4, 100000), [0xba, 0x00, 0x01, 0x86, 0xa0]), ] for expected, invals in data: self.assertEqual(expected, old_tag_length(invals, 0))
def test_old_tag_length(self): data = [ ((1, 2), [0xB0, 0x02]), ((1, 70), [0x88, 0x46]), ((2, 284), [0x89, 0x01, 0x1C]), ((2, 525), [0xB9, 0x02, 0x0D]), ((2, 1037), [0xB9, 0x04, 0x0D]), ((2, 1037), bytearray(b"\xb9\x04\x0d")), ((2, 5119), [0xB9, 0x13, 0xFF]), ((4, 100000), [0xBA, 0x00, 0x01, 0x86, 0xA0]), ] for expected, invals in data: self.assertEqual(expected, old_tag_length(invals, 0))
import hashlib, struct, time, datetime, sys from pgpdump.packet import old_tag_length inkey = open(sys.argv[1], 'rb') pubkey = inkey.read() inkey.close() now = time.time() try: # resume from last snapshot i = int(sys.argv[2]) except: i = 0 # patch date offset, length = old_tag_length(bytearray(pubkey), 0) header = ''.join( ['\x99', struct.pack('!H', length), pubkey[offset + 1:offset + 2]]) trailer = pubkey[offset + 6:offset + 1 + length] while i < now: m = hashlib.sha1() m.update(''.join([header, struct.pack('!i', i), trailer])) print m.hexdigest()[-8:], i, "%02x %02x %02x %02x" % struct.unpack( '!BBBB', struct.pack('!i', i)), datetime.datetime.fromtimestamp(i) i += 1 if i % 1000000 == 0: print >> sys.stderr, m.hexdigest(), i, datetime.datetime.fromtimestamp( i) now = time.time()
from pgpdump.packet import old_tag_length inkey=open(sys.argv[1],'rb') pubkey=inkey.read() inkey.close() now=time.time() try: # resume from last snapshot i=int(sys.argv[2]) except: i=0 # patch date offset, length = old_tag_length(bytearray(pubkey),0) header=''.join(['\x99', struct.pack('!H', length), pubkey[offset+1:offset+2]]) trailer=pubkey[offset+6:offset+1+length] while i<now: m = hashlib.sha1() m.update(''.join([header, struct.pack('!i',i), trailer])) print m.hexdigest()[-8:], i, "%02x %02x %02x %02x" % struct.unpack('!BBBB',struct.pack('!i',i)), datetime.datetime.fromtimestamp(i) i+=1 if i%1000000==0: print >>sys.stderr, m.hexdigest(), i, datetime.datetime.fromtimestamp(i) now=time.time()