From patchwork Wed Mar 4 05:33:02 2009 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sheng Yang X-Patchwork-Id: 9805 Received: from vger.kernel.org (vger.kernel.org [209.132.176.167]) by demeter.kernel.org (8.14.2/8.14.2) with ESMTP id n245X99c002763 for ; Wed, 4 Mar 2009 05:33:09 GMT Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1750832AbZCDFdH (ORCPT ); Wed, 4 Mar 2009 00:33:07 -0500 Received: (majordomo@vger.kernel.org) by vger.kernel.org id S1750940AbZCDFdH (ORCPT ); Wed, 4 Mar 2009 00:33:07 -0500 Received: from mga02.intel.com ([134.134.136.20]:34207 "EHLO mga02.intel.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1750931AbZCDFdG (ORCPT ); Wed, 4 Mar 2009 00:33:06 -0500 Received: from orsmga002.jf.intel.com ([10.7.209.21]) by orsmga101.jf.intel.com with ESMTP; 03 Mar 2009 21:27:29 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="4.38,298,1233561600"; d="scan'208";a="391449878" Received: from syang10-desktop.sh.intel.com (HELO syang10-desktop) ([10.239.13.189]) by orsmga002.jf.intel.com with ESMTP; 03 Mar 2009 21:41:41 -0800 Received: from yasker by syang10-desktop with local (Exim 4.69) (envelope-from ) id 1Lejj4-0001we-58; Wed, 04 Mar 2009 13:33:02 +0800 From: Sheng Yang To: Avi Kivity , Marcelo Tosatti Cc: kvm@vger.kernel.org, Sheng Yang , Gleb Natapov Subject: [PATCH 1/1] KVM: Merge kvm_ioapic_get_delivery_bitmask into kvm_get_intr_delivery_bitmask Date: Wed, 4 Mar 2009 13:33:02 +0800 Message-Id: <1236144782-7458-1-git-send-email-sheng@linux.intel.com> X-Mailer: git-send-email 1.5.6.3 In-Reply-To: <200903041059.47652.sheng@linux.intel.com> References: <200903041059.47652.sheng@linux.intel.com> Sender: kvm-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: kvm@vger.kernel.org Gleb fixed bitmap ops usage in kvm_ioapic_get_delivery_bitmask. Sheng merged two functions, as well as fixed several issues in kvm_get_intr_delivery_bitmask 1. deliver_bitmask is a bitmap rather than a unsigned long intereger. 2. Lowest priority target bitmap wrong calculated by mistake. 3. Prevent potential NULL reference. 4. Declaration in include/kvm_host.h caused powerpc compilation warning. 5. Add warning for guest broadcast interrupt with lowest priority delivery mode. 6. Removed duplicate bitmap clean up in caller of kvm_get_intr_delivery_bitmask. Signed-off-by: Gleb Natapov Signed-off-by: Sheng Yang --- include/linux/kvm_host.h | 3 -- virt/kvm/ioapic.c | 41 ---------------------------------------- virt/kvm/ioapic.h | 5 ++- virt/kvm/irq_comm.c | 47 ++++++++++++++++++++++++++++++++++++++++----- 4 files changed, 44 insertions(+), 52 deletions(-) diff --git a/include/linux/kvm_host.h b/include/linux/kvm_host.h index 3832243..fb60f31 100644 --- a/include/linux/kvm_host.h +++ b/include/linux/kvm_host.h @@ -363,9 +363,6 @@ void kvm_unregister_irq_mask_notifier(struct kvm *kvm, int irq, struct kvm_irq_mask_notifier *kimn); void kvm_fire_mask_notifiers(struct kvm *kvm, int irq, bool mask); -void kvm_get_intr_delivery_bitmask(struct kvm_ioapic *ioapic, - union kvm_ioapic_redirect_entry *entry, - unsigned long *deliver_bitmask); int kvm_set_irq(struct kvm *kvm, int irq_source_id, int irq, int level); void kvm_notify_acked_irq(struct kvm *kvm, unsigned irqchip, unsigned pin); void kvm_register_irq_ack_notifier(struct kvm *kvm, diff --git a/virt/kvm/ioapic.c b/virt/kvm/ioapic.c index 7c2cb2b..cd47575 100644 --- a/virt/kvm/ioapic.c +++ b/virt/kvm/ioapic.c @@ -161,45 +161,6 @@ static void ioapic_inj_nmi(struct kvm_vcpu *vcpu) kvm_vcpu_kick(vcpu); } -void kvm_ioapic_get_delivery_bitmask(struct kvm_ioapic *ioapic, u8 dest, - u8 dest_mode, unsigned long *mask) -{ - int i; - struct kvm *kvm = ioapic->kvm; - struct kvm_vcpu *vcpu; - - ioapic_debug("dest %d dest_mode %d\n", dest, dest_mode); - - *mask = 0; - if (dest_mode == 0) { /* Physical mode. */ - if (dest == 0xFF) { /* Broadcast. */ - for (i = 0; i < KVM_MAX_VCPUS; ++i) - if (kvm->vcpus[i] && kvm->vcpus[i]->arch.apic) - *mask |= 1 << i; - return; - } - for (i = 0; i < KVM_MAX_VCPUS; ++i) { - vcpu = kvm->vcpus[i]; - if (!vcpu) - continue; - if (kvm_apic_match_physical_addr(vcpu->arch.apic, dest)) { - if (vcpu->arch.apic) - *mask = 1 << i; - break; - } - } - } else if (dest != 0) /* Logical mode, MDA non-zero. */ - for (i = 0; i < KVM_MAX_VCPUS; ++i) { - vcpu = kvm->vcpus[i]; - if (!vcpu) - continue; - if (vcpu->arch.apic && - kvm_apic_match_logical_addr(vcpu->arch.apic, dest)) - *mask |= 1 << vcpu->vcpu_id; - } - ioapic_debug("mask %x\n", *mask); -} - static int ioapic_deliver(struct kvm_ioapic *ioapic, int irq) { union kvm_ioapic_redirect_entry entry = ioapic->redirtbl[irq]; @@ -213,8 +174,6 @@ static int ioapic_deliver(struct kvm_ioapic *ioapic, int irq) entry.fields.delivery_mode, entry.fields.vector, entry.fields.trig_mode); - bitmap_zero(deliver_bitmask, KVM_MAX_VCPUS); - /* Always delivery PIT interrupt to vcpu 0 */ #ifdef CONFIG_X86 if (irq == 0) diff --git a/virt/kvm/ioapic.h b/virt/kvm/ioapic.h index 7275f87..c8032ab 100644 --- a/virt/kvm/ioapic.h +++ b/virt/kvm/ioapic.h @@ -70,7 +70,8 @@ void kvm_ioapic_update_eoi(struct kvm *kvm, int vector, int trigger_mode); int kvm_ioapic_init(struct kvm *kvm); int kvm_ioapic_set_irq(struct kvm_ioapic *ioapic, int irq, int level); void kvm_ioapic_reset(struct kvm_ioapic *ioapic); -void kvm_ioapic_get_delivery_bitmask(struct kvm_ioapic *ioapic, u8 dest, - u8 dest_mode, unsigned long *mask); +void kvm_get_intr_delivery_bitmask(struct kvm_ioapic *ioapic, + union kvm_ioapic_redirect_entry *entry, + unsigned long *deliver_bitmask); #endif diff --git a/virt/kvm/irq_comm.c b/virt/kvm/irq_comm.c index d165e05..b431844 100644 --- a/virt/kvm/irq_comm.c +++ b/virt/kvm/irq_comm.c @@ -47,15 +47,52 @@ void kvm_get_intr_delivery_bitmask(struct kvm_ioapic *ioapic, union kvm_ioapic_redirect_entry *entry, unsigned long *deliver_bitmask) { + int i; + struct kvm *kvm = ioapic->kvm; struct kvm_vcpu *vcpu; - kvm_ioapic_get_delivery_bitmask(ioapic, entry->fields.dest_id, - entry->fields.dest_mode, - deliver_bitmask); + bitmap_zero(deliver_bitmask, KVM_MAX_VCPUS); + + if (entry->fields.dest_mode == 0) { /* Physical mode. */ + if (entry->fields.dest_id == 0xFF) { /* Broadcast. */ + /* Lowest priority shouldn't combine with broadcast */ + WARN_ON(entry->fields.delivery_mode == + IOAPIC_LOWEST_PRIORITY); + for (i = 0; i < KVM_MAX_VCPUS; ++i) + if (kvm->vcpus[i] && kvm->vcpus[i]->arch.apic) + __set_bit(i, deliver_bitmask); + return; + } + for (i = 0; i < KVM_MAX_VCPUS; ++i) { + vcpu = kvm->vcpus[i]; + if (!vcpu) + continue; + if (kvm_apic_match_physical_addr(vcpu->arch.apic, + entry->fields.dest_id)) { + if (vcpu->arch.apic) + __set_bit(i, deliver_bitmask); + break; + } + } + } else if (entry->fields.dest_id != 0) /* Logical mode, MDA non-zero. */ + for (i = 0; i < KVM_MAX_VCPUS; ++i) { + vcpu = kvm->vcpus[i]; + if (!vcpu) + continue; + if (vcpu->arch.apic && + kvm_apic_match_logical_addr(vcpu->arch.apic, + entry->fields.dest_id)) + __set_bit(i, deliver_bitmask); + } + switch (entry->fields.delivery_mode) { case IOAPIC_LOWEST_PRIORITY: + /* Select one in deliver_bitmask */ vcpu = kvm_get_lowest_prio_vcpu(ioapic->kvm, entry->fields.vector, deliver_bitmask); + bitmap_zero(deliver_bitmask, KVM_MAX_VCPUS); + if (!vcpu) + return; __set_bit(vcpu->vcpu_id, deliver_bitmask); break; case IOAPIC_FIXED: @@ -65,7 +102,7 @@ void kvm_get_intr_delivery_bitmask(struct kvm_ioapic *ioapic, if (printk_ratelimit()) printk(KERN_INFO "kvm: unsupported delivery mode %d\n", entry->fields.delivery_mode); - *deliver_bitmask = 0; + bitmap_zero(deliver_bitmask, KVM_MAX_VCPUS); } } @@ -80,8 +117,6 @@ static int kvm_set_msi(struct kvm_kernel_irq_routing_entry *e, BUG_ON(!ioapic); - bitmap_zero(deliver_bitmask, KVM_MAX_VCPUS); - entry.bits = 0; entry.fields.dest_id = (e->msi.address_lo & MSI_ADDR_DEST_ID_MASK) >> MSI_ADDR_DEST_ID_SHIFT;