libv8 5.1.281.59.1 → 5.2.361.43.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (127) hide show
  1. checksums.yaml +4 -4
  2. data/.travis.yml +0 -7
  3. data/CHANGELOG.md +9 -1
  4. data/README.md +41 -23
  5. data/Rakefile +1 -1
  6. data/ext/libv8/builder.rb +1 -1
  7. data/ext/libv8/compiler/apple_llvm.rb +5 -4
  8. data/ext/libv8/compiler/clang.rb +5 -4
  9. data/ext/libv8/compiler/gcc.rb +5 -4
  10. data/ext/libv8/compiler/generic_compiler.rb +11 -1
  11. data/lib/libv8/version.rb +1 -1
  12. data/patches/0001-Build-a-standalone-static-library.patch +26 -0
  13. data/patches/{0002-Disable-building-tests.patch → 0002-Don-t-compile-unnecessary-stuff.patch} +31 -34
  14. data/patches/0003-Use-the-fPIC-flag-for-the-static-library.patch +10 -10
  15. data/patches/0004-Reinterpret-thread-hash-for-FreeBSD-too.patch +25 -0
  16. data/release/armhf-linux/Vagrantfile +95 -0
  17. data/release/armhf-linux/initrd.img +0 -0
  18. data/release/armhf-linux/vmlinuz +0 -0
  19. data/release/{x86_64-freebsd10 → x86_64-freebsd-10}/Vagrantfile +3 -1
  20. data/spec/compiler/apple_llvm_spec.rb +10 -3
  21. data/spec/compiler/clang_spec.rb +7 -0
  22. data/spec/compiler_spec.rb +1 -1
  23. data/spec/support/compiler_helpers.rb +3 -1
  24. data/vendor/depot_tools/{README → README.md} +33 -12
  25. data/vendor/depot_tools/checkout.py +7 -2
  26. data/vendor/depot_tools/cit.py +51 -13
  27. data/vendor/depot_tools/cpplint.py +27 -5
  28. data/vendor/depot_tools/git_cl.py +370 -290
  29. data/vendor/depot_tools/git_common.py +133 -28
  30. data/vendor/depot_tools/git_drover.py +29 -2
  31. data/vendor/depot_tools/git_map.py +2 -2
  32. data/vendor/depot_tools/git_map_branches.py +9 -5
  33. data/vendor/depot_tools/git_rebase_update.py +3 -3
  34. data/vendor/depot_tools/git_upstream_diff.py +1 -1
  35. data/vendor/depot_tools/infra/config/OWNERS +1 -0
  36. data/vendor/depot_tools/infra/config/cq.cfg +8 -3
  37. data/vendor/depot_tools/infra/config/recipes.cfg +1 -1
  38. data/vendor/depot_tools/man/html/depot_tools.html +10 -2
  39. data/vendor/depot_tools/man/html/depot_tools_tutorial.html +14 -15
  40. data/vendor/depot_tools/man/html/git-auto-svn.html +2 -2
  41. data/vendor/depot_tools/man/html/git-cherry-pick-upload.html +2 -11
  42. data/vendor/depot_tools/man/html/git-drover.html +19 -17
  43. data/vendor/depot_tools/man/html/git-footers.html +2 -2
  44. data/vendor/depot_tools/man/html/git-freeze.html +17 -4
  45. data/vendor/depot_tools/man/html/git-hyper-blame.html +2 -2
  46. data/vendor/depot_tools/man/html/git-map-branches.html +2 -2
  47. data/vendor/depot_tools/man/html/git-map.html +3 -3
  48. data/vendor/depot_tools/man/html/git-mark-merge-base.html +2 -2
  49. data/vendor/depot_tools/man/html/git-nav-downstream.html +7 -7
  50. data/vendor/depot_tools/man/html/git-nav-upstream.html +4 -4
  51. data/vendor/depot_tools/man/html/git-new-branch.html +2 -2
  52. data/vendor/depot_tools/man/html/git-rebase-update.html +2 -2
  53. data/vendor/depot_tools/man/html/git-rename-branch.html +2 -2
  54. data/vendor/depot_tools/man/html/git-reparent-branch.html +2 -2
  55. data/vendor/depot_tools/man/html/git-retry.html +2 -2
  56. data/vendor/depot_tools/man/html/git-squash-branch.html +4 -4
  57. data/vendor/depot_tools/man/html/git-thaw.html +2 -2
  58. data/vendor/depot_tools/man/html/git-upstream-diff.html +2 -2
  59. data/vendor/depot_tools/man/man1/git-auto-svn.1 +4 -4
  60. data/vendor/depot_tools/man/man1/git-cherry-pick-upload.1 +5 -14
  61. data/vendor/depot_tools/man/man1/git-drover.1 +21 -19
  62. data/vendor/depot_tools/man/man1/git-footers.1 +5 -5
  63. data/vendor/depot_tools/man/man1/git-freeze.1 +12 -6
  64. data/vendor/depot_tools/man/man1/git-hyper-blame.1 +4 -4
  65. data/vendor/depot_tools/man/man1/git-map-branches.1 +5 -7
  66. data/vendor/depot_tools/man/man1/git-map.1 +5 -5
  67. data/vendor/depot_tools/man/man1/git-mark-merge-base.1 +4 -4
  68. data/vendor/depot_tools/man/man1/git-nav-downstream.1 +9 -9
  69. data/vendor/depot_tools/man/man1/git-nav-upstream.1 +6 -6
  70. data/vendor/depot_tools/man/man1/git-new-branch.1 +4 -4
  71. data/vendor/depot_tools/man/man1/git-rebase-update.1 +4 -4
  72. data/vendor/depot_tools/man/man1/git-rename-branch.1 +4 -4
  73. data/vendor/depot_tools/man/man1/git-reparent-branch.1 +4 -4
  74. data/vendor/depot_tools/man/man1/git-retry.1 +4 -4
  75. data/vendor/depot_tools/man/man1/git-squash-branch.1 +6 -6
  76. data/vendor/depot_tools/man/man1/git-thaw.1 +4 -4
  77. data/vendor/depot_tools/man/man1/git-upstream-diff.1 +4 -4
  78. data/vendor/depot_tools/man/man7/depot_tools.7 +9 -4
  79. data/vendor/depot_tools/man/man7/depot_tools_tutorial.7 +14 -15
  80. data/vendor/depot_tools/man/src/depot_tools_tutorial.txt +1 -2
  81. data/vendor/depot_tools/man/src/git-freeze.txt +15 -0
  82. data/vendor/depot_tools/man/src/make_docs.sh +4 -4
  83. data/vendor/depot_tools/owners.py +50 -46
  84. data/vendor/depot_tools/owners_finder.py +6 -19
  85. data/vendor/depot_tools/presubmit_canned_checks.py +2 -1
  86. data/vendor/depot_tools/presubmit_support.py +8 -10
  87. data/vendor/depot_tools/recipe_modules/bot_update/api.py +69 -55
  88. data/vendor/depot_tools/recipe_modules/bot_update/example.expected/tryjob_fail.json +1 -0
  89. data/vendor/depot_tools/recipe_modules/bot_update/example.expected/tryjob_fail_patch.json +1 -0
  90. data/vendor/depot_tools/recipe_modules/bot_update/example.expected/tryjob_fail_patch_download.json +1 -0
  91. data/vendor/depot_tools/recipe_modules/bot_update/resources/bot_update.py +2 -0
  92. data/vendor/depot_tools/recipe_modules/gclient/api.py +0 -17
  93. data/vendor/depot_tools/recipe_modules/gclient/config.py +9 -8
  94. data/vendor/depot_tools/recipe_modules/gclient/example.py +1 -1
  95. data/vendor/depot_tools/recipe_modules/git/api.py +20 -4
  96. data/vendor/depot_tools/recipe_modules/git/example.expected/can_fail_build.json +1 -0
  97. data/vendor/depot_tools/recipe_modules/git/example.expected/count-objects_with_bad_output_fails_build.json +1 -0
  98. data/vendor/depot_tools/recipe_modules/git/example.expected/git-cache-checkout.json +189 -0
  99. data/vendor/depot_tools/recipe_modules/git/example.expected/platform_win.json +2 -1
  100. data/vendor/depot_tools/recipe_modules/git/example.expected/rebase_failed.json +1 -0
  101. data/vendor/depot_tools/recipe_modules/git/example.py +6 -1
  102. data/vendor/depot_tools/recipe_modules/git_cl/api.py +13 -0
  103. data/vendor/depot_tools/recipe_modules/git_cl/example.expected/basic.json +17 -0
  104. data/vendor/depot_tools/recipe_modules/git_cl/example.py +3 -0
  105. data/vendor/depot_tools/recipe_modules/infra_paths/example.expected/paths_swarmbucket_linux.json +14 -0
  106. data/vendor/depot_tools/recipe_modules/infra_paths/example.expected/paths_swarmbucket_mac.json +14 -0
  107. data/vendor/depot_tools/recipe_modules/infra_paths/example.expected/paths_swarmbucket_win.json +14 -0
  108. data/vendor/depot_tools/recipe_modules/infra_paths/example.py +1 -1
  109. data/vendor/depot_tools/recipe_modules/infra_paths/path_config.py +23 -10
  110. data/vendor/depot_tools/recipe_modules/tryserver/api.py +5 -3
  111. data/vendor/depot_tools/recipe_modules/tryserver/example.expected/with_git_patch.json +1 -0
  112. data/vendor/depot_tools/recipe_modules/tryserver/example.expected/with_rietveld_patch.json +1 -0
  113. data/vendor/depot_tools/recipe_modules/tryserver/example.expected/with_rietveld_patch_new.json +1 -0
  114. data/vendor/depot_tools/recipe_modules/tryserver/example.expected/with_svn_patch.json +1 -0
  115. data/vendor/depot_tools/recipe_modules/tryserver/example.expected/with_wrong_patch.json +3 -1
  116. data/vendor/depot_tools/recipe_modules/tryserver/example.expected/with_wrong_patch_new.json +3 -1
  117. data/vendor/depot_tools/recipes.py +56 -27
  118. data/vendor/depot_tools/rietveld.py +10 -0
  119. data/vendor/depot_tools/third_party/httplib2/README.chromium +3 -3
  120. data/vendor/depot_tools/third_party/httplib2/__init__.py +31 -15
  121. data/vendor/depot_tools/third_party/upload.py +54 -45
  122. data/vendor/depot_tools/update_depot_tools +16 -70
  123. data/vendor/depot_tools/update_depot_tools.bat +4 -18
  124. data/vendor/depot_tools/win_toolchain/get_toolchain_if_necessary.py +10 -6
  125. metadata +15 -8
  126. data/patches/0001-Build-standalone-static-library.patch +0 -26
  127. data/vendor/depot_tools/git_utils/git-tree-prune +0 -122
