KVM: cleanup the failure path of KVM_CREATE_IRQCHIP ioctrl
If we fail to init ioapic device or the fail to setup the default irq routing, the device register by kvm_create_pic() and kvm_ioapic_init() remain unregister. This patch fixed to do this. Signed-off-by: Wei Yongjun <yjwei@cn.fujitsu.com> Signed-off-by: Avi Kivity <avi@redhat.com>
This commit is contained in:
committed by
Marcelo Tosatti
parent
1ae77badc2
commit
72bb2fcd23
@@ -543,3 +543,14 @@ struct kvm_pic *kvm_create_pic(struct kvm *kvm)
|
|||||||
|
|
||||||
return s;
|
return s;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void kvm_destroy_pic(struct kvm *kvm)
|
||||||
|
{
|
||||||
|
struct kvm_pic *vpic = kvm->arch.vpic;
|
||||||
|
|
||||||
|
if (vpic) {
|
||||||
|
kvm_io_bus_unregister_dev(kvm, KVM_PIO_BUS, &vpic->dev);
|
||||||
|
kvm->arch.vpic = NULL;
|
||||||
|
kfree(vpic);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@@ -75,6 +75,7 @@ struct kvm_pic {
|
|||||||
};
|
};
|
||||||
|
|
||||||
struct kvm_pic *kvm_create_pic(struct kvm *kvm);
|
struct kvm_pic *kvm_create_pic(struct kvm *kvm);
|
||||||
|
void kvm_destroy_pic(struct kvm *kvm);
|
||||||
int kvm_pic_read_irq(struct kvm *kvm);
|
int kvm_pic_read_irq(struct kvm *kvm);
|
||||||
void kvm_pic_update_irq(struct kvm_pic *s);
|
void kvm_pic_update_irq(struct kvm_pic *s);
|
||||||
void kvm_pic_clear_isr_ack(struct kvm *kvm);
|
void kvm_pic_clear_isr_ack(struct kvm *kvm);
|
||||||
|
@@ -2771,6 +2771,8 @@ long kvm_arch_vm_ioctl(struct file *filp,
|
|||||||
if (vpic) {
|
if (vpic) {
|
||||||
r = kvm_ioapic_init(kvm);
|
r = kvm_ioapic_init(kvm);
|
||||||
if (r) {
|
if (r) {
|
||||||
|
kvm_io_bus_unregister_dev(kvm, KVM_PIO_BUS,
|
||||||
|
&vpic->dev);
|
||||||
kfree(vpic);
|
kfree(vpic);
|
||||||
goto create_irqchip_unlock;
|
goto create_irqchip_unlock;
|
||||||
}
|
}
|
||||||
@@ -2782,10 +2784,8 @@ long kvm_arch_vm_ioctl(struct file *filp,
|
|||||||
r = kvm_setup_default_irq_routing(kvm);
|
r = kvm_setup_default_irq_routing(kvm);
|
||||||
if (r) {
|
if (r) {
|
||||||
mutex_lock(&kvm->irq_lock);
|
mutex_lock(&kvm->irq_lock);
|
||||||
kfree(kvm->arch.vpic);
|
kvm_ioapic_destroy(kvm);
|
||||||
kfree(kvm->arch.vioapic);
|
kvm_destroy_pic(kvm);
|
||||||
kvm->arch.vpic = NULL;
|
|
||||||
kvm->arch.vioapic = NULL;
|
|
||||||
mutex_unlock(&kvm->irq_lock);
|
mutex_unlock(&kvm->irq_lock);
|
||||||
}
|
}
|
||||||
create_irqchip_unlock:
|
create_irqchip_unlock:
|
||||||
|
@@ -401,6 +401,17 @@ int kvm_ioapic_init(struct kvm *kvm)
|
|||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void kvm_ioapic_destroy(struct kvm *kvm)
|
||||||
|
{
|
||||||
|
struct kvm_ioapic *ioapic = kvm->arch.vioapic;
|
||||||
|
|
||||||
|
if (ioapic) {
|
||||||
|
kvm_io_bus_unregister_dev(kvm, KVM_MMIO_BUS, &ioapic->dev);
|
||||||
|
kvm->arch.vioapic = NULL;
|
||||||
|
kfree(ioapic);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int kvm_get_ioapic(struct kvm *kvm, struct kvm_ioapic_state *state)
|
int kvm_get_ioapic(struct kvm *kvm, struct kvm_ioapic_state *state)
|
||||||
{
|
{
|
||||||
struct kvm_ioapic *ioapic = ioapic_irqchip(kvm);
|
struct kvm_ioapic *ioapic = ioapic_irqchip(kvm);
|
||||||
|
@@ -72,6 +72,7 @@ int kvm_apic_match_dest(struct kvm_vcpu *vcpu, struct kvm_lapic *source,
|
|||||||
int kvm_apic_compare_prio(struct kvm_vcpu *vcpu1, struct kvm_vcpu *vcpu2);
|
int kvm_apic_compare_prio(struct kvm_vcpu *vcpu1, struct kvm_vcpu *vcpu2);
|
||||||
void kvm_ioapic_update_eoi(struct kvm *kvm, int vector, int trigger_mode);
|
void kvm_ioapic_update_eoi(struct kvm *kvm, int vector, int trigger_mode);
|
||||||
int kvm_ioapic_init(struct kvm *kvm);
|
int kvm_ioapic_init(struct kvm *kvm);
|
||||||
|
void kvm_ioapic_destroy(struct kvm *kvm);
|
||||||
int kvm_ioapic_set_irq(struct kvm_ioapic *ioapic, int irq, int level);
|
int kvm_ioapic_set_irq(struct kvm_ioapic *ioapic, int irq, int level);
|
||||||
void kvm_ioapic_reset(struct kvm_ioapic *ioapic);
|
void kvm_ioapic_reset(struct kvm_ioapic *ioapic);
|
||||||
int kvm_irq_delivery_to_apic(struct kvm *kvm, struct kvm_lapic *src,
|
int kvm_irq_delivery_to_apic(struct kvm *kvm, struct kvm_lapic *src,
|
||||||
|
Reference in New Issue
Block a user