diff options
author | Kartik Agaram <vc@akkartik.com> | 2019-04-12 10:51:33 -0700 |
---|---|---|
committer | Kartik Agaram <vc@akkartik.com> | 2019-04-12 10:59:43 -0700 |
commit | fb2ffbd0960d8e9a9e8fd9daa9dc688405016ba2 (patch) | |
tree | 3912dc655f1a2924b379dd05acf322da4fc89640 /subx | |
parent | 61b8fe6b18c6314268ed24d79bf99de6f55be63b (diff) | |
download | mu-fb2ffbd0960d8e9a9e8fd9daa9dc688405016ba2.tar.gz |
5085 - 'assort' phase done!
Current plan for SubX translator: $ cat files.subx ... |assort |pack |survey |hex > a.out Higher-level notations will be inserted at the start of the pipeline. The first (and needed for bootstrapping) is for string literals. $ cat files.subx ... |string-literals |assort |pack |survey |hex > a.out Alternatively, we should check how often we use string literals and just convert them by hand. They're used all over in tests, and converting them would make tests hard (even harder) to read.
Diffstat (limited to 'subx')
-rw-r--r-- | subx/010---vm.cc | 4 | ||||
-rwxr-xr-x | subx/apps/assort | bin | 19649 -> 21190 bytes | |||
-rw-r--r-- | subx/apps/assort.subx | 904 | ||||
-rwxr-xr-x | subx/test_apps | 10 |
4 files changed, 510 insertions, 408 deletions
diff --git a/subx/010---vm.cc b/subx/010---vm.cc index 9fbecbc0..6fac9cf7 100644 --- a/subx/010---vm.cc +++ b/subx/010---vm.cc @@ -223,8 +223,10 @@ inline uint8_t* mem_addr_u8(uint32_t addr) { result = &Mem.at(i).data(addr); } } - if (result == NULL) + if (result == NULL) { + if (Trace_file) Trace_file.flush(); raise << "Tried to access uninitialized memory at address 0x" << HEXWORD << addr << '\n' << end(); + } return result; } inline int8_t* mem_addr_i8(uint32_t addr) { diff --git a/subx/apps/assort b/subx/apps/assort index 16084ccd..d7fbd379 100755 --- a/subx/apps/assort +++ b/subx/apps/assort Binary files differdiff --git a/subx/apps/assort.subx b/subx/apps/assort.subx index 5c13f31b..74712632 100644 --- a/subx/apps/assort.subx +++ b/subx/apps/assort.subx @@ -131,408 +131,408 @@ $convert:end: 5d/pop-to-EBP c3/return -#? test-convert: -#? # . prolog -#? 55/push-EBP -#? 89/copy 3/mod/direct 5/rm32/EBP . . . 4/r32/ESP . . # copy ESP to EBP -#? # setup -#? # . clear-stream(_test-input-stream) -#? # . . push args -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call clear-stream/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 4/imm32 # add to ESP -#? # . clear-stream(_test-input-buffered-file+4) -#? # . . push args -#? b8/copy-to-EAX _test-input-buffered-file/imm32 -#? 05/add-to-EAX 4/imm32 -#? 50/push-EAX -#? # . . call -#? e8/call clear-stream/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 4/imm32 # add to ESP -#? # . clear-stream(_test-output-stream) -#? # . . push args -#? 68/push _test-output-stream/imm32 -#? # . . call -#? e8/call clear-stream/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 4/imm32 # add to ESP -#? # . clear-stream(_test-output-buffered-file+4) -#? # . . push args -#? b8/copy-to-EAX _test-output-buffered-file/imm32 -#? 05/add-to-EAX 4/imm32 -#? 50/push-EAX -#? # . . call -#? e8/call clear-stream/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 4/imm32 # add to ESP -#? # initialize input (meta comments in parens) -#? # # comment 1 -#? # # comment 2 indented -#? # == code (new segment) -#? # # comment 3 inside a segment -#? # 1 -#? # (empty line) -#? # 2 3 # comment 4 inline with other contents -#? # == data (new segment) -#? # 4 5/imm32 -#? # == code (existing segment but non-contiguous with previous iteration) -#? # 6 7 -#? # 8 9 (multiple lines) -#? # == code (existing segment contiguous with previous iteration) -#? # 10 11 -#? # . write(_test-input-stream, "# comment 1") -#? # . . push args -#? 68/push "# comment 1"/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") -#? # . . push args -#? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, " # comment 2 indented") -#? # . . push args -#? 68/push " # comment 2 indented"/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") -#? # . . push args -#? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "== code") -#? # . . push args -#? 68/push "== code"/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") -#? # . . push args -#? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "# comment 3 inside a segment") -#? # . . push args -#? 68/push "# comment 3 inside a segment"/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") -#? # . . push args -#? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "1") -#? # . . push args -#? 68/push "1"/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") -#? # . . push args -#? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") # empty line -#? # . . push args -#? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "2 3 # comment 4 inline with other comments") -#? # . . push args -#? 68/push "2 3 # comment 4 inline with other comments"/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") -#? # . . push args -#? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "== data") -#? # . . push args -#? 68/push "== data"/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") -#? # . . push args -#? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "4 5/imm32") -#? # . . push args -#? 68/push "4 5/imm32"/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") -#? # . . push args -#? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "== code") -#? # . . push args -#? 68/push "== code"/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") -#? # . . push args -#? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "6 7") -#? # . . push args -#? 68/push "6 7"/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") -#? # . . push args -#? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "8 9") -#? # . . push args -#? 68/push "6 7"/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") -#? # . . push args -#? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 -#? # . . call -#? e8/call write/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "== code") +test-convert: + # . prolog + 55/push-EBP + 89/copy 3/mod/direct 5/rm32/EBP . . . 4/r32/ESP . . # copy ESP to EBP + # setup + # . clear-stream(_test-input-stream) + # . . push args + 68/push _test-input-stream/imm32 + # . . call + e8/call clear-stream/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 4/imm32 # add to ESP + # . clear-stream(_test-input-buffered-file+4) + # . . push args + b8/copy-to-EAX _test-input-buffered-file/imm32 + 05/add-to-EAX 4/imm32 + 50/push-EAX + # . . call + e8/call clear-stream/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 4/imm32 # add to ESP + # . clear-stream(_test-output-stream) + # . . push args + 68/push _test-output-stream/imm32 + # . . call + e8/call clear-stream/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 4/imm32 # add to ESP + # . clear-stream(_test-output-buffered-file+4) + # . . push args + b8/copy-to-EAX _test-output-buffered-file/imm32 + 05/add-to-EAX 4/imm32 + 50/push-EAX + # . . call + e8/call clear-stream/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 4/imm32 # add to ESP + # initialize input (meta comments in parens) + # # comment 1 + # # comment 2 indented + # == code (new segment) + # # comment 3 inside a segment + # 1 + # (empty line) + # 2 3 # comment 4 inline with other contents + # == data (new segment) + # 4 5/imm32 + # == code (existing segment but non-contiguous with previous iteration) + # 6 7 + # 8 9 (multiple lines) + # == code (existing segment contiguous with previous iteration) + # 10 11 + # . write(_test-input-stream, "# comment 1") + # . . push args + 68/push "# comment 1"/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, " # comment 2 indented") + # . . push args + 68/push " # comment 2 indented"/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "== code") + # . . push args + 68/push "== code"/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "# comment 3 inside a segment") + # . . push args + 68/push "# comment 3 inside a segment"/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "1") + # . . push args + 68/push "1"/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") # empty line + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "2 3 # comment 4 inline with other contents") + # . . push args + 68/push "2 3 # comment 4 inline with other contents"/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "== data") + # . . push args + 68/push "== data"/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "4 5/imm32") + # . . push args + 68/push "4 5/imm32"/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "== code") + # . . push args + 68/push "== code"/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "6 7") + # . . push args + 68/push "6 7"/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "8 9") + # . . push args + 68/push "8 9"/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "== code") + # . . push args + 68/push "== code"/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "10 11") + # . . push args + 68/push "10 11"/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write(_test-input-stream, "\n") + # . . push args + 68/push Newline/imm32 + 68/push _test-input-stream/imm32 + # . . call + e8/call write/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # convert(_test-input-buffered-file, _test-output-buffered-file) + # . . push args + 68/push _test-output-buffered-file/imm32 + 68/push _test-input-buffered-file/imm32 + # . . call + e8/call convert/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # check output + # == code + # 1 + # 2 3 # comment 4 inline with other contents + # 6 7 + # 8 9 + # 10 11 + # == data + # 4 5/imm32 +#? # dump output {{{ +#? # . write(2/stderr, "result: ^") #? # . . push args -#? 68/push "== code"/imm32 -#? 68/push _test-input-stream/imm32 +#? 68/push "result: ^"/imm32 +#? 68/push 2/imm32/stderr #? # . . call #? e8/call write/disp32 #? # . . discard args #? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") +#? # . write-stream(2/stderr, _test-output-stream) #? # . . push args -#? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 +#? 68/push _test-output-stream/imm32 +#? 68/push 2/imm32/stderr #? # . . call -#? e8/call write/disp32 +#? e8/call write-stream/disp32 #? # . . discard args #? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "10 11") +#? # . write(2/stderr, "$") #? # . . push args -#? 68/push "10 11"/imm32 -#? 68/push _test-input-stream/imm32 +#? 68/push "$"/imm32 +#? 68/push 2/imm32/stderr #? # . . call #? e8/call write/disp32 #? # . . discard args #? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # . write(_test-input-stream, "\n") +#? # . write(2/stderr, "\n") #? # . . push args #? 68/push Newline/imm32 -#? 68/push _test-input-stream/imm32 +#? 68/push 2/imm32/stderr #? # . . call #? e8/call write/disp32 #? # . . discard args #? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # convert(_test-input-buffered-file, _test-output-buffered-file) -#? # . . push args -#? 68/push _test-output-buffered-file/imm32 -#? 68/push _test-input-buffered-file/imm32 -#? # . . call -#? e8/call convert/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? # check output -#? # == code -#? # 1 -#? # 2 3 # comment 4 inline with other contents -#? # 6 7 -#? # 8 9 -#? # 10 11 -#? # == data -#? # 4 5/imm32 -#? #? # debug print {{{ -#? #? # . write(2/stderr, "^") -#? #? # . . push args -#? #? 68/push "^"/imm32 -#? #? 68/push 2/imm32/stderr -#? #? # . . call -#? #? e8/call write/disp32 -#? #? # . . discard args -#? #? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? #? # . write-stream(2/stderr, _test-output-stream) -#? #? # . . push args -#? #? 68/push _test-output-stream/imm32 -#? #? 68/push 2/imm32/stderr -#? #? # . . call -#? #? e8/call write-stream/disp32 -#? #? # . . discard args -#? #? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? #? # . write(2/stderr, "$") -#? #? # . . push args -#? #? 68/push "$"/imm32 -#? #? 68/push 2/imm32/stderr -#? #? # . . call -#? #? e8/call write/disp32 -#? #? # . . discard args -#? #? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? #? # . write(2/stderr, "\n") -#? #? # . . push args -#? #? 68/push Newline/imm32 -#? #? 68/push 2/imm32/stderr -#? #? # . . call -#? #? e8/call write/disp32 -#? #? # . . discard args -#? #? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP -#? #? # }}} -#? # . flush(_test-output-buffered-file) -#? # . . push args -#? 68/push _test-output-buffered-file/imm32 -#? # . . call -#? e8/call flush/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 4/imm32 # add to ESP -#? # . check-next-stream-line-equal(_test-output-stream, "== code", msg) -#? # . . push args -#? 68/push "F - test-convert-code-and-data-segments/0"/imm32 -#? 68/push "== code"/imm32 -#? 68/push _test-output-stream/imm32 -#? # . . call -#? e8/call check-next-stream-line-equal/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP -#? # . check-next-stream-line-equal(_test-output-stream, "1", msg) -#? # . . push args -#? 68/push "F - test-convert-code-and-data-segments/1"/imm32 -#? 68/push "e8 20 00 00 00 # e8/call 20/disp32"/imm32 -#? 68/push _test-output-stream/imm32 -#? # . . call -#? e8/call check-next-stream-line-equal/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP -#? # . check-next-stream-line-equal(_test-output-stream, "2 3 # comment 4 inline with other contents", msg) -#? # . . push args -#? 68/push "F - test-convert-code-and-data-segments/2"/imm32 -#? 68/push "2 3 # comment 4 inline with other contents"/imm32 -#? 68/push _test-output-stream/imm32 -#? # . . call -#? e8/call check-next-stream-line-equal/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP -#? # . check-next-stream-line-equal(_test-output-stream, "6 7", msg) -#? # . . push args -#? 68/push "F - test-convert-code-and-data-segments/3"/imm32 -#? 68/push "6 7"/imm32 -#? 68/push _test-output-stream/imm32 -#? # . . call -#? e8/call check-next-stream-line-equal/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP -#? # . check-next-stream-line-equal(_test-output-stream, "8 9", msg) -#? # . . push args -#? 68/push "F - test-convert-code-and-data-segments/4"/imm32 -#? 68/push "8 9"/imm32 -#? 68/push _test-output-stream/imm32 -#? # . . call -#? e8/call check-next-stream-line-equal/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP -#? # . check-next-stream-line-equal(_test-output-stream, "10 11", msg) -#? # . . push args -#? 68/push "F - test-convert-code-and-data-segments/5"/imm32 -#? 68/push "10 11"/imm32 -#? 68/push _test-output-stream/imm32 -#? # . . call -#? e8/call check-next-stream-line-equal/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP -#? # . check-next-stream-line-equal(_test-output-stream, "== data", msg) -#? # . . push args -#? 68/push "F - test-convert-code-and-data-segments/6"/imm32 -#? 68/push "== data"/imm32 -#? 68/push _test-output-stream/imm32 -#? # . . call -#? e8/call check-next-stream-line-equal/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP -#? # . check-next-stream-line-equal(_test-output-stream, "4 5/imm32", msg) -#? # . . push args -#? 68/push "F - test-convert-code-and-data-segments/4"/imm32 -#? 68/push "4 5/imm32"/imm32 -#? 68/push _test-output-stream/imm32 -#? # . . call -#? e8/call check-next-stream-line-equal/disp32 -#? # . . discard args -#? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP -#? # . epilog -#? 89/copy 3/mod/direct 4/rm32/ESP . . . 5/r32/EBP . . # copy EBP to ESP -#? 5d/pop-to-EBP -#? c3/return +#? # }}} + # . flush(_test-output-buffered-file) + # . . push args + 68/push _test-output-buffered-file/imm32 + # . . call + e8/call flush/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 4/imm32 # add to ESP + # . check-next-stream-line-equal(_test-output-stream, "== code", msg) + # . . push args + 68/push "F - test-convert/0"/imm32 + 68/push "== code"/imm32 + 68/push _test-output-stream/imm32 + # . . call + e8/call check-next-stream-line-equal/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP + # . check-next-stream-line-equal(_test-output-stream, "1", msg) + # . . push args + 68/push "F - test-convert/1"/imm32 + 68/push "1"/imm32 + 68/push _test-output-stream/imm32 + # . . call + e8/call check-next-stream-line-equal/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP + # . check-next-stream-line-equal(_test-output-stream, "2 3 # comment 4 inline with other contents", msg) + # . . push args + 68/push "F - test-convert/2"/imm32 + 68/push "2 3 # comment 4 inline with other contents"/imm32 + 68/push _test-output-stream/imm32 + # . . call + e8/call check-next-stream-line-equal/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP + # . check-next-stream-line-equal(_test-output-stream, "6 7", msg) + # . . push args + 68/push "F - test-convert/3"/imm32 + 68/push "6 7"/imm32 + 68/push _test-output-stream/imm32 + # . . call + e8/call check-next-stream-line-equal/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP + # . check-next-stream-line-equal(_test-output-stream, "8 9", msg) + # . . push args + 68/push "F - test-convert/4"/imm32 + 68/push "8 9"/imm32 + 68/push _test-output-stream/imm32 + # . . call + e8/call check-next-stream-line-equal/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP + # . check-next-stream-line-equal(_test-output-stream, "10 11", msg) + # . . push args + 68/push "F - test-convert/5"/imm32 + 68/push "10 11"/imm32 + 68/push _test-output-stream/imm32 + # . . call + e8/call check-next-stream-line-equal/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP + # . check-next-stream-line-equal(_test-output-stream, "== data", msg) + # . . push args + 68/push "F - test-convert/6"/imm32 + 68/push "== data"/imm32 + 68/push _test-output-stream/imm32 + # . . call + e8/call check-next-stream-line-equal/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP + # . check-next-stream-line-equal(_test-output-stream, "4 5/imm32", msg) + # . . push args + 68/push "F - test-convert/7"/imm32 + 68/push "4 5/imm32"/imm32 + 68/push _test-output-stream/imm32 + # . . call + e8/call check-next-stream-line-equal/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0xc/imm32 # add to ESP + # . epilog + 89/copy 3/mod/direct 4/rm32/ESP . . . 5/r32/EBP . . # copy EBP to ESP + 5d/pop-to-EBP + c3/return read-segments: # in : (address buffered-file), table : (address stream row) # pseudocode: @@ -547,17 +547,32 @@ read-segments: # in : (address buffered-file), table : (address stream row) # continue # if slice-starts-with?(word-slice, "#") # comment # continue - # if (slice-equal?(word-slice, "==")) + # if slice-equal?(word-slice, "==") # var segment-name = next-word(line) - # curr-segment = get-or-insert-segment(table, segment-name, N) + # curr-segment = get-or-insert-segment(table, segment-name, Segment-size) # else - # write-stream-data(curr-segment, line) + # rewind-stream(line) + # write-stream(curr-segment, line) # abort if curr-segment overflows + # + # word-slice and segment-name are both slices with disjoint lifetimes, so + # we'll use the same address for them. + # + # registers: + # line: ECX + # word-slice and segment-name: EDX + # segment-name and curr-segment: EBX + # word-slice->start: ESI + # temporary: EAX # # . prolog 55/push-EBP 89/copy 3/mod/direct 5/rm32/EBP . . . 4/r32/ESP . . # copy ESP to EBP # . save registers + 50/push-EAX 51/push-ECX + 52/push-EDX + 53/push-EBX + 56/push-ESI # var line/ECX : (address stream byte) = stream(512) 81 5/subop/subtract 3/mod/direct 4/rm32/ESP . . . . . 0x200/imm32 # subtract from ESP 68/push 0x200/imm32/length @@ -568,8 +583,6 @@ read-segments: # in : (address buffered-file), table : (address stream row) 68/push 0/imm32/end 68/push 0/imm32/curr 89/copy 3/mod/direct 2/rm32/EDX . . . 4/r32/ESP . . # copy ESP to EDX - # var curr-segment/EBX = null - 31/xor 3/mod/direct 3/rm32/EBX . . . 3/r32/EBX . . # clear EBX $read-segments:loop: # clear-stream(line) # . . push args @@ -645,15 +658,15 @@ $read-segments:check1: 3d/compare-EAX-and 0/imm32 0f 85/jump-if-not-equal $read-segments:loop/disp32 $read-segments:check-for-comment: - # if (slice-starts-with?(word-slice, "#")) - # . start/EDX = word-slice->start - 8b/copy 0/mod/indirect 1/rm32/ECX . . . 2/r32/EDX . . # copy *ECX to EDX + # if slice-starts-with?(word-slice, "#") + # . start/ESI = word-slice->start + 8b/copy 0/mod/indirect 2/rm32/EDX . . . 6/r32/ESI . . # copy *ECX to ESI # . c/EAX = *start 31/xor 3/mod/direct 0/rm32/EAX . . . 0/r32/EAX . . # clear EAX - 8a/copy-byte 0/mod/indirect 2/rm32/EDX . . . 0/r32/AL . . # copy byte at *EDX to AL + 8a/copy-byte 0/mod/indirect 6/rm32/ESI . . . 0/r32/AL . . # copy byte at *ESI to AL # . if (EAX == '#') continue 3d/compare-EAX-and 0x23/imm32/hash - 74/jump-if-equal $read-segments:loop/disp8 + 0f 84/jump-if-equal $read-segments:loop/disp32 $read-segments:check-for-segment-header: #? # dump word-slice {{{ #? # . write(2/stderr, "AA: ") @@ -705,7 +718,7 @@ $read-segments:check-for-segment-header: #? # . . discard args #? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP #? # }}} - # if (slice-equal?(word-slice, "==")) + # if slice-equal?(word-slice, "==") # segment-name = next-word(line) # curr-segment = get-or-insert(table, segment-name) # . EAX = slice-equal?(word-slice, "==") @@ -777,9 +790,9 @@ $read-segments:check-for-segment-header: #? # . . discard args #? 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP #? # }}} - # . EAX = get-or-insert-segment(table, segment-name, N) + # . EAX = get-or-insert-segment(table, segment-name, Segment-size) # . . push args - 68/push 0x1000/imm32/segment-size/4KB + ff 6/subop/push 0/mod/indirect 5/rm32/.disp32 . . . Segment-size/disp32 # push *Segment-size 52/push-EDX ff 6/subop/push 1/mod/*+disp8 5/rm32/EBP . . . . 0xc/disp8 . # push *(EBP+12) # . . call @@ -791,12 +804,19 @@ $read-segments:check-for-segment-header: # . continue e9/jump $read-segments:loop/disp32 $read-segments:regular-line: - # write-stream-data(curr-segment, line) + # rewind-stream(line) + # . . push args + 51/push-ECX + # . . call + e8/call rewind-stream/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 4/imm32 # add to ESP + # write-stream(curr-segment, line) # . . push args 51/push-ECX 53/push-EBX # . . call - e8/call write-stream-data/disp32 + e8/call write-stream/disp32 # . . discard args 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP # loop @@ -806,7 +826,11 @@ $read-segments:end: # . reclaim locals 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 0x214/imm32 # add to ESP # . restore registers + 5e/pop-to-ESI + 5b/pop-to-EBX + 5a/pop-to-EDX 59/pop-to-ECX + 58/pop-to-EAX # . epilog 89/copy 3/mod/direct 4/rm32/ESP . . . 5/r32/EBP . . # copy EBP to ESP 5d/pop-to-EBP @@ -814,26 +838,89 @@ $read-segments:end: write-segments: # out : (address buffered-file), table : (address stream row) # pseudocode: - # name, stream = table[0] - # var i = 0 - # while i < table.length + # var curr = table->data + # var max = table->data + table->write + # while curr < max # name = table[i].name - # if (name == null) break - # write-buffered(out, "== ") - # write-buffered(out, name) - # write-buffered(out, "\n") + # print out, "== $name\n" # stream = table[i].stream # write-stream-data(out, stream) - # ++i + # curr += 8 # flush(out) # # . prolog 55/push-EBP 89/copy 3/mod/direct 5/rm32/EBP . . . 4/r32/ESP . . # copy ESP to EBP # . save registers + 50/push-EAX + 52/push-EDX + 56/push-ESI + # ESI = table + 8b/copy 1/mod/*+disp8 5/rm32/EBP . . . 6/r32/ESI 0xc/disp8 . # copy *(EBP+12) to ESI + # write/EDX = table->write + 8b/copy 0/mod/indirect 6/rm32/ESI . . . 2/r32/EDX . . # copy *ESI to EDX + # curr/ESI = table->data + 81 0/subop/add 3/mod/direct 6/rm32/ESI . . . . . 0xc/imm32 # add to EAX + # max/EDX = curr + write + 01/add 3/mod/direct 2/rm32/EDX . . . 6/r32/ESI . . # add ESI to EDX +$write-segments:loop: + # if (curr >= max) break + 39/compare 3/mod/direct 6/rm32/ESI . . . 2/r32/EDX . . # compare ESI with EDX + 7d/jump-if-greater-or-equal $write-segments:break/disp8 + # name/EAX = table[i].name + 8b/copy 0/mod/indirect 6/rm32/ESI . . . 0/r32/EAX . . # copy *ESI to EAX + # print out, "== $name\n" + # . write-buffered(out, "== ") + # . . push args + 68/push "== "/imm32 + ff 6/subop/push 1/mod/*+disp8 5/rm32/EBP . . . . 8/disp8 . # push *(EBP+8) + # . . call + e8/call write-buffered/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write-buffered(out, name) + # . . push args + 50/push-EAX + ff 6/subop/push 1/mod/*+disp8 5/rm32/EBP . . . . 8/disp8 . # push *(EBP+8) + # . . call + e8/call write-buffered/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # . write-buffered(out, "\n") + # . . push args + 68/push Newline/imm32 + ff 6/subop/push 1/mod/*+disp8 5/rm32/EBP . . . . 8/disp8 . # push *(EBP+8) + # . . call + e8/call write-buffered/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP + # stream/EAX = table[i].stream + 8b/copy 1/mod/*+disp8 6/rm32/ESI . . . 0/r32/EAX 4/disp8 . # copy *(ESI+4) to EAX + # write-stream-data(out, stream) + # . . push args + 50/push-EAX + ff 6/subop/push 1/mod/*+disp8 5/rm32/EBP . . . . 8/disp8 . # push *(EBP+8) + # . . call + e8/call write-stream-data/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP +$write-segments:continue: + # curr += 8 + 81 0/subop/add 3/mod/direct 6/rm32/ESI . . . . . 8/imm32 # add to ESI + eb/jump $write-segments:loop/disp8 +$write-segments:break: + # flush(out) + # . . push args + ff 6/subop/push 1/mod/*+disp8 5/rm32/EBP . . . . 8/disp8 . # push *(EBP+8) + # . . call + e8/call flush/disp32 + # . . discard args + 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 4/imm32 # add to ESP $write-segments:end: - # . reclaim locals # . restore registers + 5e/pop-to-ESI + 5a/pop-to-EDX + 58/pop-to-EAX # . epilog 89/copy 3/mod/direct 4/rm32/ESP . . . 5/r32/EBP . . # copy EBP to ESP 5d/pop-to-EBP @@ -911,7 +998,7 @@ $get-or-insert-segment:not-found: e8/call slice-to-string/disp32 # . . discard args 81 0/subop/add 3/mod/direct 4/rm32/ESP . . . . . 8/imm32 # add to ESP - # . *max = EAX <= writes to 0x0a003873 + # . *max = EAX 89/copy 0/mod/indirect 2/rm32/EDX . . . 0/r32/EAX . . # copy EAX to *EDX # result/EAX = new-stream(Heap, n, 1) # . . push args @@ -1310,4 +1397,7 @@ _test-data-segment: 64/d 61/a 74/t 61/a _test-data-segment-end: +Segment-size: + 0x1000/imm32/4KB + # . . vim:nowrap:textwidth=0 diff --git a/subx/test_apps b/subx/test_apps index bca9d65b..4378a9df 100755 --- a/subx/test_apps +++ b/subx/test_apps @@ -190,4 +190,14 @@ test `uname` = 'Linux' && { echo } +echo assort +./subx translate *.subx apps/subx-common.subx apps/assort.subx -o apps/assort +[ "$1" != record ] && git diff --quiet apps/assort +./subx run apps/assort test +echo +test `uname` = 'Linux' && { + apps/assort test + echo +} + exit 0 |