Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(438)

Side by Side Diff: gmerge

Issue 6305004: Modify devserver and gmerge to be friendlier (Closed) Base URL: ssh://git@gitrw.chromium.org:9222/dev-util.git@master
Patch Set: Numerous code review fixes. Added --USE flag as well Created 9 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « devserver.py ('k') | gmerge_test.py » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 #!/bin/bash 1 #!/usr/bin/env python
2 2
3 # Copyright (c) 2009-2010 The Chromium OS Authors. All rights reserved. 3 # Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
4 # Use of this source code is governed by a BSD-style license that can be 4 # Use of this source code is governed by a BSD-style license that can be
5 # found in the LICENSE file. 5 # found in the LICENSE file.
6 6
7 # Prints the arguments and dies. 7 """Build packages on a host machine, then install them on the local target.
8 print_and_die() {
9 echo $*
10 exit 1
11 }
12 8
13 # Set up PORTAGE variables to be rooted in /usr/local/portage. 9 Contacts a devserver (trunk/src/platform/dev/devserver.py) and
14 setup_portage_vars() { 10 requests that it build a package, then performs a binary install of
15 export PORTDIR=/usr/local/portage 11 that package on the local machine.
16 export PKGDIR=/usr/local/portage 12 """
17 export DISTDIR=/usr/local/portage/distfiles
18 export PORTAGE_BINHOST="${DEVKIT_URL}/static/pkgroot/${BOARD_NAME}/packages"
19 export PORTAGE_TMPDIR=/tmp
20 export CONFIG_PROTECT="-*"
21 export FEATURES="-sandbox"
22 # Accept keywords only for stable ebuilds by default.
23 [ -z "$ACCEPT_KEYWORDS" ] && ACCEPT_KEYWORDS="arm x86 ~arm ~x86"
24 export ACCEPT_KEYWORDS
25 export ROOT=/
26 }
27 13
28 # Prompts the user to change the root to /usr/local. 14 import optparse
29 change_portage_root() { 15 import os
30 read -p "Do you wish to install this program into /usr/local? (Y/n) " input 16 import shutil
31 if [[ ${input} = [Nn]* ]]; then 17 import subprocess
32 echo "Better safe than sorry." 18 import sys
33 exit 1 19 import urllib
34 fi 20 import urllib2
35 export ROOT=/usr/local
36 }
37 21
38 set -e
39 22
40 # Get variables for the devserver from the lsb-release file. 23 class GMerger(object):
41 DEVKIT_URL=$(grep ^CHROMEOS_DEVSERVER /etc/lsb-release | cut -d = -f 2-) 24 """emerges a package from the devserver.
42 BOARD_NAME=$(grep ^CHROMEOS_RELEASE_BOARD /etc/lsb-release | cut -d = -f 2-)
43 [ -z "${BOARD_NAME}" ] && print_and_die "No board in /etc/lsb-release"
44 [ -z "${DEVKIT_URL}" ] && print_and_die "No dev server url in /etc/lsb-release"
45 25
46 setup_portage_vars 26 NB: Must be instantiated using with, e.g.:
27 with GMerger(open('/etc/lsb-release').readlines()) as merger:
28 in order to remount /tmp as executable.
29 """
47 30
48 # Determine if we should send a build command to the devserver. 31 def __init__(self, lsb_release_lines):
49 BUILD=1 32 self.lsb_release = self.ParseLsbRelease(lsb_release_lines)
50 if [ x$1 == x-n ]; then 33 try:
51 BUILD=0 34 self.devkit_url = self.lsb_release['CHROMEOS_DEVSERVER']
52 shift 35 self.board_name = self.lsb_release['CHROMEOS_RELEASE_BOARD']
53 fi 36 except KeyError, e:
37 sys.exit('Could not find /etc/lsb_release value: ' + e)
54 38
55 # Package name is the last argument. 39 def RemountOrChangeRoot(self, environ):
56 # TODO(sosa) - Support multiple packages. 40 """Remount the root filesystem rw; install into /usr/local if this fails."""
57 PACKAGE_NAME=${!#} 41 rc = subprocess.call(['mount', '-o', 'remount,rw', '/'])
42 if rc == 0:
43 return
44 answer = raw_input(
45 'Could not mount / as writable. Install into /usr/local? (Y/n)')
46 if answer[0] not in 'Yy':
47 sys.exit('Better safe than sorry.')
48 environ['ROOT'] = '/usr/local'
58 49
59 # If no package name is provided skip to emerge options. 50 def ParseLsbRelease(self, lsb_release_lines):
60 [[ ${PACKAGE_NAME} == -* ]] && BUILD=0 51 """Convert a list of KEY=VALUE lines to a dictionary."""
52 partitioned_lines = [line.rstrip().partition('=')
53 for line in lsb_release_lines]
54 return dict([(fields[0], fields[2]) for fields in partitioned_lines])
61 55
62 mount -o remount,rw / || change_portage_root 56 def SetupPortageEnvironment(self, environ):
57 """Setup portage to use stateful partition and fetch from dev server."""
58 environ.update({
59 'PORTDIR': '/usr/local/portage',
60 'PKGDIR': '/usr/local/portage',
61 'DISTDIR': '/usr/local/portage/distfiles',
62 'PORTAGE_BINHOST': '%s/static/pkgroot/%s/packages' % (
63 self.devkit_url, self.board_name),
64 'PORTAGE_TMPDIR': '/tmp',
65 'CONFIG_PROTECT': '-*',
66 'FEATURES': '-sandbox',
67 'ACCEPT_KEYWORDS': 'arm x86 ~arm ~x86',
68 'ROOT': '/',
69 })
63 70
64 # Re-mount /tmp as exec. 71 def GeneratePackageRequest(self, package_name):
65 mount -o remount,exec /tmp 72 """Build the POST string that conveys our options to the devserver."""
66 trap "mount -o remount,noexec /tmp" EXIT 73 post_data = {'board': self.board_name,
74 'pkg': package_name,
75 'use': FLAGS.use,
76 'accept_stable': FLAGS.accept_stable,
77 }
78 post_data = dict([(key, value) for (key, value) in post_data.iteritems()
79 if value])
80 return urllib.urlencode(post_data)
67 81
68 # Delete the local binary package cache. 82 def RequestPackageBuild(self, package_name):
69 rm -rf "${PKGDIR}/packages" 83 """Contacts devserver to request a build."""
84 try:
85 result = urllib2.urlopen(self.devkit_url + '/build',
86 data=self.GeneratePackageRequest(package_name))
87 print result.read()
88 result.close()
70 89
71 if [ ${BUILD} == 1 ]; then 90 except urllib2.HTTPError, e:
72 echo "Building ${PACKAGE_NAME}" 91 # The exception includes the content, which is the error mesage
73 ESCAPED_PACKAGE=$(python -c \ 92 sys.exit(e.read())
74 "import urllib; print urllib.quote('''${PACKAGE_NAME}''')")
75 ESCAPED_BOARD=$(python -c \
76 "import urllib; print urllib.quote('''${BOARD_NAME}''')")
77 93
78 wget $DEVKIT_URL/build \
79 --post-data="pkg=${ESCAPED_PACKAGE}&board=${ESCAPED_BOARD}"
80 fi
81 94
82 echo "Emerging ${PACKAGE_NAME}" 95 def main():
83 emerge --getbinpkgonly --usepkgonly "$@" 96 global FLAGS
97 parser = optparse.OptionParser(usage='usage: %prog [options] package_name')
98 parser.add_option('--accept_stable',
99 action='store_true', dest='accept_stable', default=False,
100 help=('Build even if a cros_workon package is not '
101 'using the live package'))
102 parser.add_option('-n', '--no_devserver',
103 action='store_false', dest='call_devserver', default=True,
104 help='Do not actually ask the server to build')
105 parser.add_option('--use', '--USE',
106 dest='use', default=None,
107 help='USE flags to pass to emerge on the server')
108
109 (FLAGS, remaining_arguments) = parser.parse_args()
110 if len(remaining_arguments) != 1:
111 parser.print_help()
112 sys.exit('Need exactly one package name')
113
114 package_name = remaining_arguments[0]
115
116 try:
117 subprocess.check_call(['mount', '-o', 'remount,exec', '/tmp'])
118 merger = GMerger(open('/etc/lsb-release').readlines())
119 merger.SetupPortageEnvironment(os.environ)
120 merger.RemountOrChangeRoot(os.environ)
121 if FLAGS.call_devserver:
122 merger.RequestPackageBuild(package_name)
123 else:
124 print 'Not requesting fresh build on server---installing whatever we find'
125
126 print 'Emerging ', package_name
127 subprocess.check_call([
128 'emerge', '--getbinpkgonly', '--usepkgonly', package_name])
129 finally:
130 subprocess.call(['mount', '-o', 'remount,noexec', '/tmp'])
131
132
133 if __name__ == '__main__':
134 main()
OLDNEW
« no previous file with comments | « devserver.py ('k') | gmerge_test.py » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698