Exceptions en C : __try vs. try/catch/finally
En C , les constructions try/catch/finally sont utilisées pour gérer exceptions. Cependant, ils peuvent également être rencontrés avec des traits de soulignement, tels que __try. Cela soulève la question de savoir quand ces traits de soulignement sont nécessaires.
Sur les plates-formes Windows : unification de la gestion des exceptions
Sous Windows, les exceptions sont prises en charge au niveau du système d'exploitation via les exceptions structurées. Manipulation (SEH). Ils sont comparables aux signaux Unix. Les compilateurs ciblant Windows exploitent SEH pour implémenter les exceptions C.
Non-Standard __try et __sauf
Pour gérer les exceptions SEH en C , vous devez utiliser le mot-clé non standard __try au lieu d'essayer. Le mot-clé __sauf est similaire au catch de C, mais il fournit des fonctionnalités supplémentaires. Il vous permet de spécifier une expression de filtre d'exception qui détermine si une exception active doit être interceptée.
__finally pour l'exécution de code post-exception
Le mot-clé __finally vous permet de exécuter du code après qu'une exception ait été gérée. Cette fonctionnalité n'est pas présente dans le C standard, mais elle est courante dans d'autres langages.
Désactivation de l'optimisation pour l'invocation de destructeurs
Le compilateur Microsoft effectue une optimisation qui peut empêcher les destructeurs d'être invoqué dans tous les cas pendant le déroulement de la pile. S'il détermine qu'il n'y a pas de lancement dans la portée qui régit la durée de vie de l'objet, il ignore le code d'enregistrement. Pour garantir l'invocation du destructeur, utilisez l'option de compilation /EHa pour supprimer cette optimisation.
Exemple démontrant la gestion des exceptions SEH et C
Pour illustrer les concepts, voici un extrait de code qui montre comment les exceptions SEH permettent l'invocation du destructeur C et comment les exceptions C sont construites sur SEH :
#include <iostream> class Example { public: ~Example() { std::cout << "destructed" << std::endl; } }; int filterException(int code, PEXCEPTION_POINTERS ex) { std::cout << "Filtering " << std::hex << code << std::endl; return EXCEPTION_EXECUTE_HANDLER; } void testProcessorFault() { Example e; int* p = 0; *p = 42; } void testCppException() { Example e; throw 42; } int main() { __try { testProcessorFault(); } __except(filterException(GetExceptionCode(), GetExceptionInformation())) { std::cout << "caught" << std::endl; } __try { testCppException(); } __except(filterException(GetExceptionCode(), GetExceptionInformation())) { std::cout << "caught" << std::endl; } return 0; }
Sortie :
Filtering c0000005 destructed caught Filtering e06d7363 destructed caught
Cet exemple présente la gestion des exceptions SEH et C, démontrant comment les destructeurs sont invoqués même pendant les exceptions SEH.
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!