linux/arch/x86/kvm/lapic.h
<<
>>
Prefs
   1#ifndef __KVM_X86_LAPIC_H
   2#define __KVM_X86_LAPIC_H
   3
   4#include <kvm/iodev.h>
   5
   6#include <linux/kvm_host.h>
   7
   8#define KVM_APIC_INIT           0
   9#define KVM_APIC_SIPI           1
  10
  11struct kvm_timer {
  12        struct hrtimer timer;
  13        s64 period;                             /* unit: ns */
  14        u32 timer_mode;
  15        u32 timer_mode_mask;
  16        u64 tscdeadline;
  17        u64 expired_tscdeadline;
  18        atomic_t pending;                       /* accumulated triggered timers */
  19};
  20
  21struct kvm_lapic {
  22        unsigned long base_address;
  23        struct kvm_io_device dev;
  24        struct kvm_timer lapic_timer;
  25        u32 divide_count;
  26        struct kvm_vcpu *vcpu;
  27        bool sw_enabled;
  28        bool irr_pending;
  29        bool lvt0_in_nmi_mode;
  30        /* Number of bits set in ISR. */
  31        s16 isr_count;
  32        /* The highest vector set in ISR; if -1 - invalid, must scan ISR. */
  33        int highest_isr_cache;
  34        /**
  35         * APIC register page.  The layout matches the register layout seen by
  36         * the guest 1:1, because it is accessed by the vmx microcode.
  37         * Note: Only one register, the TPR, is used by the microcode.
  38         */
  39        void *regs;
  40        gpa_t vapic_addr;
  41        struct gfn_to_hva_cache vapic_cache;
  42        unsigned long pending_events;
  43        unsigned int sipi_vector;
  44};
  45
  46struct dest_map;
  47
  48int kvm_create_lapic(struct kvm_vcpu *vcpu);
  49void kvm_free_lapic(struct kvm_vcpu *vcpu);
  50
  51int kvm_apic_has_interrupt(struct kvm_vcpu *vcpu);
  52int kvm_apic_accept_pic_intr(struct kvm_vcpu *vcpu);
  53int kvm_get_apic_interrupt(struct kvm_vcpu *vcpu);
  54void kvm_apic_accept_events(struct kvm_vcpu *vcpu);
  55void kvm_lapic_reset(struct kvm_vcpu *vcpu, bool init_event);
  56u64 kvm_lapic_get_cr8(struct kvm_vcpu *vcpu);
  57void kvm_lapic_set_tpr(struct kvm_vcpu *vcpu, unsigned long cr8);
  58void kvm_lapic_set_eoi(struct kvm_vcpu *vcpu);
  59void kvm_lapic_set_base(struct kvm_vcpu *vcpu, u64 value);
  60u64 kvm_lapic_get_base(struct kvm_vcpu *vcpu);
  61void kvm_apic_set_version(struct kvm_vcpu *vcpu);
  62
  63void __kvm_apic_update_irr(u32 *pir, void *regs);
  64void kvm_apic_update_irr(struct kvm_vcpu *vcpu, u32 *pir);
  65int kvm_apic_set_irq(struct kvm_vcpu *vcpu, struct kvm_lapic_irq *irq,
  66                     struct dest_map *dest_map);
  67int kvm_apic_local_deliver(struct kvm_lapic *apic, int lvt_type);
  68
  69bool kvm_irq_delivery_to_apic_fast(struct kvm *kvm, struct kvm_lapic *src,
  70                struct kvm_lapic_irq *irq, int *r, struct dest_map *dest_map);
  71
  72u64 kvm_get_apic_base(struct kvm_vcpu *vcpu);
  73int kvm_set_apic_base(struct kvm_vcpu *vcpu, struct msr_data *msr_info);
  74void kvm_apic_post_state_restore(struct kvm_vcpu *vcpu,
  75                struct kvm_lapic_state *s);
  76int kvm_lapic_find_highest_irr(struct kvm_vcpu *vcpu);
  77
  78u64 kvm_get_lapic_tscdeadline_msr(struct kvm_vcpu *vcpu);
  79void kvm_set_lapic_tscdeadline_msr(struct kvm_vcpu *vcpu, u64 data);
  80
  81void kvm_apic_write_nodecode(struct kvm_vcpu *vcpu, u32 offset);
  82void kvm_apic_set_eoi_accelerated(struct kvm_vcpu *vcpu, int vector);
  83
  84int kvm_lapic_set_vapic_addr(struct kvm_vcpu *vcpu, gpa_t vapic_addr);
  85void kvm_lapic_sync_from_vapic(struct kvm_vcpu *vcpu);
  86void kvm_lapic_sync_to_vapic(struct kvm_vcpu *vcpu);
  87
  88int kvm_x2apic_msr_write(struct kvm_vcpu *vcpu, u32 msr, u64 data);
  89int kvm_x2apic_msr_read(struct kvm_vcpu *vcpu, u32 msr, u64 *data);
  90
  91int kvm_hv_vapic_msr_write(struct kvm_vcpu *vcpu, u32 msr, u64 data);
  92int kvm_hv_vapic_msr_read(struct kvm_vcpu *vcpu, u32 msr, u64 *data);
  93
  94static inline bool kvm_hv_vapic_assist_page_enabled(struct kvm_vcpu *vcpu)
  95{
  96        return vcpu->arch.hyperv.hv_vapic & HV_X64_MSR_APIC_ASSIST_PAGE_ENABLE;
  97}
  98
  99int kvm_lapic_enable_pv_eoi(struct kvm_vcpu *vcpu, u64 data);
 100void kvm_lapic_init(void);
 101
 102static inline u32 kvm_apic_get_reg(struct kvm_lapic *apic, int reg_off)
 103{
 104                return *((u32 *) (apic->regs + reg_off));
 105}
 106
 107extern struct static_key kvm_no_apic_vcpu;
 108
 109static inline bool lapic_in_kernel(struct kvm_vcpu *vcpu)
 110{
 111        if (static_key_false(&kvm_no_apic_vcpu))
 112                return vcpu->arch.apic;
 113        return true;
 114}
 115
 116extern struct static_key_deferred apic_hw_disabled;
 117
 118static inline int kvm_apic_hw_enabled(struct kvm_lapic *apic)
 119{
 120        if (static_key_false(&apic_hw_disabled.key))
 121                return apic->vcpu->arch.apic_base & MSR_IA32_APICBASE_ENABLE;
 122        return MSR_IA32_APICBASE_ENABLE;
 123}
 124
 125extern struct static_key_deferred apic_sw_disabled;
 126
 127static inline bool kvm_apic_sw_enabled(struct kvm_lapic *apic)
 128{
 129        if (static_key_false(&apic_sw_disabled.key))
 130                return apic->sw_enabled;
 131        return true;
 132}
 133
 134static inline bool kvm_apic_present(struct kvm_vcpu *vcpu)
 135{
 136        return lapic_in_kernel(vcpu) && kvm_apic_hw_enabled(vcpu->arch.apic);
 137}
 138
 139static inline int kvm_lapic_enabled(struct kvm_vcpu *vcpu)
 140{
 141        return kvm_apic_present(vcpu) && kvm_apic_sw_enabled(vcpu->arch.apic);
 142}
 143
 144static inline int apic_x2apic_mode(struct kvm_lapic *apic)
 145{
 146        return apic->vcpu->arch.apic_base & X2APIC_ENABLE;
 147}
 148
 149static inline bool kvm_vcpu_apicv_active(struct kvm_vcpu *vcpu)
 150{
 151        return vcpu->arch.apic && vcpu->arch.apicv_active;
 152}
 153
 154static inline bool kvm_apic_has_events(struct kvm_vcpu *vcpu)
 155{
 156        return lapic_in_kernel(vcpu) && vcpu->arch.apic->pending_events;
 157}
 158
 159static inline bool kvm_lowest_prio_delivery(struct kvm_lapic_irq *irq)
 160{
 161        return (irq->delivery_mode == APIC_DM_LOWEST ||
 162                        irq->msi_redir_hint);
 163}
 164
 165static inline int kvm_lapic_latched_init(struct kvm_vcpu *vcpu)
 166{
 167        return lapic_in_kernel(vcpu) && test_bit(KVM_APIC_INIT, &vcpu->arch.apic->pending_events);
 168}
 169
 170static inline int kvm_apic_id(struct kvm_lapic *apic)
 171{
 172        return (kvm_apic_get_reg(apic, APIC_ID) >> 24) & 0xff;
 173}
 174
 175bool kvm_apic_pending_eoi(struct kvm_vcpu *vcpu, int vector);
 176
 177void wait_lapic_expire(struct kvm_vcpu *vcpu);
 178
 179bool kvm_intr_is_single_vcpu_fast(struct kvm *kvm, struct kvm_lapic_irq *irq,
 180                        struct kvm_vcpu **dest_vcpu);
 181int kvm_vector_to_index(u32 vector, u32 dest_vcpus,
 182                        const unsigned long *bitmap, u32 bitmap_size);
 183#endif
 184