Files
funnygame/fpc/library/target.cpp
2026-01-10 01:38:06 +02:00

237 lines
6.2 KiB
C++

#include "target.h"
#include "tier0/commandline.h"
#include "tier1/utlstring.h"
#include "sys/utsname.h"
// see Target_t::HostTarget
#if defined(__i386__) && defined(POSIX)
static utsname s_uname;
static int s_iuNameRes = uname(&s_uname);
#endif
//-----------------------------------------------------------------------------
// Generates triplet suitable for most compilers.
//-----------------------------------------------------------------------------
CUtlString Target_t::GetTriplet()
{
CUtlString triplet = "";
if ( cpu == TARGET_CPU_AMD64 )
triplet.AppendTail("x86_64");
if ( cpu == TARGET_CPU_80386 )
triplet.AppendTail("i386");
if ( cpu == TARGET_CPU_80486 )
triplet.AppendTail("i486");
if ( cpu == TARGET_CPU_80586 )
triplet.AppendTail("i586");
if ( cpu == TARGET_CPU_80686 )
triplet.AppendTail("i686");
if ( cpu == TARGET_CPU_AARCH64 )
triplet.AppendTail("aarch64");
if ( cpu == TARGET_CPU_WASM32 )
triplet.AppendTail("wasm32");
triplet.AppendTail("-");
if ( kernel == TARGET_KERNEL_UNKNOWN )
triplet.AppendTail("unknown-unknown");
if ( kernel == TARGET_KERNEL_UNKNOWN_LINUX )
triplet.AppendTail("unknown-linux");
if ( kernel == TARGET_KERNEL_PC_LINUX )
triplet.AppendTail("pc-linux");
if ( kernel == TARGET_KERNEL_ALPINE_LINUX )
triplet.AppendTail("alpine-linux");
if ( kernel == TARGET_KERNEL_WINDOWS )
triplet.AppendTail("pc-windows");
if ( kernel == TARGET_KERNEL_DARWIN )
triplet.AppendTail("apple-darwin");
if ( kernel == TARGET_KERNEL_IOS )
triplet.AppendTail("apple-ios");
if ( kernel == TARGET_KERNEL_ANDROID )
triplet.AppendTail("linux-android");
if ( kernel == TARGET_KERNEL_WASI )
triplet.AppendTail("unknown-wasi");
if ( kernel == TARGET_KERNEL_EMSCRIPTEN )
triplet.AppendTail("unknown-emscripten");
if ( abi != TARGET_ABI_DEFAULT )
triplet.AppendTail("-");
if ( abi == TARGET_ABI_GNU )
triplet.AppendTail("gnu");
if ( abi == TARGET_ABI_MUSL )
triplet.AppendTail("musl");
return triplet;
}
const char *Target_t::GetExecutableFileFormat()
{
if (kernel & TARGET_KERNEL_POSIX)
return "";
if (kernel & TARGET_KERNEL_WINDOWS_DEVICES)
{
return "%s.exe";
}
return NULL;
}
const char *Target_t::GetStaticLibraryFileFormat()
{
if (kernel & TARGET_KERNEL_POSIX)
return "lib%s.a";
if (kernel & TARGET_KERNEL_WINDOWS_DEVICES)
{
switch(abi)
{
case TARGET_ABI_MSVC:
return "%s.lib";
default:
return "lib%s.a";
}
}
return NULL;
}
const char *Target_t::GetDynamicLibraryFileFormat()
{
if (kernel & TARGET_KERNEL_LINUX_DEVICES)
return "lib%s.so";
if (kernel & TARGET_KERNEL_APPLE_DEVICES)
return "lib%s.dylib";
if (kernel & TARGET_KERNEL_WINDOWS_DEVICES)
return "lib%s.dylib";
return NULL;
}
//----------------------------------------------------------------------------
// Returns target on which fpc is being run
//
// For targets such as i386, i486, i586
//----------------------------------------------------------------------------
Target_t Target_t::HostTarget()
{
ETargetKernel kernel = TARGET_KERNEL_UNDEFINED;
#if defined(__linux__)
kernel = TARGET_KERNEL_LINUX;
#elif defined(__APPLE__)
kernel TARGET_KERNEL_DARWIN;
#endif
ETargetCPU cpu = TARGET_CPU_UNDEFINED;
#if defined(__x86_64__)
cpu = TARGET_CPU_AMD64;
#endif
#if defined(__i386__)
cpu = TARGET_CPU_80386;
#endif
// POSIX doesn't know about these
// use uname to get them
#if defined(__i386__) && defined(POSIX)
if (!V_strcmp("i486", s_uname.machine))
cpu = TARGET_CPU_80486;
if (!V_strcmp("i586", s_uname.machine))
cpu = TARGET_CPU_80586;
if (!V_strcmp("i686", s_uname.machine))
cpu = TARGET_CPU_80686;
#endif
ETargetABI abi = TARGET_ABI_GNU;
#ifdef FPC_ARCH
cpu = CPUFromString(FPC_ARCH);
#endif
#ifdef FPC_OS
kernel = KernelFromString(FPC_OS);
#endif
#ifdef FPC_ABI
abi = ABIFromString(FPC_ABI);
#endif
return {
.kernel = kernel,
.cpu = cpu,
.abi = abi,
.optimization = TARGET_DEBUG,
};
};
//-----------------------------------------------------------------------------
// Returns default target for build, by default it will be host target
//-----------------------------------------------------------------------------
Target_t Target_t::DefaultTarget()
{
CUtlString szDevice = CommandLine()->ParamValue("-device");
CUtlString szOS = CommandLine()->ParamValue("-os");
CUtlString szArch = CommandLine()->ParamValue("-arch");
CUtlString szAbi = CommandLine()->ParamValue("-abi");
ETargetKernel kernel = KernelFromString(szOS);
ETargetCPU cpu = CPUFromString(szArch);
ETargetABI abi = ABIFromString(szAbi);
if (cpu == TARGET_CPU_UNDEFINED)
cpu = HostTarget().cpu;
if (kernel == TARGET_KERNEL_UNDEFINED)
kernel = HostTarget().kernel;
if (abi == TARGET_ABI_UNDEFINED)
abi = HostTarget().abi;
return {
.kernel = kernel,
.cpu = cpu,
.abi = abi,
.optimization = TARGET_DEBUG,
};
}
ETargetCPU Target_t::CPUFromString( const char *szName )
{
CUtlString szUtlName = szName;
if ( szUtlName == "x86_64" )
return TARGET_CPU_AMD64;
else if ( szUtlName == "i386" )
return TARGET_CPU_80386;
else if ( szUtlName == "i486" )
return TARGET_CPU_80486;
else if ( szUtlName == "i586" )
return TARGET_CPU_80586;
else if ( szUtlName == "i686" )
return TARGET_CPU_80686;
else if ( szUtlName == "aarch64" )
return TARGET_CPU_AARCH64;
else if ( szUtlName == "wasm32" )
return TARGET_CPU_WASM32;
return TARGET_CPU_UNDEFINED;
}
ETargetKernel Target_t::KernelFromString( const char *szName )
{
CUtlString szUtlName = szName;
if ( szUtlName == "unknown" )
return TARGET_KERNEL_UNKNOWN;
else if ( szUtlName == "windows" )
return TARGET_KERNEL_WINDOWS;
else if ( szUtlName == "linux" )
return TARGET_KERNEL_LINUX;
else if ( szUtlName == "unknown-linux" )
return TARGET_KERNEL_UNKNOWN_LINUX;
else if ( szUtlName == "pc-linux" )
return TARGET_KERNEL_PC_LINUX;
else if ( szUtlName == "alpine-linux" )
return TARGET_KERNEL_ALPINE_LINUX;
else if ( szUtlName == "macos" )
return TARGET_KERNEL_DARWIN;
else if ( szUtlName == "ios" )
return TARGET_KERNEL_IOS;
else if ( szUtlName == "android" )
return TARGET_KERNEL_ANDROID;
return TARGET_KERNEL_UNDEFINED;
}
ETargetABI Target_t::ABIFromString( const char *szName )
{
CUtlString szUtlName = szName;
if ( szUtlName == "gnu" )
return TARGET_ABI_GNU;
else if ( szUtlName == "musl" )
return TARGET_ABI_MUSL;
return TARGET_ABI_UNDEFINED;
}