Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 29d50523 authored by Linus Torvalds's avatar Linus Torvalds
Browse files

Merge branch 'x86-hyperv-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip

Pull x86/hyperv changes from Ingo Molnar:
 "The biggest change is support for Windows 8's improved hypervisor
  interrupt model on the Linux Hyper-V guest subsystem code side.

  Smallish fixes otherwise."

* 'x86-hyperv-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip:
  x86, hyperv: HYPERV depends on X86_LOCAL_APIC
  X86: Handle Hyper-V vmbus interrupts as special hypervisor interrupts
  X86: Add a check to catch Xen emulation of Hyper-V
  x86: Hyper-V: register clocksource only if its advertised
parents 026f149c cb20e5f2
Loading
Loading
Loading
Loading
+2 −2
Original line number Diff line number Diff line
@@ -109,8 +109,8 @@

#define UV_BAU_MESSAGE			0xf5

/* Xen vector callback to receive events in a HVM domain */
#define XEN_HVM_EVTCHN_CALLBACK		0xf3
/* Vector on which hypervisor callbacks will be delivered */
#define HYPERVISOR_CALLBACK_VECTOR	0xf3

/*
 * Local APIC timer IRQ vector is on a different priority level,
+4 −0
Original line number Diff line number Diff line
@@ -11,4 +11,8 @@ struct ms_hyperv_info {

extern struct ms_hyperv_info ms_hyperv;

void hyperv_callback_vector(void);
void hyperv_vector_handler(struct pt_regs *regs);
void hv_register_vmbus_handler(int irq, irq_handler_t handler);

#endif
+53 −1
Original line number Diff line number Diff line
@@ -14,10 +14,15 @@
#include <linux/time.h>
#include <linux/clocksource.h>
#include <linux/module.h>
#include <linux/hardirq.h>
#include <linux/interrupt.h>
#include <asm/processor.h>
#include <asm/hypervisor.h>
#include <asm/hyperv.h>
#include <asm/mshyperv.h>
#include <asm/desc.h>
#include <asm/idle.h>
#include <asm/irq_regs.h>

struct ms_hyperv_info ms_hyperv;
EXPORT_SYMBOL_GPL(ms_hyperv);
@@ -30,6 +35,13 @@ static bool __init ms_hyperv_platform(void)
	if (!boot_cpu_has(X86_FEATURE_HYPERVISOR))
		return false;

	/*
	 * Xen emulates Hyper-V to support enlightened Windows.
	 * Check to see first if we are on a Xen Hypervisor.
	 */
	if (xen_cpuid_base())
		return false;

	cpuid(HYPERV_CPUID_VENDOR_AND_MAX_FUNCTIONS,
	      &eax, &hyp_signature[0], &hyp_signature[1], &hyp_signature[2]);

@@ -68,7 +80,14 @@ static void __init ms_hyperv_init_platform(void)
	printk(KERN_INFO "HyperV: features 0x%x, hints 0x%x\n",
	       ms_hyperv.features, ms_hyperv.hints);

	if (ms_hyperv.features & HV_X64_MSR_TIME_REF_COUNT_AVAILABLE)
		clocksource_register_hz(&hyperv_cs, NSEC_PER_SEC/100);
#if IS_ENABLED(CONFIG_HYPERV)
	/*
	 * Setup the IDT for hypervisor callback.
	 */
	alloc_intr_gate(HYPERVISOR_CALLBACK_VECTOR, hyperv_callback_vector);
#endif
}

const __refconst struct hypervisor_x86 x86_hyper_ms_hyperv = {
@@ -77,3 +96,36 @@ const __refconst struct hypervisor_x86 x86_hyper_ms_hyperv = {
	.init_platform		= ms_hyperv_init_platform,
};
EXPORT_SYMBOL(x86_hyper_ms_hyperv);

#if IS_ENABLED(CONFIG_HYPERV)
static int vmbus_irq = -1;
static irq_handler_t vmbus_isr;

void hv_register_vmbus_handler(int irq, irq_handler_t handler)
{
	vmbus_irq = irq;
	vmbus_isr = handler;
}

void hyperv_vector_handler(struct pt_regs *regs)
{
	struct pt_regs *old_regs = set_irq_regs(regs);
	struct irq_desc *desc;

	irq_enter();
	exit_idle();

	desc = irq_to_desc(vmbus_irq);

	if (desc)
		generic_handle_irq_desc(vmbus_irq, desc);

	irq_exit();
	set_irq_regs(old_regs);
}
#else
void hv_register_vmbus_handler(int irq, irq_handler_t handler)
{
}
#endif
EXPORT_SYMBOL_GPL(hv_register_vmbus_handler);
+8 −1
Original line number Diff line number Diff line
@@ -1091,11 +1091,18 @@ ENTRY(xen_failsafe_callback)
	_ASM_EXTABLE(4b,9b)
ENDPROC(xen_failsafe_callback)

BUILD_INTERRUPT3(xen_hvm_callback_vector, XEN_HVM_EVTCHN_CALLBACK,
BUILD_INTERRUPT3(xen_hvm_callback_vector, HYPERVISOR_CALLBACK_VECTOR,
		xen_evtchn_do_upcall)

#endif	/* CONFIG_XEN */

#if IS_ENABLED(CONFIG_HYPERV)

BUILD_INTERRUPT3(hyperv_callback_vector, HYPERVISOR_CALLBACK_VECTOR,
	hyperv_vector_handler)

#endif /* CONFIG_HYPERV */

#ifdef CONFIG_FUNCTION_TRACER
#ifdef CONFIG_DYNAMIC_FTRACE

+6 −1
Original line number Diff line number Diff line
@@ -1454,11 +1454,16 @@ ENTRY(xen_failsafe_callback)
	CFI_ENDPROC
END(xen_failsafe_callback)

apicinterrupt XEN_HVM_EVTCHN_CALLBACK \
apicinterrupt HYPERVISOR_CALLBACK_VECTOR \
	xen_hvm_callback_vector xen_evtchn_do_upcall

#endif /* CONFIG_XEN */

#if IS_ENABLED(CONFIG_HYPERV)
apicinterrupt HYPERVISOR_CALLBACK_VECTOR \
	hyperv_callback_vector hyperv_vector_handler
#endif /* CONFIG_HYPERV */

/*
 * Some functions should be protected against kprobes
 */
Loading