43
Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement et utilisation Département d’informatique et de génie logiciel

Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Embed Size (px)

Citation preview

Page 1: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Programme de baccalauréat en informatique Programmation Orientée Objets

IFT-19946

Thierry EUDEThierry EUDE

Module 6. Gestion des erreurs et des exceptions :

Fonctionnement et utilisation

Département d’informatique et de génie logiciel

Page 2: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

2

Erreurs et exceptions

On rencontre fréquemment des erreurs ou des exceptions dans les programmes.

Erreurs :•des erreurs d'entrée de données par l'usager•des erreurs du matériel ou de périphérique•des erreurs de limitations ressources du système•des erreurs de programmation de composants logiciels.

Page 3: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

3

Exceptions :

débordement de capacité d'un nombre ;division par zéro ;paramètre de fonction invalide ;connexion réseau non disponible ou interrompue.

Page 4: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

4

• Erreur d'entrée de données de l'utilisateur

L'utilisateur peut :• saisir une date invalide• demander de lire un fichier inexistant• demander d'afficher le contenu de ie dossier qui est en dehors

des limites d'un conteneur.Dans un programme interactif :

- on informe l'utilisateur du problème- on attend de nouvelles directives.

Dans un programme non interactif :- on fait le rapport de l'erreur dans un fichier- on tente de continuer ou on arrête.

Erreurs

Page 5: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

5

• Erreur du matériel ou de périphérique

Exemples :- le port série n'est pas disponible- l'imprimante peut être hors tension ou ne plus avoir de papier.

Arrêt ou suspension de la tâche en attendant que le problème soit réglé.

L'imprimante n'a plus de papier au milieu de la tâche. Le programme peut alors :

• avertir l'utilisateur de la situation• attendre qu'il nous dise quoi faire sans quitter.

Page 6: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

6

• Erreur de limitation de ressources du système

Cas typiques :• disque dur ou disquette plein• plus de mémoire disponible• plus de ressource Windows disponible (Font, Brush...)

Si un scénario est détecté, on peut :• avertir l'utilisateur de la situation en lui demandant de libérer

des ressources (si possible)• attendre ses instructions (réessayer ou annuler) sans quitter le

programme.

Page 7: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

7

• Erreur de programmation d'un composant logiciel

Exemples typiques :• tenter de créer une date invalide• tenter d'obtenir le dessus d'une pile vide• tenter d'obtenir un élément dans un vecteur qui est hors

limite.

difficile d'adopter une stratégie adaptée à toutes les situations :

• parfois, lancer une exception de contrat et arrêter le programme suffit.

• parfois, avertir l'usager, sauvegarder son travail et quitter élégamment est préférable.

Page 8: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

8Réagir à ces conditions d'erreur au niveau du code

•retourner un code d'erreur•assigner une valeur à une variable globale d'erreur•ignorer l'erreur (!)•imprimer un message d'erreur•arrêter le programme•lancer une exception.

Page 9: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

9

• Retourner un code d'erreur

Façon de faire très fréquemment rencontrée dans les programmes :

• une valeur ou un ensemble de valeurs indiquent une situation d'erreur.

Exemple : • la fonction fopen de la librairie du C standard

retourne un pointeur valide si l'ouverture du fichier a été réussie

un pointeur NULL autrement.

FILE* fopen(const char* fichierP);

Page 10: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

10

