qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v3 0/2] Fix IPI device emulation for LoongArch machine
@ 2022-07-05  6:48 Xiaojuan Yang
  2022-07-05  6:49 ` [PATCH 1/2] hw/intc/loongarch_ipi: Fix ipi device access of 64bits Xiaojuan Yang
                   ` (2 more replies)
  0 siblings, 3 replies; 4+ messages in thread
From: Xiaojuan Yang @ 2022-07-05  6:48 UTC (permalink / raw)
  To: qemu-devel
  Cc: richard.henderson, gaosong, maobibo, mark.cave-ayland, mst,
	imammedo, ani, f4bug, peter.maydell

Fix LoongArch IPI device emulation follwing Richard's advice based on v2 version:
1. Change ipi64_ops' valid.min_access_size to 8, as it only support 8 bytes writing.
2. Remove 'UL' prefix in send_ipi_data().
3. Add a condition to skip the method of geting write mask in send_ipi_data(), as the mask is 0 at most time.

Xiaojuan Yang (2):
  hw/intc/loongarch_ipi: Fix ipi device access of 64bits
  hw/intc/loongarch_ipi: Fix mail send and any send function

 hw/intc/loongarch_ipi.c         | 92 ++++++++++++++++++++++-----------
 hw/loongarch/loongson3.c        |  5 +-
 include/hw/intc/loongarch_ipi.h |  7 +--
 3 files changed, 70 insertions(+), 34 deletions(-)

-- 
2.31.1



^ permalink raw reply	[flat|nested] 4+ messages in thread

* [PATCH 1/2] hw/intc/loongarch_ipi: Fix ipi device access of 64bits
  2022-07-05  6:48 [PATCH v3 0/2] Fix IPI device emulation for LoongArch machine Xiaojuan Yang
