From 34988f835484e8a4fdc3e9a93930786755a63d05 Mon Sep 17 00:00:00 2001 From: midipix Date: Tue, 19 Feb 2019 08:30:41 -0500 Subject: driver, compile & link mode: support arbitrary & known compiler wrappers. --- include/slibtool/slibtool.h | 1 + src/driver/slbt_driver_ctx.c | 39 +++++++++++++++++++++++++++++++------ src/internal/slibtool_driver_impl.h | 1 + src/logic/slbt_exec_compile.c | 14 ++++++++++--- src/logic/slbt_exec_link.c | 18 +++++++++++++---- src/skin/slbt_skin_default.c | 9 +++++++++ 6 files changed, 69 insertions(+), 13 deletions(-) diff --git a/include/slibtool/slibtool.h b/include/slibtool/slibtool.h index 7fd99f0..360ec7c 100644 --- a/include/slibtool/slibtool.h +++ b/include/slibtool/slibtool.h @@ -244,6 +244,7 @@ struct slbt_common_ctx { char ** cargv; char ** targv; char * libname; + const char * ccwrap; const char * target; const char * output; const char * shrext; diff --git a/src/driver/slbt_driver_ctx.c b/src/driver/slbt_driver_ctx.c index a898205..da8bc76 100644 --- a/src/driver/slbt_driver_ctx.c +++ b/src/driver/slbt_driver_ctx.c @@ -263,12 +263,14 @@ static int slbt_split_argv( bool flast; bool fcopy; size_t size; + const char * base; struct argv_meta * meta; struct argv_entry * entry; struct argv_entry * mode; struct argv_entry * config; struct argv_entry * finish; struct argv_entry * features; + struct argv_entry * ccwrap; const struct argv_option ** popt; const struct argv_option ** optout; const struct argv_option * optv[SLBT_OPTV_ELEMENTS]; @@ -311,7 +313,7 @@ static int slbt_split_argv( } /* missing all of --mode, --config, --features, and --finish? */ - mode = config = finish = features = 0; + mode = config = finish = features = ccwrap = 0; for (entry=meta->entries; entry->fopt; entry++) if (entry->tag == TAG_MODE) @@ -322,6 +324,8 @@ static int slbt_split_argv( finish = entry; else if (entry->tag == TAG_FEATURES) features = entry; + else if (entry->tag == TAG_CCWRAP) + ccwrap = entry; argv_free(meta); @@ -422,8 +426,8 @@ static int slbt_split_argv( argv = sargv->dargv; /* allocate split vectors */ - if ((sargv->targv = calloc(2*(argc+1),sizeof(char *)))) - sargv->cargv = sargv->targv + argc + 1; + if ((sargv->targv = calloc(2*(argc+2),sizeof(char *)))) + sargv->cargv = sargv->targv + argc + 2; else return -1; @@ -441,13 +445,32 @@ static int slbt_split_argv( for (i=0; itargv[i] = argv[i]; + /* split vector marks */ + targv = sargv->targv + i; + cargv = sargv->cargv; + + /* known wrappers */ + if (ctx.unitidx && !ccwrap) { + if ((base = strrchr(argv[i],'/'))) + base++; + else if ((base = strrchr(argv[i],'\\'))) + base++; + else + base = argv[i]; + + if (!strcmp(base,"ccache") + || !strcmp(base,"distcc") + || !strcmp(base,"compiler") + || !strcmp(base,"purify")) { + *targv++ = "--ccwrap"; + *targv++ = argv[i++]; + } + } + /* split vectors: legacy mixture */ for (optout=optv; optout[0]->tag != TAG_OUTPUT; optout++) (void)0; - targv = sargv->targv + i; - cargv = sargv->cargv; - for (; iarg; + break; + case TAG_IMPLIB: if (!strcmp("idata",entry->arg)) { cctx.drvflags |= SLBT_DRIVER_IMPLIB_IDATA; diff --git a/src/internal/slibtool_driver_impl.h b/src/internal/slibtool_driver_impl.h index 69b3675..19b4f46 100644 --- a/src/internal/slibtool_driver_impl.h +++ b/src/internal/slibtool_driver_impl.h @@ -35,6 +35,7 @@ enum app_tags { TAG_DEPS, TAG_SILENT, TAG_TAG, + TAG_CCWRAP, TAG_VERBOSE, TAG_TARGET, TAG_HOST, diff --git a/src/logic/slbt_exec_compile.c b/src/logic/slbt_exec_compile.c index cad5bd8..8efa777 100644 --- a/src/logic/slbt_exec_compile.c +++ b/src/logic/slbt_exec_compile.c @@ -43,6 +43,7 @@ static int slbt_exec_compile_finalize_argument_vector( char ** cap; char ** src; char ** dst; + char * ccwrap; /* vector size */ base = ectx->argv; @@ -89,12 +90,17 @@ static int slbt_exec_compile_finalize_argument_vector( } } - /* (program name) */ - dst = &base[1]; + /* program name, ccwrap */ + if ((ccwrap = (char *)dctx->cctx->ccwrap)) { + base[1] = base[0]; + base[0] = ccwrap; + base++; + } /* join all other args */ src = aargv; cap = aarg; + dst = &base[1]; for (; srccctx; @@ -153,7 +160,8 @@ int slbt_exec_compile( } /* compile mode */ - ectx->program = ectx->compiler; + ccwrap = (char *)cctx->ccwrap; + ectx->program = ccwrap ? ccwrap : ectx->compiler; ectx->argv = ectx->cargv; /* -fpic */ diff --git a/src/logic/slbt_exec_link.c b/src/logic/slbt_exec_link.c index 0bfe7e0..5f94038 100644 --- a/src/logic/slbt_exec_link.c +++ b/src/logic/slbt_exec_link.c @@ -588,6 +588,7 @@ static int slbt_exec_link_finalize_argument_vector( char ** dst; char * arg; char * dot; + char * ccwrap; const char * arsuffix; /* vector size */ @@ -717,12 +718,17 @@ static int slbt_exec_link_finalize_argument_vector( } } - /* (program name) */ - dst = &base[1]; + /* program name, ccwrap */ + if ((ccwrap = (char *)dctx->cctx->ccwrap)) { + base[1] = base[0]; + base[0] = ccwrap; + base++; + } /* join object args */ src = oargv; cap = oarg; + dst = &base[1]; for (; srccctx->ccwrap; ectx->argv = depsmeta.altv; - ectx->program = depsmeta.altv[0]; + ectx->program = ccwrap ? ccwrap : depsmeta.altv[0]; /* sigh */ if (slbt_exec_link_finalize_argument_vector(dctx,ectx)) @@ -1432,6 +1440,7 @@ static int slbt_exec_link_create_executable( char ** parg; char ** xarg; char * base; + char * ccwrap; char cwd [PATH_MAX]; char output [PATH_MAX]; char wrapper[PATH_MAX]; @@ -1531,8 +1540,9 @@ static int slbt_exec_link_create_executable( return SLBT_NESTED_ERROR(dctx); /* using alternate argument vector */ + ccwrap = (char *)dctx->cctx->ccwrap; ectx->argv = depsmeta.altv; - ectx->program = depsmeta.altv[0]; + ectx->program = ccwrap ? ccwrap : depsmeta.altv[0]; /* executable wrapper symlink */ if ((size_t)snprintf(wraplnk,sizeof(wraplnk),"%s.exe.wrapper", diff --git a/src/skin/slbt_skin_default.c b/src/skin/slbt_skin_default.c index 7678f2a..6300d8f 100644 --- a/src/skin/slbt_skin_default.c +++ b/src/skin/slbt_skin_default.c @@ -56,6 +56,15 @@ const struct argv_option slbt_default_options[] = { "and/or static archive. option syntax is " "--legabits[=%s]"}, + {"ccwrap", 0,TAG_CCWRAP,ARGV_OPTARG_REQUIRED,0,0, + "", + "use %s as a compiler driver wrapper; " + "for the purpose of compatibility, " + "this switch may be omitted for known " + "wrappers (ccache, compiler, distcc, " + "and purify) when immediately followed " + "by the compiler argument."}, + {"no-warnings", 0,TAG_WARNINGS,ARGV_OPTARG_NONE,0,0,0,""}, {"preserve-dup-deps", 0,TAG_DEPS,ARGV_OPTARG_NONE,0,0,0, -- cgit v1.2.3