2017-09-11 7 views
2

J'ai une branche de l'infrastructure JavaScriptCore, dans laquelle j'ai ajouté une fonction qui est exportée. Le framework compile juste find. Courir nm sur le cadre révèle que la fonction (JSContextCreateBacktrace_unsafe) est en effet exporté:CFBundleGetFunctionPointerForName et dlsym return NULL pour la fonction exportée

Leo-Natans-Wix-MPB:JavaScriptCore.framework lnatan$ nm -gU JavaScriptCore.framework/JavaScriptCore | grep JSContextCreateBacktrace 
00000000004cb860 T _JSContextCreateBacktrace 
00000000004cba10 T _JSContextCreateBacktrace_unsafe 

Cependant, je ne peux pas obtenir le pointeur de cette fonction à l'aide CFBundleGetFunctionPointerForName ou dlsym; les deux renvoient NULL. Au début, j'ai utilisé dlopen pour ouvrir mon framework, puis j'ai essayé d'utiliser CFBundleCreate puis CFBundleGetFunctionPointerForName mais cela retourne aussi NULL.

Ce qui pourrait causer cela?

Mise à jour

quelque chose de louche qui se passe. J'ai renommé l'une des fonctions JSC, et nm reflète cela. Cependant, dlsym est toujours capable de trouver la fonction avec le nom d'origine, plutôt que le renommé.

Répondre

2

Il est difficile de dépister ce problème car cela dépend fortement de votre environnement et de votre situation spécifiques, mais il est très probable que vous rencontriez ce problème car l'image système a déjà été chargée et vous n'avez pas changé le nom de le cadre.

Si vous regardez le code source pour dlopen dans dyld/dyldAPIS.cpp:1458, vous remarquerez que le contexte transmis à dyld est configuré avec matchByInstallName = true. Ce contexte est ensuite passé à load qui exécute les différentes étapes nécessaires au chargement de l'image. Il y a quelques étapes à noter:

  • loadPhase2 dans dyld/dyld.cpp:2896 extrait la fin du chemin-cadre et recherche dans le chemin de recherche

  • loadPhase5check dans dyld/dyld:2712 itère sur toutes les images chargées et détermine le cas échéant d'entre eux ont un nom d'installation correspondant, et si tel est le cas, il renvoie cela au lieu d'en charger un nouveau.

  • loadPhase5load dans dyld/dyld:2601 charge finalement l'image si elle n'a pas été chargée/trouvée par les étapes précédentes. (Il convient de noter loadPhase5check est exécuté en premier, car le chargement des images est un processus à deux passes.)

Compte tenu de tout ce qui précède, je vais essayer de renommer votre cadre à quelque chose en plus JavaScriptCore.framework. En fonction du nom d'installation de l'infrastructure système et de votre infrastructure, je vous recommande également de modifier le nom d'installation. (Il y a beaucoup d'articles de blog et de posts de StackOverflow qui documentent comment faire cela en utilisant install_name_tool -id.)

+0

Exactement ce dont j'avais besoin. Merci pour la réponse bien fournie! –