1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
|
---
-- Create a source or binary release package.
---
---
-- Helper function: run a command while hiding its output.
---
local function execQuiet(cmd, ...)
cmd = string.format(cmd, ...) .. " > _output_.log 2> _error_.log"
local z = os.execute(cmd)
os.remove("_output_.log")
os.remove("_error_.log")
return z
end
---
-- Check the command line arguments, and show some help if needed.
---
local allowedCompilers = {}
if os.ishost("windows") then
allowedCompilers = {
"vs2019",
"vs2017",
"vs2015",
"vs2013",
"vs2012",
"vs2010",
"vs2008",
"vs2005",
}
elseif os.ishost("linux") or os.ishost("bsd") then
allowedCompilers = {
"gcc",
"clang",
}
elseif os.ishost("macosx") then
allowedCompilers = {
"clang",
}
else
error("Unsupported host os", 0)
end
local usage = 'usage is: package <branch> <type> [<compiler>]\n' ..
' <branch> is the name of the release branch to target\n' ..
' <type> is one of "source" or "binary"\n' ..
' <compiler> (default: ' .. allowedCompilers[1] .. ') is one of ' .. table.implode(allowedCompilers, "", "", " ")
if #_ARGS ~= 2 and #_ARGS ~= 3 then
error(usage, 0)
end
local branch = _ARGS[1]
local kind = _ARGS[2]
local compiler = _ARGS[3] or allowedCompilers[1]
if kind ~= "source" and kind ~= "binary" then
print("Invalid package kind: "..kind)
error(usage, 0)
end
if not table.contains(allowedCompilers, compiler) then
print("Invalid compiler: "..compiler)
error(usage, 0)
end
local compilerIsVS = compiler:startswith("vs")
--
-- Make sure I've got what I've need to be happy.
--
local required = { "git" }
if not compilerIsVS then
table.insert(required, "make")
table.insert(required, compiler)
end
for _, value in ipairs(required) do
local z = execQuiet("%s --version", value)
if not z then
error("required tool '" .. value .. "' not found", 0)
end
end
--
-- Figure out what I'm making.
--
os.chdir("..")
local text = os.outputof(string.format('git show %s:src/host/premake.h', branch))
local _, _, version = text:find('VERSION%s*"([%w%p]+)"')
local pkgName = "premake-" .. version
local pkgExt = ".zip"
if kind == "binary" then
pkgName = pkgName .. "-" .. os.host()
if not os.istarget("windows") then
pkgExt = ".tar.gz"
end
else
pkgName = pkgName .. "-src"
end
--
-- Make sure I'm sure.
--
printf("")
printf("I am about to create a %s package", kind:upper())
printf(" ...named release/%s%s", pkgName, pkgExt)
printf(" ...from the %s branch", branch)
printf("")
printf("Does this look right to you? If so, press [Enter] to begin.")
io.read()
--
-- Pull down the release branch.
--
print("Preparing release folder")
os.mkdir("release")
os.chdir("release")
os.rmdir(pkgName)
print("Cloning source code")
local z = execQuiet("git clone .. %s -b %s --recurse-submodules --depth 1 --shallow-submodules", pkgName, branch)
if not z then
error("clone failed", 0)
end
os.chdir(pkgName)
--
-- Bootstrap Premake in the newly cloned repository
--
print("Bootstrapping Premake...")
if compilerIsVS then
z = os.execute("Bootstrap.bat " .. compiler)
else
z = os.execute("make -j -f Bootstrap.mak " .. os.host())
end
if not z then
error("Failed to Bootstrap Premake", 0)
end
local premakeBin = path.translate("./bin/release/premake5")
--
-- Make absolutely sure the embedded scripts have been updated
--
print("Updating embedded scripts...")
local z = execQuiet("%s embed %s", premakeBin, iif(kind == "source", "", "--bytecode"))
if not z then
error("failed to update the embedded scripts", 0)
end
--
-- Generate a source package.
--
if kind == "source" then
local function genProjects(parameters)
if not execQuiet("%s %s", premakeBin, parameters) then
error("failed to generate project for "..parameters, 0)
end
end
os.rmdir("build")
print("Generating project files...")
local ignoreActions = {
"clean",
"embed",
"package",
"self-test",
"test",
"gmake", -- deprecated
}
local perOSActions = {
"gmake2",
"codelite"
}
for action in premake.action.each() do
if not table.contains(ignoreActions, action.trigger) then
if table.contains(perOSActions, action.trigger) then
local osList = {
{ "windows", },
{ "unix", "linux" },
{ "macosx", },
{ "bsd", },
}
for _, os in ipairs(osList) do
local osTarget = os[2] or os[1]
genProjects(string.format("--to=build/%s.%s --os=%s %s", action.trigger, os[1], osTarget, action.trigger))
end
else
genProjects(string.format("--to=build/%s %s", action.trigger, action.trigger))
end
end
end
print("Creating source code package...")
local excludeList = {
".gitignore",
".gitattributes",
".gitmodules",
".travis.yml",
".editorconfig",
"appveyor.yml",
"Bootstrap.*",
"packages/*",
}
local includeList = {
"build",
"src/scripts.c",
}
if not execQuiet("git rm --cached -r -f --ignore-unmatch "..table.concat(excludeList, ' ')) or
not execQuiet("git add -f "..table.concat(includeList, ' ')) or
not execQuiet("git stash") or
not execQuiet("git archive --format=zip -9 -o ../%s.zip --prefix=%s/ stash@{0}", pkgName, pkgName) or
not execQuiet("git stash drop stash@{0}")
then
error("failed to archive release", 0)
end
os.chdir("..")
end
--
-- Create a binary package for this platform. This step requires a working
-- GNU/Make/GCC environment.
--
if kind == "binary" then
print("Building binary...")
os.chdir("bin/release")
local addCommand = "git add -f premake5%s"
local archiveCommand = "git archive --format=%s -o ../../../%s%s stash@{0} -- ./premake5%s"
if os.ishost("windows") then
addCommand = string.format(addCommand, ".exe")
archiveCommand = string.format(archiveCommand, "zip -9", pkgName, pkgExt, ".exe")
else
addCommand = string.format(addCommand, "")
archiveCommand = string.format(archiveCommand, "tar.gz", pkgName, pkgExt, "")
end
if not execQuiet(addCommand) or
not execQuiet("git stash") or
not execQuiet(archiveCommand) or
not execQuiet("git stash drop stash@{0}")
then
error("failed to archive release", 0)
end
os.chdir("../../..")
end
--
-- Clean up
--
-- Use RMDIR token instead of os.rmdir to force remove .git dir which has read only files
execQuiet(os.translateCommands("{RMDIR} "..pkgName))
|