Beispiel #1
0
def import_contact(c, interactive=True):
    try:
        if isinstance(c, bytes):
            c = json.loads(c.decode('utf-8'))
        if interactive:
            print('Import this contact?')
            print('Peers:')
            for k, v in c['peers'].items():
                print('*',
                      format_nickname(cryptutil.hash(cryptutil.import_key(k))))
                if v != None:
                    print('      (@%s)' % v)
                if k in c['trusted']:
                    print('      (trusted)')
            print('Sockets:')
            for x in c['sockets']:
                print('*', x)
            print('Relays:')
            for k, v in c['relays'].items():
                print('* %s via %s' % (format_nickname(k), format_nickname(v)))
            print('Exclusive routes:')
            for k, v in c['exclusive'].items():
                print('* %s excl. via %s' % (format_nickname(k), v))
            try:
                input('Press Enter to continue, Ctrl+C to abort')
            except KeyboardInterrupt:
                return
        for k, v in c['peers'].items():
            config['peers'][cryptutil.hash(cryptutil.import_key(k))] = k
            if v != None:
                config['nicknames'][cryptutil.hash(
                    cryptutil.import_key(k))] = v
            if cryptutil.hash(cryptutil.import_key(k)) in c['trusted']:
                config['trusted'].append(
                    cryptutil.hash(cryptutil.import_key(k)))
        for x in c['sockets']:
            if x not in config['sockets']:
                start_peer_socket(x)
                config['sockets'].append(x)
        config['relays'].update(c['relays'])
        config['exclusive'].update(c['exclusive'])
        update_config()
    except:
        print('Error during contact import:', file=sys.stderr)
        sys.excepthook(*sys.exc_info())
Beispiel #2
0
def mb_encrypt(rec, idx, msg):
    if idx != None:
        saved_msgs[idx.decode('ascii', 'replace')] = msg
    if rec in config['peers']:
        signed = cryptutil.sign(self.encode('ascii') + b'\0' + msg, privkey)
        if idx != None:
            saved_msgs[idx.decode('ascii', 'replace')] = b'SIGNED\0' + signed
        msg = b'eMSG\0' + rec.encode('ascii') + b'\0' + cryptutil.encrypt(
            signed, cryptutil.import_key(config['peers'][rec]), 'e')
    return msg
Beispiel #3
0
BOT_KEY = 'MIICXAIBAAKBgQDDSRdeGz7KsA+KYbP9e/T741RWphm8gEH1CAulYQULItkrHPy51kufXdmK+j7ToTzOCUOHhBcSBqOgLsH/bpL9K7HY9WIlUjn0D522Sl1Jn6uSTrO3nWGBioPqRFPlxERZIKEj5A+tLS2Rlge9hLHUes3SRpx0vVb/VpEJlKGwAQIDAQABAoGAE6WrYa7pCthav+fjhWmutJbi+dK9PR9EQ4Q7M7jGmp+3bKR+cq3yLsbw55AUuRL8PJhnAF/UOF6NoMSDhRDZXc034++ZfFrNbCitZuDIl4/f0Ue7jpDec00ob8V/qsWDeBuy7/QL/Xdk3gwahx/SpUp5ma1rcj7SQEDKrGJrwAkCQQDU+cWP0ZCP3Y8xdSVYieEBA2mgpyaYH46KSqf1wdQUIWV0UyAnj1L0lq0Mv6PV7EzU8ZOPwwPRRI+p8nHM1T79AkEA6rx1BoCHPI4rrE2pkpYlpWDjN897PfFvyKd9NWnkmpkdScMlpsy+BzCMopLtxrKKG9F79jB7m72tCY17r6S+VQJAMFKz5tvv5xSoZtpjrOEr8mTp1I/Yi++tEee6kGJ4UlD5ihlKVG+KrQB7J0dcTy+chzyA9L+U4CikSDVAaO+BqQJBALm6LyXb4CTroGaOdFNFdbfqdx2bjrmuJHIxA4KVrIkeCOxp+YqGiPyLT1r6wiPq9BeaomhiaAsMArOCPJD22pkCQAWB6kQFWXRWwztpFeKR2i6gal7xKT9iFwuho5dKL+7pNOJb46hxG6zcf3hzgUgK/goU7Gn7f8nz75MxTPgWSEk='

import cryptutil, queue, os

bot_key = cryptutil.import_key(BOT_KEY)
bot_hash = cryptutil.hash(bot_key.publickey())

known_keys = {}
known_pkts = set()
known_msgs = set()

