Ring signatures pour anonymiser les noeuds sur le réseau

Alors voilà je réfléchi beaucoup a ws2p v2 en ce moment, je vais poster une RFC bientôt pour ça :wink:

Mais voilà il y a une feature que j’aimerais beaucoup implémenter a ws2p v2 mais il semble que cela ne soit pas possible avec ed25519, ou alors j’ai mal compris ? J’ai besoin de l’avis de spécialistes en crypto a ce sujet. @nanocryk peut-être ?

Alors voilà, l’implémentation du ticket #1182 aura pour conséquence que les nœuds membres masqués seront traités comme des nœuds miroir sur le réseau, ce qui pose des problème et sera bloquant pour la généralisation de cette pratique.
Il faut donc qu’un noeud membre puisse prouver qu’il est membre sans dévoiler quel membre il est, cela sera d’autant plus appréciable pour empêcher toute attaque ciblée, ce qui peut être appréciable pour l’intégration du bonus aléatoire de pow par exemple.

Soyons bien clair, les écrivains des blocs seront toujours connus, je parle juste d’une anonymisation sur le réseau, pas en blockchain.

Pour faire cela, il suffirait dans les communications WS2P ou/et dans les head que le noeud membre masqué prouve qu’il est bien membre via un message ring signé.

Seulement il semble que les ring signature ne soient pas implémentables avec ed25519, mais le soient en revanche avec les signatures de Schnorr :

Si j’ai bien compris alors il me faudra attendre l’implémentation d’autres algos pour dev cette feature, mais peut être que quelque chose m’échappe ?

2 Likes

A première vue en effet il faudrait attendre le support d’autres algo de signatures comme Schnorr.
Il faudrait alors déclarer une clé de Schnorr comme clé déléguée au calcul puis ensuite utiliser des ring signatures pour prouver qu’on fait parti des membres sans donner lequel. Pour la partie clé déléguée et algo de Schnorr je devrais pouvoir le faire, par contre pour les ring signatures je n’ai pas encore le niveau xD Mais ça m’intéresse beaucoup donc je vais surement creuser ça si tu en a besoin.

2 Likes

Alors cette fonctionnalité pose des problèmes assez important. Impossible de requeter le réseau de manière sure et décentralisée sur un mode SPV… En effet, si on ne peut plus déterminer quel noeud correspond à une identité et quel noeud ne correspond pas à une identité, les attaques sybilles sur le réseau peuvent être exécutées, pour noyer les clients décentralisés sous des fausses requêtes.

Justement si, la ring signature permettra de savoir que c’est bien un membre qui a signé, sans savoir lequel en particulier.

1 Like

Le concept est assez simple, enfin beaucoup, plus simple que tout ce qui est ZK en tout cas, il s’agit de signer un message au nom d’un groupe. De plus pas besoin de gérer ça au niveau protocole, tant que le protocole reconnait l’algo de signature de Schnorr alors c’est bon, seul le module ws2p aurait besoin de la feature ring signature.

Bah si, les clients auront toujours la preuve de quel noeud est membre ou ne l’est pas.
Par contre, justement, sans ring signature le noeud est obligé de dévoiler quel membre il est sinon il sera considérer comme miroir c’est nul :confused:

Il faudrait par contre que la plupart des membres calculateurs utilisent une clé de Schnorr comme clé déléguée au calcul, sinon il sera difficile voir impossible de faire correctement un ring.

1 Like

Exactement, j’en ai conscience. Au départ, tant que cette feature sera peu utilisée, l’anonymisation sera “faible”, mais il faut voir long-terme :wink:

Oui, mais si un membre peut avoir 50 noeuds qui apparaissent comme membre sans pouvoir identifier à quel membre il appartient, ses noeuds pèseront 50 fois plus lourd dans les requêtes décentralisées.

1 Like

Oui donc il faut trouver un moyen de reconnaitre que deux nœuds appartiennent au même membre sans savoir de quel membre il s’agit, je suis presque sûr qu’il existe un outils de crypto qui nous permettrais de faire ça :slight_smile:

2 Likes

@Inso si c’est juste pour que les clients puissent déterminer quel est le consensus réseau ils peuvent s’appuyer sur des head qui seraient toujours signés de manière classique donc on saurait toujours a quel membre appartient chaque head et chaque membre n’aurais donc toujours qu’une seule voie, qu’en pense tu ?

Ce n’est pas juste une question de consensus réseau. Il faut aussi que l’on puisse vérifier que quand on demande “Est-ce que tel identité est membre ?” au réseau, cette requête ne puisse pas être victime d’une attaque sybille (ou des dizaines de noeuds malintentionnés répondent une fausse réponse…)

Pour ça, aujourd’hui, je requête par exemple 6 noeuds membre, et je ne considère la réponse correcte que si elle a reçu 6 accords. Sinon, je requête de nouveaux noeuds membres.

1 Like

@Inso @nanocryk

Je pense que la solution se situe coté réseau : il faudrait une api client fait de telle sorte que la réponse passe par l’ensemble du réseau, un peu comme ce que fait bma avec la commande sync mais en beaucoup plus sophistiqué, je m’explique :

