~ubuntu-branches/ubuntu/quantal/virtinst/quantal-proposed

« back to all changes in this revision

Viewing changes to virtinst/DistroInstaller.py

  • Committer: Bazaar Package Importer
  • Author(s): Marc Deslauriers
  • Date: 2011-02-01 15:40:11 UTC
  • mfrom: (1.3.16 experimental)
  • Revision ID: james.westby@ubuntu.com-20110201154011-op0nusgc240xajvb
Tags: 0.500.5-1ubuntu1
* Merge from debian experimental. Remaining changes:
  - debian/patches/9001_Ubuntu.patch:
     + Updated to add maverick and natty to OS list and enable virtio
       for them.
  - debian/patches/9003-fix-path-to-hvmloader-in-testsuite.patch: adjust
    testsuite for 0001-fix-path-to-hvmloader.patch and
    0002-Fix-path-to-pygrub.patch. (refreshed)
  - debian/control: added acl package to depends.
  - Demote virt-viewer to Suggests, as it's in universe.
  - Recommends libvirt-bin
* Removed patches:
  - debian/patches/9002-libvirt_disk_format.patch: Upstream.

Show diffs side-by-side

added added

removed removed

Lines of Context:
19
19
 
20
20
import logging
21
21
import os
 
22
import sys
 
23
import shutil
 
24
import subprocess
 
25
import tempfile
22
26
 
23
27
import _util
24
28
import Installer
61
65
    return url
62
66
 
63
67
class DistroInstaller(Installer.Installer):
64
 
    def __init__(self, type = "xen", location = None, boot = None,
65
 
                 extraargs = None, os_type = None, conn = None):
 
68
    def __init__(self, type="xen", location=None, boot=None,
 
69
                 extraargs=None, os_type=None,
 
70
                 conn=None, caps=None):
66
71
        Installer.Installer.__init__(self, type, location, boot, extraargs,
67
 
                                 os_type, conn=conn)
 
72
                                     os_type, conn=conn, caps=caps)
68
73
 
69
 
        self.install = {
70
 
            "kernel" : "",
71
 
            "initrd" : "",
72
 
            "extraargs" : "",
73
 
        }
 
74
        self._livecd = False
74
75
 
75
76
        # True == location is a filesystem path
76
77
        # False == location is a url
77
78
        self._location_is_path = True
78
79
 
79
 
 
80
80
    # DistroInstaller specific methods/overwrites
81
81
 
 
82
    def _get_livecd(self):
 
83
        return self._livecd
 
84
    def _set_livecd(self, val):
 
85
        self._livecd = bool(val)
 
86
    livecd = property(_get_livecd, _set_livecd)
 
87
 
82
88
    def get_location(self):
83
89
        return self._location
84
90
    def set_location(self, val):
160
166
 
161
167
    # Private helper methods
162
168
 
163
 
    def _prepare_cdrom(self, guest, distro, meter):
 
169
    def _prepare_cdrom(self, guest, meter):
 
170
        transient = not self.livecd
164
171
        if not self._location_is_path:
165
172
            # Xen needs a boot.iso if its a http://, ftp://, or nfs: url
166
 
            cdrom = OSDistro.acquireBootDisk(self.location,
167
 
                                             meter, guest.arch,
168
 
                                             scratchdir = self.scratchdir,
169
 
                                             distro = distro)
 
173
            (store_ignore, os_type_ignore, os_variant_ignore, media) = \
 
174
             OSDistro.acquireBootDisk(guest, self.location, meter,
 
175
                                      self.scratchdir)
 
176
            cdrom = media
 
177
 
170
178
            self._tmpfiles.append(cdrom)
 
179
            transient = True
171
180
        else:
172
181
            cdrom = self.location
173
182
 
174
 
        self._install_disk = VirtualDisk(path=cdrom,
175
 
                                         conn=guest.conn,
176
 
                                         device=VirtualDisk.DEVICE_CDROM,
177
 
                                         readOnly=True,
178
 
                                         transient=True)
179
 
 
180
 
    def _prepare_kernel_and_initrd(self, guest, distro, meter):
181
 
        if self.boot is not None:
182
 
            # Got a local kernel/initrd already
183
 
            self.install["kernel"] = self.boot["kernel"]
