8
votes

Résolution des typedfs en C et C ++

J'essaie de résoudre automatiquement Typefs dans des projets arbitraires C ++ ou C .

Étant donné que certains des Typefs sont définis dans des fichiers d'en-tête système (par exemple uint32 ), je tente actuellement d'y parvenir en exécutant le prétraiteur de GCC sur mes fichiers de code, puis numérisant les fichiers prétraités. Pour Typefs. Je devrais alors être capable de remplacer les TypeDEFS dans les fichiers de code du projet.

Je me demande, s'il y en a une autre, peut-être plus simple, je manque. Pouvez-vous penser à un?

La raison, pourquoi je veux faire cela: J'exploite des métriques de code des projets C / C ++ avec des outils différents. Les métriques sont basées sur la méthode. Après avoir extrait les métriques, je dois fusionner les données, produites par les différents outils. Le problème est que l'un des outils résolve Typefs et d'autres non. S'il y a des typdefs utilisés pour les types de paramètres de méthodes, j'ai des métriques mappées sur différents noms de méthodes, qui se réfèrent à la même méthode du code source.

penser à cette méthode dans le code source: int test (uint32 Par1, int Par2)
Après avoir exécuté mes outils, j'ai des métriques, mappées sur une méthode nommée int Test (uint32 Par1, int Par2) et certaines de mes métriques sont mappées sur int test (non signé INT Par1, int Par2) .


1 commentaires

Pouvez-vous également donner des informations sur la raison pour laquelle vous avez besoin de supprimer ces TypeDEFS de votre code? Probablement, cela aidera à suggérer une solution.


3 Réponses :


2
votes

GCC-XML peut aider à résoudre les Typefs, vous auriez à Suivez les identifiants de caractères des éléments jusqu'à ce que vous les résolviez à un , ou élément.

Pour remplacer les Typefs de votre projet, vous avez un problème plus fondamental, vous ne pouvez pas simplement rechercher et remplacer car vous devriez respecter la portée des noms - Pensez à E.G. Fonction-local TypeDefs, alias d'espace de noms ou en utilisant les directives .

Selon ce que vous essayez réellement de réaliser, il doit y avoir une meilleure façon.

mise à jour: En fait, dans le contexte donné des données de métrique de fixation, le remplacement des noms de caractères à l'aide de GCC-XML devrait fonctionner correctement s'il prend en charge votre base de code.


4 commentaires

Je ne suis pas sûr, mais je pense que GCC-XML n'est plus développé activement. La dernière version officielle est, selon le site Web, à partir de 2004. Et si je vous souviens bien, la version CVS est uniquement basée sur une version 3.x de GCC. Je ne sais pas vraiment, si cela importe, cependant. Hmm, espaces de noms. N'avait pas encore pensé à cela, d'être honnête. Cela complique la question ...


Je pensais que vous vouliez dire remplacer les types de la source, cela aurait été plus compliqué. Si vous avez juste besoin de corriger les données des métriques cependant et non la source, GCC-XML devrait suffire s'il prend en charge votre base de code.


En fait, je pense que les projets, j'analysent, devraient tous être compilables par un GCC c. 3.x. Donc cela pourrait fonctionner.


Selon leur site Web, GCC-XML est capable de simuler la GCC jusqu'à la version 4.2. Donc, cela ne devrait pas être un problème. Mais le fait, qu'il utilise l'analyseur C ++ de GCC pourrait être problématique avec certains programmes C.



3
votes

Vous pouvez utiliser CLANG (le Compilateur LLVM C / C ++ Compiler) pour analyser le code d'une manière qui préserve des informations sur Typefefs et même les macros. Il possède une très belle API C ++ pour la lecture des données une fois que le code source est lu dans l'AST (Abstract Syntaxe Tree). http://clang.llvm.org/

Si vous êtes plutôt à la recherche d'un programme simple qui fait déjà la résolution de vous (au lieu de l'API de programmation de clang), je pense que vous n'avez pas de chance, car je n'ai jamais vu une telle chose.


3 commentaires

Je pensais que Clangs C ++ analyseur n'est pas encore terminé?


La génération de code est assez incomplète, mais elle peut déjà gérer la majeure partie de la bibliothèque standard, ainsi que de nombreuses bibliothèques externes. L'analyseur est plus complet, mais même il manque toujours de quelques choses (vous ne pouvez donc pas l'utiliser par ex. Avec Boost Spirit.QI). Néanmoins, je pense que ce serait la meilleure option disponible pour la demande de Customizer.


L'API a vraiment l'air génial. Je suis assez curieux de l'essayer quand sa stable est devenue stable.



5
votes

Si vous ne vous souciez pas de déterminer l'endroit où ils sont définis, vous pouvez utiliser objdump code> pour vider la table de symboles C ++ qui résout Typefs. xxx pré>

Cet extrait est de la structure suivante Définition: p>

<mangled-name>           ::= '_Z' <encoding>
<encoding>               ::= <name> <bare-function-type>
  <name>                 ::= <nested-name>
    <nested-name>        ::= 'N' <source-name> <ctor-dtor-name> 'E'
      <source-name>      ::= <number> <identifier>
      <ctor-dtor-name>   ::= 'C2' # base object constructor
    <bare-function-type> ::= <type>+
      <type>             ::= 'P' <type> # pointer to
        <type>           ::= <cv-qualifier> <type>
          <cv-qualifier> ::= 'K' # constant
            <type>       ::= 'c' # character


3 commentaires

Quand j'essaie d'exécuter mon compilateur comme celui-ci: g ++ foo.cpp -wl, -map -wl, mapname i Obtenir l'erreur / usr / bin / ld: mode d'émulation non reconnu: AP prise en charge Emulations: elf_i386 i386Linux . Suis-je en utilisant les paramètres correctement? (G ++ Version: 4.4.2 20091208 (PRERRELASE), LD Version: 2.20.0.20091101)


J'ai mis à jour ma réponse. Ma version locale est toujours à 4.0.1 et on dirait que les arguments ont changé. Essayez g ++ foo.cpp -wl, -m> foo.map .


@Tronic - merci. J'essayais mon cerveau en essayant de me souvenir de ce programme. Avec une bonne utilisation de 'Grep', 'sed', et "awk", vous pouvez extraire les symboles d'une doublure. Quelque chose comme grep __z foo.map | grep -v '.eh $' | grep -v '\ $' | awk '{imprimer $ nf}' | C ++ Filt --Strip-Underscore .