Y a-t-il un moyen de remplacer les fonctions avec une portée statique dans un module d'objet?
Si je commence par quelque chose comme ça, un module
avec symbole global "foo" est une fonction qui appelle
Symbole local "bar," qui appelle le symbole local "baz" p> Il possède un global "FOO" et deux locaux "Bar" et "Baz" P. > Supposons que je souhaite écrire des tests de l'unité qui exercent une barre d'exercice et Baz,
Je peux faire: p> et maintenant bar et baz sont des symboles globaux et accessibles de
en dehors du module. Jusqu'à présent, si bon. P> Mais si je veux interposer ma propre fonction sur le dessus
de "Baz", et ont "bar" appeler mon interposé "Baz"? P> Y a-t-il un moyen de faire cela? P> - L'option Wrap ne semble pas le faire ... p> [scameron@localhost ~]$ cat ibaz.c
#include <stdio.h>
extern void foo();
extern void bar();
void __wrap_baz()
{
printf("wrapped baz\n");
}
int main(int argc, char *argv[])
{
foo();
baz();
}
[scameron@localhost ~]$ gcc -o ibaz ibaz.c foo2.o -Xlinker --wrap -Xlinker baz
[scameron@localhost ~]$ ./ibaz
foo
bar
baz
wrapped baz
[scameron@localhost ~]$
3 Réponses :
Etant donné que Ceci pourrait enfiler l'appel de la fonction. Cela pourrait signifier remplacer une variable avec des constantes. Si le code est à l'intérieur d'un Tout cela signifie que vous ne pouvez pas rediriger de manière fiable des appels vers cette fonction. P>
Si vous compilez avec le nouveau statique code> est une promesse au compilateur C que la fonction ou la variable est locale dans le fichier, le compilateur est libre de supprimer ce code s'il peut obtenir le même résultat sans elle. p>
si code> est toujours faux, la fonction peut ne pas exister même dans le résultat compilé. P>
-Lto code> options est encore pire, car le compilateur est libre de réorganiser, supprimer ou en ligne tout le code de l'ensemble du projet. P>
Je mets autour de l'inlinçon en compilant avec -fno-inline. Il n'y a pas de fonctions qui m'intéressent entièrement par le compilateur (sinon je les aurais déjà supprimé moi-même.) Il peut y avoir des cas d'angle que je ne peux pas traiter, mais c'est bon. Je suis plus intéressé par le cas typique. Je ne suis pas opposé à la modification mécanique du code de la machine sur les sites d'appels pour atteindre cette fin, il suffit de déterminer comment le faire.
J'ai reçu un email de Ian Lance Taylor (Auteur d'or, un lien alternatif à LD): P>
Y a-t-il un moyen de remplacer les fonctions avec une portée statique dans un module d'objet? (Je suis sur X86_64 et I386 Linux) P> blockQuote>
Non, il n'y a pas. En particulier, le compilateur peut appeller des appels en ligne vers statique fonctions, et il peut également réécrire les fonctions d'utiliser une autre Convention sur appel (GCC fait toutes ces deux optimisations). il y a donc Aucun moyen fiable de remplacer une fonction statique après que le code ait été compilé. p> blockQuote>
L'inlinisation peut être traitée, je pense, par -fno-inline, mais changer les conventions appelantes est probablement trop. P>
Cela étant dit, les gars de Dynamorio prétendent pouvoir le faire, mais je ne l'ai pas vérifié: P>
Bien sûr, l'inlinfing ne peut également être traitée que par la recompilation du code.
Si vous êtes d'accord avec la modification du code de la machine, vous ne devez avoir aucun problème de modification de code source. P>
Écrire des scripts pour produire mécaniquement des sources de test d'unité à partir des sources réelles. Perl fait-il très bien. P>
Je n'ai pas encore utilisé les symboles faibles, mais ils semblent affaiblir Baz de votre module d'origine vous permettront de le remplacer par un nouveau.
J'imagine que s'il essaie de faire de telles choses, il n'a pas accès au code source
J'ai accès au code source, mais je préférerais ne pas modifier la source de la manière habituelle des tests unitaires. En réalité, cela est pour tester un module de noyau Linux. En amont, ils n'aiment généralement pas que vous mettez des changements dans la source juste pour accueillir des choses qui ne sont pas le noyau et pour la compatibilité des correctifs, je ne veux pas gâcher inutilement la source.
Affaiblir ne fonctionne pas: [Scameron @ localhost ~] $ objcopy --weaken-symbole = baz foo2.o foo3.o [Scameron @ localhost ~] $ GCC -O ibaz ibaz.c foo3.xlinker - XLinker Baz [Scameron @ localhost ~] $ ./ibaz foo bar Baz enveloppé Baz [Scameron @ localhost ~] $ (Ugh. Stackoverflow Mise en forme de commentaire suce.)
Cela semble intéressant bien que: CS .virginia.edu / kim / Publicité / PIN / DOCS / 45467 / PIN / HTML / ...
Cela semble également intéressant: dynamorio.org