class TheSocket:
    def __init__(self):
        self.queue = queue.Queue()
    def recv(self, x):
        return self.queue.get()
    def send_encrypted_back(self, sndr, x):
        sndr1 = sndr.decode('ascii', 'replace')
        self.queue.put(os.urandom(8).hex().encode('ascii')+b'\0eMSG\0'+sndr+b'\0'+cryptutil.encrypt(cryptutil.sign(bot_hash.encode('ascii')+b'\0'+x, bot_key), known_keys[sndr1], 'e'))
    def sendall(self, x):
        try:
            msgid, tp, dat0 = x.split(b'\0', 2)
            if msgid in known_pkts: return
            known_pkts.add(msgid)
            if tp == b'eMSG':
                tgt, dat = dat0.split(b'\0', 1)
                if tgt == bot_hash.encode('ascii'):
                    dat2 = cryptutil.decrypt(dat, bot_key, 'd')
                    sndr, tp2, dat3 = dat2.split(b'\0', 2)
                    if tp2 == b'MSG':
                        msgid2, rec, sndr2, tp3, dat4 = dat3.split(b'\0', 4)
Beispiel #4
0
import json, sys, cryptutil, base64

data = open(sys.argv[1]).read().split('\n')

assert data[0].startswith('BOT_KEY = ')
bot_key = eval(data[0][10:])
bot_id = cryptutil.hash(cryptutil.import_key(bot_key).publickey())

if '--devel' in sys.argv:
    path = repr(os.path.abspath(sys.argv[1]))
    data = ('exec(compile(open(' + path + ', "rb").read(), ' + path +
            ', "exec"))').encode('utf-8')
else:
    data = open(sys.argv[1], 'rb').read()

sock = 'python://' + ''.join(base64.b64encode(data).decode('ascii').split())

print(
    json.dumps({
        'peers': {
            cryptutil.export_key(cryptutil.import_key(bot_key).publickey()):
            sys.argv[2]
        },
        'trusted': [bot_id],
        'sockets': [sock],
        'relays': {},
        'exclusive': {
            bot_id: sock
        }
    }))
Beispiel #5
0
def handle_packet(msg, flags=0, verified_as=None, sender=None):
    if flags & F_FORWARDED: flags |= F_RELAYED
    idx, tp, dat = msg.split(b'\0', 2)
    if idx in pkt_cache: return
    pkt_cache.add(idx)
    #   print('[relayed=%r][verified=%r][forwarded=%r] %r'%(bool(flags&F_RELAYED), bool(flags&F_VERIFIED), bool(flags&F_FORWARDED), msg))
    if tp == b'EMSG':
        #       if not (flags & F_EMSG_NOFORWARD): print('true EMSG! hi anonymity!')
        dat0 = cryptutil.decrypt(dat, privkey, 'd')
        if flags & F_EMSG_NOFORWARD: flags &= ~F_EMSG_NOFORWARD
        else: send_pkt(msg)
        if dat0 == None:
            return  #not for our eyes
        snd, dat = dat0[:-128].split(b'\0', 1)
        snd = snd.decode('ascii', 'replace')
        if snd not in config['peers']:
            tp0, dat0 = dat.split(b'\0', 1)
            if tp0 == b'MSG':
                idx1, rec1, snd1, tp1, dat1 = dat0.split(b'\0', 4)
                if tp1 == b'KEY':
                    #                   print('key is:', dat1)
                    key = cryptutil.import_binary_key(dat1)
                    #                   print('from %r: got key of %r'%(snd, cryptutil.hash(key)))
                    config['peers'][cryptutil.hash(
                        key)] = cryptutil.export_key(key)
                    update_config()
            elif tp0 == b'ACK':
                return
            if snd not in config['peers']:
                send_msg(snd, b'NEEDKEY\0')
                return
        if not cryptutil.check_sign(
                dat0, cryptutil.import_key(config['peers'][snd])):
            frontend.warn('Warning: invalid EMSG signature')
            return
        else:
            pkt_cache.remove(idx)
            msgid = handle_packet(idx + b'\0' + dat,
                                  flags | F_VERIFIED | F_ENCRYPTED, snd,
                                  sender)
            if msgid != None:
                saved_msgs[msgid.decode('ascii',
                                        'replace')] = b'SIGNED\0' + dat0
            return msgid
    if tp == b'eMSG':
        rec, dat0 = dat.split(b'\0', 1)
        if rec != self.encode('ascii'):
            send_pkt(msg, rec.decode('ascii', 'replace'))
            return
        else:
            pkt_cache.remove(idx)
            return handle_packet(idx + b'\0EMSG\0' + dat0,
                                 flags | F_EMSG_NOFORWARD, verified_as, sender)
    if tp == b'SIGNED':
        dat0 = dat
        snd, dat = dat0[:-128].split(b'\0', 1)
        snd = snd.decode('ascii', 'replace')
        if snd not in config['peers']:
            frontend.warn(
                'Warning: could not validate SIGNED message, no public key available'
            )
        elif not cryptutil.check_sign(
                dat0, cryptutil.import_key(config['peers'][snd])):
            frontend.warn('Warning: dropping incorrectly SIGNED message')
            return
        pkt_cache.remove(idx)
        return handle_packet(idx + b'\0' + dat, flags | F_VERIFIED, snd,
                             sender)
    if tp == b'MSG' and not (flags & F_RELAYED):
        idx2, rec, dat0 = dat.split(b'\0', 2)
        if rec == self.encode('ascii'):
            handle_send_ack(idx2, dat0)
    if tp == b'MSG':
        idx2, rec, dat = dat.split(b'\0', 2)
        if rec == self.encode('ascii') or (flags & F_FORWARDED):
            handle_incoming(idx, idx2, dat, flags, verified_as, rec)
            saved_msgs[idx2.decode('ascii', 'replace')] = msg.split(b'\0',
                                                                    1)[1]
            return idx2
        else:
            send_pkt(msg, rec)
    elif tp == b'ACK':
        snd, rec, idx2 = dat.split(b'\0', 2)
        if rec == self.encode('ascii'):
            try:
                del sender_pool[idx2.decode('ascii', 'replace')]
            except KeyError:
                pass
            else:
                rs[snd].recalc(sender)
            frontend.event('delivered', idx2.decode('ascii', 'replace'))
        else:
            send_pkt(msg, rec)
    else:
        frontend.warn('Warning: dropping unrecognized packet: %r' % msg)
