source: Jenkinsfile@ c4072d8e

ADT ast-experimental pthread-emulation qualifiedEnum
Last change on this file since c4072d8e was 4f3807d, checked in by Thierry Delisle <tdelisle@…>, 3 years ago

Removed jenkins performance plots since they were not very useful

  • Property mode set to 100644
File size: 13.5 KB
Line 
1#!groovy
2
3import groovy.transform.Field
4
5//===========================================================================================================
6// Main loop of the compilation
7//===========================================================================================================
8
9// Globals
10BuildDir = null
11SrcDir = null
12Settings = null
13Tools = null
14
15// Local variables
16def err = null
17def log_needed = false
18
19currentBuild.result = "SUCCESS"
20
21try {
22 node {
23 //Wrap build to add timestamp to command line
24 wrap([$class: 'TimestamperBuildWrapper']) {
25 Settings = prepare_build()
26 }
27 }
28
29 node(Settings.Architecture.node) {
30 //Wrap build to add timestamp to command line
31 wrap([$class: 'TimestamperBuildWrapper']) {
32 BuildDir = pwd tmp: true
33 SrcDir = pwd tmp: false
34 currentBuild.description = "${currentBuild.description} on ${env.NODE_NAME}"
35
36 Tools.Clean()
37
38 Tools.Checkout()
39
40 build()
41
42 test()
43
44 benchmark()
45
46 build_doc()
47
48 publish()
49 }
50 }
51}
52
53//If an exception is caught we need to change the status and remember to
54//attach the build log to the email
55catch (Exception caughtError) {
56 // Store the result of the build log
57 currentBuild.result = "FAILURE"
58
59 // An error has occured, the build log is relevent
60 log_needed = true
61
62 // rethrow error later
63 err = caughtError
64
65 // print the error so it shows in the log
66 echo err.toString()
67}
68
69finally {
70 //Send email with final results if this is not a full build
71 email(log_needed)
72
73 echo 'Build Completed'
74
75 /* Must re-throw exception to propagate error */
76 if (err) {
77 throw err
78 }
79}
80//===========================================================================================================
81// Main compilation routines
82//===========================================================================================================
83def build() {
84 debug = true
85 release = Settings.RunAllTests || Settings.RunBenchmark
86 Tools.BuildStage('Build : configure', true) {
87 // Configure must be run inside the tree
88 dir (SrcDir) {
89 // Generate the necessary build files
90 sh './autogen.sh'
91 }
92
93 // Build outside of the src tree to ease cleaning
94 dir (BuildDir) {
95 //Configure the compilation (Output is not relevant)
96 //Use the current directory as the installation target so nothing escapes the sandbox
97 //Also specify the compiler by hand
98 targets=""
99 if( Settings.RunAllTests || Settings.RunBenchmark ) {
100 targets="--with-target-hosts='host:debug,host:nodebug'"
101 } else {
102 targets="--with-target-hosts='host:debug'"
103 }
104
105 ast = Settings.NewAST ? "--enable-new-ast" : "--disable-new-ast"
106
107 sh "${SrcDir}/configure CXX=${Settings.Compiler.CXX} CC=${Settings.Compiler.CC} ${Settings.Architecture.flags} AR=gcc-ar RANLIB=gcc-ranlib ${targets} ${ast} --quiet --prefix=${BuildDir}"
108
109 // Configure libcfa
110 sh 'make -j $(nproc) --no-print-directory configure-libcfa'
111 }
112 }
113
114 Tools.BuildStage('Build : cfa-cpp', true) {
115 // Build outside of the src tree to ease cleaning
116 dir (BuildDir) {
117 // Build driver
118 sh 'make -j $(nproc) --no-print-directory -C driver'
119
120 // Build translator
121 sh 'make -j $(nproc) --no-print-directory -C src'
122 }
123 }
124
125 Tools.BuildStage('Build : libcfa(debug)', debug) {
126 // Build outside of the src tree to ease cleaning
127 dir (BuildDir) {
128 sh "make -j \$(nproc) --no-print-directory -C libcfa/${Settings.Architecture.name}-debug"
129 }
130 }
131
132 Tools.BuildStage('Build : libcfa(nodebug)', release) {
133 // Build outside of the src tree to ease cleaning
134 dir (BuildDir) {
135 sh "make -j \$(nproc) --no-print-directory -C libcfa/${Settings.Architecture.name}-nodebug"
136 }
137 }
138
139 Tools.BuildStage('Build : install', true) {
140 // Build outside of the src tree to ease cleaning
141 dir (BuildDir) {
142 sh 'make -j $(nproc) --no-print-directory install'
143 }
144 }
145}
146
147def test() {
148 try {
149 // Print potential limits before testing
150 // in case jenkins messes with them
151 sh 'free -h'
152 sh 'ulimit -a'
153
154 Tools.BuildStage('Test: short', !Settings.RunAllTests) {
155 dir (BuildDir) {
156 //Run the tests from the tests directory
157 sh "make --no-print-directory -C tests archiveerrors=${BuildDir}/tests/crashes/short"
158 }
159 }
160
161 Tools.BuildStage('Test: full', Settings.RunAllTests) {
162 dir (BuildDir) {
163 jopt = '-j $(nproc)'
164 if( Settings.Architecture.node == 'x86' ) {
165 jopt = '-j2'
166 }
167 //Run the tests from the tests directory
168 sh """make ${jopt} --no-print-directory -C tests timeouts="--timeout=600 --global-timeout=14400" all-tests debug=yes archiveerrors=${BuildDir}/tests/crashes/full-debug"""
169 sh """make ${jopt} --no-print-directory -C tests timeouts="--timeout=600 --global-timeout=14400" all-tests debug=no archiveerrors=${BuildDir}/tests/crashes/full-nodebug"""
170 }
171 }
172 }
173 catch (Exception err) {
174 echo "Archiving core dumps"
175 dir (BuildDir) {
176 def exists = fileExists 'tests/crashes'
177 if( exists ) {
178 sh """${SrcDir}/tools/jenkins/archive-gen.sh"""
179 archiveArtifacts artifacts: "tests/crashes/**/*,lib/**/lib*.so*,setup.sh", fingerprint: true
180 }
181 }
182 throw err
183 }
184}
185
186def benchmark() {
187 Tools.BuildStage('Benchmark', Settings.RunBenchmark) {
188 dir (BuildDir) {
189 //Append bench results
190 sh "make --no-print-directory -C benchmark jenkins arch=${Settings.Architecture.name}"
191 }
192 }
193}
194
195def build_doc() {
196 Tools.BuildStage('Documentation', Settings.BuildDocumentation) {
197 dir ('doc/user') {
198 make_doc()
199 }
200
201 dir ('doc/refrat') {
202 make_doc()
203 }
204 }
205}
206
207def publish() {
208 Tools.BuildStage('Publish', true) {
209
210 if( Settings.Publish && !Settings.RunBenchmark ) { echo 'No results to publish!!!' }
211 }
212}
213
214//===========================================================================================================
215//Routine responsible of sending the email notification once the build is completed
216//===========================================================================================================
217//Standard build email notification
218def email(boolean log) {
219 node {
220 //Since tokenizer doesn't work, figure stuff out from the environnement variables and command line
221 //Configurations for email format
222 echo 'Notifying users of result'
223
224 def project_name = (env.JOB_NAME =~ /(.+)\/.+/)[0][1].toLowerCase()
225 def email_subject = "[${project_name} git][BUILD# ${env.BUILD_NUMBER} - ${currentBuild.result}] - branch ${env.BRANCH_NAME}"
226 def email_body = """<p>This is an automated email from the Jenkins build machine. It was
227generated because of a git hooks/post-receive script following
228a ref change which was pushed to the C\u2200 repository.</p>
229
230<p>- Status --------------------------------------------------------------</p>
231
232<p>BUILD# ${env.BUILD_NUMBER} - ${currentBuild.result}</p>
233<p>Check console output at ${env.BUILD_URL} to view the results.</p>
234""" + Tools.GitLogMessage()
235
236 def email_to = !Settings.IsSandbox ? "cforall@lists.uwaterloo.ca" : "tdelisle@uwaterloo.ca"
237
238 if( Settings && !Settings.Silent ) {
239 //send email notification
240 emailext body: email_body, subject: email_subject, to: email_to, attachLog: log
241 } else {
242 echo "Would send email to: ${email_to}"
243 echo "With title: ${email_subject}"
244 echo "Content: \n${email_body}"
245 }
246 }
247}
248
249//===========================================================================================================
250// Helper classes/variables/routines
251//===========================================================================================================
252//Description of a compiler (Must be serializable since pipelines are persistent)
253class CC_Desc implements Serializable {
254 public String name
255 public String CXX
256 public String CC
257 public String lto
258
259 CC_Desc(String name, String CXX, String CC, String lto) {
260 this.name = name
261 this.CXX = CXX
262 this.CC = CC
263 this.lto = lto
264 }
265}
266
267//Description of an architecture (Must be serializable since pipelines are persistent)
268class Arch_Desc implements Serializable {
269 public String name
270 public String flags
271 public String node
272
273 Arch_Desc(String name, String flags, String node) {
274 this.name = name
275 this.flags = flags
276 this.node = node
277 }
278}
279
280class BuildSettings implements Serializable {
281 public final CC_Desc Compiler
282 public final Arch_Desc Architecture
283 public final Boolean NewAST
284 public final Boolean RunAllTests
285 public final Boolean RunBenchmark
286 public final Boolean BuildDocumentation
287 public final Boolean Publish
288 public final Boolean Silent
289 public final Boolean IsSandbox
290 public final String DescLong
291 public final String DescShort
292
293 public String GitNewRef
294 public String GitOldRef
295
296 BuildSettings(java.util.Collections$UnmodifiableMap param, String branch) {
297 switch( param.Compiler ) {
298 case 'gcc-11':
299 this.Compiler = new CC_Desc('gcc-11', 'g++-11', 'gcc-11', '-flto=auto')
300 break
301 case 'gcc-10':
302 this.Compiler = new CC_Desc('gcc-10', 'g++-10', 'gcc-10', '-flto=auto')
303 break
304 case 'gcc-9':
305 this.Compiler = new CC_Desc('gcc-9', 'g++-9', 'gcc-9', '-flto=auto')
306 break
307 case 'gcc-8':
308 this.Compiler = new CC_Desc('gcc-8', 'g++-8', 'gcc-8', '-flto=auto')
309 break
310 case 'gcc-7':
311 this.Compiler = new CC_Desc('gcc-7', 'g++-7', 'gcc-7', '-flto=auto')
312 break
313 case 'gcc-6':
314 this.Compiler = new CC_Desc('gcc-6', 'g++-6', 'gcc-6', '-flto=auto')
315 break
316 case 'gcc-5':
317 this.Compiler = new CC_Desc('gcc-5', 'g++-5', 'gcc-5', '-flto=auto')
318 break
319 case 'gcc-4.9':
320 this.Compiler = new CC_Desc('gcc-4.9', 'g++-4.9', 'gcc-4.9', '-flto=auto')
321 break
322 case 'clang':
323 this.Compiler = new CC_Desc('clang', 'clang++-10', 'gcc-10', '-flto=thin -flto-jobs=0')
324 break
325 default :
326 error "Unhandled compiler : ${cc}"
327 }
328
329 switch( param.Architecture ) {
330 case 'x64':
331 this.Architecture = new Arch_Desc('x64', '--host=x86_64', 'x64')
332 break
333 case 'x86':
334 this.Architecture = new Arch_Desc('x86', '--host=i386', 'x86')
335 break
336 default :
337 error "Unhandled architecture : ${arch}"
338 }
339
340 this.IsSandbox = (branch == "jenkins-sandbox")
341 this.NewAST = param.NewAST
342 this.RunAllTests = param.RunAllTests
343 this.RunBenchmark = param.RunBenchmark
344 this.BuildDocumentation = param.BuildDocumentation
345 this.Publish = param.Publish
346 this.Silent = param.Silent
347
348 def full = param.RunAllTests ? " (Full)" : ""
349 this.DescShort = "${ this.Compiler.name }:${ this.Architecture.name }${full}"
350
351 final ast = this.NewAST ? "New AST" : "Old AST"
352 this.DescLong = """Compiler : ${ this.Compiler.name } (${ this.Compiler.CXX }/${ this.Compiler.CC })
353AST Version : ${ ast.toString() }
354Architecture : ${ this.Architecture.name }
355Arc Flags : ${ this.Architecture.flags }
356Run All Tests : ${ this.RunAllTests.toString() }
357Run Benchmark : ${ this.RunBenchmark.toString() }
358Build Documentation : ${ this.BuildDocumentation.toString() }
359Publish : ${ this.Publish.toString() }
360Silent : ${ this.Silent.toString() }
361"""
362
363 this.GitNewRef = ''
364 this.GitOldRef = ''
365 }
366}
367
368def prepare_build() {
369 // prepare the properties
370 properties ([ \
371 buildDiscarder(logRotator( \
372 artifactDaysToKeepStr: '', \
373 artifactNumToKeepStr: '', \
374 daysToKeepStr: '730', \
375 numToKeepStr: '1000' \
376 )), \
377 [$class: 'ParametersDefinitionProperty', \
378 parameterDefinitions: [ \
379 [$class: 'ChoiceParameterDefinition', \
380 description: 'Which compiler to use', \
381 name: 'Compiler', \
382 choices: 'gcc-11\ngcc-10\ngcc-9\ngcc-8\ngcc-7\ngcc-6\ngcc-5\ngcc-4.9\nclang', \
383 defaultValue: 'gcc-8', \
384 ], \
385 [$class: 'ChoiceParameterDefinition', \
386 description: 'The target architecture', \
387 name: 'Architecture', \
388 choices: 'x64\nx86', \
389 defaultValue: 'x64', \
390 ], \
391 [$class: 'BooleanParameterDefinition', \
392 description: 'If true, build compiler using new AST', \
393 name: 'NewAST', \
394 defaultValue: true, \
395 ], \
396 [$class: 'BooleanParameterDefinition', \
397 description: 'If false, only the quick test suite is ran', \
398 name: 'RunAllTests', \
399 defaultValue: false, \
400 ], \
401 [$class: 'BooleanParameterDefinition', \
402 description: 'If true, jenkins also runs benchmarks', \
403 name: 'RunBenchmark', \
404 defaultValue: false, \
405 ], \
406 [$class: 'BooleanParameterDefinition', \
407 description: 'If true, jenkins also builds documentation', \
408 name: 'BuildDocumentation', \
409 defaultValue: true, \
410 ], \
411 [$class: 'BooleanParameterDefinition', \
412 description: 'If true, jenkins also publishes results', \
413 name: 'Publish', \
414 defaultValue: false, \
415 ], \
416 [$class: 'BooleanParameterDefinition', \
417 description: 'If true, jenkins will not send emails', \
418 name: 'Silent', \
419 defaultValue: false, \
420 ], \
421 ],
422 ]])
423
424 // It's unfortunate but it looks like we need to checkout the entire repo just to get
425 // - the pretty git printer
426 // - Jenkins.tools
427 checkout scm
428
429 Tools = load "Jenkins/tools.groovy"
430
431 final settings = new BuildSettings(params, env.BRANCH_NAME)
432
433 currentBuild.description = settings.DescShort
434 echo settings.DescLong
435
436 return settings
437}
438
439def make_doc() {
440 def err = null
441 try {
442 sh 'make clean > /dev/null'
443 sh 'make > /dev/null 2>&1'
444 }
445 catch (Exception caughtError) {
446 err = caughtError //rethrow error later
447 sh 'cat build/*.log'
448 }
449 finally {
450 if (err) throw err // Must re-throw exception to propagate error
451 }
452}
Note: See TracBrowser for help on using the repository browser.