@@ -7,11 +7,12 @@
7
7
 
8
8
  """A git-command for integrating reviews on Rietveld and Gerrit."""
9
9
 
10
+ from __future__ import print_function
11
+
10
12
  from distutils.version import LooseVersion
11
13
  from multiprocessing.pool import ThreadPool
12
14
  import base64
13
15
  import collections
14
- import glob
15
16
  import httplib
16
17
  import json
17
18
  import logging
@@ -60,8 +61,9 @@ import subcommand
60
61
  import subprocess2
61
62
  import watchlists
62
63
 
63
- __version__ = '1.0'
64
+ __version__ = '2.0'
64
65
 
66
+ COMMIT_BOT_EMAIL = 'commit-bot@chromium.org'
65
67
  DEFAULT_SERVER = 'https://codereview.appspot.com'
66
68
  POSTUPSTREAM_HOOK_PATTERN = '.git/hooks/post-cl-%s'
67
69
  DESCRIPTION_BACKUP_FILE = '~/.git_cl_description_backup'
@@ -83,7 +85,7 @@ settings = None
83
85
 
84
86
 
85
87
  def DieWithError(message):
86
- print >> sys.stderr, message
88
+ print(message, file=sys.stderr)
87
89
  sys.exit(1)
88
90
 
89
91
 
@@ -366,7 +368,7 @@ def trigger_try_jobs(auth_config, changelist, options, masters, category):
366
368
  )
367
369
  print_text.append('To see results here, run: git cl try-results')
368
370
  print_text.append('To see results in browser, run: git cl web')
369
- print '\n'.join(print_text)
371
+ print('\n'.join(print_text))
370
372
 
371
373
 
372
374
  def fetch_try_jobs(auth_config, changelist, options):
@@ -380,9 +382,9 @@ def fetch_try_jobs(auth_config, changelist, options):
380
382
  if authenticator.has_cached_credentials():
381
383
  http = authenticator.authorize(httplib2.Http())
382
384
  else:
383
- print ('Warning: Some results might be missing because %s' %
384
- # Get the message on how to login.
385
- auth.LoginRequiredError(rietveld_host).message)
385
+ print('Warning: Some results might be missing because %s' %
386
+ # Get the message on how to login.
387
+ (auth.LoginRequiredError(rietveld_host).message,))
386
388
  http = httplib2.Http()
387
389
 
388
390
  http.force_exception_to_status_code = True
@@ -411,7 +413,7 @@ def fetch_try_jobs(auth_config, changelist, options):
411
413
  def print_tryjobs(options, builds):
412
414
  """Prints nicely result of fetch_try_jobs."""
413
415
  if not builds:
414
- print 'No tryjobs scheduled'
416
+ print('No tryjobs scheduled')
415
417
  return
416
418
 
417
419
  # Make a copy, because we'll be modifying builds dictionary.
@@ -426,8 +428,8 @@ def print_tryjobs(options, builds):
426
428
  parameters = json.loads(b['parameters_json'])
427
429
  name = parameters['builder_name']
428
430
  except (ValueError, KeyError) as error:
429
- print 'WARNING: failed to get builder name for build %s: %s' % (
430
- b['id'], error)
431
+ print('WARNING: failed to get builder name for build %s: %s' % (
432
+ b['id'], error))
431
433
  name = None
432
434
  builder_names_cache[b['id']] = name
433
435
  return name
@@ -467,9 +469,9 @@ def print_tryjobs(options, builds):
467
469
  builds.pop(b['id'])
468
470
  result.append(b)
469
471
  if result:
470
- print colorize(title)
472
+ print(colorize(title))
471
473
  for b in sorted(result, key=sort_key):
472
- print ' ', colorize('\t'.join(map(str, f(b))))
474
+ print(' ', colorize('\t'.join(map(str, f(b)))))
473
475
 
474
476
  total = len(builds)
475
477
  pop(status='COMPLETED', result='SUCCESS',
@@ -504,7 +506,7 @@ def print_tryjobs(options, builds):
504
506
  pop(title='Other:',
505
507
  f=lambda b: (get_name(b), 'id=%s' % b['id']))
506
508
  assert len(builds) == 0
507
- print 'Total: %d tryjobs' % total
509
+ print('Total: %d tryjobs' % total)
508
510
 
509
511
 
510
512
  def MatchSvnGlob(url, base_url, glob_spec, allow_wildcards):
@@ -768,11 +770,28 @@ class Settings(object):
768
770
  def GetSquashGerritUploads(self):
769
771
  """Return true if uploads to Gerrit should be squashed by default."""
770
772
  if self.squash_gerrit_uploads is None:
771
- self.squash_gerrit_uploads = (
772
- RunGit(['config', '--bool', 'gerrit.squash-uploads'],
773
- error_ok=True).strip() == 'true')
773
+ self.squash_gerrit_uploads = self.GetSquashGerritUploadsOverride()
774
+ if self.squash_gerrit_uploads is None:
775
+ # Default is squash now (http://crbug.com/611892#c23).
776
+ self.squash_gerrit_uploads = not (
777
+ RunGit(['config', '--bool', 'gerrit.squash-uploads'],
778
+ error_ok=True).strip() == 'false')
774
779
  return self.squash_gerrit_uploads
775
780
 
781
+ def GetSquashGerritUploadsOverride(self):
782
+ """Return True or False if codereview.settings should be overridden.
783
+
784
+ Returns None if no override has been defined.
785
+ """
786
+ # See also http://crbug.com/611892#c23
787
+ result = RunGit(['config', '--bool', 'gerrit.override-squash-uploads'],
788
+ error_ok=True).strip()
789
+ if result == 'true':
790
+ return True
791
+ if result == 'false':
792
+ return False
793
+ return None
794
+
776
795
  def GetGerritSkipEnsureAuthenticated(self):
777
796
  """Return True if EnsureAuthenticated should not be done for Gerrit
778
797
  uploads."""
@@ -1121,20 +1140,18 @@ class Changelist(object):
1121
1140
 
1122
1141
  if upstream_git_obj is None:
1123
1142
  if self.GetBranch() is None:
1124
- print >> sys.stderr, (
1125
- 'ERROR: unable to determine current branch (detached HEAD?)')
1143
+ print('ERROR: unable to determine current branch (detached HEAD?)',
1144
+ file=sys.stderr)
1126
1145
  else:
1127
- print >> sys.stderr, (
1128
- 'ERROR: no upstream branch')
1146
+ print('ERROR: no upstream branch', file=sys.stderr)
1129
1147
  return False
1130
1148
 
1131
1149
  # Verify the commit we're diffing against is in our current branch.
1132
1150
  upstream_sha = RunGit(['rev-parse', '--verify', upstream_git_obj]).strip()
1133
1151
  common_ancestor = RunGit(['merge-base', upstream_sha, 'HEAD']).strip()
1134
1152
  if upstream_sha != common_ancestor:
1135
- print >> sys.stderr, (
1136
- 'ERROR: %s is not in the current branch. You may need to rebase '
1137
- 'your tracking branch' % upstream_sha)
1153
+ print('ERROR: %s is not in the current branch. You may need to rebase '
1154
+ 'your tracking branch' % upstream_sha, file=sys.stderr)
1138
1155
  return False
1139
1156
 
1140
1157
  # List the commits inside the diff, and verify they are all local.
@@ -1150,13 +1167,13 @@ class Changelist(object):
1150
1167
 
1151
1168
  common_commits = set(commits_in_diff) & set(commits_in_remote)
1152
1169
  if common_commits:
1153
- print >> sys.stderr, (
1154
- 'ERROR: Your diff contains %d commits already in %s.\n'
1155
- 'Run "git log --oneline %s..HEAD" to get a list of commits in '
1156
- 'the diff. If you are using a custom git flow, you can override'
1157
- ' the reference used for this check with "git config '
1158
- 'gitcl.remotebranch <git-ref>".' % (
1159
- len(common_commits), remote_branch, upstream_git_obj))
1170
+ print('ERROR: Your diff contains %d commits already in %s.\n'
1171
+ 'Run "git log --oneline %s..HEAD" to get a list of commits in '
1172
+ 'the diff. If you are using a custom git flow, you can override'
1173
+ ' the reference used for this check with "git config '
1174
+ 'gitcl.remotebranch <git-ref>".' % (
1175
+ len(common_commits), remote_branch, upstream_git_obj),
1176
+ file=sys.stderr)
1160
1177
  return False
1161
1178
  return True
1162
1179
 
@@ -1323,7 +1340,7 @@ class Changelist(object):
1323
1340
  default_presubmit=None, may_prompt=may_prompt,
1324
1341
  rietveld_obj=self._codereview_impl.GetRieveldObjForPresubmit(),
1325
1342
  gerrit_obj=self._codereview_impl.GetGerritObjForPresubmit())
1326
- except presubmit_support.PresubmitFailure, e:
1343
+ except presubmit_support.PresubmitFailure as e:
1327
1344
  DieWithError(
1328
1345
  ('%s\nMaybe your depot_tools is out of date?\n'
1329
1346
  'If all fails, contact maruel@') % e)
@@ -1389,17 +1406,22 @@ class Changelist(object):
1389
1406
  local_patchset = self.GetPatchset()
1390
1407
  if (latest_patchset and local_patchset and
1391
1408
  local_patchset != latest_patchset):
1392
- print ('The last upload made from this repository was patchset #%d but '
1393
- 'the most recent patchset on the server is #%d.'
1394
- % (local_patchset, latest_patchset))
1395
- print ('Uploading will still work, but if you\'ve uploaded to this '
1396
- 'issue from another machine or branch the patch you\'re '
1397
- 'uploading now might not include those changes.')
1409
+ print('The last upload made from this repository was patchset #%d but '
1410
+ 'the most recent patchset on the server is #%d.'
1411
+ % (local_patchset, latest_patchset))
1412
+ print('Uploading will still work, but if you\'ve uploaded to this '
1413
+ 'issue from another machine or branch the patch you\'re '
1414
+ 'uploading now might not include those changes.')
1398
1415
  ask_for_data('About to upload; enter to confirm.')
1399
1416
 
1400
1417
  print_stats(options.similarity, options.find_copies, git_diff_args)
1401
1418
  ret = self.CMDUploadChange(options, git_diff_args, change)
1402
1419
  if not ret:
1420
+ if options.use_commit_queue:
1421
+ self.SetCQState(_CQState.COMMIT)
1422
+ elif options.cq_dry_run:
1423
+ self.SetCQState(_CQState.DRY_RUN)
1424
+
1403
1425
  git_set_branch_value('last-upload-hash',
1404
1426
  RunGit(['rev-parse', 'HEAD']).strip())
1405
1427
  # Run post upload hooks, if specified.
@@ -1413,10 +1435,10 @@ class Changelist(object):
1413
1435
 
