virCapsPtr umlCapsInit(void) { virCapsPtr caps; virCapsGuestPtr guest; if ((caps = virCapabilitiesNew(virArchFromHost(), false, false)) == NULL) goto error; /* Some machines have problematic NUMA toplogy causing * unexpected failures. We don't want to break the QEMU * driver in this scenario, so log errors & carry on */ if (virCapabilitiesInitNUMA(caps) < 0) { virCapabilitiesFreeNUMAInfo(caps); VIR_WARN("Failed to query host NUMA topology, disabling NUMA capabilities"); } if (virCapabilitiesInitCaches(caps) < 0) VIR_WARN("Failed to get host CPU cache info"); if (virNodeSuspendGetTargetMask(&caps->host.powerMgmt) < 0) VIR_WARN("Failed to get host power management capabilities"); if (virGetHostUUID(caps->host.host_uuid)) { virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("cannot get the host uuid")); goto error; } if ((guest = virCapabilitiesAddGuest(caps, VIR_DOMAIN_OSTYPE_UML, caps->host.arch, NULL, NULL, 0, NULL)) == NULL) goto error; if (virCapabilitiesAddGuestDomain(guest, VIR_DOMAIN_VIRT_UML, NULL, NULL, 0, NULL) == NULL) goto error; return caps; error: virObjectUnref(caps); return NULL; }
/* Functions */ virCapsPtr virLXCDriverCapsInit(virLXCDriverPtr driver) { virCapsPtr caps; virCapsGuestPtr guest; virArch altArch; char *lxc_path = NULL; if ((caps = virCapabilitiesNew(virArchFromHost(), false, false)) == NULL) goto error; /* Some machines have problematic NUMA toplogy causing * unexpected failures. We don't want to break the lxc * driver in this scenario, so log errors & carry on */ if (nodeCapsInitNUMA(caps) < 0) { virCapabilitiesFreeNUMAInfo(caps); VIR_WARN("Failed to query host NUMA topology, disabling NUMA capabilities"); } /* Only probe for power management capabilities in the driver, * not in the emulator */ if (driver && virNodeSuspendGetTargetMask(&caps->host.powerMgmt) < 0) VIR_WARN("Failed to get host power management capabilities"); if (virGetHostUUID(caps->host.host_uuid)) { virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("cannot get the host uuid")); goto error; } if (!(lxc_path = virFileFindResource("libvirt_lxc", abs_topbuilddir "/src", LIBEXECDIR))) goto error; if ((guest = virCapabilitiesAddGuest(caps, VIR_DOMAIN_OSTYPE_EXE, caps->host.arch, lxc_path, NULL, 0, NULL)) == NULL) goto error; if (virCapabilitiesAddGuestDomain(guest, VIR_DOMAIN_VIRT_LXC, NULL, NULL, 0, NULL) == NULL) goto error; /* On 64-bit hosts, we can use personality() to request a 32bit process */ if ((altArch = lxcContainerGetAlt32bitArch(caps->host.arch)) != VIR_ARCH_NONE) { if ((guest = virCapabilitiesAddGuest(caps, VIR_DOMAIN_OSTYPE_EXE, altArch, lxc_path, NULL, 0, NULL)) == NULL) goto error; if (virCapabilitiesAddGuestDomain(guest, VIR_DOMAIN_VIRT_LXC, NULL, NULL, 0, NULL) == NULL) goto error; } VIR_FREE(lxc_path); if (driver) { /* Security driver data */ const char *doi, *model, *label, *type; doi = virSecurityManagerGetDOI(driver->securityManager); model = virSecurityManagerGetModel(driver->securityManager); label = virSecurityManagerGetBaseLabel(driver->securityManager, VIR_DOMAIN_VIRT_LXC); type = virDomainVirtTypeToString(VIR_DOMAIN_VIRT_LXC); /* Allocate the primary security driver for LXC. */ if (VIR_ALLOC(caps->host.secModels) < 0) goto error; caps->host.nsecModels = 1; if (VIR_STRDUP(caps->host.secModels[0].model, model) < 0) goto error; if (VIR_STRDUP(caps->host.secModels[0].doi, doi) < 0) goto error; if (label && virCapabilitiesHostSecModelAddBaseLabel(&caps->host.secModels[0], type, label) < 0) goto error; VIR_DEBUG("Initialized caps for security driver \"%s\" with " "DOI \"%s\"", model, doi); } else { VIR_INFO("No driver, not initializing security driver"); } return caps; error: VIR_FREE(lxc_path); virObjectUnref(caps); return NULL; }
/** * nodeSuspendForDuration: * @conn: pointer to the hypervisor connection * @target: the state to which the host must be suspended to - * VIR_NODE_SUSPEND_TARGET_MEM (Suspend-to-RAM), * VIR_NODE_SUSPEND_TARGET_DISK (Suspend-to-Disk), * VIR_NODE_SUSPEND_TARGET_HYBRID (Hybrid-Suspend) * @duration: the time duration in seconds, for which the host must be * suspended * @flags: any flag values that might need to be passed; currently unused. * * Suspend the node (host machine) for the given duration of time in the * specified state (such as Mem, Disk or Hybrid-Suspend). Attempt to resume * the node after the time duration is complete. * * First, an RTC alarm is set appropriately to wake up the node from its * sleep state. Then the actual node suspend operation is carried out * asynchronously in another thread, after a short time delay so as to * give enough time for this function to return status to its caller * through the connection. However this returning of status is best-effort * only, and should generally happen due to the short delay but might be * missed if the machine suspends first. * * Returns 0 in case the node is going to be suspended after a short delay, * -1 if suspending the node is not supported, or if a previous suspend * operation is still in progress. */ int nodeSuspendForDuration(virConnectPtr conn ATTRIBUTE_UNUSED, unsigned int target, unsigned long long duration, unsigned int flags) { static virThread thread; const char *cmdString = NULL; int ret = -1; unsigned int supported; virCheckFlags(0, -1); if (virNodeSuspendGetTargetMask(&supported) < 0) return -1; /* * Ensure that we are the only ones trying to suspend. * Fail if somebody has already initiated a suspend. */ virNodeSuspendLock(); if (aboutToSuspend) { /* A suspend operation is already in progress */ virNodeSuspendError(VIR_ERR_OPERATION_INVALID, "%s", _("Suspend operation already in progress")); goto cleanup; } /* Check if the host supports the requested suspend target */ switch (target) { case VIR_NODE_SUSPEND_TARGET_MEM: if (!(supported & (1 << VIR_NODE_SUSPEND_TARGET_MEM))) { virNodeSuspendError(VIR_ERR_ARGUMENT_UNSUPPORTED, "%s", _("Suspend-to-RAM")); goto cleanup; } cmdString = "pm-suspend"; break; case VIR_NODE_SUSPEND_TARGET_DISK: if (!(supported & (1 << VIR_NODE_SUSPEND_TARGET_DISK))) { virNodeSuspendError(VIR_ERR_ARGUMENT_UNSUPPORTED, "%s", _("Suspend-to-Disk")); goto cleanup; } cmdString = "pm-hibernate"; break; case VIR_NODE_SUSPEND_TARGET_HYBRID: if (!(supported & (1 << VIR_NODE_SUSPEND_TARGET_HYBRID))) { virNodeSuspendError(VIR_ERR_ARGUMENT_UNSUPPORTED, "%s", _("Hybrid-Suspend")); goto cleanup; } cmdString = "pm-suspend-hybrid"; break; default: virNodeSuspendError(VIR_ERR_INVALID_ARG, "%s", _("Invalid suspend target")); goto cleanup; } /* Just set the RTC alarm. Don't suspend yet. */ if (virNodeSuspendSetNodeWakeup(duration) < 0) goto cleanup; if (virThreadCreate(&thread, false, virNodeSuspend, (void *)cmdString) < 0) { virNodeSuspendError(VIR_ERR_INTERNAL_ERROR, "%s", _("Failed to create thread to suspend the host\n")); goto cleanup; } aboutToSuspend = true; ret = 0; cleanup: virNodeSuspendUnlock(); return ret; }
/* Functions */ virCapsPtr lxcCapsInit(virLXCDriverPtr driver) { virCapsPtr caps; virCapsGuestPtr guest; virArch altArch; if ((caps = virCapabilitiesNew(virArchFromHost(), 0, 0)) == NULL) goto error; /* Some machines have problematic NUMA toplogy causing * unexpected failures. We don't want to break the QEMU * driver in this scenario, so log errors & carry on */ if (nodeCapsInitNUMA(caps) < 0) { virCapabilitiesFreeNUMAInfo(caps); VIR_WARN("Failed to query host NUMA topology, disabling NUMA capabilities"); } if (virNodeSuspendGetTargetMask(&caps->host.powerMgmt) < 0) VIR_WARN("Failed to get host power management capabilities"); if (virGetHostUUID(caps->host.host_uuid)) { virReportError(VIR_ERR_INTERNAL_ERROR, "%s", _("cannot get the host uuid")); goto error; } if ((guest = virCapabilitiesAddGuest(caps, "exe", caps->host.arch, LIBEXECDIR "/libvirt_lxc", NULL, 0, NULL)) == NULL) goto error; if (virCapabilitiesAddGuestDomain(guest, "lxc", NULL, NULL, 0, NULL) == NULL) goto error; /* On 64-bit hosts, we can use personality() to request a 32bit process */ if ((altArch = lxcContainerGetAlt32bitArch(caps->host.arch)) != VIR_ARCH_NONE) { if ((guest = virCapabilitiesAddGuest(caps, "exe", altArch, LIBEXECDIR "/libvirt_lxc", NULL, 0, NULL)) == NULL) goto error; if (virCapabilitiesAddGuestDomain(guest, "lxc", NULL, NULL, 0, NULL) == NULL) goto error; } if (driver) { /* Security driver data */ const char *doi, *model; doi = virSecurityManagerGetDOI(driver->securityManager); model = virSecurityManagerGetModel(driver->securityManager); if (STRNEQ(model, "none")) { /* Allocate just the primary security driver for LXC. */ if (VIR_ALLOC(caps->host.secModels) < 0) goto no_memory; caps->host.nsecModels = 1; if (VIR_STRDUP(caps->host.secModels[0].model, model) < 0) goto error; if (VIR_STRDUP(caps->host.secModels[0].doi, doi) < 0) goto error; } VIR_DEBUG("Initialized caps for security driver \"%s\" with " "DOI \"%s\"", model, doi); } else { VIR_INFO("No driver, not initializing security driver"); } return caps; no_memory: virReportOOMError(); error: virObjectUnref(caps); return NULL; }