|
|
8f60d4 |
/*******************************************************************/
|
|
|
8f60d4 |
/* slibtool: a skinny libtool implementation, written in C */
|
|
|
49181b |
/* Copyright (C) 2016--2024 SysDeer Technologies, LLC */
|
|
|
8f60d4 |
/* Released under the Standard MIT License; see COPYING.SLIBTOOL. */
|
|
|
8f60d4 |
/*******************************************************************/
|
|
|
8f60d4 |
|
|
|
8f60d4 |
#include <stdint.h>
|
|
|
8f60d4 |
#include <string.h>
|
|
|
8f60d4 |
#include <unistd.h>
|
|
|
8f60d4 |
#include <stdlib.h>
|
|
|
8f60d4 |
#include <stdbool.h>
|
|
|
8f60d4 |
#include <fcntl.h>
|
|
|
8f60d4 |
#include <spawn.h>
|
|
|
8f60d4 |
#include <sys/wait.h>
|
|
|
8f60d4 |
|
|
|
8f60d4 |
#include <slibtool/slibtool.h>
|
|
|
8f60d4 |
#include "slibtool_driver_impl.h"
|
|
|
8f60d4 |
#include "slibtool_errinfo_impl.h"
|
|
|
4b56de |
#include "slibtool_visibility_impl.h"
|
|
|
8f60d4 |
#include "slibtool_ar_impl.h"
|
|
|
8f60d4 |
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* annotation strings */
|
|
|
8f60d4 |
static const char cfgexplicit[] = "command-line argument";
|
|
|
8f60d4 |
static const char cfghost[] = "derived from <host>";
|
|
|
8f60d4 |
static const char cfgtarget[] = "derived from <target>";
|
|
|
8f60d4 |
static const char cfgcompiler[] = "derived from <compiler>";
|
|
|
8f60d4 |
static const char cfgnmachine[] = "native (cached in ccenv/host.mk)";
|
|
|
8f60d4 |
static const char cfgxmachine[] = "foreign (derived from -dumpmachine)";
|
|
|
8f60d4 |
static const char cfgnative[] = "native";
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* elf rpath */
|
|
|
8f60d4 |
static const char*ldrpath_elf[] = {
|
|
|
8f60d4 |
"/lib",
|
|
|
8f60d4 |
"/lib/64",
|
|
|
8f60d4 |
"/usr/lib",
|
|
|
8f60d4 |
"/usr/lib64",
|
|
|
8f60d4 |
"/usr/local/lib",
|
|
|
8f60d4 |
"/usr/local/lib64",
|
|
|
8f60d4 |
0};
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* flavor settings */
|
|
|
8f60d4 |
#define SLBT_FLAVOR_SETTINGS(flavor, \
|
|
|
8f60d4 |
bfmt,pic, \
|
|
|
8f60d4 |
arp,ars,dsop,dsos,osds,osdf, \
|
|
|
8f60d4 |
exep,exes,impp,imps, \
|
|
|
8f60d4 |
ldenv) \
|
|
|
8f60d4 |
static const struct slbt_flavor_settings flavor = { \
|
|
|
8f60d4 |
bfmt,arp,ars,dsop,dsos,osds,osdf, \
|
|
|
8f60d4 |
exep,exes,impp,imps, \
|
|
|
8f60d4 |
ldenv,pic}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
SLBT_FLAVOR_SETTINGS(host_flavor_default, \
|
|
|
8f60d4 |
"elf","-fPIC", \
|
|
|
8f60d4 |
"lib",".a","lib",".so",".so","", \
|
|
|
8f60d4 |
"","","","", \
|
|
|
8f60d4 |
"LD_LIBRARY_PATH");
|
|
|
8f60d4 |
|
|
|
8f60d4 |
SLBT_FLAVOR_SETTINGS(host_flavor_midipix, \
|
|
|
8f60d4 |
"pe","-fPIC", \
|
|
|
8f60d4 |
"lib",".a","lib",".so",".so","", \
|
|
|
8f60d4 |
"","","lib",".lib.a", \
|
|
|
8f60d4 |
"LD_LIBRARY_PATH");
|
|
|
8f60d4 |
|
|
|
8f60d4 |
SLBT_FLAVOR_SETTINGS(host_flavor_mingw, \
|
|
|
8f60d4 |
"pe",0, \
|
|
|
8f60d4 |
"lib",".a","lib",".dll","",".dll", \
|
|
|
8f60d4 |
"",".exe","lib",".dll.a", \
|
|
|
8f60d4 |
"PATH");
|
|
|
8f60d4 |
|
|
|
8f60d4 |
SLBT_FLAVOR_SETTINGS(host_flavor_cygwin, \
|
|
|
8f60d4 |
"pe",0, \
|
|
|
8f60d4 |
"lib",".a","lib",".dll","",".dll", \
|
|
|
8f60d4 |
"",".exe","lib",".dll.a", \
|
|
|
8f60d4 |
"PATH");
|
|
|
8f60d4 |
|
|
|
8f60d4 |
SLBT_FLAVOR_SETTINGS(host_flavor_darwin, \
|
|
|
8f60d4 |
"macho","-fPIC", \
|
|
|
8f60d4 |
"lib",".a","lib",".dylib","",".dylib", \
|
|
|
8f60d4 |
"","","","", \
|
|
|
8f60d4 |
"DYLD_LIBRARY_PATH");
|
|
|
8f60d4 |
|
|
|
8f60d4 |
|
|
|
8f60d4 |
static void slbt_get_host_quad(
|
|
|
8f60d4 |
char * hostbuf,
|
|
|
8f60d4 |
char ** hostquad)
|
|
|
8f60d4 |
{
|
|
|
8f60d4 |
char * mark;
|
|
|
8f60d4 |
char * ch;
|
|
|
8f60d4 |
int i;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
for (i=0, ch=hostbuf, mark=hostbuf; *ch && i<4; ch++) {
|
|
|
8f60d4 |
if (*ch == '-') {
|
|
|
8f60d4 |
*ch = 0;
|
|
|
8f60d4 |
hostquad[i++] = mark;
|
|
|
8f60d4 |
mark = &ch[1];
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (i<4)
|
|
|
8f60d4 |
hostquad[i] = mark;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (i==3) {
|
|
|
8f60d4 |
hostquad[1] = hostquad[2];
|
|
|
8f60d4 |
hostquad[2] = hostquad[3];
|
|
|
8f60d4 |
hostquad[3] = 0;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
|
|
|
8f60d4 |
static void slbt_spawn_ar(char ** argv, int * ecode)
|
|
|
8f60d4 |
{
|
|
|
8f60d4 |
int estatus;
|
|
|
8f60d4 |
pid_t pid;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
*ecode = 127;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if ((pid = fork()) < 0) {
|
|
|
8f60d4 |
return;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
} else if (pid == 0) {
|
|
|
8f60d4 |
execvp(argv[0],argv);
|
|
|
8f60d4 |
_exit(errno);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
} else {
|
|
|
8f60d4 |
waitpid(pid,&estatus,0);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (WIFEXITED(estatus))
|
|
|
8f60d4 |
*ecode = WEXITSTATUS(estatus);
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
|
|
|
4b56de |
slbt_hidden int slbt_init_host_params(
|
|
|
8f60d4 |
const struct slbt_driver_ctx * dctx,
|
|
|
8f60d4 |
const struct slbt_common_ctx * cctx,
|
|
|
8f60d4 |
struct slbt_host_strs * drvhost,
|
|
|
8f60d4 |
struct slbt_host_params * host,
|
|
|
8f60d4 |
struct slbt_host_params * cfgmeta,
|
|
|
771899 |
const char * cfgmeta_host,
|
|
|
8f60d4 |
const char * cfgmeta_ar,
|
|
|
b4058c |
const char * cfgmeta_as,
|
|
|
fc8ee9 |
const char * cfgmeta_ranlib,
|
|
|
fc8ee9 |
const char * cfgmeta_dlltool)
|
|
|
8f60d4 |
{
|
|
|
8f60d4 |
int fdcwd;
|
|
|
8f60d4 |
int arprobe;
|
|
|
8f60d4 |
int arfd;
|
|
|
8f60d4 |
int ecode;
|
|
|
8f60d4 |
size_t toollen;
|
|
|
8f60d4 |
char * dash;
|
|
|
8f60d4 |
char * base;
|
|
|
8f60d4 |
char * mark;
|
|
|
8f60d4 |
const char * machine;
|
|
|
8f60d4 |
bool ftarget = false;
|
|
|
8f60d4 |
bool fhost = false;
|
|
|
8f60d4 |
bool fcompiler = false;
|
|
|
8f60d4 |
bool fnative = false;
|
|
|
8f60d4 |
bool fdumpmachine = false;
|
|
|
8f60d4 |
char buf [256];
|
|
|
8f60d4 |
char hostbuf [256];
|
|
|
8f60d4 |
char machinebuf [256];
|
|
|
8f60d4 |
char * hostquad [4];
|
|
|
8f60d4 |
char * machinequad[4];
|
|
|
8f60d4 |
char * arprobeargv[4];
|
|
|
8f60d4 |
char archivename[] = "/tmp/slibtool.ar.probe.XXXXXXXXXXXXXXXX";
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* base */
|
|
|
8f60d4 |
if ((base = strrchr(cctx->cargv[0],'/')))
|
|
|
8f60d4 |
base++;
|
|
|
8f60d4 |
else
|
|
|
8f60d4 |
base = cctx->cargv[0];
|
|
|
8f60d4 |
|
|
|
8f60d4 |
fdumpmachine = (cctx->mode == SLBT_MODE_COMPILE)
|
|
|
8f60d4 |
|| (cctx->mode == SLBT_MODE_LINK)
|
|
|
8f60d4 |
|| (cctx->mode == SLBT_MODE_INFO);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
fdumpmachine &= (!strcmp(base,"xgcc")
|
|
|
8f60d4 |
|| !strcmp(base,"xg++"));
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* support the portbld <--> unknown synonym */
|
|
|
8f60d4 |
if (!(drvhost->machine = strdup(SLBT_MACHINE)))
|
|
|
8f60d4 |
return -1;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if ((mark = strstr(drvhost->machine,"-portbld-")))
|
|
|
8f60d4 |
memcpy(mark,"-unknown",8);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* host */
|
|
|
8f60d4 |
if (host->host) {
|
|
|
771899 |
cfgmeta->host = cfgmeta_host ? cfgmeta_host : cfgexplicit;
|
|
|
8f60d4 |
fhost = true;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
} else if (cctx->target) {
|
|
|
8f60d4 |
host->host = cctx->target;
|
|
|
8f60d4 |
cfgmeta->host = cfgtarget;
|
|
|
8f60d4 |
ftarget = true;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
} else if (strrchr(base,'-')) {
|
|
|
8f60d4 |
if (!(drvhost->host = strdup(cctx->cargv[0])))
|
|
|
8f60d4 |
return -1;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
dash = strrchr(drvhost->host,'-');
|
|
|
8f60d4 |
*dash = 0;
|
|
|
8f60d4 |
host->host = drvhost->host;
|
|
|
8f60d4 |
cfgmeta->host = cfgcompiler;
|
|
|
8f60d4 |
fcompiler = true;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
} else if (!fdumpmachine) {
|
|
|
8f60d4 |
host->host = drvhost->machine;
|
|
|
8f60d4 |
cfgmeta->host = cfgnmachine;
|
|
|
8f60d4 |
|
|
|
8dc63d |
} else if (slbt_util_dump_machine(cctx->cargv[0],buf,sizeof(buf)) < 0) {
|
|
|
8f60d4 |
if (dctx)
|
|
|
8f60d4 |
slbt_dprintf(
|
|
|
8f60d4 |
slbt_driver_fderr(dctx),
|
|
|
8f60d4 |
"%s: could not determine host "
|
|
|
8f60d4 |
"via -dumpmachine\n",
|
|
|
8f60d4 |
dctx->program);
|
|
|
8f60d4 |
return -1;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
} else {
|
|
|
8f60d4 |
if (!(drvhost->host = strdup(buf)))
|
|
|
8f60d4 |
return -1;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
host->host = drvhost->host;
|
|
|
8f60d4 |
fcompiler = true;
|
|
|
8f60d4 |
fnative = !strcmp(host->host,drvhost->machine);
|
|
|
8f60d4 |
cfgmeta->host = fnative ? cfgnmachine : cfgxmachine;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (!fnative) {
|
|
|
8f60d4 |
strcpy(hostbuf,host->host);
|
|
|
8f60d4 |
strcpy(machinebuf,drvhost->machine);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
slbt_get_host_quad(hostbuf,hostquad);
|
|
|
8f60d4 |
slbt_get_host_quad(machinebuf,machinequad);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (hostquad[2] && machinequad[2])
|
|
|
8f60d4 |
fnative = !strcmp(hostquad[0],machinequad[0])
|
|
|
8f60d4 |
&& !strcmp(hostquad[1],machinequad[1])
|
|
|
8f60d4 |
&& !strcmp(hostquad[2],machinequad[2]);
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* flavor */
|
|
|
8f60d4 |
if (host->flavor) {
|
|
|
8f60d4 |
cfgmeta->flavor = cfgexplicit;
|
|
|
8f60d4 |
} else {
|
|
|
8f60d4 |
if (fhost) {
|
|
|
8f60d4 |
machine = host->host;
|
|
|
8f60d4 |
cfgmeta->flavor = cfghost;
|
|
|
8f60d4 |
} else if (ftarget) {
|
|
|
8f60d4 |
machine = cctx->target;
|
|
|
8f60d4 |
cfgmeta->flavor = cfgtarget;
|
|
|
8f60d4 |
} else if (fcompiler) {
|
|
|
8f60d4 |
machine = drvhost->host;
|
|
|
8f60d4 |
cfgmeta->flavor = cfgcompiler;
|
|
|
8f60d4 |
} else {
|
|
|
8f60d4 |
machine = drvhost->machine;
|
|
|
8f60d4 |
cfgmeta->flavor = cfgnmachine;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
dash = strrchr(machine,'-');
|
|
|
8f60d4 |
cfgmeta->flavor = cfghost;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if ((dash && !strcmp(dash,"-bsd")) || strstr(machine,"-bsd-"))
|
|
|
8f60d4 |
host->flavor = "bsd";
|
|
|
8f60d4 |
else if ((dash && !strcmp(dash,"-cygwin")) || strstr(machine,"-cygwin-"))
|
|
|
8f60d4 |
host->flavor = "cygwin";
|
|
|
8f60d4 |
else if ((dash && !strcmp(dash,"-darwin")) || strstr(machine,"-darwin"))
|
|
|
8f60d4 |
host->flavor = "darwin";
|
|
|
8f60d4 |
else if ((dash && !strcmp(dash,"-linux")) || strstr(machine,"-linux-"))
|
|
|
8f60d4 |
host->flavor = "linux";
|
|
|
8f60d4 |
else if ((dash && !strcmp(dash,"-midipix")) || strstr(machine,"-midipix-"))
|
|
|
8f60d4 |
host->flavor = "midipix";
|
|
|
8f60d4 |
else if ((dash && !strcmp(dash,"-mingw")) || strstr(machine,"-mingw-"))
|
|
|
8f60d4 |
host->flavor = "mingw";
|
|
|
8f60d4 |
else if ((dash && !strcmp(dash,"-mingw32")) || strstr(machine,"-mingw32-"))
|
|
|
8f60d4 |
host->flavor = "mingw";
|
|
|
8f60d4 |
else if ((dash && !strcmp(dash,"-mingw64")) || strstr(machine,"-mingw64-"))
|
|
|
8f60d4 |
host->flavor = "mingw";
|
|
|
8f60d4 |
else if ((dash && !strcmp(dash,"-windows")) || strstr(machine,"-windows-"))
|
|
|
8f60d4 |
host->flavor = "mingw";
|
|
|
8f60d4 |
else {
|
|
|
8f60d4 |
host->flavor = "default";
|
|
|
8f60d4 |
cfgmeta->flavor = "fallback, unverified";
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (fcompiler && !fnative)
|
|
|
8f60d4 |
if ((mark = strstr(drvhost->machine,host->flavor)))
|
|
|
8f60d4 |
if (mark > drvhost->machine)
|
|
|
8f60d4 |
fnative = (*--mark == '-');
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* toollen */
|
|
|
8f60d4 |
toollen = fnative ? 0 : strlen(host->host);
|
|
|
8f60d4 |
toollen += strlen("-utility-name");
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* ar */
|
|
|
8f60d4 |
if (host->ar)
|
|
|
8f60d4 |
cfgmeta->ar = cfgmeta_ar ? cfgmeta_ar : cfgexplicit;
|
|
|
8f60d4 |
else {
|
|
|
8f60d4 |
if (!(drvhost->ar = calloc(1,toollen)))
|
|
|
8f60d4 |
return -1;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (fnative) {
|
|
|
8f60d4 |
strcpy(drvhost->ar,"ar");
|
|
|
8f60d4 |
cfgmeta->ar = cfgnative;
|
|
|
8f60d4 |
arprobe = 0;
|
|
|
8f60d4 |
} else if (cctx->mode == SLBT_MODE_LINK) {
|
|
|
8f60d4 |
arprobe = true;
|
|
|
8f60d4 |
} else if (cctx->mode == SLBT_MODE_INFO) {
|
|
|
8f60d4 |
arprobe = true;
|
|
|
8f60d4 |
} else {
|
|
|
8f60d4 |
arprobe = false;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* arprobe */
|
|
|
8f60d4 |
if (arprobe) {
|
|
|
8f60d4 |
sprintf(drvhost->ar,"%s-ar",host->host);
|
|
|
8f60d4 |
cfgmeta->ar = cfghost;
|
|
|
8f60d4 |
ecode = 127;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* empty archive */
|
|
|
8f60d4 |
if ((arfd = mkstemp(archivename)) >= 0) {
|
|
|
8f60d4 |
slbt_dprintf(arfd,"!<arch>\n");
|
|
|
8f60d4 |
|
|
|
8f60d4 |
arprobeargv[0] = drvhost->ar;
|
|
|
8f60d4 |
arprobeargv[1] = "-t";
|
|
|
8f60d4 |
arprobeargv[2] = archivename;
|
|
|
8f60d4 |
arprobeargv[3] = 0;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* <target>-ar */
|
|
|
8f60d4 |
slbt_spawn_ar(
|
|
|
8f60d4 |
arprobeargv,
|
|
|
8f60d4 |
&ecode);
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* <target>-<compiler>-ar */
|
|
|
8f60d4 |
if (ecode && !strchr(base,'-')) {
|
|
|
8f60d4 |
sprintf(drvhost->ar,"%s-%s-ar",host->host,base);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
slbt_spawn_ar(
|
|
|
8f60d4 |
arprobeargv,
|
|
|
8f60d4 |
&ecode);
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* <compiler>-ar */
|
|
|
8f60d4 |
if (ecode && !strchr(base,'-')) {
|
|
|
8f60d4 |
sprintf(drvhost->ar,"%s-ar",base);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
slbt_spawn_ar(
|
|
|
8f60d4 |
arprobeargv,
|
|
|
8f60d4 |
&ecode);
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* if target is the native target, fallback to native ar */
|
|
|
8f60d4 |
if (ecode && !strcmp(host->host,SLBT_MACHINE)) {
|
|
|
8f60d4 |
strcpy(drvhost->ar,"ar");
|
|
|
8f60d4 |
cfgmeta->ar = cfgnative;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* fdcwd */
|
|
|
8f60d4 |
fdcwd = slbt_driver_fdcwd(dctx);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* clean up */
|
|
|
8f60d4 |
if (arfd >= 0) {
|
|
|
8f60d4 |
unlinkat(fdcwd,archivename,0);
|
|
|
8f60d4 |
close(arfd);
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
host->ar = drvhost->ar;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
6bc170 |
/* as */
|
|
|
6bc170 |
if (host->as)
|
|
|
b4058c |
cfgmeta->as = cfgmeta_as ? cfgmeta_as : cfgexplicit;
|
|
|
6bc170 |
else {
|
|
|
6bc170 |
if (!(drvhost->as = calloc(1,toollen)))
|
|
|
6bc170 |
return -1;
|
|
|
6bc170 |
|
|
|
6bc170 |
if (fnative) {
|
|
|
6bc170 |
strcpy(drvhost->as,"as");
|
|
|
6bc170 |
cfgmeta->as = cfgnative;
|
|
|
6bc170 |
} else {
|
|
|
6bc170 |
sprintf(drvhost->as,"%s-as",host->host);
|
|
|
6bc170 |
cfgmeta->as = cfghost;
|
|
|
6bc170 |
}
|
|
|
6bc170 |
|
|
|
6bc170 |
host->as = drvhost->as;
|
|
|
6bc170 |
}
|
|
|
6bc170 |
|
|
|
8f60d4 |
/* ranlib */
|
|
|
8f60d4 |
if (host->ranlib)
|
|
|
8f60d4 |
cfgmeta->ranlib = cfgmeta_ranlib ? cfgmeta_ranlib : cfgexplicit;
|
|
|
8f60d4 |
else {
|
|
|
8f60d4 |
if (!(drvhost->ranlib = calloc(1,toollen)))
|
|
|
8f60d4 |
return -1;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (fnative) {
|
|
|
8f60d4 |
strcpy(drvhost->ranlib,"ranlib");
|
|
|
8f60d4 |
cfgmeta->ranlib = cfgnative;
|
|
|
8f60d4 |
} else {
|
|
|
8f60d4 |
sprintf(drvhost->ranlib,"%s-ranlib",host->host);
|
|
|
8f60d4 |
cfgmeta->ranlib = cfghost;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
host->ranlib = drvhost->ranlib;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* windres */
|
|
|
8f60d4 |
if (host->windres)
|
|
|
8f60d4 |
cfgmeta->windres = cfgexplicit;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
else if (strcmp(host->flavor,"cygwin")
|
|
|
8f60d4 |
&& strcmp(host->flavor,"midipix")
|
|
|
8f60d4 |
&& strcmp(host->flavor,"mingw")) {
|
|
|
8f60d4 |
host->windres = "";
|
|
|
8f60d4 |
cfgmeta->windres = "not applicable";
|
|
|
8f60d4 |
|
|
|
8f60d4 |
} else {
|
|
|
8f60d4 |
if (!(drvhost->windres = calloc(1,toollen)))
|
|
|
8f60d4 |
return -1;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (fnative) {
|
|
|
8f60d4 |
strcpy(drvhost->windres,"windres");
|
|
|
8f60d4 |
cfgmeta->windres = cfgnative;
|
|
|
8f60d4 |
} else {
|
|
|
8f60d4 |
sprintf(drvhost->windres,"%s-windres",host->host);
|
|
|
8f60d4 |
cfgmeta->windres = cfghost;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
host->windres = drvhost->windres;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* dlltool */
|
|
|
8f60d4 |
if (host->dlltool)
|
|
|
fc8ee9 |
cfgmeta->dlltool = cfgmeta_dlltool ? cfgmeta_dlltool : cfgexplicit;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
else if (strcmp(host->flavor,"cygwin")
|
|
|
8f60d4 |
&& strcmp(host->flavor,"midipix")
|
|
|
8f60d4 |
&& strcmp(host->flavor,"mingw")) {
|
|
|
8f60d4 |
host->dlltool = "";
|
|
|
8f60d4 |
cfgmeta->dlltool = "not applicable";
|
|
|
8f60d4 |
|
|
|
8f60d4 |
} else {
|
|
|
8f60d4 |
if (!(drvhost->dlltool = calloc(1,toollen)))
|
|
|
8f60d4 |
return -1;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (fnative) {
|
|
|
8f60d4 |
strcpy(drvhost->dlltool,"dlltool");
|
|
|
8f60d4 |
cfgmeta->dlltool = cfgnative;
|
|
|
8f60d4 |
} else {
|
|
|
8f60d4 |
sprintf(drvhost->dlltool,"%s-dlltool",host->host);
|
|
|
8f60d4 |
cfgmeta->dlltool = cfghost;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
host->dlltool = drvhost->dlltool;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* mdso */
|
|
|
8f60d4 |
if (host->mdso)
|
|
|
8f60d4 |
cfgmeta->mdso = cfgexplicit;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
else if (strcmp(host->flavor,"cygwin")
|
|
|
8f60d4 |
&& strcmp(host->flavor,"midipix")
|
|
|
8f60d4 |
&& strcmp(host->flavor,"mingw")) {
|
|
|
8f60d4 |
host->mdso = "";
|
|
|
8f60d4 |
cfgmeta->mdso = "not applicable";
|
|
|
8f60d4 |
|
|
|
8f60d4 |
} else {
|
|
|
8f60d4 |
if (!(drvhost->mdso = calloc(1,toollen)))
|
|
|
8f60d4 |
return -1;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (fnative) {
|
|
|
8f60d4 |
strcpy(drvhost->mdso,"mdso");
|
|
|
8f60d4 |
cfgmeta->mdso = cfgnative;
|
|
|
8f60d4 |
} else {
|
|
|
8f60d4 |
sprintf(drvhost->mdso,"%s-mdso",host->host);
|
|
|
8f60d4 |
cfgmeta->mdso = cfghost;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
host->mdso = drvhost->mdso;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
return 0;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
5ddd2a |
static void slbt_free_host_tool_argv(char ** argv)
|
|
|
5ddd2a |
{
|
|
|
5ddd2a |
char ** parg;
|
|
|
5ddd2a |
|
|
|
5ddd2a |
if (!argv)
|
|
|
5ddd2a |
return;
|
|
|
5ddd2a |
|
|
|
5ddd2a |
for (parg=argv; *parg; parg++)
|
|
|
5ddd2a |
free(*parg);
|
|
|
5ddd2a |
|
|
|
5ddd2a |
free(argv);
|
|
|
5ddd2a |
}
|
|
|
8f60d4 |
|
|
|
4b56de |
slbt_hidden void slbt_free_host_params(struct slbt_host_strs * host)
|
|
|
8f60d4 |
{
|
|
|
8f60d4 |
if (host->machine)
|
|
|
8f60d4 |
free(host->machine);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (host->host)
|
|
|
8f60d4 |
free(host->host);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (host->flavor)
|
|
|
8f60d4 |
free(host->flavor);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (host->ar)
|
|
|
8f60d4 |
free(host->ar);
|
|
|
8f60d4 |
|
|
|
6bc170 |
if (host->as)
|
|
|
6bc170 |
free(host->as);
|
|
|
6bc170 |
|
|
|
8f60d4 |
if (host->ranlib)
|
|
|
8f60d4 |
free(host->ranlib);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (host->windres)
|
|
|
8f60d4 |
free(host->windres);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (host->dlltool)
|
|
|
8f60d4 |
free(host->dlltool);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (host->mdso)
|
|
|
8f60d4 |
free(host->mdso);
|
|
|
8f60d4 |
|
|
|
5ddd2a |
slbt_free_host_tool_argv(host->ar_argv);
|
|
|
5ddd2a |
slbt_free_host_tool_argv(host->as_argv);
|
|
|
5ddd2a |
slbt_free_host_tool_argv(host->ranlib_argv);
|
|
|
5ddd2a |
slbt_free_host_tool_argv(host->windres_argv);
|
|
|
5ddd2a |
slbt_free_host_tool_argv(host->dlltool_argv);
|
|
|
5ddd2a |
slbt_free_host_tool_argv(host->mdso_argv);
|
|
|
5ddd2a |
|
|
|
8f60d4 |
memset(host,0,sizeof(*host));
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
|
|
|
4b56de |
slbt_hidden void slbt_init_flavor_settings(
|
|
|
8f60d4 |
struct slbt_common_ctx * cctx,
|
|
|
8f60d4 |
const struct slbt_host_params * ahost,
|
|
|
8f60d4 |
struct slbt_flavor_settings * psettings)
|
|
|
8f60d4 |
{
|
|
|
8f60d4 |
const struct slbt_host_params * host;
|
|
|
8f60d4 |
const struct slbt_flavor_settings * settings;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
host = ahost ? ahost : &cctx->host;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (!strcmp(host->flavor,"midipix"))
|
|
|
8f60d4 |
settings = &host_flavor_midipix;
|
|
|
8f60d4 |
else if (!strcmp(host->flavor,"mingw"))
|
|
|
8f60d4 |
settings = &host_flavor_mingw;
|
|
|
8f60d4 |
else if (!strcmp(host->flavor,"cygwin"))
|
|
|
8f60d4 |
settings = &host_flavor_cygwin;
|
|
|
8f60d4 |
else if (!strcmp(host->flavor,"darwin"))
|
|
|
8f60d4 |
settings = &host_flavor_darwin;
|
|
|
8f60d4 |
else
|
|
|
8f60d4 |
settings = &host_flavor_default;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (!ahost) {
|
|
|
8f60d4 |
if (!strcmp(settings->imagefmt,"elf"))
|
|
|
8f60d4 |
cctx->drvflags |= SLBT_DRIVER_IMAGE_ELF;
|
|
|
8f60d4 |
else if (!strcmp(settings->imagefmt,"pe"))
|
|
|
8f60d4 |
cctx->drvflags |= SLBT_DRIVER_IMAGE_PE;
|
|
|
8f60d4 |
else if (!strcmp(settings->imagefmt,"macho"))
|
|
|
8f60d4 |
cctx->drvflags |= SLBT_DRIVER_IMAGE_MACHO;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
memcpy(psettings,settings,sizeof(*settings));
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (cctx->shrext)
|
|
|
8f60d4 |
psettings->dsosuffix = cctx->shrext;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
|
|
|
4b56de |
slbt_hidden int slbt_init_ldrpath(
|
|
|
8f60d4 |
struct slbt_common_ctx * cctx,
|
|
|
8f60d4 |
struct slbt_host_params * host)
|
|
|
8f60d4 |
{
|
|
|
8f60d4 |
char * buf;
|
|
|
8f60d4 |
const char ** ldrpath;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (!cctx->rpath || !(cctx->drvflags & SLBT_DRIVER_IMAGE_ELF)) {
|
|
|
8f60d4 |
host->ldrpath = 0;
|
|
|
8f60d4 |
return 0;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* common? */
|
|
|
8f60d4 |
for (ldrpath=ldrpath_elf; *ldrpath; ldrpath ++)
|
|
|
8f60d4 |
if (!(strcmp(cctx->rpath,*ldrpath))) {
|
|
|
8f60d4 |
host->ldrpath = 0;
|
|
|
8f60d4 |
return 0;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* buf */
|
|
|
8f60d4 |
if (!(buf = malloc(12 + strlen(cctx->host.host))))
|
|
|
8f60d4 |
return -1;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* /usr/{host}/lib */
|
|
|
8f60d4 |
sprintf(buf,"/usr/%s/lib",cctx->host.host);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (!(strcmp(cctx->rpath,buf))) {
|
|
|
8f60d4 |
host->ldrpath = 0;
|
|
|
8f60d4 |
free(buf);
|
|
|
8f60d4 |
return 0;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
/* /usr/{host}/lib64 */
|
|
|
8f60d4 |
sprintf(buf,"/usr/%s/lib64",cctx->host.host);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (!(strcmp(cctx->rpath,buf))) {
|
|
|
8f60d4 |
host->ldrpath = 0;
|
|
|
8f60d4 |
free(buf);
|
|
|
8f60d4 |
return 0;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
host->ldrpath = cctx->rpath;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
free(buf);
|
|
|
8f60d4 |
return 0;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
|
|
|
8f60d4 |
void slbt_reset_alternate_host(const struct slbt_driver_ctx * ctx)
|
|
|
8f60d4 |
{
|
|
|
8f60d4 |
struct slbt_driver_ctx_alloc * ictx;
|
|
|
8f60d4 |
uintptr_t addr;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
addr = (uintptr_t)ctx - offsetof(struct slbt_driver_ctx_alloc,ctx);
|
|
|
8f60d4 |
addr = addr - offsetof(struct slbt_driver_ctx_impl,ctx);
|
|
|
8f60d4 |
ictx = (struct slbt_driver_ctx_alloc *)addr;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
slbt_free_host_params(&ictx->ctx.ahost);
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
int slbt_set_alternate_host(
|
|
|
8f60d4 |
const struct slbt_driver_ctx * ctx,
|
|
|
8f60d4 |
const char * host,
|
|
|
8f60d4 |
const char * flavor)
|
|
|
8f60d4 |
{
|
|
|
8f60d4 |
struct slbt_driver_ctx_alloc * ictx;
|
|
|
8f60d4 |
uintptr_t addr;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
addr = (uintptr_t)ctx - offsetof(struct slbt_driver_ctx_alloc,ctx);
|
|
|
8f60d4 |
addr = addr - offsetof(struct slbt_driver_ctx_impl,ctx);
|
|
|
8f60d4 |
ictx = (struct slbt_driver_ctx_alloc *)addr;
|
|
|
8f60d4 |
slbt_free_host_params(&ictx->ctx.ahost);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (!(ictx->ctx.ahost.host = strdup(host)))
|
|
|
8f60d4 |
return SLBT_SYSTEM_ERROR(ctx,0);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (!(ictx->ctx.ahost.flavor = strdup(flavor))) {
|
|
|
8f60d4 |
slbt_free_host_params(&ictx->ctx.ahost);
|
|
|
8f60d4 |
return SLBT_SYSTEM_ERROR(ctx,0);
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
ictx->ctx.cctx.ahost.host = ictx->ctx.ahost.host;
|
|
|
8f60d4 |
ictx->ctx.cctx.ahost.flavor = ictx->ctx.ahost.flavor;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (slbt_init_host_params(
|
|
|
8f60d4 |
0,
|
|
|
8f60d4 |
ctx->cctx,
|
|
|
8f60d4 |
&ictx->ctx.ahost,
|
|
|
8f60d4 |
&ictx->ctx.cctx.ahost,
|
|
|
8f60d4 |
&ictx->ctx.cctx.acfgmeta,
|
|
|
771899 |
0,0,0,0,0)) {
|
|
|
8f60d4 |
slbt_free_host_params(&ictx->ctx.ahost);
|
|
|
8f60d4 |
return SLBT_CUSTOM_ERROR(ctx,SLBT_ERR_HOST_INIT);
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
slbt_init_flavor_settings(
|
|
|
8f60d4 |
&ictx->ctx.cctx,
|
|
|
8f60d4 |
&ictx->ctx.cctx.ahost,
|
|
|
8f60d4 |
&ictx->ctx.cctx.asettings);
|
|
|
8f60d4 |
|
|
|
8f60d4 |
if (slbt_init_ldrpath(
|
|
|
8f60d4 |
&ictx->ctx.cctx,
|
|
|
8f60d4 |
&ictx->ctx.cctx.ahost)) {
|
|
|
8f60d4 |
slbt_free_host_params(&ictx->ctx.ahost);
|
|
|
8f60d4 |
return SLBT_CUSTOM_ERROR(ctx,SLBT_ERR_LDRPATH_INIT);
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
return 0;
|
|
|
8f60d4 |
}
|
|
|
8f60d4 |
|
|
|
8f60d4 |
int slbt_get_flavor_settings(
|
|
|
8f60d4 |
const char * flavor,
|
|
|
8f60d4 |
const struct slbt_flavor_settings ** settings)
|
|
|
8f60d4 |
{
|
|
|
8f60d4 |
if (!strcmp(flavor,"midipix"))
|
|
|
8f60d4 |
*settings = &host_flavor_midipix;
|
|
|
8f60d4 |
else if (!strcmp(flavor,"mingw"))
|
|
|
8f60d4 |
*settings = &host_flavor_mingw;
|
|
|
8f60d4 |
else if (!strcmp(flavor,"cygwin"))
|
|
|
8f60d4 |
*settings = &host_flavor_cygwin;
|
|
|
8f60d4 |
else if (!strcmp(flavor,"darwin"))
|
|
|
8f60d4 |
*settings = &host_flavor_darwin;
|
|
|
8f60d4 |
else if (!strcmp(flavor,"default"))
|
|
|
8f60d4 |
*settings = &host_flavor_default;
|
|
|
8f60d4 |
else
|
|
|
8f60d4 |
*settings = 0;
|
|
|
8f60d4 |
|
|
|
8f60d4 |
return *settings ? 0 : -1;
|
|
|
8f60d4 |
}
|