[libvirt] [PATCH] qemu: error out if PCI passthrough type is not supported
If PCI passthrough type is not supported, we should error out rather than continue building the command line. When starting a domain, the type has been already checked by qemuPrepareHostdevPCICheckSupport() before building qemu command line, so the problem doesn't emerge. But when coverting a domain xml without specifying passthrough type explictly to qemu arg, we will get a malformed command line. the xml: hostdev mode='subsystem' type='pci' managed='yes' source address domain='0x0001' bus='0x03' slot='0x00' function='0x0'/ /source address type='pci' domain='0x' bus='0x00' slot='0x05' function='0x0'/ /hostdev the converted command line: -device ,host=0001:03:00.0,id=hostdev0,bus=pci.0,addr=0x5 After this patch, virsh gives an error message: virsh domxml-to-native qemu-argv /tmp/tmp.xml error: internal error: invalid PCI passthrough type 'default' Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- src/qemu/qemu_command.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c index 7f9357c..12d6354 100644 --- a/src/qemu/qemu_command.c +++ b/src/qemu/qemu_command.c @@ -4880,7 +4880,7 @@ qemuBuildPCIHostdevDevStr(virDomainDefPtr def, virReportError(VIR_ERR_INTERNAL_ERROR, _(invalid PCI passthrough type '%s'), virDomainHostdevSubsysPCIBackendTypeToString(backend)); -break; +goto error; } virBufferAddLit(buf, ,host=); -- 1.8.0 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH] doc: add domain to address of hostdev pci
libvirt supports pci domain already, so update the documentation. Otherwise users who lookup the documentation for how to use hostdev may miss the domain and encounter error when pass-through a pci device in a domain other than 0. Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- docs/formatdomain.html.in | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in index 3c85fc5..4572feb 100644 --- a/docs/formatdomain.html.in +++ b/docs/formatdomain.html.in @@ -2777,7 +2777,7 @@ lt;devicesgt; lt;hostdev mode='subsystem' type='pci' managed='yes'gt; lt;sourcegt; -lt;address bus='0x06' slot='0x02' function='0x0'/gt; +lt;address domain='0x' bus='0x06' slot='0x02' function='0x0'/gt; lt;/sourcegt; lt;boot order='1'/gt; lt;rom bar='on' file='/etc/fake/boot.bin'/gt; @@ -2891,7 +2891,7 @@ USB bus and device number the device appears at on the host. The values of these attributes can be given in decimal, hexadecimal (starting with 0x) or octal (starting with 0) form. - For PCI devices the element carries 3 attributes allowing to designate + For PCI devices the element carries 4 attributes allowing to designate the device as can be found with the codelspci/code or with codevirsh nodedev-list/code. a href=#elementsAddressSee above/a for -- 1.9.3 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v3 3/4] qemu: add support for -device pvpanic
On Thu, Dec 12, 2013 at 09:20:43PM -0700, Eric Blake wrote: On 12/09/2013 02:11 AM, Hu Tao wrote: Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- src/qemu/qemu_capabilities.c | 3 +++ src/qemu/qemu_capabilities.h | 2 ++ src/qemu/qemu_command.c | 16 tests/qemucapabilitiesdata/caps_1.5.3-1.caps | 1 + tests/qemucapabilitiesdata/caps_1.6.0-1.caps | 1 + tests/qemucapabilitiesdata/caps_1.6.50-1.caps | 1 + 6 files changed, 24 insertions(+) More merge conflicts, and it's my bedtime; I'll resolve and push in the morning, as well as squash 3 and 4 into one patch. Thanks! -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v3 0/4] add support for panic device
panic device is a device that enables libvirt to receive notification of guest panic event. qemu implements it by pvpanic. This series adds support for panic device. It is implemented in qemu driver only. changes in v3: - introduce generic ISA address - rename pvpanic to panic. - add RNG schemas for new elements - add tests for panic device - error out if panic device is requested but qemu is too old Hu Tao (4): conf: introduce generic ISA address conf: add support for panic device qemu: add support for -device pvpanic test: add test for panic device docs/formatdomain.html.in | 33 ++ docs/schemas/basictypes.rng| 17 docs/schemas/domaincommon.rng | 16 +++ src/conf/domain_conf.c | 135 - src/conf/domain_conf.h | 18 src/qemu/qemu_capabilities.c | 3 + src/qemu/qemu_capabilities.h | 2 + src/qemu/qemu_command.c| 16 +++ tests/qemucapabilitiesdata/caps_1.5.3-1.caps | 1 + tests/qemucapabilitiesdata/caps_1.6.0-1.caps | 1 + tests/qemucapabilitiesdata/caps_1.6.50-1.caps | 1 + tests/qemuxml2argvdata/qemuxml2argv-panic.args | 6 ++ tests/qemuxml2argvdata/qemuxml2argv-panic.xml | 31 ++ tests/qemuxml2argvtest.c | 3 + tests/qemuxml2xmltest.c| 2 + 15 files changed, 284 insertions(+), 1 deletion(-) create mode 100644 tests/qemuxml2argvdata/qemuxml2argv-panic.args create mode 100644 tests/qemuxml2argvdata/qemuxml2argv-panic.xml -- 1.7.11.7 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v3 4/4] test: add test for panic device
--- tests/qemuxml2argvdata/qemuxml2argv-panic.args | 6 + tests/qemuxml2argvdata/qemuxml2argv-panic.xml | 31 ++ tests/qemuxml2argvtest.c | 3 +++ tests/qemuxml2xmltest.c| 2 ++ 4 files changed, 42 insertions(+) create mode 100644 tests/qemuxml2argvdata/qemuxml2argv-panic.args create mode 100644 tests/qemuxml2argvdata/qemuxml2argv-panic.xml diff --git a/tests/qemuxml2argvdata/qemuxml2argv-panic.args b/tests/qemuxml2argvdata/qemuxml2argv-panic.args new file mode 100644 index 000..8e07cba --- /dev/null +++ b/tests/qemuxml2argvdata/qemuxml2argv-panic.args @@ -0,0 +1,6 @@ +LC_ALL=C PATH=/bin HOME=/home/test USER=test LOGNAME=test QEMU_AUDIO_DRV=none \ +/usr/bin/qemu -S -M pc -m 214 -smp 1 -nographic -nodefconfig -nodefaults \ +-monitor unix:/tmp/test-monitor,server,nowait -no-acpi -boot c -usb \ +-hda /dev/HostVG/QEMUGuest1 \ +-device virtio-balloon-pci,id=balloon0,bus=pci.0,addr=0x3 \ +-device pvpanic,ioport=1285 diff --git a/tests/qemuxml2argvdata/qemuxml2argv-panic.xml b/tests/qemuxml2argvdata/qemuxml2argv-panic.xml new file mode 100644 index 000..e354511 --- /dev/null +++ b/tests/qemuxml2argvdata/qemuxml2argv-panic.xml @@ -0,0 +1,31 @@ +domain type='qemu' + nameQEMUGuest1/name + uuidc7a5fdbd-edaf-9455-926a-d65c16db1809/uuid + memory unit='KiB'219136/memory + currentMemory unit='KiB'219136/currentMemory + vcpu placement='static'1/vcpu + os +type arch='i686' machine='pc'hvm/type +boot dev='hd'/ + /os + clock offset='utc'/ + on_poweroffdestroy/on_poweroff + on_rebootrestart/on_reboot + on_crashdestroy/on_crash + devices +emulator/usr/bin/qemu/emulator +disk type='block' device='disk' + source dev='/dev/HostVG/QEMUGuest1'/ + target dev='hda' bus='ide'/ + address type='drive' controller='0' bus='0' target='0' unit='0'/ +/disk +controller type='usb' index='0'/ +controller type='fdc' index='0'/ +controller type='ide' index='0'/ +controller type='pci' index='0' model='pci-root'/ +memballoon model='virtio'/ +panic + address type='isa' iobase='0x505'/ +/panic + /devices +/domain diff --git a/tests/qemuxml2argvtest.c b/tests/qemuxml2argvtest.c index dad5973..537b3ce 100644 --- a/tests/qemuxml2argvtest.c +++ b/tests/qemuxml2argvtest.c @@ -1115,6 +1115,9 @@ mymain(void) DO_TEST(kvm-pit-device, QEMU_CAPS_NO_KVM_PIT, QEMU_CAPS_KVM_PIT_TICK_POLICY); +DO_TEST(panic, QEMU_CAPS_DEVICE_PANIC, +QEMU_CAPS_DEVICE, QEMU_CAPS_NODEFCONFIG); + virObjectUnref(driver.config); virObjectUnref(driver.caps); virObjectUnref(driver.xmlopt); diff --git a/tests/qemuxml2xmltest.c b/tests/qemuxml2xmltest.c index ceaaf6a..0253f4e 100644 --- a/tests/qemuxml2xmltest.c +++ b/tests/qemuxml2xmltest.c @@ -322,6 +322,8 @@ mymain(void) DO_TEST(pcihole64-none); DO_TEST(pcihole64-q35); +DO_TEST(panic); + virObjectUnref(driver.caps); virObjectUnref(driver.xmlopt); -- 1.7.11.7 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v3 3/4] qemu: add support for -device pvpanic
Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- src/qemu/qemu_capabilities.c | 3 +++ src/qemu/qemu_capabilities.h | 2 ++ src/qemu/qemu_command.c | 16 tests/qemucapabilitiesdata/caps_1.5.3-1.caps | 1 + tests/qemucapabilitiesdata/caps_1.6.0-1.caps | 1 + tests/qemucapabilitiesdata/caps_1.6.50-1.caps | 1 + 6 files changed, 24 insertions(+) diff --git a/src/qemu/qemu_capabilities.c b/src/qemu/qemu_capabilities.c index 548b988..b532dbb 100644 --- a/src/qemu/qemu_capabilities.c +++ b/src/qemu/qemu_capabilities.c @@ -243,6 +243,8 @@ VIR_ENUM_IMPL(virQEMUCaps, QEMU_CAPS_LAST, virtio-mmio, ich9-intel-hda, kvm-pit-lost-tick-policy, + + pvpanic, /* 160 */ ); struct _virQEMUCaps { @@ -1394,6 +1396,7 @@ struct virQEMUCapsStringFlags virQEMUCapsObjectTypes[] = { { usb-storage, QEMU_CAPS_DEVICE_USB_STORAGE }, { virtio-mmio, QEMU_CAPS_DEVICE_VIRTIO_MMIO }, { ich9-intel-hda, QEMU_CAPS_DEVICE_ICH9_INTEL_HDA }, +{ pvpanic, QEMU_CAPS_DEVICE_PANIC }, }; static struct virQEMUCapsStringFlags virQEMUCapsObjectPropsVirtioBlk[] = { diff --git a/src/qemu/qemu_capabilities.h b/src/qemu/qemu_capabilities.h index 02d47c6..1aedbf9 100644 --- a/src/qemu/qemu_capabilities.h +++ b/src/qemu/qemu_capabilities.h @@ -199,6 +199,8 @@ enum virQEMUCapsFlags { QEMU_CAPS_DEVICE_ICH9_INTEL_HDA = 158, /* -device ich9-intel-hda */ QEMU_CAPS_KVM_PIT_TICK_POLICY = 159, /* kvm-pit.lost_tick_policy */ +QEMU_CAPS_DEVICE_PANIC = 160, /* -device pvpanic */ + QEMU_CAPS_LAST, /* this must always be the last item */ }; diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c index 763417f..8487356 100644 --- a/src/qemu/qemu_command.c +++ b/src/qemu/qemu_command.c @@ -9588,6 +9588,22 @@ qemuBuildCommandLine(virConnectPtr conn, goto error; } +if (def-panic) { +if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE_PANIC)) { +if (def-panic-info.addr.isa.iobase 0) { +virCommandAddArg(cmd, -device); +virCommandAddArgFormat(cmd, pvpanic,ioport=%d, + def-panic-info.addr.isa.iobase); +} else { +virCommandAddArgList(cmd, -device, pvpanic, NULL); +} +} else { +virReportError(VIR_ERR_CONFIG_UNSUPPORTED, %s, + _(your QEMU is too old to support pvpanic)); +goto error; +} +} + if (mlock) { unsigned long long memKB; diff --git a/tests/qemucapabilitiesdata/caps_1.5.3-1.caps b/tests/qemucapabilitiesdata/caps_1.5.3-1.caps index 09cf657..1c84ce2 100644 --- a/tests/qemucapabilitiesdata/caps_1.5.3-1.caps +++ b/tests/qemucapabilitiesdata/caps_1.5.3-1.caps @@ -131,4 +131,5 @@ flag name='usb-storage.removable'/ flag name='ich9-intel-hda'/ flag name='kvm-pit-lost-tick-policy'/ +flag name='pvpanic'/ /qemuCaps diff --git a/tests/qemucapabilitiesdata/caps_1.6.0-1.caps b/tests/qemucapabilitiesdata/caps_1.6.0-1.caps index 33ee73b..3b1b456 100644 --- a/tests/qemucapabilitiesdata/caps_1.6.0-1.caps +++ b/tests/qemucapabilitiesdata/caps_1.6.0-1.caps @@ -135,4 +135,5 @@ flag name='virtio-mmio'/ flag name='ich9-intel-hda'/ flag name='kvm-pit-lost-tick-policy'/ +flag name='pvpanic'/ /qemuCaps diff --git a/tests/qemucapabilitiesdata/caps_1.6.50-1.caps b/tests/qemucapabilitiesdata/caps_1.6.50-1.caps index a66034a..fc9e034 100644 --- a/tests/qemucapabilitiesdata/caps_1.6.50-1.caps +++ b/tests/qemucapabilitiesdata/caps_1.6.50-1.caps @@ -134,4 +134,5 @@ flag name='virtio-mmio'/ flag name='ich9-intel-hda'/ flag name='kvm-pit-lost-tick-policy'/ +flag name='pvpanic'/ /qemuCaps -- 1.7.11.7 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v3 1/4] conf: introduce generic ISA address
--- docs/formatdomain.html.in | 5 docs/schemas/basictypes.rng | 17 docs/schemas/domaincommon.rng | 6 + src/conf/domain_conf.c| 63 ++- src/conf/domain_conf.h| 9 +++ 5 files changed, 99 insertions(+), 1 deletion(-) diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in index 1850a2b..054ebc6 100644 --- a/docs/formatdomain.html.in +++ b/docs/formatdomain.html.in @@ -2425,6 +2425,11 @@ operating system. span class=sinceSince 1.0.4/span /dd + dtcodetype='isa'/code/dt + ddISA addresses have the following additional +attributes: codeiobase/code and codeirq/code. +span class=sinceSince 1.2.1/span + /dd /dl h4a name=elementsControllersControllers/a/h4 diff --git a/docs/schemas/basictypes.rng b/docs/schemas/basictypes.rng index 268bc5a..34ef613 100644 --- a/docs/schemas/basictypes.rng +++ b/docs/schemas/basictypes.rng @@ -380,4 +380,21 @@ /element /define + define name=isaaddress +optional + attribute name=iobase +data type=string + param name=pattern0x[a-fA-F0-9]{1,4}/param +/data + /attribute +/optional +optional + attribute name=irq +data type=string + param name=pattern0x[a-fA-F0-9]/param +/data + /attribute +/optional + /define + /grammar diff --git a/docs/schemas/domaincommon.rng b/docs/schemas/domaincommon.rng index 80848d2..3e98af9 100644 --- a/docs/schemas/domaincommon.rng +++ b/docs/schemas/domaincommon.rng @@ -3921,6 +3921,12 @@ /attribute ref name=ccwaddress/ /group +group + attribute name=type +valueisa/value + /attribute + ref name=isaaddress/ +/group /choice /element /define diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c index 140eb80..7d5617e 100644 --- a/src/conf/domain_conf.c +++ b/src/conf/domain_conf.c @@ -212,7 +212,8 @@ VIR_ENUM_IMPL(virDomainDeviceAddress, VIR_DOMAIN_DEVICE_ADDRESS_TYPE_LAST, spapr-vio, virtio-s390, ccw, - virtio-mmio) + virtio-mmio, + isa) VIR_ENUM_IMPL(virDomainDisk, VIR_DOMAIN_DISK_TYPE_LAST, block, @@ -3053,6 +3054,13 @@ virDomainDeviceInfoFormat(virBufferPtr buf, case VIR_DOMAIN_DEVICE_ADDRESS_TYPE_VIRTIO_MMIO: break; +case VIR_DOMAIN_DEVICE_ADDRESS_TYPE_ISA: +if (info-addr.isa.iobase 0) +virBufferAsprintf(buf, iobase='0x%x', info-addr.isa.iobase); +if (info-addr.isa.irq 0) +virBufferAsprintf(buf, irq='0x%x', info-addr.isa.irq); +break; + default: virReportError(VIR_ERR_INTERNAL_ERROR, _(unknown address type '%d'), info-type); @@ -3389,6 +3397,40 @@ cleanup: return ret; } +static int +virDomainDeviceISAAddressParseXML(xmlNodePtr node, + virDomainDeviceISAAddressPtr addr) +{ +int ret = -1; +char *iobase; +char *irq; + +memset(addr, 0, sizeof(*addr)); + +iobase = virXMLPropString(node, iobase); +irq = virXMLPropString(node, irq); + +if (iobase +virStrToLong_ui(iobase, NULL, 16, addr-iobase) 0) { +virReportError(VIR_ERR_XML_ERROR, %s, + _(Cannot parse address 'iobase' attribute)); +goto cleanup; +} + +if (irq +virStrToLong_ui(irq, NULL, 16, addr-irq) 0) { +virReportError(VIR_ERR_XML_ERROR, %s, + _(Cannot parse address 'irq' attribute)); +goto cleanup; +} + +ret = 0; +cleanup: +VIR_FREE(iobase); +VIR_FREE(irq); +return ret; +} + /* Parse the XML definition for a device address * @param node XML nodeset to parse for device address definition */ @@ -3520,6 +3562,11 @@ virDomainDeviceInfoParseXML(xmlNodePtr node, case VIR_DOMAIN_DEVICE_ADDRESS_TYPE_VIRTIO_MMIO: break; +case VIR_DOMAIN_DEVICE_ADDRESS_TYPE_ISA: +if (virDomainDeviceISAAddressParseXML(address, info-addr.isa) 0) +goto cleanup; +break; + default: /* Should not happen */ virReportError(VIR_ERR_INTERNAL_ERROR, @@ -12916,6 +12963,20 @@ virDomainDeviceInfoCheckABIStability(virDomainDeviceInfoPtr src, return false; } break; + +case VIR_DOMAIN_DEVICE_ADDRESS_TYPE_ISA: +if (src-addr.isa.iobase != dst-addr.isa.iobase || +src-addr.isa.irq != dst-addr.isa.irq) { +virReportError(VIR_ERR_CONFIG_UNSUPPORTED, + _(Target device isa address %d:%d + does not match source %d:%d), + dst-addr.isa.iobase, + dst-addr.isa.irq, + src-addr.isa.iobase, +
[libvirt] [PATCH v3 2/4] conf: add support for panic device
panic device is a device that enables libvirt to receive notification of guest panic event. --- docs/formatdomain.html.in | 28 + docs/schemas/domaincommon.rng | 10 ++ src/conf/domain_conf.c| 72 +++ src/conf/domain_conf.h| 9 ++ 4 files changed, 119 insertions(+) diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in index 054ebc6..c8f213e 100644 --- a/docs/formatdomain.html.in +++ b/docs/formatdomain.html.in @@ -5085,6 +5085,34 @@ qemu-kvm -net nic,model=? /dev/null /dd /dl +h4a name=elementsPanicpanic device/a/h4 +p + panic device enables libvirt to receive panic notification from a QEMU + guest. + span class=sinceSince 1.2.1, QEMU and KVM only/span +/p +p + Example: usage of panic configuration +/p +pre + ... + lt;devicesgt; +lt;panicgt; + lt;address type='isa' iobase='0x505'/gt; +lt;/panicgt; + lt;/devicesgt; + ... +/pre + dl +dtcodeaddress/code/dt +dd + p +address of panic. The default ioport is 0x505. Most users +don't need to specify an address. + /p +/dd + /dl + h3a name=seclabelSecurity label/a/h3 p diff --git a/docs/schemas/domaincommon.rng b/docs/schemas/domaincommon.rng index 3e98af9..8ae96f2 100644 --- a/docs/schemas/domaincommon.rng +++ b/docs/schemas/domaincommon.rng @@ -3556,6 +3556,9 @@ optional ref name=nvram/ /optional +optional + ref name=panic/ +/optional /interleave /element /define @@ -4409,4 +4412,11 @@ /data /choice /define + define name=panic +element name=panic + optional +ref name=address/ + /optional +/element + /define /grammar diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c index 7d5617e..233b848 100644 --- a/src/conf/domain_conf.c +++ b/src/conf/domain_conf.c @@ -1877,6 +1877,15 @@ virDomainResourceDefFree(virDomainResourceDefPtr resource) VIR_FREE(resource); } +void +virDomainPanicDefFree(virDomainPanicDefPtr panic) +{ +if (!panic) +return; + +virDomainDeviceInfoClear(panic-info); +VIR_FREE(panic); +} void virDomainDefFree(virDomainDefPtr def) { @@ -1965,6 +1974,8 @@ void virDomainDefFree(virDomainDefPtr def) virDomainTPMDefFree(def-tpm); +virDomainPanicDefFree(def-panic); + VIR_FREE(def-idmap.uidmap); VIR_FREE(def-idmap.gidmap); @@ -10673,6 +10684,22 @@ cleanup: return idmap; } +static virDomainPanicDefPtr +virDomainPanicDefParseXML(xmlNodePtr node) +{ +virDomainPanicDefPtr panic; + +if (VIR_ALLOC(panic) 0) +return NULL; + +if (virDomainDeviceInfoParseXML(node, NULL, panic-info, 0) 0) +goto error; + +return panic; +error: +virDomainPanicDefFree(panic); +return NULL; +} /* Parse the XML definition for a vcpupin or emulatorpin. * @@ -12500,6 +12527,27 @@ virDomainDefParseXML(xmlDocPtr xml, } VIR_FREE(nodes); +/* analysis of the panic devices */ +def-panic = NULL; +if ((n = virXPathNodeSet(./devices/panic, ctxt, nodes)) 0) { +goto error; +} +if (n 1) { +virReportError(VIR_ERR_XML_ERROR, %s, + _(only a single panic device is supported)); +goto error; +} +if (n 0) { +virDomainPanicDefPtr panic = +virDomainPanicDefParseXML(nodes[0]); +if (!panic) +goto error; + +def-panic = panic; +VIR_FREE(nodes); +} + + /* analysis of the user namespace mapping */ if ((n = virXPathNodeSet(./idmap/uid, ctxt, nodes)) 0) goto error; @@ -13589,6 +13637,13 @@ virDomainDefFeaturesCheckABIStability(virDomainDefPtr src, return true; } +static bool +virDomainPanicCheckABIStability(virDomainPanicDefPtr src, +virDomainPanicDefPtr dst) +{ +return virDomainDeviceInfoCheckABIStability(src-info, dst-info); +} + /* This compares two configurations and looks for any differences * which will affect the guest ABI. This is primarily to allow @@ -13930,6 +13985,9 @@ virDomainDefCheckABIStability(virDomainDefPtr src, if (!virDomainRNGDefCheckABIStability(src-rng, dst-rng)) return false; +if (!virDomainPanicCheckABIStability(src-panic, dst-panic)) +return false; + return true; } @@ -15776,6 +15834,16 @@ virDomainWatchdogDefFormat(virBufferPtr buf, return 0; } +static int virDomainPanicDefFormat(virBufferPtr buf, + virDomainPanicDefPtr def) +{ +virBufferAddLit(buf, panic\n); +if (virDomainDeviceInfoFormat(buf, def-info, 0) 0) +return -1; +virBufferAddLit(buf, /panic\n); + +return 0; +} static int virDomainRNGDefFormat(virBufferPtr buf, @@ -17199,6 +17267,10 @@ virDomainDefFormatInternal(virDomainDefPtr def, if (def-nvram)
Re: [libvirt] [PATCH v2 1/2] conf: add xml element devices/pvpanic
On Thu, Dec 05, 2013 at 10:07:40AM +, Daniel P. Berrange wrote: On Thu, Dec 05, 2013 at 10:41:13AM +0800, Hu Tao wrote: On Wed, Dec 04, 2013 at 03:53:17PM +, Daniel P. Berrange wrote: On Wed, Dec 04, 2013 at 08:46:53AM -0700, Eric Blake wrote: On 12/04/2013 08:42 AM, Daniel P. Berrange wrote: Dan, do you have any thoughts on the best representation to use? Or is Hu's original proposal of: pvpanic ioport='0x505'/ I'm not a fan of doing a special case attribute for 'ioport' - this is something something that should be part of an address element, since ioport numbers are a generic addressing concept for many devices. eg ISA serial / parallel ports have IRQ / IO ports IIUC. So something more like: pvpanic address type='ioport' slot='0x505'/ /pvpanic and introducing a new type='ioport' namespace into the address XML since it is yet another numbering system for guest-visible addressing? Yes, I'm not sure I'd call the type 'ioport' - the address type reflects the bus/controller type that the device is associated with. What is the bus type that a pvpanic device is attached to ? Is it a ISA bus device, or is it a platform device or something else ? eg it might be appropriate to use address type='platform' ioport='0x666'/ It's an ISA device. So the address should be: address type='isa' ioport='0x505'/ Ok. It looks like it does not require an IRQ line though IIUC. For the general ISA address type though, we want to represent both ioport and IRQ values. So I guess we need the IRQ attribute to be optional in some manner. Just to confirm it, so the general ISA address looks like: address type='isa' ioport='0xaaa' irq='123'/ ? I checked attributes of several qemu ISA devices, iobase and irq are common, but some device(isa-ide) has iobase2. Should we handle it as well? -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v2 1/2] conf: add xml element devices/pvpanic
On Wed, Dec 04, 2013 at 03:53:17PM +, Daniel P. Berrange wrote: On Wed, Dec 04, 2013 at 08:46:53AM -0700, Eric Blake wrote: On 12/04/2013 08:42 AM, Daniel P. Berrange wrote: Dan, do you have any thoughts on the best representation to use? Or is Hu's original proposal of: pvpanic ioport='0x505'/ I'm not a fan of doing a special case attribute for 'ioport' - this is something something that should be part of an address element, since ioport numbers are a generic addressing concept for many devices. eg ISA serial / parallel ports have IRQ / IO ports IIUC. So something more like: pvpanic address type='ioport' slot='0x505'/ /pvpanic and introducing a new type='ioport' namespace into the address XML since it is yet another numbering system for guest-visible addressing? Yes, I'm not sure I'd call the type 'ioport' - the address type reflects the bus/controller type that the device is associated with. What is the bus type that a pvpanic device is attached to ? Is it a ISA bus device, or is it a platform device or something else ? eg it might be appropriate to use address type='platform' ioport='0x666'/ It's an ISA device. So the address should be: address type='isa' ioport='0x505'/ ? -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v2 1/2] conf: add xml element devices/pvpanic
On Mon, Dec 02, 2013 at 02:34:44PM -0700, Eric Blake wrote: On 12/01/2013 11:11 PM, Hu Tao wrote: This patch adds a new xml element devices/pvpanic to support qemu device pvpanic. It can be used to receive guest panic notification. Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- docs/formatdomain.html.in | 25 + src/conf/domain_conf.c| 68 +++ src/conf/domain_conf.h| 9 +++ 3 files changed, 102 insertions(+) In addition to Peter's review: when sending a series, it helps to include a 0/2 cover letter (git send-email --cover-letter). diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in index 1850a2b..0a72baa 100644 --- a/docs/formatdomain.html.in +++ b/docs/formatdomain.html.in @@ -5080,6 +5080,31 @@ qemu-kvm -net nic,model=? /dev/null /dd /dl +h4a name=elementsPvpanicpvpanic device/a/h4 pvpanic is a qemu term, but I could see the feasibility of other hypervisors having a paravirt device with a sole purpose of notifying the host about panics. Do we want to come up with a more generic name? Give it a generic name is easy, but what about attributes? different hypervisors may have different paravirt devices with different attributes, we can't just mix attributes of unrelated devices into one generic device. Make the devices concrete and accept/reject it if hypervisors recognize it or not is better. -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v2 1/2] conf: add xml element devices/pvpanic
On Mon, Dec 02, 2013 at 11:13:33AM +0100, Peter Krempa wrote: On 12/02/13 07:11, Hu Tao wrote: This patch adds a new xml element devices/pvpanic to support qemu device pvpanic. It can be used to receive guest panic notification. Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- docs/formatdomain.html.in | 25 + src/conf/domain_conf.c| 68 +++ src/conf/domain_conf.h| 9 +++ 3 files changed, 102 insertions(+) A few issues I see at first glance: 1) you didn't add ABI compatibility check for the pvpanic device 2) XML-XML tests are missing 3) RNG schemas for the new element are missing 4) XML-qemu commandline tests are missing (in 2/2) Thanks, I'll add the missing parts in next version. diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in index 1850a2b..0a72baa 100644 --- a/docs/formatdomain.html.in +++ b/docs/formatdomain.html.in @@ -5080,6 +5080,31 @@ qemu-kvm -net nic,model=? /dev/null /dd /dl +h4a name=elementsPvpanicpvpanic device/a/h4 +p + pvpanic device enables libvirt to receive panic notification from a QEMU + guest. + span class=sinceSince 1.3.0, QEMU and KVM only/span 1.3.0? the since tag is supposed to contain a libvirt version. 1.3.0 will not happen that soon. 1.2.1 is what you are looking for. OK. +/p +p + Example: usage of pvpanic configuration +/p +pre + ... + lt;devicesgt; +lt;pvpanic ioport='0x505'/gt; + lt;/devicesgt; + ... +/pre + dl +dtcodeioport/code/dt +dd + p +ioport used by pvpanic. + /p +/dd + /dl + h3a name=seclabelSecurity label/a/h3 p diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c index 140eb80..1b8f66f 100644 --- a/src/conf/domain_conf.c +++ b/src/conf/domain_conf.c ... @@ -15715,6 +15768,18 @@ virDomainWatchdogDefFormat(virBufferPtr buf, return 0; } +static int virDomainPvpanicDefFormat(virBufferPtr buf, + virDomainPvpanicDefPtr def) +{ +if (def-ioport 0) { +virBufferAsprintf(buf, pvpanic ioport='%#x'/\n, + def-ioport); +} else { +virBufferAsprintf(buf, pvpanic/\n); Would break syntax-check. For static strings use virBufferAddLit. OK. +} + +return 0; +} static int virDomainRNGDefFormat(virBufferPtr buf, -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v2 2/2] qemu: add support for -device pvpanic
On Mon, Dec 02, 2013 at 11:15:17AM +0100, Peter Krempa wrote: On 12/02/13 07:11, Hu Tao wrote: This patch will add -device pvpanic to qemu command line if user enables pvpanic in domain xml and the qemu version supports pvpanic. Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- src/qemu/qemu_capabilities.c | 3 +++ src/qemu/qemu_capabilities.h | 2 ++ src/qemu/qemu_command.c | 10 ++ 3 files changed, 15 insertions(+) ... diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c index 763417f..6310bb2 100644 --- a/src/qemu/qemu_command.c +++ b/src/qemu/qemu_command.c @@ -9588,6 +9588,16 @@ qemuBuildCommandLine(virConnectPtr conn, goto error; } +if (def-pvpanic +virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE_PVPANIC)) { +if (def-pvpanic-ioport 0) { +virCommandAddArg(cmd, -device); +virCommandAddArgFormat(cmd, pvpanic,ioport=%d, + def-pvpanic-ioport); +} else +virCommandAddArgList(cmd, -device, pvpanic, NULL); If pvpanic is requested, but not available in qemu, libvirt should error out instead of silently starting the VM without the device. +} + if (mlock) { unsigned long long memKB; Also as said in review of 1/2. You need to add tests for the new device. Thanks. -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v2 2/2] qemu: add support for -device pvpanic
On Mon, Dec 02, 2013 at 02:38:09PM -0700, Eric Blake wrote: On 12/01/2013 11:11 PM, Hu Tao wrote: This patch will add -device pvpanic to qemu command line if user enables pvpanic in domain xml and the qemu version supports pvpanic. Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- src/qemu/qemu_capabilities.c | 3 +++ src/qemu/qemu_capabilities.h | 2 ++ src/qemu/qemu_command.c | 10 ++ 3 files changed, 15 insertions(+) In addition to Peter's comments, +++ b/src/qemu/qemu_capabilities.h @@ -199,6 +199,8 @@ enum virQEMUCapsFlags { QEMU_CAPS_DEVICE_ICH9_INTEL_HDA = 158, /* -device ich9-intel-hda */ QEMU_CAPS_KVM_PIT_TICK_POLICY = 159, /* kvm-pit.lost_tick_policy */ +QEMU_CAPS_DEVICE_PVPANIC = 160, /* -device pvpanic */ Alignment looks odd here. It aligns as most of the enums do. It doesn't look alike the above two because their names are too long. +if (def-pvpanic +virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE_PVPANIC)) { +if (def-pvpanic-ioport 0) { Again, is port 0 a valid port (given that you initialized it to -1)? I know we haven't been doing a good job of domxml-from-native, but in this particular case, can we also fix the command line parser to turn '-device pvpanic' into the appropriate pvpanic device allocation? In the case of native-xml, I think we'd better to keep port 0 in xml. I'll fix it. +} else Style. If you used {} for 'if', you must also use it for 'else' (I'm still not sure how to enforce it by syntax-check, but it's on my list of things that would be nice to have). Thanks. -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v2 1/2] conf: add xml element devices/pvpanic
On Mon, Dec 02, 2013 at 02:34:44PM -0700, Eric Blake wrote: On 12/01/2013 11:11 PM, Hu Tao wrote: This patch adds a new xml element devices/pvpanic to support qemu device pvpanic. It can be used to receive guest panic notification. Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- docs/formatdomain.html.in | 25 + src/conf/domain_conf.c| 68 +++ src/conf/domain_conf.h| 9 +++ 3 files changed, 102 insertions(+) In addition to Peter's review: when sending a series, it helps to include a 0/2 cover letter (git send-email --cover-letter). OK, will include it in next version. diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in index 1850a2b..0a72baa 100644 --- a/docs/formatdomain.html.in +++ b/docs/formatdomain.html.in @@ -5080,6 +5080,31 @@ qemu-kvm -net nic,model=? /dev/null /dd /dl +h4a name=elementsPvpanicpvpanic device/a/h4 pvpanic is a qemu term, but I could see the feasibility of other hypervisors having a paravirt device with a sole purpose of notifying the host about panics. Do we want to come up with a more generic name? I'd call it 'panic notification', but it doesn't sound like a device name. Advise? + lt;devicesgt; +lt;pvpanic ioport='0x505'/gt; + lt;/devicesgt; + ... +/pre + dl +dtcodeioport/code/dt +dd + p +ioport used by pvpanic. Probably worth documenting that 0x505 is the default port, and that most users don't need to specify the ioport. OK. +ioport = virXMLPropString(node, ioport); +if (!ioport) { +pvpanic-ioport = -1; +} else { +if (virStrToLong_i(ioport, NULL, 0, pvpanic-ioport) 0) { +virReportError(VIR_ERR_INTERNAL_ERROR, %s, VIR_ERR_INTERNAL_ERROR is probably the wrong type, since this is easily triggered by a user. I know it's copy and paste from other code, but these days, VIR_ERR_XML_ERROR is preferred in new code reporting a parse error. Should virDomainDeviceType be enhanced to include this device type? And if so, you need to modify at least virDomainDeviceDefFree() to handle the new enum value. OK. +static int virDomainPvpanicDefFormat(virBufferPtr buf, + virDomainPvpanicDefPtr def) +{ +if (def-ioport 0) { Isn't this an off-by-one if someone explicitly requests port 0 (since your parser initializes to -1 when left unspecified)? port 0 means disable the device, so there is no need to add it when port is 0. But if you'd prefer to let the device handle port itself, then it's OK to add it in the case. -- Regards, Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v2 2/2] qemu: add support for -device pvpanic
This patch will add -device pvpanic to qemu command line if user enables pvpanic in domain xml and the qemu version supports pvpanic. Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- src/qemu/qemu_capabilities.c | 3 +++ src/qemu/qemu_capabilities.h | 2 ++ src/qemu/qemu_command.c | 10 ++ 3 files changed, 15 insertions(+) diff --git a/src/qemu/qemu_capabilities.c b/src/qemu/qemu_capabilities.c index 548b988..ae2c192 100644 --- a/src/qemu/qemu_capabilities.c +++ b/src/qemu/qemu_capabilities.c @@ -243,6 +243,8 @@ VIR_ENUM_IMPL(virQEMUCaps, QEMU_CAPS_LAST, virtio-mmio, ich9-intel-hda, kvm-pit-lost-tick-policy, + + pvpanic, /* 160 */ ); struct _virQEMUCaps { @@ -1394,6 +1396,7 @@ struct virQEMUCapsStringFlags virQEMUCapsObjectTypes[] = { { usb-storage, QEMU_CAPS_DEVICE_USB_STORAGE }, { virtio-mmio, QEMU_CAPS_DEVICE_VIRTIO_MMIO }, { ich9-intel-hda, QEMU_CAPS_DEVICE_ICH9_INTEL_HDA }, +{ pvpanic, QEMU_CAPS_DEVICE_PVPANIC }, }; static struct virQEMUCapsStringFlags virQEMUCapsObjectPropsVirtioBlk[] = { diff --git a/src/qemu/qemu_capabilities.h b/src/qemu/qemu_capabilities.h index 02d47c6..0abe0b9 100644 --- a/src/qemu/qemu_capabilities.h +++ b/src/qemu/qemu_capabilities.h @@ -199,6 +199,8 @@ enum virQEMUCapsFlags { QEMU_CAPS_DEVICE_ICH9_INTEL_HDA = 158, /* -device ich9-intel-hda */ QEMU_CAPS_KVM_PIT_TICK_POLICY = 159, /* kvm-pit.lost_tick_policy */ +QEMU_CAPS_DEVICE_PVPANIC = 160, /* -device pvpanic */ + QEMU_CAPS_LAST, /* this must always be the last item */ }; diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c index 763417f..6310bb2 100644 --- a/src/qemu/qemu_command.c +++ b/src/qemu/qemu_command.c @@ -9588,6 +9588,16 @@ qemuBuildCommandLine(virConnectPtr conn, goto error; } +if (def-pvpanic +virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE_PVPANIC)) { +if (def-pvpanic-ioport 0) { +virCommandAddArg(cmd, -device); +virCommandAddArgFormat(cmd, pvpanic,ioport=%d, + def-pvpanic-ioport); +} else +virCommandAddArgList(cmd, -device, pvpanic, NULL); +} + if (mlock) { unsigned long long memKB; -- 1.7.11.7 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v2 1/2] conf: add xml element devices/pvpanic
This patch adds a new xml element devices/pvpanic to support qemu device pvpanic. It can be used to receive guest panic notification. Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- docs/formatdomain.html.in | 25 + src/conf/domain_conf.c| 68 +++ src/conf/domain_conf.h| 9 +++ 3 files changed, 102 insertions(+) diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in index 1850a2b..0a72baa 100644 --- a/docs/formatdomain.html.in +++ b/docs/formatdomain.html.in @@ -5080,6 +5080,31 @@ qemu-kvm -net nic,model=? /dev/null /dd /dl +h4a name=elementsPvpanicpvpanic device/a/h4 +p + pvpanic device enables libvirt to receive panic notification from a QEMU + guest. + span class=sinceSince 1.3.0, QEMU and KVM only/span +/p +p + Example: usage of pvpanic configuration +/p +pre + ... + lt;devicesgt; +lt;pvpanic ioport='0x505'/gt; + lt;/devicesgt; + ... +/pre + dl +dtcodeioport/code/dt +dd + p +ioport used by pvpanic. + /p +/dd + /dl + h3a name=seclabelSecurity label/a/h3 p diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c index 140eb80..1b8f66f 100644 --- a/src/conf/domain_conf.c +++ b/src/conf/domain_conf.c @@ -1876,6 +1876,11 @@ virDomainResourceDefFree(virDomainResourceDefPtr resource) VIR_FREE(resource); } +void +virDomainPvpanicDefFree(virDomainPvpanicDefPtr pvpanic) +{ +VIR_FREE(pvpanic); +} void virDomainDefFree(virDomainDefPtr def) { @@ -1964,6 +1969,8 @@ void virDomainDefFree(virDomainDefPtr def) virDomainTPMDefFree(def-tpm); +virDomainPvpanicDefFree(def-pvpanic); + VIR_FREE(def-idmap.uidmap); VIR_FREE(def-idmap.gidmap); @@ -10626,6 +10633,31 @@ cleanup: return idmap; } +static virDomainPvpanicDefPtr +virDomainPvpanicDefParseXML(xmlNodePtr node) +{ +char *ioport = NULL; +virDomainPvpanicDefPtr pvpanic; + +if (VIR_ALLOC(pvpanic) 0) +return NULL; + +ioport = virXMLPropString(node, ioport); +if (!ioport) { +pvpanic-ioport = -1; +} else { +if (virStrToLong_i(ioport, NULL, 0, pvpanic-ioport) 0) { +virReportError(VIR_ERR_INTERNAL_ERROR, %s, + _(Cannot parse pvpanic 'ioport' attribute)); +goto error; +} +} + +return pvpanic; +error: +virDomainPvpanicDefFree(pvpanic); +return NULL; +} /* Parse the XML definition for a vcpupin or emulatorpin. * @@ -12453,6 +12485,27 @@ virDomainDefParseXML(xmlDocPtr xml, } VIR_FREE(nodes); +/* analysis of the pvpanic devices */ +def-pvpanic = NULL; +if ((n = virXPathNodeSet(./devices/pvpanic, ctxt, nodes)) 0) { +goto error; +} +if (n 1) { +virReportError(VIR_ERR_INTERNAL_ERROR, %s, + _(only a single pvpanic device is supported)); +goto error; +} +if (n 0) { +virDomainPvpanicDefPtr pvpanic = +virDomainPvpanicDefParseXML(nodes[0]); +if (!pvpanic) +goto error; + +def-pvpanic = pvpanic; +VIR_FREE(nodes); +} + + /* analysis of the user namespace mapping */ if ((n = virXPathNodeSet(./idmap/uid, ctxt, nodes)) 0) goto error; @@ -15715,6 +15768,18 @@ virDomainWatchdogDefFormat(virBufferPtr buf, return 0; } +static int virDomainPvpanicDefFormat(virBufferPtr buf, + virDomainPvpanicDefPtr def) +{ +if (def-ioport 0) { +virBufferAsprintf(buf, pvpanic ioport='%#x'/\n, + def-ioport); +} else { +virBufferAsprintf(buf, pvpanic/\n); +} + +return 0; +} static int virDomainRNGDefFormat(virBufferPtr buf, @@ -17138,6 +17203,9 @@ virDomainDefFormatInternal(virDomainDefPtr def, if (def-nvram) virDomainNVRAMDefFormat(buf, def-nvram, flags); +if (def-pvpanic) +virDomainPvpanicDefFormat(buf, def-pvpanic); + virBufferAddLit(buf, /devices\n); virBufferAdjustIndent(buf, 2); diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h index 4561ccc..9395852 100644 --- a/src/conf/domain_conf.h +++ b/src/conf/domain_conf.h @@ -126,6 +126,9 @@ typedef virDomainIdMapEntry *virDomainIdMapEntryPtr; typedef struct _virDomainIdMapDef virDomainIdMapDef; typedef virDomainIdMapDef *virDomainIdMapDefPtr; +typedef struct _virDomainPvpanicDef virDomainPvpanicDef; +typedef virDomainPvpanicDef *virDomainPvpanicDefPtr; + /* Flags for the 'type' field in virDomainDeviceDef */ typedef enum { VIR_DOMAIN_DEVICE_NONE = 0, @@ -1910,6 +1913,10 @@ struct _virDomainIdMapDef { }; +struct _virDomainPvpanicDef { +int ioport; +}; + void virBlkioDeviceWeightArrayClear(virBlkioDeviceWeightPtr deviceWeights, int ndevices); @@ -2061,6 +2068,7 @@ struct _virDomainDef { virSysinfoDefPtr sysinfo
Re: [libvirt] [PATCH] qemu: add support for -device pvpanic
On Wed, Nov 27, 2013 at 11:39:49AM +0100, Peter Krempa wrote: On 11/27/13 09:41, Hu Tao wrote: qemu removes the builtin pvpanic device for all qemu versions since 1.7, in order to support on_crash, '-device pvpanic' has to be added to qemu command line. Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- src/qemu/qemu_capabilities.c | 8 src/qemu/qemu_capabilities.h | 2 ++ src/qemu/qemu_command.c | 4 3 files changed, 14 insertions(+) diff --git a/src/qemu/qemu_capabilities.c b/src/qemu/qemu_capabilities.c index 548b988..7783997 100644 --- a/src/qemu/qemu_capabilities.c +++ b/src/qemu/qemu_capabilities.c @@ -243,6 +243,8 @@ VIR_ENUM_IMPL(virQEMUCaps, QEMU_CAPS_LAST, virtio-mmio, ich9-intel-hda, kvm-pit-lost-tick-policy, + + pvpanic, /* 160 */ ); struct _virQEMUCaps { @@ -1198,6 +1200,9 @@ virQEMUCapsComputeCmdFlags(const char *help, virQEMUCapsSet(qemuCaps, QEMU_CAPS_VNC_SHARE_POLICY); } +if (version = 1005000) +virQEMUCapsSet(qemuCaps, QEMU_CAPS_PVPANIC); + Hard coding the version number is not a good idea. Libvirt uses qmp monitor queries to determine supported devices. Please add this in the virQEMUCapsObjectTypes structure instead, which will do the qmp detection for you. Thanks for advising, I'll do it in next version. return 0; } @@ -2561,6 +2566,9 @@ virQEMUCapsInitQMPMonitor(virQEMUCapsPtr qemuCaps, if (qemuCaps-version = 1006000) virQEMUCapsSet(qemuCaps, QEMU_CAPS_DEVICE_VIDEO_PRIMARY); +if (qemuCaps-version = 1005000) +virQEMUCapsSet(qemuCaps, QEMU_CAPS_PVPANIC); + Same here ... this should be autoprobed by a function using the structure above. if (virQEMUCapsProbeQMPCommands(qemuCaps, mon) 0) goto cleanup; if (virQEMUCapsProbeQMPEvents(qemuCaps, mon) 0) diff --git a/src/qemu/qemu_capabilities.h b/src/qemu/qemu_capabilities.h index 02d47c6..06d2fac 100644 --- a/src/qemu/qemu_capabilities.h +++ b/src/qemu/qemu_capabilities.h @@ -199,6 +199,8 @@ enum virQEMUCapsFlags { QEMU_CAPS_DEVICE_ICH9_INTEL_HDA = 158, /* -device ich9-intel-hda */ QEMU_CAPS_KVM_PIT_TICK_POLICY = 159, /* kvm-pit.lost_tick_policy */ +QEMU_CAPS_PVPANIC= 160, /* -device pvpanic */ + QEMU_CAPS_LAST, /* this must always be the last item */ }; diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c index 763417f..b1307a3 100644 --- a/src/qemu/qemu_command.c +++ b/src/qemu/qemu_command.c @@ -9588,6 +9588,10 @@ qemuBuildCommandLine(virConnectPtr conn, goto error; } +if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_PVPANIC)) { +virCommandAddArgList(cmd, -device, pvpanic, NULL); +} + I remember discussions saying that it's NOT a good idea to enable this stuff always. As a result, this device is not being added by qemu as you described above. Shouldn't we only add this if the user enables on_crash actions? Yes we should. When I was writing the patch, I found that def-onCrash has a default value even when user doesn't set on_crash. I must be reading the code wrong. Any, let me fix it in next version. -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH] qemu: add support for -device pvpanic
On Wed, Nov 27, 2013 at 06:15:27AM -0700, Eric Blake wrote: On 11/27/2013 03:39 AM, Peter Krempa wrote: On 11/27/13 09:41, Hu Tao wrote: qemu removes the builtin pvpanic device for all qemu versions since 1.7, in order to support on_crash, '-device pvpanic' has to be added to qemu command line. Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- I remember discussions saying that it's NOT a good idea to enable this stuff always. As a result, this device is not being added by qemu as you described above. Shouldn't we only add this if the user enables on_crash actions? You are precisely right; we MUST add a new entry under devices in the domain XML before enabling this device. Is a entry under devices for pvpanic still needed? What I thought is that it is natural to enable pvpanic when user enables on_crash, he/she even has no need to know about pvpanic. See these threads for some ideas (although recall that qemu has been fixed in the meantime to state that any distro shipping a qemu with pvpanic enabled by default can be considered buggy, and that libvirt can now assume that pvpanic will not happen without an explicit '-device pvpanic'): https://www.redhat.com/archives/libvir-list/2013-August/msg01184.html https://www.redhat.com/archives/libvir-list/2013-August/msg01136.html IIRC, at the time of the thread, the pvpanic entry under devices is for addressing the compatibility of qemu 1.5(has builtin pvpanic) and qemu 1.6 and after(has no builtin pvpanic). Since now qemu removes builtin pvpanic for all versions, I think there is no need for pvpanic entry in xml. -- Regards, Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH] qemu: add support for -device pvpanic
qemu removes the builtin pvpanic device for all qemu versions since 1.7, in order to support on_crash, '-device pvpanic' has to be added to qemu command line. Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- src/qemu/qemu_capabilities.c | 8 src/qemu/qemu_capabilities.h | 2 ++ src/qemu/qemu_command.c | 4 3 files changed, 14 insertions(+) diff --git a/src/qemu/qemu_capabilities.c b/src/qemu/qemu_capabilities.c index 548b988..7783997 100644 --- a/src/qemu/qemu_capabilities.c +++ b/src/qemu/qemu_capabilities.c @@ -243,6 +243,8 @@ VIR_ENUM_IMPL(virQEMUCaps, QEMU_CAPS_LAST, virtio-mmio, ich9-intel-hda, kvm-pit-lost-tick-policy, + + pvpanic, /* 160 */ ); struct _virQEMUCaps { @@ -1198,6 +1200,9 @@ virQEMUCapsComputeCmdFlags(const char *help, virQEMUCapsSet(qemuCaps, QEMU_CAPS_VNC_SHARE_POLICY); } +if (version = 1005000) +virQEMUCapsSet(qemuCaps, QEMU_CAPS_PVPANIC); + return 0; } @@ -2561,6 +2566,9 @@ virQEMUCapsInitQMPMonitor(virQEMUCapsPtr qemuCaps, if (qemuCaps-version = 1006000) virQEMUCapsSet(qemuCaps, QEMU_CAPS_DEVICE_VIDEO_PRIMARY); +if (qemuCaps-version = 1005000) +virQEMUCapsSet(qemuCaps, QEMU_CAPS_PVPANIC); + if (virQEMUCapsProbeQMPCommands(qemuCaps, mon) 0) goto cleanup; if (virQEMUCapsProbeQMPEvents(qemuCaps, mon) 0) diff --git a/src/qemu/qemu_capabilities.h b/src/qemu/qemu_capabilities.h index 02d47c6..06d2fac 100644 --- a/src/qemu/qemu_capabilities.h +++ b/src/qemu/qemu_capabilities.h @@ -199,6 +199,8 @@ enum virQEMUCapsFlags { QEMU_CAPS_DEVICE_ICH9_INTEL_HDA = 158, /* -device ich9-intel-hda */ QEMU_CAPS_KVM_PIT_TICK_POLICY = 159, /* kvm-pit.lost_tick_policy */ +QEMU_CAPS_PVPANIC= 160, /* -device pvpanic */ + QEMU_CAPS_LAST, /* this must always be the last item */ }; diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c index 763417f..b1307a3 100644 --- a/src/qemu/qemu_command.c +++ b/src/qemu/qemu_command.c @@ -9588,6 +9588,10 @@ qemuBuildCommandLine(virConnectPtr conn, goto error; } +if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_PVPANIC)) { +virCommandAddArgList(cmd, -device, pvpanic, NULL); +} + if (mlock) { unsigned long long memKB; -- 1.8.3.1 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] pvpanic plans?
Hi All, I know it's been a long time since this thread. But qemu 1.7 is releasing, do you have any consensus on this? Thanks. -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v7 6/6] qemu: Implement oncrash 'rename-resart' event when guest panicked
On Fri, Jun 14, 2013 at 06:14:40PM +0800, Chen Fan wrote: Implements 'rename-restart' behavior of the 'on_crash' in the XML when domain crashed. --- src/qemu/qemu_driver.c | 67 ++ 1 file changed, 67 insertions(+) diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c index eefe7a2..a166468 100644 --- a/src/qemu/qemu_driver.c +++ b/src/qemu/qemu_driver.c @@ -3566,6 +3566,55 @@ cleanup: return ret; } +static int +qemuProcessVmRenameAlive(virQEMUDriverPtr driver, + virDomainObjPtr vm, char *alias) +{ +int ret = -1; +char *oldname = NULL; +char *newDefname = NULL; +char ebuf[1024]; +char *statefile = NULL; +virQEMUDriverConfigPtr cfg = virQEMUDriverGetConfig(driver); + +if (strstr(vm-def-name, -crashed)) { +ret = 0; +goto cleanup; +} + +oldname = vm-def-name; +vm-def-name = alias; + +if (vm-newDef) { +if (VIR_STRDUP(newDefname, oldname) 0) { +virReportOOMError(); +goto cleanup; +} +VIR_FREE(vm-newDef-name); +vm-newDef-name = newDefname; +} + +if (virAsprintf(statefile, %s/%s.xml, cfg-stateDir, oldname) 0) { +virReportOOMError(); +goto cleanup; +} + +if (unlink(statefile) 0 errno != ENOENT errno != ENOTDIR) +VIR_WARN(Failed to remove domain XML for %s: %s, + oldname, virStrerror(errno, ebuf, sizeof(ebuf))); + +if (virDomainSaveStatus(driver-xmlopt, cfg-stateDir, vm) 0) +VIR_WARN(Failed to save status on vm %s, vm-def-name); + +ret = 0; + +cleanup: +VIR_FREE(statefile); +VIR_FREE(oldname); +virObjectUnref(cfg); +return ret; +} + static void processGuestPanicEvent(virQEMUDriverPtr driver, virDomainObjPtr vm, @@ -3650,6 +3699,24 @@ processGuestPanicEvent(virQEMUDriverPtr driver, qemuProcessShutdownOrReboot(driver, vm); break; +case VIR_DOMAIN_LIFECYCLE_CRASH_RESTART_RENAME: +{ +char *alias = NULL; +if (virAsprintf(alias, %s-crashed, The doc doesn't say how to rename a domain on crash, I'm not sure whether oldname + -crashed is reasonable. While changing the name, should we change the UUID at the same time? +vm-def-name) 0) { +virReportOOMError(); +goto cleanup; +} +if (qemuProcessVmRenameAlive(driver, vm, alias) 0) { BTW, seems there can be a API for changing domain name. +VIR_FREE(alias); +goto cleanup; +} + +qemuDomainSetFakeReboot(driver, vm, true); +qemuProcessShutdownOrReboot(driver, vm); +} +break; + case VIR_DOMAIN_LIFECYCLE_CRASH_PRESERVE: break; -- 1.8.1.4 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [RFC PATCH 8/8] qemu: Set cpuset.mems even if the numatune mode is not strict
On Thu, May 09, 2013 at 06:22:17PM +0800, Osier Yang wrote: When the numatune memory mode is not strict, the cpuset.mems inherits the parent's setting, which causes problem like: % virsh dumpxml rhel6_local | grep interleave -2 vcpu placement='static'2/vcpu numatune memory mode='interleave' nodeset='1-2'/ /numatune os % cat /proc/3713/status | grep Mems_allowed_list Mems_allowed_list: 0-3 % virsh numatune rhel6_local numa_mode : interleave numa_nodeset : 0-3 Yes the information is misleading. Though the domain process's memory binding is set with libnuma after the cgroup setting. The reason for only allowing strict mode in current code is the cpuset.mems doesn't understand the memory policy modes (interleave, prefered, strict), it actually equals to the strict mode (strict means the allocation will fail if the memory cannot be allocated on the target node. Default operation is to fall back to other nodes. Default is localalloc. From man numa(3)). However, writing the the cpuset.mems even if the numatune memory mode is not strict should be better than the blind inheritance anyway. It's OK to interleave mode, combined with cpuset.memory_spread_xxx. But what about preferred mode? comparing: strict: Strict means the allocation will fail if the memory cannot be allocated on the target node. preferred: The system will attempt to allocate memory from the preferred node, but will fall back to other nodes if no memory is available on the the preferred node. --- However, I'm not comfortable with the solution, since anyway the modes except strict are not meaningful for cpuset.mems. Another problem what I'm not sure about is: If the cpuset.cpus will affect the libnuma setting? Assuming without this patch, domain process's cpuset.mems will be set as '0-7' (8 NUMA nodes, each has 8 CPUs). And the numatune memory mode is interleave, and libnuma set the memory binding as 1-2. Even with this patch applied, setting cpuset.mems as 1-2, any potential problem? So this patch is mainly for raising up the problem, and to see if guys have any opinions. @hutao, since these codes are from you, any opinions/idea? Thanks. --- src/qemu/qemu_cgroup.c | 18 +- 1 file changed, 13 insertions(+), 5 deletions(-) diff --git a/src/qemu/qemu_cgroup.c b/src/qemu/qemu_cgroup.c index 33eebd7..22fe25b 100644 --- a/src/qemu/qemu_cgroup.c +++ b/src/qemu/qemu_cgroup.c @@ -597,11 +597,9 @@ qemuSetupCpusetCgroup(virDomainObjPtr vm, if (!virCgroupHasController(priv-cgroup, VIR_CGROUP_CONTROLLER_CPUSET)) return 0; -if ((vm-def-numatune.memory.nodemask || - (vm-def-numatune.memory.placement_mode == - VIR_NUMA_TUNE_MEM_PLACEMENT_MODE_AUTO)) -vm-def-numatune.memory.mode == VIR_DOMAIN_NUMATUNE_MEM_STRICT) { - +if (vm-def-numatune.memory.nodemask || +(vm-def-numatune.memory.placement_mode == + VIR_NUMA_TUNE_MEM_PLACEMENT_MODE_AUTO)) { if (vm-def-numatune.memory.placement_mode == VIR_NUMA_TUNE_MEM_PLACEMENT_MODE_AUTO) mem_mask = virBitmapFormat(nodemask); @@ -614,6 +612,16 @@ qemuSetupCpusetCgroup(virDomainObjPtr vm, goto cleanup; } +if (vm-def-numatune.memory.mode == +VIR_DOMAIN_NUMATUNE_MEM_PREFERRED +strlen(mem_mask) != 1) { +virReportError(VIR_ERR_INTERNAL_ERROR, %s, + _(NUMA memory tuning in 'preferred' mode + only supports single node)); +goto cleanup; + +} + rc = virCgroupSetCpusetMems(priv-cgroup, mem_mask); if (rc != 0) { -- 1.8.1.4 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH] build: fix build error of src/libvirt.c
Following build error caused by commit 7c9a2d88: libvirt.c: In function 'virConnectGetConfigFilePath': libvirt.c:956:9: error: implicit declaration of function 'virGetUserConfigDirectory' [-Werror=implicit-function-declaration] libvirt.c:956:9: error: nested extern declaration of 'virGetUserConfigDirectory' [-Werror=nested-externs] libvirt.c:956:25: error: initialization makes pointer from integer without a cast [-Werror] libvirt.c: In function 'virConnectGetConfigFile': libvirt.c:987:5: error: implicit declaration of function 'virFileExists' [-Werror=implicit-function-declaration] libvirt.c:987:5: error: nested extern declaration of 'virFileExists' [-Werror=nested-externs] libvirt.c: In function 'virDomainSave': libvirt.c:2623:9: error: implicit declaration of function 'virFileAbsPath' [-Werror=implicit-function-declaration] libvirt.c:2623:9: error: nested extern declaration of 'virFileAbsPath' [-Werror=nested-externs] Signed-off-by: Hu Tao hu...@cn.fujitsu.com --- src/libvirt.c | 1 + 1 file changed, 1 insertion(+) diff --git a/src/libvirt.c b/src/libvirt.c index 15b37a3..467f6dd 100644 --- a/src/libvirt.c +++ b/src/libvirt.c @@ -63,6 +63,7 @@ #include viruri.h #include virthread.h #include virstring.h +#include virutil.h #ifdef WITH_TEST # include test/test_driver.h -- 1.8.1.4 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH] build: fix build error of src/libvirt.c
On Thu, May 02, 2013 at 10:08:11PM -0600, Eric Blake wrote: On 05/02/2013 09:44 PM, Hu Tao wrote: Following build error caused by commit 7c9a2d88: libvirt.c: In function 'virConnectGetConfigFilePath': libvirt.c:956:9: error: implicit declaration of function 'virGetUserConfigDirectory' [-Werror=implicit-function-declaration] +++ b/src/libvirt.c @@ -63,6 +63,7 @@ #include viruri.h #include virthread.h #include virstring.h +#include virutil.h This was already fixed in commit 348ac061. Sorry, didn't notice that one(my git server has some latency). -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v2.5 03/10] conf: Introduce scsi hostdev
On Mon, Apr 15, 2013 at 08:27:10PM +0800, Han Cheng wrote: Thanks for your best efforts. I only have one problem. Please find it at the end. 于 2013/4/10 16:59, Osier Yang 写道: On 09/04/13 10:32, Han Cheng wrote: Add scsi hostdev, it looks like: hostdev mode='subsystem' type='scsi' source adapter name='scsi_host0'/ address bus='0' target='0' unit='0'/ /source address type='drive' controller='0' bus='0' target='4' unit='8'/ /hostdev @@ -11028,6 +11154,18 @@ virDomainDefParseXML(xmlDocPtr xml, goto error; } +if (hostdev-source.subsys.type == VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI +hostdev-info-type == VIR_DOMAIN_DEVICE_ADDRESS_TYPE_NONE) { +/* We define default mapping to be 1 controller, 1 bus, + * 1 target and many units. And we reserve first 16 unit for + * disk usage in virDomainDiskDefAssignAddress */ +hostdev-info-type = VIR_DOMAIN_DEVICE_ADDRESS_TYPE_DRIVE; +hostdev-info-addr.drive.controller = 0; +hostdev-info-addr.drive.bus = 0; +hostdev-info-addr.drive.target = 0; +hostdev-info-addr.drive.unit = 16 + i; Why do we need to set the default values here? Per the address is mandatory. I don't think so. The address in source is mandatory and is parsed by virDomainHostdevSubsysScsiDefParseXML called by virDomainHostdevSubsysUsbDefParseXML. The address out of s/virDomainHostdevSubsysUsbDefParseXML/virDomainHostdevDefParseXMLSubsys/ source is not mandatory and is parsed by virDomainDeviceInfoParseXML which is called by virDomainHostdevDefParseXML. So we may need to set the default values. I'm afraid you have mixed these two addresses. I think Osier means hostdev/address, but not hostdev/source/address. -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v2 05/10] utils: util functions for scsi hostdev
On Mon, Apr 01, 2013 at 08:00:57PM +0800, Han Cheng wrote: This patch add util functions for scsi hostdev. Signed-off-by: Han Cheng hanc.f...@cn.fujitsu.com --- po/POTFILES.in |1 + src/Makefile.am |1 + src/libvirt_private.syms | 22 +++ src/util/virscsi.c | 399 ++ src/util/virscsi.h | 83 ++ 5 files changed, 506 insertions(+), 0 deletions(-) create mode 100644 src/util/virscsi.c create mode 100644 src/util/virscsi.h diff --git a/po/POTFILES.in b/po/POTFILES.in index 91e5c02..39a0a19 100644 --- a/po/POTFILES.in +++ b/po/POTFILES.in @@ -174,6 +174,7 @@ src/util/virportallocator.c src/util/virprocess.c src/util/virrandom.c src/util/virsexpr.c +src/util/virscsi.c src/util/virsocketaddr.c src/util/virstatslinux.c src/util/virstoragefile.c diff --git a/src/Makefile.am b/src/Makefile.am index 3f69d39..49d7f88 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -111,6 +111,7 @@ UTIL_SOURCES = \ util/virportallocator.c util/virportallocator.h \ util/virprocess.c util/virprocess.h \ util/virrandom.h util/virrandom.c \ + util/virscsi.c util/virscsi.h \ util/virsexpr.c util/virsexpr.h \ util/virsocketaddr.h util/virsocketaddr.c \ util/virstatslinux.c util/virstatslinux.h \ diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index f2eefc3..6a5962e 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -1665,6 +1665,28 @@ virRandomGenerateWWN; virRandomInt; +# util/virscsi.h +virSCSIDeviceFileIterate; +virSCSIDeviceFree; +virSCSIDeviceGetAdapter; +virSCSIDeviceGetBus; +virSCSIDeviceGetDevStr; +virSCSIDeviceGetName; +virSCSIDeviceGetReadonly; +virSCSIDeviceGetTarget; +virSCSIDeviceGetUnit; +virSCSIDeviceGetUsedBy; +virSCSIDeviceListAdd; +virSCSIDeviceListCount; +virSCSIDeviceListDel; +virSCSIDeviceListFind; +virSCSIDeviceListGet; +virSCSIDeviceListNew; +virSCSIDeviceListSteal; +virSCSIDeviceNew; +virSCSIDeviceSetUsedBy; + + # util/virsexpr.h sexpr2string; sexpr_append; diff --git a/src/util/virscsi.c b/src/util/virscsi.c new file mode 100644 index 000..5d0dcd7 --- /dev/null +++ b/src/util/virscsi.c @@ -0,0 +1,399 @@ +/* + * virscsi.c: helper APIs for managing host SCSI devices + * + * Copyright (C) 2013 Fujitsu, Inc. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library. If not, see + * http://www.gnu.org/licenses/. + * + * Authors: + * Han Cheng hanc.f...@cn.fujitsu.com + */ + +#include config.h + +#include dirent.h +#include fcntl.h +#include inttypes.h +#include limits.h +#include stdio.h +#include string.h +#include sys/types.h +#include sys/stat.h +#include unistd.h + +#include virscsi.h +#include virlog.h +#include viralloc.h +#include virutil.h +#include virerror.h + +#define SCSI_DEVFS /sys/bus/scsi/devices + +/* For virReportOOMError() and virReportSystemError() */ +#define VIR_FROM_THIS VIR_FROM_NONE + +struct _virSCSIDevice { +unsigned int adapter; +unsigned int bus; +unsigned int target; +unsigned int unit; + +char *name; /* adapter:bus:target:unit */ +char *id; /* model vendor */ +char *path; +const char*used_by; /* name of the domain using this dev */ + +unsigned int readonly : 1; +}; + +struct _virSCSIDeviceList { +virObjectLockable parent; +unsigned int count; +virSCSIDevicePtr *devs; +}; I think it's better to implement a generic object list, otherwise everytime who wants a list, he/she has to re-implement a list. + +static virClassPtr virSCSIDeviceListClass; + +static void virSCSIDeviceListDispose(void *obj); + +static int virSCSIOnceInit(void) +{ +if (!(virSCSIDeviceListClass = virClassNew(virClassForObjectLockable(), + virSCSIDeviceList, + sizeof(virSCSIDeviceList), + virSCSIDeviceListDispose))) The indentation style is: virClassNew(...
Re: [libvirt] [PATCH v2 01/10] conf: Introduce readonly to hostdev and change helper function
On Mon, Apr 01, 2013 at 08:00:53PM +0800, Han Cheng wrote: The only parameter in -drive affect scsi-generic is readonly. Introduce readonly/ to hostdev. The helper function to look up disk controller model may be used by scsi hostdev. But it should be changed to use info. Signed-off-by: Han Cheng hanc.f...@cn.fujitsu.com --- docs/formatdomain.html.in |3 +++ docs/schemas/domaincommon.rng |5 + src/conf/domain_conf.c|6 +++--- src/conf/domain_conf.h|6 -- src/libvirt_private.syms |2 +- src/qemu/qemu_command.c |4 ++-- 6 files changed, 18 insertions(+), 8 deletions(-) diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in index cf382e8..a6bacfa 100644 --- a/docs/formatdomain.html.in +++ b/docs/formatdomain.html.in @@ -2257,6 +2257,9 @@ codeid/code attribute that specifies the USB vendor and product id. The ids can be given in decimal, hexadecimal (starting with 0x) or octal (starting with 0) form./dd + dtcodereadonly/code/dt + ddSpecifies that the device is readonly. + span class=sinceSince 0.13.0/span for SCSI devices./dd 0.13.0 - 1.0.5 version 1.0.4 is just out. dtcodeboot/code/dt ddSpecifies that the device is bootable. The codeorder/code attribute determines the order in which devices will be tried during diff --git a/docs/schemas/domaincommon.rng b/docs/schemas/domaincommon.rng index 8d7e6db..ccf0913 100644 --- a/docs/schemas/domaincommon.rng +++ b/docs/schemas/domaincommon.rng @@ -2911,6 +2911,11 @@ ref name=alias/ /optional optional +element name='readonly' + empty/ +/element + /optional + optional ref name=deviceBoot/ /optional optional diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c index f3fca7f..d9d6b9f 100644 --- a/src/conf/domain_conf.c +++ b/src/conf/domain_conf.c @@ -3452,8 +3452,8 @@ error: } int -virDomainDiskFindControllerModel(virDomainDefPtr def, - virDomainDiskDefPtr disk, +virDomainDeviceFindControllerModel(virDomainDefPtr def, + virDomainDeviceInfoPtr info, int controllerType) Indentation. { int model = -1; @@ -3461,7 +3461,7 @@ virDomainDiskFindControllerModel(virDomainDefPtr def, for (i = 0; i def-ncontrollers; i++) { if (def-controllers[i]-type == controllerType -def-controllers[i]-idx == disk-info.addr.drive.controller) +def-controllers[i]-idx == info-addr.drive.controller) model = def-controllers[i]-model; } diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h index edddf25..f8e3973 100644 --- a/src/conf/domain_conf.h +++ b/src/conf/domain_conf.h @@ -439,6 +439,8 @@ struct _virDomainHostdevDef { } source; virDomainHostdevOrigStates origstates; virDomainDeviceInfoPtr info; /* Guest address */ +/* readonly is only used for scsi hostdev */ +unsigned int readonly; bool readonly; }; /* Two types of disk backends */ @@ -1981,8 +1983,8 @@ void virDomainInputDefFree(virDomainInputDefPtr def); void virDomainDiskDefFree(virDomainDiskDefPtr def); void virDomainLeaseDefFree(virDomainLeaseDefPtr def); void virDomainDiskHostDefFree(virDomainDiskHostDefPtr def); -int virDomainDiskFindControllerModel(virDomainDefPtr def, - virDomainDiskDefPtr disk, +int virDomainDeviceFindControllerModel(virDomainDefPtr def, + virDomainDeviceInfoPtr info, int controllerType); Indentation. virDomainDiskDefPtr virDomainDiskFindByBusAndDst(virDomainDefPtr def, int bus, diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 96eea0a..f2eefc3 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -128,6 +128,7 @@ virDomainDeviceAddressTypeToString; virDomainDeviceDefCopy; virDomainDeviceDefFree; virDomainDeviceDefParse; +virDomainDeviceFindControllerModel; virDomainDeviceInfoCopy; virDomainDeviceInfoIterate; virDomainDeviceTypeToString; @@ -145,7 +146,6 @@ virDomainDiskDeviceTypeToString; virDomainDiskErrorPolicyTypeFromString; virDomainDiskErrorPolicyTypeToString; virDomainDiskFindByBusAndDst; -virDomainDiskFindControllerModel; virDomainDiskGeometryTransTypeFromString; virDomainDiskGeometryTransTypeToString; virDomainDiskHostDefFree; diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c index a0c278f..eac72c2 100644 --- a/src/qemu/qemu_command.c +++ b/src/qemu/qemu_command.c @@ -557,7 +557,7 @@ qemuAssignDeviceDiskAliasCustom(virDomainDefPtr def, if (disk-info.type == VIR_DOMAIN_DEVICE_ADDRESS_TYPE_DRIVE) { if (disk-bus ==
Re: [libvirt] [PATCH v2 03/10] conf: Introduce scsi hostdev
On Mon, Apr 01, 2013 at 08:00:55PM +0800, Han Cheng wrote: Adding scsi hostdev, it should like: hostdev mode='subsystem' type='scsi' source adapter name='scsi_host0'/ address bus='0' target='0' unit='0'/ /source address type='drive' controller='0' bus='0' target='4' unit='8'/ /hostdev Signed-off-by: Han Cheng hanc.f...@cn.fujitsu.com --- docs/formatdomain.html.in | 34 ++-- docs/schemas/domaincommon.rng | 24 + src/conf/domain_audit.c | 10 ++ src/conf/domain_conf.c| 192 - src/conf/domain_conf.h|7 ++ 5 files changed, 258 insertions(+), 9 deletions(-) diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in index a6bacfa..be3630e 100644 --- a/docs/formatdomain.html.in +++ b/docs/formatdomain.html.in @@ -2172,13 +2172,13 @@ h4a name=elementsHostDevHost device assignment/a/h4 -h5a href=elementsHostDevSubsysUSB / PCI devices/a/h5 +h5a href=elementsHostDevSubsysUSB / PCI / SCSI devices/a/h5 p - USB and PCI devices attached to the host can be passed through + USB, PCI and SCSI devices attached to the host can be passed through to the guest using the codehostdev/code element. - span class=sincesince after 0.4.4 for USB and 0.6.0 for PCI -(KVM only)/span: + span class=sincesince after 0.4.4 for USB, 0.6.0 for PCI(KVM only) +and 0.13.0 for SCSI(KVM only)/span: s/0.13.0/1.0.5/ /p pre @@ -2209,12 +2209,29 @@ lt;/devicesgt; .../pre +por:/p + +pre + ... + lt;devicesgt; +lt;hostdev mode='subsystem' type='scsi'gt; + lt;sourcegt; +lt;adapter name='scsi_host0'/gt; +lt;address type='scsi' bus='0' target='0' unit='0'/gt; + lt;/sourcegt; + lt;readonly/gt; + lt;address type='scsi' controller= '0' bus='0' target='0' unit='0'/gt; s/controller= '0'/controller='0'/ +lt;/hostdevgt; + lt;/devicesgt; + .../pre + dl dtcodehostdev/code/dt ddThe codehostdev/code element is the main container for describing host devices. For usb device passthrough codemode/code is always -subsystem and codetype/code is usb for a USB device and pci -for a PCI device. When codemanaged/code is yes for a PCI +subsystem and codetype/code is usb for a USB device, pci s/is usb/is usb/ +for a PCI device and scsi for a SCSI device. When +codemanaged/code is yes for a PCI device, it is detached from the host before being passed on to the guest, and reattached to the host after the guest exits. If codemanaged/code is omitted or no, and for USB @@ -2224,13 +2241,15 @@ hot-plugging the device, and codevirNodeDeviceReAttach/code (or codevirsh nodedev-reattach/code) after hot-unplug or stopping the -guest./dd +guest.For SCSI device, user is responsible to make sure do not s/guest.For/guest. For/ +use this device on host/dd dtcodesource/code/dt ddThe source element describes the device as seen from the host. The USB device can either be addressed by vendor / product id using the codevendor/code and codeproduct/code elements or by the device's address on the hosts using the codeaddress/code element. PCI devices on the other hand can only be described by their codeaddress/code. + SCSI devices is described by codeadaptercode and codeaddresscode. codeadapter/code and codeaddress/code, note the closing /code. span class=sinceSince 1.0.0/span, the codesource/code element of USB devices may contain codestartupPolicy/code attribute which can @@ -2268,6 +2287,7 @@ a href=#elementsOSBIOSBIOS bootloader/a section. span class=sinceSince 0.8.8/span for PCI devices, span class=sinceSince 1.0.1/span for USB devices. + span class=sinceSince 1.0.0/span for SCSI devices. s/1.0.0/1.0.5/ dtcoderom/code/dt ddThe coderom/code element is used to change how a PCI device's ROM is presented to the guest. The optional codebar/code diff --git a/docs/schemas/domaincommon.rng b/docs/schemas/domaincommon.rng index 364abf1..209d4f5 100644 --- a/docs/schemas/domaincommon.rng +++ b/docs/schemas/domaincommon.rng @@ -2945,6 +2945,7 @@ choice ref name=hostdevsubsyspci/ ref name=hostdevsubsysusb/ + ref name=hostdevsubsysscsi/ /choice /define @@ -2997,6 +2998,18 @@ /element /define + define name=hostdevsubsysscsi +attribute name=type + valuescsi/value +/attribute +element name=source + ref name=sourceinfoadapter/ + element name=address +ref name=scsiaddress/ + /element +/element + /define + define name=hostdevcapsstorage attribute
Re: [libvirt] [PATCH] net: use newer iptables syntax
On Mon, Mar 25, 2013 at 08:39:40PM +0100, Stefan Seyfried wrote: Hi all, iptables-1.4.18 removed the long deprecated state match. Use conntrack instead in forwarding rules. Fixes openSUSE bug https://bugzilla.novell.com/811251 #811251. real patch is attached as I'm pretty sure that thunderbird will mess it up otherwise :( Basically it's s/--match state/--match conntrack/ s/--state /--ctstate/ This is supported by old iptables. (tested with 1.4.14) in src/til/viriptables.c Best regards, Stefan -- Stefan Seyfried Linux Consultant Developer Mail: seyfr...@b1-systems.de GPG Key: 0x731B665B B1 Systems GmbH Osterfeldstraße 7 / 85088 Vohburg / http://www.b1-systems.de GF: Ralph Dehner / Unternehmenssitz: Vohburg / AG: Ingolstadt,HRB 3537 From 1aa2736263537e7856db9820bce835c1b3c2b51a Mon Sep 17 00:00:00 2001 From: Stefan Seyfried seife+...@b1-systems.com Date: Mon, 25 Mar 2013 20:27:46 +0100 Subject: [PATCH] net: use newer iptables syntax iptables-1.4.18 removed the long deprecated state match. Use conntrack instead in forwarding rules. Fixes openSUSE bug https://bugzilla.novell.com/811251 #811251. --- src/util/viriptables.c | 8 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/util/viriptables.c b/src/util/viriptables.c index 8cfafc0..19d6161 100644 --- a/src/util/viriptables.c +++ b/src/util/viriptables.c @@ -480,8 +480,8 @@ iptablesForwardAllowRelatedIn(iptablesContext *ctx, --destination, networkstr, --in-interface, physdev, --out-interface, iface, ---match, state, ---state, ESTABLISHED,RELATED, +--match, conntrack, +--ctstate, ESTABLISHED,RELATED, --jump, ACCEPT, NULL); } else { @@ -490,8 +490,8 @@ iptablesForwardAllowRelatedIn(iptablesContext *ctx, action, --destination, networkstr, --out-interface, iface, ---match, state, ---state, ESTABLISHED,RELATED, +--match, conntrack, +--ctstate, ESTABLISHED,RELATED, --jump, ACCEPT, NULL); } -- 1.8.2 ACK. -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH] Remove the redundant parentheses in migrate help
On Tue, Mar 26, 2013 at 11:02:17AM +0800, Yanbing Du wrote: Signed-off-by: Yanbing Du y...@redhat.com --- tools/virsh-domain.c |2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diff --git a/tools/virsh-domain.c b/tools/virsh-domain.c index 128e516..592a6e8 100644 --- a/tools/virsh-domain.c +++ b/tools/virsh-domain.c @@ -8286,7 +8286,7 @@ static const vshCmdOptDef opts_migrate[] = { }, {.name = change-protection, .type = VSH_OT_BOOL, - .help = N_(prevent any configuration changes to domain until migration ends)) + .help = N_(prevent any configuration changes to domain until migration ends) }, {.name = unsafe, .type = VSH_OT_BOOL, -- 1.7.1 I think this one can be pushed according trivial rules. -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] failed to mount cgroup
On Tue, Mar 05, 2013 at 05:29:02PM +0800, Gao feng wrote: On 2013/03/05 14:43, Yin Olivia-R63875 wrote: Hi, I tried to run libvirt-1.0.2 with LXC as below, but it failed to mount cgroup. You should change your cgroup configuration as below cgroup on /sys/fs/cgroup/cpuset type cgroup (rw,nosuid,nodev,noexec,relatime,cpuset) cgroup on /sys/fs/cgroup/cpu,cpuacct type cgroup (rw,nosuid,nodev,noexec,relatime,cpuacct,cpu) cgroup on /sys/fs/cgroup/memory type cgroup (rw,nosuid,nodev,noexec,relatime,memory) cgroup on /sys/fs/cgroup/devices type cgroup (rw,nosuid,nodev,noexec,relatime,devices) cgroup on /sys/fs/cgroup/freezer type cgroup (rw,nosuid,nodev,noexec,relatime,freezer) cgroup on /sys/fs/cgroup/net_cls type cgroup (rw,nosuid,nodev,noexec,relatime,net_cls) cgroup on /sys/fs/cgroup/blkio type cgroup (rw,nosuid,nodev,noexec,relatime,blkio) cgroup on /sys/fs/cgroup/perf_event type cgroup (rw,nosuid,nodev,noexec,relatime,perf_event) Libvirt lxc doesn't support configure cgroup as you did below now. Why? IIRC old systems mount cgroup at /cgroup by default. This means libvirt lxc has backward compatibility on supporting cgroup? And, in the case can libvirt lxc give a user-friendly message to user about what user can do? -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v2 RESEND 0/2] cgroup refactor
ping... On Fri, Feb 08, 2013 at 10:16:25AM +0800, Hu Tao wrote: This series is for early review. This series refactors cgroup code to: - provide lazy creation of cgroup directories, despite of what level they are. - remove cgroup directories if no one is using the corresponding virCgroup. changes from v2: - rebase to latest tree. - squash patches 2-5 in v2 into one. Hu Tao (2): refactor virCgroupDetectMounts and virCgroupDetectPlacement cgroup: refactor virCgroup src/conf/domain_conf.h|5 + src/libvirt_private.syms |7 +- src/lxc/lxc_cgroup.c | 40 +- src/lxc/lxc_cgroup.h |2 +- src/lxc/lxc_controller.c | 31 +- src/lxc/lxc_driver.c | 177 +++ src/lxc/lxc_process.c | 19 +- src/qemu/qemu_cgroup.c| 162 +++--- src/qemu/qemu_cgroup.h|3 +- src/qemu/qemu_driver.c| 350 + src/qemu/qemu_hotplug.c | 21 +- src/qemu/qemu_migration.c | 20 +- src/qemu/qemu_process.c |7 +- src/util/vircgroup.c | 1263 + src/util/vircgroup.h | 19 +- 15 files changed, 920 insertions(+), 1206 deletions(-) -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v2 2/5] cgroup: refactor virCgroup
On Thu, Feb 07, 2013 at 03:33:46PM +, Daniel P. Berrange wrote: On Mon, Feb 04, 2013 at 03:40:58PM +0800, Hu Tao wrote: This patch adds a new structure, virCgroupItem, to represent a cgroup directory(named cgroup item). cgroup directory is created when needed and removed if no one is using it. --- src/libvirt_private.syms | 2 + src/util/vircgroup.c | 541 ++- src/util/vircgroup.h | 8 + 3 files changed, 545 insertions(+), 6 deletions(-) diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index c589236..f5138af 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -73,6 +73,8 @@ virCapabilitiesSetMacPrefix; # cgroup.h +virCgroup2Free; +virCgroup2New; virCgroupAddTask; virCgroupAddTaskController; virCgroupAllowDevice; I'm sorry, this approach will just not work. If you want to refactor code, you need to actually do refactoring. What you've done here is write a completely new set of APIs with new names. Then delete the old ones in the next patch. That isn't refactoring makes it impossible to sensibly review this. Well, then I'll squash 2, 3, 4, 5 into a big one. -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v2 RESEND 0/2] cgroup refactor
This series is for early review. This series refactors cgroup code to: - provide lazy creation of cgroup directories, despite of what level they are. - remove cgroup directories if no one is using the corresponding virCgroup. changes from v2: - rebase to latest tree. - squash patches 2-5 in v2 into one. Hu Tao (2): refactor virCgroupDetectMounts and virCgroupDetectPlacement cgroup: refactor virCgroup src/conf/domain_conf.h|5 + src/libvirt_private.syms |7 +- src/lxc/lxc_cgroup.c | 40 +- src/lxc/lxc_cgroup.h |2 +- src/lxc/lxc_controller.c | 31 +- src/lxc/lxc_driver.c | 177 +++ src/lxc/lxc_process.c | 19 +- src/qemu/qemu_cgroup.c| 162 +++--- src/qemu/qemu_cgroup.h|3 +- src/qemu/qemu_driver.c| 350 + src/qemu/qemu_hotplug.c | 21 +- src/qemu/qemu_migration.c | 20 +- src/qemu/qemu_process.c |7 +- src/util/vircgroup.c | 1263 + src/util/vircgroup.h | 19 +- 15 files changed, 920 insertions(+), 1206 deletions(-) -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v2 RESEND 1/2] refactor virCgroupDetectMounts and virCgroupDetectPlacement
--- src/util/vircgroup.c | 14 +++--- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/src/util/vircgroup.c b/src/util/vircgroup.c index 48cba93..71d46c5 100644 --- a/src/util/vircgroup.c +++ b/src/util/vircgroup.c @@ -113,7 +113,7 @@ bool virCgroupMounted(virCgroupPtr cgroup, int controller) * Process /proc/mounts figuring out what controllers are * mounted and where */ -static int virCgroupDetectMounts(virCgroupPtr group) +static int virCgroupDetectMounts(struct virCgroupController (*controllers)[VIR_CGROUP_CONTROLLER_LAST]) { int i; FILE *mounts = NULL; @@ -148,8 +148,8 @@ static int virCgroupDetectMounts(virCgroupPtr group) * first entry only */ if (typelen == len STREQLEN(typestr, tmp, len) -!group-controllers[i].mountPoint -!(group-controllers[i].mountPoint = strdup(entry.mnt_dir))) +!(*controllers)[i].mountPoint +!((*controllers)[i].mountPoint = strdup(entry.mnt_dir))) goto no_memory; tmp = next; } @@ -171,7 +171,7 @@ no_memory: * sub-path the current process is assigned to. ie not * necessarily in the root */ -static int virCgroupDetectPlacement(virCgroupPtr group) +static int virCgroupDetectPlacement(struct virCgroupController (*cgroupControllers)[VIR_CGROUP_CONTROLLER_LAST]) { int i; FILE *mapping = NULL; @@ -212,7 +212,7 @@ static int virCgroupDetectPlacement(virCgroupPtr group) len = strlen(tmp); } if (typelen == len STREQLEN(typestr, tmp, len) -!(group-controllers[i].placement = strdup(STREQ(path, /) ? : path))) +!((*cgroupControllers)[i].placement = strdup(STREQ(path, /) ? : path))) goto no_memory; tmp = next; @@ -236,7 +236,7 @@ static int virCgroupDetect(virCgroupPtr group) int rc; int i; -rc = virCgroupDetectMounts(group); +rc = virCgroupDetectMounts(group-controllers); if (rc 0) { VIR_ERROR(_(Failed to detect mounts for %s), group-path); return rc; @@ -251,7 +251,7 @@ static int virCgroupDetect(virCgroupPtr group) return -ENXIO; -rc = virCgroupDetectPlacement(group); +rc = virCgroupDetectPlacement(group-controllers); if (rc == 0) { /* Check that for every mounted controller, we found our placement */ -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH] fix build erro when building with --without-libvirtd
--- src/driver.h | 4 --- src/libvirt.c | 70 +- src/libvirt_internal.h | 2 -- 3 files changed, 69 insertions(+), 7 deletions(-) diff --git a/src/driver.h b/src/driver.h index 02ddd83..dab7495 100644 --- a/src/driver.h +++ b/src/driver.h @@ -1512,7 +1512,6 @@ struct _virStorageDriver { virDrvStoragePoolIsPersistent poolIsPersistent; }; -# ifdef WITH_LIBVIRTD typedef int (*virDrvStateInitialize) (bool privileged, virStateInhibitCallback callback, @@ -1531,7 +1530,6 @@ struct _virStateDriver { virDrvStateReload reload; virDrvStateStopstop; }; -# endif typedef struct _virDeviceMonitor virDeviceMonitor; @@ -1768,9 +1766,7 @@ int virRegisterStorageDriver(virStorageDriverPtr); int virRegisterDeviceMonitor(virDeviceMonitorPtr); int virRegisterSecretDriver(virSecretDriverPtr); int virRegisterNWFilterDriver(virNWFilterDriverPtr); -# ifdef WITH_LIBVIRTD int virRegisterStateDriver(virStateDriverPtr); -# endif void virDriverModuleInitialize(const char *defmoddir); void *virDriverLoadModule(const char *name); diff --git a/src/libvirt.c b/src/libvirt.c index f81a3de..38e4f6e 100644 --- a/src/libvirt.c +++ b/src/libvirt.c @@ -885,8 +885,76 @@ int virStateStop(void) { return ret; } -#endif +#else /* WITH_LIBVIRTD */ + +/** + * virRegisterStateDriver: + * @driver: pointer to a driver block + * + * Register a virtualization driver + * + * Returns the driver priority or -1 in case of error. + */ +int +virRegisterStateDriver(virStateDriverPtr driver ATTRIBUTE_UNUSED) +{ +return 0; +} + +/** + * virStateInitialize: + * @privileged: set to true if running with root privilege, false otherwise + * @callback: callback to invoke to inhibit shutdown of the daemon + * @opaque: data to pass to @callback + * + * Initialize all virtualization drivers. + * + * Returns 0 if all succeed, -1 upon any failure. + */ +int virStateInitialize(bool privileged ATTRIBUTE_UNUSED, + virStateInhibitCallback callback ATTRIBUTE_UNUSED, + void *opaque ATTRIBUTE_UNUSED) +{ +return 0; +} + +/** + * virStateCleanup: + * + * Run each virtualization driver's cleanup method. + * + * Returns 0 if all succeed, -1 upon any failure. + */ +int virStateCleanup(void) +{ +return 0; +} + +/** + * virStateReload: + * + * Run each virtualization driver's reload method. + * + * Returns 0 if all succeed, -1 upon any failure. + */ +int virStateReload(void) +{ +return 0; +} + +/** + * virStateStop: + * + * Run each virtualization driver's stop method. + * + * Returns 0 if successful, -1 on failure + */ +int virStateStop(void) +{ +return 0; +} +#endif /* WITH_LIBVIRTD */ /** diff --git a/src/libvirt_internal.h b/src/libvirt_internal.h index 595d2db..b82f6b9 100644 --- a/src/libvirt_internal.h +++ b/src/libvirt_internal.h @@ -27,7 +27,6 @@ # include internal.h -# ifdef WITH_LIBVIRTD typedef void (*virStateInhibitCallback)(bool inhibit, void *opaque); @@ -37,7 +36,6 @@ int virStateInitialize(bool privileged, int virStateCleanup(void); int virStateReload(void); int virStateStop(void); -# endif /* Feature detection. This is a libvirt-private interface for determining * what features are supported by the driver. -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH] fix build erro when building with --without-libvirtd
On Mon, Feb 04, 2013 at 11:43:59AM +, Daniel P. Berrange wrote: On Mon, Feb 04, 2013 at 04:23:30PM +0800, Hu Tao wrote: --- src/driver.h | 4 --- src/libvirt.c | 70 +- src/libvirt_internal.h | 2 -- 3 files changed, 69 insertions(+), 7 deletions(-) diff --git a/src/driver.h b/src/driver.h index 02ddd83..dab7495 100644 --- a/src/driver.h +++ b/src/driver.h @@ -1512,7 +1512,6 @@ struct _virStorageDriver { virDrvStoragePoolIsPersistent poolIsPersistent; }; -# ifdef WITH_LIBVIRTD typedef int (*virDrvStateInitialize) (bool privileged, virStateInhibitCallback callback, @@ -1531,7 +1530,6 @@ struct _virStateDriver { virDrvStateReload reload; virDrvStateStopstop; }; -# endif typedef struct _virDeviceMonitor virDeviceMonitor; @@ -1768,9 +1766,7 @@ int virRegisterStorageDriver(virStorageDriverPtr); int virRegisterDeviceMonitor(virDeviceMonitorPtr); int virRegisterSecretDriver(virSecretDriverPtr); int virRegisterNWFilterDriver(virNWFilterDriverPtr); -# ifdef WITH_LIBVIRTD int virRegisterStateDriver(virStateDriverPtr); -# endif void virDriverModuleInitialize(const char *defmoddir); void *virDriverLoadModule(const char *name); diff --git a/src/libvirt.c b/src/libvirt.c index f81a3de..38e4f6e 100644 --- a/src/libvirt.c +++ b/src/libvirt.c @@ -885,8 +885,76 @@ int virStateStop(void) { return ret; } -#endif +#else /* WITH_LIBVIRTD */ + +/** + * virRegisterStateDriver: + * @driver: pointer to a driver block + * + * Register a virtualization driver + * + * Returns the driver priority or -1 in case of error. + */ +int +virRegisterStateDriver(virStateDriverPtr driver ATTRIBUTE_UNUSED) +{ +return 0; +} + +/** + * virStateInitialize: + * @privileged: set to true if running with root privilege, false otherwise + * @callback: callback to invoke to inhibit shutdown of the daemon + * @opaque: data to pass to @callback + * + * Initialize all virtualization drivers. + * + * Returns 0 if all succeed, -1 upon any failure. + */ +int virStateInitialize(bool privileged ATTRIBUTE_UNUSED, + virStateInhibitCallback callback ATTRIBUTE_UNUSED, + void *opaque ATTRIBUTE_UNUSED) +{ +return 0; +} + +/** + * virStateCleanup: + * + * Run each virtualization driver's cleanup method. + * + * Returns 0 if all succeed, -1 upon any failure. + */ +int virStateCleanup(void) +{ +return 0; +} + +/** + * virStateReload: + * + * Run each virtualization driver's reload method. + * + * Returns 0 if all succeed, -1 upon any failure. + */ +int virStateReload(void) +{ +return 0; +} + +/** + * virStateStop: + * + * Run each virtualization driver's stop method. + * + * Returns 0 if successful, -1 on failure + */ +int virStateStop(void) +{ +return 0; +} Don't add all these stubs - just remove the WITH_LIBVIRTD conditional from the original impls. There is nothing that prevents us building them, even if libvirtd is disabled Okey, I see. I'll send v2. -- Regards, Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH] fix build erro when building with --without-libvirtd
On Mon, Feb 04, 2013 at 12:25:48PM +0100, Martin Kletzander wrote: On 02/04/2013 09:23 AM, Hu Tao wrote: --- src/driver.h | 4 --- src/libvirt.c | 70 +- src/libvirt_internal.h | 2 -- 3 files changed, 69 insertions(+), 7 deletions(-) diff --git a/src/driver.h b/src/driver.h index 02ddd83..dab7495 100644 --- a/src/driver.h +++ b/src/driver.h @@ -1512,7 +1512,6 @@ struct _virStorageDriver { virDrvStoragePoolIsPersistent poolIsPersistent; }; -# ifdef WITH_LIBVIRTD typedef int (*virDrvStateInitialize) (bool privileged, virStateInhibitCallback callback, @@ -1531,7 +1530,6 @@ struct _virStateDriver { virDrvStateReload reload; virDrvStateStopstop; }; -# endif Even though this is a solution and it makes the calls to virState* never fail during compilation, I see the other approach being used as well in some files (xen _driver.c for example): #ifdef WITH_LIBVIRTD if (virRegisterStateDriver(state_driver) == -1) return -1; #endif I like this a bit more, but that's just a subjective opinion. However, if you go with your approach, I'd rather see it cleaning up those paths as well. See. Thanks for review. -- Regards, Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH] libvirtd: Don't check WITH_LIBVIRTD in C source files
Don't check WITH_LIBVIRTD in C source files because we will build the sources even without libvirtd. --- src/driver.h | 4 src/libvirt.c | 7 --- src/libvirt_internal.h | 2 -- src/remote/remote_driver.c | 6 -- src/xen/xen_driver.c | 6 +- 5 files changed, 1 insertion(+), 24 deletions(-) diff --git a/src/driver.h b/src/driver.h index 02ddd83..dab7495 100644 --- a/src/driver.h +++ b/src/driver.h @@ -1512,7 +1512,6 @@ struct _virStorageDriver { virDrvStoragePoolIsPersistent poolIsPersistent; }; -# ifdef WITH_LIBVIRTD typedef int (*virDrvStateInitialize) (bool privileged, virStateInhibitCallback callback, @@ -1531,7 +1530,6 @@ struct _virStateDriver { virDrvStateReload reload; virDrvStateStopstop; }; -# endif typedef struct _virDeviceMonitor virDeviceMonitor; @@ -1768,9 +1766,7 @@ int virRegisterStorageDriver(virStorageDriverPtr); int virRegisterDeviceMonitor(virDeviceMonitorPtr); int virRegisterSecretDriver(virSecretDriverPtr); int virRegisterNWFilterDriver(virNWFilterDriverPtr); -# ifdef WITH_LIBVIRTD int virRegisterStateDriver(virStateDriverPtr); -# endif void virDriverModuleInitialize(const char *defmoddir); void *virDriverLoadModule(const char *name); diff --git a/src/libvirt.c b/src/libvirt.c index f81a3de..e2a7b5d 100644 --- a/src/libvirt.c +++ b/src/libvirt.c @@ -118,10 +118,8 @@ static virSecretDriverPtr virSecretDriverTab[MAX_DRIVERS]; static int virSecretDriverTabCount = 0; static virNWFilterDriverPtr virNWFilterDriverTab[MAX_DRIVERS]; static int virNWFilterDriverTabCount = 0; -#ifdef WITH_LIBVIRTD static virStateDriverPtr virStateDriverTab[MAX_DRIVERS]; static int virStateDriverTabCount = 0; -#endif #if defined(POLKIT_AUTH) @@ -771,7 +769,6 @@ virRegisterDriver(virDriverPtr driver) return virDriverTabCount++; } -#ifdef WITH_LIBVIRTD /** * virRegisterStateDriver: * @driver: pointer to a driver block @@ -885,10 +882,6 @@ int virStateStop(void) { return ret; } -#endif - - - /** * virGetVersion: * @libVer: return value for the library version (OUT) diff --git a/src/libvirt_internal.h b/src/libvirt_internal.h index 595d2db..b82f6b9 100644 --- a/src/libvirt_internal.h +++ b/src/libvirt_internal.h @@ -27,7 +27,6 @@ # include internal.h -# ifdef WITH_LIBVIRTD typedef void (*virStateInhibitCallback)(bool inhibit, void *opaque); @@ -37,7 +36,6 @@ int virStateInitialize(bool privileged, int virStateCleanup(void); int virStateReload(void); int virStateStop(void); -# endif /* Feature detection. This is a libvirt-private interface for determining * what features are supported by the driver. diff --git a/src/remote/remote_driver.c b/src/remote/remote_driver.c index 341321b..354a216 100644 --- a/src/remote/remote_driver.c +++ b/src/remote/remote_driver.c @@ -156,7 +156,6 @@ static void remoteDomainEventQueue(struct private_data *priv, virDomainEventPtr /* Helper functions for remoteOpen. */ static char *get_transport_from_scheme(char *scheme); -#ifdef WITH_LIBVIRTD static int remoteStartup(bool privileged ATTRIBUTE_UNUSED, virStateInhibitCallback callback ATTRIBUTE_UNUSED, @@ -168,7 +167,6 @@ remoteStartup(bool privileged ATTRIBUTE_UNUSED, inside_daemon = true; return 0; } -#endif #ifndef WIN32 /** @@ -6382,12 +6380,10 @@ static virNWFilterDriver nwfilter_driver = { }; -#ifdef WITH_LIBVIRTD static virStateDriver state_driver = { .name = Remote, .initialize = remoteStartup, }; -#endif /** remoteRegister: @@ -6408,9 +6404,7 @@ remoteRegister(void) if (virRegisterDeviceMonitor(dev_monitor) == -1) return -1; if (virRegisterSecretDriver(secret_driver) == -1) return -1; if (virRegisterNWFilterDriver(nwfilter_driver) == -1) return -1; -#ifdef WITH_LIBVIRTD if (virRegisterStateDriver(state_driver) == -1) return -1; -#endif return 0; } diff --git a/src/xen/xen_driver.c b/src/xen/xen_driver.c index 2795ebc..d65f4a6 100644 --- a/src/xen/xen_driver.c +++ b/src/xen/xen_driver.c @@ -91,7 +91,7 @@ static struct xenUnifiedDriver const * const drivers[XEN_UNIFIED_NR_DRIVERS] = { #endif }; -#if defined WITH_LIBVIRTD || defined __sun +#ifdef __sun static bool inside_daemon = false; #endif @@ -200,7 +200,6 @@ done: return res; } -#ifdef WITH_LIBVIRTD static int xenInitialize(bool privileged ATTRIBUTE_UNUSED, @@ -216,7 +215,6 @@ static virStateDriver state_driver = { .initialize = xenInitialize, }; -#endif /*- Dispatch functions. -*/ @@ -2398,9 +2396,7 @@ static virDriver xenUnifiedDriver = { int xenRegister(void) { -#ifdef WITH_LIBVIRTD if (virRegisterStateDriver(state_driver) == -1) return -1; -#endif return virRegisterDriver(xenUnifiedDriver); } -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com
Re: [libvirt] [PATCH] libvirtd: Don't check WITH_LIBVIRTD in C source files
On Mon, Feb 04, 2013 at 10:08:42PM -0600, Doug Goldstein wrote: On Mon, Feb 4, 2013 at 8:20 PM, Hu Tao hu...@cn.fujitsu.com wrote: Don't check WITH_LIBVIRTD in C source files because we will build the sources even without libvirtd. --- src/driver.h | 4 src/libvirt.c | 7 --- src/libvirt_internal.h | 2 -- src/remote/remote_driver.c | 6 -- src/xen/xen_driver.c | 6 +- 5 files changed, 1 insertion(+), 24 deletions(-) diff --git a/src/driver.h b/src/driver.h index 02ddd83..dab7495 100644 --- a/src/driver.h +++ b/src/driver.h @@ -1512,7 +1512,6 @@ struct _virStorageDriver { virDrvStoragePoolIsPersistent poolIsPersistent; }; -# ifdef WITH_LIBVIRTD typedef int (*virDrvStateInitialize) (bool privileged, virStateInhibitCallback callback, @@ -1531,7 +1530,6 @@ struct _virStateDriver { virDrvStateReload reload; virDrvStateStopstop; }; -# endif typedef struct _virDeviceMonitor virDeviceMonitor; @@ -1768,9 +1766,7 @@ int virRegisterStorageDriver(virStorageDriverPtr); int virRegisterDeviceMonitor(virDeviceMonitorPtr); int virRegisterSecretDriver(virSecretDriverPtr); int virRegisterNWFilterDriver(virNWFilterDriverPtr); -# ifdef WITH_LIBVIRTD int virRegisterStateDriver(virStateDriverPtr); -# endif void virDriverModuleInitialize(const char *defmoddir); void *virDriverLoadModule(const char *name); diff --git a/src/libvirt.c b/src/libvirt.c index f81a3de..e2a7b5d 100644 --- a/src/libvirt.c +++ b/src/libvirt.c @@ -118,10 +118,8 @@ static virSecretDriverPtr virSecretDriverTab[MAX_DRIVERS]; static int virSecretDriverTabCount = 0; static virNWFilterDriverPtr virNWFilterDriverTab[MAX_DRIVERS]; static int virNWFilterDriverTabCount = 0; -#ifdef WITH_LIBVIRTD static virStateDriverPtr virStateDriverTab[MAX_DRIVERS]; static int virStateDriverTabCount = 0; -#endif #if defined(POLKIT_AUTH) @@ -771,7 +769,6 @@ virRegisterDriver(virDriverPtr driver) return virDriverTabCount++; } -#ifdef WITH_LIBVIRTD /** * virRegisterStateDriver: * @driver: pointer to a driver block @@ -885,10 +882,6 @@ int virStateStop(void) { return ret; } -#endif - - - /** * virGetVersion: * @libVer: return value for the library version (OUT) diff --git a/src/libvirt_internal.h b/src/libvirt_internal.h index 595d2db..b82f6b9 100644 --- a/src/libvirt_internal.h +++ b/src/libvirt_internal.h @@ -27,7 +27,6 @@ # include internal.h -# ifdef WITH_LIBVIRTD typedef void (*virStateInhibitCallback)(bool inhibit, void *opaque); @@ -37,7 +36,6 @@ int virStateInitialize(bool privileged, int virStateCleanup(void); int virStateReload(void); int virStateStop(void); -# endif /* Feature detection. This is a libvirt-private interface for determining * what features are supported by the driver. diff --git a/src/remote/remote_driver.c b/src/remote/remote_driver.c index 341321b..354a216 100644 --- a/src/remote/remote_driver.c +++ b/src/remote/remote_driver.c @@ -156,7 +156,6 @@ static void remoteDomainEventQueue(struct private_data *priv, virDomainEventPtr /* Helper functions for remoteOpen. */ static char *get_transport_from_scheme(char *scheme); -#ifdef WITH_LIBVIRTD static int remoteStartup(bool privileged ATTRIBUTE_UNUSED, virStateInhibitCallback callback ATTRIBUTE_UNUSED, @@ -168,7 +167,6 @@ remoteStartup(bool privileged ATTRIBUTE_UNUSED, inside_daemon = true; return 0; } -#endif #ifndef WIN32 /** @@ -6382,12 +6380,10 @@ static virNWFilterDriver nwfilter_driver = { }; -#ifdef WITH_LIBVIRTD static virStateDriver state_driver = { .name = Remote, .initialize = remoteStartup, }; -#endif /** remoteRegister: @@ -6408,9 +6404,7 @@ remoteRegister(void) if (virRegisterDeviceMonitor(dev_monitor) == -1) return -1; if (virRegisterSecretDriver(secret_driver) == -1) return -1; if (virRegisterNWFilterDriver(nwfilter_driver) == -1) return -1; -#ifdef WITH_LIBVIRTD if (virRegisterStateDriver(state_driver) == -1) return -1; -#endif return 0; } diff --git a/src/xen/xen_driver.c b/src/xen/xen_driver.c index 2795ebc..d65f4a6 100644 --- a/src/xen/xen_driver.c +++ b/src/xen/xen_driver.c @@ -91,7 +91,7 @@ static struct xenUnifiedDriver const * const drivers[XEN_UNIFIED_NR_DRIVERS] = { #endif }; -#if defined WITH_LIBVIRTD || defined __sun +#ifdef __sun static bool inside_daemon = false; #endif @@ -200,7 +200,6 @@ done: return res; } -#ifdef WITH_LIBVIRTD static int xenInitialize(bool privileged ATTRIBUTE_UNUSED, @@ -216,7 +215,6 @@ static virStateDriver state_driver
Re: [libvirt] [PATCH] libvirtd: Don't check WITH_LIBVIRTD in C source files
Please add one more line to commit msg: On Tue, Feb 05, 2013 at 10:20:37AM +0800, Hu Tao wrote: Don't check WITH_LIBVIRTD in C source files because we will build the sources even without libvirtd. This patch also fix the build failure when buliding with --without-libvirtd. --- src/driver.h | 4 src/libvirt.c | 7 --- src/libvirt_internal.h | 2 -- src/remote/remote_driver.c | 6 -- src/xen/xen_driver.c | 6 +- 5 files changed, 1 insertion(+), 24 deletions(-) diff --git a/src/driver.h b/src/driver.h index 02ddd83..dab7495 100644 --- a/src/driver.h +++ b/src/driver.h @@ -1512,7 +1512,6 @@ struct _virStorageDriver { virDrvStoragePoolIsPersistent poolIsPersistent; }; -# ifdef WITH_LIBVIRTD typedef int (*virDrvStateInitialize) (bool privileged, virStateInhibitCallback callback, @@ -1531,7 +1530,6 @@ struct _virStateDriver { virDrvStateReload reload; virDrvStateStopstop; }; -# endif typedef struct _virDeviceMonitor virDeviceMonitor; @@ -1768,9 +1766,7 @@ int virRegisterStorageDriver(virStorageDriverPtr); int virRegisterDeviceMonitor(virDeviceMonitorPtr); int virRegisterSecretDriver(virSecretDriverPtr); int virRegisterNWFilterDriver(virNWFilterDriverPtr); -# ifdef WITH_LIBVIRTD int virRegisterStateDriver(virStateDriverPtr); -# endif void virDriverModuleInitialize(const char *defmoddir); void *virDriverLoadModule(const char *name); diff --git a/src/libvirt.c b/src/libvirt.c index f81a3de..e2a7b5d 100644 --- a/src/libvirt.c +++ b/src/libvirt.c @@ -118,10 +118,8 @@ static virSecretDriverPtr virSecretDriverTab[MAX_DRIVERS]; static int virSecretDriverTabCount = 0; static virNWFilterDriverPtr virNWFilterDriverTab[MAX_DRIVERS]; static int virNWFilterDriverTabCount = 0; -#ifdef WITH_LIBVIRTD static virStateDriverPtr virStateDriverTab[MAX_DRIVERS]; static int virStateDriverTabCount = 0; -#endif #if defined(POLKIT_AUTH) @@ -771,7 +769,6 @@ virRegisterDriver(virDriverPtr driver) return virDriverTabCount++; } -#ifdef WITH_LIBVIRTD /** * virRegisterStateDriver: * @driver: pointer to a driver block @@ -885,10 +882,6 @@ int virStateStop(void) { return ret; } -#endif - - - /** * virGetVersion: * @libVer: return value for the library version (OUT) diff --git a/src/libvirt_internal.h b/src/libvirt_internal.h index 595d2db..b82f6b9 100644 --- a/src/libvirt_internal.h +++ b/src/libvirt_internal.h @@ -27,7 +27,6 @@ # include internal.h -# ifdef WITH_LIBVIRTD typedef void (*virStateInhibitCallback)(bool inhibit, void *opaque); @@ -37,7 +36,6 @@ int virStateInitialize(bool privileged, int virStateCleanup(void); int virStateReload(void); int virStateStop(void); -# endif /* Feature detection. This is a libvirt-private interface for determining * what features are supported by the driver. diff --git a/src/remote/remote_driver.c b/src/remote/remote_driver.c index 341321b..354a216 100644 --- a/src/remote/remote_driver.c +++ b/src/remote/remote_driver.c @@ -156,7 +156,6 @@ static void remoteDomainEventQueue(struct private_data *priv, virDomainEventPtr /* Helper functions for remoteOpen. */ static char *get_transport_from_scheme(char *scheme); -#ifdef WITH_LIBVIRTD static int remoteStartup(bool privileged ATTRIBUTE_UNUSED, virStateInhibitCallback callback ATTRIBUTE_UNUSED, @@ -168,7 +167,6 @@ remoteStartup(bool privileged ATTRIBUTE_UNUSED, inside_daemon = true; return 0; } -#endif #ifndef WIN32 /** @@ -6382,12 +6380,10 @@ static virNWFilterDriver nwfilter_driver = { }; -#ifdef WITH_LIBVIRTD static virStateDriver state_driver = { .name = Remote, .initialize = remoteStartup, }; -#endif /** remoteRegister: @@ -6408,9 +6404,7 @@ remoteRegister(void) if (virRegisterDeviceMonitor(dev_monitor) == -1) return -1; if (virRegisterSecretDriver(secret_driver) == -1) return -1; if (virRegisterNWFilterDriver(nwfilter_driver) == -1) return -1; -#ifdef WITH_LIBVIRTD if (virRegisterStateDriver(state_driver) == -1) return -1; -#endif return 0; } diff --git a/src/xen/xen_driver.c b/src/xen/xen_driver.c index 2795ebc..d65f4a6 100644 --- a/src/xen/xen_driver.c +++ b/src/xen/xen_driver.c @@ -91,7 +91,7 @@ static struct xenUnifiedDriver const * const drivers[XEN_UNIFIED_NR_DRIVERS] = { #endif }; -#if defined WITH_LIBVIRTD || defined __sun +#ifdef __sun static bool inside_daemon = false; #endif @@ -200,7 +200,6 @@ done: return res; } -#ifdef WITH_LIBVIRTD static int xenInitialize(bool privileged ATTRIBUTE_UNUSED, @@ -216,7 +215,6 @@ static virStateDriver state_driver = { .initialize = xenInitialize, }; -#endif /*- Dispatch
Re: [libvirt] [PATCH] build: Add libcurl dependency to libvirt_driver.la
On Fri, Feb 01, 2013 at 01:45:19PM +0100, Jiri Denemark wrote: libvirt.c calls curl_global_init() if WITH_CURL is defined and thus it should be linked with libcurl. This fixes link failure in case neither xenapi nor esx driver is enabled (they are the only users of libcurl). In the case we link with libcurl just because user wants it. How about not exposing --with-curl but define WITH_CURL when needs to(xenapi or esx driver is enabled, or both)? -- Regards, Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v2 0/5] cgroup refactor
This series refactors cgroup code to: - provide lazy creation of cgroup directories, despite of what level they are. - remove cgroup directories if no one is using the corresponding virCgroup. This series is splitted in a manner for easier review. Patch 2 is the main implementation. Patch 3, 4, 5 should have been squashed into one in order to build, but harder to review. Hu Tao (5): refactor virCgroupDetectMounts and virCgroupDetectPlacement cgroup: refactor virCgroup cgroup: replace old cgroup qemu: replace old cgroup lxc: replace old cgroup src/conf/domain_conf.h|5 + src/libvirt_private.syms |7 +- src/lxc/lxc_cgroup.c | 40 +- src/lxc/lxc_cgroup.h |2 +- src/lxc/lxc_controller.c | 31 +- src/lxc/lxc_driver.c | 177 +++ src/lxc/lxc_process.c | 19 +- src/qemu/qemu_cgroup.c| 162 +++--- src/qemu/qemu_cgroup.h|3 +- src/qemu/qemu_driver.c| 351 + src/qemu/qemu_hotplug.c | 21 +- src/qemu/qemu_migration.c | 20 +- src/qemu/qemu_process.c |7 +- src/util/vircgroup.c | 1263 + src/util/vircgroup.h | 19 +- 15 files changed, 921 insertions(+), 1206 deletions(-) -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v2 5/5] lxc: replace old cgroup
--- src/lxc/lxc_cgroup.c | 40 +++ src/lxc/lxc_cgroup.h | 2 +- src/lxc/lxc_controller.c | 31 - src/lxc/lxc_driver.c | 177 +-- src/lxc/lxc_process.c| 19 +++-- 5 files changed, 111 insertions(+), 158 deletions(-) diff --git a/src/lxc/lxc_cgroup.c b/src/lxc/lxc_cgroup.c index 1984c5f..d1a1f16 100644 --- a/src/lxc/lxc_cgroup.c +++ b/src/lxc/lxc_cgroup.c @@ -242,7 +242,7 @@ int virLXCCgroupGetMeminfo(virLXCMeminfoPtr meminfo) int ret; virCgroupPtr cgroup; -ret = virCgroupGetAppRoot(cgroup); +ret = virCgroupGetAppRoot(cgroup, true); if (ret 0) { virReportSystemError(-ret, %s, _(Unable to get cgroup for container)); @@ -469,53 +469,29 @@ cleanup: } -int virLXCCgroupSetup(virDomainDefPtr def) +int virLXCCgroupSetup(virCgroupPtr cgroup, virDomainDefPtr def) { -virCgroupPtr driver = NULL; -virCgroupPtr cgroup = NULL; -int ret = -1; int rc; -rc = virCgroupForDriver(lxc, driver, 1, 0); -if (rc != 0) { -virReportSystemError(-rc, %s, - _(Unable to get cgroup for driver)); -goto cleanup; -} - -rc = virCgroupForDomain(driver, def-name, cgroup, 1); -if (rc != 0) { -virReportSystemError(-rc, - _(Unable to create cgroup for domain %s), - def-name); -goto cleanup; -} - if (virLXCCgroupSetupCpuTune(def, cgroup) 0) -goto cleanup; +return -1; if (virLXCCgroupSetupBlkioTune(def, cgroup) 0) -goto cleanup; +return -1; if (virLXCCgroupSetupMemTune(def, cgroup) 0) -goto cleanup; +return -1; if (virLXCCgroupSetupDeviceACL(def, cgroup) 0) -goto cleanup; +return -1; rc = virCgroupAddTask(cgroup, getpid()); if (rc != 0) { virReportSystemError(-rc, _(Unable to add task %d to cgroup for domain %s), getpid(), def-name); -goto cleanup; +return -1; } -ret = 0; - -cleanup: -virCgroupFree(cgroup); -virCgroupFree(driver); - -return ret; +return 0; } diff --git a/src/lxc/lxc_cgroup.h b/src/lxc/lxc_cgroup.h index 97b94e5..cd02b46 100644 --- a/src/lxc/lxc_cgroup.h +++ b/src/lxc/lxc_cgroup.h @@ -26,7 +26,7 @@ # include lxc_fuse.h # include virusb.h -int virLXCCgroupSetup(virDomainDefPtr def); +int virLXCCgroupSetup(virCgroupPtr cgroup, virDomainDefPtr def); int virLXCCgroupGetMeminfo(virLXCMeminfoPtr meminfo); int diff --git a/src/lxc/lxc_controller.c b/src/lxc/lxc_controller.c index 2673f72..4a7a63b 100644 --- a/src/lxc/lxc_controller.c +++ b/src/lxc/lxc_controller.c @@ -130,6 +130,8 @@ struct _virLXCController { int timerShutdown; virLXCFusePtr fuse; + +virCgroupPtr cgroup; }; #include lxc_controller_dispatch.h @@ -272,6 +274,8 @@ static void virLXCControllerFree(virLXCControllerPtr ctrl) VIR_FREE(ctrl-devptmx); +virCgroupFree(ctrl-cgroup); + virDomainDefFree(ctrl-def); VIR_FREE(ctrl-name); @@ -548,6 +552,31 @@ static int virLXCControllerSetupCpuAffinity(virLXCControllerPtr ctrl) return 0; } +static int virLXCControllerSetupCgroup(virLXCControllerPtr ctrl) +{ +virCgroupPtr appCgroup = NULL; +int rc; + +rc = virCgroupGetAppRoot(appCgroup, true); +if (rc != 0) { +virReportSystemError(-rc, %s, + _(Unable to get cgroup for libvirt)); +goto cleanup; +} + +rc = virCgroupNew(lxc, appCgroup, ctrl-cgroup); +if (rc != 0) { +virReportSystemError(-rc, %s, + _(Unable to get cgroup for driver)); +goto cleanup; +} + +rc = virLXCCgroupSetup(ctrl-cgroup, ctrl-def); + +cleanup: +virCgroupFree(appCgroup); +return rc; +} /** * virLXCControllerSetupResourceLimits @@ -567,7 +596,7 @@ static int virLXCControllerSetupResourceLimits(virLXCControllerPtr ctrl) if (virLXCControllerSetupNUMAPolicy(ctrl) 0) return -1; -return virLXCCgroupSetup(ctrl-def); +return virLXCControllerSetupCgroup(ctrl); } diff --git a/src/lxc/lxc_driver.c b/src/lxc/lxc_driver.c index 1fe8039..7afe969 100644 --- a/src/lxc/lxc_driver.c +++ b/src/lxc/lxc_driver.c @@ -527,7 +527,6 @@ static int lxcDomainGetInfo(virDomainPtr dom, { virLXCDriverPtr driver = dom-conn-privateData; virDomainObjPtr vm; -virCgroupPtr cgroup = NULL; int ret = -1, rc; lxcDriverLock(driver); @@ -543,22 +542,16 @@ static int lxcDomainGetInfo(virDomainPtr dom, info-state = virDomainObjGetState(vm, NULL); -if (!virDomainObjIsActive(vm) || driver-cgroup == NULL) { +if (!virDomainObjIsActive(vm) || vm-cgroup == NULL) { info-cpuTime = 0; info-memory = vm-def-mem.cur_balloon; } else { -if
[libvirt] [PATCH v2 3/5] cgroup: replace old cgroup
--- src/libvirt_private.syms | 9 +- src/util/vircgroup.c | 812 +++ src/util/vircgroup.h | 25 +- 3 files changed, 112 insertions(+), 734 deletions(-) diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index f5138af..78e387d 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -73,8 +73,6 @@ virCapabilitiesSetMacPrefix; # cgroup.h -virCgroup2Free; -virCgroup2New; virCgroupAddTask; virCgroupAddTaskController; virCgroupAllowDevice; @@ -86,10 +84,6 @@ virCgroupDenyAllDevices; virCgroupDenyDevice; virCgroupDenyDeviceMajor; virCgroupDenyDevicePath; -virCgroupForDomain; -virCgroupForDriver; -virCgroupForEmulator; -virCgroupForVcpu; virCgroupFree; virCgroupGetAppRoot; virCgroupGetBlkioWeight; @@ -110,10 +104,11 @@ virCgroupGetMemSwapUsage; virCgroupKill; virCgroupKillPainfully; virCgroupKillRecursive; +virCgroupMakePath; virCgroupMounted; virCgroupMoveTask; +virCgroupNew; virCgroupPathOfController; -virCgroupRemove; virCgroupSetBlkioDeviceWeight; virCgroupSetBlkioWeight; virCgroupSetCpuCfsPeriod; diff --git a/src/util/vircgroup.c b/src/util/vircgroup.c index dbc9688..90ff97c 100644 --- a/src/util/vircgroup.c +++ b/src/util/vircgroup.c @@ -80,7 +80,7 @@ struct _virCgroupItem { struct virCgroupController controllers[VIR_CGROUP_CONTROLLER_LAST]; }; -struct virCgroup2 { +struct virCgroup { virCgroupItemPtr items[VIR_CGROUP_CONTROLLER_LAST]; }; @@ -145,12 +145,6 @@ static int virCgroupControllersInit(struct virCgroupController (*controllers)[VI return rc; } -struct virCgroup { -char *path; - -struct virCgroupController controllers[VIR_CGROUP_CONTROLLER_LAST]; -}; - typedef enum { VIR_CGROUP_NONE = 0, /* create subdir under each cgroup if possible. */ VIR_CGROUP_MEM_HIERACHY = 1 0, /* call virCgroupSetMemoryUseHierarchy @@ -447,9 +441,21 @@ static int virCgroupItemKeyPath(virCgroupItemPtr cgroupItem, return ret; } -int virCgroup2New(const char *name, virCgroup2Ptr parent, virCgroup2Ptr *cgroup) +int virCgroupMakePath(virCgroupPtr cgroup) { -virCgroup2Ptr newCgroup = NULL; +int i; + +for (i = 0; i VIR_CGROUP_CONTROLLER_LAST; i++) { +if (virCgroupItemPath(cgroup-items[i], true, NULL) != 0) +return -1; +} + +return 0; +} + +int virCgroupNew(const char *name, virCgroupPtr parent, virCgroupPtr *cgroup) +{ +virCgroupPtr newCgroup = NULL; virCgroupItemPtr *parentCgroupItems; int ret = -1; int i = 0; @@ -502,40 +508,24 @@ error: return ret; } -void virCgroup2Free(virCgroup2Ptr *cgroup) -{ -int i; - -if (!cgroup || !*cgroup) -return; - -for (i = 0; i VIR_CGROUP_CONTROLLER_LAST; i++) { -virCgroupItemFree((*cgroup)-items[i]); -} - -VIR_FREE(*cgroup); -*cgroup = NULL; -} - /** * virCgroupFree: * * @group: The group structure to free */ -void virCgroupFree(virCgroupPtr *group) +void virCgroupFree(virCgroupPtr *cgroup) { int i; -if (*group == NULL) +if (!cgroup || !*cgroup) return; -for (i = 0 ; i VIR_CGROUP_CONTROLLER_LAST ; i++) { -VIR_FREE((*group)-controllers[i].mountPoint); -VIR_FREE((*group)-controllers[i].placement); +for (i = 0; i VIR_CGROUP_CONTROLLER_LAST; i++) { +virCgroupItemFree((*cgroup)-items[i]); } -VIR_FREE((*group)-path); -VIR_FREE(*group); +VIR_FREE(*cgroup); +*cgroup = NULL; } /** @@ -546,9 +536,13 @@ void virCgroupFree(virCgroupPtr *group) * * Returns true if a cgroup is subsystem is mounted. */ -bool virCgroupMounted(virCgroupPtr cgroup, int controller) +bool virCgroupMounted(virCgroupPtr cgroup ATTRIBUTE_UNUSED, + int controller) { -return cgroup-controllers[controller].mountPoint != NULL; +if (rootCgroupItems[controller] +rootCgroupItems[controller]-controllers[controller].mountPoint) +return true; +return false; } #if defined HAVE_MNTENT_H defined HAVE_GETMNTENT_R @@ -675,58 +669,8 @@ no_memory: } - -static int virCgroupDetect(virCgroupPtr group) -{ -int any = 0; -int rc; -int i; - -rc = virCgroupDetectMounts(group-controllers); -if (rc 0) { -VIR_ERROR(_(Failed to detect mounts for %s), group-path); -return rc; -} - -/* Check that at least 1 controller is available */ -for (i = 0 ; i VIR_CGROUP_CONTROLLER_LAST ; i++) { -if (group-controllers[i].mountPoint != NULL) -any = 1; -} -if (!any) -return -ENXIO; - - -rc = virCgroupDetectPlacement(group-controllers); - -if (rc == 0) { -/* Check that for every mounted controller, we found our placement */ -for (i = 0 ; i VIR_CGROUP_CONTROLLER_LAST ; i++) { -if (!group-controllers[i].mountPoint) -continue; - -if (!group-controllers[i].placement) { -VIR_ERROR(_(Could not
[libvirt] [PATCH v2 1/5] refactor virCgroupDetectMounts and virCgroupDetectPlacement
This patch prepares for the next one. --- src/util/vircgroup.c | 14 +++--- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/src/util/vircgroup.c b/src/util/vircgroup.c index 48cba93..71d46c5 100644 --- a/src/util/vircgroup.c +++ b/src/util/vircgroup.c @@ -113,7 +113,7 @@ bool virCgroupMounted(virCgroupPtr cgroup, int controller) * Process /proc/mounts figuring out what controllers are * mounted and where */ -static int virCgroupDetectMounts(virCgroupPtr group) +static int virCgroupDetectMounts(struct virCgroupController (*controllers)[VIR_CGROUP_CONTROLLER_LAST]) { int i; FILE *mounts = NULL; @@ -148,8 +148,8 @@ static int virCgroupDetectMounts(virCgroupPtr group) * first entry only */ if (typelen == len STREQLEN(typestr, tmp, len) -!group-controllers[i].mountPoint -!(group-controllers[i].mountPoint = strdup(entry.mnt_dir))) +!(*controllers)[i].mountPoint +!((*controllers)[i].mountPoint = strdup(entry.mnt_dir))) goto no_memory; tmp = next; } @@ -171,7 +171,7 @@ no_memory: * sub-path the current process is assigned to. ie not * necessarily in the root */ -static int virCgroupDetectPlacement(virCgroupPtr group) +static int virCgroupDetectPlacement(struct virCgroupController (*cgroupControllers)[VIR_CGROUP_CONTROLLER_LAST]) { int i; FILE *mapping = NULL; @@ -212,7 +212,7 @@ static int virCgroupDetectPlacement(virCgroupPtr group) len = strlen(tmp); } if (typelen == len STREQLEN(typestr, tmp, len) -!(group-controllers[i].placement = strdup(STREQ(path, /) ? : path))) +!((*cgroupControllers)[i].placement = strdup(STREQ(path, /) ? : path))) goto no_memory; tmp = next; @@ -236,7 +236,7 @@ static int virCgroupDetect(virCgroupPtr group) int rc; int i; -rc = virCgroupDetectMounts(group); +rc = virCgroupDetectMounts(group-controllers); if (rc 0) { VIR_ERROR(_(Failed to detect mounts for %s), group-path); return rc; @@ -251,7 +251,7 @@ static int virCgroupDetect(virCgroupPtr group) return -ENXIO; -rc = virCgroupDetectPlacement(group); +rc = virCgroupDetectPlacement(group-controllers); if (rc == 0) { /* Check that for every mounted controller, we found our placement */ -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v2 2/5] cgroup: refactor virCgroup
This patch adds a new structure, virCgroupItem, to represent a cgroup directory(named cgroup item). cgroup directory is created when needed and removed if no one is using it. --- src/libvirt_private.syms | 2 + src/util/vircgroup.c | 541 ++- src/util/vircgroup.h | 8 + 3 files changed, 545 insertions(+), 6 deletions(-) diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index c589236..f5138af 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -73,6 +73,8 @@ virCapabilitiesSetMacPrefix; # cgroup.h +virCgroup2Free; +virCgroup2New; virCgroupAddTask; virCgroupAddTaskController; virCgroupAllowDevice; diff --git a/src/util/vircgroup.c b/src/util/vircgroup.c index 71d46c5..dbc9688 100644 --- a/src/util/vircgroup.c +++ b/src/util/vircgroup.c @@ -37,6 +37,7 @@ #include libgen.h #include dirent.h +#include virobject.h #include internal.h #include virutil.h #include viralloc.h @@ -45,6 +46,7 @@ #include virfile.h #include virhash.h #include virhashcode.h +#include virthread.h #define CGROUP_MAX_VAL 512 @@ -58,6 +60,91 @@ struct virCgroupController { char *placement; }; +struct _virCgroupItem; +typedef struct _virCgroupItem virCgroupItem; +typedef virCgroupItem *virCgroupItemPtr; + +struct _virCgroupItem { +virObjectLockable object; + +char *name; +char *path; + +bool created; /* the path is created or not */ + +virCgroupItemPtr next; +virCgroupItemPtr parent; +virCgroupItemPtr children; + +int type; +struct virCgroupController controllers[VIR_CGROUP_CONTROLLER_LAST]; +}; + +struct virCgroup2 { +virCgroupItemPtr items[VIR_CGROUP_CONTROLLER_LAST]; +}; + +static virClassPtr cgroupItemClass; + +static void cgroupItemDispose(void *obj); + +static int virCgroupItemOnceInit(void) +{ +if (!(cgroupItemClass = virClassNew(virClassForObjectLockable(), +cgroupItem, +sizeof(virCgroupItem), +cgroupItemDispose))) +return -1; + +return 0; +} +VIR_ONCE_GLOBAL_INIT(virCgroupItem); + +static virCgroupItemPtr rootCgroupItems[VIR_CGROUP_CONTROLLER_LAST]; + +static virCgroupItemPtr virCgroupItemRootNew(int type); +static int virCgroupDetectMounts(struct virCgroupController (*controllers)[VIR_CGROUP_CONTROLLER_LAST]); +static int virCgroupDetectPlacement(struct virCgroupController (*controllers)[VIR_CGROUP_CONTROLLER_LAST]); + +static int virCgroupControllersInit(struct virCgroupController (*controllers)[VIR_CGROUP_CONTROLLER_LAST]) +{ +int rc; +int i; + +rc = virCgroupDetectMounts(controllers); +if (rc 0) { +VIR_ERROR(_(Failed to initialize cgroup controllers)); +return rc; +} + +rc = virCgroupDetectPlacement(controllers); + +if (rc == 0) { +/* Check that for every mounted controller, we found our placement */ +for (i = 0 ; i VIR_CGROUP_CONTROLLER_LAST ; i++) { +if (!(*controllers)[i].mountPoint) +continue; + +if (!(*controllers)[i].placement) { +VIR_ERROR(_(Could not find placement for controller %s at %s), + virCgroupControllerTypeToString(i), + (*controllers)[i].placement); +rc = -ENOENT; +break; +} + +VIR_DEBUG(Detected mount/mapping %i:%s at %s in %s, i, + virCgroupControllerTypeToString(i), + (*controllers)[i].mountPoint, + (*controllers)[i].placement); +} +} else { +VIR_ERROR(_(Failed to initialize cgroup controllers)); +} + +return rc; +} + struct virCgroup { char *path; @@ -74,6 +161,362 @@ typedef enum { * cpuacct and cpuset if possible. */ } virCgroupFlags; +static virCgroupItemPtr virCgroupItemRootNew(int type) +{ +virCgroupItemPtr rootItem = NULL; + +if (type = VIR_CGROUP_CONTROLLER_LAST || type 0) +return NULL; + +if (virCgroupItemInitialize() 0) +return NULL; + +if (!(rootItem = virObjectNew(cgroupItemClass))) +return NULL; + +if (virCgroupControllersInit(rootItem-controllers) != 0) { +virObjectUnref(rootItem); +rootItem = NULL; +return NULL; +} + +rootItem-name = strdup(/); +rootItem-next = NULL; +rootItem-parent = NULL; +rootItem-children = NULL; +rootItem-created = 1; +rootItem-type = type; +if (virAsprintf(rootItem-path, %s%s, +rootItem-controllers[rootItem-type].mountPoint, +rootItem-controllers[rootItem-type].placement) 0) { +virObjectUnref(rootItem); +rootItem = NULL; +} + +return rootItem; +} + +static virCgroupItemPtr virCgroupHasChildByName(virCgroupItemPtr item, +
Re: [libvirt] [RFC PATCH v1 1/7] call virstateCleanup to do the cleanup before libvirtd exits
On Thu, Jan 17, 2013 at 05:28:28PM +, Daniel P. Berrange wrote: On Wed, Jan 16, 2013 at 10:53:03AM +0800, Hu Tao wrote: --- daemon/libvirtd.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/daemon/libvirtd.c b/daemon/libvirtd.c index 9cdf4d9..7cb99b1 100644 --- a/daemon/libvirtd.c +++ b/daemon/libvirtd.c @@ -1500,5 +1500,7 @@ cleanup: daemonConfigFree(config); +virStateCleanup(); + return ret; } Unfortunately this causes libvirtd to segv, if you Ctrl-C the daemon shortly after startup. The problem is that virStateCleanup is running before virStateInitialize has finished its work. We probably need to put a mutex in the virStateInitialize+virStateCleanup functions to make sure they serialize Another problem about lockup is revealed by the method(Ctrl-C shortly after the daemon startup), as below: (gdb) bt #0 0x00336500ddcd in __lll_lock_wait () from /lib64/libpthread.so.0 #1 0x003365009c56 in _L_lock_840 () from /lib64/libpthread.so.0 #2 0x003365009b58 in pthread_mutex_lock () from /lib64/libpthread.so.0 #3 0x7f2d21c2dbbd in virMutexLock (m=optimized out) at util/virthreadpthread.c:85 #4 0x7f2d153e776d in qemuDriverLock (driver=optimized out) at qemu/qemu_conf.c:65 #5 0x7f2d154180ee in qemuShutdown () at qemu/qemu_driver.c:1098 #6 0x7f2d21c9fdaf in virStateCleanup () at libvirt.c:846 #7 0x0040c129 in main (argc=optimized out, argv=optimized out) at libvirtd.c:1517 (gdb) thread 2 [Switching to thread 2 (Thread 0x7f2d14f43700 (LWP 20335))] #0 0x00336500b595 in pthread_cond_wait@@GLIBC_2.3.2 () from /lib64/libpthread.so.0 (gdb) bt #0 0x00336500b595 in pthread_cond_wait@@GLIBC_2.3.2 () from /lib64/libpthread.so.0 #1 0x7f2d21c2dcea in virCondWait (c=c@entry=0x7f2d10059668, m=m@entry=0x7f2d10059640) at util/virthreadpthread.c:117 #2 0x7f2d153fd9cc in qemuMonitorSend (mon=mon@entry=0x7f2d10059630, msg=msg@entry=0x7f2d14f41f30) at qemu/qemu_monitor.c:889 #3 0x7f2d1540e913 in qemuMonitorJSONCommandWithFd (mon=mon@entry=0x7f2d10059630, cmd=cmd@entry=0x7f2d10014360, scm_fd=scm_fd@entry=-1, reply=reply@entry=0x7f2d14f41fb0) at qemu/qemu_monitor_json.c:265 #4 0x7f2d1540ea95 in qemuMonitorJSONCommand (mon=mon@entry=0x7f2d10059630, cmd=cmd@entry=0x7f2d10014360, reply=reply@entry=0x7f2d14f41fb0) at qemu/qemu_monitor_json.c:294 #5 0x7f2d15410027 in qemuMonitorJSONSetCapabilities (mon=mon@entry=0x7f2d10059630) at qemu/qemu_monitor_json.c:991 #6 0x7f2d153fea3d in qemuMonitorSetCapabilities (mon=mon@entry=0x7f2d10059630) at qemu/qemu_monitor.c:1153 #7 0x7f2d153bef70 in qemuCapsInitQMP (runGid=0, runUid=0, runDir=optimized out, libDir=0x7f2d10066310 /var/lib/libvirt/qemu, caps=0x7f2d100567f0) at qemu/qemu_capabilities.c:2381 #8 qemuCapsNewForBinary (binary=binary@entry=0x7f2d1005f300 /usr/local/bin/qemu-system-x86_64, libDir=0x7f2d10066310 /var/lib/libvirt/qemu, runDir=optimized out, runUid=0, runGid=0) at qemu/qemu_capabilities.c:2505 #9 0x7f2d153c058e in qemuCapsCacheLookup (cache=cache@entry=0x7f2d10002420, binary=0x7f2d1005f300 /usr/local/bin/qemu-system-x86_64) at qemu/qemu_capabilities.c:2597 #10 0x7f2d153c08c1 in qemuCapsInitGuest (guestarch=VIR_ARCH_I686, hostarch=VIR_ARCH_X86_64, cache=0x7f2d10002420, caps=0x7f2d100653f0) at qemu/qemu_capabilities.c:685 #11 qemuCapsInit (cache=0x7f2d10002420) at qemu/qemu_capabilities.c:920 #12 0x7f2d15418436 in qemuCreateCapabilities (driver=driver@entry=0x7f2d100269b0) at qemu/qemu_driver.c:424 #13 0x7f2d15418d37 in qemuStartup (privileged=optimized out, callback=optimized out, opaque=optimized out) at qemu/qemu_driver.c:874 #14 0x7f2d21c9fcc0 in virStateInitialize (privileged=true, callback=callback@entry=0x40d480 daemonInhibitCallback, opaque=opaque@entry=0x1ea2b40) at libvirt.c:822 #15 0x0040d5d5 in daemonRunStateInit (opaque=opaque@entry=0x1ea2b40) at libvirtd.c:877 #16 0x7f2d21c2d986 in virThreadHelper (data=optimized out) at util/virthreadpthread.c:161 #17 0x003365007d14 in start_thread () from /lib64/libpthread.so.0 #18 0x003364cf167d in clone () from /lib64/libc.so.6 (gdb) -- Thanks, Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [RFC PATCH v1 6/7] deploy the newly introduced virCgroupItem.
On Wed, Jan 16, 2013 at 10:10:50AM +, Daniel P. Berrange wrote: On Wed, Jan 16, 2013 at 10:53:08AM +0800, Hu Tao wrote: diff --git a/daemon/libvirtd.c b/daemon/libvirtd.c index 7cb99b1..92e3292 100644 --- a/daemon/libvirtd.c +++ b/daemon/libvirtd.c @@ -1442,6 +1442,9 @@ int main(int argc, char **argv) { VIR_FORCE_CLOSE(statuswrite); } +if (virCgroupInit() 0) +goto cleanup; + I don't like this addition. Our aim has been to *remove* the need to global initializers like this, not add new ones. AFAICT the reason you needed to add this is because you removed code from the individual drivers which would initialize the cgroups they required. I think I can eliminate this init/uninit thing. diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h index 2ac338c..23ff2c9 100644 --- a/src/conf/domain_conf.h +++ b/src/conf/domain_conf.h @@ -48,6 +48,7 @@ # include device_conf.h # include virbitmap.h # include virstoragefile.h +# include vircgroup.h /* forward declarations of all device types, required by * virDomainDeviceDef @@ -1843,6 +1844,10 @@ struct _virDomainDef { /* Application-specific custom metadata */ xmlNodePtr metadata; + +virCgroupItemPtr cgroup[VIR_CGROUP_CONTROLLER_LAST]; +virCgroupItemPtr (*vcpuCgroups)[VIR_CGROUP_CONTROLLER_LAST]; +virCgroupItemPtr emulatorCgroup[VIR_CGROUP_CONTROLLER_LAST]; }; Two things here. First, this is driver state and so should *not* be in the virDomainDef struct - it should be in the driver specific private data structs. Agreed. Second, the new cgroups API you've got here is really bad. It was an explicit design decision in the original API to *not* expose the concept of individual cgroup controllers to the driver APIs. The only time the drivers should can about individual controllers is when they first create the cgroup and decide which controllers they want to use. From then onwards the virCgroupPtr APIs should just 'do the right thing'. The explanation is helpful. Fortunately I think the new virCgroup can leave the original API unchanged(let me try in v2). What are important in the new virCgroup are: - the lazy creation of cgroup directories, despite of what level they are. - cgroup directories are removed if no one is using the corresponding virCgroup. Do you think it's worth doing it? If yes, can you review patch 5 about the new implementation? (forget about the API change) } +cgroup = vm-def-cgroup[VIR_CGROUP_CONTROLLER_DEVICES]; + if (qemuCgroupControllerActive(driver, VIR_CGROUP_CONTROLLER_DEVICES)) { qemuCgroupData data = { vm, cgroup }; rc = virCgroupDenyAllDevices(cgroup); @@ -300,6 +301,8 @@ int qemuSetupCgroup(virQEMUDriverPtr driver, } } +cgroup = vm-def-cgroup[VIR_CGROUP_CONTROLLER_BLKIO]; + if (vm-def-blkio.weight != 0) { if (qemuCgroupControllerActive(driver, VIR_CGROUP_CONTROLLER_BLKIO)) { rc = virCgroupSetBlkioWeight(cgroup, vm-def-blkio.weight); @@ -339,6 +342,8 @@ int qemuSetupCgroup(virQEMUDriverPtr driver, } } +cgroup = vm-def-cgroup[VIR_CGROUP_CONTROLLER_MEMORY]; + if (qemuCgroupControllerActive(driver, VIR_CGROUP_CONTROLLER_MEMORY)) { unsigned long long hard_limit = vm-def-mem.hard_limit; @@ -392,6 +397,8 @@ int qemuSetupCgroup(virQEMUDriverPtr driver, VIR_WARN(Could not autoset a RSS limit for domain %s, vm-def-name); } +cgroup = vm-def-cgroup[VIR_CGROUP_CONTROLLER_CPU]; + if (vm-def-cputune.shares != 0) { if (qemuCgroupControllerActive(driver, VIR_CGROUP_CONTROLLER_CPU)) { rc = virCgroupSetCpuShares(cgroup, vm-def-cputune.shares); @@ -407,6 +414,8 @@ int qemuSetupCgroup(virQEMUDriverPtr driver, } } +cgroup = vm-def-cgroup[VIR_CGROUP_CONTROLLER_CPUSET]; + if ((vm-def-numatune.memory.nodemask || (vm-def-numatune.memory.placement_mode == VIR_DOMAIN_NUMATUNE_MEM_PLACEMENT_MODE_AUTO)) These 4 additions are a perfect example of what this new API design is awful. The drivers now have to remember which controller they need to use for which tunable. If the original API is kept, these will be the form of: cgroup = vm-cgroup; ... doSomethingWithCgroup(cgroup) ... Is this acceptable? I'm not going to review any more because this change is fatally flawed from a design POV. Regards, Daniel -- |: http://berrange.com -o-http://www.flickr.com/photos/dberrange/ :| |: http://libvirt.org -o- http://virt-manager.org :| |: http://autobuild.org -o- http://search.cpan.org/~danberr/ :| |: http://entangle-photo.org -o- http://live.gnome.org/gtk-vnc :| -- libvir-list mailing list libvir-list@redhat.com https
[libvirt] [RFC PATCH v1 7/7] tests for virCgroup.
--- tests/Makefile.am | 5 +++ tests/vircgrouptest.c | 103 ++ 2 files changed, 108 insertions(+) create mode 100644 tests/vircgrouptest.c diff --git a/tests/Makefile.am b/tests/Makefile.am index 61b0a0c..b2ccdc1 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -99,6 +99,7 @@ test_programs = virshtest sockettest \ virlockspacetest \ virstringtest \ sysinfotest \ + vircgrouptest \ $(NULL) if WITH_GNUTLS @@ -640,6 +641,10 @@ utiltest_SOURCES = \ utiltest.c testutils.h testutils.c utiltest_LDADD = $(LDADDS) +vircgrouptest_SOURCES = \ + vircgrouptest.c testutils.h testutils.c +vircgrouptest_LDADD = $(LDADDS) + if WITH_DRIVER_MODULES virdrivermoduletest_SOURCES = \ virdrivermoduletest.c testutils.h testutils.c diff --git a/tests/vircgrouptest.c b/tests/vircgrouptest.c new file mode 100644 index 000..8d0387b --- /dev/null +++ b/tests/vircgrouptest.c @@ -0,0 +1,103 @@ +/* + * Copyright (C) 2012 Fujitsu. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library. If not, see + * http://www.gnu.org/licenses/. + * + */ + +#include config.h + +#include testutils.h + +#include vircgroup.h + +static int test_cgroup(const void *data ATTRIBUTE_UNUSED) +{ +virCgroupItemPtr cpuset; + +cpuset = virCgroupItemNew(VIR_CGROUP_CONTROLLER_CPUSET, + test_cgroup, + virCgroupGetAppRoot(VIR_CGROUP_CONTROLLER_CPUSET, false)); +if (!cpuset) +return -1; + +if (virCgroupSetCpusetCpus(cpuset, 1) 0) { +virCgroupItemFree(cpuset); +return -1; +} + +virCgroupItemFree(cpuset); + +return 0; +} + +static int test_child_cgroup(const void *data ATTRIBUTE_UNUSED) +{ +int ret = -1; +virCgroupItemPtr item = NULL, item1 = NULL, item2 = NULL; +char *cpus; + +item = virCgroupItemNew(VIR_CGROUP_CONTROLLER_CPUSET, +test_child_cgroup, +virCgroupGetAppRoot(VIR_CGROUP_CONTROLLER_CPUSET, false)); +if (!item) +goto out; + +item1 = virCgroupItemNew(VIR_CGROUP_CONTROLLER_CPUSET, child1, item); +item2 = virCgroupItemNew(VIR_CGROUP_CONTROLLER_CPUSET, child2, item1); + +if (virCgroupGetCpusetCpus(item2, cpus) 0) +goto out; + +VIR_FREE(cpus); + +if (virCgroupSetCpusetCpus(item2, 0) 0) +goto out; + +if (virCgroupGetCpusetCpus(item2, cpus) 0) +goto out; + +VIR_FREE(cpus); + +ret = 0; +out: +if (item) +virCgroupItemFree(item); +if (item1) +virCgroupItemFree(item1); +if (item2) +virCgroupItemFree(item2); +return ret; +} + +static int +mymain(void) +{ +int ret = 0; + +if (virCgroupInit() 0) +return -1; + +if (virtTestRun(test_cgroup, 1, test_cgroup, NULL) 0) +ret = -1; +if (virtTestRun(test_child_cgroup, 1, test_child_cgroup, NULL) 0) +ret = -1; + +virCgroupUninit(); + +return ret; +} + +VIRT_TEST_MAIN(mymain) -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [RFC PATCH v1 5/7] cgroup: refactor virCgroup
This patch adds a new structure, virCgroupItem, to represent a cgroup directory(named cgroup item). cgroup directory is created when needed and removed if no one is using it. --- src/libvirt_private.syms | 7 + src/util/vircgroup.c | 411 ++- src/util/vircgroup.h | 12 ++ 3 files changed, 423 insertions(+), 7 deletions(-) diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 7be58ee..636c49d 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -104,6 +104,12 @@ virCgroupGetMemorySoftLimit; virCgroupGetMemoryUsage; virCgroupGetMemSwapHardLimit; virCgroupGetMemSwapUsage; +virCgroupInit; +virCgroupItemFree; +virCgroupItemKeyPath; +virCgroupItemNew; +virCgroupItemPath; +virCgroupItemType; virCgroupKill; virCgroupKillPainfully; virCgroupKillRecursive; @@ -123,6 +129,7 @@ virCgroupSetMemory; virCgroupSetMemoryHardLimit; virCgroupSetMemorySoftLimit; virCgroupSetMemSwapHardLimit; +virCgroupUninit; # command.h diff --git a/src/util/vircgroup.c b/src/util/vircgroup.c index 71d46c5..baa0af7 100644 --- a/src/util/vircgroup.c +++ b/src/util/vircgroup.c @@ -37,6 +37,7 @@ #include libgen.h #include dirent.h +#include virobject.h #include internal.h #include virutil.h #include viralloc.h @@ -45,6 +46,7 @@ #include virfile.h #include virhash.h #include virhashcode.h +#include virthread.h #define CGROUP_MAX_VAL 512 @@ -58,6 +60,98 @@ struct virCgroupController { char *placement; }; +struct _virCgroupItem { +virObject object; + +char *name; +char *path; + +bool created; /* the path is created or not */ + +virCgroupItemPtr next; +virCgroupItemPtr parent; +virCgroupItemPtr children; + +struct virCgroupController *controller; +}; + +static virClassPtr cgroupItemClass; + +static void cgroupItemDispose(void *obj); + +static int virCgroupItemOnceInit(void) +{ +if (!(cgroupItemClass = virClassNew(cgroupItem, +sizeof(virCgroupItem), +cgroupItemDispose))) +return -1; + +return 0; +} +VIR_ONCE_GLOBAL_INIT(virCgroupItem); + +static struct virCgroupController cgroupControllers[VIR_CGROUP_CONTROLLER_LAST]; +static virCgroupItemPtr rootCgroupItems[VIR_CGROUP_CONTROLLER_LAST]; + +static virCgroupItemPtr virCgroupItemRootNew(int type); +static int virCgroupDetectMounts(struct virCgroupController (*controllers)[VIR_CGROUP_CONTROLLER_LAST]); +static int virCgroupDetectPlacement(struct virCgroupController (*controllers)[VIR_CGROUP_CONTROLLER_LAST]); + +int virCgroupInit(void) +{ +int rc; +int i; + +rc = virCgroupDetectMounts(cgroupControllers); +if (rc 0) { +VIR_ERROR(_(Failed to initialize cgroup controllers)); +return rc; +} + +rc = virCgroupDetectPlacement(cgroupControllers); + +if (rc == 0) { +/* Check that for every mounted controller, we found our placement */ +for (i = 0 ; i VIR_CGROUP_CONTROLLER_LAST ; i++) { +if (!cgroupControllers[i].mountPoint) +continue; + +if (!cgroupControllers[i].placement) { +VIR_ERROR(_(Could not find placement for controller %s at %s), + virCgroupControllerTypeToString(i), + cgroupControllers[i].placement); +rc = -ENOENT; +break; +} + +VIR_DEBUG(Detected mount/mapping %i:%s at %s in %s, i, + virCgroupControllerTypeToString(i), + cgroupControllers[i].mountPoint, + cgroupControllers[i].placement); +} +} else { +VIR_ERROR(_(Failed to initialize cgroup controllers)); +} + +for (i = 0; i VIR_CGROUP_CONTROLLER_LAST; i++) { +rootCgroupItems[i] = virCgroupItemRootNew(i); +} + +return rc; +} + +void virCgroupUninit(void) +{ +int i; + +for (i = 0; i VIR_CGROUP_CONTROLLER_LAST; i++) { +if (rootCgroupItems[i]) { +virCgroupItemFree(rootCgroupItems[i]); +rootCgroupItems[i] = NULL; +} +} +} + struct virCgroup { char *path; @@ -74,6 +168,307 @@ typedef enum { * cpuacct and cpuset if possible. */ } virCgroupFlags; +static virCgroupItemPtr virCgroupItemRootNew(int type) +{ +virCgroupItemPtr rootItem = NULL; + +if (type = VIR_CGROUP_CONTROLLER_LAST) +return NULL; + +if (!cgroupControllers[type].mountPoint) +return NULL; + +if (virCgroupItemInitialize() 0) +return NULL; + +if (!(rootItem = virObjectNew(cgroupItemClass))) +return NULL; + +rootItem-name = strdup(/); +rootItem-next = NULL; +rootItem-parent = NULL; +rootItem-children = NULL; +rootItem-controller = cgroupControllers[type]; +rootItem-created = 1; + +if (virAsprintf(rootItem-path, %s%s%s, +
[libvirt] [RFC PATCH v1 2/7] include util.h in cgroup.h
required by VIR_ENUM_DECL. --- src/util/vircgroup.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/util/vircgroup.h b/src/util/vircgroup.h index 8b6d3b2..05f2e54 100644 --- a/src/util/vircgroup.h +++ b/src/util/vircgroup.h @@ -25,6 +25,8 @@ #ifndef __VIR_CGROUP_H__ # define __VIR_CGROUP_H__ +#include virutil.h + struct virCgroup; typedef struct virCgroup *virCgroupPtr; -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [RFC PATCH v1 4/7] refactor virCgroupDetectMounts and virCgroupDetectPlacement
--- src/util/vircgroup.c | 14 +++--- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/src/util/vircgroup.c b/src/util/vircgroup.c index 48cba93..71d46c5 100644 --- a/src/util/vircgroup.c +++ b/src/util/vircgroup.c @@ -113,7 +113,7 @@ bool virCgroupMounted(virCgroupPtr cgroup, int controller) * Process /proc/mounts figuring out what controllers are * mounted and where */ -static int virCgroupDetectMounts(virCgroupPtr group) +static int virCgroupDetectMounts(struct virCgroupController (*controllers)[VIR_CGROUP_CONTROLLER_LAST]) { int i; FILE *mounts = NULL; @@ -148,8 +148,8 @@ static int virCgroupDetectMounts(virCgroupPtr group) * first entry only */ if (typelen == len STREQLEN(typestr, tmp, len) -!group-controllers[i].mountPoint -!(group-controllers[i].mountPoint = strdup(entry.mnt_dir))) +!(*controllers)[i].mountPoint +!((*controllers)[i].mountPoint = strdup(entry.mnt_dir))) goto no_memory; tmp = next; } @@ -171,7 +171,7 @@ no_memory: * sub-path the current process is assigned to. ie not * necessarily in the root */ -static int virCgroupDetectPlacement(virCgroupPtr group) +static int virCgroupDetectPlacement(struct virCgroupController (*cgroupControllers)[VIR_CGROUP_CONTROLLER_LAST]) { int i; FILE *mapping = NULL; @@ -212,7 +212,7 @@ static int virCgroupDetectPlacement(virCgroupPtr group) len = strlen(tmp); } if (typelen == len STREQLEN(typestr, tmp, len) -!(group-controllers[i].placement = strdup(STREQ(path, /) ? : path))) +!((*cgroupControllers)[i].placement = strdup(STREQ(path, /) ? : path))) goto no_memory; tmp = next; @@ -236,7 +236,7 @@ static int virCgroupDetect(virCgroupPtr group) int rc; int i; -rc = virCgroupDetectMounts(group); +rc = virCgroupDetectMounts(group-controllers); if (rc 0) { VIR_ERROR(_(Failed to detect mounts for %s), group-path); return rc; @@ -251,7 +251,7 @@ static int virCgroupDetect(virCgroupPtr group) return -ENXIO; -rc = virCgroupDetectPlacement(group); +rc = virCgroupDetectPlacement(group-controllers); if (rc == 0) { /* Check that for every mounted controller, we found our placement */ -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [RFC PATCH v1 0/7] virCgroup refactor
Hi, This series is posted for early review. This series refactors virCgroup. The changes are: - virCgroupItem is associated with a cgroup directory. The directory is created only when needed, and removed if no one is using it. - Anyone using cgroups creates instances of virCgroupItem and maintains their lifetime. Please focus on patch #5, which brings the main change(virCgroupItem), and qemu part in patch #6, which shows the usage of virCgroupItem(I've not tested lxc part yet). Hu Tao (7): call virstateCleanup to do the cleanup before libvirtd exits include util.h in cgroup.h include virterror_internal.h in threads.h refactor virCgroupDetectMounts and virCgroupDetectPlacement cgroup: refactor virCgroup deploy the newly introduced virCgroupItem. tests for virCgroup. daemon/libvirtd.c |6 + src/conf/domain_audit.c | 16 +- src/conf/domain_audit.h |6 +- src/conf/domain_conf.h|5 + src/libvirt_private.syms | 17 +- src/lxc/lxc_cgroup.c | 91 ++- src/lxc/lxc_conf.h|2 +- src/lxc/lxc_driver.c | 268 +++- src/lxc/lxc_process.c | 56 +- src/qemu/qemu_cgroup.c| 287 +++-- src/qemu/qemu_cgroup.h| 17 +- src/qemu/qemu_conf.h |2 +- src/qemu/qemu_driver.c| 478 +- src/qemu/qemu_hotplug.c | 44 +- src/qemu/qemu_migration.c | 36 +- src/qemu/qemu_process.c | 29 +- src/util/vircgroup.c | 1570 - src/util/vircgroup.h | 108 ++-- src/util/virthread.h |1 + tests/Makefile.am |5 + tests/vircgrouptest.c | 103 +++ 21 files changed, 1338 insertions(+), 1809 deletions(-) create mode 100644 tests/vircgrouptest.c -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [RFC PATCH v1 1/7] call virstateCleanup to do the cleanup before libvirtd exits
--- daemon/libvirtd.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/daemon/libvirtd.c b/daemon/libvirtd.c index 9cdf4d9..7cb99b1 100644 --- a/daemon/libvirtd.c +++ b/daemon/libvirtd.c @@ -1500,5 +1500,7 @@ cleanup: daemonConfigFree(config); +virStateCleanup(); + return ret; } -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [RFC PATCH v1 3/7] include virterror_internal.h in threads.h
required by virSetError. --- src/util/virthread.h | 1 + 1 file changed, 1 insertion(+) diff --git a/src/util/virthread.h b/src/util/virthread.h index b11a251..c209440 100644 --- a/src/util/virthread.h +++ b/src/util/virthread.h @@ -23,6 +23,7 @@ # define __THREADS_H_ # include internal.h +# include virerror.h typedef struct virMutex virMutex; typedef virMutex *virMutexPtr; -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v1 rebase 1/6] cgroup: Add a flag VIR_CGROUP_DISABLE_CPUSET
On Thu, Dec 13, 2012 at 05:10:47PM +0800, Osier Yang wrote: On 2012年12月13日 15:01, Hu Tao wrote: Add a flag VIR_CGROUP_DISABLE_CPUSET to disable cgroup cpuset. This flag inhibits making of directory under cpuset. --- src/util/cgroup.c | 7 +++ 1 file changed, 7 insertions(+) diff --git a/src/util/cgroup.c b/src/util/cgroup.c index f867fb7..e955a22 100644 --- a/src/util/cgroup.c +++ b/src/util/cgroup.c @@ -72,6 +72,7 @@ typedef enum { */ VIR_CGROUP_VCPU = 1 1, /* create subdir only under the cgroup cpu, * cpuacct and cpuset if possible. */ +VIR_CGROUP_DISABLE_CPUSET = 1 2, } virCgroupFlags; /** @@ -542,6 +543,12 @@ static int virCgroupMakeGroup(virCgroupPtr parent, if (!group-controllers[i].mountPoint) continue; +if ((flags VIR_CGROUP_DISABLE_CPUSET) +i == VIR_CGROUP_CONTROLLER_CPUSET) { +group-controllers[i].mountPoint = NULL; +continue; +} This actually exposes an existed bug, regardless of whether the user will configure qemu.conf without the controller or not. It will always be created. As it iterates over the all the internal-defined controllers without honoring the configuration in qemu.conf. (see the 'for' loop) However, It's expected to not create the cgroup as long as it's not configured in qemu.conf. Agreed. I don't think those directories should be created if not in use, neither. The right way is to fix virCgroupMakeCgroup to honor the configuration in qemu.conf instead, a new flag here only fixes the case cpuset is not configured, it doesn't fix the root cause, and the new flags is not needed if the root cause is fixed. I see this set passes driver-cgroupContollers to virCgroupMakeCgroup, which is good, but it still iterates over the internal-defined all controllers. I'm thinking about refactoring cgroup code to create cgroup dir as needed. -- Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v1 0/6] disable cgroup cpuset
ping... On Wed, Nov 07, 2012 at 06:38:40PM +0800, Hu Tao wrote: The reason to disable cgroup cpuset by default is: currently, sub-directories of cgroup cpuset won't be auto-updated if cpu hot-plug happens. For example, if we now have 0-3,5-7 pcpus online, the value of /sys/fs/cgroup/cpuset/libvirt/qemu/mydom/cpuset.cpus is 0-3,5-7, then pcpu 4 is hot-plugged, but the value of cpuset.cpus is still 0-3,5-7. This will cause a problem that we can't pin to a hot-plugged pcpu. Users can still enable cpuset by editing qemu.conf. Hu Tao (6): cgroup: Add a flag VIR_CGROUP_DISABLE_CPUSET create cgroup controllers for driver according to config create cgroup controllers for domain according to config create cgroup controllers for vcpu according to config create cgroup controllers for emulator according to config disable cgroup cpuset by default src/lxc/lxc_cgroup.c | 4 +-- src/lxc/lxc_driver.c | 22 ++-- src/lxc/lxc_process.c | 4 +-- src/qemu/qemu.conf| 2 +- src/qemu/qemu_cgroup.c| 15 src/qemu/qemu_conf.c | 1 - src/qemu/qemu_driver.c| 92 +-- src/qemu/qemu_hotplug.c | 9 +++-- src/qemu/qemu_migration.c | 2 +- src/util/cgroup.c | 49 +++-- src/util/cgroup.h | 12 --- 11 files changed, 136 insertions(+), 76 deletions(-) -- 1.7.11.7 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v1 0/6] disable cgroup cpuset
On Thu, Dec 13, 2012 at 12:21:29PM +0800, Osier Yang wrote: On 2012年11月07日 18:38, Hu Tao wrote: The reason to disable cgroup cpuset by default is: currently, sub-directories of cgroup cpuset won't be auto-updated if cpu hot-plug happens. For example, if we now have 0-3,5-7 pcpus online, the value of /sys/fs/cgroup/cpuset/libvirt/qemu/mydom/cpuset.cpus is 0-3,5-7, then pcpu 4 is hot-plugged, but the value of cpuset.cpus is still 0-3,5-7. This will cause a problem that we can't pin to a hot-plugged pcpu IMHO it's a kernel bug and should be fixed in kernel instead. The problem was discussed before, see http://www.redhat.com/archives/libvir-list/2012-September/msg00165.html http://www.redhat.com/archives/libvir-list/2012-September/msg00221.html Users can still enable cpuset by editing qemu.conf. And per users can enable/disable the cpuset cgroup in qemu.conf, why do we need to disable it by default? On one hand, it has to be enabled again once the kernel bug is fixed; On the other hand, disabling it affects many functions, it's not deserved to disable it with the only problem (actually the libvirt pinning just behaves correctly, as the hotplug pCPU is not visible yet, the root cause is in kernel) on pinning from my p.o.v. Hu Tao (6): cgroup: Add a flag VIR_CGROUP_DISABLE_CPUSET create cgroup controllers for driver according to config create cgroup controllers for domain according to config create cgroup controllers for vcpu according to config create cgroup controllers for emulator according to config disable cgroup cpuset by default src/lxc/lxc_cgroup.c | 4 +-- src/lxc/lxc_driver.c | 22 ++-- src/lxc/lxc_process.c | 4 +-- src/qemu/qemu.conf| 2 +- src/qemu/qemu_cgroup.c| 15 src/qemu/qemu_conf.c | 1 - src/qemu/qemu_driver.c| 92 +-- src/qemu/qemu_hotplug.c | 9 +++-- src/qemu/qemu_migration.c | 2 +- src/util/cgroup.c | 49 +++-- src/util/cgroup.h | 12 --- 11 files changed, 136 insertions(+), 76 deletions(-) -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v1 rebase 0/6] disable cgroup cpuset
This is merely a rebased version, so still tagged with v1. The reason to disable cgroup cpuset by default is: currently, sub-directories of cgroup cpuset won't be auto-updated if cpu hot-plug happens. For example, if we now have 0-3,5-7 pcpus online, the value of /sys/fs/cgroup/cpuset/libvirt/qemu/mydom/cpuset.cpus is 0-3,5-7, then pcpu 4 is hot-plugged, but the value of cpuset.cpus is still 0-3,5-7. This will cause a problem that we can't pin to a hot-plugged pcpu. Users can still enable cpuset by editing qemu.conf. Hu Tao (6): cgroup: Add a flag VIR_CGROUP_DISABLE_CPUSET create cgroup controllers for driver according to config create cgroup controllers for domain according to config create cgroup controllers for vcpu according to config create cgroup controllers for emulator according to config disable cgroup cpuset by default src/lxc/lxc_cgroup.c | 4 +- src/lxc/lxc_driver.c | 22 +-- src/lxc/lxc_process.c | 4 +- src/qemu/qemu.conf| 2 +- src/qemu/qemu_cgroup.c| 15 src/qemu/qemu_conf.c | 1 - src/qemu/qemu_driver.c| 93 ++- src/qemu/qemu_hotplug.c | 9 +++-- src/qemu/qemu_migration.c | 2 +- src/util/cgroup.c | 49 - src/util/cgroup.h | 12 -- 11 files changed, 137 insertions(+), 76 deletions(-) -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v1 rebase 1/6] cgroup: Add a flag VIR_CGROUP_DISABLE_CPUSET
Add a flag VIR_CGROUP_DISABLE_CPUSET to disable cgroup cpuset. This flag inhibits making of directory under cpuset. --- src/util/cgroup.c | 7 +++ 1 file changed, 7 insertions(+) diff --git a/src/util/cgroup.c b/src/util/cgroup.c index f867fb7..e955a22 100644 --- a/src/util/cgroup.c +++ b/src/util/cgroup.c @@ -72,6 +72,7 @@ typedef enum { */ VIR_CGROUP_VCPU = 1 1, /* create subdir only under the cgroup cpu, * cpuacct and cpuset if possible. */ +VIR_CGROUP_DISABLE_CPUSET = 1 2, } virCgroupFlags; /** @@ -542,6 +543,12 @@ static int virCgroupMakeGroup(virCgroupPtr parent, if (!group-controllers[i].mountPoint) continue; +if ((flags VIR_CGROUP_DISABLE_CPUSET) +i == VIR_CGROUP_CONTROLLER_CPUSET) { +group-controllers[i].mountPoint = NULL; +continue; +} + /* We need to control cpu bandwidth for each vcpu now */ if ((flags VIR_CGROUP_VCPU) (i != VIR_CGROUP_CONTROLLER_CPU -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v1 rebase 5/6] create cgroup controllers for emulator according to config
Add a parameter to virCgroupForEmulator to indicate which cgroup controllers to create. The value of the parameter is read from user config. --- src/qemu/qemu_cgroup.c | 2 +- src/qemu/qemu_driver.c | 9 ++--- src/util/cgroup.c | 12 +--- src/util/cgroup.h | 3 ++- 4 files changed, 18 insertions(+), 8 deletions(-) diff --git a/src/qemu/qemu_cgroup.c b/src/qemu/qemu_cgroup.c index 5a1bf7e..5738e93 100644 --- a/src/qemu/qemu_cgroup.c +++ b/src/qemu/qemu_cgroup.c @@ -670,7 +670,7 @@ int qemuSetupCgroupForEmulator(virQEMUDriverPtr driver, goto cleanup; } -rc = virCgroupForEmulator(cgroup, cgroup_emulator, 1); +rc = virCgroupForEmulator(cgroup, cgroup_emulator, 1, driver-cgroupControllers); if (rc 0) { virReportSystemError(-rc, _(Unable to create emulator cgroup for %s), diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c index 005dc8a..a6034c2 100644 --- a/src/qemu/qemu_driver.c +++ b/src/qemu/qemu_driver.c @@ -4418,7 +4418,8 @@ qemuDomainPinEmulator(virDomainPtr dom, */ if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup_dom, 0, driver-cgroupControllers) == 0) { -if (virCgroupForEmulator(cgroup_dom, cgroup_emulator, 0) == 0) { +if (virCgroupForEmulator(cgroup_dom, cgroup_emulator, 0, + driver-cgroupControllers) == 0) { if (qemuSetupCgroupEmulatorPin(cgroup_emulator, newVcpuPin[0]-cpumask) 0) { virReportError(VIR_ERR_OPERATION_INVALID, %s, @@ -8047,7 +8048,8 @@ qemuSetEmulatorBandwidthLive(virDomainObjPtr vm, virCgroupPtr cgroup, return 0; } -rc = virCgroupForEmulator(cgroup, cgroup_emulator, 0); +rc = virCgroupForEmulator(cgroup, cgroup_emulator, 0, + qemu_driver-cgroupControllers); if (rc 0) { virReportSystemError(-rc, _(Unable to find emulator cgroup for %s), @@ -8339,7 +8341,8 @@ qemuGetEmulatorBandwidthLive(virDomainObjPtr vm, virCgroupPtr cgroup, } /* get period and quota for emulator */ -rc = virCgroupForEmulator(cgroup, cgroup_emulator, 0); +rc = virCgroupForEmulator(cgroup, cgroup_emulator, 0, + qemu_driver-cgroupControllers); if (!cgroup_emulator) { virReportSystemError(-rc, _(Unable to find emulator cgroup for %s), diff --git a/src/util/cgroup.c b/src/util/cgroup.c index 8b117f3..2e5a7e1 100644 --- a/src/util/cgroup.c +++ b/src/util/cgroup.c @@ -1117,14 +1117,19 @@ int virCgroupForVcpu(virCgroupPtr driver ATTRIBUTE_UNUSED, #if defined HAVE_MNTENT_H defined HAVE_GETMNTENT_R int virCgroupForEmulator(virCgroupPtr driver, virCgroupPtr *group, - bool create) + bool create, + int controllers) { +unsigned flags = VIR_CGROUP_VCPU; int rc; char *path; if (driver == NULL) return -EINVAL; +if (!(controllers (1UL VIR_CGROUP_CONTROLLER_CPUSET))) +flags |= VIR_CGROUP_DISABLE_CPUSET; + if (virAsprintf(path, %s/emulator, driver-path) 0) return -ENOMEM; @@ -1132,7 +1137,7 @@ int virCgroupForEmulator(virCgroupPtr driver, VIR_FREE(path); if (rc == 0) { -rc = virCgroupMakeGroup(driver, *group, create, VIR_CGROUP_VCPU); +rc = virCgroupMakeGroup(driver, *group, create, flags); if (rc != 0) virCgroupFree(group); } @@ -1142,7 +1147,8 @@ int virCgroupForEmulator(virCgroupPtr driver, #else int virCgroupForEmulator(virCgroupPtr driver ATTRIBUTE_UNUSED, virCgroupPtr *group ATTRIBUTE_UNUSED, - bool create ATTRIBUTE_UNUSED) + bool create ATTRIBUTE_UNUSED, + int controllers ATTRIBUTE_UNUSED) { return -ENXIO; } diff --git a/src/util/cgroup.h b/src/util/cgroup.h index 4b5cc5c..0ffdd84 100644 --- a/src/util/cgroup.h +++ b/src/util/cgroup.h @@ -64,7 +64,8 @@ int virCgroupForVcpu(virCgroupPtr driver, int virCgroupForEmulator(virCgroupPtr driver, virCgroupPtr *group, - bool create); + bool create, + int controllers); int virCgroupPathOfController(virCgroupPtr group, int controller, -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v1 rebase 2/6] create cgroup controllers for driver according to config
Add a parameter to virCgroupForDriver to indicate which cgroup controllers to create. The value of the parameter is read from user config. --- src/lxc/lxc_cgroup.c | 2 +- src/lxc/lxc_driver.c | 2 +- src/qemu/qemu_driver.c | 13 +++-- src/util/cgroup.c | 12 +--- src/util/cgroup.h | 3 ++- 5 files changed, 20 insertions(+), 12 deletions(-) diff --git a/src/lxc/lxc_cgroup.c b/src/lxc/lxc_cgroup.c index 767ef26..0af9dcc 100644 --- a/src/lxc/lxc_cgroup.c +++ b/src/lxc/lxc_cgroup.c @@ -371,7 +371,7 @@ int virLXCCgroupSetup(virDomainDefPtr def) int ret = -1; int rc; -rc = virCgroupForDriver(lxc, driver, 1, 0); +rc = virCgroupForDriver(lxc, driver, 1, 0, ~0); if (rc != 0) { virReportSystemError(-rc, %s, _(Unable to get cgroup for driver)); diff --git a/src/lxc/lxc_driver.c b/src/lxc/lxc_driver.c index e0e76e6..3f5aa80 100644 --- a/src/lxc/lxc_driver.c +++ b/src/lxc/lxc_driver.c @@ -1448,7 +1448,7 @@ static int lxcStartup(bool privileged, lxc_driver-log_libvirtd = 0; /* by default log to container logfile */ lxc_driver-have_netns = lxcCheckNetNsSupport(); -rc = virCgroupForDriver(lxc, lxc_driver-cgroup, privileged, 1); +rc = virCgroupForDriver(lxc, lxc_driver-cgroup, privileged, 1, ~0); if (rc 0) { char buf[1024] ATTRIBUTE_UNUSED; VIR_DEBUG(Unable to create cgroup for LXC driver: %s, diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c index 1228f6e..d155ea7 100644 --- a/src/qemu/qemu_driver.c +++ b/src/qemu/qemu_driver.c @@ -797,17 +797,18 @@ qemuStartup(bool privileged, VIR_FREE(base); -rc = virCgroupForDriver(qemu, qemu_driver-cgroup, privileged, 1); -if (rc 0) { -VIR_INFO(Unable to create cgroup for driver: %s, - virStrerror(-rc, ebuf, sizeof(ebuf))); -} - if (qemuLoadDriverConfig(qemu_driver, driverConf) 0) { goto error; } VIR_FREE(driverConf); +rc = virCgroupForDriver(qemu, qemu_driver-cgroup, privileged, 1, +qemu_driver-cgroupControllers); +if (rc 0) { +VIR_INFO(Unable to create cgroup for driver: %s, + virStrerror(-rc, ebuf, sizeof(ebuf))); +} + /* Allocate bitmap for remote display port reservations. We cannot * do this before the config is loaded properly, since the port * numbers are configurable now */ diff --git a/src/util/cgroup.c b/src/util/cgroup.c index e955a22..37a5c08 100644 --- a/src/util/cgroup.c +++ b/src/util/cgroup.c @@ -934,11 +934,13 @@ cleanup: int virCgroupForDriver(const char *name, virCgroupPtr *group, bool privileged, - bool create) + bool create, + int controllers) { int rc; char *path = NULL; virCgroupPtr rootgrp = NULL; +unsigned flags = VIR_CGROUP_NONE; rc = virCgroupAppRoot(privileged, rootgrp, create); if (rc != 0) @@ -949,11 +951,14 @@ int virCgroupForDriver(const char *name, goto out; } +if (!(controllers (1UL VIR_CGROUP_CONTROLLER_CPUSET))) +flags |= VIR_CGROUP_DISABLE_CPUSET; + rc = virCgroupNew(path, group); VIR_FREE(path); if (rc == 0) { -rc = virCgroupMakeGroup(rootgrp, *group, create, VIR_CGROUP_NONE); +rc = virCgroupMakeGroup(rootgrp, *group, create, flags); if (rc != 0) virCgroupFree(group); } @@ -967,7 +972,8 @@ out: int virCgroupForDriver(const char *name ATTRIBUTE_UNUSED, virCgroupPtr *group ATTRIBUTE_UNUSED, bool privileged ATTRIBUTE_UNUSED, - bool create ATTRIBUTE_UNUSED) + bool create ATTRIBUTE_UNUSED, + int controllers) { /* Claim no support */ return -ENXIO; diff --git a/src/util/cgroup.h b/src/util/cgroup.h index fc9e409..3e3be91 100644 --- a/src/util/cgroup.h +++ b/src/util/cgroup.h @@ -45,7 +45,8 @@ VIR_ENUM_DECL(virCgroupController); int virCgroupForDriver(const char *name, virCgroupPtr *group, bool privileged, - bool create); + bool create, + int controllers); int virCgroupGetAppRoot(virCgroupPtr *group); -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v1 rebase 4/6] create cgroup controllers for vcpu according to config
Add a parameter to virCgroupForVcpu to indicate which cgroup controllers to create. The value of the parameter is read from user config. --- src/qemu/qemu_cgroup.c | 3 ++- src/qemu/qemu_driver.c | 18 -- src/util/cgroup.c | 9 +++-- src/util/cgroup.h | 3 ++- 4 files changed, 23 insertions(+), 10 deletions(-) diff --git a/src/qemu/qemu_cgroup.c b/src/qemu/qemu_cgroup.c index b868269..5a1bf7e 100644 --- a/src/qemu/qemu_cgroup.c +++ b/src/qemu/qemu_cgroup.c @@ -576,7 +576,8 @@ int qemuSetupCgroupForVcpu(virQEMUDriverPtr driver, virDomainObjPtr vm) } for (i = 0; i priv-nvcpupids; i++) { -rc = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 1); +rc = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 1, + driver-cgroupControllers); if (rc 0) { virReportSystemError(-rc, _(Unable to create vcpu cgroup for %s(vcpu: diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c index 2b915ff..005dc8a 100644 --- a/src/qemu/qemu_driver.c +++ b/src/qemu/qemu_driver.c @@ -3829,7 +3829,8 @@ static int qemuDomainHotplugVcpus(virQEMUDriverPtr driver, if (cgroup_available) { int rv = -1; /* Create cgroup for the onlined vcpu */ -rv = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 1); +rv = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 1, + driver-cgroupControllers); if (rv 0) { virReportSystemError(-rv, _(Unable to create vcpu cgroup for %s(vcpu: @@ -3903,7 +3904,8 @@ static int qemuDomainHotplugVcpus(virQEMUDriverPtr driver, if (cgroup_available) { int rv = -1; -rv = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 0); +rv = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 0, + driver-cgroupControllers); if (rv 0) { virReportSystemError(-rv, _(Unable to access vcpu cgroup for %s(vcpu: @@ -4150,7 +4152,8 @@ qemuDomainPinVcpuFlags(virDomainPtr dom, if (qemuCgroupControllerActive(driver, VIR_CGROUP_CONTROLLER_CPUSET)) { if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup_dom, 0, driver-cgroupControllers) == 0 -virCgroupForVcpu(cgroup_dom, vcpu, cgroup_vcpu, 0) == 0 +virCgroupForVcpu(cgroup_dom, vcpu, cgroup_vcpu, 0, + driver-cgroupControllers) == 0 qemuSetupCgroupVcpuPin(cgroup_vcpu, newVcpuPin, newVcpuPinNum, vcpu) 0) { virReportError(VIR_ERR_OPERATION_INVALID, _(failed to set cpuset.cpus in cgroup @@ -8005,7 +8008,8 @@ qemuSetVcpusBWLive(virDomainObjPtr vm, virCgroupPtr cgroup, */ if (priv-nvcpupids != 0 priv-vcpupids[0] != vm-pid) { for (i = 0; i priv-nvcpupids; i++) { -rc = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 0); +rc = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 0, + qemu_driver-cgroupControllers); if (rc 0) { virReportSystemError(-rc, _(Unable to find vcpu cgroup for %s(vcpu: @@ -8296,7 +8300,8 @@ qemuGetVcpusBWLive(virDomainObjPtr vm, virCgroupPtr cgroup, } /* get period and quota for vcpu0 */ -rc = virCgroupForVcpu(cgroup, 0, cgroup_vcpu, 0); +rc = virCgroupForVcpu(cgroup, 0, cgroup_vcpu, 0, + qemu_driver-cgroupControllers); if (!cgroup_vcpu) { virReportSystemError(-rc, _(Unable to find vcpu cgroup for %s(vcpu: 0)), @@ -14386,7 +14391,8 @@ getSumVcpuPercpuStats(virCgroupPtr group, unsigned long long tmp; int j; -if (virCgroupForVcpu(group, i, group_vcpu, 0) 0) { +if (virCgroupForVcpu(group, i, group_vcpu, 0, + qemu_driver-cgroupControllers) 0) { virReportError(VIR_ERR_INTERNAL_ERROR, %s, _(error accessing cgroup cpuacct for vcpu)); goto cleanup; diff --git a/src/util/cgroup.c b/src/util/cgroup.c index f3e4185..8b117f3 100644 --- a/src/util/cgroup.c +++ b/src/util/cgroup.c @@ -1069,14 +1069,19 @@ int virCgroupForDomain(virCgroupPtr driver ATTRIBUTE_UNUSED, int virCgroupForVcpu(virCgroupPtr driver, int vcpuid, virCgroupPtr *group, - bool create) + bool create, + int controllers) { +unsigned flags = VIR_CGROUP_VCPU; int rc; char *path; if (driver == NULL) return -EINVAL; +if (!(controllers (1UL VIR_CGROUP_CONTROLLER_CPUSET))) +flags |=
[libvirt] [PATCH v1 rebase 6/6] disable cgroup cpuset by default
The reason ti disable cgroup cpuset by default is: currently, sub-directories of cgroup cpuset won't be auto-updated if cpu hot-plug happens. For example, if we now have 0-3,5-7 pcpus online, the value of /sys/fs/cgroup/cpuset/libvirt/qemu/mydom/cpuset.cpus is 0-3,5-7, then pcpu 4 is hot-plugged, but the value of cpuset.cpus is still 0-3,5-7. This will cause a problem that we can't pin to a hot-plugged pcpu. Users can still enable cpuset by editing qemu.conf. --- src/qemu/qemu.conf | 2 +- src/qemu/qemu_conf.c | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/src/qemu/qemu.conf b/src/qemu/qemu.conf index dd853c8..b853852 100644 --- a/src/qemu/qemu.conf +++ b/src/qemu/qemu.conf @@ -226,7 +226,7 @@ # can be mounted in different locations. libvirt will detect # where they are located. # -#cgroup_controllers = [ cpu, devices, memory, blkio, cpuset, cpuacct ] +#cgroup_controllers = [ cpu, devices, memory, blkio, cpuacct ] # This is the basic set of devices allowed / required by # all virtual machines. diff --git a/src/qemu/qemu_conf.c b/src/qemu/qemu_conf.c index e95609c..96b14a0 100644 --- a/src/qemu/qemu_conf.c +++ b/src/qemu/qemu_conf.c @@ -287,7 +287,6 @@ int qemuLoadDriverConfig(virQEMUDriverPtr driver, (1 VIR_CGROUP_CONTROLLER_DEVICES) | (1 VIR_CGROUP_CONTROLLER_MEMORY) | (1 VIR_CGROUP_CONTROLLER_BLKIO) | -(1 VIR_CGROUP_CONTROLLER_CPUSET) | (1 VIR_CGROUP_CONTROLLER_CPUACCT); } for (i = 0 ; i VIR_CGROUP_CONTROLLER_LAST ; i++) { -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v1 rebase 3/6] create cgroup controllers for domain according to config
Add a parameter to virCgroupForDomain to indicate which cgroup controllers to create for domain. The value of the parameter is read from user config. --- src/lxc/lxc_cgroup.c | 2 +- src/lxc/lxc_driver.c | 20 +- src/lxc/lxc_process.c | 4 ++-- src/qemu/qemu_cgroup.c| 10 - src/qemu/qemu_driver.c| 53 ++- src/qemu/qemu_hotplug.c | 9 +--- src/qemu/qemu_migration.c | 2 +- src/util/cgroup.c | 9 ++-- src/util/cgroup.h | 3 ++- 9 files changed, 68 insertions(+), 44 deletions(-) diff --git a/src/lxc/lxc_cgroup.c b/src/lxc/lxc_cgroup.c index 0af9dcc..59007da 100644 --- a/src/lxc/lxc_cgroup.c +++ b/src/lxc/lxc_cgroup.c @@ -378,7 +378,7 @@ int virLXCCgroupSetup(virDomainDefPtr def) goto cleanup; } -rc = virCgroupForDomain(driver, def-name, cgroup, 1); +rc = virCgroupForDomain(driver, def-name, cgroup, 1, ~0); if (rc != 0) { virReportSystemError(-rc, _(Unable to create cgroup for domain %s), diff --git a/src/lxc/lxc_driver.c b/src/lxc/lxc_driver.c index 3f5aa80..0530af2 100644 --- a/src/lxc/lxc_driver.c +++ b/src/lxc/lxc_driver.c @@ -544,7 +544,7 @@ static int lxcDomainGetInfo(virDomainPtr dom, info-cpuTime = 0; info-memory = vm-def-mem.cur_balloon; } else { -if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(Unable to get cgroup for %s), vm-def-name); goto cleanup; @@ -737,7 +737,7 @@ static int lxcDomainSetMemory(virDomainPtr dom, unsigned long newmem) { goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(Unable to get cgroup for %s), vm-def-name); goto cleanup; @@ -794,7 +794,7 @@ lxcDomainSetMemoryParameters(virDomainPtr dom, goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(cannot find cgroup for domain %s), vm-def-name); goto cleanup; @@ -871,7 +871,7 @@ lxcDomainGetMemoryParameters(virDomainPtr dom, goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(Unable to get cgroup for %s), vm-def-name); goto cleanup; @@ -1795,7 +1795,7 @@ lxcSetSchedulerParametersFlags(virDomainPtr dom, %s, _(cgroup CPU controller is not mounted)); goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(cannot find cgroup for domain %s), vm-def-name); @@ -1939,7 +1939,7 @@ lxcGetSchedulerParametersFlags(virDomainPtr dom, goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(cannot find cgroup for domain %s), vm-def-name); goto cleanup; @@ -2044,7 +2044,7 @@ lxcDomainSetBlkioParameters(virDomainPtr dom, goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(cannot find cgroup for domain %s), vm-def-name); goto cleanup; @@ -2149,7 +2149,7 @@ lxcDomainGetBlkioParameters(virDomainPtr dom, goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(cannot find cgroup for domain %s), vm-def-name); goto cleanup; @@ -2383,7 +2383,7 @@ static int lxcFreezeContainer(virLXCDriverPtr driver, virDomainObjPtr vm) virCgroupPtr cgroup = NULL; if (!(driver-cgroup - virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0) == 0)) + virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0, ~0) == 0))
Re: [libvirt] [PATCH v3] bitmap: fix typo to use UL type of integer constant in virBitmapIsAllSet
On Wed, Nov 28, 2012 at 02:24:31PM +0800, Guannan Ren wrote: This bug leads to getting incorrect vcpupin information via qemudDomainGetVcpuPinInfo() API when the number of maximum cpu on a host falls into a range such as 31 ncpus 64. gcc warning: left shift count = width of type The following bug is such the case https://bugzilla.redhat.com/show_bug.cgi?id=876415 --- src/util/bitmap.c | 4 ++-- tests/virbitmaptest.c | 37 + 2 files changed, 39 insertions(+), 2 deletions(-) diff --git a/src/util/bitmap.c b/src/util/bitmap.c index 5ec5440..c29f5f3 100644 --- a/src/util/bitmap.c +++ b/src/util/bitmap.c @@ -574,8 +574,8 @@ bool virBitmapIsAllSet(virBitmapPtr bitmap) return false; if (unusedBits 0) { -if ((bitmap-map[sz] ((1U (VIR_BITMAP_BITS_PER_UNIT - unusedBits)) - 1)) -!= ((1U (VIR_BITMAP_BITS_PER_UNIT - unusedBits)) - 1)) +if ((bitmap-map[sz] ((1UL (VIR_BITMAP_BITS_PER_UNIT - unusedBits)) - 1)) +!= ((1UL (VIR_BITMAP_BITS_PER_UNIT - unusedBits)) - 1)) return false; } diff --git a/tests/virbitmaptest.c b/tests/virbitmaptest.c index f1eb9d5..af94dab 100644 --- a/tests/virbitmaptest.c +++ b/tests/virbitmaptest.c @@ -347,6 +347,41 @@ error: return ret; } +static int test7(const void *v ATTRIBUTE_UNUSED) +{ +virBitmapPtr bitmap; +size_t i; +size_t maxBit[] = { +1, 8, 31, 32, 63, 64, 95, 96, 127, 128, 159, 160 +}; +size_t nmaxBit = 12; + +for (i = 0; i nmaxBit; i++) { +bitmap = virBitmapNew(maxBit[i]); +if (!bitmap) +goto error; + +if (virBitmapIsAllSet(bitmap)) +goto error; + +ignore_value(virBitmapSetBit(bitmap, 1)); +if (virBitmapIsAllSet(bitmap)) +goto error; + +virBitmapSetAll(bitmap); +if (!virBitmapIsAllSet(bitmap)) +goto error; + +virBitmapFree(bitmap); +} + +return 0; + +error: +virBitmapFree(bitmap); +return -1; +} + static int mymain(void) { @@ -364,6 +399,8 @@ mymain(void) ret = -1; if (virtTestRun(test6, 1, test6, NULL) 0) ret = -1; +if (virtTestRun(test7, 1, test7, NULL) 0) +ret = -1; return ret; -- 1.7.11.2 Looks OK to me. -- Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v2] build: more fix to avoid C99 for loop (Re: [PATCH] build: more fix to avoid C99 for loop (Re: [PATCH] build: avoid C99 for loop))
On Wed, Nov 28, 2012 at 10:41:34AM +0100, Martin Kletzander wrote: On 11/28/2012 04:37 AM, Hu Tao wrote: On Mon, Nov 26, 2012 at 03:25:04PM -0700, Eric Blake wrote: Although we require various C99 features, we don't yet require a complete C99 compiler. On RHEL 5, compilation complained: qemu/qemu_command.c: In function 'qemuBuildGraphicsCommandLine': qemu/qemu_command.c:4688: error: 'for' loop initial declaration used outside C99 mode * src/qemu/qemu_command.c (qemuBuildGraphicsCommandLine): Declare variable sooner. * src/qemu/qemu_process.c (qemuProcessInitPasswords): Likewise. find ./ -name '*.c' | xargs grep 'for *( *int ' reveals another file, see the patch below. From 9f5f9112108c5ab42e56c1e4e9db185d7dfb6cf4 Mon Sep 17 00:00:00 2001 From: Hu Tao hu...@cn.fujitsu.com Date: Wed, 28 Nov 2012 11:31:26 +0800 Subject: [PATCH] build: more fix to avoid C99 for loop see commit 7e5aa78d0f7f4cbf1c8 * src/interface/interface_backend_udev.c: Declare variable sooner. --- src/interface/interface_backend_udev.c | 9 ++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/src/interface/interface_backend_udev.c b/src/interface/interface_backend_udev.c index 5a27cc5..ed73d54 100644 --- a/src/interface/interface_backend_udev.c +++ b/src/interface/interface_backend_udev.c @@ -515,12 +515,14 @@ udevIfaceScanDirFilter(const struct dirent *entry) static void udevIfaceFreeIfaceDef(virInterfaceDef *ifacedef) { +int i; + if (!ifacedef) return; if (ifacedef-type == VIR_INTERFACE_TYPE_BRIDGE) { VIR_FREE(ifacedef-data.bridge.delay); -for (int i = 0; i ifacedef-data.bridge.nbItf; i++) { +for (i = 0; i ifacedef-data.bridge.nbItf; i++) { udevIfaceFreeIfaceDef(ifacedef-data.bridge.itf[i]); } VIR_FREE(ifacedef-data.bridge.itf); @@ -547,6 +549,7 @@ udevIfaceGetIfaceDef(struct udev *udev, char *name) char *vlan_parent_dev = NULL; struct dirent **member_list = NULL; int member_count = 0; +int i; /* Allocate our interface definition structure */ if (VIR_ALLOC(ifacedef) 0) { @@ -679,7 +682,7 @@ udevIfaceGetIfaceDef(struct udev *udev, char *name) } ifacedef-data.bridge.nbItf = member_count; -for (int i= 0; i member_count; i++) { +for (i= 0; i member_count; i++) { Ewww, this could use a space: s/i=/i =/ Fixed. Thanks for review! From 10e878a963aeb591121910f1d3b57af923acf5de Mon Sep 17 00:00:00 2001 From: Hu Tao hu...@cn.fujitsu.com Date: Wed, 28 Nov 2012 18:13:21 +0800 Subject: [PATCH v2] build: more fix to avoid C99 for loop see commit 7e5aa78d0f7f4cbf1c8 * src/interface/interface_backend_udev.c: Declare variable sooner. --- v2: - i=0 -- i = 0 src/interface/interface_backend_udev.c | 9 ++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/src/interface/interface_backend_udev.c b/src/interface/interface_backend_udev.c index 5a27cc5..9233e87 100644 --- a/src/interface/interface_backend_udev.c +++ b/src/interface/interface_backend_udev.c @@ -515,12 +515,14 @@ udevIfaceScanDirFilter(const struct dirent *entry) static void udevIfaceFreeIfaceDef(virInterfaceDef *ifacedef) { +int i; + if (!ifacedef) return; if (ifacedef-type == VIR_INTERFACE_TYPE_BRIDGE) { VIR_FREE(ifacedef-data.bridge.delay); -for (int i = 0; i ifacedef-data.bridge.nbItf; i++) { +for (i = 0; i ifacedef-data.bridge.nbItf; i++) { udevIfaceFreeIfaceDef(ifacedef-data.bridge.itf[i]); } VIR_FREE(ifacedef-data.bridge.itf); @@ -547,6 +549,7 @@ udevIfaceGetIfaceDef(struct udev *udev, char *name) char *vlan_parent_dev = NULL; struct dirent **member_list = NULL; int member_count = 0; +int i; /* Allocate our interface definition structure */ if (VIR_ALLOC(ifacedef) 0) { @@ -679,7 +682,7 @@ udevIfaceGetIfaceDef(struct udev *udev, char *name) } ifacedef-data.bridge.nbItf = member_count; -for (int i= 0; i member_count; i++) { +for (i = 0; i member_count; i++) { ifacedef-data.bridge.itf[i] = udevIfaceGetIfaceDef(udev, member_list[i]-d_name); VIR_FREE(member_list[i]); @@ -698,7 +701,7 @@ udevIfaceGetIfaceDef(struct udev *udev, char *name) cleanup: udev_device_unref(dev); -for (int i = 0; i member_count; i++) { +for (i = 0; i member_count; i++) { VIR_FREE(member_list[i]); } VIR_FREE(member_list); -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH 3/3] Add support for shutdown / reboot APIs in LXC driver
... +static int +lxcDomainReboot(virDomainPtr dom, +unsigned int flags) +{ +virLXCDriverPtr driver = dom-conn-privateData; +virLXCDomainObjPrivatePtr priv; +virDomainObjPtr vm; +char *vroot = NULL; +int ret = -1; +int rc; + +virCheckFlags(VIR_DOMAIN_REBOOT_INITCTL | + VIR_DOMAIN_REBOOT_SIGNAL, -1); + ... + +if (flags == 0 || +(flags VIR_DOMAIN_REBOOT_INITCTL)) { +if ((rc = virInitctlSetRunLevel(VIR_INITCTL_RUNLEVEL_REBOOT, +vroot)) 0) { +goto cleanup; +} +if (rc == 0 flags != 0 +((flags ~VIR_DOMAIN_SHUTDOWN_INITCTL) == 0)) { ((flags ~VIR_DOMAIN_REBOOT_INITCTL) == 0)) { +virReportError(VIR_ERR_OPERATION_UNSUPPORTED, %s, + _(Container does not provide an initctl pipe)); +goto cleanup; +} +} else { +rc = 0; +} + ... -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v2] bitmap: fix typo to use UL type of integer constant in virBitmapIsAllSet
On Mon, Nov 26, 2012 at 01:36:00PM +0800, Guannan Ren wrote: This bug leads to get incorrect vcpupin information via qemudDomainGetVcpuPinInfo() API when the number of maximum cpu on a host falls into a range such as 31 ncpus 64. gcc warning: left shift count = width of type The following bug is such the case https://bugzilla.redhat.com/show_bug.cgi?id=876415 --- src/util/bitmap.c |4 ++-- tests/virbitmaptest.c | 33 + 2 files changed, 35 insertions(+), 2 deletions(-) diff --git a/src/util/bitmap.c b/src/util/bitmap.c index 5ec5440..c29f5f3 100644 --- a/src/util/bitmap.c +++ b/src/util/bitmap.c @@ -574,8 +574,8 @@ bool virBitmapIsAllSet(virBitmapPtr bitmap) return false; if (unusedBits 0) { -if ((bitmap-map[sz] ((1U (VIR_BITMAP_BITS_PER_UNIT - unusedBits)) - 1)) -!= ((1U (VIR_BITMAP_BITS_PER_UNIT - unusedBits)) - 1)) +if ((bitmap-map[sz] ((1UL (VIR_BITMAP_BITS_PER_UNIT - unusedBits)) - 1)) +!= ((1UL (VIR_BITMAP_BITS_PER_UNIT - unusedBits)) - 1)) return false; } diff --git a/tests/virbitmaptest.c b/tests/virbitmaptest.c index f1eb9d5..e21bb02 100644 --- a/tests/virbitmaptest.c +++ b/tests/virbitmaptest.c @@ -347,6 +347,37 @@ error: return ret; } +static int test7(const void *v ATTRIBUTE_UNUSED) +{ +virBitmapPtr bitmap; +size_t i; +size_t maxBit[] = { +1, 8, 31, 32, 63, 64, 95, 96, 127, 128, 159, 160 +}; +size_t nmaxBit = 12; + +for (i = 0; i nmaxBit; i++) { +bitmap = virBitmapNew(maxBit[i]); +if (!bitmap) +goto error; + +if (virBitmapIsAllSet(bitmap)) +goto error; Looks OK to me except: set partial bits then test + +virBitmapSetAll(bitmap); +if (!virBitmapIsAllSet(bitmap)) +goto error; + +virBitmapFree(bitmap); +} + +return 0; + +error: +virBitmapFree(bitmap); +return -1; +} + static int mymain(void) { @@ -364,6 +395,8 @@ mymain(void) ret = -1; if (virtTestRun(test6, 1, test6, NULL) 0) ret = -1; +if (virtTestRun(test7, 1, test7, NULL) 0) +ret = -1; return ret; -- 1.7.1 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH] build: more fix to avoid C99 for loop (Re: [PATCH] build: avoid C99 for loop)
On Mon, Nov 26, 2012 at 03:25:04PM -0700, Eric Blake wrote: Although we require various C99 features, we don't yet require a complete C99 compiler. On RHEL 5, compilation complained: qemu/qemu_command.c: In function 'qemuBuildGraphicsCommandLine': qemu/qemu_command.c:4688: error: 'for' loop initial declaration used outside C99 mode * src/qemu/qemu_command.c (qemuBuildGraphicsCommandLine): Declare variable sooner. * src/qemu/qemu_process.c (qemuProcessInitPasswords): Likewise. find ./ -name '*.c' | xargs grep 'for *( *int ' reveals another file, see the patch below. From 9f5f9112108c5ab42e56c1e4e9db185d7dfb6cf4 Mon Sep 17 00:00:00 2001 From: Hu Tao hu...@cn.fujitsu.com Date: Wed, 28 Nov 2012 11:31:26 +0800 Subject: [PATCH] build: more fix to avoid C99 for loop see commit 7e5aa78d0f7f4cbf1c8 * src/interface/interface_backend_udev.c: Declare variable sooner. --- src/interface/interface_backend_udev.c | 9 ++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/src/interface/interface_backend_udev.c b/src/interface/interface_backend_udev.c index 5a27cc5..ed73d54 100644 --- a/src/interface/interface_backend_udev.c +++ b/src/interface/interface_backend_udev.c @@ -515,12 +515,14 @@ udevIfaceScanDirFilter(const struct dirent *entry) static void udevIfaceFreeIfaceDef(virInterfaceDef *ifacedef) { +int i; + if (!ifacedef) return; if (ifacedef-type == VIR_INTERFACE_TYPE_BRIDGE) { VIR_FREE(ifacedef-data.bridge.delay); -for (int i = 0; i ifacedef-data.bridge.nbItf; i++) { +for (i = 0; i ifacedef-data.bridge.nbItf; i++) { udevIfaceFreeIfaceDef(ifacedef-data.bridge.itf[i]); } VIR_FREE(ifacedef-data.bridge.itf); @@ -547,6 +549,7 @@ udevIfaceGetIfaceDef(struct udev *udev, char *name) char *vlan_parent_dev = NULL; struct dirent **member_list = NULL; int member_count = 0; +int i; /* Allocate our interface definition structure */ if (VIR_ALLOC(ifacedef) 0) { @@ -679,7 +682,7 @@ udevIfaceGetIfaceDef(struct udev *udev, char *name) } ifacedef-data.bridge.nbItf = member_count; -for (int i= 0; i member_count; i++) { +for (i= 0; i member_count; i++) { ifacedef-data.bridge.itf[i] = udevIfaceGetIfaceDef(udev, member_list[i]-d_name); VIR_FREE(member_list[i]); @@ -698,7 +701,7 @@ udevIfaceGetIfaceDef(struct udev *udev, char *name) cleanup: udev_device_unref(dev); -for (int i = 0; i member_count; i++) { +for (i = 0; i member_count; i++) { VIR_FREE(member_list[i]); } VIR_FREE(member_list); -- 1.8.0.1.240.ge8a1f5a -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v1 0/6] disable cgroup cpuset
ping... On Wed, Nov 07, 2012 at 06:38:40PM +0800, Hu Tao wrote: The reason to disable cgroup cpuset by default is: currently, sub-directories of cgroup cpuset won't be auto-updated if cpu hot-plug happens. For example, if we now have 0-3,5-7 pcpus online, the value of /sys/fs/cgroup/cpuset/libvirt/qemu/mydom/cpuset.cpus is 0-3,5-7, then pcpu 4 is hot-plugged, but the value of cpuset.cpus is still 0-3,5-7. This will cause a problem that we can't pin to a hot-plugged pcpu. Users can still enable cpuset by editing qemu.conf. Hu Tao (6): cgroup: Add a flag VIR_CGROUP_DISABLE_CPUSET create cgroup controllers for driver according to config create cgroup controllers for domain according to config create cgroup controllers for vcpu according to config create cgroup controllers for emulator according to config disable cgroup cpuset by default src/lxc/lxc_cgroup.c | 4 +-- src/lxc/lxc_driver.c | 22 ++-- src/lxc/lxc_process.c | 4 +-- src/qemu/qemu.conf| 2 +- src/qemu/qemu_cgroup.c| 15 src/qemu/qemu_conf.c | 1 - src/qemu/qemu_driver.c| 92 +-- src/qemu/qemu_hotplug.c | 9 +++-- src/qemu/qemu_migration.c | 2 +- src/util/cgroup.c | 49 +++-- src/util/cgroup.h | 12 --- 11 files changed, 136 insertions(+), 76 deletions(-) -- 1.7.11.7 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH] run bootstrap if .gnulib is not present
ping... On Fri, Nov 09, 2012 at 04:47:04PM +0800, Hu Tao wrote: If .gnulib is deleted unexpectedly, autogen.sh will fail with message: fatal: ambiguous argument '.gnulib': unknown revision or path not in the working tree. Use '--' to separate paths from revisions, like this: 'git command [revision...] -- [file...]' which is actually given by git diff .gnulib, which doesn't exist. In the case to run bootstrap to create .gnulib. --- autogen.sh | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/autogen.sh b/autogen.sh index d183397..07c58a1 100755 --- a/autogen.sh +++ b/autogen.sh @@ -62,7 +62,9 @@ bootstrap_hash() # Only run bootstrap from a git checkout, never from a tarball. if test -d .git; then curr_status=.git-module-status -t=$(bootstrap_hash; git diff .gnulib) +if test -d .gnulib; then +t=$(bootstrap_hash; git diff .gnulib) +fi case $t:${CLEAN_SUBMODULE+set} in *:set) ;; *-dirty*) -- 1.7.11.7 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH] run bootstrap if .gnulib is not present
On Wed, Nov 21, 2012 at 07:08:54AM -0700, Eric Blake wrote: On 11/09/2012 01:47 AM, Hu Tao wrote: If .gnulib is deleted unexpectedly, autogen.sh will fail with message: fatal: ambiguous argument '.gnulib': unknown revision or path not in the working tree. Use '--' to separate paths from revisions, like this: 'git command [revision...] -- [file...]' which is actually given by git diff .gnulib, which doesn't exist. In the case to run bootstrap to create .gnulib. --- autogen.sh | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/autogen.sh b/autogen.sh index d183397..07c58a1 100755 --- a/autogen.sh +++ b/autogen.sh @@ -62,7 +62,9 @@ bootstrap_hash() # Only run bootstrap from a git checkout, never from a tarball. if test -d .git; then curr_status=.git-module-status -t=$(bootstrap_hash; git diff .gnulib) +if test -d .gnulib; then +t=$(bootstrap_hash; git diff .gnulib) +fi Almost. If .gnulib doesn't exist, then you failed to initialize $t, which could cause problems if it is inherited from the environment or if you run autogen under 'set -u'. ACK and pushed with this tweak. Thanks! -- Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH] run bootstrap if .gnulib is not present
If .gnulib is deleted unexpectedly, autogen.sh will fail with message: fatal: ambiguous argument '.gnulib': unknown revision or path not in the working tree. Use '--' to separate paths from revisions, like this: 'git command [revision...] -- [file...]' which is actually given by git diff .gnulib, which doesn't exist. In the case to run bootstrap to create .gnulib. --- autogen.sh | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/autogen.sh b/autogen.sh index d183397..07c58a1 100755 --- a/autogen.sh +++ b/autogen.sh @@ -62,7 +62,9 @@ bootstrap_hash() # Only run bootstrap from a git checkout, never from a tarball. if test -d .git; then curr_status=.git-module-status -t=$(bootstrap_hash; git diff .gnulib) +if test -d .gnulib; then +t=$(bootstrap_hash; git diff .gnulib) +fi case $t:${CLEAN_SUBMODULE+set} in *:set) ;; *-dirty*) -- 1.7.11.7 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v1 1/6] cgroup: Add a flag VIR_CGROUP_DISABLE_CPUSET
Add a flag VIR_CGROUP_DISABLE_CPUSET to disable cgroup cpuset. This flag inhibits making of directory under cpuset. --- src/util/cgroup.c | 7 +++ 1 file changed, 7 insertions(+) diff --git a/src/util/cgroup.c b/src/util/cgroup.c index 3f7b5f7..2f64f5d 100644 --- a/src/util/cgroup.c +++ b/src/util/cgroup.c @@ -72,6 +72,7 @@ typedef enum { */ VIR_CGROUP_VCPU = 1 1, /* create subdir only under the cgroup cpu, * cpuacct and cpuset if possible. */ +VIR_CGROUP_DISABLE_CPUSET = 1 2, } virCgroupFlags; /** @@ -540,6 +541,12 @@ static int virCgroupMakeGroup(virCgroupPtr parent, virCgroupPtr group, if (!group-controllers[i].mountPoint) continue; +if ((flags VIR_CGROUP_DISABLE_CPUSET) +i == VIR_CGROUP_CONTROLLER_CPUSET) { +group-controllers[i].mountPoint = NULL; +continue; +} + /* We need to control cpu bandwidth for each vcpu now */ if ((flags VIR_CGROUP_VCPU) (i != VIR_CGROUP_CONTROLLER_CPU -- 1.7.11.7 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v1 0/6] disable cgroup cpuset
The reason to disable cgroup cpuset by default is: currently, sub-directories of cgroup cpuset won't be auto-updated if cpu hot-plug happens. For example, if we now have 0-3,5-7 pcpus online, the value of /sys/fs/cgroup/cpuset/libvirt/qemu/mydom/cpuset.cpus is 0-3,5-7, then pcpu 4 is hot-plugged, but the value of cpuset.cpus is still 0-3,5-7. This will cause a problem that we can't pin to a hot-plugged pcpu. Users can still enable cpuset by editing qemu.conf. Hu Tao (6): cgroup: Add a flag VIR_CGROUP_DISABLE_CPUSET create cgroup controllers for driver according to config create cgroup controllers for domain according to config create cgroup controllers for vcpu according to config create cgroup controllers for emulator according to config disable cgroup cpuset by default src/lxc/lxc_cgroup.c | 4 +-- src/lxc/lxc_driver.c | 22 ++-- src/lxc/lxc_process.c | 4 +-- src/qemu/qemu.conf| 2 +- src/qemu/qemu_cgroup.c| 15 src/qemu/qemu_conf.c | 1 - src/qemu/qemu_driver.c| 92 +-- src/qemu/qemu_hotplug.c | 9 +++-- src/qemu/qemu_migration.c | 2 +- src/util/cgroup.c | 49 +++-- src/util/cgroup.h | 12 --- 11 files changed, 136 insertions(+), 76 deletions(-) -- 1.7.11.7 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v1 2/6] create cgroup controllers for driver according to config
Add a parameter to virCgroupForDriver to indicate which cgroup controllers to create. The value of the parameter is read from user config. --- src/lxc/lxc_cgroup.c | 2 +- src/lxc/lxc_driver.c | 2 +- src/qemu/qemu_driver.c | 12 ++-- src/util/cgroup.c | 12 +--- src/util/cgroup.h | 3 ++- 5 files changed, 19 insertions(+), 12 deletions(-) diff --git a/src/lxc/lxc_cgroup.c b/src/lxc/lxc_cgroup.c index bdfaa54..a5e2e97 100644 --- a/src/lxc/lxc_cgroup.c +++ b/src/lxc/lxc_cgroup.c @@ -226,7 +226,7 @@ int virLXCCgroupSetup(virDomainDefPtr def) virCgroupPtr cgroup = NULL; int rc = -1; -rc = virCgroupForDriver(lxc, driver, 1, 0); +rc = virCgroupForDriver(lxc, driver, 1, 0, ~0); if (rc != 0) { /* Skip all if no driver cgroup is configured */ if (rc == -ENXIO || rc == -ENOENT) diff --git a/src/lxc/lxc_driver.c b/src/lxc/lxc_driver.c index 991b593..5401fe7 100644 --- a/src/lxc/lxc_driver.c +++ b/src/lxc/lxc_driver.c @@ -1443,7 +1443,7 @@ static int lxcStartup(int privileged) lxc_driver-log_libvirtd = 0; /* by default log to container logfile */ lxc_driver-have_netns = lxcCheckNetNsSupport(); -rc = virCgroupForDriver(lxc, lxc_driver-cgroup, privileged, 1); +rc = virCgroupForDriver(lxc, lxc_driver-cgroup, privileged, 1, ~0); if (rc 0) { char buf[1024] ATTRIBUTE_UNUSED; VIR_DEBUG(Unable to create cgroup for LXC driver: %s, diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c index 7b8eec6..007fea9 100644 --- a/src/qemu/qemu_driver.c +++ b/src/qemu/qemu_driver.c @@ -740,17 +740,17 @@ qemudStartup(int privileged) { VIR_FREE(base); -rc = virCgroupForDriver(qemu, qemu_driver-cgroup, privileged, 1); -if (rc 0) { -VIR_INFO(Unable to create cgroup for driver: %s, - virStrerror(-rc, ebuf, sizeof(ebuf))); -} - if (qemudLoadDriverConfig(qemu_driver, driverConf) 0) { goto error; } VIR_FREE(driverConf); +rc = virCgroupForDriver(qemu, qemu_driver-cgroup, privileged, 1, qemu_driver-cgroupControllers); +if (rc 0) { +VIR_INFO(Unable to create cgroup for driver: %s, + virStrerror(-rc, ebuf, sizeof(ebuf))); +} + /* Allocate bitmap for remote display port reservations. We cannot * do this before the config is loaded properly, since the port * numbers are configurable now */ diff --git a/src/util/cgroup.c b/src/util/cgroup.c index 2f64f5d..02fc24a 100644 --- a/src/util/cgroup.c +++ b/src/util/cgroup.c @@ -932,11 +932,13 @@ cleanup: int virCgroupForDriver(const char *name, virCgroupPtr *group, int privileged, - int create) + int create, + int controllers) { int rc; char *path = NULL; virCgroupPtr rootgrp = NULL; +unsigned flags = VIR_CGROUP_NONE; rc = virCgroupAppRoot(privileged, rootgrp, create); if (rc != 0) @@ -947,11 +949,14 @@ int virCgroupForDriver(const char *name, goto out; } +if (!(controllers (1UL VIR_CGROUP_CONTROLLER_CPUSET))) +flags |= VIR_CGROUP_DISABLE_CPUSET; + rc = virCgroupNew(path, group); VIR_FREE(path); if (rc == 0) { -rc = virCgroupMakeGroup(rootgrp, *group, create, VIR_CGROUP_NONE); +rc = virCgroupMakeGroup(rootgrp, *group, create, flags); if (rc != 0) virCgroupFree(group); } @@ -965,7 +970,8 @@ out: int virCgroupForDriver(const char *name ATTRIBUTE_UNUSED, virCgroupPtr *group ATTRIBUTE_UNUSED, int privileged ATTRIBUTE_UNUSED, - int create ATTRIBUTE_UNUSED) + int create ATTRIBUTE_UNUSED, + int controllers) { /* Claim no support */ return -ENXIO; diff --git a/src/util/cgroup.h b/src/util/cgroup.h index 38fa4b7..f0945f1 100644 --- a/src/util/cgroup.h +++ b/src/util/cgroup.h @@ -45,7 +45,8 @@ VIR_ENUM_DECL(virCgroupController); int virCgroupForDriver(const char *name, virCgroupPtr *group, int privileged, - int create); + int create, + int controllers); int virCgroupForDomain(virCgroupPtr driver, const char *name, -- 1.7.11.7 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v1 3/6] create cgroup controllers for domain according to config
Add a parameter to virCgroupForDomain to indicate which cgroup controllers to create for domain. The value of the parameter is read from user config. --- src/lxc/lxc_cgroup.c | 2 +- src/lxc/lxc_driver.c | 20 +- src/lxc/lxc_process.c | 4 ++-- src/qemu/qemu_cgroup.c| 10 - src/qemu/qemu_driver.c| 53 ++- src/qemu/qemu_hotplug.c | 9 +--- src/qemu/qemu_migration.c | 2 +- src/util/cgroup.c | 9 ++-- src/util/cgroup.h | 3 ++- 9 files changed, 68 insertions(+), 44 deletions(-) diff --git a/src/lxc/lxc_cgroup.c b/src/lxc/lxc_cgroup.c index a5e2e97..b636db7 100644 --- a/src/lxc/lxc_cgroup.c +++ b/src/lxc/lxc_cgroup.c @@ -237,7 +237,7 @@ int virLXCCgroupSetup(virDomainDefPtr def) return rc; } -rc = virCgroupForDomain(driver, def-name, cgroup, 1); +rc = virCgroupForDomain(driver, def-name, cgroup, 1, ~0); if (rc != 0) { virReportSystemError(-rc, _(Unable to create cgroup for domain %s), diff --git a/src/lxc/lxc_driver.c b/src/lxc/lxc_driver.c index 5401fe7..8a08404 100644 --- a/src/lxc/lxc_driver.c +++ b/src/lxc/lxc_driver.c @@ -541,7 +541,7 @@ static int lxcDomainGetInfo(virDomainPtr dom, info-cpuTime = 0; info-memory = vm-def-mem.cur_balloon; } else { -if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(Unable to get cgroup for %s), vm-def-name); goto cleanup; @@ -734,7 +734,7 @@ static int lxcDomainSetMemory(virDomainPtr dom, unsigned long newmem) { goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(Unable to get cgroup for %s), vm-def-name); goto cleanup; @@ -791,7 +791,7 @@ lxcDomainSetMemoryParameters(virDomainPtr dom, goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(cannot find cgroup for domain %s), vm-def-name); goto cleanup; @@ -868,7 +868,7 @@ lxcDomainGetMemoryParameters(virDomainPtr dom, goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(Unable to get cgroup for %s), vm-def-name); goto cleanup; @@ -1810,7 +1810,7 @@ lxcSetSchedulerParametersFlags(virDomainPtr dom, %s, _(cgroup CPU controller is not mounted)); goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(cannot find cgroup for domain %s), vm-def-name); @@ -1954,7 +1954,7 @@ lxcGetSchedulerParametersFlags(virDomainPtr dom, goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(cannot find cgroup for domain %s), vm-def-name); goto cleanup; @@ -2059,7 +2059,7 @@ lxcDomainSetBlkioParameters(virDomainPtr dom, goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(cannot find cgroup for domain %s), vm-def-name); goto cleanup; @@ -2164,7 +2164,7 @@ lxcDomainGetBlkioParameters(virDomainPtr dom, goto cleanup; } -if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0) != 0) { +if (virCgroupForDomain(driver-cgroup, vm-def-name, group, 0, ~0) != 0) { virReportError(VIR_ERR_INTERNAL_ERROR, _(cannot find cgroup for domain %s), vm-def-name); goto cleanup; @@ -2398,7 +2398,7 @@ static int lxcFreezeContainer(virLXCDriverPtr driver, virDomainObjPtr vm) virCgroupPtr cgroup = NULL; if (!(driver-cgroup - virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0) == 0)) + virCgroupForDomain(driver-cgroup, vm-def-name, cgroup, 0, ~0) == 0))
[libvirt] [PATCH v1 6/6] disable cgroup cpuset by default
The reason to disable cgroup cpuset by default is: currently, sub-directories of cgroup cpuset won't be auto-updated if cpu hot-plug happens. For example, if we now have 0-3,5-7 pcpus online, the value of /sys/fs/cgroup/cpuset/libvirt/qemu/mydom/cpuset.cpus is 0-3,5-7, then pcpu 4 is hot-plugged, but the value of cpuset.cpus is still 0-3,5-7. This will cause a problem that we can't pin to a hot-plugged pcpu. Users can still enable cpuset by editing qemu.conf. --- src/qemu/qemu.conf | 2 +- src/qemu/qemu_conf.c | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/src/qemu/qemu.conf b/src/qemu/qemu.conf index dd853c8..b853852 100644 --- a/src/qemu/qemu.conf +++ b/src/qemu/qemu.conf @@ -226,7 +226,7 @@ # can be mounted in different locations. libvirt will detect # where they are located. # -#cgroup_controllers = [ cpu, devices, memory, blkio, cpuset, cpuacct ] +#cgroup_controllers = [ cpu, devices, memory, blkio, cpuacct ] # This is the basic set of devices allowed / required by # all virtual machines. diff --git a/src/qemu/qemu_conf.c b/src/qemu/qemu_conf.c index dc4d680..92c1864 100644 --- a/src/qemu/qemu_conf.c +++ b/src/qemu/qemu_conf.c @@ -402,7 +402,6 @@ int qemudLoadDriverConfig(struct qemud_driver *driver, (1 VIR_CGROUP_CONTROLLER_DEVICES) | (1 VIR_CGROUP_CONTROLLER_MEMORY) | (1 VIR_CGROUP_CONTROLLER_BLKIO) | -(1 VIR_CGROUP_CONTROLLER_CPUSET) | (1 VIR_CGROUP_CONTROLLER_CPUACCT); } for (i = 0 ; i VIR_CGROUP_CONTROLLER_LAST ; i++) { -- 1.7.11.7 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v1 4/6] create cgroup controllers for vcpu according to config
Add a parameter to virCgroupForVcpu to indicate which cgroup controllers to create. The value of the parameter is read from user config. --- src/qemu/qemu_cgroup.c | 3 ++- src/qemu/qemu_driver.c | 18 -- src/util/cgroup.c | 9 +++-- src/util/cgroup.h | 3 ++- 4 files changed, 23 insertions(+), 10 deletions(-) diff --git a/src/qemu/qemu_cgroup.c b/src/qemu/qemu_cgroup.c index ba54a68..04a2c08 100644 --- a/src/qemu/qemu_cgroup.c +++ b/src/qemu/qemu_cgroup.c @@ -576,7 +576,8 @@ int qemuSetupCgroupForVcpu(struct qemud_driver *driver, virDomainObjPtr vm) } for (i = 0; i priv-nvcpupids; i++) { -rc = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 1); +rc = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 1, + driver-cgroupControllers); if (rc 0) { virReportSystemError(-rc, _(Unable to create vcpu cgroup for %s(vcpu: diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c index cc532c7..dcaa693 100644 --- a/src/qemu/qemu_driver.c +++ b/src/qemu/qemu_driver.c @@ -3716,7 +3716,8 @@ static int qemudDomainHotplugVcpus(struct qemud_driver *driver, if (cgroup_available) { int rv = -1; /* Create cgroup for the onlined vcpu */ -rv = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 1); +rv = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 1, + driver-cgroupControllers); if (rv 0) { virReportSystemError(-rv, _(Unable to create vcpu cgroup for %s(vcpu: @@ -3790,7 +3791,8 @@ static int qemudDomainHotplugVcpus(struct qemud_driver *driver, if (cgroup_available) { int rv = -1; -rv = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 0); +rv = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 0, + driver-cgroupControllers); if (rv 0) { virReportSystemError(-rv, _(Unable to access vcpu cgroup for %s(vcpu: @@ -4037,7 +4039,8 @@ qemudDomainPinVcpuFlags(virDomainPtr dom, if (qemuCgroupControllerActive(driver, VIR_CGROUP_CONTROLLER_CPUSET)) { if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup_dom, 0, driver-cgroupControllers) == 0 -virCgroupForVcpu(cgroup_dom, vcpu, cgroup_vcpu, 0) == 0 +virCgroupForVcpu(cgroup_dom, vcpu, cgroup_vcpu, 0, + driver-cgroupControllers) == 0 qemuSetupCgroupVcpuPin(cgroup_vcpu, newVcpuPin, newVcpuPinNum, vcpu) 0) { virReportError(VIR_ERR_OPERATION_INVALID, _(failed to set cpuset.cpus in cgroup @@ -7897,7 +7900,8 @@ qemuSetVcpusBWLive(virDomainObjPtr vm, virCgroupPtr cgroup, */ if (priv-nvcpupids != 0 priv-vcpupids[0] != vm-pid) { for (i = 0; i priv-nvcpupids; i++) { -rc = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 0); +rc = virCgroupForVcpu(cgroup, i, cgroup_vcpu, 0, + qemu_driver-cgroupControllers); if (rc 0) { virReportSystemError(-rc, _(Unable to find vcpu cgroup for %s(vcpu: @@ -8188,7 +8192,8 @@ qemuGetVcpusBWLive(virDomainObjPtr vm, virCgroupPtr cgroup, } /* get period and quota for vcpu0 */ -rc = virCgroupForVcpu(cgroup, 0, cgroup_vcpu, 0); +rc = virCgroupForVcpu(cgroup, 0, cgroup_vcpu, 0, + qemu_driver-cgroupControllers); if (!cgroup_vcpu) { virReportSystemError(-rc, _(Unable to find vcpu cgroup for %s(vcpu: 0)), @@ -14110,7 +14115,8 @@ getSumVcpuPercpuStats(virCgroupPtr group, unsigned long long tmp; int j; -if (virCgroupForVcpu(group, i, group_vcpu, 0) 0) { +if (virCgroupForVcpu(group, i, group_vcpu, 0, + qemu_driver-cgroupControllers) 0) { virReportError(VIR_ERR_INTERNAL_ERROR, %s, _(error accessing cgroup cpuacct for vcpu)); goto cleanup; diff --git a/src/util/cgroup.c b/src/util/cgroup.c index d07a66a..b43933e 100644 --- a/src/util/cgroup.c +++ b/src/util/cgroup.c @@ -1052,14 +1052,19 @@ int virCgroupForDomain(virCgroupPtr driver ATTRIBUTE_UNUSED, int virCgroupForVcpu(virCgroupPtr driver, int vcpuid, virCgroupPtr *group, - int create) + int create, + int controllers) { +unsigned flags = VIR_CGROUP_VCPU; int rc; char *path; if (driver == NULL) return -EINVAL; +if (!(controllers (1UL VIR_CGROUP_CONTROLLER_CPUSET))) +
[libvirt] [PATCH v1 5/6] create cgroup controllers for emulator according to config
Add a parameter to virCgroupForEmulator to indicate which cgroup controllers to create. The value of the parameter is read from user config. --- src/qemu/qemu_cgroup.c | 2 +- src/qemu/qemu_driver.c | 9 ++--- src/util/cgroup.c | 12 +--- src/util/cgroup.h | 3 ++- 4 files changed, 18 insertions(+), 8 deletions(-) diff --git a/src/qemu/qemu_cgroup.c b/src/qemu/qemu_cgroup.c index 04a2c08..69320e4 100644 --- a/src/qemu/qemu_cgroup.c +++ b/src/qemu/qemu_cgroup.c @@ -670,7 +670,7 @@ int qemuSetupCgroupForEmulator(struct qemud_driver *driver, goto cleanup; } -rc = virCgroupForEmulator(cgroup, cgroup_emulator, 1); +rc = virCgroupForEmulator(cgroup, cgroup_emulator, 1, driver-cgroupControllers); if (rc 0) { virReportSystemError(-rc, _(Unable to create emulator cgroup for %s), diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c index dcaa693..e9985e8 100644 --- a/src/qemu/qemu_driver.c +++ b/src/qemu/qemu_driver.c @@ -4306,7 +4306,8 @@ qemudDomainPinEmulator(virDomainPtr dom, */ if (virCgroupForDomain(driver-cgroup, vm-def-name, cgroup_dom, 0, driver-cgroupControllers) == 0) { -if (virCgroupForEmulator(cgroup_dom, cgroup_emulator, 0) == 0) { +if (virCgroupForEmulator(cgroup_dom, cgroup_emulator, 0, + driver-cgroupControllers) == 0) { if (qemuSetupCgroupEmulatorPin(cgroup_emulator, newVcpuPin[0]-cpumask) 0) { virReportError(VIR_ERR_OPERATION_INVALID, %s, @@ -7939,7 +7940,8 @@ qemuSetEmulatorBandwidthLive(virDomainObjPtr vm, virCgroupPtr cgroup, return 0; } -rc = virCgroupForEmulator(cgroup, cgroup_emulator, 0); +rc = virCgroupForEmulator(cgroup, cgroup_emulator, 0, + qemu_driver-cgroupControllers); if (rc 0) { virReportSystemError(-rc, _(Unable to find emulator cgroup for %s), @@ -8231,7 +8233,8 @@ qemuGetEmulatorBandwidthLive(virDomainObjPtr vm, virCgroupPtr cgroup, } /* get period and quota for emulator */ -rc = virCgroupForEmulator(cgroup, cgroup_emulator, 0); +rc = virCgroupForEmulator(cgroup, cgroup_emulator, 0, + qemu_driver-cgroupControllers); if (!cgroup_emulator) { virReportSystemError(-rc, _(Unable to find emulator cgroup for %s), diff --git a/src/util/cgroup.c b/src/util/cgroup.c index b43933e..d069bf5 100644 --- a/src/util/cgroup.c +++ b/src/util/cgroup.c @@ -1100,14 +1100,19 @@ int virCgroupForVcpu(virCgroupPtr driver ATTRIBUTE_UNUSED, #if defined HAVE_MNTENT_H defined HAVE_GETMNTENT_R int virCgroupForEmulator(virCgroupPtr driver, virCgroupPtr *group, - int create) + int create, + int controllers) { +unsigned flags = VIR_CGROUP_VCPU; int rc; char *path; if (driver == NULL) return -EINVAL; +if (!(controllers (1UL VIR_CGROUP_CONTROLLER_CPUSET))) +flags |= VIR_CGROUP_DISABLE_CPUSET; + if (virAsprintf(path, %s/emulator, driver-path) 0) return -ENOMEM; @@ -1115,7 +1120,7 @@ int virCgroupForEmulator(virCgroupPtr driver, VIR_FREE(path); if (rc == 0) { -rc = virCgroupMakeGroup(driver, *group, create, VIR_CGROUP_VCPU); +rc = virCgroupMakeGroup(driver, *group, create, flags); if (rc != 0) virCgroupFree(group); } @@ -1125,7 +1130,8 @@ int virCgroupForEmulator(virCgroupPtr driver, #else int virCgroupForEmulator(virCgroupPtr driver ATTRIBUTE_UNUSED, virCgroupPtr *group ATTRIBUTE_UNUSED, - int create ATTRIBUTE_UNUSED) + int create ATTRIBUTE_UNUSED, + int controllers ATTRIBUTE_UNUSED) { return -ENXIO; } diff --git a/src/util/cgroup.h b/src/util/cgroup.h index dc0811a..e3bdc9b 100644 --- a/src/util/cgroup.h +++ b/src/util/cgroup.h @@ -62,7 +62,8 @@ int virCgroupForVcpu(virCgroupPtr driver, int virCgroupForEmulator(virCgroupPtr driver, virCgroupPtr *group, - int create); + int create, + int controllers); int virCgroupPathOfController(virCgroupPtr group, int controller, -- 1.7.11.7 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCHv2 3/3] virsh: Use virNodeGetCPUMap if possible
On Wed, Oct 31, 2012 at 06:20:58PM +0100, Viktor Mihajlovski wrote: Modified the places where virNodeGetInfo was used for the purpose of obtaining the maximum node CPU number. Transparently falling back to virNodeGetInfo in case of failure. Wrote utility function vshNodeGetCPUCount to compute node CPU number. Signed-off-by: Viktor Mihajlovski mihaj...@linux.vnet.ibm.com --- V2 Changes: Implemented Eric Blake's suggestion to remove code bloat introduced by first patch version. New helper function vshNodeGetCPUCount is now used to calculate the number of node CPUs. tools/virsh-domain.c | 32 +++- 1 file changed, 23 insertions(+), 9 deletions(-) diff --git a/tools/virsh-domain.c b/tools/virsh-domain.c index 255669f..59289f1 100644 --- a/tools/virsh-domain.c +++ b/tools/virsh-domain.c @@ -126,6 +126,26 @@ vshDomainVcpuStateToString(int state) } /* + * Determine number of CPU nodes present by trying + * virNodeGetCPUMap and falling back to virNodeGetInfo + * if needed. + */ +static int +vshNodeGetCPUCount(virConnectPtr conn) +{ +int ret; +virNodeInfo nodeinfo; + +if ((ret = virNodeGetCPUMap(conn, NULL, NULL, 0)) 0) { +/* fall back to nodeinfo */ +if (virNodeGetInfo(conn, nodeinfo) == 0) { +ret = VIR_NODEINFO_MAXCPUS(nodeinfo); +} Isn't VIR_NODEINFO_MAXCPUS buggy? Either don't fall back to nodeinfo or fix it. -- Thanks, Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH] [DRAFT] handle qemu event GUEST_PANICKED
This is for early review, comments are welcome! qemu is adding a method to detect guest panic, and a new event GUEST_PANICKED[1]. This patch adds support for GUEST_PANICKED. But I have two questions: - to react to GUEST_PANICKED, can xml element on_crash be used as the action to take, or do I have to invent another xml element to configure the action? - Currently libvirt relies on watchdog to detect guest panic, but this way is not that reliable(there has to be a watchdog device, the watchdog itself has to be working when panic occurs), so it seems to be appropriate to remove this method from libvirt as there is a better one. But, will the removal cause any problems, such as backward compatibility, user confusion, etc.? [1] http://lists.nongnu.org/archive/html/qemu-devel/2012-10/msg04361.html --- src/qemu/qemu_command.c | 31 --- src/qemu/qemu_monitor.c | 10 ++ src/qemu/qemu_monitor.h |3 +++ src/qemu/qemu_monitor_json.c |9 + src/qemu/qemu_process.c |9 + 5 files changed, 51 insertions(+), 11 deletions(-) diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c index 898c4c0..0c3f9ff 100644 --- a/src/qemu/qemu_command.c +++ b/src/qemu/qemu_command.c @@ -4300,6 +4300,9 @@ qemuBuildMachineArgStr(virCommandPtr cmd, const virDomainDefPtr def, qemuCapsPtr caps) { +virBuffer params = VIR_BUFFER_INITIALIZER; +char *tmp = NULL; + /* This should *never* be NULL, since we always provide * a machine in the capabilities data for QEMU. So this * check is just here as a safety in case the unexpected @@ -4307,29 +4310,35 @@ qemuBuildMachineArgStr(virCommandPtr cmd, if (!def-os.machine) return 0; -if (!def-mem.dump_core) { -/* if no parameter to the machine type is needed, we still use - * '-M' to keep the most of the compatibility with older versions. - */ -virCommandAddArgList(cmd, -M, def-os.machine, NULL); -} else { +virBufferAsprintf(params, ,enable_pv_event=on); + +if (def-mem.dump_core) { if (!qemuCapsGet(caps, QEMU_CAPS_DUMP_GUEST_CORE)) { virReportError(VIR_ERR_CONFIG_UNSUPPORTED, %s, _(dump-guest-core is not available with this QEMU binary)); return -1; } +virBufferAsprintf(params,,%s, + virDomainMemDumpTypeToString(def-mem.dump_core)); +} -/* However, in case there is a parameter to be added, we need to +tmp = virBufferContentAndReset(params); +if (!tmp || strlen(tmp) == 0) { +/* if no parameter to the machine type is needed, we still use + * '-M' to keep the most of the compatibility with older versions. + */ +virCommandAddArgList(cmd, -M, def-os.machine, NULL); +} else { +/* However, in case there are parameters to be added, we need to * use the -machine parameter because qemu is not parsing the * -M correctly */ virCommandAddArg(cmd, -machine); -virCommandAddArgFormat(cmd, - %s,dump-guest-core=%s, - def-os.machine, - virDomainMemDumpTypeToString(def-mem.dump_core)); +virCommandAddArgFormat(cmd, %s%s, def-os.machine, tmp); } +VIR_FREE(tmp); + return 0; } diff --git a/src/qemu/qemu_monitor.c b/src/qemu/qemu_monitor.c index 2d9c44c..8ab7ed2 100644 --- a/src/qemu/qemu_monitor.c +++ b/src/qemu/qemu_monitor.c @@ -1146,6 +1146,16 @@ int qemuMonitorEmitBalloonChange(qemuMonitorPtr mon, } +int qemuMonitorEmitPanic(qemuMonitorPtr mon) +{ +int ret = -1; +VIR_DEBUG(mon=%p, mon); + +QEMU_MONITOR_CALLBACK(mon, ret, domainPanic, mon-vm); +return ret; +} + + int qemuMonitorSetCapabilities(qemuMonitorPtr mon) { int ret; diff --git a/src/qemu/qemu_monitor.h b/src/qemu/qemu_monitor.h index 8856d9f..ea0a474 100644 --- a/src/qemu/qemu_monitor.h +++ b/src/qemu/qemu_monitor.h @@ -138,6 +138,8 @@ struct _qemuMonitorCallbacks { unsigned long long actual); int (*domainPMSuspendDisk)(qemuMonitorPtr mon, virDomainObjPtr vm); +int (*domainPanic)(qemuMonitorPtr mon, + virDomainObjPtr vm); }; char *qemuMonitorEscapeArg(const char *in); @@ -216,6 +218,7 @@ int qemuMonitorEmitBlockJob(qemuMonitorPtr mon, int qemuMonitorEmitBalloonChange(qemuMonitorPtr mon, unsigned long long actual); int qemuMonitorEmitPMSuspendDisk(qemuMonitorPtr mon); +int qemuMonitorEmitPanic(qemuMonitorPtr mon); int qemuMonitorStartCPUs(qemuMonitorPtr mon, virConnectPtr conn); diff --git a/src/qemu/qemu_monitor_json.c
[libvirt] [RFC][PATCH] change the meaning of vnc port in xml
Now the vnc port in xml file reflects the REAL port hypervisor will listen on for vnc connection. But vnc ports usually start from 5900, it's common to say 0 for 5900, 1 for 5901, and so on. This patch forbids negative vnc port number in xml, and maps port number below 5900 to 5900+port, but no change to those greater than 5900. --- I have no idea whether this behaviour is sane or not. But my vnc client(vinagre) has the same behaviour, i.e., treats port 0 as 5900, 1 as 5901, but 5900 as 5900, 5901 as 5901. src/conf/domain_conf.c |6 ++ 1 file changed, 6 insertions(+) diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c index 0cea8eb..b3cbc34 100644 --- a/src/conf/domain_conf.c +++ b/src/conf/domain_conf.c @@ -6423,6 +6423,12 @@ virDomainGraphicsDefParseXML(xmlNodePtr node, if (flags VIR_DOMAIN_XML_INACTIVE) def-data.vnc.port = 0; def-data.vnc.autoport = 1; +} else if (def-data.vnc.port 0) { +virReportError(VIR_ERR_XML_ERROR, + _(invalid vnc port %s), port); +goto error; +} else if (def-data.vnc.port 5900) { +def-data.vnc.port += 5900; } } else { def-data.vnc.port = 0; -- 1.7.10.2 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH] RFC: Clarify the relationship between vcpu, vcpupin, and emulatorpin
and virtual CPUs can be specified separately by +codecputune/code. If attribute codeemulatorpin/code +of codecputune/code is specified, codecpuset/code +specified by codevcpu/code here will be ingored; Similarly, +For virtual CPUs which has codevcpupin/code specified, +codecpuset/code specified by codecpuset/code here +will be ignored; For virtual CPUs which doesn't have +codevcpupin/code specified, it will be pinned to the physical +CPUs specified by codecpuset/code here). +Each element in that list is either a single CPU number, a range of CPU numbers, or a caret followed by a CPU number to be excluded from a previous range. span class=sinceSince 0.8.5/span, the optional attribute codecurrent/code can @@ -374,8 +384,7 @@ if it's specified. If both codecpuset/code and codeplacement/code are not specified, or if codeplacement/code is static, but no codecpuset/code is specified, the domain process will be pinned to -all the available physical CPUs. These settings are superseded -by a href=#elementsCPUTuningCPU tuning/a. +all the available physical CPUs. /dd /dl @@ -411,23 +420,26 @@ dtcodevcpupin/code/dt dd The optional codevcpupin/code element specifies which of host's -physical CPUs the domain VCPU will be pinned to. This setting supersedes -previous VCPU placement specified in a href=#elementsCPUAllocationCPU -Allocation/a using codevcpu/code element. If this is omitted, -each VCPU is pinned to all the physical CPUs by default. It contains two -required attributes, the attribute codevcpu/code specifies vcpu id, -and the attribute codecpuset/code is same as -attribute codecpuset/code -of element codevcpu/code. (NB: Only qemu driver support) +physical CPUs the domain VCPU will be pinned to. If this is omitted, +and attribute codecpuset/code of element codevcpu/code is +not specified, the vCPU is pinned to all the physical CPUs by default. +It contains two required attributes, the attribute codevcpu/code +specifies vcpu id, and the attribute codecpuset/code is same as +attribute codecpuset/code of element codevcpu/code. +(NB: Only qemu driver support) span class=sinceSince 0.9.0/span /dd dtcodeemulatorpin/code/dt dd The optional codeemulatorpin/code element specifies which of host physical CPUs the emulator, a subset of a domain not including vcpu, - will be pinned to. If this is omitted, emulator is pinned to all - the physical CPUs by default. It contains one required attribute - codecpuset/code specifying which physical CPUs to pin to. + will be pinned to. If this is omitted, and attribute + codecpuset/code of element codevcpu/code is not specified, + emulator is pinned to all the physical CPUs by default. It contains + one required attribute codecpuset/code specifying which physical + CPUs to pin to. NB, codeemulatorpin/code is not allowed if + attribute codeplacement/code of element codevcpu/code is + auto. /dd dtcodeshares/code/dt dd -- 1.7.7.6 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list -- Thanks, Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v4 9/9] remove virDomainCpuSetFormat and virDomainCpuSetParse
On Mon, Sep 17, 2012 at 03:04:40PM -0400, Laine Stump wrote: On 09/14/2012 07:24 AM, Daniel P. Berrange wrote: On Fri, Sep 14, 2012 at 03:47:04PM +0800, Hu Tao wrote: virBitmap is recommanded to store cpuset info, and virBitmapFormat/virBitmapParse can do the format/parse jobs. --- src/conf/domain_conf.c | 196 -- src/conf/domain_conf.h |7 -- src/libvirt_private.syms |2 - 3 files changed, 205 deletions(-) ACK Daniel I actually needed to add a PATCH 8.5/9 that removed two remaining uses of virDomainCpuSetParse/virDomainCpuSetFormat from xen in order to get this to build successfully. Since that is really a separate deal from this patch's purpose of removing virDomainCpuSet*, I left it as a separate patch (but pushed it prior to this one). Pushed. Thanks for pushing and other patches modifications to make the series build! -- Thanks, Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH v3 2/9] New functions for virBitmap
On Thu, Sep 13, 2012 at 02:35:03PM +0100, Daniel P. Berrange wrote: On Thu, Sep 13, 2012 at 02:03:20PM +0800, Hu Tao wrote: In many places we store bitmap info in a chunk of data (pointed to by a char *), and have redundant codes to set/unset bits. This patch extends virBitmap, and convert those codes to use virBitmap in subsequent patches. --- .gitignore |1 + src/libvirt_private.syms | 11 ++ src/util/bitmap.c| 405 +- src/util/bitmap.h| 34 tests/Makefile.am|7 +- tests/virbitmaptest.c| 362 + 6 files changed, 818 insertions(+), 2 deletions(-) create mode 100644 tests/virbitmaptest.c diff --git a/.gitignore b/.gitignore index d998f0e..1ca537e 100644 --- a/.gitignore +++ b/.gitignore @@ -157,6 +157,7 @@ /tests/utiltest /tests/viratomictest /tests/virauthconfigtest +/tests/virbitmaptest /tests/virbuftest /tests/virdrivermoduletest /tests/virhashtest diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 8dfb4ce..0ad6376 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -7,12 +7,23 @@ # bitmap.h virBitmapAlloc; +virBitmapAllocFromData; Hmm, can you rename the existing method 'virBitmapNew' and then call you addition 'virBitmapNewData' OK. I will send v4 to address this. -- Thanks, Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH] fix memory leak in virCopyLastError
memset before virResetError will cause memory leak. virResetError and virCopyError, which calls virResetError, will do memset properly, so we don't have to worry about it here. --- src/util/virterror.c |2 -- 1 file changed, 2 deletions(-) diff --git a/src/util/virterror.c b/src/util/virterror.c index 7caa69e..46afd37 100644 --- a/src/util/virterror.c +++ b/src/util/virterror.c @@ -276,8 +276,6 @@ int virCopyLastError(virErrorPtr to) { virErrorPtr err = virLastErrorObject(); -/* We can't guarantee caller has initialized it to zero */ -memset(to, 0, sizeof(*to)); if (err) virCopyError(err, to); else -- 1.7.10.2 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v4 1/9] bitmap: new member variable and function renaming
Add a new member variable map_len to store map len of bitmap. and rename size to max_bit accordingly. rename virBitmapAlloc to virBitmapNew. --- src/conf/domain_conf.c |2 +- src/conf/snapshot_conf.c |2 +- src/libvirt_private.syms |2 +- src/qemu/qemu_capabilities.c |2 +- src/qemu/qemu_driver.c |2 +- src/util/bitmap.c| 30 +- src/util/bitmap.h|2 +- tools/virsh-domain.c |2 +- 8 files changed, 20 insertions(+), 24 deletions(-) diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c index 292cc9a..3a44432 100644 --- a/src/conf/domain_conf.c +++ b/src/conf/domain_conf.c @@ -8871,7 +8871,7 @@ static virDomainDefPtr virDomainDefParseXML(virCapsPtr caps, if (STREQ(def-os.type, hvm)) { if (virDomainDefParseBootXML(ctxt, def, bootMapSize) 0) goto error; -if (bootMapSize !(bootMap = virBitmapAlloc(bootMapSize))) +if (bootMapSize !(bootMap = virBitmapNew(bootMapSize))) goto no_memory; } diff --git a/src/conf/snapshot_conf.c b/src/conf/snapshot_conf.c index e13cdd6..ba5b188 100644 --- a/src/conf/snapshot_conf.c +++ b/src/conf/snapshot_conf.c @@ -357,7 +357,7 @@ virDomainSnapshotAlignDisks(virDomainSnapshotDefPtr def, goto cleanup; } -if (!(map = virBitmapAlloc(def-dom-ndisks))) { +if (!(map = virBitmapNew(def-dom-ndisks))) { virReportOOMError(); goto cleanup; } diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 8dfb4ce..557fa0e 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -6,11 +6,11 @@ # # bitmap.h -virBitmapAlloc; virBitmapClearBit; virBitmapCopy; virBitmapFree; virBitmapGetBit; +virBitmapNew; virBitmapSetBit; virBitmapString; diff --git a/src/qemu/qemu_capabilities.c b/src/qemu/qemu_capabilities.c index ed85b6f..cf9de69 100644 --- a/src/qemu/qemu_capabilities.c +++ b/src/qemu/qemu_capabilities.c @@ -1649,7 +1649,7 @@ qemuCapsNew(void) { virBitmapPtr caps; -if (!(caps = virBitmapAlloc(QEMU_CAPS_LAST))) +if (!(caps = virBitmapNew(QEMU_CAPS_LAST))) virReportOOMError(); return caps; diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c index a410521..7a8b475 100644 --- a/src/qemu/qemu_driver.c +++ b/src/qemu/qemu_driver.c @@ -696,7 +696,7 @@ qemudStartup(int privileged) { * do this before the config is loaded properly, since the port * numbers are configurable now */ if ((qemu_driver-reservedRemotePorts = - virBitmapAlloc(qemu_driver-remotePortMax - qemu_driver-remotePortMin)) == NULL) + virBitmapNew(qemu_driver-remotePortMax - qemu_driver-remotePortMin)) == NULL) goto out_of_memory; /* We should always at least have the 'nop' manager, so diff --git a/src/util/bitmap.c b/src/util/bitmap.c index cd52802..dc9c28a 100644 --- a/src/util/bitmap.c +++ b/src/util/bitmap.c @@ -36,7 +36,8 @@ struct _virBitmap { -size_t size; +size_t max_bit; +size_t map_len; unsigned long *map; }; @@ -48,7 +49,7 @@ struct _virBitmap { /** - * virBitmapAlloc: + * virBitmapNew: * @size: number of bits * * Allocate a bitmap capable of containing @size bits. @@ -56,7 +57,7 @@ struct _virBitmap { * Returns a pointer to the allocated bitmap or NULL if * memory cannot be allocated. */ -virBitmapPtr virBitmapAlloc(size_t size) +virBitmapPtr virBitmapNew(size_t size) { virBitmapPtr bitmap; size_t sz; @@ -75,7 +76,8 @@ virBitmapPtr virBitmapAlloc(size_t size) return NULL; } -bitmap-size = size; +bitmap-max_bit = size; +bitmap-map_len = sz; return bitmap; } @@ -83,7 +85,7 @@ virBitmapPtr virBitmapAlloc(size_t size) * virBitmapFree: * @bitmap: previously allocated bitmap * - * Free @bitmap previously allocated by virBitmapAlloc. + * Free @bitmap previously allocated by virBitmapNew. */ void virBitmapFree(virBitmapPtr bitmap) { @@ -96,17 +98,12 @@ void virBitmapFree(virBitmapPtr bitmap) int virBitmapCopy(virBitmapPtr dst, virBitmapPtr src) { -size_t sz; - -if (dst-size != src-size) { +if (dst-max_bit != src-max_bit) { errno = EINVAL; return -1; } -sz = (src-size + VIR_BITMAP_BITS_PER_UNIT - 1) / -VIR_BITMAP_BITS_PER_UNIT; - -memcpy(dst-map, src-map, sz * sizeof(src-map[0])); +memcpy(dst-map, src-map, src-map_len * sizeof(src-map[0])); return 0; } @@ -123,7 +120,7 @@ int virBitmapCopy(virBitmapPtr dst, virBitmapPtr src) */ int virBitmapSetBit(virBitmapPtr bitmap, size_t b) { -if (bitmap-size = b) +if (bitmap-max_bit = b) return -1; bitmap-map[VIR_BITMAP_UNIT_OFFSET(b)] |= VIR_BITMAP_BIT(b); @@ -141,7 +138,7 @@ int virBitmapSetBit(virBitmapPtr bitmap, size_t b) */ int virBitmapClearBit(virBitmapPtr bitmap, size_t b) { -if (bitmap-size = b) +if (bitmap-max_bit = b)
[libvirt] [PATCH v4 0/9] improve virBitmap
In many places we store bitmap info in a chunk of data (pointed to by a char *), and have redundant codes to set/unset bits. This series extends virBitmap, and convert those codes to use virBitmap. changes: v4: - rename virBitmapAlloc to virBitmapNew - rename virBitmapAllocFromData to virBitmapNewData v3: - renaming member variables of virBitmap - rewrite virBitmapFormat using virBitmapNextSetBit - store bits in machine native endian format - more tests of virBitmap v2: - fix bug in qemuSetupCgroupForEmulator - new function virBitmapNextSetBit - virBitmapcmp - virBitmapEqual - virBitmap: store bits in little endian format - some improvements of virBitmap - fix some memory leaks Hu Tao (9): bitmap: new member variable and function renaming New functions for virBitmap use virBitmap to store cpupin info use virBitmap to store cpu affinity info use virBitmap to store numa nodemask info. use virBitmap to store cpumask info. use virBitmap to store cells' cpumask info. use virBitmap to store nodeinfo. remove virDomainCpuSetFormat and virDomainCpuSetParse .gitignore |1 + src/conf/cpu_conf.c | 17 +- src/conf/cpu_conf.h |3 +- src/conf/domain_conf.c | 394 ++ src/conf/domain_conf.h | 18 +- src/conf/snapshot_conf.c |2 +- src/libvirt_private.syms | 16 +- src/lxc/lxc_controller.c | 56 +++-- src/nodeinfo.c | 26 +-- src/nodeinfo.h |6 +- src/parallels/parallels_driver.c |5 +- src/qemu/qemu_capabilities.c |2 +- src/qemu/qemu_cgroup.c | 10 +- src/qemu/qemu_cgroup.h |2 +- src/qemu/qemu_command.c | 43 +--- src/qemu/qemu_driver.c | 170 +++ src/qemu/qemu_process.c | 141 src/test/test_driver.c |5 +- src/util/bitmap.c| 435 -- src/util/bitmap.h| 36 +++- src/util/processinfo.c | 36 ++-- src/util/processinfo.h |9 +- src/vmx/vmx.c| 36 ++-- tests/Makefile.am|7 +- tests/cpuset |2 +- tests/virbitmaptest.c| 362 +++ tools/virsh-domain.c |2 +- 27 files changed, 1136 insertions(+), 706 deletions(-) create mode 100644 tests/virbitmaptest.c -- 1.7.10.2 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
Re: [libvirt] [PATCH] fix memory leak in virCopyLastError
On Fri, Sep 14, 2012 at 03:10:13PM +0800, Daniel Veillard wrote: On Fri, Sep 14, 2012 at 02:24:15PM +0800, Hu Tao wrote: memset before virResetError will cause memory leak. virResetError and virCopyError, which calls virResetError, will do memset properly, so we don't have to worry about it here. Disagree, it's a public API, we can't justify behaviour just on how it is used internally. NACK, at least the explanation need to be fixed What is the scenario for the leak ? The leaked memory was allocated at qemu_monitor.c:636. One of the leak reported by valgrind is: ==12636== 40 bytes in 1 blocks are definitely lost in loss record 302 of 620 ==12636==at 0x4A05E46: malloc (vg_replace_malloc.c:195) ==12636==by 0x306B27FC01: strdup (in /lib64/libc-2.13.so) ==12636==by 0x4EA5669: virCopyError (virterror.c:182) ==12636==by 0x4EA573C: virCopyLastError (virterror.c:282) ==12636==by 0x110CFEA9: qemuMonitorIO (qemu_monitor.c:636) ==12636==by 0x4E83950: virEventPollRunOnce (event_poll.c:485) ==12636==by 0x4E82004: virEventRunDefaultImpl (event.c:247) ==12636==by 0x4F822BC: virNetServerRun (virnetserver.c:751) ==12636==by 0x40C433: main (libvirtd.c:1338) The scenario is: If we deep-copy a virError, by virCopyLastError, into another virError object which is previously deep-copied into, then we have no chance to free previously allocated memory, because the memset in virCopyLastError loses any pointers to them. -- Thanks, Hu Tao -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v4 3/9] use virBitmap to store cpupin info
--- src/conf/domain_conf.c | 148 +++--- src/conf/domain_conf.h |6 +- src/libvirt_private.syms |1 + src/qemu/qemu_cgroup.c |3 +- src/qemu/qemu_driver.c | 29 + src/qemu/qemu_process.c | 20 --- 6 files changed, 80 insertions(+), 127 deletions(-) diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c index 3a44432..41612f2 100644 --- a/src/conf/domain_conf.c +++ b/src/conf/domain_conf.c @@ -52,6 +52,7 @@ #include netdev_bandwidth_conf.h #include netdev_vlan_conf.h #include device_conf.h +#include bitmap.h #define VIR_FROM_THIS VIR_FROM_DOMAIN @@ -1510,10 +1511,9 @@ virDomainVcpuPinDefCopy(virDomainVcpuPinDefPtr *src, int nvcpupin) for (i = 0; i nvcpupin; i++) { if (VIR_ALLOC(ret[i]) 0) goto no_memory; -if (VIR_ALLOC_N(ret[i]-cpumask, VIR_DOMAIN_CPUMASK_LEN) 0) -goto no_memory; ret[i]-vcpuid = src[i]-vcpuid; -memcpy(ret[i]-cpumask, src[i]-cpumask, VIR_DOMAIN_CPUMASK_LEN); +if ((ret[i]-cpumask = virBitmapNewCopy(src[i]-cpumask)) == NULL) +goto no_memory; } return ret; @@ -1522,7 +1522,7 @@ no_memory: if (ret) { for ( ; i = 0; --i) { if (ret[i]) { -VIR_FREE(ret[i]-cpumask); +virBitmapFree(ret[i]-cpumask); VIR_FREE(ret[i]); } } @@ -1534,8 +1534,17 @@ no_memory: } void -virDomainVcpuPinDefFree(virDomainVcpuPinDefPtr *def, -int nvcpupin) +virDomainVcpuPinDefFree(virDomainVcpuPinDefPtr def) +{ +if (def) { +virBitmapFree(def-cpumask); +VIR_FREE(def); +} +} + +void +virDomainVcpuPinDefArrayFree(virDomainVcpuPinDefPtr *def, + int nvcpupin) { int i; @@ -1543,8 +1552,7 @@ virDomainVcpuPinDefFree(virDomainVcpuPinDefPtr *def, return; for(i = 0; i nvcpupin; i++) { -VIR_FREE(def[i]-cpumask); -VIR_FREE(def[i]); +virDomainVcpuPinDefFree(def[i]); } VIR_FREE(def); @@ -1668,7 +1676,9 @@ void virDomainDefFree(virDomainDefPtr def) virCPUDefFree(def-cpu); -virDomainVcpuPinDefFree(def-cputune.vcpupin, def-cputune.nvcpupin); +virDomainVcpuPinDefArrayFree(def-cputune.vcpupin, def-cputune.nvcpupin); + +virDomainVcpuPinDefFree(def-cputune.emulatorpin); VIR_FREE(def-numatune.memory.nodemask); @@ -8028,12 +8038,8 @@ virDomainVcpuPinDefParseXML(const xmlNodePtr node, char *set = tmp; int cpumasklen = VIR_DOMAIN_CPUMASK_LEN; -if (VIR_ALLOC_N(def-cpumask, cpumasklen) 0) { -virReportOOMError(); -goto error; -} -if (virDomainCpuSetParse(set, 0, def-cpumask, - cpumasklen) 0) +if (virBitmapParse(set, 0, def-cpumask, + cpumasklen) 0) goto error; VIR_FREE(tmp); } else { @@ -8468,18 +8474,11 @@ static virDomainDefPtr virDomainDefParseXML(virCapsPtr caps, goto error; } -if (VIR_ALLOC(def-cputune.emulatorpin) 0) { -goto no_memory; -} +def-cputune.emulatorpin = virDomainVcpuPinDefParseXML(nodes[0], ctxt, + def-maxvcpus, 1); -virDomainVcpuPinDefPtr emulatorpin = NULL; -emulatorpin = virDomainVcpuPinDefParseXML(nodes[0], ctxt, - def-maxvcpus, 1); - -if (!emulatorpin) +if (!def-cputune.emulatorpin) goto error; - -def-cputune.emulatorpin = emulatorpin; } VIR_FREE(nodes); @@ -11097,34 +11096,6 @@ virDomainVcpuPinFindByVcpu(virDomainVcpuPinDefPtr *def, return NULL; } -static char *bitmapFromBytemap(unsigned char *bytemap, int maplen) -{ -char *bitmap = NULL; -int i; - -if (VIR_ALLOC_N(bitmap, VIR_DOMAIN_CPUMASK_LEN) 0) { -virReportOOMError(); -goto cleanup; -} - -/* Reset bitmap to all 0s. */ -for (i = 0; i VIR_DOMAIN_CPUMASK_LEN; i++) -bitmap[i] = 0; - -/* Convert bitmap (bytemap) to bitmap, which is byte map? */ -for (i = 0; i maplen; i++) { -int cur; - -for (cur = 0; cur 8; cur++) { -if (bytemap[i] (1 cur)) -bitmap[i * 8 + cur] = 1; -} -} - -cleanup: -return bitmap; -} - int virDomainVcpuPinAdd(virDomainVcpuPinDefPtr **vcpupin_list, int *nvcpupin, unsigned char *cpumap, @@ -11132,20 +11103,21 @@ int virDomainVcpuPinAdd(virDomainVcpuPinDefPtr **vcpupin_list, int vcpu) { virDomainVcpuPinDefPtr vcpupin = NULL; -char *cpumask = NULL; if (!vcpupin_list) return -1; -if ((cpumask = bitmapFromBytemap(cpumap, maplen)) == NULL) -return -1; - vcpupin =
[libvirt] [PATCH v4 4/9] use virBitmap to store cpu affinity info
--- src/lxc/lxc_controller.c | 23 + src/qemu/qemu_driver.c | 62 - src/qemu/qemu_process.c | 85 -- src/util/processinfo.c | 36 +++- src/util/processinfo.h |9 ++--- 5 files changed, 84 insertions(+), 131 deletions(-) diff --git a/src/lxc/lxc_controller.c b/src/lxc/lxc_controller.c index e5aea11..dc45a6a 100644 --- a/src/lxc/lxc_controller.c +++ b/src/lxc/lxc_controller.c @@ -493,8 +493,7 @@ static int virLXCControllerSetupCpuAffinity(virLXCControllerPtr ctrl) { int i, hostcpus, maxcpu = CPU_SETSIZE; virNodeInfo nodeinfo; -unsigned char *cpumap; -int cpumaplen; +virBitmapPtr cpumap; VIR_DEBUG(Setting CPU affinity); @@ -507,37 +506,33 @@ static int virLXCControllerSetupCpuAffinity(virLXCControllerPtr ctrl) if (maxcpu hostcpus) maxcpu = hostcpus; -cpumaplen = VIR_CPU_MAPLEN(maxcpu); -if (VIR_ALLOC_N(cpumap, cpumaplen) 0) { -virReportOOMError(); +cpumap = virBitmapNew(maxcpu); +if (!cpumap) return -1; -} if (ctrl-def-cpumask) { /* XXX why don't we keep 'cpumask' in the libvirt cpumap * format to start with ?!?! */ for (i = 0 ; i maxcpu i ctrl-def-cpumasklen ; i++) if (ctrl-def-cpumask[i]) -VIR_USE_CPU(cpumap, i); +ignore_value(virBitmapSetBit(cpumap, i)); } else { /* You may think this is redundant, but we can't assume libvirtd * itself is running on all pCPUs, so we need to explicitly set * the spawned LXC instance to all pCPUs if no map is given in * its config file */ -for (i = 0 ; i maxcpu ; i++) -VIR_USE_CPU(cpumap, i); +virBitmapSetAll(cpumap); } -/* We are pressuming we are running between fork/exec of LXC +/* We are presuming we are running between fork/exec of LXC * so use '0' to indicate our own process ID. No threads are * running at this point */ -if (virProcessInfoSetAffinity(0, /* Self */ - cpumap, cpumaplen, maxcpu) 0) { -VIR_FREE(cpumap); +if (virProcessInfoSetAffinity(0 /* Self */, cpumap) 0) { +virBitmapFree(cpumap); return -1; } -VIR_FREE(cpumap); +virBitmapFree(cpumap); return 0; } diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c index 9bbd451..1697293 100644 --- a/src/qemu/qemu_driver.c +++ b/src/qemu/qemu_driver.c @@ -92,6 +92,7 @@ #include virnodesuspend.h #include virtime.h #include virtypedparam.h +#include bitmap.h #define VIR_FROM_THIS VIR_FROM_QEMU @@ -3715,10 +3716,10 @@ qemudDomainPinVcpuFlags(virDomainPtr dom, virNodeInfo nodeinfo; int ret = -1; qemuDomainObjPrivatePtr priv; -bool canResetting = true; +bool doReset = false; int newVcpuPinNum = 0; virDomainVcpuPinDefPtr *newVcpuPin = NULL; -int pcpu; +virBitmapPtr pcpumap = NULL; virCheckFlags(VIR_DOMAIN_AFFECT_LIVE | VIR_DOMAIN_AFFECT_CONFIG, -1); @@ -3754,15 +3755,16 @@ qemudDomainPinVcpuFlags(virDomainPtr dom, maxcpu = maplen * 8; if (maxcpu hostcpus) maxcpu = hostcpus; + +pcpumap = virBitmapNewData(cpumap, maplen); +if (!pcpumap) +goto cleanup; + /* pinning to all physical cpus means resetting, * so check if we can reset setting. */ -for (pcpu = 0; pcpu hostcpus; pcpu++) { -if ((cpumap[pcpu/8] (1 (pcpu % 8))) == 0) { -canResetting = false; -break; -} -} +if (virBitmapIsAllSet(pcpumap)) +doReset = true; if (flags VIR_DOMAIN_AFFECT_LIVE) { @@ -3805,8 +3807,7 @@ qemudDomainPinVcpuFlags(virDomainPtr dom, goto cleanup; } } else { -if (virProcessInfoSetAffinity(priv-vcpupids[vcpu], - cpumap, maplen, maxcpu) 0) { +if (virProcessInfoSetAffinity(priv-vcpupids[vcpu], pcpumap) 0) { virReportError(VIR_ERR_SYSTEM_ERROR, _(failed to set cpu affinity for vcpu %d), vcpu); @@ -3814,7 +3815,7 @@ qemudDomainPinVcpuFlags(virDomainPtr dom, } } -if (canResetting) { +if (doReset) { if (virDomainVcpuPinDel(vm-def, vcpu) 0) { virReportError(VIR_ERR_INTERNAL_ERROR, %s, _(failed to delete vcpupin xml of @@ -3839,7 +3840,7 @@ qemudDomainPinVcpuFlags(virDomainPtr dom, if (flags VIR_DOMAIN_AFFECT_CONFIG) { -if (canResetting) { +if (doReset) { if (virDomainVcpuPinDel(persistentDef, vcpu) 0) { virReportError(VIR_ERR_INTERNAL_ERROR, %s, _(failed to delete vcpupin xml of @@ -3879,6 +3880,7
[libvirt] [PATCH v4 6/9] use virBitmap to store cpumask info.
--- src/conf/domain_conf.c | 24 +--- src/conf/domain_conf.h |3 +-- src/lxc/lxc_controller.c | 14 ++ src/parallels/parallels_driver.c |3 +-- src/qemu/qemu_process.c | 12 +--- src/test/test_driver.c |5 - src/vmx/vmx.c| 36 ++-- tests/cpuset |2 +- 8 files changed, 45 insertions(+), 54 deletions(-) diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c index cc54d39..6ecec54 100644 --- a/src/conf/domain_conf.c +++ b/src/conf/domain_conf.c @@ -8394,14 +8394,12 @@ static virDomainDefPtr virDomainDefParseXML(virCapsPtr caps, if (def-placement_mode != VIR_DOMAIN_CPU_PLACEMENT_MODE_AUTO) { tmp = virXPathString(string(./vcpu[1]/@cpuset), ctxt); if (tmp) { -char *set = tmp; -def-cpumasklen = VIR_DOMAIN_CPUMASK_LEN; -if (VIR_ALLOC_N(def-cpumask, def-cpumasklen) 0) { -goto no_memory; -} -if (virDomainCpuSetParse(set, 0, def-cpumask, - def-cpumasklen) 0) +if (virBitmapParse(tmp, 0, def-cpumask, + VIR_DOMAIN_CPUMASK_LEN) 0) { +virReportError(VIR_ERR_XML_ERROR, + %s, _(topology cpuset syntax error)); goto error; +} VIR_FREE(tmp); } } @@ -13011,7 +13009,7 @@ virDomainDefFormatInternal(virDomainDefPtr def, unsigned char *uuid; char uuidstr[VIR_UUID_STRING_BUFLEN]; const char *type = NULL; -int n, allones = 1; +int n; int i; bool blkio = false; @@ -13140,17 +13138,13 @@ virDomainDefFormatInternal(virDomainDefPtr def, /memoryBacking\n, NULL); } -for (n = 0 ; n def-cpumasklen ; n++) -if (def-cpumask[n] != 1) -allones = 0; - virBufferAddLit(buf, vcpu); virBufferAsprintf(buf, placement='%s', virDomainCpuPlacementModeTypeToString(def-placement_mode)); -if (!allones) { + +if (def-cpumask !virBitmapIsAllSet(def-cpumask)) { char *cpumask = NULL; -if ((cpumask = - virDomainCpuSetFormat(def-cpumask, def-cpumasklen)) == NULL) +if ((cpumask = virBitmapFormat(def-cpumask)) == NULL) goto cleanup; virBufferAsprintf(buf, cpuset='%s', cpumask); VIR_FREE(cpumask); diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h index 975c565..042b518 100644 --- a/src/conf/domain_conf.h +++ b/src/conf/domain_conf.h @@ -1614,8 +1614,7 @@ struct _virDomainDef { unsigned short vcpus; unsigned short maxvcpus; int placement_mode; -int cpumasklen; -char *cpumask; +virBitmapPtr cpumask; struct { unsigned long shares; diff --git a/src/lxc/lxc_controller.c b/src/lxc/lxc_controller.c index 44ec7aa..7e98006 100644 --- a/src/lxc/lxc_controller.c +++ b/src/lxc/lxc_controller.c @@ -490,9 +490,9 @@ static int virLXCControllerSetupNUMAPolicy(virLXCControllerPtr ctrl) */ static int virLXCControllerSetupCpuAffinity(virLXCControllerPtr ctrl) { -int i, hostcpus, maxcpu = CPU_SETSIZE; +int hostcpus, maxcpu = CPU_SETSIZE; virNodeInfo nodeinfo; -virBitmapPtr cpumap; +virBitmapPtr cpumap, cpumapToSet; VIR_DEBUG(Setting CPU affinity); @@ -509,12 +509,10 @@ static int virLXCControllerSetupCpuAffinity(virLXCControllerPtr ctrl) if (!cpumap) return -1; +cpumapToSet = cpumap; + if (ctrl-def-cpumask) { -/* XXX why don't we keep 'cpumask' in the libvirt cpumap - * format to start with ?!?! */ -for (i = 0 ; i maxcpu i ctrl-def-cpumasklen ; i++) -if (ctrl-def-cpumask[i]) -ignore_value(virBitmapSetBit(cpumap, i)); +cpumapToSet = ctrl-def-cpumask; } else { /* You may think this is redundant, but we can't assume libvirtd * itself is running on all pCPUs, so we need to explicitly set @@ -527,7 +525,7 @@ static int virLXCControllerSetupCpuAffinity(virLXCControllerPtr ctrl) * so use '0' to indicate our own process ID. No threads are * running at this point */ -if (virProcessInfoSetAffinity(0 /* Self */, cpumap) 0) { +if (virProcessInfoSetAffinity(0 /* Self */, cpumapToSet) 0) { virBitmapFree(cpumap); return -1; } diff --git a/src/parallels/parallels_driver.c b/src/parallels/parallels_driver.c index cf9f6ab..46efe14 100644 --- a/src/parallels/parallels_driver.c +++ b/src/parallels/parallels_driver.c @@ -1407,8 +1407,7 @@ parallelsApplyChanges(virDomainObjPtr dom, virDomainDefPtr new) return -1; } -if (old-cpumasklen != new-cpumasklen || -(memcmp(old-cpumask, new-cpumask, old-cpumasklen))) { +if (!virBitmapEqual(old-cpumask,
[libvirt] [PATCH v4 2/9] New functions for virBitmap
In many places we store bitmap info in a chunk of data (pointed to by a char *), and have redundant codes to set/unset bits. This patch extends virBitmap, and convert those codes to use virBitmap in subsequent patches. --- .gitignore |1 + src/libvirt_private.syms | 11 ++ src/util/bitmap.c| 405 +- src/util/bitmap.h| 34 tests/Makefile.am|7 +- tests/virbitmaptest.c| 362 + 6 files changed, 818 insertions(+), 2 deletions(-) create mode 100644 tests/virbitmaptest.c diff --git a/.gitignore b/.gitignore index d998f0e..1ca537e 100644 --- a/.gitignore +++ b/.gitignore @@ -157,6 +157,7 @@ /tests/utiltest /tests/viratomictest /tests/virauthconfigtest +/tests/virbitmaptest /tests/virbuftest /tests/virdrivermoduletest /tests/virhashtest diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 557fa0e..da0e647 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -6,13 +6,24 @@ # # bitmap.h +virBitmapClearAll; virBitmapClearBit; virBitmapCopy; +virBitmapEqual; +virBitmapFormat; virBitmapFree; virBitmapGetBit; +virBitmapIsAllSet; virBitmapNew; +virBitmapNewCopy; +virBitmapNewData; +virBitmapNextSetBit; +virBitmapParse; +virBitmapSetAll; virBitmapSetBit; +virBitmapSize; virBitmapString; +virBitmapToData; # buf.h diff --git a/src/util/bitmap.c b/src/util/bitmap.c index dc9c28a..51e567a 100644 --- a/src/util/bitmap.c +++ b/src/util/bitmap.c @@ -33,6 +33,8 @@ #include bitmap.h #include memory.h #include buf.h +#include util.h +#include c-ctype.h struct _virBitmap { @@ -145,6 +147,12 @@ int virBitmapClearBit(virBitmapPtr bitmap, size_t b) return 0; } +/* Helper function. caller must ensure b bitmap-max_bit */ +static bool virBitmapIsSet(virBitmapPtr bitmap, size_t b) +{ +return !!(bitmap-map[VIR_BITMAP_UNIT_OFFSET(b)] VIR_BITMAP_BIT(b)); +} + /** * virBitmapGetBit: * @bitmap: Pointer to bitmap @@ -161,7 +169,7 @@ int virBitmapGetBit(virBitmapPtr bitmap, size_t b, bool *result) if (bitmap-max_bit = b) return -1; -*result = !!(bitmap-map[VIR_BITMAP_UNIT_OFFSET(b)] VIR_BITMAP_BIT(b)); +*result = virBitmapIsSet(bitmap, b); return 0; } @@ -195,3 +203,398 @@ char *virBitmapString(virBitmapPtr bitmap) return virBufferContentAndReset(buf); } + +/** + * virBitmapFormat: + * @bitmap: the bitmap + * + * This function is the counterpart of virBitmapParse. This function creates + * a human-readable string representing the bits in bitmap. + * + * See virBitmapParse for the format of @str. + * + * Returns the string on success or NULL otherwise. Caller should call + * VIR_FREE to free the string. + */ +char *virBitmapFormat(virBitmapPtr bitmap) +{ +virBuffer buf = VIR_BUFFER_INITIALIZER; +bool first = true; +int start, cur, prev; + +if (!bitmap) +return NULL; + +cur = virBitmapNextSetBit(bitmap, -1); +if (cur 0) +return strdup(); + +start = prev = cur; +while (prev = 0) { +cur = virBitmapNextSetBit(bitmap, prev); + +if (cur == prev + 1) { +prev = cur; +continue; +} + +/* cur 0 or cur prev + 1 */ + +if (!first) +virBufferAddLit(buf, ,); +else +first = false; + +if (prev == start) +virBufferAsprintf(buf, %d, start); +else +virBufferAsprintf(buf, %d-%d, start, prev); + +start = prev = cur; +} + +if (virBufferError(buf)) { +virBufferFreeAndReset(buf); +return NULL; +} + +return virBufferContentAndReset(buf); +} + +/** + * virBitmapParse: + * @str: points to a string representing a human-readable bitmap + * @bitmap: a bitmap created from @str + * @bitmapSize: the upper limit of num of bits in created bitmap + * + * This function is the counterpart of virBitmapFormat. This function creates + * a bitmap, in which bits are set according to the content of @str. + * + * @str is a comma separated string of fields N, which means a number of bit + * to set, and ^N, which means to unset the bit, and N-M for ranges of bits + * to set. + * + * Returns the number of bits set in @bitmap, or -1 in case of error. + */ + +int virBitmapParse(const char *str, + char sep, + virBitmapPtr *bitmap, + size_t bitmapSize) +{ +int ret = 0; +bool neg = false; +const char *cur; +char *tmp; +int i, start, last; + +if (!str) +return -1; + +cur = str; +virSkipSpaces(cur); + +if (*cur == 0) +return -1; + +*bitmap = virBitmapNew(bitmapSize); +if (!*bitmap) +return -1; + +while (*cur != 0 *cur != sep) { +/* + * 3 constructs are allowed: + * - N : a single CPU number + * - N-M : a range of CPU numbers with N M +
[libvirt] [PATCH v4 5/9] use virBitmap to store numa nodemask info.
--- src/conf/domain_conf.c | 24 +--- src/conf/domain_conf.h |2 +- src/lxc/lxc_controller.c | 25 src/parallels/parallels_driver.c |2 +- src/qemu/qemu_cgroup.c |7 ++--- src/qemu/qemu_cgroup.h |2 +- src/qemu/qemu_driver.c | 58 ++ src/qemu/qemu_process.c | 52 -- 8 files changed, 65 insertions(+), 107 deletions(-) diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c index 41612f2..cc54d39 100644 --- a/src/conf/domain_conf.c +++ b/src/conf/domain_conf.c @@ -1680,7 +1680,7 @@ void virDomainDefFree(virDomainDefPtr def) virDomainVcpuPinDefFree(def-cputune.emulatorpin); -VIR_FREE(def-numatune.memory.nodemask); +virBitmapFree(def-numatune.memory.nodemask); virSysinfoDefFree(def-sysinfo); @@ -8523,19 +8523,10 @@ static virDomainDefPtr virDomainDefParseXML(virCapsPtr caps, nodeset = virXMLPropString(cur, nodeset); if (nodeset) { -char *set = nodeset; -int nodemasklen = VIR_DOMAIN_CPUMASK_LEN; - -if (VIR_ALLOC_N(def-numatune.memory.nodemask, -nodemasklen) 0) { -virReportOOMError(); -goto error; -} - -/* nodeset uses the same syntax as cpuset. */ -if (virDomainCpuSetParse(set, 0, - def-numatune.memory.nodemask, - nodemasklen) 0) { +if (virBitmapParse(nodeset, + 0, + def-numatune.memory.nodemask, + VIR_DOMAIN_CPUMASK_LEN) 0) { VIR_FREE(nodeset); goto error; } @@ -8577,7 +8568,7 @@ static virDomainDefPtr virDomainDefParseXML(virCapsPtr caps, /* Ignore 'nodeset' if 'placement' is 'auto' finally */ if (placement_mode == VIR_DOMAIN_NUMATUNE_MEM_PLACEMENT_MODE_AUTO) -VIR_FREE(def-numatune.memory.nodemask); +virBitmapFree(def-numatune.memory.nodemask); /* Copy 'placement' of numatune to vcpu if its 'placement' * is not specified and 'placement' of numatune is specified. @@ -13246,8 +13237,7 @@ virDomainDefFormatInternal(virDomainDefPtr def, if (def-numatune.memory.placement_mode == VIR_DOMAIN_NUMATUNE_MEM_PLACEMENT_MODE_STATIC) { -nodemask = virDomainCpuSetFormat(def-numatune.memory.nodemask, - VIR_DOMAIN_CPUMASK_LEN); +nodemask = virBitmapFormat(def-numatune.memory.nodemask); if (nodemask == NULL) { virReportError(VIR_ERR_INTERNAL_ERROR, %s, _(failed to format nodeset for diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h index bb3721c..975c565 100644 --- a/src/conf/domain_conf.h +++ b/src/conf/domain_conf.h @@ -1560,7 +1560,7 @@ typedef struct _virDomainNumatuneDef virDomainNumatuneDef; typedef virDomainNumatuneDef *virDomainNumatuneDefPtr; struct _virDomainNumatuneDef { struct { -char *nodemask; +virBitmapPtr nodemask; int mode; int placement_mode; /* enum virDomainNumatuneMemPlacementMode */ } memory; diff --git a/src/lxc/lxc_controller.c b/src/lxc/lxc_controller.c index dc45a6a..44ec7aa 100644 --- a/src/lxc/lxc_controller.c +++ b/src/lxc/lxc_controller.c @@ -418,20 +418,19 @@ static int virLXCControllerSetupNUMAPolicy(virLXCControllerPtr ctrl) /* Convert nodemask to NUMA bitmask. */ nodemask_zero(mask); -for (i = 0; i VIR_DOMAIN_CPUMASK_LEN; i++) { -if (ctrl-def-numatune.memory.nodemask[i]) { -if (i NUMA_NUM_NODES) { -virReportError(VIR_ERR_CONFIG_UNSUPPORTED, - _(Host cannot support NUMA node %d), i); -return -1; -} -if (i maxnode !warned) { -VIR_WARN(nodeset is out of range, there is only %d NUMA - nodes on host, maxnode); -warned = true; -} -nodemask_set(mask, i); +i = -1; +while ((i = virBitmapNextSetBit(ctrl-def-numatune.memory.nodemask, i)) = 0) { +if (i NUMA_NUM_NODES) { +virReportError(VIR_ERR_CONFIG_UNSUPPORTED, + _(Host cannot support NUMA node %d), i); +return -1; +} +if (i maxnode !warned) { +VIR_WARN(nodeset is out of range, there is
[libvirt] [PATCH v4 7/9] use virBitmap to store cells' cpumask info.
--- src/conf/cpu_conf.c | 17 ++--- src/conf/cpu_conf.h |3 ++- src/qemu/qemu_command.c | 43 +++ 3 files changed, 15 insertions(+), 48 deletions(-) diff --git a/src/conf/cpu_conf.c b/src/conf/cpu_conf.c index 87e9540..48d5740 100644 --- a/src/conf/cpu_conf.c +++ b/src/conf/cpu_conf.c @@ -83,7 +83,7 @@ virCPUDefFree(virCPUDefPtr def) virCPUDefFreeModel(def); for (i = 0 ; i def-ncells ; i++) { -VIR_FREE(def-cells[i].cpumask); +virBitmapFree(def-cells[i].cpumask); VIR_FREE(def-cells[i].cpustr); } VIR_FREE(def-cells); @@ -164,11 +164,10 @@ virCPUDefCopy(const virCPUDefPtr cpu) copy-cells[i].cellid = cpu-cells[i].cellid; copy-cells[i].mem = cpu-cells[i].mem; -if (VIR_ALLOC_N(copy-cells[i].cpumask, -VIR_DOMAIN_CPUMASK_LEN) 0) +copy-cells[i].cpumask = virBitmapNewCopy(cpu-cells[i].cpumask); + +if (!copy-cells[i].cpumask) goto no_memory; -memcpy(copy-cells[i].cpumask, cpu-cells[i].cpumask, - VIR_DOMAIN_CPUMASK_LEN); if (!(copy-cells[i].cpustr = strdup(cpu-cells[i].cpustr))) goto no_memory; @@ -454,7 +453,6 @@ virCPUDefParseXML(const xmlNodePtr node, for (i = 0 ; i n ; i++) { char *cpus, *memory; -int cpumasklen = VIR_DOMAIN_CPUMASK_LEN; int ret, ncpus = 0; def-cells[i].cellid = i; @@ -466,11 +464,8 @@ virCPUDefParseXML(const xmlNodePtr node, } def-cells[i].cpustr = cpus; -if (VIR_ALLOC_N(def-cells[i].cpumask, cpumasklen) 0) -goto no_memory; - -ncpus = virDomainCpuSetParse(cpus, 0, def-cells[i].cpumask, - cpumasklen); +ncpus = virBitmapParse(cpus, 0, def-cells[i].cpumask, + VIR_DOMAIN_CPUMASK_LEN); if (ncpus = 0) goto error; def-cells_cpus += ncpus; diff --git a/src/conf/cpu_conf.h b/src/conf/cpu_conf.h index 601e208..4e03fd2 100644 --- a/src/conf/cpu_conf.h +++ b/src/conf/cpu_conf.h @@ -27,6 +27,7 @@ # include util.h # include buf.h # include xml.h +# include bitmap.h # define VIR_CPU_VENDOR_ID_LENGTH 12 @@ -92,7 +93,7 @@ typedef struct _virCellDef virCellDef; typedef virCellDef *virCellDefPtr; struct _virCellDef { int cellid; - char *cpumask; /* CPUs that are part of this node */ + virBitmapPtr cpumask; /* CPUs that are part of this node */ char *cpustr; /* CPUs stored in string form for dumpxml */ unsigned int mem; /* Node memory in kB */ }; diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c index cd4ee93..b5359f2 100644 --- a/src/qemu/qemu_command.c +++ b/src/qemu/qemu_command.c @@ -4261,54 +4261,25 @@ qemuBuildSmpArgStr(const virDomainDefPtr def, return virBufferContentAndReset(buf); } -static void -qemuBuildNumaCPUArgStr(char *cpumask, virBufferPtr buf) -{ -int i, first, last; -int cpuSet = 0; - -first = last = 0; -for (i = 0; i VIR_DOMAIN_CPUMASK_LEN; i++) { -if (cpumask[i]) { -if (cpuSet) { -last = i; -} else { -first = last = i; -cpuSet = 1; -} -} else { -if (!cpuSet) -continue; -if (first == last) -virBufferAsprintf(buf, %d,, first); -else -virBufferAsprintf(buf, %d-%d,, first, last); -cpuSet = 0; -} -} - -if (cpuSet) { -if (first == last) -virBufferAsprintf(buf, %d,, first); -else -virBufferAsprintf(buf, %d-%d,, first, last); -} -} - static int qemuBuildNumaArgStr(const virDomainDefPtr def, virCommandPtr cmd) { int i; virBuffer buf = VIR_BUFFER_INITIALIZER; +char *cpumask; for (i = 0; i def-cpu-ncells; i++) { virCommandAddArg(cmd, -numa); virBufferAsprintf(buf, node,nodeid=%d, def-cpu-cells[i].cellid); virBufferAddLit(buf, ,cpus=); -qemuBuildNumaCPUArgStr(def-cpu-cells[i].cpumask, buf); +cpumask = virBitmapFormat(def-cpu-cells[i].cpumask); +if (cpumask) { +virBufferAsprintf(buf, %s, cpumask); +VIR_FREE(cpumask); +} def-cpu-cells[i].mem = VIR_DIV_UP(def-cpu-cells[i].mem, 1024) * 1024; -virBufferAsprintf(buf, mem=%d, def-cpu-cells[i].mem / 1024); +virBufferAsprintf(buf, ,mem=%d, def-cpu-cells[i].mem / 1024); if (virBufferError(buf)) goto error; -- 1.7.10.2 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list
[libvirt] [PATCH v4 8/9] use virBitmap to store nodeinfo.
--- src/nodeinfo.c | 26 +++--- src/nodeinfo.h |6 +++--- src/qemu/qemu_driver.c | 19 --- 3 files changed, 26 insertions(+), 25 deletions(-) diff --git a/src/nodeinfo.c b/src/nodeinfo.c index e3d4a24..803b261 100644 --- a/src/nodeinfo.c +++ b/src/nodeinfo.c @@ -737,10 +737,10 @@ cleanup: * and max cpu is 7. The map file shows 0-4,6-7. This function parses * it and returns cpumap. */ -static char * +static virBitmapPtr linuxParseCPUmap(int *max_cpuid, const char *path) { -char *map = NULL; +virBitmapPtr map = NULL; char *str = NULL; int max_id = 0, i; @@ -749,20 +749,16 @@ linuxParseCPUmap(int *max_cpuid, const char *path) goto error; } -if (VIR_ALLOC_N(map, VIR_DOMAIN_CPUMASK_LEN) 0) { -virReportOOMError(); -goto error; -} -if (virDomainCpuSetParse(str, 0, map, - VIR_DOMAIN_CPUMASK_LEN) 0) { +if (virBitmapParse(str, 0, map, + VIR_DOMAIN_CPUMASK_LEN) 0) { goto error; } -for (i = 0; i VIR_DOMAIN_CPUMASK_LEN; i++) { -if (map[i]) { -max_id = i; -} +i = -1; +while ((i = virBitmapNextSetBit(map, i)) = 0) { +max_id = i; } + *max_cpuid = max_id; VIR_FREE(str); @@ -770,7 +766,7 @@ linuxParseCPUmap(int *max_cpuid, const char *path) error: VIR_FREE(str); -VIR_FREE(map); +virBitmapFree(map); return NULL; } #endif @@ -909,14 +905,14 @@ int nodeGetMemoryStats(virConnectPtr conn ATTRIBUTE_UNUSED, #endif } -char * +virBitmapPtr nodeGetCPUmap(virConnectPtr conn ATTRIBUTE_UNUSED, int *max_id ATTRIBUTE_UNUSED, const char *mapname ATTRIBUTE_UNUSED) { #ifdef __linux__ char *path; -char *cpumap; +virBitmapPtr cpumap; if (virAsprintf(path, SYSFS_SYSTEM_PATH /cpu/%s, mapname) 0) { virReportOOMError(); diff --git a/src/nodeinfo.h b/src/nodeinfo.h index 12090e2..182b0b6 100644 --- a/src/nodeinfo.h +++ b/src/nodeinfo.h @@ -46,7 +46,7 @@ int nodeGetCellsFreeMemory(virConnectPtr conn, int maxCells); unsigned long long nodeGetFreeMemory(virConnectPtr conn); -char *nodeGetCPUmap(virConnectPtr conn, -int *max_id, -const char *mapname); +virBitmapPtr nodeGetCPUmap(virConnectPtr conn, + int *max_id, + const char *mapname); #endif /* __VIR_NODEINFO_H__*/ diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c index 4abfbd5..2278657 100644 --- a/src/qemu/qemu_driver.c +++ b/src/qemu/qemu_driver.c @@ -13502,8 +13502,8 @@ qemuDomainGetPercpuStats(virDomainPtr domain, int start_cpu, unsigned int ncpus) { -char *map = NULL; -char *map2 = NULL; +virBitmapPtr map = NULL; +virBitmapPtr map2 = NULL; int rv = -1; int i, id, max_id; char *pos; @@ -13515,6 +13515,7 @@ qemuDomainGetPercpuStats(virDomainPtr domain, virTypedParameterPtr ent; int param_idx; unsigned long long cpu_time; +bool result; /* return the number of supported params */ if (nparams == 0 ncpus != 0) @@ -13553,7 +13554,9 @@ qemuDomainGetPercpuStats(virDomainPtr domain, id = start_cpu + ncpus - 1; for (i = 0; i = id; i++) { -if (!map[i]) { +if (virBitmapGetBit(map, i, result) 0) +goto cleanup; +if (!result) { cpu_time = 0; } else if (virStrToLong_ull(pos, pos, 10, cpu_time) 0) { virReportError(VIR_ERR_INTERNAL_ERROR, %s, @@ -13585,7 +13588,7 @@ qemuDomainGetPercpuStats(virDomainPtr domain, /* Check that the mapping of online cpus didn't change mid-parse. */ map2 = nodeGetCPUmap(domain-conn, max_id, present); -if (!map2 || memcmp(map, map2, VIR_DOMAIN_CPUMASK_LEN) != 0) { +if (!map2 || !virBitmapEqual(map, map2)) { virReportError(VIR_ERR_OPERATION_INVALID, %s, _(the set of online cpus changed while reading)); goto cleanup; @@ -13593,7 +13596,9 @@ qemuDomainGetPercpuStats(virDomainPtr domain, sum_cpu_pos = sum_cpu_time; for (i = 0; i = id; i++) { -if (!map[i]) +if (virBitmapGetBit(map, i, result) 0) +goto cleanup; +if (!result) cpu_time = 0; else cpu_time = *(sum_cpu_pos++); @@ -13611,8 +13616,8 @@ qemuDomainGetPercpuStats(virDomainPtr domain, cleanup: VIR_FREE(sum_cpu_time); VIR_FREE(buf); -VIR_FREE(map); -VIR_FREE(map2); +virBitmapFree(map); +virBitmapFree(map2); return rv; } -- 1.7.10.2 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list