- change this script to one whose primary jobs is to generate the API
[myplc.git] / build.sh
1 #!/bin/bash
2 #
3 # Builds a Fedora based PLC image. You should be able to run this
4 # script multiple times without a problem.
5 #
6 # Mark Huang <mlhuang@cs.princeton.edu>
7 # Copyright (C) 2006 The Trustees of Princeton University
8 #
9 # $Id$
10 #
11
12 PATH=/sbin:/bin:/usr/sbin:/usr/bin
13
14 # In both a normal CVS environment and a PlanetLab RPM
15 # build environment, all of our dependencies are checked out into
16 # directories at the same level as us.
17 if [ -d ../build ] ; then
18     PATH=$PATH:../build
19     srcdir=..
20 else
21     echo "Error: Could not find $(cd .. && pwd -P)/build/"
22     exit 1
23 fi
24
25 export PATH
26
27 # PLC configuration file
28 config=plc_config.xml
29
30 # Release and architecture to install
31 releasever=4
32 basearch=i386
33
34 # Initial size of the image
35 size=1000000000
36
37 usage()
38 {
39     echo "Usage: build.sh [OPTION]..."
40     echo "      -c file         PLC configuration file (default: $config)"
41     echo "      -r release      Fedora release number (default: $releasever)"
42     echo "      -a arch         Fedora architecture (default: $basearch)"
43     echo "      -s size         Approximate size of the installation (default: $size)"
44     echo "      -h              This message"
45     exit 1
46 }
47
48 # Get options
49 while getopts "c:r:a:s:h" opt ; do
50     case $opt in
51         c)
52             config=$OPTARG
53             ;;
54         r)
55             releasever=$OPTARG
56             ;;
57         a)
58             basearch=$OPTARG
59             ;;
60         s)
61             size=$OPTARG
62             ;;
63         h|*)
64             usage
65             ;;
66     esac
67 done
68
69 # Do not tolerate errors
70 set -e
71
72 root=root
73 data=data
74
75 if [ ! -f $root.img ] ; then
76     bs=4096
77     count=$(($size / 4096))
78     dd bs=$bs count=$count if=/dev/zero of=$root.img
79     mkfs.ext3 -j -F $root.img
80 fi
81
82 mkdir -p $root $data
83 mount -o loop $root.img $root
84 trap "umount $root" ERR
85
86 #
87 # Build
88 #
89
90 # Get package list
91 while read package ; do
92     packages="$packages -p $package"
93 done < <(./plc-config --packages $config)
94
95 # Install base system
96 mkfedora -v -r $releasever -a $basearch -k $packages $root
97
98 # Disable all services in reference image
99 chroot $root sh -c "/sbin/chkconfig --list | awk '{ print \$1 }' | xargs -i /sbin/chkconfig {} off"
100
101 # FC2 minilogd starts up during shutdown and makes unmounting
102 # impossible. Just get rid of it.
103 rm -f $root/sbin/minilogd
104 ln -nsf /bin/true $root/sbin/minilogd
105
106 # Build schema
107 make -C $srcdir/pl_db
108
109 #
110 # Install
111 #
112
113 # Install configuration scripts
114 echo "* Installing configuration scripts"
115 install -D -m 755 plc_config.py $root/tmp/plc_config.py
116 chroot $root sh -c 'cd /tmp; python plc_config.py build; python plc_config.py install'
117 install -D -m 755 plc-config $root/usr/bin/plc-config
118 install -D -m 755 api-config $root/usr/bin/api-config
119 install -D -m 755 db-config $root/usr/bin/db-config
120 install -D -m 755 dns-config $root/usr/bin/dns-config
121
122 # Install OpenSSL configuration
123 install -D -m 644 openssl.cnf $root/etc/planetlab/ssl/openssl.cnf
124
125 # Install initscripts
126 echo "* Installing initscripts"
127 find plc.d | cpio -p -d -u $root/etc/
128 install -D -m 755 guest.init $root/etc/init.d/plc
129 chroot $root sh -c 'chkconfig --add plc; chkconfig plc on'
130
131 # Install DB schema and API code
132 echo "* Installing DB schema and API code"
133 mkdir -p $root/usr/share
134 rsync -a $srcdir/pl_db $srcdir/plc_api $root/usr/share/
135
136 # Install web scripts
137 echo "* Installing web scripts"
138 mkdir -p $root/usr/bin
139 install -m 755 \
140     $srcdir/plc/scripts/gen-sites-xml.py \
141     $srcdir/plc/scripts/gen-slices-xml-05.py \
142     $srcdir/plc/scripts/gen-static-content.py \
143     $root/usr/bin/
144
145 # Install web pages
146 echo "* Installing web pages"
147 mkdir -p $root/var/www/html
148 # Exclude old cruft, unrelated GENI pages, and official documents
149 rsync -a \
150     --exclude='*2002' --exclude='*2003' \
151     --exclude=geni --exclude=PDN --exclude=Talks \
152     $srcdir/plc_www/ $root/var/www/html/
153
154 # Install configuration file
155 echo "* Installing configuration file"
156 install -D -m 444 $config $data/etc/planetlab/default_config.xml
157 install -D -m 444 plc_config.dtd $data/etc/planetlab/plc_config.dtd
158
159 # Move "data" directories out of the installation
160 datadirs=(
161 /etc/planetlab
162 /var/lib/pgsql
163 /var/www/html/alpina-logs
164 /var/www/html/boot
165 /var/www/html/download
166 /var/www/html/generated
167 /var/www/html/install-rpms
168 /var/www/html/xml
169 )
170
171 echo "* Moving data directories out of the installation"
172 mkdir -p $root/data
173 for datadir in "${datadirs[@]}" ; do
174     mkdir -p ${data}$datadir
175     if [ -d $root/$datadir -a ! -h $root/$datadir ] ; then
176         (cd $root && find ./$datadir | cpio -p -d -u ../$data/)
177     fi
178     rm -rf $root/$datadir
179     mkdir -p $(dirname $root/$datadir)
180     ln -nsf /data$datadir $root/$datadir
181 done
182
183 # Shrink to 100 MB free space
184 kb=$(python <<EOF
185 import os
186 df = os.statvfs('$root')
187 target = 100 * 1024 * 1024 / df.f_bsize
188 if df.f_bavail > target:
189     print (df.f_blocks - (df.f_bavail - target)) * df.f_bsize / 1024
190 EOF
191 )
192
193 umount $root
194 trap - ERR
195
196 if [ -n "$kb" ] ; then
197     # Setup loopback association. Newer versions of losetup have a -f
198     # option which finds an unused loopback device, but we must
199     # support FC2 for now.
200     # dev_loop=$(losetup -f)
201     for i in `seq 1 7` ; do
202         if ! grep -q "^/dev/loop$i" /proc/mounts ; then
203             dev_loop="/dev/loop$i"
204             break
205         fi
206     done
207     losetup $dev_loop $root.img
208     trap "losetup -d $dev_loop" ERR
209
210     # Resize the filesystem
211     echo "* Checking filesystem"
212     e2fsck -a -f $dev_loop
213     echo "* Shrinking filesystem"
214     resize2fs $dev_loop ${kb}K
215
216     # Tear down loopback association
217     losetup -d $dev_loop
218     trap - ERR
219
220     # Truncate the image file
221     perl -e "truncate '$root.img', $kb*1024"
222 fi
223
224 # Write sysconfig
225 cat >plc.sysconfig <<EOF
226 PLC_ROOT=/plc/$root
227 PLC_DATA=/plc/$data
228 #PLC_OPTIONS="-v"
229 EOF
230
231 # Initialize node RPMs directory. The PlanetLab-Bootstrap.tar.bz2
232 # tarball already contains all of the node RPMs pre-installed. Only
233 # updates or optional packages should be placed in this directory.
234 if [ -n "$RPM_BUILD_DIR" ] ; then
235     echo "* Initializing node RPMs directory"
236     RPM_RPMS_DIR=$(cd $(dirname $RPM_BUILD_DIR)/RPMS && pwd -P)
237     mkdir -p $data/var/www/html/install-rpms/planetlab
238     if [ -f $RPM_RPMS_DIR/yumgroups.xml ] ; then
239         install -D -m 644 $RPM_RPMS_DIR/yumgroups.xml \
240             $data/var/www/html/install-rpms/planetlab/yumgroups.xml
241     fi
242     # yum-2.0.x
243     if [ -x /usr/bin/yum-arch ] ; then
244         yum-arch $data/var/www/html/install-rpms/planetlab
245     fi
246     # yum-2.4.x
247     if [ -x /usr/bin/createrepo ] ; then
248         if [ -f $data/var/www/html/install-rpms/planetlab/yumgroups.xml ] ; then
249             groupfile="-g yumgroups.xml"
250         fi
251         createrepo $groupfile $data/var/www/html/install-rpms/planetlab
252     fi
253 fi
254
255 # Bootstrap the system for quicker startup (and to populate the
256 # PlanetLabConf tables from PLC, which may not be accessible
257 # later). The bootstrap.xml configuration overlay configures the web
258 # server to run on an alternate port (in case the build machine itself
259 # is running a web server on port 80). Start everything up to
260 # bootstrap the database, then shut it back down again immediately.
261 echo "* Bootstrapping installation"
262
263 install -D -m 644 bootstrap.xml $data/etc/planetlab/configs/bootstrap.xml
264
265 # Otherwise, host.init will try to read /etc/sysconfig/plc
266 export PLC_ROOT=$PWD/$root
267 export PLC_DATA=$PWD/$data
268 #export PLC_OPTIONS="-v"
269
270 ./host.init start
271 RETVAL=$?
272
273 # Remove ISO and USB images, which take up >100MB but only take a
274 # couple of seconds to generate at first boot.
275 rm -f $data/var/www/html/download/*.{iso,usb}
276
277 ./host.init stop
278 RETVAL=$(($RETVAL+$?))
279
280 # Restore default configuration
281 rm -f $data/etc/planetlab/configs/bootstrap.xml
282 install -D -m 444 $config $data/etc/planetlab/plc_config.xml
283
284 exit $RETVAL