170 lines
No EOL
4.5 KiB
Python
170 lines
No EOL
4.5 KiB
Python
import os
|
||
from typing import Optional
|
||
|
||
from cryptography.exceptions import InvalidSignature
|
||
from cryptography.hazmat.primitives import hashes
|
||
from cryptography.hazmat.primitives.asymmetric import padding
|
||
|
||
from .Card import Card
|
||
|
||
|
||
class Machine:
|
||
"""
|
||
|
||
"""
|
||
|
||
def __init__(self):
|
||
# First DB: list of people authorized to vote on this machine.
|
||
# Public (que name et procuration pas empreinte) ?
|
||
|
||
# fonction insérer élément
|
||
# fonction check
|
||
self.emerging_list = {}
|
||
#[
|
||
# {
|
||
# "name": "Bob",
|
||
# "personne": (pub_key_bob, Hash(empreinte_bob)),
|
||
# "procuration": None,
|
||
# },
|
||
# {
|
||
# "name": "Alice",
|
||
# "personne": (pub_key_alice, Hash(empreinte_alice)),
|
||
# "procuration": (pub_key_Eve, Hash(empreinte_eve)), # Eve peut voter pour Alice.
|
||
# }
|
||
# {
|
||
# "name": "Eve",
|
||
# "personne": (pub_key_eve, Hash(empreinte_eve)),
|
||
# "procuration": None
|
||
# }
|
||
# ]
|
||
|
||
# Second DB: list of people who voted.
|
||
# - public
|
||
self.signing_list = {}
|
||
# [
|
||
# ("pub_key_Alice", "pub_key_Eve", "date", signature("message")),
|
||
# ("pub_key_Bob", "pub_key_Bob", "date", signature("message")),
|
||
# ]
|
||
|
||
# Third DB: votes (shuffle when vote is inserted).
|
||
# - private
|
||
self._vote_list = []
|
||
# ["A", "B", "C"]
|
||
|
||
# If details during the simulation.
|
||
#def send_challenge(self) -> bytes:
|
||
# pass
|
||
#def check_challenge(self, hash_rand: bytes) -> bool:
|
||
# pass
|
||
|
||
def search_pubkey(self, pubkey: bytes) -> list[tuple[bytes, bytes]]:
|
||
"""
|
||
Search pubkey in emerging list.
|
||
:param pubkey: Public key to search in the emerging list.
|
||
:return: All entries.
|
||
"""
|
||
|
||
next(filter(
|
||
lambda data: data["personne"][0] == and
|
||
self.emerging_list
|
||
))
|
||
|
||
def check_fingerprint(self, empreinte: bytes) -> bool:
|
||
"""
|
||
|
||
:return:
|
||
"""
|
||
return True
|
||
|
||
|
||
def check_card(self, card: Card, pin: int) -> bool:
|
||
"""
|
||
Check if the card is valid.
|
||
:param card:
|
||
:param pin:
|
||
:return:
|
||
"""
|
||
# Public key.
|
||
public_key = card.public_key()
|
||
|
||
# Challenge to verify public key.
|
||
challenge = os.urandom(128)
|
||
signature = card.reply_challenge(challenge)
|
||
|
||
try:
|
||
public_key.verify(
|
||
signature,
|
||
challenge,
|
||
padding.PSS(
|
||
mgf=padding.MGF1(hashes.SHA256()),
|
||
salt_length=padding.PSS.MAX_LENGTH
|
||
),
|
||
hashes.SHA256()
|
||
)
|
||
except InvalidSignature:
|
||
return False
|
||
|
||
# Pin
|
||
# CHECK(biloute02,faraphel): c’est bon comme ça le digest ?
|
||
digest = hashes.Hash(hashes.SHA256())
|
||
digest.update(pin.as_bytes())
|
||
hashed_pin = digest.finalize()
|
||
if not card.check_pin(hashed_pin):
|
||
return False
|
||
|
||
# Is in emerging list?
|
||
|
||
return True
|
||
|
||
def authenticate(self, card: Card, pin: int, empreinte: bytes) -> bool:
|
||
# Check if card is v
|
||
if not self.check_card(card, pin):
|
||
print("")
|
||
return False
|
||
|
||
pubkey = card.public_key
|
||
# Check pubkey
|
||
entries = self.search_pubkey(pubkey)
|
||
if not entry:
|
||
return False
|
||
|
||
# Check fingerprint
|
||
if
|
||
return True
|
||
|
||
def vote(self, card: Card, vote: str) -> bool:
|
||
public_key = card.public_key
|
||
|
||
# Chercher si public_key in signing_list for person.
|
||
personne = self.search_personne(public_key)
|
||
if personne is not None:
|
||
print("La personne peut voter pour elle-même")
|
||
return True
|
||
|
||
# Chercher si public_key in signing_list for procuration.
|
||
mandataire = self.search_procuration(public_key)
|
||
if mandataire is not None:
|
||
print("La personne a une procuration")
|
||
return True
|
||
|
||
print("La personne peut plus voter")
|
||
return False
|
||
|
||
# vote = get_vote()
|
||
# generate_signature(vote, card)
|
||
# add_vote_to_urn(vote)
|
||
# print("Vote comptabilisé!")
|
||
# return True
|
||
|
||
def print_signing_list(self) -> None:
|
||
...
|
||
|
||
def print_emerging_list(self) -> None:
|
||
...
|
||
|
||
def cloture_du_vote(self) -> tuple[list[vote], signature]:
|
||
...
|
||
|
||
|
||
machine = Machine()
|
||
machine.emerging_list |