1*c403d5ffSBibo Mao /* SPDX-License-Identifier: GPL-2.0-or-later */ 2*c403d5ffSBibo Mao /* 3*c403d5ffSBibo Mao * LoongArch IPI interrupt support 4*c403d5ffSBibo Mao * 5*c403d5ffSBibo Mao * Copyright (C) 2024 Loongson Technology Corporation Limited 6*c403d5ffSBibo Mao */ 7*c403d5ffSBibo Mao 8*c403d5ffSBibo Mao #include "qemu/osdep.h" 9*c403d5ffSBibo Mao #include "hw/boards.h" 10*c403d5ffSBibo Mao #include "hw/intc/loongarch_ipi.h" 11*c403d5ffSBibo Mao #include "target/loongarch/cpu.h" 12*c403d5ffSBibo Mao 13*c403d5ffSBibo Mao static AddressSpace *get_iocsr_as(CPUState *cpu) 14*c403d5ffSBibo Mao { 15*c403d5ffSBibo Mao return LOONGARCH_CPU(cpu)->env.address_space_iocsr; 16*c403d5ffSBibo Mao } 17*c403d5ffSBibo Mao 18*c403d5ffSBibo Mao static int archid_cmp(const void *a, const void *b) 19*c403d5ffSBibo Mao { 20*c403d5ffSBibo Mao CPUArchId *archid_a = (CPUArchId *)a; 21*c403d5ffSBibo Mao CPUArchId *archid_b = (CPUArchId *)b; 22*c403d5ffSBibo Mao 23*c403d5ffSBibo Mao return archid_a->arch_id - archid_b->arch_id; 24*c403d5ffSBibo Mao } 25*c403d5ffSBibo Mao 26*c403d5ffSBibo Mao static CPUArchId *find_cpu_by_archid(MachineState *ms, uint32_t id) 27*c403d5ffSBibo Mao { 28*c403d5ffSBibo Mao CPUArchId apic_id, *found_cpu; 29*c403d5ffSBibo Mao 30*c403d5ffSBibo Mao apic_id.arch_id = id; 31*c403d5ffSBibo Mao found_cpu = bsearch(&apic_id, ms->possible_cpus->cpus, 32*c403d5ffSBibo Mao ms->possible_cpus->len, 33*c403d5ffSBibo Mao sizeof(*ms->possible_cpus->cpus), 34*c403d5ffSBibo Mao archid_cmp); 35*c403d5ffSBibo Mao 36*c403d5ffSBibo Mao return found_cpu; 37*c403d5ffSBibo Mao } 38*c403d5ffSBibo Mao 39*c403d5ffSBibo Mao static CPUState *loongarch_cpu_by_arch_id(int64_t arch_id) 40*c403d5ffSBibo Mao { 41*c403d5ffSBibo Mao MachineState *machine = MACHINE(qdev_get_machine()); 42*c403d5ffSBibo Mao CPUArchId *archid; 43*c403d5ffSBibo Mao 44*c403d5ffSBibo Mao archid = find_cpu_by_archid(machine, arch_id); 45*c403d5ffSBibo Mao if (archid) { 46*c403d5ffSBibo Mao return CPU(archid->cpu); 47*c403d5ffSBibo Mao } 48*c403d5ffSBibo Mao 49*c403d5ffSBibo Mao return NULL; 50*c403d5ffSBibo Mao } 51*c403d5ffSBibo Mao 52*c403d5ffSBibo Mao static void loongarch_ipi_class_init(ObjectClass *klass, void *data) 53*c403d5ffSBibo Mao { 54*c403d5ffSBibo Mao LoongsonIPICommonClass *licc = LOONGSON_IPI_COMMON_CLASS(klass); 55*c403d5ffSBibo Mao 56*c403d5ffSBibo Mao licc->get_iocsr_as = get_iocsr_as; 57*c403d5ffSBibo Mao licc->cpu_by_arch_id = loongarch_cpu_by_arch_id; 58*c403d5ffSBibo Mao } 59*c403d5ffSBibo Mao 60*c403d5ffSBibo Mao static const TypeInfo loongarch_ipi_types[] = { 61*c403d5ffSBibo Mao { 62*c403d5ffSBibo Mao .name = TYPE_LOONGARCH_IPI, 63*c403d5ffSBibo Mao .parent = TYPE_LOONGSON_IPI_COMMON, 64*c403d5ffSBibo Mao .class_init = loongarch_ipi_class_init, 65*c403d5ffSBibo Mao } 66*c403d5ffSBibo Mao }; 67*c403d5ffSBibo Mao 68*c403d5ffSBibo Mao DEFINE_TYPES(loongarch_ipi_types) 69