diff --git a/build/premake/extern_libs5.lua b/build/premake/extern_libs5.lua index de84a8272e..87cc6fee9a 100644 --- a/build/premake/extern_libs5.lua +++ b/build/premake/extern_libs5.lua @@ -638,7 +638,7 @@ extern_lib_defs = { compile_settings = function() if _OPTIONS["with-system-mozjs"] then if not _OPTIONS["android"] then - pkgconfig.add_includes("mozjs-91") + pkgconfig.add_includes_after("mozjs-91") end else if os.istarget("windows") then diff --git a/build/premake/pkgconfig/pkgconfig.lua b/build/premake/pkgconfig/pkgconfig.lua index 2d8a22fbc0..28d20490bd 100644 --- a/build/premake/pkgconfig/pkgconfig.lua +++ b/build/premake/pkgconfig/pkgconfig.lua @@ -1,5 +1,5 @@ local m = {} -m._VERSION = "1.1.2-dev" +m._VERSION = "1.2.0-dev" m.additional_pc_path = nil m.static_link_libs = false @@ -8,7 +8,7 @@ local function os_capture(cmd) return io.popen(cmd, 'r'):read('*a'):gsub("\n", " ") end -function m.add_includes(lib, alternative_cmd, alternative_flags) +local function parse_pkg_config_includes(lib, alternative_cmd, alternative_flags) local result if not alternative_cmd then local pc_path = m.additional_pc_path and "PKG_CONFIG_PATH="..m.additional_pc_path or "" @@ -24,6 +24,7 @@ function m.add_includes(lib, alternative_cmd, alternative_flags) -- Small trick: delete the space after -include so that we can detect -- which files have to be force-included without difficulty. result = result:gsub("%-include +(%g+)", "-include%1") + result = result:gsub("%-isystem +(%g+)", "-isystem%1") local dirs = {} local files = {} @@ -31,6 +32,8 @@ function m.add_includes(lib, alternative_cmd, alternative_flags) for w in string.gmatch(result, "[^' ']+") do if string.sub(w,1,2) == "-I" then table.insert(dirs, string.sub(w,3)) + elseif string.sub(w,1,8) == "-isystem" then + table.insert(dirs, string.sub(w,9)) elseif string.sub(w,1,8) == "-include" then table.insert(files, string.sub(w,9)) else @@ -38,6 +41,12 @@ function m.add_includes(lib, alternative_cmd, alternative_flags) end end + return dirs, files, options +end + +function m.add_includes(lib, alternative_cmd, alternative_flags) + local dirs, files, options = parse_pkg_config_includes(lib, alternative_cmd, alternative_flags) + -- As of premake5-beta2, `sysincludedirs` has been deprecated in favour of -- `externalincludedirs`, and continuing to use it causes warnings to be emitted. -- We use `externalincludedirs` when available to prevent the warnings, falling back @@ -53,6 +62,20 @@ function m.add_includes(lib, alternative_cmd, alternative_flags) buildoptions(options) end +function m.add_includes_after(lib, alternative_cmd, alternative_flags) + -- Support for includedirsafter was added after the 5.0.0-beta2 release. + -- Fall back if unavailable to support `--with-system-premake5` + if includedirsafter then + local dirs, files, options = parse_pkg_config_includes(lib, alternative_cmd, alternative_flags) + + includedirsafter(dirs) + forceincludes(files) + buildoptions(options) + else + m.add_includes(lib, alternative_cmd, alternative_flags) + end +end + function m.add_links(lib, alternative_cmd, alternative_flags) local result if not alternative_cmd then diff --git a/libraries/source/premake-core/build.sh b/libraries/source/premake-core/build.sh index 00bb4a354a..83d9024fac 100755 --- a/libraries/source/premake-core/build.sh +++ b/libraries/source/premake-core/build.sh @@ -8,7 +8,7 @@ set -e cd "$(dirname "$0")" PV=5.0.0-beta2 -LIB_VERSION=${PV}+wfg1 +LIB_VERSION=${PV}+wfg2 if [ -e .already-built ] && [ "$(cat .already-built || true)" = "${LIB_VERSION}" ]; then echo "premake is already up to date." @@ -28,6 +28,7 @@ tar -xf "premake-core-${PV}.tar.gz" #patch patch -d "premake-core-${PV}" -p1 +Date: Sun, 29 Jan 2023 19:18:15 -0500 +Subject: Add support for idirafter flag in GCC/Clang + +--- + modules/codelite/codelite_project.lua | 2 +- + .../codelite/tests/test_codelite_config.lua | 10 +++++ + modules/gmake/gmake_cpp.lua | 2 +- + modules/gmake2/gmake2_cpp.lua | 2 +- + modules/gmake2/tests/_tests.lua | 1 + + modules/gmake2/tests/test_gmake2_includes.lua | 42 +++++++++++++++++++ + modules/vstudio/vs2010_vcxproj.lua | 3 +- + modules/xcode/tests/test_xcode_project.lua | 30 +++++++++++++ + modules/xcode/xcode_common.lua | 13 +++--- + src/_premake_init.lua | 7 ++++ + src/tools/clang.lua | 13 +++++- + src/tools/gcc.lua | 27 +++++++++++- + src/tools/msc.lua | 11 ++++- + tests/tools/test_gcc.lua | 15 +++++-- + tests/tools/test_msc.lua | 17 ++++++++ + website/docs/Project-API.md | 1 + + website/docs/includedirsafter.md | 41 ++++++++++++++++++ + website/sidebars.js | 2 + + 18 files changed, 221 insertions(+), 18 deletions(-) + create mode 100644 modules/gmake2/tests/test_gmake2_includes.lua + create mode 100644 website/docs/includedirsafter.md + +diff --git a/modules/codelite/codelite_project.lua b/modules/codelite/codelite_project.lua +index 47a678fd..5a798207 100755 +--- a/modules/codelite/codelite_project.lua ++++ b/modules/codelite/codelite_project.lua +@@ -202,7 +202,7 @@ + end + + local toolset = m.getcompiler(cfg) +- local externalincludedirs = toolset.getincludedirs(cfg, {}, cfg.externalincludedirs, cfg.frameworkdirs) ++ local externalincludedirs = toolset.getincludedirs(cfg, {}, cfg.externalincludedirs, cfg.frameworkdirs, cfg.includedirsafter) + local forceincludes = toolset.getforceincludes(cfg) + local cxxflags = table.concat(table.join(externalincludedirs, toolset.getcxxflags(cfg), forceincludes, cfg.buildoptions), ";") + local cflags = table.concat(table.join(externalincludedirs, toolset.getcflags(cfg), forceincludes, cfg.buildoptions), ";") +diff --git a/modules/codelite/tests/test_codelite_config.lua b/modules/codelite/tests/test_codelite_config.lua +index 423bbe05..10e9a030 100644 +--- a/modules/codelite/tests/test_codelite_config.lua ++++ b/modules/codelite/tests/test_codelite_config.lua +@@ -86,6 +86,16 @@ + ]] + end + ++ function suite.OnProjectCfg_IncludeDirsAfter() ++ includedirsafter { "sysdir", "sysdir2/"} ++ prepare() ++ codelite.project.compiler(cfg) ++ test.capture [[ ++ ++ ++ ]] ++ end ++ + + function suite.OnProjectCfg_Defines() + defines { "TEST", "DEF", "VAL=1", "ESCAPE=\"WITH SPACE\"" } +diff --git a/modules/gmake/gmake_cpp.lua b/modules/gmake/gmake_cpp.lua +index dcd6f27c..a31587ea 100644 +--- a/modules/gmake/gmake_cpp.lua ++++ b/modules/gmake/gmake_cpp.lua +@@ -521,7 +521,7 @@ end + + + function make.includes(cfg, toolset) +- local includes = toolset.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs, cfg.frameworkdirs) ++ local includes = toolset.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs, cfg.frameworkdirs, cfg.includedirsafter) + _p(' INCLUDES +=%s', make.list(includes)) + end + +diff --git a/modules/gmake2/gmake2_cpp.lua b/modules/gmake2/gmake2_cpp.lua +index 01f1e2ce..7edf32c6 100644 +--- a/modules/gmake2/gmake2_cpp.lua ++++ b/modules/gmake2/gmake2_cpp.lua +@@ -386,7 +386,7 @@ + + + function cpp.includes(cfg, toolset) +- local includes = toolset.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs, cfg.frameworkdirs) ++ local includes = toolset.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs, cfg.frameworkdirs, cfg.includedirsafter) + p.outln('INCLUDES +=' .. gmake2.list(includes)) + end + +diff --git a/modules/gmake2/tests/_tests.lua b/modules/gmake2/tests/_tests.lua +index 19b2ff36..5b866d1e 100644 +--- a/modules/gmake2/tests/_tests.lua ++++ b/modules/gmake2/tests/_tests.lua +@@ -5,6 +5,7 @@ return { + "test_gmake2_clang.lua", + "test_gmake2_file_rules.lua", + "test_gmake2_flags.lua", ++ "test_gmake2_includes.lua", + "test_gmake2_ldflags.lua", + "test_gmake2_linking.lua", + "test_gmake2_makefile.lua", +diff --git a/modules/gmake2/tests/test_gmake2_includes.lua b/modules/gmake2/tests/test_gmake2_includes.lua +new file mode 100644 +index 00000000..f39a0933 +--- /dev/null ++++ b/modules/gmake2/tests/test_gmake2_includes.lua +@@ -0,0 +1,42 @@ ++-- ++-- test_gmake2_includes.lua ++-- Validate the link step generation for makefiles. ++-- (c) 2016-2023 Jason Perkins and the Premake project ++-- ++ ++local suite = test.declare("gmake2_includes") ++ ++local p = premake ++local gmake2 = p.modules.gmake2 ++ ++local project = p.project ++ ++ ++-- ++-- Setup and teardown ++-- ++ ++local wks, prj ++ ++function suite.setup() ++ wks, prj = test.createWorkspace() ++end ++ ++local function prepare(calls) ++ local cfg = test.getconfig(prj, "Debug") ++ local toolset = p.tools.gcc ++ gmake2.cpp.includes(cfg, toolset) ++end ++ ++ ++-- ++-- Check for idirafter flags ++-- ++ ++function suite.includeDirsAfter() ++ includedirsafter { 'DirAfter' } ++ prepare() ++ test.capture [[ ++INCLUDES += -idirafter DirAfter ++ ]] ++end +\ No newline at end of file +diff --git a/modules/vstudio/vs2010_vcxproj.lua b/modules/vstudio/vs2010_vcxproj.lua +index fe84c4f3..57faa0f7 100644 +--- a/modules/vstudio/vs2010_vcxproj.lua ++++ b/modules/vstudio/vs2010_vcxproj.lua +@@ -2205,7 +2205,8 @@ + + + function m.includePath(cfg) +- local dirs = vstudio.path(cfg, cfg.externalincludedirs) ++ local externaldirs = table.join(cfg.externalincludedirs, cfg.includedirsafter) ++ local dirs = vstudio.path(cfg, externaldirs) + if #dirs > 0 then + if _ACTION < "vs2022" then + m.element("IncludePath", nil, "%s;$(IncludePath)", table.concat(dirs, ";")) +diff --git a/modules/xcode/tests/test_xcode_project.lua b/modules/xcode/tests/test_xcode_project.lua +index 87096e21..a0e445af 100644 +--- a/modules/xcode/tests/test_xcode_project.lua ++++ b/modules/xcode/tests/test_xcode_project.lua +@@ -2428,6 +2428,36 @@ + ]] + end + ++ function suite.XCBuildConfigurationProject_OnIncludeDirsAfter() ++ includedirsafter { "../include", "../libs", "../name with spaces" } ++ prepare() ++ xcode.XCBuildConfiguration_Project(tr, tr.configs[1]) ++ test.capture [[ ++ A14350AC4595EE5E57CE36EC /* Debug */ = { ++ isa = XCBuildConfiguration; ++ buildSettings = { ++ ARCHS = "$(NATIVE_ARCH_ACTUAL)"; ++ CONFIGURATION_BUILD_DIR = "$(SYMROOT)"; ++ CONFIGURATION_TEMP_DIR = "$(OBJROOT)"; ++ GCC_OPTIMIZATION_LEVEL = 0; ++ GCC_SYMBOLS_PRIVATE_EXTERN = NO; ++ GCC_WARN_ABOUT_RETURN_TYPE = YES; ++ GCC_WARN_UNUSED_VARIABLE = YES; ++ OBJROOT = obj/Debug; ++ ONLY_ACTIVE_ARCH = NO; ++ SYMROOT = bin/Debug; ++ SYSTEM_HEADER_SEARCH_PATHS = ( ++ ../include, ++ ../libs, ++ "\"../name with spaces\"", ++ "$(inherited)", ++ ); ++ }; ++ name = Debug; ++ }; ++ ]] ++ end ++ + function suite.XCBuildConfigurationProject_OnBuildOptions() + buildoptions { "build option 1", "build option 2" } + prepare() +diff --git a/modules/xcode/xcode_common.lua b/modules/xcode/xcode_common.lua +index bacfcabb..b08122ae 100644 +--- a/modules/xcode/xcode_common.lua ++++ b/modules/xcode/xcode_common.lua +@@ -1521,14 +1521,15 @@ + end + settings['USER_HEADER_SEARCH_PATHS'] = cfg.includedirs + +- local externalincludedirs = project.getrelative(cfg.project, cfg.externalincludedirs) +- for i,v in ipairs(externalincludedirs) do +- cfg.externalincludedirs[i] = p.quoted(v) ++ local systemincludedirs = project.getrelative(cfg.project, table.join(cfg.externalincludedirs or {}, cfg.includedirsafter or {})) ++ for i,v in ipairs(systemincludedirs) do ++ systemincludedirs[i] = p.quoted(v) + end +- if not table.isempty(cfg.externalincludedirs) then +- table.insert(cfg.externalincludedirs, "$(inherited)") ++ if not table.isempty(systemincludedirs) then ++ table.insert(systemincludedirs, "$(inherited)") + end +- settings['SYSTEM_HEADER_SEARCH_PATHS'] = cfg.externalincludedirs ++ ++ settings['SYSTEM_HEADER_SEARCH_PATHS'] = systemincludedirs + + for i,v in ipairs(cfg.libdirs) do + cfg.libdirs[i] = p.project.getrelative(cfg.project, cfg.libdirs[i]) +diff --git a/src/_premake_init.lua b/src/_premake_init.lua +index 6055eefb..df69d226 100644 +--- a/src/_premake_init.lua ++++ b/src/_premake_init.lua +@@ -1504,6 +1504,13 @@ + } + } + ++ api.register { ++ name = "includedirsafter", ++ scope = "config", ++ kind = "list:directory", ++ tokens = true ++ } ++ + api.register { -- DEPRECATED 2021-11-16 + name = "sysincludedirs", + scope = "config", +diff --git a/src/tools/clang.lua b/src/tools/clang.lua +index a9e2da54..96af8e3c 100644 +--- a/src/tools/clang.lua ++++ b/src/tools/clang.lua +@@ -186,14 +186,23 @@ + -- @param dirs + -- An array of include file search directories; as an array of + -- string values. ++-- @param extdirs ++-- An array of include file search directories for external includes; ++-- as an array of string values. ++-- @param frameworkdirs ++-- An array of file search directories for the framework includes; ++-- as an array of string vlaues ++-- @param includedirsafter ++-- An array of include file search directories for includes after system; ++-- as an array of string values. + -- @return + -- An array of symbols with the appropriate flag decorations. + -- + +- function clang.getincludedirs(cfg, dirs, extdirs, frameworkdirs) ++ function clang.getincludedirs(cfg, dirs, extdirs, frameworkdirs, includedirsafter) + + -- Just pass through to GCC for now +- local flags = gcc.getincludedirs(cfg, dirs, extdirs, frameworkdirs) ++ local flags = gcc.getincludedirs(cfg, dirs, extdirs, frameworkdirs, includedirsafter) + return flags + + end +diff --git a/src/tools/gcc.lua b/src/tools/gcc.lua +index 3aca52b2..1b2c67ea 100644 +--- a/src/tools/gcc.lua ++++ b/src/tools/gcc.lua +@@ -296,10 +296,28 @@ + + + -- +--- Decorate include file search paths for the GCC command line. ++-- Returns a list of include file search directories, decorated for ++-- the compiler command line. ++-- ++-- @param cfg ++-- The project configuration. ++-- @param dirs ++-- An array of include file search directories; as an array of ++-- string values. ++-- @param extdirs ++-- An array of include file search directories for external includes; ++-- as an array of string values. ++-- @param frameworkdirs ++-- An array of file search directories for the framework includes; ++-- as an array of string vlaues ++-- @param includedirsafter ++-- An array of include file search directories for includes after system; ++-- as an array of string values. ++-- @return ++-- An array of symbols with the appropriate flag decorations. + -- + +- function gcc.getincludedirs(cfg, dirs, extdirs, frameworkdirs) ++ function gcc.getincludedirs(cfg, dirs, extdirs, frameworkdirs, includedirsafter) + local result = {} + for _, dir in ipairs(dirs) do + dir = project.getrelative(cfg.project, dir) +@@ -318,6 +336,11 @@ + table.insert(result, '-isystem ' .. p.quoted(dir)) + end + ++ for _, dir in ipairs(includedirsafter or {}) do ++ dir = project.getrelative(cfg.project, dir) ++ table.insert(result, '-idirafter ' .. p.quoted(dir)) ++ end ++ + return result + end + +diff --git a/src/tools/msc.lua b/src/tools/msc.lua +index efff2740..2a5fe550 100644 +--- a/src/tools/msc.lua ++++ b/src/tools/msc.lua +@@ -251,7 +251,7 @@ + -- Decorate include file search paths for the MSVC command line. + -- + +- function msc.getincludedirs(cfg, dirs, extdirs, frameworkdirs) ++ function msc.getincludedirs(cfg, dirs, extdirs, frameworkdirs, includedirsafter) + local result = {} + for _, dir in ipairs(dirs) do + dir = project.getrelative(cfg.project, dir) +@@ -267,6 +267,15 @@ + end + end + ++ for _, dir in ipairs(includedirsafter or {}) do ++ dir = project.getrelative(cfg.project, dir) ++ if cfg.toolset and cfg.toolset >= "msc-v142" then ++ table.insert(result, '/external:I' .. p.quoted(dir)) ++ else ++ table.insert(result, '-I' .. p.quoted(dir)) ++ end ++ end ++ + return result + end + +diff --git a/tests/tools/test_gcc.lua b/tests/tools/test_gcc.lua +index 94b50d23..d8143eeb 100644 +--- a/tests/tools/test_gcc.lua ++++ b/tests/tools/test_gcc.lua +@@ -644,7 +644,7 @@ + includedirs { "../include", "src/include" } + externalincludedirs { "test/include" } + prepare() +- test.isequal({ '-I../include', '-Isrc/include', '-isystem test/include' }, gcc.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs)) ++ test.isequal({ '-I../include', '-Isrc/include', '-isystem test/include' }, gcc.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs, cfg.frameworkdirs, cfg.includedirsafter)) + end + + +@@ -668,16 +668,25 @@ + includedirs { "include files" } + externalincludedirs { "test include" } + prepare() +- test.isequal({ '-I"include files"', '-isystem "test include"' }, gcc.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs)) ++ test.isequal({ '-I"include files"', '-isystem "test include"' }, gcc.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs, cfg.frameworkdirs, cfg.includedirsafter)) + end + + function suite.includeDirs_onEnvVars() + includedirs { "$(IntDir)/includes" } + externalincludedirs { "$(BinDir)/include" } + prepare() +- test.isequal({ '-I"$(IntDir)/includes"', '-isystem "$(BinDir)/include"' }, gcc.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs)) ++ test.isequal({ '-I"$(IntDir)/includes"', '-isystem "$(BinDir)/include"' }, gcc.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs, cfg.frameworkdirs, cfg.includedirsafter)) + end + ++-- ++-- Include Directories After correctly take idirafter flag ++-- ++ ++ function suite.includeDirs_includeDirAfter() ++ includedirsafter { "after/path" } ++ prepare() ++ test.isequal({ '-idirafter after/path'}, gcc.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs, cfg.frameworkdirs, cfg.includedirsafter)) ++ end + + + -- +diff --git a/tests/tools/test_msc.lua b/tests/tools/test_msc.lua +index e6e6f11a..9cb0abb2 100644 +--- a/tests/tools/test_msc.lua ++++ b/tests/tools/test_msc.lua +@@ -308,6 +308,23 @@ + test.contains("/external:I/usr/local/include", msc.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs)) + end + ++-- ++-- Check handling includedirsafter. ++-- ++ ++function suite.cflags_onIncludeDirsAfter() ++ includedirsafter { "/usr/local/include" } ++ prepare() ++ test.contains("-I/usr/local/include", msc.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs, cfg.frameworkdirs, cfg.includedirsafter)) ++end ++ ++function suite.cflags_onVs2022IncludeDirsAfter() ++ p.action.set("vs2022") ++ includedirsafter { "/usr/local/include" } ++ prepare() ++ test.contains("/external:I/usr/local/include", msc.getincludedirs(cfg, cfg.includedirs, cfg.externalincludedirs, cfg.frameworkdirs, cfg.includedirsafter)) ++end ++ + + -- + -- Check handling of library search paths. +diff --git a/website/docs/Project-API.md b/website/docs/Project-API.md +index 2b456fd5..b5a29114 100644 +--- a/website/docs/Project-API.md ++++ b/website/docs/Project-API.md +@@ -108,6 +108,7 @@ + | [implibsuffix](implibsuffix.md) | | + | [include](include.md) | | + | [includedirs](includedirs.md) | | ++| [includedirsafter](includedirsafter.md) | | + | [includeexternal](includeexternal.md) | | + | [inlining](inlining.md) | Tells the compiler when it should inline functions | + | [intrinsics](intrinsics.md) | | +diff --git a/website/docs/includedirsafter.md b/website/docs/includedirsafter.md +new file mode 100644 +index 00000000..3a357e0b +--- /dev/null ++++ b/website/docs/includedirsafter.md +@@ -0,0 +1,41 @@ ++Specifies the include directories to parse last per the toolset ordering and marks the directory as an external include directory. If the exporter or toolset ++does not support include directory ordering, these directories are added to the external include directory path. ++ ++```lua ++includedirsafter { "paths" } ++``` ++ ++### Parameters ### ++ ++`paths` specifies a list of include file search directories. Paths should be specified relative to the currently running script file. Search order is evaluated from left ++to right. ++ ++### Applies To ### ++ ++Project configurations. ++ ++### Availability ### ++ ++Premake 5.0 or later. ++ ++GCC and Clang are the only toolsets supporting the ordering functionality in the gmake, gmake2 and Codelite exporters. All exporters and toolsets ++support appending the directories to the external include directories. ++ ++### Examples ### ++ ++Define two include file search paths. ++ ++```lua ++includedirsafter { "../lua/include", "../zlib" } ++``` ++ ++You can also use wildcards to match multiple directories. The * will match against a single directory, ** will recurse into subdirectories as well. ++ ++```lua ++includedirsafter { "../includes/**" } ++``` ++ ++### See Also ### ++ ++* [includedirs](includedirs.md) ++* [externalincludedirs](externalincludedirs.md) +diff --git a/website/sidebars.js b/website/sidebars.js +index 2a3699a8..c36c5be6 100644 +--- a/website/sidebars.js ++++ b/website/sidebars.js +@@ -180,6 +180,7 @@ module.exports = { + 'implibsuffix', + 'importdirs', + 'includedirs', ++ 'includedirsafter', + 'inheritdependencies', + 'inlinesvisibility', + 'inlining', +@@ -235,6 +236,7 @@ module.exports = { + 'rules', + 'runpathdirs', + 'runtime', ++ 'sanitize', + 'scanformoduledependencies', + 'shaderassembler', + 'shaderassembleroutput', +-- +2.44.2 +