aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--README.md8
-rw-r--r--backend/ninja/Ninja.cpp65
-rw-r--r--include/Conf.hpp17
-rw-r--r--project.conf2
-rw-r--r--src/CmakeModule.cpp34
-rw-r--r--src/main.cpp45
6 files changed, 122 insertions, 49 deletions
diff --git a/README.md b/README.md
index 5d1db06..6feace7 100644
--- a/README.md
+++ b/README.md
@@ -32,9 +32,9 @@ Use `sibs init` to create a project, which includes a config file to get started
and run the binary under `sibs-build/<platform>/debug/<executable_name>`.
### Supported platforms
-|Linux|Windows(1)|MacOS|OpenBSD|Haiku|... |
-|-----|----------|-----|-------|-----|------|
-|✓ |✓ |✓ |✓ |✓ |TBD(2)|
+|Linux|Windows(1)|MacOS|OpenBSD |Haiku|(Webassembly) Emscripten |... |
+|-----|----------|-----|--------|-----|---------------------------|------|
+|✓ |✓ |✓ |✓ |✓ |✓ |TBD(2)|
(1). Msvc, mingw-w64 and cygwin are supported. Cygwin is defined as a linux platform while mingw-w64 is defined as a windows system.\
(2). Sibs is intended to work on as many platforms as possible, you can help by porting sibs to another platform. Should only be minor changes if the platform is unix-like.
@@ -171,7 +171,7 @@ These are examples of the version string format:
# Version above 1.0 but less or equal to 1.3.2
>1 and <=1.3.2
```
-Dependencies are automatically choosen from system (linux, mac) or if no package manager exists, then it's download from an url (see https://gitlab.com/DEC05EBA/sibs_packages).
+Dependencies are automatically choosen from system (linux, mac) or if no package manager exists, then it's download from an url (see https://git.dec05eba.com/sibs-packages/plain/packages.json).
The dependency can also be a git project, in which case it will have the fields 'git' and optionally 'branch' and 'revision'.
'git' specifies the url to the git repository, 'branch' is the git branch that should be used - defaults to 'master'.
'revision' is the git revision to checkout, defaults to 'HEAD' (latest commit).
diff --git a/backend/ninja/Ninja.cpp b/backend/ninja/Ninja.cpp
index bacbd4c..48595bb 100644
--- a/backend/ninja/Ninja.cpp
+++ b/backend/ninja/Ninja.cpp
@@ -399,15 +399,34 @@ namespace backend
return Result<bool>::Ok(true);
}
- static vector<ninja::NinjaArg> getCompilerSanitizerFlags(const SibsConfig &config)
+ static ninja::NinjaArg getCompilerSanitizerFlag(const SibsConfig &config)
{
if(config.getCompiler() == Compiler::GCC || config.getCompiler() == Compiler::MINGW_W64)
{
- return {
- ninja::NinjaArg::createRaw("-fsanitize=address"),
- ninja::NinjaArg::createRaw("-fsanitize=undefined"),
- ninja::NinjaArg::createRaw("-fsanitize=leak")
- };
+ switch(config.getSanitize()) {
+ case Sanitize::NONE:
+ return {};
+ case Sanitize::ADDRESS:
+ return ninja::NinjaArg::createRaw("-fsanitize=address");
+ case Sanitize::UNDEFINED:
+ return ninja::NinjaArg::createRaw("-fsanitize=undefined");
+ case Sanitize::LEAK:
+ return ninja::NinjaArg::createRaw("-fsanitize=leak");
+ }
+ }
+ return {};
+ }
+
+ static ninja::NinjaArg getlinkerSanitizerFlags(const SibsConfig &config) {
+ switch(config.getSanitize()) {
+ case Sanitize::NONE:
+ return {};
+ case Sanitize::ADDRESS:
+ return ninja::NinjaArg::createRaw("-lasan");
+ case Sanitize::UNDEFINED:
+ return ninja::NinjaArg::createRaw("-lubsan");
+ case Sanitize::LEAK:
+ return ninja::NinjaArg::createRaw("-llsan");
}
return {};
}
@@ -749,9 +768,9 @@ namespace backend
if(compilerType == RuntimeCompilerType::NONE)
compilerType = cppCompilerType;
- bool sanitize = config.getSanitize();
+ Sanitize sanitize = config.getSanitize();
if(compilerType == RuntimeCompilerType::EMSCRIPTEN)
- sanitize = false;
+ sanitize = Sanitize::NONE;
Result<bool> createBuildDirResult = createDirectoryRecursive(savePath);
if (!createBuildDirResult)
@@ -1028,11 +1047,9 @@ namespace backend
vector<ninja::NinjaArg> optimizationFlags = getCompilerOptimizationFlags(config);
compileCCommand.insert(compileCCommand.end(), optimizationFlags.begin(), optimizationFlags.end());
- if(sanitize)
- {
- vector<ninja::NinjaArg> sanitizerFlags = getCompilerSanitizerFlags(config);
- compileCCommand.insert(compileCCommand.end(), sanitizerFlags.begin(), sanitizerFlags.end());
- }
+ ninja::NinjaArg sanitizerFlag = getCompilerSanitizerFlag(config);
+ if(sanitizerFlag.type != ninja::NinjaArg::Type::NONE)
+ compileCCommand.push_back(std::move(sanitizerFlag));
compileCppCommand = compileCCommand;
compileCppCommand[0] = ninja::NinjaArg::createRaw(cppCompilerName);
@@ -1082,11 +1099,9 @@ namespace backend
vector<ninja::NinjaArg> optimizationFlags = getCompilerOptimizationFlags(config);
compileCCommand.insert(compileCCommand.end(), optimizationFlags.begin(), optimizationFlags.end());
- if(sanitize)
- {
- vector<ninja::NinjaArg> sanitizerFlags = getCompilerSanitizerFlags(config);
- compileCCommand.insert(compileCCommand.end(), sanitizerFlags.begin(), sanitizerFlags.end());
- }
+ ninja::NinjaArg sanitizerFlag = getCompilerSanitizerFlag(config);
+ if(sanitizerFlag.type != ninja::NinjaArg::Type::NONE)
+ compileCCommand.push_back(std::move(sanitizerFlag));
compileCppCommand = compileCCommand;
compileCppCommand.push_back(ninja::NinjaArg("/EHs"));
@@ -1378,10 +1393,9 @@ namespace backend
if(!rpath.empty())
buildExeArgs.push_back(ninja::NinjaArg("-Wl,-rpath," + rpath));
- if(sanitize)
- {
- buildExeArgs.push_back(ninja::NinjaArg::createRaw("-lasan -lubsan -llsan"));
- }
+ ninja::NinjaArg sanitizeFlag = getlinkerSanitizerFlags(config);
+ if(sanitizeFlag.type != ninja::NinjaArg::Type::NONE)
+ buildExeArgs.push_back(std::move(sanitizeFlag));
else if(config.getOptimizationLevel() == OPT_LEV_RELEASE)
{
// Strip binary
@@ -1612,10 +1626,9 @@ namespace backend
buildDynamicArgs.push_back(ninja::NinjaArg::createRaw("-s SIDE_MODULE=1"));
}
- if(sanitize)
- {
- buildDynamicArgs.push_back(ninja::NinjaArg::createRaw("-lasan -lubsan -llsan"));
- }
+ ninja::NinjaArg sanitizeFlag = getlinkerSanitizerFlags(config);
+ if(sanitizeFlag.type != ninja::NinjaArg::Type::NONE)
+ buildDynamicArgs.push_back(std::move(sanitizeFlag));
if(config.getOptimizationLevel() == OPT_LEV_RELEASE)
{
diff --git a/include/Conf.hpp b/include/Conf.hpp
index a854552..2ec3148 100644
--- a/include/Conf.hpp
+++ b/include/Conf.hpp
@@ -200,6 +200,15 @@ namespace sibs
bool directoryToIgnore(const FileString &dir, const std::vector<std::string> &ignoreDirList);
bool isProjectNameValid(const std::string &projectName);
+ enum class Sanitize {
+ NONE,
+ ADDRESS,
+ UNDEFINED,
+ LEAK
+ };
+
+ const Sanitize SANITIZE_INVALID = (Sanitize)-1;
+
class SibsConfig : public ConfigCallback
{
public:
@@ -214,7 +223,7 @@ namespace sibs
cVersion(CVersion::C11),
cppVersion(CPPVersion::CPP14),
mainProject(false),
- sanitize(false),
+ sanitize(Sanitize::NONE),
showWarnings(false),
errorOnWarning(false),
zigTestAllFiles(false),
@@ -396,12 +405,12 @@ namespace sibs
this->mainProject = mainProject;
}
- bool getSanitize() const
+ Sanitize getSanitize() const
{
return sanitize;
}
- void setSanitize(bool sanitize)
+ void setSanitize(Sanitize sanitize)
{
this->sanitize = sanitize;
}
@@ -472,7 +481,7 @@ namespace sibs
bool buildTests;
bool finishedProcessing;
bool mainProject;
- bool sanitize;
+ Sanitize sanitize;
};
class SibsTestConfig : public SibsConfig
diff --git a/project.conf b/project.conf
index f7915a8..ecf6f54 100644
--- a/project.conf
+++ b/project.conf
@@ -1,7 +1,7 @@
[package]
name = "sibs"
type = "executable"
-version = "0.3.1"
+version = "0.3.2"
authors = ["DEC05EBA <0xdec05eba@gmail.com>"]
platforms = ["any"]
diff --git a/src/CmakeModule.cpp b/src/CmakeModule.cpp
index a690948..f57a8cf 100644
--- a/src/CmakeModule.cpp
+++ b/src/CmakeModule.cpp
@@ -74,6 +74,23 @@ namespace sibs
string allLinkerFlags = "";
#endif
+ if(config.getCompiler() == Compiler::GCC || config.getCompiler() == Compiler::MINGW_W64)
+ {
+ switch(config.getSanitize()) {
+ case Sanitize::NONE:
+ break;
+ case Sanitize::ADDRESS:
+ allLinkerFlags += " -lasan";
+ break;
+ case Sanitize::UNDEFINED:
+ allLinkerFlags += TINYDIR_STRING(" -lubsan");
+ break;
+ case Sanitize::LEAK:
+ allLinkerFlags += TINYDIR_STRING(" -llsan");
+ break;
+ }
+ }
+
#if 0
// TODO: Somehow check loading order, because it has to be correct to work.. Or does it for dynamic libraries?
// Anyways it's required for static libraries (especially on Windows)
@@ -180,9 +197,22 @@ namespace sibs
FileString cflags = TINYDIR_STRING("-fPIC");
FileString cxxflags;
- if(config.getCompiler() == Compiler::GCC && config.getSanitize())
+ if(config.getCompiler() == Compiler::GCC || config.getCompiler() == Compiler::MINGW_W64)
{
- cflags += TINYDIR_STRING(" -fno-omit-frame-pointer -fsanitize=address -fsanitize=undefined -fsanitize=leak -lasan -lubsan -llsan");
+ cflags += TINYDIR_STRING(" -fno-omit-frame-pointer");
+ switch(config.getSanitize()) {
+ case Sanitize::NONE:
+ break;
+ case Sanitize::ADDRESS:
+ cflags += TINYDIR_STRING(" -fsanitize=address");
+ break;
+ case Sanitize::UNDEFINED:
+ cflags += TINYDIR_STRING(" -fsanitize=undefined");
+ break;
+ case Sanitize::LEAK:
+ cflags += TINYDIR_STRING(" -fsanitize=leak");
+ break;
+ }
}
#if OS_FAMILY == OS_FAMILY_POSIX
diff --git a/src/main.cpp b/src/main.cpp
index 47da4bb..3d11fd5 100644
--- a/src/main.cpp
+++ b/src/main.cpp
@@ -129,19 +129,19 @@ static void usage()
static void usageBuild()
{
- printf("Usage: sibs build [project_path] [--debug|--release] [--sanitize] [--platform <platform>]\n\n");
+ printf("Usage: sibs build [project_path] [--debug|--release] [--sanitize=(address|undefined|leak|none)] [--platform <platform>]\n\n");
printf("Build a sibs project\n\n");
printf("Options:\n");
printf(" project_path\t\tThe directory containing a project.conf file - Optional (default: current directory)\n");
printf(" --debug|--release\t\tOptimization level to build project and dependencies with (if not a system package) - Optional (default: --debug)\n");
- printf(" --sanitize\t\tAdd runtime address/undefined behavior sanitization. Program can be up to 3 times slower and use 10 times as much RAM. Ignored if compiler doesn't support sanitization - Optional (default: disabled)\n");
+ printf(" --sanitize\t\tAdd runtime address/undefined behavior sanitization. Program can be up to 3 times slower and use 10 times as much RAM. Ignored if compiler doesn't support sanitization - Optional (default: none)\n");
printf(" --platform\t\tThe platform to build for - Optional (default: the running platform)\n");
printf("Examples:\n");
printf(" sibs build\n");
printf(" sibs build dirA/dirB\n");
printf(" sibs build --release\n");
printf(" sibs build dirA --release\n");
- printf(" sibs build --sanitize\n");
+ printf(" sibs build --sanitize=address\n");
printf(" sibs build --release --platform win64\n");
exit(1);
}
@@ -163,17 +163,17 @@ static void usageNew()
static void usageTest()
{
- printf("Usage: sibs test [project_path] [--no-sanitize] [--file <filepath>...|--all-files]\n\n");
+ printf("Usage: sibs test [project_path] [--sanitize=(address|undefined|leak|none)] [--file <filepath>...|--all-files]\n\n");
printf("Build and run tests for a sibs project\n\n");
printf("Options:\n");
printf(" project_path\t\tThe directory containing a project.conf file - Optional (default: current directory)\n");
- printf(" --no-sanitize\t\tDisable runtime address/undefined behavior - Optional (default: enabled), Only applicable for C and C++\n");
+ printf(" --sanitize\t\tAdd runtime address/undefined behavior sanitization. Program can be up to 3 times slower and use 10 times as much RAM. Ignored if compiler doesn't support sanitization - Optional (default: address)\n");
printf(" --file\t\t\tSpecify file to test, path to test file should be defined after this. Can be defined multiple times to test multiple files - Optional (default: not used), Only applicable for Zig\n");
printf(" --all-files\t\t\tTest all files - Optional (default: not used), Only applicable for Zig\n");
printf("Examples:\n");
printf(" sibs test\n");
printf(" sibs test dirA/dirB\n");
- printf(" sibs test --no-sanitize\n");
+ printf(" sibs test --sanitize=none\n");
printf(" sibs test --all-files\n");
printf(" sibs test --file src/foo.zig --file src/bar.zig\n");
exit(1);
@@ -450,11 +450,24 @@ static int buildProject(const FileString &projectPath, const FileString &project
return 0;
}
+static Sanitize sanitize_string_to_type(const _tinydir_char_t *str) {
+ if(strcmp(str, TINYDIR_STRING("address")) == 0)
+ return Sanitize::ADDRESS;
+ else if(strcmp(str, TINYDIR_STRING("undefined")) == 0)
+ return Sanitize::UNDEFINED;
+ else if(strcmp(str, TINYDIR_STRING("leak")) == 0)
+ return Sanitize::LEAK;
+ else if(strcmp(str, TINYDIR_STRING("none")) == 0)
+ return Sanitize::NONE;
+ else
+ return SANITIZE_INVALID;
+}
+
static int buildProject(int argc, const _tinydir_char_t **argv)
{
OptimizationLevel optimizationLevel = OPT_LEV_NONE;
FileString projectPath;
- bool sanitize = false;
+ Sanitize sanitize = Sanitize::NONE;
FileString platformName;
for(int i = 0; i < argc; ++i)
@@ -478,9 +491,13 @@ static int buildProject(int argc, const _tinydir_char_t **argv)
}
optimizationLevel = OPT_LEV_RELEASE;
}
- else if(_tinydir_strcmp(arg, TINYDIR_STRING("--sanitize")) == 0)
+ else if(_tinydir_strncmp(arg, TINYDIR_STRING("--sanitize="), 10) == 0)
{
- sanitize = true;
+ sanitize = sanitize_string_to_type(arg + 11);
+ if(sanitize == SANITIZE_INVALID) {
+ ferr << "Error: Invalid sanitize option " << (arg + 11) << ", expected address, undefined, leak or none" << endl;
+ usageBuild();
+ }
}
else if(_tinydir_strcmp(arg, TINYDIR_STRING("--platform")) == 0)
{
@@ -587,14 +604,18 @@ static int testProject(int argc, const _tinydir_char_t **argv)
FileString projectPath;
vector<FileString> filesToTest;
bool testAllFiles = false;
- bool sanitize = true;
+ Sanitize sanitize = Sanitize::ADDRESS;
for(int i = 0; i < argc; ++i)
{
const _tinydir_char_t *arg = argv[i];
- if(_tinydir_strcmp(arg, TINYDIR_STRING("--no-sanitize")) == 0)
+ if(_tinydir_strncmp(arg, TINYDIR_STRING("--sanitize="), 10) == 0)
{
- sanitize = false;
+ sanitize = sanitize_string_to_type(arg + 11);
+ if(sanitize == SANITIZE_INVALID) {
+ ferr << "Error: Invalid sanitize option " << (arg + 11) << ", expected address, undefined, leak or none" << endl;
+ usageTest();
+ }
}
else if(_tinydir_strcmp(arg, TINYDIR_STRING("--file")) == 0)
{