* [PULL 1/7] target/loongarch: Add compatible support about VM reboot
2024-09-12 12:51 [PULL 0/7] loongarch-to-apply queue Song Gao
@ 2024-09-12 12:51 ` Song Gao
2024-09-12 12:51 ` [PULL 2/7] hw/loongarch: Remove default enable with VIRTIO_VGA device Song Gao
` (6 subsequent siblings)
7 siblings, 0 replies; 11+ messages in thread
From: Song Gao @ 2024-09-12 12:51 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, Bibo Mao
From: Bibo Mao <maobibo@loongson.cn>
With edk2-stable202408 LoongArch UEFI bios, CSR PGD register is set only
if its value is equal to zero for boot cpu, it causes reboot issue. Since
CSR PGD register is changed with linux kernel, UEFI BIOS cannot use it.
Add workaround to clear CSR registers relative with TLB in function
loongarch_cpu_reset_hold(), so that VM can reboot with edk2-stable202408
UEFI bios.
Signed-off-by: Bibo Mao <maobibo@loongson.cn>
Reviewed-by: Song Gao <gaosong@loongson.cn>
Message-Id: <20240827035807.3326293-1-maobibo@loongson.cn>
Signed-off-by: Song Gao <gaosong@loongson.cn>
---
target/loongarch/cpu.c | 14 ++++++++++++++
1 file changed, 14 insertions(+)
diff --git a/target/loongarch/cpu.c b/target/loongarch/cpu.c
index 5e85b9dbef..115922113a 100644
--- a/target/loongarch/cpu.c
+++ b/target/loongarch/cpu.c
@@ -549,6 +549,20 @@ static void loongarch_cpu_reset_hold(Object *obj, ResetType type)
env->CSR_TLBRERA = FIELD_DP64(env->CSR_TLBRERA, CSR_TLBRERA, ISTLBR, 0);
env->CSR_MERRCTL = FIELD_DP64(env->CSR_MERRCTL, CSR_MERRCTL, ISMERR, 0);
env->CSR_TID = cs->cpu_index;
+ /*
+ * Workaround for edk2-stable202408, CSR PGD register is set only if
+ * its value is equal to zero for boot cpu, it causes reboot issue.
+ *
+ * Here clear CSR registers relative with TLB.
+ */
+ env->CSR_PGDH = 0;
+ env->CSR_PGDL = 0;
+ env->CSR_PWCL = 0;
+ env->CSR_PWCH = 0;
+ env->CSR_STLBPS = 0;
+ env->CSR_EENTRY = 0;
+ env->CSR_TLBRENTRY = 0;
+ env->CSR_MERRENTRY = 0;
for (n = 0; n < 4; n++) {
env->CSR_DMW[n] = FIELD_DP64(env->CSR_DMW[n], CSR_DMW, PLV0, 0);
--
2.34.1
^ permalink raw reply related [flat|nested] 11+ messages in thread
* [PULL 2/7] hw/loongarch: Remove default enable with VIRTIO_VGA device
2024-09-12 12:51 [PULL 0/7] loongarch-to-apply queue Song Gao
2024-09-12 12:51 ` [PULL 1/7] target/loongarch: Add compatible support about VM reboot Song Gao
@ 2024-09-12 12:51 ` Song Gao
2024-09-12 12:51 ` [PULL 3/7] target/loongarch/kvm: Add vCPU reset function Song Gao
` (5 subsequent siblings)
7 siblings, 0 replies; 11+ messages in thread
From: Song Gao @ 2024-09-12 12:51 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, Bibo Mao
From: Bibo Mao <maobibo@loongson.cn>
For virtio VGA deivce libvirt will select VIRTIO_VGA firstly rather than
VIRTIO_GPU, VIRTIO_VGA device supports frame buffer however it requires
legacy VGA compatible support. Frame buffer area 0xa0000 -- 0xc0000
conflicts with low memory area 0 -- 0x10000000.
Here remove default support for VIRTIO_VGA device, VIRTIO_GPU is prefered
on LoongArch system. For frame buffer video card support, standard VGA can
be used.
Signed-off-by: Bibo Mao <maobibo@loongson.cn>
Reviewed-by: Song Gao <gaosong@loongson.cn>
Message-Id: <20240823073050.2619484-1-maobibo@loongson.cn>
Signed-off-by: Song Gao <gaosong@loongson.cn>
---
hw/loongarch/Kconfig | 1 -
1 file changed, 1 deletion(-)
diff --git a/hw/loongarch/Kconfig b/hw/loongarch/Kconfig
index 0de713a439..9c69170968 100644
--- a/hw/loongarch/Kconfig
+++ b/hw/loongarch/Kconfig
@@ -5,7 +5,6 @@ config LOONGARCH_VIRT
select DEVICE_TREE
select PCI
select PCI_EXPRESS_GENERIC_BRIDGE
- imply VIRTIO_VGA
imply PCI_DEVICES
imply NVDIMM
imply TPM_TIS_SYSBUS
--
2.34.1
^ permalink raw reply related [flat|nested] 11+ messages in thread
* [PULL 3/7] target/loongarch/kvm: Add vCPU reset function
2024-09-12 12:51 [PULL 0/7] loongarch-to-apply queue Song Gao
2024-09-12 12:51 ` [PULL 1/7] target/loongarch: Add compatible support about VM reboot Song Gao
2024-09-12 12:51 ` [PULL 2/7] hw/loongarch: Remove default enable with VIRTIO_VGA device Song Gao
@ 2024-09-12 12:51 ` Song Gao
2024-09-12 12:51 ` [PULL 4/7] target/loongarch: Support QMP dump-guest-memory Song Gao
` (4 subsequent siblings)
7 siblings, 0 replies; 11+ messages in thread
From: Song Gao @ 2024-09-12 12:51 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, Bibo Mao
From: Bibo Mao <maobibo@loongson.cn>
KVM provides interface KVM_REG_LOONGARCH_VCPU_RESET to reset vCPU,
it can be used to clear internal state about kvm kernel. vCPU reset
function is added here for kvm mode.
Signed-off-by: Bibo Mao <maobibo@loongson.cn>
Reviewed-by: Song Gao <gaosong@loongson.cn>
Message-Id: <20240822022827.2273534-1-maobibo@loongson.cn>
Signed-off-by: Song Gao <gaosong@loongson.cn>
---
target/loongarch/cpu.c | 2 +-
target/loongarch/kvm/kvm.c | 5 ++++-
target/loongarch/kvm/kvm_loongarch.h | 2 +-
3 files changed, 6 insertions(+), 3 deletions(-)
diff --git a/target/loongarch/cpu.c b/target/loongarch/cpu.c
index 115922113a..6a569285b8 100644
--- a/target/loongarch/cpu.c
+++ b/target/loongarch/cpu.c
@@ -577,7 +577,7 @@ static void loongarch_cpu_reset_hold(Object *obj, ResetType type)
memset(env->tlb, 0, sizeof(env->tlb));
#endif
if (kvm_enabled()) {
- kvm_arch_reset_vcpu(env);
+ kvm_arch_reset_vcpu(cs);
}
#endif
diff --git a/target/loongarch/kvm/kvm.c b/target/loongarch/kvm/kvm.c
index e1be6a6959..4786cd5efa 100644
--- a/target/loongarch/kvm/kvm.c
+++ b/target/loongarch/kvm/kvm.c
@@ -476,9 +476,12 @@ static int kvm_loongarch_put_regs_fp(CPUState *cs)
return ret;
}
-void kvm_arch_reset_vcpu(CPULoongArchState *env)
+void kvm_arch_reset_vcpu(CPUState *cs)
{
+ CPULoongArchState *env = cpu_env(cs);
+
env->mp_state = KVM_MP_STATE_RUNNABLE;
+ kvm_set_one_reg(cs, KVM_REG_LOONGARCH_VCPU_RESET, 0);
}
static int kvm_loongarch_get_mpstate(CPUState *cs)
diff --git a/target/loongarch/kvm/kvm_loongarch.h b/target/loongarch/kvm/kvm_loongarch.h
index d945b6bb82..1051a341ec 100644
--- a/target/loongarch/kvm/kvm_loongarch.h
+++ b/target/loongarch/kvm/kvm_loongarch.h
@@ -11,6 +11,6 @@
#define QEMU_KVM_LOONGARCH_H
int kvm_loongarch_set_interrupt(LoongArchCPU *cpu, int irq, int level);
-void kvm_arch_reset_vcpu(CPULoongArchState *env);
+void kvm_arch_reset_vcpu(CPUState *cs);
#endif
--
2.34.1
^ permalink raw reply related [flat|nested] 11+ messages in thread
* [PULL 4/7] target/loongarch: Support QMP dump-guest-memory
2024-09-12 12:51 [PULL 0/7] loongarch-to-apply queue Song Gao
` (2 preceding siblings ...)
2024-09-12 12:51 ` [PULL 3/7] target/loongarch/kvm: Add vCPU reset function Song Gao
@ 2024-09-12 12:51 ` Song Gao
2024-09-12 12:51 ` [PULL 5/7] hw/loongarch: virt: support up to 4 serial ports Song Gao
` (3 subsequent siblings)
7 siblings, 0 replies; 11+ messages in thread
From: Song Gao @ 2024-09-12 12:51 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, Bibo Mao
From: Bibo Mao <maobibo@loongson.cn>
Add the support needed for creating prstatus elf notes. This allows
us to use QMP dump-guest-memory.
Now ELF notes of LoongArch only supports general elf notes, LSX and
LASX is not supported, since it is mainly used to dump guest memory.
Signed-off-by: Bibo Mao <maobibo@loongson.cn>
Reviewed-by: Song Gao <gaosong@loongson.cn>
Tested-by: Song Gao <gaosong@loongson.cn>
Message-Id: <20240822065245.2286214-1-maobibo@loongson.cn>
Signed-off-by: Song Gao <gaosong@loongson.cn>
---
target/loongarch/arch_dump.c | 167 +++++++++++++++++++++++++++++++++++
target/loongarch/cpu.c | 1 +
target/loongarch/internals.h | 2 +
target/loongarch/meson.build | 1 +
4 files changed, 171 insertions(+)
create mode 100644 target/loongarch/arch_dump.c
diff --git a/target/loongarch/arch_dump.c b/target/loongarch/arch_dump.c
new file mode 100644
index 0000000000..4986db970e
--- /dev/null
+++ b/target/loongarch/arch_dump.c
@@ -0,0 +1,167 @@
+/*
+ * Support for writing ELF notes for LoongArch architectures
+ *
+ * Copyright (c) 2023 Loongarch Technology
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2 or later, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program. If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+#include "qemu/osdep.h"
+#include "cpu.h"
+#include "elf.h"
+#include "sysemu/dump.h"
+#include "internals.h"
+
+/* struct user_pt_regs from arch/loongarch/include/uapi/asm/ptrace.h */
+struct loongarch_user_regs {
+ uint64_t gpr[32];
+ uint64_t pad1[1];
+ /* Special CSR registers. */
+ uint64_t csr_era;
+ uint64_t csr_badv;
+ uint64_t pad2[10];
+} QEMU_PACKED;
+
+QEMU_BUILD_BUG_ON(sizeof(struct loongarch_user_regs) != 360);
+
+/* struct elf_prstatus from include/uapi/linux/elfcore.h */
+struct loongarch_elf_prstatus {
+ char pad1[32]; /* 32 == offsetof(struct elf_prstatus, pr_pid) */
+ uint32_t pr_pid;
+ /*
+ * 76 == offsetof(struct elf_prstatus, pr_reg) -
+ * offsetof(struct elf_prstatus, pr_ppid)
+ */
+ char pad2[76];
+ struct loongarch_user_regs pr_reg;
+ uint32_t pr_fpvalid;
+ char pad3[4];
+} QEMU_PACKED;
+
+QEMU_BUILD_BUG_ON(sizeof(struct loongarch_elf_prstatus) != 480);
+
+/* struct user_fp_state from arch/loongarch/include/uapi/asm/ptrace.h */
+struct loongarch_fpu_struct {
+ uint64_t fpr[32];
+ uint64_t fcc;
+ unsigned int fcsr;
+} QEMU_PACKED;
+
+QEMU_BUILD_BUG_ON(sizeof(struct loongarch_fpu_struct) != 268);
+
+struct loongarch_note {
+ Elf64_Nhdr hdr;
+ char name[8]; /* align_up(sizeof("CORE"), 4) */
+ union {
+ struct loongarch_elf_prstatus prstatus;
+ struct loongarch_fpu_struct fpu;
+ };
+} QEMU_PACKED;
+
+#define LOONGARCH_NOTE_HEADER_SIZE offsetof(struct loongarch_note, prstatus)
+#define LOONGARCH_PRSTATUS_NOTE_SIZE \
+ (LOONGARCH_NOTE_HEADER_SIZE + sizeof(struct loongarch_elf_prstatus))
+#define LOONGARCH_PRFPREG_NOTE_SIZE \
+ (LOONGARCH_NOTE_HEADER_SIZE + sizeof(struct loongarch_fpu_struct))
+
+static void loongarch_note_init(struct loongarch_note *note, DumpState *s,
+ const char *name, Elf64_Word namesz,
+ Elf64_Word type, Elf64_Word descsz)
+{
+ memset(note, 0, sizeof(*note));
+
+ note->hdr.n_namesz = cpu_to_dump32(s, namesz);
+ note->hdr.n_descsz = cpu_to_dump32(s, descsz);
+ note->hdr.n_type = cpu_to_dump32(s, type);
+
+ memcpy(note->name, name, namesz);
+}
+
+static int loongarch_write_elf64_fprpreg(WriteCoreDumpFunction f,
+ CPULoongArchState *env, int cpuid,
+ DumpState *s)
+{
+ struct loongarch_note note;
+ int ret, i;
+
+ loongarch_note_init(¬e, s, "CORE", 5, NT_PRFPREG, sizeof(note.fpu));
+ note.fpu.fcsr = cpu_to_dump64(s, env->fcsr0);
+
+ for (i = 0; i < 8; i++) {
+ note.fpu.fcc |= env->cf[i] << (8 * i);
+ }
+ note.fpu.fcc = cpu_to_dump64(s, note.fpu.fcc);
+
+ for (i = 0; i < 32; ++i) {
+ note.fpu.fpr[i] = cpu_to_dump64(s, env->fpr[i].vreg.UD[0]);
+ }
+
+ ret = f(¬e, LOONGARCH_PRFPREG_NOTE_SIZE, s);
+ if (ret < 0) {
+ return -1;
+ }
+
+ return 0;
+}
+
+int loongarch_cpu_write_elf64_note(WriteCoreDumpFunction f, CPUState *cs,
+ int cpuid, DumpState *s)
+{
+ struct loongarch_note note;
+ CPULoongArchState *env = &LOONGARCH_CPU(cs)->env;
+ int ret, i;
+
+ loongarch_note_init(¬e, s, "CORE", 5, NT_PRSTATUS,
+ sizeof(note.prstatus));
+ note.prstatus.pr_pid = cpu_to_dump32(s, cpuid);
+ note.prstatus.pr_fpvalid = cpu_to_dump32(s, 1);
+
+ for (i = 0; i < 32; ++i) {
+ note.prstatus.pr_reg.gpr[i] = cpu_to_dump64(s, env->gpr[i]);
+ }
+ note.prstatus.pr_reg.csr_era = cpu_to_dump64(s, env->CSR_ERA);
+ note.prstatus.pr_reg.csr_badv = cpu_to_dump64(s, env->CSR_BADV);
+ ret = f(¬e, LOONGARCH_PRSTATUS_NOTE_SIZE, s);
+ if (ret < 0) {
+ return -1;
+ }
+
+ ret = loongarch_write_elf64_fprpreg(f, env, cpuid, s);
+ if (ret < 0) {
+ return -1;
+ }
+
+ return ret;
+}
+
+int cpu_get_dump_info(ArchDumpInfo *info,
+ const GuestPhysBlockList *guest_phys_blocks)
+{
+ info->d_machine = EM_LOONGARCH;
+ info->d_endian = ELFDATA2LSB;
+ info->d_class = ELFCLASS64;
+
+ return 0;
+}
+
+ssize_t cpu_get_note_size(int class, int machine, int nr_cpus)
+{
+ size_t note_size = 0;
+
+ if (class == ELFCLASS64) {
+ note_size = LOONGARCH_PRSTATUS_NOTE_SIZE + LOONGARCH_PRFPREG_NOTE_SIZE;
+ }
+
+ return note_size * nr_cpus;
+}
diff --git a/target/loongarch/cpu.c b/target/loongarch/cpu.c
index 6a569285b8..7212fb5f8f 100644
--- a/target/loongarch/cpu.c
+++ b/target/loongarch/cpu.c
@@ -768,6 +768,7 @@ static const TCGCPUOps loongarch_tcg_ops = {
#include "hw/core/sysemu-cpu-ops.h"
static const struct SysemuCPUOps loongarch_sysemu_ops = {
+ .write_elf64_note = loongarch_cpu_write_elf64_note,
.get_phys_page_debug = loongarch_cpu_get_phys_page_debug,
};
diff --git a/target/loongarch/internals.h b/target/loongarch/internals.h
index 944153b180..1a02427627 100644
--- a/target/loongarch/internals.h
+++ b/target/loongarch/internals.h
@@ -72,5 +72,7 @@ void write_fcc(CPULoongArchState *env, uint64_t val);
int loongarch_cpu_gdb_read_register(CPUState *cs, GByteArray *mem_buf, int n);
int loongarch_cpu_gdb_write_register(CPUState *cs, uint8_t *mem_buf, int n);
void loongarch_cpu_register_gdb_regs_for_features(CPUState *cs);
+int loongarch_cpu_write_elf64_note(WriteCoreDumpFunction f, CPUState *cpu,
+ int cpuid, DumpState *s);
#endif
diff --git a/target/loongarch/meson.build b/target/loongarch/meson.build
index e002e9aaf6..7817318287 100644
--- a/target/loongarch/meson.build
+++ b/target/loongarch/meson.build
@@ -8,6 +8,7 @@ loongarch_ss.add(files(
loongarch_system_ss = ss.source_set()
loongarch_system_ss.add(files(
+ 'arch_dump.c',
'cpu_helper.c',
'loongarch-qmp-cmds.c',
'machine.c',
--
2.34.1
^ permalink raw reply related [flat|nested] 11+ messages in thread
* [PULL 5/7] hw/loongarch: virt: support up to 4 serial ports
2024-09-12 12:51 [PULL 0/7] loongarch-to-apply queue Song Gao
` (3 preceding siblings ...)
2024-09-12 12:51 ` [PULL 4/7] target/loongarch: Support QMP dump-guest-memory Song Gao
@ 2024-09-12 12:51 ` Song Gao
2024-09-12 12:51 ` [PULL 6/7] hw/loongarch: virt: pass random seed to fdt Song Gao
` (2 subsequent siblings)
7 siblings, 0 replies; 11+ messages in thread
From: Song Gao @ 2024-09-12 12:51 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, Jason A. Donenfeld, Bibo Mao
From: "Jason A. Donenfeld" <Jason@zx2c4.com>
In order to support additional channels of communication using
`-serial`, add several serial ports, up to the standard 4 generally
supported by the 8250 driver.
Fixed: https://lore.kernel.org/all/20240907143439.2792924-1-Jason@zx2c4.com/
Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
Tested-by: Bibo Mao <maobibo@loongson.cn>
[gaosong: ACPI uart need't reverse order]
Signed-off-by: Song Gao <gaosong@loongson.cn>
Message-Id: <20240907143439.2792924-1-Jason@zx2c4.com>
---
hw/loongarch/acpi-build.c | 23 +++++++++++++++--------
hw/loongarch/virt.c | 27 +++++++++++++++++----------
include/hw/pci-host/ls7a.h | 9 +++++----
3 files changed, 37 insertions(+), 22 deletions(-)
diff --git a/hw/loongarch/acpi-build.c b/hw/loongarch/acpi-build.c
index 2638f87434..04107c84ba 100644
--- a/hw/loongarch/acpi-build.c
+++ b/hw/loongarch/acpi-build.c
@@ -31,6 +31,7 @@
#include "hw/acpi/generic_event_device.h"
#include "hw/pci-host/gpex.h"
+#include "sysemu/sysemu.h"
#include "sysemu/tpm.h"
#include "hw/platform-bus.h"
#include "hw/acpi/aml-build.h"
@@ -252,23 +253,27 @@ struct AcpiBuildState {
MemoryRegion *linker_mr;
} AcpiBuildState;
-static void build_uart_device_aml(Aml *table)
+static void build_uart_device_aml(Aml *table, int index)
{
Aml *dev;
Aml *crs;
Aml *pkg0, *pkg1, *pkg2;
- uint32_t uart_irq = VIRT_UART_IRQ;
-
- Aml *scope = aml_scope("_SB");
- dev = aml_device("COMA");
+ Aml *scope;
+ uint32_t uart_irq;
+ uint64_t base;
+
+ uart_irq = VIRT_UART_IRQ + index;
+ base = VIRT_UART_BASE + index * VIRT_UART_SIZE;
+ scope = aml_scope("_SB");
+ dev = aml_device("COM%d", index);
aml_append(dev, aml_name_decl("_HID", aml_string("PNP0501")));
- aml_append(dev, aml_name_decl("_UID", aml_int(0)));
+ aml_append(dev, aml_name_decl("_UID", aml_int(index)));
aml_append(dev, aml_name_decl("_CCA", aml_int(1)));
crs = aml_resource_template();
aml_append(crs,
aml_qword_memory(AML_POS_DECODE, AML_MIN_FIXED, AML_MAX_FIXED,
AML_NON_CACHEABLE, AML_READ_WRITE,
- 0, VIRT_UART_BASE, VIRT_UART_BASE + VIRT_UART_SIZE - 1,
+ 0, base, base + VIRT_UART_SIZE - 1,
0, VIRT_UART_SIZE));
aml_append(crs, aml_interrupt(AML_CONSUMER, AML_LEVEL, AML_ACTIVE_HIGH,
AML_SHARED, &uart_irq, 1));
@@ -401,6 +406,7 @@ static void acpi_dsdt_add_tpm(Aml *scope, LoongArchVirtMachineState *vms)
static void
build_dsdt(GArray *table_data, BIOSLinker *linker, MachineState *machine)
{
+ int i;
Aml *dsdt, *scope, *pkg;
LoongArchVirtMachineState *lvms = LOONGARCH_VIRT_MACHINE(machine);
AcpiTable table = { .sig = "DSDT", .rev = 1, .oem_id = lvms->oem_id,
@@ -408,7 +414,8 @@ build_dsdt(GArray *table_data, BIOSLinker *linker, MachineState *machine)
acpi_table_begin(&table, table_data);
dsdt = init_aml_allocator();
- build_uart_device_aml(dsdt);
+ for (i = 0; i < VIRT_UART_COUNT; i++)
+ build_uart_device_aml(dsdt, i);
build_pci_device_aml(dsdt, lvms);
build_la_ged_aml(dsdt, machine);
build_flash_aml(dsdt, lvms);
diff --git a/hw/loongarch/virt.c b/hw/loongarch/virt.c
index 29040422aa..76dd29a391 100644
--- a/hw/loongarch/virt.c
+++ b/hw/loongarch/virt.c
@@ -280,10 +280,10 @@ static void fdt_add_rtc_node(LoongArchVirtMachineState *lvms,
}
static void fdt_add_uart_node(LoongArchVirtMachineState *lvms,
- uint32_t *pch_pic_phandle)
+ uint32_t *pch_pic_phandle, hwaddr base,
+ int irq, bool chosen)
{
char *nodename;
- hwaddr base = VIRT_UART_BASE;
hwaddr size = VIRT_UART_SIZE;
MachineState *ms = MACHINE(lvms);
@@ -292,9 +292,9 @@ static void fdt_add_uart_node(LoongArchVirtMachineState *lvms,
qemu_fdt_setprop_string(ms->fdt, nodename, "compatible", "ns16550a");
qemu_fdt_setprop_cells(ms->fdt, nodename, "reg", 0x0, base, 0x0, size);
qemu_fdt_setprop_cell(ms->fdt, nodename, "clock-frequency", 100000000);
- qemu_fdt_setprop_string(ms->fdt, "/chosen", "stdout-path", nodename);
- qemu_fdt_setprop_cells(ms->fdt, nodename, "interrupts",
- VIRT_UART_IRQ - VIRT_GSI_BASE, 0x4);
+ if (chosen)
+ qemu_fdt_setprop_string(ms->fdt, "/chosen", "stdout-path", nodename);
+ qemu_fdt_setprop_cells(ms->fdt, nodename, "interrupts", irq, 0x4);
qemu_fdt_setprop_cell(ms->fdt, nodename, "interrupt-parent",
*pch_pic_phandle);
g_free(nodename);
@@ -706,11 +706,18 @@ static void virt_devices_init(DeviceState *pch_pic,
/* Add pcie node */
fdt_add_pcie_node(lvms, pch_pic_phandle, pch_msi_phandle);
- serial_mm_init(get_system_memory(), VIRT_UART_BASE, 0,
- qdev_get_gpio_in(pch_pic,
- VIRT_UART_IRQ - VIRT_GSI_BASE),
- 115200, serial_hd(0), DEVICE_LITTLE_ENDIAN);
- fdt_add_uart_node(lvms, pch_pic_phandle);
+ /*
+ * Create uart fdt node in reverse order so that they appear
+ * in the finished device tree lowest address first
+ */
+ for (i = VIRT_UART_COUNT; i --> 0;) {
+ hwaddr base = VIRT_UART_BASE + i * VIRT_UART_SIZE;
+ int irq = VIRT_UART_IRQ + i - VIRT_GSI_BASE;
+ serial_mm_init(get_system_memory(), base, 0,
+ qdev_get_gpio_in(pch_pic, irq),
+ 115200, serial_hd(i), DEVICE_LITTLE_ENDIAN);
+ fdt_add_uart_node(lvms, pch_pic_phandle, base, irq, i == 0);
+ }
/* Network init */
pci_init_nic_devices(pci_bus, mc->default_nic);
diff --git a/include/hw/pci-host/ls7a.h b/include/hw/pci-host/ls7a.h
index cd7c9ec7bc..79d4ea8501 100644
--- a/include/hw/pci-host/ls7a.h
+++ b/include/hw/pci-host/ls7a.h
@@ -36,17 +36,18 @@
#define VIRT_PCH_PIC_IRQ_NUM 32
#define VIRT_GSI_BASE 64
#define VIRT_DEVICE_IRQS 16
+#define VIRT_UART_COUNT 4
#define VIRT_UART_IRQ (VIRT_GSI_BASE + 2)
#define VIRT_UART_BASE 0x1fe001e0
-#define VIRT_UART_SIZE 0X100
-#define VIRT_RTC_IRQ (VIRT_GSI_BASE + 3)
+#define VIRT_UART_SIZE 0x100
+#define VIRT_RTC_IRQ (VIRT_GSI_BASE + 6)
#define VIRT_MISC_REG_BASE (VIRT_PCH_REG_BASE + 0x00080000)
#define VIRT_RTC_REG_BASE (VIRT_MISC_REG_BASE + 0x00050100)
#define VIRT_RTC_LEN 0x100
-#define VIRT_SCI_IRQ (VIRT_GSI_BASE + 4)
+#define VIRT_SCI_IRQ (VIRT_GSI_BASE + 7)
#define VIRT_PLATFORM_BUS_BASEADDRESS 0x16000000
#define VIRT_PLATFORM_BUS_SIZE 0x2000000
#define VIRT_PLATFORM_BUS_NUM_IRQS 2
-#define VIRT_PLATFORM_BUS_IRQ (VIRT_GSI_BASE + 5)
+#define VIRT_PLATFORM_BUS_IRQ (VIRT_GSI_BASE + 8)
#endif
--
2.34.1
^ permalink raw reply related [flat|nested] 11+ messages in thread
* [PULL 6/7] hw/loongarch: virt: pass random seed to fdt
2024-09-12 12:51 [PULL 0/7] loongarch-to-apply queue Song Gao
` (4 preceding siblings ...)
2024-09-12 12:51 ` [PULL 5/7] hw/loongarch: virt: support up to 4 serial ports Song Gao
@ 2024-09-12 12:51 ` Song Gao
2024-11-18 19:57 ` Daniel P. Berrangé
2024-09-12 12:51 ` [PULL 7/7] hw/loongarch: Add acpi SPCR table support Song Gao
2024-09-13 13:34 ` [PULL 0/7] loongarch-to-apply queue Peter Maydell
7 siblings, 1 reply; 11+ messages in thread
From: Song Gao @ 2024-09-12 12:51 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, Jason A. Donenfeld
From: "Jason A. Donenfeld" <Jason@zx2c4.com>
If the FDT contains /chosen/rng-seed, then the Linux RNG will use it to
initialize early. Set this using the usual guest random number
generation function.
This is the same procedure that's done in b91b6b5a2c ("hw/microblaze:
pass random seed to fdt"), e4b4f0b71c ("hw/riscv: virt: pass random seed
to fdt"), c6fe3e6b4c ("hw/openrisc: virt: pass random seed to fdt"),
67f7e426e5 ("hw/i386: pass RNG seed via setup_data entry"), c287941a4d
("hw/rx: pass random seed to fdt"), 5e19cc68fb ("hw/mips: boston: pass
random seed to fdt"), 6b23a67916 ("hw/nios2: virt: pass random seed to fdt")
c4b075318e ("hw/ppc: pass random seed to fdt"), and 5242876f37
("hw/arm/virt: dt: add rng-seed property").
These earlier commits later were amended to rerandomize the RNG seed on
snapshot load, but the LoongArch code somehow already does that, despite
not having this patch here, presumably due to some lucky copy and
pasting.
Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
Reviewed-by: Song Gao <gaosong@loongson.cn>
Message-Id: <20240905153316.2038769-1-Jason@zx2c4.com>
Signed-off-by: Song Gao <gaosong@loongson.cn>
---
hw/loongarch/virt.c | 6 ++++++
1 file changed, 6 insertions(+)
diff --git a/hw/loongarch/virt.c b/hw/loongarch/virt.c
index 76dd29a391..81b1f9486f 100644
--- a/hw/loongarch/virt.c
+++ b/hw/loongarch/virt.c
@@ -48,6 +48,7 @@
#include "hw/block/flash.h"
#include "hw/virtio/virtio-iommu.h"
#include "qemu/error-report.h"
+#include "qemu/guest-random.h"
static bool virt_is_veiointc_enabled(LoongArchVirtMachineState *lvms)
{
@@ -303,6 +304,7 @@ static void fdt_add_uart_node(LoongArchVirtMachineState *lvms,
static void create_fdt(LoongArchVirtMachineState *lvms)
{
MachineState *ms = MACHINE(lvms);
+ uint8_t rng_seed[32];
ms->fdt = create_device_tree(&lvms->fdt_size);
if (!ms->fdt) {
@@ -316,6 +318,10 @@ static void create_fdt(LoongArchVirtMachineState *lvms)
qemu_fdt_setprop_cell(ms->fdt, "/", "#address-cells", 0x2);
qemu_fdt_setprop_cell(ms->fdt, "/", "#size-cells", 0x2);
qemu_fdt_add_subnode(ms->fdt, "/chosen");
+
+ /* Pass seed to RNG */
+ qemu_guest_getrandom_nofail(rng_seed, sizeof(rng_seed));
+ qemu_fdt_setprop(ms->fdt, "/chosen", "rng-seed", rng_seed, sizeof(rng_seed));
}
static void fdt_add_cpu_nodes(const LoongArchVirtMachineState *lvms)
--
2.34.1
^ permalink raw reply related [flat|nested] 11+ messages in thread
* Re: [PULL 6/7] hw/loongarch: virt: pass random seed to fdt
2024-09-12 12:51 ` [PULL 6/7] hw/loongarch: virt: pass random seed to fdt Song Gao
@ 2024-11-18 19:57 ` Daniel P. Berrangé
2024-11-19 1:36 ` mao bibo
0 siblings, 1 reply; 11+ messages in thread
From: Daniel P. Berrangé @ 2024-11-18 19:57 UTC (permalink / raw)
To: Song Gao; +Cc: qemu-devel, peter.maydell, Jason A. Donenfeld
Hi Song / Jason,
We're seeing non-deterministic hangs in our functional test
suite 'tests/functional/test_loongarch64_virt.py' and my
attempt at git bisect is blaming this commit.
With this applied, perhaps 1 time in 10, the test case hangs,
with zero serial port output from EDK2 emitted
https://gitlab.com/qemu-project/qemu/-/issues/2686
I'm not seeing an obvious flaw in this commit's code, so I'm
wondering if it has accidentally tickled some other subtle
pre-existing bug elsewhere. Some general problem with FDT
handling on loongarch64 perhaps ?
On Thu, Sep 12, 2024 at 08:51:31PM +0800, Song Gao wrote:
> From: "Jason A. Donenfeld" <Jason@zx2c4.com>
>
> If the FDT contains /chosen/rng-seed, then the Linux RNG will use it to
> initialize early. Set this using the usual guest random number
> generation function.
>
> This is the same procedure that's done in b91b6b5a2c ("hw/microblaze:
> pass random seed to fdt"), e4b4f0b71c ("hw/riscv: virt: pass random seed
> to fdt"), c6fe3e6b4c ("hw/openrisc: virt: pass random seed to fdt"),
> 67f7e426e5 ("hw/i386: pass RNG seed via setup_data entry"), c287941a4d
> ("hw/rx: pass random seed to fdt"), 5e19cc68fb ("hw/mips: boston: pass
> random seed to fdt"), 6b23a67916 ("hw/nios2: virt: pass random seed to fdt")
> c4b075318e ("hw/ppc: pass random seed to fdt"), and 5242876f37
> ("hw/arm/virt: dt: add rng-seed property").
>
> These earlier commits later were amended to rerandomize the RNG seed on
> snapshot load, but the LoongArch code somehow already does that, despite
> not having this patch here, presumably due to some lucky copy and
> pasting.
>
> Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
> Reviewed-by: Song Gao <gaosong@loongson.cn>
> Message-Id: <20240905153316.2038769-1-Jason@zx2c4.com>
> Signed-off-by: Song Gao <gaosong@loongson.cn>
> ---
> hw/loongarch/virt.c | 6 ++++++
> 1 file changed, 6 insertions(+)
>
> diff --git a/hw/loongarch/virt.c b/hw/loongarch/virt.c
> index 76dd29a391..81b1f9486f 100644
> --- a/hw/loongarch/virt.c
> +++ b/hw/loongarch/virt.c
> @@ -48,6 +48,7 @@
> #include "hw/block/flash.h"
> #include "hw/virtio/virtio-iommu.h"
> #include "qemu/error-report.h"
> +#include "qemu/guest-random.h"
>
> static bool virt_is_veiointc_enabled(LoongArchVirtMachineState *lvms)
> {
> @@ -303,6 +304,7 @@ static void fdt_add_uart_node(LoongArchVirtMachineState *lvms,
> static void create_fdt(LoongArchVirtMachineState *lvms)
> {
> MachineState *ms = MACHINE(lvms);
> + uint8_t rng_seed[32];
>
> ms->fdt = create_device_tree(&lvms->fdt_size);
> if (!ms->fdt) {
> @@ -316,6 +318,10 @@ static void create_fdt(LoongArchVirtMachineState *lvms)
> qemu_fdt_setprop_cell(ms->fdt, "/", "#address-cells", 0x2);
> qemu_fdt_setprop_cell(ms->fdt, "/", "#size-cells", 0x2);
> qemu_fdt_add_subnode(ms->fdt, "/chosen");
> +
> + /* Pass seed to RNG */
> + qemu_guest_getrandom_nofail(rng_seed, sizeof(rng_seed));
> + qemu_fdt_setprop(ms->fdt, "/chosen", "rng-seed", rng_seed, sizeof(rng_seed));
> }
>
> static void fdt_add_cpu_nodes(const LoongArchVirtMachineState *lvms)
> --
> 2.34.1
>
>
With regards,
Daniel
--
|: https://berrange.com -o- https://www.flickr.com/photos/dberrange :|
|: https://libvirt.org -o- https://fstop138.berrange.com :|
|: https://entangle-photo.org -o- https://www.instagram.com/dberrange :|
^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [PULL 6/7] hw/loongarch: virt: pass random seed to fdt
2024-11-18 19:57 ` Daniel P. Berrangé
@ 2024-11-19 1:36 ` mao bibo
0 siblings, 0 replies; 11+ messages in thread
From: mao bibo @ 2024-11-19 1:36 UTC (permalink / raw)
To: Daniel P. Berrangé, Song Gao
Cc: qemu-devel, peter.maydell, Jason A. Donenfeld,
lixianglai@loongson.cn
Hi Daniel,
Thanks for reporting the problem. I can reproduce this problem with my
local environment, we will investigate this issue ASAP.
Regards
Bibo Mao
On 2024/11/19 上午3:57, Daniel P. Berrangé wrote:
> Hi Song / Jason,
>
> We're seeing non-deterministic hangs in our functional test
> suite 'tests/functional/test_loongarch64_virt.py' and my
> attempt at git bisect is blaming this commit.
>
> With this applied, perhaps 1 time in 10, the test case hangs,
> with zero serial port output from EDK2 emitted
>
> https://gitlab.com/qemu-project/qemu/-/issues/2686
>
> I'm not seeing an obvious flaw in this commit's code, so I'm
> wondering if it has accidentally tickled some other subtle
> pre-existing bug elsewhere. Some general problem with FDT
> handling on loongarch64 perhaps ?
>
> On Thu, Sep 12, 2024 at 08:51:31PM +0800, Song Gao wrote:
>> From: "Jason A. Donenfeld" <Jason@zx2c4.com>
>>
>> If the FDT contains /chosen/rng-seed, then the Linux RNG will use it to
>> initialize early. Set this using the usual guest random number
>> generation function.
>>
>> This is the same procedure that's done in b91b6b5a2c ("hw/microblaze:
>> pass random seed to fdt"), e4b4f0b71c ("hw/riscv: virt: pass random seed
>> to fdt"), c6fe3e6b4c ("hw/openrisc: virt: pass random seed to fdt"),
>> 67f7e426e5 ("hw/i386: pass RNG seed via setup_data entry"), c287941a4d
>> ("hw/rx: pass random seed to fdt"), 5e19cc68fb ("hw/mips: boston: pass
>> random seed to fdt"), 6b23a67916 ("hw/nios2: virt: pass random seed to fdt")
>> c4b075318e ("hw/ppc: pass random seed to fdt"), and 5242876f37
>> ("hw/arm/virt: dt: add rng-seed property").
>>
>> These earlier commits later were amended to rerandomize the RNG seed on
>> snapshot load, but the LoongArch code somehow already does that, despite
>> not having this patch here, presumably due to some lucky copy and
>> pasting.
>>
>> Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
>> Reviewed-by: Song Gao <gaosong@loongson.cn>
>> Message-Id: <20240905153316.2038769-1-Jason@zx2c4.com>
>> Signed-off-by: Song Gao <gaosong@loongson.cn>
>> ---
>> hw/loongarch/virt.c | 6 ++++++
>> 1 file changed, 6 insertions(+)
>>
>> diff --git a/hw/loongarch/virt.c b/hw/loongarch/virt.c
>> index 76dd29a391..81b1f9486f 100644
>> --- a/hw/loongarch/virt.c
>> +++ b/hw/loongarch/virt.c
>> @@ -48,6 +48,7 @@
>> #include "hw/block/flash.h"
>> #include "hw/virtio/virtio-iommu.h"
>> #include "qemu/error-report.h"
>> +#include "qemu/guest-random.h"
>>
>> static bool virt_is_veiointc_enabled(LoongArchVirtMachineState *lvms)
>> {
>> @@ -303,6 +304,7 @@ static void fdt_add_uart_node(LoongArchVirtMachineState *lvms,
>> static void create_fdt(LoongArchVirtMachineState *lvms)
>> {
>> MachineState *ms = MACHINE(lvms);
>> + uint8_t rng_seed[32];
>>
>> ms->fdt = create_device_tree(&lvms->fdt_size);
>> if (!ms->fdt) {
>> @@ -316,6 +318,10 @@ static void create_fdt(LoongArchVirtMachineState *lvms)
>> qemu_fdt_setprop_cell(ms->fdt, "/", "#address-cells", 0x2);
>> qemu_fdt_setprop_cell(ms->fdt, "/", "#size-cells", 0x2);
>> qemu_fdt_add_subnode(ms->fdt, "/chosen");
>> +
>> + /* Pass seed to RNG */
>> + qemu_guest_getrandom_nofail(rng_seed, sizeof(rng_seed));
>> + qemu_fdt_setprop(ms->fdt, "/chosen", "rng-seed", rng_seed, sizeof(rng_seed));
>> }
>>
>> static void fdt_add_cpu_nodes(const LoongArchVirtMachineState *lvms)
>> --
>> 2.34.1
>>
>>
>
> With regards,
> Daniel
>
^ permalink raw reply [flat|nested] 11+ messages in thread
* [PULL 7/7] hw/loongarch: Add acpi SPCR table support
2024-09-12 12:51 [PULL 0/7] loongarch-to-apply queue Song Gao
` (5 preceding siblings ...)
2024-09-12 12:51 ` [PULL 6/7] hw/loongarch: virt: pass random seed to fdt Song Gao
@ 2024-09-12 12:51 ` Song Gao
2024-09-13 13:34 ` [PULL 0/7] loongarch-to-apply queue Peter Maydell
7 siblings, 0 replies; 11+ messages in thread
From: Song Gao @ 2024-09-12 12:51 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, Bibo Mao
From: Bibo Mao <maobibo@loongson.cn>
Serial port console redirection table can be used for default serial
port selection, like chosen stdout-path selection with FDT method.
With acpi SPCR table added, early debug console can be parsed from
SPCR table with simple kernel parameter earlycon rather than
earlycon=uart,mmio,0x1fe001e0
Signed-off-by: Bibo Mao <maobibo@loongson.cn>
Reviewed-by: Song Gao <gaosong@loongson.cn>
Message-Id: <20240907073037.243353-1-maobibo@loongson.cn>
Signed-off-by: Song Gao <gaosong@loongson.cn>
---
hw/loongarch/acpi-build.c | 40 +++++++++++++++++++++++++++++++++++++++
1 file changed, 40 insertions(+)
diff --git a/hw/loongarch/acpi-build.c b/hw/loongarch/acpi-build.c
index 04107c84ba..50709bda0f 100644
--- a/hw/loongarch/acpi-build.c
+++ b/hw/loongarch/acpi-build.c
@@ -242,6 +242,44 @@ build_srat(GArray *table_data, BIOSLinker *linker, MachineState *machine)
acpi_table_end(linker, &table);
}
+/*
+ * Serial Port Console Redirection Table (SPCR)
+ * https://learn.microsoft.com/en-us/windows-hardware/drivers/serports/serial-port-console-redirection-table
+ */
+static void
+spcr_setup(GArray *table_data, BIOSLinker *linker, MachineState *machine)
+{
+ LoongArchVirtMachineState *lvms;
+ AcpiSpcrData serial = {
+ .interface_type = 0, /* 16550 compatible */
+ .base_addr.id = AML_AS_SYSTEM_MEMORY,
+ .base_addr.width = 32,
+ .base_addr.offset = 0,
+ .base_addr.size = 1,
+ .base_addr.addr = VIRT_UART_BASE,
+ .interrupt_type = 0, /* Interrupt not supported */
+ .pc_interrupt = 0,
+ .interrupt = VIRT_UART_IRQ,
+ .baud_rate = 7, /* 115200 */
+ .parity = 0,
+ .stop_bits = 1,
+ .flow_control = 0,
+ .terminal_type = 3, /* ANSI */
+ .language = 0, /* Language */
+ .pci_device_id = 0xffff, /* not a PCI device*/
+ .pci_vendor_id = 0xffff, /* not a PCI device*/
+ .pci_bus = 0,
+ .pci_device = 0,
+ .pci_function = 0,
+ .pci_flags = 0,
+ .pci_segment = 0,
+ };
+
+ lvms = LOONGARCH_VIRT_MACHINE(machine);
+ build_spcr(table_data, linker, &serial, 2, lvms->oem_id,
+ lvms->oem_table_id);
+}
+
typedef
struct AcpiBuildState {
/* Copy of table in RAM (for patching). */
@@ -484,6 +522,8 @@ static void acpi_build(AcpiBuildTables *tables, MachineState *machine)
acpi_add_table(table_offsets, tables_blob);
build_srat(tables_blob, tables->linker, machine);
+ acpi_add_table(table_offsets, tables_blob);
+ spcr_setup(tables_blob, tables->linker, machine);
if (machine->numa_state->num_nodes) {
if (machine->numa_state->have_numa_distance) {
--
2.34.1
^ permalink raw reply related [flat|nested] 11+ messages in thread
* Re: [PULL 0/7] loongarch-to-apply queue
2024-09-12 12:51 [PULL 0/7] loongarch-to-apply queue Song Gao
` (6 preceding siblings ...)
2024-09-12 12:51 ` [PULL 7/7] hw/loongarch: Add acpi SPCR table support Song Gao
@ 2024-09-13 13:34 ` Peter Maydell
7 siblings, 0 replies; 11+ messages in thread
From: Peter Maydell @ 2024-09-13 13:34 UTC (permalink / raw)
To: Song Gao; +Cc: qemu-devel
On Thu, 12 Sept 2024 at 14:09, Song Gao <gaosong@loongson.cn> wrote:
>
> The following changes since commit 4b7ea33074450bc6148c8e1545d78f179e64adb4:
>
> Merge tag 'pull-request-2024-09-11' of https://gitlab.com/thuth/qemu into staging (2024-09-11 19:28:23 +0100)
>
> are available in the Git repository at:
>
> https://gitlab.com/gaosong/qemu.git tags/pull-loongarch-20240912
>
> for you to fetch changes up to 45d1fe46e5a6fe2b22b034e2b2bc0d941acd4b9e:
>
> hw/loongarch: Add acpi SPCR table support (2024-09-12 20:57:54 +0800)
>
> ----------------------------------------------------------------
> pull-loongarch-20240912
>
> ----------------------------------------------------------------
Applied, thanks.
Please update the changelog at https://wiki.qemu.org/ChangeLog/9.2
for any user-visible changes.
-- PMM
^ permalink raw reply [flat|nested] 11+ messages in thread