aboutsummaryrefslogtreecommitdiff
path: root/backend
diff options
context:
space:
mode:
Diffstat (limited to 'backend')
-rw-r--r--backend/ninja/Ninja.cpp356
1 files changed, 228 insertions, 128 deletions
diff --git a/backend/ninja/Ninja.cpp b/backend/ninja/Ninja.cpp
index 2c76fd4..0b7dbe5 100644
--- a/backend/ninja/Ninja.cpp
+++ b/backend/ninja/Ninja.cpp
@@ -498,7 +498,7 @@ namespace backend
string resultStr;
for(ninja::NinjaArg &include : result)
{
- resultStr += "-isystem \"" + include.arg + "\"";
+ resultStr += " -isystem \"" + include.arg + "\"";
}
return resultStr;
}
@@ -592,6 +592,16 @@ namespace backend
return filepath.size();
}
+ static string combineObjectFilesAsZigArgs(const vector<string> &objectFiles)
+ {
+ string result;
+ for(const string &objectFile : objectFiles)
+ {
+ result += " --object \"" + objectFile + "\"";
+ }
+ return result;
+ }
+
Result<bool> Ninja::build(const SibsConfig &config, const _tinydir_char_t *savePath, LinkerFlagCallbackFunc staticLinkerFlagCallbackFunc, LinkerFlagCallbackFunc dynamicLinkerFlagCallback, GlobalIncludeDirCallbackFunc globalIncludeDirCallback)
{
Result<bool> createBuildDirResult = createDirectoryRecursive(savePath);
@@ -888,58 +898,59 @@ namespace backend
// TODO: Remove --library c if project does not depend on c libraries or project only has .zig files
+ vector<ninja::NinjaArg> commonZigArgs = {
+ ninja::NinjaArg::createRaw("-isystem ../../"),
+ ninja::NinjaArg::createRaw("--color on"),
+ ninja::NinjaArg::createRaw("--library c"), // TODO: Remove this if project does not depend on c libraries or project only has .zig files
+ ninja::NinjaArg::createRaw("$globalIncDirZig")
+ };
+
ninja::NinjaVariable zigHeaderFile("headerFile");
vector<ninja::NinjaArg> zigTestArgs = {
- ninja::NinjaArg::createRaw("zig test $in --output $out --output-h $headerFile -isystem ../../ --color on --library c $globalIncDirZig")
+ ninja::NinjaArg::createRaw("zig test $in --output $out --output-h $headerFile")
};
- // TODO: Find a way to do this more efficiently
- vector<ninja::NinjaArg> cflagsIncludes = convertCFlagsIncludesToZigIncludes(config.getCompiler(), cflags);
vector<ninja::NinjaArg> compileZigArgs = {
ninja::NinjaArg::createRaw("zig build-obj"),
ninja::NinjaArg::createRaw("$in"),
- ninja::NinjaArg::createRaw("--output $out"),
ninja::NinjaArg::createRaw("--output-h $headerFile"),
- ninja::NinjaArg::createRaw("-isystem ../../"),
- ninja::NinjaArg::createRaw("--color on"),
- ninja::NinjaArg::createRaw("--library c"), // TODO: Remove this if project does not depend on c libraries or project only has .zig files
- ninja::NinjaArg::createRaw("$globalIncDirZig")
+ ninja::NinjaArg::createRaw("--output $out")
};
- compileZigArgs.insert(compileZigArgs.end(), cflagsIncludes.begin(), cflagsIncludes.end());
- zigTestArgs.insert(zigTestArgs.end(), cflagsIncludes.begin(), cflagsIncludes.end());
-
- if(zigTest)
- {
- // TODO: Verify if we really need to add all libraries for every object file
- vector<ninja::NinjaArg> zigLibraryFlags = convertCLibrariesToZigLibraries(config.getCompiler(), allLinkerFlags);
- zigTestArgs.insert(zigTestArgs.end(), zigLibraryFlags.begin(), zigLibraryFlags.end());
- }
+ // TODO: Find a way to do this more efficiently
+ vector<ninja::NinjaArg> cflagsIncludes = convertCFlagsIncludesToZigIncludes(config.getCompiler(), cflags);
+ commonZigArgs.insert(commonZigArgs.end(), cflagsIncludes.begin(), cflagsIncludes.end());
if(config.getOptimizationLevel() == sibs::OPT_LEV_RELEASE)
{
// TODO: Specify a way to change these options, either in project.conf or argument to sibs build
- compileZigArgs.insert(compileZigArgs.end(), {
- ninja::NinjaArg::createRaw("--release-safe"),
- ninja::NinjaArg::createRaw("--strip")
- });
-
- zigTestArgs.insert(zigTestArgs.end(), {
+ commonZigArgs.insert(commonZigArgs.end(), {
ninja::NinjaArg::createRaw("--release-safe"),
ninja::NinjaArg::createRaw("--strip")
});
}
+ zigTestArgs.insert(zigTestArgs.end(), commonZigArgs.begin(), commonZigArgs.end());
+ compileZigArgs.insert(compileZigArgs.end(), commonZigArgs.begin(), commonZigArgs.end());
+
if(libraryType == LibraryType::STATIC)
compileZigArgs.push_back(ninja::NinjaArg::createRaw("--static"));
else if(libraryType == LibraryType::DYNAMIC) // TODO: Verify if this is the correct way to handle dynamic libraries in zig
compileZigArgs.push_back(ninja::NinjaArg::createRaw("-rdynamic"));
+ if(zigTest)
+ {
+ // TODO: Verify if we really need to add all libraries for every object file
+ vector<ninja::NinjaArg> zigLibraryFlags = convertCLibrariesToZigLibraries(config.getCompiler(), allLinkerFlags);
+ zigTestArgs.insert(zigTestArgs.end(), zigLibraryFlags.begin(), zigLibraryFlags.end());
+ }
+
ninja::NinjaRule *compileZigRule = ninjaBuildFile.createRule("compile_zig", compileZigArgs);
ninja::NinjaRule *testZigRule = ninjaBuildFile.createRule("zig_test", zigTestArgs);
bool usesCFiles = false;
bool usesCppFiles = false;
+ bool onlyZigFiles = true;
vector<string> objectNames;
objectNames.reserve(sourceFiles.size());
@@ -973,6 +984,8 @@ namespace backend
ninjaBuild = compileZigRule->build("../../" + sourceFile.filepath, objectName, { zigHeaderFileValue });
zigBuilds.push_back(ninjaBuild);
}
+ else
+ onlyZigFiles = false;
}
for(const sibs::SourceFile &sourceFile : sourceFiles)
@@ -982,6 +995,7 @@ namespace backend
{
case sibs::Language::C:
{
+ // TODO: Verify what happens if object name contains colon or space
objectName += config.getPackageName() + "@exe/" + sourceFile.filepath;
objectName += getObjectFileExtension(config.getCompiler());
compileCRule->build("../../" + sourceFile.filepath, objectName, {}, zigBuilds);
@@ -1017,72 +1031,98 @@ namespace backend
string projectGeneratedBinary = "\"";
projectGeneratedBinary += savePathUtf8;
projectGeneratedBinary += "/";
+
+ ninja::NinjaVariable zigObjectArgs("object_args");
+ string objectZigArgs;
+ if(onlyZigFiles)
+ objectZigArgs = combineObjectFilesAsZigArgs(objectNames);
+ ninja::NinjaArgValue zigObjectArgsValue = { zigObjectArgs, move(objectZigArgs) };
switch (libraryType)
{
case LibraryType::EXECUTABLE:
{
vector<ninja::NinjaArg> buildExeArgs;
- switch (config.getCompiler())
+ if(onlyZigFiles)
{
- case Compiler::GCC:
+ buildExeArgs.insert(buildExeArgs.end(), {
+ ninja::NinjaArg::createRaw("zig build-exe"),
+ ninja::NinjaArg::createRaw("--name __tmp_zig"),
+ ninja::NinjaArg::createRaw("--output $out"),
+ ninja::NinjaArg::createRaw("$object_args"),
+ });
+ buildExeArgs.insert(buildExeArgs.end(), commonZigArgs.begin(), commonZigArgs.end());
+
+ vector<ninja::NinjaArg> zigLibraryFlags = convertCLibrariesToZigLibraries(config.getCompiler(), allLinkerFlags);
+ buildExeArgs.insert(buildExeArgs.end(), zigLibraryFlags.begin(), zigLibraryFlags.end());
+
+ ninja::NinjaRule *buildExeRule = ninjaBuildFile.createRule("build_exec", buildExeArgs);
+ buildExeRule->build(join(objectNames, " "), config.getPackageName(), { zigObjectArgsValue });
+ }
+ else
+ {
+ switch (config.getCompiler())
{
- buildExeArgs.insert(buildExeArgs.end(), {
- ninja::NinjaArg("ccache"),
- ninja::NinjaArg(usesCppFiles ? "c++" : "cc"),
- ninja::NinjaArg("-o"),
- ninja::NinjaArg("$out"),
- ninja::NinjaArg("$in"),
- ninja::NinjaArg("-Wl,--no-undefined,--as-needed")
- });
-
- if(config.getSanitize())
+ case Compiler::GCC:
{
buildExeArgs.insert(buildExeArgs.end(), {
- ninja::NinjaArg("-lasan"),
- ninja::NinjaArg("-lubsan")
+ ninja::NinjaArg::createRaw("ccache"),
+ ninja::NinjaArg::createRaw(usesCppFiles ? "c++" : "cc"),
+ ninja::NinjaArg::createRaw("-o"),
+ ninja::NinjaArg::createRaw("$out"),
+ ninja::NinjaArg::createRaw("$in"),
+ ninja::NinjaArg::createRaw("-Wl,--no-undefined,--as-needed")
});
- }
- // TODO: Add flag to disable -ldl and -lm (dlopen, dlclose, floor, max, ...)
- buildExeArgs.insert(buildExeArgs.end(), {
- ninja::NinjaArg("-ldl"),
- ninja::NinjaArg("-lm")
- });
- break;
- }
- case Compiler::MSVC:
- {
- // TODO: Do not link all of these. Find a way to only link the ones that are needed
- buildExeArgs.insert(buildExeArgs.end(), {
- ninja::NinjaArg("cl.exe"),
- ninja::NinjaArg("$in"),
- ninja::NinjaArg("/Fe$out"),
- ninja::NinjaArg("Ws2_32.lib"),
- ninja::NinjaArg("Wldap32.lib"),
- ninja::NinjaArg("Crypt32.lib"),
- ninja::NinjaArg("Advapi32.lib"),
- ninja::NinjaArg("Gdi32.lib"),
- ninja::NinjaArg("User32.lib"),
- ninja::NinjaArg("Userenv.lib"),
- ninja::NinjaArg("OpenGL32.lib"),
- ninja::NinjaArg("GlU32.lib"),
- ninja::NinjaArg("Shell32.lib")
- });
- break;
+ if(config.getSanitize())
+ {
+ buildExeArgs.insert(buildExeArgs.end(), {
+ ninja::NinjaArg::createRaw("-lasan"),
+ ninja::NinjaArg::createRaw("-lubsan")
+ });
+ }
+
+ // TODO: Add flag to disable -ldl and -lm (dlopen, dlclose, floor, max, ...)
+ buildExeArgs.insert(buildExeArgs.end(), {
+ ninja::NinjaArg::createRaw("-ldl"),
+ ninja::NinjaArg::createRaw("-lm")
+ });
+ break;
+ }
+ case Compiler::MSVC:
+ {
+ // TODO: Do not link all of these. Find a way to only link the ones that are needed
+ buildExeArgs.insert(buildExeArgs.end(), {
+ ninja::NinjaArg::createRaw("cl.exe"),
+ ninja::NinjaArg::createRaw("$in"),
+ ninja::NinjaArg::createRaw("/Fe$out"),
+ ninja::NinjaArg::createRaw("Ws2_32.lib"),
+ ninja::NinjaArg::createRaw("Wldap32.lib"),
+ ninja::NinjaArg::createRaw("Crypt32.lib"),
+ ninja::NinjaArg::createRaw("Advapi32.lib"),
+ ninja::NinjaArg::createRaw("Gdi32.lib"),
+ ninja::NinjaArg::createRaw("User32.lib"),
+ ninja::NinjaArg::createRaw("Userenv.lib"),
+ ninja::NinjaArg::createRaw("OpenGL32.lib"),
+ ninja::NinjaArg::createRaw("GlU32.lib"),
+ ninja::NinjaArg::createRaw("Shell32.lib")
+ });
+ break;
+ }
}
- }
- if (!allLinkerFlags.empty())
- buildExeArgs.push_back(ninja::NinjaArg::createRaw(allLinkerFlags));
+ if (!allLinkerFlags.empty())
+ buildExeArgs.push_back(ninja::NinjaArg::createRaw(allLinkerFlags));
- ninja::NinjaRule *buildExeRule = ninjaBuildFile.createRule("build_exec", buildExeArgs);
- buildExeRule->build(join(objectNames, " "), config.getPackageName(), {});
+ ninja::NinjaRule *buildExeRule = ninjaBuildFile.createRule("build_exec", buildExeArgs);
+ buildExeRule->build(join(objectNames, " "), config.getPackageName(), {});
+ }
projectGeneratedBinary += config.getPackageName();
#if OS_FAMILY == OS_FAMILY_WINDOWS
projectGeneratedBinary += ".exe";
#endif
+ projectGeneratedBinary += "\"";
break;
}
case LibraryType::STATIC:
@@ -1094,28 +1134,60 @@ namespace backend
case Compiler::GCC:
{
generatedFile = "lib" + config.getPackageName() + ".a";
- buildStaticArgs.insert(buildStaticArgs.end(), {
- ninja::NinjaArg::createRaw("ar"),
- ninja::NinjaArg::createRaw("rcs"),
- ninja::NinjaArg::createRaw("$out"),
- ninja::NinjaArg::createRaw("$in")
- });
break;
}
case Compiler::MSVC:
{
generatedFile = config.getPackageName() + ".lib";
- buildStaticArgs.insert(buildStaticArgs.end(), {
- ninja::NinjaArg::createRaw("lib.exe"),
- ninja::NinjaArg::createRaw("/OUT:$out"),
- ninja::NinjaArg::createRaw("$in")
- });
break;
}
}
- ninja::NinjaRule *buildStaticRule = ninjaBuildFile.createRule("build_static", buildStaticArgs);
- buildStaticRule->build(join(objectNames, " "), generatedFile, {});
+ if(onlyZigFiles)
+ {
+ buildStaticArgs.insert(buildStaticArgs.end(), {
+ ninja::NinjaArg::createRaw("zig build-lib --static"),
+ ninja::NinjaArg::createRaw("--name __tmp_zig"),
+ ninja::NinjaArg::createRaw("--output $out"),
+ ninja::NinjaArg::createRaw("$object_args")
+ });
+ buildStaticArgs.insert(buildStaticArgs.end(), commonZigArgs.begin(), commonZigArgs.end());
+
+ // TODO: Verify if this is needed. It's not needed for c/c++ files...
+ //vector<ninja::NinjaArg> zigLibraryFlags = convertCLibrariesToZigLibraries(config.getCompiler(), allLinkerFlags);
+ //buildStaticArgs.insert(buildStaticArgs.end(), zigLibraryFlags.begin(), zigLibraryFlags.end());
+
+ ninja::NinjaRule *buildStaticRule = ninjaBuildFile.createRule("build_static", buildStaticArgs);
+ buildStaticRule->build(join(objectNames, " "), generatedFile, { zigObjectArgsValue });
+ }
+ else
+ {
+ switch (config.getCompiler())
+ {
+ case Compiler::GCC:
+ {
+ buildStaticArgs.insert(buildStaticArgs.end(), {
+ ninja::NinjaArg::createRaw("ar"),
+ ninja::NinjaArg::createRaw("rcs"),
+ ninja::NinjaArg::createRaw("$out"),
+ ninja::NinjaArg::createRaw("$in")
+ });
+ break;
+ }
+ case Compiler::MSVC:
+ {
+ buildStaticArgs.insert(buildStaticArgs.end(), {
+ ninja::NinjaArg::createRaw("lib.exe"),
+ ninja::NinjaArg::createRaw("/OUT:$out"),
+ ninja::NinjaArg::createRaw("$in")
+ });
+ break;
+ }
+ }
+
+ ninja::NinjaRule *buildStaticRule = ninjaBuildFile.createRule("build_static", buildStaticArgs);
+ buildStaticRule->build(join(objectNames, " "), generatedFile, {});
+ }
projectGeneratedBinary += generatedFile;
projectGeneratedBinary += "\"";
@@ -1133,59 +1205,89 @@ namespace backend
case Compiler::GCC:
{
generatedFile = "lib" + config.getPackageName() + ".so";
-
- buildDynamicArgs.insert(buildDynamicArgs.end(), {
- ninja::NinjaArg("ccache"),
- ninja::NinjaArg(usesCppFiles ? "c++" : "cc"),
- ninja::NinjaArg("$in"),
- ninja::NinjaArg("-shared"),
- ninja::NinjaArg("-o"),
- ninja::NinjaArg("$out"),
- ninja::NinjaArg("-Wl,--no-undefined,--as-needed")
- });
-
- if(config.getSanitize())
- {
- buildDynamicArgs.insert(buildDynamicArgs.end(), {
- ninja::NinjaArg("-lasan"),
- ninja::NinjaArg("-lubsan")
- });
- }
-
- // TODO: Add flag to disable -ldl and -lm (dlopen, dlclose, floor, max, ...)
- buildDynamicArgs.insert(buildDynamicArgs.end(), {
- ninja::NinjaArg("-ldl"),
- ninja::NinjaArg("-lm")
- });
break;
}
case Compiler::MSVC:
{
generatedFile = config.getPackageName() + ".dll";
- buildDynamicArgs.insert(buildDynamicArgs.end(), {
- ninja::NinjaArg::createRaw("lib.exe"),
- ninja::NinjaArg::createRaw("/OUT:$out"),
- ninja::NinjaArg::createRaw("$in"),
- ninja::NinjaArg("Ws2_32.lib"),
- ninja::NinjaArg("Wldap32.lib"),
- ninja::NinjaArg("Crypt32.lib"),
- ninja::NinjaArg("Advapi32.lib"),
- ninja::NinjaArg("Gdi32.lib"),
- ninja::NinjaArg("User32.lib"),
- ninja::NinjaArg("Userenv.lib"),
- ninja::NinjaArg("OpenGL32.lib"),
- ninja::NinjaArg("GlU32.lib"),
- ninja::NinjaArg("Shell32.lib")
- });
break;
}
}
- if (!allLinkerFlags.empty())
- buildDynamicArgs.push_back(ninja::NinjaArg::createRaw(allLinkerFlags));
+ if(onlyZigFiles)
+ {
+ buildDynamicArgs.insert(buildDynamicArgs.end(), {
+ ninja::NinjaArg::createRaw("zig build-lib --rdynamic"),
+ ninja::NinjaArg::createRaw("--name __tmp_zig"),
+ ninja::NinjaArg::createRaw("--output $out"),
+ ninja::NinjaArg::createRaw("$object_args")
+ });
+ buildDynamicArgs.insert(buildDynamicArgs.end(), commonZigArgs.begin(), commonZigArgs.end());
+
+ vector<ninja::NinjaArg> zigLibraryFlags = convertCLibrariesToZigLibraries(config.getCompiler(), allLinkerFlags);
+ buildDynamicArgs.insert(buildDynamicArgs.end(), zigLibraryFlags.begin(), zigLibraryFlags.end());
+
+ ninja::NinjaRule *buildDynamicRule = ninjaBuildFile.createRule("build_dynamic", buildDynamicArgs);
+ buildDynamicRule->build(join(objectNames, " "), generatedFile, { zigObjectArgsValue });
+ }
+ else
+ {
+ switch (config.getCompiler())
+ {
+ case Compiler::GCC:
+ {
+ buildDynamicArgs.insert(buildDynamicArgs.end(), {
+ ninja::NinjaArg::createRaw("ccache"),
+ ninja::NinjaArg::createRaw(usesCppFiles ? "c++" : "cc"),
+ ninja::NinjaArg::createRaw("$in"),
+ ninja::NinjaArg::createRaw("-shared"),
+ ninja::NinjaArg::createRaw("-o"),
+ ninja::NinjaArg::createRaw("$out"),
+ ninja::NinjaArg::createRaw("-Wl,--no-undefined,--as-needed")
+ });
+
+ if(config.getSanitize())
+ {
+ buildDynamicArgs.insert(buildDynamicArgs.end(), {
+ ninja::NinjaArg::createRaw("-lasan"),
+ ninja::NinjaArg::createRaw("-lubsan")
+ });
+ }
+
+ // TODO: Add flag to disable -ldl and -lm (dlopen, dlclose, floor, max, ...)
+ buildDynamicArgs.insert(buildDynamicArgs.end(), {
+ ninja::NinjaArg::createRaw("-ldl"),
+ ninja::NinjaArg::createRaw("-lm")
+ });
+ break;
+ }
+ case Compiler::MSVC:
+ {
+ buildDynamicArgs.insert(buildDynamicArgs.end(), {
+ ninja::NinjaArg::createRaw("lib.exe"),
+ ninja::NinjaArg::createRaw("/OUT:$out"),
+ ninja::NinjaArg::createRaw("$in"),
+ ninja::NinjaArg::createRaw("Ws2_32.lib"),
+ ninja::NinjaArg::createRaw("Wldap32.lib"),
+ ninja::NinjaArg::createRaw("Crypt32.lib"),
+ ninja::NinjaArg::createRaw("Advapi32.lib"),
+ ninja::NinjaArg::createRaw("Gdi32.lib"),
+ ninja::NinjaArg::createRaw("User32.lib"),
+ ninja::NinjaArg::createRaw("Userenv.lib"),
+ ninja::NinjaArg::createRaw("OpenGL32.lib"),
+ ninja::NinjaArg::createRaw("GlU32.lib"),
+ ninja::NinjaArg::createRaw("Shell32.lib")
+ });
+ break;
+ }
+ }
+
+ if (!allLinkerFlags.empty())
+ buildDynamicArgs.push_back(ninja::NinjaArg::createRaw(allLinkerFlags));
- ninja::NinjaRule *buildDynamicRule = ninjaBuildFile.createRule("build_dynamic", buildDynamicArgs);
- buildDynamicRule->build(join(objectNames, " "), generatedFile, {});
+ ninja::NinjaRule *buildDynamicRule = ninjaBuildFile.createRule("build_dynamic", buildDynamicArgs);
+ buildDynamicRule->build(join(objectNames, " "), generatedFile, {});
+ }
projectGeneratedBinary += generatedFile;
projectGeneratedBinary += "\"";
@@ -1209,8 +1311,6 @@ namespace backend
if (fileOverwriteResult.isErr())
return fileOverwriteResult;
- //nprintf(TINYDIR_STRING("Created ninja build file: %s\n"), ninjaBuildFilePath.c_str());
-
Result<bool> buildResult = compile(savePath);
if (!buildResult)
return buildResult;