blob: 8f4810bc3efbf940b735d19ad8426ae4cd741e84 [file] [log] [blame]
Tom Rini83d290c2018-05-06 17:58:06 -04001# SPDX-License-Identifier: GPL-2.0+
Simon Glassfc3fe1c2013-04-03 11:07:16 +00002# Copyright (c) 2013 The Chromium OS Authors.
3#
Simon Glassfc3fe1c2013-04-03 11:07:16 +00004
5import multiprocessing
6import os
Simon Glass883a3212014-09-05 19:00:18 -06007import shutil
Simon Glass0ede00f2020-04-17 18:09:02 -06008import subprocess
Simon Glassfc3fe1c2013-04-03 11:07:16 +00009import sys
10
Simon Glass0ede00f2020-04-17 18:09:02 -060011from buildman import board
12from buildman import bsettings
Simon Glass2b4806e2022-01-22 05:07:33 -070013from buildman import cfgutil
Simon Glass0ede00f2020-04-17 18:09:02 -060014from buildman import toolchain
15from buildman.builder import Builder
Simon Glassbf776672020-04-17 18:09:04 -060016from patman import command
17from patman import gitutil
18from patman import patchstream
19from patman import terminal
Paul Barker5fe50f92021-09-08 12:38:01 +010020from patman import tools
Simon Glass098b10f2022-01-29 14:14:18 -070021from patman.terminal import tprint
Simon Glassfc3fe1c2013-04-03 11:07:16 +000022
23def GetPlural(count):
24 """Returns a plural 's' if count is not 1"""
25 return 's' if count != 1 else ''
26
Simon Glassfea58582014-08-09 15:32:59 -060027def GetActionSummary(is_summary, commits, selected, options):
Simon Glassfc3fe1c2013-04-03 11:07:16 +000028 """Return a string summarising the intended action.
29
30 Returns:
31 Summary string.
32 """
Simon Glassfea58582014-08-09 15:32:59 -060033 if commits:
34 count = len(commits)
Simon Glassc05aa032019-10-31 07:42:53 -060035 count = (count + options.step - 1) // options.step
Simon Glassfea58582014-08-09 15:32:59 -060036 commit_str = '%d commit%s' % (count, GetPlural(count))
37 else:
38 commit_str = 'current source'
39 str = '%s %s for %d boards' % (
40 'Summary of' if is_summary else 'Building', commit_str,
Simon Glassfc3fe1c2013-04-03 11:07:16 +000041 len(selected))
42 str += ' (%d thread%s, %d job%s per thread)' % (options.threads,
43 GetPlural(options.threads), options.jobs, GetPlural(options.jobs))
44 return str
45
Simon Glass06890362018-06-11 23:26:46 -060046def ShowActions(series, why_selected, boards_selected, builder, options,
47 board_warnings):
Simon Glassfc3fe1c2013-04-03 11:07:16 +000048 """Display a list of actions that we would take, if not a dry run.
49
50 Args:
51 series: Series object
52 why_selected: Dictionary where each key is a buildman argument
Simon Glass8d7523c2017-01-23 05:38:56 -070053 provided by the user, and the value is the list of boards
54 brought in by that argument. For example, 'arm' might bring
55 in 400 boards, so in this case the key would be 'arm' and
Simon Glassfc3fe1c2013-04-03 11:07:16 +000056 the value would be a list of board names.
57 boards_selected: Dict of selected boards, key is target name,
58 value is Board object
59 builder: The builder that will be used to build the commits
60 options: Command line options object
Simon Glass06890362018-06-11 23:26:46 -060061 board_warnings: List of warnings obtained from board selected
Simon Glassfc3fe1c2013-04-03 11:07:16 +000062 """
63 col = terminal.Color()
Simon Glassc05aa032019-10-31 07:42:53 -060064 print('Dry run, so not doing much. But I would do this:')
65 print()
Simon Glassfea58582014-08-09 15:32:59 -060066 if series:
67 commits = series.commits
68 else:
69 commits = None
Simon Glassc05aa032019-10-31 07:42:53 -060070 print(GetActionSummary(False, commits, boards_selected,
71 options))
72 print('Build directory: %s' % builder.base_dir)
Simon Glassfea58582014-08-09 15:32:59 -060073 if commits:
74 for upto in range(0, len(series.commits), options.step):
75 commit = series.commits[upto]
Simon Glass252ac582022-01-29 14:14:17 -070076 print(' ', col.build(col.YELLOW, commit.hash[:8], bright=False), end=' ')
Simon Glassc05aa032019-10-31 07:42:53 -060077 print(commit.subject)
78 print()
Simon Glassfc3fe1c2013-04-03 11:07:16 +000079 for arg in why_selected:
80 if arg != 'all':
Simon Glassc05aa032019-10-31 07:42:53 -060081 print(arg, ': %d boards' % len(why_selected[arg]))
Simon Glass8d7523c2017-01-23 05:38:56 -070082 if options.verbose:
Simon Glassc05aa032019-10-31 07:42:53 -060083 print(' %s' % ' '.join(why_selected[arg]))
84 print(('Total boards to build for each commit: %d\n' %
85 len(why_selected['all'])))
Simon Glass06890362018-06-11 23:26:46 -060086 if board_warnings:
87 for warning in board_warnings:
Simon Glass252ac582022-01-29 14:14:17 -070088 print(col.build(col.YELLOW, warning))
Simon Glassfc3fe1c2013-04-03 11:07:16 +000089
Simon Glass4e9162d2020-03-18 09:42:47 -060090def ShowToolchainPrefix(boards, toolchains):
Simon Glass57cb9d52019-12-05 15:59:14 -070091 """Show information about a the tool chain used by one or more boards
92
Simon Glass4e9162d2020-03-18 09:42:47 -060093 The function checks that all boards use the same toolchain, then prints
94 the correct value for CROSS_COMPILE.
Simon Glass57cb9d52019-12-05 15:59:14 -070095
96 Args:
97 boards: Boards object containing selected boards
98 toolchains: Toolchains object containing available toolchains
Simon Glass57cb9d52019-12-05 15:59:14 -070099
100 Return:
101 None on success, string error message otherwise
102 """
103 boards = boards.GetSelectedDict()
104 tc_set = set()
105 for brd in boards.values():
106 tc_set.add(toolchains.Select(brd.arch))
107 if len(tc_set) != 1:
108 return 'Supplied boards must share one toolchain'
109 return False
110 tc = tc_set.pop()
Simon Glass4e9162d2020-03-18 09:42:47 -0600111 print(tc.GetEnvArgs(toolchain.VAR_CROSS_COMPILE))
Simon Glass57cb9d52019-12-05 15:59:14 -0700112 return None
113
Simon Glass883a3212014-09-05 19:00:18 -0600114def DoBuildman(options, args, toolchains=None, make_func=None, boards=None,
Simon Glass8116c782021-04-11 16:27:27 +1200115 clean_dir=False, test_thread_exceptions=False):
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000116 """The main control code for buildman
117
118 Args:
119 options: Command line options object
120 args: Command line arguments (list of strings)
Simon Glassd4144e42014-09-05 19:00:13 -0600121 toolchains: Toolchains to use - this should be a Toolchains()
122 object. If None, then it will be created and scanned
123 make_func: Make function to use for the builder. This is called
124 to execute 'make'. If this is None, the normal function
125 will be used, which calls the 'make' tool with suitable
126 arguments. This setting is useful for tests.
Simon Glass823e60b2014-09-05 19:00:16 -0600127 board: Boards() object to use, containing a list of available
128 boards. If this is None it will be created and scanned.
Simon Glass24993312021-04-11 16:27:25 +1200129 clean_dir: Used for tests only, indicates that the existing output_dir
130 should be removed before starting the build
Simon Glass8116c782021-04-11 16:27:27 +1200131 test_thread_exceptions: Uses for tests only, True to make the threads
132 raise an exception instead of reporting their result. This simulates
133 a failure in the code somewhere
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000134 """
Simon Glass883a3212014-09-05 19:00:18 -0600135 global builder
136
Simon Glass48ba5852014-09-05 19:00:11 -0600137 if options.full_help:
Simon Glassc1aa66e2022-01-29 14:14:04 -0700138 tools.print_full_help(
Paul Barker5fe50f92021-09-08 12:38:01 +0100139 os.path.join(os.path.dirname(os.path.realpath(sys.argv[0])), 'README')
140 )
Simon Glass48ba5852014-09-05 19:00:11 -0600141 return 0
142
Simon Glass0157b182022-01-29 14:14:11 -0700143 gitutil.setup()
Simon Glass713bea32016-07-27 20:33:02 -0600144 col = terminal.Color()
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000145
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000146 options.git_dir = os.path.join(options.git, '.git')
147
Simon Glass7e92e462016-07-27 20:33:04 -0600148 no_toolchains = toolchains is None
149 if no_toolchains:
Simon Glass00beb242019-01-07 16:44:20 -0700150 toolchains = toolchain.Toolchains(options.override_toolchain)
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000151
Simon Glass827e37b2014-12-01 17:34:06 -0700152 if options.fetch_arch:
153 if options.fetch_arch == 'list':
154 sorted_list = toolchains.ListArchs()
Simon Glass252ac582022-01-29 14:14:17 -0700155 print(col.build(col.BLUE, 'Available architectures: %s\n' %
Simon Glassc05aa032019-10-31 07:42:53 -0600156 ' '.join(sorted_list)))
Simon Glass827e37b2014-12-01 17:34:06 -0700157 return 0
158 else:
159 fetch_arch = options.fetch_arch
160 if fetch_arch == 'all':
161 fetch_arch = ','.join(toolchains.ListArchs())
Simon Glass252ac582022-01-29 14:14:17 -0700162 print(col.build(col.CYAN, '\nDownloading toolchains: %s' %
Simon Glassc05aa032019-10-31 07:42:53 -0600163 fetch_arch))
Simon Glass827e37b2014-12-01 17:34:06 -0700164 for arch in fetch_arch.split(','):
Simon Glassc05aa032019-10-31 07:42:53 -0600165 print()
Simon Glass827e37b2014-12-01 17:34:06 -0700166 ret = toolchains.FetchAndInstall(arch)
167 if ret:
168 return ret
169 return 0
170
Simon Glass7e92e462016-07-27 20:33:04 -0600171 if no_toolchains:
172 toolchains.GetSettings()
Simon Glass40232c92018-11-06 16:02:10 -0700173 toolchains.Scan(options.list_tool_chains and options.verbose)
Simon Glass7e92e462016-07-27 20:33:04 -0600174 if options.list_tool_chains:
175 toolchains.List()
Simon Glassc05aa032019-10-31 07:42:53 -0600176 print()
Simon Glass7e92e462016-07-27 20:33:04 -0600177 return 0
178
Simon Glasseb70a2c2020-04-09 15:08:51 -0600179 if options.incremental:
Simon Glass252ac582022-01-29 14:14:17 -0700180 print(col.build(col.RED,
Simon Glasseb70a2c2020-04-09 15:08:51 -0600181 'Warning: -I has been removed. See documentation'))
Simon Glass88daaef2020-04-17 17:51:32 -0600182 if not options.output_dir:
183 if options.work_in_output:
Simon Glass252ac582022-01-29 14:14:17 -0700184 sys.exit(col.build(col.RED, '-w requires that you specify -o'))
Simon Glass88daaef2020-04-17 17:51:32 -0600185 options.output_dir = '..'
Simon Glasseb70a2c2020-04-09 15:08:51 -0600186
Simon Glass7c66ead2019-12-05 15:59:13 -0700187 # Work out what subset of the boards we are building
188 if not boards:
189 if not os.path.exists(options.output_dir):
190 os.makedirs(options.output_dir)
191 board_file = os.path.join(options.output_dir, 'boards.cfg')
Simon Glass5a910b92020-07-19 09:59:49 -0600192 our_path = os.path.dirname(os.path.realpath(__file__))
193 genboardscfg = os.path.join(our_path, '../genboardscfg.py')
194 if not os.path.exists(genboardscfg):
195 genboardscfg = os.path.join(options.git, 'tools/genboardscfg.py')
Simon Glass7c66ead2019-12-05 15:59:13 -0700196 status = subprocess.call([genboardscfg, '-q', '-o', board_file])
197 if status != 0:
Simon Glass5a910b92020-07-19 09:59:49 -0600198 # Older versions don't support -q
199 status = subprocess.call([genboardscfg, '-o', board_file])
200 if status != 0:
201 sys.exit("Failed to generate boards.cfg")
Simon Glass7c66ead2019-12-05 15:59:13 -0700202
203 boards = board.Boards()
204 boards.ReadBoards(board_file)
205
206 exclude = []
207 if options.exclude:
208 for arg in options.exclude:
209 exclude += arg.split(',')
210
211 if options.boards:
212 requested_boards = []
213 for b in options.boards:
214 requested_boards += b.split(',')
215 else:
216 requested_boards = None
217 why_selected, board_warnings = boards.SelectBoards(args, exclude,
218 requested_boards)
219 selected = boards.GetSelected()
220 if not len(selected):
Simon Glass252ac582022-01-29 14:14:17 -0700221 sys.exit(col.build(col.RED, 'No matching boards found'))
Simon Glass7c66ead2019-12-05 15:59:13 -0700222
Simon Glass4e9162d2020-03-18 09:42:47 -0600223 if options.print_prefix:
Simon Glass97944d32020-04-17 17:51:31 -0600224 err = ShowToolchainPrefix(boards, toolchains)
Simon Glass57cb9d52019-12-05 15:59:14 -0700225 if err:
Simon Glass252ac582022-01-29 14:14:17 -0700226 sys.exit(col.build(col.RED, err))
Simon Glass57cb9d52019-12-05 15:59:14 -0700227 return 0
228
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000229 # Work out how many commits to build. We want to build everything on the
230 # branch. We also build the upstream commit as a control so we can see
231 # problems introduced by the first commit on the branch.
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000232 count = options.count
Simon Glass5abab202014-12-01 17:33:57 -0700233 has_range = options.branch and '..' in options.branch
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000234 if count == -1:
235 if not options.branch:
Simon Glassfea58582014-08-09 15:32:59 -0600236 count = 1
237 else:
Simon Glass5abab202014-12-01 17:33:57 -0700238 if has_range:
Simon Glass0157b182022-01-29 14:14:11 -0700239 count, msg = gitutil.count_commits_in_range(options.git_dir,
Simon Glass5abab202014-12-01 17:33:57 -0700240 options.branch)
241 else:
Simon Glass0157b182022-01-29 14:14:11 -0700242 count, msg = gitutil.count_commits_in_branch(options.git_dir,
Simon Glass5abab202014-12-01 17:33:57 -0700243 options.branch)
Simon Glassfea58582014-08-09 15:32:59 -0600244 if count is None:
Simon Glass252ac582022-01-29 14:14:17 -0700245 sys.exit(col.build(col.RED, msg))
Simon Glass5abab202014-12-01 17:33:57 -0700246 elif count == 0:
Simon Glass252ac582022-01-29 14:14:17 -0700247 sys.exit(col.build(col.RED, "Range '%s' has no commits" %
Simon Glass5abab202014-12-01 17:33:57 -0700248 options.branch))
Simon Glass2a9e2c62014-12-01 17:33:54 -0700249 if msg:
Simon Glass252ac582022-01-29 14:14:17 -0700250 print(col.build(col.YELLOW, msg))
Simon Glassfea58582014-08-09 15:32:59 -0600251 count += 1 # Build upstream commit also
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000252
253 if not count:
254 str = ("No commits found to process in branch '%s': "
255 "set branch's upstream or use -c flag" % options.branch)
Simon Glass252ac582022-01-29 14:14:17 -0700256 sys.exit(col.build(col.RED, str))
Simon Glassd829f122020-03-18 09:42:42 -0600257 if options.work_in_output:
258 if len(selected) != 1:
Simon Glass252ac582022-01-29 14:14:17 -0700259 sys.exit(col.build(col.RED,
Simon Glassd829f122020-03-18 09:42:42 -0600260 '-w can only be used with a single board'))
261 if count != 1:
Simon Glass252ac582022-01-29 14:14:17 -0700262 sys.exit(col.build(col.RED,
Simon Glassd829f122020-03-18 09:42:42 -0600263 '-w can only be used with a single commit'))
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000264
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000265 # Read the metadata from the commits. First look at the upstream commit,
266 # then the ones in the branch. We would like to do something like
267 # upstream/master~..branch but that isn't possible if upstream/master is
268 # a merge commit (it will list all the commits that form part of the
269 # merge)
Simon Glass950a2312014-09-05 19:00:23 -0600270 # Conflicting tags are not a problem for buildman, since it does not use
271 # them. For example, Series-version is not useful for buildman. On the
272 # other hand conflicting tags will cause an error. So allow later tags
273 # to overwrite earlier ones by setting allow_overwrite=True
Simon Glassfea58582014-08-09 15:32:59 -0600274 if options.branch:
Simon Glass3b74ba52014-08-09 15:33:09 -0600275 if count == -1:
Simon Glass5abab202014-12-01 17:33:57 -0700276 if has_range:
277 range_expr = options.branch
278 else:
Simon Glass0157b182022-01-29 14:14:11 -0700279 range_expr = gitutil.get_range_in_branch(options.git_dir,
Simon Glass5abab202014-12-01 17:33:57 -0700280 options.branch)
Simon Glass0157b182022-01-29 14:14:11 -0700281 upstream_commit = gitutil.get_upstream(options.git_dir,
Simon Glass3b74ba52014-08-09 15:33:09 -0600282 options.branch)
Simon Glassd93720e2020-10-29 21:46:19 -0600283 series = patchstream.get_metadata_for_list(upstream_commit,
Simon Glass950a2312014-09-05 19:00:23 -0600284 options.git_dir, 1, series=None, allow_overwrite=True)
Simon Glassfea58582014-08-09 15:32:59 -0600285
Simon Glassd93720e2020-10-29 21:46:19 -0600286 series = patchstream.get_metadata_for_list(range_expr,
Simon Glass950a2312014-09-05 19:00:23 -0600287 options.git_dir, None, series, allow_overwrite=True)
Simon Glass3b74ba52014-08-09 15:33:09 -0600288 else:
289 # Honour the count
Simon Glassd93720e2020-10-29 21:46:19 -0600290 series = patchstream.get_metadata_for_list(options.branch,
Simon Glass950a2312014-09-05 19:00:23 -0600291 options.git_dir, count, series=None, allow_overwrite=True)
Simon Glassfea58582014-08-09 15:32:59 -0600292 else:
293 series = None
Simon Glass8d7523c2017-01-23 05:38:56 -0700294 if not options.dry_run:
295 options.verbose = True
296 if not options.summary:
297 options.show_errors = True
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000298
299 # By default we have one thread per CPU. But if there are not enough jobs
300 # we can have fewer threads and use a high '-j' value for make.
Simon Glassb82492b2021-01-30 22:17:46 -0700301 if options.threads is None:
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000302 options.threads = min(multiprocessing.cpu_count(), len(selected))
303 if not options.jobs:
304 options.jobs = max(1, (multiprocessing.cpu_count() +
Simon Glassc05aa032019-10-31 07:42:53 -0600305 len(selected) - 1) // len(selected))
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000306
307 if not options.step:
308 options.step = len(series.commits) - 1
309
Simon Glassd9800692022-01-29 14:14:05 -0700310 gnu_make = command.output(os.path.join(options.git,
Simon Glass785f1542016-07-25 18:59:00 -0600311 'scripts/show-gnu-make'), raise_on_error=False).rstrip()
Masahiro Yamada99796922014-07-22 11:19:09 +0900312 if not gnu_make:
Masahiro Yamada31e21412014-08-16 00:59:26 +0900313 sys.exit('GNU Make not found')
Masahiro Yamada99796922014-07-22 11:19:09 +0900314
Simon Glass05c96b12014-12-01 17:33:52 -0700315 # Create a new builder with the selected options.
316 output_dir = options.output_dir
Simon Glassfea58582014-08-09 15:32:59 -0600317 if options.branch:
Simon Glassf7582ce2014-09-05 19:00:22 -0600318 dirname = options.branch.replace('/', '_')
Simon Glass5971ab52014-12-01 17:33:55 -0700319 # As a special case allow the board directory to be placed in the
320 # output directory itself rather than any subdirectory.
321 if not options.no_subdirs:
322 output_dir = os.path.join(options.output_dir, dirname)
Lothar Waßmann409fc022018-04-08 05:14:11 -0600323 if clean_dir and os.path.exists(output_dir):
324 shutil.rmtree(output_dir)
Simon Glass2b4806e2022-01-22 05:07:33 -0700325 adjust_cfg = cfgutil.convert_list_to_dict(options.adjust_cfg)
326
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000327 builder = Builder(toolchains, output_dir, options.git_dir,
Masahiro Yamada99796922014-07-22 11:19:09 +0900328 options.threads, options.jobs, gnu_make=gnu_make, checkout=True,
Simon Glass5971ab52014-12-01 17:33:55 -0700329 show_unknown=options.show_unknown, step=options.step,
Simon Glassd2ce6582014-12-01 17:34:07 -0700330 no_subdirs=options.no_subdirs, full_path=options.full_path,
Stephen Warrenf79f1e02016-04-11 10:48:44 -0600331 verbose_build=options.verbose_build,
Simon Glasseb70a2c2020-04-09 15:08:51 -0600332 mrproper=options.mrproper,
Simon Glassb50113f2016-11-13 14:25:51 -0700333 per_board_out_dir=options.per_board_out_dir,
Simon Glassb464f8e2016-11-13 14:25:53 -0700334 config_only=options.config_only,
Daniel Schwierzeck2371d1b2018-01-26 16:31:05 +0100335 squash_config_y=not options.preserve_config_y,
Simon Glassd829f122020-03-18 09:42:42 -0600336 warnings_as_errors=options.warnings_as_errors,
Simon Glass8116c782021-04-11 16:27:27 +1200337 work_in_output=options.work_in_output,
Simon Glass2b4806e2022-01-22 05:07:33 -0700338 test_thread_exceptions=test_thread_exceptions,
339 adjust_cfg=adjust_cfg)
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000340 builder.force_config_on_failure = not options.quick
Simon Glassd4144e42014-09-05 19:00:13 -0600341 if make_func:
342 builder.do_make = make_func
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000343
344 # For a dry run, just show our actions as a sanity check
345 if options.dry_run:
Simon Glass06890362018-06-11 23:26:46 -0600346 ShowActions(series, why_selected, selected, builder, options,
347 board_warnings)
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000348 else:
349 builder.force_build = options.force_build
Simon Glass4266dc22014-07-13 12:22:31 -0600350 builder.force_build_failures = options.force_build_failures
Simon Glass97e91522014-07-14 17:51:02 -0600351 builder.force_reconfig = options.force_reconfig
Simon Glass189a4962014-07-14 17:51:03 -0600352 builder.in_tree = options.in_tree
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000353
354 # Work out which boards to build
355 board_selected = boards.GetSelectedDict()
356
Simon Glassfea58582014-08-09 15:32:59 -0600357 if series:
358 commits = series.commits
Simon Glass883a3212014-09-05 19:00:18 -0600359 # Number the commits for test purposes
360 for commit in range(len(commits)):
361 commits[commit].sequence = commit
Simon Glassfea58582014-08-09 15:32:59 -0600362 else:
363 commits = None
364
Simon Glass098b10f2022-01-29 14:14:18 -0700365 tprint(GetActionSummary(options.summary, commits, board_selected,
Simon Glass174592b2020-04-09 15:08:52 -0600366 options))
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000367
Simon Glass7798e222014-09-14 20:23:16 -0600368 # We can't show function sizes without board details at present
369 if options.show_bloat:
370 options.show_detail = True
Simon Glass174592b2020-04-09 15:08:52 -0600371 builder.SetDisplayOptions(
372 options.show_errors, options.show_sizes, options.show_detail,
373 options.show_bloat, options.list_error_boards, options.show_config,
Simon Glass113a8a52020-04-09 15:08:53 -0600374 options.show_environment, options.filter_dtb_warnings,
375 options.filter_migration_warnings)
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000376 if options.summary:
Simon Glassb2ea7ab2014-08-09 15:33:02 -0600377 builder.ShowSummary(commits, board_selected)
Simon Glassfc3fe1c2013-04-03 11:07:16 +0000378 else:
Simon Glass8116c782021-04-11 16:27:27 +1200379 fail, warned, excs = builder.BuildBoards(
380 commits, board_selected, options.keep_outputs, options.verbose)
381 if excs:
382 return 102
383 elif fail:
Simon Glassb1e5e6d2020-04-09 10:49:45 -0600384 return 100
Simon Glass7beb43c2020-03-18 09:42:44 -0600385 elif warned and not options.ignore_warnings:
Simon Glassb1e5e6d2020-04-09 10:49:45 -0600386 return 101
Simon Glass2c3deb92014-08-28 09:43:39 -0600387 return 0