^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0-only
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * Copyright (C) 2015, 2016 ARM Ltd.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) #include <linux/kvm.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) #include <linux/kvm_host.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) #include <trace/events/kvm.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) #include <kvm/arm_vgic.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #include "vgic.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) * vgic_irqfd_set_irq: inject the IRQ corresponding to the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) * irqchip routing entry
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) * This is the entry point for irqfd IRQ injection
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) static int vgic_irqfd_set_irq(struct kvm_kernel_irq_routing_entry *e,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) struct kvm *kvm, int irq_source_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) int level, bool line_status)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) unsigned int spi_id = e->irqchip.pin + VGIC_NR_PRIVATE_IRQS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) if (!vgic_valid_spi(kvm, spi_id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) return kvm_vgic_inject_irq(kvm, 0, spi_id, level, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) * kvm_set_routing_entry: populate a kvm routing entry
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) * from a user routing entry
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) * @kvm: the VM this entry is applied to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) * @e: kvm kernel routing entry handle
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) * @ue: user api routing entry handle
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) * return 0 on success, -EINVAL on errors.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) int kvm_set_routing_entry(struct kvm *kvm,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) struct kvm_kernel_irq_routing_entry *e,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) const struct kvm_irq_routing_entry *ue)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) int r = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) switch (ue->type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) case KVM_IRQ_ROUTING_IRQCHIP:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) e->set = vgic_irqfd_set_irq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) e->irqchip.irqchip = ue->u.irqchip.irqchip;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) e->irqchip.pin = ue->u.irqchip.pin;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) if ((e->irqchip.pin >= KVM_IRQCHIP_NUM_PINS) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) (e->irqchip.irqchip >= KVM_NR_IRQCHIPS))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) case KVM_IRQ_ROUTING_MSI:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) e->set = kvm_set_msi;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) e->msi.address_lo = ue->u.msi.address_lo;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) e->msi.address_hi = ue->u.msi.address_hi;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) e->msi.data = ue->u.msi.data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) e->msi.flags = ue->flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) e->msi.devid = ue->u.msi.devid;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) r = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) return r;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) static void kvm_populate_msi(struct kvm_kernel_irq_routing_entry *e,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) struct kvm_msi *msi)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) msi->address_lo = e->msi.address_lo;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) msi->address_hi = e->msi.address_hi;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) msi->data = e->msi.data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) msi->flags = e->msi.flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) msi->devid = e->msi.devid;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) * kvm_set_msi: inject the MSI corresponding to the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) * MSI routing entry
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) * This is the entry point for irqfd MSI injection
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) * and userspace MSI injection.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) int kvm_set_msi(struct kvm_kernel_irq_routing_entry *e,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) struct kvm *kvm, int irq_source_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) int level, bool line_status)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) struct kvm_msi msi;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) if (!vgic_has_its(kvm))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) if (!level)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) return -1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) kvm_populate_msi(e, &msi);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) return vgic_its_inject_msi(kvm, &msi);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) * kvm_arch_set_irq_inatomic: fast-path for irqfd injection
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) int kvm_arch_set_irq_inatomic(struct kvm_kernel_irq_routing_entry *e,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) struct kvm *kvm, int irq_source_id, int level,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) bool line_status)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) if (!level)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) return -EWOULDBLOCK;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) switch (e->type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) case KVM_IRQ_ROUTING_MSI: {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) struct kvm_msi msi;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) if (!vgic_has_its(kvm))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) kvm_populate_msi(e, &msi);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) return vgic_its_inject_cached_translation(kvm, &msi);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) case KVM_IRQ_ROUTING_IRQCHIP:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) * Injecting SPIs is always possible in atomic context
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) * as long as the damn vgic is initialized.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) if (unlikely(!vgic_initialized(kvm)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) return vgic_irqfd_set_irq(e, kvm, irq_source_id, 1, line_status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) return -EWOULDBLOCK;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) int kvm_vgic_setup_default_irq_routing(struct kvm *kvm)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) struct kvm_irq_routing_entry *entries;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) struct vgic_dist *dist = &kvm->arch.vgic;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) u32 nr = dist->nr_spis;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) int i, ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) entries = kcalloc(nr, sizeof(*entries), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) if (!entries)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) for (i = 0; i < nr; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) entries[i].gsi = i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) entries[i].type = KVM_IRQ_ROUTING_IRQCHIP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) entries[i].u.irqchip.irqchip = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) entries[i].u.irqchip.pin = i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) ret = kvm_set_irq_routing(kvm, entries, nr, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) kfree(entries);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) }