Les clients pourraient requeter n’importe-quel noeud (membre ou pas) et lui dire : “je veut la réponse de X membres a la requête Y”. Le noeud en question relayerai alors immédiatement (via ws2p par exemple) le message a l’ensemble des nœuds auquel il est connecté puis par rebond ça se diffuserai puis il récupèrerai les réponses (le noeud d’origine aurait donc amender son ws2id+pubkey a la requete qu’il partage) et enfin il enverrai toutes les réponses au client demandeur, chaque réponse de membre étant signée de façon classique avec sa clé publique de membre dans la réponse.

Cela demanderai de bien interfacer GVA et WS2P dans le cœur, mais je ne vois pas de barrière technique en tout cas :slight_smile:

Une autre solution qui viendra avec le nouveau protocole :

Dans le nouveau protocole, tous les documents seront indexés dans un Merkle Tree.

Un client se synchronise en ne recuperant que les headers et la preuve de travail, qui contiennent les Merkle Root, tous les documents étant segregués plus loin dans le bloc (et ne faisant de la preuve que via le Merkle Root). C’est quelque chose qui pèsera très peu par bloc, surtout s’il ne stocke pas tous les informations annexes. Il peux le faire au près de plusieurs noeuds, pour être sur de partager la même chaine.

Note : en se synchronisant on peut finalement stocker uniquement les Merkle Root, soit 32 o/bloc, soit moins de 3Mo pour toute la blockchain G1, et on pourrait même imaginer de combiner les Merkle Root au fur et à mesure, pour n’en stocker un complet de toute la blockchain. Le client n’aurait alors que 32o à stocker, et log2(nombre de documents) hashs à recevoir des noeuds.

Ensuite, s’il veut vérifier que telle identité est membre, il génère le document d’identité correspondant (sans le signer), et il peux calculer son hash (l’UID du document). Il peut ensuite demander à un premier noeud “Donne moi la branche de Merkle qui contient ce document”. Si on lui donne, il est sur que ce document est bien dans la bloc chain (il peut recalculer l’arbre de Merkle et tomber sur la même Merkle Root). Si on ne lui donne pas, il va demander à un autre noeud.

Avec ce système on ne peux pas prouver que le document n’existe pas, et on peut assumer qu’après un certain nombre d’essais le document n’existe bel et bien pas. Mais dès que la preuve est obtenue (1er, 2ème requete par exemple), il n’est plus nécéssaire de demander à d’autres noeuds.

Note 2 : Cette technique fonctionne avec n’importe quel document, et permet aussi de prouver que des certifications/transactions/revocations existent, ce qui pourrait être très pratique pour les clients.

Du coup chaque request est broadcast à tous les membres du réseau ? Ca risque pas d’être assez énorme comme charge ?

Correction : log2 et pas ln.
Correction 2 : log2(nombre de documents) et pas log2(nombre de blocs).

Non seulement aux nœuds auquel le noeud est connecté via ws2p, ensuite on peut limiter les rebond a 1 ou 2 step en fonction du nombre X de membres différents souhaités. C’est d’ailleurs ce que je pense déjà vous proposer pour les head afin d’éviter une surcharge du réseau le jours ou il sera très grand :wink:

Le mécanisme basé sur les merkleRoot ne permet malheuresement pas de faire des requêtes avancées telles qu’on l’envisage avec GVA (Telle identité est elle membre, est-elle dans la WoT ou trop loin des sentries,e tc).

Mais c’est un mécanisme intéressant pour toutes les requêtes de type “validation d’écriture de document dans la chaine”. Ca spam moins le réseau que de faire une requête comparative.


Sinon le mécanisme d’elois pourrait fonctionner. Ca risque par contre de surcharger les sockets inter-noeuds au lieu des sockets externes (clients <-> noeuds) ce qui est un risque il me semble. Et les délais de réponse peuvent être allongés (on rajoute N rebonds entre le client et les noeuds, au lieu d’avoir un lien direct client <-> noeud).

1 Like

Alors en fait le plus souvent il ne s’y échange rien, sauf l’hors de l’arrive d’un nouveau bloc, mais entre deux blocs les sockets inter-nœuds sont largement sous-exploités :slight_smile:

Oui il faudrait bien réfléchir a comment optimiser ça. Après dans la pratique un noeud étant connecté en moyenne a plus de 10 autres, et les membres étant prioritaires, 1 seul rebond suffirait pour voir une réponse de 6 membres différents :wink:

Avec le recul, ça pose quand même un problème : ce n’est pas le client qui décide qui lui répond dans ce cas. Comme les 6 noeuds ne sont pas décidés par lui, on peut imaginer qu’un noeud malveillant enverrait spécifiquement une demande de confirmation à 5 autres noeuds malveillant. Ca affaiblit quand même fortement le modèle de sécurité de ces requêtes.

@Inso A un moment il faut faire un choix entre sécurité ou vitesse, ça pourrait être au client de choisir :

Soit le client choisi X membres parmi ceux dans la fenetre courante et dit qu’il veut la réponse de ses 6 membres la, il y aura plus de rebond et un temps de réponse un peu plus long mais ce sera safe.
Soit le client dit “je veut la réponse de X membre le plus vite possible” et la c’est les plus proches sur le réseau qui répondent.

A voir si déja il est vraiment nécessaire d’anonymiser les noeuds sur le réseau :slight_smile:

Savoir quelle clé membre correspond à quelle machine/IP me semble plutôt risqué.

1 Like