aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDrahflow <drahflow@gmx.de>2013-01-22 10:24:59 +0100
committerDrahflow <drahflow@gmx.de>2013-01-22 10:24:59 +0100
commit6b1773ef18dbc3b3e50630bce8193d2cc1b8ffe9 (patch)
tree0b1b4843a3862c0ea4d0c35b25eb73d51ac57d43
parent7bc7f34f29a7b54c3d0f1ebffa885a860f36ac72 (diff)
each fixed, reverse.ey now working
-rw-r--r--compiler/elymasAsm.ey28
-rw-r--r--compiler/elymasAsmLib.ey60
2 files changed, 82 insertions, 6 deletions
diff --git a/compiler/elymasAsm.ey b/compiler/elymasAsm.ey
index 80e7066..3f658d9 100644
--- a/compiler/elymasAsm.ey
+++ b/compiler/elymasAsm.ey
@@ -394,6 +394,14 @@
/one reg modrm11
} /decqReg deff
+ { ==reg
+ reg bit64assert
+
+ 1 /none /none reg rex
+ %F7
+ /six reg modrm11
+ } /divqReg deff
+
{ ==mem
mem bit64assert
@@ -439,6 +447,17 @@
disp imm8
} /leaqMemDisp8Reg deff
+ { ==reg ==mem ==idx ==scale
+ reg bit64assert
+ mem bit64assert
+ idx bit64assert
+
+ 1 reg idx mem rex
+ %8D
+ reg /sib modrm00
+ scale idx mem sib
+ } /leaqMemIndexScaleReg deff
+
{ ==mem ==i
mem bit64assert
i 256 lt assert
@@ -707,6 +726,15 @@
scale idx mem sib
} /pushqMemIndexScale deff
+ { ==mem ==idx ==scale ==disp
+ mem regno %07 gt idx regno %07 gt or { 1 /none idx mem rex } rep
+ disp 128 lt assert
+ %FF
+ /six /sib modrm01
+ scale idx mem sib
+ disp imm8
+ } /pushqMemIndexScaleDisp8 deff
+
{ ==reg
reg regno %07 gt { 1 /none /none reg rex } rep
%50 reg regno %07 band add
diff --git a/compiler/elymasAsmLib.ey b/compiler/elymasAsmLib.ey
index e2635b0..8c7bc7b 100644
--- a/compiler/elymasAsmLib.ey
+++ b/compiler/elymasAsmLib.ey
@@ -51,6 +51,7 @@
# error strings
"unresolved name: " toErrString ==errUnresolvedName
"neither string nor array in len" toErrString ==errNeitherStringNorArrayInLen
+ "not an executable thing" toErrString ==errNotExecutable
> { defv }' allocateOffsetStruct
{ _ =*array len _ 4 div ==largeMoves
@@ -581,6 +582,19 @@
/rdx :popqReg
+ 7 /rdx /cl :movbMemDisp8Reg
+ %F0 /cl :andbImmReg
+ %50 /cl :cmpbImmReg
+ /normalFunction :jeLbl8
+ %70 /cl :cmpbImmReg
+ /arrayFunction :jeLbl8
+
+ errNotExecutable /rdi :movqImmReg
+ internalDumpErrorString /rax :movqImmReg
+ /rax :callqReg
+ :ud2
+
+ @normalFunction
# save current scope
currentScope /rax :movqImmReg
/rax /rsi :movqMemReg
@@ -604,9 +618,6 @@
/rax :callqReg
/done :jmpLbl8
- @typed
- :ud2 # TODO handle typed functions and autolooping
-
@done
/r15 /rcx :movqMemReg
currentScope /rax :movqImmReg
@@ -615,6 +626,39 @@
/r15 :pushqMem
8 /r15 :addqImm8Reg
:retn
+
+ @arrayFunction
+ # rdx == array on heap
+ /rbx :popqReg
+
+ 7 /rbx /cl :movbMemDisp8Reg
+ %F0 /cl :andbImmReg
+ %00 /cl :cmpbImmReg
+ /arrayIntArgument :jeLbl8
+ :ud2 # TODO handle the fully typed case
+
+ @arrayIntArgument
+ 8 /rbx /rax :movqMemDisp8Reg # rax == requested index
+ /rdx /ecx :movlMemReg # load array length
+ 3 /rcx :shrqImm8Reg # divide by object pointer size
+ /rcx :decqReg # rcx == number of elements in array
+
+ /rsi /rsi :xorqRegReg
+ /rdx /rsi :xchgqRegReg
+
+ # TODO: think about skipping this if index fits
+ /rcx :divqReg
+
+ # rsi == array object on heap
+ # rdx == correct array index
+ 8 8 /rdx /rsi :pushqMemIndexScaleDisp8 # use some of the CISC goodness
+
+ /r15 :pushqMem
+ 8 /r15 :addqImm8Reg
+ :retn
+
+ @typed
+ :ud2 # TODO handle typed functions and autolooping
] :labelResolve /ey* defv
# dump top stack element (actually drop it for now)
@@ -660,13 +704,17 @@
/rax /ecx :movlMemReg
3 /rcx :shrqImm8Reg
- /rcx :decqReg
+ /rcx :decqReg # rcx == number of array elements
+ /rcx /rcx :testqRegReg
+ /empty :jzLbl8
- 8 /rax :addqImm8Reg
+ 8 /rcx /rax /rax :leaqMemIndexScaleReg # rax == address of last cell
@copy
/rax :popqMem
+ 8 /rax :subqImm8Reg
/copy :loopLbl8
+ @empty
/r15 :pushqMem
8 /r15 :addqImm8Reg
:retn
@@ -1117,7 +1165,7 @@
/rcx /r15 :movqRegMem
/rax /edx :movlMemReg
- /rdx /rcx :addqRegReg
+ 1 /rdx /rax /rcx :leaqMemIndexScaleReg
/rcx 8 /r15 :movqRegMemDisp8
# /r15 -> current array element