ia64/xen-unstable

changeset 6572:edbdd7123d24

Provide xend support for setting up TPM front- and back-end interfaces.

Signed-off-by: Steven Hand <steven@xensource.com>
Signed-off-by: Stefan Berger <stefanb@us.ibm.com>
author shand@ubuntu.eng.hq.xensource.com
date Tue Aug 30 11:28:26 2005 -0800 (2005-08-30)
parents 69d21d9d6b57
children 9ba52ccadc06
files tools/examples/xmexample1 tools/examples/xmexample2 tools/examples/xmexample3 tools/python/xen/xend/XendDomainInfo.py tools/python/xen/xend/image.py tools/python/xen/xend/server/tpmif.py tools/python/xen/xm/create.py
line diff
     1.1 --- a/tools/examples/xmexample1	Tue Aug 30 11:19:52 2005 -0800
     1.2 +++ b/tools/examples/xmexample1	Tue Aug 30 11:28:26 2005 -0800
     1.3 @@ -48,6 +48,20 @@ name = "ExampleDomain"
     1.4  disk = [ 'phy:hda1,hda1,w' ]
     1.5  
     1.6  #----------------------------------------------------------------------------
     1.7 +# Define to which TPM instance the user domain should communicate.
     1.8 +# The vtpm entry is of the form 'instance=INSTANCE,backend=DOM'
     1.9 +# where INSTANCE indicates the instance number of the TPM the VM
    1.10 +# should be talking to and DOM provides the domain where the backend
    1.11 +# is located.
    1.12 +# Note that no two virtual machines should try to connect to the same
    1.13 +# TPM instance. The handling of all TPM instances does require
    1.14 +# some management effort in so far that VM configration files (and thus
    1.15 +# a VM) should be associated with a TPM instance throughout the lifetime
    1.16 +# of the VM / VM configuration file. The instance number must be
    1.17 +# greater or equal to 1.
    1.18 +#vtpm = [ 'instance=1,backend=0' ]
    1.19 +
    1.20 +#----------------------------------------------------------------------------
    1.21  # Set the kernel command line for the new domain.
    1.22  # You only need to define the IP parameters and hostname if the domain's
    1.23  # IP config doesn't, e.g. in ifcfg-eth0 or via DHCP.
     2.1 --- a/tools/examples/xmexample2	Tue Aug 30 11:19:52 2005 -0800
     2.2 +++ b/tools/examples/xmexample2	Tue Aug 30 11:28:26 2005 -0800
     2.3 @@ -84,6 +84,20 @@ disk = [ 'phy:sda%d,sda1,w' % (7+vmid),
     2.4           'phy:sda6,sda6,r' ]
     2.5  
     2.6  #----------------------------------------------------------------------------
     2.7 +# Define to which TPM instance the user domain should communicate.
     2.8 +# The vtpm entry is of the form 'instance=INSTANCE,backend=DOM'
     2.9 +# where INSTANCE indicates the instance number of the TPM the VM
    2.10 +# should be talking to and DOM provides the domain where the backend
    2.11 +# is located.
    2.12 +# Note that no two virtual machines should try to connect to the same
    2.13 +# TPM instance. The handling of all TPM instances does require
    2.14 +# some management effort in so far that VM configration files (and thus
    2.15 +# a VM) should be associated with a TPM instance throughout the lifetime
    2.16 +# of the VM / VM configuration file. The instance number must be
    2.17 +# greater or equal to 1.
    2.18 +#vtpm = ['instance=%d,backend=0' % (vmid) ]
    2.19 +
    2.20 +#----------------------------------------------------------------------------
    2.21  # Set the kernel command line for the new domain.
    2.22  # You only need to define the IP parameters and hostname if the domain's
    2.23  # IP config doesn't, e.g. in ifcfg-eth0 or via DHCP.
     3.1 --- a/tools/examples/xmexample3	Tue Aug 30 11:19:52 2005 -0800
     3.2 +++ b/tools/examples/xmexample3	Tue Aug 30 11:28:26 2005 -0800
     3.3 @@ -80,6 +80,20 @@ vif = [ 'ip=192.168.%d.1/24' % (vmid)]
     3.4  disk = [ 'phy:hda%d,hda1,w' % (vmid)]
     3.5  
     3.6  #----------------------------------------------------------------------------
     3.7 +# Define to which TPM instance the user domain should communicate.
     3.8 +# The vtpm entry is of the form 'instance=INSTANCE,backend=DOM'
     3.9 +# where INSTANCE indicates the instance number of the TPM the VM
    3.10 +# should be talking to and DOM provides the domain where the backend
    3.11 +# is located.
    3.12 +# Note that no two virtual machines should try to connect to the same
    3.13 +# TPM instance. The handling of all TPM instances does require
    3.14 +# some management effort in so far that VM configration files (and thus
    3.15 +# a VM) should be associated with a TPM instance throughout the lifetime
    3.16 +# of the VM / VM configuration file. The instance number must be
    3.17 +# greater or equal to 1.
    3.18 +#vtpm = ['instance=%d,backend=0' % (vmid) ]
    3.19 +
    3.20 +#----------------------------------------------------------------------------
    3.21  # Set the kernel command line for the new domain.
    3.22  # You only need to define the IP parameters and hostname if the domain's
    3.23  # IP config doesn't, e.g. in ifcfg-eth0 or via DHCP.
     4.1 --- a/tools/python/xen/xend/XendDomainInfo.py	Tue Aug 30 11:19:52 2005 -0800
     4.2 +++ b/tools/python/xen/xend/XendDomainInfo.py	Tue Aug 30 11:28:26 2005 -0800
     4.3 @@ -269,6 +269,7 @@ class XendDomainInfo:
     4.4          self.blkif_backend = False
     4.5          self.netif_backend = False
     4.6          self.netif_idx = 0
     4.7 +        self.tpmif_backend = False
     4.8          
     4.9          #todo: state: running, suspended
    4.10          self.state = STATE_VM_OK
    4.11 @@ -458,6 +459,31 @@ class XendDomainInfo:
    4.12  
    4.13              return
    4.14          
    4.15 +        if type == 'vtpm':
    4.16 +            backdom = domain_exists(sxp.child_value(devconfig, 'backend', '0'))
    4.17 +
    4.18 +            devnum = int(sxp.child_value(devconfig, 'instance', '0'))
    4.19 +            log.error("The domain has a TPM with instance %d." % devnum)
    4.20 +
    4.21 +            # create backend db
    4.22 +            backdb = backdom.db.addChild("/backend/%s/%s/%d" %
    4.23 +                                         (type, self.uuid, devnum))
    4.24 +            # create frontend db
    4.25 +            db = self.db.addChild("/device/%s/%d" % (type, devnum))
    4.26 +
    4.27 +            backdb['frontend'] = db.getPath()
    4.28 +            backdb['frontend-id'] = "%i" % self.id
    4.29 +            backdb['instance'] = sxp.child_value(devconfig, 'instance', '0')
    4.30 +            backdb.saveDB(save=True)
    4.31 +
    4.32 +            db['handle'] = "%i" % devnum
    4.33 +            db['backend'] = backdb.getPath()
    4.34 +            db['backend-id'] = "%i" % int(sxp.child_value(devconfig,
    4.35 +                                                          'backend', '0'))
    4.36 +            db.saveDB(save=True)
    4.37 +
    4.38 +            return
    4.39 +
    4.40          ctrl = self.findDeviceController(type)
    4.41          return ctrl.createDevice(devconfig, recreate=self.recreate,
    4.42                                   change=change)
    4.43 @@ -779,6 +805,11 @@ class XendDomainInfo:
    4.44                  for dev in typedb.keys():
    4.45                      typedb[dev].delete()
    4.46                  typedb.saveDB(save=True)
    4.47 +            if type == 'vtpm':
    4.48 +                typedb = ddb.addChild(type)
    4.49 +                for dev in typedb.keys():
    4.50 +                    typedb[dev].delete()
    4.51 +                typedb.saveDB(save=True)
    4.52  
    4.53      def show(self):
    4.54          """Print virtual machine info.
    4.55 @@ -1018,6 +1049,8 @@ class XendDomainInfo:
    4.56                  self.netif_backend = True
    4.57              elif name == 'usbif':
    4.58                  self.usbif_backend = True
    4.59 +            elif name == 'tpmif':
    4.60 +                self.tpmif_backend = True
    4.61              else:
    4.62                  raise VmError('invalid backend type:' + str(name))
    4.63  
    4.64 @@ -1190,6 +1223,10 @@ from server import netif
    4.65  controller.addDevControllerClass("vif", netif.NetifController)
    4.66  add_device_handler("vif", "vif")
    4.67  
    4.68 +from server import tpmif
    4.69 +controller.addDevControllerClass("vtpm", tpmif.TPMifController)
    4.70 +add_device_handler("vtpm", "vtpm")
    4.71 +
    4.72  from server import pciif
    4.73  controller.addDevControllerClass("pci", pciif.PciController)
    4.74  add_device_handler("pci", "pci")
     5.1 --- a/tools/python/xen/xend/image.py	Tue Aug 30 11:19:52 2005 -0800
     5.2 +++ b/tools/python/xen/xend/image.py	Tue Aug 30 11:28:26 2005 -0800
     5.3 @@ -32,6 +32,9 @@ SIF_BLK_BE_DOMAIN = (1<<4)
     5.4  """Flag for a net device backend domain."""
     5.5  SIF_NET_BE_DOMAIN = (1<<5)
     5.6  
     5.7 +"""Flag for a TPM device backend domain."""
     5.8 +SIF_TPM_BE_DOMAIN = (1<<7)
     5.9 +
    5.10  class ImageHandler:
    5.11      """Abstract base class for image handlers.
    5.12  
    5.13 @@ -194,6 +197,7 @@ class ImageHandler:
    5.14          self.flags = 0
    5.15          if self.vm.netif_backend: self.flags |= SIF_NET_BE_DOMAIN
    5.16          if self.vm.blkif_backend: self.flags |= SIF_BLK_BE_DOMAIN
    5.17 +        if self.vm.tpmif_backend: self.flags |= SIF_TPM_BE_DOMAIN
    5.18  
    5.19          if self.vm.recreate or self.vm.restore:
    5.20              return
    5.21 @@ -366,6 +370,11 @@ class VmxImageHandler(ImageHandler):
    5.22                 mac = sxp.child_value(vifinfo, 'mac')
    5.23                 ret.append("-macaddr")
    5.24                 ret.append("%s" % mac)
    5.25 +            if name == 'vtpm':
    5.26 +               vtpminfo = sxp.child(device, 'vtpm')
    5.27 +               instance = sxp.child_value(vtpminfo, 'instance')
    5.28 +               ret.append("-instance")
    5.29 +               ret.append("%s" % instance)
    5.30  
    5.31  	# Handle graphics library related options
    5.32  	vnc = sxp.child_value(self.vm.config, 'vnc')
     6.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     6.2 +++ b/tools/python/xen/xend/server/tpmif.py	Tue Aug 30 11:28:26 2005 -0800
     6.3 @@ -0,0 +1,52 @@
     6.4 +# Copyright (C) 2005 IBM Corporation
     6.5 +#   Authort: Stefan Berger, stefanb@us.ibm.com
     6.6 +# Derived from netif.py:
     6.7 +# Copyright (C) 2004 Mike Wray <mike.wray@hp.com>
     6.8 +"""Support for virtual TPM interfaces.
     6.9 +"""
    6.10 +
    6.11 +import random
    6.12 +
    6.13 +from xen.xend import sxp
    6.14 +from xen.xend.XendError import XendError, VmError
    6.15 +from xen.xend.XendLogging import log
    6.16 +from xen.xend.XendRoot import get_component
    6.17 +from xen.xend.xenstore import DBVar
    6.18 +
    6.19 +from xen.xend.server import channel
    6.20 +from xen.xend.server.controller import CtrlMsgRcvr, Dev, DevController
    6.21 +from xen.xend.server.messages import *
    6.22 +
    6.23 +class TPMifController(DevController):
    6.24 +    """TPM interface controller. Handles all TPM devices for a domain.
    6.25 +    """
    6.26 +
    6.27 +    def __init__(self, vm, recreate=False):
    6.28 +        DevController.__init__(self, vm, recreate=recreate)
    6.29 +        self.rcvr = None
    6.30 +        self.channel = None
    6.31 +
    6.32 +    def initController(self, recreate=False, reboot=False):
    6.33 +        self.destroyed = False
    6.34 +        self.channel = self.getChannel()
    6.35 +
    6.36 +    def destroyController(self, reboot=False):
    6.37 +        """Destroy the controller and all devices.
    6.38 +        """
    6.39 +        self.destroyed = True
    6.40 +        self.destroyDevices(reboot=reboot)
    6.41 +        if self.rcvr:
    6.42 +            self.rcvr.deregisterChannel()
    6.43 +
    6.44 +    def sxpr(self):
    6.45 +        val = ['tpmif', ['dom', self.getDomain()]]
    6.46 +        return val
    6.47 +
    6.48 +    def newDevice(self, id, config, recreate=False):
    6.49 +        """Create a TPM device.
    6.50 +
    6.51 +        @param id: interface id
    6.52 +        @param config: device configuration
    6.53 +        @param recreate: recreate flag (true after xend restart)
    6.54 +        """
    6.55 +        return None
     7.1 --- a/tools/python/xen/xm/create.py	Tue Aug 30 11:19:52 2005 -0800
     7.2 +++ b/tools/python/xen/xm/create.py	Tue Aug 30 11:28:26 2005 -0800
     7.3 @@ -175,6 +175,12 @@ gopts.var('netif', val='no|yes',
     7.4            fn=set_bool, default=0,
     7.5            use="Make the domain a network interface backend.")
     7.6  
     7.7 +gopts.var('tpmif', val='frontend=DOM',
     7.8 +          fn=append_value, default=[],
     7.9 +          use="""Make the domain a TPM interface backend. If frontend is given,
    7.10 +          the frontend in that domain is connected to this backend (not
    7.11 +          completely implemented, yet)""")
    7.12 +
    7.13  gopts.var('disk', val='phy:DEV,VDEV,MODE[,DOM]',
    7.14            fn=append_value, default=[],
    7.15            use="""Add a disk device to a domain. The physical device is DEV,
    7.16 @@ -213,6 +219,12 @@ gopts.var('vif', val="mac=MAC,be_mac=MAC
    7.17            This option may be repeated to add more than one vif.
    7.18            Specifying vifs will increase the number of interfaces as needed.""")
    7.19  
    7.20 +gopts.var('vtpm', val="instance=INSTANCE,backend=DOM",
    7.21 +          fn=append_value, default=[],
    7.22 +          use="""Add a tpm interface. On the backend side us the the given
    7.23 +          instance as virtual TPM instance. Use the backend in the given
    7.24 +          domain.""")
    7.25 +
    7.26  gopts.var('nics', val="NUM",
    7.27            fn=set_int, default=1,
    7.28            use="""Set the number of network interfaces.
    7.29 @@ -369,6 +381,46 @@ def configure_usb(opts, config_devs, val
    7.30          config_usb = ['usb', ['path', path]]
    7.31          config_devs.append(['device', config_usb])
    7.32  
    7.33 +def configure_vtpm(opts, config_devs, vals):
    7.34 +    """Create the config for virtual TPM interfaces.
    7.35 +    """
    7.36 +    vtpm = vals.vtpm
    7.37 +    vtpm_n = 1
    7.38 +    for idx in range(0, vtpm_n):
    7.39 +        if idx < len(vtpm):
    7.40 +            d = vtpm[idx]
    7.41 +            instance = d.get('instance')
    7.42 +            if instance == "VTPMD":
    7.43 +                instance = "0"
    7.44 +            else:
    7.45 +                try:
    7.46 +                    if int(instance) == 0:
    7.47 +                        opts.err('VM config error: vTPM instance must not be 0.')
    7.48 +                except ValueError:
    7.49 +                    opts.err('Vm config error: could not parse instance number.')
    7.50 +            backend = d.get('backend')
    7.51 +            config_vtpm = ['vtpm']
    7.52 +            if instance:
    7.53 +                config_vtpm.append(['instance', instance])
    7.54 +            if backend:
    7.55 +                config_vtpm.append(['backend', backend])
    7.56 +            config_devs.append(['device', config_vtpm])
    7.57 +
    7.58 +def configure_tpmif(opts, config_devs, vals):
    7.59 +    """Create the config for virtual TPM interfaces.
    7.60 +    """
    7.61 +    tpmif = vals.tpmif
    7.62 +    tpmif_n = 1
    7.63 +    for idx in range(0, tpmif_n):
    7.64 +        if idx < len(tpmif):
    7.65 +            d = tpmif[idx]
    7.66 +            frontend = d.get('frontend')
    7.67 +            config_tpmif = ['tpmif']
    7.68 +            if frontend:
    7.69 +                config_tpmif.append(['frontend', frontend])
    7.70 +            config_devs.append(['device', config_tpmif])
    7.71 +
    7.72 +
    7.73  def randomMAC():
    7.74      """Generate a random MAC address.
    7.75  
    7.76 @@ -479,6 +531,8 @@ def make_config(opts, vals):
    7.77          config.append(['backend', ['blkif']])
    7.78      if vals.netif:
    7.79          config.append(['backend', ['netif']])
    7.80 +    if vals.tpmif:
    7.81 +        config.append(['backend', ['tpmif']])
    7.82      if vals.restart:
    7.83          config.append(['restart', vals.restart])
    7.84  
    7.85 @@ -491,6 +545,7 @@ def make_config(opts, vals):
    7.86      configure_pci(opts, config_devs, vals)
    7.87      configure_vifs(opts, config_devs, vals)
    7.88      configure_usb(opts, config_devs, vals)
    7.89 +    configure_vtpm(opts, config_devs, vals)
    7.90      configure_vmx(opts, config_devs, vals)
    7.91      config += config_devs
    7.92  
    7.93 @@ -539,6 +594,38 @@ def preprocess_vifs(opts, vals):
    7.94          vifs.append(d)
    7.95      vals.vif = vifs
    7.96  
    7.97 +def preprocess_vtpm(opts, vals):
    7.98 +    if not vals.vtpm: return
    7.99 +    vtpms = []
   7.100 +    for vtpm in vals.vtpm:
   7.101 +        d = {}
   7.102 +        a = vtpm.split(',')
   7.103 +        for b in a:
   7.104 +            (k, v) = b.strip().split('=', 1)
   7.105 +            k = k.strip()
   7.106 +            v = v.strip()
   7.107 +            if k not in ['backend', 'instance']:
   7.108 +                opts.err('Invalid vtpm specifier: ' + vtpm)
   7.109 +            d[k] = v
   7.110 +        vtpms.append(d)
   7.111 +    vals.vtpm = vtpms
   7.112 +
   7.113 +def preprocess_tpmif(opts, vals):
   7.114 +    if not vals.tpmif: return
   7.115 +    tpmifs = []
   7.116 +    for tpmif in vals.tpmif:
   7.117 +        d = {}
   7.118 +        a = tpmif.split(',')
   7.119 +        for b in a:
   7.120 +            (k, v) = b.strip().split('=', 1)
   7.121 +            k = k.strip()
   7.122 +            v = v.strip()
   7.123 +            if k not in ['frontend']:
   7.124 +                opts.err('Invalid tpmif specifier: ' + vtpm)
   7.125 +            d[k] = v
   7.126 +        tpmifs.append(d)
   7.127 +    vals.tpmif = tpmifs
   7.128 +
   7.129  def preprocess_ip(opts, vals):
   7.130      if vals.ip or vals.dhcp != 'off':
   7.131          dummy_nfs_server = '1.2.3.4'
   7.132 @@ -627,6 +714,8 @@ def preprocess(opts, vals):
   7.133      preprocess_ip(opts, vals)
   7.134      preprocess_nfs(opts, vals)
   7.135      preprocess_vnc(opts, vals)
   7.136 +    preprocess_vtpm(opts, vals)
   7.137 +    preprocess_tpmif(opts, vals)
   7.138           
   7.139  def make_domain(opts, config):
   7.140      """Create, build and start a domain.