Advertisement
Hexkritor

Untitled

Feb 6th, 2017
133
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 7.69 KB | None | 0 0
  1. import socket
  2. import threading
  3. import hashlib
  4. import rsa
  5. import sqlite3
  6.  
  7. ID = 'id'
  8. NAME = 'name'
  9. VOTES = 'votes'
  10. TABLE_VOTE_DICT = \
  11.     {
  12.         ID: 0,
  13.         NAME: 1,
  14.         VOTES: 2
  15.     }
  16. CREATE_VOTE_TABLE = 'CREATE TABLE IF NOT EXISTS elections (id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, name varchar, votes INTEGER)'
  17. INC_VOTE = "UPDATE elections SET votes = '%s' WHERE name = '%s'"
  18. VOTE_DICT = \
  19.     {
  20.         0: 'Putin',
  21.         1: 'Zyuganov',
  22.         2: 'Zhirinovsky',
  23.         3: 'Mironov'
  24.     }
  25.  
  26. def _incVote_(c, vote, name):
  27.     c.execute(INC_VOTE%(vote+1,name))
  28.  
  29. def _checkIfTableExists_(c):
  30.     c.execute(CREATE_VOTE_TABLE)
  31.  
  32. def handleVote(vote):
  33.     vote &=  ((1 << 20) - 1)
  34.     print(vote)
  35.     conn = sqlite3.connect('elections.sqlite')
  36.     c = conn.cursor()
  37.     c.execute('SELECT * FROM elections')
  38.     row = c.fetchone()
  39.     while row is not None:
  40.         if row[TABLE_VOTE_DICT[NAME]] == VOTE_DICT[vote]:
  41.             _incVote_(c, row[TABLE_VOTE_DICT[VOTES]], VOTE_DICT[vote])
  42.             break
  43.         row = c.fetchone()
  44.     conn.commit()
  45.     c.close()
  46.     conn.close()
  47.  
  48. def addCandidate(name):
  49.     conn = sqlite3.connect('elections.sqlite')
  50.     c = conn.cursor()
  51.     c.execute("INSERT INTO elections (name,votes) VALUES ('%s','%i')"%(name,0))
  52.     conn.commit()
  53.     c.close()
  54.     conn.close()
  55.  
  56. def resetElection():
  57.     conn = sqlite3.connect('elections.sqlite')
  58.     c = conn.cursor()
  59.     c.execute("UPDATE elections SET votes = 0")
  60.     conn.commit()
  61.     c.close()
  62.     conn.close()
  63.  
  64. LOGIN = 'login'
  65. PASSWORD = 'password'
  66. VOTED = 'voted'
  67. ERR_PASSWORD_TOO_SHORT = 'Password is too short!'
  68. ERR_LOGIN_EXISTS = 'Login already exists!'
  69. MIN_PASS = 6
  70. MAX_PASS = 20
  71. TABLE_DICT = \
  72.     {
  73.         ID: 0,
  74.         LOGIN: 1,
  75.         PASSWORD: 2,
  76.         VOTED: 3
  77.     }
  78. CREATE_TABLE = 'CREATE TABLE IF NOT EXISTS '\
  79.                +'users (id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, '\
  80.                +'login varchar, password varchar, voted INTEGER)'
  81. ADD_USER = "INSERT INTO users (login, password, voted) VALUES ('%s','%s', 0)"
  82. MARK_AS_VOTED = "UPDATE users SET voted = 1 WHERE login = '%s'"
  83. NULL_VOTES = "UPDATE users SET voted = 0"
  84.  
  85. def _checkPassLength_(password):
  86.     length = len(password)
  87.     return length >= MIN_PASS or length <= MAX_PASS
  88.  
  89. def _checkLoginUniqueness_(c, login):
  90.     # TODO: simplify the query
  91.     c.execute("SELECT * FROM users")
  92.     for row in c:
  93.         if (login == row[TABLE_DICT[LOGIN]]):
  94.             return False
  95.     return True
  96.  
  97. def _str2hashstr_(string):
  98.     tNumber = string
  99.     hashObj = hashlib.sha256()
  100.     byteArray = str.encode(string)
  101.     hashObj.update(byteArray)
  102.     return hashObj.hexdigest()
  103.  
  104. def _initDB_():
  105.     conn = sqlite3.connect('users.sqlite')
  106.     c = conn.cursor()
  107.     c.execute(CREATE_TABLE)
  108.     return (conn, c)
  109.  
  110. def _closeDB_(conn, c):
  111.     conn.commit()
  112.     c.close()
  113.     conn.close()
  114.  
  115. def createAccount(login, password):
  116.     if not _checkPassLength_(password):
  117.         print(ERR_PASSWORD_TOO_SHORT)
  118.         return False
  119.     conn, c = _initDB_()
  120.     if not _checkLoginUniqueness_(c, login):
  121.         print(ERR_LOGIN_EXISTS)
  122.         return False
  123.     hash = _str2hashstr_(password)
  124.     c.execute(ADD_USER%(login,hash))
  125.     _closeDB_(conn, c)
  126.     return True
  127.  
  128. def authentification(login, password):
  129.     conn, c = _initDB_()
  130.     # TODO: simplify the query
  131.     c.execute("SELECT * FROM users")
  132.     for row in c:
  133.         if login == row[TABLE_DICT[LOGIN]]:
  134.             _closeDB_(conn, c)
  135.             return _str2hashstr_(password) == row[TABLE_DICT[PASSWORD]]
  136.     #print('Login not found!')
  137.     _closeDB_(conn, c)
  138.  
  139. def markAsVoted(login):
  140.     ret = False
  141.     conn, c = _initDB_()
  142.     # TODO: simplify the query
  143.     c.execute("SELECT * FROM users")
  144.     for row in c:
  145.         if row[TABLE_DICT[LOGIN]] == login:
  146.             c.execute(MARK_AS_VOTED%login)
  147.             ret = True
  148.     _closeDB_(conn, c)
  149.     return ret
  150.  
  151. def checkIfVoted(login):
  152.     conn, c = _initDB_()
  153.     # TODO: simplify the query
  154.     c.execute("SELECT * FROM users")
  155.     for row in c:
  156.         if row[TABLE_DICT[LOGIN]] == login:
  157.             return bool(row[TABLE_DICT[VOTED]])
  158.     _closeDB_(conn, c)
  159.  
  160. def nullVotes():
  161.     conn, c = _initDB_()
  162.     c.execute("SELECT * FROM users")
  163.     c.execute(NULL_VOTES)
  164.     _closeDB_(conn, c)
  165.  
  166. def powMod (n ,pow ,mod):
  167.     res=1
  168.     while pow>0:
  169.         if (pow&1):
  170.             res = (res * n) % mod
  171.         n = (n * n) % mod
  172.         pow>>=1
  173.     return res
  174.  
  175. def number2hashnum(number):
  176.     tNumber = number
  177.     hashObj = hashlib.sha256()
  178.     byteNumber = bytearray()
  179.     while tNumber > 0:
  180.         byteNumber.append(tNumber & 0xFF)
  181.         tNumber >>= 8
  182.     byteNumber.reverse()
  183.     hashObj.update(byteNumber)
  184.     hash = hashObj.digest()
  185.     hashArray = bytearray(hash)
  186.     hashNumber = 0
  187.     hashArray.reverse()
  188.     length = len(hashArray)
  189.     i = 0
  190.     while i<length :
  191.         hashNumber += hashArray[i] << (i * 8)
  192.         i += 1
  193.     return hashNumber
  194.  
  195. def checkVote(R,S,D,N):
  196.     res = powMod(S,D,N)
  197.     hash = number2hashnum(R)
  198.     return res==hash
  199.  
  200. def sendKeys(client,N,D):
  201.     client.send((str(N)+' '+str(D)+' ').encode())
  202.  
  203.     print('Keys sent')
  204.  
  205. def sendBulletin(client):
  206.     bulletin = 'President elections 2018\nChoose the candidate:\n1.Putin\n2.Zuganov\n3.Zhirinovsky\n4.Mironov\n'
  207.     client.send((bulletin).encode())
  208.  
  209. def signVote(h_, c, n):
  210.     return powMod(h_, c, n)
  211.  
  212. def receiveVote():
  213.     voteSock = socket.socket()
  214.     voteSock.bind(('', 9091))
  215.     voteSock.listen(5)
  216.     while(True):
  217.         clientSock, clientAddr = voteSock.accept()
  218.         vote = clientSock.recv(2048)
  219.         R, S = parseMessageTo2Ints(vote)
  220.         isValid = checkVote(R,S,D,N)
  221.         print(isValid)
  222.         if(isValid):
  223.             handleVote(R)
  224.         clientSock.close()
  225.         print('Vote received')
  226.  
  227. def userThread(clientSock):
  228.     while(True):
  229.         message = clientSock.recv(2048)
  230.         message = message.decode().split(' ')
  231.         if(message[0]=="reg"):
  232.             clientSock.send(('1').encode()) if createAccount(message[1],message[2]) else clientSock.send(('0').encode())
  233.         if(message[0]=="log" and authentification(message[1],message[2])):
  234.             if(checkIfVoted(message[1])):
  235.                 print('User already voted')
  236.                 clientSock.send(('2').encode())
  237.             else:
  238.                 markAsVoted(message[1])
  239.                 clientSock.send(('1').encode())
  240.                 print('Ready to send')
  241.                 break
  242.         if(message[0]=="log" and not authentification(message[1],message[2])):
  243.             print('Login failed')
  244.             clientSock.send(('0').encode())
  245.     sendKeys(clientSock, N, D)
  246.     clientSock.recv(2048)
  247.     sendBulletin(clientSock)
  248.     h_ = clientSock.recv(2048)
  249.     signedVote = signVote(int(h_.decode()), C, N)
  250.     clientSock.send(str(signedVote).encode())
  251.     clientSock.close()
  252.  
  253. def parseMessageTo2Ints(message):
  254.     message = message.decode()
  255.     message = message.split(' ')
  256.     return int(message[0]), int(message[1])
  257.  
  258. def ParametrPrivkeys():
  259.     (pubkey, privkey) = rsa.newkeys(1024)
  260.     D = privkey.e
  261.     C = privkey.d
  262.     N = privkey.n
  263.     Q = privkey.q
  264.     P = privkey.p
  265.     return D, C, N, Q, P
  266.  
  267. D, C, N, Q, P = ParametrPrivkeys()
  268. servSock = socket.socket()
  269. servSock.bind(('', 9090))
  270. servSock.listen(5)
  271. resetElection()
  272. nullVotes()
  273. print('Server launched!')
  274.  
  275. voteThread = threading.Thread(target=receiveVote)
  276. voteThread.start()
  277.  
  278. userThreads = list()
  279.  
  280. while(True):
  281.     clientSock, clientAddr = servSock.accept()
  282.     userThreads.append(threading.Thread(target=userThread,args=[clientSock]))
  283.     userThreads[len(userThreads)-1].start()
  284.  
  285. print("I'm off")
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement