1#!/usr/bin/env python2 2# 3# Copyright 2010 The Chromium OS Authors. All rights reserved. 4# Use of this source code is governed by a BSD-style license that can be 5# found in the LICENSE file. 6"""Script to checkout the ChromeOS source. 7 8This script sets up the ChromeOS source in the given directory, matching a 9particular release of ChromeOS. 10""" 11 12from __future__ import print_function 13 14__author__ = 'raymes@google.com (Raymes Khoury)' 15 16from datetime import datetime 17 18import argparse 19import os 20import pickle 21import sys 22import tempfile 23import time 24from cros_utils import command_executer 25from cros_utils import logger 26from cros_utils import manifest_versions 27 28GCLIENT_FILE = """solutions = [ 29 { "name" : "CHROME_DEPS", 30 "url" : 31 "svn://svn.chromium.org/chrome-internal/trunk/tools/buildspec/releases/%s", 32 "custom_deps" : { 33 "src/third_party/WebKit/LayoutTests": None, 34 "src-pdf": None, 35 "src/pdf": None, 36 }, 37 "safesync_url": "", 38 }, 39] 40""" 41 42# List of stable versions used for common team image 43# Sheriff must update this list when a new common version becomes available 44COMMON_VERSIONS = '/home/mobiletc-prebuild/common_images/common_list.txt' 45 46 47def Usage(parser): 48 parser.print_help() 49 sys.exit(0) 50 51 52# Get version spec file, either from "paladin" or "buildspec" directory. 53def GetVersionSpecFile(version, versions_git): 54 temp = tempfile.mkdtemp() 55 commands = ['cd {0}'.format(temp), \ 56 'git clone {0} versions'.format(versions_git)] 57 cmd_executer = command_executer.GetCommandExecuter() 58 ret = cmd_executer.RunCommands(commands) 59 err_msg = None 60 if ret: 61 err_msg = 'Failed to checkout versions_git - {0}'.format(versions_git) 62 ret = None 63 else: 64 v, m = version.split('.', 1) 65 paladin_spec = 'paladin/buildspecs/{0}/{1}.xml'.format(v, m) 66 generic_spec = 'buildspecs/{0}/{1}.xml'.format(v, m) 67 paladin_path = '{0}/versions/{1}'.format(temp, paladin_spec) 68 generic_path = '{0}/versions/{1}'.format(temp, generic_spec) 69 if os.path.exists(paladin_path): 70 ret = paladin_spec 71 elif os.path.exists(generic_path): 72 ret = generic_spec 73 else: 74 err_msg = 'No spec found for version {0}'.format(version) 75 ret = None 76 # Fall through to clean up. 77 78 commands = ['rm -rf {0}'.format(temp)] 79 cmd_executer.RunCommands(commands) 80 if err_msg: 81 logger.GetLogger().LogFatal(err_msg) 82 return ret 83 84 85def TimeToCommonVersion(timestamp): 86 """Convert timestamp to common image version.""" 87 tdt = datetime.fromtimestamp(float(timestamp)) 88 with open(COMMON_VERSIONS, 'r') as f: 89 common_list = pickle.load(f) 90 for sv in common_list: 91 sdt = datetime.strptime(sv['date'], '%Y-%m-%d %H:%M:%S.%f') 92 if tdt >= sdt: 93 return '%s.%s' % (sv['chrome_major_version'], sv['chromeos_version']) 94 # should never reach here 95 logger.GetLogger().LogFatal('No common version for timestamp') 96 return None 97 98 99def Main(argv): 100 """Checkout the ChromeOS source.""" 101 parser = argparse.ArgumentParser() 102 parser.add_argument( 103 '--dir', 104 dest='directory', 105 help='Target directory for ChromeOS installation.') 106 parser.add_argument( 107 '--version', 108 dest='version', 109 default='latest_lkgm', 110 help="""ChromeOS version. Can be: 111(1) A release version in the format: 'X.X.X.X' 112(2) 'top' for top of trunk 113(3) 'latest_lkgm' for the latest lkgm version 114(4) 'lkgm' for the lkgm release before timestamp 115(5) 'latest_common' for the latest team common stable version 116(6) 'common' for the team common stable version before timestamp 117Default is 'latest_lkgm'.""") 118 parser.add_argument( 119 '--timestamp', 120 dest='timestamp', 121 default=None, 122 help='Timestamps in epoch format. It will check out the' 123 'latest LKGM or the latest COMMON version of ChromeOS' 124 ' before the timestamp. Use in combination with' 125 ' --version=latest or --version=common. Use ' 126 '"date -d <date string> +%s" to find epoch time') 127 parser.add_argument( 128 '--minilayout', 129 dest='minilayout', 130 default=False, 131 action='store_true', 132 help='Whether to checkout the minilayout (smaller ' 133 'checkout).') 134 parser.add_argument( 135 '--jobs', '-j', dest='jobs', help='Number of repo sync threads to use.') 136 parser.add_argument( 137 '--public', 138 '-p', 139 dest='public', 140 default=False, 141 action='store_true', 142 help='Use the public checkout instead of the private ' 143 'one.') 144 145 options = parser.parse_args(argv) 146 147 if not options.version: 148 parser.print_help() 149 logger.GetLogger().LogFatal('No version specified.') 150 else: 151 version = options.version.strip() 152 153 if not options.timestamp: 154 timestamp = '' 155 else: 156 timestamp = options.timestamp.strip() 157 if version not in ('lkgm', 'common'): 158 parser.print_help() 159 logger.GetLogger().LogFatal('timestamp option only applies for ' 160 "versions \"lkgm\" or \"common\"") 161 162 if not options.directory: 163 parser.print_help() 164 logger.GetLogger().LogFatal('No directory specified.') 165 166 directory = options.directory.strip() 167 168 if options.public: 169 manifest_repo = 'https://chromium.googlesource.com/chromiumos/manifest.git' 170 versions_repo = ('https://chromium.googlesource.com/' 171 'chromiumos/manifest-versions.git') 172 else: 173 manifest_repo = ('https://chrome-internal.googlesource.com/chromeos/' 174 'manifest-internal.git') 175 versions_repo = ('https://chrome-internal.googlesource.com/chromeos/' 176 'manifest-versions.git') 177 178 if version == 'top': 179 init = 'repo init -u %s' % manifest_repo 180 elif version == 'latest_lkgm': 181 manifests = manifest_versions.ManifestVersions() 182 version = manifests.TimeToVersionChromeOS(time.mktime(time.gmtime())) 183 version, manifest = version.split('.', 1) 184 logger.GetLogger().LogOutput('found version %s.%s for latest LKGM' % 185 (version, manifest)) 186 init = ('repo init -u %s -m paladin/buildspecs/%s/%s.xml' % 187 (versions_repo, version, manifest)) 188 del manifests 189 elif version == 'lkgm': 190 if not timestamp: 191 parser.print_help() 192 logger.GetLogger().LogFatal('No timestamp specified for version=lkgm') 193 manifests = manifest_versions.ManifestVersions() 194 version = manifests.TimeToVersion(timestamp) 195 version, manifest = version.split('.', 1) 196 logger.GetLogger().LogOutput( 197 'found version %s.%s for LKGM at timestamp %s' % (version, manifest, 198 timestamp)) 199 init = ('repo init -u %s -m paladin/buildspecs/%s/%s.xml' % 200 (versions_repo, version, manifest)) 201 del manifests 202 elif version == 'latest_common': 203 version = TimeToCommonVersion(time.mktime(time.gmtime())) 204 version, manifest = version.split('.', 1) 205 logger.GetLogger().LogOutput('found version %s.%s for latest Common image' % 206 (version, manifest)) 207 init = ('repo init -u %s -m buildspecs/%s/%s.xml' % (versions_repo, version, 208 manifest)) 209 elif version == 'common': 210 if not timestamp: 211 parser.print_help() 212 logger.GetLogger().LogFatal('No timestamp specified for version=lkgm') 213 version = TimeToCommonVersion(timestamp) 214 version, manifest = version.split('.', 1) 215 logger.GetLogger().LogOutput('found version %s.%s for latest common image ' 216 'at timestamp %s' % (version, manifest, 217 timestamp)) 218 init = ('repo init -u %s -m buildspecs/%s/%s.xml' % (versions_repo, version, 219 manifest)) 220 else: 221 # user specified a specific version number 222 version_spec_file = GetVersionSpecFile(version, versions_repo) 223 if not version_spec_file: 224 return 1 225 init = 'repo init -u %s -m %s' % (versions_repo, version_spec_file) 226 227 if options.minilayout: 228 init += ' -g minilayout' 229 230 init += ' --repo-url=https://chromium.googlesource.com/external/repo.git' 231 232 # crosbug#31837 - "Sources need to be world-readable to properly 233 # function inside the chroot" 234 sync = 'umask 022 && repo sync' 235 if options.jobs: 236 sync += ' -j %s' % options.jobs 237 238 commands = ['mkdir -p %s' % directory, 'cd %s' % directory, init, sync] 239 cmd_executer = command_executer.GetCommandExecuter() 240 ret = cmd_executer.RunCommands(commands) 241 if ret: 242 return ret 243 244 return cmd_executer.RunCommand( 245 'git ls-remote ' 246 'https://chrome-internal.googlesource.com/chrome/src-internal.git ' 247 '> /dev/null') 248 249 250if __name__ == '__main__': 251 retval = Main(sys.argv[1:]) 252 sys.exit(retval) 253