Скачиваний:
10
Добавлен:
27.05.2017
Размер:
50.05 Кб
Скачать
import sys
from PyQt5.Qt import *
from PyQt5.QtCore import *
from PyQt5.QtWidgets import *
import random
import base64
import pickle
from Crypto import Random
from Crypto.Cipher import AES
import datetime
import rsa

class AESCipher:

    def __init__( self, key ):
        self.key = key

    def encrypt(self, raw):
        BS = 16
        pad = lambda s: s + (BS - len(s) % BS) * chr(BS - len(s) % BS)##
        pad=lambda s:s+(BS-len(s)%BS)*chr(BS-len(s)%BS).encode('utf-8')#b'\xd0'
        unpad = lambda s : s[0:-s[-1]]
        raw = pad(raw)
        iv = Random.new().read(AES.block_size)
        cipher = AES.new(self.key, AES.MODE_CBC, iv)
        return base64.b64encode(iv + cipher.encrypt(raw))

    def decrypt(self, enc):
        BS = 16
        #pad = lambda s: s + (BS - len(s) % BS) * chr(BS - len(s) % BS)
        unpad = lambda s : s[0:-s[-1]]
        enc = base64.b64decode(enc)
        iv = enc[:16]
        cipher = AES.new(self.key, AES.MODE_CBC, iv)
        return unpad(cipher.decrypt( enc[16:] ))

class NotRealNetwork:

    '''буфер, симулирующий сеть'''

    def __init__(self):
        self.contact=dict()#здесь лежит информация про зарегистрированные объекты и их "почтовые ящики"
        # потоки будут по очереди использовать этот словарь через блокировку

    def enter(self, name):

        '''Вход объекта в "сеть". Через имя объект может получить информацию о том,
        что с ним хотят свяаться. Тогда в списке будет кортеж их имени отправителя и
        содержания послания'''

        if self.contact.get(name) is None:
            self.contact[name]=[]
            return True
        else:
            return False

    def delete(self, name):
        if self.contact.get(name) is None:
            return False
        else:
            self.contact.pop(name)
            return True


    def write(self, send_name, rec_name, data):

        '''Пишет в ящик получателя информацию и имя отправителя'''
        if self.contact.get(rec_name) is None:
            return False
        else:
            self.contact[rec_name].append((send_name, data))
            return True

    def read(self, name):

        '''Выдаёт получателю следующий по очереди отправленный ему пакет, если он есть'''

        if self.contact.get(name):
            return self.contact[name].pop(0)
        else:
            return []

