• R/O
  • SSH

premake-stable: Commit

A friendly fork of Premake4 used to generate project files for WinDirStat. These patches applied for use in WinDirStat are not necessarily part of the upstream premake-stable. The WDS-build branch is the one used for the accumulated changes from all other branches. Code-signed binaries available.


Commit MetaInfo

Révisionafc0b5c48c950813225fad5b8e3b39012caedb72 (tree)
l'heure2022-03-14 07:49:34
AuteurOliver Schneider <oliver@assa...>
CommiterOliver Schneider

Message de Log

Reviewed and reworked the premake4.lua to make better use of modern VS versions

- Still sticking to VS2005 as the "default" for my release builds for now.
- The premake4 behavioral patches moved to the bottom of premake4.lua to improve

readbility (most people are stumped by seeing lots of Lua code). So since it
doesn't even matter where these go, let's place them at the bottom.

Change Summary

Modification

diff -r a6b0e342a3ac -r afc0b5c48c95 Premake4.vs8.vcproj
--- a/Premake4.vs8.vcproj Mon Feb 28 21:55:37 2022 +0000
+++ b/Premake4.vs8.vcproj Sun Mar 13 22:49:34 2022 +0000
@@ -48,7 +48,6 @@
4848 UsePrecompiledHeader="0"
4949 WarningLevel="4"
5050 Detect64BitPortabilityProblems="false"
51- ProgramDataBaseFileName="$(OutDir)\premake4.pdb"
5251 DebugInformationFormat="0"
5352 CompileAs="1"
5453 />
@@ -135,7 +134,6 @@
135134 UsePrecompiledHeader="0"
136135 WarningLevel="4"
137136 Detect64BitPortabilityProblems="false"
138- ProgramDataBaseFileName="$(OutDir)\premake4.pdb"
139137 DebugInformationFormat="4"
140138 CompileAs="1"
141139 />
@@ -157,7 +155,6 @@
157155 LinkIncremental="2"
158156 AdditionalLibraryDirectories=""
159157 GenerateDebugInformation="true"
160- ProgramDataBaseFileName="$(OutDir)\premake4.pdb"
161158 SubSystem="1"
162159 EntryPointSymbol="mainCRTStartup"
163160 TargetMachine="1"
@@ -220,7 +217,6 @@
220217 UsePrecompiledHeader="0"
221218 WarningLevel="4"
222219 Detect64BitPortabilityProblems="false"
223- ProgramDataBaseFileName="$(OutDir)\premake4.pdb"
224220 DebugInformationFormat="0"
225221 CompileAs="1"
226222 />
diff -r a6b0e342a3ac -r afc0b5c48c95 premake4.lua
--- a/premake4.lua Mon Feb 28 21:55:37 2022 +0000
+++ b/premake4.lua Sun Mar 13 22:49:34 2022 +0000
@@ -12,292 +12,20 @@
1212 ]]
1313 local action = _ACTION or ""
1414 if _OPTIONS["publish"] then
15- print "INFO: Creating 'Publish' build solution."
16- publish = true
17-end
18-do
19- -- This is mainly to support older premake4 builds
20- if not premake.project.getbasename then
21- print "Magic happens for old premake4 versions without premake.project.getbasename() ..."
22- -- override the function to establish the behavior we'd get after patching Premake to have premake.project.getbasename
23- premake.project.getbasename = function(prjname, pattern)
24- return pattern:gsub("%%%%", prjname)
25- end
26- -- obviously we also need to overwrite the following to generate functioning VS solution files
27- premake.vstudio.projectfile = function(prj)
28- local pattern
29- if prj.language == "C#" then
30- pattern = "%%.csproj"
31- else
32- pattern = iif(_ACTION > "vs2008", "%%.vcxproj", "%%.vcproj")
33- end
34-
35- local fname = premake.project.getbasename(prj.name, pattern)
36- fname = path.join(prj.location, fname)
37- return fname
38- end
39- -- we simply overwrite the original function on older Premake versions
40- premake.project.getfilename = function(prj, pattern)
41- local fname = premake.project.getbasename(prj.name, pattern)
42- fname = path.join(prj.location, fname)
43- return path.getrelative(os.getcwd(), fname)
44- end
45- end
46- -- This is mainly to support older premake4 in which CompileAs did not work
47- -- for VS2010 and newer
48- if not premake.vstudio.vc2010.individualSourceFile or not premake.vstudio.vc200x.individualSourceFile then
49- local vc2010 = premake.vstudio.vc2010
50- local vc200x = premake.vstudio.vc200x
51- local tree = premake.tree
52- print "Magic happens for old premake4 versions faulty CompileAs handling for VS2010 and newer ..."
53- -- A boilerplate implementation
54- vc200x.individualSourceFile = function(prj, depth, fname, node)
55- -- handle file configuration stuff. This needs to be cleaned up and simplified.
56- -- configurations are cached, so this isn't as bad as it looks
57- for _, cfginfo in ipairs(prj.solution.vstudio_configs) do
58- if cfginfo.isreal then
59- local cfg = premake.getconfig(prj, cfginfo.src_buildcfg, cfginfo.src_platform)
60-
61- local usePCH = (not prj.flags.NoPCH and prj.pchsource == node.cfg.name)
62- local isSourceCode = path.iscppfile(fname)
63- local needsCompileAs = (path.iscfile(fname) ~= premake.project.iscproject(prj))
64-
65- if usePCH or (isSourceCode and needsCompileAs) then
66- _p(depth, '<FileConfiguration')
67- _p(depth, '\tName="%s"', cfginfo.name)
68- _p(depth, '\t>')
69- _p(depth, '\t<Tool')
70- _p(depth, '\t\tName="%s"', iif(cfg.system == "Xbox360",
71- "VCCLX360CompilerTool",
72- "VCCLCompilerTool"))
73- if needsCompileAs then
74- _p(depth, '\t\tCompileAs="%s"', iif(path.iscfile(fname), 1, 2))
75- end
76-
77- if usePCH then
78- if cfg.system == "PS3" then
79- local options = table.join(premake.snc.getcflags(cfg),
80- premake.snc.getcxxflags(cfg),
81- cfg.buildoptions)
82- options = table.concat(options, " ");
83- options = options .. ' --create_pch="$(IntDir)/$(TargetName).pch"'
84- _p(depth, '\t\tAdditionalOptions="%s"', premake.esc(options))
85- else
86- _p(depth, '\t\tUsePrecompiledHeader="1"')
87- end
88- end
89-
90- _p(depth, '\t/>')
91- _p(depth, '</FileConfiguration>')
92- end
93-
94- end
95- end
96- end
97- vc200x.Files = function(prj)
98- local tr = premake.project.buildsourcetree(prj)
99-
100- tree.traverse(tr, {
101- -- folders are handled at the internal nodes
102- onbranchenter = function(node, depth)
103- _p(depth, '<Filter')
104- _p(depth, '\tName="%s"', node.name)
105- _p(depth, '\tFilter=""')
106- _p(depth, '\t>')
107- end,
108-
109- onbranchexit = function(node, depth)
110- _p(depth, '</Filter>')
111- end,
112-
113- -- source files are handled at the leaves
114- onleaf = function(node, depth)
115- local fname = node.cfg.name
116-
117- _p(depth, '<File')
118- _p(depth, '\tRelativePath="%s"', path.translate(fname, "\\"))
119- _p(depth, '\t>')
120- depth = depth + 1
121-
122- vc200x.individualSourceFile(prj, depth, fname, node)
123-
124- depth = depth - 1
125- _p(depth, '</File>')
126- end,
127- }, false, 2)
128-
129- end
130- -- A boilerplate implementation
131- vc2010.individualSourceFile = function(prj, config_mappings, file)
132- local configs = prj.solution.vstudio_configs
133- local translatedpath = path.translate(file.name, "\\")
134- _p(2,'<ClCompile Include=\"%s\">', translatedpath)
135- for _, cfginfo in ipairs(configs) do
136- if config_mappings[cfginfo] and translatedpath == config_mappings[cfginfo] then
137- _p(3,'<PrecompiledHeader '.. if_config_and_platform() .. '>Create</PrecompiledHeader>', premake.esc(cfginfo.name))
138- config_mappings[cfginfo] = nil --only one source file per pch
139- end
140- end
141- if path.iscfile(file.name) ~= premake.project.iscproject(prj) then
142- _p(3,'<CompileAs>%s</CompileAs>', iif(path.iscfile(file.name), 'CompileAsC', 'CompileAsCpp'))
143- end
144- _p(2,'</ClCompile>')
145- end
146- -- Overriding the function which calls the above
147- vc2010.compilerfilesgroup = function(prj)
148- local configs = prj.solution.vstudio_configs
149- local files = vc2010.getfilegroup(prj, "ClCompile")
150- if #files > 0 then
151- local config_mappings = {}
152- for _, cfginfo in ipairs(configs) do
153- local cfg = premake.getconfig(prj, cfginfo.src_buildcfg, cfginfo.src_platform)
154- if cfg.pchheader and cfg.pchsource and not cfg.flags.NoPCH then
155- config_mappings[cfginfo] = path.translate(cfg.pchsource, "\\")
156- end
157- end
158-
159- _p(1,'<ItemGroup>')
160- for _, file in ipairs(files) do
161- vc2010.individualSourceFile(prj, config_mappings, file)
162- end
163- _p(1,'</ItemGroup>')
164- end
165- end
166- end
167- -- Make UUID generation for filters deterministic
168- if os.str2uuid ~= nil then
169- local vc2010 = premake.vstudio.vc2010
170- vc2010.filteridgroup = function(prj)
171- local filters = { }
172- local filterfound = false
173-
174- for file in premake.project.eachfile(prj) do
175- -- split the path into its component parts
176- local folders = string.explode(file.vpath, "/", true)
177- local path = ""
178- for i = 1, #folders - 1 do
179- -- element is only written if there *are* filters
180- if not filterfound then
181- filterfound = true
182- _p(1,'<ItemGroup>')
183- end
184-
185- path = path .. folders[i]
186-
187- -- have I seen this path before?
188- if not filters[path] then
189- local seed = path .. (prj.uuid or "")
190- local deterministic_uuid = os.str2uuid(seed)
191- filters[path] = true
192- _p(2, '<Filter Include="%s">', path)
193- _p(3, '<UniqueIdentifier>{%s}</UniqueIdentifier>', deterministic_uuid)
194- _p(2, '</Filter>')
195- end
196-
197- -- prepare for the next subfolder
198- path = path .. "\\"
199- end
200- end
201-
202- if filterfound then
203- _p(1,'</ItemGroup>')
204- end
205- end
206- end
207- -- Name the project files after their VS version
208- local orig_getbasename = premake.project.getbasename
209- premake.project.getbasename = function(prjname, pattern)
210- -- The below is used to insert the .vs(8|9|10|11|12|14|15|16|17) into the file names for projects and solutions
211- if _ACTION then
212- name_map = {vs2005 = "vs8", vs2008 = "vs9", vs2010 = "vs10", vs2012 = "vs11", vs2013 = "vs12", vs2015 = "vs14", vs2017 = "vs15", vs2019 = "vs16", vs2022 = "vs17"}
213- if name_map[_ACTION] then
214- pattern = pattern:gsub("%%%%", "%%%%." .. name_map[_ACTION])
215- else
216- pattern = pattern:gsub("%%%%", "%%%%." .. _ACTION)
217- end
218- end
219- return orig_getbasename(prjname, pattern)
220- end
221- -- Older versions of Premake4 fail to set the proper entry point, although they could simply let it out entirely ...
222- local orig_vc2010_link = premake.vstudio.vc2010.link
223- premake.vstudio.vc2010.link = function(cfg)
224- if cfg.flags and cfg.flags.Unicode then
225- io.capture()
226- orig_vc2010_link(cfg)
227- local captured = io.endcapture()
228- captured = captured:gsub("(<EntryPointSymbol>)(mainCRTStartup)", "%1w%2")
229- io.write(captured)
230- else
231- orig_vc2010_link(cfg)
232- end
233- end
234- local orig_vc200x_VCLinkerTool = premake.vstudio.vc200x.VCLinkerTool
235- premake.vstudio.vc200x.VCLinkerTool = function(cfg)
236- if cfg.flags and cfg.flags.Unicode then
237- io.capture()
238- orig_vc200x_VCLinkerTool(cfg)
239- local captured = io.endcapture()
240- captured = captured:gsub('(EntryPointSymbol=")(mainCRTStartup)', "%1w%2")
241- io.write(captured)
242- else
243- orig_vc200x_VCLinkerTool(cfg)
244- end
245- end
246- premake.vstudio.vc200x.toolmap.VCLinkerTool = premake.vstudio.vc200x.VCLinkerTool
247- -- Make sure we can generate XP-compatible projects for newer Visual Studio versions
248- local orig_vc2010_configurationPropertyGroup = premake.vstudio.vc2010.configurationPropertyGroup
249- premake.vstudio.vc2010.configurationPropertyGroup = function(cfg, cfginfo)
250- io.capture()
251- orig_vc2010_configurationPropertyGroup(cfg, cfginfo)
252- local captured = io.endcapture()
253- local toolsets = { vs2012 = "v110", vs2013 = "v120", vs2015 = "v140", vs2017 = "v141" }
254- local toolset = toolsets[_ACTION]
255- if toolset then
256- if _OPTIONS["xp"] then
257- toolset = toolset .. "_xp"
258- captured = captured:gsub("(</PlatformToolset>)", "_xp%1")
259- end
260- end
261- io.write(captured)
262- end
263- -- Override the object directory paths ... don't make them "unique" inside premake4
264- local orig_gettarget = premake.gettarget
265- premake.gettarget = function(cfg, direction, pathstyle, namestyle, system)
266- local r = orig_gettarget(cfg, direction, pathstyle, namestyle, system)
267- if (cfg.objectsdir) and (cfg.objdir) then
268- cfg.objectsdir = cfg.objdir
269- end
270- return r
271- end
272- -- Silently suppress generation of the .user files ...
273- local orig_generate = premake.generate
274- premake.generate = function(obj, filename, callback)
275- if filename:find('.vcproj.user') or filename:find('.vcxproj.user') then
276- return
277- end
278- orig_generate(obj, filename, callback)
279- end
280- -- We want to output the file with UTF-8 BOM
281- local orig_vc2010_header = premake.vstudio.vc2010.header
282- premake.vstudio.vc2010.header = function(targets)
283- io.capture()
284- orig_vc2010_header(targets)
285- local captured = io.endcapture()
286- io.write("\239\187\191")
287- io.write(captured)
288- end
15+ print "INFO: Creating 'Publish' build solution."
16+ publish = true
28917 end
29018 local function transformMN(input) -- transform the macro names for older Visual Studio versions
291- local new_map = { vs2002 = 0, vs2003 = 0, vs2005 = 0, vs2008 = 0 }
292- local replacements = { Platform = "PlatformName", Configuration = "ConfigurationName" }
293- if new_map[action] ~= nil then
294- for k,v in pairs(replacements) do
295- if input:find(k) then
296- input = input:gsub(k, v)
297- end
298- end
299- end
300- return input
19+ local new_map = { vs2002 = 0, vs2003 = 0, vs2005 = 0, vs2008 = 0 }
20+ local replacements = { Platform = "PlatformName", Configuration = "ConfigurationName" }
21+ if new_map[action] ~= nil then
22+ for k,v in pairs(replacements) do
23+ if input:find(k) then
24+ input = input:gsub(k, v)
25+ end
26+ end
27+ end
28+ return input
30129 end
30230 --
30331 -- Define the project. Put the release configuration first so it will be the
@@ -306,82 +34,82 @@
30634 --
30735
30836 solution "Premake4"
309- configurations { "Release", "Debug", "Publish" }
310- location ( _OPTIONS["to"] )
311-
312- project "Premake4"
313- local int_dir = "intermediate/" .. action .. "_$(" .. transformMN("Platform") .. ")_$(" .. transformMN("Configuration") .. ")"
314- uuid "7F000221-EACC-2F4F-A07F-6A5D34AF10D0"
315- targetname "premake4"
316- language "C"
317- kind "ConsoleApp"
318- objdir (int_dir)
319- flags { "No64BitChecks", "ExtraWarnings", "StaticRuntime" }
320- includedirs { "src/host/lua-5.1.4/src" }
321- defines { "USE_KECCAK" }
322-
323- files
324- {
325- "*.txt", "**.lua",
326- "src/**.h", "src/**.c",
327- "src/host/scripts.c"
328- }
329-
330- excludes
331- {
332- "src/premake.lua",
333- "src/host/lua-5.1.4/src/lua.c",
334- "src/host/lua-5.1.4/src/luac.c",
335- "src/host/lua-5.1.4/src/print.c",
336- "src/host/lua-5.1.4/**.lua",
337- "src/host/lua-5.1.4/etc/*.c",
338- "src/host/hgtip.h",
339- "packages/**",
340- "samples/**",
341- "tests/**",
342- }
37+ configurations { "Release", "Debug", "Publish" }
38+ location ( _OPTIONS["to"] )
34339
344- configuration "Debug"
345- targetdir "bin/debug"
346- defines "_DEBUG"
347- flags { "Symbols" }
348-
349- configuration "Release or Publish"
350- targetdir "bin/release"
351- defines "NDEBUG"
352- flags { "OptimizeSize" }
353-
354- configuration "vs*"
355- defines { "_CRT_SECURE_NO_WARNINGS" }
356-
357- configuration "vs2005"
358- defines {"_CRT_SECURE_NO_DEPRECATE" }
359-
360- configuration "windows"
361- links { "ole32" }
362- files { "src/host/premake4.rc" }
40+ project "Premake4"
41+ local int_dir = "intermediate/" .. action .. "_$(" .. transformMN("Platform") .. ")_$(" .. transformMN("Configuration") .. ")"
42+ uuid "7F000221-EACC-2F4F-A07F-6A5D34AF10D0"
43+ targetname "premake4"
44+ language "C"
45+ kind "ConsoleApp"
46+ objdir (int_dir)
47+ flags { "No64BitChecks", "ExtraWarnings", "StaticRuntime" }
48+ includedirs { "src/host/lua-5.1.4/src" }
49+ defines { "USE_KECCAK" }
36350
364- configuration {"windows", "Publish"}
365- defines { "HAVE_HGTIP", "PREMAKE_VERSION=4.4-wds"}
366-
367- configuration "linux or bsd"
368- defines { "LUA_USE_POSIX", "LUA_USE_DLOPEN" }
369- links { "m" }
370- linkoptions { "-rdynamic" }
51+ files
52+ {
53+ "*.txt", "**.lua",
54+ "src/**.h", "src/**.c",
55+ "src/host/scripts.c"
56+ }
37157
372- configuration "linux"
373- links { "dl" }
58+ excludes
59+ {
60+ "src/premake.lua",
61+ "src/host/lua-5.1.4/src/lua.c",
62+ "src/host/lua-5.1.4/src/luac.c",
63+ "src/host/lua-5.1.4/src/print.c",
64+ "src/host/lua-5.1.4/**.lua",
65+ "src/host/lua-5.1.4/etc/*.c",
66+ "src/host/hgtip.h",
67+ "packages/**",
68+ "samples/**",
69+ "tests/**",
70+ }
37471
375- configuration "macosx"
376- defines { "LUA_USE_MACOSX" }
377- links { "CoreServices.framework" }
72+ configuration "Debug"
73+ targetdir "bin/debug"
74+ defines "_DEBUG"
75+ flags { "Symbols" }
37876
379- configuration { "macosx", "gmake" }
380- buildoptions { "-mmacosx-version-min=10.4" }
381- linkoptions { "-mmacosx-version-min=10.4" }
77+ configuration "Release or Publish"
78+ targetdir "bin/release"
79+ defines "NDEBUG"
80+ flags { "OptimizeSize" }
38281
383- configuration { "solaris" }
384- linkoptions { "-Wl,--export-dynamic" }
82+ configuration "vs*"
83+ defines { "_CRT_SECURE_NO_WARNINGS" }
84+
85+ configuration "vs2005"
86+ defines {"_CRT_SECURE_NO_DEPRECATE" }
87+
88+ configuration "windows"
89+ links { "ole32" }
90+ files { "src/host/premake4.rc" }
91+
92+ configuration {"windows", "Publish"}
93+ defines { "HAVE_HGTIP", "PREMAKE_VERSION=4.4-wds"}
94+
95+ configuration "linux or bsd"
96+ defines { "LUA_USE_POSIX", "LUA_USE_DLOPEN" }
97+ links { "m" }
98+ linkoptions { "-rdynamic" }
99+
100+ configuration "linux"
101+ links { "dl" }
102+
103+ configuration "macosx"
104+ defines { "LUA_USE_MACOSX" }
105+ links { "CoreServices.framework" }
106+
107+ configuration { "macosx", "gmake" }
108+ buildoptions { "-mmacosx-version-min=10.4" }
109+ linkoptions { "-mmacosx-version-min=10.4" }
110+
111+ configuration { "solaris" }
112+ linkoptions { "-Wl,--export-dynamic" }
385113
386114
387115
@@ -389,10 +117,10 @@
389117 -- A more thorough cleanup.
390118 --
391119
392- if _ACTION == "clean" then
393- os.rmdir("bin")
394- os.rmdir("build")
395- end
120+ if _ACTION == "clean" then
121+ os.rmdir("bin")
122+ os.rmdir("build")
123+ end
396124
397125
398126
@@ -402,15 +130,15 @@
402130 -- in preparation for deployment.
403131 --
404132
405- newoption {
406- trigger = "to",
407- value = "path",
408- description = "Set the output location for the generated files"
409- }
410- newoption {
411- trigger = "xp",
412- description = "Enable XP-compatible build for newer Visual Studio versions."
413- }
133+ newoption {
134+ trigger = "to",
135+ value = "path",
136+ description = "Set the output location for the generated files"
137+ }
138+ newoption {
139+ trigger = "xp",
140+ description = "Enable XP-compatible build for newer Visual Studio versions."
141+ }
414142
415143
416144
@@ -420,13 +148,13 @@
420148 -- a release build.
421149 --
422150
423- dofile("scripts/embed.lua")
151+ dofile("scripts/embed.lua")
424152
425- newaction {
426- trigger = "embed",
427- description = "Embed scripts in scripts.c; required before release builds",
428- execute = doembed
429- }
153+ newaction {
154+ trigger = "embed",
155+ description = "Embed scripts in scripts.c; required before release builds",
156+ execute = doembed
157+ }
430158
431159
432160 --
@@ -435,10 +163,281 @@
435163 --
436164
437165
438- dofile("scripts/release.lua")
166+ dofile("scripts/release.lua")
439167
440- newaction {
441- trigger = "release",
442- description = "Prepare a new release (incomplete)",
443- execute = dorelease
444- }
168+ newaction {
169+ trigger = "release",
170+ description = "Prepare a new release (incomplete)",
171+ execute = dorelease
172+ }
173+
174+--[[
175+ This part of the premake4.lua modifies the core premake4 behavior a little.
176+
177+ It does the following (in order of appearence below):
178+
179+ - New option --sdkver to override <WindowsTargetPlatformVersion> on modern VS
180+ - New option --clang to request ClangCL toolset on modern VS
181+ - New option --xp to request XP-compatible toolset on modern VS
182+ - On older premake4 versions it will provide a premake.project.getbasename
183+ function, furthermore two other functions get patched to make use of it
184+ - premake.project.getbasename() gets overridden to insert a marker into the
185+ created file name, based on the chosen action
186+ Example: foobar.vcxproj becomes foobar.vs2022.vcxproj etc ...
187+ The purpose of this exercise is to allow for projects/solutions of several
188+ Visual Studio versions to reside in the same folder
189+ - Options "dotnet" gets removed
190+ - The "platform" option has some allowed values removed
191+ - The "os" option has some allowed values removed
192+ - The actions are trimmed to what we know can work
193+]]
194+
195+newoption { trigger = "sdkver", value = "SDKVER", description = "Allows to override SDK version (VS2015 through VS2022)" }
196+newoption { trigger = "clang", description = "Allows to use clang-cl as compiler and lld-link as linker (VS2019 and VS2022)" }
197+newoption { trigger = "xp", description = "Allows to use a supported XP toolset for some VS versions" }
198+
199+do
200+ -- This is mainly to support older premake4 builds
201+ if not premake.project.getbasename then
202+ print "Magic happens for old premake4 versions without premake.project.getbasename() ..."
203+ -- override the function to establish the behavior we'd get after patching Premake to have premake.project.getbasename
204+ premake.project.getbasename = function(prjname, pattern)
205+ return pattern:gsub("%%%%", prjname)
206+ end
207+ -- obviously we also need to overwrite the following to generate functioning VS solution files
208+ premake.vstudio.projectfile = function(prj)
209+ local pattern
210+ if prj.language == "C#" then
211+ pattern = "%%.csproj"
212+ else
213+ pattern = iif(_ACTION > "vs2008", "%%.vcxproj", "%%.vcproj")
214+ end
215+
216+ local fname = premake.project.getbasename(prj.name, pattern)
217+ fname = path.join(prj.location, fname)
218+ return fname
219+ end
220+ -- we simply overwrite the original function on older Premake versions
221+ premake.project.getfilename = function(prj, pattern)
222+ local fname = premake.project.getbasename(prj.name, pattern)
223+ fname = path.join(prj.location, fname)
224+ return path.getrelative(os.getcwd(), fname)
225+ end
226+ end
227+ -- Make UUID generation for filters deterministic
228+ if os.str2uuid ~= nil then
229+ local vc2010 = premake.vstudio.vc2010
230+ vc2010.filteridgroup = function(prj)
231+ local filters = { }
232+ local filterfound = false
233+
234+ for file in premake.project.eachfile(prj) do
235+ -- split the path into its component parts
236+ local folders = string.explode(file.vpath, "/", true)
237+ local path = ""
238+ for i = 1, #folders - 1 do
239+ -- element is only written if there *are* filters
240+ if not filterfound then
241+ filterfound = true
242+ _p(1,"<ItemGroup>")
243+ end
244+
245+ path = path .. folders[i]
246+
247+ -- have I seen this path before?
248+ if not filters[path] then
249+ local seed = path .. (prj.uuid or "")
250+ local deterministic_uuid = os.str2uuid(seed)
251+ filters[path] = true
252+ _p(2, '<Filter Include="%s">', path)
253+ _p(3, "<UniqueIdentifier>{%s}</UniqueIdentifier>", deterministic_uuid)
254+ _p(2, "</Filter>")
255+ end
256+
257+ -- prepare for the next subfolder
258+ path = path .. "\\"
259+ end
260+ end
261+
262+ if filterfound then
263+ _p(1,"</ItemGroup>")
264+ end
265+ end
266+ end
267+ -- Name the project files after their VS version
268+ local orig_getbasename = premake.project.getbasename
269+ premake.project.getbasename = function(prjname, pattern)
270+ -- The below is used to insert the .vs(8|9|10|11|12|14|15|16|17) into the file names for projects and solutions
271+ if _ACTION then
272+ name_map = {vs2005 = "vs8", vs2008 = "vs9", vs2010 = "vs10", vs2012 = "vs11", vs2013 = "vs12", vs2015 = "vs14", vs2017 = "vs15", vs2019 = "vs16", vs2022 = "vs17"}
273+ if name_map[_ACTION] then
274+ pattern = pattern:gsub("%%%%", "%%%%." .. name_map[_ACTION])
275+ else
276+ pattern = pattern:gsub("%%%%", "%%%%." .. _ACTION)
277+ end
278+ end
279+ return orig_getbasename(prjname, pattern)
280+ end
281+ -- Premake4 sets the PDB file name for the compiler's PDB to the default
282+ -- value used by the linker's PDB. This causes error C1052 on VS2017. Fix it.
283+ -- But this also fixes up certain other areas of the generated project. The idea
284+ -- here is to catch the original _p() invocations, evaluate the arguments and
285+ -- then act based on those, using orig_p() as a standin during a call to the
286+ -- underlying premake.vs2010_vcxproj() function ;-)
287+ local orig_premake_vs2010_vcxproj = premake.vs2010_vcxproj
288+ premake.vs2010_vcxproj = function(prj)
289+ -- The whole stunt below is necessary in order to modify the resource_compile()
290+ -- output. Given it's a local function we have to go through hoops.
291+ local orig_p = _G._p
292+ local besilent = false
293+ -- We patch the global _p() function
294+ _G._p = function(indent, msg, first, ...)
295+ -- Look for non-empty messages and narrow it down by the indent values
296+ if msg ~= nil then
297+ if msg:match("<ProgramDataBaseFileName>[^<]+</ProgramDataBaseFileName>") then
298+ return -- we want to suppress these
299+ end
300+ if indent == 2 then
301+ if msg == '<ClCompile Include=\"%s\">' and first == "delayload-stubs\\ntdll-delayed-stubs.c" then
302+ orig_p(indent, msg, first, ...) -- what was originally supposed to be output
303+ orig_p(indent+1, "<ExcludedFromBuild>true</ExcludedFromBuild>")
304+ return
305+ end
306+ if msg == "<RootNamespace>%s</RootNamespace>" then
307+ local sdkmap = {vs2015 = "8.1", vs2017 = "10.0.17763.0", vs2019 = "10.0", vs2022 = "10.0"}
308+ if (not _ACTION) or (not sdkmap[_ACTION]) then -- should not happen, but tread carefully anyway
309+ orig_p(indent, msg, first, ...) -- what was originally supposed to be output
310+ return
311+ end
312+ local sdkver = _OPTIONS["sdkver"] or sdkmap[_ACTION]
313+ orig_p(indent, msg, first, ...) -- what was originally supposed to be output
314+ orig_p(indent, "<WindowsTargetPlatformVersion>%s</WindowsTargetPlatformVersion>", sdkver)
315+ return
316+ end
317+ if msg == "<PlatformToolset>%s</PlatformToolset>" then
318+ if (_OPTIONS["clang"] ~= nil) and (_ACTION == "vs2017") then
319+ if _OPTIONS["xp"] ~= nil then
320+ print "WARNING: The --clang option takes precedence over --xp, therefore picking v141_clang_c2 toolset."
321+ end
322+ print "WARNING: If you are used to Clang support from VS2019 and newer, be sure to review your choice. It's not the same on older VS versions."
323+ orig_p(indent, msg, "v141_clang_c2")
324+ return
325+ elseif (_OPTIONS["clang"] ~= nil) and (_ACTION >= "vs2019") then
326+ if _OPTIONS["xp"] ~= nil then
327+ print "WARNING: The --clang option takes precedence over --xp, therefore picking ClangCL toolset."
328+ end
329+ orig_p(indent, msg, "ClangCL")
330+ return
331+ elseif _OPTIONS["xp"] ~= nil then
332+ local toolsets = { vs2012 = "v110", vs2013 = "v120", vs2015 = "v140", vs2017 = "v141", vs2019 = "v142", vs2022 = "v143" }
333+ local toolset = toolsets[_ACTION]
334+ if toolset then
335+ if _OPTIONS["xp"] and toolset >= "v141" then
336+ toolset = "v141" -- everything falls back to the VS2017 XP toolset for more recent VS
337+ end
338+ orig_p(indent,"<PlatformToolset>%s_xp</PlatformToolset>", toolset)
339+ return
340+ end
341+ end
342+ end
343+ elseif indent == 3 then
344+ -- This is what vanilla VS would output it as, so let's try to align with that
345+ if msg == "<PrecompiledHeader></PrecompiledHeader>" then
346+ orig_p(indent, "<PrecompiledHeader>")
347+ orig_p(indent, "</PrecompiledHeader>")
348+ return
349+ end
350+ end
351+ end
352+ if not besilent then -- should we be silent (i.e. suppress default output)?
353+ orig_p(indent, msg, first, ...)
354+ end
355+ end
356+ orig_premake_vs2010_vcxproj(prj)
357+ _G._p = orig_p -- restore in any case
358+ end
359+ -- ... same as above but for VS200x this time
360+ local function wrap_remove_pdb_attribute(origfunc)
361+ local fct = function(cfg)
362+ local old_captured = io.captured -- save io.captured state
363+ io.capture() -- this sets io.captured = ""
364+ origfunc(cfg)
365+ local captured = io.endcapture()
366+ assert(captured ~= nil)
367+ captured = captured:gsub('%s+ProgramDataBaseFileName=\"[^"]+\"', "")
368+ if old_captured ~= nil then
369+ io.captured = old_captured .. captured -- restore outer captured state, if any
370+ else
371+ io.write(captured)
372+ end
373+ end
374+ return fct
375+ end
376+ premake.vstudio.vc200x.VCLinkerTool = wrap_remove_pdb_attribute(premake.vstudio.vc200x.VCLinkerTool)
377+ premake.vstudio.vc200x.toolmap.VCLinkerTool = premake.vstudio.vc200x.VCLinkerTool -- this is important as well
378+ premake.vstudio.vc200x.VCCLCompilerTool = wrap_remove_pdb_attribute(premake.vstudio.vc200x.VCCLCompilerTool)
379+ premake.vstudio.vc200x.toolmap.VCCLCompilerTool = premake.vstudio.vc200x.VCCLCompilerTool -- this is important as well
380+ -- Override the object directory paths ... don't make them "unique" inside premake4
381+ local orig_gettarget = premake.gettarget
382+ premake.gettarget = function(cfg, direction, pathstyle, namestyle, system)
383+ local r = orig_gettarget(cfg, direction, pathstyle, namestyle, system)
384+ if (cfg.objectsdir) and (cfg.objdir) then
385+ cfg.objectsdir = cfg.objdir
386+ end
387+ return r
388+ end
389+ -- Silently suppress generation of the .user files ...
390+ local orig_generate = premake.generate
391+ premake.generate = function(obj, filename, callback)
392+ if filename:find(".vcproj.user") or filename:find(".vcxproj.user") then
393+ return
394+ end
395+ orig_generate(obj, filename, callback)
396+ end
397+ -- Fix up premake.getlinks() to not do stupid stuff with object files we pass
398+ local orig_premake_getlinks = premake.getlinks
399+ premake.getlinks = function(cfg, kind, part)
400+ local origret = orig_premake_getlinks(cfg, kind, part)
401+ local ret = {}
402+ for k,v in ipairs(origret) do
403+ local dep = v:gsub(".obj.lib", ".obj")
404+ dep = dep:gsub(".lib.lib", ".lib")
405+ table.insert(ret, dep)
406+ end
407+ return ret
408+ end
409+
410+ -- Remove an option altogether or some otherwise accepted values for that option
411+ local function remove_allowed_optionvalues(option, values_toremove)
412+ if premake.option.list[option] ~= nil then
413+ if values_toremove == nil then
414+ premake.option.list[option] = nil
415+ return
416+ end
417+ if premake.option.list.platform["allowed"] ~= nil then
418+ local allowed = premake.option.list[option].allowed
419+ for i = #allowed, 1, -1 do
420+ if values_toremove[allowed[i][1]] then
421+ table.remove(allowed, i)
422+ end
423+ end
424+ end
425+ end
426+ end
427+
428+ local function remove_action(action)
429+ if premake.action.list[action] ~= nil then
430+ premake.action.list[action] = nil
431+ end
432+ end
433+
434+ -- Remove some unwanted/outdated options
435+ remove_allowed_optionvalues("dotnet")
436+ remove_allowed_optionvalues("platform", { universal = 0, universal32 = 0, universal64 = 0, ps3 = 0, xbox360 = 0, })
437+ remove_allowed_optionvalues("os") -- ... , { bsd = 0, haiku = 0, linux = 0, macosx = 0, solaris = 0, }
438+ remove_allowed_optionvalues("cc")
439+ -- ... and actions (mainly because they are untested)
440+ for k,v in pairs({codeblocks = 0, codelite = 0, xcode3 = 0, xcode4 = 0, vs2002 = 0, vs2003 = 0, }) do -- vs2005 = 0, vs2008 = 0, vs2010 = 0, vs2012 = 0, vs2013 = 0
441+ remove_action(k)
442+ end
443+end
Afficher sur ancien navigateur de dépôt.