diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/logic/linkcmd/slbt_linkcmd_argv.c | 78 | ||||
-rw-r--r-- | src/skin/slbt_skin_default.c | 4 |
2 files changed, 81 insertions, 1 deletions
diff --git a/src/logic/linkcmd/slbt_linkcmd_argv.c b/src/logic/linkcmd/slbt_linkcmd_argv.c index 3999b29..403023f 100644 --- a/src/logic/linkcmd/slbt_linkcmd_argv.c +++ b/src/logic/linkcmd/slbt_linkcmd_argv.c @@ -739,6 +739,7 @@ slbt_hidden int slbt_exec_link_finalize_argument_vector( char ** oargv; char ** lobjv; char ** cnvlv; + char ** dlargv; char ** cap; char ** src; char ** dst; @@ -902,6 +903,10 @@ slbt_hidden int slbt_exec_link_finalize_argument_vector( *aarg++ = *parg++; } + /* dlsyms vtable object must only be added once (see below) */ + } else if (!strcmp(*parg,"-dlpreopen")) { + parg++; + /* placeholder argument? */ } else if (!strncmp(*parg,"-USLIBTOOL_PLACEHOLDER_",23)) { parg++; @@ -912,6 +917,10 @@ slbt_hidden int slbt_exec_link_finalize_argument_vector( } } + /* dlsyms vtable object inclusion */ + if (ectx->dlopenobj) + *oarg++ = ectx->dlopenobj; + /* export-symbols-regex, proper dlpreopen support */ if (dctx->cctx->libname) if (slbt_exec_link_create_expsyms_archive( @@ -954,6 +963,75 @@ slbt_hidden int slbt_exec_link_finalize_argument_vector( ectx->mout[1] = ectx->mout[0] + 1; } + /* dlsyms vtable object compilation */ + if (ectx->dlopenobj) { + dlargv = (slbt_get_exec_ictx(ectx))->dlargv; + *dlargv = base[0]; + + src = aargv; + cap = aarg; + dst = &dlargv[1]; + + /* compile argv, based on the linkcmd argv */ + for (; src<cap; ) { + if ((src[0][0] == '-') && (src[0][1] == '-')) { + *dst++ = *src; + + } else if ((src[0][0] == '-') && (src[0][1] == 'L')) { + (void)0; + + } else if ((src[0][0] == '-') && (src[0][1] == 'l')) { + (void)0; + + } else if ((src[0][0] == '-') && (src[0][1] == 'o')) { + src++; + + } else if ((src[0][0] == '-') && (src[0][1] == 'D')) { + if (!src[0][2]) + src++; + + } else if ((src[0][0] == '-') && (src[0][1] == 'U')) { + if (!src[0][2]) + src++; + + } else if ((src[0][0] == '-') && (src[0][1] == 'W')) { + if ((src[0][2] == 'a') && (src[0][3] == ',')) + *dst++ = *src; + } else { + *dst++ = *src; + } + + src++; + } + + *dst++ = dctx->cctx->settings.picswitch + ? dctx->cctx->settings.picswitch + : *ectx->fpic; + + *dst++ = "-c"; + *dst++ = ectx->dlopensrc; + + *dst++ = "-o"; + *dst++ = ectx->dlopenobj; + + /* nested compile step */ + ectx->argv = dlargv; + + if (!(dctx->cctx->drvflags & SLBT_DRIVER_SILENT)) + if (slbt_output_compile(ectx)) + return SLBT_NESTED_ERROR(dctx); + + if ((slbt_spawn(ectx,true) < 0) && (ectx->pid < 0)) + return SLBT_SYSTEM_ERROR(dctx,0); + + if (ectx->exitcode) + return SLBT_CUSTOM_ERROR( + dctx, + SLBT_ERR_COMPILE_ERROR); + + ectx->argv = base; + } + /* all done */ if (sargvbuf) free(sargvbuf); diff --git a/src/skin/slbt_skin_default.c b/src/skin/slbt_skin_default.c index a6cc9b2..d01d236 100644 --- a/src/skin/slbt_skin_default.c +++ b/src/skin/slbt_skin_default.c @@ -209,7 +209,9 @@ const slbt_hidden struct argv_option slbt_default_options[] = { ARGV_OPTION_HYBRID_ONLY|ARGV_OPTION_HYBRID_SPACE, 0,"<FILE>", "Link the specified %s into the generated library " - "or executable"}, + "or executable, and make it available to the compiled " + "shared library, dynamic module, or executable program " + "via a backward-compatible dlsymas vtable."}, {"export-dynamic", 0,TAG_EXPORT_DYNAMIC,ARGV_OPTARG_NONE, ARGV_OPTION_HYBRID_ONLY,0,0, |