@ 2022-07-05  6:49 ` Xiaojuan Yang
  2022-07-05  6:49 ` [PATCH 2/2] hw/intc/loongarch_ipi: Fix mail send and any send function Xiaojuan Yang
  2022-07-05 10:54 ` [PATCH v3 0/2] Fix IPI device emulation for LoongArch machine Richard Henderson
  2 siblings, 0 replies; 4+ messages in thread
From: Xiaojuan Yang @ 2022-07-05  6:49 UTC (permalink / raw)
  To: qemu-devel
  Cc: richard.henderson, gaosong, maobibo, mark.cave-ayland, mst,
	imammedo, ani, f4bug, peter.maydell

In general loongarch ipi device, 32bit registers is emulated, however for
anysend/mailsend device only 64bit register access is supported. So separate
the ipi memory region into two regions, including 32 bits and 64 bits.

Signed-off-by: Xiaojuan Yang <yangxiaojuan@loongson.cn>
---
 hw/intc/loongarch_ipi.c         | 38 +++++++++++++++++++++++++++------
 hw/loongarch/loongson3.c        |  5 ++++-
 include/hw/intc/loongarch_ipi.h |  7 +++---
 3 files changed, 39 insertions(+), 11 deletions(-)

diff --git a/hw/intc/loongarch_ipi.c b/hw/intc/loongarch_ipi.c
index 66bee93675..b8b1b9cd53 100644
--- a/hw/intc/loongarch_ipi.c
+++ b/hw/intc/loongarch_ipi.c
@@ -150,12 +150,6 @@ static void loongarch_ipi_writel(void *opaque, hwaddr addr, uint64_t val,
     case IOCSR_IPI_SEND:
         ipi_send(val);
         break;
-    case IOCSR_MAIL_SEND:
-        mail_send(val);
-        break;
-    case IOCSR_ANY_SEND:
-        any_send(val);
-        break;
     default:
         qemu_log_mask(LOG_UNIMP, "invalid write: %x", (uint32_t)addr);
         break;
@@ -172,6 +166,32 @@ static const MemoryRegionOps loongarch_ipi_ops = {
     .endianness = DEVICE_LITTLE_ENDIAN,
 };
 
+/* mail send and any send only support writeq */
+static void loongarch_ipi_writeq(void *opaque, hwaddr addr, uint64_t val,
+                                 unsigned size)
+{
+    addr &= 0xfff;
+    switch (addr) {
+    case MAIL_SEND_OFFSET:
+        mail_send(val);
+        break;
+    case ANY_SEND_OFFSET:
+        any_send(val);
+        break;
+    default:
+       break;
+    }
+}
+
+static const MemoryRegionOps loongarch_ipi64_ops = {
+    .write = loongarch_ipi_writeq,
+    .impl.min_access_size = 8,
+    .impl.max_access_size = 8,
+    .valid.min_access_size = 8,
+    .valid.max_access_size = 8,
+    .endianness = DEVICE_LITTLE_ENDIAN,
+};
+
 static void loongarch_ipi_init(Object *obj)
 {
     int cpu;
@@ -187,8 +207,12 @@ static void loongarch_ipi_init(Object *obj)
     lams = LOONGARCH_MACHINE(machine);
     for (cpu = 0; cpu < MAX_IPI_CORE_NUM; cpu++) {
         memory_region_init_io(&s->ipi_iocsr_mem[cpu], obj, &loongarch_ipi_ops,
-                            &lams->ipi_core[cpu], "loongarch_ipi_iocsr", 0x100);
+                            &lams->ipi_core[cpu], "loongarch_ipi_iocsr", 0x48);
         sysbus_init_mmio(sbd, &s->ipi_iocsr_mem[cpu]);
+
+        memory_region_init_io(&s->ipi64_iocsr_mem[cpu], obj, &loongarch_ipi64_ops,
+                              &lams->ipi_core[cpu], "loongarch_ipi64_iocsr", 0x118);
+        sysbus_init_mmio(sbd, &s->ipi64_iocsr_mem[cpu]);
         qdev_init_gpio_out(DEVICE(obj), &lams->ipi_core[cpu].irq, 1);
     }
 }
diff --git a/hw/loongarch/loongson3.c b/hw/loongarch/loongson3.c
index a0cd61cc88..d14ec06d02 100644
--- a/hw/loongarch/loongson3.c
+++ b/hw/loongarch/loongson3.c
@@ -453,7 +453,10 @@ static void loongarch_irq_init(LoongArchMachineState *lams)
         /* IPI iocsr memory region */
         memory_region_add_subregion(&env->system_iocsr, SMP_IPI_MAILBOX,
                                     sysbus_mmio_get_region(SYS_BUS_DEVICE(ipi),
-                                    cpu));
+                                    cpu * 2));
+        memory_region_add_subregion(&env->system_iocsr, MAIL_SEND_ADDR,
+                                    sysbus_mmio_get_region(SYS_BUS_DEVICE(ipi),
+                                    cpu * 2 + 1));
         /* extioi iocsr memory region */
         memory_region_add_subregion(&env->system_iocsr, APIC_BASE,
                                 sysbus_mmio_get_region(SYS_BUS_DEVICE(extioi),
diff --git a/include/hw/intc/loongarch_ipi.h b/include/hw/intc/loongarch_ipi.h
index 996ed7ea93..0ee48fca55 100644
--- a/include/hw/intc/loongarch_ipi.h
+++ b/include/hw/intc/loongarch_ipi.h
@@ -24,8 +24,9 @@
 #define IOCSR_MAIL_SEND       0x48
 #define IOCSR_ANY_SEND        0x158
 
-/* IPI system memory address */
-#define IPI_SYSTEM_MEM        0x1fe01000
+#define MAIL_SEND_ADDR        (SMP_IPI_MAILBOX + IOCSR_MAIL_SEND)
+#define MAIL_SEND_OFFSET      0
+#define ANY_SEND_OFFSET       (IOCSR_ANY_SEND - IOCSR_MAIL_SEND)
 
 #define MAX_IPI_CORE_NUM      4
 #define MAX_IPI_MBX_NUM       4
@@ -46,7 +47,7 @@ typedef struct IPICore {
 struct LoongArchIPI {
     SysBusDevice parent_obj;
     MemoryRegion ipi_iocsr_mem[MAX_IPI_CORE_NUM];
-    MemoryRegion ipi_system_mem[MAX_IPI_CORE_NUM];
+    MemoryRegion ipi64_iocsr_mem[MAX_IPI_CORE_NUM];
 };
 
 #endif
-- 
2.31.1



^ permalink raw reply related	[flat|nested] 4+ messages in thread

* [PATCH 2/2] hw/intc/loongarch_ipi: Fix mail send and any send function
  2022-07-05  6:48 [PATCH v3 0/2] Fix IPI device emulation for LoongArch machine Xiaojuan Yang
  2022-07-05  6:49 ` [PATCH 1/2] hw/intc/loongarch_ipi: Fix ipi device access of 64bits Xiaojuan Yang
@ 2022-07-05  6:49 ` Xiaojuan Yang
  2022-07-05 10:54 ` [PATCH v3 0/2] Fix IPI device emulation for LoongArch machine Richard Henderson
  2 siblings, 0 replies; 4+ messages in thread
From: Xiaojuan Yang @ 2022-07-05  6:49 UTC (permalink / raw)
  To: qemu-devel
  Cc: richard.henderson, gaosong, maobibo, mark.cave-ayland, mst,
	imammedo, ani, f4bug, peter.maydell

By the document of ipi mailsend device, byte is written only when the mask bit
is 0. The original code discards mask bit and overwrite the data always, this
patch fixes the issue.

Signed-off-by: Xiaojuan Yang <yangxiaojuan@loongson.cn>
---
 hw/intc/loongarch_ipi.c | 54 +++++++++++++++++++++++------------------
 1 file changed, 31 insertions(+), 23 deletions(-)

diff --git a/hw/intc/loongarch_ipi.c b/hw/intc/loongarch_ipi.c
index b8b1b9cd53..4f3c58f872 100644
--- a/hw/intc/loongarch_ipi.c
+++ b/hw/intc/loongarch_ipi.c
@@ -50,35 +50,45 @@ static uint64_t loongarch_ipi_readl(void *opaque, hwaddr addr, unsigned size)
     return ret;
 }
 
