<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>https://air.imag.fr/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Corentin.Humbert</id>
	<title>air - User contributions [en]</title>
	<link rel="self" type="application/atom+xml" href="https://air.imag.fr/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Corentin.Humbert"/>
	<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php/Special:Contributions/Corentin.Humbert"/>
	<updated>2026-05-30T02:38:25Z</updated>
	<subtitle>User contributions</subtitle>
	<generator>MediaWiki 1.39.17</generator>
	<entry>
		<id>https://air.imag.fr/index.php?title=Projets_2021-2022&amp;diff=52476</id>
		<title>Projets 2021-2022</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=Projets_2021-2022&amp;diff=52476"/>
		<updated>2022-03-18T10:51:27Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;&amp;lt;[[Projets 2020-2021]] | [[Projets]] | [[Projets 2022-2023]]&amp;gt;&amp;gt;&lt;br /&gt;
=INFO=&lt;br /&gt;
==INFO3==&lt;br /&gt;
&lt;br /&gt;
==INFO4==&lt;br /&gt;
===Projet Semestre S8===&lt;br /&gt;
&lt;br /&gt;
Enseignants responsables : Olivier Richard&lt;br /&gt;
&lt;br /&gt;
* Dates : Lundi après-midi, Mardi après-midi  &lt;br /&gt;
* Lancement: 10 Janvier 2021 après midi&lt;br /&gt;
* Soutenance à mi-parcours: A définir&lt;br /&gt;
* Soutenance: A définir&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;Evaluation à mi-parcours le lundi/mardi ???&#039;&#039;&#039;: Format: 10min (5min de présentation 3 slides au plus, 5min de discussion). Cette évaluation sera prise en compte dans la note finale.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Consignes générales:&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;Vous devez être pro-actifs !!!&#039;&#039;&#039;: Si des points sont pas ou mals spécifiés, vous le faîtes et vous justifiez vos choix. Pour les problèmes techniques éventuels vous pouvez: creuser la question, contacter l&#039;auteur du code si il y a lieu, écrire un rapport de bug (&#039;&#039;&#039;Attention:&#039;&#039;&#039; ca se prépare !), soumettre un patch/pull request, contacter l&#039;enseignant ou la personne référente du projet.&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;Vous devez maintenir une fiche de suivi de projet&#039;&#039;&#039;: elle doit être mise à jour chaque semaine, elle rassemble les élements essentiels du projet, elle indique les évolutions du projet et présente sa feuille de route. &#039;&#039;&#039;Note:&#039;&#039;&#039; le nom de la fiche doit être composé du nom du projet et suffixé par info4_2021_2022. &#039;&#039;&#039;Cette fiche compte pour la note finale&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;Votre code&#039;&#039;&#039; pour doit être hébergé sur le gitlab et à l&#039;URL suivante https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22 , vous utiliserez votre compte UGA.&lt;br /&gt;
&lt;br /&gt;
* Chaque projet doit avoir &#039;&#039;&#039;aux moins 2 dépôts git&#039;&#039;&#039;:&lt;br /&gt;
** &#039;&#039;&#039;Un pour les documents&#039;&#039;&#039; demandés rapport, présentation de pré-soutenante, de soutenance, flyer. &#039;&#039;&#039;Il sera appelé documents.&#039;&#039;&#039;&lt;br /&gt;
** Un ou plusieurs pour le code, les tests, les évaluations, les preuves de concept, la ou les documentations afférentes. &lt;br /&gt;
&lt;br /&gt;
* Les &#039;&#039;&#039;documents public doivent être rédigés en anglais (README, documentation, commentaires de code, nom de variables et de fonctions)&#039;&#039;&#039;.  Le *rapport* sera aussi demandé en *anglais* (il fera la taille d&#039;un rapport de TP). Les transparents des présentation peuvent être en anglais ou en francais, la soutenance sera taire en francais.&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;La note obtenue&#039;&#039;&#039; tiendra compte du &#039;&#039;&#039;nombre et de la qualité des commits&#039;&#039;&#039; observé dans &#039;&#039;&#039;vos dépots git et la branche master&#039;&#039;&#039; (or depot documents). La qualité comprend l&#039;intitulé du commit et son contenu. Les notes pourront être différentiées dans un groupe, il n&#039;est pas acceptable de pas avoir de commit dans le(s) dépôt(s) du projet (or dépôt documents).&lt;br /&gt;
&lt;br /&gt;
* Il est fortement conseillé de suivre un &#039;&#039;&#039;développement incrémental&#039;&#039;&#039; qui permette d&#039;avoir à tout moment un démonstrateur à présenter, un projet peut être constituer d&#039;une succession de &#039;&#039;&#039;démonstrateurs présentables séparément&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
* Vous devez faire aussi des &#039;&#039;&#039;schémas d&#039;architectures générales et/ou spéficiques, des diagrammes de séquence&#039;&#039;&#039;, et autre documents de spécification si nécessaire. Ces documents vous serviront de base de discussion/brainstorming interne ainsi que dans vos différents documents (rapport, présentations, documentation). Ces schémas sont avant tout conceptuels et techniques.&lt;br /&gt;
&lt;br /&gt;
===Propositions de projets S8===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
* 1. [https://codimd.math.cnrs.fr/?next=%2Fs%2FB029qfT5Q Courriels à Suppression Programmée] : Michaël Périn&lt;br /&gt;
* 2. [[Firmwares open source pour une station de réception de satellites pour l’Internet des Objets isolés]], Didier DONSEZ.&lt;br /&gt;
* 3. [[Evaluation du toolkit AI de STM32 pour l&#039;analyse de l&#039;environnement sonore]] (Suite 2022), Didier DONSEZ.&lt;br /&gt;
* 4. [[Algorithmes de géolocalisation d’objets par TDOA (Time Difference of Arrival)]] (suite), Didier DONSEZ.&lt;br /&gt;
* 5. [[Dashboard pour Overwatch]] Olivier Richard&lt;br /&gt;
* 6. [[Application mobile d&#039;enregistrements de noeuds IoT LoRaWAN dans plusieurs réseaux]] (Suite) : Didier DONSEZ&lt;br /&gt;
* 7. [[Bluetooth 5.1 Angle of Arrival based Indoor Localization]] (Suite) : Didier DONSEZ&lt;br /&gt;
* 8. Intégration de composants de mesures environnementales (eau, air, ...) pour le [[Contribution au projet STM32Python|projet STM32Python]] à destination des lycéens: Didier DONSEZ&lt;br /&gt;
* 9. [[Air Quality Station]] (Suite) : Didier DONSEZ&lt;br /&gt;
* 10. [[Floating Water Quality Station]] : Didier DONSEZ, Nicolas PALIX&lt;br /&gt;
* 12. [[Testeur de terrain pour réseaux LoRaWAN privés et publics (TTN, CampusIoT et Helium)]] (suite 2021), Didier DONSEZ.&lt;br /&gt;
* 13. [[Géolocalition Indoor en LoRa 2.4GHz]], Didier DONSEZ.&lt;br /&gt;
* 14. [[RealWorld avec Dioxus]] (Rust + web), Olivier Richard&lt;br /&gt;
* 15. Poursuite projet 20-21 [[Rust Engine | Executeur de tâche en Rust]], Olivier Richard&lt;br /&gt;
* 16. Poursuite projet 20-21 [[Retrocompute simulateur | RetroComputing]]: (vintage style) Coupler le simulateur Digital avec un simulateur de processeur 8bits, Olivier Richard&lt;br /&gt;
* 17. Poursuite projet 19-20 [[Portail pour gestionnaire de taches]](react, Typescript), Olivier Richard&lt;br /&gt;
* 18. [[Paquets NIX pour Polytech]], Olivier Richard&lt;br /&gt;
* 19. [[Mini compilateur C pour mini CPU]], Olivier Richard&lt;br /&gt;
* 20. Mode jeu en réseau (Wifi/Bluetooth) pour [[TanksOfFreedom]], Nicolas Palix&lt;br /&gt;
&lt;br /&gt;
Non affecté&lt;br /&gt;
* xx. [[Bibliothèque de décodeurs standards et d&#039;afficheurs Grafana pour objets connectés LoRaWAN]] : Didier DONSEZ&lt;br /&gt;
* xx. [[ASAC|Agriculture connectée]] en partenariat avec les projets collectifs IESE/MAT : Nicolas Palix&lt;br /&gt;
* xx. [[Faults In Linux]], Nicolas Palix&lt;br /&gt;
&lt;br /&gt;
===Affectations===&lt;br /&gt;
{|class=&amp;quot;wikitable alternance&amp;quot;&lt;br /&gt;
|+ Affectation des projets INFO4 21-22&lt;br /&gt;
|-&lt;br /&gt;
|&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Sujet&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Etudiants&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Enseignant(s)&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Fiche de suivi&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Documents&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 1&lt;br /&gt;
| [https://air.imag.fr/index.php/Planned_Deletion_Emails Courriels à Suppression Programmée]&lt;br /&gt;
| CANIN CORENTIN,MONTEILLER JOSHUA,WAGNER SAMY&lt;br /&gt;
| Michaël PÉRIN&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/01/docs/-/blob/main/%20Courriels%20%C3%A0%20Suppression%20Programm%C3%A9e%20info4_2021_2022.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 2&lt;br /&gt;
| [https://air.imag.fr/index.php/Firmwares_open_source_pour_une_station_de_r%C3%A9ception_de_satellites_pour_l%E2%80%99Internet_des_Objets_isol%C3%A9s# Firmwares open source pour une station de réception de satellites pour l’Internet des Objets isolés]&lt;br /&gt;
| CARMONA DAMIAN,DA COSTA TOM,WOZNY PIERRE-RAPHAEL&lt;br /&gt;
| Didier DONSEZ&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/02/docs/-/blob/main/Firmwares_open_source_pour_une_station_de_r%C3%A9ception_de_satellites_pour_l_Internet_des_Objets_isol%C3%A9s_info4_2021_2022.md# Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 3&lt;br /&gt;
| [https://air.imag.fr/index.php/Evaluation_du_toolkit_AI_de_STM32_pour_l%27analyse_de_l%27environnement_sonore Evaluation du toolkit AI de STM32 pour l&#039;analyse de l&#039;environnement sonore]&lt;br /&gt;
| BACH THOMAS,BARBE FLORENT,SIMO YOKAM GEORGES HARRISSO&lt;br /&gt;
| Didier DONSEZ&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/03/docs/ Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:Midterm_presentation_3_2022.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 5&lt;br /&gt;
| [https://air.imag.fr/index.php/Dashboard_pour_Overwatch# Dashboard pour Overwatch]&lt;br /&gt;
| CAILLES MAXIME,REYGNER ETIENNE,VERRIER MARTIN&lt;br /&gt;
| Olivier RICHARD&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/05/docs/-/blob/main/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 6&lt;br /&gt;
| [[Application mobile d&#039;enregistrements de noeuds IoT LoRaWAN dans plusieurs réseaux]]&lt;br /&gt;
| CHIOTTI MAEL,LAVIROTTE GAETAN,MOTTINO LORIS&lt;br /&gt;
| Didier DONSEZ&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/06/docs/-/tree/main Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 8&lt;br /&gt;
| [https://air.imag.fr/index.php/Contribution_au_projet_STM32Python  Intégration de composants de mesures environnementales (eau, air...) pour le projet STM32Python à destination des lycéens]&lt;br /&gt;
| GUIRGUIS MIRETTE,HADIBY CHEMSSEDDINE,MOHSEN HACHEM&lt;br /&gt;
| Didier DONSEZ&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/08/docs/-/blob/main/README.md#lorawan Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 10&lt;br /&gt;
| [[Floating Water Quality Station]]&lt;br /&gt;
| BRETON EMERIC,FAGHLOUMI AYMAN,VIALLET CAMILLE&lt;br /&gt;
| Didier DONSEZ, Nicolas PALIX&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/10/docs/-/blob/main/info4_2021_2022_Fiche_suivi_projet.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/10/docs/-/blob/main/Soutenance%20mi-parcours%20Projet_S8.pdf Presentation de mi-parcours]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 13&lt;br /&gt;
| [https://air.imag.fr/index.php/G%C3%A9olocalition_Indoor_en_LoRa_2.4GHz Géolocalition Indoor en LoRa 2.4GHz]&lt;br /&gt;
| BERNERD CLARA,JARDIN BAPTISTE,NGUYEN JUSTIN&lt;br /&gt;
| Didier DONSEZ&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/13/docs/-/blob/main/Fiche_de_suivi.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 14&lt;br /&gt;
| [[RealWorld avec Dioxus]]&lt;br /&gt;
| IFAKIREN SAMI,MONTHE DJEUMOU BRICE,NGUYEN CLEMEN&lt;br /&gt;
| Olivier RICHARD&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/14/docs Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 15&lt;br /&gt;
| [https://air.imag.fr/index.php/Rust_Engine Exécuteur de tâche en Rust]&lt;br /&gt;
| CHAPPAZ FLORIAN,DE OLIVEIRA VALENTIN,KURKLU FIKRET&lt;br /&gt;
| Olivier RICHARD&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/15/docs/-/blob/main/Rust_Engine_info4_2021_2022.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/15/docs/-/blob/main/rust_engine_mid_presentation.pdf Presentation de mi-parcours]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 17&lt;br /&gt;
| [https://air.imag.fr/index.php/Portail_pour_gestionnaire_de_taches Portail Pour Gestionnaire De Taches]&lt;br /&gt;
| KACHA TOM,MAHAMAN NOURY ABDOURAHAMANE,MEIGNEN HUGO,ZHANG KEMING&lt;br /&gt;
| Olivier RICHARD&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/17/docs/-/blob/main/Fiche_De_Suivi_17.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/17/docs/-/blob/main/Pr%C3%A9sentation-mi-parcours.pdf Presentation de mi-parcours]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 18&lt;br /&gt;
| [[Paquets NIX pour Polytech]]&lt;br /&gt;
| CONJARD SAMUEL,FODOR GERGELY,PELISSE-VERDOUX CYPRIEN&lt;br /&gt;
| Olivier RICHARD&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/18/docs/-/blob/master/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 19&lt;br /&gt;
| [[Mini compilateur C pour mini CPU]]&lt;br /&gt;
| CAPET THEO,POITEVIN EVE,ROYET JULIAN&lt;br /&gt;
| Olivier Richard&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/19/docs/-/blob/main/C_compiler_for_MCPU_info4_2021_2022.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 20&lt;br /&gt;
| Mode jeu en réseau pour [[TanksOfFreedom]],&lt;br /&gt;
| ABECASSIS THOMAS,FOURNIER THOMAS,ZAFFUTO LUCA&lt;br /&gt;
| Nicolas Palix&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/20/docs/-/blob/main/fiche_de_suivi.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
==INFO5==&lt;br /&gt;
===Projet IoT S9===&lt;br /&gt;
Enseignants responsables : Bernard Tourancheau&lt;br /&gt;
&lt;br /&gt;
Calendrier:  Octobre à Décembre 2021. Soutenance 24 Janvier 2022.&lt;br /&gt;
&lt;br /&gt;
{|class=&amp;quot;wikitable alternance&amp;quot;&lt;br /&gt;
|+ Choix des projet des projets INFO5 Réseaux 21-22&lt;br /&gt;
|-&lt;br /&gt;
|&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Sujet&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Etudiants&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Documents&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Github/Trello&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 1&lt;br /&gt;
| [[Réseau de capteur de dichlorométhane]]&lt;br /&gt;
| Dorian BARET - Malone JULIENNE - Quentin CAMBUS&lt;br /&gt;
| [https://lesjoiesducode.fr/quand-notre-revue-de-sprint-se-passe-nickel Fiche]&lt;br /&gt;
| [https://github.com/Cambus-Quentin/DichloWan2021/blob/main/README.md git]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 2&lt;br /&gt;
| [[Création d&#039;un système pour localiser les élèves lors de courses d&#039;orientation]]&lt;br /&gt;
| Antoine Gitton, Gilles Mertens, Bertrand Baudeur&lt;br /&gt;
| [[Media:2021_2022_INFO5_IOT_Orientation_spec.pdf|Spécification paquets LoRa]]&lt;br /&gt;
| [[Media:2021_2022_INFO5_IOT_Orientation_backend.zip|Souces back-end]] - [[Media:2021_2022_INFO5_IOT_Orientation_carte.zip|Souces carte]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 3&lt;br /&gt;
| [[Harnais animalier permettant de suivre notre animal domestique]]&lt;br /&gt;
| Sami ELHADJI TCHIAMBOU, Corentin HUMBERT, Paul LAMBERT, Hugo PRAT CAPILLA&lt;br /&gt;
| [[Media:PSP_Presentation.pdf|Présentation finale]]&lt;br /&gt;
| [https://github.com/Bicorpro Organisation GitHub]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 4&lt;br /&gt;
| [[Géolocalisation et suivi des transports en commun]]&lt;br /&gt;
| Liam ANDRIEUX, Lucas DREZET, Roman REGOUIN&lt;br /&gt;
|&lt;br /&gt;
| [https://github.com/2021-2022-IoT-INFO5-G4 Organisation GitHub]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 5&lt;br /&gt;
| [[Tracking des déplacements de joueurs sur un terrain]]&lt;br /&gt;
| Elias EL YANDOUZI, Lucas CHALOYARD&lt;br /&gt;
| [[Media:IOT_Presentation.pdf|Présentation finale]]&lt;br /&gt;
| [https://github.com/Indoor-Shadow/ble-experiment Github Repo]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 6&lt;br /&gt;
| [[Beer Pong connecté]]&lt;br /&gt;
| Yael PARA, Théo TEYSSIER, Victor MALOD, Alexis LANQUETIN&lt;br /&gt;
| [[Media:BeerPong_Presentation.pdf|Présentation finale]]&lt;br /&gt;
| [https://github.com/McReaper/BeerPongLora Gitub Repo]&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
Exposés points techniques 10&#039; - questions 5&#039;&lt;br /&gt;
* Nom Sujet&lt;br /&gt;
* ??? Python&lt;br /&gt;
* ??? MQTT&lt;br /&gt;
* ??? COAP&lt;br /&gt;
* 26/11/2021 - Elias El Yandouzi - Les différentes techniques de virtualisation&lt;br /&gt;
&lt;br /&gt;
===Projet Semestre S10===&lt;br /&gt;
&lt;br /&gt;
Enseignant responsable : [[user:Donsez|Didier Donsez]]&lt;br /&gt;
&lt;br /&gt;
Convention des projets tutorés externes : Elise Didier.&lt;br /&gt;
&lt;br /&gt;
Calendrier: 27/01 (8H30-12H00) au 18/03.&lt;br /&gt;
&lt;br /&gt;
Séances de Management de projets innovants: A voir dessus.&lt;br /&gt;
&lt;br /&gt;
Réunion de présentation et choix des sujets: 27/01 (8H30-12H00) en salle Polygone P206 (voir ADE)&lt;br /&gt;
&lt;br /&gt;
Démarrage : 27/01&lt;br /&gt;
&lt;br /&gt;
Soutenance à mi-parcours (à définir) : ??/02/2021 13H30-17H30 en distantiel (15 minutes par équipe).&lt;br /&gt;
&lt;br /&gt;
Soutenance finale : 18/03/2021 (8H30-12H00 et 13H30-17H00). 30 minutes par équipe, questions/réponses et démonstration incluse. Prière de rapporter au fablab le matériel emprunté juste après votre soutenance. &lt;br /&gt;
&lt;br /&gt;
====Séances MPI====&lt;br /&gt;
&lt;br /&gt;
Voir ADE qui fait foi).&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Soutenance intermédiaire S10 ====&lt;br /&gt;
Date: 18/02 Matin. Distantiel (sur Zoom). Créneaux de 10 minutes.&lt;br /&gt;
&lt;br /&gt;
L&#039;objectif de la soutenance intermédiaire est de vérifier si l&#039;équipe projet est en bon ordre de marche&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;équipe présentera en 5-6 transparents en 7 minutes.&lt;br /&gt;
* les équipiers et leurs rôles&lt;br /&gt;
* le contexte, le sujet et l&#039;objectif du projet&lt;br /&gt;
* l&#039;architecture du systèmes à réaliser&lt;br /&gt;
* les technologies utilisées&lt;br /&gt;
* le plan de travail (backlog, planning, ce qui est fait, ce qu&#039;il reste à faire ...)&lt;br /&gt;
* les difficultés (s&#039;il y a)&lt;br /&gt;
&lt;br /&gt;
Prévoyez du temps pour les questions-réponses (3 minutes max).&lt;br /&gt;
&lt;br /&gt;
Respectez bien les créneaux indiqués (par respect pour les autres équipes) et soyez présents un peu en avance dans la salle d&#039;attente.&lt;br /&gt;
&lt;br /&gt;
La présence des porteurs n&#039;est pas obligatoire.&lt;br /&gt;
&lt;br /&gt;
==== Soutenance finale S10 ====&lt;br /&gt;
Date provisoire: 18/03/2022 (8H30-12H00 et 13H30-17H00).&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;La présence du(des) porteur(s) est obligatoire. Pensez à les prévenir bien à l&#039;avance&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Durée: 30 minutes par équipe: présentation, questions/réponses et démonstration incluse.&lt;br /&gt;
&lt;br /&gt;
Les documents devront être en ligne sur le wiki (colonne Documents) la veille (ie avant le 17/03/2021 23:59:59 CET).&lt;br /&gt;
&lt;br /&gt;
La présentation est constituée des chapitres suivants:&lt;br /&gt;
* Rappel du sujet/besoin et cahier des charges&lt;br /&gt;
* Technologies employées&lt;br /&gt;
* Architecture techniques&lt;br /&gt;
* Réalisations techniques&lt;br /&gt;
* Gestion de projet (méthode, planning prévisionnel et effectif, gestion des risques, rôles des membres ...)&lt;br /&gt;
* Outils (collaboration, CD/CI ...)&lt;br /&gt;
* Métriques logiciels : lignes de code, langages, performance, temps ingénieur (d&#039;après vos journaux), la répartition  des lignes de code et des commits en pourcentage entre les membres du projet ...)&lt;br /&gt;
* Conclusion (Retour d&#039;expérience)&lt;br /&gt;
* Transparent expliquant la démonstration&lt;br /&gt;
&lt;br /&gt;
L&#039;ensemble des documents doit être accessible depuis le tableau ci-dessus et dans chaque fiche de suivi.&lt;br /&gt;
&lt;br /&gt;
Le screencast (réalisé lors de la dernière répétition) sera rendu disponible via un partage caché (wetransfer, google drive …) dont le lien sera ajouté dans le devoir idoine sur Moodle et également envoyé par mail à votre tuteur.&lt;br /&gt;
&lt;br /&gt;
Le rapport final contient les mêmes chapitres que la présentation ainsi qu&#039;un glossaire et une bibliographie. Le rapport ne doit pas dépasser 15 pages (schémas et figures compris). Vous pourrez référencer les autres documents que vous avez produits au cours du projet (spécifications détaillées, algorithmes, conception d&#039;écrans ...).&lt;br /&gt;
&lt;br /&gt;
Le rapport final est au format Markdown et doit être placé dans un des dépôts Git de votre groupe/organisation.&lt;br /&gt;
&lt;br /&gt;
Votre fiche d&#039;auto-évaluation doit être déposée sur [https://im2ag-moodle.univ-grenoble-alpes.fr/course/view.php?id=99 Moodle]&lt;br /&gt;
&lt;br /&gt;
NB: le rapport technique listé dans la colonne Documents contient tout ce qui ne tient pas dans les 15 pages du rapport final : cahier des charges, diagrammes UML, enquêtes utilisateurs design UI, API, technologies employées (détail), plan de tests, term of services, conformance RPGD, audits/diagnostiques sécurité, MTBR, rapport de vulnérabilité, plan de charge, rapports de charge, manuel d&#039;installation …  : ça dépend un peu de la nature de votre projet.&lt;br /&gt;
&lt;br /&gt;
Conseil : 30 minutes c&#039;est très court alors répétez la soutenance auparavant ! Prévoyez des transparents supplémentaires en annexe pour répondre aux questions.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Prière de rapporter au fablab le matériel emprunté juste après votre soutenance&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==== Affectations S10====&lt;br /&gt;
{|class=&amp;quot;wikitable alternance&amp;quot;&lt;br /&gt;
 |+ Affectation des projets INFO5 2021-2022&lt;br /&gt;
 |-&lt;br /&gt;
 |&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Sujet&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Etudiants&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Porteur(s)&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Fiche de suivi&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Documents&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Dépôt Git&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Soutenance intermédiaire&lt;br /&gt;
 |-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 1&lt;br /&gt;
| [[Test d&#039;infrastructures avec NixOS]]&lt;br /&gt;
| HUMBERT CORENTIN, MINIER MANCINI TITOUAN (Chef de projet), SUEUR CORENTIN (Scrum master)&lt;br /&gt;
| Olivier RICHARD et Quentin GUILLETEAU&lt;br /&gt;
| [[Test Infrastructures NixOS 2021-2022|Fiche de suivi]]&lt;br /&gt;
| [[Rapport Test Infrastructures NixOS 2021-2022|Rapport final]] - [[Media:Presentation_finale_NixOs.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:Presentation_mi_parcours_NixOs.pdf|Presentation de mi-parcours]] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:English_Poster_NixOS.pdf|Poster EN]] - [[Media:Pitch_NixOS-Compose.pdf|Pitch]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:Presentation_mi_parcours_NixOs.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 2&lt;br /&gt;
| [[Plan dynamique d’un appartement connecté]]&lt;br /&gt;
| GRANGER OSCAR (Chef de projet), NOERIE SOPHIE, SARRE MARGAUX, SALMON AMAD, TEYSSIER THEO (Scrum master)&lt;br /&gt;
| Sybille CAFFIAU&lt;br /&gt;
| [[Projet INFO5 2022 - Plan d&#039;un appartement connecté | Fiche de suivi ]]&lt;br /&gt;
| [[Media:Rapport_de_projet_Plan_de_lappartement_connecte_DOMUS.pdf|Rapport final]] - [[Media:Presentation_finale_FR_DOMUS.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:Presentation_intermediaire_DOMUS.pdf|Presentation de mi-parcours]] - [[Media:Poster_DOMUS_FR.pdf|Poster FR]] - [[Media:Poster_DOMUS_EN.pdf|Poster EN]] - [[Media:Pitch_Plan_dynamique_appartement_connecte.pdf|Pitch]]&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/plateforme-domus/appartementdynamique Dépot Git]&lt;br /&gt;
| [[Media:Presentation_intermediaire_DOMUS.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 3&lt;br /&gt;
| [[Suivi de troupeaux (ovins, bovins) en zone montagneuse avec un réseau LoRaWAN : expérimentation dans la Matheysine]]&lt;br /&gt;
| GITTON ANTOINE, MALOD VICTOR, MUTEL MATHIS&lt;br /&gt;
| Fabrice FOREST&lt;br /&gt;
| [[PROJET-INFO5 2022 AgriLoRa|Fiche de suivi]]&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/-/snippets/237 Rapport final] [[Media:INFO5_AgriConnect_presentation_finale.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Flyer]] - [[Media:INFO5_AgriConnect_presentation_miparcours.pdf|Presentation de mi-parcours]] - [[Media:INFO5_AgriConnect_poster_fr.pdf|Poster FR]] - [[Media:INFO5_AgriConnect_poster_en.pdf|Poster EN]] - [[Media:INFO5_AgriConnect_pitch.pdf|Pitch]] - [https://drive.google.com/file/d/15bZaHscxOSBFGXu1xTfehl1Fqa0u_POn/view?usp=sharing Screencast]&lt;br /&gt;
| [https://gitlab.com/agrilora Dépot Git]&lt;br /&gt;
| [[Media:INFO5_AgriConnect_presentation_miparcours.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 4&lt;br /&gt;
| [[FitSize]]&lt;br /&gt;
| GEITNER TEVA	, GONZALEZ JULES, PARA YAEL&lt;br /&gt;
| Fidèle Eya&#039;a&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [https://github.com/pfefitsize/DOCS/tree/main/Rapport Rapport final] - [[Media:presentation_fitsize.pdf|Presentation finale FR]] - [[Media:PrésentationFitSize.pdf|Presentation de mi-parcours]] - [[Media:poster_fitsize.pdf|Poster EN]] - [[Media:pitch_fitsize.pdf|Pitch]] - [[Media:rapport_technique.pdf|Rapport technique]]&lt;br /&gt;
| [https://github.com/pfefitsize Dépot Git]&lt;br /&gt;
| [[Media:PrésentationFitSize.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 5&lt;br /&gt;
| [[GenderedNews]]&lt;br /&gt;
| AGUIAR MATHILDE (Chef de projet), HAJJI OUMAIMA (SCRUM Master), SIDIBE ROKIATOU DITE ROSE&lt;br /&gt;
| François PORTET, Gilles BASTIN, Ange RICHARD&lt;br /&gt;
| [[PROJET-INFO5 2022 GenderedNews|Fiche de suivi]]&lt;br /&gt;
| [[Media:Genderednews_rapport_.pdf|Rapport final]] - [[Media:Soutenance_finale_genderednews_.pdf|Présentation finale FR]] - [[Media:GenderedNews_final_presentation_.pdf|Final Presentation EN]] - [[Media:flyer_genderednews.pdf|Flyer]] - [[Media: Soutenance_interm_genderednews.pdf|Presentation de mi-parcours]] - [[Media:Poster-genderednews-fr.pdf|Poster FR]] - [[Media:Poster-genderednews-en.pdf|Poster EN]] - [[Media: Pitch_genderednews.pdf | Pitch 180 secondes]]&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/getalp/genderednews Dépot Git]&lt;br /&gt;
| [[Media: Soutenance_interm_genderednews.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 6&lt;br /&gt;
| [[Système d&#039;analyse de traces sportives]]&lt;br /&gt;
| HERQUE ERIC (Scrum Master), VACHERIAS GUILLAUME (Chef de projet)&lt;br /&gt;
| Vivien QUEMA&lt;br /&gt;
| [[PROJET-INFO5 2022 Systeme d&#039;analyse de traces sportive fiche suivis | Fiche de suivi]]&lt;br /&gt;
| [[Media:Rapport_Final_systeme_analyse_trace_sportive.pdf|Rapport final]] - [[Media:Presentation_Final_systeme_analyse_trace_sportive.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Flyer]] - [[Media:Presentation_mi_parcours_systeme_analyse_trace_sportive.pdf|Presentation de mi-parcours]]- [[Media:Poster_systeme_analyse_trace_sportive.pdf|Poster FR]] - [[Media:Poster_systeme_analyse_trace_sportive.pdf|Poster EN]] - [[PROJET-INFO5 2022 Systeme d&#039;analyse de traces sportive pitch | Pitch 180 secondes]]&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/vacherig/systeme-analyse-de-traces-sportives Dépot Git]&lt;br /&gt;
| [[Media:Presentation_mi_parcours_systeme_analyse_trace_sportive.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 7&lt;br /&gt;
| [[Qualité de l&#039;Air et Santé des Populations]]&lt;br /&gt;
| BAUDEUR BERTRAND (Scrum Master), MERTENS GILLES (Chef)&lt;br /&gt;
| Marie-Laure AIX&lt;br /&gt;
| [[Qualité de l&#039;Air et Santé des Populations | Fiche de suivi]]&lt;br /&gt;
| [https://github.com/Air-Quality-LoRa/docs/blob/main/README.md Rapport final] - [[Media:presentation_finale_qualite_air.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:Presentation_mi_parcours_qualite_air_baudeur_mertens.pdf|Presentation de mi-parcours]] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-Air-Quality-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://github.com/Air-Quality-LoRa Dépot Git]&lt;br /&gt;
| [[Media:Presentation_mi_parcours_qualite_air_baudeur_mertens.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 8&lt;br /&gt;
| [[Artiphonie(saison 3)]] extension de la [[Artiphonie (saison 2)]]&lt;br /&gt;
| BUISINE JULIEN (Chef de Projet), ELHADJI TCHIAMBOU SAMI, LAMBERT DAPHNE (Scrum Master), LAMBERT PAUL&lt;br /&gt;
| Olivier Richard, Estelle Gillet Perret&lt;br /&gt;
| [[Media: JournalDeBord_2022.pdf|Fiche de suivi]]&lt;br /&gt;
| [[Media:Rapport_final.pdf|Rapport final]] - [[Media:Présentation_finale_-_Artiphonie.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:Poster_Artiphonie_FR.pdf|Flyer]] - [[Media: Artiphonie-Presentation_mi-parcours.pdf|Presentation intermédiaire]] - [[Media:Poster_Artiphonie_FR.pdf|Poster FR]] - [[Media:Poster_Artiphonie_-_LAMBERT,_BUISINE,_ELHADJI_TCHIAMBOU.pdf|Poster EN]] - [[Media: Pitch_Artiphonie_2022.pdf|Pitch Artiphonie 2022]]&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/artiphonie/projet-info5-21-22 Dépot Git]&lt;br /&gt;
| [[Media: Artiphonie-Presentation_mi-parcours.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 9&lt;br /&gt;
| [[Quark Project]] &lt;br /&gt;
| CHALOYARD LUCAS, EL YANDOUZI ELIAS&lt;br /&gt;
| Olivier Gruber&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:Quark_defense.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:Soutenance QuarkV3.pdf|Presentation de mi-parcours]] - [[Media:POSTER QUARK.pdf|Poster FR]] - [[Media:POSTER QUARK.pdf|Poster EN]] - [[Media:ProjetQuark Pitch.pdf|Pitch]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:Soutenance QuarkV3.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 10&lt;br /&gt;
| [[Jorigine]]&lt;br /&gt;
| BLANQUET ANTOINE (&#039;&#039;&#039;Scrum Master&#039;&#039;&#039;), LANQUETIN ALEXIS (&#039;&#039;&#039;Chef de projet&#039;&#039;&#039;), MALECOT ETHAN, PRAT-CAPILLA HUGO&lt;br /&gt;
| Sylvain Delangue&lt;br /&gt;
| [[Media:Fiche_Suivi_Jorigine_Grp10.pdf|Fiche de Suivi]]&lt;br /&gt;
| [[Media:Rapport_Jorigine_Grp10.pdf|Rapport Final]] - [[Media:Presentation_finale_jorigine_2022.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:JorigineFlyer.pdf|Flyer]] - [[Media:Presentation_Projet_miparcours_S10.pdf|Presentation de mi-parcours]] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:PosterJorigine2022_vfinal.pdf|Poster EN]] - [[Media:Pitch_Jorigine_grp10.pdf|Pitch en 180 secondes]] - [https://drive.google.com/file/d/1fUGc38NtNAAjlsfBPqPdwKDNI5l7g1vs/view?usp=sharing Screencast]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:Presentation_Projet_miparcours_S10.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 11&lt;br /&gt;
| [[Contributions open source au projet EdCampus|EdCampus]] &lt;br /&gt;
| ANDRIEUX LIAM, COSOTTI KEVIN, DREZET LUCAS (&#039;&#039;&#039;Chef de projet&#039;&#039;&#039;), REGOUIN ROMAN (&#039;&#039;&#039;Scrum Master&#039;&#039;&#039;)&lt;br /&gt;
| Anthony GEOURJON&lt;br /&gt;
| [https://c.tenor.com/x8v1oNUOmg4AAAAd/rickroll-roll.gif Fiche]&lt;br /&gt;
| [[Rapport EDCampus 2021-2022|Rapport final]] - [https://air.imag.fr/images/2/23/Soutenance_finale_-_EDCampus.pdf Presentation finale FR] - [https://air.imag.fr/images/5/5a/Soutenance_finale_EN_-_EDCampus.pdf Final Presentation EN] - [https://c.tenor.com/x8v1oNUOmg4AAAAd/rickroll-roll.gif Flyer] - [https://air.imag.fr/images/c/ca/Soutenance_interm%C3%A9diaire_-_EDCampus_2021-2022.pdf Presentation de mi-parcours] - [https://air.imag.fr/images/0/00/PosterFREDCampus20212022.pdf Poster FR] - [https://air.imag.fr/images/d/df/EDCampus_-_2021_2022.pdf Poster EN] - [https://air.imag.fr/images/d/d5/PitchEDCampus20212022.pdf Pitch]&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/edcampus Dépot Git]&lt;br /&gt;
| [https://air.imag.fr/images/c/ca/Soutenance_interm%C3%A9diaire_-_EDCampus_2021-2022.pdf Presentation intermédiaire]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 12&lt;br /&gt;
| [[Contributions open source au projet LabnBook|LabnBook]] &lt;br /&gt;
| CIRSTEA PAUL, SOULARD	ALEXANDRE (Chef de projet), TONDEUX EMILIE (Scrum master), YUNG	KEVIN&lt;br /&gt;
| Anthony GEOURJON, Cédric DHAM&lt;br /&gt;
| [[PROJET-INFO5 2022 LabNbook|Fiche de suivi]]&lt;br /&gt;
| [https://github.com/AlexandreSoulard/Groupe-LabnBook/blob/main/rapportLabNbook.md Rapport final] - [[Media:LabnBook_Presentation_finale.pdf|Presentation finale FR]] - [[Media:LabNbook_flyer.pdf|Flyer]] - [[Media:LabnBook.pdf|Presentation de mi-parcours]] - [[Media:Poster_GroupLabnBook_Cirstea_Soulard_Tondeux_Yung.pdf|Poster EN]] - [https://drive.google.com/file/d/102KIVqH-wFF7UYggyVtJiUww-lcN7oXY/view?usp=sharing Pitch 180 secondes] - [https://drive.google.com/file/d/1eWU090ieX3dC8vweB4UKzwfu9E7jk1vI/view?usp=sharing Screencast]&lt;br /&gt;
| [https://github.com/AlexandreSoulard/Groupe-LabnBook Dépot Git]&lt;br /&gt;
| [[Media:LabnBook.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 13&lt;br /&gt;
| [[Green collect]]&lt;br /&gt;
| BARET	DORIAN, CAMBUS QUENTIN (Chef de projet), JULIENNE MALONE, MALLEN GUILLAUME (Scrum master)&lt;br /&gt;
| Bernard TOURANCHEAU&lt;br /&gt;
| [https://github.com/GreenCollects/docs/blob/main/project_managment/Fiche%20de%20suivis.pdf Fiche]&lt;br /&gt;
| [https://github.com/GreenCollects/docs/blob/main/report/CR-Final-Report.md Rapport final] - [https://github.com/GreenCollects/docs/blob/main/soutenance/Soutenance%20final.pdf Presentation finale FR] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [https://github.com/GreenCollects/docs/blob/main/soutenance/Soutenance%20de%20mi-parcours.pdf Presentation de mi-parcours] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [https://github.com/GreenCollects/docs/blob/main/report/PosterEN.pdf Poster EN] - [https://github.com/GreenCollects/docs/blob/main/report/CR-MPI-seance2.md Pitch 180 secondes]&lt;br /&gt;
| [https://github.com/GreenCollects Dépot Git]&lt;br /&gt;
| [https://github.com/GreenCollects/docs/blob/main/soutenance/Soutenance%20de%20mi-parcours.pdf Presentation intermédiaire]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
Sujets non choisis&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
# [[LoRaWAN Roaming]] avec [[Chirpstack]], [[TheThingStack]] et [[Actility]] pour le projet [https://gricad-gitlab.univ-grenoble-alpes.fr/thingsat/public/-/blob/master/cubesat_mission/README.md Thingsat]: Didier DONSEZ, Olivier ALPHAND.&lt;br /&gt;
# [[Contributions logicielles au projet RIOT OS pour le New Space]] : Francois-Xavier MOLINA, Olivier ALPHAND, Didier DONSEZ&lt;br /&gt;
# [[Réseaux social d&#039;organisation de sortie (saison 2)]] refonte [[Réseaux social d&#039;organisation de sortie]], Olivier Richard&lt;br /&gt;
# [[Experiment Process Management]], Olivier Richard&lt;br /&gt;
# [[Language Server for Visual Studio]]: Olivier Gruber&lt;br /&gt;
# ABANDONNé [[Réseau d&#039;Alumni de formations]] (à confirmer), Gérard POLLIER ([https://disrupt-campus.univ-grenoble-alpes.fr/design-factory-grenoble/ Design Factory Grenoble])&lt;br /&gt;
# [[Evaluation du kit IA embarqué Wio Terminal]]: Louis CLOSSON, Didier DONSEZ (sous réserve de réception du matériel commandé)&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=File:Pitch_NixOS-Compose.pdf&amp;diff=52475</id>
		<title>File:Pitch NixOS-Compose.pdf</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=File:Pitch_NixOS-Compose.pdf&amp;diff=52475"/>
		<updated>2022-03-18T10:50:32Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=Rapport_Test_Infrastructures_NixOS_2021-2022&amp;diff=52461</id>
		<title>Rapport Test Infrastructures NixOS 2021-2022</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=Rapport_Test_Infrastructures_NixOS_2021-2022&amp;diff=52461"/>
		<updated>2022-03-18T09:41:37Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;=Rappel du sujet et cahier des charges=&lt;br /&gt;
&lt;br /&gt;
L’objectif est d’expérimenter et de manipuler une technologie récente : &#039;&#039;&#039;NixOS&#039;&#039;&#039; et le projet de recherche &#039;&#039;&#039;NixOS-Compose&#039;&#039;&#039;. Nix est un outil de gestion de paquets (bibliothèques, morceau logiciel offrant certaines fonctionnalités), et NixOS est un système d&#039;exploitation Linux qui utilise Nix dans son architecture. Nous parlerons plus en détails des différentes technologiques manipulées dans la prochaine partie.&lt;br /&gt;
&lt;br /&gt;
Nos expérimentations ont consistées à déployer trois projets différents : &#039;&#039;&#039;Kubernetes&#039;&#039;&#039;, &#039;&#039;&#039;ELK&#039;&#039;&#039; et &#039;&#039;&#039;Hadoop&#039;&#039;&#039; en utilisant l&#039;outil NixOS-Compose. La partie la plus importante n&#039;étant pas de déployer une version aboutie et complête pour chacun de projets mais de documenter nos expériences pour fournir des retours utilisateurs permettant l&#039;amélioration de NixOS-Compose.&lt;br /&gt;
&lt;br /&gt;
=Technologies employées=&lt;br /&gt;
&lt;br /&gt;
==Nix==&lt;br /&gt;
&lt;br /&gt;
Nix est un gestionnaire de paquets et un langage fonctionnel qui se différencie de l&#039;approche classique avec sa grande reproductibilité qu&#039;il trouve incompatible avec le &#039;&#039;Filesystem Hierarchy Standard&#039;&#039;. Il dénonce l&#039;enfer des dépendances que l&#039;on retrouve avec cette approche où l&#039;on ne peut pas déterminer les versions utilisées. Nix repose sur son &#039;&#039;&#039;store&#039;&#039;&#039;, où il stocke toutes les &#039;&#039;&#039;dérivations&#039;&#039;&#039; pour chaque paquet. Ces dérivations contiennent des informations sur toutes les dépendances (d&#039;autres &#039;&#039;dérivations&#039;&#039;) et les instructions de build. Le nom de la &#039;&#039;dérivation&#039;&#039; indique le nom du paquet et un hash qui la rend unique mais surtout qui l&#039;identifie : &#039;&#039;&#039;une même dérivation produira toujours la même sortie.&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Avec cette approche, Nix permet plusieurs choses, notamment :&lt;br /&gt;
* La reproductibilité due au déterminisme des &#039;&#039;dérivations&#039;&#039;&lt;br /&gt;
* La possibilité d&#039;utiliser plusieurs versions d&#039;un même paquet en parallèle&lt;br /&gt;
* Comme le nom de la dérivation l&#039;identifie, il est possible de mettre en cache la sortie et la récupérer sans avoir à la reconstruire&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Nixpkgs&#039;&#039;&#039; est un répertoire en ligne contenant de nombreux paquets (80 000 actuellement) construits à partir de &#039;&#039;dérivations&#039;&#039; fournies par la communauté et accessibles à tous.&lt;br /&gt;
&lt;br /&gt;
==NixOS==&lt;br /&gt;
&lt;br /&gt;
NixOS est une distribution GNU/Linux reposant sur Nix en tant que gestionnaire de paquets mais également de gestionnaire de configuration. L&#039;ensemble du système et toutes les configurations sont considérés comme des dérivations. Cela permet entre autres de faire des restorations du système à des versions précédentes simplement, chaque modification du système occasionne la création d&#039;une nouvelle version &#039;&#039;&#039;atomique&#039;&#039;&#039;. Par ailleurs, le système d&#039;exploitation hérite ainsi de la propriété &#039;&#039;&#039;déterministe&#039;&#039;&#039; et &#039;&#039;&#039;reproductible&#039;&#039;&#039; que Nix offre.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;NixOS-test&#039;&#039;&#039; est une librairie de test qui permet, à partir d&#039;un ensemble de fichiers de configuration Nix, de fournir une interface python pour manipuler ces configurations sur une/des machines virtuelles avec &#039;&#039;&#039;QEMU&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==NixOS-Compose==&lt;br /&gt;
&lt;br /&gt;
NixOS-Compose est un projet de l’équipe Datamove qui étend l’utilisation de NixOS vers d’autres supports que les machines virtuelles, comme notamment la plateforme &#039;&#039;&#039;Grid&#039;5000&#039;&#039;&#039; et des solutions de conteneurs comme &#039;&#039;&#039;Docker&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
Kubernetes est un &#039;&#039;&#039;orchestrateur de conteneurs&#039;&#039;&#039; permettant de déployer, mettre à l&#039;échelle et surveiller des applications conteneurisées sur un cluster de machines. Développé en Go et rendu open source en 2015 par Google inspiré de leur solution privée Borg, Kubernetes est maintenant l&#039;outil central du monde du &#039;&#039;&#039;DevOps&#039;&#039;&#039; dans l&#039;industrie. Il apporte une couche d&#039;abstraction au dessus d&#039;un datacenter, dont la mise en place a également été facilitée par le cloud, pour fournir une &#039;&#039;&#039;plateforme de déploiement&#039;&#039;&#039; fortement disponible aux développeurs. Kubernetes dispose également d&#039;un &#039;&#039;&#039;large écosystème&#039;&#039;&#039; d&#039;outils et plugins améliorant différents aspects de son utilisation : routage, monitoring, sécurité, gitops, déploiements (vert/bleu, canary...), serverless etc.&lt;br /&gt;
    &lt;br /&gt;
En cette qualité, Kubernetes est une plateforme de choix dans le cadre d&#039;expériences nécessitant notamment un certain nombre de services ou applications, comme dans le cas d&#039;architectures &#039;&#039;&#039;microservices&#039;&#039;&#039; par exemple. De plus, malgré ses nombreux atouts, Kubernetes est une solution souvent difficile et longue à mettre initialement en place pour cause d&#039;une &#039;&#039;&#039;configuration complexe&#039;&#039;&#039; liée à l&#039;architecture microservice de la plateforme elle-même. (Il faut reconnaître qu&#039;avec le cloud il est maintenant très simple de déployer un cluster Kubernetes, &#039;&#039;Terraform&#039;&#039; est notamment un concurrent potentiel de NixOS-Compose) &lt;br /&gt;
&lt;br /&gt;
Dans le cadre de notre projet, être en mesure de fournir un cluster Kubernetes de la taille voulue, &#039;&#039;&#039;simplement&#039;&#039;&#039;, &#039;&#039;&#039;rapidemment&#039;&#039;&#039; et de manière &#039;&#039;&#039;reproductible&#039;&#039;&#039;, est un objectif très intéressant, non seulement pour l&#039;aspect apprentissage mais également pour son utilisation dans le contextes d&#039;expériences scientifiques avec NixOS-Compose. &#039;&#039;&#039;Kubernetes est en lui même un solution qui permet une forte reproductibilité au niveau des déploiements internes, mais c&#039;est la phase de déploiement des machines et de bootstrap du cluster qui manque cette qualité, et c&#039;est là que nous nous positionnons.&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
&amp;quot;ELK&amp;quot; est l&#039;acronyme de trois projets open source : &#039;&#039;&#039;Elasticsearch&#039;&#039;&#039;, &#039;&#039;&#039;Logstash&#039;&#039;&#039; et &#039;&#039;&#039;Kibana&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
[[File:Elk_stack.png|thumb|600px|right|Intéraction des composants au sein de la stack ELK ou BELK]]&lt;br /&gt;
&lt;br /&gt;
===Elasticsearch===&lt;br /&gt;
&lt;br /&gt;
Elasticsearch est un &#039;&#039;&#039;outil de recherche et d&#039;analyse de données&#039;&#039;&#039; fonctionnant de manière &#039;&#039;&#039;distribuée&#039;&#039;&#039; et basé sur [Apache Lucene](https://lucene.apache.org/). Créé par Shay Banon en 2004, au fil des années, Elasticsearch n&#039;a cessé d&#039;évoluer et aujourd&#039;hui c&#039;est l&#039;outil de référence pour réaliser une recherche performante sur une large quantité de données.&lt;br /&gt;
&lt;br /&gt;
Technologiquement parlant, il s&#039;agit d&#039;une base de données programmée en Java et &#039;&#039;&#039;spécialisée dans la recherche et l&#039;indexation de documents&#039;&#039;&#039;. Si Elasticsearch est aussi performant c&#039;est grâce à son fonctionnement en mode distribué. La tâche de recherche est exécutée en parallèle par plusieurs nœuds Elasticsearch, ce qui améliore la réactivité du système. Elasticsearch a aussi la force d&#039;être facilement configurable et mis à l&#039;échelle.&lt;br /&gt;
&lt;br /&gt;
===Logstash===&lt;br /&gt;
&lt;br /&gt;
Logstash est un outil écrit en Java et en Ruby permettant de &#039;&#039;&#039;centraliser des traces&#039;&#039;&#039; provenant de plusieurs systèmes, de les analyser et de les stocker. Conceptuellement, Logstash peut être vu comme un &#039;&#039;&#039;&amp;quot;pipe&amp;quot;&#039;&#039;&#039; où les données rentrent d&#039;un bout, et sont traitées avant de ressortir de l&#039;autre bout. Logstash est plus qu&#039;un simple &amp;quot;pipe&amp;quot; puisqu&#039;il peut prendre une multitude de sources différentes en entrées et renvoyées les données traitées vers différentes sorties. Il sert généralement à filtrer/analyser des messages avant de les envoyer à Elasticsearch qui va, lui, se charger de les stocker et de les indexer.&lt;br /&gt;
&lt;br /&gt;
===Kibana===&lt;br /&gt;
&lt;br /&gt;
Kibana est un outil permettant la &#039;&#039;&#039;visualisation de données&#039;&#039;&#039; écrit en JavaScript est la dernière composante majeure de la stack ELK. Il est similaire à d&#039;autres outils de visualisation tel que [Grafana](https://grafana.com/), mais a la particularité d&#039;être spécialisé pour une utilisation au sein de la stack ELK. Le rôle de Kibana est donc de récupérer les données indexées par Elasticsearch et de les rendre visuellement exploitables pour un humain.&lt;br /&gt;
&lt;br /&gt;
===Beats===&lt;br /&gt;
&lt;br /&gt;
Bien que la stack ELK soit l&#039;acronyme des trois projets majeurs dont nous avons parlé précédemment, ELK est consistué d&#039;un autre projet nommé &#039;&#039;&#039;Beats&#039;&#039;&#039;. Il y a d&#039;ailleurs quelques discussions autour du renommage de la stack ELK en stack BELK pour inclure le projet Beats. Beats est une plateforme réunissant une multitude de petits &#039;&#039;&#039;outils permettant d&#039;expédier des données&#039;&#039;&#039; vers Logstash ou Elasticsearch. Chaque outil vise un type de données spécifiques. On retrouvera par exemple l&#039;outil Filebeat pour l&#039;expédition de traces systèmes, Metricbeat pour les métriques, Packetbeat pour le réseau ou encore Heartbeat pour le monitoring. Cette liste est non exhaustive, il existe plein d&#039;autres beats, chacun spécialisé pour des données de nature différente.&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Hadoop est un framework open source Java destiné à faciliter la création d&#039;applications distribuées (au niveau du stockage des données et de leur traitement) et scalables permettant aux applications de travailler avec des milliers de nœuds et des masses importantes de données. Ainsi chaque nœud est constitué de machines standard regroupées en grappe. Hadoop fonctionne avec de nombreux modules ou services conçus selon l&#039;idée que les pannes matérielles sont fréquentes et qu&#039;en conséquence elles doivent être gérées automatiquement par le framework. Cet aspect de redondance n&#039;est pas traité dans ce projet.&lt;br /&gt;
&lt;br /&gt;
=Architectures techniques=&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
L&#039;architecture de Kubernetes est distribuée sous forme de microservices avec plusieurs composants, chacun responsable d&#039;une certaine tâche pour contrôler le cluster et les applications qui y vivent. Tout d&#039;abord, les composants sont à séparer en deux groupes: le control plane, tête pensante du cluster, et les composants des nodes, responsables de faire fonctionner les conteneurs. Une machine est dite nœud maître dès lors qu&#039;elle est membre du control plane (elle exécute les composants du control plane, seule ou en communication avec les autres maîtres). Une machine peut à la fois être maître et exécuter des conteneurs (control plane et *Node*), ce n&#039;est toutefois pas recommandé au vu de l&#039;importance du rôle du control plane.&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-kubernetes-architecture.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://kubernetes.io/docs/concepts/overview/components&lt;br /&gt;
&lt;br /&gt;
===Control plane===&lt;br /&gt;
&lt;br /&gt;
Le &#039;&#039;&#039;control plane&#039;&#039;&#039; est un ensemble de composants responsable du bon fonctionnement du cluster. Ces composants sont présents sur chaque nœud maître du cluster. Dans le cas d&#039;un cluster à haute disponibilité (plusieurs maîtres), ces composants fonctionnent de manière distribuée, et nécessitent un load balancer.&lt;br /&gt;
&lt;br /&gt;
Le composant principal est l&#039;&#039;&#039;&#039;apiserver&#039;&#039;&#039;, qui est donc une API permettant la communication entre les différents composants. L&#039;apiserver est le seul composant avec qui les autres composants communiquent. Ensuite le &#039;&#039;&#039;controller manager&#039;&#039;&#039;, regroupe les différents contrôleurs dont le rôle est de gérer les resources qui leur corresponde (le contrôleur des *Pod* veille au bon fonctionnement des &#039;&#039;Pod&#039;&#039;, pareil pour les &#039;&#039;ReplicasSet&#039;&#039;, &#039;&#039;Endpoint&#039;&#039;, &#039;&#039;Node&#039;&#039;...). Le &#039;&#039;&#039;scheduler&#039;&#039;&#039; est responsable de l&#039;attribution des resources (machines) aux applications (&#039;&#039;Pod&#039;&#039;, &#039;&#039;Deployment&#039;&#039;...) selon les disponibilités et besoins. Enfin, &#039;&#039;&#039;etcd&#039;&#039;&#039; est une base de données distribuée de configuration qui conserve l&#039;état du cluster. C&#039;est une solution tiers et elle peut être exécutée sur un cluster à part des nœuds maître.&lt;br /&gt;
&lt;br /&gt;
===Node===&lt;br /&gt;
&lt;br /&gt;
Pour Kubernetes, un &#039;&#039;&#039;Node&#039;&#039;&#039; (ou nœud en français) est l&#039;abstraction d&#039;une machine (réelle ou virtuelle). Chaque machine représentant un &#039;&#039;Node&#039;&#039; doit faire tourner trois services: le kubelet, le kube-proxy et un environnement d&#039;exécution de conteneurs.&lt;br /&gt;
&lt;br /&gt;
Le &#039;&#039;&#039;kubelet&#039;&#039;&#039; est véritablement le responsable des conteneurs en pratique, il est le contremaître obéissant au control plane, chargé de faire appliquer ses directives. Le kubelet ordonne à l&#039;environnement d&#039;exécution de conteneurs et fait ses rapports de situation au control plane. Le &#039;&#039;&#039;kube-proxy&#039;&#039;&#039; est chargé de mettre en place les règles de réseau (iptables ou IPVS) pour veiller au bon fonctionnement notamment des &#039;&#039;Service&#039;&#039; et &#039;&#039;Endpoint&#039;&#039;. Enfin, &#039;&#039;&#039;l&#039;environnement d&#039;exécution de conteneurs&#039;&#039;&#039; peut être n&#039;importe quel solution respectant la CRI (container runtime interface) comme containerd ou CRI-O.&lt;br /&gt;
&lt;br /&gt;
Non-obligatoire mais également souvent présent est un &#039;&#039;&#039;plugin de CNI&#039;&#039;&#039; (container network interface) qui met en place le plan de réseau exigé par Kubernetes (à savoir un réseau où les &#039;&#039;Pod&#039;&#039; disposent d&#039;une adresse IP et peuvent communiquer entre eux) à ne pas confondre avec le réseau connectant les machines entre elles. On peut citer notamment Calico, Weave et celui qui est utilisé dans notre projet est Flannel (moins puissant). Parmi les addons on retrouve également un &#039;&#039;&#039;serveur DNS&#039;&#039;&#039; (nécessaire au bon fonctionnement des Services), anciennement kube-dns et maintenant plutôt coredns.&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
En ce qui concerne ELK, il ne s&#039;agit non pas d&#039;un système ou d&#039;un outil en lui-même mais de la collaboration d&#039;une multitude d&#039;outils open source ayant chacun leurs particularités et un fonctionnement qui leur est propre. Pour visualiser plus aisément l&#039;intéraction entre les différentes composantes de la stack ELK, on pourra s&#039;intéresser à l&#039;exemple suivant:&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-elk-architecture.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://fr.wikipedia.org/wiki/Logstash&lt;br /&gt;
&lt;br /&gt;
Dans l&#039;exemple ci-dessus, on distingue trois sources indépendantes: MediaWiki, des services Node.js et Hadoop. Chacune des trois sources envoie des données à une instance différente de Logstash. Les instances de Logstash ne communiquent pas entre elles, toutefois, une fois le traitement des données effectué, chaque instance envoie ses données à un nœud Elasticsearch. Dans le schéma ci-dessus, les trois nœuds font partie d&#039;un même cluster, ce qui permet donc la mise en commun de l&#039;intégralité des données pouvant ensuite être visualisées via Kibana.&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Hadoop est un environement distribué de par son stockage mais également son traitement de données. C&#039;est une suite de solution open source pour le big data. The goal is to instanciate the different kind of nodes from one of the two possible implementation below, and make them communicate to run a job on the cluster.&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-hadoop-architecture-1.png|center]]&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-hadoop-architecture-2.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://www.geeksforgeeks.org/hadoop-introduction&lt;br /&gt;
&lt;br /&gt;
=Réalisations techniques=&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
L&#039;expérience avec Kubernetes consiste avant tout à déployer un cluster Kubernetes fonctionnel, utilisable comme n&#039;importe quel autre cluster. Pour cela nous nous reposons donc tout d&#039;abord sur la dérivation de Kubernetes sur nixpkgs. Ensuite nous utilisons d&#039;autres outils comme &#039;&#039;Helm&#039;&#039; et &#039;&#039;Istio&#039;&#039; pour enrichir l&#039;expérience.&lt;br /&gt;
&lt;br /&gt;
La dérivations de Kubernetes propose la version 1.21.6, avec certains aspects de configuration qui sont cependant déprécié (notamment au niveau des ports uti lisés et des flags devenus déconseillés) car non mis à jour depuis 4 ans. La configuration de cette dérivation peut se faire de deux manière: en précisant la configuration de tous les composants (cf. partie II), ou en précisant uniquement le rôle de la machine. Avec la première approche non pouvons avoir un contrôle complet sur la configuration alors que dans le second tout est plus abstrait. En revanche la deuxième manière est plus simple et plus claire. Nous avons opté pour la seconde en ajoutant un certain nombre d&#039;options supplémentaires. &lt;br /&gt;
&lt;br /&gt;
La composition de l&#039;expérience commence avec la description des machines ainsi que leur rôle dans le cluster. Nous utilisons généralement un nœud maître et deux nœuds de travail, sachant qu&#039;il n&#039;est pas possible actuellement de déployer un cluster à haute disponibilité dont le bootstrap des certificats est automatisé dans le déploiement, autrement il faut le faire manuellement ce qui est hors de question dans le cadre d&#039;un environnement reproductible.&lt;br /&gt;
&lt;br /&gt;
Ensuite nous disposons d&#039;une fonction pour générer la configuration des machines du cluster. Cette configuration contient donc le rôle du node mais également des ajustements sur les ports et addresses IP de certains composants pour permettre la bonne communication des composants entre eux.&lt;br /&gt;
&lt;br /&gt;
Nous ajoutons également une machine supplémentaire hors-cluster, c&#039;est une serveur NFS, une solution parmis d&#039;autres pour fournir au cluster un moyen de créer des volumes (&#039;&#039;PersistentVolume&#039;&#039;) accessibles par tous les nœuds. Ce serveur est monté sur toutes les machines, ce qui permet à l&#039;expérimentateur de soit utiliser des volumes NFS, soit des volumes locaux pour plus de simplicité.&lt;br /&gt;
&lt;br /&gt;
Avec Istio nous pouvons suivre le guide d&#039;exemple présent dans la documentation pour déployer une application microservice et vérifier le bon fonctionnement du cluster.&lt;br /&gt;
&lt;br /&gt;
Cette composition est fonctionnelle pour la plateforme de nixos-test et nixos-test-driver, toutes deux reposant sur QEMU, et également sur Grid&#039;5000 où elle dévoile son vrai potentielle car les machines sont réelles et véritablement utilisables pour administrer le cluster. Elle n&#039;est pas fonctionnelle sur Docker pour des raisons propres à NixOS-Compose qui ne permettent pas de modifier les noms d&#039;hôtes (/etc/hosts), ce qui empêche la dérivation de fonctionner correctement.&lt;br /&gt;
&lt;br /&gt;
Certains éléments de bootstrap se révèlent être difficilement applicable lors du déploiement avec NixOS-Compose et nous reposons donc en partie sur un script d&#039;initialisation du cluster. Ce script est créé dans la composition et accessible dans le path. Il redémarre les composants éventuellement échoués et affiche une commande à l&#039;utilisateur permettant d&#039;ajouter des machines au cluster, cette étape n&#039;tant pas automatisable simplement (l&#039;approche est la même que kubeadm).&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;expérience ELK, une grande partie du temps a été passée à comprendre la stack ELK et ses différentes composantes. Pour réaliser une composition fonctionnelle via NixOS-Compose, nous nous sommes basés sur une composition pré-existante écrite pour NixOS-Tests. La composition a ensuite été modifiée de manière à fonctionner correctement pour les différents modes de déploiement (Docker, Grid&#039;5000).&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Un paquet hadoop existe deja et il s&#039;agit principalement d&#039;en faire sa configuration. Plusieurs configurations différentes ont été réalisées, une minimale afin de comprendre le fonctionnement général, puis une se servant de yarn afin de maitriser la multiplicité des nœuds de travail.&lt;br /&gt;
    &lt;br /&gt;
Dans la composition minimale nous avons pu mettre, comme le premier shéma de la partie précédente, créer un node de front (namenode) ainsi qu&#039;un datanode fonctionnant avec le filesystem.&lt;br /&gt;
&lt;br /&gt;
=Gestion de projet=&lt;br /&gt;
&lt;br /&gt;
Ce projet relève en partie d’un travail de recherche au vu du manque de documentation, du développement toujours en cours de l’OS et de sa faible utilisation de la part de la communauté d’utilisateurs.&lt;br /&gt;
&lt;br /&gt;
Une importante partie de ce projet repose sur la communication entre notre équipe et l’équipe Datamove pour recevoir des consignes et fournir des retours. Pour fluidifier ces échanges nous avons organisé des réunions régulières et mis en place des solutions de communication en permanence à travers des outils comme Telegram et Zoom pour les réunions.&lt;br /&gt;
&lt;br /&gt;
Nous avons mis en place deux types de réunions : des réunions quotidiennes avec un membre de l’équipe Datamove et des réunions hebdomadaires en équipe complète. Les réunions quotidiennes servent principalement à partager l’avancement et exprimer des éventuels blocages. Les réunions hebdomadaires visent davantage à faire un point global et à définir les prochaines étapes.&lt;br /&gt;
&lt;br /&gt;
==Planification==&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de la planification, il nous paraissait essentiel pour un projet comme le nôtre dans lequel énormément de temps est alloué à l&#039;apprentissage d&#039;une technologie plutôt qu&#039;à la production réelle de code de définir une roadmap.&lt;br /&gt;
&lt;br /&gt;
Cette roadmap avait pour but de planifier nos actions sur l’ensemble de la durée du projet. Nous avons fait évoluer la roadmap au fur et à mesure de notre avancement réel. Celle-ci nous a permis non seulement de travailler avec un objectif en tête mais également de partager ces objectifs avec l’équipe Datamove.&lt;br /&gt;
&lt;br /&gt;
==Organisation du travail==&lt;br /&gt;
&lt;br /&gt;
Au commencement de projet, notre objectif à tous était de se former rapidement sur Nix afin de comprendre l&#039;étendu des possibilités de l&#039;outil NixOS-Compose et de commencer à le tester.&lt;br /&gt;
&lt;br /&gt;
Notre première tâche a consisté à écrire une composition k3s compatible avec NixOS-Compose de manière à découvrir la puissance de l&#039;outil.&lt;br /&gt;
&lt;br /&gt;
Ensuite, nous sommes chacun parti sur un projet différent dans l&#039;optique de fournir trois expériences utilisateurs distinctes. La répartition des projets était la suivante :&lt;br /&gt;
* Titouan Minier Mancini : Kubernetes&lt;br /&gt;
* Corentin Humbert : Stack ELK&lt;br /&gt;
* Corentin Sueur : Hadoop&lt;br /&gt;
&lt;br /&gt;
Nous avons donc progressé chacun de notre côté sur nos projets respectifs tout en restant en contact constant de manière à éviter de passer trop temps bloqué sur une partie du projet. La communication a été impérative pour un tel projet au vu de sa complexité et du temps dont nous disposions pour le mener à terme.&lt;br /&gt;
&lt;br /&gt;
==Suivi du travail==&lt;br /&gt;
&lt;br /&gt;
En parallèle nous avons suivi la rédaction de carnets de route individuels où nous expliquons toutes nos actions dans la journée, avec un maximum de détails notamment sur les erreurs. L’objectif est de permettre aux membres de l’équipe Datamove de suivre notre avancée individuelle et d’aider sur les problèmes techniques éventuels. Ces carnet doivent permettre un maximum la reproductibilité des situations pour faciliter la correction.&lt;br /&gt;
&lt;br /&gt;
=Outils de travail=&lt;br /&gt;
&lt;br /&gt;
Au cours de notre projet, nous avons été amenés à utiliser de nombreux outils nous permettant d’échanger entre nous et avec l’équipe Datamove que ce soit pour poser des questions ou partager nos productions.&lt;br /&gt;
&lt;br /&gt;
* Communication écrite/orale :&lt;br /&gt;
** Au sein du groupe : Discord&lt;br /&gt;
** Avec l’équipe Datamove : Telegram, BBB, Zoom&lt;br /&gt;
* Échanges d’informations :&lt;br /&gt;
** Google docs, CodiMD&lt;br /&gt;
* Stockage des documents et du code produit :&lt;br /&gt;
** Dépôt GitLab&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=Métriques logiciels=&lt;br /&gt;
&lt;br /&gt;
Ce projet ne rentre pas dans le cadre d&#039;une production logicielle, la quantité de code produit est faible car le travail est avant tout un travail de compréhension et de recherche. Nous avons produit un fichier de composition pour chaque pile logicielle, ce qui correspond à une centaine de lignes chacune. Le temps était principalement accordé à l&#039;essai, l&#039;avancement à tâtons pour explorer les différentes options disponibles, et à la compréhension du fonctionnement de NixOS-Compose.&lt;br /&gt;
&lt;br /&gt;
Nous avons tous travaillé 35 heures par semaine, à l&#039;exception des première semaines en parallèle avec le projet ECOM où Titouan et Corention Humbert n&#039;étaient plus disponibles qu&#039;à hauteur de 21 à 28 heures par semaine.&lt;br /&gt;
&lt;br /&gt;
=Conclusion=&lt;br /&gt;
&lt;br /&gt;
Ce projet nous a avant tout permis de découvrir l&#039;environnement Nix et la solution NixOS-Compose, qui promet d&#039;être intéressante et un candidat potentiel à l&#039;*Infrastructure as Code* de demain. L&#039;approche est différente de ce que l&#039;on peut rencontrer avec d&#039;autres outils comme Terraform et il est enrichissant de s&#039;y pencher pour élargir sa pensée.&lt;br /&gt;
&lt;br /&gt;
Nous avons également pu travailler sur des piles logicielles que nous ne connaissions pas forcément, ce qui a aussi été très enrichissant. Nous avons appris à utiliser ces piles logicielles et à les configurer, ce qui est généralement le plus important pour ce genre de système. Nous avons appris ou réappris des technologies, et amélioré notre capacité à appréhender un système distribué, savoir d&#039;où viennent les problèmes et comment les résoudre.&lt;br /&gt;
&lt;br /&gt;
Les compositions que nous avons pu fournir à l&#039;issue du projet sont très satisfaisantes. Elles sont fonctionnelles et permettent à d&#039;autres utilisateurs d&#039;appréhender la solution NixOS-Compose. Nous avons également fourni des tutoriels et explications avec ces compositions pour exprimer des retours utilisateur au projet NixOS-Compose, ce qui, nous espérons, permettra de mettre en valeur ce beau projet.&lt;br /&gt;
&lt;br /&gt;
=Démonstration=&lt;br /&gt;
&lt;br /&gt;
La démonstration que nous proposons est de présenter le déploiement de chacune des piles logicielles.&lt;br /&gt;
&lt;br /&gt;
Vidéo de démonstration sur Kubernetes: https://www.youtube.com/watch?v=uOh8BJPj7MU&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=Rapport_Test_Infrastructures_NixOS_2021-2022&amp;diff=52460</id>
		<title>Rapport Test Infrastructures NixOS 2021-2022</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=Rapport_Test_Infrastructures_NixOS_2021-2022&amp;diff=52460"/>
		<updated>2022-03-18T09:38:41Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;=Rappel du sujet et cahier des charges=&lt;br /&gt;
&lt;br /&gt;
L’objectif est d’expérimenter et de manipuler une technologie récente : &#039;&#039;&#039;NixOS&#039;&#039;&#039; et le projet de recherche &#039;&#039;&#039;NixOS-Compose&#039;&#039;&#039;. Nix est un outil de gestion de paquets (bibliothèques, morceau logiciel offrant certaines fonctionnalités), et NixOS est un système d&#039;exploitation Linux qui utilise Nix dans son architecture. Nous parlerons plus en détails des différentes technologiques manipulées dans la prochaine partie.&lt;br /&gt;
&lt;br /&gt;
Nos expérimentations ont consistées à déployer trois projets différents : &#039;&#039;&#039;Kubernetes&#039;&#039;&#039;, &#039;&#039;&#039;ELK&#039;&#039;&#039; et &#039;&#039;&#039;Hadoop&#039;&#039;&#039; en utilisant l&#039;outil NixOS-Compose. La partie la plus importante n&#039;étant pas de déployer une version aboutie et complête pour chacun de projets mais de documenter nos expériences pour fournir des retours utilisateurs permettant l&#039;amélioration de NixOS-Compose.&lt;br /&gt;
&lt;br /&gt;
=Technologies employées=&lt;br /&gt;
&lt;br /&gt;
==Nix==&lt;br /&gt;
&lt;br /&gt;
Nix est un gestionnaire de paquets et un langage fonctionnel qui se différencie de l&#039;approche classique avec sa grande reproductibilité qu&#039;il trouve incompatible avec le &#039;&#039;Filesystem Hierarchy Standard&#039;&#039;. Il dénonce l&#039;enfer des dépendances que l&#039;on retrouve avec cette approche où l&#039;on ne peut pas déterminer les versions utilisées. Nix repose sur son &#039;&#039;&#039;store&#039;&#039;&#039;, où il stocke toutes les &#039;&#039;&#039;dérivations&#039;&#039;&#039; pour chaque paquet. Ces dérivations contiennent des informations sur toutes les dépendances (d&#039;autres &#039;&#039;dérivations&#039;&#039;) et les instructions de build. Le nom de la &#039;&#039;dérivation&#039;&#039; indique le nom du paquet et un hash qui la rend unique mais surtout qui l&#039;identifie : &#039;&#039;&#039;une même dérivation produira toujours la même sortie.&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Avec cette approche, Nix permet plusieurs choses, notamment :&lt;br /&gt;
* La reproductibilité due au déterminisme des &#039;&#039;dérivations&#039;&#039;&lt;br /&gt;
* La possibilité d&#039;utiliser plusieurs versions d&#039;un même paquet en parallèle&lt;br /&gt;
* Comme le nom de la dérivation l&#039;identifie, il est possible de mettre en cache la sortie et la récupérer sans avoir à la reconstruire&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Nixpkgs&#039;&#039;&#039; est un répertoire en ligne contenant de nombreux paquets (80 000 actuellement) construits à partir de &#039;&#039;dérivations&#039;&#039; fournies par la communauté et accessibles à tous.&lt;br /&gt;
&lt;br /&gt;
==NixOS==&lt;br /&gt;
&lt;br /&gt;
NixOS est une distribution GNU/Linux reposant sur Nix en tant que gestionnaire de paquets mais également de gestionnaire de configuration. L&#039;ensemble du système et toutes les configurations sont considérés comme des dérivations. Cela permet entre autres de faire des restorations du système à des versions précédentes simplement, chaque modification du système occasionne la création d&#039;une nouvelle version &#039;&#039;&#039;atomique&#039;&#039;&#039;. Par ailleurs, le système d&#039;exploitation hérite ainsi de la propriété &#039;&#039;&#039;déterministe&#039;&#039;&#039; et &#039;&#039;&#039;reproductible&#039;&#039;&#039; que Nix offre.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;NixOS-test&#039;&#039;&#039; est une librairie de test qui permet, à partir d&#039;un ensemble de fichiers de configuration Nix, de fournir une interface python pour manipuler ces configurations sur une/des machines virtuelles avec &#039;&#039;&#039;QEMU&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==NixOS-Compose==&lt;br /&gt;
&lt;br /&gt;
NixOS-Compose est un projet de l’équipe Datamove qui étend l’utilisation de NixOS vers d’autres supports que les machines virtuelles, comme notamment la plateforme &#039;&#039;&#039;Grid&#039;5000&#039;&#039;&#039; et des solutions de conteneurs comme &#039;&#039;&#039;Docker&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
Kubernetes est un &#039;&#039;&#039;orchestrateur de conteneurs&#039;&#039;&#039; permettant de déployer, mettre à l&#039;échelle et surveiller des applications conteneurisées sur un cluster de machines. Développé en Go et rendu open source en 2015 par Google inspiré de leur solution privée Borg, Kubernetes est maintenant l&#039;outil central du monde du &#039;&#039;&#039;DevOps&#039;&#039;&#039; dans l&#039;industrie. Il apporte une couche d&#039;abstraction au dessus d&#039;un datacenter, dont la mise en place a également été facilitée par le cloud, pour fournir une &#039;&#039;&#039;plateforme de déploiement&#039;&#039;&#039; fortement disponible aux développeurs. Kubernetes dispose également d&#039;un &#039;&#039;&#039;large écosystème&#039;&#039;&#039; d&#039;outils et plugins améliorant différents aspects de son utilisation : routage, monitoring, sécurité, gitops, déploiements (vert/bleu, canary...), serverless etc.&lt;br /&gt;
    &lt;br /&gt;
En cette qualité, Kubernetes est une plateforme de choix dans le cadre d&#039;expériences nécessitant notamment un certain nombre de services ou applications, comme dans le cas d&#039;architectures &#039;&#039;&#039;microservices&#039;&#039;&#039; par exemple. De plus, malgré ses nombreux atouts, Kubernetes est une solution souvent difficile et longue à mettre initialement en place pour cause d&#039;une &#039;&#039;&#039;configuration complexe&#039;&#039;&#039; liée à l&#039;architecture microservice de la plateforme elle-même. (Il faut reconnaître qu&#039;avec le cloud il est maintenant très simple de déployer un cluster Kubernetes, &#039;&#039;Terraform&#039;&#039; est notamment un concurrent potentiel de NixOS-Compose) &lt;br /&gt;
&lt;br /&gt;
Dans le cadre de notre projet, être en mesure de fournir un cluster Kubernetes de la taille voulue, &#039;&#039;&#039;simplement&#039;&#039;&#039;, &#039;&#039;&#039;rapidemment&#039;&#039;&#039; et de manière &#039;&#039;&#039;reproductible&#039;&#039;&#039;, est un objectif très intéressant, non seulement pour l&#039;aspect apprentissage mais également pour son utilisation dans le contextes d&#039;expériences scientifiques avec NixOS-Compose. &#039;&#039;&#039;Kubernetes est en lui même un solution qui permet une forte reproductibilité au niveau des déploiements internes, mais c&#039;est la phase de déploiement des machines et de bootstrap du cluster qui manque cette qualité, et c&#039;est là que nous nous positionnons.&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
&amp;quot;ELK&amp;quot; est l&#039;acronyme de trois projets open source : &#039;&#039;&#039;Elasticsearch&#039;&#039;&#039;, &#039;&#039;&#039;Logstash&#039;&#039;&#039; et &#039;&#039;&#039;Kibana&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
[[File:Elk_stack.png|300px|right|Intéraction des composants au sein de la stack ELK ou BELK]]&lt;br /&gt;
&lt;br /&gt;
===Elasticsearch===&lt;br /&gt;
&lt;br /&gt;
Elasticsearch est un &#039;&#039;&#039;outil de recherche et d&#039;analyse de données&#039;&#039;&#039; fonctionnant de manière &#039;&#039;&#039;distribuée&#039;&#039;&#039; et basé sur [Apache Lucene](https://lucene.apache.org/). Créé par Shay Banon en 2004, au fil des années, Elasticsearch n&#039;a cessé d&#039;évoluer et aujourd&#039;hui c&#039;est l&#039;outil de référence pour réaliser une recherche performante sur une large quantité de données.&lt;br /&gt;
&lt;br /&gt;
Technologiquement parlant, il s&#039;agit d&#039;une base de données programmée en Java et &#039;&#039;&#039;spécialisée dans la recherche et l&#039;indexation de documents&#039;&#039;&#039;. Si Elasticsearch est aussi performant c&#039;est grâce à son fonctionnement en mode distribué. La tâche de recherche est exécutée en parallèle par plusieurs nœuds Elasticsearch, ce qui améliore la réactivité du système. Elasticsearch a aussi la force d&#039;être facilement configurable et mis à l&#039;échelle.&lt;br /&gt;
&lt;br /&gt;
===Logstash===&lt;br /&gt;
&lt;br /&gt;
Logstash est un outil écrit en Java et en Ruby permettant de &#039;&#039;&#039;centraliser des traces&#039;&#039;&#039; provenant de plusieurs systèmes, de les analyser et de les stocker. Conceptuellement, Logstash peut être vu comme un &#039;&#039;&#039;&amp;quot;pipe&amp;quot;&#039;&#039;&#039; où les données rentrent d&#039;un bout, et sont traitées avant de ressortir de l&#039;autre bout. Logstash est plus qu&#039;un simple &amp;quot;pipe&amp;quot; puisqu&#039;il peut prendre une multitude de sources différentes en entrées et renvoyées les données traitées vers différentes sorties. Il sert généralement à filtrer/analyser des messages avant de les envoyer à Elasticsearch qui va, lui, se charger de les stocker et de les indexer.&lt;br /&gt;
&lt;br /&gt;
===Kibana===&lt;br /&gt;
&lt;br /&gt;
Kibana est un outil permettant la &#039;&#039;&#039;visualisation de données&#039;&#039;&#039; écrit en JavaScript est la dernière composante majeure de la stack ELK. Il est similaire à d&#039;autres outils de visualisation tel que [Grafana](https://grafana.com/), mais a la particularité d&#039;être spécialisé pour une utilisation au sein de la stack ELK. Le rôle de Kibana est donc de récupérer les données indexées par Elasticsearch et de les rendre visuellement exploitables pour un humain.&lt;br /&gt;
&lt;br /&gt;
===Beats===&lt;br /&gt;
&lt;br /&gt;
Bien que la stack ELK soit l&#039;acronyme des trois projets majeurs dont nous avons parlé précédemment, ELK est consistué d&#039;un autre projet nommé &#039;&#039;&#039;Beats&#039;&#039;&#039;. Il y a d&#039;ailleurs quelques discussions autour du renommage de la stack ELK en stack BELK pour inclure le projet Beats. Beats est une plateforme réunissant une multitude de petits &#039;&#039;&#039;outils permettant d&#039;expédier des données&#039;&#039;&#039; vers Logstash ou Elasticsearch. Chaque outil vise un type de données spécifiques. On retrouvera par exemple l&#039;outil Filebeat pour l&#039;expédition de traces systèmes, Metricbeat pour les métriques, Packetbeat pour le réseau ou encore Heartbeat pour le monitoring. Cette liste est non exhaustive, il existe plein d&#039;autres beats, chacun spécialisé pour des données de nature différente.&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Hadoop est un framework open source Java destiné à faciliter la création d&#039;applications distribuées (au niveau du stockage des données et de leur traitement) et scalables permettant aux applications de travailler avec des milliers de nœuds et des masses importantes de données. Ainsi chaque nœud est constitué de machines standard regroupées en grappe. Hadoop fonctionne avec de nombreux modules ou services conçus selon l&#039;idée que les pannes matérielles sont fréquentes et qu&#039;en conséquence elles doivent être gérées automatiquement par le framework. Cet aspect de redondance n&#039;est pas traité dans ce projet.&lt;br /&gt;
&lt;br /&gt;
=Architectures techniques=&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
L&#039;architecture de Kubernetes est distribuée sous forme de microservices avec plusieurs composants, chacun responsable d&#039;une certaine tâche pour contrôler le cluster et les applications qui y vivent. Tout d&#039;abord, les composants sont à séparer en deux groupes: le control plane, tête pensante du cluster, et les composants des nodes, responsables de faire fonctionner les conteneurs. Une machine est dite nœud maître dès lors qu&#039;elle est membre du control plane (elle exécute les composants du control plane, seule ou en communication avec les autres maîtres). Une machine peut à la fois être maître et exécuter des conteneurs (control plane et *Node*), ce n&#039;est toutefois pas recommandé au vu de l&#039;importance du rôle du control plane.&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-kubernetes-architecture.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://kubernetes.io/docs/concepts/overview/components&lt;br /&gt;
&lt;br /&gt;
===Control plane===&lt;br /&gt;
&lt;br /&gt;
Le &#039;&#039;&#039;control plane&#039;&#039;&#039; est un ensemble de composants responsable du bon fonctionnement du cluster. Ces composants sont présents sur chaque nœud maître du cluster. Dans le cas d&#039;un cluster à haute disponibilité (plusieurs maîtres), ces composants fonctionnent de manière distribuée, et nécessitent un load balancer.&lt;br /&gt;
&lt;br /&gt;
Le composant principal est l&#039;&#039;&#039;&#039;apiserver&#039;&#039;&#039;, qui est donc une API permettant la communication entre les différents composants. L&#039;apiserver est le seul composant avec qui les autres composants communiquent. Ensuite le &#039;&#039;&#039;controller manager&#039;&#039;&#039;, regroupe les différents contrôleurs dont le rôle est de gérer les resources qui leur corresponde (le contrôleur des *Pod* veille au bon fonctionnement des &#039;&#039;Pod&#039;&#039;, pareil pour les &#039;&#039;ReplicasSet&#039;&#039;, &#039;&#039;Endpoint&#039;&#039;, &#039;&#039;Node&#039;&#039;...). Le &#039;&#039;&#039;scheduler&#039;&#039;&#039; est responsable de l&#039;attribution des resources (machines) aux applications (&#039;&#039;Pod&#039;&#039;, &#039;&#039;Deployment&#039;&#039;...) selon les disponibilités et besoins. Enfin, &#039;&#039;&#039;etcd&#039;&#039;&#039; est une base de données distribuée de configuration qui conserve l&#039;état du cluster. C&#039;est une solution tiers et elle peut être exécutée sur un cluster à part des nœuds maître.&lt;br /&gt;
&lt;br /&gt;
===Node===&lt;br /&gt;
&lt;br /&gt;
Pour Kubernetes, un &#039;&#039;&#039;Node&#039;&#039;&#039; (ou nœud en français) est l&#039;abstraction d&#039;une machine (réelle ou virtuelle). Chaque machine représentant un &#039;&#039;Node&#039;&#039; doit faire tourner trois services: le kubelet, le kube-proxy et un environnement d&#039;exécution de conteneurs.&lt;br /&gt;
&lt;br /&gt;
Le &#039;&#039;&#039;kubelet&#039;&#039;&#039; est véritablement le responsable des conteneurs en pratique, il est le contremaître obéissant au control plane, chargé de faire appliquer ses directives. Le kubelet ordonne à l&#039;environnement d&#039;exécution de conteneurs et fait ses rapports de situation au control plane. Le &#039;&#039;&#039;kube-proxy&#039;&#039;&#039; est chargé de mettre en place les règles de réseau (iptables ou IPVS) pour veiller au bon fonctionnement notamment des &#039;&#039;Service&#039;&#039; et &#039;&#039;Endpoint&#039;&#039;. Enfin, &#039;&#039;&#039;l&#039;environnement d&#039;exécution de conteneurs&#039;&#039;&#039; peut être n&#039;importe quel solution respectant la CRI (container runtime interface) comme containerd ou CRI-O.&lt;br /&gt;
&lt;br /&gt;
Non-obligatoire mais également souvent présent est un &#039;&#039;&#039;plugin de CNI&#039;&#039;&#039; (container network interface) qui met en place le plan de réseau exigé par Kubernetes (à savoir un réseau où les &#039;&#039;Pod&#039;&#039; disposent d&#039;une adresse IP et peuvent communiquer entre eux) à ne pas confondre avec le réseau connectant les machines entre elles. On peut citer notamment Calico, Weave et celui qui est utilisé dans notre projet est Flannel (moins puissant). Parmi les addons on retrouve également un &#039;&#039;&#039;serveur DNS&#039;&#039;&#039; (nécessaire au bon fonctionnement des Services), anciennement kube-dns et maintenant plutôt coredns.&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
En ce qui concerne ELK, il ne s&#039;agit non pas d&#039;un système ou d&#039;un outil en lui-même mais de la collaboration d&#039;une multitude d&#039;outils open source ayant chacun leurs particularités et un fonctionnement qui leur est propre. Pour visualiser plus aisément l&#039;intéraction entre les différentes composantes de la stack ELK, on pourra s&#039;intéresser à l&#039;exemple suivant:&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-elk-architecture.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://fr.wikipedia.org/wiki/Logstash&lt;br /&gt;
&lt;br /&gt;
Dans l&#039;exemple ci-dessus, on distingue trois sources indépendantes: MediaWiki, des services Node.js et Hadoop. Chacune des trois sources envoie des données à une instance différente de Logstash. Les instances de Logstash ne communiquent pas entre elles, toutefois, une fois le traitement des données effectué, chaque instance envoie ses données à un nœud Elasticsearch. Dans le schéma ci-dessus, les trois nœuds font partie d&#039;un même cluster, ce qui permet donc la mise en commun de l&#039;intégralité des données pouvant ensuite être visualisées via Kibana.&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Hadoop est un environement distribué de par son stockage mais également son traitement de données. C&#039;est une suite de solution open source pour le big data. The goal is to instanciate the different kind of nodes from one of the two possible implementation below, and make them communicate to run a job on the cluster.&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-hadoop-architecture-1.png|center]]&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-hadoop-architecture-2.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://www.geeksforgeeks.org/hadoop-introduction&lt;br /&gt;
&lt;br /&gt;
=Réalisations techniques=&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
L&#039;expérience avec Kubernetes consiste avant tout à déployer un cluster Kubernetes fonctionnel, utilisable comme n&#039;importe quel autre cluster. Pour cela nous nous reposons donc tout d&#039;abord sur la dérivation de Kubernetes sur nixpkgs. Ensuite nous utilisons d&#039;autres outils comme &#039;&#039;Helm&#039;&#039; et &#039;&#039;Istio&#039;&#039; pour enrichir l&#039;expérience.&lt;br /&gt;
&lt;br /&gt;
La dérivations de Kubernetes propose la version 1.21.6, avec certains aspects de configuration qui sont cependant déprécié (notamment au niveau des ports uti lisés et des flags devenus déconseillés) car non mis à jour depuis 4 ans. La configuration de cette dérivation peut se faire de deux manière: en précisant la configuration de tous les composants (cf. partie II), ou en précisant uniquement le rôle de la machine. Avec la première approche non pouvons avoir un contrôle complet sur la configuration alors que dans le second tout est plus abstrait. En revanche la deuxième manière est plus simple et plus claire. Nous avons opté pour la seconde en ajoutant un certain nombre d&#039;options supplémentaires. &lt;br /&gt;
&lt;br /&gt;
La composition de l&#039;expérience commence avec la description des machines ainsi que leur rôle dans le cluster. Nous utilisons généralement un nœud maître et deux nœuds de travail, sachant qu&#039;il n&#039;est pas possible actuellement de déployer un cluster à haute disponibilité dont le bootstrap des certificats est automatisé dans le déploiement, autrement il faut le faire manuellement ce qui est hors de question dans le cadre d&#039;un environnement reproductible.&lt;br /&gt;
&lt;br /&gt;
Ensuite nous disposons d&#039;une fonction pour générer la configuration des machines du cluster. Cette configuration contient donc le rôle du node mais également des ajustements sur les ports et addresses IP de certains composants pour permettre la bonne communication des composants entre eux.&lt;br /&gt;
&lt;br /&gt;
Nous ajoutons également une machine supplémentaire hors-cluster, c&#039;est une serveur NFS, une solution parmis d&#039;autres pour fournir au cluster un moyen de créer des volumes (&#039;&#039;PersistentVolume&#039;&#039;) accessibles par tous les nœuds. Ce serveur est monté sur toutes les machines, ce qui permet à l&#039;expérimentateur de soit utiliser des volumes NFS, soit des volumes locaux pour plus de simplicité.&lt;br /&gt;
&lt;br /&gt;
Avec Istio nous pouvons suivre le guide d&#039;exemple présent dans la documentation pour déployer une application microservice et vérifier le bon fonctionnement du cluster.&lt;br /&gt;
&lt;br /&gt;
Cette composition est fonctionnelle pour la plateforme de nixos-test et nixos-test-driver, toutes deux reposant sur QEMU, et également sur Grid&#039;5000 où elle dévoile son vrai potentielle car les machines sont réelles et véritablement utilisables pour administrer le cluster. Elle n&#039;est pas fonctionnelle sur Docker pour des raisons propres à NixOS-Compose qui ne permettent pas de modifier les noms d&#039;hôtes (/etc/hosts), ce qui empêche la dérivation de fonctionner correctement.&lt;br /&gt;
&lt;br /&gt;
Certains éléments de bootstrap se révèlent être difficilement applicable lors du déploiement avec NixOS-Compose et nous reposons donc en partie sur un script d&#039;initialisation du cluster. Ce script est créé dans la composition et accessible dans le path. Il redémarre les composants éventuellement échoués et affiche une commande à l&#039;utilisateur permettant d&#039;ajouter des machines au cluster, cette étape n&#039;tant pas automatisable simplement (l&#039;approche est la même que kubeadm).&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;expérience ELK, une grande partie du temps a été passée à comprendre la stack ELK et ses différentes composantes. Pour réaliser une composition fonctionnelle via NixOS-Compose, nous nous sommes basés sur une composition pré-existante écrite pour NixOS-Tests. La composition a ensuite été modifiée de manière à fonctionner correctement pour les différents modes de déploiement (Docker, Grid&#039;5000).&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Un paquet hadoop existe deja et il s&#039;agit principalement d&#039;en faire sa configuration. Plusieurs configurations différentes ont été réalisées, une minimale afin de comprendre le fonctionnement général, puis une se servant de yarn afin de maitriser la multiplicité des nœuds de travail.&lt;br /&gt;
    &lt;br /&gt;
Dans la composition minimale nous avons pu mettre, comme le premier shéma de la partie précédente, créer un node de front (namenode) ainsi qu&#039;un datanode fonctionnant avec le filesystem.&lt;br /&gt;
&lt;br /&gt;
=Gestion de projet=&lt;br /&gt;
&lt;br /&gt;
Ce projet relève en partie d’un travail de recherche au vu du manque de documentation, du développement toujours en cours de l’OS et de sa faible utilisation de la part de la communauté d’utilisateurs.&lt;br /&gt;
&lt;br /&gt;
Une importante partie de ce projet repose sur la communication entre notre équipe et l’équipe Datamove pour recevoir des consignes et fournir des retours. Pour fluidifier ces échanges nous avons organisé des réunions régulières et mis en place des solutions de communication en permanence à travers des outils comme Telegram et Zoom pour les réunions.&lt;br /&gt;
&lt;br /&gt;
Nous avons mis en place deux types de réunions : des réunions quotidiennes avec un membre de l’équipe Datamove et des réunions hebdomadaires en équipe complète. Les réunions quotidiennes servent principalement à partager l’avancement et exprimer des éventuels blocages. Les réunions hebdomadaires visent davantage à faire un point global et à définir les prochaines étapes.&lt;br /&gt;
&lt;br /&gt;
==Planification==&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de la planification, il nous paraissait essentiel pour un projet comme le nôtre dans lequel énormément de temps est alloué à l&#039;apprentissage d&#039;une technologie plutôt qu&#039;à la production réelle de code de définir une roadmap.&lt;br /&gt;
&lt;br /&gt;
Cette roadmap avait pour but de planifier nos actions sur l’ensemble de la durée du projet. Nous avons fait évoluer la roadmap au fur et à mesure de notre avancement réel. Celle-ci nous a permis non seulement de travailler avec un objectif en tête mais également de partager ces objectifs avec l’équipe Datamove.&lt;br /&gt;
&lt;br /&gt;
==Organisation du travail==&lt;br /&gt;
&lt;br /&gt;
Au commencement de projet, notre objectif à tous était de se former rapidement sur Nix afin de comprendre l&#039;étendu des possibilités de l&#039;outil NixOS-Compose et de commencer à le tester.&lt;br /&gt;
&lt;br /&gt;
Notre première tâche a consisté à écrire une composition k3s compatible avec NixOS-Compose de manière à découvrir la puissance de l&#039;outil.&lt;br /&gt;
&lt;br /&gt;
Ensuite, nous sommes chacun parti sur un projet différent dans l&#039;optique de fournir trois expériences utilisateurs distinctes. La répartition des projets était la suivante :&lt;br /&gt;
* Titouan Minier Mancini : Kubernetes&lt;br /&gt;
* Corentin Humbert : Stack ELK&lt;br /&gt;
* Corentin Sueur : Hadoop&lt;br /&gt;
&lt;br /&gt;
Nous avons donc progressé chacun de notre côté sur nos projets respectifs tout en restant en contact constant de manière à éviter de passer trop temps bloqué sur une partie du projet. La communication a été impérative pour un tel projet au vu de sa complexité et du temps dont nous disposions pour le mener à terme.&lt;br /&gt;
&lt;br /&gt;
==Suivi du travail==&lt;br /&gt;
&lt;br /&gt;
En parallèle nous avons suivi la rédaction de carnets de route individuels où nous expliquons toutes nos actions dans la journée, avec un maximum de détails notamment sur les erreurs. L’objectif est de permettre aux membres de l’équipe Datamove de suivre notre avancée individuelle et d’aider sur les problèmes techniques éventuels. Ces carnet doivent permettre un maximum la reproductibilité des situations pour faciliter la correction.&lt;br /&gt;
&lt;br /&gt;
=Outils de travail=&lt;br /&gt;
&lt;br /&gt;
Au cours de notre projet, nous avons été amenés à utiliser de nombreux outils nous permettant d’échanger entre nous et avec l’équipe Datamove que ce soit pour poser des questions ou partager nos productions.&lt;br /&gt;
&lt;br /&gt;
* Communication écrite/orale :&lt;br /&gt;
** Au sein du groupe : Discord&lt;br /&gt;
** Avec l’équipe Datamove : Telegram, BBB, Zoom&lt;br /&gt;
* Échanges d’informations :&lt;br /&gt;
** Google docs, CodiMD&lt;br /&gt;
* Stockage des documents et du code produit :&lt;br /&gt;
** Dépôt GitLab&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=Métriques logiciels=&lt;br /&gt;
&lt;br /&gt;
Ce projet ne rentre pas dans le cadre d&#039;une production logicielle, la quantité de code produit est faible car le travail est avant tout un travail de compréhension et de recherche. Nous avons produit un fichier de composition pour chaque pile logicielle, ce qui correspond à une centaine de lignes chacune. Le temps était principalement accordé à l&#039;essai, l&#039;avancement à tâtons pour explorer les différentes options disponibles, et à la compréhension du fonctionnement de NixOS-Compose.&lt;br /&gt;
&lt;br /&gt;
Nous avons tous travaillé 35 heures par semaine, à l&#039;exception des première semaines en parallèle avec le projet ECOM où Titouan et Corention Humbert n&#039;étaient plus disponibles qu&#039;à hauteur de 21 à 28 heures par semaine.&lt;br /&gt;
&lt;br /&gt;
=Conclusion=&lt;br /&gt;
&lt;br /&gt;
Ce projet nous a avant tout permis de découvrir l&#039;environnement Nix et la solution NixOS-Compose, qui promet d&#039;être intéressante et un candidat potentiel à l&#039;*Infrastructure as Code* de demain. L&#039;approche est différente de ce que l&#039;on peut rencontrer avec d&#039;autres outils comme Terraform et il est enrichissant de s&#039;y pencher pour élargir sa pensée.&lt;br /&gt;
&lt;br /&gt;
Nous avons également pu travailler sur des piles logicielles que nous ne connaissions pas forcément, ce qui a aussi été très enrichissant. Nous avons appris à utiliser ces piles logicielles et à les configurer, ce qui est généralement le plus important pour ce genre de système. Nous avons appris ou réappris des technologies, et amélioré notre capacité à appréhender un système distribué, savoir d&#039;où viennent les problèmes et comment les résoudre.&lt;br /&gt;
&lt;br /&gt;
Les compositions que nous avons pu fournir à l&#039;issue du projet sont très satisfaisantes. Elles sont fonctionnelles et permettent à d&#039;autres utilisateurs d&#039;appréhender la solution NixOS-Compose. Nous avons également fourni des tutoriels et explications avec ces compositions pour exprimer des retours utilisateur au projet NixOS-Compose, ce qui, nous espérons, permettra de mettre en valeur ce beau projet.&lt;br /&gt;
&lt;br /&gt;
=Démonstration=&lt;br /&gt;
&lt;br /&gt;
La démonstration que nous proposons est de présenter le déploiement de chacune des piles logicielles.&lt;br /&gt;
&lt;br /&gt;
Vidéo de démonstration sur Kubernetes: https://www.youtube.com/watch?v=uOh8BJPj7MU&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=Rapport_Test_Infrastructures_NixOS_2021-2022&amp;diff=52459</id>
		<title>Rapport Test Infrastructures NixOS 2021-2022</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=Rapport_Test_Infrastructures_NixOS_2021-2022&amp;diff=52459"/>
		<updated>2022-03-18T09:38:07Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;=Rappel du sujet et cahier des charges=&lt;br /&gt;
&lt;br /&gt;
L’objectif est d’expérimenter et de manipuler une technologie récente : &#039;&#039;&#039;NixOS&#039;&#039;&#039; et le projet de recherche &#039;&#039;&#039;NixOS-Compose&#039;&#039;&#039;. Nix est un outil de gestion de paquets (bibliothèques, morceau logiciel offrant certaines fonctionnalités), et NixOS est un système d&#039;exploitation Linux qui utilise Nix dans son architecture. Nous parlerons plus en détails des différentes technologiques manipulées dans la prochaine partie.&lt;br /&gt;
&lt;br /&gt;
Nos expérimentations ont consistées à déployer trois projets différents : &#039;&#039;&#039;Kubernetes&#039;&#039;&#039;, &#039;&#039;&#039;ELK&#039;&#039;&#039; et &#039;&#039;&#039;Hadoop&#039;&#039;&#039; en utilisant l&#039;outil NixOS-Compose. La partie la plus importante n&#039;étant pas de déployer une version aboutie et complête pour chacun de projets mais de documenter nos expériences pour fournir des retours utilisateurs permettant l&#039;amélioration de NixOS-Compose.&lt;br /&gt;
&lt;br /&gt;
=Technologies employées=&lt;br /&gt;
&lt;br /&gt;
==Nix==&lt;br /&gt;
&lt;br /&gt;
Nix est un gestionnaire de paquets et un langage fonctionnel qui se différencie de l&#039;approche classique avec sa grande reproductibilité qu&#039;il trouve incompatible avec le &#039;&#039;Filesystem Hierarchy Standard&#039;&#039;. Il dénonce l&#039;enfer des dépendances que l&#039;on retrouve avec cette approche où l&#039;on ne peut pas déterminer les versions utilisées. Nix repose sur son &#039;&#039;&#039;store&#039;&#039;&#039;, où il stocke toutes les &#039;&#039;&#039;dérivations&#039;&#039;&#039; pour chaque paquet. Ces dérivations contiennent des informations sur toutes les dépendances (d&#039;autres &#039;&#039;dérivations&#039;&#039;) et les instructions de build. Le nom de la &#039;&#039;dérivation&#039;&#039; indique le nom du paquet et un hash qui la rend unique mais surtout qui l&#039;identifie : &#039;&#039;&#039;une même dérivation produira toujours la même sortie.&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Avec cette approche, Nix permet plusieurs choses, notamment :&lt;br /&gt;
* La reproductibilité due au déterminisme des &#039;&#039;dérivations&#039;&#039;&lt;br /&gt;
* La possibilité d&#039;utiliser plusieurs versions d&#039;un même paquet en parallèle&lt;br /&gt;
* Comme le nom de la dérivation l&#039;identifie, il est possible de mettre en cache la sortie et la récupérer sans avoir à la reconstruire&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Nixpkgs&#039;&#039;&#039; est un répertoire en ligne contenant de nombreux paquets (80 000 actuellement) construits à partir de &#039;&#039;dérivations&#039;&#039; fournies par la communauté et accessibles à tous.&lt;br /&gt;
&lt;br /&gt;
==NixOS==&lt;br /&gt;
&lt;br /&gt;
NixOS est une distribution GNU/Linux reposant sur Nix en tant que gestionnaire de paquets mais également de gestionnaire de configuration. L&#039;ensemble du système et toutes les configurations sont considérés comme des dérivations. Cela permet entre autres de faire des restorations du système à des versions précédentes simplement, chaque modification du système occasionne la création d&#039;une nouvelle version &#039;&#039;&#039;atomique&#039;&#039;&#039;. Par ailleurs, le système d&#039;exploitation hérite ainsi de la propriété &#039;&#039;&#039;déterministe&#039;&#039;&#039; et &#039;&#039;&#039;reproductible&#039;&#039;&#039; que Nix offre.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;NixOS-test&#039;&#039;&#039; est une librairie de test qui permet, à partir d&#039;un ensemble de fichiers de configuration Nix, de fournir une interface python pour manipuler ces configurations sur une/des machines virtuelles avec &#039;&#039;&#039;QEMU&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==NixOS-Compose==&lt;br /&gt;
&lt;br /&gt;
NixOS-Compose est un projet de l’équipe Datamove qui étend l’utilisation de NixOS vers d’autres supports que les machines virtuelles, comme notamment la plateforme &#039;&#039;&#039;Grid&#039;5000&#039;&#039;&#039; et des solutions de conteneurs comme &#039;&#039;&#039;Docker&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
Kubernetes est un &#039;&#039;&#039;orchestrateur de conteneurs&#039;&#039;&#039; permettant de déployer, mettre à l&#039;échelle et surveiller des applications conteneurisées sur un cluster de machines. Développé en Go et rendu open source en 2015 par Google inspiré de leur solution privée Borg, Kubernetes est maintenant l&#039;outil central du monde du &#039;&#039;&#039;DevOps&#039;&#039;&#039; dans l&#039;industrie. Il apporte une couche d&#039;abstraction au dessus d&#039;un datacenter, dont la mise en place a également été facilitée par le cloud, pour fournir une &#039;&#039;&#039;plateforme de déploiement&#039;&#039;&#039; fortement disponible aux développeurs. Kubernetes dispose également d&#039;un &#039;&#039;&#039;large écosystème&#039;&#039;&#039; d&#039;outils et plugins améliorant différents aspects de son utilisation : routage, monitoring, sécurité, gitops, déploiements (vert/bleu, canary...), serverless etc.&lt;br /&gt;
    &lt;br /&gt;
En cette qualité, Kubernetes est une plateforme de choix dans le cadre d&#039;expériences nécessitant notamment un certain nombre de services ou applications, comme dans le cas d&#039;architectures &#039;&#039;&#039;microservices&#039;&#039;&#039; par exemple. De plus, malgré ses nombreux atouts, Kubernetes est une solution souvent difficile et longue à mettre initialement en place pour cause d&#039;une &#039;&#039;&#039;configuration complexe&#039;&#039;&#039; liée à l&#039;architecture microservice de la plateforme elle-même. (Il faut reconnaître qu&#039;avec le cloud il est maintenant très simple de déployer un cluster Kubernetes, &#039;&#039;Terraform&#039;&#039; est notamment un concurrent potentiel de NixOS-Compose) &lt;br /&gt;
&lt;br /&gt;
Dans le cadre de notre projet, être en mesure de fournir un cluster Kubernetes de la taille voulue, &#039;&#039;&#039;simplement&#039;&#039;&#039;, &#039;&#039;&#039;rapidemment&#039;&#039;&#039; et de manière &#039;&#039;&#039;reproductible&#039;&#039;&#039;, est un objectif très intéressant, non seulement pour l&#039;aspect apprentissage mais également pour son utilisation dans le contextes d&#039;expériences scientifiques avec NixOS-Compose. &#039;&#039;&#039;Kubernetes est en lui même un solution qui permet une forte reproductibilité au niveau des déploiements internes, mais c&#039;est la phase de déploiement des machines et de bootstrap du cluster qui manque cette qualité, et c&#039;est là que nous nous positionnons.&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
&amp;quot;ELK&amp;quot; est l&#039;acronyme de trois projets open source : &#039;&#039;&#039;Elasticsearch&#039;&#039;&#039;, &#039;&#039;&#039;Logstash&#039;&#039;&#039; et &#039;&#039;&#039;Kibana&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
[[File:Elk_stack.png|thumb|300px|right|Intéraction des composants au sein de la stack ELK ou BELK]]&lt;br /&gt;
&lt;br /&gt;
===Elasticsearch===&lt;br /&gt;
&lt;br /&gt;
Elasticsearch est un &#039;&#039;&#039;outil de recherche et d&#039;analyse de données&#039;&#039;&#039; fonctionnant de manière &#039;&#039;&#039;distribuée&#039;&#039;&#039; et basé sur [Apache Lucene](https://lucene.apache.org/). Créé par Shay Banon en 2004, au fil des années, Elasticsearch n&#039;a cessé d&#039;évoluer et aujourd&#039;hui c&#039;est l&#039;outil de référence pour réaliser une recherche performante sur une large quantité de données.&lt;br /&gt;
&lt;br /&gt;
Technologiquement parlant, il s&#039;agit d&#039;une base de données programmée en Java et &#039;&#039;&#039;spécialisée dans la recherche et l&#039;indexation de documents&#039;&#039;&#039;. Si Elasticsearch est aussi performant c&#039;est grâce à son fonctionnement en mode distribué. La tâche de recherche est exécutée en parallèle par plusieurs nœuds Elasticsearch, ce qui améliore la réactivité du système. Elasticsearch a aussi la force d&#039;être facilement configurable et mis à l&#039;échelle.&lt;br /&gt;
&lt;br /&gt;
===Logstash===&lt;br /&gt;
&lt;br /&gt;
Logstash est un outil écrit en Java et en Ruby permettant de &#039;&#039;&#039;centraliser des traces&#039;&#039;&#039; provenant de plusieurs systèmes, de les analyser et de les stocker. Conceptuellement, Logstash peut être vu comme un &#039;&#039;&#039;&amp;quot;pipe&amp;quot;&#039;&#039;&#039; où les données rentrent d&#039;un bout, et sont traitées avant de ressortir de l&#039;autre bout. Logstash est plus qu&#039;un simple &amp;quot;pipe&amp;quot; puisqu&#039;il peut prendre une multitude de sources différentes en entrées et renvoyées les données traitées vers différentes sorties. Il sert généralement à filtrer/analyser des messages avant de les envoyer à Elasticsearch qui va, lui, se charger de les stocker et de les indexer.&lt;br /&gt;
&lt;br /&gt;
===Kibana===&lt;br /&gt;
&lt;br /&gt;
Kibana est un outil permettant la &#039;&#039;&#039;visualisation de données&#039;&#039;&#039; écrit en JavaScript est la dernière composante majeure de la stack ELK. Il est similaire à d&#039;autres outils de visualisation tel que [Grafana](https://grafana.com/), mais a la particularité d&#039;être spécialisé pour une utilisation au sein de la stack ELK. Le rôle de Kibana est donc de récupérer les données indexées par Elasticsearch et de les rendre visuellement exploitables pour un humain.&lt;br /&gt;
&lt;br /&gt;
===Beats===&lt;br /&gt;
&lt;br /&gt;
Bien que la stack ELK soit l&#039;acronyme des trois projets majeurs dont nous avons parlé précédemment, ELK est consistué d&#039;un autre projet nommé &#039;&#039;&#039;Beats&#039;&#039;&#039;. Il y a d&#039;ailleurs quelques discussions autour du renommage de la stack ELK en stack BELK pour inclure le projet Beats. Beats est une plateforme réunissant une multitude de petits &#039;&#039;&#039;outils permettant d&#039;expédier des données&#039;&#039;&#039; vers Logstash ou Elasticsearch. Chaque outil vise un type de données spécifiques. On retrouvera par exemple l&#039;outil Filebeat pour l&#039;expédition de traces systèmes, Metricbeat pour les métriques, Packetbeat pour le réseau ou encore Heartbeat pour le monitoring. Cette liste est non exhaustive, il existe plein d&#039;autres beats, chacun spécialisé pour des données de nature différente.&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Hadoop est un framework open source Java destiné à faciliter la création d&#039;applications distribuées (au niveau du stockage des données et de leur traitement) et scalables permettant aux applications de travailler avec des milliers de nœuds et des masses importantes de données. Ainsi chaque nœud est constitué de machines standard regroupées en grappe. Hadoop fonctionne avec de nombreux modules ou services conçus selon l&#039;idée que les pannes matérielles sont fréquentes et qu&#039;en conséquence elles doivent être gérées automatiquement par le framework. Cet aspect de redondance n&#039;est pas traité dans ce projet.&lt;br /&gt;
&lt;br /&gt;
=Architectures techniques=&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
L&#039;architecture de Kubernetes est distribuée sous forme de microservices avec plusieurs composants, chacun responsable d&#039;une certaine tâche pour contrôler le cluster et les applications qui y vivent. Tout d&#039;abord, les composants sont à séparer en deux groupes: le control plane, tête pensante du cluster, et les composants des nodes, responsables de faire fonctionner les conteneurs. Une machine est dite nœud maître dès lors qu&#039;elle est membre du control plane (elle exécute les composants du control plane, seule ou en communication avec les autres maîtres). Une machine peut à la fois être maître et exécuter des conteneurs (control plane et *Node*), ce n&#039;est toutefois pas recommandé au vu de l&#039;importance du rôle du control plane.&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-kubernetes-architecture.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://kubernetes.io/docs/concepts/overview/components&lt;br /&gt;
&lt;br /&gt;
===Control plane===&lt;br /&gt;
&lt;br /&gt;
Le &#039;&#039;&#039;control plane&#039;&#039;&#039; est un ensemble de composants responsable du bon fonctionnement du cluster. Ces composants sont présents sur chaque nœud maître du cluster. Dans le cas d&#039;un cluster à haute disponibilité (plusieurs maîtres), ces composants fonctionnent de manière distribuée, et nécessitent un load balancer.&lt;br /&gt;
&lt;br /&gt;
Le composant principal est l&#039;&#039;&#039;&#039;apiserver&#039;&#039;&#039;, qui est donc une API permettant la communication entre les différents composants. L&#039;apiserver est le seul composant avec qui les autres composants communiquent. Ensuite le &#039;&#039;&#039;controller manager&#039;&#039;&#039;, regroupe les différents contrôleurs dont le rôle est de gérer les resources qui leur corresponde (le contrôleur des *Pod* veille au bon fonctionnement des &#039;&#039;Pod&#039;&#039;, pareil pour les &#039;&#039;ReplicasSet&#039;&#039;, &#039;&#039;Endpoint&#039;&#039;, &#039;&#039;Node&#039;&#039;...). Le &#039;&#039;&#039;scheduler&#039;&#039;&#039; est responsable de l&#039;attribution des resources (machines) aux applications (&#039;&#039;Pod&#039;&#039;, &#039;&#039;Deployment&#039;&#039;...) selon les disponibilités et besoins. Enfin, &#039;&#039;&#039;etcd&#039;&#039;&#039; est une base de données distribuée de configuration qui conserve l&#039;état du cluster. C&#039;est une solution tiers et elle peut être exécutée sur un cluster à part des nœuds maître.&lt;br /&gt;
&lt;br /&gt;
===Node===&lt;br /&gt;
&lt;br /&gt;
Pour Kubernetes, un &#039;&#039;&#039;Node&#039;&#039;&#039; (ou nœud en français) est l&#039;abstraction d&#039;une machine (réelle ou virtuelle). Chaque machine représentant un &#039;&#039;Node&#039;&#039; doit faire tourner trois services: le kubelet, le kube-proxy et un environnement d&#039;exécution de conteneurs.&lt;br /&gt;
&lt;br /&gt;
Le &#039;&#039;&#039;kubelet&#039;&#039;&#039; est véritablement le responsable des conteneurs en pratique, il est le contremaître obéissant au control plane, chargé de faire appliquer ses directives. Le kubelet ordonne à l&#039;environnement d&#039;exécution de conteneurs et fait ses rapports de situation au control plane. Le &#039;&#039;&#039;kube-proxy&#039;&#039;&#039; est chargé de mettre en place les règles de réseau (iptables ou IPVS) pour veiller au bon fonctionnement notamment des &#039;&#039;Service&#039;&#039; et &#039;&#039;Endpoint&#039;&#039;. Enfin, &#039;&#039;&#039;l&#039;environnement d&#039;exécution de conteneurs&#039;&#039;&#039; peut être n&#039;importe quel solution respectant la CRI (container runtime interface) comme containerd ou CRI-O.&lt;br /&gt;
&lt;br /&gt;
Non-obligatoire mais également souvent présent est un &#039;&#039;&#039;plugin de CNI&#039;&#039;&#039; (container network interface) qui met en place le plan de réseau exigé par Kubernetes (à savoir un réseau où les &#039;&#039;Pod&#039;&#039; disposent d&#039;une adresse IP et peuvent communiquer entre eux) à ne pas confondre avec le réseau connectant les machines entre elles. On peut citer notamment Calico, Weave et celui qui est utilisé dans notre projet est Flannel (moins puissant). Parmi les addons on retrouve également un &#039;&#039;&#039;serveur DNS&#039;&#039;&#039; (nécessaire au bon fonctionnement des Services), anciennement kube-dns et maintenant plutôt coredns.&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
En ce qui concerne ELK, il ne s&#039;agit non pas d&#039;un système ou d&#039;un outil en lui-même mais de la collaboration d&#039;une multitude d&#039;outils open source ayant chacun leurs particularités et un fonctionnement qui leur est propre. Pour visualiser plus aisément l&#039;intéraction entre les différentes composantes de la stack ELK, on pourra s&#039;intéresser à l&#039;exemple suivant:&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-elk-architecture.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://fr.wikipedia.org/wiki/Logstash&lt;br /&gt;
&lt;br /&gt;
Dans l&#039;exemple ci-dessus, on distingue trois sources indépendantes: MediaWiki, des services Node.js et Hadoop. Chacune des trois sources envoie des données à une instance différente de Logstash. Les instances de Logstash ne communiquent pas entre elles, toutefois, une fois le traitement des données effectué, chaque instance envoie ses données à un nœud Elasticsearch. Dans le schéma ci-dessus, les trois nœuds font partie d&#039;un même cluster, ce qui permet donc la mise en commun de l&#039;intégralité des données pouvant ensuite être visualisées via Kibana.&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Hadoop est un environement distribué de par son stockage mais également son traitement de données. C&#039;est une suite de solution open source pour le big data. The goal is to instanciate the different kind of nodes from one of the two possible implementation below, and make them communicate to run a job on the cluster.&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-hadoop-architecture-1.png|center]]&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-hadoop-architecture-2.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://www.geeksforgeeks.org/hadoop-introduction&lt;br /&gt;
&lt;br /&gt;
=Réalisations techniques=&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
L&#039;expérience avec Kubernetes consiste avant tout à déployer un cluster Kubernetes fonctionnel, utilisable comme n&#039;importe quel autre cluster. Pour cela nous nous reposons donc tout d&#039;abord sur la dérivation de Kubernetes sur nixpkgs. Ensuite nous utilisons d&#039;autres outils comme &#039;&#039;Helm&#039;&#039; et &#039;&#039;Istio&#039;&#039; pour enrichir l&#039;expérience.&lt;br /&gt;
&lt;br /&gt;
La dérivations de Kubernetes propose la version 1.21.6, avec certains aspects de configuration qui sont cependant déprécié (notamment au niveau des ports uti lisés et des flags devenus déconseillés) car non mis à jour depuis 4 ans. La configuration de cette dérivation peut se faire de deux manière: en précisant la configuration de tous les composants (cf. partie II), ou en précisant uniquement le rôle de la machine. Avec la première approche non pouvons avoir un contrôle complet sur la configuration alors que dans le second tout est plus abstrait. En revanche la deuxième manière est plus simple et plus claire. Nous avons opté pour la seconde en ajoutant un certain nombre d&#039;options supplémentaires. &lt;br /&gt;
&lt;br /&gt;
La composition de l&#039;expérience commence avec la description des machines ainsi que leur rôle dans le cluster. Nous utilisons généralement un nœud maître et deux nœuds de travail, sachant qu&#039;il n&#039;est pas possible actuellement de déployer un cluster à haute disponibilité dont le bootstrap des certificats est automatisé dans le déploiement, autrement il faut le faire manuellement ce qui est hors de question dans le cadre d&#039;un environnement reproductible.&lt;br /&gt;
&lt;br /&gt;
Ensuite nous disposons d&#039;une fonction pour générer la configuration des machines du cluster. Cette configuration contient donc le rôle du node mais également des ajustements sur les ports et addresses IP de certains composants pour permettre la bonne communication des composants entre eux.&lt;br /&gt;
&lt;br /&gt;
Nous ajoutons également une machine supplémentaire hors-cluster, c&#039;est une serveur NFS, une solution parmis d&#039;autres pour fournir au cluster un moyen de créer des volumes (&#039;&#039;PersistentVolume&#039;&#039;) accessibles par tous les nœuds. Ce serveur est monté sur toutes les machines, ce qui permet à l&#039;expérimentateur de soit utiliser des volumes NFS, soit des volumes locaux pour plus de simplicité.&lt;br /&gt;
&lt;br /&gt;
Avec Istio nous pouvons suivre le guide d&#039;exemple présent dans la documentation pour déployer une application microservice et vérifier le bon fonctionnement du cluster.&lt;br /&gt;
&lt;br /&gt;
Cette composition est fonctionnelle pour la plateforme de nixos-test et nixos-test-driver, toutes deux reposant sur QEMU, et également sur Grid&#039;5000 où elle dévoile son vrai potentielle car les machines sont réelles et véritablement utilisables pour administrer le cluster. Elle n&#039;est pas fonctionnelle sur Docker pour des raisons propres à NixOS-Compose qui ne permettent pas de modifier les noms d&#039;hôtes (/etc/hosts), ce qui empêche la dérivation de fonctionner correctement.&lt;br /&gt;
&lt;br /&gt;
Certains éléments de bootstrap se révèlent être difficilement applicable lors du déploiement avec NixOS-Compose et nous reposons donc en partie sur un script d&#039;initialisation du cluster. Ce script est créé dans la composition et accessible dans le path. Il redémarre les composants éventuellement échoués et affiche une commande à l&#039;utilisateur permettant d&#039;ajouter des machines au cluster, cette étape n&#039;tant pas automatisable simplement (l&#039;approche est la même que kubeadm).&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;expérience ELK, une grande partie du temps a été passée à comprendre la stack ELK et ses différentes composantes. Pour réaliser une composition fonctionnelle via NixOS-Compose, nous nous sommes basés sur une composition pré-existante écrite pour NixOS-Tests. La composition a ensuite été modifiée de manière à fonctionner correctement pour les différents modes de déploiement (Docker, Grid&#039;5000).&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Un paquet hadoop existe deja et il s&#039;agit principalement d&#039;en faire sa configuration. Plusieurs configurations différentes ont été réalisées, une minimale afin de comprendre le fonctionnement général, puis une se servant de yarn afin de maitriser la multiplicité des nœuds de travail.&lt;br /&gt;
    &lt;br /&gt;
Dans la composition minimale nous avons pu mettre, comme le premier shéma de la partie précédente, créer un node de front (namenode) ainsi qu&#039;un datanode fonctionnant avec le filesystem.&lt;br /&gt;
&lt;br /&gt;
=Gestion de projet=&lt;br /&gt;
&lt;br /&gt;
Ce projet relève en partie d’un travail de recherche au vu du manque de documentation, du développement toujours en cours de l’OS et de sa faible utilisation de la part de la communauté d’utilisateurs.&lt;br /&gt;
&lt;br /&gt;
Une importante partie de ce projet repose sur la communication entre notre équipe et l’équipe Datamove pour recevoir des consignes et fournir des retours. Pour fluidifier ces échanges nous avons organisé des réunions régulières et mis en place des solutions de communication en permanence à travers des outils comme Telegram et Zoom pour les réunions.&lt;br /&gt;
&lt;br /&gt;
Nous avons mis en place deux types de réunions : des réunions quotidiennes avec un membre de l’équipe Datamove et des réunions hebdomadaires en équipe complète. Les réunions quotidiennes servent principalement à partager l’avancement et exprimer des éventuels blocages. Les réunions hebdomadaires visent davantage à faire un point global et à définir les prochaines étapes.&lt;br /&gt;
&lt;br /&gt;
==Planification==&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de la planification, il nous paraissait essentiel pour un projet comme le nôtre dans lequel énormément de temps est alloué à l&#039;apprentissage d&#039;une technologie plutôt qu&#039;à la production réelle de code de définir une roadmap.&lt;br /&gt;
&lt;br /&gt;
Cette roadmap avait pour but de planifier nos actions sur l’ensemble de la durée du projet. Nous avons fait évoluer la roadmap au fur et à mesure de notre avancement réel. Celle-ci nous a permis non seulement de travailler avec un objectif en tête mais également de partager ces objectifs avec l’équipe Datamove.&lt;br /&gt;
&lt;br /&gt;
==Organisation du travail==&lt;br /&gt;
&lt;br /&gt;
Au commencement de projet, notre objectif à tous était de se former rapidement sur Nix afin de comprendre l&#039;étendu des possibilités de l&#039;outil NixOS-Compose et de commencer à le tester.&lt;br /&gt;
&lt;br /&gt;
Notre première tâche a consisté à écrire une composition k3s compatible avec NixOS-Compose de manière à découvrir la puissance de l&#039;outil.&lt;br /&gt;
&lt;br /&gt;
Ensuite, nous sommes chacun parti sur un projet différent dans l&#039;optique de fournir trois expériences utilisateurs distinctes. La répartition des projets était la suivante :&lt;br /&gt;
* Titouan Minier Mancini : Kubernetes&lt;br /&gt;
* Corentin Humbert : Stack ELK&lt;br /&gt;
* Corentin Sueur : Hadoop&lt;br /&gt;
&lt;br /&gt;
Nous avons donc progressé chacun de notre côté sur nos projets respectifs tout en restant en contact constant de manière à éviter de passer trop temps bloqué sur une partie du projet. La communication a été impérative pour un tel projet au vu de sa complexité et du temps dont nous disposions pour le mener à terme.&lt;br /&gt;
&lt;br /&gt;
==Suivi du travail==&lt;br /&gt;
&lt;br /&gt;
En parallèle nous avons suivi la rédaction de carnets de route individuels où nous expliquons toutes nos actions dans la journée, avec un maximum de détails notamment sur les erreurs. L’objectif est de permettre aux membres de l’équipe Datamove de suivre notre avancée individuelle et d’aider sur les problèmes techniques éventuels. Ces carnet doivent permettre un maximum la reproductibilité des situations pour faciliter la correction.&lt;br /&gt;
&lt;br /&gt;
=Outils de travail=&lt;br /&gt;
&lt;br /&gt;
Au cours de notre projet, nous avons été amenés à utiliser de nombreux outils nous permettant d’échanger entre nous et avec l’équipe Datamove que ce soit pour poser des questions ou partager nos productions.&lt;br /&gt;
&lt;br /&gt;
* Communication écrite/orale :&lt;br /&gt;
** Au sein du groupe : Discord&lt;br /&gt;
** Avec l’équipe Datamove : Telegram, BBB, Zoom&lt;br /&gt;
* Échanges d’informations :&lt;br /&gt;
** Google docs, CodiMD&lt;br /&gt;
* Stockage des documents et du code produit :&lt;br /&gt;
** Dépôt GitLab&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=Métriques logiciels=&lt;br /&gt;
&lt;br /&gt;
Ce projet ne rentre pas dans le cadre d&#039;une production logicielle, la quantité de code produit est faible car le travail est avant tout un travail de compréhension et de recherche. Nous avons produit un fichier de composition pour chaque pile logicielle, ce qui correspond à une centaine de lignes chacune. Le temps était principalement accordé à l&#039;essai, l&#039;avancement à tâtons pour explorer les différentes options disponibles, et à la compréhension du fonctionnement de NixOS-Compose.&lt;br /&gt;
&lt;br /&gt;
Nous avons tous travaillé 35 heures par semaine, à l&#039;exception des première semaines en parallèle avec le projet ECOM où Titouan et Corention Humbert n&#039;étaient plus disponibles qu&#039;à hauteur de 21 à 28 heures par semaine.&lt;br /&gt;
&lt;br /&gt;
=Conclusion=&lt;br /&gt;
&lt;br /&gt;
Ce projet nous a avant tout permis de découvrir l&#039;environnement Nix et la solution NixOS-Compose, qui promet d&#039;être intéressante et un candidat potentiel à l&#039;*Infrastructure as Code* de demain. L&#039;approche est différente de ce que l&#039;on peut rencontrer avec d&#039;autres outils comme Terraform et il est enrichissant de s&#039;y pencher pour élargir sa pensée.&lt;br /&gt;
&lt;br /&gt;
Nous avons également pu travailler sur des piles logicielles que nous ne connaissions pas forcément, ce qui a aussi été très enrichissant. Nous avons appris à utiliser ces piles logicielles et à les configurer, ce qui est généralement le plus important pour ce genre de système. Nous avons appris ou réappris des technologies, et amélioré notre capacité à appréhender un système distribué, savoir d&#039;où viennent les problèmes et comment les résoudre.&lt;br /&gt;
&lt;br /&gt;
Les compositions que nous avons pu fournir à l&#039;issue du projet sont très satisfaisantes. Elles sont fonctionnelles et permettent à d&#039;autres utilisateurs d&#039;appréhender la solution NixOS-Compose. Nous avons également fourni des tutoriels et explications avec ces compositions pour exprimer des retours utilisateur au projet NixOS-Compose, ce qui, nous espérons, permettra de mettre en valeur ce beau projet.&lt;br /&gt;
&lt;br /&gt;
=Démonstration=&lt;br /&gt;
&lt;br /&gt;
La démonstration que nous proposons est de présenter le déploiement de chacune des piles logicielles.&lt;br /&gt;
&lt;br /&gt;
Vidéo de démonstration sur Kubernetes: https://www.youtube.com/watch?v=uOh8BJPj7MU&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=Rapport_Test_Infrastructures_NixOS_2021-2022&amp;diff=52458</id>
		<title>Rapport Test Infrastructures NixOS 2021-2022</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=Rapport_Test_Infrastructures_NixOS_2021-2022&amp;diff=52458"/>
		<updated>2022-03-18T09:37:35Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;=Rappel du sujet et cahier des charges=&lt;br /&gt;
&lt;br /&gt;
L’objectif est d’expérimenter et de manipuler une technologie récente : &#039;&#039;&#039;NixOS&#039;&#039;&#039; et le projet de recherche &#039;&#039;&#039;NixOS-Compose&#039;&#039;&#039;. Nix est un outil de gestion de paquets (bibliothèques, morceau logiciel offrant certaines fonctionnalités), et NixOS est un système d&#039;exploitation Linux qui utilise Nix dans son architecture. Nous parlerons plus en détails des différentes technologiques manipulées dans la prochaine partie.&lt;br /&gt;
&lt;br /&gt;
Nos expérimentations ont consistées à déployer trois projets différents : &#039;&#039;&#039;Kubernetes&#039;&#039;&#039;, &#039;&#039;&#039;ELK&#039;&#039;&#039; et &#039;&#039;&#039;Hadoop&#039;&#039;&#039; en utilisant l&#039;outil NixOS-Compose. La partie la plus importante n&#039;étant pas de déployer une version aboutie et complête pour chacun de projets mais de documenter nos expériences pour fournir des retours utilisateurs permettant l&#039;amélioration de NixOS-Compose.&lt;br /&gt;
&lt;br /&gt;
=Technologies employées=&lt;br /&gt;
&lt;br /&gt;
==Nix==&lt;br /&gt;
&lt;br /&gt;
Nix est un gestionnaire de paquets et un langage fonctionnel qui se différencie de l&#039;approche classique avec sa grande reproductibilité qu&#039;il trouve incompatible avec le &#039;&#039;Filesystem Hierarchy Standard&#039;&#039;. Il dénonce l&#039;enfer des dépendances que l&#039;on retrouve avec cette approche où l&#039;on ne peut pas déterminer les versions utilisées. Nix repose sur son &#039;&#039;&#039;store&#039;&#039;&#039;, où il stocke toutes les &#039;&#039;&#039;dérivations&#039;&#039;&#039; pour chaque paquet. Ces dérivations contiennent des informations sur toutes les dépendances (d&#039;autres &#039;&#039;dérivations&#039;&#039;) et les instructions de build. Le nom de la &#039;&#039;dérivation&#039;&#039; indique le nom du paquet et un hash qui la rend unique mais surtout qui l&#039;identifie : &#039;&#039;&#039;une même dérivation produira toujours la même sortie.&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Avec cette approche, Nix permet plusieurs choses, notamment :&lt;br /&gt;
* La reproductibilité due au déterminisme des &#039;&#039;dérivations&#039;&#039;&lt;br /&gt;
* La possibilité d&#039;utiliser plusieurs versions d&#039;un même paquet en parallèle&lt;br /&gt;
* Comme le nom de la dérivation l&#039;identifie, il est possible de mettre en cache la sortie et la récupérer sans avoir à la reconstruire&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Nixpkgs&#039;&#039;&#039; est un répertoire en ligne contenant de nombreux paquets (80 000 actuellement) construits à partir de &#039;&#039;dérivations&#039;&#039; fournies par la communauté et accessibles à tous.&lt;br /&gt;
&lt;br /&gt;
==NixOS==&lt;br /&gt;
&lt;br /&gt;
NixOS est une distribution GNU/Linux reposant sur Nix en tant que gestionnaire de paquets mais également de gestionnaire de configuration. L&#039;ensemble du système et toutes les configurations sont considérés comme des dérivations. Cela permet entre autres de faire des restorations du système à des versions précédentes simplement, chaque modification du système occasionne la création d&#039;une nouvelle version &#039;&#039;&#039;atomique&#039;&#039;&#039;. Par ailleurs, le système d&#039;exploitation hérite ainsi de la propriété &#039;&#039;&#039;déterministe&#039;&#039;&#039; et &#039;&#039;&#039;reproductible&#039;&#039;&#039; que Nix offre.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;NixOS-test&#039;&#039;&#039; est une librairie de test qui permet, à partir d&#039;un ensemble de fichiers de configuration Nix, de fournir une interface python pour manipuler ces configurations sur une/des machines virtuelles avec &#039;&#039;&#039;QEMU&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==NixOS-Compose==&lt;br /&gt;
&lt;br /&gt;
NixOS-Compose est un projet de l’équipe Datamove qui étend l’utilisation de NixOS vers d’autres supports que les machines virtuelles, comme notamment la plateforme &#039;&#039;&#039;Grid&#039;5000&#039;&#039;&#039; et des solutions de conteneurs comme &#039;&#039;&#039;Docker&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
Kubernetes est un &#039;&#039;&#039;orchestrateur de conteneurs&#039;&#039;&#039; permettant de déployer, mettre à l&#039;échelle et surveiller des applications conteneurisées sur un cluster de machines. Développé en Go et rendu open source en 2015 par Google inspiré de leur solution privée Borg, Kubernetes est maintenant l&#039;outil central du monde du &#039;&#039;&#039;DevOps&#039;&#039;&#039; dans l&#039;industrie. Il apporte une couche d&#039;abstraction au dessus d&#039;un datacenter, dont la mise en place a également été facilitée par le cloud, pour fournir une &#039;&#039;&#039;plateforme de déploiement&#039;&#039;&#039; fortement disponible aux développeurs. Kubernetes dispose également d&#039;un &#039;&#039;&#039;large écosystème&#039;&#039;&#039; d&#039;outils et plugins améliorant différents aspects de son utilisation : routage, monitoring, sécurité, gitops, déploiements (vert/bleu, canary...), serverless etc.&lt;br /&gt;
    &lt;br /&gt;
En cette qualité, Kubernetes est une plateforme de choix dans le cadre d&#039;expériences nécessitant notamment un certain nombre de services ou applications, comme dans le cas d&#039;architectures &#039;&#039;&#039;microservices&#039;&#039;&#039; par exemple. De plus, malgré ses nombreux atouts, Kubernetes est une solution souvent difficile et longue à mettre initialement en place pour cause d&#039;une &#039;&#039;&#039;configuration complexe&#039;&#039;&#039; liée à l&#039;architecture microservice de la plateforme elle-même. (Il faut reconnaître qu&#039;avec le cloud il est maintenant très simple de déployer un cluster Kubernetes, &#039;&#039;Terraform&#039;&#039; est notamment un concurrent potentiel de NixOS-Compose) &lt;br /&gt;
&lt;br /&gt;
Dans le cadre de notre projet, être en mesure de fournir un cluster Kubernetes de la taille voulue, &#039;&#039;&#039;simplement&#039;&#039;&#039;, &#039;&#039;&#039;rapidemment&#039;&#039;&#039; et de manière &#039;&#039;&#039;reproductible&#039;&#039;&#039;, est un objectif très intéressant, non seulement pour l&#039;aspect apprentissage mais également pour son utilisation dans le contextes d&#039;expériences scientifiques avec NixOS-Compose. &#039;&#039;&#039;Kubernetes est en lui même un solution qui permet une forte reproductibilité au niveau des déploiements internes, mais c&#039;est la phase de déploiement des machines et de bootstrap du cluster qui manque cette qualité, et c&#039;est là que nous nous positionnons.&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
&amp;quot;ELK&amp;quot; est l&#039;acronyme de trois projets open source : &#039;&#039;&#039;Elasticsearch&#039;&#039;&#039;, &#039;&#039;&#039;Logstash&#039;&#039;&#039; et &#039;&#039;&#039;Kibana&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
[[File:Elk_stack.png|right|Intéraction des composants au sein de la stack ELK ou BELK]]&lt;br /&gt;
&lt;br /&gt;
===Elasticsearch===&lt;br /&gt;
&lt;br /&gt;
Elasticsearch est un &#039;&#039;&#039;outil de recherche et d&#039;analyse de données&#039;&#039;&#039; fonctionnant de manière &#039;&#039;&#039;distribuée&#039;&#039;&#039; et basé sur [Apache Lucene](https://lucene.apache.org/). Créé par Shay Banon en 2004, au fil des années, Elasticsearch n&#039;a cessé d&#039;évoluer et aujourd&#039;hui c&#039;est l&#039;outil de référence pour réaliser une recherche performante sur une large quantité de données.&lt;br /&gt;
&lt;br /&gt;
Technologiquement parlant, il s&#039;agit d&#039;une base de données programmée en Java et &#039;&#039;&#039;spécialisée dans la recherche et l&#039;indexation de documents&#039;&#039;&#039;. Si Elasticsearch est aussi performant c&#039;est grâce à son fonctionnement en mode distribué. La tâche de recherche est exécutée en parallèle par plusieurs nœuds Elasticsearch, ce qui améliore la réactivité du système. Elasticsearch a aussi la force d&#039;être facilement configurable et mis à l&#039;échelle.&lt;br /&gt;
&lt;br /&gt;
===Logstash===&lt;br /&gt;
&lt;br /&gt;
Logstash est un outil écrit en Java et en Ruby permettant de &#039;&#039;&#039;centraliser des traces&#039;&#039;&#039; provenant de plusieurs systèmes, de les analyser et de les stocker. Conceptuellement, Logstash peut être vu comme un &#039;&#039;&#039;&amp;quot;pipe&amp;quot;&#039;&#039;&#039; où les données rentrent d&#039;un bout, et sont traitées avant de ressortir de l&#039;autre bout. Logstash est plus qu&#039;un simple &amp;quot;pipe&amp;quot; puisqu&#039;il peut prendre une multitude de sources différentes en entrées et renvoyées les données traitées vers différentes sorties. Il sert généralement à filtrer/analyser des messages avant de les envoyer à Elasticsearch qui va, lui, se charger de les stocker et de les indexer.&lt;br /&gt;
&lt;br /&gt;
===Kibana===&lt;br /&gt;
&lt;br /&gt;
Kibana est un outil permettant la &#039;&#039;&#039;visualisation de données&#039;&#039;&#039; écrit en JavaScript est la dernière composante majeure de la stack ELK. Il est similaire à d&#039;autres outils de visualisation tel que [Grafana](https://grafana.com/), mais a la particularité d&#039;être spécialisé pour une utilisation au sein de la stack ELK. Le rôle de Kibana est donc de récupérer les données indexées par Elasticsearch et de les rendre visuellement exploitables pour un humain.&lt;br /&gt;
&lt;br /&gt;
===Beats===&lt;br /&gt;
&lt;br /&gt;
Bien que la stack ELK soit l&#039;acronyme des trois projets majeurs dont nous avons parlé précédemment, ELK est consistué d&#039;un autre projet nommé &#039;&#039;&#039;Beats&#039;&#039;&#039;. Il y a d&#039;ailleurs quelques discussions autour du renommage de la stack ELK en stack BELK pour inclure le projet Beats. Beats est une plateforme réunissant une multitude de petits &#039;&#039;&#039;outils permettant d&#039;expédier des données&#039;&#039;&#039; vers Logstash ou Elasticsearch. Chaque outil vise un type de données spécifiques. On retrouvera par exemple l&#039;outil Filebeat pour l&#039;expédition de traces systèmes, Metricbeat pour les métriques, Packetbeat pour le réseau ou encore Heartbeat pour le monitoring. Cette liste est non exhaustive, il existe plein d&#039;autres beats, chacun spécialisé pour des données de nature différente.&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Hadoop est un framework open source Java destiné à faciliter la création d&#039;applications distribuées (au niveau du stockage des données et de leur traitement) et scalables permettant aux applications de travailler avec des milliers de nœuds et des masses importantes de données. Ainsi chaque nœud est constitué de machines standard regroupées en grappe. Hadoop fonctionne avec de nombreux modules ou services conçus selon l&#039;idée que les pannes matérielles sont fréquentes et qu&#039;en conséquence elles doivent être gérées automatiquement par le framework. Cet aspect de redondance n&#039;est pas traité dans ce projet.&lt;br /&gt;
&lt;br /&gt;
=Architectures techniques=&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
L&#039;architecture de Kubernetes est distribuée sous forme de microservices avec plusieurs composants, chacun responsable d&#039;une certaine tâche pour contrôler le cluster et les applications qui y vivent. Tout d&#039;abord, les composants sont à séparer en deux groupes: le control plane, tête pensante du cluster, et les composants des nodes, responsables de faire fonctionner les conteneurs. Une machine est dite nœud maître dès lors qu&#039;elle est membre du control plane (elle exécute les composants du control plane, seule ou en communication avec les autres maîtres). Une machine peut à la fois être maître et exécuter des conteneurs (control plane et *Node*), ce n&#039;est toutefois pas recommandé au vu de l&#039;importance du rôle du control plane.&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-kubernetes-architecture.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://kubernetes.io/docs/concepts/overview/components&lt;br /&gt;
&lt;br /&gt;
===Control plane===&lt;br /&gt;
&lt;br /&gt;
Le &#039;&#039;&#039;control plane&#039;&#039;&#039; est un ensemble de composants responsable du bon fonctionnement du cluster. Ces composants sont présents sur chaque nœud maître du cluster. Dans le cas d&#039;un cluster à haute disponibilité (plusieurs maîtres), ces composants fonctionnent de manière distribuée, et nécessitent un load balancer.&lt;br /&gt;
&lt;br /&gt;
Le composant principal est l&#039;&#039;&#039;&#039;apiserver&#039;&#039;&#039;, qui est donc une API permettant la communication entre les différents composants. L&#039;apiserver est le seul composant avec qui les autres composants communiquent. Ensuite le &#039;&#039;&#039;controller manager&#039;&#039;&#039;, regroupe les différents contrôleurs dont le rôle est de gérer les resources qui leur corresponde (le contrôleur des *Pod* veille au bon fonctionnement des &#039;&#039;Pod&#039;&#039;, pareil pour les &#039;&#039;ReplicasSet&#039;&#039;, &#039;&#039;Endpoint&#039;&#039;, &#039;&#039;Node&#039;&#039;...). Le &#039;&#039;&#039;scheduler&#039;&#039;&#039; est responsable de l&#039;attribution des resources (machines) aux applications (&#039;&#039;Pod&#039;&#039;, &#039;&#039;Deployment&#039;&#039;...) selon les disponibilités et besoins. Enfin, &#039;&#039;&#039;etcd&#039;&#039;&#039; est une base de données distribuée de configuration qui conserve l&#039;état du cluster. C&#039;est une solution tiers et elle peut être exécutée sur un cluster à part des nœuds maître.&lt;br /&gt;
&lt;br /&gt;
===Node===&lt;br /&gt;
&lt;br /&gt;
Pour Kubernetes, un &#039;&#039;&#039;Node&#039;&#039;&#039; (ou nœud en français) est l&#039;abstraction d&#039;une machine (réelle ou virtuelle). Chaque machine représentant un &#039;&#039;Node&#039;&#039; doit faire tourner trois services: le kubelet, le kube-proxy et un environnement d&#039;exécution de conteneurs.&lt;br /&gt;
&lt;br /&gt;
Le &#039;&#039;&#039;kubelet&#039;&#039;&#039; est véritablement le responsable des conteneurs en pratique, il est le contremaître obéissant au control plane, chargé de faire appliquer ses directives. Le kubelet ordonne à l&#039;environnement d&#039;exécution de conteneurs et fait ses rapports de situation au control plane. Le &#039;&#039;&#039;kube-proxy&#039;&#039;&#039; est chargé de mettre en place les règles de réseau (iptables ou IPVS) pour veiller au bon fonctionnement notamment des &#039;&#039;Service&#039;&#039; et &#039;&#039;Endpoint&#039;&#039;. Enfin, &#039;&#039;&#039;l&#039;environnement d&#039;exécution de conteneurs&#039;&#039;&#039; peut être n&#039;importe quel solution respectant la CRI (container runtime interface) comme containerd ou CRI-O.&lt;br /&gt;
&lt;br /&gt;
Non-obligatoire mais également souvent présent est un &#039;&#039;&#039;plugin de CNI&#039;&#039;&#039; (container network interface) qui met en place le plan de réseau exigé par Kubernetes (à savoir un réseau où les &#039;&#039;Pod&#039;&#039; disposent d&#039;une adresse IP et peuvent communiquer entre eux) à ne pas confondre avec le réseau connectant les machines entre elles. On peut citer notamment Calico, Weave et celui qui est utilisé dans notre projet est Flannel (moins puissant). Parmi les addons on retrouve également un &#039;&#039;&#039;serveur DNS&#039;&#039;&#039; (nécessaire au bon fonctionnement des Services), anciennement kube-dns et maintenant plutôt coredns.&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
En ce qui concerne ELK, il ne s&#039;agit non pas d&#039;un système ou d&#039;un outil en lui-même mais de la collaboration d&#039;une multitude d&#039;outils open source ayant chacun leurs particularités et un fonctionnement qui leur est propre. Pour visualiser plus aisément l&#039;intéraction entre les différentes composantes de la stack ELK, on pourra s&#039;intéresser à l&#039;exemple suivant:&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-elk-architecture.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://fr.wikipedia.org/wiki/Logstash&lt;br /&gt;
&lt;br /&gt;
Dans l&#039;exemple ci-dessus, on distingue trois sources indépendantes: MediaWiki, des services Node.js et Hadoop. Chacune des trois sources envoie des données à une instance différente de Logstash. Les instances de Logstash ne communiquent pas entre elles, toutefois, une fois le traitement des données effectué, chaque instance envoie ses données à un nœud Elasticsearch. Dans le schéma ci-dessus, les trois nœuds font partie d&#039;un même cluster, ce qui permet donc la mise en commun de l&#039;intégralité des données pouvant ensuite être visualisées via Kibana.&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Hadoop est un environement distribué de par son stockage mais également son traitement de données. C&#039;est une suite de solution open source pour le big data. The goal is to instanciate the different kind of nodes from one of the two possible implementation below, and make them communicate to run a job on the cluster.&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-hadoop-architecture-1.png|center]]&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-hadoop-architecture-2.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://www.geeksforgeeks.org/hadoop-introduction&lt;br /&gt;
&lt;br /&gt;
=Réalisations techniques=&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
L&#039;expérience avec Kubernetes consiste avant tout à déployer un cluster Kubernetes fonctionnel, utilisable comme n&#039;importe quel autre cluster. Pour cela nous nous reposons donc tout d&#039;abord sur la dérivation de Kubernetes sur nixpkgs. Ensuite nous utilisons d&#039;autres outils comme &#039;&#039;Helm&#039;&#039; et &#039;&#039;Istio&#039;&#039; pour enrichir l&#039;expérience.&lt;br /&gt;
&lt;br /&gt;
La dérivations de Kubernetes propose la version 1.21.6, avec certains aspects de configuration qui sont cependant déprécié (notamment au niveau des ports uti lisés et des flags devenus déconseillés) car non mis à jour depuis 4 ans. La configuration de cette dérivation peut se faire de deux manière: en précisant la configuration de tous les composants (cf. partie II), ou en précisant uniquement le rôle de la machine. Avec la première approche non pouvons avoir un contrôle complet sur la configuration alors que dans le second tout est plus abstrait. En revanche la deuxième manière est plus simple et plus claire. Nous avons opté pour la seconde en ajoutant un certain nombre d&#039;options supplémentaires. &lt;br /&gt;
&lt;br /&gt;
La composition de l&#039;expérience commence avec la description des machines ainsi que leur rôle dans le cluster. Nous utilisons généralement un nœud maître et deux nœuds de travail, sachant qu&#039;il n&#039;est pas possible actuellement de déployer un cluster à haute disponibilité dont le bootstrap des certificats est automatisé dans le déploiement, autrement il faut le faire manuellement ce qui est hors de question dans le cadre d&#039;un environnement reproductible.&lt;br /&gt;
&lt;br /&gt;
Ensuite nous disposons d&#039;une fonction pour générer la configuration des machines du cluster. Cette configuration contient donc le rôle du node mais également des ajustements sur les ports et addresses IP de certains composants pour permettre la bonne communication des composants entre eux.&lt;br /&gt;
&lt;br /&gt;
Nous ajoutons également une machine supplémentaire hors-cluster, c&#039;est une serveur NFS, une solution parmis d&#039;autres pour fournir au cluster un moyen de créer des volumes (&#039;&#039;PersistentVolume&#039;&#039;) accessibles par tous les nœuds. Ce serveur est monté sur toutes les machines, ce qui permet à l&#039;expérimentateur de soit utiliser des volumes NFS, soit des volumes locaux pour plus de simplicité.&lt;br /&gt;
&lt;br /&gt;
Avec Istio nous pouvons suivre le guide d&#039;exemple présent dans la documentation pour déployer une application microservice et vérifier le bon fonctionnement du cluster.&lt;br /&gt;
&lt;br /&gt;
Cette composition est fonctionnelle pour la plateforme de nixos-test et nixos-test-driver, toutes deux reposant sur QEMU, et également sur Grid&#039;5000 où elle dévoile son vrai potentielle car les machines sont réelles et véritablement utilisables pour administrer le cluster. Elle n&#039;est pas fonctionnelle sur Docker pour des raisons propres à NixOS-Compose qui ne permettent pas de modifier les noms d&#039;hôtes (/etc/hosts), ce qui empêche la dérivation de fonctionner correctement.&lt;br /&gt;
&lt;br /&gt;
Certains éléments de bootstrap se révèlent être difficilement applicable lors du déploiement avec NixOS-Compose et nous reposons donc en partie sur un script d&#039;initialisation du cluster. Ce script est créé dans la composition et accessible dans le path. Il redémarre les composants éventuellement échoués et affiche une commande à l&#039;utilisateur permettant d&#039;ajouter des machines au cluster, cette étape n&#039;tant pas automatisable simplement (l&#039;approche est la même que kubeadm).&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;expérience ELK, une grande partie du temps a été passée à comprendre la stack ELK et ses différentes composantes. Pour réaliser une composition fonctionnelle via NixOS-Compose, nous nous sommes basés sur une composition pré-existante écrite pour NixOS-Tests. La composition a ensuite été modifiée de manière à fonctionner correctement pour les différents modes de déploiement (Docker, Grid&#039;5000).&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Un paquet hadoop existe deja et il s&#039;agit principalement d&#039;en faire sa configuration. Plusieurs configurations différentes ont été réalisées, une minimale afin de comprendre le fonctionnement général, puis une se servant de yarn afin de maitriser la multiplicité des nœuds de travail.&lt;br /&gt;
    &lt;br /&gt;
Dans la composition minimale nous avons pu mettre, comme le premier shéma de la partie précédente, créer un node de front (namenode) ainsi qu&#039;un datanode fonctionnant avec le filesystem.&lt;br /&gt;
&lt;br /&gt;
=Gestion de projet=&lt;br /&gt;
&lt;br /&gt;
Ce projet relève en partie d’un travail de recherche au vu du manque de documentation, du développement toujours en cours de l’OS et de sa faible utilisation de la part de la communauté d’utilisateurs.&lt;br /&gt;
&lt;br /&gt;
Une importante partie de ce projet repose sur la communication entre notre équipe et l’équipe Datamove pour recevoir des consignes et fournir des retours. Pour fluidifier ces échanges nous avons organisé des réunions régulières et mis en place des solutions de communication en permanence à travers des outils comme Telegram et Zoom pour les réunions.&lt;br /&gt;
&lt;br /&gt;
Nous avons mis en place deux types de réunions : des réunions quotidiennes avec un membre de l’équipe Datamove et des réunions hebdomadaires en équipe complète. Les réunions quotidiennes servent principalement à partager l’avancement et exprimer des éventuels blocages. Les réunions hebdomadaires visent davantage à faire un point global et à définir les prochaines étapes.&lt;br /&gt;
&lt;br /&gt;
==Planification==&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de la planification, il nous paraissait essentiel pour un projet comme le nôtre dans lequel énormément de temps est alloué à l&#039;apprentissage d&#039;une technologie plutôt qu&#039;à la production réelle de code de définir une roadmap.&lt;br /&gt;
&lt;br /&gt;
Cette roadmap avait pour but de planifier nos actions sur l’ensemble de la durée du projet. Nous avons fait évoluer la roadmap au fur et à mesure de notre avancement réel. Celle-ci nous a permis non seulement de travailler avec un objectif en tête mais également de partager ces objectifs avec l’équipe Datamove.&lt;br /&gt;
&lt;br /&gt;
==Organisation du travail==&lt;br /&gt;
&lt;br /&gt;
Au commencement de projet, notre objectif à tous était de se former rapidement sur Nix afin de comprendre l&#039;étendu des possibilités de l&#039;outil NixOS-Compose et de commencer à le tester.&lt;br /&gt;
&lt;br /&gt;
Notre première tâche a consisté à écrire une composition k3s compatible avec NixOS-Compose de manière à découvrir la puissance de l&#039;outil.&lt;br /&gt;
&lt;br /&gt;
Ensuite, nous sommes chacun parti sur un projet différent dans l&#039;optique de fournir trois expériences utilisateurs distinctes. La répartition des projets était la suivante :&lt;br /&gt;
* Titouan Minier Mancini : Kubernetes&lt;br /&gt;
* Corentin Humbert : Stack ELK&lt;br /&gt;
* Corentin Sueur : Hadoop&lt;br /&gt;
&lt;br /&gt;
Nous avons donc progressé chacun de notre côté sur nos projets respectifs tout en restant en contact constant de manière à éviter de passer trop temps bloqué sur une partie du projet. La communication a été impérative pour un tel projet au vu de sa complexité et du temps dont nous disposions pour le mener à terme.&lt;br /&gt;
&lt;br /&gt;
==Suivi du travail==&lt;br /&gt;
&lt;br /&gt;
En parallèle nous avons suivi la rédaction de carnets de route individuels où nous expliquons toutes nos actions dans la journée, avec un maximum de détails notamment sur les erreurs. L’objectif est de permettre aux membres de l’équipe Datamove de suivre notre avancée individuelle et d’aider sur les problèmes techniques éventuels. Ces carnet doivent permettre un maximum la reproductibilité des situations pour faciliter la correction.&lt;br /&gt;
&lt;br /&gt;
=Outils de travail=&lt;br /&gt;
&lt;br /&gt;
Au cours de notre projet, nous avons été amenés à utiliser de nombreux outils nous permettant d’échanger entre nous et avec l’équipe Datamove que ce soit pour poser des questions ou partager nos productions.&lt;br /&gt;
&lt;br /&gt;
* Communication écrite/orale :&lt;br /&gt;
** Au sein du groupe : Discord&lt;br /&gt;
** Avec l’équipe Datamove : Telegram, BBB, Zoom&lt;br /&gt;
* Échanges d’informations :&lt;br /&gt;
** Google docs, CodiMD&lt;br /&gt;
* Stockage des documents et du code produit :&lt;br /&gt;
** Dépôt GitLab&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=Métriques logiciels=&lt;br /&gt;
&lt;br /&gt;
Ce projet ne rentre pas dans le cadre d&#039;une production logicielle, la quantité de code produit est faible car le travail est avant tout un travail de compréhension et de recherche. Nous avons produit un fichier de composition pour chaque pile logicielle, ce qui correspond à une centaine de lignes chacune. Le temps était principalement accordé à l&#039;essai, l&#039;avancement à tâtons pour explorer les différentes options disponibles, et à la compréhension du fonctionnement de NixOS-Compose.&lt;br /&gt;
&lt;br /&gt;
Nous avons tous travaillé 35 heures par semaine, à l&#039;exception des première semaines en parallèle avec le projet ECOM où Titouan et Corention Humbert n&#039;étaient plus disponibles qu&#039;à hauteur de 21 à 28 heures par semaine.&lt;br /&gt;
&lt;br /&gt;
=Conclusion=&lt;br /&gt;
&lt;br /&gt;
Ce projet nous a avant tout permis de découvrir l&#039;environnement Nix et la solution NixOS-Compose, qui promet d&#039;être intéressante et un candidat potentiel à l&#039;*Infrastructure as Code* de demain. L&#039;approche est différente de ce que l&#039;on peut rencontrer avec d&#039;autres outils comme Terraform et il est enrichissant de s&#039;y pencher pour élargir sa pensée.&lt;br /&gt;
&lt;br /&gt;
Nous avons également pu travailler sur des piles logicielles que nous ne connaissions pas forcément, ce qui a aussi été très enrichissant. Nous avons appris à utiliser ces piles logicielles et à les configurer, ce qui est généralement le plus important pour ce genre de système. Nous avons appris ou réappris des technologies, et amélioré notre capacité à appréhender un système distribué, savoir d&#039;où viennent les problèmes et comment les résoudre.&lt;br /&gt;
&lt;br /&gt;
Les compositions que nous avons pu fournir à l&#039;issue du projet sont très satisfaisantes. Elles sont fonctionnelles et permettent à d&#039;autres utilisateurs d&#039;appréhender la solution NixOS-Compose. Nous avons également fourni des tutoriels et explications avec ces compositions pour exprimer des retours utilisateur au projet NixOS-Compose, ce qui, nous espérons, permettra de mettre en valeur ce beau projet.&lt;br /&gt;
&lt;br /&gt;
=Démonstration=&lt;br /&gt;
&lt;br /&gt;
La démonstration que nous proposons est de présenter le déploiement de chacune des piles logicielles.&lt;br /&gt;
&lt;br /&gt;
Vidéo de démonstration sur Kubernetes: https://www.youtube.com/watch?v=uOh8BJPj7MU&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=Rapport_Test_Infrastructures_NixOS_2021-2022&amp;diff=52457</id>
		<title>Rapport Test Infrastructures NixOS 2021-2022</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=Rapport_Test_Infrastructures_NixOS_2021-2022&amp;diff=52457"/>
		<updated>2022-03-18T09:37:03Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;=Rappel du sujet et cahier des charges=&lt;br /&gt;
&lt;br /&gt;
L’objectif est d’expérimenter et de manipuler une technologie récente : &#039;&#039;&#039;NixOS&#039;&#039;&#039; et le projet de recherche &#039;&#039;&#039;NixOS-Compose&#039;&#039;&#039;. Nix est un outil de gestion de paquets (bibliothèques, morceau logiciel offrant certaines fonctionnalités), et NixOS est un système d&#039;exploitation Linux qui utilise Nix dans son architecture. Nous parlerons plus en détails des différentes technologiques manipulées dans la prochaine partie.&lt;br /&gt;
&lt;br /&gt;
Nos expérimentations ont consistées à déployer trois projets différents : &#039;&#039;&#039;Kubernetes&#039;&#039;&#039;, &#039;&#039;&#039;ELK&#039;&#039;&#039; et &#039;&#039;&#039;Hadoop&#039;&#039;&#039; en utilisant l&#039;outil NixOS-Compose. La partie la plus importante n&#039;étant pas de déployer une version aboutie et complête pour chacun de projets mais de documenter nos expériences pour fournir des retours utilisateurs permettant l&#039;amélioration de NixOS-Compose.&lt;br /&gt;
&lt;br /&gt;
=Technologies employées=&lt;br /&gt;
&lt;br /&gt;
==Nix==&lt;br /&gt;
&lt;br /&gt;
Nix est un gestionnaire de paquets et un langage fonctionnel qui se différencie de l&#039;approche classique avec sa grande reproductibilité qu&#039;il trouve incompatible avec le &#039;&#039;Filesystem Hierarchy Standard&#039;&#039;. Il dénonce l&#039;enfer des dépendances que l&#039;on retrouve avec cette approche où l&#039;on ne peut pas déterminer les versions utilisées. Nix repose sur son &#039;&#039;&#039;store&#039;&#039;&#039;, où il stocke toutes les &#039;&#039;&#039;dérivations&#039;&#039;&#039; pour chaque paquet. Ces dérivations contiennent des informations sur toutes les dépendances (d&#039;autres &#039;&#039;dérivations&#039;&#039;) et les instructions de build. Le nom de la &#039;&#039;dérivation&#039;&#039; indique le nom du paquet et un hash qui la rend unique mais surtout qui l&#039;identifie : &#039;&#039;&#039;une même dérivation produira toujours la même sortie.&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Avec cette approche, Nix permet plusieurs choses, notamment :&lt;br /&gt;
* La reproductibilité due au déterminisme des &#039;&#039;dérivations&#039;&#039;&lt;br /&gt;
* La possibilité d&#039;utiliser plusieurs versions d&#039;un même paquet en parallèle&lt;br /&gt;
* Comme le nom de la dérivation l&#039;identifie, il est possible de mettre en cache la sortie et la récupérer sans avoir à la reconstruire&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Nixpkgs&#039;&#039;&#039; est un répertoire en ligne contenant de nombreux paquets (80 000 actuellement) construits à partir de &#039;&#039;dérivations&#039;&#039; fournies par la communauté et accessibles à tous.&lt;br /&gt;
&lt;br /&gt;
==NixOS==&lt;br /&gt;
&lt;br /&gt;
NixOS est une distribution GNU/Linux reposant sur Nix en tant que gestionnaire de paquets mais également de gestionnaire de configuration. L&#039;ensemble du système et toutes les configurations sont considérés comme des dérivations. Cela permet entre autres de faire des restorations du système à des versions précédentes simplement, chaque modification du système occasionne la création d&#039;une nouvelle version &#039;&#039;&#039;atomique&#039;&#039;&#039;. Par ailleurs, le système d&#039;exploitation hérite ainsi de la propriété &#039;&#039;&#039;déterministe&#039;&#039;&#039; et &#039;&#039;&#039;reproductible&#039;&#039;&#039; que Nix offre.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;NixOS-test&#039;&#039;&#039; est une librairie de test qui permet, à partir d&#039;un ensemble de fichiers de configuration Nix, de fournir une interface python pour manipuler ces configurations sur une/des machines virtuelles avec &#039;&#039;&#039;QEMU&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==NixOS-Compose==&lt;br /&gt;
&lt;br /&gt;
NixOS-Compose est un projet de l’équipe Datamove qui étend l’utilisation de NixOS vers d’autres supports que les machines virtuelles, comme notamment la plateforme &#039;&#039;&#039;Grid&#039;5000&#039;&#039;&#039; et des solutions de conteneurs comme &#039;&#039;&#039;Docker&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
Kubernetes est un &#039;&#039;&#039;orchestrateur de conteneurs&#039;&#039;&#039; permettant de déployer, mettre à l&#039;échelle et surveiller des applications conteneurisées sur un cluster de machines. Développé en Go et rendu open source en 2015 par Google inspiré de leur solution privée Borg, Kubernetes est maintenant l&#039;outil central du monde du &#039;&#039;&#039;DevOps&#039;&#039;&#039; dans l&#039;industrie. Il apporte une couche d&#039;abstraction au dessus d&#039;un datacenter, dont la mise en place a également été facilitée par le cloud, pour fournir une &#039;&#039;&#039;plateforme de déploiement&#039;&#039;&#039; fortement disponible aux développeurs. Kubernetes dispose également d&#039;un &#039;&#039;&#039;large écosystème&#039;&#039;&#039; d&#039;outils et plugins améliorant différents aspects de son utilisation : routage, monitoring, sécurité, gitops, déploiements (vert/bleu, canary...), serverless etc.&lt;br /&gt;
    &lt;br /&gt;
En cette qualité, Kubernetes est une plateforme de choix dans le cadre d&#039;expériences nécessitant notamment un certain nombre de services ou applications, comme dans le cas d&#039;architectures &#039;&#039;&#039;microservices&#039;&#039;&#039; par exemple. De plus, malgré ses nombreux atouts, Kubernetes est une solution souvent difficile et longue à mettre initialement en place pour cause d&#039;une &#039;&#039;&#039;configuration complexe&#039;&#039;&#039; liée à l&#039;architecture microservice de la plateforme elle-même. (Il faut reconnaître qu&#039;avec le cloud il est maintenant très simple de déployer un cluster Kubernetes, &#039;&#039;Terraform&#039;&#039; est notamment un concurrent potentiel de NixOS-Compose) &lt;br /&gt;
&lt;br /&gt;
Dans le cadre de notre projet, être en mesure de fournir un cluster Kubernetes de la taille voulue, &#039;&#039;&#039;simplement&#039;&#039;&#039;, &#039;&#039;&#039;rapidemment&#039;&#039;&#039; et de manière &#039;&#039;&#039;reproductible&#039;&#039;&#039;, est un objectif très intéressant, non seulement pour l&#039;aspect apprentissage mais également pour son utilisation dans le contextes d&#039;expériences scientifiques avec NixOS-Compose. &#039;&#039;&#039;Kubernetes est en lui même un solution qui permet une forte reproductibilité au niveau des déploiements internes, mais c&#039;est la phase de déploiement des machines et de bootstrap du cluster qui manque cette qualité, et c&#039;est là que nous nous positionnons.&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
&amp;quot;ELK&amp;quot; est l&#039;acronyme de trois projets open source : &#039;&#039;&#039;Elasticsearch&#039;&#039;&#039;, &#039;&#039;&#039;Logstash&#039;&#039;&#039; et &#039;&#039;&#039;Kibana&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
[[File:Elk_stack.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Intéraction des composants au sein de la stack ELK ou BELK]]&lt;br /&gt;
&lt;br /&gt;
===Elasticsearch===&lt;br /&gt;
&lt;br /&gt;
Elasticsearch est un &#039;&#039;&#039;outil de recherche et d&#039;analyse de données&#039;&#039;&#039; fonctionnant de manière &#039;&#039;&#039;distribuée&#039;&#039;&#039; et basé sur [Apache Lucene](https://lucene.apache.org/). Créé par Shay Banon en 2004, au fil des années, Elasticsearch n&#039;a cessé d&#039;évoluer et aujourd&#039;hui c&#039;est l&#039;outil de référence pour réaliser une recherche performante sur une large quantité de données.&lt;br /&gt;
&lt;br /&gt;
Technologiquement parlant, il s&#039;agit d&#039;une base de données programmée en Java et &#039;&#039;&#039;spécialisée dans la recherche et l&#039;indexation de documents&#039;&#039;&#039;. Si Elasticsearch est aussi performant c&#039;est grâce à son fonctionnement en mode distribué. La tâche de recherche est exécutée en parallèle par plusieurs nœuds Elasticsearch, ce qui améliore la réactivité du système. Elasticsearch a aussi la force d&#039;être facilement configurable et mis à l&#039;échelle.&lt;br /&gt;
&lt;br /&gt;
===Logstash===&lt;br /&gt;
&lt;br /&gt;
Logstash est un outil écrit en Java et en Ruby permettant de &#039;&#039;&#039;centraliser des traces&#039;&#039;&#039; provenant de plusieurs systèmes, de les analyser et de les stocker. Conceptuellement, Logstash peut être vu comme un &#039;&#039;&#039;&amp;quot;pipe&amp;quot;&#039;&#039;&#039; où les données rentrent d&#039;un bout, et sont traitées avant de ressortir de l&#039;autre bout. Logstash est plus qu&#039;un simple &amp;quot;pipe&amp;quot; puisqu&#039;il peut prendre une multitude de sources différentes en entrées et renvoyées les données traitées vers différentes sorties. Il sert généralement à filtrer/analyser des messages avant de les envoyer à Elasticsearch qui va, lui, se charger de les stocker et de les indexer.&lt;br /&gt;
&lt;br /&gt;
===Kibana===&lt;br /&gt;
&lt;br /&gt;
Kibana est un outil permettant la &#039;&#039;&#039;visualisation de données&#039;&#039;&#039; écrit en JavaScript est la dernière composante majeure de la stack ELK. Il est similaire à d&#039;autres outils de visualisation tel que [Grafana](https://grafana.com/), mais a la particularité d&#039;être spécialisé pour une utilisation au sein de la stack ELK. Le rôle de Kibana est donc de récupérer les données indexées par Elasticsearch et de les rendre visuellement exploitables pour un humain.&lt;br /&gt;
&lt;br /&gt;
===Beats===&lt;br /&gt;
&lt;br /&gt;
Bien que la stack ELK soit l&#039;acronyme des trois projets majeurs dont nous avons parlé précédemment, ELK est consistué d&#039;un autre projet nommé &#039;&#039;&#039;Beats&#039;&#039;&#039;. Il y a d&#039;ailleurs quelques discussions autour du renommage de la stack ELK en stack BELK pour inclure le projet Beats. Beats est une plateforme réunissant une multitude de petits &#039;&#039;&#039;outils permettant d&#039;expédier des données&#039;&#039;&#039; vers Logstash ou Elasticsearch. Chaque outil vise un type de données spécifiques. On retrouvera par exemple l&#039;outil Filebeat pour l&#039;expédition de traces systèmes, Metricbeat pour les métriques, Packetbeat pour le réseau ou encore Heartbeat pour le monitoring. Cette liste est non exhaustive, il existe plein d&#039;autres beats, chacun spécialisé pour des données de nature différente.&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Hadoop est un framework open source Java destiné à faciliter la création d&#039;applications distribuées (au niveau du stockage des données et de leur traitement) et scalables permettant aux applications de travailler avec des milliers de nœuds et des masses importantes de données. Ainsi chaque nœud est constitué de machines standard regroupées en grappe. Hadoop fonctionne avec de nombreux modules ou services conçus selon l&#039;idée que les pannes matérielles sont fréquentes et qu&#039;en conséquence elles doivent être gérées automatiquement par le framework. Cet aspect de redondance n&#039;est pas traité dans ce projet.&lt;br /&gt;
&lt;br /&gt;
=Architectures techniques=&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
L&#039;architecture de Kubernetes est distribuée sous forme de microservices avec plusieurs composants, chacun responsable d&#039;une certaine tâche pour contrôler le cluster et les applications qui y vivent. Tout d&#039;abord, les composants sont à séparer en deux groupes: le control plane, tête pensante du cluster, et les composants des nodes, responsables de faire fonctionner les conteneurs. Une machine est dite nœud maître dès lors qu&#039;elle est membre du control plane (elle exécute les composants du control plane, seule ou en communication avec les autres maîtres). Une machine peut à la fois être maître et exécuter des conteneurs (control plane et *Node*), ce n&#039;est toutefois pas recommandé au vu de l&#039;importance du rôle du control plane.&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-kubernetes-architecture.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://kubernetes.io/docs/concepts/overview/components&lt;br /&gt;
&lt;br /&gt;
===Control plane===&lt;br /&gt;
&lt;br /&gt;
Le &#039;&#039;&#039;control plane&#039;&#039;&#039; est un ensemble de composants responsable du bon fonctionnement du cluster. Ces composants sont présents sur chaque nœud maître du cluster. Dans le cas d&#039;un cluster à haute disponibilité (plusieurs maîtres), ces composants fonctionnent de manière distribuée, et nécessitent un load balancer.&lt;br /&gt;
&lt;br /&gt;
Le composant principal est l&#039;&#039;&#039;&#039;apiserver&#039;&#039;&#039;, qui est donc une API permettant la communication entre les différents composants. L&#039;apiserver est le seul composant avec qui les autres composants communiquent. Ensuite le &#039;&#039;&#039;controller manager&#039;&#039;&#039;, regroupe les différents contrôleurs dont le rôle est de gérer les resources qui leur corresponde (le contrôleur des *Pod* veille au bon fonctionnement des &#039;&#039;Pod&#039;&#039;, pareil pour les &#039;&#039;ReplicasSet&#039;&#039;, &#039;&#039;Endpoint&#039;&#039;, &#039;&#039;Node&#039;&#039;...). Le &#039;&#039;&#039;scheduler&#039;&#039;&#039; est responsable de l&#039;attribution des resources (machines) aux applications (&#039;&#039;Pod&#039;&#039;, &#039;&#039;Deployment&#039;&#039;...) selon les disponibilités et besoins. Enfin, &#039;&#039;&#039;etcd&#039;&#039;&#039; est une base de données distribuée de configuration qui conserve l&#039;état du cluster. C&#039;est une solution tiers et elle peut être exécutée sur un cluster à part des nœuds maître.&lt;br /&gt;
&lt;br /&gt;
===Node===&lt;br /&gt;
&lt;br /&gt;
Pour Kubernetes, un &#039;&#039;&#039;Node&#039;&#039;&#039; (ou nœud en français) est l&#039;abstraction d&#039;une machine (réelle ou virtuelle). Chaque machine représentant un &#039;&#039;Node&#039;&#039; doit faire tourner trois services: le kubelet, le kube-proxy et un environnement d&#039;exécution de conteneurs.&lt;br /&gt;
&lt;br /&gt;
Le &#039;&#039;&#039;kubelet&#039;&#039;&#039; est véritablement le responsable des conteneurs en pratique, il est le contremaître obéissant au control plane, chargé de faire appliquer ses directives. Le kubelet ordonne à l&#039;environnement d&#039;exécution de conteneurs et fait ses rapports de situation au control plane. Le &#039;&#039;&#039;kube-proxy&#039;&#039;&#039; est chargé de mettre en place les règles de réseau (iptables ou IPVS) pour veiller au bon fonctionnement notamment des &#039;&#039;Service&#039;&#039; et &#039;&#039;Endpoint&#039;&#039;. Enfin, &#039;&#039;&#039;l&#039;environnement d&#039;exécution de conteneurs&#039;&#039;&#039; peut être n&#039;importe quel solution respectant la CRI (container runtime interface) comme containerd ou CRI-O.&lt;br /&gt;
&lt;br /&gt;
Non-obligatoire mais également souvent présent est un &#039;&#039;&#039;plugin de CNI&#039;&#039;&#039; (container network interface) qui met en place le plan de réseau exigé par Kubernetes (à savoir un réseau où les &#039;&#039;Pod&#039;&#039; disposent d&#039;une adresse IP et peuvent communiquer entre eux) à ne pas confondre avec le réseau connectant les machines entre elles. On peut citer notamment Calico, Weave et celui qui est utilisé dans notre projet est Flannel (moins puissant). Parmi les addons on retrouve également un &#039;&#039;&#039;serveur DNS&#039;&#039;&#039; (nécessaire au bon fonctionnement des Services), anciennement kube-dns et maintenant plutôt coredns.&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
En ce qui concerne ELK, il ne s&#039;agit non pas d&#039;un système ou d&#039;un outil en lui-même mais de la collaboration d&#039;une multitude d&#039;outils open source ayant chacun leurs particularités et un fonctionnement qui leur est propre. Pour visualiser plus aisément l&#039;intéraction entre les différentes composantes de la stack ELK, on pourra s&#039;intéresser à l&#039;exemple suivant:&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-elk-architecture.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://fr.wikipedia.org/wiki/Logstash&lt;br /&gt;
&lt;br /&gt;
Dans l&#039;exemple ci-dessus, on distingue trois sources indépendantes: MediaWiki, des services Node.js et Hadoop. Chacune des trois sources envoie des données à une instance différente de Logstash. Les instances de Logstash ne communiquent pas entre elles, toutefois, une fois le traitement des données effectué, chaque instance envoie ses données à un nœud Elasticsearch. Dans le schéma ci-dessus, les trois nœuds font partie d&#039;un même cluster, ce qui permet donc la mise en commun de l&#039;intégralité des données pouvant ensuite être visualisées via Kibana.&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Hadoop est un environement distribué de par son stockage mais également son traitement de données. C&#039;est une suite de solution open source pour le big data. The goal is to instanciate the different kind of nodes from one of the two possible implementation below, and make them communicate to run a job on the cluster.&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-hadoop-architecture-1.png|center]]&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-hadoop-architecture-2.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://www.geeksforgeeks.org/hadoop-introduction&lt;br /&gt;
&lt;br /&gt;
=Réalisations techniques=&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
L&#039;expérience avec Kubernetes consiste avant tout à déployer un cluster Kubernetes fonctionnel, utilisable comme n&#039;importe quel autre cluster. Pour cela nous nous reposons donc tout d&#039;abord sur la dérivation de Kubernetes sur nixpkgs. Ensuite nous utilisons d&#039;autres outils comme &#039;&#039;Helm&#039;&#039; et &#039;&#039;Istio&#039;&#039; pour enrichir l&#039;expérience.&lt;br /&gt;
&lt;br /&gt;
La dérivations de Kubernetes propose la version 1.21.6, avec certains aspects de configuration qui sont cependant déprécié (notamment au niveau des ports uti lisés et des flags devenus déconseillés) car non mis à jour depuis 4 ans. La configuration de cette dérivation peut se faire de deux manière: en précisant la configuration de tous les composants (cf. partie II), ou en précisant uniquement le rôle de la machine. Avec la première approche non pouvons avoir un contrôle complet sur la configuration alors que dans le second tout est plus abstrait. En revanche la deuxième manière est plus simple et plus claire. Nous avons opté pour la seconde en ajoutant un certain nombre d&#039;options supplémentaires. &lt;br /&gt;
&lt;br /&gt;
La composition de l&#039;expérience commence avec la description des machines ainsi que leur rôle dans le cluster. Nous utilisons généralement un nœud maître et deux nœuds de travail, sachant qu&#039;il n&#039;est pas possible actuellement de déployer un cluster à haute disponibilité dont le bootstrap des certificats est automatisé dans le déploiement, autrement il faut le faire manuellement ce qui est hors de question dans le cadre d&#039;un environnement reproductible.&lt;br /&gt;
&lt;br /&gt;
Ensuite nous disposons d&#039;une fonction pour générer la configuration des machines du cluster. Cette configuration contient donc le rôle du node mais également des ajustements sur les ports et addresses IP de certains composants pour permettre la bonne communication des composants entre eux.&lt;br /&gt;
&lt;br /&gt;
Nous ajoutons également une machine supplémentaire hors-cluster, c&#039;est une serveur NFS, une solution parmis d&#039;autres pour fournir au cluster un moyen de créer des volumes (&#039;&#039;PersistentVolume&#039;&#039;) accessibles par tous les nœuds. Ce serveur est monté sur toutes les machines, ce qui permet à l&#039;expérimentateur de soit utiliser des volumes NFS, soit des volumes locaux pour plus de simplicité.&lt;br /&gt;
&lt;br /&gt;
Avec Istio nous pouvons suivre le guide d&#039;exemple présent dans la documentation pour déployer une application microservice et vérifier le bon fonctionnement du cluster.&lt;br /&gt;
&lt;br /&gt;
Cette composition est fonctionnelle pour la plateforme de nixos-test et nixos-test-driver, toutes deux reposant sur QEMU, et également sur Grid&#039;5000 où elle dévoile son vrai potentielle car les machines sont réelles et véritablement utilisables pour administrer le cluster. Elle n&#039;est pas fonctionnelle sur Docker pour des raisons propres à NixOS-Compose qui ne permettent pas de modifier les noms d&#039;hôtes (/etc/hosts), ce qui empêche la dérivation de fonctionner correctement.&lt;br /&gt;
&lt;br /&gt;
Certains éléments de bootstrap se révèlent être difficilement applicable lors du déploiement avec NixOS-Compose et nous reposons donc en partie sur un script d&#039;initialisation du cluster. Ce script est créé dans la composition et accessible dans le path. Il redémarre les composants éventuellement échoués et affiche une commande à l&#039;utilisateur permettant d&#039;ajouter des machines au cluster, cette étape n&#039;tant pas automatisable simplement (l&#039;approche est la même que kubeadm).&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;expérience ELK, une grande partie du temps a été passée à comprendre la stack ELK et ses différentes composantes. Pour réaliser une composition fonctionnelle via NixOS-Compose, nous nous sommes basés sur une composition pré-existante écrite pour NixOS-Tests. La composition a ensuite été modifiée de manière à fonctionner correctement pour les différents modes de déploiement (Docker, Grid&#039;5000).&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Un paquet hadoop existe deja et il s&#039;agit principalement d&#039;en faire sa configuration. Plusieurs configurations différentes ont été réalisées, une minimale afin de comprendre le fonctionnement général, puis une se servant de yarn afin de maitriser la multiplicité des nœuds de travail.&lt;br /&gt;
    &lt;br /&gt;
Dans la composition minimale nous avons pu mettre, comme le premier shéma de la partie précédente, créer un node de front (namenode) ainsi qu&#039;un datanode fonctionnant avec le filesystem.&lt;br /&gt;
&lt;br /&gt;
=Gestion de projet=&lt;br /&gt;
&lt;br /&gt;
Ce projet relève en partie d’un travail de recherche au vu du manque de documentation, du développement toujours en cours de l’OS et de sa faible utilisation de la part de la communauté d’utilisateurs.&lt;br /&gt;
&lt;br /&gt;
Une importante partie de ce projet repose sur la communication entre notre équipe et l’équipe Datamove pour recevoir des consignes et fournir des retours. Pour fluidifier ces échanges nous avons organisé des réunions régulières et mis en place des solutions de communication en permanence à travers des outils comme Telegram et Zoom pour les réunions.&lt;br /&gt;
&lt;br /&gt;
Nous avons mis en place deux types de réunions : des réunions quotidiennes avec un membre de l’équipe Datamove et des réunions hebdomadaires en équipe complète. Les réunions quotidiennes servent principalement à partager l’avancement et exprimer des éventuels blocages. Les réunions hebdomadaires visent davantage à faire un point global et à définir les prochaines étapes.&lt;br /&gt;
&lt;br /&gt;
==Planification==&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de la planification, il nous paraissait essentiel pour un projet comme le nôtre dans lequel énormément de temps est alloué à l&#039;apprentissage d&#039;une technologie plutôt qu&#039;à la production réelle de code de définir une roadmap.&lt;br /&gt;
&lt;br /&gt;
Cette roadmap avait pour but de planifier nos actions sur l’ensemble de la durée du projet. Nous avons fait évoluer la roadmap au fur et à mesure de notre avancement réel. Celle-ci nous a permis non seulement de travailler avec un objectif en tête mais également de partager ces objectifs avec l’équipe Datamove.&lt;br /&gt;
&lt;br /&gt;
==Organisation du travail==&lt;br /&gt;
&lt;br /&gt;
Au commencement de projet, notre objectif à tous était de se former rapidement sur Nix afin de comprendre l&#039;étendu des possibilités de l&#039;outil NixOS-Compose et de commencer à le tester.&lt;br /&gt;
&lt;br /&gt;
Notre première tâche a consisté à écrire une composition k3s compatible avec NixOS-Compose de manière à découvrir la puissance de l&#039;outil.&lt;br /&gt;
&lt;br /&gt;
Ensuite, nous sommes chacun parti sur un projet différent dans l&#039;optique de fournir trois expériences utilisateurs distinctes. La répartition des projets était la suivante :&lt;br /&gt;
* Titouan Minier Mancini : Kubernetes&lt;br /&gt;
* Corentin Humbert : Stack ELK&lt;br /&gt;
* Corentin Sueur : Hadoop&lt;br /&gt;
&lt;br /&gt;
Nous avons donc progressé chacun de notre côté sur nos projets respectifs tout en restant en contact constant de manière à éviter de passer trop temps bloqué sur une partie du projet. La communication a été impérative pour un tel projet au vu de sa complexité et du temps dont nous disposions pour le mener à terme.&lt;br /&gt;
&lt;br /&gt;
==Suivi du travail==&lt;br /&gt;
&lt;br /&gt;
En parallèle nous avons suivi la rédaction de carnets de route individuels où nous expliquons toutes nos actions dans la journée, avec un maximum de détails notamment sur les erreurs. L’objectif est de permettre aux membres de l’équipe Datamove de suivre notre avancée individuelle et d’aider sur les problèmes techniques éventuels. Ces carnet doivent permettre un maximum la reproductibilité des situations pour faciliter la correction.&lt;br /&gt;
&lt;br /&gt;
=Outils de travail=&lt;br /&gt;
&lt;br /&gt;
Au cours de notre projet, nous avons été amenés à utiliser de nombreux outils nous permettant d’échanger entre nous et avec l’équipe Datamove que ce soit pour poser des questions ou partager nos productions.&lt;br /&gt;
&lt;br /&gt;
* Communication écrite/orale :&lt;br /&gt;
** Au sein du groupe : Discord&lt;br /&gt;
** Avec l’équipe Datamove : Telegram, BBB, Zoom&lt;br /&gt;
* Échanges d’informations :&lt;br /&gt;
** Google docs, CodiMD&lt;br /&gt;
* Stockage des documents et du code produit :&lt;br /&gt;
** Dépôt GitLab&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=Métriques logiciels=&lt;br /&gt;
&lt;br /&gt;
Ce projet ne rentre pas dans le cadre d&#039;une production logicielle, la quantité de code produit est faible car le travail est avant tout un travail de compréhension et de recherche. Nous avons produit un fichier de composition pour chaque pile logicielle, ce qui correspond à une centaine de lignes chacune. Le temps était principalement accordé à l&#039;essai, l&#039;avancement à tâtons pour explorer les différentes options disponibles, et à la compréhension du fonctionnement de NixOS-Compose.&lt;br /&gt;
&lt;br /&gt;
Nous avons tous travaillé 35 heures par semaine, à l&#039;exception des première semaines en parallèle avec le projet ECOM où Titouan et Corention Humbert n&#039;étaient plus disponibles qu&#039;à hauteur de 21 à 28 heures par semaine.&lt;br /&gt;
&lt;br /&gt;
=Conclusion=&lt;br /&gt;
&lt;br /&gt;
Ce projet nous a avant tout permis de découvrir l&#039;environnement Nix et la solution NixOS-Compose, qui promet d&#039;être intéressante et un candidat potentiel à l&#039;*Infrastructure as Code* de demain. L&#039;approche est différente de ce que l&#039;on peut rencontrer avec d&#039;autres outils comme Terraform et il est enrichissant de s&#039;y pencher pour élargir sa pensée.&lt;br /&gt;
&lt;br /&gt;
Nous avons également pu travailler sur des piles logicielles que nous ne connaissions pas forcément, ce qui a aussi été très enrichissant. Nous avons appris à utiliser ces piles logicielles et à les configurer, ce qui est généralement le plus important pour ce genre de système. Nous avons appris ou réappris des technologies, et amélioré notre capacité à appréhender un système distribué, savoir d&#039;où viennent les problèmes et comment les résoudre.&lt;br /&gt;
&lt;br /&gt;
Les compositions que nous avons pu fournir à l&#039;issue du projet sont très satisfaisantes. Elles sont fonctionnelles et permettent à d&#039;autres utilisateurs d&#039;appréhender la solution NixOS-Compose. Nous avons également fourni des tutoriels et explications avec ces compositions pour exprimer des retours utilisateur au projet NixOS-Compose, ce qui, nous espérons, permettra de mettre en valeur ce beau projet.&lt;br /&gt;
&lt;br /&gt;
=Démonstration=&lt;br /&gt;
&lt;br /&gt;
La démonstration que nous proposons est de présenter le déploiement de chacune des piles logicielles.&lt;br /&gt;
&lt;br /&gt;
Vidéo de démonstration sur Kubernetes: https://www.youtube.com/watch?v=uOh8BJPj7MU&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=File:Elk_stack.png&amp;diff=52456</id>
		<title>File:Elk stack.png</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=File:Elk_stack.png&amp;diff=52456"/>
		<updated>2022-03-18T09:35:36Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=Rapport_Test_Infrastructures_NixOS_2021-2022&amp;diff=52455</id>
		<title>Rapport Test Infrastructures NixOS 2021-2022</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=Rapport_Test_Infrastructures_NixOS_2021-2022&amp;diff=52455"/>
		<updated>2022-03-18T09:32:57Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;=Rappel du sujet et cahier des charges=&lt;br /&gt;
&lt;br /&gt;
L’objectif est d’expérimenter et de manipuler une technologie récente : &#039;&#039;&#039;NixOS&#039;&#039;&#039; et le projet de recherche &#039;&#039;&#039;NixOS-Compose&#039;&#039;&#039;. Nix est un outil de gestion de paquets (bibliothèques, morceau logiciel offrant certaines fonctionnalités), et NixOS est un système d&#039;exploitation Linux qui utilise Nix dans son architecture. Nous parlerons plus en détails des différentes technologiques manipulées dans la prochaine partie.&lt;br /&gt;
&lt;br /&gt;
Nos expérimentations ont consistées à déployer trois projets différents : &#039;&#039;&#039;Kubernetes&#039;&#039;&#039;, &#039;&#039;&#039;ELK&#039;&#039;&#039; et &#039;&#039;&#039;Hadoop&#039;&#039;&#039; en utilisant l&#039;outil NixOS-Compose. La partie la plus importante n&#039;étant pas de déployer une version aboutie et complête pour chacun de projets mais de documenter nos expériences pour fournir des retours utilisateurs permettant l&#039;amélioration de NixOS-Compose.&lt;br /&gt;
&lt;br /&gt;
=Technologies employées=&lt;br /&gt;
&lt;br /&gt;
==Nix==&lt;br /&gt;
&lt;br /&gt;
Nix est un gestionnaire de paquets et un langage fonctionnel qui se différencie de l&#039;approche classique avec sa grande reproductibilité qu&#039;il trouve incompatible avec le &#039;&#039;Filesystem Hierarchy Standard&#039;&#039;. Il dénonce l&#039;enfer des dépendances que l&#039;on retrouve avec cette approche où l&#039;on ne peut pas déterminer les versions utilisées. Nix repose sur son &#039;&#039;&#039;store&#039;&#039;&#039;, où il stocke toutes les &#039;&#039;&#039;dérivations&#039;&#039;&#039; pour chaque paquet. Ces dérivations contiennent des informations sur toutes les dépendances (d&#039;autres &#039;&#039;dérivations&#039;&#039;) et les instructions de build. Le nom de la &#039;&#039;dérivation&#039;&#039; indique le nom du paquet et un hash qui la rend unique mais surtout qui l&#039;identifie : &#039;&#039;&#039;une même dérivation produira toujours la même sortie.&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Avec cette approche, Nix permet plusieurs choses, notamment :&lt;br /&gt;
* La reproductibilité due au déterminisme des &#039;&#039;dérivations&#039;&#039;&lt;br /&gt;
* La possibilité d&#039;utiliser plusieurs versions d&#039;un même paquet en parallèle&lt;br /&gt;
* Comme le nom de la dérivation l&#039;identifie, il est possible de mettre en cache la sortie et la récupérer sans avoir à la reconstruire&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Nixpkgs&#039;&#039;&#039; est un répertoire en ligne contenant de nombreux paquets (80 000 actuellement) construits à partir de &#039;&#039;dérivations&#039;&#039; fournies par la communauté et accessibles à tous.&lt;br /&gt;
&lt;br /&gt;
==NixOS==&lt;br /&gt;
&lt;br /&gt;
NixOS est une distribution GNU/Linux reposant sur Nix en tant que gestionnaire de paquets mais également de gestionnaire de configuration. L&#039;ensemble du système et toutes les configurations sont considérés comme des dérivations. Cela permet entre autres de faire des restorations du système à des versions précédentes simplement, chaque modification du système occasionne la création d&#039;une nouvelle version &#039;&#039;&#039;atomique&#039;&#039;&#039;. Par ailleurs, le système d&#039;exploitation hérite ainsi de la propriété &#039;&#039;&#039;déterministe&#039;&#039;&#039; et &#039;&#039;&#039;reproductible&#039;&#039;&#039; que Nix offre.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;NixOS-test&#039;&#039;&#039; est une librairie de test qui permet, à partir d&#039;un ensemble de fichiers de configuration Nix, de fournir une interface python pour manipuler ces configurations sur une/des machines virtuelles avec &#039;&#039;&#039;QEMU&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==NixOS-Compose==&lt;br /&gt;
&lt;br /&gt;
NixOS-Compose est un projet de l’équipe Datamove qui étend l’utilisation de NixOS vers d’autres supports que les machines virtuelles, comme notamment la plateforme &#039;&#039;&#039;Grid&#039;5000&#039;&#039;&#039; et des solutions de conteneurs comme &#039;&#039;&#039;Docker&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
Kubernetes est un &#039;&#039;&#039;orchestrateur de conteneurs&#039;&#039;&#039; permettant de déployer, mettre à l&#039;échelle et surveiller des applications conteneurisées sur un cluster de machines. Développé en Go et rendu open source en 2015 par Google inspiré de leur solution privée Borg, Kubernetes est maintenant l&#039;outil central du monde du &#039;&#039;&#039;DevOps&#039;&#039;&#039; dans l&#039;industrie. Il apporte une couche d&#039;abstraction au dessus d&#039;un datacenter, dont la mise en place a également été facilitée par le cloud, pour fournir une &#039;&#039;&#039;plateforme de déploiement&#039;&#039;&#039; fortement disponible aux développeurs. Kubernetes dispose également d&#039;un &#039;&#039;&#039;large écosystème&#039;&#039;&#039; d&#039;outils et plugins améliorant différents aspects de son utilisation : routage, monitoring, sécurité, gitops, déploiements (vert/bleu, canary...), serverless etc.&lt;br /&gt;
    &lt;br /&gt;
En cette qualité, Kubernetes est une plateforme de choix dans le cadre d&#039;expériences nécessitant notamment un certain nombre de services ou applications, comme dans le cas d&#039;architectures &#039;&#039;&#039;microservices&#039;&#039;&#039; par exemple. De plus, malgré ses nombreux atouts, Kubernetes est une solution souvent difficile et longue à mettre initialement en place pour cause d&#039;une &#039;&#039;&#039;configuration complexe&#039;&#039;&#039; liée à l&#039;architecture microservice de la plateforme elle-même. (Il faut reconnaître qu&#039;avec le cloud il est maintenant très simple de déployer un cluster Kubernetes, &#039;&#039;Terraform&#039;&#039; est notamment un concurrent potentiel de NixOS-Compose) &lt;br /&gt;
&lt;br /&gt;
Dans le cadre de notre projet, être en mesure de fournir un cluster Kubernetes de la taille voulue, &#039;&#039;&#039;simplement&#039;&#039;&#039;, &#039;&#039;&#039;rapidemment&#039;&#039;&#039; et de manière &#039;&#039;&#039;reproductible&#039;&#039;&#039;, est un objectif très intéressant, non seulement pour l&#039;aspect apprentissage mais également pour son utilisation dans le contextes d&#039;expériences scientifiques avec NixOS-Compose. &#039;&#039;&#039;Kubernetes est en lui même un solution qui permet une forte reproductibilité au niveau des déploiements internes, mais c&#039;est la phase de déploiement des machines et de bootstrap du cluster qui manque cette qualité, et c&#039;est là que nous nous positionnons.&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
&amp;quot;ELK&amp;quot; est l&#039;acronyme de trois projets open source : &#039;&#039;&#039;Elasticsearch&#039;&#039;&#039;, &#039;&#039;&#039;Logstash&#039;&#039;&#039; et &#039;&#039;&#039;Kibana&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
===Elasticsearch===&lt;br /&gt;
&lt;br /&gt;
Elasticsearch est un &#039;&#039;&#039;outil de recherche et d&#039;analyse de données&#039;&#039;&#039; fonctionnant de manière &#039;&#039;&#039;distribuée&#039;&#039;&#039; et basé sur [Apache Lucene](https://lucene.apache.org/). Créé par Shay Banon en 2004, au fil des années, Elasticsearch n&#039;a cessé d&#039;évoluer et aujourd&#039;hui c&#039;est l&#039;outil de référence pour réaliser une recherche performante sur une large quantité de données.&lt;br /&gt;
&lt;br /&gt;
Technologiquement parlant, il s&#039;agit d&#039;une base de données programmée en Java et &#039;&#039;&#039;spécialisée dans la recherche et l&#039;indexation de documents&#039;&#039;&#039;. Si Elasticsearch est aussi performant c&#039;est grâce à son fonctionnement en mode distribué. La tâche de recherche est exécutée en parallèle par plusieurs nœuds Elasticsearch, ce qui améliore la réactivité du système. Elasticsearch a aussi la force d&#039;être facilement configurable et mis à l&#039;échelle.&lt;br /&gt;
&lt;br /&gt;
===Logstash===&lt;br /&gt;
&lt;br /&gt;
Logstash est un outil écrit en Java et en Ruby permettant de &#039;&#039;&#039;centraliser des traces&#039;&#039;&#039; provenant de plusieurs systèmes, de les analyser et de les stocker. Conceptuellement, Logstash peut être vu comme un &#039;&#039;&#039;&amp;quot;pipe&amp;quot;&#039;&#039;&#039; où les données rentrent d&#039;un bout, et sont traitées avant de ressortir de l&#039;autre bout. Logstash est plus qu&#039;un simple &amp;quot;pipe&amp;quot; puisqu&#039;il peut prendre une multitude de sources différentes en entrées et renvoyées les données traitées vers différentes sorties. Il sert généralement à filtrer/analyser des messages avant de les envoyer à Elasticsearch qui va, lui, se charger de les stocker et de les indexer.&lt;br /&gt;
&lt;br /&gt;
===Kibana===&lt;br /&gt;
&lt;br /&gt;
Kibana est un outil permettant la &#039;&#039;&#039;visualisation de données&#039;&#039;&#039; écrit en JavaScript est la dernière composante majeure de la stack ELK. Il est similaire à d&#039;autres outils de visualisation tel que [Grafana](https://grafana.com/), mais a la particularité d&#039;être spécialisé pour une utilisation au sein de la stack ELK. Le rôle de Kibana est donc de récupérer les données indexées par Elasticsearch et de les rendre visuellement exploitables pour un humain.&lt;br /&gt;
&lt;br /&gt;
===Beats===&lt;br /&gt;
&lt;br /&gt;
Bien que la stack ELK soit l&#039;acronyme des trois projets majeurs dont nous avons parlé précédemment, ELK est consistué d&#039;un autre projet nommé &#039;&#039;&#039;Beats&#039;&#039;&#039;. Il y a d&#039;ailleurs quelques discussions autour du renommage de la stack ELK en stack BELK pour inclure le projet Beats. Beats est une plateforme réunissant une multitude de petits &#039;&#039;&#039;outils permettant d&#039;expédier des données&#039;&#039;&#039; vers Logstash ou Elasticsearch. Chaque outil vise un type de données spécifiques. On retrouvera par exemple l&#039;outil Filebeat pour l&#039;expédition de traces systèmes, Metricbeat pour les métriques, Packetbeat pour le réseau ou encore Heartbeat pour le monitoring. Cette liste est non exhaustive, il existe plein d&#039;autres beats, chacun spécialisé pour des données de nature différente.&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Hadoop est un framework open source Java destiné à faciliter la création d&#039;applications distribuées (au niveau du stockage des données et de leur traitement) et scalables permettant aux applications de travailler avec des milliers de nœuds et des masses importantes de données. Ainsi chaque nœud est constitué de machines standard regroupées en grappe. Hadoop fonctionne avec de nombreux modules ou services conçus selon l&#039;idée que les pannes matérielles sont fréquentes et qu&#039;en conséquence elles doivent être gérées automatiquement par le framework. Cet aspect de redondance n&#039;est pas traité dans ce projet.&lt;br /&gt;
&lt;br /&gt;
=Architectures techniques=&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
L&#039;architecture de Kubernetes est distribuée sous forme de microservices avec plusieurs composants, chacun responsable d&#039;une certaine tâche pour contrôler le cluster et les applications qui y vivent. Tout d&#039;abord, les composants sont à séparer en deux groupes: le control plane, tête pensante du cluster, et les composants des nodes, responsables de faire fonctionner les conteneurs. Une machine est dite nœud maître dès lors qu&#039;elle est membre du control plane (elle exécute les composants du control plane, seule ou en communication avec les autres maîtres). Une machine peut à la fois être maître et exécuter des conteneurs (control plane et *Node*), ce n&#039;est toutefois pas recommandé au vu de l&#039;importance du rôle du control plane.&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-kubernetes-architecture.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://kubernetes.io/docs/concepts/overview/components&lt;br /&gt;
&lt;br /&gt;
===Control plane===&lt;br /&gt;
&lt;br /&gt;
Le &#039;&#039;&#039;control plane&#039;&#039;&#039; est un ensemble de composants responsable du bon fonctionnement du cluster. Ces composants sont présents sur chaque nœud maître du cluster. Dans le cas d&#039;un cluster à haute disponibilité (plusieurs maîtres), ces composants fonctionnent de manière distribuée, et nécessitent un load balancer.&lt;br /&gt;
&lt;br /&gt;
Le composant principal est l&#039;&#039;&#039;&#039;apiserver&#039;&#039;&#039;, qui est donc une API permettant la communication entre les différents composants. L&#039;apiserver est le seul composant avec qui les autres composants communiquent. Ensuite le &#039;&#039;&#039;controller manager&#039;&#039;&#039;, regroupe les différents contrôleurs dont le rôle est de gérer les resources qui leur corresponde (le contrôleur des *Pod* veille au bon fonctionnement des &#039;&#039;Pod&#039;&#039;, pareil pour les &#039;&#039;ReplicasSet&#039;&#039;, &#039;&#039;Endpoint&#039;&#039;, &#039;&#039;Node&#039;&#039;...). Le &#039;&#039;&#039;scheduler&#039;&#039;&#039; est responsable de l&#039;attribution des resources (machines) aux applications (&#039;&#039;Pod&#039;&#039;, &#039;&#039;Deployment&#039;&#039;...) selon les disponibilités et besoins. Enfin, &#039;&#039;&#039;etcd&#039;&#039;&#039; est une base de données distribuée de configuration qui conserve l&#039;état du cluster. C&#039;est une solution tiers et elle peut être exécutée sur un cluster à part des nœuds maître.&lt;br /&gt;
&lt;br /&gt;
===Node===&lt;br /&gt;
&lt;br /&gt;
Pour Kubernetes, un &#039;&#039;&#039;Node&#039;&#039;&#039; (ou nœud en français) est l&#039;abstraction d&#039;une machine (réelle ou virtuelle). Chaque machine représentant un &#039;&#039;Node&#039;&#039; doit faire tourner trois services: le kubelet, le kube-proxy et un environnement d&#039;exécution de conteneurs.&lt;br /&gt;
&lt;br /&gt;
Le &#039;&#039;&#039;kubelet&#039;&#039;&#039; est véritablement le responsable des conteneurs en pratique, il est le contremaître obéissant au control plane, chargé de faire appliquer ses directives. Le kubelet ordonne à l&#039;environnement d&#039;exécution de conteneurs et fait ses rapports de situation au control plane. Le &#039;&#039;&#039;kube-proxy&#039;&#039;&#039; est chargé de mettre en place les règles de réseau (iptables ou IPVS) pour veiller au bon fonctionnement notamment des &#039;&#039;Service&#039;&#039; et &#039;&#039;Endpoint&#039;&#039;. Enfin, &#039;&#039;&#039;l&#039;environnement d&#039;exécution de conteneurs&#039;&#039;&#039; peut être n&#039;importe quel solution respectant la CRI (container runtime interface) comme containerd ou CRI-O.&lt;br /&gt;
&lt;br /&gt;
Non-obligatoire mais également souvent présent est un &#039;&#039;&#039;plugin de CNI&#039;&#039;&#039; (container network interface) qui met en place le plan de réseau exigé par Kubernetes (à savoir un réseau où les &#039;&#039;Pod&#039;&#039; disposent d&#039;une adresse IP et peuvent communiquer entre eux) à ne pas confondre avec le réseau connectant les machines entre elles. On peut citer notamment Calico, Weave et celui qui est utilisé dans notre projet est Flannel (moins puissant). Parmi les addons on retrouve également un &#039;&#039;&#039;serveur DNS&#039;&#039;&#039; (nécessaire au bon fonctionnement des Services), anciennement kube-dns et maintenant plutôt coredns.&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
En ce qui concerne ELK, il ne s&#039;agit non pas d&#039;un système ou d&#039;un outil en lui-même mais de la collaboration d&#039;une multitude d&#039;outils open source ayant chacun leurs particularités et un fonctionnement qui leur est propre. Pour visualiser plus aisément l&#039;intéraction entre les différentes composantes de la stack ELK, on pourra s&#039;intéresser à l&#039;exemple suivant:&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-elk-architecture.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://fr.wikipedia.org/wiki/Logstash&lt;br /&gt;
&lt;br /&gt;
Dans l&#039;exemple ci-dessus, on distingue trois sources indépendantes: MediaWiki, des services Node.js et Hadoop. Chacune des trois sources envoie des données à une instance différente de Logstash. Les instances de Logstash ne communiquent pas entre elles, toutefois, une fois le traitement des données effectué, chaque instance envoie ses données à un nœud Elasticsearch. Dans le schéma ci-dessus, les trois nœuds font partie d&#039;un même cluster, ce qui permet donc la mise en commun de l&#039;intégralité des données pouvant ensuite être visualisées via Kibana.&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Hadoop est un environement distribué de par son stockage mais également son traitement de données. C&#039;est une suite de solution open source pour le big data. The goal is to instanciate the different kind of nodes from one of the two possible implementation below, and make them communicate to run a job on the cluster.&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-hadoop-architecture-1.png|center]]&lt;br /&gt;
&lt;br /&gt;
[[File:nixos-hadoop-architecture-2.png|center]]&lt;br /&gt;
&lt;br /&gt;
Source : https://www.geeksforgeeks.org/hadoop-introduction&lt;br /&gt;
&lt;br /&gt;
=Réalisations techniques=&lt;br /&gt;
&lt;br /&gt;
==Kubernetes==&lt;br /&gt;
&lt;br /&gt;
L&#039;expérience avec Kubernetes consiste avant tout à déployer un cluster Kubernetes fonctionnel, utilisable comme n&#039;importe quel autre cluster. Pour cela nous nous reposons donc tout d&#039;abord sur la dérivation de Kubernetes sur nixpkgs. Ensuite nous utilisons d&#039;autres outils comme &#039;&#039;Helm&#039;&#039; et &#039;&#039;Istio&#039;&#039; pour enrichir l&#039;expérience.&lt;br /&gt;
&lt;br /&gt;
La dérivations de Kubernetes propose la version 1.21.6, avec certains aspects de configuration qui sont cependant déprécié (notamment au niveau des ports uti lisés et des flags devenus déconseillés) car non mis à jour depuis 4 ans. La configuration de cette dérivation peut se faire de deux manière: en précisant la configuration de tous les composants (cf. partie II), ou en précisant uniquement le rôle de la machine. Avec la première approche non pouvons avoir un contrôle complet sur la configuration alors que dans le second tout est plus abstrait. En revanche la deuxième manière est plus simple et plus claire. Nous avons opté pour la seconde en ajoutant un certain nombre d&#039;options supplémentaires. &lt;br /&gt;
&lt;br /&gt;
La composition de l&#039;expérience commence avec la description des machines ainsi que leur rôle dans le cluster. Nous utilisons généralement un nœud maître et deux nœuds de travail, sachant qu&#039;il n&#039;est pas possible actuellement de déployer un cluster à haute disponibilité dont le bootstrap des certificats est automatisé dans le déploiement, autrement il faut le faire manuellement ce qui est hors de question dans le cadre d&#039;un environnement reproductible.&lt;br /&gt;
&lt;br /&gt;
Ensuite nous disposons d&#039;une fonction pour générer la configuration des machines du cluster. Cette configuration contient donc le rôle du node mais également des ajustements sur les ports et addresses IP de certains composants pour permettre la bonne communication des composants entre eux.&lt;br /&gt;
&lt;br /&gt;
Nous ajoutons également une machine supplémentaire hors-cluster, c&#039;est une serveur NFS, une solution parmis d&#039;autres pour fournir au cluster un moyen de créer des volumes (&#039;&#039;PersistentVolume&#039;&#039;) accessibles par tous les nœuds. Ce serveur est monté sur toutes les machines, ce qui permet à l&#039;expérimentateur de soit utiliser des volumes NFS, soit des volumes locaux pour plus de simplicité.&lt;br /&gt;
&lt;br /&gt;
Avec Istio nous pouvons suivre le guide d&#039;exemple présent dans la documentation pour déployer une application microservice et vérifier le bon fonctionnement du cluster.&lt;br /&gt;
&lt;br /&gt;
Cette composition est fonctionnelle pour la plateforme de nixos-test et nixos-test-driver, toutes deux reposant sur QEMU, et également sur Grid&#039;5000 où elle dévoile son vrai potentielle car les machines sont réelles et véritablement utilisables pour administrer le cluster. Elle n&#039;est pas fonctionnelle sur Docker pour des raisons propres à NixOS-Compose qui ne permettent pas de modifier les noms d&#039;hôtes (/etc/hosts), ce qui empêche la dérivation de fonctionner correctement.&lt;br /&gt;
&lt;br /&gt;
Certains éléments de bootstrap se révèlent être difficilement applicable lors du déploiement avec NixOS-Compose et nous reposons donc en partie sur un script d&#039;initialisation du cluster. Ce script est créé dans la composition et accessible dans le path. Il redémarre les composants éventuellement échoués et affiche une commande à l&#039;utilisateur permettant d&#039;ajouter des machines au cluster, cette étape n&#039;tant pas automatisable simplement (l&#039;approche est la même que kubeadm).&lt;br /&gt;
&lt;br /&gt;
==ELK==&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;expérience ELK, une grande partie du temps a été passée à comprendre la stack ELK et ses différentes composantes. Pour réaliser une composition fonctionnelle via NixOS-Compose, nous nous sommes basés sur une composition pré-existante écrite pour NixOS-Tests. La composition a ensuite été modifiée de manière à fonctionner correctement pour les différents modes de déploiement (Docker, Grid&#039;5000).&lt;br /&gt;
&lt;br /&gt;
==Hadoop==&lt;br /&gt;
&lt;br /&gt;
Un paquet hadoop existe deja et il s&#039;agit principalement d&#039;en faire sa configuration. Plusieurs configurations différentes ont été réalisées, une minimale afin de comprendre le fonctionnement général, puis une se servant de yarn afin de maitriser la multiplicité des nœuds de travail.&lt;br /&gt;
    &lt;br /&gt;
Dans la composition minimale nous avons pu mettre, comme le premier shéma de la partie précédente, créer un node de front (namenode) ainsi qu&#039;un datanode fonctionnant avec le filesystem.&lt;br /&gt;
&lt;br /&gt;
=Gestion de projet=&lt;br /&gt;
&lt;br /&gt;
Ce projet relève en partie d’un travail de recherche au vu du manque de documentation, du développement toujours en cours de l’OS et de sa faible utilisation de la part de la communauté d’utilisateurs.&lt;br /&gt;
&lt;br /&gt;
Une importante partie de ce projet repose sur la communication entre notre équipe et l’équipe Datamove pour recevoir des consignes et fournir des retours. Pour fluidifier ces échanges nous avons organisé des réunions régulières et mis en place des solutions de communication en permanence à travers des outils comme Telegram et Zoom pour les réunions.&lt;br /&gt;
&lt;br /&gt;
Nous avons mis en place deux types de réunions : des réunions quotidiennes avec un membre de l’équipe Datamove et des réunions hebdomadaires en équipe complète. Les réunions quotidiennes servent principalement à partager l’avancement et exprimer des éventuels blocages. Les réunions hebdomadaires visent davantage à faire un point global et à définir les prochaines étapes.&lt;br /&gt;
&lt;br /&gt;
==Planification==&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de la planification, il nous paraissait essentiel pour un projet comme le nôtre dans lequel énormément de temps est alloué à l&#039;apprentissage d&#039;une technologie plutôt qu&#039;à la production réelle de code de définir une roadmap.&lt;br /&gt;
&lt;br /&gt;
Cette roadmap avait pour but de planifier nos actions sur l’ensemble de la durée du projet. Nous avons fait évoluer la roadmap au fur et à mesure de notre avancement réel. Celle-ci nous a permis non seulement de travailler avec un objectif en tête mais également de partager ces objectifs avec l’équipe Datamove.&lt;br /&gt;
&lt;br /&gt;
==Organisation du travail==&lt;br /&gt;
&lt;br /&gt;
Au commencement de projet, notre objectif à tous était de se former rapidement sur Nix afin de comprendre l&#039;étendu des possibilités de l&#039;outil NixOS-Compose et de commencer à le tester.&lt;br /&gt;
&lt;br /&gt;
Notre première tâche a consisté à écrire une composition k3s compatible avec NixOS-Compose de manière à découvrir la puissance de l&#039;outil.&lt;br /&gt;
&lt;br /&gt;
Ensuite, nous sommes chacun parti sur un projet différent dans l&#039;optique de fournir trois expériences utilisateurs distinctes. La répartition des projets était la suivante :&lt;br /&gt;
* Titouan Minier Mancini : Kubernetes&lt;br /&gt;
* Corentin Humbert : Stack ELK&lt;br /&gt;
* Corentin Sueur : Hadoop&lt;br /&gt;
&lt;br /&gt;
Nous avons donc progressé chacun de notre côté sur nos projets respectifs tout en restant en contact constant de manière à éviter de passer trop temps bloqué sur une partie du projet. La communication a été impérative pour un tel projet au vu de sa complexité et du temps dont nous disposions pour le mener à terme.&lt;br /&gt;
&lt;br /&gt;
==Suivi du travail==&lt;br /&gt;
&lt;br /&gt;
En parallèle nous avons suivi la rédaction de carnets de route individuels où nous expliquons toutes nos actions dans la journée, avec un maximum de détails notamment sur les erreurs. L’objectif est de permettre aux membres de l’équipe Datamove de suivre notre avancée individuelle et d’aider sur les problèmes techniques éventuels. Ces carnet doivent permettre un maximum la reproductibilité des situations pour faciliter la correction.&lt;br /&gt;
&lt;br /&gt;
=Outils de travail=&lt;br /&gt;
&lt;br /&gt;
Au cours de notre projet, nous avons été amenés à utiliser de nombreux outils nous permettant d’échanger entre nous et avec l’équipe Datamove que ce soit pour poser des questions ou partager nos productions.&lt;br /&gt;
&lt;br /&gt;
* Communication écrite/orale :&lt;br /&gt;
** Au sein du groupe : Discord&lt;br /&gt;
** Avec l’équipe Datamove : Telegram, BBB, Zoom&lt;br /&gt;
* Échanges d’informations :&lt;br /&gt;
** Google docs, CodiMD&lt;br /&gt;
* Stockage des documents et du code produit :&lt;br /&gt;
** Dépôt GitLab&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=Métriques logiciels=&lt;br /&gt;
&lt;br /&gt;
Ce projet ne rentre pas dans le cadre d&#039;une production logicielle, la quantité de code produit est faible car le travail est avant tout un travail de compréhension et de recherche. Nous avons produit un fichier de composition pour chaque pile logicielle, ce qui correspond à une centaine de lignes chacune. Le temps était principalement accordé à l&#039;essai, l&#039;avancement à tâtons pour explorer les différentes options disponibles, et à la compréhension du fonctionnement de NixOS-Compose.&lt;br /&gt;
&lt;br /&gt;
Nous avons tous travaillé 35 heures par semaine, à l&#039;exception des première semaines en parallèle avec le projet ECOM où Titouan et Corention Humbert n&#039;étaient plus disponibles qu&#039;à hauteur de 21 à 28 heures par semaine.&lt;br /&gt;
&lt;br /&gt;
=Conclusion=&lt;br /&gt;
&lt;br /&gt;
Ce projet nous a avant tout permis de découvrir l&#039;environnement Nix et la solution NixOS-Compose, qui promet d&#039;être intéressante et un candidat potentiel à l&#039;*Infrastructure as Code* de demain. L&#039;approche est différente de ce que l&#039;on peut rencontrer avec d&#039;autres outils comme Terraform et il est enrichissant de s&#039;y pencher pour élargir sa pensée.&lt;br /&gt;
&lt;br /&gt;
Nous avons également pu travailler sur des piles logicielles que nous ne connaissions pas forcément, ce qui a aussi été très enrichissant. Nous avons appris à utiliser ces piles logicielles et à les configurer, ce qui est généralement le plus important pour ce genre de système. Nous avons appris ou réappris des technologies, et amélioré notre capacité à appréhender un système distribué, savoir d&#039;où viennent les problèmes et comment les résoudre.&lt;br /&gt;
&lt;br /&gt;
Les compositions que nous avons pu fournir à l&#039;issue du projet sont très satisfaisantes. Elles sont fonctionnelles et permettent à d&#039;autres utilisateurs d&#039;appréhender la solution NixOS-Compose. Nous avons également fourni des tutoriels et explications avec ces compositions pour exprimer des retours utilisateur au projet NixOS-Compose, ce qui, nous espérons, permettra de mettre en valeur ce beau projet.&lt;br /&gt;
&lt;br /&gt;
=Démonstration=&lt;br /&gt;
&lt;br /&gt;
La démonstration que nous proposons est de présenter le déploiement de chacune des piles logicielles.&lt;br /&gt;
&lt;br /&gt;
Vidéo de démonstration sur Kubernetes: https://www.youtube.com/watch?v=uOh8BJPj7MU&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=Projets_2021-2022&amp;diff=52200</id>
		<title>Projets 2021-2022</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=Projets_2021-2022&amp;diff=52200"/>
		<updated>2022-02-18T08:36:30Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;&amp;lt;[[Projets 2020-2021]] | [[Projets]] | [[Projets 2022-2023]]&amp;gt;&amp;gt;&lt;br /&gt;
=INFO=&lt;br /&gt;
==INFO3==&lt;br /&gt;
&lt;br /&gt;
==INFO4==&lt;br /&gt;
===Projet Semestre S8===&lt;br /&gt;
&lt;br /&gt;
Enseignants responsables : Olivier Richard&lt;br /&gt;
&lt;br /&gt;
* Dates : Lundi après-midi, Mardi après-midi  &lt;br /&gt;
* Lancement: 10 Janvier 2021 après midi&lt;br /&gt;
* Soutenance à mi-parcours: A définir&lt;br /&gt;
* Soutenance: A définir&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;Evaluation à mi-parcours le lundi/mardi ???&#039;&#039;&#039;: Format: 10min (5min de présentation 3 slides au plus, 5min de discussion). Cette évaluation sera prise en compte dans la note finale.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Consignes générales:&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;Vous devez être pro-actifs !!!&#039;&#039;&#039;: Si des points sont pas ou mals spécifiés, vous le faîtes et vous justifiez vos choix. Pour les problèmes techniques éventuels vous pouvez: creuser la question, contacter l&#039;auteur du code si il y a lieu, écrire un rapport de bug (&#039;&#039;&#039;Attention:&#039;&#039;&#039; ca se prépare !), soumettre un patch/pull request, contacter l&#039;enseignant ou la personne référente du projet.&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;Vous devez maintenir une fiche de suivi de projet&#039;&#039;&#039;: elle doit être mise à jour chaque semaine, elle rassemble les élements essentiels du projet, elle indique les évolutions du projet et présente sa feuille de route. &#039;&#039;&#039;Note:&#039;&#039;&#039; le nom de la fiche doit être composé du nom du projet et suffixé par info4_2021_2022. &#039;&#039;&#039;Cette fiche compte pour la note finale&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;Votre code&#039;&#039;&#039; pour doit être hébergé sur le gitlab et à l&#039;URL suivante https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22 , vous utiliserez votre compte UGA.&lt;br /&gt;
&lt;br /&gt;
* Chaque projet doit avoir &#039;&#039;&#039;aux moins 2 dépôts git&#039;&#039;&#039;:&lt;br /&gt;
** &#039;&#039;&#039;Un pour les documents&#039;&#039;&#039; demandés rapport, présentation de pré-soutenante, de soutenance, flyer. &#039;&#039;&#039;Il sera appelé documents.&#039;&#039;&#039;&lt;br /&gt;
** Un ou plusieurs pour le code, les tests, les évaluations, les preuves de concept, la ou les documentations afférentes. &lt;br /&gt;
&lt;br /&gt;
* Les &#039;&#039;&#039;documents public doivent être rédigés en anglais (README, documentation, commentaires de code, nom de variables et de fonctions)&#039;&#039;&#039;.  Le *rapport* sera aussi demandé en *anglais* (il fera la taille d&#039;un rapport de TP). Les transparents des présentation peuvent être en anglais ou en francais, la soutenance sera taire en francais.&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;La note obtenue&#039;&#039;&#039; tiendra compte du &#039;&#039;&#039;nombre et de la qualité des commits&#039;&#039;&#039; observé dans &#039;&#039;&#039;vos dépots git et la branche master&#039;&#039;&#039; (or depot documents). La qualité comprend l&#039;intitulé du commit et son contenu. Les notes pourront être différentiées dans un groupe, il n&#039;est pas acceptable de pas avoir de commit dans le(s) dépôt(s) du projet (or dépôt documents).&lt;br /&gt;
&lt;br /&gt;
* Il est fortement conseillé de suivre un &#039;&#039;&#039;développement incrémental&#039;&#039;&#039; qui permette d&#039;avoir à tout moment un démonstrateur à présenter, un projet peut être constituer d&#039;une succession de &#039;&#039;&#039;démonstrateurs présentables séparément&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
* Vous devez faire aussi des &#039;&#039;&#039;schémas d&#039;architectures générales et/ou spéficiques, des diagrammes de séquence&#039;&#039;&#039;, et autre documents de spécification si nécessaire. Ces documents vous serviront de base de discussion/brainstorming interne ainsi que dans vos différents documents (rapport, présentations, documentation). Ces schémas sont avant tout conceptuels et techniques.&lt;br /&gt;
&lt;br /&gt;
===Propositions de projets S8===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
* 1. [https://codimd.math.cnrs.fr/?next=%2Fs%2FB029qfT5Q Courriels à Suppression Programmée] : Michaël Périn&lt;br /&gt;
* 2. [[Firmwares open source pour une station de réception de satellites pour l’Internet des Objets isolés]], Didier DONSEZ.&lt;br /&gt;
* 3. [[Evaluation du toolkit AI de STM32 pour l&#039;analyse de l&#039;environnement sonore]] (Suite 2022), Didier DONSEZ.&lt;br /&gt;
* 4. [[Algorithmes de géolocalisation d’objets par TDOA (Time Difference of Arrival)]] (suite), Didier DONSEZ.&lt;br /&gt;
* 5. [[Dashboard pour Overwatch]] Olivier Richard&lt;br /&gt;
* 6. [[Application mobile d&#039;enregistrements de noeuds IoT LoRaWAN dans plusieurs réseaux]] (Suite) : Didier DONSEZ&lt;br /&gt;
* 7. [[Bluetooth 5.1 Angle of Arrival based Indoor Localization]] (Suite) : Didier DONSEZ&lt;br /&gt;
* 8. Intégration de composants de mesures environnementales (eau, air, ...) pour le [[Contribution au projet STM32Python|projet STM32Python]] à destination des lycéens: Didier DONSEZ&lt;br /&gt;
* 9. [[Air Quality Station]] (Suite) : Didier DONSEZ&lt;br /&gt;
* 10. [[Floating Water Quality Station]] : Didier DONSEZ, Nicolas PALIX&lt;br /&gt;
* 12. [[Testeur de terrain pour réseaux LoRaWAN privés et publics (TTN, CampusIoT et Helium)]] (suite 2021), Didier DONSEZ.&lt;br /&gt;
* 13. [[Géolocalition Indoor en LoRa 2.4GHz]], Didier DONSEZ.&lt;br /&gt;
* 14. [[RealWorld avec Dioxus]] (Rust + web), Olivier Richard&lt;br /&gt;
* 15. Poursuite projet 20-21 [[Rust Engine | Executeur de tâche en Rust]], Olivier Richard&lt;br /&gt;
* 16. Poursuite projet 20-21 [[Retrocompute simulateur | RetroComputing]]: (vintage style) Coupler le simulateur Digital avec un simulateur de processeur 8bits, Olivier Richard&lt;br /&gt;
* 17. Poursuite projet 19-20 [[Portail pour gestionnaire de taches]](react, Typescript), Olivier Richard&lt;br /&gt;
* 18. [[Paquets NIX pour Polytech]], Olivier Richard&lt;br /&gt;
* 19. [[Mini compilateur C pour mini CPU]], Olivier Richard&lt;br /&gt;
* 20. Mode jeu en réseau (Wifi/Bluetooth) pour [[TanksOfFreedom]], Nicolas Palix&lt;br /&gt;
&lt;br /&gt;
Non affecté&lt;br /&gt;
* xx. [[Bibliothèque de décodeurs standards et d&#039;afficheurs Grafana pour objets connectés LoRaWAN]] : Didier DONSEZ&lt;br /&gt;
* xx. [[ASAC|Agriculture connectée]] en partenariat avec les projets collectifs IESE/MAT : Nicolas Palix&lt;br /&gt;
* xx. [[Faults In Linux]], Nicolas Palix&lt;br /&gt;
&lt;br /&gt;
===Affectations===&lt;br /&gt;
{|class=&amp;quot;wikitable alternance&amp;quot;&lt;br /&gt;
|+ Affectation des projets INFO4 21-22&lt;br /&gt;
|-&lt;br /&gt;
|&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Sujet&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Etudiants&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Enseignant(s)&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Fiche de suivi&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Documents&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 1&lt;br /&gt;
| [https://air.imag.fr/index.php/Planned_Deletion_Emails Courriels à Suppression Programmée]&lt;br /&gt;
| CANIN CORENTIN,MONTEILLER JOSHUA,WAGNER SAMY&lt;br /&gt;
| Michaël PÉRIN&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/01/docs/-/blob/main/%20Courriels%20%C3%A0%20Suppression%20Programm%C3%A9e%20info4_2021_2022.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 2&lt;br /&gt;
| [https://air.imag.fr/index.php/Firmwares_open_source_pour_une_station_de_r%C3%A9ception_de_satellites_pour_l%E2%80%99Internet_des_Objets_isol%C3%A9s# Firmwares open source pour une station de réception de satellites pour l’Internet des Objets isolés]&lt;br /&gt;
| CARMONA DAMIAN,DA COSTA TOM,WOZNY PIERRE-RAPHAEL&lt;br /&gt;
| Didier DONSEZ&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/02/docs/-/blob/main/Firmwares_open_source_pour_une_station_de_r%C3%A9ception_de_satellites_pour_l_Internet_des_Objets_isol%C3%A9s_info4_2021_2022.md# Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 3&lt;br /&gt;
| [https://air.imag.fr/index.php/Evaluation_du_toolkit_AI_de_STM32_pour_l%27analyse_de_l%27environnement_sonore Evaluation du toolkit AI de STM32 pour l&#039;analyse de l&#039;environnement sonore]&lt;br /&gt;
| BACH THOMAS,BARBE FLORENT,SIMO YOKAM GEORGES HARRISSO&lt;br /&gt;
| Didier DONSEZ&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/03/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 5&lt;br /&gt;
| [https://air.imag.fr/index.php/Dashboard_pour_Overwatch# Dashboard pour Overwatch]&lt;br /&gt;
| CAILLES MAXIME,REYGNER ETIENNE,VERRIER MARTIN&lt;br /&gt;
| Olivier RICHARD&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/05/docs/-/blob/main/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 6&lt;br /&gt;
| [[Application mobile d&#039;enregistrements de noeuds IoT LoRaWAN dans plusieurs réseaux]]&lt;br /&gt;
| CHIOTTI MAEL,LAVIROTTE GAETAN,MOTTINO LORIS&lt;br /&gt;
| Didier DONSEZ&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/06/docs/-/tree/main Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 8&lt;br /&gt;
| [[TODO]]&lt;br /&gt;
| GUIRGUIS MIRETTE,HADIBY CHEMSSEDDINE,MOHSEN HACHE&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/08/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 10&lt;br /&gt;
| [[Floating Water Quality Station]]&lt;br /&gt;
| BRETON EMERIC,FAGHLOUMI AYMAN,VIALLET CAMILLE&lt;br /&gt;
| Didier DONSEZ, Nicolas PALIX&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/10/docs/-/blob/main/info4_2021_2022_Fiche_suivi_projet.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 13&lt;br /&gt;
| [https://air.imag.fr/index.php/G%C3%A9olocalition_Indoor_en_LoRa_2.4GHz Géolocalition Indoor en LoRa 2.4GHz]&lt;br /&gt;
| BERNERD CLARA,JARDIN BAPTISTE,NGUYEN JUSTIN&lt;br /&gt;
| Didier DONSEZ&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/13/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 14&lt;br /&gt;
| [[TODO]]&lt;br /&gt;
| IFAKIREN SAMI,MONTHE DJEUMOU BRICE,NGUYEN CLEMEN&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/14/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 15&lt;br /&gt;
| [https://air.imag.fr/index.php/Rust_Engine Exécuteur de tâche en Rust]&lt;br /&gt;
| CHAPPAZ FLORIAN,DE OLIVEIRA VALENTIN,KURKLU FIKRET&lt;br /&gt;
| Olivier RICHARD&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/15/docs/-/blob/main/Rust_Engine_info4_2021_2022.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 17&lt;br /&gt;
| [https://air.imag.fr/index.php/Portail_pour_gestionnaire_de_taches Portail Pour Gestionnaire De Taches]&lt;br /&gt;
| KACHA TOM,MAHAMAN NOURY ABDOURAHAMANE,MEIGNEN HUGO,ZHANG KEMING&lt;br /&gt;
| Olivier RICHARD&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/17/docs/-/blob/main/Fiche_De_Suivi_17.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 18&lt;br /&gt;
| [[Paquets NIX pour Polytech]]&lt;br /&gt;
| CONJARD SAMUEL,FODOR GERGELY,PELISSE-VERDOUX CYPRIEN&lt;br /&gt;
| Olivier RICHARD&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/18/docs/-/blob/master/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 19&lt;br /&gt;
| [[Mini compilateur C pour mini CPU]]&lt;br /&gt;
| CAPET THEO,POITEVIN EVE,ROYET JULIAN&lt;br /&gt;
| Olivier Richard&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/19/docs/-/blob/main/C_compiler_for_MCPU_info4_2021_2022.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 20&lt;br /&gt;
| Mode jeu en réseau pour [[TanksOfFreedom]],&lt;br /&gt;
| ABECASSIS THOMAS,FOURNIER THOMAS,ZAFFUTO LUCA&lt;br /&gt;
| Nicolas Palix&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/20/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
==INFO5==&lt;br /&gt;
===Projet IoT S9===&lt;br /&gt;
Enseignants responsables : Bernard Tourancheau&lt;br /&gt;
&lt;br /&gt;
Calendrier:  Octobre à Décembre 2021. Soutenance 24 Janvier 2022.&lt;br /&gt;
&lt;br /&gt;
{|class=&amp;quot;wikitable alternance&amp;quot;&lt;br /&gt;
|+ Choix des projet des projets INFO5 Réseaux 21-22&lt;br /&gt;
|-&lt;br /&gt;
|&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Sujet&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Etudiants&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Documents&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Github/Trello&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 1&lt;br /&gt;
| [[Réseau de capteur de dichlorométhane]]&lt;br /&gt;
| Dorian BARET - Malone JULIENNE - Quentin CAMBUS&lt;br /&gt;
| [https://lesjoiesducode.fr/quand-notre-revue-de-sprint-se-passe-nickel Fiche]&lt;br /&gt;
| [https://github.com/Cambus-Quentin/DichloWan2021/blob/main/README.md git]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 2&lt;br /&gt;
| [[Création d&#039;un système pour localiser les élèves lors de courses d&#039;orientation]]&lt;br /&gt;
| Antoine Gitton, Gilles Mertens, Bertrand Baudeur&lt;br /&gt;
| [[Media:2021_2022_INFO5_IOT_Orientation_spec.pdf|Spécification paquets LoRa]]&lt;br /&gt;
| [[Media:2021_2022_INFO5_IOT_Orientation_backend.zip|Souces back-end]] - [[Media:2021_2022_INFO5_IOT_Orientation_carte.zip|Souces carte]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 3&lt;br /&gt;
| [[Harnais animalier permettant de suivre notre animal domestique]]&lt;br /&gt;
| Sami ELHADJI TCHIAMBOU, Corentin HUMBERT, Paul LAMBERT, Hugo PRAT CAPILLA&lt;br /&gt;
| [[Media:PSP_Presentation.pdf|Présentation finale]]&lt;br /&gt;
| [https://github.com/Bicorpro Organisation GitHub]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 4&lt;br /&gt;
| [[Géolocalisation et suivi des transports en commun]]&lt;br /&gt;
| Liam ANDRIEUX, Lucas DREZET, Roman REGOUIN&lt;br /&gt;
|&lt;br /&gt;
| [https://github.com/2021-2022-IoT-INFO5-G4 Organisation GitHub]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 5&lt;br /&gt;
| [[Tracking des déplacements de joueurs sur un terrain]]&lt;br /&gt;
| Elias EL YANDOUZI, Lucas CHALOYARD&lt;br /&gt;
| [[Media:IOT_Presentation.pdf|Présentation finale]]&lt;br /&gt;
| [https://github.com/Indoor-Shadow/ble-experiment Github Repo]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 6&lt;br /&gt;
| [[Beer Pong connecté]]&lt;br /&gt;
| Yael PARA, Théo TEYSSIER, Victor MALOD, Alexis LANQUETIN&lt;br /&gt;
| [[Media:BeerPong_Presentation.pdf|Présentation finale]]&lt;br /&gt;
| [https://github.com/McReaper/BeerPongLora Gitub Repo]&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
Exposés points techniques 10&#039; - questions 5&#039;&lt;br /&gt;
* Nom Sujet&lt;br /&gt;
* ??? Python&lt;br /&gt;
* ??? MQTT&lt;br /&gt;
* ??? COAP&lt;br /&gt;
* 26/11/2021 - Elias El Yandouzi - Les différentes techniques de virtualisation&lt;br /&gt;
&lt;br /&gt;
===Projet Semestre S10===&lt;br /&gt;
&lt;br /&gt;
Enseignant responsable : [[user:Donsez|Didier Donsez]]&lt;br /&gt;
&lt;br /&gt;
Convention des projets tutorés externes : Elise Didier.&lt;br /&gt;
&lt;br /&gt;
Calendrier: 27/01 (8H30-12H00) au 18/03.&lt;br /&gt;
&lt;br /&gt;
Séances de Management de projets innovants: A voir dessus.&lt;br /&gt;
&lt;br /&gt;
Réunion de présentation et choix des sujets: 27/01 (8H30-12H00) en salle Polygone P206 (voir ADE)&lt;br /&gt;
&lt;br /&gt;
Démarrage : 27/01&lt;br /&gt;
&lt;br /&gt;
Soutenance à mi-parcours (à définir) : ??/02/2021 13H30-17H30 en distantiel (15 minutes par équipe).&lt;br /&gt;
&lt;br /&gt;
Soutenance finale : 18/03/2021 (8H30-12H00 et 13H30-17H00). 30 minutes par équipe, questions/réponses et démonstration incluse. Prière de rapporter au fablab le matériel emprunté juste après votre soutenance. &lt;br /&gt;
&lt;br /&gt;
====Séances MPI====&lt;br /&gt;
&lt;br /&gt;
Voir ADE qui fait foi).&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Soutenance intermédiaire S10 ====&lt;br /&gt;
Date: 18/02 Matin. Distantiel (sur Zoom). Créneaux de 10 minutes.&lt;br /&gt;
&lt;br /&gt;
L&#039;objectif de la soutenance intermédiaire est de vérifier si l&#039;équipe projet est en bon ordre de marche&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;équipe présentera en 5-6 transparents en 7 minutes.&lt;br /&gt;
* les équipiers et leurs rôles&lt;br /&gt;
* le contexte, le sujet et l&#039;objectif du projet&lt;br /&gt;
* l&#039;architecture du systèmes à réaliser&lt;br /&gt;
* les technologies utilisées&lt;br /&gt;
* le plan de travail (backlog, planning, ce qui est fait, ce qu&#039;il reste à faire ...)&lt;br /&gt;
* les difficultés (s&#039;il y a)&lt;br /&gt;
&lt;br /&gt;
Prévoyez du temps pour les questions-réponses (3 minutes max).&lt;br /&gt;
&lt;br /&gt;
Respectez bien les créneaux indiqués (par respect pour les autres équipes) et soyez présents un peu en avance dans la salle d&#039;attente.&lt;br /&gt;
&lt;br /&gt;
La présence des porteurs n&#039;est pas obligatoire.&lt;br /&gt;
&lt;br /&gt;
==== Soutenance finale S10 ====&lt;br /&gt;
Date provisoire: 18/03/2022 (8H30-12H00 et 13H30-17H00).&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;La présence du(des) porteur(s) est obligatoire. Pensez à les prévenir bien à l&#039;avance&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Durée: 30 minutes par équipe: présentation, questions/réponses et démonstration incluse.&lt;br /&gt;
&lt;br /&gt;
Les documents devront être en ligne sur le wiki (colonne Documents) la veille (ie avant le ??/03/2021 23:59:59 CET).&lt;br /&gt;
&lt;br /&gt;
La présentation est constituée des chapitres suivants:&lt;br /&gt;
* Rappel du sujet/besoin et cahier des charges&lt;br /&gt;
* Technologies employées&lt;br /&gt;
* Architecture techniques&lt;br /&gt;
* Réalisations techniques&lt;br /&gt;
* Gestion de projet (méthode, planning prévisionnel et effectif, gestion des risques, rôles des membres ...)&lt;br /&gt;
* Outils (collaboration, CD/CI ...)&lt;br /&gt;
* Métriques logiciels : lignes de code, langages, performance, temps ingénieur (d&#039;après vos journaux), la répartition  des lignes de code et des commits en pourcentage entre les membres du projet ...)&lt;br /&gt;
* Conclusion (Retour d&#039;expérience)&lt;br /&gt;
* Transparent expliquant la démonstration&lt;br /&gt;
&lt;br /&gt;
L&#039;ensemble des documents doit être accessible depuis le tableau ci-dessus et dans chaque fiche de suivi.&lt;br /&gt;
&lt;br /&gt;
Le screencast (réalisé lors de la dernière répétition) sera rendu disponible via un partage caché (wetransfer, google drive …) dont le lien sera ajouté dans le devoir idoine sur Moodle et également envoyé par mail à votre tuteur.&lt;br /&gt;
&lt;br /&gt;
Le rapport final contient les mêmes chapitres que la présentation ainsi qu&#039;un glossaire et une bibliographie. Le rapport ne doit pas dépasser 15 pages (schémas et figures compris). Vous pourrez référencer les autres documents que vous avez produits au cours du projet (spécifications détaillées, algorithmes, conception d&#039;écrans ...).&lt;br /&gt;
&lt;br /&gt;
Le rapport final est au format Markdown et doit être placé dans un des dépôts Git de votre groupe/organisation.&lt;br /&gt;
&lt;br /&gt;
NB: le rapport technique listé dans la colonne Documents contient tout ce qui ne tient pas dans les 15 pages du rapport final : cahier des charges, diagrammes UML, enquêtes utilisateurs design UI, API, technologies employées (détail), plan de tests, term of services, conformance RPGD, audits/diagnostiques sécurité, MTBR, rapport de vulnérabilité, plan de charge, rapports de charge, manuel d&#039;installation …  : ça dépend un peu de la nature de votre projet.&lt;br /&gt;
&lt;br /&gt;
Conseil : 30 minutes c&#039;est très court alors répétez la soutenance auparavant ! Prévoyez des transparents supplémentaires en annexe pour répondre aux questions.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Prière de rapporter au fablab le matériel emprunté juste après votre soutenance&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==== Affectations S10====&lt;br /&gt;
{|class=&amp;quot;wikitable alternance&amp;quot;&lt;br /&gt;
 |+ Affectation des projets INFO5 2021-2022&lt;br /&gt;
 |-&lt;br /&gt;
 |&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Sujet&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Etudiants&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Porteur(s)&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Fiche de suivi&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Documents&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Dépôt Git&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Soutenance intermédiaire&lt;br /&gt;
 |-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 1&lt;br /&gt;
| [[Test d&#039;infrastructures avec NixOS]]&lt;br /&gt;
| HUMBERT CORENTIN, MINIER MANCINI TITOUAN (Chef de projet), SUEUR CORENTIN (Scrum master)&lt;br /&gt;
| Olivier RICHARD et Quentin GUILLETEAU&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:Presentation_mi_parcours_NixOs.pdf|Presentation de mi-parcours]] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-xxx-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:Presentation_mi_parcours_NixOs.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 2&lt;br /&gt;
| [[Plan dynamique d’un appartement connecté]]&lt;br /&gt;
| GRANGER OSCAR, NOERIE SOPHIE, SARRE MARGAUX, SALMON AMAD, TEYSSIER THEO&lt;br /&gt;
| Sybille CAFFIAU&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-xxx-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 3&lt;br /&gt;
| [[Suivi de troupeaux (ovins, bovins) en zone montagneuse avec un réseau LoRaWAN : expérimentation dans la Matheysine]]&lt;br /&gt;
| GITTON ANTOINE, MALOD VICTOR, MUTEL MATHIS&lt;br /&gt;
| Fabrice FOREST&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-xxx-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 4&lt;br /&gt;
| [[FitSize]]&lt;br /&gt;
| GEITNER TEVA	, GONZALEZ JULES, PARA YAEL&lt;br /&gt;
| Fidèle Eya&#039;a&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-xxx-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 5&lt;br /&gt;
| [[GenderedNews]]&lt;br /&gt;
| AGUIAR MATHILDE (Chef de projet), HAJJI OUMAIMA (SCRUM Master), SIDIBE ROKIATOU DITE ROSE&lt;br /&gt;
| François PORTET, Gilles BASTIN, Ange RICHARD&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media: Soutenance_interm_genderednews.pdf|Presentation de mi-parcours]] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-xxx-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media: Soutenance_interm_genderednews.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 6&lt;br /&gt;
| [[Système d&#039;analyse de traces sportives]]&lt;br /&gt;
| HERQUE ERIC (Scrum Master), VACHERIAS GUILLAUME (Chef de projet)&lt;br /&gt;
| Vivien QUEMA&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]- [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-xxx-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 7&lt;br /&gt;
| [[Qualité de l&#039;Air et Santé des Populations]]&lt;br /&gt;
| BAUDEUR BERTRAND (Scrum Master), MERTENS GILLES (Chef)&lt;br /&gt;
| Marie-Laure AIX&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:Presentation_mi_parcours_qualite_air_baudeur_mertens.pdf|Presentation de mi-parcours]] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-xxx-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://github.com/Air-Quality-LoRa Dépot Git]&lt;br /&gt;
| [[Media:Presentation_mi_parcours_qualite_air_baudeur_mertens.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 8&lt;br /&gt;
| [[Artiphonie(saison 3)]] extension de la [[Artiphonie (saison 2)]]&lt;br /&gt;
| BUISINE JULIEN (Chef de Projet), ELHADJI TCHIAMBOU SAMI, LAMBERT DAPHNE (Scrum Master), LAMBERT PAUL&lt;br /&gt;
| Olivier Richard&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-xxx-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media: Artiphonie-Presentation_mi-parcours.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 9&lt;br /&gt;
| [[Quark Project]] &lt;br /&gt;
| CHALOYARD LUCAS, EL YANDOUZI ELIAS&lt;br /&gt;
| Olivier Gruber&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-xxx-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 10&lt;br /&gt;
| [[Jorigine]]&lt;br /&gt;
| BLANQUET ANTOINE (&#039;&#039;&#039;Scrum Master&#039;&#039;&#039;), LANQUETIN ALEXIS (&#039;&#039;&#039;Chef de projet&#039;&#039;&#039;), MALECOT ETHAN, PRAT-CAPILLA HUGO&lt;br /&gt;
| Sylvain Delangue&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-xxx-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 11&lt;br /&gt;
| [[Contributions open source au projet EdCampus|EdCampus]] &lt;br /&gt;
| ANDRIEUX LIAM, COSOTTI KEVIN, DREZET LUCAS (&#039;&#039;&#039;Chef de projet&#039;&#039;&#039;), REGOUIN ROMAN (&#039;&#039;&#039;Scrum Master&#039;&#039;&#039;)&lt;br /&gt;
| Anthony GEOURJON&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [https://air.imag.fr/images/c/ca/Soutenance_interm%C3%A9diaire_-_EDCampus_2021-2022.pdf Presentation de mi-parcours] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-xxx-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 12&lt;br /&gt;
| [[Contributions open source au projet LabnBook|LabnBook]] &lt;br /&gt;
| CIRSTEA PAUL, SOULARD	ALEXANDRE (Chef de projet), TONDEUX EMILIE (Scrum master), YUNG	KEVIN&lt;br /&gt;
| Anthony GEOURJON, Cédric DHAM&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-xxx-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:LabnBook.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 13&lt;br /&gt;
| [[Green collect]]&lt;br /&gt;
| BARET	DORIAN, CAMBUS QUENTIN (Chef de projet), JULIENNE MALONE, MALLEN GUILLAUME (Scrum master)&lt;br /&gt;
| Bernard TOURANCHEAU&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [https://github.com/GreenCollects/docs/blob/main/soutenance/Soutenance%20de%20mi-parcours.pdf Presentation de mi-parcours] - [[Media:Poster-xxx-fr.pdf|Poster FR]] - [[Media:Poster-xxx-en.pdf|Poster EN]] - [https://tontube.fr Pitch 180 secondes]&lt;br /&gt;
| [https://github.com/GreenCollects Dépot Git]&lt;br /&gt;
| [https://github.com/GreenCollects/docs/blob/main/soutenance/Soutenance%20de%20mi-parcours.pdf Presentation intermédiaire]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
Sujets non choisis&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
# [[LoRaWAN Roaming]] avec [[Chirpstack]], [[TheThingStack]] et [[Actility]] pour le projet [https://gricad-gitlab.univ-grenoble-alpes.fr/thingsat/public/-/blob/master/cubesat_mission/README.md Thingsat]: Didier DONSEZ, Olivier ALPHAND.&lt;br /&gt;
# [[Contributions logicielles au projet RIOT OS pour le New Space]] : Francois-Xavier MOLINA, Olivier ALPHAND, Didier DONSEZ&lt;br /&gt;
# [[Réseaux social d&#039;organisation de sortie (saison 2)]] refonte [[Réseaux social d&#039;organisation de sortie]], Olivier Richard&lt;br /&gt;
# [[Experiment Process Management]], Olivier Richard&lt;br /&gt;
# [[Language Server for Visual Studio]]: Olivier Gruber&lt;br /&gt;
# ABANDONNé [[Réseau d&#039;Alumni de formations]] (à confirmer), Gérard POLLIER ([https://disrupt-campus.univ-grenoble-alpes.fr/design-factory-grenoble/ Design Factory Grenoble])&lt;br /&gt;
# [[Evaluation du kit IA embarqué Wio Terminal]]: Louis CLOSSON, Didier DONSEZ (sous réserve de réception du matériel commandé)&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=File:PSP_Presentation.pdf&amp;diff=52122</id>
		<title>File:PSP Presentation.pdf</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=File:PSP_Presentation.pdf&amp;diff=52122"/>
		<updated>2022-02-07T11:47:25Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=Projets_2021-2022&amp;diff=52121</id>
		<title>Projets 2021-2022</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=Projets_2021-2022&amp;diff=52121"/>
		<updated>2022-02-07T11:46:55Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;&amp;lt;[[Projets 2020-2021]] | [[Projets]] | [[Projets 2022-2023]]&amp;gt;&amp;gt;&lt;br /&gt;
=INFO=&lt;br /&gt;
==INFO3==&lt;br /&gt;
&lt;br /&gt;
==INFO4==&lt;br /&gt;
===Projet Semestre S8===&lt;br /&gt;
&lt;br /&gt;
Enseignants responsables : Olivier Richard&lt;br /&gt;
&lt;br /&gt;
* Dates : Lundi après-midi, Mardi après-midi  &lt;br /&gt;
* Lancement: 10 Janvier 2021 après midi&lt;br /&gt;
* Soutenance à mi-parcours: A définir&lt;br /&gt;
* Soutenance: A définir&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;Evaluation à mi-parcours le lundi/mardi ???&#039;&#039;&#039;: Format: 10min (5min de présentation 3 slides au plus, 5min de discussion). Cette évaluation sera prise en compte dans la note finale.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Consignes générales:&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;Vous devez être pro-actifs !!!&#039;&#039;&#039;: Si des points sont pas ou mals spécifiés, vous le faîtes et vous justifiez vos choix. Pour les problèmes techniques éventuels vous pouvez: creuser la question, contacter l&#039;auteur du code si il y a lieu, écrire un rapport de bug (&#039;&#039;&#039;Attention:&#039;&#039;&#039; ca se prépare !), soumettre un patch/pull request, contacter l&#039;enseignant ou la personne référente du projet.&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;Vous devez maintenir une fiche de suivi de projet&#039;&#039;&#039;: elle doit être mise à jour chaque semaine, elle rassemble les élements essentiels du projet, elle indique les évolutions du projet et présente sa feuille de route. &#039;&#039;&#039;Note:&#039;&#039;&#039; le nom de la fiche doit être composé du nom du projet et suffixé par info4_2021_2022. &#039;&#039;&#039;Cette fiche compte pour la note finale&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;Votre code&#039;&#039;&#039; pour doit être hébergé sur le gitlab et à l&#039;URL suivante https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22 , vous utiliserez votre compte UGA.&lt;br /&gt;
&lt;br /&gt;
* Chaque projet doit avoir &#039;&#039;&#039;aux moins 2 dépôts git&#039;&#039;&#039;:&lt;br /&gt;
** &#039;&#039;&#039;Un pour les documents&#039;&#039;&#039; demandés rapport, présentation de pré-soutenante, de soutenance, flyer. &#039;&#039;&#039;Il sera appelé documents.&#039;&#039;&#039;&lt;br /&gt;
** Un ou plusieurs pour le code, les tests, les évaluations, les preuves de concept, la ou les documentations afférentes. &lt;br /&gt;
&lt;br /&gt;
* Les &#039;&#039;&#039;documents public doivent être rédigés en anglais (README, documentation, commentaires de code, nom de variables et de fonctions)&#039;&#039;&#039;.  Le *rapport* sera aussi demandé en *anglais* (il fera la taille d&#039;un rapport de TP). Les transparents des présentation peuvent être en anglais ou en francais, la soutenance sera taire en francais.&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;La note obtenue&#039;&#039;&#039; tiendra compte du &#039;&#039;&#039;nombre et de la qualité des commits&#039;&#039;&#039; observé dans &#039;&#039;&#039;vos dépots git et la branche master&#039;&#039;&#039; (or depot documents). La qualité comprend l&#039;intitulé du commit et son contenu. Les notes pourront être différentiées dans un groupe, il n&#039;est pas acceptable de pas avoir de commit dans le(s) dépôt(s) du projet (or dépôt documents).&lt;br /&gt;
&lt;br /&gt;
* Il est fortement conseillé de suivre un &#039;&#039;&#039;développement incrémental&#039;&#039;&#039; qui permette d&#039;avoir à tout moment un démonstrateur à présenter, un projet peut être constituer d&#039;une succession de &#039;&#039;&#039;démonstrateurs présentables séparément&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
* Vous devez faire aussi des &#039;&#039;&#039;schémas d&#039;architectures générales et/ou spéficiques, des diagrammes de séquence&#039;&#039;&#039;, et autre documents de spécification si nécessaire. Ces documents vous serviront de base de discussion/brainstorming interne ainsi que dans vos différents documents (rapport, présentations, documentation). Ces schémas sont avant tout conceptuels et techniques.&lt;br /&gt;
&lt;br /&gt;
===Propositions de projets S8===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
* 1. [https://codimd.math.cnrs.fr/s/B029qfT5Q Courriels à Suppression Programmée] : Michaël Périn&lt;br /&gt;
* 2. [[Firmwares open source pour une station de réception de satellites pour l’Internet des Objets isolés]], Didier DONSEZ.&lt;br /&gt;
* 3. [[Evaluation du toolkit AI de STM32 pour l&#039;analyse de l&#039;environnement sonore]] (Suite 2022), Didier DONSEZ.&lt;br /&gt;
* 4. [[Algorithmes de géolocalisation d’objets par TDOA (Time Difference of Arrival)]] (suite), Didier DONSEZ.&lt;br /&gt;
* 5. [[Dashboard pour Overwatch]] Olivier Richard&lt;br /&gt;
* 6. [[Application mobile d&#039;enregistrements de noeuds IoT LoRaWAN dans plusieurs réseaux]] (Suite) : Didier DONSEZ&lt;br /&gt;
* 7. [[Bluetooth 5.1 Angle of Arrival based Indoor Localization]] (Suite) : Didier DONSEZ&lt;br /&gt;
* 8. Intégration de composants de mesures environnementales (eau, air, ...) pour le [[Contribution au projet STM32Python|projet STM32Python]] à destination des lycéens: Didier DONSEZ&lt;br /&gt;
* 9. [[Air Quality Station]] (Suite) : Didier DONSEZ&lt;br /&gt;
* 10. [[Floating Water Quality Station]] : Didier DONSEZ, Nicolas PALIX&lt;br /&gt;
* 12. [[Testeur de terrain pour réseaux LoRaWAN privés et publics (TTN, CampusIoT et Helium)]] (suite 2021), Didier DONSEZ.&lt;br /&gt;
* 13. [[Géolocalition Indoor en LoRa 2.4GHz]], Didier DONSEZ.&lt;br /&gt;
* 14. [[RealWorld avec Dioxus]] (Rust + web), Olivier Richard&lt;br /&gt;
* 15. Poursuite projet 20-21 [[Rust Engine | Executeur de tâche en Rust]], Olivier Richard&lt;br /&gt;
* 16. Poursuite projet 20-21 [[Retrocompute simulateur | RetroComputing]]: (vintage style) Coupler le simulateur Digital avec un simulateur de processeur 8bits, Olivier Richard&lt;br /&gt;
* 17. Poursuite projet 19-20 [[Portail pour gestionnaire de taches]](react, Typescript), Olivier Richard&lt;br /&gt;
* 18. [[Paquets NIX pour Polytech]], Olivier Richard&lt;br /&gt;
* 19. [[Mini compilateur C pour mini CPU]], Olivier Richard&lt;br /&gt;
* 20. Mode jeu en réseau (Wifi/Bluetooth) pour [[TanksOfFreedom]], Nicolas Palix&lt;br /&gt;
&lt;br /&gt;
Non affecté&lt;br /&gt;
* xx. [[Bibliothèque de décodeurs standards et d&#039;afficheurs Grafana pour objets connectés LoRaWAN]] : Didier DONSEZ&lt;br /&gt;
* xx. [[ASAC|Agriculture connectée]] en partenariat avec les projets collectifs IESE/MAT : Nicolas Palix&lt;br /&gt;
* xx. [[Faults In Linux]], Nicolas Palix&lt;br /&gt;
&lt;br /&gt;
===Affectations===&lt;br /&gt;
{|class=&amp;quot;wikitable alternance&amp;quot;&lt;br /&gt;
|+ Affectation des projets INFO4 21-22&lt;br /&gt;
|-&lt;br /&gt;
|&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Sujet&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Etudiants&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Enseignant(s)&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Fiche de suivi&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Documents&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 1&lt;br /&gt;
| [[TODO]]&lt;br /&gt;
| CANIN CORENTIN,MONTEILLER JOSHUA,WAGNER SAM&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/01/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 2&lt;br /&gt;
| [[TODO]]&lt;br /&gt;
| CARMONA DAMIAN,DA COSTA TOM,WOZNY PIERRE-RAPHAE&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/02/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 3&lt;br /&gt;
| [[TODO]]&lt;br /&gt;
| BACH THOMAS,BARBE FLORENT,SIMO YOKAM GEORGES HARRISSO&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/03/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 5&lt;br /&gt;
| [[TODO]]&lt;br /&gt;
| CAILLES MAXIME,REYGNER ETIENNE,VERRIER MARTI&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/05/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 6&lt;br /&gt;
| [[TODO]]&lt;br /&gt;
| CHIOTTI MAEL,LAVIROTTE GAETAN,MOTTINO LORI&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/06/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 8&lt;br /&gt;
| [[TODO]]&lt;br /&gt;
| GUIRGUIS MIRETTE,HADIBY CHEMSSEDDINE,MOHSEN HACHE&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/08/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 10&lt;br /&gt;
| [[Floating Water Quality Station]]&lt;br /&gt;
| BRETON EMERIC,FAGHLOUMI AYMAN,VIALLET CAMILLE&lt;br /&gt;
| Didier DONSEZ, Nicolas PALIX&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/10/docs/-/blob/main/info4_2021_2022_Fiche_suivi_projet.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 13&lt;br /&gt;
| [[TODO]]&lt;br /&gt;
| BERNERD CLARA,JARDIN BAPTISTE,NGUYEN JUSTI&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/13/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 14&lt;br /&gt;
| [[TODO]]&lt;br /&gt;
| IFAKIREN SAMI,MONTHE DJEUMOU BRICE,NGUYEN CLEMEN&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/14/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 15&lt;br /&gt;
| [[TODO]]&lt;br /&gt;
| CHAPPAZ FLORIAN,DE OLIVEIRA VALENTIN,KURKLU FIKRE&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/15/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 17&lt;br /&gt;
| [[TODO]]&lt;br /&gt;
| KACHA TOM,MAHAMAN NOURY ABDOURAHAMANE,MEIGNEN HUGO,ZHANG KEMIN&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/17/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 18&lt;br /&gt;
| [[Paquets NIX pour Polytech]]&lt;br /&gt;
| CONJARD SAMUEL,FODOR GERGELY,PELISSE-VERDOUX CYPRIEN&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/18/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 19&lt;br /&gt;
| [[TODO]]&lt;br /&gt;
| CAPET THEO,POITEVIN EVE,ROYET JULIA&lt;br /&gt;
| TODO&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/19/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 20&lt;br /&gt;
| Mode jeu en réseau pour [[TanksOfFreedom]],&lt;br /&gt;
| ABECASSIS THOMAS,FOURNIER THOMAS,ZAFFUTO LUCA&lt;br /&gt;
| Nicolas Palix&lt;br /&gt;
| [https://gricad-gitlab.univ-grenoble-alpes.fr/Projets-INFO4/21-22/20/docs/README.md Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
|-&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
==INFO5==&lt;br /&gt;
===Projet IoT S9===&lt;br /&gt;
Enseignants responsables : Bernard Tourancheau&lt;br /&gt;
&lt;br /&gt;
Calendrier:  Octobre à Décembre 2021. Soutenance 24 Janvier 2022.&lt;br /&gt;
&lt;br /&gt;
{|class=&amp;quot;wikitable alternance&amp;quot;&lt;br /&gt;
|+ Choix des projet des projets INFO5 Réseaux 21-22&lt;br /&gt;
|-&lt;br /&gt;
|&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Sujet&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Etudiants&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Documents&lt;br /&gt;
!scope=&amp;quot;col&amp;quot;| Github/Trello&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 1&lt;br /&gt;
| [[Réseau de capteur de dichlorométhane]]&lt;br /&gt;
| Dorian BARET - Malone JULIENNE - Quentin CAMBUS&lt;br /&gt;
| [https://lesjoiesducode.fr/quand-notre-revue-de-sprint-se-passe-nickel Fiche]&lt;br /&gt;
| [https://github.com/Cambus-Quentin/DichloWan2021/blob/main/README.md git]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 2&lt;br /&gt;
| [[Création d&#039;un système pour localiser les élèves lors de courses d&#039;orientation]]&lt;br /&gt;
| Antoine Gitton, Gilles Mertens, Bertrand Baudeur&lt;br /&gt;
| [[Media:2021_2022_INFO5_IOT_Orientation_spec.pdf|Spécification paquets LoRa]]&lt;br /&gt;
| [[Media:2021_2022_INFO5_IOT_Orientation_backend.zip|Souces back-end]] - [[Media:2021_2022_INFO5_IOT_Orientation_carte.zip|Souces carte]]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 3&lt;br /&gt;
| [[Harnais animalier permettant de suivre notre animal domestique]]&lt;br /&gt;
| Sami ELHADJI TCHIAMBOU, Corentin HUMBERT, Paul LAMBERT, Hugo PRAT CAPILLA&lt;br /&gt;
| [[Media:PSP_Presentation.pdf|Présentation finale]]&lt;br /&gt;
| [https://github.com/Bicorpro Organisation GitHub]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 4&lt;br /&gt;
| [[Géolocalisation et suivi des transports en commun]]&lt;br /&gt;
| Liam ANDRIEUX, Lucas DREZET, Roman REGOUIN&lt;br /&gt;
|&lt;br /&gt;
| [https://github.com/2021-2022-IoT-INFO5-G4 Organisation GitHub]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 5&lt;br /&gt;
| [[Tracking des déplacements de joueurs sur un terrain]]&lt;br /&gt;
| Elias EL YANDOUZI, Lucas CHALOYARD&lt;br /&gt;
| [[Media:IOT_Presentation.pdf|Présentation finale]]&lt;br /&gt;
| [https://github.com/Indoor-Shadow/ble-experiment Github Repo]&lt;br /&gt;
|-&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 6&lt;br /&gt;
| [[Beer Pong connecté]]&lt;br /&gt;
| Yael PARA, Théo TEYSSIER, Victor MALOD, Alexis LANQUETIN&lt;br /&gt;
|&lt;br /&gt;
|&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
Exposés points techniques 10&#039; - questions 5&#039;&lt;br /&gt;
* Nom Sujet&lt;br /&gt;
* ??? Python&lt;br /&gt;
* ??? MQTT&lt;br /&gt;
* ??? COAP&lt;br /&gt;
* 26/11/2021 - Elias El Yandouzi - Les différentes techniques de virtualisation&lt;br /&gt;
&lt;br /&gt;
===Projet Semestre S10===&lt;br /&gt;
&lt;br /&gt;
Enseignant responsable : [[user:Donsez|Didier Donsez]]&lt;br /&gt;
&lt;br /&gt;
Convention des projets tutorés externes : Elise Didier.&lt;br /&gt;
&lt;br /&gt;
Calendrier: 27/01 (8H30-12H00) au 18/03.&lt;br /&gt;
&lt;br /&gt;
Séances de Management de projets innovants: A voir dessus.&lt;br /&gt;
&lt;br /&gt;
Réunion de présentation et choix des sujets: 27/01 (8H30-12H00) en salle Polygone P206 (voir ADE)&lt;br /&gt;
&lt;br /&gt;
Démarrage : 27/01&lt;br /&gt;
&lt;br /&gt;
Soutenance à mi-parcours (à définir) : ??/02/2021 13H30-17H30 en distantiel (15 minutes par équipe).&lt;br /&gt;
&lt;br /&gt;
Soutenance finale : 18/03/2021 (8H30-12H00 et 13H30-17H00). 30 minutes par équipe, questions/réponses et démonstration incluse. Prière de rapporter au fablab le matériel emprunté juste après votre soutenance. &lt;br /&gt;
&lt;br /&gt;
====Séances MPI====&lt;br /&gt;
&lt;br /&gt;
Voir ADE qui fait foi).&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Soutenance intermédiaire S10 ====&lt;br /&gt;
Date (à définir): ??/02 Après midi. Distantiel (sur Zoom).&lt;br /&gt;
&lt;br /&gt;
L&#039;objectif de la soutenance intermédiaire est de vérifier si l&#039;équipe projet est en bon ordre de marche. La présence du porteur n&#039;est pas obligatoire. Prévoyez du temps pour les questions-réponses (5 minutes max).&lt;br /&gt;
&lt;br /&gt;
L&#039;équipe présentera en 5-6 transparents en 8 minutes.&lt;br /&gt;
* les équipiers et leurs rôles&lt;br /&gt;
* le contexte, le sujet et l&#039;objectif du projet&lt;br /&gt;
* l&#039;architecture du systèmes à réaliser&lt;br /&gt;
* les technologies utilisées&lt;br /&gt;
* le plan de travail (backlog, planning, ce qui est fait, ce qu&#039;il reste à faire ...)&lt;br /&gt;
* les difficultés (s&#039;il y a)&lt;br /&gt;
&lt;br /&gt;
Respectez bien les créneaux indiqués (par respect pour les autres équipes).&lt;br /&gt;
&lt;br /&gt;
==== Soutenance finale S10 ====&lt;br /&gt;
Date provisoire: 18/03/2022 (8H30-12H00 et 13H30-17H00).&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;La présence du(des) porteur(s) est obligatoire. Pensez à les prévenir bien à l&#039;avance&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Durée: 30 minutes par équipe: présentation, questions/réponses et démonstration incluse.&lt;br /&gt;
&lt;br /&gt;
Les documents devront être en ligne sur le wiki (colonne Documents) la veille (ie avant le ??/03/2021 23:59:59 CET).&lt;br /&gt;
&lt;br /&gt;
La présentation est constituée des chapitres suivants:&lt;br /&gt;
* Rappel du sujet/besoin et cahier des charges&lt;br /&gt;
* Technologies employées&lt;br /&gt;
* Architecture techniques&lt;br /&gt;
* Réalisations techniques&lt;br /&gt;
* Gestion de projet (méthode, planning prévisionnel et effectif, gestion des risques, rôles des membres ...)&lt;br /&gt;
* Outils (collaboration, CD/CI ...)&lt;br /&gt;
* Métriques logiciels : lignes de code, langages, performance, temps ingénieur (d&#039;après vos journaux), la répartition  des lignes de code et des commits en pourcentage entre les membres du projet ...)&lt;br /&gt;
* Conclusion (Retour d&#039;expérience)&lt;br /&gt;
* Transparent expliquant la démonstration&lt;br /&gt;
&lt;br /&gt;
L&#039;ensemble des documents doit être accessible depuis le tableau ci-dessus et dans chaque fiche de suivi.&lt;br /&gt;
&lt;br /&gt;
Le screencast (réalisé lors de la dernière répétition) sera rendu disponible via un partage caché (wetransfer, google drive …) dont le lien sera ajouté dans le devoir idoine sur Moodle et également envoyé par mail à votre tuteur.&lt;br /&gt;
&lt;br /&gt;
Le rapport final contient les mêmes chapitres que la présentation ainsi qu&#039;un glossaire et une bibliographie. Le rapport ne doit pas dépasser 15 pages (schémas et figures compris). Vous pourrez référencer les autres documents que vous avez produits au cours du projet (spécifications détaillées, algorithmes, conception d&#039;écrans ...).&lt;br /&gt;
&lt;br /&gt;
Le rapport final est au format Markdown et doit être placé dans un des dépôts Git de votre groupe/organisation.&lt;br /&gt;
&lt;br /&gt;
NB: le rapport technique listé dans la colonne Documents contient tout ce qui ne tient pas dans les 15 pages du rapport final : cahier des charges, diagrammes UML, enquêtes utilisateurs design UI, API, technologies employées (détail), plan de tests, term of services, conformance RPGD, audits/diagnostiques sécurité, MTBR, rapport de vulnérabilité, plan de charge, rapports de charge, manuel d&#039;installation …  : ça dépend un peu de la nature de votre projet.&lt;br /&gt;
&lt;br /&gt;
Conseil : 30 minutes c&#039;est très court alors répétez la soutenance auparavant ! Prévoyez des transparents supplémentaires en annexe pour répondre aux questions.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Prière de rapporter au fablab le matériel emprunté juste après votre soutenance&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
==== Affectations S10====&lt;br /&gt;
{|class=&amp;quot;wikitable alternance&amp;quot;&lt;br /&gt;
 |+ Affectation des projets INFO5 2021-2022&lt;br /&gt;
 |-&lt;br /&gt;
 |&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Sujet&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Etudiants&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Porteur(s)&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Fiche de suivi&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Documents&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Dépôt Git&lt;br /&gt;
 !scope=&amp;quot;col&amp;quot;| Soutenance intermédiaire&lt;br /&gt;
 |-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 1&lt;br /&gt;
| [[Test d&#039;infrastructures avec NixOS]]&lt;br /&gt;
| HUMBERT CORENTIN, MINIER MANCINI TITOUAN (Chef de projet), SUEUR CORENTIN (Scrum master)&lt;br /&gt;
| Olivier RICHARD et Quentin GUILLETEAU&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 2&lt;br /&gt;
| [[Plan dynamique d’un appartement connecté]]&lt;br /&gt;
| GRANGER OSCAR, NOERIE SOPHIE, SARRE MARGAUX, SALMON AMAD, TEYSSIER THEO&lt;br /&gt;
| Sybille CAFFIAU&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 3&lt;br /&gt;
| [[Suivi de troupeaux (ovins, bovins) en zone montagneuse avec un réseau LoRaWAN : expérimentation dans la Matheysine]]&lt;br /&gt;
| GITTON ANTOINE, MALOD VICTOR, MUTEL MATHIS&lt;br /&gt;
| Fabrice FOREST&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 4&lt;br /&gt;
| [[FitSize]]&lt;br /&gt;
| GEITNER TEVA	, GONZALEZ JULES, PARA YAEL&lt;br /&gt;
| Fidèle Eya&#039;a&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 5&lt;br /&gt;
| [[GenderedNews]]&lt;br /&gt;
| AGUIAR MATHILDE (Chef de projet), HAJJI OUMAIMA (SCRUM Master), SIDIBE ROKIATOU DITE ROSE&lt;br /&gt;
| François PORTET, Gilles BASTIN, Ange RICHARD&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 6&lt;br /&gt;
| [[Système d&#039;analyse de traces sportives]]&lt;br /&gt;
| HERQUE ERIC (Scrum Master), VACHERIAS GUILLAUME (Chef de projet)&lt;br /&gt;
| Vivien QUEMA&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 7&lt;br /&gt;
| [[Qualité de l&#039;Air et Santé des Populations]]&lt;br /&gt;
| BAUDEUR BERTRAND (Scrum Master), MERTENS GILLES (Chef)&lt;br /&gt;
| Marie-Laure AIX&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 8&lt;br /&gt;
| [[Artiphonie(saison 3)]] extension de la [[Artiphonie (saison 2)]]&lt;br /&gt;
| BUISINE JULIEN, ELHADJI TCHIAMBOU SAMI, LAMBERT DAPHNE (Scrum Master), LAMBERT PAUL&lt;br /&gt;
| Olivier Richard&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 9&lt;br /&gt;
| [[Quark Project]] &lt;br /&gt;
| CHALOYARD LUCAS, EL YANDOUZI ELIAS&lt;br /&gt;
| Olivier Gruber&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 10&lt;br /&gt;
| [[Jorigine]]&lt;br /&gt;
| BLANQUET ANTOINE (&#039;&#039;&#039;Scrum Master&#039;&#039;&#039;), LANQUETIN ALEXIS (&#039;&#039;&#039;Chef de projet&#039;&#039;&#039;), MALECOT ETHAN, PRAT-CAPILLA HUGO&lt;br /&gt;
| Sylvain Delangue&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 11&lt;br /&gt;
| [[Contributions open source au projet EdCampus|EdCampus]] &lt;br /&gt;
| ANDRIEUX LIAM, COSOTTI KEVIN, DREZET LUCAS (&#039;&#039;&#039;Chef de projet&#039;&#039;&#039;), REGOUIN ROMAN (&#039;&#039;&#039;Scrum Master&#039;&#039;&#039;)&lt;br /&gt;
| Anthony GEOURJON&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 12&lt;br /&gt;
| [[Contributions open source au projet LabnBook|LabnBook]] &lt;br /&gt;
| CIRSTEA PAUL, SOULARD	ALEXANDRE (Chef de projet), TONDEUX EMILIE (Scrum master), YUNG	KEVIN&lt;br /&gt;
| Anthony GEOURJON, Cédric DHAM&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
| [https://git/xxx Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
!scope=&amp;quot;row&amp;quot;| 13&lt;br /&gt;
| [[Green collect]]&lt;br /&gt;
| BARET	DORIAN, CAMBUS QUENTIN (Chef de projet), JULIENNE MALONE, MALLEN GUILLAUME (Scrum master)&lt;br /&gt;
| Bernard TOURANCHEAU&lt;br /&gt;
| [XXXX Fiche]&lt;br /&gt;
| [[Media:xxx.pdf|Rapport final]] - [[Media:xxx.pdf|Presentation finale FR]] - [[Media:xxx.pdf|Final Presentation EN]] - [[Media:xxx.pdf|Flyer]] - [[Media:xxx.pdf|Presentation de mi-parcours]]&lt;br /&gt;
| [https://github.com/malleng/Projet_S10 Dépot Git]&lt;br /&gt;
| [[Media:xxx.pdf|Presentation intermédiaire]]&lt;br /&gt;
|-&lt;br /&gt;
&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
Sujets non choisis&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
# [[LoRaWAN Roaming]] avec [[Chirpstack]], [[TheThingStack]] et [[Actility]] pour le projet [https://gricad-gitlab.univ-grenoble-alpes.fr/thingsat/public/-/blob/master/cubesat_mission/README.md Thingsat]: Didier DONSEZ, Olivier ALPHAND.&lt;br /&gt;
# [[Contributions logicielles au projet RIOT OS pour le New Space]] : Francois-Xavier MOLINA, Olivier ALPHAND, Didier DONSEZ&lt;br /&gt;
# [[Réseaux social d&#039;organisation de sortie (saison 2)]] refonte [[Réseaux social d&#039;organisation de sortie]], Olivier Richard&lt;br /&gt;
# [[Experiment Process Management]], Olivier Richard&lt;br /&gt;
# [[Language Server for Visual Studio]]: Olivier Gruber&lt;br /&gt;
# ABANDONNé [[Réseau d&#039;Alumni de formations]] (à confirmer), Gérard POLLIER ([https://disrupt-campus.univ-grenoble-alpes.fr/design-factory-grenoble/ Design Factory Grenoble])&lt;br /&gt;
# [[Evaluation du kit IA embarqué Wio Terminal]]: Louis CLOSSON, Didier DONSEZ (sous réserve de réception du matériel commandé)&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=File:VT2021_Merkle_Trees_presentation.pdf&amp;diff=51758</id>
		<title>File:VT2021 Merkle Trees presentation.pdf</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=File:VT2021_Merkle_Trees_presentation.pdf&amp;diff=51758"/>
		<updated>2021-12-13T16:23:30Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: Corentin.Humbert uploaded a new version of File:VT2021 Merkle Trees presentation.pdf&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Summary ==&lt;br /&gt;
Merke Trees presentation by Corentin Humbert and Kevin Yung&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51738</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51738"/>
		<updated>2021-12-13T13:29:25Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des [https://fr.wikipedia.org/wiki/Arbre_binaire arbres binaires] utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants. Chaque arbre est unique et une donnée donnera toujours le même arbre. On retrouvera typiquement les arbres de Merkle lorsqu&#039;on voudra faire du téléchargement de fichiers sur un réseau [https://fr.wikipedia.org/wiki/Pair-%C3%A0-pair pair-à-pair]. Comme on ne peut pas vérifier l&#039;identité des machines participant à l&#039;envoi de fichier, il est indispensable de mettre en place une structure de vérification comme les arbres de Merkle pour s&#039;assurer que les données reçues correspondent bien à celles désirées.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé :&#039;&#039;&#039; arbres de Merkle, arbres binaires, hachage, structure de données, validation, pair à pair&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle trees are [https://en.wikipedia.org/wiki/Binary_tree binary trees] used in data validation. A tree consists of nodes and leaves. The leaves contain the cryptographic hash corresponding to a part of the data we want to validate. The nodes contain a hash obtained by concatenating the hashes of the two child nodes and passing the concatenated string through a hashing function. This overall process creates a dependance between the nodes where each node&#039;s hash depends on the hash values of the underlying nodes. Each Merkle tree is unique and specific data will always give the same tree. A common use for Merkle trees is the download of files in [https://en.wikipedia.org/wiki/Peer-to-peer peer-to-peer] networks. As it is impossible to verify the identity of machines in the network, it is necessary to use validation structures such as Merkle trees to ensure that the received data is the desired one.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords:&#039;&#039;&#039; Merkle trees, binary trees, hash, data structure, validation, peer to peer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier dans un réseau pair-à-pair, comme on ne peut pas vérifier l&#039;identité des machines sur le réseau, il est fort probable que certaines d&#039;entre elles tentent d&#039;envoyer des fichiers malveillants. Il faudrait donc mettre en place un mécanisme permettant d&#039;identifier ces fichiers non désirés. Les arbres de Merkle sont une solution à ce problème. Un arbre de Merkle est un arbre binaire qui va permettre d&#039;identifier de manière unique et sûre une ressource sur un réseau.&lt;br /&gt;
&lt;br /&gt;
Une fois qu&#039;une donnée aura été mise en ligne sur un réseau pair-à-pair, on va la découper en plusieurs blocs et calculer les hachages pour chacun des blocs. Ces hachages de premier niveau vont constituer les feuilles de l&#039;arbre de Merkle. Les feuilles vont ensuite être fusionnées deux à deux pour former un parent commun avec un hachage différent, et ce même parent va fusionner avec son voisin de la même manière et réitérer le processus jusqu&#039;à obtenir la racine de l&#039;arbre contenant le hachage unique qui va permettre d&#039;identifier la donnée dans son intégrité.&lt;br /&gt;
&lt;br /&gt;
La racine de l&#039;arbre servant d&#039;identifiant pour la donnée va être une manière fiable et rapide de rechercher la donnée sur le réseau. La racine va également servir à vérifier que la donnée téléchargée correspondant bien à la donnée désirée. Cela solutionne le problème initial puisque même si nous ne pouvons pas vérifier l&#039;identité des machines, nous sommes en mesure de déterminer si la donnée reçue correspond bien à celle voulue.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Diagramme représentant la structure générique d&#039;un arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-contre (&#039;&#039;&#039;figure 1&#039;&#039;&#039;) contient l&#039;arbre de Merkle d&#039;une donnée découpée en quatre blocs (Data Nodes). Juste au-dessus des blocs, on retrouve les feuilles de l&#039;arbre (Merkle leaves) contenant les hachages des blocs. Encore au-dessus, on va retrouver les nœuds intermédiaires (Merkle branches) qui correspondent à la fusion des deux hachages du niveau précédent. Enfin, tout en haut, on retrouve la racine de l&#039;arbre (Merkle root) qui contient le hachage final servant à identifier la donnée.&lt;br /&gt;
&lt;br /&gt;
Dans la suite de ce document, nous allons présenter plus en détails les arbres de Merkle et expliquer leur fonctionnement ainsi que leurs domaines d&#039;applications. Nous commencerons par introduire les fonctions de hachage et par décrire leur fonctionnement général ainsi que leurs avantages et désavantages. Ensuite, nous expliquerons le processus de construction d&#039;un arbre de Merkle et tous les différents scénarios qui peuvent altérer la façon dont l&#039;arbre va être construit. Nous enchaînerons ensuite sur la partie validation avec un exemple concret. Enfin, nous parlerons de différentes implémentations des arbres de Merkle dans des infrastructures réelles telles que la sécurité des transactions des cryptomonnaies.&lt;br /&gt;
&lt;br /&gt;
Commençons sans plus attendre par faire un point sur le hachage !&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;arbre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;arbre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les arbres de Merkel étaient construits, mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire ? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;arbre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un arbre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant-dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable, car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un arbre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quel que soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on dupliquait les nœuds impairs et les fusionnait avec eux-mêmes est notable puisqu&#039;ici, on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau, mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;arbre a une structure un peu bizarre; on a deux niveaux de feuilles. Exécutons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commençant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précèdent vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds, mais quatre : Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seconde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour les construire. Toutefois, nous n&#039;avons pas encore vu comment les utiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données, mais nous n&#039;avons pas encore détaillé comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple : on veut télécharger un fichier en utilisant un réseau pair à pair. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré, mais à une multitude de machines dans un réseau qui vont participer au téléchargement. On dispose du hachage unique permettant d&#039;identifier le fichier, ce hachage nous a été envoyé par une machine connue à laquelle on fait confiance. Le hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage, et les machines du réseau vont s&#039;occuper de nous envoyer les blocs de données. À ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de le vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine de l&#039;arbre reconstruit est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non-légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque nœud dépend des nœuds qui le précèdent, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hachage des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Cryptomonnaie ===&lt;br /&gt;
&lt;br /&gt;
La cryptomonnaie a été très popularisée récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de cryptomonnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La cryptomonnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocs contiennent un ID, qui correspond à l&#039;en-tête fields haché (cf. image), et au sein de cet en-tête haché, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet des cryptomonnaies, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380 Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non-critiques de l&#039;espace de stockage. Les nœuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque nœud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles comme les transactions utilisées, ne laissant que les branches contenant les hachages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données clé-valeur NoSQL, entièrement managée et serverless qui est conçue pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque nœuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc surveiller la moindre différence et de repérer l&#039;endroit divergent.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficiles à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préférera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Fonction de hachage&amp;quot;&#039;&#039;&#039;, Wikipedia, https://fr.wikipedia.org/wiki/Fonction_de_hachage&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=File:VT2021_Merkle_Trees_presentation.pdf&amp;diff=51737</id>
		<title>File:VT2021 Merkle Trees presentation.pdf</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=File:VT2021_Merkle_Trees_presentation.pdf&amp;diff=51737"/>
		<updated>2021-12-13T13:26:27Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: Merke Trees presentation by Corentin Humbert and Kevin Yung&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Summary ==&lt;br /&gt;
Merke Trees presentation by Corentin Humbert and Kevin Yung&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51726</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51726"/>
		<updated>2021-12-13T10:42:32Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des [https://fr.wikipedia.org/wiki/Arbre_binaire arbres binaires] utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants. Chaque arbre est unique et une donnée donnera toujours le même arbre. On retrouvera typiquement les arbres de Merkle lorsqu&#039;on voudra faire du téléchargement de fichiers sur un réseau [https://fr.wikipedia.org/wiki/Pair-%C3%A0-pair pair-à-pair]. Comme on ne peut pas vérifier l&#039;identité des machines participant à l&#039;envoi de fichier, il est indispensable de mettre en place une structure de vérification comme les arbres de Merkle pour s&#039;assurer que les données reçues correspondent bien à celles désirées.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé :&#039;&#039;&#039; arbres de Merkle, arbres binaires, hachage, structure de données, validation, pair à pair&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle trees are [https://en.wikipedia.org/wiki/Binary_tree binary trees] used in data validation. A tree consists of nodes and leaves. The leaves contain the cryptographic hash corresponding to a part of the data we want to validate. The nodes contain a hash obtained by concatenating the hashes of the two child nodes and passing the concatenated string through a hashing function. This overall process creates a dependance between the nodes where each node&#039;s hash depends on the hash values of the underlying nodes. Each Merkle tree is unique and specific data will always give the same tree. A common use for Merkle trees is the download of files in [https://en.wikipedia.org/wiki/Peer-to-peer peer-to-peer] networks. As it is impossible to verify the identity of machines in the network, it is necessary to use validation structures such as Merkle trees to ensure that the received data is the desired one.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords:&#039;&#039;&#039; Merkle trees, binary trees, hash, data structure, validation, peer to peer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier dans un réseau pair-à-pair, comme on ne peut pas vérifier l&#039;identité des machines sur le réseau, il est fort probable que certaines d&#039;entre elles tentent d&#039;envoyer des fichiers malveillants. Il faudrait donc mettre en place un mécanisme permettant d&#039;identifier ces fichiers non désirés. Les arbres de Merkle sont une solution à ce problème. Un arbre de Merkle est un arbre binaire qui va permettre d&#039;identifier de manière unique et sûre une ressource sur un réseau.&lt;br /&gt;
&lt;br /&gt;
Une fois qu&#039;une donnée aura été mise en ligne sur un réseau pair-à-pair, on va la découper en plusieurs blocs et calculer les hachages pour chacun des blocs. Ces hachages de premier niveau vont constituer les feuilles de l&#039;arbre de Merkle. Les feuilles vont ensuite être fusionnées deux à deux pour former un parent commun avec un hachage différent, et ce même parent va fusionner avec son voisin de la même manière et réitérer le processus jusqu&#039;à obtenir la racine de l&#039;arbre contenant le hachage unique qui va permettre d&#039;identifier la donnée dans son intégrité.&lt;br /&gt;
&lt;br /&gt;
La racine de l&#039;arbre servant d&#039;identifiant pour la donnée va être une manière fiable et rapide de rechercher la donnée sur le réseau. La racine va également servir à vérifier que la donnée téléchargée correspondant bien à la donnée désirée. Cela solutionne le problème initial puisque même si nous ne pouvons pas vérifier l&#039;identité des machines, nous sommes en mesure de déterminer si la donnée reçue correspond bien à celle voulue.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Diagramme représentant la structure générique d&#039;un arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-contre (&#039;&#039;&#039;figure 1&#039;&#039;&#039;) contient l&#039;arbre de Merkle d&#039;une donnée découpée en quatre blocs (Data Nodes). Juste au-dessus des blocs, on retrouve les feuilles de l&#039;arbre (Merkle leaves) contenant les hachages des blocs. Encore au-dessus, on va retrouver les nœuds intermédiaires (Merkle branches) qui correspondent à la fusion des deux hachages du niveau précédent. Enfin, tout en haut, on retrouve la racine de l&#039;arbre (Merkle root) qui contient le hachage final servant à identifier la donnée.&lt;br /&gt;
&lt;br /&gt;
Dans la suite de ce document, nous allons présenter plus en détails les arbres de Merkle et expliquer leur fonctionnement ainsi que leurs domaines d&#039;applications. Nous commencerons par introduire les fonctions de hachage et par décrire leur fonctionnement général ainsi que leurs avantages et désavantages. Ensuite, nous expliquerons le processus de construction d&#039;un arbre de Merkle et tous les différents scénarios qui peuvent altérer la façon dont l&#039;arbre va être construit. Nous enchaînerons ensuite sur la partie validation avec un exemple concret. Enfin, nous parlerons de différentes implémentations des arbres de Merkle dans des infrastructures réelles telles que la sécurité des transactions des cryptomonnaies.&lt;br /&gt;
&lt;br /&gt;
Commençons sans plus attendre par faire un point sur le hachage !&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;arbre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;arbre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les arbres de Merkel étaient construits, mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire ? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;arbre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un arbre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant-dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable, car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un arbre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quel que soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on dupliquait les nœuds impairs et les fusionnait avec eux-mêmes est notable puisqu&#039;ici, on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau, mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;arbre a une structure un peu bizarre; on a deux niveaux de feuilles. Exécutons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commençant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précèdent vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds, mais quatre : Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seconde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour les construire. Toutefois, nous n&#039;avons pas encore vu comment les utiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données, mais nous n&#039;avons pas encore détaillé comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple : on veut télécharger un fichier en utilisant un réseau pair à pair. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré, mais à une multitude de machines dans un réseau qui vont participer au téléchargement. On dispose du hachage unique permettant d&#039;identifier le fichier, ce hachage nous a été envoyé par une machine connue à laquelle on fait confiance. Le hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage, et les machines du réseau vont s&#039;occuper de nous envoyer les blocs de données. À ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de le vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine de l&#039;arbre reconstruit est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non-légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque nœud dépend des nœuds qui le précèdent, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hachage des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Cryptomonnaie ===&lt;br /&gt;
&lt;br /&gt;
La cryptomonnaie a été très popularisée récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de cryptomonnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La cryptomonnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocs contiennent un ID, qui correspond à l&#039;en-tête fields haché (cf. image), et au sein de cet en-tête haché, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet des cryptomonnaies, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380 Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non-critiques de l&#039;espace de stockage. Les nœuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque nœud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles comme les transactions utilisées, ne laissant que les branches contenant les hachages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données clé-valeur NoSQL, entièrement managée et serverless qui est conçue pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque nœuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc surveiller la moindre différence et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficiles à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préférera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Fonction de hachage&amp;quot;&#039;&#039;&#039;, Wikipedia, https://fr.wikipedia.org/wiki/Fonction_de_hachage&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51719</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51719"/>
		<updated>2021-12-13T10:28:27Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des [https://fr.wikipedia.org/wiki/Arbre_binaire arbres binaires] utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants. Chaque arbre est unique et une donnée donnera toujours le même arbre. On retrouvera typiquement les arbres de Merkle lorsqu&#039;on voudra faire du téléchargement de fichiers sur un réseau [https://fr.wikipedia.org/wiki/Pair-%C3%A0-pair pair-à-pair]. Comme on ne peut pas vérifier l&#039;identité des machines participant à l&#039;envoi de fichier, il est indispensable de mettre en place une structure de vérification comme les arbres de Merkle pour s&#039;assurer que les données reçues correspondent bien à celles désirées.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé :&#039;&#039;&#039; arbres de Merkle, arbres binaires, hachage, structure de données, validation, pair à pair&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle trees are [https://en.wikipedia.org/wiki/Binary_tree binary trees] used in data validation. A tree consists of nodes and leaves. The leaves contain the cryptographic hash corresponding to a part of the data we want to validate. The nodes contain a hash obtained by concatenating the hashes of the two child nodes and passing the concatenated string through a hashing function. This overall process creates a dependance between the nodes where each node&#039;s hash depends on the hash values of the underlying nodes. Each Merkle tree is unique and specific data will always give the same tree. A common use for Merkle trees is the download of files in [https://en.wikipedia.org/wiki/Peer-to-peer peer-to-peer] networks. As it is impossible to verify the identity of machines in the network, it is necessary to use validation structures such as Merkle trees to ensure that the received data is the desired one.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords:&#039;&#039;&#039; Merkle trees, binary trees, hash, data structure, validation, peer to peer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier dans un réseau pair-à-pair, comme on ne peut pas vérifier l&#039;identité des machines sur le réseau, il est fort probable que certaines d&#039;entre elles tentent d&#039;envoyer des fichiers malveillants. Il faudrait donc mettre en place un mécanisme permettant d&#039;identifier ces fichiers non désirés. Les arbres de Merkle sont une solution à ce problème. Un arbre de Merkle est un arbre binaire qui va permettre d&#039;identifier de manière unique et sûre une ressource sur un réseau.&lt;br /&gt;
&lt;br /&gt;
Une fois qu&#039;une donnée aura été mise en ligne sur un réseau pair-à-pair, on va la découper en plusieurs blocs et calculer les hachages pour chacun des blocs. Ces hachages de premier niveau vont constituer les feuilles de l&#039;arbre de Merkle. Les feuilles vont ensuite être fusionnées deux à deux pour former un parent commun avec un hachage différent, et ce même parent va fusionner avec son voisin de la même manière et réitérer le processus jusqu&#039;à obtenir la racine de l&#039;arbre contenant le hachage unique qui va permettre d&#039;identifier la donnée dans son intégrité.&lt;br /&gt;
&lt;br /&gt;
La racine de l&#039;arbre servant d&#039;identifiant pour la donnée va être une manière fiable et rapide de rechercher la donnée sur le réseau. La racine va également servir à vérifier que la donnée téléchargée correspondant bien à la donnée désirée. Cela solutionne le problème initial puisque même si nous ne pouvons pas vérifier l&#039;identité des machines, nous sommes en mesure de déterminer si la donnée reçue correspond bien à celle voulue.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Diagramme représentant la structure générique d&#039;un arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-contre (&#039;&#039;&#039;figure 1&#039;&#039;&#039;) contient l&#039;arbre de Merkle d&#039;une donnée découpée en quatre blocs (Data Nodes). Juste au-dessus des blocs, on retrouve les feuilles de l&#039;arbre (Merkle leaves) contenant les hachages des blocs. Encore au-dessus, on va retrouver les nœuds intermédiaires (Merkle branches) qui correspondent à la fusion des deux hachages du niveau précédent. Enfin, tout en haut, on retrouve la racine de l&#039;arbre (Merkle root) qui contient le hachage final servant à identifier la donnée.&lt;br /&gt;
&lt;br /&gt;
Dans la suite de ce document, nous allons présenter plus en détails les arbres de Merkle et expliquer leur fonctionnement ainsi que leurs domaines d&#039;applications. Nous commencerons par introduire les fonctions de hachage et par décrire leur fonctionnement général ainsi que leurs avantages et désavantages. Ensuite, nous expliquerons le processus de construction d&#039;un arbre de Merkle et tous les différents scénarios qui peuvent altérer la façon dont l&#039;arbre va être construit. Nous enchaînerons ensuite sur la partie validation avec un exemple concret. Enfin, nous parlerons de différentes implémentations des arbres de Merkle dans des infrastructures réelles telles que la sécurité des transactions des cryptomonnaies.&lt;br /&gt;
&lt;br /&gt;
Commençons sans plus attendre par faire un point sur le hachage !&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;arbre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;arbre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les arbres de Merkel étaient construits, mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire ? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;arbre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un arbre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant-dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable, car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un arbre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quel que soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on dupliquait les nœuds impairs et les fusionnait avec eux-mêmes est notable puisqu&#039;ici, on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau, mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;arbre a une structure un peu bizarre; on a deux niveaux de feuilles. Exécutons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commençant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précèdent vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds, mais quatre : Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seconde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour les construire. Toutefois, nous n&#039;avons pas encore vu comment les utiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données, mais nous n&#039;avons pas encore détaillé comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple : on veut télécharger un fichier en utilisant un réseau pair à pair. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré, mais à une multitude de machines dans un réseau qui vont participer au téléchargement. On dispose du hachage unique permettant d&#039;identifier le fichier, ce hachage nous a été envoyé par une machine connue à laquelle on fait confiance. Le hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage, et les machines du réseau vont s&#039;occuper de nous envoyer les blocs de données. À ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de le vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine de l&#039;arbre reconstruit est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non-légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque nœud dépend des nœuds qui le précèdent, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Cryptomonnaie ===&lt;br /&gt;
&lt;br /&gt;
La cryptomonnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de cryptomonnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La cryptomonnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet des cryptomonnaies, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Fonction de hachage&amp;quot;&#039;&#039;&#039;, Wikipedia, https://fr.wikipedia.org/wiki/Fonction_de_hachage&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51718</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51718"/>
		<updated>2021-12-13T10:27:21Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des [https://fr.wikipedia.org/wiki/Arbre_binaire arbres binaires] utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants. Chaque arbre est unique et une donnée donnera toujours le même arbre. On retrouvera typiquement les arbres de Merkle lorsqu&#039;on voudra faire du téléchargement de fichiers sur un réseau [https://fr.wikipedia.org/wiki/Pair-%C3%A0-pair pair-à-pair]. Comme on ne peut pas vérifier l&#039;identité des machines participant à l&#039;envoi de fichier, il est indispensable de mettre en place une structure de vérification comme les arbres de Merkle pour s&#039;assurer que les données reçues correspondent bien à celles désirées.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé :&#039;&#039;&#039; arbres de Merkle, arbres binaires, hachage, structure de données, validation, pair à pair&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle trees are [https://en.wikipedia.org/wiki/Binary_tree binary trees] used in data validation. A tree consists of nodes and leaves. The leaves contain the cryptographic hash corresponding to a part of the data we want to validate. The nodes contain a hash obtained by concatenating the hashes of the two child nodes and passing the concatenated string through a hashing function. This overall process creates a dependance between the nodes where each node&#039;s hash depends on the hash values of the underlying nodes. Each Merkle tree is unique and specific data will always give the same tree. A common use for Merkle trees is the download of files in [https://en.wikipedia.org/wiki/Peer-to-peer peer-to-peer] networks. As it is impossible to verify the identity of machines in the network, it is necessary to use validation structures such as Merkle trees to ensure that the received data is the desired one.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords:&#039;&#039;&#039; Merkle trees, binary trees, hash, data structure, validation, peer to peer&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier dans un réseau pair-à-pair, comme on ne peut pas vérifier l&#039;identité des machines sur le réseau, il est fort probable que certaines d&#039;entre elles tentent d&#039;envoyer des fichiers malveillants. Il faudrait donc mettre en place un mécanisme permettant d&#039;identifier ces fichiers non désirés. Les arbres de Merkle sont une solution à ce problème. Un arbre de Merkle est un arbre binaire qui va permettre d&#039;identifier de manière unique et sûre une ressource sur un réseau.&lt;br /&gt;
&lt;br /&gt;
Une fois qu&#039;une donnée aura été mise en ligne sur un réseau pair-à-pair, on va la découper en plusieurs blocs et calculer les hachages pour chacun des blocs. Ces hachages de premier niveau vont constituer les feuilles de l&#039;arbre de Merkle. Les feuilles vont ensuite être fusionnées deux à deux pour former un parent commun avec un hachage différent, et ce même parent va fusionner avec son voisin de la même manière et réitérer le processus jusqu&#039;à obtenir la racine de l&#039;arbre contenant le hachage unique qui va permettre d&#039;identifier la donnée dans son intégrité.&lt;br /&gt;
&lt;br /&gt;
La racine de l&#039;arbre servant d&#039;identifiant pour la donnée va être une manière fiable et rapide de rechercher la donnée sur le réseau. La racine va également servir à vérifier que la donnée téléchargée correspondant bien à la donnée désirée. Cela solutionne le problème initial puisque même si nous ne pouvons pas vérifier l&#039;identité des machines, nous sommes en mesure de déterminer si la donnée reçue correspond bien à celle voulue.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Diagramme représentant la structure générique d&#039;un arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-contre (&#039;&#039;&#039;figure 1&#039;&#039;&#039;) contient l&#039;arbre de Merkle d&#039;une donnée découpée en quatre blocs (Data Nodes). Juste au-dessus des blocs, on retrouve les feuilles de l&#039;arbre (Merkle leaves) contenant les hachages des blocs. Encore au-dessus, on va retrouver les nœuds intermédiaires (Merkle branches) qui correspondent à la fusion des deux hachages du niveau précédent. Enfin, tout en haut, on retrouve la racine de l&#039;arbre (Merkle root) qui contient le hachage final servant à identifier la donnée.&lt;br /&gt;
&lt;br /&gt;
Dans la suite de ce document, nous allons présenter plus en détails les arbres de Merkle et expliquer leur fonctionnement ainsi que leurs domaines d&#039;applications. Nous commencerons par introduire les fonctions de hachage et par décrire leur fonctionnement général ainsi que leurs avantages et désavantages. Ensuite, nous expliquerons le processus de construction d&#039;un arbre de Merkle et tous les différents scénarios qui peuvent altérer la façon dont l&#039;arbre va être construit. Nous enchaînerons ensuite sur la partie validation avec un exemple concret. Enfin, nous parlerons de différentes implémentations des arbres de Merkle dans des infrastructures réelles telles que la sécurité des transactions des cryptomonnaies.&lt;br /&gt;
&lt;br /&gt;
Commençons sans plus attendre par faire un point sur le hachage !&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;arbre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;arbre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les arbres de Merkel étaient construits, mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire ? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;arbre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un arbre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant-dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable, car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un arbre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quel que soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on dupliquait les nœuds impairs et les fusionnait avec eux-mêmes est notable puisqu&#039;ici, on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau, mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;arbre a une structure un peu bizarre; on a deux niveaux de feuilles. Exécutons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commençant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précèdent vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds, mais quatre : Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seconde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour les construire. Toutefois, nous n&#039;avons pas encore vu comment les utiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données, mais nous n&#039;avons pas encore détaillé comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple : on veut télécharger un fichier en utilisant un réseau pair à pair. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré, mais à une multitude de machines dans un réseau qui vont participer au téléchargement. On dispose du hachage unique permettant d&#039;identifier le fichier, ce hachage nous a été envoyé par une machine connue à laquelle on fait confiance. Le hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage, et les machines du réseau vont s&#039;occuper de nous envoyer les blocs de données. À ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de le vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine de l&#039;arbre reconstruit est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non-légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque nœud dépend des nœuds qui le précèdent, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Cryptomonnaie ===&lt;br /&gt;
&lt;br /&gt;
La cryptomonnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de cryptomonnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La cryptomonnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet des cryptomonnaies, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Fonction de hachage&amp;quot;&#039;&#039;&#039;, Wikipedia, https://fr.wikipedia.org/wiki/Fonction_de_hachage&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51715</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51715"/>
		<updated>2021-12-13T10:20:48Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des [https://fr.wikipedia.org/wiki/Arbre_binaire arbres binaires] utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants. Chaque arbre est unique et une donnée donnera toujours le même arbre. On retrouvera typiquement les arbres de Merkle lorsqu&#039;on voudra faire du téléchargement de fichiers sur un réseau [https://fr.wikipedia.org/wiki/Pair-%C3%A0-pair pair-à-pair]. Comme on ne peut pas vérifier l&#039;identité des machines participant à l&#039;envoi de fichier, il est indispensable de mettre en place une structure de vérification comme les arbres de Merkle pour s&#039;assurer que les données reçues correspondent bien à celles désirées.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé :&#039;&#039;&#039; arbres de Merkle, arbres binaires, hachage, structure de données, validation, pair à pair&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle trees are [https://en.wikipedia.org/wiki/Binary_tree binary trees] used in data validation. A tree consists of nodes and leaves. The leaves contain the cryptographic hash corresponding to a part of the data we want to validate. The nodes contain a hash obtained by concatenating the hashes of the two child nodes and passing the concatenated string through a hashing function. This overall process creates a dependance between the nodes where each node&#039;s hash depends on the hash values of the underlying nodes. Each Merkle tree is unique and specific data will always give the same tree. A common use for Merkle trees is the download of files in [https://en.wikipedia.org/wiki/Peer-to-peer peer-to-peer] networks. As it is impossible to verify the identity of machines in the network, it is necessary to use validation structures such as Merkle trees to ensure that the received data is the desired one.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords:&#039;&#039;&#039; Merkle trees, binary trees, hash, data structure, validation, peer to peer&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier dans un réseau pair-à-pair, comme on ne peut pas vérifier l&#039;identité des machines sur le réseau, il est fort probable que certaines d&#039;entre elles tentent d&#039;envoyer des fichiers malveillants. Il faudrait donc mettre en place un mécanisme permettant d&#039;identifier ces fichiers non désirés. Les arbres de Merkle sont une solution à ce problème. Un arbre de Merkle est un arbre binaire qui va permettre d&#039;identifier de manière unique et sûre une ressource sur un réseau.&lt;br /&gt;
&lt;br /&gt;
Une fois qu&#039;une donnée aura été mise en ligne sur un réseau pair-à-pair, on va la découper en plusieurs blocs et calculer les hachages pour chacun des blocs. Ces hachages de premier niveau vont constituer les feuilles de l&#039;arbre de Merkle. Les feuilles vont ensuite être fusionnées deux à deux pour former un parent commun avec un hachage différent, et ce même parent va fusionner avec son voisin de la même manière et réitérer le processus jusqu&#039;à obtenir la racine de l&#039;arbre contenant le hachage unique qui va permettre d&#039;identifier la donnée dans son intégrité.&lt;br /&gt;
&lt;br /&gt;
La racine de l&#039;arbre servant d&#039;identifiant pour la donnée va être une manière fiable et rapide de rechercher la donnée sur le réseau. La racine va également servir à vérifier que la donnée téléchargée correspondant bien à la donnée désirée. Cela solutionne le problème initial puisque même si nous ne pouvons pas vérifier l&#039;identité des machines, nous sommes en mesure de déterminer si la donnée reçue correspond bien à celle voulue.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Diagramme représentant la structure générique d&#039;un arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-contre (&#039;&#039;&#039;figure 1&#039;&#039;&#039;) contient l&#039;arbre de Merkle d&#039;une donnée découpée en quatre blocs (Data Nodes). Juste au-dessus des blocs, on retrouve les feuilles de l&#039;arbre (Merkle leaves) contenant les hachages des blocs. Encore au-dessus, on va retrouver les nœuds intermédiaires (Merkle branches) qui correspondent à la fusion des deux hachages du niveau précédent. Enfin, tout en haut, on retrouve la racine de l&#039;arbre (Merkle root) qui contient le hachage final servant à identifier la donnée.&lt;br /&gt;
&lt;br /&gt;
Dans la suite de ce document, nous allons présenter plus en détails les arbres de Merkle et expliquer leur fonctionnement ainsi que leurs domaines d&#039;applications. Nous commencerons par introduire les fonctions de hachage et par décrire leur fonctionnement général ainsi que leurs avantages et désavantages. Ensuite, nous expliquerons le processus de construction d&#039;un arbre de Merkle et tous les différents scénarios qui peuvent altérer la façon dont l&#039;arbre va être construit. Nous enchaînerons ensuite sur la partie validation avec un exemple concret. Enfin, nous parlerons de différentes implémentations des arbres de Merkle dans des infrastructures réelles telles que la sécurité des transactions des cryptomonnaies.&lt;br /&gt;
&lt;br /&gt;
Commençons sans plus attendre par faire un point sur le hachage !&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;arbre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;arbre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les arbres de Merkel étaient construits, mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire ? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;arbre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un arbre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant-dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable, car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un arbre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quel que soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on dupliquait les nœuds impairs et les fusionnait avec eux-mêmes est notable puisqu&#039;ici, on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau, mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;arbre a une structure un peu bizarre; on a deux niveaux de feuilles. Exécutons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commençant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précèdent vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds, mais quatre : Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seconde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les arbres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un arbre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Cryptomonnaie ===&lt;br /&gt;
&lt;br /&gt;
La cryptomonnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de cryptomonnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La cryptomonnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet des cryptomonnaies, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Fonction de hachage&amp;quot;&#039;&#039;&#039;, Wikipedia, https://fr.wikipedia.org/wiki/Fonction_de_hachage&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51708</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51708"/>
		<updated>2021-12-13T10:08:19Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des [https://fr.wikipedia.org/wiki/Arbre_binaire arbres binaires] utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants. Chaque arbre est unique et une donnée donnera toujours le même arbre. On retrouvera typiquement les arbres de Merkle lorsqu&#039;on voudra faire du téléchargement de fichiers sur un réseau [https://fr.wikipedia.org/wiki/Pair-%C3%A0-pair pair-à-pair]. Comme on ne peut pas vérifier l&#039;identité des machines participant à l&#039;envoi de fichier, il est indispensable de mettre en place une structure de vérification comme les arbres de Merkle pour s&#039;assurer que les données reçues correspondent bien à celles désirées.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé :&#039;&#039;&#039; arbres de Merkle, arbres binaires, hachage, structure de données, validation, pair à pair&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle trees are [https://en.wikipedia.org/wiki/Binary_tree binary trees] used in data validation. A tree consists of nodes and leaves. The leaves contain the cryptographic hash corresponding to a part of the data we want to validate. The nodes contain a hash obtained by concatenating the hashes of the two child nodes and passing the concatenated string through a hashing function. This overall process creates a dependance between the nodes where each node&#039;s hash depends on the hash values of the underlying nodes. Each Merkle tree is unique and specific data will always give the same tree. A common use for Merkle trees is the download of files in [https://en.wikipedia.org/wiki/Peer-to-peer peer-to-peer] networks. As it is impossible to verify the identity of machines in the network, it is necessary to use validation structures such as Merkle trees to ensure that the received data is the desired one.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords:&#039;&#039;&#039; Merkle trees, binary trees, hash, data structure, validation, peer to peer&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier dans un réseau pair-à-pair, comme on ne peut pas vérifier l&#039;identité des machines sur le réseau, il est fort probable que certaines d&#039;entre elles tentent d&#039;envoyer des fichiers malveillants. Il faudrait donc mettre en place un mécanisme permettant d&#039;identifier ces fichiers non désirés. Les arbres de Merkle sont une solution à ce problème. Un arbre de Merkle est un arbre binaire qui va permettre d&#039;identifier de manière unique et sûre une ressource sur un réseau.&lt;br /&gt;
&lt;br /&gt;
Une fois qu&#039;une donnée aura été mise en ligne sur un réseau pair-à-pair, on va la découper en plusieurs blocs et calculer les hachages pour chacun des blocs. Ces hachages de premier niveau vont constituer les feuilles de l&#039;arbre de Merkle. Les feuilles vont ensuite être fusionnées deux à deux pour former un parent commun avec un hachage différent, et ce même parent va fusionner avec son voisin de la même manière et réitérer le processus jusqu&#039;à obtenir la racine de l&#039;arbre contenant le hachage unique qui va permettre d&#039;identifier la donnée dans son intégrité.&lt;br /&gt;
&lt;br /&gt;
La racine de l&#039;arbre servant d&#039;identifiant pour la donnée va être une manière fiable et rapide de rechercher la donnée sur le réseau. La racine va également servir à vérifier que la donnée téléchargée correspondant bien à la donnée désirée. Cela solutionne le problème initial puisque même si nous ne pouvons pas vérifier l&#039;identité des machines, nous sommes en mesure de déterminer si la donnée reçue correspond bien à celle voulue.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Diagramme représentant la structure générique d&#039;un arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-contre (&#039;&#039;&#039;figure 1&#039;&#039;&#039;) contient l&#039;arbre de Merkle d&#039;une donnée découpée en quatre blocs (Data Nodes). Juste au-dessus des blocs, on retrouve les feuilles de l&#039;arbre (Merkle leaves) contenant les hachages des blocs. Encore au-dessus, on va retrouver les nœuds intermédiaires (Merkle branches) qui correspondent à la fusion des deux hachages du niveau précédent. Enfin, tout en haut, on retrouve la racine de l&#039;arbre (Merkle root) qui contient le hachage final servant à identifier la donnée.&lt;br /&gt;
&lt;br /&gt;
Dans la suite de ce document, nous allons présenter plus en détails les arbres de Merkle et expliquer leur fonctionnement ainsi que leurs domaines d&#039;applications. Nous commencerons par introduire les fonctions de hachage et par décrire leur fonctionnement général ainsi que leurs avantages et désavantages. Ensuite, nous expliquerons le processus de construction d&#039;un arbre de Merkle et tous les différents scénarios qui peuvent altérer la façon dont l&#039;arbre va être construit. Nous enchaînerons ensuite sur la partie validation avec un exemple concret. Enfin, nous parlerons de différentes implémentations des arbres de Merkle dans des infrastructures réelles telles que la sécurité des transactions des cryptomonnaies.&lt;br /&gt;
&lt;br /&gt;
Commençons sans plus attendre par faire un point sur le hachage !&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;arbre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les arbres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;arbre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un arbre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un arbre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;arbre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les arbres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un arbre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Cryptomonnaie ===&lt;br /&gt;
&lt;br /&gt;
La cryptomonnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de cryptomonnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La cryptomonnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet des cryptomonnaies, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Fonction de hachage&amp;quot;&#039;&#039;&#039;, Wikipedia, https://fr.wikipedia.org/wiki/Fonction_de_hachage&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51706</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51706"/>
		<updated>2021-12-13T10:02:24Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des [https://fr.wikipedia.org/wiki/Arbre_binaire arbres binaires] utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants. Chaque arbre est unique et une donnée donnera toujours le même arbre. On retrouvera typiquement les arbres de Merkle lorsqu&#039;on voudra faire du téléchargement de fichiers sur un réseau [https://fr.wikipedia.org/wiki/Pair-%C3%A0-pair pair-à-pair]. Comme on ne peut pas vérifier l&#039;identité des machines participant à l&#039;envoi de fichier, il est indispensable de mettre en place une structure de vérification comme les arbres de Merkle pour s&#039;assurer que les données reçues correspondent bien à celles désirées.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé :&#039;&#039;&#039; arbres de Merkle, arbres binaires, hachage, structure de données, validation, pair à pair&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle trees are [https://en.wikipedia.org/wiki/Binary_tree binary trees] used in data validation. A tree consists of nodes and leaves. The leaves contain the cryptographic hash corresponding to a part of the data we want to validate. The nodes contain a hash obtained by concatenating the hashes of the two child nodes and passing the concatenated string through a hashing function. This overall process creates a dependance between the nodes where each node&#039;s hash depends on the hash values of the underlying nodes. Each Merkle tree is unique and specific data will always give the same tree. A common use for Merkle trees is the download of files in [https://en.wikipedia.org/wiki/Peer-to-peer peer-to-peer] networks. As it is impossible to verify the identity of machines in the network, it is necessary to use validation structures such as Merkle trees to ensure that the received data is the desired one.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords:&#039;&#039;&#039; Merkle trees, binary trees, hash, data structure, validation, peer to peer&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier dans un réseau pair-à-pair, comme on ne peut pas vérifier l&#039;identité des machines sur le réseau, il est fort probable que certaines d&#039;entre elles tentent d&#039;envoyer des fichiers malveillants. Il faudrait donc mettre en place un mécanisme permettant d&#039;identifier ces fichiers non désirés. Les arbres de Merkle sont une solution à ce problème. Un arbre de Merkle est un arbre binaire qui va permettre d&#039;identifier de manière unique et sûre une ressource sur un réseau.&lt;br /&gt;
&lt;br /&gt;
Une fois qu&#039;une donnée aura été mise en ligne sur un réseau pair-à-pair, on va la découper en plusieurs blocs et calculer les hachages pour chacun des blocs. Ces hachages de premier niveau vont constituer les feuilles de l&#039;arbre de Merkle. Les feuilles vont ensuite être fusionnées deux à deux pour former un parent commun avec un hachage différent, et ce même parent va fusionner avec son voisin de la même manière et réitérer le processus jusqu&#039;à obtenir la racine de l&#039;arbre contenant le hachage unique qui va permettre d&#039;identifier la donnée dans son intégrité.&lt;br /&gt;
&lt;br /&gt;
La racine de l&#039;arbre servant d&#039;identifiant pour la donnée va être une manière fiable et rapide de rechercher la donnée sur le réseau. La racine va également servir à vérifier que la donnée téléchargée correspondant bien à la donnée désirée. Cela solutionne le problème initial puisque même si nous ne pouvons pas vérifier l&#039;identité des machines, nous sommes en mesure de déterminer si la donnée reçue correspond bien à celle voulue.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-contre (&#039;&#039;&#039;figure 1&#039;&#039;&#039;) contient l&#039;arbre de Merkle d&#039;une donnée découpée en quatre blocs (Data Nodes). Juste au-dessus des blocs, on retrouve les feuilles de l&#039;arbre (Merkle leaves) contenant les hachages des blocs. Encore au-dessus, on va retrouver les nœuds intermédiaires (Merkle branches) qui correspondent à la fusion des deux hachages du niveau précédent. Enfin, tout en haut, on retrouve la racine de l&#039;arbre (Merkle root) qui contient le hachage final servant à identifier la donnée.&lt;br /&gt;
&lt;br /&gt;
Dans la suite de ce document, nous allons présenter plus en détails les arbres de Merkle et expliquer leur fonctionnement ainsi que leurs domaines d&#039;applications. Nous commencerons par introduire les fonctions de hachage et par décrire leur fonctionnement général ainsi que leurs avantages et désavantages. Ensuite, nous expliquerons le processus de construction d&#039;un arbre de Merkle et tous les différents scénarios qui peuvent altérer la façon dont l&#039;arbre va être construit. Nous enchaînerons ensuite sur la partie validation avec un exemple concret. Enfin, nous parlerons de différentes implémentations des arbres de Merkle dans des infrastructures réelles telles que la sécurité des transactions des cryptomonnaies.&lt;br /&gt;
&lt;br /&gt;
Commençons sans plus attendre par faire un point sur le hachage !&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les abres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un abre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Cryptomonnaie ===&lt;br /&gt;
&lt;br /&gt;
La cryptomonnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de cryptomonnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La cryptomonnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet des cryptomonnaies, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Fonction de hachage&amp;quot;&#039;&#039;&#039;, Wikipedia, https://fr.wikipedia.org/wiki/Fonction_de_hachage&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51705</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51705"/>
		<updated>2021-12-13T09:53:58Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des [https://fr.wikipedia.org/wiki/Arbre_binaire arbres binaires] utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants. Chaque arbre est unique et une donnée donnera toujours le même arbre. On retrouvera typiquement les arbres de Merkle lorsqu&#039;on voudra faire du téléchargement de fichiers sur un réseau [https://fr.wikipedia.org/wiki/Pair-%C3%A0-pair pair-à-pair]. Comme on ne peut pas vérifier l&#039;identité des machines participant à l&#039;envoi de fichier, il est indispensable de mettre en place une structure de vérification comme les arbres de Merkle pour s&#039;assurer que les données reçues correspondent bien à celles désirées.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé :&#039;&#039;&#039; arbres de Merkle, arbres binaires, hachage, structure de données, validation, pair à pair&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle trees are [https://en.wikipedia.org/wiki/Binary_tree binary trees] used in data validation. A tree consists of nodes and leaves. the leaves contain the cryptographic hash corresponding to a part of the data we want to validate. The nodes contain a hash obtained by concatenating the hashes of the two child nodes and passing the concatenated string through a hashing function. This overall process creates a dependance between the nodes where each node&#039;s hash depends on the hash values of the underlying nodes. Each Merkle tree is unique and specific data will always give the same tree. A common use for Merkle trees is the download of files in [https://en.wikipedia.org/wiki/Peer-to-peer peer-to-peer] networks. As it is impossible to verify the identity of machines in the network, it is necessary to use validation structures such as Merkle trees to ensure that the received data is the desired one.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords:&#039;&#039;&#039; Merkle trees, binary trees, hash, data structure, validation, peer to peer&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier dans un réseau pair-à-pair, comme on ne peut pas pas vérifier l&#039;identité des machines sur le réseau, il est fort probable que certaines d&#039;entre elles tentent d&#039;envoyer des fichiers malveillants. Il faudrait donc mettre en place un méchanisme permettant d&#039;identifier ces fichiers non désirés. Les arbres de Merkle sont une solution à ce problème. Un arbre de Merkle est un arbre binaire qui va permettre d&#039;identifier de manière unique et sûre une ressource sur un réseau.&lt;br /&gt;
&lt;br /&gt;
Une fois qu&#039;une donnée aura été mise en ligne sur un réseau pair-à-pair, on va la découper en plusieurs blocs et calculer les hachages pour chacun des blocs. Ces hachages de premier niveau vont constituer les feuilles de l&#039;arbre de Merkle. Les feuilles vont ensuite être fusionnées deux à deux pour former un parent commun avec un hachage différent, et ce même parent va fusionner avec son voisin de la même manière et réitérer le processus jusqu&#039;à obtenir la racine de l&#039;arbre contenant le hachage unique qui va permettre d&#039;identifier la donnée dans son intégrité.&lt;br /&gt;
&lt;br /&gt;
La racine de l&#039;arbre servant d&#039;identifiant pour la donnée va être une manière fiable et rapide de rechercher la donnée sur le réseau. La racine va également servir à vérifier que la donnée téléchargée correspondant bien à la donnée désirée. Cela solutionne le problème initial puisque malgré que nous ne puissions vérifier l&#039;identité des machines, nous sommes en mesure de déterminer si la donnée est reçue correspond bien à celle voulue.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-contre (&#039;&#039;&#039;figure 1&#039;&#039;&#039;) contient l&#039;arbre de Merkle d&#039;une donnée découpée en quatre blocs (Data Nodes). Juste au dessus des blocs, on retrouve les feuilles de l&#039;arbre (Merkle leaves) contenant les hachages des blocs. Encore au dessus, on va retrouver les nœuds intermédiaires (Merkle branches) qui correspondent à la fusion des deux hachages du niveau précédent. Enfin, tout en haut, on retrouve la racine de l&#039;arbre (Merkle root) qui contient le hachage final servant à identifier la donnée.&lt;br /&gt;
&lt;br /&gt;
Dans la suite de ce document, nous allons présenter plus en détails les arbres de Merkle et expliquer leur fonctionnement ainsi que leurs domaines d&#039;applications. Nous commencerons par introduire les fonctions de hachage et par décrire leur fonctionnement général ainsi que leurs avantages et désavantages. Ensuite, nous expliquerons le processus de construction d&#039;un arbre de Merkle et tous les différents scénarios qui peuvent altérer la façon dont l&#039;arbre va être construit. Nous enchaînerons ensuite sur la partie validation avec un exemple concrèt. Enfin, nous parlerons de différentes implémentations des arbres de Merkle dans des infrastructures réelles telles que la sécurité des transactions des crypto-monnaies.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Commençons sans plus attendre par faire un point sur le hachage !&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les abres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un abre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Crypto-monnaie ===&lt;br /&gt;
&lt;br /&gt;
La crypto monnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de crypto monnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La crypto monnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet de crypto, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Fonction de hachage&amp;quot;&#039;&#039;&#039;, Wikipedia, https://fr.wikipedia.org/wiki/Fonction_de_hachage&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51697</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51697"/>
		<updated>2021-12-13T09:32:55Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des [https://fr.wikipedia.org/wiki/Arbre_binaire arbres binaires] utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants. Chaque arbre est unique et une donnée donnera toujours le même arbre. On retrouvera typiquement les arbres de Merkle lorsqu&#039;on voudra faire du téléchargement de fichiers sur un réseau [https://fr.wikipedia.org/wiki/Pair-%C3%A0-pair pair-à-pair]. Comme on ne peut pas vérifier l&#039;identité des machines participant à l&#039;envoi de fichier, il est indispensable de mettre en place une structure de vérification comme les arbres de Merkle pour s&#039;assurer que les données reçues correspondent bien à celles désirées.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé :&#039;&#039;&#039; arbres de Merkle, arbres binaires, hachage, structure de données, validation, pair à pair&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle trees are [https://en.wikipedia.org/wiki/Binary_tree binary trees] used in data validation. A tree consists of nodes and leaves. the leaves contain the cryptographic hash corresponding to a part of the data we want to validate. The nodes contain a hash obtained by concatenating the hashes of the two child nodes and passing the concatenated string through a hashing function. This overall process creates a dependance between the nodes where each node&#039;s hash depends on the hash values of the underlying nodes. Each Merkle tree is unique and specific data will always give the same tree. A common use for Merkle trees is the download of files in [https://en.wikipedia.org/wiki/Peer-to-peer peer-to-peer] networks. As it is impossible to verify the identity of machines in the network, it is necessary to use validation structures such as Merkle trees to ensure that the received data is the desired one.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords:&#039;&#039;&#039; Merkle trees, binary trees, hash, data structure, validation, peer to peer&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des [https://fr.wikipedia.org/wiki/Arbre_binaire arbres binaires] utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les abres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un abre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Crypto-monnaie ===&lt;br /&gt;
&lt;br /&gt;
La crypto monnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de crypto monnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La crypto monnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet de crypto, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Fonction de hachage&amp;quot;&#039;&#039;&#039;, Wikipedia, https://fr.wikipedia.org/wiki/Fonction_de_hachage&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51692</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51692"/>
		<updated>2021-12-13T09:28:07Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants. Chaque arbre est unique et une donnée donnera toujours le même arbre. On retrouvera typiquement les arbres de Merkle lorsqu&#039;on voudra faire du téléchargement de fichiers sur un réseau pair à pair. Comme on ne peut pas vérifier l&#039;identité des machines participant à l&#039;envoi de fichier, il est indispensable de mettre en place une structure de vérification comme les arbres de Merkle pour s&#039;assurer que les données reçues correspondent bien à celles désirées.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé :&#039;&#039;&#039; arbres de Merkle, arbres binaires, hachage, structure de données, validation, pair à pair&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle trees are binary trees used in data validation. A tree consists of nodes and leaves. the leaves contain the hash corresponding to a part of the data we want to validate. The nodes contain a hash obtained by concatenating the hashes of the two child nodes and passing the concatenated string through a hashing function. This overall process creates a dependance between the nodes where each node&#039;s hash depends on the hash values of the underlying nodes. Each Merkle tree is unique and specific data will always give the same tree. A common use for Merkle trees is the download of files in peer to peer networks. As it is impossible to verify the identity of machines in the network, it is necessary to use validation structures such as Merkle trees to ensure that the received data is the desired one.&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords:&#039;&#039;&#039; Merkle trees, binary trees, hash, data structure, validation, peer to peer&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les abres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un abre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Crypto-monnaie ===&lt;br /&gt;
&lt;br /&gt;
La crypto monnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de crypto monnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La crypto monnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet de crypto, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Fonction de hachage&amp;quot;&#039;&#039;&#039;, Wikipedia, https://fr.wikipedia.org/wiki/Fonction_de_hachage&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51686</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51686"/>
		<updated>2021-12-13T09:26:15Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants. Chaque arbre est unique et une donnée donnera toujours le même arbre. On retrouvera typiquement les arbres de Merkle lorsqu&#039;on voudra faire du téléchargement de fichiers sur un réseau pair à pair. Comme on ne peut pas vérifier l&#039;identité des machines participant à l&#039;envoi de fichier, il est indispensable de mettre en place une structure de vérification comme les arbres de Merkle pour s&#039;assurer que les données reçues correspondent bien à celles désirées.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: arbre de Merkle, arbres binaires, hachage, structure de données, validation, pair à pair&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle trees are binary trees used in data validation. A tree consists of nodes and leaves. the leaves contain the hash corresponding to a part of the data we want to validate. The nodes contain a hash obtained by concatenating the hashes of the two child nodes and passing the concatenated string through a hashing function. This overall process creates a dependance between the nodes where each node&#039;s hash depends on the hash values of the underlying nodes. Each Merkle tree is unique and specific data will always give the same tree. A common use for Merkle trees is the download of files in peer to peer networks. As it is impossible to verify the identity of machines in the network, it is necessary to use validation structures such as Merkle trees to ensure that the received data is the desired one.&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle trees, binary trees, hash, data structure, validation, peer to peer&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les abres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un abre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Crypto-monnaie ===&lt;br /&gt;
&lt;br /&gt;
La crypto monnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de crypto monnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La crypto monnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet de crypto, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Fonction de hachage&amp;quot;&#039;&#039;&#039;, Wikipedia, https://fr.wikipedia.org/wiki/Fonction_de_hachage&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51683</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51683"/>
		<updated>2021-12-13T09:24:53Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants. Chaque arbre est unique et une donnée donnera toujours le même arbre. On retrouvera typiquement les arbres de Merkle lorsqu&#039;on voudra faire du téléchargement de fichiers sur un réseau pair à pair. Comme on ne peut pas vérifier l&#039;identité des machines participant à l&#039;envoi de fichier, il est indispensable de mettre en place une structure de vérification comme les arbres de Merkle pour s&#039;assurer que les données reçues correspondent bien à celles désirées.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: arbre de Merkle, arbres binaires, hachage, structure de données, validation, pair à pair&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle trees are binary trees used in data validation. A tree consists of nodes and leaves. the leaves contain the hash corresponding to a part of the data we want to validate. The nodes contain a hash obtained by concatenating the hashes of the two child nodes and passing the concatenated string through a hashing function. This overall process creates a dependance between the nodes where each node&#039;s hash depends on the hash values of the underlying nodes. Each Merkle tree is a unique and any data will always give the same tree. A common use for Merkle trees is the download of files in peer to peer networks. As it is impossible to verifiy the identity of machines in the network, it is necessary to use validation structures such as Merkle trees to ensure that the received data is the desired one.&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle trees, binary trees, hash, data structure, validation, peer to peer&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les abres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un abre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Crypto-monnaie ===&lt;br /&gt;
&lt;br /&gt;
La crypto monnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de crypto monnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La crypto monnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet de crypto, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Fonction de hachage&amp;quot;&#039;&#039;&#039;, Wikipedia, https://fr.wikipedia.org/wiki/Fonction_de_hachage&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51681</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51681"/>
		<updated>2021-12-13T09:10:07Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les abres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un abre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Crypto-monnaie ===&lt;br /&gt;
&lt;br /&gt;
La crypto monnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de crypto monnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La crypto monnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet de crypto, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Fonction de hachage&amp;quot;&#039;&#039;&#039;, Wikipedia, https://fr.wikipedia.org/wiki/Fonction_de_hachage&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51680</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51680"/>
		<updated>2021-12-13T09:08:35Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Validation.png|500px|thumb|right|&#039;&#039;&#039;Figure 5 :&#039;&#039;&#039; Validation de l&#039;arbre de Merkle identifié par &#039;&#039;&#039;&amp;quot;b74b3&amp;quot;&#039;&#039;&#039;. L&#039;arbre reçu (à droite) contient Data5 à la place de Data4, cette erreur est immédiatement détectée lors de la comparaison du hachage racine avec celui du fichier désiré]]&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les abres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un abre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Crypto-monnaie ===&lt;br /&gt;
&lt;br /&gt;
La crypto monnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de crypto monnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La crypto monnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet de crypto, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=File:Merkle_Tree_Validation.png&amp;diff=51679</id>
		<title>File:Merkle Tree Validation.png</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=File:Merkle_Tree_Validation.png&amp;diff=51679"/>
		<updated>2021-12-13T09:00:33Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: Diagram of the validation of a Merkle Tree&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Summary ==&lt;br /&gt;
Diagram of the validation of a Merkle Tree&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51675</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51675"/>
		<updated>2021-12-13T08:33:31Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les abres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un abre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Crypto-currency ===&lt;br /&gt;
&lt;br /&gt;
La crypto monnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de crypto monnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La crypto monnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet de crypto, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51666</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51666"/>
		<updated>2021-12-12T21:37:03Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les abres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un abre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Crypto-currency ===&lt;br /&gt;
&lt;br /&gt;
La crypto monnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de crypto monnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La crypto monnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet de crypto, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Conclusion ===&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont très pratiques pour effectuer de la validation de données dans un système pair à pair. Ils ne sont pas difficile à stocker puisque les seules données qu&#039;ils contiennent (en dehors des blocs de données) vont être des hachages dont la taille varie autour de la centaine d&#039;octets en fonction des algorithmes de hachage utilisés. Leur simplicité permet également une validation rapide des données puisqu&#039;il suffit de faire des opérations de concaténation (très faible coût) et de calcul de hachage (coût faible en moyenne, peut varier suivant la fonction de hachage utilisée). La structure en arbre permet également d&#039;apporter une certaine granularité et l&#039;ajout de fonctionnement annexe par rapport à une simple concaténation des hachages de chaque bloc de données.&lt;br /&gt;
Enfin, la robustesse d&#039;un arbre va entièrement dépendre des fonctions de hachages utilisées. Par exemple, si l&#039;on voulait valider des données sensibles comme des transactions sur la blockchain, on préferera utiliser des fonctions sécurisées comme celles de la famille SHA plutôt qu&#039;un simple md5.&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51665</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51665"/>
		<updated>2021-12-12T19:31:59Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les abres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un abre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
Git est un logiciel de gestion de versions décentralisé qui est beaucoup utilisé aujourd&#039;hui. Tous les fichiers sont enregistrés sur l&#039;ordinateur de tous les utilisateurs, à tout moment. Les Merkle trees permettent d&#039;assurer que tout changement soit cohérent sur les ordinateurs de tous les utilisateurs. En comparant simplement le hashages des fichiers ou dossiers entre 2 différents commits, on peut facilement et surtout rapidement savoir si celui-ci a été modifié ou non.&lt;br /&gt;
&lt;br /&gt;
=== Crypto-currency ===&lt;br /&gt;
&lt;br /&gt;
La crypto monnaie a été très popularisé récemment, et continuer de s&#039;étendre, notamment le bitcoin.&lt;br /&gt;
Toutes les transactions de crypto monnaie sont stockées dans des blocks, aussi appelés blockchain.&lt;br /&gt;
La crypto monnaie utilise les Merkle Trees pour s&#039;assurer la validation des transactions dans les blocks. En effet, les blocks contiennent un ID, qui est le header fields hashé (cf. image), et parmi ce header hashé, une partie contient la racine de du Merkle Tree. De ce fait, elle permet de s&#039;assurer de l&#039;unicité de l&#039;enregistrement des transactions dans le block.&lt;br /&gt;
&lt;br /&gt;
=== Blockchain pruning ===&lt;br /&gt;
&lt;br /&gt;
Pour continuer sur le sujet de crypto, l&#039;émondation ou l&#039;élagage des blockchains est un sujet qui reste d&#039;affût de nos jours. En effet, sachant que les blockchains grandissent de plus en plus actuellement, cela veut également dire que celles-ci prennent de plus en plus de place en terme de stockage. Par exemple, en Février 2021, la taille de la blockchain du Bitcoin est d&#039;environ 380Go. De ce fait, l&#039;élagage de la blockchain consiste à épurer l&#039;arbre, en supprimant les informations de la blockchain non critiques de l&#039;espace de stockage. Les noeuds pleins gardent une copie de tous ce qui est stockés dans la blockchain, notamment des informations qui ne sont plus forcément utiles. Sachant que l&#039;objectif d&#039;un Merkle Tree est de synthétiser et de relier de grandes quantités d&#039;informations. Chaque noeud contient l&#039;information de ses fils, et donc la proposition est d&#039;élaguer les informations qui ne sont plus utiles commes les transactions utilisées, ne laissant que les branches contenant les hashages pour vérifier les autres transactions.&lt;br /&gt;
&lt;br /&gt;
=== Base de données (AWS Dynamo DB) ===&lt;br /&gt;
&lt;br /&gt;
Dynamo DB est une base de données distribuée provenant en partie de la plateforme Amazon Web Services. C&#039;est une base de données key-value NoSQL, entièrement managée et serverless qui est designé pour exécuter des applications hautes performances à n&#039;importe quelle échelle. Dynamo DB héberge les données (values) dans des data nodes qui sont aussi appelés &amp;quot;virtual nodes&amp;quot; et chaque virtual nodes héberge une key-range (gamme de clés). Un Merkle tree est construit pour chaque key-range, où les feuilles de l&#039;arbre sont les valeurs de la key-range data. La Merkle Root contient donc un résumé des données de chaque noeuds. De ce fait, en comparant les Merkle Roots de chaque virtual nodes qui possèdent les mêmes key-range, on peut donc monitorer la moindre différences et de repérer l&#039;endroit divergent.&lt;br /&gt;
=== File System (ZFS) ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
==== Pourquoi utiliser des arbres de Merkle ? ====&lt;br /&gt;
Nous savons maintenant comment créer un arbre, et comment l&#039;utiliser pour valider des données. Une question que l&#039;on pourrait se poser est &amp;quot;Pourquoi utiliser des arbres de Merkle, ne pourrait-on pas simplement concaténer les hachages des blocs de données ?&amp;quot;. En effet, on pourrait tout à fait se contenter de concaténer les hachages des différents blocs, le moindre changement sur un bloc changerait le hachage final. Alors pourquoi s&#039;embeter avec des arbres ?&lt;br /&gt;
&lt;br /&gt;
==== Attaque de préimage ====&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51664</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51664"/>
		<updated>2021-12-12T19:07:50Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle déséquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les abres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un abre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
==== Pourquoi utiliser des arbres de Merkle ? ====&lt;br /&gt;
Nous savons maintenant comment créer un arbre, et comment l&#039;utiliser pour valider des données. Une question que l&#039;on pourrait se poser est &amp;quot;Pourquoi utiliser des arbres de Merkle, ne pourrait-on pas simplement concaténer les hachages des blocs de données ?&amp;quot;. En effet, on pourrait tout à fait se contenter de concaténer les hachages des différents blocs, le moindre changement sur un bloc changerait le hachage final. Alors pourquoi s&#039;embeter avec des arbres ?&lt;br /&gt;
&lt;br /&gt;
==== Attaque de préimage ====&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51663</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51663"/>
		<updated>2021-12-12T10:26:46Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
Dans les parties précédentes, nous avons vu ce qu&#039;étaient les arbres de Merkle, et comment procéder pour en construire un. Toutefois, nous n&#039;avons pas encore vu comment les uiliser. Nous avons parlé brièvement du fait qu&#039;ils servaient à faire de la validation de données mais nous n&#039;avons pas encore détaillé exactement comment. C&#039;est ce dont nous allons parler dans cette partie.&lt;br /&gt;
&lt;br /&gt;
Imaginons que nous voulions télécharger un fichier assez conséquent depuis Internet. On veut utiliser un système pair à pair pour télécharger le fichier. On ne va donc pas se connecter à un serveur unique qui détient le fichier désiré mais à une multitude de machines dans un réseau qui vont participer au téléchargement. Le pair à pair a de nombreux avantages mais nous ne rentrerons pas en détail sur son fonctionnement dans ce document. L&#039;un des problèmes majeurs des architectures pair à pair est la confiance que l&#039;on accorde à chaque machine. En effet, contrairement à une architecture client-serveur classique où le serveur est une machine identifiée et à laquelle on fait généralement confiance, la modularité des systèmes pair à pair fait que nous soyions obligé de nous reposer sur des machines anonymes et potentiellement malicieuses. Il est impossible de vérifier si chaque machine est légitime ou si l&#039;une d&#039;entre elles tente de nous envoyer un fichier corrompu. C&#039;est justement pour pallier ce problème que nous pouvons utiliser les abres de Merkle.&lt;br /&gt;
&lt;br /&gt;
Reprenons notre problèmatique de téléchargement de fichier. Ici, le fichier que l&#039;on veut obtenir va être transformé en un abre de Merkle. En d&#039;autres termes, il va être divisé en un certain nombre de blocs que l&#039;on va hacher un à un jusqu&#039;à obtenir un hachage unique qui permet d&#039;identifier l&#039;intégralité du fichier (il s&#039;agit de la racine de l&#039;arbre). Nous avons donc un arbre plus ou moins massifs qui va représenter le fichier que nous voulons télécharger. Mais comment-va-t&#039;on faire pour vérifier que le fichier que nous avons demandé est bien celui que nous avons reçu ?&lt;br /&gt;
Tout repose sur le hachage racine. Si on part du principe que nous avons obtenu le hachage racine d&#039;un tier auquel nous faisons confiance, nous allons pouvoir, par ce seul hachage, s&#039;assurer que le fichier que nous obtenons soit bel et bien celui que nous voulions.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Prenons un exemple très simple: On veut télécharger un fichier F en utilisant un réseau pair à pair. On dispose du hachage unique permettant d&#039;identifier le fichier grâce à un tier à qui nous faisons confiance. Ce hachage, un peu à la manière d&#039;un URL va permettre d&#039;identifier le fichier au sein du réseau. On va donc indiquer le fichier que l&#039;on désire télécharger en fournissant son hachage et les pairs vont s&#039;occuper de nous envoyer les blocs de données. A ce niveau-là, nous ne pouvons rien dire sur la légitimité des machines qui nous envoient les blocs de données, il est possible que certaines d&#039;entres elles soient malicieuses mais impossible pour nous de vérifier. Toutefois, lorsque nous aurons reçu tous les blocs de données, nous allons pouvoir les valider en reconstruisant l&#039;arbre de Merkle et en vérifiant que le hachage racine obtenu est identique à celui que nous avions à l&#039;origine. S&#039;il s&#039;agit du même hachage, alors le fichier est bien conforme. Si l&#039;une des machines du réseau pair à pair a tenté de nous envoyer des données non légitimes, on va pouvoir très facilement le détecter. En effet, comme chaque noeud dépend des noeuds qui le précède, le moindre changement va se propager et changer completement le hachage racine.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;efficacité des arbres de Merkle a détecter le moindre changement de bit dans un fichier repose sur la nature des fonctions de hachage qu&#039;il utilise. En effet, une particularité des fonctions de hachage est qu&#039;elles sont très chaotiques et que le changement du moindre bit va complètement changer le hachage résultant.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
==== Pourquoi utiliser des arbres de Merkle ? ====&lt;br /&gt;
Nous savons maintenant comment créer un arbre, et comment l&#039;utiliser pour valider des données. Une question que l&#039;on pourrait se poser est &amp;quot;Pourquoi utiliser des arbres de Merkle, ne pourrait-on pas simplement concaténer les hachages des blocs de données ?&amp;quot;. En effet, on pourrait tout à fait se contenter de concaténer les hachages des différents blocs, le moindre changement sur un bloc changerait le hachage final. Alors pourquoi s&#039;embeter avec des arbres ?&lt;br /&gt;
&lt;br /&gt;
==== Attaque de préimage ====&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;How Merkle Trees Enable the Decentralized Web!&amp;quot;&#039;&#039;&#039;, Youtube (Coding Tech channel), https://www.youtube.com/watch?v=YIc6MNfv5iQ&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51662</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51662"/>
		<updated>2021-12-12T09:18:00Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51661</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51661"/>
		<updated>2021-12-12T09:00:20Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Perfect_Tree.png|thumb|right|&#039;&#039;&#039;Figure 4 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de création d&#039;arbre parfait (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Cette seconde méthode va consister à transformer n&#039;importe quel arbre déséquilibré en un arbre parfait dès la première itération. En d&#039;autres termes, quelque soit le nombre de blocs de données en entrée, on aura un arbre équilibré dès le premier niveau de branches (juste au dessus des feuilles). La différence avec la précédente approche où l&#039;on duplicait les nœuds impairs et les fusionnait avec eux-même est notable puisqu&#039;ici on ne va pas avoir à vérifier la parité du nombre de nœuds à chaque niveau mais seulement au tout début. L&#039;idée va donc être de pré-calculer le nombre de transformations nécessaires sur les feuilles pour que l&#039;on obtienne une quantité de nœuds au niveau suivant les feuilles qui soit une puissance de deux.&lt;br /&gt;
&lt;br /&gt;
L&#039;algorithme utilisé est le suivant :&lt;br /&gt;
* On commence par trouver &#039;&#039;x&#039;&#039;, tel que &#039;&#039;2^x&#039;&#039; soit supérieur au nombre de blocs de données. (cela revient à utiliser un logarithme en base 2)&lt;br /&gt;
* On soustrait ensuite à &#039;&#039;2^x&#039;&#039; le nombre de blocs de données, cela va nous donner l&#039;indice auquel nous allons commencer la première itération de construction de l&#039;arbre&lt;br /&gt;
* On procède en effectuant la première itération à partir du bloc de donnée correspondant à l&#039;indice trouvé.&lt;br /&gt;
* Une fois la première itération terminée, le nombre de nœuds à l&#039;itération suivante est une puissance de deux, on peut procéder normalement sans avoir à se soucier de potentiels problème de parité.&lt;br /&gt;
&lt;br /&gt;
Pour nous aider à visualiser le fonctionnement de cette approche, nous allons travailler avec l&#039;exemple de la &#039;&#039;&#039;figure 4&#039;&#039;&#039;. Au premier coup d&#039;œil on remarque que l&#039;abre a une structure un peu bizarre; on a deux niveaux de feuilles. Executons l&#039;algorithme sans attendre pour comprendre ce qu&#039;il se passe :&lt;br /&gt;
* On dispose de cinq blocs de données (Data1 jusqu&#039;à Data5). Si on cherche &#039;&#039;x&#039;&#039; tel que &#039;&#039;2^x &amp;gt; 5&#039;&#039;, on trouve &#039;&#039;2^3 = 8 &amp;gt; 4&#039;&#039;, soit &#039;&#039;x = 3&#039;&#039;.&lt;br /&gt;
* On soustrait désormais le nombre de blocs à la puissance trouvée, soit &#039;&#039;8 - 5 = 3&#039;&#039;, ce qui nous donne l&#039;indice de départ pour la première itération. On commencant à compter les indices à partir de zéro, l&#039;indice 3 va correspondre à Data4. Tous les blocs qui suivent Data4, lui y compris vont participer à la première itération. Tandis que tous ceux qui le précède vont attendre l&#039;itération d&#039;après.&lt;br /&gt;
* On lance la première itération qui ne concerne ici que Data4 et Data5. On va donc naturellement calculer leur hachage respectif, ce qui nous donne Hash4 et Hash5, que l&#039;on va concaténer et hacher de manière à obtenir Hash45, qui lui, appartient à la seconde itération. La première itération est désormais terminée puisque Data5 était le dernier nœud.&lt;br /&gt;
* On commence la seconde itération, avec cette fois non pas cinq nœuds mais quatre: Hash1, Hash2, Hash3 et le hachage Hash45 obtenu lors de l&#039;itération précédente. Comme le nombre de nœuds est une puissance de deux, rien de plus simple, on va concaténer Hash1 et Hash2 pour obtenir Hash12, et Hash3 et Hash45 pour obtenir Hash345. La seoncde itération se termine. La dernière itération va concaténer Hash12 et Hash345, ce qui va nous permettre d&#039;obtenir Hash12345.&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=File:Merkle_Tree_Perfect_Tree.png&amp;diff=51660</id>
		<title>File:Merkle Tree Perfect Tree.png</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=File:Merkle_Tree_Perfect_Tree.png&amp;diff=51660"/>
		<updated>2021-12-12T08:53:00Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: source: https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Summary ==&lt;br /&gt;
source: https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51640</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51640"/>
		<updated>2021-12-07T12:40:08Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|300px|thumb|right|&#039;&#039;&#039;Figure 1 :&#039;&#039;&#039; Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|&#039;&#039;&#039;Figure 2 :&#039;&#039;&#039; Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|&#039;&#039;&#039;Figure 3 :&#039;&#039;&#039; Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51639</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51639"/>
		<updated>2021-12-07T12:34:19Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|300px|thumb|right|Figure 1 : Exemple d&#039;arbre de Merkle]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque nœud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque nœud dépend des valeurs de ses nœuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les nœuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|Figure 2 : Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau nœud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (nœud de hauteur 2), deux nœuds de hauteur 1 et un nœud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois nœuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque nœud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de nœud, devons-nous changer la structure de l&#039;abre et autoriser des nœuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du nœud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|Figure 3 : Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les nœuds qui se retrouvent tout seul. Sur la &#039;&#039;&#039;figure 3&#039;&#039;&#039;, on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre arbre de Merkle se retrouve déséquilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons rencontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois nœuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième nœud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques.). Cela nous permet de faire un quatrième nœud, le nombre de nœuds du niveau étant paire, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de nœuds que le niveau précédent, ce qui nous ramène à deux nœuds. Comme la quantité de nœuds est paire, pas besoin de dupliquer de nœud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains nœuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51567</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51567"/>
		<updated>2021-12-05T16:11:54Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|300px|thumb|right|Simple Merkle Tree]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque noeud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque noeud dépend des valeurs de ses noeuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les noeuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau noeud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (noeud de hauteur 2), deux noeuds de hauteur 1 et un noeud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois noeuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque noeud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de noeud, devons-nous changer la structure de l&#039;abre et autoriser des noeuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du noeud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les noeuds qui se retrouvent tout seul. Sur la figure 4., on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre abre de Merkle se retrouve désequilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons recontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois noeuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième noeud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques). Cela nous permet de faire un quatrième noeud, le nombre de noeuds du niveau étant pair, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de noeuds que le niveau précédent, ce qui nous ramène à deux noeuds. Comme la quantité de noeuds est pair, pas besoin de dupliquer de noeud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. On pourrait cependant se poser des questions sur la fiabilité de cette solution de duplication. En effet, celle-ci est assez simple à mettre en place, mais il introduit une faille de sécurité notable car certains noeuds ne contiendront en réalité qu&#039;un seul hachage. (copié deux fois)&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51565</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51565"/>
		<updated>2021-12-05T16:09:24Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|300px|thumb|right|Simple Merkle Tree]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque noeud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque noeud dépend des valeurs de ses noeuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les noeuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau noeud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (noeud de hauteur 2), deux noeuds de hauteur 1 et un noeud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois noeuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque noeud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de noeud, devons-nous changer la structure de l&#039;abre et autoriser des noeuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du noeud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png|thumb|right|Équilibrage d&#039;un abre de Merkle en utilisant la technique de duplication (source: Medium)]]&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les noeuds qui se retrouvent tout seul. Sur la figure 4., on peut observer que l&#039;arbre de Merkle contient cinq feuilles. Cinq étant un chiffre impair, notre abre de Merkle se retrouve désequilibré. On va donc choisir de dupliquer la feuille se retrouvant toute seule pour ré-équilibrer l&#039;arbre. Ici, il va s&#039;agir de la feuille contenant le hachage du cinquième bloc de donnée : Hash5. La feuille va donc être copiée de manière à faire apparaître une sixième feuille contenant également Hash5. Il n&#039;y a plus de problème au niveau des feuilles de l&#039;arbre puisqu&#039;il y en a désormais une quantité paire. Cependant, nous allons recontrer un problème au niveau supérieur. En effet, nos six feuilles vont se transformer en trois noeuds et on retombe encore une fois sur une quantité impaire. On va donc ré-itérer le procédé et dupliquer cette fois le troisième noeud contenant Hash55 (On remarque que ce hachage est obtenu en appliquant la fonction de hachage sur la concaténation de deux hachages identiques). Cela nous permet de faire un quatrième noeud, le nombre de noeuds du niveau étant pair, on peut passer au niveau suivant. Pour l&#039;avant dernier niveau, on va avoir deux fois moins de noeuds que le niveau précédent, ce qui nous ramène à deux noeuds. Comme la quantité de noeuds est pair, pas besoin de dupliquer de noeud. L&#039;algorithme de duplication prend fin ici puisque le prochain niveau va simplement contenir la racine.&lt;br /&gt;
&lt;br /&gt;
Notre arbre de Merkle est donc désormais équilibré et exploitable. &lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51553</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51553"/>
		<updated>2021-12-03T16:25:06Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|300px|thumb|right|Simple Merkle Tree]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque noeud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque noeud dépend des valeurs de ses noeuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les noeuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau noeud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (noeud de hauteur 2), deux noeuds de hauteur 1 et un noeud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois noeuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque noeud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de noeud, devons-nous changer la structure de l&#039;abre et autoriser des noeuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du noeud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les noeuds qui se retrouvent tout seul. Dans l&#039;exemple suivant, on va donc dupliquer Hash5 de manière à pouvoir créer un parent dont les enfants seront deux copies de Hash5. On va réitérer l&#039;opération à chaque fois qu&#039;on montera d&#039;un niveau de manière à avoir un arbre équilibré.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png]]&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51552</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51552"/>
		<updated>2021-12-03T16:23:57Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|300px|thumb|right|Simple Merkle Tree]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque noeud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque noeud dépend des valeurs de ses noeuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les noeuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Très difficilement réversible&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de retrouver la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau noeud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (noeud de hauteur 2), deux noeuds de hauteur 1 et un noeud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois noeuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque noeud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de noeud, devons-nous changer la structure de l&#039;abre et autoriser des noeuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du noeud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les noeuds qui se retrouvent tout seul. Dans l&#039;exemple suivant, on va donc dupliquer Hash5 de manière à pouvoir créer un parent dont les enfants seront deux copies de Hash5. On va réitérer l&#039;opération à chaque fois qu&#039;on montera d&#039;un niveau de manière à avoir un arbre équilibré.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png]]&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51551</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51551"/>
		<updated>2021-12-03T16:22:34Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|300px|thumb|right|Simple Merkle Tree]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque noeud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque noeud dépend des valeurs de ses noeuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les noeuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de remonter à la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau noeud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (noeud de hauteur 2), deux noeuds de hauteur 1 et un noeud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois noeuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque noeud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de noeud, devons-nous changer la structure de l&#039;abre et autoriser des noeuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du noeud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les noeuds qui se retrouvent tout seul. Dans l&#039;exemple suivant, on va donc dupliquer Hash5 de manière à pouvoir créer un parent dont les enfants seront deux copies de Hash5. On va réitérer l&#039;opération à chaque fois qu&#039;on montera d&#039;un niveau de manière à avoir un arbre équilibré.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png]]&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51550</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51550"/>
		<updated>2021-12-03T16:20:15Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|300px|thumb|right|Simple Merkle Tree]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque noeud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque noeud dépend des valeurs de ses noeuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les noeuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par [https://fr.wikipedia.org/wiki/Idempotence idempotence], chaque donnée donnera toujours la même empreinte. En pratique, les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est due au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;a une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à résister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constitue cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage, c&#039;est la difficulté de remonter à la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant. Alors que l&#039;opération inverse, qui correspond à retrouver la donnée initiale à partir de l&#039;empreinte est mathématiquement extrêmement compliquée, et impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être le stockage de mots de passe. Lors d&#039;une inscription sur un site web, on ne va jamais stocker le mot de passe en clair dans une base de données. À la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. À chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocké dans la base au préalable, ce qui sécurise davantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
Nous avons évoqué plus haut le fait que les fonctions de hachages ne garantissent pas la bijectivité et que des collisions puissent arriver (deux données différentes avec la même empreinte), pour des données aussi petites que des mots de passe (une cinquantaine de caractères tout au plus), le phénomène de collisions a une probabilité d&#039;arriver quasi nulle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe chinoise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figure. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple.) Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents, comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en place ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre davantage, je vous invite à cliquer sur les différents liens hypertextes présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau noeud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (noeud de hauteur 2), deux noeuds de hauteur 1 et un noeud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois noeuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque noeud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de noeud, devons-nous changer la structure de l&#039;abre et autoriser des noeuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du noeud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les noeuds qui se retrouvent tout seul. Dans l&#039;exemple suivant, on va donc dupliquer Hash5 de manière à pouvoir créer un parent dont les enfants seront deux copies de Hash5. On va réitérer l&#039;opération à chaque fois qu&#039;on montera d&#039;un niveau de manière à avoir un arbre équilibré.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png]]&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51549</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51549"/>
		<updated>2021-12-03T16:10:30Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|300px|thumb|right|Simple Merkle Tree]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque noeud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque noeud dépend des valeurs de ses noeuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les noeuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique permettant d&#039;identifier la donnée initiale de manière unique. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par idempotence, chaque donnée donnera toujours la même empreinte. En pratique; les fonctions de hachages sont bijectives, dans le sens où chaque donnée a une seule empreinte et chaque empreinte ne correspond qu&#039;à une seule donnée. En théorie, la possibilité de surjectivité existe. Cela est dûe au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes est de taille fini contrairement à l&#039;ensemble des données en entrées qui lui peut être infini. On pourrait donc trouver deux données différentes partageant une même empreinte. Cependant, l&#039;ensemble d&#039;arrivée est en général suffisamment grand pour que ce phénomène ne se produise jamais. On parle souvent de la capacité qu&#039;à une fonction de hachage à [https://fr.wikipedia.org/wiki/R%C3%A9sistance_aux_collisions résister aux collisions] (deux données différentes partageant une même empreinte). Cette capacité à resister aux collisions varie en fonction des algorithmes. Certains algorithmes réduisent d&#039;ailleurs l&#039;ensemble d&#039;entrée en un ensemble fini pour s&#039;assurer que le phénomène de collision ne se produise jamais. La présence de collisions constituent cependant une faille de sécurité importante pour les fonctions de hachages et un problème qu&#039;on ne peut pas ignorer.&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage c&#039;est l&#039;incapacité de remonter à la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant, tandis que l&#039;opération inverse correspondant à retrouver la donnée initiale à partir de son empreinte est mathématiquement extrêmement compliquée, et de ce fait, impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être pour le stockage de mots de passe. Lors d&#039;une inscription sur un site Web, on ne va jamais stocker le mot de passe en clair dans une base de données. A la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. A chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocker dans la base au préalable, ce qui sécurise d&#039;avantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
Nous avons évoqué plus haut le fait que les fonctions de hachages ne garantissent pas la bijectivité et que des collisions puissent arriver (deux données différentes avec la même empreinte), pour des données aussi petites que des mots de passes (une cinquantaine de caractères tout au plus), le phénomène de collisions a une probabilité d&#039;arriver quasi nulle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe choise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figures. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple). Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en places ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre d&#039;avantage, je vous invite à cliquer sur les différents liens hypertexte présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau noeud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (noeud de hauteur 2), deux noeuds de hauteur 1 et un noeud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois noeuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque noeud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de noeud, devons-nous changer la structure de l&#039;abre et autoriser des noeuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du noeud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les noeuds qui se retrouvent tout seul. Dans l&#039;exemple suivant, on va donc dupliquer Hash5 de manière à pouvoir créer un parent dont les enfants seront deux copies de Hash5. On va réitérer l&#039;opération à chaque fois qu&#039;on montera d&#039;un niveau de manière à avoir un arbre équilibré.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png]]&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51548</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51548"/>
		<updated>2021-12-03T15:51:16Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|300px|thumb|right|Simple Merkle Tree]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque noeud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque noeud dépend des valeurs de ses noeuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les noeuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique qui va permettre d&#039;identifier rapidement la donnée initiale. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par idempotence, chaque donnée donnera toujours la même empreinte. Dans l&#039;idéal, on voudrait s&#039;assurer que les fonctions de hachages soient bijectives de manière à ce que chaque donnée ait une seule empreinte et que chaque empreinte ne corresponde qu&#039;à une seule donnée. En pratique, les fonctions de hachages sont surjectives, cela est dûe au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes soit de taille fini contrairement à l&#039;ensemble des données en entrées qui lui est infini. On pourra donc avoir deux données différentes qui ont la même empreinte. La fréquence à laquelle ce genre de phénomènes se produit dépend de l&#039;algorithme de hachage utilisé mais en principe, il est extrêmement peu probable que deux données différentes partagent la même empreinte.&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage c&#039;est l&#039;incapacité de remonter à la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant, tandis que l&#039;opération inverse correspondant à retrouver la donnée initiale à partir de son empreinte est mathématiquement extrêmement compliquée, et de ce fait, impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être pour le stockage de mots de passe. Lors d&#039;une inscription sur un site Web, on ne va jamais stocker le mot de passe en clair dans une base de données. A la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. A chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocker dans la base au préalable, ce qui sécurise d&#039;avantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
Nous avons évoqué plus haut le fait que les fonctions de hachages ne garantissent pas la bijectivité et que des collisions puissent arriver (deux données différentes avec la même empreinte), pour des données aussi petites que des mots de passes (une cinquantaine de caractères tout au plus), le phénomène de collisions a une probabilité d&#039;arriver quasi nulle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991 par [https://fr.wikipedia.org/wiki/Ronald_Rivest Ronald Rivest], qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe choise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figures. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple). Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en places ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre d&#039;avantage, je vous invite à cliquer sur les différents liens hypertexte présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau noeud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (noeud de hauteur 2), deux noeuds de hauteur 1 et un noeud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois noeuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque noeud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de noeud, devons-nous changer la structure de l&#039;abre et autoriser des noeuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du noeud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les noeuds qui se retrouvent tout seul. Dans l&#039;exemple suivant, on va donc dupliquer Hash5 de manière à pouvoir créer un parent dont les enfants seront deux copies de Hash5. On va réitérer l&#039;opération à chaque fois qu&#039;on montera d&#039;un niveau de manière à avoir un arbre équilibré.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png]]&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51547</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51547"/>
		<updated>2021-12-03T15:48:29Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|300px|thumb|right|Simple Merkle Tree]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque noeud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque noeud dépend des valeurs de ses noeuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les noeuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|Exemples de hachages obtenus en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique qui va permettre d&#039;identifier rapidement la donnée initiale. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par idempotence, chaque donnée donnera toujours la même empreinte. Dans l&#039;idéal, on voudrait s&#039;assurer que les fonctions de hachages soient bijectives de manière à ce que chaque donnée ait une seule empreinte et que chaque empreinte ne corresponde qu&#039;à une seule donnée. En pratique, les fonctions de hachages sont surjectives, cela est dûe au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes soit de taille fini contrairement à l&#039;ensemble des données en entrées qui lui est infini. On pourra donc avoir deux données différentes qui ont la même empreinte. La fréquence à laquelle ce genre de phénomènes se produit dépend de l&#039;algorithme de hachage utilisé mais en principe, il est extrêmement peu probable que deux données différentes partagent la même empreinte.&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage c&#039;est l&#039;incapacité de remonter à la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant, tandis que l&#039;opération inverse correspondant à retrouver la donnée initiale à partir de son empreinte est mathématiquement extrêmement compliquée, et de ce fait, impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être pour le stockage de mots de passe. Lors d&#039;une inscription sur un site Web, on ne va jamais stocker le mot de passe en clair dans une base de données. A la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. A chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocker dans la base au préalable, ce qui sécurise d&#039;avantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
Nous avons évoqué plus haut le fait que les fonctions de hachages ne garantissent pas la bijectivité et que des collisions puissent arriver (deux données différentes avec la même empreinte), pour des données aussi petites que des mots de passes (une cinquantaine de caractères tout au plus), le phénomène de collisions a une probabilité d&#039;arriver quasi nulle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991, qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe choise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figures. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple). Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en places ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre d&#039;avantage, je vous invite à cliquer sur les différents liens hypertexte présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau noeud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (noeud de hauteur 2), deux noeuds de hauteur 1 et un noeud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois noeuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque noeud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de noeud, devons-nous changer la structure de l&#039;abre et autoriser des noeuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du noeud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les noeuds qui se retrouvent tout seul. Dans l&#039;exemple suivant, on va donc dupliquer Hash5 de manière à pouvoir créer un parent dont les enfants seront deux copies de Hash5. On va réitérer l&#039;opération à chaque fois qu&#039;on montera d&#039;un niveau de manière à avoir un arbre équilibré.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png]]&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51546</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51546"/>
		<updated>2021-12-03T15:46:01Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|300px|thumb|right|Simple Merkle Tree]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque noeud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque noeud dépend des valeurs de ses noeuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les noeuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|Exemples de hachages en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique qui va permettre d&#039;identifier rapidement la donnée initiale. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par idempotence, chaque donnée donnera toujours la même empreinte. Dans l&#039;idéal, on voudrait s&#039;assurer que les fonctions de hachages soient bijectives de manière à ce que chaque donnée ait une seule empreinte et que chaque empreinte ne corresponde qu&#039;à une seule donnée. En pratique, les fonctions de hachages sont surjectives, cela est dûe au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes soit de taille fini contrairement à l&#039;ensemble des données en entrées qui lui est infini. On pourra donc avoir deux données différentes qui ont la même empreinte. La fréquence à laquelle ce genre de phénomènes se produit dépend de l&#039;algorithme de hachage utilisé mais en principe, il est extrêmement peu probable que deux données différentes partagent la même empreinte.&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage c&#039;est l&#039;incapacité de remonter à la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant, tandis que l&#039;opération inverse correspondant à retrouver la donnée initiale à partir de son empreinte est mathématiquement extrêmement compliquée, et de ce fait, impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être pour le stockage de mots de passe. Lors d&#039;une inscription sur un site Web, on ne va jamais stocker le mot de passe en clair dans une base de données. A la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. A chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocker dans la base au préalable, ce qui sécurise d&#039;avantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
Nous avons évoqué plus haut le fait que les fonctions de hachages ne garantissent pas la bijectivité et que des collisions puissent arriver (deux données différentes avec la même empreinte), pour des données aussi petites que des mots de passes (une cinquantaine de caractères tout au plus), le phénomène de collisions a une probabilité d&#039;arriver quasi nulle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991, qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe choise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figures. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple). Toutefois, il est à bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en places ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre d&#039;avantage, je vous invite à cliquer sur les différents liens hypertexte présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau noeud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (noeud de hauteur 2), deux noeuds de hauteur 1 et un noeud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois noeuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque noeud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de noeud, devons-nous changer la structure de l&#039;abre et autoriser des noeuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du noeud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les noeuds qui se retrouvent tout seul. Dans l&#039;exemple suivant, on va donc dupliquer Hash5 de manière à pouvoir créer un parent dont les enfants seront deux copies de Hash5. On va réitérer l&#039;opération à chaque fois qu&#039;on montera d&#039;un niveau de manière à avoir un arbre équilibré.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png]]&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
	<entry>
		<id>https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51545</id>
		<title>VT2021 Merkle Trees fiche</title>
		<link rel="alternate" type="text/html" href="https://air.imag.fr/index.php?title=VT2021_Merkle_Trees_fiche&amp;diff=51545"/>
		<updated>2021-12-03T15:44:29Z</updated>

		<summary type="html">&lt;p&gt;Corentin.Humbert: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;pre style=&amp;quot;color: red&amp;quot;&amp;gt;⚠️ Cette page est en cours de construction et de ce fait beaucoup d&#039;informations sont encore manquantes... ⚠️&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Présenté par :&lt;br /&gt;
* Corentin Humbert : [mailto:corentin.humbert@etu.univ-grenoble-alpes.fr corentin.humbert@etu.univ-grenoble-alpes.fr] &lt;br /&gt;
* Kévin Yung : [mailto:kevin.yung@etu.univ-grenoble-alpes.fr kevin.yung@etu.univ-grenoble-alpes.fr]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
= Merkle Trees =&lt;br /&gt;
&lt;br /&gt;
== Résumé ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mots-clé&#039;&#039;&#039;: Merkle, arbres, hachage, structure de données, validation&lt;br /&gt;
&lt;br /&gt;
== Abstract ==&lt;br /&gt;
&lt;br /&gt;
Merkle Trees are binary trees in which every node is labelled with a cryptographic hash. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Keywords&#039;&#039;&#039;: Merkle, Trees, hash, data structure, validation&lt;br /&gt;
&lt;br /&gt;
== Fonctionnement ==&lt;br /&gt;
&lt;br /&gt;
=== Principe ===&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree.png|300px|thumb|right|Simple Merkle Tree]]&lt;br /&gt;
&lt;br /&gt;
Les arbres de Merkle sont des arbres binaires utilisés pour effectuer de la validation de données. Pour ce faire, chaque feuille de l&#039;arbre va contenir le hachage correspondant à une partie de la donnée à valider. Chaque noeud de l&#039;arbre va également contenir un hachage. Ce hachage est obtenu en concaténant le hachage des deux enfants et en passant le résultat dans une fonction pour créer un tout nouveau hachage. Il se construit alors une dépendance générale où la valeur de chaque noeud dépend des valeurs de ses noeuds enfants.&lt;br /&gt;
&lt;br /&gt;
L&#039;image ci-dessous contient un arbre de Merkle servant à valider une donnée découpée en quatre blocs (Data Nodes). Les feuilles de l&#039;abre (Merkle leaves) vont contenir le hachage correspondant pour chaque bloc. Les noeuds intermédiaires (Merkle branches) vont contenir le hachage issu de la concaténation des hachages de leurs deux enfants. Enfin, la racine de l&#039;arbre (Merkle root) va contenir le hachage final servant à identifier l&#039;arbre de Merkle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Un point sur le hachage ===&lt;br /&gt;
&lt;br /&gt;
Avant de s&#039;immiscer dans le fonctionnement des arbres, il est important de parler du &#039;&#039;&#039;hachage&#039;&#039;&#039; et plus particulièrement des fonctions de hachage.&lt;br /&gt;
&lt;br /&gt;
[[File:Hashing_Principle.png|400px|thumb|right|Exemples de hachages en utilisant MD5 (source: Wikipedia)]]&lt;br /&gt;
&lt;br /&gt;
En cryptographie, une fonction de hachage est une fonction qui, à partir d&#039;une donnée fournie en entrée, va être capable de calculer une empreinte numérique qui va permettre d&#039;identifier rapidement la donnée initiale. La taille en sortie de cette empreinte est fixe et ne dépend pas de la taille de la donnée en entrée. Par idempotence, chaque donnée donnera toujours la même empreinte. Dans l&#039;idéal, on voudrait s&#039;assurer que les fonctions de hachages soient bijectives de manière à ce que chaque donnée ait une seule empreinte et que chaque empreinte ne corresponde qu&#039;à une seule donnée. En pratique, les fonctions de hachages sont surjectives, cela est dûe au fait que l&#039;ensemble d&#039;arrivée correspondant aux empreintes soit de taille fini contrairement à l&#039;ensemble des données en entrées qui lui est infini. On pourra donc avoir deux données différentes qui ont la même empreinte. La fréquence à laquelle ce genre de phénomènes se produit dépend de l&#039;algorithme de hachage utilisé mais en principe, il est extrêmement peu probable que deux données différentes partagent la même empreinte.&lt;br /&gt;
&lt;br /&gt;
Ce qui fait la puissance et la fiabilité d&#039;une fonction de hachage c&#039;est l&#039;incapacité de remonter à la donnée initiale à partir de son empreinte. Il est très simple, pour une donnée en entrée, de calculer le hachage correspondant, tandis que l&#039;opération inverse correspondant à retrouver la donnée initiale à partir de son empreinte est mathématiquement extrêmement compliquée, et de ce fait, impossible à mettre en place sur les ordinateurs de nos jours. Une utilisation notable du hachage va être pour le stockage de mots de passe. Lors d&#039;une inscription sur un site Web, on ne va jamais stocker le mot de passe en clair dans une base de données. A la place, on va calculer le hachage correspondant au mot de passe et le stocker dans la base. A chaque fois que l&#039;on voudra s&#039;authentifier sur le site en rentrant le mot de passe, le hachage sera calculé et comparé à celui présent dans la base de données. Si les deux sont égaux, alors il s&#039;agit du bon mot de passe. On peut donc vérifier qu&#039;un mot de passe est valide sans l&#039;avoir stocker dans la base au préalable, ce qui sécurise d&#039;avantage les comptes utilisateurs.&lt;br /&gt;
&lt;br /&gt;
Nous avons évoqué plus haut le fait que les fonctions de hachages ne garantissent pas la bijectivité et que des collisions puissent arriver (deux données différentes avec la même empreinte), pour des données aussi petites que des mots de passes (une cinquantaine de caractères tout au plus), le phénomène de collisions a une probabilité d&#039;arriver quasi nulle.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Résistance aux collisions&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Les fonctions de hachage ont tout de même quelques faiblesses notables. La première, réside dans la complexité de l&#039;algorithme de hachage et de sa résistance aux collisions. C&#039;est le cas de la fonction [https://fr.wikipedia.org/wiki/MD5 MD5] inventée en 1991, qui a pu être utilisée de manière fiable jusqu&#039;en 2004 où une équipe choise a réussi à casser la fonction et prouver qu&#039;elle ne garantissait une assez bonne résistance aux collisions. Le MD5 est aujourd&#039;hui encore utilisé dans certains cas de figures. (notamment pour vérifier l&#039;intégrité d&#039;une donnée, c&#039;est le cas pour les sommes de contrôle de certaines distributions Linux par exemple). Toutefois, il est bannir pour le hachage de mots de passe qui sont des données extrêmement sensibles. Il existe aujourd&#039;hui des fonctions de hachage sécurisées telles que les fonctions dites [https://fr.wikipedia.org/wiki/Secure_Hash_Algorithm SHA] (pour Secure Hashing Algorithm) et plus précisément les familles de fonctions [https://fr.wikipedia.org/wiki/SHA-2 SHA-2] et [https://fr.wikipedia.org/wiki/SHA-3 SHA-3] qui n&#039;ont pas encore été cassées.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Limites du hachage&#039;&#039;&#039;&lt;br /&gt;
&lt;br /&gt;
Une autre faiblesse des fonctions de hachage est l&#039;idempotence. Puisque chaque donnée a une empreinte unique, un attaquant pourrait calculer en amont les hachages pour des centaines de millions de données différentes et se contenter de les comparer à des hachages volés dans des bases de données de manière à identifier la donnée source. Dans le cadre du vol de mot de passe, on parle de [https://fr.wikipedia.org/wiki/Rainbow_table rainbow table] qui sont simplement des gigantesques tables faisant correspondre un mot de passe à son hachage. Il existe différentes méthodes que l&#039;on peut mettre en place pour limiter le vol de mots de passe tel que le principe de [https://fr.wikipedia.org/wiki/Salage_(cryptographie) salage] ou encore l&#039;utilisation d&#039;algorithmes lents comme [https://fr.wikipedia.org/wiki/Bcrypt bcrypt] visant à ralentir l&#039;opération de hachage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Enfin, il est important de garder à l&#039;esprit que toutes les méthodes mises en places ne résolvent pas le problème, elles visent simplement à ralentir considérablement les attaquants. Un attaquant disposant de suffisamment de temps et de puissance de calcul finira par retrouver n&#039;importe quel mot de passe. Il y a également les récentes innovations au niveau des ordinateurs quantiques qui sont vouées à compromettre significativement les dispositifs de sécurité mis en place sur Internet aujourd&#039;hui. Nous ne nous étendrons pas plus sur le sujet du hachage dans ce document, si vous désirez en apprendre d&#039;avantage, je vous invite à cliquer sur les différents liens hypertexte présents dans cette partie.&lt;br /&gt;
&lt;br /&gt;
=== Création d&#039;un arbre ===&lt;br /&gt;
&lt;br /&gt;
Pour réaliser un arbre de Merkle pour une donnée particulière, on va commencer par découper la donnée en entrée en un certain nombres de blocs. Le nombre de blocs va varier en fonction de la taille de la donnée. Une fois la donnée scindée en blocs, on va calculer pour chaque bloc son hachage et l&#039;ajouter à l&#039;arbre de Merkle. Deux blocs consécutifs vont être reliés par un nouveau noeud parent dont le hachage sera calculé en effectuant la concaténation des deux hachages enfant et en hachant une dernière fois ce résultat. On va réitérer cette opération pour chaque bloc, jusqu&#039;à ce que tous les blocs de données hachés appartiennent à l&#039;abre et qu&#039;une racine soit calculée. Une fois la racine obtenue, la construction de l&#039;abre est terminée.&lt;br /&gt;
&lt;br /&gt;
Pour ce qui est de l&#039;algorithme de hachage utilisé, celui-ci va varier en fonction des implémentations. Généralement, on utilisera des fonctions de hachage robustes tel que le SHA2 ou SHA3.&lt;br /&gt;
&lt;br /&gt;
=== Arbre de Merkle désiquilibré ===&lt;br /&gt;
&lt;br /&gt;
Nous avons parlé précédemment de comment les abres de Merkel étaient construits mais nous avons oublié d&#039;évoquer un point. L&#039;algorithme décrit marche très bien lorsque le nombre de blocs en entrée est une puissance de 2. Par exemple, avec quatre blocs, on aura quatre feuilles (noeud de hauteur 2), deux noeuds de hauteur 1 et un noeud de hauteur 0 (la racine). Mais que se passe-t-il si au lieu d&#039;avoir quatre blocs, nous en avions six ? Nous aurions alors six feuilles, trois noeuds de hauteur 1 et...&lt;br /&gt;
Comment faire? Chaque noeud ne peut avoir que deux enfants et nous nous trouvons avec un nombre impair de noeud, devons-nous changer la structure de l&#039;abre et autoriser des noeuds à avoir trois enfants ?&lt;br /&gt;
&lt;br /&gt;
Ils existent différentes approches permettant de pallier ce problème.&lt;br /&gt;
&lt;br /&gt;
==== Duplication du noeud impair (Bitcoin) ====&lt;br /&gt;
&lt;br /&gt;
Pour cette première approche, on va dupliquer les noeuds qui se retrouvent tout seul. Dans l&#039;exemple suivant, on va donc dupliquer Hash5 de manière à pouvoir créer un parent dont les enfants seront deux copies de Hash5. On va réitérer l&#039;opération à chaque fois qu&#039;on montera d&#039;un niveau de manière à avoir un arbre équilibré.&lt;br /&gt;
&lt;br /&gt;
[[File:Merkle_Tree_Duplicating_Node.png]]&lt;br /&gt;
&lt;br /&gt;
==== Création d&#039;un arbre parfait (Monero) ====&lt;br /&gt;
&lt;br /&gt;
=== Validation de données ===&lt;br /&gt;
&lt;br /&gt;
=== Limites et faiblesses ===&lt;br /&gt;
&lt;br /&gt;
== Cas d&#039;utilisations ==&lt;br /&gt;
&lt;br /&gt;
=== Blockchain ===&lt;br /&gt;
&lt;br /&gt;
=== Amazon AWS DynamoDB ===&lt;br /&gt;
&lt;br /&gt;
=== Système de fichier ZFS ===&lt;br /&gt;
&lt;br /&gt;
=== Git ===&lt;br /&gt;
&lt;br /&gt;
== Références ==&lt;br /&gt;
&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle tree&amp;quot;&#039;&#039;&#039;, Wikipedia, https://en.wikipedia.org/wiki/Merkle_tree&lt;br /&gt;
* &#039;&#039;&#039;&amp;quot;Merkle Trees: Concepts and Use Cases&amp;quot;&#039;&#039;&#039;, Medium, https://medium.com/coinmonks/merkle-trees-concepts-and-use-cases-5da873702318&lt;/div&gt;</summary>
		<author><name>Corentin.Humbert</name></author>
	</entry>
</feed>