VIR_FREE(cell);
}
+static void
+virCapabilitiesFreeGuestMachine(virCapsGuestMachinePtr machine)
+{
+ if (machine == NULL)
+ return;
+ VIR_FREE(machine->name);
+ VIR_FREE(machine->canonical);
+ VIR_FREE(machine);
+}
+
static void
virCapabilitiesFreeGuestDomain(virCapsGuestDomainPtr dom)
{
VIR_FREE(dom->info.emulator);
VIR_FREE(dom->info.loader);
for (i = 0 ; i < dom->info.nmachines ; i++)
- VIR_FREE(dom->info.machines[i]);
+ virCapabilitiesFreeGuestMachine(dom->info.machines[i]);
VIR_FREE(dom->info.machines);
VIR_FREE(dom->type);
VIR_FREE(guest->arch.defaultInfo.emulator);
VIR_FREE(guest->arch.defaultInfo.loader);
for (i = 0 ; i < guest->arch.defaultInfo.nmachines ; i++)
- VIR_FREE(guest->arch.defaultInfo.machines[i]);
+ virCapabilitiesFreeGuestMachine(guest->arch.defaultInfo.machines[i]);
VIR_FREE(guest->arch.defaultInfo.machines);
for (i = 0 ; i < guest->arch.ndomains ; i++)
return 0;
}
+/**
+ * virCapabilitiesAllocMachines:
+ * @machines: machine variants for emulator ('pc', or 'isapc', etc)
+ * @nmachines: number of machine variants for emulator
+ *
+ * Allocate a table of virCapsGuestMachinePtr from the supplied table
+ * of machine names.
+ */
+virCapsGuestMachinePtr *
+virCapabilitiesAllocMachines(const char *const *names, int nnames)
+{
+ virCapsGuestMachinePtr *machines;
+ int i;
+
+ if (VIR_ALLOC_N(machines, nnames) < 0)
+ return NULL;
+
+ for (i = 0; i < nnames; i++) {
+ if (VIR_ALLOC(machines[i]) < 0 ||
+ !(machines[i]->name = strdup(names[i]))) {
+ virCapabilitiesFreeMachines(machines, nnames);
+ return NULL;
+ }
+ }
+
+ return machines;
+}
+
+/**
+ * virCapabilitiesFreeMachines:
+ * @machines: table of vircapsGuestMachinePtr
+ *
+ * Free a table of virCapsGuestMachinePtr
+ */
+void
+virCapabilitiesFreeMachines(virCapsGuestMachinePtr *machines,
+ int nmachines)
+{
+ int i;
+ if (!machines)
+ return;
+ for (i = 0; i < nmachines && machines[i]; i++) {
+ virCapabilitiesFreeGuestMachine(machines[i]);
+ machines[i] = NULL;
+ }
+ VIR_FREE(machines);
+}
/**
* virCapabilitiesAddGuest:
const char *emulator,
const char *loader,
int nmachines,
- const char *const *machines)
+ virCapsGuestMachinePtr *machines)
{
virCapsGuestPtr guest;
- int i;
if (VIR_ALLOC(guest) < 0)
goto no_memory;
(guest->arch.defaultInfo.loader = strdup(loader)) == NULL)
goto no_memory;
if (nmachines) {
- if (VIR_ALLOC_N(guest->arch.defaultInfo.machines,
- nmachines) < 0)
- goto no_memory;
- for (i = 0 ; i < nmachines ; i++) {
- if ((guest->arch.defaultInfo.machines[i] = strdup(machines[i])) == NULL)
- goto no_memory;
- guest->arch.defaultInfo.nmachines++;
- }
+ guest->arch.defaultInfo.nmachines = nmachines;
+ guest->arch.defaultInfo.machines = machines;
}
if (VIR_REALLOC_N(caps->guests,
const char *emulator,
const char *loader,
int nmachines,
- const char *const *machines)
+ virCapsGuestMachinePtr *machines)
{
virCapsGuestDomainPtr dom;
- int i;
if (VIR_ALLOC(dom) < 0)
goto no_memory;
(dom->info.loader = strdup(loader)) == NULL)
goto no_memory;
if (nmachines) {
- if (VIR_ALLOC_N(dom->info.machines, nmachines) < 0)
- goto no_memory;
- for (i = 0 ; i < nmachines ; i++) {
- if ((dom->info.machines[i] = strdup(machines[i])) == NULL)
- goto no_memory;
- dom->info.nmachines++;
- }
+ dom->info.nmachines = nmachines;
+ dom->info.machines = machines;
}
if (VIR_REALLOC_N(guest->arch.domains,
if (STREQ(caps->guests[i]->ostype, ostype) &&
STREQ(caps->guests[i]->arch.name, arch) &&
caps->guests[i]->arch.defaultInfo.nmachines)
- return caps->guests[i]->arch.defaultInfo.machines[0];
+ return caps->guests[i]->arch.defaultInfo.machines[0]->name;
}
return NULL;
}
for (j = 0 ; j < caps->guests[i]->arch.defaultInfo.nmachines ; j++) {
virBufferVSprintf(&xml, " <machine>%s</machine>\n",
- caps->guests[i]->arch.defaultInfo.machines[j]);
+ caps->guests[i]->arch.defaultInfo.machines[j]->name);
}
for (j = 0 ; j < caps->guests[i]->arch.ndomains ; j++) {
for (k = 0 ; k < caps->guests[i]->arch.domains[j]->info.nmachines ; k++) {
virBufferVSprintf(&xml, " <machine>%s</machine>\n",
- caps->guests[i]->arch.domains[j]->info.machines[k]);
+ caps->guests[i]->arch.domains[j]->info.machines[k]->name);
}
virBufferAddLit(&xml, " </domain>\n");
}
int toggle;
};
+typedef struct _virCapsGuestMachine virCapsGuestMachine;
+typedef virCapsGuestMachine *virCapsGuestMachinePtr;
+struct _virCapsGuestMachine {
+ char *name;
+ char *canonical;
+};
+
typedef struct _virCapsGuestDomainInfo virCapsGuestDomainInfo;
typedef virCapsGuestDomainInfo *virCapsGuestDomainInfoPtr;
struct _virCapsGuestDomainInfo {
char *emulator;
char *loader;
int nmachines;
- char **machines;
+ virCapsGuestMachinePtr *machines;
};
typedef struct _virCapsGuestDomain virCapsGuestDomain;
+extern virCapsGuestMachinePtr *
+virCapabilitiesAllocMachines(const char *const *names,
+ int nnames);
+extern void
+virCapabilitiesFreeMachines(virCapsGuestMachinePtr *machines,
+ int nmachines);
+
extern virCapsGuestPtr
virCapabilitiesAddGuest(virCapsPtr caps,
const char *ostype,
const char *emulator,
const char *loader,
int nmachines,
- const char *const *machines);
+ virCapsGuestMachinePtr *machines);
extern virCapsGuestDomainPtr
virCapabilitiesAddGuestDomain(virCapsGuestPtr guest,
const char *emulator,
const char *loader,
int nmachines,
- const char *const *machines);
+ virCapsGuestMachinePtr *machines);
extern virCapsGuestFeaturePtr
virCapabilitiesAddGuestFeature(virCapsGuestPtr guest,
virCapabilitiesGenerateMac;
virCapabilitiesSetEmulatorRequired;
virCapabilitiesIsEmulatorRequired;
+virCapabilitiesAllocMachines;
+virCapabilitiesFreeMachines;
# conf.h
*/
static int
qemudParseMachineTypesStr(const char *output,
- char ***machines,
+ virCapsGuestMachinePtr **machines,
int *nmachines)
{
const char *p = output;
const char *next;
- char **list = NULL;
- int i, nitems = 0;
+ virCapsGuestMachinePtr *list = NULL;
+ int nitems = 0;
do {
const char *t;
- char *machine;
+ virCapsGuestMachinePtr machine;
if ((next = strchr(p, '\n')))
++next;
if (!(t = strchr(p, ' ')) || (next && t >= next))
continue;
- if (!(machine = strndup(p, t - p)))
+ if (VIR_ALLOC(machine) < 0)
goto error;
+ if (!(machine->name = strndup(p, t - p))) {
+ VIR_FREE(machine);
+ goto error;
+ }
+
if (VIR_REALLOC_N(list, nitems + 1) < 0) {
+ VIR_FREE(machine->name);
VIR_FREE(machine);
goto error;
}
return 0;
error:
- for (i = 0; i < nitems; i++)
- VIR_FREE(list[i]);
- VIR_FREE(list);
+ virCapabilitiesFreeMachines(list, nitems);
return -1;
}
static int
qemudProbeMachineTypes(const char *binary,
- char ***machines,
+ virCapsGuestMachinePtr **machines,
int *nmachines)
{
const char *const qemuarg[] = { binary, "-M", "?", NULL };
int haskqemu = 0;
const char *kvmbin = NULL;
const char *binary = NULL;
- char **machines = NULL;
+ virCapsGuestMachinePtr *machines = NULL;
int nmachines = 0;
/* Check for existance of base emulator, or alternate base
return 0;
if (info->machine) {
- char *machine;
+ virCapsGuestMachinePtr machine;
+
+ if (VIR_ALLOC(machine) < 0)
+ return -1;
- if (!(machine = strdup(info->machine)))
+ if (!(machine->name = strdup(info->machine))) {
+ VIR_FREE(machine);
return -1;
+ }
if (VIR_ALLOC_N(machines, nmachines) < 0) {
+ VIR_FREE(machine->name);
VIR_FREE(machine);
return -1;
}
binary,
NULL,
nmachines,
- (const char *const *)machines)) == NULL) {
- for (i = 0; i < nmachines; i++)
+ machines)) == NULL) {
+ for (i = 0; i < nmachines; i++) {
+ VIR_FREE(machines[i]->name);
VIR_FREE(machines[i]);
+ }
VIR_FREE(machines);
return -1;
}
- for (i = 0; i < nmachines; i++)
- VIR_FREE(machines[i]);
- VIR_FREE(machines);
-
if (hvm) {
if (virCapabilitiesAddGuestDomain(guest,
"qemu",
for (i = 0; i < nr_guest_archs; ++i) {
virCapsGuestPtr guest;
- char const *const machines[] = {guest_archs[i].hvm ? "xenfv" : "xenpv"};
+ char const *const xen_machines[] = {guest_archs[i].hvm ? "xenfv" : "xenpv"};
+ virCapsGuestMachinePtr *machines;
+
+ if ((machines = virCapabiltiesAllocMachines(xen_machines, 1)) == NULL)
+ goto no_memory;
if ((guest = virCapabilitiesAddGuest(caps,
guest_archs[i].hvm ? "hvm" : "xen",
"/usr/lib/xen/boot/hvmloader" :
NULL),
1,
- machines)) == NULL)
+ machines)) == NULL) {
+ virCapabilitiesFreeMachines(machines, 1);
goto no_memory;
+ }
+
+ virCapabilitiesFreeMachines(machines, 1);
if (virCapabilitiesAddGuestDomain(guest,
"xen",
struct utsname utsname;
virCapsPtr caps;
virCapsGuestPtr guest;
+ virCapsGuestMachinePtr *machines;
+ int nmachines;
static const char *const x86_machines[] = {
"pc", "isapc"
};
0, 0)) == NULL)
return NULL;
+ nmachines = 2;
+ if ((machines = virCapabilitiesAllocMachines(x86_machines, nmachines)) == NULL)
+ goto cleanup;
+
if ((guest = virCapabilitiesAddGuest(caps, "hvm", "i686", 32,
"/usr/bin/qemu", NULL,
- 2, x86_machines)) == NULL)
+ nmachines, machines)) == NULL)
goto cleanup;
+ machines = NULL;
+
if (virCapabilitiesAddGuestDomain(guest,
"qemu",
NULL,
NULL) == NULL)
goto cleanup;
+ nmachines = 2;
+ if ((machines = virCapabilitiesAllocMachines(x86_machines, nmachines)) == NULL)
+ goto cleanup;
+
if ((guest = virCapabilitiesAddGuest(caps, "hvm", "x86_64", 64,
"/usr/bin/qemu-system-x86_64", NULL,
- 2, x86_machines)) == NULL)
+ nmachines, machines)) == NULL)
goto cleanup;
+ machines = NULL;
+
if (virCapabilitiesAddGuestDomain(guest,
"qemu",
NULL,
NULL) == NULL)
goto cleanup;
+ nmachines = 1;
+ if ((machines = virCapabilitiesAllocMachines(xen_machines, nmachines)) == NULL)
+ goto cleanup;
+
if ((guest = virCapabilitiesAddGuest(caps, "xen", "x86_64", 64,
"/usr/bin/xenner", NULL,
- 1, xen_machines)) == NULL)
+ 1, machines)) == NULL)
goto cleanup;
+ machines = NULL;
+
if (virCapabilitiesAddGuestDomain(guest,
"kvm",
"/usr/bin/kvm",
return caps;
cleanup:
+ virCapabilitiesFreeMachines(machines, nmachines);
virCapabilitiesFree(caps);
return NULL;
}