209 lines
8.0 KiB
Diff
209 lines
8.0 KiB
Diff
|
|
From aeaef8019c4c1f16af1ebcb60c73c06f4f691261 Mon Sep 17 00:00:00 2001
|
||
|
|
From: xianglai li <lixianglai@loongson.cn>
|
||
|
|
Date: Fri, 28 Jul 2023 03:18:44 -0400
|
||
|
|
Subject: [PATCH 2/3] Support for loongarch64 in the QEMU driver
|
||
|
|
|
||
|
|
Implement support for loongarch64 in the QEMU driver.
|
||
|
|
|
||
|
|
Signed-off-by: "Xianglai Li" <lixianglai@loongson.cn>
|
||
|
|
Signed-off-by: Xianglai Li <lixianglai@loongson.cn>
|
||
|
|
---
|
||
|
|
src/qemu/qemu_capabilities.c | 10 +++++----
|
||
|
|
src/qemu/qemu_command.c | 3 ++-
|
||
|
|
src/qemu/qemu_domain.c | 42 ++++++++++++++++++++++++++++++++----
|
||
|
|
src/qemu/qemu_domain.h | 1 +
|
||
|
|
src/qemu/qemu_validate.c | 1 +
|
||
|
|
5 files changed, 48 insertions(+), 9 deletions(-)
|
||
|
|
|
||
|
|
diff --git a/src/qemu/qemu_capabilities.c b/src/qemu/qemu_capabilities.c
|
||
|
|
index 509e751274..79414becfd 100644
|
||
|
|
--- a/src/qemu/qemu_capabilities.c
|
||
|
|
+++ b/src/qemu/qemu_capabilities.c
|
||
|
|
@@ -1139,7 +1139,8 @@ virQEMUCapsInitGuestFromBinary(virCaps *caps,
|
||
|
|
NULL, NULL, 0, NULL);
|
||
|
|
}
|
||
|
|
|
||
|
|
- if ((ARCH_IS_X86(guestarch) || guestarch == VIR_ARCH_AARCH64))
|
||
|
|
+ if (ARCH_IS_X86(guestarch) || guestarch == VIR_ARCH_AARCH64 ||
|
||
|
|
+ ARCH_IS_LOONGARCH(guestarch))
|
||
|
|
virCapabilitiesAddGuestFeatureWithToggle(guest, VIR_CAPS_GUEST_FEATURE_TYPE_ACPI,
|
||
|
|
true, true);
|
||
|
|
|
||
|
|
@@ -2075,9 +2076,10 @@ bool virQEMUCapsHasPCIMultiBus(const virDomainDef *def)
|
||
|
|
if (ARCH_IS_S390(def->os.arch))
|
||
|
|
return true;
|
||
|
|
|
||
|
|
- /* If the virt machine, both on ARM and RISC-V, supports PCI,
|
||
|
|
+ /* If the virt machine, both on ARM and RISC-V and LOONGARCH64, supports PCI,
|
||
|
|
* then it also supports multibus */
|
||
|
|
if (qemuDomainIsARMVirt(def) ||
|
||
|
|
+ qemuDomainIsLoongArchVirt(def) ||
|
||
|
|
qemuDomainIsRISCVVirt(def)) {
|
||
|
|
return true;
|
||
|
|
}
|
||
|
|
@@ -2667,7 +2669,7 @@ static const char *preferredMachines[] =
|
||
|
|
NULL, /* VIR_ARCH_ITANIUM (doesn't exist in QEMU any more) */
|
||
|
|
"lm32-evr", /* VIR_ARCH_LM32 */
|
||
|
|
|
||
|
|
- NULL, /* VIR_ARCH_LOONGARCH64 */
|
||
|
|
+ "virt", /* VIR_ARCH_LOONGARCH64 */
|
||
|
|
"mcf5208evb", /* VIR_ARCH_M68K */
|
||
|
|
"petalogix-s3adsp1800", /* VIR_ARCH_MICROBLAZE */
|
||
|
|
"petalogix-s3adsp1800", /* VIR_ARCH_MICROBLAZEEL */
|
||
|
|
@@ -3743,7 +3745,7 @@ virQEMUCapsInitCPUModel(virQEMUCaps *qemuCaps,
|
||
|
|
} else if (ARCH_IS_X86(qemuCaps->arch)) {
|
||
|
|
ret = virQEMUCapsInitCPUModelX86(qemuCaps, type, modelInfo,
|
||
|
|
cpu, migratable);
|
||
|
|
- } else if (ARCH_IS_ARM(qemuCaps->arch)) {
|
||
|
|
+ } else if (ARCH_IS_ARM(qemuCaps->arch) || ARCH_IS_LOONGARCH(qemuCaps->arch)) {
|
||
|
|
ret = 2;
|
||
|
|
}
|
||
|
|
|
||
|
|
diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
|
||
|
|
index 6403d5692e..609eb6772e 100644
|
||
|
|
--- a/src/qemu/qemu_command.c
|
||
|
|
+++ b/src/qemu/qemu_command.c
|
||
|
|
@@ -9209,7 +9209,8 @@ qemuChrIsPlatformDevice(const virDomainDef *def,
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
- if (ARCH_IS_RISCV(def->os.arch)) {
|
||
|
|
+ if (ARCH_IS_RISCV(def->os.arch) ||
|
||
|
|
+ ARCH_IS_LOONGARCH(def->os.arch)) {
|
||
|
|
|
||
|
|
/* 16550a (used by riscv/virt guests) is a platform device */
|
||
|
|
if (chr->deviceType == VIR_DOMAIN_CHR_DEVICE_TYPE_SERIAL &&
|
||
|
|
diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c
|
||
|
|
index 8374780507..020cfc8bff 100644
|
||
|
|
--- a/src/qemu/qemu_domain.c
|
||
|
|
+++ b/src/qemu/qemu_domain.c
|
||
|
|
@@ -4229,11 +4229,14 @@ qemuDomainDefAddDefaultDevices(virQEMUDriver *driver,
|
||
|
|
addPCIRoot = true;
|
||
|
|
break;
|
||
|
|
|
||
|
|
+ case VIR_ARCH_LOONGARCH64:
|
||
|
|
+ addPCIeRoot = true;
|
||
|
|
+ break;
|
||
|
|
+
|
||
|
|
case VIR_ARCH_ARMV7B:
|
||
|
|
case VIR_ARCH_CRIS:
|
||
|
|
case VIR_ARCH_ITANIUM:
|
||
|
|
case VIR_ARCH_LM32:
|
||
|
|
- case VIR_ARCH_LOONGARCH64:
|
||
|
|
case VIR_ARCH_M68K:
|
||
|
|
case VIR_ARCH_MICROBLAZE:
|
||
|
|
case VIR_ARCH_MICROBLAZEEL:
|
||
|
|
@@ -5400,7 +5403,8 @@ static int
|
||
|
|
qemuDomainDefaultNetModel(const virDomainDef *def,
|
||
|
|
virQEMUCaps *qemuCaps)
|
||
|
|
{
|
||
|
|
- if (ARCH_IS_S390(def->os.arch))
|
||
|
|
+ if (ARCH_IS_S390(def->os.arch) ||
|
||
|
|
+ qemuDomainIsLoongArchVirt(def))
|
||
|
|
return VIR_DOMAIN_NET_MODEL_VIRTIO;
|
||
|
|
|
||
|
|
if (def->os.arch == VIR_ARCH_ARMV6L ||
|
||
|
|
@@ -5639,6 +5643,9 @@ qemuDomainControllerDefPostParse(virDomainControllerDef *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;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
/* forbid usb model 'qusb1' and 'qusb2' in this kind of hyperviosr */
|
||
|
|
@@ -5738,7 +5745,9 @@ qemuDomainChrDefPostParse(virDomainChrDef *chr,
|
||
|
|
chr->targetType = VIR_DOMAIN_CHR_SERIAL_TARGET_TYPE_ISA;
|
||
|
|
} else if (qemuDomainIsPSeries(def)) {
|
||
|
|
chr->targetType = VIR_DOMAIN_CHR_SERIAL_TARGET_TYPE_SPAPR_VIO;
|
||
|
|
- } else if (qemuDomainIsARMVirt(def) || qemuDomainIsRISCVVirt(def)) {
|
||
|
|
+ } else if (qemuDomainIsARMVirt(def) ||
|
||
|
|
+ qemuDomainIsLoongArchVirt(def) ||
|
||
|
|
+ qemuDomainIsRISCVVirt(def)) {
|
||
|
|
chr->targetType = VIR_DOMAIN_CHR_SERIAL_TARGET_TYPE_SYSTEM;
|
||
|
|
} else if (ARCH_IS_S390(def->os.arch)) {
|
||
|
|
chr->targetType = VIR_DOMAIN_CHR_SERIAL_TARGET_TYPE_SCLP;
|
||
|
|
@@ -5764,7 +5773,8 @@ qemuDomainChrDefPostParse(virDomainChrDef *chr,
|
||
|
|
case VIR_DOMAIN_CHR_SERIAL_TARGET_TYPE_SYSTEM:
|
||
|
|
if (qemuDomainIsARMVirt(def)) {
|
||
|
|
chr->targetModel = VIR_DOMAIN_CHR_SERIAL_TARGET_MODEL_PL011;
|
||
|
|
- } else if (qemuDomainIsRISCVVirt(def)) {
|
||
|
|
+ } else if (qemuDomainIsLoongArchVirt(def) ||
|
||
|
|
+ qemuDomainIsRISCVVirt(def)) {
|
||
|
|
chr->targetModel = VIR_DOMAIN_CHR_SERIAL_TARGET_MODEL_16550A;
|
||
|
|
}
|
||
|
|
break;
|
||
|
|
@@ -5936,6 +5946,7 @@ qemuDomainDefaultVideoDevice(const virDomainDef *def,
|
||
|
|
if (ARCH_IS_PPC64(def->os.arch))
|
||
|
|
return VIR_DOMAIN_VIDEO_TYPE_VGA;
|
||
|
|
if (qemuDomainIsARMVirt(def) ||
|
||
|
|
+ qemuDomainIsLoongArchVirt(def) ||
|
||
|
|
qemuDomainIsRISCVVirt(def) ||
|
||
|
|
ARCH_IS_S390(def->os.arch)) {
|
||
|
|
return VIR_DOMAIN_VIDEO_TYPE_VIRTIO;
|
||
|
|
@@ -8930,6 +8941,22 @@ qemuDomainMachineIsPSeries(const char *machine,
|
||
|
|
}
|
||
|
|
|
||
|
|
|
||
|
|
+static bool
|
||
|
|
+qemuDomainMachineIsLoongArchVirt(const char *machine,
|
||
|
|
+ const virArch arch)
|
||
|
|
+{
|
||
|
|
+ if (!ARCH_IS_LOONGARCH(arch))
|
||
|
|
+ return false;
|
||
|
|
+
|
||
|
|
+ if (STREQ(machine, "virt") ||
|
||
|
|
+ STRPREFIX(machine, "virt-")) {
|
||
|
|
+ return true;
|
||
|
|
+ }
|
||
|
|
+
|
||
|
|
+ return false;
|
||
|
|
+}
|
||
|
|
+
|
||
|
|
+
|
||
|
|
static bool
|
||
|
|
qemuDomainMachineIsMipsMalta(const char *machine,
|
||
|
|
const virArch arch)
|
||
|
|
@@ -9023,6 +9050,13 @@ qemuDomainIsMipsMalta(const virDomainDef *def)
|
||
|
|
}
|
||
|
|
|
||
|
|
|
||
|
|
+bool
|
||
|
|
+qemuDomainIsLoongArchVirt(const virDomainDef *def)
|
||
|
|
+{
|
||
|
|
+ return qemuDomainMachineIsLoongArchVirt(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 7074023229..c90a361e8a 100644
|
||
|
|
--- a/src/qemu/qemu_domain.h
|
||
|
|
+++ b/src/qemu/qemu_domain.h
|
||
|
|
@@ -829,6 +829,7 @@ bool qemuDomainIsQ35(const virDomainDef *def);
|
||
|
|
bool qemuDomainIsI440FX(const virDomainDef *def);
|
||
|
|
bool qemuDomainIsS390CCW(const virDomainDef *def);
|
||
|
|
bool qemuDomainIsARMVirt(const virDomainDef *def);
|
||
|
|
+bool qemuDomainIsLoongArchVirt(const virDomainDef *def);
|
||
|
|
bool qemuDomainIsRISCVVirt(const virDomainDef *def);
|
||
|
|
bool qemuDomainIsPSeries(const virDomainDef *def);
|
||
|
|
bool qemuDomainIsMipsMalta(const virDomainDef *def);
|
||
|
|
diff --git a/src/qemu/qemu_validate.c b/src/qemu/qemu_validate.c
|
||
|
|
index 18c5b60a35..a51cb6017d 100644
|
||
|
|
--- a/src/qemu/qemu_validate.c
|
||
|
|
+++ b/src/qemu/qemu_validate.c
|
||
|
|
@@ -2064,6 +2064,7 @@ qemuValidateDomainChrDef(const virDomainChrDef *dev,
|
||
|
|
isCompatible = false;
|
||
|
|
}
|
||
|
|
if (dev->targetModel == VIR_DOMAIN_CHR_SERIAL_TARGET_MODEL_16550A &&
|
||
|
|
+ !qemuDomainIsLoongArchVirt(def) &&
|
||
|
|
!qemuDomainIsRISCVVirt(def)) {
|
||
|
|
isCompatible = false;
|
||
|
|
}
|
||
|
|
--
|
||
|
|
2.39.1
|
||
|
|
|