mirror of
https://github.com/RGBCube/serenity
synced 2025-07-27 02:57:44 +00:00
Kernel: Add helpers for manipulating x86 control registers
Use read_cr{0,2,3,4} and write_cr{0,3,4} helpers instead of inline asm.
This commit is contained in:
parent
8d0b744ebb
commit
da100f12a6
2 changed files with 37 additions and 60 deletions
|
@ -149,18 +149,7 @@ static void dump(const RegisterState& regs)
|
||||||
dbgln(" ds={:04x} es={:04x} fs={:04x} gs={:04x}", (u16)regs.ds, (u16)regs.es, (u16)regs.fs, (u16)regs.gs);
|
dbgln(" ds={:04x} es={:04x} fs={:04x} gs={:04x}", (u16)regs.ds, (u16)regs.es, (u16)regs.fs, (u16)regs.gs);
|
||||||
dbgln(" eax={:08x} ebx={:08x} ecx={:08x} edx={:08x}", regs.eax, regs.ebx, regs.ecx, regs.edx);
|
dbgln(" eax={:08x} ebx={:08x} ecx={:08x} edx={:08x}", regs.eax, regs.ebx, regs.ecx, regs.edx);
|
||||||
dbgln(" ebp={:08x} esp={:08x} esi={:08x} edi={:08x}", regs.ebp, regs.esp, regs.esi, regs.edi);
|
dbgln(" ebp={:08x} esp={:08x} esi={:08x} edi={:08x}", regs.ebp, regs.esp, regs.esi, regs.edi);
|
||||||
|
dbgln(" cr0={:08x} cr2={:08x} cr3={:08x} cr4={:08x}", read_cr0(), read_cr2(), read_cr3(), read_cr4());
|
||||||
u32 cr0;
|
|
||||||
asm("movl %%cr0, %%eax"
|
|
||||||
: "=a"(cr0));
|
|
||||||
u32 cr2;
|
|
||||||
asm("movl %%cr2, %%eax"
|
|
||||||
: "=a"(cr2));
|
|
||||||
u32 cr3 = read_cr3();
|
|
||||||
u32 cr4;
|
|
||||||
asm("movl %%cr4, %%eax"
|
|
||||||
: "=a"(cr4));
|
|
||||||
dbgln(" cr0={:08x} cr2={:08x} cr3={:08x} cr4={:08x}", cr0, cr2, cr3, cr4);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void handle_crash(RegisterState& regs, const char* description, int signal, bool out_of_memory)
|
void handle_crash(RegisterState& regs, const char* description, int signal, bool out_of_memory)
|
||||||
|
@ -364,20 +353,11 @@ void breakpoint_handler(TrapFrame* trap)
|
||||||
current_thread->send_urgent_signal_to_self(SIGTRAP);
|
current_thread->send_urgent_signal_to_self(SIGTRAP);
|
||||||
}
|
}
|
||||||
|
|
||||||
#define EH(i, msg) \
|
#define EH(i, msg) \
|
||||||
static void _exception##i() \
|
static void _exception##i() \
|
||||||
{ \
|
{ \
|
||||||
dbgln("{}", msg); \
|
dbgln("{}", msg); \
|
||||||
u32 cr0, cr2, cr3, cr4; \
|
PANIC("cr0={:08x} cr2={:08x} cr3={:08x} cr4={:08x}", read_cr0(), read_cr2(), read_cr3(), read_cr4()); \
|
||||||
asm("movl %%cr0, %%eax" \
|
|
||||||
: "=a"(cr0)); \
|
|
||||||
asm("movl %%cr2, %%eax" \
|
|
||||||
: "=a"(cr2)); \
|
|
||||||
asm("movl %%cr3, %%eax" \
|
|
||||||
: "=a"(cr3)); \
|
|
||||||
asm("movl %%cr4, %%eax" \
|
|
||||||
: "=a"(cr4)); \
|
|
||||||
PANIC("cr0={:08x} cr2={:08x} cr3={:08x} cr4={:08x}", cr0, cr2, cr3, cr4); \
|
|
||||||
}
|
}
|
||||||
|
|
||||||
EH(2, "Unknown error")
|
EH(2, "Unknown error")
|
||||||
|
@ -733,16 +713,20 @@ void exit_trap(TrapFrame* trap)
|
||||||
return Processor::current().exit_trap(*trap);
|
return Processor::current().exit_trap(*trap);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void write_cr0(u32 value)
|
||||||
|
{
|
||||||
|
asm volatile("movl %%eax, %%cr0" ::"a"(value));
|
||||||
|
}
|
||||||
|
|
||||||
|
void write_cr4(u32 value)
|
||||||
|
{
|
||||||
|
asm volatile("movl %%eax, %%cr4" ::"a"(value));
|
||||||
|
}
|
||||||
|
|
||||||
static void sse_init()
|
static void sse_init()
|
||||||
{
|
{
|
||||||
asm volatile(
|
write_cr0((read_cr0() & 0xfffffffbu) | 0x2);
|
||||||
"mov %cr0, %eax\n"
|
write_cr4(read_cr4() | 0x600);
|
||||||
"andl $0xfffffffb, %eax\n"
|
|
||||||
"orl $0x2, %eax\n"
|
|
||||||
"mov %eax, %cr0\n"
|
|
||||||
"mov %cr4, %eax\n"
|
|
||||||
"orl $0x600, %eax\n"
|
|
||||||
"mov %eax, %cr4\n");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
u32 read_cr0()
|
u32 read_cr0()
|
||||||
|
@ -753,6 +737,14 @@ u32 read_cr0()
|
||||||
return cr0;
|
return cr0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
u32 read_cr2()
|
||||||
|
{
|
||||||
|
u32 cr2;
|
||||||
|
asm("movl %%cr2, %%eax"
|
||||||
|
: "=a"(cr2));
|
||||||
|
return cr2;
|
||||||
|
}
|
||||||
|
|
||||||
u32 read_cr3()
|
u32 read_cr3()
|
||||||
{
|
{
|
||||||
u32 cr3;
|
u32 cr3;
|
||||||
|
@ -911,18 +903,11 @@ void Processor::cpu_setup()
|
||||||
if (has_feature(CPUFeature::SSE))
|
if (has_feature(CPUFeature::SSE))
|
||||||
sse_init();
|
sse_init();
|
||||||
|
|
||||||
asm volatile(
|
write_cr0(read_cr0() | 0x00010000);
|
||||||
"movl %%cr0, %%eax\n"
|
|
||||||
"orl $0x00010000, %%eax\n"
|
|
||||||
"movl %%eax, %%cr0\n" ::
|
|
||||||
: "%eax", "memory");
|
|
||||||
|
|
||||||
if (has_feature(CPUFeature::PGE)) {
|
if (has_feature(CPUFeature::PGE)) {
|
||||||
// Turn on CR4.PGE so the CPU will respect the G bit in page tables.
|
// Turn on CR4.PGE so the CPU will respect the G bit in page tables.
|
||||||
asm volatile(
|
write_cr4(read_cr4() | 0x80);
|
||||||
"mov %cr4, %eax\n"
|
|
||||||
"orl $0x80, %eax\n"
|
|
||||||
"mov %eax, %cr4\n");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (has_feature(CPUFeature::NX)) {
|
if (has_feature(CPUFeature::NX)) {
|
||||||
|
@ -936,32 +921,20 @@ void Processor::cpu_setup()
|
||||||
|
|
||||||
if (has_feature(CPUFeature::SMEP)) {
|
if (has_feature(CPUFeature::SMEP)) {
|
||||||
// Turn on CR4.SMEP
|
// Turn on CR4.SMEP
|
||||||
asm volatile(
|
write_cr4(read_cr4() | 0x100000);
|
||||||
"mov %cr4, %eax\n"
|
|
||||||
"orl $0x100000, %eax\n"
|
|
||||||
"mov %eax, %cr4\n");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (has_feature(CPUFeature::SMAP)) {
|
if (has_feature(CPUFeature::SMAP)) {
|
||||||
// Turn on CR4.SMAP
|
// Turn on CR4.SMAP
|
||||||
asm volatile(
|
write_cr4(read_cr4() | 0x200000);
|
||||||
"mov %cr4, %eax\n"
|
|
||||||
"orl $0x200000, %eax\n"
|
|
||||||
"mov %eax, %cr4\n");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (has_feature(CPUFeature::UMIP)) {
|
if (has_feature(CPUFeature::UMIP)) {
|
||||||
asm volatile(
|
write_cr4(read_cr4() | 0x800);
|
||||||
"mov %cr4, %eax\n"
|
|
||||||
"orl $0x800, %eax\n"
|
|
||||||
"mov %eax, %cr4\n");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (has_feature(CPUFeature::TSC)) {
|
if (has_feature(CPUFeature::TSC)) {
|
||||||
asm volatile(
|
write_cr4(read_cr4() | 0x4);
|
||||||
"mov %cr4, %eax\n"
|
|
||||||
"orl $0x4, %eax\n"
|
|
||||||
"mov %eax, %cr4\n");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -526,10 +526,14 @@ inline FlatPtr offset_in_page(const void* address)
|
||||||
}
|
}
|
||||||
|
|
||||||
u32 read_cr0();
|
u32 read_cr0();
|
||||||
|
u32 read_cr2();
|
||||||
u32 read_cr3();
|
u32 read_cr3();
|
||||||
void write_cr3(u32);
|
|
||||||
u32 read_cr4();
|
u32 read_cr4();
|
||||||
|
|
||||||
|
void write_cr0(u32);
|
||||||
|
void write_cr3(u32);
|
||||||
|
void write_cr4(u32);
|
||||||
|
|
||||||
u32 read_dr6();
|
u32 read_dr6();
|
||||||
|
|
||||||
static inline bool is_kernel_mode()
|
static inline bool is_kernel_mode()
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue