blob: 8c3696d744da7a5ca4cc3ff038d591337f0439bf [file] [log] [blame]
Chris Sosa9ba47752012-02-27 15:27:37 -08001# Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
Chris Sosadad0d322011-01-31 16:37:33 -08002# Use of this source code is governed by a BSD-style license that can be
3# found in the LICENSE file.
4
5"""This module uprevs Chrome for cbuildbot.
6
7After calling, it prints outs CHROME_VERSION_ATOM=(version atom string). A
8caller could then use this atom with emerge to build the newly uprevved version
9of Chrome e.g.
10
11./cros_mark_chrome_as_stable tot
12Returns chrome-base/chromeos-chrome-8.0.552.0_alpha_r1
13
14emerge-x86-generic =chrome-base/chromeos-chrome-8.0.552.0_alpha_r1
15"""
16
Stefan Zagerd49d9ff2014-08-15 21:33:37 -070017import base64
Mike Frysingera94f1252019-09-12 02:39:28 -040018import distutils.version # pylint: disable=import-error,no-name-in-module
Chris Sosa8be39132011-04-14 12:09:24 -070019import filecmp
Chris Sosadad0d322011-01-31 16:37:33 -080020import os
21import re
Mike Frysingere852b072021-05-21 12:39:03 -040022import urllib.parse
Chris Sosadad0d322011-01-31 16:37:33 -080023
Aviv Keshetb7519e12016-10-04 00:50:00 -070024from chromite.lib import constants
Mike Frysingera13c04f2016-09-01 00:35:17 -040025from chromite.lib import commandline
David James1b363582012-12-17 11:53:11 -080026from chromite.lib import cros_build_lib
Ralph Nathan03047282015-03-23 11:09:32 -070027from chromite.lib import cros_logging as logging
David James97d95872012-11-16 15:09:56 -080028from chromite.lib import git
Stefan Zagerd49d9ff2014-08-15 21:33:37 -070029from chromite.lib import gob_util
Alex Deymo075c2292014-09-04 18:31:50 -070030from chromite.lib import portage_util
Stefan Zagerd49d9ff2014-08-15 21:33:37 -070031from chromite.lib import timeout_util
Mike Frysinger6cb624a2012-05-24 18:17:38 -040032from chromite.scripts import cros_mark_as_stable
Chris Sosadad0d322011-01-31 16:37:33 -080033
Mike Frysinger750c5f52014-09-16 16:16:57 -040034
Chris Sosadad0d322011-01-31 16:37:33 -080035# Helper regex's for finding ebuilds.
David James7c352bc2013-03-15 14:19:57 -070036_CHROME_VERSION_REGEX = r'\d+\.\d+\.\d+\.\d+'
37_NON_STICKY_REGEX = r'%s[(_rc.*)|(_alpha.*)]+' % _CHROME_VERSION_REGEX
Chris Sosadad0d322011-01-31 16:37:33 -080038
39# Dir where all the action happens.
David Zeuthen665d3132014-08-25 15:27:02 -040040_OVERLAY_DIR = '%(srcroot)s/third_party/chromiumos-overlay/'
Chris Sosadad0d322011-01-31 16:37:33 -080041
David Zeuthen665d3132014-08-25 15:27:02 -040042_GIT_COMMIT_MESSAGE = ('Marking %(chrome_rev)s for %(chrome_pn)s ebuild '
43 'with version %(chrome_version)s as stable.')
Chris Sosadad0d322011-01-31 16:37:33 -080044
Chris Masone592cab52011-08-02 14:05:48 -070045# URLs that print lists of chrome revisions between two versions of the browser.
46_CHROME_VERSION_URL = ('http://omahaproxy.appspot.com/changelog?'
47 'old_version=%(old)s&new_version=%(new)s')
Chris Sosadd611df2012-02-03 15:26:23 -080048
49# Only print links when we rev these types.
50_REV_TYPES_FOR_LINKS = [constants.CHROME_REV_LATEST,
51 constants.CHROME_REV_STICKY]
Chris Masone592cab52011-08-02 14:05:48 -070052
ChromeOS Developer03118eb2013-02-12 14:27:09 -080053
petermayo@chromium.org163b3372011-09-12 02:06:05 -040054def _GetVersionContents(chrome_version_info):
Peter Mayo177500f2011-09-09 17:25:23 -040055 """Returns the current Chromium version, from the contents of a VERSION file.
Chris Sosadad0d322011-01-31 16:37:33 -080056
Peter Mayo177500f2011-09-09 17:25:23 -040057 Args:
Mike Frysinger6f3c48e2015-05-06 02:38:51 -040058 chrome_version_info: The contents of a chromium VERSION file.
Peter Mayo177500f2011-09-09 17:25:23 -040059 """
Chris Sosadad0d322011-01-31 16:37:33 -080060 chrome_version_array = []
Chris Sosadad0d322011-01-31 16:37:33 -080061 for line in chrome_version_info.splitlines():
62 chrome_version_array.append(line.rpartition('=')[2])
63
64 return '.'.join(chrome_version_array)
65
Mike Frysingercc838832014-05-24 13:10:30 -040066
Stefan Zagerd49d9ff2014-08-15 21:33:37 -070067def _GetSpecificVersionUrl(git_url, revision, time_to_wait=600):
petermayo@chromium.org163b3372011-09-12 02:06:05 -040068 """Returns the Chromium version, from a repository URL and version.
Peter Mayo177500f2011-09-09 17:25:23 -040069
70 Args:
Mike Frysinger6f3c48e2015-05-06 02:38:51 -040071 git_url: Repository URL for chromium.
72 revision: the git revision we want to use.
73 time_to_wait: the minimum period before abandoning our wait for the
74 desired revision to be present.
Peter Mayo177500f2011-09-09 17:25:23 -040075 """
Mike Frysinger3dcacee2019-08-23 17:09:11 -040076 parsed_url = urllib.parse.urlparse(git_url)
Stefan Zagerd49d9ff2014-08-15 21:33:37 -070077 host = parsed_url[1]
78 path = parsed_url[2].rstrip('/') + (
79 '/+/%s/chrome/VERSION?format=text' % revision)
petermayo@chromium.org163b3372011-09-12 02:06:05 -040080
Stefan Zagerd49d9ff2014-08-15 21:33:37 -070081 # Allow for git repository replication lag with sleep/retry loop.
82 def _fetch():
Jack Rosenthal61e67832019-09-16 12:48:38 -060083 return gob_util.FetchUrl(host, path, ignore_404=True)
petermayo@chromium.org163b3372011-09-12 02:06:05 -040084
Mike Frysingercc55c782014-12-03 22:32:08 -050085 def _wait_msg(_remaining):
Ralph Nathan03047282015-03-23 11:09:32 -070086 logging.info('Repository does not yet have revision %s. Sleeping...',
87 revision)
petermayo@chromium.org163b3372011-09-12 02:06:05 -040088
Stefan Zagerd49d9ff2014-08-15 21:33:37 -070089 content = timeout_util.WaitForSuccess(
90 retry_check=lambda x: not bool(x),
91 func=_fetch,
92 timeout=time_to_wait,
93 period=30,
94 side_effect_func=_wait_msg)
Jack Rosenthal61e67832019-09-16 12:48:38 -060095 return _GetVersionContents(base64.b64decode(content).decode('utf-8'))
petermayo@chromium.org163b3372011-09-12 02:06:05 -040096
Peter Mayo177500f2011-09-09 17:25:23 -040097
98def _GetTipOfTrunkVersionFile(root):
99 """Returns the current Chromium version, from a file in a checkout.
100
101 Args:
Mike Frysinger6f3c48e2015-05-06 02:38:51 -0400102 root: path to the root of the chromium checkout.
Peter Mayo177500f2011-09-09 17:25:23 -0400103 """
104 version_file = os.path.join(root, 'src', 'chrome', 'VERSION')
Mike Frysinger94a459c2019-09-29 23:43:05 -0400105 try:
106 chrome_version_info = cros_build_lib.run(
107 ['cat', version_file],
Mike Frysinger0282d222019-12-17 17:15:48 -0500108 stdout=True).stdout
Mike Frysinger94a459c2019-09-29 23:43:05 -0400109 except cros_build_lib.RunCommandError as e:
110 e.msg += '\nCould not read version file at %s.' % version_file
111 raise e
Peter Mayo177500f2011-09-09 17:25:23 -0400112
petermayo@chromium.org163b3372011-09-12 02:06:05 -0400113 return _GetVersionContents(chrome_version_info)
Peter Mayo177500f2011-09-09 17:25:23 -0400114
ChromeOS Developer03118eb2013-02-12 14:27:09 -0800115
Stefan Zagerd49d9ff2014-08-15 21:33:37 -0700116def CheckIfChromeRightForOS(deps_content):
Dharani Govindan4beb94c2014-07-18 13:31:47 -0700117 """Checks if DEPS is right for Chrome OS.
118
119 This function checks for a variable called 'buildspec_platforms' to
120 find out if its 'chromeos' or 'all'. If any of those values,
121 then it chooses that DEPS.
122
123 Args:
Stefan Zagerd49d9ff2014-08-15 21:33:37 -0700124 deps_content: Content of release buildspec DEPS file.
Dharani Govindan4beb94c2014-07-18 13:31:47 -0700125
126 Returns:
127 True if DEPS is the right Chrome for Chrome OS.
128 """
Stefan Zagerd49d9ff2014-08-15 21:33:37 -0700129 platforms_search = re.search(r'buildspec_platforms.*\s.*\s', deps_content)
Dharani Govindancbbf69c2014-07-29 15:37:39 -0700130
131 if platforms_search:
132 platforms = platforms_search.group()
133 if 'chromeos' in platforms or 'all' in platforms:
134 return True
Dharani Govindan4beb94c2014-07-18 13:31:47 -0700135
136 return False
137
138
Stefan Zagerd49d9ff2014-08-15 21:33:37 -0700139def GetLatestRelease(git_url, branch=None):
140 """Gets the latest release version from the release tags in the repository.
Chris Sosadad0d322011-01-31 16:37:33 -0800141
142 Args:
Stefan Zagerd49d9ff2014-08-15 21:33:37 -0700143 git_url: URL of git repository.
Mike Frysingerad8c6ca2014-02-03 11:28:45 -0500144 branch: If set, gets the latest release for branch, otherwise latest
Chris Sosadad0d322011-01-31 16:37:33 -0800145 release.
Mike Frysinger1a736a82013-12-12 01:50:59 -0500146
Chris Sosadad0d322011-01-31 16:37:33 -0800147 Returns:
148 Latest version string.
149 """
Stefan Zagerd49d9ff2014-08-15 21:33:37 -0700150 # TODO(szager): This only works for public release buildspecs in the chromium
151 # src repository. Internal buildspecs are tracked differently. At the time
152 # of writing, I can't find any callers that use this method to scan for
153 # internal buildspecs. But there may be something lurking...
154
Mike Frysinger3dcacee2019-08-23 17:09:11 -0400155 parsed_url = urllib.parse.urlparse(git_url)
Stefan Zagerd49d9ff2014-08-15 21:33:37 -0700156 path = parsed_url[2].rstrip('/') + '/+refs/tags?format=JSON'
157 j = gob_util.FetchUrlJson(parsed_url[1], path, ignore_404=False)
Chris Sosadad0d322011-01-31 16:37:33 -0800158 if branch:
David James7c352bc2013-03-15 14:19:57 -0700159 chrome_version_re = re.compile(r'^%s\.\d+.*' % branch)
Chris Sosadad0d322011-01-31 16:37:33 -0800160 else:
David James7c352bc2013-03-15 14:19:57 -0700161 chrome_version_re = re.compile(r'^[0-9]+\..*')
Stefan Zagerd49d9ff2014-08-15 21:33:37 -0700162 matching_versions = [key for key in j.keys() if chrome_version_re.match(key)]
163 matching_versions.sort(key=distutils.version.LooseVersion)
164 for chrome_version in reversed(matching_versions):
165 path = parsed_url[2].rstrip() + (
166 '/+/refs/tags/%s/DEPS?format=text' % chrome_version)
Jack Rosenthal61e67832019-09-16 12:48:38 -0600167 content = gob_util.FetchUrl(parsed_url[1], path, ignore_404=False)
Stefan Zagerd49d9ff2014-08-15 21:33:37 -0700168 if content:
Jack Rosenthal61e67832019-09-16 12:48:38 -0600169 deps_content = base64.b64decode(content).decode('utf-8')
Stefan Zagerd49d9ff2014-08-15 21:33:37 -0700170 if CheckIfChromeRightForOS(deps_content):
171 return chrome_version
Peter Mayoad8173d2011-11-08 16:18:23 -0500172
173 return None
Chris Sosadad0d322011-01-31 16:37:33 -0800174
175
176def _GetStickyEBuild(stable_ebuilds):
177 """Returns the sticky ebuild."""
178 sticky_ebuilds = []
179 non_sticky_re = re.compile(_NON_STICKY_REGEX)
180 for ebuild in stable_ebuilds:
181 if not non_sticky_re.match(ebuild.version):
182 sticky_ebuilds.append(ebuild)
183
184 if not sticky_ebuilds:
185 raise Exception('No sticky ebuilds found')
186 elif len(sticky_ebuilds) > 1:
Mike Frysinger6c2a6242019-03-20 20:37:24 -0400187 logging.warning('More than one sticky ebuild found:')
188 for ebuild in sticky_ebuilds:
189 logging.warning(' %s', ebuild.ebuild_path)
190 logging.warning('Make sure to *not* create xxx.0-r1.ebuilds')
Chris Sosadad0d322011-01-31 16:37:33 -0800191
Alex Deymo075c2292014-09-04 18:31:50 -0700192 return portage_util.BestEBuild(sticky_ebuilds)
Chris Sosadad0d322011-01-31 16:37:33 -0800193
194
Alex Deymo075c2292014-09-04 18:31:50 -0700195class ChromeEBuild(portage_util.EBuild):
Chris Sosadad0d322011-01-31 16:37:33 -0800196 """Thin sub-class of EBuild that adds a chrome_version field."""
David Zeuthen665d3132014-08-25 15:27:02 -0400197 chrome_version_re = re.compile(r'.*-(%s|9999).*' % (
198 _CHROME_VERSION_REGEX))
Chris Sosadad0d322011-01-31 16:37:33 -0800199 chrome_version = ''
200
201 def __init__(self, path):
Alex Deymo075c2292014-09-04 18:31:50 -0700202 portage_util.EBuild.__init__(self, path)
Chris Sosadad0d322011-01-31 16:37:33 -0800203 re_match = self.chrome_version_re.match(self.ebuild_path_no_revision)
204 if re_match:
205 self.chrome_version = re_match.group(1)
206
Chris Sosadad0d322011-01-31 16:37:33 -0800207 def __str__(self):
208 return self.ebuild_path
209
210
David Zeuthen665d3132014-08-25 15:27:02 -0400211def FindChromeCandidates(package_dir):
Chris Sosadad0d322011-01-31 16:37:33 -0800212 """Return a tuple of chrome's unstable ebuild and stable ebuilds.
213
214 Args:
David Zeuthen665d3132014-08-25 15:27:02 -0400215 package_dir: The path to where the package ebuild is stored.
Mike Frysinger1a736a82013-12-12 01:50:59 -0500216
Chris Sosadad0d322011-01-31 16:37:33 -0800217 Returns:
218 Tuple [unstable_ebuild, stable_ebuilds].
Mike Frysinger1a736a82013-12-12 01:50:59 -0500219
Chris Sosadad0d322011-01-31 16:37:33 -0800220 Raises:
221 Exception: if no unstable ebuild exists for Chrome.
222 """
223 stable_ebuilds = []
224 unstable_ebuilds = []
225 for path in [
David Zeuthen665d3132014-08-25 15:27:02 -0400226 os.path.join(package_dir, entry) for entry in os.listdir(package_dir)]:
Chris Sosadad0d322011-01-31 16:37:33 -0800227 if path.endswith('.ebuild'):
228 ebuild = ChromeEBuild(path)
229 if not ebuild.chrome_version:
Lann Martinffb95162018-08-28 12:02:54 -0600230 logging.warning('Poorly formatted ebuild found at %s', path)
Chris Sosadad0d322011-01-31 16:37:33 -0800231 else:
232 if '9999' in ebuild.version:
233 unstable_ebuilds.append(ebuild)
234 else:
235 stable_ebuilds.append(ebuild)
236
237 # Apply some sanity checks.
238 if not unstable_ebuilds:
David Zeuthen665d3132014-08-25 15:27:02 -0400239 raise Exception('Missing 9999 ebuild for %s' % package_dir)
Chris Sosadad0d322011-01-31 16:37:33 -0800240 if not stable_ebuilds:
Lann Martinffb95162018-08-28 12:02:54 -0600241 logging.warning('Missing stable ebuild for %s', package_dir)
Chris Sosadad0d322011-01-31 16:37:33 -0800242
Alex Deymo075c2292014-09-04 18:31:50 -0700243 return portage_util.BestEBuild(unstable_ebuilds), stable_ebuilds
Chris Sosadad0d322011-01-31 16:37:33 -0800244
245
246def FindChromeUprevCandidate(stable_ebuilds, chrome_rev, sticky_branch):
247 """Finds the Chrome uprev candidate for the given chrome_rev.
248
249 Using the pre-flight logic, this means the stable ebuild you are uprevving
250 from. The difference here is that the version could be different and in
251 that case we want to find it to delete it.
252
253 Args:
254 stable_ebuilds: A list of stable ebuilds.
255 chrome_rev: The chrome_rev designating which candidate to find.
Mike Frysingerad8c6ca2014-02-03 11:28:45 -0500256 sticky_branch: The the branch that is currently sticky with Major/Minor
Chris Sosa9ba47752012-02-27 15:27:37 -0800257 components. For example: 9.0.553. Can be None but not if chrome_rev
258 is CHROME_REV_STICKY.
Mike Frysinger1a736a82013-12-12 01:50:59 -0500259
Chris Sosadad0d322011-01-31 16:37:33 -0800260 Returns:
Mike Frysinger1a736a82013-12-12 01:50:59 -0500261 The EBuild, otherwise None if none found.
Chris Sosadad0d322011-01-31 16:37:33 -0800262 """
263 candidates = []
petermayo@chromium.org163b3372011-09-12 02:06:05 -0400264 if chrome_rev in [constants.CHROME_REV_LOCAL, constants.CHROME_REV_TOT,
265 constants.CHROME_REV_SPEC]:
266 # These are labelled alpha, for historic reasons,
Peter Mayo177500f2011-09-09 17:25:23 -0400267 # not just for the fun of confusion.
David James7c352bc2013-03-15 14:19:57 -0700268 chrome_branch_re = re.compile(r'%s.*_alpha.*' % _CHROME_VERSION_REGEX)
Chris Sosadad0d322011-01-31 16:37:33 -0800269 for ebuild in stable_ebuilds:
270 if chrome_branch_re.search(ebuild.version):
271 candidates.append(ebuild)
272
Ryan Cuic6e097d2011-06-16 12:23:14 -0700273 elif chrome_rev == constants.CHROME_REV_STICKY:
Chris Sosa9ba47752012-02-27 15:27:37 -0800274 assert sticky_branch is not None
David James7c352bc2013-03-15 14:19:57 -0700275 chrome_branch_re = re.compile(r'%s\..*' % sticky_branch)
Chris Sosadad0d322011-01-31 16:37:33 -0800276 for ebuild in stable_ebuilds:
277 if chrome_branch_re.search(ebuild.version):
278 candidates.append(ebuild)
279
280 else:
David James7c352bc2013-03-15 14:19:57 -0700281 chrome_branch_re = re.compile(r'%s.*_rc.*' % _CHROME_VERSION_REGEX)
Chris Sosadad0d322011-01-31 16:37:33 -0800282 for ebuild in stable_ebuilds:
Chris Sosa9ba47752012-02-27 15:27:37 -0800283 if chrome_branch_re.search(ebuild.version):
Chris Sosadad0d322011-01-31 16:37:33 -0800284 candidates.append(ebuild)
285
286 if candidates:
Alex Deymo075c2292014-09-04 18:31:50 -0700287 return portage_util.BestEBuild(candidates)
Chris Sosadad0d322011-01-31 16:37:33 -0800288 else:
289 return None
290
Mike Frysingercc838832014-05-24 13:10:30 -0400291
Chris Masone592cab52011-08-02 14:05:48 -0700292def GetChromeRevisionLinkFromVersions(old_chrome_version, chrome_version):
293 """Return appropriately formatted link to revision info, given versions
294
295 Given two chrome version strings (e.g. 9.0.533.0), generate a link to a
296 page that prints the Chromium revisions between those two versions.
297
298 Args:
299 old_chrome_version: version to diff from
300 chrome_version: version to which to diff
Mike Frysinger1a736a82013-12-12 01:50:59 -0500301
Chris Masone592cab52011-08-02 14:05:48 -0700302 Returns:
303 The desired URL.
304 """
Mike Frysingerd6e2df02014-11-26 02:55:04 -0500305 return _CHROME_VERSION_URL % {'old': old_chrome_version,
306 'new': chrome_version}
Chris Masone592cab52011-08-02 14:05:48 -0700307
Mike Frysinger750c5f52014-09-16 16:16:57 -0400308
Chris Masone592cab52011-08-02 14:05:48 -0700309def GetChromeRevisionListLink(old_chrome, new_chrome, chrome_rev):
310 """Returns a link to the list of revisions between two Chromium versions
311
312 Given two ChromeEBuilds and the kind of rev we're doing, generate a
313 link to a page that prints the Chromium changes between those two
314 revisions, inclusive.
315
316 Args:
317 old_chrome: ebuild for the version to diff from
318 new_chrome: ebuild for the version to which to diff
319 chrome_rev: one of constants.VALID_CHROME_REVISIONS
Mike Frysinger1a736a82013-12-12 01:50:59 -0500320
Chris Masone592cab52011-08-02 14:05:48 -0700321 Returns:
322 The desired URL.
323 """
Chris Sosadd611df2012-02-03 15:26:23 -0800324 assert chrome_rev in _REV_TYPES_FOR_LINKS
325 return GetChromeRevisionLinkFromVersions(old_chrome.chrome_version,
326 new_chrome.chrome_version)
Chris Sosadad0d322011-01-31 16:37:33 -0800327
Mike Frysingercc838832014-05-24 13:10:30 -0400328
David Zeuthen665d3132014-08-25 15:27:02 -0400329def MarkChromeEBuildAsStable(stable_candidate, unstable_ebuild, chrome_pn,
Mike Frysinger93ad2262018-08-30 18:42:14 -0400330 chrome_rev, chrome_version, package_dir):
David James7c352bc2013-03-15 14:19:57 -0700331 r"""Uprevs the chrome ebuild specified by chrome_rev.
Chris Sosadad0d322011-01-31 16:37:33 -0800332
333 This is the main function that uprevs the chrome_rev from a stable candidate
334 to its new version.
335
336 Args:
337 stable_candidate: ebuild that corresponds to the stable ebuild we are
338 revving from. If None, builds the a new ebuild given the version
339 and logic for chrome_rev type with revision set to 1.
Mike Frysingerad8c6ca2014-02-03 11:28:45 -0500340 unstable_ebuild: ebuild corresponding to the unstable ebuild for chrome.
David Zeuthen665d3132014-08-25 15:27:02 -0400341 chrome_pn: package name.
Peter Mayo177500f2011-09-09 17:25:23 -0400342 chrome_rev: one of constants.VALID_CHROME_REVISIONS or LOCAL
petermayo@chromium.org163b3372011-09-12 02:06:05 -0400343 constants.CHROME_REV_SPEC - Requires commit value. Revs the ebuild for
344 the specified version and uses the portage suffix of _alpha.
Ryan Cuic6e097d2011-06-16 12:23:14 -0700345 constants.CHROME_REV_TOT - Requires commit value. Revs the ebuild for
346 the TOT version and uses the portage suffix of _alpha.
Peter Mayo177500f2011-09-09 17:25:23 -0400347 constants.CHROME_REV_LOCAL - Requires a chrome_root. Revs the ebuild for
348 the local version and uses the portage suffix of _alpha.
Ryan Cuic6e097d2011-06-16 12:23:14 -0700349 constants.CHROME_REV_LATEST - This uses the portage suffix of _rc as they
350 are release candidates for the next sticky version.
351 constants.CHROME_REV_STICKY - Revs the sticky version.
Mike Frysingerad8c6ca2014-02-03 11:28:45 -0500352 chrome_version: The \d.\d.\d.\d version of Chrome.
David Zeuthen665d3132014-08-25 15:27:02 -0400353 package_dir: Path to the chromeos-chrome package dir.
Mike Frysinger1a736a82013-12-12 01:50:59 -0500354
Chris Sosadad0d322011-01-31 16:37:33 -0800355 Returns:
356 Full portage version atom (including rc's, etc) that was revved.
357 """
Chris Sosa8be39132011-04-14 12:09:24 -0700358 def IsTheNewEBuildRedundant(new_ebuild, stable_ebuild):
359 """Returns True if the new ebuild is redundant.
360
361 This is True if there if the current stable ebuild is the exact same copy
David James89608f92012-11-03 14:14:12 -0700362 of the new one.
Chris Sosa8be39132011-04-14 12:09:24 -0700363 """
364 if not stable_ebuild:
365 return False
366
367 if stable_candidate.chrome_version == new_ebuild.chrome_version:
David James89608f92012-11-03 14:14:12 -0700368 return filecmp.cmp(
369 new_ebuild.ebuild_path, stable_ebuild.ebuild_path, shallow=False)
Chris Sosa8be39132011-04-14 12:09:24 -0700370
David James629febb2012-11-25 13:07:34 -0800371 # Mark latest release and sticky branches as stable.
372 mark_stable = chrome_rev not in [constants.CHROME_REV_TOT,
373 constants.CHROME_REV_SPEC,
374 constants.CHROME_REV_LOCAL]
375
Chris Sosadad0d322011-01-31 16:37:33 -0800376 # Case where we have the last stable candidate with same version just rev.
377 if stable_candidate and stable_candidate.chrome_version == chrome_version:
378 new_ebuild_path = '%s-r%d.ebuild' % (
379 stable_candidate.ebuild_path_no_revision,
380 stable_candidate.current_revision + 1)
381 else:
David James629febb2012-11-25 13:07:34 -0800382 suffix = 'rc' if mark_stable else 'alpha'
David Zeuthen665d3132014-08-25 15:27:02 -0400383 pf = '%s-%s_%s-r1' % (chrome_pn, chrome_version, suffix)
384 new_ebuild_path = os.path.join(package_dir, '%s.ebuild' % pf)
Chris Sosadad0d322011-01-31 16:37:33 -0800385
Alex Deymo075c2292014-09-04 18:31:50 -0700386 portage_util.EBuild.MarkAsStable(
David James065b2012012-04-01 14:51:11 -0700387 unstable_ebuild.ebuild_path, new_ebuild_path,
Mike Frysinger93ad2262018-08-30 18:42:14 -0400388 {}, make_stable=mark_stable)
Chris Sosadad0d322011-01-31 16:37:33 -0800389 new_ebuild = ChromeEBuild(new_ebuild_path)
Chris Sosa8be39132011-04-14 12:09:24 -0700390
391 # Determine whether this is ebuild is redundant.
392 if IsTheNewEBuildRedundant(new_ebuild, stable_candidate):
David James1b363582012-12-17 11:53:11 -0800393 msg = 'Previous ebuild with same version found and ebuild is redundant.'
Ralph Nathan03047282015-03-23 11:09:32 -0700394 logging.info(msg)
Chris Sosa8be39132011-04-14 12:09:24 -0700395 os.unlink(new_ebuild_path)
396 return None
Chris Sosadad0d322011-01-31 16:37:33 -0800397
Chris Sosadd611df2012-02-03 15:26:23 -0800398 if stable_candidate and chrome_rev in _REV_TYPES_FOR_LINKS:
David Riley3e3f64e2016-02-03 08:17:55 -0800399 logging.PrintBuildbotLink('Chromium revisions',
400 GetChromeRevisionListLink(stable_candidate,
401 new_ebuild, chrome_rev))
Chris Masone592cab52011-08-02 14:05:48 -0700402
David Zeuthen665d3132014-08-25 15:27:02 -0400403 git.RunGit(package_dir, ['add', new_ebuild_path])
Chris Sosa9ba47752012-02-27 15:27:37 -0800404 if stable_candidate and not stable_candidate.IsSticky():
David Zeuthen665d3132014-08-25 15:27:02 -0400405 git.RunGit(package_dir, ['rm', stable_candidate.ebuild_path])
Chris Sosadad0d322011-01-31 16:37:33 -0800406
Alex Deymo075c2292014-09-04 18:31:50 -0700407 portage_util.EBuild.CommitChange(
David Zeuthen665d3132014-08-25 15:27:02 -0400408 _GIT_COMMIT_MESSAGE % {'chrome_pn': chrome_pn,
409 'chrome_rev': chrome_rev,
Mike Frysinger2ebe3732012-05-08 17:04:12 -0400410 'chrome_version': chrome_version},
David Zeuthen665d3132014-08-25 15:27:02 -0400411 package_dir)
Chris Sosadad0d322011-01-31 16:37:33 -0800412
Chris Sosadad0d322011-01-31 16:37:33 -0800413 return '%s-%s' % (new_ebuild.package, new_ebuild.version)
414
415
Mike Frysingera13c04f2016-09-01 00:35:17 -0400416def GetParser():
417 """Return a command line parser."""
418 parser = commandline.ArgumentParser(description=__doc__)
419 parser.add_argument('-b', '--boards')
420 parser.add_argument('-c', '--chrome_url',
421 default=constants.CHROMIUM_GOB_URL)
422 parser.add_argument('-f', '--force_version',
423 help='Chrome version or git revision hash to use')
424 parser.add_argument('-s', '--srcroot',
425 default=os.path.join(os.environ['HOME'], 'trunk', 'src'),
426 help='Path to the src directory')
427 parser.add_argument('-t', '--tracking_branch', default='cros/master',
428 help='Branch we are tracking changes against')
429 parser.add_argument('revision', choices=constants.VALID_CHROME_REVISIONS)
430 return parser
Chris Sosadad0d322011-01-31 16:37:33 -0800431
Chris Sosadad0d322011-01-31 16:37:33 -0800432
Mike Frysingera13c04f2016-09-01 00:35:17 -0400433def main(argv):
434 parser = GetParser()
435 options = parser.parse_args(argv)
436 options.Freeze()
437 chrome_rev = options.revision
438
439 if options.force_version and chrome_rev not in (constants.CHROME_REV_SPEC,
440 constants.CHROME_REV_LATEST):
David Jamesfb160012014-07-01 10:00:57 -0700441 parser.error('--force_version is not compatible with the %r '
Mike Frysingera13c04f2016-09-01 00:35:17 -0400442 'option.' % (chrome_rev,))
David Jamesfb160012014-07-01 10:00:57 -0700443
David Zeuthen665d3132014-08-25 15:27:02 -0400444 overlay_dir = os.path.abspath(_OVERLAY_DIR % {'srcroot': options.srcroot})
445 chrome_package_dir = os.path.join(overlay_dir, constants.CHROME_CP)
Chris Sosadad0d322011-01-31 16:37:33 -0800446 version_to_uprev = None
Chris Sosa9ba47752012-02-27 15:27:37 -0800447 sticky_branch = None
Chris Sosadad0d322011-01-31 16:37:33 -0800448
David Zeuthen665d3132014-08-25 15:27:02 -0400449 (unstable_ebuild, stable_ebuilds) = FindChromeCandidates(chrome_package_dir)
Chris Sosadad0d322011-01-31 16:37:33 -0800450
Peter Mayo177500f2011-09-09 17:25:23 -0400451 if chrome_rev == constants.CHROME_REV_LOCAL:
452 if 'CHROME_ROOT' in os.environ:
453 chrome_root = os.environ['CHROME_ROOT']
454 else:
455 chrome_root = os.path.join(os.environ['HOME'], 'chrome_root')
456
457 version_to_uprev = _GetTipOfTrunkVersionFile(chrome_root)
Ralph Nathan03047282015-03-23 11:09:32 -0700458 logging.info('Using local source, versioning is untrustworthy.')
petermayo@chromium.org163b3372011-09-12 02:06:05 -0400459 elif chrome_rev == constants.CHROME_REV_SPEC:
David Jamesfb160012014-07-01 10:00:57 -0700460 if '.' in options.force_version:
461 version_to_uprev = options.force_version
462 else:
463 commit_to_use = options.force_version
464 if '@' in commit_to_use:
Stefan Zagerd49d9ff2014-08-15 21:33:37 -0700465 commit_to_use = commit_to_use.rpartition('@')[2]
David Jamesfb160012014-07-01 10:00:57 -0700466 version_to_uprev = _GetSpecificVersionUrl(options.chrome_url,
467 commit_to_use)
Peter Mayo177500f2011-09-09 17:25:23 -0400468 elif chrome_rev == constants.CHROME_REV_TOT:
Stefan Zagerd49d9ff2014-08-15 21:33:37 -0700469 commit_to_use = gob_util.GetTipOfTrunkRevision(options.chrome_url)
petermayo@chromium.org163b3372011-09-12 02:06:05 -0400470 version_to_uprev = _GetSpecificVersionUrl(options.chrome_url,
471 commit_to_use)
Ryan Cuic6e097d2011-06-16 12:23:14 -0700472 elif chrome_rev == constants.CHROME_REV_LATEST:
David James9a5980e2014-07-16 09:37:00 -0700473 if options.force_version:
474 if '.' not in options.force_version:
475 parser.error('%s only accepts released Chrome versions, not SVN or '
476 'Git revisions.' % (chrome_rev,))
477 version_to_uprev = options.force_version
478 else:
479 version_to_uprev = GetLatestRelease(options.chrome_url)
Chris Sosadad0d322011-01-31 16:37:33 -0800480 else:
Chris Sosa9ba47752012-02-27 15:27:37 -0800481 sticky_ebuild = _GetStickyEBuild(stable_ebuilds)
482 sticky_version = sticky_ebuild.chrome_version
483 sticky_branch = sticky_version.rpartition('.')[0]
Yu-Ju Hong39806322014-06-24 16:46:32 -0700484 version_to_uprev = GetLatestRelease(options.chrome_url, sticky_branch)
Chris Sosadad0d322011-01-31 16:37:33 -0800485
486 stable_candidate = FindChromeUprevCandidate(stable_ebuilds, chrome_rev,
487 sticky_branch)
488
489 if stable_candidate:
Lann Martinffb95162018-08-28 12:02:54 -0600490 logging.info('Stable candidate found %s', stable_candidate)
Chris Sosadad0d322011-01-31 16:37:33 -0800491 else:
Ralph Nathan03047282015-03-23 11:09:32 -0700492 logging.info('No stable candidate found.')
Chris Sosadad0d322011-01-31 16:37:33 -0800493
Chris Sosa8049f3b2011-05-02 20:09:28 -0700494 tracking_branch = 'remotes/m/%s' % os.path.basename(options.tracking_branch)
David Zeuthen665d3132014-08-25 15:27:02 -0400495 existing_branch = git.GetCurrentBranch(chrome_package_dir)
Ryan Cui05a31ba2011-05-31 17:47:37 -0700496 work_branch = cros_mark_as_stable.GitBranch(constants.STABLE_EBUILD_BRANCH,
David Zeuthen665d3132014-08-25 15:27:02 -0400497 tracking_branch,
498 chrome_package_dir)
Chris Sosadad0d322011-01-31 16:37:33 -0800499 work_branch.CreateBranch()
David Jamesd6708c02012-03-22 10:49:15 -0700500
501 # In the case of uprevving overlays that have patches applied to them,
502 # include the patched changes in the stabilizing branch.
503 if existing_branch:
David Zeuthen665d3132014-08-25 15:27:02 -0400504 git.RunGit(chrome_package_dir, ['rebase', existing_branch])
David Jamesd6708c02012-03-22 10:49:15 -0700505
Chris Sosadad0d322011-01-31 16:37:33 -0800506 chrome_version_atom = MarkChromeEBuildAsStable(
David Zeuthen665d3132014-08-25 15:27:02 -0400507 stable_candidate, unstable_ebuild, 'chromeos-chrome', chrome_rev,
Mike Frysinger93ad2262018-08-30 18:42:14 -0400508 version_to_uprev, chrome_package_dir)
Yu-Ju Hong078c9ec2014-08-06 18:25:16 -0700509 if chrome_version_atom:
510 if options.boards:
David James96c2c992015-07-14 10:21:50 -0700511 cros_mark_as_stable.CleanStalePackages(options.srcroot,
512 options.boards.split(':'),
Yu-Ju Hong078c9ec2014-08-06 18:25:16 -0700513 [chrome_version_atom])
David Zeuthen665d3132014-08-25 15:27:02 -0400514
515 # If we did rev Chrome, now is a good time to uprev other packages.
516 for other_ebuild in constants.OTHER_CHROME_PACKAGES:
517 other_ebuild_name = os.path.basename(other_ebuild)
518 other_package_dir = os.path.join(overlay_dir, other_ebuild)
519 (other_unstable_ebuild, other_stable_ebuilds) = FindChromeCandidates(
520 other_package_dir)
521 other_stable_candidate = FindChromeUprevCandidate(other_stable_ebuilds,
522 chrome_rev,
523 sticky_branch)
524 revved_atom = MarkChromeEBuildAsStable(other_stable_candidate,
525 other_unstable_ebuild,
526 other_ebuild_name,
527 chrome_rev, version_to_uprev,
Mike Frysinger93ad2262018-08-30 18:42:14 -0400528 other_package_dir)
David Zeuthen665d3132014-08-25 15:27:02 -0400529 if revved_atom and options.boards:
David James96c2c992015-07-14 10:21:50 -0700530 cros_mark_as_stable.CleanStalePackages(options.srcroot,
531 options.boards.split(':'),
David Zeuthen665d3132014-08-25 15:27:02 -0400532 [revved_atom])
533
534 # Explicit print to communicate to caller.
535 if chrome_version_atom:
Mike Frysinger383367e2014-09-16 15:06:17 -0400536 print('CHROME_VERSION_ATOM=%s' % chrome_version_atom)