Felix Held has submitted this change. ( https://review.coreboot.org/c/coreboot/+/67916 )
Change subject: arch/x86/include: Split CPUID access into separate file ......................................................................
arch/x86/include: Split CPUID access into separate file
To allow testing of code that uses CPUID calls, separate the actual calls into a separate header file, This allows the tests to emulate the cpuid access without replacing the rest of the cpu.h definitions.
Signed-off-by: Martin Roth gaumless@gmail.com Change-Id: Ic5ee29f1fbb6304738f2eb7999cbcfdf8f7d4932 Reviewed-on: https://review.coreboot.org/c/coreboot/+/67916 Tested-by: build bot (Jenkins) no-reply@coreboot.org Reviewed-by: Jakub Czapiga jacz@semihalf.com Reviewed-by: Angel Pons th3fanbus@gmail.com Reviewed-by: Felix Held felix-coreboot@felixheld.de --- M src/arch/x86/include/arch/cpu.h A src/arch/x86/include/arch/cpuid.h 2 files changed, 131 insertions(+), 103 deletions(-)
Approvals: build bot (Jenkins): Verified Felix Held: Looks good to me, approved Angel Pons: Looks good to me, approved Jakub Czapiga: Looks good to me, approved
diff --git a/src/arch/x86/include/arch/cpu.h b/src/arch/x86/include/arch/cpu.h index d3f50bf..3402215 100644 --- a/src/arch/x86/include/arch/cpu.h +++ b/src/arch/x86/include/arch/cpu.h @@ -4,6 +4,7 @@ #define ARCH_CPU_H
#include <types.h> +#include <arch/cpuid.h>
/* * EFLAGS bits @@ -26,109 +27,6 @@ #define X86_EFLAGS_VIP 0x00100000 /* Virtual Interrupt Pending */ #define X86_EFLAGS_ID 0x00200000 /* CPUID detection flag */
-struct cpuid_result { - uint32_t eax; - uint32_t ebx; - uint32_t ecx; - uint32_t edx; -}; - -/* - * Generic CPUID function - */ -static inline struct cpuid_result cpuid(int op) -{ - struct cpuid_result result; - asm volatile( - "mov %%ebx, %%edi;" - "cpuid;" - "mov %%ebx, %%esi;" - "mov %%edi, %%ebx;" - : "=a" (result.eax), - "=S" (result.ebx), - "=c" (result.ecx), - "=d" (result.edx) - : "0" (op) - : "edi"); - return result; -} - -/* - * Generic Extended CPUID function - */ -static inline struct cpuid_result cpuid_ext(int op, unsigned int ecx) -{ - struct cpuid_result result; - asm volatile( - "mov %%ebx, %%edi;" - "cpuid;" - "mov %%ebx, %%esi;" - "mov %%edi, %%ebx;" - : "=a" (result.eax), - "=S" (result.ebx), - "=c" (result.ecx), - "=d" (result.edx) - : "0" (op), "2" (ecx) - : "edi"); - return result; -} - -/* - * CPUID functions returning a single datum - */ -static inline unsigned int cpuid_eax(unsigned int op) -{ - unsigned int eax; - - __asm__("mov %%ebx, %%edi;" - "cpuid;" - "mov %%edi, %%ebx;" - : "=a" (eax) - : "0" (op) - : "ecx", "edx", "edi"); - return eax; -} - -static inline unsigned int cpuid_ebx(unsigned int op) -{ - unsigned int eax, ebx; - - __asm__("mov %%ebx, %%edi;" - "cpuid;" - "mov %%ebx, %%esi;" - "mov %%edi, %%ebx;" - : "=a" (eax), "=S" (ebx) - : "0" (op) - : "ecx", "edx", "edi"); - return ebx; -} - -static inline unsigned int cpuid_ecx(unsigned int op) -{ - unsigned int eax, ecx; - - __asm__("mov %%ebx, %%edi;" - "cpuid;" - "mov %%edi, %%ebx;" - : "=a" (eax), "=c" (ecx) - : "0" (op) - : "edx", "edi"); - return ecx; -} - -static inline unsigned int cpuid_edx(unsigned int op) -{ - unsigned int eax, edx; - - __asm__("mov %%ebx, %%edi;" - "cpuid;" - "mov %%edi, %%ebx;" - : "=a" (eax), "=d" (edx) - : "0" (op) - : "ecx", "edi"); - return edx; -} - static inline unsigned int cpuid_get_max_func(void) { return cpuid_eax(0); diff --git a/src/arch/x86/include/arch/cpuid.h b/src/arch/x86/include/arch/cpuid.h new file mode 100644 index 0000000..27848a8 --- /dev/null +++ b/src/arch/x86/include/arch/cpuid.h @@ -0,0 +1,111 @@ +/* SPDX-License-Identifier: GPL-2.0-only */ + +#ifndef ARCH_CPUID_H +#define ARCH_CPUID_H + +#include <types.h> + +struct cpuid_result { + uint32_t eax; + uint32_t ebx; + uint32_t ecx; + uint32_t edx; +}; + +/* + * Generic CPUID function + */ +static inline struct cpuid_result cpuid(int op) +{ + struct cpuid_result result; + asm volatile( + "mov %%ebx, %%edi;" + "cpuid;" + "mov %%ebx, %%esi;" + "mov %%edi, %%ebx;" + : "=a" (result.eax), + "=S" (result.ebx), + "=c" (result.ecx), + "=d" (result.edx) + : "0" (op) + : "edi"); + return result; +} + +/* + * Generic Extended CPUID function + */ +static inline struct cpuid_result cpuid_ext(int op, unsigned int ecx) +{ + struct cpuid_result result; + asm volatile( + "mov %%ebx, %%edi;" + "cpuid;" + "mov %%ebx, %%esi;" + "mov %%edi, %%ebx;" + : "=a" (result.eax), + "=S" (result.ebx), + "=c" (result.ecx), + "=d" (result.edx) + : "0" (op), "2" (ecx) + : "edi"); + return result; +} + +/* + * CPUID functions returning a single datum + */ +static inline unsigned int cpuid_eax(unsigned int op) +{ + unsigned int eax; + + __asm__("mov %%ebx, %%edi;" + "cpuid;" + "mov %%edi, %%ebx;" + : "=a" (eax) + : "0" (op) + : "ecx", "edx", "edi"); + return eax; +} + +static inline unsigned int cpuid_ebx(unsigned int op) +{ + unsigned int eax, ebx; + + __asm__("mov %%ebx, %%edi;" + "cpuid;" + "mov %%ebx, %%esi;" + "mov %%edi, %%ebx;" + : "=a" (eax), "=S" (ebx) + : "0" (op) + : "ecx", "edx", "edi"); + return ebx; +} + +static inline unsigned int cpuid_ecx(unsigned int op) +{ + unsigned int eax, ecx; + + __asm__("mov %%ebx, %%edi;" + "cpuid;" + "mov %%edi, %%ebx;" + : "=a" (eax), "=c" (ecx) + : "0" (op) + : "edx", "edi"); + return ecx; +} + +static inline unsigned int cpuid_edx(unsigned int op) +{ + unsigned int eax, edx; + + __asm__("mov %%ebx, %%edi;" + "cpuid;" + "mov %%edi, %%ebx;" + : "=a" (eax), "=d" (edx) + : "0" (op) + : "ecx", "edi"); + return edx; +} + +#endif /* ARCH_CPUID_H */