web-dev-qa-db-fra.com

Quel est le but de __cxa_pure_virtual?

Lors de la compilation avec avr-gcc, j'ai rencontré des erreurs de l'éditeur de liens telles que les suivantes:

undefined reference to `__cxa_pure_virtual'

J'ai trouvé ce document qui dit:

La fonction __cxa_pure_virtual Est un gestionnaire d'erreur qui est appelé lorsqu'une fonction virtuelle pure est appelée.

Si vous écrivez une application C++ dotée de fonctions virtuelles pures, vous devez fournir votre propre fonction de gestionnaire d'erreur __cxa_pure_virtual. Par exemple:

extern "C" void __cxa_pure_virtual() { while (1); }

Définir cette fonction comme suggéré corrige les erreurs mais j'aimerais savoir:

  • quel est le but de cette fonction,
  • pourquoi je devrais le définir moi-même et
  • pourquoi est-il acceptable de le coder comme une boucle infinie?
51
Matthew Murdoch

Si, n'importe où dans l'exécution de votre programme, un objet est créé avec un pointeur de fonction virtuelle non renseigné, et lorsque la fonction correspondante est appelée, vous appelez une "fonction virtuelle pure".

Le gestionnaire que vous décrivez doit être défini dans les bibliothèques par défaut fournies avec votre environnement de développement. S'il vous arrive d'omettre les bibliothèques par défaut, vous trouverez ce gestionnaire non défini: l'éditeur de liens voit une déclaration, mais pas de définition. C'est alors que vous devez fournir votre propre version.

La boucle infinie est acceptable car c'est une erreur "forte": les utilisateurs de votre logiciel la remarqueront immédiatement. Toute autre implémentation "bruyante" est également acceptable.

38
xtofl

1) Quel est le but de la fonction __cxa_pure_virtual ()?

Les fonctions virtuelles pures peuvent être appelées pendant la construction/destruction d'un objet. Si cela se produit, __cxa_pure_virtual () est appelé pour signaler l'erreur. Voir D'où viennent les "appels de fonction virtuelle pure"?

2) Pourquoi pourriez-vous avoir besoin de le définir vous-même?

Normalement, cette fonction est fournie par libstdc ++ (par exemple sous Linux), mais avr-gcc et la chaîne d'outils Arduino ne fournissent pas de libstdc ++.

L'Arduino IDE parvient à éviter l'erreur de l'éditeur de liens lors de la construction de certains programmes car il se compile avec les options "-ffunction-sections -fdata-sections" et établit un lien avec "-Wl, - gc-sections ", qui supprime certaines références aux symboles inutilisés.

3) Pourquoi est-il acceptable de coder __cxa_pure_virtual () comme une boucle infinie?

Eh bien, c'est au moins sûr; il fait quelque chose de prévisible. Il serait plus utile d'interrompre le programme et de signaler l'erreur. Une boucle infinie serait cependant difficile à déboguer, sauf si vous disposez d'un débogueur qui peut interrompre l'exécution et donner une trace de pile.

22
Mark Seaborn