class Subject:

    '''Субьект протокола, управляется пользователем'''

    def __init__(self, name, web):
        self.name=name
        self.web=web
        self.number=-1
        self.number_check=-1
        self.key=-1
        self.numberA=-1
        self.nimberB=-1
        self.asim_reg_database=dict()

    def reg_web(self):
        f=self.web.enter(self.name)
        return f

    def check(self, system_name, suc, fail):

        '''проверяет результаты действия. suc - строка, возврат которо обозначает успех, fail - наоборот'''
        obj=objs=self.web.read(self.name) #берём первое письмо и запоминаем
        if not obj or obj is None: #если ничего не написали, то следующая попытка
            return False

        while not (obj[0]==system_name and obj[1]['nomination']==suc): #другое письмо
            if obj[0]==system_name and obj[1]['nomination']==fail: #пришёл отказ - регистрация не удалать
                return False

            self.web.write(obj[0], self.name, obj[1]) #возвращаем ненужное письмо обратно в очередь
            obj=self.web.read(self.name) #и берём следующее
            if obj[1] is objs[1]: #если все письма уже перебрали, а нужного не нашли
                break
        else: # нашли нужное письмо!
            return obj

    def check_time(self, time):
        stime=datetime.datetime.now()
        if time.hour==stime.hour and time.minute>=stime.minute-10 and time.minute<=stime.minute:
            return True
        else:
            return False

    def sim_reg(self, system_name, name, password):
        send = dict()
        send['nomination'] = 'sim reg'
        send['name'] = name
        send['password'] = password
        f = self.web.write(self.name, system_name, send)
        return f

    def sim_reg_result(self, system_name):
        res=self.check(system_name, 'sim reg done', 'sim reg fail')
        return res

    def nid_shr_inquiry(self, system_name, name, other_name):
        send = dict()
        send['nomination'] = 'sim nid shr inquiry'
        send['name'] = name
        send['other name'] = other_name
        number = random.randint(0, 2000000)
        self.number=number
        send['random'] = number
        f = self.web.write(self.name, system_name, send)
        return (f, number)

    def nid_shr_delivery(self, system_name, password, other_name):
        res=self.check(system_name, 'nid shr answer', 'nid shr fail')
        if not res:
            return False
        cipher = AESCipher(password)
        decrypted=cipher.decrypt(res[1]['answer'])
        decrypted = pickle.loads(decrypted)
        self.key=str(decrypted[2])
        if self.number!=decrypted[0]:
            return False

        send=dict()
        send['nomination']='nid shr transfer'
        send['transfer']=decrypted[3]
        f=self.web.write(self.name, other_name, send)
        return (f, decrypted)

    def nid_shr_check(self, other_name, password):
        res=self.check(other_name, 'nid shr transfer', 'nid shr fail')
        if not res:
            return False
        cipher = AESCipher(password)
        decrypted = pickle.loads(cipher.decrypt(res[1]['transfer']))
        key=decrypted[0]
        self.key=str(key)
        self.number_check=random.randint(0, 2000000)
        cipher = AESCipher(str(key))
        encrypted=cipher.encrypt(str(self.number_check).encode('utf-8'))

        send=dict()
        send['nomination']='nid shr check'
        send['check']=encrypted
        f=self.web.write(self.name, decrypted[1], send)
        return (f, decrypted, self.number_check)

    def nid_shr_check_step_two(self, other_name):
        res=self.check(other_name, 'nid shr check', 'nid shr fail')
        if not res:
            return False
        cipher = AESCipher(self.key)
        decrypted = cipher.decrypt(res[1]['check'])
        encrypted=decrypted.decode('utf-8')
        s=encrypted=int(encrypted)-1
        encrypted=str(encrypted).encode('utf-8')
        encrypted=cipher.encrypt(encrypted)
        send=dict()
        send['nomination']='nid shr check two'
        send['check two']=encrypted
        f=self.web.write(self.name, other_name, send)
        return (f, s+1)

    def nid_shr_finally(self, other_name):
        res=self.check(other_name, 'nid shr check two', 'nid shr fail')
        if not res:
            return False
        cipher = AESCipher(self.key)
        decrypted = cipher.decrypt(res[1]['check two']).decode('utf-8')
        if decrypted==str(self.number_check-1):
            return (True, decrypted)
        else:
            return False

    def kerberos_inquiry(self, system_name, name, other_name):
        send = dict()
        send['nomination'] = 'kerberos inquiry'
        send['name'] = name
        send['other name'] = other_name
        f = self.web.write(self.name, system_name, send)
        return f

    def kerberos_delivery(self, system_name, password, other_name):
        res=self.check(system_name, 'kerberos answer', 'kerberos fail')
        if not res:
            return False
        cipher = AESCipher(password)
        decrypted=cipher.decrypt(res[1]['answer'][0])
        decrypted = pickle.loads(decrypted)
        self.key=str(decrypted[2])
        self.time=decrypted[0]
        if not self.check_time(decrypted[0]):
            return False

        cipher = AESCipher(self.key)
        asend = cipher.encrypt(pickle.dumps((self.name, decrypted[0]), 2))
        bsend=res[1]['answer'][1]

        send=dict()
        send['nomination']='kerberos transfer'
        send['transfer']=(asend, bsend)
        f=self.web.write(self.name, other_name, send)
        return (f, decrypted)

    def kerberos_check(self, other_name, password):
        res=self.check(other_name, 'kerberos transfer', 'kerberos fail')
        if not res:
            return False
        cipher = AESCipher(password)
        decryptedB = pickle.loads(cipher.decrypt(res[1]['transfer'][1]))
        if not self.check_time(decryptedB[0]):
            return False
        key=decryptedB[2]
        self.key=str(key)

        cipher = AESCipher(self.key)
        decryptedA=pickle.loads(cipher.decrypt(res[1]['transfer'][0]))
        if decryptedA[0]!=decryptedB[3] or decryptedA[1]!=decryptedB[0]:
            return False

        time=decryptedB[0].replace(hour=decryptedB[0].hour+1)

        cipher = AESCipher(str(key))
        encrypted=cipher.encrypt(pickle.dumps(time, 2))

        send=dict()
        send['nomination']='kerberos check'
        send['check']=encrypted
        f=self.web.write(self.name, decryptedA[0], send)
        return (f, decryptedA, self.key)

    def kerberos_check_step_two(self, other_name):
        res=self.check(other_name, 'kerberos check', 'kerberos fail')
        if not res:
            return False
        cipher = AESCipher(self.key)
        decrypted = cipher.decrypt(res[1]['check'])
        decrypted=pickle.loads(decrypted)

        if not (decrypted.hour==self.time.hour+1 and decrypted.minute==self.time.minute and decrypted.second==self.time.second):
            return False

        return decrypted

    def otway_inquiry(self, password, name, other_name):
        send = dict()
        send['nomination'] = 'otway inquiry'
        send['name'] = name
        send['other name'] = other_name
        number = random.randint(0, 2000000)
        self.number=number
        numberA = random.randint(0, 2000000)
        self.numberA=numberA
        send['N'] = number

        cipher=AESCipher(password)
        send['encrypted'] =cipher.encrypt(pickle.dumps((numberA, number, name, other_name), 2))

        f = self.web.write(self.name, other_name, send)
        return (f, number, numberA)

    def otway_delivery(self, system_name, password, other_name):
        res=self.check(other_name, 'otway inquiry', 'otway fail')
        if not res:
            return False
        cipher = AESCipher(password)
        numberB=random.randint(0, 2000000)
        self.nimberB=numberB
        encryptedB=cipher.encrypt(pickle.dumps((numberB, res[1]['N'], res[1]['name'], self.name),2))

        send=dict()
        send['nomination']='otway delivery'
        send['N']=res[1]['N']
        send['other name']=res[1]['name']
        send['name']=self.name
        send['encryptedA']=res[1]['encrypted']
        send['encryptedB']=encryptedB
        f=self.web.write(self.name, system_name, send)
        return (f, res[1]['name'], self.nimberB, res[1]['N'])

    def otway_delivery_two(self, system_name, password, other_name):
        res=self.check(system_name, 'otway answer', 'otway fail')
        if not res:
            return False

        decrypted=res[1]['answerB']
        cipher = AESCipher(password)
        decrypted=cipher.decrypt(decrypted)
        decrypted=pickle.loads(decrypted)

        if decrypted[0]!=self.nimberB:
            return False

        self.key=decrypted[1]

        send=dict()
        send['nomination']='otway delivery two'
        send['name']=self.name
        send['delivery two']=res[1]['answerA']
        f=self.web.write(self.name, other_name, send)
        return (f, self.key, decrypted[0])

    def otway_finally(self, system_name, password, other_name):
        res=self.check(other_name, 'otway delivery two', 'otway fail')
        if not res:
            return False

        decrypted=res[1]['delivery two']
        cipher = AESCipher(password)
        decrypted=cipher.decrypt(decrypted)
        decrypted=pickle.loads(decrypted)
        if decrypted[0]!=self.numberA:
            return False

        self.key=decrypted[1]
        return (self.key, decrypted[0])

    def asim_reg(self, name, other_name):
        (pubkey, privkey) = rsa.newkeys(512)
        self.privkey=privkey
        send = dict()
        send['nomination'] = 'asim reg'
        send['name'] = name
        send['password'] = pubkey
        f = self.web.write(self.name, other_name, send)
        return f

    def asim_reg_check(self, name, other_name):
        send = dict()
        res = self.check(other_name, 'asim reg', 'asim fail')
        if not res or self.asim_reg_database.get(res[1]['name']):
            send['nomination']='asim reg fail'
            self.web.write(name, res[1]['name'], send)
            return False

        self.asim_reg_database[res[1]['name']]=res[1]['password']

        send['nomination'] = 'asim reg done'
        f = self.web.write(name, res[1]['name'], send)
        return (f, res[1]['name'], res[1]['password'])

    def asim_reg_result(self, other_name):
        res=self.check(other_name, 'asim reg done', 'asim reg fail')
        return res

    def asim_inquiry(self, name, other_name):
        send = dict()
        send['nomination'] = 'asim inquiry'
        send['name'] = name
        send['other name'] = other_name
        keyA = random.randint(0, 2000000)
        self.keyA=keyA
        crypto=pickle.dumps((name, self.keyA),2)
        crypto=rsa.encrypt(crypto, self.asim_reg_database[other_name])
        send['crypto']=crypto

        f = self.web.write(self.name, other_name, send)
        return (f, self.keyA)

    def asim_answer(self, name, other_name):
        res=self.check(other_name, 'asim inquiry', 'asim fail')
        if not res:
            return False

        message=rsa.decrypt(res[1]['crypto'], self.privkey)
        message=pickle.loads(message)

        if message[0]!=res[0]:
            send=dict()
            send['nomination']='asim fail'
            self.web.write(self.name, other_name, send)
            return False

        self.keyB=random.randint(0, 2000000)
        self.keyA=message[1]
        crypto=rsa.encrypt(pickle.dumps((self.keyA, self.keyB),2), self.asim_reg_database[message[0]])

        send=dict()
        send['nomination']='asim answer'
        send['other name']=other_name
        send['name']=self.name
        send['answer']=crypto
        f=self.web.write(self.name, other_name, send)
        return (f, res[1]['name'], self.keyA, self.keyB)

    def asim_answer_two(self, name, other_name):
        res=self.check(other_name, 'asim answer', 'asim fail')
        if not res:
            return False

        message=rsa.decrypt(res[1]['answer'], self.privkey)
        message=pickle.loads(message)

        if message[0]!=self.keyA:
            send=dict()
            send['nomination']='asim fail'
            self.web.write(self.name, other_name, send)
            return False

        self.keyB=message[1]
        crypto=rsa.encrypt(pickle.dumps((self.keyB),2), self.asim_reg_database[res[0]])

        send=dict()
        send['nomination']='asim answer two'
        send['other name']=other_name
        send['name']=self.name
        send['answer']=crypto
        f=self.web.write(self.name, other_name, send)
        return (f, res[1]['name'], self.keyA, self.keyB)

    def asim_finally(self, name, other_name):
        res=self.check(other_name, 'asim answer two', 'asim fail')
        if not res:
            return False

        message=rsa.decrypt(res[1]['answer'], self.privkey)
        message=pickle.loads(message)

        if message!=self.keyB:
            send=dict()
            send['nomination']='asim fail'
            self.web.write(self.name, other_name, send)
            return False

        return (message)

class AuthSystem:

    '''Аутентификационная система'''

    def __init__(self, name, web):
        self.name=name
        self.web=web
        self.data=[]
        self.sim_database=dict()

    def reg_web(self):
        f=self.web.enter(self.name)
        return f

    def del_web(self):
        f=self.web.delete(self.name)
        return f

    def sim_reg(self, name, obj):
        send = dict()
        if self.sim_database.get(obj['name']) is None:
            self.sim_database[obj['name']] = obj['password']
            send['nomination'] = 'sim reg done'
            self.web.write(self.name, name, send)
            return True
        else:
            send['nomination'] = 'sim reg fail'
            self.web.write(self.name, name, send)
            return False

    def nid_shr_response(self, name, obj):
        send = dict()
        if self.sim_database.get(obj['name']) is None or self.sim_database.get(obj['other name']) is None:
            send['nomination'] = 'nid shr fail'
            self.web.write(self.name, name, send)
            return False
        else:
            key=random.randint(1000000000000000, 9999999999999999)
            cipherA = AESCipher(self.sim_database[obj['name']])
            cipherB=AESCipher(self.sim_database[obj['other name']])
            bsend=cipherB.encrypt(pickle.dumps((key, obj['name']), 2))
            letter=pickle.dumps((obj['random'], obj['other name'], key, bsend), 2)
            encrypted = cipherA.encrypt(letter)
            send['nomination'] = 'nid shr answer'
            send['answer']=encrypted
            self.web.write(self.name, name, send)
            return key

    def kerberos_response(self, name, obj):
        send = dict()
        if self.sim_database.get(obj['name']) is None or self.sim_database.get(obj['other name']) is None:
            send['nomination'] = 'kerberos fail'
            self.web.write(self.name, name, send)
            return False
        else:
            key=random.randint(1000000000000000, 9999999999999999)
            time=datetime.datetime.now()
            l='Неделя'
            cipherB=AESCipher(self.sim_database[obj['other name']])
            bsend=cipherB.encrypt(pickle.dumps((time, l, key, obj['name']), 2))

            cipherA = AESCipher(self.sim_database[obj['name']])
            letter=pickle.dumps((time, l, key, obj['other name']), 2)
            asend = cipherA.encrypt(letter)

            send['nomination'] = 'kerberos answer'
            send['answer']=(asend, bsend)

            self.web.write(self.name, name, send)
            return (time, key)

    def otway_response(self, name, obj):
        send = dict()
        if self.sim_database.get(obj['name']) is None or self.sim_database.get(obj['other name']) is None:
            send['nomination'] = 'otway fail'
            self.web.write(self.name, name, send)
            return False
        else:
            key=random.randint(1000000000000000, 9999999999999999)

            cipherA = AESCipher(self.sim_database[obj['other name']])
            cipherB=AESCipher(self.sim_database[obj['name']])

            decryptedA=cipherA.decrypt(obj['encryptedA'])
            decryptedA=pickle.loads(decryptedA)
            asend=cipherA.encrypt(pickle.dumps((decryptedA[0], key), 2))

            decryptedB = cipherB.decrypt(obj['encryptedB'])
            decryptedB = pickle.loads(decryptedB)
            bsend = cipherB.encrypt(pickle.dumps((decryptedB[0], key), 2))

            send['nomination'] = 'otway answer'
            send['answerA']=asend
            send['answerB']=bsend
            self.web.write(self.name, obj['name'], send)
            return key

    def signal_waiting(self):
        obj=self.web.read(self.name)#obj - name, описание, login, password
        if not obj or obj is None:
            return
        if obj[1]['nomination']=='sim reg':
            f=self.sim_reg(obj[0], obj[1])
            self.data.append((obj, f))
        elif obj[1]['nomination']=='sim nid shr inquiry':
            f=self.nid_shr_response(obj[0], obj[1])
            self.data.append((obj, f))
        elif obj[1]['nomination']=='kerberos inquiry':
            f=self.kerberos_response(obj[0], obj[1])
            self.data.append((obj, f))
        elif obj[1]['nomination']=='otway delivery':
            f=self.otway_response(obj[0], obj[1])
            self.data.append((obj, f))
        else:
            self.data.append((dict(nomination='Error'), False))

