Les connections sécurisées, par exemple à une banque ou à un site de commerce en ligne, utilisent le protocole HTTPS, une version chiffrée du protocole HTTP, qui repose sur le protocole TLS (Transport Layer Security), successeur de SSL (Secure Socket Layer).
Le pricipe général est d'utiliser la cryptographie asymétrique pour négocier des clefs de session (TLS handshake), et la cryptographie symétrique pour chiffrer les données échangées pendant la session.
Le serveur et le client négocient les détails des algorithmes de chiffrement utilisés et les clefs avant de transmettre aucune donnée.
La cryptographie à clef publique permet aux deux parties de s'authentifier. Ce n'est pas obligatoire, mais dans le cas d'HTTPS, il faut au moins que le serveur soit authentifié.
Chaque message contient un code d'authentification de message (MAC) qui assure l'intégrité des données transmises.
HTTPS peut chiffrer entièrement les données transmise par HTTP, en particulier l'URL demandée, les paramètres des requètes, les en-têtes el les cookies. Toutefois, les adresse IP du client et du serveur ne peuvent évidemment pas être protégées, non plus que le volume des données transférées.
Les connections TLS utilisent des certificats basés sur des autorités de certification, et respectant le standard X.509.
Ces certificats sont pré-installés sur les navigateur, de sorte qu'un utilisateur pourra faire confiance à un site sécurisé seulement si :
Ces conditions ne sont pas toujours réunies, voir par exemple ici ou là pour quelques exemples édifiants.
Un certificat se compose essentiellement d'une clef publique, signée par un autorité de certification, possédant elle même un certificat autosigné (certificat racine).
On peut voir les certificats de firefox en allant dans préférences/avancé/certificats :
On clique sur "exporter", et on obtient (par défaut) un fichier au format pem.
!cat Amazon
On reconnait un encodage en base 64. Comme pour les clefs ssh, on pourrait décoder le base 64 et continuer avec pyasn1. Pour cela, il faut connaître la structure du certificat, définie dans la RFC2459
La partie authentifiée contient les champs suivants :
Version Numéro de série Algorithme de signature du certificat DN (Distinguished Name) du délivreur (autorité de certification) Validité (dates limites) Pas avant Pas après DN de l'objet du certificat Informations sur la clé publique Algorithme de la clé publique Clé publique proprement dite Identifiant unique du signataire (optionnel, X.509v2) Identifiant unique du détenteur du certificat (optionnel, X.509v2) Extensions (optionnel, à partir de X.509v3) Liste des extensions Signature des informations ci-dessus par l'autorité de certificationLes noms de l'émetteur (également signataire) comme du titulaire sont des noms X.501, que l'on retrouve également dans les annuaires ISO et LDAP. Le contenu ci-dessus est suivi par une répétition de l'algorithme de signature et de la signature proprement dite.
Pour décoder les certificats, il est plus simple d'utiliser openssl :
!openssl x509 -in Amazon -text
On voit donc que les serveurs d'Amazon utilisent une clef RSA de 2048 bits, et une signture RSA d'un hachage SHA256.
Il existe un module tiers, pyopenssl permettant d'utiliser openssl avec Python.
Jusqu'à une époque récente, le paiement par cartes bancaires était authentifié à l'aide d'une simple signature RSA.
La mémoire de la carte est divisée en deux zones, une accessible avec n'importe quel lecteur, et une autre (zone secrète) qui n'est accessible qu'au processeur de la carte, et illisible autrement. La zone publique contient une valeur d'authentification, qui est obtenue en chiffrant des données publiques (comme le numéro de la carte et sa date d'expiration) avec une clé RSA secrète. Les terminaux de paiement et les distributeurs de billets connaissent la clé publique, et l'utilisent pour vérifier la valeur d'authentification, qui est précisément une signature numérique RSA, sans hachage vu le petit nombre de données.
Si la signature est correcte, la carte est considérée comme authentique, et le code est demandé au client. Le terminal envoie le code à la carte qui le compare avec celui contenu dans sa zone secrète, et répond « oui » ou »non ». Si la réponse est « oui », le paiement est accepté.
Vous pourrez au prochain TD déchiffrer les données d'une authentique carte bancaire de l'époque, et en observant leur structure, forger les données d'une fausse carte à l'aide de la clef factorisée.
Les processeurs des cartes a puces interprètent des instructions appelées APDU (Application Protocol Data Unit) composées de deux octets obligatoires CLA (Class) et INS (Instruction) et de paramètres, par exemple une adresse (en quartets) et le nombre d'octets à lire.
Le résultat se compose des données demandées et de deux octets SW1, SW2 indiquant si tout s'est bien passé.
Sur un système Linux disposant d'un lecteur de cartes à puce, il faut installer pcsc-lite et activer le démon pcscd. Il est interfacé avec Python (module pyscard. On peut aussi utiliser gscriptor, un petite interface graphique pour envoyer des instructions à la carte.
Voici les données à exploiter dans le prochain TD.
On peut trouver des explications détaillées dans cette archive d'un site disparu.