From 76636769bd9a53acbf21bbfd411f731d2ab51e49 Mon Sep 17 00:00:00 2001 From: Pawel Dziepak Date: Tue, 6 May 2014 21:41:49 +0200 Subject: [PATCH] kernel/x86_64: inline x86_{read, write}_msr() This patch makes it possible to inline rdmsr and wrmsr instruction. The performance impact shouldn't be significant since they are used relatively rarely and wrmsr is usually a serializing instruction, but there is no reason not to do so. --- headers/private/kernel/arch/x86/64/cpu.h | 16 ++++++++++++++++ headers/private/kernel/arch/x86/arch_cpu.h | 6 ++++-- src/system/kernel/arch/x86/64/arch.S | 22 ---------------------- 3 files changed, 20 insertions(+), 24 deletions(-) diff --git a/headers/private/kernel/arch/x86/64/cpu.h b/headers/private/kernel/arch/x86/64/cpu.h index 273115914c..a5bb7e7be7 100644 --- a/headers/private/kernel/arch/x86/64/cpu.h +++ b/headers/private/kernel/arch/x86/64/cpu.h @@ -9,6 +9,22 @@ #include +static inline uint64_t +x86_read_msr(uint32_t msr) +{ + uint64_t high, low; + asm volatile("rdmsr" : "=a" (low), "=d" (high) : "c" (msr)); + return (high << 32) | low; +} + + +static inline void +x86_write_msr(uint32_t msr, uint64_t value) +{ + asm volatile("wrmsr" : : "a" (value) , "d" (value >> 32), "c" (msr)); +} + + static inline void x86_context_switch(arch_thread* oldState, arch_thread* newState) { diff --git a/headers/private/kernel/arch/x86/arch_cpu.h b/headers/private/kernel/arch/x86/arch_cpu.h index b59717f477..900f3c666b 100644 --- a/headers/private/kernel/arch/x86/arch_cpu.h +++ b/headers/private/kernel/arch/x86/arch_cpu.h @@ -461,8 +461,6 @@ void x86_fxrstor(const void* fpuState); void x86_noop_swap(void* oldFpuState, const void* newFpuState); void x86_fxsave_swap(void* oldFpuState, const void* newFpuState); addr_t x86_get_stack_frame(); -uint64 x86_read_msr(uint32 registerNumber); -void x86_write_msr(uint32 registerNumber, uint64 value); uint32 x86_count_mtrrs(void); void x86_set_mtrr(uint32 index, uint64 base, uint64 length, uint8 type); status_t x86_get_mtrr(uint32 index, uint64* _base, uint64* _length, @@ -481,6 +479,10 @@ void x86_hardware_interrupt(iframe* frame); void x86_page_fault_exception(iframe* iframe); #ifndef __x86_64__ + +uint64 x86_read_msr(uint32 registerNumber); +void x86_write_msr(uint32 registerNumber, uint64 value); + void x86_context_switch(struct arch_thread* oldState, struct arch_thread* newState); diff --git a/src/system/kernel/arch/x86/64/arch.S b/src/system/kernel/arch/x86/64/arch.S index 3553081c19..9bd3f16885 100644 --- a/src/system/kernel/arch/x86/64/arch.S +++ b/src/system/kernel/arch/x86/64/arch.S @@ -55,28 +55,6 @@ FUNCTION(x86_get_stack_frame): FUNCTION_END(x86_get_stack_frame) -/* uint64 x86_read_msr(uint32 register); */ -FUNCTION(x86_read_msr): - mov %edi, %ecx - rdmsr - shl $32, %rdx - mov %eax, %eax - or %rdx, %rax - ret -FUNCTION_END(x86_read_msr) - - -/* void x86_write_msr(uint32 register, uint64 value); */ -FUNCTION(x86_write_msr): - mov %rsi, %rdx - mov %esi, %eax - mov %edi, %ecx - shr $32, %rdx - wrmsr - ret -FUNCTION_END(x86_write_msr) - - /* void x86_64_thread_entry(); */ FUNCTION(x86_64_thread_entry): xorq %rbp, %rbp