From mboxrd@z Thu Jan 1 00:00:00 1970 From: Eric Biggers Subject: [PATCH] KVM: fix unregistering coalesced mmio zone from wrong bus Date: Mon, 17 Dec 2018 09:36:19 -0800 Message-ID: <20181217173619.210795-1-ebiggers@kernel.org> References: <5b22a63b-e4c2-58af-8070-5aec20302dfc@redhat.com> Mime-Version: 1.0 Content-Transfer-Encoding: 8bit Cc: Peng Hao , syzkaller-bugs@googlegroups.com, linux-kernel@vger.kernel.org To: kvm@vger.kernel.org, Paolo Bonzini , =?UTF-8?q?Radim=20Kr=C4=8Dm=C3=A1=C5=99?= Return-path: In-Reply-To: <5b22a63b-e4c2-58af-8070-5aec20302dfc@redhat.com> Sender: linux-kernel-owner@vger.kernel.org List-Id: kvm.vger.kernel.org From: Eric Biggers If you register a kvm_coalesced_mmio_zone with '.pio = 0' but then unregister it with '.pio = 1', KVM_UNREGISTER_COALESCED_MMIO will try to unregister it from KVM_PIO_BUS rather than KVM_MMIO_BUS, which is a no-op. But it frees the kvm_coalesced_mmio_dev anyway, causing a use-after-free. Fix it by only unregistering and freeing the zone if the correct value of 'pio' is provided. Reported-by: syzbot+f87f60bb6f13f39b54e3@syzkaller.appspotmail.com Fixes: 0804c849f1df ("kvm/x86 : add coalesced pio support") Signed-off-by: Eric Biggers --- virt/kvm/coalesced_mmio.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/virt/kvm/coalesced_mmio.c b/virt/kvm/coalesced_mmio.c index 3710342cf6ad0..6855cce3e5287 100644 --- a/virt/kvm/coalesced_mmio.c +++ b/virt/kvm/coalesced_mmio.c @@ -175,10 +175,14 @@ int kvm_vm_ioctl_unregister_coalesced_mmio(struct kvm *kvm, { struct kvm_coalesced_mmio_dev *dev, *tmp; + if (zone->pio != 1 && zone->pio != 0) + return -EINVAL; + mutex_lock(&kvm->slots_lock); list_for_each_entry_safe(dev, tmp, &kvm->coalesced_zones, list) - if (coalesced_mmio_in_range(dev, zone->addr, zone->size)) { + if (zone->pio == dev->zone.pio && + coalesced_mmio_in_range(dev, zone->addr, zone->size)) { kvm_io_bus_unregister_dev(kvm, zone->pio ? KVM_PIO_BUS : KVM_MMIO_BUS, &dev->dev); kvm_iodevice_destructor(&dev->dev); -- 2.20.0.405.gbc1bbc6f85-goog