summaryrefslogtreecommitdiff
path: root/kernel/asm.s
diff options
context:
space:
mode:
authorJake Mannens <jake72360@gmail.com>2018-07-30 04:46:10 +1000
committerJake Mannens <jake72360@gmail.com>2018-07-30 04:46:10 +1000
commit5a4038a196887994a09968dc08bee4b11e30c411 (patch)
treeb157ce10ea6893bf2327327a84eeb01fda3bdd5e /kernel/asm.s
parent902abebefe10e5e8bc9d80b73e46bcb1635f0be8 (diff)
Added a new subroutine invlpg() to asm.s which simply checks the current
CPU is not an i386 before executing the invlpg instruction with the provided address. This will once again make the kernel compatible with the i386 processor as executing the invlpg instruction without these checks would have resulted in an invalid opcode exception.
Diffstat (limited to 'kernel/asm.s')
-rw-r--r--kernel/asm.s38
1 files changed, 34 insertions, 4 deletions
diff --git a/kernel/asm.s b/kernel/asm.s
index 8b5c231..655dcfc 100644
--- a/kernel/asm.s
+++ b/kernel/asm.s
@@ -1,12 +1,13 @@
global clear_tss
-global switch_to
+global invlpg
global set_tss
+global switch_to
extern ctask
extern ctaskn
extern gdt
extern save_state
-; void switch_to(int n, struct task_struct *task);
+; void switch_to(int n, struct task_struct *task)
switch_to:
push ebp
mov ebp, esp
@@ -36,7 +37,36 @@ switch_to:
.tmp:
dq 0
-; void set_tss(unsigned int n, void *tss);
+; void invlpg(void *page)
+invlpg:
+ push ebp
+ mov ebp, esp
+ ; test if we're running on a i386 and abort if so (only i486+ have caches)
+ pushf
+ pop eax
+ and eax, 0xFFFBFFFF
+ push eax
+ popf
+ pushf
+ pop eax
+ test eax, 0x40000
+ jnz .skip
+ pushf
+ pop eax
+ or eax, 0x40000
+ push eax
+ popf
+ pushf
+ pop eax
+ test eax, 0x40000
+ jz .skip
+ mov eax, [ebp+8]
+ invlpg [eax]
+.skip:
+ pop ebp
+ ret
+
+; void set_tss(unsigned int n, void *tss)
set_tss:
push ebp
mov ebp, esp
@@ -59,7 +89,7 @@ set_tss:
pop ebp
ret
-; void clear_tss(unsigned int n);
+; void clear_tss(unsigned int n)
clear_tss:
push ebp
mov ebp, esp