停止dlopen失败的过程

时间:2014-07-27 16:22:35

标签: linux gcc dlopen

也许是一个边界线问题,更多与调试有关。严格意义上编码的系统管理员

我正在努力(在Debian / Sid / x86-64上)准备下一个GCC MELT版本,它是GCC提供的复杂元插件(通过免费软件GPLv3)插件)GCC的领域特定语言翻译为C ++。

(如果您想要当前快照,请下载http://gcc-melt.org/melt-plugin-snapshot-r213101-2014july27.tar.bz2它有3.8M字节)

MELT的建造程序是神秘的,需要15分钟(在i7 3770K上)。它涉及几个运行时生成的C ++代码和生成的shell脚本以及复杂的makefile。所以这是一场噩梦。

我的一些代码中有一个错误。 dlopen失败了。 dlopen由一些系统 GCC编译器完成(实际上它当然是cc1plus ...)。这种情况发生在深层嵌套的脚本中(例如make调用autogen代shell脚本,然后生成的shell脚本调用另一个make,调用该GCC命令;某些shell或者使变量不正确......)。

当然,系统cc1plusdlsym失败时正确地给出致命错误。

我的错误(某个地方,现在还没有)在某些shell或环境或make变量被错误传输,而不是调用/usr/bin/g++-4.8编译器,一些中间脚本是在我的Debian上调用/usr/bin/g++,默认g++g++-4.9

当然,我不想重新编译我的系统/usr/bin/g++-4.8/usr/bin/g++-4.9

问题:

是否可能(可能通过 oprofile LD_PRELOAD可爱的技巧?)运行一系列复杂的流程(某些他们是g++g++-4.8以及停止或断点,任何cc1pluscc1 (在/usr/lib/gcc/x86_64-linux-gnu/4.8.3/或在/usr/lib/gcc/x86_64-linux-gnu/4.9.1dlopen失败?

如果执行失败cc1plus的错误进程dlopen已停止 - 没有退出 - 我可以跟踪所有脚本和make链启动它。 < / p>

血腥细节

如果你足够勇敢尝试重现我的错误(我不会问这个,这很费劲!)下载我的melt-plugin-snapshot-r213101-2014july27.tar.bz2以及同时拥有gcc-4.8的Debian / Sid(安装了4.8.3)和gcc-4.9(4.9.1)及其plugin-dev(默认/usr/bin/gcc为4.9.1版本),将我的插件快照解压缩到/tmp并输入解压缩目录make MELTGCC=gcc-4.8 GCCMELT_CXX=g++-4.8

中的/tmp/melt-plugin-snapshot-r213101-2014july27/

最后我得错了

 MELT BUILD SCRIPT INFO: meltfrom=melt-build-script.tpl:375/230-melt-build-script.tpl:451/377 meltmode=translateinit meltbase=warmelt-first meltstage=meltbuild-stage1 meltprevstage=meltbuild-stage0-quicklybuilt meltinit=meltbuild-stage0-quicklybuilt/warmelt-first.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-base.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-debug.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-macro.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-moremacro.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-normal.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-normatch.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-genobj.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-outobj.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-hooks.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-modes.quicklybuilt meltinclude= meltsrc=/tmp/melt-plugin-snapshot-r213101-2014july27/melt/warmelt-first.melt
 MELT BUILD SCRIPT INFO: melt-build-script.tpl:375/230-melt-build-script.tpl:451/377 emit C++ code for warmelt-first of meltbuild-stage1
 MELT BUILD SCRIPT INFO: melt-build-script.tpl:375/230-melt-build-script.tpl:451/377 argument file meltbuild-stage1/warmelt-first.args is
 -Wno-shadow -frandom-seed=ea257ebecb10e5a2143d906632a799b0
  -DGCCMELT_FROM_ARG="melt-build-script.tpl:375/230-melt-build-script.tpl:451/377"
  -fplugin-arg-melt-mode=translateinit
  -fplugin-arg-melt-arg=/tmp/melt-plugin-snapshot-r213101-2014july27/melt/warmelt-first.melt
  -fplugin-arg-melt-output=meltbuild-stage1/warmelt-first
  -fplugin-arg-melt-module-make-command='make'
  -fplugin-arg-melt-module-makefile=/tmp/melt-plugin-snapshot-r213101-2014july27/melt-module.mk
  -fplugin-arg-melt-module-cflags='-I /tmp/melt-plugin-snapshot-r213101-2014july27 -I /tmp/melt-plugin-snapshot-r213101-2014july27/melt/generated  -I. -Imeltbuild-stage1 -Imeltbuild-stage0-quicklybuilt -I /usr/lib/gcc/x86_64-linux-gnu/4.8/plugin/melt-headers/1.1-rc1-snap-svnrev-213094 -I /usr/lib/gcc/x86_64-linux-gnu/4.8/plugin/include -I /usr/lib/gcc/x86_64-linux-gnu/4.8/plugin/include/c-family -I /tmp/melt-plugin-snapshot-r213101-2014july27/melt/generated -I /tmp/melt-plugin-snapshot-r213101-2014july27'
  -fplugin-arg-melt-init=meltbuild-stage0-quicklybuilt/warmelt-first.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-base.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-debug.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-macro.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-moremacro.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-normal.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-normatch.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-genobj.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-outobj.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-hooks.quicklybuilt:meltbuild-stage0-quicklybuilt/warmelt-modes.quicklybuilt
  -fplugin-arg-melt-workdir=meltbuild-workdir
  -fplugin-arg-melt-tempdir=meltbuild-tempdir
  -fplugin-arg-melt-source-path=meltbuild-stage1:meltbuild-stage0-quicklybuilt:.
  -fplugin-arg-melt-module-path=meltbuild-stage1:meltbuild-stage0-quicklybuilt:.
  -fplugin-arg-melt-bootstrapping
  -fplugin-arg-melt-generate-work-link
  -fplugin-arg-melt-generated-c-file-list=meltbuild-stage1/warmelt-first.cfilist
 meltbuild-empty-file.c
 cc1plus: error: cannot load plugin ./melt.so
 ./melt.so: undefined symbol: _Z28gt_ggc_mx_gimple_statement_dPv
 MELT BUILD SCRIPT FAILURE: melt-build-script.tpl:375/230-melt-build-script.tpl:451/377 failed with arguments @meltbuild-stage1/warmelt-first.args
 Makefile:429: recipe for target 'melt-translator' failed
 make: *** [melt-translator] Error 1
 rm gfmeltgcc_revision _melt-runtime.c gfmeltgcc_run_md5 gfmeltgcc_version_number _meltrunsup-inc.c
 make MELTGCC=gcc-4.8 GCCMELT_CXX=g++-4.8  77.48s user 3.79s system 98% cpu 1:22.34 total

当然g++-4.9 错误地 dlopen - 为GCC 4.8 melt.so。错误是我的,有些东西正在开始g++而不是g++-4.8(应该由make和shell变量传输)。


解决方法....

我没有找到我的问题的答案,但我做了一个解决方法:我修补了GCC 4.9.1源代码(文件gcc/plugin.c函数try_init_one_plugin)以在失败后添加一些语句{{1例如

dlopen

dl_handle = dlopen (plugin->full_name, RTLD_NOW | RTLD_GLOBAL); if (!dl_handle) { char*errmsg = xstrdup(dlerror ()); fprintf(stderr, "\n @@ GCC PLUGIN LOAD FAILURE pid %d %s: %s\n", (int) getpid(), plugin->full_name, errmsg); fflush(NULL); system("pstree -a -h -l -s"); system("ps auxw"); fflush(NULL); fprintf(stderr, "\n @@ GCC PLUGIN LOAD FAILURE sleeping 8 seconds\n"); fflush(NULL); sleep (8); fprintf(stderr, "\n @@ GCC PLUGIN LOAD FAILURE selfstopping\n"); fflush(NULL); sleep (1); kill (SIGSTOP, getpid()); fflush(NULL); error ("cannot load plugin %s\n%s", plugin->full_name, errmsg); free (errmsg); return false; } fprintfsystemfflush的结果strdupfree}调用以上表单我的临时补丁。然后我编译了修补后的GCC 4.9.1并使用dlerror技巧确保它被调用。

有了这个,我就能纠正我最初的错误。

修补PATH会很困难且非常危险(在太多地方经常使用)。

我还想到了流程会计acct(2)&amp; acct(5) ......)。最后修补GCC是最容易(但有点可耻)的事情。

BTW,这样的错误就是为什么我越来越相信自由软件。如果我的编译器接受插件是封闭源代码,我将更难找到错误。

N.B。我会在几天内删除插件快照。

0 个答案:

没有答案