1414
1436
  # Upload all dependencies if specified.
1415
1437
  if options.dependencies:
1416
- print
1417
- print '--dependencies has been specified.'
1418
- print 'All dependent local branches will be re-uploaded.'
1419
- print
1438
+ print()
1439
+ print('--dependencies has been specified.')
1440
+ print('All dependent local branches will be re-uploaded.')
1441
+ print()
1420
1442
  # Remove the dependencies flag from args so that we do not end up in a
1421
1443
  # loop.
1422
1444
  orig_args.remove('--dependencies')
@@ -1577,7 +1599,8 @@ class _RietveldChangelistImpl(_ChangelistCodereviewBase):
1577
1599
  def __init__(self, changelist, auth_config=None, rietveld_server=None):
1578
1600
  super(_RietveldChangelistImpl, self).__init__(changelist)
1579
1601
  assert settings, 'must be initialized in _ChangelistCodereviewBase'
1580
- settings.GetDefaultServerUrl()
1602
+ if not rietveld_server:
1603
+ settings.GetDefaultServerUrl()
1581
1604
 
1582
1605
  self._rietveld_server = rietveld_server
1583
1606
  self._auth_config = auth_config
@@ -1625,9 +1648,8 @@ class _RietveldChangelistImpl(_ChangelistCodereviewBase):
1625
1648
  DieWithError(
1626
1649
  '\nFailed to fetch issue description. HTTP error %d' % e.code)
1627
1650
  except urllib2.URLError as e:
1628
- print >> sys.stderr, (
1629
- 'Warning: Failed to retrieve CL description due to network '
1630
- 'failure.')
1651
+ print('Warning: Failed to retrieve CL description due to network '
1652
+ 'failure.', file=sys.stderr)
1631
1653
  return ''
1632
1654
 
1633
1655
  def GetMostRecentPatchset(self):
@@ -1691,11 +1713,23 @@ class _RietveldChangelistImpl(_ChangelistCodereviewBase):
1691
1713
 
1692
1714
  messages = props.get('messages') or []
1693
1715
 
1716
+ # Skip CQ messages that don't require owner's action.
1717
+ while messages and messages[-1]['sender'] == COMMIT_BOT_EMAIL:
1718
+ if 'Dry run:' in messages[-1]['text']:
1719
+ messages.pop()
1720
+ elif 'The CQ bit was unchecked' in messages[-1]['text']:
1721
+ # This message always follows prior messages from CQ,
1722
+ # so skip this too.
1723
+ messages.pop()
1724
+ else:
1725
+ # This is probably a CQ messages warranting user attention.
1726
+ break
1727
+
1694
1728
  if not messages:
1695
1729
  # No message was sent.
1696
1730
  return 'unsent'
1697
1731
  if messages[-1]['sender'] != props.get('owner_email'):
1698
- # Non-LGTM reply from non-owner
1732
+ # Non-LGTM reply from non-owner and not CQ bot.
1699
1733
  return 'reply'
1700
1734
  return 'waiting'
1701
1735
 
@@ -1707,13 +1741,19 @@ class _RietveldChangelistImpl(_ChangelistCodereviewBase):
1707
1741
  return self.RpcServer().close_issue(self.GetIssue())
1708
1742
 
1709
1743
  def SetFlag(self, flag, value):
1710
- """Patchset must match."""
1744
+ return self.SetFlags({flag: value})
1745
+
1746
+ def SetFlags(self, flags):
1747
+ """Sets flags on this CL/patchset in Rietveld.
1748
+
1749
+ The latest patchset in Rietveld must be the same as latest known locally.
1750
+ """
1711
1751
  if not self.GetPatchset():
1712
1752
  DieWithError('The patchset needs to match. Send another patchset.')
1713
1753
  try:
1714
- return self.RpcServer().set_flag(
1715
- self.GetIssue(), self.GetPatchset(), flag, value)
1716
- except urllib2.HTTPError, e:
1754
+ return self.RpcServer().set_flags(
1755
+ self.GetIssue(), self.GetPatchset(), flags)
1756
+ except urllib2.HTTPError as e:
1717
1757
  if e.code == 404:
1718
1758
  DieWithError('The issue %s doesn\'t exist.' % self.GetIssue())
1719
1759
  if e.code == 403:
@@ -1761,9 +1801,10 @@ class _RietveldChangelistImpl(_ChangelistCodereviewBase):
1761
1801
  if new_state == _CQState.COMMIT:
1762
1802
  self.SetFlag('commit', '1')
1763
1803
  elif new_state == _CQState.NONE:
1764
- self.SetFlag('commit', '0')
1804
+ self.SetFlags({'commit': '0', 'cq_dry_run': '0'})
1765
1805
  else:
1766
- raise NotImplementedError()
1806
+ assert new_state == _CQState.DRY_RUN
1807
+ self.SetFlags({'commit': '1', 'cq_dry_run': '1'})
1767
1808
 
1768
1809
 
1769
1810
  def CMDPatchWithParsedIssue(self, parsed_issue_arg, reject, nocommit,
@@ -1819,7 +1860,7 @@ class _RietveldChangelistImpl(_ChangelistCodereviewBase):
1819
1860
  subprocess2.check_call(cmd, env=GetNoGitPagerEnv(),
1820
1861
  stdin=patch_data, stdout=subprocess2.VOID)
1821
1862
  except subprocess2.CalledProcessError:
1822
- print 'Failed to apply the patch'
1863
+ print('Failed to apply the patch')
1823
1864
  return 1
1824
1865
 
1825
1866
  # If we had an issue, commit the current state and register the issue.
@@ -1830,9 +1871,9 @@ class _RietveldChangelistImpl(_ChangelistCodereviewBase):
1830
1871
  % {'i': self.GetIssue(), 'p': patchset})])
1831
1872
  self.SetIssue(self.GetIssue())
1832
1873
  self.SetPatchset(patchset)
1833
- print "Committed patch locally."
1874
+ print('Committed patch locally.')
1834
1875
  else:
1835
- print "Patch applied to index."
1876
+ print('Patch applied to index.')
1836
1877
  return 0
1837
1878
 
1838
1879
  @staticmethod
@@ -1869,15 +1910,15 @@ class _RietveldChangelistImpl(_ChangelistCodereviewBase):
1869
1910
  upload_args.extend(['--email', options.email])
1870
1911
 
1871
1912
  if self.GetIssue():
1872
- if options.title:
1913
+ if options.title is not None:
1873
1914
  upload_args.extend(['--title', options.title])
1874
1915
  if options.message:
1875
1916
  upload_args.extend(['--message', options.message])
1876
1917
  upload_args.extend(['--issue', str(self.GetIssue())])
1877
- print ('This branch is associated with issue %s. '
1878
- 'Adding patch to that issue.' % self.GetIssue())
1918
+ print('This branch is associated with issue %s. '
1919
+ 'Adding patch to that issue.' % self.GetIssue())
1879
1920
  else:
1880
- if options.title:
1921
+ if options.title is not None:
1881
1922
  upload_args.extend(['--title', options.title])
1882
1923
  message = (options.title or options.message or
1883
1924
  CreateDescriptionFromLog(args))
@@ -1887,10 +1928,10 @@ class _RietveldChangelistImpl(_ChangelistCodereviewBase):
1887
1928
  options.tbr_owners,
1888
1929
  change)
1889
1930
  if not options.force:
1890
- change_desc.prompt()
1931
+ change_desc.prompt(bug=options.bug)
1891
1932
 
1892
1933
  if not change_desc.description:
1893
- print "Description is empty; aborting."
1934
+ print('Description is empty; aborting.')
1894
1935
  return 1
1895
1936
 
1896
1937
  upload_args.extend(['--message', change_desc.description])
@@ -1948,10 +1989,10 @@ class _RietveldChangelistImpl(_ChangelistCodereviewBase):
1948
1989
  # A local branch is being tracked.
1949
1990
  local_branch = upstream_branch
1950
1991
  if settings.GetIsSkipDependencyUpload(local_branch):
1951
- print
1952
- print ('Skipping dependency patchset upload because git config '
1953
- 'branch.%s.skip-deps-uploads is set to True.' % local_branch)
1954
- print
1992
+ print()
1993
+ print('Skipping dependency patchset upload because git config '
1994
+ 'branch.%s.skip-deps-uploads is set to True.' % local_branch)
1995
+ print()
1955
1996
  else:
1956
1997
  auth_config = auth.extract_auth_config_from_options(options)
1957
1998
  branch_cl = Changelist(branchref='refs/heads/'+local_branch,
@@ -1975,9 +2016,6 @@ class _RietveldChangelistImpl(_ChangelistCodereviewBase):
1975
2016
  if project:
1976
2017
  upload_args.extend(['--project', project])
1977
2018
 
1978
- if options.cq_dry_run:
1979
- upload_args.extend(['--cq_dry_run'])
1980
-
1981
2019
  try:
1982
2020
  upload_args = ['upload'] + upload_args + args
1983
2021
  logging.info('upload.RealMain(%s)', upload_args)
@@ -2001,9 +2039,6 @@ class _RietveldChangelistImpl(_ChangelistCodereviewBase):
2001
2039
  if not self.GetIssue():
2002
2040
  self.SetIssue(issue)
2003
2041
  self.SetPatchset(patchset)
2004
-
2005
- if options.use_commit_queue:
2006
- self.SetCQState(_CQState.COMMIT)
2007
2042
  return 0
2008
2043
 
2009
2044
 
@@ -2019,6 +2054,15 @@ class _GerritChangelistImpl(_ChangelistCodereviewBase):
2019
2054
  def _GetGerritHost(self):
2020
2055
  # Lazy load of configs.
2021
2056
  self.GetCodereviewServer()
2057
+ if self._gerrit_host and '.' not in self._gerrit_host:
2058
+ # Abbreviated domain like "chromium" instead of chromium.googlesource.com.
2059
+ # This happens for internal stuff http://crbug.com/614312.
2060
+ parsed = urlparse.urlparse(self.GetRemoteUrl())
2061
+ if parsed.scheme == 'sso':
2062
+ print('WARNING: using non https URLs for remote is likely broken\n'
2063
+ ' Your current remote is: %s' % self.GetRemoteUrl())
2064
+ self._gerrit_host = '%s.googlesource.com' % self._gerrit_host
2065
+ self._gerrit_server = 'https://%s' % self._gerrit_host
2022
2066
  return self._gerrit_host
2023
2067
 
2024
2068
  def _GetGitHost(self):
@@ -2225,6 +2269,14 @@ class _GerritChangelistImpl(_ChangelistCodereviewBase):
2225
2269
  def CMDLand(self, force, bypass_hooks, verbose):
2226
2270
  if git_common.is_dirty_git_tree('land'):
2227
2271
  return 1
2272
+ detail = self._GetChangeDetail(['CURRENT_REVISION', 'LABELS'])
2273
+ if u'Commit-Queue' in detail.get('labels', {}):
2274
+ if not force:
2275
+ ask_for_data('\nIt seems this repository has a Commit Queue, '
2276
+ 'which can test and land changes for you. '
2277
+ 'Are you sure you wish to bypass it?\n'
2278
+ 'Press Enter to continue, Ctrl+C to abort.')
2279
+
2228
2280
  differs = True
2229
2281
  last_upload = RunGit(['config',
2230
2282
  'branch.%s.gerritsquashhash' % self.GetBranch()],
@@ -2233,7 +2285,6 @@ class _GerritChangelistImpl(_ChangelistCodereviewBase):
2233
2285
  if not last_upload or RunGit(['diff', last_upload]).strip():
2234
2286
  print('WARNING: some changes from local branch haven\'t been uploaded')
2235
2287
  else:
2236
- detail = self._GetChangeDetail(['CURRENT_REVISION'])
2237
2288
  if detail['current_revision'] == last_upload:
2238
2289
  differs = False
2239
2290
  else:
@@ -2339,8 +2390,13 @@ class _GerritChangelistImpl(_ChangelistCodereviewBase):
2339
2390
  """Upload the current branch to Gerrit."""
2340
2391
  if options.squash and options.no_squash:
2341
2392
  DieWithError('Can only use one of --squash or --no-squash')
2342
- options.squash = ((settings.GetSquashGerritUploads() or options.squash) and
2343
- not options.no_squash)
2393
+
2394
+ if not options.squash and not options.no_squash:
2395
+ # Load default for user, repo, squash=true, in this order.
2396
+ options.squash = settings.GetSquashGerritUploads()
2397
+ elif options.no_squash:
2398
+ options.squash = False
2399
+
2344
2400
  # We assume the remote called "origin" is the one we want.
2345
2401
  # It is probably not worthwhile to support different workflows.
2346
2402
  gerrit_remote = 'origin'
@@ -2351,37 +2407,6 @@ class _GerritChangelistImpl(_ChangelistCodereviewBase):
2351
2407
 
2352
2408
  if options.squash:
2353
2409
  self._GerritCommitMsgHookCheck(offer_removal=not options.force)
2354
- if not self.GetIssue():
2355
- # TODO(tandrii): deperecate this after 2016Q2. Backwards compatibility
2356
- # with shadow branch, which used to contain change-id for a given
2357
- # branch, using which we can fetch actual issue number and set it as the
2358
- # property of the branch, which is the new way.
2359
- message = RunGitSilent([
2360
- 'show', '--format=%B', '-s',
2361
- 'refs/heads/git_cl_uploads/%s' % self.GetBranch()])
2362
- if message:
2363
- change_ids = git_footers.get_footer_change_id(message.strip())
2364
- if change_ids and len(change_ids) == 1:
2365
- details = self._GetChangeDetail(issue=change_ids[0])
2366
- if details:
2367
- print('WARNING: found old upload in branch git_cl_uploads/%s '
2368
- 'corresponding to issue %s' %
2369
- (self.GetBranch(), details['_number']))
2370
- self.SetIssue(details['_number'])
2371
- if not self.GetIssue():
2372
- DieWithError(
2373
- '\n' # For readability of the blob below.
2374
- 'Found old upload in branch git_cl_uploads/%s, '
2375
- 'but failed to find corresponding Gerrit issue.\n'
2376
- 'If you know the issue number, set it manually first:\n'
2377
- ' git cl issue 123456\n'
2378
- 'If you intended to upload this CL as new issue, '
2379
- 'just delete or rename the old upload branch:\n'
2380
- ' git rename-branch git_cl_uploads/%s old_upload-%s\n'
2381
- 'After that, please run git cl upload again.' %
2382
- tuple([self.GetBranch()] * 3))
2383
- # End of backwards compatability.
2384
-
2385
2410
  if self.GetIssue():
2386
2411
  # Try to get the message from a previous upload.
2387
2412
  message = self.GetDescription()
@@ -2415,7 +2440,7 @@ class _GerritChangelistImpl(_ChangelistCodereviewBase):
2415
2440
  ask_for_data('Press enter to edit now, Ctrl+C to abort')
2416
2441
  if not options.force:
2417
2442
  change_desc = ChangeDescription(message)
2418
- change_desc.prompt()
2443
+ change_desc.prompt(bug=options.bug)
2419
2444
  message = change_desc.description
2420
2445
  if not message:
2421
2446
  DieWithError("Description is empty. Aborting...")
@@ -2428,7 +2453,7 @@ class _GerritChangelistImpl(_ChangelistCodereviewBase):
2428
2453
  change_desc = ChangeDescription(
2429
2454
  options.message or CreateDescriptionFromLog(args))
2430
2455
  if not options.force:
2431
- change_desc.prompt()
2456
+ change_desc.prompt(bug=options.bug)
2432
2457
  if not change_desc.description:
2433
2458
  DieWithError("Description is empty. Aborting...")
2434
2459
  message = change_desc.description
@@ -2457,11 +2482,10 @@ class _GerritChangelistImpl(_ChangelistCodereviewBase):
2457
2482
  # Gerrit will create additional CLs when uploading.
2458
2483
  if not parent or (RunGitSilent(['rev-parse', upstream_branch + ':']) !=
2459
2484
  RunGitSilent(['rev-parse', parent + ':'])):
2460
- # TODO(tandrii): remove "old depot_tools" part on April 12, 2016.
2461
2485
  DieWithError(
2462
2486
  'Upload upstream branch %s first.\n'
2463
- 'Note: maybe you\'ve uploaded it with --no-squash or with an old '
2464
- 'version of depot_tools. If so, then re-upload it with:\n'
2487
+ 'Note: maybe you\'ve uploaded it with --no-squash. '
2488
+ 'If so, then re-upload it with:\n'
2465
2489
  ' git cl upload --squash\n' % upstream_branch_name)
2466
2490
  else:
2467
2491
  parent = self.GetCommonAncestorWithUpstream()
@@ -2563,15 +2587,13 @@ class _GerritChangelistImpl(_ChangelistCodereviewBase):
2563
2587
  RunGit(git_command)
2564
2588
  new_log_desc = CreateDescriptionFromLog(args)
2565
2589
  if git_footers.get_footer_change_id(new_log_desc):
2566
- print 'git-cl: Added Change-Id to commit message.'
2590
+ print('git-cl: Added Change-Id to commit message.')
2567
2591
  return new_log_desc
2568
2592
  else:
2569
2593
  DieWithError('ERROR: Gerrit commit-msg hook not installed.')
2570
2594
 
2571
2595
  def SetCQState(self, new_state):
2572
2596
  """Sets the Commit-Queue label assuming canonical CQ config for Gerrit."""
2573
- # TODO(tandrii): maybe allow configurability in codereview.settings or by
2574
- # self-discovery of label config for this CL using REST API.
2575
2597
  vote_map = {
2576
2598
  _CQState.NONE: 0,
2577
2599
  _CQState.DRY_RUN: 1,
@@ -2610,6 +2632,41 @@ def _process_codereview_select_options(parser, options):
2610
2632
  options.forced_codereview = 'rietveld'
2611
2633
 
2612
2634
 
2635
+ def _get_bug_line_values(default_project, bugs):
2636
+ """Given default_project and comma separated list of bugs, yields bug line
2637
+ values.
2638
+
2639
+ Each bug can be either:
2640
+ * a number, which is combined with default_project
2641
+ * string, which is left as is.
2642
+
2643
+ This function may produce more than one line, because bugdroid expects one
2644
+ project per line.
2645
+
2646
+ >>> list(_get_bug_line_values('v8', '123,chromium:789'))
2647
+ ['v8:123', 'chromium:789']
2648
+ """
2649
+ default_bugs = []
2650
+ others = []
2651
+ for bug in bugs.split(','):
2652
+ bug = bug.strip()
2653
+ if bug:
2654
+ try:
2655
+ default_bugs.append(int(bug))
2656
+ except ValueError:
2657
+ others.append(bug)
2658
+
2659
+ if default_bugs:
2660
+ default_bugs = ','.join(map(str, default_bugs))
2661
+ if default_project:
2662
+ yield '%s:%s' % (default_project, default_bugs)
2663
+ else:
2664
+ yield default_bugs
2665
+ for other in sorted(others):
2666
+ # Don't bother finding common prefixes, CLs with >2 bugs are very very rare.
2667
+ yield other
2668
+
2669
+
2613
2670
  class ChangeDescription(object):
2614
2671
  """Contains a parsed form of the change description."""
2615
2672
  R_LINE = r'^[ \t]*(TBR|R)[ \t]*=[ \t]*(.*?)[ \t]*$'
@@ -2663,7 +2720,7 @@ class ChangeDescription(object):
2663
2720
  reviewers.append(name)
2664
2721
  if add_owners_tbr:
2665
2722
  owners_db = owners.Database(change.RepositoryRoot(),
2666
- fopen=file, os_path=os.path, glob=glob.glob)
2723
+ fopen=file, os_path=os.path)
2667
2724
  all_reviewers = set(tbr_names + reviewers)
2668
2725
  missing_files = owners_db.files_not_covered_by(change.LocalPaths(),
2669
2726
  all_reviewers)
@@ -2685,7 +2742,7 @@ class ChangeDescription(object):
2685
2742
  if new_tbr_line:
2686
2743
  self.append_footer(new_tbr_line)
2687
2744
 
2688
- def prompt(self):
2745
+ def prompt(self, bug=None):
2689
2746
  """Asks the user to update the description."""
2690
2747
  self.set_description([
2691
2748
  '# Enter a description of the change.',
@@ -2697,7 +2754,12 @@ class ChangeDescription(object):
2697
2754
 
2698
2755
  regexp = re.compile(self.BUG_LINE)
2699
2756
  if not any((regexp.match(line) for line in self._description_lines)):
2700
- self.append_footer('BUG=%s' % settings.GetBugPrefix())
2757
+ prefix = settings.GetBugPrefix()
2758
+ values = list(_get_bug_line_values(prefix, bug or '')) or [prefix]
2759
+ for value in values:
2760
+ # TODO(tandrii): change this to 'Bug: xxx' to be a proper Gerrit footer.
2761
+ self.append_footer('BUG=%s' % value)
2762
+
2701
2763
  content = gclient_utils.RunEditor(self.description, True,
2702
2764
  git_editor=settings.GetGitEditor())
2703
2765
  if not content:
@@ -2870,10 +2932,6 @@ def DownloadGerritHook(force):
2870
2932
  if not force:
2871
2933
  return
2872
2934
  try:
2873
- print(
2874
- 'WARNING: installing Gerrit commit-msg hook.\n'
2875
- ' This behavior of git cl will soon be disabled.\n'
2876
- ' See bug http://crbug.com/579176.')
2877
2935
  urlretrieve(src, dst)
2878
2936
  if not hasSheBang(dst):
2879
2937
  DieWithError('Not a script: %s\n'
@@ -2969,11 +3027,11 @@ def CMDbaseurl(parser, args):
2969
3027
  branch = ShortBranchName(branchref)
2970
3028
  _, args = parser.parse_args(args)
2971
3029
  if not args:
2972
- print("Current base-url:")
3030
+ print('Current base-url:')
2973
3031
  return RunGit(['config', 'branch.%s.base-url' % branch],
2974
3032
  error_ok=False).strip()
2975
3033
  else:
2976
- print("Setting base-url to %s" % args[0])
3034
+ print('Setting base-url to %s' % args[0])
2977
3035
  return RunGit(['config', 'branch.%s.base-url' % branch, args[0]],
2978
3036
  error_ok=False).strip()
2979
3037
 
@@ -3088,25 +3146,25 @@ def upload_branch_deps(cl, args):
3088
3146
  branch_name, tracked = tokens
3089
3147
  tracked_to_dependents[tracked].append(branch_name)
3090
3148
 
3091
- print
3092
- print 'The dependent local branches of %s are:' % root_branch
3149
+ print()
3150
+ print('The dependent local branches of %s are:' % root_branch)
3093
3151
  dependents = []
3094
3152
  def traverse_dependents_preorder(branch, padding=''):
3095
3153
  dependents_to_process = tracked_to_dependents.get(branch, [])
3096
3154
  padding += ' '
3097
3155
  for dependent in dependents_to_process:
3098
- print '%s%s' % (padding, dependent)
3156
+ print('%s%s' % (padding, dependent))
3099
3157
  dependents.append(dependent)
3100
3158
  traverse_dependents_preorder(dependent, padding)
3101
3159
  traverse_dependents_preorder(root_branch)
3102
- print
3160
+ print()
3103
3161
 
3104
3162
  if not dependents:
3105
- print 'There are no dependent local branches for %s' % root_branch
3163
+ print('There are no dependent local branches for %s' % root_branch)
3106
3164
  return 0
3107
3165
 
3108
- print ('This command will checkout all dependent branches and run '
3109
- '"git cl upload".')
3166
+ print('This command will checkout all dependent branches and run '
3167
+ '"git cl upload".')
3110
3168
  ask_for_data('[Press enter to continue or ctrl-C to quit]')
3111
3169
 
3112
3170
  # Add a default patchset title to all upload calls in Rietveld.
@@ -3118,28 +3176,28 @@ def upload_branch_deps(cl, args):
3118
3176
  # Go through all dependents, checkout the branch and upload.
3119
3177
  try:
3120
3178
  for dependent_branch in dependents:
3121
- print
3122
- print '--------------------------------------'
3123
- print 'Running "git cl upload" from %s:' % dependent_branch
3179
+ print()
3180
+ print('--------------------------------------')
3181
+ print('Running "git cl upload" from %s:' % dependent_branch)
3124
3182
  RunGit(['checkout', '-q', dependent_branch])
3125
- print
3183
+ print()
3126
3184
  try:
3127
3185
  if CMDupload(OptionParser(), args) != 0:
3128
- print 'Upload failed for %s!' % dependent_branch
3186
+ print('Upload failed for %s!' % dependent_branch)
3129
3187
  failures[dependent_branch] = 1
3130
3188
  except: # pylint: disable=W0702
3131
3189
  failures[dependent_branch] = 1
3132
- print
3190
+ print()
3133
3191
  finally:
3134
3192
  # Swap back to the original root branch.
3135
3193
  RunGit(['checkout', '-q', root_branch])
3136
3194
 
3137
- print
3138
- print 'Upload complete for dependent branches!'
3195
+ print()
3196
+ print('Upload complete for dependent branches!')
3139
3197
  for dependent_branch in dependents:
3140
3198
  upload_status = 'failed' if failures.get(dependent_branch) else 'succeeded'
3141
- print ' %s : %s' % (dependent_branch, upload_status)
3142
- print
3199
+ print(' %s : %s' % (dependent_branch, upload_status))
3200
+ print()
3143
3201
 
3144
3202
  return 0
3145
3203
 
@@ -3163,7 +3221,7 @@ def CMDarchive(parser, args):
3163
3221
  if not branches:
3164
3222
  return 0
3165
3223
 
3166
- print 'Finding all branches associated with closed issues...'
3224
+ print('Finding all branches associated with closed issues...')
3167
3225
  changes = [Changelist(branchref=b, auth_config=auth_config)
3168
3226
  for b in branches.splitlines()]
3169
3227
  alignment = max(5, max(len(c.GetBranch()) for c in changes))
@@ -3177,15 +3235,15 @@ def CMDarchive(parser, args):
3177
3235
  proposal.sort()
3178
3236
 
3179
3237
  if not proposal:
3180
- print 'No branches with closed codereview issues found.'
3238
+ print('No branches with closed codereview issues found.')
3181
3239
  return 0
3182
3240
 
3183
3241
  current_branch = GetCurrentBranch()
3184
3242
 
3185
- print '\nBranches with closed issues that will be archived:\n'
3186
- print '%*s | %s' % (alignment, 'Branch name', 'Archival tag name')
3243
+ print('\nBranches with closed issues that will be archived:\n')
3244
+ print('%*s | %s' % (alignment, 'Branch name', 'Archival tag name'))
3187
3245
  for next_item in proposal:
3188
- print '%*s %s' % (alignment, next_item[0], next_item[1])
3246
+ print('%*s %s' % (alignment, next_item[0], next_item[1]))
3189
3247
 
3190
3248
  if any(branch == current_branch for branch, _ in proposal):
3191
3249
  print('You are currently on a branch \'%s\' which is associated with a '
@@ -3195,14 +3253,15 @@ def CMDarchive(parser, args):
3195
3253
  return 1
3196
3254
 
3197
3255
  if not options.force:
3198
- if ask_for_data('\nProceed with deletion (Y/N)? ').lower() != 'y':
3199
- print 'Aborted.'
3256
+ answer = ask_for_data('\nProceed with deletion (Y/n)? ').lower()
3257
+ if answer not in ('y', ''):
3258
+ print('Aborted.')
3200
3259
  return 1
3201
3260
 
3202
3261
  for branch, tagname in proposal:
3203
3262
  RunGit(['tag', tagname, branch])
3204
3263
  RunGit(['branch', '-D', branch])
3205
- print '\nJob\'s done!'
3264
+ print('\nJob\'s done!')
3206
3265
 
3207
3266
  return 0
3208
3267
 
@@ -3237,19 +3296,19 @@ def CMDstatus(parser, args):
3237
3296
  if options.field:
3238
3297
  cl = Changelist(auth_config=auth_config)
3239
3298
  if options.field.startswith('desc'):
3240
- print cl.GetDescription()
3299
+ print(cl.GetDescription())
3241
3300
  elif options.field == 'id':
3242
3301
  issueid = cl.GetIssue()
3243
3302
  if issueid:
3244
- print issueid
3303
+ print(issueid)
3245
3304
  elif options.field == 'patch':
3246
3305
  patchset = cl.GetPatchset()
3247
3306
  if patchset:
3248
- print patchset
3307
+ print(patchset)
3249
3308
  elif options.field == 'url':
3250
3309
  url = cl.GetIssueURL()
3251
3310
  if url:
3252
- print url
3311
+ print(url)
3253
3312
  return 0
3254
3313
 
3255
3314
  branches = RunGit(['for-each-ref', '--format=%(refname)', 'refs/heads'])
@@ -3260,7 +3319,7 @@ def CMDstatus(parser, args):
3260
3319
  changes = [
3261
3320
  Changelist(branchref=b, auth_config=auth_config)
3262
3321
  for b in branches.splitlines()]
3263
- print 'Branches associated with reviews:'
3322
+ print('Branches associated with reviews:')
3264
3323
  output = get_cl_statuses(changes,
3265
3324
  fine_grained=not options.fast,
3266
3325
  max_processes=options.maxjobs)
@@ -3284,21 +3343,21 @@ def CMDstatus(parser, args):
3284
3343
  color = ''
3285
3344
  reset = ''
3286
3345
  status_str = '(%s)' % status if status else ''
3287
- print ' %*s : %s%s %s%s' % (
3346
+ print(' %*s : %s%s %s%s' % (
3288
3347
  alignment, ShortBranchName(branch), color, url,
3289
- status_str, reset)
3348
+ status_str, reset))
3290
3349
 
3291
3350
  cl = Changelist(auth_config=auth_config)
3292
- print
3293
- print 'Current branch:',
3294
- print cl.GetBranch()
3351
+ print()
3352
+ print('Current branch:',)
3353
+ print(cl.GetBranch())
3295
3354
  if not cl.GetIssue():
3296
- print 'No issue assigned.'
3355
+ print('No issue assigned.')
3297
3356
  return 0
3298
- print 'Issue number: %s (%s)' % (cl.GetIssue(), cl.GetIssueURL())
3357
+ print('Issue number: %s (%s)' % (cl.GetIssue(), cl.GetIssueURL()))
3299
3358
  if not options.fast:
3300
- print 'Issue description:'
3301
- print cl.GetDescription(pretty=True)
3359
+ print('Issue description:')
3360
+ print(cl.GetDescription(pretty=True))
3302
3361
  return 0
3303
3362
 
3304
3363
 
@@ -3346,8 +3405,8 @@ def CMDissue(parser, args):
3346
3405
  for issue in args:
3347
3406
  if not issue:
3348
3407
  continue
3349
- print 'Branch for issue number %s: %s' % (
3350
- issue, ', '.join(issue_branch_map.get(int(issue)) or ('None',)))
3408
+ print('Branch for issue number %s: %s' % (
3409
+ issue, ', '.join(issue_branch_map.get(int(issue)) or ('None',))))
3351
3410
  else:
3352
3411
  cl = Changelist(codereview=options.forced_codereview)
3353
3412
  if len(args) > 0:
@@ -3357,7 +3416,7 @@ def CMDissue(parser, args):
3357
3416
  DieWithError('Pass a number to set the issue or none to list it.\n'
3358
3417
  'Maybe you want to run git cl status?')
3359
3418
  cl.SetIssue(issue)
3360
- print 'Issue number: %s (%s)' % (cl.GetIssue(), cl.GetIssueURL())
3419
+ print('Issue number: %s (%s)' % (cl.GetIssue(), cl.GetIssueURL()))
3361
3420
  return 0
3362
3421
 
3363
3422
 
@@ -3406,11 +3465,11 @@ def CMDcomments(parser, args):
3406
3465
  color = Fore.MAGENTA
3407
3466
  else:
3408
3467
  color = Fore.BLUE
3409
- print '\n%s%s %s%s' % (
3468
+ print('\n%s%s %s%s' % (
3410
3469
  color, message['date'].split('.', 1)[0], message['sender'],
3411
- Fore.RESET)
3470
+ Fore.RESET))
3412
3471
  if message['text'].strip():
3413
- print '\n'.join(' ' + l for l in message['text'].splitlines())
3472
+ print('\n'.join(' ' + l for l in message['text'].splitlines()))
3414
3473
  if options.json_file:
3415
3474
  with open(options.json_file, 'wb') as f:
3416
3475
  json.dump(summary, f)
@@ -3432,24 +3491,30 @@ def CMDdescription(parser, args):
3432
3491
 
3433
3492
  target_issue = None
3434
3493
  if len(args) > 0:
3435
- issue_arg = ParseIssueNumberArgument(args[0])
3436
- if not issue_arg.valid:
3494
+ target_issue = ParseIssueNumberArgument(args[0])
3495
+ if not target_issue.valid:
3437
3496
  parser.print_help()
3438
3497
  return 1
3439
- target_issue = issue_arg.issue
3440
3498
 
3441
3499
  auth_config = auth.extract_auth_config_from_options(options)
3442
3500
 
3443
- cl = Changelist(
3444
- auth_config=auth_config, issue=target_issue,
3445
- codereview=options.forced_codereview)
3501
+ kwargs = {
3502
+ 'auth_config': auth_config,
3503
+ 'codereview': options.forced_codereview,
3504
+ }
3505
+ if target_issue:
3506
+ kwargs['issue'] = target_issue.issue
3507
+ if options.forced_codereview == 'rietveld':
3508
+ kwargs['rietveld_server'] = target_issue.hostname
3509
+
3510
+ cl = Changelist(**kwargs)
3446
3511
 
3447
3512
  if not cl.GetIssue():
3448
3513
  DieWithError('This branch has no associated changelist.')
3449
3514
  description = ChangeDescription(cl.GetDescription())
3450
3515
 
3451
3516
  if options.display:
3452
- print description.description
3517
+ print(description.description)
3453
3518
  return 0
3454
3519
 
3455
3520
  if options.new_description:
@@ -3494,7 +3559,7 @@ def CMDlint(parser, args):
3494
3559
  import cpplint
3495
3560
  import cpplint_chromium
3496
3561
  except ImportError:
3497
- print "Your depot_tools is missing cpplint.py and/or cpplint_chromium.py."
3562
+ print('Your depot_tools is missing cpplint.py and/or cpplint_chromium.py.')
3498
3563
  return 1
3499
3564
 
3500
3565
  # Change the current working directory before calling lint so that it
@@ -3506,7 +3571,7 @@ def CMDlint(parser, args):
3506
3571
  change = cl.GetChange(cl.GetCommonAncestorWithUpstream(), None)
3507
3572
  files = [f.LocalPath() for f in change.AffectedFiles()]
3508
3573
  if not files:
3509
- print "Cannot lint an empty CL"
3574
+ print('Cannot lint an empty CL')
3510
3575
  return 1
3511
3576
 
3512
3577
  # Process cpplints arguments if any.
@@ -3521,15 +3586,15 @@ def CMDlint(parser, args):
3521
3586
  for filename in filenames:
3522
3587
  if white_regex.match(filename):
3523
3588
  if black_regex.match(filename):
3524
- print "Ignoring file %s" % filename
3589
+ print('Ignoring file %s' % filename)
3525
3590
  else:
3526
3591
  cpplint.ProcessFile(filename, cpplint._cpplint_state.verbose_level,
3527
3592
  extra_check_functions)
3528
3593
  else:
3529
- print "Skipping file %s" % filename
3594
+ print('Skipping file %s' % filename)
3530
3595
  finally:
3531
3596
  os.chdir(previous_cwd)
3532
- print "Total errors found: %d\n" % cpplint._cpplint_state.error_count
3597
+ print('Total errors found: %d\n' % cpplint._cpplint_state.error_count)
3533
3598
  if cpplint._cpplint_state.error_count != 0:
3534
3599
  return 1
3535
3600
  return 0
@@ -3546,7 +3611,7 @@ def CMDpresubmit(parser, args):
3546
3611
  auth_config = auth.extract_auth_config_from_options(options)
3547
3612
 
3548
3613
  if not options.force and git_common.is_dirty_git_tree('presubmit'):
3549
- print 'use --force to check even if tree is dirty.'
3614
+ print('use --force to check even if tree is dirty.')
3550
3615
  return 1
3551
3616
 
3552
3617
  cl = Changelist(auth_config=auth_config)
@@ -3678,6 +3743,11 @@ def CMDupload(parser, args):
3678
3743
  parser.add_option('-f', action='store_true', dest='force',
3679
3744
  help="force yes to questions (don't prompt)")
3680
3745
  parser.add_option('-m', dest='message', help='message for patchset')
3746
+ parser.add_option('-b', '--bug',
3747
+ help='pre-populate the bug number(s) for this issue. '
3748
+ 'If several, separate with commas')
3749
+ parser.add_option('--message-file', dest='message_file',
3750
+ help='file which contains message for patchset')
3681
3751
  parser.add_option('-t', dest='title',
3682
3752
  help='title for patchset (Rietveld only)')
3683
3753
  parser.add_option('-r', '--reviewers',
@@ -3733,6 +3803,15 @@ def CMDupload(parser, args):
3733
3803
  options.reviewers = cleanup_list(options.reviewers)
3734
3804
  options.cc = cleanup_list(options.cc)
3735
3805
 
3806
+ if options.message_file:
3807
+ if options.message:
3808
+ parser.error('only one of --message and --message-file allowed.')
3809
+ options.message = gclient_utils.FileRead(options.message_file)
3810
+ options.message_file = None
3811
+
3812
+ if options.cq_dry_run and options.use_commit_queue:
3813
+ parser.error('only one of --use-commit-queue and --cq-dry-run allowed.')
3814
+
3736
3815
  # For sanity of test expectations, do this otherwise lazy-loading *now*.
3737
3816
  settings.GetIsGerrit()
3738
3817
 
@@ -3798,16 +3877,16 @@ def SendUpstream(parser, args, cmd):
3798
3877
  current = cl.GetBranch()
3799
3878
  remote, upstream_branch = cl.FetchUpstreamTuple(cl.GetBranch())
3800
3879
  if not settings.GetIsGitSvn() and remote == '.':
3801
- print
3802
- print 'Attempting to push branch %r into another local branch!' % current
3803
- print
3804
- print 'Either reparent this branch on top of origin/master:'
3805
- print ' git reparent-branch --root'
3806
- print
3807
- print 'OR run `git rebase-update` if you think the parent branch is already'
3808
- print 'committed.'
3809
- print
3810
- print ' Current parent: %r' % upstream_branch
3880
+ print()
3881
+ print('Attempting to push branch %r into another local branch!' % current)
3882
+ print()
3883
+ print('Either reparent this branch on top of origin/master:')
3884
+ print(' git reparent-branch --root')
3885
+ print()
3886
+ print('OR run `git rebase-update` if you think the parent branch is ')
3887
+ print('already committed.')
3888
+ print()
3889
+ print(' Current parent: %r' % upstream_branch)
3811
3890
  return 1
3812
3891
 
3813
3892
  if not args or cmd == 'land':
@@ -3816,7 +3895,7 @@ def SendUpstream(parser, args, cmd):
3816
3895
 
3817
3896
  if options.contributor:
3818
3897
  if not re.match('^.*\s<\S+@\S+>$', options.contributor):
3819
- print "Please provide contibutor as 'First Last <email@example.com>'"
3898
+ print("Please provide contibutor as 'First Last <email@example.com>'")
3820
3899
  return 1
3821
3900
 
3822
3901
  base_branch = args[0]
@@ -3830,9 +3909,9 @@ def SendUpstream(parser, args, cmd):
3830
3909
  upstream_commits = RunGit(['rev-list', '^' + cl.GetBranchRef(),
3831
3910
  base_branch]).splitlines()
3832
3911
  if upstream_commits:
3833
- print ('Base branch "%s" has %d commits '
3834
- 'not in this branch.' % (base_branch, len(upstream_commits)))
3835
- print 'Run "git merge %s" before attempting to %s.' % (base_branch, cmd)
3912
+ print('Base branch "%s" has %d commits '
3913
+ 'not in this branch.' % (base_branch, len(upstream_commits)))
3914
+ print('Run "git merge %s" before attempting to %s.' % (base_branch, cmd))
3836
3915
  return 1
3837
3916
 
3838
3917
  # This is the revision `svn dcommit` will commit on top of.
@@ -3850,10 +3929,10 @@ def SendUpstream(parser, args, cmd):
3850
3929
 
3851
3930
  extra_commits = RunGit(['rev-list', '^' + svn_head, base_svn_head])
3852
3931
  if extra_commits:
3853
- print ('This branch has %d additional commits not upstreamed yet.'
3854
- % len(extra_commits.splitlines()))
3855
- print ('Upstream "%s" or rebase this branch on top of the upstream trunk '
3856
- 'before attempting to %s.' % (base_branch, cmd))
3932
+ print('This branch has %d additional commits not upstreamed yet.'
3933
+ % len(extra_commits.splitlines()))
3934
+ print('Upstream "%s" or rebase this branch on top of the upstream trunk '
3935
+ 'before attempting to %s.' % (base_branch, cmd))
3857
3936
  return 1
3858
3937
 
3859
3938
  merge_base = RunGit(['merge-base', base_branch, 'HEAD']).strip()
@@ -3888,8 +3967,8 @@ def SendUpstream(parser, args, cmd):
3888
3967
  if not cl.GetIssue() and options.bypass_hooks:
3889
3968
  change_desc = ChangeDescription(CreateDescriptionFromLog([merge_base]))
3890
3969
  else:
3891
- print 'No description set.'
3892
- print 'Visit %s/edit to set it.' % (cl.GetIssueURL())
3970
+ print('No description set.')
3971
+ print('Visit %s/edit to set it.' % (cl.GetIssueURL()))
3893
3972
  return 1
3894
3973
 
3895
3974
  # Keep a separate copy for the commit message, because the commit message
@@ -4007,7 +4086,7 @@ def SendUpstream(parser, args, cmd):
4007
4086
  RunGit(['branch', '-D', CHERRY_PICK_BRANCH])
4008
4087
 
4009
4088
  if not revision:
4010
- print 'Failed to push. If this persists, please file a bug.'
4089
+ print('Failed to push. If this persists, please file a bug.')
4011
4090
  return 1
4012
4091
 
4013
4092
  killed = False
@@ -4029,8 +4108,8 @@ def SendUpstream(parser, args, cmd):
4029
4108
  'Committed: %s%s' % (viewvc_url, revision))
4030
4109
  elif revision:
4031
4110
  change_desc.append_footer('Committed: %s' % (revision,))
4032
- print ('Closing issue '
4033
- '(you may be prompted for your codereview password)...')
4111
+ print('Closing issue '
4112
+ '(you may be prompted for your codereview password)...')
4034
4113
  cl.UpdateDescription(change_desc.description)
4035
4114
  cl.CloseIssue()
4036
4115
  props = cl.GetIssueProperties()
@@ -4042,14 +4121,12 @@ def SendUpstream(parser, args, cmd):
4042
4121
  else:
4043
4122
  comment += ' (presubmit successful).'
4044
4123
  cl.RpcServer().add_comment(cl.GetIssue(), comment)
4045
- cl.SetIssue(None)
4046
4124
 
4047
4125
  if pushed_to_pending:
4048
4126
  _, branch = cl.FetchUpstreamTuple(cl.GetBranch())
4049
- print 'The commit is in the pending queue (%s).' % pending_ref
4050
- print (
4051
- 'It will show up on %s in ~1 min, once it gets a Cr-Commit-Position '
4052
- 'footer.' % branch)
4127
+ print('The commit is in the pending queue (%s).' % pending_ref)
4128
+ print('It will show up on %s in ~1 min, once it gets a Cr-Commit-Position '
4129
+ 'footer.' % branch)
4053
4130
 
4054
4131
  hook = POSTUPSTREAM_HOOK_PATTERN % cmd
4055
4132
  if os.path.isfile(hook):
@@ -4059,9 +4136,9 @@ def SendUpstream(parser, args, cmd):
4059
4136
 
4060
4137
 
4061
4138
  def WaitForRealCommit(remote, pushed_commit, local_base_ref, real_ref):
4062
- print
4063
- print 'Waiting for commit to be landed on %s...' % real_ref
4064
- print '(If you are impatient, you may Ctrl-C once without harm)'
4139
+ print()
4140
+ print('Waiting for commit to be landed on %s...' % real_ref)
4141
+ print('(If you are impatient, you may Ctrl-C once without harm)')
4065
4142
  target_tree = RunGit(['rev-parse', '%s:' % pushed_commit]).strip()
4066
4143
  current_rev = RunGit(['rev-parse', local_base_ref]).strip()
4067
4144
  mirror = settings.GetGitMirror(remote)
@@ -4079,7 +4156,7 @@ def WaitForRealCommit(remote, pushed_commit, local_base_ref, real_ref):
4079
4156
  commits = RunGit(['rev-list', '%s..%s' % (current_rev, to_rev)])
4080
4157
  for commit in commits.splitlines():
4081
4158
  if RunGit(['rev-parse', '%s:' % commit]).strip() == target_tree:
4082
- print 'Found commit on %s' % real_ref
4159
+ print('Found commit on %s' % real_ref)
4083
4160
  return commit
4084
4161
 
4085
4162
  current_rev = to_rev
@@ -4100,51 +4177,49 @@ def PushToGitPending(remote, pending_ref, upstream_ref):
4100
4177
  attempts_left = max_attempts
4101
4178
  while attempts_left:
4102
4179
  if attempts_left != max_attempts:
4103
- print 'Retrying, %d attempts left...' % (attempts_left - 1,)
4180
+ print('Retrying, %d attempts left...' % (attempts_left - 1,))
4104
4181
  attempts_left -= 1
4105
4182
 
4106
4183
  # Fetch. Retry fetch errors.
4107
- print 'Fetching pending ref %s...' % pending_ref
4184
+ print('Fetching pending ref %s...' % pending_ref)
4108
4185
  code, out = RunGitWithCode(
4109
4186
  ['retry', 'fetch', remote, '+%s:%s' % (pending_ref, local_pending_ref)])
4110
4187
  if code:
4111
- print 'Fetch failed with exit code %d.' % code
4188
+ print('Fetch failed with exit code %d.' % code)
4112
4189
  if out.strip():
4113
- print out.strip()
4190
+ print(out.strip())
4114
4191
  continue
4115
4192
 
4116
4193
  # Try to cherry pick. Abort on merge conflicts.
4117
- print 'Cherry-picking commit on top of pending ref...'
4194
+ print('Cherry-picking commit on top of pending ref...')
4118
4195
  RunGitWithCode(['checkout', local_pending_ref], suppress_stderr=True)
4119
4196
  code, out = RunGitWithCode(['cherry-pick', cherry])
4120
4197
  if code:
4121
- print (
4122
- 'Your patch doesn\'t apply cleanly to ref \'%s\', '
4123
- 'the following files have merge conflicts:' % pending_ref)
4124
- print RunGit(['diff', '--name-status', '--diff-filter=U']).strip()
4125
- print 'Please rebase your patch and try again.'
4198
+ print('Your patch doesn\'t apply cleanly to ref \'%s\', '
4199
+ 'the following files have merge conflicts:' % pending_ref)
4200
+ print(RunGit(['diff', '--name-status', '--diff-filter=U']).strip())
4201
+ print('Please rebase your patch and try again.')
4126
4202
  RunGitWithCode(['cherry-pick', '--abort'])
4127
4203
  return code, out
4128
4204
 
4129
4205
  # Applied cleanly, try to push now. Retry on error (flake or non-ff push).
4130
- print 'Pushing commit to %s... It can take a while.' % pending_ref
4206
+ print('Pushing commit to %s... It can take a while.' % pending_ref)
4131
4207
  code, out = RunGitWithCode(
4132
4208
  ['retry', 'push', '--porcelain', remote, 'HEAD:%s' % pending_ref])
4133
4209
  if code == 0:
4134
4210
  # Success.
4135
- print 'Commit pushed to pending ref successfully!'
4211
+ print('Commit pushed to pending ref successfully!')
4136
4212
  return code, out
4137
4213
 
4138
- print 'Push failed with exit code %d.' % code
4214
+ print('Push failed with exit code %d.' % code)
4139
4215
  if out.strip():
4140
- print out.strip()
4216
+ print(out.strip())
4141
4217
  if IsFatalPushFailure(out):
4142
- print (
4143
- 'Fatal push error. Make sure your .netrc credentials and git '
4144
- 'user.email are correct and you have push access to the repo.')
4218
+ print('Fatal push error. Make sure your .netrc credentials and git '
4219
+ 'user.email are correct and you have push access to the repo.')
4145
4220
  return code, out
4146
4221
 
4147
- print 'All attempts to push to pending ref failed.'
4222
+ print('All attempts to push to pending ref failed.')
4148
4223
  return code, out
4149
4224
 
4150
4225
 
@@ -4173,6 +4248,11 @@ review to be closed, without actually landing upstream. If you choose to
4173
4248
  proceed, please verify that the commit lands upstream as expected."""
4174
4249
  print(message)
4175
4250
  ask_for_data('[Press enter to dcommit or ctrl-C to quit]')
4251
+ # TODO(tandrii): kill this post SVN migration with
4252
+ # https://codereview.chromium.org/2076683002
4253
+ print('WARNING: chrome infrastructure is migrating SVN repos to Git.\n'
4254
+ 'Please let us know of this project you are committing to:'
4255
+ ' http://crbug.com/600451')
4176
4256
  return SendUpstream(parser, args, 'dcommit')
4177
4257
 
4178
4258
 
@@ -4346,12 +4426,12 @@ def CMDtree(parser, args):
4346
4426
  _, args = parser.parse_args(args)
4347
4427
  status = GetTreeStatus()
4348
4428
  if 'unset' == status:
4349
- print 'You must configure your tree status URL by running "git cl config".'
4429
+ print('You must configure your tree status URL by running "git cl config".')
4350
4430
  return 2
4351
4431
 
4352
- print "The tree is %s" % status
4353
- print
4354
- print GetTreeStatusReason()
4432
+ print('The tree is %s' % status)
4433
+ print()
4434
+ print(GetTreeStatusReason())
4355
4435
  if status != 'open':
4356
4436
  return 1
4357
4437
  return 0
@@ -4469,28 +4549,8 @@ def CMDtry(parser, args):
4469
4549
  options.verbose,
4470
4550
  sys.stdout)
4471
4551
 
4472
- if not options.bot:
4473
- # Get try masters from cq.cfg if any.
4474
- # TODO(tandrii): some (but very few) projects store cq.cfg in different
4475
- # location.
4476
- cq_cfg = os.path.join(change.RepositoryRoot(),
4477
- 'infra', 'config', 'cq.cfg')
4478
- if os.path.exists(cq_cfg):
4479
- masters = {}
4480
- cq_masters = commit_queue.get_master_builder_map(
4481
- cq_cfg, include_experimental=False, include_triggered=False)
4482
- for master, builders in cq_masters.iteritems():
4483
- for builder in builders:
4484
- # Skip presubmit builders, because these will fail without LGTM.
4485
- masters.setdefault(master, {})[builder] = ['defaulttests']
4486
- if masters:
4487
- print('Loaded default bots from CQ config (%s)' % cq_cfg)
4488
- return masters
4489
- else:
4490
- print('CQ config exists (%s) but has no try bots listed' % cq_cfg)
4491
-
4492
4552
  if not options.bot:
4493
- parser.error('No default try builder to try, use --bot')
4553
+ return {}
4494
4554
 
4495
4555
  builders_and_tests = {}
4496
4556
  # TODO(machenbach): The old style command-line options don't support
@@ -4515,14 +4575,35 @@ def CMDtry(parser, args):
4515
4575
  return {options.master: builders_and_tests}
4516
4576
 
4517
4577
  masters = GetMasterMap()
4578
+ if not masters:
4579
+ # Default to triggering Dry Run (see http://crbug.com/625697).
4580
+ if options.verbose:
4581
+ print('git cl try with no bots now defaults to CQ Dry Run.')
4582
+ try:
4583
+ cl.SetCQState(_CQState.DRY_RUN)
4584
+ print('scheduled CQ Dry Run on %s' % cl.GetIssueURL())
4585
+ return 0
4586
+ except KeyboardInterrupt:
4587
+ raise
4588
+ except:
4589
+ print('WARNING: failed to trigger CQ Dry Run.\n'
4590
+ 'Either:\n'
4591
+ ' * your project has no CQ\n'
4592
+ ' * you don\'t have permission to trigger Dry Run\n'
4593
+ ' * bug in this code (see stack trace below).\n'
4594
+ 'Consider specifying which bots to trigger manually '
4595
+ 'or asking your project owners for permissions '
4596
+ 'or contacting Chrome Infrastructure team at '
4597
+ 'https://www.chromium.org/infra\n\n')
4598
+ # Still raise exception so that stack trace is printed.
4599
+ raise
4518
4600
 
4519
4601
  for builders in masters.itervalues():
4520
4602
  if any('triggered' in b for b in builders):
4521
- print >> sys.stderr, (
4522
- 'ERROR You are trying to send a job to a triggered bot. This type of'
4523
- ' bot requires an\ninitial job from a parent (usually a builder). '
4524
- 'Instead send your job to the parent.\n'
4525
- 'Bot list: %s' % builders)
4603
+ print('ERROR You are trying to send a job to a triggered bot. This type '
4604
+ 'of bot requires an\ninitial job from a parent (usually a builder).'
4605
+ ' Instead send your job to the parent.\n'
4606
+ 'Bot list: %s' % builders, file=sys.stderr)
4526
4607
  return 1
4527
4608
 
4528
4609
  patchset = cl.GetMostRecentPatchset()
@@ -4537,12 +4618,12 @@ def CMDtry(parser, args):
4537
4618
  try:
4538
4619
  trigger_try_jobs(auth_config, cl, options, masters, 'git_cl_try')
4539
4620
  except BuildbucketResponseException as ex:
4540
- print 'ERROR: %s' % ex
4621
+ print('ERROR: %s' % ex)
4541
4622
  return 1
4542
4623
  except Exception as e:
4543
4624
  stacktrace = (''.join(traceback.format_stack()) + traceback.format_exc())
4544
- print 'ERROR: Exception when trying to trigger tryjobs: %s\n%s' % (
4545
- e, stacktrace)
4625
+ print('ERROR: Exception when trying to trigger tryjobs: %s\n%s' %
4626
+ (e, stacktrace))
4546
4627
  return 1
4547
4628
  else:
4548
4629
  try:
@@ -4558,10 +4639,10 @@ def CMDtry(parser, args):
4558
4639
 
4559
4640
  for (master, builders) in sorted(masters.iteritems()):
4560
4641
  if master:
4561
- print 'Master: %s' % master
4642
+ print('Master: %s' % master)
4562
4643
  length = max(len(builder) for builder in builders)
4563
4644
  for builder in sorted(builders):
4564
- print ' %*s: %s' % (length, builder, ','.join(builders[builder]))
4645
+ print(' %*s: %s' % (length, builder, ','.join(builders[builder])))
4565
4646
  return 0
4566
4647
 
4567
4648
 
@@ -4598,12 +4679,12 @@ def CMDtry_results(parser, args):
4598
4679
  try:
4599
4680
  jobs = fetch_try_jobs(auth_config, cl, options)
4600
4681
  except BuildbucketResponseException as ex:
4601
- print 'Buildbucket error: %s' % ex
4682
+ print('Buildbucket error: %s' % ex)
4602
4683
  return 1
4603
4684
  except Exception as e:
4604
4685
  stacktrace = (''.join(traceback.format_stack()) + traceback.format_exc())
4605
- print 'ERROR: Exception when trying to fetch tryjobs: %s\n%s' % (
4606
- e, stacktrace)
4686
+ print('ERROR: Exception when trying to fetch tryjobs: %s\n%s' %
4687
+ (e, stacktrace))
4607
4688
  return 1
4608
4689
  print_tryjobs(options, jobs)
4609
4690
  return 0
@@ -4622,12 +4703,12 @@ def CMDupstream(parser, args):
4622
4703
  branch = cl.GetBranch()
4623
4704
  RunGit(['branch', '--set-upstream', branch, args[0]])
4624
4705
  cl = Changelist()
4625
- print "Upstream branch set to " + cl.GetUpstreamBranch()
4706
+ print('Upstream branch set to %s' % (cl.GetUpstreamBranch(),))
4626
4707
 
4627
4708
  # Clear configured merge-base, if there is one.
4628
4709
  git_common.remove_merge_base(branch)
4629
4710
  else:
4630
- print cl.GetUpstreamBranch()
4711
+ print(cl.GetUpstreamBranch())
4631
4712
  return 0
4632
4713
 
4633
4714
 
@@ -4639,7 +4720,7 @@ def CMDweb(parser, args):
4639
4720
 
4640
4721
  issue_url = Changelist().GetIssueURL()
4641
4722
  if not issue_url:
4642
- print >> sys.stderr, 'ERROR No issue to open'
4723
+ print('ERROR No issue to open', file=sys.stderr)
4643
4724
  return 1
4644
4725
 
4645
4726
  webbrowser.open(issue_url)
@@ -4662,7 +4743,7 @@ def CMDset_commit(parser, args):
4662
4743
 
4663
4744
  cl = Changelist(auth_config=auth_config)
4664
4745
  if options.clear:
4665
- state = _CQState.CLEAR
4746
+ state = _CQState.NONE
4666
4747
  elif options.dry_run:
4667
4748
  state = _CQState.DRY_RUN
4668
4749
  else:
@@ -4759,7 +4840,7 @@ def CMDowners(parser, args):
4759
4840
  [f.LocalPath() for f in
4760
4841
  cl.GetChange(base_branch, None).AffectedFiles()],
4761
4842
  change.RepositoryRoot(), author,
4762
- fopen=file, os_path=os.path, glob=glob.glob,
4843
+ fopen=file, os_path=os.path,
4763
4844
  disable_color=options.no_color).run()
4764
4845
 
4765
4846
 
@@ -4785,8 +4866,8 @@ def MatchingFileType(file_name, extensions):
4785
4866
  @subcommand.usage('[files or directories to diff]')
4786
4867
  def CMDformat(parser, args):
4787
4868
  """Runs auto-formatting tools (clang-format etc.) on the diff."""
4788
- CLANG_EXTS = ['.cc', '.cpp', '.h', '.mm', '.proto', '.java']
4789
- GN_EXTS = ['.gn', '.gni']
4869
+ CLANG_EXTS = ['.cc', '.cpp', '.h', '.m', '.mm', '.proto', '.java']
4870
+ GN_EXTS = ['.gn', '.gni', '.typemap']
4790
4871
  parser.add_option('--full', action='store_true',
4791
4872
  help='Reformat the full content of all touched files')
4792
4873
  parser.add_option('--dry-run', action='store_true',
@@ -4840,7 +4921,7 @@ def CMDformat(parser, args):
4840
4921
  # Locate the clang-format binary in the checkout
4841
4922
  try:
4842
4923
  clang_format_tool = clang_format.FindClangFormatToolInChromiumTree()
4843
- except clang_format.NotFoundError, e:
4924
+ except clang_format.NotFoundError as e:
4844
4925
  DieWithError(e)
4845
4926
 
4846
4927
  if opts.full:
@@ -4856,7 +4937,7 @@ def CMDformat(parser, args):
4856
4937
  try:
4857
4938
  script = clang_format.FindClangFormatScriptInChromiumTree(
4858
4939
  'clang-format-diff.py')
4859
- except clang_format.NotFoundError, e:
4940
+ except clang_format.NotFoundError as e:
4860
4941
  DieWithError(e)
4861
4942
 
4862
4943
  cmd = [sys.executable, script, '-p0']
@@ -4905,9 +4986,9 @@ def CMDformat(parser, args):
4905
4986
  if opts.dry_run and stdout:
4906
4987
  return_value = 2
4907
4988
  except dart_format.NotFoundError as e:
4908
- print ('Warning: Unable to check Dart code formatting. Dart SDK not ' +
4909
- 'found in this checkout. Files in other languages are still ' +
4910
- 'formatted.')
4989
+ print('Warning: Unable to check Dart code formatting. Dart SDK not '
4990
+ 'found in this checkout. Files in other languages are still '
4991
+ 'formatted.')
4911
4992
 
4912
4993
  # Format GN build files. Always run on full build files for canonical form.
4913
4994
  if gn_diff_files:
@@ -4951,19 +5032,19 @@ def CMDcheckout(parser, args):
4951
5032
  for cls in _CODEREVIEW_IMPLEMENTATIONS.values():
4952
5033
  branches.extend(find_issues(cls.IssueSettingSuffix()))
4953
5034
  if len(branches) == 0:
4954
- print 'No branch found for issue %s.' % target_issue
5035
+ print('No branch found for issue %s.' % target_issue)
4955
5036
  return 1
4956
5037
  if len(branches) == 1:
4957
5038
  RunGit(['checkout', branches[0]])
4958
5039
  else:
4959
- print 'Multiple branches match issue %s:' % target_issue
5040
+ print('Multiple branches match issue %s:' % target_issue)
4960
5041
  for i in range(len(branches)):
4961
- print '%d: %s' % (i, branches[i])
5042
+ print('%d: %s' % (i, branches[i]))
4962
5043
  which = raw_input('Choose by index: ')
4963
5044
  try:
4964
5045
  RunGit(['checkout', branches[int(which)]])
4965
5046
  except (IndexError, ValueError):
4966
- print 'Invalid selection, not checking out any branch.'
5047
+ print('Invalid selection, not checking out any branch.')
4967
5048
  return 1
4968
5049
 
4969
5050
  return 0
@@ -4971,11 +5052,11 @@ def CMDcheckout(parser, args):
4971
5052
 
4972
5053
  def CMDlol(parser, args):
4973
5054
  # This command is intentionally undocumented.
4974
- print zlib.decompress(base64.b64decode(
5055
+ print(zlib.decompress(base64.b64decode(
4975
5056
  'eNptkLEOwyAMRHe+wupCIqW57v0Vq84WqWtXyrcXnCBsmgMJ+/SSAxMZgRB6NzE'
4976
5057
  'E2ObgCKJooYdu4uAQVffUEoE1sRQLxAcqzd7uK2gmStrll1ucV3uZyaY5sXyDd9'
4977
5058
  'JAnN+lAXsOMJ90GANAi43mq5/VeeacylKVgi8o6F1SC63FxnagHfJUTfUYdCR/W'
4978
- 'Ofe+0dHL7PicpytKP750Fh1q2qnLVof4w8OZWNY'))
5059
+ 'Ofe+0dHL7PicpytKP750Fh1q2qnLVof4w8OZWNY')))
4979
5060
  return 0
4980
5061
 
4981
5062
 
@@ -4997,9 +5078,8 @@ class OptionParser(optparse.OptionParser):
4997
5078
 
4998
5079
  def main(argv):
4999
5080
  if sys.hexversion < 0x02060000:
5000
- print >> sys.stderr, (
5001
- '\nYour python version %s is unsupported, please upgrade.\n' %
5002
- sys.version.split(' ', 1)[0])
5081
+ print('\nYour python version %s is unsupported, please upgrade.\n' %
5082
+ (sys.version.split(' ', 1)[0],), file=sys.stderr)
5003
5083
  return 2
5004
5084
 
5005
5085
  # Reload settings.
@@ -5012,7 +5092,7 @@ def main(argv):
5012
5092
  return dispatcher.execute(OptionParser(), argv)
5013
5093
  except auth.AuthenticationError as e:
5014
5094
  DieWithError(str(e))
5015
- except urllib2.HTTPError, e:
5095
+ except urllib2.HTTPError as e:
5016
5096
  if e.code != 500:
5017
5097
  raise
5018
5098
  DieWithError(