summaryrefslogtreecommitdiff
path: root/arch/x86/coco/tdx
diff options
context:
space:
mode:
authorKirill A. Shutemov <kirill.shutemov@linux.intel.com>2023-03-21 03:35:11 +0300
committerDave Hansen <dave.hansen@linux.intel.com>2023-03-22 21:36:05 +0300
commit7a3a401874bea02f568aa416ac29170d8cde0dc2 (patch)
tree6a54f38698e90f3c2c8f3771f662ddb02ed4d822 /arch/x86/coco/tdx
parente8d018dd0257f744ca50a729e3d042cf2ec9da65 (diff)
downloadlinux-7a3a401874bea02f568aa416ac29170d8cde0dc2.tar.xz
x86/tdx: Drop flags from __tdx_hypercall()
After TDX_HCALL_ISSUE_STI got dropped, the only flag left is TDX_HCALL_HAS_OUTPUT. The flag indicates if the caller wants to see tdx_hypercall_args updated based on the hypercall output. Drop the flags and provide __tdx_hypercall_ret() that matches TDX_HCALL_HAS_OUTPUT semantics. Suggested-by: Peter Zijlstra <peterz@infradead.org> Signed-off-by: Kirill A. Shutemov <kirill.shutemov@linux.intel.com> Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com> Acked-by: Peter Zijlstra (Intel) <peterz@infradead.org> Link: https://lore.kernel.org/all/20230321003511.9469-1-kirill.shutemov%40linux.intel.com
Diffstat (limited to 'arch/x86/coco/tdx')
-rw-r--r--arch/x86/coco/tdx/tdcall.S66
-rw-r--r--arch/x86/coco/tdx/tdx.c18
2 files changed, 47 insertions, 37 deletions
diff --git a/arch/x86/coco/tdx/tdcall.S b/arch/x86/coco/tdx/tdcall.S
index 6a255e6809bc..b193c0a1d8db 100644
--- a/arch/x86/coco/tdx/tdcall.S
+++ b/arch/x86/coco/tdx/tdcall.S
@@ -85,12 +85,12 @@ SYM_FUNC_START(__tdx_module_call)
SYM_FUNC_END(__tdx_module_call)
/*
- * __tdx_hypercall() - Make hypercalls to a TDX VMM using TDVMCALL leaf
- * of TDCALL instruction
+ * TDX_HYPERCALL - Make hypercalls to a TDX VMM using TDVMCALL leaf of TDCALL
+ * instruction
*
* Transforms values in function call argument struct tdx_hypercall_args @args
* into the TDCALL register ABI. After TDCALL operation, VMM output is saved
- * back in @args.
+ * back in @args, if \ret is 1.
*
*-------------------------------------------------------------------------
* TD VMCALL ABI:
@@ -105,26 +105,18 @@ SYM_FUNC_END(__tdx_module_call)
* specification. Non zero value indicates vendor
* specific ABI.
* R11 - VMCALL sub function number
- * RBX, RBP, RDI, RSI - Used to pass VMCALL sub function specific arguments.
+ * RBX, RDX, RDI, RSI - Used to pass VMCALL sub function specific arguments.
* R8-R9, R12-R15 - Same as above.
*
* Output Registers:
*
* RAX - TDCALL instruction status (Not related to hypercall
* output).
- * R10 - Hypercall output error code.
- * R11-R15 - Hypercall sub function specific output values.
+ * RBX, RDX, RDI, RSI - Hypercall sub function specific output values.
+ * R8-R15 - Same as above.
*
- *-------------------------------------------------------------------------
- *
- * __tdx_hypercall() function ABI:
- *
- * @args (RDI) - struct tdx_hypercall_args for input and output
- * @flags (RSI) - TDX_HCALL_* flags
- *
- * On successful completion, return the hypercall error code.
*/
-SYM_FUNC_START(__tdx_hypercall)
+.macro TDX_HYPERCALL ret:req
FRAME_BEGIN
/* Save callee-saved GPRs as mandated by the x86_64 ABI */
@@ -134,9 +126,8 @@ SYM_FUNC_START(__tdx_hypercall)
push %r12
push %rbx
- /* Free RDI and RSI to be used as TDVMCALL arguments */
+ /* Free RDI to be used as TDVMCALL arguments */
movq %rdi, %rax
- push %rsi
/* Copy hypercall registers from arg struct: */
movq TDX_HYPERCALL_r8(%rax), %r8
@@ -171,14 +162,11 @@ SYM_FUNC_START(__tdx_hypercall)
* and are handled by callers.
*/
testq %rax, %rax
- jne .Lpanic
+ jne .Lpanic\@
pop %rax
- /* Copy hypercall result registers to arg struct if needed */
- testq $TDX_HCALL_HAS_OUTPUT, (%rsp)
- jz .Lout
-
+ .if \ret
movq %r8, TDX_HYPERCALL_r8(%rax)
movq %r9, TDX_HYPERCALL_r9(%rax)
movq %r10, TDX_HYPERCALL_r10(%rax)
@@ -191,7 +179,8 @@ SYM_FUNC_START(__tdx_hypercall)
movq %rsi, TDX_HYPERCALL_rsi(%rax)
movq %rbx, TDX_HYPERCALL_rbx(%rax)
movq %rdx, TDX_HYPERCALL_rdx(%rax)
-.Lout:
+ .endif
+
/* TDVMCALL leaf return code is in R10 */
movq %r10, %rax
@@ -208,9 +197,6 @@ SYM_FUNC_START(__tdx_hypercall)
xor %rdi, %rdi
xor %rdx, %rdx
- /* Remove TDX_HCALL_* flags from the stack */
- pop %rsi
-
/* Restore callee-saved GPRs as mandated by the x86_64 ABI */
pop %rbx
pop %r12
@@ -221,9 +207,33 @@ SYM_FUNC_START(__tdx_hypercall)
FRAME_END
RET
-.Lpanic:
+.Lpanic\@:
call __tdx_hypercall_failed
/* __tdx_hypercall_failed never returns */
REACHABLE
- jmp .Lpanic
+ jmp .Lpanic\@
+.endm
+
+/*
+ *
+ * __tdx_hypercall() function ABI:
+ *
+ * @args (RDI) - struct tdx_hypercall_args for input
+ *
+ * On successful completion, return the hypercall error code.
+ */
+SYM_FUNC_START(__tdx_hypercall)
+ TDX_HYPERCALL ret=0
SYM_FUNC_END(__tdx_hypercall)
+
+/*
+ *
+ * __tdx_hypercall_ret() function ABI:
+ *
+ * @args (RDI) - struct tdx_hypercall_args for input and output
+ *
+ * On successful completion, return the hypercall error code.
+ */
+SYM_FUNC_START(__tdx_hypercall_ret)
+ TDX_HYPERCALL ret=1
+SYM_FUNC_END(__tdx_hypercall_ret)
diff --git a/arch/x86/coco/tdx/tdx.c b/arch/x86/coco/tdx/tdx.c
index 055300e08fb3..e146b599260f 100644
--- a/arch/x86/coco/tdx/tdx.c
+++ b/arch/x86/coco/tdx/tdx.c
@@ -66,7 +66,7 @@ static inline u64 _tdx_hypercall(u64 fn, u64 r12, u64 r13, u64 r14, u64 r15)
.r15 = r15,
};
- return __tdx_hypercall(&args, 0);
+ return __tdx_hypercall(&args);
}
/* Called from __tdx_hypercall() for unrecoverable failure */
@@ -99,7 +99,7 @@ long tdx_kvm_hypercall(unsigned int nr, unsigned long p1, unsigned long p2,
.r14 = p4,
};
- return __tdx_hypercall(&args, 0);
+ return __tdx_hypercall(&args);
}
EXPORT_SYMBOL_GPL(tdx_kvm_hypercall);
#endif
@@ -179,7 +179,7 @@ static void __noreturn tdx_panic(const char *msg)
* happens to return.
*/
while (1)
- __tdx_hypercall(&args, 0);
+ __tdx_hypercall(&args);
}
static void tdx_parse_tdinfo(u64 *cc_mask)
@@ -289,7 +289,7 @@ static u64 __cpuidle __halt(const bool irq_disabled)
* can keep the vCPU in virtual HLT, even if an IRQ is
* pending, without hanging/breaking the guest.
*/
- return __tdx_hypercall(&args, 0);
+ return __tdx_hypercall(&args);
}
static int handle_halt(struct ve_info *ve)
@@ -326,7 +326,7 @@ static int read_msr(struct pt_regs *regs, struct ve_info *ve)
* can be found in TDX Guest-Host-Communication Interface
* (GHCI), section titled "TDG.VP.VMCALL<Instruction.RDMSR>".
*/
- if (__tdx_hypercall(&args, TDX_HCALL_HAS_OUTPUT))
+ if (__tdx_hypercall_ret(&args))
return -EIO;
regs->ax = lower_32_bits(args.r11);
@@ -348,7 +348,7 @@ static int write_msr(struct pt_regs *regs, struct ve_info *ve)
* can be found in TDX Guest-Host-Communication Interface
* (GHCI) section titled "TDG.VP.VMCALL<Instruction.WRMSR>".
*/
- if (__tdx_hypercall(&args, 0))
+ if (__tdx_hypercall(&args))
return -EIO;
return ve_instr_len(ve);
@@ -380,7 +380,7 @@ static int handle_cpuid(struct pt_regs *regs, struct ve_info *ve)
* ABI can be found in TDX Guest-Host-Communication Interface
* (GHCI), section titled "VP.VMCALL<Instruction.CPUID>".
*/
- if (__tdx_hypercall(&args, TDX_HCALL_HAS_OUTPUT))
+ if (__tdx_hypercall_ret(&args))
return -EIO;
/*
@@ -407,7 +407,7 @@ static bool mmio_read(int size, unsigned long addr, unsigned long *val)
.r15 = *val,
};
- if (__tdx_hypercall(&args, TDX_HCALL_HAS_OUTPUT))
+ if (__tdx_hypercall_ret(&args))
return false;
*val = args.r11;
return true;
@@ -541,7 +541,7 @@ static bool handle_in(struct pt_regs *regs, int size, int port)
* in TDX Guest-Host-Communication Interface (GHCI) section titled
* "TDG.VP.VMCALL<Instruction.IO>".
*/
- success = !__tdx_hypercall(&args, TDX_HCALL_HAS_OUTPUT);
+ success = !__tdx_hypercall_ret(&args);
/* Update part of the register affected by the emulated instruction */
regs->ax &= ~mask;