class SubjectDraw(QWidget):

    '''Визуализация субъектов'''

    def __init__(self, web, nm):
        QWidget.__init__(self)
        self.initUI(nm)
        self.subject=dict() # массив с зарегистрированными субъектами
        self.web=web

    def initUI(self, nm):
        self.resize(500, 700)
        vbox = QVBoxLayout()

        hbox1 = QHBoxLayout()
        self.name = QLabel("Имя")
        hbox1.addWidget(self.name)
        self.system_name = QLabel("Имя системы")
        hbox1.addWidget(self.system_name)
        self.other_name = QLabel("Другое имя")
        hbox1.addWidget(self.other_name)
        self.password_label = QLabel("Пароль")
        hbox1.addWidget(self.password_label)
        vbox.addLayout(hbox1)

        hbox2 = QHBoxLayout()
        self.name_edit = QLineEdit()
        self.name_edit.setText("name"+nm)
        hbox2.addWidget(self.name_edit)
        self.system_name_edit = QLineEdit()
        self.system_name_edit.setText("sys")
        hbox2.addWidget(self.system_name_edit)
        self.other_name_edit = QLineEdit()

        if nm=='A':
            self.other_name_edit.setText('nameB')
        elif nm=='B':
            self.other_name_edit.setText('nameA')

        hbox2.addWidget(self.other_name_edit)
        self.password_edit = QLineEdit()
        self.password_edit.setText(nm*16)
        hbox2.addWidget(self.password_edit)
        vbox.addLayout(hbox2)

        self.plain_text = QPlainTextEdit()
        vbox.addWidget(self.plain_text)

        hbox = QHBoxLayout()
        self.create_button = QPushButton("Создать объект")
        self.create_button.clicked.connect(self.create_subject)
        hbox.addWidget(self.create_button)
        self.web_button = QPushButton("Зайти в сеть")
        self.web_button.clicked.connect(self.web_reg)
        hbox.addWidget(self.web_button)
        self.sim_reg_button = QPushButton("Симметричная регистрация")
        self.sim_reg_button.clicked.connect(self.sim_reg)
        hbox.addWidget(self.sim_reg_button)
        self.sim_reg_check_button = QPushButton("Проверка симметричной регистрации")
        self.sim_reg_check_button.clicked.connect(self.sim_reg_check)
        hbox.addWidget(self.sim_reg_check_button)
        vbox.addLayout(hbox)

        hbox1 = QHBoxLayout()
        self.nid_shr_inwuiry_button = QPushButton("Запрос на симметричный Нид.-Шр.")
        self.nid_shr_inwuiry_button.clicked.connect(self.nid_shr_inquiry)
        hbox1.addWidget(self.nid_shr_inwuiry_button)
        self.nid_shr_delivery_button = QPushButton("Передать сообщение")
        self.nid_shr_delivery_button.clicked.connect(self.nid_shr_delivery)
        hbox1.addWidget(self.nid_shr_delivery_button)
        self.nid_shr_check_button = QPushButton("Проверить")
        self.nid_shr_check_button.clicked.connect(self.nid_shr_check)
        hbox1.addWidget(self.nid_shr_check_button)
        self.nid_shr_check_step_two_button = QPushButton("Ответ на проверку")
        self.nid_shr_check_step_two_button.clicked.connect(self.nid_shr_check_step_two)
        hbox1.addWidget(self.nid_shr_check_step_two_button)
        self.nid_shr_finally_button = QPushButton("Результат")
        self.nid_shr_finally_button.clicked.connect(self.nid_shr_finally)
        hbox1.addWidget(self.nid_shr_finally_button)
        vbox.addLayout(hbox1)

        hbox2 = QHBoxLayout()
        self.kerberos_inquiry_button = QPushButton("Запрос на Керберос")
        self.kerberos_inquiry_button.clicked.connect(self.kerberos_inquiry)
        hbox2.addWidget(self.kerberos_inquiry_button)
        self.kerberos_delivery_button = QPushButton("Передать сообщение")
        self.kerberos_delivery_button.clicked.connect(self.kerberos_delivery)
        hbox2.addWidget(self.kerberos_delivery_button)
        self.kerberos_check_button = QPushButton("Проверить")
        self.kerberos_check_button.clicked.connect(self.kerberos_check)
        hbox2.addWidget(self.kerberos_check_button)
        self.kerberos_check_step_two_button = QPushButton("Ответ на проверку")
        self.kerberos_check_step_two_button.clicked.connect(self.kerberos_check_step_two)
        hbox2.addWidget(self.kerberos_check_step_two_button)
        vbox.addLayout(hbox2)

        hbox3 = QHBoxLayout()
        self.otway_inquiry_button = QPushButton("Запрос на протокол От.-Р.")
        self.otway_inquiry_button.clicked.connect(self.otway_inquiry)
        hbox3.addWidget(self.otway_inquiry_button)
        self.otway_delivery_button = QPushButton("Передать сообщение")
        self.otway_delivery_button.clicked.connect(self.otway_delivery)
        hbox3.addWidget(self.otway_delivery_button)
        self.otway_delivery_two_button = QPushButton("Проверить вторую часть")
        self.otway_delivery_two_button.clicked.connect(self.otway_delivery_two)
        hbox3.addWidget(self.otway_delivery_two_button)
        self.otway_finally_button = QPushButton("Проверить первую часть")
        self.otway_finally_button.clicked.connect(self.otway_finally)
        hbox3.addWidget(self.otway_finally_button)
        vbox.addLayout(hbox3)

        hbox4 = QHBoxLayout()
        self.asim_reg_button = QPushButton("Ассиметричная регистрация")
        self.asim_reg_button.clicked.connect(self.asim_reg)
        hbox4.addWidget(self.asim_reg_button)
        self.asim_check_button = QPushButton("Проверить чужую регистрацию")
        self.asim_check_button.clicked.connect(self.asim_check)
        hbox4.addWidget(self.asim_check_button)
        self.asim_res_button = QPushButton("Результат своей регистрации")
        self.asim_res_button.clicked.connect(self.asim_reg_result)
        hbox4.addWidget(self.asim_res_button)
        vbox.addLayout(hbox4)

        hbox5 = QHBoxLayout()
        self.asim_inquiry_button = QPushButton("Запрос на ассиметричный протокол Нид.-Шр.")
        self.asim_inquiry_button.clicked.connect(self.asim_inquiry)
        hbox5.addWidget(self.asim_inquiry_button)
        self.asim_answer_button = QPushButton("Проверить запрос")
        self.asim_answer_button.clicked.connect(self.asim_answer)
        hbox5.addWidget(self.asim_answer_button)
        self.asim_answer_two_button = QPushButton("Проверить ответ на запрос")
        self.asim_answer_two_button.clicked.connect(self.asim_answer_two)
        hbox5.addWidget(self.asim_answer_two_button)
        self.asim_finally_button = QPushButton("Результат")
        self.asim_finally_button.clicked.connect(self.asim_finally)
        hbox5.addWidget(self.asim_finally_button)
        vbox.addLayout(hbox5)

        self.setLayout(vbox)

    def create_subject(self):
        name=self.name_edit.text()
        if not self.subject.get(name) is None:
            self.plain_text.appendPlainText("Уже зарегистрирован")
        else:
            self.subject[name]=Subject(name, self.web)
            self.plain_text.appendPlainText("Создан")

    def web_reg(self):
        name = self.name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Объекта нет")
        else:
            if self.subject[name].reg_web():
                self.plain_text.appendPlainText("Зашёл")
            else:
                self.plain_text.appendPlainText("Вход этим именем уже произведён")

    def sim_reg(self):
        name = self.name_edit.text()
        system_name = self.system_name_edit.text()
        password = self.password_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не создан")
            return
        else:
            self.subject[name].sim_reg(system_name, name, password)
            self.plain_text.appendPlainText("Запрос регистрации отправлен")

    def sim_reg_check(self):
        name = self.name_edit.text()
        system_name = self.system_name_edit.text()
        if self.subject[name].sim_reg_result(system_name):
            self.plain_text.appendPlainText("Регистрация успешна")
        else:
            self.plain_text.appendPlainText("Регистрация не прошла")

    def nid_shr_inquiry(self):
        name = self.name_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f=self.subject[name].nid_shr_inquiry(system_name, name, other_name)
            if f:
                self.plain_text.appendPlainText("Запрос отправлен. Послано случайное число "+str(f[1]))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def nid_shr_delivery(self):
        name = self.name_edit.text()
        password=self.password_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f=self.subject[name].nid_shr_delivery(system_name, password, other_name)
            if f:
                self.plain_text.appendPlainText("Пришёл секрет "+str(f[1][2]))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def nid_shr_check(self):
        name = self.name_edit.text()
        password=self.password_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f=self.subject[name].nid_shr_check(other_name, password)
            if f:
                self.plain_text.appendPlainText("Пришёл секрет "+str(f[1][0])+' от '+str(f[1][1])+". Послано число "+str(f[2]))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def nid_shr_check_step_two(self):
        name = self.name_edit.text()
        password=self.password_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f=self.subject[name].nid_shr_check_step_two( other_name)
            if f:
                self.plain_text.appendPlainText("Пришло число "+str(f[1])+". Послано число "+str(f[1]-1))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def nid_shr_finally(self):
        name = self.name_edit.text()
        password=self.password_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f=self.subject[name].nid_shr_finally(other_name)
            if f:
                self.plain_text.appendPlainText("Пришло число "+str(f[1])+". Протокол завершён верно")
            else:
                self.plain_text.appendPlainText("Ошибка")

    def kerberos_inquiry(self):
        name = self.name_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f=self.subject[name].kerberos_inquiry(system_name, name, other_name)
            if f:
                self.plain_text.appendPlainText("Запрос отправлен.")
            else:
                self.plain_text.appendPlainText("Ошибка")

    def kerberos_delivery(self):
        name = self.name_edit.text()
        password=self.password_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f=self.subject[name].kerberos_delivery(system_name, password, other_name)
            if f:
                self.plain_text.appendPlainText("Пришёл секрет "+str(f[1][2]))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def kerberos_check(self):
        name = self.name_edit.text()
        password=self.password_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f=self.subject[name].kerberos_check(other_name, password)
            if f:
                self.plain_text.appendPlainText("Пришёл секрет "+str(f[2])+' от '+str(f[1][0])+". Метка времени "+str(f[1][1].hour)+ ' '+str(f[1][1].minute)+ ' '+str(f[1][1].second)+'. Послано '+str(f[1][1].hour+1)+ ' '+str(f[1][1].minute)+ ' '+str(f[1][1].second))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def kerberos_check_step_two(self):
        name = self.name_edit.text()
        password=self.password_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f=self.subject[name].kerberos_check_step_two( other_name)
            if f:
                self.plain_text.appendPlainText("Пришла метка времени "+str(f.hour)+ ' '+str(f.minute)+ ' '+str(f.second)+'. Протокол завершён успешно')
            else:
                self.plain_text.appendPlainText("Ошибка")

    def otway_inquiry(self):
        name = self.name_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        password=self.password_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f = self.subject[name].otway_inquiry(password, name, other_name)
            if f:
                self.plain_text.appendPlainText("Запрос отправлен. Сгенерированы числа N "+str(f[1])+' и Na '+str(f[2]))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def otway_delivery(self):
        name = self.name_edit.text()
        password=self.password_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f=self.subject[name].otway_delivery(system_name, password, other_name)
            if f:
                self.plain_text.appendPlainText("Пришёл запрос от "+str(f[1])+" с числом "+str(f[3])+". Сгенерированно число "+str(f[2]))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def otway_delivery_two(self):
        name = self.name_edit.text()
        password=self.password_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f=self.subject[name].otway_delivery_two(system_name, password, other_name)
            if f:
                self.plain_text.appendPlainText("Прислано число "+str(f[2])+". Система аутентифицирована. Прислан секрет "+str(f[1]))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def otway_finally(self):
        name = self.name_edit.text()
        password=self.password_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f=self.subject[name].otway_finally(system_name, password, other_name)
            if f:
                self.plain_text.appendPlainText("Прислано число "+str(f[1])+". Система аутентифицирована. Прислан секрет "+str(f[0]))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def asim_reg(self):
        name = self.name_edit.text()
        password=self.password_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f=self.subject[name].asim_reg(name, other_name)
            if f:
                self.plain_text.appendPlainText("Запрос отправлен")
            else:
                self.plain_text.appendPlainText("Ошибка")

    def asim_check(self):
        name = self.name_edit.text()
        password = self.password_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f = self.subject[name].asim_reg_check(name, other_name)
            if f:
                self.plain_text.appendPlainText("Прислан запрос от " + str(f[1]) + "с паролем " + str(f[2]))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def asim_reg_result(self):
        name = self.name_edit.text()
        password = self.password_edit.text()
        system_name = self.system_name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f = self.subject[name].asim_reg_result(other_name)
            if f:
                self.plain_text.appendPlainText("Регистрация успешна")
            else:
                self.plain_text.appendPlainText("Ошибка")

    def asim_inquiry(self):
        name = self.name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f = self.subject[name].asim_inquiry(name, other_name)
            if f:
                self.plain_text.appendPlainText("Запрос отправлен. Сгенерирована часть ключа "+str(f[1]))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def asim_answer(self):
        name = self.name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f = self.subject[name].asim_answer(name, other_name)
            if f:
                self.plain_text.appendPlainText("Получен запрос от "+str(f[1])+" с ключом "+str(f[2])+". Сгенерирована часть ключа "+str(f[3]))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def asim_answer_two(self):
        name = self.name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f = self.subject[name].asim_answer_two(name, other_name)
            if f:
                self.plain_text.appendPlainText("Получен ответ от "+str(f[1])+" с ключом "+str(f[2])+" "+str(f[3]))
            else:
                self.plain_text.appendPlainText("Ошибка")

    def asim_finally(self):
        name = self.name_edit.text()
        other_name = self.other_name_edit.text()
        if self.subject.get(name) is None:
            self.plain_text.appendPlainText("Не зарегистрирован")
            return
        else:
            f = self.subject[name].asim_finally(name, other_name)
            if f:
                self.plain_text.appendPlainText("Протокол завершён. Пришло число "+str(f))
            else:
                self.plain_text.appendPlainText("Ошибка")

