commit 39c4cc52adcc529e7754f816eded31ba415b2321
parent d36df5155713ba5da61455dc6193892c3838cc17
Author: Virgil Dupras <hsoft@hardcoded.net>
Date: Sat, 1 Jul 2023 08:04:06 -0400
hal i386: consolidate
Make that code a bit more grokkable.
Diffstat:
1 file changed, 39 insertions(+), 32 deletions(-)
diff --git a/fs/xcomp/i386/kernel.fs b/fs/xcomp/i386/kernel.fs
@@ -43,11 +43,12 @@
\ Constants and labels
0 to realmode
: values ( n -- ) for 0 value next ;
-24 values lblmainalias lblbootptr lblnextword lblcurword lblnextmeta lblret
+25 values lblmainalias lblbootptr lblnextword lblcurword lblnextmeta lblret
lblsysdict lblhere lbl[rcnt] lblhbank lblmod
lblparsec lblparseh lblparseud lblerrmsg
lblfind lblcompiling lblidt
- lblwriterange lblrelwr lblcallwr lblmodrmwr lblderef lblariwr
+ lblwriterange lblrelwr lblcallwr
+ lblmodrmwr lblderef lblregularwr lblariwr
$8000 const HERESTART
$500 to binstart
@@ -66,7 +67,9 @@ $80000 const HALINV
: wwrite, ( opmod -- ) _ lblhere m) 2 i) add, ; \ Destroys dx
: dwrite, ( opmod -- ) _ lblhere m) 4 i) add, ; \ Destroys dx
: movewrite, ( a u ) cx swap i) mov, di swap i) mov, lblwriterange abscall, ;
-: reg0, ( 8bopmod -- ) $c7 i) and, ;
+: reg!, ( r 8bitoperand -- ) dup $c7 i) and, swap 7 and 3 lshift i) or, ;
+: modrm!, ( mod r 8bop -- )
+ dup $38 i) and, rot> 7 and swap 6 lshift or i) or, ;
\ Let's go!
here# to org
@@ -226,6 +229,8 @@ pc to L2 ( operand -- ) \ disp8
xdrop, ret,
\ Write modrm in AL, with disp8/disp32/SIB if appropriate.
+\ When mod<>0 (or modrm=mem), add disp8 or disp32
+\ When targeting ESP, mangle op appropriately to add SIB byte.
pc to lblmodrmwr ( operand -- )
al cwrite,
dx ax mov, dl $7 i) and, dl $4 i) cmp, forward8 jnz,
@@ -243,34 +248,28 @@ pc to lblderef ( operand -- operand )
ax HALDEREF i) test, forward8 jnz, ret, forward!
ax HALDEREF ^ i) and,
dx ax mov, dl $c7 i) and, dl $05 i) cmp, forward8 jnz, \ is m)? make it i)
- al $38 i) and, ax HALIMM i) or, ret, forward!
+ 0 0 al modrm!, ax HALIMM i) or, ret, forward!
ax $c0 i) test, \ mod
forward8 jnz, \ mod=0, set to mod=3
ax $c0 i) or, ret, forward!
\ TODO: HAL error on mod=3
\ Write LEA to CX
- xdup,
- al reg0, al $08 i) or, \ reg=CX
+ xdup, cx al reg!,
$8d i) cwrite, lblmodrmwr abscall, \ lea,
- al $38 i) and, al $c1 i) or, \ rm=CX
+ 3 cx al modrm!,
ret,
-\ Write operand and code which have already been merged together.
+\ Write "regular" operation, that is, a modrm op with b0=8b and b1=direction
\ Opcode is in b15:8 and modrm in b7:0.
\ Add 16b prefix when 16b flag is set.
-\ When targeting ESP, mangle op appropriately to add SIB byte.
-\ When modrm indicate there's a displacement, add it from bank.
\ If the HALINV flag is set, invert direction bit from instruction.
-pc to L1 ( operand -- )
+pc to lblregularwr ( operand -- )
lblderef abscall,
ax HAL16B i) test, forward8 jz, $66 i) cwrite, forward!
ax HALINV i) test, forward8 jz, ax $0200 i) xor, forward! \ inv dir bit
ah cwrite,
lblmodrmwr absjmp,
-xcode !, ( operand -- ) \ operand ax mov,
- ax $8800 i) or, L1 absjmp,
-
pc to L3 ( operand -- ) \ immediate
al 3 i) shr, al 7 i) and, al $b8 i) or,
al cwrite,
@@ -280,7 +279,7 @@ pc to L3 ( operand -- ) \ immediate
pc to L2 ( operand -- ) \ 16b or 8b, movzx
ax HAL16B ^ i) and, \ don't put 16b prefix with movzx
$0f i) cwrite,
- ax $b600 i) or, L1 absjmp,
+ ax $b600 i) or, lblregularwr absjmp,
xcode @, ( operand -- ) \ ax operand mov,
lblderef abscall,
ax HALIMM i) test, L3 abs>rel jnz,
@@ -288,18 +287,24 @@ xcode @, ( operand -- ) \ ax operand mov,
ax HAL16B i) test, L2 abs>rel jnz,
ax HAL8B i) test, L2 abs>rel jz,
forward!
- ax $8a00 i) or, L1 absjmp,
+ ax $8a00 i) or, lblregularwr absjmp,
+
+xcode !, ( operand -- )
+ wcall, <>)
+ wjmp, @,
xcode @!, ( operand -- ) \ operand ax xchg,
- ax $8600 i) or, L1 absjmp,
+ ax $8600 i) or, lblregularwr absjmp,
xcode addr, ( operand -- ) \ ax operand lea,
- ax $8d00 i) or, L1 absjmp,
+ ax $8d00 i) or, lblregularwr absjmp,
xcode +n, ( n operand -- ) \ operand n i) add,
- si 0 d) 1 i) cmp, forward8 jnz, xnip, ax $fe00 i) or, L1 absjmp, forward!
- si 0 d) -1 i) cmp, forward8 jnz, xnip, ax $fe08 i) or, L1 absjmp, forward!
- ax $8000 i) or, L1 abscall, ( n -- )
+ si 0 d) 1 i) cmp, forward8 jnz,
+ xnip, ax $fe00 i) or, lblregularwr absjmp, forward!
+ si 0 d) -1 i) cmp, forward8 jnz,
+ xnip, ax $fe08 i) or, lblregularwr absjmp, forward!
+ ax $8000 i) or, lblregularwr abscall, ( n -- )
ax dwrite, xdrop, ret,
\ Before writing the operand MUL/DIV operation, we check if the operand is
@@ -313,18 +318,19 @@ pc to L2 ( operand -- )
ret,
xcode *, ( operand -- )
+ lblderef abscall,
L2 abscall,
xdup,
ax HALINV i) test, forward8 jz, \ inverted, save AX to DI
ax HALINV ^ i) and,
$c789 i) wwrite, forward! \ di ax mov,
dx ax mov, dl $38 i) and, dl $18 i) cmp, forward8 jnz, \ reg=BX (A>)
- $93 i) cwrite, al reg0, forward! \ ax bx xchg,
- ax $f720 i) or, L1 abscall,
+ $93 i) cwrite, ax al reg!, forward! \ ax bx xchg,
+ ax $f7 i) cwrite, al $20 i) or, lblmodrmwr abscall, \ MUL
dx ax mov, dl $38 i) and, dl $18 i) cmp, forward8 jnz, \ reg=BX (A>)
$93 i) cwrite, forward! \ ax bx xchg,
ax HALINV i) test, forward8 jz, \ inverted, save AX to src.
- al reg0, \ regid=AX
+ ax al reg!, \ regid=AX
wcall, @,
$f889 i) wwrite,
ret, forward! \ ax di mov,
@@ -332,9 +338,10 @@ xcode *, ( operand -- )
ret,
xcode /mod, ( operand -- )
+ lblderef abscall,
L2 abscall,
$d231 i) wwrite, \ dx dx xor,
- ax $f730 i) or, L1 abscall,
+ ax $f7 i) cwrite, al $30 i) or, lblmodrmwr abscall, \ DIV
$d389 i) wwrite, \ bx dx mov,
ret,
@@ -346,7 +353,7 @@ pc to L2 ( operand -- operand-with-di-src )
ax HAL8B i) test, forward8 jnz, di 1 i) mov, forward!
xgrow, si 0 d) di mov,
xdup, ( op n op )
- al $38 i) or, \ target=di
+ di al reg!,
wcall, 32b) wcall, @,
wcall, 32b) wcall, +n,
ax $20100 i) and, \ Set operand to W) but preserve size flags
@@ -364,14 +371,14 @@ xcode [!+], ( operand -- )
\ operand's src in a register so that the operation is upscaled to 32-bit.
pc to L2 ( operand -- ) \ dx=opcodes
dx push, xdup,
- al reg0, al $10 i) or, \ reg=DX
+ dx al reg!, \ reg=DX
wcall, @, ( op )
dx pop,
- ax $38 i) and, \ keep reg only
- ax $c2 i) or, \ DX modrm
+ ax $ff i) and,
+ 3 dx al modrm!,
ah dh mov, \ opcode
ah 1 i) or, \ 32bit
- L1 absjmp,
+ lblregularwr absjmp,
\ Write arithmetic operand with specified opcodes, handling the imm/register
\ complexity. opcodes are supplied as 2 bytes: b15:8 is the "not imm" opcode
@@ -381,7 +388,7 @@ pc to lblariwr ( operand -- ) \ dx=opcodes
ax HALINV i) test, forward8 jnz,
ax HAL16B i) test, L2 abs>rel jnz,
ax HAL8B i) test, L2 abs>rel jz, forward!
- dx $ff00 i) and, ax dx or, L1 absjmp, forward!
+ dx $ff00 i) and, ax dx or, lblregularwr absjmp, forward!
\ mod becomes 3, reg moves to rm and dx is orred into modrm
al 3 i) shr, al 7 i) and, al $c0 i) or, al dl or,
$81 i) cwrite, al cwrite,
@@ -410,7 +417,7 @@ xcode compare, ( operand -- )
pc to L1 ( operand -- ) \ dx=SHL/SHR regid
dx push,
ax HALIMM i) test, forward8 jnz, \ not an immediate
- xdup, al reg0, al $08 i) or, \ target CX
+ xdup, cx al reg!, \ target CX
wcall, @,
\ mod becomes 3, reg moves to rm and DL is orred into modrm
dx pop, al 3 i) shr, al 7 i) and, al $c0 i) or, al dl or,