web-dev-qa-db-fra.com

Existe-t-il une bonne bibliothèque Python capable d’analyser C++?

Google n'a rien révélé de pertinent.

J'ai un tas de code C++ de travail existant et j'aimerais utiliser python pour l'explorer et comprendre les relations entre les classes, etc.

EDIT: Je voulais juste souligner: je ne pense pas avoir besoin ou envie d'analyser chaque élément de C++; J'ai juste besoin de quelque chose d'assez intelligent pour saisir les déclarations de variable de classe, de fonction et de membre, et pour ignorer les définitions de fonction.

46
csbrooks

C++ est notoirement difficile à analyser. La plupart des personnes qui essaient de le faire correctement finissent par démonter un compilateur. En fait, c’est en partie la raison pour laquelle LLVM a démarré: Apple avait besoin d’une méthode lui permettant d’analyser le C++ pour une utilisation dans XCode, qui correspond à la façon dont le compilateur l’a analysé. 

C'est pourquoi il existe des projets tels que GCC_XML que vous pouvez combiner avec une bibliothèque XML python.

Certains projets non-compilateurs qui semblent faire un très bon travail pour l'analyse de C++ sont les suivants:

  • Eclipse CDT
  • OpenGrok
  • Doxygen
31
Stef

Pas une réponse en tant que telle, mais juste pour montrer à quel point il est difficile d'analyser correctement C++. Ma démo préférée:

template<bool> struct a_t;

template<> struct a_t<true> {
    template<int> struct b {};
};

template<> struct a_t<false> {
    enum { b };
};

typedef a_t<sizeof(void*)==sizeof(int)> a;

enum { c, d };
int main() {
    a::b<c>d; // declaration or expression?
}

Ceci est parfaitement valide, C++ conforme aux normes, mais la signification exacte de la ligne commentée dépend de votre implémentation. Si sizeof(void*)==sizeof(int) (typique des plates-formes 32 bits), il s’agit d’une déclaration de la variable locale d de type a::b<c>. Si la condition ne tient pas, il s'agit d'une expression sans opération ((a::b < c) > d). L'ajout d'un constructeur pour a::b vous permettra en réalité d'exposer la différence via la présence/l'absence d'effets secondaires.

44
Pavel Minaev

Vous ne trouverez pas de bibliothèque Python ouverte à cet effet. Analyser C++ est fastidieux, et peu d’analyseurs ont été écrits qui ne font pas partie d’un compilateur. Vous pouvez trouver un bon résumé des problèmes ici .

Le meilleur choix pourrait être clang , car son support C++ est bien établi . Bien que ce ne soit pas une solution Python, il semble qu'il serait possible de le réutiliser dans un wrapper Python, étant donné l'accent mis sur l'encapsulation et la qualité de son développement.

5
jlarcombe

Depuis de nombreuses années, j'utilise pygccxml , un très joli wrapper Python pour GCC-XML. C'est un paquet très complet qui est à la base de certains outils de génération de code bien utilisés, tels que py ++ , du même auteur.

5
jkp

Pycparser est un analyseur syntaxique complet et fonctionnel pour ANSI C. Peut-être que vous pouvez l’étendre en c ++ :-)

4
Eli Bendersky

Si vous avez formaté vos commentaires de manière compatible, doxygen fait un travail fantastique. Il va même dessiner des diagrammes d'héritage si vous avez graphviz installé.

Par exemple, exécutez doxygen sur les éléments suivants:

/// <summary>
/// A summary of my class
/// </summary>
public class MyClass
{
protected:
    int m_numOfWidgets; /// Keeps track of the number of widgets stored

public:
    /// <summary>
    /// Constructor for the class.
    /// </summary>
    /// <param paramName="numOfWidgets">Specifies how many widgets to start with</param>
    MyClass(int numOfWidgets)
    {
        m_numOfWidgets = numOfWidgets;
    }

    /// <summary>
    /// Increments the number of widgets stored by the amount supplied.
    /// </summary>
    /// <param paramName="numOfWidgets">Specifies how many widgets to start with</param>
    /// <returns>The number of widgets stored</returns>
    IncreaseWidgets(int numOfWidgetsToAdd)
    {
        m_numOfWidgets += numOfWidgets;
        return m_numOfWidgets;
    }
};

Va transformer tous ces commentaires en entrées dans des fichiers .html. Avec des conceptions plus complexes, le résultat est encore plus bénéfique - souvent beaucoup plus facile que d'essayer de parcourir la source.

4
Jon Cage

Cette page montre une grammaire C++ écrite en Antlr, et vous pouvez générer du code Python à partir de celle-ci.

Il semble également que quelqu'un travaille sur un analyseur C++ dans Pyparsing, mais je n'ai pas été en mesure de trouver qui ou son statut actuel.

1
Kathy Van Stone

Il n'y a pas de bonne bibliothèque (gratuite) pour analyser le C++ dans any language.
Vos meilleurs choix sont probablement le plugin Dehydra g ++, clang ou Elsa .

1
Employed Russian

Le wiki pyparsing montre cet exemple - il ne fait qu'analyser les déclarations de structure. Cela peut donc vous donner un aperçu de l'ampleur du problème.

Je vous suggère (ou mieux encore, votre employeur) de débourser 200 dollars et d’acheter Enterprise Architect auprès de sparxsystems . Ce logiciel est incroyablement puissant pour son prix et comprend de très bonnes fonctionnalités d’ingénierie inverse. Vous passerez beaucoup plus que cela à votre rythme pour ne faire que 2% du travail. Dans ce cas, "achète" l'emporte sur "make".

0
PaulMcG

Le projet Clang fournit des bibliothèques permettant d’analyser simplement le code C++.

Soit avec Clang et GCC, vous pouvez générer une représentation XML du code

Si vous préférez une solution plus pythonienne, vous pouvez également rechercher une grammaire C++ yacc et utiliser py-ply (Yacc pour Python), mais cela semble être la solution qui nécessite davantage de travail.

0
SystematicFrank

Ctypes utilise gcc-xml pour la génération de code. Il est possible que cpptypes le soit également. Même si ce n'est pas le cas, vous pouvez utiliser gcc-xml pour générer du XML à partir de votre fichier C++, puis analyser le fichier XML avec l'un des analyseurs syntaxiques Python intégrés ou tiers.

0
Jason R. Coombs

Je garderais un oeil sur gcc.gnu.org/wiki/plugins car il me semble que les plugins sont la voie à suivre. De plus, le gcc-python-plugin semble avoir une implémentation de Nice.

0
stephenmm

Voici un projet SourceForge qui prétend analyser les en-têtes c ++. Comme l'ont souligné d'autres commentateurs, il n'y a pas de solution générale, mais vous semblez dire que cela suffira à vos besoins. (Je viens de le rencontrer pour un besoin similaire et je ne l'ai pas encore essayé moi-même.)

http://sourceforge.net/projects/cppheaderparser/

0
Bill