.
This commit is contained in:
parent
96b6d623a6
commit
1b9ddcefb9
50
html/mu_instructions.html
generated
50
html/mu_instructions.html
generated
|
@ -7,14 +7,15 @@
|
|||
<meta name="plugin-version" content="vim8.1_v1">
|
||||
<meta name="syntax" content="none">
|
||||
<meta name="settings" content="use_css,no_foldcolumn,expand_tabs,prevent_copy=">
|
||||
<meta name="colorscheme" content="minimal-light">
|
||||
<meta name="colorscheme" content="minimal-dark">
|
||||
<style type="text/css">
|
||||
<!--
|
||||
pre { font-family: monospace; color: #000000; background-color: #c6c6c6; }
|
||||
body { font-family: monospace; color: #000000; background-color: #c6c6c6; }
|
||||
pre { font-family: monospace; color: #000000; background-color: #a8a8a8; }
|
||||
body { font-family: monospace; color: #000000; background-color: #a8a8a8; }
|
||||
* { font-size: 1em; }
|
||||
.PreProc { color: #c000c0; }
|
||||
.muComment { color: #005faf; }
|
||||
.Delimiter { color: #c000c0; }
|
||||
.Constant { color: #008787; }
|
||||
.Special { color: #ff6060; }
|
||||
-->
|
||||
|
@ -317,6 +318,31 @@ Similar float variants like `<span class="PreProc">break-if-float<`</span> ar
|
|||
`addr` equivalents. The x86 instruction set stupidly has floating-point
|
||||
operations only update a subset of flags.
|
||||
|
||||
Four sets of conditional jumps are useful for detecting overflow.
|
||||
|
||||
<span class="PreProc">break-if-carry</span> => <span class="Constant">"0f 82/jump-if-carry break/disp32"</span>
|
||||
<span class="PreProc">break-if-carry</span> label => <span class="Constant">"0f 82/jump-if-carry "</span> label <span class="Constant">"/disp32"</span>
|
||||
<span class="PreProc">loop-if-carry</span> => <span class="Constant">"0f 82/jump-if-carry break/disp32"</span>
|
||||
<span class="PreProc">loop-if-carry</span> label => <span class="Constant">"0f 82/jump-if-carry "</span> label <span class="Constant">"/disp32"</span>
|
||||
|
||||
<span class="PreProc">break-if-not-carry</span> => <span class="Constant">"0f 83/jump-if-not-carry break/disp32"</span>
|
||||
<span class="PreProc">break-if-not-carry</span> label => <span class="Constant">"0f 83/jump-if-not-carry "</span> label <span class="Constant">"/disp32"</span>
|
||||
<span class="PreProc">loop-if-not-carry</span> => <span class="Constant">"0f 83/jump-if-not-carry break/disp32"</span>
|
||||
<span class="PreProc">loop-if-not-carry</span> label => <span class="Constant">"0f 83/jump-if-not-carry "</span> label <span class="Constant">"/disp32"</span>
|
||||
|
||||
<span class="PreProc">break-if-overflow</span> => <span class="Constant">"0f 80/jump-if-overflow break/disp32"</span>
|
||||
<span class="PreProc">break-if-overflow</span> label => <span class="Constant">"0f 80/jump-if-overflow "</span> label <span class="Constant">":break/disp32"</span>
|
||||
<span class="PreProc">loop-if-overflow</span> => <span class="Constant">"0f 80/jump-if-overflow loop/disp32"</span>
|
||||
<span class="PreProc">loop-if-overflow</span> label => <span class="Constant">"0f 80/jump-if-overflow "</span> label <span class="Constant">":loop/disp32"</span>
|
||||
|
||||
<span class="PreProc">break-if-not-overflow</span> => <span class="Constant">"0f 81/jump-if-not-overflow break/disp32"</span>
|
||||
<span class="PreProc">break-if-not-overflow</span> label => <span class="Constant">"0f 81/jump-if-not-overflow "</span> label <span class="Constant">":break/disp32"</span>
|
||||
<span class="PreProc">loop-if-not-overflow</span> => <span class="Constant">"0f 81/jump-if-not-overflow loop/disp32"</span>
|
||||
<span class="PreProc">loop-if-not-overflow</span> label => <span class="Constant">"0f 81/jump-if-not-overflow "</span> label <span class="Constant">":loop/disp32"</span>
|
||||
|
||||
All this relies on a convention that every `<span class="Delimiter">{}</span>` block is delimited by labels
|
||||
ending in `:<span class="PreProc">loop</span>` and `:<span class="PreProc">break</span>`.
|
||||
|
||||
<span class="muComment">## Returns</span>
|
||||
|
||||
The `<span class="PreProc">return</span>` instruction cleans up variable declarations just like an unconditional
|
||||
|
@ -342,13 +368,17 @@ var/reg: (addr T) <span class="Special"><-</span> address var2: T
|
|||
|
||||
var/reg: (addr T) <span class="Special"><-</span> index arr/rega: (addr array T), idx/regi: int
|
||||
| if size-of(T) is <span class="Constant">1</span>, <span class="Constant">2</span>, <span class="Constant">4</span> or <span class="Constant">8</span>
|
||||
=> <span class="Constant">"(__check-mu-array-bounds *"</span> rega <span class="Constant">" %"</span> regi <span class="Constant">" "</span> size-of(T) <span class="Constant">")"</span>
|
||||
=> <span class="Constant">"81 7/subop/compare %"</span> rega <span class="Constant">" 0/imm32"</span>
|
||||
<span class="Constant">"0f 84/jump-if-= __mu-abort-null-index-base-address/disp32"</span>
|
||||
<span class="Constant">"(__check-mu-array-bounds *"</span> rega <span class="Constant">" %"</span> regi <span class="Constant">" "</span> size-of(T) <span class="Constant">")"</span>
|
||||
<span class="Constant">"8d/copy-address *("</span> rega <span class="Constant">"+"</span> regi <span class="Constant">"<<"</span> log2(size-of(T)) <span class="Constant">"+4) "</span> reg <span class="Constant">"/r32"</span>
|
||||
var/reg: (addr T) <span class="Special"><-</span> index arr: (array T len), idx/regi: int
|
||||
=> <span class="Constant">"(__check-mu-array-bounds *(ebp+"</span> arr.stack-offset <span class="Constant">") %"</span> regi <span class="Constant">" "</span> size-of(T) <span class="Constant">")"</span>
|
||||
<span class="Constant">"8d/copy-address *(ebp+"</span> regi <span class="Constant">"<<"</span> log2(size-of(T)) <span class="Constant">"+"</span> (arr.stack-offset + <span class="Constant">4</span>) <span class="Constant">") "</span> reg <span class="Constant">"/r32"</span>
|
||||
var/reg: (addr T) <span class="Special"><-</span> index arr/rega: (addr array T), n
|
||||
=> <span class="Constant">"(__check-mu-array-bounds *"</span> rega <span class="Constant">" "</span> n <span class="Constant">" "</span> size-of(T) <span class="Constant">")"</span>
|
||||
=> <span class="Constant">"81 7/subop/compare %"</span> rega <span class="Constant">" 0/imm32"</span>
|
||||
<span class="Constant">"0f 84/jump-if-= __mu-abort-null-index-base-address/disp32"</span>
|
||||
<span class="Constant">"(__check-mu-array-bounds *"</span> rega <span class="Constant">" "</span> n <span class="Constant">" "</span> size-of(T) <span class="Constant">")"</span>
|
||||
<span class="Constant">"8d/copy-address *("</span> rega <span class="Constant">"+"</span> (n*size-of(T)+<span class="Constant">4</span>) <span class="Constant">") "</span> reg <span class="Constant">"/r32"</span>
|
||||
var/reg: (addr T) <span class="Special"><-</span> index arr: (array T len), n
|
||||
=> <span class="Constant">"(__check-mu-array-bounds *(ebp+"</span> arr.stack-offset <span class="Constant">") "</span> n <span class="Constant">" "</span> size-of(T) <span class="Constant">")"</span>
|
||||
|
@ -359,7 +389,9 @@ var/reg: (offset T) <span class="Special"><-</span> compute-offset arr: (addr
|
|||
var/reg: (offset T) <span class="Special"><-</span> compute-offset arr: (addr array T), idx: int <span class="muComment"># arr can be in reg or mem</span>
|
||||
=> <span class="Constant">"69/multiply *(ebp+"</span> idx.stack-offset <span class="Constant">") "</span> size-of(T) <span class="Constant">"/imm32 "</span> reg <span class="Constant">"/r32"</span>
|
||||
var/reg: (addr T) <span class="Special"><-</span> index arr/rega: (addr array T), o/rego: (offset T)
|
||||
=> <span class="Constant">"(__check-mu-array-bounds %"</span> rega <span class="Constant">" %"</span> rego <span class="Constant">" 1 \"" function-name "</span>\<span class="Constant">")"</span>
|
||||
=> <span class="Constant">"81 7/subop/compare %"</span> rega <span class="Constant">" 0/imm32"</span>
|
||||
<span class="Constant">"0f 84/jump-if-= __mu-abort-null-index-base-address/disp32"</span>
|
||||
<span class="Constant">"(__check-mu-array-bounds %"</span> rega <span class="Constant">" %"</span> rego <span class="Constant">" 1 \"" function-name "</span>\<span class="Constant">")"</span>
|
||||
<span class="Constant">"8d/copy-address *("</span> rega <span class="Constant">"+"</span> rego <span class="Constant">"+4) "</span> reg <span class="Constant">"/r32"</span>
|
||||
|
||||
Computing the length of an array is complex.
|
||||
|
@ -398,10 +430,14 @@ If a record (product) <span class="PreProc">type</span> T was defined to have el
|
|||
types T_a, T_b, T_c, ..., then accessing one of those elements f of <span class="PreProc">type</span> T_f:
|
||||
|
||||
var/reg: (addr T_f) <span class="Special"><-</span> get var2/reg2: (addr T), f
|
||||
=> <span class="Constant">"8d/copy-address *("</span> reg2 <span class="Constant">"+"</span> offset(f) <span class="Constant">") "</span> reg <span class="Constant">"/r32"</span>
|
||||
=> <span class="Constant">"81 7/subop/compare %"</span> reg2 <span class="Constant">" 0/imm32"</span>
|
||||
<span class="Constant">"0f 84/jump-if-= __mu-abort-null-get-base-address/disp32"</span>
|
||||
<span class="Constant">"8d/copy-address *("</span> reg2 <span class="Constant">"+"</span> offset(f) <span class="Constant">") "</span> reg <span class="Constant">"/r32"</span>
|
||||
var/reg: (addr T_f) <span class="Special"><-</span> get var2: T, f
|
||||
=> <span class="Constant">"8d/copy-address *(ebp+"</span> var2.stack-offset <span class="Constant">"+"</span> offset(f) <span class="Constant">") "</span> reg <span class="Constant">"/r32"</span>
|
||||
|
||||
When the base is an address we perform a null check.
|
||||
|
||||
<span class="muComment"># Allocating memory</span>
|
||||
|
||||
allocate in: (addr handle T)
|
||||
|
|
Loading…
Reference in New Issue
Block a user