SegWit

Les adresses Bitcoin sont des objets auxquels les membres de la cryptosphère sont habitués. Qu’elle se manifeste sous la forme d’une (rébarbative) suite de caractères ou d’un QR code, chacun a déjà eu affaire à une telle adresse. Et chacun aura ainsi eu l’occasion de se rendre compte qu’il en existe différents formats (“Tiens, c’est fou toutes ces adresses qui commencent par 1 ou par 3 !”).

Concrètement, il existe trois préfixes possibles pour les différentes adresses Bitcoin :

  • celles commençant par un 1, dites legacy. Ce sont les adresses “classiques” et historiques du protocole Bitcoin
  • celles commençant par un 3, dites segwit-nested (même s’il peut également s’agir d’adresses multisig)
  • celles commençant par bc1, dites segwit-native et dont le format s’appelle Bech32

Le lecteur attentif aura remarqué que, derrière les deux derniers types d’adresses, semble se cacher quelque chose d’un peu mystérieux, au doux nom de SegWit. Mais qu’est-ce donc que cet animal ?

Qu’est-ce que c’est ?

SegWit est un changement dans l’architecture des transactions qui permet de stocker les signatures dans une structure de donnée séparée, liée au bloc mais qui n’est pas prise en compte dans le calcul des identifiants (ou hash) des transactions. C’est d’ailleurs de là que vient son nom, SegWit étant la contraction de segregated (séparé) et witnesses (témoins, désignant ici les signatures).

En effet, avant SegWit, chaque transaction était incorporée dans le bloc avec sa signature attachée. Pour chaque transaction, son identifiant résultait du hachage des informations de la transactions et de la signature. Ensuite, tous les identifiants de transaction étaient combinés dans un arbre de Merkle, pour finalement donner un hash unique, la racine de Merkle, qui résume l’arbre entier et est inséré en haut du bloc (dans le header pour les connaisseurs).

Une représentation d’un arbre de Merkle. Les hash des transactions sont tout en bas de l’arbre (les feuilles, ici Ha, Hb, Hc et Hd). En les combinant successivement deux à deux, on finit par obtenir un hash unique (la racine de Merkle, tout en haut) qui “résume” l’ensemble de l’arbre.

Avec SegWit, on n’a plus un seul arbre de Merkle, mais deux : un pour les transactions, et l’autre pour les signatures. La racine de Merkle des transactions est, comme avant, inscrite dans le header, tandis que la racine de Merkle des signatures se trouve dans la transaction coinbase (celle qui contient la récompense de bloc pour le mineur).

SegWit a été implémenté sur le réseau Bitcoin au cours d’un soft fork en août 2017. L’utiliser reste une option : nul n’est obligé d’utiliser SegWit. Cependant, pour un nombre de raisons que nous allons détailler plus bas, l’utilisation de SegWit n’a eu de cesse de gagner du terrain depuis son implémentation.

A quoi ça sert ?

SegWit, en conservant les signatures dans le même bloc mais en les plaçant dans un arbre de Merkle séparé, apporte une solution à deux problèmes importants du protocole Bitcoin :

  • la taille limitée des blocs, qui résulte dans une augmentation des frais de transaction lorsque le nombre de transactions est trop important
  • la taille de la blockchain Bitcoin
  • la malléabilité, où un attaquant peut modifier l’identifiant d’une transaction sans altérer sa validité

Taille des blocs et frais de transaction

En déplaçant les signatures et en insérant la Merkle root qui leur est associée dans la transaction coinbase, SegWit a permis d’augmenter la taille des blocs, sans recourir pour cela à un hard fork et sans toucher à la taille physique des blocs (block size, fixée à 1 Mo). De l’optimisation pure et simple !

Pour parvenir à cette prouesse, SegWit s’affranchit de la notion de block size et la remplace par celle de max block weight, ou poids de bloc maximal en bon français. On estime ainsi que cela permet actuellement de faire rentrer jusqu’à 1,7 Mo de transactions dans un bloc, et même 2 Mo si l’utilisation de SegWit s’élargit (et qu’il n’y a donc plus que des transactions SegWit dans les blocs). Le tout en maintenant un rétro-compatibilité avec les noeuds qui ne sont pas passés à SegWit, ce qu’un hard fork ne permettrait pas.

Les signatures des transactions peuvent représenter une bonne part de la donnée (en terme de place occupée) d’une transaction. Les placer dans une structure de donnée séparée (mais, encore une fois, toujours dans le bloc) permet de bénéficier d’une réduction des frais liés à la transaction. Plus précisément, c’est la donnée liée à la signature qui est inscrite dans le bloc à moindre frais, mais comme cette donnée représente une part non négligeable de la donnée totale de la transaction, cela résulte en une diminution globale des frais de transactions en utilisant SegWit, comparé aux transactions “traditionnelles”.

La taille de la blockchain

En outre, une fois qu’un noeud (complet par exemple, ou full validating node) a validé les signatures, il n’est plus obligé (comme c’était le cas autrefois) de les conserver sur son disque dur, ce qui rend la blockchain Bitcoin bien plus légère à héberger pour les noeuds.

La malléabilité

La malléabilité est un problème bien connu du protocole Bitcoin, qui permet à un attaquant de modifier l’identifiant d’une transaction en changeant très légèrement la signature qui y est attachée. Ainsi, la transaction est toujours valide, mais avec un identifiant différent. Cela peut poser problème lorsque d’autres transactions s’appuient sur cette transaction, comme c’est le cas pour de nombreux smart contracts, comme ceux permettant d’ouvrir des canaux de paiements par exemple.

Avec SegWit, les signatures ne sont pas prises en compte dans le calcul des identifiants des transactions. Ainsi, il n’est plus possible de modifier l’identifiant d’une transaction en changeant sa signature. Cela permet donc d’implémenter sereinement certains protocoles qui reposent sur l’élaboration de transactions Bitcoin complexes, comme le Lightning Network par exemple.

En résumé

SegWit représente donc une amélioration majeure du protocole Bitcoin. Son implémentation permet :

  • de faire rentrer plus de transactions dans un seul bloc en optimisant l’espace disponible, débouchant ainsi sur une diminution des frais de transactions
  • de réduire la taille de la blockchain à stocker, et ce même pour les noeuds validants (et pas simplement pour les noeuds effectuant de la SPV)
  • d’ouvrir la voie à l’implémentation de smart contracts et protocoles s’appuyant sur des transactions Bitcoin complexes, comme le Lightning Network par exemple.

L’élégance de cette amélioration résulte également dans le fait qu’elle fut menée au travers d’un soft fork (contrairement à la proposition SegWit2x, qui aurait nécessité un hard fork), maintenant ainsi une rétro-compatibilité avec les noeuds utilisant encore l’ancienne version du protocole. En témoignent les adresses segwit-nested, commençant par “3”, et qui, bien que qu’implémentant SegWit, reste compréhensibles des wallets qui ne l’ont pas encore implémenté.

Laisser un commentaire

Ce site utilise Akismet pour réduire les indésirables. En savoir plus sur comment les données de vos commentaires sont utilisées.