Le programmeur a la responsabilité de vérifier le code de retour de la fonction pour s'assurer du succès de l'appel :FILE* fP = fopen("toto.txt");if (fP != NULL){ // --- Écrire dans le fichier}else{

// --- Gérer l'erreur}

Page 11: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

11

Dans certains cas, il est difficile de trouver une valeur désignant la situation d'erreur :

• Une fonction qui retourne un entier dont toutes les valeurs peuvent être valides n'a pas vraiment de moyen pour retourner une erreur (0 pouvant être valide).

• Souvent, on rencontre des standards dans lequel toutes les fonctions retournent un code d'erreur. Les valeurs de retour (données en retour) sont passées en paramètre.

Page 12: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

12

Exemple

bool fonct1(double v, int& ret);

int fonct2(double v, int& ret);

fonct1 retourne true en cas de succès et false autrement.fonct2 pourrait retourner différentes valeurs entières

spécifiant des cas d'erreur et un cas valide.

Dans les deux cas, les valeurs retournées passent par les paramètres et le retour ne sert qu'aux codes d'erreur.

Page 13: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

13

• Variable globale d'erreur

La plupart des fonctions de la librairie standard du C fonctionnent avec la célèbre variable globale errno.

Exemple :• si on appelle unlink pour effacer un fichier, la fonction retourne 0 en cas de succès et -1 autrement.

• En cas d'erreur, on a assigné un code d'erreur à la variable globale errno :EACCES: Accès interditENOENT: Chemin d'accès ou fichier introuvable

Page 14: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

14

Exemple

void main(){ const char* fichierP = "log.bak"; if (unlink(fichierP) == -1) { if (errno==EACCES) { cout << "L'accès au fichier : "

<< fichierP << " est interdit" << endl; } else if (errno == ENOENT) { cout << "Le fichier ou le chemin d'acces"

<< " est introuvable" << endl; } }}

Page 15: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

15

Problème important :• approche non compatible avec une architecture multi-tâche.

On doit protéger l'accès à cette variable globale...• On peut perdre de l'information si deux erreurs se produisent coup sur coup. La première erreur est écrasée par la seconde

potentiellement on peut mal interpréter la signification de l'erreur.

Page 16: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

16

• Ignorer l'erreur

Prendre la décision de ne rien faire en cas de demande erronée peut parfois être la seule solution «raisonnable».

• Beaucoup de fonctions de la librairie standard ont un comportement «non défini» lors d'appel invalide.

• Que ce passe-t-il si on tente d'accéder un vecteur en dehors de ses limites ? (On ne sait pas !!!)

Ce style de programmation n'est pas à favoriser car il peut masquer des erreurs importantes.

Page 17: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

17

• Imprimer un message d'erreur

Imprimer un message d'erreur décrivant l'erreur :• est acceptable pour un petit programme en phase de

débogage.• est inacceptable pour un logiciel commercial.

L'utilisateur ne devrait voir que des messages qui ont du sens pour lui et sur lesquels il peut prendre action.

Exemple :• si on l'avertit que le disque est plein, il peut effacer des fichiers

pour libérer de l'espace et poursuivre.

Page 18: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

18

• Arrêter le programme

En phase de développement, • il est tout à fait acceptable d'arrêter le programme ou d'offrir de démarrer le débuggeur à l'endroit de l'erreur.

Pour un produit commercial, ce n'est pas acceptable.

• L'usager peut avoir travaillé plusieurs minutes (heures) avant de perdre son travail (...)

• Au minimum, il faut enregistrer les documents modifiés sur disque et enlever les fichiers temporaires.

Page 19: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

19

• Lancer une exception

Les exceptions ont été ajoutées dans beaucoup de langages OO dont le C++.

Le mécanisme des exceptions est un moyen sûr et pratique :• pour lancer des exceptions sur le site de l'erreur.• transférer le contrôle à une autre partie du code qui pourra gérer

la situation avec compétence.Exemple :• «Incapable d'écrire ces bytes» pourrait être devenir «Disque

plein» à un niveau supérieur.

Page 20: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

20

Synthèse

Erreurs• • • •

Réactions aux erreurs• • • • • •

Page 21: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

21

ExceptionsLancer une exception

Lorsque se produit une erreur qui ne peut être prise en charge à l'endroit de sa détection,

une exception peut être lancée avec la commande throw :throw e;

où e peut être n'importe quoi : un entier, une string, ou beaucoup mieux, un objet.throw "Division par zéro";throw ERR_DIVISION_ZERO;throw DivParZeroException();

Page 22: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

22

• Lancer une exception

Il est préférable d'utiliser les objets pour représenter les exceptions :

• utile pour spécifier le type de l'exception auquel on fait face ;

• permet de définir des sites d'interception basés sur le type d'exception ;

• permet de transporter de l'information dans l'objet du site de l'erreur jusqu'au site d'interception de l'exception.

Page 23: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

23

• Une fonction ne retourne pas normalement

Lorsqu'une fonction lance une exception, le mécanisme veut que le système se mette immédiatement

à la recherche d'un site d'interception pour cette exception.La fonction ne retourne pas normalement,

• l'exécution de la fonction se termine immédiatement • l'exécution est transférée au site d'interception le plus proche

(pour cette exception).// --- lance DivParZeroExceptiondouble r = divise (3, 0);// --- Ne sera pas exécutécout << "Résultat: " << r << endl;

Page 24: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

24

• Gérer une exception

Les sites d'interception des exceptions sont spécifiés à l'aide de blocs try-catch.try{ // code pouvant lancer une exception}catch (Type-exception e){ // e contient de l'information sur // l'exception. // code de gestion de l'exception}

Page 25: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

25

double divise (int d, int n){

if (n==0) throw DivParZeroException(); return (double)d/n;}

try{ // --- lance DivParZeroException double r = divise (3, 0); cout << "Résultat: " << r << endl;}catch (DivParZeroException& e){ // --- Traitement de l'exception}

Page 26: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

26

Le mécanisme peut sembler un peu lourd si on veut l'utiliser pour vérifier chaque appel de fonction comme :try{ double n = pile.pop();}catch (ContratException& e){ ...}

Page 27: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

27

• Gérer une exception : résumé

Les exceptions sont utiles pour gérer des erreurs pouvant se produire n'importe où dans un sous-système.

Le transfert de contrôle du point de détection de l'erreur à un point de gestion compétent permet de mieux gérer les erreurs.

Ne pas être capable d'écrire un entier dans une stream (point de détection de l'erreur) devient détection d'une disquette pleine (sur le site de gestion de l'exception).

à ce niveau d'intervention, on peut interagir avec l'utilisateur dans des termes compréhensibles pour lui.

Page 28: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

28

• Hiérarchie d'exceptions

La gestion des exceptions est basée sur le type d'exception (la classe),

• construire de petites classes appartenant à une hiérarchie.

La librairie standard du C++ a déjà mis en place un certain nombre d'exceptions.

La théorie du contrat définit des exceptions qui sont attachées à cette hiérarchie

• Du côté logic_error, i.e. erreur de programmation. • Du côté runtime_error par contre, il s'agit d'exception pouvant

toujours se produire.

Page 29: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

29

• Classes définies dans la librairie standard

std::exception

std::logic_error std::runtime_error

std::domain_error

std::invalid_argument

std::length_error

std::out_of_range

std::overflow_error

std::underflow_error

std::range_error

Page 30: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

30

• Gérer plus d'une exception

À partir d'un bloc try-catch, on peut gérer plusieurs exceptions à la fois :try{ // Code pouvant lancer des exceptions}catch (overflow_error& o){ // Gère des exceptions d'overflow}catch (underflow_error& u){ // Gère des exceptions d'underflow}

Page 31: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

31

Si le code dans le bloc try génère une exception de type overflow_error ou underflow_error,

• le traitement correspondant est activé.

Si une exception d'un type différent est lancée, • elle doit être gérée ailleurs sur un site d'interception du bon

type.Si un tel site n'existe pas, le programme s'arrêtera en donnant

une erreur du type "Unhandle exception".

Page 32: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

32

• Classes d'exception de contrat

std::logic_error

ContratException

m_ligne : intm_fichier : stringm_expression : string

reqTexteException() : string

InvariantException AssertionExceptionPostconditionExceptionPreconditionException

Page 33: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

33

• Hiérarchie d'exceptions de contrat

Si on veut gérer toutes les exceptions de contrat, • mentionner catch (ContratException& e)

• toutes les exceptions de contrat : precondition, postcondition, invariant et assertion seront attrapées.

Si on veut gérer seulement les préconditions, • mentionner :catch (PreconditionException &e).

On pourrait gérer toutes les erreurs de programmation en mentionnant :catch (logic_error& e)

Page 34: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

34

• Attraper toutes les exceptions et relancer

À l'occasion, nous voulons attraper toutes les exceptions (sans exception!!) qui passent à un endroit donné :

• pour faire une action protectrice• pour faire un nettoyage quelconque.

try{ // code}catch (...){ // Gestion de n'importe quelle exception throw; // Relance l'exception}

Page 35: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

35

L'énoncé catch(...) avec les 3 petits points permet de gérer n'importe quel type d'exception.

L'énoncé throw sans argument dans un bloc catch permet de relancer l'exception courante de nouveau.

De fait, on doit toujours relancer une exception qu'on ne sait pas comment gérer (quoiqu'il aurait été préférable de ne pas l'avoir interceptée).

Une exception non interceptée arrête le programme.

Page 36: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

36

• La pile d'appel

Gestion de la pile d'appel par le mécanisme des exceptions.Le flot linéaire d'exécution des instructions ne s'applique

plus lorsque qu'une exception est lancée.Au moment où une exception se produit, le contrôle passe

au site d'interception le plus proche pour cette exception.Tous les objets entre l'énoncé throw et l'énoncé catch

seront détruits et leur destructeur est appelé.Normalement les objets sur la pile sont détruits lorsque

l'exécution du programme atteint la fin d'un bloc ou d'une fonction.

Page 37: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

37

Le mécanisme des exceptions garantit que tous les destructeurs des objets sur la pile seront appelés.après avoir lancé une exception et l'avoir récupéré, on peut continuer l'exécution.

Gérer les ressources de façon cohérente en fonction de cette nouvelle réalité.

point du catch

point du throw

main()

f1()

f2()

f3()

f4()

Page 38: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

38

• Gestion des ressources

La possibilité qu'une exception puisse être lancée et qu'on ne puisse plus compter sur le flot linéaire d'exécution ajoute une préoccupation :

• Sommes-nous «exception-safe» ?

Exemples:

FILE* fichierP = fopen("input.dat");foo(fichierP); // peut lancer une exceptionfclose(fichierP); // peut ne jamais être exécuté

Employe* eP = new Employe();foo(eP); // peut lancer une exceptiondelete eP; // peut ne jamais être libérée

Page 39: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

39

FILE* fP = fopen ("input.dat");try{ foo (fP);}catch (...){ fclose (fP); throw;}fclose (fP);

Employe* eP = new Employe();try{ foo (eP);}catch (...){ delete eP; throw;}delete eP;

Attraper toutes les exceptions, fermer le fichier ou libérer la mémoire et relancer l'exception est techniquement correct.

Appliqué à grande échelle, la viedu programmeur deviendrait pirequ'avant...

Page 40: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

40

Structurer le code pour bénéficier de la gestion automatique des ressources en utilisant les constructeurs et les destructeurs des classes.

En utilisant une variable locale de type ifstream, on ouvre le fichier par le constructeur et le fichier est fermé par le destructeur :ifstream fs("input.dat");foo (fs);

Le fichier sera fermé lorsque le programme sera à la recherche d'un site d'interception pour une exception et que tous objets seront désalloués.

Page 41: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

41

Même problème avec la mémoire allouée sur le monceau. On ne doit pas conserver de pointeur comme variable d'une

fonction. La classe auto_ptr<> du standard permet de conserver les

pointeurs dans des classes dont le destructeur gère la désallocation.

#include <memory>#include "Employe.h"using namespace std;- Pointeur sur la pile dans une fonctionEmploye* eP = new Employe("Yves");- Pointeur comme attribut d'un objetauto_ptr<Employe> pstr(new Employe("Yves"));

Page 42: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

42

• Quelles exceptions lancer ?

Une exception non gérée résulte en un programme arrêté, • il est vital que le code minimise le nombre d'exceptions lancées

et que celles-ci soient clairement documentées.Ne jamais se servir des exceptions pour retourner des

résultats de calcul. • on peut ne pas tenir compte du type de retour d'une méthode

sans péril. ce n'est pas le cas avec une exception --> arrêt immédiat du programme.

Page 43: Programme de baccalauréat en informatique Programmation Orientée Objets IFT-19946 Thierry EUDE Module 6. Gestion des erreurs et des exceptions : Fonctionnement

Département d’informatique et de génie logiciel

43

Synthèse

Exception• • Lancer:• Attraper:

Simple:Multiple:Tous:

• Objets: