[libvirt] libvirtError: internal error unknown boot device 'floppy'
by John Lumby
Hello. I believe I've found a bug in libvirtd but not sure.
Using libvirt-0.8.1 and virtinst-0.500.3 (and virt-manager-0.8.4 and Python 2.6.5 if relevant) on a linux system (kernel 2.6.35-rc4 if relevant)
I ran this virt-install command , which is trying to create a windows2k virt mc by importing an existing system consisting of a boot-floppy image on a file (the boot device) and one real disk device on /dev/sdc
virt-install --connect qemu:///system --name=RH7win2k --ram=392 --cpuset=0 --description="win2k on RH7 disk on usb, nat network" --import --network=network=default --virt-type=kqemu --accelerate --vnc --vncport=5905 --video=cirrus --disk=/mnt/soltbakp/commonfiles/win2k_boot.floppage,device=floppy --disk=/dev/sdc,device=disk --os-type=windows --os-variant=win2k
and it fails like so
ERROR internal error unknown boot device 'floppy'
ERROR internal error unknown boot device 'floppy'
Traceback (most recent call last):
File "/usr/local/bin/virt-install", line 1033, in <module>
main()
File "/usr/local/bin/virt-install", line 915, in main
start_time, guest.start_install)
File "/usr/local/bin/virt-install", line 957, in do_install
dom = install_func(conscb, progresscb, wait=(not wait))
File "/usr/local/lib/python2.6/site-packages/virtinst/Guest.py", line 972, in start_install
return self._do_install(consolecb, meter, removeOld, wait)
File "/usr/local/lib/python2.6/site-packages/virtinst/Guest.py", line 1037, in _do_install
"install")
File "/usr/local/lib/python2.6/site-packages/virtinst/Guest.py", line 1021, in _create_guest
self.domain = self.conn.defineXML(final_xml)
File "/usr/local/lib/python2.6/site-packages/libvirt.py", line 1224, in defineXML
if ret is None:raise libvirtError('virDomainDefineXML() failed', conn=self)
libvirtError: internal error unknown boot device 'floppy'
but if I repeat the command with just interchanging the order of the floppy and disk definitions, (so that I am telling it to use the disk as boot device), then the virt-install works ok as far as setup goes, but of course fails during boot (and I can then alter the boot order back to what I should be in virt-manager and it then boots)
Is this a bug? and if so is it already known? (I couldn't find how to search the archives for this list and don't see it in google)
John Lumby
_________________________________________________________________
MSN Dating: Find someone special. Start now.
http://go.microsoft.com/?linkid=9734384
14 years, 4 months
[libvirt] [PATCH] cpuCompare: Fix comparison of two host CPUs
by Jiri Denemark
When a CPU to be compared with host CPU describes a host CPU instead of
a guest CPU, the result is incorrect. This is because instead of
treating additional features in host CPU description as required, they
were treated as if they were mentioned with all possible policies at the
same time.
---
src/cpu/cpu_x86.c | 13 +++++++------
1 files changed, 7 insertions(+), 6 deletions(-)
diff --git a/src/cpu/cpu_x86.c b/src/cpu/cpu_x86.c
index 114235c..ab7c8cc 100644
--- a/src/cpu/cpu_x86.c
+++ b/src/cpu/cpu_x86.c
@@ -826,8 +826,7 @@ x86ModelFromCPU(const virCPUDefPtr cpu,
struct x86_model *model = NULL;
int i;
- if (cpu->type == VIR_CPU_TYPE_HOST
- || policy == VIR_CPU_FEATURE_REQUIRE) {
+ if (policy == VIR_CPU_FEATURE_REQUIRE) {
if ((model = x86ModelFind(map, cpu->model)) == NULL) {
virCPUReportError(VIR_ERR_INTERNAL_ERROR,
_("Unknown CPU model %s"), cpu->model);
@@ -839,6 +838,8 @@ x86ModelFromCPU(const virCPUDefPtr cpu,
}
else if (VIR_ALLOC(model) < 0)
goto no_memory;
+ else if (cpu->type == VIR_CPU_TYPE_HOST)
+ return model;
for (i = 0; i < cpu->nfeatures; i++) {
const struct x86_feature *feature;
@@ -1181,7 +1182,7 @@ x86Compute(virCPUDefPtr host,
}
if (!(map = x86LoadMap()) ||
- !(host_model = x86ModelFromCPU(host, map, 0)) ||
+ !(host_model = x86ModelFromCPU(host, map, VIR_CPU_FEATURE_REQUIRE)) ||
!(cpu_force = x86ModelFromCPU(cpu, map, VIR_CPU_FEATURE_FORCE)) ||
!(cpu_require = x86ModelFromCPU(cpu, map, VIR_CPU_FEATURE_REQUIRE)) ||
!(cpu_optional = x86ModelFromCPU(cpu, map, VIR_CPU_FEATURE_OPTIONAL)) ||
@@ -1611,7 +1612,7 @@ x86Baseline(virCPUDefPtr *cpus,
if (!(map = x86LoadMap()))
goto error;
- if (!(base_model = x86ModelFromCPU(cpus[0], map, 0)))
+ if (!(base_model = x86ModelFromCPU(cpus[0], map, VIR_CPU_FEATURE_REQUIRE)))
goto error;
if (VIR_ALLOC(cpu) < 0 ||
@@ -1630,7 +1631,7 @@ x86Baseline(virCPUDefPtr *cpus,
for (i = 1; i < ncpus; i++) {
const char *vn = NULL;
- if (!(model = x86ModelFromCPU(cpus[i], map, 0)))
+ if (!(model = x86ModelFromCPU(cpus[i], map, VIR_CPU_FEATURE_REQUIRE)))
goto error;
if (cpus[i]->vendor && model->vendor &&
@@ -1710,7 +1711,7 @@ x86Update(virCPUDefPtr guest,
union cpuData *data = NULL;
if (!(map = x86LoadMap()) ||
- !(host_model = x86ModelFromCPU(host, map, 0)))
+ !(host_model = x86ModelFromCPU(host, map, VIR_CPU_FEATURE_REQUIRE)))
goto cleanup;
for (i = 0; i < guest->nfeatures; i++) {
--
1.7.1.1
14 years, 4 months
[libvirt] [PATCH] esx: Add autodetection for the SCSI controller model
by Matthias Bolte
This works for file-backed SCSI disk device with a datastore
related source path.
---
docs/drvesx.html.in | 6 ++
docs/schemas/domain.rng | 1 +
src/conf/domain_conf.c | 1 +
src/conf/domain_conf.h | 1 +
src/esx/esx_vi_generator.input | 149 +++++++++++++++++++++++++++++++++
src/esx/esx_vi_generator.py | 3 +
src/esx/esx_vmx.c | 180 +++++++++++++++++++++++++++++++++++++++-
src/esx/esx_vmx.h | 8 ++-
8 files changed, 344 insertions(+), 5 deletions(-)
diff --git a/docs/drvesx.html.in b/docs/drvesx.html.in
index f4e7530..75c24cb 100644
--- a/docs/drvesx.html.in
+++ b/docs/drvesx.html.in
@@ -292,6 +292,12 @@ ethernet0.checkMACAddress = "false"
<h4>SCSI controller models</h4>
<dl>
+ <dt><code>auto</code></dt>
+ <dd>
+ This isn't a actual controller model. If specified the ESX driver
+ tries to detect the SCSI controller model referenced in the
+ <code>.vmdk</code> file and use it. <span class="since">Since 0.8.3</span>
+ </dd>
<dt><code>buslogic</code></dt>
<dd>
BusLogic SCSI controller for older guests.
diff --git a/docs/schemas/domain.rng b/docs/schemas/domain.rng
index b171d01..e090366 100644
--- a/docs/schemas/domain.rng
+++ b/docs/schemas/domain.rng
@@ -673,6 +673,7 @@
<optional>
<attribute name="model">
<choice>
+ <value>auto</value>
<value>buslogic</value>
<value>lsilogic</value>
<value>lsisas1068</value>
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index 3cd43c4..eb7fa13 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -140,6 +140,7 @@ VIR_ENUM_IMPL(virDomainController, VIR_DOMAIN_CONTROLLER_TYPE_LAST,
"virtio-serial")
VIR_ENUM_IMPL(virDomainControllerModel, VIR_DOMAIN_CONTROLLER_MODEL_LAST,
+ "auto",
"buslogic",
"lsilogic",
"lsisas1068",
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
index 3451302..890fa0b 100644
--- a/src/conf/domain_conf.h
+++ b/src/conf/domain_conf.h
@@ -196,6 +196,7 @@ enum virDomainControllerType {
enum virDomainControllerModel {
+ VIR_DOMAIN_CONTROLLER_MODEL_AUTO,
VIR_DOMAIN_CONTROLLER_MODEL_BUSLOGIC,
VIR_DOMAIN_CONTROLLER_MODEL_LSILOGIC,
VIR_DOMAIN_CONTROLLER_MODEL_LSISAS1068,
diff --git a/src/esx/esx_vi_generator.input b/src/esx/esx_vi_generator.input
index ff65178..b4b33f6 100644
--- a/src/esx/esx_vi_generator.input
+++ b/src/esx/esx_vi_generator.input
@@ -184,6 +184,40 @@ object Event
end
+object FileInfo
+ String path r
+ Long fileSize o
+ DateTime modification o
+end
+
+
+object FileQuery
+end
+
+
+object FileQueryFlags
+ Boolean fileType r
+ Boolean fileSize r
+ Boolean modification r
+end
+
+
+object FloppyImageFileInfo extends FileInfo
+end
+
+
+object FloppyImageFileQuery extends FileQuery
+end
+
+
+object FolderFileInfo extends FileInfo
+end
+
+
+object FolderFileQuery extends FileQuery
+end
+
+
object HostCpuIdInfo
Int level r
String vendor o
@@ -194,6 +228,22 @@ object HostCpuIdInfo
end
+object HostDatastoreBrowserSearchResults
+ ManagedObjectReference datastore o
+ String folderPath o
+ FileInfo file ol
+end
+
+
+object HostDatastoreBrowserSearchSpec
+ FileQuery query ol
+ FileQueryFlags details o
+ Boolean searchCaseInsensitive o
+ String matchPattern ol
+ Boolean sortFoldersFirst o
+end
+
+
object HostFileSystemVolume
String type r
String name r
@@ -225,6 +275,14 @@ object HostVmfsVolume extends HostFileSystemVolume
end
+object IsoImageFileInfo extends FileInfo
+end
+
+
+object IsoImageFileQuery extends FileQuery
+end
+
+
object LocalDatastoreInfo extends DatastoreInfo
String path o
end
@@ -424,6 +482,14 @@ object TaskInfo
end
+object TemplateConfigFileInfo extends VmConfigFileInfo
+end
+
+
+object TemplateConfigFileQuery extends VmConfigFileQuery
+end
+
+
object TraversalSpec extends SelectionSpec
String type r
String path r
@@ -502,6 +568,82 @@ object VirtualMachineSnapshotTree
end
+object VmConfigFileInfo extends FileInfo
+ Int configVersion o
+end
+
+
+object VmConfigFileQuery extends FileQuery
+ VmConfigFileQueryFilter filter o
+ VmConfigFileQueryFlags details o
+end
+
+
+object VmConfigFileQueryFilter
+ Int matchConfigVersion ol
+end
+
+
+object VmConfigFileQueryFlags
+ Boolean configVersion r
+end
+
+
+object VmDiskFileInfo extends FileInfo
+ String diskType o
+ Long capacityKb o
+ Int hardwareVersion o
+ String controllerType o
+ String diskExtents ol
+end
+
+
+object VmDiskFileQuery extends FileQuery
+ VmDiskFileQueryFilter filter o
+ VmDiskFileQueryFlags details o
+end
+
+
+object VmDiskFileQueryFilter
+ String diskType ol
+ Int matchHardwareVersion ol
+ String controllerType ol
+end
+
+
+object VmDiskFileQueryFlags
+ Boolean diskType r
+ Boolean capacityKb r
+ Boolean hardwareVersion r
+ Boolean controllerType o
+ Boolean diskExtents o
+end
+
+
+object VmLogFileInfo extends FileInfo
+end
+
+
+object VmLogFileQuery extends FileQuery
+end
+
+
+object VmNvramFileInfo extends FileInfo
+end
+
+
+object VmNvramFileQuery extends FileQuery
+end
+
+
+object VmSnapshotFileInfo extends FileInfo
+end
+
+
+object VmSnapshotFileQuery extends FileQuery
+end
+
+
object VmfsDatastoreInfo extends DatastoreInfo
HostVmfsVolume vmfs o
end
@@ -658,6 +800,13 @@ method RevertToSnapshot_Task returns ManagedObjectReference r
end
+method SearchDatastore_Task returns ManagedObjectReference r
+ ManagedObjectReference _this r
+ String datastorePath r
+ HostDatastoreBrowserSearchSpec searchSpec o
+end
+
+
method SessionIsActive returns Boolean r
ManagedObjectReference _this:SessionManager r
String sessionID r
diff --git a/src/esx/esx_vi_generator.py b/src/esx/esx_vi_generator.py
index ff3e3d1..82bc9b6 100755
--- a/src/esx/esx_vi_generator.py
+++ b/src/esx/esx_vi_generator.py
@@ -1123,7 +1123,10 @@ additional_enum_features = { "ManagedEntityStatus" : Enum.FEATURE__ANY_TYPE
additional_object_features = { "DatastoreInfo" : Object.FEATURE__ANY_TYPE | Object.FEATURE__DYNAMIC_CAST,
"Event" : Object.FEATURE__LIST,
+ "FileInfo" : Object.FEATURE__DYNAMIC_CAST,
+ "FileQuery" : Object.FEATURE__DYNAMIC_CAST,
"HostCpuIdInfo" : Object.FEATURE__ANY_TYPE | Object.FEATURE__LIST,
+ "HostDatastoreBrowserSearchResults" : Object.FEATURE__ANY_TYPE,
"ManagedObjectReference" : Object.FEATURE__ANY_TYPE,
"ObjectContent" : Object.FEATURE__DEEP_COPY | Object.FEATURE__LIST,
"PerfCounterInfo" : Object.FEATURE__LIST,
diff --git a/src/esx/esx_vmx.c b/src/esx/esx_vmx.c
index 46875f3..f57e046 100644
--- a/src/esx/esx_vmx.c
+++ b/src/esx/esx_vmx.c
@@ -29,6 +29,7 @@
#include "virterror_internal.h"
#include "memory.h"
#include "logging.h"
+#include "esx_vi_methods.h"
#include "esx_private.h"
#include "esx_util.h"
#include "esx_vmx.h"
@@ -707,8 +708,172 @@ esxVMX_HandleLegacySCSIDiskDriverName(virDomainDefPtr def,
int
-esxVMX_GatherSCSIControllers(virDomainDefPtr def, int virtualDev[4],
- bool present[4])
+esxVMX_AutodetectSCSIControllerModel(esxVI_Context *ctx,
+ virDomainDiskDefPtr def, int *model)
+{
+ int result = -1;
+ char *datastoreName = NULL;
+ char *directoryName = NULL;
+ char *fileName = NULL;
+ char *datastorePath = NULL;
+ esxVI_String *propertyNameList = NULL;
+ esxVI_ObjectContent *datastore = NULL;
+ esxVI_ManagedObjectReference *hostDatastoreBrowser = NULL;
+ esxVI_HostDatastoreBrowserSearchSpec *searchSpec = NULL;
+ esxVI_VmDiskFileQuery *vmDiskFileQuery = NULL;
+ esxVI_ManagedObjectReference *task = NULL;
+ esxVI_TaskInfoState taskInfoState;
+ esxVI_TaskInfo *taskInfo = NULL;
+ esxVI_HostDatastoreBrowserSearchResults *searchResults = NULL;
+ esxVI_VmDiskFileInfo *vmDiskFileInfo = NULL;
+
+ if (def->device != VIR_DOMAIN_DISK_DEVICE_DISK ||
+ def->bus != VIR_DOMAIN_DISK_BUS_SCSI ||
+ def->type != VIR_DOMAIN_DISK_TYPE_FILE ||
+ def->src == NULL ||
+ ! STRPREFIX(def->src, "[")) {
+ /*
+ * This isn't a file-based SCSI disk device with a datastore related
+ * source path => do nothing.
+ */
+ return 0;
+ }
+
+ if (esxUtil_ParseDatastoreRelatedPath(def->src, &datastoreName,
+ &directoryName, &fileName) < 0) {
+ goto cleanup;
+ }
+
+ if (directoryName == NULL) {
+ if (virAsprintf(&datastorePath, "[%s]", datastoreName) < 0) {
+ virReportOOMError();
+ goto cleanup;
+ }
+ } else {
+ if (virAsprintf(&datastorePath, "[%s] %s", datastoreName,
+ directoryName) < 0) {
+ virReportOOMError();
+ goto cleanup;
+ }
+ }
+
+ /* Lookup HostDatastoreBrowser */
+ if (esxVI_String_AppendValueToList(&propertyNameList, "browser") < 0 ||
+ esxVI_LookupDatastoreByName(ctx, datastoreName, propertyNameList,
+ &datastore,
+ esxVI_Occurrence_RequiredItem) < 0 ||
+ esxVI_GetManagedObjectReference(datastore, "browser",
+ &hostDatastoreBrowser,
+ esxVI_Occurrence_RequiredItem) < 0) {
+ goto cleanup;
+ }
+
+ /* Build HostDatastoreBrowserSearchSpec */
+ if (esxVI_HostDatastoreBrowserSearchSpec_Alloc(&searchSpec) < 0 ||
+ esxVI_FileQueryFlags_Alloc(&searchSpec->details) < 0) {
+ goto cleanup;
+ }
+
+ searchSpec->details->fileType = esxVI_Boolean_True;
+ searchSpec->details->fileSize = esxVI_Boolean_False;
+ searchSpec->details->modification = esxVI_Boolean_False;
+
+ if (esxVI_VmDiskFileQuery_Alloc(&vmDiskFileQuery) < 0 ||
+ esxVI_VmDiskFileQueryFlags_Alloc(&vmDiskFileQuery->details) < 0 ||
+ esxVI_FileQuery_AppendToList
+ (&searchSpec->query,
+ esxVI_FileQuery_DynamicCast(vmDiskFileQuery)) < 0) {
+ goto cleanup;
+ }
+
+ vmDiskFileQuery->details->diskType = esxVI_Boolean_False;
+ vmDiskFileQuery->details->capacityKb = esxVI_Boolean_False;
+ vmDiskFileQuery->details->hardwareVersion = esxVI_Boolean_False;
+ vmDiskFileQuery->details->controllerType = esxVI_Boolean_True;
+ vmDiskFileQuery->details->diskExtents = esxVI_Boolean_False;
+
+ if (esxVI_String_Alloc(&searchSpec->matchPattern) < 0) {
+ goto cleanup;
+ }
+
+ searchSpec->matchPattern->value = fileName;
+
+ /* Search datastore for file */
+ if (esxVI_SearchDatastore_Task(ctx, hostDatastoreBrowser, datastorePath,
+ searchSpec, &task) < 0 ||
+ esxVI_WaitForTaskCompletion(ctx, task, NULL, esxVI_Boolean_False,
+ &taskInfoState) < 0) {
+ goto cleanup;
+ }
+
+ if (taskInfoState != esxVI_TaskInfoState_Success) {
+ ESX_ERROR(VIR_ERR_INTERNAL_ERROR,
+ _("Could not serach in datastore '%s'"), datastoreName);
+ goto cleanup;
+ }
+
+ if (esxVI_LookupTaskInfoByTask(ctx, task, &taskInfo) < 0 ||
+ esxVI_HostDatastoreBrowserSearchResults_CastFromAnyType
+ (taskInfo->result, &searchResults) < 0) {
+ goto cleanup;
+ }
+
+ /* Interpret search result */
+ vmDiskFileInfo = esxVI_VmDiskFileInfo_DynamicCast(searchResults->file);
+
+ if (vmDiskFileInfo == NULL || vmDiskFileInfo->controllerType == NULL) {
+ ESX_ERROR(VIR_ERR_INTERNAL_ERROR,
+ _("Could not lookup controller model for '%s'"), def->src);
+ goto cleanup;
+ }
+
+ if (STRCASEEQ(vmDiskFileInfo->controllerType,
+ "VirtualBusLogicController")) {
+ *model = VIR_DOMAIN_CONTROLLER_MODEL_BUSLOGIC;
+ } else if (STRCASEEQ(vmDiskFileInfo->controllerType,
+ "VirtualLsiLogicController")) {
+ *model = VIR_DOMAIN_CONTROLLER_MODEL_LSILOGIC;
+ } else if (STRCASEEQ(vmDiskFileInfo->controllerType,
+ "VirtualLsiLogicSASController")) {
+ *model = VIR_DOMAIN_CONTROLLER_MODEL_LSISAS1068;
+ } else if (STRCASEEQ(vmDiskFileInfo->controllerType,
+ "ParaVirtualSCSIController")) {
+ *model = VIR_DOMAIN_CONTROLLER_MODEL_PVSCSI;
+ } else {
+ ESX_ERROR(VIR_ERR_INTERNAL_ERROR,
+ _("Found unexpected controller model '%s' for disk '%s'"),
+ vmDiskFileInfo->controllerType, def->src);
+ goto cleanup;
+ }
+
+ result = 0;
+
+ cleanup:
+ /* Don't double free fileName */
+ if (searchSpec != NULL && searchSpec->matchPattern != NULL) {
+ searchSpec->matchPattern->value = NULL;
+ }
+
+ VIR_FREE(datastoreName);
+ VIR_FREE(directoryName);
+ VIR_FREE(fileName);
+ VIR_FREE(datastorePath);
+ esxVI_String_Free(&propertyNameList);
+ esxVI_ObjectContent_Free(&datastore);
+ esxVI_ManagedObjectReference_Free(&hostDatastoreBrowser);
+ esxVI_HostDatastoreBrowserSearchSpec_Free(&searchSpec);
+ esxVI_ManagedObjectReference_Free(&task);
+ esxVI_TaskInfo_Free(&taskInfo);
+ esxVI_HostDatastoreBrowserSearchResults_Free(&searchResults);
+
+ return result;
+}
+
+
+
+int
+esxVMX_GatherSCSIControllers(esxVI_Context *ctx, virDomainDefPtr def,
+ int virtualDev[4], bool present[4])
{
int i;
virDomainDiskDefPtr disk;
@@ -737,6 +902,14 @@ esxVMX_GatherSCSIControllers(virDomainDefPtr def, int virtualDev[4],
return -1;
}
+ if (ctx != NULL &&
+ controller->model == VIR_DOMAIN_CONTROLLER_MODEL_AUTO) {
+ if (esxVMX_AutodetectSCSIControllerModel(ctx, disk,
+ &controller->model) < 0) {
+ return -1;
+ }
+ }
+
if (controller->model != -1 &&
controller->model != VIR_DOMAIN_CONTROLLER_MODEL_BUSLOGIC &&
controller->model != VIR_DOMAIN_CONTROLLER_MODEL_LSILOGIC &&
@@ -2611,7 +2784,8 @@ esxVMX_FormatConfig(esxVI_Context *ctx, virCapsPtr caps, virDomainDefPtr def,
}
}
- if (esxVMX_GatherSCSIControllers(def, scsi_virtualDev, scsi_present) < 0) {
+ if (esxVMX_GatherSCSIControllers(ctx, def, scsi_virtualDev,
+ scsi_present) < 0) {
goto failure;
}
diff --git a/src/esx/esx_vmx.h b/src/esx/esx_vmx.h
index a9015fb..3ccae7a 100644
--- a/src/esx/esx_vmx.h
+++ b/src/esx/esx_vmx.h
@@ -48,8 +48,12 @@ esxVMX_HandleLegacySCSIDiskDriverName(virDomainDefPtr def,
virDomainDiskDefPtr disk);
int
-esxVMX_GatherSCSIControllers(virDomainDefPtr def, int virtualDev[4],
- bool present[4]);
+esxVMX_AutodetectSCSIControllerModel(esxVI_Context *ctx,
+ virDomainDiskDefPtr def, int *model);
+
+int
+esxVMX_GatherSCSIControllers(esxVI_Context *ctx, virDomainDefPtr def,
+ int virtualDev[4], bool present[4]);
char *
esxVMX_AbsolutePathToDatastoreRelatedPath(esxVI_Context *ctx,
--
1.7.0.4
14 years, 4 months
[libvirt] [PATCH] esx: Make esxVI_*_Deserialize dynamically dispatched
by Matthias Bolte
This will be used to deserialize the response from a call
to esxVI_SearchDatastore_Task (to be added in the next patch)
properly.
---
src/esx/esx_vi_generator.py | 45 ++++++++++++++++++------
src/esx/esx_vi_types.c | 82 ++++++++++++++++++++++++++++++++++++++++++-
2 files changed, 115 insertions(+), 12 deletions(-)
diff --git a/src/esx/esx_vi_generator.py b/src/esx/esx_vi_generator.py
index 8df0e80..ff3e3d1 100755
--- a/src/esx/esx_vi_generator.py
+++ b/src/esx/esx_vi_generator.py
@@ -469,18 +469,21 @@ class Object:
return source
- def generate_dynamic_cast_code(self):
+ def generate_dynamic_cast_code(self, is_first = True):
global objects_by_name
source = ""
if self.extended_by is not None:
+ if not is_first:
+ source += "\n"
+
source += " /* %s */\n" % self.name
for extended_by in self.extended_by:
source += " ESX_VI__TEMPLATE__DYNAMIC_CAST__ACCEPT(%s)\n" % extended_by
for extended_by in self.extended_by:
- source += objects_by_name[extended_by].generate_dynamic_cast_code()
+ source += objects_by_name[extended_by].generate_dynamic_cast_code(False)
return source
@@ -820,18 +823,38 @@ class Object:
source += "ESX_VI__TEMPLATE__LIST__SERIALIZE(%s)\n\n" % self.name
# deserilaize
- if self.features & Object.FEATURE__DESERIALIZE:
- source += "/* esxVI_%s_Deserialize */\n" % self.name
- source += "ESX_VI__TEMPLATE__DESERIALIZE(%s,\n" % self.name
- source += "{\n"
+ if self.extended_by is None:
+ if self.features & Object.FEATURE__DESERIALIZE:
+ source += "/* esxVI_%s_Deserialize */\n" % self.name
+ source += "ESX_VI__TEMPLATE__DESERIALIZE(%s,\n" % self.name
+ source += "{\n"
- source += self.generate_deserialize_code()
+ source += self.generate_deserialize_code()
- source += "})\n\n"
+ source += "})\n\n"
- if self.features & Object.FEATURE__LIST:
- source += "/* esxVI_%s_DeserializeList */\n" % self.name
- source += "ESX_VI__TEMPLATE__LIST__DESERIALIZE(%s)\n\n" % self.name
+ if self.features & Object.FEATURE__LIST:
+ source += "/* esxVI_%s_DeserializeList */\n" % self.name
+ source += "ESX_VI__TEMPLATE__LIST__DESERIALIZE(%s)\n\n" % self.name
+ else:
+ if self.features & Object.FEATURE__DESERIALIZE:
+ source += "/* esxVI_%s_Deserialize */\n" % self.name
+ source += "ESX_VI__TEMPLATE__DYNAMIC_DESERIALIZE(%s,\n" % self.name
+ source += "{\n"
+
+ for extended_by in self.extended_by:
+ source += " ESX_VI__TEMPLATE__DISPATCH__DESERIALIZE(%s)\n" % extended_by
+
+ source += "},\n"
+ source += "{\n"
+
+ source += self.generate_deserialize_code()
+
+ source += "})\n\n"
+
+ if self.features & Object.FEATURE__LIST:
+ source += "/* esxVI_%s_DeserializeList */\n" % self.name
+ source += "ESX_VI__TEMPLATE__LIST__DESERIALIZE(%s)\n\n" % self.name
source += "\n\n"
diff --git a/src/esx/esx_vi_types.c b/src/esx/esx_vi_types.c
index 3f34fee..6e75995 100644
--- a/src/esx/esx_vi_types.c
+++ b/src/esx/esx_vi_types.c
@@ -250,12 +250,14 @@
-#define ESX_VI__TEMPLATE__DESERIALIZE(_type, _deserialize) \
+#define ESX_VI__TEMPLATE__DESERIALIZE_EXTRA(_type, _extra, _deserialize) \
int \
esxVI_##_type##_Deserialize(xmlNodePtr node, esxVI_##_type **ptrptr) \
{ \
xmlNodePtr childNode = NULL; \
\
+ _extra \
+ \
if (ptrptr == NULL || *ptrptr != NULL) { \
ESX_VI_ERROR(VIR_ERR_INTERNAL_ERROR, "%s", \
_("Invalid argument")); \
@@ -293,6 +295,11 @@
+#define ESX_VI__TEMPLATE__DESERIALIZE(_type, _deserialize) \
+ ESX_VI__TEMPLATE__DESERIALIZE_EXTRA(_type, /* nothing */, _deserialize)
+
+
+
#define ESX_VI__TEMPLATE__DESERIALIZE_NUMBER(_type, _xsdType, _min, _max) \
int \
esxVI_##_type##_Deserialize(xmlNodePtr node, esxVI_##_type **number) \
@@ -544,6 +551,12 @@
+#define ESX_VI__TEMPLATE__DISPATCH__DESERIALIZE(_type) \
+ case esxVI_Type_##_type: \
+ return esxVI_##_type##_Deserialize(node, (esxVI_##_type **)ptrptr);
+
+
+
#define ESX_VI__TEMPLATE__DYNAMIC_FREE(__type, _dispatch, _body) \
ESX_VI__TEMPLATE__FREE(__type, \
ESX_VI__TEMPLATE__DISPATCH(__type, _dispatch, /* nothing */) \
@@ -584,6 +597,73 @@
+#define ESX_VI__TEMPLATE__DYNAMIC_DESERIALIZE(__type, _dispatch, \
+ _deserialize) \
+ ESX_VI__TEMPLATE__DESERIALIZE_EXTRA(__type, \
+ esxVI_Type type = esxVI_Type_Undefined; \
+ \
+ if (esxVI_GetActualObjectType(node, esxVI_Type_##__type, &type) < 0) { \
+ return -1; \
+ } \
+ \
+ switch (type) { \
+ _dispatch \
+ \
+ case esxVI_Type_##__type: \
+ break; \
+ \
+ default: \
+ ESX_VI_ERROR(VIR_ERR_INTERNAL_ERROR, \
+ _("Call to %s for unexpected type '%s'"), \
+ __FUNCTION__, esxVI_Type_ToString(type)); \
+ return -1; \
+ }, \
+ _deserialize)
+
+
+
+static int
+esxVI_GetActualObjectType(xmlNodePtr node, esxVI_Type baseType,
+ esxVI_Type *actualType)
+{
+ int result = -1;
+ char *type = NULL;
+
+ if (actualType == NULL || *actualType != esxVI_Type_Undefined) {
+ ESX_VI_ERROR(VIR_ERR_INTERNAL_ERROR, "%s", _("Invalid argument"));
+ return -1;
+ }
+
+ type = (char *)xmlGetNsProp
+ (node, BAD_CAST "type",
+ BAD_CAST "http://www.w3.org/2001/XMLSchema-instance");
+
+ if (type == NULL) {
+ ESX_VI_ERROR(VIR_ERR_INTERNAL_ERROR,
+ _("%s is missing 'type' property"),
+ esxVI_Type_ToString(baseType));
+ return -1;
+ }
+
+ *actualType = esxVI_Type_FromString(type);
+
+ if (*actualType == esxVI_Type_Undefined) {
+ ESX_VI_ERROR(VIR_ERR_INTERNAL_ERROR,
+ _("Unknown value '%s' for %s 'type' property"),
+ type, esxVI_Type_ToString(baseType));
+ goto cleanup;
+ }
+
+ result = 0;
+
+ cleanup:
+ VIR_FREE(type);
+
+ return result;
+}
+
+
+
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
* XSI: Type
*/
--
1.7.0.4
14 years, 4 months
[libvirt] [PATCH 0/1] RFC: Canonicalize block device paths
by David Allan
I had a look at the problem of finding the devices representing the
partitions of a block device, and it's a messy problem. There are a
lot of different conventions that are used depending on what kind of
device is partitioned. The following patch seems like a promising
approach, but before I spend a bunch of time testing that it works in
a variety of cases, I thought I should send it out for comment.
Dave
David Allan (1):
RFC: Canonicalize block device paths
src/Makefile.am | 9 +++++++--
src/storage/parthelper.c | 35 +++++++++++++++++++++++++++++++++--
2 files changed, 40 insertions(+), 4 deletions(-)
14 years, 4 months
[libvirt] [PATCH] Add openauth example to demonstrate a custom auth callback
by Matthias Bolte
---
Makefile.am | 2 +-
configure.ac | 1 +
examples/openauth/.gitignore | 5 +
examples/openauth/Makefile.am | 5 +
examples/openauth/openauth.c | 287 +++++++++++++++++++++++++++++++++++++++++
libvirt.spec.in | 3 +-
6 files changed, 301 insertions(+), 2 deletions(-)
create mode 100644 examples/openauth/.gitignore
create mode 100644 examples/openauth/Makefile.am
create mode 100644 examples/openauth/openauth.c
diff --git a/Makefile.am b/Makefile.am
index 286b13b..a6af20f 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -6,7 +6,7 @@ GENHTML = genhtml
SUBDIRS = gnulib/lib include src daemon tools proxy docs gnulib/tests \
python tests po examples/domain-events/events-c examples/hellolibvirt \
examples/dominfo examples/domsuspend examples/python examples/apparmor \
- examples/xml/nwfilter
+ examples/xml/nwfilter examples/openauth
ACLOCAL_AMFLAGS = -I m4 -I gnulib/m4
diff --git a/configure.ac b/configure.ac
index c9c5b53..eece723 100644
--- a/configure.ac
+++ b/configure.ac
@@ -2129,6 +2129,7 @@ AC_OUTPUT(Makefile src/Makefile include/Makefile docs/Makefile \
examples/domain-events/events-c/Makefile \
examples/domsuspend/Makefile \
examples/dominfo/Makefile \
+ examples/openauth/Makefile \
examples/python/Makefile \
examples/hellolibvirt/Makefile \
examples/xml/nwfilter/Makefile)
diff --git a/examples/openauth/.gitignore b/examples/openauth/.gitignore
new file mode 100644
index 0000000..1431557
--- /dev/null
+++ b/examples/openauth/.gitignore
@@ -0,0 +1,5 @@
+Makefile
+Makefile.in
+openauth
+.deps
+.libs
diff --git a/examples/openauth/Makefile.am b/examples/openauth/Makefile.am
new file mode 100644
index 0000000..279a032
--- /dev/null
+++ b/examples/openauth/Makefile.am
@@ -0,0 +1,5 @@
+INCLUDES = -I$(top_builddir)/include -I$(top_srcdir)/include
+noinst_PROGRAMS = openauth
+openauth_CFLAGS = $(WARN_CFLAGS)
+openauth_SOURCES = openauth.c
+openauth_LDADD = @top_builddir(a)/src/libvirt.la
diff --git a/examples/openauth/openauth.c b/examples/openauth/openauth.c
new file mode 100644
index 0000000..ff830cb
--- /dev/null
+++ b/examples/openauth/openauth.c
@@ -0,0 +1,287 @@
+/* This is a copy of the hellolibvirt example demonstaring how to use
+ * virConnectOpenAuth with a custom auth callback */
+
+#include <config.h>
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <libvirt/libvirt.h>
+#include <libvirt/virterror.h>
+
+static void
+showError(virConnectPtr conn)
+{
+ int ret;
+ virErrorPtr err;
+
+ err = malloc(sizeof(*err));
+ if (NULL == err) {
+ printf("Could not allocate memory for error data\n");
+ goto out;
+ }
+
+ ret = virConnCopyLastError(conn, err);
+
+ switch (ret) {
+ case 0:
+ printf("No error found\n");
+ break;
+
+ case -1:
+ printf("Parameter error when attempting to get last error\n");
+ break;
+
+ default:
+ printf("libvirt reported: \"%s\"\n", err->message);
+ break;
+ }
+
+ virResetError(err);
+ free(err);
+
+out:
+ return;
+}
+
+
+static int
+showHypervisorInfo(virConnectPtr conn)
+{
+ int ret = 0;
+ unsigned long hvVer, major, minor, release;
+ const char *hvType;
+
+ /* virConnectGetType returns a pointer to a static string, so no
+ * allocation or freeing is necessary; it is possible for the call
+ * to fail if, for example, there is no connection to a
+ * hypervisor, so check what it returns. */
+ hvType = virConnectGetType(conn);
+ if (NULL == hvType) {
+ ret = 1;
+ printf("Failed to get hypervisor type\n");
+ showError(conn);
+ goto out;
+ }
+
+ if (0 != virConnectGetVersion(conn, &hvVer)) {
+ ret = 1;
+ printf("Failed to get hypervisor version\n");
+ showError(conn);
+ goto out;
+ }
+
+ major = hvVer / 1000000;
+ hvVer %= 1000000;
+ minor = hvVer / 1000;
+ release = hvVer % 1000;
+
+ printf("Hypervisor: \"%s\" version: %lu.%lu.%lu\n",
+ hvType,
+ major,
+ minor,
+ release);
+
+out:
+ return ret;
+}
+
+
+static int
+showDomains(virConnectPtr conn)
+{
+ int ret = 0, i, numNames, numInactiveDomains, numActiveDomains;
+ char **nameList = NULL;
+
+ numActiveDomains = virConnectNumOfDomains(conn);
+ if (-1 == numActiveDomains) {
+ ret = 1;
+ printf("Failed to get number of active domains\n");
+ showError(conn);
+ goto out;
+ }
+
+ numInactiveDomains = virConnectNumOfDefinedDomains(conn);
+ if (-1 == numInactiveDomains) {
+ ret = 1;
+ printf("Failed to get number of inactive domains\n");
+ showError(conn);
+ goto out;
+ }
+
+ printf("There are %d active and %d inactive domains\n",
+ numActiveDomains, numInactiveDomains);
+
+ nameList = malloc(sizeof(*nameList) * numInactiveDomains);
+
+ if (NULL == nameList) {
+ ret = 1;
+ printf("Could not allocate memory for list of inactive domains\n");
+ goto out;
+ }
+
+ numNames = virConnectListDefinedDomains(conn,
+ nameList,
+ numInactiveDomains);
+
+ if (-1 == numNames) {
+ ret = 1;
+ printf("Could not get list of defined domains from hypervisor\n");
+ showError(conn);
+ goto out;
+ }
+
+ if (numNames > 0) {
+ printf("Inactive domains:\n");
+ }
+
+ for (i = 0 ; i < numNames ; i++) {
+ printf(" %s\n", *(nameList + i));
+ /* The API documentation doesn't say so, but the names
+ * returned by virConnectListDefinedDomains are strdup'd and
+ * must be freed here. */
+ free(*(nameList + i));
+ }
+
+out:
+ free(nameList);
+ return ret;
+}
+
+/* Struct to pass the credentials to the auth callback via the cbdata pointer */
+struct _AuthData {
+ char *username;
+ char *password;
+};
+
+typedef struct _AuthData AuthData;
+
+/* This function will be called by libvirt to obtain credentials in order to
+ * authenticate to the hypervisor */
+static int
+authCallback(virConnectCredentialPtr cred, unsigned int ncred, void *cbdata)
+{
+ int i;
+ AuthData *authData = cbdata;
+
+ /* libvirt might request multiple credentials in a single call.
+ * This example supports VIR_CRED_AUTHNAME and VIR_CRED_PASSPHRASE
+ * credentials only, but there are several other types.
+ *
+ * A request may also contain a prompt message that can be displayed
+ * to the user and a challenge. The challenge is specific to the
+ * credential type and hypervisor type.
+ *
+ * For example the ESX driver passes the hostname of the ESX or vCenter
+ * server as challenge. This allows a auth callback to return the
+ * proper credentials. */
+ for (i = 0; i < ncred ; ++i) {
+ switch (cred[i].type) {
+ case VIR_CRED_AUTHNAME:
+ cred[i].result = strdup(authData->username);
+
+ if (cred[i].result == NULL) {
+ return -1;
+ }
+
+ cred[i].resultlen = strlen(cred[i].result);
+ break;
+
+ case VIR_CRED_PASSPHRASE:
+ cred[i].result = strdup(authData->password);
+
+ if (cred[i].result == NULL) {
+ return -1;
+ }
+
+ cred[i].resultlen = strlen(cred[i].result);
+ break;
+
+ default:
+ return -1;
+ }
+ }
+
+ return 0;
+}
+
+
+/* The list of credential types supported by our auth callback */
+static int credTypes[] = {
+ VIR_CRED_AUTHNAME,
+ VIR_CRED_PASSPHRASE
+};
+
+
+/* The auth struct that will be passed to virConnectOpenAuth */
+static virConnectAuth auth = {
+ credTypes,
+ sizeof(credTypes) / sizeof(int),
+ authCallback,
+ NULL, // cbdata will be initialized in main
+};
+
+
+int
+main(int argc, char *argv[])
+{
+ int ret = 0;
+ virConnectPtr conn;
+ char *uri;
+ AuthData authData;
+
+ if (argc != 4) {
+ ret = 1;
+ printf("Usage: %s <uri> <username> <password>\n", argv[0]);
+ goto out;
+ }
+
+ uri = argv[1];
+ authData.username = argv[2];
+ authData.password = argv[3];
+ auth.cbdata = &authData;
+
+ printf("Attempting to connect to hypervisor\n");
+
+ conn = virConnectOpenAuth(uri, &auth, 0);
+
+ if (NULL == conn) {
+ ret = 1;
+ printf("No connection to hypervisor\n");
+ showError(conn);
+ goto out;
+ }
+
+ uri = virConnectGetURI(conn);
+ if (NULL == uri) {
+ ret = 1;
+ printf("Failed to get URI for hypervisor connection\n");
+ showError(conn);
+ goto disconnect;
+ }
+
+ printf("Connected to hypervisor at \"%s\"\n", uri);
+ free(uri);
+
+ if (0 != showHypervisorInfo(conn)) {
+ ret = 1;
+ goto disconnect;
+ }
+
+ if (0 != showDomains(conn)) {
+ ret = 1;
+ goto disconnect;
+ }
+
+disconnect:
+ if (0 != virConnectClose(conn)) {
+ printf("Failed to disconnect from hypervisor\n");
+ showError(conn);
+ ret = 1;
+ } else {
+ printf("Disconnected from hypervisor\n");
+ }
+
+out:
+ return ret;
+}
diff --git a/libvirt.spec.in b/libvirt.spec.in
index 33e757c..ce58f2a 100644
--- a/libvirt.spec.in
+++ b/libvirt.spec.in
@@ -585,7 +585,7 @@ gzip -9 ChangeLog
rm -fr %{buildroot}
%makeinstall
-for i in domain-events/events-c dominfo domsuspend hellolibvirt python xml/nwfilter
+for i in domain-events/events-c dominfo domsuspend hellolibvirt openauth python xml/nwfilter
do
(cd examples/$i ; make clean ; rm -rf .deps .libs Makefile Makefile.in)
done
@@ -887,6 +887,7 @@ fi
%doc examples/domain-events/events-c
%doc examples/dominfo
%doc examples/domsuspend
+%doc examples/openauth
%doc examples/xml
%if %{with_python}
--
1.7.0.4
14 years, 4 months
[libvirt] [PATCH] Eliminate compiler warning due to gettext string with no format args
by Laine Stump
From: Laine Stump <laine(a)redhat.com>
I just pushed this trivial fix, since it breaks the build for anyone
who uses -Wformat-security -Werror.
---
tools/virsh.c | 2 +-
1 files changed, 1 insertions(+), 1 deletions(-)
diff --git a/tools/virsh.c b/tools/virsh.c
index 8e6e2b4..38ecc0f 100644
--- a/tools/virsh.c
+++ b/tools/virsh.c
@@ -1462,7 +1462,7 @@ cmdManagedSaveRemove(vshControl *ctl, const vshCmd *cmd)
hassave = virDomainHasManagedSaveImage(dom, 0);
if (hassave < 0) {
- vshError(ctl, _("Failed to check for domain managed save image"));
+ vshError(ctl, "%s", _("Failed to check for domain managed save image"));
goto cleanup;
}
--
1.7.1.1
14 years, 4 months
[libvirt] [PATCH] docs: fix so generated .html files are removed with make clean
by Justin Clift
---
This is a simple fix so generated .html files in the docs directory
are removed when make clean is run. Otherwise they're left in place.
docs/Makefile.am | 2 +-
1 files changed, 1 insertions(+), 1 deletions(-)
diff --git a/docs/Makefile.am b/docs/Makefile.am
index 1183321..a6a6d07 100644
--- a/docs/Makefile.am
+++ b/docs/Makefile.am
@@ -150,7 +150,7 @@ $(python_generated_files): $(srcdir)/apibuild.py \
check-local: all
clean-local:
- rm -f *~ *.bak *.hierarchy *.signals *-unused.txt
+ rm -f *~ *.bak *.hierarchy *.signals *-unused.txt *.html
maintainer-clean-local: clean-local
rm -rf libvirt-api.xml libvirt-refs.xml
--
1.7.1.1
14 years, 4 months
[libvirt] [PATCH] cpuCompare: Fix crash on unexpected CPU XML
by Jiri Denemark
When comparing a CPU without <model> element, such as
<cpu>
<topology sockets='1' cores='1' threads='1'/>
</cpu>
libvirt would happily crash without warning.
---
src/cpu/cpu.c | 6 ++++++
1 files changed, 6 insertions(+), 0 deletions(-)
diff --git a/src/cpu/cpu.c b/src/cpu/cpu.c
index 279eee7..def6974 100644
--- a/src/cpu/cpu.c
+++ b/src/cpu/cpu.c
@@ -90,6 +90,12 @@ cpuCompareXML(virCPUDefPtr host,
if (cpu == NULL)
goto cleanup;
+ if (!cpu->model) {
+ virCPUReportError(VIR_ERR_OPERATION_INVALID,
+ "%s", _("no CPU model specified"));
+ goto cleanup;
+ }
+
ret = cpuCompare(host, cpu);
cleanup:
--
1.7.1.1
14 years, 4 months
[libvirt] [PATCH] cpu: Fail when CPU type cannot be detected from XML
by Jiri Denemark
When autodetecting whether XML describes guest or host CPU, the presence
of <arch> element is checked. If it's present, we treat the XML as host
CPU definition. Which is right, since guest CPU definitions do not
contain <arch> element. However, if at the same time the root <cpu>
element contains `match' attribute, we would silently ignore it and
still treat the XML as host CPU. We should rather refuse such invalid
XML.
---
src/conf/cpu_conf.c | 10 ++++++++--
1 files changed, 8 insertions(+), 2 deletions(-)
diff --git a/src/conf/cpu_conf.c b/src/conf/cpu_conf.c
index d9aa69c..35bcce8 100644
--- a/src/conf/cpu_conf.c
+++ b/src/conf/cpu_conf.c
@@ -130,9 +130,15 @@ virCPUDefParseXML(const xmlNodePtr node,
}
if (mode == VIR_CPU_TYPE_AUTO) {
- if (virXPathBoolean("boolean(./arch)", ctxt))
+ if (virXPathBoolean("boolean(./arch)", ctxt)) {
+ if (virXPathBoolean("boolean(./@match)", ctxt)) {
+ virCPUReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+ _("'arch' element element cannot be used inside 'cpu'"
+ " element with 'match' attribute'"));
+ goto error;
+ }
def->type = VIR_CPU_TYPE_HOST;
- else
+ } else
def->type = VIR_CPU_TYPE_GUEST;
} else
def->type = mode;
--
1.7.1.1
14 years, 4 months