vdpa: change libvirt/qemu/kernel base version and docs

Change-Id: I574115f5e44e56ac2baaad71eeab6b9fd7149747
This commit is contained in:
jiangdongxu 2024-10-12 16:01:18 +08:00
parent 79c4324644
commit fac818adb1
1256 changed files with 2531 additions and 193928 deletions

View File

@ -1,22 +1,190 @@
# generic vDPA
## 介绍
vDPA是一种基于VirtIO 半虚拟化技术的提出的数据面加速的框架。
DPU卡呈现的VirtIO类型的存储/网络/文件系统设备通过对接vDPA框架提供与硬件持平的IO性能并通过统一上层管理的接口实现多种设备类型、多种DPU卡的接口统一。
## 软件架构
![vdpa framework](<doc/vdpa_framework.png>)
目录说明:
+ **kernel**generic vdpa基本功能及热迁移依赖的内核代码
+ **qemu**: generic vdpa设备基本功能及热迁移依赖的qemu代码
+ **libvirt**: generic vdpa设备管理及支持生命周期依赖的libvirt代码
+ **doc**: 项目资料等。
## Release 计划
- generic vDPA基本功能实现 - 2024.08.30
- generic vDPA热迁移功能实现 - 2024.10.30
- generic vDPA相关文档输出 - 2024.11.30
# generic vDPA
## 介绍
vDPA是一种基于VirtIO 半虚拟化技术的提出的数据面加速的框架。
DPU卡呈现的VirtIO类型的存储/网络/文件系统设备通过对接vDPA框架提供与硬件持平的IO性能并通过统一上层管理的接口实现多种设备类型、多种DPU卡的接口统一。
## 软件架构
![vdpa framework](<doc/vdpa_framework.png>)
## 部署教程
目录说明:
+ **kernel**generic vdpa基本功能及热迁移依赖的内核代码
+ **qemu**: generic vdpa设备基本功能及热迁移依赖的qemu代码
+ **libvirt**: generic vdpa设备管理及支持生命周期依赖的libvirt代码
+ **doc**: 项目资料等
generic vDPA当前开源社区尚未完全支持因此需要在开源软件的基础上打上补丁代码来支持相关功能主要涉及的有三个开源软件kernel、qemu、libvirt。
基于kernel-6.6、qemu-8.2.0、libvirt-9.10.0版本进行软件编译以及安装。
#### 内核编译以及安装:
```shell
1. cd kernel
2. wget -O kernel-6.6.tar.gz https://codeload.github.com/torvalds/linux/tar.gz/refs/tags/v6.6
3. tar xvf kernel-6.6.tar.gz & cd linux-6.6
4. for p in $(ls ../*.patch); do patch -p 1 -F 0 < $p; done
5. 打开内核VHOST_VDPA的编译选项
6. make -j64 && make modules_install -j64 && make install
```
#### qemu编译及安装
```shell
1. cd qemu
2. tar xvf qemu-8.2.0.tar.gz && cd qemu-8.2.0
3. for p in $(ls ../*.patch); do patch -p 1 -F 0 < $p; done
4. ./configure --target-list=aarch64-softmmu --enable-kvm --enable-vhost-vdpa
5. make -j64 && make install
```
#### libvirt编译及安装
```shell
1. cd libvirt
2. tar xvf libvirt-9.10.0.tar.gz && cd libvirt-9.10.0
3. meson setup build -Dsystem=true -Ddriver_qemu=enabled -Ddriver_lxc=disabled -Dlogin_shell=disabled
4. ninja -C build
5. ninja -C build install
```
#### 操作方法
请使用root用户按照如下操作步骤配置
1. 开启网卡SRIOV模式
1. 在HostOS的BIOS中开启SMMU的支持不同厂家服务器的开启可能不同请参考各服务器的帮助文档。
2. HostOS中对需要配置给虚拟机的PF配置SRIOV创建VF以virtio-net设备为例
```shell
# lspci -s 83:00.6
83:00.6 Ethernet controller: Virtio: Virtio network device
# echo 16 > /sys/bus/pci/devices/0000\:83\:00.6/sriov_numvfs
# lspci | grep Virtio
83:00.6 Ethernet controller: Virtio: Virtio network device
83:01.1 Ethernet controller: Virtio: Virtio network device
83:01.2 Ethernet controller: Virtio: Virtio network device
83:01.3 Ethernet controller: Virtio: Virtio network device
83:01.4 Ethernet controller: Virtio: Virtio network device
83:01.5 Ethernet controller: Virtio: Virtio network device
83:01.6 Ethernet controller: Virtio: Virtio network device
83:01.7 Ethernet controller: Virtio: Virtio network device
83:02.0 Ethernet controller: Virtio: Virtio network device
83:02.1 Ethernet controller: Virtio: Virtio network device
83:02.2 Ethernet controller: Virtio: Virtio network device
83:02.3 Ethernet controller: Virtio: Virtio network device
83:02.4 Ethernet controller: Virtio: Virtio network device
83:02.5 Ethernet controller: Virtio: Virtio network device
83:02.6 Ethernet controller: Virtio: Virtio network device
83:02.7 Ethernet controller: Virtio: Virtio network device
```
2. 解绑VF驱动并绑定对应硬件的厂商vdpa驱动
```shell
echo 0000:83:01.1 > /sys/bus/pci/devices/0000\:08\:01.1/driver/unbind
echo 0000:83:01.2 > /sys/bus/pci/devices/0000\:08\:01.2/driver/unbind
echo 0000:83:01.3 > /sys/bus/pci/devices/0000\:08\:01.3/driver/unbind
echo 0000:83:01.4 > /sys/bus/pci/devices/0000\:08\:01.4/driver/unbind
echo 0000:83:01.5 > /sys/bus/pci/devices/0000\:08\:01.5/driver/unbind
echo -n "1af4 1000" > /sys/bus/pci/drivers/${vendor_vdpa}/new_id
```
3. 绑定vDPA设备后可以通过vdpa命令查询vdpa管理设备列表
```shell
# vdpa mgmtdev show
pci/0000:83:01.1:
supported_classes net
pci/0000:83:01.2:
supported_classes net
pci/0000:83:01.3:
supported_classes net
pci/0000:83:01.4:
supported_classes net
pci/0000:83:01.5:
supported_classes net
```
4. 完成vdpa设备的创建后创建vhost-vDPA设备
```shell
vdpa dev add name vdpa0 mgmtdev pci/0000:83:01.1
vdpa dev add name vdpa1 mgmtdev pci/0000:83:01.2
vdpa dev add name vdpa2 mgmtdev pci/0000:83:01.3
vdpa dev add name vdpa3 mgmtdev pci/0000:83:01.4
vdpa dev add name vdpa4 mgmtdev pci/0000:83:01.5
```
5. 完成vhost-vDPA的设备创建后可以通过vdpa命令查询vdpa设备列表也可以通过libvirt命令查询环境的vhost-vDPA设备信息
```shell
# vdpa dev show
vdpa0: type network mgmtdev pci/0000:83:01.1 vendor_id 6900 max_vqs 3 max_vq_size 256
vdpa1: type network mgmtdev pci/0000:83:01.2 vendor_id 6900 max_vqs 3 max_vq_size 256
vdpa2: type network mgmtdev pci/0000:83:01.3 vendor_id 6900 max_vqs 3 max_vq_size 256
vdpa3: type network mgmtdev pci/0000:83:01.4 vendor_id 6900 max_vqs 3 max_vq_size 256
vdpa4: type network mgmtdev pci/0000:83:01.5 vendor_id 6900 max_vqs 3 max_vq_size 256
# virsh nodedev-list vdpa
vdpa_vdpa0
vdpa_vdpa1
vdpa_vdpa2
vdpa_vdpa3
vdpa_vdpa4
# virsh nodedev-dumpxml vdpa_vdpa0
<device>
<name>vdpa_vdpa0</name>
<path>/sys/devices/pci0000:00/0000:00:0c.0/0000:83:01.1/vdpa0</path>
<parent>pci_0000_83_01_1</parent>
<driver>
<name>vhost_vdpa</name>
</driver>
<capability type='vdpa'>
<chardev>/dev/vhost-vdpa-0</chardev>
</capability>
</device>
```
6. 创建虚拟机时在虚拟机配置文件中增加vDPA直通设备的配置项其中source dev为host上创建的vhost-vdpa设备的字符设备路径
```xml
<devices>
<hostdev mode='subsystem' type='vdpa'>
<source dev='/dev/vhost-vdpa-0'/>
</hostdev>
</devices>
```
7. 虚拟机创建后可以在虚拟机内看到对应的virtio-net设备配置IP后网卡功能正常
```
# lspci | grep -i eth
05:00.0 Ethernet controller: Virtio: Virtio network device (rev 01)
# ifconfig eth0 192.168.1.100
# ping 192.168.1.200
PING 192.168.1.200 (192.168.1.200) 56(84) bytes of data.
64 bytes from 192.168.1.200: icmp_seq=1 ttl=64 time=0.324 ms
64 bytes from 192.168.1.200: icmp_seq=2 ttl=64 time=0.141 ms
--- 192.168.1.200 ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1001ms
rtt min/avg/max/mdev = 0.141/0.232/0.324/0.091 ms
```
## Release 计划
- generic vDPA基本功能实现 - 2024.08.30
- generic vDPA热迁移功能实现 - 2024.10.30
- generic vDPA相关文档输出 - 2024.11.30

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,411 @@
From 6dc4fe1e3b41614801ccdb92b5e7a1d8914ed939 Mon Sep 17 00:00:00 2001
From: AlexChen <alex.chen@huawei.com>
Date: Fri, 29 Mar 2024 15:27:46 +0800
Subject: [PATCH 1/3] hostdev:Introduce vDPA device to hostdev subsystem as a
new subtype
The following is the xml of vdpa device:
<devices>
<hostdev mode='subsystem' type='vdpa'>
<source dev='/dev/vhost-vdpa-0'/>
</hostdev>
</devices>
And the command line passed to QEMU is as follows:
-device {"driver":"vhost-vdpa-device-pci","vhostdev":"/dev/vhost-vdpa-0"}
This solution is selected according to the previous discussion
on the solution of supporting the vDPA device.
For details, see the following:
https://listman.redhat.com/archives/libvir-list/2023-March/239018.html
Signed-off-by: AlexChen <alex.chen@huawei.com>
---
src/conf/domain_audit.c | 4 +++
src/conf/domain_conf.c | 43 +++++++++++++++++++++++++++++++++
src/conf/domain_conf.h | 6 +++++
src/conf/domain_postparse.c | 1 +
src/conf/domain_validate.c | 1 +
src/conf/virconftypes.h | 2 ++
src/qemu/qemu_command.c | 19 +++++++++++++++
src/qemu/qemu_command.h | 3 +++
src/qemu/qemu_domain.c | 7 ++++++
src/qemu/qemu_hotplug.c | 3 +++
src/qemu/qemu_migration.c | 2 ++
src/qemu/qemu_validate.c | 2 ++
src/security/security_dac.c | 2 ++
src/security/security_selinux.c | 2 ++
14 files changed, 97 insertions(+)
diff --git a/src/conf/domain_audit.c b/src/conf/domain_audit.c
index 7a6bb02..e4d4d6d 100644
--- a/src/conf/domain_audit.c
+++ b/src/conf/domain_audit.c
@@ -344,6 +344,7 @@ virDomainAuditHostdev(virDomainObj *vm, virDomainHostdevDef *hostdev,
virDomainHostdevSubsysSCSI *scsisrc = &hostdev->source.subsys.u.scsi;
virDomainHostdevSubsysSCSIVHost *hostsrc = &hostdev->source.subsys.u.scsi_host;
virDomainHostdevSubsysMediatedDev *mdevsrc = &hostdev->source.subsys.u.mdev;
+ virDomainHostdevSubsysVDPA *vdpasrc = &hostdev->source.subsys.u.vdpa;
virUUIDFormat(vm->def->uuid, uuidstr);
if (!(vmname = virAuditEncode("vm", vm->def->name))) {
@@ -383,6 +384,9 @@ virDomainAuditHostdev(virDomainObj *vm, virDomainHostdevDef *hostdev,
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_MDEV:
address = g_strdup(mdevsrc->uuidstr);
break;
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
+ address = g_strdup(vdpasrc->devpath);
+ break;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
default:
VIR_WARN("Unexpected hostdev type while encoding audit message: %d",
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index 22ad43e..37b2460 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -1052,6 +1052,7 @@ VIR_ENUM_IMPL(virDomainHostdevSubsys,
"scsi",
"scsi_host",
"mdev",
+ "vdpa",
);
VIR_ENUM_IMPL(virDomainHostdevSubsysPCIBackend,
@@ -2645,6 +2646,9 @@ virDomainHostdevDefClear(virDomainHostdevDef *def)
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI:
g_clear_pointer(&def->source.subsys.u.pci.origstates, virBitmapFree);
break;
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
+ VIR_FREE(def->source.subsys.u.vdpa.devpath);
+ break;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_MDEV:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
@@ -6170,6 +6174,22 @@ virDomainHostdevSubsysMediatedDevDefParseXML(virDomainHostdevDef *def,
return 0;
}
+static int
+virDomainHostdevSubsysVDPADefParseXML(xmlNodePtr sourcenode,
+ virDomainHostdevDef *def)
+{
+ g_autofree char *devpath = NULL;
+ virDomainHostdevSubsysVDPA *vdpa = &def->source.subsys.u.vdpa;
+
+ if(!(devpath = virXMLPropString(sourcenode, "dev"))) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("Missing 'dev' attribute for element <source>"));
+ return -1;
+ }
+ vdpa->devpath = g_steal_pointer(&devpath);
+ return 0;
+}
+
static int
virDomainHostdevDefParseXMLSubsys(xmlNodePtr node,
xmlXPathContextPtr ctxt,
@@ -6315,6 +6335,11 @@ virDomainHostdevDefParseXMLSubsys(xmlNodePtr node,
if (virDomainHostdevSubsysMediatedDevDefParseXML(def, ctxt) < 0)
return -1;
break;
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
+ if (virDomainHostdevSubsysVDPADefParseXML(sourcenode, def) < 0) {
+ return -1;
+ }
+ break;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
default:
@@ -13005,6 +13030,7 @@ virDomainHostdevDefParseXML(virDomainXMLOption *xmlopt,
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI_HOST:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_MDEV:
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
break;
}
@@ -14152,6 +14178,9 @@ virDomainHostdevMatchSubsys(virDomainHostdevDef *a,
return 0;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_MDEV:
return virDomainHostdevMatchSubsysMediatedDev(a, b);
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
+ return STREQ(a->source.subsys.u.vdpa.devpath,
+ b->source.subsys.u.vdpa.devpath);
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
return 0;
}
@@ -23501,6 +23530,16 @@ virDomainHostdevDefFormatSubsysMdev(virBuffer *buf,
virXMLFormatElement(buf, "source", NULL, &sourceChildBuf);
}
+static void
+virDomainHostdevDefFormatSubsysVDPA(virBuffer *buf,
+ virDomainHostdevDef *def)
+{
+ g_auto(virBuffer) sourceAttrBuf = VIR_BUFFER_INITIALIZER;
+ virDomainHostdevSubsysVDPA *vdpasrc = &def->source.subsys.u.vdpa;
+ virBufferAsprintf(&sourceAttrBuf, " dev='%s'", vdpasrc->devpath);
+ virXMLFormatElement(buf, "source", &sourceAttrBuf, NULL);
+}
+
static int
virDomainHostdevDefFormatSubsys(virBuffer *buf,
@@ -23528,6 +23567,10 @@ virDomainHostdevDefFormatSubsys(virBuffer *buf,
virDomainHostdevDefFormatSubsysMdev(buf, def);
return 0;
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
+ virDomainHostdevDefFormatSubsysVDPA(buf, def);
+ return 0;
+
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
default:
virReportEnumRangeError(virDomainHostdevSubsysType, def->source.subsys.type);
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
index ed07859..9a4003c 100644
--- a/src/conf/domain_conf.h
+++ b/src/conf/domain_conf.h
@@ -197,6 +197,7 @@ typedef enum {
VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI,
VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI_HOST,
VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_MDEV,
+ VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA,
VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST
} virDomainHostdevSubsysType;
@@ -289,6 +290,10 @@ struct _virDomainHostdevSubsysMediatedDev {
virTristateSwitch ramfb;
};
+struct _virDomainHostdevSubsysVDPA {
+ char *devpath; /* vDPA device path */
+};
+
typedef enum {
VIR_DOMAIN_HOSTDEV_SUBSYS_SCSI_HOST_PROTOCOL_TYPE_NONE = 0,
VIR_DOMAIN_HOSTDEV_SUBSYS_SCSI_HOST_PROTOCOL_TYPE_VHOST,
@@ -323,6 +328,7 @@ struct _virDomainHostdevSubsys {
virDomainHostdevSubsysSCSI scsi;
virDomainHostdevSubsysSCSIVHost scsi_host;
virDomainHostdevSubsysMediatedDev mdev;
+ virDomainHostdevSubsysVDPA vdpa;
} u;
};
diff --git a/src/conf/domain_postparse.c b/src/conf/domain_postparse.c
index e79913b..b948bf0 100644
--- a/src/conf/domain_postparse.c
+++ b/src/conf/domain_postparse.c
@@ -351,6 +351,7 @@ virDomainHostdevDefPostParse(virDomainHostdevDef *dev,
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI_HOST:
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
break;
}
diff --git a/src/conf/domain_validate.c b/src/conf/domain_validate.c
index c721088..d88ef6b 100644
--- a/src/conf/domain_validate.c
+++ b/src/conf/domain_validate.c
@@ -2190,6 +2190,7 @@ virDomainHostdevDefValidate(const virDomainHostdevDef *hostdev)
}
break;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_MDEV:
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
break;
}
diff --git a/src/conf/virconftypes.h b/src/conf/virconftypes.h
index 26cb966..bcdcb8b 100644
--- a/src/conf/virconftypes.h
+++ b/src/conf/virconftypes.h
@@ -120,6 +120,8 @@ typedef struct _virDomainHostdevSubsys virDomainHostdevSubsys;
typedef struct _virDomainHostdevSubsysMediatedDev virDomainHostdevSubsysMediatedDev;
+typedef struct _virDomainHostdevSubsysVDPA virDomainHostdevSubsysVDPA;
+
typedef struct _virDomainHostdevSubsysPCI virDomainHostdevSubsysPCI;
typedef struct _virDomainHostdevSubsysSCSI virDomainHostdevSubsysSCSI;
diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index d54149e..de3be7f 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -5004,6 +5004,18 @@ qemuBuildHostdevMediatedDevProps(const virDomainDef *def,
return g_steal_pointer(&props);
}
+virJSONValue *
+qemuBuildHostdevVDPADevProps(virDomainHostdevDef *dev)
+{
+ g_autoptr(virJSONValue) props = NULL;
+ virDomainHostdevSubsysVDPA *vdpasrc = &dev->source.subsys.u.vdpa;
+ if (virJSONValueObjectAdd(&props,
+ "s:driver", "vhost-vdpa-device-pci",
+ "s:vhostdev", vdpasrc->devpath,
+ NULL) < 0)
+ return NULL;
+ return g_steal_pointer(&props);
+}
qemuBlockStorageSourceAttachData *
qemuBuildHostdevSCSIDetachPrepare(virDomainHostdevDef *hostdev,
@@ -5199,6 +5211,13 @@ qemuBuildHostdevCommandLine(virCommand *cmd,
return -1;
break;
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
+ if (!(devprops = qemuBuildHostdevVDPADevProps(hostdev)))
+ return -1;
+ if (qemuBuildDeviceCommandlineFromJSON(cmd, devprops, def, qemuCaps) < 0)
+ return -1;
+ break;
+
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
break;
}
diff --git a/src/qemu/qemu_command.h b/src/qemu/qemu_command.h
index 341ec43..432ea59 100644
--- a/src/qemu/qemu_command.h
+++ b/src/qemu/qemu_command.h
@@ -198,6 +198,9 @@ virJSONValue *
qemuBuildHostdevMediatedDevProps(const virDomainDef *def,
virDomainHostdevDef *dev);
+virJSONValue *
+qemuBuildHostdevVDPADevProps(virDomainHostdevDef *dev);
+
virJSONValue *
qemuBuildRedirdevDevProps(const virDomainDef *def,
virDomainRedirdevDef *dev);
diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c
index 953808f..834040f 100644
--- a/src/qemu/qemu_domain.c
+++ b/src/qemu/qemu_domain.c
@@ -10521,6 +10521,8 @@ qemuDomainGetHostdevPath(virDomainHostdevDef *dev,
virDomainHostdevSubsysSCSI *scsisrc = &dev->source.subsys.u.scsi;
virDomainHostdevSubsysSCSIVHost *hostsrc = &dev->source.subsys.u.scsi_host;
virDomainHostdevSubsysMediatedDev *mdevsrc = &dev->source.subsys.u.mdev;
+ virDomainHostdevSubsysVDPA *vdpasrc = &dev->source.subsys.u.vdpa;
+
g_autoptr(virUSBDevice) usb = NULL;
g_autoptr(virSCSIDevice) scsi = NULL;
g_autoptr(virSCSIVHostDevice) host = NULL;
@@ -10591,6 +10593,10 @@ qemuDomainGetHostdevPath(virDomainHostdevDef *dev,
if (!(tmpPath = virMediatedDeviceGetIOMMUGroupDev(mdevsrc->uuidstr)))
return -1;
+ perm = VIR_CGROUP_DEVICE_RW;
+ break;
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
+ tmpPath = g_strdup(vdpasrc->devpath);
perm = VIR_CGROUP_DEVICE_RW;
break;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
@@ -11366,6 +11372,7 @@ qemuDomainPrepareHostdev(virDomainHostdevDef *hostdev,
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI_HOST:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_MDEV:
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
break;
}
diff --git a/src/qemu/qemu_hotplug.c b/src/qemu/qemu_hotplug.c
index 4e2fc72..29c0856 100644
--- a/src/qemu/qemu_hotplug.c
+++ b/src/qemu/qemu_hotplug.c
@@ -2805,6 +2805,7 @@ qemuDomainAttachHostDevice(virQEMUDriver *driver,
return -1;
break;
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
default:
virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
@@ -4717,6 +4718,7 @@ qemuDomainRemoveHostDevice(virQEMUDriver *driver,
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_MDEV:
qemuDomainRemoveMediatedDevice(driver, vm, hostdev);
break;
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
break;
}
@@ -5743,6 +5745,7 @@ qemuDomainDetachPrepHostdev(virDomainObj *vm,
break;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI_HOST:
break;
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
default:
virReportError(VIR_ERR_INTERNAL_ERROR,
diff --git a/src/qemu/qemu_migration.c b/src/qemu/qemu_migration.c
index f9c34b7..9eb371b 100644
--- a/src/qemu/qemu_migration.c
+++ b/src/qemu/qemu_migration.c
@@ -1305,6 +1305,8 @@ qemuMigrationSrcIsAllowedHostdev(const virDomainDef *def)
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI_HOST:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_MDEV:
+ /* The vDPA devices don't support migration for now */
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
virReportError(VIR_ERR_OPERATION_UNSUPPORTED,
_("cannot migrate a domain with <hostdev mode='subsystem' type='%1$s'>"),
virDomainHostdevSubsysTypeToString(hostdev->source.subsys.type));
diff --git a/src/qemu/qemu_validate.c b/src/qemu/qemu_validate.c
index e475ad0..18c5b60 100644
--- a/src/qemu/qemu_validate.c
+++ b/src/qemu/qemu_validate.c
@@ -2496,6 +2496,8 @@ qemuValidateDomainDeviceDefHostdev(const virDomainHostdevDef *hostdev,
break;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_MDEV:
return qemuValidateDomainMdevDef(hostdev, def, qemuCaps);
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
+ break;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
default:
virReportEnumRangeError(virDomainHostdevSubsysType,
diff --git a/src/security/security_dac.c b/src/security/security_dac.c
index c07e488..96aebfc 100644
--- a/src/security/security_dac.c
+++ b/src/security/security_dac.c
@@ -1313,6 +1313,7 @@ virSecurityDACSetHostdevLabel(virSecurityManager *mgr,
break;
}
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
ret = 0;
break;
@@ -1469,6 +1470,7 @@ virSecurityDACRestoreHostdevLabel(virSecurityManager *mgr,
break;
}
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
ret = 0;
break;
diff --git a/src/security/security_selinux.c b/src/security/security_selinux.c
index 84c5ce7..652c086 100644
--- a/src/security/security_selinux.c
+++ b/src/security/security_selinux.c
@@ -2256,6 +2256,7 @@ virSecuritySELinuxSetHostdevSubsysLabel(virSecurityManager *mgr,
break;
}
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
ret = 0;
break;
@@ -2487,6 +2488,7 @@ virSecuritySELinuxRestoreHostdevSubsysLabel(virSecurityManager *mgr,
break;
}
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
ret = 0;
break;
--
2.46.0.windows.1

View File

@ -0,0 +1,131 @@
From 8cddfc34b30ae4a7fb62b3668d82b23a3cd7b0aa Mon Sep 17 00:00:00 2001
From: AlexChen <alex.chen@huawei.com>
Date: Fri, 29 Mar 2024 16:16:09 +0800
Subject: [PATCH 2/3] vdpa: support vdpa device hot plug/unplug
support vdpa device hot plug/unplug
Signed-off-by: AlexChen <alex.chen@huawei.com>
---
src/qemu/qemu_hotplug.c | 84 +++++++++++++++++++++++++++++++++++++++++
1 file changed, 84 insertions(+)
diff --git a/src/qemu/qemu_hotplug.c b/src/qemu/qemu_hotplug.c
index 29c0856..87353d2 100644
--- a/src/qemu/qemu_hotplug.c
+++ b/src/qemu/qemu_hotplug.c
@@ -2761,6 +2761,82 @@ qemuDomainAttachMediatedDevice(virQEMUDriver *driver,
return ret;
}
+static int
+qemuDomainAttachVDPADevice(virQEMUDriver *driver,
+ virDomainObj *vm,
+ virDomainHostdevDef *hostdev)
+{
+ int ret = -1;
+ g_autoptr(virJSONValue) devprops = NULL;
+ bool teardowncgroup = false;
+ bool teardownlabel = false;
+ bool teardowndevice = false;
+ bool teardownmemlock = false;
+ bool releaseaddr = false;
+ qemuDomainObjPrivate *priv = vm->privateData;
+ virDomainDeviceDef dev = { VIR_DOMAIN_DEVICE_HOSTDEV,
+ { .hostdev = hostdev } };
+
+ if (qemuDomainNamespaceSetupHostdev(vm, hostdev, &teardowndevice) < 0)
+ goto cleanup;
+
+ if (qemuSetupHostdevCgroup(vm, hostdev) < 0)
+ goto cleanup;
+ teardowncgroup = true;
+
+ if (qemuSecuritySetHostdevLabel(driver, vm, hostdev) < 0)
+ goto cleanup;
+ teardownlabel = true;
+
+ if (qemuDomainEnsurePCIAddress(vm, &dev) < 0)
+ goto cleanup;
+ releaseaddr = true;
+
+ qemuAssignDeviceHostdevAlias(vm->def, &hostdev->info->alias, -1);
+
+ if (!virDomainObjIsActive(vm)) {
+ virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+ _("guest unexpectedly quit during hotplug"));
+ goto cleanup;
+ }
+
+ if (!(devprops = qemuBuildHostdevVDPADevProps(hostdev)))
+ goto cleanup;
+
+ VIR_REALLOC_N(vm->def->hostdevs, vm->def->nhostdevs + 1);
+
+ if (qemuDomainAdjustMaxMemLockHostdev(vm, hostdev) < 0)
+ goto cleanup;
+ teardownmemlock = true;
+
+ qemuDomainObjEnterMonitor(vm);
+ ret = qemuMonitorAddDeviceProps(priv->mon, &devprops);
+ qemuDomainObjExitMonitor(vm);
+
+ virDomainAuditHostdev(vm, hostdev, "attach", ret == 0);
+ if (ret < 0)
+ goto cleanup;
+
+ vm->def->hostdevs[vm->def->nhostdevs++] = hostdev;
+
+ return 0;
+
+ cleanup:
+ if (teardowncgroup && qemuTeardownHostdevCgroup(vm, hostdev) < 0)
+ VIR_WARN("Unable to remove host device cgroup ACL on hotplug fail");
+ if (teardownlabel &&
+ qemuSecurityRestoreHostdevLabel(driver, vm, hostdev) < 0)
+ VIR_WARN("Unable to restore host device labelling on hotplug fail");
+ if (teardowndevice &&
+ qemuDomainNamespaceTeardownHostdev(vm, hostdev) < 0)
+ VIR_WARN("Unable to remove host device from /dev");
+ if (teardownmemlock && qemuDomainAdjustMaxMemLock(vm) < 0)
+ VIR_WARN("Unable to reset maximum locked memory on hotplug fail");
+ if (releaseaddr)
+ qemuDomainReleaseDeviceAddress(vm, hostdev->info);
+
+ return -1;
+}
static int
qemuDomainAttachHostDevice(virQEMUDriver *driver,
@@ -2806,6 +2882,9 @@ qemuDomainAttachHostDevice(virQEMUDriver *driver,
break;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
+ if (qemuDomainAttachVDPADevice(driver, vm, hostdev) < 0)
+ return -1;
+ break;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
default:
virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
@@ -5689,6 +5768,7 @@ qemuDomainDetachPrepHostdev(virDomainObj *vm,
virDomainHostdevSubsysPCI *pcisrc = &subsys->u.pci;
virDomainHostdevSubsysSCSI *scsisrc = &subsys->u.scsi;
virDomainHostdevSubsysMediatedDev *mdevsrc = &subsys->u.mdev;
+ virDomainHostdevSubsysVDPA *vdpasrc = &subsys->u.vdpa;
virDomainHostdevDef *hostdev = NULL;
int idx;
@@ -5746,6 +5826,10 @@ qemuDomainDetachPrepHostdev(virDomainObj *vm,
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI_HOST:
break;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
+ virReportError(VIR_ERR_DEVICE_MISSING,
+ _("vdpa device '%s' not found"),
+ vdpasrc->devpath);
+ break;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST:
default:
virReportError(VIR_ERR_INTERNAL_ERROR,
--
2.46.0.windows.1

View File

@ -0,0 +1,37 @@
From 6a6c0787fc4f51f0feb949f4b6b3bca5c94da064 Mon Sep 17 00:00:00 2001
From: AlexChen <alex.chen@huawei.com>
Date: Sat, 25 Nov 2023 09:55:08 +0800
Subject: [PATCH 3/3] vdpa: support vdpa device migrate
support vdpa device migrate
Signed-off-by: jiangdongxu <jiangdongxu1@huawei.com>
Signed-off-by: AlexChen <alex.chen@huawei.com>
---
src/qemu/qemu_migration.c | 5 ++---
1 file changed, 2 insertions(+), 3 deletions(-)
diff --git a/src/qemu/qemu_migration.c b/src/qemu/qemu_migration.c
index 9eb371b..8861ae2 100644
--- a/src/qemu/qemu_migration.c
+++ b/src/qemu/qemu_migration.c
@@ -1299,14 +1299,13 @@ qemuMigrationSrcIsAllowedHostdev(const virDomainDef *def)
case VIR_DOMAIN_HOSTDEV_MODE_SUBSYS:
switch (hostdev->source.subsys.type) {
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB:
- /* USB devices can be "migrated" */
+ case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
+ /* USB and VDPA devices can be "migrated" */
continue;
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI_HOST:
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_MDEV:
- /* The vDPA devices don't support migration for now */
- case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_VDPA:
virReportError(VIR_ERR_OPERATION_UNSUPPORTED,
_("cannot migrate a domain with <hostdev mode='subsystem' type='%1$s'>"),
virDomainHostdevSubsysTypeToString(hostdev->source.subsys.type));
--
2.46.0.windows.1

View File

@ -1,69 +0,0 @@
From 55c7dc34b8ff1a75bb011ca783b6cd3c7f1a5643 Mon Sep 17 00:00:00 2001
From: zhaotianrui <zhaotianrui@loongson.cn>
Date: Wed, 11 Jan 2023 11:41:55 -0500
Subject: [PATCH 2/4] Add loongarch cpu model and vendor info
Define loongarch cpu model type and vendor id in
cpu_map/loongarch.xml
Signed-off-by: zhaotianrui <zhaotianrui@loongson.cn>
---
src/cpu_map/Makefile.inc.am | 2 ++
src/cpu_map/index.xml | 5 +++++
src/cpu_map/loongarch_3a5000.xml | 6 ++++++
src/cpu_map/loongarch_vendors.xml | 3 +++
4 files changed, 16 insertions(+)
create mode 100644 src/cpu_map/loongarch_3a5000.xml
create mode 100644 src/cpu_map/loongarch_vendors.xml
diff --git a/src/cpu_map/Makefile.inc.am b/src/cpu_map/Makefile.inc.am
index 8eb818706a..3c674dea40 100644
--- a/src/cpu_map/Makefile.inc.am
+++ b/src/cpu_map/Makefile.inc.am
@@ -68,6 +68,8 @@ cpumap_DATA = \
cpu_map/x86_Skylake-Server-noTSX-IBRS.xml \
cpu_map/x86_Westmere.xml \
cpu_map/x86_Westmere-IBRS.xml \
+ cpu_map/loongarch_vendors.xml \
+ cpu_map/loongarch_3a5000.xml \
cpu_map/arm_vendors.xml \
cpu_map/arm_cortex-a53.xml \
cpu_map/arm_cortex-a57.xml \
diff --git a/src/cpu_map/index.xml b/src/cpu_map/index.xml
index 3ccc76b9ed..1c05dd814d 100644
--- a/src/cpu_map/index.xml
+++ b/src/cpu_map/index.xml
@@ -101,4 +101,9 @@
<include filename='arm_FT-2000plus.xml'/>
<include filename='arm_Tengyun-S2500.xml'/>
</arch>
+
+ <arch name='loongarch64'>
+ <include filename="loongarch_vendors.xml"/>
+ <include filename="loongarch_3a5000.xml"/>
+ </arch>
</cpus>
diff --git a/src/cpu_map/loongarch_3a5000.xml b/src/cpu_map/loongarch_3a5000.xml
new file mode 100644
index 0000000000..f6fe3386f7
--- /dev/null
+++ b/src/cpu_map/loongarch_3a5000.xml
@@ -0,0 +1,6 @@
+<cpus>
+ <model name='Loongson-3A5000'>
+ <vendor name='Loongson'/>
+ <prid value='0x14c010' mask='0xfffff0'/>
+ </model>
+</cpus>
diff --git a/src/cpu_map/loongarch_vendors.xml b/src/cpu_map/loongarch_vendors.xml
new file mode 100644
index 0000000000..c744654617
--- /dev/null
+++ b/src/cpu_map/loongarch_vendors.xml
@@ -0,0 +1,3 @@
+<cpus>
+ <vendor name='Loongson'/>
+</cpus>
--
2.25.1

View File

@ -1,994 +0,0 @@
From c0b26612cf12d5f0594a9dfa5bd97fcf7acfe9da Mon Sep 17 00:00:00 2001
From: zhaotianrui <zhaotianrui@loongson.cn>
Date: Wed, 11 Jan 2023 10:53:08 -0500
Subject: [PATCH 1/4] Add loongarch cpu support
Add loongarch cpu support: Define new cpu type 'loongarch64'
and implement it's driver functions.
Signed-off-by: zhaotianrui <zhaotianrui@loongson.cn>
---
docs/schemas/basictypes.rng | 1 +
po/POTFILES.in | 1 +
src/cpu/Makefile.inc.am | 3 +
src/cpu/cpu.c | 2 +
src/cpu/cpu.h | 3 +-
src/cpu/cpu_loongarch.c | 739 +++++++++++++++++++++++++++++++++++
src/cpu/cpu_loongarch.h | 28 ++
src/cpu/cpu_loongarch_data.h | 40 ++
src/qemu/qemu_capabilities.c | 1 +
src/qemu/qemu_domain.c | 4 +
src/util/virarch.c | 1 +
src/util/virarch.h | 3 +
12 files changed, 825 insertions(+), 1 deletion(-)
create mode 100644 src/cpu/cpu_loongarch.c
create mode 100644 src/cpu/cpu_loongarch.h
create mode 100644 src/cpu/cpu_loongarch_data.h
diff --git a/docs/schemas/basictypes.rng b/docs/schemas/basictypes.rng
index 81465273c8..34d285db48 100644
--- a/docs/schemas/basictypes.rng
+++ b/docs/schemas/basictypes.rng
@@ -444,6 +444,7 @@
<value>x86_64</value>
<value>xtensa</value>
<value>xtensaeb</value>
+ <value>loongarch64</value>
</choice>
</define>
diff --git a/po/POTFILES.in b/po/POTFILES.in
index 197ff2f3d3..24dc8087d6 100644
--- a/po/POTFILES.in
+++ b/po/POTFILES.in
@@ -60,6 +60,7 @@
@SRCDIR@/src/cpu/cpu_arm.c
@SRCDIR@/src/cpu/cpu_map.c
@SRCDIR@/src/cpu/cpu_ppc64.c
+@SRCDIR@/src/cpu/cpu_loongarch.c
@SRCDIR@/src/cpu/cpu_s390.c
@SRCDIR@/src/cpu/cpu_x86.c
@SRCDIR@/src/datatypes.c
diff --git a/src/cpu/Makefile.inc.am b/src/cpu/Makefile.inc.am
index 1ee1290c2d..e2219bbc1c 100644
--- a/src/cpu/Makefile.inc.am
+++ b/src/cpu/Makefile.inc.am
@@ -15,6 +15,9 @@ CPU_SOURCES = \
cpu/cpu_ppc64.h \
cpu/cpu_ppc64.c \
cpu/cpu_ppc64_data.h \
+ cpu/cpu_loongarch.h \
+ cpu/cpu_loongarch.c \
+ cpu/cpu_loongarch_data.h \
cpu/cpu_map.h \
cpu/cpu_map.c \
$(NULL)
diff --git a/src/cpu/cpu.c b/src/cpu/cpu.c
index 89c06aceeb..df78a0d33f 100644
--- a/src/cpu/cpu.c
+++ b/src/cpu/cpu.c
@@ -30,6 +30,7 @@
#include "cpu_s390.h"
#include "cpu_arm.h"
#include "cpu_sw64.h"
+#include "cpu_loongarch.h"
#include "capabilities.h"
#include "virstring.h"
@@ -44,6 +45,7 @@ static struct cpuArchDriver *drivers[] = {
&cpuDriverS390,
&cpuDriverArm,
&cpuDriverSW64,
+ &cpuDriverLoongArch,
};
diff --git a/src/cpu/cpu.h b/src/cpu/cpu.h
index ec22a183a1..307c85fb61 100644
--- a/src/cpu/cpu.h
+++ b/src/cpu/cpu.h
@@ -28,7 +28,7 @@
#include "cpu_x86_data.h"
#include "cpu_ppc64_data.h"
#include "cpu_arm_data.h"
-
+#include "cpu_loongarch_data.h"
typedef struct _virCPUData virCPUData;
typedef virCPUData *virCPUDataPtr;
@@ -38,6 +38,7 @@ struct _virCPUData {
virCPUx86Data x86;
virCPUppc64Data ppc64;
virCPUarmData arm;
+ virCPULoongArchData loongarch;
/* generic driver needs no data */
} data;
};
diff --git a/src/cpu/cpu_loongarch.c b/src/cpu/cpu_loongarch.c
new file mode 100644
index 0000000000..953316bf78
--- /dev/null
+++ b/src/cpu/cpu_loongarch.c
@@ -0,0 +1,739 @@
+/*
+ * cpu_loongarch.c: CPU driver for 64-bit LOONGARCH CPUs
+ *
+ * Copyright (C) 2023 Loongson Technology.
+ *
+ * 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 <fcntl.h>
+#include <unistd.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <sys/time.h>
+#include <sys/types.h>
+#include <sys/wait.h>
+#include <sys/resource.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include "virlog.h"
+#include "viralloc.h"
+#include "cpu.h"
+#include "virstring.h"
+#include "cpu_map.h"
+#include "virbuffer.h"
+
+#define VIR_FROM_THIS VIR_FROM_CPU
+
+VIR_LOG_INIT("cpu.cpu_loongarch");
+
+static const virArch archs[] = { VIR_ARCH_LOONGARCH64 };
+
+typedef struct {
+ char *name;
+} LoongArch_vendor;
+
+typedef struct {
+ char *name;
+ const LoongArch_vendor *vendor;
+ virCPULoongArchData data;
+} LoongArch_model;
+
+typedef struct {
+ size_t nvendors;
+ LoongArch_vendor **vendors;
+ size_t nmodels;
+ LoongArch_model **models;
+} LoongArch_map;
+
+static void
+LoongArchDataClear(virCPULoongArchData *data)
+{
+ if (!data)
+ return;
+
+ VIR_FREE(data->prid);
+}
+
+static int
+LoongArchDataCopy(virCPULoongArchData *dst, const virCPULoongArchData *src)
+{
+ size_t i;
+
+ if (VIR_ALLOC_N(dst->prid, src->len) < 0)
+ return -1;
+
+ dst->len = src->len;
+
+ for (i = 0; i < src->len; i++) {
+ dst->prid[i].value = src->prid[i].value;
+ dst->prid[i].mask = src->prid[i].mask;
+ }
+
+ return 0;
+}
+
+static void
+LoongArchVendorFree(LoongArch_vendor *vendor)
+{
+ if (!vendor)
+ return;
+
+ VIR_FREE(vendor->name);
+ VIR_FREE(vendor);
+}
+
+static LoongArch_vendor *
+LoongArchVendorFind(const LoongArch_map *map,
+ const char *name)
+{
+ size_t i;
+
+ for (i = 0; i < map->nvendors; i++) {
+ if (STREQ(map->vendors[i]->name, name))
+ return map->vendors[i];
+ }
+
+ return NULL;
+}
+
+static void
+LoongArchModelFree(LoongArch_model *model)
+{
+ if (!model)
+ return;
+
+ LoongArchDataClear(&model->data);
+ VIR_FREE(model->name);
+ VIR_FREE(model);
+}
+
+static LoongArch_model *
+LoongArchModelCopy(const LoongArch_model *model)
+{
+ LoongArch_model *copy;
+
+ if (VIR_ALLOC(copy) < 0)
+ goto cleanup;
+
+ copy->name = g_strdup(model->name);
+
+ if (LoongArchDataCopy(&copy->data, &model->data) < 0)
+ goto cleanup;
+
+ copy->vendor = model->vendor;
+
+ return copy;
+
+ cleanup:
+ LoongArchModelFree(copy);
+ return NULL;
+}
+
+static LoongArch_model *
+LoongArchModelFind(const LoongArch_map *map,
+ const char *name)
+{
+ size_t i;
+
+ for (i = 0; i < map->nmodels; i++) {
+ if (STREQ(map->models[i]->name, name))
+ return map->models[i];
+ }
+
+ return NULL;
+}
+
+static LoongArch_model *
+LoongArchModelFindPrid(const LoongArch_map *map,
+ uint32_t prid)
+{
+ size_t i;
+ size_t j;
+
+ for (i = 0; i < map->nmodels; i++) {
+ LoongArch_model *model = map->models[i];
+ for (j = 0; j < model->data.len; j++) {
+ if ((prid & model->data.prid[j].mask) == model->data.prid[j].value)
+ return model;
+ }
+ }
+
+ return NULL;
+}
+
+static LoongArch_model *
+LoongArchModelFromCPU(const virCPUDef *cpu,
+ const LoongArch_map *map)
+{
+ LoongArch_model *model;
+
+ if (!cpu->model) {
+ virReportError(VIR_ERR_INVALID_ARG, "%s",
+ _("no CPU model specified"));
+ return NULL;
+ }
+
+ if (!(model = LoongArchModelFind(map, cpu->model))) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Unknown CPU model %s"), cpu->model);
+ return NULL;
+ }
+
+ return LoongArchModelCopy(model);
+}
+
+static void
+LoongArchMapFree(LoongArch_map *map)
+{
+ size_t i;
+
+ if (!map)
+ return;
+
+ for (i = 0; i < map->nmodels; i++)
+ LoongArchModelFree(map->models[i]);
+ VIR_FREE(map->models);
+
+ for (i = 0; i < map->nvendors; i++)
+ LoongArchVendorFree(map->vendors[i]);
+ VIR_FREE(map->vendors);
+
+ VIR_FREE(map);
+}
+
+static int
+LoongArchVendorParse(xmlXPathContextPtr ctxt ATTRIBUTE_UNUSED,
+ const char *name,
+ void *data)
+{
+ LoongArch_map *map = data;
+ LoongArch_vendor *vendor;
+ int ret = -1;
+
+ if (VIR_ALLOC(vendor) < 0)
+ return ret;
+ vendor->name = g_strdup(name);
+
+ if (LoongArchVendorFind(map, vendor->name)) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("CPU vendor %s already defined"), vendor->name);
+ goto cleanup;
+ }
+
+ if (VIR_APPEND_ELEMENT(map->vendors, map->nvendors, vendor) < 0)
+ goto cleanup;
+
+ ret = 0;
+
+ cleanup:
+ LoongArchVendorFree(vendor);
+ return ret;
+}
+
+static int
+LoongArchModelParse(xmlXPathContextPtr ctxt,
+ const char *name,
+ void *data)
+{
+ LoongArch_map *map = data;
+ LoongArch_model *model;
+ xmlNodePtr *nodes = NULL;
+ char *vendor = NULL;
+ unsigned long prid;
+ size_t i;
+ int n;
+ int ret = -1;
+
+ if (VIR_ALLOC(model) < 0)
+ goto cleanup;
+
+ model->name = g_strdup(name);
+
+ if (LoongArchModelFind(map, model->name)) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("CPU model %s already defined"), model->name);
+ goto cleanup;
+ }
+
+ if (virXPathBoolean("boolean(./vendor)", ctxt)) {
+ vendor = virXPathString("string(./vendor/@name)", ctxt);
+ if (!vendor) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Invalid vendor element in CPU model %s"),
+ model->name);
+ goto cleanup;
+ }
+
+ if (!(model->vendor = LoongArchVendorFind(map, vendor))) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Unknown vendor %s referenced by CPU model %s"),
+ vendor, model->name);
+ goto cleanup;
+ }
+ }
+
+ if ((n = virXPathNodeSet("./prid", ctxt, &nodes)) <= 0) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Missing Prid information for CPU model %s"),
+ model->name);
+ goto cleanup;
+ }
+
+ if (VIR_ALLOC_N(model->data.prid, n) < 0)
+ goto cleanup;
+
+ model->data.len = n;
+
+ for (i = 0; i < n; i++) {
+ ctxt->node = nodes[i];
+
+ if (virXPathULongHex("string(./@value)", ctxt, &prid) < 0) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Missing or invalid Prid value in CPU model %s"),
+ model->name);
+ goto cleanup;
+ }
+ model->data.prid[i].value = prid;
+
+ if (virXPathULongHex("string(./@mask)", ctxt, &prid) < 0) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Missing or invalid PVR mask in CPU model %s"),
+ model->name);
+ goto cleanup;
+ }
+ model->data.prid[i].mask = prid;
+ }
+
+ if (VIR_APPEND_ELEMENT(map->models, map->nmodels, model) < 0)
+ goto cleanup;
+
+ ret = 0;
+
+ cleanup:
+ LoongArchModelFree(model);
+ VIR_FREE(vendor);
+ VIR_FREE(nodes);
+ return ret;
+}
+
+static LoongArch_map *
+LoongArchLoadMap(void)
+{
+ LoongArch_map *map;
+
+ if (VIR_ALLOC(map) < 0)
+ goto cleanup;
+
+ if (cpuMapLoad("loongarch64", LoongArchVendorParse, NULL, LoongArchModelParse, map) < 0)
+ goto cleanup;
+
+ return map;
+
+ cleanup:
+ LoongArchMapFree(map);
+ return NULL;
+}
+
+static virCPUDataPtr
+LoongArchMakeCPUData(virArch arch,
+ virCPULoongArchData *data)
+{
+ virCPUDataPtr cpuData;
+
+ if (VIR_ALLOC(cpuData) < 0)
+ return NULL;
+
+ cpuData->arch = arch;
+
+ if (LoongArchDataCopy(&cpuData->data.loongarch, data) < 0)
+ VIR_FREE(cpuData);
+
+ return cpuData;
+}
+
+static virCPUCompareResult
+LoongArchCompute(virCPUDefPtr host,
+ const virCPUDef *other,
+ virCPUDataPtr *guestData,
+ char **message)
+{
+ LoongArch_map *map = NULL;
+ LoongArch_model *host_model = NULL;
+ LoongArch_model *guest_model = NULL;
+ virCPUDefPtr cpu = NULL;
+ virCPUCompareResult ret = VIR_CPU_COMPARE_ERROR;
+ virArch arch;
+ size_t i;
+
+ /* Ensure existing configurations are handled correctly */
+ if (!(cpu = virCPUDefCopy(other)))
+ goto cleanup;
+
+ if (cpu->arch != VIR_ARCH_NONE) {
+ bool found = false;
+
+ for (i = 0; i < G_N_ELEMENTS(archs); i++) {
+ if (archs[i] == cpu->arch) {
+ found = true;
+ break;
+ }
+ }
+
+ if (!found) {
+ VIR_DEBUG("CPU arch %s does not match host arch",
+ virArchToString(cpu->arch));
+ if (message) {
+ *message = g_strdup_printf(_("CPU arch %s does not match host arch"),
+ virArchToString(cpu->arch));
+ }
+ ret = VIR_CPU_COMPARE_INCOMPATIBLE;
+ goto cleanup;
+ }
+ arch = cpu->arch;
+ } else {
+ arch = host->arch;
+ }
+
+ if (cpu->vendor &&
+ (!host->vendor || STRNEQ(cpu->vendor, host->vendor))) {
+ VIR_DEBUG("host CPU vendor does not match required CPU vendor %s",
+ cpu->vendor);
+ if (message) {
+ *message = g_strdup_printf(_("host CPU vendor does not match required "
+ "CPU vendor %s"), cpu->vendor);
+ }
+ ret = VIR_CPU_COMPARE_INCOMPATIBLE;
+ goto cleanup;
+ }
+
+ if (!(map = LoongArchLoadMap()))
+ goto cleanup;
+
+ /* Host CPU information */
+ if (!(host_model = LoongArchModelFromCPU(host, map)))
+ goto cleanup;
+
+ if (cpu->type == VIR_CPU_TYPE_GUEST) {
+ /* Guest CPU information */
+ switch (cpu->mode) {
+ case VIR_CPU_MODE_HOST_MODEL:
+ case VIR_CPU_MODE_HOST_PASSTHROUGH:
+ /* host-model and host-passthrough:
+ * the guest CPU is the same as the host */
+ guest_model = LoongArchModelCopy(host_model);
+ break;
+
+ case VIR_CPU_MODE_CUSTOM:
+ /* custom:
+ * look up guest CPU information */
+ guest_model = LoongArchModelFromCPU(cpu, map);
+ break;
+ }
+ } else {
+ /* Other host CPU information */
+ guest_model = LoongArchModelFromCPU(cpu, map);
+ }
+
+ if (!guest_model)
+ goto cleanup;
+
+ if (STRNEQ(guest_model->name, host_model->name)) {
+ VIR_DEBUG("host CPU model does not match required CPU model %s",
+ guest_model->name);
+ if (message) {
+ *message = g_strdup_printf(_("host CPU model does not match required "
+ "CPU model %s"),guest_model->name);
+ }
+ ret = VIR_CPU_COMPARE_INCOMPATIBLE;
+ goto cleanup;
+ }
+
+ if (guestData)
+ if (!(*guestData = LoongArchMakeCPUData(arch, &guest_model->data)))
+ goto cleanup;
+
+ ret = VIR_CPU_COMPARE_IDENTICAL;
+
+ cleanup:
+ virCPUDefFree(cpu);
+ LoongArchMapFree(map);
+ LoongArchModelFree(host_model);
+ LoongArchModelFree(guest_model);
+ return ret;
+}
+
+static virCPUCompareResult
+virCPULoongArchCompare(virCPUDefPtr host,
+ virCPUDefPtr cpu,
+ bool failIncompatible)
+{
+ virCPUCompareResult ret;
+ char *message = NULL;
+
+ if (!host || !host->model) {
+ if (failIncompatible) {
+ virReportError(VIR_ERR_CPU_INCOMPATIBLE, "%s",
+ _("unknown host CPU"));
+ } else {
+ VIR_WARN("unknown host CPU");
+ ret = VIR_CPU_COMPARE_INCOMPATIBLE;
+ }
+ return -1;
+ }
+
+ ret = LoongArchCompute(host, cpu, NULL, &message);
+
+ if (failIncompatible && ret == VIR_CPU_COMPARE_INCOMPATIBLE) {
+ ret = VIR_CPU_COMPARE_ERROR;
+ if (message) {
+ virReportError(VIR_ERR_CPU_INCOMPATIBLE, "%s", message);
+ } else {
+ virReportError(VIR_ERR_CPU_INCOMPATIBLE, NULL);
+ }
+ }
+ VIR_FREE(message);
+
+ return ret;
+}
+
+static int
+LoongArchDriverDecode(virCPUDefPtr cpu,
+ const virCPUData *data,
+ virDomainCapsCPUModelsPtr models)
+{
+ int ret = -1;
+ LoongArch_map *map;
+ const LoongArch_model *model;
+
+ if (!data || !(map = LoongArchLoadMap()))
+ return -1;
+
+ if (!(model = LoongArchModelFindPrid(map, data->data.loongarch.prid[0].value))) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ _("Cannot find CPU model with Prid 0x%08x"),
+ data->data.loongarch.prid[0].value);
+ goto cleanup;
+ }
+
+ if (!virCPUModelIsAllowed(model->name, models)) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
+ _("CPU model %s is not supported by hypervisor"),
+ model->name);
+ goto cleanup;
+ }
+
+ cpu->model = g_strdup(model->name);
+ if (model->vendor) {
+ cpu->vendor = g_strdup(model->vendor->name);
+ }
+ ret = 0;
+
+ cleanup:
+ LoongArchMapFree(map);
+
+ return ret;
+}
+
+static void
+virCPULoongArchDataFree(virCPUDataPtr data)
+{
+ if (!data)
+ return;
+
+ LoongArchDataClear(&data->data.loongarch);
+ VIR_FREE(data);
+}
+
+static int
+virCPULoongArchGetHostPRID(void)
+{
+ return 0x14c010;
+}
+
+static int
+virCPULoongArchGetHost(virCPUDefPtr cpu,
+ virDomainCapsCPUModelsPtr models)
+{
+ virCPUDataPtr cpuData = NULL;
+ virCPULoongArchData *data;
+ int ret = -1;
+
+ if (!(cpuData = virCPUDataNew(archs[0])))
+ goto cleanup;
+
+ data = &cpuData->data.loongarch;
+ if (VIR_ALLOC(data->prid) < 0)
+ goto cleanup;
+
+
+ data->len = 1;
+
+ data->prid[0].value = virCPULoongArchGetHostPRID();
+ data->prid[0].mask = 0xffff00ul;
+
+ ret = LoongArchDriverDecode(cpu, cpuData, models);
+
+ cleanup:
+ virCPULoongArchDataFree(cpuData);
+ return ret;
+}
+
+
+static int
+virCPULoongArchUpdate(virCPUDefPtr guest,
+ const virCPUDef *host ATTRIBUTE_UNUSED)
+{
+ /*
+ * - host-passthrough doesn't even get here
+ * - host-model is used for host CPU running in a compatibility mode and
+ * it needs to remain unchanged
+ * - custom doesn't support any optional features, there's nothing to
+ * update
+ */
+
+ if (guest->mode == VIR_CPU_MODE_CUSTOM)
+ guest->match = VIR_CPU_MATCH_EXACT;
+
+ return 0;
+}
+
+static virCPUDefPtr
+LoongArchDriverBaseline(virCPUDefPtr *cpus,
+ unsigned int ncpus,
+ virDomainCapsCPUModelsPtr models ATTRIBUTE_UNUSED,
+ const char **features ATTRIBUTE_UNUSED,
+ bool migratable ATTRIBUTE_UNUSED)
+{
+ LoongArch_map *map;
+ const LoongArch_model *model;
+ const LoongArch_vendor *vendor = NULL;
+ virCPUDefPtr cpu = NULL;
+ size_t i;
+
+ if (!(map = LoongArchLoadMap()))
+ goto error;
+
+ if (!(model = LoongArchModelFind(map, cpus[0]->model))) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Unknown CPU model %s"), cpus[0]->model);
+ goto error;
+ }
+
+ for (i = 0; i < ncpus; i++) {
+ const LoongArch_vendor *vnd;
+
+ if (STRNEQ(cpus[i]->model, model->name)) {
+ virReportError(VIR_ERR_OPERATION_FAILED, "%s",
+ _("CPUs are incompatible"));
+ goto error;
+ }
+
+ if (!cpus[i]->vendor)
+ continue;
+
+ if (!(vnd = LoongArchVendorFind(map, cpus[i]->vendor))) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ _("Unknown CPU vendor %s"), cpus[i]->vendor);
+ goto error;
+ }
+
+ if (model->vendor) {
+ if (model->vendor != vnd) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ _("CPU vendor %s of model %s differs from "
+ "vendor %s"),
+ model->vendor->name, model->name,
+ vnd->name);
+ goto error;
+ }
+ } else if (vendor) {
+ if (vendor != vnd) {
+ virReportError(VIR_ERR_OPERATION_FAILED, "%s",
+ _("CPU vendors do not match"));
+ goto error;
+ }
+ } else {
+ vendor = vnd;
+ }
+ }
+
+ cpu = virCPUDefNew();
+ cpu->model = g_strdup(model->name);
+ if (vendor) {
+ cpu->vendor = g_strdup(vendor->name);
+ }
+ cpu->type = VIR_CPU_TYPE_GUEST;
+ cpu->match = VIR_CPU_MATCH_EXACT;
+ cpu->fallback = VIR_CPU_FALLBACK_FORBID;
+
+ cleanup:
+ LoongArchMapFree(map);
+ return cpu;
+
+ error:
+ virCPUDefFree(cpu);
+ cpu = NULL;
+ goto cleanup;
+}
+
+static int
+virCPULoongArchDriverGetModels(char ***models)
+{
+ LoongArch_map *map;
+ size_t i;
+ int ret = -1;
+
+ if (!(map = LoongArchLoadMap())) {
+ goto error;
+ }
+
+ if (models) {
+ if (VIR_ALLOC_N(*models, map->nmodels + 1) < 0)
+ goto error;
+
+ for (i = 0; i < map->nmodels; i++) {
+ (*models)[i] = g_strdup(map->models[i]->name);
+ }
+ }
+
+ ret = map->nmodels;
+
+ cleanup:
+ LoongArchMapFree(map);
+ return ret;
+
+ error:
+ if (models) {
+ virStringListFree(*models);
+ *models = NULL;
+ }
+ goto cleanup;
+}
+
+struct cpuArchDriver cpuDriverLoongArch = {
+ .name = "LoongArch",
+ .arch = archs,
+ .narch = G_N_ELEMENTS(archs),
+ .compare = virCPULoongArchCompare,
+ .decode = LoongArchDriverDecode,
+ .encode = NULL,
+ .dataFree = virCPULoongArchDataFree,
+ .getHost = virCPULoongArchGetHost,
+ .baseline = LoongArchDriverBaseline,
+ .update = virCPULoongArchUpdate,
+ .getModels = virCPULoongArchDriverGetModels,
+};
diff --git a/src/cpu/cpu_loongarch.h b/src/cpu/cpu_loongarch.h
new file mode 100644
index 0000000000..304af628d4
--- /dev/null
+++ b/src/cpu/cpu_loongarch.h
@@ -0,0 +1,28 @@
+/*
+ * cpu_loongarch.h: CPU driver for 64-bit LOONGARCH CPUs
+ *
+ * Copyright (C) 2023 Loongson Technology.
+ *
+ * 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/>.
+ */
+
+#ifndef __VIR_CPU_LOONGARCH_H__
+# define __VIR_CPU_LOONGARCH_H__
+
+# include "cpu.h"
+
+extern struct cpuArchDriver cpuDriverLoongArch;
+
+#endif /* __VIR_CPU_LOONGARCH_H__ */
diff --git a/src/cpu/cpu_loongarch_data.h b/src/cpu/cpu_loongarch_data.h
new file mode 100644
index 0000000000..c640a0c6b4
--- /dev/null
+++ b/src/cpu/cpu_loongarch_data.h
@@ -0,0 +1,40 @@
+/*
+ * cpu_loongarch_data.h: 64-bit LOONGARCH CPU specific data
+ *
+ * Copyright (C) 2023 Loongson Technology.
+ *
+ * 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/>.
+ */
+
+#ifndef __VIR_CPU_LOONGARCH_DATA_H__
+# define __VIR_CPU_LOONGARCH_DATA_H__
+
+# include <stdint.h>
+
+typedef struct _virCPULoongArchPrid virCPULoongArchPrid;
+struct _virCPULoongArchPrid {
+ uint32_t value;
+ uint32_t mask;
+};
+
+# define VIR_CPU_LOONGARCH_DATA_INIT { 0 }
+
+typedef struct _virCPULoongArchData virCPULoongArchData;
+struct _virCPULoongArchData {
+ size_t len;
+ virCPULoongArchPrid *prid;
+};
+
+#endif /* __VIR_CPU_MIPS64_DATA_H__ */
diff --git a/src/qemu/qemu_capabilities.c b/src/qemu/qemu_capabilities.c
index 2e9f2025ba..0c3eb148b2 100644
--- a/src/qemu/qemu_capabilities.c
+++ b/src/qemu/qemu_capabilities.c
@@ -2692,6 +2692,7 @@ static const char *preferredMachines[] =
"sim", /* VIR_ARCH_XTENSAEB */
"core3", /* VIR_ARCH_SW_64 */
+ "loongson7a", /* VIR_ARCH_LOONGARCH64 */
};
G_STATIC_ASSERT(G_N_ELEMENTS(preferredMachines) == VIR_ARCH_LAST);
diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c
index 70835e4efd..37dac3694b 100644
--- a/src/qemu/qemu_domain.c
+++ b/src/qemu/qemu_domain.c
@@ -4361,6 +4361,10 @@ qemuDomainDefAddDefaultDevices(virDomainDefPtr def,
addPCIeRoot = true;
break;
+ case VIR_ARCH_LOONGARCH64:
+ addPCIeRoot = true;
+ break;
+
case VIR_ARCH_ARMV7B:
case VIR_ARCH_CRIS:
case VIR_ARCH_ITANIUM:
diff --git a/src/util/virarch.c b/src/util/virarch.c
index 653136cc73..decdbdd7ac 100644
--- a/src/util/virarch.c
+++ b/src/util/virarch.c
@@ -85,6 +85,7 @@ static const struct virArchData {
{ "xtensaeb", 32, VIR_ARCH_BIG_ENDIAN },
{ "sw_64", 64, VIR_ARCH_LITTLE_ENDIAN},
+ { "loongarch64", 64, VIR_ARCH_LITTLE_ENDIAN },
};
G_STATIC_ASSERT(G_N_ELEMENTS(virArchData) == VIR_ARCH_LAST);
diff --git a/src/util/virarch.h b/src/util/virarch.h
index 5eb146eb1b..a7834ae799 100644
--- a/src/util/virarch.h
+++ b/src/util/virarch.h
@@ -70,6 +70,7 @@ typedef enum {
VIR_ARCH_XTENSAEB, /* XTensa 32 BE http://en.wikipedia.org/wiki/Xtensa#Processor_Cores */
VIR_ARCH_SW_64, /* SW64 64 LE XHB*/
+ VIR_ARCH_LOONGARCH64, /* LoongArch 64 LE */
VIR_ARCH_LAST,
} virArch;
@@ -99,6 +100,8 @@ typedef enum {
#define ARCH_IS_SW64(arch) ((arch) == VIR_ARCH_SW_64)
+#define ARCH_IS_LOONGARCH(arch) ((arch) == VIR_ARCH_LOONGARCH64)
+
typedef enum {
VIR_ARCH_LITTLE_ENDIAN,
VIR_ARCH_BIG_ENDIAN,
--
2.25.1

View File

@ -1,263 +0,0 @@
From 4b7f6284eaa3e3b15360e25848fc68b37ee6c768 Mon Sep 17 00:00:00 2001
From: zhaotianrui <zhaotianrui@loongson.cn>
Date: Wed, 11 Jan 2023 11:56:03 -0500
Subject: [PATCH 3/4] Config some capabilities for loongarch virt machine
Config some capabilities for loongarch virt machine such as
PCI multi bus and the path of loongarch uefi binary.
Signed-off-by: zhaotianrui <zhaotianrui@loongson.cn>
---
src/qemu/qemu.conf | 3 +-
src/qemu/qemu_capabilities.c | 4 ++
src/qemu/qemu_conf.c | 3 +-
src/qemu/qemu_domain.c | 31 ++++++++++-
src/qemu/qemu_domain.h | 1 +
src/qemu/qemu_domain_address.c | 86 ++++++++++++++++++++++++++++++
src/qemu/test_libvirtd_qemu.aug.in | 1 +
7 files changed, 125 insertions(+), 4 deletions(-)
diff --git a/src/qemu/qemu.conf b/src/qemu/qemu.conf
index abdbf07fec..3856087248 100644
--- a/src/qemu/qemu.conf
+++ b/src/qemu/qemu.conf
@@ -771,7 +771,8 @@
# "/usr/share/OVMF/OVMF_CODE.fd:/usr/share/OVMF/OVMF_VARS.fd",
# "/usr/share/OVMF/OVMF_CODE.secboot.fd:/usr/share/OVMF/OVMF_VARS.fd",
# "/usr/share/AAVMF/AAVMF_CODE.fd:/usr/share/AAVMF/AAVMF_VARS.fd",
-# "/usr/share/AAVMF/AAVMF32_CODE.fd:/usr/share/AAVMF/AAVMF32_VARS.fd"
+# "/usr/share/AAVMF/AAVMF32_CODE.fd:/usr/share/AAVMF/AAVMF32_VARS.fd",
+# "/usr/share/qemu/loongarch_bios.bin:/usr/share/qemu/loongarch_vars.bin"
#]
# The backend to use for handling stdout/stderr output from
diff --git a/src/qemu/qemu_capabilities.c b/src/qemu/qemu_capabilities.c
index 0c3eb148b2..21b477cd4d 100644
--- a/src/qemu/qemu_capabilities.c
+++ b/src/qemu/qemu_capabilities.c
@@ -1983,6 +1983,10 @@ bool virQEMUCapsHasPCIMultiBus(virQEMUCapsPtr qemuCaps,
* since forever */
if (ARCH_IS_SW64(def->os.arch))
return true;
+ /* loongarch64 support PCI-multibus on all machine types
+ * since forever */
+ if (ARCH_IS_LOONGARCH(def->os.arch))
+ return true;
if (def->os.arch == VIR_ARCH_PPC ||
ARCH_IS_PPC64(def->os.arch)) {
diff --git a/src/qemu/qemu_conf.c b/src/qemu/qemu_conf.c
index 28319a1baf..3253875d6e 100644
--- a/src/qemu/qemu_conf.c
+++ b/src/qemu/qemu_conf.c
@@ -98,7 +98,8 @@ qemuDriverUnlock(virQEMUDriverPtr driver)
"/usr/share/OVMF/OVMF_CODE.fd:/usr/share/OVMF/OVMF_VARS.fd:" \
"/usr/share/OVMF/OVMF_CODE.secboot.fd:/usr/share/OVMF/OVMF_VARS.fd:" \
"/usr/share/AAVMF/AAVMF_CODE.fd:/usr/share/AAVMF/AAVMF_VARS.fd:" \
- "/usr/share/AAVMF/AAVMF32_CODE.fd:/usr/share/AAVMF/AAVMF32_VARS.fd"
+ "/usr/share/AAVMF/AAVMF32_CODE.fd:/usr/share/AAVMF/AAVMF32_VARS.fd:" \
+ "/usr/share/qemu/loongarch_bios.bin:/usr/share/qemu/loongarch_vars.bin"
#endif
diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c
index 37dac3694b..152c8615d5 100644
--- a/src/qemu/qemu_domain.c
+++ b/src/qemu/qemu_domain.c
@@ -5186,7 +5186,7 @@ qemuDomainDefValidateFeatures(const virDomainDef *def,
switch ((virDomainFeature) i) {
case VIR_DOMAIN_FEATURE_IOAPIC:
if (def->features[i] != VIR_DOMAIN_IOAPIC_NONE) {
- if (!ARCH_IS_X86(def->os.arch)) {
+ if (!ARCH_IS_X86(def->os.arch) && !ARCH_IS_LOONGARCH(def->os.arch)) {
virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
_("The '%s' feature is not supported for "
"architecture '%s' or machine type '%s'"),
@@ -9089,6 +9089,11 @@ qemuDomainControllerDefPostParse(virDomainControllerDefPtr cont,
cont->model = VIR_DOMAIN_CONTROLLER_MODEL_USB_QEMU_XHCI;
else if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_NEC_USB_XHCI))
cont->model = VIR_DOMAIN_CONTROLLER_MODEL_USB_NEC_XHCI;
+ } else if (ARCH_IS_LOONGARCH(def->os.arch)) {
+ if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE_QEMU_XHCI))
+ cont->model = VIR_DOMAIN_CONTROLLER_MODEL_USB_QEMU_XHCI;
+ else if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_NEC_USB_XHCI))
+ cont->model = VIR_DOMAIN_CONTROLLER_MODEL_USB_NEC_XHCI;
}
}
/* forbid usb model 'qusb1' and 'qusb2' in this kind of hyperviosr */
@@ -12985,6 +12990,20 @@ qemuDomainMachineIsPSeries(const char *machine,
return false;
}
+static bool
+qemuDomainMachineIsLoongson(const char *machine,
+ const virArch arch)
+{
+ if (!ARCH_IS_LOONGARCH(arch))
+ return false;
+
+ if (STREQ(machine, "loongson7a") ||
+ STRPREFIX(machine, "loongson7a-")) {
+ return true;
+ }
+
+ return false;
+}
/* You should normally avoid this function and use
* qemuDomainHasBuiltinIDE() instead. */
@@ -12996,7 +13015,8 @@ qemuDomainMachineHasBuiltinIDE(const char *machine,
STREQ(machine, "malta") ||
STREQ(machine, "sun4u") ||
STREQ(machine, "core3") ||
- STREQ(machine, "g3beige");
+ STREQ(machine, "g3beige") ||
+ STREQ(machine, "loongson7a");
}
@@ -13066,6 +13086,13 @@ qemuDomainIsPSeries(const virDomainDef *def)
}
+bool
+qemuDomainIsLoongson(const virDomainDef *def)
+{
+ return qemuDomainMachineIsLoongson(def->os.machine, def->os.arch);
+}
+
+
bool
qemuDomainHasPCIRoot(const virDomainDef *def)
{
diff --git a/src/qemu/qemu_domain.h b/src/qemu/qemu_domain.h
index 7603724ccd..368fc4030f 100644
--- a/src/qemu/qemu_domain.h
+++ b/src/qemu/qemu_domain.h
@@ -999,6 +999,7 @@ bool qemuDomainIsS390CCW(const virDomainDef *def);
bool qemuDomainIsARMVirt(const virDomainDef *def);
bool qemuDomainIsRISCVVirt(const virDomainDef *def);
bool qemuDomainIsPSeries(const virDomainDef *def);
+bool qemuDomainIsLoongson(const virDomainDef *def);
bool qemuDomainHasPCIRoot(const virDomainDef *def);
bool qemuDomainHasPCIeRoot(const virDomainDef *def);
bool qemuDomainHasBuiltinIDE(const virDomainDef *def);
diff --git a/src/qemu/qemu_domain_address.c b/src/qemu/qemu_domain_address.c
index ab6bce19f4..7f48773832 100644
--- a/src/qemu/qemu_domain_address.c
+++ b/src/qemu/qemu_domain_address.c
@@ -2078,6 +2078,87 @@ qemuDomainValidateDevicePCISlotsQ35(virDomainDefPtr def,
return 0;
}
+static int
+qemuDomainValidateDevicePCISlotsLoongson(virDomainDefPtr def,
+ virQEMUCapsPtr qemuCaps,
+ virDomainPCIAddressSetPtr addrs)
+{
+ int ret = -1;
+ virPCIDeviceAddress tmp_addr;
+ bool qemuDeviceVideoUsable = virQEMUCapsGet(qemuCaps, QEMU_CAPS_DEVICE_VIDEO_PRIMARY);
+ g_autofree char *addrStr = NULL;
+ virDomainPCIConnectFlags flags = VIR_PCI_CONNECT_TYPE_PCI_DEVICE;
+
+ if (addrs->nbuses) {
+ memset(&tmp_addr, 0, sizeof(tmp_addr));
+ tmp_addr.slot = 1;
+ /* pci-ohci at 00:01.0 */
+ if (virDomainPCIAddressReserveAddr(addrs, &tmp_addr, flags, 0) < 0)
+ return -1;
+ }
+
+ if (def->nvideos > 0 &&
+ def->videos[0]->type != VIR_DOMAIN_VIDEO_TYPE_NONE &&
+ def->videos[0]->type != VIR_DOMAIN_VIDEO_TYPE_RAMFB) {
+ /* reserve slot 2 for vga device */
+ virDomainVideoDefPtr primaryVideo = def->videos[0];
+
+ if (virDeviceInfoPCIAddressIsWanted(&primaryVideo->info)) {
+ memset(&tmp_addr, 0, sizeof(tmp_addr));
+ tmp_addr.slot = 2;
+
+ if (!(addrStr = virPCIDeviceAddressAsString(&tmp_addr)))
+ return -1;
+ if (!virDomainPCIAddressValidate(addrs, &tmp_addr,
+ addrStr, flags, true))
+ return ret;
+
+ if (virDomainPCIAddressSlotInUse(addrs, &tmp_addr)) {
+ if (qemuDeviceVideoUsable) {
+ if (qemuDomainPCIAddressReserveNextAddr(addrs,
+ &primaryVideo->info) < 0) {
+ return ret;
+ }
+ } else {
+ virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+ _("PCI address 0:0:2.0 is in use, "
+ "QEMU needs it for primary video"));
+ return ret;
+ }
+ } else {
+ if (virDomainPCIAddressReserveAddr(addrs, &tmp_addr, flags, 0) < 0)
+ return ret;
+ primaryVideo->info.addr.pci = tmp_addr;
+ primaryVideo->info.type = VIR_DOMAIN_DEVICE_ADDRESS_TYPE_PCI;
+ }
+ } else if (!qemuDeviceVideoUsable) {
+ if (primaryVideo->info.addr.pci.domain != 0 ||
+ primaryVideo->info.addr.pci.bus != 0 ||
+ primaryVideo->info.addr.pci.slot != 2 ||
+ primaryVideo->info.addr.pci.function != 0) {
+ virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+ _("Primary video card must have PCI address 0:0:2.0"));
+ return ret;
+ }
+ /* If TYPE == PCI, then qemuDomainCollectPCIAddress() function
+ * has already reserved the address, so we must skip */
+ }
+ } else if (addrs->nbuses && !qemuDeviceVideoUsable) {
+ memset(&tmp_addr, 0, sizeof(tmp_addr));
+ tmp_addr.slot = 2;
+
+ if (virDomainPCIAddressSlotInUse(addrs, &tmp_addr)) {
+ VIR_DEBUG("PCI address 0:0:2.0 in use, future addition of a video"
+ " device will not be possible without manual"
+ " intervention");
+ } else if (virDomainPCIAddressReserveAddr(addrs, &tmp_addr, flags, 0) < 0) {
+ return ret;
+ }
+ }
+
+ ret = 0;
+ return ret;
+}
static int
qemuDomainValidateDevicePCISlotsChipsets(virDomainDefPtr def,
@@ -2094,6 +2175,11 @@ qemuDomainValidateDevicePCISlotsChipsets(virDomainDefPtr def,
return -1;
}
+ if (qemuDomainIsLoongson(def) &&
+ qemuDomainValidateDevicePCISlotsLoongson(def, qemuCaps, addrs) < 0) {
+ return -1;
+ }
+
return 0;
}
diff --git a/src/qemu/test_libvirtd_qemu.aug.in b/src/qemu/test_libvirtd_qemu.aug.in
index 19da591aae..caa06a45cb 100644
--- a/src/qemu/test_libvirtd_qemu.aug.in
+++ b/src/qemu/test_libvirtd_qemu.aug.in
@@ -95,6 +95,7 @@ module Test_libvirtd_qemu =
{ "2" = "/usr/share/OVMF/OVMF_CODE.secboot.fd:/usr/share/OVMF/OVMF_VARS.fd" }
{ "3" = "/usr/share/AAVMF/AAVMF_CODE.fd:/usr/share/AAVMF/AAVMF_VARS.fd" }
{ "4" = "/usr/share/AAVMF/AAVMF32_CODE.fd:/usr/share/AAVMF/AAVMF32_VARS.fd" }
+ { "5" = "/usr/share/qemu/loongarch_bios.bin:/usr/share/qemu/loongarch_vars.bin" }
}
{ "stdio_handler" = "logd" }
{ "gluster_debug_level" = "9" }
--
2.25.1

View File

@ -1,76 +0,0 @@
From 1c5804926a289882ff4a84f1c6ca6df1dd117215 Mon Sep 17 00:00:00 2001
From: rpm-build <rpm-build>
Date: Tue, 31 Aug 2021 08:22:41 -0400
Subject: [PATCH] Don't cache device-mapper major
---
src/util/virdevmapper.c | 19 +++++--------------
1 file changed, 5 insertions(+), 14 deletions(-)
diff --git a/src/util/virdevmapper.c b/src/util/virdevmapper.c
index a471504..2b9e689 100644
--- a/src/util/virdevmapper.c
+++ b/src/util/virdevmapper.c
@@ -46,11 +46,8 @@
G_STATIC_ASSERT(BUF_SIZE > sizeof(struct dm_ioctl));
-static unsigned int virDMMajor;
-
-
static int
-virDevMapperOnceInit(void)
+virDevMapperGetMajor(unsigned int *major)
{
g_autofree char *buf = NULL;
VIR_AUTOSTRINGLIST lines = NULL;
@@ -69,7 +66,7 @@ virDevMapperOnceInit(void)
if (sscanf(lines[i], "%u %ms\n", &maj, &dev) == 2 &&
STREQ(dev, DM_NAME)) {
- virDMMajor = maj;
+ *major = maj;
break;
}
}
@@ -84,10 +81,6 @@ virDevMapperOnceInit(void)
return 0;
}
-
-VIR_ONCE_GLOBAL_INIT(virDevMapper);
-
-
static void *
virDMIoctl(int controlFD, int cmd, struct dm_ioctl *dm, char **buf)
{
@@ -305,9 +298,6 @@ virDevMapperGetTargets(const char *path,
* consist of devices or yet another targets. If that's the
* case, we have to stop recursion somewhere. */
- if (virDevMapperInitialize() < 0)
- return -1;
-
if ((controlFD = virDMOpen()) < 0)
return -1;
@@ -319,13 +309,14 @@ bool
virIsDevMapperDevice(const char *dev_name)
{
struct stat buf;
+ unsigned int major;
- if (virDevMapperInitialize() < 0)
+ if (virDevMapperGetMajor(&major) < 0)
return false;
if (!stat(dev_name, &buf) &&
S_ISBLK(buf.st_mode) &&
- major(buf.st_rdev) == virDMMajor)
+ major(buf.st_rdev) == major)
return true;
return false;
--
2.18.2

View File

@ -1,68 +0,0 @@
From bfcbf70e99b9fb06468de8135d3a251ef22e0cd3 Mon Sep 17 00:00:00 2001
From: Michal Privoznik <mprivozn@redhat.com>
Date: Mon, 14 Jun 2021 12:46:02 +0200
Subject: [PATCH 094/108] Don't call qsort() over NULL
In a few places it may happen that the array we want to sort is
still NULL (e.g. because there were no leases found, no paths for
secdriver to lock or no cache banks). However, passing NULL to
qsort() is undefined and even though glibc plays nicely we
shouldn't rely on undefined behaviour.
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
Reviewed-by: Tim Wiederhake <twiederh@redhat.com>
(cherry picked from commit 1ab5a37c4a70434a1dacebbdababb91baaa29ef1)
---
src/conf/capabilities.c | 6 ++++--
src/security/security_manager.c | 3 ++-
tools/nss/libvirt_nss.c | 3 ++-
3 files changed, 8 insertions(+), 4 deletions(-)
diff --git a/src/conf/capabilities.c b/src/conf/capabilities.c
index d6ec1f12f4..deb99cecd3 100644
--- a/src/conf/capabilities.c
+++ b/src/conf/capabilities.c
@@ -1982,8 +1982,10 @@ virCapabilitiesInitCaches(virCapsPtr caps)
/* Sort the array in order for the tests to be predictable. This way we can
* still traverse the directory instead of guessing names (in case there is
* 'index1' and 'index3' but no 'index2'). */
- qsort(caps->host.cache.banks, caps->host.cache.nbanks,
- sizeof(*caps->host.cache.banks), virCapsHostCacheBankSorter);
+ if (caps->host.cache.banks) {
+ qsort(caps->host.cache.banks, caps->host.cache.nbanks,
+ sizeof(*caps->host.cache.banks), virCapsHostCacheBankSorter);
+ }
if (virCapabilitiesInitResctrlMemory(caps) < 0)
goto cleanup;
diff --git a/src/security/security_manager.c b/src/security/security_manager.c
index 9d5dfec12b..a74b663685 100644
--- a/src/security/security_manager.c
+++ b/src/security/security_manager.c
@@ -1302,7 +1302,8 @@ virSecurityManagerMetadataLock(virSecurityManagerPtr mgr G_GNUC_UNUSED,
* paths in the same order and thus no deadlock can occur.
* Lastly, it makes searching for duplicate paths below
* simpler. */
- qsort(paths, npaths, sizeof(*paths), cmpstringp);
+ if (paths)
+ qsort(paths, npaths, sizeof(*paths), cmpstringp);
for (i = 0; i < npaths; i++) {
const char *p = paths[i];
diff --git a/tools/nss/libvirt_nss.c b/tools/nss/libvirt_nss.c
index 3b89f72742..265ef236cc 100644
--- a/tools/nss/libvirt_nss.c
+++ b/tools/nss/libvirt_nss.c
@@ -69,7 +69,8 @@ static void
sortAddr(leaseAddress *tmpAddress,
size_t ntmpAddress)
{
- qsort(tmpAddress, ntmpAddress, sizeof(*tmpAddress), leaseAddressSorter);
+ if (tmpAddress)
+ qsort(tmpAddress, ntmpAddress, sizeof(*tmpAddress), leaseAddressSorter);
}
--
2.33.0

View File

@ -1,53 +0,0 @@
From 805efc1e0446e84c4b9bf9984c92b9e05b6ced62 Mon Sep 17 00:00:00 2001
From: tangbin <tangbin_yewu@cmss.chinamobile.com>
Date: Wed, 23 Nov 2022 16:00:29 +0200
Subject: [PATCH 09/23] Fix allocation of virDomainFSDef
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Some less commonly used drivers were omitted when we switched
the allocator from a plain VIR_ALLOC to virDomainFSDefNew.
https://bugzilla.redhat.com/show_bug.cgi?id=1846450
Fixes: da665fbd4858890fbb3bbf5da2a7b6ca37bb3220
Signed-off-by: Ján Tomko <jtomko@redhat.com>
Reviewed-by: Andrea Bolognani <abologna@redhat.com>
Signed-off-by: tangbin <tangbin_yewu@cmss.chinamobile.com>
(cherry-pick from ea3320048897f5279bc49cb49d26f8099706a834)
---
src/openvz/openvz_conf.c | 2 +-
src/vbox/vbox_common.c | 2 +-
2 files changed, 2 insertions(+), 2 deletions(-)
diff --git a/src/openvz/openvz_conf.c b/src/openvz/openvz_conf.c
index 78547b8b28..15e1e2ae9f 100644
--- a/src/openvz/openvz_conf.c
+++ b/src/openvz/openvz_conf.c
@@ -357,7 +357,7 @@ openvzReadFSConf(virDomainDefPtr def,
goto error;
}
- if (VIR_ALLOC(fs) < 0)
+ if (!(fs = virDomainFSDefNew(NULL)))
goto error;
veid_str = g_strdup_printf("%d", veid);
diff --git a/src/vbox/vbox_common.c b/src/vbox/vbox_common.c
index e98ae04ec0..d06a5f79ab 100644
--- a/src/vbox/vbox_common.c
+++ b/src/vbox/vbox_common.c
@@ -3620,7 +3620,7 @@ vboxDumpSharedFolders(virDomainDefPtr def, vboxDriverPtr data, IMachine *machine
char *hostPath = NULL;
PRBool writable = PR_FALSE;
- if (VIR_ALLOC(def->fss[i]) < 0)
+ if (!(def->fss[i] = virDomainFSDefNew(data->xmlopt)))
goto cleanup;
def->fss[i]->type = VIR_DOMAIN_FS_TYPE_MOUNT;
--
2.27.0

View File

@ -1,58 +0,0 @@
From: Jim Fehlig <jfehlig@suse.com>
Date: Tue, 11 Apr 2023 09:15:43 -0600
Subject: [PATCH] qemu: Fix potential crash during driver cleanup
During qemu driver shutdown, objects are freed in qemuStateCleanup that
could still be used by active worker threads, resulting in crashes. E.g.
a worker thread could be processing a monitor EOF event after the
security manager is already disposed
Program terminated with signal SIGSEGV, Segmentation fault.
#0 0x00007fd9a9a1e1fe in virSecurityManagerMoveImageMetadata (mgr=0x7fd948012160, pid=-1, src=src@entry=0x7fd98c072c90, dst=dst@entry=0x0)
at ../../src/security/security_manager.c:468
#1 0x00007fd9646ff0f0 in qemuSecurityMoveImageMetadata (driver=driver@entry=0x7fd948043830, vm=vm@entry=0x7fd98c066db0, src=src@entry=0x7fd98c072c90,
dst=dst@entry=0x0) at ../../src/qemu/qemu_security.c:182
#2 0x00007fd96462c7b0 in qemuBlockRemoveImageMetadata (driver=driver@entry=0x7fd948043830, vm=vm@entry=0x7fd98c066db0, diskTarget=0x7fd98c072530 "vda",
src=<optimized out>) at ../../src/qemu/qemu_block.c:2628
#3 0x00007fd9646929d6 in qemuProcessStop (driver=driver@entry=0x7fd948043830, vm=vm@entry=0x7fd98c066db0, reason=reason@entry=VIR_DOMAIN_SHUTOFF_SHUTDOWN,
asyncJob=asyncJob@entry=QEMU_ASYNC_JOB_NONE, flags=<optimized out>) at ../../src/qemu/qemu_process.c:7585
#4 0x00007fd9646fc842 in processMonitorEOFEvent (vm=0x7fd98c066db0, driver=0x7fd948043830) at ../../src/qemu/qemu_driver.c:4794
#5 qemuProcessEventHandler (data=0x561a93febb60, opaque=0x7fd948043830) at ../../src/qemu/qemu_driver.c:4900
#6 0x00007fd9a9971a31 in virThreadPoolWorker (opaque=opaque@entry=0x561a93fb58e0) at ../../src/util/virthreadpool.c:163
(gdb) p mgr->drv
$2 = (virSecurityDriverPtr) 0x0
Prior to commit 7cf76d4e3ab, the worker thread pool was freed before
disposing any driver objects. Let's return to that pattern, but leave
the other changes made by 7cf76d4e3ab.
Signed-off-by: Tamara Schmitz <tamara.schmitz@suse.com>
Signed-off-by: Jim Fehlig <jfehlig@suse.com>
Reviewed-by: Martin Kletzander <mkletzan@redhat.com>
---
src/qemu/qemu_driver.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index 32b3ef3..7a70d6c 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -1120,6 +1120,7 @@ qemuStateCleanup(void)
if (!qemu_driver)
return -1;
+ virThreadPoolFree(qemu_driver->workerPool);
virObjectUnref(qemu_driver->migrationErrors);
virObjectUnref(qemu_driver->closeCallbacks);
virLockManagerPluginUnref(qemu_driver->lockManager);
@@ -1139,7 +1140,6 @@ qemuStateCleanup(void)
ebtablesContextFree(qemu_driver->ebtables);
VIR_FREE(qemu_driver->qemuImgBinary);
virObjectUnref(qemu_driver->domains);
- virThreadPoolFree(qemu_driver->workerPool);
if (qemu_driver->lockFD != -1)
virPidFileRelease(qemu_driver->config->stateDir, "driver", qemu_driver->lockFD);
--
2.33.0

View File

@ -1,211 +0,0 @@
From 9a12606bb5caf3e213ce1564445d88325592e642 Mon Sep 17 00:00:00 2001
From: AlexChen <alex.chen@huawei.com>
Date: Tue, 19 Oct 2021 14:50:32 +0800
Subject: [PATCH] Hotpatch: introduce DomainHotpatchManage API
Signed-off-by: Hao Wang <wanghao232@huawei.com>
Signed-off-by: Bihong Yu <yubihong@huawei.com>
Signed-off-by: AlexChen <alex.chen@huawei.com>
---
include/libvirt/libvirt-domain.h | 18 ++++++++++
scripts/check-aclrules.py | 1 +
src/driver-hypervisor.h | 8 +++++
src/libvirt-domain.c | 58 ++++++++++++++++++++++++++++++++
src/libvirt_public.syms | 4 +++
src/remote/remote_driver.c | 1 +
src/remote/remote_protocol.x | 20 ++++++++++-
7 files changed, 109 insertions(+), 1 deletion(-)
diff --git a/include/libvirt/libvirt-domain.h b/include/libvirt/libvirt-domain.h
index 90cb652db1..f91061724b 100644
--- a/include/libvirt/libvirt-domain.h
+++ b/include/libvirt/libvirt-domain.h
@@ -4991,4 +4991,22 @@ int virDomainBackupBegin(virDomainPtr domain,
char *virDomainBackupGetXMLDesc(virDomainPtr domain,
unsigned int flags);
+typedef enum {
+ VIR_DOMAIN_HOTPATCH_NONE = 0, /* No action */
+ VIR_DOMAIN_HOTPATCH_APPLY, /* Apply hotpatch */
+ VIR_DOMAIN_HOTPATCH_UNAPPLY, /* Unapply hotpatch */
+ VIR_DOMAIN_HOTPATCH_QUERY, /* Query hotpatch */
+
+# ifdef VIR_ENUM_SENTINELS
+ VIR_DOMAIN_HOTPATCH_LAST
+# endif
+} virDomainHotpatchAction;
+
+char *
+virDomainHotpatchManage(virDomainPtr domain,
+ int action,
+ const char *patch,
+ const char *id,
+ unsigned int flags);
+
#endif /* LIBVIRT_DOMAIN_H */
diff --git a/scripts/check-aclrules.py b/scripts/check-aclrules.py
index a1fa473174..e196f81de9 100755
--- a/scripts/check-aclrules.py
+++ b/scripts/check-aclrules.py
@@ -53,6 +53,7 @@ whitelist = {
"connectURIProbe": True,
"localOnly": True,
"domainQemuAttach": True,
+ "domainHotpatchManage": True,
}
# XXX this vzDomainMigrateConfirm3Params looks
diff --git a/src/driver-hypervisor.h b/src/driver-hypervisor.h
index bce023017d..afc21a0b3f 100644
--- a/src/driver-hypervisor.h
+++ b/src/driver-hypervisor.h
@@ -1387,6 +1387,13 @@ typedef char *
(*virDrvDomainBackupGetXMLDesc)(virDomainPtr domain,
unsigned int flags);
+typedef char *
+(*virDrvDomainHotpatchManage)(virDomainPtr domain,
+ int action,
+ const char *patch,
+ const char *id,
+ unsigned int flags);
+
typedef struct _virHypervisorDriver virHypervisorDriver;
typedef virHypervisorDriver *virHypervisorDriverPtr;
@@ -1650,4 +1657,5 @@ struct _virHypervisorDriver {
virDrvDomainAgentSetResponseTimeout domainAgentSetResponseTimeout;
virDrvDomainBackupBegin domainBackupBegin;
virDrvDomainBackupGetXMLDesc domainBackupGetXMLDesc;
+ virDrvDomainHotpatchManage domainHotpatchManage;
};
diff --git a/src/libvirt-domain.c b/src/libvirt-domain.c
index a12809c2d5..068ab52f54 100644
--- a/src/libvirt-domain.c
+++ b/src/libvirt-domain.c
@@ -12733,3 +12733,61 @@ virDomainBackupGetXMLDesc(virDomainPtr domain,
virDispatchError(conn);
return NULL;
}
+
+/**
+ * virDomainHotpatchManage:
+ * @domain: a domain object
+ * @action: the action type from virDomainHotpatchAction
+ * @patch: the target hotpatch file
+ * @id: the patch id of the target hotpatch
+ * @flags: extra flags; not used yet, so callers should always pass 0
+ *
+ * Manage hotpatch for the current domain according to @action.
+ *
+ * If the @action is set to VIR_DOMAIN_HOTPATCH_APPLY, apply hotpatch
+ * @patch to the current domain.
+ *
+ * If the @action is set to VIR_DOMAIN_HOTPATCH_UNAPPLY, unapply the
+ * hotpatch which is matched with @id from the current domain.
+ *
+ * If the @action is set to VIR_DOMAIN_HOTPATCH_QUERY, query infomations
+ * of the applied hotpatch of the current domain.
+ *
+ * Returns success messages in case of success, NULL otherwise.
+ */
+char *
+virDomainHotpatchManage(virDomainPtr domain,
+ int action,
+ const char *patch,
+ const char *id,
+ unsigned int flags)
+{
+ virConnectPtr conn;
+
+ virResetLastError();
+
+ virCheckDomainReturn(domain, NULL);
+ conn = domain->conn;
+
+ virCheckReadOnlyGoto(conn->flags, error);
+
+ if (action == VIR_DOMAIN_HOTPATCH_APPLY)
+ virCheckNonNullArgGoto(patch, error);
+
+ if (action == VIR_DOMAIN_HOTPATCH_UNAPPLY)
+ virCheckNonNullArgGoto(id, error);
+
+ if (conn->driver->domainHotpatchManage) {
+ char *ret;
+ ret = conn->driver->domainHotpatchManage(domain, action, patch, id, flags);
+ if (!ret)
+ goto error;
+
+ return ret;
+ }
+
+ virReportUnsupportedError();
+ error:
+ virDispatchError(conn);
+ return NULL;
+}
diff --git a/src/libvirt_public.syms b/src/libvirt_public.syms
index 539d2e3943..0ad0b9e489 100644
--- a/src/libvirt_public.syms
+++ b/src/libvirt_public.syms
@@ -873,4 +873,8 @@ LIBVIRT_6.0.0 {
virDomainBackupGetXMLDesc;
} LIBVIRT_5.10.0;
+LIBVIRT_6.2.0 {
+ global:
+ virDomainHotpatchManage;
+} LIBVIRT_6.0.0;
# .... define new API here using predicted next version number ....
diff --git a/src/remote/remote_driver.c b/src/remote/remote_driver.c
index 7bae0c2514..1202d44017 100644
--- a/src/remote/remote_driver.c
+++ b/src/remote/remote_driver.c
@@ -8684,6 +8684,7 @@ static virHypervisorDriver hypervisor_driver = {
.domainAgentSetResponseTimeout = remoteDomainAgentSetResponseTimeout, /* 5.10.0 */
.domainBackupBegin = remoteDomainBackupBegin, /* 6.0.0 */
.domainBackupGetXMLDesc = remoteDomainBackupGetXMLDesc, /* 6.0.0 */
+ .domainHotpatchManage = remoteDomainHotpatchManage, /* 6.2.0 */
};
static virNetworkDriver network_driver = {
diff --git a/src/remote/remote_protocol.x b/src/remote/remote_protocol.x
index 8b05082b61..ee13075ce1 100644
--- a/src/remote/remote_protocol.x
+++ b/src/remote/remote_protocol.x
@@ -3771,6 +3771,18 @@ struct remote_domain_backup_get_xml_desc_ret {
remote_nonnull_string xml;
};
+struct remote_domain_hotpatch_manage_args {
+ remote_nonnull_domain dom;
+ int action;
+ remote_string patch;
+ remote_string id;
+ unsigned int flags;
+};
+
+struct remote_domain_hotpatch_manage_ret {
+ remote_string info;
+};
+
/*----- Protocol. -----*/
/* Define the program number, protocol version and procedure numbers here. */
@@ -6668,5 +6680,11 @@ enum remote_procedure {
* @priority: high
* @acl: domain:read
*/
- REMOTE_PROC_DOMAIN_BACKUP_GET_XML_DESC = 422
+ REMOTE_PROC_DOMAIN_BACKUP_GET_XML_DESC = 422,
+
+ /**
+ * @generate: both
+ * @acl: domain:read
+ */
+ REMOTE_PROC_DOMAIN_HOTPATCH_MANAGE = 800
};
--
2.27.0

View File

@ -1,65 +0,0 @@
From 4123437e633f05af0ae8091d5db440597394ba36 Mon Sep 17 00:00:00 2001
From: zhaotianrui <zhaotianrui@loongson.cn>
Date: Wed, 11 Jan 2023 14:09:41 -0500
Subject: [PATCH 4/4] Implement the method of getting host info for loongarch
Implement method for loongarch to get host info, such as
cpu frequency, system info, etc.
Signed-off-by: zhaotianrui <zhaotianrui@loongson.cn>
---
src/util/virarch.c | 2 ++
src/util/virhostcpu.c | 2 +-
src/util/virsysinfo.c | 3 ++-
3 files changed, 5 insertions(+), 2 deletions(-)
diff --git a/src/util/virarch.c b/src/util/virarch.c
index decdbdd7ac..0520a1c80b 100644
--- a/src/util/virarch.c
+++ b/src/util/virarch.c
@@ -227,6 +227,8 @@ virArch virArchFromHost(void)
arch = VIR_ARCH_X86_64;
} else if (STREQ(ut.machine, "sw_64")) {
arch = VIR_ARCH_SW_64;
+ } else if (STREQ(ut.machine, "loongarch64")) {
+ arch = VIR_ARCH_LOONGARCH64;
} else {
/* Otherwise assume the canonical name */
if ((arch = virArchFromString(ut.machine)) == VIR_ARCH_NONE) {
diff --git a/src/util/virhostcpu.c b/src/util/virhostcpu.c
index 5ec98d6016..ce3da7e6ec 100644
--- a/src/util/virhostcpu.c
+++ b/src/util/virhostcpu.c
@@ -577,7 +577,7 @@ virHostCPUParseFrequency(FILE *cpuinfo,
char line[1024];
/* No sensible way to retrieve CPU frequency */
- if (ARCH_IS_ARM(arch))
+ if (ARCH_IS_ARM(arch) || ARCH_IS_LOONGARCH(arch))
return 0;
if (ARCH_IS_X86(arch))
diff --git a/src/util/virsysinfo.c b/src/util/virsysinfo.c
index 8a53702224..6d4778fed7 100644
--- a/src/util/virsysinfo.c
+++ b/src/util/virsysinfo.c
@@ -1190,7 +1190,7 @@ virSysinfoRead(void)
{
#if defined(__powerpc__)
return virSysinfoReadPPC();
-#elif defined(__arm__) || defined(__aarch64__)
+#elif defined(__arm__) || defined(__aarch64__) || defined(__loongarch__)
return virSysinfoReadARM();
#elif defined(__s390__) || defined(__s390x__)
return virSysinfoReadS390();
@@ -1198,6 +1198,7 @@ virSysinfoRead(void)
(defined(__x86_64__) || \
defined(__i386__) || \
defined(__amd64__) || \
+ defined(__loongarch__) || \
defined(__sw_64__))
return virSysinfoReadDMI();
#else /* WIN32 || not supported arch */
--
2.25.1

View File

@ -1,322 +0,0 @@
From e8597e64126a5cf77fbb9422977268878a6376b6 Mon Sep 17 00:00:00 2001
From: AlexChen <alex.chen@huawei.com>
Date: Wed, 14 Oct 2020 12:08:30 -0500
Subject: [PATCH] Include vdpa devices in node device list
The current udev node device driver ignores all events related to vdpa
devices. Since libvirt now supports vDPA network devices, include these
devices in the device list.
Example output:
virsh # nodedev-list
[...ommitted long list of nodedevs...]
vdpa_vdpa0
virsh # nodedev-dumpxml vdpa_vdpa0
<device>
<name>vdpa_vdpa0</name>
<path>/sys/devices/vdpa0</path>
<parent>computer</parent>
<driver>
<name>vhost_vdpa</name>
</driver>
<capability type='vdpa'>
<chardev>/dev/vhost-vdpa-0</chardev>
</capability>
</device>
NOTE: normally the 'parent' would be a PCI device instead of 'computer',
but this example output is from the vdpa_sim kernel module, so it
doesn't have a normal parent device.
Signed-off-by: Jonathon Jongsma <jjongsma@redhat.com>
Signed-off-by: AlexChen <alex.chen@huawei.com>
---
docs/formatnode.html.in | 9 ++++++
docs/schemas/nodedev.rng | 10 ++++++
include/libvirt/libvirt-nodedev.h | 1 +
src/conf/node_device_conf.c | 13 ++++++++
src/conf/node_device_conf.h | 11 ++++++-
src/conf/virnodedeviceobj.c | 4 ++-
src/node_device/node_device_udev.c | 51 ++++++++++++++++++++++++++++++
tools/virsh-nodedev.c | 3 ++
8 files changed, 100 insertions(+), 2 deletions(-)
diff --git a/docs/formatnode.html.in b/docs/formatnode.html.in
index c2a8f8fb7a..573391ef0f 100644
--- a/docs/formatnode.html.in
+++ b/docs/formatnode.html.in
@@ -341,6 +341,15 @@
<dd>The device number.</dd>
</dl>
</dd>
+ <dt><code>vdpa</code></dt>
+ <dd>Describes a virtual datapath acceleration (vDPA) network device.
+ <span class="since">Since 6.9.0</span>. Sub-elements include:
+ <dl>
+ <dt><code>chardev</code></dt>
+ <dd>The path to the character device that is used to access the
+ device.</dd>
+ </dl>
+ </dd>
</dl>
</dd>
</dl>
diff --git a/docs/schemas/nodedev.rng b/docs/schemas/nodedev.rng
index fe6ffa0b53..4f197b327a 100644
--- a/docs/schemas/nodedev.rng
+++ b/docs/schemas/nodedev.rng
@@ -85,6 +85,7 @@
<ref name="capdrm"/>
<ref name="capmdev"/>
<ref name="capccwdev"/>
+ <ref name="capvdpa"/>
</choice>
</element>
</define>
@@ -651,6 +652,15 @@
</element>
</define>
+ <define name="capvdpa">
+ <attribute name="type">
+ <value>vdpa</value>
+ </attribute>
+ <element name="chardev">
+ <ref name="path"/>
+ </element>
+ </define>
+
<define name='address'>
<element name='address'>
<attribute name='domain'><ref name='hexuint'/></attribute>
diff --git a/include/libvirt/libvirt-nodedev.h b/include/libvirt/libvirt-nodedev.h
index a2ad61ac6d..4129f1afed 100644
--- a/include/libvirt/libvirt-nodedev.h
+++ b/include/libvirt/libvirt-nodedev.h
@@ -81,6 +81,7 @@ typedef enum {
VIR_CONNECT_LIST_NODE_DEVICES_CAP_MDEV_TYPES = 1 << 13, /* Capable of mediated devices */
VIR_CONNECT_LIST_NODE_DEVICES_CAP_MDEV = 1 << 14, /* Mediated device */
VIR_CONNECT_LIST_NODE_DEVICES_CAP_CCW_DEV = 1 << 15, /* CCW device */
+ VIR_CONNECT_LIST_NODE_DEVICES_CAP_VDPA = 1 << 17, /* vDPA device */
} virConnectListAllNodeDeviceFlags;
int virConnectListAllNodeDevices (virConnectPtr conn,
diff --git a/src/conf/node_device_conf.c b/src/conf/node_device_conf.c
index d64f6d3986..41d7c7d12e 100644
--- a/src/conf/node_device_conf.c
+++ b/src/conf/node_device_conf.c
@@ -65,6 +65,7 @@ VIR_ENUM_IMPL(virNodeDevCap,
"mdev_types",
"mdev",
"ccw",
+ "vdpa",
);
VIR_ENUM_IMPL(virNodeDevNetCap,
@@ -500,6 +501,12 @@ virNodeDeviceCapStorageDefFormat(virBufferPtr buf,
virBufferAddLit(buf, "<capability type='hotpluggable'/>\n");
}
+static void
+virNodeDeviceCapVDPADefFormat(virBufferPtr buf,
+ const virNodeDevCapData *data)
+{
+ virBufferEscapeString(buf, "<chardev>%s</chardev>\n", data->vdpa.chardev);
+}
char *
virNodeDeviceDefFormat(const virNodeDeviceDef *def)
@@ -595,6 +602,9 @@ virNodeDeviceDefFormat(const virNodeDeviceDef *def)
virBufferAsprintf(&buf, "<devno>0x%04x</devno>\n",
data->ccw_dev.devno);
break;
+ case VIR_NODE_DEV_CAP_VDPA:
+ virNodeDeviceCapVDPADefFormat(&buf, data);
+ break;
case VIR_NODE_DEV_CAP_MDEV_TYPES:
case VIR_NODE_DEV_CAP_FC_HOST:
case VIR_NODE_DEV_CAP_VPORTS:
@@ -1897,6 +1907,7 @@ virNodeDevCapsDefParseXML(xmlXPathContextPtr ctxt,
case VIR_NODE_DEV_CAP_FC_HOST:
case VIR_NODE_DEV_CAP_VPORTS:
case VIR_NODE_DEV_CAP_SCSI_GENERIC:
+ case VIR_NODE_DEV_CAP_VDPA:
case VIR_NODE_DEV_CAP_LAST:
virReportError(VIR_ERR_INTERNAL_ERROR,
_("unknown capability type '%d' for '%s'"),
@@ -2209,6 +2220,7 @@ virNodeDevCapsDefFree(virNodeDevCapsDefPtr caps)
case VIR_NODE_DEV_CAP_FC_HOST:
case VIR_NODE_DEV_CAP_VPORTS:
case VIR_NODE_DEV_CAP_CCW_DEV:
+ case VIR_NODE_DEV_CAP_VDPA:
case VIR_NODE_DEV_CAP_LAST:
/* This case is here to shutup the compiler */
break;
@@ -2262,6 +2274,7 @@ virNodeDeviceUpdateCaps(virNodeDeviceDefPtr def)
case VIR_NODE_DEV_CAP_MDEV_TYPES:
case VIR_NODE_DEV_CAP_MDEV:
case VIR_NODE_DEV_CAP_CCW_DEV:
+ case VIR_NODE_DEV_CAP_VDPA:
case VIR_NODE_DEV_CAP_LAST:
break;
}
diff --git a/src/conf/node_device_conf.h b/src/conf/node_device_conf.h
index 9e4b0847fb..a14eaef742 100644
--- a/src/conf/node_device_conf.h
+++ b/src/conf/node_device_conf.h
@@ -64,6 +64,7 @@ typedef enum {
VIR_NODE_DEV_CAP_MDEV_TYPES, /* Device capable of mediated devices */
VIR_NODE_DEV_CAP_MDEV, /* Mediated device */
VIR_NODE_DEV_CAP_CCW_DEV, /* s390 CCW device */
+ VIR_NODE_DEV_CAP_VDPA, /* vDPA device */
VIR_NODE_DEV_CAP_LAST
} virNodeDevCapType;
@@ -271,6 +272,12 @@ struct _virNodeDevCapCCW {
unsigned int devno;
};
+typedef struct _virNodeDevCapVDPA virNodeDevCapVDPA;
+typedef virNodeDevCapVDPA *virNodeDevCapVDPAPtr;
+struct _virNodeDevCapVDPA {
+ char *chardev;
+};
+
typedef struct _virNodeDevCapData virNodeDevCapData;
typedef virNodeDevCapData *virNodeDevCapDataPtr;
struct _virNodeDevCapData {
@@ -289,6 +296,7 @@ struct _virNodeDevCapData {
virNodeDevCapDRM drm;
virNodeDevCapMdev mdev;
virNodeDevCapCCW ccw_dev;
+ virNodeDevCapVDPA vdpa;
};
};
@@ -364,7 +372,8 @@ virNodeDevCapsDefFree(virNodeDevCapsDefPtr caps);
VIR_CONNECT_LIST_NODE_DEVICES_CAP_DRM | \
VIR_CONNECT_LIST_NODE_DEVICES_CAP_MDEV_TYPES | \
VIR_CONNECT_LIST_NODE_DEVICES_CAP_MDEV | \
- VIR_CONNECT_LIST_NODE_DEVICES_CAP_CCW_DEV)
+ VIR_CONNECT_LIST_NODE_DEVICES_CAP_CCW_DEV | \
+ VIR_CONNECT_LIST_NODE_DEVICES_CAP_VDPA)
int
virNodeDeviceGetSCSIHostCaps(virNodeDevCapSCSIHostPtr scsi_host);
diff --git a/src/conf/virnodedeviceobj.c b/src/conf/virnodedeviceobj.c
index 3a34a324ca..be111741bf 100644
--- a/src/conf/virnodedeviceobj.c
+++ b/src/conf/virnodedeviceobj.c
@@ -676,6 +676,7 @@ virNodeDeviceObjHasCap(const virNodeDeviceObj *obj,
case VIR_NODE_DEV_CAP_MDEV_TYPES:
case VIR_NODE_DEV_CAP_MDEV:
case VIR_NODE_DEV_CAP_CCW_DEV:
+ case VIR_NODE_DEV_CAP_VDPA:
case VIR_NODE_DEV_CAP_LAST:
break;
}
@@ -826,7 +827,8 @@ virNodeDeviceObjMatch(virNodeDeviceObjPtr obj,
MATCH(DRM) ||
MATCH(MDEV_TYPES) ||
MATCH(MDEV) ||
- MATCH(CCW_DEV)))
+ MATCH(CCW_DEV) ||
+ MATCH(VDPA)))
return false;
}
diff --git a/src/node_device/node_device_udev.c b/src/node_device/node_device_udev.c
index 0d8a7db5c6..2764315325 100644
--- a/src/node_device/node_device_udev.c
+++ b/src/node_device/node_device_udev.c
@@ -1089,6 +1089,53 @@ udevProcessCCW(struct udev_device *device,
return 0;
}
+static int
+udevGetVDPACharDev(const char *sysfs_path,
+ virNodeDevCapDataPtr data)
+{
+ struct dirent *entry;
+ DIR *dir = NULL;
+ int direrr;
+
+ if (virDirOpenIfExists(&dir, sysfs_path) <= 0)
+ return -1;
+
+ while ((direrr = virDirRead(dir, &entry, NULL)) > 0) {
+ if (g_str_has_prefix(entry->d_name, "vhost-vdpa")) {
+ g_autofree char *chardev = g_strdup_printf("/dev/%s", entry->d_name);
+
+ if (!virFileExists(chardev)) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("vDPA chardev path '%s' does not exist"),
+ chardev);
+ return -1;
+ }
+ VIR_DEBUG("vDPA chardev is at '%s'", chardev);
+
+ data->vdpa.chardev = g_steal_pointer(&chardev);
+ break;
+ }
+ }
+
+ if (direrr < 0)
+ return -1;
+
+ return 0;
+}
+
+static int
+udevProcessVDPA(struct udev_device *device,
+ virNodeDeviceDefPtr def)
+{
+ if (udevGenerateDeviceName(device, def, NULL) != 0)
+ return -1;
+
+ if (udevGetVDPACharDev(def->sysfs_path, &def->caps->data) < 0)
+ return -1;
+
+ return 0;
+}
+
static int
udevGetDeviceNodes(struct udev_device *device,
@@ -1168,6 +1215,8 @@ udevGetDeviceType(struct udev_device *device,
*type = VIR_NODE_DEV_CAP_MDEV;
else if (STREQ_NULLABLE(subsystem, "ccw"))
*type = VIR_NODE_DEV_CAP_CCW_DEV;
+ else if (STREQ_NULLABLE(subsystem, "vdpa"))
+ *type = VIR_NODE_DEV_CAP_VDPA;
VIR_FREE(subsystem);
}
@@ -1212,6 +1261,8 @@ udevGetDeviceDetails(struct udev_device *device,
return udevProcessMediatedDevice(device, def);
case VIR_NODE_DEV_CAP_CCW_DEV:
return udevProcessCCW(device, def);
+ case VIR_NODE_DEV_CAP_VDPA:
+ return udevProcessVDPA(device, def);
case VIR_NODE_DEV_CAP_MDEV_TYPES:
case VIR_NODE_DEV_CAP_SYSTEM:
case VIR_NODE_DEV_CAP_FC_HOST:
diff --git a/tools/virsh-nodedev.c b/tools/virsh-nodedev.c
index 7f091d7cf8..f831b36054 100644
--- a/tools/virsh-nodedev.c
+++ b/tools/virsh-nodedev.c
@@ -462,6 +462,9 @@ cmdNodeListDevices(vshControl *ctl, const vshCmd *cmd G_GNUC_UNUSED)
case VIR_NODE_DEV_CAP_CCW_DEV:
flags |= VIR_CONNECT_LIST_NODE_DEVICES_CAP_CCW_DEV;
break;
+ case VIR_NODE_DEV_CAP_VDPA:
+ flags |= VIR_CONNECT_LIST_NODE_DEVICES_CAP_VDPA;
+ break;
case VIR_NODE_DEV_CAP_LAST:
break;
}
--
2.27.0

View File

@ -1,108 +0,0 @@
From 78c25600daf2a2822e7ecec2af9e7458b9f44eff Mon Sep 17 00:00:00 2001
From: yezengruan <yezengruan@huawei.com>
Date: Sat, 12 Mar 2022 09:35:07 +0800
Subject: [PATCH 1/6] Revert libvirt: support aarch64 vtpm with parameter
tpm-tis-device
Before backport the patch support aarch64 vtpm, let's
revert it first.
Signed-off-by: yezengruan <yezengruan@huawei.com>
---
src/conf/domain_conf.c | 1 -
src/conf/domain_conf.h | 1 -
src/qemu/qemu_capabilities.c | 9 +--------
src/qemu/qemu_capabilities.h | 4 +---
src/qemu/qemu_domain.c | 3 ---
5 files changed, 2 insertions(+), 16 deletions(-)
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index 4e3bcf479c..54228a2151 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -1141,7 +1141,6 @@ VIR_ENUM_IMPL(virDomainTPMModel,
"tpm-tis",
"tpm-crb",
"tpm-spapr",
- "tpm-tis-device",
);
VIR_ENUM_IMPL(virDomainTPMBackend,
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
index ccee986849..e057c384c6 100644
--- a/src/conf/domain_conf.h
+++ b/src/conf/domain_conf.h
@@ -1280,7 +1280,6 @@ typedef enum {
VIR_DOMAIN_TPM_MODEL_TIS,
VIR_DOMAIN_TPM_MODEL_CRB,
VIR_DOMAIN_TPM_MODEL_SPAPR,
- VIR_DOMAIN_TPM_MODEL_TIS_DEVICE,
VIR_DOMAIN_TPM_MODEL_LAST
} virDomainTPMModel;
diff --git a/src/qemu/qemu_capabilities.c b/src/qemu/qemu_capabilities.c
index 6013be9d05..0fb3e74c77 100644
--- a/src/qemu/qemu_capabilities.c
+++ b/src/qemu/qemu_capabilities.c
@@ -568,9 +568,7 @@ VIR_ENUM_IMPL(virQEMUCaps,
"blockdev-snapshot.allow-write-only-overlay",
"blockdev-reopen",
"storage.werror",
-
- /* 360 */
- "tpm-tis-device",
+
"migration-param.bandwidth",
"migration-param.downtime",
"migration-param.xbzrle-cache-size",
@@ -1292,7 +1290,6 @@ struct virQEMUCapsStringFlags virQEMUCapsObjectTypes[] = {
{ "rng-builtin", QEMU_CAPS_OBJECT_RNG_BUILTIN },
{ "tpm-spapr", QEMU_CAPS_DEVICE_TPM_SPAPR },
{ "vhost-user-fs-device", QEMU_CAPS_DEVICE_VHOST_USER_FS },
- { "tpm-tis-device", QEMU_CAPS_DEVICE_TPM_TIS_DEVICE },
};
static struct virQEMUCapsStringFlags virQEMUCapsDevicePropsVirtioBalloon[] = {
@@ -3100,10 +3097,6 @@ const struct tpmTypeToCaps virQEMUCapsTPMModelsToCaps[] = {
.type = VIR_DOMAIN_TPM_MODEL_SPAPR,
.caps = QEMU_CAPS_DEVICE_TPM_SPAPR,
},
- {
- .type = VIR_DOMAIN_TPM_MODEL_TIS_DEVICE,
- .caps = QEMU_CAPS_DEVICE_TPM_TIS_DEVICE,
- },
};
static int
diff --git a/src/qemu/qemu_capabilities.h b/src/qemu/qemu_capabilities.h
index 5f28006b48..10a6ce50e7 100644
--- a/src/qemu/qemu_capabilities.h
+++ b/src/qemu/qemu_capabilities.h
@@ -549,9 +549,7 @@ typedef enum { /* virQEMUCapsFlags grouping marker for syntax-check */
QEMU_CAPS_BLOCKDEV_SNAPSHOT_ALLOW_WRITE_ONLY, /* blockdev-snapshot has the 'allow-write-only-overlay' feature */
QEMU_CAPS_BLOCKDEV_REOPEN, /* 'blockdev-reopen' qmp command is supported */
QEMU_CAPS_STORAGE_WERROR, /* virtio-blk,scsi-hd.werror */
-
- /* 360 */
- QEMU_CAPS_DEVICE_TPM_TIS_DEVICE, /* -device tpm-tis-device */
+
QEMU_CAPS_MIGRATION_PARAM_BANDWIDTH, /* max-bandwidth field in migrate-set-parameters */
QEMU_CAPS_MIGRATION_PARAM_DOWNTIME, /* downtime-limit field in migrate-set-parameters */
QEMU_CAPS_MIGRATION_PARAM_XBZRLE_CACHE_SIZE, /* xbzrle-cache-size field in migrate-set-parameters */
diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c
index 2351cac120..cb2fbdc179 100644
--- a/src/qemu/qemu_domain.c
+++ b/src/qemu/qemu_domain.c
@@ -8130,9 +8130,6 @@ qemuDomainDeviceDefValidateTPM(virDomainTPMDef *tpm,
case VIR_DOMAIN_TPM_MODEL_SPAPR:
flag = QEMU_CAPS_DEVICE_TPM_SPAPR;
break;
- case VIR_DOMAIN_TPM_MODEL_TIS_DEVICE:
- flag = QEMU_CAPS_DEVICE_TPM_TIS_DEVICE;
- break;
case VIR_DOMAIN_TPM_MODEL_LAST:
default:
virReportEnumRangeError(virDomainTPMModel, tpm->model);
--
2.27.0

View File

@ -1,36 +0,0 @@
From 3dc1e0f37c013c317f3e868d1e4a6668d8f18a03 Mon Sep 17 00:00:00 2001
From: mayunlong <mayunlong6@huawei.com>
Date: Wed, 9 Aug 2023 20:51:37 +0800
Subject: [PATCH] Revert "selinux: adapt to libselinux"
use the solution modified by the upstream community torevert this patch
This reverts commit 20fd0fb6b915363efecd2d108363995d8dea8e1a.
---
src/security/security_selinux.c | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/src/security/security_selinux.c b/src/security/security_selinux.c
index cb4dc3e101..c91c7ca484 100644
--- a/src/security/security_selinux.c
+++ b/src/security/security_selinux.c
@@ -541,7 +541,7 @@ static char *
virSecuritySELinuxContextAddRange(char *src,
char *dst)
{
- const char *str = NULL;
+ char *str = NULL;
char *ret = NULL;
context_t srccon = NULL;
context_t dstcon = NULL;
@@ -582,7 +582,7 @@ virSecuritySELinuxGenNewContext(const char *basecontext,
{
context_t context = NULL;
char *ret = NULL;
- const char *str;
+ char *str;
char *ourSecContext = NULL;
context_t ourContext = NULL;
--
2.41.0.windows.1

View File

@ -1,42 +0,0 @@
From 8629a253113a019215b38f7206db03892157a370 Mon Sep 17 00:00:00 2001
From: imxcc <xingchaochao@huawei.com>
Date: Sat, 29 Jan 2022 17:14:59 +0800
Subject: [PATCH] Revert tests: disabale storage tests
Signed-off-by: imxcc <xingchaochao@huawei.com>
---
tests/Makefile.am | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/tests/Makefile.am b/tests/Makefile.am
index abb261e..ada5b8f 100644
--- a/tests/Makefile.am
+++ b/tests/Makefile.am
@@ -363,10 +363,16 @@ endif WITH_NWFILTER
if WITH_STORAGE
test_programs += storagevolxml2argvtest
+test_programs += storagepoolxml2argvtest
test_programs += virstorageutiltest
+test_programs += storagepoolxml2xmltest
test_programs += storagepoolcapstest
endif WITH_STORAGE
+if WITH_STORAGE_FS
+test_programs += virstoragetest
+endif WITH_STORAGE_FS
+
if WITH_LINUX
test_programs += virscsitest
endif WITH_LINUX
@@ -424,6 +430,7 @@ test_scripts += $(libvirtd_test_scripts)
test_programs += \
eventtest \
+ virdrivermoduletest \
virdriverconnvalidatetest
else ! WITH_LIBVIRTD
EXTRA_DIST += $(libvirtd_test_scripts)
--
2.27.0

View File

@ -1,100 +0,0 @@
From 37a05df2eb7e880c1bde301adf2b2eb32fc9a891 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?J=C3=A1n=20Tomko?= <jtomko@redhat.com>
Date: Tue, 22 Sep 2020 22:17:03 +0200
Subject: [PATCH] Use (un)signed printf specifiers correctly
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Various places reported by cppcheck's invalidPrintfArgType_sint
and invalidPrintfArgType_uint.
Signed-off-by: Ján Tomko <jtomko@redhat.com>
Reviewed-by: Peter Krempa <pkrempa@redhat.com>
Signed-off-by: zhujun2 <zhujun2_yewu@cmss.chinamobile.com>
(cherry-pick from 8b80d9f0f924ddf900b726871916f8ba5ae29243)
---
examples/c/domain/domtop.c | 2 +-
examples/c/domain/suspend.c | 2 +-
tests/qemusecuritymock.c | 2 +-
tests/virhashtest.c | 4 ++--
tests/virpcimock.c | 2 +-
5 files changed, 6 insertions(+), 6 deletions(-)
diff --git a/examples/c/domain/domtop.c b/examples/c/domain/domtop.c
index 15611c586d..5228445b7c 100644
--- a/examples/c/domain/domtop.c
+++ b/examples/c/domain/domtop.c
@@ -115,7 +115,7 @@ parse_argv(int argc, char *argv[],
}
*milliseconds = val;
if (*milliseconds != val) {
- ERROR("Integer overflow: %ld", val);
+ ERROR("Integer overflow: %lu", val);
exit(EXIT_FAILURE);
}
break;
diff --git a/examples/c/domain/suspend.c b/examples/c/domain/suspend.c
index 980c4584c7..3ff24f6861 100644
--- a/examples/c/domain/suspend.c
+++ b/examples/c/domain/suspend.c
@@ -105,7 +105,7 @@ parse_argv(int argc, char *argv[],
}
*seconds = val;
if (*seconds != val) {
- ERROR("Integer overflow: %ld", val);
+ ERROR("Integer overflow: %lu", val);
return -1;
}
break;
diff --git a/tests/qemusecuritymock.c b/tests/qemusecuritymock.c
index ad182c7bf7..e1057bef7b 100644
--- a/tests/qemusecuritymock.c
+++ b/tests/qemusecuritymock.c
@@ -269,7 +269,7 @@ mock_chown(const char *path,
int ret = -1;
if (gid >> 16 || uid >> 16) {
- fprintf(stderr, "Attempt to set too high UID or GID: %lld %lld",
+ fprintf(stderr, "Attempt to set too high UID or GID: %llu %llu",
(unsigned long long) uid, (unsigned long long) gid);
abort();
}
diff --git a/tests/virhashtest.c b/tests/virhashtest.c
index 4d05cbb0f8..af30791241 100644
--- a/tests/virhashtest.c
+++ b/tests/virhashtest.c
@@ -34,7 +34,7 @@ testHashInit(int size)
}
if (virHashTableSize(hash) != oldsize) {
- VIR_TEST_DEBUG("hash grown from %zd to %zd",
+ VIR_TEST_DEBUG("hash grown from %zu to %zu",
(size_t)oldsize, (size_t)virHashTableSize(hash));
}
}
@@ -313,7 +313,7 @@ testHashRemoveSet(const void *data G_GNUC_UNUSED)
if (count != rcount) {
VIR_TEST_VERBOSE("\nvirHashRemoveSet didn't remove expected number of"
- " entries, %d != %u",
+ " entries, %d != %d",
rcount, count);
goto cleanup;
}
diff --git a/tests/virpcimock.c b/tests/virpcimock.c
index 92b6f810d8..d0fe11e5f1 100644
--- a/tests/virpcimock.c
+++ b/tests/virpcimock.c
@@ -120,7 +120,7 @@ struct pciDeviceAddress {
unsigned int device;
unsigned int function;
};
-# define ADDR_STR_FMT "%04x:%02x:%02x.%d"
+# define ADDR_STR_FMT "%04x:%02x:%02x.%u"
struct pciDevice {
struct pciDeviceAddress addr;
--
2.27.0

View File

@ -1,80 +0,0 @@
From 0ef9a886d3d8bd468800ee3d6aadac2231359501 Mon Sep 17 00:00:00 2001
From: root <root@openeuleropenstack.dev01>
Date: Thu, 4 Feb 2021 17:35:46 +0800
Subject: [PATCH] add phytium 2000plus and s2500 support on arm architecture
for capability
---
src/cpu_map/Makefile.inc.am | 2 ++
src/cpu_map/arm_FT-2000plus.xml | 6 ++++++
src/cpu_map/arm_Tengyun-S2500.xml | 6 ++++++
src/cpu_map/arm_vendors.xml | 1 +
src/cpu_map/index.xml | 4 ++++
5 files changed, 19 insertions(+)
create mode 100644 src/cpu_map/arm_FT-2000plus.xml
create mode 100644 src/cpu_map/arm_Tengyun-S2500.xml
diff --git a/src/cpu_map/Makefile.inc.am b/src/cpu_map/Makefile.inc.am
index 8663877b97..ab5268d94f 100644
--- a/src/cpu_map/Makefile.inc.am
+++ b/src/cpu_map/Makefile.inc.am
@@ -72,6 +72,8 @@ cpumap_DATA = \
cpu_map/arm_cortex-a57.xml \
cpu_map/arm_cortex-a72.xml \
cpu_map/arm_Kunpeng-920.xml \
+ cpu_map/arm_FT-2000plus.xml \
+ cpu_map/arm_Tengyun-S2500.xml \
$(NULL)
EXTRA_DIST += $(cpumap_DATA)
diff --git a/src/cpu_map/arm_FT-2000plus.xml b/src/cpu_map/arm_FT-2000plus.xml
new file mode 100644
index 0000000000..b532f65f68
--- /dev/null
+++ b/src/cpu_map/arm_FT-2000plus.xml
@@ -0,0 +1,6 @@
+<cpus>
+ <model name='FT-2000+'>
+ <vendor name='Phytium'/>
+ <pvr value='0x662'/>
+ </model>
+</cpus>
diff --git a/src/cpu_map/arm_Tengyun-S2500.xml b/src/cpu_map/arm_Tengyun-S2500.xml
new file mode 100644
index 0000000000..22b865e368
--- /dev/null
+++ b/src/cpu_map/arm_Tengyun-S2500.xml
@@ -0,0 +1,6 @@
+<cpus>
+ <model name='Tengyun-S2500'>
+ <vendor name='Phytium'/>
+ <pvr value='0x663'/>
+ </model>
+</cpus>
diff --git a/src/cpu_map/arm_vendors.xml b/src/cpu_map/arm_vendors.xml
index 840bf9a2f8..05175495a0 100644
--- a/src/cpu_map/arm_vendors.xml
+++ b/src/cpu_map/arm_vendors.xml
@@ -11,4 +11,5 @@
<vendor name="Qualcomm" value="0x51"/>
<vendor name="Marvell" value="0x56"/>
<vendor name="Intel" value="0x69"/>
+ <vendor name='Phytium' value='0x70'/>
</cpus>
diff --git a/src/cpu_map/index.xml b/src/cpu_map/index.xml
index 985af86ba2..672d0a3c92 100644
--- a/src/cpu_map/index.xml
+++ b/src/cpu_map/index.xml
@@ -95,5 +95,9 @@
<!-- Hisilicon-based CPU models -->
<include filename="arm_Kunpeng-920.xml"/>
+
+ <!-- Phytium-based CPU models -->
+ <include filename='arm_FT-2000plus.xml'/>
+ <include filename='arm_Tengyun-S2500.xml'/>
</arch>
</cpus>
--
2.27.0

View File

@ -1,62 +0,0 @@
From 90b8168fd93490f3a0fadadb38030163712a0e85 Mon Sep 17 00:00:00 2001
From: wangmeiyang <wangmeiyang@xfusion.com>
Date: Fri, 21 Apr 2023 14:43:45 +0800
Subject: [PATCH] admin: fix leak of typed parameters on error
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
A few admin client methods had the xdr_free call the wrong
side of the cleanup label, so typed parameters would not
be freed on error.
origin commit: https://gitlab.com/libvirt/libvirt/-/commit/0edf44664e9f2f75c7ba5faab91e2e190b5626af
Reviewed-by: Martin Kletzander <mkletzan@redhat.com>
Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
Signed-off-by: Meiyang Wang <wangmeiyang@xfusion.com>
---
src/admin/admin_remote.c | 8 ++++----
1 file changed, 4 insertions(+), 4 deletions(-)
diff --git a/src/admin/admin_remote.c b/src/admin/admin_remote.c
index ca5e0c9fe4..2499fb8b0f 100644
--- a/src/admin/admin_remote.c
+++ b/src/admin/admin_remote.c
@@ -271,9 +271,9 @@ remoteAdminServerGetThreadPoolParameters(virAdmServerPtr srv,
goto cleanup;
rv = 0;
- xdr_free((xdrproc_t)xdr_admin_server_get_threadpool_parameters_ret, (char *) &ret);
cleanup:
+ xdr_free((xdrproc_t)xdr_admin_server_get_threadpool_parameters_ret, (char *) &ret);
virObjectUnlock(priv);
return rv;
}
@@ -344,9 +344,9 @@ remoteAdminClientGetInfo(virAdmClientPtr client,
goto cleanup;
rv = 0;
- xdr_free((xdrproc_t)xdr_admin_client_get_info_ret, (char *) &ret);
cleanup:
+ xdr_free((xdrproc_t)xdr_admin_client_get_info_ret, (char *) &ret);
virObjectUnlock(priv);
return rv;
}
@@ -382,10 +382,10 @@ remoteAdminServerGetClientLimits(virAdmServerPtr srv,
goto cleanup;
rv = 0;
- xdr_free((xdrproc_t) xdr_admin_server_get_client_limits_ret,
- (char *) &ret);
cleanup:
+ xdr_free((xdrproc_t) xdr_admin_server_get_client_limits_ret,
+ (char *) &ret);
virObjectUnlock(priv);
return rv;
}
--
2.27.0

View File

@ -1,31 +0,0 @@
From 58d0830491d3be2fedec55f42f6f832d32783a73 Mon Sep 17 00:00:00 2001
From: luzhipeng <luzhipeng@cestc.cn>
Date: Sat, 7 May 2022 09:17:31 +0800
Subject: [PATCH] apibuild: Fix self.waring method call
The parameters of self.warning is inconsistent with its definition, So
fix it.
Signed-off-by: dinglimin <dinglimin@cmss.chinamobile.com>
Signed-off-by: luzhipeng <luzhipeng@cestc.cn>
Reviewed-by: Martin Kletzander <mkletzan@redhat.com>
---
scripts/apibuild.py | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/scripts/apibuild.py b/scripts/apibuild.py
index 05a169c30d..c98bcf6091 100755
--- a/scripts/apibuild.py
+++ b/scripts/apibuild.py
@@ -315,7 +315,7 @@ class index:
if type in type_map:
type_map[type][name] = d
else:
- self.warning("Unable to register type ", type)
+ self.warning("Unable to register type %s" % type)
if name == debugsym and not quiet:
print("New symbol: %s" % (d))
--
2.27.0

View File

@ -1,38 +0,0 @@
From 9abebfb36b2380829be4a901d7c9785a7a8f5f6a Mon Sep 17 00:00:00 2001
From: Jim Fehlig <jfehlig@suse.com>
Date: Mon, 7 Jun 2021 16:21:28 -0600
Subject: [PATCH] apparmor: Permit new capabilities required by libvirtd
The audit log contains the following denials from libvirtd
apparmor="DENIED" operation="capable" profile="libvirtd" pid=6012 comm="daemon-init" capability=17 capname="sys_rawio"
apparmor="DENIED" operation="capable" profile="libvirtd" pid=6012 comm="rpc-worker" capability=39 capname="bpf"
apparmor="DENIED" operation="capable" profile="libvirtd" pid=6012 comm="rpc-worker" capability=38 capname="perfmon"
Squelch the denials and allow the capabilities in the libvirtd
apparmor profile.
Signed-off-by: Jim Fehlig <jfehlig@suse.com>
Reviewed-by: Neal Gompa <ngompa13@gmail.com>
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
---
src/security/apparmor/usr.sbin.libvirtd.in | 3 +++
1 file changed, 3 insertions(+)
diff --git a/src/security/apparmor/usr.sbin.libvirtd.in b/src/security/apparmor/usr.sbin.libvirtd.in
index 1e137039e9..49266743f5 100644
--- a/src/security/apparmor/usr.sbin.libvirtd.in
+++ b/src/security/apparmor/usr.sbin.libvirtd.in
@@ -25,6 +25,9 @@ profile libvirtd @sbindir@/libvirtd flags=(attach_disconnected) {
capability fsetid,
capability audit_write,
capability ipc_lock,
+ capability sys_rawio,
+ capability bpf,
+ capability perfmon,
# Needed for vfio
capability sys_resource,
--
2.27.0

View File

@ -1,155 +0,0 @@
From 2b3bbbc1b7f8723c4947c6d1e4fb43cabc25fb2e Mon Sep 17 00:00:00 2001
From: Pavel Hrdina <phrdina@redhat.com>
Date: Fri, 24 Jul 2020 16:30:06 +0200
Subject: [PATCH 2/4] meson: drop debug_logs configure argument
There is no point of having this option in libvirt because the debug
logs can be configured using log filters.
origin commit: https://gitlab.com/libvirt/libvirt/-/commit/da6d644ea7b49500680a3d4a403571234fecefad
Signed-off-by: Pavel Hrdina <phrdina@redhat.com>
Reviewed-by: Peter Krempa <pkrempa@redhat.com>
Reviewed-by: Neal Gompa <ngompa13@gmail.com>
Signed-off-by: Chenxi Mao <chenxi.mao@suse.com>
---
configure.ac | 3 ---
m4/virt-debug.m4 | 33 ---------------------------------
src/util/virlog.h | 23 +----------------------
tools/virsh.c | 2 --
tools/virt-admin.c | 2 --
5 files changed, 1 insertion(+), 62 deletions(-)
delete mode 100644 m4/virt-debug.m4
diff --git a/configure.ac b/configure.ac
index cb62e5aac8..93d13496f3 100644
--- a/configure.ac
+++ b/configure.ac
@@ -496,7 +496,6 @@ dnl
dnl Miscellaneous checks
dnl
-LIBVIRT_ARG_DEBUG
LIBVIRT_ARG_DTRACE
LIBVIRT_ARG_NUMAD
LIBVIRT_ARG_INIT_SCRIPT
@@ -509,7 +508,6 @@ LIBVIRT_ARG_TLS_PRIORITY
LIBVIRT_ARG_SYSCTL_CONFIG
-LIBVIRT_CHECK_DEBUG
LIBVIRT_CHECK_DTRACE
LIBVIRT_CHECK_NUMAD
LIBVIRT_CHECK_INIT_SCRIPT
@@ -1038,7 +1036,6 @@ LIBVIRT_RESULT([Coverage], [$enable_test_coverage])
AC_MSG_NOTICE([])
AC_MSG_NOTICE([Miscellaneous])
AC_MSG_NOTICE([])
-LIBVIRT_RESULT_DEBUG
LIBVIRT_RESULT([Use -Werror], [$enable_werror])
LIBVIRT_RESULT([Warning Flags], [$WARN_CFLAGS])
LIBVIRT_RESULT_DTRACE
diff --git a/m4/virt-debug.m4 b/m4/virt-debug.m4
deleted file mode 100644
index d3ac0564f2..0000000000
--- a/m4/virt-debug.m4
+++ /dev/null
@@ -1,33 +0,0 @@
-dnl The debug check
-dnl
-dnl Copyright (C) 2016 Red Hat, Inc.
-dnl
-dnl This library is free software; you can redistribute it and/or
-dnl modify it under the terms of the GNU Lesser General Public
-dnl License as published by the Free Software Foundation; either
-dnl version 2.1 of the License, or (at your option) any later version.
-dnl
-dnl This library is distributed in the hope that it will be useful,
-dnl but WITHOUT ANY WARRANTY; without even the implied warranty of
-dnl MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-dnl Lesser General Public License for more details.
-dnl
-dnl You should have received a copy of the GNU Lesser General Public
-dnl License along with this library. If not, see
-dnl <http://www.gnu.org/licenses/>.
-dnl
-
-AC_DEFUN([LIBVIRT_ARG_DEBUG], [
- LIBVIRT_ARG_ENABLE([DEBUG], [enable debugging output], [yes])
-])
-
-AC_DEFUN([LIBVIRT_CHECK_DEBUG], [
- AM_CONDITIONAL([ENABLE_DEBUG], test x"$enable_debug" = x"yes")
- if test x"$enable_debug" = x"yes"; then
- AC_DEFINE([ENABLE_DEBUG], [], [whether debugging is enabled])
- fi
-])
-
-AC_DEFUN([LIBVIRT_RESULT_DEBUG], [
- LIBVIRT_RESULT([Debug], [$enable_debug])
-])
diff --git a/src/util/virlog.h b/src/util/virlog.h
index feb2f85904..716fb9a378 100644
--- a/src/util/virlog.h
+++ b/src/util/virlog.h
@@ -78,29 +78,8 @@ struct _virLogSource {
.serial = 0, \
}
-/*
- * If configured with --enable-debug=yes then library calls
- * are printed to stderr for debugging or to an appropriate channel
- * defined at runtime from the libvirt daemon configuration file
- */
-#ifdef ENABLE_DEBUG
-# define VIR_DEBUG_INT(src, filename, linenr, funcname, ...) \
+#define VIR_DEBUG_INT(src, filename, linenr, funcname, ...) \
virLogMessage(src, VIR_LOG_DEBUG, filename, linenr, funcname, NULL, __VA_ARGS__)
-#else
-/**
- * virLogEatParams:
- *
- * Do nothing but eat parameters.
- */
-static inline void virLogEatParams(virLogSourcePtr unused, ...)
-{
- /* Silence gcc */
- unused = unused;
-}
-# define VIR_DEBUG_INT(src, filename, linenr, funcname, ...) \
- virLogEatParams(src, filename, linenr, funcname, __VA_ARGS__)
-#endif /* !ENABLE_DEBUG */
-
#define VIR_INFO_INT(src, filename, linenr, funcname, ...) \
virLogMessage(src, VIR_LOG_INFO, filename, linenr, funcname, NULL, __VA_ARGS__)
#define VIR_WARN_INT(src, filename, linenr, funcname, ...) \
diff --git a/tools/virsh.c b/tools/virsh.c
index 197a90636d..06ff5e8336 100644
--- a/tools/virsh.c
+++ b/tools/virsh.c
@@ -614,9 +614,7 @@ virshShowVersion(vshControl *ctl G_GNUC_UNUSED)
#ifdef WITH_SECRETS
vshPrint(ctl, " Secrets");
#endif
-#ifdef ENABLE_DEBUG
vshPrint(ctl, " Debug");
-#endif
#ifdef WITH_DTRACE_PROBES
vshPrint(ctl, " DTrace");
#endif
diff --git a/tools/virt-admin.c b/tools/virt-admin.c
index a8e5e0a5af..df23330ee1 100644
--- a/tools/virt-admin.c
+++ b/tools/virt-admin.c
@@ -1277,9 +1277,7 @@ vshAdmShowVersion(vshControl *ctl G_GNUC_UNUSED)
#ifdef WITH_LIBVIRTD
vshPrint(ctl, " Daemon");
#endif
-#ifdef ENABLE_DEBUG
vshPrint(ctl, " Debug");
-#endif
#if WITH_READLINE
vshPrint(ctl, " Readline");
#endif
--
2.33.0

View File

@ -1,67 +0,0 @@
From f6c9bb6adbee8f74172707845dcdf221e79e35d4 Mon Sep 17 00:00:00 2001
From: Peter Krempa <pkrempa@redhat.com>
Date: Tue, 23 Aug 2022 15:29:43 +0200
Subject: [PATCH 1/4] virhostcpu: Fix build with clang and newest kernel
headers
The most recent environment e.g. present in our Fedora Rawhide builds
fail to build the tree with clang with the following error:
../src/util/virhostcpu.c:1291:25: error: field 'header' with variable sized type 'struct kvm_msrs' not at the end of a struct or class is a GNU extension [-Werror,-Wgnu-variable-sized-type-not-at-end]
struct kvm_msrs header;
^
The problem seems to be that clang doesn't like the new way the
'entries' field in struct kvm_msrs is declared.
To work around the issue we can simply allocate the variable dynamically
and use the 'entries' member as it was intended to to access the
members.
origin commit: https://gitlab.com/libvirt/libvirt/-/commit/56b3ee743916c8951a32a1650616621d78afe8c7
Signed-off-by: Peter Krempa <pkrempa@redhat.com>
Reviewed-by: Jiri Denemark <jdenemar@redhat.com>
Signed-off-by: Chenxi Mao <chenxi.mao@suse.com>
---
src/util/virhostcpu.c | 15 ++++++---------
1 file changed, 6 insertions(+), 9 deletions(-)
diff --git a/src/util/virhostcpu.c b/src/util/virhostcpu.c
index ce3da7e6ec..8c8fc3a476 100644
--- a/src/util/virhostcpu.c
+++ b/src/util/virhostcpu.c
@@ -1275,25 +1275,22 @@ virHostCPUGetMSRFromKVM(unsigned long index,
uint64_t *result)
{
VIR_AUTOCLOSE fd = -1;
- struct {
- struct kvm_msrs header;
- struct kvm_msr_entry entry;
- } msr = {
- .header = { .nmsrs = 1 },
- .entry = { .index = index },
- };
+ g_autofree struct kvm_msrs *msr = g_malloc0(sizeof(struct kvm_msrs) +
+ sizeof(struct kvm_msr_entry));
+ msr->nmsrs = 1;
+ msr->entries[0].index = index;
if ((fd = open(KVM_DEVICE, O_RDONLY)) < 0) {
virReportSystemError(errno, _("Unable to open %s"), KVM_DEVICE);
return -1;
}
- if (ioctl(fd, KVM_GET_MSRS, &msr) < 0) {
+ if (ioctl(fd, KVM_GET_MSRS, msr) < 0) {
VIR_DEBUG("Cannot get MSR 0x%lx from KVM", index);
return 1;
}
- *result = msr.entry.data;
+ *result = msr->entries[0].data;
return 0;
}
--
2.33.0

View File

@ -1,42 +0,0 @@
From 6d3c4b49c08d5fcf42f324af0d04551619e4109f Mon Sep 17 00:00:00 2001
From: Michal Privoznik <mprivozn@redhat.com>
Date: Thu, 7 Jan 2021 17:59:55 +0100
Subject: [PATCH 3/4] vshCommandStringGetArg: Drop @sz
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
This variable is unused since introduction of the function in
v0.8.5~150.
origin commit: https://gitlab.com/libvirt/libvirt/-/commit/9b9542586cc047075469053606d1e12cb017b5ca
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
Reviewed-by: Ján Tomko <jtomko@redhat.com>
Signed-off-by: Chenxi Mao <chenxi.mao@suse.com>
---
tools/vsh.c | 2 --
1 file changed, 2 deletions(-)
diff --git a/tools/vsh.c b/tools/vsh.c
index 3646f37cea..f5fa7b6f6f 100644
--- a/tools/vsh.c
+++ b/tools/vsh.c
@@ -1641,7 +1641,6 @@ vshCommandStringGetArg(vshControl *ctl, vshCommandParser *parser, char **res,
{
bool single_quote = false;
bool double_quote = false;
- int sz = 0;
char *p = parser->pos;
char *q = g_strdup(p);
@@ -1695,7 +1694,6 @@ vshCommandStringGetArg(vshControl *ctl, vshCommandParser *parser, char **res,
}
*q++ = *p++;
- sz++;
}
if (double_quote) {
if (report)
--
2.33.0

View File

@ -1,31 +0,0 @@
From 4bdf8aeb2e907b53cc71c07b3c6be8f82e3f1e4a Mon Sep 17 00:00:00 2001
From: Xu Zheng <xuzheng_yewu@cmss.chinamobile.com>
Date: Thu, 24 Nov 2022 17:58:28 +0800
Subject: [PATCH 20/23] bash-completion: fix variable leaks of "word"
cherry-pick from 097296c30b72f472bcf4e72cf8ab2aeb55903c49
Signed-off-by: Koichi Murase <myoga.murase@gmail.com>
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
Signed-off-by: Xu Zheng <xuzheng_yewu@cmss.chinamobile.com>
---
tools/bash-completion/vsh | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/tools/bash-completion/vsh b/tools/bash-completion/vsh
index 8493cad28b..363097c601 100644
--- a/tools/bash-completion/vsh
+++ b/tools/bash-completion/vsh
@@ -21,7 +21,7 @@ _vsh_complete()
# See what URI is user trying to connect to and if they are
# connecting RO. Honour that.
while [ $c -le $COMP_CWORD ]; do
- word="${COMP_WORDS[c]}"
+ local word="${COMP_WORDS[c]}"
case "$word" in
-r|--readonly) RO=1 ;;
-c|--connect) c=$((++c)); URI=${COMP_WORDS[c]} ;;
--
2.27.0

View File

@ -1,30 +0,0 @@
From 0559dfd4d4fa74484dae487711a986cc9acdfbfc Mon Sep 17 00:00:00 2001
From: Chenxi Mao <chenxi.mao@suse.com>
Date: Tue, 4 Apr 2023 14:25:17 +0800
Subject: [PATCH 4/4] Fix warnings found by clang
Warnings found if build with clang 15:
[ 257s] ../../src/qemu/qemu_hotpatch.c:217:22: error: unused variable 'libvirtd_conf' [-Werror,-Wunused-variable]
[ 257s] g_autofree char *libvirtd_conf = NULL;
Signed-off-by: Chenxi Mao <chenxi.mao@suse.com>
---
src/qemu/qemu_hotpatch.c | 1 -
1 file changed, 1 deletion(-)
diff --git a/src/qemu/qemu_hotpatch.c b/src/qemu/qemu_hotpatch.c
index 02f511cc38..64aac9bb4c 100644
--- a/src/qemu/qemu_hotpatch.c
+++ b/src/qemu/qemu_hotpatch.c
@@ -214,7 +214,6 @@ qemuDomainHotpatchAutoload(virDomainObjPtr vm, char *hotpatch_path)
VIR_AUTOSTRINGLIST applied_patches = NULL;
VIR_AUTOSTRINGLIST lines = NULL;
g_autofree char *applied_patch = NULL;
- g_autofree char *libvirtd_conf = NULL;
g_autofree char *patch_conf = NULL;
g_autofree char *buf = NULL;
char *ret = NULL;
--
2.33.0

View File

@ -1,43 +0,0 @@
From 35de7404370eb24089b6160d109f6fe559a91864 Mon Sep 17 00:00:00 2001
From: mayunlong <mayunlong6@huawei.com>
Date: Fri, 24 Mar 2023 11:31:49 +0800
Subject: [PATCH] bugfix: move the check function
qemuDomainDiskBlockIoTuneIsSupported to currect place.
move the check function qemuDomainDiskBlockIoTuneIsSupported for
conf_disk to currect place in function: qemuDomainSetBlockIotTune.
fix commit: e07709c7275349eac376660c08bacc6d18f28ff8
origin commit: https://libvirt.org/git/?p=libvirt.git;a=commitdiff;h=d763466edc6e8d4965fb42092c6e8f4296acf6c6
Signed-off-by:mayunlong<mayunlong6@huawei.com>
---
src/qemu/qemu_driver.c | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index 32b3ef3cf1..c7545a7a98 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -19301,9 +19301,6 @@ qemuDomainSetBlockIoTune(virDomainPtr dom,
goto endjob;
}
- if (!qemuDomainDiskBlockIoTuneIsSupported(conf_disk->src))
- goto endjob;
-
cur_info = qemuDomainFindGroupBlockIoTune(def, disk, &info);
if (qemuDomainSetBlockIoTuneDefaults(&info, cur_info,
@@ -19386,6 +19383,9 @@ qemuDomainSetBlockIoTune(virDomainPtr dom,
goto endjob;
}
+ if (!qemuDomainDiskBlockIoTuneIsSupported(conf_disk->src))
+ goto endjob;
+
conf_cur_info = qemuDomainFindGroupBlockIoTune(persistentDef, conf_disk, &info);
if (qemuDomainSetBlockIoTuneDefaults(&conf_info, conf_cur_info,
--
2.25.1

View File

@ -1,70 +0,0 @@
From 61de276ed3cd5692b99ebc6d5b700a21b16ab5e8 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?J=C3=A1n=20Tomko?= <jtomko@redhat.com>
Date: Tue, 8 Sep 2020 14:57:14 +0200
Subject: [PATCH 014/108] check for NULL before calling g_regex_unref
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
g_regex_unref reports an error if called with a NULL argument.
We have two cases in the code where we (possibly) call it on a NULL
argument. The interesting one is in virDomainQemuMonitorEventCleanup.
Based on VIR_CONNECT_DOMAIN_QEMU_MONITOR_EVENT_REGISTER_REGEX, we unref
data->regex, which has two problems:
* On the client side, flags is -1 so the comparison is true even if no
regex was used, reproducible by:
$ virsh qemu-monitor-event --timeout 1
which results in an ugly error:
(process:1289846): GLib-CRITICAL **: 14:58:42.631: g_regex_unref: assertion 'regex != NULL' failed
* On the server side, we only create the regex if both the flag and the
string are present, so it's possible to trigger this message by:
$ virsh qemu-monitor-event --regex --timeout 1
Use a non-NULL comparison instead of the flag to decide whether we need
to unref the regex. And add a non-NULL check to the unref in the
VirtualBox test too.
Signed-off-by: Ján Tomko <jtomko@redhat.com>
Fixes: 71efb59a4de7c51b1bc889a316f1796ebf55738f
https://bugzilla.redhat.com/show_bug.cgi?id=1876907
Reviewed-by: Peter Krempa <pkrempa@redhat.com>
Reviewed-by: Martin Kletzander <mkletzan@redhat.com>
(cherry picked from commit 92b252456ee6d6ffc6e39e62ce1ce6c50113e00e)
---
src/conf/domain_event.c | 2 +-
tests/vboxsnapshotxmltest.c | 3 ++-
2 files changed, 3 insertions(+), 2 deletions(-)
diff --git a/src/conf/domain_event.c b/src/conf/domain_event.c
index 33fbf10406..d3acde0236 100644
--- a/src/conf/domain_event.c
+++ b/src/conf/domain_event.c
@@ -2194,7 +2194,7 @@ virDomainQemuMonitorEventCleanup(void *opaque)
virDomainQemuMonitorEventData *data = opaque;
VIR_FREE(data->event);
- if (data->flags & VIR_CONNECT_DOMAIN_QEMU_MONITOR_EVENT_REGISTER_REGEX)
+ if (data->regex)
g_regex_unref(data->regex);
if (data->freecb)
(data->freecb)(data->opaque);
diff --git a/tests/vboxsnapshotxmltest.c b/tests/vboxsnapshotxmltest.c
index 2ea460d8bd..853d930865 100644
--- a/tests/vboxsnapshotxmltest.c
+++ b/tests/vboxsnapshotxmltest.c
@@ -136,7 +136,8 @@ mymain(void)
DO_TEST("2disks-3snap-brother");
cleanup:
- g_regex_unref(testSnapshotXMLVariableLineRegex);
+ if (testSnapshotXMLVariableLineRegex)
+ g_regex_unref(testSnapshotXMLVariableLineRegex);
return ret == 0 ? EXIT_SUCCESS : EXIT_FAILURE;
}
--
2.33.0

View File

@ -1,34 +0,0 @@
From 5d84740e04d99a8503f20b2281f3fd70fa1f69ab Mon Sep 17 00:00:00 2001
From: jipengfei <jipengfei_yewu@cmss.chinamobile.com>
Date: Thu, 24 Nov 2022 16:43:51 +0800
Subject: [PATCH 16/23] checkpoint: Fix a typo of comments
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
cherry-pick from 75134a3a7d1ca6976dfc2af7cd53461cb0aee529
Signed-off-by: Han Han <hhan@redhat.com>
Signed-off-by: jipengfei <jipengfei_yewu@cmss.chinamobile.com>
Reviewed-by: Ján Tomko <jtomko@redhat.com>
Signed-off-by: Ján Tomko <jtomko@redhat.com>
---
src/libvirt-domain-checkpoint.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/src/libvirt-domain-checkpoint.c b/src/libvirt-domain-checkpoint.c
index 432c2d5a52..58668c391c 100644
--- a/src/libvirt-domain-checkpoint.c
+++ b/src/libvirt-domain-checkpoint.c
@@ -236,7 +236,7 @@ virDomainCheckpointGetXMLDesc(virDomainCheckpointPtr checkpoint,
* @checkpoints: pointer to variable to store the array containing checkpoint
* object, or NULL if the list is not required (just returns
* number of checkpoints)
- * @flags: bitwise-OR of supported virDomainCheckpoinListFlags
+ * @flags: bitwise-OR of supported virDomainCheckpointListFlags
*
* Collect the list of domain checkpoints for the given domain and allocate
* an array to store those objects.
--
2.27.0

View File

@ -1,47 +0,0 @@
From ea9860d9f89252f0890dae01c6b92af2a82227f4 Mon Sep 17 00:00:00 2001
From: tangbinzy <tangbin_yewu@cmss.chinamobile.com>
Date: Tue, 29 Nov 2022 08:19:29 +0000
Subject: [PATCH 02/24] client: fix memory leak in client msg When closing
client->waitDispatch in virNetClientIOEventLoopRemoveAll or
virNetClientIOEventLoopRemoveDone, VIR_FREE() is called to free call->msg
directly, resulting in leak of the memory call->msg->buffer points to. Use
virNetMessageFree(call->msg) instead of VIR_FREE(call->msg).
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Signed-off-by: Hao Wang <wanghao232@huawei.com>
Reviewed-by: Ján Tomko <jtomko@redhat.com>
Signed-off-by: Ján Tomko <jtomko@redhat.com>
Signed-off-by: tangbin <tangbin_yewu@cmss.chinamobile.com>
(cherry-pick from 0011ec3191a5bffff14fc2c53fbdf457a805cfb1)
---
src/rpc/virnetclient.c | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/src/rpc/virnetclient.c b/src/rpc/virnetclient.c
index 1c5bef86a1..70ace5d0e8 100644
--- a/src/rpc/virnetclient.c
+++ b/src/rpc/virnetclient.c
@@ -1519,7 +1519,7 @@ static bool virNetClientIOEventLoopRemoveDone(virNetClientCallPtr call,
if (call->expectReply)
VIR_WARN("Got a call expecting a reply but without a waiting thread");
virCondDestroy(&call->cond);
- VIR_FREE(call->msg);
+ virNetMessageFree(call->msg);
VIR_FREE(call);
}
@@ -1546,7 +1546,7 @@ virNetClientIOEventLoopRemoveAll(virNetClientCallPtr call,
VIR_DEBUG("Removing call %p", call);
virCondDestroy(&call->cond);
- VIR_FREE(call->msg);
+ virNetMessageFree(call->msg);
VIR_FREE(call);
return true;
}
--
2.27.0

View File

@ -1,36 +0,0 @@
From dd54dd905f334ee31ebd9d667dc0fd2db9ddeaf0 Mon Sep 17 00:00:00 2001
From: Tim Wiederhake <twiederh@redhat.com>
Date: Mon, 19 Apr 2021 13:54:13 +0200
Subject: [PATCH 061/108] cmdCheckpointList: Fix memory leak
Fixes: 3caa28dc50df7ec215713075d669b20bef6473a2
Signed-off-by: Tim Wiederhake <twiederh@redhat.com>
Reviewed-by: Laine Stump <laine@redhat.com>
(cherry picked from commit 8b8c91f487592c6c067847ca59dde405ca17573f)
---
tools/virsh-checkpoint.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/tools/virsh-checkpoint.c b/tools/virsh-checkpoint.c
index e82a67f075..1a3a74b2d5 100644
--- a/tools/virsh-checkpoint.c
+++ b/tools/virsh-checkpoint.c
@@ -720,7 +720,6 @@ cmdCheckpointList(vshControl *ctl,
virDomainCheckpointPtr checkpoint = NULL;
long long creation_longlong;
g_autoptr(GDateTime) then = NULL;
- g_autofree gchar *thenstr = NULL;
bool tree = vshCommandOptBool(cmd, "tree");
bool name = vshCommandOptBool(cmd, "name");
bool from = vshCommandOptBool(cmd, "from");
@@ -803,6 +802,7 @@ cmdCheckpointList(vshControl *ctl,
}
for (i = 0; i < checkpointlist->nchks; i++) {
+ g_autofree gchar *thenstr = NULL;
const char *chk_name;
/* free up memory from previous iterations of the loop */
--
2.33.0

View File

@ -1,36 +0,0 @@
From 4732cb4a9306ea9b8487b66fa14316caa05428ed Mon Sep 17 00:00:00 2001
From: Tim Wiederhake <twiederh@redhat.com>
Date: Mon, 19 Apr 2021 13:54:14 +0200
Subject: [PATCH 062/108] cmdSnapshotList: Fix memory leak
Fixes: 3caa28dc50df7ec215713075d669b20bef6473a2
Signed-off-by: Tim Wiederhake <twiederh@redhat.com>
Reviewed-by: Laine Stump <laine@redhat.com>
(cherry picked from commit 89ce1ef86b0c8b0e039ae770221376497354f085)
---
tools/virsh-snapshot.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/tools/virsh-snapshot.c b/tools/virsh-snapshot.c
index d5e68e4b18..376290d468 100644
--- a/tools/virsh-snapshot.c
+++ b/tools/virsh-snapshot.c
@@ -1493,7 +1493,6 @@ cmdSnapshotList(vshControl *ctl, const vshCmd *cmd)
char *state = NULL;
long long creation_longlong;
g_autoptr(GDateTime) then = NULL;
- g_autofree gchar *thenstr = NULL;
bool tree = vshCommandOptBool(cmd, "tree");
bool name = vshCommandOptBool(cmd, "name");
bool from = vshCommandOptBool(cmd, "from");
@@ -1588,6 +1587,7 @@ cmdSnapshotList(vshControl *ctl, const vshCmd *cmd)
}
for (i = 0; i < snaplist->nsnaps; i++) {
+ g_autofree gchar *thenstr = NULL;
const char *snap_name;
/* free up memory from previous iterations of the loop */
--
2.33.0

View File

@ -1,81 +0,0 @@
From efd4f6469f9f5f6d3a34d250cd80faf59a8dc373 Mon Sep 17 00:00:00 2001
From: Jiri Denemark <jdenemar@redhat.com>
Date: Wed, 11 Nov 2020 16:50:16 +0100
Subject: [PATCH 068/108] conf: Use unsigned long long for timer frequency
Although the code in qemuProcessStartValidateTSC works as if the
timer frequency was already unsigned long long (by using an appropriate
temporary variable), the virDomainTimerDef structure actually defines
frequency as unsigned long, which is not guaranteed to be 64b.
Fixes support for frequencies higher than 2^32 - 1 on 32b systems.
Signed-off-by: Jiri Denemark <jdenemar@redhat.com>
Reviewed-by: Martin Kletzander <mkletzan@redhat.com>
(cherry picked from commit 3c7c7cd4d82c2f9a5a59bbd06673b8cd1eb23ce3)
---
src/conf/domain_conf.c | 6 +++---
src/conf/domain_conf.h | 2 +-
src/qemu/qemu_command.c | 2 +-
3 files changed, 5 insertions(+), 5 deletions(-)
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index a33f9144f5..9c83f4e347 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -13951,7 +13951,7 @@ virDomainTimerDefParseXML(xmlNodePtr node,
}
}
- ret = virXPathULong("string(./@frequency)", ctxt, &def->frequency);
+ ret = virXPathULongLong("string(./@frequency)", ctxt, &def->frequency);
if (ret == -1) {
def->frequency = 0;
} else if (ret < 0) {
@@ -22259,7 +22259,7 @@ virDomainTimerDefCheckABIStability(virDomainTimerDefPtr src,
if (src->name == VIR_DOMAIN_TIMER_NAME_TSC) {
if (src->frequency != dst->frequency) {
virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
- _("Target TSC frequency %lu does not match source %lu"),
+ _("Target TSC frequency %llu does not match source %llu"),
dst->frequency, src->frequency);
return false;
}
@@ -27355,7 +27355,7 @@ virDomainTimerDefFormat(virBufferPtr buf,
if (def->name == VIR_DOMAIN_TIMER_NAME_TSC) {
if (def->frequency > 0)
- virBufferAsprintf(buf, " frequency='%lu'", def->frequency);
+ virBufferAsprintf(buf, " frequency='%llu'", def->frequency);
if (def->mode != -1) {
const char *mode
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
index 15b9e79d69..c0a323d465 100644
--- a/src/conf/domain_conf.h
+++ b/src/conf/domain_conf.h
@@ -2078,7 +2078,7 @@ struct _virDomainTimerDef {
int track; /* host|guest */
/* frequency & mode are only valid for name='tsc' */
- unsigned long frequency; /* in Hz, unspecified = 0 */
+ unsigned long long frequency; /* in Hz, unspecified = 0 */
int mode; /* auto|native|emulate|paravirt */
};
diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index 27b2eef8e5..42f6e10b33 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -6761,7 +6761,7 @@ qemuBuildCpuCommandLine(virCommandPtr cmd,
break;
case VIR_DOMAIN_TIMER_NAME_TSC:
if (timer->frequency > 0)
- virBufferAsprintf(&buf, ",tsc-frequency=%lu", timer->frequency);
+ virBufferAsprintf(&buf, ",tsc-frequency=%llu", timer->frequency);
break;
case VIR_DOMAIN_TIMER_NAME_ARMVTIMER:
switch (timer->tickpolicy) {
--
2.33.0

View File

@ -1,31 +0,0 @@
From 5d762303253a8cf15204839e93cc3f6e562d3708 Mon Sep 17 00:00:00 2001
From: Mao Zhongyi <maozhongyi@cmss.chinamobile.com>
Date: Sat, 18 Sep 2021 14:20:24 +0800
Subject: [PATCH] conf/domain_conf: pin the retry_interval and retry_timeout
parameters to xml
Signed-off-by: Mao Zhongyi <maozhongyi@cmss.chinamobile.com>
---
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 a4e9b3290c..4e3bcf479c 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -24977,6 +24977,12 @@ virDomainDiskDefFormatDriver(virBufferPtr buf,
virBufferAsprintf(&driverBuf, " rerror_policy='%s'",
virDomainDiskErrorPolicyTypeToString(disk->rerror_policy));
+ if (disk->retry_interval)
+ virBufferAsprintf(&driverBuf, " retry_interval='%ld'", disk->retry_interval);
+
+ if (disk->retry_timeout)
+ virBufferAsprintf(&driverBuf, " retry_timeout='%ld'", disk->retry_timeout);
+
if (disk->iomode)
virBufferAsprintf(&driverBuf, " io='%s'",
virDomainDiskIoTypeToString(disk->iomode));
--
2.27.0

View File

@ -1,617 +0,0 @@
From 02565aca5158fb4d9870546ea29be85278649511 Mon Sep 17 00:00:00 2001
From: Luo Yifan <luoyifan_yewu@cmss.chinamobile.com>
Date: Wed, 30 Nov 2022 18:13:36 +0800
Subject: [PATCH 15/24] conf: implement support for vhostuser disk
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Signed-off-by: Pavel Hrdina <phrdina@redhat.com>
Reviewed-by: Ján Tomko <jtomko@redhat.com>
Reviewed-by: Peter Krempa <pkrempa@redhat.com>
(cherry picked from commit f00fe96eb045eed2b6b40d5046449bec6d495875)
Signed-off-by: Luo Yifan <luoyifan_yewu@cmss.chinamobile.com>
---
src/conf/domain_conf.c | 254 ++++++++++++++++++
src/libxl/xen_xl.c | 1 +
src/qemu/qemu_block.c | 6 +
src/qemu/qemu_command.c | 1 +
src/qemu/qemu_driver.c | 4 +
src/qemu/qemu_migration.c | 2 +
src/util/virstoragefile.c | 4 +
src/util/virstoragefile.h | 4 +
tests/qemuxml2argvdata/disk-vhostuser.xml | 30 +++
.../disk-vhostuser.x86_64-latest.xml | 48 ++++
tests/qemuxml2xmltest.c | 1 +
11 files changed, 355 insertions(+)
create mode 100644 tests/qemuxml2argvdata/disk-vhostuser.xml
create mode 100644 tests/qemuxml2xmloutdata/disk-vhostuser.x86_64-latest.xml
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index b60b9d31a1..8b1ca76d39 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -1278,6 +1278,17 @@ static virClassPtr virDomainXMLOptionClass;
static void virDomainObjDispose(void *obj);
static void virDomainXMLOptionDispose(void *obj);
+static int
+virDomainChrSourceDefFormat(virBufferPtr buf,
+ virDomainChrSourceDefPtr def,
+ unsigned int flags);
+
+
+static int
+virDomainChrSourceReconnectDefParseXML(virDomainChrSourceReconnectDefPtr def,
+ xmlNodePtr node,
+ xmlXPathContextPtr ctxt);
+
static int virDomainObjOnceInit(void)
{
if (!VIR_CLASS_NEW(virDomainObj, virClassForObjectLockable()))
@@ -5200,6 +5211,12 @@ virDomainDiskDefPostParse(virDomainDiskDefPtr disk,
disk->src->nvme->managed = VIR_TRISTATE_BOOL_YES;
}
+ /* vhost-user doesn't allow us to snapshot, disable snapshots by default */
+ if (disk->src->type == VIR_STORAGE_TYPE_VHOST_USER &&
+ disk->snapshot == VIR_DOMAIN_SNAPSHOT_LOCATION_DEFAULT) {
+ disk->snapshot = VIR_DOMAIN_SNAPSHOT_LOCATION_NONE;
+ }
+
if (disk->info.type == VIR_DOMAIN_DEVICE_ADDRESS_TYPE_NONE &&
virDomainDiskDefAssignAddress(xmlopt, disk, def) < 0) {
return -1;
@@ -5995,6 +6012,174 @@ virDomainDiskAddressDiskBusCompatibility(virDomainDiskBus bus,
return true;
}
+static int
+virDomainDiskVhostUserValidate(const virDomainDiskDef *disk)
+{
+ if (disk->bus != VIR_DOMAIN_DISK_BUS_VIRTIO) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("vhostuser disk supports only virtio bus"));
+ return -1;
+ }
+
+ if (disk->snapshot != VIR_DOMAIN_SNAPSHOT_LOCATION_NONE) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("only snapshot=no is supported with vhostuser disk"));
+ return -1;
+ }
+
+ /* Unsupported driver attributes */
+
+ if (disk->cachemode != VIR_DOMAIN_DISK_CACHE_DEFAULT) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("cache is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->error_policy || disk->rerror_policy) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("error_policy is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->iomode) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("io is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->ioeventfd != VIR_TRISTATE_SWITCH_ABSENT) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("ioeventfd is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->copy_on_read) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("copy_on_read is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->discard) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("discard is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->iothread) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("iothread is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->detect_zeroes) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("detect_zeroes is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ /* Unsupported driver elements */
+
+ if (disk->virtio) {
+ if (disk->virtio->iommu != VIR_TRISTATE_SWITCH_ABSENT) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("iommu is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->virtio->ats != VIR_TRISTATE_SWITCH_ABSENT) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("ats is not supported with vhostuser disk"));
+ return -1;
+ }
+ }
+
+ /* Unsupported disk elements */
+
+ if (disk->blkdeviotune.group_name ||
+ virDomainBlockIoTuneInfoHasAny(&disk->blkdeviotune)) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("iotune is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->src->backingStore) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("backingStore is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->src->encryption) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("encryption is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->src->readonly) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("readonly is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->src->shared) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("shareable is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->transient) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("transient is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->serial) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("serial is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->wwn) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("wwn is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->vendor) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("vendor is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->product) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("product is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->src->auth) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("auth is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->geometry.cylinders > 0 ||
+ disk->geometry.heads > 0 ||
+ disk->geometry.sectors > 0 ||
+ disk->geometry.trans != VIR_DOMAIN_DISK_TRANS_DEFAULT) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("geometry is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ if (disk->blockio.logical_block_size > 0 ||
+ disk->blockio.physical_block_size > 0) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
+ _("blockio is not supported with vhostuser disk"));
+ return -1;
+ }
+
+ return 0;
+}
static int
virSecurityDeviceLabelDefValidateXML(virSecurityDeviceLabelDefPtr *seclabels,
@@ -6095,6 +6280,11 @@ virDomainDiskDefValidate(const virDomainDef *def,
}
}
+ if (disk->src->type == VIR_STORAGE_TYPE_VHOST_USER &&
+ virDomainDiskVhostUserValidate(disk) < 0) {
+ return -1;
+ }
+
for (next = disk->src; next; next = next->backingStore) {
if (virSecurityDeviceLabelDefValidateXML(next->seclabels,
next->nseclabels,
@@ -9530,6 +9720,47 @@ virDomainDiskSourceNetworkParse(xmlNodePtr node,
return 0;
}
+static int
+virDomainDiskSourceVHostUserParse(xmlNodePtr node,
+ virStorageSourcePtr src,
+ virDomainXMLOptionPtr xmlopt,
+ xmlXPathContextPtr ctxt)
+{
+ g_autofree char *type = virXMLPropString(node, "type");
+ g_autofree char *path = virXMLPropString(node, "path");
+
+ if (!type) {
+ virReportError(VIR_ERR_XML_ERROR, "%s",
+ _("missing 'type' attribute for vhostuser disk source"));
+ return -1;
+ }
+
+ if (STRNEQ(type, "unix")) {
+ virReportError(VIR_ERR_XML_ERROR, "%s",
+ _("invalid 'type' attribute for vhostuser disk source"));
+ return -1;
+ }
+
+ if (!path) {
+ virReportError(VIR_ERR_XML_ERROR, "%s",
+ _("missing 'path' attribute for vhostuser disk source"));
+ return -1;
+ }
+
+ if (!(src->vhostuser = virDomainChrSourceDefNew(xmlopt)))
+ return -1;
+
+ src->vhostuser->type = virDomainChrTypeFromString(type);
+ src->vhostuser->data.nix.path = g_steal_pointer(&path);
+
+ if (virDomainChrSourceReconnectDefParseXML(&src->vhostuser->data.nix.reconnect,
+ node,
+ ctxt) < 0) {
+ return -1;
+ }
+
+ return 0;
+}
static int
virDomainDiskSourceNVMeParse(xmlNodePtr node,
@@ -9746,6 +9977,10 @@ virDomainStorageSourceParse(xmlNodePtr node,
if (virDomainDiskSourceNVMeParse(node, ctxt, src) < 0)
return -1;
break;
+ case VIR_STORAGE_TYPE_VHOST_USER:
+ if (virDomainDiskSourceVHostUserParse(node, src, xmlopt, ctxt) < 0)
+ return -1;
+ break;
case VIR_STORAGE_TYPE_NONE:
case VIR_STORAGE_TYPE_LAST:
virReportError(VIR_ERR_INTERNAL_ERROR,
@@ -24682,6 +24917,21 @@ virDomainDiskSourceNVMeFormat(virBufferPtr attrBuf,
virPCIDeviceAddressFormat(childBuf, nvme->pciAddr, false);
}
+static void
+virDomainChrSourceReconnectDefFormat(virBufferPtr buf,
+ virDomainChrSourceReconnectDefPtr def);
+
+
+static void
+virDomainDiskSourceVhostuserFormat(virBufferPtr attrBuf,
+ virBufferPtr childBuf,
+ virDomainChrSourceDefPtr vhostuser)
+{
+ virBufferAddLit(attrBuf, " type='unix'");
+ virBufferAsprintf(attrBuf, " path='%s'", vhostuser->data.nix.path);
+
+ virDomainChrSourceReconnectDefFormat(childBuf, &vhostuser->data.nix.reconnect);
+}
static int
virDomainDiskSourceFormatPrivateData(virBufferPtr buf,
@@ -24796,6 +25046,10 @@ virDomainDiskSourceFormat(virBufferPtr buf,
virDomainDiskSourceNVMeFormat(&attrBuf, &childBuf, src->nvme);
break;
+ case VIR_STORAGE_TYPE_VHOST_USER:
+ virDomainDiskSourceVhostuserFormat(&attrBuf, &childBuf, src->vhostuser);
+ break;
+
case VIR_STORAGE_TYPE_NONE:
case VIR_STORAGE_TYPE_LAST:
virReportError(VIR_ERR_INTERNAL_ERROR,
diff --git a/src/libxl/xen_xl.c b/src/libxl/xen_xl.c
index 91b1825399..08eea48d6c 100644
--- a/src/libxl/xen_xl.c
+++ b/src/libxl/xen_xl.c
@@ -1641,6 +1641,7 @@ xenFormatXLDiskSrc(virStorageSourcePtr src, char **srcstr)
case VIR_STORAGE_TYPE_VOLUME:
case VIR_STORAGE_TYPE_NVME:
+ case VIR_STORAGE_TYPE_VHOST_USER:
case VIR_STORAGE_TYPE_NONE:
case VIR_STORAGE_TYPE_LAST:
break;
diff --git a/src/qemu/qemu_block.c b/src/qemu/qemu_block.c
index d32277d7fd..8bd6238238 100644
--- a/src/qemu/qemu_block.c
+++ b/src/qemu/qemu_block.c
@@ -1108,6 +1108,11 @@ qemuBlockStorageSourceGetBackendProps(virStorageSourcePtr src,
return NULL;
break;
+ case VIR_STORAGE_TYPE_VHOST_USER:
+ virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+ _("unable to create blockdev props for vhostuser disk type"));
+ return NULL;
+
case VIR_STORAGE_TYPE_VOLUME:
virReportError(VIR_ERR_INTERNAL_ERROR,
_("storage source pool '%s' volume '%s' is not translated"),
@@ -2491,6 +2496,7 @@ qemuBlockStorageSourceCreateGetStorageProps(virStorageSourcePtr src,
case VIR_STORAGE_TYPE_DIR:
case VIR_STORAGE_TYPE_VOLUME:
case VIR_STORAGE_TYPE_NVME:
+ case VIR_STORAGE_TYPE_VHOST_USER:
return 0;
case VIR_STORAGE_TYPE_NONE:
diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index 9157008b73..bc62843783 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -1166,6 +1166,7 @@ qemuGetDriveSourceString(virStorageSourcePtr src,
case VIR_STORAGE_TYPE_VOLUME:
case VIR_STORAGE_TYPE_NVME:
+ case VIR_STORAGE_TYPE_VHOST_USER:
case VIR_STORAGE_TYPE_NONE:
case VIR_STORAGE_TYPE_LAST:
break;
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index 854b56a563..b2ad021e4d 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -14536,6 +14536,7 @@ qemuDomainSnapshotPrepareDiskExternalInactive(virDomainSnapshotDiskDefPtr snapdi
case VIR_STORAGE_TYPE_DIR:
case VIR_STORAGE_TYPE_VOLUME:
case VIR_STORAGE_TYPE_NVME:
+ case VIR_STORAGE_TYPE_VHOST_USER:
case VIR_STORAGE_TYPE_NONE:
case VIR_STORAGE_TYPE_LAST:
virReportError(VIR_ERR_INTERNAL_ERROR,
@@ -14553,6 +14554,7 @@ qemuDomainSnapshotPrepareDiskExternalInactive(virDomainSnapshotDiskDefPtr snapdi
case VIR_STORAGE_TYPE_DIR:
case VIR_STORAGE_TYPE_VOLUME:
case VIR_STORAGE_TYPE_NVME:
+ case VIR_STORAGE_TYPE_VHOST_USER:
case VIR_STORAGE_TYPE_NONE:
case VIR_STORAGE_TYPE_LAST:
virReportError(VIR_ERR_INTERNAL_ERROR,
@@ -14621,6 +14623,7 @@ qemuDomainSnapshotPrepareDiskExternalActive(virDomainSnapshotDiskDefPtr snapdisk
case VIR_STORAGE_TYPE_DIR:
case VIR_STORAGE_TYPE_VOLUME:
case VIR_STORAGE_TYPE_NVME:
+ case VIR_STORAGE_TYPE_VHOST_USER:
case VIR_STORAGE_TYPE_NONE:
case VIR_STORAGE_TYPE_LAST:
virReportError(VIR_ERR_INTERNAL_ERROR,
@@ -14749,6 +14752,7 @@ qemuDomainSnapshotPrepareDiskInternal(virDomainDiskDefPtr disk,
case VIR_STORAGE_TYPE_DIR:
case VIR_STORAGE_TYPE_VOLUME:
case VIR_STORAGE_TYPE_NVME:
+ case VIR_STORAGE_TYPE_VHOST_USER:
case VIR_STORAGE_TYPE_NONE:
case VIR_STORAGE_TYPE_LAST:
virReportError(VIR_ERR_INTERNAL_ERROR,
diff --git a/src/qemu/qemu_migration.c b/src/qemu/qemu_migration.c
index 1c48138ce3..faf4e223a8 100644
--- a/src/qemu/qemu_migration.c
+++ b/src/qemu/qemu_migration.c
@@ -228,6 +228,7 @@ qemuMigrationDstPrecreateDisk(virConnectPtr conn,
case VIR_STORAGE_TYPE_BLOCK:
case VIR_STORAGE_TYPE_DIR:
case VIR_STORAGE_TYPE_NVME:
+ case VIR_STORAGE_TYPE_VHOST_USER:
case VIR_STORAGE_TYPE_NONE:
case VIR_STORAGE_TYPE_LAST:
virReportError(VIR_ERR_INTERNAL_ERROR,
@@ -1358,6 +1359,7 @@ qemuMigrationSrcIsSafe(virDomainDefPtr def,
unsafe = true;
break;
+ case VIR_STORAGE_TYPE_VHOST_USER:
case VIR_STORAGE_TYPE_NONE:
case VIR_STORAGE_TYPE_BLOCK:
case VIR_STORAGE_TYPE_DIR:
diff --git a/src/util/virstoragefile.c b/src/util/virstoragefile.c
index ffc8bdb344..2515dbf5ed 100644
--- a/src/util/virstoragefile.c
+++ b/src/util/virstoragefile.c
@@ -56,6 +56,7 @@ VIR_ENUM_IMPL(virStorage,
"network",
"volume",
"nvme",
+ "vhostuser",
);
VIR_ENUM_IMPL(virStorageFileFormat,
@@ -2617,6 +2618,7 @@ virStorageSourceIsLocalStorage(const virStorageSource *src)
/* While NVMe disks are local, they are not accessible via src->path.
* Therefore, we have to return false here. */
case VIR_STORAGE_TYPE_NVME:
+ case VIR_STORAGE_TYPE_VHOST_USER:
case VIR_STORAGE_TYPE_LAST:
case VIR_STORAGE_TYPE_NONE:
return false;
@@ -4164,6 +4166,7 @@ virStorageSourceUpdatePhysicalSize(virStorageSourcePtr src,
/* We shouldn't get VOLUME, but the switch requires all cases */
case VIR_STORAGE_TYPE_VOLUME:
case VIR_STORAGE_TYPE_NVME:
+ case VIR_STORAGE_TYPE_VHOST_USER:
case VIR_STORAGE_TYPE_NONE:
case VIR_STORAGE_TYPE_LAST:
return -1;
@@ -4610,6 +4613,7 @@ virStorageSourceIsRelative(virStorageSourcePtr src)
case VIR_STORAGE_TYPE_NETWORK:
case VIR_STORAGE_TYPE_VOLUME:
case VIR_STORAGE_TYPE_NVME:
+ case VIR_STORAGE_TYPE_VHOST_USER:
case VIR_STORAGE_TYPE_NONE:
case VIR_STORAGE_TYPE_LAST:
return false;
diff --git a/src/util/virstoragefile.h b/src/util/virstoragefile.h
index 7939c09cd5..f2096b8705 100644
--- a/src/util/virstoragefile.h
+++ b/src/util/virstoragefile.h
@@ -28,6 +28,7 @@
#include "virseclabel.h"
#include "virstorageencryption.h"
#include "virsecret.h"
+#include "../conf/virconftypes.h"
#include "virenum.h"
#include "virpci.h"
@@ -52,6 +53,7 @@ typedef enum {
VIR_STORAGE_TYPE_NETWORK,
VIR_STORAGE_TYPE_VOLUME,
VIR_STORAGE_TYPE_NVME,
+ VIR_STORAGE_TYPE_VHOST_USER,
VIR_STORAGE_TYPE_LAST
} virStorageType;
@@ -302,6 +304,8 @@ struct _virStorageSource {
virStorageSourceNVMeDefPtr nvme; /* type == VIR_STORAGE_TYPE_NVME */
+ virDomainChrSourceDefPtr vhostuser; /* type == VIR_STORAGE_TYPE_VHOST_USER */
+
virStorageSourceInitiatorDef initiator;
virObjectPtr privateData;
diff --git a/tests/qemuxml2argvdata/disk-vhostuser.xml b/tests/qemuxml2argvdata/disk-vhostuser.xml
new file mode 100644
index 0000000000..c96ef9119c
--- /dev/null
+++ b/tests/qemuxml2argvdata/disk-vhostuser.xml
@@ -0,0 +1,30 @@
+<domain type='qemu'>
+ <name>QEMUGuest1</name>
+ <uuid>c7a5fdbd-edaf-9455-926a-d65c16db1809</uuid>
+ <memory unit='KiB'>219136</memory>
+ <currentMemory unit='KiB'>219136</currentMemory>
+ <memoryBacking>
+ <source type='memfd'/>
+ <access mode='shared'/>
+ </memoryBacking>
+ <vcpu placement='static'>1</vcpu>
+ <os>
+ <type arch='i686' machine='pc'>hvm</type>
+ </os>
+ <devices>
+ <emulator>/usr/bin/qemu-system-x86_64</emulator>
+ <disk type='vhostuser' device='disk'>
+ <driver name='qemu' type='raw'/>
+ <source type='unix' path='/tmp/vhost1.sock'/>
+ <target dev='vda' bus='virtio'/>
+ <boot order='1'/>
+ </disk>
+ <disk type='vhostuser' device='disk'>
+ <driver name='qemu' type='raw'/>
+ <source type='unix' path='/tmp/vhost1.sock'>
+ <reconnect enabled='yes' timeout='10'/>
+ </source>
+ <target dev='vdb' bus='virtio'/>
+ </disk>
+ </devices>
+</domain>
diff --git a/tests/qemuxml2xmloutdata/disk-vhostuser.x86_64-latest.xml b/tests/qemuxml2xmloutdata/disk-vhostuser.x86_64-latest.xml
new file mode 100644
index 0000000000..9712dc0b12
--- /dev/null
+++ b/tests/qemuxml2xmloutdata/disk-vhostuser.x86_64-latest.xml
@@ -0,0 +1,48 @@
+<domain type='qemu'>
+ <name>QEMUGuest1</name>
+ <uuid>c7a5fdbd-edaf-9455-926a-d65c16db1809</uuid>
+ <memory unit='KiB'>219136</memory>
+ <currentMemory unit='KiB'>219136</currentMemory>
+ <memoryBacking>
+ <source type='memfd'/>
+ <access mode='shared'/>
+ </memoryBacking>
+ <vcpu placement='static'>1</vcpu>
+ <os>
+ <type arch='i686' machine='pc'>hvm</type>
+ </os>
+ <cpu mode='custom' match='exact' check='none'>
+ <model fallback='forbid'>qemu64</model>
+ </cpu>
+ <clock offset='utc'/>
+ <on_poweroff>destroy</on_poweroff>
+ <on_reboot>restart</on_reboot>
+ <on_crash>destroy</on_crash>
+ <devices>
+ <emulator>/usr/bin/qemu-system-x86_64</emulator>
+ <disk type='vhostuser' device='disk' snapshot='no'>
+ <driver name='qemu' type='raw'/>
+ <source type='unix' path='/tmp/vhost1.sock'/>
+ <target dev='vda' bus='virtio'/>
+ <boot order='1'/>
+ <address type='pci' domain='0x0000' bus='0x00' slot='0x02' function='0x0'/>
+ </disk>
+ <disk type='vhostuser' device='disk' snapshot='no'>
+ <driver name='qemu' type='raw'/>
+ <source type='unix' path='/tmp/vhost1.sock'>
+ <reconnect enabled='yes' timeout='10'/>
+ </source>
+ <target dev='vdb' bus='virtio'/>
+ <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/>
+ </disk>
+ <controller type='usb' index='0' model='piix3-uhci'>
+ <address type='pci' domain='0x0000' bus='0x00' slot='0x01' function='0x2'/>
+ </controller>
+ <controller type='pci' index='0' model='pci-root'/>
+ <input type='mouse' bus='ps2'/>
+ <input type='keyboard' bus='ps2'/>
+ <memballoon model='virtio'>
+ <address type='pci' domain='0x0000' bus='0x00' slot='0x04' function='0x0'/>
+ </memballoon>
+ </devices>
+</domain>
diff --git a/tests/qemuxml2xmltest.c b/tests/qemuxml2xmltest.c
index 3a2539596b..2569c27261 100644
--- a/tests/qemuxml2xmltest.c
+++ b/tests/qemuxml2xmltest.c
@@ -338,6 +338,7 @@ mymain(void)
DO_TEST("disk-network-vxhs", NONE);
DO_TEST("disk-network-tlsx509", NONE);
DO_TEST("disk-nvme", QEMU_CAPS_VIRTIO_SCSI, QEMU_CAPS_QCOW2_LUKS);
+ DO_TEST_CAPS_LATEST("disk-vhostuser");
DO_TEST("disk-scsi", QEMU_CAPS_SCSI_LSI, QEMU_CAPS_SCSI_MEGASAS,
QEMU_CAPS_SCSI_MPTSAS1068, QEMU_CAPS_SCSI_DISK_WWN);
DO_TEST("disk-virtio-scsi-reservations",
--
2.27.0

View File

@ -1,110 +0,0 @@
From a5ec03f25b225408a9e7ebbf7b9fc9e3e2f15166 Mon Sep 17 00:00:00 2001
From: Laine Stump <laine@redhat.com>
Date: Sat, 22 Aug 2020 23:42:52 -0400
Subject: [PATCH 049/108] conf: properly clear out autogenerated macvtap names
when formatting/parsing
Back when macvtap support was added in commit 315baab9443 in Feb. 2010
(libvirt-0.7.7), it was setup to autogenerate a name for the device if
one wasn't supplied, in the pattern "macvtap%d" (or "macvlan%d"),
similar to the way an unspecified standard tap device name will lead
to an autogenerated "vnet%d".
As a matter of fact, in commit ca1b7cc8e45 added in May 2010, the code
was changed to *always* ignore a supplied device name for macvtap
interfaces by deleting *any* name immediately during the <interface>
parsing (this was intended to prevent one domain which had failed to
completely start from deleting the macvtap device of another domain
which had subsequently been provided the same device name (this will
seem mildly ironic later). This was later fixed to only clear the
device name when inactive XML was being parsed. HOWEVER - this was
only done if the xml was <interface type='direct'> - autogenerated
names were not cleared for <interface type='network'> (which could
also result in a macvtap device).
Although the names of "vnetX" tap devices had always been
automatically cleared when parsing <interface> (see commit d1304583d
from July 2008 (!)), at the time macvtap support was added, both vnetX
and macvtapX device names were always included when formatting the
XML.
Then in commit a8be259d0cc (July 2011, libvirt-0.9.4), <interface>
formatting was changed to also clear out "vnetX" device names during
XML formatting as well. However the same treatment wasn't given to
"macvtapX".
Now in 2020, there has been a report that a failed migration leads to
the macvtap device of some other unrelated guest on the destination
host losing its network connectivity. It was determined that this was
due to the domain XML in the migration containing a macvtap device
name, e.g. "macvtap0", that was already in use by the other guest on
the destination. Normally this wouldn't be a problem, because libvirt
would see that the device was already in use, and then find a
different unused name. But in this case, other external problems were
causing the migration to fail prior to selecting a macvtap device and
successfully opening it, and during error recovery, qemuProcessStop()
was called, which went through all def->nets objects and (if they were
macvtap) deleted the device specified in net->ifname; since libvirt
hadn't gotten to the point of replacing the incoming "macvtap0" with
the name of a device it actually created for this guest, that meant
that "macvtap0" was deleted, *even though it was currently in use by a
different guest*!
Whew!
So, it turns out that when formatting "migratable" XML, "vnetX"
devices are omitted, just as when formatting "inactive" XML. By making
the code in both interface parsing and formatting consistent for
"vnetX", "macvtapX", and "macvlanX", we can thus make sure that the
autogenerated (and unneeded / completely *not* wanted) macvtap device
name will not be sent with the migration XML. This way when a
migration fails, net->ifname will be NULL, and libvirt won't have any
device to try and (erroneously) delete.
Signed-off-by: Laine Stump <laine@redhat.com>
Reviewed-by: Daniel Henrique Barboza <danielhb413@gmail.com>
(cherry picked from commit 282d135ddbb7203565cd5527b451469b14953994)
---
src/conf/domain_conf.c | 12 ++++--------
1 file changed, 4 insertions(+), 8 deletions(-)
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index 54228a2151..d3565ececf 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -12357,14 +12357,6 @@ virDomainNetDefParseXML(virDomainXMLOptionPtr xmlopt,
}
def->data.direct.linkdev = g_steal_pointer(&dev);
-
- if (ifname &&
- flags & VIR_DOMAIN_DEF_PARSE_INACTIVE &&
- (STRPREFIX(ifname, VIR_NET_GENERATED_MACVTAP_PREFIX) ||
- STRPREFIX(ifname, VIR_NET_GENERATED_MACVLAN_PREFIX))) {
- VIR_FREE(ifname);
- }
-
break;
case VIR_DOMAIN_NET_TYPE_HOSTDEV:
@@ -12410,6 +12402,8 @@ virDomainNetDefParseXML(virDomainXMLOptionPtr xmlopt,
if (def->managed_tap != VIR_TRISTATE_BOOL_NO && ifname &&
(flags & VIR_DOMAIN_DEF_PARSE_INACTIVE) &&
(STRPREFIX(ifname, VIR_NET_GENERATED_TAP_PREFIX) ||
+ STRPREFIX(ifname, VIR_NET_GENERATED_MACVTAP_PREFIX) ||
+ STRPREFIX(ifname, VIR_NET_GENERATED_MACVLAN_PREFIX) ||
(prefix && STRPREFIX(ifname, prefix)))) {
/* An auto-generated target name, blank it out */
VIR_FREE(ifname);
@@ -26263,6 +26257,8 @@ virDomainNetDefFormat(virBufferPtr buf,
(def->managed_tap == VIR_TRISTATE_BOOL_NO ||
!((flags & VIR_DOMAIN_DEF_FORMAT_INACTIVE) &&
(STRPREFIX(def->ifname, VIR_NET_GENERATED_TAP_PREFIX) ||
+ STRPREFIX(def->ifname, VIR_NET_GENERATED_MACVTAP_PREFIX) ||
+ STRPREFIX(def->ifname, VIR_NET_GENERATED_MACVLAN_PREFIX) ||
(prefix && STRPREFIX(def->ifname, prefix)))))) {
/* Skip auto-generated target names for inactive config. */
virBufferEscapeString(&attrBuf, " dev='%s'", def->ifname);
--
2.33.0

View File

@ -1,41 +0,0 @@
From 0e6fcb0eb5e3eb499a3cc7232fa1b7bf9f1813a2 Mon Sep 17 00:00:00 2001
From: jiangdawei15 <jiangdawei15@huawei.com>
Date: Thu, 11 Aug 2022 21:24:35 +0800
Subject: [PATCH 06/22] conf: validate serial port model in ABI checks
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
The serial port model cannot be allowed to
change across migration as it affects ABI.
Reviewed-by: Andrea Bolognani <abologna@redhat.com>
Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
Signed-off-by: Dawei Jiang jiangdawei15@huawei.com
---
src/conf/domain_conf.c | 8 ++++++++
1 file changed, 8 insertions(+)
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index 1689d92c51..2d1726af8f 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -23058,6 +23058,14 @@ virDomainSerialDefCheckABIStability(virDomainChrDefPtr src,
return false;
}
+ if (src->targetModel != dst->targetModel) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
+ _("Target serial model %s does not match source %s"),
+ virDomainChrSerialTargetModelTypeToString(dst->targetModel),
+ virDomainChrSerialTargetModelTypeToString(src->targetModel));
+ return false;
+ }
+
if (src->target.port != dst->target.port) {
virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
_("Target serial port %d does not match source %d"),
--
2.33.0

View File

@ -1,167 +0,0 @@
From 41717af8988db9c2d9d8b753f306f6deaa1cec8d Mon Sep 17 00:00:00 2001
From: Jiri Denemark <jdenemar@redhat.com>
Date: Tue, 19 May 2020 15:08:11 +0200
Subject: [PATCH 2/3] cpu_map: Add Cooperlake x86 CPU model
The stepping range (10-11) is likely incomplete. QEMU uses 10 and the
CPUID data for Cooperlake show 11. We will update the range if needed
once more details about he CPU are available.
Signed-off-by: Jiri Denemark <jdenemar@redhat.com>
Reviewed-by: Pavel Hrdina <phrdina@redhat.com>
Signed-off-by: Jingyi Wang <wangjingyi11@huawei.com>
---
src/cpu_map/index.xml | 1 +
src/cpu_map/x86_Cooperlake.xml | 89 +++++++++++++++++++
.../domaincapsdata/qemu_5.0.0-q35.x86_64.xml | 1 +
.../domaincapsdata/qemu_5.0.0-tcg.x86_64.xml | 1 +
tests/domaincapsdata/qemu_5.0.0.x86_64.xml | 1 +
5 files changed, 93 insertions(+)
create mode 100644 src/cpu_map/x86_Cooperlake.xml
diff --git a/src/cpu_map/index.xml b/src/cpu_map/index.xml
index 672d0a3c92..3ccc76b9ed 100644
--- a/src/cpu_map/index.xml
+++ b/src/cpu_map/index.xml
@@ -54,6 +54,7 @@
<include filename="x86_Icelake-Client-noTSX.xml"/>
<include filename="x86_Icelake-Server.xml"/>
<include filename="x86_Icelake-Server-noTSX.xml"/>
+ <include filename="x86_Cooperlake.xml"/>
<!-- AMD CPUs -->
<include filename="x86_athlon.xml"/>
diff --git a/src/cpu_map/x86_Cooperlake.xml b/src/cpu_map/x86_Cooperlake.xml
new file mode 100644
index 0000000000..77e695aea4
--- /dev/null
+++ b/src/cpu_map/x86_Cooperlake.xml
@@ -0,0 +1,89 @@
+<cpus>
+ <model name='Cooperlake'>
+ <decode host='on' guest='on'/>
+ <vendor name='Intel'/>
+ <feature name="3dnowprefetch"/>
+ <feature name="abm"/>
+ <feature name="adx"/>
+ <feature name="aes"/>
+ <feature name="apic"/>
+ <feature name="arat"/>
+ <feature name="arch-capabilities"/>
+ <feature name="avx"/>
+ <feature name="avx2"/>
+ <feature name="avx512-bf16"/>
+ <feature name="avx512bw"/>
+ <feature name="avx512cd"/>
+ <feature name="avx512dq"/>
+ <feature name="avx512f"/>
+ <feature name="avx512vl"/>
+ <feature name="avx512vnni"/>
+ <feature name="bmi1"/>
+ <feature name="bmi2"/>
+ <feature name="clflush"/>
+ <feature name="clflushopt"/>
+ <feature name="clwb"/>
+ <feature name="cmov"/>
+ <feature name="cx16"/>
+ <feature name="cx8"/>
+ <feature name="de"/>
+ <feature name="erms"/>
+ <feature name="f16c"/>
+ <feature name="fma"/>
+ <feature name="fpu"/>
+ <feature name="fsgsbase"/>
+ <feature name="fxsr"/>
+ <feature name="hle"/>
+ <feature name="ibrs-all"/>
+ <feature name="invpcid"/>
+ <feature name="lahf_lm"/>
+ <feature name="lm"/>
+ <feature name="mca"/>
+ <feature name="mce"/>
+ <feature name="mds-no"/>
+ <feature name="mmx"/>
+ <feature name="movbe"/>
+ <feature name="msr"/>
+ <feature name="mtrr"/>
+ <feature name="nx"/>
+ <feature name="pae"/>
+ <feature name="pat"/>
+ <feature name="pcid"/>
+ <feature name="pclmuldq"/>
+ <feature name="pdpe1gb"/>
+ <feature name="pge"/>
+ <feature name="pku"/>
+ <feature name="pni"/>
+ <feature name="popcnt"/>
+ <feature name="pschange-mc-no"/>
+ <feature name="pse"/>
+ <feature name="pse36"/>
+ <feature name="rdctl-no"/>
+ <feature name="rdrand"/>
+ <feature name="rdseed"/>
+ <feature name="rdtscp"/>
+ <feature name="rtm"/>
+ <feature name="sep"/>
+ <feature name="skip-l1dfl-vmentry"/>
+ <feature name="smap"/>
+ <feature name="smep"/>
+ <feature name="spec-ctrl"/>
+ <feature name="ssbd"/>
+ <feature name="sse"/>
+ <feature name="sse2"/>
+ <feature name="sse4.1"/>
+ <feature name="sse4.2"/>
+ <feature name="ssse3"/>
+ <feature name="stibp"/>
+ <feature name="syscall"/>
+ <feature name="taa-no"/>
+ <feature name="tsc"/>
+ <feature name="tsc-deadline"/>
+ <feature name="vme"/>
+ <feature name="x2apic"/>
+ <feature name="xgetbv1"/>
+ <feature name="xsave"/>
+ <feature name="xsavec"/>
+ <feature name="xsaveopt"/>
+ </model>
+</cpus>
diff --git a/tests/domaincapsdata/qemu_5.0.0-q35.x86_64.xml b/tests/domaincapsdata/qemu_5.0.0-q35.x86_64.xml
index ff721530cd..fa945fc002 100644
--- a/tests/domaincapsdata/qemu_5.0.0-q35.x86_64.xml
+++ b/tests/domaincapsdata/qemu_5.0.0-q35.x86_64.xml
@@ -93,6 +93,7 @@
<model usable='no'>EPYC-IBPB</model>
<model usable='no'>EPYC</model>
<model usable='no'>Dhyana</model>
+ <model usable='no'>Cooperlake</model>
<model usable='yes'>Conroe</model>
<model usable='no'>Cascadelake-Server-noTSX</model>
<model usable='no'>Cascadelake-Server</model>
diff --git a/tests/domaincapsdata/qemu_5.0.0-tcg.x86_64.xml b/tests/domaincapsdata/qemu_5.0.0-tcg.x86_64.xml
index d567863f49..a0eeed7c2d 100644
--- a/tests/domaincapsdata/qemu_5.0.0-tcg.x86_64.xml
+++ b/tests/domaincapsdata/qemu_5.0.0-tcg.x86_64.xml
@@ -101,6 +101,7 @@
<model usable='no'>EPYC-IBPB</model>
<model usable='no'>EPYC</model>
<model usable='no'>Dhyana</model>
+ <model usable='no'>Cooperlake</model>
<model usable='yes'>Conroe</model>
<model usable='no'>Cascadelake-Server-noTSX</model>
<model usable='no'>Cascadelake-Server</model>
diff --git a/tests/domaincapsdata/qemu_5.0.0.x86_64.xml b/tests/domaincapsdata/qemu_5.0.0.x86_64.xml
index 2c6066003d..fbde7a6ba2 100644
--- a/tests/domaincapsdata/qemu_5.0.0.x86_64.xml
+++ b/tests/domaincapsdata/qemu_5.0.0.x86_64.xml
@@ -92,6 +92,7 @@
<model usable='no'>EPYC-IBPB</model>
<model usable='no'>EPYC</model>
<model usable='no'>Dhyana</model>
+ <model usable='no'>Cooperlake</model>
<model usable='yes'>Conroe</model>
<model usable='no'>Cascadelake-Server-noTSX</model>
<model usable='no'>Cascadelake-Server</model>
--
2.27.0

View File

@ -1,131 +0,0 @@
From 9696e88e150fce9ea82eadb16726c8c3a7a197ae Mon Sep 17 00:00:00 2001
From: Jiri Denemark <jdenemar@redhat.com>
Date: Mon, 18 May 2020 20:55:42 +0200
Subject: [PATCH 1/3] cpu_map: Add pschange-mc-no bit in IA32_ARCH_CAPABILITIES
MSR
Signed-off-by: Jiri Denemark <jdenemar@redhat.com>
Reviewed-by: Pavel Hrdina <phrdina@redhat.com>
Signed-off-by: Jingyi Wang <wangjingyi11@huawei.com>
---
src/cpu_map/x86_features.xml | 3 +++
tests/cputestdata/x86_64-cpuid-Core-i7-8550U-enabled.xml | 2 +-
tests/cputestdata/x86_64-cpuid-Core-i7-8550U-guest.xml | 1 +
tests/cputestdata/x86_64-cpuid-Core-i7-8550U-host.xml | 1 +
tests/cputestdata/x86_64-cpuid-Core-i7-8550U-json.xml | 1 +
tests/domaincapsdata/qemu_4.2.0-q35.x86_64.xml | 1 +
tests/domaincapsdata/qemu_4.2.0.x86_64.xml | 1 +
tests/domaincapsdata/qemu_5.0.0-q35.x86_64.xml | 1 +
tests/domaincapsdata/qemu_5.0.0.x86_64.xml | 1 +
9 files changed, 11 insertions(+), 1 deletion(-)
diff --git a/src/cpu_map/x86_features.xml b/src/cpu_map/x86_features.xml
index 2c4c29dc99..8525ae0fa5 100644
--- a/src/cpu_map/x86_features.xml
+++ b/src/cpu_map/x86_features.xml
@@ -509,6 +509,9 @@
<feature name='mds-no'>
<msr index='0x10a' edx='0x00000000' eax='0x00000020'/>
</feature>
+ <feature name='pschange-mc-no'>
+ <msr index='0x10a' edx='0x00000000' eax='0x00000040'/>
+ </feature>
<feature name='tsx-ctrl'>
<msr index='0x10a' edx='0x00000000' eax='0x00000080'/>
</feature>
diff --git a/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-enabled.xml b/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-enabled.xml
index 6c480eeacf..57f8ebabba 100644
--- a/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-enabled.xml
+++ b/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-enabled.xml
@@ -5,5 +5,5 @@
<cpuid eax_in='0x00000007' ecx_in='0x00' eax='0x00000000' ebx='0x009c47ab' ecx='0x00000004' edx='0xac000400'/>
<cpuid eax_in='0x0000000d' ecx_in='0x01' eax='0x0000000f' ebx='0x00000000' ecx='0x00000000' edx='0x00000000'/>
<cpuid eax_in='0x80000001' ecx_in='0x00' eax='0x00000000' ebx='0x00000000' ecx='0x00000121' edx='0x2c100800'/>
- <msr index='0x10a' edx='0x00000000' eax='0x00000008'/>
+ <msr index='0x10a' edx='0x00000000' eax='0x00000048'/>
</cpudata>
diff --git a/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-guest.xml b/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-guest.xml
index 92404e4d03..ed06515e99 100644
--- a/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-guest.xml
+++ b/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-guest.xml
@@ -26,6 +26,7 @@
<feature policy='require' name='pdpe1gb'/>
<feature policy='require' name='invtsc'/>
<feature policy='require' name='skip-l1dfl-vmentry'/>
+ <feature policy='require' name='pschange-mc-no'/>
<feature policy='disable' name='hle'/>
<feature policy='disable' name='rtm'/>
</cpu>
diff --git a/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-host.xml b/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-host.xml
index 7f6fe2eac3..7681c94649 100644
--- a/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-host.xml
+++ b/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-host.xml
@@ -27,4 +27,5 @@
<feature name='pdpe1gb'/>
<feature name='invtsc'/>
<feature name='skip-l1dfl-vmentry'/>
+ <feature name='pschange-mc-no'/>
</cpu>
diff --git a/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-json.xml b/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-json.xml
index 645c0934c2..4774d39c7e 100644
--- a/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-json.xml
+++ b/tests/cputestdata/x86_64-cpuid-Core-i7-8550U-json.xml
@@ -14,6 +14,7 @@
<feature policy='require' name='xsaves'/>
<feature policy='require' name='pdpe1gb'/>
<feature policy='require' name='skip-l1dfl-vmentry'/>
+ <feature policy='require' name='pschange-mc-no'/>
<feature policy='disable' name='hle'/>
<feature policy='disable' name='rtm'/>
</cpu>
diff --git a/tests/domaincapsdata/qemu_4.2.0-q35.x86_64.xml b/tests/domaincapsdata/qemu_4.2.0-q35.x86_64.xml
index 1b8b8be2f5..fcb0505da0 100644
--- a/tests/domaincapsdata/qemu_4.2.0-q35.x86_64.xml
+++ b/tests/domaincapsdata/qemu_4.2.0-q35.x86_64.xml
@@ -47,6 +47,7 @@
<feature policy='require' name='pdpe1gb'/>
<feature policy='require' name='invtsc'/>
<feature policy='require' name='skip-l1dfl-vmentry'/>
+ <feature policy='require' name='pschange-mc-no'/>
</mode>
<mode name='custom' supported='yes'>
<model usable='yes'>qemu64</model>
diff --git a/tests/domaincapsdata/qemu_4.2.0.x86_64.xml b/tests/domaincapsdata/qemu_4.2.0.x86_64.xml
index 213dcc5a08..e22ef8e032 100644
--- a/tests/domaincapsdata/qemu_4.2.0.x86_64.xml
+++ b/tests/domaincapsdata/qemu_4.2.0.x86_64.xml
@@ -46,6 +46,7 @@
<feature policy='require' name='pdpe1gb'/>
<feature policy='require' name='invtsc'/>
<feature policy='require' name='skip-l1dfl-vmentry'/>
+ <feature policy='require' name='pschange-mc-no'/>
</mode>
<mode name='custom' supported='yes'>
<model usable='yes'>qemu64</model>
diff --git a/tests/domaincapsdata/qemu_5.0.0-q35.x86_64.xml b/tests/domaincapsdata/qemu_5.0.0-q35.x86_64.xml
index 45c3e00b1e..ff721530cd 100644
--- a/tests/domaincapsdata/qemu_5.0.0-q35.x86_64.xml
+++ b/tests/domaincapsdata/qemu_5.0.0-q35.x86_64.xml
@@ -47,6 +47,7 @@
<feature policy='require' name='pdpe1gb'/>
<feature policy='require' name='invtsc'/>
<feature policy='require' name='skip-l1dfl-vmentry'/>
+ <feature policy='require' name='pschange-mc-no'/>
</mode>
<mode name='custom' supported='yes'>
<model usable='yes'>qemu64</model>
diff --git a/tests/domaincapsdata/qemu_5.0.0.x86_64.xml b/tests/domaincapsdata/qemu_5.0.0.x86_64.xml
index d2a884eed1..2c6066003d 100644
--- a/tests/domaincapsdata/qemu_5.0.0.x86_64.xml
+++ b/tests/domaincapsdata/qemu_5.0.0.x86_64.xml
@@ -46,6 +46,7 @@
<feature policy='require' name='pdpe1gb'/>
<feature policy='require' name='invtsc'/>
<feature policy='require' name='skip-l1dfl-vmentry'/>
+ <feature policy='require' name='pschange-mc-no'/>
</mode>
<mode name='custom' supported='yes'>
<model usable='yes'>qemu64</model>
--
2.27.0

View File

@ -1,30 +0,0 @@
From fc20e12b3be7a4c96ff0a71112d69181408506d1 Mon Sep 17 00:00:00 2001
From: Jiri Denemark <jdenemar@redhat.com>
Date: Tue, 26 May 2020 12:52:00 +0200
Subject: [PATCH 3/3] cpu_map: Distribute x86_Cooperlake.xml
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Signed-off-by: Jiri Denemark <jdenemar@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Signed-off-by: Jingyi Wang <wangjingyi11@huawei.com>
---
src/cpu_map/Makefile.inc.am | 1 +
1 file changed, 1 insertion(+)
diff --git a/src/cpu_map/Makefile.inc.am b/src/cpu_map/Makefile.inc.am
index ab5268d94f..8eb818706a 100644
--- a/src/cpu_map/Makefile.inc.am
+++ b/src/cpu_map/Makefile.inc.am
@@ -22,6 +22,7 @@ cpumap_DATA = \
cpu_map/x86_Cascadelake-Server.xml \
cpu_map/x86_Cascadelake-Server-noTSX.xml \
cpu_map/x86_Conroe.xml \
+ cpu_map/x86_Cooperlake.xml \
cpu_map/x86_core2duo.xml \
cpu_map/x86_coreduo.xml \
cpu_map/x86_cpu64-rhel5.xml \
--
2.27.0

View File

@ -1,45 +0,0 @@
From a70f3b2d8b707063c63fb3b43751651e5fedebb9 Mon Sep 17 00:00:00 2001
From: Tim Wiederhake <twiederh@redhat.com>
Date: Wed, 2 Dec 2020 11:38:22 +0100
Subject: [PATCH 012/108] cpu_map: Fix Icelake Server model number
See arch/x86/include/asm/intel-family.h in the Kernel:
#define INTEL_FAM6_ICELAKE_X 0x6A
Signed-off-by: Tim Wiederhake <twiederh@redhat.com>
Reviewed-by: Jiri Denemark <jdenemar@redhat.com>
(cherry picked from commit 1278ac6265589cd83cc2e661056c860e98105507)
---
src/cpu_map/x86_Icelake-Server-noTSX.xml | 2 +-
src/cpu_map/x86_Icelake-Server.xml | 2 +-
2 files changed, 2 insertions(+), 2 deletions(-)
diff --git a/src/cpu_map/x86_Icelake-Server-noTSX.xml b/src/cpu_map/x86_Icelake-Server-noTSX.xml
index 2fd6906406..34a0f7c18c 100644
--- a/src/cpu_map/x86_Icelake-Server-noTSX.xml
+++ b/src/cpu_map/x86_Icelake-Server-noTSX.xml
@@ -1,7 +1,7 @@
<cpus>
<model name='Icelake-Server-noTSX'>
<decode host='on' guest='off'/>
- <signature family='6' model='134'/> <!-- 080660 -->
+ <signature family='6' model='106'/> <!-- 0606A5 -->
<vendor name='Intel'/>
<feature name='3dnowprefetch'/>
<feature name='abm'/>
diff --git a/src/cpu_map/x86_Icelake-Server.xml b/src/cpu_map/x86_Icelake-Server.xml
index 367ade7240..1ee4ea9cd4 100644
--- a/src/cpu_map/x86_Icelake-Server.xml
+++ b/src/cpu_map/x86_Icelake-Server.xml
@@ -1,7 +1,7 @@
<cpus>
<model name='Icelake-Server'>
<decode host='on' guest='on'/>
- <signature family='6' model='134'/> <!-- 080660 -->
+ <signature family='6' model='106'/> <!-- 0606A5 -->
<vendor name='Intel'/>
<feature name='3dnowprefetch'/>
<feature name='abm'/>
--
2.33.0

View File

@ -1,44 +0,0 @@
From 9549d796fd310e41ec58f1c438328d1bedc0cb93 Mon Sep 17 00:00:00 2001
From: tangbinzy <tangbin_yewu@cmss.chinamobile.com>
Date: Tue, 29 Nov 2022 12:12:58 +0000
Subject: [PATCH 09/24] cpu_ppc64: compare CPU function is ignoring return
value Function to compare CPU on 64-bits PowerPC is ignoring the flag to
avoid failure in case of CPUs (host and guest) are incompatible. Basically,
the function is returning -1 even if it is set to continue.
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Signed-off-by: Julio Faracco jcfaracco@gmail.com
Reviewed-by: Ján Tomko jtomko@redhat.com
Signed-off-by: Ján Tomko jtomko@redhat.com
Signed-off-by: tangbin tangbin_yewu@cmss.chinamobile.com
(cherry-pick from b356d81b8960c3a43212f8c0e9eab66465c8c10a)
---
src/cpu/cpu_ppc64.c | 8 ++++----
1 file changed, 4 insertions(+), 4 deletions(-)
diff --git a/src/cpu/cpu_ppc64.c b/src/cpu/cpu_ppc64.c
index 6b3590ab6a..9cbb28cbc5 100644
--- a/src/cpu/cpu_ppc64.c
+++ b/src/cpu/cpu_ppc64.c
@@ -561,11 +561,11 @@ virCPUppc64Compare(virCPUDefPtr host,
if (failIncompatible) {
virReportError(VIR_ERR_CPU_INCOMPATIBLE, "%s",
_("unknown host CPU"));
- } else {
- VIR_WARN("unknown host CPU");
- ret = VIR_CPU_COMPARE_INCOMPATIBLE;
+ return VIR_CPU_COMPARE_ERROR;
}
- return -1;
+
+ VIR_WARN("unknown host CPU");
+ return VIR_CPU_COMPARE_INCOMPATIBLE;
}
ret = ppc64Compute(host, cpu, NULL, &message);
--
2.27.0

View File

@ -1,108 +0,0 @@
From a450496281dbbc2b240bf5dc0829a17d113aed22 Mon Sep 17 00:00:00 2001
From: zhangxinhao <zhangxinhao1@huawei.com>
Date: Wed, 17 May 2023 09:41:19 +0800
Subject: cpu_topo: fix detection of vCPU pids when multiple
clusters are present
The logic for querying hotpluggable CPUs needs to sort the list
of CPUs returned by QEMU. Add the logic of cluster when sorting
the hotpluggable CPUs.
Signed-off-by: zhangxinhao <zhangxinhao1@huawei.com>
---
src/qemu/qemu_domain.c | 3 ++-
src/qemu/qemu_monitor.c | 2 ++
src/qemu/qemu_monitor.h | 2 ++
src/qemu/qemu_monitor_json.c | 5 +++++
4 files changed, 11 insertions(+), 1 deletion(-)
diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c
index 152c8615d5..fbc665aff3 100644
--- a/src/qemu/qemu_domain.c
+++ b/src/qemu/qemu_domain.c
@@ -13877,11 +13877,12 @@ qemuDomainRefreshVcpuInfo(virQEMUDriverPtr driver,
if (validTIDs)
VIR_DEBUG("vCPU[%zu] PID %llu is valid "
- "(node=%d socket=%d die=%d core=%d thread=%d)",
+ "(node=%d socket=%d die=%d cluster=%d core=%d thread=%d)",
i, (unsigned long long)info[i].tid,
info[i].node_id,
info[i].socket_id,
info[i].die_id,
+ info[i].cluster_id,
info[i].core_id,
info[i].thread_id);
}
diff --git a/src/qemu/qemu_monitor.c b/src/qemu/qemu_monitor.c
index ffd1d348e5..3bdfdbe078 100644
--- a/src/qemu/qemu_monitor.c
+++ b/src/qemu/qemu_monitor.c
@@ -1676,6 +1676,7 @@ qemuMonitorCPUInfoClear(qemuMonitorCPUInfoPtr cpus,
cpus[i].qemu_id = -1;
cpus[i].socket_id = -1;
cpus[i].die_id = -1;
+ cpus[i].cluster_id = -1;
cpus[i].core_id = -1;
cpus[i].thread_id = -1;
cpus[i].node_id = -1;
@@ -1832,6 +1833,7 @@ qemuMonitorGetCPUInfoHotplug(struct qemuMonitorQueryHotpluggableCpusEntry *hotpl
!vcpus[mastervcpu].online;
vcpus[mastervcpu].socket_id = hotplugvcpus[i].socket_id;
vcpus[mastervcpu].die_id = hotplugvcpus[i].die_id;
+ vcpus[mastervcpu].cluster_id = hotplugvcpus[i].cluster_id;
vcpus[mastervcpu].core_id = hotplugvcpus[i].core_id;
vcpus[mastervcpu].thread_id = hotplugvcpus[i].thread_id;
vcpus[mastervcpu].node_id = hotplugvcpus[i].node_id;
diff --git a/src/qemu/qemu_monitor.h b/src/qemu/qemu_monitor.h
index 76d0bbb753..1c6b001872 100644
--- a/src/qemu/qemu_monitor.h
+++ b/src/qemu/qemu_monitor.h
@@ -579,6 +579,7 @@ struct qemuMonitorQueryHotpluggableCpusEntry {
int node_id;
int socket_id;
int die_id;
+ int cluster_id;
int core_id;
int thread_id;
@@ -602,6 +603,7 @@ struct _qemuMonitorCPUInfo {
* all entries are -1 */
int socket_id;
int die_id;
+ int cluster_id;
int core_id;
int thread_id;
int node_id;
diff --git a/src/qemu/qemu_monitor_json.c b/src/qemu/qemu_monitor_json.c
index a02d0e2780..afd826bc2f 100644
--- a/src/qemu/qemu_monitor_json.c
+++ b/src/qemu/qemu_monitor_json.c
@@ -8598,12 +8598,14 @@ qemuMonitorJSONProcessHotpluggableCpusReply(virJSONValuePtr vcpu,
entry->node_id = -1;
entry->socket_id = -1;
entry->die_id = -1;
+ entry->cluster_id = -1;
entry->core_id = -1;
entry->thread_id = -1;
ignore_value(virJSONValueObjectGetNumberInt(props, "node-id", &entry->node_id));
ignore_value(virJSONValueObjectGetNumberInt(props, "socket-id", &entry->socket_id));
ignore_value(virJSONValueObjectGetNumberInt(props, "die-id", &entry->die_id));
+ ignore_value(virJSONValueObjectGetNumberInt(props, "cluster-id", &entry->cluster_id));
ignore_value(virJSONValueObjectGetNumberInt(props, "core-id", &entry->core_id));
ignore_value(virJSONValueObjectGetNumberInt(props, "thread-id", &entry->thread_id));
@@ -8641,6 +8643,9 @@ qemuMonitorQueryHotpluggableCpusEntrySort(const void *p1,
if (a->die_id != b->die_id)
return a->die_id - b->die_id;
+ if (a->cluster_id != b->cluster_id)
+ return a->cluster_id - b->cluster_id;
+
if (a->core_id != b->core_id)
return a->core_id - b->core_id;
--
2.25.1

View File

@ -1,522 +0,0 @@
From baa40f939ab38d80597651aec82779af25599bb0 Mon Sep 17 00:00:00 2001
From: zhangxinhao <zhangxinhao1@huawei.com>
Date: Tue, 9 May 2023 23:28:59 +0800
Subject: cpu_topo: support for reporting cluster_id in NUMA
topology
Support report the die_id in the NUMA topology capabilities.
Signed-off-by: zhangxinhao <zhangxinhao1@huawei.com>
---
docs/schemas/capability.rng | 3 ++
src/conf/capabilities.c | 4 ++-
src/conf/capabilities.h | 1 +
src/libvirt_linux.syms | 1 +
src/util/virhostcpu.c | 22 +++++++++++++
src/util/virhostcpu.h | 1 +
.../vircaps2xmldata/vircaps-aarch64-basic.xml | 32 +++++++++----------
.../vircaps-x86_64-basic-dies.xml | 24 +++++++-------
.../vircaps2xmldata/vircaps-x86_64-basic.xml | 32 +++++++++----------
.../vircaps2xmldata/vircaps-x86_64-caches.xml | 16 +++++-----
.../vircaps-x86_64-resctrl-cdp.xml | 24 +++++++-------
.../vircaps-x86_64-resctrl-cmt.xml | 24 +++++++-------
.../vircaps-x86_64-resctrl-fake-feature.xml | 24 +++++++-------
.../vircaps-x86_64-resctrl-skx-twocaches.xml | 2 +-
.../vircaps-x86_64-resctrl-skx.xml | 2 +-
.../vircaps-x86_64-resctrl.xml | 24 +++++++-------
16 files changed, 133 insertions(+), 103 deletions(-)
diff --git a/docs/schemas/capability.rng b/docs/schemas/capability.rng
index 031c55bf20..f5b37d8c18 100644
--- a/docs/schemas/capability.rng
+++ b/docs/schemas/capability.rng
@@ -268,6 +268,9 @@
<attribute name='die_id'>
<ref name='unsignedInt'/>
</attribute>
+ <attribute name='cluster_id'>
+ <ref name='unsignedInt'/>
+ </attribute>
<attribute name='core_id'>
<ref name='unsignedInt'/>
</attribute>
diff --git a/src/conf/capabilities.c b/src/conf/capabilities.c
index 12c8c3a324..3c3a66a78a 100644
--- a/src/conf/capabilities.c
+++ b/src/conf/capabilities.c
@@ -874,9 +874,10 @@ virCapabilitiesHostNUMAFormat(virCapsHostNUMAPtr caps,
return -1;
virBufferAsprintf(buf,
- " socket_id='%d' die_id='%d' core_id='%d' siblings='%s'",
+ " socket_id='%d' die_id='%d' cluster_id='%d' core_id='%d' siblings='%s'",
cell->cpus[j].socket_id,
cell->cpus[j].die_id,
+ cell->cpus[j].cluster_id,
cell->cpus[j].core_id,
siblings);
VIR_FREE(siblings);
@@ -1465,6 +1466,7 @@ virCapabilitiesFillCPUInfo(int cpu_id G_GNUC_UNUSED,
if (virHostCPUGetSocket(cpu_id, &cpu->socket_id) < 0 ||
virHostCPUGetDie(cpu_id, &cpu->die_id) < 0 ||
+ virHostCPUGetCluster(cpu_id, &cpu->cluster_id) < 0 ||
virHostCPUGetCore(cpu_id, &cpu->core_id) < 0)
return -1;
diff --git a/src/conf/capabilities.h b/src/conf/capabilities.h
index e2581fac8b..f88bb412b5 100644
--- a/src/conf/capabilities.h
+++ b/src/conf/capabilities.h
@@ -89,6 +89,7 @@ struct _virCapsHostNUMACellCPU {
unsigned int id;
unsigned int socket_id;
unsigned int die_id;
+ unsigned int cluster_id;
unsigned int core_id;
virBitmapPtr siblings;
};
diff --git a/src/libvirt_linux.syms b/src/libvirt_linux.syms
index 55649ae39c..004cbfee97 100644
--- a/src/libvirt_linux.syms
+++ b/src/libvirt_linux.syms
@@ -3,6 +3,7 @@
#
# util/virhostcpu.h
+virHostCPUGetCluster;
virHostCPUGetCore;
virHostCPUGetDie;
virHostCPUGetInfoPopulateLinux;
diff --git a/src/util/virhostcpu.c b/src/util/virhostcpu.c
index 8c8fc3a476..d2ac31e784 100644
--- a/src/util/virhostcpu.c
+++ b/src/util/virhostcpu.c
@@ -240,6 +240,28 @@ virHostCPUGetDie(unsigned int cpu, unsigned int *die)
return 0;
}
+int
+virHostCPUGetCluster(unsigned int cpu, unsigned int *cluster)
+{
+ int cluster_id;
+ int ret = virFileReadValueInt(&cluster_id,
+ "%s/cpu/cpu%u/topology/cluster_id",
+ SYSFS_SYSTEM_PATH, cpu);
+ if (ret == -1)
+ return -1;
+
+ /* If the file is not there, it's 0.
+ * Another alternative is cluster_id set to -1, meaning that
+ * the arch does not have cluster_id support. Set @cluster to
+ * 0 in this case too. */
+ if (ret == -2 || cluster_id < 0)
+ cluster_id = 0;
+
+ *cluster = cluster_id;
+
+ return 0;
+}
+
int
virHostCPUGetCore(unsigned int cpu, unsigned int *core)
{
diff --git a/src/util/virhostcpu.h b/src/util/virhostcpu.h
index 9be2e51a38..e3a04c2eeb 100644
--- a/src/util/virhostcpu.h
+++ b/src/util/virhostcpu.h
@@ -66,6 +66,7 @@ int virHostCPUStatsAssign(virNodeCPUStatsPtr param,
#ifdef __linux__
int virHostCPUGetSocket(unsigned int cpu, unsigned int *socket);
int virHostCPUGetDie(unsigned int cpu, unsigned int *die);
+int virHostCPUGetCluster(unsigned int cpu, unsigned int *cluster);
int virHostCPUGetCore(unsigned int cpu, unsigned int *core);
virBitmapPtr virHostCPUGetSiblingsList(unsigned int cpu);
diff --git a/tests/vircaps2xmldata/vircaps-aarch64-basic.xml b/tests/vircaps2xmldata/vircaps-aarch64-basic.xml
index 0a04052c40..5533ae0586 100644
--- a/tests/vircaps2xmldata/vircaps-aarch64-basic.xml
+++ b/tests/vircaps2xmldata/vircaps-aarch64-basic.xml
@@ -16,10 +16,10 @@
<pages unit='KiB' size='2048'>4096</pages>
<pages unit='KiB' size='1048576'>6144</pages>
<cpus num='4'>
- <cpu id='0' socket_id='0' die_id='0' core_id='0' siblings='0'/>
- <cpu id='1' socket_id='0' die_id='0' core_id='1' siblings='1'/>
- <cpu id='2' socket_id='0' die_id='0' core_id='2' siblings='2'/>
- <cpu id='3' socket_id='0' die_id='0' core_id='3' siblings='3'/>
+ <cpu id='0' socket_id='0' die_id='0' cluster_id='0' core_id='0' siblings='0'/>
+ <cpu id='1' socket_id='0' die_id='0' cluster_id='0' core_id='1' siblings='1'/>
+ <cpu id='2' socket_id='0' die_id='0' cluster_id='0' core_id='2' siblings='2'/>
+ <cpu id='3' socket_id='0' die_id='0' cluster_id='0' core_id='3' siblings='3'/>
</cpus>
</cell>
<cell id='1'>
@@ -28,10 +28,10 @@
<pages unit='KiB' size='2048'>6144</pages>
<pages unit='KiB' size='1048576'>8192</pages>
<cpus num='4'>
- <cpu id='4' socket_id='1' die_id='0' core_id='4' siblings='4'/>
- <cpu id='5' socket_id='1' die_id='0' core_id='5' siblings='5'/>
- <cpu id='6' socket_id='1' die_id='0' core_id='6' siblings='6'/>
- <cpu id='7' socket_id='1' die_id='0' core_id='7' siblings='7'/>
+ <cpu id='4' socket_id='1' die_id='0' cluster_id='0' core_id='4' siblings='4'/>
+ <cpu id='5' socket_id='1' die_id='0' cluster_id='0' core_id='5' siblings='5'/>
+ <cpu id='6' socket_id='1' die_id='0' cluster_id='0' core_id='6' siblings='6'/>
+ <cpu id='7' socket_id='1' die_id='0' cluster_id='0' core_id='7' siblings='7'/>
</cpus>
</cell>
<cell id='2'>
@@ -40,10 +40,10 @@
<pages unit='KiB' size='2048'>8192</pages>
<pages unit='KiB' size='1048576'>10240</pages>
<cpus num='4'>
- <cpu id='8' socket_id='2' die_id='0' core_id='8' siblings='8'/>
- <cpu id='9' socket_id='2' die_id='0' core_id='9' siblings='9'/>
- <cpu id='10' socket_id='2' die_id='0' core_id='10' siblings='10'/>
- <cpu id='11' socket_id='2' die_id='0' core_id='11' siblings='11'/>
+ <cpu id='8' socket_id='2' die_id='0' cluster_id='0' core_id='8' siblings='8'/>
+ <cpu id='9' socket_id='2' die_id='0' cluster_id='0' core_id='9' siblings='9'/>
+ <cpu id='10' socket_id='2' die_id='0' cluster_id='0' core_id='10' siblings='10'/>
+ <cpu id='11' socket_id='2' die_id='0' cluster_id='0' core_id='11' siblings='11'/>
</cpus>
</cell>
<cell id='3'>
@@ -52,10 +52,10 @@
<pages unit='KiB' size='2048'>10240</pages>
<pages unit='KiB' size='1048576'>12288</pages>
<cpus num='4'>
- <cpu id='12' socket_id='3' die_id='0' core_id='12' siblings='12'/>
- <cpu id='13' socket_id='3' die_id='0' core_id='13' siblings='13'/>
- <cpu id='14' socket_id='3' die_id='0' core_id='14' siblings='14'/>
- <cpu id='15' socket_id='3' die_id='0' core_id='15' siblings='15'/>
+ <cpu id='12' socket_id='3' die_id='0' cluster_id='0' core_id='12' siblings='12'/>
+ <cpu id='13' socket_id='3' die_id='0' cluster_id='0' core_id='13' siblings='13'/>
+ <cpu id='14' socket_id='3' die_id='0' cluster_id='0' core_id='14' siblings='14'/>
+ <cpu id='15' socket_id='3' die_id='0' cluster_id='0' core_id='15' siblings='15'/>
</cpus>
</cell>
</cells>
diff --git a/tests/vircaps2xmldata/vircaps-x86_64-basic-dies.xml b/tests/vircaps2xmldata/vircaps-x86_64-basic-dies.xml
index 8a3ca2d13c..c86dc4defc 100644
--- a/tests/vircaps2xmldata/vircaps-x86_64-basic-dies.xml
+++ b/tests/vircaps2xmldata/vircaps-x86_64-basic-dies.xml
@@ -14,18 +14,18 @@
<pages unit='KiB' size='2048'>4096</pages>
<pages unit='KiB' size='1048576'>6144</pages>
<cpus num='12'>
- <cpu id='0' socket_id='0' die_id='0' core_id='0' siblings='0'/>
- <cpu id='1' socket_id='0' die_id='0' core_id='1' siblings='1'/>
- <cpu id='2' socket_id='0' die_id='1' core_id='0' siblings='2'/>
- <cpu id='3' socket_id='0' die_id='1' core_id='1' siblings='3'/>
- <cpu id='4' socket_id='0' die_id='2' core_id='0' siblings='4'/>
- <cpu id='5' socket_id='0' die_id='2' core_id='1' siblings='5'/>
- <cpu id='6' socket_id='1' die_id='0' core_id='0' siblings='6'/>
- <cpu id='7' socket_id='1' die_id='0' core_id='1' siblings='7'/>
- <cpu id='8' socket_id='1' die_id='1' core_id='0' siblings='8'/>
- <cpu id='9' socket_id='1' die_id='1' core_id='1' siblings='9'/>
- <cpu id='10' socket_id='1' die_id='2' core_id='0' siblings='10'/>
- <cpu id='11' socket_id='1' die_id='2' core_id='1' siblings='11'/>
+ <cpu id='0' socket_id='0' die_id='0' cluster_id='0' core_id='0' siblings='0'/>
+ <cpu id='1' socket_id='0' die_id='0' cluster_id='0' core_id='1' siblings='1'/>
+ <cpu id='2' socket_id='0' die_id='1' cluster_id='0' core_id='0' siblings='2'/>
+ <cpu id='3' socket_id='0' die_id='1' cluster_id='0' core_id='1' siblings='3'/>
+ <cpu id='4' socket_id='0' die_id='2' cluster_id='0' core_id='0' siblings='4'/>
+ <cpu id='5' socket_id='0' die_id='2' cluster_id='0' core_id='1' siblings='5'/>
+ <cpu id='6' socket_id='1' die_id='0' cluster_id='0' core_id='0' siblings='6'/>
+ <cpu id='7' socket_id='1' die_id='0' cluster_id='0' core_id='1' siblings='7'/>
+ <cpu id='8' socket_id='1' die_id='1' cluster_id='0' core_id='0' siblings='8'/>
+ <cpu id='9' socket_id='1' die_id='1' cluster_id='0' core_id='1' siblings='9'/>
+ <cpu id='10' socket_id='1' die_id='2' cluster_id='0' core_id='0' siblings='10'/>
+ <cpu id='11' socket_id='1' die_id='2' cluster_id='0' core_id='1' siblings='11'/>
</cpus>
</cell>
</cells>
diff --git a/tests/vircaps2xmldata/vircaps-x86_64-basic.xml b/tests/vircaps2xmldata/vircaps-x86_64-basic.xml
index 4da09f889c..9ae155d571 100644
--- a/tests/vircaps2xmldata/vircaps-x86_64-basic.xml
+++ b/tests/vircaps2xmldata/vircaps-x86_64-basic.xml
@@ -14,10 +14,10 @@
<pages unit='KiB' size='2048'>4096</pages>
<pages unit='KiB' size='1048576'>6144</pages>
<cpus num='4'>
- <cpu id='0' socket_id='0' die_id='0' core_id='0' siblings='0'/>
- <cpu id='1' socket_id='0' die_id='0' core_id='1' siblings='1'/>
- <cpu id='2' socket_id='0' die_id='0' core_id='2' siblings='2'/>
- <cpu id='3' socket_id='0' die_id='0' core_id='3' siblings='3'/>
+ <cpu id='0' socket_id='0' die_id='0' cluster_id='0' core_id='0' siblings='0'/>
+ <cpu id='1' socket_id='0' die_id='0' cluster_id='0' core_id='1' siblings='1'/>
+ <cpu id='2' socket_id='0' die_id='0' cluster_id='0' core_id='2' siblings='2'/>
+ <cpu id='3' socket_id='0' die_id='0' cluster_id='0' core_id='3' siblings='3'/>
</cpus>
</cell>
<cell id='1'>
@@ -26,10 +26,10 @@
<pages unit='KiB' size='2048'>6144</pages>
<pages unit='KiB' size='1048576'>8192</pages>
<cpus num='4'>
- <cpu id='4' socket_id='1' die_id='0' core_id='4' siblings='4'/>
- <cpu id='5' socket_id='1' die_id='0' core_id='5' siblings='5'/>
- <cpu id='6' socket_id='1' die_id='0' core_id='6' siblings='6'/>
- <cpu id='7' socket_id='1' die_id='0' core_id='7' siblings='7'/>
+ <cpu id='4' socket_id='1' die_id='0' cluster_id='0' core_id='4' siblings='4'/>
+ <cpu id='5' socket_id='1' die_id='0' cluster_id='0' core_id='5' siblings='5'/>
+ <cpu id='6' socket_id='1' die_id='0' cluster_id='0' core_id='6' siblings='6'/>
+ <cpu id='7' socket_id='1' die_id='0' cluster_id='0' core_id='7' siblings='7'/>
</cpus>
</cell>
<cell id='2'>
@@ -38,10 +38,10 @@
<pages unit='KiB' size='2048'>8192</pages>
<pages unit='KiB' size='1048576'>10240</pages>
<cpus num='4'>
- <cpu id='8' socket_id='2' die_id='0' core_id='8' siblings='8'/>
- <cpu id='9' socket_id='2' die_id='0' core_id='9' siblings='9'/>
- <cpu id='10' socket_id='2' die_id='0' core_id='10' siblings='10'/>
- <cpu id='11' socket_id='2' die_id='0' core_id='11' siblings='11'/>
+ <cpu id='8' socket_id='2' die_id='0' cluster_id='0' core_id='8' siblings='8'/>
+ <cpu id='9' socket_id='2' die_id='0' cluster_id='0' core_id='9' siblings='9'/>
+ <cpu id='10' socket_id='2' die_id='0' cluster_id='0' core_id='10' siblings='10'/>
+ <cpu id='11' socket_id='2' die_id='0' cluster_id='0' core_id='11' siblings='11'/>
</cpus>
</cell>
<cell id='3'>
@@ -50,10 +50,10 @@
<pages unit='KiB' size='2048'>10240</pages>
<pages unit='KiB' size='1048576'>12288</pages>
<cpus num='4'>
- <cpu id='12' socket_id='3' die_id='0' core_id='12' siblings='12'/>
- <cpu id='13' socket_id='3' die_id='0' core_id='13' siblings='13'/>
- <cpu id='14' socket_id='3' die_id='0' core_id='14' siblings='14'/>
- <cpu id='15' socket_id='3' die_id='0' core_id='15' siblings='15'/>
+ <cpu id='12' socket_id='3' die_id='0' cluster_id='0' core_id='12' siblings='12'/>
+ <cpu id='13' socket_id='3' die_id='0' cluster_id='0' core_id='13' siblings='13'/>
+ <cpu id='14' socket_id='3' die_id='0' cluster_id='0' core_id='14' siblings='14'/>
+ <cpu id='15' socket_id='3' die_id='0' cluster_id='0' core_id='15' siblings='15'/>
</cpus>
</cell>
</cells>
diff --git a/tests/vircaps2xmldata/vircaps-x86_64-caches.xml b/tests/vircaps2xmldata/vircaps-x86_64-caches.xml
index 28f00c0a90..05b33147b7 100644
--- a/tests/vircaps2xmldata/vircaps-x86_64-caches.xml
+++ b/tests/vircaps2xmldata/vircaps-x86_64-caches.xml
@@ -17,14 +17,14 @@
<pages unit='KiB' size='2048'>4096</pages>
<pages unit='KiB' size='1048576'>6144</pages>
<cpus num='8'>
- <cpu id='0' socket_id='0' die_id='0' core_id='0' siblings='0,4'/>
- <cpu id='1' socket_id='0' die_id='0' core_id='1' siblings='1,5'/>
- <cpu id='2' socket_id='0' die_id='0' core_id='2' siblings='2,6'/>
- <cpu id='3' socket_id='0' die_id='0' core_id='3' siblings='3,7'/>
- <cpu id='4' socket_id='0' die_id='0' core_id='0' siblings='0,4'/>
- <cpu id='5' socket_id='0' die_id='0' core_id='1' siblings='1,5'/>
- <cpu id='6' socket_id='0' die_id='0' core_id='2' siblings='2,6'/>
- <cpu id='7' socket_id='0' die_id='0' core_id='3' siblings='3,7'/>
+ <cpu id='0' socket_id='0' die_id='0' cluster_id='0' core_id='0' siblings='0,4'/>
+ <cpu id='1' socket_id='0' die_id='0' cluster_id='0' core_id='1' siblings='1,5'/>
+ <cpu id='2' socket_id='0' die_id='0' cluster_id='0' core_id='2' siblings='2,6'/>
+ <cpu id='3' socket_id='0' die_id='0' cluster_id='0' core_id='3' siblings='3,7'/>
+ <cpu id='4' socket_id='0' die_id='0' cluster_id='0' core_id='0' siblings='0,4'/>
+ <cpu id='5' socket_id='0' die_id='0' cluster_id='0' core_id='1' siblings='1,5'/>
+ <cpu id='6' socket_id='0' die_id='0' cluster_id='0' core_id='2' siblings='2,6'/>
+ <cpu id='7' socket_id='0' die_id='0' cluster_id='0' core_id='3' siblings='3,7'/>
</cpus>
</cell>
</cells>
diff --git a/tests/vircaps2xmldata/vircaps-x86_64-resctrl-cdp.xml b/tests/vircaps2xmldata/vircaps-x86_64-resctrl-cdp.xml
index ee26fe9464..167b217d8e 100644
--- a/tests/vircaps2xmldata/vircaps-x86_64-resctrl-cdp.xml
+++ b/tests/vircaps2xmldata/vircaps-x86_64-resctrl-cdp.xml
@@ -17,12 +17,12 @@
<pages unit='KiB' size='2048'>4096</pages>
<pages unit='KiB' size='1048576'>6144</pages>
<cpus num='6'>
- <cpu id='0' socket_id='0' die_id='0' core_id='0' siblings='0'/>
- <cpu id='1' socket_id='0' die_id='0' core_id='1' siblings='1'/>
- <cpu id='2' socket_id='0' die_id='0' core_id='2' siblings='2'/>
- <cpu id='3' socket_id='0' die_id='0' core_id='3' siblings='3'/>
- <cpu id='4' socket_id='0' die_id='0' core_id='4' siblings='4'/>
- <cpu id='5' socket_id='0' die_id='0' core_id='5' siblings='5'/>
+ <cpu id='0' socket_id='0' die_id='0' cluster_id='0' core_id='0' siblings='0'/>
+ <cpu id='1' socket_id='0' die_id='0' cluster_id='0' core_id='1' siblings='1'/>
+ <cpu id='2' socket_id='0' die_id='0' cluster_id='0' core_id='2' siblings='2'/>
+ <cpu id='3' socket_id='0' die_id='0' cluster_id='0' core_id='3' siblings='3'/>
+ <cpu id='4' socket_id='0' die_id='0' cluster_id='0' core_id='4' siblings='4'/>
+ <cpu id='5' socket_id='0' die_id='0' cluster_id='0' core_id='5' siblings='5'/>
</cpus>
</cell>
<cell id='1'>
@@ -31,12 +31,12 @@
<pages unit='KiB' size='2048'>6144</pages>
<pages unit='KiB' size='1048576'>8192</pages>
<cpus num='6'>
- <cpu id='6' socket_id='1' die_id='0' core_id='0' siblings='6'/>
- <cpu id='7' socket_id='1' die_id='0' core_id='1' siblings='7'/>
- <cpu id='8' socket_id='1' die_id='0' core_id='2' siblings='8'/>
- <cpu id='9' socket_id='1' die_id='0' core_id='3' siblings='9'/>
- <cpu id='10' socket_id='1' die_id='0' core_id='4' siblings='10'/>
- <cpu id='11' socket_id='1' die_id='0' core_id='5' siblings='11'/>
+ <cpu id='6' socket_id='1' die_id='0' cluster_id='0' core_id='0' siblings='6'/>
+ <cpu id='7' socket_id='1' die_id='0' cluster_id='0' core_id='1' siblings='7'/>
+ <cpu id='8' socket_id='1' die_id='0' cluster_id='0' core_id='2' siblings='8'/>
+ <cpu id='9' socket_id='1' die_id='0' cluster_id='0' core_id='3' siblings='9'/>
+ <cpu id='10' socket_id='1' die_id='0' cluster_id='0' core_id='4' siblings='10'/>
+ <cpu id='11' socket_id='1' die_id='0' cluster_id='0' core_id='5' siblings='11'/>
</cpus>
</cell>
</cells>
diff --git a/tests/vircaps2xmldata/vircaps-x86_64-resctrl-cmt.xml b/tests/vircaps2xmldata/vircaps-x86_64-resctrl-cmt.xml
index acdd97ec58..311bb58e6a 100644
--- a/tests/vircaps2xmldata/vircaps-x86_64-resctrl-cmt.xml
+++ b/tests/vircaps2xmldata/vircaps-x86_64-resctrl-cmt.xml
@@ -17,12 +17,12 @@
<pages unit='KiB' size='2048'>4096</pages>
<pages unit='KiB' size='1048576'>6144</pages>
<cpus num='6'>
- <cpu id='0' socket_id='0' die_id='0' core_id='0' siblings='0'/>
- <cpu id='1' socket_id='0' die_id='0' core_id='1' siblings='1'/>
- <cpu id='2' socket_id='0' die_id='0' core_id='2' siblings='2'/>
- <cpu id='3' socket_id='0' die_id='0' core_id='3' siblings='3'/>
- <cpu id='4' socket_id='0' die_id='0' core_id='4' siblings='4'/>
- <cpu id='5' socket_id='0' die_id='0' core_id='5' siblings='5'/>
+ <cpu id='0' socket_id='0' die_id='0' cluster_id='0' core_id='0' siblings='0'/>
+ <cpu id='1' socket_id='0' die_id='0' cluster_id='0' core_id='1' siblings='1'/>
+ <cpu id='2' socket_id='0' die_id='0' cluster_id='0' core_id='2' siblings='2'/>
+ <cpu id='3' socket_id='0' die_id='0' cluster_id='0' core_id='3' siblings='3'/>
+ <cpu id='4' socket_id='0' die_id='0' cluster_id='0' core_id='4' siblings='4'/>
+ <cpu id='5' socket_id='0' die_id='0' cluster_id='0' core_id='5' siblings='5'/>
</cpus>
</cell>
<cell id='1'>
@@ -31,12 +31,12 @@
<pages unit='KiB' size='2048'>6144</pages>
<pages unit='KiB' size='1048576'>8192</pages>
<cpus num='6'>
- <cpu id='6' socket_id='1' die_id='0' core_id='0' siblings='6'/>
- <cpu id='7' socket_id='1' die_id='0' core_id='1' siblings='7'/>
- <cpu id='8' socket_id='1' die_id='0' core_id='2' siblings='8'/>
- <cpu id='9' socket_id='1' die_id='0' core_id='3' siblings='9'/>
- <cpu id='10' socket_id='1' die_id='0' core_id='4' siblings='10'/>
- <cpu id='11' socket_id='1' die_id='0' core_id='5' siblings='11'/>
+ <cpu id='6' socket_id='1' die_id='0' cluster_id='0' core_id='0' siblings='6'/>
+ <cpu id='7' socket_id='1' die_id='0' cluster_id='0' core_id='1' siblings='7'/>
+ <cpu id='8' socket_id='1' die_id='0' cluster_id='0' core_id='2' siblings='8'/>
+ <cpu id='9' socket_id='1' die_id='0' cluster_id='0' core_id='3' siblings='9'/>
+ <cpu id='10' socket_id='1' die_id='0' cluster_id='0' core_id='4' siblings='10'/>
+ <cpu id='11' socket_id='1' die_id='0' cluster_id='0' core_id='5' siblings='11'/>
</cpus>
</cell>
</cells>
diff --git a/tests/vircaps2xmldata/vircaps-x86_64-resctrl-fake-feature.xml b/tests/vircaps2xmldata/vircaps-x86_64-resctrl-fake-feature.xml
index 5f3678e072..8f64bcad63 100644
--- a/tests/vircaps2xmldata/vircaps-x86_64-resctrl-fake-feature.xml
+++ b/tests/vircaps2xmldata/vircaps-x86_64-resctrl-fake-feature.xml
@@ -17,12 +17,12 @@
<pages unit='KiB' size='2048'>4096</pages>
<pages unit='KiB' size='1048576'>6144</pages>
<cpus num='6'>
- <cpu id='0' socket_id='0' die_id='0' core_id='0' siblings='0'/>
- <cpu id='1' socket_id='0' die_id='0' core_id='1' siblings='1'/>
- <cpu id='2' socket_id='0' die_id='0' core_id='2' siblings='2'/>
- <cpu id='3' socket_id='0' die_id='0' core_id='3' siblings='3'/>
- <cpu id='4' socket_id='0' die_id='0' core_id='4' siblings='4'/>
- <cpu id='5' socket_id='0' die_id='0' core_id='5' siblings='5'/>
+ <cpu id='0' socket_id='0' die_id='0' cluster_id='0' core_id='0' siblings='0'/>
+ <cpu id='1' socket_id='0' die_id='0' cluster_id='0' core_id='1' siblings='1'/>
+ <cpu id='2' socket_id='0' die_id='0' cluster_id='0' core_id='2' siblings='2'/>
+ <cpu id='3' socket_id='0' die_id='0' cluster_id='0' core_id='3' siblings='3'/>
+ <cpu id='4' socket_id='0' die_id='0' cluster_id='0' core_id='4' siblings='4'/>
+ <cpu id='5' socket_id='0' die_id='0' cluster_id='0' core_id='5' siblings='5'/>
</cpus>
</cell>
<cell id='1'>
@@ -31,12 +31,12 @@
<pages unit='KiB' size='2048'>6144</pages>
<pages unit='KiB' size='1048576'>8192</pages>
<cpus num='6'>
- <cpu id='6' socket_id='1' die_id='0' core_id='0' siblings='6'/>
- <cpu id='7' socket_id='1' die_id='0' core_id='1' siblings='7'/>
- <cpu id='8' socket_id='1' die_id='0' core_id='2' siblings='8'/>
- <cpu id='9' socket_id='1' die_id='0' core_id='3' siblings='9'/>
- <cpu id='10' socket_id='1' die_id='0' core_id='4' siblings='10'/>
- <cpu id='11' socket_id='1' die_id='0' core_id='5' siblings='11'/>
+ <cpu id='6' socket_id='1' die_id='0' cluster_id='0' core_id='0' siblings='6'/>
+ <cpu id='7' socket_id='1' die_id='0' cluster_id='0' core_id='1' siblings='7'/>
+ <cpu id='8' socket_id='1' die_id='0' cluster_id='0' core_id='2' siblings='8'/>
+ <cpu id='9' socket_id='1' die_id='0' cluster_id='0' core_id='3' siblings='9'/>
+ <cpu id='10' socket_id='1' die_id='0' cluster_id='0' core_id='4' siblings='10'/>
+ <cpu id='11' socket_id='1' die_id='0' cluster_id='0' core_id='5' siblings='11'/>
</cpus>
</cell>
</cells>
diff --git a/tests/vircaps2xmldata/vircaps-x86_64-resctrl-skx-twocaches.xml b/tests/vircaps2xmldata/vircaps-x86_64-resctrl-skx-twocaches.xml
index 6769bd0591..eb53eb2142 100644
--- a/tests/vircaps2xmldata/vircaps-x86_64-resctrl-skx-twocaches.xml
+++ b/tests/vircaps2xmldata/vircaps-x86_64-resctrl-skx-twocaches.xml
@@ -17,7 +17,7 @@
<pages unit='KiB' size='2048'>4096</pages>
<pages unit='KiB' size='1048576'>6144</pages>
<cpus num='1'>
- <cpu id='0' socket_id='0' die_id='0' core_id='0' siblings='0'/>
+ <cpu id='0' socket_id='0' die_id='0' cluster_id='0' core_id='0' siblings='0'/>
</cpus>
</cell>
</cells>
diff --git a/tests/vircaps2xmldata/vircaps-x86_64-resctrl-skx.xml b/tests/vircaps2xmldata/vircaps-x86_64-resctrl-skx.xml
index bc52480905..38ea0bdc27 100644
--- a/tests/vircaps2xmldata/vircaps-x86_64-resctrl-skx.xml
+++ b/tests/vircaps2xmldata/vircaps-x86_64-resctrl-skx.xml
@@ -17,7 +17,7 @@
<pages unit='KiB' size='2048'>4096</pages>
<pages unit='KiB' size='1048576'>6144</pages>
<cpus num='1'>
- <cpu id='0' socket_id='0' die_id='0' core_id='0' siblings='0'/>
+ <cpu id='0' socket_id='0' die_id='0' cluster_id='0' core_id='0' siblings='0'/>
</cpus>
</cell>
</cells>
diff --git a/tests/vircaps2xmldata/vircaps-x86_64-resctrl.xml b/tests/vircaps2xmldata/vircaps-x86_64-resctrl.xml
index c386edd4b0..ea9e2613d7 100644
--- a/tests/vircaps2xmldata/vircaps-x86_64-resctrl.xml
+++ b/tests/vircaps2xmldata/vircaps-x86_64-resctrl.xml
@@ -17,12 +17,12 @@
<pages unit='KiB' size='2048'>4096</pages>
<pages unit='KiB' size='1048576'>6144</pages>
<cpus num='6'>
- <cpu id='0' socket_id='0' die_id='0' core_id='0' siblings='0'/>
- <cpu id='1' socket_id='0' die_id='0' core_id='1' siblings='1'/>
- <cpu id='2' socket_id='0' die_id='0' core_id='2' siblings='2'/>
- <cpu id='3' socket_id='0' die_id='0' core_id='3' siblings='3'/>
- <cpu id='4' socket_id='0' die_id='0' core_id='4' siblings='4'/>
- <cpu id='5' socket_id='0' die_id='0' core_id='5' siblings='5'/>
+ <cpu id='0' socket_id='0' die_id='0' cluster_id='0' core_id='0' siblings='0'/>
+ <cpu id='1' socket_id='0' die_id='0' cluster_id='0' core_id='1' siblings='1'/>
+ <cpu id='2' socket_id='0' die_id='0' cluster_id='0' core_id='2' siblings='2'/>
+ <cpu id='3' socket_id='0' die_id='0' cluster_id='0' core_id='3' siblings='3'/>
+ <cpu id='4' socket_id='0' die_id='0' cluster_id='0' core_id='4' siblings='4'/>
+ <cpu id='5' socket_id='0' die_id='0' cluster_id='0' core_id='5' siblings='5'/>
</cpus>
</cell>
<cell id='1'>
@@ -31,12 +31,12 @@
<pages unit='KiB' size='2048'>6144</pages>
<pages unit='KiB' size='1048576'>8192</pages>
<cpus num='6'>
- <cpu id='6' socket_id='1' die_id='0' core_id='0' siblings='6'/>
- <cpu id='7' socket_id='1' die_id='0' core_id='1' siblings='7'/>
- <cpu id='8' socket_id='1' die_id='0' core_id='2' siblings='8'/>
- <cpu id='9' socket_id='1' die_id='0' core_id='3' siblings='9'/>
- <cpu id='10' socket_id='1' die_id='0' core_id='4' siblings='10'/>
- <cpu id='11' socket_id='1' die_id='0' core_id='5' siblings='11'/>
+ <cpu id='6' socket_id='1' die_id='0' cluster_id='0' core_id='0' siblings='6'/>
+ <cpu id='7' socket_id='1' die_id='0' cluster_id='0' core_id='1' siblings='7'/>
+ <cpu id='8' socket_id='1' die_id='0' cluster_id='0' core_id='2' siblings='8'/>
+ <cpu id='9' socket_id='1' die_id='0' cluster_id='0' core_id='3' siblings='9'/>
+ <cpu id='10' socket_id='1' die_id='0' cluster_id='0' core_id='4' siblings='10'/>
+ <cpu id='11' socket_id='1' die_id='0' cluster_id='0' core_id='5' siblings='11'/>
</cpus>
</cell>
</cells>
--
2.25.1

View File

@ -1,163 +0,0 @@
From 2e275763162623b59b1872a16c0c9f0f3837f530 Mon Sep 17 00:00:00 2001
From: zhangxinhao <zhangxinhao1@huawei.com>
Date: Tue, 9 May 2023 23:01:36 +0800
Subject: cpu_topo: support for specifying "clusters" in qemu
comand
Support for cpu topology "clusters" for qemu command parameter "-smp".
Signed-off-by: zhangxinhao <zhangxinhao1@huawei.com>
---
src/qemu/qemu_capabilities.c | 2 ++
src/qemu/qemu_capabilities.h | 1 +
src/qemu/qemu_command.c | 7 ++---
tests/qemuxml2argvdata/smp-clusters.args | 30 +++++++++++++++++++++
tests/qemuxml2argvdata/smp-clusters.xml | 33 ++++++++++++++++++++++++
tests/qemuxml2argvtest.c | 1 +
6 files changed, 69 insertions(+), 5 deletions(-)
create mode 100644 tests/qemuxml2argvdata/smp-clusters.args
create mode 100644 tests/qemuxml2argvdata/smp-clusters.xml
diff --git a/src/qemu/qemu_capabilities.c b/src/qemu/qemu_capabilities.c
index 21b477cd4d..19030b2040 100644
--- a/src/qemu/qemu_capabilities.c
+++ b/src/qemu/qemu_capabilities.c
@@ -579,6 +579,7 @@ VIR_ENUM_IMPL(virQEMUCaps,
/* 365 */
"calc-dirty-rate",
"dirtyrate-param.mode",
+ "smp-clusters",
);
@@ -3218,6 +3219,7 @@ static struct virQEMUCapsCommandLineProps virQEMUCapsCommandLine[] = {
{ "chardev", "fd", QEMU_CAPS_CHARDEV_FD_PASS },
{ "overcommit", NULL, QEMU_CAPS_OVERCOMMIT },
{ "smp-opts", "dies", QEMU_CAPS_SMP_DIES },
+ { "smp-opts", "clusters", QEMU_CAPS_SMP_CLUSTERS },
};
static int
diff --git a/src/qemu/qemu_capabilities.h b/src/qemu/qemu_capabilities.h
index 00682eb52c..43507760c8 100644
--- a/src/qemu/qemu_capabilities.h
+++ b/src/qemu/qemu_capabilities.h
@@ -560,6 +560,7 @@ typedef enum { /* virQEMUCapsFlags grouping marker for syntax-check */
/* 365 */
QEMU_CAPS_CALC_DIRTY_RATE, /* accepts calc-dirty-rate */
QEMU_CAPS_DIRTYRATE_MODE , /* calc-dirty-rate accepts mode parameter */
+ QEMU_CAPS_SMP_CLUSTERS, /* -smp clusters= */
QEMU_CAPS_LAST /* this must always be the last item */
} virQEMUCapsFlags;
diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index 85f95b41c3..dc7fb871e7 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -7335,14 +7335,11 @@ qemuBuildSmpCommandLine(virCommandPtr cmd,
_("Only 1 die per socket is supported"));
return -1;
}
- if (def->cpu->clusters != 1) {
- virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
- _("Only 1 cluster per dies is supported"));
- return -1;
- }
virBufferAsprintf(&buf, ",sockets=%u", def->cpu->sockets);
if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_SMP_DIES))
virBufferAsprintf(&buf, ",dies=%u", def->cpu->dies);
+ if (virQEMUCapsGet(qemuCaps, QEMU_CAPS_SMP_CLUSTERS))
+ virBufferAsprintf(&buf, ",clusters=%u", def->cpu->clusters);
virBufferAsprintf(&buf, ",cores=%u", def->cpu->cores);
virBufferAsprintf(&buf, ",threads=%u", def->cpu->threads);
} else {
diff --git a/tests/qemuxml2argvdata/smp-clusters.args b/tests/qemuxml2argvdata/smp-clusters.args
new file mode 100644
index 0000000000..ab91ad7218
--- /dev/null
+++ b/tests/qemuxml2argvdata/smp-clusters.args
@@ -0,0 +1,30 @@
+LC_ALL=C \
+PATH=/bin \
+HOME=/tmp/lib/domain--1-QEMUGuest1 \
+USER=test \
+LOGNAME=test \
+XDG_DATA_HOME=/tmp/lib/domain--1-QEMUGuest1/.local/share \
+XDG_CACHE_HOME=/tmp/lib/domain--1-QEMUGuest1/.cache \
+XDG_CONFIG_HOME=/tmp/lib/domain--1-QEMUGuest1/.config \
+QEMU_AUDIO_DRV=none \
+/usr/bin/qemu-system-i386 \
+-name QEMUGuest1 \
+-S \
+-machine pc,usb=off,dump-guest-core=off \
+-accel tcg \
+-m 214 \
+-realtime mlock=off \
+-smp 1,maxcpus=4,sockets=2,clusters=2,cores=1,threads=1 \
+-uuid c7a5fdbd-edaf-9455-926a-d65c16db1809 \
+-display none \
+-no-user-config \
+-nodefaults \
+-chardev socket,id=charmonitor,path=/tmp/lib/domain--1-QEMUGuest1/monitor.sock,\
+server,nowait \
+-mon chardev=charmonitor,id=monitor,mode=control \
+-rtc base=utc \
+-no-shutdown \
+-no-acpi \
+-usb \
+-drive file=/dev/HostVG/QEMUGuest1,format=raw,if=none,id=drive-ide0-0-0 \
+-device ide-hd,bus=ide.0,unit=0,drive=drive-ide0-0-0,id=ide0-0-0,bootindex=1
diff --git a/tests/qemuxml2argvdata/smp-clusters.xml b/tests/qemuxml2argvdata/smp-clusters.xml
new file mode 100644
index 0000000000..c1845b8213
--- /dev/null
+++ b/tests/qemuxml2argvdata/smp-clusters.xml
@@ -0,0 +1,33 @@
+<domain type='qemu'>
+ <name>QEMUGuest1</name>
+ <uuid>c7a5fdbd-edaf-9455-926a-d65c16db1809</uuid>
+ <memory unit='KiB'>219136</memory>
+ <currentMemory unit='KiB'>219136</currentMemory>
+ <vcpu placement='static' current='1'>4</vcpu>
+ <os>
+ <type arch='i686' machine='pc'>hvm</type>
+ <boot dev='hd'/>
+ </os>
+ <cpu>
+ <topology sockets='2' clusters='2' cores='1' threads='1'/>
+ </cpu>
+ <clock offset='utc'/>
+ <on_poweroff>destroy</on_poweroff>
+ <on_reboot>restart</on_reboot>
+ <on_crash>destroy</on_crash>
+ <devices>
+ <emulator>/usr/bin/qemu-system-i386</emulator>
+ <disk type='block' device='disk'>
+ <driver name='qemu' type='raw'/>
+ <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='ide' index='0'/>
+ <controller type='pci' index='0' model='pci-root'/>
+ <input type='mouse' bus='ps2'/>
+ <input type='keyboard' bus='ps2'/>
+ <memballoon model='none'/>
+ </devices>
+</domain>
diff --git a/tests/qemuxml2argvtest.c b/tests/qemuxml2argvtest.c
index ec90532b5f..df62dfacb6 100644
--- a/tests/qemuxml2argvtest.c
+++ b/tests/qemuxml2argvtest.c
@@ -1828,6 +1828,7 @@ mymain(void)
DO_TEST("smp", NONE);
DO_TEST("smp-dies", QEMU_CAPS_SMP_DIES);
+ DO_TEST("smp-clusters", QEMU_CAPS_SMP_CLUSTERS);
DO_TEST("iothreads", QEMU_CAPS_OBJECT_IOTHREAD);
DO_TEST("iothreads-ids", QEMU_CAPS_OBJECT_IOTHREAD);
--
2.25.1

View File

@ -1,42 +0,0 @@
From 9e4751b3a9c0435c4cb199c353144acb55458473 Mon Sep 17 00:00:00 2001
From: Sebastian Mitterle <smitterl@redhat.com>
Date: Sat, 29 Aug 2020 00:49:07 +0000
Subject: [PATCH 027/108] disk storage: fix allocation size for pool format dos
The changed condition was always false because the function was always
called with boundary values 0.
Use the free extent's start value to get its start offset from the
cylinder boundary and determine if the needed size for allocation
needs to be expanded too in case the offset doesn't fit within extra
bytes for alignment.
This fixes an issue where vol-create-from will call qemu-img convert
to create a destination volume of same capacity as the source volume
and qemu-img will error 'Cannot grow device files' due to the partition
being too small for the source although both destination partition and
source volume have the same capacity.
Signed-off-by: Sebastian Mitterle <smitterl@redhat.com>
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
(cherry picked from commit 653fdf48e352814efdbff72aa5421f65385088ac)
---
src/storage/storage_backend_disk.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/src/storage/storage_backend_disk.c b/src/storage/storage_backend_disk.c
index eae23ec24a..da06357b90 100644
--- a/src/storage/storage_backend_disk.c
+++ b/src/storage/storage_backend_disk.c
@@ -691,7 +691,7 @@ virStorageBackendDiskPartBoundaries(virStoragePoolObjPtr pool,
if (def->source.format == VIR_STORAGE_POOL_DISK_DOS) {
/* align to cylinder boundary */
neededSize += extraBytes;
- if ((*start % cylinderSize) > extraBytes) {
+ if ((dev->freeExtents[i].start % cylinderSize) > extraBytes) {
/* add an extra cylinder if the offset can't fit within
the extra bytes we have */
neededSize += cylinderSize;
--
2.33.0

View File

@ -1,60 +0,0 @@
From 2fc51790318ec17fbca46185991fac8cc3302ec0 Mon Sep 17 00:00:00 2001
From: Martin Kletzander <mkletzan@redhat.com>
Date: Mon, 21 Feb 2022 09:26:13 +0100
Subject: [PATCH] docs: Fix template matching in page.xsl
Our last default template had a match of "node()" which incidentally matched
everything, including text nodes. Since this has the same priority according to
the XSLT spec, section 5.5:
https://www.w3.org/TR/1999/REC-xslt-19991116#conflict
this is an error. Also according to the same spec section, the XSLT processor
may signal the error or pick the last rule.
This was uncovered with libxslt 1.1.35 which contains the following commit:
https://gitlab.gnome.org/GNOME/libxslt/-/commit/b0074eeca3c6b21b4da14fdf712b853900c51635
which makes the build fail with:
runtime error: file ../docs/page.xsl line 223 element element
xsl:element: The effective name '' is not a valid QName.
because our last rule also matches text nodes and we are trying to extract the
node name out of them.
To fix this we change the match to "*" which only matches elements and not all
the nodes, and to avoid any possible errors with different XSLT processors we
also bump the priority of the match="text()" rule a little higher, just in case
someone needs to use an XSLT processor that chooses signalling the error instead
of the optional recovery.
https://bugs.gentoo.org/833586
Signed-off-by: Martin Kletzander <mkletzan@redhat.com>
---
docs/page.xsl | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/docs/page.xsl b/docs/page.xsl
index ddae5ab508..5dc46329fd 100644
--- a/docs/page.xsl
+++ b/docs/page.xsl
@@ -194,11 +194,11 @@
</xsl:element>
</xsl:template>
- <xsl:template match="text()" mode="copy">
+ <xsl:template match="text()" mode="copy" priority="0">
<xsl:value-of select="."/>
</xsl:template>
- <xsl:template match="node()" mode="copy">
+ <xsl:template match="*" mode="copy">
<xsl:element name="{name()}">
<xsl:copy-of select="./@*"/>
<xsl:apply-templates mode="copy" />
--
2.27.0

View File

@ -1,62 +0,0 @@
From c99e7e8abe1e22f504173a976a82e1a72551bdc1 Mon Sep 17 00:00:00 2001
From: Peter Krempa <pkrempa@redhat.com>
Date: Mon, 3 Aug 2020 07:32:29 +0200
Subject: [PATCH] docs: build: Don't include stylesheet in intermediate html
files generated from RST
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
'docutils' add a stylesheet to the output html file for direct
consumption. Since we use the html files just as an intermediate step
which is post-processed to add our own stylesheet and drop the docutils
one in the process we can ask 'rst2html' to not add any for an
intermediate file with less garbage.
Signed-off-by: Peter Krempa <pkrempa@redhat.com>
Reviewed-by: Ján Tomko <jtomko@redhat.com>
Signed-off-by: rpm-build <rpm-build>
---
docs/Makefile.am | 4 ++--
docs/Makefile.in | 4 ++--
2 files changed, 4 insertions(+), 4 deletions(-)
diff --git a/docs/Makefile.am b/docs/Makefile.am
index 61862c4..4c44504 100644
--- a/docs/Makefile.am
+++ b/docs/Makefile.am
@@ -420,11 +420,11 @@ manpages/%.html.in: manpages/%.rst
grep -v '^:Manual ' < $< | \
sed -e 's|SYSCONFDIR|$(sysconfdir)|g' \
-e 's|RUNSTATEDIR|$(runstatedir)|g' | \
- $(RST2HTML) --strict > $@ || { rm $@ && exit 1; }
+ $(RST2HTML) --stylesheet= --strict > $@ || { rm $@ && exit 1; }
%.html.in: %.rst
$(AM_V_GEN)$(MKDIR_P) `dirname $@` && \
- $(RST2HTML) --strict $< > $@ || { rm $@ && exit 1; }
+ $(RST2HTML) --stylesheet= --strict $< > $@ || { rm $@ && exit 1; }
%.html.tmp: %.html.in site.xsl subsite.xsl page.xsl \
$(acl_generated)
diff --git a/docs/Makefile.in b/docs/Makefile.in
index 61eac52..1836655 100644
--- a/docs/Makefile.in
+++ b/docs/Makefile.in
@@ -1469,11 +1469,11 @@ manpages/%.html.in: manpages/%.rst
grep -v '^:Manual ' < $< | \
sed -e 's|SYSCONFDIR|$(sysconfdir)|g' \
-e 's|RUNSTATEDIR|$(runstatedir)|g' | \
- $(RST2HTML) --strict > $@ || { rm $@ && exit 1; }
+ $(RST2HTML) --stylesheet= --strict > $@ || { rm $@ && exit 1; }
%.html.in: %.rst
$(AM_V_GEN)$(MKDIR_P) `dirname $@` && \
- $(RST2HTML) --strict $< > $@ || { rm $@ && exit 1; }
+ $(RST2HTML) --stylesheet= --strict $< > $@ || { rm $@ && exit 1; }
%.html.tmp: %.html.in site.xsl subsite.xsl page.xsl \
$(acl_generated)
--
2.27.0

View File

@ -1,149 +0,0 @@
From 0b8ff5672665c3792c27c02d9d05e0951c03d440 Mon Sep 17 00:00:00 2001
From: Luo Yifan <luoyifan_yewu@cmss.chinamobile.com>
Date: Wed, 30 Nov 2022 18:13:36 +0800
Subject: [PATCH 14/24] docs: introduces new vhostuser disk type
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
<disk type='vhostuser' device='disk'>
<driver name='qemu' type='raw'/>
<source type='unix' path='/tmp/vhost-blk.sock'>
<reconnect enabled='yes' timeout='10'/>
</source>
<target dev='vda' bus='virtio'/>
</disk>
Signed-off-by: Pavel Hrdina <phrdina@redhat.com>
Reviewed-by: Ján Tomko <jtomko@redhat.com>
Reviewed-by: Peter Krempa <pkrempa@redhat.com>
(cherry picked from commit e88bdaf789b6f1cc5347b217240f15afd86a94c1)
Signed-off-by: Luo Yifan <luoyifan_yewu@cmss.chinamobile.com>
---
docs/formatdomain.html.in | 51 ++++++++++++++++++++++++++++++++++-
docs/schemas/domaincommon.rng | 19 +++++++++++++
2 files changed, 69 insertions(+), 1 deletion(-)
diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in
index aaeb05961f..5860ec9f20 100644
--- a/docs/formatdomain.html.in
+++ b/docs/formatdomain.html.in
@@ -2977,6 +2977,13 @@
&lt;/source&gt;
&lt;target dev='vde' bus='virtio'/&gt;
&lt;/disk&gt;
+ &lt;disk type='vhostuser' device='disk'&gt;
+ &lt;driver name='qemu' type='raw'/&gt;
+ &lt;source type='unix' path='/tmp/vhost-blk.sock'&gt;
+ &lt;reconnect enabled='yes' timeout='10'/&gt;
+ &lt;/source&gt;
+ &lt;target dev='vdf' bus='virtio'/&gt;
+ &lt;/disk&gt;
&lt;/devices&gt;
...</pre>
@@ -2991,7 +2998,8 @@
"dir" (<span class="since">since 0.7.5</span>),
"network" (<span class="since">since 0.8.7</span>), or
"volume" (<span class="since">since 1.0.5</span>), or
- "nvme" (<span class="since">since 6.0.0</span>)
+ "nvme" (<span class="since">since 6.0.0</span>), or
+ "vhostuser" (<span class="since">since 6.2.0</span>)
and refer to the underlying source for the disk.
<span class="since">Since 0.0.3</span>
</dd>
@@ -3217,6 +3225,31 @@
<code>&lt;disk type='block'&gt;</code> and therefore lower
latencies can be achieved.
</dd>
+ <dt><code>vhostuser</code></dt>
+ <dd>
+ Enables the hypervisor to connect to another process using vhost-user
+ protocol. Requires shared memory configured for the VM, for more details
+ see <code>access</code> mode for
+ <code>memoryBacking &lt;#elementsMemoryBacking&gt;</code> element.
+
+ The <code>source</code> element has following mandatory attributes:
+ <dl>
+ <dt><code>type</code></dt>
+ <dd>The type of char device. Currently only <code>unix</code> type
+ is supported.
+ </dd>
+
+ <dt><code>path</code></dt>
+ <dd>Path to the unix socket to be used as disk source.
+ </dd>
+ </dl>
+
+ Note that the vhost server replaces both the disk frontend and backend
+ thus almost all of the disk properties can't be configured via the
+ <code>&lt;disk&gt;</code> XML for this disk type. Additionally features
+ such as blockjobs, incremental backups and snapshots are not supported
+ for this disk type.
+ </dd>
</dl>
With "file", "block", and "volume", one or more optional
sub-elements <code>seclabel</code>, <a href="#seclabel">described
@@ -3424,6 +3457,22 @@
Note that '0' is considered as if the value is not provided.
<span class="since">Since 6.2.0</span>
</dd>
+ <dt><code>reconnect</code></dt>
+ <dd>
+ For disk type <code>vhostuser</code> configures reconnect timeout
+ if the connection is lost. It has two mandatory attributes:
+ <dl>
+ <dt><code>enabled</code></dt>
+ <dd>If the reconnect feature is enabled, accepts<code>yes</code>
+ and <code>no</code>
+ </dd>
+
+ <dt><code>timeout</code></dt>
+ <dd>The amount of seconds after which hypervisor tries to reconnect.
+ </dd>
+ </dl>
+ <span class="since">Since 6.2.0</span>
+ </dd>
</dl>
<p>
diff --git a/docs/schemas/domaincommon.rng b/docs/schemas/domaincommon.rng
index 1807df521c..764f826df4 100644
--- a/docs/schemas/domaincommon.rng
+++ b/docs/schemas/domaincommon.rng
@@ -1631,6 +1631,7 @@
<ref name="diskSourceNetwork"/>
<ref name="diskSourceVolume"/>
<ref name="diskSourceNvme"/>
+ <ref name="diskSourceVhostUser"/>
</choice>
</define>
@@ -2103,6 +2104,24 @@
</optional>
</define>
+ <define name="diskSourceVhostUser">
+ <attribute name="type">
+ <value>vhostuser</value>
+ </attribute>
+ <element name="source">
+ <attribute name="type">
+ <value>unix</value>
+ </attribute>
+ <attribute name="path">
+ <ref name="absFilePath"/>
+ </attribute>
+ <optional>
+ <ref name="reconnect"/>
+ </optional>
+ <empty/>
+ </element>
+ </define>
+
<define name="diskTarget">
<data type="string">
<param name="pattern">(ioemu:)?(fd|hd|sd|vd|xvd|ubd)[a-zA-Z0-9_]+</param>
--
2.27.0

View File

@ -1,45 +0,0 @@
From e59b2064ffefbc94c729d38ec0180197e2b1f8ed Mon Sep 17 00:00:00 2001
From: AlexChen <alex.chen@huawei.com>
Date: Mon, 12 Jul 2021 21:28:41 +0800
Subject: [PATCH] domain: add logs for virDomainHotpatchManage
Add logs for virDomainHotpatchManage to facilitate the location of
issues related to subsequent hotpatch.
Signed-off-by: Bihong Yu <yubihong@huawei.com>
Signed-off-by: AlexChen <alex.chen@huawei.com>
---
src/libvirt-domain.c | 13 +++++++++++--
1 file changed, 11 insertions(+), 2 deletions(-)
diff --git a/src/libvirt-domain.c b/src/libvirt-domain.c
index 068ab52f54..3cf6bcb3b4 100644
--- a/src/libvirt-domain.c
+++ b/src/libvirt-domain.c
@@ -12777,12 +12777,21 @@ virDomainHotpatchManage(virDomainPtr domain,
if (action == VIR_DOMAIN_HOTPATCH_UNAPPLY)
virCheckNonNullArgGoto(id, error);
+ VIR_INFO("enter virDomainHotpatchManage domainname=%s, action=%d, "
+ "patch=%s, id=%s, flags=%d",
+ NULLSTR(domain->name), action,
+ NULLSTR(patch), NULLSTR(id), flags);
+
if (conn->driver->domainHotpatchManage) {
char *ret;
ret = conn->driver->domainHotpatchManage(domain, action, patch, id, flags);
- if (!ret)
+ if (!ret) {
+ VIR_ERROR("domain %s managed hotpatch failed",
+ NULLSTR(domain->name));
goto error;
-
+ }
+ VIR_INFO("domain %s managed hotpatch successfully",
+ NULLSTR(domain->name));
return ret;
}
--
2.27.0

View File

@ -1,121 +0,0 @@
From 11073a79e7c7275436a43a43dd6b6e772b05588f Mon Sep 17 00:00:00 2001
From: Michal Privoznik <mprivozn@redhat.com>
Date: Wed, 18 Nov 2020 11:58:01 +0100
Subject: [PATCH 066/108] domain_capabilities: Assert enums fit into unsigned
int bitmask
The way our domain capabilities work currently, is that we have
virDomainCapsEnum struct which contains 'unsigned int values'
member which serves as a bitmask. More complicated structs are
composed from this struct, giving us whole virDomainCaps
eventually.
Whenever we want to report that a certain value is supported, the
'1 << value' bit is set in the corresponding unsigned int member.
This works as long as the resulting value after bitshift does not
overflow unsigned int. There is a check inside
virDomainCapsEnumSet() which ensures exactly this, but no caller
really checks whether virDomainCapsEnumSet() succeeded. Also,
checking at runtime is a bit too late.
Fortunately, we know the largest value we want to store in each
member, because each enum of ours ends with _LAST member.
Therefore, we can check at build time whether an overflow can
occur.
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
Reviewed-by: Erik Skultety <eskultet@redhat.com>
(cherry picked from commit 912421e7b63a358d552b79fac62a5518ec58f4e5)
---
src/conf/domain_capabilities.h | 19 +++++++++++++++++++
1 file changed, 19 insertions(+)
diff --git a/src/conf/domain_capabilities.h b/src/conf/domain_capabilities.h
index 9f4a23d015..0345c84855 100644
--- a/src/conf/domain_capabilities.h
+++ b/src/conf/domain_capabilities.h
@@ -36,6 +36,9 @@ struct _virDomainCapsEnum {
unsigned int values; /* Bitmask of values supported in the corresponding enum */
};
+#define STATIC_ASSERT_ENUM(last) \
+ G_STATIC_ASSERT(last <= sizeof(unsigned int) * CHAR_BIT)
+
typedef struct _virDomainCapsStringValues virDomainCapsStringValues;
typedef virDomainCapsStringValues *virDomainCapsStringValuesPtr;
struct _virDomainCapsStringValues {
@@ -43,6 +46,8 @@ struct _virDomainCapsStringValues {
size_t nvalues; /* number of strings */
};
+STATIC_ASSERT_ENUM(VIR_DOMAIN_LOADER_TYPE_LAST);
+STATIC_ASSERT_ENUM(VIR_TRISTATE_BOOL_LAST);
typedef struct _virDomainCapsLoader virDomainCapsLoader;
typedef virDomainCapsLoader *virDomainCapsLoaderPtr;
struct _virDomainCapsLoader {
@@ -53,6 +58,7 @@ struct _virDomainCapsLoader {
virDomainCapsEnum secure; /* Info about secure:virTristateBool */
};
+STATIC_ASSERT_ENUM(VIR_DOMAIN_OS_DEF_FIRMWARE_LAST);
typedef struct _virDomainCapsOS virDomainCapsOS;
typedef virDomainCapsOS *virDomainCapsOSPtr;
struct _virDomainCapsOS {
@@ -61,6 +67,9 @@ struct _virDomainCapsOS {
virDomainCapsLoader loader; /* Info about virDomainLoaderDef */
};
+STATIC_ASSERT_ENUM(VIR_DOMAIN_DISK_DEVICE_LAST);
+STATIC_ASSERT_ENUM(VIR_DOMAIN_DISK_BUS_LAST);
+STATIC_ASSERT_ENUM(VIR_DOMAIN_DISK_MODEL_LAST);
typedef struct _virDomainCapsDeviceDisk virDomainCapsDeviceDisk;
typedef virDomainCapsDeviceDisk *virDomainCapsDeviceDiskPtr;
struct _virDomainCapsDeviceDisk {
@@ -71,6 +80,7 @@ struct _virDomainCapsDeviceDisk {
/* add new fields here */
};
+STATIC_ASSERT_ENUM(VIR_DOMAIN_GRAPHICS_TYPE_LAST);
typedef struct _virDomainCapsDeviceGraphics virDomainCapsDeviceGraphics;
typedef virDomainCapsDeviceGraphics *virDomainCapsDeviceGraphicsPtr;
struct _virDomainCapsDeviceGraphics {
@@ -78,6 +88,7 @@ struct _virDomainCapsDeviceGraphics {
virDomainCapsEnum type; /* virDomainGraphicsType */
};
+STATIC_ASSERT_ENUM(VIR_DOMAIN_VIDEO_TYPE_LAST);
typedef struct _virDomainCapsDeviceVideo virDomainCapsDeviceVideo;
typedef virDomainCapsDeviceVideo *virDomainCapsDeviceVideoPtr;
struct _virDomainCapsDeviceVideo {
@@ -85,6 +96,11 @@ struct _virDomainCapsDeviceVideo {
virDomainCapsEnum modelType; /* virDomainVideoType */
};
+STATIC_ASSERT_ENUM(VIR_DOMAIN_HOSTDEV_MODE_LAST);
+STATIC_ASSERT_ENUM(VIR_DOMAIN_STARTUP_POLICY_LAST);
+STATIC_ASSERT_ENUM(VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST);
+STATIC_ASSERT_ENUM(VIR_DOMAIN_HOSTDEV_CAPS_TYPE_LAST);
+STATIC_ASSERT_ENUM(VIR_DOMAIN_HOSTDEV_PCI_BACKEND_TYPE_LAST);
typedef struct _virDomainCapsDeviceHostdev virDomainCapsDeviceHostdev;
typedef virDomainCapsDeviceHostdev *virDomainCapsDeviceHostdevPtr;
struct _virDomainCapsDeviceHostdev {
@@ -97,6 +113,8 @@ struct _virDomainCapsDeviceHostdev {
/* add new fields here */
};
+STATIC_ASSERT_ENUM(VIR_DOMAIN_RNG_MODEL_LAST);
+STATIC_ASSERT_ENUM(VIR_DOMAIN_RNG_BACKEND_LAST);
typedef struct _virDomainCapsDeviceRNG virDomainCapsDeviceRNG;
typedef virDomainCapsDeviceRNG *virDomainCapsDeviceRNGPtr;
struct _virDomainCapsDeviceRNG {
@@ -105,6 +123,7 @@ struct _virDomainCapsDeviceRNG {
virDomainCapsEnum backendModel; /* virDomainRNGBackend */
};
+STATIC_ASSERT_ENUM(VIR_GIC_VERSION_LAST);
typedef struct _virDomainCapsFeatureGIC virDomainCapsFeatureGIC;
typedef virDomainCapsFeatureGIC *virDomainCapsFeatureGICPtr;
struct _virDomainCapsFeatureGIC {
--
2.33.0

View File

@ -1,48 +0,0 @@
From da99b4e69fab6a14f55873a0b27f962ed6ed5f11 Mon Sep 17 00:00:00 2001
From: Daniel Henrique Barboza <danielhb413@gmail.com>
Date: Mon, 22 Mar 2021 16:28:59 -0300
Subject: [PATCH 091/108] domain_cgroup.c: update domain after setting
blkio.weight
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Commit ac87d3520ad5 consolidated common cgroup code between the QEMU and
lxc drivers in domain_cgroup.c. In this process, in
virDomainCgroupSetupDomainBlkioParameters(), a call to
virCgroupGetBlkioWeight() went missing.
The result is that 'virsh blkiotune' is setting the blkio.weight for the
guest in the host cgroup, but not on the domain XML, because
virCgroupGetBlkioWeight() is also used to write the blkio.weight value
in the domain object.
Fix it by adding the virCgroupGetBlkioWeight() call in the
virDomainCgroupSetupDomainBlkioParameters() helper.
Fixes: ac87d3520ad542d558854a72b0ae0a81fddc6747
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1941407
Reviewed-by: Ján Tomko <jtomko@redhat.com>
Signed-off-by: Daniel Henrique Barboza <danielhb413@gmail.com>
(cherry picked from commit e2602f2bb186da100116a5668d95ca829b7f2767)
---
src/hypervisor/domain_cgroup.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/src/hypervisor/domain_cgroup.c b/src/hypervisor/domain_cgroup.c
index eb4fa20a9e..05e3aa7e6a 100644
--- a/src/hypervisor/domain_cgroup.c
+++ b/src/hypervisor/domain_cgroup.c
@@ -104,7 +104,8 @@ virDomainCgroupSetupDomainBlkioParameters(virCgroupPtr cgroup,
virTypedParameterPtr param = &params[i];
if (STREQ(param->field, VIR_DOMAIN_BLKIO_WEIGHT)) {
- if (virCgroupSetBlkioWeight(cgroup, params[i].value.ui) < 0)
+ if (virCgroupSetBlkioWeight(cgroup, params[i].value.ui) < 0 ||
+ virCgroupGetBlkioWeight(cgroup, &def->blkio.weight) < 0)
ret = -1;
} else if (STREQ(param->field, VIR_DOMAIN_BLKIO_DEVICE_WEIGHT) ||
STREQ(param->field, VIR_DOMAIN_BLKIO_DEVICE_READ_IOPS) ||
--
2.33.0

View File

@ -1,40 +0,0 @@
From 5862d4429c3c3b813b46c32830800df34c6dafe0 Mon Sep 17 00:00:00 2001
From: Pavel Hrdina <phrdina@redhat.com>
Date: Wed, 11 Mar 2020 13:25:59 +0100
Subject: [PATCH 074/108] domain_conf: fix NULL dereference on error in
virDomainObjCopyPersistentDef
The issue was introduced together with the function itself by commit
<da1eba6bc8f58bfce34136710d1979a3a44adb17>. Calling
`virDomainObjGetPersistentDef` may return NULL which is later passed
to `virDomainDefFormat` where the `def` attribute is marked as NONNULL
and later in `virDomainDefFormatInternalSetRootName` it is actually
defererenced without any other check.
Signed-off-by: Pavel Hrdina <phrdina@redhat.com>
Reviewed-by: Peter Krempa <pkrempa@redhat.com>
(cherry picked from commit b96174d9f2dcf0197bb6e58eea3fbbda17043478)
---
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 9c83f4e347..b60b9d31a1 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -30074,6 +30074,12 @@ virDomainObjCopyPersistentDef(virDomainObjPtr dom,
virDomainDefPtr cur;
cur = virDomainObjGetPersistentDef(xmlopt, dom, parseOpaque);
+ if (!cur) {
+ virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+ _("failed to get persistent definition object"));
+ return NULL;
+ }
+
return virDomainDefCopy(cur, xmlopt, parseOpaque, false);
}
--
2.33.0

View File

@ -1,65 +0,0 @@
From fbb537ad89c6820e8763a57722cebc5a3db363e0 Mon Sep 17 00:00:00 2001
From: Daniel Henrique Barboza <danielhb413@gmail.com>
Date: Thu, 19 Nov 2020 13:57:43 -0300
Subject: [PATCH 067/108] domain_conf.c: do not leak 'video' in
virDomainDefParseXML()
The 'video' pointer is only being freed on error path, meaning
that we're leaking it after each loop restart.
There are more opportunities for auto cleanups of virDomainVideoDef
pointers, so let's register AUTOPTR_CLEANUP_FUNC for it to use
g_autoptr() later on.
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
Signed-off-by: Daniel Henrique Barboza <danielhb413@gmail.com>
(cherry picked from commit 18d29844c616fb633f7042dbe4cf80819cdd2f1d)
---
src/conf/domain_conf.c | 4 +---
src/conf/domain_conf.h | 1 +
2 files changed, 2 insertions(+), 3 deletions(-)
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index d3565ececf..a33f9144f5 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -21631,7 +21631,7 @@ virDomainDefParseXML(xmlDocPtr xml,
if (n && VIR_ALLOC_N(def->videos, n) < 0)
goto error;
for (i = 0; i < n; i++) {
- virDomainVideoDefPtr video;
+ g_autoptr(virDomainVideoDef) video = NULL;
ssize_t insertAt = -1;
if (!(video = virDomainVideoDefParseXML(xmlopt, nodes[i],
@@ -21640,7 +21640,6 @@ virDomainDefParseXML(xmlDocPtr xml,
if (video->primary) {
if (def->nvideos != 0 && def->videos[0]->primary) {
- virDomainVideoDefFree(video);
virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
_("Only one primary video device is supported"));
goto error;
@@ -21652,7 +21651,6 @@ virDomainDefParseXML(xmlDocPtr xml,
insertAt,
def->nvideos,
video) < 0) {
- virDomainVideoDefFree(video);
goto error;
}
}
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
index e057c384c6..15b9e79d69 100644
--- a/src/conf/domain_conf.h
+++ b/src/conf/domain_conf.h
@@ -2938,6 +2938,7 @@ void virDomainNVRAMDefFree(virDomainNVRAMDefPtr def);
void virDomainWatchdogDefFree(virDomainWatchdogDefPtr def);
virDomainVideoDefPtr virDomainVideoDefNew(virDomainXMLOptionPtr xmlopt);
void virDomainVideoDefFree(virDomainVideoDefPtr def);
+G_DEFINE_AUTOPTR_CLEANUP_FUNC(virDomainVideoDef, virDomainVideoDefFree);
void virDomainVideoDefClear(virDomainVideoDefPtr def);
virDomainHostdevDefPtr virDomainHostdevDefNew(void);
void virDomainHostdevDefClear(virDomainHostdevDefPtr def);
--
2.33.0

View File

@ -1,125 +0,0 @@
From 04c5fee85547da11323b66b2fb79fb590e8307a1 Mon Sep 17 00:00:00 2001
From: jiangdawei15 <jiangdawei15@huawei.com>
Date: Thu, 18 Aug 2022 20:15:54 +0800
Subject: [PATCH 22/22] enum: Add helpers for converting virTristate* to a
plain bool
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
The helpers will update the passed boolean if the tristate's value is
not _ABSENT.
Signed-off-by: Peter Krempa <pkrempa@redhat.com>
Reviewed-by: Ján Tomko <jtomko@redhat.com>
---
src/libvirt_private.syms | 2 ++
src/util/virenum.c | 54 ++++++++++++++++++++++++++++++++++++++++
src/util/virenum.h | 2 ++
3 files changed, 58 insertions(+)
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
index f30eb7ffb5..a00e354859 100644
--- a/src/libvirt_private.syms
+++ b/src/libvirt_private.syms
@@ -1965,9 +1965,11 @@ ebtablesRemoveForwardAllowIn;
virEnumFromString;
virEnumToString;
virTristateBoolFromBool;
+virTristateBoolToBool;
virTristateBoolTypeFromString;
virTristateBoolTypeToString;
virTristateSwitchFromBool;
+virTristateSwitchToBool;
virTristateSwitchTypeFromString;
virTristateSwitchTypeToString;
diff --git a/src/util/virenum.c b/src/util/virenum.c
index 26093bd795..dfedc28ba7 100644
--- a/src/util/virenum.c
+++ b/src/util/virenum.c
@@ -47,6 +47,33 @@ virTristateBoolFromBool(bool val)
}
+/**
+ * virTristateBoolToBool: The value pointed to by @b is
+ * updated if the tristate value @t is not absent.
+ *
+ * @t: a virTristateBool value
+ * @b: pointer to a boolean to be updated according to the value of @t
+ */
+void
+virTristateBoolToBool(virTristateBool t,
+ bool *b)
+{
+ switch (t) {
+ case VIR_TRISTATE_BOOL_YES:
+ *b = true;
+ break;
+
+ case VIR_TRISTATE_BOOL_NO:
+ *b = false;
+ break;
+
+ case VIR_TRISTATE_BOOL_ABSENT:
+ case VIR_TRISTATE_BOOL_LAST:
+ break;
+ }
+}
+
+
virTristateSwitch
virTristateSwitchFromBool(bool val)
{
@@ -57,6 +84,33 @@ virTristateSwitchFromBool(bool val)
}
+/**
+ * virTristateSwitchToBool: The value pointed to by @b
+ * is updated if the tristate value @t is not absent.
+ *
+ * @t: a virTristateSwitch value
+ * @b: pointer to a boolean to be updated according to the value of @t
+ */
+void
+virTristateSwitchToBool(virTristateSwitch t,
+ bool *b)
+{
+ switch (t) {
+ case VIR_TRISTATE_SWITCH_ON:
+ *b = true;
+ break;
+
+ case VIR_TRISTATE_SWITCH_OFF:
+ *b = false;
+ break;
+
+ case VIR_TRISTATE_SWITCH_ABSENT:
+ case VIR_TRISTATE_SWITCH_LAST:
+ break;
+ }
+}
+
+
int
virEnumFromString(const char * const *types,
unsigned int ntypes,
diff --git a/src/util/virenum.h b/src/util/virenum.h
index d74af35530..98f01d574d 100644
--- a/src/util/virenum.h
+++ b/src/util/virenum.h
@@ -68,7 +68,9 @@ VIR_ENUM_DECL(virTristateBool);
VIR_ENUM_DECL(virTristateSwitch);
virTristateBool virTristateBoolFromBool(bool val);
+void virTristateBoolToBool(virTristateBool t, bool *b);
virTristateSwitch virTristateSwitchFromBool(bool val);
+void virTristateSwitchToBool(virTristateSwitch t, bool *b);
/* the two enums must be in sync to be able to use helpers interchangeably in
* some special cases */
--
2.33.0

View File

@ -1,42 +0,0 @@
From 9b80543fb6ebccf64d0bcbe91a2e97873886164c Mon Sep 17 00:00:00 2001
From: tangbinzy <tangbin_yewu@cmss.chinamobile.com>
Date: Thu, 16 Mar 2023 07:03:51 +0000
Subject: [PATCH] esx: call freeaddrinfo earlier in esxUtil_ResolveHostname
Call freeaddrinfo() as soon as @result is not needed anymore, i.e. right
after getnameinfo(); this avoids calling freeaddrinfo() in two branches.
Signed-off-by: Pino Toscano <ptoscano@redhat.com>
Reviewed-by: Laine Stump <laine@redhat.com>
Signed-off-by: tangbin <tangbin_yewu@cmss.chinamobile.com>
(cherry-pick from 3aaf23ff69cea9abb7b7a43d9ff3eb687a916a2e)
---
src/esx/esx_util.c | 4 +---
1 file changed, 1 insertion(+), 3 deletions(-)
diff --git a/src/esx/esx_util.c b/src/esx/esx_util.c
index 89d136248f..98ce462ff0 100644
--- a/src/esx/esx_util.c
+++ b/src/esx/esx_util.c
@@ -311,17 +311,15 @@ esxUtil_ResolveHostname(const char *hostname,
errcode = getnameinfo(result->ai_addr, result->ai_addrlen, ipAddress,
ipAddress_length, NULL, 0, NI_NUMERICHOST);
+ freeaddrinfo(result);
if (errcode != 0) {
virReportError(VIR_ERR_INTERNAL_ERROR,
_("Formatting IP address for host '%s' failed: %s"), hostname,
gai_strerror(errcode));
- freeaddrinfo(result);
return -1;
}
- freeaddrinfo(result);
-
return 0;
}
--
2.27.0

View File

@ -1,41 +0,0 @@
From 7a13a72308b5ad5887497e13995522ab151e6293 Mon Sep 17 00:00:00 2001
From: wangmeiyang <wangmeiyang_yewu@cmss.chinamobile.com>
Date: Wed, 30 Nov 2022 19:47:10 +0800
Subject: [PATCH 20/24] examples: hellolibvirt: fix argc check
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
https://gitlab.com/libvirt/libvirt/-/issues/255
cherry-pick from dacf616b788a989ecaa1679845a07ff8010372cf
Reported-by: Jeremy Alcim
Signed-off-by: Ján Tomko <jtomko@redhat.com>
Signed-off-by: Meiyang Wang <wangmeiyang_yewu@cmss.chinamobile.com>
---
examples/c/misc/hellolibvirt.c | 5 +++--
1 file changed, 3 insertions(+), 2 deletions(-)
diff --git a/examples/c/misc/hellolibvirt.c b/examples/c/misc/hellolibvirt.c
index a598e01be2..39cefe934c 100644
--- a/examples/c/misc/hellolibvirt.c
+++ b/examples/c/misc/hellolibvirt.c
@@ -107,11 +107,12 @@ main(int argc, char *argv[])
{
int ret = 0;
virConnectPtr conn;
- char *uri;
+ char *uri = NULL;
printf("Attempting to connect to hypervisor\n");
- uri = (argc > 0 ? argv[1] : NULL);
+ if (argc > 1)
+ uri = argv[1];
/* virConnectOpenAuth is called here with all default parameters,
* except, possibly, the URI of the hypervisor. */
--
2.27.0

View File

@ -1,32 +0,0 @@
From 56dc1a61719f5133b30676afe71c4d1482c84476 Mon Sep 17 00:00:00 2001
From: Zhenyu Ye <yezhenyu2@huawei.com>
Date: Thu, 19 Aug 2021 20:14:11 +0800
Subject: [PATCH] fix error in printf format string
Use %s to print NULLSTR(duri).
Reported-by: Peng Liang <liangpeng10@huawei.com>
Signed-off-by: Zhenyu Ye <yezhenyu2@huawei.com>
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
Signed-off-by: zhujun2 <zhujun2_yewu@cmss.chinamobile.com>
(cherry-pick from 94ac9d55fd9067326c483372c858bb4233826880)
---
src/libvirt-domain.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/src/libvirt-domain.c b/src/libvirt-domain.c
index 6ce4a6715c..8f6ff2fe22 100644
--- a/src/libvirt-domain.c
+++ b/src/libvirt-domain.c
@@ -4086,7 +4086,7 @@ virDomainMigrateToURI(virDomainPtr domain,
const char *dconnuri = NULL;
const char *miguri = NULL;
- VIR_DOMAIN_DEBUG(domain, "duri=%p, flags=0x%lx, dname=%s, bandwidth=%lu",
+ VIR_DOMAIN_DEBUG(domain, "duri=%s, flags=0x%lx, dname=%s, bandwidth=%lu",
NULLSTR(duri), flags, NULLSTR(dname), bandwidth);
virResetLastError();
--
2.41.0.windows.1

View File

@ -1,24 +0,0 @@
From d5c1bd627d522b16eb87e2684a912c16ce79c12b Mon Sep 17 00:00:00 2001
From: lifeng 71117973 <lif121@chinatelecom.cn>
Date: Mon, 15 May 2023 15:39:32 +0800
Subject: [PATCH] fix the issue of errors when saving after 'virsh edit'
---
docs/schemas/basictypes.rng | 1 +
1 file changed, 1 insertion(+)
diff --git a/docs/schemas/basictypes.rng b/docs/schemas/basictypes.rng
index 34d285db48..8b430e71a6 100644
--- a/docs/schemas/basictypes.rng
+++ b/docs/schemas/basictypes.rng
@@ -440,6 +440,7 @@
<value>sh4eb</value>
<value>sparc</value>
<value>sparc64</value>
+ <value>sw_64</value>
<value>unicore32</value>
<value>x86_64</value>
<value>xtensa</value>
--
2.27.0

View File

@ -1,70 +0,0 @@
From 1ac928729853d29d030944ece5e10db69d54267d Mon Sep 17 00:00:00 2001
From: mayunlong <mayunlong6@huawei.com>
Date: Tue, 14 Feb 2023 19:09:08 +0800
Subject: [PATCH] glibcompat: Provide implementation for G_GNUC_NO_INLINE
Currently, we require glib-2.56.0 at minimum (because of RHEL-8)
but we use G_GNUC_NO_INLINE which was introduced in 2.58.0. While
we provide an implementation for older versions, where the macro
does not exists, it's a bit more tricky than that. Since we
define GLIB_VERSION_MAX_ALLOWED we would get a compile time error
when trying to use something too new, except for G_GNUC_NO_INLINE
which was intentionally not marked as
GLIB_AVAILABLE_MACRO_IN_2_58. But this is about to change with
glib-2.73.2 (which contains commit [1]).
At the same time, we can't just bump glib and thus we have to
provide an alternative implementation without the version
annotation.
1: https://gitlab.gnome.org/GNOME/glib/-/commit/a6f8fe071e44b0145619c21f3bfbc90c56ab805e
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
Reviewed-by: Pavel Hrdina <phrdina@redhat.com>
---
src/internal.h | 12 ------------
src/util/glibcompat.h | 9 +++++++++
2 files changed, 9 insertions(+), 12 deletions(-)
diff --git a/src/internal.h b/src/internal.h
index 302fddba34..440f01d370 100644
--- a/src/internal.h
+++ b/src/internal.h
@@ -94,18 +94,6 @@
# endif
#endif
-/**
- * G_GNUC_NO_INLINE:
- *
- * Force compiler not to inline a method. Should be used if
- * the method need to be overridable by test mocks.
- *
- * TODO: Remove after upgrading to GLib >= 2.58
- */
-#ifndef G_GNUC_NO_INLINE
-# define G_GNUC_NO_INLINE __attribute__((__noinline__))
-#endif
-
/**
* ATTRIBUTE_PACKED
*
diff --git a/src/util/glibcompat.h b/src/util/glibcompat.h
index 6f50a76f3c..15d3266686 100644
--- a/src/util/glibcompat.h
+++ b/src/util/glibcompat.h
@@ -37,3 +37,12 @@ char *vir_g_strdup_vprintf(const char *msg, va_list args)
#define g_canonicalize_filename vir_g_canonicalize_filename
#undef g_fsync
#define g_fsync vir_g_fsync
+
+/* Intentionally redefine macro so that it's not marked as available in 2.58
+ * and newer. Drop when bumping to 2.58 or newer. */
+#undef G_GNUC_NO_INLINE
+#if g_macro__has_attribute(__noinline__)
+# define G_GNUC_NO_INLINE __attribute__ ((__noinline__))
+#else
+# define G_GNUC_NO_INLINE
+#endif
--
2.25.1

View File

@ -1,45 +0,0 @@
From 24ae6a276d538a31f42feb5e988d15b08b444b4a Mon Sep 17 00:00:00 2001
From: Erik Skultety <eskultet@redhat.com>
Date: Thu, 7 Jan 2021 16:48:40 +0100
Subject: [PATCH 078/108] hostdev: Update mdev pointer reference after checking
device type
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
We set the pointer to some garbage packed structure data without
knowing whether we were actually handling the type of device we
expected to be handling. On its own, this was harmless, because we'd
never use the pointer as we'd skip the device if it were not the
expected type. However, it's better to make the logic even more
explicit - we first check the device and only when we're sure we have
the expected type we then update the pointer shortcut.
Signed-off-by: Erik Skultety <eskultet@redhat.com>
Reviewed-by: Ján Tomko <jtomko@redhat.com>
(cherry picked from commit 964738cff3d949d90fc5c3317a2618fcd8d217b4)
---
src/hypervisor/virhostdev.c | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/src/hypervisor/virhostdev.c b/src/hypervisor/virhostdev.c
index 9017cc3be8..c88c8bee0e 100644
--- a/src/hypervisor/virhostdev.c
+++ b/src/hypervisor/virhostdev.c
@@ -1986,11 +1986,11 @@ virHostdevReAttachMediatedDevices(virHostdevManagerPtr mgr,
virDomainHostdevSubsysMediatedDevPtr mdevsrc;
virDomainHostdevDefPtr hostdev = hostdevs[i];
- mdevsrc = &hostdev->source.subsys.u.mdev;
-
if (!virHostdevIsMdevDevice(hostdev))
continue;
+ mdevsrc = &hostdev->source.subsys.u.mdev;
+
if (!(mdev = virMediatedDeviceNew(mdevsrc->uuidstr,
mdevsrc->model)))
continue;
--
2.33.0

View File

@ -1,161 +0,0 @@
From 7b752336bd26048514d55bb222531c0b0183fa9c Mon Sep 17 00:00:00 2001
From: Erik Skultety <eskultet@redhat.com>
Date: Thu, 7 Jan 2021 16:53:21 +0100
Subject: [PATCH 079/108] hostdev: mdev: Lookup mdevs by sysfs path rather than
mdev struct
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
The lookup didn't do anything apart from comparing the sysfs paths
anyway since that's what makes each mdev unique.
The most ridiculous usage of the old logic was in
virHostdevReAttachMediatedDevices where in order to drop an mdev
hostdev from the list of active devices we first had to create a new
mdev and use it in the lookup call. Why couldn't we have used the
hostdev directly? Because the hostdev and mdev structures are
incompatible.
The way mdevs are currently removed is via a write to a specific sysfs
attribute. If you do it while the machine which has the mdev assigned
is running, the write call may block (with a new enough kernel, with
older kernels it would return a write error!) until the device
is no longer in use which is when the QEMU process exits.
The interesting part here comes afterwards when we're cleaning up and
call virHostdevReAttachMediatedDevices. The domain doesn't exist
anymore, so the list of active hostdevs needs to be updated and the
respective hostdevs removed from the list, but remember we had to
create an mdev object in the memory in order to find it in the list
first which will fail because the write to sysfs had already removed
the mdev instance from the host system.
And so the next time you try to start the same domain you'll get:
"Requested operation is not valid: mediated device <path> is in use by
driver QEMU, domain <name>"
Fixes: https://gitlab.com/libvirt/libvirt/-/issues/119
Signed-off-by: Erik Skultety <eskultet@redhat.com>
Reviewed-by: Ján Tomko <jtomko@redhat.com>
(cherry picked from commit 49cb59778a4e6c2d04bb9383a9d97fbbc83f9fce)
---
src/hypervisor/virhostdev.c | 10 ++++------
src/util/virmdev.c | 16 ++++++++--------
src/util/virmdev.h | 4 ++--
3 files changed, 14 insertions(+), 16 deletions(-)
diff --git a/src/hypervisor/virhostdev.c b/src/hypervisor/virhostdev.c
index c88c8bee0e..4057f7b25f 100644
--- a/src/hypervisor/virhostdev.c
+++ b/src/hypervisor/virhostdev.c
@@ -1981,7 +1981,7 @@ virHostdevReAttachMediatedDevices(virHostdevManagerPtr mgr,
virObjectLock(mgr->activeMediatedHostdevs);
for (i = 0; i < nhostdevs; i++) {
- g_autoptr(virMediatedDevice) mdev = NULL;
+ g_autofree char *sysfspath = NULL;
virMediatedDevicePtr tmp;
virDomainHostdevSubsysMediatedDevPtr mdevsrc;
virDomainHostdevDefPtr hostdev = hostdevs[i];
@@ -1990,14 +1990,12 @@ virHostdevReAttachMediatedDevices(virHostdevManagerPtr mgr,
continue;
mdevsrc = &hostdev->source.subsys.u.mdev;
-
- if (!(mdev = virMediatedDeviceNew(mdevsrc->uuidstr,
- mdevsrc->model)))
- continue;
+ sysfspath = virMediatedDeviceGetSysfsPath(mdevsrc->uuidstr);
/* Remove from the list only mdevs assigned to @drv_name/@dom_name */
- tmp = virMediatedDeviceListFind(mgr->activeMediatedHostdevs, mdev);
+ tmp = virMediatedDeviceListFind(mgr->activeMediatedHostdevs,
+ sysfspath);
/* skip inactive devices */
if (!tmp)
diff --git a/src/util/virmdev.c b/src/util/virmdev.c
index c2499c0a20..bae4a7d2c1 100644
--- a/src/util/virmdev.c
+++ b/src/util/virmdev.c
@@ -312,7 +312,7 @@ int
virMediatedDeviceListAdd(virMediatedDeviceListPtr list,
virMediatedDevicePtr *dev)
{
- if (virMediatedDeviceListFind(list, *dev)) {
+ if (virMediatedDeviceListFind(list, (*dev)->path)) {
virReportError(VIR_ERR_INTERNAL_ERROR,
_("device %s is already in use"), (*dev)->path);
return -1;
@@ -358,7 +358,7 @@ virMediatedDevicePtr
virMediatedDeviceListSteal(virMediatedDeviceListPtr list,
virMediatedDevicePtr dev)
{
- int idx = virMediatedDeviceListFindIndex(list, dev);
+ int idx = virMediatedDeviceListFindIndex(list, dev->path);
return virMediatedDeviceListStealIndex(list, idx);
}
@@ -374,13 +374,13 @@ virMediatedDeviceListDel(virMediatedDeviceListPtr list,
int
virMediatedDeviceListFindIndex(virMediatedDeviceListPtr list,
- virMediatedDevicePtr dev)
+ const char *sysfspath)
{
size_t i;
for (i = 0; i < list->count; i++) {
- virMediatedDevicePtr other = list->devs[i];
- if (STREQ(other->path, dev->path))
+ virMediatedDevicePtr dev = list->devs[i];
+ if (STREQ(sysfspath, dev->path))
return i;
}
return -1;
@@ -389,11 +389,11 @@ virMediatedDeviceListFindIndex(virMediatedDeviceListPtr list,
virMediatedDevicePtr
virMediatedDeviceListFind(virMediatedDeviceListPtr list,
- virMediatedDevicePtr dev)
+ const char *sysfspath)
{
int idx;
- if ((idx = virMediatedDeviceListFindIndex(list, dev)) >= 0)
+ if ((idx = virMediatedDeviceListFindIndex(list, sysfspath)) >= 0)
return list->devs[idx];
else
return NULL;
@@ -407,7 +407,7 @@ virMediatedDeviceIsUsed(virMediatedDevicePtr dev,
const char *drvname, *domname;
virMediatedDevicePtr tmp = NULL;
- if ((tmp = virMediatedDeviceListFind(list, dev))) {
+ if ((tmp = virMediatedDeviceListFind(list, dev->path))) {
virMediatedDeviceGetUsedBy(tmp, &drvname, &domname);
virReportError(VIR_ERR_OPERATION_INVALID,
_("mediated device %s is in use by "
diff --git a/src/util/virmdev.h b/src/util/virmdev.h
index 51f7f608a2..1d97f7d44f 100644
--- a/src/util/virmdev.h
+++ b/src/util/virmdev.h
@@ -119,11 +119,11 @@ virMediatedDeviceListDel(virMediatedDeviceListPtr list,
virMediatedDevicePtr
virMediatedDeviceListFind(virMediatedDeviceListPtr list,
- virMediatedDevicePtr dev);
+ const char *sysfspath);
int
virMediatedDeviceListFindIndex(virMediatedDeviceListPtr list,
- virMediatedDevicePtr dev);
+ const char *sysfspath);
int
virMediatedDeviceListMarkDevices(virMediatedDeviceListPtr dst,
--
2.33.0

View File

@ -1,336 +0,0 @@
From b255a024007eb236745b703586a2fed8bdedae6c Mon Sep 17 00:00:00 2001
From: AlexChen <alex.chen@huawei.com>
Date: Tue, 19 Oct 2021 22:11:45 +0800
Subject: [PATCH] hotpatch: Implement qemuDomainHotpatchManage
Signed-off-by: Hao Wang <wanghao232@huawei.com>
Signed-off-by: Bihong Yu <yubihong@huawei.com>
Signed-off-by: AlexChen <alex.chen@huawei.com>
---
src/qemu/Makefile.inc.am | 2 +
src/qemu/qemu_driver.c | 48 +++++++++++
src/qemu/qemu_hotpatch.c | 182 +++++++++++++++++++++++++++++++++++++++
src/qemu/qemu_hotpatch.h | 36 ++++++++
4 files changed, 268 insertions(+)
create mode 100644 src/qemu/qemu_hotpatch.c
create mode 100644 src/qemu/qemu_hotpatch.h
diff --git a/src/qemu/Makefile.inc.am b/src/qemu/Makefile.inc.am
index 51cd79879d..a1a8bfa17c 100644
--- a/src/qemu/Makefile.inc.am
+++ b/src/qemu/Makefile.inc.am
@@ -73,6 +73,8 @@ QEMU_DRIVER_SOURCES = \
qemu/qemu_checkpoint.h \
qemu/qemu_backup.c \
qemu/qemu_backup.h \
+ qemu/qemu_hotpatch.c \
+ qemu/qemu_hotpatch.h \
$(NULL)
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index 5901f922bf..f6d99957a5 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -50,6 +50,7 @@
#include "qemu_security.h"
#include "qemu_checkpoint.h"
#include "qemu_backup.h"
+#include "qemu_hotpatch.h"
#include "virerror.h"
#include "virlog.h"
@@ -23171,6 +23172,52 @@ qemuDomainAgentSetResponseTimeout(virDomainPtr dom,
return ret;
}
+static char *
+qemuDomainHotpatchManage(virDomainPtr domain,
+ int action,
+ const char *patch,
+ const char *id,
+ unsigned int flags)
+{
+ virDomainObjPtr vm;
+ char *ret = NULL;
+ size_t len;
+
+ virCheckFlags(0, NULL);
+
+ if (!(vm = qemuDomainObjFromDomain(domain)))
+ goto cleanup;
+
+ switch (action) {
+ case VIR_DOMAIN_HOTPATCH_APPLY:
+ ret = qemuDomainHotpatchApply(vm, patch);
+ break;
+
+ case VIR_DOMAIN_HOTPATCH_UNAPPLY:
+ ret = qemuDomainHotpatchUnapply(vm, id);
+ break;
+
+ case VIR_DOMAIN_HOTPATCH_QUERY:
+ ret = qemuDomainHotpatchQuery(vm);
+ break;
+
+ default:
+ virReportError(VIR_ERR_OPERATION_INVALID, "%s",
+ _("Unknow hotpatch action"));
+ }
+
+ if (!ret)
+ goto endjob;
+
+ /* Wipeout redundant empty line */
+ len = strlen(ret);
+ if (len > 0)
+ ret[len - 1] = '\0';
+
+ cleanup:
+ virDomainObjEndAPI(&vm);
+ return ret;
+}
static virHypervisorDriver qemuHypervisorDriver = {
.name = QEMU_DRIVER_NAME,
@@ -23411,6 +23458,7 @@ static virHypervisorDriver qemuHypervisorDriver = {
.domainAgentSetResponseTimeout = qemuDomainAgentSetResponseTimeout, /* 5.10.0 */
.domainBackupBegin = qemuDomainBackupBegin, /* 6.0.0 */
.domainBackupGetXMLDesc = qemuDomainBackupGetXMLDesc, /* 6.0.0 */
+ .domainHotpatchManage = qemuDomainHotpatchManage, /* 6.2.0 */
};
diff --git a/src/qemu/qemu_hotpatch.c b/src/qemu/qemu_hotpatch.c
new file mode 100644
index 0000000000..45796b3f24
--- /dev/null
+++ b/src/qemu/qemu_hotpatch.c
@@ -0,0 +1,182 @@
+/*
+ * huawei_qemu_hotpatch.h: huawei qemu hotpatch functions
+ *
+ * Copyright (C) 2021-2021 HUAWEI, 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/>.
+ *
+ */
+
+
+#include <unistd.h>
+#include "viralloc.h"
+#include "virerror.h"
+#include "virfile.h"
+#include "virlog.h"
+#include "vircommand.h"
+#include "qemu/qemu_domain.h"
+#include "qemu_hotpatch.h"
+
+#define LIBCARE_CTL "libcare-ctl"
+#define LIBCARE_ERROR_NUMBER 255
+#define MAX_PATCHID_LEN 8
+
+#define VIR_FROM_THIS VIR_FROM_QEMU
+
+VIR_LOG_INIT("qemu_hotpatch");
+
+char *
+qemuDomainHotpatchQuery(virDomainObjPtr vm)
+{
+ g_autoptr(virCommand) cmd = NULL;
+ g_autofree char *binary = NULL;
+ char *output = NULL;
+ int ret = -1;
+
+ if (!(binary = virFindFileInPath(LIBCARE_CTL))) {
+ virReportError(VIR_ERR_OPERATION_FAILED, "%s",
+ _("Failed to find libcare-ctl command."));
+ return NULL;
+ }
+
+ cmd = virCommandNewArgList(binary, "info", "-p", NULL);
+ virCommandAddArgFormat(cmd, "%d", vm->pid);
+ virCommandSetOutputBuffer(cmd, &output);
+
+ VIR_DEBUG("Querying hotpatch for domain %s. (%s info -p %d)",
+ vm->def->name, binary, vm->pid);
+
+ if (virCommandRun(cmd, &ret) < 0)
+ goto error;
+
+ if (ret == LIBCARE_ERROR_NUMBER) {
+ virReportError(VIR_ERR_OPERATION_FAILED, "%s",
+ _("Failed to execute libcare-ctl command."));
+ goto error;
+ }
+ return output;
+
+ error:
+ VIR_FREE(output);
+ return NULL;
+}
+
+char *
+qemuDomainHotpatchApply(virDomainObjPtr vm,
+ const char *patch)
+{
+ g_autoptr(virCommand) cmd = NULL;
+ g_autofree char *binary = NULL;
+ char *output = NULL;
+ int ret = -1;
+
+ if (!patch || !virFileExists(patch)) {
+ virReportError(VIR_ERR_INVALID_ARG,
+ "%s", _("Invalid hotpatch file."));
+ return NULL;
+ }
+
+ if (!(binary = virFindFileInPath(LIBCARE_CTL))) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ "%s", _("Failed to find libcare-ctl command."));
+ return NULL;
+ }
+
+ cmd = virCommandNewArgList(binary, "patch", "-p", NULL);
+ virCommandAddArgFormat(cmd, "%d", vm->pid);
+ virCommandAddArgList(cmd, patch, NULL);
+ virCommandSetOutputBuffer(cmd, &output);
+
+ VIR_DEBUG("Applying hotpatch for domain %s. (%s patch -p %d %s)",
+ vm->def->name, binary, vm->pid, patch);
+
+ if (virCommandRun(cmd, &ret) < 0)
+ goto error;
+
+ if (ret == LIBCARE_ERROR_NUMBER) {
+ virReportError(VIR_ERR_OPERATION_FAILED, "%s",
+ _("Failed to execute libcare-ctl command."));
+ goto error;
+ }
+ return output;
+
+ error:
+ VIR_FREE(output);
+ return NULL;
+}
+
+static bool
+qemuDomainHotpatchIsPatchidValid(const char *id)
+{
+ size_t len, i;
+
+ if (!id)
+ return false;
+
+ len = strlen(id);
+ if (len > MAX_PATCHID_LEN - 1)
+ return false;
+
+ for (i = 0; i < len; i++) {
+ if (!g_ascii_isalnum(*(id + i)))
+ return false;
+ }
+
+ return true;
+}
+
+char *
+qemuDomainHotpatchUnapply(virDomainObjPtr vm,
+ const char *id)
+{
+ g_autoptr(virCommand) cmd = NULL;
+ g_autofree char *binary = NULL;
+ char *output = NULL;
+ int ret = -1;
+
+ if (!id || !qemuDomainHotpatchIsPatchidValid(id)) {
+ virReportError(VIR_ERR_INVALID_ARG,
+ "%s", _("Invalid hotpatch id."));
+ return NULL;
+ }
+
+ if (!(binary = virFindFileInPath(LIBCARE_CTL))) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ "%s", _("Failed to find libcare-ctl command."));
+ return NULL;
+ }
+
+ cmd = virCommandNewArgList(binary, "unpatch", "-p", NULL);
+ virCommandAddArgFormat(cmd, "%d", vm->pid);
+ virCommandAddArgList(cmd, "-i", id, NULL);
+ virCommandSetOutputBuffer(cmd, &output);
+
+ VIR_DEBUG("Unapplying hotpatch for domain %s. (%s unpatch -p %d -i %s)",
+ vm->def->name, binary, vm->pid, id);
+
+ if (virCommandRun(cmd, &ret) < 0)
+ goto error;
+
+ if (ret == LIBCARE_ERROR_NUMBER) {
+ virReportError(VIR_ERR_OPERATION_FAILED, "%s",
+ _("Failed to execute libcare-ctl command."));
+ goto error;
+ }
+ return output;
+
+ error:
+ VIR_FREE(output);
+ return NULL;
+}
diff --git a/src/qemu/qemu_hotpatch.h b/src/qemu/qemu_hotpatch.h
new file mode 100644
index 0000000000..4c84a57950
--- /dev/null
+++ b/src/qemu/qemu_hotpatch.h
@@ -0,0 +1,36 @@
+/*
+ * huawei_qemu_hotpatch.h: huawei qemu hotpatch functions
+ *
+ * Copyright (C) 2021-2021 HUAWEI, 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/>.
+ *
+ */
+
+#pragma once
+
+#include <unistd.h>
+#include "qemu/qemu_conf.h"
+
+char *
+qemuDomainHotpatchQuery(virDomainObjPtr vm);
+
+char *
+qemuDomainHotpatchApply(virDomainObjPtr vm,
+ const char *patch);
+
+char *
+qemuDomainHotpatchUnapply(virDomainObjPtr vm,
+ const char *id);
--
2.27.0

View File

@ -1,135 +0,0 @@
From 58121fbc3085296364e6b90bc16cb56eeaf36f77 Mon Sep 17 00:00:00 2001
From: AlexChen <alex.chen@huawei.com>
Date: Fri, 9 Jul 2021 10:50:07 +0800
Subject: [PATCH] hotpatch: check vm id and pid before using hotpatch api
Check if the vm is alive before using hotpatch api by calling
virDomainObjCheckActive() to check vm id and calling
qemuDomainHotpatchCheckPid() to check vm pid.
Signed-off-by: Bihong Yu <yubihong@huawei.com>
Signed-off-by: AlexChen <alex.chen@huawei.com>
---
src/qemu/qemu_driver.c | 3 +++
src/qemu/qemu_hotpatch.c | 36 ++++++++++++++++++++++++++++++------
2 files changed, 33 insertions(+), 6 deletions(-)
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index d4c5f073bb..2b24881f75 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -23196,6 +23196,9 @@ qemuDomainHotpatchManage(virDomainPtr domain,
VIR_DOMAIN_JOB_OPERATION_HOTPATCH, 0) < 0)
goto cleanup;
+ if (virDomainObjCheckActive(vm) < 0)
+ goto endjob;
+
qemuDomainObjSetAsyncJobMask(vm, QEMU_JOB_DEFAULT_MASK);
switch (action) {
diff --git a/src/qemu/qemu_hotpatch.c b/src/qemu/qemu_hotpatch.c
index 45796b3f24..03e63c1341 100644
--- a/src/qemu/qemu_hotpatch.c
+++ b/src/qemu/qemu_hotpatch.c
@@ -37,12 +37,25 @@
VIR_LOG_INIT("qemu_hotpatch");
+static int
+qemuDomainHotpatchCheckPid(pid_t pid)
+{
+ if (pid <= 0) {
+ virReportError(VIR_ERR_INVALID_ARG,
+ "%s", _("Invalid pid"));
+ return -1;
+ }
+
+ return 0;
+}
+
char *
qemuDomainHotpatchQuery(virDomainObjPtr vm)
{
g_autoptr(virCommand) cmd = NULL;
g_autofree char *binary = NULL;
char *output = NULL;
+ pid_t pid = vm->pid;
int ret = -1;
if (!(binary = virFindFileInPath(LIBCARE_CTL))) {
@@ -51,12 +64,15 @@ qemuDomainHotpatchQuery(virDomainObjPtr vm)
return NULL;
}
+ if (qemuDomainHotpatchCheckPid(pid) < 0)
+ return NULL;
+
cmd = virCommandNewArgList(binary, "info", "-p", NULL);
- virCommandAddArgFormat(cmd, "%d", vm->pid);
+ virCommandAddArgFormat(cmd, "%d", pid);
virCommandSetOutputBuffer(cmd, &output);
VIR_DEBUG("Querying hotpatch for domain %s. (%s info -p %d)",
- vm->def->name, binary, vm->pid);
+ vm->def->name, binary, pid);
if (virCommandRun(cmd, &ret) < 0)
goto error;
@@ -80,6 +96,7 @@ qemuDomainHotpatchApply(virDomainObjPtr vm,
g_autoptr(virCommand) cmd = NULL;
g_autofree char *binary = NULL;
char *output = NULL;
+ pid_t pid = vm->pid;
int ret = -1;
if (!patch || !virFileExists(patch)) {
@@ -94,13 +111,16 @@ qemuDomainHotpatchApply(virDomainObjPtr vm,
return NULL;
}
+ if (qemuDomainHotpatchCheckPid(pid) < 0)
+ return NULL;
+
cmd = virCommandNewArgList(binary, "patch", "-p", NULL);
- virCommandAddArgFormat(cmd, "%d", vm->pid);
+ virCommandAddArgFormat(cmd, "%d", pid);
virCommandAddArgList(cmd, patch, NULL);
virCommandSetOutputBuffer(cmd, &output);
VIR_DEBUG("Applying hotpatch for domain %s. (%s patch -p %d %s)",
- vm->def->name, binary, vm->pid, patch);
+ vm->def->name, binary, pid, patch);
if (virCommandRun(cmd, &ret) < 0)
goto error;
@@ -144,6 +164,7 @@ qemuDomainHotpatchUnapply(virDomainObjPtr vm,
g_autoptr(virCommand) cmd = NULL;
g_autofree char *binary = NULL;
char *output = NULL;
+ pid_t pid = vm->pid;
int ret = -1;
if (!id || !qemuDomainHotpatchIsPatchidValid(id)) {
@@ -158,13 +179,16 @@ qemuDomainHotpatchUnapply(virDomainObjPtr vm,
return NULL;
}
+ if (qemuDomainHotpatchCheckPid(pid) < 0)
+ return NULL;
+
cmd = virCommandNewArgList(binary, "unpatch", "-p", NULL);
- virCommandAddArgFormat(cmd, "%d", vm->pid);
+ virCommandAddArgFormat(cmd, "%d", pid);
virCommandAddArgList(cmd, "-i", id, NULL);
virCommandSetOutputBuffer(cmd, &output);
VIR_DEBUG("Unapplying hotpatch for domain %s. (%s unpatch -p %d -i %s)",
- vm->def->name, binary, vm->pid, id);
+ vm->def->name, binary, pid, id);
if (virCommandRun(cmd, &ret) < 0)
goto error;
--
2.27.0

View File

@ -1,110 +0,0 @@
From cf380e22898f70f5782bcea8b0d22027ff7d86af Mon Sep 17 00:00:00 2001
From: AlexChen <alex.chen@huawei.com>
Date: Wed, 20 Oct 2021 11:07:34 +0800
Subject: [PATCH] hotpatch: implement hotpatch virsh api
Signed-off-by: Hao Wang <wanghao232@huawei.com>
Signed-off-by: Bihong Yu <yubihong@huawei.com>
Signed-off-by: AlexChen <alex.chen@huawei.com>
---
tools/virsh-domain.c | 78 ++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 78 insertions(+)
diff --git a/tools/virsh-domain.c b/tools/virsh-domain.c
index f643bd403e..813be4a0db 100644
--- a/tools/virsh-domain.c
+++ b/tools/virsh-domain.c
@@ -14326,6 +14326,78 @@ cmdGuestInfo(vshControl *ctl, const vshCmd *cmd)
return ret;
}
+/*
+ * "hotpatch" command
+ */
+static const vshCmdInfo info_hotpatch[] = {
+ {.name = "help",
+ .data = N_("Manage hotpatch of a live domain")
+ },
+ {.name = "desc",
+ .data = N_("Manage hotpatch of a live domain")
+ },
+ {.name = NULL}
+};
+
+static const vshCmdOptDef opts_hotpatch[] = {
+ VIRSH_COMMON_OPT_DOMAIN_FULL(0),
+ {.name = "action",
+ .type = VSH_OT_DATA,
+ .flags = VSH_OFLAG_REQ,
+ .help = N_("hotpatch action, choose from <apply>, <unapply> and <query>")
+ },
+ {.name = "patch",
+ .type = VSH_OT_STRING,
+ .help = N_("the absolute path of the hotpatch file, mandatory when action=apply")
+ },
+ {.name = "id",
+ .type = VSH_OT_STRING,
+ .help = N_("the unique id of the target patch, mandatory when action=unapply")
+ },
+ {.name = NULL}
+};
+
+VIR_ENUM_DECL(virDomainHotpatchAction);
+VIR_ENUM_IMPL(virDomainHotpatchAction,
+ VIR_DOMAIN_HOTPATCH_LAST,
+ "none",
+ "apply",
+ "unapply",
+ "query");
+
+static bool
+cmdHotpatch(vshControl *ctl,
+ const vshCmd *cmd)
+{
+ g_autoptr(virshDomain) dom = NULL;
+ const char *patch = NULL;
+ const char *id = NULL;
+ const char *actionstr = NULL;
+ int action = -1;
+ g_autofree char *ret = NULL;
+
+ if (!(dom = virshCommandOptDomain(ctl, cmd, NULL)))
+ return false;
+
+ if (vshCommandOptStringReq(ctl, cmd, "action", &actionstr) < 0)
+ return false;
+
+ if (actionstr)
+ action = virDomainHotpatchActionTypeFromString(actionstr);
+
+ if (vshCommandOptStringReq(ctl, cmd, "patch", &patch) < 0)
+ return false;
+
+ if (vshCommandOptStringReq(ctl, cmd, "id", &id) < 0)
+ return false;
+
+ if (!(ret = virDomainHotpatchManage(dom, action, patch, id, 0)))
+ return false;
+
+ vshPrint(ctl, _("%s"), ret);
+ return true;
+}
+
const vshCmdDef domManagementCmds[] = {
{.name = "attach-device",
.handler = cmdAttachDevice,
@@ -14953,5 +15025,11 @@ const vshCmdDef domManagementCmds[] = {
.info = info_guestinfo,
.flags = 0
},
+ {.name = "hotpatch",
+ .handler = cmdHotpatch,
+ .opts = opts_hotpatch,
+ .info = info_hotpatch,
+ .flags = 0
+ },
{.name = NULL}
};
--
2.27.0

View File

@ -1,155 +0,0 @@
From a83bb0dc19d7c92c200b9a234e120d16878eac19 Mon Sep 17 00:00:00 2001
From: AlexChen <alex.chen@huawei.com>
Date: Tue, 19 Oct 2021 22:41:24 +0800
Subject: [PATCH] hotpatch: introduce hotpatch async job flag
Signed-off-by: Hao Wang <wanghao232@huawei.com>
Signed-off-by: Bihong Yu <yubihong@huawei.com>
Signed-off-by: AlexChen <alex.chen@huawei.com>
---
include/libvirt/libvirt-domain.h | 1 +
src/qemu/qemu_domain.c | 3 +++
src/qemu/qemu_domain.h | 1 +
src/qemu/qemu_driver.c | 13 +++++++++++++
src/qemu/qemu_migration.c | 2 ++
src/qemu/qemu_process.c | 1 +
tools/virsh-domain.c | 1 +
7 files changed, 22 insertions(+)
diff --git a/include/libvirt/libvirt-domain.h b/include/libvirt/libvirt-domain.h
index f91061724b..2d6432cab2 100644
--- a/include/libvirt/libvirt-domain.h
+++ b/include/libvirt/libvirt-domain.h
@@ -3295,6 +3295,7 @@ typedef enum {
VIR_DOMAIN_JOB_OPERATION_SNAPSHOT_REVERT = 7,
VIR_DOMAIN_JOB_OPERATION_DUMP = 8,
VIR_DOMAIN_JOB_OPERATION_BACKUP = 9,
+ VIR_DOMAIN_JOB_OPERATION_HOTPATCH = 10,
# ifdef VIR_ENUM_SENTINELS
VIR_DOMAIN_JOB_OPERATION_LAST
diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c
index 5d35d49638..2351cac120 100644
--- a/src/qemu/qemu_domain.c
+++ b/src/qemu/qemu_domain.c
@@ -111,6 +111,7 @@ VIR_ENUM_IMPL(qemuDomainAsyncJob,
"snapshot",
"start",
"backup",
+ "hotpatch",
);
VIR_ENUM_IMPL(qemuDomainNamespace,
@@ -217,6 +218,7 @@ qemuDomainAsyncJobPhaseToString(qemuDomainAsyncJob job,
case QEMU_ASYNC_JOB_START:
case QEMU_ASYNC_JOB_NONE:
case QEMU_ASYNC_JOB_BACKUP:
+ case QEMU_ASYNC_JOB_HOTPATCH:
G_GNUC_FALLTHROUGH;
case QEMU_ASYNC_JOB_LAST:
break;
@@ -243,6 +245,7 @@ qemuDomainAsyncJobPhaseFromString(qemuDomainAsyncJob job,
case QEMU_ASYNC_JOB_START:
case QEMU_ASYNC_JOB_NONE:
case QEMU_ASYNC_JOB_BACKUP:
+ case QEMU_ASYNC_JOB_HOTPATCH:
G_GNUC_FALLTHROUGH;
case QEMU_ASYNC_JOB_LAST:
break;
diff --git a/src/qemu/qemu_domain.h b/src/qemu/qemu_domain.h
index cf19f4d101..678ddab624 100644
--- a/src/qemu/qemu_domain.h
+++ b/src/qemu/qemu_domain.h
@@ -107,6 +107,7 @@ typedef enum {
QEMU_ASYNC_JOB_SNAPSHOT,
QEMU_ASYNC_JOB_START,
QEMU_ASYNC_JOB_BACKUP,
+ QEMU_ASYNC_JOB_HOTPATCH,
QEMU_ASYNC_JOB_LAST
} qemuDomainAsyncJob;
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index f6d99957a5..d4c5f073bb 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -13866,6 +13866,9 @@ static int qemuDomainAbortJob(virDomainPtr dom)
ret = 0;
break;
+ case QEMU_ASYNC_JOB_HOTPATCH:
+ break;
+
case QEMU_ASYNC_JOB_LAST:
default:
virReportEnumRangeError(qemuDomainAsyncJob, priv->job.asyncJob);
@@ -23180,6 +23183,7 @@ qemuDomainHotpatchManage(virDomainPtr domain,
unsigned int flags)
{
virDomainObjPtr vm;
+ virQEMUDriverPtr driver = domain->conn->privateData;
char *ret = NULL;
size_t len;
@@ -23188,6 +23192,12 @@ qemuDomainHotpatchManage(virDomainPtr domain,
if (!(vm = qemuDomainObjFromDomain(domain)))
goto cleanup;
+ if (qemuDomainObjBeginAsyncJob(driver, vm, QEMU_ASYNC_JOB_HOTPATCH,
+ VIR_DOMAIN_JOB_OPERATION_HOTPATCH, 0) < 0)
+ goto cleanup;
+
+ qemuDomainObjSetAsyncJobMask(vm, QEMU_JOB_DEFAULT_MASK);
+
switch (action) {
case VIR_DOMAIN_HOTPATCH_APPLY:
ret = qemuDomainHotpatchApply(vm, patch);
@@ -23214,6 +23224,9 @@ qemuDomainHotpatchManage(virDomainPtr domain,
if (len > 0)
ret[len - 1] = '\0';
+ endjob:
+ qemuDomainObjEndAsyncJob(driver, vm);
+
cleanup:
virDomainObjEndAPI(&vm);
return ret;
diff --git a/src/qemu/qemu_migration.c b/src/qemu/qemu_migration.c
index 3f4627bd39..1665071eb3 100644
--- a/src/qemu/qemu_migration.c
+++ b/src/qemu/qemu_migration.c
@@ -1532,6 +1532,8 @@ qemuMigrationJobName(virDomainObjPtr vm)
return _("start job");
case QEMU_ASYNC_JOB_BACKUP:
return _("backup job");
+ case QEMU_ASYNC_JOB_HOTPATCH:
+ return _("hotpatch job");
case QEMU_ASYNC_JOB_LAST:
default:
return _("job");
diff --git a/src/qemu/qemu_process.c b/src/qemu/qemu_process.c
index 9cf7242f31..818a72d8f9 100644
--- a/src/qemu/qemu_process.c
+++ b/src/qemu/qemu_process.c
@@ -3646,6 +3646,7 @@ qemuProcessRecoverJob(virQEMUDriverPtr driver,
priv->job.current->started = now;
break;
+ case QEMU_ASYNC_JOB_HOTPATCH:
case QEMU_ASYNC_JOB_NONE:
case QEMU_ASYNC_JOB_LAST:
break;
diff --git a/tools/virsh-domain.c b/tools/virsh-domain.c
index 65d5c831ec..f643bd403e 100644
--- a/tools/virsh-domain.c
+++ b/tools/virsh-domain.c
@@ -6167,6 +6167,7 @@ VIR_ENUM_IMPL(virshDomainJobOperation,
N_("Snapshot revert"),
N_("Dump"),
N_("Backup"),
+ N_("Hotpatch"),
);
static const char *
--
2.27.0

View File

@ -1,302 +0,0 @@
From 3be8bb571d13795c2824dd6d2089035a1be6cf57 Mon Sep 17 00:00:00 2001
From: jiang-dawei15 <jiangdawei15@huawei.com>
Date: Wed, 26 Jan 2022 15:18:10 +0800
Subject: [PATCH] hotpatch: virsh support autoload mode
---
include/libvirt/libvirt-domain.h | 1 +
src/qemu/qemu_conf.c | 9 +++
src/qemu/qemu_conf.h | 1 +
src/qemu/qemu_driver.c | 5 ++
src/qemu/qemu_hotpatch.c | 122 +++++++++++++++++++++++++++++++
src/qemu/qemu_hotpatch.h | 3 +
src/qemu/qemu_process.c | 6 ++
tools/virsh-domain.c | 5 +-
8 files changed, 150 insertions(+), 2 deletions(-)
diff --git a/include/libvirt/libvirt-domain.h b/include/libvirt/libvirt-domain.h
index 2d6432cab2..4ab0c9c0b2 100644
--- a/include/libvirt/libvirt-domain.h
+++ b/include/libvirt/libvirt-domain.h
@@ -4997,6 +4997,7 @@ typedef enum {
VIR_DOMAIN_HOTPATCH_APPLY, /* Apply hotpatch */
VIR_DOMAIN_HOTPATCH_UNAPPLY, /* Unapply hotpatch */
VIR_DOMAIN_HOTPATCH_QUERY, /* Query hotpatch */
+ VIR_DOMAIN_HOTPATCH_AUTOLOAD, /* Autoload hotpatch */
# ifdef VIR_ENUM_SENTINELS
VIR_DOMAIN_HOTPATCH_LAST
diff --git a/src/qemu/qemu_conf.c b/src/qemu/qemu_conf.c
index 809e8fe526..bd96ccb78e 100644
--- a/src/qemu/qemu_conf.c
+++ b/src/qemu/qemu_conf.c
@@ -1006,6 +1006,12 @@ virQEMUDriverConfigLoadCapsFiltersEntry(virQEMUDriverConfigPtr cfg,
return 0;
}
+static int
+virQEMUDriverConfigLoadHotpatchPathEntry(virQEMUDriverConfigPtr cfg,
+ virConfPtr conf)
+{
+ return virConfGetValueString(conf, "hotpatch_path", &cfg->hotpatchPath);
+}
int virQEMUDriverConfigLoadFile(virQEMUDriverConfigPtr cfg,
const char *filename,
@@ -1078,6 +1084,9 @@ int virQEMUDriverConfigLoadFile(virQEMUDriverConfigPtr cfg,
if (virQEMUDriverConfigLoadCapsFiltersEntry(cfg, conf) < 0)
return -1;
+ if (virQEMUDriverConfigLoadHotpatchPathEntry(cfg, conf) < 0)
+ return -1;
+
return 0;
}
diff --git a/src/qemu/qemu_conf.h b/src/qemu/qemu_conf.h
index 14f9b9e81e..f0124a0fe2 100644
--- a/src/qemu/qemu_conf.h
+++ b/src/qemu/qemu_conf.h
@@ -220,6 +220,7 @@ struct _virQEMUDriverConfig {
gid_t swtpm_group;
char **capabilityfilters;
+ char *hotpatchPath;
};
G_DEFINE_AUTOPTR_CLEANUP_FUNC(virQEMUDriverConfig, virObjectUnref);
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index 2b24881f75..37b2c4a2da 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -23186,6 +23186,7 @@ qemuDomainHotpatchManage(virDomainPtr domain,
virQEMUDriverPtr driver = domain->conn->privateData;
char *ret = NULL;
size_t len;
+ g_autoptr(virQEMUDriverConfig) cfg = virQEMUDriverGetConfig(driver);
virCheckFlags(0, NULL);
@@ -23214,6 +23215,10 @@ qemuDomainHotpatchManage(virDomainPtr domain,
ret = qemuDomainHotpatchQuery(vm);
break;
+ case VIR_DOMAIN_HOTPATCH_AUTOLOAD:
+ ret = qemuDomainHotpatchAutoload(vm, cfg->hotpatchPath);
+ break;
+
default:
virReportError(VIR_ERR_OPERATION_INVALID, "%s",
_("Unknow hotpatch action"));
diff --git a/src/qemu/qemu_hotpatch.c b/src/qemu/qemu_hotpatch.c
index 03e63c1341..02f511cc38 100644
--- a/src/qemu/qemu_hotpatch.c
+++ b/src/qemu/qemu_hotpatch.c
@@ -25,6 +25,8 @@
#include "virerror.h"
#include "virfile.h"
#include "virlog.h"
+#include "virbuffer.h"
+#include "virstring.h"
#include "vircommand.h"
#include "qemu/qemu_domain.h"
#include "qemu_hotpatch.h"
@@ -32,6 +34,7 @@
#define LIBCARE_CTL "libcare-ctl"
#define LIBCARE_ERROR_NUMBER 255
#define MAX_PATCHID_LEN 8
+#define MAX_FILE_SIZE (1024*1024)
#define VIR_FROM_THIS VIR_FROM_QEMU
@@ -204,3 +207,122 @@ qemuDomainHotpatchUnapply(virDomainObjPtr vm,
VIR_FREE(output);
return NULL;
}
+
+char *
+qemuDomainHotpatchAutoload(virDomainObjPtr vm, char *hotpatch_path)
+{
+ VIR_AUTOSTRINGLIST applied_patches = NULL;
+ VIR_AUTOSTRINGLIST lines = NULL;
+ g_autofree char *applied_patch = NULL;
+ g_autofree char *libvirtd_conf = NULL;
+ g_autofree char *patch_conf = NULL;
+ g_autofree char *buf = NULL;
+ char *ret = NULL;
+ int i, j, len;
+
+ if (hotpatch_path == NULL) {
+ virReportError(VIR_ERR_INVALID_ARG, "%s",
+ _("Invalid hotpatch path."));
+ return NULL;
+ }
+
+ /* get hotpatch info from Patch.conf */
+ patch_conf = g_strdup_printf("%s/Patch.conf", hotpatch_path);
+ if ((len = virFileReadAll(patch_conf, MAX_FILE_SIZE, &buf)) < 0) {
+ virReportError(VIR_ERR_INVALID_ARG, "%s",
+ _("Failed to read Patch.conf file."));
+ return NULL;
+ }
+ if (len > 0)
+ buf[len-1] = '\0';
+
+ lines = virStringSplit(buf, "\n", 0);
+ if (!lines)
+ return NULL;
+
+ /* get domain hotpatch infomation */
+ applied_patch = qemuDomainHotpatchQuery(vm);
+ if (!applied_patch)
+ return NULL;
+
+ applied_patches = virStringSplit(applied_patch, "\n", 0);
+ if (!applied_patches)
+ return NULL;
+
+ /* load all hotpatch which are listed in Patch.conf one by one */
+ for (i = 0; lines[i] != NULL; i++) {
+ VIR_AUTOSTRINGLIST patch_info = NULL;
+ g_autofree char *kpatch_dir = NULL;
+ g_autofree char *file_path = NULL;
+ struct dirent *de;
+ DIR *dh;
+ int direrr;
+
+ if (!strstr(lines[i], "QEMU-"))
+ continue;
+
+ patch_info = virStringSplit(lines[i], " ", 0);
+ if (!patch_info)
+ continue;
+
+ /* skip already applied patch */
+ if (strstr(applied_patch, patch_info[2]))
+ continue;
+
+ /* get the kpatch file name */
+ kpatch_dir = g_strdup_printf("%s/%s", hotpatch_path, patch_info[1]);
+ if (!kpatch_dir || !virFileExists(kpatch_dir))
+ return NULL;
+
+ if (virDirOpen(&dh, kpatch_dir) < 0)
+ return NULL;
+ if ((direrr = virDirRead(dh, &de, kpatch_dir)) > 0) {
+ GStatBuf sb;
+
+ file_path = g_strdup_printf("%s/%s", kpatch_dir, de->d_name);
+ if (g_lstat(file_path, &sb) < 0) {
+ virReportSystemError(errno, _("Cannot access '%s'"),
+ file_path);
+ VIR_DIR_CLOSE(dh);
+ return NULL;
+ }
+ }
+ VIR_DIR_CLOSE(dh);
+
+ if (qemuDomainHotpatchApply(vm, file_path) == NULL) {
+ virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+ _("failed to apply the hotpatch."));
+ return NULL;
+ }
+ }
+
+ /* unload the hotpatch which are not listed in Patch.conf */
+ for (i = 0; applied_patches[i] != NULL; i++) {
+ const char *patch_id = NULL;
+ bool is_need_unload = true;
+
+ if (!strstr(applied_patches[i], "Patch id"))
+ continue;
+
+ patch_id = strstr(applied_patches[i], ":") + 1;
+ virSkipSpaces(&patch_id);
+
+ for (j = 0; lines[j] != NULL; j++) {
+ if (!strstr(lines[j], "QEMU-"))
+ continue;
+ if (strstr(lines[j], patch_id)) {
+ is_need_unload = false;
+ break;
+ }
+ }
+ if (is_need_unload == true)
+ if (qemuDomainHotpatchUnapply(vm, patch_id) == NULL) {
+ virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+ _("failed to unapply the hotpatch."));
+ return NULL;
+ }
+ }
+
+ ret = g_strdup_printf("Hotpatch autoload successfully.\n");
+ return ret;
+}
diff --git a/src/qemu/qemu_hotpatch.h b/src/qemu/qemu_hotpatch.h
index 4c84a57950..8e0bfe348a 100644
--- a/src/qemu/qemu_hotpatch.h
+++ b/src/qemu/qemu_hotpatch.h
@@ -34,3 +34,6 @@ qemuDomainHotpatchApply(virDomainObjPtr vm,
char *
qemuDomainHotpatchUnapply(virDomainObjPtr vm,
const char *id);
+
+char *
+qemuDomainHotpatchAutoload(virDomainObjPtr vm, char *path_config);
diff --git a/src/qemu/qemu_process.c b/src/qemu/qemu_process.c
index 818a72d8f9..24dd9f052c 100644
--- a/src/qemu/qemu_process.c
+++ b/src/qemu/qemu_process.c
@@ -59,6 +59,7 @@
#include "qemu_firmware.h"
#include "qemu_backup.h"
#include "qemu_dbus.h"
+#include "qemu_hotpatch.h"
#include "cpu/cpu.h"
#include "cpu/cpu_x86.h"
@@ -6684,6 +6685,7 @@ qemuProcessLaunch(virConnectPtr conn,
g_autoptr(virQEMUDriverConfig) cfg = NULL;
size_t nnicindexes = 0;
g_autofree int *nicindexes = NULL;
+ g_autofree char *autoLoadStatus = NULL;
size_t i;
VIR_DEBUG("conn=%p driver=%p vm=%p name=%s if=%d asyncJob=%d "
@@ -6993,6 +6995,10 @@ qemuProcessLaunch(virConnectPtr conn,
qemuProcessAutoDestroyAdd(driver, vm, conn) < 0)
goto cleanup;
+ /* Autoload hotpatch */
+ if ((autoLoadStatus = qemuDomainHotpatchAutoload(vm, cfg->hotpatchPath)) == NULL) {
+ VIR_WARN("Failed to autoload the hotpatch for %s.", vm->def->name);
+ }
ret = 0;
cleanup:
diff --git a/tools/virsh-domain.c b/tools/virsh-domain.c
index 813be4a0db..b5375ebd3e 100644
--- a/tools/virsh-domain.c
+++ b/tools/virsh-domain.c
@@ -14344,7 +14344,7 @@ static const vshCmdOptDef opts_hotpatch[] = {
{.name = "action",
.type = VSH_OT_DATA,
.flags = VSH_OFLAG_REQ,
- .help = N_("hotpatch action, choose from <apply>, <unapply> and <query>")
+ .help = N_("hotpatch action, choose from <apply>, <unapply>, <query> and <autoload>")
},
{.name = "patch",
.type = VSH_OT_STRING,
@@ -14363,7 +14363,8 @@ VIR_ENUM_IMPL(virDomainHotpatchAction,
"none",
"apply",
"unapply",
- "query");
+ "query",
+ "autoload");
static bool
cmdHotpatch(vshControl *ctl,
--
2.30.0

View File

@ -1,32 +0,0 @@
From ee9069defba076d94b432662af93a784ea002f5a Mon Sep 17 00:00:00 2001
From: tangbinzy <tangbin_yewu@cmss.chinamobile.com>
Date: Tue, 29 Nov 2022 08:57:42 +0000
Subject: [PATCH 04/24] hyperv: fix the number of threads per core The operands
were reversed, producing an incorrect result.
Co-authored-by: Sri Ramanujam <sramanujam@datto.com>
Signed-off-by: Matt Coleman <matt@datto.com>
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
Signed-off-by: tangbin <tangbin_yewu@cmss.chinamobile.com>
(cherry-pick from 1e18d3b833b9daa7bb18b9550a2cf4d140303d86)
---
src/hyperv/hyperv_driver.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/src/hyperv/hyperv_driver.c b/src/hyperv/hyperv_driver.c
index 4677a25ff8..213dd8837b 100644
--- a/src/hyperv/hyperv_driver.c
+++ b/src/hyperv/hyperv_driver.c
@@ -310,7 +310,7 @@ hypervNodeGetInfo(virConnectPtr conn, virNodeInfoPtr info)
}
info->cores = processorList->data.common->NumberOfCores;
- info->threads = info->cores / processorList->data.common->NumberOfLogicalProcessors;
+ info->threads = processorList->data.common->NumberOfLogicalProcessors / info->cores;
info->cpus = info->sockets * info->cores;
result = 0;
--
2.27.0

View File

@ -1,77 +0,0 @@
From c4c665b4654280560eafe5782359b71e8ef2b1b5 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Hyman=20Huang=28=E9=BB=84=E5=8B=87=29?=
<huangy81@chinatelecom.cn>
Date: Sun, 20 Feb 2022 21:28:11 +0800
Subject: [PATCH 6/7] include: Introduce virDomainDirtyRateCalcFlags
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Introduce virDomainDirtyRateCalcFlags to get ready for
adding mode parameter to qemuDomainStartDirtyRateCalc.
Signed-off-by: Hyman Huang(黄勇) <huangy81@chinatelecom.cn>
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
---
include/libvirt/libvirt-domain.h | 13 +++++++++++++
src/libvirt-domain.c | 12 +++++++++++-
2 files changed, 24 insertions(+), 1 deletion(-)
diff --git a/include/libvirt/libvirt-domain.h b/include/libvirt/libvirt-domain.h
index e1954ae663..c7956c81d6 100644
--- a/include/libvirt/libvirt-domain.h
+++ b/include/libvirt/libvirt-domain.h
@@ -5030,6 +5030,19 @@ typedef enum {
# endif
} virDomainDirtyRateStatus;
+/**
+ * virDomainDirtyRateCalcFlags:
+ *
+ * Flags OR'ed together to provide specific behaviour when calculating dirty page
+ * rate for a Domain
+ *
+ */
+typedef enum {
+ VIR_DOMAIN_DIRTYRATE_MODE_PAGE_SAMPLING = 0, /* default mode - page-sampling */
+ VIR_DOMAIN_DIRTYRATE_MODE_DIRTY_BITMAP = 1 << 0, /* dirty-bitmap mode */
+ VIR_DOMAIN_DIRTYRATE_MODE_DIRTY_RING = 1 << 1, /* dirty-ring mode */
+} virDomainDirtyRateCalcFlags;
+
int virDomainStartDirtyRateCalc(virDomainPtr domain,
int seconds,
unsigned int flags);
diff --git a/src/libvirt-domain.c b/src/libvirt-domain.c
index 6a37ea85b7..0ff99c94b6 100644
--- a/src/libvirt-domain.c
+++ b/src/libvirt-domain.c
@@ -12821,7 +12821,7 @@ virDomainHotpatchManage(virDomainPtr domain,
* virDomainStartDirtyRateCalc:
* @domain: a domain object
* @seconds: specified calculating time in seconds
- * @flags: extra flags; not used yet, so callers should always pass 0
+ * @flags: bitwise-OR of supported virDomainDirtyRateCalcFlags
*
* Calculate the current domain's memory dirty rate in next @seconds.
* The calculated dirty rate information is available by calling
@@ -12845,6 +12845,16 @@ virDomainStartDirtyRateCalc(virDomainPtr domain,
virCheckReadOnlyGoto(conn->flags, error);
+ VIR_EXCLUSIVE_FLAGS_GOTO(VIR_DOMAIN_DIRTYRATE_MODE_PAGE_SAMPLING,
+ VIR_DOMAIN_DIRTYRATE_MODE_DIRTY_BITMAP,
+ error);
+ VIR_EXCLUSIVE_FLAGS_GOTO(VIR_DOMAIN_DIRTYRATE_MODE_PAGE_SAMPLING,
+ VIR_DOMAIN_DIRTYRATE_MODE_DIRTY_RING,
+ error);
+ VIR_EXCLUSIVE_FLAGS_GOTO(VIR_DOMAIN_DIRTYRATE_MODE_DIRTY_BITMAP,
+ VIR_DOMAIN_DIRTYRATE_MODE_DIRTY_RING,
+ error);
+
if (conn->driver->domainStartDirtyRateCalc) {
int ret;
ret = conn->driver->domainStartDirtyRateCalc(domain, seconds, flags);
--
2.27.0

View File

@ -1,51 +0,0 @@
From 75d4ed800f297532a7b3ac2b8f8a94c049959e3b Mon Sep 17 00:00:00 2001
From: Michal Privoznik <mprivozn@redhat.com>
Date: Fri, 18 Dec 2020 16:09:08 +0100
Subject: [PATCH 024/108] leaseshelper: Report errors on failure
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
If leasehelper fails all that we are left with is a simple error
message produced by dnsmasq:
lease-init script returned exit code 1
This is because the leasehelper did not write any message to
stderr. According to dnsmasq's manpage, whenever it's invoking
leasehelper the stderr is kept open:
All file descriptors are closed except stdin, which is open to
/dev/null, and stdout and stderr which capture output for
logging by dnsmasq.
As debugging leasehelper is not trivial (because dnsmasq invokes
it with plenty of env vars set - that's how data is passed onto
helper), let's print an error into stderr if exiting with an
error. And since we are not calling public APIs, we have to call
virDispatchError() explicitly and since we don't have any
connection open, we have to pass NULL.
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
(cherry picked from commit c14bd64f3eba9838af8ab1cac369d51abfeb21b9)
---
src/network/leaseshelper.c | 2 ++
1 file changed, 2 insertions(+)
diff --git a/src/network/leaseshelper.c b/src/network/leaseshelper.c
index 2b5fc0f442..fdd7fd3e80 100644
--- a/src/network/leaseshelper.c
+++ b/src/network/leaseshelper.c
@@ -253,6 +253,8 @@ main(int argc, char **argv)
rv = EXIT_SUCCESS;
cleanup:
+ if (rv != EXIT_SUCCESS)
+ virDispatchError(NULL);
if (pid_file_fd != -1)
virPidFileReleasePath(pid_file, pid_file_fd);
--
2.33.0

Binary file not shown.

View File

@ -1,119 +0,0 @@
From 9ba3e54d2b33e1105f5879fff3656c093337e60a Mon Sep 17 00:00:00 2001
From: Jiahui Cen <cenjiahui@huawei.com>
Date: Thu, 25 Feb 2021 18:55:30 +0800
Subject: [PATCH] libvirt: Add 'retry' support for error policy
Introduce error_policy=/rerror_policy='retry' to support
werror=/rerror=retry mechanism in qemu.
Add retry_interval parameter to control the interval between retries.
Add retry_timeout parameter to control the total retry times.
Signed-off-by: Jiahui Cen <cenjiahui@huawei.com>
Signed-off-by: Ying Fang <fangying1@huawei.com>
---
src/conf/domain_conf.c | 25 +++++++++++++++++++++++++
src/conf/domain_conf.h | 3 +++
src/qemu/qemu_command.c | 8 ++++++++
src/qemu/qemu_domain.c | 2 ++
4 files changed, 38 insertions(+)
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index dbc3e103ff..5c469cedd0 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -355,6 +355,7 @@ VIR_ENUM_IMPL(virDomainDiskErrorPolicy,
"report",
"ignore",
"enospace",
+ "retry",
);
VIR_ENUM_IMPL(virDomainDiskIo,
@@ -10213,6 +10214,30 @@ virDomainDiskDefDriverParseXML(virDomainDiskDefPtr def,
}
VIR_FREE(tmp);
+ def->retry_interval = -1;
+ if ((tmp = virXMLPropString(cur, "retry_interval")) &&
+ ((def->error_policy != VIR_DOMAIN_DISK_ERROR_POLICY_RETRY &&
+ def->rerror_policy != VIR_DOMAIN_DISK_ERROR_POLICY_RETRY) ||
+ (virStrToLong_l(tmp, NULL, 10, &def->retry_interval) < 0) ||
+ (def->retry_interval < 0))) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
+ _("unknown disk retry interval '%s'"), tmp);
+ return -1;
+ }
+ VIR_FREE(tmp);
+
+ def->retry_timeout = -1;
+ if ((tmp = virXMLPropString(cur, "retry_timeout")) &&
+ ((def->error_policy != VIR_DOMAIN_DISK_ERROR_POLICY_RETRY &&
+ def->rerror_policy != VIR_DOMAIN_DISK_ERROR_POLICY_RETRY) ||
+ (virStrToLong_l(tmp, NULL, 10, &def->retry_timeout) < 0) ||
+ (def->retry_timeout < 0))) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
+ _("unknown disk retry interval '%s'"), tmp);
+ return -1;
+ }
+ VIR_FREE(tmp);
+
if ((tmp = virXMLPropString(cur, "io")) &&
(def->iomode = virDomainDiskIoTypeFromString(tmp)) <= 0) {
virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
index 16e625331c..86a86d3090 100644
--- a/src/conf/domain_conf.h
+++ b/src/conf/domain_conf.h
@@ -396,6 +396,7 @@ typedef enum {
VIR_DOMAIN_DISK_ERROR_POLICY_REPORT,
VIR_DOMAIN_DISK_ERROR_POLICY_IGNORE,
VIR_DOMAIN_DISK_ERROR_POLICY_ENOSPACE,
+ VIR_DOMAIN_DISK_ERROR_POLICY_RETRY,
VIR_DOMAIN_DISK_ERROR_POLICY_LAST
} virDomainDiskErrorPolicy;
@@ -561,6 +562,8 @@ struct _virDomainDiskDef {
int cachemode; /* enum virDomainDiskCache */
int error_policy; /* enum virDomainDiskErrorPolicy */
int rerror_policy; /* enum virDomainDiskErrorPolicy */
+ long retry_interval;
+ long retry_timeout;
int iomode; /* enum virDomainDiskIo */
int ioeventfd; /* enum virTristateSwitch */
int event_idx; /* enum virTristateSwitch */
diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index 315deb5cfd..c3ad041959 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -1723,6 +1723,14 @@ qemuBuildDiskFrontendAttributeErrorPolicy(virDomainDiskDefPtr disk,
virBufferAsprintf(buf, ",werror=%s", wpolicy);
if (rpolicy)
virBufferAsprintf(buf, ",rerror=%s", rpolicy);
+ if ((disk->error_policy == VIR_DOMAIN_DISK_ERROR_POLICY_RETRY ||
+ disk->rerror_policy == VIR_DOMAIN_DISK_ERROR_POLICY_RETRY) &&
+ disk->retry_interval >= 0)
+ virBufferAsprintf(buf, ",retry_interval=%ld", disk->retry_interval);
+ if ((disk->error_policy == VIR_DOMAIN_DISK_ERROR_POLICY_RETRY ||
+ disk->rerror_policy == VIR_DOMAIN_DISK_ERROR_POLICY_RETRY) &&
+ disk->retry_timeout >= 0)
+ virBufferAsprintf(buf, ",retry_timeout=%ld", disk->retry_timeout);
}
diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c
index f89ff20a84..58493706a1 100644
--- a/src/qemu/qemu_domain.c
+++ b/src/qemu/qemu_domain.c
@@ -12308,6 +12308,8 @@ qemuDomainDiskChangeSupported(virDomainDiskDefPtr disk,
CHECK_EQ(cachemode, "cache", true);
CHECK_EQ(error_policy, "error_policy", true);
CHECK_EQ(rerror_policy, "rerror_policy", true);
+ CHECK_EQ(retry_interval, "retry_interval", true);
+ CHECK_EQ(retry_timeout, "retry_timeout", true);
CHECK_EQ(iomode, "io", true);
CHECK_EQ(ioeventfd, "ioeventfd", true);
CHECK_EQ(event_idx, "event_idx", true);
--
2.27.0

View File

@ -1,42 +0,0 @@
From 19845de491a3102df4256a3457c7d5669bccda63 Mon Sep 17 00:00:00 2001
From: Michal Privoznik <mprivozn@redhat.com>
Date: Mon, 18 May 2020 10:07:30 +0200
Subject: [PATCH] Don't require secdrivers to implement
.domainMoveImageMetadata
The AppArmor secdriver does not use labels to grant access to
resources. Therefore, it doesn't use XATTRs and hence it lacks
implementation of .domainMoveImageMetadata callback. This leads
to a harmless but needless error message appearing in the logs:
virSecurityManagerMoveImageMetadata:476 : this function is not
supported by the connection driver: virSecurityManagerMoveImageMetadata
Closes: https://gitlab.com/libvirt/libvirt/-/issues/25
cherry-pick from commit: cc8c297e473afd55e5d8e35e18345d8df176059d
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
Reviewed-by: Erik Skultety <eskultet@redhat.com>
Signed-off-by: Jin Yan <jinyan12@huawei.com>
---
src/security/security_manager.c | 3 +--
1 file changed, 1 insertion(+), 2 deletions(-)
diff --git a/src/security/security_manager.c b/src/security/security_manager.c
index fe03274..1445291 100644
--- a/src/security/security_manager.c
+++ b/src/security/security_manager.c
@@ -473,8 +473,7 @@ virSecurityManagerMoveImageMetadata(virSecurityManagerPtr mgr,
return ret;
}
- virReportUnsupportedError();
- return -1;
+ return 0;
}
--
1.8.3.1

View File

@ -1,56 +0,0 @@
From 42e4b74e1bbd08aad3afa46d741e46c40a8af73d Mon Sep 17 00:00:00 2001
From: Bihong Yu <yubihong@huawei.com>
Date: Sat, 6 Jun 2020 18:52:35 +0800
Subject: [PATCH] Fix some wrong usage of ATTRIBUTE_NONNULL()
The virStateInitialize() function has ATTRIBUTE_NONNULL()
referring to @root argument (incorrectly anyway) but in
daemonRunStateInit() NULL is passed in anyway.
Then there is virCommandAddArgPair() which also has
ATTRIBUTE_NONNULL() for one of its arguments and then checks the
argument for being NULL anyways.
cherry-pick from commit: 2a372a5ad5fab3bf26fb9bea019d38fa04ba8b34
Signed-off-by:Bihong Yu <yubihong@huawei.com>
Reviewed-by:Chuan Zheng <zhengchuan@huawei.com>
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
Signed-off-by: Jin Yan <jinyan12@huawei.com>
---
src/libvirt_internal.h | 3 +--
src/util/vircommand.h | 3 +--
2 files changed, 2 insertions(+), 4 deletions(-)
diff --git a/src/libvirt_internal.h b/src/libvirt_internal.h
index 00ef7aa..72c6127 100644
--- a/src/libvirt_internal.h
+++ b/src/libvirt_internal.h
@@ -33,8 +33,7 @@ int virStateInitialize(bool privileged,
bool mandatory,
const char *root,
virStateInhibitCallback inhibit,
- void *opaque)
- ATTRIBUTE_NONNULL(2);
+ void *opaque);
int virStateCleanup(void);
int virStateReload(void);
int virStateStop(void);
diff --git a/src/util/vircommand.h b/src/util/vircommand.h
index 9086f9a..4e6cb0a 100644
--- a/src/util/vircommand.h
+++ b/src/util/vircommand.h
@@ -128,8 +128,7 @@ void virCommandAddArgFormat(virCommandPtr cmd,
void virCommandAddArgPair(virCommandPtr cmd,
const char *name,
- const char *val)
- ATTRIBUTE_NONNULL(2) ATTRIBUTE_NONNULL(3);
+ const char *val);
void virCommandAddArgSet(virCommandPtr cmd,
const char *const*vals) ATTRIBUTE_NONNULL(2);
--
1.8.3.1

View File

@ -1,320 +0,0 @@
From 0ca4dd0cd279448ff28beb4c88e52107531783a3 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Tue, 4 Aug 2020 01:44:48 +0000
Subject: [PATCH] Substitute security_context_t with char *
Historically, we've used security_context_t for variables passed
to libselinux APIs. But almost 7 years ago, libselinux developers
admitted in their API that in fact, it's just a 'char *' type
[1]. Ever since then the APIs accept 'char *' instead, but they
kept the old alias just for API stability. Well, not anymore [2].
1: https://github.com/SELinuxProject/selinux/commit/9eb9c9327563014ad6a807814e7975424642d5b9
2: https://github.com/SELinuxProject/selinux/commit/7a124ca2758136f49cc38efc26fb1a2d385ecfd9
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
Reviewed-by: Andrea Bolognani <abologna@redhat.com>
(cherry-picked from commit e71e13488dc1aa65456e54a4b41bc925821b4263)
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/libvirt-lxc.c | 2 +-
src/rpc/virnetsocket.c | 2 +-
src/security/security_selinux.c | 26 +++++++++++++-------------
src/storage/storage_util.c | 2 +-
src/util/viridentity.c | 2 +-
tests/securityselinuxhelper.c | 16 ++++++++--------
tests/securityselinuxlabeltest.c | 4 ++--
tests/securityselinuxtest.c | 2 +-
tests/viridentitytest.c | 2 +-
9 files changed, 29 insertions(+), 29 deletions(-)
diff --git a/src/libvirt-lxc.c b/src/libvirt-lxc.c
index 47a06a3..25f1cfc 100644
--- a/src/libvirt-lxc.c
+++ b/src/libvirt-lxc.c
@@ -204,7 +204,7 @@ virDomainLxcEnterSecurityLabel(virSecurityModelPtr model,
if (STREQ(model->model, "selinux")) {
#ifdef WITH_SELINUX
if (oldlabel) {
- security_context_t ctx;
+ char *ctx;
if (getcon(&ctx) < 0) {
virReportSystemError(errno,
diff --git a/src/rpc/virnetsocket.c b/src/rpc/virnetsocket.c
index 6c790cb..5537289 100644
--- a/src/rpc/virnetsocket.c
+++ b/src/rpc/virnetsocket.c
@@ -1595,7 +1595,7 @@ int virNetSocketGetUNIXIdentity(virNetSocketPtr sock G_GNUC_UNUSED,
int virNetSocketGetSELinuxContext(virNetSocketPtr sock,
char **context)
{
- security_context_t seccon = NULL;
+ char *seccon = NULL;
int ret = -1;
*context = NULL;
diff --git a/src/security/security_selinux.c b/src/security/security_selinux.c
index 8aeb6e4..72d1658 100644
--- a/src/security/security_selinux.c
+++ b/src/security/security_selinux.c
@@ -198,7 +198,7 @@ virSecuritySELinuxTransactionAppend(const char *path,
static int
virSecuritySELinuxRememberLabel(const char *path,
- const security_context_t con)
+ const char *con)
{
return virSecuritySetRememberedLabel(SECURITY_SELINUX_NAME,
path, con);
@@ -207,7 +207,7 @@ virSecuritySELinuxRememberLabel(const char *path,
static int
virSecuritySELinuxRecallLabel(const char *path,
- security_context_t *con)
+ char **con)
{
int rv;
@@ -431,7 +431,7 @@ virSecuritySELinuxMCSGetProcessRange(char **sens,
int *catMin,
int *catMax)
{
- security_context_t ourSecContext = NULL;
+ char *ourSecContext = NULL;
context_t ourContext = NULL;
char *cat = NULL;
char *tmp;
@@ -530,8 +530,8 @@ virSecuritySELinuxMCSGetProcessRange(char **sens,
}
static char *
-virSecuritySELinuxContextAddRange(security_context_t src,
- security_context_t dst)
+virSecuritySELinuxContextAddRange(char *src,
+ char *dst)
{
char *str = NULL;
char *ret = NULL;
@@ -575,7 +575,7 @@ virSecuritySELinuxGenNewContext(const char *basecontext,
context_t context = NULL;
char *ret = NULL;
char *str;
- security_context_t ourSecContext = NULL;
+ char *ourSecContext = NULL;
context_t ourContext = NULL;
VIR_DEBUG("basecontext=%s mcs=%s isObjectContext=%d",
@@ -967,7 +967,7 @@ virSecuritySELinuxReserveLabel(virSecurityManagerPtr mgr,
virDomainDefPtr def,
pid_t pid)
{
- security_context_t pctx;
+ char *pctx;
context_t ctx = NULL;
const char *mcs;
int rv;
@@ -1217,7 +1217,7 @@ virSecuritySELinuxGetProcessLabel(virSecurityManagerPtr mgr G_GNUC_UNUSED,
pid_t pid,
virSecurityLabelPtr sec)
{
- security_context_t ctx;
+ char *ctx;
if (getpidcon_raw(pid, &ctx) == -1) {
virReportSystemError(errno,
@@ -1330,7 +1330,7 @@ virSecuritySELinuxSetFilecon(virSecurityManagerPtr mgr,
bool remember)
{
bool privileged = virSecurityManagerGetPrivileged(mgr);
- security_context_t econ = NULL;
+ char *econ = NULL;
int refcount;
int rc;
bool rollback = false;
@@ -1440,7 +1440,7 @@ virSecuritySELinuxFSetFilecon(int fd, char *tcon)
/* Set fcon to the appropriate label for path and mode, or return -1. */
static int
getContext(virSecurityManagerPtr mgr G_GNUC_UNUSED,
- const char *newpath, mode_t mode, security_context_t *fcon)
+ const char *newpath, mode_t mode, char **fcon)
{
virSecuritySELinuxDataPtr data = virSecurityManagerGetPrivateData(mgr);
@@ -1457,7 +1457,7 @@ virSecuritySELinuxRestoreFileLabel(virSecurityManagerPtr mgr,
{
bool privileged = virSecurityManagerGetPrivileged(mgr);
struct stat buf;
- security_context_t fcon = NULL;
+ char *fcon = NULL;
char *newpath = NULL;
int rc;
int ret = -1;
@@ -2972,7 +2972,7 @@ virSecuritySELinuxSetDaemonSocketLabel(virSecurityManagerPtr mgr G_GNUC_UNUSED,
{
/* TODO: verify DOI */
virSecurityLabelDefPtr secdef;
- security_context_t scon = NULL;
+ char *scon = NULL;
char *str = NULL;
int rc = -1;
@@ -3259,7 +3259,7 @@ virSecuritySELinuxSetTapFDLabel(virSecurityManagerPtr mgr,
int fd)
{
struct stat buf;
- security_context_t fcon = NULL;
+ char *fcon = NULL;
virSecurityLabelDefPtr secdef;
char *str = NULL, *proc = NULL, *fd_path = NULL;
int rc = -1;
diff --git a/src/storage/storage_util.c b/src/storage/storage_util.c
index 1ec1d13..4c67d3a 100644
--- a/src/storage/storage_util.c
+++ b/src/storage/storage_util.c
@@ -1818,7 +1818,7 @@ virStorageBackendUpdateVolTargetInfoFD(virStorageSourcePtr target,
struct stat *sb)
{
#if WITH_SELINUX
- security_context_t filecon = NULL;
+ char *filecon = NULL;
#endif
if (virStorageSourceUpdateBackingSizes(target, fd, sb) < 0)
diff --git a/src/util/viridentity.c b/src/util/viridentity.c
index 8cc2db2..2cb9042 100644
--- a/src/util/viridentity.c
+++ b/src/util/viridentity.c
@@ -157,7 +157,7 @@ virIdentityPtr virIdentityGetSystem(void)
unsigned long long startTime;
g_autoptr(virIdentity) ret = NULL;
#if WITH_SELINUX
- security_context_t con;
+ char *con;
#endif
if (!(ret = virIdentityNew()))
diff --git a/tests/securityselinuxhelper.c b/tests/securityselinuxhelper.c
index f89224c..63b5726 100644
--- a/tests/securityselinuxhelper.c
+++ b/tests/securityselinuxhelper.c
@@ -58,7 +58,7 @@ static struct selabel_handle *(*real_selabel_open)(unsigned int backend,
unsigned nopts);
static void (*real_selabel_close)(struct selabel_handle *handle);
static int (*real_selabel_lookup_raw)(struct selabel_handle *handle,
- security_context_t *con,
+ char **con,
const char *key,
int type);
@@ -94,7 +94,7 @@ static void init_syms(void)
* the virt_use_nfs bool is set.
*/
-int getcon_raw(security_context_t *context)
+int getcon_raw(char **context)
{
if (!is_selinux_enabled()) {
errno = EINVAL;
@@ -109,12 +109,12 @@ int getcon_raw(security_context_t *context)
return 0;
}
-int getcon(security_context_t *context)
+int getcon(char **context)
{
return getcon_raw(context);
}
-int getpidcon_raw(pid_t pid, security_context_t *context)
+int getpidcon_raw(pid_t pid, char **context)
{
if (!is_selinux_enabled()) {
errno = EINVAL;
@@ -134,7 +134,7 @@ int getpidcon_raw(pid_t pid, security_context_t *context)
return 0;
}
-int getpidcon(pid_t pid, security_context_t *context)
+int getpidcon(pid_t pid, char **context)
{
return getpidcon_raw(pid, context);
}
@@ -170,7 +170,7 @@ int setfilecon(const char *path, const char *con)
return setfilecon_raw(path, con);
}
-int getfilecon_raw(const char *path, security_context_t *con)
+int getfilecon_raw(const char *path, char **con)
{
char *constr = NULL;
ssize_t len = getxattr(path, "user.libvirt.selinux",
@@ -194,7 +194,7 @@ int getfilecon_raw(const char *path, security_context_t *con)
}
-int getfilecon(const char *path, security_context_t *con)
+int getfilecon(const char *path, char **con)
{
return getfilecon_raw(path, con);
}
@@ -315,7 +315,7 @@ void selabel_close(struct selabel_handle *handle)
}
int selabel_lookup_raw(struct selabel_handle *handle,
- security_context_t *con,
+ char **con,
const char *key,
int type)
{
diff --git a/tests/securityselinuxlabeltest.c b/tests/securityselinuxlabeltest.c
index 3040a36..50b447c 100644
--- a/tests/securityselinuxlabeltest.c
+++ b/tests/securityselinuxlabeltest.c
@@ -252,7 +252,7 @@ static int
testSELinuxCheckLabels(testSELinuxFile *files, size_t nfiles)
{
size_t i;
- security_context_t ctx;
+ char *ctx;
for (i = 0; i < nfiles; i++) {
ctx = NULL;
@@ -360,7 +360,7 @@ mymain(void)
if (virTestRun("Labelling " # name, testSELinuxLabeling, name) < 0) \
ret = -1;
- setcon((security_context_t)"system_r:system_u:libvirtd_t:s0:c0.c1023");
+ setcon("system_r:system_u:libvirtd_t:s0:c0.c1023");
DO_TEST_LABELING("disks");
DO_TEST_LABELING("kernel");
diff --git a/tests/securityselinuxtest.c b/tests/securityselinuxtest.c
index 6c8314d..3f069c2 100644
--- a/tests/securityselinuxtest.c
+++ b/tests/securityselinuxtest.c
@@ -217,7 +217,7 @@ testSELinuxGenLabel(const void *opaque)
context_t con = NULL;
context_t imgcon = NULL;
- if (setcon_raw((security_context_t)data->pidcon) < 0) {
+ if (setcon_raw(data->pidcon) < 0) {
perror("Cannot set process security context");
return -1;
}
diff --git a/tests/viridentitytest.c b/tests/viridentitytest.c
index 3f87af1..9a8c891 100644
--- a/tests/viridentitytest.c
+++ b/tests/viridentitytest.c
@@ -120,7 +120,7 @@ static int testIdentityGetSystem(const void *data)
static int testSetFakeSELinuxContext(const void *data G_GNUC_UNUSED)
{
#if WITH_SELINUX
- return setcon_raw((security_context_t)data);
+ return setcon_raw(data);
#else
VIR_DEBUG("libvirt not compiled with SELinux, skipping this test");
return EXIT_AM_SKIP;
--
2.25.4

View File

@ -1,34 +0,0 @@
From 432afe3f14418ea5d2d69e62d678ef5bb08caaa1 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Wed, 15 Apr 2020 11:55:43 +0800
Subject: cgroup: cleanup eventParams when virTypedParamsAddULLong failed
Function virTypedParamsAddULLong use realloc to gain memory,
and doesn't free it when failed. so we need free eventParams to
prevent a memory leak.
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/qemu/qemu_cgroup.c | 5 ++++-
1 file changed, 4 insertions(+), 1 deletion(-)
diff --git a/src/qemu/qemu_cgroup.c b/src/qemu/qemu_cgroup.c
index c0e30f6..057f871 100644
--- a/src/qemu/qemu_cgroup.c
+++ b/src/qemu/qemu_cgroup.c
@@ -904,8 +904,11 @@ qemuSetupCpuCgroup(virDomainObjPtr vm)
if (virTypedParamsAddULLong(&eventParams, &eventNparams,
&eventMaxparams,
VIR_DOMAIN_TUNABLE_CPU_CPU_SHARES,
- val) < 0)
+ val) < 0) {
+ if (eventParams)
+ virTypedParamsFree(eventParams, eventNparams);
return -1;
+ }
event = virDomainEventTunableNewFromObj(vm, eventParams, eventNparams);
}
--
2.23.0

View File

@ -1,53 +0,0 @@
From cec735e6f4001caa0395eddc9d8a0fe18e97f9eb Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Tue, 4 Aug 2020 08:40:36 +0000
Subject: [PATCH] conf: Don't format http cookies unless
VIR_DOMAIN_DEF_FORMAT_SECURE is used
Starting with 3b076391befc3fe72deb0c244ac6c2b4c100b410
(v6.1.0-122-g3b076391be) we support http cookies. Since they may contain
somewhat sensitive information we should not format them into the XML
unless VIR_DOMAIN_DEF_FORMAT_SECURE is asserted.
Reported-by: Han Han <hhan@redhat.com>
Signed-off-by: Peter Krempa <pkrempa@redhat.com>
Reviewed-by: Erik Skultety <eskultet@redhat.com>
(cherry-picked from commit a5b064bf4b17a9884d7d361733737fb614ad8979)
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/conf/domain_conf.c | 8 ++++++--
1 file changed, 6 insertions(+), 2 deletions(-)
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index 914e03c..cf93a59 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -24565,11 +24565,15 @@ virDomainSourceDefFormatSeclabel(virBufferPtr buf,
static void
virDomainDiskSourceFormatNetworkCookies(virBufferPtr buf,
- virStorageSourcePtr src)
+ virStorageSourcePtr src,
+ unsigned int flags)
{
g_auto(virBuffer) childBuf = VIR_BUFFER_INIT_CHILD(buf);
size_t i;
+ if (!(flags & VIR_DOMAIN_DEF_FORMAT_SECURE))
+ return;
+
for (i = 0; i < src->ncookies; i++) {
virBufferEscapeString(&childBuf, "<cookie name='%s'>", src->cookies[i]->name);
virBufferEscapeString(&childBuf, "%s</cookie>\n", src->cookies[i]->value);
@@ -24630,7 +24634,7 @@ virDomainDiskSourceFormatNetwork(virBufferPtr attrBuf,
virTristateBoolTypeToString(src->sslverify));
}
- virDomainDiskSourceFormatNetworkCookies(childBuf, src);
+ virDomainDiskSourceFormatNetworkCookies(childBuf, src, flags);
if (src->readahead)
virBufferAsprintf(childBuf, "<readahead size='%llu'/>\n", src->readahead);
--
2.25.4

View File

@ -1,33 +0,0 @@
From fc8c41dbb52eb9ce3ee36680ecb53a41f4146610 Mon Sep 17 00:00:00 2001
From: Jiri Denemark <jdenemar@redhat.com>
Date: Thu, 11 Jun 2020 13:53:27 +0200
Subject: [PATCH] conf: Increase cpuset length limit for CPU pinning
Domains are now allowed to be pinned to host CPUs with IDs up to 16383.
The new limit is as arbitrary as the old one. It's just bigger.
cherry-pick from commit: e728ffba5119cfb1488aa7363fef596940449f50
Signed-off-by: Jiri Denemark <jdenemar@redhat.com>
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
Signed-off-by: Jin Yan <jinyan12@huawei.com>
---
src/conf/domain_conf.h | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
index a40773a..16e6253 100644
--- a/src/conf/domain_conf.h
+++ b/src/conf/domain_conf.h
@@ -2241,7 +2241,7 @@ struct _virDomainHugePage {
unsigned long long size; /* hugepage size in KiB */
};
-#define VIR_DOMAIN_CPUMASK_LEN 1024
+#define VIR_DOMAIN_CPUMASK_LEN 16384
struct _virDomainIOThreadIDDef {
bool autofill;
--
1.8.3.1

View File

@ -1,87 +0,0 @@
From 04292a5ad4cb9741fa8f9687befd1e1c644043a6 Mon Sep 17 00:00:00 2001
From: Jiahui Cen <cenjiahui@huawei.com>
Date: Thu, 18 Mar 2021 15:14:20 +0800
Subject: [PATCH] libvirt/conf: Set default values of retry fileds
Currently the default values of retry_interval and retry_timeout are set
to -1, when 'driver' option exists without retry fileds. It conflicts
with the default values when the 'driver' option does not exist.
So let's set default values of retry_interval and retry_timeout to 0 when
retry policy is not enabled.
Signed-off-by: Jiahui Cen <cenjiahui@huawei.com>
---
src/conf/domain_conf.c | 18 ++++++++++++------
src/conf/domain_conf.h | 3 +++
2 files changed, 15 insertions(+), 6 deletions(-)
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index 5c469cedd0..a4e9b3290c 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -10186,6 +10186,7 @@ virDomainDiskDefDriverParseXML(virDomainDiskDefPtr def,
xmlNodePtr cur)
{
g_autofree char *tmp = NULL;
+ bool retry_enabled = false;
def->driverName = virXMLPropString(cur, "name");
@@ -10214,28 +10215,33 @@ virDomainDiskDefDriverParseXML(virDomainDiskDefPtr def,
}
VIR_FREE(tmp);
- def->retry_interval = -1;
+ retry_enabled = (def->error_policy == VIR_DOMAIN_DISK_ERROR_POLICY_RETRY) ||
+ (def->rerror_policy == VIR_DOMAIN_DISK_ERROR_POLICY_RETRY);
+
if ((tmp = virXMLPropString(cur, "retry_interval")) &&
- ((def->error_policy != VIR_DOMAIN_DISK_ERROR_POLICY_RETRY &&
- def->rerror_policy != VIR_DOMAIN_DISK_ERROR_POLICY_RETRY) ||
+ (!retry_enabled ||
(virStrToLong_l(tmp, NULL, 10, &def->retry_interval) < 0) ||
(def->retry_interval < 0))) {
virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
_("unknown disk retry interval '%s'"), tmp);
return -1;
}
+ if (retry_enabled && !tmp) {
+ def->retry_interval = VIR_DOMAIN_DISK_DEFAULT_RETRY_INTERVAL;
+ }
VIR_FREE(tmp);
- def->retry_timeout = -1;
if ((tmp = virXMLPropString(cur, "retry_timeout")) &&
- ((def->error_policy != VIR_DOMAIN_DISK_ERROR_POLICY_RETRY &&
- def->rerror_policy != VIR_DOMAIN_DISK_ERROR_POLICY_RETRY) ||
+ (!retry_enabled ||
(virStrToLong_l(tmp, NULL, 10, &def->retry_timeout) < 0) ||
(def->retry_timeout < 0))) {
virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
_("unknown disk retry interval '%s'"), tmp);
return -1;
}
+ if (retry_enabled && !tmp) {
+ def->retry_timeout = VIR_DOMAIN_DISK_DEFAULT_RETRY_TIMEOUT;
+ }
VIR_FREE(tmp);
if ((tmp = virXMLPropString(cur, "io")) &&
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
index 86a86d3090..ccee986849 100644
--- a/src/conf/domain_conf.h
+++ b/src/conf/domain_conf.h
@@ -523,6 +523,9 @@ typedef enum {
} virDomainMemoryAllocation;
+#define VIR_DOMAIN_DISK_DEFAULT_RETRY_INTERVAL 1000
+#define VIR_DOMAIN_DISK_DEFAULT_RETRY_TIMEOUT 0
+
/* Stores the virtual disk configuration */
struct _virDomainDiskDef {
virStorageSourcePtr src; /* non-NULL. XXX Allow NULL for empty cdrom? */
--
2.27.0

View File

@ -1,100 +0,0 @@
From 657c7f5d79fe43823ffb4d46e244bea15a65baf6 Mon Sep 17 00:00:00 2001
From: Laine Stump <laine@redhat.com>
Date: Thu, 18 Jun 2020 12:49:09 -0400
Subject: [PATCH 1/6] conf, vmx: check for OOM after calling xmlBufferCreate()
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Although libvirt itself uses g_malloc0() and friends, which exit when
there isn't enouogh memory, libxml2 uses standard malloc(), which just
returns NULL on OOM - this means we must check for NULL on return from
any libxml2 functions that allocate memory.
xmlBufferCreate(), for example, might return NULL, and we don't always
check for it. This patch adds checks where it isn't already done.
(NB: Although libxml2 has a provision for changing behavior on OOM (by
calling xmlMemSetup() to change what functions are used to
allocating/freeing memory), we can't use that, since parts of libvirt
code end up in libvirt.so, which is linked and called directly by
applications that may themselves use libxml2 (and may have already set
their own alternate malloc()), e.g. drivers like esx which live totally
in the library rather than a separate process.)
cherry pick from: b7a92bce070fd57844a59bf8b1c30cb4ef4f3acd
Signed-off-by: Laine Stump <laine@redhat.com>
Reviewed-by: Ján Tomko <jtomko@redhat.com>
---
src/conf/domain_conf.c | 6 +++++-
src/conf/network_conf.c | 6 +++++-
src/vmx/vmx.c | 11 +++++++----
3 files changed, 17 insertions(+), 6 deletions(-)
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index 914e03c..37c785a 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -29022,7 +29022,11 @@ virDomainDefFormatInternalSetRootName(virDomainDefPtr def,
* Thankfully, libxml maps what looks like globals into
* thread-local uses, so we are thread-safe. */
xmlIndentTreeOutput = 1;
- xmlbuf = xmlBufferCreate();
+ if (!(xmlbuf = xmlBufferCreate())) {
+ virReportOOMError();
+ goto error;
+ }
+
if (xmlNodeDump(xmlbuf, def->metadata->doc, def->metadata,
virBufferGetIndent(buf) / 2, 1) < 0) {
xmlBufferFree(xmlbuf);
diff --git a/src/conf/network_conf.c b/src/conf/network_conf.c
index 819b645..c379042 100644
--- a/src/conf/network_conf.c
+++ b/src/conf/network_conf.c
@@ -2478,7 +2478,11 @@ virNetworkDefFormatBuf(virBufferPtr buf,
* Thankfully, libxml maps what looks like globals into
* thread-local uses, so we are thread-safe. */
xmlIndentTreeOutput = 1;
- xmlbuf = xmlBufferCreate();
+ if (!(xmlbuf = xmlBufferCreate())) {
+ virReportOOMError();
+ return -1;
+ }
+
if (xmlNodeDump(xmlbuf, def->metadata->doc, def->metadata,
virBufferGetIndent(buf) / 2, 1) < 0) {
xmlBufferFree(xmlbuf);
diff --git a/src/vmx/vmx.c b/src/vmx/vmx.c
index b1fd118..fbc8366 100644
--- a/src/vmx/vmx.c
+++ b/src/vmx/vmx.c
@@ -697,8 +697,8 @@ virVMXConvertToUTF8(const char *encoding, const char *string)
{
char *result = NULL;
xmlCharEncodingHandlerPtr handler;
- xmlBufferPtr input;
- xmlBufferPtr utf8;
+ xmlBufferPtr input = NULL;
+ xmlBufferPtr utf8 = NULL;
handler = xmlFindCharEncodingHandler(encoding);
@@ -708,8 +708,11 @@ virVMXConvertToUTF8(const char *encoding, const char *string)
return NULL;
}
- input = xmlBufferCreateStatic((char *)string, strlen(string));
- utf8 = xmlBufferCreate();
+ if (!(input = xmlBufferCreateStatic((char *)string, strlen(string))) ||
+ !(utf8 = xmlBufferCreate())) {
+ virReportOOMError();
+ goto cleanup;
+ }
if (xmlCharEncInFunc(handler, utf8, input) < 0) {
virReportError(VIR_ERR_INTERNAL_ERROR,
--
1.8.3.1

View File

@ -1,44 +0,0 @@
From 1e6875a732d896138d3bc2351e5284d1ad13dd59 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Wed, 20 May 2020 02:33:27 -0400
Subject: [PATCH] cpu/aarch64: enable host-model cpu for AArch64 architecture
The 'host-model' cpu is support by kunpeng-v virtualization
suit, skip hypervisor host-model externsion checking on AArch64
architecture.
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/qemu/qemu_command.c | 2 +-
tests/qemuxml2argvtest.c | 2 --
2 files changed, 1 insertion(+), 3 deletions(-)
diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index 2f0e919..2f65b8d 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -6582,7 +6582,7 @@ qemuBuildCpuModelArgStr(virQEMUDriverPtr driver,
break;
}
- if ((ARCH_IS_S390(def->os.arch) || ARCH_IS_ARM(def->os.arch)) &&
+ if (ARCH_IS_S390(def->os.arch) &&
cpu->features &&
!virQEMUCapsGet(qemuCaps, QEMU_CAPS_QUERY_CPU_MODEL_EXPANSION)) {
virReportError(VIR_ERR_INTERNAL_ERROR,
diff --git a/tests/qemuxml2argvtest.c b/tests/qemuxml2argvtest.c
index 596dd7a..2153e44 100644
--- a/tests/qemuxml2argvtest.c
+++ b/tests/qemuxml2argvtest.c
@@ -2736,8 +2736,6 @@ mymain(void)
DO_TEST("aarch64-noacpi-nouefi", NONE);
DO_TEST_PARSE_ERROR("aarch64-acpi-nouefi", NONE);
- /* QEMU 4.0.0 didn't have support for aarch64 CPU features */
- DO_TEST_CAPS_ARCH_VER_FAILURE("aarch64-features-sve", "aarch64", "4.0.0");
/* aarch64 doesn't support the same CPU features as x86 */
DO_TEST_CAPS_ARCH_LATEST_FAILURE("aarch64-features-wrong", "aarch64");
/* Can't enable vector lengths when SVE is overall disabled */
--
1.8.3.1

View File

@ -1,51 +0,0 @@
From efde450d2d0648475cde04f04f5e26c1a006c226 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Fri, 17 Apr 2020 14:40:27 +0800
Subject: cpu/arm: add cpu data free function to virCPUarmDataFree
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu_arm.c | 20 ++++++++++++++++++++
1 file changed, 20 insertions(+)
diff --git a/src/cpu/cpu_arm.c b/src/cpu/cpu_arm.c
index ee58021..230cd27 100644
--- a/src/cpu/cpu_arm.c
+++ b/src/cpu/cpu_arm.c
@@ -61,6 +61,25 @@ virCPUarmFeatureFree(virCPUarmFeaturePtr feature)
G_DEFINE_AUTOPTR_CLEANUP_FUNC(virCPUarmFeature, virCPUarmFeatureFree);
+static void
+virCPUarmDataClear(virCPUarmData *data)
+{
+ if (!data)
+ return;
+
+ VIR_FREE(data->features);
+}
+
+static void
+virCPUarmDataFree(virCPUDataPtr cpuData)
+{
+ if (!cpuData)
+ return;
+
+ virCPUarmDataClear(&cpuData->data.arm);
+ VIR_FREE(cpuData);
+}
+
typedef struct _virCPUarmMap virCPUarmMap;
typedef virCPUarmMap *virCPUarmMapPtr;
struct _virCPUarmMap {
@@ -259,6 +278,7 @@ struct cpuArchDriver cpuDriverArm = {
.compare = virCPUarmCompare,
.decode = NULL,
.encode = NULL,
+ .dataFree = virCPUarmDataFree,
.baseline = virCPUarmBaseline,
.update = virCPUarmUpdate,
.validateFeatures = virCPUarmValidateFeatures,
--
2.23.0

View File

@ -1,275 +0,0 @@
From c69a629367b0e9bfa1a034301a4c3f88ad080586 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Sat, 18 Apr 2020 11:16:13 +0800
Subject: cpu/arm: add decode function
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu_arm.c | 150 ++++++++++++++++++++++++++++++++++--------
src/cpu_map/index.xml | 3 -
2 files changed, 122 insertions(+), 31 deletions(-)
diff --git a/src/cpu/cpu_arm.c b/src/cpu/cpu_arm.c
index d85f111..eb9b1c9 100644
--- a/src/cpu/cpu_arm.c
+++ b/src/cpu/cpu_arm.c
@@ -55,7 +55,6 @@ virCPUarmFeatureFree(virCPUarmFeaturePtr feature)
return;
g_free(feature->name);
-
g_free(feature);
}
@@ -80,6 +79,8 @@ virCPUarmDataFree(virCPUDataPtr cpuData)
g_free(cpuData);
}
+G_DEFINE_AUTOPTR_CLEANUP_FUNC(virCPUData, virCPUarmDataFree);
+
typedef struct _virCPUarmVendor virCPUarmVendor;
typedef virCPUarmVendor *virCPUarmVendorPtr;
struct _virCPUarmVendor {
@@ -103,6 +104,8 @@ virCPUarmVendorFree(virCPUarmVendorPtr vendor)
VIR_FREE(vendor);
}
+G_DEFINE_AUTOPTR_CLEANUP_FUNC(virCPUarmVendor, virCPUarmVendorFree);
+
typedef struct _virCPUarmModel virCPUarmModel;
typedef virCPUarmModel *virCPUarmModelPtr;
struct _virCPUarmModel {
@@ -175,6 +178,38 @@ virCPUarmMapFree(virCPUarmMapPtr map)
G_DEFINE_AUTOPTR_CLEANUP_FUNC(virCPUarmMap, virCPUarmMapFree);
+static virCPUarmVendorPtr
+virCPUarmVendorFindByID(virCPUarmMapPtr map,
+ unsigned long vendor_id)
+{
+ size_t i;
+
+ for (i = 0; i < map->vendors->len; i++) {
+ virCPUarmVendorPtr vendor = g_ptr_array_index(map->vendors, i);
+
+ if (vendor->value == vendor_id)
+ return vendor;
+ }
+
+ return NULL;
+}
+
+static virCPUarmVendorPtr
+virCPUarmVendorFindByName(virCPUarmMapPtr map,
+ const char *name)
+{
+ size_t i;
+
+ for (i = 0; i < map->vendors->len; i++) {
+ virCPUarmVendorPtr vendor = g_ptr_array_index(map->vendors, i);
+
+ if (STREQ(vendor->name, name))
+ return vendor;
+ }
+
+ return NULL;
+}
+
static virCPUarmFeaturePtr
virCPUarmMapFeatureFind(virCPUarmMapPtr map,
const char *name)
@@ -213,36 +248,43 @@ virCPUarmMapFeatureParse(xmlXPathContextPtr ctxt G_GNUC_UNUSED,
return 0;
}
-static virCPUarmVendorPtr
-virCPUarmVendorFindByID(virCPUarmMapPtr map,
- unsigned long vendor_id)
+static int
+armCpuDataParseFeatures(virCPUDefPtr cpu,
+ const virCPUarmData *cpuData)
{
+ int ret = -1;
size_t i;
+ char **features;
- for (i = 0; i < map->vendors->len; i++) {
- virCPUarmVendorPtr vendor = g_ptr_array_index(map->vendors, i);
+ if (!cpu || !cpuData)
+ return ret;
- if (vendor->value == vendor_id)
- return vendor;
- }
+ if (!(features = virStringSplitCount(cpuData->features, " ",
+ 0, &cpu->nfeatures)))
+ return ret;
- return NULL;
-}
+ if (cpu->nfeatures) {
+ if (VIR_ALLOC_N(cpu->features, cpu->nfeatures) < 0)
+ goto error;
-static virCPUarmVendorPtr
-virCPUarmVendorFindByName(virCPUarmMapPtr map,
- const char *name)
-{
- size_t i;
+ for (i = 0; i < cpu->nfeatures; i++) {
+ cpu->features[i].policy = VIR_CPU_FEATURE_REQUIRE;
+ cpu->features[i].name = g_strdup(features[i]);
+ }
+ }
- for (i = 0; i < map->vendors->len; i++) {
- virCPUarmVendorPtr vendor = g_ptr_array_index(map->vendors, i);
+ ret = 0;
- if (STREQ(vendor->name, name))
- return vendor;
- }
+cleanup:
+ virStringListFree(features);
+ return ret;
- return NULL;
+error:
+ for (i = 0; i < cpu->nfeatures; i++)
+ VIR_FREE(cpu->features[i].name);
+ VIR_FREE(cpu->features);
+ cpu->nfeatures = 0;
+ goto cleanup;
}
static int
@@ -252,7 +294,6 @@ virCPUarmVendorParse(xmlXPathContextPtr ctxt,
{
virCPUarmMapPtr map = (virCPUarmMapPtr)data;
g_autoptr(virCPUarmVendor) vendor = NULL;
- int ret = -1;
if (virCPUarmVendorFindByName(map, name)) {
virReportError(VIR_ERR_INTERNAL_ERROR,
@@ -289,7 +330,7 @@ virCPUarmModelFindByPVR(virCPUarmMapPtr map,
for (i = 0; i < map->models->len; i++) {
virCPUarmModelPtr model = g_ptr_array_index(map->models, i);
- if (STREQ(model->pvr, pvr))
+ if (model->data.pvr == pvr)
return model;
}
@@ -299,7 +340,7 @@ virCPUarmModelFindByPVR(virCPUarmMapPtr map,
static virCPUarmModelPtr
virCPUarmModelFindByName(virCPUarmMapPtr map,
- const char *name)
+ const char *name)
{
size_t i;
@@ -321,7 +362,6 @@ virCPUarmModelParse(xmlXPathContextPtr ctxt,
virCPUarmMapPtr map = (virCPUarmMapPtr)data;
g_autoptr(virCPUarmModel) model = NULL;
char *vendor = NULL;
- int ret = -1;
if (virCPUarmModelFindByName(map, name)) {
virReportError(VIR_ERR_INTERNAL_ERROR,
@@ -404,6 +444,60 @@ virCPUarmGetMap(void)
return cpuMap;
}
+static int
+virCPUarmDecode(virCPUDefPtr cpu,
+ const virCPUarmData *cpuData,
+ virDomainCapsCPUModelsPtr models)
+{
+ virCPUarmMapPtr map;
+ virCPUarmModelPtr model;
+ virCPUarmVendorPtr vendor = NULL;
+
+ if (!cpuData || !(map = virCPUarmGetMap()))
+ return -1;
+
+ if (!(model = virCPUarmModelFindByPVR(map, cpuData->pvr))) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ _("Cannot find CPU model with PVR 0x%03lx"),
+ cpuData->pvr);
+ return -1;
+ }
+
+ if (!virCPUModelIsAllowed(model->name, models)) {
+ virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
+ _("CPU model %s is not supported by hypervisor"),
+ model->name);
+ return -1;
+ }
+
+ cpu->model = g_strdup(model->name);
+
+ if (cpuData->vendor_id &&
+ !(vendor = virCPUarmVendorFindByID(map, cpuData->vendor_id))) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ _("Cannot find CPU vendor with vendor id 0x%02lx"),
+ cpuData->vendor_id);
+ return -1;
+ }
+
+ if (vendor)
+ cpu->vendor = g_strdup(vendor->name);
+
+ if (cpuData->features &&
+ armCpuDataParseFeatures(cpu, cpuData) < 0)
+ return -1;
+
+ return 0;
+}
+
+static int
+virCPUarmDecodeCPUData(virCPUDefPtr cpu,
+ const virCPUData *data,
+ virDomainCapsCPUModelsPtr models)
+{
+ return virCPUarmDecode(cpu, &data->data.arm, models);
+}
+
static int
virCPUarmUpdate(virCPUDefPtr guest,
const virCPUDef *host)
@@ -432,7 +526,7 @@ virCPUarmUpdate(virCPUDefPtr guest,
guest->match = VIR_CPU_MATCH_EXACT;
ret = 0;
- cleanup:
+cleanup:
virCPUDefFree(updated);
return ret;
}
@@ -493,7 +587,7 @@ struct cpuArchDriver cpuDriverArm = {
.arch = archs,
.narch = G_N_ELEMENTS(archs),
.compare = virCPUarmCompare,
- .decode = NULL,
+ .decode = virCPUarmDecodeCPUData,
.encode = NULL,
.dataFree = virCPUarmDataFree,
.baseline = virCPUarmBaseline,
diff --git a/src/cpu_map/index.xml b/src/cpu_map/index.xml
index 2e78834..985af86 100644
--- a/src/cpu_map/index.xml
+++ b/src/cpu_map/index.xml
@@ -86,9 +86,6 @@
<arch name='arm'>
<include filename='arm_features.xml'/>
- </arch>
-
- <arch name='arm'>
<include filename="arm_vendors.xml"/>
<!-- ARM-based CPU models -->
--
2.23.0

View File

@ -1,287 +0,0 @@
From a0574d45603010761d3f3034f97457fda94d2266 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Fri, 17 Apr 2020 18:13:32 +0800
Subject: cpu/arm: add load cpu map parse function
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu_arm.c | 223 +++++++++++++++++++++++++++++++++++++++++++++-
1 file changed, 220 insertions(+), 3 deletions(-)
diff --git a/src/cpu/cpu_arm.c b/src/cpu/cpu_arm.c
index 230cd27..d85f111 100644
--- a/src/cpu/cpu_arm.c
+++ b/src/cpu/cpu_arm.c
@@ -67,7 +67,7 @@ virCPUarmDataClear(virCPUarmData *data)
if (!data)
return;
- VIR_FREE(data->features);
+ g_free(data->features);
}
static void
@@ -77,12 +77,64 @@ virCPUarmDataFree(virCPUDataPtr cpuData)
return;
virCPUarmDataClear(&cpuData->data.arm);
- VIR_FREE(cpuData);
+ g_free(cpuData);
}
+typedef struct _virCPUarmVendor virCPUarmVendor;
+typedef virCPUarmVendor *virCPUarmVendorPtr;
+struct _virCPUarmVendor {
+ char *name;
+ unsigned long value;
+};
+
+static virCPUarmVendorPtr
+virCPUarmVendorNew(void)
+{
+ return g_new0(virCPUarmVendor, 1);
+}
+
+static void
+virCPUarmVendorFree(virCPUarmVendorPtr vendor)
+{
+ if (!vendor)
+ return;
+
+ g_free(vendor->name);
+ VIR_FREE(vendor);
+}
+
+typedef struct _virCPUarmModel virCPUarmModel;
+typedef virCPUarmModel *virCPUarmModelPtr;
+struct _virCPUarmModel {
+ char *name;
+ virCPUarmVendorPtr vendor;
+ virCPUarmData data;
+};
+
+static virCPUarmModelPtr
+virCPUarmModelNew(void)
+{
+ return g_new0(virCPUarmModel, 1);
+}
+
+static void
+virCPUarmModelFree(virCPUarmModelPtr model)
+{
+ if (!model)
+ return;
+
+ virCPUarmDataClear(&model->data);
+ g_free(model->name);
+ g_free(model);
+}
+
+G_DEFINE_AUTOPTR_CLEANUP_FUNC(virCPUarmModel, virCPUarmModelFree);
+
typedef struct _virCPUarmMap virCPUarmMap;
typedef virCPUarmMap *virCPUarmMapPtr;
struct _virCPUarmMap {
+ GPtrArray *vendors;
+ GPtrArray *models;
GPtrArray *features;
};
@@ -93,6 +145,14 @@ virCPUarmMapNew(void)
map = g_new0(virCPUarmMap, 1);
+ map->vendors = g_ptr_array_new();
+ g_ptr_array_set_free_func(map->vendors,
+ (GDestroyNotify) virCPUarmVendorFree);
+
+ map->models = g_ptr_array_new();
+ g_ptr_array_set_free_func(map->models,
+ (GDestroyNotify) virCPUarmModelFree);
+
map->features = g_ptr_array_new();
g_ptr_array_set_free_func(map->features,
(GDestroyNotify) virCPUarmFeatureFree);
@@ -106,6 +166,8 @@ virCPUarmMapFree(virCPUarmMapPtr map)
if (!map)
return;
+ g_ptr_array_free(map->vendors, TRUE);
+ g_ptr_array_free(map->models, TRUE);
g_ptr_array_free(map->features, TRUE);
g_free(map);
@@ -151,6 +213,161 @@ virCPUarmMapFeatureParse(xmlXPathContextPtr ctxt G_GNUC_UNUSED,
return 0;
}
+static virCPUarmVendorPtr
+virCPUarmVendorFindByID(virCPUarmMapPtr map,
+ unsigned long vendor_id)
+{
+ size_t i;
+
+ for (i = 0; i < map->vendors->len; i++) {
+ virCPUarmVendorPtr vendor = g_ptr_array_index(map->vendors, i);
+
+ if (vendor->value == vendor_id)
+ return vendor;
+ }
+
+ return NULL;
+}
+
+static virCPUarmVendorPtr
+virCPUarmVendorFindByName(virCPUarmMapPtr map,
+ const char *name)
+{
+ size_t i;
+
+ for (i = 0; i < map->vendors->len; i++) {
+ virCPUarmVendorPtr vendor = g_ptr_array_index(map->vendors, i);
+
+ if (STREQ(vendor->name, name))
+ return vendor;
+ }
+
+ return NULL;
+}
+
+static int
+virCPUarmVendorParse(xmlXPathContextPtr ctxt,
+ const char *name,
+ void *data)
+{
+ virCPUarmMapPtr map = (virCPUarmMapPtr)data;
+ g_autoptr(virCPUarmVendor) vendor = NULL;
+ int ret = -1;
+
+ if (virCPUarmVendorFindByName(map, name)) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("CPU vendor %s already defined"), name);
+ return -1;
+ }
+
+ vendor = virCPUarmVendorNew();
+ vendor->name = g_strdup(name);
+
+ if (virXPathULongHex("string(@value)", ctxt, &vendor->value) < 0) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ "%s", _("Missing CPU vendor value"));
+ return -1;
+ }
+
+ if (virCPUarmVendorFindByID(map, vendor->value)) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("CPU vendor value 0x%2lx already defined"), vendor->value);
+ return -1;
+ }
+
+ g_ptr_array_add(map->vendors, g_steal_pointer(&vendor));
+
+ return 0;
+}
+
+static virCPUarmModelPtr
+virCPUarmModelFindByPVR(virCPUarmMapPtr map,
+ unsigned long pvr)
+{
+ size_t i;
+
+ for (i = 0; i < map->models->len; i++) {
+ virCPUarmModelPtr model = g_ptr_array_index(map->models, i);
+
+ if (STREQ(model->pvr, pvr))
+ return model;
+ }
+
+ return NULL;
+
+}
+
+static virCPUarmModelPtr
+virCPUarmModelFindByName(virCPUarmMapPtr map,
+ const char *name)
+{
+ size_t i;
+
+ for (i = 0; i < map->models->len; i++) {
+ virCPUarmModelPtr model = g_ptr_array_index(map->models, i);
+
+ if (STREQ(model->name, name))
+ return model;
+ }
+
+ return NULL;
+}
+
+static int
+virCPUarmModelParse(xmlXPathContextPtr ctxt,
+ const char *name,
+ void *data)
+{
+ virCPUarmMapPtr map = (virCPUarmMapPtr)data;
+ g_autoptr(virCPUarmModel) model = NULL;
+ char *vendor = NULL;
+ int ret = -1;
+
+ if (virCPUarmModelFindByName(map, name)) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("CPU model %s already defined"), name);
+ return -1;
+ }
+
+ model = virCPUarmModelNew();
+ model->name = g_strdup(name);
+
+ if (virXPathBoolean("boolean(./vendor)", ctxt)) {
+ vendor = virXPathString("string(./vendor/@name)", ctxt);
+ if (!vendor) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Invalid vendor element in CPU model %s"),
+ name);
+ return -1;
+ }
+
+ if (!(model->vendor = virCPUarmVendorFindByName(map, vendor))) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Unknown vendor %s referenced by CPU model %s"),
+ vendor, model->name);
+ return -1;
+ }
+ }
+
+ if (!virXPathBoolean("boolean(./pvr)", ctxt)) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Missing PVR information for CPU model %s"),
+ model->name);
+ return -1;
+ }
+
+ if (virXPathULongHex("string(./pvr/@value)", ctxt, &model->data.pvr) < 0) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Missing or invalid PVR value in CPU model %s"),
+ model->name);
+ return -1;
+ }
+
+ g_ptr_array_add(map->models, g_steal_pointer(&model));
+
+ return 0;
+}
+
static virCPUarmMapPtr
virCPUarmLoadMap(void)
{
@@ -158,7 +375,7 @@ virCPUarmLoadMap(void)
map = virCPUarmMapNew();
- if (cpuMapLoad("arm", NULL, virCPUarmMapFeatureParse, NULL, map) < 0)
+ if (cpuMapLoad("arm", virCPUarmVendorParse, virCPUarmMapFeatureParse, virCPUarmModelParse, map) < 0)
return NULL;
return g_steal_pointer(&map);
--
2.23.0

View File

@ -1,127 +0,0 @@
From 208c9f1eb9a06d2550b7b3cfe0172840925255d4 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Mon, 20 Apr 2020 17:29:17 +0800
Subject: cpu/arm: add virCPUarmGetHost implment
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu_arm.c | 86 +++++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 86 insertions(+)
diff --git a/src/cpu/cpu_arm.c b/src/cpu/cpu_arm.c
index eb9b1c9..78e604c 100644
--- a/src/cpu/cpu_arm.c
+++ b/src/cpu/cpu_arm.c
@@ -26,9 +26,15 @@
#include "cpu_map.h"
#include "virstring.h"
#include "virxml.h"
+#include "virfile.h"
#define VIR_FROM_THIS VIR_FROM_CPU
+static const char *sysinfoCpuinfo = "/proc/cpuinfo";
+
+#define CPUINFO sysinfoCpuinfo
+#define CPUINFO_FILE_LEN (1024*1024) /* 1MB limit for /proc/cpuinfo file */
+
static const virArch archs[] = {
VIR_ARCH_ARMV6L,
VIR_ARCH_ARMV7B,
@@ -531,6 +537,85 @@ cleanup:
return ret;
}
+static int
+armCpuDataFromCpuInfo(virCPUarmData *data)
+{
+ g_autofree char *str_vendor = NULL;
+ g_autofree char *str_pvr = NULL;
+ g_autofree char *outbuf = NULL;
+ char *eol = NULL;
+ const char *cur;
+
+ if (!data)
+ return -1;
+
+ if (virFileReadAll(CPUINFO, CPUINFO_FILE_LEN, &outbuf) < 0) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Failed to open %s"), CPUINFO);
+ return -1;
+ }
+
+ /* Account for format 'CPU implementer : XXXX' */
+ if ((cur = strstr(outbuf, "CPU implementer")) == NULL) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("there is no \"CPU implementer\" info in %s"), CPUINFO);
+ return -1;
+ }
+
+ cur = strchr(cur, ':') + 1;
+ eol = strchr(cur, '\n');
+ virSkipSpaces(&cur);
+ if (!eol || !(str_vendor = g_strndup(cur, eol - cur)) ||
+ virStrToLong_ul(str_vendor, NULL, 16, &data->vendor_id) < 0)
+ return -1;
+
+ /* Account for format 'CPU part : XXXX' */
+ if ((cur = strstr(outbuf, "CPU part")) == NULL) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("there is no \"CPU part\" info in %s"), CPUINFO);
+ return -1;
+ }
+
+ cur = strchr(cur, ':') + 1;
+ eol = strchr(cur, '\n');
+ virSkipSpaces(&cur);
+ if (!eol || !(str_pvr = g_strndup(cur, eol - cur)) ||
+ virStrToLong_ul(str_pvr, NULL, 16, &data->pvr) < 0)
+ return -1;
+
+ /* Account for format 'CPU Features : XXXX' */
+ if ((cur = strstr(outbuf, "Features")) == NULL) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("there is no \"Features\" info in %s"), CPUINFO);
+ return -1;
+ }
+ cur = strchr(cur, ':') + 1;
+ eol = strchr(cur, '\n');
+ virSkipSpaces(&cur);
+ if (eol && !(data->features = g_strndup(cur, eol - cur)))
+ return -1;
+
+ return 0;
+}
+
+static int
+virCPUarmGetHost(virCPUDefPtr cpu,
+ virDomainCapsCPUModelsPtr models)
+{
+ g_autoptr(virCPUData) cpuData = NULL;
+
+ if (virCPUarmDriverInitialize() < 0)
+ return -1;
+
+ if (!(cpuData = virCPUDataNew(archs[0])))
+ return -1;
+
+ if (armCpuDataFromCpuInfo(&cpuData->data.arm) < 0)
+ return -1;
+
+ return virCPUarmDecodeCPUData(cpu, cpuData, models);
+}
+
static virCPUDefPtr
virCPUarmBaseline(virCPUDefPtr *cpus,
@@ -590,6 +675,7 @@ struct cpuArchDriver cpuDriverArm = {
.decode = virCPUarmDecodeCPUData,
.encode = NULL,
.dataFree = virCPUarmDataFree,
+ .getHost = virCPUarmGetHost,
.baseline = virCPUarmBaseline,
.update = virCPUarmUpdate,
.validateFeatures = virCPUarmValidateFeatures,
--
2.23.0

View File

@ -1,216 +0,0 @@
From 4606782bde2a6e75e88d782fc58e5db5365502c2 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Mon, 20 Apr 2020 19:17:56 +0800
Subject: cpu/arm: implment cpu baseline function
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu_arm.c | 178 ++++++++++++++++++++++++++++++++++++++++++++--
1 file changed, 174 insertions(+), 4 deletions(-)
diff --git a/src/cpu/cpu_arm.c b/src/cpu/cpu_arm.c
index 78e604c..a7c9523 100644
--- a/src/cpu/cpu_arm.c
+++ b/src/cpu/cpu_arm.c
@@ -616,24 +616,194 @@ virCPUarmGetHost(virCPUDefPtr cpu,
return virCPUarmDecodeCPUData(cpu, cpuData, models);
}
+static void
+virCPUarmDataIntersect(virCPUarmData *data1,
+ const virCPUarmData *data2)
+{
+ char **features = NULL;
+ char **features1 = NULL;
+ char **features2 = NULL;
+ size_t count = 0;
+ size_t i;
+
+ if (!data1 || !data2)
+ return;
+
+ data1->pvr = MIN(data1->pvr, data2->pvr);
+
+ if (virStringIsEmpty(data1->features) ||
+ virStringIsEmpty(data2->features)) {
+ VIR_FREE(data1->features);
+ return;
+ }
+
+ if (STREQ_NULLABLE(data1->features, data2->features))
+ return;
+
+ if (!(features = virStringSplitCount(data1->features, " ", 0, &count)) ||
+ !(features1 = virStringSplitCount(data1->features, " ", 0, &count)) ||
+ !(features2 = virStringSplit(data2->features, " ", 0)))
+ goto cleanup;
+
+ for (i = 0; i < count; i++) {
+ if (!virStringListHasString((const char**)features2, features1[i]))
+ virStringListRemove(&features, features1[i]);
+ }
+
+ VIR_FREE(data1->features);
+ if (features)
+ data1->features = virStringListJoin((const char**)features, " ");
+
+cleanup:
+ virStringListFree(features);
+ virStringListFree(features1);
+ virStringListFree(features2);
+ return;
+}
+
+static void
+virCPUarmDataCopy(virCPUarmData *dst, const virCPUarmData *src)
+{
+ dst->features = g_strdup(src->features);
+ dst->vendor_id = src->vendor_id;
+ dst->pvr = src->pvr;
+}
+
+static virCPUarmModelPtr
+virCPUarmModelCopy(virCPUarmModelPtr model)
+{
+ g_autoptr(virCPUarmModel) copy = NULL;
+
+ copy = virCPUarmModelNew();
+
+ virCPUarmDataCopy(&copy->data, &model->data);
+ copy->name = g_strdup(model->name);
+ copy->vendor = model->vendor;
+
+ return g_steal_pointer(&copy);
+}
+
+static virCPUarmModelPtr
+virCPUarmModelFromCPU(const virCPUDef *cpu,
+ virCPUarmMapPtr map)
+{
+ g_autoptr(virCPUarmModel) model = NULL;
+ virCPUarmVendorPtr vendor = NULL;
+ char **features = NULL;
+ size_t i;
+
+ if (!cpu->model) {
+ virReportError(VIR_ERR_INVALID_ARG, "%s",
+ _("no CPU model specified"));
+ return NULL;
+ }
+
+ if (!(model = virCPUarmModelFindByName(map, cpu->model))) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Unknown CPU model %s"), cpu->model);
+ return NULL;
+ }
+
+ if (!(model = virCPUarmModelCopy(model)))
+ return NULL;
+
+ if (cpu->vendor) {
+ if (!(vendor = virCPUarmVendorFindByName(map, cpu->vendor))) {
+ virReportError(VIR_ERR_INTERNAL_ERROR,
+ _("Unknown CPU vendor %s"), cpu->vendor);
+ return NULL;
+ }
+ model->data.vendor_id = vendor->value;
+ }
+
+ if (cpu->nfeatures) {
+ if (VIR_REALLOC_N(features, cpu->nfeatures + 1) < 0)
+ return model;
+
+ features[cpu->nfeatures] = NULL;
+ for (i = 0; i < cpu->nfeatures; i++)
+ features[i] = g_strdup(cpu->features[i].name);
+ VIR_FREE(model->data.features);
+ model->data.features = virStringListJoin((const char **)features, " ");
+ }
+
+ virStringListFree(features);
+ return g_steal_pointer(&model);
+}
static virCPUDefPtr
virCPUarmBaseline(virCPUDefPtr *cpus,
- unsigned int ncpus G_GNUC_UNUSED,
- virDomainCapsCPUModelsPtr models G_GNUC_UNUSED,
+ unsigned int ncpus,
+ virDomainCapsCPUModelsPtr models,
const char **features G_GNUC_UNUSED,
bool migratable G_GNUC_UNUSED)
{
- virCPUDefPtr cpu = NULL;
+ virCPUarmMapPtr map = NULL;
+ g_autoptr(virCPUDef) cpu = NULL;
+ g_autoptr(virCPUarmModel) model = NULL;
+ g_autoptr(virCPUarmModel) baseModel = NULL;
+ virCPUarmVendorPtr vendor = NULL;
+ bool outputVendor = true;
+ size_t i;
cpu = virCPUDefNew();
cpu->model = g_strdup(cpus[0]->model);
+ cpu->arch = cpus[0]->arch;
cpu->type = VIR_CPU_TYPE_GUEST;
cpu->match = VIR_CPU_MATCH_EXACT;
+ cpu->fallback = VIR_CPU_FALLBACK_FORBID;
+
+ if (!(map = virCPUarmGetMap()))
+ return NULL;
+
+ if (!(baseModel = virCPUarmModelFromCPU(cpus[0], map)))
+ return NULL;
+
+ if (!cpus[0]->vendor) {
+ outputVendor = false;
+ } else if (!(vendor = virCPUarmVendorFindByName(map, cpus[0]->vendor))) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ _("Unknown CPU vendor %s"), cpus[0]->vendor);
+ return NULL;
+ }
+
+ for (i = 0; i < ncpus; i++) {
+ const char *vn = NULL;
+ if (!(model = virCPUarmModelFromCPU(cpus[i], map)))
+ return NULL;
+
+ if (cpus[i]->vendor) {
+ vn = cpus[i]->vendor;
+ } else {
+ outputVendor = false;
+ }
+
+ if (vn) {
+ if (!vendor) {
+ if (!(vendor = virCPUarmVendorFindByName(map, vn))) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ _("Unknown CPU vendor %s"), vn);
+ return NULL;
+ }
+ } else if (STRNEQ(vendor->name, vn)) {
+ virReportError(VIR_ERR_OPERATION_FAILED,
+ "%s", _("CPU vendors do not match"));
+ return NULL;
+ }
+
+ virCPUarmDataIntersect(&baseModel->data, &model->data);
+ }
+ }
+
+ if (virCPUarmDecode(cpu, &baseModel->data, models) < 0)
+ return NULL;
+
+ if (!outputVendor)
+ g_free(cpu->vendor);
- return cpu;
+ return g_steal_pointer(&cpu);
}
static virCPUCompareResult
--
2.23.0

View File

@ -1,239 +0,0 @@
From 1a70b1e3bdbd8d0dcf9281341bc23b4ff2ffaa3a Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Mon, 20 Apr 2020 19:33:49 +0800
Subject: cpu/arm: implment cpu compare function
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu_arm.c | 196 +++++++++++++++++++++++++++++++++++++++++++++-
1 file changed, 193 insertions(+), 3 deletions(-)
diff --git a/src/cpu/cpu_arm.c b/src/cpu/cpu_arm.c
index a7c9523..3ef54b9 100644
--- a/src/cpu/cpu_arm.c
+++ b/src/cpu/cpu_arm.c
@@ -21,6 +21,7 @@
#include <config.h>
+#include "virlog.h"
#include "viralloc.h"
#include "cpu.h"
#include "cpu_map.h"
@@ -30,6 +31,8 @@
#define VIR_FROM_THIS VIR_FROM_CPU
+VIR_LOG_INIT("cpu.cpu_arm");
+
static const char *sysinfoCpuinfo = "/proc/cpuinfo";
#define CPUINFO sysinfoCpuinfo
@@ -806,14 +809,201 @@ virCPUarmBaseline(virCPUDefPtr *cpus,
return g_steal_pointer(&cpu);
}
+static bool
+virCPUarmFeaturesIsSub(char *subFeatures,
+ char *fullFeatures)
+{
+ bool ret = false;
+ char **sub = NULL;
+ char **full = NULL;
+ size_t subCount = 0;
+ size_t fullCount = 0;
+ size_t i;
+
+ if (virStringIsEmpty(subFeatures))
+ return true;
+
+ if (virStringIsEmpty(fullFeatures))
+ return ret;
+
+ if (STREQ(subFeatures, fullFeatures))
+ return true;
+
+ if (!(sub = virStringSplitCount(subFeatures, " ", 0, &subCount)) ||
+ !(full = virStringSplitCount(fullFeatures, " ", 0, &fullCount)) ||
+ subCount > fullCount)
+ goto cleanup;
+
+ for (i = 0; i < subCount; i++) {
+ if (!virStringListHasString((const char**)full, sub[i]))
+ goto cleanup;
+ }
+
+ ret = true;
+
+ cleanup:
+ virStringListFree(sub);
+ virStringListFree(full);
+ return ret;
+}
+
+static virCPUDataPtr
+armMakeCPUData(virArch arch,
+ virCPUarmData *data)
+{
+ virCPUDataPtr cpuData;
+
+ if (!(cpuData = virCPUDataNew(arch)))
+ return NULL;
+
+ virCPUarmDataCopy(&cpuData->data.arm, data);
+
+ return cpuData;
+}
+
static virCPUCompareResult
-virCPUarmCompare(virCPUDefPtr host G_GNUC_UNUSED,
- virCPUDefPtr cpu G_GNUC_UNUSED,
- bool failMessages G_GNUC_UNUSED)
+armCompute(virCPUDefPtr host,
+ virCPUDefPtr cpu,
+ virCPUDataPtr *guestData,
+ char **message)
{
+ virCPUarmMapPtr map = NULL;
+ g_autoptr(virCPUarmModel) hostModel = NULL;
+ g_autoptr(virCPUarmModel) guestModel = NULL;
+ virArch arch;
+ size_t i;
+
+ if (cpu->arch != VIR_ARCH_NONE) {
+ bool found = false;
+
+ for (i = 0; i < G_N_ELEMENTS(archs); i++) {
+ if (archs[i] == cpu->arch) {
+ found = true;
+ break;
+ }
+ }
+
+ if (!found) {
+ VIR_DEBUG("CPU arch %s does not match host arch",
+ virArchToString(cpu->arch));
+ if (message)
+ *message = g_strdup_printf(_("CPU arch %s does not match host arch"),
+ virArchToString(cpu->arch));
+
+ return VIR_CPU_COMPARE_INCOMPATIBLE;
+ }
+ arch = cpu->arch;
+ } else {
+ arch = host->arch;
+ }
+
+ if (cpu->vendor &&
+ (!host->vendor || STRNEQ(cpu->vendor, host->vendor))) {
+ VIR_DEBUG("host CPU vendor does not match required CPU vendor %s",
+ cpu->vendor);
+ if (message)
+ *message = g_strdup_printf(_("host CPU vendor does not match required "
+ "CPU vendor %s"),
+ cpu->vendor);
+
+ return VIR_CPU_COMPARE_INCOMPATIBLE;
+ }
+
+ if (!(map = virCPUarmGetMap()))
+ return VIR_CPU_COMPARE_ERROR;
+
+ /* Host CPU information */
+ if (!(hostModel = virCPUarmModelFromCPU(host, map)))
+ return VIR_CPU_COMPARE_ERROR;
+
+ if (cpu->type == VIR_CPU_TYPE_GUEST) {
+ /* Guest CPU information */
+ switch (cpu->mode) {
+ case VIR_CPU_MODE_HOST_MODEL:
+ case VIR_CPU_MODE_HOST_PASSTHROUGH:
+ /* host-model and host-passthrough:
+ * the guest CPU is the same as the host */
+ guestModel = virCPUarmModelCopy(hostModel);
+ break;
+
+ case VIR_CPU_MODE_CUSTOM:
+ /* custom:
+ * look up guest CPU information */
+ guestModel = virCPUarmModelFromCPU(cpu, map);
+ break;
+ }
+ } else {
+ /* Other host CPU information */
+ guestModel = virCPUarmModelFromCPU(cpu, map);
+ }
+
+ if (!guestModel)
+ return VIR_CPU_COMPARE_ERROR;
+
+ if (STRNEQ(guestModel->name, hostModel->name)) {
+ VIR_DEBUG("host CPU model %s does not match required CPU model %s",
+ hostModel->name, guestModel->name);
+ if (message)
+ *message = g_strdup_printf(_("host CPU model %s does not match required "
+ "CPU model %s"),
+ hostModel->name, guestModel->name);
+
+ return VIR_CPU_COMPARE_INCOMPATIBLE;
+ }
+
+ if (!virCPUarmFeaturesIsSub(guestModel->data.features, hostModel->data.features)) {
+ VIR_DEBUG("guest CPU features '%s' is not subset of "
+ "host CPU features '%s'",
+ guestModel->data.features, hostModel->data.features);
+ if (message)
+ *message = g_strdup_printf(_("guest CPU features '%s' is not subset of "
+ "host CPU features '%s'"),
+ guestModel->data.features,
+ hostModel->data.features);
+
+ return VIR_CPU_COMPARE_INCOMPATIBLE;
+ }
+
+ if (guestData &&
+ !(*guestData = armMakeCPUData(arch, &guestModel->data)))
+ return VIR_CPU_COMPARE_ERROR;
+
return VIR_CPU_COMPARE_IDENTICAL;
}
+static virCPUCompareResult
+virCPUarmCompare(virCPUDefPtr host,
+ virCPUDefPtr cpu,
+ bool failMessages)
+{
+ virCPUCompareResult ret = VIR_CPU_COMPARE_ERROR;
+ g_autofree char *message = NULL;
+
+ if (!host || !host->model) {
+ if (failMessages) {
+ virReportError(VIR_ERR_CPU_INCOMPATIBLE, "%s",
+ _("unknown host CPU"));
+ } else {
+ VIR_WARN("unknown host CPU");
+ return VIR_CPU_COMPARE_INCOMPATIBLE;
+ }
+ return VIR_CPU_COMPARE_ERROR;
+ }
+
+ ret = armCompute(host, cpu, NULL, &message);
+
+ if (failMessages && ret == VIR_CPU_COMPARE_INCOMPATIBLE) {
+ if (message) {
+ virReportError(VIR_ERR_CPU_INCOMPATIBLE, "%s", message);
+ } else {
+ virReportError(VIR_ERR_CPU_INCOMPATIBLE, NULL);
+ }
+ return VIR_CPU_COMPARE_ERROR;
+ }
+
+ return ret;
+}
+
static int
virCPUarmValidateFeatures(virCPUDefPtr cpu)
{
--
2.23.0

View File

@ -1,76 +0,0 @@
From 43ebd81b60121ce002a58ebc046b19f31bb23cb6 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Thu, 16 Apr 2020 11:00:49 +0800
Subject: cpu: introduce virCPUarmData to virCPUData
introduce virCPUarmData to virCPUData union, CPUarmData include
vendor id, pvr and cpu features.
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu/cpu.h | 2 ++
src/cpu/cpu_arm_data.h | 32 ++++++++++++++++++++++++++++++++
2 files changed, 34 insertions(+)
create mode 100644 src/cpu/cpu_arm_data.h
diff --git a/src/cpu/cpu.h b/src/cpu/cpu.h
index f779d2b..ec22a18 100644
--- a/src/cpu/cpu.h
+++ b/src/cpu/cpu.h
@@ -27,6 +27,7 @@
#include "cpu_conf.h"
#include "cpu_x86_data.h"
#include "cpu_ppc64_data.h"
+#include "cpu_arm_data.h"
typedef struct _virCPUData virCPUData;
@@ -36,6 +37,7 @@ struct _virCPUData {
union {
virCPUx86Data x86;
virCPUppc64Data ppc64;
+ virCPUarmData arm;
/* generic driver needs no data */
} data;
};
diff --git a/src/cpu/cpu_arm_data.h b/src/cpu/cpu_arm_data.h
new file mode 100644
index 0000000..72b3a29
--- /dev/null
+++ b/src/cpu/cpu_arm_data.h
@@ -0,0 +1,32 @@
+/*
+ * cpu_arm_data.h: 64-bit arm CPU specific data
+ *
+ * Copyright (C) 2019. Huawei Technologies Co., Ltd. All rights reserved.
+ *
+ * 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/>.
+ *
+ */
+
+#pragma once
+
+
+#define VIR_CPU_ARM_DATA_INIT { 0 }
+
+typedef struct _virCPUarmData virCPUarmData;
+struct _virCPUarmData {
+ unsigned long vendor_id;
+ unsigned long pvr;
+ char *features;
+};
--
2.23.0

View File

@ -1,150 +0,0 @@
From b305f4c05d22277ba6092bc0c2a15b752959bdec Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Thu, 16 Apr 2020 10:57:11 +0800
Subject: cpu_map: Introduce arm CPU models
Support vendor and model for virConnectGetCapabilities in ARM,
add arm cpu info to cpu map.
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu_map/Makefile.inc.am | 5 +++++
src/cpu_map/arm_Kunpeng-920.xml | 24 ++++++++++++++++++++++++
src/cpu_map/arm_cortex-a53.xml | 6 ++++++
src/cpu_map/arm_cortex-a57.xml | 6 ++++++
src/cpu_map/arm_cortex-a72.xml | 6 ++++++
src/cpu_map/arm_vendors.xml | 14 ++++++++++++++
src/cpu_map/index.xml | 12 ++++++++++++
7 files changed, 73 insertions(+)
create mode 100644 src/cpu_map/arm_Kunpeng-920.xml
create mode 100644 src/cpu_map/arm_cortex-a53.xml
create mode 100644 src/cpu_map/arm_cortex-a57.xml
create mode 100644 src/cpu_map/arm_cortex-a72.xml
create mode 100644 src/cpu_map/arm_vendors.xml
diff --git a/src/cpu_map/Makefile.inc.am b/src/cpu_map/Makefile.inc.am
index be64c9a..8663877 100644
--- a/src/cpu_map/Makefile.inc.am
+++ b/src/cpu_map/Makefile.inc.am
@@ -67,6 +67,11 @@ cpumap_DATA = \
cpu_map/x86_Skylake-Server-noTSX-IBRS.xml \
cpu_map/x86_Westmere.xml \
cpu_map/x86_Westmere-IBRS.xml \
+ cpu_map/arm_vendors.xml \
+ cpu_map/arm_cortex-a53.xml \
+ cpu_map/arm_cortex-a57.xml \
+ cpu_map/arm_cortex-a72.xml \
+ cpu_map/arm_Kunpeng-920.xml \
$(NULL)
EXTRA_DIST += $(cpumap_DATA)
diff --git a/src/cpu_map/arm_Kunpeng-920.xml b/src/cpu_map/arm_Kunpeng-920.xml
new file mode 100644
index 0000000..b681546
--- /dev/null
+++ b/src/cpu_map/arm_Kunpeng-920.xml
@@ -0,0 +1,24 @@
+<cpus>
+ <model name='Kunpeng-920'>
+ <vendor name='Hisilicon'/>
+ <pvr value='0xd01'/>
+ <feature name="fp"/>
+ <feature name="asimd"/>
+ <feature name="evtstrm"/>
+ <feature name="aes"/>
+ <feature name="pmull"/>
+ <feature name="sha1"/>
+ <feature name="sha2"/>
+ <feature name="crc32"/>
+ <feature name="atomics"/>
+ <feature name="fphp"/>
+ <feature name="asimdhp"/>
+ <feature name="cpuid"/>
+ <feature name="asimdrdm"/>
+ <feature name="jscvt"/>
+ <feature name="fcma"/>
+ <feature name="dcpop"/>
+ <feature name="asimddp"/>
+ <feature name="asimdfhm"/>
+ </model>
+</cpus>
diff --git a/src/cpu_map/arm_cortex-a53.xml b/src/cpu_map/arm_cortex-a53.xml
new file mode 100644
index 0000000..3580236
--- /dev/null
+++ b/src/cpu_map/arm_cortex-a53.xml
@@ -0,0 +1,6 @@
+<cpus>
+ <model name='cortex-a53'>
+ <vendor name='ARM'/>
+ <pvr value='0xd03'/>
+ </model>
+</cpus>
diff --git a/src/cpu_map/arm_cortex-a57.xml b/src/cpu_map/arm_cortex-a57.xml
new file mode 100644
index 0000000..3bc4324
--- /dev/null
+++ b/src/cpu_map/arm_cortex-a57.xml
@@ -0,0 +1,6 @@
+<cpus>
+ <model name='cortex-a57'>
+ <vendor name='ARM'/>
+ <pvr value='0xd07'/>
+ </model>
+</cpus>
diff --git a/src/cpu_map/arm_cortex-a72.xml b/src/cpu_map/arm_cortex-a72.xml
new file mode 100644
index 0000000..c509a40
--- /dev/null
+++ b/src/cpu_map/arm_cortex-a72.xml
@@ -0,0 +1,6 @@
+<cpus>
+ <model name='cortex-a72'>
+ <vendor name='ARM'/>
+ <pvr value='0xd08'/>
+ </model>
+</cpus>
diff --git a/src/cpu_map/arm_vendors.xml b/src/cpu_map/arm_vendors.xml
new file mode 100644
index 0000000..840bf9a
--- /dev/null
+++ b/src/cpu_map/arm_vendors.xml
@@ -0,0 +1,14 @@
+<cpus>
+ <vendor name="ARM" value="0x41"/>
+ <vendor name="Broadcom" value="0x42"/>
+ <vendor name="Cavium" value="0x43"/>
+ <vendor name="DigitalEquipment" value="0x44"/>
+ <vendor name="Hisilicon" value="0x48"/>
+ <vendor name="Infineon" value="0x49"/>
+ <vendor name="Freescale" value="0x4D"/>
+ <vendor name="NVIDIA" value="0x4E"/>
+ <vendor name="APM" value="0x50"/>
+ <vendor name="Qualcomm" value="0x51"/>
+ <vendor name="Marvell" value="0x56"/>
+ <vendor name="Intel" value="0x69"/>
+</cpus>
diff --git a/src/cpu_map/index.xml b/src/cpu_map/index.xml
index 50b030d..2e78834 100644
--- a/src/cpu_map/index.xml
+++ b/src/cpu_map/index.xml
@@ -87,4 +87,16 @@
<arch name='arm'>
<include filename='arm_features.xml'/>
</arch>
+
+ <arch name='arm'>
+ <include filename="arm_vendors.xml"/>
+
+ <!-- ARM-based CPU models -->
+ <include filename="arm_cortex-a53.xml"/>
+ <include filename="arm_cortex-a57.xml"/>
+ <include filename="arm_cortex-a72.xml"/>
+
+ <!-- Hisilicon-based CPU models -->
+ <include filename="arm_Kunpeng-920.xml"/>
+ </arch>
</cpus>
--
2.23.0

View File

@ -1,41 +0,0 @@
From f67e57fa41c76e21effd9e61773319ef424a5265 Mon Sep 17 00:00:00 2001
From: Xu Yandong <xuyandong2@huawei.com>
Date: Tue, 26 May 2020 20:08:07 +0800
Subject: [PATCH] cpu_map: add kunpeng-920 features to arm features
Signed-off-by: Xu Yandong <xuyandong2@huawei.com>
---
src/cpu_map/arm_features.xml | 19 +++++++++++++++++++
1 file changed, 19 insertions(+)
diff --git a/src/cpu_map/arm_features.xml b/src/cpu_map/arm_features.xml
index 8a53384..5bed298 100644
--- a/src/cpu_map/arm_features.xml
+++ b/src/cpu_map/arm_features.xml
@@ -19,4 +19,23 @@
<feature name='sve1920'/>
<feature name='sve2048'/>
+ <!-- Kunpeng-920 cpu features -->
+ <feature name='fp'/>
+ <feature name='asimd'/>
+ <feature name='evtstrm'/>
+ <feature name='aes'/>
+ <feature name='pmull'/>
+ <feature name='sha1'/>
+ <feature name='sha2'/>
+ <feature name='crc32'/>
+ <feature name='atomics'/>
+ <feature name='fphp'/>
+ <feature name='asimdhp'/>
+ <feature name='cpuid'/>
+ <feature name='asimdrdm'/>
+ <feature name='jscvt'/>
+ <feature name='fcma'/>
+ <feature name='dcpop'/>
+ <feature name='asimddp'/>
+ <feature name='asimdfhm'/>
</cpus>
--
2.23.0

View File

@ -1,39 +0,0 @@
From fe9f75a69b6dac1dec4f77d8b17ec2406415d89d Mon Sep 17 00:00:00 2001
From: Matt Coleman <mcoleman@datto.com>
Date: Mon, 21 Sep 2020 22:01:46 -0400
Subject: [PATCH 037/108] libvirt: ensure defresult is used in
virConnectAuthCallbackDefault
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
A previous change to this function's password handling broke the use of
default values for credential types other than VIR_CRED_PASSPHRASE and
VIR_CRED_NOECHOPROMPT.
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Reviewed-by: Neal Gompa <ngompa13@gmail.com>
Signed-off-by: Matt Coleman <matt@datto.com>
(cherry picked from commit 1bb9f872a02f8be50c8f98b0ad13de62d2986fa9)
---
src/libvirt.c | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/src/libvirt.c b/src/libvirt.c
index 76bf1fa677..b11a15d7fe 100644
--- a/src/libvirt.c
+++ b/src/libvirt.c
@@ -146,7 +146,9 @@ virConnectAuthCallbackDefault(virConnectCredentialPtr cred,
len = strlen(buf);
if (len != 0 && buf[len-1] == '\n')
buf[len-1] = '\0';
- bufptr = g_strdup(buf);
+
+ if (strlen(buf) > 0)
+ bufptr = g_strdup(buf);
break;
case VIR_CRED_PASSPHRASE:
--
2.33.0

View File

@ -1,40 +0,0 @@
From bad0bdbee1225d4d5831bc7ea7d4113df4de743d Mon Sep 17 00:00:00 2001
From: tangbinzy <tangbin_yewu@cmss.chinamobile.com>
Date: Tue, 29 Nov 2022 10:01:51 +0000
Subject: [PATCH 08/24] libvirt-guests: Sync time for autostarted guests
Setting SYNC_TIME=1 does not work on autostarted guests.
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
See https://bugzilla.redhat.com/show_bug.cgi?id=1555398.
Signed-off-by: Tim Wiederhake <twiederh@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Signed-off-by: tangbin <tangbin_yewu@cmss.chinamobile.com>
(cherry-pick from a501fa7cae2b93807496295945e6d3b51e5ccb3f)
---
tools/libvirt-guests.sh.in | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/tools/libvirt-guests.sh.in b/tools/libvirt-guests.sh.in
index a881f6266e..74286a12c4 100644
--- a/tools/libvirt-guests.sh.in
+++ b/tools/libvirt-guests.sh.in
@@ -200,9 +200,9 @@ start() {
retval run_virsh "$uri" start $bypass "$name" \
>/dev/null && \
gettext "done"; echo
- if "$sync_time"; then
- run_virsh "$uri" domtime --sync "$name" >/dev/null
- fi
+ fi
+ if "$sync_time"; then
+ run_virsh "$uri" domtime --sync "$name" >/dev/null
fi
fi
done
--
2.27.0

View File

@ -1,66 +0,0 @@
From cc842aa3030697b1a454e15ccfb2a201e57d5602 Mon Sep 17 00:00:00 2001
From: Michal Privoznik <mprivozn@redhat.com>
Date: Mon, 15 Jun 2020 12:53:48 +0200
Subject: [PATCH 3/6] leaseshelper: Report more errors
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Some functions or code paths that may fail don't report error
(e.g. when acquiring PID file fails) leading to a silent quit
of the leaseshelper. This makes it super hard for us and users
to debug what is happening. Fortunately, dnsmasq captures both
stdout and stderr so we can write an error message there.
cherry pick from: 9ed345ac1a035c8cf1de37431de638f4bac41de3
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
---
src/network/leaseshelper.c | 18 ++++++++++++++----
1 file changed, 14 insertions(+), 4 deletions(-)
diff --git a/src/network/leaseshelper.c b/src/network/leaseshelper.c
index 86c847d..2b5fc0f 100644
--- a/src/network/leaseshelper.c
+++ b/src/network/leaseshelper.c
@@ -131,8 +131,10 @@ main(int argc, char **argv)
* events for expired leases. So, libvirtd sets another env var for this
* purpose */
if (!interface &&
- !(interface = getenv("VIR_BRIDGE_NAME")))
- goto cleanup;
+ !(interface = getenv("VIR_BRIDGE_NAME"))) {
+ fprintf(stderr, _("interface not set\n"));
+ exit(EXIT_FAILURE);
+ }
ip = argv[3];
mac = argv[2];
@@ -160,13 +162,21 @@ main(int argc, char **argv)
pid_file = g_strdup(RUNSTATEDIR "/leaseshelper.pid");
/* Try to claim the pidfile, exiting if we can't */
- if ((pid_file_fd = virPidFileAcquirePath(pid_file, true, getpid())) < 0)
+ if ((pid_file_fd = virPidFileAcquirePath(pid_file, true, getpid())) < 0) {
+ fprintf(stderr,
+ _("Unable to acquire PID file: %s\n errno=%d"),
+ pid_file, errno);
goto cleanup;
+ }
/* Since interfaces can be hot plugged, we need to make sure that the
* corresponding custom lease file exists. If not, 'touch' it */
- if (virFileTouch(custom_lease_file, 0644) < 0)
+ if (virFileTouch(custom_lease_file, 0644) < 0) {
+ fprintf(stderr,
+ _("Unable to create: %s\n errno=%d"),
+ custom_lease_file, errno);
goto cleanup;
+ }
switch ((enum virLeaseActionFlags) action) {
case VIR_LEASE_ACTION_ADD:
--
1.8.3.1

View File

@ -1,45 +0,0 @@
From 173b80e8f8103f26438d344e9b97335d4e5036b4 Mon Sep 17 00:00:00 2001
From: Michal Privoznik <mprivozn@redhat.com>
Date: Thu, 11 Jun 2020 16:43:22 +0200
Subject: [PATCH 2/6] leaseshelper: Wait to acquire PID file
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
On a DHCP transaction, dnsmasq runs our leases helper which
updates corresponding JSON files. While one dnsmasq won't run the
leaseshelper in parallel, two dnsmasqs (from two distinct
networks) might. To avoid corrupting JSON file, the leaseshelper
acquires PID file first. Well, the way it's acquiring it is not
ideal - it calls virPidFileAcquirePath(wait = false); which
means, that either it acquires the PID file instantly or returns
an error and does not touch the JSON at all. This in turn means
that there might be a leases record missing. With wait = true,
this won't happen.
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1840307
cherry pick from: 876211ef4a192df1603b45715044ec14567d7e9f
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
---
src/network/leaseshelper.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/src/network/leaseshelper.c b/src/network/leaseshelper.c
index a1780ca..86c847d 100644
--- a/src/network/leaseshelper.c
+++ b/src/network/leaseshelper.c
@@ -160,7 +160,7 @@ main(int argc, char **argv)
pid_file = g_strdup(RUNSTATEDIR "/leaseshelper.pid");
/* Try to claim the pidfile, exiting if we can't */
- if ((pid_file_fd = virPidFileAcquirePath(pid_file, false, getpid())) < 0)
+ if ((pid_file_fd = virPidFileAcquirePath(pid_file, true, getpid())) < 0)
goto cleanup;
/* Since interfaces can be hot plugged, we need to make sure that the
--
1.8.3.1

View File

@ -1,48 +0,0 @@
From 0e95f7b912055cf254b71b0b02dcb0acf7da3870 Mon Sep 17 00:00:00 2001
From: Jim Fehlig <jfehlig@suse.com>
Date: Fri, 3 Apr 2020 15:51:48 -0600
Subject: [PATCH 1/8] libxl: fix crash when initializing driver
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Commit 54a401af478 split out DriverConfigInit from DriverConfigNew, but
then called it a bit late from libxlStateInitialize. The cfg is used in
libxlDriverConfigLoadFile and when uninitialized results in a crash.
Calling DriverConfigInit immediately after DriverConfigNew fixes the
crash.
Signed-off-by: Jim Fehlig <jfehlig@suse.com>
Reviewed-by: Erik Skultety <eskultet@redhat.com>
Reviewed-by: Ján Tomko <jtomko@redhat.com>
(cherry-picked from commit 88011ed2)
Signed-off-by: AlexChen <alex.chen@huawei.com>
---
src/libxl/libxl_driver.c | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/src/libxl/libxl_driver.c b/src/libxl/libxl_driver.c
index 7ec4fcc3d1..980984b199 100644
--- a/src/libxl/libxl_driver.c
+++ b/src/libxl/libxl_driver.c
@@ -702,14 +702,14 @@ libxlStateInitialize(bool privileged,
if (!(cfg = libxlDriverConfigNew()))
goto error;
+ if (libxlDriverConfigInit(cfg) < 0)
+ goto error;
+
driverConf = g_strdup_printf("%s/libxl.conf", cfg->configBaseDir);
if (libxlDriverConfigLoadFile(cfg, driverConf) < 0)
goto error;
- if (libxlDriverConfigInit(cfg) < 0)
- goto error;
-
/* Register the callbacks providing access to libvirt's event loop */
libxl_osevent_register_hooks(cfg->ctx, &libxl_osevent_callbacks, cfg->ctx);
--
2.23.0

Some files were not shown because too many files have changed in this diff Show More