⚙️ Documentation technique - Le chiffrement dans Tchap
Tchap est une application de messagerie sécurisée : elle est souveraine et chiffrée de bout-en-bout.
Cela signifie que seul l'émetteur et les destinataires d'un message sont capables de déchiffrer son contenu.
Cet article présente de manière rapide de quelle manière Tchap (qui est basée sur Element et le protocole Matrix) :
chiffre et déchiffre les messages à l'aide de clés de chiffrement
échange ces clés de chiffrement de manière sécurisée
Système de communication dans lequel seuls l'émetteur et le destinataire d'un message peuvent déchiffrer les échanges. Les intermédiaires (providers internet, hébergeur de l'application,…) ne peuvent pas déchiffrer les messages, même s'ils les interceptent.
Tchap chiffre les messages échangés à l'aide de clés de chiffrement de message. Ces clés de chiffrement de message (Sender keys) sont échangées directement entre les clients via un canal sécurisé.
La sécurité de cette transmission repose sur l'échange de clés Diffie-Hellman (https://fr.wikipedia.org/wiki/Échange_de_clés_Diffie-Hellman) qui permet, à partir de :
un élément arbitraire public décidé en commun
un élément secret propre à chacun et non partagé
de calculer un nouvel élément chacun de son côté mais dont ils savent que la valeur sera la même ("la magie des maths !").
Ce nouvel élément sera donc leur clé commune de chiffrement symétrique pour chiffrer la suite de leurs échanges.
Cette clé de chiffrement DH a été calculée à partir d'éléments publics et privés, sans qu'ils aient besoin de s'échanger (et donc de faire transiter) cette clé commune finale. Elle ne peut donc pas être interceptée ni compromise.
Mais si cette clé est dérobée sur l'appareil d'un des participants, alors les messages chiffrés à l'aide de cette clé pourront être déchiffrés par un tiers.
Matrix repose sur 2 algorithmes pour chiffrer les messages :
Olm (basé sur le double-ratchet) pour les échanges de clés de chiffrement
Megolm (basé sur le simple-ratchet) pour les messages directs et de groupe (les salons)
La transmission chiffrée sécurisée repose sur l'hypothèse que le moyen de chiffrement-déchiffrement n'est connu que par les correspondants et personne d'autre.
Ce moyen de chiffrement-déchiffrement sont les clés de chiffrement de message (Sender Keys) vues précédemment.
Pour limiter la fuite de données dans ce cas-là, Matrix fait appel à l'algorithme appelé Simple-Ratchet :
chaque nouveau message est chiffrée avec une nouvelle clé calculée à partir de la précédente (on 'dérive' de nouvelles clés à partir d'une clé-racine en fait)
la fonction de dérivation n'est pas réversible, ce qui fait qu'on ne peut pas calculer les anciennes clés à partir de la clé actuelle éventuellement dérobée. Cela protège l'historique des échanges : les messages précédant le vol de clé ne pourront pas être déchiffrés. C'est la signification du "ratchet" dans le nom : c'est un cliquet bloquant dans un sens uniquement. On ne peut pas revenir en arrière.
Par contre, si le voleur connaît l'algorithme de dérivation (qui n'est de toute façon pas considéré comme un secret), il peut calculer les clés de chiffrement suivantes et peut donc déchiffrer les futurs messages chiffrés interceptés.
Pour modérer la gravité de cette compromission de clé, une nouvelle clé-racine sera régulièrement transmise de manière sécurisée (échange de clés Diffie-Hellman) entre les participants. Cette clé sera le nouveau départ pour une nouvelle suite de dérivation de clés de chiffrement. Le voleur ne connaissant pas cette nouvelle clé-racine, sa capacité de déchiffrement des nouveaux messages cessera. C’est le principe du “Double-ratchet”.
Dans une discussion de groupe, il est trop coûteux de gérer un canal direct (basé sur Olm) entre chaque paire de participants du groupe.
La stratégie choisie est que chaque participant génère une clé-racine de chiffrement (la Sender Key). Cette Sender Key est transmise à chaque participant via le canal Olm pour un maximum de sécurité et limiter la plage de compromission potentielle (double-ratchet) .
C'est pourquoi le 1er envoi de message pour un participant qui rejoint un grand groupe est long. C'est la phase initiale de génération et distribution de la Sender Key du participant. Les messages suivant ne seront transmis qu'au serveur, ce qui est beaucoup plus rapide.
Quand un participant envoie un message au groupe, il chiffre son message avec une dérivation de sa Sender Key et transmet le message au serveur (et non aux autres utilisateurs). Les autres utilisateurs peuvent alors récupérer le message depuis le serveur et le déchiffrer par une dérivation de la Sender Key de l'émetteur qu'ils ont reçue précédemment par le canal Olm.
Chaque message chiffré transmis au serveur est associé à un session_id (la sender key de l'émetteur) et un index de dérivation (pour pouvoir calculer sa clé de déchiffrement à partir de la sender key reçue au préalable).
Les Sender Keys d'un groupe (Megolm session) sont régénérées :
chaque semaine
tous les 100 messages
quand un appareil quitte le groupe (pour que cet appareil ne puisse pas déchiffrer les prochains messages)
quand un participant le demande (commande '\discardsession')
Il n'est pas nécessaire de régénérer les Sender Keys des participants quand on nouveau participant arrive. Il recevra les Sender Keys des autres participants dans leur dérivation actuelle et sera incapable de déchiffrer l'historique du salon car il ne peut pas revenir en arrière dans les dérivations de clés (bloqué par le "ratchet").
Quand un message ne peut pas être déchiffré sur un appareil c'est parce que cet appareil n'a pas reçu la clé de déchiffrement (sender key) qui est sensée être transmise par le canal Olm direct (d'appareil à appareil).
Des raisons habituelles de non-déchiffrement sont :
le message fait partie de l'historique et ne pourra jamais être déchiffré (ratchet)
l'émetteur et le destinataire sont sur deux homeServers différents (fédération) et le homeServer de l'émetteur n'était pas informé de l'existence du destinataire au moment de l'envoi (lag/délai dans la fédération)
un réseau peu fiable n'ayant pas pu acheminer la sender key au destinataire
Les différents appareils d'un utilisateur, lorsqu'ils sont vérifiés, peuvent aussi s'échanger les clés de chiffrement qu'ils connaissent. C'est le Megolm Key Request. Le nouvel appareil interroge les autres appareils de l'utilisateur au besoin pour récupérer des clés de déchiffrement. Si aucun autre appareil de l'utilisateur n'est accessible en ligne à ce moment, il ne pourra pas obtenir de clés de chiffrement par ce moyen.
Ainsi, un nouvel appareil qui se connecte à un compte, une fois vérifié, pourra avoir accès à l'historique des messages si un autre appareil de l'utilisateur y a déjà accès.
Le key request entre appareils de l'utilisateur se fait salon par salon, et au fur et à mesure du défilement dans le salon.
L'échange de clés permet d'être sûr que le canal de communication est chiffré de bout-en-bout.
La phase de vérification permet d'être sûr qu'il n'y a pas d'intermédiaire qui intercepte le flux (pas de Man-in-the-middle).
Un Man-in-the-middle pourrait se placer sur le flux chiffré de manière invisible : il déchiffrerait-rechiffrerait les flux à la volée entre 2 participants.
La vérification permet d'être sûr que ce n'est pas le cas : si c'était le cas, les emojis/codes de vérification présentés par les 2 appareils se vérifiant ne seraient pas les mêmes du fait du changement de chiffrement au milieu.
La sauvegarde automatique des clés de chiffrement sur le serveur (Megolm keys) permet à une nouvelle session vérifiée de récupérer toutes les clés de chiffrement même quand aucun autre appareil de l'utilisateur n'est joignable en ligne (pas de Key Request possible).
Cette sauvegarde activée permet que chaque fois qu'un appareil de l'utilisateur a connaissance d'une nouvelle clé de chiffrement, cette nouvelle clé est envoyée sous forme chiffrée dans la sauvegarde sur le serveur.
La sauvegarde locale de clés peut faire plusieurs dizaines de Mo.
L'API de sauvegarde de clés sur le serveur est très complète et permet de demander les clés progressivement.
Cela signifie que seul l'émetteur et les destinataires d'un message sont capables de déchiffrer son contenu.
Cet article présente de manière rapide de quelle manière Tchap (qui est basée sur Element et le protocole Matrix) :
chiffre et déchiffre les messages à l'aide de clés de chiffrement
échange ces clés de chiffrement de manière sécurisée
Chiffrement de bout en bout - End to End Encryption (E2EE)
Système de communication dans lequel seuls l'émetteur et le destinataire d'un message peuvent déchiffrer les échanges. Les intermédiaires (providers internet, hébergeur de l'application,…) ne peuvent pas déchiffrer les messages, même s'ils les interceptent.
Echange de clés Diffie-Hellman (pour sécuriser l'échange des clés de chiffrement des messages de Tchap)
Tchap chiffre les messages échangés à l'aide de clés de chiffrement de message. Ces clés de chiffrement de message (Sender keys) sont échangées directement entre les clients via un canal sécurisé.
La sécurité de cette transmission repose sur l'échange de clés Diffie-Hellman (https://fr.wikipedia.org/wiki/Échange_de_clés_Diffie-Hellman) qui permet, à partir de :
un élément arbitraire public décidé en commun
un élément secret propre à chacun et non partagé
de calculer un nouvel élément chacun de son côté mais dont ils savent que la valeur sera la même ("la magie des maths !").
Ce nouvel élément sera donc leur clé commune de chiffrement symétrique pour chiffrer la suite de leurs échanges.
Cette clé de chiffrement DH a été calculée à partir d'éléments publics et privés, sans qu'ils aient besoin de s'échanger (et donc de faire transiter) cette clé commune finale. Elle ne peut donc pas être interceptée ni compromise.
Mais si cette clé est dérobée sur l'appareil d'un des participants, alors les messages chiffrés à l'aide de cette clé pourront être déchiffrés par un tiers.
Échange de messages chiffrés dans Tchap/Matrix
Matrix repose sur 2 algorithmes pour chiffrer les messages :
Olm (basé sur le double-ratchet) pour les échanges de clés de chiffrement
Megolm (basé sur le simple-ratchet) pour les messages directs et de groupe (les salons)
La transmission chiffrée sécurisée repose sur l'hypothèse que le moyen de chiffrement-déchiffrement n'est connu que par les correspondants et personne d'autre.
Ce moyen de chiffrement-déchiffrement sont les clés de chiffrement de message (Sender Keys) vues précédemment.
Ratchet (simple et double)
Pour limiter la fuite de données dans ce cas-là, Matrix fait appel à l'algorithme appelé Simple-Ratchet :
chaque nouveau message est chiffrée avec une nouvelle clé calculée à partir de la précédente (on 'dérive' de nouvelles clés à partir d'une clé-racine en fait)
la fonction de dérivation n'est pas réversible, ce qui fait qu'on ne peut pas calculer les anciennes clés à partir de la clé actuelle éventuellement dérobée. Cela protège l'historique des échanges : les messages précédant le vol de clé ne pourront pas être déchiffrés. C'est la signification du "ratchet" dans le nom : c'est un cliquet bloquant dans un sens uniquement. On ne peut pas revenir en arrière.
Par contre, si le voleur connaît l'algorithme de dérivation (qui n'est de toute façon pas considéré comme un secret), il peut calculer les clés de chiffrement suivantes et peut donc déchiffrer les futurs messages chiffrés interceptés.
Pour modérer la gravité de cette compromission de clé, une nouvelle clé-racine sera régulièrement transmise de manière sécurisée (échange de clés Diffie-Hellman) entre les participants. Cette clé sera le nouveau départ pour une nouvelle suite de dérivation de clés de chiffrement. Le voleur ne connaissant pas cette nouvelle clé-racine, sa capacité de déchiffrement des nouveaux messages cessera. C’est le principe du “Double-ratchet”.
Clés de chiffrement (Sender key)
Dans une discussion de groupe, il est trop coûteux de gérer un canal direct (basé sur Olm) entre chaque paire de participants du groupe.
La stratégie choisie est que chaque participant génère une clé-racine de chiffrement (la Sender Key). Cette Sender Key est transmise à chaque participant via le canal Olm pour un maximum de sécurité et limiter la plage de compromission potentielle (double-ratchet) .
C'est pourquoi le 1er envoi de message pour un participant qui rejoint un grand groupe est long. C'est la phase initiale de génération et distribution de la Sender Key du participant. Les messages suivant ne seront transmis qu'au serveur, ce qui est beaucoup plus rapide.
Quand un participant envoie un message au groupe, il chiffre son message avec une dérivation de sa Sender Key et transmet le message au serveur (et non aux autres utilisateurs). Les autres utilisateurs peuvent alors récupérer le message depuis le serveur et le déchiffrer par une dérivation de la Sender Key de l'émetteur qu'ils ont reçue précédemment par le canal Olm.
Chaque message chiffré transmis au serveur est associé à un session_id (la sender key de l'émetteur) et un index de dérivation (pour pouvoir calculer sa clé de déchiffrement à partir de la sender key reçue au préalable).
Stratégie d'expiration des clés de chiffrement (Sender keys)
Les Sender Keys d'un groupe (Megolm session) sont régénérées :
chaque semaine
tous les 100 messages
quand un appareil quitte le groupe (pour que cet appareil ne puisse pas déchiffrer les prochains messages)
quand un participant le demande (commande '\discardsession')
Il n'est pas nécessaire de régénérer les Sender Keys des participants quand on nouveau participant arrive. Il recevra les Sender Keys des autres participants dans leur dérivation actuelle et sera incapable de déchiffrer l'historique du salon car il ne peut pas revenir en arrière dans les dérivations de clés (bloqué par le "ratchet").
Quand un message ne peut pas être déchiffré sur un appareil c'est parce que cet appareil n'a pas reçu la clé de déchiffrement (sender key) qui est sensée être transmise par le canal Olm direct (d'appareil à appareil).
Des raisons habituelles de non-déchiffrement sont :
le message fait partie de l'historique et ne pourra jamais être déchiffré (ratchet)
l'émetteur et le destinataire sont sur deux homeServers différents (fédération) et le homeServer de l'émetteur n'était pas informé de l'existence du destinataire au moment de l'envoi (lag/délai dans la fédération)
un réseau peu fiable n'ayant pas pu acheminer la sender key au destinataire
Dialogue entre appareils d'un même utilisateur (Key Request)
Les différents appareils d'un utilisateur, lorsqu'ils sont vérifiés, peuvent aussi s'échanger les clés de chiffrement qu'ils connaissent. C'est le Megolm Key Request. Le nouvel appareil interroge les autres appareils de l'utilisateur au besoin pour récupérer des clés de déchiffrement. Si aucun autre appareil de l'utilisateur n'est accessible en ligne à ce moment, il ne pourra pas obtenir de clés de chiffrement par ce moyen.
Ainsi, un nouvel appareil qui se connecte à un compte, une fois vérifié, pourra avoir accès à l'historique des messages si un autre appareil de l'utilisateur y a déjà accès.
Le key request entre appareils de l'utilisateur se fait salon par salon, et au fur et à mesure du défilement dans le salon.
Vérification d'appareil pour éviter une attaque de type Man-in-the-middle
L'échange de clés permet d'être sûr que le canal de communication est chiffré de bout-en-bout.
La phase de vérification permet d'être sûr qu'il n'y a pas d'intermédiaire qui intercepte le flux (pas de Man-in-the-middle).
Un Man-in-the-middle pourrait se placer sur le flux chiffré de manière invisible : il déchiffrerait-rechiffrerait les flux à la volée entre 2 participants.
La vérification permet d'être sûr que ce n'est pas le cas : si c'était le cas, les emojis/codes de vérification présentés par les 2 appareils se vérifiant ne seraient pas les mêmes du fait du changement de chiffrement au milieu.
Sauvegarde automatique (Key backup)
La sauvegarde automatique des clés de chiffrement sur le serveur (Megolm keys) permet à une nouvelle session vérifiée de récupérer toutes les clés de chiffrement même quand aucun autre appareil de l'utilisateur n'est joignable en ligne (pas de Key Request possible).
Cette sauvegarde activée permet que chaque fois qu'un appareil de l'utilisateur a connaissance d'une nouvelle clé de chiffrement, cette nouvelle clé est envoyée sous forme chiffrée dans la sauvegarde sur le serveur.
La sauvegarde locale de clés peut faire plusieurs dizaines de Mo.
L'API de sauvegarde de clés sur le serveur est très complète et permet de demander les clés progressivement.
Mis à jour le : 24/06/2024
Merci !