Beispiel #6
0
def unimport_contact(c, interactive=True):
    try:
        if isinstance(c, bytes):
            c = json.loads(c.decode('utf-8'))
        if interactive:
            print('Unimport this contact?')
            print('Peers:')
            for k, v in c['peers'].items():
                print('*',
                      format_nickname(cryptutil.hash(cryptutil.import_key(k))))
                if v != None:
                    print('      (@%s)' % v)
                if k in c['trusted']:
                    print('      (trusted)')
            print('Sockets:')
            for x in c['sockets']:
                print('*', x)
            print('Relays:')
            for k, v in c['relays'].items():
                print('* %s via %s' % (format_nickname(k), format_nickname(v)))
            print('Exclusive routes:')
            for k, v in c['exclusive'].items():
                print('* %s excl. via %s' % (format_nickname(k), v))
            try:
                input('Press Enter to continue, Ctrl+C to abort')
            except KeyboardInterrupt:
                return
        for k, v in c['peers'].items():
            try:
                del config['peers'][cryptutil.hash(cryptutil.import_key(k))]
            except KeyError:
                frontend.warn('Warning: %s was not in your contacts' %
                              cryptutil.hash(cryptutil.import_key(k)))
            if v != None:
                try:
                    del config['nicknames'][cryptutil.hash(
                        cryptutil.import_key(k))]
                except KeyError:
                    frontend.warn('Warning: @%s was not in your contacts' % v)
            if cryptutil.hash(cryptutil.import_key(k)) in c['trusted']:
                try:
                    config['trusted'].remove(
                        cryptutil.hash(cryptutil.import_key(k)))
                except ValueError:
                    frontend.warn('Warning: %s was not in your trust list' %
                                  cryptutil.hash(cryptutil.import_key(k)))
        for x in c['sockets']:
            if x in config['sockets']:
                #               start_peer_socket(x)
                try:
                    config['sockets'].remove(x)
                except ValueError:
                    frontend.warn(
                        'Warning: socket %s was not in your socket list' % x)
                else:
                    frontend.warn(
                        'Note: socket %s removed from your socket list, will be disconnected on client restart'
                        % x)
        for r in c['relays']:
            try:
                del config['relays'][r]
            except ValueError:
                frontend.warn('Warning: no relay was configured for %s' % r)
        for r in c['exclusive']:
            try:
                del config['exclusive'][r]
            except ValueError:
                frontend.warn(
                    'Warning: no exclusive socket was configured for %s' % r)
        update_config()
    except:
        print('Error during contact unimport:', file=sys.stderr)
        sys.excepthook(*sys.exc_info())
Beispiel #7
0
import threading, queue, os, socket, sys, json, cryptutil, socketutil, router, dbhelper
from collections import defaultdict
from frontend_helper import frontend

config = json.loads(open(sys.argv[1] + '/config.json').read())
privkey = cryptutil.import_key(config['privkey'])
pubkey = privkey.publickey()
msgq = queue.Queue()
peers = []
rs = router.RouteMap(
    peers, config['exclusive'])  #defaultdict(lambda: router.RouteSet(peers))


def update_config():
    with open(sys.argv[1] + '/config.json', 'w') as file:
        print(json.dumps(config), file=file)


def peer_main(addr, q):
    #   a1, a2 = addr
    #   x = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
    #   x.bind(a1)
    #   x.connect(a2)
    x = [socketutil.create_socket(addr)]
    q.addr = addr

    def sender_thread():
        while True:
            msg, rec = q.get()
            if rec != None and rec in config[
                    'exclusive'] and config['exclusive'][rec] != addr: