Plates-formes et mises à jour dynamiques configurables

Mettre à jour un logiciel nécessite usuellement son redémarrage : il faut sauvegarder son état, l’arrêter, modifier son code, le démarrer à nouveau et enfin, recharger son état. Si cette tâche s’avère déjà ennuyeuse dans le cas d’un logiciel de bureautique ou d’un système d’exploitation personnel, elle devient coûteuse ou impossible dans certains domaines particuliers. En effet, mettre à jour un service informatique de manière traditionnelle le rend indisponible, générant des manques à gagner pour les services commerciaux ou causant des problèmes de sécurité pour des services critiques (par exemple, les systèmes d’une tour de contrôle aérien). Différentes solutions sont adoptées pour palier à cette indisponibilité. L’une d’entre elles consistant en la distribution des services sur de nombreux serveurs dont les logiciels sont mis à jour à tour de rôle, assurant ainsi un service minimum en permanence. Ces solutions viennent avec leurs propres avantages et inconvénients qui ne seront pas explicités ici. Il est seulement à noter qu’elles ne s’adressent qu’à un problème : maintenir la disponibilité de services lors de leurs redémarrages.

Le domaine de la mise à jour dynamique (DSU pour Dynamic Software Updating) s’adresse, à un autre problème : mettre à jour les logiciels sans que leur redémarrage ne soit nécessaire. Dans cette optique, de nombreuses plates-formes ont été développées. Ces plates-formes sont combinées avec les programmes, qui constituent les logiciels, avant leur démarrage. Chaque fois qu’une mise à jour dynamique est invoquée, la plate-forme utilise des mécanismes pour appliquer les modifications au programme. Ce dernier continue son exécution, sans interruption de service, et paraît n’avoir jamais été mis à jour : il semblera, pour un observateur extérieur, que le programme a été lancé dans sa version la plus récente depuis le départ. D’une manière générale, il est voulu que la plate-forme soit la plus transparente possible. C’est-à-dire qu’à chaque mise à jour, les développeurs doivent fournir le moins d’informations possible. Dans ce but, seul le code de la nouvelle version du programme, parfois associé à quelques instructions supplémentaires, est demandé aux développeurs et aux personnes appliquant la mise à jour. Les mécanismes employés pour appliquer la mise à jour sont toujours les mêmes durant toute la vie du programme. En conséquence, les capacités des plates-formes en terme d’application de mises à jour sont limitées. En effet, chaque mécanisme de mise à jour a ses avantages et inconvénients et peut, en conséquence, ne pas être compatible avec l’application de certaines modifications. En fixant une combinaison de mécanismes employée pour chaque mise à jour, les plates-formes se spécialisent quant au type de modifications qu’elles peuvent supporter. Ainsi, la majorité des plates-formes se spécialise dans l’application de correctifs de bugs ou de failles de sécurité qui ne changent pas la sémantique du programme .

Par exemple, la plate-forme OPUS [2] permet de mettre à jour des programmes C dynamiquement à la condition que les modifications se limitent aux fonctions et n’en changent pas la sémantique. C’est-àdire que les mises à jour ne peuvent ni changer la signature des fonctions, ni changer leurs effets de bord (les opérations d’écriture sur la mémoire partagée avec le reste du programme ne doivent pas changer lors d’une mise à jour). De telles restrictions proviennent du choix des mécanismes employés, guidé par l’objectif de la plate-forme : permettre d’appliquer des mises à jour corrigeant des bugs ou des failles de sécurité. En effet, il est peu fréquent qu’une mise à jour corrective change la sémantique des fonctions d’un programme ou qu’elle affecte les données traitées par le programme (types, variables).

Conventions de nommage et modèles

Le présent manuscrit, utilise certains termes pour identifier les éléments en jeu lors d’une mise à jour dynamique et présentera les logiciels selon un modèle présenté dans cette section. Chaque fois que ces usages ou que ce modèle sera invalidé, cela sera précisé. Dans les prochains chapitres, un logiciel est un ensemble de programmes coopérant dans un objectif commun. Une plate-forme se combine à un programme et il est imaginable d’utiliser plusieurs platesformes différentes pour mettre à jour les différents programmes d’un même logiciel. Dans la suite du manuscrit, seule la mise à jour d’un unique programme est considérée, qu’il s’agisse de mettre à jour l’unique programme d’un logiciel ou de mettre à jour partiellement un plus gros logiciel en modifiant un de ses programmes. S’il est possible de voir la mise à jour d’un logiciel complet comme plusieurs mises à jour simultanées des différents programmes qui le composent pour des cas simples, des cas complexes peuvent invalider cette généralisation. Toutefois, les logiciels constitués d’un unique programme sont suffisamment nombreux pour que la contribution faite dans ce manuscrit soit intéressante.

Structure d’un programme

Afin de pouvoir parler des programmes en général, la modélisation suivante  est adoptée dans ce manuscrit : chaque programme est composé d’un ou plusieurs fils d’exécution qui exécutent des fonctions et utilisent des données. Ces données peuvent ensuite se diviser en deux catégories : les données liées à l’exécution du programme (pointeur d’instruction courante, pile d’exécution, …) et les données liées à la logique du programme (variables, objets, …). Les données de la seconde catégorie sont souvent caractérisées par des types définis par le programme ou son système d’exécution. Les données logiques sont manipulées directement par les développeurs du programme et des mises à jour. Le développeur du programme définit les types et créé les variables, le développeur de mise à jour indique comment mettre à jour ces types et ces variables. Les données d’exécution sont généralement manipulées par les mécanismes de mise à jour dynamique dans le but de maintenir un état cohérent du programme (par exemple en modifiant la pile d’exécution pour changer toutes les références à du code obsolète et les remplacer par des références vers la nouvelle version). Dans ce manuscrit, le terme données désigne les données logiques d’un programme, sauf mention du contraire.

Structure d’une mise à jour

Dans ce manuscrit, une distinction est faite entre développeur du programme et développeur de mise à jour, le premier fournissant le logiciel original et le second fournissant les mises à jour (qui peuvent inclure plus que le code de la nouvelle version des programmes). Même si en pratique, ce sont souvent les mêmes personnes physiques qui remplissent ces deux rôles, cette distinction permettra de discerner ces deux rôles qui agissent à deux étapes différentes de la vie d’un logiciel en utilisant des méthodes et des outils éventuellement différents. Ce que le développeur de mise à jour doit fournir pour chaque mise à jour dynamique dépend de la ou des plates-formes utilisées. Ces entrées sont généralement transformées en un tout communément appelé patch dynamique dans le domaine. Ce manuscrit identifie deux composants élémentaires d’un patch dynamique : le nouveau code et le script de mise à jour. Le premier peut être le code de la nouvelle version du programme, le code des éléments modifiés du programme ou encore un diff des codes originaux et modifiés (code source, bytecode ou encore binaire). Le second est une série d’instructions indiquant quelles tâches doivent être accomplies pour mettre à jour le programme. Selon les plates-formes, le script de mise à jour peut contenir plus ou moins d’instructions en fonction de la marge de manœuvre laissée au développeur des mises à jour. Par exemple, dans le cas d’une plate-forme fixant de manière permanente tous les mécanismes qu’elle utilise comme OPUS [2], le script de mise à jour est vide. Il est à noter que dans un tel cas, le script de mise à jour est considéré comme fixé par la plate forme, et ce pour toutes les mises à jour. Le nouveau code est donc intégralement fourni dans le patch dynamique tandis que le script de mise à jour peut être en partie fixé par la plate-forme. La suite de ce manuscrit montrera que dans une majorité de cas, la plate-forme fixe l’intégralité du script de mise à jour et que le patch dynamique ne contient que le nouveau code.

Principes de base de la mise à jour dynamique

Pour pouvoir mettre à jour dynamiquement un programme, il faut habituellement le combiner avec une plate-forme avant de le démarrer. Suivant la plate-forme utilisée, cela peut nécessiter de modifier le code du programme (par exemple, Kitsune [44] demande de placer des points de mise à jour dans le code du programme). Lorsqu’une mise à jour est requise par un développeur, un patch dynamique est généré. Il précise quels éléments du programme vont être modifiés et quelles sont ces modifications. Le patch est ensuite soumis à la plate-forme qui agira, soit elle-même, soit par l’intermédiaire d’un gestionnaire de mise à jour. La première étape est d’abord de charger le nouveau code dans le programme. Il faut ensuite attendre un moment propice à la mise à jour. En effet, si le programme n’est pas dans un état stable, appliquer une mise à jour peut provoquer des erreurs, ou le crash du programme. Par exemple, une fonction fraîchement mise à jour peut tenter d’accéder à de vieilles données qui ne sont plus compatibles. Généralement, dans cet état stable, les éléments modifiés ou les éléments qui leurs sont liés sont quiescents. C’est-à-dire que ces éléments ne sont pas utilisés et ne le seront pas dans un futur proche. Par extension un peu abusive, cet état stable est communément appelé quiescence du programme. Cependant, il existe aussi d’autres conditions de stabilité plus ou moins restrictives que la quiescence. Pour éviter toute confusion, la suite de ce manuscrit appellera altérabilité tout état stable propice à la mise à jour.

Lorsque le programme est altérable (dans un état d’altérabilité), son exécution est suspendue et les modifications peuvent être appliquées : il faut remplacer les fonctions obsolètes par leur nouvelle version, mettre à jour les types puis accéder aux données et les transformer pour qu’elles adoptent la nouvelle version de leur type. Pour chaque type de modification, il existe plusieurs mécanismes dans la littérature, chacun utilisant une méthode différente avec ses propres avantages, exigences et désavantages. Lorsque toutes les modifications ont été appliquées, l’exécution du programme est reprise. Ainsi, le programme continuera son exécution dans sa nouvelle version, comme s’il avait été démarré dans sa dernière version depuis le début.

Si les fonctions et les types sont identifiables dans le programme, les données peuvent être statiques (variables globales, constantes, …) ou dynamiques (objets crées par l’exécution du programme, fils d’exécution, …). Les éléments statiques étant définis explicitement par le développeur du programme sont faciles d’accès lors de la mise à jour : le développeur de la mise à jour peut explicitement faire référence à un élément statique donné. Les éléments dynamiques sont plus difficiles à modifier car le développeur de la mise à jour peut ignorer leur existence (par exemple, il ne connaît pas a priori l’ensemble des objets créés par l’exécution du programme). Il doit alors faire référence à ces éléments à partir des éléments statiques (toutes les variables d’un type donné, tous les fils d’exécution exécutant une fonction donnée, …). Généralement, les éléments dynamiques qu’un développeur de mise à jour souhaite accéder font partie de l’ensemble des données du programme. C’est pourquoi les plates-formes fournissent des mécanismes permettant l’accès aux données dynamiques : d’où le nom de cette tâche : accès aux données.

Le rapport de stage ou le pfe est un document d’analyse, de synthèse et d’évaluation de votre apprentissage, c’est pour cela chatpfe.com propose le téléchargement des modèles complet de projet de fin d’étude, rapport de stage, mémoire, pfe, thèse, pour connaître la méthodologie à avoir et savoir comment construire les parties d’un projet de fin d’étude.

Table des matières