-static int get_ipi_data(target_ulong val)
+static void send_ipi_data(CPULoongArchState *env, target_ulong val, target_ulong addr)
 {
-    int i, mask, data;
+    int i, mask = 0, data = 0;
 
-    data = val >> 32;
-    mask = (val >> 27) & 0xf;
-
-    for (i = 0; i < 4; i++) {
-        if ((mask >> i) & 1) {
-            data &= ~(0xff << (i * 8));
+    /*
+     * bit 27-30 is mask for byte writing,
+     * if the mask is 0, we need not to do anything.
+     */
+    if ((val >> 27) & 0xf) {
+        data = address_space_ldl(&env->address_space_iocsr, addr,
+                                 MEMTXATTRS_UNSPECIFIED, NULL);
+        for (i = 0; i < 4; i++) {
+            /* get mask for byte writing */
+            if (val & (0x1 << (27 + i))) {
+                mask |= 0xff << (i * 8);
+            }
         }
     }
-    return data;
+
+    data &= mask;
+    data |= (val >> 32) & ~mask;
+    address_space_stl(&env->address_space_iocsr, addr,
+                      data, MEMTXATTRS_UNSPECIFIED, NULL);
 }
 
 static void ipi_send(uint64_t val)
 {
     int cpuid, data;
     CPULoongArchState *env;
+    CPUState *cs;
+    LoongArchCPU *cpu;
 
     cpuid = (val >> 16) & 0x3ff;
     /* IPI status vector */
     data = 1 << (val & 0x1f);
-    qemu_mutex_lock_iothread();
-    CPUState *cs = qemu_get_cpu(cpuid);
-    LoongArchCPU *cpu = LOONGARCH_CPU(cs);
+    cs = qemu_get_cpu(cpuid);
+    cpu = LOONGARCH_CPU(cs);
     env = &cpu->env;
     loongarch_cpu_set_irq(cpu, IRQ_IPI, 1);
-    qemu_mutex_unlock_iothread();
     address_space_stl(&env->address_space_iocsr, 0x1008,
                       data, MEMTXATTRS_UNSPECIFIED, NULL);
 
@@ -86,23 +96,23 @@ static void ipi_send(uint64_t val)
 
 static void mail_send(uint64_t val)
 {
-    int cpuid, data;
+    int cpuid;
     hwaddr addr;
     CPULoongArchState *env;
+    CPUState *cs;
+    LoongArchCPU *cpu;
 
     cpuid = (val >> 16) & 0x3ff;
     addr = 0x1020 + (val & 0x1c);
-    CPUState *cs = qemu_get_cpu(cpuid);
-    LoongArchCPU *cpu = LOONGARCH_CPU(cs);
+    cs = qemu_get_cpu(cpuid);
+    cpu = LOONGARCH_CPU(cs);
     env = &cpu->env;
-    data = get_ipi_data(val);
-    address_space_stl(&env->address_space_iocsr, addr,
-                      data, MEMTXATTRS_UNSPECIFIED, NULL);
+    send_ipi_data(env, val, addr);
 }
 
 static void any_send(uint64_t val)
 {
-    int cpuid, data;
+    int cpuid;
     hwaddr addr;
     CPULoongArchState *env;
 
@@ -111,9 +121,7 @@ static void any_send(uint64_t val)
     CPUState *cs = qemu_get_cpu(cpuid);
     LoongArchCPU *cpu = LOONGARCH_CPU(cs);
     env = &cpu->env;
-    data = get_ipi_data(val);
-    address_space_stl(&env->address_space_iocsr, addr,
-                      data, MEMTXATTRS_UNSPECIFIED, NULL);
+    send_ipi_data(env, val, addr);
 }
 
 static void loongarch_ipi_writel(void *opaque, hwaddr addr, uint64_t val,
-- 
2.31.1



^ permalink raw reply related	[flat|nested] 4+ messages in thread

* Re: [PATCH v3 0/2] Fix IPI device emulation for LoongArch machine
  2022-07-05  6:48 [PATCH v3 0/2] Fix IPI device emulation for LoongArch machine Xiaojuan Yang
  2022-07-05  6:49 ` [PATCH 1/2] hw/intc/loongarch_ipi: Fix ipi device access of 64bits Xiaojuan Yang
  2022-07-05  6:49 ` [PATCH 2/2] hw/intc/loongarch_ipi: Fix mail send and any send function Xiaojuan Yang
@ 2022-07-05 10:54 ` Richard Henderson
  2 siblings, 0 replies; 4+ messages in thread
From: Richard Henderson @ 2022-07-05 10:54 UTC (permalink / raw)
  To: Xiaojuan Yang, qemu-devel
  Cc: gaosong, maobibo, mark.cave-ayland, mst, imammedo, ani, f4bug,
	peter.maydell

On 7/5/22 12:18, Xiaojuan Yang wrote:
> Fix LoongArch IPI device emulation follwing Richard's advice based on v2 version:
> 1. Change ipi64_ops' valid.min_access_size to 8, as it only support 8 bytes writing.
> 2. Remove 'UL' prefix in send_ipi_data().
> 3. Add a condition to skip the method of geting write mask in send_ipi_data(), as the mask is 0 at most time.
> 
> Xiaojuan Yang (2):
>    hw/intc/loongarch_ipi: Fix ipi device access of 64bits
>    hw/intc/loongarch_ipi: Fix mail send and any send function
> 
>   hw/intc/loongarch_ipi.c         | 92 ++++++++++++++++++++++-----------
>   hw/loongarch/loongson3.c        |  5 +-
>   include/hw/intc/loongarch_ipi.h |  7 +--
>   3 files changed, 70 insertions(+), 34 deletions(-)
> 

Reviewed-by: Richard Henderson <richard.henderson@linaro.org>

Applied.


r~


^ permalink raw reply	[flat|nested] 4+ messages in thread

end of thread, other threads:[~2022-07-05 11:00 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2022-07-05  6:48 [PATCH v3 0/2] Fix IPI device emulation for LoongArch machine Xiaojuan Yang
2022-07-05  6:49 ` [PATCH 1/2] hw/intc/loongarch_ipi: Fix ipi device access of 64bits Xiaojuan Yang
2022-07-05  6:49 ` [PATCH 2/2] hw/intc/loongarch_ipi: Fix mail send and any send function Xiaojuan Yang
2022-07-05 10:54 ` [PATCH v3 0/2] Fix IPI device emulation for LoongArch machine Richard Henderson

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).