irq_comm.c 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101
  1. /*
  2. * irq_comm.c: Common API for in kernel interrupt controller
  3. * Copyright (c) 2007, Intel Corporation.
  4. *
  5. * This program is free software; you can redistribute it and/or modify it
  6. * under the terms and conditions of the GNU General Public License,
  7. * version 2, as published by the Free Software Foundation.
  8. *
  9. * This program is distributed in the hope it will be useful, but WITHOUT
  10. * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11. * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
  12. * more details.
  13. *
  14. * You should have received a copy of the GNU General Public License along with
  15. * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
  16. * Place - Suite 330, Boston, MA 02111-1307 USA.
  17. * Authors:
  18. * Yaozu (Eddie) Dong <Eddie.dong@intel.com>
  19. *
  20. */
  21. #include <linux/kvm_host.h>
  22. #include "irq.h"
  23. #include "ioapic.h"
  24. /* This should be called with the kvm->lock mutex held */
  25. void kvm_set_irq(struct kvm *kvm, int irq_source_id, int irq, int level)
  26. {
  27. unsigned long *irq_state = (unsigned long *)&kvm->arch.irq_states[irq];
  28. /* Logical OR for level trig interrupt */
  29. if (level)
  30. set_bit(irq_source_id, irq_state);
  31. else
  32. clear_bit(irq_source_id, irq_state);
  33. /* Not possible to detect if the guest uses the PIC or the
  34. * IOAPIC. So set the bit in both. The guest will ignore
  35. * writes to the unused one.
  36. */
  37. kvm_ioapic_set_irq(kvm->arch.vioapic, irq, !!(*irq_state));
  38. #ifdef CONFIG_X86
  39. kvm_pic_set_irq(pic_irqchip(kvm), irq, !!(*irq_state));
  40. #endif
  41. }
  42. void kvm_notify_acked_irq(struct kvm *kvm, unsigned gsi)
  43. {
  44. struct kvm_irq_ack_notifier *kian;
  45. struct hlist_node *n;
  46. hlist_for_each_entry(kian, n, &kvm->arch.irq_ack_notifier_list, link)
  47. if (kian->gsi == gsi)
  48. kian->irq_acked(kian);
  49. }
  50. void kvm_register_irq_ack_notifier(struct kvm *kvm,
  51. struct kvm_irq_ack_notifier *kian)
  52. {
  53. hlist_add_head(&kian->link, &kvm->arch.irq_ack_notifier_list);
  54. }
  55. void kvm_unregister_irq_ack_notifier(struct kvm_irq_ack_notifier *kian)
  56. {
  57. hlist_del_init(&kian->link);
  58. }
  59. /* The caller must hold kvm->lock mutex */
  60. int kvm_request_irq_source_id(struct kvm *kvm)
  61. {
  62. unsigned long *bitmap = &kvm->arch.irq_sources_bitmap;
  63. int irq_source_id = find_first_zero_bit(bitmap,
  64. sizeof(kvm->arch.irq_sources_bitmap));
  65. if (irq_source_id >= sizeof(kvm->arch.irq_sources_bitmap)) {
  66. printk(KERN_WARNING "kvm: exhaust allocatable IRQ sources!\n");
  67. return -EFAULT;
  68. }
  69. ASSERT(irq_source_id != KVM_USERSPACE_IRQ_SOURCE_ID);
  70. set_bit(irq_source_id, bitmap);
  71. return irq_source_id;
  72. }
  73. void kvm_free_irq_source_id(struct kvm *kvm, int irq_source_id)
  74. {
  75. int i;
  76. ASSERT(irq_source_id != KVM_USERSPACE_IRQ_SOURCE_ID);
  77. if (irq_source_id < 0 ||
  78. irq_source_id >= sizeof(kvm->arch.irq_sources_bitmap)) {
  79. printk(KERN_ERR "kvm: IRQ source ID out of range!\n");
  80. return;
  81. }
  82. for (i = 0; i < KVM_IOAPIC_NUM_PINS; i++)
  83. clear_bit(irq_source_id, &kvm->arch.irq_states[i]);
  84. clear_bit(irq_source_id, &kvm->arch.irq_sources_bitmap);
  85. }