1 Introduction
1.1 Conventions de nommage et modèles
1.1.1 Structure d’un programme
1.1.2 Structure d’une mise à jour
1.2 Principes de base de la mise à jour dynamique
2 Etat de l’art
2.1 Précédents états de l’art
2.2 Plates-formes pour langages compilés
2.2.1 OPUS .
2.2.2 Ginseng
2.3 Plates-formes pour langages à machine virtuelle
2.3.1 Jvolve
2.3.2 ActiveContext
2.4 Systèmes d’exploitation
2.4.1 Ksplice
2.4.2 K42
2.5 Travaux similaires ou connexes
2.6 Des mécanismes divers mais transversaux
I Analyse des plates-formes
3 Une étude centrée mécanismes
3.1 Limitations des taxonomies
3.2 Un modèle générique
3.3 Terminologie
3.3.1 Altérabilité
3.3.2 Gestionnaire de mise à jour
3.3.3 Stratégie de mise à jour des données
3.4 Cycle de vie générique
4 Analyse des plates-formes
4.1 Cycle de vie
4.1.1 Observations
4.2 Architecture
4.2.1 Choix de conception
4.2.2 Observations
4.3 Mécanismes de mise à jour
4.3.1 Tâches de mise à jour
4.3.2 Observations
4.4 Quelques cas d’étude
4.4.1 Kitsune
4.4.2 ProteOS
4.5 Bilan
5 Analyses statistiques
5.1 Une étude exploratoire des combinaisons de mécanismes
5.2 Détection des motifs fréquents
5.2.1 Propriétés fréquentes
5.2.2 Combinaisons fréquentes de propriétés
5.2.3 Synergies entre propriétés
5.3 Familles de plates-formes
5.3.1 Familles d’architecture
5.3.2 Familles de combinaison de mécanismes
5.3.3 Familles de cycles de vie
5.3.4 Familles générales
5.4 Diversité des combinaisons et construction de mises à jour
II Exigences des mécanismes
6 Sémantique opérationnelle
6.1 λDSU : λ-calcul étendu
6.1.1 Grammaire
6.1.2 Règles de réduction
6.2 Programme de mise à jour dynamique
6.2.1 Grammaire du langage de mise à jour
6.2.2 Réduction d’une mise à jour
6.3 Autres sémantiques
6.4 Premiers résultats
7 Étude de mises à jour dynamiques
7.1 Altérabilité
7.1.1 Quiescence d’une fonction
7.1.2 Point de mise à jour
7.2 Modification des données
7.2.1 Accès aux données
7.2.2 Transformation des données
7.3 Modification du flot de contrôle
7.3.1 Redéfinition de fonction
7.3.2 Redémarrage des fils d’exécution
7.4 Bilan
7.4.1 Expression des mises à jour
7.4.2 Mécanismes et exigences
III Implémentation de plates-formes
8 Architecture Starmoult
8.1 Utilisation d’une plate-forme Starmoult
8.2 L’ Architecture Starmoult
8.2.1 Gestionnaires et unités de mise à jour
8.2.2 Cycle de vie
8.3 Une architecture universelle
9 Pymoult
9.1 Retour sur l’architecture
9.1.1 Gestionnaires
9.1.2 Unités de mise à jour
9.1.3 Patch dynamique
9.1.4 Listener
9.2 Quelques fonctionnalités de Python
9.3 Implémentation de mécanismes
9.3.1 Détection de quiescence
9.3.2 Redéfinition de fonctions
9.3.3 Redémarrage de fil d’exécution
9.3.4 Accès aux données
9.4 Interpréteurs
9.5 Une plate-forme de prototypage
10 Cmoult
10.1 Instrumentation du code
10.2 Implémentation de mécanismes
10.2.1 Suspension de fils d’exécution
10.2.2 Redéfinition de fonctions
10.2.3 Détection de la quiescence
10.3 Impact sur l’architecture
11 Quelques cas d’utilisation de Pymoult
11.1 Exemples de combinaisons de mécanismes
11.1.1 Le programme
11.1.2 Compression des données en cache
11.1.3 Durée de vie des données en cache
11.1.4 Concevoir la stratégie de mise à jour
11.2 Applications concrètes
11.2.1 Pyftpdlib
11.2.2 Django
11.2.3 Coqcots & Pycots
11.3 Discussion
12 Conclusion

Lire le rapport complet

Télécharger aussi :

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *