1
0
mirror of https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git synced 2026-01-11 17:10:13 +00:00
torvalds-linux/arch/x86/hyperv/mshv_vtl_asm.S
Naman Jain 7bfe3b8ea6 Drivers: hv: Introduce mshv_vtl driver
Provide an interface for Virtual Machine Monitor like OpenVMM and its
use as OpenHCL paravisor to control VTL0 (Virtual trust Level).
Expose devices and support IOCTLs for features like VTL creation,
VTL0 memory management, context switch, making hypercalls,
mapping VTL0 address space to VTL2 userspace, getting new VMBus
messages and channel events in VTL2 etc.

Co-developed-by: Roman Kisel <romank@linux.microsoft.com>
Signed-off-by: Roman Kisel <romank@linux.microsoft.com>
Co-developed-by: Saurabh Sengar <ssengar@linux.microsoft.com>
Signed-off-by: Saurabh Sengar <ssengar@linux.microsoft.com>
Reviewed-by: Michael Kelley <mhklinux@outlook.com>
Signed-off-by: Naman Jain <namjain@linux.microsoft.com>
Signed-off-by: Wei Liu <wei.liu@kernel.org>
2025-12-05 23:16:26 +00:00

117 lines
3.3 KiB
ArmAsm

/* SPDX-License-Identifier: GPL-2.0
*
* Assembly level code for mshv_vtl VTL transition
*
* Copyright (c) 2025, Microsoft Corporation.
*
* Author:
* Naman Jain <namjain@microsoft.com>
*/
#include <linux/linkage.h>
#include <linux/static_call_types.h>
#include <asm/asm.h>
#include <asm/asm-offsets.h>
#include <asm/frame.h>
#include "mshv-asm-offsets.h"
.text
.section .noinstr.text, "ax"
/*
* void __mshv_vtl_return_call(struct mshv_vtl_cpu_context *vtl0)
*
* This function is used to context switch between different Virtual Trust Levels.
* It is marked as 'noinstr' to prevent against instrumentation and debugging facilities.
* NMIs aren't a problem because the NMI handler saves/restores CR2 specifically to guard
* against #PFs in NMI context clobbering the guest state.
*/
SYM_FUNC_START(__mshv_vtl_return_call)
/* Push callee save registers */
pushq %rbp
mov %rsp, %rbp
pushq %r12
pushq %r13
pushq %r14
pushq %r15
pushq %rbx
/* register switch to VTL0 clobbers all registers except rax/rcx */
mov %_ASM_ARG1, %rax
/* grab rbx/rbp/rsi/rdi/r8-r15 */
mov MSHV_VTL_CPU_CONTEXT_rbx(%rax), %rbx
mov MSHV_VTL_CPU_CONTEXT_rbp(%rax), %rbp
mov MSHV_VTL_CPU_CONTEXT_rsi(%rax), %rsi
mov MSHV_VTL_CPU_CONTEXT_rdi(%rax), %rdi
mov MSHV_VTL_CPU_CONTEXT_r8(%rax), %r8
mov MSHV_VTL_CPU_CONTEXT_r9(%rax), %r9
mov MSHV_VTL_CPU_CONTEXT_r10(%rax), %r10
mov MSHV_VTL_CPU_CONTEXT_r11(%rax), %r11
mov MSHV_VTL_CPU_CONTEXT_r12(%rax), %r12
mov MSHV_VTL_CPU_CONTEXT_r13(%rax), %r13
mov MSHV_VTL_CPU_CONTEXT_r14(%rax), %r14
mov MSHV_VTL_CPU_CONTEXT_r15(%rax), %r15
mov MSHV_VTL_CPU_CONTEXT_cr2(%rax), %rdx
mov %rdx, %cr2
mov MSHV_VTL_CPU_CONTEXT_rdx(%rax), %rdx
/* stash host registers on stack */
pushq %rax
pushq %rcx
xor %ecx, %ecx
/* make a hypercall to switch VTL */
call STATIC_CALL_TRAMP_STR(__mshv_vtl_return_hypercall)
/* stash guest registers on stack, restore saved host copies */
pushq %rax
pushq %rcx
mov 16(%rsp), %rcx
mov 24(%rsp), %rax
mov %rdx, MSHV_VTL_CPU_CONTEXT_rdx(%rax)
mov %cr2, %rdx
mov %rdx, MSHV_VTL_CPU_CONTEXT_cr2(%rax)
pop MSHV_VTL_CPU_CONTEXT_rcx(%rax)
pop MSHV_VTL_CPU_CONTEXT_rax(%rax)
add $16, %rsp
/* save rbx/rbp/rsi/rdi/r8-r15 */
mov %rbx, MSHV_VTL_CPU_CONTEXT_rbx(%rax)
mov %rbp, MSHV_VTL_CPU_CONTEXT_rbp(%rax)
mov %rsi, MSHV_VTL_CPU_CONTEXT_rsi(%rax)
mov %rdi, MSHV_VTL_CPU_CONTEXT_rdi(%rax)
mov %r8, MSHV_VTL_CPU_CONTEXT_r8(%rax)
mov %r9, MSHV_VTL_CPU_CONTEXT_r9(%rax)
mov %r10, MSHV_VTL_CPU_CONTEXT_r10(%rax)
mov %r11, MSHV_VTL_CPU_CONTEXT_r11(%rax)
mov %r12, MSHV_VTL_CPU_CONTEXT_r12(%rax)
mov %r13, MSHV_VTL_CPU_CONTEXT_r13(%rax)
mov %r14, MSHV_VTL_CPU_CONTEXT_r14(%rax)
mov %r15, MSHV_VTL_CPU_CONTEXT_r15(%rax)
/* pop callee-save registers r12-r15, rbx */
pop %rbx
pop %r15
pop %r14
pop %r13
pop %r12
pop %rbp
RET
SYM_FUNC_END(__mshv_vtl_return_call)
/*
* Make sure that static_call_key symbol: __SCK____mshv_vtl_return_hypercall is accessible here.
* Below code is inspired from __ADDRESSABLE(sym) macro. Symbol name is kept simple, to avoid
* naming it something like "__UNIQUE_ID_addressable___SCK____mshv_vtl_return_hypercall_662.0"
* which would otherwise have been generated by the macro.
*/
.section .discard.addressable,"aw"
.align 8
.type mshv_vtl_return_sym, @object
.size mshv_vtl_return_sym, 8
mshv_vtl_return_sym:
.quad __SCK____mshv_vtl_return_hypercall