docs: def create(vm_):
      '''
      Provision a single machine
      '''
      clone_strategy = vm_.get('clone_strategy') or 'full'
  
      if clone_strategy not in ('quick', 'full'):
          raise SaltCloudSystemExit("'clone_strategy' must be one of quick or full. Got '{0}'".format(clone_strategy))
  
      ip_source = vm_.get('ip_source') or 'ip-learning'
  
      if ip_source not in ('ip-learning', 'qemu-agent'):
          raise SaltCloudSystemExit("'ip_source' must be one of qemu-agent or ip-learning. Got '{0}'".format(ip_source))
  
      validate_xml = vm_.get('validate_xml') if vm_.get('validate_xml') is not None else True
  
      log.info("Cloning '%s' with strategy '%s' validate_xml='%s'", vm_['name'], clone_strategy, validate_xml)
  
      try:
          # Check for required profile parameters before sending any API calls.
          if vm_['profile'] and config.is_profile_configured(__opts__,
                                                             __active_provider_name__ or 'libvirt',
                                                             vm_['profile']) is False:
              return False
      except AttributeError:
          pass
  
      # TODO: check name qemu/libvirt will choke on some characters (like '/')?
      name = vm_['name']
  
      __utils__['cloud.fire_event'](
          'event',
          'starting create',
          'salt/cloud/{0}/creating'.format(name),
          args=__utils__['cloud.filter_event']('creating', vm_, ['name', 'profile', 'provider', 'driver']),
          sock_dir=__opts__['sock_dir'],
          transport=__opts__['transport']
      )
  
      key_filename = config.get_cloud_config_value(
          'private_key', vm_, __opts__, search_global=False, default=None
      )
      if key_filename is not None and not os.path.isfile(key_filename):
          raise SaltCloudConfigError(
              'The defined key_filename \'{0}\' does not exist'.format(
                  key_filename
              )
          )
      vm_['key_filename'] = key_filename
      # wait_for_instance requires private_key
      vm_['private_key'] = key_filename
  
      cleanup = []
      try:
          # clone the vm
          base = vm_['base_domain']
          conn = __get_conn(vm_['url'])
  
          try:
              # for idempotency the salt-bootstrap needs -F argument
              #  script_args: -F
              clone_domain = conn.lookupByName(name)
          except libvirtError as e:
              domain = conn.lookupByName(base)
              # TODO: ensure base is shut down before cloning
              xml = domain.XMLDesc(0)
  
              kwargs = {
                  'name': name,
                  'base_domain': base,
              }
  
              __utils__['cloud.fire_event'](
                  'event',
                  'requesting instance',
                  'salt/cloud/{0}/requesting'.format(name),
                  args={
                      'kwargs': __utils__['cloud.filter_event']('requesting', kwargs, list(kwargs)),
                  },
                  sock_dir=__opts__['sock_dir'],
                  transport=__opts__['transport']
              )
  
              log.debug("Source machine XML '%s'", xml)
  
              domain_xml = ElementTree.fromstring(xml)
              domain_xml.find('./name').text = name
              if domain_xml.find('./description') is None:
                  description_elem = ElementTree.Element('description')
                  domain_xml.insert(0, description_elem)
              description = domain_xml.find('./description')
              description.text = "Cloned from {0}".format(base)
              domain_xml.remove(domain_xml.find('./uuid'))
  
              for iface_xml in domain_xml.findall('./devices/interface'):
                  iface_xml.remove(iface_xml.find('./mac'))
                  # enable IP learning, this might be a default behaviour...
                  # Don't always enable since it can cause problems through libvirt-4.5
                  if ip_source == 'ip-learning' and iface_xml.find("./filterref/parameter[@name='CTRL_IP_LEARNING']") is None:
                      iface_xml.append(ElementTree.fromstring(IP_LEARNING_XML))
  
              # If a qemu agent is defined we need to fix the path to its socket
              # <channel type='unix'>
              #   <source mode='bind' path='/var/lib/libvirt/qemu/channel/target/domain-<dom-name>/org.qemu.guest_agent.0'/>
              #   <target type='virtio' name='org.qemu.guest_agent.0'/>
              #   <address type='virtio-serial' controller='0' bus='0' port='2'/>
              # </channel>
              for agent_xml in domain_xml.findall("""./devices/channel[@type='unix']"""):
                  #  is org.qemu.guest_agent.0 an option?
                  if agent_xml.find("""./target[@type='virtio'][@name='org.qemu.guest_agent.0']""") is not None:
                      source_element = agent_xml.find("""./source[@mode='bind']""")
                      # see if there is a path element that needs rewriting
                      if source_element and 'path' in source_element.attrib:
                          path = source_element.attrib['path']
                          new_path = path.replace('/domain-{0}/'.format(base), '/domain-{0}/'.format(name))
                          log.debug("Rewriting agent socket path to %s", new_path)
                          source_element.attrib['path'] = new_path
  
              for disk in domain_xml.findall("""./devices/disk[@device='disk'][@type='file']"""):
                  # print "Disk: ", ElementTree.tostring(disk)
                  # check if we can clone
                  driver = disk.find("./driver[@name='qemu']")
                  if driver is None:
                      # Err on the safe side
                      raise SaltCloudExecutionFailure("Non qemu driver disk encountered bailing out.")
                  disk_type = driver.attrib.get('type')
                  log.info("disk attributes %s", disk.attrib)
                  if disk_type == 'qcow2':
                      source = disk.find("./source").attrib['file']
                      pool, volume = find_pool_and_volume(conn, source)
                      if clone_strategy == 'quick':
                          new_volume = pool.createXML(create_volume_with_backing_store_xml(volume), 0)
                      else:
                          new_volume = pool.createXMLFrom(create_volume_xml(volume), volume, 0)
                      cleanup.append({'what': 'volume', 'item': new_volume})
  
                      disk.find("./source").attrib['file'] = new_volume.path()
                  elif disk_type == 'raw':
                      source = disk.find("./source").attrib['file']
                      pool, volume = find_pool_and_volume(conn, source)
                      # TODO: more control on the cloned disk type
                      new_volume = pool.createXMLFrom(create_volume_xml(volume), volume, 0)
                      cleanup.append({'what': 'volume', 'item': new_volume})
  
                      disk.find("./source").attrib['file'] = new_volume.path()
                  else:
                      raise SaltCloudExecutionFailure("Disk type '{0}' not supported".format(disk_type))
  
              clone_xml = salt.utils.stringutils.to_str(ElementTree.tostring(domain_xml))
              log.debug("Clone XML '%s'", clone_xml)
  
              validate_flags = libvirt.VIR_DOMAIN_DEFINE_VALIDATE if validate_xml else 0
              clone_domain = conn.defineXMLFlags(clone_xml, validate_flags)
  
              cleanup.append({'what': 'domain', 'item': clone_domain})
              clone_domain.createWithFlags(libvirt.VIR_DOMAIN_START_FORCE_BOOT)
  
          log.debug("VM '%s'", vm_)
  
          if ip_source == 'qemu-agent':
              ip_source = libvirt.VIR_DOMAIN_INTERFACE_ADDRESSES_SRC_AGENT
          elif ip_source == 'ip-learning':
              ip_source = libvirt.VIR_DOMAIN_INTERFACE_ADDRESSES_SRC_LEASE
  
          address = salt.utils.cloud.wait_for_ip(
              get_domain_ip,
              update_args=(clone_domain, 0, ip_source),
              timeout=config.get_cloud_config_value('wait_for_ip_timeout', vm_, __opts__, default=10 * 60),
              interval=config.get_cloud_config_value('wait_for_ip_interval', vm_, __opts__, default=10),
              interval_multiplier=config.get_cloud_config_value('wait_for_ip_interval_multiplier', vm_, __opts__, default=1),
          )
  
          log.info('Address = %s', address)
  
          vm_['ssh_host'] = address
  
          # the bootstrap script needs to be installed first in /etc/salt/cloud.deploy.d/
          # salt-cloud -u is your friend
          ret = __utils__['cloud.bootstrap'](vm_, __opts__)
  
          __utils__['cloud.fire_event'](
              'event',
              'created instance',
              'salt/cloud/{0}/created'.format(name),
              args=__utils__['cloud.filter_event']('created', vm_, ['name', 'profile', 'provider', 'driver']),
              sock_dir=__opts__['sock_dir'],
              transport=__opts__['transport']
          )
  
          return ret
      except Exception as e:  # pylint: disable=broad-except
          do_cleanup(cleanup)
          # throw the root cause after cleanup
          raise e