diff options
| author | Saikari <[email protected]> | 2026-02-01 12:19:49 +0300 |
|---|---|---|
| committer | GitHub <[email protected]> | 2026-02-01 12:19:49 +0300 |
| commit | 9fce99ffc77bdd8c77cb0e3d4c129eaa012246f1 (patch) | |
| tree | dc636b1925aaa56d81501529b6b2330e6ea6058c | |
| parent | 336fce6edf7a4a2932b8ac0881cd10b2d62d3ecc (diff) | |
| parent | d7bdbc99bcc5b64a3fa257c5835014f5d8878150 (diff) | |
Merge branch 'xmake-io:dev' into stdin
21 files changed, 522 insertions, 31 deletions
diff --git a/core/src/xmake/engine.c b/core/src/xmake/engine.c index eb07fe2b5..df5ae06be 100644 --- a/core/src/xmake/engine.c +++ b/core/src/xmake/engine.c @@ -278,6 +278,7 @@ tb_int_t xm_winos_registry_query(lua_State *lua); tb_int_t xm_winos_registry_keys(lua_State *lua); tb_int_t xm_winos_registry_values(lua_State *lua); tb_int_t xm_winos_short_path(lua_State *lua); +tb_int_t xm_winos_processes(lua_State* lua); #endif // the utf8 functions @@ -483,6 +484,7 @@ static luaL_Reg const g_winos_functions[] = { { "registry_keys", xm_winos_registry_keys }, { "registry_values", xm_winos_registry_values }, { "short_path", xm_winos_short_path }, + { "processes", xm_winos_processes }, { tb_null, tb_null }, }; #endif diff --git a/core/src/xmake/os/processes.c b/core/src/xmake/os/processes.c new file mode 100644 index 000000000..8dbb92aa2 --- /dev/null +++ b/core/src/xmake/os/processes.c @@ -0,0 +1,86 @@ +/*!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, Xmake Open Source Community. + * + * @author ruki + * @file processes.c + * + */ + +/* ////////////////////////////////////////////////////////////////////////////////////// + * trace + */ +#define TB_TRACE_MODULE_NAME "processes" +#define TB_TRACE_MODULE_DEBUG (0) + +/* ////////////////////////////////////////////////////////////////////////////////////// + * includes + */ +#include "prefix.h" +#ifdef TB_CONFIG_OS_WINDOWS +#include <windows.h> +#include <tlhelp32.h> +#endif + +/* ////////////////////////////////////////////////////////////////////////////////////// + * implementation + */ + +tb_int_t xm_winos_processes(lua_State* lua) { +#ifdef TB_CONFIG_OS_WINDOWS + // init result table + lua_newtable(lua); + + HANDLE hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0); + if (hSnapshot != INVALID_HANDLE_VALUE) { + PROCESSENTRY32W pe32; + pe32.dwSize = sizeof(PROCESSENTRY32W); + + if (Process32FirstW(hSnapshot, &pe32)) { + tb_int_t i = 1; + do { + // new process entry table + lua_newtable(lua); + + // name + tb_char_t name[MAX_PATH * 4]; + tb_size_t size = tb_wtoa(name, pe32.szExeFile, sizeof(name)); + if (size != -1) { + lua_pushlstring(lua, name, size); + } else { + lua_pushstring(lua, ""); + } + lua_setfield(lua, -2, "name"); + + // pid + lua_pushinteger(lua, (tb_int_t)pe32.th32ProcessID); + lua_setfield(lua, -2, "pid"); + + // ppid + lua_pushinteger(lua, (tb_int_t)pe32.th32ParentProcessID); + lua_setfield(lua, -2, "parent_pid"); + + // result[i++] = entry + lua_rawseti(lua, -2, i++); + + } while (Process32NextW(hSnapshot, &pe32)); + } + CloseHandle(hSnapshot); + } + return 1; +#else + return 0; +#endif +} diff --git a/tests/projects/nim/link_library/headers/test_header.h b/tests/projects/nim/link_library/headers/test_header.h new file mode 100644 index 000000000..4b71d3173 --- /dev/null +++ b/tests/projects/nim/link_library/headers/test_header.h @@ -0,0 +1,10 @@ +#ifndef TEST_HEADER_H +#define TEST_HEADER_H + +#define TEST_HEADER_VAL 123 + +static int test_add_five(int x) { + return x + 5; +} + +#endif diff --git a/tests/projects/nim/link_library/inc/test.h b/tests/projects/nim/link_library/inc/test.h new file mode 100644 index 000000000..f7d68cac8 --- /dev/null +++ b/tests/projects/nim/link_library/inc/test.h @@ -0,0 +1,11 @@ + +#ifndef TEST_H +#define TEST_H + +#ifdef TEST_STATIC + #define TEST_MSG "Hello from Static Lib!" +#else + #define TEST_MSG "Hello from Shared Lib!" +#endif + +#endif diff --git a/tests/projects/nim/link_library/maindll.nim b/tests/projects/nim/link_library/maindll.nim new file mode 100644 index 000000000..b13fe1caf --- /dev/null +++ b/tests/projects/nim/link_library/maindll.nim @@ -0,0 +1,16 @@ +import shared + +echo "Calling shared lib mulTwo(10): ", mulTwo(10) +echo "Calling shared lib countWords('hello, world, hello'): ", countWords("hello, world, hello") +echo "Calling shared lib getMsg('test'): ", getMsg() + +{.emit: """ +#include <test_header.h> +""".} + +var testHeaderVal {.importc: "TEST_HEADER_VAL", nodecl.}: cint +echo "TEST_HEADER_VAL: ", testHeaderVal + +proc test_add_five(x: cint): cint {.importc: "test_add_five", nodecl.} +echo "test_add_five(80): ", test_add_five(80) + diff --git a/tests/projects/nim/link_library/mainlib.nim b/tests/projects/nim/link_library/mainlib.nim new file mode 100644 index 000000000..1a1fae06c --- /dev/null +++ b/tests/projects/nim/link_library/mainlib.nim @@ -0,0 +1,30 @@ +import static + +{.emit: """ +#include <zlib.h> +#define STB_IMAGE_IMPLEMENTATION +#include <stb_image.h> +""".} + +proc zlibVersion(): cstring {.importc: "zlibVersion", nodecl.} +proc stbi_set_flip_vertically_on_load(flag_true_if_should_flip: cint) {.importc: "stbi_set_flip_vertically_on_load", nodecl.} + +echo "Zlib Version: ", zlibVersion() + +stbi_set_flip_vertically_on_load(1) +echo "STB Image: Flip vertically on load set to 1" + +echo "Calling static lib addTwo(10): ", addTwo(10) +echo "Calling static lib getAlphabet(): ", getAlphabet() +echo "Calling static lib getMsg('test'): ", getMsg() + +{.emit: """ +#include <test_header.h> +""".} + +var testHeaderVal {.importc: "TEST_HEADER_VAL", nodecl.}: cint +echo "TEST_HEADER_VAL: ", testHeaderVal + +proc test_add_five(x: cint): cint {.importc: "test_add_five", nodecl.} +echo "test_add_five(55): ", test_add_five(55) + diff --git a/tests/projects/nim/link_library/shared.nim b/tests/projects/nim/link_library/shared.nim new file mode 100644 index 000000000..58dacc6df --- /dev/null +++ b/tests/projects/nim/link_library/shared.nim @@ -0,0 +1,29 @@ +proc mulTwo*(x: int): int = + return x * 2 + +import tables, strutils + +proc countWords*(input: string): string = + var wordFrequencies = initCountTable[string]() + for word in input.split(", "): + wordFrequencies.inc(word) + return "The most frequent word is '" & $wordFrequencies.largest & "'" + +{.emit: """ +#include "test.h" +""".} + +proc getMsg*(): cstring {.exportc, dynlib.} = + var msg: cstring + {.emit: "`msg` = TEST_MSG;".} + return msg + +{.emit: """ +#include <test_header.h> +""".} + +var testHeaderVal {.importc: "TEST_HEADER_VAL", nodecl.}: cint +echo "TEST_HEADER_VAL: ", testHeaderVal + +proc test_add_five(x: cint): cint {.importc: "test_add_five", nodecl.} +echo "test_add_five(10): ", test_add_five(10) diff --git a/tests/projects/nim/link_library/static.nim b/tests/projects/nim/link_library/static.nim new file mode 100644 index 000000000..6808d5895 --- /dev/null +++ b/tests/projects/nim/link_library/static.nim @@ -0,0 +1,26 @@ +proc addTwo*(x: int): int = + return x + 2 + +proc getAlphabet*(): string = + for letter in 'a'..'z': + result.add(letter) + +{.emit: """ +#define TEST_STATIC +#include "test.h" +""".} + +proc getMsg*(): cstring {.exportc, dynlib.} = + var msg: cstring + {.emit: "`msg` = TEST_MSG;".} + return msg + +{.emit: """ +#include <test_header.h> +""".} + +var testHeaderVal {.importc: "TEST_HEADER_VAL", nodecl.}: cint +echo "TEST_HEADER_VAL: ", testHeaderVal + +proc test_add_five(x: cint): cint {.importc: "test_add_five", nodecl.} +echo "test_add_five(60): ", test_add_five(60) diff --git a/tests/projects/nim/link_library/xmake.lua b/tests/projects/nim/link_library/xmake.lua new file mode 100644 index 000000000..ba56fcbf2 --- /dev/null +++ b/tests/projects/nim/link_library/xmake.lua @@ -0,0 +1,47 @@ +set_project("link_libs") +add_rules("mode.debug", "mode.release") + +add_requires("zlib", {system = false, configs = {shared = true}}) +add_requires("stb", {system = false}) + +target("headers") + set_kind("headeronly") + add_headerfiles("headers/*.h") + add_includedirs("headers", {public = true}) + +target("executablestatic") + set_kind("binary") + add_files("mainlib.nim") + add_deps("staticlib") + add_packages("zlib", "stb", {public = true}) + if is_plat("linux") then + add_syslinks("pthread", "m") + end + +target("executableshared") + set_kind("binary") + add_files("maindll.nim") + add_deps("sharedlib") + if is_plat("linux") then + add_syslinks("pthread", "m") + end + +target("staticlib") + set_kind("static") + add_files("static.nim") + add_includedirs("inc", {public = true}) + add_headerfiles("inc/*.h") + if is_plat("linux") then + add_syslinks("pthread", "m") + end + add_deps("headers") + +target("sharedlib") + set_kind("shared") + add_files("shared.nim") + add_includedirs("inc", {public = true}) + add_headerfiles("inc/*.h") + if is_plat("linux") then + add_syslinks("pthread", "m") + end + add_deps("headers") diff --git a/tests/projects/policy/compile_commands/src/main.c b/tests/projects/policy/compile_commands/src/main.c new file mode 100644 index 000000000..9b130982d --- /dev/null +++ b/tests/projects/policy/compile_commands/src/main.c @@ -0,0 +1,3 @@ +int main(int argc, char** argv) { + return 0; +} diff --git a/tests/projects/policy/compile_commands/xmake.lua b/tests/projects/policy/compile_commands/xmake.lua new file mode 100644 index 000000000..1ccf48af6 --- /dev/null +++ b/tests/projects/policy/compile_commands/xmake.lua @@ -0,0 +1,10 @@ +add_rules("mode.debug", "mode.release") + +target("enabled") + set_kind("binary") + add_files("src/main.c") + +target("disabled") + set_kind("binary") + add_files("src/main.c") + set_policy("generator.compile_commands", false) diff --git a/xmake/core/base/tty.lua b/xmake/core/base/tty.lua index b3ac35b2b..c3681cdd3 100644 --- a/xmake/core/base/tty.lua +++ b/xmake/core/base/tty.lua @@ -235,15 +235,68 @@ function tty.flush() return tty end --- find the shell from the parent process (linux) -function tty._find_shell_from_parent() - if os.host() ~= "linux" or not os.isfile("/proc/self/stat") then - return +function tty._find_shell_from_parent_on_windows() + local shell + local winos = require("base/winos") + if winos.processes then + local processes = winos.processes() + if processes then + local pid = os.getpid() + local processes_map = {} + for _, process in ipairs(processes) do + processes_map[process.pid] = process + end + local count = 0 + while pid and pid ~= 0 and count < 10 do + count = count + 1 + local process = processes_map[pid] + if not process then + break + end + local name = process.name + if name then + name = name:lower() + if name:sub(-4) == ".exe" then + name = name:sub(1, #name - 4) + end + for _, shellname in ipairs({"zsh", "bash", "fish", "nu", "elvish", "pwsh", "powershell", "cmd", "sh"}) do + if name == shellname then + shell = shellname + break + end + end + end + if shell then + break + end + pid = process.parent_pid or process.ppid -- for backward compatibility + end + end end - local shell + if not shell then + local subhost = xmake._SUBHOST + if subhost == "windows" then + if os.getenv("PROMPT") then + shell = "cmd" + else + local ok, result = os.iorun("pwsh -v") + if ok then + shell = "pwsh" + else + shell = "powershell" + end + end + end + end + return shell +end + + +function tty._find_shell_from_parent_on_linux() local pid = os.getpid() local count = 0 + local shell while pid ~= 0 and count < 4 do count = count + 1 local shell_name = nil @@ -288,6 +341,20 @@ function tty._find_shell_from_parent() return shell end +-- find the shell from the parent process +function tty._find_shell_from_parent() + + -- for windows + if os.host() == "windows" then + return tty._find_shell_from_parent_on_windows() + end + + -- for linux + if os.host() == "linux" and os.isfile("/proc/self/stat") then + return tty._find_shell_from_parent_on_linux() + end +end + -- get shell name function tty.shell() local shell = tty._SHELL @@ -295,22 +362,7 @@ function tty.shell() if os.getenv("NU_VERSION") then shell = "nu" end - if not shell then - local subhost = xmake._SUBHOST - if subhost == "windows" then - if os.getenv("PROMPT") then - shell = "cmd" - else - local ok, result = os.iorun("pwsh -v") - if ok then - shell = "pwsh" - else - shell = "powershell" - end - end - end - end - -- try to find the shell from the parent process (linux) + -- try to find the shell from the parent process if not shell then shell = tty._find_shell_from_parent() end diff --git a/xmake/core/base/winos.lua b/xmake/core/base/winos.lua index 73657662e..9d786fdfc 100644 --- a/xmake/core/base/winos.lua +++ b/xmake/core/base/winos.lua @@ -31,6 +31,7 @@ winos._oem_cp = winos._oem_cp or winos.oem_cp winos._registry_query = winos._registry_query or winos.registry_query winos._registry_keys = winos._registry_keys or winos.registry_keys winos._registry_values = winos._registry_values or winos.registry_values +winos._processes = winos._processes or winos.processes function winos.ansi_cp() if not winos._ANSI_CP then @@ -46,6 +47,10 @@ function winos.oem_cp() return winos._OEM_CP end +if not winos.processes then + winos.processes = winos._processes +end + -- get windows version from name function winos._version_from_name(name) winos._VERSIONS = winos._VERSIONS or { diff --git a/xmake/core/project/policy.lua b/xmake/core/project/policy.lua index 1cecfd01a..5123f0a5c 100644 --- a/xmake/core/project/policy.lua +++ b/xmake/core/project/policy.lua @@ -192,6 +192,8 @@ function policy.policies() ["network.mode"] = {description = "Set the network mode", type = "string"}, -- Set the compatibility version, e.g. 2.0, 3.0 ["compatibility.version"] = {description = "Set the compatibility version", type = "string", default = "3.0", values = {"2.0", "3.0"}}, + -- Enable compile_commands + ["generator.compile_commands"] = {description = "Enable compile_commands.", default = true, type = "boolean"}, -- Generate the solution file in root output directory -- @see https://github.com/xmake-io/xmake/issues/6519 ["generator.vsxmake.root_sln"] = {description = "Generate the solution file in root output directory", default = false, type = "boolean"} diff --git a/xmake/core/sandbox/modules/winos.lua b/xmake/core/sandbox/modules/winos.lua index fec1d07df..eddcf91d4 100644 --- a/xmake/core/sandbox/modules/winos.lua +++ b/xmake/core/sandbox/modules/winos.lua @@ -33,6 +33,7 @@ sandbox_winos.console_cp = winos.console_cp sandbox_winos.console_output_cp = winos.console_output_cp sandbox_winos.logical_drives = winos.logical_drives sandbox_winos.cmdargv = winos.cmdargv +sandbox_winos.processes = winos.processes sandbox_winos.inherit_handles_safely = winos.inherit_handles_safely -- get windows system version diff --git a/xmake/languages/nim/xmake.lua b/xmake/languages/nim/xmake.lua index 65ad6429b..458cd1d33 100644 --- a/xmake/languages/nim/xmake.lua +++ b/xmake/languages/nim/xmake.lua @@ -39,10 +39,13 @@ language("nim") , "target.optimize:check" , "target.vectorexts:check" , "target.includedirs" + , "target.sysincludedirs" , "toolchain.includedirs" } , binary = { "config.linkdirs" + , "target.includedirs" + , "target.sysincludedirs" , "target.linkdirs" , "target.rpathdirs" , "target.strip" @@ -52,9 +55,14 @@ language("nim") , "config.links" , "target.links" , "toolchain.links" + , "config.syslinks" + , "target.syslinks" + , "toolchain.syslinks" } , shared = { "config.linkdirs" + , "target.includedirs" + , "target.sysincludedirs" , "target.linkdirs" , "target.strip" , "target.symbols" @@ -62,10 +70,15 @@ language("nim") , "config.links" , "target.links" , "toolchain.links" + , "config.syslinks" + , "target.syslinks" + , "toolchain.syslinks" } , static = { "target.strip" , "target.symbols" + , "target.includedirs" + , "target.sysincludedirs" } } diff --git a/xmake/modules/core/tools/gcc/has_flags.lua b/xmake/modules/core/tools/gcc/has_flags.lua index c743f91fb..5539fc0f4 100644 --- a/xmake/modules/core/tools/gcc/has_flags.lua +++ b/xmake/modules/core/tools/gcc/has_flags.lua @@ -125,7 +125,7 @@ function _check_try_running(flags, opt, islinker) if not cuda_gpu_flags then local cuda = get_config("cuda") local cuda_sdk = find_cuda(cuda) - local cuda_sdkver = cuda_sdk and cuda_sdk.sdkver or "7.0" + local cuda_sdkver = cuda_sdk and cuda_sdk.version or "7.0" if cuda_sdkver and semver.compare(cuda_sdkver, "12.0") >= 0 then table.insert(args, 1, "--cuda-gpu-arch=sm_80") end diff --git a/xmake/modules/core/tools/nim.lua b/xmake/modules/core/tools/nim.lua index 94cc0645c..415d102f2 100644 --- a/xmake/modules/core/tools/nim.lua +++ b/xmake/modules/core/tools/nim.lua @@ -34,6 +34,23 @@ function init(self) -- init shflags self:set("ncshflags", "--app:lib", "--noMain") + + -- init arch flags + local arch = self:arch() + if arch then + if self:is_arch("x86", "i386") then + self:add("ncflags", "--cpu:i386", "--define:bit32") + if self:is_plat("linux", "macosx", "bsd", "mingw") then + self:add("ncflags", '--passC:"-m32"', '--passL:"-m32"') + end + elseif self:is_arch("x64", "x86_64") then + self:add("ncflags", "--cpu:amd64", "--define:bit64") + elseif self:is_arch("arm64.*") then + self:add("ncflags", "--cpu:arm64", "--define:bit64") + elseif self:is_arch("arm.*") then + self:add("ncflags", "--cpu:arm", "--define:bit32") + end + end end -- make the warning flag @@ -92,31 +109,113 @@ end function nf_strip(self, level) if self:is_plat("linux", "macosx", "bsd") then if level == "debug" or level == "all" then - return "--passL:-s" + return '--passL:"-s"' end end end -- make the includedir flag function nf_includedir(self, dir) - return {"--passC:-I" .. path.translate(dir)} + return {string.format('--passC:"-I%s"', path.translate(dir))} +end + +-- make the sysincludedir flag +function nf_sysincludedir(self, dir) + return nf_includedir(self, dir) end -- make the link flag function nf_link(self, lib) if self:is_plat("windows") then - return "--passL:" .. lib .. ".lib" + return string.format('--passL:"%s.lib"', lib) + else + return string.format('--passL:"-l%s"', lib) + end +end + +-- make the syslink flag +function nf_syslink(self, lib) + if self:is_plat("windows") then + return string.format('--passL:"%s.lib"', lib) else - return "--passL:-l" .. lib + if lib == "pthread" then + return {"--threads:on", string.format('--passL:"-l%s"', lib), '--dynlibOverride:"pthread"'} + else + return string.format('--passL:"-l%s"', lib) + end end end -- make the linkdir flag function nf_linkdir(self, dir) if self:is_plat("windows") then - return {"--passL:-libpath:" .. path.translate(dir)} + return {string.format('--passL:"-libpath:%s"', path.translate(dir))} else - return {"--passL:-L" .. path.translate(dir)} + return {string.format('--passL:"-L%s"', path.translate(dir))} + end +end + +-- make the rpathdir flag +function nf_rpathdir(self, dir, opt) + if self:is_plat("windows") then + return + end + opt = opt or {} + local extra = opt.extra + if extra and extra.installonly then + return + end + dir = path.translate(dir) + + -- Use --passL:"-Wl,-rpath=<dir>" to pass rpath to the linker + -- We use standard -Wl,-rpath for gcc/clang on linux/macosx/bsd without check mainly. + if self:is_plat("macosx", "iphoneos") then + dir = dir:gsub("([@$][%w_]+)", function (name) + if name == "$ORIGIN" then + return "@loader_path" + end + return name + end) + local rpath = string.format("-Wl,-rpath,%s", dir) + return {string.format('--passL:"%s"', rpath)} + elseif self:is_plat("linux", "bsd", "android") then + dir = dir:gsub("([@$][%w_]+)", function (name) + if name == "@loader_path" or name == "@executable_path" then + return "\\$ORIGIN" + elseif name == "$ORIGIN" then + return "\\$ORIGIN" + end + return name + end) + local rpath = string.format("-Wl,-rpath=%s", dir) + local flags = {string.format('--passL:"%s"', rpath)} + if extra then + if extra.runpath == false and self:has_flags(string.format('--passL:"%s,--disable-new-dtags"', rpath), "ldflags") then + flags[1] = string.format('--passL:"%s,--disable-new-dtags"', rpath) + elseif extra.runpath == true and self:has_flags(string.format('--passL:"%s,--enable-new-dtags"', rpath), "ldflags") then + flags[1] = string.format('--passL:"%s,--enable-new-dtags"', rpath) + end + end + return flags + end + + -- fallback + if self:has_flags(string.format('--passL:"-Wl,-rpath=%s"', dir), "ldflags") then + local flags = {string.format('--passL:"-Wl,-rpath=%s"', (dir:gsub("@[%w_]+", function (name) + local maps = { ["@loader_path"] = "$ORIGIN", ["@executable_path"] = "$ORIGIN" } + return maps[name] + end)))} + -- add_rpathdirs("...", {runpath = false}) + if extra then + if extra.runpath == false and self:has_flags(string.format('--passL:"-Wl,-rpath=%s,--disable-new-dtags"', dir), "ldflags") then + flags[1] = string.format('--passL:"-Wl,-rpath=%s,--disable-new-dtags"', dir) + elseif extra.runpath == true and self:has_flags(string.format('--passL:"-Wl,-rpath=%s,--enable-new-dtags"', dir), "ldflags") then + flags[1] = string.format('--passL:"-Wl,-rpath=%s,--enable-new-dtags"', dir) + end + end + return flags + elseif self:has_flags('--passL:"-Xlinker" --passL:"-rpath" --passL:"-Xlinker" ' .. string.format('--passL:"%s"', dir), "ldflags") then + return {'--passL:"-Xlinker"', '--passL:"-rpath"', '--passL:"-Xlinker"', string.format('--passL:"%s"', (dir:gsub("%$ORIGIN", "@loader_path")))} end end diff --git a/xmake/modules/detect/sdks/find_cuda.lua b/xmake/modules/detect/sdks/find_cuda.lua index b767e8e34..5a90cc581 100644 --- a/xmake/modules/detect/sdks/find_cuda.lua +++ b/xmake/modules/detect/sdks/find_cuda.lua @@ -131,7 +131,7 @@ function _find_cuda(sdkdir, sdkver) local includedirs = {path.join(sdkdir, "include")} -- get version - local sdkver = find_programver(path.join(bindir, "nvcc"), {parse = "release (%d+%.%d+),"}) + local version = find_programver(path.join(bindir, "nvcc"), {parse = "release (%d+%.%d+),"}) -- find msbuildextensionsdir on windows local msbuildextensionsdir @@ -140,7 +140,7 @@ function _find_cuda(sdkdir, sdkver) end -- get toolchains - return {sdkdir = sdkdir, bindir = bindir, sdkver = sdkver, linkdirs = linkdirs, includedirs = includedirs, msbuildextensionsdir = msbuildextensionsdir} + return {sdkdir = sdkdir, bindir = bindir, version = version, linkdirs = linkdirs, includedirs = includedirs, msbuildextensionsdir = msbuildextensionsdir} end -- find cuda sdk toolchains @@ -176,7 +176,7 @@ function main(sdkdir, opt) -- save to config config.set("cuda", cuda.sdkdir, {force = true, readonly = true}) - config.set("cuda_sdkver", cuda.sdkver, {force = true, readonly = true}) + config.set("cuda_sdkver", cuda.version, {force = true, readonly = true}) -- trace if opt.verbose or option.get("verbose") then diff --git a/xmake/modules/detect/sdks/find_vstudio.lua b/xmake/modules/detect/sdks/find_vstudio.lua index cf56fcca9..22f5dea6b 100644 --- a/xmake/modules/detect/sdks/find_vstudio.lua +++ b/xmake/modules/detect/sdks/find_vstudio.lua @@ -21,6 +21,7 @@ -- imports import("core.base.option") import("core.base.semver") +import("core.base.hashset") import("core.project.config") import("lib.detect.find_file") import("lib.detect.find_tool") @@ -93,6 +94,9 @@ local vsenvs = , ["4.2"] = "VS42COMNTOOLS" } +-- the original environment variables +local _env_orgs = {} + -- get all known Visual Studio environment variables function get_vcvars() local realvcvars = vcvars @@ -310,6 +314,9 @@ function _load_vcvarsall_impl(vcvarsall, vsver, arch, opt) variables[name] = value end end + + -- check if the environment variables are truncated + _check_vcvarsall_env(variables) if not variables.path then return end @@ -381,6 +388,40 @@ function _strip_toolset_ver(vs_toolset) return vs_toolset end +-- check if the environment variables are truncated +-- https://github.com/xmake-io/xmake/issues/7281 +function _check_vcvarsall_env(vars) + if not option.get("diagnosis") then + return + end + local check_vars = {"PATH", "INCLUDE", "LIB", "LIBPATH"} + for _, name in ipairs(check_vars) do + local value_org = _env_orgs[name] + if value_org == nil then + local value_str = os.getenv(name) + if value_str then + _env_orgs[name] = path.splitenv(value_str) + else + _env_orgs[name] = false + end + value_org = _env_orgs[name] + end + local value_new = vars[name] or vars[name:lower()] + if value_org and value_new and #value_org > 0 then + local values_new = hashset.from(path.splitenv(value_new)) + for _, p in ipairs(value_org) do + if not values_new:has(p) then + if #p > 256 then + p = p:sub(1, 256) .. "..." + end + wprint("%%%s%% is too long and truncated, msvc detection may fail, please clear some unused variables!\n > %s", name, p) + break + end + end + end + end +end + function _load_vcvarsall(vcvarsall, vsver, arch, opt) opt = opt or {} local vs_toolset = opt.toolset or opt.vcvars_ver @@ -414,6 +455,9 @@ end function _find_vstudio(opt) opt = opt or {} + -- clear local cache of environment variables + _env_orgs = {} + -- find the single current MSVC/VS from environment variables local VCInstallDir = os.getenv("VCInstallDir") if VCInstallDir and (VCInstallDir ~= "") then diff --git a/xmake/plugins/project/clang/compile_commands.lua b/xmake/plugins/project/clang/compile_commands.lua index 4f01354fa..909184800 100644 --- a/xmake/plugins/project/clang/compile_commands.lua +++ b/xmake/plugins/project/clang/compile_commands.lua @@ -266,6 +266,11 @@ function _add_target(jsonfile, target) -- https://github.com/xmake-io/xmake/issues/2337 target:data_set("plugin.project.kind", "compile_commands") + -- disable compile_commands? + if target:policy("generator.compile_commands") == false then + return + end + -- enter package environments local oldenvs = os.addenvs(target:pkgenvs()) |
