[kvm-unit-tests PATCH v2 07/16] x86/run_in_user: Preserve exception handler

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



run_in_user() replaces the exception handler for the expected fault
vector to ensure the code can properly return back to kernel mode in
case of such exceptions. However, it leaves the exception handler in
place which may confuse later test code triggering the same exception
without installing a handler first.

Fix this be restoring the previous exception handler. Running the
longjmp() handler out of context will lead to no good.

We now also need to make 'rax' volatile to avoid a related compiler
warning.

Signed-off-by: Mathias Krause <minipli@xxxxxxxxxxxxxx>
---
 lib/x86/usermode.c | 10 +++++++---
 1 file changed, 7 insertions(+), 3 deletions(-)

diff --git a/lib/x86/usermode.c b/lib/x86/usermode.c
index b976123ca753..10fcea288a62 100644
--- a/lib/x86/usermode.c
+++ b/lib/x86/usermode.c
@@ -36,15 +36,17 @@ uint64_t run_in_user(usermode_func func, unsigned int fault_vector,
 		uint64_t arg4, bool *raised_vector)
 {
 	extern char ret_to_kernel[];
-	uint64_t rax = 0;
+	volatile uint64_t rax = 0;
 	static unsigned char user_stack[USERMODE_STACK_SIZE];
+	handler old_ex;
 
 	*raised_vector = 0;
 	set_idt_entry(RET_TO_KERNEL_IRQ, ret_to_kernel, 3);
-	handle_exception(fault_vector,
-			restore_exec_to_jmpbuf_exception_handler);
+	old_ex = handle_exception(fault_vector,
+				  restore_exec_to_jmpbuf_exception_handler);
 
 	if (setjmp(jmpbuf) != 0) {
+		handle_exception(fault_vector, old_ex);
 		*raised_vector = 1;
 		return 0;
 	}
@@ -114,5 +116,7 @@ uint64_t run_in_user(usermode_func func, unsigned int fault_vector,
 			:
 			"rsi", "rdi", "rcx", "rdx");
 
+	handle_exception(fault_vector, old_ex);
+
 	return rax;
 }
-- 
2.39.2




[Index of Archives]     [KVM ARM]     [KVM ia64]     [KVM ppc]     [Virtualization Tools]     [Spice Development]     [Libvirt]     [Libvirt Users]     [Linux USB Devel]     [Linux Audio Users]     [Yosemite Questions]     [Linux Kernel]     [Linux SCSI]     [XFree86]

  Powered by Linux