GCC et exception handler en linux

yann459 Messages postés 1 Date d'inscription samedi 27 juillet 2024 Statut Membre Dernière intervention 27 juillet 2024 - Modifié le 30 juil. 2024 à 18:12
mamiemando Messages postés 33268 Date d'inscription jeudi 12 mai 2005 Statut Modérateur Dernière intervention 18 septembre 2024 - 30 juil. 2024 à 18:21

Bonjour,
Le programme ci-dessous :

#include <stdio.h>
#include <stdlib.h>
 
int main(int argc, char* argv[]) {
    printf("Hello !!\n");
    try {
        printf("1\n");
        int *num;
        num=NULL;
        *num=8556; // Provoque l'exception
    } catch(int o) {
        printf("Exception\n"); // Ne passe jamais là
    }
    printf("fin ! \n");
}


compilé en linux avec comme commande :

g++ -o main main.c -lpthread

Le programme s’exécute , mais l'exception ne fonctionne pas.

Qu'est ce que je dois faire ?
Merci

A voir également:

2 réponses

Salut.

Je n'y connais pas grand chose en c++, mais un segfault n'est pas une erreur que l'on peut choper.

https://stackoverflow.com/questions/12978234/catch-segmentation-fault-in-c

0
mamiemando Messages postés 33268 Date d'inscription jeudi 12 mai 2005 Statut Modérateur Dernière intervention 18 septembre 2024 7 780
Modifié le 30 juil. 2024 à 18:22

Bonjour,

Je suis d'accord avec flibustier, tu ne peux pas rattraper une erreur de segmentation. Un programme correct ne peut donc en aucun cas déclencher une erreur de segmentation.

Si tu veux déboguer une telle erreur, il faut compiler avec l'option -g et regarder avec gdb l'instruction qui la déclenche (puis lancer l'exécution r, attendre que le programme plante, et afficher la trace d'exécution bt). Tu peux aussi regarder tout ce qui ne va pas niveau mémoire avec valgrind.

Par ailleurs, il a quelques points qui ne vont pas avec ton code :

  • Si tu utilises try ... catch, c'est que tu fais du C++, pas du C
    • L'opérateur catch sert à rattraper une instance d'exception, pas un entier
  • Dans ce cas, tu es supposé inclure <cstdio> (au lieu de <stdio.h>), <cstdlib> (au lieu de <stdlib.h>). Même raisonnement pour les autres headers du C (<string.h>, <limits.h>, etc...)
    • Il n'y a pas de raison d'inclure <cstdlib> dans ton programme puisque tu n'utilises pas de fonction fournie par ce header.
  • En C++, pour écrire du texte, on utilise plutôt <iostream> et l'opérateur <<.
  • Il manque en fin de main le retour du code d'exécution (0 si tout va bien).

Si l'on omet que le try ... catch est ici inutile, ton programme s'écrit alors :

#include <iostream>

int main(int argc, char* argv[]) {
    using namespace std;
    cout << "Hello !!" << endl;
    try {
        cout << 1 << endl;
        int *num;
        num = NULL;
        *num = 8556; // Provoque l'exception
    } catch(...) {
        cerr << "Exception" << endl; // Ne passe jamais là
    }
    cout << "fin !" << endl;
    return 0;
}

Exemple :

(mando@cenedra) (~) $ g++ -g toto.cpp 

(mando@cenedra) (~) $ ./a.out 
Hello !!
1
Erreur de segmentation (core dumped)

(mando@cenedra) (~) $ gdb a.out 
GNU gdb (Debian 13.2-1+b2) 13.2
Copyright (C) 2023 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.
Type "show copying" and "show warranty" for details.
This GDB was configured as "x86_64-linux-gnu".
Type "show configuration" for configuration details.
For bug reporting instructions, please see:
<https://www.gnu.org/software/gdb/bugs/>.
Find the GDB manual and other documentation resources online at:
    <http://www.gnu.org/software/gdb/documentation/>.

For help, type "help".
Type "apropos word" to search for commands related to "word"...
Reading symbols from a.out...
(gdb) r
Starting program: /home/mando/a.out 
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/lib/x86_64-linux-gnu/libthread_db.so.1".
Hello !!
1

Program received signal SIGSEGV, Segmentation fault.
0x00005555555551f6 in main (argc=1, argv=0x7fffffffdca8) at toto.cpp:10
10              *num = 8556; // Provoque l'exception
(gdb) bt
#0  0x00005555555551f6 in main (argc=1, argv=0x7fffffffdca8) at toto.cpp:10

On voit bien où plante le programme.

Bonne chance

0