|
@@ -99,7 +99,6 @@ bool kvm_gsi_direct_mapping;
|
|
|
bool kvm_allowed;
|
|
|
bool kvm_readonly_mem_allowed;
|
|
|
bool kvm_vm_attributes_allowed;
|
|
|
-bool kvm_direct_msi_allowed;
|
|
|
bool kvm_ioeventfd_any_length_allowed;
|
|
|
bool kvm_msi_use_devid;
|
|
|
bool kvm_has_guest_debug;
|
|
@@ -1848,7 +1847,7 @@ static void clear_gsi(KVMState *s, unsigned int gsi)
|
|
|
|
|
|
void kvm_init_irq_routing(KVMState *s)
|
|
|
{
|
|
|
- int gsi_count, i;
|
|
|
+ int gsi_count;
|
|
|
|
|
|
gsi_count = kvm_check_extension(s, KVM_CAP_IRQ_ROUTING) - 1;
|
|
|
if (gsi_count > 0) {
|
|
@@ -1860,12 +1859,6 @@ void kvm_init_irq_routing(KVMState *s)
|
|
|
s->irq_routes = g_malloc0(sizeof(*s->irq_routes));
|
|
|
s->nr_allocated_irq_routes = 0;
|
|
|
|
|
|
- if (!kvm_direct_msi_allowed) {
|
|
|
- for (i = 0; i < KVM_MSI_HASHTAB_SIZE; i++) {
|
|
|
- QTAILQ_INIT(&s->msi_hashtab[i]);
|
|
|
- }
|
|
|
- }
|
|
|
-
|
|
|
kvm_arch_init_irq_routing(s);
|
|
|
}
|
|
|
|
|
@@ -1985,41 +1978,10 @@ void kvm_irqchip_change_notify(void)
|
|
|
notifier_list_notify(&kvm_irqchip_change_notifiers, NULL);
|
|
|
}
|
|
|
|
|
|
-static unsigned int kvm_hash_msi(uint32_t data)
|
|
|
-{
|
|
|
- /* This is optimized for IA32 MSI layout. However, no other arch shall
|
|
|
- * repeat the mistake of not providing a direct MSI injection API. */
|
|
|
- return data & 0xff;
|
|
|
-}
|
|
|
-
|
|
|
-static void kvm_flush_dynamic_msi_routes(KVMState *s)
|
|
|
-{
|
|
|
- KVMMSIRoute *route, *next;
|
|
|
- unsigned int hash;
|
|
|
-
|
|
|
- for (hash = 0; hash < KVM_MSI_HASHTAB_SIZE; hash++) {
|
|
|
- QTAILQ_FOREACH_SAFE(route, &s->msi_hashtab[hash], entry, next) {
|
|
|
- kvm_irqchip_release_virq(s, route->kroute.gsi);
|
|
|
- QTAILQ_REMOVE(&s->msi_hashtab[hash], route, entry);
|
|
|
- g_free(route);
|
|
|
- }
|
|
|
- }
|
|
|
-}
|
|
|
-
|
|
|
static int kvm_irqchip_get_virq(KVMState *s)
|
|
|
{
|
|
|
int next_virq;
|
|
|
|
|
|
- /*
|
|
|
- * PIC and IOAPIC share the first 16 GSI numbers, thus the available
|
|
|
- * GSI numbers are more than the number of IRQ route. Allocating a GSI
|
|
|
- * number can succeed even though a new route entry cannot be added.
|
|
|
- * When this happens, flush dynamic MSI entries to free IRQ route entries.
|
|
|
- */
|
|
|
- if (!kvm_direct_msi_allowed && s->irq_routes->nr == s->gsi_count) {
|
|
|
- kvm_flush_dynamic_msi_routes(s);
|
|
|
- }
|
|
|
-
|
|
|
/* Return the lowest unused GSI in the bitmap */
|
|
|
next_virq = find_first_zero_bit(s->used_gsi_bitmap, s->gsi_count);
|
|
|
if (next_virq >= s->gsi_count) {
|
|
@@ -2029,63 +1991,17 @@ static int kvm_irqchip_get_virq(KVMState *s)
|
|
|
}
|
|
|
}
|
|
|
|
|
|
-static KVMMSIRoute *kvm_lookup_msi_route(KVMState *s, MSIMessage msg)
|
|
|
-{
|
|
|
- unsigned int hash = kvm_hash_msi(msg.data);
|
|
|
- KVMMSIRoute *route;
|
|
|
-
|
|
|
- QTAILQ_FOREACH(route, &s->msi_hashtab[hash], entry) {
|
|
|
- if (route->kroute.u.msi.address_lo == (uint32_t)msg.address &&
|
|
|
- route->kroute.u.msi.address_hi == (msg.address >> 32) &&
|
|
|
- route->kroute.u.msi.data == le32_to_cpu(msg.data)) {
|
|
|
- return route;
|
|
|
- }
|
|
|
- }
|
|
|
- return NULL;
|
|
|
-}
|
|
|
-
|
|
|
int kvm_irqchip_send_msi(KVMState *s, MSIMessage msg)
|
|
|
{
|
|
|
struct kvm_msi msi;
|
|
|
- KVMMSIRoute *route;
|
|
|
-
|
|
|
- if (kvm_direct_msi_allowed) {
|
|
|
- msi.address_lo = (uint32_t)msg.address;
|
|
|
- msi.address_hi = msg.address >> 32;
|
|
|
- msi.data = le32_to_cpu(msg.data);
|
|
|
- msi.flags = 0;
|
|
|
- memset(msi.pad, 0, sizeof(msi.pad));
|
|
|
-
|
|
|
- return kvm_vm_ioctl(s, KVM_SIGNAL_MSI, &msi);
|
|
|
- }
|
|
|
-
|
|
|
- route = kvm_lookup_msi_route(s, msg);
|
|
|
- if (!route) {
|
|
|
- int virq;
|
|
|
|
|
|
- virq = kvm_irqchip_get_virq(s);
|
|
|
- if (virq < 0) {
|
|
|
- return virq;
|
|
|
- }
|
|
|
-
|
|
|
- route = g_new0(KVMMSIRoute, 1);
|
|
|
- route->kroute.gsi = virq;
|
|
|
- route->kroute.type = KVM_IRQ_ROUTING_MSI;
|
|
|
- route->kroute.flags = 0;
|
|
|
- route->kroute.u.msi.address_lo = (uint32_t)msg.address;
|
|
|
- route->kroute.u.msi.address_hi = msg.address >> 32;
|
|
|
- route->kroute.u.msi.data = le32_to_cpu(msg.data);
|
|
|
-
|
|
|
- kvm_add_routing_entry(s, &route->kroute);
|
|
|
- kvm_irqchip_commit_routes(s);
|
|
|
-
|
|
|
- QTAILQ_INSERT_TAIL(&s->msi_hashtab[kvm_hash_msi(msg.data)], route,
|
|
|
- entry);
|
|
|
- }
|
|
|
+ msi.address_lo = (uint32_t)msg.address;
|
|
|
+ msi.address_hi = msg.address >> 32;
|
|
|
+ msi.data = le32_to_cpu(msg.data);
|
|
|
+ msi.flags = 0;
|
|
|
+ memset(msi.pad, 0, sizeof(msi.pad));
|
|
|
|
|
|
- assert(route->kroute.type == KVM_IRQ_ROUTING_MSI);
|
|
|
-
|
|
|
- return kvm_set_irq(s, route->kroute.gsi, 1);
|
|
|
+ return kvm_vm_ioctl(s, KVM_SIGNAL_MSI, &msi);
|
|
|
}
|
|
|
|
|
|
int kvm_irqchip_add_msi_route(KVMRouteChange *c, int vector, PCIDevice *dev)
|
|
@@ -2660,10 +2576,6 @@ static int kvm_init(MachineState *ms)
|
|
|
|
|
|
s->max_nested_state_len = kvm_check_extension(s, KVM_CAP_NESTED_STATE);
|
|
|
|
|
|
-#ifdef KVM_CAP_IRQ_ROUTING
|
|
|
- kvm_direct_msi_allowed = (kvm_check_extension(s, KVM_CAP_SIGNAL_MSI) > 0);
|
|
|
-#endif
|
|
|
-
|
|
|
s->intx_set_mask = kvm_check_extension(s, KVM_CAP_PCI_2_3);
|
|
|
|
|
|
s->irq_set_ioctl = KVM_IRQ_LINE;
|