mirror of
https://github.com/qemu/qemu.git
synced 2025-08-16 06:43:21 +00:00
hw/riscv/virt.c, riscv_aplic.c: add 'emulated_aplic' helpers
The current logic to determine if we don't need an emulated APLIC controller, i.e. KVM will provide for us, is to determine if we're running KVM, with in-kernel irqchip support, and running aia=aplic-imsic. This is modelled by riscv_is_kvm_aia_aplic_imsic() and virt_use_kvm_aia_aplic_imsic(). This won't suffice to support irqchip_split() mode: it will match exactly the same conditions as the one above, but setting the irqchip to 'split' mode will now require us to emulate an APLIC s-mode controller, like we're doing with 'aia=aplic'. Create a new riscv_use_emulated_aplic() helper that will encapsulate this logic. Replace the uses of "riscv_is_kvm_aia_aplic_imsic()" with this helper every time we're taking a decision on emulate an APLIC controller or not. Do the same in virt.c with virt_use_emulated_aplic(). Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com> Reviewed-by: Alistair Francis <alistair.francis@wdc.com> Message-ID: <20241119191706.718860-6-dbarboza@ventanamicro.com> Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
This commit is contained in:
parent
3fd619db23
commit
b319ef15b8
@ -32,6 +32,7 @@
|
||||
#include "target/riscv/cpu.h"
|
||||
#include "sysemu/sysemu.h"
|
||||
#include "sysemu/kvm.h"
|
||||
#include "sysemu/tcg.h"
|
||||
#include "kvm/kvm_riscv.h"
|
||||
#include "migration/vmstate.h"
|
||||
|
||||
@ -159,6 +160,23 @@ bool riscv_is_kvm_aia_aplic_imsic(bool msimode)
|
||||
return kvm_irqchip_in_kernel() && msimode;
|
||||
}
|
||||
|
||||
bool riscv_use_emulated_aplic(bool msimode)
|
||||
{
|
||||
#ifdef CONFIG_KVM
|
||||
if (tcg_enabled()) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (!riscv_is_kvm_aia_aplic_imsic(msimode)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return kvm_kernel_irqchip_split();
|
||||
#else
|
||||
return true;
|
||||
#endif
|
||||
}
|
||||
|
||||
static bool riscv_aplic_irq_rectified_val(RISCVAPLICState *aplic,
|
||||
uint32_t irq)
|
||||
{
|
||||
@ -857,7 +875,7 @@ static void riscv_aplic_realize(DeviceState *dev, Error **errp)
|
||||
uint32_t i;
|
||||
RISCVAPLICState *aplic = RISCV_APLIC(dev);
|
||||
|
||||
if (!riscv_is_kvm_aia_aplic_imsic(aplic->msimode)) {
|
||||
if (riscv_use_emulated_aplic(aplic->msimode)) {
|
||||
aplic->bitfield_words = (aplic->num_irqs + 31) >> 5;
|
||||
aplic->sourcecfg = g_new0(uint32_t, aplic->num_irqs);
|
||||
aplic->state = g_new0(uint32_t, aplic->num_irqs);
|
||||
@ -881,7 +899,7 @@ static void riscv_aplic_realize(DeviceState *dev, Error **errp)
|
||||
* have IRQ lines delegated by their parent APLIC.
|
||||
*/
|
||||
if (!aplic->parent) {
|
||||
if (kvm_enabled() && riscv_is_kvm_aia_aplic_imsic(aplic->msimode)) {
|
||||
if (kvm_enabled() && !riscv_use_emulated_aplic(aplic->msimode)) {
|
||||
qdev_init_gpio_in(dev, riscv_kvm_aplic_request, aplic->num_irqs);
|
||||
} else {
|
||||
qdev_init_gpio_in(dev, riscv_aplic_request, aplic->num_irqs);
|
||||
@ -1025,7 +1043,7 @@ DeviceState *riscv_aplic_create(hwaddr addr, hwaddr size,
|
||||
|
||||
sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal);
|
||||
|
||||
if (!riscv_is_kvm_aia_aplic_imsic(msimode)) {
|
||||
if (riscv_use_emulated_aplic(msimode)) {
|
||||
sysbus_mmio_map(SYS_BUS_DEVICE(dev), 0, addr);
|
||||
}
|
||||
|
||||
|
@ -66,6 +66,13 @@ static bool virt_use_kvm_aia_aplic_imsic(RISCVVirtAIAType aia_type)
|
||||
return riscv_is_kvm_aia_aplic_imsic(msimode);
|
||||
}
|
||||
|
||||
static bool virt_use_emulated_aplic(RISCVVirtAIAType aia_type)
|
||||
{
|
||||
bool msimode = aia_type == VIRT_AIA_TYPE_APLIC_IMSIC;
|
||||
|
||||
return riscv_use_emulated_aplic(msimode);
|
||||
}
|
||||
|
||||
static bool virt_aclint_allowed(void)
|
||||
{
|
||||
return tcg_enabled() || qtest_enabled();
|
||||
@ -779,8 +786,11 @@ static void create_fdt_sockets(RISCVVirtState *s, const MemMapEntry *memmap,
|
||||
*msi_pcie_phandle = msi_s_phandle;
|
||||
}
|
||||
|
||||
/* KVM AIA aplic-imsic only has one APLIC instance */
|
||||
if (kvm_enabled() && virt_use_kvm_aia_aplic_imsic(s->aia_type)) {
|
||||
/*
|
||||
* With KVM AIA aplic-imsic, using an irqchip without split
|
||||
* mode, we'll use only one APLIC instance.
|
||||
*/
|
||||
if (!virt_use_emulated_aplic(s->aia_type)) {
|
||||
create_fdt_socket_aplic(s, memmap, 0,
|
||||
msi_m_phandle, msi_s_phandle, phandle,
|
||||
&intc_phandles[0], xplic_phandles,
|
||||
|
@ -72,6 +72,7 @@ struct RISCVAPLICState {
|
||||
|
||||
void riscv_aplic_add_child(DeviceState *parent, DeviceState *child);
|
||||
bool riscv_is_kvm_aia_aplic_imsic(bool msimode);
|
||||
bool riscv_use_emulated_aplic(bool msimode);
|
||||
|
||||
DeviceState *riscv_aplic_create(hwaddr addr, hwaddr size,
|
||||
uint32_t hartid_base, uint32_t num_harts, uint32_t num_sources,
|
||||
|
Loading…
Reference in New Issue
Block a user