summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorruki <[email protected]>2021-10-21 12:42:39 +0800
committerGitHub <[email protected]>2021-10-21 12:42:39 +0800
commitae65d03b29b506c5cc7122214d9eb81ad1efdbcc (patch)
tree166b77f484136db9e33459f4ee64389ba8f8f1ea
parent94529263aba197863bfc37c66ffba12f93b93cd6 (diff)
parent3c5a1cc28b28bab2f714dd4ec163a6f2b1f61cae (diff)
Merge pull request #1759 from xmake-io/nim
Support Nim Language
-rw-r--r--CHANGELOG.md2
-rw-r--r--README.md2
-rw-r--r--README_zh.md2
-rwxr-xr-xtests/projects/nim/console/src/mainbin0 -> 92184 bytes
-rw-r--r--tests/projects/nim/console/src/main.nim1
-rw-r--r--tests/projects/nim/console/xmake.lua5
-rw-r--r--tests/projects/nim/console_with_c/src/foo.c3
-rw-r--r--tests/projects/nim/console_with_c/src/main.nim3
-rw-r--r--tests/projects/nim/console_with_c/xmake.lua10
-rw-r--r--tests/projects/nim/console_with_packages/src/main.nim3
-rw-r--r--tests/projects/nim/console_with_packages/xmake.lua8
-rw-r--r--tests/projects/nim/shared_library/src/foo.nim5
-rw-r--r--tests/projects/nim/shared_library/src/main.nim4
-rw-r--r--tests/projects/nim/shared_library/xmake.lua12
-rw-r--r--tests/projects/nim/static_library/src/bar.nim5
-rw-r--r--tests/projects/nim/static_library/src/foo.nim8
-rw-r--r--tests/projects/nim/static_library/src/main.nim5
-rw-r--r--tests/projects/nim/static_library/xmake.lua12
-rw-r--r--xmake/core/tool/toolchain.lua4
-rw-r--r--xmake/languages/nim/load.lua56
-rw-r--r--xmake/languages/nim/xmake.lua87
-rw-r--r--xmake/modules/core/tools/nim.lua124
-rw-r--r--xmake/modules/detect/tools/find_nim.lua52
-rw-r--r--xmake/modules/detect/tools/nim/has_flags.lua98
-rw-r--r--xmake/platforms/linux/xmake.lua2
-rw-r--r--xmake/platforms/macosx/xmake.lua2
-rw-r--r--xmake/platforms/windows/xmake.lua2
-rw-r--r--xmake/rules/nim/xmake.lua37
-rw-r--r--xmake/rules/rust/build/target.lua7
-rwxr-xr-xxmake/templates/nim/console/project/src/mainbin0 -> 92184 bytes
-rw-r--r--xmake/templates/nim/console/project/src/main.nim1
-rw-r--r--xmake/templates/nim/console/project/xmake.lua7
-rw-r--r--xmake/templates/nim/console/template.lua2
-rw-r--r--xmake/templates/nim/shared/project/src/foo.nim6
-rw-r--r--xmake/templates/nim/shared/project/src/main.nim3
-rw-r--r--xmake/templates/nim/shared/project/xmake.lua14
-rw-r--r--xmake/templates/nim/shared/template.lua2
-rw-r--r--xmake/templates/nim/static/project/src/foo.nim6
-rw-r--r--xmake/templates/nim/static/project/src/main.nim3
-rw-r--r--xmake/templates/nim/static/project/xmake.lua14
-rw-r--r--xmake/templates/nim/static/template.lua2
-rw-r--r--xmake/templates/rust/console/project/xmake.lua6
-rw-r--r--xmake/toolchains/nim/xmake.lua38
43 files changed, 653 insertions, 12 deletions
diff --git a/CHANGELOG.md b/CHANGELOG.md
index e2da4954c..ba059a5c4 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -11,6 +11,7 @@
* [#1747](https://github.com/xmake-io/xmake/issues/1747): Add `set_kind("headeronly")` for target to install files for headeronly library
* [#1019](https://github.com/xmake-io/xmake/issues/1019): Support Unity build
* [#1438](https://github.com/xmake-io/xmake/issues/1438): Support code amalgamation, `xmake l cli.amalgamate`
+* [#1765](https://github.com/xmake-io/xmake/issues/1756): Support nim language
### Changes
@@ -1114,6 +1115,7 @@
* [#1747](https://github.com/xmake-io/xmake/issues/1747): 添加 `set_kind("headeronly")` 更好的处理 headeronly 库的安装
* [#1019](https://github.com/xmake-io/xmake/issues/1019): 支持 Unity build
* [#1438](https://github.com/xmake-io/xmake/issues/1438): 增加 `xmake l cli.amalgamate` 命令支持代码合并
+* [#1765](https://github.com/xmake-io/xmake/issues/1756): 支持 nim 语言
### 改进
diff --git a/README.md b/README.md
index 12ffb7438..741e90823 100644
--- a/README.md
+++ b/README.md
@@ -225,6 +225,7 @@ ifort Intel Fortran Compiler
muslcc The musl-based cross-compilation toolchain
fpc Free Pascal Programming Language Compiler
wasi WASI-enabled WebAssembly C/C++ toolchain
+nim Nim Programming Language Compiler
```
## Supported Languages
@@ -242,6 +243,7 @@ wasi WASI-enabled WebAssembly C/C++ toolchain
* Zig
* Vala
* Pascal
+* Nim
## Supported Features
diff --git a/README_zh.md b/README_zh.md
index d00577c2d..8b40da549 100644
--- a/README_zh.md
+++ b/README_zh.md
@@ -233,6 +233,7 @@ ifort Intel Fortran Compiler
muslcc The musl-based cross-compilation toolchain
fpc Free Pascal Programming Language Compiler
wasi WASI-enabled WebAssembly C/C++ toolchain
+nim Nim Programming Language Compiler
```
## 支持语言
@@ -249,6 +250,7 @@ wasi WASI-enabled WebAssembly C/C++ toolchain
* Zig
* Vala
* Pascal
+* Nim
## 支持特性
diff --git a/tests/projects/nim/console/src/main b/tests/projects/nim/console/src/main
new file mode 100755
index 000000000..84f0819ac
--- /dev/null
+++ b/tests/projects/nim/console/src/main
Binary files differ
diff --git a/tests/projects/nim/console/src/main.nim b/tests/projects/nim/console/src/main.nim
new file mode 100644
index 000000000..17179284f
--- /dev/null
+++ b/tests/projects/nim/console/src/main.nim
@@ -0,0 +1 @@
+echo "hello xmake!"
diff --git a/tests/projects/nim/console/xmake.lua b/tests/projects/nim/console/xmake.lua
new file mode 100644
index 000000000..40459a274
--- /dev/null
+++ b/tests/projects/nim/console/xmake.lua
@@ -0,0 +1,5 @@
+add_rules("mode.debug", "mode.release")
+
+target("test")
+ set_kind("binary")
+ add_files("src/main.nim")
diff --git a/tests/projects/nim/console_with_c/src/foo.c b/tests/projects/nim/console_with_c/src/foo.c
new file mode 100644
index 000000000..7e3f727d6
--- /dev/null
+++ b/tests/projects/nim/console_with_c/src/foo.c
@@ -0,0 +1,3 @@
+int foo(int n) {
+ return n;
+}
diff --git a/tests/projects/nim/console_with_c/src/main.nim b/tests/projects/nim/console_with_c/src/main.nim
new file mode 100644
index 000000000..1be3abe69
--- /dev/null
+++ b/tests/projects/nim/console_with_c/src/main.nim
@@ -0,0 +1,3 @@
+proc foo(n: int): int {.cdecl, importc}
+
+echo foo(2)
diff --git a/tests/projects/nim/console_with_c/xmake.lua b/tests/projects/nim/console_with_c/xmake.lua
new file mode 100644
index 000000000..c2d067cd6
--- /dev/null
+++ b/tests/projects/nim/console_with_c/xmake.lua
@@ -0,0 +1,10 @@
+add_rules("mode.debug", "mode.release")
+
+target("foo")
+ set_kind("static")
+ add_files("src/*.c")
+
+target("test")
+ set_kind("binary")
+ add_deps("foo")
+ add_files("src/main.nim")
diff --git a/tests/projects/nim/console_with_packages/src/main.nim b/tests/projects/nim/console_with_packages/src/main.nim
new file mode 100644
index 000000000..a3368303a
--- /dev/null
+++ b/tests/projects/nim/console_with_packages/src/main.nim
@@ -0,0 +1,3 @@
+proc zlibVersion(): cstring {.cdecl, importc}
+
+echo zlibVersion()
diff --git a/tests/projects/nim/console_with_packages/xmake.lua b/tests/projects/nim/console_with_packages/xmake.lua
new file mode 100644
index 000000000..924ee9632
--- /dev/null
+++ b/tests/projects/nim/console_with_packages/xmake.lua
@@ -0,0 +1,8 @@
+add_rules("mode.debug", "mode.release")
+
+add_requires("zlib")
+
+target("test")
+ set_kind("binary")
+ add_files("src/main.nim")
+ add_packages("zlib")
diff --git a/tests/projects/nim/shared_library/src/foo.nim b/tests/projects/nim/shared_library/src/foo.nim
new file mode 100644
index 000000000..db968d723
--- /dev/null
+++ b/tests/projects/nim/shared_library/src/foo.nim
@@ -0,0 +1,5 @@
+proc foo(n: int): int {.cdecl, exportc, dynlib.} =
+ if n < 2:
+ result = n
+ else:
+ result = foo(n - 1) + (n - 2).foo
diff --git a/tests/projects/nim/shared_library/src/main.nim b/tests/projects/nim/shared_library/src/main.nim
new file mode 100644
index 000000000..81a64bda0
--- /dev/null
+++ b/tests/projects/nim/shared_library/src/main.nim
@@ -0,0 +1,4 @@
+proc foo(n: int): int {.cdecl, importc}
+
+echo foo(2)
+
diff --git a/tests/projects/nim/shared_library/xmake.lua b/tests/projects/nim/shared_library/xmake.lua
new file mode 100644
index 000000000..b560961d6
--- /dev/null
+++ b/tests/projects/nim/shared_library/xmake.lua
@@ -0,0 +1,12 @@
+add_rules("mode.debug", "mode.release")
+
+target("foo")
+ set_kind("shared")
+ add_files("src/foo.nim")
+
+target("test")
+ set_kind("binary")
+ add_deps("foo")
+ add_files("src/main.nim")
+
+
diff --git a/tests/projects/nim/static_library/src/bar.nim b/tests/projects/nim/static_library/src/bar.nim
new file mode 100644
index 000000000..911a3cc85
--- /dev/null
+++ b/tests/projects/nim/static_library/src/bar.nim
@@ -0,0 +1,5 @@
+proc bar(n: int): int {.cdecl, exportc} =
+ if n < 2:
+ result = n
+ else:
+ result = bar(n - 1) + (n - 2).bar
diff --git a/tests/projects/nim/static_library/src/foo.nim b/tests/projects/nim/static_library/src/foo.nim
new file mode 100644
index 000000000..ba0fcad5b
--- /dev/null
+++ b/tests/projects/nim/static_library/src/foo.nim
@@ -0,0 +1,8 @@
+import bar
+
+proc foo(n: int): int {.cdecl, exportc} =
+ if n < 2:
+ result = n
+ else:
+ result = foo(n - 1) + (n - 2).foo
+
diff --git a/tests/projects/nim/static_library/src/main.nim b/tests/projects/nim/static_library/src/main.nim
new file mode 100644
index 000000000..a91ba0614
--- /dev/null
+++ b/tests/projects/nim/static_library/src/main.nim
@@ -0,0 +1,5 @@
+proc foo(n: int): int {.cdecl, importc}
+proc bar(n: int): int {.cdecl, importc}
+
+echo foo(2)
+echo bar(2)
diff --git a/tests/projects/nim/static_library/xmake.lua b/tests/projects/nim/static_library/xmake.lua
new file mode 100644
index 000000000..7ef38314a
--- /dev/null
+++ b/tests/projects/nim/static_library/xmake.lua
@@ -0,0 +1,12 @@
+add_rules("mode.debug", "mode.release")
+
+target("foo")
+ set_kind("static")
+ add_files("src/foo.nim")
+
+target("test")
+ set_kind("binary")
+ add_deps("foo")
+ add_files("src/main.nim")
+
+
diff --git a/xmake/core/tool/toolchain.lua b/xmake/core/tool/toolchain.lua
index 868d05746..59e171d58 100644
--- a/xmake/core/tool/toolchain.lua
+++ b/xmake/core/tool/toolchain.lua
@@ -369,6 +369,10 @@ function _instance:_description(toolkind)
cu = "the cuda compiler",
culd = "the cuda linker",
cuccbin = "the cuda host c++ compiler",
+ nc = "the nim compiler",
+ ncld = "the nim linker",
+ ncsh = "the nim shared library linker",
+ ncar = "the nim static library archiver"
}
self._DESCRIPTIONS = descriptions
end
diff --git a/xmake/languages/nim/load.lua b/xmake/languages/nim/load.lua
new file mode 100644
index 000000000..1e96d7c39
--- /dev/null
+++ b/xmake/languages/nim/load.lua
@@ -0,0 +1,56 @@
+--!A cross-platform build utility based on Lua
+--
+-- Licensed under the Apache License, Version 2.0 (the "License");
+-- you may not use this file except in compliance with the License.
+-- You may obtain a copy of the License at
+--
+-- http://www.apache.org/licenses/LICENSE-2.0
+--
+-- Unless required by applicable law or agreed to in writing, software
+-- distributed under the License is distributed on an "AS IS" BASIS,
+-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-- See the License for the specific language governing permissions and
+-- limitations under the License.
+--
+-- Copyright (C) 2015-present, TBOOX Open Source Group.
+--
+-- @author ruki
+-- @file load.lua
+--
+
+function _get_apis()
+ local apis = {}
+ apis.values = {
+ -- target.add_xxx
+ "target.add_ncflags"
+ , "target.add_ldflags"
+ , "target.add_arflags"
+ , "target.add_shflags"
+ , "target.add_rpathdirs" -- @note do not translate path, it's usually an absolute path or contains $ORIGIN/@loader_path
+ -- option.add_xxx
+ , "option.add_ncflags"
+ , "option.add_ldflags"
+ , "option.add_arflags"
+ , "option.add_shflags"
+ , "option.add_rpathdirs"
+ -- toolchain.add_xxx
+ , "toolchain.add_ncflags"
+ , "toolchain.add_ldflags"
+ , "toolchain.add_arflags"
+ , "toolchain.add_shflags"
+ , "toolchain.add_rpathdirs"
+ }
+ apis.paths = {
+ -- target.add_xxx
+ "target.add_linkdirs"
+ -- option.add_xxx
+ , "option.add_linkdirs"
+ }
+ return apis
+end
+
+function main()
+ return {apis = _get_apis()}
+end
+
+
diff --git a/xmake/languages/nim/xmake.lua b/xmake/languages/nim/xmake.lua
new file mode 100644
index 000000000..44deef165
--- /dev/null
+++ b/xmake/languages/nim/xmake.lua
@@ -0,0 +1,87 @@
+--!A cross-platform build utility based on Lua
+--
+-- Licensed under the Apache License, Version 2.0 (the "License");
+-- you may not use this file except in compliance with the License.
+-- You may obtain a copy of the License at
+--
+-- http://www.apache.org/licenses/LICENSE-2.0
+--
+-- Unless required by applicable law or agreed to in writing, software
+-- distributed under the License is distributed on an "AS IS" BASIS,
+-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-- See the License for the specific language governing permissions and
+-- limitations under the License.
+--
+-- Copyright (C) 2015-present, TBOOX Open Source Group.
+--
+-- @author ruki
+-- @file xmake.lua
+--
+
+language("nim")
+ add_rules("nim")
+ set_sourcekinds {nc = ".nim"}
+ set_sourceflags {nc = "ncflags"}
+ set_targetkinds {binary = "ncld", static = "ncar", shared = "ncsh"}
+ set_targetflags {binary = "ldflags", static = "arflags", shared = "shflags"}
+ set_langkinds {nim = "nc"}
+ set_mixingkinds("nc")
+
+ on_load("load")
+
+ set_nameflags {
+ object = {
+ "config.includedirs"
+ , "target.symbols"
+ , "target.warnings"
+ , "target.defines"
+ , "target.undefines"
+ , "target.optimize:check"
+ , "target.vectorexts:check"
+ , "target.includedirs"
+ , "toolchain.includedirs"
+ }
+ , binary = {
+ "config.linkdirs"
+ , "target.linkdirs"
+ , "target.rpathdirs"
+ , "target.strip"
+ , "target.symbols"
+ , "toolchain.linkdirs"
+ , "toolchain.rpathdirs"
+ , "config.links"
+ , "target.links"
+ , "toolchain.links"
+ }
+ , shared = {
+ "config.linkdirs"
+ , "target.linkdirs"
+ , "target.strip"
+ , "target.symbols"
+ , "toolchain.linkdirs"
+ , "config.links"
+ , "target.links"
+ , "toolchain.links"
+ }
+ , static = {
+ "target.strip"
+ , "target.symbols"
+ }
+ }
+
+ set_menu {
+ config =
+ {
+ {category = "Cross Complation Configuration/Compiler Configuration" }
+ , {nil, "nc", "kv", nil, "The Nim Compiler" }
+
+ , {category = "Cross Complation Configuration/Linker Configuration" }
+ , {nil, "ncld", "kv", nil, "The Nim Linker" }
+ , {nil, "ncar", "kv", nil, "The Nim Static Library Archiver" }
+ , {nil, "ncsh", "kv", nil, "The Nim Shared Library Linker" }
+
+ , {category = "Cross Complation Configuration/Builtin Flags Configuration" }
+ , {nil, "linkdirs", "kv", nil, "The Link Search Directories" }
+ }
+ }
+
diff --git a/xmake/modules/core/tools/nim.lua b/xmake/modules/core/tools/nim.lua
new file mode 100644
index 000000000..20ec40353
--- /dev/null
+++ b/xmake/modules/core/tools/nim.lua
@@ -0,0 +1,124 @@
+--!A cross-platform build utility based on Lua
+--
+-- Licensed under the Apache License, Version 2.0 (the "License");
+-- you may not use this file except in compliance with the License.
+-- You may obtain a copy of the License at
+--
+-- http://www.apache.org/licenses/LICENSE-2.0
+--
+-- Unless required by applicable law or agreed to in writing, software
+-- distributed under the License is distributed on an "AS IS" BASIS,
+-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-- See the License for the specific language governing permissions and
+-- limitations under the License.
+--
+-- Copyright (C) 2015-present, TBOOX Open Source Group.
+--
+-- @author ruki
+-- @file nim.lua
+--
+
+-- imports
+import("core.base.option")
+import("core.project.config")
+import("core.project.project")
+
+-- init it
+--
+-- @see https://nim-lang.org/docs/nimc.html
+function init(self)
+
+ -- init arflags
+ self:set("ncarflags", "--app:staticlib", "--noMain")
+
+ -- init shflags
+ self:set("ncshflags", "--app:lib", "--noMain")
+end
+
+-- make the warning flag
+function nf_warning(self, level)
+ local maps =
+ {
+ none = "--warning:X:off"
+ , less = "--warning:X:on"
+ , more = "--warning:X:on"
+ , all = "--warning:X:on"
+ , allextra = "--warning:X:on"
+ , everything = "--warning:X:on"
+ , error = "--warningAsError:X:on"
+ }
+ return maps[level]
+end
+
+-- make the define flag
+function nf_define(self, macro)
+ return "--define:" .. macro
+end
+
+-- make the undefine flag
+function nf_undefine(self, macro)
+ return "--undef:" .. macro
+end
+
+-- make the optimize flag
+function nf_optimize(self, level)
+ local maps =
+ {
+ none = "--opt:none"
+ , fast = "--opt:speed"
+ , faster = "--opt:speed"
+ , fastest = "--opt:speed"
+ , smallest = "--opt:size"
+ , aggressive = "--opt:speed"
+ }
+ return maps[level]
+end
+
+-- make the symbol flag
+function nf_symbol(self, level)
+ local maps =
+ {
+ debug = "--stackTrace:on"
+ }
+ return maps[level]
+end
+
+-- make the includedir flag
+function nf_includedir(self, dir)
+ return {"--passC:-I" .. path.translate(dir)}
+end
+
+-- make the link flag
+function nf_link(self, lib)
+ return "--passL:-l" .. lib
+end
+
+-- make the linkdir flag
+function nf_linkdir(self, dir)
+ return {"--passL:-L" .. path.translate(dir)}
+end
+
+-- make the build arguments list
+function buildargv(self, sourcefiles, targetkind, targetfile, flags)
+ local flags_extra = {}
+ if targetkind == "static" then
+ -- fix multiple definition of `NimMain', it is only workaround solution
+ -- we need to wait for this problem to be resolved
+ --
+ -- @see https://github.com/nim-lang/Nim/issues/15955
+ local uniquekey = hash.uuid(targetfile):split("-", {plain = true})[1]
+ table.insert(flags_extra, "--passC:-DNimMain=NimMain_" .. uniquekey)
+ table.insert(flags_extra, "--passC:-DNimMainInner=NimMainInner_" .. uniquekey)
+ table.insert(flags_extra, "--passC:-DNimMainModule=NimMainModule_" .. uniquekey)
+ table.insert(flags_extra, "--passC:-DPreMain=PreMain_" .. uniquekey)
+ table.insert(flags_extra, "--passC:-DPreMainInner=PreMainInner_" .. uniquekey)
+ end
+ return self:program(), table.join("c", flags, flags_extra, "-o:" .. targetfile, sourcefiles)
+end
+
+-- build the target file
+function build(self, sourcefiles, targetkind, targetfile, flags)
+ os.mkdir(path.directory(targetfile))
+ os.runv(buildargv(self, sourcefiles, targetkind, targetfile, flags))
+end
+
diff --git a/xmake/modules/detect/tools/find_nim.lua b/xmake/modules/detect/tools/find_nim.lua
new file mode 100644
index 000000000..ae524ddbc
--- /dev/null
+++ b/xmake/modules/detect/tools/find_nim.lua
@@ -0,0 +1,52 @@
+--!A cross-platform build utility based on Lua
+--
+-- Licensed under the Apache License, Version 2.0 (the "License");
+-- you may not use this file except in compliance with the License.
+-- You may obtain a copy of the License at
+--
+-- http://www.apache.org/licenses/LICENSE-2.0
+--
+-- Unless required by applicable law or agreed to in writing, software
+-- distributed under the License is distributed on an "AS IS" BASIS,
+-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-- See the License for the specific language governing permissions and
+-- limitations under the License.
+--
+-- Copyright (C) 2015-present, TBOOX Open Source Group.
+--
+-- @author ruki
+-- @file find_nim.lua
+--
+
+-- imports
+import("lib.detect.find_program")
+import("lib.detect.find_programver")
+
+-- find nim
+--
+-- @param opt the argument options, e.g. {version = true}
+--
+-- @return program, version
+--
+-- @code
+--
+-- local nim = find_nim()
+-- local nim, version = find_nim({program = "nim", version = true})
+--
+-- @endcode
+--
+function main(opt)
+
+ -- init options
+ opt = opt or {}
+
+ -- find program
+ local program = find_program(opt.program or "nim", opt)
+
+ -- find program version
+ local version = nil
+ if program and opt.version then
+ version = find_programver(program, opt)
+ end
+ return program, version
+end
diff --git a/xmake/modules/detect/tools/nim/has_flags.lua b/xmake/modules/detect/tools/nim/has_flags.lua
new file mode 100644
index 000000000..2fe415241
--- /dev/null
+++ b/xmake/modules/detect/tools/nim/has_flags.lua
@@ -0,0 +1,98 @@
+--!A cross-platform build utility based on Lua
+--
+-- Licensed under the Apache License, Version 2.0 (the "License");
+-- you may not use this file except in compliance with the License.
+-- You may obtain a copy of the License at
+--
+-- http://www.apache.org/licenses/LICENSE-2.0
+--
+-- Unless required by applicable law or agreed to in writing, software
+-- distributed under the License is distributed on an "AS IS" BASIS,
+-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-- See the License for the specific language governing permissions and
+-- limitations under the License.
+--
+-- Copyright (C) 2015-present, TBOOX Open Source Group.
+--
+-- @author ruki
+-- @file has_flags.lua
+--
+
+-- imports
+import("core.cache.detectcache")
+
+-- try running
+function _try_running(...)
+
+ local argv = {...}
+ local errors = nil
+ return try { function () os.runv(table.unpack(argv)); return true end, catch { function (errs) errors = (errs or ""):trim() end }}, errors
+end
+
+-- attempt to check it from the argument list
+function _check_from_arglist(flags, opt)
+
+ -- only one flag?
+ if #flags > 1 then
+ return
+ end
+
+ -- make cache key
+ local key = "detect.tools.nim.has_flags"
+
+ -- make allflags key
+ local flagskey = opt.program .. "_" .. (opt.programver or "")
+
+ -- get all allflags from argument list
+ local allflags = detectcache:get2(key, flagskey)
+ if not allflags then
+
+ -- get argument list
+ allflags = {}
+ local arglist = os.iorunv(opt.program, {"--help"})
+ if arglist then
+ for arg in arglist:gmatch("%s+(%-[%-%a%d]+)%s+") do
+ allflags[arg] = true
+ end
+ end
+
+ -- save cache
+ detectcache:set2(key, flagskey, allflags)
+ detectcache:save()
+ end
+ return allflags[flags[1]]
+end
+
+-- try running to check flags
+function _check_try_running(flags, opt)
+
+ -- make an stub source file
+ local sourcefile = path.join(os.tmpdir(), "detect", "nim_has_flags.nim")
+ if not os.isfile(sourcefile) then
+ io.writefile(sourcefile, "echo \"hello\"")
+ end
+
+ -- check it
+ local binaryfile = os.tmpfile()
+ local ok, errors = _try_running(opt.program, table.join("c", flags, "-o:" .. binaryfile, sourcefile))
+ os.tryrm(binaryfile)
+ return ok, errors
+end
+
+-- has_flags(flags)?
+--
+-- @param opt the argument options, e.g. {toolname = "", program = "", programver = "", toolkind = "[cc|cxx|ld|ar|sh|gc|rc|dc|mm|mxx]"}
+--
+-- @return true or false
+--
+function main(flags, opt)
+
+ -- attempt to check it from the argument list
+ if _check_from_arglist(flags, opt) then
+ return true
+ end
+
+ -- try running to check it
+ return _check_try_running(flags, opt)
+end
+
diff --git a/xmake/platforms/linux/xmake.lua b/xmake/platforms/linux/xmake.lua
index f855903f3..ab7c71f75 100644
--- a/xmake/platforms/linux/xmake.lua
+++ b/xmake/platforms/linux/xmake.lua
@@ -40,7 +40,7 @@ platform("linux")
set_installdir("/usr/local")
-- set toolchains
- set_toolchains("envs", "cross", "gcc", "clang", "yasm", "nasm", "fasm", "cuda", "dlang", "go", "rust", "gfortran", "zig", "fpc")
+ set_toolchains("envs", "cross", "gcc", "clang", "yasm", "nasm", "fasm", "cuda", "dlang", "go", "rust", "gfortran", "zig", "fpc", "nim")
-- set menu
set_menu {
diff --git a/xmake/platforms/macosx/xmake.lua b/xmake/platforms/macosx/xmake.lua
index 792a5cad3..8571a13c4 100644
--- a/xmake/platforms/macosx/xmake.lua
+++ b/xmake/platforms/macosx/xmake.lua
@@ -40,7 +40,7 @@ platform("macosx")
set_installdir("/usr/local")
-- set toolchains
- set_toolchains("envs", "xcode", "clang", "gcc", "yasm", "nasm", "cuda", "dlang", "rust", "go", "gfortran", "zig", "fpc")
+ set_toolchains("envs", "xcode", "clang", "gcc", "yasm", "nasm", "cuda", "dlang", "rust", "go", "gfortran", "zig", "fpc", "nim")
-- set menu
set_menu {
diff --git a/xmake/platforms/windows/xmake.lua b/xmake/platforms/windows/xmake.lua
index caf707d50..f7687f44b 100644
--- a/xmake/platforms/windows/xmake.lua
+++ b/xmake/platforms/windows/xmake.lua
@@ -38,7 +38,7 @@ platform("windows")
set_formats("symbol", "$(name).pdb")
-- set toolchains
- set_toolchains("msvc", "clang", "yasm", "nasm", "cuda", "dlang", "rust", "go", "gfortran", "zig", "fpc")
+ set_toolchains("msvc", "clang", "yasm", "nasm", "cuda", "dlang", "rust", "go", "gfortran", "zig", "fpc", "nim")
-- set menu
set_menu {
diff --git a/xmake/rules/nim/xmake.lua b/xmake/rules/nim/xmake.lua
new file mode 100644
index 000000000..7d65c9c12
--- /dev/null
+++ b/xmake/rules/nim/xmake.lua
@@ -0,0 +1,37 @@
+--!A cross-platform build utility based on Lua
+--
+-- Licensed under the Apache License, Version 2.0 (the "License");
+-- you may not use this file except in compliance with the License.
+-- You may obtain a copy of the License at
+--
+-- http://www.apache.org/licenses/LICENSE-2.0
+--
+-- Unless required by applicable law or agreed to in writing, software
+-- distributed under the License is distributed on an "AS IS" BASIS,
+-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-- See the License for the specific language governing permissions and
+-- limitations under the License.
+--
+-- Copyright (C) 2015-present, TBOOX Open Source Group.
+--
+-- @author ruki
+-- @file xmake.lua
+--
+
+-- define rule: nim.build
+rule("nim.build")
+ set_sourcekinds("nc")
+ on_load(function (target)
+ local cachedir = path.join(target:autogendir(), "nimcache")
+ target:add("ncflags", "--nimcache:" .. cachedir, {force = true})
+ end)
+ on_build("build.target")
+
+-- define rule: nim
+rule("nim")
+
+ -- add build rules
+ add_deps("nim.build")
+
+ -- inherit links and linkdirs of all dependent targets by default
+ add_deps("utils.inherit.links")
diff --git a/xmake/rules/rust/build/target.lua b/xmake/rules/rust/build/target.lua
index a1f34beff..5f0167693 100644
--- a/xmake/rules/rust/build/target.lua
+++ b/xmake/rules/rust/build/target.lua
@@ -76,10 +76,11 @@ end
function main(target, opt)
-- @note only support one source kind!
- for _, sourcebatch in pairs(target:sourcebatches()) do
- if sourcebatch.sourcekind == "rc" then
+ local sourcebatches = target:sourcebatches()
+ if sourcebatches then
+ local sourcebatch = sourcebatches["rust.build"]
+ if sourcebatch then
build_sourcefiles(target, sourcebatch, opt)
- break
end
end
end
diff --git a/xmake/templates/nim/console/project/src/main b/xmake/templates/nim/console/project/src/main
new file mode 100755
index 000000000..84f0819ac
--- /dev/null
+++ b/xmake/templates/nim/console/project/src/main
Binary files differ
diff --git a/xmake/templates/nim/console/project/src/main.nim b/xmake/templates/nim/console/project/src/main.nim
new file mode 100644
index 000000000..17179284f
--- /dev/null
+++ b/xmake/templates/nim/console/project/src/main.nim
@@ -0,0 +1 @@
+echo "hello xmake!"
diff --git a/xmake/templates/nim/console/project/xmake.lua b/xmake/templates/nim/console/project/xmake.lua
new file mode 100644
index 000000000..f41148c2f
--- /dev/null
+++ b/xmake/templates/nim/console/project/xmake.lua
@@ -0,0 +1,7 @@
+add_rules("mode.debug", "mode.release")
+
+target("${TARGETNAME}")
+ set_kind("binary")
+ add_files("src/main.nim")
+
+${FAQ}
diff --git a/xmake/templates/nim/console/template.lua b/xmake/templates/nim/console/template.lua
new file mode 100644
index 000000000..ed2e13b57
--- /dev/null
+++ b/xmake/templates/nim/console/template.lua
@@ -0,0 +1,2 @@
+template("console")
+ add_configfiles("xmake.lua")
diff --git a/xmake/templates/nim/shared/project/src/foo.nim b/xmake/templates/nim/shared/project/src/foo.nim
new file mode 100644
index 000000000..cde4de7ca
--- /dev/null
+++ b/xmake/templates/nim/shared/project/src/foo.nim
@@ -0,0 +1,6 @@
+proc foo(n: int): int {.cdecl, exportc, dynlib.} =
+ if n < 2:
+ result = n
+ else:
+ result = foo(n - 1) + (n - 2).foo
+
diff --git a/xmake/templates/nim/shared/project/src/main.nim b/xmake/templates/nim/shared/project/src/main.nim
new file mode 100644
index 000000000..1be3abe69
--- /dev/null
+++ b/xmake/templates/nim/shared/project/src/main.nim
@@ -0,0 +1,3 @@
+proc foo(n: int): int {.cdecl, importc}
+
+echo foo(2)
diff --git a/xmake/templates/nim/shared/project/xmake.lua b/xmake/templates/nim/shared/project/xmake.lua
new file mode 100644
index 000000000..e2d380ac6
--- /dev/null
+++ b/xmake/templates/nim/shared/project/xmake.lua
@@ -0,0 +1,14 @@
+add_rules("mode.debug", "mode.release")
+
+target("${TARGETNAME}")
+ set_kind("shared")
+ add_files("src/foo.nim")
+
+target("${TARGETNAME}_demo")
+ set_kind("binary")
+ add_deps("${TARGETNAME}")
+ add_files("src/main.nim")
+
+${FAQ}
+
+
diff --git a/xmake/templates/nim/shared/template.lua b/xmake/templates/nim/shared/template.lua
new file mode 100644
index 000000000..d7ec5bae4
--- /dev/null
+++ b/xmake/templates/nim/shared/template.lua
@@ -0,0 +1,2 @@
+template("shared")
+ add_configfiles("xmake.lua")
diff --git a/xmake/templates/nim/static/project/src/foo.nim b/xmake/templates/nim/static/project/src/foo.nim
new file mode 100644
index 000000000..be0904262
--- /dev/null
+++ b/xmake/templates/nim/static/project/src/foo.nim
@@ -0,0 +1,6 @@
+proc foo(n: int): int {.cdecl, exportc} =
+ if n < 2:
+ result = n
+ else:
+ result = foo(n - 1) + (n - 2).foo
+
diff --git a/xmake/templates/nim/static/project/src/main.nim b/xmake/templates/nim/static/project/src/main.nim
new file mode 100644
index 000000000..1be3abe69
--- /dev/null
+++ b/xmake/templates/nim/static/project/src/main.nim
@@ -0,0 +1,3 @@
+proc foo(n: int): int {.cdecl, importc}
+
+echo foo(2)
diff --git a/xmake/templates/nim/static/project/xmake.lua b/xmake/templates/nim/static/project/xmake.lua
new file mode 100644
index 000000000..cf70acb9e
--- /dev/null
+++ b/xmake/templates/nim/static/project/xmake.lua
@@ -0,0 +1,14 @@
+add_rules("mode.debug", "mode.release")
+
+target("${TARGETNAME}")
+ set_kind("static")
+ add_files("src/foo.nim")
+
+target("${TARGETNAME}_demo")
+ set_kind("binary")
+ add_deps("${TARGETNAME}")
+ add_files("src/main.nim")
+
+${FAQ}
+
+
diff --git a/xmake/templates/nim/static/template.lua b/xmake/templates/nim/static/template.lua
new file mode 100644
index 000000000..abfe91a4b
--- /dev/null
+++ b/xmake/templates/nim/static/template.lua
@@ -0,0 +1,2 @@
+template("static")
+ add_configfiles("xmake.lua")
diff --git a/xmake/templates/rust/console/project/xmake.lua b/xmake/templates/rust/console/project/xmake.lua
index 7a363c461..5c3f06804 100644
--- a/xmake/templates/rust/console/project/xmake.lua
+++ b/xmake/templates/rust/console/project/xmake.lua
@@ -1,13 +1,7 @@
--- add modes: debug and release
add_rules("mode.debug", "mode.release")
--- add target
target("${TARGETNAME}")
-
- -- set kind
set_kind("binary")
-
- -- add files
add_files("src/*.rs")
${FAQ}
diff --git a/xmake/toolchains/nim/xmake.lua b/xmake/toolchains/nim/xmake.lua
new file mode 100644
index 000000000..660f63f56
--- /dev/null
+++ b/xmake/toolchains/nim/xmake.lua
@@ -0,0 +1,38 @@
+--!A cross-platform build utility based on Lua
+--
+-- Licensed under the Apache License, Version 2.0 (the "License");
+-- you may not use this file except in compliance with the License.
+-- You may obtain a copy of the License at
+--
+-- http://www.apache.org/licenses/LICENSE-2.0
+--
+-- Unless required by applicable law or agreed to in writing, software
+-- distributed under the License is distributed on an "AS IS" BASIS,
+-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-- See the License for the specific language governing permissions and
+-- limitations under the License.
+--
+-- Copyright (C) 2015-present, TBOOX Open Source Group.
+--
+-- @author ruki
+-- @file xmake.lua
+--
+
+-- define toolchain
+toolchain("nim")
+
+ -- set homepage
+ set_homepage("https://nim-lang.org/")
+ set_description("Nim Programming Language Compiler")
+
+ -- set toolset
+ set_toolset("nc", "$(env NC)", "nim")
+ set_toolset("ncld", "$(env NC)", "nim")
+ set_toolset("ncsh", "$(env NC)", "nim")
+ set_toolset("ncar", "$(env NC)", "nim")
+
+ -- on load
+ on_load(function (toolchain)
+ toolchain:set("ncshflags", "")
+ toolchain:set("ncldflags", "")
+ end)