184
 
            self.install["initrd"] = self.boot["initrd"]
185
 
            if not self.extraargs is None:
186
 
                self.install["extraargs"] = self.extraargs
187
 
        else:
188
 
            # Need to fetch the kernel & initrd from a remote site, or
189
 
            # out of a loopback mounted disk image/device
190
 
 
191
 
            ((kernelfn, initrdfn, args),
192
 
             os_type, os_variant) = OSDistro.acquireKernel(guest,
193
 
                self.location, meter, guest.arch, scratchdir=self.scratchdir,
194
 
                type=self.os_type, distro=distro)
195
 
 
196
 
            if guest.get_os_autodetect():
197
 
                if os_type:
198
 
                    logging.debug("Auto detected OS type as: %s" % os_type)
199
 
                    guest.os_type = os_type
200
 
 
201
 
                if (os_variant and guest.os_type == os_type):
202
 
                    logging.debug("Auto detected OS variant as: %s" %
203
 
                                  os_variant)
204
 
                    guest.os_variant = os_variant
205
 
 
206
 
            self.install["kernel"] = kernelfn
207
 
            self.install["initrd"] = initrdfn
208
 
            self.install["extraargs"] = args
209
 
 
210
 
            self._tmpfiles.append(kernelfn)
211
 
            if initrdfn:
212
 
                self._tmpfiles.append(initrdfn)
213
 
 
214
 
        # If they're installing off a local file/device, we map it
215
 
        # through to a virtual CD or disk
216
 
        if (self.location is not None and self._location_is_path
217
 
           and not os.path.isdir(self.location)):
 
183
        disk = VirtualDisk(path=cdrom,
 
184
                           conn=guest.conn,
 
185
                           device=VirtualDisk.DEVICE_CDROM,
 
186
                           readOnly=True,
 
187
                           transient=transient)
 
188
        self.install_devices.append(disk)
 
189
 
 
190
    def _perform_initrd_injections(self):
 
191
        """
 
192
        Insert files into the root directory of the initial ram disk
 
193
        """
 
194
        initrd = self._install_bootconfig.initrd
 
195
        tempdir = tempfile.mkdtemp(dir=self.scratchdir)
 
196
        os.chmod(tempdir, 0775)
 
197
 
 
198
        for filename in self._initrd_injections:
 
199
            logging.debug("Copying %s to the initrd." % filename)
 
200
            shutil.copy(filename, tempdir)
 
201
 
 
202
        logging.debug("Appending to the initrd.")
 
203
        find_proc = subprocess.Popen(['find', '.', '-print0'],
 
204
                                     stdout=subprocess.PIPE,
 
205
                                     stderr=sys.stderr, cwd=tempdir)
 
206
        cpio_proc = subprocess.Popen(['cpio', '-o', '--null', '-Hnewc', '--quiet'],
 
207
                                     stdin=find_proc.stdout,
 
208
                                     stdout=subprocess.PIPE,
 
209
                                     stderr=sys.stderr, cwd=tempdir)
 
210
        f = open(initrd, 'ab')
 
211
        gzip_proc = subprocess.Popen(['gzip'], stdin=cpio_proc.stdout,
 
212
                                     stdout=f, stderr=sys.stderr)
 
213
        cpio_proc.wait()
 
214
        find_proc.wait()
 
215
        gzip_proc.wait()
 
216
        f.close()
 
217
        shutil.rmtree(tempdir)
 
218
 
 
219
    def _prepare_kernel_and_initrd(self, guest, meter):
 
220
        disk = None
 
221
 
 
222
        # If installing off a local path, map it through to a virtual CD/disk
 
223
        if (self.location is not None and
 
224
            self._location_is_path and
 
225
            not os.path.isdir(self.location)):
218
226
            device = VirtualDisk.DEVICE_DISK
219
227
            if guest._lookup_osdict_key('pv_cdrom_install'):
220
228
                device = VirtualDisk.DEVICE_CDROM
221
229
 
222
 
            self._install_disk = VirtualDisk(conn=guest.conn,
223
 
                                             device=device,
224
 
                                             path=self.location,
225
 
                                             readOnly=True,
226
 
                                             transient=True)
 
