1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 import glob
20 import logging
21 import os
22 import suite
23 import shutil
24 import tempfile
25 import VMBuilder.disk as disk
26 from VMBuilder.util import run_cmd
27 from VMBuilder.exception import VMBuilderException
28
30 updategrub = "/sbin/update-grub"
31 grubroot = "/lib/grub"
32 valid_flavours = { 'i386' : ['386', '686', '686-smp', 'k7', 'k7-smp', 'server', 'server-bigiron'],
33 'amd64' : ['amd64-generic', 'amd64-k8', 'amd64-k8-smp', 'amd64-server', 'amd64-xeon']}
34 default_flavour = { 'i386' : 'server', 'amd64' : 'amd64-server' }
35 disk_prefix = 'hd'
36 xen_kernel_flavour = None
37 virtio_net = False
38 chpasswd_cmd = [ 'chpasswd', '--md5' ]
39 preferred_filesystem = 'ext3'
40
43
46
49
51 raise VMBuilderException('Do not call this method!')
52
53
54 logging.debug("Creating device.map")
55 self.install_device_map()
56
57 logging.debug("Copy host settings")
58 self.copy_settings()
59
60 if hasattr(self.context, 'ec2') and self.context.ec2:
61 logging.debug("Configuring for ec2")
62 self.install_ec2()
63
65 manifest = self.context.get_setting('manifest')
66 if manifest:
67 logging.debug("Creating manifest")
68 manifest_contents = self.run_in_target('dpkg-query', '-W', '--showformat=${Package} ${Version}\n')
69 fp = open(manifest, 'w')
70 fp.write(manifest_contents)
71 fp.close
72 self.call_hook('fix_ownership', manifest)
73
75 self.run_in_target('apt-get', '-y', '--force-yes', 'dist-upgrade',
76 env={ 'DEBIAN_FRONTEND' : 'noninteractive' })
77
79 ssh_key = self.context.get_setting('ssh-key')
80 if ssh_key:
81 os.mkdir('%s/root/.ssh' % self.context.chroot_dir, 0700)
82 shutil.copy(ssh_key, '%s/root/.ssh/authorized_keys' % self.context.chroot_dir)
83 os.chmod('%s/root/.ssh/authorized_keys' % self.context.chroot_dir, 0644)
84
85 user = self.context.get_setting('user')
86 ssh_user_key = self.context.get_setting('ssh-user-key')
87 if ssh_user_key:
88 os.mkdir('%s/home/%s/.ssh' % (self.context.chroot_dir, user), 0700)
89 shutil.copy(ssh_user_key, '%s/home/%s/.ssh/authorized_keys' % (self.context.chroot_dir, user))
90 os.chmod('%s/home/%s/.ssh/authorized_keys' % (self.context.chroot_dir, user), 0644)
91 self.run_in_target('chown', '-R', '%s:%s' % ((user,)*2), '/home/%s/.ssh/' % (user))
92
93 if ssh_user_key or ssh_key:
94 addpkg = self.context.get_setting('addpkg')
95 addpkg += ['openssh-server']
96 self.context.set_setting('addpkg', addpkg)
97
99 run_cmd('mount', '--bind', '/dev', '%s/dev' % self.context.chroot_dir)
100 self.context.add_clean_cb(self.unmount_dev)
101
102 run_cmd('mount', '--bind', '/dev/pts', '%s/dev/pts' % self.context.chroot_dir)
103 self.context.add_clean_cb(self.unmount_dev_pts)
104
105 self.run_in_target('mount', '-t', 'proc', 'proc', '/proc')
106 self.context.add_clean_cb(self.unmount_proc)
107
111
115
119
137
139 uid = self.context.get_setting('uid')
140 name = self.context.get_setting('name')
141 user = self.context.get_setting('user')
142 if uid:
143 self.run_in_target('adduser', '--disabled-password', '--uid', uid, '--gecos', name, user)
144 else:
145 self.run_in_target('adduser', '--disabled-password', '--gecos', name, user)
146
147 self.run_in_target('addgroup', '--system', 'admin')
148 self.run_in_target('adduser', user, 'admin')
149
150 self.install_from_template('/etc/sudoers', 'sudoers')
151 for group in ['adm', 'audio', 'cdrom', 'dialout', 'floppy', 'video', 'plugdev', 'dip', 'netdev', 'powerdev', 'lpadmin', 'scanner']:
152 self.run_in_target('adduser', user, group, ignore_fail=True)
153
154 self.update_passwords()
155
160
162 hostname = self.context.get_setting('hostname')
163 domain = self.context.get_setting('domain')
164 self.context.install_file('/etc/hostname', hostname)
165 self.install_from_template('/etc/hosts', 'etc_hosts', { 'hostname' : hostname, 'domain' : domain })
166
168 self.install_from_template('/etc/network/interfaces', 'interfaces',
169 { 'ip' : nics[0].type == 'dhcp' and 'dhcp' or nics[0].ip,
170 'mask' : nics[0].netmask,
171 'net' : nics[0].network,
172 'bcast' : nics[0].broadcast,
173 'gw' : nics[0].gateway,
174 'dns' : nics[0].dns,
175 'domain' : self.context.get_setting('domain') })
176
178 os.unlink('%s/usr/sbin/policy-rc.d' % self.context.chroot_dir)
179
182
183 - def seed(self, seedfile):
184 """Seed debconf with the contents of a seedfile"""
185 logging.info('Seeding with "%s"' % seedfile)
186
187 self.run_in_target('debconf-set-selections', stdin=open(seedfile, 'r').read())
188
190 seedfile = self.context.get_setting('seedfile')
191 if seedfile:
192 self.seed(seedfile)
193
194 addpkg = self.context.get_setting('addpkg')
195 removepkg = self.context.get_setting('removepkg')
196 if not addpkg and not removepkg:
197 return
198
199 cmd = ['apt-get', 'install', '-y', '--force-yes']
200 cmd += addpkg or []
201 cmd += ['%s-' % pkg for pkg in removepkg or []]
202 self.run_in_target(env={ 'DEBIAN_FRONTEND' : 'noninteractive' }, *cmd)
203
205 for mntpnt in glob.glob('%s/lib/modules/*/volatile' % self.context.chroot_dir):
206 logging.debug("Unmounting %s" % mntpnt)
207 run_cmd('umount', mntpnt)
208
214
216 bootdev = disk.bootpart(disks)
217 run_cmd('sed', '-ie', 's/^# kopt=root=\([^ ]*\)\(.*\)/# kopt=root=\/dev\/hd%s%d\\2/g' % (bootdev.disk.devletters(), bootdev.get_index()+1), '%s/boot/grub/menu.lst' % self.context.chroot_dir)
218 run_cmd('sed', '-ie', 's/^# groot.*/# groot %s/g' % bootdev.get_grub_id(), '%s/boot/grub/menu.lst' % self.context.chroot_dir)
219 run_cmd('sed', '-ie', '/^# kopt_2_6/ d', '%s/boot/grub/menu.lst' % self.context.chroot_dir)
220
222 if final:
223 mirror = updates_mirror = self.context.get_setting('mirror')
224 security_mirror = self.context.get_setting('security-mirror')
225 else:
226 mirror, updates_mirror, security_mirror = self.install_mirrors()
227
228 components = self.context.get_setting('components')
229 ppa = self.context.get_setting('ppa')
230 suite = self.context.get_setting('suite')
231 self.install_from_template('/etc/apt/sources.list', 'sources.list', { 'mirror' : mirror,
232 'security_mirror' : security_mirror,
233 'updates_mirror' : updates_mirror,
234 'components' : components,
235 'ppa' : ppa,
236 'suite' : suite })
237
238
239
240
241 self.run_in_target('apt-get', 'update', ignore_fail=final)
242
244 proxy = self.context.get_setting('proxy')
245 if proxy is not None:
246 self.context.install_file('/etc/apt/apt.conf', '// Proxy added by vmbuilder\nAcquire::http { Proxy "%s"; };' % proxy)
247
250
253
255 arch = self.context.get_setting('arch')
256 cmd = ['/usr/sbin/debootstrap', '--arch=%s' % arch]
257
258 variant = self.context.get_setting('variant')
259 if variant:
260 cmd += ['--variant=%s' % variant]
261
262 suite = self.context.get_setting('suite')
263 cmd += [suite, self.context.chroot_dir, self.debootstrap_mirror()]
264 kwargs = { 'env' : { 'DEBIAN_FRONTEND' : 'noninteractive' } }
265
266 proxy = self.context.get_setting('proxy')
267 if proxy:
268 kwargs['env']['http_proxy'] = proxy
269 run_cmd(*cmd, **kwargs)
270
272 iso = self.context.get_setting('iso')
273 if iso:
274 isodir = tempfile.mkdtemp()
275 self.context.add_clean_cb(lambda:os.rmdir(isodir))
276 run_cmd('mount', '-o', 'loop', '-t', 'iso9660', iso, isodir)
277 self.context.add_clean_cmd('umount', isodir)
278 self.iso_mounted = True
279
280 return 'file://%s' % isodir
281 else:
282 return self.install_mirrors()[0]
283
284
286 install_mirror = self.context.get_setting('install-mirror')
287 if install_mirror:
288 mirror = install_mirror
289 else:
290 mirror = self.context.get_setting('mirror')
291
292 updates_mirror = mirror
293
294 install_security_mirror = self.context.get_setting('install-security-mirror')
295 if install_security_mirror:
296 security_mirror = install_security_mirror
297 else:
298 security_mirror = self.context.get_setting('security-mirror')
299
300 return (mirror, updates_mirror, security_mirror)
301
303 run_cmd('chroot', destdir, 'apt-get', '--force-yes', '-y', 'install', self.kernel_name(), env={ 'DEBIAN_FRONTEND' : 'noninteractive' })
304
306 self.install_from_template('/etc/kernel-img.conf', 'kernelimg', { 'updategrub' : self.updategrub })
307 arch = self.context.get_setting('arch')
308 self.run_in_target('apt-get', '--force-yes', '-y', 'install', 'grub', env={ 'DEBIAN_FRONTEND' : 'noninteractive' })
309 run_cmd('rsync', '-a', '%s%s/%s/' % (chroot_dir, self.grubroot, arch == 'amd64' and 'x86_64-pc' or 'i386-pc'), '%s/boot/grub/' % chroot_dir)
310
313
314
315
316
317
318
319
320
321
322
325
328
330 logging.debug("Copying %s on host to %s in guest" % (infile, destpath))
331 dir = '%s/%s' % (self.destdir, os.path.dirname(destpath))
332 if not os.path.isdir(dir):
333 os.makedirs(dir)
334 if os.path.isdir(infile):
335 shutil.copytree(infile, '%s/%s' % (self.destdir, destpath))
336 else:
337 shutil.copy(infile, '%s/%s' % (self.destdir, destpath))
338
339 - def post_mount(self, fs):
340 if fs.mntpnt == '/':
341 logging.debug("Creating /var/run in root filesystem")
342 os.makedirs('%s/var/run' % fs.mntpath)
343 logging.debug("Creating /var/lock in root filesystem")
344 os.makedirs('%s/var/lock' % fs.mntpath)
345
347 lang = self.context.get_setting('lang')
348 if lang:
349 self.install_from_template('/etc/default/locale', 'locale', { 'lang' : lang })
350 if lang != "C":
351 self.run_in_target('locale-gen', lang)
352 self.run_in_target('dpkg-reconfigure', '-fnoninteractive', '-pcritical', 'libc6')
353 self.run_in_target('dpkg-reconfigure', '-fnoninteractive', '-pcritical', 'locales')
354
356 shutil.copy(logfile, '%s/var/log/vmbuilder-install.log' % (rootdir,))
357
359 timezone = self.context.get_setting('timezone')
360 if timezone:
361 self.install_from_template('/etc/timezone', 'timezone', { 'timezone' : timezone })
362 self.run_in_target('dpkg-reconfigure', '-fnoninteractive', '-pcritical', 'locales')
363
365 if self.context.ec2:
366 logging.debug('This suite does not support ec2')
367
369 fp = open('%s/etc/default/rcS' % self.destdir, 'a')
370 fp.write('HWCLOCKACCESS=no')
371 fp.close()
372
375