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>
This commit is contained in:
parent
9c64c08b18
commit
568670f94d
|
@ -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);
|
||||
|
|
|
@ -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 */
|
Loading…
Reference in New Issue