diff options
author | Song Gao <gaosong@loongson.cn> | 2023-04-06 15:11:31 +0800 |
---|---|---|
committer | Song Gao <gaosong@loongson.cn> | 2023-05-15 19:09:33 +0800 |
commit | 7ef0eb35a4e6961d7e40f03f16ed241c95ae93f9 (patch) | |
tree | ddd4866838ad501e49382744c48e5fe6857736e9 /hw/intc | |
parent | 646c39b220f789158313fee5d207f370e29c586a (diff) | |
download | qemu-7ef0eb35a4e6961d7e40f03f16ed241c95ae93f9.zip qemu-7ef0eb35a4e6961d7e40f03f16ed241c95ae93f9.tar.gz qemu-7ef0eb35a4e6961d7e40f03f16ed241c95ae93f9.tar.bz2 |
hw/intc: Add NULL pointer check on LoongArch ipi device
When ipi mailbox is used, cpu_index is decoded from iocsr register.
cpu maybe does not exist. This patch adds NULL pointer check on
ipi device.
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
Signed-off-by: Song Gao <gaosong@loongson.cn>
Message-Id: <20230512100421.1867848-4-gaosong@loongson.cn>
Diffstat (limited to 'hw/intc')
-rw-r--r-- | hw/intc/loongarch_ipi.c | 40 | ||||
-rw-r--r-- | hw/intc/trace-events | 1 |
2 files changed, 30 insertions, 11 deletions
diff --git a/hw/intc/loongarch_ipi.c b/hw/intc/loongarch_ipi.c index 054e143..d6ab917 100644 --- a/hw/intc/loongarch_ipi.c +++ b/hw/intc/loongarch_ipi.c @@ -77,31 +77,42 @@ static void send_ipi_data(CPULoongArchState *env, uint64_t val, hwaddr addr) static void ipi_send(uint64_t val) { - int cpuid, data; + uint32_t cpuid; + uint8_t vector; CPULoongArchState *env; CPUState *cs; LoongArchCPU *cpu; - cpuid = (val >> 16) & 0x3ff; + cpuid = extract32(val, 16, 10); + if (cpuid >= LOONGARCH_MAX_CPUS) { + trace_loongarch_ipi_unsupported_cpuid("IOCSR_IPI_SEND", cpuid); + return; + } + /* IPI status vector */ - data = 1 << (val & 0x1f); + vector = extract8(val, 0, 5); + cs = qemu_get_cpu(cpuid); cpu = LOONGARCH_CPU(cs); env = &cpu->env; address_space_stl(&env->address_space_iocsr, 0x1008, - data, MEMTXATTRS_UNSPECIFIED, NULL); - + BIT(vector), MEMTXATTRS_UNSPECIFIED, NULL); } static void mail_send(uint64_t val) { - int cpuid; + uint32_t cpuid; hwaddr addr; CPULoongArchState *env; CPUState *cs; LoongArchCPU *cpu; - cpuid = (val >> 16) & 0x3ff; + cpuid = extract32(val, 16, 10); + if (cpuid >= LOONGARCH_MAX_CPUS) { + trace_loongarch_ipi_unsupported_cpuid("IOCSR_MAIL_SEND", cpuid); + return; + } + addr = 0x1020 + (val & 0x1c); cs = qemu_get_cpu(cpuid); cpu = LOONGARCH_CPU(cs); @@ -111,14 +122,21 @@ static void mail_send(uint64_t val) static void any_send(uint64_t val) { - int cpuid; + uint32_t cpuid; hwaddr addr; CPULoongArchState *env; + CPUState *cs; + LoongArchCPU *cpu; + + cpuid = extract32(val, 16, 10); + if (cpuid >= LOONGARCH_MAX_CPUS) { + trace_loongarch_ipi_unsupported_cpuid("IOCSR_ANY_SEND", cpuid); + return; + } - cpuid = (val >> 16) & 0x3ff; addr = val & 0xffff; - CPUState *cs = qemu_get_cpu(cpuid); - LoongArchCPU *cpu = LOONGARCH_CPU(cs); + cs = qemu_get_cpu(cpuid); + cpu = LOONGARCH_CPU(cs); env = &cpu->env; send_ipi_data(env, val, addr); } diff --git a/hw/intc/trace-events b/hw/intc/trace-events index 50cadfb..5c6094c 100644 --- a/hw/intc/trace-events +++ b/hw/intc/trace-events @@ -292,6 +292,7 @@ sh_intc_set(int id, int enable) "setting interrupt group %d to %d" # loongarch_ipi.c loongarch_ipi_read(unsigned size, uint64_t addr, uint64_t val) "size: %u addr: 0x%"PRIx64 "val: 0x%"PRIx64 loongarch_ipi_write(unsigned size, uint64_t addr, uint64_t val) "size: %u addr: 0x%"PRIx64 "val: 0x%"PRIx64 +loongarch_ipi_unsupported_cpuid(const char *s, uint32_t cpuid) "%s unsupported cpuid 0x%" PRIx32 # loongarch_pch_pic.c loongarch_pch_pic_irq_handler(int irq, int level) "irq %d level %d" |