class SystemDraw(QWidget):

    '''Визуализация систем аутентификации'''

    def __init__(self, web):
        QWidget.__init__(self)
        self.initUI()
        self.system=dict() # словарь систем
        self.web=web

    def initUI(self):
        self.resize(500, 700)
        vbox = QVBoxLayout()

        hbox = QHBoxLayout()
        self.name = QLabel("Имя системы")
        hbox.addWidget(self.name)
        self.name_edit = QLineEdit()
        self.name_edit.setText('sys')
        hbox.addWidget(self.name_edit)
        self.create_button=QPushButton("Создать")
        self.create_button.clicked.connect(self.create_system)
        hbox.addWidget(self.create_button)
        self.reg_button=QPushButton("Зарегистрировать")
        self.reg_button.clicked.connect(self.reg_system)
        hbox.addWidget(self.reg_button)
        self.stop_button=QPushButton("Удалить")
        self.stop_button.clicked.connect(self.stop_system)
        hbox.addWidget(self.stop_button)
        self.read_button=QPushButton("Считать")
        self.read_button.clicked.connect(self.read_data)
        hbox.addWidget(self.read_button)
        vbox.addLayout(hbox)

        self.plain_text = QPlainTextEdit()
        vbox.addWidget(self.plain_text)

        self.setLayout(vbox)

    def create_system(self):
        name=self.name_edit.text()
        if not self.system.get(name) is None:
            self.plain_text.appendPlainText("Система с таким именем уже существует")
        else:
            self.system[name]=AuthSystem(name, self.web)
            self.plain_text.appendPlainText("Система создана")

    def reg_system(self):
        name=self.name_edit.text()
        f=self.system[name].reg_web()
        if f:
            self.plain_text.appendPlainText("Система зарегистрирована в сети")
        else:
            self.plain_text.appendPlainText("Регистрация в сети невозможна")

    def stop_system(self):
        name=self.name_edit.text()
        if self.system.get(name) is None:
            self.plain_text.appendPlainText("Система с таким именем не существует")
        else:
            self.system[name].del_web()
            self.system.pop(name)
            self.plain_text.appendPlainText("Удалена")

    def read_data(self):
        #захватить данные системы
        name=self.name_edit.text()
        if self.system.get(name) is None:
            self.plain_text.appendPlainText("Система с таким именем не существует")
        else:
            self.system[name].signal_waiting()
            if self.system[name].data:
                if self.system[name].data is None:
                    self.plain_text.appendPlainText(name + " - ничего не принято" )
                    return

                obj=self.system[name].data[0]#cообщение и результат. Надо сделать перебор
                if obj[0][1]['nomination']=='sim reg':
                    self.plain_text.appendPlainText(name+" принят запрос на симетричную регистрацию от "+obj[0][1]['name']+", пароль "+obj[0][1]['password'])
                    if obj[1]:
                        self.plain_text.appendPlainText("Регистрация прошла")
                    else:
                        self.plain_text.appendPlainText("Регистрация не прошла")
                    self.system[name].data.pop()
                    return
                if obj[0][1]['nomination']=='sim nid shr inquiry':
                    self.plain_text.appendPlainText(name+" принят запрос на симетричный алгоритм Нидхема-Шрёдера от "+obj[0][1]['name']+" для "+obj[0][1]['other name']+'. Случайное число '+str(obj[0][1]['random'])+'. Послан секрет '+str(obj[1]))
                    if obj[1]:
                        self.plain_text.appendPlainText("Сообщение передано")
                    else:
                        self.plain_text.appendPlainText("Сообщение не передано")
                    self.system[name].data.pop()
                    return
                if obj[0][1]['nomination']=='kerberos inquiry':
                    self.plain_text.appendPlainText(name+" принят запрос на алгоритм Керберос от "+obj[0][1]['name']+" для "+obj[0][1]['other name']+'. Метка времени '+str(obj[1][0].hour)+' '+str(obj[1][0].minute)+' '+str(obj[1][0].second)+' '+'. Послан секрет '+str(obj[1][1]))
                    if obj[1]:
                        self.plain_text.appendPlainText("Сообщение передано")
                    else:
                        self.plain_text.appendPlainText("Сообщение не передано")
                    self.system[name].data.pop()
                    return
                if obj[0][1]['nomination']=='otway delivery':
                    self.plain_text.appendPlainText(name+" принят запрос на алгоритм Отвея-Рииса от "+obj[0][1]['name']+" для "+obj[0][1]['other name']+'. Послан секрет '+str(obj[1]))
                    if obj[1]:
                        self.plain_text.appendPlainText("Сообщение передано")
                    else:
                        self.plain_text.appendPlainText("Сообщение не передано")
                    self.system[name].data.pop()
                    return
            else:
                self.plain_text.appendPlainText("Ничего не принято")
                return

w=NotRealNetwork()
app = QApplication(sys.argv)
s1 = SubjectDraw(w, 'A')
s2 = SystemDraw(w)
s3 = SubjectDraw(w, 'B')
s1.show()
s2.show()
s3.show()
app.exit(app.exec_())
Соседние файлы в предмете Технология построения защищенных распределённых приложений