230
            disk = VirtualDisk(conn=guest.conn,
 
231
                               device=device,
 
232
                               path=self.location,
 
233
                               readOnly=True,
 
234
                               transient=True)
 
235
 
 
236
        # Make sure we always fetch kernel here if required
 
237
        if self._install_bootconfig.kernel and not self.scratchdir_required():
 
238
            return disk
 
239
 
 
240
        # Need to fetch the kernel & initrd from a remote site, or
 
241
        # out of a loopback mounted disk image/device
 
242
        ignore, os_type, os_variant, media = OSDistro.acquireKernel(guest,
 
243
                                                self.location, meter,
 
244
                                                self.scratchdir,
 
245
                                                self.os_type)
 
246
        (kernelfn, initrdfn, args) = media
 
247
 
 
248
        if guest.get_os_autodetect():
 
249
            if os_type:
 
250
                logging.debug("Auto detected OS type as: %s" % os_type)
 
251
                guest.os_type = os_type
 
252
 
 
253
            if (os_variant and guest.os_type == os_type):
 
254
                logging.debug("Auto detected OS variant as: %s" % os_variant)
 
255
                guest.os_variant = os_variant
 
256
 
 
257
        self._install_bootconfig.kernel = kernelfn
 
258
        self._install_bootconfig.initrd = initrdfn
 
259
        self._install_bootconfig.kernel_args = args
 
260
 
 
261
        self._tmpfiles.append(kernelfn)
 
262
        if initrdfn:
 
263
            self._tmpfiles.append(initrdfn)
 
264
 
 
265
        if self._initrd_injections:
 
266
            self._perform_initrd_injections()
 
267
 
 
268
        return disk
 
269
 
 
270
    def _persistent_cd(self):
 
271
        return (self._location_is_path and self.cdrom and self.livecd)
 
272
 
 
273
    def _get_bootdev(self, isinstall, guest):
 
274
        if isinstall or self._persistent_cd():
 
275
            bootdev = self.bootconfig.BOOT_DEVICE_CDROM
 
276
        else:
 
277
            bootdev = self.bootconfig.BOOT_DEVICE_HARDDISK
 
278
        return bootdev
227
279
 
228
280
    # General Installer methods
229
281
 
230
282
    def scratchdir_required(self):
231
 
        return bool(not self._location_is_path)
232
 
 
233
 
    def prepare(self, guest, meter, distro = None):
 
283
        if not self.location:
 
284
            return False
 
285
 
 
286
        is_url = not self._location_is_path
 
287
        mount_dvd = self._location_is_path and not self.cdrom
 
288
 
 
289
        return bool(is_url or mount_dvd)
 
290
 
 
291
    def prepare(self, guest, meter):
234
292
        self.cleanup()
235
293
 
236
 
        self.install = {
237
 
            "kernel" : "",
238
 
            "initrd" : "",
239
 
            "extraargs" : "",
240
 
        }
241
 
 
 
294
        dev = None
242
295
        if self.cdrom:
243
296
            if self.location:
244
 
                self._prepare_cdrom(guest, distro, meter)
 
297
                dev = self._prepare_cdrom(guest, meter)
245
298
            else:
246
299
                # Booting from a cdrom directly allocated to the guest
247
300
                pass
248
301
        else:
249
 
            self._prepare_kernel_and_initrd(guest, distro, meter)
250
 
 
251
 
    def get_install_xml(self, guest, isinstall):
252
 
        if isinstall:
253
 
            bootdev = "cdrom"
 
302
            dev = self._prepare_kernel_and_initrd(guest, meter)
 
303
 
 
304
        if dev:
 
305
            self.install_devices.append(dev)
 
306
 
 
307
    def check_location(self):
 
308
        if self._location_is_path:
 
309
            # We already mostly validated this
 
310
            return True
254
311
        else:
255
 
            bootdev = "hd"
256
 
 
257
 
        return self._get_osblob_helper(isinstall=isinstall, guest=guest,
258
 
                                       kernel=self.install, bootdev=bootdev)
 
312
            # This will throw an error for us
 
313
            OSDistro.detectMediaDistro(location=self.location, arch=self.arch)
 
314
        return True
259
315
 
260
316
    def detect_distro(self):
261
317
        try: