|
@@ -187,12 +187,6 @@ static int cpu_timer_irq_pending(struct kvm_vcpu *vcpu)
|
|
|
return kvm_s390_get_cpu_timer(vcpu) >> 63;
|
|
|
}
|
|
|
|
|
|
-static inline int is_ioirq(unsigned long irq_type)
|
|
|
-{
|
|
|
- return ((irq_type >= IRQ_PEND_IO_ISC_7) &&
|
|
|
- (irq_type <= IRQ_PEND_IO_ISC_0));
|
|
|
-}
|
|
|
-
|
|
|
static uint64_t isc_to_isc_bits(int isc)
|
|
|
{
|
|
|
return (0x80 >> isc) << 24;
|
|
@@ -1016,24 +1010,6 @@ out:
|
|
|
return rc;
|
|
|
}
|
|
|
|
|
|
-typedef int (*deliver_irq_t)(struct kvm_vcpu *vcpu);
|
|
|
-
|
|
|
-static const deliver_irq_t deliver_irq_funcs[] = {
|
|
|
- [IRQ_PEND_MCHK_EX] = __deliver_machine_check,
|
|
|
- [IRQ_PEND_MCHK_REP] = __deliver_machine_check,
|
|
|
- [IRQ_PEND_PROG] = __deliver_prog,
|
|
|
- [IRQ_PEND_EXT_EMERGENCY] = __deliver_emergency_signal,
|
|
|
- [IRQ_PEND_EXT_EXTERNAL] = __deliver_external_call,
|
|
|
- [IRQ_PEND_EXT_CLOCK_COMP] = __deliver_ckc,
|
|
|
- [IRQ_PEND_EXT_CPU_TIMER] = __deliver_cpu_timer,
|
|
|
- [IRQ_PEND_RESTART] = __deliver_restart,
|
|
|
- [IRQ_PEND_SET_PREFIX] = __deliver_set_prefix,
|
|
|
- [IRQ_PEND_PFAULT_INIT] = __deliver_pfault_init,
|
|
|
- [IRQ_PEND_EXT_SERVICE] = __deliver_service,
|
|
|
- [IRQ_PEND_PFAULT_DONE] = __deliver_pfault_done,
|
|
|
- [IRQ_PEND_VIRTIO] = __deliver_virtio,
|
|
|
-};
|
|
|
-
|
|
|
/* Check whether an external call is pending (deliverable or not) */
|
|
|
int kvm_s390_ext_call_pending(struct kvm_vcpu *vcpu)
|
|
|
{
|
|
@@ -1197,7 +1173,6 @@ void kvm_s390_clear_local_irqs(struct kvm_vcpu *vcpu)
|
|
|
int __must_check kvm_s390_deliver_pending_interrupts(struct kvm_vcpu *vcpu)
|
|
|
{
|
|
|
struct kvm_s390_local_interrupt *li = &vcpu->arch.local_int;
|
|
|
- deliver_irq_t func;
|
|
|
int rc = 0;
|
|
|
unsigned long irq_type;
|
|
|
unsigned long irqs;
|
|
@@ -1217,16 +1192,57 @@ int __must_check kvm_s390_deliver_pending_interrupts(struct kvm_vcpu *vcpu)
|
|
|
while ((irqs = deliverable_irqs(vcpu)) && !rc) {
|
|
|
/* bits are in the reverse order of interrupt priority */
|
|
|
irq_type = find_last_bit(&irqs, IRQ_PEND_COUNT);
|
|
|
- if (is_ioirq(irq_type)) {
|
|
|
+ switch (irq_type) {
|
|
|
+ case IRQ_PEND_IO_ISC_0:
|
|
|
+ case IRQ_PEND_IO_ISC_1:
|
|
|
+ case IRQ_PEND_IO_ISC_2:
|
|
|
+ case IRQ_PEND_IO_ISC_3:
|
|
|
+ case IRQ_PEND_IO_ISC_4:
|
|
|
+ case IRQ_PEND_IO_ISC_5:
|
|
|
+ case IRQ_PEND_IO_ISC_6:
|
|
|
+ case IRQ_PEND_IO_ISC_7:
|
|
|
rc = __deliver_io(vcpu, irq_type);
|
|
|
- } else {
|
|
|
- func = deliver_irq_funcs[irq_type];
|
|
|
- if (!func) {
|
|
|
- WARN_ON_ONCE(func == NULL);
|
|
|
- clear_bit(irq_type, &li->pending_irqs);
|
|
|
- continue;
|
|
|
- }
|
|
|
- rc = func(vcpu);
|
|
|
+ break;
|
|
|
+ case IRQ_PEND_MCHK_EX:
|
|
|
+ case IRQ_PEND_MCHK_REP:
|
|
|
+ rc = __deliver_machine_check(vcpu);
|
|
|
+ break;
|
|
|
+ case IRQ_PEND_PROG:
|
|
|
+ rc = __deliver_prog(vcpu);
|
|
|
+ break;
|
|
|
+ case IRQ_PEND_EXT_EMERGENCY:
|
|
|
+ rc = __deliver_emergency_signal(vcpu);
|
|
|
+ break;
|
|
|
+ case IRQ_PEND_EXT_EXTERNAL:
|
|
|
+ rc = __deliver_external_call(vcpu);
|
|
|
+ break;
|
|
|
+ case IRQ_PEND_EXT_CLOCK_COMP:
|
|
|
+ rc = __deliver_ckc(vcpu);
|
|
|
+ break;
|
|
|
+ case IRQ_PEND_EXT_CPU_TIMER:
|
|
|
+ rc = __deliver_cpu_timer(vcpu);
|
|
|
+ break;
|
|
|
+ case IRQ_PEND_RESTART:
|
|
|
+ rc = __deliver_restart(vcpu);
|
|
|
+ break;
|
|
|
+ case IRQ_PEND_SET_PREFIX:
|
|
|
+ rc = __deliver_set_prefix(vcpu);
|
|
|
+ break;
|
|
|
+ case IRQ_PEND_PFAULT_INIT:
|
|
|
+ rc = __deliver_pfault_init(vcpu);
|
|
|
+ break;
|
|
|
+ case IRQ_PEND_EXT_SERVICE:
|
|
|
+ rc = __deliver_service(vcpu);
|
|
|
+ break;
|
|
|
+ case IRQ_PEND_PFAULT_DONE:
|
|
|
+ rc = __deliver_pfault_done(vcpu);
|
|
|
+ break;
|
|
|
+ case IRQ_PEND_VIRTIO:
|
|
|
+ rc = __deliver_virtio(vcpu);
|
|
|
+ break;
|
|
|
+ default:
|
|
|
+ WARN_ONCE(1, "Unknown pending irq type %ld", irq_type);
|
|
|
+ clear_bit(irq_type, &li->pending_irqs);
|
|
|
}
|
|
|
}
|
|
|
|