From 333b605b2afd472b823aeda0adf0e8b1ea9843c0 Mon Sep 17 00:00:00 2001 From: fishsoupisgood Date: Mon, 27 May 2019 02:41:51 +0100 Subject: initial commit from asl-1.41r8.tar.gz --- tests/t_166/asflags | 0 tests/t_166/t_166.asm | 232 ++ tests/t_166/t_166.doc | 5 + tests/t_166/t_166.ori | Bin 0 -> 534 bytes tests/t_16c5x/asflags | 0 tests/t_16c5x/t_16c5x.asm | 45 + tests/t_16c5x/t_16c5x.doc | 5 + tests/t_16c5x/t_16c5x.ori | Bin 0 -> 70 bytes tests/t_16c84/asflags | 0 tests/t_16c84/t_16c84.asm | 53 + tests/t_16c84/t_16c84.doc | 5 + tests/t_16c84/t_16c84.ori | Bin 0 -> 90 bytes tests/t_17c42/asflags | 0 tests/t_17c42/t_17c42.asm | 66 + tests/t_17c42/t_17c42.doc | 5 + tests/t_17c42/t_17c42.ori | Bin 0 -> 112 bytes tests/t_251/asflags | 0 tests/t_251/t_251.asm | 399 ++++ tests/t_251/t_251.doc | 5 + tests/t_251/t_251.ori | Bin 0 -> 1035 bytes tests/t_296/asflags | 0 tests/t_296/t_296.asm | 132 ++ tests/t_296/t_296.doc | 6 + tests/t_296/t_296.ori | Bin 0 -> 463 bytes tests/t_29k/asflags | 0 tests/t_29k/t_29k.asm | 80 + tests/t_29k/t_29k.doc | 5 + tests/t_29k/t_29k.ori | Bin 0 -> 220 bytes tests/t_32/asflags | 0 tests/t_32/t_32.asm | 39 + tests/t_32/t_32.doc | 6 + tests/t_32/t_32.ori | Bin 0 -> 134 bytes tests/t_3201x/asflags | 0 tests/t_3201x/t_3201x.asm | 74 + tests/t_3201x/t_3201x.doc | 5 + tests/t_3201x/t_3201x.ori | Bin 0 -> 148 bytes tests/t_3203x/asflags | 0 tests/t_3203x/t_3203x.asm | 271 +++ tests/t_3203x/t_3203x.doc | 5 + tests/t_3203x/t_3203x.ori | Bin 0 -> 816 bytes tests/t_3205x/asflags | 0 tests/t_3205x/t_3205x.asm | 499 ++++ tests/t_3205x/t_3205x.doc | 7 + tests/t_3205x/t_3205x.ori | Bin 0 -> 866 bytes tests/t_3206x/asflags | 0 tests/t_3206x/t_3206x.asm | 241 ++ tests/t_3206x/t_3206x.doc | 5 + tests/t_3206x/t_3206x.ori | Bin 0 -> 744 bytes tests/t_370/asflags | 0 tests/t_370/t_370.asm | 163 ++ tests/t_370/t_370.doc | 5 + tests/t_370/t_370.ori | Bin 0 -> 317 bytes tests/t_4004/asflags | 0 tests/t_4004/t_4004.asm | 205 ++ tests/t_4004/t_4004.doc | 5 + tests/t_4004/t_4004.ori | Bin 0 -> 240 bytes tests/t_403/asflags | 0 tests/t_403/t_403.asm | 27 + tests/t_403/t_403.doc | 6 + tests/t_403/t_403.ori | Bin 0 -> 64 bytes tests/t_4500/asflags | 0 tests/t_4500/t_4500.asm | 109 + tests/t_4500/t_4500.doc | 5 + tests/t_4500/t_4500.ori | Bin 0 -> 246 bytes tests/t_47c00/asflags | 0 tests/t_47c00/t_47c00.asm | 255 ++ tests/t_47c00/t_47c00.doc | 5 + tests/t_47c00/t_47c00.ori | Bin 0 -> 529 bytes tests/t_48/asflags | 0 tests/t_48/t_48.asm | 178 ++ tests/t_48/t_48.doc | 5 + tests/t_48/t_48.ori | Bin 0 -> 137 bytes tests/t_56000/asflags | 0 tests/t_56000/t_56000.asm | 244 ++ tests/t_56000/t_56000.doc | 5 + tests/t_56000/t_56000.ori | Bin 0 -> 980 bytes tests/t_56300/asflags | 0 tests/t_56300/t_56300.asm | 1462 ++++++++++++ tests/t_56300/t_56300.doc | 6 + tests/t_56300/t_56300.ori | Bin 0 -> 6788 bytes tests/t_65/asflags | 0 tests/t_65/t_65.asm | 283 +++ tests/t_65/t_65.doc | 5 + tests/t_65/t_65.ori | Bin 0 -> 460 bytes tests/t_6502u/asflags | 0 tests/t_6502u/t_6502u.asm | 110 + tests/t_6502u/t_6502u.doc | 7 + tests/t_6502u/t_6502u.ori | Bin 0 -> 207 bytes tests/t_6804/asflags | 0 tests/t_6804/t_6804.asm | 72 + tests/t_6804/t_6804.doc | 5 + tests/t_6804/t_6804.ori | Bin 0 -> 92 bytes tests/t_68040/asflags | 0 tests/t_68040/t_68040.asm | 29 + tests/t_68040/t_68040.doc | 6 + tests/t_68040/t_68040.ori | Bin 0 -> 60 bytes tests/t_6805/asflags | 0 tests/t_6805/t_6805.asm | 244 ++ tests/t_6805/t_6805.doc | 5 + tests/t_6805/t_6805.ori | Bin 0 -> 405 bytes tests/t_6808/asflags | 0 tests/t_6808/t_6808.asm | 406 ++++ tests/t_6808/t_6808.doc | 6 + tests/t_6808/t_6808.ori | Bin 0 -> 671 bytes tests/t_6812/asflags | 0 tests/t_6812/t_6812.asm | 644 ++++++ tests/t_6812/t_6812.doc | 5 + tests/t_6812/t_6812.ori | Bin 0 -> 1104 bytes tests/t_6816/asflags | 0 tests/t_6816/t_6816.asm | 1037 +++++++++ tests/t_6816/t_6816.doc | 5 + tests/t_6816/t_6816.ori | Bin 0 -> 2874 bytes tests/t_7000/asflags | 0 tests/t_7000/t_7000.asm | 249 ++ tests/t_7000/t_7000.doc | 5 + tests/t_7000/t_7000.ori | Bin 0 -> 428 bytes tests/t_75k0/asflags | 0 tests/t_75k0/t_75k0.asm | 191 ++ tests/t_75k0/t_75k0.doc | 5 + tests/t_75k0/t_75k0.ori | Bin 0 -> 262 bytes tests/t_7700/asflags | 0 tests/t_7700/t_7700.asm | 356 +++ tests/t_7700/t_7700.doc | 5 + tests/t_7700/t_7700.ori | Bin 0 -> 934 bytes tests/t_7720/asflags | 0 tests/t_7720/t_7720.asm | 141 ++ tests/t_7720/t_7720.doc | 5 + tests/t_7720/t_7720.ori | Bin 0 -> 392 bytes tests/t_77230/asflags | 0 tests/t_77230/t_77230.asm | 245 ++ tests/t_77230/t_77230.doc | 5 + tests/t_77230/t_77230.ori | Bin 0 -> 668 bytes tests/t_7725/asflags | 0 tests/t_7725/t_7725.asm | 171 ++ tests/t_7725/t_7725.doc | 5 + tests/t_7725/t_7725.ori | Bin 0 -> 508 bytes tests/t_78c1x/asflags | 0 tests/t_78c1x/t_78c1x.asm | 258 +++ tests/t_78c1x/t_78c1x.doc | 5 + tests/t_78c1x/t_78c1x.ori | Bin 0 -> 465 bytes tests/t_78k0/asflags | 0 tests/t_78k0/t_78k0.asm | 291 +++ tests/t_78k0/t_78k0.doc | 5 + tests/t_78k0/t_78k0.ori | Bin 0 -> 606 bytes tests/t_85/asflags | 0 tests/t_85/t_85.asm | 134 ++ tests/t_85/t_85.doc | 5 + tests/t_85/t_85.ori | Bin 0 -> 180 bytes tests/t_87c800/asflags | 0 tests/t_87c800/t_87c800.asm | 310 +++ tests/t_87c800/t_87c800.doc | 5 + tests/t_87c800/t_87c800.ori | Bin 0 -> 609 bytes tests/t_8x30x/asflags | 0 tests/t_8x30x/t_8x30x.asm | 57 + tests/t_8x30x/t_8x30x.doc | 5 + tests/t_8x30x/t_8x30x.ori | Bin 0 -> 80 bytes tests/t_96/asflags | 0 tests/t_96/t_96.asm | 217 ++ tests/t_96/t_96.doc | 5 + tests/t_96/t_96.ori | Bin 0 -> 531 bytes tests/t_960/asflags | 0 tests/t_960/t_960.asm | 101 + tests/t_960/t_960.doc | 5 + tests/t_960/t_960.ori | Bin 0 -> 404 bytes tests/t_97c241/asflags | 0 tests/t_97c241/t_97c241.asm | 336 +++ tests/t_97c241/t_97c241.doc | 5 + tests/t_97c241/t_97c241.ori | Bin 0 -> 1100 bytes tests/t_9900/asflags | 0 tests/t_9900/t_9900.asm | 222 ++ tests/t_9900/t_9900.doc | 5 + tests/t_9900/t_9900.ori | Bin 0 -> 550 bytes tests/t_ace/asflags | 0 tests/t_ace/t_ace.asm | 132 ++ tests/t_ace/t_ace.doc | 5 + tests/t_ace/t_ace.ori | Bin 0 -> 159 bytes tests/t_avr/asflags | 0 tests/t_avr/t_avr.asm | 229 ++ tests/t_avr/t_avr.doc | 5 + tests/t_avr/t_avr.ori | Bin 0 -> 238 bytes tests/t_bas52/asflags | 0 tests/t_bas52/bas52.clk | 18 + tests/t_bas52/bas52.fp | 1616 +++++++++++++ tests/t_bas52/bas52.out | 75 + tests/t_bas52/bas52.pgm | 125 + tests/t_bas52/bas52.pwm | 25 + tests/t_bas52/bas52.rst | 111 + tests/t_bas52/bas52.tl | 16 + tests/t_bas52/look52.inc | 779 +++++++ tests/t_bas52/t_bas52.asm | 4644 +++++++++++++++++++++++++++++++++++++ tests/t_bas52/t_bas52.doc | 11 + tests/t_bas52/t_bas52.inc | 2 + tests/t_bas52/t_bas52.ori | Bin 0 -> 8192 bytes tests/t_buf32/asflags | 0 tests/t_buf32/t_buf32.asm | 4883 +++++++++++++++++++++++++++++++++++++++ tests/t_buf32/t_buf32.doc | 5 + tests/t_buf32/t_buf32.inc | 2 + tests/t_buf32/t_buf32.ori | Bin 0 -> 8192 bytes tests/t_cop8/asflags | 0 tests/t_cop8/t_cop8.asm | 128 + tests/t_cop8/t_cop8.doc | 5 + tests/t_cop8/t_cop8.ori | Bin 0 -> 262 bytes tests/t_f2mc8l/asflags | 0 tests/t_f2mc8l/t_f2mc8l.asm | 242 ++ tests/t_f2mc8l/t_f2mc8l.doc | 5 + tests/t_f2mc8l/t_f2mc8l.ori | Bin 0 -> 314 bytes tests/t_fl90/asflags | 0 tests/t_fl90/cpu_time.inc | 170 ++ tests/t_fl90/float.inc | 1601 +++++++++++++ tests/t_fl90/macros.inc | 57 + tests/t_fl90/mon.inc | 11 + tests/t_fl90/t_fl90.asm | 179 ++ tests/t_fl90/t_fl90.doc | 6 + tests/t_fl90/t_fl90.ori | Bin 0 -> 5466 bytes tests/t_fl900/asflags | 0 tests/t_fl900/conout.inc | 154 ++ tests/t_fl900/cpu_time.inc | 240 ++ tests/t_fl900/float.inc | 973 ++++++++ tests/t_fl900/macros.inc | 16 + tests/t_fl900/t_fl900.asm | 166 ++ tests/t_fl900/t_fl900.doc | 6 + tests/t_fl900/t_fl900.inc | 2 + tests/t_fl900/t_fl900.ori | Bin 0 -> 3408 bytes tests/t_full09/asflags | 1 + tests/t_full09/t_full09.asm | 1604 +++++++++++++ tests/t_full09/t_full09.doc | 6 + tests/t_full09/t_full09.ori | Bin 0 -> 7308 bytes tests/t_h8_3/asflags | 0 tests/t_h8_3/t_h8_3.asm | 353 +++ tests/t_h8_3/t_h8_3.doc | 5 + tests/t_h8_3/t_h8_3.ori | Bin 0 -> 1156 bytes tests/t_h8_5/asflags | 0 tests/t_h8_5/t_h8_5.asm | 229 ++ tests/t_h8_5/t_h8_5.doc | 5 + tests/t_h8_5/t_h8_5.ori | Bin 0 -> 407 bytes tests/t_m16c/asflags | 0 tests/t_m16c/t_m16c.asm | 4051 ++++++++++++++++++++++++++++++++ tests/t_m16c/t_m16c.doc | 6 + tests/t_m16c/t_m16c.ori | Bin 0 -> 15722 bytes tests/t_mcore/asflags | 0 tests/t_mcore/t_mcore.asm | 140 ++ tests/t_mcore/t_mcore.doc | 5 + tests/t_mcore/t_mcore.ori | Bin 0 -> 240 bytes tests/t_mic51/DEBUG.ASM | 532 +++++ tests/t_mic51/MAKRO1.ASM | 542 +++++ tests/t_mic51/MEM1.ASM | 727 ++++++ tests/t_mic51/RUN1.ASM | 773 +++++++ tests/t_mic51/TAST1.ASM | 250 ++ tests/t_mic51/TEACH1.ASM | 504 ++++ tests/t_mic51/asflags | 1 + tests/t_mic51/defKey.inc | 83 + tests/t_mic51/defModul.inc | 18 + tests/t_mic51/defMsg.inc | 141 ++ tests/t_mic51/defParam.inc | 46 + tests/t_mic51/defgequ.inc | 48 + tests/t_mic51/defint.inc | 234 ++ tests/t_mic51/defmacro.inc | 175 ++ tests/t_mic51/net_lcd.inc | 33 + tests/t_mic51/t_mic51.asm | 2197 ++++++++++++++++++ tests/t_mic51/t_mic51.doc | 6 + tests/t_mic51/t_mic51.inc | 165 ++ tests/t_mic51/t_mic51.ori | Bin 0 -> 17582 bytes tests/t_mic51/t_mod1.asm | 487 ++++ tests/t_msp/asflags | 0 tests/t_msp/t_msp.asm | 116 + tests/t_msp/t_msp.doc | 5 + tests/t_msp/t_msp.ori | Bin 0 -> 363 bytes tests/t_parsys/asflags | 1 + tests/t_parsys/float.i68 | 1226 ++++++++++ tests/t_parsys/float81.i68 | 293 +++ tests/t_parsys/parsys.i68 | 115 + tests/t_parsys/t_parsys.asm | 994 ++++++++ tests/t_parsys/t_parsys.doc | 8 + tests/t_parsys/t_parsys.inc | 10 + tests/t_parsys/t_parsys.ori | Bin 0 -> 7516 bytes tests/t_scmp/asflags | 0 tests/t_scmp/t_scmp.asm | 59 + tests/t_scmp/t_scmp.doc | 5 + tests/t_scmp/t_scmp.ori | Bin 0 -> 68 bytes tests/t_secdrive/asflags | 0 tests/t_secdrive/lowlevel.inc | 1 + tests/t_secdrive/secparam.inc | 1619 +++++++++++++ tests/t_secdrive/t_secdrive.asm | 1476 ++++++++++++ tests/t_secdrive/t_secdrive.doc | 9 + tests/t_secdrive/t_secdrive.ori | Bin 0 -> 11271 bytes tests/t_secdrive/wd1002xt.inc | 773 +++++++ tests/t_secdrive/wd1003at.inc | 952 ++++++++ tests/t_st6/asflags | 0 tests/t_st6/t_st6.asm | 82 + tests/t_st6/t_st6.doc | 5 + tests/t_st6/t_st6.ori | Bin 0 -> 102 bytes tests/t_st7/asflags | 0 tests/t_st7/t_st7.asm | 561 +++++ tests/t_st7/t_st7.doc | 5 + tests/t_st7/t_st7.ori | Bin 0 -> 1313 bytes tests/t_st9/asflags | 0 tests/t_st9/t_st9.asm | 1243 ++++++++++ tests/t_st9/t_st9.doc | 5 + tests/t_st9/t_st9.ori | Bin 0 -> 3290 bytes tests/t_tms7/asflags | 0 tests/t_tms7/t_tms7.asm | 364 +++ tests/t_tms7/t_tms7.doc | 5 + tests/t_tms7/t_tms7.ori | Bin 0 -> 696 bytes tests/t_xa/asflags | 0 tests/t_xa/t_xa.asm | 603 +++++ tests/t_xa/t_xa.doc | 5 + tests/t_xa/t_xa.ori | Bin 0 -> 1525 bytes tests/t_z380/asflags | 0 tests/t_z380/t_z380.asm | 677 ++++++ tests/t_z380/t_z380.doc | 5 + tests/t_z380/t_z380.ori | Bin 0 -> 1650 bytes tests/t_z8/asflags | 0 tests/t_z8/t_z8.asm | 116 + tests/t_z8/t_z8.doc | 5 + tests/t_z8/t_z8.ori | Bin 0 -> 180 bytes tests/testall | 38 + tests/testall.bat | 117 + tests/testall.cmd | 117 + tests/warnlog.DE | 35 + tests/warnlog.EN | 35 + 320 files changed, 52799 insertions(+) create mode 100644 tests/t_166/asflags create mode 100644 tests/t_166/t_166.asm create mode 100644 tests/t_166/t_166.doc create mode 100644 tests/t_166/t_166.ori create mode 100644 tests/t_16c5x/asflags create mode 100755 tests/t_16c5x/t_16c5x.asm create mode 100644 tests/t_16c5x/t_16c5x.doc create mode 100755 tests/t_16c5x/t_16c5x.ori create mode 100644 tests/t_16c84/asflags create mode 100644 tests/t_16c84/t_16c84.asm create mode 100644 tests/t_16c84/t_16c84.doc create mode 100644 tests/t_16c84/t_16c84.ori create mode 100644 tests/t_17c42/asflags create mode 100644 tests/t_17c42/t_17c42.asm create mode 100644 tests/t_17c42/t_17c42.doc create mode 100644 tests/t_17c42/t_17c42.ori create mode 100644 tests/t_251/asflags create mode 100644 tests/t_251/t_251.asm create mode 100644 tests/t_251/t_251.doc create mode 100644 tests/t_251/t_251.ori create mode 100644 tests/t_296/asflags create mode 100644 tests/t_296/t_296.asm create mode 100644 tests/t_296/t_296.doc create mode 100755 tests/t_296/t_296.ori create mode 100644 tests/t_29k/asflags create mode 100644 tests/t_29k/t_29k.asm create mode 100644 tests/t_29k/t_29k.doc create mode 100644 tests/t_29k/t_29k.ori create mode 100644 tests/t_32/asflags create mode 100644 tests/t_32/t_32.asm create mode 100644 tests/t_32/t_32.doc create mode 100644 tests/t_32/t_32.ori create mode 100644 tests/t_3201x/asflags create mode 100644 tests/t_3201x/t_3201x.asm create mode 100644 tests/t_3201x/t_3201x.doc create mode 100644 tests/t_3201x/t_3201x.ori create mode 100644 tests/t_3203x/asflags create mode 100644 tests/t_3203x/t_3203x.asm create mode 100644 tests/t_3203x/t_3203x.doc create mode 100755 tests/t_3203x/t_3203x.ori create mode 100644 tests/t_3205x/asflags create mode 100644 tests/t_3205x/t_3205x.asm create mode 100644 tests/t_3205x/t_3205x.doc create mode 100644 tests/t_3205x/t_3205x.ori create mode 100644 tests/t_3206x/asflags create mode 100644 tests/t_3206x/t_3206x.asm create mode 100644 tests/t_3206x/t_3206x.doc create mode 100644 tests/t_3206x/t_3206x.ori create mode 100644 tests/t_370/asflags create mode 100644 tests/t_370/t_370.asm create mode 100644 tests/t_370/t_370.doc create mode 100644 tests/t_370/t_370.ori create mode 100644 tests/t_4004/asflags create mode 100644 tests/t_4004/t_4004.asm create mode 100644 tests/t_4004/t_4004.doc create mode 100644 tests/t_4004/t_4004.ori create mode 100644 tests/t_403/asflags create mode 100644 tests/t_403/t_403.asm create mode 100644 tests/t_403/t_403.doc create mode 100644 tests/t_403/t_403.ori create mode 100644 tests/t_4500/asflags create mode 100644 tests/t_4500/t_4500.asm create mode 100644 tests/t_4500/t_4500.doc create mode 100644 tests/t_4500/t_4500.ori create mode 100644 tests/t_47c00/asflags create mode 100644 tests/t_47c00/t_47c00.asm create mode 100644 tests/t_47c00/t_47c00.doc create mode 100644 tests/t_47c00/t_47c00.ori create mode 100644 tests/t_48/asflags create mode 100644 tests/t_48/t_48.asm create mode 100644 tests/t_48/t_48.doc create mode 100644 tests/t_48/t_48.ori create mode 100644 tests/t_56000/asflags create mode 100644 tests/t_56000/t_56000.asm create mode 100644 tests/t_56000/t_56000.doc create mode 100644 tests/t_56000/t_56000.ori create mode 100644 tests/t_56300/asflags create mode 100644 tests/t_56300/t_56300.asm create mode 100644 tests/t_56300/t_56300.doc create mode 100644 tests/t_56300/t_56300.ori create mode 100644 tests/t_65/asflags create mode 100755 tests/t_65/t_65.asm create mode 100644 tests/t_65/t_65.doc create mode 100755 tests/t_65/t_65.ori create mode 100644 tests/t_6502u/asflags create mode 100644 tests/t_6502u/t_6502u.asm create mode 100644 tests/t_6502u/t_6502u.doc create mode 100644 tests/t_6502u/t_6502u.ori create mode 100644 tests/t_6804/asflags create mode 100644 tests/t_6804/t_6804.asm create mode 100644 tests/t_6804/t_6804.doc create mode 100644 tests/t_6804/t_6804.ori create mode 100644 tests/t_68040/asflags create mode 100644 tests/t_68040/t_68040.asm create mode 100644 tests/t_68040/t_68040.doc create mode 100644 tests/t_68040/t_68040.ori create mode 100644 tests/t_6805/asflags create mode 100755 tests/t_6805/t_6805.asm create mode 100644 tests/t_6805/t_6805.doc create mode 100755 tests/t_6805/t_6805.ori create mode 100644 tests/t_6808/asflags create mode 100644 tests/t_6808/t_6808.asm create mode 100644 tests/t_6808/t_6808.doc create mode 100644 tests/t_6808/t_6808.ori create mode 100644 tests/t_6812/asflags create mode 100644 tests/t_6812/t_6812.asm create mode 100644 tests/t_6812/t_6812.doc create mode 100644 tests/t_6812/t_6812.ori create mode 100644 tests/t_6816/asflags create mode 100644 tests/t_6816/t_6816.asm create mode 100644 tests/t_6816/t_6816.doc create mode 100644 tests/t_6816/t_6816.ori create mode 100644 tests/t_7000/asflags create mode 100644 tests/t_7000/t_7000.asm create mode 100644 tests/t_7000/t_7000.doc create mode 100644 tests/t_7000/t_7000.ori create mode 100644 tests/t_75k0/asflags create mode 100644 tests/t_75k0/t_75k0.asm create mode 100644 tests/t_75k0/t_75k0.doc create mode 100644 tests/t_75k0/t_75k0.ori create mode 100644 tests/t_7700/asflags create mode 100644 tests/t_7700/t_7700.asm create mode 100644 tests/t_7700/t_7700.doc create mode 100644 tests/t_7700/t_7700.ori create mode 100644 tests/t_7720/asflags create mode 100644 tests/t_7720/t_7720.asm create mode 100644 tests/t_7720/t_7720.doc create mode 100644 tests/t_7720/t_7720.ori create mode 100644 tests/t_77230/asflags create mode 100644 tests/t_77230/t_77230.asm create mode 100644 tests/t_77230/t_77230.doc create mode 100644 tests/t_77230/t_77230.ori create mode 100644 tests/t_7725/asflags create mode 100644 tests/t_7725/t_7725.asm create mode 100644 tests/t_7725/t_7725.doc create mode 100644 tests/t_7725/t_7725.ori create mode 100644 tests/t_78c1x/asflags create mode 100644 tests/t_78c1x/t_78c1x.asm create mode 100644 tests/t_78c1x/t_78c1x.doc create mode 100644 tests/t_78c1x/t_78c1x.ori create mode 100644 tests/t_78k0/asflags create mode 100644 tests/t_78k0/t_78k0.asm create mode 100644 tests/t_78k0/t_78k0.doc create mode 100644 tests/t_78k0/t_78k0.ori create mode 100644 tests/t_85/asflags create mode 100644 tests/t_85/t_85.asm create mode 100644 tests/t_85/t_85.doc create mode 100644 tests/t_85/t_85.ori create mode 100644 tests/t_87c800/asflags create mode 100644 tests/t_87c800/t_87c800.asm create mode 100644 tests/t_87c800/t_87c800.doc create mode 100644 tests/t_87c800/t_87c800.ori create mode 100644 tests/t_8x30x/asflags create mode 100644 tests/t_8x30x/t_8x30x.asm create mode 100644 tests/t_8x30x/t_8x30x.doc create mode 100644 tests/t_8x30x/t_8x30x.ori create mode 100644 tests/t_96/asflags create mode 100644 tests/t_96/t_96.asm create mode 100644 tests/t_96/t_96.doc create mode 100644 tests/t_96/t_96.ori create mode 100644 tests/t_960/asflags create mode 100644 tests/t_960/t_960.asm create mode 100644 tests/t_960/t_960.doc create mode 100644 tests/t_960/t_960.ori create mode 100644 tests/t_97c241/asflags create mode 100644 tests/t_97c241/t_97c241.asm create mode 100644 tests/t_97c241/t_97c241.doc create mode 100644 tests/t_97c241/t_97c241.ori create mode 100644 tests/t_9900/asflags create mode 100644 tests/t_9900/t_9900.asm create mode 100644 tests/t_9900/t_9900.doc create mode 100644 tests/t_9900/t_9900.ori create mode 100644 tests/t_ace/asflags create mode 100644 tests/t_ace/t_ace.asm create mode 100644 tests/t_ace/t_ace.doc create mode 100644 tests/t_ace/t_ace.ori create mode 100644 tests/t_avr/asflags create mode 100644 tests/t_avr/t_avr.asm create mode 100644 tests/t_avr/t_avr.doc create mode 100644 tests/t_avr/t_avr.ori create mode 100644 tests/t_bas52/asflags create mode 100644 tests/t_bas52/bas52.clk create mode 100644 tests/t_bas52/bas52.fp create mode 100644 tests/t_bas52/bas52.out create mode 100644 tests/t_bas52/bas52.pgm create mode 100644 tests/t_bas52/bas52.pwm create mode 100644 tests/t_bas52/bas52.rst create mode 100644 tests/t_bas52/bas52.tl create mode 100644 tests/t_bas52/look52.inc create mode 100644 tests/t_bas52/t_bas52.asm create mode 100644 tests/t_bas52/t_bas52.doc create mode 100644 tests/t_bas52/t_bas52.inc create mode 100644 tests/t_bas52/t_bas52.ori create mode 100644 tests/t_buf32/asflags create mode 100644 tests/t_buf32/t_buf32.asm create mode 100644 tests/t_buf32/t_buf32.doc create mode 100644 tests/t_buf32/t_buf32.inc create mode 100644 tests/t_buf32/t_buf32.ori create mode 100644 tests/t_cop8/asflags create mode 100644 tests/t_cop8/t_cop8.asm create mode 100644 tests/t_cop8/t_cop8.doc create mode 100644 tests/t_cop8/t_cop8.ori create mode 100644 tests/t_f2mc8l/asflags create mode 100644 tests/t_f2mc8l/t_f2mc8l.asm create mode 100644 tests/t_f2mc8l/t_f2mc8l.doc create mode 100644 tests/t_f2mc8l/t_f2mc8l.ori create mode 100644 tests/t_fl90/asflags create mode 100644 tests/t_fl90/cpu_time.inc create mode 100644 tests/t_fl90/float.inc create mode 100644 tests/t_fl90/macros.inc create mode 100644 tests/t_fl90/mon.inc create mode 100644 tests/t_fl90/t_fl90.asm create mode 100644 tests/t_fl90/t_fl90.doc create mode 100644 tests/t_fl90/t_fl90.ori create mode 100644 tests/t_fl900/asflags create mode 100644 tests/t_fl900/conout.inc create mode 100644 tests/t_fl900/cpu_time.inc create mode 100644 tests/t_fl900/float.inc create mode 100644 tests/t_fl900/macros.inc create mode 100644 tests/t_fl900/t_fl900.asm create mode 100644 tests/t_fl900/t_fl900.doc create mode 100644 tests/t_fl900/t_fl900.inc create mode 100755 tests/t_fl900/t_fl900.ori create mode 100644 tests/t_full09/asflags create mode 100644 tests/t_full09/t_full09.asm create mode 100644 tests/t_full09/t_full09.doc create mode 100644 tests/t_full09/t_full09.ori create mode 100644 tests/t_h8_3/asflags create mode 100644 tests/t_h8_3/t_h8_3.asm create mode 100644 tests/t_h8_3/t_h8_3.doc create mode 100644 tests/t_h8_3/t_h8_3.ori create mode 100644 tests/t_h8_5/asflags create mode 100644 tests/t_h8_5/t_h8_5.asm create mode 100644 tests/t_h8_5/t_h8_5.doc create mode 100644 tests/t_h8_5/t_h8_5.ori create mode 100644 tests/t_m16c/asflags create mode 100644 tests/t_m16c/t_m16c.asm create mode 100644 tests/t_m16c/t_m16c.doc create mode 100644 tests/t_m16c/t_m16c.ori create mode 100644 tests/t_mcore/asflags create mode 100644 tests/t_mcore/t_mcore.asm create mode 100644 tests/t_mcore/t_mcore.doc create mode 100644 tests/t_mcore/t_mcore.ori create mode 100644 tests/t_mic51/DEBUG.ASM create mode 100644 tests/t_mic51/MAKRO1.ASM create mode 100644 tests/t_mic51/MEM1.ASM create mode 100644 tests/t_mic51/RUN1.ASM create mode 100644 tests/t_mic51/TAST1.ASM create mode 100644 tests/t_mic51/TEACH1.ASM create mode 100644 tests/t_mic51/asflags create mode 100644 tests/t_mic51/defKey.inc create mode 100644 tests/t_mic51/defModul.inc create mode 100644 tests/t_mic51/defMsg.inc create mode 100644 tests/t_mic51/defParam.inc create mode 100644 tests/t_mic51/defgequ.inc create mode 100644 tests/t_mic51/defint.inc create mode 100644 tests/t_mic51/defmacro.inc create mode 100644 tests/t_mic51/net_lcd.inc create mode 100644 tests/t_mic51/t_mic51.asm create mode 100644 tests/t_mic51/t_mic51.doc create mode 100644 tests/t_mic51/t_mic51.inc create mode 100755 tests/t_mic51/t_mic51.ori create mode 100644 tests/t_mic51/t_mod1.asm create mode 100644 tests/t_msp/asflags create mode 100644 tests/t_msp/t_msp.asm create mode 100644 tests/t_msp/t_msp.doc create mode 100644 tests/t_msp/t_msp.ori create mode 100644 tests/t_parsys/asflags create mode 100644 tests/t_parsys/float.i68 create mode 100644 tests/t_parsys/float81.i68 create mode 100644 tests/t_parsys/parsys.i68 create mode 100644 tests/t_parsys/t_parsys.asm create mode 100644 tests/t_parsys/t_parsys.doc create mode 100644 tests/t_parsys/t_parsys.inc create mode 100644 tests/t_parsys/t_parsys.ori create mode 100644 tests/t_scmp/asflags create mode 100644 tests/t_scmp/t_scmp.asm create mode 100644 tests/t_scmp/t_scmp.doc create mode 100755 tests/t_scmp/t_scmp.ori create mode 100644 tests/t_secdrive/asflags create mode 120000 tests/t_secdrive/lowlevel.inc create mode 100644 tests/t_secdrive/secparam.inc create mode 100644 tests/t_secdrive/t_secdrive.asm create mode 100644 tests/t_secdrive/t_secdrive.doc create mode 100755 tests/t_secdrive/t_secdrive.ori create mode 100644 tests/t_secdrive/wd1002xt.inc create mode 100644 tests/t_secdrive/wd1003at.inc create mode 100644 tests/t_st6/asflags create mode 100755 tests/t_st6/t_st6.asm create mode 100644 tests/t_st6/t_st6.doc create mode 100755 tests/t_st6/t_st6.ori create mode 100644 tests/t_st7/asflags create mode 100644 tests/t_st7/t_st7.asm create mode 100644 tests/t_st7/t_st7.doc create mode 100644 tests/t_st7/t_st7.ori create mode 100644 tests/t_st9/asflags create mode 100644 tests/t_st9/t_st9.asm create mode 100644 tests/t_st9/t_st9.doc create mode 100755 tests/t_st9/t_st9.ori create mode 100644 tests/t_tms7/asflags create mode 100755 tests/t_tms7/t_tms7.asm create mode 100644 tests/t_tms7/t_tms7.doc create mode 100755 tests/t_tms7/t_tms7.ori create mode 100644 tests/t_xa/asflags create mode 100644 tests/t_xa/t_xa.asm create mode 100644 tests/t_xa/t_xa.doc create mode 100644 tests/t_xa/t_xa.ori create mode 100644 tests/t_z380/asflags create mode 100644 tests/t_z380/t_z380.asm create mode 100644 tests/t_z380/t_z380.doc create mode 100644 tests/t_z380/t_z380.ori create mode 100644 tests/t_z8/asflags create mode 100644 tests/t_z8/t_z8.asm create mode 100644 tests/t_z8/t_z8.doc create mode 100644 tests/t_z8/t_z8.ori create mode 100755 tests/testall create mode 100644 tests/testall.bat create mode 100644 tests/testall.cmd create mode 100644 tests/warnlog.DE create mode 100644 tests/warnlog.EN (limited to 'tests') diff --git a/tests/t_166/asflags b/tests/t_166/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_166/t_166.asm b/tests/t_166/t_166.asm new file mode 100644 index 0000000..d23a52b --- /dev/null +++ b/tests/t_166/t_166.asm @@ -0,0 +1,232 @@ + cpu 80c167 + page 0 + include reg166 + + diswdt + einit + idle + nop + pwrdn + ret + reti + rets + srst + srvwdt + +targ: jmpr targ + jmpr nz,targ + jmpr ult,targ + jmpr sgt,targ + jmpr nv,targ + jmpr net,targ + callr targ + + jmpa targ + jmpa nz,targ + jmpa ult,targ + jmpa sgt,targ + jmpa nv,targ + jmpa net,targ + calla 1234h + + jmps targ + jmps 1,2345h + calls targ + + jmpi [r3] + jmpi z,[r12] + calli nc,[r4] + + jmp 10000h + jmp 3ffffh + jmp 12345h + jmp 80h + jmp 2000h + jmp [r14] + + call 10000h + call 3ffffh + call 12345h + call z,80h + call sle,2000h + call nn,[r14] + + add 1234h,r10 + addb 2345h,0fe00h + addc r7,1234h + addcb 0fe02h,2345h + sub r12,#4 + subb r5,#200 + subc 0fe04h,#4 + subcb 0fe06h,#200 + cmp r5,r3 + cmpb rh0,rl0 + and r1,[r2] + andb r5,[r1] + or r3,[r3+] + xorb r15,[r0+] + + ashr r2,r4 + rol r5,#4 + ror r10,r1 + shl r3,#12 + shr r15,r0 + + band r2.5,r7.14 + bmov r3.7,0fd08h.5 + bmovn r7.10,0ff10h.12 + bcmp r7.14,r2.5 + bor 0fd08h.5,r3.7 + bxor 0ff10h.12,r7.10 + bset r5.2 + bclr 0ff80h.13 + bfldl r5,#0c3h,#3ch + bfldh 0fd02h,#0c3h,#3ch + + cmpd1 r5,#10 + cmpd2 r12,#200 + cmpi1 r9,Targ + cmpi2 r14,#(5*4)-7 + + cpl r5 + cplb rh1 + neg r12 + negb r10 + + div r3 + divl r7 + divu r10 + divlu r0 + +targ2: jb r5.2,targ2 + jbc 0fd30h.12,targ2 + jnb r7.14,targ2 + jnbs 0ff58h.2,targ2 + + mov r2,r5 + movb r0,rh5 + mov r4,#2 + movb r6,#10 + mov r12,#1234 + movb r0,#23h + mov r0,[r2] + movb rl4,[r10] + mov r3,[r4+] + movb r10,[r7+] + mov r1,[r1+300] + movb r10,[30+r4-40] + mov r12,Targ + movb rl2,targ2 + + mov 0fe00h,#10 + movb 0fe02h,#100 + mov 0fe04h,[r2] + movb 0fe06h,[r7] + mov 0fe08h,Targ + movb 0fe0ah,targ2 + mov [r4],r3 + movb [r7],rl5 + mov [r10],[r2] + movb [r14],[r0] + mov [r13],[r6+] + movb [r14],[r2+] + mov [r11],targ2 + movb [r15],Targ + mov [-r4],r2 + movb [-r15],rh7 + mov [r6+],[r13] + movb [r2+],[r14] + mov [r15+20],r4 + movb [r0-7],rh1 + mov targ2,[r7] + movb Targ,[r4] + mov Targ,0fe10h + movb targ2,0ff10h + + movbs r10,rh1 + movbs 0fe04h,targ2 + movbs targ2,0fe04h + movbz r11,rl1 + movbz 0fe08h,targ2 + movbz targ2,0fe40h + + mul r12,r15 + mulu r0,r7 + prior r2,r4 + + pcall r10,targ2 + pcall 0fe02h,8000h + + push r2 + pop 0ff20h + retp r14 + + scxt 0fe20h,#1234h + scxt r5,targ2 + + trap #10 + trap #127 + +;------------------------------- +; Pipeline-Tests + + mov dpp0,#4 + assume dpp0:4 + mov r0,12345h ; DPP0 noch nicht ver„nert + mov r0,12345h ; ab hier wieder gut + mov dpp0,#0 + assume dpp0:0 + + mov cp,0fc00h + mov r5,r3 ; gleich doppelt + movb r3,r1 + + mov sp,0fd00h ; SP noch in der Pipe + pop r4 + ret + +;------------------------------- +; Bit-Tests + + bset 123h +tbit bit 0ff80h.4 + +;------------------------------- + +Str equ "PSW+5" +tmp equ Val(Str) + +;------------------------------- +; Adressierungs-Tests + + atomic #2 + + extr #1 + mov 0f000h,#1234h + mov 0fe00h,#1234h + +ebit bit 0f100h.4 +sbit bit 0ff00h.4 + + extr #1 + bclr ebit + bclr sbit + + extr #1 + bset 0f1deh.12 + bset 0ffdeh.12 + + extp r5,#1 + mov r0,0abcdh + mov r0,0abcdh + + extpr #4,#1 + extp #4,#1 + mov r0,12345h + mov r0,12345h + + extsr #1,#1 + exts #1,#1 + mov r0,12345h + mov r0,12345h + diff --git a/tests/t_166/t_166.doc b/tests/t_166/t_166.doc new file mode 100644 index 0000000..a21d1c6 --- /dev/null +++ b/tests/t_166/t_166.doc @@ -0,0 +1,5 @@ ++-------------------------- Test Application 166 ----------------------------+ +| | +| This is a (synthetic) test of the 80C166 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_166/t_166.ori b/tests/t_166/t_166.ori new file mode 100644 index 0000000..0fbb6db Binary files /dev/null and b/tests/t_166/t_166.ori differ diff --git a/tests/t_16c5x/asflags b/tests/t_16c5x/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_16c5x/t_16c5x.asm b/tests/t_16c5x/t_16c5x.asm new file mode 100755 index 0000000..805013f --- /dev/null +++ b/tests/t_16c5x/t_16c5x.asm @@ -0,0 +1,45 @@ + cpu 16c57 + page 0 + relaxed on + + clrw + nop + option + sleep + + andlw 12h + iorlw 12h + movlw 12h + retlw 12h + xorlw 12h + + addwf 12h + andwf 12h,0 + comf 12h,1 + decf 12h,w + decfsz 12h,f + incf 12h + incfsz 12h,0 + iorwf 12h,1 + movf 12h,w + rlf 12h,f + rrf 12h + subwf 12h,0 + swapf 12h,1 + xorwf 12h,w + + bcf 10h,3 + bsf 17h,5 + btfsc 12h,7 + btfss 08h,1 + + clrf 12h + movwf 12h + + tris 5 + tris 6 + tris 7 + + call 234h + goto 123h + diff --git a/tests/t_16c5x/t_16c5x.doc b/tests/t_16c5x/t_16c5x.doc new file mode 100644 index 0000000..e75d915 --- /dev/null +++ b/tests/t_16c5x/t_16c5x.doc @@ -0,0 +1,5 @@ ++----------------------- Test Application 16C5x ----------------------------+ +| | +| This is a (synthetic) test of the PIC 16C5x code generator | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_16c5x/t_16c5x.ori b/tests/t_16c5x/t_16c5x.ori new file mode 100755 index 0000000..03a128c Binary files /dev/null and b/tests/t_16c5x/t_16c5x.ori differ diff --git a/tests/t_16c84/asflags b/tests/t_16c84/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_16c84/t_16c84.asm b/tests/t_16c84/t_16c84.asm new file mode 100644 index 0000000..e5b2ed4 --- /dev/null +++ b/tests/t_16c84/t_16c84.asm @@ -0,0 +1,53 @@ + cpu 16c84 + + clrw + nop + clrwdt + retfie + return + sleep + option + + addlw 1 + andlw 100 + iorlw $55 + movlw %10101010 + retlw 0 + sublw 300-400 + xorlw 186 + + addwf 3,f + addwf 4,w + addwf 5 + addwf 6,0 + addwf 7,1 + andwf 8 + comf 9,f + comf 10,w + comf 11 + comf 12,0 + comf 13,1 + decf 14 + decfsz 15 + incf 16 + incfsz 17 + iorwf 18 + movf 19 + rlf 20 + rrf 21 + subwf 22 + swapf 23 + xorwf 24 + + bcf 17,4 + bsf 500,6 + btfsc 23,3 + btfss 20,0 + + clrf 20 + movwf 33 + + tris 6 + + call $200 + goto $300 diff --git a/tests/t_16c84/t_16c84.doc b/tests/t_16c84/t_16c84.doc new file mode 100644 index 0000000..999b8bd --- /dev/null +++ b/tests/t_16c84/t_16c84.doc @@ -0,0 +1,5 @@ ++----------------------- Test Application 16C84 ----------------------------+ +| | +| This is a (synthetic) test of the PIC 16C8x code generator | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_16c84/t_16c84.ori b/tests/t_16c84/t_16c84.ori new file mode 100644 index 0000000..1c6741a Binary files /dev/null and b/tests/t_16c84/t_16c84.ori differ diff --git a/tests/t_17c42/asflags b/tests/t_17c42/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_17c42/t_17c42.asm b/tests/t_17c42/t_17c42.asm new file mode 100644 index 0000000..a74fb9c --- /dev/null +++ b/tests/t_17c42/t_17c42.asm @@ -0,0 +1,66 @@ + cpu 17c42 + relaxed on + + retfie + return + clrwdt + nop + sleep + + movlb 12h + addlw 12h + andlw 12h + iorlw 12h + movlw 12h + sublw 12h + xorlw 12h + retlw 12h + + addwf 12h,0 + addwfc 12h,1 + andwf 12h,w + clrf 12h,f + comf 12h + daw 12h,0 + decf 12h,1 + incf 12h,w + iorwf 12h,f + negw 12h + rlcf 12h,0 + rlncf 12h,1 + rrcf 12h,w + rrncf 12h,f + setf 12h + subwf 12h,0 + subwfb 12h,1 + swapf 12h,w + xorwf 12h,f + decfsz 12h + dcfsnz 12h,0 + incfsz 12h,1 + infsnz 12h,w + + bcf 12h,1 + bsf 12h,3 + btfsc 12h,5 + btfss 12h,7 + btg 12h,1 + + movwf 12h + cpfseq 12h + cpfsgt 12h + tstfsz 12h + + movfp 34h,12h + movpf 12h,34h + + tablrd 1,1,12h + tablwt 1,1,12h + + tlrd 1,12h + tlwt 1,12h + + call 1234h + goto 1234h + lcall 0fedch + diff --git a/tests/t_17c42/t_17c42.doc b/tests/t_17c42/t_17c42.doc new file mode 100644 index 0000000..22221cc --- /dev/null +++ b/tests/t_17c42/t_17c42.doc @@ -0,0 +1,5 @@ ++----------------------- Test Application 17C42 ----------------------------+ +| | +| This is a (synthetic) test of the PIC 17C42 code generator | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_17c42/t_17c42.ori b/tests/t_17c42/t_17c42.ori new file mode 100644 index 0000000..1db73f8 Binary files /dev/null and b/tests/t_17c42/t_17c42.ori differ diff --git a/tests/t_251/asflags b/tests/t_251/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_251/t_251.asm b/tests/t_251/t_251.asm new file mode 100644 index 0000000..2002ac9 --- /dev/null +++ b/tests/t_251/t_251.asm @@ -0,0 +1,399 @@ + cpu 80c251 + include reg251 + + page 0 + + org 0ff0000h + +data equ 30h +;acc equ 0eeh +Bit1 bit 21h.7 +Bit2 bit s:90h.4 +Bit3 bit data.5 +Bit4 bit acc.3 +Bit5 bit Bit3 + + acall Targ + ajmp Targ + + lcall Targ + lcall @wr4 + ljmp Targ + ljmp @wr2 + + ecall Targ + ecall @dpx + ejmp Targ + ejmp @dr16 + + sjmp Targ + jc Targ + jnc Targ + jnz Targ + jz Targ + je Targ + jsle Targ + jle Targ + jne Targ + jsg Targ + jsge Targ + jsl Targ + jsle Targ + + jmp @a+dptr + jmp @wr2 + jmp @dr16 + jmp Targ + jmp Targ+4000h + jmp 4000h + call @wr4 + call @dpx + call Targ + call Targ+4000h + + jb Bit1,Targ + jbc Bit2,Targ + jnb Bit4,Targ + jb Bit3,Targ + jnb s:91h.4,Targ + jbc 44h.5,Targ + + djnz r5,Targ + djnz acc,Targ + djnz data,Targ + + cjne a,data,Targ + cjne a,#'A',Targ + cjne r6,#50,Targ + cjne @r1,#40h,Targ + +Targ: + + add a,#12h + add a,data + add a,1234h + add a,@r1 + add a,@wr2 + add a,@dr8 + add a,r4 + add a,a + add a,r13 + add r3,r12 + add wr8,wr12 + add dr20,dpx + add r4,#23h + add r11,#23h + add wr4,#1234h + add dr4,#1234h + add r8,data + add r11,data + add wr8,data + add r8,1234h + add wr8,55ah + add r11,@r1 + add r2,@wr6 + add r6,@dr12 + + sub a,r7 + sub wr4,wr10 + sub dr12,dr28 + sub r4,#10 + sub wr6,#1000 + sub dr16,#05aa5h + sub a,data + sub wr8,data + sub r12,1243h + sub wr10,1342h + sub r3,@wr14 + sub a,@spx + + cmp a,r7 + cmp wr4,wr10 + cmp dr12,dr28 + cmp r4,#10 + cmp wr6,#1000 + cmp dr16,#05aa5h + cmp dr16,#-3 + cmp a,data + cmp wr8,data + cmp r12,1243h + cmp wr10,1342h + cmp r3,@wr14 + cmp a,@spx + + addc a,r6 + addc r11,@r0 + addc a,data + addc a,#20h + subb a,r6 + subb r11,@r0 + subb a,data + subb a,#20h + + anl c,Bit1 + anl cy,Bit3 + anl c,/Bit1 + anl cy,/Bit3 + orl c,Bit1 + orl cy,Bit3 + orl c,/Bit1 + orl cy,/Bit3 + + anl data,a + anl data,r11 + anl data,#10001111b + anl a,#20h + anl a,acc + anl a,90h + anl a,s:90h + anl a,@r1 + anl a,@wr10 + anl a,@dr12 + anl a,r4 + anl a,r10 + anl a,a + anl r10,r4 + anl wr10,wr6 + anl r10,#55h + anl r11,#0aah + anl wr14,#1000100010001001b + anl r1,data + anl r11,data + anl wr4,data + anl r10,1234h + anl wr2,1234h + anl r11,@r1 + anl r6,@wr14 + anl r7,@dr16 + + orl data,a + orl data,r11 + orl data,#10001111b + orl a,#20h + orl a,acc + orl a,90h + orl a,s:90h + orl a,@r1 + orl a,@wr10 + orl a,@dr12 + orl a,r4 + orl a,r10 + orl a,a + orl r10,r4 + orl wr10,wr6 + orl r10,#55h + orl r11,#0aah + orl wr14,#1000100010001001b + orl r1,data + orl r11,data + orl wr4,data + orl r10,1234h + orl wr2,1234h + orl r11,@r1 + orl r6,@wr14 + orl r7,@dr16 + + xrl data,a + xrl data,r11 + xrl data,#10001111b + xrl a,#20h + xrl a,acc + xrl a,90h + xrl a,s:90h + xrl a,@r1 + xrl a,@wr10 + xrl a,@dr12 + xrl a,r4 + xrl a,r10 + xrl a,a + xrl r10,r4 + xrl wr10,wr6 + xrl r10,#55h + xrl r11,#0aah + xrl wr14,#1000100010001001b + xrl r1,data + xrl r11,data + xrl wr4,data + xrl r10,1234h + xrl wr2,1234h + xrl r11,@r1 + xrl r6,@wr14 + xrl r7,@dr16 + + + clr a + clr c + clr Bit1 + clr s:92h.6 + + cpl a + cpl c + cpl Bit1 + cpl s:92h.6 + + setb c + setb Bit1 + setb s:92h.6 + + dec a + dec data + dec @r1 + dec r5,#1 + dec r10 + dec r11,#1 + dec a,#2 + dec r11,#4 + dec wr2,#2 + dec spx,#4 + + inc a + inc data + inc @r1 + inc r5,#1 + inc r10 + inc r11,#1 + inc a,#2 + inc r11,#4 + inc wr2,#2 + inc spx,#4 + inc dptr + + mul ab + mul r5,r7 + mul wr10,wr14 + + div ab + div r5,r7 + div wr10,wr14 + + mov a,#10 + mov acc,#20 + mov @r1,#30 + mov r4,#40 + mov data,acc + mov s:90h,@r1 + mov 70h,r6 + mov @r1,data + mov r5,data + mov a,acc + mov a,@r1 + mov a,r2 + mov acc,a + mov @r1,a + mov r4,a + mov a,r12 + mov r12,a + mov r11,r5 + mov r5,r11 + mov r10,r6 + mov wr4,wr10 + mov dr12,dpx + mov r11,#50 + mov r7,#60 + mov r14,#70 + mov wr12,#8090 + mov dr12,#8090 + mov dr12,#-100 + mov r11,data + mov r4,data + mov r15,data + mov wr10,acc + mov dr16,s:0a0h + mov a,1234h + mov r10,1234h + mov wr14,1234h + mov dr20,1243h + mov a,@wr10 + mov r2,@wr10 + mov a,@dr12 + mov r4,@dr12 + mov wr10,@wr12 + mov wr10,@dr12 + mov data,r11 + mov data,r5 + mov data,r8 + mov data,wr2 + mov data,spx + mov 1234h,a + mov 1234h,r5 + mov 1234h,wr8 + mov 1234h,dr16 + mov @wr14,a + mov @wr14,r9 + mov @dr12,a + mov @dr12,r8 + mov @wr14,wr18 + mov @dr8,wr18 + mov a,@wr2+10 + mov r4,@wr2-20 + mov wr10,@wr2+30 + mov a,@dpx-40 + mov r8,@dpx+50 + mov wr10,@dpx-60 + mov @wr2+10,a + mov @wr2-20,r4 + mov @wr2+30,wr10 + mov @dpx-40,a + mov @dpx+50,r8 + mov @dpx-60,wr10 + mov dptr,#1234h + + movc a,@a+dptr + movc a,@a+pc + + movh dr12,#55aah + + movs wr10,a + movz wr12,r12 + + movx a,@dptr + movx a,@r1 + movx @dptr,a + movx @r0,r11 + + pop data + pop acc + pop a + pop r5 + pop wr8 + pop dr20 + push data + push acc + push a + push r5 + push wr8 + push dr20 + push #20 + pushw #55aah + + xch a,r5 + xch a,data + xch a,@r1 + xch r5,r11 + xch data,a + xch @r1,a + xchd a,@r1 + xchd @r1,r11 + + nop + ret + reti + eret + trap + + da a + rl a + rlc a + rr a + rrc a + swap r11 + + sll a + sll r6 + sll wr12 + sra a + sra r6 + sra wr12 + srl a + srl r6 + srl wr12 diff --git a/tests/t_251/t_251.doc b/tests/t_251/t_251.doc new file mode 100644 index 0000000..e2b4505 --- /dev/null +++ b/tests/t_251/t_251.doc @@ -0,0 +1,5 @@ ++----------------------- Test Application 251 ----------------------------+ +| | +| This is a (synthetic) test of the MCS-251 code generator | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_251/t_251.ori b/tests/t_251/t_251.ori new file mode 100644 index 0000000..ecd8c4c Binary files /dev/null and b/tests/t_251/t_251.ori differ diff --git a/tests/t_296/asflags b/tests/t_296/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_296/t_296.asm b/tests/t_296/t_296.asm new file mode 100644 index 0000000..27cdb60 --- /dev/null +++ b/tests/t_296/t_296.asm @@ -0,0 +1,132 @@ + cpu 80296 + +ax equ 40 +al equ ax +ah equ al+1 +bx equ 42 +cx equ 44 +dx equ 46 + + reti + + eld ax,[bx] + eld ax,0[bx] + eld ax,100[bx] ; nur 24-Bit-Displacement + eld ax,1000[bx] + eld ax,100000[bx] + eld ax,-100[bx] + eld ax,-1000[bx] + eld ax,-100000[bx] + eld ax,123456h + + eldb al,[bx] + eldb al,0[bx] + eldb al,100[bx] ; nur 24-Bit-Displacement + eldb al,1000[bx] + eldb al,100000[bx] + eldb al,-100[bx] + eldb al,-1000[bx] + eldb al,-100000[bx] + eldb al,123456h + + est ax,[bx] + est ax,0[bx] + est ax,100[bx] ; nur 24-Bit-Displacement + est ax,1000[bx] + est ax,100000[bx] + est ax,-100[bx] + est ax,-1000[bx] + est ax,-100000[bx] + est ax,123456h + + estb al,[bx] + estb al,0[bx] + estb al,100[bx] ; nur 24-Bit-Displacement + estb al,1000[bx] + estb al,100000[bx] + estb al,-100[bx] + estb al,-1000[bx] + estb al,-100000[bx] + estb al,123456h + + ecall $+123456h + ejmp $-10h + ebr [bx] + + ebmovi cx,ax + + mac #12h + mac ax,#12h + + macr bx + macr ax,bx + + macrz 10[bx] + macrz ax,10[bx] + + macz -1000[bx] + macz ax,-1000[bx] + + smac [cx] + smac ax,[cx] + + smacr [cx]+ + smacr ax,[cx]+ + + smacrz 1000h + smacrz ax,1000h + + smacz 0ffc0h + smacz ax,0ffc0h + + msac ax,#20 + + mvac cx,al + + rpt ax + rptnst #10 + rptnh [cx] + rptgt [cx]+ + rptnc ax + rptnvt #10 + rptnv [cx] + rptge [cx]+ + rptne ax + rptst #10 + rpth [cx] + rptle [cx]+ + rptc ax + rptvt #10 + rptv [cx] + rptlt [cx]+ + rpte ax + rpti #10 + rptinst [cx] + rptinh [cx]+ + rptigt ax + rptinc #10 + rptinvt [cx] + rptinv [cx]+ + rptige ax + rptine #10 + rptist [cx] + rptih [cx]+ + rptile ax + rptic #10 + rptivt [cx] + rptiv [cx]+ + rptilt ax + rptie #10 + + assume wsr:3eh ; 1f80h...1fbfh --> 0c0h...0ffh + assume wsr1:9eh ; 0f780h...0f7bfh --> 40h..7fh + + ld ax,3eh ; normal + ld ax,44h ; muß absolut werden + ld ax,92h ; wieder normal + ld ax,0d0h ; muß wieder absolut werden + ld ax,1000h ; muß absolut bleiben + ld ax,1f90h ; mit WSR + ld ax,2000h ; muß wieder absolut bleiben + ld ax,0f7a0h ; mit WSR1 + ld ax,0fffeh ; muß wieder absolut bleiben diff --git a/tests/t_296/t_296.doc b/tests/t_296/t_296.doc new file mode 100644 index 0000000..da5b3ba --- /dev/null +++ b/tests/t_296/t_296.doc @@ -0,0 +1,6 @@ ++------------------------- Test Application 296 -----------------------------+ +| | +| This is a (synthetic) test of the 80196Nx/80296's instruction set | +| extensions | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_296/t_296.ori b/tests/t_296/t_296.ori new file mode 100755 index 0000000..b4fe458 Binary files /dev/null and b/tests/t_296/t_296.ori differ diff --git a/tests/t_29k/asflags b/tests/t_29k/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_29k/t_29k.asm b/tests/t_29k/t_29k.asm new file mode 100644 index 0000000..303a6af --- /dev/null +++ b/tests/t_29k/t_29k.asm @@ -0,0 +1,80 @@ + cpu AM29240 + emulated class,convert,sqrt + supmode on + + page 0 + relaxed on + + include reg29k + + add r128,r129,r130 + add r129,r130,131 + add r130,r131 + add r131,132 + ; andere Op's dito... + + dadd r132,r133,r134 + dadd r133,r134 + ; andere Op's dito + + aseq 134,r135,r136 + aseq 135,r136,137 + + call r136,$+0x048d0 + call r137,0x30000 + call r138,r139 + calli r139,r140 + jmp $ + jmpi r141 + jmpf r142,$ + jmpfi r143,r144 + jmpfdec r144,$ + jmpt r145,$ + jmpti r146,r147 + + load 0,27,r160,r161 + loadl 27,r161,r162 + loadm 27,r162,163 + loadset 13,r163,r164 + store 13,r164,165 + storel 13,r165,r166 + storem 7,r166,167 + + class r147,r148,2 + sqrt r147,r148,2 + sqrt r149,2 + + clz r148,r149 + clz r149,150 + + const r150,151 + const r151,-152 + const r152,0x153154 + consth r153,500 + constn r154,0xffff1234 + constn r155,-5 + constn r156,0123 + + convert r157,r158,1,2,2,1 + exhws r158,r159 + + halt + iret + + inv + iretinv 2 + + emulate 20,lr10,lr11 + + mfsr r148,lru + mtsr ipc,r148 + mtsrim lru,0xa55a + mftlb r159,r160 + mttlb r160,r161 + + add lr122,lr110,0 + addc gr10,gr30 + + add gr20,gr40,gr60 + assume rbp:0b0000000000000010 + add gr20,gr40,gr60 diff --git a/tests/t_29k/t_29k.doc b/tests/t_29k/t_29k.doc new file mode 100644 index 0000000..a0ccad8 --- /dev/null +++ b/tests/t_29k/t_29k.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 29K -----------------------------+ +| | +| This is a (synthetic) test of the AM29K instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_29k/t_29k.ori b/tests/t_29k/t_29k.ori new file mode 100644 index 0000000..c878f69 Binary files /dev/null and b/tests/t_29k/t_29k.ori differ diff --git a/tests/t_32/asflags b/tests/t_32/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_32/t_32.asm b/tests/t_32/t_32.asm new file mode 100644 index 0000000..d7738e5 --- /dev/null +++ b/tests/t_32/t_32.asm @@ -0,0 +1,39 @@ + cpu 68340 + supmode on + include reg683xx.inc + page 0 + + lpstop #$55aa + + link a6,#10 + link.l a6,#10 + + bgnd + +Test1 tbls.b (a4),d5 +Test2: tbls.w 30(a6),d1 + Test3: tbls.l 20(a4,d5*1),d6 + Test4: tblsn.b (a4),d5 + tblsn.w 30(a6),d1 + tblsn.l 20(a4,d5*1),d6 + tblu.b (a4),d5 + tblu.w 30(a6),d1 + tblu.l 20(a4,d5*1),d6 + tblun.b (a4),d5 + tblun.w 30(a6),d1 + tblun.l 20(a4,d5*1),d6 + + tbls.b d1:d2,d3 + tbls.w d2:d3,d4 + tbls.l d3:d4,d5 + tblsn.b d1:d2,d3 + tblsn.w d2:d3,d4 + tblsn.l d3:d4,d5 + tblu.b d1:d2,d3 + tblu.w d2:d3,d4 + tblu.l d3:d4,d5 + tblun.b d1:d2,d3 + tblun.w d2:d3,d4 + tblun.l d3:d4,d5 + + move.l (d0.l),d0 diff --git a/tests/t_32/t_32.doc b/tests/t_32/t_32.doc new file mode 100644 index 0000000..e069ffe --- /dev/null +++ b/tests/t_32/t_32.doc @@ -0,0 +1,6 @@ ++-------------------------- Test Application 32 -----------------------------+ +| | +| This is a (synthetic) test of the CPU32's extensions to the 680x0 | +| basic instruction set. | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_32/t_32.ori b/tests/t_32/t_32.ori new file mode 100644 index 0000000..1413840 Binary files /dev/null and b/tests/t_32/t_32.ori differ diff --git a/tests/t_3201x/asflags b/tests/t_3201x/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_3201x/t_3201x.asm b/tests/t_3201x/t_3201x.asm new file mode 100644 index 0000000..f07148f --- /dev/null +++ b/tests/t_3201x/t_3201x.asm @@ -0,0 +1,74 @@ + cpu 32015 + + abs + apac + cala + dint + eint + nop + pac + pop + push + ret + rovm + sovm + spac + zac + + b 345h + banz 345h + bgez 345h + bgz 345h + bioz 345h + blez 345h + blz 345h + bnz 345h + bv 345h + bz 345h + call 345h + + addh *,ar1 + adds *-,ar0 + and *+,ar1 + dmov *,1 + ldp *-,0 + lst *+,1 + lt dat123 + lta dat45 + ltd 12h + mar *,ar1 + mpy *-,ar0 + or *+,ar1 + sst *,1 + subc *-,0 + subh *+,1 + subs dat123 + tblr dat45 + tblw 12h + xor *,ar1 + zalh *-,ar0 + zals *+,ar1 + + add *+,4,ar0 + lac *+,ar0 + sach 12h,4 + sacl 12h + sub 12h,6 + + lack 12h + ldpk 1 + mpyk 123h + + in *,2,ar1 + in 45h,4 + out *,2,ar1 + out 45h,4 + + larp ar1 + larp 1 + + lar ar1,12h + sar 1,*,ar0 + + lark ar1,12h + diff --git a/tests/t_3201x/t_3201x.doc b/tests/t_3201x/t_3201x.doc new file mode 100644 index 0000000..6fc74f1 --- /dev/null +++ b/tests/t_3201x/t_3201x.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 3201x ---------------------------+ +| | +| This is a (synthetic) test of the TMS3201x instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_3201x/t_3201x.ori b/tests/t_3201x/t_3201x.ori new file mode 100644 index 0000000..4b0cfb6 Binary files /dev/null and b/tests/t_3201x/t_3201x.ori differ diff --git a/tests/t_3203x/asflags b/tests/t_3203x/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_3203x/t_3203x.asm b/tests/t_3203x/t_3203x.asm new file mode 100644 index 0000000..d6b35ef --- /dev/null +++ b/tests/t_3203x/t_3203x.asm @@ -0,0 +1,271 @@ + cpu 320C30 + relaxed on + page 0 + + org $123456 + +targ: br targ + brd targ + call targ + + bu r0 + bud r0 + bu targ + bud targ + blo ar1 + blsd targ + bhi ir0 + bhs targ + beqd ar4 + bne targ + blt targ + ble r10 + bgtd targ + bge r6 + bzd targ + bnz ar5 + bpd targ + bn targ + bnnd ar3 + bnv targ + bv ar7 + bnufd ir1 + buf targ + bnc ar2 + bcd iof + bnlv targ + blv targ + bnluf targ + bluf targ + bzuf targ + b targ + + callne r4 + callnluf targ + + dbne ar1,r5 + dbn ar5,targ + dbud ar2,ar7 + dbzufd ar6,targ + db ar7,targ + + retine + retsnc + retsu + rets + + trapu 7 + trapuf 2 + + swi + sigi + idle + + rol r4 + rolc ar2 + ror sp + rorc r20 + + rptb targ + + nop ar2 + nop *+ar3(2) + nop *-ar4(200) + nop *++ar5(30) + nop *--ar6 + nop *ar5++(20) + nop *ar1--(12h) + nop *ar7++($56)% + nop *ar0--(0x10)% + nop *+ar6(ir0) + nop *-ar4(ir0) + nop *++ar2(ir0) + nop *--ar2(ir0) + nop *ar2++(ir0) + nop *ar2--(ir0) + nop *ar2++(ir0)% + nop *ar2--(ir0)% + nop *+ar6(ir1) + nop *-ar4(ir1) + nop *++ar2(ir1) + nop *--ar2(ir1) + nop *ar2++(ir1) + nop *ar2--(ir1) + nop *ar2++(ir1)% + nop *ar2--(ir1)% + nop *ar4 + nop *ar3(100-$64) + nop *ar1++(ir0)B + iack *ar5 + rpts ar5 + + absf r4 + absf ar2,r5 + absf @$1300,r7 + absf *ar4++,r3 + absf 200,r5 + + absi r4 + absi ar2,r5 + absi @$1300,r7 + absi *ar4++,r3 + absi 200,r5 + ; + addc ar2,r5 + addc @$1300,r7 + addc *ar4++,r3 + addc 200,r5 + + addc3 *ar1++(1),*ar2,r5 + addc3 *-ar3,r5,r2 + addc3 r6,*ar4++,r3 + addc3 r1,r2,r3 + + stf r4,@2000h + stf r6,*ar5 + + tstb3 r5,*ar3++ + + absf *ar4++,r6 +|| stf r6,*ar5++ + + sti r5,*ar3 +|| absi *ar4++%,r1 + + addf3 *ar4++,r5,r7 +|| stf r3,*ar5++ + + sti r3,*ar5++ +|| addi3 *ar4++,r5,r7 + + mpyi3 *ar4,*ar5,r1 +|| subi3 r6,r7,r3 + + subi3 *ar4,r6,r3 +|| mpyi3 *ar5,r7,r1 + + mpyi3 r7,*ar5,r1 +|| subi3 *ar4,r6,r3 + + mpyi3 *ar5,r7,r1 +|| subi3 r6,*ar4,r3 + + mpyi3 r7,*ar5,r1 +|| subi3 r6,*ar4,r3 + + mpyi3 r6,r7,r1 +|| subi3 *ar5,*ar4,r3 + + absf *++ar3(ir1) ,r4 +|| stf r4,*-ar7(1) + + absi *-ar5(1),r5 +|| sti r1,*ar2--(ir1) + + addf3 *+ar3(ir1),r2,r5 +|| stf r4,*ar2 + + addi3 *ar0--(ir0),r5,r0 +|| sti r3,*ar7 + + and3 *+ar1(ir0),r4,r7 +|| sti r3,*ar2 + + ash3 r1,*ar6++(ir1),r0 +|| sti r5,*ar2 + + fix *++ar4(1),r1 +|| sti r0,*ar2 + + float *+ar2(ir0),r6 +|| stf r7,*ar1 + + ldf *--ar1(ir0),r7 +|| ldf *ar7++(1),r3 + + ldf *ar2--(1),r1 +|| stf r3,*ar4++(ir1) + + ldi *-ar1(1),r7 +|| ldi *ar7++(ir0),r1 + + ldi *-ar1(1),r2 +|| sti r7,*ar5++(ir0) + + lsh3 r7,*ar2--(1),r2 +|| sti r0,*+ar0(1) + + mpyf3 *ar5++(1),*--ar1(ir0),r0 +|| addf3 r5,r7,r3 + + mpyf3 *-ar2(1),r7,r0 +|| stf r3,*ar0--(ir0) + + mpyf3 r5,*++ar7(ir1),r0 +|| subf3 r7,*ar3--(1),r2 + + mpyi3 r7,r4,r0 +|| addi3 *-ar3,*ar5--(1),r3 + + mpyi3 *++ar0(1),r5,r7 +|| sti r2,*-ar3(1) + + mpyi3 r2,*++ar0(1),r0 +|| subi3 *ar5--(ir1),r4,r2 + + negf *ar4--(1),r7 +|| stf r2,*++ar5(1) + + negi *-ar3,r2 +|| sti r2,*ar1++ + + not *+ar2,r3 +|| sti r7,*--ar4(ir1) + + or3 *++ar2,r5,r2 +|| sti r6,*ar1-- + + stf r4,*ar3-- +|| stf r3,*++ar5 + + sti r0,*++ar2(ir0) +|| sti r5,*ar0 + + subf3 r1,*-ar4(ir1),r0 +|| stf r7,*+ar5(ir0) + + subi3 r7,*+ar2(ir0),r1 +|| sti r3,*++ar7 + + xor3 *ar1++,r3,r3 +|| sti r6,*-ar2(ir0) + + xor3 *ar1++,r3,r3 + ||sti r6,*-ar2(ir0) + + ldfz r3,r5 + ldfzuf 20h,r6 + ldiz r4,r6 + ldp @123456h,dp + + pop r3 + popf r4 + push r6 + pushf r2 + + ldfz 1.27578125e+01,r4 + + ldi *ar5,r6 + ||ldi *ar5++,r6 + + addf3 *ar5++,*ar5++,r3 + + single 1.79750e+02 + single -6.281250e+01 + single -9.90337307e+27 + single 9.90337307e+27 + single -6.118750e+01, 1.79750e+02 + extended 9.90337307e+27 + bss 20h + word 20,55,'ABCD' + data 12345h,-1.2345e6,"Hello world" diff --git a/tests/t_3203x/t_3203x.doc b/tests/t_3203x/t_3203x.doc new file mode 100644 index 0000000..618d68b --- /dev/null +++ b/tests/t_3203x/t_3203x.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 3203x ---------------------------+ +| | +| This is a (synthetic) test of the TMS320C3x instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_3203x/t_3203x.ori b/tests/t_3203x/t_3203x.ori new file mode 100755 index 0000000..7874442 Binary files /dev/null and b/tests/t_3203x/t_3203x.ori differ diff --git a/tests/t_3205x/asflags b/tests/t_3205x/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_3205x/t_3205x.asm b/tests/t_3205x/t_3205x.asm new file mode 100644 index 0000000..7ae84a6 --- /dev/null +++ b/tests/t_3205x/t_3205x.asm @@ -0,0 +1,499 @@ +;------------------------------------ +; C20x subset + + cpu 320c203 + page 0 + + abs + + add #25 + add #2255 + add #25,0 + add #25,1 + add #2255,1 + add 123 + add 123,3 + add 123,16 + add * + add *,3 + add *,16 + add *,0,AR2 + add *,3,AR2 + add *,16,AR2 + + addc 123 + addc * + addc *,ar2 + + adds 123 + adds * + adds *,ar2 + + addt 123 + addt * + addt *,ar2 + + adrk #30 + + and 123 + and * + and *,ar2 + and #255 + and #255, 3 + and #255,16 + + apac + + b 1234h + b 1234h, * + b 1234h, *, ar2 + + bacc + + banz 1234h + banz 1234h, * + banz 1234h, *, ar2 + + bcnd 1234h, eq, c + + bit 123, 3 + bit *, 3 + bit *, 3, ar2 + + bitt 123 + bitt * + bitt *,ar2 + + bldd #10, 123 + bldd #10, * + bldd #10, *, ar2 + bldd 123, #10 + bldd *, #10 + bldd *, #10, ar2 + + blpd #1234h, 123 + blpd #1233h, *, ar2 + + cala + + call 1234h + call 1234h, * + call 1234h, *, ar2 + + cc 1234h, eq, c + + clrc c + clrc cnf + clrc intm + clrc ovm + clrc sxm + clrc tc + clrc xf + + cmpl + + cmpr 2 + + dmov 123 + dmov * + dmov *,ar2 + + idle + + in 123, 1234h + in *, 1234h + in *, 1234h, ar2 + + intr 4 + + lacc 123 + lacc 123, 16 + lacc * + lacc *, 16 + lacc *, 0, ar2 + lacc *, 16, ar2 + lacc #2 + lacc #2, 10 + + lacl 123 + lacl * + lacl *, ar2 + lacl #23 + + lact 123 + lact * + lact *, ar2 + + lar ar2, 123 + lar ar2, * + lar ar2, *, ar2 + lar ar2, #10 + lar ar2, #1000 + + ldp 123 + ldp * + ldp *, ar2 + ldp #40 + + lph 123 + lph * + lph *, ar2 + + lst #0, 123 + lst #0, * + lst #0, *, ar2 + + lst #1, 123 + lst #1, * + lst #1, *, ar2 + + lt 123 + lt * + lt *, ar2 + + lta 123 + lta * + lta *, ar2 + + ltd 123 + ltd * + ltd *, ar2 + + ltp 123 + ltp * + ltp *, ar2 + + lts 123 + lts * + lts *, ar2 + + mac 1234h, 123 + mac 1234h, * + mac 1234h, *, ar2 + + macd 1234h, 123 + macd 1234h, * + macd 1234h, *, ar2 + + mar 123 + mar * + mar *, ar2 + + mpy 123 + mpy * + mpy *, ar2 + mpy #300 + mpy #-300 + + mpya 123 + mpya * + mpya *, ar2 + + mpys 123 + mpys * + mpys *, ar2 + + mpyu 123 + mpyu * + mpyu *, ar2 + + neg + + nmi + + nop + + norm * + norm *, ar2 + + or 123 + or * + or *,ar2 + or #255 + or #255, 3 + or #255,16 + + out 123, 1234h + out *, 1234h + out *, 1234h, ar2 + + pac + + pop + + popd 123 + popd * + popd *, ar2 + + pshd 123 + pshd * + pshd *, ar2 + + push + + ret + + retc eq + + rol + + ror + + rpt #30 + rpt 123 + rpt * + rpt *, ar2 + + sach 123 + sach *, 0 + sach *, 2 + sach *, 0, ar2 + sach *, 2, ar2 + + sacl 123 + sacl *, 0 + sacl *, 2 + sacl *, 0, ar2 + sacl *, 2, ar2 + + sar ar3, 123 + sar ar3, * + sar ar3, *, ar2 + + sbrk #10 + + setc c + setc cnf + setc intm + setc ovm + setc sxm + setc tc + setc xf + + sfl + + sfr + + spac + + spl 123 + spl * + spl *, ar2 + + sph 123 + sph * + sph *, ar2 + + splk #1234, 123 + splk #1234, * + splk #1234, *, ar2 + + spm 2 + + sqra 123 + sqra * + sqra *, ar2 + + sqrs 123 + sqrs * + sqrs *, ar2 + + sst #0, 123 + sst #0, * + sst #0, *, ar2 + + sst #1, 123 + sst #1, * + sst #1, *, ar2 + + sub #25 + sub #2255 + sub #25,0 + sub #25,1 + sub #2255,1 + sub 123 + sub 123,3 + sub 123,16 + sub * + sub *,3 + sub *,16 + sub *,0,AR2 + sub *,3,AR2 + sub *,16,AR2 + + subb 123 + subb * + subb *, ar2 + + subc 123 + subc * + subc *, ar2 + + subs 123 + subs * + subs *, ar2 + + subt 123 + subt * + subt *, ar2 + + tblr 123 + tblr * + tblr *, ar2 + + tblw 123 + tblw * + tblw *, ar2 + + trap + + xor 123 + xor * + xor *,ar2 + xor #255 + xor #255, 3 + xor #255,16 + + zalr 123 + zalr * + zalr *, ar2 + +;------------------------------------ +; C5x additions + + cpu 320c50 + + adcb + + addb + + andb + + apl #10, 123 + apl #10, * + apl #10, *, ar2 + apl 123 + apl * + apl *, ar2 + + bd 1234h + bd 1234h, * + bd 1234h, *, ar2 + + baccd + + banzd 1234h + banzd 1234h, * + banzd 1234h, *, ar2 + + bcndd 1234h, eq, c + + bldd bmar, 123 + bldd bmar, * + bldd bmar, *, ar2 + bldd 123, bmar + bldd *, bmar + bldd *, bmar, ar2 + + bldp 123 + bldp * + bldp *, ar2 + + blpd bmar, 123 + blpd bmar, * + blpd bmar, *, ar2 + + bsar 7 + + calad + + calld 1234h + calld 1234h, * + calld 1234h, *, ar2 + + ccd 1234h, eq, c + + cpl #10, 123 + cpl #10, * + cpl #10, *, ar2 + cpl 123 + cpl * + cpl *, ar2 + + crgt + + crlt + + exar + + idle2 + + lacb + + lamm 123 + lamm * + lamm *, ar2 + + lmmr 123, #1234 + lmmr *, #1234 + lmmr *, #1234, ar2 + + madd 123 + madd * + madd *, ar2 + + mads 123 + mads * + mads *, ar2 + + opl #10, 123 + opl #10, * + opl #10, *, ar2 + opl 123 + opl * + opl *, ar2 + + orb + + retd + + retcd eq + + rete + + reti + + rolb + + rorb + + rptb 123 + + rptz #10 + + sacb + + samm 123 + samm * + samm *, ar2 + + sath + + satl + + sbb + + sbbb + + sflb + + sfrb + +; haven't found encoding of the C5x SHM instruction so far :-( +; shm + + smmr 123, #1234 + smmr *, #1234 + smmr *, #1234, ar2 + + xc 2, eq diff --git a/tests/t_3205x/t_3205x.doc b/tests/t_3205x/t_3205x.doc new file mode 100644 index 0000000..1f2b721 --- /dev/null +++ b/tests/t_3205x/t_3205x.doc @@ -0,0 +1,7 @@ ++------------------------- Test Application 3205x ---------------------------+ +| | +| This is a (synthetic) test of the TMS320C5x instruction set | +| It includes moreover a clear separation between the C20x subset and | +| the full C5x instruction set. | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_3205x/t_3205x.ori b/tests/t_3205x/t_3205x.ori new file mode 100644 index 0000000..e0089cb Binary files /dev/null and b/tests/t_3205x/t_3205x.ori differ diff --git a/tests/t_3206x/asflags b/tests/t_3206x/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_3206x/t_3206x.asm b/tests/t_3206x/t_3206x.asm new file mode 100644 index 0000000..5c5804d --- /dev/null +++ b/tests/t_3206x/t_3206x.asm @@ -0,0 +1,241 @@ + cpu 32060 + + page 0 + +mv macro src,dest + add.ATTRIBUTE 0,src,dest + endm + +neg macro src,dest + sub.ATTRIBUTE 0,src,dest + endm + +not macro src,dest + xor.ATTRIBUTE -1,src,dest + endm + + not a0,a1 + +zero macro dest + xor.ATTRIBUTE dst,dst,dst + endm + + mv a1,a3 + mv.l2 a1,b3 + + nop +|| nop +|| nop + nop + nop + + [b0] nop +|| [!b0] nop + + idle + + nop + nop 7 + + abs a4,a7 + abs.l1 a4,a7 + abs b4,a7 + abs.l1 b4,a7 + abs.l1x b4,a7 + abs b3:b2,b11:b10 + abs a7:a6,b11:b10 + + add a1,a3,a7:a6 + add a1,b3,a7:a6 + add b1,a3,a7:a6 + add a7,a5:a4,a13:a12 + add b7,a5:a4,a13:a12 + add a5:a4,a7,a13:a12 + add a5:a4,b7,a13:a12 + add b9:b8,-3,b15:b14 + add -3,b9:b8,b15:b14 + + addab.d1 a4,a2,a4 + addah.d1 a4,a2,a4 + addaw.d2 b4,2,b4 + subab.d1 a4,a2,a4 + subah.d1 a4,a2,a4 + subaw.d2 b4,2,b4 + + addk 15401,a1 + addk.s1 15401,a1 + + add2 a1,b1,a2 + sub2 b1,a0,b2 + + clr a1,4,19,a2 + clr b1,b3,b2 + + cmpeq.l2 a1,b1,b2 + cmpeq.l1 -9,a1,a2 + cmpeq.l2 a1,b3:b2,b1 + cmpgt.l1 a1,b2,a2 + cmpgt.l1 a1,b1,a2 + cmpgt.l1 8,a1,a2 + cmpgt.l1 a1,b1,a2 + cmpgtu.l1 a1,a2,a3 + cmpgtu.l1 0ah,a1,a2 + cmpgtu.l1 0eh,a3:a2,a4 + cmplt.l1 a1,a2,a3 + cmplt.l1 9,a1,a2 + cmpltu.l1 a1,a2,a3 + cmpltu.l1 14,a1,a2 + cmpltu.l1 a1,a5:a4,a2 + + ext.s1 a1,10,19,a2 + ext.s1 a1,a2,a3 + extu.s1 a1,10,19,a2 + extu.s1 a1,a2,a3 + + ldw.d1 *a10,a1 + ldb.d1 *-a5[4],a7 + ldh.d1 *++a4[a1],a8 + ldw.d1 *a4++[1],a6 + ldw.d1 *++a4(4),a6 + ldb.d2 *+b14[36],b1 + + lmbd a1,a2,a3 + + mpy.m1 a1,a2,a3 + mpyu.m1 a1,a2,a3 + mpyus.m1 a1,a2,a3 + mpy.m1 13,a1,a2 + mpysu.m1 13,a1,a2 + mpyh.m1 a1,a2,a3 + mpyhu.m1 a1,a2,a3 + mpyhsu.m1 a1,a2,a3 + mpyhl.m1 a1,a2,a3 + mpylh.m1 a1,a2,a3 + + mvc.s2 a1,amr + mvc istp,b4 + + mvk.s1 293,a1 + mvk.s2 125h,b1 + mvk.s1 0ff12h,a1 + mvkh.s1 0a329123h,a1 + mvklh 7a8h,a1 + + norm a1,a2 + norm a1:a0,a2 + + sadd.l1 a1,a2,a3 + sadd.l1 b2,a5:a4,a7:a6 + + sat.l1 a1:a0,a2 + sat.l2 b1:b0,b5 + + set.s1 a0,7,21,a1 + set.s2 b0,b1,b2 + + shl.s1 a0,4,a1 + shl.s2 b0,b1,b2 + shl.s2 b1:b0,b2,b3:b2 + + shr.s1 a0,8,a1 + shr.s2 b0,b1,b2 + shr.s2 b1:b0,b2,b3:b2 + + shru.s1 a0,8,a1 + + smpy.m1 a1,a2,a3 + smpyhl.m1 a1,a2,a3 + smpylh.m1 a1,a2,a3 + + sshl.s1 a0,2,a1 + sshl.s1 a0,a1,a2 + + ssub.l2 b1,b2,b3 + ssub.l1 a0,a1,a2 + + stb.d1 a1,*a10 + sth.d1 a1,*+a10(4) + stw.d1 a1,*++a10[1] + sth.d1 a1,*a10--[a11] + stb.d2 b1,*+b14[40] + + align 32 + mvk.s1 2c80h,a0 +|| mvk.s2 0200h,b0 + mvkh.s1 01880000h,a0 +|| mvkh.s2 00000000h,b0 + mvc.s2 a0,pdata_o + stp.s2 b0 + nop 4 + mpy.m1 a1,a2,a3 + + sub.l1 a1,a2,a3 + subu.l1 a1,a2,a5:a4 + subc.l1 a0,a1,a0 + + align 32 + ifdef error + add.s1 a0,a1,a2 +|| shr.s1 a3,15,a4 + endif + add.l1 a0,a1,a2 +|| shr.s1 a3,15,a4 + + align 32 + ifdef error + add.l1x a0,b1,a1 +|| mpy.m1x a4,b4,a5 + endif + add.l1x a0,b1,a1 +|| mpy.m2x a4,b4,b2 + + align 32 + ifdef error + ldw.d1 *a0,a1 +|| ldw.d1 *a2,b2 + endif + ldw.d1 *a0,a1 +|| ldw.d2 *b0,b2 + + align 32 + ifdef error + ldw.d1 *a4,a5 +|| stw.d2 a6,*b4 + endif + ldw.d1 *a4,b4 +|| stw.d2 a6,*b4 + + align 32 + ifdef error + add.l1 a5:a4,a1,a3:a2 +|| shl.s1 a8,a9,a7:a6 + endif + add.l1 a5:a4,a1,a3:a2 +|| shl.s2 b8,b9,b7:b6 + + align 32 + ifdef error + add.l1 a5:a4,a1,a3:a2 +|| stw.d1 a8,*a9 + endif + add.l1 a4,a1,a3:a2 +|| stw.d1 a8,*a9 + + align 32 + ifdef error + mpy.m1 a1,a1,a4 +|| add.l1 a1,a1,a5 +|| sub.d1 a1,a2,a3 + endif + mpy.m1 a1,a1,a4 +|| [a1] add.l1 a0,a1,a5 +|| sub.d1 a1,a2,a3 + + align 32 + ifdef error + add.l2 b5,b6,b7 +|| sub.s2 b8,b9,b7 + endif +[!b0] add.l2 b5,b6,b7 +|| [b0] sub.s2 b8,b9,b7 + diff --git a/tests/t_3206x/t_3206x.doc b/tests/t_3206x/t_3206x.doc new file mode 100644 index 0000000..ddfa640 --- /dev/null +++ b/tests/t_3206x/t_3206x.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 3206x ---------------------------+ +| | +| This is a (synthetic) test of the TMS320C6x instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_3206x/t_3206x.ori b/tests/t_3206x/t_3206x.ori new file mode 100644 index 0000000..d8cf606 Binary files /dev/null and b/tests/t_3206x/t_3206x.ori differ diff --git a/tests/t_370/asflags b/tests/t_370/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_370/t_370.asm b/tests/t_370/t_370.asm new file mode 100644 index 0000000..120f985 --- /dev/null +++ b/tests/t_370/t_370.asm @@ -0,0 +1,163 @@ + page 0 + + cpu 370c010 + +cat equ r16 +dog equ r011 +mouse equ p055 +rat equ p127 + + clrc + setc + dint + eint + eintl + einth + idle + ldsp + stsp + nop + rti + rts + +Targ: jmp Targ + jc Targ + jeq Targ + jg Targ + jge Targ + jhs Targ + jl Targ + jle Targ + jlo Targ + jn Targ + jnc Targ + jne Targ + jnv Targ + jnz Targ + jp Targ + jpz Targ + jv Targ + jz Targ + + adc b,a + add dog,a + dac cat,b + dsb dog,cat + sbb #55h,a + sub #0aah,b + mpy #' ',dog + + and a,p050 + btjo b,a,Targ + btjz b,p10,Targ + or cat,a + xor dog,b + and r020,r10 + btjo #55,a,Targ + btjz #66,b,Targ + or #77,r10 + xor #88,rat + + br Targ + br @dog + br Targ(b) + br 10(cat) + call Targ + call @dog + call Targ(b) + call 10(cat) + callr Targ + callr @dog + callr Targ(b) + callr 10(cat) + jmpl Targ + jmpl @dog + jmpl Targ(b) + jmpl 10(cat) + + clr a + compl b + dec cat + inc a + inv b + pop dog + push a + pop st + push st + rl b + rlc r020 + rr a + rrc b + swap dog + xchb a + djnz b,$ + + cmp 2000h,a + cmp @dog,a + cmp targ(b),a + cmp 10(cat),a + cmp -5(sp),a + cmp b,a + cmp dog,a + cmp cat,b + cmp cat,dog + cmp #55h,a + cmp #66h,b + cmp #77h,r0ff + +bit1 dbit 1,r12 +bit2 dbit 4,p033 +bit3 dbit 5,b + + cmpbit bit1 + cmpbit bit2 + jbit0 bit1,$ + jbit0 bit2,$ + jbit1 bit1,$ + jbit1 bit2,$ + sbit0 bit1 + sbit0 bit2 + sbit1 bit1 + sbit1 bit2 + + div r45,a + incw #56h,dog + ldst #12 + + mov a,b + mov a,cat + mov a,mouse + mov a,1234h + mov a,@r33 + mov a,Targ(b) + mov a,15(r015) + mov a,-2(sp) + mov dog,a + mov cat,b + mov 1234h,a + mov @dog,a + mov Targ(b),a + mov -33(cat),a + mov 15(sp),a + mov b,a + mov b,dog + mov b,rat + mov cat,dog + mov dog,mouse + mov rat,a + mov p15,b + mov p15,r015 + mov #11h,a + mov #-1,b + mov #0110110b,r10 + mov #10h,rat + + movw cat,dog + movw #12345,r010 + movw #Targ(b),cat + movw #(cat),cat + + trap 7 + + tst a + tst b diff --git a/tests/t_370/t_370.doc b/tests/t_370/t_370.doc new file mode 100644 index 0000000..da6bdb5 --- /dev/null +++ b/tests/t_370/t_370.doc @@ -0,0 +1,5 @@ ++-------------------------- Test Application 370 ----------------------------+ +| | +| This is a (synthetic) test of the TMS370 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_370/t_370.ori b/tests/t_370/t_370.ori new file mode 100644 index 0000000..75db2ab Binary files /dev/null and b/tests/t_370/t_370.ori differ diff --git a/tests/t_4004/asflags b/tests/t_4004/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_4004/t_4004.asm b/tests/t_4004/t_4004.asm new file mode 100644 index 0000000..fc6d55f --- /dev/null +++ b/tests/t_4004/t_4004.asm @@ -0,0 +1,205 @@ + cpu 4004 + + nop + + jcn z, Next + jcn nz, Next + jcn c, Next + jcn nc, Next + jcn t, Next + jcn nt, Next + jcm z, Next + jcm nz, Next + jcm c, Next + jcm nc, Next + jcm t, Next + jcm nt, Next +Next: + fim r0r1, 12h + fim r2r3, 23h + fim r4r5, 34h + fim r6r7, 45h + fim r8r9, 56h + fim rarb, 67h + fim rcrd, 78h + fim rerf, 89h + + src r0r1 + src r2r3 + src r4r5 + src r6r7 + src r8r9 + src rarb + src rcrd + src rerf + + fin r0r1 + fin r2r3 + fin r4r5 + fin r6r7 + fin r8r9 + fin rarb + fin rcrd + fin rerf + + jin r0r1 + jin r2r3 + jin r4r5 + jin r6r7 + jin r8r9 + jin rarb + jin rcrd + jin rerf + + jun 123h + jms 456h + + inc r0 + inc r1 + inc r2 + inc r3 + inc r4 + inc r5 + inc r6 + inc r7 + inc r8 + inc r9 + inc ra + inc rb + inc rc + inc rd + inc re + inc rf + +loop: + isz r0, loop + isz r1, loop + isz r2, loop + isz r3, loop + isz r4, loop + isz r5, loop + isz r6, loop + isz r7, loop + isz r8, loop + isz r9, loop + isz ra, loop + isz rb, loop + isz rc, loop + isz rd, loop + isz re, loop + isz rf, loop + + add a, r0 + add a, r1 + add a, r2 + add a, r3 + add a, r4 + add a, r5 + add a, r6 + add a, r7 + add a, r8 + add a, r9 + add a, ra + add a, rb + add a, rc + add a, rd + add a, re + add a, rf + + sub a, r0 + sub a, r1 + sub a, r2 + sub a, r3 + sub a, r4 + sub a, r5 + sub a, r6 + sub a, r7 + sub a, r8 + sub a, r9 + sub a, ra + sub a, rb + sub a, rc + sub a, rd + sub a, re + sub a, rf + + ld a, r0 + ld a, r1 + ld a, r2 + ld a, r3 + ld a, r4 + ld a, r5 + ld a, r6 + ld a, r7 + ld a, r8 + ld a, r9 + ld a, ra + ld a, rb + ld a, rc + ld a, rd + ld a, re + ld a, rf + + xch r0 + xch r1 + xch r2 + xch r3 + xch r4 + xch r5 + xch r6 + xch r7 + xch r8 + xch r9 + xch ra + xch rb + xch rc + xch rd + xch re + xch rf + + bbl 1 + bbl 3 + bbl 0dh + + ldm 1 + ldm 3 + ldm 0dh + + wrm + wmp + wrr + wpm + wr0 + wr1 + wr2 + wr3 + sbm + rdm + rdr + adm + ad0 + ad1 + ad2 + ad3 + rd0 + rd1 + rd2 + rd3 + + clb + clc + iac + cmc + cma + ral + rar + tcc + dac + tcs + stc + daa + kbp + dcl + + data 1,2,3,4,5 + data "This is a test" diff --git a/tests/t_4004/t_4004.doc b/tests/t_4004/t_4004.doc new file mode 100644 index 0000000..a5f66e1 --- /dev/null +++ b/tests/t_4004/t_4004.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 4004 ----------------------------+ +| | +| This is a (synthetic) test of the 4004 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_4004/t_4004.ori b/tests/t_4004/t_4004.ori new file mode 100644 index 0000000..e508c0c Binary files /dev/null and b/tests/t_4004/t_4004.ori differ diff --git a/tests/t_403/asflags b/tests/t_403/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_403/t_403.asm b/tests/t_403/t_403.asm new file mode 100644 index 0000000..0ee143a --- /dev/null +++ b/tests/t_403/t_403.asm @@ -0,0 +1,27 @@ + cpu ppc403 + page 0 + include stddef60 + + org 0x1000 + + + mtdcr 10,r5 + mtbear r5 + mfdcr r5,10 + mfbesr r5 + wrtee r10 + wrteei 1 + + bdnzl 0x10 + bdztla 7,0x10 + beq 0x10 + beq 2,0x10 + beq cr2,0x10 + + cmpw r1,r2 + clrlwi r1,r2,5 + + mtspr pit,r5 + + mcrf cr4,cr5 + mcrf 4,5 diff --git a/tests/t_403/t_403.doc b/tests/t_403/t_403.doc new file mode 100644 index 0000000..893ca08 --- /dev/null +++ b/tests/t_403/t_403.doc @@ -0,0 +1,6 @@ ++------------------------- Test Application 403 -----------------------------+ +| | +| This is a (synthetic) test of the PPC403's extensions to the PowerPC | +| basic instruction set. | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_403/t_403.ori b/tests/t_403/t_403.ori new file mode 100644 index 0000000..8bae53a Binary files /dev/null and b/tests/t_403/t_403.ori differ diff --git a/tests/t_4500/asflags b/tests/t_4500/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_4500/t_4500.asm b/tests/t_4500/t_4500.asm new file mode 100644 index 0000000..5e9f028 --- /dev/null +++ b/tests/t_4500/t_4500.asm @@ -0,0 +1,109 @@ + cpu melps4500 + + a 10 + am + amc + and + b $20 + bl $20,$20 + bl $1234 + bla 7 + bm $110 + bml $20,$20 + bml $1234 + bmla 7 + cld + cma + dey + di + ei + iap0 + iap1 + iap2 + iap3 + iap4 + iny + la $c + lxy 2,3 + lxy $ac + lz %10 + nop + or + op0a + op1a + pof + pof2 + rar + rb 2 + rc + rc3 + rc4 + rd + rt + rti + rts + sb 1 + sc + sc3 + sc4 + sd + sea 3 + seam + snz0 + snzp + snzt1 + snzt2 + snzt3 + spcr + stcr + szb 3 + szc + szd + t1r1 + t3ab + tab + tab3 + tabe + tabp 1 + tad + tai1 + tal1 + tam 7 + tamr + tasp + tav1 + taw1 + taw2 + taw3 + tax + tay + taz + tba + tc1a + tc2a + tda + teab + ti1a + tl1a + tl2a + tl3a + tlca + tma 12 + tmra + tpta + tpaa + tr1a + tr1ab + tv1a + tw1a + tw2a + tw3a + tya + wrst + xam 2 + xamd 12 + xami 6 + + res 5 + data 10,1000,-13,'A' + data "ABC" diff --git a/tests/t_4500/t_4500.doc b/tests/t_4500/t_4500.doc new file mode 100644 index 0000000..7cb1aec --- /dev/null +++ b/tests/t_4500/t_4500.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 4500 ----------------------------+ +| | +| This is a (synthetic) test of the MELPS/45xx instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_4500/t_4500.ori b/tests/t_4500/t_4500.ori new file mode 100644 index 0000000..727e60d Binary files /dev/null and b/tests/t_4500/t_4500.ori differ diff --git a/tests/t_47c00/asflags b/tests/t_47c00/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_47c00/t_47c00.asm b/tests/t_47c00/t_47c00.asm new file mode 100644 index 0000000..30ab5d9 --- /dev/null +++ b/tests/t_47c00/t_47c00.asm @@ -0,0 +1,255 @@ + cpu 470ac00 + include stddef47.inc + + page 0 + + + segment data + +nvar1 db ? +nvar2 db ? + align 4 +bvar db 2 dup (?) + + + segment io + +port1 db ? +port2 db ? +port3 port 7 + + segment code + +targ: db ? + + ret + nop + reti + + inc @hl + dec @hl + inc a + dec a + inc l + dec l + + and a,@hl + and @hl,#3 + and a,#5 + or a,@hl + or @hl,#3 + or a,#5 + xor a,@hl + + ld a,@hl + ld a,123 + ld hl,bvar + ld a,#4 + ld h,#-3 + ld l,#7 + ld hl,#0a5h + ld dmb,#2 + ld dmb,@hl + + ldl a,@dc + ldh a,@dc+ + + st a,@hl + st a,@hl+ + st a,@hl- + st a,123 + st #3,@hl+ + st #5,nvar1 + st dmb,@hl + + mov h,a + mov l,a + mov a,dmb + mov dmb,a + mov a,spw13 + mov stk13,a + + xch a,@hl + xch nvar2,a + xch hl,bvar + xch a,l + xch h,a + xch eir,a + + in %port1,a + in %15h,a + in %port2,@hl + in %1ah,@hl + + out a,%port1 + out @hl,%port2 + out #-3,%port2 + + outb @hl + + cmpr a,@hl + cmpr a,nvar2 + cmpr nvar2,#3 + cmpr a,#4 + cmpr h,#5 + cmpr l,#6 + + add a,@hl + add @hl,#4 + add nvar2,#5 + add a,#6 + add h,#7 + add l,#7 + + addc a,@hl + subrc a,@hl + + subr a,#7 + subr @hl,#0ah + + rolc a + rolc a,3 + rorc a + rorc a,2 + + clr @l + set @l + test @l + + test cf + testp cf + + testp zf + +; clr gf +; set gf +; testp gf + +; clr dmb +; set dmb +; test dmb +; testp dmb + + clr dmb0 + set dmb0 + test dmb0 + testp dmb0 + + clr dmb1 + set dmb1 + test dmb1 + testp dmb1 + + clr stk13 + set stk13 + + clr il,8h + + test a,2 + + clr @hl,1 + set @hl,3 + test @hl,2 + + clr %5,1 + set %6,3 + test %7,2 + testp %8,0 + + clr nvar2,1 + set nvar2,3 + test nvar2,2 + testp nvar2,0 + + bss ($&3fc0h)+20h + bs 123h + bsl 0123h + bsl 1123h + bsl 2123h + bsl 3123h + + calls 002eh + + call 123h + + eiclr il,3 + diclr il,5 + + b ($&3fc0h)+20h + b 123h + b 0123h + b 1123h + b 2123h + b 3123h + + bz targ + bnz targ + bc targ + bnc targ + be a,@hl,targ + be a,nvar2,targ + be a,#3,targ + be h,#4,targ + be l,#5,targ + be nvar1,#6,targ + bne a,@hl,targ + bne a,nvar2,targ + bne a,#3,targ + bne h,#4,targ + bne l,#5,targ + bne nvar1,#6,targ + bge a,@hl,targ + bge a,nvar2,targ + bge a,#3,targ + bge h,#4,targ + bge l,#5,targ + bge nvar1,#6,targ + bgt a,@hl,targ + bgt a,nvar2,targ + bgt a,#3,targ + bgt h,#4,targ + bgt l,#5,targ + bgt nvar1,#6,targ + ble a,@hl,targ + ble a,nvar2,targ + ble a,#3,targ + ble h,#4,targ + ble l,#5,targ + ble nvar1,#6,targ + blt a,@hl,targ + blt a,nvar2,targ + blt a,#3,targ + blt h,#4,targ + blt l,#5,targ + blt nvar1,#6,targ + + callss 0 + callss 5 + + callz targ + callnz targ + callc targ + callnc targ + + retz + retnz + retc + retnc + retiz + retinz + retic + retinc + + shl a,2 + shl h,2 + shl l,2 + shl @hl,2 + shl nvar1,2 + shr a,2 + shr h,2 + shr l,2 + shr @hl,2 + shr nvar1,2 + + ei + di \ No newline at end of file diff --git a/tests/t_47c00/t_47c00.doc b/tests/t_47c00/t_47c00.doc new file mode 100644 index 0000000..23953b5 --- /dev/null +++ b/tests/t_47c00/t_47c00.doc @@ -0,0 +1,5 @@ ++------------------------ Test Application 47C00 ----------------------------+ +| | +| This is a (synthetic) test of the TLCS-47(0(A)) instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_47c00/t_47c00.ori b/tests/t_47c00/t_47c00.ori new file mode 100644 index 0000000..122b6d9 Binary files /dev/null and b/tests/t_47c00/t_47c00.ori differ diff --git a/tests/t_48/asflags b/tests/t_48/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_48/t_48.asm b/tests/t_48/t_48.asm new file mode 100644 index 0000000..fc50424 --- /dev/null +++ b/tests/t_48/t_48.asm @@ -0,0 +1,178 @@ + cpu 8048 + + add a,r2 + add a,@r1 + add a,#21h + + addc a,r3 + addc a,@r1 + addc a,#21h + + anl a,r4 + anl a,@r1 + anl a,#21h + anl bus,#12h + + anld p5,a + + call 345h + + clr a + clr c + clr f0 + clr f1 + + cpl a + cpl c + cpl f0 + cpl f1 + + da a + + dec a + dec r1 + + dis i + dis tcnti + + djnz r2,$ + + en i + en tcnti + + ent0 clk + + in a,p1 + in a,p2 + + inc a + inc r7 + inc @r1 + + ins a,bus + + jb3 $ + + jc $ + + jf0 $ + jf1 $ + + jmp 123h + + jnc $ + + jni $ + + jnt0 $ + jnt1 $ + + jnz $ + + jt0 $ + jt1 $ + + jtf $ + + jz $ + + jmpp @a + + mov a,r2 + mov a,@r1 + mov a,#21h + mov r3,a + mov @r1,a + mov r4,#21h + mov @r1,#21h + mov a,psw + mov psw,a + mov a,t + mov t,a + + movd a,p5 + movd p6,a + + movx a,@r1 + movx @r1,a + + movp a,@a + movp3 a,@a + + nop + + orl a,r5 + orl a,@r1 + orl a,#21h + orl bus,#12h + + orld p5,a + + outl p1,a + outl p2,a + outl bus,a + + ret + + retr + + rl a + + rlc a + + rr a + + rrc a + + sel mb0 + sel mb1 + sel rb0 + sel rb1 + + strt cnt + strt t + + stop tcnt + + swap a + + xch a,r5 + xch a,@r1 + + xchd a,@r1 + + xrl a,r6 + xrl a,@r1 + xrl a,#21h + + + cpu 8041 + + en dma + en flags + + in a,dbb + + jnibf $ + + jobf $ + + mov sts,a + + out dbb,a + + + cpu 80c39 + + idl + + + cpu 8022 + + in a,p0 + outl p0,a + + sel an0 + sel an1 + rad + diff --git a/tests/t_48/t_48.doc b/tests/t_48/t_48.doc new file mode 100644 index 0000000..1ca6179 --- /dev/null +++ b/tests/t_48/t_48.doc @@ -0,0 +1,5 @@ ++-------------------------- Test Application 48 -----------------------------+ +| | +| This is a (synthetic) test of the MCS-48 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_48/t_48.ori b/tests/t_48/t_48.ori new file mode 100644 index 0000000..15d3a3b Binary files /dev/null and b/tests/t_48/t_48.ori differ diff --git a/tests/t_56000/asflags b/tests/t_56000/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_56000/t_56000.asm b/tests/t_56000/t_56000.asm new file mode 100644 index 0000000..acf594f --- /dev/null +++ b/tests/t_56000/t_56000.asm @@ -0,0 +1,244 @@ + page 0 + + cpu 56000 + + include stddef56k.inc + + segment code + org $300 + + nop + enddo + illegal + reset + rti + rts + stop + swi + wait + + jmp $214 + jsr $889 + jmp $3567 + jsr $2340 + jmp (r3) + jsr (r5) + jmp (r6)+ + jsr (r1)+ + jmp (r4)- + jsr (r2)- + jmp -(r5) + jsr -(r0) + jmp (r3+n3) + jsr (r7+n7) + jmp (r2)+n2 + jsr (r6)+n6 + jmp (r5)-n5 + jsr (r3)-n3 + + jcc $123 + jge $2345 + jne (r7) + jpl (r6)- + jnn (r5)+ + jec -(r4) + jlc (r3+n3) + jgt (r2)+n2 + jcs (r1)-n1 + jlt $123 + jeq $2345 + jmi (r0) + jnr (r1)- + jes (r2)+ + jls -(r3) + jle (r4+n4) + jhs (r5)+n5 + jlo (r6)-n6 + + jsnn $768 + jsle (r0) + + + move (r3)+n3 + move (r4)-n4 + move (r2)- + move (r6)+ + + move n5,a2 + move r4,b1 + move a0,b2 + move a,r4 + + move #$30,n5 + move #$ff,r3 + + move x:#$123456,a0 + move y:#$234567,y1 + move #$345678,r5 + move y:#$456789,n1 + + move x:$12,b2 + move y:$34,n6 + move x:$1234,a + move y:$2345,b2 + move b2,x:$12 + move n6,y:$34 + move a,x:$1234 + move b2,y:$2345 + + move x:(r3),a0 + move y:(r4)+n4,x1 + move a0,x:(r3) + move x1,y:(r4)+n4 + + move l:$12,ab + move $3456,y + move ab,l:$12 + move y,$3456 + + move b,x:(r1)+ x0,b + move y0,b b,y:(r1)+ + + move x1,x:(r2)+ a,y:(r5)+n5 + move x:(r2)+,x1 a,y:(r5)+n5 + move x:(r2)+,x1 y:(r5)+n5,a + + move x:(r5),x1 a,y1 + move a,x:-(r1) b,y0 + move b,x:$1234 a,y0 + move #$234567,x0 b,y1 + + move b,x1 y:(r6)-n6,b + + abs a #$123456,x0 a,y0 + asl a (r3)- + asr b x:-(r3),r3 + clr a #$7f,n0 + lsl b #$7f,r0 + lsr a a1,n4 + neg b x1,x:(r3)+ y:(r6)-,a + not a ab,l:(r2)+ + rnd a #$123456,x1 b,y1 + rol a #$314,n2 + ror b #$1234,r2 + tst a #$345678,b + adc y,b a10,l:$4 + sbc y,b a10,l:$4 + add x0,a a,x1 a,y:(r1)+ + cmp y0,b x0,x:(r6)+n6 y1,y:(r0)- + cmpm x1,a ba,l:-(r4) + sub x1,a x:(r2)+n2,r0 + addl a,b #$0,r0 + addr b,a x0,x:(r1)+n1 y0,y:(r4)- + subl a,b y:(r5+n5),r7 + subr b,a n5,y:-(r5) + and x0,a (r5)-n5 + eor y1,b (r2)+ + or y1,b ba,l:$1234 + mac x0,x0,a x:(r2)+n2,y1 + macr x0,y0,b y:(r4)+n4,y0 + mpy -x1,y1,a #$543210,y0 + mpyr -y0,y0,b (r3)-n3 + + bchg #$7,x:$ffe2 + bclr #$e,x:$ffe4 + bset #$0,x:$ffe5 + btst #$1,x:$ffee + bclr #$4,y:$ffe0 + bclr #$5,x:$0020 + bclr #$6,y:$0012 + bclr #$7,x:$1234 + bclr #$8,y:(r3)+ + bclr #$9,r5 + bclr #$a,m6 + bclr #$b,omr + + div x1,b + + do x:(r3),$1234 + do y:(r5+n5),$2345 + do x:$12,$3456 + do y:$23,$4567 + do #$123,$5678 + do n7,$6789 + + jclr #$5,x:$fff1,$1234 + jsclr #$1,y:$ffe3,$1357 + jset #12,x:$fff2,$4321 + jsset #$17,y:$3f,$100 + jclr #21,x:(r5),$6789 + jclr #22,ssh,$5678 + + lua (r0)+n0,r1 + + movec m0,m2 + movec m4,r2 + movec n5,ssl + movec #0,omr + movec #123456,ssh + movec x:$12,m2 + movec m2,x:$12 + movec y:$23,m2 + movec m2,y:$23 + movec x:(r4),m5 + movec m5,y:(r4) + movec y:(r4),m5 + movec m5,x:(r4) + + movem m4,$12 + movem $12,m4 + movem $123,m4 + movem m4,$123 + + andi #2,ccr + ori #5,omr + + norm r5,a + norm r2,b + + rep r4 + rep #$987 + rep x:$12 + rep y:$23 + rep x:(r3) + rep y:$12 + + movep x:(r3),x:$ffe0 + movep y:(r3),x:$ffe1 + movep #$123456,x:$ffe2 + movep x:$ffe3,x:(r3) + movep x:$ffe4,y:(r3) + movep x:(r3),y:$ffe5 + movep y:(r3),y:$ffe6 + movep #$123456,y:$ffe7 + movep y:$ffe8,x:(r3) + movep y:$ffe9,y:(r3) + movep p:(r3),x:$ffea + movep x:$ffeb,p:(r3) + movep p:(r3),y:$ffec + movep y:$ffed,p:(r3) + movep a1,x:$ffef + movep x:$fff0,r3 + movep n5,y:$fff1 + movep y:$fff2,m1 + + tfr a,b a,x1 y:(r4+n4),y0 + tfr y0,a + + tgt x0,a r0,r1 + tne y1,a + + dc "Hallo" + dc '123' + dc $123456 + dc "Dies ist ein Test, Leute" 0 + + segment xdata + + org $123 +var1: ds 1 + + segment ydata + + org $234 +var2: ds 1 diff --git a/tests/t_56000/t_56000.doc b/tests/t_56000/t_56000.doc new file mode 100644 index 0000000..326f888 --- /dev/null +++ b/tests/t_56000/t_56000.doc @@ -0,0 +1,5 @@ ++---------------------- Test Application 56000 ----------------------------+ +| | +| This is a (synthetic) test of the DSP56K code generator | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_56000/t_56000.ori b/tests/t_56000/t_56000.ori new file mode 100644 index 0000000..e661401 Binary files /dev/null and b/tests/t_56000/t_56000.ori differ diff --git a/tests/t_56300/asflags b/tests/t_56300/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_56300/t_56300.asm b/tests/t_56300/t_56300.asm new file mode 100644 index 0000000..d392a11 --- /dev/null +++ b/tests/t_56300/t_56300.asm @@ -0,0 +1,1462 @@ + cpu 56300 + page 0 + + org $8000 + + abs a ; >=56000 + abs b + + adc x,a ; >=56000 + adc y,a + adc x,b + adc y,b + + add x0,a ; >=56000 + add x1,a + add y0,a + add y1,a + add x,a + add y,a + add b,a + add x0,b ; >=56000 + add x1,b + add y0,b + add y1,b + add x,b + add y,b + add a,b + + add #31,a ; >=56300 + add #1234,a + add #31,b + add #1234,b + + addl b,a ; >=56000 + addl a,b + + addr b,a + addr a,b + + and x0,a ; >=56000 + and x1,a + and y0,a + and y1,a + and x0,b + and x1,b + and y0,b + and y1,b + + and #31,a ; >=56000 + and #1234,a + and #31,b + and #1234,b + + andi #$12,mr ; >=56000 + andi #$12,ccr + andi #$12,com + andi #$12,eom + + asl a ; >=56000 + asl b + asl #$23,a,a ; >=56300 + asl #$23,a,b + asl #$23,b,a + asl #$23,b,b + asl a1,a,a ; >=56300 + asl b1,a,a + asl x0,a,a + asl y0,a,a + asl x1,a,a + asl y1,a,a + asl a1,a,b + asl b1,a,b + asl x0,a,b + asl y0,a,b + asl x1,a,b + asl y1,a,b + asl a1,b,a + asl b1,b,a + asl x0,b,a + asl y0,b,a + asl x1,b,a + asl y1,b,a + asl a1,b,b + asl b1,b,b + asl x0,b,b + asl y0,b,b + asl x1,b,b + asl y1,b,b + + asr a ; >=56000 + asr b + asr #$23,a,a ; >=56300 + asr #$23,a,b + asr #$23,b,a + asr #$23,b,b + asr a1,a,a ; >=56300 + asr b1,a,a + asr x0,a,a + asr y0,a,a + asr x1,a,a + asr y1,a,a + asr a1,a,b + asr b1,a,b + asr x0,a,b + asr y0,a,b + asr x1,a,b + asr y1,a,b + asr a1,b,a + asr b1,b,a + asr x0,b,a + asr y0,b,a + asr x1,b,a + asr y1,b,a + asr a1,b,b + asr b1,b,b + asr x0,b,b + asr y0,b,b + asr x1,b,b + asr y1,b,b + + bcc *+$2000 + bge *+$20 + bne r3 + bpl *-$2000 + bnn *-$20 + bec r4 + blc >*+$20 + bgt <*-$20 + bcs *+$2000 + blt *+$20 + beq r5 + bmi *-$2000 + bnr *-$20 + bes r6 + bls >*+$20 + ble <*-$20 + bhs *+$2000 + blo *+$20 + + bchg #2,x:(r1)-n1 ; >=56000 + bchg #2,y:(r1)-n1 + bchg #3,x:(r2)+n2 + bchg #3,y:(r2)+n2 + bchg #4,x:(r3)- + bchg #4,y:(r3)- + bchg #5,x:(r4)+ + bchg #5,y:(r4)+ + bchg #6,x:(r5) + bchg #6,y:(r5) + bchg #7,x:(r6+n6) + bchg #7,y:(r6+n6) + bchg #8,x:-(r7) + bchg #8,y:-(r7) + bchg #9,x:$1234 + bchg #9,y:$1234 + bchg #11,x:$20 + bchg #11,y:$20 + bchg #13,x:$ffffca + bchg #13,y:$ffffca + bchg #7,x:$ffff95 ; >=56300 + bchg #7,y:$ffff95 + bchg #10,r6 ; >=56000 + bchg #10,b + + bclr #2,x:(r1)-n1 ; >=56000 + bclr #2,y:(r1)-n1 + bclr #3,x:(r2)+n2 + bclr #3,y:(r2)+n2 + bclr #4,x:(r3)- + bclr #4,y:(r3)- + bclr #5,x:(r4)+ + bclr #5,y:(r4)+ + bclr #6,x:(r5) + bclr #6,y:(r5) + bclr #7,x:(r6+n6) + bclr #7,y:(r6+n6) + bclr #8,x:-(r7) + bclr #8,y:-(r7) + bclr #9,x:$1234 + bclr #9,y:$1234 + bclr #11,x:$20 + bclr #11,y:$20 + bclr #13,x:$ffffca + bclr #13,y:$ffffca + bclr #7,x:$ffff95 ; >=56300 + bclr #7,y:$ffff95 + bclr #10,r6 ; >=56000 + bclr #10,b + + bra *+$2000 + bra *+$20 + bra *-$2000 + bra *-$20 + bra >*+$20 + bra >*-$20 + bra r5 + + brclr #2,x:(r1)-n1,* ; >=56300 + brclr #2,y:(r1)-n1,* + brclr #3,x:(r2)+n2,* + brclr #3,y:(r2)+n2,* + brclr #4,x:(r3)-,* + brclr #4,y:(r3)-,* + brclr #5,x:(r4)+,* + brclr #5,y:(r4)+,* + brclr #6,x:(r5),* + brclr #6,y:(r5),* + brclr #7,x:(r6+n6),* + brclr #7,y:(r6+n6),* + brclr #8,x:-(r7),* + brclr #8,y:-(r7),* + brclr #11,x:$20,* + brclr #11,y:$20,* + brclr #13,x:$ffffca,* + brclr #13,y:$ffffca,* + brclr #7,x:$ffff95,* + brclr #7,y:$ffff95,* + brclr #10,r6,* + brclr #10,b,* + + brkcc + brkge + brkne + brkpl + brknn + brkec + brklc + brkgt + brkcs + brklt + brkeq + brkmi + brknr + brkes + brkls + brkle + brkhs + brklo + + brset #2,x:(r1)-n1,* ; >=56300 + brset #2,y:(r1)-n1,* + brset #3,x:(r2)+n2,* + brset #3,y:(r2)+n2,* + brset #4,x:(r3)-,* + brset #4,y:(r3)-,* + brset #5,x:(r4)+,* + brset #5,y:(r4)+,* + brset #6,x:(r5),* + brset #6,y:(r5),* + brset #7,x:(r6+n6),* + brset #7,y:(r6+n6),* + brset #8,x:-(r7),* + brset #8,y:-(r7),* + brset #11,x:$20,* + brset #11,y:$20,* + brset #13,x:$ffffca,* + brset #13,y:$ffffca,* + brset #7,x:$ffff95,* + brset #7,y:$ffff95,* + brset #10,r6,* + brset #10,b,* + + bscc *+$2000 + bsge *+$20 + bsne r3 + bspl *-$2000 + bsnn *-$20 + bsec r4 + bslc >*+$20 + bsgt <*-$20 + bscs *+$2000 + bslt *+$20 + bseq r5 + bsmi *-$2000 + bsnr *-$20 + bses r6 + bsls >*+$20 + bsle <*-$20 + bshs *+$2000 + bslo *+$20 + + bsclr #2,x:(r1)-n1,* ; >=56300 + bsclr #2,y:(r1)-n1,* + bsclr #3,x:(r2)+n2,* + bsclr #3,y:(r2)+n2,* + bsclr #4,x:(r3)-,* + bsclr #4,y:(r3)-,* + bsclr #5,x:(r4)+,* + bsclr #5,y:(r4)+,* + bsclr #6,x:(r5),* + bsclr #6,y:(r5),* + bsclr #7,x:(r6+n6),* + bsclr #7,y:(r6+n6),* + bsclr #8,x:-(r7),* + bsclr #8,y:-(r7),* + bsclr #11,x:$20,* + bsclr #11,y:$20,* + bsclr #13,x:$ffffca,* + bsclr #13,y:$ffffca,* + bsclr #7,x:$ffff95,* + bsclr #7,y:$ffff95,* + bsclr #10,r6,* + bsclr #10,b,* + + bset #2,x:(r1)-n1 ; >=56000 + bset #2,y:(r1)-n1 + bset #3,x:(r2)+n2 + bset #3,y:(r2)+n2 + bset #4,x:(r3)- + bset #4,y:(r3)- + bset #5,x:(r4)+ + bset #5,y:(r4)+ + bset #6,x:(r5) + bset #6,y:(r5) + bset #7,x:(r6+n6) + bset #7,y:(r6+n6) + bset #8,x:-(r7) + bset #8,y:-(r7) + bset #9,x:$1234 + bset #9,y:$1234 + bset #11,x:$20 + bset #11,y:$20 + bset #13,x:$ffffca + bset #13,y:$ffffca + bset #7,x:$ffff95 ; >=56300 + bset #7,y:$ffff95 + bset #10,r6 ; >=56000 + bset #10,b + + bsr *+$2000 + bsr *+$20 + bsr *-$2000 + bsr *-$20 + bsr >*+$20 + bsr >*-$20 + bsr r5 + + bsset #2,x:(r1)-n1,* ; >=56300 + bsset #2,y:(r1)-n1,* + bsset #3,x:(r2)+n2,* + bsset #3,y:(r2)+n2,* + bsset #4,x:(r3)-,* + bsset #4,y:(r3)-,* + bsset #5,x:(r4)+,* + bsset #5,y:(r4)+,* + bsset #6,x:(r5),* + bsset #6,y:(r5),* + bsset #7,x:(r6+n6),* + bsset #7,y:(r6+n6),* + bsset #8,x:-(r7),* + bsset #8,y:-(r7),* + bsset #11,x:$20,* + bsset #11,y:$20,* + bsset #13,x:$ffffca,* + bsset #13,y:$ffffca,* + bsset #7,x:$ffff95,* + bsset #7,y:$ffff95,* + bsset #10,r6,* + bsset #10,b,* + + btst #2,x:(r1)-n1 ; >=56000 + btst #2,y:(r1)-n1 + btst #3,x:(r2)+n2 + btst #3,y:(r2)+n2 + btst #4,x:(r3)- + btst #4,y:(r3)- + btst #5,x:(r4)+ + btst #5,y:(r4)+ + btst #6,x:(r5) + btst #6,y:(r5) + btst #7,x:(r6+n6) + btst #7,y:(r6+n6) + btst #8,x:-(r7) + btst #8,y:-(r7) + btst #9,x:$1234 + btst #9,y:$1234 + btst #11,x:$20 + btst #11,y:$20 + btst #13,x:$ffffca + btst #13,y:$ffffca + btst #7,x:$ffff95 ; >=56300 + btst #7,y:$ffff95 + btst #10,r6 ; >=56000 + btst #10,b + + clb a,a ; >=56300 + clb a,b + clb b,a + clb b,b + + clr a ; >=56000 + clr b + + cmp x0,a ; >=56000 + cmp x1,a + cmp y0,a + cmp y1,a + cmp x,a + cmp y,a + cmp b,a + cmp x0,b ; >=56000 + cmp x1,b + cmp y0,b + cmp y1,b + cmp x,b + cmp y,b + cmp a,b + + cmp #31,a ; >=56300 + cmp #1234,a + cmp #31,b + cmp #1234,b + + cmpm x0,a ; >=56000 + cmpm x1,a + cmpm y0,a + cmpm y1,a + cmpm b,a + cmpm x0,b + cmpm x1,b + cmpm y0,b + cmpm y1,b + cmpm a,b + + cmpu x0,a ; >=56300 + cmpu x1,a + cmpu y0,a + cmpu y1,a + cmpu b,a + cmpu x0,b + cmpu x1,b + cmpu y0,b + cmpu y1,b + cmpu a,b + + debug ; >=56300 + debugcc + debugge + debugne + debugpl + debugnn + debugec + debuglc + debuggt + debugcs + debuglt + debugeq + debugmi + debugnr + debuges + debugls + debugle + debughs + debuglo + + dec a ; >=56002 + dec b + + div x0,a ; >=56000 + div x1,a + div y0,a + div y1,a + div x0,b + div x1,b + div y0,b + div y1,b + + dmacss +x0,x0,a ; >=56300 + dmacss -y0,y0,a + dmacss +x1,x0,b + dmacss -y1,y0,b + dmacss +x1,x1,a + dmacss -y1,y1,a + dmacss +x0,x1,b + dmacss -y0,y1,b + dmacss +x0,y1,a + dmacss -y0,x0,a + dmacss +x1,y0,b + dmacss -y1,x1,b + dmacss +y1,x0,a + dmacss -x0,y0,a + dmacss +y0,x1,b + dmacss -x1,y1,b + + dmacsu +x0,x0,a ; >=56300 + dmacsu -y0,y0,a + dmacsu +x1,x0,b + dmacsu -y1,y0,b + dmacsu +x1,x1,a + dmacsu -y1,y1,a + dmacsu +x0,x1,b + dmacsu -y0,y1,b + dmacsu +x0,y1,a + dmacsu -y0,x0,a + dmacsu +x1,y0,b + dmacsu -y1,x1,b + dmacsu +y1,x0,a + dmacsu -x0,y0,a + dmacsu +y0,x1,b + dmacsu -x1,y1,b + + dmacuu +x0,x0,a ; >=56300 + dmacuu -y0,y0,a + dmacuu +x1,x0,b + dmacuu -y1,y0,b + dmacuu +x1,x1,a + dmacuu -y1,y1,a + dmacuu +x0,x1,b + dmacuu -y0,y1,b + dmacuu +x0,y1,a + dmacuu -y0,x0,a + dmacuu +x1,y0,b + dmacuu -y1,x1,b + dmacuu +y1,x0,a + dmacuu -x0,y0,a + dmacuu +y0,x1,b + dmacuu -x1,y1,b + + do x:(r1)-n1,*+2 ; >=56000 + do y:(r1)-n1,*+2 + do x:(r2)+n2,*+2 + do y:(r2)+n2,*+2 + do x:(r3)-,*+2 + do y:(r3)-,*+2 + do x:(r4)+,*+2 + do y:(r4)+,*+2 + do x:(r5),*+2 + do y:(r5),*+2 + do x:(r6+n6),*+2 + do y:(r6+n6),*+2 + do x:-(r7),*+2 + do y:-(r7),*+2 + do x:$12,*+2 + do y:$12,*+2 + do #$78,*+2 + do #$678,*+2 + do r4,*+2 + do forever,*+2 ; >=56300 + + dor x:(r1)-n1,*+3 ; >=56300 + dor y:(r1)-n1,*+3 + dor x:(r2)+n2,*+3 + dor y:(r2)+n2,*+3 + dor x:(r3)-,*+3 + dor y:(r3)-,*+3 + dor x:(r4)+,*+3 + dor y:(r4)+,*+3 + dor x:(r5),*+3 + dor y:(r5),*+3 + dor x:(r6+n6),*+3 + dor y:(r6+n6),*+3 + dor x:-(r7),*+3 + dor y:-(r7),*+3 + dor x:$12,*+3 + dor y:$12,*+3 + dor #$78,*+3 + dor #$678,*+3 + dor r4,*+3 + dor forever,*+3 + + enddo ; >=56000 + + eor x0,a ; >=56000 + eor y0,a + eor x1,a + eor y1,a + eor x0,b + eor y0,b + eor x1,b + eor y1,b + + eor #$34,a ; >=56300 + eor #$34,b + eor #$123456,a + eor #$123456,b + + extract a1,a,a ; >=56300 + extract b1,a,a + extract x0,a,a + extract x1,a,a + extract y0,a,a + extract y1,a,a + extract a1,b,a + extract a1,a,b + extract #$234567,a,a + extract #$234567,a,b + extract #$234567,b,a + extract #$234567,b,b + + extractu a1,a,a ; >=56300 + extractu b1,a,a + extractu x0,a,a + extractu x1,a,a + extractu y0,a,a + extractu y1,a,a + extractu a1,b,a + extractu a1,a,b + extractu #$234567,a,a + extractu #$234567,a,b + extractu #$234567,b,a + extractu #$234567,b,b + + abs a ifcc ; >=56300 + abs a ifge + abs a ifne + abs a ifpl + abs a ifnn + abs a ifec + abs a iflc + abs a ifgt + abs a ifcs + abs a iflt + abs a ifeq + abs a ifmi + abs a ifnr + abs a ifes + abs a ifls + abs a ifle + abs a ifhs + abs a iflo + + abs a ifcc.u ; >=56300 + abs a ifge.u + abs a ifne.u + abs a ifpl.u + abs a ifnn.u + abs a ifec.u + abs a iflc.u + abs a ifgt.u + abs a ifcs.u + abs a iflt.u + abs a ifeq.u + abs a ifmi.u + abs a ifnr.u + abs a ifes.u + abs a ifls.u + abs a ifle.u + abs a ifhs.u + abs a iflo.u + + illegal ; >=56000 + + inc a ; >=56002 + inc b + + insert a1,a0,a ; >=56300 + insert b1,a0,a + insert x0,a0,a + insert y0,a0,a + insert x1,a0,a + insert y1,a0,a + insert a1,b0,a + insert a1,x0,a + insert a1,y0,a + insert a1,x1,a + insert a1,y1,a + insert a1,a0,b + insert #345678,a0,a + insert #345678,b0,a + insert #345678,x0,a + insert #345678,y0,a + insert #345678,x1,a + insert #345678,y1,a + insert #345678,a0,b + + jcc $123 + jge $123456 + jne (r1)-n1 + jpl (r2)+n2 + jnn (r3)- + jec (r4)+ + jlc (r5) + jgt (r6+n6) + jcs -(r7) + jlt $123 + jeq $123456 + jmi (r1)-n1 + jnr (r2)+n2 + jes (r3)- + jls (r4)+ + jle (r5) + jhs (r6+n6) + jlo -(r7) + + jclr #2,x:(r1)-n1,* ; >=56000 + jclr #2,y:(r1)-n1,* + jclr #3,x:(r2)+n2,* + jclr #3,y:(r2)+n2,* + jclr #4,x:(r3)-,* + jclr #4,y:(r3)-,* + jclr #5,x:(r4)+,* + jclr #5,y:(r4)+,* + jclr #6,x:(r5),* + jclr #6,y:(r5),* + jclr #7,x:(r6+n6),* + jclr #7,y:(r6+n6),* + jclr #8,x:-(r7),* + jclr #8,y:-(r7),* + jclr #11,x:$20,* + jclr #11,y:$20,* + jclr #13,x:$ffffca,* + jclr #13,y:$ffffca,* + jclr #7,x:$ffff95,* ; >=56300 + jclr #7,y:$ffff95,* + jclr #10,r6,* ; >=56000 + jclr #10,b,* + + jmp $123 ; >=56000 + jmp $123456 + jmp (r1)-n1 + jmp (r2)+n2 + jmp (r3)- + jmp (r4)+ + jmp (r5) + jmp (r6+n6) + jmp -(r7) + + jscc $123 ; >=56000 + jsge $123456 + jsne (r1)-n1 + jspl (r2)+n2 + jsnn (r3)- + jsec (r4)+ + jslc (r5) + jsgt (r6+n6) + jscs -(r7) + jslt $123 + jseq $123456 + jsmi (r1)-n1 + jsnr (r2)+n2 + jses (r3)- + jsls (r4)+ + jsle (r5) + jshs (r6+n6) + jslo -(r7) + + jsclr #2,x:(r1)-n1,* ; >=56000 + jsclr #2,y:(r1)-n1,* + jsclr #3,x:(r2)+n2,* + jsclr #3,y:(r2)+n2,* + jsclr #4,x:(r3)-,* + jsclr #4,y:(r3)-,* + jsclr #5,x:(r4)+,* + jsclr #5,y:(r4)+,* + jsclr #6,x:(r5),* + jsclr #6,y:(r5),* + jsclr #7,x:(r6+n6),* + jsclr #7,y:(r6+n6),* + jsclr #8,x:-(r7),* + jsclr #8,y:-(r7),* + jsclr #11,x:$20,* + jsclr #11,y:$20,* + jsclr #13,x:$ffffca,* + jsclr #13,y:$ffffca,* + jsclr #7,x:$ffff95,* ; >=56300 + jsclr #7,y:$ffff95,* + jsclr #10,r6,* ; >=56000 + jsclr #10,b,* + + jset #2,x:(r1)-n1,* ; >=56000 + jset #2,y:(r1)-n1,* + jset #3,x:(r2)+n2,* + jset #3,y:(r2)+n2,* + jset #4,x:(r3)-,* + jset #4,y:(r3)-,* + jset #5,x:(r4)+,* + jset #5,y:(r4)+,* + jset #6,x:(r5),* + jset #6,y:(r5),* + jset #7,x:(r6+n6),* + jset #7,y:(r6+n6),* + jset #8,x:-(r7),* + jset #8,y:-(r7),* + jset #11,x:$20,* + jset #11,y:$20,* + jset #13,x:$ffffca,* + jset #13,y:$ffffca,* + jset #7,x:$ffff95,* ; >=56300 + jset #7,y:$ffff95,* + jset #10,r6,* ; >=56000 + jset #10,b,* + + jsr $123 ; >=56000 + jsr $123456 + jsr (r1)-n1 + jsr (r2)+n2 + jsr (r3)- + jsr (r4)+ + jsr (r5) + jsr (r6+n6) + jsr -(r7) + + jsset #2,x:(r1)-n1,* ; >=56000 + jsset #2,y:(r1)-n1,* + jsset #3,x:(r2)+n2,* + jsset #3,y:(r2)+n2,* + jsset #4,x:(r3)-,* + jsset #4,y:(r3)-,* + jsset #5,x:(r4)+,* + jsset #5,y:(r4)+,* + jsset #6,x:(r5),* + jsset #6,y:(r5),* + jsset #7,x:(r6+n6),* + jsset #7,y:(r6+n6),* + jsset #8,x:-(r7),* + jsset #8,y:-(r7),* + jsset #11,x:$20,* + jsset #11,y:$20,* + jsset #13,x:$ffffca,* + jsset #13,y:$ffffca,* + jsset #7,x:$ffff95,* ; >=56300 + jsset #7,y:$ffff95,* + jsset #10,r6,* ; >=56000 + jsset #10,b,* + + lra r3,x0 ; >=56000 + lra r3,x1 + lra r3,y0 + lra r3,y1 + lra r3,a0 + lra r3,b0 + lra r3,a2 + lra r3,b2 + lra r3,a1 + lra r3,b1 + lra r3,a + lra r3,b + lra r3,r5 + lra r3,n5 + + lra *+2,x0 ; >=56000 + lra *+2,x1 + lra *+2,y0 + lra *+2,y1 + lra *+2,a0 + lra *+2,b0 + lra *+2,a2 + lra *+2,b2 + lra *+2,a1 + lra *+2,b1 + lra *+2,a + lra *+2,b + lra *+2,r5 + lra *+2,n5 + + lsl a ; >=56000 + lsl b + lsl #$13,a ; >=56300 + lsl #$13,b + lsl a1,a + lsl b1,a + lsl x0,a + lsl y0,a + lsl x1,a + lsl y1,a + lsl a1,b + lsl b1,b + lsl x0,b + lsl y0,b + lsl x1,b + lsl y1,b + + lsr a ; >=56000 + lsr b + lsr #$13,a ; >=56300 + lsr #$13,b + lsr a1,a + lsr b1,a + lsr x0,a + lsr y0,a + lsr x1,a + lsr y1,a + lsr a1,b + lsr b1,b + lsr x0,b + lsr y0,b + lsr x1,b + lsr y1,b + + lua (r1)-n1,x0 ; >=56000 + lua (r2)+n2,x1 + lua (r3)-,y0 + lua (r4)+,y1 + lua (r5)-n5,a0 + lua (r6)+n6,b0 + lua (r7)-,a2 + lua (r1)+,b2 + lua (r2)-n2,a1 + lua (r3)+n3,b1 + lua (r4)-,a + lua (r5)+,b + lua (r6)-n6,r4 + lua (r7)+n7,n6 + lua (r2+20),r5 ; >=56300 + lua (r3-20),n7 + + mac +x0,x0,a ; >=56000 + mac -y0,y0,a + mac +x1,x0,b + mac -y1,y0,b + mac +x0,y1,a + mac -y0,x0,a + mac +x1,y0,b + mac -y1,x1,b + mac +y1,#8,a ; >=56300 + mac -x0,#32,a + mac +y0,#128,b + mac -x1,#(1<<22),b + + maci +#$123456,x0,a ; >=56300 + maci -#$234567,y0,a + maci +#$345678,x1,b + maci -#$456789,y1,b + + macsu +x0,x0,a ; >=56300 + macsu -y0,y0,a + macsu +x1,x0,b + macsu -y1,y0,b + macsu +x1,x1,a + macsu -y1,y1,a + macsu +x0,x1,b + macsu -y0,y1,b + macsu +x0,y1,a + macsu -y0,x0,a + macsu +x1,y0,b + macsu -y1,x1,b + macsu +y1,x0,a + macsu -x0,y0,a + macsu +y0,x1,b + macsu -x1,y1,b + + macuu +x0,x0,a ; >=56300 + macuu -y0,y0,a + macuu +x1,x0,b + macuu -y1,y0,b + macuu +x1,x1,a + macuu -y1,y1,a + macuu +x0,x1,b + macuu -y0,y1,b + macuu +x0,y1,a + macuu -y0,x0,a + macuu +x1,y0,b + macuu -y1,x1,b + macuu +y1,x0,a + macuu -x0,y0,a + macuu +y0,x1,b + macuu -x1,y1,b + + macr +x0,x0,a ; >=56000 + macr -y0,y0,a + macr +x1,x0,b + macr -y1,y0,b + macr +x0,y1,a + macr -y0,x0,a + macr +x1,y0,b + macr -y1,x1,b + macr +y1,#8,a ; >=56300 + macr -x0,#32,a + macr +y0,#128,b + macr -x1,#(1<<22),b + + macri +#$123456,x0,a ; >=56300 + macri -#$234567,y0,a + macri +#$345678,x1,b + macri -#$456789,y1,b + + max a,b ifne ; >=56300 + maxm a,b + + merge a1,a ; >=56300 + merge b1,a + merge x0,a + merge y0,a + merge x1,a + merge y1,a + merge a1,b + merge b1,b + merge x0,b + merge y0,b + merge x1,b + merge y1,b + + move ; >=56000 + + move #30,x0 ; >=56000 + move #31,x1 + move #32,y0 + move #33,y1 + move #34,a0 + move #35,b0 + move #36,a2 + move #37,b2 + move #38,a1 + move #39,b1 + move #40,a + move #41,b + move #42,r2 + move #43,n4 + + move n4,x0 ; >=56000 + move x0,x1 + move x1,y0 + move y0,y1 + move y1,a0 + move a0,b0 + move b0,a2 + move a2,b2 + move b2,a1 + move a1,b1 + move b1,a + move a,b + move b,r2 + move r2,n4 + + move (r1)-n1 ; >=56000 + move (r2)+n2 + move (r3)- + move (r4)+ + + move x:(r1)-n1,x0 ; >=56000 + move x:(r2)+n2,x1 + move x:(r3)-,y0 + move x:(r4)+,y1 + move x:(r5),a0 + move x:(r6+n6),b0 + move x:-(r7),a2 + move x:$123456,b2 + move x:#$123456,a1 + move x:$12,b1 + move a,x:(r1)-n1 + move b,x:(r2)+n2 + move r0,x:(r3)- + move r1,x:(r4)+ + move r2,x:(r5) + move r3,x:(r6+n6) + move r4,x:-(r7) + move r5,x:$123456 + move r6,x:$12 + move n0,x:$12 + + move x:(r1+30),x0 ; >=56300 + move x:(r2-30),x1 + move x:(r3+300),y0 + move x:(r4-300),y1 + move x:(r5+30),n2 + move x:(r6-30),n2 + move x0,x:(r1+30) ; >=56300 + move x1,x:(r2-30) + move y0,x:(r3+300) + move y1,x:(r4-300) + move n2,x:(r5+30) + move n2,x:(r6-30) + + move x0,x:(r1)-n1 a,y0 ; >=56000 + move x1,x:(r2)+n2 a,y1 + move a,x:(r3)- b,y0 + move b,x:(r4)+ b,y1 + move x:(r5),x0 a,y0 + move x:(r6+n6),x1 a,y1 + move x:-(r7),a b,y0 + move x:$123,b b,y1 + move #$1234,a a,y0 + + move a,x:(r1)-n1 x0,a ; >=56000 + move b,x:(r2)+n2 x0,b + + move y:(r1)-n1,x0 ; >=56000 + move y:(r2)+n2,x1 + move y:(r3)-,y0 + move y:(r4)+,y1 + move y:(r5),a0 + move y:(r6+n6),b0 + move y:-(r7),a2 + move y:$123456,b2 + move y:#$123456,a1 + move y:$12,b1 + move a,y:(r1)-n1 + move b,y:(r2)+n2 + move r0,y:(r3)- + move r1,y:(r4)+ + move r2,y:(r5) + move r3,y:(r6+n6) + move r4,y:-(r7) + move r5,y:$123456 + move r6,y:$12 + move n0,y:$12 + + move y:(r1+30),x0 ; >=56300 + move y:(r2-30),x1 + move y:(r3+300),y0 + move y:(r4-300),y1 + move y:(r5+30),n2 + move y:(r6-30),n2 + move x0,y:(r1+30) ; >=56300 + move x1,y:(r2-30) + move y0,y:(r3+300) + move y1,y:(r4-300) + move n2,y:(r5+30) + move n2,y:(r6-30) + + move a,x0 y0,y:(r1)-n1 ; >=56000 + move a,x1 y1,y:(r2)+n2 + move b,x0 a,y:(r3)- + move b,x1 b,y:(r4)+ + move a,x0 y:(r5),y0 + move a,x1 y:(r6+n6),y1 + move b,x0 y:-(r7),a + move b,x1 y:$123,b + move a,x0 #$1234,a + + move y0,a a,y:(r1)-n1 ; >=56000 + move y0,b b,y:(r2)+n2 + + move l:(r1)-n1,a10 ; >=56000 + move l:(r2)+n2,b10 + move l:(r3)-,x + move l:(r4)+,y + move l:(r5),a + move l:(r6+n6),b + move l:-(r7),ab + move l:$123456,ba + move l:$12,ba + + move a10,l:(r1)-n1 ; >=56000 + move b10,l:(r2)+n2 + move x,l:(r3)- + move y,l:(r4)+ + move a,l:(r5) + move b,l:(r6+n6) + move ab,l:-(r7) + move ba,l:$123456 + move ba,l:$12 + + move x:(r0)+n0,x0 y:(r4)+n4,y0 ; >=56000 + move x:(r1)-,x1 y:(r5)-,y1 + move x:(r2)+,a y:(r6)+,b + move x:(r3),b y:(r7),a + move x0,x:(r0)+n0 y0,y:(r4)+n4 + move x1,x:(r1)- y1,y:(r5)- + move a,x:(r2)+ b,y:(r6)+ + move b,x:(r3) a,y:(r7) + + movec x:(r1)-n1,m0 ; >=56000 + movec x:(r2)+n2,m1 + movec x:(r3)-,m2 + movec x:(r4)+,m3 + movec x:(r5),m4 + movec x:(r6+n6),m5 + movec x:-(r7),m6 + movec x:$123456,m7 + movec x:$12,ep + movec r4,vba + movec #$123456,sc + movec #$12,sz + movec y:(r1)-n1,sr + movec y:(r2)+n2,omr + movec y:(r3)-,sp + movec y:(r4)+,ssh + movec y:(r5),ssl + movec y:(r6+n6),la + movec y:-(r7),lc + + movec m0,x:(r1)-n1 ; >=56000 + movec m1,x:(r2)+n2 + movec m2,x:(r3)- + movec m3,x:(r4)+ + movec m4,x:(r5) + movec m5,x:(r6+n6) + movec m6,x:-(r7) + movec m7,x:$123456 + movec ep,x:$12 + movec vba,r4 + movec sr,y:(r1)-n1 + movec omr,y:(r2)+n2 + movec sp,y:(r3)- + movec ssh,y:(r4)+ + movec ssl,y:(r5) + movec la,y:(r6+n6) + movec lc,y:-(r7) + + movem r4,p:$123456 ; >=56000 + movem p:$123456,r4 + movem r4,p:$12 + movem p:$12,r4 + + movep x:$ffffd2,x:$123456 ; >=56000 + movep y:$ffffd2,x:$123456 + movep x:$ffffd2,y:$123456 + movep y:$ffffd2,y:$123456 + movep x:$123456,x:$ffffd2 + movep x:$123456,y:$ffffd2 + movep y:$123456,x:$ffffd2 + movep y:$123456,y:$ffffd2 + + movep x:$ffff92,x:$123456 + movep x:$ffff92,y:$123456 + movep x:$123456,x:$ffff92 + movep y:$123456,x:$ffff92 + + movep y:$ffff92,x:$123456 + movep y:$ffff92,y:$123456 + movep x:$123456,y:$ffff92 + movep y:$123456,y:$ffff92 + + movep x:$ffffd2,p:$123456 + movep y:$ffffd2,p:$123456 + movep p:$123456,x:$ffffd2 + movep p:$123456,y:$ffffd2 + + movep x:$ffff92,p:$123456 + movep y:$ffff92,p:$123456 + movep p:$123456,x:$ffff92 + movep p:$123456,y:$ffff92 + + movep x:$ffffd2,r4 + movep y:$ffffd2,r4 + movep r4,x:$ffffd2 + movep r4,y:$ffffd2 + + movep x:$ffff92,r4 + movep y:$ffff92,r4 + movep r4,x:$ffff92 + movep r4,y:$ffff92 + + mpy +x0,x0,a ; >=56000 + mpy -y0,y0,a + mpy +x1,x0,b + mpy -y1,y0,b + mpy +x0,y1,a + mpy -y0,x0,a + mpy +x1,y0,b + mpy -y1,x1,b + mpy +y1,#8,a ; >=56300 + mpy -x0,#32,a + mpy +y0,#128,b + mpy -x1,#(1<<22),b + + mpysu +x0,x0,a ; >=56300 + mpysu -y0,y0,a + mpysu +x1,x0,b + mpysu -y1,y0,b + mpysu +x1,x1,a + mpysu -y1,y1,a + mpysu +x0,x1,b + mpysu -y0,y1,b + mpysu +x0,y1,a + mpysu -y0,x0,a + mpysu +x1,y0,b + mpysu -y1,x1,b + mpysu +y1,x0,a + mpysu -x0,y0,a + mpysu +y0,x1,b + mpysu -x1,y1,b + + mpyuu +x0,x0,a ; >=56300 + mpyuu -y0,y0,a + mpyuu +x1,x0,b + mpyuu -y1,y0,b + mpyuu +x1,x1,a + mpyuu -y1,y1,a + mpyuu +x0,x1,b + mpyuu -y0,y1,b + mpyuu +x0,y1,a + mpyuu -y0,x0,a + mpyuu +x1,y0,b + mpyuu -y1,x1,b + mpyuu +y1,x0,a + mpyuu -x0,y0,a + mpyuu +y0,x1,b + mpyuu -x1,y1,b + + mpyi +#$123456,x0,a ; >=56300 + mpyi -#$234567,y0,a + mpyi +#$345678,x1,b + mpyi -#$456789,y1,b + + mpyr +x0,x0,a ; >=56000 + mpyr -y0,y0,a + mpyr +x1,x0,b + mpyr -y1,y0,b + mpyr +x0,y1,a + mpyr -y0,x0,a + mpyr +x1,y0,b + mpyr -y1,x1,b + mpyr +y1,#8,a ; >=56300 + mpyr -x0,#32,a + mpyr +y0,#128,b + mpyr -x1,#(1<<22),b + + mpyri +#$123456,x0,a ; >=56300 + mpyri -#$234567,y0,a + mpyri +#$345678,x1,b + mpyri -#$456789,y1,b + + neg a ; >=56000 + neg b + + nop + + norm r2,a ; >=56000 + norm r4,b + + normf a1,a ; >=56300 + normf b1,a + normf x0,a + normf y0,a + normf x1,a + normf y1,a + normf a1,b + normf b1,b + normf x0,b + normf y0,b + normf x1,b + normf y1,b + + not a ; >=56000 + not b + + or x0,a ; >=56000 + or x1,a + or y0,a + or y1,a + or x0,b + or x1,b + or y0,b + or y1,b + + or #31,a ; >=56000 + or #1234,a + or #31,b + or #1234,b + + ori #$12,mr ; >=56000 + ori #$12,ccr + ori #$12,com + ori #$12,eom + + pflush ; >=56300 + pflushun + pfree + plock $123456 + plockr * + punlockr * + + rep x:(r1)-n1 ; >=56000 + rep x:(r2)+n2 + rep x:(r3)- + rep x:(r4)+ + rep x:(r5) + rep x:(r6+n6) + rep x:-(r7) + rep x:$12 + rep y:(r1)-n1 + rep y:(r2)+n2 + rep y:(r3)- + rep y:(r4)+ + rep y:(r5) + rep y:(r6+n6) + rep y:-(r7) + rep y:$12 + rep r4 + rep #$234 + + reset ; >=56000 + + rnd a ; >=56000 + rnd b + + rol a ; >=56000 + rol b + + ror a ; >=56000 + ror b + + rti ; >=56000 + rts + + sbc x,a ; >=56000 + sbc y,a + sbc x,b + sbc y,b + + stop ; >=56000 + + sub x0,a ; >=56000 + sub x1,a + sub y0,a + sub y1,a + sub x,a + sub y,a + sub b,a + sub x0,b ; >=56000 + sub x1,b + sub y0,b + sub y1,b + sub x,b + sub y,b + sub a,b + + sub #31,a ; >=56300 + sub #1234,a + sub #31,b + sub #1234,b + + subl b,a ; >=56000 + subl a,b + + subr b,a ; >=56000 + subr a,b + + tne b,a ; >=56000 + tne x0,a + tne y0,a + tne x1,a + tne y1,a + tne a,b + tne x0,b + tne y0,b + tne x1,b + tne y1,b + + tne r2,r3 ; >=56000 + + tne y1,b r2,r3 ; >=56000 + + tfr b,a ; >=56000 + tfr x0,a + tfr y0,a + tfr x1,a + tfr y1,a + tfr a,b + tfr x0,b + tfr y0,b + tfr x1,b + tfr y1,b + + trap ; >=56300 + + trapcc ; >=56300 + trapge + trapne + trappl + trapnn + trapec + traplc + trapgt + trapcs + traplt + trapeq + trapmi + trapnr + trapes + trapls + traple + traphs + traplo + + tst a ; >=56000 + tst b + + wait + diff --git a/tests/t_56300/t_56300.doc b/tests/t_56300/t_56300.doc new file mode 100644 index 0000000..9798c65 --- /dev/null +++ b/tests/t_56300/t_56300.doc @@ -0,0 +1,6 @@ ++---------------------- Test Application 56300 ----------------------------+ +| | +| This is a (synthetic but halfway complete) test of the DSP563xx's | +| instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_56300/t_56300.ori b/tests/t_56300/t_56300.ori new file mode 100644 index 0000000..2418ca4 Binary files /dev/null and b/tests/t_56300/t_56300.ori differ diff --git a/tests/t_65/asflags b/tests/t_65/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_65/t_65.asm b/tests/t_65/t_65.asm new file mode 100755 index 0000000..0b9d3bc --- /dev/null +++ b/tests/t_65/t_65.asm @@ -0,0 +1,283 @@ + cpu melps740 + + adc #$12 + adc $12 + adc $12,x + adc $12,y + adc $1234 + adc $1234,x + adc $1234,y + adc ($12,x) + adc ($12),y + + and #$12 + and $12 + and $12,x + and $12,y + and $1234 + and $1234,x + and $1234,y + and ($12,x) + and ($12),y + + asl + asl a + asl $12 + asl $12,x + asl $1234 + asl $1234,x + + bbc 3,a,* + bbc 4,$12,* + + bbs 5,a,* + bbs 6,$12,*+1 + + bcc *+2 + bcs *+3 + beq *+4 + + bit $12 + bit $1234 + + bmi *+5 + bne *+6 + bpl *+7 + bra *+8 + + brk + + bvc *+9 + bvs *+10 + + clb 2,a + clb 3,$12 + + clc + cld + cli + clt + clv + + cmp #$12 + cmp $12 + cmp $12,x + cmp $12,y + cmp $1234 + cmp $1234,x + cmp $1234,y + cmp ($12,x) + cmp ($12),y + + com $12 + + cpx #$12 + cpx $12 + cpx $1234 + + cpy #$12 + cpy $12 + cpy $1234 + + dec + dec a + dec $12 + dec $12,x + dec $1234 + dec $1234,x + + dex + dey + + div $12,x + + eor #$12 + eor $12 + eor $12,x + eor $12,y + eor $1234 + eor $1234,x + eor $1234,y + eor ($12,x) + eor ($12),y + + fst + + inc + inc a + inc $12 + inc $12,x + inc $1234 + inc $1234,x + + inx + iny + + jmp $1234 + jmp ($1234) + jmp ($12) + + assume sp:$12 + jsr $1234 + jsr \$1234 + jsr ($12) + + lda #$12 + lda $12 + lda $12,x + lda $12,y + lda $1234 + lda $1234,x + lda $1234,y + lda ($12,x) + lda ($12),y + + ldm #$12,$34 + + ldx #$12 + ldx $12 + ldx $12,y + ldx $1234 + ldx $1234,y + + ldy #$12 + ldy $12 + ldy $12,x + ldy $1234 + ldy $1234,x + + lsr + lsr a + lsr $12 + lsr $12,x + lsr $1234 + lsr $1234,x + + mul $12,x + + nop + + ora #$12 + ora $12 + ora $12,x + ora $12,y + ora $1234 + ora $1234,x + ora $1234,y + ora ($12,x) + ora ($12),y + + pha + php + pla + plp + + rol + rol a + rol $12 + rol $12,x + rol $1234 + rol $1234,x + + ror + ror a + ror $12 + ror $12,x + ror $1234 + ror $1234,x + + rrf $12 + + rti + rts + + sbc #$12 + sbc $12 + sbc $12,x + sbc $12,y + sbc $1234 + sbc $1234,x + sbc $1234,y + sbc ($12,x) + sbc ($12),y + + seb 2,a + seb 3,$12 + + sec + sed + sei + set + + slw + + sta $12 + sta $12,x + sta $12,y + sta $1234 + sta $1234,x + sta $1234,y + sta ($12,x) + sta ($12),y + + stp + + stx $12 + stx $12,y + stx $1234 + + sty $12 + sty $12,x + sty $1234 + + tax + tay + + tst $12 + + tsx + txa + txs + tya + + wit + + cpu 65c02 + + dec a + inc a + plx + ply + phx + phy + + tsb $12 + trb $12 + tsb $1234 + trb $1234 + + stz $12 + stz $1234 + stz $12,x + stz $1234,x + + bit $12,x + bit $1234,x + bit #$12 + + lda ($12) + sta ($12) + adc ($12) + sbc ($12) + and ($12) + ora ($12) + eor ($12) + cmp ($12) + + jmp ($12,x) + + bbr2 $12,* + bbs4 $12,* + + rmb3 $12 + smb5 $12 diff --git a/tests/t_65/t_65.doc b/tests/t_65/t_65.doc new file mode 100644 index 0000000..6d7cba0 --- /dev/null +++ b/tests/t_65/t_65.doc @@ -0,0 +1,5 @@ ++-------------------------- Test Application 65 -----------------------------+ +| | +| This is a (synthetic) test of the 65xx/MELPS-740 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_65/t_65.ori b/tests/t_65/t_65.ori new file mode 100755 index 0000000..2ff599b Binary files /dev/null and b/tests/t_65/t_65.ori differ diff --git a/tests/t_6502u/asflags b/tests/t_6502u/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_6502u/t_6502u.asm b/tests/t_6502u/t_6502u.asm new file mode 100644 index 0000000..337b5d1 --- /dev/null +++ b/tests/t_6502u/t_6502u.asm @@ -0,0 +1,110 @@ + cpu 6502undoc + + nop + nop #$12 + nop $12 + nop $12,x + nop $1234 + nop $1234,x + + jam + crs + kil + + slo $12 + slo $12,x + slo $1234 + slo $1234,x + slo $12,y + slo $1234,y + slo ($12,x) + slo ($12),y + + anc #$12 + + rla $12 + rla $12,x + rla $1234 + rla $1234,x + rla $12,y + rla $1234,y + rla ($12,x) + rla ($12),y + + sre $12 + sre $12,x + sre $1234 + sre $1234,x + sre $12,y + sre $1234,y + sre ($12,x) + sre ($12),y + + asr #$12 + + rra $12 + rra $12,x + rra $1234 + rra $1234,x + rra $12,y + rra $1234,y + rra ($12,x) + rra ($12),y + + arr #$12 + + sax $12 + sax $12,y + sax $1234 + sax ($12,x) + + ane #$12 + + sha $12,x + sha $1234,x + sha $12,y + sha $1234,y + + shs $12,y + shs $1234,y + + shy $12,y + shy $1234,y + + shx $12,x + shx $1234,x + + lax $12 + lax $12,y + lax $1234 + lax $1234,y + lax ($12,x) + lax ($12),y + + lxa #$12 + + lae $12,y + lae $1234,y + + dcp $12 + dcp $12,x + dcp $1234 + dcp $1234,x + dcp $12,y + dcp $1234,y + dcp ($12,x) + dcp ($12),y + + sbx #$12 + + isb $12 + isb $12,x + isb $1234 + isb $1234,x + isb $12,y + isb $1234,y + isb ($12,x) + isb ($12),y + + end * + diff --git a/tests/t_6502u/t_6502u.doc b/tests/t_6502u/t_6502u.doc new file mode 100644 index 0000000..62849cc --- /dev/null +++ b/tests/t_6502u/t_6502u.doc @@ -0,0 +1,7 @@ ++------------------------ Test Application 6502U ----------------------------+ +| | +| Hacker's corner: This tests the 'undocumented' instructions of the 6502/ | +| 6510 processor, i.e. the things the processor does when yuo use undocu- | +| mented opcode bytes. I do not recommend that, but it's your program... | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_6502u/t_6502u.ori b/tests/t_6502u/t_6502u.ori new file mode 100644 index 0000000..1e4282a Binary files /dev/null and b/tests/t_6502u/t_6502u.ori differ diff --git a/tests/t_6804/asflags b/tests/t_6804/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_6804/t_6804.asm b/tests/t_6804/t_6804.asm new file mode 100644 index 0000000..78da533 --- /dev/null +++ b/tests/t_6804/t_6804.asm @@ -0,0 +1,72 @@ + cpu 6804 + + include stddef04.inc + + clra + clrx + clry + coma + rola + asla + inca + incx + incy + deca + decx + decy + tax + tay + txa + tya + rts + rti + nop + +targ: beq targ + bne targ + blo targ + bcs targ + bhs targ + bcc targ + + jmp $123 + jsr $456 + + add (x) + add (y) + add $30 + add #$40 + sub (x) + sub (y) + sub $50 + sub #$60 + cmp (x) + cmp (y) + cmp $70 + cmp #$80 + and (x) + and (y) + and $90 + and #$a0 + + lda (x) + sta (y) + lda $82 + sta $40 + lda #55 + + ldxi #0 + ldyi #-1 + + mvi $12,#$45 + + dec $82 + inc $40 + dec (y) + inc (x) + + bset 1,$12 + bclr 3,$34 + + brset 5,$56,targ + brclr 7,$78,targ diff --git a/tests/t_6804/t_6804.doc b/tests/t_6804/t_6804.doc new file mode 100644 index 0000000..3fc32a7 --- /dev/null +++ b/tests/t_6804/t_6804.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 6804 ----------------------------+ +| | +| This is a (synthetic) test of the 6804's instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_6804/t_6804.ori b/tests/t_6804/t_6804.ori new file mode 100644 index 0000000..ecaff8c Binary files /dev/null and b/tests/t_6804/t_6804.ori differ diff --git a/tests/t_68040/asflags b/tests/t_68040/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_68040/t_68040.asm b/tests/t_68040/t_68040.asm new file mode 100644 index 0000000..b356a56 --- /dev/null +++ b/tests/t_68040/t_68040.asm @@ -0,0 +1,29 @@ + cpu 68040 + supmode on + pmmu on + + move16 (a1)+,(a3)+ + move16 (a4)+,$1234 + move16 $12345,(a5)+ + move16 (a6),$12345 + move16 $1234,(a7) + + cinva dc + cinva ic + cinva dc/ic + cinvl dc/ic,(a1) + cinvp dc/ic,(a2) + cpusha dc + cpusha ic + cpusha ic/dc + cpushl dc/ic,(a3) + cpushp dc/ic,(a4) + + pflushn (a2) + pflush (a3) + pflushan + pflusha + + ptestw (a2) + ptestr (a4) + diff --git a/tests/t_68040/t_68040.doc b/tests/t_68040/t_68040.doc new file mode 100644 index 0000000..29ec852 --- /dev/null +++ b/tests/t_68040/t_68040.doc @@ -0,0 +1,6 @@ ++------------------------ Test Application 68040 ----------------------------+ +| | +| This is a (synthetic) test of the 68040's extensions to the 680x0 | +| instruction set. | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_68040/t_68040.ori b/tests/t_68040/t_68040.ori new file mode 100644 index 0000000..3b5f3ac Binary files /dev/null and b/tests/t_68040/t_68040.ori differ diff --git a/tests/t_6805/asflags b/tests/t_6805/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_6805/t_6805.asm b/tests/t_6805/t_6805.asm new file mode 100755 index 0000000..cbd5697 --- /dev/null +++ b/tests/t_6805/t_6805.asm @@ -0,0 +1,244 @@ + cpu 6805 + page 0 + + brset0 $12,* + brset1 $12,*+1 + brset2 $12,*+2 + brset3 $12,*+3 + brset4 $12,*+4 + brset5 $12,*+5 + brset6 $12,*+6 + brset7 $12,*+7 + brclr0 $12,*+8 + brclr1 $12,*+9 + brclr2 $12,*+10 + brclr3 $12,*+11 + brclr4 $12,*+12 + brclr5 $12,*+13 + brclr6 $12,*+14 + brclr7 $12,*+15 + + bset0 $12 + bset1 $12 + bset2 $12 + bset3 $12 + bset4 $12 + bset5 $12 + bset6 $12 + bset7 $12 + bclr0 $12 + bclr1 $12 + bclr2 $12 + bclr3 $12 + bclr4 $12 + bclr5 $12 + bclr6 $12 + bclr7 $12 + + bra *-1 + brn *-2 + bhi *-3 + bls *-4 + bcc *-5 + bcs *-6 + bne *-7 + beq *-8 + bhcc *-9 + bhcs *-10 + bpl *-11 + bmi *-12 + bmc *-13 + bms *-14 + bil *-15 + bih *-16 + + neg $12 + nega + negx + neg $12,x + neg x + + com $12 + coma + comx + com $12,x + com x + + lsr $12 + lsra + lsrx + lsr $12,x + lsr x + + ror $12 + rora + rorx + ror $12,x + ror x + + asr $12 + asra + asrx + asr $12,x + asr x + + lsl $12 + lsla + lslx + lsl $12,x + lsl x + + rol $12 + rola + rolx + rol $12,x + rol x + + dec $12 + deca + decx + dec $12,x + dec x + + inc $12 + inca + incx + inc $12,x + inc x + + tst $12 + tsta + tstx + tst $12,x + tst x + + clr $12 + clra + clrx + clr $12,x + clr x + + mul + rti + rts + swi + tax + clc + sec + cli + sei + rsp + nop + stop + wait + txa + + sub #$12 + sub $12 + sub $1234 + sub $1234,x + sub $12,x + sub x + + cmp #$12 + cmp $12 + cmp $1234 + cmp $1234,x + cmp $12,x + cmp x + + cpx #$12 + cpx $12 + cpx $1234 + cpx $1234,x + cpx $12,x + cpx x + + sbc #$12 + sbc $12 + sbc $1234 + sbc $1234,x + sbc $12,x + sbc x + + and #$12 + and $12 + and $1234 + and $1234,x + and $12,x + and x + + bit #$12 + bit $12 + bit $1234 + bit $1234,x + bit $12,x + bit x + + lda #$12 + lda $12 + lda $1234 + lda $1234,x + lda $12,x + lda x + + sta $12 + sta $1234 + sta $1234,x + sta $12,x + sta x + + eor #$12 + eor $12 + eor $1234 + eor $1234,x + eor $12,x + eor x + + adc #$12 + adc $12 + adc $1234 + adc $1234,x + adc $12,x + adc x + + ora #$12 + ora $12 + ora $1234 + ora $1234,x + ora $12,x + ora x + + add #$12 + add $12 + add $1234 + add $1234,x + add $12,x + add x + + jmp $12 + jmp $1234 + jmp $1234,x + jmp $12,x + jmp x + + bsr * + jsr $12 + jsr $1234 + jsr $1234,x + jsr $12,x + jsr x + + ldx #$12 + ldx $12 + ldx $1234 + ldx $1234,x + ldx $12,x + ldx x + + stx $12 + stx $1234 + stx $1234,x + stx $12,x + stx x + diff --git a/tests/t_6805/t_6805.doc b/tests/t_6805/t_6805.doc new file mode 100644 index 0000000..dd38f44 --- /dev/null +++ b/tests/t_6805/t_6805.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 6805 ----------------------------+ +| | +| This is a (synthetic) test of the 6805 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_6805/t_6805.ori b/tests/t_6805/t_6805.ori new file mode 100755 index 0000000..b60907f Binary files /dev/null and b/tests/t_6805/t_6805.ori differ diff --git a/tests/t_6808/asflags b/tests/t_6808/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_6808/t_6808.asm b/tests/t_6808/t_6808.asm new file mode 100644 index 0000000..0143d90 --- /dev/null +++ b/tests/t_6808/t_6808.asm @@ -0,0 +1,406 @@ + cpu 68HC08 + page 0 + + adc #$55 + adc $20 + adc <$20 + adc >$20 + adc $2030 + adc >$2030 + adc ,x + adc 0,x + adc <0,x + adc $40,x + adc <$40,x + adc >$40,x + adc $4050,x + adc >$4050,x + adc ,sp + adc 0,sp + adc <0,sp + adc $40,sp + adc <$40,sp + adc >$40,sp + adc $4050,sp + adc >$4050,sp + + add #$55 + add $20 + add $2030 + add ,x + add $40,x + add $4050,x + add $40,sp + add $4050,sp + + aix #34 + + ais #-16 + + and #$55 + and $20 + and $2030 + and ,x + and $40,x + and $4050,x + and $40,sp + and $4050,sp + + asla + aslx + asl $20 + asl ,x + asl $40,x + asl $40,sp + + asra + asrx + asr $20 + asr ,x + asr $40,x + asr $40,sp + + bcc * + + bclr 0,$20 + bclr 1,$20 + bclr 2,$20 + bclr 3,$20 + bclr 4,$20 + bclr 5,$20 + bclr 6,$20 + bclr 7,$20 + + bcs * + + beq * + + bge * + + bgt * + + bhcc * + + bhcs * + + bhi * + + bhs * + + bih * + + bil * + + bit #$55 + bit $20 + bit $2030 + bit ,x + bit $40,x + bit $4050,x + bit $40,sp + bit $4050,sp + + ble * + + blo * + + bls * + + blt * + + bmc * + + bmi * + + bms * + + bne * + + bpl * + + bra * + + brclr 0,$20,* + brclr 1,$20,* + brclr 2,$20,* + brclr 3,$20,* + brclr 4,$20,* + brclr 5,$20,* + brclr 6,$20,* + brclr 7,$20,* + + brn * + + brset 0,$20,* + brset 1,$20,* + brset 2,$20,* + brset 3,$20,* + brset 4,$20,* + brset 5,$20,* + brset 6,$20,* + brset 7,$20,* + + bset 0,$20 + bset 1,$20 + bset 2,$20 + bset 3,$20 + bset 4,$20 + bset 5,$20 + bset 6,$20 + bset 7,$20 + + bsr * + + cbeq $20,* + cbeq x+,* + cbeq $40,x+,* + cbeq $40,sp,* + + cbeqa #$55,* + cbeqx #$66,* + + clc + + cli + + clra + clrx + clrh + clr $20 + clr ,x + clr $40,x + clr $40,sp + + cmp #$55 + cmp $20 + cmp $2030 + cmp ,x + cmp $40,x + cmp $4050,x + cmp $40,sp + cmp $4050,sp + + coma + comx + com $20 + com ,x + com $40,x + com $40,sp + + cphx #$55aa + cphx $20 + + cpx #$55 + cpx $20 + cpx $2030 + cpx ,x + cpx $40,x + cpx $4050,x + cpx $40,sp + cpx $4050,sp + + daa + + dbnza * + dbnzx * + + dbnz $20,* + dbnz x,* + dbnz $40,x,* + dbnz $40,sp,* + + deca + decx + dec $20 + dec ,x + dec $40,x + dec $40,sp + + div + + eor #$55 + eor $20 + eor $2030 + eor ,x + eor $40,x + eor $4050,x + eor $40,sp + eor $4050,sp + + inca + incx + inc $20 + inc ,x + inc $40,x + inc $40,sp + + jmp $20 + jmp $2030 + jmp ,x + jmp $40,x + jmp $4050,x + + jsr $20 + jsr $2030 + jsr ,x + jsr $40,x + jsr $4050,x + + lda #$55 + lda $20 + lda $2030 + lda ,x + lda $40,x + lda $4050,x + lda $40,sp + lda $4050,sp + + ldhx #$55aa + ldhx $20 + + ldx #$55 + ldx $20 + ldx $2030 + ldx ,x + ldx $40,x + ldx $4050,x + ldx $40,sp + ldx $4050,sp + + lsla + lslx + lsl $20 + lsl ,x + lsl $40,x + lsl $40,sp + + lsra + lsrx + lsr $20 + lsr ,x + lsr $40,x + lsr $40,sp + + mov #$55,$20 + mov $20,$40 + mov x+,$20 + mov $40,x+ + + mul + + nega + negx + neg $20 + neg ,x + neg $40,x + neg $40,sp + + nop + + nsa + + ora #$55 + ora $20 + ora $2030 + ora ,x + ora $40,x + ora $4050,x + ora $40,sp + ora $4050,sp + + psha + + pshh + + pshx + + pula + + pulh + + pulx + + rola + rolx + rol $20 + rol ,x + rol $40,x + rol $40,sp + + rora + rorx + ror $20 + ror ,x + ror $40,x + ror $40,sp + + rsp + + rti + + rts + + sbc #$55 + sbc $20 + sbc $2030 + sbc ,x + sbc $40,x + sbc $4050,x + sbc $40,sp + sbc $4050,sp + + sec + + sei + + sta $20 + sta $2030 + sta ,x + sta $40,x + sta $4050,x + sta $40,sp + sta $4050,sp + + sthx $20 + + stop + + stx $20 + stx $2030 + stx ,x + stx $40,x + stx $4050,x + stx $40,sp + stx $4050,sp + + sub #$55 + sub $20 + sub $2030 + sub ,x + sub $40,x + sub $4050,x + sub $40,sp + sub $4050,sp + + swi + + tap + + tax + + tpa + + tsta + tstx + tst $20 + tst ,x + tst $40,x + tst $40,sp + + tsx + + txa + + txs + + wait diff --git a/tests/t_6808/t_6808.doc b/tests/t_6808/t_6808.doc new file mode 100644 index 0000000..714175b --- /dev/null +++ b/tests/t_6808/t_6808.doc @@ -0,0 +1,6 @@ ++------------------------- Test Application 6808 ----------------------------+ +| | +| This is a (synthetic) test of the 68HC08's extensions to the 6805 | +| basic instruction set. | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_6808/t_6808.ori b/tests/t_6808/t_6808.ori new file mode 100644 index 0000000..ca94eea Binary files /dev/null and b/tests/t_6808/t_6808.ori differ diff --git a/tests/t_6812/asflags b/tests/t_6812/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_6812/t_6812.asm b/tests/t_6812/t_6812.asm new file mode 100644 index 0000000..35c547e --- /dev/null +++ b/tests/t_6812/t_6812.asm @@ -0,0 +1,644 @@ + cpu 68hc12 + page 0 + + aba + + abx + + aby + + adca #45 + adca $45 + adca $1234 + adca >$45 + adca ,y + adca 5,x + adca -5,sp + adca *,pc + adca *+10,pc + adca *+17,pc + adca a,y + adca b,sp + adca d,pc + adca 55,y + adca -55,sp + adca <5,y + adca <-5,sp + adca *+18,pc + adca *+258,pc + adca 555,y + adca -555,sp + adca >55,y + adca >-55,sp + adca *+259,pc + adca [d,sp] + adca [d,x] + adca [-5,y] + adca [500,y] + adca 4,+y + adca 4,y+ + adca 4,-y + adca 4,y- + + adcb #55 + adcb $55 + adcb ,x + adcb $1234 + + adda #55 + adda $55 + adda ,x + adda $1234 + + addb #55 + addb $55 + addb ,x + addb $1234 + + addd #55 + addd $55 + addd ,x + addd $1234 + + anda #55 + anda $55 + anda ,x + anda $1234 + + andb #55 + andb $55 + andb ,x + andb $1234 + + andcc #$fe + + asl $55 + asl ,x + asl $1234 + + asla + + aslb + + asld + + asr $55 + asr ,x + asr $1234 + + asra + + asrb + + bcc * + + bclr $20 #$40 + bclr $20,#$40 + bclr $1234 #$40 + bclr $1234,#$40 + bclr ,x $40 + bclr $20,y,$40 + bclr *,pc,$40 + + bcs * + + beq * + + bge * + + bgnd + + bgt * + + bhi * + + bhs * + + bita #$55 + bita $55 + bita ,x + bita $1234 + + bitb #$55 + bitb $55 + bitb ,x + bitb $1234 + + ble * + + blo * + + bls * + + blt * + + bmi * + + bne * + + bpl * + + bra * + + brclr $20 #$40 * + brclr $2000,#$40,* + brclr ,x,#$40,* + brclr *,pc,#$40,* + + brn * + + brset $20 #$40 * + brset $2000,#$40,* + brset ,x,#$40,* + brset *,pc,#$40,* + + bset $20 #$40 + bset $20,#$40 + bset $1234 #$40 + bset $1234,#$40 + bset ,x $40 + bset $20,y,$40 + + bsr * + + bvc * + + bvs * + + call $2000,5 + call 5,y,6 + call 200,y,7 + call 20000,y,8 + call [d,y] + call [20,y] + + cba + + clc + andcc #$fe + + cli + andcc #$ef + + clr $55 + clr ,x + clr $1234 + + clra + + clrb + + clv + andcc #$fd + + cmpa #55 + cmpa $55 + cmpa ,x + cmpa $1234 + + cmpb #55 + cmpb $55 + cmpb ,x + cmpb $1234 + + com $55 + com ,x + com $1234 + + coma + + comb + + cpd #55 + cpd $55 + cpd ,x + cpd $1234 + + cps #55 + cps $55 + cps ,x + cps $1234 + + cpx #55 + cpx $55 + cpx ,x + cpx $1234 + + cpy #55 + cpy $55 + cpy ,x + cpy $1234 + + daa + + dbeq x,* + + dbne x,* + + dec $55 + dec ,x + dec $1234 + + deca + + decb + + des + leas -1,sp + + dex + + dey + + ediv + + edivs + + emacs $1234 + + emaxd ,x + + emaxm ,x + + emind ,x + + eminm ,x + + emul + + emuls + + eora #55 + eora $55 + eora ,x + eora $1234 + + eorb #55 + eorb $55 + eorb ,x + eorb $1234 + + etbl 5,y + + exg ccr,sp + + fdiv + + ibeq a,* + + ibne a,* + + idiv + + idivs + + inc $55 + inc ,x + inc $1234 + + inca + + incb + + ins + leas 1,sp + + inx + + iny + + jmp $2000 + jmp $20 + jmp [d,x] + + jsr $2000 + jsr $20 + jsr [d,x] + + lbcc * + + lbcs * + + lbeq * + + lbge * + + lbgt * + + lbhi * + + lbhs * + + lble * + + lblo * + + lbls * + + lblt * + + lbmi * + + lbne * + + lbpl * + + lbra * + + lbrn * + + lbvc * + + lbvs * + + ldaa #55 + ldaa $55 + ldaa ,x + ldaa $1234 + + ldab #55 + ldab $55 + ldab ,x + ldab $1234 + + ldd #55 + ldd $55 + ldd ,x + ldd $1234 + + lds #55 + lds $55 + lds ,x + lds $1234 + + ldx #55 + ldx $55 + ldx ,x + ldx $1234 + + ldy #55 + ldy $55 + ldy ,x + ldy $1234 + + leas 2000,sp + + leax ,y + + leay ,x + + lsl $55 + lsl ,x + lsl $1234 + + lsla + + lslb + + lsld + + lsr $55 + lsr ,x + lsr $1234 + + lsra + + lsrb + + lsrd + + maxa ,x + + maxm ,x + + mem + + mina ,x + + minm ,x + + movb #$55 $1234 + movb #$55,$1234 + movb #$55 2,y + movb #$55,2,y + movb #$55,next_a,pc +next_a: movb $1234 $3456 + movb $1234,$3456 + movb $1234 2,y + movb $1234,2,y + movb $1234,next_b,pc +next_b: movb 2,y $1234 + movb 2,y,$1234 + movb next_c,pc,$1234 +next_c: movb 2,y 2,y + movb 2,y,2,y + movb next_d,pc next_d,pc +next_d: + movw #$55 $1234 + movw #$55,$1234 + movw #$55 2,y + movw #$55,2,y + movw #$55,next_e,pc +next_e: movw $1234 $3456 + movw $1234,$3456 + movw $1234 2,y + movw $1234,2,y + movw $1234,next_f,pc +next_f: movw 2,y $1234 + movw 2,y,$1234 + movw next_g,pc,$1234 +next_g: movw 2,y 2,y + movw 2,y,2,y + movw next_h,pc next_h,pc +next_h: + + mul + + neg $55 + neg ,x + neg $1234 + + nega + + negb + + nop + + oraa #55 + oraa $55 + oraa ,x + oraa $1234 + + orab #55 + orab $55 + orab ,x + orab $1234 + + orcc #$10 + + psha + + pshb + + pshc + + pshd + + pshx + + pshy + + pula + + pulb + + pulc + + puld + + pulx + + puly + + rev + + revw + + rol $55 + rol ,x + rol $1234 + + rola + + rolb + + ror $55 + ror ,x + ror $1234 + + rora + + rorb + + rtc + + rti + + rts + + sba + + sbca #55 + sbca $55 + sbca ,x + sbca $1234 + + sbcb #55 + sbcb $55 + sbcb ,x + sbcb $1234 + + sec + orcc #$01 + + sei + orcc #$10 + + sev + orcc #$02 + + sex a,d + + staa $55 + staa ,x + staa $1234 + + stab $55 + stab ,x + stab $1234 + + std $55 + std ,x + std $1234 + + sts $55 + sts ,x + sts $1234 + + stx $55 + stx ,x + stx $1234 + + sty $55 + sty ,x + sty $1234 + + stop + + suba #55 + suba $55 + suba ,x + suba $1234 + + subb #55 + subb $55 + subb ,x + subb $1234 + + subd #55 + subd $55 + subd ,x + subd $1234 + + swi + + tab + + tap + tfr a,ccr + + tba + + tbeq d,* + + tbl a,x + + tbne d,* + + tfr a,b + tfr x,y + + tpa + tfr ccr,a + + trap #$42 + + tst $55 + tst ,x + tst $1234 + + tsta + + tstb + + tsx + tfr sp,x + + tsy + tfr sp,y + + txs + tfr x,sp + + tys + tfr y,sp + + wai + + wav + + xgdx + exg d,x + + xgdy + exg d,y diff --git a/tests/t_6812/t_6812.doc b/tests/t_6812/t_6812.doc new file mode 100644 index 0000000..ed4a23a --- /dev/null +++ b/tests/t_6812/t_6812.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 6812 ----------------------------+ +| | +| This is a (synthetic) test of the 68HC12 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_6812/t_6812.ori b/tests/t_6812/t_6812.ori new file mode 100644 index 0000000..b57d4cd Binary files /dev/null and b/tests/t_6812/t_6812.ori differ diff --git a/tests/t_6816/asflags b/tests/t_6816/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_6816/t_6816.asm b/tests/t_6816/t_6816.asm new file mode 100644 index 0000000..70299d2 --- /dev/null +++ b/tests/t_6816/t_6816.asm @@ -0,0 +1,1037 @@ + cpu 68hc16 + page 0 + assume ek:0 + + aba ;$370b + abx ;$374f + aby ;$375f + abz ;$376f + ace ;$3722 + aced ;$3723 + ade ;$2778 + adx ;$37cd + ady ;$37dd + adz ;$37ed + aex ;$374d + aey ;$375d + aez ;$376d + asla ;$3704 + aslb ;$3714 + asld ;$27f4 + asle ;$2774 + aslm ;$27b6 + asra ;$370d + asrb ;$371d + asrd ;$27fd + asre ;$277d + asrm ;$27ba + bgnd ;$37a6 + cba ;$371b + clra ;$3705 + clrb ;$3715 + clrd ;$27f5 + clre ;$2775 + clrm ;$27b7 + coma ;$3700 + comb ;$3710 + comd ;$27f0 + come ;$2770 + daa ;$3721 + deca ;$3701 + decb ;$3711 + ediv ;$3728 + edivs ;$3729 + emul ;$3725 + emuls ;$3726 + fdiv ;$372b + fmuls ;$3727 + idiv ;$372a + inca ;$3703 + incb ;$3713 + lpstop ;$27f1 + lsla ;$3704 + lslb ;$3714 + lsld ;$27f4 + lsle ;$2774 + lsra ;$370f + lsrb ;$371f + lsrd ;$27ff + lsre ;$277f + mul ;$3724 + nega ;$3702 + negb ;$3712 + negd ;$27f2 + nege ;$2772 + nop ;$274c + psha ;$3708 + pshb ;$3718 + pshmac ;$27b8 + pula ;$3709 + pulb ;$3719 + pulmac ;$27b9 + rola ;$370c + rolb ;$371c + rold ;$27fc + role ;$277c + rora ;$370e + rorb ;$371e + rord ;$27fe + rore ;$277e + rti ;$2777 + rts ;$27f7 + sba ;$370a + sde ;$2779 + swi ;$3720 + sxt ;$27f8 + tab ;$3717 + tap ;$37fd + tba ;$3707 + tbek ;$27fa + tbsk ;$379f + tbxk ;$379c + tbyk ;$379d + tbzk ;$379e + tde ;$277b + tdmsk ;$372f + tdp ;$372d + ted ;$27fb + tedm ;$27b1 + tekb ;$27bb + tem ;$27b2 + tmer ;$27b4 + tmet ;$27b5 + tmxed ;$27b3 + tpa ;$37fc + tpd ;$372c + tskb ;$37af + tsta ;$3706 + tstb ;$3716 + tstd ;$27f6 + tste ;$2776 + tsx ;$274f + tsy ;$275f + tsz ;$276f + txkb ;$37ac + txs ;$374e + txy ;$275c + txz ;$276c + tykb ;$37ad + tys ;$375e + tyx ;$274d + tyz ;$276d + tzkb ;$37ae + tzs ;$376e + tzx ;$274e + tzy ;$275e + wai ;$27f3 + xgab ;$371a + xgde ;$277a + xgdx ;$37cc + xgdy ;$37dc + xgdz ;$37ec + xgex ;$374c + xgey ;$375c + xgez ;$376c + +targ: bra targ + brn targ + bcc targ + bcs targ + bhs targ + blo targ + bmi targ + bne targ + bpl targ + bvc targ + bvs targ + bhi targ + bls targ + beq targ + bge targ + bgt targ + ble targ + blt targ + lbra targ + lbrn targ + lbcc targ + lbcs targ + lbhs targ + lblo targ + lbmi targ + lbne targ + lbpl targ + lbvc targ + lbvs targ + lbhi targ + lbls targ + lbeq targ + lbge targ + lbgt targ + lble targ + lblt targ + bsr targ + lbev targ + lbmv targ + lbsr targ + + adca $55,x + adca $55,y + adca $55,z + adca #$aa + adca $5aa5,x + adca $5aa5,y + adca $5aa5,z + adca $1234 + adca e,x + adca e,y + adca e,z + + adcb $55,x + adcb $55,y + adcb $55,z + adcb #$aa + adcb $5aa5,x + adcb $5aa5,y + adcb $5aa5,z + adcb $1234 + adcb e,x + adcb e,y + adcb e,z + + adcd $55,x + adcd $55,y + adcd $55,z + adcd #$aa + adcd $5aa5,x + adcd $5aa5,y + adcd $5aa5,z + adcd $1234 + adcd e,x + adcd e,y + adcd e,z + + adce $55,x + adce $55,y + adce $55,z + adce #$aa + adce $5aa5,x + adce $5aa5,y + adce $5aa5,z + adce $1234 + + adda $55,x + adda $55,y + adda $55,z + adda #$aa + adda $5aa5,x + adda $5aa5,y + adda $5aa5,z + adda $1234 + adda e,x + adda e,y + adda e,z + + addb $55,x + addb $55,y + addb $55,z + addb #$aa + addb $5aa5,x + addb $5aa5,y + addb $5aa5,z + addb $1234 + addb e,x + addb e,y + addb e,z + + addd $55,x + addd $55,y + addd $55,z + addd #$55 + addd #$aa + addd $5aa5,x + addd $5aa5,y + addd $5aa5,z + addd $1234 + addd e,x + addd e,y + addd e,z + + adde $55,x + adde $55,y + adde $55,z + adde #$55 + adde #$aa + adde $5aa5,x + adde $5aa5,y + adde $5aa5,z + adde $1234 + + anda $55,x + anda $55,y + anda $55,z + anda #$aa + anda $5aa5,x + anda $5aa5,y + anda $5aa5,z + anda $1234 + anda e,x + anda e,y + anda e,z + + andb $55,x + andb $55,y + andb $55,z + andb #$aa + andb $5aa5,x + andb $5aa5,y + andb $5aa5,z + andb $1234 + andb e,x + andb e,y + andb e,z + + andd $55,x + andd $55,y + andd $55,z + andd #$aa + andd $5aa5,x + andd $5aa5,y + andd $5aa5,z + andd $1234 + andd e,x + andd e,y + andd e,z + + ande $55,x + ande $55,y + ande $55,z + ande #$aa + ande $5aa5,x + ande $5aa5,y + ande $5aa5,z + ande $1234 + + asl $55,x + asl $55,y + asl $55,z + asl $5aa5,x + asl $5aa5,y + asl $5aa5,z + asl $1234 + + aslw $5aa5,x + aslw $5aa5,y + aslw $5aa5,z + aslw $1234 + + asr $55,x + asr $55,y + asr $55,z + asr $5aa5,x + asr $5aa5,y + asr $5aa5,z + asr $1234 + + asrw $5aa5,x + asrw $5aa5,y + asrw $5aa5,z + asrw $1234 + + bita $55,x + bita $55,y + bita $55,z + bita #$aa + bita $5aa5,x + bita $5aa5,y + bita $5aa5,z + bita $1234 + bita e,x + bita e,y + bita e,z + + bitb $55,x + bitb $55,y + bitb $55,z + bitb #$aa + bitb $5aa5,x + bitb $5aa5,y + bitb $5aa5,z + bitb $1234 + bitb e,x + bitb e,y + bitb e,z + + clr $55,x + clr $55,y + clr $55,z + clr $5aa5,x + clr $5aa5,y + clr $5aa5,z + clr $1234 + + clrw $5aa5,x + clrw $5aa5,y + clrw $5aa5,z + clrw $1234 + + cmpa $55,x + cmpa $55,y + cmpa $55,z + cmpa #$aa + cmpa $5aa5,x + cmpa $5aa5,y + cmpa $5aa5,z + cmpa $1234 + cmpa e,x + cmpa e,y + cmpa e,z + + cmpb $55,x + cmpb $55,y + cmpb $55,z + cmpb #$aa + cmpb $5aa5,x + cmpb $5aa5,y + cmpb $5aa5,z + cmpb $1234 + cmpb e,x + cmpb e,y + cmpb e,z + + com $55,x + com $55,y + com $55,z + com $5aa5,x + com $5aa5,y + com $5aa5,z + com $1234 + + comw $5aa5,x + comw $5aa5,y + comw $5aa5,z + comw $1234 + + cpd $55,x + cpd $55,y + cpd $55,z + cpd #$aa + cpd $5aa5,x + cpd $5aa5,y + cpd $5aa5,z + cpd $1234 + cpd e,x + cpd e,y + cpd e,z + + cpe $55,x + cpe $55,y + cpe $55,z + cpe #$aa + cpe $5aa5,x + cpe $5aa5,y + cpe $5aa5,z + cpe $1234 + + dec $55,x + dec $55,y + dec $55,z + dec $5aa5,x + dec $5aa5,y + dec $5aa5,z + dec $1234 + + decw $5aa5,x + decw $5aa5,y + decw $5aa5,z + decw $1234 + + eora $55,x + eora $55,y + eora $55,z + eora #$aa + eora $5aa5,x + eora $5aa5,y + eora $5aa5,z + eora $1234 + eora e,x + eora e,y + eora e,z + + eorb $55,x + eorb $55,y + eorb $55,z + eorb #$aa + eorb $5aa5,x + eorb $5aa5,y + eorb $5aa5,z + eorb $1234 + eorb e,x + eorb e,y + eorb e,z + + eord $55,x + eord $55,y + eord $55,z + eord #$aa + eord $5aa5,x + eord $5aa5,y + eord $5aa5,z + eord $1234 + eord e,x + eord e,y + eord e,z + + eore $55,x + eore $55,y + eore $55,z + eore #$aa + eore $5aa5,x + eore $5aa5,y + eore $5aa5,z + eore $1234 + + inc $55,x + inc $55,y + inc $55,z + inc $5aa5,x + inc $5aa5,y + inc $5aa5,z + inc $1234 + + incw $5aa5,x + incw $5aa5,y + incw $5aa5,z + incw $1234 + + ldaa $55,x + ldaa $55,y + ldaa $55,z + ldaa #$aa + ldaa $5aa5,x + ldaa $5aa5,y + ldaa $5aa5,z + ldaa $1234 + ldaa e,x + ldaa e,y + ldaa e,z + + ldab $55,x + ldab $55,y + ldab $55,z + ldab #$aa + ldab $5aa5,x + ldab $5aa5,y + ldab $5aa5,z + ldab $1234 + ldab e,x + ldab e,y + ldab e,z + + ldd $55,x + ldd $55,y + ldd $55,z + ldd #$aa + ldd $5aa5,x + ldd $5aa5,y + ldd $5aa5,z + ldd $1234 + ldd e,x + ldd e,y + ldd e,z + + lde $55,x + lde $55,y + lde $55,z + lde #$aa + lde $5aa5,x + lde $5aa5,y + lde $5aa5,z + lde $1234 + + lsl $55,x + lsl $55,y + lsl $55,z + lsl $5aa5,x + lsl $5aa5,y + lsl $5aa5,z + lsl $1234 + + lslw $5aa5,x + lslw $5aa5,y + lslw $5aa5,z + lslw $1234 + + lsr $55,x + lsr $55,y + lsr $55,z + lsr $5aa5,x + lsr $5aa5,y + lsr $5aa5,z + lsr $1234 + + lsrw $5aa5,x + lsrw $5aa5,y + lsrw $5aa5,z + lsrw $1234 + + neg $55,x + neg $55,y + neg $55,z + neg $5aa5,x + neg $5aa5,y + neg $5aa5,z + neg $1234 + + negw $5aa5,x + negw $5aa5,y + negw $5aa5,z + negw $1234 + + oraa $55,x + oraa $55,y + oraa $55,z + oraa #$aa + oraa $5aa5,x + oraa $5aa5,y + oraa $5aa5,z + oraa $1234 + oraa e,x + oraa e,y + oraa e,z + + orab $55,x + orab $55,y + orab $55,z + orab #$aa + orab $5aa5,x + orab $5aa5,y + orab $5aa5,z + orab $1234 + orab e,x + orab e,y + orab e,z + + ord $55,x + ord $55,y + ord $55,z + ord #$aa + ord $5aa5,x + ord $5aa5,y + ord $5aa5,z + ord $1234 + ord e,x + ord e,y + ord e,z + + ore $55,x + ore $55,y + ore $55,z + ore #$aa + ore $5aa5,x + ore $5aa5,y + ore $5aa5,z + ore $1234 + + rol $55,x + rol $55,y + rol $55,z + rol $5aa5,x + rol $5aa5,y + rol $5aa5,z + rol $1234 + + rolw $5aa5,x + rolw $5aa5,y + rolw $5aa5,z + rolw $1234 + + ror $55,x + ror $55,y + ror $55,z + ror $5aa5,x + ror $5aa5,y + ror $5aa5,z + ror $1234 + + rorw $5aa5,x + rorw $5aa5,y + rorw $5aa5,z + rorw $1234 + + sbca $55,x + sbca $55,y + sbca $55,z + sbca #$aa + sbca $5aa5,x + sbca $5aa5,y + sbca $5aa5,z + sbca $1234 + sbca e,x + sbca e,y + sbca e,z + + sbcb $55,x + sbcb $55,y + sbcb $55,z + sbcb #$aa + sbcb $5aa5,x + sbcb $5aa5,y + sbcb $5aa5,z + sbcb $1234 + sbcb e,x + sbcb e,y + sbcb e,z + + sbcd $55,x + sbcd $55,y + sbcd $55,z + sbcd #$aa + sbcd $5aa5,x + sbcd $5aa5,y + sbcd $5aa5,z + sbcd $1234 + sbcd e,x + sbcd e,y + sbcd e,z + + sbce $55,x + sbce $55,y + sbce $55,z + sbce #$aa + sbce $5aa5,x + sbce $5aa5,y + sbce $5aa5,z + sbce $1234 + + staa $55,x + staa $55,y + staa $55,z + staa $5aa5,x + staa $5aa5,y + staa $5aa5,z + staa $1234 + staa e,x + staa e,y + staa e,z + + stab $55,x + stab $55,y + stab $55,z + stab $5aa5,x + stab $5aa5,y + stab $5aa5,z + stab $1234 + stab e,x + stab e,y + stab e,z + + std $55,x + std $55,y + std $55,z + std $5aa5,x + std $5aa5,y + std $5aa5,z + std $1234 + std e,x + std e,y + std e,z + + ste $55,x + ste $55,y + ste $55,z + ste $5aa5,x + ste $5aa5,y + ste $5aa5,z + ste $1234 + + suba $55,x + suba $55,y + suba $55,z + suba #$aa + suba $5aa5,x + suba $5aa5,y + suba $5aa5,z + suba $1234 + suba e,x + suba e,y + suba e,z + + subb $55,x + subb $55,y + subb $55,z + subb #$aa + subb $5aa5,x + subb $5aa5,y + subb $5aa5,z + subb $1234 + subb e,x + subb e,y + subb e,z + + subd $55,x + subd $55,y + subd $55,z + subd #$aa + subd $5aa5,x + subd $5aa5,y + subd $5aa5,z + subd $1234 + subd e,x + subd e,y + subd e,z + + sube $55,x + sube $55,y + sube $55,z + sube #$aa + sube $5aa5,x + sube $5aa5,y + sube $5aa5,z + sube $1234 + + tst $55,x + tst $55,y + tst $55,z + tst $5aa5,x + tst $5aa5,y + tst $5aa5,z + tst $1234 + + tstw $5aa5,x + tstw $5aa5,y + tstw $5aa5,z + tstw $1234 + + cps $55,x + cps $55,y + cps $55,z + cps #$aa + cps $5aa5,x + cps $5aa5,y + cps $5aa5,z + cps $1234 + + cpx $55,x + cpx $55,y + cpx $55,z + cpx #$aa + cpx $5aa5,x + cpx $5aa5,y + cpx $5aa5,z + cpx $1234 + + cpy $55,x + cpy $55,y + cpy $55,z + cpy #$aa + cpy $5aa5,x + cpy $5aa5,y + cpy $5aa5,z + cpy $1234 + + cpz $55,x + cpz $55,y + cpz $55,z + cpz #$aa + cpz $5aa5,x + cpz $5aa5,y + cpz $5aa5,z + cpz $1234 + + lds $55,x + lds $55,y + lds $55,z + lds #$aa + lds $5aa5,x + lds $5aa5,y + lds $5aa5,z + lds $1234 + + ldx $55,x + ldx $55,y + ldx $55,z + ldx #$aa + ldx $5aa5,x + ldx $5aa5,y + ldx $5aa5,z + ldx $1234 + + ldy $55,x + ldy $55,y + ldy $55,z + ldy #$aa + ldy $5aa5,x + ldy $5aa5,y + ldy $5aa5,z + ldy $1234 + + ldz $55,x + ldz $55,y + ldz $55,z + ldz #$aa + ldz $5aa5,x + ldz $5aa5,y + ldz $5aa5,z + ldz $1234 + + sts $55,x + sts $55,y + sts $55,z + sts $5aa5,x + sts $5aa5,y + sts $5aa5,z + sts $1234 + + stx $55,x + stx $55,y + stx $55,z + stx $5aa5,x + stx $5aa5,y + stx $5aa5,z + stx $1234 + + sty $55,x + sty $55,y + sty $55,z + sty $5aa5,x + sty $5aa5,y + sty $5aa5,z + sty $1234 + + stz $55,x + stz $55,y + stz $55,z + stz $5aa5,x + stz $5aa5,y + stz $5aa5,z + stz $1234 + + jmp $12345 + jmp $23456,x + jmp $23456,y + jmp $23456,z + + jsr $12345 + jsr $23456,x + jsr $23456,y + jsr $23456,z + + ais #-2 + ais #1000 + + aix #-2 + aix #1000 + + aiy #-2 + aiy #1000 + + aiz #-2 + aiz #1000 + + andp #$feff + orp #$0100 + + lded $a55a + ldhi $a55a + sted $5aa5 + + mac 3,5 + rmac 5,3 + + pshm d,x,z,ccr + pulm e,y,k + + bclr $55,x,#2 + bclr $55,y,#2 + bclr $55,z,#2 + bclr $5aa5,x,#2 + bclr $5aa5,y,#2 + bclr $5aa5,z,#2 + bclr $1234,#2 + + bset $55,x,#2 + bset $55,y,#2 + bset $55,z,#2 + bset $5aa5,x,#2 + bset $5aa5,y,#2 + bset $5aa5,z,#2 + bset $1234,#2 + + bclrw $55,x,#2 + bclrw $55,y,#2 + bclrw $55,z,#2 + bclrw $5aa5,x,#2 + bclrw $5aa5,y,#2 + bclrw $5aa5,z,#2 + bclrw $1234,#2 + + bsetw $55,x,#2 + bsetw $55,y,#2 + bsetw $55,z,#2 + bsetw $5aa5,x,#2 + bsetw $5aa5,y,#2 + bsetw $5aa5,z,#2 + bsetw $1234,#2 + + movb $1234,$5678 + movb $1234,5,x + movb -5,x,$5678 + + movw $1234,$5678 + movw $1234,5,x + movw -5,x,$5678 + + brclr $55,x,#2,*+$30 + brclr $55,y,#2,*+$30 + brclr $55,z,#2,*+$30 + brclr $55,x,#2,*+$300 + brclr $55,y,#2,*+$300 + brclr $55,z,#2,*+$300 + brclr $5aa5,x,#2,*+$300 + brclr $5aa5,y,#2,*+$300 + brclr $5aa5,z,#2,*+$300 + brclr $1234,#2,*+$300 + + brset $55,x,#2,*+$30 + brset $55,y,#2,*+$30 + brset $55,z,#2,*+$30 + brset $55,x,#2,*+$300 + brset $55,y,#2,*+$300 + brset $55,z,#2,*+$300 + brset $5aa5,x,#2,*+$300 + brset $5aa5,y,#2,*+$300 + brset $5aa5,z,#2,*+$300 + brset $1234,#2,*+$300 + + clc + andp #$feff + cli + andp #$ff1f + clv + andp #$fdff + des + ais #-1 + dex + aix #-1 + dey + aiy #-1 + ins + ais #1 + inx + aix #1 + iny + aiy #1 + pshx + pshm x + pshy + pshm y + pulx + pulm x + puly + pulm y + sec + orp #$0100 + sei + orp #$00e0 + sev + orp #$0200 diff --git a/tests/t_6816/t_6816.doc b/tests/t_6816/t_6816.doc new file mode 100644 index 0000000..ad1fc09 --- /dev/null +++ b/tests/t_6816/t_6816.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 6816 ----------------------------+ +| | +| This is a (synthetic) test of the 68HC16 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_6816/t_6816.ori b/tests/t_6816/t_6816.ori new file mode 100644 index 0000000..1642194 Binary files /dev/null and b/tests/t_6816/t_6816.ori differ diff --git a/tests/t_7000/asflags b/tests/t_7000/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_7000/t_7000.asm b/tests/t_7000/t_7000.asm new file mode 100644 index 0000000..ed60212 --- /dev/null +++ b/tests/t_7000/t_7000.asm @@ -0,0 +1,249 @@ + cpu sh7600 + page 0 + supmode on + + rts + rte + rtb + clrt + sett + clrmac + nop + sleep + div0u + brk + + movt r4 + cmp/pz r6 + cmp/pl r12 + rotl r5 + rotr sp + rotcl r8 + rotcr r2 + shal r1 + shar r13 + shll r9 + shlr r11 + shll2 r4 + shlr2 r10 + shll8 r15 + shlr8 r3 + shll16 r5 + shlr16 r7 + stbr r5 + ldbr sp + dt r6 + + tas @sp + + xtrct r0,r1 + addc r1,r2 + addv r2,r3 + cmp/hs r3,r4 + cmp/ge r4,r5 + cmp/hi r5,r6 + cmp/gt r6,r7 + cmp/str r7,r8 + div1 r8,r9 + div0s r9,r10 + muls.w r10,r11 + mulu.w r11,r12 + neg r12,r13 + negc r13,r14 + sub r14,r15 + subc r15,r0 + subv r0,r1 + not r1,r2 + dmuls.l r2,r3 + dmulu.l r3,r4 + mul r4,r5 + + swap.b r5,r10 + swap.w r6,r11 + exts.b r7,r12 + exts.w r8,r13 + extu.b r9,r14 + extu.w r10,r15 + + add r3,r5 + add #-30,r4 + cmp/eq r3,r5 + cmp/eq #-30,r0 + mac @r5+,@r7+ + mac.l @r5+,@r7+ + + and r5,r9 + and #30,r0 + and.b #$55,@(r0,gbr) + + or r7,sp + or #%10111011,r0 + or #123,@(gbr,r0,3-5+2) + + tst r4,r12 + tst.l #20,r0 + tst.b #33,@(r0,gbr) + + xor r5,r3 + xor.l #45,r0 + xor #%10,@(gbr,r0) + + + bt targ +targ: bf targ + bt/s targ + bf/s targ + bra targ + bsr targ + jmp @r5 + jsr @r10 + + ldc r5,sr + ldc r10,gbr + ldc r7,vbr + ldc @r6+,sr + ldc @r9+,gbr + ldc @r13+,vbr + stc sr,r4 + stc gbr,r3 + stc vbr,r7 + stc sr,@-r6 + stc gbr,@-r4 + stc vbr,@-r14 + lds r5,mach + lds r10,macl + lds r7,pr + lds @r6+,mach + lds @r9+,macl + lds @r13+,pr + sts mach,r4 + sts macl,r3 + sts pr,r7 + sts mach,@-r6 + sts macl,@-r4 + sts pr,@-r14 + + mova ldata,r0 + + mov.l r5,r13 + + mov.b r1,@-r2 + mov.b @r2+,r1 + mov.w r3,@-r4 + mov.w @r4+,r3 + mov.l r6,@-r5 + mov.l @r5+,r6 + + mov.b r12,@r5 + mov.b @r5,r12 + mov.w r5,@r14 + mov.w @r14,r5 + mov.l r7,@r7 + mov.l @r7,r7 + + mov.b r0,@(r6,3) + mov.b @(r6,1+2),r0 + mov.w r0,@(10,r12) + mov.w @(10,r12),r0 + mov.l r7,@(60,r3) + mov.l @(2*30,r3),r7 + + mov.b r4,@(r0,r5) + mov.b @(r5,r0),r4 + mov.w r6,@(r0,r10) + mov.w @(r10,r0),r6 + mov.l r7,@(r0,r6) + mov.l @(r6,r0),r7 + + mov.b r0,@(gbr,30) + mov.b @(30,gbr),r0 + mov.w r0,@(gbr,60) + mov.w @(10,5*5*2,gbr),r0 + mov.l r0,@(gbr,120) + mov.l @(120,gbr),r0 + + mov #120,r4 + mov.w wdata,r3 + mov.l ldata,r12 + + trapa #$21 + + mov #$1234,r3 + mov #$8000,r3 + mov #$11223344,r3 + mov #$0000,r3 + mov #$1122,r3 + mov #$3344,r3 + + bra next + mov #$1234,r3 + bra next + mov #$11223344,r3 + nop +next: nop + nop + + section test + mov #$1234,r5 + nop + ltorg + endsection + + align 4 +ldata: dc.l $12345678 +wdata: dc.w $1234 + + ltorg + + cpu sh7700 + + clrs + sets + ldtlb + + ldc r4,ssr + ldc r4,spc + ldc r4,r0_bank + ldc r4,r1_bank + ldc r4,r2_bank + ldc r4,r3_bank + ldc r4,r4_bank + ldc r4,r5_bank + ldc r4,r6_bank + ldc r4,r7_bank + ldc.l @r4+,ssr + ldc.l @r4+,spc + ldc.l @r4+,r0_bank + ldc.l @r4+,r1_bank + ldc.l @r4+,r2_bank + ldc.l @r4+,r3_bank + ldc.l @r4+,r4_bank + ldc.l @r4+,r5_bank + ldc.l @r4+,r6_bank + ldc.l @r4+,r7_bank + stc ssr,r4 + stc spc,r4 + stc r0_bank,r4 + stc r1_bank,r4 + stc r2_bank,r4 + stc r3_bank,r4 + stc r4_bank,r4 + stc r5_bank,r4 + stc r6_bank,r4 + stc r7_bank,r4 + stc.l ssr,@-r4 + stc.l spc,@-r4 + stc.l r0_bank,@-r4 + stc.l r1_bank,@-r4 + stc.l r2_bank,@-r4 + stc.l r3_bank,@-r4 + stc.l r4_bank,@-r4 + stc.l r5_bank,@-r4 + stc.l r6_bank,@-r4 + stc.l r7_bank,@-r4 + + pref @r5 + + shad r3,r7 + shld r12,sp + diff --git a/tests/t_7000/t_7000.doc b/tests/t_7000/t_7000.doc new file mode 100644 index 0000000..9be3f47 --- /dev/null +++ b/tests/t_7000/t_7000.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 7000 ----------------------------+ +| | +| This is a (synthetic) test of the SH7x00 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_7000/t_7000.ori b/tests/t_7000/t_7000.ori new file mode 100644 index 0000000..560ff72 Binary files /dev/null and b/tests/t_7000/t_7000.ori differ diff --git a/tests/t_75k0/asflags b/tests/t_75k0/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_75k0/t_75k0.asm b/tests/t_75k0/t_75k0.asm new file mode 100644 index 0000000..9925e87 --- /dev/null +++ b/tests/t_75k0/t_75k0.asm @@ -0,0 +1,191 @@ + cpu 75104 + page 0 + include stddef75 + + ret + reti + rets + halt + stop + nop + + br pc+5 + br pc-5 + br pc+200h + br pc+2000h + br $pc+5 + brcb pc+5 + br !pc+5 + br $pc-5 + brcb pc-5 + br !pc-5 + brcb pc+200h + br !pc+200h + br !pc+2000h + br pcde + br pcxa + + call !200h + call !2000h + call 200h + call 2000h + callf 200h + callf !200h + + adds a,#5 + adds xa,#30 + adds a,@hl + adds xa,hl + adds xa,de + adds xa,bc + adds xa,xa' + adds xa,hl' + adds xa,de` + adds xa,bc` + adds de,xa + + addc a,@hl + addc xa,bc + addc de`,xa + + subs a,@hl + subs xa,bc + subs de`,xa + + subc a,@hl + subc xa,bc + subc de`,xa + + and a,#13 + and a,@hl + and xa,bc + and de`,xa + + or a,#13 + or a,@hl + or xa,bc + or de`,xa + + xor a,#13 + xor a,@hl + xor xa,bc + xor de`,xa + + incs d + incs de + incs @hl + incs 20h + + decs d + decs de' + + ske b,#5 + ske @hl,#6 + ske a,@hl + ske @hl,a + ske xa,@hl + ske @hl,xa + ske a,c + ske c,a + ske xa,hl' + ske hl`,xa + + mov a,#5 + mov b,#5 + mov de,#55h + mov a,@hl + mov a,@hl+ + mov a,@hl- + mov a,@de + mov a,@dl + mov xa,@hl + mov @hl,a + mov @hl,xa + mov a,12h + mov xa,34h + mov 56h,a + mov 78h,xa + mov a,c + mov xa,bc' + mov d,a + mov hl`,xa + + xch a,@hl+ + xch @hl+,a + xch xa,@hl + xch @hl,xa + xch a,12h + xch 12h,a + xch xa,34h + xch 34h,xa + xch a,d + xch d,a + xch xa,de + xch de,xa + + movt xa,@pcde + movt xa,@pcxa + + mov1 cy,0fb2h.2 + mov1 0ff4h.1,cy + mov1 cy,0fe4h.@l + mov1 @h+13.3,cy + + set1 cy + set1 40h.2 + set1 0ff2h.3 + + clr1 cy + clr1 40h.2 + clr1 0ff2h.3 + + skt cy + skt 40h.2 + skt 0ff2h.3 + + skf 40h.2 + skf 0ff2h.3 + + not1 cy + sktclr 0ff2h.3 + + and1 cy,0ff2h.3 + or1 cy,0ff2h.3 + xor1 cy,0ff2h.3 + + rorc a + not a + + push bs + pop bs + push hl + pop bc + + in a,port3 + in xa,port12 + out port10,a + out port7,xa + + ei + di + ei ieks + di iew + + sel rb2 + sel mb10 + + geti 15 + +bit1 bit 0ff0h.@l +bit2 bit 0fb0h.2 +bit3 bit 0ff0h.1 +bit4 bit 0430h.3 +bit5 bit @h+5+3.2 + + set1 bit1 + clr1 bit4 + sel mb4 + set1 mbe + assume mbs:4,mbe:1 + clr1 bit4 + diff --git a/tests/t_75k0/t_75k0.doc b/tests/t_75k0/t_75k0.doc new file mode 100644 index 0000000..68b87c8 --- /dev/null +++ b/tests/t_75k0/t_75k0.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 75K0 ----------------------------+ +| | +| This is a (synthetic) test of the 75K0 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_75k0/t_75k0.ori b/tests/t_75k0/t_75k0.ori new file mode 100644 index 0000000..09c49c4 Binary files /dev/null and b/tests/t_75k0/t_75k0.ori differ diff --git a/tests/t_7700/asflags b/tests/t_7700/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_7700/t_7700.asm b/tests/t_7700/t_7700.asm new file mode 100644 index 0000000..f4537d9 --- /dev/null +++ b/tests/t_7700/t_7700.asm @@ -0,0 +1,356 @@ + cpu melps7751 + page 0 + + + ldt #0 + assume pg:0,dt:0,dpr:0 + +accmode macro size + switch size + case 8 + sep #$20 + assume m:1 + case 16 + clp #$20 + assume m:0 + elsecase + fatal "accmode: ungltige Operandengr”áe: $\{SIZE}" + endcase + endm + +idxmode macro size + switch size + case 8 + sep #$10 + assume x:1 + case 16 + clp #$10 + assume x:0 + elsecase + fatal "idxmode: ungltige Operandengr”áe: $\{SIZE}" + endcase + endm + + xab + wit + tyx + tyb + tya + txy + txs + txb + txa + tsx + tsb + tsa + tdb + tda + tby + tbx + tbs + tbd + tay + tax + tas + tad + stp + sem + sei + sec + rts + rtl + rti + ply + plx + plt + plp + pld + plb + pla + phy + phx + pht + php + phg + phd + phb + pha + nop + iny + inx + dey + dex + clv + clm + cli + clc + + rla #7 + +targ: + bcc targ + bcs targ + beq targ + bmi targ + bne targ + bpl targ + bvc targ + bvs targ + bra targ + per targ + org *+$100 + bra targ + per targ + + accmode 8 + idxmode 8 + + adc #20 + and a,#-1 + cmp b,#-$a + +targ2: + bbc #$80,$20,targ2 + bbs #$40,$2000,targ2 + clb #$20,$20 + seb #$10,$2000 + + cpx #$aa + cpy #$aa + ldx #$bb + ldy #$bb + + ldm #$aa,$20 + ldm #$aa,$2000 + ldm #$aa,$20,x + ldm #$aa,$2000,x + + accmode 16 + idxmode 16 + + eor #%0000111111110000 + lda a,#'AB' + ora b,#3000 + + sbc $20 + sta a,$2000 + adc b,$200000 + + and $30,x + cmp a,$3000,x + eor b,$300000,x + + lda $40,y + ora a,$4000,y +; sbc b,$400000,y + + sta ($50) +; adc a,($5000) +; and b,($500000) + + cmpl ($60) +; eorl a,($6000) +; ldal b,($600000) + + ora ($70,x) +; sbc ($7000,x) +; sta ($700000,x) + + adc ($80),y +; and ($8000),y +; cmp ($800000),y + + eorl ($80),y +; ldal ($8000),y +; oral ($800000),y + + sbc b,3,s + sta a,(5,s),y + + asl + dec a + inc b + lsr $20 + rol $2000 + ror $20,x + asl $2000,x + +targ3: + bbs #$80,$20,targ3 + bbc #$40,$2000,targ3 + clb #$20,$20 + seb #$10,$2000 + + cpx #$aa + cpy #$aa + ldx #$bb + ldy #$bb + cpx $20 + cpy $20 + ldx $20 + ldy $20 + stx $20 + sty $20 + cpx $2000 + cpy $2000 + ldx $2000 + ldy $2000 + stx $2000 + sty $2000 + ldx $30,y + ldy $30,x + stx $30,y + sty $30,x + ldx $3000,y + ldy $3000,x + + mpy #55 + accmode 8 + mpy #55 + accmode 16 + mpy $12 + mpy $12,x + mpy ($12) + mpy ($12,x) + mpy ($12),y + mpyl ($12) + mpyl ($12),y + mpy $1234 + mpy $1234,x + mpy $1234,y + mpy $123456 + mpy $123456,x + mpy $12,s + mpy ($12,s),y + + div #55 + accmode 8 + div #55 + accmode 16 + div $12 + div $12,x + div ($12) + div ($12,x) + div ($12),y + divl ($12) + divl ($12),y + div $1234 + div $1234,x + div $1234,y + div $123456 + div $123456,x + div $12,s + div ($12,s),y + + jmp $20 + jmp $2000 + jmp $200000 + jmp ($3000) + jmpl ($3000) + jmp ($4000,x) + jsr $20 + jsr $2000 + jsr $200000 + jsr ($4000,x) + + ldm #$aa,$20 + ldm #$aa,$2000 + ldm #$aa,$20,x + ldm #$aa,$2000,x + + mvn $200000,$300000 + mvp $200000,$300000 + +;- - - - - - - - - - - - - - - - - - - - - - - - - - - - + + cpu 65816 + + cop + jml $2000 + jsl $4000 + brl * + rep #$55 + tsb $33 + trb $66 + tsb $9999 + trb $cccc + bit $00 + bit $11,x + bit $2222 + bit $3333,x + bit #$44 + stz $55 + stz $6666 + stz $77,x + stz $8888,x + cld + sed + tcs + tsc + phk + tcd + tdc + phb + plb + wai + xba + xce + +;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + cpu melps7750 + + asr + asr a + asr b + asr $aa + asr $1234 + asr $aa,x + asr $1234,x + + extz + extz a + extz b + exts + exts a + exts b + + mpys #55 + accmode 8 + mpys #55 + accmode 16 + mpys $12 + mpys $12,x + mpys ($12) + mpys ($12,x) + mpys ($12),y + mpysl ($12) + mpysl ($12),y + mpys $1234 + mpys $1234,x + mpys $1234,y + mpys $123456 + mpys $123456,x + mpys $12,s + mpys ($12,s),y + + divs #55 + accmode 8 + divs #55 + accmode 16 + divs $12 + divs $12,x + divs ($12) + divs ($12,x) + divs ($12),y + divsl ($12) + divsl ($12),y + divs $1234 + divs $1234,x + divs $1234,y + divs $123456 + divs $123456,x + divs $12,s + divs ($12,s),y + + diff --git a/tests/t_7700/t_7700.doc b/tests/t_7700/t_7700.doc new file mode 100644 index 0000000..d7186e0 --- /dev/null +++ b/tests/t_7700/t_7700.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 7700 ----------------------------+ +| | +| This is a (synthetic) test of the MELPS/77xx instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_7700/t_7700.ori b/tests/t_7700/t_7700.ori new file mode 100644 index 0000000..df9af4e Binary files /dev/null and b/tests/t_7700/t_7700.ori differ diff --git a/tests/t_7720/asflags b/tests/t_7720/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_7720/t_7720.asm b/tests/t_7720/t_7720.asm new file mode 100644 index 0000000..d25c058 --- /dev/null +++ b/tests/t_7720/t_7720.asm @@ -0,0 +1,141 @@ + cpu 7720 + + jmp lab + call lab + jnca lab + jncb lab + jcb lab + jnza lab + jza lab + jnzb lab + jzb lab + jnova0 lab + jova0 lab + jnovb0 lab + jovb0 lab + jnova1 lab + jova1 lab + jnovb1 lab + jovb1 lab + jnsa0 lab + jsa0 lab + jnsb0 lab + jsb0 lab + jnsa1 lab + jsa1 lab + jnsb1 lab + jsb1 lab + jdpl0 lab + jdplf lab + jnsiak lab + jsiak lab + jnsoak lab + jsoak lab + jnrqm lab + jrqm lab +lab: + + ldi @non,1234h + ldi @a,1234h + ldi @b,1234h + ldi @tr,1234h + ldi @dp,1234h + ldi @rp,1234h + ldi @dr,1234h + ldi @sr,1234h + ldi @sol,1234h + ldi @som,1234h + ldi @k,1234h + ldi @klr,1234h + ldi @klm,1234h + ldi @l,1234h + ldi @mem,1234h + + op mov @a,non + op mov @a,a + op mov @a,b + op mov @a,tr + op mov @a,dp + op mov @a,rp + op mov @a,ro + op mov @a,sgn + op mov @a,dr + op mov @a,drnf + op mov @a,sr + op mov @a,sim + op mov @a,sil + op mov @a,k + op mov @a,l + op mov @a,mem + + op mov @a,non + or acca,ram + op mov @a,non + or accb,ram + op mov @a,non + or acca,idb + op mov @a,non + or acca,m + op mov @a,non + or acca,n + op mov @a,non + and acca,ram + op mov @a,non + xor acca,ram + op mov @a,non + sub acca,ram + op mov @a,non + add acca,ram + op mov @a,non + sbb acca,ram + op mov @a,non + adc acca,ram + op mov @a,non + cmp acca,ram + op mov @a,non + inc accb + op mov @a,non + dec acca + op mov @a,non + shr1 accb + op mov @a,non + shl1 acca + op mov @a,non + shl2 accb + op mov @a,non + shl4 acca + op mov @a,non + xchg accb + op mov @a,non + nop + + op mov @a,non + dpnop + op mov @a,non + dpinc + op mov @a,non + dpdec + op mov @a,non + dpclr + + op mov @a,non + m0 + op mov @a,non + m1 + op mov @a,non + m2 + op mov @a,non + m3 + op mov @a,non + m4 + op mov @a,non + m5 + op mov @a,non + m6 + op mov @a,non + m7 + + op mov @a,non + rpnop + op mov @a,non + rpdec diff --git a/tests/t_7720/t_7720.doc b/tests/t_7720/t_7720.doc new file mode 100644 index 0000000..cdf17c8 --- /dev/null +++ b/tests/t_7720/t_7720.doc @@ -0,0 +1,5 @@ ++-------------------------- Test Application 7720 ---------------------------+ +| | +| This is a (synthetic) test of the uPD7720 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_7720/t_7720.ori b/tests/t_7720/t_7720.ori new file mode 100644 index 0000000..bb3ef05 Binary files /dev/null and b/tests/t_7720/t_7720.ori differ diff --git a/tests/t_77230/asflags b/tests/t_77230/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_77230/t_77230.asm b/tests/t_77230/t_77230.asm new file mode 100644 index 0000000..494b9c3 --- /dev/null +++ b/tests/t_77230/t_77230.asm @@ -0,0 +1,245 @@ + cpu 77230 + page 0 + + ; Test Case 1 (nur LDI) und DestReg-Kodierungen + + ldi rp,123456h + ldi psw0,123456h + ldi psw1,123456h + ldi svr,123456h + ldi sr,123456h + ldi lc,123456h + ldi stk,123456h + ldi lkr0,123456h + ldi klr1,123456h + ldi tre,123456h + ldi tr,123456h + ldi ar,123456h + ldi so,123456h + ldi dr,123456h + ldi drs,123456h + ldi wr0,123456h + ldi wr1,123456h + ldi wr2,123456h + ldi wr3,123456h + ldi wr4,123456h + ldi wr5,123456h + ldi wr6,123456h + ldi wr7,123456h + ldi ram0,123456h + ldi ram1,123456h + ldi bp0,123456h + ldi bp1,123456h + ldi ix0,123456h + ldi ix1,123456h + ldi k,123456h + ldi l,123456h + + ; Sprünge wahlweise mit oder ohne MOV, Test SrcReg-Kodierungen + jmp target + call target mov wr0,rp + ret + ret mov wr0,psw0 + mov wr0,psw1 jnzrp target + jz0 target mov wr0,svr + mov wr0,sr jnz0 target + jz1 target mov wr0,lc + mov wr0,stx jnz1 target + jc0 target mov wr0,m + mov wr0,ml jnc0 target + jc1 target mov wr0,rom + mov wr0,tr jnc1 target + js0 target mov wr0,ar + mov wr0,si jns0 target + js1 target mov wr0,dr + mov wr0,drs jns1 target + jv0 target mov wr0,wr0 + mov wr0,wr1 jnv0 target + jv1 target mov wr0,wr2 + mov wr0,wr3 jnv1 target + jev0 target mov wr0,wr4 + mov wr0,wr5 jev1 target + jnfsi target mov wr0,wr6 + mov wr0,wr7 jneso target + jip0 target mov wr0,ram0 + mov wr0,ram1 jip1 target + jnzix0 target mov wr0,bp0 + mov wr0,bp1 jnzix1 target + jnzbp0 target mov wr0,ix0 + mov wr0,ix1 jnzbp1 target + jrdy target mov wr0,k + mov wr0,l jrqm target +target: + + ; ALU + + nop + inc wr1 + dec wr2 + abs wr3 + not wr4 + neg wr5 + shlc wr6 + shrc wr7 + rol wr1 + ror wr2 + shlm wr3 + shrm wr4 + shram wr5 + clr wr6 + norm wr7 + cvt wr1 + add wr1,ib + sub wr1,m + addc wr1,ram0 + subc wr1,ram1 + cmp wr1,ib + and wr1,m + or wr1,ram0 + xor wr1,ram1 + addf wr1,ib + subf wr1,m + + ; Mx-Felder + + spcbp0 spcbi1 + spcix0 spcix1 + spcbi0 spcbp1 + + ; DPx-Felder + + incbp0 clrix1 + decbp0 decix1 + clrbp0 incix1 + stix0 stix1 + incix0 clrbp1 + decix0 decbp1 + clrix0 incbp1 + + ; EA-Feld + + incar + decar + + ; FC-Feld + + xchpsw + + ; RP-Feld + + incrp + decrp + incbrp + + ; L-Feld + + declc + + ; BASE-Felder + + mcnbp0 0 mcnbp1 7 + mcnbp0 1 mcnbp1 6 + mcnbp0 2 mcnbp1 5 + mcnbp0 3 mcnbp1 4 + mcnbp0 4 mcnbp1 3 + mcnbp0 5 mcnbp1 2 + mcnbp0 6 mcnbp1 1 + mcnbp0 7 mcnbp1 0 + + ; RPC-Feld + + bitrp 0 + bitrp 1 + bitrp 2 + bitrp 3 + bitrp 4 + bitrp 5 + bitrp 6 + bitrp 7 + bitrp 8 + bitrp 9 + + ; Ports nur im Paket + + clrp2 clrp3 + setp2 clrp3 + clrp2 setp3 + setp2 setp3 + + ; Interrupts nur mit Ports + + clrp2 clrp3 clrbm + clrp2 clrp3 setbm + clrp2 clrp3 di + clrp2 clrp3 ei + clrp2 clrp3 ei clrbm + clrp2 clrp3 ei setbm + + ; RW-Feld + + rd + wr + + ; WT-Feld + + wrbord + wrbl24 + wrbl23 + wrbel8 + wrbl8e + wrbxch + wrbbrv + + ; NF-Feld + + trnorm + rdnorm + fltfix + fixma + + ; WI-Feld + + bwrl24 + bwrord + + ; FIS-Feld + + spcpsw0 + spcpsw1 + clrpsw0 + clrpsw1 + clrpsw + + ; FD-Feld + + spie + iesp + + ; SHV-Feld + + setsvl 7 + setsvr 17 + + ; RPS-Feld + + spcra 123 + + ; NAL-Feld + + jblk $+5 + + ; Datenablage + + dw 12345678h + dw 32.0,-32.0 + dw 1.0,-1.0 +; dw 3.6e-46 ; these do not work on machines that +; dw 3.6e-45 ; do not support denormalized values, +; dw 3.6e-44 ; so we better leave them out for portable +; dw 3.6e-43 ; tests... +; dw 3.6e-42 +; dw 3.6e-41 +; dw 3.6e-40 +; dw 3.6e-39 + dw 3.6e-38 + diff --git a/tests/t_77230/t_77230.doc b/tests/t_77230/t_77230.doc new file mode 100644 index 0000000..a891a66 --- /dev/null +++ b/tests/t_77230/t_77230.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 77230 ---------------------------+ +| | +| This is a (synthetic) test of the uPD77230 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_77230/t_77230.ori b/tests/t_77230/t_77230.ori new file mode 100644 index 0000000..d121bd3 Binary files /dev/null and b/tests/t_77230/t_77230.ori differ diff --git a/tests/t_7725/asflags b/tests/t_7725/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_7725/t_7725.asm b/tests/t_7725/t_7725.asm new file mode 100644 index 0000000..2611a7d --- /dev/null +++ b/tests/t_7725/t_7725.asm @@ -0,0 +1,171 @@ + cpu 7725 + + jmp lab + call lab + jnca lab + jncb lab + jcb lab + jnza lab + jza lab + jnzb lab + jzb lab + jnova0 lab + jova0 lab + jnovb0 lab + jovb0 lab + jnova1 lab + jova1 lab + jnovb1 lab + jovb1 lab + jnsa0 lab + jsa0 lab + jnsb0 lab + jsb0 lab + jnsa1 lab + jsa1 lab + jnsb1 lab + jsb1 lab + jdpl0 lab + jdplf lab + jnsiak lab + jsiak lab + jnsoak lab + jsoak lab + jnrqm lab + jrqm lab + jdpln0 lab + jdplnf lab +lab: + + ldi @non,1234h + ldi @a,1234h + ldi @b,1234h + ldi @tr,1234h + ldi @dp,1234h + ldi @rp,1234h + ldi @dr,1234h + ldi @sr,1234h + ldi @sol,1234h + ldi @som,1234h + ldi @k,1234h + ldi @klr,1234h + ldi @klm,1234h + ldi @l,1234h + ldi @mem,1234h + ldi @trb,1234h + + op mov @a,non + op mov @a,a + op mov @a,b + op mov @a,tr + op mov @a,dp + op mov @a,rp + op mov @a,ro + op mov @a,sgn + op mov @a,dr + op mov @a,drnf + op mov @a,sr + op mov @a,sim + op mov @a,sil + op mov @a,k + op mov @a,l + op mov @a,mem + + op mov @a,non + or acca,ram + op mov @a,non + or accb,ram + op mov @a,non + or acca,idb + op mov @a,non + or acca,m + op mov @a,non + or acca,n + op mov @a,non + and acca,ram + op mov @a,non + xor acca,ram + op mov @a,non + sub acca,ram + op mov @a,non + add acca,ram + op mov @a,non + sbb acca,ram + op mov @a,non + adc acca,ram + op mov @a,non + cmp acca,ram + op mov @a,non + inc accb + op mov @a,non + dec acca + op mov @a,non + shr1 accb + op mov @a,non + shl1 acca + op mov @a,non + shl2 accb + op mov @a,non + shl4 acca + op mov @a,non + xchg accb + op mov @a,non + nop + + op mov @a,non + dpnop + op mov @a,non + dpinc + op mov @a,non + dpdec + op mov @a,non + dpclr + + op mov @a,non + m0 + op mov @a,non + m1 + op mov @a,non + m2 + op mov @a,non + m3 + op mov @a,non + m4 + op mov @a,non + m5 + op mov @a,non + m6 + op mov @a,non + m7 + op mov @a,non + m8 + op mov @a,non + m9 + op mov @a,non + ma + op mov @a,non + mb + op mov @a,non + mc + op mov @a,non + md + op mov @a,non + me + op mov @a,non + mf + + op mov @a,non + rpnop + op mov @a,non + rpdec + + data 1,2,3 + data "a" + data "ab" + data "abc" + data "abcd" + data "abcde" + data "abcdef" + data "abcdefg" + data "abcdefgh" + diff --git a/tests/t_7725/t_7725.doc b/tests/t_7725/t_7725.doc new file mode 100644 index 0000000..c8d6a1a --- /dev/null +++ b/tests/t_7725/t_7725.doc @@ -0,0 +1,5 @@ ++-------------------------- Test Application 7725 ---------------------------+ +| | +| This is a (synthetic) test of the uPD7725 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_7725/t_7725.ori b/tests/t_7725/t_7725.ori new file mode 100644 index 0000000..667ba6d Binary files /dev/null and b/tests/t_7725/t_7725.ori differ diff --git a/tests/t_78c1x/asflags b/tests/t_78c1x/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_78c1x/t_78c1x.asm b/tests/t_78c1x/t_78c1x.asm new file mode 100644 index 0000000..4b9b143 --- /dev/null +++ b/tests/t_78c1x/t_78c1x.asm @@ -0,0 +1,258 @@ + cpu 78c10 + + block + calb + clc + daa + di + ei + exa + exh + exx + hlt + jb + jea + nega + nop + ret + reti + rets + rld + rrd + softi + stc + stop + table + + aci a,0 + aci h,10 + aci pc,55h + + adi a,40 + adi b,33o + adi eom,6 + + adinc a,56 + ani l,33h + eqi mkh,34 + gti a,20 + lti c,34 + nei mkl,10 + offi a,0ffh + oni d,0 + ori anm,47 + sbi a,41h + sui v,7 + suinb smh,98 + + xri a,055h + xri v,1010b + xri pb,40h + + adc a,v + adc v,a + addnc a,b + addnc b,a + sub a,c + sub c,a + sbb a,d + sbb d,a + subnb a,e + subnb e,a + ana a,h + ana h,a + ora a,l + ora l,a + xra a,v + xra v,a + gta a,b + gta b,a + lta a,c + lta c,a + nea a,d + nea d,a + eqa a,e + eqa e,a + ona a,h + ona h,a + offa a,l + offa l,a + + assume v:0 + + adcw 10h + addncw 20h + addw 30h + subw 40h + sbbw 50h + subnbw 60h + anaw 70h + oraw 80h + xraw 90h + gtaw 0a0h + ltaw 0b0h + neaw 0c0h + eqaw 0d0h + onaw 0e0h + offaw 0f0h + + adcx b + addncx d + addx h + subx d+ + sbbx h+ + subnbx d- + anax h- + orax b + xrax d + gtax h + ltax d+ + neax h+ + eqax d- + onax h- + offax b + + dadc ea,b + daddnc ea,d + dadd ea,h + dsub ea,b + dsbb ea,d + dsubnb ea,h + dan ea,b + dor ea,d + dxr ea,h + dgt ea,b + dlt ea,d + dne ea,h + deq ea,b + don ea,d + doff ea,h + + aniw 10h,'A' + eqiw 20h,'B' + gtiw 30h,'C' + ltiw 40h,'D' + neiw 50h,'E' + oniw 60h,'F' + offiw 70h,'G' + oriw 80h,'H' + + call 1234h + jmp 5678h + lbcd 1234h + sbcd 5678h + lded 1234h + sded 5678h + lhld 1234h + shld 5678h + lspd 1234h + sspd 5678h + + calf 0c08h + calt 150 + + bit 5,20h + bit 2,0ffh + + dcr a + inr b + mul c + div a + sll b + slr c + sllc a + slrc b + rll c + rlr a + + dcrw 20h + inrw 30h + ldaw 40h + staw 50h + + inx ea + dcx ea + inx h + dcx b + + dmov ea,b + dmov h,ea + dmov ea,ecpt + dmov etm0,ea + + drll ea + dsll ea + drlr ea + dslr ea + + eadd ea,b + esub ea,c + +back: nop + jr back + jre $-100 + jr forw + jre $+100 +forw: nop + + ldax b + ldax d + ldax h + ldax d+ + ldax h+ + ldax d- + ldax h- + ldax d+20 + ldax d-30 + ldax h+a + ldax h+b + ldax h+ea + ldax h+40 + ldax h-50 + stax b + stax d + stax h + stax d+ + stax h+ + stax d- + stax h- + stax d+20 + stax d-30 + stax h+a + stax h+b + stax h+ea + stax h+40 + stax h-50 + + ldeax h++ + steax d++ + ldeax h+ea + steax h-5 + + lxi sp,2000h + lxi h,101010101010b + lxi ea,1001 + + mov a,eal + mov h,a + mov a,pa + mov pa,a + mov c,1000h + mov 1234h,d + + mvi d,55h + mvi eom,0 + + mviw 20h,01101001b + mvix d,22o + + push va + push b + pop h + pop ea + + sk z + skn hc + + skit fsr + skint an6 diff --git a/tests/t_78c1x/t_78c1x.doc b/tests/t_78c1x/t_78c1x.doc new file mode 100644 index 0000000..61460db --- /dev/null +++ b/tests/t_78c1x/t_78c1x.doc @@ -0,0 +1,5 @@ ++------------------------ Test Application 78C1x ----------------------------+ +| | +| This is a (synthetic) test of the uPD78C1x instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_78c1x/t_78c1x.ori b/tests/t_78c1x/t_78c1x.ori new file mode 100644 index 0000000..e1c44ea Binary files /dev/null and b/tests/t_78c1x/t_78c1x.ori differ diff --git a/tests/t_78k0/asflags b/tests/t_78k0/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_78k0/t_78k0.asm b/tests/t_78k0/t_78k0.asm new file mode 100644 index 0000000..8dd0a33 --- /dev/null +++ b/tests/t_78k0/t_78k0.asm @@ -0,0 +1,291 @@ + cpu 78070 + page 0 + relaxed on + + include reg78k0.inc + +saddr equ 0fe80h +sfr equ 0ff90h + + brk + ret + retb + reti + nop + ei + di + halt + stop + adjba + adjbs + + mov d,#20 + mov saddr,#30 + mov sfr,#40 + mov a,c + mov e,a + mov a,saddr + mov saddr,a + mov a,sfr + mov sfr,a + mov a,!saddr + mov !saddr,r1 + mov psw,#40h + mov a,psw + mov psw,a + mov a,[de] + mov [de],a + mov a,[hl] + mov [hl],a + mov a,[hl+10] + mov [hl+10],a + mov a,[hl+b] + mov [hl+b],a + mov a,[hl+c] + mov [hl+c],a + + xch a,d + xch l,a + xch a,saddr + xch a,sfr + xch a,!saddr + xch a,[de] + xch a,[hl] + xch a,[hl+10] + xch a,[hl+b] + xch a,[hl+c] + + movw de,#1000 + movw saddr,#2000 + movw sfr,#3000 + movw ax,saddr + movw saddr,ax + movw ax,sfr + movw sfr,ax + movw ax,de + movw hl,ax + movw ax,!saddr + movw !saddr,ax + + xchw ax,de + xchw hl,ax + + add a,#10 + add saddr,#20 + add a,c + add h,a + add a,saddr + add a,!saddr + add a,[hl] + add a,[hl+10] + add a,[hl+b] + add a,[hl+c] + + addc a,#10 + addc saddr,#20 + addc a,c + addc h,a + addc a,saddr + addc a,!saddr + addc a,[hl] + addc a,[hl+10] + addc a,[hl+b] + addc a,[hl+c] + + sub a,#10 + sub saddr,#20 + sub a,c + sub h,a + sub a,saddr + sub a,!saddr + sub a,[hl] + sub a,[hl+10] + sub a,[hl+b] + sub a,[hl+c] + + subc a,#10 + subc saddr,#20 + subc a,c + subc h,a + subc a,saddr + subc a,!saddr + subc a,[hl] + subc a,[hl+10] + subc a,[hl+b] + subc a,[hl+c] + + and a,#10 + and saddr,#20 + and a,c + and h,a + and a,saddr + and a,!saddr + and a,[hl] + and a,[hl+10] + and a,[hl+b] + and a,[hl+c] + + or a,#10 + or saddr,#20 + or a,c + or h,a + or a,saddr + or a,!saddr + or a,[hl] + or a,[hl+10] + or a,[hl+b] + or a,[hl+c] + + xor a,#10 + xor saddr,#20 + xor a,c + xor h,a + xor a,saddr + xor a,!saddr + xor a,[hl] + xor a,[hl+10] + xor a,[hl+b] + xor a,[hl+c] + + cmp a,#10 + cmp saddr,#20 + cmp a,c + cmp h,a + cmp a,saddr + cmp a,!saddr + cmp a,[hl] + cmp a,[hl+10] + cmp a,[hl+b] + cmp a,[hl+c] + + addw ax,#1234h + subw rp0,#2345h + cmpw ax,#3456h + + mulu x + divuw c + + inc d + inc saddr + dec e + dec saddr + + incw hl + decw de + + ror a,1 + rol a,1 + rorc a,1 + rolc a,1 + + ror4 [hl] + rol4 [hl] + + mov1 cy,saddr.3 + mov1 cy,sfr.4 + mov1 cy,a.5 + mov1 cy,psw.6 + mov1 cy,[hl].7 + mov1 saddr.3,cy + mov1 sfr.4,cy + mov1 a.5,cy + mov1 psw.6,cy + mov1 [hl].7,cy + + and1 cy,saddr.3 + and1 cy,sfr.4 + and1 cy,a.5 + and1 cy,psw.6 + and1 cy,[hl].7 + + or1 cy,saddr.3 + or1 cy,sfr.4 + or1 cy,a.5 + or1 cy,psw.6 + or1 cy,[hl].7 + + xor1 cy,saddr.3 + xor1 cy,sfr.4 + xor1 cy,a.5 + xor1 cy,psw.6 + xor1 cy,[hl].7 + + set1 saddr.3 + set1 sfr.4 + set1 a.5 + set1 psw.6 + set1 [hl].7 + + clr1 saddr.3 + clr1 sfr.4 + clr1 a.5 + clr1 psw.6 + clr1 [hl].7 + + set1 cy + clr1 cy + not1 cy + + call 1234h + callf 234h + callt [12h] + + push psw + push de + pop psw + pop hl + + movw sp,#1234h + movw sp,ax + movw ax,sp + + br ax + br rp0 + br 1234h + br pc + br $pc + br !pc + + bc pc + bnc pc + bz pc + bnz pc + + bt saddr.3,pc + bt sfr.4,pc + bt a.5,pc + bt psw.6,pc + bt [hl].7,pc + + bf saddr.3,pc + bf sfr.4,pc + bf a.5,pc + bf psw.6,pc + bf [hl].7,pc + + btclr saddr.3,pc + btclr sfr.4,pc + btclr a.5,pc + btclr psw.6,pc + btclr [hl].7,pc + + dbnz b,pc + dbnz c,pc + dbnz saddr,pc + + sel rb0 + sel rb1 + sel rb2 + sel rb3 + + db 1,2,3 + dw 1,2,3 + dd 1,2,3 + dd 1.0,2.0,3.0 + dq 1.0,2.0,3.0 + dt 1.0,2.0,3.0 + db 10 dup (?) + db 0 + + end + diff --git a/tests/t_78k0/t_78k0.doc b/tests/t_78k0/t_78k0.doc new file mode 100644 index 0000000..3d02b67 --- /dev/null +++ b/tests/t_78k0/t_78k0.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 78K0 ----------------------------+ +| | +| This is a (synthetic) test of the 78K0 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_78k0/t_78k0.ori b/tests/t_78k0/t_78k0.ori new file mode 100644 index 0000000..5b6fc6a Binary files /dev/null and b/tests/t_78k0/t_78k0.ori differ diff --git a/tests/t_85/asflags b/tests/t_85/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_85/t_85.asm b/tests/t_85/t_85.asm new file mode 100644 index 0000000..3243692 --- /dev/null +++ b/tests/t_85/t_85.asm @@ -0,0 +1,134 @@ + cpu 8085 + page 0 + + mov d,h + mov m,a + mov c,m + mvi d,12h + mvi m,12h + lxi b,1234h + lxi d,1234h + lxi h,1234h + stax b + stax d + stax h + ldax b + ldax d + ldax d + ldax h + sta 1234h + lda 1234h + shld 1234h + lhld 1234h + xchg + + push b + push d + push h + push psw + pop b + pop d + pop h + pop psw + xthl + sphl + lxi sp,1234h + inx sp + dcx sp + + jmp 1234h + jc 1234h + jnc 1234h + jz 1234h + jnz 1234h + jp 1234h + jm 1234h + jpe 1234h + jpo 1234h + pchl + + call 1234h + cc 1234h + cnc 1234h + cz 1234h + cnz 1234h + cp 1234h + cm 1234h + cpe 1234h + cpo 1234h + + ret + rc + rnc + rz + rnz + rp + rm + rpe + rpo + + rst 2 + + in 12h + out 12h + + inr d + dcr h + inr m + dcr m + inx b + inx d + inx h + dcx b + dcx d + dcx h + + add c + adc d + add m + adc m + adi 12h + aci 12h + dad b + dad d + dad h + dad sp + + sub c + sbb d + sub m + sbb m + sui 12h + sbi 12h + + ana c + xra c + ora c + cmp c + ana m + xra m + ora m + cmp m + ani 12h + xri 12h + ori 12h + cpi 12h + + rlc + rrc + ral + rar + + cma + stc + cmc + daa + + ei + di + nop + hlt + + rim + sim + diff --git a/tests/t_85/t_85.doc b/tests/t_85/t_85.doc new file mode 100644 index 0000000..244e635 --- /dev/null +++ b/tests/t_85/t_85.doc @@ -0,0 +1,5 @@ ++-------------------------- Test Application 85 -----------------------------+ +| | +| This is a (synthetic) test of the 8080/8085 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_85/t_85.ori b/tests/t_85/t_85.ori new file mode 100644 index 0000000..0bbef41 Binary files /dev/null and b/tests/t_85/t_85.ori differ diff --git a/tests/t_87c800/asflags b/tests/t_87c800/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_87c800/t_87c800.asm b/tests/t_87c800/t_87c800.asm new file mode 100644 index 0000000..c8e1276 --- /dev/null +++ b/tests/t_87c800/t_87c800.asm @@ -0,0 +1,310 @@ + cpu 87c70 + include stddef87.inc + page 0 + + ei + di + swi + nop + ret + reti + retn + +targ: jrs t,targ + jrs f,targ + + jr t,targ + jr f,targ + jr eq,targ + jr z,targ + jr ne,targ + jr nz,targ + jr cs,targ + jr lt,targ + jr cc,targ + jr ge,targ + jr le,targ + jr gt,targ + jr targ + + daa a + daa b + das a + das c + shlc a + shlc d + shrc a + shrc e + rolc a + rolc h + rorc a + rorc l + swap a + swap b + + add a,c + addc l,a + sub wa,de + subb a,(12h) + and a,(hl) + or a,(de) + xor a,(hl+) + cmp a,(-hl) + add a,(hl+10) + addc a,(hl-125) + sub a,(hl+c) + subb a,(c+hl) + and a,(pc+a) + or a,(a+pc) + cmp (12h),(hl) + add (de),(hl) + addc (hl+5),(hl) + sub (hl+c),(hl) + subb (pc+a),(hl) + and a,55h + or c,55h + xor hl,5678h + cmp (12h),55h + add (hl),55h + addc (hl+),55h + sub (-hl),55h + subb (hl-32),55h + and (hl+c),55h + or (pc+a),55h + + mcmp (12h),55h + mcmp (de),55h + mcmp (hl+),55h + mcmp (-hl),55h + mcmp (hl+3),55h + mcmp (c+hl),55h + mcmp (pc+a),55h + + inc c + inc bc + inc (12h) + inc (hl) + inc (de) + inc (hl+) + inc (-hl) + inc (hl+4) + inc (hl+c) + inc (a+pc) + dec e + dec hl + dec (12h) + dec (hl) + dec (de) + dec (hl+) + dec (-hl) + dec (hl-7) + dec (hl+c) + dec (pc+a) + + mul w,a + mul c,b + mul d,e + mul l,h + + div wa,c + div de,c + div hl,c + + rold a,(12h) + rold a,(hl) + rold a,(hl+) + rold a,(-hl) + rold a,(hl+16) + rold a,(c+hl) + rord a,(12h) + rord a,(hl) + rord a,(hl+) + rord a,(-hl) + rord a,(hl-16) + rord a,(hl+c) + + xch a,d + xch d,w + xch hl,de + xch bc,wa + xch b,(12h) + xch (12h),c + xch d,(hl) + xch (de),e + xch l,(hl+) + xch (hl+),h + xch a,(-hl) + xch (-hl),w + xch b,(hl+5) + xch (hl-3),c + xch d,(hl+c) + xch (c+hl),e + xch h,(pc+a) + xch (a+pc),l + + clr b + clr de + clr (12h) + clr (hl) + clr (de) + clr (hl+) + clr (-hl) + clr (hl+5) + + ldw hl,1234h + ldw (12h),1234h + ldw (hl),1234h + + ld a,l + ld d,a + ld w,h + ld a,(12h) + ld c,(12h) + ld a,(hl) + ld d,(hl) + ld c,(de) + ld b,(-hl) + ld h,(hl+) + ld c,(hl-122) + ld w,(hl+c) + ld d,(a+pc) + ld h,20 + + ld hl,bc + ld de,(12h) + ld bc,(de) + ld wa,(hl+1) + ld hl,(hl+c) + ld de,(pc+a) + ld bc,1234 + + ld (12h),a + ld (12h),c + ld (12h),de + ld (12h),(23h) + ld (12h),(de) + ld (12h),(hl-42) + ld (12h),(hl+c) + ld (12h),(pc+a) + ld (12h),23h + + ld (hl),a + ld (de),d + ld (hl+),c + ld (-hl),e + ld (hl+4),h + ld (hl),de + ld (hl+5),bc + ld (hl),(12h) + ld (hl),(de) + ld (hl),(hl+1) + ld (hl),(hl+c) + ld (hl),(pc+a) + ld (hl),23h + ld (de),23h + ld (hl+),23h + ld (-hl),23h + ld (hl-77),23h + + ld sp,1234h + ld sp,de + ld hl,sp + ld rbs,7 + + jp 2000h + call 1234h + call 0ff54h + jp hl + call de + jp (hl) + jp (de) + jp (12h) + call (12h) + jp (hl+5) + call (hl-100) + jp (hl+c) + call (a+pc) + jp (c+hl) + call (pc+a) + + callv 3 + + callp 76h + callp 0ff12h + + push psw + push de + pop wa + pop psw + + ld cf,a.5 + ld cf,(12h).4 + ld cf,(hl).3 + ld cf,(hl+).2 + ld cf,(-hl).1 + ld cf,(hl+3).0 + ld cf,(hl+c).7 + ld cf,(pc+a).3 + ld cf,(de).c + + ld a.5,cf + ld (12h).4,cf + ld (hl).3,cf + ld (hl+).2,cf + ld (-hl).1,cf + ld (hl+3).0,cf + ld (hl+c).7,cf + ld (pc+a).3,cf + ld (de).c,cf + + xor cf,d.3 + xor cf,(12h).4 + xor cf,(de).5 + xor cf,(hl+).6 + xor cf,(-hl).7 + xor cf,(hl+3).0 + xor cf,(hl+c).1 + xor cf,(pc+a).2 + + clr cf + clr d.3 + clr (12h).4 + clr (de).5 + clr (hl+).6 + clr (-hl).7 + clr (hl+3).0 + clr (hl+c).1 + clr (pc+a).2 + clr (de).c + + set cf + set d.3 + set (12h).4 + set (de).5 + set (hl+).6 + set (-hl).7 + set (hl+3).0 + set (hl+c).1 + set (pc+a).2 + set (de).c + + cpl cf + cpl d.3 + cpl (12h).4 + cpl (de).5 + cpl (hl+).6 + cpl (-hl).7 + cpl (hl+3).0 + cpl (hl+c).1 + cpl (pc+a).2 + cpl (de).c + + test d.3 + test (12h).4 + test (de).5 + test (hl+).6 + test (-hl).7 + test (hl+3).0 + test (hl+c).1 + test (pc+a).2 + test (de).c \ No newline at end of file diff --git a/tests/t_87c800/t_87c800.doc b/tests/t_87c800/t_87c800.doc new file mode 100644 index 0000000..3a5a505 --- /dev/null +++ b/tests/t_87c800/t_87c800.doc @@ -0,0 +1,5 @@ ++------------------------ Test Application 87C800 ---------------------------+ +| | +| This is a (synthetic) test of the TLCS-870 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_87c800/t_87c800.ori b/tests/t_87c800/t_87c800.ori new file mode 100644 index 0000000..662b119 Binary files /dev/null and b/tests/t_87c800/t_87c800.ori differ diff --git a/tests/t_8x30x/asflags b/tests/t_8x30x/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_8x30x/t_8x30x.asm b/tests/t_8x30x/t_8x30x.asm new file mode 100644 index 0000000..9062243 --- /dev/null +++ b/tests/t_8x30x/t_8x30x.asm @@ -0,0 +1,57 @@ + cpu 8x305 + +leftobj liv $12,3,4 +left2obj liv $12,5,6 +rightobj riv $34,5,6 +right2obj riv $34,3,4 + + move r3,ivl ; Register-->Register: ohne Rotation + add r11(3),r5 ; mit Rotation + and liv1,r1 ; I/O -->Register: direkt, ohne L„nge + xor riv3,6,r4 ; direkt, mit L„nge + move leftobj,r5 ; symbolisch, ohne L„nge + add leftobj,4,r5 ; symbolisch, mit L„nge (redundant) + and r2,liv6 ; Register-->I/O direkt, ohne L„nge + xor r3,3,riv4 ; direkt, mit L„nge + move r11,rightobj ; symbolisch, ohne L„nge + add r11,6,rightobj ; symbolisch, mit L„nge (redundant) + and liv2,riv4 ; Register-->Register: direkt-->direkt, ohne L„nge + xor liv2,5,riv4 ; direkt-->direkt, mit L„nge + move riv1,leftobj ; direkt-->symbolisch, ohne L„nge + add riv1,4,leftobj ; direkt-->symbolisch, mit L„nge(redundant) + and rightobj,liv5 ; symbolisch-->direkt, ohne L„nge + xor rightobj,6,liv5 ; symbolisch-->direkt, mit L„nge(redundant) + move leftobj,right2obj ; symbolisch-->symbolisch, ohne L„ange + add leftobj,4,right2obj ; symbolisch-->symbolisch, mit L„nge(redundant) + + xec $55(r5) + xec $12(liv3) + xec $12(liv3),6 + xec $12(leftobj) + xec $12(leftobj),4 + + nzt r5,* + nzt liv3,* + nzt liv3,6,* + nzt leftobj,* + nzt leftobj,4,* + + xmit $34,r5 + xmit $12,liv3 + xmit $12,liv3,6 + xmit $12,leftobj + xmit $12,leftobj,4 + + sel leftobj + sel rightobj + + nop + + halt + + xml 2 + xmr $0f + +temp1 riv @200,7,8 + sel temp1 + diff --git a/tests/t_8x30x/t_8x30x.doc b/tests/t_8x30x/t_8x30x.doc new file mode 100644 index 0000000..06e7536 --- /dev/null +++ b/tests/t_8x30x/t_8x30x.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 8X30x ---------------------------+ +| | +| This is a (synthetic) test of the 8X30x instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_8x30x/t_8x30x.ori b/tests/t_8x30x/t_8x30x.ori new file mode 100644 index 0000000..0370a9e Binary files /dev/null and b/tests/t_8x30x/t_8x30x.ori differ diff --git a/tests/t_96/asflags b/tests/t_96/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_96/t_96.asm b/tests/t_96/t_96.asm new file mode 100644 index 0000000..a98eef5 --- /dev/null +++ b/tests/t_96/t_96.asm @@ -0,0 +1,217 @@ + cpu 80196 + + include reg96 + +ax equ 20h +al equ ax +ah equ ax+1 +eax equ ax +bx equ 24h +bl equ bx +bh equ bx+1 +ebx equ bx +cx equ 28h +cl equ cx +ch equ cx+1 +ecx equ cx +dx equ 2ch +dl equ dx +dh equ dx+1 +edx equ dx + + CLRC + CLRVT + DI + EI + NOP + POPF + PUSHF + RET + RSC + SETC + TRAP + PUSHA + POPA + EPTS + DPTS + +targ: + JC targ + JE targ + JGE targ + JGT targ + JH targ + JLE targ + JLT targ + JNC targ + JNE targ + JNH targ + JNST targ + JNV targ + JNVT targ + JST targ + JV targ + JVT targ + + bmov eax,cx + bmovi eax,cx + + add ax,bx + add ax,2000h + add ax,[bx] + add ax,[bx]+ + add ax,2[bx] + add ax,-15[bx] + add ax,700[bx] + add ax,-300[bx] + add ax,#1234h + + add ax,cx,bx + add ax,cx,2000h + add ax,cx,[bx] + add ax,cx,[bx]+ + add ax,cx,2[bx] + add ax,cx,-15[bx] + add ax,cx,700[bx] + add ax,cx,-300[bx] + add ax,cx,#1234h + + addb al,bl + addb al,2000h + addb al,[bx] + addb al,[bx]+ + addb al,2[bx] + addb al,-15[bx] + addb al,700[bx] + addb al,-300[bx] + addb al,#12h + + addb al,cl,bl + addb al,cl,2000h + addb al,cl,[bx] + addb al,cl,[bx]+ + addb al,cl,2[bx] + addb al,cl,-15[bx] + addb al,cl,700[bx] + addb al,cl,-300[bx] + addb al,cl,#12h + + and dx,300h + mulu eax,bx,cx + mulb ax,cl,ch + subb cl,#5 + + addc ax,bx + addcb al,[bx] + cmp ax,[bx]+ + cmpb al,2[bx] + cmpl ecx,edx + div eax,-15[bx] + divb ax,200[bx] + divu eax,-300[bx] + divub ax,200 + ld ax,#2345h + ldb al,#16 + st ax,bx + stb al,[bx] + subc ax,[bx]+ + subcb al,2[bx] + xor ax,-15[bx] + xorb al,200[bx] + + push ax + push [bx] + push #1234h + pop 2000h + pop 10[cx] + + xch ax,bx + xch ax,[bx] + xch ax,10[bx] + xch ax,-150[bx] + xch ax,[bx]+ + xch ax,2000h + xchb bl,al + xchb [bx],al + xchb 10[bx],al + xchb -150[bx],al + xchb [bx]+,al + xchb 2000h,al + + clr ax + clrb al + dec bx + decb bh + ext eax + extb ax + inc cx + incb cl + neg dx + negb dh + not ax + notb al + + scall targ + lcall targ + call targ + + sjmp targ + ljmp targ + br targ + br [dx] + + djnz cl,$ + djnzw cx,$ + + jbc dh,3,$ + jbs al,1,$ + + tijmp bx,ax,#127 + + ldbse ax,#-1 + ldbze cx,[bx]+ + + norml eax,cl + + shl ax,#5 + shl ax,cl + shlb al,#6 + shlb al,cl + shll eax,#7 + shll eax,cl + shr ax,#5 + shr ax,cl + shrb al,#6 + shrb al,cl + shrl eax,#7 + shrl eax,cl + shra ax,#5 + shra ax,cl + shrab al,#6 + shrab al,cl + shral eax,#7 + shral eax,cl + + skip dl + + idlpd #2 + + + ldb al,100h ; lang + ldb al,0c0h ; kurz + ldb al,000h ; kurz + ldb al,140h ; lang + ldb al,[0c0h] + ldb al,[000h] + + assume wsr:24h ; =100h..13fh auf 0c0h..0ffh + + ldb al,100h ; jetzt kurz + ldb al,0c0h ; jetzt lang + ldb al,000h ; immmer noch kurz + ldb al,140h ; immer noch lang + ldb al,[100h] + ldb al,[000h] + + bne 2000h + bc 2000h diff --git a/tests/t_96/t_96.doc b/tests/t_96/t_96.doc new file mode 100644 index 0000000..6e89bc7 --- /dev/null +++ b/tests/t_96/t_96.doc @@ -0,0 +1,5 @@ ++-------------------------- Test Application 96 -----------------------------+ +| | +| This is a (synthetic) test of the MCS-96 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_96/t_96.ori b/tests/t_96/t_96.ori new file mode 100644 index 0000000..d8d17cd Binary files /dev/null and b/tests/t_96/t_96.ori differ diff --git a/tests/t_960/asflags b/tests/t_960/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_960/t_960.asm b/tests/t_960/t_960.asm new file mode 100644 index 0000000..df58c12 --- /dev/null +++ b/tests/t_960/t_960.asm @@ -0,0 +1,101 @@ + cpu 80960 + org 0 + + fpu on + supmode on + +start: + flushreg + fmark + mark + ret + syncf + faultno + faultg + faulte + faultge + faultl + faultne + faultle + faulto + + addc r3,r4,r5 ; lokale Register + addc g3,g4,g5 ; globale Register + addc g3,g5 ; impl. src2=dest + addc 10,r4,g10 ; src1 immediate + addc g2,20,g4 ; src2 immediate + + addr r3,r4,r5 ; Float: normale Register + addr fp2,r4,r5 ; Float-Register + addr r3,fp1,r5 + addr r3,r4,fp3 + addr 0,r4,r5 ; Float-Konstanten + addr r3,1,r5 + + addc sp,fp,rip ; Sonderregister + + addi r3,r4,r5 ; nur noch mal zum Testen der Opcodes... + addo r3,r4,r5 + + calls g2 ; nur ein Operand: + calls 4 + + chkbit 7,r5 ; kein Ziel + + classr fp1 ; ein Float-Operand + classrl g4 + + cosr fp1 ; dito mit Ziel + cosr g4,fp2 + + modpc r3,r4,r5 ; nur im Supervisor-Mode erlaubt + + bbc r4,g5,$+32 ; COBR-Anweisungen + bbs 10,r10,$+32 + cmpobge 10,r4,$+32 + testne r5 + + b $-32 ; CTRL-Anweisungen + call $+32 + bal $+64 + ble $-64 + + bx (r5) ; MEMA ohne disp + bx 2345(r5) ; MEMA mit disp + bx 2345 ; MEMA ohne base + bx -30(r5) ; MEMB base+disp + bx 5000(r5) ; dito positiv + bx $(ip) ; PC-relativ + bx [r4] ; nur Index + bx [r4*1] ; Scaling + bx [r4*2] + bx [r4*4] + bx [r4*8] + bx [r4*16] + bx 0(r5)[r4] ; base+index + bx 12345678h ; nur disp + bx 450[r6*4] ; disp+index + bx 123(r5)[r6*4] ; volles Programm + + st r7,123(r5)[r6*4]; mit 2 Ops + ld 123(r5)[r6*4],r7 + + db 1 + align 4 + db 1,2 + align 4 + db 1,2,3 + align 4 + db 1,2,3,4 + dw 1 + align 4 + dw 1,2 + dd 1 + dd 1.0 + dq 1.0 + dt 1.0 + dw 0 + + space 32 + + word 1,2,3,4,5 diff --git a/tests/t_960/t_960.doc b/tests/t_960/t_960.doc new file mode 100644 index 0000000..177a972 --- /dev/null +++ b/tests/t_960/t_960.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 960 -----------------------------+ +| | +| This is a (very incomplete) test of the i960 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_960/t_960.ori b/tests/t_960/t_960.ori new file mode 100644 index 0000000..26b7924 Binary files /dev/null and b/tests/t_960/t_960.ori differ diff --git a/tests/t_97c241/asflags b/tests/t_97c241/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_97c241/t_97c241.asm b/tests/t_97c241/t_97c241.asm new file mode 100644 index 0000000..3c117fb --- /dev/null +++ b/tests/t_97c241/t_97c241.asm @@ -0,0 +1,336 @@ + page 0 + + cpu 97c241 + + unlk + szf + svf + ssf + scf + rzf + rvf + rsf + rets + reti + ret + rcf + nop + halt + ei + di + czf + cvf + csf + ccf + +Targ: jr Targ + calr Targ + jr $+1002h + + jrc z,Targ + jrc ult,Targ + jrc ge,Targ + + jrbc 5,1234h,$+108h + jrbs 1,345h,Targ + + djnz rw5,Targ + djnz.d (123456h),$+100ah + djnzc rw6,nov,Targ + djnzc.d (rd2+123456h),eq,$+100ah + + link 20h + link 3334h + retd -122 + retd -1234 + + swi 7 + + cpl rb2 + cpl rw12 + cpl rd14 + + cpl.b rb5 + cpl.w rw15 + cpl.d rd4 + + cpl.b (123h) + cpl.w (123h) + cpl.d (123h) + + cpl.b (123456h) + cpl.w (123456h) + cpl.d (123456h) + + cpl.b (rw2) + cpl.w (rw5) + cpl.d (rw0) + + cpl.b (rd10) + cpl.w (rd6 ) + cpl.d (rd12) + + cpl.b (rw4++) + cpl.w (rw6++) + cpl.d (rw9++) + + cpl.b (--rw8) + cpl.w (--rw7) + cpl.d (--rw5) + + cpl.b (rd2++) + cpl.w (rd10++) + cpl.d (rd14++) + + cpl.b (--rd4) + cpl.w (--rd8) + cpl.d (--rd12) + + cpl.b (rw3+123h) + cpl.w (rw7+123h) + cpl.d (rw1+123h) + + cpl.b (rd2-123h) + cpl.w (rd8-123h) + cpl.d (rd4-123h) + + cpl.b (rw4 +123456h) + cpl.w (rw7 +123456h) + cpl.d (rw14+123456h) + + cpl.b (rd6 -123456h) + cpl.w (rd12-123456h) + cpl.d (rd10-123456h) + + cpl.b (rw0+12h) + cpl.w (rw0+12h) + cpl.d (rw0+12h) + + cpl.b (rd0-12h) + cpl.w (rd0-12h) + cpl.d (rd0-12h) + + cpl.b (rw0+12345h) + cpl.w (rw0+12345h) + cpl.d (rw0+12345h) + + cpl.b (rd0-12345h) + cpl.w (rd0-12345h) + cpl.d (rd0-12345h) + + cpl.b (sp+12h) + cpl.w (sp+12h) + cpl.d (sp+12h) + + cpl.b (sp+89h) + cpl.w (sp+89h) + cpl.d (sp+89h) + + cpl.b (sp+12345h) + cpl.w (sp+12345h) + cpl.d (sp+12345h) + + cpl.b (pc-89h) + cpl.w (pc-89h) + cpl.d (pc-89h) + + cpl.b (pc-12345h) + cpl.w (pc-12345h) + cpl.d (pc-12345h) + + cpl.b (rw2 *4) + cpl.w (rw5 *4) + cpl.d (rw10*4) + + cpl.b (13h+rd10*8) + cpl.w (rd14*8+12h) + cpl.d (rd4 *8+12h) + + cpl.b (rw7*2-12345h) + cpl.w (rw9*2-12345h) + cpl.d (rw1*2-12345h) + + cpl.b (rd10*2+12345h) + cpl.w (rd4 *2+12345h) + cpl.d (rd6 *2+12345h) + + cpl.b (rw4 + rw6 *8 + 12h) + cpl.w (rw5 + rd8 *4 + 12h) + cpl.d (rd4 + rw9 *2 + 12h) + cpl.b (rd10 + rd14 *1 + 12h) + cpl.w (sp + rw5 *2 + 12h) + cpl.d (sp + rd2 *4 + 12h) + cpl.b (pc + rw11 *8 + 12h) + cpl.w (pc + rd4 *4 + 12h) + + cpl sp + cpl isp + cpl esp + cpl pbp + cpl cbp + cpl psw + cpl imc + cpl cc + + call targ + call (rw2) + call.w 123456h + clr rb5 + clr.w (rw3-4) + clr.d (--rd2) + exts rw1 + exts.d (sp+20) + extz.w (pc-7) + extz.d rd12 + jp Targ + jp.w (rd4++) + jp.d (--rw5) + mirr rb1 + mirr.w (Targ) + mirr.d (sp+1234h) + neg.d rd8 + pop.b (rd10++) + push.d 12345678h + pusha Targ + rvby.w (sp+rw4*4+0aah) + tjp.d (rd6) + tst.w rw13 + + lda rd6,(rd4+12345h) + + add3 rw4,(rd4),(rw2) + sub3 rw4,(rd4),1000 + add3 rw4,(rd4),100 + sub3 rd2,rd10,(123456h) + add3 rd8,(rw2*4+12345h),10 + sub3 rb5,rb3,rb15 + + mac rw4,rb3,rb1 + macs rd14,(rw4-2),(rd2+4) + + cpsz (rd6++),rb2,rw15 + cpsn.w (--rd4),(--rd10),rw14 + lds.d (rd8++),10,rw13 + lds.w (--rd10),1000,rw12 + + rrm.b rb5,rw3,4 + rlm.d (123456h),rw4,(123456h) + + bfex rw7,rd10,2,12 + bfexs.b rw9,(rd4),4,6 + bfin.w (sp+5),rw3,10,3 + bfex rw10,rd12,20,5 + bfexs.d rw12,(rd4),30,2 + + abcd rb5,(rw2*4) + abcd rw4,(1234h) + abcd (1234h),rd4 + adc.w (rd4+2),(rd2*8+5) + adc.b (Targ),4 + cbcd.b (Targ),99h + cpc rb5,(rw4+rw4) + cpc rb5,(2) + max rb5,rb2 + maxs rw5,(Targ) + min.d (Targ),(rw2) + mins.d (rd4+3),(rd6-3) + sbc.w (rd4),(rd2) + sbc.d (Targ),1 + sbcd rw4,(Targ) + sbcd (rd2),rd0 + + andcf rw10,15 + andcf.b (rd2),(rw4) + andcf.d (rw10),(Targ) + andcf.w (Targ),1 + ldcf rw10,15 + ldcf.b (rd2),(rw4) + ldcf.d (rw10),(Targ) + ldcf.w (Targ),1 + orcf rw10,15 + orcf.b (rd2),(rw4) + orcf.d (rw10),(Targ) + orcf.w (Targ),1 + stcf rw10,15 + stcf.b (rd2),(rw4) + stcf.d (rw10),(Targ) + stcf.w (Targ),1 + tset rw10,15 + tset.b (rd2),(rw4) + tset.d (rw10),(Targ) + tset.w (Targ),1 + xorcf rw10,15 + xorcf.b (rd2),(rw4) + xorcf.d (rw10),(Targ) + xorcf.w (Targ),1 + + bs0b rb10,rd12 + bs0f (Targ),rw3 + bs1b.w rb10,(Targ) + bs1f.b (Targ),(rw10+2) + + chk.d:g (Targ),rd8 + chk.d (Targ),rd8 + chks.w (rd6),(rd4) + chks.w (rw2),(Targ) + + mul rd2,rw1 + muls.w (rw2),(Targ) + div.d (Targ),(rw2) + divs rw4,rb8 + + add rw11,2 + add (rw4),rd8 + add.w (rd4+2),(rd6+rd8*4+100) + add.b rb2,150 + add.w rw2,150 + add.d rd2,150 + add.d (Targ),2 + add.w:a rw14,(Targ) ; !!! automatische Wahl sonst S + + ld rd10,2000 + cp rd8,(Targ) + sub.w (rd4++),(rd6++) + + and rw4,rw3 + and.d rd10,rd12 + or rd10,(rd8) + or.w (Targ),(rd4+rw2*4-5) + xor.d (Targ),12345678h + xor rd2,1000h + or rb2,rb7 + and.w (Targ),rw4 + xor.d (rw2),(Targ) + + bres rb4,1 + bset rw7,5 + bchg rw12,10 + btst rd4,8 + bres rd12,20 + bset.w (rd4),10 + bchg.d (rw2),15 + btst.b (Targ),rb1 + bres rb1,(Targ) + + ex rb1,rb7 + ex rw5,(rd4) + ex.d (Targ),(rw1) + ex.b (rw1),(Targ) + + rl rw4,1 + rlc.w (rd6*2),1 + rr rd0,5 + rrc rw1,(rd4) + sla rw7,(Targ) + sll.d (Targ),3 + sra.w (rd4),(rw4) + srl.b (rw4),(rd4) + + add.w (rw4+0eah),rw7 + add.w (sp+rw4*4+1234h),(sp+28h) + add.w:g (rw4+12345h),(10028h) + add.w (rw4+12345h),(10028h) + add.w:g (rw4+56h),3579h + add.w (rw4+56h),3579h + jrc nz,$-1234h + diff --git a/tests/t_97c241/t_97c241.doc b/tests/t_97c241/t_97c241.doc new file mode 100644 index 0000000..08358f7 --- /dev/null +++ b/tests/t_97c241/t_97c241.doc @@ -0,0 +1,5 @@ ++------------------------ Test Application 97C241 ---------------------------+ +| | +| This is a (synthetic) test of the TLCS-9000 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_97c241/t_97c241.ori b/tests/t_97c241/t_97c241.ori new file mode 100644 index 0000000..6b72195 Binary files /dev/null and b/tests/t_97c241/t_97c241.ori differ diff --git a/tests/t_9900/asflags b/tests/t_9900/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_9900/t_9900.asm b/tests/t_9900/t_9900.asm new file mode 100644 index 0000000..1c15261 --- /dev/null +++ b/tests/t_9900/t_9900.asm @@ -0,0 +1,222 @@ + cpu tms9900 + page 0 + supmode on + + a r5,r3 + + a wr5,wr3 + ab wr6,*wr10 + c wr7,*wr2+ + cb wr8,@1234h + s wr9,@1234h(wr6) + + sb *wr10,wr9 + soc *wr11,*wr6 + socb *wr12,*wr1+ + szc *wr13,@1234h + szcb *wr14,@1234h(wr14) + + mov *wr15+,wr10 + movb *wr0+,*wr6 + a *wr1+,*wr6+ + ab *wr2+,@1234h + c *wr3+,@1234h(wr7) + + cb *wr4+,wr5 + s *wr5+,*wr13 + sb *wr6+,*wr13+ + soc *wr7+,@1234h + socb *wr8+,@1234h(wr12) + + szc @1234h,wr10 + szcb @1234h,*wr2 + mov @1234h,*wr3+ + movb @1234h,@2345h + a @1234h,@2345h(wr8) + + ab @1234h(wr9),wr5 + c @1234h(wr10),*wr1 + cb @1234h(wr11),*wr14+ + s @1234h(wr12),@2345h + sb @1234h(wr13),@2345h(wr5) + + + coc wr12,wr5 + czc *wr4,wr10 + xor *wr12+,wr7 + mpy @1234h,wr4 + div @200(wr4),wr6 + xop @2345h,wr5 + + mpys wr5 + divs *wr9+ + + b @1234h + bl *wr5 + blwp *wr7+ + clr wr4 + seto @1234h(wr8) + inv wr7 + neg *wr15 + abs wr3 + swpb wr9 + inc *wr12+ + inct *wr12+ + dec *wr12+ + dect *wr12+ + x *wr6 + + ldcr wr5,10 + stcr wr6,16 + + sbo 10 + sbz -33 + tb 34h + + jeq lab + jgt lab + jh lab + jhe lab + jl lab + jle lab +lab: jlt lab + jmp lab + jnc lab + jne lab + jno lab + joc lab + jop lab + + sla wr1,1 + sra wr5,wr0 + src wr6,10 + srl wr10,15 + + ai wr5,1234h + andi wr10,2345h + ci wr15,3456h + li wr5,4567h + ori wr10,5678h + + lwpi 1234h + limi 2345h + + stst wr2 + lst wr4 + stwp wr6 + lwp wr8 + + rtwp + idle + rset + ckof + ckon + lrex + + padding on + + byte 1,2,3,4,5 + byte "Hello World" + byte 1,2,3,4,5,6 + byte "Hello World!" + word 1,2,3,4,5 + + padding off + + byte 1,2,3,4,5 + byte "Hello World" + byte 1,2,3,4,5,6 + byte "Hello World!" + word 1,2,3,4,5 + + +table equ 1234h +oldval equ 2345h +newval equ 3456h +new equ 4567h +loc equ 5678h +count equ 6789h +list equ 789ah +tran equ 89abh +testbits equ 9abch +testbit equ 0abcdh +ones equ 0bcdeh +temp equ 0cdefh +change equ 0def0h +bits equ 0ef01h +testva equ 0f012h +prt equ r3 + + a r5,@table + ab 3,*2+ + ai 6,0ch + s @oldval,@newval + sb *6+,1 + mpy @new,5 + div @loc,2 + inc @count + inct 5 + dec @count + dect prt + abs @list(7) + neg 5 + b *3 + bl @tran + blwp @tran + rtwp + jmp $ + jh $ + jl $ + jhe $ + jle $ + jgt $ + jlt $ + jeq $ + jne $ + joc $ + jnc $ + jno $ + jop $ + x @tran + c r5,@table + cb 3,*2+ + ci 9,0f330h + coc @testbits,8 + czc @testbit,8 + rset + idle + ckof + ckon + lrex + sbo 20 + sbz 30 + tb 40 + ldcr @1234h,7 + stcr @1234h,7 + li 7,5 + limi 3 + lwpi 12h + lmf r5,0 + mov 7,7 + mov @ones,9 + movb @temp,3 + swpb *0+ + stst 7 + stwp r5 + andi 0,6d03h + ori 5,60d3h + xor @change,2 + inv 11 + clr *0bh + seto 3 + soc 3,@new + socb 5,8 + szc 5,7 + SZCB @bits,@testva + sra 5,0 + sla 10,5 + srl 0,3 + src 2,7 + xop *4,wr4 + lds @bits + ldd @bits diff --git a/tests/t_9900/t_9900.doc b/tests/t_9900/t_9900.doc new file mode 100644 index 0000000..b0dc9c4 --- /dev/null +++ b/tests/t_9900/t_9900.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application 9900 ----------------------------+ +| | +| This is a (synthetic) test of the TMS99xx instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_9900/t_9900.ori b/tests/t_9900/t_9900.ori new file mode 100644 index 0000000..b50ef4a Binary files /dev/null and b/tests/t_9900/t_9900.ori differ diff --git a/tests/t_ace/asflags b/tests/t_ace/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_ace/t_ace.asm b/tests/t_ace/t_ace.asm new file mode 100644 index 0000000..cf4389b --- /dev/null +++ b/tests/t_ace/t_ace.asm @@ -0,0 +1,132 @@ + cpu ace1202 + page 0 + + adc a, #055h + adc a, 030h + adc a, [x] + adc a, [#33h, x] + + add a, #055h + add a, 030h + add a, [x] + add a, [#33h, x] + + and a, #055h + and a, 030h + and a, [x] + and a, [#33h, x] + + clr a + clr x + clr 030h + + dec a + dec x + dec 030h + + ifbit 7, a + ifbit 7, 033h + ifbit 7, [x] + + ifc + + ifeq a, #033h + ifeq a, 033h + ifeq a, [x] + ifeq a, [#044h, x] + ifeq x, #00344h + ifeq 033h, #044h + + ifgt a, #033h + ifgt a, 033h + ifgt a, [x] + ifgt a, [#044h, x] + ifgt x, #00344h + + iflt x, #00344h + + ifnc + + ifne a, #055h + ifne a, 030h + ifne a, [x] + ifne a, [#33h, x] + + inc a + inc x + inc 030h + + intr + + invc + + jmp 070eh + jmp [#01h, x] + + jp $-30 + jp $-15 + jp $-1 + jp $ + jp $+1 + jp $+15 + jp $+31 + jp $+32 + + jsr 070eh + jsr [#01h, x] + + ld a, #033h + ld a, 033h + ld a, [x] + ld a, [#044h, x] + ld x, #00344h + ld 033h, #044h + ld 033h, 034h + + ldc 2, 033h + + nop + + or a, #055h + or a, 030h + or a, [x] + or a, [#33h, x] + + rbit 2, 033h + rbit 2, [x] + rbit 2, a ; Makro + + rc + + ret + + reti + + rlc a + rlc 030h + + rrc a + rrc 030h + + sbit 2, 033h + sbit 2, [x] + sbit 2, a ; Makro + + sc + + st a, 033h + st a, [x] + st a, [#044h, x] + + stc 2, 033h + + subc a, #055h + subc a, 030h + subc a, [x] + subc a, [#33h, x] + + xor a, #055h + xor a, 030h + xor a, [x] + xor a, [#33h, x] + diff --git a/tests/t_ace/t_ace.doc b/tests/t_ace/t_ace.doc new file mode 100644 index 0000000..5f86dbf --- /dev/null +++ b/tests/t_ace/t_ace.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application ACE -----------------------------+ +| | +| This is a (synthetic) test of the ACE code generator | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_ace/t_ace.ori b/tests/t_ace/t_ace.ori new file mode 100644 index 0000000..6db9f2e Binary files /dev/null and b/tests/t_ace/t_ace.ori differ diff --git a/tests/t_avr/asflags b/tests/t_avr/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_avr/t_avr.asm b/tests/t_avr/t_avr.asm new file mode 100644 index 0000000..e84e084 --- /dev/null +++ b/tests/t_avr/t_avr.asm @@ -0,0 +1,229 @@ + + cpu at90s8515 + page 0 + include regavr.inc + + adc r3,r1 + + add r28,r28 + + and r2,r16 + + andi r19,$aa + + adiw r26,14 + + asr r17 + + bclr 7 + + bld r0,4 + + brbc 1,* + + brbs 6,* + + brcc next ; 1 = 01 + + brcs next ; 0 = 00 +next: + breq next ; -1 = 7F + + brge next ; -2 = 7E + + brsh next ; -3 = 7D + + brid next ; -4 = 7C + + brie next ; -5 = 7B + + brlo next ; -6 = 7A + + brlt next ; -7 = 79 + + brmi next ; -8 = 78 + + brne next ; -9 = 77 + + brhc next ; -10 = 76 + + brhs next ; -11 = 75 + + brpl next ; -12 = 74 + + brtc next ; -13 = 73 + + brts next ; -14 = 72 + + brvc next ; -15 = 71 + + brvs next ; -16 = 70 + + bset 6 + + bst r1,2 + +; call $123456 + + cbr r16,$f0 + + cbi $12,7 + + clc + + cli + + cln + + clh + + clr r18 + + cls + + clt + + clv + + clz + + com r4 + + cp r4,r19 + + cpc r3,r1 + + cpi r19,3 + + cpse r4,r0 + + dec r17 + + eor r0,r22 + + icall + + ijmp + + in r23,$34 + + inc r22 + +; jmp $123456 + + ld r2,x + ld r0,x+ + ld r3,-x + + ld r1,y + ld r0,y+ + ld r3,-y + ldd r4,y+$33 + + ld r1,z + ld r0,z+ + ld r3,-z + ldd r4,z+$33 + + ldi r30,$f0 + + lds r2,$ff00 + + lpm + + lsl r0 + + lsr r0 + + mov r16,r0 + +; mul r6,r5 + + neg r11 + + nop + + or r15,r16 + + ori r16,$f0 + + out $18,r16 + + pop r13 + + push r14 + + rcall * + + ret + + reti + + rjmp * + + rol r15 + + ror r15 + + sbc r3,r1 + + sbci r17,$4f + + sbi $1c,3 + + sbic $1c,1 + + sbis $10,3 + + sbr r16,3 + + sbrc r0,7 + + sbrs r0,7 + + sec + + sei + + sen + + seh + + ser r17 + + ses + + set + + sev + + sez + + sleep + + st x,r1 + st x+,r0 + st -x,r3 + + st y,r1 + st y+,r0 + st -y,r3 + std y+2,r4 + + st z,r1 + st z+,r0 + st -z,r3 + std z+2,r4 + + sts $ff00,r2 + + sub r13,r12 + + subi r22,$11 + + swap r1 + + tst r3 + + wdr + diff --git a/tests/t_avr/t_avr.doc b/tests/t_avr/t_avr.doc new file mode 100644 index 0000000..71f3709 --- /dev/null +++ b/tests/t_avr/t_avr.doc @@ -0,0 +1,5 @@ ++-------------------------- Test Application AVR ----------------------------+ +| | +| This is a (synthetic) test of the Atmel AVR instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_avr/t_avr.ori b/tests/t_avr/t_avr.ori new file mode 100644 index 0000000..9a74d6f Binary files /dev/null and b/tests/t_avr/t_avr.ori differ diff --git a/tests/t_bas52/asflags b/tests/t_bas52/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_bas52/bas52.clk b/tests/t_bas52/bas52.clk new file mode 100644 index 0000000..d019e11 --- /dev/null +++ b/tests/t_bas52/bas52.clk @@ -0,0 +1,18 @@ + ;************************************************************** + ; + ; The statement action routine - CLOCK + ; + ;************************************************************** + ; +SCLOCK: ACALL OTST ;GET CHARACTER AFTER CLOCK TOKEN + CLR ET0 + CLR C_BIT + JNC SC_R ;EXIT IF A ZERO + ANL TMOD,#0F0H ;SET UP THE MODE + SETB C_BIT ;USER INTERRUPTS + ORL IE,#82H ;ENABLE ET0 AND EA + SETB TR0 ;TURN ON THE TIMER + ; +SC_R: RET + ; + diff --git a/tests/t_bas52/bas52.fp b/tests/t_bas52/bas52.fp new file mode 100644 index 0000000..c8a137c --- /dev/null +++ b/tests/t_bas52/bas52.fp @@ -0,0 +1,1616 @@ +;************************************************************ +; +; This is a complete BCD floating point package for the 8051 micro- +; controller. It provides 8 digits of accuracy with exponents that +; range from +127 to -127. The mantissa is in packed BCD, while the +; exponent is expressed in pseudo-twos complement. A ZERO exponent +; is used to express the number ZERO. An exponent value of 80H or +; greater than means the exponent is positive, i.e. 80H = E 0, +; 81H = E+1, 82H = E+2 and so on. If the exponent is 7FH or less, +; the exponent is negative, 7FH = E-1, 7EH = E-2, and so on. +; ALL NUMBERS ARE ASSUMED TO BE NORMALIZED and all results are +; normalized after calculation. A normalized mantissa is >=.10 and +; <=.99999999. +; +; The numbers in memory assumed to be stored as follows: +; +; EXPONENT OF ARGUMENT 2 = VALUE OF ARG_STACK+FP_NUMBER_SIZE +; SIGN OF ARGUMENT 2 = VALUE OF ARG_STACK+FP_NUMBER_SIZE-1 +; DIGIT 78 OF ARGUMENT 2 = VALUE OF ARG_STACK+FP_NUMBER_SIZE-2 +; DIGIT 56 OF ARGUMENT 2 = VALUE OF ARG_STACK+FP_NUMBER_SIZE-3 +; DIGIT 34 OF ARGUMENT 2 = VALUE OF ARG_STACK+FP_NUMBER_SIZE-4 +; DIGIT 12 OF ARGUMENT 2 = VALUE OF ARG_STACK+FP_NUMBER_SIZE-5 +; +; EXPONENT OF ARGUMENT 1 = VALUE OF ARG_STACK +; SIGN OF ARGUMENT 1 = VALUE OF ARG_STACK-1 +; DIGIT 78 OF ARGUMENT 1 = VALUE OF ARG_STACK-2 +; DIGIT 56 OF ARGUMENT 1 = VALUE OF ARG_STACK-3 +; DIGIT 34 OF ARGUMENT 1 = VALUE OF ARG_STACK-4 +; DIGIT 12 OF ARGUMENT 1 = VALUE OF ARG_STACK-5 +; +; The operations are performed thusly: +; +; ARG_STACK+FP_NUMBER_SIZE = ARG_STACK+FP_NUMBER_SIZE # ARG_STACK +; +; Which is ARGUMENT 2 = ARGUMENT 2 # ARGUMENT 1 +; +; Where # can be ADD, SUBTRACT, MULTIPLY OR DIVIDE. +; +; Note that the stack gets popped after an operation. +; +; The FP_COMP instruction POPS the ARG_STACK TWICE and returns status. +; +;********************************************************************** +; + + segment code + newpage + section float ; protect symbols +;********************************************************************** +; +; STATUS ON RETURN - After performing an operation (+, -, *, /) +; the accumulator contains the following status +; +; ACCUMULATOR - BIT 0 - FLOATING POINT UNDERFLOW OCCURED +; +; - BIT 1 - FLOATING POINT OVERFLOW OCCURED +; +; - BIT 2 - RESULT WAS ZER0 +; +; - BIT 3 - DIVIDE BY ZERO ATTEMPTED +; +; - BIT 4 - NOT USED, 0 RETURNED +; +; - BIT 5 - NOT USED, 0 RETURNED +; +; - BIT 6 - NOT USED, 0 RETURNED +; +; - BIT 7 - NOT USED, 0 RETURNED +; +; NOTE: When underflow occures, a ZERO result is returned. +; When overflow or divide by zero occures, a result of +; .99999999 E+127 is returned and it is up to the user +; to handle these conditions as needed in the program. +; +; NOTE: The Compare instruction returns F0 = 0 if ARG 1 = ARG 2 +; and returns a CARRY FLAG = 1 if ARG 1 is > ARG 2 +; +;*********************************************************************** +; + newpage +;*********************************************************************** +; +; The following values MUST be provided by the user +; +;*********************************************************************** +; +ARG_STACK EQU 9 ;ARGUMENT STACK POINTER +ARG_STACK_PAGE EQU 1 +FORMAT EQU 23 ;LOCATION OF OUTPUT FORMAT BYTE +OUTPUT EQU 1990H ;CALL LOCATION TO OUTPUT A CHARACTER +CONVT EQU 58H ;LOCATION TO CONVERT NUMBERS +INTGRC BIT 25 ;BIT SET IF INTGER ERROR +ZSURP BIT 54 ;ZERO SUPRESSION FOR HEX PRINT +; +;*********************************************************************** +; +; The following equates are used internally +; +;*********************************************************************** +; +FP_NUMBER_SIZE EQU 6 +DIGIT EQU FP_NUMBER_SIZE-2 +R0B0 EQU 0 +R1B0 EQU 1 +UNDERFLOW EQU 0 +ACC_UNDERFLOW BIT ACC.0 ; ******AA added +OVERFLOW EQU 1 +ACC_OVERFLOW BIT ACC.1 ; ******AA added +ZERO EQU 2 +ACC_ZERO BIT ACC.2 ; ******AA added +ZERO_DIVIDE EQU 3 +ACC_ZERO_DIVIDE BIT ACC.3 ; ******AA added +; +;*********************************************************************** + newpage + ;************************************************************** + ; + ; The following internal locations are used by the math pack + ; ordering is important and the FP_DIGITS must be bit + ; addressable + ; + ;*************************************************************** + ; +FP_STATUS EQU 28H ;NOT USED +FP_TEMP EQU FP_STATUS+1 ;NOT USED +FP_CARRY SFRB FP_STATUS+2 ;USED FOR BITS ******AA EQU-->SFRB +ADD_IN BIT 35 ;DCMPXZ IN BASIC BACKAGE +XSIGN BIT FP_CARRY.0 +FOUND_RADIX BIT FP_CARRY.1 +FIRST_RADIX BIT FP_CARRY.2 +DONE_LOAD BIT FP_CARRY.3 +FP_DIG12 EQU FP_CARRY+1 +FP_DIG34 EQU FP_CARRY+2 +FP_DIG56 EQU FP_CARRY+3 +FP_DIG78 EQU FP_CARRY+4 +FP_SIGN SFRB FP_CARRY+5 ; ******AA EQU-->SFRB +MSIGN BIT FP_SIGN.0 +FP_EXP EQU FP_CARRY+6 +FP_NIB1 EQU FP_DIG12 +FP_NIB2 EQU FP_NIB1+1 +FP_NIB3 EQU FP_NIB1+2 +FP_NIB4 EQU FP_NIB1+3 +FP_NIB5 EQU FP_NIB1+4 +FP_NIB6 EQU FP_NIB1+5 +FP_NIB7 EQU FP_NIB1+6 +FP_NIB8 EQU FP_NIB1+7 +FP_ACCX EQU FP_NIB1+8 +FP_ACCC EQU FP_NIB1+9 +FP_ACC1 EQU FP_NIB1+10 +FP_ACC2 EQU FP_NIB1+11 +FP_ACC3 EQU FP_NIB1+12 +FP_ACC4 EQU FP_NIB1+13 +FP_ACC5 EQU FP_NIB1+14 +FP_ACC6 EQU FP_NIB1+15 +FP_ACC7 EQU FP_NIB1+16 +FP_ACC8 EQU FP_NIB1+17 +FP_ACCS EQU FP_NIB1+18 + ; + newpage + ORG 1993H + ; + ;************************************************************** + ; + ; The floating point entry points and jump table + ; + ;************************************************************** + ; + AJMP FLOATING_ADD + AJMP FLOATING_SUB + AJMP FLOATING_COMP + AJMP FLOATING_MUL + AJMP FLOATING_DIV + AJMP HEXSCAN + AJMP FLOATING_POINT_INPUT + AJMP FLOATING_POINT_OUTPUT + AJMP CONVERT_BINARY_TO_ASCII_STRING + AJMP CONVERT_ASCII_STRING_TO_BINARY + AJMP MULNUM10 + AJMP HEXOUT + AJMP PUSHR2R0 + ; + newpage + ; +FLOATING_SUB: + ; + MOV P2,#ARG_STACK_PAGE + MOV R0,ARG_STACK + DEC R0 ;POINT TO SIGN + MOVX A,@R0 ;READ SIGN + CPL ACC.0 + MOVX @R0,A + ; + ;AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA + ; +FLOATING_ADD: + ; + ;AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA + ; + ; + ACALL MDES1 ;R7=TOS EXP, R6=TOS-1 EXP, R4=TOS SIGN + ;R3=TOS-1 SIGN, OPERATION IS R1 # R0 + ; + MOV A,R7 ;GET TOS EXPONENT + JZ POP_AND_EXIT ;IF TOS=0 THEN POP AND EXIT + CJNE R6,#0,LOAD1 ;CLEAR CARRY EXIT IF ZERO + ; + ;************************************************************** + ; +SWAP_AND_EXIT: ; Swap external args and return + ; + ;************************************************************** + ; + ACALL LOAD_POINTERS + MOV R7,#FP_NUMBER_SIZE + ; +SE1: MOVX A,@R0 ;SWAP THE ARGUMENTS + MOVX @R1,A + DEC R0 + DEC R1 + DJNZ R7,SE1 + ; +POP_AND_EXIT: + ; + MOV A,ARG_STACK ;POP THE STACK + ADD A,#FP_NUMBER_SIZE + MOV ARG_STACK,A + CLR A + RET + ; + ; +LOAD1: SUBB A,R6 ;A = ARG 1 EXP - ARG 2 EXP + MOV FP_EXP,R7 ;SAVE EXPONENT AND SIGN + MOV FP_SIGN,R4 + JNC LOAD2 ;ARG1 EXPONENT IS LARGER OR SAME + MOV FP_EXP,R6 + MOV FP_SIGN,R3 + CPL A + INC A ;COMPENSATE FOR EXP DELTA + XCH A,R0 ;FORCE R0 TO POINT AT THE LARGEST + XCH A,R1 ;EXPONENT + XCH A,R0 + ; +LOAD2: MOV R7,A ;SAVE THE EXPONENT DELTA IN R7 + CLR ADD_IN + CJNE R5,#0,$+5 + SETB ADD_IN + ; + newpage + ; Load the R1 mantissa + ; + ACALL LOADR1_MANTISSA ;LOAD THE SMALLEST NUMBER + ; + ; Now align the number to the delta exponent + ; R4 points to the string of the last digits lost + ; + CJNE R7,#DIGIT+DIGIT+3,$+3 + JC $+4 + MOV R7,#DIGIT+DIGIT+2 + ; + MOV FP_CARRY,#00 ;CLEAR THE CARRY + ACALL RIGHT ;SHIFT THE NUMBER + ; + ; Set up for addition and subtraction + ; + MOV R7,#DIGIT ;LOOP COUNT + MOV R1,#FP_DIG78 + MOV A,#9EH + CLR C + SUBB A,R4 + DA A + XCH A,R4 + JNZ $+3 + MOV R4,A + CJNE A,#50H,$+3 ;TEST FOR SUBTRACTION + JNB ADD_IN,SUBLP ;DO SUBTRACTION IF NO ADD_IN + CPL C ;FLIP CARRY FOR ADDITION + ACALL ADDLP ;DO ADDITION + ; + JNC ADD_R + INC FP_CARRY + MOV R7,#1 + ACALL RIGHT + ACALL INC_FP_EXP ;SHIFT AND BUMP EXPONENT + ; +ADD_R: AJMP STORE_ALIGN_TEST_AND_EXIT + ; +ADDLP: MOVX A,@R0 + ADDC A,@R1 + DA A + MOV @R1,A + DEC R0 + DEC R1 + DJNZ R7,ADDLP ;LOOP UNTIL DONE + RET + ; + newpage + ; +SUBLP: MOVX A,@R0 ;NOW DO SUBTRACTION + MOV R6,A + CLR A + ADDC A,#99H + SUBB A,@R1 + ADD A,R6 + DA A + MOV @R1,A + DEC R0 + DEC R1 + DJNZ R7,SUBLP + JC FSUB6 + ; + newpage + ; + ; Need to complement the result and sign because the floating + ; point accumulator mantissa was larger than the external + ; memory and their signs were equal. + ; + CPL FP_SIGN.0 + MOV R1,#FP_DIG78 + MOV R7,#DIGIT ;LOOP COUNT + ; +FSUB5: MOV A,#9AH + SUBB A,@R1 + ADD A,#0 + DA A + MOV @R1,A + DEC R1 + CPL C + DJNZ R7,FSUB5 ;LOOP + ; + ; Now see how many zeros their are + ; +FSUB6: MOV R0,#FP_DIG12 + MOV R7,#0 + ; +FSUB7: MOV A,@R0 + JNZ FSUB8 + INC R7 + INC R7 + INC R0 + CJNE R0,#FP_SIGN,FSUB7 + AJMP ZERO_AND_EXIT + ; +FSUB8: CJNE A,#10H,$+3 + JNC FSUB9 + INC R7 + ; + ; Now R7 has the number of leading zeros in the FP ACC + ; +FSUB9: MOV A,FP_EXP ;GET THE OLD EXPONENT + CLR C + SUBB A,R7 ;SUBTRACT FROM THE NUMBER OF ZEROS + JZ FSUB10 + JC FSUB10 + ; + MOV FP_EXP,A ;SAVE THE NEW EXPONENT + ; + ACALL LEFT1 ;SHIFT THE FP ACC + MOV FP_CARRY,#0 + AJMP STORE_ALIGN_TEST_AND_EXIT + ; +FSUB10: AJMP UNDERFLOW_AND_EXIT + ; + newpage + ;*************************************************************** + ; +FLOATING_COMP: ; Compare two floating point numbers + ; used for relational operations and is faster + ; than subtraction. ON RETURN, The carry is set + ; if ARG1 is > ARG2, else carry is not set + ; if ARG1 = ARG2, F0 gets set + ; + ;*************************************************************** + ; + ACALL MDES1 ;SET UP THE REGISTERS + MOV A,ARG_STACK + ADD A,#FP_NUMBER_SIZE+FP_NUMBER_SIZE + MOV ARG_STACK,A ;POP THE STACK TWICE, CLEAR THE CARRY + MOV A,R6 ;CHECK OUT EXPONENTS + CLR F0 + SUBB A,R7 + JZ EXPONENTS_EQUAL + JC ARG1_EXP_IS_LARGER + ; + ; Now the ARG2 EXPONENT is > ARG1 EXPONENT + ; +SIGNS_DIFFERENT: + ; + MOV A,R3 ;SEE IF SIGN OF ARG2 IS POSITIVE + SJMP $+3 + ; +ARG1_EXP_IS_LARGER: + ; + MOV A,R4 ;GET THE SIGN OF ARG1 EXPONENT + JZ $+3 + CPL C + RET + ; +EXPONENTS_EQUAL: + ; + ; First, test the sign, then the mantissa + ; + CJNE R5,#0,SIGNS_DIFFERENT + ; +BOTH_PLUS: + ; + MOV R7,#DIGIT ;POINT AT MS DIGIT + DEC R0 + DEC R0 + DEC R0 + DEC R1 + DEC R1 + DEC R1 + ; + ; Now do the compare + ; +CLOOP: MOVX A,@R0 + MOV R6,A + MOVX A,@R1 + SUBB A,R6 + JNZ ARG1_EXP_IS_LARGER + INC R0 + INC R1 + DJNZ R7,CLOOP + ; + ; If here, the numbers are the same, the carry is cleared + ; + SETB F0 + RET ;EXIT WITH EQUAL + ; + newpage +;MMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMM +; +FLOATING_MUL: ; Floating point multiply +; +;MMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMM +; + ACALL MUL_DIV_EXP_AND_SIGN + ; + ; check for zero exponents + ; + CJNE R6,#00,$+5 ;ARG 2 EXP ZERO? + AJMP ZERO_AND_EXIT + ; + ; calculate the exponent + ; +FMUL1: MOV FP_SIGN,R5 ;SAVE THE SIGN, IN CASE OF FAILURE + ; + MOV A,R7 + JZ FMUL1-2 + ADD A,R6 ;ADD THE EXPONENTS + JB ACC.7,FMUL_OVER + JBC CY,FMUL2 ;SEE IF CARRY IS SET + ; + AJMP UNDERFLOW_AND_EXIT + ; +FMUL_OVER: + ; + JNC FMUL2 ;OK IF SET + ; +FOV: AJMP OVERFLOW_AND_EXIT + ; +FMUL2: SUBB A,#129 ;SUBTRACT THE EXPONENT BIAS + MOV R6,A ;SAVE IT FOR LATER + ; + ; Unpack and load R0 + ; + ACALL UNPACK_R0 + ; + ; Now set up for loop multiply + ; + MOV R3,#DIGIT + MOV R4,R1B0 + ; + newpage + ; + ; Now, do the multiply and accumulate the product + ; +FMUL3: MOV R1B0,R4 + MOVX A,@R1 + MOV R2,A + ACALL MUL_NIBBLE + ; + MOV A,R2 + SWAP A + ACALL MUL_NIBBLE + DEC R4 + DJNZ R3,FMUL3 + ; + ; Now, pack and restore the sign + ; + MOV FP_EXP,R6 + MOV FP_SIGN,R5 + AJMP PACK ;FINISH IT OFF + ; + newpage + ;DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD + ; +FLOATING_DIV: + ; + ;DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD + ; + ACALL MDES1 + ; + ; Check the exponents + ; + MOV FP_SIGN,R5 ;SAVE THE SIGN + CJNE R7,#0,DIV0 ;CLEARS THE CARRY + ACALL OVERFLOW_AND_EXIT + CLR A + SETB ACC_ZERO_DIVIDE + RET + ; +DIV0: MOV A,R6 ;GET EXPONENT + JZ FMUL1-2 ;EXIT IF ZERO + SUBB A,R7 ;DELTA EXPONENT + JB ACC.7,D_UNDER + JNC DIV3 + AJMP UNDERFLOW_AND_EXIT + ; +D_UNDER:JNC FOV + ; +DIV3: ADD A,#129 ;CORRECTLY BIAS THE EXPONENT + MOV FP_EXP,A ;SAVE THE EXPONENT + ACALL LOADR1_MANTISSA ;LOAD THE DIVIDED + ; + MOV R2,#FP_ACCC ;SAVE LOCATION + MOV R3,R0B0 ;SAVE POINTER IN R3 + MOV FP_CARRY,#0 ;ZERO CARRY BYTE + ; +DIV4: MOV R5,#0FFH ;LOOP COUNT + SETB C + ; +DIV5: MOV R0B0,R3 ;RESTORE THE EXTERNAL POINTER + MOV R1,#FP_DIG78 ;SET UP INTERNAL POINTER + MOV R7,#DIGIT ;LOOP COUNT + JNC DIV7 ;EXIT IF NO CARRY + ; +DIV6: MOVX A,@R0 ;DO ACCUMLATION + MOV R6,A + CLR A + ADDC A,#99H + SUBB A,R6 + ADD A,@R1 + DA A + MOV @R1,A + DEC R0 + DEC R1 + DJNZ R7,DIV6 ;LOOP + ; + INC R5 ;SUBTRACT COUNTER + JC DIV5 ;KEEP LOOPING IF CARRY + MOV A,@R1 ;GET CARRY + SUBB A,#1 ;CARRY IS CLEARED + MOV @R1,A ;SAVE CARRY DIGIT + CPL C + SJMP DIV5 ;LOOP + ; + ; Restore the result if carry was found + ; +DIV7: ACALL ADDLP ;ADD NUMBER BACK + MOV @R1,#0 ;CLEAR CARRY + MOV R0B0,R2 ;GET SAVE COUNTER + MOV @R0,5 ;SAVE COUNT BYTE + ; + INC R2 ;ADJUST SAVE COUNTER + MOV R7,#1 ;BUMP DIVIDEND + ACALL LEFT + CJNE R2,#FP_ACC8+2,DIV4 + ; + DJNZ FP_EXP,DIV8 + AJMP UNDERFLOW_AND_EXIT + ; +DIV8: MOV FP_CARRY,#0 + ; + newpage + ;*************************************************************** + ; +PACK: ; Pack the mantissa + ; + ;*************************************************************** + ; + ; First, set up the pointers + ; + MOV R0,#FP_ACCC + MOV A,@R0 ;GET FP_ACCC + MOV R6,A ;SAVE FOR ZERO COUNT + JZ PACK0 ;JUMP OVER IF ZERO + ACALL INC_FP_EXP ;BUMP THE EXPONENT + DEC R0 + ; +PACK0: INC R0 ;POINT AT FP_ACC1 + ; +PACK1: MOV A,#8 ;ADJUST NIBBLE POINTER + MOV R1,A + ADD A,R0 + MOV R0,A + CJNE @R0,#5,$+3 ;SEE IF ADJUSTING NEEDED + JC PACK3+1 + ; +PACK2: SETB C + CLR A + DEC R0 + ADDC A,@R0 + DA A + XCHD A,@R0 ;SAVE THE VALUE + JNB ACC.4,PACK3 + DJNZ R1,PACK2 + ; + DEC R0 + MOV @R0,#1 + ACALL INC_FP_EXP + SJMP PACK4 + ; +PACK3: DEC R1 + MOV A,R1 + CLR C + XCH A,R0 + SUBB A,R0 + MOV R0,A + ; +PACK4: MOV R1,#FP_DIG12 + ; + ; Now, pack + ; +PLOOP: MOV A,@R0 + SWAP A ;FLIP THE DIGITS + INC R0 + XCHD A,@R0 + ORL 6,A ;ACCUMULATE THE OR'ED DIGITS + MOV @R1,A + INC R0 + INC R1 + CJNE R1,#FP_SIGN,PLOOP + MOV A,R6 + JNZ STORE_ALIGN_TEST_AND_EXIT + MOV FP_EXP,#0 ;ZERO EXPONENT + ; + ;************************************************************** + ; +STORE_ALIGN_TEST_AND_EXIT: ;Save the number align carry and exit + ; + ;************************************************************** + ; + ACALL LOAD_POINTERS + MOV ARG_STACK,R1 ;SET UP THE NEW STACK + MOV R0,#FP_EXP + ; + ; Now load the numbers + ; +STORE2: MOV A,@R0 + MOVX @R1,A ;SAVE THE NUMBER + DEC R0 + DEC R1 + CJNE R0,#FP_CARRY,STORE2 + ; + CLR A ;NO ERRORS + ; +PRET: RET ;EXIT + ; + newpage +INC_FP_EXP: + ; + INC FP_EXP + MOV A,FP_EXP + JNZ PRET ;EXIT IF NOT ZERO + POP ACC ;WASTE THE CALLING STACK + POP ACC + AJMP OVERFLOW_AND_EXIT + ; +;*********************************************************************** +; +UNPACK_R0: ; Unpack BCD digits and load into nibble locations +; +;*********************************************************************** + ; + PUSH R1B0 + MOV R1,#FP_NIB8 + ; +ULOOP: MOVX A,@R0 + ANL A,#0FH + MOV @R1,A ;SAVE THE NIBBLE + MOVX A,@R0 + SWAP A + ANL A,#0FH + DEC R1 + MOV @R1,A ;SAVE THE NIBBLE AGAIN + DEC R0 + DEC R1 + CJNE R1,#FP_NIB1-1,ULOOP + ; + POP R1B0 + ; +LOAD7: RET + ; + newpage + ;************************************************************** + ; +OVERFLOW_AND_EXIT: ;LOAD 99999999 E+127, SET OV BIT, AND EXIT + ; + ;************************************************************** + ; + MOV R0,#FP_DIG78 + MOV A,#99H + ; +OVE1: MOV @R0,A + DEC R0 + CJNE R0,#FP_CARRY,OVE1 + ; + MOV FP_EXP,#0FFH + ACALL STORE_ALIGN_TEST_AND_EXIT + ; + SETB ACC_OVERFLOW ; ******AA + RET + ; + newpage + ;************************************************************** + ; +UNDERFLOW_AND_EXIT: ;LOAD 0, SET UF BIT, AND EXIT + ; + ;************************************************************** + ; + ACALL ZERO_AND_EXIT + CLR A + SETB ACC_UNDERFLOW ; ******AA + RET + ; + ;************************************************************** + ; +ZERO_AND_EXIT: ;LOAD 0, SET ZERO BIT, AND EXIT + ; + ;************************************************************** + ; + ACALL FP_CLEAR + ACALL STORE_ALIGN_TEST_AND_EXIT + SETB ACC_ZERO ; ******AA + RET ;EXIT + ; + ;************************************************************** + ; +FP_CLEAR: + ; + ; Clear internal storage + ; + ;************************************************************** + ; + CLR A + MOV R0,#FP_ACC8+1 + ; +FPC1: MOV @R0,A + DEC R0 + CJNE R0,#FP_TEMP,FPC1 + RET + ; + newpage + ;************************************************************** + ; +RIGHT: ; Shift ACCUMULATOR RIGHT the number of nibbles in R7 + ; Save the shifted values in R4 if SAVE_ROUND is set + ; + ;************************************************************** + ; + MOV R4,#0 ;IN CASE OF NO SHIFT + ; +RIGHT1: CLR C + MOV A,R7 ;GET THE DIGITS TO SHIFT + JZ RIGHT5-1 ;EXIT IF ZERO + SUBB A,#2 ;TWO TO DO? + JNC RIGHT5 ;SHIFT TWO NIBBLES + ; + ; Swap one nibble then exit + ; +RIGHT3: PUSH R0B0 ;SAVE POINTER REGISTER + PUSH R1B0 + ; + MOV R1,#FP_DIG78 ;LOAD THE POINTERS + MOV R0,#FP_DIG56 + MOV A,R4 ;GET THE OVERFLOW REGISTER + XCHD A,@R1 ;GET DIGIT 8 + SWAP A ;FLIP FOR LOAD + MOV R4,A + ; +RIGHTL: MOV A,@R1 ;GET THE LOW ORDER BYTE + XCHD A,@R0 ;SWAP NIBBLES + SWAP A ;FLIP FOR STORE + MOV @R1,A ;SAVE THE DIGITS + DEC R0 ;BUMP THE POINTERS + DEC R1 + CJNE R1,#FP_DIG12-1,RIGHTL ;LOOP + ; + MOV A,@R1 ;ACC = CH8 + SWAP A ;ACC = 8CH + ANL A,#0FH ;ACC = 0CH + MOV @R1,A ;CARRY DONE + POP R1B0 ;EXIT + POP R0B0 ;RESTORE REGISTER + RET + ; +RIGHT5: MOV R7,A ;SAVE THE NEW SHIFT NUMBER + CLR A + XCH A,FP_CARRY ;SWAP THE NIBBLES + XCH A,FP_DIG12 + XCH A,FP_DIG34 + XCH A,FP_DIG56 + XCH A,FP_DIG78 + MOV R4,A ;SAVE THE LAST DIGIT SHIFTED + SJMP RIGHT1+1 + ; + newpage + ;*************************************************************** + ; +LEFT: ; Shift ACCUMULATOR LEFT the number of nibbles in R7 + ; + ;*************************************************************** + ; + MOV R4,#00H ;CLEAR FOR SOME ENTRYS + ; +LEFT1: CLR C + MOV A,R7 ;GET SHIFT VALUE + JZ LEFT5-1 ;EXIT IF ZERO + SUBB A,#2 ;SEE HOW MANY BYTES TO SHIFT + JNC LEFT5 + ; +LEFT3: PUSH R0B0 ;SAVE POINTER + PUSH R1B0 + MOV R0,#FP_CARRY + MOV R1,#FP_DIG12 + ; + MOV A,@R0 ;ACC=CHCL + SWAP A ;ACC = CLCH + MOV @R0,A ;ACC = CLCH, @R0 = CLCH + ; +LEFTL: MOV A,@R1 ;DIG 12 + SWAP A ;DIG 21 + XCHD A,@R0 + MOV @R1,A ;SAVE IT + INC R0 ;BUMP POINTERS + INC R1 + CJNE R0,#FP_DIG78,LEFTL + ; + MOV A,R4 + SWAP A + XCHD A,@R0 + ANL A,#0F0H + MOV R4,A + ; + POP R1B0 + POP R0B0 ;RESTORE + RET ;DONE + ; +LEFT5: MOV R7,A ;RESTORE COUNT + CLR A + XCH A,R4 ;GET THE RESTORATION BYTE + XCH A,FP_DIG78 ;DO THE SWAP + XCH A,FP_DIG56 + XCH A,FP_DIG34 + XCH A,FP_DIG12 + XCH A,FP_CARRY + SJMP LEFT1+1 + ; + newpage +MUL_NIBBLE: + ; + ; Multiply the nibble in R7 by the FP_NIB locations + ; accumulate the product in FP_ACC + ; + ; Set up the pointers for multiplication + ; + ANL A,#0FH ;STRIP OFF MS NIBBLE + MOV R7,A + MOV R0,#FP_ACC8 + MOV R1,#FP_NIB8 + CLR A + MOV FP_ACCX,A + ; +MNLOOP: DEC R0 ;BUMP POINTER TO PROPAGATE CARRY + ADD A,@R0 ;ATTEMPT TO FORCE CARRY + DA A ;BCD ADJUST + JNB ACC.4,MNL0 ;DON'T ADJUST IF NO NEED + DEC R0 ;PROPAGATE CARRY TO THE NEXT DIGIT + INC @R0 ;DO THE ADJUSTING + INC R0 ;RESTORE R0 + ; +MNL0: XCHD A,@R0 ;RESTORE INITIAL NUMBER + MOV B,R7 ;GET THE NUBBLE TO MULTIPLY + MOV A,@R1 ;GET THE OTHER NIBBLE + MUL AB ;DO THE MULTIPLY + MOV B,#10 ;NOW BCD ADJUST + DIV AB + XCH A,B ;GET THE REMAINDER + ADD A,@R0 ;PROPAGATE THE PARTIAL PRODUCTS + DA A ;BCD ADJUST + JNB ACC.4,MNL1 ;PROPAGATE PARTIAL PRODUCT CARRY + INC B + ; +MNL1: INC R0 + XCHD A,@R0 ;SAVE THE NEW PRODUCT + DEC R0 + MOV A,B ;GET BACK THE QUOTIENT + DEC R1 + CJNE R1,#FP_NIB1-1,MNLOOP + ; + ADD A,FP_ACCX ;GET THE OVERFLOW + DA A ;ADJUST + MOV @R0,A ;SAVE IT + RET ;EXIT + ; + newpage + ;*************************************************************** + ; +LOAD_POINTERS: ; Load the ARG_STACK into R0 and bump R1 + ; + ;*************************************************************** + ; + MOV P2,#ARG_STACK_PAGE + MOV R0,ARG_STACK + MOV A,#FP_NUMBER_SIZE + ADD A,R0 + MOV R1,A + RET + ; + ;*************************************************************** + ; +MUL_DIV_EXP_AND_SIGN: + ; + ; Load the sign into R7, R6. R5 gets the sign for + ; multiply and divide. + ; + ;*************************************************************** + ; + ACALL FP_CLEAR ;CLEAR INTERNAL MEMORY + ; +MDES1: ACALL LOAD_POINTERS ;LOAD REGISTERS + MOVX A,@R0 ;ARG 1 EXP + MOV R7,A ;SAVED IN R7 + MOVX A,@R1 ;ARG 2 EXP + MOV R6,A ;SAVED IN R6 + DEC R0 ;BUMP POINTERS TO SIGN + DEC R1 + MOVX A,@R0 ;GET THE SIGN + MOV R4,A ;SIGN OF ARG1 + MOVX A,@R1 ;GET SIGN OF NEXT ARG + MOV R3,A ;SIGN OF ARG2 + XRL A,R4 ;ACC GETS THE NEW SIGN + MOV R5,A ;R5 GETS THE NEW SIGN + ; + ; Bump the pointers to point at the LS digit + ; + DEC R0 + DEC R1 + ; + RET + ; + newpage + ;*************************************************************** + ; +LOADR1_MANTISSA: + ; + ; Load the mantissa of R0 into FP_Digits + ; + ;*************************************************************** + ; + PUSH R0B0 ;SAVE REGISTER 1 + MOV R0,#FP_DIG78 ;SET UP THE POINTER + ; +LOADR1: MOVX A,@R1 + MOV @R0,A + DEC R1 + DEC R0 + CJNE R0,#FP_CARRY,LOADR1 + ; + POP R0B0 + RET + ; + newpage + ;*************************************************************** + ; +HEXSCAN: ; Scan a string to determine if it is a hex number + ; set carry if hex, else carry = 0 + ; + ;*************************************************************** + ; + ACALL GET_DPTR_CHARACTER + PUSH DPH + PUSH DPL ;SAVE THE POINTER + ; +HEXSC1: MOVX A,@DPTR ;GET THE CHARACTER + ACALL DIGIT_CHECK ;SEE IF A DIGIT + JC HS1 ;CONTINUE IF A DIGIT + ACALL HEX_CHECK ;SEE IF HEX + JC HS1 + ; + CLR ACC.5 ;NO LOWER CASE + CJNE A,#'H',HEXDON + SETB C + SJMP HEXDO1 ;NUMBER IS VALID HEX, MAYBE + ; +HEXDON: CLR C + ; +HEXDO1: POP DPL ;RESTORE POINTER + POP DPH + RET + ; +HS1: INC DPTR ;BUMP TO NEXT CHARACTER + SJMP HEXSC1 ;LOOP + ; +HEX_CHECK: ;CHECK FOR A VALID ASCII HEX, SET CARRY IF FOUND + ; + CLR ACC.5 ;WASTE LOWER CASE + CJNE A,#'F'+1,$+3 ;SEE IF F OR LESS + JC HC1 + RET + ; +HC1: CJNE A,#'A',$+3 ;SEE IF A OR GREATER + CPL C + RET + ; + newpage + ; +PUSHR2R0: + ; + MOV R3,#HI(CONVT) ;CONVERSION LOCATION + MOV R1,#LO(CONVT) + ACALL CONVERT_BINARY_TO_ASCII_STRING + MOV A,#0DH ;A CR TO TERMINATE + MOVX @R1,A ;SAVE THE CR + MOV DPTR,#CONVT + ; + ; Falls thru to FLOATING INPUT + ; + newpage + ;*************************************************************** + ; +FLOATING_POINT_INPUT: ; Input a floating point number pointed to by + ; the DPTR + ; + ;*************************************************************** + ; + ACALL FP_CLEAR ;CLEAR EVERYTHING + ACALL GET_DPTR_CHARACTER + ACALL PLUS_MINUS_TEST + MOV MSIGN,C ;SAVE THE MANTISSA SIGN + ; + ; Now, set up for input loop + ; + MOV R0,#FP_ACCC + MOV R6,#7FH ;BASE EXPONENT + SETB F0 ;SET INITIAL FLAG + ; +INLOOP: ACALL GET_DIGIT_CHECK + JNC GTEST ;IF NOT A CHARACTER, WHAT IS IT? + ANL A,#0FH ;STRIP ASCII + ACALL STDIG ;STORE THE DIGITS + ; +INLPIK: INC DPTR ;BUMP POINTER FOR LOOP + SJMP INLOOP ;LOOP FOR INPUT + ; +GTEST: CJNE A,#'.',GT1 ;SEE IF A RADIX + JB FOUND_RADIX,INERR + SETB FOUND_RADIX + CJNE R0,#FP_ACCC,INLPIK + SETB FIRST_RADIX ;SET IF FIRST RADIX + SJMP INLPIK ;GET ADDITIONAL DIGITS + ; +GT1: JB F0,INERR ;ERROR IF NOT CLEARED + CJNE A,#'e',$+5 ;CHECK FOR LOWER CASE + SJMP $+5 + CJNE A,#'E',FINISH_UP + ACALL INC_AND_GET_DPTR_CHARACTER + ACALL PLUS_MINUS_TEST + MOV XSIGN,C ;SAVE SIGN STATUS + ACALL GET_DIGIT_CHECK + JNC INERR + ; + ANL A,#0FH ;STRIP ASCII BIAS OFF THE CHARACTER + MOV R5,A ;SAVE THE CHARACTER IN R5 + ; +GT2: INC DPTR + ACALL GET_DIGIT_CHECK + JNC FINISH1 + ANL A,#0FH ;STRIP OFF BIAS + XCH A,R5 ;GET THE LAST DIGIT + MOV B,#10 ;MULTIPLY BY TEN + MUL AB + ADD A,R5 ;ADD TO ORIGINAL VALUE + MOV R5,A ;SAVE IN R5 + JNC GT2 ;LOOP IF NO CARRY + MOV R5,#0FFH ;FORCE AN ERROR + ; +FINISH1:MOV A,R5 ;GET THE SIGN + JNB XSIGN,POSNUM ;SEE IF EXPONENT IS POS OR NEG + CLR C + SUBB A,R6 + CPL A + INC A + JC FINISH2 + MOV A,#01H + RET + ; +POSNUM: ADD A,R6 ;ADD TO EXPONENT + JNC FINISH2 + ; +POSNM1: MOV A,#02H + RET + ; +FINISH2:XCH A,R6 ;SAVE THE EXPONENT + ; +FINISH_UP: + ; + MOV FP_EXP,R6 ;SAVE EXPONENT + CJNE R0,#FP_ACCC,$+5 + ACALL FP_CLEAR ;CLEAR THE MEMORY IF 0 + MOV A,ARG_STACK ;GET THE ARG STACK + CLR C + SUBB A,#FP_NUMBER_SIZE+FP_NUMBER_SIZE + MOV ARG_STACK,A ;ADJUST FOR STORE + AJMP PACK + ; +STDIG: CLR F0 ;CLEAR INITIAL DESIGNATOR + JNZ STDIG1 ;CONTINUE IF NOT ZERO + CJNE R0,#FP_ACCC,STDIG1 + JNB FIRST_RADIX,RET_X + ; +DECX: DJNZ R6,RET_X + ; +INERR: MOV A,#0FFH + ; +RET_X: RET + ; +STDIG1: JB DONE_LOAD,FRTEST + CLR FIRST_RADIX + ; +FRTEST: JB FIRST_RADIX,DECX + ; +FDTEST: JB FOUND_RADIX,FDT1 + INC R6 + ; +FDT1: JB DONE_LOAD,RET_X + CJNE R0,#FP_ACC8+1,FDT2 + SETB DONE_LOAD + ; +FDT2: MOV @R0,A ;SAVE THE STRIPPED ACCUMULATOR + INC R0 ;BUMP THE POINTER + RET ;EXIT + ; + newpage + ;*************************************************************** + ; + ; I/O utilities + ; + ;*************************************************************** + ; +INC_AND_GET_DPTR_CHARACTER: + ; + INC DPTR + ; +GET_DPTR_CHARACTER: + ; + MOVX A,@DPTR ;GET THE CHARACTER + CJNE A,#' ',PMT1 ;SEE IF A SPACE + ; + ; Kill spaces + ; + SJMP INC_AND_GET_DPTR_CHARACTER + ; +PLUS_MINUS_TEST: + ; + CJNE A,#0E3H,$+5 ;SEE IF A PLUS, PLUS TOKEN FROM BASIC + SJMP PMT3 + CJNE A,#'+',$+5 + SJMP PMT3 + CJNE A,#0E5H,$+5 ;SEE IF MINUS, MINUS TOKEN FROM BASIC + SJMP PMT2 + CJNE A,#'-',PMT1 + ; +PMT2: SETB C + ; +PMT3: INC DPTR + ; +PMT1: RET + ; + newpage + ;*************************************************************** + ; +FLOATING_POINT_OUTPUT: ; Output the number, format is in location 23 + ; + ; IF FORMAT = 00 - FREE FLOATING + ; = FX - EXPONENTIAL (X IS THE NUMBER OF SIG DIGITS) + ; = NX - N = NUM BEFORE RADIX, X = NUM AFTER RADIX + ; N + X = 8 MAX + ; + ;*************************************************************** + ; + ACALL MDES1 ;GET THE NUMBER TO OUTPUT, R0 IS POINTER + ACALL POP_AND_EXIT ;OUTPUT POPS THE STACK + MOV A,R7 + MOV R6,A ;PUT THE EXPONENT IN R6 + ACALL UNPACK_R0 ;UNPACK THE NUMBER + MOV R0,#FP_NIB1 ;POINT AT THE NUMBER + MOV A,FORMAT ;GET THE FORMAT + MOV R3,A ;SAVE IN CASE OF EXP FORMAT + JZ FREE ;FREE FLOATING? + CJNE A,#0F0H,$+3 ;SEE IF EXPONENTIAL + JNC EXPOUT + ; + ; If here, must be integer USING format + ; + MOV A,R6 ;GET THE EXPONENT + JNZ $+4 + MOV R6,#80H + MOV A,R3 ;GET THE FORMAT + SWAP A ;SPLIT INTEGER AND FRACTION + ANL A,#0FH + MOV R2,A ;SAVE INTEGER + ACALL NUM_LT ;GET THE NUMBER OF INTEGERS + XCH A,R2 ;FLIP FOR SUBB + CLR C + SUBB A,R2 + MOV R7,A + JNC $+8 + MOV R5,#'?' ;OUTPUT A QUESTION MARK + ACALL SOUT1 ;NUMBER IS TOO LARGE FOR FORMAT + AJMP FREE + CJNE R2,#00,USING0 ;SEE IF ZERO + DEC R7 + ACALL SS7 + ACALL ZOUT ;OUTPUT A ZERO + SJMP USING1 + ; +USING0: ACALL SS7 ;OUTPUT SPACES, IF NEED TO + MOV A,R2 ;OUTPUT DIGITS + MOV R7,A + ACALL OUTR0 + ; +USING1: MOV A,R3 + ANL A,#0FH ;GET THE NUMBER RIGHT OF DP + MOV R2,A ;SAVE IT + JZ PMT1 ;EXIT IF ZERO + ACALL ROUT ;OUTPUT DP + ACALL NUM_RT + CJNE A,2,USINGX ;COMPARE A TO R2 + ; +USINGY: MOV A,R2 + AJMP Z7R7 + ; +USINGX: JNC USINGY + ; +USING2: XCH A,R2 + CLR C + SUBB A,R2 + XCH A,R2 + ACALL Z7R7 ;OUTPUT ZEROS IF NEED TO + MOV A,R2 + MOV R7,A + AJMP OUTR0 + ; + ; First, force exponential output, if need to + ; +FREE: MOV A,R6 ;GET THE EXPONENT + JNZ FREE1 ;IF ZERO, PRINT IT + ACALL SOUT + AJMP ZOUT + ; +FREE1: MOV R3,#0F0H ;IN CASE EXP NEEDED + MOV A,#80H-DIGIT-DIGIT-1 + ADD A,R6 + JC EXPOUT + SUBB A,#0F7H + JC EXPOUT + ; + ; Now, just print the number + ; + ACALL SINOUT ;PRINT THE SIGN OF THE NUMBER + ACALL NUM_LT ;GET THE NUMBER LEFT OF DP + CJNE A,#8,FREE4 + AJMP OUTR0 + ; +FREE4: ACALL OUTR0 + ACALL ZTEST ;TEST FOR TRAILING ZEROS + JZ U_RET ;DONE IF ALL TRAILING ZEROS + ACALL ROUT ;OUTPUT RADIX + ; +FREE2: MOV R7,#1 ;OUTPUT ONE DIGIT + ACALL OUTR0 + JNZ U_RET + ACALL ZTEST + JZ U_RET + SJMP FREE2 ;LOOP + ; +EXPOUT: ACALL SINOUT ;PRINT THE SIGN + MOV R7,#1 ;OUTPUT ONE CHARACTER + ACALL OUTR0 + ACALL ROUT ;OUTPUT RADIX + MOV A,R3 ;GET FORMAT + ANL A,#0FH ;STRIP INDICATOR + JZ EXPOTX + ; + MOV R7,A ;OUTPUT THE NUMBER OF DIGITS + DEC R7 ;ADJUST BECAUSE ONE CHAR ALREADY OUT + ACALL OUTR0 + SJMP EXPOT4 + ; +EXPOTX: ACALL FREE2 ;OUTPUT UNTIL TRAILING ZEROS + ; +EXPOT4: ACALL SOUT ;OUTPUT A SPACE + MOV R5,#'E' + ACALL SOUT1 ;OUTPUT AN E + MOV A,R6 ;GET THE EXPONENT + JZ XOUT0 ;EXIT IF ZERO + DEC A ;ADJUST FOR THE DIGIT ALREADY OUTPUT + CJNE A,#80H,XOUT2 ;SEE WHAT IT IS + ; +XOUT0: ACALL SOUT + CLR A + SJMP XOUT4 + ; +XOUT2: JC XOUT3 ;NEGATIVE EXPONENT + MOV R5,#'+' ;OUTPUT A PLUS SIGN + ACALL SOUT1 + SJMP XOUT4 + ; +XOUT3: ACALL MOUT + CPL A ;FLIP BITS + INC A ;BUMP + ; +XOUT4: CLR ACC.7 + MOV R0,A + MOV R2,#0 + MOV R1,#LO(CONVT) ;CONVERSION LOCATION + MOV R3,#HI(CONVT) + ACALL CONVERT_BINARY_TO_ASCII_STRING + MOV R0,#LO(CONVT) ;NOW, OUTPUT EXPONENT + ; +EXPOT5: MOVX A,@R0 ;GET THE CHARACTER + MOV R5,A ;OUTPUT IT + ACALL SOUT1 + INC R0 ;BUMP THE POINTER + MOV A,R0 ;GET THE POINTER + CJNE A,R1B0,EXPOT5 ;LOOP + ; +U_RET: RET ;EXIT + ; +OUTR0: ; Output the characters pointed to by R0, also bias ascii + ; + MOV A,R7 ;GET THE COUNTER + JZ OUTR ;EXIT IF DONE + MOV A,@R0 ;GET THE NUMBER + ORL A,#30H ;ASCII BIAS + INC R0 ;BUMP POINTER AND COUNTER + DEC R7 + MOV R5,A ;PUT CHARACTER IN OUTPUT REGISTER + ACALL SOUT1 ;OUTPUT THE CHARACTER + CLR A ;JUST FOR TEST + CJNE R0,#FP_NIB8+1,OUTR0 + MOV A,#55H ;KNOW WHERE EXIT OCCURED + ; +OUTR: RET + ; +ZTEST: MOV R1,R0B0 ;GET POINTER REGISTER + ; +ZT0: MOV A,@R1 ;GET THE VALUE + JNZ ZT1 + INC R1 ;BUMP POINTER + CJNE R1,#FP_NIB8+1,ZT0 + ; +ZT1: RET + ; +NUM_LT: MOV A,R6 ;GET EXPONENT + CLR C ;GET READY FOR SUBB + SUBB A,#80H ;SUB EXPONENT BIAS + JNC NL1 ;OK IF NO CARRY + CLR A ;NO DIGITS LEFT + ; +NL1: MOV R7,A ;SAVE THE COUNT + RET + ; +NUM_RT: CLR C ;SUBB AGAIN + MOV A,#80H ;EXPONENT BIAS + SUBB A,R6 ;GET THE BIASED EXPONENT + JNC NR1 + CLR A + ; +NR1: RET ;EXIT + ; +SPACE7: MOV A,R7 ;GET THE NUMBER OF SPACES + JZ NR1 ;EXIT IF ZERO + ACALL SOUT ;OUTPUT A SPACE + DEC R7 ;BUMP COUNTER + SJMP SPACE7 ;LOOP + ; +Z7R7: MOV R7,A + ; +ZERO7: MOV A,R7 ;GET COUNTER + JZ NR1 ;EXIT IF ZERO + ACALL ZOUT ;OUTPUT A ZERO + DEC R7 ;BUMP COUNTER + SJMP ZERO7 ;LOOP + ; +SS7: ACALL SPACE7 + ; +SINOUT: MOV A,R4 ;GET THE SIGN + JZ SOUT ;OUTPUT A SPACE IF ZERO + ; +MOUT: MOV R5,#'-' + SJMP SOUT1 ;OUTPUT A MINUS IF NOT + ; +ROUT: MOV R5,#'.' ;OUTPUT A RADIX + SJMP SOUT1 + ; +ZOUT: MOV R5,#'0' ;OUTPUT A ZERO + SJMP SOUT1 + ; +SOUT: MOV R5,#' ' ;OUTPUT A SPACE + ; +SOUT1: AJMP OUTPUT + ; + newpage + ;*************************************************************** + ; +CONVERT_ASCII_STRING_TO_BINARY: + ; + ;DPTR POINTS TO ASCII STRING + ;PUT THE BINARY NUMBER IN R2:R0, ERROR IF >64K + ; + ;*************************************************************** + ; +CASB: ACALL HEXSCAN ;SEE IF HEX NUMBER + MOV ADD_IN,C ;IF ADD_IN IS SET, THE NUMBER IS HEX + ACALL GET_DIGIT_CHECK + CPL C ;FLIP FOR EXIT + JC RCASB + MOV R3,#00H ;ZERO R3:R1 FOR LOOP + MOV R1,#00H + SJMP CASB5 + ; +CASB2: INC DPTR + MOV R0B0,R1 ;SAVE THE PRESENT CONVERTED VALUE + MOV R0B0+2,R3 ;IN R2:R0 + ACALL GET_DIGIT_CHECK + JC CASB5 + JNB ADD_IN,RCASB ;CONVERSION COMPLETE + ACALL HEX_CHECK ;SEE IF HEX NUMBER + JC CASB4 ;PROCEED IF GOOD + INC DPTR ;BUMP PAST H + SJMP RCASB + ; +CASB4: ADD A,#9 ;ADJUST HEX ASCII BIAS + ; +CASB5: MOV B,#10 + JNB ADD_IN,CASB6 + MOV B,#16 ;HEX MODE + ; +CASB6: ACALL MULNUM ;ACCUMULATE THE DIGITS + JNC CASB2 ;LOOP IF NO CARRY + ; +RCASB: CLR A ;RESET ACC + MOV ACC_OVERFLOW,C ;IF OVERFLOW, SAY SO ******AA + RET ;EXIT + ; + newpage + ; +MULNUM10:MOV B,#10 + ; + ;*************************************************************** + ; +MULNUM: ; Take the next digit in the acc (masked to 0FH) + ; accumulate in R3:R1 + ; + ;*************************************************************** + ; + PUSH ACC ;SAVE ACC + PUSH B ;SAVE MULTIPLIER + MOV A,R1 ;PUT LOW ORDER BITS IN ACC + MUL AB ;DO THE MULTIPLY + MOV R1,A ;PUT THE RESULT BACK + MOV A,R3 ;GET THE HIGH ORDER BYTE + MOV R3,B ;SAVE THE OVERFLOW + POP B ;GET THE MULTIPLIER + MUL AB ;DO IT + MOV C,OV ;SAVE OVERFLOW IN F0 + MOV F0,C + ADD A,R3 ;ADD OVERFLOW TO HIGH RESULT + MOV R3,A ;PUT IT BACK + POP ACC ;GET THE ORIGINAL ACC BACK + ORL C,F0 ;OR CARRY AND OVERFLOW + JC MULX ;NO GOOD IF THE CARRY IS SET + ; +MUL11: ANL A,#0FH ;MASK OFF HIGH ORDER BITS + ADD A,R1 ;NOW ADD THE ACC + MOV R1,A ;PUT IT BACK + CLR A ;PROPAGATE THE CARRY + ADDC A,R3 + MOV R3,A ;PUT IT BACK + ; +MULX: RET ;EXIT WITH OR WITHOUT CARRY + ; + ;*************************************************************** + ; +CONVERT_BINARY_TO_ASCII_STRING: + ; + ;R3:R1 contains the address of the string + ;R2:R0 contains the value to convert + ;DPTR, R7, R6, and ACC gets clobbered + ; + ;*************************************************************** + ; + CLR A ;NO LEADING ZEROS + MOV DPTR,#10000 ;SUBTRACT 10000 + ACALL RSUB ;DO THE SUBTRACTION + MOV DPTR,#1000 ;NOW 1000 + ACALL RSUB + MOV DPTR,#100 ;NOW 100 + ACALL RSUB + MOV DPTR,#10 ;NOW 10 + ACALL RSUB + MOV DPTR,#1 ;NOW 1 + ACALL RSUB + JZ RSUB2 ;JUMP OVER RET + ; +RSUB_R: RET + ; +RSUB: MOV R6,#-1 ;SET UP THE COUNTER + ; +RSUB1: INC R6 ;BUMP THE COUNTER + XCH A,R2 ;DO A FAST COMPARE + CJNE A,DPH,$+3 + XCH A,R2 + JC FAST_DONE + XCH A,R0 ;GET LOW BYTE + SUBB A,DPL ;SUBTRACT, CARRY IS CLEARED + XCH A,R0 ;PUT IT BACK + XCH A,R2 ;GET THE HIGH BYTE + SUBB A,DPH ;ADD THE HIGH BYTE + XCH A,R2 ;PUT IT BACK + JNC RSUB1 ;LOOP UNTIL CARRY + ; + XCH A,R0 + ADD A,DPL ;RESTORE R2:R0 + XCH A,R0 + XCH A,R2 + ADDC A,DPH + XCH A,R2 + ; +FAST_DONE: + ; + ORL A,R6 ;OR THE COUNT VALUE + JZ RSUB_R ;RETURN IF ZERO + ; +RSUB2: MOV A,#'0' ;GET THE ASCII BIAS + ADD A,R6 ;ADD THE COUNT + ; +RSUB4: MOV P2,R3 ;SET UP P2 + MOVX @R1,A ;PLACE THE VALUE IN MEMORY + INC R1 + CJNE R1,#00H,RSUB3 ;SEE IF RAPPED AROUND + INC R3 ;BUMP HIGH BYTE + ; +RSUB3: RET ;EXIT + ; + newpage + ;*************************************************************** + ; +HEXOUT: ; Output the hex number in R3:R1, supress leading zeros, if set + ; + ;*************************************************************** + ; + ACALL SOUT ;OUTPUT A SPACE + MOV C,ZSURP ;GET ZERO SUPPRESSION BIT + MOV ADD_IN,C + MOV A,R3 ;GET HIGH NIBBLE AND PRINT IT + ACALL HOUTHI + MOV A,R3 + ACALL HOUTLO + ; +HEX2X: CLR ADD_IN ;DON'T SUPPRESS ZEROS + MOV A,R1 ;GET LOW NIBBLE AND PRINT IT + ACALL HOUTHI + MOV A,R1 + ACALL HOUTLO + MOV R5,#'H' ;OUTPUT H TO INDICATE HEX MODE + ; +SOUT_1: AJMP SOUT1 + ; +HOUT1: CLR ADD_IN ;PRINTED SOMETHING, SO CLEAR ADD_IN + ADD A,#90H ;CONVERT TO ASCII + DA A + ADDC A,#40H + DA A ;GOT IT HERE + MOV R5,A ;OUTPUT THE BYTE + SJMP SOUT_1 + ; +HOUTHI: SWAP A ;SWAP TO OUTPUT HIGH NIBBLE + ; +HOUTLO: ANL A,#0FH ;STRIP + JNZ HOUT1 ;PRINT IF NOT ZERO + JNB ADD_IN,HOUT1 ;OUTPUT A ZERO IF NOT SUPRESSED + RET + ; + newpage + ORG 1FEBH ;FOR LINK COMPATABILITY + ; + ; +GET_DIGIT_CHECK: ; Get a character, then check for digit + ; + ACALL GET_DPTR_CHARACTER + ; +DIGIT_CHECK: ;CHECK FOR A VALID ASCII DIGIT, SET CARRY IF FOUND + ; + CJNE A,#'9'+1,$+3 ;SEE IF ASCII 9 OR LESS + JC DC1 + RET + ; +DC1: CJNE A,#'0',$+3 ;SEE IF ASCII 0 OR GREATER + CPL C + RET + + endsection diff --git a/tests/t_bas52/bas52.out b/tests/t_bas52/bas52.out new file mode 100644 index 0000000..b6a0f80 --- /dev/null +++ b/tests/t_bas52/bas52.out @@ -0,0 +1,75 @@ + ;*************************************************************** + ; + ; TEROT - Output a character to the system console + ; update PHEAD position. + ; + ;*************************************************************** + ; +STEROT: MOV R5,#' ' ;OUTPUT A SPACE + ; +TEROT: PUSH ACC ;SAVE THE ACCUMULATOR + PUSH DPH ;SAVE THE DPTR + PUSH DPL + JNB CNT_S,$+7 ;WAIT FOR A CONTROL Q + ACALL BCK ;GET SERIAL STATUS + SJMP $-5 + MOV A,R5 ;PUT OUTPUT BYTE IN A + JNB BO,$+8 ;CHECK FOR MONITOR + LCALL 2040H ;DO THE MONITOR + AJMP TEROT1 ;CLEAN UP + JNB COUB,$+8 ;SEE IF USER WANTS OUTPUT + LCALL 4030H + AJMP TEROT1 + JNB UPB,T_1 ;NO AT IF NO XBIT + JNB LPB,T_1 ;AT PRINT + LCALL 403CH ;CALL AT LOCATION + AJMP TEROT1 ;FINISH OFF OUTPUT + ; +T_1: JNB COB,TXX ;SEE IF LIST SET + MOV DPTR,#SPV ;LOAD BAUD RATE + ACALL LD_T + CLR LP ;OUTPUT START BIT + ACALL TIMER_LOAD ;LOAD AND START THE TIMER + MOV A,R5 ;GET THE OUTPUT BYTE + SETB C ;SET CARRY FOR LAST OUTPUT + MOV R5,#9 ;LOAD TIMER COUNTDOWN + ; +LTOUT1: RRC A ;ROTATE A + JNB TF1,$ ;WAIT TILL TIMER READY + MOV LP,C ;OUTPUT THE BIT + ACALL TIMER_LOAD ;DO THE NEXT BIT + DJNZ R5,LTOUT1 ;LOOP UNTIL DONE + JNB TF1,$ ;FIRST STOP BIT + ACALL TIMER_LOAD + JNB TF1,$ ;SECOND STOP BIT + MOV R5,A ;RESTORE R5 + SJMP TEROT1 ;BACK TO TEROT + ; + newpage +TXX: JNB TI,$ ;WAIT FOR TRANSMIT READY + CLR TI + MOV SBUF,R5 ;SEND OUT THE CHARACTER + ; +TEROT1: CJNE R5,#CR,$+6 ;SEE IF A CR + MOV PHEAD,#00H ;IF A CR, RESET PHEAD AND + ; + CJNE R5,#LF,NLC ;SEE IF A LF + MOV A,NULLCT ;GET THE NULL COUNT + JZ NLC ;NO NULLS IF ZERO + ; +TEROT2: MOV R5,#NULL ;PUT THE NULL IN THE OUTPUT REGISTER + ACALL TEROT ;OUTPUT THE NULL + DEC A ;DECREMENT NULL COUNT + JNZ TEROT2 ;LOOP UNTIL DONE + ; +NLC: CJNE R5,#BS,$+5 ;DEC PHEAD IF A BACKSPACE + DEC PHEAD + CJNE R5,#20H,$+3 ;IS IT A PRINTABLE CHARACTER? + JC $+4 ;DON'T INCREMENT PHEAD IF NOT PRINTABLE + INC PHEAD ;BUMP PRINT HEAD + POP DPL ;RESTORE DPTR + POP DPH + POP ACC ;RESTORE ACC + RET ;EXIT + ; + diff --git a/tests/t_bas52/bas52.pgm b/tests/t_bas52/bas52.pgm new file mode 100644 index 0000000..080d43f --- /dev/null +++ b/tests/t_bas52/bas52.pgm @@ -0,0 +1,125 @@ + +PG8: MOV R7,#00H ;PROGRAM ONE BYTE AT A TIME + MOV R6,#01H + MOV R2,#HI(ROMADR-1) + MOV R0,#LO(ROMADR-1);LOAD PROM ADDRESS + ACALL PG1+3 + INC R6 + DB 0E5H ;MOV A DIRECT OP CODE + DB 0CBH ;ADDRESS OF R2CAP HIGH + ACALL PG1+3 + DB 0E5H ;MOV A, DIRECT OP CODE + DB 0CAH ;R2CAP LOW + MOV R6,#3 + MOV R1,#LO(MEMTOP-1) + MOV R3,#HI(MEMTOP) + ACALL PG1+3 ;SAVE MEMTOP + SJMP PGR + ; +CIPROG: MOV DPTR,#IPROGS ;LOAD IPROG LOCATION + SETB INTELB + SJMP $+7 ;GO DO PROG + ; +CPROG: MOV DPTR,#PROGS ;LOAD PROG LOCATION + CLR INTELB + ; + ACALL LD_T ;LOAD THE TIMER + CLR PROMV ;TURN ON THE PROM VOLTAGE + LCALL DELTST ;SEE IF A CR ******AA CALL-->LCALL + JNZ PG8 ;SAVE TIMER IF SO + MOV R4,#0FEH + SETB INBIT + ACALL ROMFD ;GET THE ROM ADDRESS OF THE LAST LOCATION + LCALL TEMPD ;SAVE THE ADDRESS ******AA CALL-->LCALL + MOV A,R4 ;GET COUNT + CPL A + LCALL TWO_R2 ;PUT IT ON THE STACK ******AA CALL-->LCALL + CALL FP_BASE+14 ;OUTPUT IT + ACALL CCAL ;GET THE PROGRAM + ACALL CRLF ;DO CRLF + MOV R0,TEMP4 ;GET ADDRESS + MOV R2,TEMP5 + MOV A,#55H ;LOAD SIGNIFIER + INC R6 ;LOAD LEN + 1 + CJNE R6,#00,$+4 + INC R7 + ACALL PG2-2 + ; + newpage +PGR: SETB PROMV + AJMP C_K + ; +PG1: MOV P2,R3 ;GET THE BYTE TO PROGRAM + MOVX A,@R1 + LCALL INC3210 ;BUMP POINTERS + MOV R5,#1 ;SET UP INTELLIGENT COUMTER + ; +PG2: MOV R4,A ;SAVE THE BYTE IN R4 + ACALL PG7 ;PROGRAM THE BYTE + ACALL PG9 + JB INTELB,PG4 ;SEE IF INTELLIGENT PROGRAMMING + ; +PG3: XRL A,R4 + JNZ PG6 ;ERROR IF NOT THE SAME + LCALL DEC76 ;BUMP THE COUNTERS ******AA CALL-->LCALL + JNZ PG1 ;LOOP IF NOT DONE + ANL PSW,#11100111B ;INSURE RB0 + RET + ; +PG4: XRL A,R4 ;SEE IF PROGRAMMED + JNZ PG5 ;JUMP IF NOT + MOV A,R4 ;GET THE DATA BACK + ACALL PG7 ;PROGRAM THE LOCATION + ACALL ZRO ;AGAIN + ACALL ZRO ;AND AGAIN + ACALL ZRO ;AND AGAIN + DJNZ R5,$-6 ;KEEP DOING IT + ACALL PG9 ;RESET PROG + SJMP PG3 ;FINISH THE LOOP + ; +PG5: INC R5 ;BUMP THE COUNTER + MOV A,R4 ;GET THE BYTE + CJNE R5,#25,PG2 ;SEE IF TRIED 25 TIMES + ; +PG6: SETB PROMV ;TURN OFF PROM VOLTAGE + MOV PSW,#0 ;INSURE RB0 + JNB DIRF,PG4-1 ;EXIT IF IN RUN MODE + MOV DPTR,#E16X ;PROGRAMMING ERROR + ; +ERRLK: LJMP ERROR ;PROCESS THE ERROR + ; + newpage +PG7: MOV P0,R0 ;SET UP THE PORTS + MOV P2,R2 ;LATCH LOW ORDER ADDRESS + ACALL PG11 ;DELAY FOR 8748/9 + CLR ALED + MOV P0,A ;PUT DATA ON THE PORT + ; +ZRO: NOP ;SETTLEING TIME + FP ZERO + NOP + NOP + NOP + NOP + NOP + ACALL PG11 ;DELAY A WHILE + CLR PROMP ;START PROGRAMMING + ACALL TIMER_LOAD ;START THE TIMER + JNB TF1,$ ;WAIT FOR PART TO PROGRAM + RET ;EXIT + ; +PG9: SETB PROMP + ACALL PG11 ;DELAY FOR A WHILE + JNB P3.2,$ ;LOOP FOR EEPROMS + MOV P0,#0FFH + CLR P3.7 ;LOWER READ + ACALL PG11 + MOV A,P0 ;READ THE PORT + SETB P3.7 + SETB ALED + RET + ; +PG11: MOV TEMP5,#12 ;DELAY 30uS AT 12 MHZ + DJNZ TEMP5,$ + RET + ; + diff --git a/tests/t_bas52/bas52.pwm b/tests/t_bas52/bas52.pwm new file mode 100644 index 0000000..44ac409 --- /dev/null +++ b/tests/t_bas52/bas52.pwm @@ -0,0 +1,25 @@ + ;************************************************************** + ; +STONE: ; Toggle the I/O port + ; + ;************************************************************** + ; + CALL THREE ;GET THE NUMBERS + ACALL CBIAS ;BIAS R3:R1 FOR COUNT LOOP + ; +STONE1: CLR T_BIT ;TOGGLE THE BIT + CLR TR1 ;STOP THE TIMER + MOV TH1,R3 ;LOAD THE TIMER + MOV TL1,R1 + CLR TF1 ;CLEAR THE OVERFLOW FLAG + SETB TR1 ;TURN IT ON + ACALL DEC76 + JNB TF1,$ ;WAIT + ACALL ALPAR + SETB T_BIT ;BACK TO A ONE + CALL TIMER_LOAD+2 ;LOAD THE HIGH VALUE + JNB TF1,$ ;WAIT + JNZ STONE1 ;LOOP + RET + ; + diff --git a/tests/t_bas52/bas52.rst b/tests/t_bas52/bas52.rst new file mode 100644 index 0000000..2d2f13a --- /dev/null +++ b/tests/t_bas52/bas52.rst @@ -0,0 +1,111 @@ + + ;************************************************************** + ; +CRST: ; This performs system initialzation, it was moved here so the + ; new power on reset functions could be tested in an 8751. + ; + ;************************************************************** + ; + ; First, initialize SFR's + ; + MOV SCON,#5AH ;INITIALIZE SFR'S + MOV TMOD,#10H + MOV TCON,#54H + DB 75H ;MOV DIRECT, # OP CODE + DB 0C8H ;T2CON LOCATION + DB 34H ;CONFIGURATION BYTE + ; + MOV DPTR,#2001H ;READ CODE AT 2001H + CLR A + MOVC A,@A+DPTR + CJNE A,#0AAH,$+6 ;IF IT IS AN AAH, DO USER RESET + LCALL 2090H + ; + MOV R0,#IRAMTOP ;PUT THE TOP OF RAM IN R0 + CLR A ;ZERO THE ACC + ; + MOV @R0,A ;CLEAR INTERNAL MEMORY + DJNZ R0,$-1 ;LOOP TIL DONE + ; + ; Now, test the external memory + ; + MOV SPSAV,#CMNDSP ;SET UP THE STACK + MOV SP,SPSAV + ; + MOV BOFAH,#HI(ROMADR) + MOV BOFAL,#LO(ROMADR+17) + MOV DPTR,#ROMADR ;GET THE BYTE AT 8000H + MOVX A,@DPTR + CLR C + SUBB A,#31H ;FOR BIAS + MOV MT1,A ;SAVE IN DIRECT MATH LOC + CLR ACC.2 ;SAVE FOR RESET + MOV R7,A ;SAVE IT IN R7 + INC DPTR + ACALL L31DPI ;SAVE BAUD RATE + LCALL RCL + INC DPTR ;GET MEMTOP + ACALL L31DPI + MOV DPTR,#5FH ;READ THE EXTERNAL BYTE + MOVX A,@DPTR + MOV DPTR,#0 ;ESTABLISH BASE FOR CLEAR + CJNE A,#0A5H,CRS + MOV A,MT1 + CLR ACC.0 ;CLEAR BIT ONE + XRL A,#4H + JZ CR2 + ; +CRS: CJNE R7,#2,$+5 + SJMP $+5 + CJNE R7,#3,$+7 + ACALL CL_1 + SJMP CR1 + ; +CR0: MOV R3,DPH ;SAVE THE DPTR + MOV R1,DPL + INC DPTR + MOV A,#5AH + MOVX @DPTR,A + MOVX A,@DPTR + CJNE A,#5AH,CR1 + CLR A + MOVX @DPTR,A + CJNE R3,#0E0H,CR0 + ; +CR1: CJNE R3,#03H,$+3 ;NEED THIS MUCH RAM + JC CRST + MOV DPTR,#MEMTOP ;SAVE MEMTOP + ACALL S31DP2 ;SAVE MEMTOP AND SEED RCELL + ACALL CNEW ;CLEAR THE MEMORY AND SET UP POINTERS + ; +CR2: ACALL RC1 ;SET UP STACKS IF NOT DONE + ; + LCALL AXTAL0 ;DO THE CRYSTAL + MOV A,MT1 ;GET THE RESET BYTE + CJNE A,#5,$+6 + LCALL 4039H + JNC BG1 ;CHECK FOR 0,1,2,3, OR 4 + JNB ACC.0,BG3 ;NO RUN IF WRONG TYPE + MOV DPTR,#ROMADR+16 + MOVX A,@DPTR ;READ THE BYTE + CJNE A,#55H,BG3 + LJMP CRUN + ; +BG1: CLR A ;DO BAUD RATE + MOV R3,A + MOV R1,A + MOV R0,#4 + JB RXD,$ ;LOOP UNTIL A CHARACTER IS RECEIVED + ; +BG2: DJNZ R0,$ ;FOUR CLOCKS, IN LOOP + LCALL DEC3210+4 ;NINE CLOCKS ******AA CALL-->LCALL + MOV R0,#2 ;ONE CLOCK + JNB RXD,BG2 ;TWO CLOCKS, LOOP UNTIL DONE + JB RXD,$ ;WAIT FOR STOP CHARACTER TO END + JNB RXD,$ + LCALL RCL ;LOAD THE TIMER ******AA CALL-->LCALL + ; +BG3: MOV DPTR,#S_N ;GET THE MESSAGE + ACALL CRP ;PRINT IT + LJMP CRAM + diff --git a/tests/t_bas52/bas52.tl b/tests/t_bas52/bas52.tl new file mode 100644 index 0000000..fdf95da --- /dev/null +++ b/tests/t_bas52/bas52.tl @@ -0,0 +1,16 @@ + + ;************************************************************** + ; +TIMER_LOAD:; Load the timer + ; + ;************************************************************* + ; + ACALL $-1 ;DELAY FOUR CLOCKS + CLR TR1 ;STOP IT WHILE IT'S LOADED + MOV TH1,T_HH + MOV TL1,T_LL + CLR TF1 ;CLEAR THE OVERFLOW FLAG + SETB TR1 ;START IT NOW + RET + ; + diff --git a/tests/t_bas52/look52.inc b/tests/t_bas52/look52.inc new file mode 100644 index 0000000..b4d13f4 --- /dev/null +++ b/tests/t_bas52/look52.inc @@ -0,0 +1,779 @@ + ;************************************************************** + ; + ; This is the equate table for 8052 basic. + ; + ;************************************************************** + ; + ; The register to direct equates for CJNE instructions. + ; +R0B0 EQU 0 +R1B0 EQU 1 +R2B0 EQU 2 +R3B0 EQU 3 +R4B0 EQU 4 +R5B0 EQU 5 +R6B0 EQU 6 +R7B0 EQU 7 + ; + ; Register bank 1 contains the text pointer + ; and the arg stack pointer. + ; +TXAL EQU 8 ;R0 BANK 1 = TEXT POINTER LOW +ASTKA EQU 9 ;R1 BANK 1 = ARG STACK +TXAH EQU 10 ;R2 BANK 1 = TEXT POINTER HIGH + ; + ; Now five temporary locations that are used by basic. + ; +TEMP1 EQU 11 +TEMP2 EQU 12 +TEMP3 EQU 13 +TEMP4 EQU 14 +TEMP5 EQU 15 + ; + newpage + ; Register bank 2 contains the read text pointer + ; and the control stack pointer. + ; +RTXAL EQU 16 ;R0 BANK 2 = READ TEXT POINTER LOW +CSTKA EQU 17 ;R1 BANK 2 = CONTROL STACK POINTER +RTXAH EQU 18 ;R2 BANK 2 = READ TEXT POINTER HIGH + ; + ; Now some internal system equates. + ; +BOFAH EQU 19 ;START OF THE BASIC PROGRAM, HIGH BYTE +BOFAL EQU 20 ;START OF THE BASIC PROGRAM, LOW BYTE +NULLCT EQU 21 ;NULL COUNT +PHEAD EQU 22 ;PRINT HEAD POSITION +FORMAT EQU 23 + ; + ; Register bank 3 is for the user and can be loaded + ; by basic + ; + ; + ; + ; Now everything else is used by basic. + ; First the bit locations, these use bytes 34, 35, 36, 37 and 38 + ; + newpage +OTS BIT 16 ;34.0-ON TIME INSTRUCTION EXECUTED +INPROG BIT 17 ;34.1-INTERRUPT IN PROCESS +INTBIT BIT 18 ;34.2-INTERRUPT SET BIT +ON_ERR BIT 19 ;34.3-ON ERROR EXECUTED +OTI BIT 20 ;34.4-ON TIME INTERRUPT IN PROGRESS +LINEB BIT 21 ;34.5-LINE CHANGE OCCURED +INTPEN BIT 22 ;34.6-INTERRUPT PENDING BIT +CONB BIT 23 ;34.7-CAN CONTINUE IF SET +GTRD BIT 24 ;35.0-READ GET LOCATION +LPB BIT 25 ;35.1-PRINT TO LINE PRINTER PORT +CKS_B BIT 26 ;35.2-FOR PWM INTERRUPT +COB BIT 27 ;35.3-CONSOLE OUT BIT + ; 0 = SERIAL PORT + ; 1 = LINE PRINTER +COUB BIT 28 ;35.4-USER CONSOLE OUT BIT + ; 0 = SERIAL PORT + ; 1 = USER DRIVER +INBIT BIT 29 ;35.5-INITIALIZATION BIT +CIUB BIT 30 ;35.6-USER CONSOLE IN BIT + ; 0 = SERIAL PORT + ; 1 = USER ROUTINE +SPINT BIT 31 ;35.7-SERIAL PORT INTERRUPT +STOPBIT BIT 32 ;36.0-PROGRAM STOP ENCOUNTERED +U_IDL BIT 33 ;36.1-USER IDLE BREAK +INP_B BIT 34 ;36.2-SET DURING INPUT INSTRUCTION +;DCMPXZ BIT 35 ;36.3-DCMPX ZERO FLAG +ARGF BIT 36 ;36.4-ARG STACK HAS A VALUE +RETBIT BIT 37 ;36.5-RET FROM INTERRUPT EXECUTED +I_T0 BIT 38 ;36.6-TRAP INTERRUPT ZERO TO MON +UPB BIT 39 ;36.7-SET WHEN @ IS VALID +JKBIT BIT 40 ;37.0-WB TRIGGER +ENDBIT BIT 41 ;37.1-GET END OF PROGRAM +UBIT BIT 42 ;37.2-FOR DIM STATEMENT +ISAV BIT 43 ;37.3-SAVE INTERRUPT STATUS +BO BIT 44 ;37.4-BUBBLE OUTPUT +XBIT BIT 45 ;37.5-EXTERNAL PROGRAM PRESENT +C_BIT BIT 46 ;37.6-SET WHEN CLOCK RUNNING +DIRF BIT 47 ;37.7-DIRECT INPUT MODE +NO_C BIT 48 ;38.0-NO CONTROL C +DRQ BIT 49 ;38.1-DMA ENABLED +BI BIT 50 ;38.2-BUBBLE INPUT +INTELB BIT 51 ;38.3-INTELLIGENT PROM PROGRAMMING +C0ORX1 BIT 52 ;38.4-PRINT FROM ROM OR RAM +CNT_S BIT 53 ;38.5-CONTROL S ENCOUNTERED +ZSURP BIT 54 ;38.6-ZERO SUPRESS +HMODE BIT 55 ;38.7-HEX MODE PRINT +LP BIT P1.7 ;SOFTWARE LINE PRINTER +DACK BIT P1.6 ;DMA ACK +PROMV BIT P1.5 ;TURN ON PROM VOLTAGE +PROMP BIT P1.4 ;PROM PULSE +ALED BIT P1.3 ;ALE DISABLE +T_BIT BIT P1.2 ;I/O TOGGLE BIT + ; + newpage + ; + ; The next location is a bit addressable byte counter + ; +BABC EQU 39 + ; + ; Now floating point and the other temps + ; + ; FP Uses to locations 03CH + ; + ; Now the stack designators. + ; +SPSAV EQU 3EH +S_LEN EQU 3FH +T_HH EQU 40H +T_LL EQU 41H +INTXAH EQU 42H +INTXAL EQU 43H +MT1 EQU 45H +MT2 EQU 46H +MILLIV EQU 47H ;TIMER LOCATIONS +TVH EQU 48H +TVL EQU 49H +SAVE_T EQU 4AH +SP_H EQU 4BH ;SERIAL PORT TIME OUT +SP_L EQU 4CH +CMNDSP EQU 4DH ;SYSTEM STACK POINTER +IRAMTOP EQU 0FFH ;TOP OF RAM +STACKTP EQU 0FEH ;ARG AND CONTROL STACK TOPS + ; + ; The character equates + ; +CR EQU 0DH ;CARRIAGE RETURN +LF EQU 0AH ;LINE FEED +BELL EQU 07H ;BELL CHARACTER +BS EQU 08H ;BACK SPACE +CNTRLC EQU 03H ;CONTROL C +CNTRLD EQU 04H ;CONTROL D +NULL EQU 00H ;NULL + ; + newpage + ; + ; The internal system equates + ; +LINLEN EQU 73 ;THE LENGTH OF AN INPUT LINE +EOF EQU 01 ;END OF FILE CHARACTER +ASTKAH EQU 01 ;ASTKA IS IN PAGE 1 OF RAM +CSTKAH EQU 00 ;CSTKA IS IN PAGE 0 OF RAM +FTYPE EQU 01 ;CONTROL STACK "FOR" +GTYPE EQU 02 ;CONTROL STACK "GOSUB" +DTYPE EQU 03 ;DO-WHILE/UNTIL TYPE +ROMADR EQU 8000H ;LOCATION OF ROM + ; + ; The floating point equates + ; +FPSIZ EQU 6 ;NO. OF BYTES IN A FLOATING NUM +DIGIT EQU FPSIZ-2 ;THE MANTISSA OF A FLOATING NUM +STESIZ EQU FPSIZ+3 ;SIZE OF SYMBOL ADJUSTED TABLE ELEMENT +FP_BASE EQU 1993H ;BASE OF FLOATING POINT ROUTINES +PSTART EQU 512 ;START OF A PROGRAM IN RAM +FSIZE EQU FPSIZ+FPSIZ+2+2+1 + ; + newpage + ;************************************************************** + ; +USENT: ; User entry jump table + ; + ;************************************************************** + ; + DW CMND1 ;(00, 00H)COMMAND MODE JUMP + DW IFIX ;(01, 01H)CONVERT FP TO INT + DW PUSHAS ;(02, 02H)PUSH VALUE ONTO ARG STACK + DW POPAS ;(03, 03H)POP VALUE OFF ARG STACK + DW PG1 ;(04, 04H)PROGRAM A PROM + DW INLINE ;(05, 05H)INPUT A LINE + DW UPRNT ;(06, 06H)PRINT A LINR + DW CRLF ;(07, 07H)OUTPUT A CRLF + ; + ;************************************************************** + ; + ; This is the operation jump table for arithmetics + ; + ;************************************************************** + ; +OPTAB: DW ALPAR ;(08, 08H)LEFT PAREN + DW AEXP ;(09, 09H)EXPONENTAION + DW AMUL ;(10, 0AH)FP MUL + DW AADD ;(11, 0BH)FLOATING POINT ADD + DW ADIV ;(12, 0CH)FLOATING POINT DIVIDE + DW ASUB ;(13, 0DH)FLOATING POINT SUBTRACTION + DW AXRL ;(14, 0EH)XOR + DW AANL ;(15, 0FH)AND + DW AORL ;(16, 10H)OR + DW ANEG ;(17, 11H)NEGATE + DW AEQ ;(18, 12H)EQUAL + DW AGE ;(19, 13H)GREATER THAN OR EQUAL + DW ALE ;(20, 14H)LESS THAN OR EQUAL + DW ANE ;(21, 15H)NOT EQUAL + DW ALT ;(22, 16H)LESS THAN + DW AGT ;(23, 17H)GREATER THAN + ; + newpage + ;*************************************************************** + ; + ; This is the jump table for unary operators + ; + ;*************************************************************** + ; + DW AABS ;(24, 18H)ABSOLUTE VALUE + DW AINT ;(25, 19H)INTEGER OPERATOR + DW ASGN ;(26, 1AH)SIGN OPERATOR + DW ANOT ;(27, 1BH)ONE'S COMPLEMENT + DW ACOS ;(28, 1CH)COSINE + DW ATAN ;(29, 1DH)TANGENT + DW ASIN ;(30, 1EH)SINE + DW ASQR ;(31, 1FH)SQUARE ROOT + DW ACBYTE ;(32, 20H)READ CODE + DW AETOX ;(33, 21H)E TO THE X + DW AATAN ;(34, 22H)ARC TANGENT + DW ALN ;(35, 23H)NATURAL LOG + DW ADBYTE ;(36, 24H)READ DATA MEMORY + DW AXBYTE ;(37, 25H)READ EXTERNAL MEMORY + DW PIPI ;(38, 26H)PI + DW ARND ;(39, 27H)RANDOM NUMBER + DW AGET ;(40, 28H)GET INPUT CHARACTER + DW AFREE ;(41, 29H)COMPUTE #BYTES FREE + DW ALEN ;(42, 2AH) COMPUTE LEN OF PORGRAM + DW AXTAL ;(43, 2BH) CRYSTAL + DW PMTOP ;(44, 2CH)TOP OF MEMORY + DW ATIME ;(45, 2DH) TIME + DW A_IE ;(46, 2EH) IE + DW A_IP ;(47, 2FH) IP + DW ATIM0 ;(48, 30H) TIMER 0 + DW ATIM1 ;(49, 31H) TIMER 1 + DW ATIM2 ;(50, 32H) TIMER 2 + DW AT2CON ;(51, 33H) T2CON + DW ATCON ;(52, 34H) TCON + DW ATMOD ;(53, 35H) ATMOD + DW ARCAP2 ;(54, 36H) RCAP2 + DW AP1 ;(55, 37H) P1 + DW APCON ;(56, 38H) PCON + DW EXPRB ;(57, 39H) EVALUATE AN EXPRESSION + DW AXTAL1 ;(58, 3AH) CALCULATE CRYSTAL + DW LINE ;(59, 3BH) EDIT A LINE + DW PP ;(60, 3CH) PROCESS A LINE + DW UPPL-3 ;(61, 3DH) UNPROCESS A LINE + DW VAR ;(62, 3EH) FIND A VARIABLE + DW GC ;(63, 3FH) GET A CHARACTER + DW GCI ;(64, 40H) GET CHARACTER AND INCREMENT + DW INCHAR ;(65, 41H) INPUT A CHARACTER + DW CRUN ;(66, 42H) RUN A PROGRAM + newpage +OPBOL: DB 1 ; + ; + DB 15 ;LEFT PAREN + DB 14 ;EXPONENTIAN ** + DB 10 ;MUL + DB 8 ;ADD + DB 10 ;DIVIDE + DB 8 ;SUB + DB 3 ;XOR + DB 5 ;AND + DB 4 ;OR + DB 12 ;NEGATE + DB 6 ;EQ + DB 6 ;GT + DB 6 ;LT + DB 6 ;NE + DB 6 ;LE + DB 6 ;GE + ; +UOPBOL: DB 15 ;AABS + DB 15 ;AAINT + DB 15 ;ASGN + DB 15 ;ANOT + DB 15 ;ACOS + DB 15 ;ATAN + DB 15 ;ASIN + DB 15 ;ASQR + DB 15 ;ACBYTE + DB 15 ;E TO THE X + DB 15 ;AATAN + DB 15 ;NATURAL LOG + DB 15 ;DBYTE + DB 15 ;XBYTE + ; + newpage + ;*************************************************************** + ; + ; The ASCII printed messages. + ; + ;*************************************************************** + ; +STP: DB "STOP",'"' + ; +IAN: DB "TRY AGAIN",'"' + ; +RDYS: DB "READY",'"' + ; +INS: DB " - IN LINE ",'"' + ; + ;************************************************************** + ; + ; This is the command jump table + ; + ;************************************************************** + ; +CMNDD: DW CRUN ;RUN + DW CLIST ;LIST + DW CNULL ;NULL + DW CNEW ;NEW + DW CCONT ;CONTINUE + DW CPROG ;PROGRAM A PROM + DW CXFER ;TRANSFER FROM ROM TO RAM + DW CRAM ;RAM MODE + DW CROM ;ROM MODE + DW CIPROG ;INTELLIGENT PROM PROGRAMMING + ; + newpage + ;*************************************************************** + ; + ; This is the statement jump table. + ; + ;************************************************************** + ; +STATD: ; + DW SLET ;LET 80H + DW SCLR ;CLEAR 81H + DW SPUSH ;PUSH VAR 82H + DW SGOTO ;GO TO 83H + DW STONE ;TONE 84H + DW SPH0 ;PRINT MODE 0 85H + DW SUI ;USER INPUT 86H + DW SUO ;USER OUTPUT 87H + DW SPOP ;POP VAR 88H + DW SPRINT ;PRINT 89H + DW SCALL ;CALL 8AH + DW SDIMX ;DIMENSION 8BH + DW STRING ;STRING ALLO 8CH + DW SBAUD ;SET BAUD 8DH + DW SCLOCK ;CLOCK 8EH + DW SPH1 ;PRINT MODE 1 8FH + ; + ; No direct mode from here on + ; + DW SSTOP ;STOP 90H + DW SOT ;ON TIME 91H + DW SONEXT ;ON EXT INT 92H + DW SRETI ;RET FROM INT 93H + DW S_DO ;DO 94H + DW SRESTR ;RESTOR 95H + DW WCR ;REM 96H + DW SNEXT ;NEXT 97H + DW SONERR ;ON ERROR 98H + DW S_ON ;ON 99H + DW SINPUT ;INPUT 9AH + DW SREAD ;READ 9BH + DW FINDCR ;DATA 9CH + DW SRETRN ;RETURN 9DH + DW SIF ;IF 9EH + DW SGOSUB ;GOSUB 9FH + DW SFOR ;FOR A0H + DW SWHILE ;WHILE A1H + DW SUNTIL ;UNTIL A2H + DW CMND1 ;END A3H + DW I_DL ;IDLE A4H + DW ST_A ;STORE AT A5H + DW LD_A ;LOAD AT A6H + DW PGU ;PGM A7H + DW RROM ;RUN A ROM A9H + ; + newpage + ;************************************************************** + ; +TOKTAB: ; This is the basic token table + ; + ;************************************************************** + ; + ; First the tokens for statements + ; + DB 80H ;LET TOKEN + DB "LET" + ; + DB 81H ;CLEAR TOKEN + DB "CLEAR" + ; + DB 82H ;PUSH TOKEN + DB "PUSH" + ; +T_GOTO EQU 83H + ; + DB 83H ;GO TO TOKEN + DB "GOTO" + ; + DB 84H ;TOGGLE TOKEN + DB "PWM" + ; + DB 85H ;PRINT HEX MODE 0 + DB "PH0." + ; + DB 86H ;USER IN TOKEN + DB "UI" + ; + DB 87H ;USER OUT TOKEN + DB "UO" + ; + DB 88H ;POP TOKEN + DB "POP" + ; + newpage + DB 89H ;PRINT TOKEN + DB "PRINT" + DB 89H + DB "P." ;P. ALSO MEANS PRINT + DB 89H ;? ALSO + DB '?' + ; + DB 8AH ;CALL TOKEN + DB "CALL" + ; + DB 8BH ;DIMENSION TOKEN + DB "DIM" + ; + DB 8CH ;STRING TOKEN + DB "STRING" + ; + DB 8DH ;SET BAUD RATE + DB "BAUD" + ; + DB 8EH ;CLOCK + DB "CLOCK" + ; + DB 8FH ;PRINT HEX MODE 1 + DB "PH1." + ; +T_STOP EQU 90H ;STOP TOKEN + DB T_STOP + DB "STOP" + ; +T_DIR EQU T_STOP ;NO DIRECT FROM HERE ON + ; + DB T_STOP+1 ;ON TIMER INTERRUPT + DB "ONTIME" + ; + DB T_STOP+2 ;ON EXTERNAL INTERRUPT + DB "ONEX1" + ; + DB T_STOP+3 ;RETURN FROM INTERRUPT + DB "RETI" + ; + DB T_STOP+4 ;DO TOKEN + DB "DO" + ; + DB T_STOP+5 ;RESTORE TOKEN + DB "RESTORE" + ; + newpage +T_REM EQU T_STOP+6 ;REMARK TOKEN + DB T_REM + DB "REM" + ; + DB T_REM+1 ;NEXT TOKEN + DB "NEXT" + ; + DB T_REM+2 ;ON ERROR TOKEN + DB "ONERR" + ; + DB T_REM+3 ;ON TOKEN + DB "ON" + ; + DB T_REM+4 ;INPUT + DB "INPUT" + ; + DB T_REM+5 ;READ + DB "READ" + ; +T_DATA EQU T_REM+6 ;DATA + DB T_DATA + DB "DATA" + ; + DB T_DATA+1 ;RETURN + DB "RETURN" + ; + DB T_DATA+2 ;IF + DB "IF" + ; +T_GOSB EQU T_DATA+3 ;GOSUB + DB T_GOSB + DB "GOSUB" + ; + DB T_GOSB+1 ;FOR + DB "FOR" + ; + DB T_GOSB+2 ;WHILE + DB "WHILE" + ; + DB T_GOSB+3 ;UNTIL + DB "UNTIL" + ; + DB T_GOSB+4 ;END + DB "END" + ; + newpage +T_LAST EQU T_GOSB+5 ;LAST INITIAL TOKEN + ; +T_TAB EQU T_LAST ;TAB TOKEN + DB T_TAB + DB "TAB" + ; +T_THEN EQU T_LAST+1 ;THEN TOKEN + DB T_THEN + DB "THEN" + ; +T_TO EQU T_LAST+2 ;TO TOKEN + DB T_TO + DB "TO" + ; +T_STEP EQU T_LAST+3 ;STEP TOKEN + DB T_STEP + DB "STEP" + ; +T_ELSE EQU T_LAST+4 ;ELSE TOKEN + DB T_ELSE + DB "ELSE" + ; +T_SPC EQU T_LAST+5 ;SPACE TOKEN + DB T_SPC + DB "SPC" + ; +T_CR EQU T_LAST+6 + DB T_CR + DB "CR" + ; + DB T_CR+1 + DB "IDLE" + ; + DB T_CR+2 + DB "ST@" + ; + DB T_CR+3 + DB "LD@" + ; + DB T_CR+4 + DB "PGM" + ; + DB T_CR+5 + DB "RROM" + ; + newpage + ; Operator tokens + ; +T_LPAR EQU 0E0H ;LEFT PAREN + DB T_LPAR + DB '(' + ; + DB T_LPAR+1 ;EXPONENTIAN + DB "**" + ; + DB T_LPAR+2 ;FP MULTIPLY + DB '*' + ; +T_ADD EQU T_LPAR+3 + DB T_LPAR+3 ;ADD TOKEN + DB '+' + ; + DB T_LPAR+4 ;DIVIDE TOKEN + DB '/' + ; +T_SUB EQU T_LPAR+5 ;SUBTRACT TOKEN + DB T_SUB + DB '-' + ; + DB T_LPAR+6 ;LOGICAL EXCLUSIVE OR + DB ".XOR." + ; + DB T_LPAR+7 ;LOGICAL AND + DB ".AND." + ; + DB T_LPAR+8 ;LOGICAL OR + DB ".OR." + ; +T_NEG EQU T_LPAR+9 + ; +T_EQU EQU T_LPAR+10 ;EQUAL + DB T_EQU + DB '=' + ; + DB T_LPAR+11 ;GREATER THAN OR EQUAL + DB ">=" + ; + DB T_LPAR+12 ;LESS THAN OR EQUAL + DB "<=" + ; + DB T_LPAR+13 ;NOT EQUAL + DB "<>" + ; + DB T_LPAR+14 ;LESS THAN + DB '<' + ; + DB T_LPAR+15 ;GREATER THAN + DB '>' + ; + ; +T_UOP EQU 0B0H ;UNARY OP BASE TOKEN + ; + DB T_UOP ;ABS TOKEN + DB "ABS" + ; + DB T_UOP+1 ;INTEGER TOKEN + DB "INT" + ; + DB T_UOP+2 ;SIGN TOKEN + DB "SGN" + ; + DB T_UOP+3 ;GET TOKEN + DB "NOT" + ; + DB T_UOP+4 ;COSINE TOKEN + DB "COS" + ; + DB T_UOP+5 ;TANGENT TOKEN + DB "TAN" + ; + DB T_UOP+6 ;SINE TOKEN + DB "SIN" + ; + DB T_UOP+7 ;SQUARE ROOT TOKEN + DB "SQR" + ; + DB T_UOP+8 ;CBYTE TOKEN + DB "CBY" + ; + DB T_UOP+9 ;EXP (E TO THE X) TOKEN + DB "EXP" + ; + DB T_UOP+10 + DB "ATN" + ; + DB T_UOP+11 + DB "LOG" + ; + DB T_UOP+12 ;DBYTE TOKEN + DB "DBY" + ; + DB T_UOP+13 ;XBYTE TOKEN + DB "XBY" + ; +T_ULAST EQU T_UOP+14 ;LAST OPERATOR NEEDING PARENS + ; + DB T_ULAST + DB "PI" + ; + DB T_ULAST+1 ;RND TOKEN + DB "RND" + ; + DB T_ULAST+2 ;GET TOKEN + DB "GET" + ; + DB T_ULAST+3 ;FREE TOKEN + DB "FREE" + ; + DB T_ULAST+4 ;LEN TOKEN + DB "LEN" + ; +T_XTAL EQU T_ULAST+5 ;CRYSTAL TOKEN + DB T_XTAL + DB "XTAL" + ; +T_MTOP EQU T_ULAST+6 ;MTOP + DB T_MTOP + DB "MTOP" + ; +T_IE EQU T_ULAST+8 ;IE REGISTER + DB T_IE + DB "IE" + ; +T_IP EQU T_ULAST+9 ;IP REGISTER + DB T_IP + DB "IP" + ; +TMR0 EQU T_ULAST+10 ;TIMER 0 + DB TMR0 + DB "TIMER0" + ; +TMR1 EQU T_ULAST+11 ;TIMER 1 + DB TMR1 + DB "TIMER1" + ; +TMR2 EQU T_ULAST+12 ;TIMER 2 + DB TMR2 + DB "TIMER2" + ; +T_TIME EQU T_ULAST+7 ;TIME + DB T_TIME + DB "TIME" + ; +TT2C EQU T_ULAST+13 ;T2CON + DB TT2C + DB "T2CON" + ; +TTC EQU T_ULAST+14 ;TCON + DB TTC + DB "TCON" + ; +TTM EQU T_ULAST+15 ;TMOD + DB TTM + DB "TMOD" + ; +TRC2 EQU T_ULAST+16 ;RCAP2 + DB TRC2 + DB "RCAP2" + ; +T_P1 EQU T_ULAST+17 ;P1 + DB T_P1 + DB "PORT1" + ; +T_PC EQU T_ULAST+18 ;PCON + DB T_PC + DB "PCON" + ; +T_ASC EQU T_ULAST+19 ;ASC TOKEN + DB T_ASC + DB "ASC(" + ; +T_USE EQU T_ULAST+20 ;USING TOKEN + DB T_USE + DB "USING(" + DB T_USE + DB "U.(" + ; +T_CHR EQU T_ULAST+21 ;CHR TOKEN + DB T_CHR + DB "CHR(" + ; + newpage +T_CMND EQU 0F0H ;COMMAND BASE + ; + DB 0F0H ;RUN TOKEN + DB "RUN" + ; + DB 0F1H ;LIST TOKEN + DB "LIST" + ; + DB 0F2H ;NULL TOKEN + DB "NULL" + ; + DB 0F3H ;NEW TOKEN + DB "NEW" + ; + DB 0F4H ;CONTINUE TOKEN + DB "CONT" + ; + DB 0F5H ;PROGRAM TOKEN + DB "PROG" + ; + DB 0F6H ;TRANSFER TOKEN + DB "XFER" + ; + DB 0F7H ;RAM MODE + DB "RAM" + ; + DB 0F8H ;ROM MODE + DB "ROM" + ; + DB 0F9H ;INTELLIGENT PROM PROGRAMMING + DB "FPROG" + ; + DB 0FFH ;END OF TABLE + ; diff --git a/tests/t_bas52/t_bas52.asm b/tests/t_bas52/t_bas52.asm new file mode 100644 index 0000000..3fff5d8 --- /dev/null +++ b/tests/t_bas52/t_bas52.asm @@ -0,0 +1,4644 @@ +; December 18, 1986 +; MS-DOS compatible Source code for MCS BASIC-52 (tm) +; Assembles with ASM51 Macro Assembler Version 2.2 +; +; The following source code does not include the floating point math +; routines. These are seperately compiled using FP52.SRC. +; +; Both the BASIC.SRC and FP52.SRC programs assemble into ABSOLUTE +; object files, and do not need to be relocated or linked. The FP52 +; object code and the BASIC object code, when compiled without modification +; of the source listings, create the same object code that is found on +; the MCS BASIC-52 Version 1.1 microcontrollers. +; +; The original source code had 7 "include" files that have been incorporated +; into this file for ease of assembly. +; These 7 files are: LOOK52.SRC, BAS52.RST, BAS52.PGM, BAS52.TL, BAS52.OUT, +; BAS52.PWM, and BAS52.CLK. +; +; +; Intel Corporation, Embedded Controller Operations + + cpu 8052 + + page 0 + newpage + + include stddef51.inc + include bitfuncs.inc + bigendian on + + segment code + + ;************************************************************** + ; + ; TRAP VECTORS TO MONITOR + ; + ; RESET TAG (0AAH) ---------2001H + ; + ; TAG LOCATION (5AH) ------ 2002H + ; + ; EXTERNAL INTERRUPT 0 ---- 2040H + ; + ; COMMAND MODE ENTRY ------ 2048H + ; + ; SERIAL PORT ------------- 2050H + ; + ; MONITOR (BUBBLE) OUTPUT - 2058H + ; + ; MONITOR (BUBBLE) INPUT -- 2060H + ; + ; MONITOR (BUBBLE) CSTS --- 2068H + ; + ; GET USER JUMP VECTOR ---- 2070H + ; + ; GET USER LOOKUP VECTOR -- 2078H + ; + ; PRINT AT VECTOR --------- 2080H + ; + ; INTERRUPT PWM ----------- 2088H + ; + ; EXTERNAL RESET ---------- 2090H + ; + ; USER OUTPUT-------------- 4030H + ; + ; USER INPUT -------------- 4033H + ; + ; USER CSTS --------------- 4036H + ; + ; USER RESET -------------- 4039H + ; + ; USER DEFINED PRINT @ --- 403CH + ; + ;*************************************************************** + ; + newpage + ;*************************************************************** + ; + ; MCS - 51 - 8K BASIC VERSION 1.1 + ; + ;*************************************************************** + ; + AJMP CRST ;START THE PROGRAM + db 037h ; ******AA inserted + ; + ORG 3H + ; + ;*************************************************************** + ; + ;EXTERNAL INTERRUPT 0 + ; + ;*************************************************************** + ; + JB DRQ,STQ ;SEE IF DMA IS SET + PUSH PSW ;SAVE THE STATUS + LJMP 4003H ;JUMP TO USER IF NOT SET + ; + ORG 0BH + ; + ;*************************************************************** + ; + ;TIMER 0 OVERFLOW INTERRUPT + ; + ;*************************************************************** + ; + PUSH PSW ;SAVE THE STATUS + JB C_BIT,STJ ;SEE IF USER WANTS INTERRUPT + LJMP 400BH ;EXIT IF USER WANTS INTERRUPTS + ; + ORG 13H + ; + ;*************************************************************** + ; + ;EXTERNAL INTERRUPT 1 + ; + ;*************************************************************** + ; + JB INTBIT,STK + PUSH PSW + LJMP 4013H + ; + newpage + ; + ORG 1BH + ; + ;*************************************************************** + ; + ;TIMER 1 OVERFLOW INTERRUPT + ; + ;*************************************************************** + ; + PUSH PSW + LJMP CKS_I + ; +STJ: LJMP I_DR ;DO THE INTERRUPT + ; + ;*************************************************************** + ; + ;SERIAL PORT INTERRUPT + ; + ;*************************************************************** + ; + ORG 23H + ; + PUSH PSW + JB SPINT,STU ;SEE IF MONITOR EANTS INTERRUPT + LJMP 4023H + ; + ORG 2BH + ; + ;************************************************************** + ; + ;TIMER 2 OVERFLOW INTERRUPT + ; + ;************************************************************** + ; + PUSH PSW + LJMP 402BH + ; + newpage + ;************************************************************** + ; + ;USER ENTRY + ; + ;************************************************************** + ; + ORG 30H + ; + LJMP IBLK ;LINK TO USER BLOCK + ; +STQ: JB I_T0,STS ;SEE IF MONITOR WANTS IT + CLR DACK + JNB P3.2,$ ;WAIT FOR DMA TO END + SETB DACK + RETI + ; +STS: LJMP 2040H ;GO TO THE MONITOR + ; +STK: SETB INTPEN ;TELL BASIC AN INTERRUPT WAS RECEIVED + RETI + ; +STU: LJMP 2050H ;SERIAL PORT INTERRUPT + ; + newpage + + include look52.inc ; ******AA + +EIG: DB "EXTRA IGNORED",'"' + ; +EXA: DB "A-STACK",'"' + ; +EXC: DB "C-STACK",'"' + ; + newpage + + include bas52.rst ; ******AA + + newpage + ;*************************************************************** + ; + ; CIPROG AND CPROG - Program a prom + ; + ;*************************************************************** + ; + include bas52.pgm ; ******AA + newpage + ;************************************************************** + ; +PGU: ;PROGRAM A PROM FOR THE USER + ; + ;************************************************************** + ; + CLR PROMV ;TURN ON THE VOLTAGE + MOV PSW,#00011000B ;SELECT RB3 + ACALL PG1 ;DO IT + SETB PROMV ;TURN IT OFF + RET + ; + ; + ;************************************************************* + ; +CCAL: ; Set up for prom moves + ; R3:R1 gets source + ; R7:R6 gets # of bytes + ; + ;************************************************************* + ; + ACALL GETEND ;GET THE LAST LOCATION + INC DPTR ;BUMP TO LOAD EOF + MOV R3,BOFAH + MOV R1,BOFAL ;RESTORE START + CLR C ;PREPARE FOR SUBB + MOV A,DPL ;SUB DPTR - BOFA > R7:R6 + SUBB A,R1 + MOV R6,A + MOV A,DPH + SUBB A,R3 + MOV R7,A + RET + ; + ; + include bas52.tl ; ******AA + newpage + ;*************************************************************** + ; +CROM: ; The command action routine - ROM - Run out of rom + ; + ;*************************************************************** + ; + CLR CONB ;CAN'T CONTINUE IF MODE CHANGE + ACALL RO1 ;DO IT + ; +C_K: LJMP CL3 ;EXIT + ; +RO1: LCALL DELTST ;SEE IF INTGER PRESENT ******AA CALL-->LCALL, INTGER-->DELTST + MOV R4,#R1B0 ;SAVE THE NUMBER ******AA ABS-->IMM, R0B0-->R0B1 ?!? + JNC $+6 ; ******AA $+4-->$+6 ??? + ;MOV R4,#01H ;ONE IF NO INTEGER PRESENT ******AA repl. by next two + LCALL ONE ; ******AA + MOV R4,A ; ******AA + ACALL ROMFD ;FIND THE PROGRAM + CJNE R4,#0,RFX ;EXIT IF R4 <> 0 + INC DPTR ;BUMP PAST TAG + MOV BOFAH,DPH ;SAVE THE ADDRESS + MOV BOFAL,DPL + RET + ; +ROMFD: MOV DPTR,#ROMADR+16 ;START OF USER PROGRAM + ; +RF1: MOVX A,@DPTR ;GET THE BYTE + CJNE A,#55H,RF3 ;SEE IF PROPER TAG + DJNZ R4,RF2 ;BUMP COUNTER + ; +RFX: RET ;DPTR HAS THE START ADDRESS + ; +RF2: INC DPTR ;BUMP PAST TAG + ACALL G5 + INC DPTR ;BUMP TO NEXT PROGRAM + SJMP RF1 ;DO IT AGAIN + ; +RF3: JBC INBIT,RFX ;EXIT IF SET + ; +NOGO: MOV DPTR,#NOROM + AJMP ERRLK + ; + newpage + ;*************************************************************** + ; +L20DPI: ; load R2:R0 with the location the DPTR is pointing to + ; + ;*************************************************************** + ; + MOVX A,@DPTR + MOV R2,A + INC DPTR + MOVX A,@DPTR + MOV R0,A + RET ;DON'T BUMP DPTR + ; + ;*************************************************************** + ; +X31DP: ; swap R3:R1 with DPTR + ; + ;*************************************************************** + ; + XCH A,R3 + XCH A,DPH + XCH A,R3 + XCH A,R1 + XCH A,DPL + XCH A,R1 + RET + ; + ;*************************************************************** + ; +LD_T: ; Load the timer save location with the value the DPTR is + ; pointing to. + ; + ;**************************************************************** + ; + MOVX A,@DPTR + MOV T_HH,A + INC DPTR + MOVX A,@DPTR + MOV T_LL,A + RET + ; + newpage + ; + ;*************************************************************** + ; + ;GETLIN - FIND THE LOCATION OF THE LINE NUMBER IN R3:R1 + ; IF ACC = 0 THE LINE WAS NOT FOUND I.E. R3:R1 + ; WAS TOO BIG, ELSE ACC <> 0 AND THE DPTR POINTS + ; AT THE LINE THAT IS GREATER THAN OR EQUAL TO THE + ; VALUE IN R3:R1. + ; + ;*************************************************************** + ; +GETEND: SETB ENDBIT ;GET THE END OF THE PROGRAM + ; +GETLIN: LCALL DP_B ;GET BEGINNING ADDRESS ******AA CALL-->LCALL + ; +G1: LCALL B_C ; ******AA CALL-->LCALL + JZ G3 ;EXIT WITH A ZERO IN A IF AT END + INC DPTR ;POINT AT THE LINE NUMBER + JB ENDBIT,G2 ;SEE IF WE WANT TO FIND THE END + ACALL DCMPX ;SEE IF (DPTR) = R3:R1 + ACALL DECDP ;POINT AT LINE COUNT + MOVX A,@DPTR ;PUT LINE LENGTH INTO ACC + JB UBIT,G3 ;EXIT IF EQUAL + JC G3 ;SEE IF LESS THAN OR ZERO + ; +G2: ACALL ADDPTR ;ADD IT TO DPTR + SJMP G1 ;LOOP + ; +G3: CLR ENDBIT ;RESET ENDBIT + RET ;EXIT + ; +G4: MOV DPTR,#PSTART ;DO RAM + ; +G5: SETB ENDBIT + SJMP G1 ;NOW DO TEST + ; + newpage + ;*************************************************************** + ; + ; LDPTRI - Load the DATA POINTER with the value it is pointing + ; to - DPH = (DPTR) , DPL = (DPTR+1) + ; + ; acc gets wasted + ; + ;*************************************************************** + ; +LDPTRI: MOVX A,@DPTR ;GET THE HIGH BYTE + PUSH ACC ;SAVE IT + INC DPTR ;BUMP THE POINTER + MOVX A,@DPTR ;GET THE LOW BYTE + MOV DPL,A ;PUT IT IN DPL + POP DPH ;GET THE HIGH BYTE + RET ;GO BACK + ; + ;*************************************************************** + ; + ;L31DPI - LOAD R3 WITH (DPTR) AND R1 WITH (DPTR+1) + ; + ;ACC GETS CLOBBERED + ; + ;*************************************************************** + ; +L31DPI: MOVX A,@DPTR ;GET THE HIGH BYTE + MOV R3,A ;PUT IT IN THE REG + INC DPTR ;BUMP THE POINTER + MOVX A,@DPTR ;GET THE NEXT BYTE + MOV R1,A ;SAVE IT + RET + ; + ;*************************************************************** + ; + ;DECDP - DECREMENT THE DATA POINTER - USED TO SAVE SPACE + ; + ;*************************************************************** + ; +DECDP2: ACALL DECDP + ; +DECDP: XCH A,DPL ;GET DPL + JNZ $+4 ;BUMP IF ZERO + DEC DPH + DEC A ;DECREMENT IT + XCH A,DPL ;GET A BACK + RET ;EXIT + ; + newpage + ;*************************************************************** + ; + ;DCMPX - DOUBLE COMPARE - COMPARE (DPTR) TO R3:R1 + ;R3:R1 - (DPTR) = SET CARRY FLAG + ; + ;IF R3:R1 > (DPTR) THEN C = 0 + ;IF R3:R1 < (DPTR) THEN C = 1 + ;IF R3:R1 = (DPTR) THEN C = 0 + ; + ;*************************************************************** + ; +DCMPX: CLR UBIT ;ASSUME NOT EQUAL + MOVX A,@DPTR ;GET THE BYTE + CJNE A,R3B0,D1 ;IF A IS GREATER THAN R3 THEN NO CARRY + ;WHICH IS R3<@DPTR = NO CARRY AND + ;R3>@DPTR CARRY IS SET + INC DPTR ;BUMP THE DATA POINTER + MOVX A,@DPTR ;GET THE BYTE + ACALL DECDP ;PUT DPTR BACK + CJNE A,R1B0,D1 ;DO THE COMPARE + CPL C ;FLIP CARRY + ; + CPL UBIT ;SET IT +D1: CPL C ;GET THE CARRY RIGHT + RET ;EXIT + ; + ;*************************************************************** + ; + ; ADDPTR - Add acc to the dptr + ; + ; acc gets wasted + ; + ;*************************************************************** + ; +ADDPTR: ADD A,DPL ;ADD THE ACC TO DPL + MOV DPL,A ;PUT IT IN DPL + JNC $+4 ;JUMP IF NO CARRY + INC DPH ;BUMP DPH + RET ;EXIT + ; + newpage + ;************************************************************* + ; +LCLR: ; Set up the storage allocation + ; + ;************************************************************* + ; + ACALL ICLR ;CLEAR THE INTERRUPTS + ACALL G4 ;PUT END ADDRESS INTO DPTR + MOV A,#6 ;ADJUST MATRIX SPACE + ACALL ADDPTR ;ADD FOR PROPER BOUNDS + ACALL X31DP ;PUT MATRIX BOUNDS IN R3:R1 + MOV DPTR,#MT_ALL ;SAVE R3:R1 IN MATRIX FREE SPACE + ACALL S31DP ;DPTR POINTS TO MEMTOP + ACALL L31DPI ;LOAD MEMTOP INTO R3:R1 + MOV DPTR,#STR_AL ;GET MEMORY ALLOCATED FOR STRINGS + ACALL LDPTRI + LCALL DUBSUB ;R3:R1 = MEMTOP - STRING ALLOCATION ******AA CALL-->LCALL + MOV DPTR,#VARTOP ;SAVE R3:R1 IN VARTOP + ; + ; FALL THRU TO S31DP2 + ; + ;*************************************************************** + ; + ;S31DP - STORE R3 INTO (DPTR) AND R1 INTO (DPTR+1) + ; + ;ACC GETS CLOBBERED + ; + ;*************************************************************** + ; +S31DP2: ACALL S31DP ;DO IT TWICE + ; +S31DP: MOV A,R3 ;GET R3 INTO ACC + MOVX @DPTR,A ;STORE IT + INC DPTR ;BUMP DPTR + MOV A,R1 ;GET R1 + MOVX @DPTR,A ;STORE IT + INC DPTR ;BUMP IT AGAIN TO SAVE PROGRAM SPACE + RET ;GO BACK + ; + ; + ;*************************************************************** + ; +STRING: ; Allocate memory for strings + ; + ;*************************************************************** + ; + LCALL TWO ;R3:R1 = NUMBER, R2:R0 = LEN + MOV DPTR,#STR_AL ;SAVE STRING ALLOCATION + ACALL S31DP + INC R6 ;BUMP + MOV S_LEN,R6 ;SAVE STRING LENGTH + AJMP RCLEAR ;CLEAR AND SET IT UP + ; + newpage + ;*************************************************************** + ; + ; F_VAR - Find the variable in symbol table + ; R7:R6 contain the variable name + ; If not found create a zero entry and set the carry + ; R2:R0 has the address of variable on return + ; + ;*************************************************************** + ; +F_VAR: MOV DPTR,#VARTOP ;PUT VARTOP IN DPTR + ACALL LDPTRI + ACALL DECDP2 ;ADJUST DPTR FOR LOOKUP + ; +F_VAR0: MOVX A,@DPTR ;LOAD THE VARIABLE + JZ F_VAR2 ;TEST IF AT THE END OF THE TABLE + INC DPTR ;BUMP FOR NEXT BYTE + CJNE A,R7B0,F_VAR1 ;SEE IF MATCH + MOVX A,@DPTR ;LOAD THE NAME + CJNE A,R6B0,F_VAR1 + ; + ; Found the variable now adjust and put in R2:R0 + ; +DLD: MOV A,DPL ;R2:R0 = DPTR-2 + SUBB A,#2 + MOV R0,A + MOV A,DPH + SUBB A,#0 ;CARRY IS CLEARED + MOV R2,A + RET + ; +F_VAR1: MOV A,DPL ;SUBTRACT THE STACK SIZE+ADJUST + CLR C + SUBB A,#STESIZ + MOV DPL,A ;RESTORE DPL + JNC F_VAR0 + DEC DPH + SJMP F_VAR0 ;CONTINUE COMPARE + ; + newpage + ; + ; Add the entry to the symbol table + ; +F_VAR2: LCALL R76S ;SAVE R7 AND R6 + CLR C + ACALL DLD ;BUMP THE POINTER TO GET ENTRY ADDRESS + ; + ; Adjust pointer and save storage allocation + ; and make sure we aren't wiping anything out + ; First calculate new storage allocation + ; + MOV A,R0 + SUBB A,#STESIZ-3 ;NEED THIS MUCH RAM + MOV R1,A + MOV A,R2 + SUBB A,#0 + MOV R3,A + ; + ; Now save the new storage allocation + ; + MOV DPTR,#ST_ALL + CALL S31DP ;SAVE STORAGE ALLOCATION + ; + ; Now make sure we didn't blow it, by wiping out MT_ALL + ; + ACALL DCMPX ;COMPARE STORAGE ALLOCATION + JC CCLR3 ;ERROR IF CARRY + SETB C ;DID NOT FIND ENTRY + RET ;EXIT IF TEST IS OK + ; + newpage + ;*************************************************************** + ; + ; Command action routine - NEW + ; + ;*************************************************************** + ; +CNEW: MOV DPTR,#PSTART ;SAVE THE START OF PROGRAM + MOV A,#EOF ;END OF FILE + MOVX @DPTR,A ;PUT IT IN MEMORY + ; + ; falls thru + ; + ;***************************************************************** + ; + ; The statement action routine - CLEAR + ; + ;***************************************************************** + ; + CLR LINEB ;SET UP FOR RUN AND GOTO + ; +RCLEAR: ACALL LCLR ;CLEAR THE INTERRUPTS, SET UP MATRICES + MOV DPTR,#MEMTOP ;PUT MEMTOP IN R3:R1 + ACALL L31DPI + ACALL G4 ;DPTR GETS END ADDRESS + ACALL CL_1 ;CLEAR THE MEMORY + ; +RC1: MOV DPTR,#STACKTP ;POINT AT CONTROL STACK TOP + CLR A ;CONTROL UNDERFLOW + ; +RC2: MOVX @DPTR,A ;SAVE IN MEMORY + MOV CSTKA,#STACKTP + MOV ASTKA,#STACKTP + CLR CONB ;CAN'T CONTINUE + RET + ; + newpage + ;*************************************************************** + ; + ; Loop until the memory is cleared + ; + ;*************************************************************** + ; +CL_1: INC DPTR ;BUMP MEMORY POINTER + CLR A ;CLEAR THE MEMORY + MOVX @DPTR,A ;CLEAR THE RAM + MOVX A,@DPTR ;READ IT + JNZ CCLR3 ;MAKE SURE IT IS CLEARED + MOV A,R3 ;GET POINTER FOR COMPARE + CJNE A,DPH,CL_1 ;SEE TO LOOP + MOV A,R1 ;NOW TEST LOW BYTE + CJNE A,DPL,CL_1 + ; +CL_2: RET + ; +CCLR3: LJMP TB ;ALLOCATED MEMORY DOESN'T EXSIST ******AA JMP-->LJMP + ; + ;************************************************************** + ; +SCLR: ;Entry point for clear return + ; + ;************************************************************** + ; + LCALL DELTST ;TEST FOR A CR ******AA CALL-->LCALL + JNC RCLEAR + LCALL GCI1 ;BUMP THE TEST POINTER ******AA CALL-->LCALL + CJNE A,#'I',RC1 ;SEE IF I, ELSE RESET THE STACK + ; + ;************************************************************** + ; +ICLR: ; Clear interrupts and system garbage + ; + ;************************************************************** + ; + JNB INTBIT,$+5 ;SEE IF BASIC HAS INTERRUPTS + CLR EX1 ;IF SO, CLEAR INTERRUPTS + ANL 34,#00100000B ;SET INTERRUPTS + CONTINUE + RETI + ; + newpage + ;*************************************************************** + ; + ;OUTPUT ROUTINES + ; + ;*************************************************************** + ; +CRLF2: ACALL CRLF ;DO TWO CRLF'S + ; +CRLF: MOV R5,#CR ;LOAD THE CR + ACALL TEROT ;CALL TERMINAL OUT + MOV R5,#LF ;LOAD THE LF + AJMP TEROT ;OUTPUT IT AND RETURN + ; + ;PRINT THE MESSAGE ADDRESSED IN ROM OR RAM BY THE DPTR + ;ENDS WITH THE CHARACTER IN R4 + ;DPTR HAS THE ADDRESS OF THE TERMINATOR + ; +CRP: ACALL CRLF ;DO A CR THEN PRINT ROM + ; +ROM_P: CLR A ;CLEAR A FOR LOOKUP + MOVC A,@A+DPTR ;GET THE CHARACTER + CLR ACC.7 ;CLEAR MS BIT + CJNE A,#'"',$+4 ;EXIT IF TERMINATOR + RET + SETB C0ORX1 + ; +PN1: MOV R5,A ;OUTPUT THE CHARACTER + ACALL TEROT + INC DPTR ;BUMP THE POINTER + SJMP PN0 + ; +UPRNT: ACALL X31DP + ; +PRNTCR: MOV R4,#CR ;OUTPUT UNTIL A CR + ; +PN0: JBC C0ORX1,ROM_P + MOVX A,@DPTR ;GET THE RAM BYTE + JZ $+5 + CJNE A,R4B0,$+4 ;SEE IF THE SAME AS TERMINATOR + RET ;EXIT IF THE SAME + CJNE A,#CR,PN1 ;NEVER PRINT A CR IN THIS ROUTINE + LJMP E1XX ;BAD SYNTAX + ; + newpage + ;*************************************************************** + ; + ; INLINE - Input a line to IBUF, exit when a CR is received + ; + ;*************************************************************** + ; +INL2: CJNE A,#CNTRLD,INL2B ;SEE IF A CONTROL D + ; +INL0: ACALL CRLF ;DO A CR + ; +INLINE: MOV P2,#HI(IBUF) ;IBUF IS IN THE ZERO PAGE + MOV R0,#LO(IBUF) ;POINT AT THE INPUT BUFFER + ; +INL1: ACALL INCHAR ;GET A CHARACTER + MOV R5,A ;SAVE IN R5 FOR OUTPUT + CJNE A,#7FH,INL2 ;SEE IF A DELETE CHARACTER + CJNE R0,#LO(IBUF),INL6 + MOV R5,#BELL ;OUTPUT A BELL + ; +INLX: ACALL TEROT ;OUTPUT CHARACTER + SJMP INL1 ;DO IT AGAIN + ; +INL2B: MOVX @R0,A ;SAVE THE CHARACTER + CJNE A,#CR,$+5 ;IS IT A CR + AJMP CRLF ;OUTPUT A CRLF AND EXIT + CJNE A,#20H,$+3 + JC INLX ;ONLY ECHO CONTROL CHARACTERS + INC R0 ;BUMP THE POINTER + CJNE R0,#IBUF+79,INLX + DEC R0 ;FORCE 79 + SJMP INLX-2 ;OUTPUT A BELL + ; +INL6: DEC R0 ;DEC THE RAM POINTER + MOV R5,#BS ;OUTPUT A BACK SPACE + ACALL TEROT + ACALL STEROT ;OUTPUT A SPACE + MOV R5,#BS ;ANOTHER BACK SPACE + SJMP INLX ;OUTPUT IT + ; +PTIME: DB 128-2 ; PROM PROGRAMMER TIMER + DB 00H + DB 00H + DB 50H + DB 67H + DB 41H + ; + newpage + include bas52.out ; ******AA + ; +BCK: ACALL CSTS ;CHECK STATUS + JNC CI_RET+1 ;EXIT IF NO CHARACTER + ; + newpage + ;*************************************************************** + ; + ;INPUTS A CHARACTER FROM THE SYSTEM CONSOLE. + ; + ;*************************************************************** + ; +INCHAR: JNB BI,$+8 ;CHECK FOR MONITOR (BUBBLE) + LCALL 2060H + SJMP INCH1 + JNB CIUB,$+8 ;CHECK FOR USER + LCALL 4033H + SJMP INCH1 + JNB RI,$ ;WAIT FOR RECEIVER READY. + MOV A,SBUF + CLR RI ;RESET READY + CLR ACC.7 ;NO BIT 7 + ; +INCH1: CJNE A,#13H,$+5 + SETB CNT_S + CJNE A,#11H,$+5 + CLR CNT_S + CJNE A,#CNTRLC,$+7 + JNB NO_C,C_EX ;TRAP NO CONTROL C + RET + ; + CLR JKBIT + CJNE A,#17H,CI_RET ;CONTROL W + SETB JKBIT + ; +CI_RET: SETB C ;CARRY SET IF A CHARACTER + RET ;EXIT + ; + ;************************************************************* + ; + ;RROM - The Statement Action Routine RROM + ; + ;************************************************************* + ; +RROM: SETB INBIT ;SO NO ERRORS + ACALL RO1 ;FIND THE LINE NUMBER + JBC INBIT,CRUN + RET ;EXIT + ; + newpage + ;*************************************************************** + ; +CSTS: ; RETURNS CARRY = 1 IF THERE IS A CHARACTER WAITING FROM + ; THE SYSTEM CONSOLE. IF NO CHARACTER THE READY CHARACTER + ; WILL BE CLEARED + ; + ;*************************************************************** + ; + JNB BI,$+6 ;BUBBLE STATUS + LJMP 2068H + JNB CIUB,$+6 ;SEE IF EXTERNAL CONSOLE + LJMP 4036H + MOV C,RI + RET + ; + MOV DPTR,#WB ;EGO MESSAGE + ACALL ROM_P + ; +C_EX: CLR CNT_S ;NO OUTPUT STOP + LCALL SPRINT+4 ;ASSURE CONSOLE + ACALL CRLF + JBC JKBIT,C_EX-5 + ; + JNB DIRF,SSTOP0 + AJMP C_K ;CLEAR COB AND EXIT + ; +T_CMP: MOV A,TVH ;COMPARE TIMER TO SP_H AND SP_L + MOV R1,TVL + CJNE A,TVH,T_CMP + XCH A,R1 + SUBB A,SP_L + MOV A,R1 + SUBB A,SP_H + RET + ; + ;************************************************************* + ; +BR0: ; Trap the timer interrupt + ; + ;************************************************************* + ; + CALL T_CMP ;COMPARE TIMER + JC BCHR+6 ;EXIT IF TEST FAILS + SETB OTI ;DOING THE TIMER INTERRUPT + CLR OTS ;CLEAR TIMER BIT + MOV C,INPROG ;SAVE IN PROGRESS + MOV ISAV,C + MOV DPTR,#TIV + SJMP BR2 + ; + newpage + ;*************************************************************** + ; + ; The command action routine - RUN + ; + ;*************************************************************** + ; +CRUN: LCALL RCLEAR-2 ;CLEAR THE STORAGE ARRAYS + ACALL SRESTR+2 ;GET THE STARTING ADDRESS + ACALL B_C + JZ CMNDLK ;IF NULL GO TO COMMAND MODE + ; + ACALL T_DP + ACALL B_TXA ;BUMP TO STARTING LINE + ; +CILOOP: ACALL SP0 ;DO A CR AND A LF + CLR DIRF ;NOT IN DIRECT MODE + ; + ;INTERPERTER DRIVER + ; +ILOOP: MOV SP,SPSAV ;RESTORE THE STACK EACH TIME + JB DIRF,$+9 ;NO INTERRUPTS IF IN DIRECT MODE + MOV INTXAH,TXAH ;SAVE THE TEXT POINTER + MOV INTXAL,TXAL + LCALL BCK ;GET CONSOLE STATUS + JB DIRF,I_L ;DIRECT MODE + ANL C,/GTRD ;SEE IF CHARACTER READY + JNC BCHR ;NO CHARACTER = NO CARRY + ; + ; DO TRAP OPERATION + ; + MOV DPTR,#GTB ;SAVE TRAP CHARACTER + MOVX @DPTR,A + SETB GTRD ;SAYS READ A BYTE + ; +BCHR: JB OTI,I_L ;EXIT IF TIMER INTERRUPT IN PROGRESS + JB OTS,BR0 ;TEST TIMER VALUE IF SET + JNB INTPEN,I_L ;SEE IF INTERRUPT PENDING + JB INPROG,I_L ;DON'T DO IT AGAIN IF IN PROGRESS + MOV DPTR,#INTLOC ;POINT AT INTERRUPT LOCATION + ; +BR2: MOV R4,#GTYPE ;SETUP FOR A FORCED GOSUB + ACALL SGS1 ;PUT TXA ON STACK + SETB INPROG ;INTERRUPT IN PROGRESS + ; +ERL4: CALL L20DPI + AJMP D_L1 ;GET THE LINE NUMBER + ; +I_L: ACALL ISTAT ;LOOP + ACALL CLN_UP ;FINISH IT OFF + JNC ILOOP ;LOOP ON THE DRIVER + JNB DIRF,CMNDLK ;CMND1 IF IN RUN MODE + LJMP CMNDR ;DON'T PRINT READY + ; +CMNDLK: LJMP CMND1 ;DONE ******AA JMP-->LJMP + newpage + ;************************************************************** + ; + ; The Statement Action Routine - STOP + ; + ;************************************************************** + ; +SSTOP: ACALL CLN_UP ;FINISH OFF THIS LINE + MOV INTXAH,TXAH ;SAVE TEXT POINTER FOR CONT + MOV INTXAL,TXAL + ; +SSTOP0: SETB CONB ;CONTINUE WILL WORK + MOV DPTR,#STP ;PRINT THE STOP MESSAGE + SETB STOPBIT ;SET FOR ERROR ROUTINE + LJMP ERRS ;JUMP TO ERROR ROUTINE ******AA JMP-->LJMP + ; + newpage + ;************************************************************** + ; + ; ITRAP - Trap special function register operators + ; + ;************************************************************** + ; +ITRAP: CJNE A,#TMR0,$+8 ;TIMER 0 + MOV TH0,R3 + MOV TL0,R1 + RET + ; + CJNE A,#TMR1,$+8 ;TIMER 1 + MOV TH1,R3 + MOV TL1,R1 + RET + ; + CJNE A,#TMR2,$+8 ;TIMER 2 + DB 8BH ;MOV R3 DIRECT OP CODE + DB 0CDH ;T2H LOCATION + DB 89H ;MOV R1 DIRECT OP CODE + DB 0CCH ;T2L LOCATION + RET + ; + CJNE A,#TRC2,$+8 ;RCAP2 TOKEN +RCL: DB 8BH ;MOV R3 DIRECT OP CODE + DB 0CBH ;RCAP2H LOCATION + DB 89H ;MOV R1 DIRECT OP CODE + DB 0CAH ;RCAP2L LOCATION + RET + ; + ACALL R3CK ;MAKE SURE THAT R3 IS ZERO + CJNE A,#TT2C,$+6 + DB 89H ;MOV R1 DIRECT OP CODE + DB 0C8H ;T2CON LOCATION + RET + ; + CJNE A,#T_IE,$+6 ;IE TOKEN + MOV IE,R1 + RET + ; + CJNE A,#T_IP,$+6 ;IP TOKEN + MOV IP,R1 + RET + ; + CJNE A,#TTC,$+6 ;TCON TOKEN + MOV TCON,R1 + RET + ; + CJNE A,#TTM,$+6 ;TMOD TOKEN + MOV TMOD,R1 + RET + ; + CJNE A,#T_P1,T_T2 ;P1 TOKEN + MOV P1,R1 + RET + ; + ;*************************************************************** + ; + ; T_TRAP - Trap special operators + ; + ;*************************************************************** + ; +T_T: MOV TEMP5,A ;SAVE THE TOKEN + ACALL GCI1 ;BUMP POINTER + ACALL SLET2 ;EVALUATE AFTER = + MOV A,TEMP5 ;GET THE TOKEN BACK + CJNE A,#T_XTAL,$+6 + LJMP AXTAL1 ;SET UP CRYSTAL + ; + ACALL IFIXL ;R3:R1 HAS THE TOS + MOV A,TEMP5 ;GET THE TOKEN AGAIN + CJNE A,#T_MTOP,T_T1 ;SEE IF MTOP TOKEN + MOV DPTR,#MEMTOP + CALL S31DP + JMP RCLEAR ;CLEAR THE MEMORY + ; +T_T1: CJNE A,#T_TIME,ITRAP ;SEE IF A TIME TOKEN + MOV C,EA ;SAVE INTERRUPTS + CLR EA ;NO TIMER 0 INTERRUPTS DURING LOAD + MOV TVH,R3 ;SAVE THE TIME + MOV TVL,R1 + MOV EA,C ;RESTORE INTERRUPTS + RET ;EXIT + ; +T_T2: CJNE A,#T_PC,INTERX ;PCON TOKEN + DB 89H ;MOV DIRECT, R1 OP CODE + DB 87H ;ADDRESS OF PCON + RET ;EXIT + ; +T_TRAP: CJNE A,#T_ASC,T_T ;SEE IF ASC TOKEN + ACALL IGC ;EAT IT AND GET THE NEXT CHARACTER + CJNE A,#'$',INTERX ;ERROR IF NOT A STRING + ACALL CSY ;CALCULATE ADDRESS + ACALL X3120 + LCALL TWO_EY ; ******AA CALL-->LCALL + ACALL SPEOP+4 ;EVALUATE AFTER EQUALS + AJMP ISTAX1 ;SAVE THE CHARACTER + ; + newpage + ;************************************************************** + ; + ;INTERPERT THE STATEMENT POINTED TO BY TXAL AND TXAH + ; + ;************************************************************** + ; +ISTAT: ACALL GC ;GET THR FIRST CHARACTER + JNB XBIT,IAT ;TRAP TO EXTERNAL RUN PACKAGE + CJNE A,#20H,$+3 + JNC IAT + LCALL 2070H ;LET THE USER SET UP THE DPTR + ACALL GCI1 + ANL A,#0FH ;STRIP OFF BIAS + SJMP ISTA1 + ; +IAT: CJNE A,#T_XTAL,$+3 + JNC T_TRAP + JNB ACC.7,SLET ;IMPLIED LET IF BIT 7 NOT SET + CJNE A,#T_UOP+12,ISTAX ;DBYTE TOKEN + ACALL SPEOP ;EVALUATE SPECIAL OPERATOR + ACALL R3CK ;CHECK LOCATION + MOV @R1,A ;SAVE IT + RET + ; +ISTAX: CJNE A,#T_UOP+13,ISTAY ;XBYTE TOKEN + ACALL SPEOP + ; +ISTAX1: MOV P2,R3 + MOVX @R1,A + RET + ; +ISTAY: CJNE A,#T_CR+1,$+3 ;TRAP NEW OPERATORS + JC I_S + CJNE A,#0B0H,$+3 ;SEE IF TOO BIG + JNC INTERX + ADD A,#0F9H ;BIAS FOR LOOKUP TABLE + SJMP ISTA0 ;DO THE OPERATION + ; +I_S: CJNE A,#T_LAST,$+3 ;MAKE SURE AN INITIAL RESERVED WORD + JC $+5 ;ERROR IF NOT + ; +INTERX: LJMP E1XX ;SYNTAX ERROR + ; + JNB DIRF,ISTA0 ;EXECUTE ALL STATEMENTS IF IN RUN MODE + CJNE A,#T_DIR,$+3 ;SEE IF ON TOKEN + JC ISTA0 ;OK IF DIRECT + CJNE A,#T_GOSB+1,$+5 ;SEE IF FOR + SJMP ISTA0 ;FOR IS OK + CJNE A,#T_REM+1,$+5 ;NEXT IS OK + SJMP ISTA0 + CJNE A,#T_STOP+6,INTERX ;SO IS REM + ; + newpage +ISTA0: ACALL GCI1 ;ADVANCE THE TEXT POINTER + MOV DPTR,#STATD ;POINT DPTR TO LOOKUP TABLE + CJNE A,#T_GOTO-3,$+5 ;SEE IF LET TOKEN + SJMP ISTAT ;WASTE LET TOKEN + ANL A,#3FH ;STRIP OFF THE GARBAGE + ; +ISTA1: RL A ;ROTATE FOR OFFSET + ADD A,DPL ;BUMP + MOV DPL,A ;SAVE IT + CLR A + MOVC A,@A+DPTR ;GET HIGH BYTE + PUSH ACC ;SAVE IT + INC DPTR + CLR A + MOVC A,@A+DPTR ;GET LOW BYTE + POP DPH + MOV DPL,A + ; +AC1: CLR A + JMP @A+DPTR ;GO DO IT + ; + newpage + ;*************************************************************** + ; + ; The statement action routine - LET + ; + ;*************************************************************** + ; +SLET: ACALL S_C ;CHECK FOR POSSIBLE STRING + JC SLET0 ;NO STRING + CLR LINEB ;USED STRINGS + ; + CALL X31DP ;PUT ADDRESS IN DPTR + MOV R7,#T_EQU ;WASTE = + ACALL EATC + ACALL GC ;GET THE NEXT CHARACTER + CJNE A,#'"',S_3 ;CHECK FOR A " + MOV R7,S_LEN ;GET THE STRING LENGTH + ; +S_0: ACALL GCI1 ;BUMP PAST " + ACALL DELTST ;CHECK FOR DELIMITER + JZ INTERX ;EXIT IF CARRIAGE RETURN + MOVX @DPTR,A ;SAVE THE CHARACTER + CJNE A,#'"',S_1 ;SEE IF DONE + ; +S_E: MOV A,#CR ;PUT A CR IN A + MOVX @DPTR,A ;SAVE CR + AJMP GCI1 + ; +S_3: PUSH DPH + PUSH DPL ;SAVE DESTINATION + ACALL S_C ;CALCULATE SOURCE + JC INTERX ;ERROR IF CARRY + POP R0B0 ;GET DESTINATION BACK + POP R2B0 + ; +SSOOP: MOV R7,S_LEN ;SET UP COUNTER + ; +S_4: LCALL TBYTE ;TRANSFER THE BYTE ******AA CALL-->LCALL + CJNE A,#CR,$+4 ;EXIT IF A CR + RET + DJNZ R7,S_5 ;BUMP COUNTER + MOV A,#CR ;SAVE A CR + MOVX @R0,A + AJMP EIGP ;PRINT EXTRA IGNORED + ; + newpage + ; +S_5: CALL INC3210 ;BUMP POINTERS + SJMP S_4 ;LOOP + ; +S_1: DJNZ R7,$+8 ;SEE IF DONE + ACALL S_E + ACALL EIGP ;PRINT EXTRA IGNORED + AJMP FINDCR ;GO FIND THE END + INC DPTR ;BUMP THE STORE POINTER + SJMP S_0 ;CONTINUE TO LOOP + ; +E3XX: MOV DPTR,#E3X ;BAD ARG ERROR + AJMP EK + ; +SLET0: ACALL SLET1 + AJMP POPAS ;COPY EXPRESSION TO VARIABLE + ; +SLET1: ACALL VAR_ER ;CHECK FOR A"VARIABLE" + ; +SLET2: PUSH R2B0 ;SAVE THE VARIABLE ADDRESS + PUSH R0B0 + MOV R7,#T_EQU ;GET EQUAL TOKEN + ACALL WE + POP R1B0 ;POP VARIABLE TO R3:R1 + POP R3B0 + RET ;EXIT + ; +R3CK: CJNE R3,#00H,E3XX ;CHECK TO SEE IF R3 IS ZERO + RET + ; +SPEOP: ACALL GCI1 ;BUMP TXA + ACALL P_E ;EVALUATE PAREN + ACALL SLET2 ;EVALUATE AFTER = + CALL TWOL ;R7:R6 GETS VALUE, R3:R1 GETS LOCATION + MOV A,R6 ;SAVE THE VALUE + ; + CJNE R7,#00H,E3XX ;R2 MUST BE = 0 + RET + ; + newpage + ;************************************************************** + ; + ; ST_CAL - Calculate string Address + ; + ;************************************************************** + ; +IST_CAL:; + ; + ACALL I_PI ;BUMP TEXT, THEN EVALUATE + ACALL R3CK ;ERROR IF R3 <> 0 + INC R1 ;BUMP FOR OFFSET + MOV A,R1 ;ERROR IF R1 = 255 + JZ E3XX + MOV DPTR,#VARTOP ;GET TOP OF VARIABLE STORAGE + MOV B,S_LEN ;MULTIPLY FOR LOCATION + ACALL VARD ;CALCULATE THE LOCATION + MOV DPTR,#MEMTOP ;SEE IF BLEW IT + CALL FUL1 + MOV DPL,S_LEN ;GET STRING LENGTH, DPH = 00H + DEC DPH ;DPH = 0 + ; +DUBSUB: CLR C + MOV A,R1 + SUBB A,DPL + MOV R1,A + MOV A,R3 + SUBB A,DPH + MOV R3,A + ORL A,R1 + RET + ; + ;*************************************************************** + ; + ;VARD - Calculate the offset base + ; + ;*************************************************************** + ; +VARB: MOV B,#FPSIZ ;SET UP FOR OPERATION + ; +VARD: CALL LDPTRI ;LOAD DPTR + MOV A,R1 ;MULTIPLY BASE + MUL AB + ADD A,DPL + MOV R1,A + MOV A,B + ADDC A,DPH + MOV R3,A + RET + ; + newpage + ;************************************************************* + ; +CSY: ; Calculate a biased string address and put in R3:R1 + ; + ;************************************************************* + ; + ACALL IST_CAL ;CALCULATE IT + PUSH R3B0 ;SAVE IT + PUSH R1B0 + MOV R7,#',' ;WASTE THE COMMA + ACALL EATC + ACALL ONE ;GET THE NEXT EXPRESSION + MOV A,R1 ;CHECK FOR BOUNDS + CJNE A,S_LEN,$+3 + JNC E3XX ;MUST HAVE A CARRY + DEC R1 ;BIAS THE POINTER + POP ACC ;GET VALUE LOW + ADD A,R1 ;ADD IT TO BASE + MOV R1,A ;SAVE IT + POP R3B0 ;GET HIGH ADDRESS + JNC $+3 ;PROPAGATE THE CARRY + INC R3 + AJMP ERPAR ;WASTE THE RIGHT PAREN + ; + newpage + ;*************************************************************** + ; + ; The statement action routine FOR + ; + ;*************************************************************** + ; +SFOR: ACALL SLET1 ;SET UP CONTROL VARIABLE + PUSH R3B0 ;SAVE THE CONTROL VARIABLE LOCATION + PUSH R1B0 + ACALL POPAS ;POP ARG STACK AND COPY CONTROL VAR + MOV R7,#T_TO ;GET TO TOKEN + ACALL WE + ACALL GC ;GET NEXT CHARACTER + CJNE A,#T_STEP,SF2 + ACALL GCI1 ;EAT THE TOKEN + ACALL EXPRB ;EVALUATE EXPRESSION + SJMP $+5 ;JUMP OVER + ; +SF2: LCALL PUSH_ONE ;PUT ONE ON THE STACK + ; + MOV A,#-FSIZE ;ALLOCATE FSIZE BYTES ON THE CONTROL STACK + ACALL PUSHCS ;GET CS IN R0 + ACALL CSC ;CHECK CONTROL STACK + MOV R3,#CSTKAH ;IN CONTROL STACK + MOV R1,R0B0 ;STACK ADDRESS + ACALL POPAS ;PUT STEP ON STACK + ACALL POPAS ;PUT LIMIT ON STACK + ACALL DP_T ;DPTR GETS TEXT + MOV R0,R1B0 ;GET THE POINTER + ACALL T_X_S ;SAVE THE TEXT + POP TXAL ;GET CONTROL VARIABLE + POP TXAH + MOV R4,#FTYPE ;AND THE TYPE + ACALL T_X_S ;SAVE IT + ; +SF3: ACALL T_DP ;GET THE TEXT POINTER + AJMP ILOOP ;CONTINUE TO PROCESS + ; + newpage + ;************************************************************** + ; + ; The statement action routines - PUSH and POP + ; + ;************************************************************** + ; +SPUSH: ACALL EXPRB ;PUT EXPRESSION ON STACK + ACALL C_TST ;SEE IF MORE TO DO + JNC SPUSH ;IF A COMMA PUSH ANOTHER + RET + ; + ; +SPOP: ACALL VAR_ER ;GET VARIABLE + ACALL XPOP ;FLIP THE REGISTERS FOR POPAS + ACALL C_TST ;SEE IF MORE TO DO + JNC SPOP + ; + RET + ; + ;*************************************************************** + ; + ; The statement action routine - IF + ; + ;*************************************************************** + ; +SIF: ACALL RTST ;EVALUATE THE EXPRESSION + MOV R1,A ;SAVE THE RESULT + ACALL GC ;GET THE CHARACTER AFTER EXPR + CJNE A,#T_THEN,$+5 ;SEE IF THEN TOKEN + ACALL GCI1 ;WASTE THEN TOKEN + CJNE R1,#0,T_F1 ;CHECK R_OP RESULT + ; +E_FIND: MOV R7,#T_ELSE ;FIND ELSE TOKEN + ACALL FINDC + JZ SIF-1 ;EXIT IF A CR + ACALL GCI1 ;BUMP PAST TOKEN + CJNE A,#T_ELSE,E_FIND;WASTE IF NO ELSE + ; +T_F1: ACALL INTGER ;SEE IF NUMBER + JNC D_L1 ;EXECUTE LINE NUMBER + AJMP ISTAT ;EXECUTE STATEMENT IN NOT + ; +B_C: MOVX A,@DPTR + DEC A + JB ACC.7,FL3-5 + RET + ; + newpage + ;*************************************************************** + ; + ; The statement action routine - GOTO + ; + ;*************************************************************** + ; +SGOTO: ACALL RLINE ;R2:R0 AND DPTR GET INTGER + ; +SGT1: ACALL T_DP ;TEXT POINTER GETS DPTR + ; + JBC RETBIT,SGT2 ;SEE IF RETI EXECUTED + ; + JNB LINEB,$+6 ;SEE IF A LINE WAS EDITED + LCALL RCLEAR-2 ;CLEAR THE MEMORY IF SET + AJMP ILOOP-2 ;CLEAR DIRF AND LOOP + ; +SGT2: JBC OTI,$+8 ;SEE IF TIMER INTERRUPT + ANL 34,#10111101B ;CLEAR INTERRUPTS + AJMP ILOOP ;EXECUTE + MOV C,ISAV + MOV INPROG,C + AJMP ILOOP ;RESTORE INTERRUPTS AND RET + ; + ; + ;************************************************************* + ; +RTST: ; Test for ZERO + ; + ;************************************************************* + ; + ACALL EXPRB ;EVALUATE EXPRESSION + CALL INC_ASTKA ;BUMP ARG STACK + JZ $+4 ;EXIT WITH ZERO OR 0FFH + MOV A,#0FFH + RET + ; + newpage + ; + ;************************************************************** + ; + ; GLN - get the line number in R2:R0, return in DPTR + ; + ;************************************************************** + ; +GLN: ACALL DP_B ;GET THE BEGINNING ADDRESS + ; +FL1: MOVX A,@DPTR ;GET THE LENGTH + MOV R7,A ;SAVE THE LENGTH + DJNZ R7,FL3 ;SEE IF END OF FILE + ; + MOV DPTR,#E10X ;NO LINE NUMBER + AJMP EK ;HANDLE THE ERROR + ; +FL3: JB ACC.7,$-5 ;CHECK FOR BIT 7 + INC DPTR ;POINT AT HIGH BYTE + MOVX A,@DPTR ;GET HIGH BYTE + CJNE A,R2B0,FL2 ;SEE IF MATCH + INC DPTR ;BUMP TO LOW BYTE + DEC R7 ;ADJUST AGAIN + MOVX A,@DPTR ;GET THE LOW BYTE + CJNE A,R0B0,FL2 ;SEE IF LOW BYTE MATCH + INC DPTR ;POINT AT FIRST CHARACTER + RET ;FOUND IT + ; +FL2: MOV A,R7 ;GET THE LENGTH COUNTER + CALL ADDPTR ;ADD A TO DATA POINTER + SJMP FL1 ;LOOP + ; + ; + ;************************************************************* + ; + ;RLINE - Read in ASCII string, get line, and clean it up + ; + ;************************************************************* + ; +RLINE: ACALL INTERR ;GET THE INTEGER + ; +RL1: ACALL GLN + AJMP CLN_UP + ; + ; +D_L1: ACALL GLN ;GET THE LINE + AJMP SGT1 ;EXECUTE THE LINE + ; + newpage + ;*************************************************************** + ; + ; The statement action routines WHILE and UNTIL + ; + ;*************************************************************** + ; +SWHILE: ACALL RTST ;EVALUATE RELATIONAL EXPRESSION + CPL A + SJMP S_WU + ; +SUNTIL: ACALL RTST ;EVALUATE RELATIONAL EXPRESSION + ; +S_WU: MOV R4,#DTYPE ;DO EXPECTED + MOV R5,A ;SAVE R_OP RESULT + SJMP SR0 ;GO PROCESS + ; + ; + ;*************************************************************** + ; +CNULL: ; The Command Action Routine - NULL + ; + ;*************************************************************** + ; + ACALL INTERR ;GET AN INTEGER FOLLOWING NULL + MOV NULLCT,R0 ;SAVE THE NULLCOUNT + AJMP CMNDLK ;JUMP TO COMMAND MODE + ; + newpage + ;*************************************************************** + ; + ; The statement action routine - RETI + ; + ;*************************************************************** + ; +SRETI: SETB RETBIT ;SAYS THAT RETI HAS BEEN EXECUTED + ; + ;*************************************************************** + ; + ; The statement action routine - RETURN + ; + ;*************************************************************** + ; +SRETRN: MOV R4,#GTYPE ;MAKE SURE OF GOSUB + MOV R5,#55H ;TYPE RETURN TYPE + ; +SR0: ACALL CSETUP ;SET UP CONTROL STACK + MOVX A,@R0 ;GET RETURN TEXT ADDRESS + MOV DPH,A + INC R0 + MOVX A,@R0 + MOV DPL,A + INC R0 ;POP CONTROL STACK + MOVX A,@DPTR ;SEE IF GOSUB WAS THE LAST STATEMENT + CJNE A,#EOF,$+5 + AJMP CMNDLK + MOV A,R5 ;GET TYPE + JZ SGT1 ;EXIT IF ZERO + MOV CSTKA,R0 ;POP THE STACK + CPL A ;OPTION TEST, 00H, 55H, 0FFH, NOW 55H + JNZ SGT1 ;MUST BE GOSUB + RET ;NORMAL FALL THRU EXIT FOR NO MATCH + ; + newpage + ;*************************************************************** + ; + ; The statement action routine - GOSUB + ; + ;*************************************************************** + ; +SGOSUB: ACALL RLINE ;NEW TXA IN DPTR + ; +SGS0: MOV R4,#GTYPE + ACALL SGS1 ;SET EVERYTHING UP + AJMP SF3 ;EXIT + ; +SGS1: MOV A,#-3 ;ALLOCATE 3 BYTES ON CONTROL STACK + ACALL PUSHCS + ; +T_X_S: MOV P2,#CSTKAH ;SET UP PORT FOR CONTROL STACK + MOV A,TXAL ;GET RETURN ADDRESS AND SAVE IT + MOVX @R0,A + DEC R0 + MOV A,TXAH + MOVX @R0,A + DEC R0 + MOV A,R4 ;GET TYPE + MOVX @R0,A ;SAVE TYPE + RET ;EXIT + ; + ; +CS1: MOV A,#3 ;POP 3 BYTES + ACALL PUSHCS + ; +CSETUP: MOV R0,CSTKA ;GET CONTROL STACK + MOV P2,#CSTKAH + MOVX A,@R0 ;GET BYTE + CJNE A,R4B0,$+5 ;SEE IF TYPE MATCH + INC R0 + RET + JZ E4XX ;EXIT IF STACK UNDERFLOW + CJNE A,#FTYPE,CS1 ;SEE IF FOR TYPE + ACALL PUSHCS-2 ;WASTE THE FOR TYPE + SJMP CSETUP ;LOOP + ; + newpage + ;*************************************************************** + ; + ; The statement action routine - NEXT + ; + ;*************************************************************** + ; +SNEXT: MOV R4,#FTYPE ;FOR TYPE + ACALL CSETUP ;SETUP CONTROL STACK + MOV TEMP5,R0 ;SAVE CONTROL VARIABLE ADDRESS + MOV R1,#TEMP1 ;SAVE VAR + RETURN IN TEMP1-4 + ; +XXI: MOVX A,@R0 ;LOOP UNTIL DONE + MOV @R1,A + INC R1 + INC R0 + CJNE R1,#TEMP5,XXI + ; + ACALL VAR ;SEE IF THE USER HAS A VARIABLE + JNC $+6 + MOV R2,TEMP1 + MOV R0,TEMP2 + MOV A,R2 ;SEE IF VAR'S AGREE + CJNE A,TEMP1,E4XX + MOV A,R0 + CJNE A,TEMP2,E4XX + ACALL PUSHAS ;PUT CONTROL VARIABLE ON STACK + MOV A,#FPSIZ+FPSIZ+2;COMPUTE ADDRESS TO STEP VALUE SIGN + ADD A,TEMP5 ;ADD IT TO BASE OF STACK + MOV R0,A ;SAVE IN R0 + MOV R2,#CSTKAH ;SET UP TO PUSH STEP VALUE + MOV P2,R2 ;SET UP PORT + MOVX A,@R0 ;GET SIGN + INC R0 ;BACK TO EXPONENT + PUSH ACC ;SAVE SIGN OF STEP + ACALL PUSHAS ;PUT STEP VALUE ON STACK + PUSH R0B0 ;SAVE LIMIT VALUE LOCATION + CALL AADD ;ADD STEP VALUE TO VARIABLE + CALL CSTAKA ;COPY STACK + MOV R3,TEMP1 ;GET CONTROL VARIABLE + MOV R1,TEMP2 + ACALL POPAS ;SAVE THE RESULT + MOV R2,#CSTKAH ;RESTORE LIMIT LOCATION + POP R0B0 + ACALL PUSHAS ;PUT LIMIT ON STACK + CALL FP_BASE+4 ;DO THE COMPARE + POP ACC ;GET LIMIT SIGN BACK + JZ $+3 ;IF SIGN NEGATIVE, TEST "BACKWARDS" + CPL C + ORL C,F0 ;SEE IF EQUAL + JC N4 ;STILL SMALLER THAN LIMIT? + MOV A,#FSIZE ;REMOVE CONTROL STACK ENTRY + ; + ; Fall thru to PUSHCS + ; + newpage + ;*************************************************************** + ; + ; PUSHCS - push frame onto control stack + ; acc has - number of bytes, also test for overflow + ; + ;*************************************************************** + ; +PUSHCS: ADD A,CSTKA ;BUMP CONTROL STACK + CJNE A,#CONVT+17,$+3 ;SEE IF OVERFLOWED + JC E4XX ;EXIT IF STACK OVERFLOW + XCH A,CSTKA ;STORE NEW CONTROL STACK VALUE, GET OLD + DEC A ;BUMP OLD VALUE + MOV R0,A ;PUT OLD-1 IN R0 + ; + RET ;EXIT + ; +CSC: ACALL CLN_UP ;FINISH OFF THE LINE + JNC CSC-1 ;EXIT IF NO TERMINATOR + ; +E4XX: MOV DPTR,#EXC ;CONTROL STACK ERROR + AJMP EK ;STACK ERROR + ; +N4: MOV TXAH,TEMP3 ;GET TEXT POINTER + MOV TXAL,TEMP4 + AJMP ILOOP ;EXIT + ; + ;*************************************************************** + ; + ; The statement action routine - RESTORE + ; + ;*************************************************************** + ; +SRESTR: ACALL X_TR ;SWAP POINTERS + ACALL DP_B ;GET THE STARTING ADDRESS + ACALL T_DP ;PUT STARTING ADDRESS IN TEXT POINTER + ACALL B_TXA ;BUMP TXA + ; + ; Fall thru + ; +X_TR: ;swap txa and rtxa + ; + XCH A,TXAH + XCH A,RTXAH + XCH A,TXAH + XCH A,TXAL + XCH A,RTXAL + XCH A,TXAL + RET ;EXIT + ; + newpage + ;*************************************************************** + ; + ; The statement action routine - READ + ; + ;*************************************************************** + ; +SREAD: ACALL X_TR ;SWAP POINTERS + ; +SRD0: ACALL C_TST ;CHECK FOR COMMA + JC SRD4 ;SEE WHAT IT IS + ; +SRD: ACALL EXPRB ;EVALUATE THE EXPRESSION + ACALL GC ;GET THE CHARACTER AFTER EXPRESSION + CJNE A,#',',SRD1 ;SEE IF MORE DATA + SJMP SRD2 ;BYBASS CLEAN UP IF A COMMA + ; +SRD1: ACALL CLN_UP ;FINISH OFF THE LINE, IF AT END + ; +SRD2: ACALL X_TR ;RESTORE POINTERS + ACALL VAR_ER ;GET VARIABLE ADDRESS + ACALL XPOP ;FLIP THE REGISTERS FOR POPAS + ACALL C_TST ;SEE IF A COMMA + JNC SREAD ;READ AGAIN IF A COMMA + RET ;EXIT IF NOT + ; +SRD4: CJNE A,#T_DATA,SRD5 ;SEE IF DATA + ACALL GCI1 ;BUMP POINTER + SJMP SRD + ; +SRD5: CJNE A,#EOF,SRD6 ;SEE IF YOU BLEW IT + ACALL X_TR ;GET THE TEXT POINTER BACK + MOV DPTR,#E14X ;READ ERROR + ; +EK: LJMP ERROR + ; +SRD6: ACALL FINDCR ;WASTE THIS LINE + ACALL CLN_UP ;CLEAN IT UP + JC SRD5+3 ;ERROR IF AT END + SJMP SRD0 + ; +NUMC: ACALL GC ;GET A CHARACTER + CJNE A,#'#',NUMC1 ;SEE IF A # + SETB COB ;VALID LINE PRINT + AJMP IGC ;BUMP THE TEXT POINTER + ; +NUMC1: CJNE A,#'@',SRD4-1 ;EXIT IF NO GOOD + SETB LPB + AJMP IGC + ; + newpage + ;*************************************************************** + ; + ; The statement action routine - PRINT + ; + ;*************************************************************** + ; +SPH0: SETB ZSURP ;NO ZEROS + ; +SPH1: SETB HMODE ;HEX MODE + ; +SPRINT: ACALL NUMC ;TEST FOR A LINE PRINT + ACALL $+9 ;PROCEED + ANL 35,#11110101B ;CLEAR COB AND LPB + ANL 38,#00111111B ;NO HEX MODE + ; + RET + ; + ACALL DELTST ;CHECK FOR A DELIMITER + JC SP1 + ; +SP0: JMP CRLF ;EXIT WITH A CR IF SO + ; +SP2: ACALL C_TST ;CHECK FOR A COMMA + JC SP0 ;EXIT IF NO COMMA + ; +SP1: ACALL CPS ;SEE IF A STRING TO PRINT + JNC SP2 ;IF A STRING, CHECK FOR A COMMA + ; +SP4: CJNE A,#T_TAB,SP6 + ACALL I_PI ;ALWAYS CLEARS CARRY + SUBB A,PHEAD ;TAKE DELTA BETWEEN TAB AND PHEAD + JC SP2 ;EXIT IF PHEAD > TAB + SJMP SP7 ;OUTPUT SPACES + ; +SP6: CJNE A,#T_SPC,SM + ACALL I_PI ;SET UP PAREN VALUE + ; +SP7: JZ SP2 + LCALL STEROT ;OUTPUT A SPACE + DEC A ;DECREMENT COUNTER + SJMP SP7 ;LOOP + ; + newpage +SM: CJNE A,#T_CHR,SP8 + ACALL IGC + CJNE A,#'$',$+9 + ACALL CNX ;PUT THE CHARACTER ON THE STACK + ACALL IFIXL ;PUT THE CHARACTER IN R1 + SJMP $+6 + ACALL ONE ;EVALUATE THE EXPRESSION, PUT IN R3:R1 + ACALL ERPAR + MOV R5,R1B0 ;BYTE TO OUTPUT + SJMP SQ + ; +SP8: CJNE A,#T_CR,SX + ACALL GCI1 ;EAT THE TOKEN + MOV R5,#CR + ; +SQ: CALL TEROT + SJMP SP2 ;OUTPUT A CR AND DO IT AGAIN + ; +SX: CJNE A,#T_USE,SP9 ;USING TOKEN + ACALL IGC ;GE THE CHARACTER AFTER THE USING TOKEN + CJNE A,#'F',U4 ;SEE IF FLOATING + MOV FORMAT,#0F0H ;SET FLOATING + ACALL IGC ;BUMP THE POINTER AND GET THE CHARACTER + ACALL GCI1 ;BUMP IT AGAIN + ANL A,#0FH ;STRIP OFF ASCII BIAS + JZ U3 ;EXIT IF ZERO + CJNE A,#3,$+3 ;SEE IF AT LEAST A THREE + JNC U3 ;FORCE A THREE IF NOT A THREE + MOV A,#3 + ; +U3: ORL FORMAT,A ;PUT DIGIT IN FORMAT + SJMP U8 ;CLEAN UP END + ; +U4: CJNE A,#'0',U5 + MOV FORMAT,#0 ;FREE FORMAT + ACALL GCI1 ;BUMP THE POINTER + SJMP U8 + ; +U5: CJNE A,#'#',U8 ;SEE IF INTGER FORMAT + ACALL U6 + MOV FORMAT,R7 ;SAVE THE FORMAT + CJNE A,#'.',U8A ;SEE IF TERMINATOR WAS RADIX + ACALL IGC ;BUMP PAST . + ACALL U6 ;LOOP AGAIN + MOV A,R7 ;GET COUNT + ADD A,FORMAT ;SEE IF TOO BIG + ADD A,#0F7H + JNC U5A + ; + newpage +SE0: AJMP INTERX ;ERROR, BAD SYNTAX + ; +U5A: MOV A,R7 ;GET THE COUNT BACK + SWAP A ;ADJUST + ORL FORMAT,A ;GET THE COUNT + ; +U8A: MOV A,FORMAT + ; +U8B: SWAP A ;GET THE FORMAT RIGHT + MOV FORMAT,A + ; +U8: ACALL ERPAR + AJMP SP2 ;DONE + ; +U6: MOV R7,#0 ;SET COUNTER + ; +U7: CJNE A,#'#',SP9A ;EXIT IF NOT A # + INC R7 ;BUMP COUNTER + ACALL IGC ;GET THE NEXT CHARACTER + SJMP U7 ;LOOP + ; +SP9: ACALL DELTST+2 ;CHECK FOR DELIMITER + JNC SP9A ;EXIT IF A DELIMITER + ; + CJNE A,#T_ELSE,SS + ; +SP9A: RET ;EXIT IF ELSE TOKEN + ; + ;************************************************************** + ; + ; P_E - Evaluate an expression in parens ( ) + ; + ;************************************************************** + ; +P_E: MOV R7,#T_LPAR + ACALL WE + ; +ERPAR: MOV R7,#')' ;EAT A RIGHT PAREN + ; +EATC: ACALL GCI ;GET THE CHARACTER + CJNE A,R7B0,SE0 ;ERROR IF NOT THE SAME + RET + ; + newpage + ;*************************************************************** + ; +S_ON: ; ON Statement + ; + ;*************************************************************** + ; + ACALL ONE ;GET THE EXPRESSION + ACALL GCI ;GET THE NEXT CHARACTER + CJNE A,#T_GOTO,C0 + ACALL C1 ;EAT THE COMMAS + AJMP SF3 ;DO GOTO + ; +C0: CJNE A,#T_GOSB,SE0 + ACALL C1 + AJMP SGS0 ;DO GOSUB + ; +C1: CJNE R1,#0,C2 + ACALL INTERR ;GET THE LINE NUMBER + ACALL FINDCR + AJMP RL1 ;FINISH UP THIS LINE + ; +C2: MOV R7,#',' + ACALL FINDC + CJNE A,#',',SE0 ;ERROR IF NOT A COMMA + DEC R1 + ACALL GCI1 ;BUMP PAST COMMA + SJMP C1 + ; + newpage + ; +SS: ACALL S_C ;SEE IF A STRING + JC SA ;NO STRING IF CARRY IS SET + LCALL UPRNT ;PUT POINTER IN DPTR + AJMP SP2 ;SEE IF MORE + ; +SA: ACALL EXPRB ;MUST BE AN EXPRESSION + MOV A,#72 + CJNE A,PHEAD,$+3 ;CHECK PHEAD POSITION + JNC $+4 + ACALL SP0 ;FORCE A CRLF + JNB HMODE,S13 ;HEX MODE? + CALL FCMP ;SEE IF TOS IS < 0FFFH + JC S13 ;EXIT IF GREATER + CALL AABS ;GET THE SIGN + JNZ OOPS ;WASTE IF NEGATIVE + ACALL IFIXL + CALL FP_BASE+22 ;PRINT HEXMODE + AJMP SP2 +OOPS: CALL ANEG ;MAKE IT NEGATIVE + ; +S13: CALL FP_BASE+14 ;DO FP OUTPUT + MOV A,#1 ;OUTPUT A SPACE + AJMP SP7 + ; + newpage + ;*************************************************************** + ; + ; ANU - Get variable name from text - set carry if not found + ; if succeeds returns variable in R7:R6 + ; R6 = 0 if no digit in name + ; + ;*************************************************************** + ; +ANU: ACALL IGC ;INCREMENT AND GET CHARACTER + LCALL 1FEDH ;CHECK FOR DIGIT + JC $+14 ;EXIT IF VALID DIGIT + CJNE A,#'_',$+4 ;SEE IF A _ + RET + ; +AL: CJNE A,#'A',$+3 ;IS IT AN ASCII A? + JC $+6 ;EXIT IF CARRY IS SET + CJNE A,#'Z'+1,$+3 ;IS IT LESS THAN AN ASCII Z + CPL C ;FLIP CARRY + RET + ; + JNB F0,VAR2 + ; +SD0: MOV DPTR,#E6X + AJMP EK + ; +SDIMX: SETB F0 ;SAYS DOING A DIMENSION + SJMP VAR1 + ; +VAR: CLR F0 ;SAYS DOING A VARIABLE + ; +VAR1: ACALL GC ;GET THE CHARACTER + ACALL AL ;CHECK FOR ALPHA + JNC $+6 ;ERROR IF IN DIM + JB F0,SD0 + RET + MOV R7,A ;SAVE ALPHA CHARACTER + CLR A ;ZERO IN CASE OF FAILURE + MOV R5,A ;SAVE IT + ; +VY: MOV R6,A + ACALL ANU ;CHECK FOR ALPHA OR NUMBER + JC VX ;EXIT IF NO ALPHA OR NUM + ; + XCH A,R7 + ADD A,R5 ;NUMBER OF CHARACTERS IN ALPHABET + XCH A,R7 ;PUT IT BACK + MOV R5,#26 ;FOR THE SECOND TIME AROUND + SJMP VY + ; +VX: CLR LINEB ;TELL EDITOR A VARIABLE IS DECLARED + CJNE A,#T_LPAR,V4 ;SEE IF A LEFT PAREN + ; + ORL R6B0,#80H ;SET BIT 7 TO SIGINIFY MATRIX + CALL F_VAR ;FIND THE VARIABLE + PUSH R2B0 ;SAVE THE LOCATION + PUSH R0B0 + JNC SD0-3 ;DEFAULT IF NOT IN TABLE + JB F0,SDI ;NO DEFAULT FOR DIMENSION + MOV R1,#10 + MOV R3,#0 + ACALL D_CHK + ; +VAR2: ACALL PAREN_INT ;EVALUATE INTEGER IN PARENS + CJNE R3,#0,SD0 ;ERROR IF R3<>0 + POP DPL ;GET VAR FOR LOOKUP + POP DPH + MOVX A,@DPTR ;GET DIMENSION + DEC A ;BUMP OFFSET + SUBB A,R1 ;A MUST BE > R1 + JC SD0 + LCALL DECDP2 ;BUMP POINTER TWICE + ACALL VARB ;CALCULATE THE BASE + ; +X3120: XCH A,R1 ;SWAP R2:R0, R3:R1 + XCH A,R0 + XCH A,R1 + XCH A,R3 + XCH A,R2 + XCH A,R3 + RET + ; +V4: JB F0,SD0 ;ERROR IF NO LPAR FOR DIM + LCALL F_VAR ;GET SCALAR VARIABLE + CLR C + RET + ; + newpage + ; +SDI: ACALL PAREN_INT ;EVALUATE PAREN EXPRESSION + CJNE R3,#0,SD0 ;ERROR IF NOT ZERO + POP R0B0 ;SET UP R2:R0 + POP R2B0 + ACALL D_CHK ;DO DIM + ACALL C_TST ;CHECK FOR COMMA + JNC SDIMX ;LOOP IF COMMA + RET ;RETURN IF NO COMMA + ; +D_CHK: INC R1 ;BUMP FOR TABLE LOOKUP + MOV A,R1 + JZ SD0 ;ERROR IF 0FFFFH + MOV R4,A ;SAVE FOR LATER + MOV DPTR,#MT_ALL ;GET MATRIX ALLOCATION + ACALL VARB ;DO THE CALCULATION + MOV R7,DPH ;SAVE MATRIX ALLOCATION + MOV R6,DPL + MOV DPTR,#ST_ALL ;SEE IF TOO MUCH MEMORY TAKEN + CALL FUL1 ;ST_ALL SHOULD BE > R3:R1 + MOV DPTR,#MT_ALL ;SAVE THE NEW MATRIX POINTER + CALL S31DP + MOV DPL,R0 ;GET VARIABLE ADDRESS + MOV DPH,R2 + MOV A,R4 ;DIMENSION SIZE + MOVX @DPTR,A ;SAVE IT + CALL DECDP2 ;SAVE TARGET ADDRESS + ; +R76S: MOV A,R7 + MOVX @DPTR,A + INC DPTR + MOV A,R6 ;ELEMENT SIZE + MOVX @DPTR,A + RET ;R2:R0 STILL HAS SYMBOL TABLE ADDRESS + ; + newpage + ;*************************************************************** + ; + ; The statement action routine - INPUT + ; + ;*************************************************************** + ; +SINPUT: ACALL CPS ;PRINT STRING IF THERE + ; + ACALL C_TST ;CHECK FOR A COMMA + JNC IN2A ;NO CRLF + ACALL SP0 ;DO A CRLF + ; +IN2: MOV R5,#'?' ;OUTPUT A ? + CALL TEROT + ; +IN2A: SETB INP_B ;DOING INPUT + CALL INLINE ;INPUT THE LINE + CLR INP_B + MOV TEMP5,#HI(IBUF) + MOV TEMP4,#LO(IBUF) + ; +IN3: ACALL S_C ;SEE IF A STRING + JC IN3A ;IF CARRY IS SET, NO STRING + ACALL X3120 ;FLIP THE ADDRESSES + MOV R3,TEMP5 + MOV R1,TEMP4 + ACALL SSOOP + ACALL C_TST ;SEE IF MORE TO DO + JNC IN2 + RET + ; +IN3A: CALL DTEMP ;GET THE USER LOCATION + CALL GET_NUM ;GET THE USER SUPPLIED NUMBER + JNZ IN5 ;ERROR IF NOT ZERO + CALL TEMPD ;SAVE THE DATA POINTER + ACALL VAR_ER ;GET THE VARIABLE + ACALL XPOP ;SAVE THE VARIABLE + CALL DTEMP ;GET DPTR BACK FROM VAR_ER + ACALL C_TST ;SEE IF MORE TO DO + JC IN6 ;EXIT IF NO COMMA + MOVX A,@DPTR ;GET INPUT TERMINATOR + CJNE A,#',',IN5 ;IF NOT A COMMA DO A CR AND TRY AGAIN + INC DPTR ;BUMP PAST COMMA AND READ NEXT VALUE + CALL TEMPD + SJMP IN3 + ; + newpage + ; +IN5: MOV DPTR,#IAN ;PRINT INPUT A NUMBER + CALL CRP ;DO A CR, THEN, PRINT FROM ROM + LJMP CC1 ;TRY IT AGAIN + ; +IN6: MOVX A,@DPTR + CJNE A,#CR,EIGP + RET + ; +EIGP: MOV DPTR,#EIG + CALL CRP ;PRINT THE MESSAGE AND EXIT + AJMP SP0 ;EXIT WITH A CRLF + ; + ;*************************************************************** + ; +SOT: ; On timer interrupt + ; + ;*************************************************************** + ; + ACALL TWO ;GET THE NUMBERS + MOV SP_H,R3 + MOV SP_L,R1 + MOV DPTR,#TIV ;SAVE THE NUMBER + SETB OTS + AJMP R76S ;EXIT + ; + ; + ;*************************************************************** + ; +SCALL: ; Call a user rountine + ; + ;*************************************************************** + ; + ACALL INTERR ;CONVERT INTEGER + CJNE R2,#0,S_C_1 ;SEE IF TRAP + MOV A,R0 + JB ACC.7,S_C_1 + ADD A,R0 + MOV DPTR,#4100H + MOV DPL,A + ; +S_C_1: ACALL AC1 ;JUMP TO USER PROGRAM + ANL PSW,#11100111B ;BACK TO BANK 0 + RET ;EXIT + ; + newpage + ;************************************************************** + ; +THREE: ; Save value for timer function + ; + ;************************************************************** + ; + ACALL ONE ;GET THE FIRST INTEGER + CALL CBIAS ;BIAS FOR TIMER LOAD + MOV T_HH,R3 + MOV T_LL,R1 + MOV R7,#',' ;WASTE A COMMA + ACALL EATC ;FALL THRU TO TWO + ; + ;************************************************************** + ; +TWO: ; Get two values seperated by a comma off the stack + ; + ;************************************************************** + ; + ACALL EXPRB + MOV R7,#',' ;WASTE THE COMMA + ACALL WE + JMP TWOL ;EXIT + ; + ;************************************************************* + ; +ONE: ; Evaluate an expression and get an integer + ; + ;************************************************************* + ; + ACALL EXPRB ;EVALUATE EXPERSSION + ; +IFIXL: CALL IFIX ;INTEGERS IN R3:R1 + MOV A,R1 + RET + ; + ; + ;************************************************************* + ; +I_PI: ; Increment text pointer then get an integer + ; + ;************************************************************* + ; + ACALL GCI1 ;BUMP TEXT, THEN GET INTEGER + ; +PAREN_INT:; Get an integer in parens ( ) + ; + ACALL P_E + SJMP IFIXL + ; + newpage + ; +DP_B: MOV DPH,BOFAH + MOV DPL,BOFAL + RET + ; +DP_T: MOV DPH,TXAH + MOV DPL,TXAL + RET + ; +CPS: ACALL GC ;GET THE CHARACTER + CJNE A,#'"',NOPASS ;EXIT IF NO STRING + ACALL DP_T ;GET TEXT POINTER + INC DPTR ;BUMP PAST " + MOV R4,#'"' + CALL PN0 ;DO THE PRINT + INC DPTR ;GO PAST QUOTE + CLR C ;PASSED TEST + ; +T_DP: MOV TXAH,DPH ;TEXT POINTER GETS DPTR + MOV TXAL,DPL + RET + ; + ;************************************************************* + ; +S_C: ; Check for a string + ; + ;************************************************************* + ; + ACALL GC ;GET THE CHARACTER + CJNE A,#'$',NOPASS ;SET CARRY IF NOT A STRING + AJMP IST_CAL ;CLEAR CARRY, CALCULATE OFFSET + ; + ; + ; + ;************************************************************** + ; +C_TST: ACALL GC ;GET A CHARACTER + CJNE A,#',',NOPASS ;SEE IF A COMMA + ; + newpage + ;*************************************************************** + ; + ;GC AND GCI - GET A CHARACTER FROM TEXT (NO BLANKS) + ; PUT CHARACTER IN THE ACC + ; + ;*************************************************************** + ; +IGC: ACALL GCI1 ;BUMP POINTER, THEN GET CHARACTER + ; +GC: SETB RS0 ;USE BANK 1 + MOV P2,R2 ;SET UP PORT 2 + MOVX A,@R0 ;GET EXTERNAL BYTE + CLR RS0 ;BACK TO BANK 0 + RET ;EXIT + ; +GCI: ACALL GC + ; + ; This routine bumps txa by one and always clears the carry + ; +GCI1: SETB RS0 ;BANK 1 + INC R0 ;BUMP TXA + CJNE R0,#0,$+4 + INC R2 + CLR RS0 + RET ;EXIT + ; + newpage + ;************************************************************** + ; + ; Check delimiters + ; + ;************************************************************** + ; +DELTST: ACALL GC ;GET A CHARACTER + CJNE A,#CR,DT1 ;SEE IF A CR + CLR A + RET + ; +DT1: CJNE A,#':',NOPASS ;SET CARRY IF NO MATCH + ; +L_RET: RET + ; + ; + ;*************************************************************** + ; + ; FINDC - Find the character in R7, update TXA + ; + ;*************************************************************** + ; +FINDCR: MOV R7,#CR ;KILL A STATEMENT LINE + ; +FINDC: ACALL DELTST + JNC L_RET + ; + CJNE A,R7B0,FNDCL2 ;MATCH? + RET + ; +FNDCL2: ACALL GCI1 + SJMP FINDC ;LOOP + ; + ACALL GCI1 + ; +WCR: ACALL DELTST ;WASTE UNTIL A "REAL" CR + JNZ WCR-2 + RET + ; + newpage + ;*************************************************************** + ; + ; VAR_ER - Check for a variable, exit if error + ; + ;*************************************************************** + ; +VAR_ER: ACALL VAR + SJMP INTERR+2 + ; + ; + ;*************************************************************** + ; + ; S_D0 - The Statement Action Routine DO + ; + ;*************************************************************** + ; +S_DO: ACALL CSC ;FINISH UP THE LINE + MOV R4,#DTYPE ;TYPE FOR STACK + ACALL SGS1 ;SAVE ON STACK + AJMP ILOOP ;EXIT + ; + newpage + ;*************************************************************** + ; + ; CLN_UP - Clean up the end of a statement, see if at end of + ; file, eat character and line count after CR + ; + ;*************************************************************** + ; +C_2: CJNE A,#':',C_1 ;SEE IF A TERMINATOR + AJMP GCI1 ;BUMP POINTER AND EXIT, IF SO + ; +C_1: CJNE A,#T_ELSE,EP5 + ACALL WCR ;WASTE UNTIL A CR + ; +CLN_UP: ACALL GC ;GET THE CHARACTER + CJNE A,#CR,C_2 ;SEE IF A CR + ACALL IGC ;GET THE NEXT CHARACTER + CJNE A,#EOF,B_TXA ;SEE IF TERMINATOR + ; +NOPASS: SETB C + RET + ; +B_TXA: XCH A,TXAL ;BUMP TXA BY THREE + ADD A,#3 + XCH A,TXAL + JBC CY,$+4 + RET + INC TXAH + RET + ; + newpage + ;*************************************************************** + ; + ; Get an INTEGER from the text + ; sets CARRY if not found + ; returns the INTGER value in DPTR and R2:R0 + ; returns the terminator in ACC + ; + ;*************************************************************** + ; +INTERR: ACALL INTGER ;GET THE INTEGER + JC EP5 ;ERROR IF NOT FOUND + RET ;EXIT IF FOUND + ; +INTGER: ACALL DP_T + CALL FP_BASE+18 ;CONVERT THE INTEGER + ACALL T_DP + MOV DPH,R2 ;PUT THE RETURNED VALUE IN THE DPTR + MOV DPL,R0 + ; +ITRET: RET ;EXIT + ; + ; +WE: ACALL EATC ;WASTE THE CHARACTER + ; + ; Fall thru to evaluate the expression + ; + newpage + ;*************************************************************** + ; + ; EXPRB - Evaluate an expression + ; + ;*************************************************************** + ; +EXPRB: MOV R2,#LO(OPBOL) ;BASE PRECEDENCE + ; +EP1: PUSH R2B0 ;SAVE OPERATOR PRECEDENCE + CLR ARGF ;RESET STACK DESIGNATOR + ; +EP2: MOV A,SP ;GET THE STACK POINTER + ADD A,#12 ;NEED AT LEAST 12 BYTES + JNC $+5 + LJMP ERROR-3 + MOV A,ASTKA ;GET THE ARG STACK + SUBB A,#LO(TM_TOP+12);NEED 12 BYTES ALSO + JNC $+5 + LJMP E4YY + JB ARGF,EP4 ;MUST BE AN OPERATOR, IF SET + ACALL VAR ;IS THE VALUE A VARIABLE? + JNC EP3 ;PUT VARIABLE ON STACK + ; + ACALL CONST ;IS THE VALUE A NUMERIC CONSTANT? + JNC EP4 ;IF SO, CONTINUE, IF NOT, SEE WHAT + CALL GC ;GET THE CHARACTER + CJNE A,#T_LPAR,EP4 ;SEE IF A LEFT PAREN + MOV A,#(LO(OPBOL+1)) + SJMP XLPAR ;PROCESS THE LEFT PAREN + ; +EP3: ACALL PUSHAS ;SAVE VAR ON STACK + ; +EP4: ACALL GC ;GET THE OPERATOR + ; + CJNE A,#T_LPAR,$+3 ;IS IT AN OPERATOR + JNC XOP ;PROCESS OPERATOR + CJNE A,#T_UOP,$+3 ;IS IT A UNARY OPERATOR + JNC XBILT ;PROCESS UNARY (BUILT IN) OPERATOR + POP R2B0 ;GET BACK PREVIOUS OPERATOR PRECEDENCE + JB ARGF,ITRET ;OK IF ARG FLAG IS SET + ; +EP5: CLR C ;NO RECOVERY + LJMP E1XX+2 + ; + ; Process the operator + ; +XOP: ANL A,#1FH ;STRIP OFF THE TOKE BITS + JB ARGF,XOP1 ;IF ARG FLAG IS SET, PROCESS + CJNE A,#T_SUB-T_LPAR,XOP3 + MOV A,#T_NEG-T_LPAR + ; + newpage +XOP1: ADD A,#LO(OPBOL+1) ;BIAS THE TABLE + MOV R2,A + MOV DPTR,#00H + MOVC A,@A+DPTR ;GET THE CURRENT PRECEDENCE + MOV R4,A + POP ACC ;GET THE PREVIOUS PRECEDENCE + MOV R5,A ;SAVE THE PREVIOUS PRECEDENCE + MOVC A,@A+DPTR ;GET IT + CJNE A,R4B0,$+7 ;SEE WHICH HAS HIGHER PRECEDENCE + CJNE A,#12,ITRET ;SEE IF ANEG + SETB C + JNC ITRET ;PROCESS NON-INCREASING PRECEDENCE + ; + ; Save increasing precedence + ; + PUSH R5B0 ;SAVE OLD PRECEDENCE ADDRESS + PUSH R2B0 ;SAVE NEW PRECEDENCE ADDRESS + ACALL GCI1 ;EAT THE OPERATOR + ACALL EP1 ;EVALUATE REMAINING EXPRESSION + POP ACC + ; + ; R2 has the action address, now setup and perform operation + ; +XOP2: MOV DPTR,#OPTAB + ADD A,#LO(~OPBOL) + CALL ISTA1 ;SET UP TO RETURN TO EP2 + AJMP EP2 ;JUMP TO EVALUATE EXPRESSION + ; + ; Built-in operator processing + ; +XBILT: ACALL GCI1 ;EAT THE TOKEN + ADD A,#LO(50H+LO(UOPBOL)) + JB ARGF,EP5 ;XBILT MUST COME AFTER AN OPERATOR + CJNE A,#STP,$+3 + JNC XOP2 + ; +XLPAR: PUSH ACC ;PUT ADDRESS ON THE STACK + ACALL P_E + SJMP XOP2-2 ;PERFORM OPERATION + ; +XOP3: CJNE A,#T_ADD-T_LPAR,EP5 + ACALL GCI1 + AJMP EP2 ;WASTE + SIGN + ; + newpage +XPOP: ACALL X3120 ;FLIP ARGS THEN POP + ; + ;*************************************************************** + ; + ; POPAS - Pop arg stack and copy variable to R3:R1 + ; + ;*************************************************************** + ; +POPAS: LCALL INC_ASTKA + JMP VARCOP ;COPY THE VARIABLE + ; +AXTAL: MOV R2,#HI(CXTAL) + MOV R0,#LO(CXTAL) + ; + ; fall thru + ; + ;*************************************************************** + ; +PUSHAS: ; Push the Value addressed by R2:R0 onto the arg stack + ; + ;*************************************************************** + ; + CALL DEC_ASTKA + SETB ARGF ;SAYS THAT SOMTHING IS ON THE STACK + LJMP VARCOP + ; + ; + ;*************************************************************** + ; +ST_A: ; Store at expression + ; + ;*************************************************************** + ; + ACALL ONE ;GET THE EXPRESSION + SJMP POPAS ;SAVE IT + ; + ; + ;*************************************************************** + ; +LD_A: ; Load at expression + ; + ;*************************************************************** + ; + ACALL ONE ;GET THE EXPRESSION + ACALL X3120 ;FLIP ARGS + SJMP PUSHAS + ; + newpage + ;*************************************************************** + ; +CONST: ; Get a constant fron the text + ; + ;*************************************************************** + ; + CALL GC ;FIRST SEE IF LITERAL + CJNE A,#T_ASC,C0C ;SEE IF ASCII TOKEN + CALL IGC ;GET THE CHARACTER AFTER TOKEN + CJNE A,#'$',CN0 ;SEE IF A STRING + ; +CNX: CALL CSY ;CALCULATE IT + LJMP AXBYTE+2 ;SAVE IT ON THE STACK ******AA JMP-->LJMP + ; +CN0: LCALL TWO_R2 ;PUT IT ON THE STACK ******AA CALL-->LCALL + CALL GCI1 ;BUMP THE POINTER + LJMP ERPAR ;WASTE THE RIGHT PAREN ******AA JMP-->LJMP + ; + ; +C0C: CALL DP_T ;GET THE TEXT POINTER + CALL GET_NUM ;GET THE NUMBER + CJNE A,#0FFH,C1C ;SEE IF NO NUMBER + SETB C +C2C: RET + ; +C1C: JNZ FPTST + CLR C + SETB ARGF + ; +C3C: JMP T_DP + ; +FPTST: ANL A,#00001011B ;CHECK FOR ERROR + JZ C2C ;EXIT IF ZERO + ; + ; Handle the error condition + ; + MOV DPTR,#E2X ;DIVIDE BY ZERO + JNB ACC.0,$+6 ;UNDERFLOW + MOV DPTR,#E7X + JNB ACC.1,$+6 ;OVERFLOW + MOV DPTR,#E11X + ; +FPTS: JMP ERROR + ; + newpage + ;*************************************************************** + ; + ; The Command action routine - LIST + ; + ;*************************************************************** + ; +CLIST: CALL NUMC ;SEE IF TO LINE PORT + ACALL FSTK ;PUT 0FFFFH ON THE STACK + CALL INTGER ;SEE IF USER SUPPLIES LN + CLR A ;LN = 0 TO START + MOV R3,A + MOV R1,A + JC CL1 ;START FROM ZERO + ; + CALL TEMPD ;SAVE THE START ADDTESS + CALL GCI ;GET THE CHARACTER AFTER LIST + CJNE A,#T_SUB,$+10 ;CHECK FOR TERMINATION ADDRESS '-' + ACALL INC_ASTKA ;WASTE 0FFFFH + LCALL INTERR ;GET TERMINATION ADDRESS + ACALL TWO_EY ;PUT TERMINATION ON THE ARG STACK + MOV R3,TEMP5 ;GET THE START ADDTESS + MOV R1,TEMP4 + ; +CL1: CALL GETLIN ;GET THE LINE NO IN R3:R1 + JZ CL3 ;RET IF AT END + ; +CL2: ACALL C3C ;SAVE THE ADDRESS + INC DPTR ;POINT TO LINE NUMBER + ACALL PMTOP+3 ;PUT LINE NUMBER ON THE STACK + ACALL CMPLK ;COMPARE LN TO END ADDRESS + JC CL3 ;EXIT IF GREATER + CALL BCK ;CHECK FOR A CONTROL C + ACALL DEC_ASTKA ;SAVE THE COMPARE ADDRESS + CALL DP_T ;RESTORE ADDRESS + ACALL UPPL ;UN-PROCESS THE LINE + ACALL C3C ;SAVE THE CR ADDRESS + ACALL CL6 ;PRINT IT + INC DPTR ;BUMP POINTER TO NEXT LINE + MOVX A,@DPTR ;GET LIN LENGTH + DJNZ ACC,CL2 ;LOOP + ACALL INC_ASTKA ;WASTE THE COMPARE BYTE + ; +CL3: AJMP CMND1 ;BACK TO COMMAND PROCESSOR + ; +CL6: MOV DPTR,#IBUF ;PRINT IBUF + CALL PRNTCR ;PRINT IT + CALL DP_T + ; +CL7: JMP CRLF + ; + LCALL X31DP + newpage + ;*************************************************************** + ; + ;UPPL - UN PREPROCESS A LINE ADDRESSED BY DPTR INTO IBUF + ; RETURN SOURCE ADDRESS OF CR IN DPTR ON RETURN + ; + ;*************************************************************** + ; +UPPL: MOV R3,#HI(IBUF) ;POINT R3 AT HIGH IBUF + MOV R1,#LO(IBUF) ;POINT R1 AT IBUF + INC DPTR ;SKIP OVER LINE LENGTH + ACALL C3C ;SAVE THE DPTR (DP_T) + CALL L20DPI ;PUT LINE NUMBER IN R2:R0 + CALL FP_BASE+16 ;CONVERT R2:R0 TO INTEGER + CALL DP_T + INC DPTR ;BUMP DPTR PAST THE LINE NUMBER + ; +UPP0: CJNE R1,#LO(IBUF+6),$+3 + JC UPP1A-4 ;PUT SPACES IN TEXT + INC DPTR ;BUMP PAST LN HIGH + MOVX A,@DPTR ;GET USER TEXT + MOV R6,A ;SAVE A IN R6 FOR TOKE COMPARE + JB ACC.7,UPP1 ;IF TOKEN, PROCESS + CJNE A,#20H,$+3 ;TRAP THE USER TOKENS + JNC $+5 + CJNE A,#CR,UPP1 ;DO IT IF NOT A CR + CJNE A,#'"',UPP9 ;SEE IF STRING + ACALL UPP7 ;SAVE IT + ACALL UPP8 ;GET THE NEXT CHARACTER AND SAVE IT + CJNE A,#'"',$-2 ;LOOP ON QUOTES + SJMP UPP0 + ; +UPP9: CJNE A,#':',UPP1A ;PUT A SPACE IN DELIMITER + ACALL UPP7A + MOV A,R6 + ACALL UPP7 + ACALL UPP7A + SJMP UPP0 + ; +UPP1A: ACALL UPP8+2 ;SAVE THE CHARACTER, UPDATE POINTER + SJMP UPP0 ;EXIT IF A CR, ELSE LOOP + ; +UPP1: ACALL C3C ;SAVE THE TEXT POINTER + MOV C,XBIT + MOV F0,C ;SAVE XBIT IN F0 + MOV DPTR,#TOKTAB ;POINT AT TOKEN TABLE + JNB F0,UPP2 + LCALL 2078H ;SET UP DPTR FOR LOOKUP + ; +UPP2: CLR A ;ZERO A FOR LOOKUP + MOVC A,@A+DPTR ;GET TOKEN + INC DPTR ;ADVANCE THE TOKEN POINTER + CJNE A,#0FFH,UP_2 ;SEE IF DONE + JBC F0,UPP2-9 ;NOW DO NORMAL TABLE + AJMP CMND1 ;EXIT IF NOT FOUND + ; +UP_2: CJNE A,R6B0,UPP2 ;LOOP UNTIL THE SAME + ; +UP_3: CJNE A,#T_UOP,$+3 + JNC UPP3 + ACALL UPP7A ;PRINT THE SPACE IF OK + ; +UPP3: CLR A ;DO LOOKUP + MOVC A,@A+DPTR + JB ACC.7,UPP4 ;EXIT IF DONE, ELSE SAVE + JZ UPP4 ;DONE IF ZERO + ACALL UPP7 ;SAVE THE CHARACTER + INC DPTR + SJMP UPP3 ;LOOP + ; +UPP4: CALL DP_T ;GET IT BACK + MOV A,R6 ;SEE IF A REM TOKEN + XRL A,#T_REM + JNZ $+6 + ACALL UPP8 + SJMP $-2 + JNC UPP0 ;START OVER AGAIN IF NO TOKEN + ACALL UPP7A ;PRINT THE SPACE IF OK + SJMP UPP0 ;DONE + ; +UPP7A: MOV A,#' ' ;OUTPUT A SPACE + ; +UPP7: AJMP PPL9+1 ;SAVE A + ; +UPP8: INC DPTR + MOVX A,@DPTR + CJNE A,#CR,UPP7 + AJMP PPL7+1 + ; + newpage + ;************************************************************** + ; + ; This table contains all of the floating point constants + ; + ; The constants in ROM are stored "backwards" from the way + ; basic normally treats floating point numbers. Instead of + ; loading from the exponent and decrementing the pointer, + ; ROM constants pointers load from the most significant + ; digits and increment the pointers. This is done to 1) make + ; arg stack loading faster and 2) compensate for the fact that + ; no decrement data pointer instruction exsist. + ; + ; The numbers are stored as follows: + ; + ; BYTE X+5 = MOST SIGNIFICANT DIGITS IN BCD + ; BYTE X+4 = NEXT MOST SIGNIFICANT DIGITS IN BCD + ; BYTE X+3 = NEXT LEAST SIGNIFICANT DIGITS IN BCD + ; BYTE X+2 = LEAST SIGNIFICANT DIGITS IN BCD + ; BYTE X+1 = SIGN OF THE ABOVE MANTISSA 0 = +, 1 = - + ; BYTE X = EXPONENT IN TWO'S COMPLEMENT BINARY + ; ZERO EXPONENT = THE NUMBER ZERO + ; + ;************************************************************** + ; +ATTAB: DB 128-2 ; ARCTAN LOOKUP + DB 00H + DB 57H + DB 22H + DB 66H + DB 28H + ; + DB 128-1 + DB 01H + DB 37H + DB 57H + DB 16H + DB 16H + ; + DB 128-1 + DB 00H + DB 14H + DB 96H + DB 90H + DB 42H + ; + DB 128-1 + DB 01H + DB 40H + DB 96H + DB 28H + DB 75H + ; + DB 128 + DB 00H + DB 64H + DB 62H + DB 65H + DB 10H + ; + DB 128 + DB 01H + DB 99H + DB 88H + DB 20H + DB 14H + ; + DB 128 + DB 00H + DB 51H + DB 35H + DB 99H + DB 19H + ; + DB 128 + DB 01H + DB 45H + DB 31H + DB 33H + DB 33H + ; + DB 129 + DB 00H + DB 00H + DB 00H + DB 00H + DB 10H + ; + DB 0FFH ;END OF TABLE + ; +NTWO: DB 129 + DB 0 + DB 0 + DB 0 + DB 0 + DB 20H + ; +TTIME: DB 128-4 ; CLOCK CALCULATION + DB 00H + DB 00H + DB 00H + DB 04H + DB 13H + ; + newpage + ;*************************************************************** + ; + ; COSINE - Add pi/2 to stack, then fall thru to SIN + ; + ;*************************************************************** + ; +ACOS: ACALL POTWO ;PUT PI/2 ON THE STACK + ACALL AADD ;TOS = TOS+PI/2 + ; + ;*************************************************************** + ; + ; SINE - use taylor series to calculate sin function + ; + ;*************************************************************** + ; +ASIN: ACALL PIPI ;PUT PI ON THE STACK + ACALL RV ;REDUCE THE VALUE + MOV A,MT2 ;CALCULATE THE SIGN + ANL A,#01H ;SAVE LSB + XRL MT1,A ;SAVE SIGN IN MT1 + ACALL CSTAKA ;NOW CONVERT TO ONE QUADRANT + ACALL POTWO + ACALL CMPLK ;DO COMPARE + JC $+6 + ACALL PIPI + ACALL ASUB + ACALL AABS + MOV DPTR,#SINTAB ;SET UP LOOKUP TABLE + ACALL POLYC ;CALCULATE THE POLY + ACALL STRIP + AJMP SIN0 + ; + ; Put PI/2 on the stack + ; +POTWO: ACALL PIPI ;PUT PI ON THE STACK, NOW DIVIDE + ; +DBTWO: MOV DPTR,#NTWO + ACALL PUSHC + ;MOV A,#2 ;BY TWO + ;ACALL TWO_R2 + AJMP ADIV + ; + newpage + ;************************************************************* + ; +POLYC: ; Expand a power series to calculate a polynomial + ; + ;************************************************************* + ; + ACALL CSTAKA2 ;COPY THE STACK + ACALL AMUL ;SQUARE THE STACK + ACALL POP_T1 ;SAVE X*X + ACALL PUSHC ;PUT CONSTANT ON STACK + ; +POLY1: ACALL PUSH_T1 ;PUT COMPUTED VALUE ON STACK + ACALL AMUL ;MULTIPLY CONSTANT AND COMPUTED VALUE + ACALL PUSHC ;PUT NEXT CONSTANT ON STACK + ACALL AADD ;ADD IT TO THE OLD VALUE + CLR A ;CHECK TO SEE IF DONE + MOVC A,@A+DPTR + CJNE A,#0FFH,POLY1 ;LOOP UNTIL DONE + ; +AMUL: LCALL FP_BASE+6 + AJMP FPTST + ; + ;************************************************************* + ; +RV: ; Reduce a value for Trig and A**X functions + ; + ; value = (value/x - INT(value/x)) * x + ; + ;************************************************************* + ; + ACALL C_T2 ;COPY TOS TO T2 + ACALL ADIV ;TOS = TOS/TEMP2 + ACALL AABS ;MAKE THE TOS A POSITIVE NUMBER + MOV MT1,A ;SAVE THE SIGN + ACALL CSTAKA2 ;COPY THE STACK TWICE + ACALL IFIX ;PUT THE NUMBER IN R3:R1 + PUSH R3B0 ;SAVE R3 + MOV MT2,R1 ;SAVE THE LS BYTE IN MT2 + ACALL AINT ;MAKE THE TOS AN INTEGER + ACALL ASUB ;TOS = TOS/T2 - INT(TOS/T2) + ACALL P_T2 ;TOS = T2 + ACALL AMUL ;TOS = T2*(TOS/T2 - INT(TOS/T2) + POP R3B0 ;RESTORE R3 + RET ;EXIT + ; + newpage + ;************************************************************** + ; + ; TAN + ; + ;************************************************************** + ; +ATAN: ACALL CSTAKA ;DUPLACATE STACK + ACALL ASIN ;TOS = SIN(X) + ACALL SWAP_ASTKA ;TOS = X + ACALL ACOS ;TOS = COS(X) + AJMP ADIV ;TOS = SIN(X)/COS(X) + ; +STRIP: ACALL SETREG ;SETUP R0 + MOV R3,#1 ;LOOP COUNT + AJMP AI2-1 ;WASTE THE LSB + ; + ;************************************************************ + ; + ; ARC TAN + ; + ;************************************************************ + ; +AATAN: ACALL AABS + MOV MT1,A ;SAVE THE SIGN + ACALL SETREG ;GET THE EXPONENT + ADD A,#7FH ;BIAS THE EXPONENT + MOV UBIT,C ;SAVE CARRY STATUS + JNC $+4 ;SEE IF > 1 + ACALL RECIP ;IF > 1, TAKE RECIP + MOV DPTR,#ATTAB ;SET UP TO CALCULATE THE POLY + ACALL POLYC ;CALCULATE THE POLY + JNB UBIT,SIN0 ;JUMP IF NOT SET + ACALL ANEG ;MAKE X POLY NEGATIVE + ACALL POTWO ;SUBTRACT PI/2 + ACALL AADD + ; +SIN0: MOV A,MT1 ;GET THE SIGN + JZ SRT + AJMP ANEG + ; + newpage + ;************************************************************* + ; + ; FCOMP - COMPARE 0FFFFH TO TOS + ; + ;************************************************************* + ; +FCMP: ACALL CSTAKA ;COPY THE STACK + ACALL FSTK ;MAKE THE TOS = 0FFFFH + ACALL SWAP_ASTKA ;NOW COMPARE IS 0FFFFH - X + ; +CMPLK: JMP FP_BASE+4 ;DO THE COMPARE + ; + ;************************************************************* + ; +DEC_ASTKA: ;Push ARG STACK and check for underflow + ; + ;************************************************************* + ; + MOV A,#-FPSIZ + ADD A,ASTKA + CJNE A,#LO(TM_TOP+6),$+3 + JC E4YY + MOV ASTKA,A + MOV R1,A + MOV R3,#ASTKAH + ; +SRT: RET + ; +E4YY: MOV DPTR,#EXA + AJMP FPTS ;ARG STACK ERROR + ; + ; +AXTAL3: ACALL PUSHC ;PUSH CONSTANT, THEN MULTIPLY + ACALL AMUL + ; + ; Fall thru to IFIX + ; + newpage + ;*************************************************************** + ; +IFIX: ; Convert a floating point number to an integer, put in R3:R1 + ; + ;*************************************************************** + ; + CLR A ;RESET THE START + MOV R3,A + MOV R1,A + MOV R0,ASTKA ;GET THE ARG STACK + MOV P2,#ASTKAH + MOVX A,@R0 ;READ EXPONENT + CLR C + SUBB A,#81H ;BASE EXPONENT + MOV R4,A ;SAVE IT + DEC R0 ;POINT AT SIGN + MOVX A,@R0 ;GET THE SIGN + JNZ SQ_ERR ;ERROR IF NEGATIVE + JC INC_ASTKA ;EXIT IF EXPONENT IS < 81H + INC R4 ;ADJUST LOOP COUNTER + MOV A,R0 ;BUMP THE POINTER REGISTER + SUBB A,#FPSIZ-1 + MOV R0,A + ; +I2: INC R0 ;POINT AT DIGIT + MOVX A,@R0 ;GET DIGIT + SWAP A ;FLIP + CALL FP_BASE+20 ;ACCUMULATE + JC SQ_ERR + DJNZ R4,$+4 + SJMP INC_ASTKA + MOVX A,@R0 ;GET DIGIT + CALL FP_BASE+20 + JC SQ_ERR + DJNZ R4,I2 + ; + newpage + ;************************************************************ + ; +INC_ASTKA: ; Pop the ARG STACK and check for overflow + ; + ;************************************************************ + ; + MOV A,#FPSIZ ;NUMBER TO POP + SJMP SETREG+1 + ; +SETREG: CLR A ;DON'T POP ANYTHING + MOV R0,ASTKA + MOV R2,#ASTKAH + MOV P2,R2 + ADD A,R0 + JC E4YY + MOV ASTKA,A + MOVX A,@R0 +A_D: RET + ; + ;************************************************************ + ; + ; EBIAS - Bias a number for E to the X calculations + ; + ;************************************************************ + ; +EBIAS: ACALL PUSH_ONE + ACALL RV + CJNE R3,#00H,SQ_ERR ;ERROR IF R3 <> 0 + ACALL C_T2 ;TEMP 2 GETS FRACTIONS + ACALL INC_ASTKA + ACALL POP_T1 + ACALL PUSH_ONE + ; +AELP: MOV A,MT2 + JNZ AEL1 + ; + MOV A,MT1 + JZ A_D + MOV DPTR,#FPT2-1 + MOVX @DPTR,A ;MAKE THE FRACTIONS NEGATIVE + ; +RECIP: ACALL PUSH_ONE + ACALL SWAP_ASTKA + AJMP ADIV + ; +AEL1: DEC MT2 + ACALL PUSH_T1 + ACALL AMUL + SJMP AELP + ; +SQ_ERR: LJMP E3XX ;LINK TO BAD ARG + ; + newpage + ;************************************************************ + ; + ; SQUARE ROOT + ; + ;************************************************************ + ; +ASQR: ACALL AABS ;GET THE SIGN + JNZ SQ_ERR ;ERROR IF NEGATIVE + ACALL C_T2 ;COPY VARIABLE TO T2 + ACALL POP_T1 ;SAVE IT IN T1 + MOV R0,#LO(FPT1) + MOVX A,@R0 ;GET EXPONENT + JZ ALN-2 ;EXIT IF ZERO + ADD A,#128 ;BIAS THE EXPONENT + JNC SQR1 ;SEE IF < 80H + RR A + ANL A,#127 + SJMP SQR2 + ; +SQR1: CPL A ;FLIP BITS + INC A + RR A + ANL A,#127 ;STRIP MSB + CPL A + INC A + ; +SQR2: ADD A,#128 ;BIAS EXPONENT + MOVX @R0,A ;SAVE IT + ; + ; NEWGUESS = ( X/OLDGUESS + OLDGUESS) / 2 + ; +SQR4: ACALL P_T2 ;TOS = X + ACALL PUSH_T1 ;PUT NUMBER ON STACK + ACALL ADIV ;TOS = X/GUESS + ACALL PUSH_T1 ;PUT ON AGAIN + ACALL AADD ;TOS = X/GUESS + GUESS + ACALL DBTWO ;TOS = ( X/GUESS + GUESS ) / 2 + ACALL TEMP_COMP ;SEE IF DONE + JNB F0,SQR4 + ; + AJMP PUSH_T1 ;PUT THE ANSWER ON THE STACK + ; + newpage + ;************************************************************* + ; + ; NATURAL LOG + ; + ;************************************************************* + ; +ALN: ACALL AABS ;MAKE SURE THAT NUM IS POSITIVE + JNZ SQ_ERR ;ERROR IF NOT + MOV MT2,A ;CLEAR FOR LOOP + INC R0 ;POINT AT EXPONENT + MOVX A,@R0 ;READ THE EXPONENT + JZ SQ_ERR ;ERROR IF EXPONENT IS ZERO + CJNE A,#81H,$+3 ;SEE IF NUM >= 1 + MOV UBIT,C ;SAVE CARRY STATUS + JC $+4 ;TAKE RECIP IF >= 1 + ACALL RECIP + ; + ; Loop to reduce + ; +ALNL: ACALL CSTAKA ;COPY THE STACK FOR COMPARE + ACALL PUSH_ONE ;COMPARE NUM TO ONE + ACALL CMPLK + JNC ALNO ;EXIT IF DONE + ACALL SETREG ;GET THE EXPONENT + ADD A,#85H ;SEE HOW BIG IT IS + JNC ALN11 ;BUMP BY EXP(11) IF TOO SMALL + ACALL PLNEXP ;PUT EXP(1) ON STACK + MOV A,#1 ;BUMP COUNT + ; +ALNE: ADD A,MT2 + JC SQ_ERR + MOV MT2,A + ACALL AMUL ;BIAS THE NUMBER + SJMP ALNL + ; +ALN11: MOV DPTR,#EXP11 ;PUT EXP(11) ON STACK + ACALL PUSHC + MOV A,#11 + SJMP ALNE + ; + newpage +ALNO: ACALL C_T2 ;PUT NUM IN TEMP 2 + ACALL PUSH_ONE ;TOS = 1 + ACALL ASUB ;TOS = X - 1 + ACALL P_T2 ;TOS = X + ACALL PUSH_ONE ;TOS = 1 + ACALL AADD ;TOS = X + 1 + ACALL ADIV ;TOS = (X-1)/(X+1) + MOV DPTR,#LNTAB ;LOG TABLE + ACALL POLYC + INC DPTR ;POINT AT LN(10) + ACALL PUSHC + ACALL AMUL + MOV A,MT2 ;GET THE COUNT + ACALL TWO_R2 ;PUT IT ON THE STACK + ACALL ASUB ;INT - POLY + ACALL STRIP + JNB UBIT,AABS + ; +LN_D: RET + ; + ;************************************************************* + ; +TEMP_COMP: ; Compare FPTEMP1 to TOS, FPTEMP1 gets TOS + ; + ;************************************************************* + ; + ACALL PUSH_T1 ;SAVE THE TEMP + ACALL SWAP_ASTKA ;TRADE WITH THE NEXT NUMBER + ACALL CSTAKA ;COPY THE STACK + ACALL POP_T1 ;SAVE THE NEW NUMBER + JMP FP_BASE+4 ;DO THE COMPARE + ; + newpage +AETOX: ACALL PLNEXP ;EXP(1) ON TOS + ACALL SWAP_ASTKA ;X ON TOS + ; +AEXP: ;EXPONENTIATION + ; + ACALL EBIAS ;T1=BASE,T2=FRACTIONS,TOS=INT MULTIPLIED + MOV DPTR,#FPT2 ;POINT AT FRACTIONS + MOVX A,@DPTR ;READ THE EXP OF THE FRACTIONS + JZ LN_D ;EXIT IF ZERO + ACALL P_T2 ;TOS = FRACTIONS + ACALL PUSH_T1 ;TOS = BASE + ACALL SETREG ;SEE IF BASE IS ZERO + JZ $+4 + ACALL ALN ;TOS = LN(BASE) + ACALL AMUL ;TOS = FRACTIONS * LN(BASE) + ACALL PLNEXP ;TOS = EXP(1) + ACALL SWAP_ASTKA ;TOS = FRACTIONS * LN(BASE) + ACALL EBIAS ;T2 = FRACTIONS, TOS = INT MULTIPLIED + MOV MT2,#00H ;NOW CALCULATE E**X + ACALL PUSH_ONE + ACALL CSTAKA + ACALL POP_T1 ;T1 = 1 + ; +AEXL: ACALL P_T2 ;TOS = FRACTIONS + ACALL AMUL ;TOS = FRACTIONS * ACCUMLATION + INC MT2 ;DO THE DEMONIATOR + MOV A,MT2 + ACALL TWO_R2 + ACALL ADIV + ACALL CSTAKA ;SAVE THE ITERATION + ACALL PUSH_T1 ;NOW ACCUMLATE + ACALL AADD ;ADD ACCUMLATION + ACALL TEMP_COMP + JNB F0,AEXL ;LOOP UNTIL DONE + ; + ACALL INC_ASTKA + ACALL PUSH_T1 + ACALL AMUL ;LAST INT MULTIPLIED + ; +MU1: AJMP AMUL ;FIRST INT MULTIPLIED + ; + newpage + ;*************************************************************** + ; + ; integer operator - INT + ; + ;*************************************************************** + ; +AINT: ACALL SETREG ;SET UP THE REGISTERS, CLEAR CARRY + SUBB A,#129 ;SUBTRACT EXPONENT BIAS + JNC AI1 ;JUMP IF ACC > 81H + ; + ; Force the number to be a zero + ; + ACALL INC_ASTKA ;BUMP THE STACK + ; +P_Z: MOV DPTR,#ZRO ;PUT ZERO ON THE STACK + AJMP PUSHC + ; +AI1: SUBB A,#7 + JNC AI3 + CPL A + INC A + MOV R3,A + DEC R0 ;POINT AT SIGN + ; +AI2: DEC R0 ;NOW AT LSB'S + MOVX A,@R0 ;READ BYTE + ANL A,#0F0H ;STRIP NIBBLE + MOVX @R0,A ;WRITE BYTE + DJNZ R3,$+3 + RET + CLR A + MOVX @R0,A ;CLEAR THE LOCATION + DJNZ R3,AI2 + ; +AI3: RET ;EXIT + ; + newpage + ;*************************************************************** + ; +AABS: ; Absolute value - Make sign of number positive + ; return sign in ACC + ; + ;*************************************************************** + ; + ACALL ANEG ;CHECK TO SEE IF + OR - + JNZ ALPAR ;EXIT IF NON ZERO, BECAUSE THE NUM IS + MOVX @R0,A ;MAKE A POSITIVE SIGN + RET + ; + ;*************************************************************** + ; +ASGN: ; Returns the sign of the number 1 = +, -1 = - + ; + ;*************************************************************** + ; + ACALL INC_ASTKA ;POP STACK, GET EXPONENT + JZ P_Z ;EXIT IF ZERO + DEC R0 ;BUMP TO SIGN + MOVX A,@R0 ;GET THE SIGN + MOV R7,A ;SAVE THE SIGN + ACALL PUSH_ONE ;PUT A ONE ON THE STACK + MOV A,R7 ;GET THE SIGN + JZ ALPAR ;EXIT IF ZERO + ; + ; Fall thru to ANEG + ; + ;*************************************************************** + ; +ANEG: ; Flip the sign of the number on the tos + ; + ;*************************************************************** + ; + ACALL SETREG + DEC R0 ;POINT AT THE SIGN OF THE NUMBER + JZ ALPAR ;EXIT IF ZERO + MOVX A,@R0 + XRL A,#01H ;FLIP THE SIGN + MOVX @R0,A + XRL A,#01H ;RESTORE THE SIGN + ; +ALPAR: RET + ; + newpage + ;*************************************************************** + ; +ACBYTE: ; Read the ROM + ; + ;*************************************************************** + ; + ACALL IFIX ;GET EXPRESSION + CALL X31DP ;PUT R3:R1 INTO THE DP + CLR A + MOVC A,@A+DPTR + AJMP TWO_R2 + ; + ;*************************************************************** + ; +ADBYTE: ; Read internal memory + ; + ;*************************************************************** + ; + ACALL IFIX ;GET THE EXPRESSION + CALL R3CK ;MAKE SURE R3 = 0 + MOV A,@R1 + AJMP TWO_R2 + ; + ;*************************************************************** + ; +AXBYTE: ; Read external memory + ; + ;*************************************************************** + ; + ACALL IFIX ;GET THE EXPRESSION + MOV P2,R3 + MOVX A,@R1 + AJMP TWO_R2 + ; + newpage + ;*************************************************************** + ; + ; The relational operators - EQUAL (=) + ; GREATER THAN (>) + ; LESS THAN (<) + ; GREATER THAN OR EQUAL (>=) + ; LESS THAN OR EQUAL (<=) + ; NOT EQUAL (<>) + ; + ;*************************************************************** + ; +AGT: ACALL CMPLK + ORL C,F0 ;SEE IF EITHER IS A ONE + JC P_Z + ; +FSTK: MOV DPTR,#FS + AJMP PUSHC + ; +FS: DB 85H + DB 00H + DB 00H + DB 50H + DB 53H + DB 65H + ; +ALT: ACALL CMPLK + CPL C + SJMP AGT+4 + ; +AEQ: ACALL CMPLK + MOV C,F0 + SJMP ALT+2 + ; +ANE: ACALL CMPLK + CPL F0 + SJMP AEQ+2 + ; +AGE: ACALL CMPLK + SJMP AGT+4 + ; +ALE: ACALL CMPLK + ORL C,F0 + SJMP ALT+2 + ; + newpage + ;*************************************************************** + ; +ARND: ; Generate a random number + ; + ;*************************************************************** + ; + MOV DPTR,#RCELL ;GET THE BINARY SEED + CALL L31DPI + MOV A,R1 + CLR C + RRC A + MOV R0,A + MOV A,#6 + RRC A + ADD A,R1 + XCH A,R0 + ADDC A,R3 + MOV R2,A + DEC DPL ;SAVE THE NEW SEED + ACALL S20DP + ACALL TWO_EY + ACALL FSTK + ; +ADIV: LCALL FP_BASE+8 + AJMP FPTST + ; + newpage + ;*************************************************************** + ; +SONERR: ; ON ERROR Statement + ; + ;*************************************************************** + ; + LCALL INTERR ;GET THE LINE NUMBER + SETB ON_ERR + MOV DPTR,#ERRNUM ;POINT AT THR ERROR LOCATION + SJMP S20DP + ; + ; + ;************************************************************** + ; +SONEXT: ; ON EXT1 Statement + ; + ;************************************************************** + ; + LCALL INTERR + SETB INTBIT + ORL IE,#10000100B ;ENABLE INTERRUPTS + MOV DPTR,#INTLOC + ; +S20DP: MOV A,R2 ;SAVE R2:R0 @DPTR + MOVX @DPTR,A + INC DPTR + MOV A,R0 + MOVX @DPTR,A + RET + ; + newpage + ;*************************************************************** + ; + ; CASTAK - Copy and push another top of arg stack + ; + ;*************************************************************** + ; +CSTAKA2:ACALL CSTAKA ;COPY STACK TWICE + ; +CSTAKA: ACALL SETREG ;SET UP R2:R0 + SJMP PUSH_T1+4 + ; +PLNEXP: MOV DPTR,#EXP1 + ; + ;*************************************************************** + ; + ; PUSHC - Push constant on to the arg stack + ; + ;*************************************************************** + ; +PUSHC: ACALL DEC_ASTKA + MOV P2,R3 + MOV R3,#FPSIZ ;LOOP COUNTER + ; +PCL: CLR A ;SET UP A + MOVC A,@A+DPTR ;LOAD IT + MOVX @R1,A ;SAVE IT + INC DPTR ;BUMP POINTERS + DEC R1 + DJNZ R3,PCL ;LOOP + ; + SETB ARGF + RET ;EXIT + ; +PUSH_ONE:; + ; + MOV DPTR,#FPONE + AJMP PUSHC + ; + newpage + ; +POP_T1: + ; + MOV R3,#HI(FPT1) + MOV R1,#LO(FPT1) + JMP POPAS + ; +PUSH_T1: + ; + MOV R0,#LO(FPT1) + MOV R2,#HI(FPT1) + LJMP PUSHAS + ; +P_T2: MOV R0,#LO(FPT2) + SJMP $-7 ;JUMP TO PUSHAS + ; + ;**************************************************************** + ; +SWAP_ASTKA: ; SWAP TOS<>TOS-1 + ; + ;**************************************************************** + ; + ACALL SETREG ;SET UP R2:R0 AND P2 + MOV A,#FPSIZ ;PUT TOS+1 IN R1 + MOV R2,A + ADD A,R0 + MOV R1,A + ; +S_L: MOVX A,@R0 + MOV R3,A + MOVX A,@R1 + MOVX @R0,A + MOV A,R3 + MOVX @R1,A + DEC R1 + DEC R0 + DJNZ R2,S_L + RET + ; + newpage + ; +C_T2: ACALL SETREG ;SET UP R2:R0 + MOV R3,#HI(FPT2) + MOV R1,#LO(FPT2) ;TEMP VALUE + ; + ; Fall thru + ; + ;*************************************************************** + ; + ; VARCOP - Copy a variable from R2:R0 to R3:R1 + ; + ;*************************************************************** + ; +VARCOP: MOV R4,#FPSIZ ;LOAD THE LOOP COUNTER + ; +V_C: MOV P2,R2 ;SET UP THE PORTS + MOVX A,@R0 ;READ THE VALUE + MOV P2,R3 ;PORT TIME AGAIN + MOVX @R1,A ;SAVE IT + ACALL DEC3210 ;BUMP POINTERS + DJNZ R4,V_C ;LOOP + RET ;EXIT + ; +PIPI: MOV DPTR,#PIE + AJMP PUSHC + ; + newpage + ;*************************************************************** + ; + ; The logical operators ANL, ORL, XRL, NOT + ; + ;*************************************************************** + ; +AANL: ACALL TWOL ;GET THE EXPRESSIONS + MOV A,R3 ;DO THE AND + ANL A,R7 + MOV R2,A + MOV A,R1 + ANL A,R6 + SJMP TWO_EX + ; +AORL: ACALL TWOL ;SAME THING FOR OR + MOV A,R3 + ORL A,R7 + MOV R2,A + MOV A,R1 + ORL A,R6 + SJMP TWO_EX + ; +ANOT: ACALL FSTK ;PUT 0FFFFH ON THE STACK + ; +AXRL: ACALL TWOL + MOV A,R3 + XRL A,R7 + MOV R2,A + MOV A,R1 + XRL A,R6 + SJMP TWO_EX + ; +TWOL: ACALL IFIX + MOV R7,R3B0 + MOV R6,R1B0 + AJMP IFIX + ; + newpage + ;************************************************************* + ; +AGET: ; READ THE BREAK BYTE AND PUT IT ON THE ARG STACK + ; + ;************************************************************* + ; + MOV DPTR,#GTB ;GET THE BREAK BYTE + MOVX A,@DPTR + JBC GTRD,TWO_R2 + CLR A + ; +TWO_R2: MOV R2,#00H ;ACC GOES TO STACK + ; + ; +TWO_EX: MOV R0,A ;R2:ACC GOES TO STACK + ; + ; +TWO_EY: SETB ARGF ;R2:R0 GETS PUT ON THE STACK + JMP FP_BASE+24 ;DO IT + ; + newpage + ;************************************************************* + ; + ; Put directs onto the stack + ; + ;************************************************************** + ; +A_IE: MOV A,IE ;IE + SJMP TWO_R2 + ; +A_IP: MOV A,IP ;IP + SJMP TWO_R2 + ; +ATIM0: MOV R2,TH0 ;TIMER 0 + MOV R0,TL0 + SJMP TWO_EY + ; +ATIM1: MOV R2,TH1 ;TIMER 1 + MOV R0,TL1 + SJMP TWO_EY + ; +ATIM2: DB 0AAH ;MOV R2 DIRECT OP CODE + DB 0CDH ;T2 HIGH + DB 0A8H ;MOV R0 DIRECT OP CODE + DB 0CCH ;T2 LOW + SJMP TWO_EY ;TIMER 2 + ; +AT2CON: DB 0E5H ;MOV A,DIRECT OPCODE + DB 0C8H ;T2CON LOCATION + SJMP TWO_R2 + ; +ATCON: MOV A,TCON ;TCON + SJMP TWO_R2 + ; +ATMOD: MOV A,TMOD ;TMOD + SJMP TWO_R2 + ; +ARCAP2: DB 0AAH ;MOV R2, DIRECT OP CODE + DB 0CBH ;RCAP2H LOCATION + DB 0A8H ;MOV R0, DIRECT OP CODE + DB 0CAH ;R2CAPL LOCATION + SJMP TWO_EY + ; +AP1: MOV A,P1 ;GET P1 + SJMP TWO_R2 ;PUT IT ON THE STACK + ; +APCON: DB 0E5H ;MOV A, DIRECT OP CODE + DB 87H ;ADDRESS OF PCON + SJMP TWO_R2 ;PUT PCON ON THE STACK + ; + newpage + ;*************************************************************** + ; + ;THIS IS THE LINE EDITOR + ; + ;TAKE THE PROCESSED LINE IN IBUF AND INSERT IT INTO THE + ;BASIC TEXT FILE. + ; + ;*************************************************************** + ; + LJMP NOGO ;CAN'T EDIT A ROM + ; +LINE: MOV A,BOFAH + CJNE A,#HI(PSTART),LINE-3 + CALL G4 ;GET END ADDRESS FOR EDITING + MOV R4,DPL + MOV R5,DPH + MOV R3,TEMP5 ;GET HIGH ORDER IBLN + MOV R1,TEMP4 ;LOW ORDER IBLN + ; + CALL GETLIN ;FIND THE LINE + JNZ INSR ;INSERT IF NOT ZERO, ELSE APPEND + ; + ;APPEND THE LINE AT THE END + ; + MOV A,TEMP3 ;PUT IBCNT IN THE ACC + CJNE A,#4H,$+4 ;SEE IF NO ENTRY + RET ;RET IF NO ENTRY + ; + ACALL FULL ;SEE IF ENOUGH SPACE LEFT + MOV R2,R5B0 ;PUT END ADDRESS A INTO TRANSFER + MOV R0,R4B0 ;REGISTERS + ACALL IMOV ;DO THE BLOCK MOVE + ; +UE: MOV A,#EOF ;SAVE EOF CHARACTER + AJMP TBR + ; + ;INSERT A LINE INTO THE FILE + ; +INSR: MOV R7,A ;SAVE IT IN R7 + CALL TEMPD ;SAVE INSERATION ADDRESS + MOV A,TEMP3 ;PUT THE COUNT LENGTH IN THE ACC + JC LTX ;JUMP IF NEW LINE # NOT = OLD LINE # + CJNE A,#04H,$+4 ;SEE IF NULL + CLR A + ; + SUBB A,R7 ;SUBTRACT LINE COUNT FROM ACC + JZ LIN1 ;LINE LENGTHS EQUAL + JC GTX ;SMALLER LINE + ; + newpage + ; + ;EXPAND FOR A NEW LINE OR A LARGER LINE + ; +LTX: MOV R7,A ;SAVE A IN R7 + MOV A,TEMP3 ;GET THE COUNT IN THE ACC + CJNE A,#04H,$+4 ;DO NO INSERTATION IF NULL LINE + RET ;EXIT IF IT IS + ; + MOV A,R7 ;GET THE COUNT BACK - DELTA IN A + ACALL FULL ;SEE IF ENOUGH MEMORY NEW EOFA IN R3:R1 + CALL DTEMP ;GET INSERATION ADDRESS + ACALL NMOV ;R7:R6 GETS (EOFA)-DPTR + CALL X3120 + MOV R1,R4B0 ;EOFA LOW + MOV R3,R5B0 ;EOFA HIGH + INC R6 ;INCREMENT BYTE COUNT + CJNE R6,#00,$+4 ;NEED TO BUMP HIGH BYTE? + INC R7 + ; + ACALL RMOV ;GO DO THE INSERTION + SJMP LIN1 ;INSERT THE CURRENT LINE + ; +GTX: CPL A ;FLIP ACC + INC A ;TWOS COMPLEMENT + CALL ADDPTR ;DO THE ADDITION + ACALL NMOV ;R7:R6 GETS (EOFA)-DPTR + MOV R1,DPL ;SET UP THE REGISTERS + MOV R3,DPH + MOV R2,TEMP5 ;PUT INSERTATION ADDRESS IN THE RIGHT REG + MOV R0,TEMP4 + JZ $+4 ;IF ACC WAS ZERO FROM NMOV, JUMP + ACALL LMOV ;IF NO ZERO DO A LMOV + ; + ACALL UE ;SAVE NEW END ADDRESS + ; +LIN1: MOV R2,TEMP5 ;GET THE INSERTATION ADDRESS + MOV R0,TEMP4 + MOV A,TEMP3 ;PUT THE COUNT LENGTH IN ACC + CJNE A,#04H,IMOV ;SEE IF NULL + RET ;EXIT IF NULL + newpage + ;*************************************************************** + ; + ;INSERT A LINE AT ADDRESS R2:R0 + ; + ;*************************************************************** + ; +IMOV: CLR A ;TO SET UP + MOV R1,#LO(IBCNT) ;INITIALIZE THE REGISTERS + MOV R3,A + MOV R6,TEMP3 ;PUT THE BYTE COUNT IN R6 FOR LMOV + MOV R7,A ;PUT A 0 IN R7 FOR LMOV + ; + ;*************************************************************** + ; + ;COPY A BLOCK FROM THE BEGINNING + ; + ;R2:R0 IS THE DESTINATION ADDRESS + ;R3:R1 IS THE SOURCE ADDRESS + ;R7:R6 IS THE COUNT REGISTER + ; + ;*************************************************************** + ; +LMOV: ACALL TBYTE ;TRANSFER THE BYTE + ACALL INC3210 ;BUMP THE POINTER + ACALL DEC76 ;BUMP R7:R6 + JNZ LMOV ;LOOP + RET ;GO BACK TO CALLING ROUTINE + ; +INC3210:INC R0 + CJNE R0,#00H,$+4 + INC R2 + ; + INC R1 + CJNE R1,#00H,$+4 + INC R3 + RET + ; + newpage + ;*************************************************************** + ; + ;COPY A BLOCK STARTING AT THE END + ; + ;R2:R0 IS THE DESTINATION ADDRESS + ;R3:R1 IS THE SOURCE ADDRESS + ;R6:R7 IS THE COUNT REGISTER + ; + ;*************************************************************** + ; +RMOV: ACALL TBYTE ;TRANSFER THE BYTE + ACALL DEC3210 ;DEC THE LOCATIONS + ACALL DEC76 ;BUMP THE COUNTER + JNZ RMOV ;LOOP + ; +DEC_R: NOP ;CREATE EQUAL TIMING + RET ;EXIT + ; +DEC3210:DEC R0 ;BUMP THE POINTER + CJNE R0,#0FFH,$+4 ;SEE IF OVERFLOWED + DEC R2 ;BUMP THE HIGH BYTE + DEC R1 ;BUMP THE POINTER + CJNE R1,#0FFH,DEC_R ;SEE IF OVERFLOWED + DEC R3 ;CHANGE THE HIGH BYTE + RET ;EXIT + ; + ;*************************************************************** + ; + ;TBYTE - TRANSFER A BYTE + ; + ;*************************************************************** + ; +TBYTE: MOV P2,R3 ;OUTPUT SOURCE REGISTER TO PORT + MOVX A,@R1 ;PUT BYTE IN ACC + ; +TBR: MOV P2,R2 ;OUTPUT DESTINATION TO PORT + MOVX @R0,A ;SAVE THE BYTE + RET ;EXIT + ; + newpage + ;*************************************************************** + ; + ;NMOV - R7:R6 = END ADDRESS - DPTR + ; + ;ACC GETS CLOBBERED + ; + ;*************************************************************** + ; +NMOV: MOV A,R4 ;THE LOW BYTE OF EOFA + CLR C ;CLEAR THE CARRY FOR SUBB + SUBB A,DPL ;SUBTRACT DATA POINTER LOW + MOV R6,A ;PUT RESULT IN R6 + MOV A,R5 ;HIGH BYTE OF EOFA + SUBB A,DPH ;SUBTRACT DATA POINTER HIGH + MOV R7,A ;PUT RESULT IN R7 + ORL A,R6 ;SEE IF ZERO + RET ;EXIT + ; + ;*************************************************************** + ; + ;CHECK FOR A FILE OVERFLOW + ;LEAVES THE NEW END ADDRESS IN R3:R1 + ;A HAS THE INCREASE IN SIZE + ; + ;*************************************************************** + ; +FULL: ADD A,R4 ;ADD A TO END ADDRESS + MOV R1,A ;SAVE IT + CLR A + ADDC A,R5 ;ADD THE CARRY + MOV R3,A + MOV DPTR,#VARTOP ;POINT AT VARTOP + ; +FUL1: CALL DCMPX ;COMPARE THE TWO + JC FULL-1 ;OUT OF ROOM + ; +TB: MOV DPTR,#E5X ;OUT OF MEMORY + AJMP FPTS + ; + newpage + ;*************************************************************** + ; + ; PP - Preprocesses the line in IBUF back into IBUF + ; sets F0 if no line number + ; leaves the correct length of processed line in IBCNT + ; puts the line number in IBLN + ; wastes the text address TXAL and TXAH + ; + ;*************************************************************** + ; +PP: ACALL T_BUF ;TXA GETS IBUF + CALL INTGER ;SEE IF A NUMBER PRESENT + CALL TEMPD ;SAVE THE INTEGER IN TEMP5:TEMP4 + MOV F0,C ;SAVE INTEGER IF PRESENT + MOV DPTR,#IBLN ;SAVE THE LINE NUMBER, EVEN IF NONE + ACALL S20DP + MOV R0,TXAL ;TEXT POINTER + MOV R1,#LO(IBUF) ;STORE POINTER + ; + ; Now process the line back into IBUF + ; +PPL: CLR ARGF ;FIRST PASS DESIGNATOR + MOV DPTR,#TOKTAB ;POINT DPTR AT LOOK UP TABLE + ; +PPL1: MOV R5B0,R0 ;SAVE THE READ POINTER + CLR A ;ZERO A FOR LOOKUP + MOVC A,@A+DPTR ;GET THE TOKEN + MOV R7,A ;SAVE TOKEN IN CASE OF MATCH + ; +PPL2: MOVX A,@R0 ;GET THE USER CHARACTER + MOV R3,A ;SAVE FOR REM + CJNE A,#'a',$+3 + JC PPX ;CONVERT LOWER TO UPPER CASE + CJNE A,#('z'+1),$+3 + JNC PPX + CLR ACC.5 + ; +PPX: MOV R2,A + MOVX @R0,A ;SAVE UPPER CASE + INC DPTR ;BUMP THE LOOKUP POINTER + CLR A + MOVC A,@A+DPTR + CJNE A,R2B0,PPL3 ;LEAVE IF NOT THE SAME + INC R0 ;BUMP THE USER POINTER + SJMP PPL2 ;CONTINUE TO LOOP + ; +PPL3: JB ACC.7,PPL6 ;JUMP IF FOUND MATCH + JZ PPL6 ;USER MATCH + ; + ; + ; Scan to the next TOKTAB entry + ; +PPL4: INC DPTR ;ADVANCE THE POINTER + CLR A ;ZERO A FOR LOOKUP + MOVC A,@A+DPTR ;LOAD A WITH TABLE + JB ACC.7,$+6 ;KEEP SCANNING IF NOT A RESERVED WORD + JNZ PPL4 + INC DPTR + ; + ; See if at the end of TOKTAB + ; + MOV R0,R5B0 ;RESTORE THE POINTER + CJNE A,#0FFH,PPL1 ;SEE IF END OF TABLE + ; + ; Character not in TOKTAB, so see what it is + ; + CJNE R2,#' ',PPLX ;SEE IF A SPACE + INC R0 ;BUMP USER POINTER + SJMP PPL ;TRY AGAIN + ; +PPLX: JNB XBIT,PPLY ;EXTERNAL TRAP + JB ARGF,PPLY + SETB ARGF ;SAYS THAT THE USER HAS TABLE + LCALL 2078H ;SET UP POINTER + AJMP PPL1 + ; +PPLY: ACALL PPL7 ;SAVE CHARACTER, EXIT IF A CR + CJNE A,#'"',PPL ;SEE IF QUOTED STRING, START AGAIN IF NOT + ; + ; Just copy a quoted string + ; + ACALL PPL7 ;SAVE THE CHARACTER, TEST FOR CR + CJNE A,#'"',$-2 ;IS THERE AN ENDQUOTE, IF NOT LOOP + SJMP PPL ;DO IT AGAIN IF ENDQUOTE + ; +PPL6: MOV A,R7 ;GET THE TOKEN + ACALL PPL9+1 ;SAVE THE TOKEN + CJNE A,#T_REM,PPL ;SEE IF A REM TOKEN + MOV A,R3 + ACALL PPL7+1 ;WASTE THE REM STATEMENT + ACALL PPL7 ;LOOP UNTIL A CR + SJMP $-2 + ; +PPL7: MOVX A,@R0 ;GET THE CHARACTER + CJNE A,#CR,PPL9 ;FINISH IF A CR + POP R0B0 ;WASTE THE CALLING STACK + POP R0B0 + MOVX @R1,A ;SAVE CR IN MEMORY + INC R1 ;SAVE A TERMINATOR + MOV A,#EOF + MOVX @R1,A + MOV A,R1 ;SUBTRACT FOR LENGTH + SUBB A,#4 + MOV TEMP3,A ;SAVE LENGTH + MOV R1,#LO(IBCNT) ;POINT AT BUFFER COUNT + ; +PPL9: INC R0 + MOVX @R1,A ;SAVE THE CHARACTER + INC R1 ;BUMP THE POINTERS + RET ;EXIT TO CALLING ROUTINE + ; + ; + ;*************************************************************** + ; + ;DEC76 - DECREMENT THE REGISTER PAIR R7:R6 + ; + ;ACC = ZERO IF R7:R6 = ZERO ; ELSE ACC DOES NOT + ; + ;*************************************************************** + ; +DEC76: DEC R6 ;BUMP R6 + CJNE R6,#0FFH,$+4 ;SEE IF RAPPED AROUND + DEC R7 + MOV A,R7 ;SEE IF ZERO + ORL A,R6 + RET ;EXIT + ; + ;*************************************************************** + ; + ; MTOP - Get or Put the top of assigned memory + ; + ;*************************************************************** + ; +PMTOP: MOV DPTR,#MEMTOP + CALL L20DPI + AJMP TWO_EY ;PUT R2:R0 ON THE STACK + ; + newpage + ;************************************************************* + ; + ; AXTAL - Crystal value calculations + ; + ;************************************************************* + ; +AXTAL0: MOV DPTR,#XTALV ;CRYSTAL VALUE + ACALL PUSHC + ; +AXTAL1: ACALL CSTAKA2 ;COPY CRYSTAL VALUE TWICE + ACALL CSTAKA + MOV DPTR,#PTIME ;PROM TIMER + ACALL AXTAL2 + MOV DPTR,#PROGS + ACALL S31L + MOV DPTR,#IPTIME ;IPROM TIMER + ACALL AXTAL2 + MOV DPTR,#IPROGS + ACALL S31L + MOV DPTR,#TTIME ;CLOCK CALCULATION + ACALL AXTAL3 + MOV A,R1 + CPL A + INC A + MOV SAVE_T,A + MOV R3,#HI(CXTAL) + MOV R1,#LO(CXTAL) + JMP POPAS + ; +AXTAL2: ACALL AXTAL3 + ; +CBIAS: ;Bias the crystal calculations + ; + MOV A,R1 ;GET THE LOW COUNT + CPL A ;FLIP IT FOR TIMER LOAD + ADD A,#15 ;BIAS FOR CALL AND LOAD TIMES + MOV R1,A ;RESTORE IT + MOV A,R3 ;GET THE HIGH COUNT + CPL A ;FLIP IT + ADDC A,#00H ;ADD THE CARRY + MOV R3,A ;RESTORE IT + RET + ; + newpage + include bas52.pwm ; ******AA + newpage + ;LNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLN + ; +LNTAB: ; Natural log lookup table + ; + ;LNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLNLN + ; + DB 80H + DB 00H + DB 71H + DB 37H + DB 13H + DB 19H + ; + DB 7FH + DB 00H + DB 76H + DB 64H + DB 37H + DB 94H + ; + DB 80H + DB 00H + DB 07H + DB 22H + DB 75H + DB 17H + ; + DB 80H + DB 00H + DB 52H + DB 35H + DB 93H + DB 28H + ; + DB 80H + DB 00H + DB 71H + DB 91H + DB 85H + DB 86H + ; + DB 0FFH + ; + DB 81H + DB 00H + DB 51H + DB 58H + DB 02H + DB 23H + ; + newpage + ;SINSINSINSINSINSINSINSINSINSINSINSINSINSINSINSINSIN + ; +SINTAB: ; Sin lookup table + ; + ;SINSINSINSINSINSINSINSINSINSINSINSINSINSINSINSINSIN + ; + DB 128-9 + DB 00H + DB 44H + DB 90H + DB 05H + DB 16H + ; + DB 128-7 + DB 01H + DB 08H + DB 21H + DB 05H + DB 25H + ; + DB 128-5 + DB 00H + DB 19H + DB 73H + DB 55H + DB 27H + ; + newpage + ; + DB 128-3 + DB 01H + DB 70H + DB 12H + DB 84H + DB 19H + ; + DB 128-2 + DB 00H + DB 33H + DB 33H + DB 33H + DB 83H + ; + DB 128 + DB 01H + DB 67H + DB 66H + DB 66H + DB 16H + ; +FPONE: DB 128+1 + DB 00H + DB 00H + DB 00H + DB 00H + DB 10H + ; + DB 0FFH ;END OF TABLE + ; + newpage + ; +SBAUD: CALL AXTAL ;PUT CRYSTAL ON THE STACK + CALL EXPRB ;PUT THE NUMBER AFTER BAUD ON STACK + MOV A,#12 + ACALL TWO_R2 ;TOS = 12 + ACALL AMUL ;TOS = 12*BAUD + ACALL ADIV ;TOS = XTAL/(12*BAUD) + ACALL IFIX + ACALL CBIAS + MOV DPTR,#SPV + ; +S31L: JMP S31DP + ; +AFREE: CALL PMTOP ;PUT MTOP ON STACK + CALL G4 ;GET END ADDRESS + MOV R0,DPL + MOV R2,DPH + ACALL TWO_EY + ; +ASUB: LCALL FP_BASE+2 ;DO FP SUB + AJMP FPTST + ; +ALEN: CALL CCAL ;CALCULATE THE LEN OF THE SELECTED PROGRAM + MOV R2,R7B0 ;SAVE THE HIGH BYTE + MOV A,R6 ;SAVE THE LOW BYTE + AJMP TWO_EX ;PUT IT ON THE STACK + ; +ATIME: MOV C,EA ;SAVE INTERRUTS + CLR EA + PUSH MILLIV ;SAVE MILLI VALUE + MOV R2,TVH ;GET THE TIMER + MOV A,TVL + MOV EA,C ;SAVE INTERRUPTS + ACALL TWO_EX ;PUT TIMER ON THE STACK + POP ACC ;GET MILLI + ACALL TWO_R2 ;PUT MILLI ON STACK + MOV A,#200 + ACALL TWO_R2 ;DIVIDE MILLI BY 200 + ACALL ADIV + ; +AADD: LCALL FP_BASE ;DO FP ADDITION + AJMP FPTST ;CHECK FOR ERRORS + ; + newpage + ;************************************************************** + ; + ; Here are some error messages that were moved + ; + ;************************************************************** + ; + ; +E1X: DB "BAD SYNTAX",'"' +E2X: DB 128+10 + DB "DIVIDE BY ZERO",'"' + ; +E6X: DB "ARRAY SIZE",'"' + ; + newpage + ;************************************************************** + ; +T_BUF: ; TXA gets IBUF + ; + ;************************************************************** + ; + MOV TXAH,#HI(IBUF) + MOV TXAL,#LO(IBUF) + RET + ; + ; + ;*************************************************************** + ; +CXFER: ; Transfer a program from rom to ram + ; + ;*************************************************************** + ; + CALL CCAL ;GET EVERYTHING SET UP + MOV R2,#HI(PSTART) + MOV R0,#LO(PSTART) + ACALL LMOV ;DO THE TRANSFER + CALL RCLEAR ;CLEAR THE MEMORY + ; + ; Fall thru to CRAM + ; + ;*************************************************************** + ; +CRAM: ; The command action routine - RAM - Run out of ram + ; + ;*************************************************************** + ; + CLR CONB ;CAN'T CONTINUE IF MODE CHANGE + MOV BOFAH,#HI(PSTART) + MOV BOFAL,#LO(PSTART) + ; + ; Fall thru to Command Processor + ; + newpage + ;*************************************************************** + ; +CMND1: ; The entry point for the command processor + ; + ;*************************************************************** + ; + LCALL SPRINT+4 ;WASTE AT AND HEX + CLR XBIT ;TO RESET IF NEEDED + CLR A + MOV DPTR,#2002H ;CHECK FOR EXTERNAL TRAP PACKAGE + MOVC A,@A+DPTR + CJNE A,#5AH,$+6 + LCALL 2048H ;IF PRESENT JUMP TO LOCATION 200BH + MOV DPTR,#RDYS ;PRINT THE READY MESSAGE + CALL CRP ;DO A CR, THEN, PRINT FROM THE ROM + ; +CMNDR: SETB DIRF ;SET THE DIRECT INPUT BIT + MOV SP,SPSAV ;LOAD THE STACK + ACALL CL7 ;DO A CRLF + ; +CMNX: CLR GTRD ;CLEAR BREAK + MOV DPTR,#5EH ;DO RUN TRAP + MOVX A,@DPTR + XRL A,#52 + JNZ $+5 + LJMP CRUN + MOV R5,#'>' ;OUTPUT A PROMPT + LCALL TEROT + CALL INLINE ;INPUT A LINE INTO IBUF + CALL PP ;PRE-PROCESS THE LINE + JB F0,CMND3 ;NO LINE NUMBER + CALL LINE ;PROCESS THE LINE + LCALL LCLR + JB LINEB,CMNX ;DON'T CLEAR MEMORY IF NO NEED + SETB LINEB + LCALL RCLEAR ;CLEAR THE MEMORY + SJMP CMNX ;LOOP BACK + ; +CMND3: CALL T_BUF ;SET UP THE TEXT POINTER + CALL DELTST ;GET THE CHARACTER + JZ CMNDR ;IF CR, EXIT + MOV DPTR,#CMNDD ;POINT AT THE COMMAND LOOKUP + CJNE A,#T_CMND,$+3 ;PROCESS STATEMENT IF NOT A COMMAND + JC CMND5 + CALL GCI1 ;BUMP TXA + ANL A,#0FH ;STRIP MSB'S FOR LOOKUP + LCALL ISTA1 ;PROCESS COMMAND + SJMP CMNDR + ; +CMND5: LJMP ILOOP ;CHECK FOR A POSSIBLE BREAK + ; + ; + ; + ;CONSTANTS + ; +XTALV: DB 128+8 ; DEFAULT CRYSTAL VALUE + DB 00H + DB 00H + DB 92H + DB 05H + DB 11H + ; +EXP11: DB 85H + DB 00H + DB 42H + DB 41H + DB 87H + DB 59H + ; +EXP1: DB 128+1 ; EXP(1) + DB 00H + DB 18H + DB 28H + DB 18H + DB 27H + ; +IPTIME: DB 128-4 ;FPROG TIMING + DB 00H + DB 00H + DB 00H + DB 75H + DB 83H + ; +PIE: DB 128+1 ;PI + DB 00H + DB 26H + DB 59H + DB 41H + DB 31H ; 3.1415926 + ; + newpage + ;*************************************************************** + ; + ; The error messages, some have been moved + ; + ;*************************************************************** + ; +E7X: DB 128+30 + DB "ARITH. UNDERFLOW",'"' + ; +E5X: DB "MEMORY ALLOCATION",'"' + ; +E3X: DB 128+40 + DB "BAD ARGUMENT",'"' + ; +EXI: DB "I-STACK",'"' + ; + newpage + ;*************************************************************** + ; + ; The command action routine - CONTINUE + ; + ;*************************************************************** + ; +CCONT: MOV DPTR,#E15X + JNB CONB,ERROR ;ERROR IF CONTINUE IS NOT SET + ; +CC1: ;used for input statement entry + ; + MOV TXAH,INTXAH ;RESTORE TXA + MOV TXAL,INTXAL + JMP CILOOP ;EXECUTE + ; +DTEMP: MOV DPH,TEMP5 ;RESTORE DPTR + MOV DPL,TEMP4 + RET + ; +TEMPD: MOV TEMP5,DPH + MOV TEMP4,DPL + RET + ; + newpage + ;************************************************************** + ; +I_DL: ; IDLE + ; + ;************************************************************** + ; + JB DIRF,E1XX ;SYNTAX ERROR IN DIRECT INPUT + CLR DACK ;ACK IDLE + ; +U_ID1: DB 01000011B ;ORL DIRECT OP CODE + DB 87H ;PCON ADDRESS + DB 01H ;SET IDLE BIT + JB INTPEN,I_RET ;EXIT IF EXTERNAL INTERRUPT + JBC U_IDL,I_RET ;EXIT IF USER WANTS TO + JNB OTS,U_ID1 ;LOOP IF TIMER NOT ENABLED + LCALL T_CMP ;CHECK THE TIMER + JC U_ID1 ;LOOP IF TIME NOT BIG ENOUGH + ; +I_RET: SETB DACK ;RESTORE EXECUTION + RET ;EXIT IF IT IS + ; + ; + ; +ER0: INC DPTR ;BUMP TO TEXT + JB DIRF,ERROR0 ;CAN'T GET OUT OF DIRECT MODE + JNB ON_ERR,ERROR0 ;IF ON ERROR ISN'T SET, GO BACK + MOV DPTR,#ERRLOC ;SAVE THE ERROR CODE + CALL RC2 ;SAVE ERROR AND SET UP THE STACKS + INC DPTR ;POINT AT ERRNUM + JMP ERL4 ;LOAD ERR NUM AND EXIT + ; + newpage + ; + ; Syntax error + ; +E1XX: MOV C,DIRF ;SEE IF IN DIRECT MODE + MOV DPTR,#E1X ;ERROR MESSAGE + SJMP ERROR+1 ;TRAP ON SET DIRF + ; + MOV DPTR,#EXI ;STACK ERROR + ; + ; Falls through + ; + ;*************************************************************** + ; + ;ERROR PROCESSOR - PRINT OUT THE ERROR TYPE, CHECK TO SEE IF IN + ; RUN OR COMMAND MODE, FIND AND PRINT OUT THE + ; LINE NUMBER IF IN RUN MODE + ; + ;*************************************************************** + ; +ERROR: CLR C ;RESET STACK + MOV SP,SPSAV ;RESET THE STACK + LCALL SPRINT+4 ;CLEAR LINE AND AT MODE + CLR A ;SET UP TO GET ERROR CODE + MOVC A,@A+DPTR + JBC ACC.7,ER0 ;PROCESS ERROR + ; +ERROR0: ACALL TEMPD ;SAVE THE DATA POINTER + JC $+5 ;NO RESET IF CARRY IS SET + LCALL RC1 ;RESET THE STACKS + CALL CRLF2 ;DO TWO CARRIAGE RET - LINE FEED + MOV DPTR,#ERS ;OUTPUT ERROR MESSAGE + CALL ROM_P + CALL DTEMP ;GET THE ERROR MESSAGE BACK + ; +ERRS: CALL ROM_P ;PRINT ERROR TYPE + JNB DIRF,ER1 ;DO NOT PRINT IN LINE IF DIRF=1 + ; +SERR1: CLR STOPBIT ;PRINT STOP THEN EXIT, FOR LIST + JMP CMND1 + ; +ER1: MOV DPTR,#INS ;OUTPUT IN LINE + CALL ROM_P + ; + ;NOW, FIND THE LINE NUMBER + ; + ; + newpage + ; + ; + CALL DP_B ;GET THE FIRST ADDRESS OF THE PROGRAM + CLR A ;FOR INITIALIZATION + ; +ER2: ACALL TEMPD ;SAVE THE DPTR + CALL ADDPTR ;ADD ACC TO DPTR + ACALL ER4 ;R3:R1 = TXA-DPTR + JC ER3 ;EXIT IF DPTR>TXA + JZ ER3 ;EXIT IF DPTR=TXA + MOVX A,@DPTR ;GET LENGTH + CJNE A,#EOF,ER2 ;SEE IF AT THE END + ; +ER3: ACALL DTEMP ;PUT THE LINE IN THE DPTR + ACALL ER4 ;R3:R1 = TXA - BEGINNING OF LINE + MOV A,R1 ;GET LENGTH + ADD A,#10 ;ADD 10 TO LENGTH, DPTR STILL HAS ADR + MOV MT1,A ;SAVE THE COUNT + INC DPTR ;POINT AT LINE NUMBER HIGH BYTE + CALL PMTOP+3 ;LOAD R2:R0, PUT IT ON THE STACK + ACALL FP_BASE+14 ;OUTPUT IT + JB STOPBIT,SERR1 ;EXIT IF STOP BIT SET + CALL CRLF2 ;DO SOME CRLF'S + CALL DTEMP + CALL UPPL ;UNPROCESS THE LINE + CALL CL6 ;PRINT IT + MOV R5,#'-' ;OUTPUT DASHES, THEN AN X + ACALL T_L ;PRINT AN X IF ERROR CHARACTER FOUND + DJNZ MT1,$-4 ;LOOP UNTIL DONE + MOV R5,#'X' + ACALL T_L + AJMP SERR1 + ; +ER4: MOV R3,TXAH ;GET TEXT POINTER AND PERFORM SUBTRACTION + MOV R1,TXAL + JMP DUBSUB + ; + newpage + ;************************************************************** + ; + ; Interrupt driven timer + ; + ;************************************************************** + ; +I_DR: MOV TH0,SAVE_T ;LOAD THE TIMER + XCH A,MILLIV ;SAVE A, GET MILLI COUNTER + INC A ;BUMP COUNTER + CJNE A,#200,TR ;CHECK OUT TIMER VALUE + CLR A ;FORCE ACC TO BE ZERO + INC TVL ;INCREMENT LOW TIMER + CJNE A,TVL,TR ;CHECK LOW VALUE + INC TVH ;BUMP TIMER HIGH + ; +TR: XCH A,MILLIV + POP PSW + RETI + ; + newpage + include bas52.clk + ;*************************************************************** + ; +SUI: ; Statement USER IN action routine + ; + ;*************************************************************** + ; + ACALL OTST + MOV CIUB,C ;SET OR CLEAR CIUB + RET + ; + ;*************************************************************** + ; +SUO: ; Statement USER OUT action routine + ; + ;*************************************************************** + ; + ACALL OTST + MOV COUB,C + RET + ; +OTST: ; Check for a one + ; + LCALL GCI ;GET THE CHARACTER, CLEARS CARRY + SUBB A,#'1' ;SEE IF A ONE + CPL C ;SETS CARRY IF ONE, CLEARS IT IF ZERO + RET + ; + newpage + ;************************************************************** + ; + ; IBLK - EXECUTE USER SUPPLIED TOKEN + ; + ;************************************************************** + ; +IBLK: JB PSW.4,IBLK-1 ;EXIT IF REGISTER BANK <> 0 + JB PSW.3,IBLK-1 + JBC ACC.7,$+9 ;SEE IF BIT SEVEN IS SET + MOV DPTR,#USENT ;USER ENTRY LOCATION + LJMP ISTA1 + ; + JB ACC.0,199FH ;FLOATING POINT INPUT + JZ T_L ;DO OUTPUT ON 80H + MOV DPTR,#FP_BASE-2 + JMP @A+DPTR + ; + ; + ;************************************************************** + ; + ; GET_NUM - GET A NUMBER, EITHER HEX OR FLOAT + ; + ;************************************************************** + ; +GET_NUM:ACALL FP_BASE+10 ;SCAN FOR HEX + JNC FP_BASE+12 ;DO FP INPUT + ; + ACALL FP_BASE+18 ;ASCII STRING TO R2:R0 + JNZ H_RET + PUSH DPH ;SAVE THE DATA_POINTER + PUSH DPL + ACALL FP_BASE+24 ;PUT R2:R0 ON THE STACK + POP DPL ;RESTORE THE DATA_POINTER + POP DPH + CLR A ;NO ERRORS + RET ;EXIT + ; + newpage + ;************************************************************** + ; + ; WB - THE EGO MESSAGE + ; + ;************************************************************** + ; +WB: DB 'W'+80H,'R'+80H + DB 'I'+80H,'T'+80H,'T','E'+80H,'N'+80H + DB ' ','B'+80H,'Y'+80H,' ' + DB 'J'+80H,'O'+80H,'H'+80H,'N'+80H,' '+80H + DB 'K','A'+80H,'T'+80H,'A'+80H,'U'+80H + DB 'S','K'+80H,'Y'+80H + DB ", I",'N'+80H,'T'+80H,'E'+80H,'L'+80H + DB ' '+80H,'C'+80H,'O'+80H,'R'+80H,'P'+80H + DB ". 1",'9'+80H,"85" +H_RET: RET + ; + newpage + ORG 1990H + ; +T_L: LJMP TEROT + ; + ORG 1F78H + ; +CKS_I: JB CKS_B,CS_I + LJMP 401BH + ; +CS_I: LJMP 2088H + ; +E14X: DB "NO DATA",'"' + ; +E11X: DB 128+20 + DB "ARITH. OVERFLOW",'"' + ; +E16X: DB "PROGRAMMING",'"' + ; +E15X: DB "CAN" + DB 27H + DB "T CONTINUE",'"' + ; +E10X: DB "INVALID LINE NUMBER",'"' + ; +NOROM: DB "PROM MODE",'"' + ; +S_N: DB "*MCS-51(tm) BASIC V1.1*",'"' + ; + ORG 1FF8H + ; +ERS: DB "ERROR: ",'"' + ; + newpage + ;*************************************************************** + ; + segment xdata ;External Ram + ; + ;*************************************************************** + ; + DS 4 +IBCNT: DS 1 ;LENGTH OF A LINE +IBLN: DS 2 ;THE LINE NUMBER +IBUF: DS LINLEN ;THE INPUT BUFFER +CONVT: DS 15 ;CONVERSION LOCATION FOR FPIN + ; + ORG 100H + ; +GTB: DS 1 ;GET LOCATION +ERRLOC: DS 1 ;ERROR TYPE +ERRNUM: DS 2 ;WHERE TO GO ON AN ERROR +VARTOP: DS 2 ;TOP OF VARIABLE STORAGE +ST_ALL: DS 2 ;STORAGE ALLOCATION +MT_ALL: DS 2 ;MATRIX ALLOCATION +MEMTOP: DS 2 ;TOP OF MEMORY +RCELL: DS 2 ;RANDOM NUMBER CELL + DS FPSIZ-1 +CXTAL: DS 1 ;CRYSTAL + DS FPSIZ-1 +FPT1: DS 1 ;FLOATINP POINT TEMP 1 + DS FPSIZ-1 +FPT2: DS 1 ;FLOATING POINT TEMP 2 +INTLOC: DS 2 ;LOCATION TO GO TO ON INTERRUPT +STR_AL: DS 2 ;STRING ALLOCATION +SPV: DS 2 ;SERIAL PORT BAUD RATE +TIV: DS 2 ;TIMER INTERRUPT NUM AND LOC +PROGS: DS 2 ;PROGRAM A PROM TIME OUT +IPROGS: DS 2 ;INTELLIGENT PROM PROGRAMMER TIMEOUT +TM_TOP: DS 1 + + include bas52.fp + + END diff --git a/tests/t_bas52/t_bas52.doc b/tests/t_bas52/t_bas52.doc new file mode 100644 index 0000000..05efe9d --- /dev/null +++ b/tests/t_bas52/t_bas52.doc @@ -0,0 +1,11 @@ ++---------------------- Test Application BAS52 ----------------------------+ +| | +| This is the source of the BASIC interpreter for Intel's 8052AH-Basic | +| (version 1.1). In contrast to other test programs, the reference binary | +| was extracted from a real 8052AH and not generated with the BP version | +| of AS. Since the source of this interpreter is now freeware, it should | +| be okay to include this program. Of course, I had to modify the code a | +| bit to adapt it to AS... The source and ROM dump was provided by | +| squest@cris.com. | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_bas52/t_bas52.inc b/tests/t_bas52/t_bas52.inc new file mode 100644 index 0000000..6bf1b5c --- /dev/null +++ b/tests/t_bas52/t_bas52.inc @@ -0,0 +1,2 @@ +; tests/t_bas52/t_bas52.asm-Includefile für Assembler-Programm +; Ende Includefile für Assembler-Programm diff --git a/tests/t_bas52/t_bas52.ori b/tests/t_bas52/t_bas52.ori new file mode 100644 index 0000000..f86786d Binary files /dev/null and b/tests/t_bas52/t_bas52.ori differ diff --git a/tests/t_buf32/asflags b/tests/t_buf32/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_buf32/t_buf32.asm b/tests/t_buf32/t_buf32.asm new file mode 100644 index 0000000..83e1d42 --- /dev/null +++ b/tests/t_buf32/t_buf32.asm @@ -0,0 +1,4883 @@ +;* BUFFALO +;* "Bit User's Fast Friendly Aid to Logical Operation" +;* +;* Rev 2.0 - 4/23/85 - added disassembler. +;* - variables now PTRn and TMPn. +;* Rev 2.1 - 4/29/85 - added byte erase to chgbyt routine. +;* Rev 2.2 - 5/16/85 - added hooks for evb board - acia +;* drivers, init and host routines. +;* 7/8/85 - fixed dump wraparound problem. +;* 7/10/85 - added evm board commands. +;* - added fill instruction. +;* 7/18/85 - added jump to EEPROM. +;* Rev 2.3 - 8/22/85 - call targco to disconnect sci from host +;* in reset routine for evb board. +;* 10/3/85 - modified load for download through terminal. +;* Rev 2.4 - 7/1/86 - Changed DFLOP address to fix conflicts with +;* EEPROM. (was at A000) +;* Rev 2.5 - 9/8/86 - Modified to provide additional protection from +;* program run-away on power down. Also fixed bugs +;* in MM and MOVE. Changed to 1 stop bit from 2. +;* Rev 2.6 - 9/25/86 - Modified boot routine for variable length download +;* for use with 'HC11E8. +;* Rev 3.0 1/15/87 - EEPROM programming routines consolidated into WRITE. +;* Fill, Assem, and breakpoints will now do EEPROM. +;* - Added compare a to $0D to WSKIP routine. +;* 2/11/87 - Set up load to detect receiver error. +;* Rev 3.2 7/7/87 - Add disassembly to trace. +;* - Add entries to jump table. +;* 9/20/87 - Rewrote trace to use XIRQ, added STOPAT Command +;* 11/24/87- Write block protect reg for 'E9 version +;* - Modified variable length download for use +;* with 'E9 bootloader (XBOOT command) +;* +;* +;**************************************************** +;* Although the information contained herein, * +;* as well as any information provided relative * +;* thereto, has been carefully reviewed and is * +;* believed accurate, Motorola assumes no * +;* liability arising out of its application or * +;* use, neither does it convey any license under * +;* its patent rights nor the rights of others. * +;**************************************************** + + CPU 6811 + +;*************** +;* EQUATES * +;*************** +RAMBS EQU $0000 ; start of ram +REGBS EQU $1000 ; start of registers +ROMBS EQU $E000 ; start of rom +STREE EQU $B600 ; start of eeprom +ENDEE EQU $B7FF ; end of eeprom +PORTE EQU REGBS+$0A ; port e +CFORC EQU REGBS+$0B ; force output compare +TCNT EQU REGBS+$0E ; timer count +TOC5 EQU REGBS+$1E ; oc5 reg +TCTL1 EQU REGBS+$20 ; timer control 1 +TMSK1 EQU REGBS+$22 ; timer mask 1 +TFLG1 EQU REGBS+$23 ; timer flag 1 +TMSK2 EQU REGBS+$24 ; timer mask 2 +BAUD EQU REGBS+$2B ; sci baud reg +SCCR1 EQU REGBS+$2C ; sci control1 reg +SCCR2 EQU REGBS+$2D ; sci control2 reg +SCSR EQU REGBS+$2E ; sci status reg +SCDAT EQU REGBS+$2F ; sci data reg +BPROT EQU REGBS+$35 ; block protect reg +OPTION EQU REGBS+$39 ; option reg +COPRST EQU REGBS+$3A ; cop reset reg +PPROG EQU REGBS+$3B ; ee prog reg +HPRIO EQU REGBS+$3C ; hprio reg +CONFIG EQU REGBS+$3F ; config register +DFLOP EQU $4000 ; evb d flip flop +DUART EQU $D000 ; duart address +PORTA EQU DUART +PORTB EQU DUART+8 +ACIA EQU $9800 ; acia address +PROMPT EQU '>' +BUFFLNG EQU 35 +CTLA EQU $01 ; exit host or assembler +CTLB EQU $02 ; send break to host +CTLW EQU $17 ; wait +CTLX EQU $18 ; abort +DEL EQU $7F ; abort +EOT EQU $04 ; end of text/table +SWI EQU $3F + +;*************** +;* RAM * +;*************** + ORG $33 +;*** Buffalo ram space *** + RMB 20 ; user stack area +USTACK RMB 30 ; monitor stack area +STACK RMB 1 +REGS RMB 9 ; user's pc,y,x,a,b,c +SP RMB 2 ; user's sp +INBUFF RMB BUFFLNG ; input buffer +ENDBUFF EQU * +COMBUFF RMB 8 ; command buffer +SHFTREG RMB 2 ; input shift register +BRKTABL RMB 8 ; breakpoint table +AUTOLF RMB 1 ; auto lf flag for i/o +IODEV RMB 1 ; 0=sci, 1=acia, 2=duartA, 3=duartB +EXTDEV RMB 1 ; 0=none, 1=acia, 2=duart, +HOSTDEV RMB 1 ; 0=sci, 1=acia, 3=duartB +COUNT RMB 1 ; # characters read +CHRCNT RMB 1 ; # characters output on current line +PTRMEM RMB 2 ; current memory location + +;*** Buffalo variables - used by: *** +PTR0 RMB 2 ; main,readbuff,incbuff,AS +PTR1 RMB 2 ; main,BR,DU,MO,AS,EX +PTR2 RMB 2 ; EX,DU,MO,AS +PTR3 RMB 2 ; EX,HO,MO,AS +PTR4 RMB 2 ; EX,AS +PTR5 RMB 2 ; EX,AS,BOOT +PTR6 RMB 2 ; EX,AS,BOOT +PTR7 RMB 2 ; EX,AS +PTR8 RMB 2 ; AS +TMP1 RMB 1 ; main,hexbin,buffarg,termarg +TMP2 RMB 1 ; GO,HO,AS,LOAD +TMP3 RMB 1 ; AS,LOAD +TMP4 RMB 1 ; TR,HO,ME,AS,LOAD +;*** Vector jump table *** +JSCI RMB 3 +JSPI RMB 3 +JPAIE RMB 3 +JPAO RMB 3 +JTOF RMB 3 +JTOC5 RMB 3 +JTOC4 RMB 3 +JTOC3 RMB 3 +JTOC2 RMB 3 +JTOC1 RMB 3 +JTIC3 RMB 3 +JTIC2 RMB 3 +JTIC1 RMB 3 +JRTI RMB 3 +JIRQ RMB 3 +JXIRQ RMB 3 +JSWI RMB 3 +JILLOP RMB 3 +JCOP RMB 3 +JCLM RMB 3 + +;***************** +;* +;* ROM starts here * +;* +;***************** + + ORG ROMBS + +;***************** +;** BUFFALO - This is where Buffalo starts +;** out of reset. All initialization is done +;** here including determination of where the +;** user terminal is (SCI,ACIA, or DUART). +;***************** + +BUFFALO LDX #PORTE + BRCLR 0,X,#01,BUFISIT ; if bit 0 of port e is 1 + JMP $B600 ; then jump to the start of EEPROM +BUFISIT LDAA #$93 + STAA OPTION ; adpu, dly, irqe, cop + LDAA #$00 + STAA TMSK2 ; timer pre = %1 for trace + LDAA #$00 + STAA BPROT ; clear 'E9 eeprom block protect + LDS #STACK ; monitor stack pointer + JSR VECINIT + LDX #USTACK + STX SP ; default user stack + LDAA TCTL1 + ORAA #$03 + STAA TCTL1 ; force oc5 pin high for trace + LDAA #$D0 + STAA REGS+8 ; default user ccr + LDD #$3F0D ; initial command is ? + STD INBUFF + JSR BPCLR ; clear breakpoints + CLR AUTOLF + INC AUTOLF ; auto cr/lf = on + +;* Determine type of external comm device - none, or acia * + + CLR EXTDEV ; default is none + LDAA HPRIO + ANDA #$20 + BEQ BUFF2 ; jump if single chip mode + LDAA #$03 ; see if external acia exists + STAA ACIA ; master reset + LDAA ACIA + ANDA #$7F ; mask irq bit from status register + BNE BUFF1 ; jump if status reg not 0 + LDAA #$12 + STAA ACIA ; turn on acia + LDAA ACIA + ANDA #$02 + BEQ BUFF1 ; jump if tdre not set + LDAA #$01 + STAA EXTDEV ; external device is acia + BRA BUFF2 + +BUFF1 EQU * ; see if duart exists + LDAA DUART+$0C ; read IRQ vector register + CMPA #$0F ; should be out of reset + BNE BUFF2 + LDAA #$AA + STAA DUART+$0C ; write irq vector register + LDAA DUART+$0C ; read irq vector register + CMPA #$AA + BNE BUFF2 + LDAA #$02 + STAA EXTDEV ; external device is duart A + +;* Find terminal port - SCI or external. * + +BUFF2 CLR IODEV + JSR TARGCO ; disconnect sci for evb board + JSR SIGNON ; initialize sci + LDAA EXTDEV + BEQ BUFF3 ; jump if no external device + STAA IODEV + JSR SIGNON ; initialize external device +BUFF3 CLR IODEV + JSR INPUT ; get input from sci port + CMPA #$0D + BEQ BUFF4 ; jump if cr - sci is terminal port + LDAA EXTDEV + BEQ BUFF3 ; jump if no external device + STAA IODEV + JSR INPUT ; get input from external device + CMPA #$0D + BEQ BUFF4 ; jump if cr - terminal found ext + BRA BUFF3 + +SIGNON JSR INIT ; initialize device + LDX #MSG1 ; buffalo message + JSR OUTSTRG + RTS + +;* Determine where host port should be. * + +BUFF4 CLR HOSTDEV ; default - host = sci port + LDAA IODEV + CMPA #$01 + BEQ BUFF5 ; default host if term = acia + LDAA #$03 + STAA HOSTDEV ; else host is duart port b +BUFF5 EQU * + +;***************** +;** MAIN - This module reads the user's input into +;** a buffer called INBUFF. The first field (assumed +;** to be the command field) is then parsed into a +;** second buffer called COMBUFF. The command table +;** is then searched for the contents of COMBUFF and +;** if found, the address of the corresponding task +;** routine is fetched from the command table. The +;** task is then called as a subroutine so that +;** control returns back to here upon completion of +;** the task. Buffalo expects the following format +;** for commands: +;** [...] +;** [] implies contents optional. +;** means whitespace character (space,comma,tab). +;** = command string of 1-8 characters. +;** = Argument particular to the command. +;** = Carriage return signifying end of input string. +;***************** +;* Prompt user +;*do +;* a=input(); +;* if(a==(cntlx or del)) continue; +;* elseif(a==backspace) +;* b--; +;* if(b<0) b=0; +;* else +;* if(a==cr && buffer empty) +;* repeat last command; +;* else put a into buffer; +;* check if buffer full; +;*while(a != (cr or /) + +MAIN LDS #STACK ; initialize sp every time + CLR AUTOLF + INC AUTOLF ; auto cr/lf = on + JSR OUTCRLF + LDAA #PROMPT ; prompt user + JSR OUTPUT + CLRB +MAIN1 JSR INCHAR ; read terminal + LDX #INBUFF + ABX ; pointer into buffer + CMPA #CTLX + BEQ MAIN ; jump if cntl X + CMPA #DEL + BEQ MAIN ; jump if del + CMPA #$08 + BNE MAIN2 ; jump if not bckspc + DECB + BLT MAIN ; jump if buffer empty + BRA MAIN1 +MAIN2 CMPA #$D + BNE MAIN3 ; jump if not cr + TSTB + BEQ COMM0 ; jump if buffer empty + STAA ,X ; put a in buffer + BRA COMM0 +MAIN3 STAA ,X ; put a in buffer + INCB + CMPB #BUFFLNG + BLE MAIN4 ; jump if not long + LDX #MSG3 ; "long" + JSR OUTSTRG + BRA MAIN +MAIN4 CMPA #'/' + BNE MAIN1 ; jump if not "/" +;* ******************* + +;***************** +;* Parse out and evaluate the command field. +;***************** +;*Initialize + +COMM0 EQU * + CLR TMP1 ; Enable "/" command + CLR SHFTREG + CLR SHFTREG+1 + CLRB + LDX #INBUFF ; ptrbuff[] = inbuff[] + STX PTR0 + JSR WSKIP ; find first char + +;*while((a=readbuff) != (cr or wspace)) +;* upcase(a); +;* buffptr[b] = a +;* b++ +;* if (b > 8) error(too long); +;* if(a == "/") +;* if(enabled) mslash(); +;* else error(command?); +;* else hexbin(a); + +COMM1 EQU * + JSR READBUFF ; read from buffer + LDX #COMBUFF + ABX + JSR UPCASE ; convert to upper case + STAA ,X ; put in command buffer + CMPA #$0D + BEQ SRCH ; jump if cr + JSR WCHEK + BEQ SRCH ; jump if wspac + JSR INCBUFF ; move buffer pointer + INCB + CMPB #$8 + BLE COMM2 + LDX #MSG3 ; "long" + JSR OUTSTRG + JMP MAIN + +COMM2 EQU * + CMPA #'/' + BNE COMM4 ; jump if not "/" + TST TMP1 + BNE COMM3 ; jump if not enabled + DECB + STAB COUNT + LDX #MSLASH + JMP EXEC ; execute "/" +COMM3 LDX #MSG8 ; "command?" + JSR OUTSTRG + JMP MAIN +COMM4 EQU * + JSR HEXBIN + BRA COMM1 + +;***************** +;* Search tables for command. At this point, +;* COMBUFF holds the command field to be executed, +;* and B = # of characters in the command field. +;* The command table holds the whole command name +;* but only the first n characters of the command +;* must match what is in COMBUFF where n is the +;* number of characters entered by the user. +;***************** +;*count = b; +;*ptr1 = comtabl; +;*while(ptr1[0] != end of table) +;* ptr1 = next entry +;* for(b=1; b=count; b++) +;* if(ptr1[b] == combuff[b]) continue; +;* else error(not found); +;* execute task; +;* return(); +;*return(command not found); + +SRCH STAB COUNT ; size of command entered + LDX #COMTABL ; pointer to table + STX PTR1 ; pointer to next entry +SRCH1 LDX PTR1 + LDY #COMBUFF ; pointer to command buffer + LDAB 0,X + CMPB #$FF + BNE SRCH2 + LDX #MSG2 ; "command not found" + JSR OUTSTRG + JMP MAIN +SRCH2 PSHX ; compute next table entry + ADDB #$3 + ABX + STX PTR1 + PULX + CLRB +SRCHLP INCB ; match characters loop + LDAA 1,X ; read table + CMPA 0,Y ; compare to combuff + BNE SRCH1 ; try next entry + INX ; move pointers + INY + CMPB COUNT + BLT SRCHLP ; loop countu1 times + LDX PTR1 + DEX + DEX + LDX 0,X ; jump address from table +EXEC JSR 0,X ; call task as subroutine + JMP MAIN +;* +;***************** +;* UTILITY SUBROUTINES - These routines +;* are called by any of the task routines. +;***************** +;***************** +;* UPCASE(a) - If the contents of A is alpha, +;* returns a converted to uppercase. +;***************** +UPCASE CMPA #'a' + BLT UPCASE1 ; jump if < a + CMPA #'z' + BGT UPCASE1 ; jump if > z + SUBA #$20 ; convert +UPCASE1 RTS + +;***************** +;* BPCLR() - Clear all entries in the +;* table of breakpoints. +;***************** +BPCLR LDX #BRKTABL + LDAB #8 +BPCLR1 CLR 0,X + INX + DECB + BGT BPCLR1 ; loop 8 times + RTS + +;***************** +;* RPRNT1(x) - Prints name and contents of a single +;* user register. On entry X points to name of register +;* in reglist. On exit, a=register name. +;***************** +REGLIST FCC "PYXABCS" ; names + FCB 0,2,4,6,7,8,9 ; offset + FCB 1,1,1,0,0,0,1 ; size +RPRNT1 LDAA 0,X + PSHA + PSHX + JSR OUTPUT ; name + LDAA #'-' + JSR OUTPUT ; dash + LDAB 7,X ; contents offset + LDAA 14,X ; bytesize + LDX #REGS ; address + ABX + TSTA + BEQ RPRN2 ; jump if 1 byte + JSR OUT1BYT ; 2 bytes +RPRN2 JSR OUT1BSP + PULX + PULA + RTS + +;***************** +;* RPRINT() - Print the name and contents +;* of all the user registers. +;***************** +RPRINT PSHX + LDX #REGLIST +RPRI1 JSR RPRNT1 ; print name + INX + CMPA #'S' ; s is last register + BNE RPRI1 ; jump if not done + PULX + RTS + +;***************** +;* HEXBIN(a) - Convert the ASCII character in a +;* to binary and shift into shftreg. Returns value +;* in tmp1 incremented if a is not hex. +;***************** +HEXBIN PSHA + PSHB + PSHX + JSR UPCASE ; convert to upper case + CMPA #'0' + BLT HEXNOT ; jump if a < $30 + CMPA #'9' + BLE HEXNMB ; jump if 0-9 + CMPA #'A' + BLT HEXNOT ; jump if $39> a <$41 + CMPA #'F' + BGT HEXNOT ; jump if a > $46 + ADDA #$9 ; convert $A-$F +HEXNMB ANDA #$0F ; convert to binary + LDX #SHFTREG + LDAB #4 +HEXSHFT ASL 1,X ; 2 byte shift through + ROL 0,X ; carry bit + DECB + BGT HEXSHFT ; shift 4 times + ORAA 1,X + STAA 1,X + BRA HEXRTS +HEXNOT INC TMP1 ; indicate not hex +HEXRTS PULX + PULB + PULA + RTS + +;***************** +;* BUFFARG() - Build a hex argument from the +;* contents of the input buffer. Characters are +;* converted to binary and shifted into shftreg +;* until a non-hex character is found. On exit +;* shftreg holds the last four digits read, count +;* holds the number of digits read, ptrbuff points +;* to the first non-hex character read, and A holds +;* that first non-hex character. +;***************** +;*Initialize +;*while((a=readbuff()) not hex) +;* hexbin(a); +;*return(); + +BUFFARG CLR TMP1 ; not hex indicator + CLR COUNT ; # or digits + CLR SHFTREG + CLR SHFTREG+1 + JSR WSKIP +BUFFLP JSR READBUFF ; read char + JSR HEXBIN + TST TMP1 + BNE BUFFRTS ; jump if not hex + INC COUNT + JSR INCBUFF ; move buffer pointer + BRA BUFFLP +BUFFRTS RTS + +;***************** +;* TERMARG() - Build a hex argument from the +;* terminal. Characters are converted to binary +;* and shifted into shftreg until a non-hex character +;* is found. On exit shftreg holds the last four +;* digits read, count holds the number of digits +;* read, and A holds the first non-hex character. +;***************** +;*initialize +;*while((a=inchar()) == hex) +;* if(a = cntlx or del) +;* abort; +;* else +;* hexbin(a); countu1++; +;*return(); + +TERMARG CLR COUNT + CLR SHFTREG + CLR SHFTREG+1 +TERM0 JSR INCHAR + CMPA #CTLX + BEQ TERM1 ; jump if controlx + CMPA #DEL + BNE TERM2 ; jump if not delete +TERM1 JMP MAIN ; abort +TERM2 CLR TMP1 ; hex indicator + JSR HEXBIN + TST TMP1 + BNE TERM3 ; jump if not hex + INC COUNT + BRA TERM0 +TERM3 RTS + +;***************** +;* CHGBYT() - If shftreg is not empty, put +;* contents of shftreg at address in X. If X +;* is an address in EEPROM then program it. +;***************** +;*if(count != 0) +;* (x) = a; +CHGBYT TST COUNT + BEQ CHGBYT4 ; quit if shftreg empty + LDAA SHFTREG+1 ; get data into a + JSR WRITE +CHGBYT4 RTS + + +;***************** +;* WRITE() - This routine is used to write the +;*contents of A to the address of X. If the +;*address is in EEPROM, it will be programmed +;*and if it is already programmed, it will be +;*byte erased first. +;****************** +;*if(X is eeprom)then +;* if(not erased) then erase; +;* program (x) = A; +;*write (x) = A; +;*if((x) != A) error(rom); +WRITE EQU * + CPX #CONFIG + BEQ WRITE1 ; jump if config + CPX #STREE ; start of EE + BLO WRITE2 ; jump if not EE + CPX #ENDEE ; end of EE + BHI WRITE2 ; jump if not EE +WRITEE PSHB + LDAB 0,X + CMPB #$FF + PULB + BEQ WRITE1 ; jump if erased + JSR EEBYTE ; byte erase +WRITE1 JSR EEWRIT ; byte program +WRITE2 STAA 0,X ; write for non EE + CMPA 0,X + BEQ WRITE3 ; jump if write ok + PSHX + LDX #MSG6 ; "rom" + JSR OUTSTRG + PULX +WRITE3 RTS + + +;***************** +;* EEWRIT(), EEBYTE(), EEBULK() - +;* These routines are used to program and eeprom +;*locations. eewrite programs the address in X with +;*the value in A, eebyte does a byte address at X, +;*and eebulk does a bulk of eeprom. Whether eebulk +;*erases the config or not depends on the address it +;*receives in X. +;**************** +EEWRIT EQU * ; program one byte at x + PSHB + LDAB #$02 + STAB PPROG + STAA 0,X + LDAB #$03 + BRA EEPROG +;*** +EEBYTE EQU * ; byte erase address x + PSHB + LDAB #$16 + STAB PPROG + LDAB #$FF + STAB 0,X + LDAB #$17 + BRA EEPROG +;*** +EEBULK EQU * ; bulk erase eeprom + PSHB + LDAB #$06 + STAB PPROG + LDAB #$FF + STAB 0,X ; erase config or not + LDAB #$07 ; depends on X addr +EEPROG BNE ACL1 + CLRB ; fail safe +ACL1 STAB PPROG + PULB +;*** +DLY10MS EQU * ; delay 10ms at E = 2MHz + PSHX + LDX #$0D06 +DLYLP DEX + BNE DLYLP + PULX + CLR PPROG + RTS + + +;***************** +;* READBUFF() - Read the character in INBUFF +;* pointed at by ptrbuff into A. Returns ptrbuff +;* unchanged. +;***************** +READBUFF PSHX + LDX PTR0 + LDAA 0,X + PULX + RTS + +;***************** +;* INCBUFF(), DECBUFF() - Increment or decrement +;* ptrbuff. +;***************** +INCBUFF PSHX + LDX PTR0 + INX + BRA INCDEC +DECBUFF PSHX + LDX PTR0 + DEX +INCDEC STX PTR0 + PULX + RTS + +;***************** +;* WSKIP() - Read from the INBUFF until a +;* non whitespace (space, comma, tab) character +;* is found. Returns ptrbuff pointing to the +;* first non-whitespace character and a holds +;* that character. WSKIP also compares a to +;* $0D (CR) and cond codes indicating the +;* results of that compare. +;***************** +WSKIP JSR READBUFF ; read character + JSR WCHEK + BNE WSKIP1 ; jump if not wspc + JSR INCBUFF ; move pointer + BRA WSKIP ; loop +WSKIP1 CMPA #$0D + RTS + +;***************** +;* WCHEK(a) - Returns z=1 if a holds a +;* whitespace character, else z=0. +;***************** +WCHEK CMPA #$2C ; comma + BEQ WCHEK1 + CMPA #$20 ; space + BEQ WCHEK1 + CMPA #$09 ; tab +WCHEK1 RTS + +;***************** +;* DCHEK(a) - Returns Z=1 if a = whitespace +;* or carriage return. Else returns z=0. +;***************** +DCHEK JSR WCHEK + BEQ DCHEK1 ; jump if whitespace + CMPA #$0D +DCHEK1 RTS + +;***************** +;* CHKABRT() - Checks for a control x or delete +;* from the terminal. If found, the stack is +;* reset and the control is transferred to main. +;* Note that this is an abnormal termination. +;* If the input from the terminal is a control W +;* then this routine keeps waiting until any other +;* character is read. +;***************** +;*a=input(); +;*if(a=cntl w) wait until any other key; +;*if(a = cntl x or del) abort; + +CHKABRT JSR INPUT + BEQ CHK4 ; jump if no input + CMPA #CTLW + BNE CHK2 ; jump in not cntlw +CHKABRT1 JSR INPUT + BEQ CHKABRT1 ; jump if no input +CHK2 CMPA #DEL + BEQ CHK3 ; jump if delete + CMPA #CTLX + BEQ CHK3 ; jump if control x + CMPA #CTLA + BNE CHK4 ; jump not control a +CHK3 JMP MAIN ; abort +CHK4 RTS ; return + +;*********************** +;* HOSTCO - connect sci to host for evb board. +;* TARGCO - connect sci to target for evb board. +;*********************** +HOSTCO PSHA + LDAA #$01 + STAA DFLOP ; send 1 to d-flop + PULA + RTS + +TARGCO PSHA + LDAA #$00 + STAA DFLOP ; send 0 to d-flop + PULA + RTS + +;* +;********** +;* +;* VECINIT - This routine checks for +;* vectors in the RAM table. All +;* uninitialized vectors are programmed +;* to JMP STOPIT +;* +;********** +;* +VECINIT LDX #JSCI ; Point to First RAM Vector + LDY #STOPIT ; Pointer to STOPIT routine + LDD #$7E03 ; A=JMP opcode; B=offset +VECLOOP CMPA 0,X + BEQ VECNEXT ; If vector already in + STAA 0,X ; install JMP + STY 1,X ; to STOPIT routine +VECNEXT ABX ; Add 3 to point at next vector + CPX #JCLM+3 ; Done? + BNE VECLOOP ; If not, continue loop + RTS +;* +STOPIT LDAA #$50 ; Stop-enable; IRQ, XIRQ-Off + TAP + STOP ; You are lost! Shut down + JMP STOPIT ; In case continue by XIRQ + +;********** +;* +;* I/O MODULE +;* Communications with the outside world. +;* 3 I/O routines (INIT, INPUT, and OUTPUT) call +;* drivers specified by IODEV (0=SCI, 1=ACIA, +;* 2=DUARTA, 3=DUARTB). +;* +;********** +;* INIT() - Initialize device specified by iodev. +;********* +;* +INIT EQU * + PSHA ; save registers + PSHX + LDAA IODEV + CMPA #$00 + BNE INIT1 ; jump not sci + JSR ONSCI ; initialize sci + BRA INIT4 +INIT1 CMPA #$01 + BNE INIT2 ; jump not acia + JSR ONACIA ; initialize acia + BRA INIT4 +INIT2 LDX #PORTA + CMPA #$02 + BEQ INIT3 ; jump duart a + LDX #PORTB +INIT3 JSR ONUART ; initialize duart +INIT4 PULX ; restore registers + PULA + RTS + +;********** +;* INPUT() - Read device. Returns a=char or 0. +;* This routine also disarms the cop. +;********** +INPUT EQU * + PSHX + LDAA #$55 ; reset cop + STAA COPRST + LDAA #$AA + STAA COPRST + LDAA IODEV + BNE INPUT1 ; jump not sci + JSR INSCI ; read sci + BRA INPUT4 +INPUT1 CMPA #$01 + BNE INPUT2 ; jump not acia + JSR INACIA ; read acia + BRA INPUT4 +INPUT2 LDX #PORTA + CMPA #$02 + BEQ INPUT3 ; jump if duart a + LDX #PORTB +INPUT3 JSR INUART ; read uart +INPUT4 PULX + RTS + +;********** +;* OUTPUT() - Output character in A. +;* chrcnt indicates the current column on the +;*output display. It is incremented every time +;*a character is outputted, and cleared whenever +;*the subroutine outcrlf is called. +;********** + +OUTPUT EQU * + PSHA ; save registers + PSHB + PSHX + LDAB IODEV + BNE OUTPUT1 ; jump not sci + JSR OUTSCI ; write sci + BRA OUTPUT4 +OUTPUT1 CMPB #$01 + BNE OUTPUT2 ; jump not acia + JSR OUTACIA ; write acia + BRA OUTPUT4 +OUTPUT2 LDX #PORTA + CMPB #$02 + BEQ OUTPUT3 ; jump if duart a + LDX #PORTB +OUTPUT3 JSR OUTUART ; write uart +OUTPUT4 PULX + PULB + PULA + INC CHRCNT ; increment column count + RTS + +;********** +;* ONUART(port) - Initialize a duart port. +;* Sets duart to internal clock, divide by 16, +;* 8 data + 1 stop bits. +;********** + +ONUART LDAA #$22 + STAA 2,X ; reset receiver + LDAA #$38 + STAA 2,X ; reset transmitter + LDAA #$40 + STAA 2,X ; reset error status + LDAA #$10 + STAA 2,X ; reset pointer + LDAA #$00 + STAA DUART+4 ; clock source + LDAA #$00 + STAA DUART+5 ; interrupt mask + LDAA #$13 + STAA 0,X ; 8 data, no parity + LDAA #$07 + STAA 0,X ; 1 stop bits + LDAA #$BB ; baud rate (9600) + STAA 1,X ; tx and rcv baud rate + LDAA #$05 + STAA 2,X ; enable tx and rcv + RTS + +;********** +;* INUART(port) - Check duart for any input. +;********** +INUART LDAA 1,X ; read status + ANDA #$01 ; check rxrdy + BEQ INUART1 ; jump if no data + LDAA 3,X ; read data + ANDA #$7F ; mask parity +INUART1 RTS + +;********** +;* OUTUART(port) - Output the character in a. +;* if autolf=1, transmits cr or lf as crlf. +;********** +OUTUART TST AUTOLF + BEQ OUTUART2 ; jump if no autolf + BSR OUTUART2 + CMPA #$0D + BNE OUTUART1 + LDAA #$0A ; if cr, output lf + BRA OUTUART2 +OUTUART1 CMPA #$0A + BNE OUTUART3 + LDAA #$0D ; if lf, output cr +OUTUART2 LDAB 1,X ; check status + ANDB #$4 + BEQ OUTUART2 ; loop until tdre=1 + ANDA #$7F ; mask parity + STAA 3,X ; send character +OUTUART3 RTS + +;********** +;* ONSCI() - Initialize the SCI for 9600 +;* baud at 8 MHz Extal. +;********** +ONSCI LDAA #$30 + STAA BAUD ; baud register + LDAA #$00 + STAA SCCR1 + LDAA #$0C + STAA SCCR2 ; enable + RTS + +;********** +;* INSCI() - Read from SCI. Return a=char or 0. +;********** +INSCI LDAA SCSR ; read status reg + ANDA #$20 ; check rdrf + BEQ INSCI1 ; jump if no data + LDAA SCDAT ; read data + ANDA #$7F ; mask parity +INSCI1 RTS + +;********** +;* OUTSCI() - Output A to sci. IF autolf = 1, +;* cr and lf sent as crlf. +;********** +OUTSCI TST AUTOLF + BEQ OUTSCI2 ; jump if autolf=0 + BSR OUTSCI2 + CMPA #$0D + BNE OUTSCI1 + LDAA #$0A ; if cr, send lf + BRA OUTSCI2 +OUTSCI1 CMPA #$0A + BNE OUTSCI3 + LDAA #$0D ; if lf, send cr +OUTSCI2 LDAB SCSR ; read status + BITB #$80 + BEQ OUTSCI2 ; loop until tdre=1 + ANDA #$7F ; mask parity + STAA SCDAT ; send character +OUTSCI3 RTS + +;********** +;* ONACIA - Initialize the ACIA for +;* 8 data bits, 1 stop bit, divide by 64 clock. +;********** +ONACIA LDX #ACIA + LDAA #$03 + STAA 0,X ; master reset + LDAA #$16 + STAA 0,X ; setup + RTS + +;********** +;* INACIA - Read from the ACIA, Return a=char or 0. +;* Tmp3 is used to flag overrun or framing error. +;********** +INACIA LDX #ACIA + LDAA 0,X ; read status register + PSHA + ANDA #$30 ; check ov, fe + PULA + BEQ INACIA1 ; jump - no error + LDAA #$01 + STAA TMP3 ; flag receiver error + BRA INACIA2 ; read data to clear status +INACIA1 ANDA #$01 ; check rdrf + BEQ INACIA3 ; jump if no data +INACIA2 LDAA 1,X ; read data + ANDA #$7F ; mask parity +INACIA3 RTS + +;********** +;* OUTACIA - Output A to acia. IF autolf = 1, +;* cr or lf sent as crlf. +;********** +OUTACIA BSR OUTACIA3 ; output char + TST AUTOLF + BEQ OUTACIA2 ; jump no autolf + CMPA #$0D + BNE OUTACIA1 + LDAA #$0A + BSR OUTACIA3 ; if cr, output lf + BRA OUTACIA2 +OUTACIA1 CMPA #$0A + BNE OUTACIA2 + LDAA #$0D + BSR OUTACIA3 ; if lf, output cr +OUTACIA2 RTS + +OUTACIA3 LDX #ACIA + LDAB 0,X + BITB #$2 + BEQ OUTACIA3 ; loop until tdre + ANDA #$7F ; mask parity + STAA 1,X ; output + RTS +;* +;* Space for modifying OUTACIA routine +;* + FDB $FFFF,$FFFF,$FFFF,$FFFF +;******************************* +;*** I/O UTILITY SUBROUTINES *** +;***These subroutines perform the neccesary +;* data I/O operations. +;* OUTLHLF-Convert left 4 bits of A from binary +;* to ASCII and output. +;* OUTRHLF-Convert right 4 bits of A from binary +;* to ASCII and output. +;* OUT1BYT-Convert byte addresed by X from binary +;* to ASCII and output. +;* OUT1BSP-Convert byte addressed by X from binary +;* to ASCII and output followed by a space. +;* OUT2BSP-Convert 2 bytes addressed by X from binary +;* to ASCII and output followed by a space. +;* OUTSPAC-Output a space. +;* +;* OUTCRLF-Output a line feed and carriage return. +;* +;* OUTSTRG-Output the string of ASCII bytes addressed +;* by X until $04. +;* OUTA-Output the ASCII character in A. +;* +;* TABTO-Output spaces until column 20 is reached. +;* +;* INCHAR-Input to A and echo one character. Loops +;* until character read. +;* ******************* +; +;********** +;* OUTRHLF(), OUTLHLF(), OUTA() +;*Convert A from binary to ASCII and output. +;*Contents of A are destroyed.. +;********** +OUTLHLF LSRA ; shift data to right + LSRA + LSRA + LSRA +OUTRHLF ANDA #$0F ; mask top half + ADDA #$30 ; convert to ascii + CMPA #$39 + BLE OUTA ; jump if 0-9 + ADDA #$07 ; convert to hex A-F +OUTA JSR OUTPUT ; output character + RTS + +;********** +;* OUT1BYT(x) - Convert the byte at X to two +;* ASCII characters and output. Return X pointing +;* to next byte. +;********** +OUT1BYT PSHA + LDAA 0,X ; get data in a + PSHA ; save copy + BSR OUTLHLF ; output left half + PULA ; retrieve copy + BSR OUTRHLF ; output right half + PULA + INX + RTS + +;********** +;* OUT1BSP(x), OUT2BSP(x) - Output 1 or 2 bytes +;* at x followed by a space. Returns x pointing to +;* next byte. +;********** +OUT2BSP JSR OUT1BYT ; do first byte +OUT1BSP JSR OUT1BYT ; do next byte +OUTSPAC LDAA #$20 ; output a space + JSR OUTPUT + RTS + +;********** +;* OUTCRLF() - Output a Carriage return and +;* a line feed. Returns a = cr. +;********** +OUTCRLF LDAA #$0D ; cr + JSR OUTPUT ; output a + LDAA #$00 + JSR OUTPUT ; output padding + LDAA #$0D + CLR CHRCNT ; zero the column counter + RTS + +;********** +;* OUTSTRG(x) - Output string of ASCII bytes +;* starting at x until end of text ($04). Can +;* be paused by control w (any char restarts). +;********** +OUTSTRG JSR OUTCRLF +OUTSTRG0 PSHA +OUTSTRG1 LDAA 0,X ; read char into a + CMPA #EOT + BEQ OUTSTRG3 ; jump if eot + JSR OUTPUT ; output character + INX + JSR INPUT + BEQ OUTSTRG1 ; jump if no input + CMPA #CTLW + BNE OUTSTRG1 ; jump if not cntlw +OUTSTRG2 JSR INPUT + BEQ OUTSTRG2 ; jump if any input + BRA OUTSTRG1 +OUTSTRG3 PULA + RTS + + +;********* +;* TABTO() - move cursor over to column 20. +;*while(chrcnt < 16) outspac. +TABTO EQU * + PSHA +TABTOLP JSR OUTSPAC + LDAA CHRCNT + CMPA #20 + BLE TABTOLP + PULA + RTS + +;********** +;* INCHAR() - Reads input until character sent. +;* Echoes char and returns with a = char. +INCHAR JSR INPUT + TSTA + BEQ INCHAR ; jump if no input + JSR OUTPUT ; echo + RTS + +;********************* +;*** COMMAND TABLE *** +COMTABL EQU * + FCB 5 + FCC "ASSEM" + FDB ASSEM + FCB 5 + FCC "BREAK" + FDB BREAK + FCB 4 + FCC "BULK" + FDB BULK + FCB 7 + FCC "BULKALL" + FDB BULKALL + FCB 4 + FCC "CALL" + FDB CALL + FCB 4 + FCC "DUMP" + FDB DUMP + FCB 4 + FCC "FILL" + FDB FILL + FCB 2 + FCC "GO" + FDB GO + FCB 4 + FCC "HELP" + FDB HELP + FCB 4 + FCC "HOST" + FDB HOST + FCB 4 + FCC "LOAD" + FDB LOAD + FCB 6 ; LENGTH OF COMMAND + FCC "MEMORY" ; ASCII COMMAND + FDB MEMORY ; COMMAND ADDRESS + FCB 4 + FCC "MOVE" + FDB MOVE + FCB 7 + FCC "PROCEED" + FDB PROCEED + FCB 8 + FCC "REGISTER" + FDB REGISTER + FCB 6 + FCC "STOPAT" + FDB STOPAT + FCB 5 + FCC "TRACE" + FDB TRACE + FCB 6 + FCC "VERIFY" + FDB VERIFY + FCB 1 + FCC "?" ; initial command + FDB HELP + FCB 5 + FCC "XBOOT" + FDB BOOT +;* +;*** Command names for evm compatability *** +;* + FCB 3 + FCC "ASM" + FDB ASSEM + FCB 2 + FCC "BF" + FDB FILL + FCB 4 + FCC "COPY" + FDB MOVE + FCB 5 + FCC "ERASE" + FDB BULK + FCB 2 + FCC "MD" + FDB DUMP + FCB 2 + FCC "MM" + FDB MEMORY + FCB 2 + FCC "RD" + FDB REGISTER + FCB 2 + FCC "RM" + FDB REGISTER + FCB 4 + FCC "READ" + FDB MOVE + FCB 2 + FCC "TM" + FDB HOST + FCB 4 + FCC "TEST" + FDB EVBTEST + FCB $FF + +;******************* +;*** TEXT TABLES *** + +MSG1 FCC "BUFFALO 3.2 (int) - Bit User Fast Friendly Aid to Logical Operation" + FCB EOT +MSG2 FCC "What?" + FCB EOT +MSG3 FCC "Too Long" + FCB EOT +MSG4 FCC "Full" + FCB EOT +MSG5 FCC "Op- " + FCB EOT +MSG6 FCC "rom-" + FCB EOT +MSG8 FCC "Command?" + FCB EOT +MSG9 FCC "Bad argument" + FCB EOT +MSG10 FCC "No host port available" + FCB EOT +MSG11 FCC "done" + FCB EOT +MSG12 FCC "checksum error" + FCB EOT +MSG13 FCC "error addr " + FCB EOT +MSG14 FCC "receiver error" + FCB EOT + +;********** +;* break [-][] . . . +;* Modifies the breakpoint table. More than +;* one argument can be entered on the command +;* line but the table will hold only 4 entries. +;* 4 types of arguments are implied above: +;* break Prints table contents. +;* break Inserts . +;* break - Deletes . +;* break - Clears all entries. +;********** +;* while 1 +;* a = wskip(); +;* switch(a) +;* case(cr): +;* bprint(); return; + +BREAK JSR WSKIP + BNE BRKDEL ; jump if not cr + JSR BPRINT ; print table + RTS + +;* case("-"): +;* incbuff(); readbuff(); +;* if(dchek(a)) /* look for wspac or cr */ +;* bpclr(); +;* breaksw; +;* a = buffarg(); +;* if( !dchek(a) ) return(bad argument); +;* b = bpsrch(); +;* if(b >= 0) +;* brktabl[b] = 0; +;* breaksw; + +BRKDEL CMPA #'-' + BNE BRKDEF ; jump if not - + JSR INCBUFF + JSR READBUFF + JSR DCHEK + BNE BRKDEL1 ; jump if not delimeter + JSR BPCLR ; clear table + JMP BREAK ; do next argument +BRKDEL1 JSR BUFFARG ; get address to delete + JSR DCHEK + BEQ BRKDEL2 ; jump if delimeter + LDX #MSG9 ; "bad argument" + JSR OUTSTRG + RTS +BRKDEL2 JSR BPSRCH ; look for addr in table + TSTB + BMI BRKDEL3 ; jump if not found + LDX #BRKTABL + ABX + CLR 0,X ; clear entry + CLR 1,X +BRKDEL3 JMP BREAK ; do next argument + +;* default: +;* a = buffarg(); +;* if( !dchek(a) ) return(bad argument); +;* b = bpsrch(); +;* if(b < 0) /* not already in table */ +;* x = shftreg; +;* shftreg = 0; +;* a = x[0]; x[0] = $3F +;* b = x[0]; x[0] = a; +;* if(b != $3F) return(rom); +;* b = bpsrch(); /* look for hole */ +;* if(b >= 0) return(table full); +;* brktabl[b] = x; +;* breaksw; + +BRKDEF JSR BUFFARG ; get argument + JSR DCHEK + BEQ BRKDEF1 ; jump if delimiter + LDX #MSG9 ; "bad argument" + JSR OUTSTRG + RTS +BRKDEF1 JSR BPSRCH ; look for entry in table + TSTB + BGE BREAK ; jump if already in table + + LDX SHFTREG ; x = new entry addr + LDAA 0,X ; save original contents + PSHA + LDAA #SWI + JSR WRITE ; write to entry addr + LDAB 0,X ; read back + PULA + JSR WRITE ; restore original + CMPB #SWI + BEQ BRKDEF2 ; jump if writes ok + STX PTR1 ; save address + LDX #PTR1 + JSR OUT2BSP ; print address + JSR BPRINT + RTS +BRKDEF2 CLR SHFTREG + CLR SHFTREG+1 + PSHX + JSR BPSRCH ; look for 0 entry + PULX + TSTB + BPL BRKDEF3 ; jump if table not full + LDX #MSG4 ; "full" + JSR OUTSTRG + JSR BPRINT + RTS +BRKDEF3 LDY #BRKTABL + ABY + STX 0,Y ; put new entry in + JMP BREAK ; do next argument + +;********** +;* bprint() - print the contents of the table. +;********** +BPRINT JSR OUTCRLF + LDX #BRKTABL + LDAB #4 +BPRINT1 JSR OUT2BSP + DECB + BGT BPRINT1 ; loop 4 times + RTS + +;********** +;* bpsrch() - search table for address in +;* shftreg. Returns b = index to entry or +;* b = -1 if not found. +;********** +;*for(b=0; b=6; b=+2) +;* x[] = brktabl + b; +;* if(x[0] = shftreg) +;* return(b); +;*return(-1); + +BPSRCH CLRB +BPSRCH1 LDX #BRKTABL + ABX + LDX 0,X ; get table entry + CPX SHFTREG + BNE BPSRCH2 ; jump if no match + RTS +BPSRCH2 INCB + INCB + CMPB #$6 + BLE BPSRCH1 ; loop 4 times + LDAB #$FF + RTS + + +;********** +;* bulk - Bulk erase the eeprom not config. +;* bulkall - Bulk erase eeprom and config. +;********* +BULK EQU * + LDX #$B600 + BRA BULK1 +BULKALL LDX #CONFIG +BULK1 LDAA #$FF + JSR EEBULK + RTS + + + +;********** +;* dump [ []] - Dump memory +;* in 16 byte lines from to . +;* Default starting address is "current +;* location" and default number of lines is 8. +;********** +;*ptr1 = ptrmem; /* default start address */ +;*ptr2 = ptr1 + $80; /* default end address */ +;*a = wskip(); +;*if(a != cr) +;* a = buffarg(); +;* if(countu1 = 0) return(bad argument); +;* if( !dchek(a) ) return(bad argument); +;* ptr1 = shftreg; +;* ptr2 = ptr1 + $80; /* default end address */ +;* a = wskip(); +;* if(a != cr) +;* a = buffarg(); +;* if(countu1 = 0) return(bad argument); +;* a = wskip(); +;* if(a != cr) return(bad argument); +;* ptr2 = shftreg; + +DUMP LDX PTRMEM ; current location + STX PTR1 ; default start + LDAB #$80 + ABX + STX PTR2 ; default end + JSR WSKIP + BEQ DUMP1 ; jump - no arguments + JSR BUFFARG ; read argument + TST COUNT + BEQ DUMPERR ; jump if no argument + JSR DCHEK + BNE DUMPERR ; jump if delimiter + LDX SHFTREG + STX PTR1 + LDAB #$80 + ABX + STX PTR2 ; default end address + JSR WSKIP + BEQ DUMP1 ; jump - 1 argument + JSR BUFFARG ; read argument + TST COUNT + BEQ DUMPERR ; jump if no argument + JSR WSKIP + BNE DUMPERR ; jump if not cr + LDX SHFTREG + STX PTR2 + BRA DUMP1 ; jump - 2 arguments +DUMPERR LDX #MSG9 ; "bad argument" + JSR OUTSTRG + RTS + +;*ptrmem = ptr1; +;*ptr1 = ptr1 & $fff0; + +DUMP1 LDD PTR1 + STD PTRMEM ; new current location + ANDB #$F0 + STD PTR1 ; start dump at 16 byte boundary + +;*** dump loop starts here *** +;*do: +;* output address of first byte; + +DUMPLP JSR OUTCRLF + LDX #PTR1 + JSR OUT2BSP ; first address + +;* x = ptr1; +;* for(b=0; b=16; b++) +;* output contents; + + LDX PTR1 ; base address + CLRB ; loop counter +DUMPDAT JSR OUT1BSP ; hex value loop + INCB + CMPB #$10 + BLT DUMPDAT ; loop 16 times + +;* x = ptr1; +;* for(b=0; b=16; b++) +;* a = x[b]; +;* if($7A < a < $20) a = $20; +;* output ascii contents; + + CLRB ; loop counter +DUMPASC LDX PTR1 ; base address + ABX + LDAA ,X ; ascii value loop + CMPA #$20 + BLO DUMP3 ; jump if non printable + CMPA #$7A + BLS DUMP4 ; jump if printable +DUMP3 LDAA #$20 ; space for non printables +DUMP4 JSR OUTPUT ; output ascii value + INCB + CMPB #$10 + BLT DUMPASC ; loop 16 times + +;* chkabrt(); +;* ptr1 = ptr1 + $10; +;*while(ptr1 <= ptr2); +;*return; + + JSR CHKABRT ; check abort or wait + LDD PTR1 + ADDD #$10 ; point to next 16 byte bound + STD PTR1 ; update ptr1 + CPD PTR2 + BHI DUMP5 ; quit if ptr1 > ptr2 + CPD #$00 ; check wraparound at $ffff + BNE DUMPLP ; jump - no wraparound + LDD PTR2 + CPD #$FFF0 + BLO DUMPLP ; upper bound not at top +DUMP5 RTS ; quit + + + +;********** +;* fill [] - Block fill +;*memory from addr1 to addr2 with data. Data +;*defaults to $FF. +;********** +;*get addr1 and addr2 +FILL EQU * + JSR WSKIP + JSR BUFFARG + TST COUNT + BEQ FILLERR ; jump if no argument + JSR WCHEK + BNE FILLERR ; jump if bad argument + LDX SHFTREG + STX PTR1 ; address1 + JSR WSKIP + JSR BUFFARG + TST COUNT + BEQ FILLERR ; jump if no argument + JSR DCHEK + BNE FILLERR ; jump if bad argument + LDX SHFTREG + STX PTR2 ; address2 + +;*Get data if it exists + LDAA #$FF + STAA TMP2 ; default data + JSR WSKIP + BEQ FILL1 ; jump if default data + JSR BUFFARG + TST COUNT + BEQ FILLERR ; jump if no argument + JSR WSKIP + BNE FILLERR ; jump if bad argument + LDAA SHFTREG+1 + STAA TMP2 + +;*while(ptr1 <= ptr2) +;* *ptr1 = data +;* if(*ptr1 != data) abort + +FILL1 EQU * + JSR CHKABRT ; check for abort + LDX PTR1 ; starting address + LDAA TMP2 ; data + JSR WRITE ; write the data to x + CMPA 0,X + BNE FILLBAD ; jump if no write + CPX PTR2 + BEQ FILL2 ; quit yet? + INX + STX PTR1 + BRA FILL1 ; loop +FILL2 RTS + +FILLERR LDX #MSG9 ; "bad argument" + JSR OUTSTRG + RTS + +FILLBAD EQU * + LDX #PTR1 ; output bad address + JSR OUT2BSP + RTS + + + +;********** +;* call [] - Execute a jsr to or user +;*pc value. Return to monitor via rts or breakpoint. +;********** +;*a = wskip(); +;*if(a != cr) +;* a = buffarg(); +;* a = wskip(); +;* if(a != cr) return(bad argument) +;* pc = shftreg; +CALL JSR WSKIP + BEQ CALL3 ; jump if no arg + JSR BUFFARG + JSR WSKIP + BEQ CALL2 ; jump if cr + LDX #MSG9 ; "bad argument" + JSR OUTSTRG + RTS +CALL2 LDX SHFTREG + STX REGS ; pc = + +;*put return address on user stack +;*setbps(); +;*restack(); /* restack and go*/ +CALL3 LDX SP + DEX ; user stack pointer + LDD #RETURN ; return address + STD 0,X + DEX + STX SP ; new user stack pointer + JSR SETBPS + CLR TMP2 ; 1=go, 0=call + JMP RESTACK ; go to user code + +;********** +;* return() - Return here from rts after +;*call command. +;********** +RETURN PSHA ; save a register + TPA + STAA REGS+8 ; cc register + PULA + STD REGS+6 ; a and b registers + STX REGS+4 ; x register + STY REGS+2 ; y register + STS SP ; user stack pointer + LDS PTR2 ; monitor stack pointer + JSR REMBPS ; remove breakpoints + JSR OUTCRLF + JSR RPRINT ; print user registers + RTS + + +;********** +;* proceed - Same as go except it ignores +;*a breakpoint at the first opcode. Calls +;*runone for the first instruction only. +;********** +PROCEED EQU * + JSR RUNONE ; run one instruction + JSR CHKABRT ; check for abort + CLR TMP2 ; flag for breakpoints + INC TMP2 ; 1=go 0=call + JSR SETBPS + JMP RESTACK ; go execute + +;********** +;* go [] - Execute starting at or +;*user's pc value. Executes an rti to user code. +;*Returns to monitor via an swi through swiin. +;********** +;*a = wskip(); +;*if(a != cr) +;* a = buffarg(); +;* a = wskip(); +;* if(a != cr) return(bad argument) +;* pc = shftreg; +;*setbps(); +;*restack(); /* restack and go*/ +GO JSR WSKIP + BEQ GO2 ; jump if no arg + JSR BUFFARG + JSR WSKIP + BEQ GO1 ; jump if cr + LDX #MSG9 ; "bad argument" + JSR OUTSTRG + RTS +GO1 LDX SHFTREG + STX REGS ; pc = +GO2 CLR TMP2 + INC TMP2 ; 1=go, 0=call + JSR SETBPS + JMP RESTACK ; go to user code + +;***** +;** SWIIN - Breakpoints from go or call commands enter here. +;*Remove breakpoints, save user registers, return +SWIIN EQU * ; swi entry point + TSX ; user sp -> x + LDS PTR2 ; restore monitor sp + JSR SAVSTACK ; save user regs + JSR REMBPS ; remove breakpoints from code + LDX REGS + DEX + STX REGS ; save user pc value + +;*if(call command) remove call return addr from user stack; + TST TMP2 ; 1=go, 0=call + BNE GO3 ; jump if go command + LDX SP ; remove return address + INX ; user stack pointer + INX + STX SP +GO3 JSR OUTCRLF ; print register values + JSR RPRINT + RTS ; done + +;********** +;* setbps - Replace user code with swi's at +;*breakpoint addresses. +;********** +;*for(b=0; b=6; b =+ 2) +;* x = brktabl[b]; +;* if(x != 0) +;* optabl[b] = x[0]; +;* x[0] = $3F; +;*Put monitor SWI vector into jump table + +SETBPS CLRB +SETBPS1 LDX #BRKTABL + LDY #PTR4 + ABX + ABY + LDX 0,X ; breakpoint table entry + BEQ SETBPS2 ; jump if 0 + LDAA 0,X ; save user opcode + STAA 0,Y + LDAA #SWI + JSR WRITE ; insert swi into code +SETBPS2 ADDB #$2 + CMPB #$6 + BLE SETBPS1 ; loop 4 times + LDX JSWI+1 + STX PTR3 ; save user swi vector + LDAA #$7E ; jmp opcode + STAA JSWI + LDX #SWIIN + STX JSWI+1 ; monitor swi vector + RTS + +;********** +;* rembps - Remove breakpoints from user code. +;********** +;*for(b=0; b=6; b =+ 2) +;* x = brktabl[b]; +;* if(x != 0) +;* x[0] = optabl[b]; +;*Replace user's SWI vector +REMBPS CLRB +REMBPS1 LDX #BRKTABL + LDY #PTR4 + ABX + ABY + LDX 0,X ; breakpoint table entry + BEQ REMBPS2 ; jump if 0 + LDAA 0,Y + JSR WRITE ; restore user opcode +REMBPS2 ADDB #$2 + CMPB #$6 + BLE REMBPS1 ; loop 4 times + LDX PTR3 ; restore user swi vector + STX JSWI+1 + RTS + + +;********** +;* trace - Trace n instructions starting +;*at user's pc value. n is a hex number less than +;*$FF (defaults to 1). +;********** +;*a = wskip(); +;*if(a != cr) +;* a = buffarg(); a = wskip(); +;* if(a != cr) return(bad argument); +;* countt1 = n +TRACE CLR TMP4 + INC TMP4 ; default count=1 + CLR CHRCNT ; set up for display + JSR WSKIP + BEQ TRACE2 ; jump if cr + JSR BUFFARG + JSR WSKIP + BEQ TRACE1 ; jump if cr + LDX #MSG9 ; "bad argument" + JSR OUTSTRG + RTS +TRACE1 LDAA SHFTREG+1 ; n + STAA TMP4 + +;*Disassemble the line about to be traced +TRACE2 EQU * + LDAB TMP4 + PSHB + LDX REGS + STX PTR1 ; pc value for disass + JSR DISASSM + PULB + STAB TMP4 + +;*run one instruction +;*rprint(); +;*while(count > 0) continue trace; + JSR RUNONE + JSR CHKABRT ; check for abort + JSR TABTO ; print registers for + JSR RPRINT ; result of trace + DEC TMP4 + BEQ TRACDON ; quit if count=0 +TRACE3 JSR OUTCRLF + BRA TRACE2 +TRACDON RTS + + +;********** +;* stopat - Trace instructions until +;*is reached. +;********** +;*if((a=wskip) != cr) +;* a = buffarg(); a = wskip(); +;* if(a != cr) return(bad argument); +;*else return(bad argument); +STOPAT EQU * + JSR WSKIP + BEQ STOPGO ; jump if cr - no argument + JSR BUFFARG + JSR WSKIP + BEQ STOPAT1 ; jump if cr + LDX #MSG9 ; "bad argument" + JSR OUTSTRG + RTS +STOPAT1 TST COUNT + BEQ STOPGO ; jump if no argument + LDX SHFTREG + STX PTRMEM ; update "current location" + +;*while(!(ptrmem <= userpc < ptrmem+10)) runone(); +;*rprint(); +STOPGO LDD REGS ; userpc + CPD PTRMEM + BLO STOPNEXT ; if(userpc < ptrmem) runone + LDD PTRMEM + ADDD #10 + CPD REGS + BHI STOPDON ; quit if ptrmem+10 > userpc +STOPNEXT JSR RUNONE + JSR CHKABRT ; check for abort + BRA STOPGO +STOPDON JSR OUTCRLF + JSR RPRINT ; result of trace + RTS ; done + + +;************************* +;* runone - This routine is used by the trace and +;* execute commands to run one only one user instruction. +;* Control is passed to the user code via an RTI. OC5 +;* is then used to trigger an XIRQ as soon as the first user +;* opcode is fetched. Control then returns to the monitor +;* through XIRQIN. +;* Externally, the OC5 pin must be wired to the XIRQ pin. +;************************ +;* Disable oc5 interrupts +;* Put monitor XIRQ vector into jump table +;* Unmask x bit in user ccr +;* Setup OC5 to go low when first user instruction executed +RUNONE EQU * + LDAA #$7E ; put "jmp xirqin" in jump table + STAA JTOC5 + LDX #XIRQIN + STX JXIRQ+1 + LDAA REGS+8 ; x bit will be cleared when + ANDA #$BF ; rti is executed below + STAA REGS+8 + LDAB #87 ; cycles to end of rti + LDX TCNT + ABX ; 3~ \ + STX TOC5 ; oc5 match register 5~ \ + LDAA TCTL1 ; 4~ \ + ANDA #$FE ; set up oc5 low on match 2~ \ + STAA TCTL1 ; enable oc5 interrupt 4~ / 86~ + +;** RESTACK - Restore user stack and RTI to user code. +;* This code is the pathway to execution of user code. +;*(Force extended addressing to maintain cycle count) +;*Restore user stack and rti to user code +RESTACK EQU * ; 68~ + STS >PTR2 ; save monitor sp + LDS >SP ; user stack pointer + LDX >REGS + PSHX ; pc + LDX >REGS+2 + PSHX ; y + LDX >REGS+4 + PSHX ; x + LDD >REGS+6 + PSHA ; a + PSHB ; b + LDAA >REGS+8 + PSHA ; ccr + RTI + +;** Return here from run one line of user code. +XIRQIN EQU * + TSX ; user sp -> x + LDS PTR2 ; restore monitor sp + +;** SAVSTACK - Save user's registers. +;* On entry - x points to top of user stack. +SAVSTACK EQU * + LDAA 0,X + STAA REGS+8 ; user ccr + LDD 1,X + STAA REGS+7 ; b + STAB REGS+6 ; a + LDD 3,X + STD REGS+4 ; x + LDD 5,X + STD REGS+2 ; y + LDD 7,X + STD REGS ; pc + LDAB #8 + ABX + STX SP ; user stack pointer + LDAA TCTL1 ; force oc5 pin high which + ORAA #$03 ; is tied to xirq line + STAA TCTL1 + LDAA #$08 + STAA CFORC + RTS + + +;********** +;* help - List buffalo commands to terminal. +;********** +HELP EQU * + LDX #HELPMSG1 + JSR OUTSTRG ; print help screen + RTS + +HELPMSG1 EQU * + FCC "ASM [] Line assembler/disassembler." + FCB $0D + FCC " / Do same address. ^ Do previous address." + FCB $0D + FCC " CTRL-J Do next address. RETURN Do next opcode." + FCB $0D + FCC " CTRL-A Quit." + FCB $0D + FCC "BF [] Block fill." + FCB $0D + FCC "BR [-][] Set up breakpoint table." + FCB $0D + FCC "BULK Erase the EEPROM. BULKALL Erase EEPROM and CONFIG." + FCB $0D + FCC "CALL [] Call user subroutine. G [] Execute user code." + FCB $0D + FCC "LOAD, VERIFY [T] Load or verify S-records." + FCB $0D + FCC "MD [ []] Memory dump." + FCB $0D + FCC "MM [] Memory modify." + FCB $0D + FCC " / Open same address. CTRL-H or ^ Open previous address." + FCB $0D + FCC " CTRL-J Open next address. SPACE Open next address." + FCB $0D + FCC " RETURN Quit. O Compute offset to ." + FCB $0D + FCC "MOVE [] Block move." + FCB $0D + FCC "P Proceed/continue execution." + FCB $0D + FCC "RM [P, Y, X, A, B, C, or S] Register modify." + FCB $0D + FCC "T [] Trace n instructions." + FCB $0D + FCC "TM Transparent mode (CTRL-A = exit, CTRL-B = send break)." + FCB $0D + FCC "CTRL-H Backspace. CTRL-W Wait for any key." + FCB $0D + FCC "CTRL-X or DELETE Abort/cancel command." + FCB $0D + FCC "RETURN Repeat last command." + FCB 4 + +;********** +;* HOST() - Establishes transparent link between +;* terminal and host. Port used for host is +;* determined in the reset initialization routine +;* and stored in HOSTDEV. +;* To exit type control A. +;* To send break to host type control B. +;*if(no external device) return; +;*initialize host port; +;*While( !(control A)) +;* input(terminal); output(host); +;* input(host); output(terminal); + +HOST LDAA EXTDEV + BNE HOST0 ; jump if host port avail. + LDX #MSG10 ; "no host port avail" + JSR OUTSTRG + RTS +HOST0 CLR AUTOLF ; turn off autolf + JSR HOSTCO ; connect sci (evb board) + JSR HOSTINIT ; initialize host port +HOST1 JSR INPUT ; read terminal + TSTA + BEQ HOST3 ; jump if no char + CMPA #CTLA + BEQ HOSTEND ; jump if control a + CMPA #CTLB + BNE HOST2 ; jump if not control b + JSR TXBREAK ; send break to host + BRA HOST3 +HOST2 JSR HOSTOUT ; echo to host +HOST3 JSR HOSTIN ; read host + TSTA + BEQ HOST1 ; jump if no char + JSR OUTPUT ; echo to terminal + BRA HOST1 +HOSTEND INC AUTOLF ; turn on autolf + JSR TARGCO ; disconnect sci (evb board) + RTS ; return + +;********** +;* txbreak() - transmit break to host port. +;* The duration of the transmitted break is +;* approximately 200,000 E-clock cycles, or +;* 100ms at 2.0 MHz. +;*********** +TXBREAK EQU * + LDAA HOSTDEV + CMPA #$03 + BEQ TXBDU ; jump if duartb is host + +TXBSCI LDX #SCCR2 ; sci is host + BSET 0,X,#01 ; set send break bit + BSR TXBWAIT + BCLR 0,X,#01 ; clear send break bit + BRA TXB1 + +TXBDU LDX #PORTB ; duart host port + LDAA #$60 ; start break cmd + STAA 2,X ; port b command register + BSR TXBWAIT + LDAA #$70 ; stop break cmd + STAA 2,X ; port b command register + +TXB1 LDAA #$0D + JSR HOSTOUT ; send carriage return + LDAA #$0A + JSR HOSTOUT ; send linefeed + RTS + +TXBWAIT LDY #$6F9B ; loop count = 28571 +TXBWAIT1 DEY ; 7 cycle loop + BNE TXBWAIT1 + RTS + + +;********** +;* hostinit(), hostin(), hostout() - host i/o +;*routines. Restores original terminal device. +;********** +HOSTINIT LDAB IODEV ; save terminal + PSHB + LDAB HOSTDEV + STAB IODEV ; point to host + JSR INIT ; initialize host + BRA TERMRES ; restore terminal +HOSTIN LDAB IODEV ; save terminal + PSHB + LDAB HOSTDEV + STAB IODEV ; point to host + JSR INPUT ; read host + BRA TERMRES ; restore terminal +HOSTOUT LDAB IODEV ; save terminal + PSHB + LDAB HOSTDEV + STAB IODEV ; point to host + JSR OUTPUT ; write to host +TERMRES PULB ; restore terminal device + STAB IODEV + RTS + + +;********** +;* load(ptrbuff[]) - Load s1/s9 records from +;*host to memory. Ptrbuff[] points to string in +;*input buffer which is a command to output s1/s9 +;*records from the host ("cat filename" for unix). +;* Returns error and address if it can't write +;*to a particular location. +;********** +;* verify(ptrbuff[]) - Verify memory from load +;*command. Ptrbuff[] is same as for load. +;* tmp3 is used as an error indication, 0=no errors, +;* 1=receiver, 2=rom error, 3=checksum error. +;********** +VERIFY CLR TMP2 + INC TMP2 ; TMP2=1=verify + BRA LOAD1 +LOAD CLR TMP2 ; 0=load + +;*a=wskip(); +;*if(a = cr) goto transparent mode; +;*if(t option) hostdev = iodev; +LOAD1 CLR TMP3 ; clear error flag + JSR WSKIP + BNE LOAD2 + JMP HOST ; go to host if no args +LOAD2 JSR UPCASE + CMPA #'T' ; look for t option + BNE LOAD3 ; jump not t option + JSR INCBUFF + JSR READBUFF ; get next character + JSR DECBUFF + CMPA #$0D + BNE LOAD3 ; jump if not t option + CLR AUTOLF + LDAA IODEV + STAA HOSTDEV ; set host port = terminal + BRA LOAD10 ; go wait for s1 records + +;*else while(not cr) +;* read character from input buffer; +;* send character to host; +LOAD3 CLR AUTOLF + JSR HOSTCO ; connect sci (evb board) + JSR HOSTINIT ; initialize host port +LOAD4 JSR READBUFF ; get next char + JSR INCBUFF + PSHA ; save char + JSR HOSTOUT ; output to host + JSR OUTPUT ; echo to terminal + PULA + CMPA #$0D + BNE LOAD4 ; jump if not cr + +;*repeat: /* look for s records */ +;* if(hostdev != iodev) check abort; +;* a = hostin(); +;* if(a = 'S') +;* a = hostin; +;* if(a = '1') +;* checksum = 0; +;* get byte count in b; +;* get base address in x; +;* while(byte count > 0) +;* byte(); +;* x++; b--; +;* if(tmp3=0) /* no error */ +;* if(load) x[0] = shftreg+1; +;* if(x[0] != shftreg+1) +;* tmp3 = 2; /* rom error */ +;* ptr3 = x; /* save address */ +;* if(tmp3 = 0) do checksum; +;* if(checksum err) tmp3 = 3; /* checksum error */ +LOAD10 EQU * + LDAA HOSTDEV + CMPA IODEV + BEQ LOAD11 ; jump if hostdev=iodev + JSR CHKABRT ; check for abort +LOAD11 JSR HOSTIN ; read host + TSTA + BEQ LOAD10 ; jump if no input + CMPA #'S' + BNE LOAD10 ; jump if not S +LOAD12 JSR HOSTIN ; read host + TSTA + BEQ LOAD12 ; jump if no input + CMPA #'9' + BEQ LOAD90 ; jump if S9 record + CMPA #'1' + BNE LOAD10 ; jump if not S1 + CLR TMP4 ; clear checksum + JSR BYTE + LDAB SHFTREG+1 + SUBB #$2 ; b = byte count + JSR BYTE + JSR BYTE + LDX SHFTREG ; x = base address + DEX +LOAD20 JSR BYTE ; get next byte + INX + DECB ; check byte count + BEQ LOAD30 ; if b=0, go do checksum + TST TMP3 + BNE LOAD10 ; jump if error flagged + TST TMP2 + BNE LOAD21 ; jump if verify + LDAA SHFTREG+1 + JSR WRITE ; load only +LOAD21 CMPA 0,X ; verify ram location + BEQ LOAD20 ; jump if ram ok + LDAA #$02 + STAA TMP3 ; indicate rom error + STX PTR3 ; save error address + BRA LOAD20 ; finish download + +;* calculate checksum +LOAD30 TST TMP3 + BNE LOAD10 ; jump if error already + LDAA TMP4 + INCA ; do checksum + BEQ LOAD10 ; jump if s1 record okay + LDAA #$03 + STAA TMP3 ; indicate checksum error + BRA LOAD10 + +;* if(a = '9') +;* read rest of record; +;* if(tmp3=2) return("[ptr3]"); +;* if(tmp3=1) return("rcv error"); +;* if(tmp3=3) return("checksum err"); +;* else return("done"); +LOAD90 JSR BYTE + LDAB SHFTREG+1 ; b = byte count +LOAD91 JSR BYTE + DECB + BNE LOAD91 ; loop until end of record + INC AUTOLF ; turn on autolf + JSR TARGCO ; disconnect sci (evb) + LDX #MSG11 ; "done" default msg + LDAA TMP3 + CMPA #$02 + BNE LOAD92 ; jump not rom error + LDX #PTR3 + JSR OUT2BSP ; address of rom error + BRA LOAD95 +LOAD92 CMPA #$01 + BNE LOAD93 ; jump not rcv error + LDX #MSG14 ; "rcv error" + BRA LOAD94 +LOAD93 CMPA #$03 + BNE LOAD94 ; jump not checksum error + LDX #MSG12 ; "checksum error" +LOAD94 JSR OUTSTRG +LOAD95 RTS + + +;********** +;* byte() - Read 2 ascii bytes from host and +;*convert to one hex byte. Returns byte +;*shifted into shftreg and added to tmp4. +;********** +BYTE PSHB + PSHX +BYTE0 JSR HOSTIN ; read host (1st byte) + TSTA + BEQ BYTE0 ; loop until input + JSR HEXBIN +BYTE1 JSR HOSTIN ; read host (2nd byte) + TSTA + BEQ BYTE1 ; loop until input + JSR HEXBIN + LDAA SHFTREG+1 + ADDA TMP4 + STAA TMP4 ; add to checksum + PULX + PULB + RTS + + +;******************************************* +;* MEMORY [] +;* []/ +;* Opens memory and allows user to modify the +;*contents at or the last opened location. +;* Subcommands: +;* [] - Close current location and exit. +;* [] - Close current and open next. +;* []<^> - Close current and open previous. +;* [] - Close current and open next. +;* []/ - Reopen current location. +;* The contents of the current location is only +;* changed if valid data is entered before each +;* subcommand. +;* []O - Compute relative offset from current +;* location to . The current location must +;* be the address of the offset byte. +;********** +;*a = wskip(); +;*if(a != cr) +;* a = buffarg(); +;* if(a != cr) return(bad argument); +;* if(countu1 != 0) ptrmem[] = shftreg; + +MEMORY JSR WSKIP + BEQ MEM1 ; jump if cr + JSR BUFFARG + JSR WSKIP + BEQ MSLASH ; jump if cr + LDX #MSG9 ; "bad argument" + JSR OUTSTRG + RTS +MSLASH TST COUNT + BEQ MEM1 ; jump if no argument + LDX SHFTREG + STX PTRMEM ; update "current location" + +;********** +;* Subcommands +;********** +;*outcrlf(); +;*out2bsp(ptrmem[]); +;*out1bsp(ptrmem[0]); + +MEM1 JSR OUTCRLF +MEM2 LDX #PTRMEM + JSR OUT2BSP ; output address +MEM3 LDX PTRMEM + JSR OUT1BSP ; output contents + CLR SHFTREG + CLR SHFTREG+1 +;*while 1 +;*a = termarg(); +;* switch(a) +;* case(space): +;* chgbyt(); +;* ptrmem[]++; +;* case(linefeed): +;* chgbyt(); +;* ptrmem[]++; +;* case(up arrow): +;* case(backspace): +;* chgbyt(); +;* ptrmem[]--; +;* case("/"): +;* chgbyt(); +;* outcrlf(); +;* case(O): +;* d = ptrmem[0] - (shftreg); +;* if($80 < d < $ff81) +;* print(out of range); +;* countt1 = d-1; +;* out1bsp(countt1); +;* case(carriage return): +;* chgbyt(); +;* return; +;* default: return(command?) + +MEM4 JSR TERMARG + JSR UPCASE + LDX PTRMEM + CMPA #$20 + BEQ MEMSP ; jump if space + CMPA #$0A + BEQ MEMLF ; jump if linefeed + CMPA #$5E + BEQ MEMUA ; jump if up arrow + CMPA #$08 + BEQ MEMBS ; jump if backspace + CMPA #'/' + BEQ MEMSL ; jump if / + CMPA #'O' + BEQ MEMOFF ; jump if O + CMPA #$0D + BEQ MEMCR ; jump if carriage ret + LDX #MSG8 ; "command?" + JSR OUTSTRG + JMP MEM1 +MEMSP JSR CHGBYT + INX + STX PTRMEM + JMP MEM3 ; output contents +MEMLF JSR CHGBYT + INX + STX PTRMEM + JMP MEM2 ; output addr, contents +MEMUA EQU * +MEMBS JSR CHGBYT + DEX + STX PTRMEM + JMP MEM1 ; output cr, addr, contents +MEMSL JSR CHGBYT + JMP MEM1 ; output cr, addr, contents +MEMOFF LDD SHFTREG ; destination addr + SUBD PTRMEM + CMPA #$0 + BNE MEMOFF1 ; jump if not 0 + CMPB #$80 + BLS MEMOFF3 ; jump if in range + BRA MEMOFF2 ; out of range +MEMOFF1 CMPA #$FF + BNE MEMOFF2 ; out of range + CMPB #$81 + BHS MEMOFF3 ; in range +MEMOFF2 LDX #MSG3 ; "Too long" + JSR OUTSTRG + JMP MEM1 ; output cr, addr, contents +MEMOFF3 SUBD #$1 ; b now has offset + STAB TMP4 + JSR OUTSPAC + LDX #TMP4 + JSR OUT1BSP ; output offset + JMP MEM1 ; output cr, addr, contents +MEMCR JSR CHGBYT + RTS ; exit task + + +;********** +;* move [] - move +;*block at to to . +;* Moves block 1 byte up if no . +;********** +;*a = buffarg(); +;*if(countu1 = 0) return(bad argument); +;*if( !wchek(a) ) return(bad argument); +;*ptr1 = shftreg; /* src1 */ + +MOVE EQU * + JSR BUFFARG + TST COUNT + BEQ MOVERR ; jump if no arg + JSR WCHEK + BNE MOVERR ; jump if no delim + LDX SHFTREG ; src1 + STX PTR1 + +;*a = buffarg(); +;*if(countu1 = 0) return(bad argument); +;*if( !dchek(a) ) return(bad argument); +;*ptr2 = shftreg; /* src2 */ + + JSR BUFFARG + TST COUNT + BEQ MOVERR ; jump if no arg + JSR DCHEK + BNE MOVERR ; jump if no delim + LDX SHFTREG ; src2 + STX PTR2 + +;*a = buffarg(); +;*a = wskip(); +;*if(a != cr) return(bad argument); +;*if(countu1 != 0) tmp2 = shftreg; /* dest */ +;*else tmp2 = ptr1 + 1; + + JSR BUFFARG + JSR WSKIP + BNE MOVERR ; jump if not cr + TST COUNT + BEQ MOVE1 ; jump if no arg + LDX SHFTREG ; dest + BRA MOVE2 +MOVERR LDX #MSG9 ; "bad argument" + JSR OUTSTRG + RTS + +MOVE1 LDX PTR1 + INX ; default dest +MOVE2 STX PTR3 + +;*if(src1 < dest <= src2) +;* dest = dest+(src2-src1); +;* for(x = src2; x = src1; x--) +;* dest[0]-- = x[0]--; + LDX PTR3 ; dest + CPX PTR1 ; src1 + BLS MOVE3 ; jump if dest =< src1 + CPX PTR2 ; src2 + BHI MOVE3 ; jump if dest > src2 + LDD PTR2 + SUBD PTR1 + ADDD PTR3 + STD PTR3 ; dest = dest+(src2-src1) + LDX PTR2 +MOVELP1 JSR CHKABRT ; check for abort + LDAA ,X ; char at src2 + PSHX + LDX PTR3 + JSR WRITE ; write a to x + CMPA 0,X + BNE MOVEBAD ; jump if no write + DEX + STX PTR3 + PULX + CPX PTR1 + BEQ MOVRTS + DEX + BRA MOVELP1 ; Loop SRC2 - SRC1 times +;* +;* else +;* for(x=src1; x=src2; x++) +;* dest[0]++ = x[0]++; + + +MOVE3 LDX PTR1 ; srce1 +MOVELP2 JSR CHKABRT ; check for abort + LDAA ,X + PSHX + LDX PTR3 ; dest + JSR WRITE ; write a to x + CMPA 0,X + BNE MOVEBAD ; jump if no write + INX + STX PTR3 + PULX + CPX PTR2 + BEQ MOVRTS + INX + BRA MOVELP2 ; Loop SRC2-SRC1 times +MOVRTS RTS + +MOVEBAD LDX #PTR3 + JSR OUT2BSP ; output bad address + RTS + +;********** +;* register [] - prints the user regs +;*and opens them for modification. is +;*the first register opened (default = P). +;* Subcommands: +;* [] Opens the next register. +;* [] Return. +;* The register value is only changed if +;* is entered before the subcommand. +;********** +;*x[] = reglist +;*a = wskip(); a = upcase(a); +;*if(a != cr) +;* while( a != x[0] ) +;* if( x[0] = "s") return(bad argument); +;* x[]++; +;* incbuff(); a = wskip(); +;* if(a != cr) return(bad argument); + +REGISTER LDX #REGLIST + JSR WSKIP ; a = first char of arg + JSR UPCASE ; convert to upper case + CMPA #$D + BEQ REG4 ; jump if no argument +REG1 CMPA 0,X + BEQ REG3 + LDAB 0,X + INX + CMPB #'S' + BNE REG1 ; jump if not "s" +REG2 LDX #MSG9 ; "bad argument" + JSR OUTSTRG + RTS +REG3 PSHX + JSR INCBUFF + JSR WSKIP ; next char after arg + PULX + BNE REG2 ; jump if not cr + +;*rprint(); +;* while(x[0] != "s") +;* rprnt1(x); +;* a = termarg(); /* read from terminal */ +;* if( ! dchek(a) ) return(bad argument); +;* if(countu1 != 0) +;* if(x[14] = 1) +;* regs[x[7]++ = shftreg; +;* regs[x[7]] = shftreg+1; +;* if(a = cr) break; +;*return; + +REG4 JSR RPRINT ; print all registers +REG5 JSR OUTCRLF + JSR RPRNT1 ; print reg name + CLR SHFTREG + CLR SHFTREG+1 + JSR TERMARG ; read subcommand + JSR DCHEK + BEQ REG6 ; jump if delimeter + LDX #MSG9 ; "bad argument" + JSR OUTSTRG + RTS +REG6 PSHA + PSHX + TST COUNT + BEQ REG8 ; jump if no input + LDAB 7,X ; get reg offset + LDAA 14,X ; byte size + LDX #REGS ; user registers + ABX + TSTA + BEQ REG7 ; jump if 1 byte reg + LDAA SHFTREG + STAA 0,X ; put in top byte + INX +REG7 LDAA SHFTREG+1 + STAA 0,X ; put in bottom byte +REG8 PULX + PULA + LDAB 0,X ; CHECK FOR REGISTER S + CMPB #'S' + BEQ REG9 ; jump if "s" + INX ; point to next register + CMPA #$D + BNE REG5 ; jump if not cr +REG9 RTS + +PAGE1 EQU $00 ; values for page opcodes +PAGE2 EQU $18 +PAGE3 EQU $1A +PAGE4 EQU $CD +IMMED EQU $0 ; addressing modes +INDX EQU $1 +INDY EQU $2 +LIMMED EQU $3 ; (long immediate) +OTHER EQU $4 + +;*** Rename variables for assem/disassem *** +AMODE EQU TMP2 ; addressing mode +YFLAG EQU TMP3 +PNORM EQU TMP4 ; page for normal opcode +OLDPC EQU PTR8 +PC EQU PTR1 ; program counter +PX EQU PTR2 ; page for x indexed +PY EQU PTR2+1 ; page for y indexed +BASEOP EQU PTR3 ; base opcode +CLASS EQU PTR3+1 ; class +DISPC EQU PTR4 ; pc for disassembler +BRADDR EQU PTR5 ; relative branch offset +MNEPTR EQU PTR6 ; pointer to table for dis +ASSCOMM EQU PTR7 ; subcommand for assembler + +;*** Error messages for assembler *** +MSGDIR FDB MSGA1 ; message table index + FDB MSGA2 + FDB MSGA3 + FDB MSGA4 + FDB MSGA5 + FDB MSGA6 + FDB MSGA7 + FDB MSGA8 + FDB MSGA9 +MSGA1 FCC "Immediate mode illegal" + FCB EOT +MSGA2 FCC "Error in mnemonic table" + FCB EOT +MSGA3 FCC "Illegal bit op" + FCB EOT +MSGA4 FCC "Bad argument" + FCB EOT +MSGA5 FCC "Mnemonic not found" + FCB EOT +MSGA6 FCC "Unknown addressing mode" + FCB EOT +MSGA7 FCC "Indexed addressing assumed" + FCB EOT +MSGA8 FCC "Syntax error" + FCB EOT +MSGA9 FCC "Branch out of range" + FCB EOT + +;**************** +;* assem(addr) -68HC11 line assembler/disassembler. +;* This routine will disassemble the opcode at +;* and then allow the user to enter a line for +;*assembly. Rules for assembly are as follows: +;* -A '#' sign indicates immediate addressing. +;* -A ',' (comma) indicates indexed addressing +;* and the next character must be X or Y. +;* -All arguments are assumed to be hex and the +;* '$' sign shouldn't be used. +;* -Arguments should be separated by 1 or more +;* spaces or tabs. +;* -Any input after the required number of +;* arguments is ignored. +;* -Upper or lower case makes no difference. +;* +;* To signify end of input line, the following +;*commands are available and have the indicated action: +;* -Carriage return finds the next opcode for +;* assembly. If there was no assembly input, +;* the next opcode disassembled is retrieved +;* from the disassembler. +;* -Linefeed works the same as carriage return +;* except if there was no assembly input, the +;* is incremented and the next is +;* disassembled. +;* '^' -Up arrow decrements and the previous +;* address is then disassembled. +;* '/' -Slash redisassembles the current address. +;* +;* To exit the assembler use CONTROL A. Of course +;*control X and DEL will also allow you to abort. +;********** +;*oldpc = rambase; +;*a = wskip(); +;*if (a != cr) +;* buffarg() +;* a = wskip(); +;* if ( a != cr ) return(error); +;* oldpc = a; + +ASSEM EQU * + LDX #RAMBS + STX OLDPC + JSR WSKIP + BEQ ASSLOOP ; jump if no argument + JSR BUFFARG + JSR WSKIP + BEQ ASSEM1 ; jump if argument ok + LDX #MSGA4 ; "bad argument" + JSR OUTSTRG + RTS +ASSEM1 LDX SHFTREG + STX OLDPC + +;*repeat +;* pc = oldpc; +;* out2bsp(pc); +;* disassem(); +;* a=readln(); +;* asscomm = a; /* save command */ +;* if(a == ('^' or '/')) outcrlf; +;* if(a == 0) return(error); + +ASSLOOP LDX OLDPC + STX PC + JSR OUTCRLF + LDX #PC + JSR OUT2BSP ; output the address + JSR DISASSM ; disassemble opcode + JSR TABTO + LDAA #PROMPT ; prompt user + JSR OUTA ; output prompt character + JSR READLN ; read input for assembly + STAA ASSCOMM + CMPA #'^' + BEQ ASSLP0 ; jump if up arrow + CMPA #'/' + BEQ ASSLP0 ; jump if slash + CMPA #$00 + BNE ASSLP1 ; jump if none of above + RTS ; return if bad input +ASSLP0 JSR OUTCRLF +ASSLP1 EQU * + JSR OUTSPAC + JSR OUTSPAC + JSR OUTSPAC + JSR OUTSPAC + JSR OUTSPAC + +;* b = parse(input); /* get mnemonic */ +;* if(b > 5) print("not found"); asscomm='/'; +;* elseif(b >= 1) +;* msrch(); +;* if(class==$FF) +;* print("not found"); asscomm='/'; +;* else +;* a = doop(opcode,class); +;* if(a == 0) dispc=0; +;* else process error; asscomm='/'; + + JSR PARSE + CMPB #$5 + BLE ASSLP2 ; jump if mnemonic <= 5 chars + LDX #MSGA5 ; "mnemonic not found" + JSR OUTSTRG + BRA ASSLP5 +ASSLP2 EQU * + CMPB #$0 + BEQ ASSLP10 ; jump if no input + JSR MSRCH + LDAA CLASS + CMPA #$FF + BNE ASSLP3 + LDX #MSGA5 ; "mnemonic not found" + JSR OUTSTRG + BRA ASSLP5 +ASSLP3 JSR DOOP + CMPA #$00 + BNE ASSLP4 ; jump if doop error + LDX #$00 + STX DISPC ; indicate good assembly + BRA ASSLP10 +ASSLP4 DECA ; a = error message index + TAB + LDX #MSGDIR + ABX + ABX + LDX 0,X + JSR OUTSTRG ; output error message +ASSLP5 CLR ASSCOMM ; error command + +;* /* compute next address - asscomm holds subcommand +;* and dispc indicates if valid assembly occured. */ +;* if(asscomm=='^') oldpc -= 1; +;* if(asscomm==(lf or cr) +;* if(dispc==0) oldpc=pc; +;* else +;* if(asscomm==lf) dispc=oldpc+1; +;* oldpc=dispc; +;*until(eot) + + +ASSLP10 EQU * + LDAA ASSCOMM + CMPA #'^' + BNE ASSLP11 ; jump if not up arrow + LDX OLDPC + DEX + STX OLDPC ; back up + BRA ASSLP15 +ASSLP11 CMPA #$0A + BEQ ASSLP12 ; jump if linefeed + CMPA #$0D + BNE ASSLP15 ; jump if not cr +ASSLP12 LDX DISPC + BNE ASSLP13 ; jump if dispc != 0 + LDX PC + STX OLDPC + BRA ASSLP15 +ASSLP13 CMPA #$0A + BNE ASSLP14 ; jump if not linefeed + LDX OLDPC + INX + STX DISPC +ASSLP14 LDX DISPC + STX OLDPC +ASSLP15 JMP ASSLOOP + +;**************** +;* readln() --- Read input from terminal into buffer +;* until a command character is read (cr,lf,/,^). +;* If more chars are typed than the buffer will hold, +;* the extra characters are overwritten on the end. +;* On exit: b=number of chars read, a=0 if quit, +;* else a=next command. +;**************** +;*for(b==0;b<=bufflng;b++) inbuff[b] = cr; + +READLN CLRB + LDAA #$0D ; carriage ret +RLN0 LDX #INBUFF + ABX + STAA 0,X ; initialize input buffer + INCB + CMPB #BUFFLNG + BLT RLN0 +;*b=0; +;*repeat +;* if(a == (ctla, cntlc, cntld, cntlx, del)) +;* return(a=0); +;* if(a == backspace) +;* if(b > 0) b--; +;* else b=0; +;* else inbuff[b] = upcase(a); +;* if(b < bufflng) b++; +;*until (a == (cr,lf,^,/)) +;*return(a); + + CLRB +RLN1 JSR INCHAR + CMPA #DEL ; Delete + BEQ RLNQUIT + CMPA #CTLX ; Control X + BEQ RLNQUIT + CMPA #CTLA ; Control A + BEQ RLNQUIT + CMPA #$03 ; Control C + BEQ RLNQUIT + CMPA #$04 ; Control D + BEQ RLNQUIT + CMPA #$08 ; backspace + BNE RLN2 + DECB + BGT RLN1 + BRA READLN ; start over +RLN2 LDX #INBUFF + ABX + JSR UPCASE + STAA 0,X ; put char in buffer + CMPB #BUFFLNG ; max buffer length + BGE RLN3 ; jump if buffer full + INCB ; move buffer pointer +RLN3 JSR ASSCHEK ; check for subcommand + BNE RLN1 + RTS +RLNQUIT CLRA ; quit + RTS ; return + + +;********** +;* parse() -parse out the mnemonic from INBUFF +;* to COMBUFF. on exit: b=number of chars parsed. +;********** +;*combuff[3] = ; initialize 4th character to space. +;*ptrbuff[] = inbuff[]; +;*a=wskip(); +;*for (b = 0; b = 5; b++) +;* a=readbuff(); incbuff(); +;* if (a = (cr,lf,^,/,wspace)) return(b); +;* combuff[b] = upcase(a); +;*return(b); + +PARSE LDAA #$20 + STAA COMBUFF+3 + LDX #INBUFF ; initialize buffer ptr + STX PTR0 + JSR WSKIP ; find first character + CLRB +PARSLP JSR READBUFF ; read character + JSR INCBUFF + JSR WCHEK + BEQ PARSRT ; jump if whitespace + JSR ASSCHEK + BEQ PARSRT ; jump if end of line + JSR UPCASE ; convert to upper case + LDX #COMBUFF + ABX + STAA 0,X ; store in combuff + INCB + CMPB #$5 + BLE PARSLP ; loop 6 times +PARSRT RTS + + +;**************** +;* asschek() -perform compares for +;* cr, lf, ^, / +;**************** +ASSCHEK CMPA #$0A ; linefeed + BEQ ASSCHK1 + CMPA #$0D ; carriage ret + BEQ ASSCHK1 + CMPA #'^' ; up arrow + BEQ ASSCHK1 + CMPA #'/' ; slash +ASSCHK1 RTS + + +;********* +;* msrch() --- Search MNETABL for mnemonic in COMBUFF. +;*stores base opcode at baseop and class at class. +;* Class = FF if not found. +;********** +;*while ( != EOF ) +;* if (COMBUFF[0-3] = MNETABL[0-3]) +;* return(MNETABL[4],MNETABL[5]); +;* else *MNETABL =+ 6 + +MSRCH LDX #MNETABL ; pointer to mnemonic table + LDY #COMBUFF ; pointer to string + BRA MSRCH1 +MSNEXT EQU * + LDAB #6 + ABX ; point to next table entry +MSRCH1 LDAA 0,X ; read table + CMPA #EOT + BNE MSRCH2 ; jump if not end of table + LDAA #$FF + STAA CLASS ; FF = not in table + RTS +MSRCH2 CMPA 0,Y ; op[0] = tabl[0] ? + BNE MSNEXT + LDAA 1,X + CMPA 1,Y ; op[1] = tabl[1] ? + BNE MSNEXT + LDAA 2,X + CMPA 2,Y ; op[2] = tabl[2] ? + BNE MSNEXT + LDAA 3,X + CMPA 3,Y ; op[2] = tabl[2] ? + BNE MSNEXT + LDD 4,X ; opcode, class + STAA BASEOP + STAB CLASS + RTS + +;********** +;** doop(baseop,class) --- process mnemonic. +;** on exit: a=error code corresponding to error +;** messages. +;********** +;*amode = OTHER; /* addressing mode */ +;*yflag = 0; /* ynoimm, nlimm, and cpd flag */ +;*x[] = ptrbuff[] + +DOOP EQU * + LDAA #OTHER + STAA AMODE ; mode + CLR YFLAG + LDX PTR0 + +;*while (*x != end of buffer) +;* if (x[0]++ == ',') +;* if (x[0] == 'y') amode = INDY; +;* else amod = INDX; +;* break; +;*a = wskip() +;*if( a == '#' ) amode = IMMED; + +DOPLP1 CPX #ENDBUFF ; (end of buffer) + BEQ DOOP1 ; jump if end of buffer + LDD 0,X ; read 2 chars from buffer + INX ; move pointer + CMPA #',' + BNE DOPLP1 + CMPB #'Y' ; look for ",y" + BNE DOPLP2 + LDAA #INDY + STAA AMODE + BRA DOOP1 +DOPLP2 CMPB #'X' ; look for ",x" + BNE DOOP1 ; jump if not x + LDAA #INDX + STAA AMODE + BRA DOOP1 +DOOP1 JSR WSKIP + CMPA #'#' ; look for immediate mode + BNE DOOP2 + JSR INCBUFF ; point at argument + LDAA #IMMED + STAA AMODE +DOOP2 EQU * + +;*switch(class) + LDAB CLASS + CMPB #P2INH + BNE DOSW1 + JMP DOP2I +DOSW1 CMPB #INH + BNE DOSW2 + JMP DOINH +DOSW2 CMPB #REL + BNE DOSW3 + JMP DOREL +DOSW3 CMPB #LIMM + BNE DOSW4 + JMP DOLIM +DOSW4 CMPB #NIMM + BNE DOSW5 + JMP DONOI +DOSW5 CMPB #GEN + BNE DOSW6 + JMP DOGENE +DOSW6 CMPB #GRP2 + BNE DOSW7 + JMP DOGRP +DOSW7 CMPB #CPD + BNE DOSW8 + JMP DOCPD +DOSW8 CMPB #XNIMM + BNE DOSW9 + JMP DOXNOI +DOSW9 CMPB #XLIMM + BNE DOSW10 + JMP DOXLI +DOSW10 CMPB #YNIMM + BNE DOSW11 + JMP DOYNOI +DOSW11 CMPB #YLIMM + BNE DOSW12 + JMP DOYLI +DOSW12 CMPB #BTB + BNE DOSW13 + JMP DOBTB +DOSW13 CMPB #SETCLR + BNE DODEF + JMP DOSET + +;* default: return("error in mnemonic table"); + +DODEF LDAA #$2 + RTS + +;* case P2INH: emit(PAGE2) + +DOP2I LDAA #PAGE2 + JSR EMIT + +;* case INH: emit(baseop); +;* return(0); + +DOINH LDAA BASEOP + JSR EMIT + CLRA + RTS + +;* case REL: a = assarg(); +;* if(a=4) return(a); +;* d = address - pc + 2; +;* if ($7f >= d >= $ff82) +;* return (out of range); +;* emit(opcode); +;* emit(offset); +;* return(0); + +DOREL JSR ASSARG + CMPA #$04 + BNE DOREL1 ; jump if arg ok + RTS +DOREL1 LDD SHFTREG ; get branch address + LDX PC ; get program counter + INX + INX ; point to end of opcode + STX BRADDR + SUBD BRADDR ; calculate offset + STD BRADDR ; save result + CPD #$7F ; in range ? + BLS DOREL2 ; jump if in range + CPD #$FF80 + BHS DOREL2 ; jump if in range + LDAA #$09 ; 'Out of range' + RTS +DOREL2 LDAA BASEOP + JSR EMIT ; emit opcode + LDAA BRADDR+1 + JSR EMIT ; emit offset + CLRA ; normal return + RTS + +;* case LIMM: if (amode == IMMED) amode = LIMMED; + +DOLIM LDAA AMODE + CMPA #IMMED + BNE DONOI + LDAA #LIMMED + STAA AMODE + +;* case NIMM: if (amode == IMMED) +;* return("Immediate mode illegal"); + +DONOI LDAA AMODE + CMPA #IMMED + BNE DOGENE ; jump if not immediate + LDAA #$1 ; "immediate mode illegal" + RTS + +;* case GEN: dogen(baseop,amode,PAGE1,PAGE1,PAGE2); +;* return; + +DOGENE LDAA #PAGE1 + STAA PNORM + STAA PX + LDAA #PAGE2 + STAA PY + JSR DOGEN + RTS + +;* case GRP2: if (amode == INDY) +;* emit(PAGE2); +;* amode = INDX; +;* if( amode == INDX ) +;* doindx(baseop); +;* else a = assarg(); +;* if(a=4) return(a); +;* emit(opcode+0x10); +;* emit(extended address); +;* return; + +DOGRP LDAA AMODE + CMPA #INDY + BNE DOGRP1 + LDAA #PAGE2 + JSR EMIT + LDAA #INDX + STAA AMODE +DOGRP1 EQU * + LDAA AMODE + CMPA #INDX + BNE DOGRP2 + JSR DOINDEX + RTS +DOGRP2 EQU * + LDAA BASEOP + ADDA #$10 + JSR EMIT + JSR ASSARG + CMPA #$04 + BEQ DOGRPRT ; jump if bad arg + LDD SHFTREG ; extended address + JSR EMIT + TBA + JSR EMIT + CLRA +DOGRPRT RTS + +;* case CPD: if (amode == IMMED) +;* amode = LIMMED; /* cpd */ +;* if( amode == INDY ) yflag = 1; +;* dogen(baseop,amode,PAGE3,PAGE3,PAGE4); +;* return; + +DOCPD LDAA AMODE + CMPA #IMMED + BNE DOCPD1 + LDAA #LIMMED + STAA AMODE +DOCPD1 LDAA AMODE + CMPA #INDY + BNE DOCPD2 + INC YFLAG +DOCPD2 LDAA #PAGE3 + STAA PNORM + STAA PX + LDAA #PAGE4 + STAA PY + JSR DOGEN + RTS + +;* case XNIMM: if (amode == IMMED) /* stx */ +;* return("Immediate mode illegal"); + +DOXNOI LDAA AMODE + CMPA #IMMED + BNE DOXLI + LDAA #$1 ; "immediate mode illegal" + RTS + +;* case XLIMM: if (amode == IMMED) /* cpx, ldx */ +;* amode = LIMMED; +;* dogen(baseop,amode,PAGE1,PAGE1,PAGE4); +;* return; + +DOXLI LDAA AMODE + CMPA #IMMED + BNE DOXLI1 + LDAA #LIMMED + STAA AMODE +DOXLI1 LDAA #PAGE1 + STAA PNORM + STAA PX + LDAA #PAGE4 + STAA PY + JSR DOGEN + RTS + +;* case YNIMM: if (amode == IMMED) /* sty */ +;* return("Immediate mode illegal"); + +DOYNOI LDAA AMODE + CMPA #IMMED + BNE DOYLI + LDAA #$1 ; "immediate mode illegal" + RTS + +;* case YLIMM: if (amode == INDY) yflag = 1;/* cpy, ldy */ +;* if(amode == IMMED) amode = LIMMED; +;* dogen(opcode,amode,PAGE2,PAGE3,PAGE2); +;* return; + +DOYLI LDAA AMODE + CMPA #INDY + BNE DOYLI1 + INC YFLAG +DOYLI1 CMPA #IMMED + BNE DOYLI2 + LDAA #LIMMED + STAA AMODE +DOYLI2 LDAA #PAGE2 + STAA PNORM + STAA PY + LDAA #PAGE3 + STAA PX + JSR DOGEN + RTS + +;* case BTB: /* bset, bclr */ +;* case SETCLR: a = bitop(baseop,amode,class); +;* if(a=0) return(a = 3); +;* if( amode == INDY ) +;* emit(PAGE2); +;* amode = INDX; + +DOBTB EQU * +DOSET JSR BITOP + CMPA #$00 + BNE DOSET1 + LDAA #$3 ; "illegal bit op" + RTS +DOSET1 LDAA AMODE + CMPA #INDY + BNE DOSET2 + LDAA #PAGE2 + JSR EMIT + LDAA #INDX + STAA AMODE +DOSET2 EQU * + +;* emit(baseop); +;* a = assarg(); +;* if(a = 4) return(a); +;* emit(index offset); +;* if( amode == INDX ) +;* Buffptr += 2; /* skip ,x or ,y */ + + LDAA BASEOP + JSR EMIT + JSR ASSARG + CMPA #$04 + BNE DOSET22 ; jump if arg ok + RTS +DOSET22 LDAA SHFTREG+1 ; index offset + JSR EMIT + LDAA AMODE + CMPA #INDX + BNE DOSET3 + JSR INCBUFF + JSR INCBUFF +DOSET3 EQU * + +;* a = assarg(); +;* if(a = 4) return(a); +;* emit(mask); /* mask */ +;* if( class == SETCLR ) +;* return; + + JSR ASSARG + CMPA #$04 + BNE DOSET33 ; jump if arg ok + RTS +DOSET33 LDAA SHFTREG+1 ; mask + JSR EMIT + LDAA CLASS + CMPA #SETCLR + BNE DOSET4 + CLRA + RTS +DOSET4 EQU * + +;* a = assarg(); +;* if(a = 4) return(a); +;* d = (pc+1) - shftreg; +;* if ($7f >= d >= $ff82) +;* return (out of range); +;* emit(branch offset); +;* return(0); + + JSR ASSARG + CMPA #$04 + BNE DOSET5 ; jump if arg ok + RTS +DOSET5 LDX PC ; program counter + INX ; point to next inst + STX BRADDR ; save pc value + LDD SHFTREG ; get branch address + SUBD BRADDR ; calculate offset + CPD #$7F + BLS DOSET6 ; jump if in range + CPD #$FF80 + BHS DOSET6 ; jump if in range + CLRA + JSR EMIT + LDAA #$09 ; 'out of range' + RTS +DOSET6 TBA ; offset + JSR EMIT + CLRA + RTS + + +;********** +;** bitop(baseop,amode,class) --- adjust opcode on bit +;** manipulation instructions. Returns opcode in a +;** or a = 0 if error +;********** +;*if( amode == INDX || amode == INDY ) return(op); +;*if( class == SETCLR ) return(op-8); +;*else if(class==BTB) return(op-12); +;*else fatal("bitop"); + +BITOP EQU * + LDAA AMODE + LDAB CLASS + CMPA #INDX + BNE BITOP1 + RTS +BITOP1 CMPA #INDY + BNE BITOP2 ; jump not indexed + RTS +BITOP2 CMPB #SETCLR + BNE BITOP3 ; jump not bset,bclr + LDAA BASEOP ; get opcode + SUBA #8 + STAA BASEOP + RTS +BITOP3 CMPB #BTB + BNE BITOP4 ; jump not bit branch + LDAA BASEOP ; get opcode + SUBA #12 + STAA BASEOP + RTS +BITOP4 CLRA ; 0 = fatal bitop + RTS + +;********** +;** dogen(baseop,mode,pnorm,px,py) - process +;** general addressing modes. Returns a = error #. +;********** +;*pnorm = page for normal addressing modes: IMM,DIR,EXT +;*px = page for INDX addressing +;*py = page for INDY addressing +;*switch(amode) +DOGEN LDAA AMODE + CMPA #LIMMED + BEQ DOGLIM + CMPA #IMMED + BEQ DOGIMM + CMPA #INDY + BEQ DOGINDY + CMPA #INDX + BEQ DOGINDX + CMPA #OTHER + BEQ DOGOTH + +;*default: error("Unknown Addressing Mode"); + +DOGDEF LDAA #$06 ; unknown addre... + RTS + +;*case LIMMED: epage(pnorm); +;* emit(baseop); +;* a = assarg(); +;* if(a = 4) return(a); +;* emit(2 bytes); +;* return(0); + +DOGLIM LDAA PNORM + JSR EPAGE +DOGLIM1 LDAA BASEOP + JSR EMIT + JSR ASSARG ; get next argument + CMPA #$04 + BNE DOGLIM2 ; jump if arg ok + RTS +DOGLIM2 LDD SHFTREG + JSR EMIT + TBA + JSR EMIT + CLRA + RTS + +;*case IMMED: epage(pnorm); +;* emit(baseop); +;* a = assarg(); +;* if(a = 4) return(a); +;* emit(lobyte); +;* return(0); + +DOGIMM LDAA PNORM + JSR EPAGE + LDAA BASEOP + JSR EMIT + JSR ASSARG + CMPA #$04 + BNE DOGIMM1 ; jump if arg ok + RTS +DOGIMM1 LDAA SHFTREG+1 + JSR EMIT + CLRA + RTS + +;*case INDY: epage(py); +;* a=doindex(op+0x20); +;* return(a); + +DOGINDY LDAA PY + JSR EPAGE + LDAA BASEOP + ADDA #$20 + STAA BASEOP + JSR DOINDEX + RTS + +;*case INDX: epage(px); +;* a=doindex(op+0x20); +;* return(a); + +DOGINDX LDAA PX + JSR EPAGE + LDAA BASEOP + ADDA #$20 + STAA BASEOP + JSR DOINDEX + RTS + +;*case OTHER: a = assarg(); +;* if(a = 4) return(a); +;* epage(pnorm); +;* if(countu1 <= 2 digits) /* direct */ +;* emit(op+0x10); +;* emit(lobyte(Result)); +;* return(0); +;* else emit(op+0x30); /* extended */ +;* eword(Result); +;* return(0) + +DOGOTH JSR ASSARG + CMPA #$04 + BNE DOGOTH0 ; jump if arg ok + RTS +DOGOTH0 LDAA PNORM + JSR EPAGE + LDAA COUNT + CMPA #$2 + BGT DOGOTH1 + LDAA BASEOP + ADDA #$10 ; direct mode opcode + JSR EMIT + LDAA SHFTREG+1 + JSR EMIT + CLRA + RTS +DOGOTH1 LDAA BASEOP + ADDA #$30 ; extended mode opcode + JSR EMIT + LDD SHFTREG + JSR EMIT + TBA + JSR EMIT + CLRA + RTS + +;********** +;** doindex(op) --- handle all wierd stuff for +;** indexed addressing. Returns a = error number. +;********** +;*emit(baseop); +;*a=assarg(); +;*if(a = 4) return(a); +;*if( a != ',' ) return("Syntax"); +;*buffptr++ +;*a=readbuff() +;*if( a != 'x' && != 'y') warn("Ind Addr Assumed"); +;*emit(lobyte); +;*return(0); + +DOINDEX LDAA BASEOP + JSR EMIT + JSR ASSARG + CMPA #$04 + BNE DOINDX0 ; jump if arg ok + RTS +DOINDX0 CMPA #',' + BEQ DOINDX1 + LDAA #$08 ; "syntax error" + RTS +DOINDX1 JSR INCBUFF + JSR READBUFF + CMPA #'Y' + BEQ DOINDX2 + CMPA #'X' + BEQ DOINDX2 + LDX MSGA7 ; "index addr assumed" + JSR OUTSTRG +DOINDX2 LDAA SHFTREG+1 + JSR EMIT + CLRA + RTS + +;********** +;** assarg(); - get argument. Returns a = 4 if bad +;** argument, else a = first non hex char. +;********** +;*a = buffarg() +;*if(asschk(aa) && countu1 != 0) return(a); +;*return(bad argument); + +ASSARG JSR BUFFARG + JSR ASSCHEK ; check for command + BEQ ASSARG1 ; jump if ok + JSR WCHEK ; check for whitespace + BNE ASSARG2 ; jump if not ok +ASSARG1 TST COUNT + BEQ ASSARG2 ; jump if no argument + RTS +ASSARG2 LDAA #$04 ; bad argument + RTS + +;********** +;** epage(a) --- emit page prebyte +;********** +;*if( a != PAGE1 ) emit(a); + +EPAGE CMPA #PAGE1 + BEQ EPAGRT ; jump if page 1 + JSR EMIT +EPAGRT RTS + +;********** +;* emit(a) --- emit contents of a +;********** +EMIT LDX PC + JSR WRITE ; write a to x + JSR OUT1BSP + STX PC + RTS + +;*Mnemonic table for hc11 line assembler +NULL EQU $0 ; nothing +INH EQU $1 ; inherent +P2INH EQU $2 ; page 2 inherent +GEN EQU $3 ; general addressing +GRP2 EQU $4 ; group 2 +REL EQU $5 ; relative +IMM EQU $6 ; immediate +NIMM EQU $7 ; general except for immediate +LIMM EQU $8 ; 2 byte immediate +XLIMM EQU $9 ; longimm for x +XNIMM EQU $10 ; no immediate for x +YLIMM EQU $11 ; longimm for y +YNIMM EQU $12 ; no immediate for y +BTB EQU $13 ; bit test and branch +SETCLR EQU $14 ; bit set or clear +CPD EQU $15 ; compare d +BTBD EQU $16 ; bit test and branch direct +SETCLRD EQU $17 ; bit set or clear direct + +;********** +;* mnetabl - includes all '11 mnemonics, base opcodes, +;* and type of instruction. The assembler search routine +;*depends on 4 characters for each mnemonic so that 3 char +;*mnemonics are extended with a space and 5 char mnemonics +;*are truncated. +;********** + +MNETABL EQU * + FCC "ABA " ; Mnemonic + FCB $1B ; Base opcode + FCB INH ; Class + FCC "ABX " + FCB $3A + FCB INH + FCC "ABY " + FCB $3A + FCB P2INH + FCC "ADCA" + FCB $89 + FCB GEN + FCC "ADCB" + FCB $C9 + FCB GEN + FCC "ADDA" + FCB $8B + FCB GEN + FCC "ADDB" + FCB $CB + FCB GEN + FCC "ADDD" + FCB $C3 + FCB LIMM + FCC "ANDA" + FCB $84 + FCB GEN + FCC "ANDB" + FCB $C4 + FCB GEN + FCC "ASL " + FCB $68 + FCB GRP2 + FCC "ASLA" + FCB $48 + FCB INH + FCC "ASLB" + FCB $58 + FCB INH + FCC "ASLD" + FCB $05 + FCB INH + FCC "ASR " + FCB $67 + FCB GRP2 + FCC "ASRA" + FCB $47 + FCB INH + FCC "ASRB" + FCB $57 + FCB INH + FCC "BCC " + FCB $24 + FCB REL + FCC "BCLR" + FCB $1D + FCB SETCLR + FCC "BCS " + FCB $25 + FCB REL + FCC "BEQ " + FCB $27 + FCB REL + FCC "BGE " + FCB $2C + FCB REL + FCC "BGT " + FCB $2E + FCB REL + FCC "BHI " + FCB $22 + FCB REL + FCC "BHS " + FCB $24 + FCB REL + FCC "BITA" + FCB $85 + FCB GEN + FCC "BITB" + FCB $C5 + FCB GEN + FCC "BLE " + FCB $2F + FCB REL + FCC "BLO " + FCB $25 + FCB REL + FCC "BLS " + FCB $23 + FCB REL + FCC "BLT " + FCB $2D + FCB REL + FCC "BMI " + FCB $2B + FCB REL + FCC "BNE " + FCB $26 + FCB REL + FCC "BPL " + FCB $2A + FCB REL + FCC "BRA " + FCB $20 + FCB REL + FCC "BRCL" ; (BRCLR) + FCB $1F + FCB BTB + FCC "BRN " + FCB $21 + FCB REL + FCC "BRSE" ; (BRSET) + FCB $1E + FCB BTB + FCC "BSET" + FCB $1C + FCB SETCLR + FCC "BSR " + FCB $8D + FCB REL + FCC "BVC " + FCB $28 + FCB REL + FCC "BVS " + FCB $29 + FCB REL + FCC "CBA " + FCB $11 + FCB INH + FCC "CLC " + FCB $0C + FCB INH + FCC "CLI " + FCB $0E + FCB INH + FCC "CLR " + FCB $6F + FCB GRP2 + FCC "CLRA" + FCB $4F + FCB INH + FCC "CLRB" + FCB $5F + FCB INH + FCC "CLV " + FCB $0A + FCB INH + FCC "CMPA" + FCB $81 + FCB GEN + FCC "CMPB" + FCB $C1 + FCB GEN + FCC "COM " + FCB $63 + FCB GRP2 + FCC "COMA" + FCB $43 + FCB INH + FCC "COMB" + FCB $53 + FCB INH + FCC "CPD " + FCB $83 + FCB CPD + FCC "CPX " + FCB $8C + FCB XLIMM + FCC "CPY " + FCB $8C + FCB YLIMM + FCC "DAA " + FCB $19 + FCB INH + FCC "DEC " + FCB $6A + FCB GRP2 + FCC "DECA" + FCB $4A + FCB INH + FCC "DECB" + FCB $5A + FCB INH + FCC "DES " + FCB $34 + FCB INH + FCC "DEX " + FCB $09 + FCB INH + FCC "DEY " + FCB $09 + FCB P2INH + FCC "EORA" + FCB $88 + FCB GEN + FCC "EORB" + FCB $C8 + FCB GEN + FCC "FDIV" + FCB $03 + FCB INH + FCC "IDIV" + FCB $02 + FCB INH + FCC "INC " + FCB $6C + FCB GRP2 + FCC "INCA" + FCB $4C + FCB INH + FCC "INCB" + FCB $5C + FCB INH + FCC "INS " + FCB $31 + FCB INH + FCC "INX " + FCB $08 + FCB INH + FCC "INY " + FCB $08 + FCB P2INH + FCC "JMP " + FCB $6E + FCB GRP2 + FCC "JSR " + FCB $8D + FCB NIMM + FCC "LDAA" + FCB $86 + FCB GEN + FCC "LDAB" + FCB $C6 + FCB GEN + FCC "LDD " + FCB $CC + FCB LIMM + FCC "LDS " + FCB $8E + FCB LIMM + FCC "LDX " + FCB $CE + FCB XLIMM + FCC "LDY " + FCB $CE + FCB YLIMM + FCC "LSL " + FCB $68 + FCB GRP2 + FCC "LSLA" + FCB $48 + FCB INH + FCC "LSLB" + FCB $58 + FCB INH + FCC "LSLD" + FCB $05 + FCB INH + FCC "LSR " + FCB $64 + FCB GRP2 + FCC "LSRA" + FCB $44 + FCB INH + FCC "LSRB" + FCB $54 + FCB INH + FCC "LSRD" + FCB $04 + FCB INH + FCC "MUL " + FCB $3D + FCB INH + FCC "NEG " + FCB $60 + FCB GRP2 + FCC "NEGA" + FCB $40 + FCB INH + FCC "NEGB" + FCB $50 + FCB INH + FCC "NOP " + FCB $01 + FCB INH + FCC "ORAA" + FCB $8A + FCB GEN + FCC "ORAB" + FCB $CA + FCB GEN + FCC "PSHA" + FCB $36 + FCB INH + FCC "PSHB" + FCB $37 + FCB INH + FCC "PSHX" + FCB $3C + FCB INH + FCC "PSHY" + FCB $3C + FCB P2INH + FCC "PULA" + FCB $32 + FCB INH + FCC "PULB" + FCB $33 + FCB INH + FCC "PULX" + FCB $38 + FCB INH + FCC "PULY" + FCB $38 + FCB P2INH + FCC "ROL " + FCB $69 + FCB GRP2 + FCC "ROLA" + FCB $49 + FCB INH + FCC "ROLB" + FCB $59 + FCB INH + FCC "ROR " + FCB $66 + FCB GRP2 + FCC "RORA" + FCB $46 + FCB INH + FCC "RORB" + FCB $56 + FCB INH + FCC "RTI " + FCB $3B + FCB INH + FCC "RTS " + FCB $39 + FCB INH + FCC "SBA " + FCB $10 + FCB INH + FCC "SBCA" + FCB $82 + FCB GEN + FCC "SBCB" + FCB $C2 + FCB GEN + FCC "SEC " + FCB $0D + FCB INH + FCC "SEI " + FCB $0F + FCB INH + FCC "SEV " + FCB $0B + FCB INH + FCC "STAA" + FCB $87 + FCB NIMM + FCC "STAB" + FCB $C7 + FCB NIMM + FCC "STD " + FCB $CD + FCB NIMM + FCC "STOP" + FCB $CF + FCB INH + FCC "STS " + FCB $8F + FCB NIMM + FCC "STX " + FCB $CF + FCB XNIMM + FCC "STY " + FCB $CF + FCB YNIMM + FCC "SUBA" + FCB $80 + FCB GEN + FCC "SUBB" + FCB $C0 + FCB GEN + FCC "SUBD" + FCB $83 + FCB LIMM + FCC "SWI " + FCB $3F + FCB INH + FCC "TAB " + FCB $16 + FCB INH + FCC "TAP " + FCB $06 + FCB INH + FCC "TBA " + FCB $17 + FCB INH + FCC "TPA " + FCB $07 + FCB INH + FCC "TEST" + FCB $00 + FCB INH + FCC "TST " + FCB $6D + FCB GRP2 + FCC "TSTA" + FCB $4D + FCB INH + FCC "TSTB" + FCB $5D + FCB INH + FCC "TSX " + FCB $30 + FCB INH + FCC "TSY " + FCB $30 + FCB P2INH + FCC "TXS " + FCB $35 + FCB INH + FCC "TYS " + FCB $35 + FCB P2INH + FCC "WAI " + FCB $3E + FCB INH + FCC "XGDX" + FCB $8F + FCB INH + FCC "XGDY" + FCB $8F + FCB P2INH + FCC "BRSE" ; bit direct modes for + FCB $12 ; disassembler. + FCB BTBD + FCC "BRCL" + FCB $13 + FCB BTBD + FCC "BSET" + FCB $14 + FCB SETCLRD + FCC "BCLR" + FCB $15 + FCB SETCLRD + FCB EOT ; End of table + +;********************************************** +PG1 EQU $0 +PG2 EQU $1 +PG3 EQU $2 +PG4 EQU $3 + +;****************** +;*disassem() - disassemble the opcode. +;****************** +;*(check for page prebyte) +;*baseop=pc[0]; +;*pnorm=PG1; +;*if(baseop==$18) pnorm=PG2; +;*if(baseop==$1A) pnorm=PG3; +;*if(baseop==$CD) pnorm=PG4; +;*if(pnorm != PG1) dispc=pc+1; +;*else dispc=pc; (dispc points to next byte) + +DISASSM EQU * + LDX PC ; address + LDAA 0,X ; opcode + LDAB #PG1 + CMPA #$18 + BEQ DISP2 ; jump if page2 + CMPA #$1A + BEQ DISP3 ; jump if page3 + CMPA #$CD + BNE DISP1 ; jump if not page4 +DISP4 INCB ; set up page value +DISP3 INCB +DISP2 INCB + INX +DISP1 STX DISPC ; point to opcode + STAB PNORM ; save page + +;*If(opcode == ($00-$5F or $8D or $8F or $CF)) +;* if(pnorm == (PG3 or PG4)) +;* disillop(); return(); +;* b=disrch(opcode,NULL); +;* if(b==0) disillop(); return(); + + LDAA 0,X ; get current opcode + STAA BASEOP + INX + STX DISPC ; point to next byte + CMPA #$5F + BLS DIS1 ; jump if in range + CMPA #$8D + BEQ DIS1 ; jump if bsr + CMPA #$8F + BEQ DIS1 ; jump if xgdx + CMPA #$CF + BEQ DIS1 ; jump if stop + JMP DISGRP ; try next part of map +DIS1 LDAB PNORM + CMPB #PG3 + BLO DIS2 ; jump if page 1 or 2 + JSR DISILLOP ; "illegal opcode" + RTS +DIS2 LDAB BASEOP ; opcode + CLRB ; class=null + JSR DISRCH + TSTB + BNE DISPEC ; jump if opcode found + JSR DISILLOP ; "illegal opcode" + RTS + +;* if(opcode==$8D) dissrch(opcode,REL); +;* if(opcode==($8F or $CF)) disrch(opcode,INH); + +DISPEC LDAA BASEOP + CMPA #$8D + BNE DISPEC1 + LDAB #REL + BRA DISPEC3 ; look for BSR opcode +DISPEC1 CMPA #$8F + BEQ DISPEC2 ; jump if XGDX opcode + CMPA #$CF + BNE DISINH ; jump not STOP opcode +DISPEC2 LDAB #INH +DISPEC3 JSR DISRCH ; find other entry in table + +;* if(class==INH) /* INH */ +;* if(pnorm==PG2) +;* b=disrch(baseop,P2INH); +;* if(b==0) disillop(); return(); +;* prntmne(); +;* return(); + +DISINH EQU * + LDAB CLASS + CMPB #INH + BNE DISREL ; jump if not inherent + LDAB PNORM + CMPB #PG1 + BEQ DISINH1 ; jump if page1 + LDAA BASEOP ; get opcode + LDAB #P2INH ; class=p2inh + JSR DISRCH + TSTB + BNE DISINH1 ; jump if found + JSR DISILLOP ; "illegal opcode" + RTS +DISINH1 JSR PRNTMNE + RTS + +;* elseif(class=REL) /* REL */ +;* if(pnorm != PG1) +;* disillop(); return(); +;* prntmne(); +;* disrelad(); +;* return(); + +DISREL EQU * + LDAB CLASS + CMPB #REL + BNE DISBTD + TST PNORM + BEQ DISREL1 ; jump if page1 + JSR DISILLOP ; "illegal opcode" + RTS +DISREL1 JSR PRNTMNE ; output mnemonic + JSR DISRELAD ; compute relative address + RTS + +;* else /* SETCLR,SETCLRD,BTB,BTBD */ +;* if(class == (SETCLRD or BTBD)) +;* if(pnorm != PG1) +;* disillop(); return(); /* illop */ +;* prntmne(); /* direct */ +;* disdir(); /* output $byte */ +;* else (class == (SETCLR or BTB)) +;* prntmne(); /* indexed */ +;* disindx(); +;* outspac(); +;* disdir(); +;* outspac(); +;* if(class == (BTB or BTBD)) +;* disrelad(); +;* return(); + +DISBTD EQU * + LDAB CLASS + CMPB #SETCLRD + BEQ DISBTD1 + CMPB #BTBD + BNE DISBIT ; jump not direct bitop +DISBTD1 TST PNORM + BEQ DISBTD2 ; jump if page 1 + JSR DISILLOP + RTS +DISBTD2 JSR PRNTMNE + JSR DISDIR ; operand(direct) + BRA DISBIT1 +DISBIT EQU * + JSR PRNTMNE + JSR DISINDX ; operand(indexed) +DISBIT1 JSR OUTSPAC + JSR DISDIR ; mask + LDAB CLASS + CMPB #BTB + BEQ DISBIT2 ; jump if btb + CMPB #BTBD + BNE DISBIT3 ; jump if not bit branch +DISBIT2 JSR DISRELAD ; relative address +DISBIT3 RTS + + +;*Elseif($60 <= opcode <= $7F) /* GRP2 */ +;* if(pnorm == (PG3 or PG4)) +;* disillop(); return(); +;* if((pnorm==PG2) and (opcode != $6x)) +;* disillop(); return(); +;* b=disrch(baseop & $6F,NULL); +;* if(b==0) disillop(); return(); +;* prntmne(); +;* if(opcode == $6x) +;* disindx(); +;* else +;* disext(); +;* return(); + +DISGRP EQU * + CMPA #$7F ; a=opcode + BHI DISNEXT ; try next part of map + LDAB PNORM + CMPB #PG3 + BLO DISGRP2 ; jump if page 1 or 2 + JSR DISILLOP ; "illegal opcode" + RTS +DISGRP2 ANDA #$6F ; mask bit 4 + CLRB ; class=null + JSR DISRCH + TSTB + BNE DISGRP3 ; jump if found + JSR DISILLOP ; "illegal opcode" + RTS +DISGRP3 JSR PRNTMNE + LDAA BASEOP ; get opcode + ANDA #$F0 + CMPA #$60 + BNE DISGRP4 ; jump if not 6x + JSR DISINDX ; operand(indexed) + RTS +DISGRP4 JSR DISEXT ; operand(extended) + RTS + +;*Else ($80 <= opcode <= $FF) +;* if(opcode == ($87 or $C7)) +;* disillop(); return(); +;* b=disrch(opcode&$CF,NULL); +;* if(b==0) disillop(); return(); + +DISNEXT EQU * + CMPA #$87 ; a=opcode + BEQ DISNEX1 + CMPA #$C7 + BNE DISNEX2 +DISNEX1 JSR DISILLOP ; "illegal opcode" + RTS +DISNEX2 ANDA #$CF + CLRB ; class=null + JSR DISRCH + TSTB + BNE DISNEW ; jump if mne found + JSR DISILLOP ; "illegal opcode" + RTS + +;* if(opcode&$CF==$8D) disrch(baseop,NIMM; (jsr) +;* if(opcode&$CF==$8F) disrch(baseop,NIMM; (sts) +;* if(opcode&$CF==$CF) disrch(baseop,XNIMM; (stx) +;* if(opcode&$CF==$83) disrch(baseop,LIMM); (subd) + +DISNEW LDAA BASEOP + ANDA #$CF + CMPA #$8D + BNE DISNEW1 ; jump not jsr + LDAB #NIMM + BRA DISNEW4 +DISNEW1 CMPA #$8F + BNE DISNEW2 ; jump not sts + LDAB #NIMM + BRA DISNEW4 +DISNEW2 CMPA #$CF + BNE DISNEW3 ; jump not stx + LDAB #XNIMM + BRA DISNEW4 +DISNEW3 CMPA #$83 + BNE DISGEN ; jump not subd + LDAB #LIMM +DISNEW4 JSR DISRCH + TSTB + BNE DISGEN ; jump if found + JSR DISILLOP ; "illegal opcode" + RTS + +;* if(class == (GEN or NIMM or LIMM )) /* GEN,NIMM,LIMM,CPD */ +;* if(opcode&$CF==$83) +;* if(pnorm==(PG3 or PG4)) disrch(opcode#$CF,CPD) +;* class=LIMM; +;* if((pnorm == (PG2 or PG4) and (opcode != ($Ax or $Ex))) +;* disillop(); return(); +;* disgenrl(); +;* return(); + +DISGEN LDAB CLASS ; get class + CMPB #GEN + BEQ DISGEN1 + CMPB #NIMM + BEQ DISGEN1 + CMPB #LIMM + BNE DISXLN ; jump if other class +DISGEN1 LDAA BASEOP + ANDA #$CF + CMPA #$83 + BNE DISGEN3 ; jump if not #$83 + LDAB PNORM + CMPB #PG3 + BLO DISGEN3 ; jump not pg3 or 4 + LDAB #CPD + JSR DISRCH ; look for cpd mne + LDAB #LIMM + STAB CLASS ; set class to limm +DISGEN3 LDAB PNORM + CMPB #PG2 + BEQ DISGEN4 ; jump if page 2 + CMPB #PG4 + BNE DISGEN5 ; jump not page 2 or 4 +DISGEN4 LDAA BASEOP + ANDA #$B0 ; mask bits 6,3-0 + CMPA #$A0 + BEQ DISGEN5 ; jump if $Ax or $Ex + JSR DISILLOP ; "illegal opcode" + RTS +DISGEN5 JSR DISGENRL ; process general class + RTS + +;* else /* XLIMM,XNIMM,YLIMM,YNIMM */ +;* if(pnorm==(PG2 or PG3)) +;* if(class==XLIMM) disrch(opcode&$CF,YLIMM); +;* else disrch(opcode&$CF,YNIMM); +;* if((pnorm == (PG3 or PG4)) +;* if(opcode != ($Ax or $Ex)) +;* disillop(); return(); +;* class=LIMM; +;* disgen(); +;* return(); + +DISXLN LDAB PNORM + CMPB #PG2 + BEQ DISXLN1 ; jump if page2 + CMPB #PG3 + BNE DISXLN4 ; jump not page3 +DISXLN1 LDAA BASEOP + ANDA #$CF + LDAB CLASS + CMPB #XLIMM + BNE DISXLN2 + LDAB #YLIMM + BRA DISXLN3 ; look for ylimm +DISXLN2 LDAB #YNIMM ; look for ynimm +DISXLN3 JSR DISRCH +DISXLN4 LDAB PNORM + CMPB #PG3 + BLO DISXLN5 ; jump if page 1 or 2 + LDAA BASEOP ; get opcode + ANDA #$B0 ; mask bits 6,3-0 + CMPA #$A0 + BEQ DISXLN5 ; jump opcode = $Ax or $Ex + JSR DISILLOP ; "illegal opcode" + RTS +DISXLN5 LDAB #LIMM + STAB CLASS + JSR DISGENRL ; process general class + RTS + + +;****************** +;*disrch(a=opcode,b=class) +;*return b=0 if not found +;* else mneptr=points to mnemonic +;* class=class of opcode +;****************** +;*x=#MNETABL +;*while(x[0] != eot) +;* if((opcode==x[4]) && ((class=NULL) || (class=x[5]))) +;* mneptr=x; +;* class=x[5]; +;* return(1); +;* x += 6; +;*return(0); /* not found */ + +DISRCH EQU * + LDX #MNETABL ; point to top of table +DISRCH1 CMPA 4,X ; test opcode + BNE DISRCH3 ; jump not this entry + TSTB + BEQ DISRCH2 ; jump if class=null + CMPB 5,X ; test class + BNE DISRCH3 ; jump not this entry +DISRCH2 LDAB 5,X + STAB CLASS + STX MNEPTR ; return ptr to mnemonic + INCB + RTS ; return found +DISRCH3 PSHB ; save class + LDAB #6 + ABX + LDAB 0,X + CMPB #EOT ; test end of table + PULB + BNE DISRCH1 + CLRB + RTS ; return not found + +;****************** +;*prntmne() - output the mnemonic pointed +;*at by mneptr. +;****************** +;*outa(mneptr[0-3]); +;*outspac; +;*return(); + +PRNTMNE EQU * + LDX MNEPTR + LDAA 0,X + JSR OUTA ; output char1 + LDAA 1,X + JSR OUTA ; output char2 + LDAA 2,X + JSR OUTA ; output char3 + LDAA 3,X + JSR OUTA ; output char4 + JSR OUTSPAC + RTS + +;****************** +;*disindx() - process indexed mode +;****************** +;*disdir(); +;*outa(','); +;*if(pnorm == (PG2 or PG4)) outa('Y'); +;*else outa('X'); +;*return(); + +DISINDX EQU * + JSR DISDIR ; output $byte + LDAA #',' + JSR OUTA ; output , + LDAB PNORM + CMPB #PG2 + BEQ DISIND1 ; jump if page2 + CMPB #PG4 + BNE DISIND2 ; jump if not page4 +DISIND1 LDAA #'Y' + BRA DISIND3 +DISIND2 LDAA #'X' +DISIND3 JSR OUTA ; output x or y + RTS + +;****************** +;*disrelad() - compute and output relative address. +;****************** +;* braddr = dispc[0] + (dispc++);( 2's comp arith) +;*outa('$'); +;*out2bsp(braddr); +;*return(); + +DISRELAD EQU * + LDX DISPC + LDAB 0,X ; get relative offset + INX + STX DISPC + TSTB + BMI DISRLD1 ; jump if negative + ABX + BRA DISRLD2 +DISRLD1 DEX + INCB + BNE DISRLD1 ; subtract +DISRLD2 STX BRADDR ; save address + JSR OUTSPAC + LDAA #'$' + JSR OUTA + LDX #BRADDR + JSR OUT2BSP ; output address + RTS + + +;****************** +;*disgenrl() - output data for the general cases which +;*includes immediate, direct, indexed, and extended modes. +;****************** +;*prntmne(); +;*if(baseop == ($8x or $Cx)) /* immediate */ +;* outa('#'); +;* disdir(); +;* if(class == LIMM) +;* out1byt(dispc++); +;*elseif(baseop == ($9x or $Dx)) /* direct */ +;* disdir(); +;*elseif(baseop == ($Ax or $Ex)) /* indexed */ +;* disindx(); +;*else (baseop == ($Bx or $Fx)) /* extended */ +;* disext(); +;*return(); + +DISGENRL EQU * + JSR PRNTMNE ; print mnemonic + LDAA BASEOP ; get opcode + ANDA #$B0 ; mask bits 6,3-0 + CMPA #$80 + BNE DISGRL2 ; jump if not immed + LDAA #'#' ; do immediate + JSR OUTA + JSR DISDIR + LDAB CLASS + CMPB #LIMM + BEQ DISGRL1 ; jump class = limm + RTS +DISGRL1 LDX DISPC + JSR OUT1BYT + STX DISPC + RTS +DISGRL2 CMPA #$90 + BNE DISGRL3 ; jump not direct + JSR DISDIR ; do direct + RTS +DISGRL3 CMPA #$A0 + BNE DISGRL4 ; jump not indexed + JSR DISINDX ; do extended + RTS +DISGRL4 JSR DISEXT ; do extended + RTS + +;***************** +;*disdir() - output "$ next byte" +;***************** +DISDIR EQU * + LDAA #'$' + JSR OUTA + LDX DISPC + JSR OUT1BYT + STX DISPC + RTS + +;***************** +;*disext() - output "$ next 2 bytes" +;***************** +DISEXT EQU * + LDAA #'$' + JSR OUTA + LDX DISPC + JSR OUT2BSP + STX DISPC + RTS + + +;***************** +;*disillop() - output "illegal opcode" +;***************** +DISMSG1 FCC "ILLOP" + FCB EOT +DISILLOP EQU * + PSHX + LDX #DISMSG1 + JSR OUTSTRG0 ; no cr + PULX + RTS + +;* Equates +JPORTD EQU $08 +JDDRD EQU $09 +JBAUD EQU $2B +JSCCR1 EQU $2C +JSCCR2 EQU $2D +JSCSR EQU $2E +JSCDAT EQU $2F +;* + +;************ +;* xboot [ []] - Use SCI to talk to an 'hc11 in +;* boot mode. Downloads bytes from addr1 thru addr2. +;* Default addr1 = $C000 and addr2 = $C0ff. +;* +;* IMPORTANT: +;* if talking to an 'A8 or 'A2: use either default addresses or ONLY +;* addr1 - this sends 256 bytes +;* if talking to an 'E9: include BOTH addr1 and addr2 for variable +;* length +;************ + +;*Get arguments +;*If no args, default $C000 +BOOT JSR WSKIP + BNE BOT1 ; jump if arguments + LDX #$C0FF ; addr2 default + STX PTR5 + LDY #$C000 ; addr1 default + BRA BOT2 ; go - use default address + +;*Else get arguments +BOT1 JSR BUFFARG + TST COUNT + BEQ BOTERR ; jump if no address + LDY SHFTREG ; start address (addr1) + JSR WSKIP + BNE BOT1A ; go get addr2 + STY PTR5 ; default addr2... + LDD PTR5 ; ...by taking addr1... + ADDD #$FF ; ...and adding 255 to it... + STD PTR5 ; ...for a total download of 256 + BRA BOT2 ; continue +;* +BOT1A JSR BUFFARG + TST COUNT + BEQ BOTERR ; jump if no address + LDX SHFTREG ; end address (addr2) + STX PTR5 + JSR WSKIP + BNE BOTERR ; go use addr1 and addr2 + BRA BOT2 + +;* +BOTERR LDX #MSG9 ; "bad argument" + JSR OUTSTRG + RTS + +;*Boot routine +BOT2 LDAB #$FF ; control character ($ff -> download) + JSR BTSUB ; set up SCI and send control char +;* initializes X as register pointer +;*Download block +BLOP LDAA 0,Y + STAA JSCDAT,X ; write to transmitter + BRCLR JSCSR,X,#80,* ; wait for TDRE + CPY PTR5 ; if last... + BEQ BTDONE ; ...quit + INY ; else... + BRA BLOP ; ...send next +BTDONE RTS + +;************************************************ +;*Subroutine +;* btsub - sets up SCI and outputs control character +;* On entry, B = control character +;* On exit, X = $1000 +;* A = $0C +;*************************** + +BTSUB EQU * + LDX #$1000 ; to use indexed addressing + LDAA #$02 + STAA JPORTD,X ; drive transmitter line + STAA JDDRD,X ; high + CLR JSCCR2,X ; turn off XMTR and RCVR + LDAA #$22 ; BAUD = /16 + STAA JBAUD,X + LDAA #$0C ; TURN ON XMTR & RCVR + STAA JSCCR2,X + STAB JSCDAT,X + BRCLR JSCSR,X,#80,* ; wait for TDRE + RTS + +;****************** +;* +;* EVBTEST - This routine makes it a little easier +;* on us to test this board. +;* +;****************** + +EVBTEST LDAA #$FF + STAA $1000 ; Write ones to port A + CLR AUTOLF ; Turn off auto lf + JSR HOSTCO ; Connect host + JSR HOSTINIT ; Initialize host + LDAA #$7f + JSR HOSTOUT ; Send Delete to Altos + LDAA #$0d + JSR HOSTOUT ; Send + INC AUTOLF ; Turn on Auto LF + LDX #INBUFF+5 ; Point at Load message + STX PTR0 ; Set pointer for load command + LDY #MSGEVB ; Point at cat line +LOOP LDAA 0,Y ; Loop to xfer command line + CMPA #04 ; Into buffalo line buffer + BEQ DONE ; Quit on $04 + STAA 0,X + INX ; next character + INY + BRA LOOP +DONE CLR TMP2 ; Set load vs. verify + JSR LOAD3 ; Jmp into middle of load + LDS #STACK ; Reset Stack + JMP $C0B3 ; Jump to Downloaded code + +MSGEVB FCC "cat evbtest.out" + FCB $0D + FCB $04 + + + +;*** Jump table *** + ORG ROMBS+$1F7C +.WARMST JMP MAIN +.BPCLR JMP BPCLR +.RPRINT JMP RPRINT +.HEXBIN JMP HEXBIN +.BUFFAR JMP BUFFARG +.TERMAR JMP TERMARG +.CHGBYT JMP CHGBYT +.READBU JMP READBUFF +.INCBUF JMP INCBUFF +.DECBUF JMP DECBUFF +.WSKIP JMP WSKIP +.CHKABR JMP CHKABRT + + ORG ROMBS+$1FA0 +.UPCASE JMP UPCASE +.WCHEK JMP WCHEK +.DCHEK JMP DCHEK +.INIT JMP INIT +.INPUT JMP INPUT +.OUTPUT JMP OUTPUT +.OUTLHL JMP OUTLHLF +.OUTRHL JMP OUTRHLF +.OUTA JMP OUTA +.OUT1BY JMP OUT1BYT +.OUT1BS JMP OUT1BSP +.OUT2BS JMP OUT2BSP +.OUTCRL JMP OUTCRLF +.OUTSTR JMP OUTSTRG +.OUTST0 JMP OUTSTRG0 +.INCHAR JMP INCHAR +.VECINT JMP VECINIT + + ORG ROMBS+$1FD6 +;*** Vectors *** +VSCI FDB JSCI +VSPI FDB JSPI +VPAIE FDB JPAIE +VPAO FDB JPAO +VTOF FDB JTOF +VTOC5 FDB JTOC5 +VTOC4 FDB JTOC4 +VTOC3 FDB JTOC3 +VTOC2 FDB JTOC2 +VTOC1 FDB JTOC1 +VTIC3 FDB JTIC3 +VTIC2 FDB JTIC2 +VTIC1 FDB JTIC1 +VRTI FDB JRTI +VIRQ FDB JIRQ +VXIRQ FDB JXIRQ +VSWI FDB JSWI +VILLOP FDB JILLOP +VCOP FDB JCOP +VCLM FDB JCLM +VRST FDB BUFFALO + END diff --git a/tests/t_buf32/t_buf32.doc b/tests/t_buf32/t_buf32.doc new file mode 100644 index 0000000..67e8f37 --- /dev/null +++ b/tests/t_buf32/t_buf32.doc @@ -0,0 +1,5 @@ ++------------------------ Test Application BUF32 ----------------------------+ +| | +| This is a version of Motorola's 68HC11-Monitor Buffalo-32 adapted for AS. | +| | ++-----------------------------------------------------------------------------+ diff --git a/tests/t_buf32/t_buf32.inc b/tests/t_buf32/t_buf32.inc new file mode 100644 index 0000000..98ae373 --- /dev/null +++ b/tests/t_buf32/t_buf32.inc @@ -0,0 +1,2 @@ +; tests/t_buf32/t_buf32.asm-Includefile für Assembler-Programm +; Ende Includefile für Assembler-Programm diff --git a/tests/t_buf32/t_buf32.ori b/tests/t_buf32/t_buf32.ori new file mode 100644 index 0000000..774e9c9 Binary files /dev/null and b/tests/t_buf32/t_buf32.ori differ diff --git a/tests/t_cop8/asflags b/tests/t_cop8/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_cop8/t_cop8.asm b/tests/t_cop8/t_cop8.asm new file mode 100644 index 0000000..68573d1 --- /dev/null +++ b/tests/t_cop8/t_cop8.asm @@ -0,0 +1,128 @@ + cpu cop87l84 + + macexp off + + include regcop8.inc + + nop + ret + reti + retsk + sc + rc + ifc + ifnc + vis + jid + intr + laid + rpnd + + clr a + inc a + dec a + dcor a + rrc a + rlc a + swap a + pop a + push a + + adc a,[b] + adc a,0x12 + adc a,#0x12 + + subc a,[b] + subc a,0x12 + subc a,#0x12 + + add a,[b] + add a,0x12 + add a,#0x12 + + ifgt a,[b] + ifgt a,0x12 + ifgt a,#0x12 + + and a,[b] + and a,0x12 + and a,#0x12 + + xor a,[b] + xor a,0x12 + xor a,#0x12 + + or a,[b] + or a,0x12 + or a,#0x12 + + ld a,[b] + ld a,0x12 + ld a,#0x12 + ld a,[x] + ld r4,#0x12 + ld b,#12 + ld b,#0x12 + ld a,[b+] + ld a,[x+] + ld a,[b-] + ld a,[x-] + ld [b],#0x12 + ld [b+],#0x12 + ld [b-],#0x12 + ld 0x12,#0x12 + + x a,[b] + x [x],a + x a,[b+] + x [x+],a + x a,[b-] + x [x-],a + x a,0x12 + + andsz a,#0x12 + + ifeq a,[b] + ifeq a,0x12 + ifeq a,#0x12 + ifeq 0x12,#0x12 + + ifne a,[b] + ifne a,0x12 + ifne a,#0x12 + + ifbit 3,[b] + ifbit 5,0x12 + sbit 3,[b] + sbit 5,0x12 + rbit 3,[b] + rbit 5,0x12 + + ifbne #7 + ifbne #0xc + + jmp 0x123 + jsr 0x987 + + jmpl 0x1234 + jsrl 0x3456 + + jp .+6 + jp .-20 + jp .+1 + + drsz r12 + drsz r8 + +reg sfr 10 + + addr 1,2,3,4,5 + addrw 1,2,3,4,5 + byte 1,2,3,4,5 + word 1,2,3,4,5 + dsb 20 + dsw 20 + fb 10,20 + fw 10,20 + + diff --git a/tests/t_cop8/t_cop8.doc b/tests/t_cop8/t_cop8.doc new file mode 100644 index 0000000..94aacd5 --- /dev/null +++ b/tests/t_cop8/t_cop8.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application COP8 ----------------------------+ +| | +| This is a (synthetic) test of the COP8 code generator | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_cop8/t_cop8.ori b/tests/t_cop8/t_cop8.ori new file mode 100644 index 0000000..15e176e Binary files /dev/null and b/tests/t_cop8/t_cop8.ori differ diff --git a/tests/t_f2mc8l/asflags b/tests/t_f2mc8l/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_f2mc8l/t_f2mc8l.asm b/tests/t_f2mc8l/t_f2mc8l.asm new file mode 100644 index 0000000..25540b7 --- /dev/null +++ b/tests/t_f2mc8l/t_f2mc8l.asm @@ -0,0 +1,242 @@ + cpu mb89190 + page 0 + +;---------------------------------------------------------------------------- +; Transfer + + mov 23h,a + mov @ix+34h,a + mov 1234h,a + mov @ep,a + mov r0,a + mov r1,a + mov r2,a + mov r3,a + mov r4,a + mov r5,a + mov r6,a + mov r7,a + mov a,#12h + mov a,23h + mov a,@ix+34h + mov a,1234h + mov a,@a + mov a,@ep + mov a,r0 + mov a,r1 + mov a,r2 + mov a,r3 + mov a,r4 + mov a,r5 + mov a,r6 + mov a,r7 + mov 23h,#12h + mov @ix+34h,#12h + mov @ep,#12h + mov r0,#12h + mov r1,#12h + mov r2,#12h + mov r3,#12h + mov r4,#12h + mov r5,#12h + mov r6,#12h + mov r7,#12h + movw 12h,a + movw @ix+34h,a + movw 1234h,a + movw @ep,a + movw ep,a + movw a,#2345h + movw a,12h + movw a,@ix+34h + movw a,1234h + movw a,@a + movw a,@ep + movw a,ep + movw ep,#2345h + movw ix,a + movw a,ix + movw sp,a + movw a,sp + mov @a,t + movw @a,t + movw ix,#2345h + movw a,ps + movw ps,a + movw sp,#2345h + swap + setb 12h:6 + clrb 12h:5 + xch a,t + xchw a,t + xchw a,ep + xchw a,ix + xchw a,sp + movw a,pc + + +;---------------------------------------------------------------------------- +; Arithmetik + + addc a,r0 + addc a,r1 + addc a,r2 + addc a,r3 + addc a,r4 + addc a,r5 + addc a,r6 + addc a,r7 + addc a,#12h + addc a,23h + addc a,@ix+34h + addc a,@ep + addcw a + addc a + subc a,r0 + subc a,r1 + subc a,r2 + subc a,r3 + subc a,r4 + subc a,r5 + subc a,r6 + subc a,r7 + subc a,#12h + subc a,23h + subc a,@ix+34h + subc a,@ep + subcw a + subc a + inc r0 + inc r1 + inc r2 + inc r3 + inc r4 + inc r5 + inc r6 + inc r7 + incw ep + incw ix + incw a + dec r0 + dec r1 + dec r2 + dec r3 + dec r4 + dec r5 + dec r6 + dec r7 + decw ep + decw ix + decw a + mulu a + divu a + andw a + orw a + xorw a + cmp a + rorc a + rolc a + cmp a,#12h + cmp a,23h + cmp a,@ix+34h + cmp a,@ep + cmp a,r0 + cmp a,r1 + cmp a,r2 + cmp a,r3 + cmp a,r4 + cmp a,r5 + cmp a,r6 + cmp a,r7 + daa + das + xor a + xor a,#12h + xor a,23h + xor a,@ix+34h + xor a,@ep + xor a,r0 + xor a,r1 + xor a,r2 + xor a,r3 + xor a,r4 + xor a,r5 + xor a,r6 + xor a,r7 + and a + and a,#12h + and a,23h + and a,@ix+34h + and a,@ep + and a,r0 + and a,r1 + and a,r2 + and a,r3 + and a,r4 + and a,r5 + and a,r6 + and a,r7 + or a + or a,#12h + or a,23h + or a,@ix+34h + or a,@ep + or a,r0 + or a,r1 + or a,r2 + or a,r3 + or a,r4 + or a,r5 + or a,r6 + or a,r7 + cmp 23h,#12h + cmp @ep,#12h + cmp @ix+34h,#12h + cmp r0,#12h + cmp r1,#12h + cmp r2,#12h + cmp r3,#12h + cmp r4,#12h + cmp r5,#12h + cmp r6,#12h + cmp r7,#12h + incw sp + decw sp + +;---------------------------------------------------------------------------- +; Spruenge + + bz $ + beq $ + bnz $ + bne $ + bc $ + blo $ + bnc $ + bhs $ + bn $ + bp $ + blt $ + bge $ + bbc 23h:5,$ + bbs 23h:4,$ + jmp @a + jmp 2345h + callv #4 + call 2345h + xchw a,pc + ret + reti + +;---------------------------------------------------------------------------- +; Sonstiges + + pushw a + popw a + pushw ix + popw ix + nop + clrc + setc + clri + seti diff --git a/tests/t_f2mc8l/t_f2mc8l.doc b/tests/t_f2mc8l/t_f2mc8l.doc new file mode 100644 index 0000000..8bb3785 --- /dev/null +++ b/tests/t_f2mc8l/t_f2mc8l.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application F2MC8L --------------------------+ +| | +| This is a (synthetic) test of the F2MC8L's instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_f2mc8l/t_f2mc8l.ori b/tests/t_f2mc8l/t_f2mc8l.ori new file mode 100644 index 0000000..3f1f4ae Binary files /dev/null and b/tests/t_f2mc8l/t_f2mc8l.ori differ diff --git a/tests/t_fl90/asflags b/tests/t_fl90/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_fl90/cpu_time.inc b/tests/t_fl90/cpu_time.inc new file mode 100644 index 0000000..bb23594 --- /dev/null +++ b/tests/t_fl90/cpu_time.inc @@ -0,0 +1,170 @@ +; CPU_TIME.INC +;****************************************************************************** +;* Zeitmessmodul fr TLCS 90 * +;* * +;* Originale fr den TLCS 900 von Oli(ver Sellke) * +;* Implementierung TLCS 90 von Alfred Arnold, Dezember 1993 * +;* * +;* Routine Funktion Eingabe Ausgabe Stack L„nge * +;* * +;* InitTimer Timer initialisieren ---- ---- 0 Byte 6 Byte * +;* StartTimer Timer starten ---- ---- 0 Byte 7 Byte * +;* StopTime Timer stoppen & Ausgabe ---- ---- 6 Byte 117 Byte *) * +;* * +;* *) bei hoher Aufl”sung * +;* * +;* - Die Routinen benutzen Timer 4, dieser darf nicht von der Anwendung * +;* benutzt werden!! * +;* - Die Aufl”sung kann ber das Symbol BigTime umgeschaltet werden: * +;* * +;* BigTime Aufl”sung Maximalzeit * +;* definiert 0,8 us 52,428 ms * +;* undefiniert 12,8 us 838,848 ms * +;* * +;* - Die Datei MON.INC wird fr die Einsprnge des TDBTMP90-Monitors ben”tigt.* +;* - MACROS.INC muá vorher eingebunden werden * +;* * +;****************************************************************************** + + section CPU_Time + +;------------------------------------------------------------------------------ +; Monitoreinsprungadressen laden + + include "mon.inc" + +;------------------------------------------------------------------------------ +; Timer vorinitialisieren + + proc InitTimer + ifdef BigTime + ld (T4MOD),00100010b ; nur Software-Capture, Phi16 + elseif + ld (T4MOD),00100001b ; nur Software-Capture, Phi1 + endif + set 5,(TRUN) ; Vorteiler starten + res 4,(TRUN) ; Timer steht noch + ret + endp + +;------------------------------------------------------------------------------ +; Timer starten + + proc StartTimer + set 2,(T4MOD) ; Timer l”schen + res 2,(T4MOD) + set 4,(TRUN) ; Timer starten + ret + endp + +;------------------------------------------------------------------------------ +; Timer stoppen & Wert auf Konsole ausgeben + + subproc Div24 + + ld b,16 ; A-HL : B = HL und A +DivLoop: sll l ; Divident hochschieben + rl h + rla + srl h ; fr nachher + rr l + sub a,c ; paát Divisor hinein ? + jr nc,DivOK + add a,c ; nein, zurcknehmen + scf ; ins Ergebnis 0 einschieben +DivOK: ccf ; neues Ergebnisbit + rl l ; Ergebnis in HL einschieben + rl h + djnz DivLoop + ret + + endp + + + proc StopTimer + + push af ; Register retten + push hl + push de + push bc + + res 5,(T4MOD) ; Wert im CAP1 latchen + res 4,(TRUN) ; Timer wieder anhalten + ld hl,(CAP1L) ; Wert auslesen + + ifdef BigTime + ld a,h ; groáe Periode: x128... + ld h,l + ld l,0 + srla + rr h + rr l + ld c,100 ; ...Teilen durch 100 + elseif + ld a,0 ; kleine Periode: x8... + rept 3 + sll l + rl h + rla + endm + ld c,10 ; ...Teilen durch 10 + endif + call Div24 ; Division durchfhren + ifdef BigTime ; Kommatrennung fr groáe Periode + ld a,0 + call Div24 + ld d,a ; Rest merken + endif + ld e,0 ; Zeichenz„hler nullen + ld c,10 ; Teilerfaktor konstant +InLoop: ld a,0 ; Erweiterung auf 24 Bit + call Div24 ; einmal teilen + push af ; Zeichen auf LIFO merken + inc e ; ein Zeichen mehr + or hl,hl ; noch etwas brig ? + jr nz,InLoop + ld a,5 ; Leerzeichen fr Ausrichtung + sub a,e ; Zahl berechnen + jr z,OutErg ; Nullschleife abfangen + ld b,a ; ansonsten passende Zahl Leerzeichen +BlankLoop: call BLAUS ; voranstellen + djnz BlankLoop +OutErg: ld b,e ; jetzt die Zeichen ausgeben +OutLoop: pop af + add a,'0' + call CONOUT + djnz OutLoop + ifdef BigTime ; bei groáer Aufl”sung Nachkommastellen + ld a,'.' + call CONOUT + ld l,d ; Zehner/Einerzerlegung + ld h,0 + div hl,c + add hl,'00' + ld a,l + call CONOUT + ld a,h + call CONOUT + call BLAUS + ld a,'m' + elseif + ld a,' ' + call CONOUT + ld a,'u' + endif + call CONOUT ; Ausgabe Einheit + ld a,'s' + call CONOUT + + pop bc ; Register zurck + pop de + pop hl + pop af + + ret + endp + +;------------------------------------------------------------------------------ +; gemeinsames Ende + + endsection diff --git a/tests/t_fl90/float.inc b/tests/t_fl90/float.inc new file mode 100644 index 0000000..7355130 --- /dev/null +++ b/tests/t_fl90/float.inc @@ -0,0 +1,1601 @@ +; FLOAT.INC +;****************************************************************************** +;* Gleitkommabibliothek fr TLCS 90 * +;* * +;* Originale fr den Z80 aus mc 12/88,1/89 * +;* Portierung auf TLCS 90 von Alfred Arnold, Dezember 1993 * +;* * +;* Routine Funktion Eingabe Ausgabe Stack L„nge Zeit/10MHz * +;* * +;* fadd Addition 2*Stack BC-DE 14 Byte 347 Byte 248 us * +;* fsub Subtraktion 2*Stack BC-DE 14 Byte 12 Byte 255 us * +;* fmul Multiplikation 2*Stack BC-DE 20 Byte 356 Byte 936 us * +;* fdiv Division 2*Stack BC-DE 22 Byte 303 Byte 1081 us * +;* fmul2 Mult. mit 2er-Potenz Stack,A BC-DE 10 Byte 162 Byte 28 us * +;* fsqrt Quadratwurzel Stack BC-DE 22 Byte 621 Byte 1900 us * +;* fitof Int-->Float Stack BC-DE 10 Byte 84 Byte 160 us *) * +;* fftoi Float-->Int Stack BC-DE 10 Byte 104 Byte 170 us *) * +;* fftoa Float-->ASCII 3*Stack ----- 40 Byte 451 Byte *) * +;* fatof ASCII-->Float Stack C,BC-DE 42 Byte 396 Byte *) * +;* * +;* *) Die Ausfhrungszeiten streuen je nach Operand sehr stark und k”nnen * +;* bei den ASCII-Funktionen bei vielen Millisekunden liegen. * +;* * +;* - Parametereingabe ber den Stack bedeutet, daá die Parameter mittels * +;* PUSH vor dem Aufruf auf den Stack gelegt werden mssen. Diese Werte * +;* werden von den Unterroutinen am Ende automatisch vom Stack entfernt. * +;* Der zur šbergabe ben”tigte Platz ist bei den Angaben zur Stackbelastung * +;* eingerechnet! * +;* - Wollen Sie einzelne Routinen entfernen, so beachten Sie, daá fsub Teile * +;* aus fadd, fdiv Teile aus fmul sowie fftoi Teile aus fitof verwendet ! * +;* - Gleitkommaformat ist IEEE Single (32 Bit) * +;* - Integerwerte bei fmul2, fitof und fftoi sind vorzeichenbehaftet * +;* - Da die Routinen lokale Labels verwenden, ist mindestens AS 1.39 erfor- * +;* derlich * +;* - MACROS.INC muá vorher eingebunden werden * +;****************************************************************************** + + section float + +;------------------------------------------------------------------------------ +; modulglobale Konstanten + +MaxExpo equ 255 +Bias equ 127 + +OpSize equ 4 ; Gr”áe eines Operanden + +fIX_alt equ 0 ; Top of Stack liegt IX +FAdr equ 2 ; Rcksprungadresse +Op2 equ 4 ; Adresse Operand 2 +Op1 equ Op2+OpSize ; Adresse Operand 1 + +Ld10: dd ld(10) +One: dd 1.0 +Ten: dd 10.0 +Tenth: dd 3dcccccdh ; =0.1, aber die Rundung auf manchen + ; Systemen variiert (damit Test nicht + ; scheitert) +Half: dd 0.5 + +cpsh macro reg,op,{NoExpand} + ld reg,(op+2) + push reg + ld reg,(op) + push reg + endm + +;------------------------------------------------------------------------------ +; Addition + + proc fadd + link ix,0 ; Eintritt + + push af ; Register retten + push hl + + public AddSub:Parent ; Einsprung fr fsub + +AddSub: ld a,(ix+Op1+3) ; Vorzeichen Operand 1 laden + ld e,a ; Ergebnisvorzeichen in E, Bit 7 + xor a,(ix+Op2+3) ; mit Vorzeichen von Op2 verknpfen + ld d,a ; Subtraktionsflag in D, Bit 7 + res 7,(ix+Op1+3) ; Vorzeichen in Mantisse 1 l”schen + res 7,(ix+Op2+3) ; Vorzeichen in Mantisse 2 l”schen + +; Die Operanden sind jetzt in der Form 0eee eeee efff ... ffff + + ld hl,(ix+Op1) ; Differenz Op1-Op2 bilden + sub hl,(ix+Op2) + ld hl,(ix+Op1+2) + sbc hl,(ix+Op2+2) + jr nc,Ad_1 ; Sprung falls Op1>Op2 + ld bc,(ix+Op1) ; ansonsten Operanden vertauschen + ex bc,(ix+Op2) + ld (ix+Op1),bc + ld bc,(ix+Op1+2) + ex bc,(ix+Op2+2) + ld (ix+Op1+2),bc + ld a,e ; Ergebnisvorzeichen neu berechnen + xor a,d + ld e,a + +Ad_1: ld a,(ix+Op1+2) ; Exponent der gr”áeren Zahl laden + ld c,(ix+Op1+3) + slaa + rl c + jr z,Den1 + set 7,(ix+Op1+2) ; implizite Eins erzeugen +Den1: ld a,(ix+Op2+2) ; dito Zahl 2 + ld b,(ix+Op2+3) + slaa + rl b + jr z,Den2 + set 7,(ix+Op2+2) + +Den2: push bc ; jetzt die Register fr den + push de ; Blocktransferbefehl retten + ld bc,2*OpSize-1 ; beide Operanden verschieben + ld hl,ix ; HL zeigt auf letztes Byte + add hl,Op2+2*OpSize-1 + ld de,hl ; HL nach DE kopieren + dec hl ; HL zeigt auf vorletztes Byte + lddr ; Verschiebung beider Mantissen + pop de ; um 8 Bit nach links + pop bc + + xor a,a + ld (ix+Op1),a ; Form: ffff ... ffff 0000 0000 + ld (ix+Op2),a + ld a,c ; Differenz der Exponenten berechnen + sub a,b + ld b,a ; Differenz nach B fr LOOP-Befehl + jr z,N_Anp ; falls Null, keine Anpassung + cp a,25 ; mehr als 24? (Abfrage mit Carry + jp c,Anp ; erfordert Vergleich mit 25) + ld b,0 ; !!!! + jp Round + +Anp: srl (ix+Op2+3) ; Anpassung der zweiten Mantisse + rr (ix+Op2+2) ; durch Verschiebung nach rechts + rr (ix+Op2+1) + rr (ix+Op2) + djnz Anp ; bis B=0 + +N_Anp: bit 7,d ; Addition oder Subtraktion ? + jr nz,Subtract ; ggfs. zur Subtraktion springen + ld hl,(ix+Op1) ; jetzt werden die beiden Mantissen + add hl,(ix+Op2) ; zueinander addiert + ld (ix+Op1),hl + ld hl,(ix+Op1+2) + adc hl,(ix+Op2+2) + ld (ix+Op1+2),hl + jr nc,Round ; kein šberlauf-->zum Runden + rr (ix+Op1+3) ; šberlauf einschieben + rr (ix+Op1+2) + rr (ix+Op1+1) + rr (ix+Op1) + inc bc ; Exponent erh”hen (B ist 0 durch + jr Round ; Schleife), zum Runden + +Subtract: ld hl,(ix+Op1) ; beide Mantissen werden voneinander + sub hl,(ix+Op2) ; subtrahiert + ld (ix+Op1),hl + ld hl,(ix+Op1+2) + sbc hl,(ix+Op2+2) + ld (ix+Op1+2),hl + jr m,Round ; bei fhrender Eins zum Runden + jr nz,Norm ; ungleich 0 ? Dann zum Normalisieren + cp hl,(ix+Op1) ; Rest der Mantisse auch Null ? + jr eq,Zero ; alles Null --> Ergebnis ist Null + +Norm: ld a,b ; Exponent noch nicht Null ? + or a,c + jr z,Round + dec bc ; Exponent erniedrigen + sla (ix+Op1) ; Mantisse normalisieren, bis + rl (ix+Op1+1) ; fhrende Eins auftaucht + rl (ix+Op1+2) + rl (ix+Op1+3) + jr p,Norm ; noch keine Eins-->weitermachen + +Round: add (ix+Op1),80h ; jetzt Runden auf Bit hinter Mantisse + jr nc,NoOver ; kein šbertrag ? + inc (ix+Op1+1) ; doch, n„chstes Mantissenbyte + jr nz,NoOver ; behandeln, jetzt auf Null prfen, + inc (ix+Op1+2) ; da der INC-Befehl kein Carry liefert + jr nz,NoOver + inc (ix+Op1+3) + jr nz,NoOver + scf ; fhrende Eins erzeugen + rr (ix+Op1+3) ; bei šberlauf Mantisse durch + rr (ix+Op1+2) ; Rechtsschieben wieder normalisieren + rr (ix+Op1+1) ; (nur fr 24 Bit notwendig) + inc bc ; und Exponent korrigieren + +NoOver: xor a,a ; A = 0 + cp a,(ix+Op1+3) ; Mantisse auf Null prfen + jr nz,NoZero + cp a,(ix+Op1+2) + jr nz,NoZero + cp a,(ix+Op1+1) ; alle Mantissenbytes Null ? + jr nz,NoZero ; dann ist auch das Ergebnis Null + +Zero: ld b,a ; Null-Ergebnis aufbauen + ld c,a + ld de,bc + jr Exit ; dann Routine verlassen + +NoZero: cp a,b ; A ist Null + ld a,MaxExpo ; Exponent oberes Byte ungleich Null ? + jr nz,Over ; dann ist šberlauf eingetreten + cp a,c ; oder genau MaxExpo erreicht ? + jr nz,NoUe +Over: ld c,a ; Exponent auf MaxExpo setzen + xor a,a ; und Mantisse auf Null + ld (ix+Op1+3),a + ld (ix+Op1+2),a + ld (ix+Op1+1),a + jr DeNorm + +NoUe: xor a,a ; A = 0 + cp a,c ; Exponent Null (Zahl denormalisiert ? + jr z,DeNorm ; ja --> + sla (ix+Op1+1) ; fhrendes Bit wird nicht gespeichert + rl (ix+Op1+2) ; daher Mantisse um 1 Bit nach links + rl (ix+Op1+3) + +DeNorm: ld b,c ; Ergebnis aufbauen: Exponent in B + ld c,(ix+Op1+3) ; Mantisse oberstes Byte + ld d,(ix+Op1+2) + sla e ; Vorzeichen aus E in Carry schieben + ld e,(ix+Op1+1) + rr b ; Vorzeichen in Ergebnis einschieben + rr c + rr d + rr e + +Exit: pop hl ; Register restaurieren + pop af + + unlk ix ; Austritt + retd 2*OpSize ; Parameter abr„umen + endp + +;------------------------------------------------------------------------------ +; Subtraktion + + proc fsub + + link ix,0 ; Eintritt + + push af ; Register retten + push hl + + xor (ix+Op2+3),80h ; Vorzeichen Operand 2 kippen + + jrl AddSub ; weiter wie Addition + + endp + +;------------------------------------------------------------------------------ +; Multiplikation + + proc fmul + + DefLocal temp,6 ; Platz Tempor„rvariable + + link ix,LocalSize ; Platz auf Stack reservieren + + push af ; Register retten + push hl + + ld a,(ix+Op1+3) ; Ergebnisvorzeichen bestimmen + xor a,(ix+Op2+3) + ld c,a ; in C merken + + ld d,0 ; Exponent 1 laden + ld e,(ix+Op1+3) + ld a,(ix+Op1+2) + slaa ; Exponent unterstes Bit in Carry + rl e ; und in E einschieben + srla ; ergibt Bit 7=0 + ld (ix+Op1+3),a ; impl. Null vorbesetzen+um 8 Bit schieben + cp e,0 + jr z,Den1 ; falls Null, dann denormalisiert + set 7,(ix+Op1+3) ; ansonsten impl. Eins erzeugen + dec de ; Bias kompensieren +Den1: ld hl,(ix+Op1) ; jetzt restliche Bytes verschieben + ld (ix+Op1+1),hl + xor hl,hl ; unterste Mantissenbits l”schen + ld (ix+Op1),h ; Form: ffff ... ffff 0000 0000 + + ld (ix+temp+4),hl ; lokale Variable mit Null vorbesetzen + ld (ix+temp+2),hl + ld (ix+temp),hl + + ld l,(ix+Op2+3) ; Exponent 2 in HL aufbauen + ld a,(ix+Op2+2) + res 7,(ix+Op2+2) ; gleiches Verfahren wie Op1 + slaa + rl l + jr z,Den2 + set 7,(ix+Op2+2) + dec hl +Den2: + add hl,de ; Exponenten aufaddieren + sub hl,Bias-3 ; Bias-3 subtrahieren + jp p,NoZero ; positiv-->kein Unterlauf + ld a,l ; Exponent <-24 ? + cp a,-24 + jr nc,NoZero + jp MulZero ; ja, dann ist Ergebnis Null + +NoZero: ld b,24 ; Schleifenz„hler Multiplikation + ld de,0 ; Hilfsregister Multiplikand + push hl ; HL zum Addieren benutzen +Multiply: srl (ix+Op1+3) ; Multiplikand nach rechts schieben + rr (ix+Op1+2) + rr (ix+Op1+1) + rr (ix+Op1) + rr d ; DE als Verl„ngerung von Operand 1 + rr e + sla (ix+Op2) ; Multiplikator nach links schieben + rl (ix+Op2+1) + rl (ix+Op2+2) ; falls fhrendes Bit 0, nicht addieren + jr nc,NoAdd + ld hl,(ix+temp) ; sonst aufaddieren + add hl,de + ld (ix+temp),hl + ld hl,(ix+temp+2) + adc hl,(ix+Op1) + ld (ix+temp+2),hl + ld hl,(ix+temp+4) + adc hl,(ix+Op1+2) + ld (ix+temp+4),hl +NoAdd: djnz Multiply ; Schleife durchlaufen + pop hl + ld a,(ix+temp+5) + or a,a ; Flags setzen + jp m,MulRound ; bei fhrender Eins zum Runden + jr nz,Normalize ; ansonsten normalisieren + cp a,(ix+temp+4) + jr nz,Normalize + cp a,(ix+temp+3) + jr nz,Normalize + cp a,(ix+temp+2) + jr Normalize + jp MulZero ; komplett Null-->Ergebnis Null + +Normalize: bit 7,h ; Exponent negativ ? + jp nz,Underrun ; ggf. Unterlauf behandlen + +Norm1: cp hl,0 ; Exponent=0 ? + jr z,MulRound + dec hl ; Exponent erniedrigen, + sla (ix+temp) ; Mantisse verschieben... + rl (ix+temp+1) + rl (ix+temp+2) + rl (ix+temp+3) + rl (ix+temp+4) + rl (ix+temp+5) + jp p,Norm1 ; ...bis fhrende Eins auftaucht + + public MulRound:Parent ; Einsprung fr Division +MulRound: ld a,(ix+temp+2) ; jetzt Runden auf Bit hinter Mantisse + add a,80h + jr nc,NoOver ; kein šbertrag + inc (ix+temp+3) ; doch, n„chstes Mantissenbyte + jr nz,NoOver ; behandeln, jetzt auf Null prfen + inc (ix+temp+4) ; da INC kein Carry liefert + jr nz,NoOver + inc (ix+temp+5) + jr nz,NoOver + scf ; Eins erzeugen + rr (ix+temp+5) ; bei šberlauf Mantisse durch + rr (ix+temp+4) ; Rechtsschieben wieder normalisieren + rr (ix+temp+3) + inc hl ; und Exponent korrigieren + +NoOver: cp hl,MaxExpo ; Exponent prfen + jr ult,NoUeber ; kein šberlauf + + public MulOver:Parent ; Einsprung fr fdiv +MulOver: ld hl,MaxExpo ; šberlauf: Exponent=MaxExpo + ld (ix+temp+5),h + ld (ix+temp+4),h + ld (ix+temp+3),h + jr DeNorm + +NoUeber: xor a,a ; A=0 + cp a,l ; Exponent ist Null ? + jr z,DeNorm ; ja, Ergebnis ist denormalisiert + sla (ix+temp+3) ; nein, fhrende=implizite Eins + rl (ix+temp+4) ; rausschieben + rl (ix+temp+5) + +DeNorm: sla c ; Vorzeichen in Carry schieben + ld b,l ; Exponent einsetzen + ld c,(ix+temp+5) + ld d,(ix+temp+4) + ld e,(ix+temp+3) + rr b ; und Vorzeichen einschieben + rr c + rr d + rr e ; Form: seee eeee efff ffff ... ffff + +Result: pop hl ; Register zurck + pop af + + unlk ix ; Stackrahmen abbauen + retd 2*OpSize ; Operanden abr„umen + + public MulZero:Parent ; Einsprung fr fdiv +MulZero: xor a,a ; Ergebnis ist Null + ld b,a + ld c,a + ld d,a + ld e,a + jr Result + +Underrun: ld a,l ; Exponent in A + neg a ; negieren fr Schleifenz„hler + cp a,24 ; totaler Unterlauf ? + jr nc,MulZero ; ja, dann ist Ergebnis Null + ld b,a ; Mantisse denormalisieren +Shr: srl (ix+temp+5) ; bis Exponent Null ist + rr (ix+temp+4) + rr (ix+temp+3) + djnz Shr + ld l,b ; Exponent in Register L=B=0 + jp Denorm ; denormalisiertes Ergebnis erzeugen + + endp + +;------------------------------------------------------------------------------ +; Division + + proc fdiv + + DefLocal temp,6 ; Platz Tempor„rvariable + + link ix,LocalSize ; 6 Byte Platz auf Stack reservieren + + push af ; Register retten + push hl + + ld a,(ix+Op1+3) ; Ergebnisvorzeichen bestimmen + xor a,(ix+Op2+3) + ld c,a ; Vorzeichen in C Bit 7 merken + push bc ; Vorzeichen retten + + ld h,0 ; Exponent 1 laden + ld l,(ix+Op1+3) + ld a,(ix+Op1+2) + res 7,(ix+Op1+2) ; impl. Null vorbesetzen + slaa ; Exponent unterstes Bit in Carry + rl l ; und in L einschieben + jr z,Den1 ; falls Null, dann Op1 denormalisiert + set 7,(ix+Op1+2) ; implizite Eins erzeugen + dec hl ; Bias kompensieren +Den1: + ld d,0 ; Exponent 2 in DE aufbauen + ld e,(ix+Op2+3) + ld a,(ix+Op2+2) + ld (ix+Op2+3),a ; Verfahren wie oben + res 7,(ix+Op2+3) + slaa + rl e + jr z,Den2 + set 7,(ix+Op2+3) + dec de +Den2: + ld bc,(ix+Op2) ; jetzt restliche Bytes kopieren + ld (ix+Op2+1),bc + xor a,a ; A=0 + ld (ix+Op2),a ; Form: ffff ... ffff 0000 0000 + srl (ix+Op2+3) + rr (ix+Op2+2) + rr (ix+Op2+1) + rr (ix+Op2) ; Form: 0fff ... ffff f000 0000 + jr nz,NoZero1 ; Mantisse 2 auf Null prfen + cp a,(ix+Op2+1) + jr nz,NoZero1 + cp a,(ix+Op2+2) + jr nz,NoZero1 + cp a,(ix+Op2+3) + jr nz,NoZero1 + jp MulOver + +NoZero1: xor a,a ; Carry-Flag l”schen + sbc hl,de ; Exponenten subtrahieren + add hl,Bias ; Bias addieren + jr p,NoZero ; Exponent negativ ? + cp l,-24 ; Exponent kleiner als -24 ? + jr nc,NoZero + jp MulZero ; ja, dann ist das Ergebnis Null +NoZero: + add hl,25 ; Exponent um 25 erh”hen; jetzt ist er sicher gr”áer als Null + xor a,a ; A=0 + ld bc,(ix+Op1+1) ; Divident in Register kopieren + ld d,(ix+Op1) + ld e,a ; die untersten Bits sind Null + cp a,d ; ist Divident Null ? + jr nz,NoZero2 + cp a,c + jr nz,NoZero2 + cp a,b + jr nz,NoZero2 + pop bc ; Stack bereinigen (Vorzeichen laden) + jp MulZero ; und Null als Ergebnis ausgeben +NoZero2: + ld (ix+temp+5),a ; Ergebnis vorbesetzen + ld (ix+temp+4),a + ld (ix+temp+3),a + ld (ix+temp+2),a + +NormLoop: bit 6,(ix+Op2+3) ; ist der Divisor normalisiert ? + jr nz,Norm ; ja--> + inc hl ; nein, Exponent erh”hen + sla (ix+Op2) ; Divisor verschieben bis in + rl (ix+Op2+1) ; Form 01ff ... + rl (ix+Op2+2) + rl (ix+Op2+3) + jr NormLoop +Norm: srl b + rr c + rr d + rr e ; Form: 0fff ... ffff f000 0000 + + push iy ; Exponent nach IY + ld iy,hl +Loop: ld (ix+Op1+2),bc ; Divident zwischenspeichern + ; die Speicherpl„tze von Op1 + ld (ix+Op1),de ; stehen zur Verfgung, da wir Op1 + ; in die Register BC-DE kopiert haben + ld hl,de ; jetzt Divisor abziehen + sub hl,(ix+Op2) + ld de,hl + ld hl,bc + sbc hl,(ix+Op2+2) + ld bc,hl + jr nc,IsOne ; kein Carry: Divisor paát + ld de,(ix+Op1) ; ansonsten zurckkopieren + ld bc,(ix+Op1+2) ; Carry bleibt erhalten! +IsOne: ccf ; Carry-Flag umdrehen + rl (ix+temp+2) ; Ergebnis aufbauen + rl (ix+temp+3) + rl (ix+temp+4) + rl (ix+temp+5) + sla e ; Divident verschieben + rl d + rl c + rl b + + add iy,-1 ; Exponent erniedrigen + jr z,DeNorm ; falls Null, dann denormalisiert + bit 0,(ix+temp+5) ; fhrende Eins in Ergebnis-Mantisse ? + jr z,Loop ; nein, weiter rechnen + +DeNorm: ld hl,iy ; Exponent zurck + ld b,(ix+temp+5) ; h”chstes Bit merken + ld a,(ix+temp+4) + ld (ix+temp+5),a ; Mantisse in Form + ld iy,(ix+temp+2) ; ffff ... ffff 0000 0000 + ld (ix+temp+3),iy + pop iy ; IY erst jetzt freigeben + rr b ; h”chstes Bit einschieben + rr (ix+temp+5) + rr (ix+temp+4) + rr (ix+temp+3) + rr (ix+temp+2) + + pop bc ; Vorzeichen wieder laden + xor a,a ; A=0 + cp a,(ix+temp+5) ; Mantisse ist Null ? + jr nz,NoZero3 + cp a,(ix+temp+4) + jr nz,NoZero3 + cp a,(ix+temp+3) + jr nz,NoZero3 + cp a,(ix+temp+2) + jp z,MulZero +NoZero3: + jp MulRound + + endp + +;------------------------------------------------------------------------------ +; Wandlung Integer-->Gleitkomma + + proc fitof + + link ix,0 ; Stackrahmen aufbauen + push af ; Register retten + push hl + + ld bc,(ix+Op2+2) ; Operanden hereinholen + ld de,(ix+Op2) ; Reihenfolge: BCDE + + ld hl,bc ; Operand = 0 ? + or hl,de + jr z,ItofResult ; dann Ergebnis Null + + bit 7,b ; Zahl positiv ? + jr z,Positive + ld hl,bc ; dann Zahl negieren + xor hl,-1 + ld bc,hl + ld hl,de + xor hl,-1 + inc hl + or hl,hl + ld de,hl + jr nz,Positive + inc bc + +Positive: ld l,Bias+32 ; Exponent vorbesetzen +Shift: dec l + sla e ; Mantisse verschieben, bis fhrende + rl d ; Eins auftaucht + rl c + rl b + jr nc,Shift + ld e,d ; Exponent einsetzen + ld d,c + ld c,b + ld b,l + sla (ix+Op2+3) ; Vorzeichen in Carry + rr b ; ins Ergebnis einschieben + rr c + rr d + rr e + + public ItofResult:Parent +ItofResult: pop hl ; Register zurck + pop af + unlk ix ; abbauen + retd 4 ; Ende + + endp + +;------------------------------------------------------------------------------ +; Wandlung Gleitkomma-->Integer + + proc fftoi + + link ix,0 ; Stackrahmen aufbauen + + push af ; Register retten + push hl + + ld d,(ix+Op2) ; Operand in Register laden + ld bc,(ix+Op2+1) ; Reihenfolge: EBCD + ld e,(ix+Op2+3) ; erspart sp„ter Vertauschungen + + ld h,e ; Vorzeichen in H, Bit 7 + ld a,e ; Exponent in A aufbauen + sla b ; LSB aus B holen + rla + scf ; impl. Eins einschieben + rr b + sub a,Bias + ld l,a ; Exponent nach L kopieren + jp m,Zero ; falls keiner Null, Ergebnis Null + ld a,30 + cp a,l ; gr”áer 30 ? + jr c,Over ; dann šberlauf + ld e,0 ; Zahl jetzt in BCDE in der Form + inc a ; 1fff ... ffff 0000 0000 + +Shift: srl b ; jetzt Mantisse verschieben + rr c + rr d + rr e + inc l + cp a,l ; bis Exponent stimmt + jr nz,Shift + bit 7,h ; Zahl negativ ? + jr z,ItofResult ; nein, fertig + + ld hl,de ; Zahl negieren + xor hl,-1 + ld de,hl + ld hl,bc + xor hl,-1 + ld bc,hl + inc de + jr nz,ItofResult + inc bc + jr nz,ItofResult + +Zero: ld bc,0 + ld de,bc + jp ItofResult ; Ergebnis Null + +Over: bit 7,h ; Ergebnis positiv ? + jr z,OpPos + ld b,80h ; MININT laden + xor a,a ; A=0 + ld c,a + ld d,a + ld e,a + jp ItofResult +OpPos: ld b,7fh ; MAXINT laden + ld a,0ffh + ld c,a + ld d,a + ld e,a + jp ItofResult + + endp + +;------------------------------------------------------------------------------ +; Multiplikation mit Zweierpotenz (in A) + + proc fmul2 + + link ix,0 ; Stackrahmen aufbauen + + push af ; Register retten + push hl + + ld de,(ix+Op2) ; Operand 1 in Register laden + ld bc,(ix+Op2+2) + + ld h,a ; Operand 2 nach H kopieren + ld l,b ; Vorzeichen nach L, Bit 7 + xor a,a ; A=0 + cp a,b ; Operand 1 = Null ? + jr nz,NoZero + cp a,c + jr nz,NoZero + cp a,d + jr nz,NoZero + cp a,e + jr z,Zero + +NoZero: sla e ; Operand 1 verschieben + rl d + rl c + rl b ; Form: eeee eeee ffff ... fff0 + jr z,Den ; Falls Exponent Null -->denormal + + add a,h ; A=0+H + jr m,Div ; Falls Op2<0-->Division + add a,b ; A=Summe der Exponenten + ld b,a ; zurck nach B + jr c,Over ; bei šberlauf--> + cp a,MaxExpo ; oder genau MaxExpo + jr z,Over + +Result: sla l ; Vorzeichen in Carry schieben + rr b + rr c + rr d + rr e ; Ergebnis zusammensetzen + +Zero: pop hl ; Register zurck + pop af + + unlk ix ; Stackrahmen abbauen + retd 4 ; Ende + +Over: ld b,MaxExpo ; šberlauf: Exponent=MaxExpo + xor a,a ; Mantisse=0 + ld c,a + ld d,a + ld e,a + jr Result + +Div: add a,b ; A = Summe der Exponenten + ld b,a ; zurck nach B + jr z,Div2 + jr p,Result ; falls >0, Ergebnis abliefern +Div2: scf ; implizite Eins real machen + rr c + rr d + rr e ; Form: eeee eeee 1fff ... ffff + +Denorm: xor a,a ; A = 0 + cp a,b ; Exponent Null ? + jr z,Result ; ja, ergebnis abliefern + srl c + rr d + rr e ; Mantisse denormalisieren + jr nz,NoZero2 + cp a,d + jr nz,NoZero2 + cp a,c + jr nz,NoZero2 + ld b,a ; totaler Unterlauf, Ergebnis = Null + jr Zero + +NoZero2: inc b ; Exponent erh”hen + jr Denorm ; weiter denormalisieren + +DDD: add a,b ; Summe der Exponenten bilden + ld b,a ; zurck nach B + jr Denorm + +Den: add a,h ; A=0+H + jr m,DDD ; bei Division verzweigen +NoOver: sla e ; Multiplikation: Eine + rl d ; denormalisierte Mantisse + rl c ; wird wieder normalisiert + jr c,Stop ; bis fhrende Eins rausfliegt + dec h ; oder Operand 2 = Null + jr nz,NoOver + jr Result + +Stop: ld a,h ; Summe der Exponenten bilden + add a,b + ld b,a ; zurck nach B + jr Result + + endp + +;------------------------------------------------------------------------------ +; Quadratwurzel ziehen + + proc fsqrt + +Op equ 4 ; Lage Parameter + DefLocal XRoot,4 ; Iterationsvariablen + DefLocal m2,4 + DefLocal xx2,4 + + link ix,LocalSize ; Stackrahmen aufbauen + + push af ; Register retten + push hl + push iy + + bit 7,(ix+Op+3) ; negatives Argument ? + jp nz,DomainError ; dann Fehler + + ld hl,(ix+Op+2) ; Exponent isolieren + and hl,07f80h + jp z,Zero ; keine Behandlung denormaler Zahlen + + ld (ix+Op+3),0 ; Mantisse isolieren + and (ix+Op+2),7fh + sub hl,7fh*80h ; Bias vom Exponenten entfernen + ld bc,hl + bit 7,c ; Exponent ungerade ? + res 7,c + jr z,EvenExp + ld hl,(ix+Op) ; ja: Mantisse verdoppeln + add hl,hl + ld (ix+Op),hl + ld hl,(ix+Op+2) + adc hl,hl + add hl,100h-80h ; impl. Eins dazu + ld (ix+Op+2),hl +EvenExp: + sra b ; Exponent/2 mit Vorzeichen + rr c + ld hl,7fh*80h ; Bias wieder dazu + add hl,bc + ld iy,hl ; Exponent in IY aufheben + ld de,(ix+Op+1) ; x ausrichten (um 7 nach links) + ld a,(ix+Op+3) ; oberstes Byte merken + ld (ix+Op+2),de ; da wir hier eins zuviel schieben + ld d,(ix+Op) + ld e,0 + ld (ix+Op),de + srla ; dieses Bit einschieben + rr (ix+Op+3) + rr (ix+Op+2) + rr (ix+Op+1) + rr (ix+Op) + ld de,0 ; vorbelegen + ld (ix+XRoot),de + ld (ix+m2),de + ld d,40h + ld (ix+XRoot+2),de + ld d,10h + ld (ix+m2+2),de +Loop10: ld de,(ix+Op) ; xx2 = x + ld (ix+xx2),de + ld de,(ix+Op+2) + ld (ix+xx2+2),de +Loop11: ld hl,(ix+xx2) ; xx2 -= xroot + sub hl,(ix+XRoot) + ld (ix+xx2),hl + ld hl,(ix+xx2+2) + sbc hl,(ix+XRoot+2) + ld (ix+xx2+2),hl + srl (ix+XRoot+3) ; xroot /= 2 + rr (ix+XRoot+2) + rr (ix+XRoot+1) + rr (ix+XRoot) + ld hl,(ix+xx2) ; xx2 -= m2 + sub hl,(ix+m2) + ld (ix+xx2),hl + ld hl,(ix+xx2+2) + sbc hl,(ix+m2+2) + ld (ix+xx2+2),hl + jr m,DontSet1 + ld hl,(ix+xx2) ; x = xx2 + ld (ix+Op),hl + ld hl,(ix+xx2+2) + ld (ix+Op+2),hl + ld hl,(ix+XRoot) ; xroot += m2 + or hl,(ix+m2) + ld (ix+XRoot),hl + ld hl,(ix+XRoot+2) + or hl,(ix+m2+2) + ld (ix+XRoot+2),hl + ld hl,(ix+m2) ; m2 /= 4 + ld de,(ix+m2+2) + rept 2 + srl d + rr e + rr h + rr l + endm + ld (ix+m2),hl + ld (ix+m2+2),de + or hl,de + jr nz,Loop11 + jr IsSame +DontSet1: ld hl,(ix+m2) ; m2 /= 4 + ld de,(ix+m2+2) + rept 2 + srl d + rr e + rr h + rr l + endm + ld (ix+m2),hl + ld (ix+m2+2),de + or hl,de + jp nz,Loop10 ; 15* abarbeiten + ; Bit 22..8 + ld hl,(ix+Op) ; 17. Iteration separat + ld (ix+xx2),hl + ld hl,(ix+Op+2) + ld (ix+xx2+2),hl +IsSame: ld hl,(ix+xx2) + sub hl,(ix+XRoot) + ld (ix+xx2),hl + ld hl,(ix+xx2+2) + sbc hl,(ix+XRoot+2) + ld (ix+xx2+2),hl + ld de,(ix+XRoot+2) ; mitsamt Carry... + ld hl,(ix+XRoot) + srl d + rr e + rr h + rr l + jr nc,NoC1 + set 7,d +NoC1: ld (ix+XRoot+2),hl ; auf neues Alignment umstellen + ld (ix+XRoot),de + decw (ix+xx2) ; Carry von 0-$4000: xx2 -= m2 + jr nz,NoC2 + decw (ix+xx2+2) +NoC2: bit 7,(ix+xx2+3) + jr nz,DontSet7 + or (ix+xx2+3),0c0h ; 0-$4000: x2 -= m2, Teil 2 + ld hl,(ix+xx2) + ld (ix+Op),hl + ld hl,(ix+xx2+2) + ld (ix+Op+2),hl + or (ix+XRoot+1),40h; xroot += m2 +DontSet7: ld hl,(ix+Op) ; x auf neues Alignment umstellen + ld de,(ix+Op+2) + ld (ix+Op),de + ld (ix+Op+2),hl + ld hl,1000h ; m2 - obere H„lfte schon 0 + ld (ix+m2),hl +Loop20: ld hl,(ix+Op) ; xx2 = x + ld (ix+xx2),hl + ld hl,(ix+Op+2) + ld (ix+xx2+2),hl +Loop21: ld hl,(ix+xx2) ; xx2 -= xroot + sub hl,(ix+XRoot) + ld (ix+xx2),hl + ld hl,(ix+xx2+2) + sbc hl,(ix+XRoot+2) + ld (ix+xx2+2),hl + srl (ix+XRoot+3) ; XRoot = XRoot/2 + rr (ix+XRoot+2) + rr (ix+XRoot+1) + rr (ix+XRoot) + ld hl,(ix+xx2) ; x2 -= m2 + sub hl,(ix+m2) + ld (ix+xx2),hl + ld hl,(ix+xx2+2) + sbc hl,(ix+m2+2) + ld (ix+xx2+2),hl + jr m,DontSet2 + ld hl,(ix+xx2) ; x = xx2 + ld (ix+Op),hl + ld hl,(ix+xx2+2) + ld (ix+Op+2),hl + ld hl,(ix+XRoot) ; xroot += m2 + or hl,(ix+m2) + ld (ix+XRoot),hl + ld hl,(ix+XRoot+2) + or hl,(ix+m2+2) + ld (ix+XRoot+2),hl + ld hl,(ix+m2) ; m2 /= 4 + ld de,(ix+m2+2) + rept 2 + srl d + rr e + rr h + rr l + endm + ld (ix+m2),hl + ld (ix+m2+2),de + or hl,de + jr nz,Loop21 + jr Finish +DontSet2: ld hl,(ix+m2) ; m2 /= 4 + ld de,(ix+m2+2) + rept 2 + srl d + rr e + rr h + rr l + endm + ld (ix+m2),hl + ld (ix+m2+2),de + or hl,de + jp nz,Loop20 ; 7* abarbeiten + +Finish: ld hl,(ix+Op) ; Aufrunden notwendig ? + sub hl,(ix+XRoot) + ld (ix+Op),hl + ld hl,(ix+Op+2) + sub hl,(ix+XRoot+2) + ld (ix+Op+2),hl + jr ule,NoInc + incw (ix+XRoot) ; wenn ja, durchfhren + jr nz,NoInc + incw (ix+XRoot) +NoInc: res 7,(ix+XRoot+2) ; impl. Eins l”schen + ld hl,(ix+XRoot+2) ; Exponent einbauen + or hl,iy + ld bc,hl ; Ergebnis in BC-DE + ld de,(ix+XRoot) + jr End + +DomainError: ld bc,0ffc0h ; - NAN zuckgeben + ld de,0 + jr End + +Zero: ld bc,0 ; Ergebnis 0 + ld de,bc + +End: pop iy ; Register zurck + pop hl + pop af + + unlk ix ; Stackrahmen abbauen + retd 4 ; Ende + + endp + +;------------------------------------------------------------------------------ +; Zehnerpotenz bilden + + subproc fPot10 + + push ix ; Register retten + push iy + push hl + + ld bc,(One+2) ; Ausgangspunkt frs Multiplizieren + ld de,(One) + ld ix,(Ten+2) ; zu benutzende Potenz + ld iy,(Ten) + or hl,hl ; negative Potenz? + jr p,IsPos + ld ix,(Tenth+2) ; dann eben mit Zehntel + ld iy,(Tenth) + xor hl,-1 ; Zweierkomplement + inc hl +IsPos: + or hl,hl ; weiter multiplizieren ? + jr z,End ; nein, Ende + bit 0,l ; Restpotenz ungerade ? + jr z,IsEven + push bc ; ja: einzeln multiplizieren + push de + push ix + push iy + call fmul +IsEven: srl h + rr l + push bc ; n„chste Potenz berechnen + push de + push ix ; durch quadrieren + push iy + push ix + push iy + call fmul + ld ix,bc + ld iy,de + pop de + pop bc + jr IsPos ; weitersuchen +End: + pop hl ; Register zurck + pop iy + pop ix + + ret ; Ende + + endp + +;------------------------------------------------------------------------------ + + subproc fOutDec + +Op equ 6 ; Adresse Operand +Format equ 4 ; Formatdeskriptor + DefLocal Temp,4 ; 64-Bit-Erweiterung Divident + + link ix,LocalSize + + push af ; Register retten + push bc + push de + push hl + + bit 7,(ix+Op+3) ; negativ ? + jr z,IsPos + ld (iy),'-' ; ja: vermerken... + inc iy + ld hl,(ix+Op) ; ...und Zweierkomplement + xor hl,-1 + ld (ix+Op),hl + ld hl,(ix+Op+2) + xor hl,-1 + ld (ix+Op+2),hl + incw (ix+Op) + jr nz,GoOn + incw (ix+Op+2) + jr GoOn +IsPos: bit 7,(ix+Format+1) ; Pluszeichen ausgeben ? + jr nz,GoOn + ld (iy),'+' + inc iy +GoOn: res 7,(ix+Format+1) ; Plusflag l”schen + ld de,0 ; Nullflag & Z„hler l”schen + +InLoop: ld hl,0 ; Division vorbereiten + ld (ix+Temp),hl ; dazu auf 64 Bit erweitern + ld (ix+Temp+2),hl + ld b,32 ; 32-Bit-Division +DivLoop: sll (ix+Op) ; eins weiterschieben + rl (ix+Op+1) + rl (ix+Op+2) + rl (ix+Op+3) + rl (ix+Temp) + rl (ix+Temp+1) + rl (ix+Temp+2) + rl (ix+Temp+3) + srl (ix+Op) ; fr nachher + ld hl,(ix+Temp) ; probeweise abziehen + sub hl,10 + ld (ix+Temp),hl + ld hl,(ix+Temp+2) + sbc hl,0 + ld (ix+Temp+2),hl + jr nc,DivOK ; paát es ? + ld hl,(ix+Temp) ; nein, zurcknehmen + add hl,10 + ld (ix+Temp),hl + ld hl,(ix+Temp+2) + adc hl,0 + ld (ix+Temp+2),hl + scf ; ins Ergebnis 0 einschieben +DivOK: ccf ; neues Ergebnisbit + rl (ix+Op) ; von unten einschieben + djnz DivLoop + + ld a,(ix+Temp) ; ASCII-Offset addieren + add a,'0' + bit 0,d ; schon im Nullbereich ? + jr z,NormVal + ld a,(ix+Format) ; ja, dann gewnschtes Leerzeichen +NormVal: push af ; auf LIFO legen + inc e ; ein Zeichen mehr + ld a,(ix+Op) ; Quotient Null ? + or a,(ix+Op+1) + or a,(ix+Op+2) + or a,(ix+Op+3) + ld d,0 ; Annahme: nicht Null + jr nz,InLoop ; falls <>0, auf jeden Fall weiter + ld d,0ffh ; Flag auf True setzen + ld a,e ; ansonsten nur weiter, falls minimale + cp a,(ix+Format+1) ; Zahl noch nicht erreicht + jr ult,InLoop + + ld b,e ; jetzt Zeichen ausgeben +OutLoop: pop af + ld (iy),a + inc iy + djnz OutLoop + + pop hl ; Register zurck + pop de + pop bc + pop af + + unlk ix + retd 6 + + endp + +;------------------------------------------------------------------------------ +; Wandlung Float-->ASCII + + proc fftoa + +Op equ 8 ; Lage Eingabe auf Stack +Format equ 6 ; Lage Formatdeskriptor auf Stack +Buffer equ 4 ; Pufferadresse + DefLocal Copy,4 ; Tempor„rkopie der Zahl + DefLocal ExpSave,2 ; berechneter Exponent + + link ix,LocalSize ; Platz fr Exponenten/Kopie der Zahl + + push af ; Register retten + push de + push iy + push hl + + ld iy,(ix+Buffer) ; Pufferadresse holen + + ld hl,(ix+Op) ; Zahl kopieren + ld (ix+Copy),hl + ld hl,(ix+Op+2) + res 7,h ; dabei Vorzeichen l”schen + ld (ix+Copy+2),hl + + ld a,'+' ; Annahme positiv + sll (ix+Op) ; Vorzeichen herausschieben + rl (ix+Op+1) ; und in Carry bringen + rl (ix+Op+2) + rl (ix+Op+3) + jr c,IsNeg ; Minuszeichen immer erforderlich + bit 0,(ix+Format+1) ; Pluszeichen dagegen optional + jr nz,NoMantSgn + jr WrMantSgn +IsNeg: ld a,'-' ; negative Zahl +WrMantSgn: ld (iy),a ; Vorzeichen ablegen + inc iy +NoMantSgn: + ld l,(ix+Op+3) ; Exponent herausholen... + ld h,0 ; ...auf 16 Bit erweitern... + ld bc,(ix+Op+1) ; ...und in Quelle l”schen + ld (ix+Op+2),bc + ld b,(ix+Op) + ld c,0 + ld (ix+Op),bc + + cp hl,MaxExpo ; Sonderwerte ? + jp z,SpecialVals ; ja--> + + or hl,hl ; Zahl denormal ? + jr nz,IsNormal ; nein, normal weiter + ld a,(ix+Op+3) ; falls Mantisse Null, + or a,(ix+Op+2) ; nicht normalisieren + or a,(ix+Op+1) + jr z,IsNull +Normalize: sll (ix+Op+1) ; ansonsten schieben, bis fhrende + rl (ix+Op+2) ; Eins da + rl (ix+Op+3) + jr c,IsNormal + dec hl + jr Normalize +IsNormal: sub hl,Bias ; Bias abziehen +IsNull: + ld b,h ; Zweierexponenten in Float wandeln + ld c,h + push bc + push hl + call fitof + push bc ; in Dezimalexponenten wandeln + push de + cpsh bc,Ld10 + call fdiv + bit 7,b ; Zahl negativ ? + jr z,NoCorr + push bc ; dann noch eins abziehen wegen + push de ; unterer Gauáklammer + cpsh bc,One + call fsub +NoCorr: push bc ; den Ausflug in Float beenden + push de + call fftoi + ld (ix+ExpSave),de ; Exponenten retten + + ld bc,(ix+Copy+2) ; Originalzahl + push bc + ld bc,(ix+Copy) + push bc + ld hl,de ; durch die Zehnerpotenz + call fPot10 ; des Exponenten + push bc + push de + call fdiv ; teilen +Again: ld (ix+Copy),de ; Ergebnis zwischen 1...9,999 retten + ld (ix+Copy+2),bc + push bc ; Vorkommastelle berechnen + push de + call fftoi + cp e,10 ; doch etwas drber ? + jr ult,NoRoundErr + ld bc,(ix+Copy+2) ; dann nocheinmal zehnteln + push bc + ld bc,(ix+Copy) + push bc + cpsh bc,Tenth + call fmul + incw (ix+ExpSave) + jr Again +NoRoundErr: add e,'0' ; Vorkommastelle nach ASCII + ld (iy),e ; ablegen + inc iy + sub e,'0' ; wieder rckg„ngig machen + cp (ix+Format),0 ; gar keine Nachkommastellen ? + jr eq,NoComma + ld (iy),'.' ; Dezimalpunkt ausgeben + inc iy + push bc ; Vorkomma nach Float wandeln + push de + call fitof + push bc + push de + cpsh bc,ix+Copy ; von alter Zahl abziehen + call fsub + xor b,80h ; war verkehrtherum + push bc ; zum Skalieren auf Stack + push de + ld l,(ix+Format) ; passende Skalierungskonstante ausrechnen + ld h,0 + call fPot10 + push bc + push de + call fmul ; hochskalieren + push bc ; Rundung + push de + cpsh bc,Half + call fadd + push bc ; Stellen nach Integer + push de + call fftoi + push bc ; entspr. ausgeben + push de + ld b,(ix+Format) ; Format fr fOutDec aufbauen + set 7,b ; kein Pluszeichen + ld c,'0' ; Fllzeichen Nullen + push bc + call fOutDec + bit 5,(ix+Format+1) ; Nullen am Ende abr„umen ? + jr nz,CleanZeros +NoComma: + ld a,(ix+Format+1) ; falls Minimalstellenzahl Exponent=0 + and a,00011100b ; und Exponent=0, vergessen + or a,(ix+ExpSave) + or a,(ix+ExpSave+1) + jr z,End + + ld (iy),'E' ; Exponenten ausgeben + inc iy + ld hl,(ix+ExpSave) + ld b,h + ld c,h + push bc + push hl + ld c,'0' ; evtl. vornullen + ld b,(ix+Format+1) + rrc b ; Bit 1-->Bit 7 + rrc b + and b,87h + push bc + call fOutDec + +End: ld (iy),0 ; NUL-Zeichen als Terminierer + ld de,iy ; Endezeiger nach DE + pop hl ; Register zurck + pop iy + ex de,hl ; zur Subtraktion tauschen + sub hl,de ; = Zahl geschriebener Zeichen + ex de,hl ; HL wieder original + ld bc,de ; Ergebnis nach BC + pop de + pop af + + unlk ix ; Stackrahmen abbauen + retd 8 ; Ende + +SpecialVals: ld a,(ix+Op+3) ; Mantisse Null ? + or a,(ix+Op+2) + or a,(ix+Op+1) + jr nz,IsNAN + ld (iy),'I' ; ja: Unendlichkeit + ld (iy+1),'N' + ld (iy+2),'F' + add iy,3 + jr End +IsNAN: ld (iy),'N' ; nein: NAN + ld (iy+1),'A' + ld (iy+2),'N' + add iy,3 + jr End + +CleanZeros: cp (iy-1),'0' ; Null am Ende ? + jr nz,CleanNoZero ; nein, Ende + dec iy ; ja: Z„hler runter, so daá ber- + jr CleanZeros ; schrieben wird und neuer Versuch +CleanNoZero: cp (iy-1),'.' ; evtl. Komma entfernbar ? + jr nz,Ready ; nein--> + dec iy ; ja: noch ein Zeichen weniger +Ready: jrl NoComma + + endp + +;------------------------------------------------------------------------------ +; Wandlung ASCII-->Float + + proc fatof + +SrcAddr equ 4 ; Lage Parameter auf Stack + DefLocal Flags,2 ; Steuerflags + DefLocal Exp,2 ; Speicher Exponent + DefLocal Mant,4 ; Speicher fr Mantissenzwischenwert + DefLocal Factor,4 ; Speicher fr Zehnerpotenz + + link ix,LocalSize ; Stackrahmen aufbauen + + push af ; Register retten + push hl + push iy + + ld iy,(ix+SrcAddr) ; Zeigeradresse laden + ld (ix+Flags),01h ; Phase 1 (Mantisse), noch kein Vorzeichen + ld (ix+Flags+1),0 + ld bc,(Ten) ; in der Mantisse mit 10 hochmultiplizieren + ld (ix+Factor),bc + ld bc,(Ten+2) + ld (ix+Factor+2),bc + ld bc,0 ; Exponent mit 0 vorbelegen + ld (ix+Exp),bc + ld (ix+Mant),bc ; Mantisse auch + ld (ix+Mant+2),bc + +ReadLoop: ld a,(iy) ; ein neues Zeichen holen + inc iy + + cp a,0 ; Endezeichen ? + jp eq,Combine ; ja, zusammenbauen + + cp a,' ' ; Leerzeichen ignorieren + jr eq,ReadLoop + + cp a,'+' ; Pluszeichen gnadenhalber zulassen + jr ne,NoPlus ; ist aber nur ein Dummy + bit 0,(ix+Flags+1) ; schon ein Vorzeichen dagewesen ? + jp nz,Error ; dann Fehler + set 0,(ix+Flags+1) ; ansonsten einfach setzen + jr ReadLoop +NoPlus: + cp a,'-' ; Minuszeichen bewirkt schon eher etwas + jr ne,NoMinus + bit 0,(ix+Flags+1) ; darf auch nur einmal auftreten + jp nz,Error + set 0,(ix+Flags+1) + cp (ix+Flags),1 ; je nach Phase anderes Flag setzen + jr ne,MinPhase3 + set 1,(ix+Flags+1) ; bei Mantisse Bit 1... + jr ReadLoop +MinPhase3: set 2,(ix+Flags+1) ; ...bei Exponent Bit 2 + jr ReadLoop +NoMinus: + cp a,'.' ; Umschaltung Phase 2 (Nachkomma) ? + jr ne,NoPoint + cp (ix+Flags),1 ; bish. Phase muá Eins sein + jp ne,Error + ld (ix+Flags),2 ; neue Phase eintragen + set 0,(ix+Flags+1) ; Nachkomma darf kein Vorzeichen haben + ld bc,(Tenth) ; im Nachkomma durch 10 teilen + ld (ix+Factor),bc + ld bc,(Tenth+2) + ld (ix+Factor+2),bc + jr ReadLoop +NoPoint: + cp a,'e' ; kleines & groáes E zulassen + jr eq,IsE + cp a,'E' + jr ne,NoE +IsE: cp (ix+Flags),3 ; vorh. Phase muá 1 oder 2 sein + jp eq,Error + ld (ix+Flags),3 ; vermerken + res 0,(ix+Flags+1) ; Vorzeichen wieder zulassen + jr ReadLoop +NoE: + sub a,'0' ; jetzt nur noch 0..9 zugelassen + jp c,Error + cp a,9 + jp ugt,Error + set 0,(ix+Flags+1) ; nach Ziffern keine Vorzeichen mehr zulassen + + cp (ix+Flags),1 ; Phase 1 (Mantisse) : + jr ne,NoPhase1 + cpsh bc,ix+Mant ; bish. Mantisse * 10 + cpsh bc,ix+Factor + call fmul + push bc ; Ziffer dazuaddieren + push de + ld e,a + ld d,0 + ld bc,0 + push bc + push de + call fitof + push bc + push de + call fadd + ld (ix+Mant),de ; Mantisse zurcklegen + ld (ix+Mant+2),bc + jrl ReadLoop +NoPhase1: + cp (ix+Flags),2 ; Phase 2 (Nachkomma) : + jr nz,NoPhase2 + ld e,a ; Stelle nach Float + ld d,0 + ld bc,0 + push bc + push de + call fitof + push bc ; mit Zehnerpotenz skalieren + push de + cpsh bc,ix+Factor + call fmul + push bc ; zur Mantisse addieren + push de + cpsh bc,ix+Mant + call fadd + ld (ix+Mant),de ; Mantisse zurcklegen + ld (ix+Mant+2),bc + cpsh bc,ix+Factor ; Faktor * 1/10 + cpsh bc,Tenth + call fmul + ld (ix+Factor),de + ld (ix+Factor+2),bc + jrl ReadLoop +NoPhase2: + ld hl,(ix+Exp) + mul hl,10 ; Exponent heraufmultiplizieren + add a,l + ld l,a + ld a,0 + adc h,0 + cp hl,45 ; Minimum ist 1E-45 + jr ugt,Error + ld (ix+Exp),hl + jrl ReadLoop + +Combine: ld hl,(ix+Exp) + bit 2,(ix+Flags+1) ; Exponent negativ ? + jr z,ExpPos + xor hl,-1 + inc hl +ExpPos: call fPot10 ; Zehnerpotenz des Exponenten bilden + push bc + push de + cpsh bc,ix+Mant ; mit Mantisse kombinieren + call fmul + bit 1,(ix+Flags+1) ; Mantisse negativ ? + jr z,ManPos + set 7,b +ManPos: rcf ; Ende ohne Fehler + +End: pop iy ; Register zurck + pop hl + pop af + + unlk ix ; Rahmen abbauen + retd 2 ; Ende + +Error: ld hl,iy ; rel. Zeichenposition ermitteln + sub hl,(ix+SrcAddr) + ld bc,hl + scf ; Ende mit Fehler + jr End + + endp + +;------------------------------------------------------------------------------ +; gemeinsames Ende + + endsection + diff --git a/tests/t_fl90/macros.inc b/tests/t_fl90/macros.inc new file mode 100644 index 0000000..d949ddc --- /dev/null +++ b/tests/t_fl90/macros.inc @@ -0,0 +1,57 @@ +; MACROS.INC +;****************************************************************************** +;* überall gebrauchte Makros * +;* * +;* Alfred Arnold, Oktober 1993 * +;****************************************************************************** + +proc macro name,{NoExpand} ; Prozedureintritt + section name + forward LocalSize ; lokal reservierter Speicher auf Stack +LocalSize eval 0 + public name +name label $ + endm + +subproc macro name,{NoExpand} ; Prozedureintritt für private Routine + section name + forward LocalSize ; lokal reservierter Speicher auf Stack +LocalSize eval 0 + public name:Parent +name label $ + endm + +endp macro name,{NoExpand} ; Prozeduraustritt +LocalSize eval 0-LocalSize ; damit man's im Listing lesen kann + endsection name + endm + +link macro reg,count,{NoExpand} ; Stack-Rahmen einrichten + push reg ; alten Basepointer retten + ld reg,sp ; neuen aufbauen + if count<>0 + add sp,count ; Platz auf Stack reservieren + endif + endm + +unlk macro reg,{NoExpand} ; Stack-Rahmen abbauen + ld sp,reg ; Speicherreservierung zurücknehmen + pop reg ; alten Basepointer zurück + endm + +retd macro dist,{NoExpand} ; Return and Deallocate + if dist<>0 + push hl ; Arbeitsregister retten + ld hl,(sp+2) ; Rücksprungadresse umkopieren + ld (sp+2+dist),hl + ld hl,(sp) ; Arbeitsregister zurück + add sp,2+dist ; Stack aufräumen + endif + ret + endm + +DefLocal macro Name,Size,{NoExpand} ; eine lokale Variable definieren +LocalSize eval LocalSize-Size ; zählt lok. reservierten Speicher +Name equ LocalSize ; liegt an neuem unteren Ende des Stackrahmens + endm + diff --git a/tests/t_fl90/mon.inc b/tests/t_fl90/mon.inc new file mode 100644 index 0000000..46e08d3 --- /dev/null +++ b/tests/t_fl90/mon.inc @@ -0,0 +1,11 @@ +MRET EQU 0080H ; RETURN TO MONITOR +CONIN EQU 0083H ; CONSOLE INPUT +COSTAT EQU 0086H ; CONSOLE STATUS +CONOUT EQU 0089H ; CONSOLE OUTPUT +TXTAUS EQU 008CH ; TEXT-OUTPUT +PSTR EQU 008FH ; STRING OUTPUT +A_ASC EQU 0092H ; CONVERT CONTENT OF A TO ASCII +HL_ASC EQU 0095H ; CONVERT CONTENT OF HL TO ASCII +BLAUS EQU 0098H ; BLANK OUTPUT +GETZEIL EQU 009BH ; READ LINE + diff --git a/tests/t_fl90/t_fl90.asm b/tests/t_fl90/t_fl90.asm new file mode 100644 index 0000000..3e53195 --- /dev/null +++ b/tests/t_fl90/t_fl90.asm @@ -0,0 +1,179 @@ +; FTEST.ASM +;****************************************************************************** +;* Testet Gleitkommabibliothek für TLCS90 * +;* * +;* Hardware: TDB-TMP90 * +;* Software: AS 1.39p5 oder höher * +;* Includes MACROS.INC, FLOAT.INC, CPU_TIME.INC * +;* * +;* Übersetzen mit AS ftest oder beiliegendem Makefile * +;* * +;****************************************************************************** + + cpu 90c141 + + org 8500h ; Startadresse User-RAM + +;------------------------------------------------------------------------------ + +CR equ 13 +LF equ 10 +Format_Tab equ 0000100000000110b ; fftoa-Format für tab. Ausgabe +Format_Min equ 0010001100000101b ; fftoa-Format für minimale Länge +; ^<+>^^<--+---> +; | | || | +; | | || +------ Maximalzahl Nachkommastellen +; | | |+---------- Mantissenpluszeichen unterdrücken +; | | +----------- Exponentenpluszeichen unterdrücken +; | +------------- Minimalstellenzahl Exponent +; +--------------- anhängende Nullen in Mantisse löschen +Format equ Format_Tab ; gewähltes fftoa-Format + +;------------------------------------------------------------------------------ +; Vorgaben + + include stddef90.inc ; Registeradressen + include macros.inc ; für Unterroutinen benötigte Makros + include mon.inc ; Einsprungadressen TDBTMP90-Monitor + + section MainProg + +;------------------------------------------------------------------------------ +; Makros zur Schreiberleichterung + +pushop macro adr,{NoExpand} ; einen Operanden auf den Stack legen + ld hl,(adr+2) + push hl + ld hl,(adr) + push hl + endm + +storeop macro {NoExpand} ; Ergebnis in Array ablegen + ld (iy),de + ld (iy+2),bc + add iy,4 + endm + +OneOp macro Msg,Operation,Op1,Op2,{Expand} ; Aufruf, Ausgabe und + call PSTR ; Zeitmessung + db Msg,0 + call StartTimer + if "OP1"<>"" + pushop Op1 + endif + if "OP2"<>"" + pushop Op2 + endif + call Operation + storeop + call StopTimer + if (("OPERATION"<>"FNOP") && ("OPERATION"<>"FFTOI")) + call PSTR + db ", Ergebnis ",0 + push bc + push de + ld hl,Format + push hl + ld hl,CharBuffer + push hl + call fftoa + call TXTAUS + endif + call PSTR + db CR,LF,0 + endm + +;------------------------------------------------------------------------------ +; Hauptroutine + + proc Main + + ld sp,Stack ; Stack reservieren + ld iy,Erg ; Zeiger auf Ergebnisfeld + call InitTimer ; Zeitmessung vorinitialisieren + + OneOp "Ladeoverhead : ",fnop,Eins,Eins + OneOp "Addition 2+Pi : ",fadd,Zwei,Pi + OneOp "Addition 100000+2 : ",fadd,Thou,Zwei + OneOp "Addition 0+1 : ",fadd,Null,Eins + OneOp "Subtraktion Pi-2 : ",fsub,Pi,Zwei + OneOp "Subtraktion 100000-1 : ",fsub,Thou,Eins + OneOp "Multiplikation 2*Pi : ",fmul,Zwei,Pi + OneOp "Division 1/Pi : ",fdiv,Eins,Pi + OneOp "Wurzel aus 2 : ",fsqrt,Zwei, + OneOp "Wurzel aus 10000 : ",fsqrt,Thou, + OneOp "Wurzel aus -1 : ",fsqrt,MinEins, + OneOp "Wandlung 1-->Float : ",fitof,IntEins, + OneOp "Wandlung 1E5-->Float : ",fitof,IntThou, + OneOp "Wandlung 1-->Int : ",fftoi,Eins, + OneOp "Wandlung 1E5-->Int : ",fftoi,Thou, + ld a,10 + OneOp "Pi*2^10 : ",fmul2,Pi, + ld a,-10 + OneOp "Pi*2^(-10) : ",fmul2,Pi, + + call PSTR + db "Eingabe: ",0 + ld hl,InpBuffer + call TXTAUS + ld hl,InpBuffer + push hl + call fatof + storeop + call PSTR + db ", Ergebnis: ",0 + push bc + push de + ld hl,Format + push hl + ld hl,CharBuffer + push hl + call fftoa + call TXTAUS + call PSTR + db 13,10,0 + + jp MRET + + endp + + proc fnop ; Dummyroutine fr Overheadmessung + + link ix,0 + unlk ix + + retd 8 + + endp + +CharBuffer: db 30 dup (?) ; Puffer fr fftoa +InpBuffer: db "-123.456E-7",0 ; Puffer fr fatof + + align 4 +Eins: dd 1.0 ; ben”tigte Konstanten +MinEins: dd -1.0 +Zwei: dd 2.0 +Pi: dd 40490fdbh ; um Vergleichsfehler durch Rundung zu + ; vermeiden +Zehn: dd 10.0 +Null: dd 0.0 +Thou: dd 100000.0 +IntEins: dd 1 +IntThou: dd 100000 +Erg: dd 40 dup (?) ; Ergebnisfeld + + align 2 ; Platz fr Stack + db 300 dup (?) +Stack: + endsection + +;------------------------------------------------------------------------------ +; ben”tigte Module + + include cpu_time.inc ; Zeitmessung + include float.inc ; Gleitkommabibliothek + +;------------------------------------------------------------------------------ + + end Main + diff --git a/tests/t_fl90/t_fl90.doc b/tests/t_fl90/t_fl90.doc new file mode 100644 index 0000000..668986f --- /dev/null +++ b/tests/t_fl90/t_fl90.doc @@ -0,0 +1,6 @@ ++------------------------ Test Application FL90 -----------------------------+ +| | +| This is an IEEE single precision floating point library for the Toshiba | +| TLCS-90 microcontroller, embedded into a small test program. | +| | ++-----------------------------------------------------------------------------+ diff --git a/tests/t_fl90/t_fl90.ori b/tests/t_fl90/t_fl90.ori new file mode 100644 index 0000000..4aff532 Binary files /dev/null and b/tests/t_fl90/t_fl90.ori differ diff --git a/tests/t_fl900/asflags b/tests/t_fl900/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_fl900/conout.inc b/tests/t_fl900/conout.inc new file mode 100644 index 0000000..6483884 --- /dev/null +++ b/tests/t_fl900/conout.inc @@ -0,0 +1,154 @@ +; CONOUT.INC +;****************************************************************************** +;* Konsolenausgabe fr Micro-ICE TLCS900 * +;* * +;* Routinen CONOUT, PSTR, A_ASC von Oliver Sellke * +;* Routine WriteDec von Alfred Arnold, Oktober 1993 * +;* 20.11.1993 StrTerm C-konform auf 00h ge„ndert * +;* TXTAUS hinzugefgt * +;* * +;* Routine Funktion Eingabe Stack * +;* * +;* CONOUT Zeichen ausgeben A 1..3 Byte * +;* TXTAUS String ausgeben (XHL) * +;* PSTR String ausgeben hinter CALL+StrTerm als Ende 6 Byte * +;* A_ASC Byte hex ausgeben A 2 Byte * +;* WriteDec Wort dez ausgeben WA 6 Byte * +;* * +;* - Da die Routinen lokale Labels verwenden, ist mindestens AS 1.39 erfor- * +;* derlich * +;* - Der Prozessor muá sich im Maximum-Modus befinden * +;* - Symbol SIODelay setzen, falls langsames Terminal vorhanden * +;* - MACROS.INC muá vorher eingebunden werden * +;****************************************************************************** + +;------------------------------------------------------------------------------ +; gemeinsamer Anfang, Definitionen + + section ConOut + + public StrTerm +StrTerm equ 0 + +SC0BUF EQU 050H +INTES0 EQU 077H + +;****************************************************************************** +; (7 bit ASCII) Ausgabe ber SIO-Kanal 0 + + proc CONOUT + PUSH A ;sichern + RES 7,A ;MSB ausblenden (nur ASCII!) +CONOUT1: BIT 7,(INTES0) ;ist der Buffer frei? + JR Z,CONOUT1 ;Wenn nicht, dann weiter prfen + LD (INTES0),0Dh ;Flag rcksetzen + LD (SC0BUF),A ;Zeichen in Transmit-Buffer + ifdef SIODelay + PUSH HL ;sichern + LD HL,80H ;Verz”gerungszeit laden +WAIT: DEC 1,HL ;Z„hler - 1 + CP HL,0 ;Ist Z„hler = 0? + JR NZ,WAIT ;Wenn nicht, dann weiter DEC + POP HL ;restaurieren + endif + POP A ;restaurieren + RET ;Zurck zum Aufruf + endp + +;****************************************************************************** +; ASCIIZ-String ab (XHL) ausgeben: + + proc TXTAUS + push xhl ; Register retten + push a +Schl: ld a,(xhl+) ; ein Zeichen holen + cp a,StrTerm ; Endemarkierung ? + jr eq,Ende + call CONOUT ; nein, ausgeben + jr Schl ; Go on... +Ende: pop a ; Register zurck + pop xhl + ret + endp + +;****************************************************************************** +; String der dem Aufruf folgt bis zur Endemarkierung ausgeben +; Siehe auch TXTAUS: + + proc PSTR + PUSH XHL ;sichern + LD XHL,(XSP+4) ;Datenadresse lesen + PUSH F ;sichern + PUSH A ;dito +PSTR1: LD A,(XHL) ;Zeichen holen + INC 1,C ;Zeichenz„hler + 1 + INC 1,XHL ;Zeichenzeiger + 1 + CP A,StrTerm ;Endemarkierung erwischt? + JR Z,PSTR2 ;Wenn ja, dann Ende + AND A,A ;Null-Zeichen erwischt? + JR Z,PSTR1 ;Wenn ja, dann nicht ausgeben + CALL CONOUT ;Zeichen ausgeben + AND A,A ;War das 8. Bit gesetzt? + JR P,PSTR1 ;Wenn nicht, dann n„chstes Zeichen +PSTR2: POP A ;restaurieren + POP F ;dito + LD (XSP+4),XHL ;Rcksprungadresse restaurieren + POP XHL ;Rcksprungadresse abspeichern + RET ;Zurck zum Aufruf + endp + +;****************************************************************************** +; "A" als ASCII Text ausgeben + + proc A_ASC + PUSH F ;Sichern + PUSH A ;dito + RR 4,A ;high nibble an die richtige + CALL A_ASC00 ;Stelle und ausgeben + POP A ;restaurieren bzw. + POP F ;low nibble laden +A_ASC00: AND A,00FH ;low nibble maskieren + CP A,00AH ;eine Zahl ? + JR C,A_ASC01 ;ja + ADD A,007H ;Offset A-F +A_ASC01: ADD A,'0' ;Offset ASCII + JP CONOUT ;Ausgabe und Ende UP + endp + +;****************************************************************************** +; Zahl in WA dezimal ausgeben +; C = minimale Stellenzahl +; B = Fllzeichen (z.B. ' ', '0') + + proc WriteDec + push xwa ; Register retten + push de + + sub de,de ; E z„hlt echte Stellenzahl, D=1 falls Null +InLoop: extz xwa ; fr Division vorbereiten + div xwa,10 ; letzte Stelle ausmaskieren + add qa,'0' ; ASCII-Offset + cp d,1 ; schon im Nullbereich ? + jr ne,NormVal + ld qa,b ; ja, dann gewnschtes Leerzeichen +NormVal: push qa ; ein Zeichen mehr + inc e + or wa,wa ; schon Null ? + scc z,d + jr nz,InLoop ; wenn nicht Null, auf jeden Fall weiter + cp e,c ; noch nicht genug Zeichen ? + jr ult,InLoop ; dann auch weiter + +OutLoop: pop a ; umgekehrt ausgeben + call ConOut + djnz e,OutLoop + + pop de + pop xwa + ret + endp + +;****************************************************************************** +; Modulende + + endsection diff --git a/tests/t_fl900/cpu_time.inc b/tests/t_fl900/cpu_time.inc new file mode 100644 index 0000000..1240be2 --- /dev/null +++ b/tests/t_fl900/cpu_time.inc @@ -0,0 +1,240 @@ +; CPU_TIME.INC +;************************************************************************* +;* * +;* Author...: Oli(ver Sellke) D-65199 Wiesbaden * +;* auf AS umgestellt von Alfred Arnold, Oktober 1993 * +;* die Low-Level-Ausgaberoutinen sind nach CONOUT.INC verlagert * +;* Date.....: 14 Okt 1993 Version..: 1.0 * +;* Target...: TLCS900-Family (TOSHIBA) Compiler.: AS V1.39p1 * +;* Project..: General Purpose / e.g. TMP96C141F / Watt Ihr Volt * +;* * +;* Function.: Mit dieser Routine kann man die Ausfhrungszeit die * +;* ein Programm(teil) ben”tigt ermitteln. * +;* Die Zeit wird mit Timer4 und CAP1 davon gemessen, d.h. * +;* dieser darf innerhalb des gemessenen Programm(teil)s * +;* nicht (!) benutzt werden. * +;* !!! Alle Zeiten beziehen sich auf einen 14,7456MHz Quarz!! * +;* Zur Ausgabe des Messwertes werden Monitor-Routinen benutzt,* +;* deshalb kann es auch nur unter Anwendung von diesem zur * +;* Ausfhrung gebracht werden. * +;* Wenn ein Programm(teil) getestet wird, dessen Ausfhrungs- * +;* zeit unbekannt ist, sollte man die 8,681æs Aufl”sung w„hlen* +;* um einen Overrun des Counters zu verhindern. Wenn der Wert * +;* entsprechend klein ist ( <0FFF ), kann man die 0,543æs Auf-* +;* l”sung w„hlen um genauere Werte zu bekommen. * +;* Auáerdem ist die Ermittlung der 16 gr”áten und 16 kleinsten* +;* Werte die bei mehreren Durchl„ufen erzielt wurden m”glich! * +;* Man kann so einige 1000 Durchl„ufe fahren mit immer unter- * +;* schiedlichen Randbedingungen auf die der zu testende Pro- * +;* teil entsprechend reagiert und auch Zeit ben”tigt. * +;* So hat man sicher die minimale und maximale Laufzeit. * +;* * +;* Bei allgemeiner Verwendung: * +;* Max.Meáwert=0FFFFH = 35.585æs bei 0,543æs Aufl”sung * +;* Max.Meáwert=0FFFFH = 568.909æs bei 8,681æs Aufl”sung * +;* * +;* Hardware.: getested auf Micro-ICE TLCS900 mit 14,7456MHz Quarz !!!! * +;* * +;* Routine Funktion Ausgabe Stack * +;* * +;* CPU_TI_INI Initialisierung ------ 6 Byte * +;* CPU_TIME Uhr starten ------ 0 Byte * +;* CPU_STOP Uhr stoppen Zeit+Statistik 8 Byte * +;* * +;* - Der Prozessor muá sich im Maximum-Modus befinden * +;* - Symbol BigTime definieren fr gr”áere Aufl”sung * +;* - Da die Routinen lokale Labels verwenden, ist mindestens AS 1.39 * +;* erforderlich * +;* - MACROS.INC muá vorher, CONOUT.INC irgendwo eingebunden werden * +;************************************************************************* + +;------------------------------------------------------------------------- +; gemeinsamer Anfang, Definitionen + + section Timer + +TRUN EQU 020H +CAP1L EQU 034H +CAP1H EQU 035H +T4MOD EQU 038H + +CR EQU 0DH +LF EQU 0AH + + ifdef BigTime +Overhead equ 1 ; Eigenverbrauch Start/Stop + elseif +Overhead equ 9 + endif + +CPU_TI_FAA db 40h dup (?) ; FeldAnfangsAdresse, ab hier wer- + ; den 40H (64) RAM-Zellen ben”tigt + ; gleich 2 * 16 Worte +CPU_TI_CR dd ? ; CPU_TIME-Control-Register, + ; wird noch nicht ben”tigt!!! + +;************************************************************************* +;Dieser Aufruf geh”rt in den Initialisierungsbereich des zu testenden +;Programmabschnittes!! + + proc CPU_TI_INI + +;Hier werden die Feldwerte initialisiert.. + + PUSH XDE ;Wird gleich benutzt + PUSH BC ;Wird gleich benutzt + LD B,10H ;16 W”rter fr Max.Werte werden gebraucht + LD XDE,CPU_TI_FAA ;FeldAnfangsAdresse laden +CPU_TI_INI1: LDW (XDE),00000H ;Feldzelle fr Max.Werte initalisieren + INC 2,XDE ;n„chste Max.Wert-Feldzelle + ;adressieren + DJNZ CPU_TI_INI1 ;Alle Max.Werte initialisiert? + LD B,10H ;16 W”rter fr Min.Werte werden gebraucht +CPU_TI_INI2: LDW (XDE),0FFFFH ;Feldzelle fr Min.Werte initalisieren + INC 2,XDE ;n„chste Max.Wert-Feldzelle + ;adressieren + DJNZ CPU_TI_INI2 ;Alle Min.Werte initialisiert? + POP BC ;Und wieder restaurieren + POP XDE ;hier auch... + RET ;Zurck zum Aufruf! + endp + +;************************************************************************* +; Uhr starten + + proc CPU_TIME + + ;Timer4 CPU-Time-Messung vorbereiten + RES 4,(TRUN) ;Timer4 stop and clear ! + ifdef BigTime + LD (T4MOD),00100011B ;Bit 0+1:Source-Clock: 8,681æs + elseif + LD (T4MOD),00100001B ;Bit 0+1:Source-Clock: 0,543æs + endif + ;Bit 2 :clear from TREG5 disabled + ;Bit 3+4:INT-Capture disabled + ;Bit 5 :No Sw. capture now + SET 4,(TRUN) ;Timer4 start and count ! + RET + endp + +;************************************************************************* + + proc CPU_STOP + + RES 5,(T4MOD) ;Capture1 grabs count + CALL CPU_TI_SOUT ;Einzelausgabe des gemessenen Wertes + CALL CPU_TI_SOR ;gemessenen Wert ins Feld sortieren + RET ;Zurck zum Aufruf! + endp + +;************************************************************************* +;Hier wird der gerade gemessene Wert ausgegeben. Diese Ausgabe ist +;ausreichend um Laufzeitwerte von statischen Programmabschnitten +;zu ermitteln (keine Verzweigungen im Programmabschnitt). + +CPU_TI_SOUT: PUSH A ; needed little later + PUSH F ; needed little later + push bc ; needed little later + ld wa,(cap1l) ; gemesser Wert + call WriteTime + pop bc ; back to the roots ... + POP F + POP A + RET ; Zurck zum Aufruf! + +;************************************************************************* +;Hier werden die ermittelten Werte sortiert abgelegt! +;Jeweils am Feldanfang steht der gr”áte und der kleinste Wert. +;Falls ein Wert einem anderen im Feld entspricht (gleicher Messwert) +;wird dieser nicht nochmal eingetragen!!!! +;!!Achtung diese Routine ben”tigt max. 145æs (14,7456MHz Quarz) +; im worst case!! Aber nur wenn Daten und Code 16Bit breit sind +; und keine Waitstates zugeschaltet sind (Micro-ICE TLCS900 default RAM)! + +CPU_TI_SOR: PUSH HL ;Wird gleich benutzt + PUSH BC ;Wird gleich benutzt + PUSH XDE ;Wird gleich benutzt + ;Max.Werte sortiert ablegen!!! + LD B,10H ;16 W”rter enth„lt Max.Wert-Feld + LD HL,(CAP1L) ;gemessenen Wert aus Capture-Reg. holen + LD XDE,CPU_TI_FAA ;erste Max.Wert-Feldzelle adressieren +CPU_TI_SOR1: CP HL,(XDE) ;Wert mit Feldinhalt vergleichen + JR ULT,CPU_TI_SOR2 ;Ist Wert kleiner als Feldinhalt? + JR Z,CPU_TI_SOR3 ;Ist Wert gleich Feldinhalt? Abbrechen! + EX (XDE),HL ;Nein-->Wert mit Feldinhalt tauschen! +CPU_TI_SOR2: INC 2,XDE ;n„chste Feldzelle adressieren + DJNZ B,CPU_TI_SOR1 ;Alle 16 Max.Werte kontrolliert? + ;Min.Werte sortiert ablegen!!! +CPU_TI_SOR3: LD B,10H ;16 W”rter enth„lt Min.Wert-Feld + LD HL,(CAP1L) ;gemessenen Wert aus Capture-Reg. holen + LD XDE,CPU_TI_FAA+20H ;erste Min.Wert-Feldzelle adressieren +CPU_TI_SOR4: CP HL,(XDE) ;Wert mit Feldinhalt vergleichen + JR UGT,CPU_TI_SOR5 ;Ist Wert gr”áer als Feldinhalt? + JR Z,CPU_TI_SOR6 ;Ist Wert gleich Feldinhalt? Abbrechen! + EX (XDE),HL ;Nein-->Wert mit Feldinhalt tauschen! +CPU_TI_SOR5: INC 2,XDE ;n„chste Feldzelle adressieren + DJNZ B,CPU_TI_SOR4 ;Alle 16 Min.Werte kontrolliert? +CPU_TI_SOR6: POP XDE ;Und wieder restaurieren + POP BC ;wieder restaurieren + POP HL ;hier auch... + RET ;Zurck zum Aufruf! + +;************************************************************************* +;Hier werden die im Feld abgelegten Werte ausgeben. + +CPU_TI_MOUT: ;Muá noch geschrieben werden! + RET ;Zurck zum Aufruf! + +;************************************************************************* +; eine Zeitdifferenz in WA umrechnen und ausgeben +; wegen der Aufl”sung der Timer ist die letzte Stelle hinter dem Komma +; bei hoher Aufl”sung mit Vorsicht zu genieáen + +WriteTime: push xwa ; Register retten + push bc + sub wa,Overhead ; Zeit korrigieren + ifdef BigTime ; Fall 1: niedrige Aufl”sung + mul xwa,8681 ; -->Nanos in XWA + add xwa,5000 ; !!Rundung!! + div xwa,10000 ; Nanos , einzelne Mikros wegschmeiáen + extz xwa + div xwa,100 ; Millisekunden in WA + ld bc,2003h ; ausgeben + call WriteDec + ld a,'.' + call CONOUT + ld wa,qwa ; auf 10 us genau ausgeben + ld bc,3002h + call WriteDec + call PSTR + db " Milli",StrTerm + elseif ; Fall 2: hohe Aufl”sung + mul xwa,543 ; -->Nanosekunden in XWA + div xwa,1000 ; -->Nanos in QWA, Mikros in WA + ld bc,2005h ; Mikros 5-stellig mit Blanks + call WriteDec + ld a,'.' + call CONOUT + ld wa,qwa ; Nanos einstellig + add wa,50 ; Rundung + extz xwa + div xwa,100 ; Ergebnis 0..9 + cp wa,10 + jr ne,NoErr + ld wa,9 +NoErr: ld bc,3001h ; einstellig ausgeben + call WriteDec + call PSTR + db " Mikro",StrTerm + endif + call PSTR + db "sekunden",StrTerm ; gemeinsamer Rest + pop bc ; Register zurck + pop xwa + ret + +;************************************************************************* +; gemeinsames Ende + + endsection diff --git a/tests/t_fl900/float.inc b/tests/t_fl900/float.inc new file mode 100644 index 0000000..dd4796c --- /dev/null +++ b/tests/t_fl900/float.inc @@ -0,0 +1,973 @@ +; FLOAT.INC +;****************************************************************************** +;* Gleitkommabibliothek fr TLCS 900 * +;* * +;* Originale fr den 68000 aus mc, bis auf die Quadratwurzel aus c't * +;* Portierung auf TLCS 900 von Alfred Arnold, Oktober 1993 * +;* * +;* Routine Funktion Eingabe Ausgabe Stack L„nge Zeit/14MHz * +;* * +;* fadd Addition XWA+XHL XWA 12 Byte 194 Byte 60 us * +;* fsub Subtraktion XWA-XHL XWA 12 Byte 7 Byte 65 us * +;* fmul Multiplikation XWA*XHL XWA 20 Byte 218 Byte 70 us * +;* fdiv Division XWA/XHL XWA 20 Byte 147 Byte 300 us * +;* fmul2 Mult. mit 2er-Potenz XWA*(2^BC) XWA 6 Byte 99 Byte 20 us * +;* fitof Int-->Float XWA XWA 4 Byte 41 Byte 90 us * +;* fftoi Float-->Int XWA XWA 2 Byte 72 Byte 20 us * +;* fsqrt Quadratwurzel XWA XWA 16 Byte 192 Byte 220 us * +;* fftoa Float-->ASCII XWA (XHL),BC ~38 Byte 228 Byte ~4500 us * +;* fatof ASCII-->Float (XHL),BC XWA,[BC] ~40 Byte 260 Byte ~2300 us * +;* * +;* - Wollen Sie einzelne Routinen entfernen, so beachten Sie, daá fsub Teile * +;* aus fadd und fdiv Teile aus fmul verwendet ! * +;* - Gleitkommaformat ist IEEE Single (32 Bit) * +;* - Integerwerte bei fmul2, fitof und fftoi sind vorzeichenbehaftet * +;* - Der Prozessor muá sich im Maximum-Modus befinden * +;* - Da die Routinen lokale Labels verwenden, ist mindestens AS 1.39 erfor- * +;* derlich * +;* - Die Ausfhrungszeiten k”nnen je nach Operand streuen, insbesondere bei * +;* den Konvertierungsfunktionen * +;* - MACROS.INC muá vorher eingebunden werden * +;****************************************************************************** + +;------------------------------------------------------------------------------ +; gemeinsamer Anfang, Makros + +shifta macro op,dest ; Schieben, falls evtl. A>=16 + push a ; A wird zerschossen + bit 4,a ; Akku im Bereich 16..31 ? + jr z,smaller + op 16,dest ; dann einmal groá schieben +smaller: push f ; Carry erhalten + and a,15 ; obere Bits pl„tten + jr z,fertig + pop f ; evtl. Rest verarbeiten + op a,dest + jr ende ; Carry schon gut +fertig: pop f +ende: pop a ; A zurck + endm + + section FloatLib + +;------------------------------------------------------------------------------ +; Konstanten + +Ld10: dd ld(10) ; Konversionskonstanten +One: dd 1.0 +Half: dd 0.5 +Ten: dd 10.0 +Tenth: dd 3dcccccdh ; =0.1, aber die Rundung auf manchen + ; Systemen variiert (damit Test nicht + ; scheitert) + +Bias equ 127 +MaxExpo equ 255 +Comma equ '.' + +;------------------------------------------------------------------------------ +; Addition: XWA=XWA+XHL + + proc fadd + + push xbc ; andere Register retten + push xde + push xhl + + ld xde,xwa ; Operand 1 nach XDE verschieben + rlc 1,xde ; Vorzeichen der Operanden nach Bit 0 + rlc 1,xhl + ld xbc,xde ; Differenz bilden + sub xbc,xhl + jr nc,NoSwap ; evtl. vertauschen, so daá + ld xwa,xhl ; gr”áere in XDE + ld xhl,xde + ld xde,xwa +NoSwap: ld qa,e ; Vorzeichen 1 ausmaskieren + and qa,1 ; (=Ergebnis Vorzeichen) + bit 0,c ; gleiches Vorzeichen ? + jr z,NoSub + set 1,qa ; dann Subtraktion vormerken + +NoSub: sub xbc,xbc ; XBC initialisieren + rlc 8,xde ; Exponent 1 rausholen + ld c,e + or e,e ; falls <>0, implizite 1 einbauen + scc nz,e + rrc 1,xde + ld e,0 ; Bit 0..7 wieder pl„tten + + rlc 8,xhl ; dito Exponent 2 extrahieren + ld qc,l + or l,l + scc nz,l + rrc 1,xhl + ld l,0 + +; Zwischenstand: +; - Mantissen linksbndig inkl. impliziter Eins in XDE und XHL +; - Exponent 1 in BC, Exponent 2 in QBC +; - Ergebnisvorzeichen in QA, Bit 0 +; - Subtraktionsflag in QA, Bit 1 + + ld wa,bc ; Exponentendifferenz berechnen + sub wa,qbc + cp wa,24 ; >24, d.h. Zahl 2 vernachl„ssigbar gegen Zahl 1 + jr gt,Round ; ja, Ergebnis ist gr”áere Zahl + shifta srl,xhl ; ansonsten Mantisse 2 entspr. anpassen + +Add: bit 1,qa ; subtrahieren ? + jr nz,Subtract ; ja--> + add xde,xhl ; nein, Mantissen addieren + jr nc,Round ; kein šberlauf, runden + rr 1,xde ; ansonsten šberlauf einschieben... + inc bc ; ...und Exponent korrigieren + jr Round ; normal weiter runden + +Subtract: sub xde,xhl ; Mantissen subtrahieren + jr z,Zero ; falls Null, Gesamtergebnis 0 + jr m,Round ; fhrende 1 noch da: zum Runden +Normalize: or bc,bc ; Exponent bereits Null ? + jr z,Round ; dann denormales Ergebnis + dec bc ; ansonsten Mantisse eins rauf, Exponent + sll 1,xde ; eins runter + jr p,Normalize ; solange, bis Eins auftaucht + +Round: add xde,80h ; Rundung auf Bit hinter Mantisse + jr nc,NoOver + rr 1,xde ; Bei šberlauf korrigieren + inc bc +NoOver: ld e,0 ; Mantissenrest pl„tten + or xde,xde ; insgesamt 0 ? + jr z,Zero ; dann Ergebnis 0 + cp bc,MaxExpo ; Exponentenberlauf ? + jr lt,NoEOver + ld bc,MaxExpo ; ja: Unendlich: Exponent=Maximum + sub xde,xde ; Mantisse=0 + jr Denormal + +NoEOver: or bc,bc ; Exponent 0 ? + jr z,Denormal ; ja, denormal + sll 1,xde ; fhrende Eins nicht speichern +Denormal: ld e,c ; Exponenten einbauen + rrc 8,xde ; nach oben schieben + rr 1,qa ; Vorzeichen einbauen + rr 1,xde + +Zero: ld xwa,xde ; Ergebnis in Akku + + pop xhl ; Register zurck + pop xde + pop xbc + + ret + + endp + +;------------------------------------------------------------------------------ +; Subtraktion: XWA=XWA-XHL + + proc fsub + + xor qh,80h ; Vorzeichen 2 drehen + jp fadd ; ansonsten wie Addition + + endp + +;------------------------------------------------------------------------------ +; Multiplikation: XWA=XWA*XHL + + proc fmul + + public MulRound:Parent,MulZero:Parent,MulResult:Parent + public DivError:Parent + + push xbc ; Register retten + push xde + push xhl + push xix + push xiy + + ld xiy,xwa ; Op1 kopieren + xor xiy,xhl ; Ergebnisvorzeichen bestimmen + + ex wa,qwa ; Registerh„lften Op1 vertauschen + ld xde,xwa ; Op1 ab sofort in XDE + and de,7fh ; Exponent und Vz. behandeln + and wa,7f80h ; Exponent maskieren + jr z,Denorm1 ; gleich Null-->Op1 denormal + set 7,de ; ansonsten implizite Eins einbauen + sub wa,80h ; Bias kompensieren +Denorm1: + ex hl,qhl ; Op2 genauso behandeln + ld xbc,xhl + and hl,7fh + and bc,7f80h + jr z,Denorm2 + set 7,hl + sub bc,80h +Denorm2: + add bc,wa ; Exponenten addieren + srl 7,bc ; richtig positionieren + sub bc,Bias-3 ; Bias-3 abziehen + cp bc,-24 ; totaler Unterlauf ? + jr lt,MulZero ; dann Ergebnis 0 + + ld wa,de ; beide oberen H„lften multiplizieren + mul xwa,hl + ex wa,qwa ; Ergebnis in oberer H„lfte lagern + ld wa,de ; obere H„lfte Op1 retten + ex de,qde ; untere H„lfte Op1 holen + ld ix,hl ; untere H„lfte Op1 * obere Op2 + mul xix,de + ex hl,qhl ; untere Op1 * untere Op2 + mul xde,hl + ex de,qde ; obere Op1 * untere Op2 + mul xhl,wa + + ld wa,de ; Teile aufaddieren + add xwa,xix + add xwa,xhl + jr z,MulResult ; Mantisse Null, Ergebnis Null + jr m,MulRound + + or bc,bc ; Exponent negativ ? + jr m,Unterlauf ; ggfs. Unterlauf behandeln + +Nor: or bc,bc ; Exponent Null ? + jr z,MulRound ; ja-->zum Runden + rl 1,xde ; nein, Mantisse eins nachschieben + rl 1,xwa + dec bc ; und Exponent runter + or xwa,xwa ; fhrende Eins da ? + jr p,Nor ; nein, weiterschieben + +MulRound: add xwa,80h ; Rundung + jr nc,NoROver ; dabei šberlauf ? + rr 1,xwa ; ja: Mantisse & Exponent korrigieren + inc bc +NoROver: cp bc,MaxExpo ; Exponentenberlauf ? + jr lt,NoEOver +DivError: ld bc,MaxExpo ; dann unendlich einstellen + sub xwa,xwa + jr Denormal + +NoEOver: or bc,bc ; Exponent 0 ? + jr z,Denormal + sll 1,xwa ; fhrende 1 l”schen + +Denormal: ld a,c ; Exponent einbauen + rrc 8,xwa ; hochschieben + rl 1,xiy ; Vorzeichen einbauen + rr 1,xwa + +MulResult: pop xiy + pop xix + pop xhl + pop xde + pop xbc + + ret + +MulZero: sub xwa,xwa ; Null erzeugen + jr MulResult + +Unterlauf: cp bc,-24 ; totaler Unterlauf ? + jr le,MulZero ; dann Null + neg bc ; sonst umbauen + ld xde,xwa ; dazu Akku freimachen + sub wa,wa ; Endexponent + ex wa,bc ; ist 0 + shifta srl,xde ; Mantisse herunterschieben + ld xwa,xde ; Ergebnis zurck nach XWA + jr MulRound ; zurck mit Exponent 0 + + endp + +;------------------------------------------------------------------------------ +; Division: XWA=XWA/XHL + + proc fdiv + + push xbc ; Register retten (muá gleich zu fmul sein) + push xde + push xhl + push xix + push xiy + + ld xiy,xwa ; Op1 kopieren + xor xiy,xhl ; Ergebnisvorzeichen bestimmen + + ex wa,qwa ; Vorbehandlung wie bei fmul + ld xde,xwa + and de,7fh + and wa,7f80h + jr z,Denorm1 + set 7,de + sub wa,80h +Denorm1: + ex hl,qhl + ld xbc,xhl + and hl,7fh + and bc,7f80h + jr z,Denorm2 + set 7,hl + sub bc,80h +Denorm2: + sub wa,bc ; Exponentendifferenz bilden + ld bc,wa ; muá in BC liegen + sra 7,bc ; richtig positionieren + add bc,Bias ; Bias addieren + cp bc,-24 ; totaler Unterlauf ? + jr lt,MulZero ; ja, Ergebnis Null + + ex hl,qhl ; Format 0fff ... ffff 0000 0000 + or xhl,xhl ; Ergebnis unendlich ? + jrl z,DivError + sll 7,xhl + ex de,qde ; dito Divident + or xde,xde ; falls Null, Ergebnis Null + jrl z,MulZero + sll 7,xde + +NormLoop: bit 14,qhl ; Divisor normalisiert ? + jr nz,Normal + inc bc ; nein, Exponent RAUF (ist Ergebnisexponent) + sll 1,xhl + jr NormLoop + +Normal: sub xwa,xwa ; Ergebnisquotient vorbesetzen + add bc,25 ; Exponent nicht gr”áer als 0 + +Loop: ld xix,xde ; Divident zwischenspeichern + sub xde,xhl ; probeweise abziehen + ccf ; Carry drehen + jr c,IsOne ; ungedrehter Carry=1: Divisor paát + ld xde,xix ; ansonsten zurckkopieren +IsOne: rl 1,xwa ; Ergebnisbit einschieben + sll 1,xde ; Divident verschieben + dec bc ; Exponent runter + or bc,bc + jr z,Denorm ; falls Null, denormalisieren + bit 8,qwa ; fhrende Eins da ? + jr z,Loop ; nein, weiterrechnen + +Denorm: sll 7,xwa ; Mantisse positionieren + jrl z,MulResult ; Ergebnis 0 ? + jrl MulRound ; ansonsten zum Runden + + endp + +;----------------------------------------------------------------------------- +; Multiplikation mit Zweierpotenz: XWA=XWA*2^BC + + proc fmul2 + + push bc ; Register retten + push xde + + ld xde,xwa ; Vorzeichen merken + sll 1,xwa ; Vorzeichen rausschieben + jr z,Zero ; falls Null, Ergebnis Null + rlc 8,xwa ; Exponent nach unten... + sub de,de ; und in DE packen + add e,a + jr z,Denorm ; falls denormalisiert.. + or bc,bc ; Multiplikation oder Division ? + jr m,Divide ; (neg. Exponent=Division) + + add de,bc ; Exponent addieren + cp de,MaxExpo ; šberlauf ? + jr ge,Over ; ja, Ergebnis unendlich +Result: ld a,e ; Ergebnisexponent einbauen + rrc 8,xwa ; Exponent nach oben + rl 1,xde ; Vorzeichen einschieben + rr 1,xwa + +Zero: pop xde ; Register zurck + pop bc + ret + +Over: ld de,MaxExpo ; Ergebnis unendlich + sub xwa,xwa + jr Result + +Divide: add de,bc ; Exponentensumme bilden + jr gt,Result ; >0, keine Sonderbehandlung + scf ; ansonsten 1 explizit fr + rr 1,xwa ; denormale Zahl machen +DDenorm: or de,de ; Exponent=0 ? + jr z,Result ; ja, Ergebnis einfach denormal + srl 1,xwa ; ansonsten weiter denormalisieren + jr z,Zero ; dabei totaler Unterlauf->Null + inc de ; Exponent korrigieren + jr DDenorm +DDDenorm: add de,bc ; Exponentensumme bilden + jr DDenorm + +Denorm: or bc,bc ; Multiplikation oder Division ? + jr m,DDDenorm + sub a,a ; alten Exponenten l”schen +Norm: sll 1,xwa ; normalisieren... + jr c,Stop ; bis fhrende Eins da + dec bc ; oder 2. Exponent 0 + or bc,bc + jr nz,Norm + jr Result ; Multiplikator kompl. fr Normalisierung draufgegangen +Stop: add de,bc ; Rest addieren + jr Result ; alles andere schon o.k. + + endp + +;------------------------------------------------------------------------------ +; LongInt-->Float : XWA-->XWA + + proc fitof + + push xbc ; Register retten + + or xwa,xwa ; Null ? + jr z,Result ; dann Ergebnis Null + scc m,qc ; Vorzeichen nach QC, Bit 0 + jr p,Positive + cpl wa ; falls negativ,drehen + cpl qwa + inc xwa +Positive: ld bc,Bias+32 ; Exponent vorbesetzen +Shift: dec bc ; Mantisse verschieben + sll 1,xwa + jr nc,Shift + ld a,c ; Exponent einbauen + rrc 8,xwa ; Exponent nach oben + rr 1,qc ; Vorzeichen einbauen + rr 1,xwa + +Result: pop xbc ; Register zurck + ret + + endp + +;------------------------------------------------------------------------------ +; Float-->LongInt : XWA-->XWA + + proc fftoi + + push bc ; Register retten + + rl 1,xwa ; Vorzeichen in Carry + scc c,b ; in B merken + + rlc 8,xwa ; Exponent nach unten + ld c,a ; in C legen + sub c,Bias ; Bias abziehen + + jr m,Zero ; neg. Exponent -> Zahl<0 -> Ergebnis 0 + cp c,31 ; šberlauf ? + jr ge,Over + + scf ; fhrende Eins einschieben + rr 1,xwa + sub a,a ; Exponent l”schen + +Shift: srl 1,xwa ; jetzt schieben, bis Ergebnis stimmt + inc c + cp c,31 + jr ne,Shift + + srl 1,b ; negieren ? + jr nc,Positive + cpl wa ; ggfs. negieren + cpl qwa + inc xwa + +Positive: pop bc ; Register zurck + ret + +Zero: sub xwa,xwa ; Ergebnis 0 + jr Positive + +Over: ld xwa,7fffffffh ; šberlauf: Maxint zurckgeben + srl 1,b ; negativ ? + jr nc,Positive + cpl wa ; ja, neg. Maximum zurckgeben + cpl qwa + jr Positive + + endp + +;------------------------------------------------------------------------------ +; Quadratwurzel: XWA=SQRT(XWA) + + proc fsqrt + + push xbc ; Register retten + push xde + push xhl + push xix + + ld xix,xwa ; Argument retten + or xix,xix ; Zahl negativ ? + jrl m,DomainError ; dann geht es nicht + + ex ix,qix ; MSW holen + and xix,7f80h ; Exponent isolieren + jrl z,Zero ; keine Behandlung denormaler Zahlen + + and xwa,7fffffh ; Mantisse isolieren + sub ix,7fh*80h ; Bias vom Exponenten entfernen + bit 7,ix ; Exponent ungerade ? + res 7,ix + jr z,EvenExp + add xwa,xwa ; ja: Mantisse verdoppeln + add xwa,1000000h-800000h ; impl. Eins dazu +EvenExp: ; erste Iteration ohne impl. Eins + sra 1,ix ; Exponent/2 mit Vorzeichen + add ix,7fh*80h ; Bias wieder dazu + ex ix,qix ; neuen Exponenten in QIX aufheben + sll 7,xwa ; x ausrichten + ld xde,40000000h ; xroot nach erster Iteration + ld xhl,10000000h ; m2=2 << (MaxBit-1) +Loop10: ld xbc,xwa ; xx2 = x +Loop11: sub xbc,xde ; xx2 -= xroot + srl 1,xde ; xroot = xroot/2 + sub xbc,xhl ; x2 -= m2 + jr m,DontSet1 + ld xwa,xbc ; x = xx2 + or xde,xhl ; xroot += m2 + srl 2,xhl ; m2 = m2/4 + jr nz,Loop11 + jr WABCSame +DontSet1: srl 2,xhl ; m2 = m2/4 + jr nz,Loop10 ; 15* abarbeiten + ; Bit 22..8 + ld xbc,xwa ; 17. Iteration separat +WABCSame: sub xbc,xde + rrc 1,xde ; mitsamt Carry... + ex de,qde ; auf neues Alignment umstellen + sub xbc,1 ; Carry von 0-$4000: x2 -= m2 + jr m,DontSet7 + or xbc,-40000000h ; 0-$4000: x2 -= m2, Teil 2 + ld xwa,xbc + or de,4000h ; xroot += m2 +DontSet7: ex wa,qwa ; x auf neues Alignment umstellen + ld hl,1000h ; m2 - obere H„lfte schon 0 +Loop20: ld xbc,xwa ; xx2 = x +Loop21: sub xbc,xde ; xx2 -= xroot + srl 1,xde ; xroot = xroot/2 + sub xbc,xhl ; x2 -= m2 + jr m,DontSet2 + ld xwa,xbc ; x = xx2 + or xde,xhl ; xroot += m2 + srl 2,xhl ; m2 = m2/4 + jr nz,Loop21 + jr Finish +DontSet2: srl 2,xhl ; m2 = m2/4 + jr nz,Loop20 ; 7* abarbeiten + +Finish: sub xwa,xde ; Aufrunden notwendig ? + jr ule,NoInc + inc xde ; wenn ja, durchfhren +NoInc: res 7,qde ; impl. Eins l”schen + or xde,xix + ld xwa,xde ; Ergebnis in XWA + jr End + +DomainError: ld xwa,0ffc00000h ; -NAN zurckgeben + jr End + +Zero: sub xwa,xwa ; Ergebnis 0 + +End: pop xix ; Register zurck + pop xhl + pop xde + pop xbc + ret + + endp + +;------------------------------------------------------------------------------ +; Unterroutine Zehnerpotenz bilden: XWA=10.0^BC + + section fPot10 ; nicht mit proc, da private Funktion + public fPot10:Parent +fPot10: + + push xbc ; Register retten + push xhl + + ld xwa,(One) ; Ausgangspunkt frs Multiplizieren + ld xhl,(Ten) ; zu benutzende Potenz + or bc,bc ; negative Potenz ? + jr p,IsPos + ld xhl,(Tenth) ; dann eben Zehntel multiplizieren + neg bc ; fr Schleife immer positiv +IsPos: + or bc,bc ; Noch weiter multiplizieren ? + jr z,End + bit 0,bc ; Restpotenz ungerade ? + jr z,IsEven + call fmul ; ja: einzeln multiplizieren +IsEven: srl 1,bc ; n„chste Stelle + push xwa ; neue Potenz berechnen + ld xwa,xhl + call fmul ; durch quadrieren + ld xhl,xwa + pop xwa + jr IsPos ; weiter nach Einsen suchen + +End: pop xhl ; Register zurck + pop xbc + ret + + endsection + +;------------------------------------------------------------------------------ +; Unterroutine Zahl dezimal wandeln + + section fOutDec + public fOutDec:Parent +fOutDec: + + push xwa ; Register retten + push xbc + push de + push xhl + + bit 15,qwa ; negativ ? + jr z,IsPos + ld (xix+),'-' ; ja: vermerken... + cpl wa ; ...und Zweierkomplement + cpl qwa + inc xwa + jr GoOn +IsPos: bit 7,c ; Pluszeichen ausgeben ? + jr nz,GoOn + ld (xix+),'+' +GoOn: res 7,c ; Plusflag l”schen + ld qbc,0 ; Nullflag und Z„hler l”schen + +InLoop: ld xhl,0 ; Division vorbereiten + ld e,32 ; 32 Bit-Division +DivLoop: sll 1,xwa ; eins weiterschieben + rl 1,xhl + srl 1,xwa ; fr nachher + sub xhl,10 ; paát Divisor hinein ? + jr nc,DivOK + add xhl,10 ; nein, zurcknehmen... + scf ; im Ergebnis 0 einschieben +DivOK: ccf ; neues Ergebnisbit + rl 1,xwa ; Ergebnis in XWA einschieben... + djnz e,DivLoop + + add l,'0' ; ASCII-Offset addieren + bit 1,qb ; schon im Nullbereich ? + jr z,NormVal + ld l,b ; ja, dann gewnschtes Leerzeichen +NormVal: push l ; auf LIFO legen + inc qc ; ein Zeichen mehr + or xwa,xwa ; Quotient Null ? + scc z,qb + jr nz,InLoop ; wenn nicht Null, auf jeden Fall weiter + cp c,qc ; ansonsten nur, falls min. Stellenzahl + jr ugt,InLoop ; noch nicht erreicht + +OutLoop: pop a ; jetzt Zeichen umgekehrt ablegen + ld (xix+),a + djnz qc,OutLoop + + pop xhl ; Register zurck + pop de + pop xbc + pop xwa + + ret + + endsection + +;------------------------------------------------------------------------------ +; Gleitkomma nach ASCII wandeln: +; In: Zahl in XWA +; Zeiger auf Speicher in XHL +; max. Anzahl Nachkommastellen in C +; B/Bit 0 setzen, falls Mantissen-Pluszeichen unerwnscht +; B/Bit 1 setzen, falls Exponenten-Pluszeichen unerwnscht +; B/Bit 2..4 = Stellenzahl Exponent +; B/Bit 5 setzen, falls Nullen am Ende der Mantisse unerwnscht +; Out: Zahl abgelegter Zeichen (exkl. NUL am Ende) in BC +; (XHL) = gebildeter String + + proc fftoa + + push xix ; Register retten + push xhl + push de + push xbc + push xwa + + ld xix,xhl ; Zeiger auf Speicher kopieren + ld de,bc ; Parameter sichern + + ld xhl,xwa ; Zahl auf die Zerlegebank bringen + res 15,qwa ; Vorzeichen hier nicht mehr gebraucht + + ld c,'+' ; Annahme positiv + sll 1,xhl ; Vorzeichen in Carry bringen + jr c,IsNeg ; Minuszeichen immer erforderlich... + bit 0,d ; ...Pluszeichen optional + jr nz,NoMantSgn + jr WrMantSgn +IsNeg: ld c,'-' ; ja +WrMantSgn: ld (xix+),c ; Mantissenvorzeichen ablegen +NoMantSgn: + ld c,qh ; Exponenten herausholen... + extz bc ; ...auf 16 Bit erweitern... + sll 8,xhl ; ...und in Quelle l”schen + + cp bc,MaxExpo ; Sonderwert (INF/NAN) ? + jrl z,SpecialVals ; ja--> + + or bc,bc ; Zahl denormal ? + jr nz,IsNormal ; nein, normal weiter + or xhl,xhl ; bei kompl. Null auch berspringen + jr z,IsNull +Normalize: sll 1,xhl ; ja: solange z„hlen, bis 1 erscheint + jr c,IsNormal + dec bc + jr Normalize +IsNormal: sub bc,Bias ; Bias abziehen +IsNull: + push xwa ; fr folgendes Zahl retten + ld wa,bc ; Zweierexponenten in Float wandeln + exts xwa + call fitof + ld xhl,(Ld10) ; in Dezimalexponenten wandeln + call fdiv + or xwa,xwa ; Zahl negativ ? + jr p,NoCorr + ld xhl,(One) ; dann nocheinmal korrigieren wg. + call fsub ; unterer Gauáklammer +NoCorr: call fftoi ; Den Ausflug in Float beenden + ld qbc,wa ; den Zehnerexponenten retten + ld bc,wa + call fPot10 ; von diesem Exponenten Zehnerpotenz + ld xhl,xwa ; bilden + pop xwa ; alte Zahl zurck + call fdiv ; Teilen: Ergebnis ist Zahl zwischen +Again: ld xhl,xwa ; 1.0 und 9.9999..., diese retten + call fftoi ; Vorkommastelle berechnen + cp a,10 ; doch etwas drber ? + jr ult,NoRoundErr + ld xwa,xhl ; ja, dann noch einmal zehnteln + ld xhl,(Tenth) + call fmul + inc qbc + jr Again +NoRoundErr: add a,'0' ; diese nach ASCII wandeln... + ld (xix+),a ; ...und ablegen + sub a,'0' ; wieder rckg„ngig machen + cp e,0 ; gar keine Nachkommastellen ? + jr eq,NoComma + ld (xix+),Comma ; Dezimalpunkt ausgeben + call fitof ; in ganze Gleitkommazahl wandeln + call fsub ; Differenz bilden + chg 15,qwa ; war verkehrtherum... + ld xhl,xwa ; nach XHL verschieben, weil XWA gebraucht + ld c,e ; Zehnerpotenz fr Skalierung ausrechnen + extz bc ; auf 16 Bit aufblasen + call fPot10 ; Skalierungswert berechnen + call fmul ; hochmultiplizieren + ld xhl,(Half) ; Rundung + call fadd + call fftoi ; diese herausziehen + ld b,'0' ; n-stellig mit Vornullen ausgeben + ld c,e + set 7,c ; kein Pluszeichen! + call fOutDec + bit 5,d ; Nullen am Ende abr„umen ? + jr nz,CleanZeros +NoComma: + ld a,d ; falls Minimalstellenzahl Exponent=0 + and a,00011100b ; und Exponent=0, vergessen + or a,qb + or a,qc + jr z,End + + ld (xix+),'E' ; Exponenten ausgeben + ld wa,qbc + exts xwa + ld b,'0' ; evtl. vornullen... + ld c,d ; Bit 1-->Bit 7 + rrc 2,c + and c,87h ; Bits ausmaskieren + call fOutDec + +End: pop xwa ; Register zurck + pop xbc + pop de + pop xhl + ld (xix),0 ; NUL-Zeichen im String nicht vergessen + sub xix,xhl ; Stringl„nge berechnen + ld bc,ix + pop xix + + ret + +SpecialVals: or xde,xde ; Ist die Mantisse Null ? + jr nz,IsNAN + ldw (xix+),'NI' ; ja: INF einschreiben + ld (xix+),'F' + jr End +IsNAN: ldw (xix+),'AN' ; nein: NAN einschreiben + ld (xix+),'N' + jr End + +CleanZeros: cp (xix-1),'0' ; steht da eine Null am Ende ? + jr nz,CleanNoZero ; nein, Ende + dec xix ; ja: Z„hler runter, so daá ber- + jr CleanZeros ; schrieben wird und neuer Versuch +CleanNoZero: cp (xix-1),Comma ; evtl. Komma entfernbar ? + jr nz,NoComma ; nein--> + dec xix ; ja: noch ein Zeichen weniger + jr NoComma + + endp + +;------------------------------------------------------------------------------ +; ASCII nach Gleitkomma wandeln: +; In: Zeiger auf String (ASCIIZ) in XHL +; Out: XWA = Ergebnis bzw. fehlerhafte Stelle +; CY = 0, falls fehlerfrei + + proc fatof + + push xbc ; Register retten + push xde + push xhl + push xix + + ld xix,xhl ; Zeiger nach XIX + ld qbc,01 ; Phase 1 (Mantisse), noch kein Vorzeichen + ld xde,(Ten) ; in der Mantisse mit 10 hochmultiplizieren + ld xhl,0 ; Mantisse vorbelegen + ld bc,0 ; Exponent vorbelegen + +ReadLoop: ld a,(xix+) ; ein neues Zeichen holen + extz wa ; auf 32 Bit aufblasen + extz xwa + + cp a,0 ; Endezeichen ? + jrl eq,Combine ; ja, alles zusammen + + cp a,' ' ; Leerzeichen ignorieren + jr eq,ReadLoop + + cp a,'+' ; Pluszeichen gnadenhalber zugelassen + jr ne,NoPlus ; ist aber nur ein Dummy + bit 0,qb ; schon ein Vorzeichen dagewesen ? + jrl nz,Error ; dann Fehler + set 0,qb ; ansonsten einfach setzen + jr ReadLoop +NoPlus: + cp a,'-' ; Minuszeichen bewirkt schon eher etwas + jr ne,NoMinus + bit 0,qb ; darf auch nur einmal auftreten + jrl nz,Error + set 0,qb + cp qc,1 ; je nach Phase anderes Flag setzen + jr ne,MinPhase3 + set 1,qb ; bei Mantisse Bit 1... + jr ReadLoop +MinPhase3: set 2,qb ; bei Exponent Bit 2 + jr ReadLoop +NoMinus: + cp a,'.' ; Umschaltung zu Phase 2 (Nachkomma) ? + jr ne,NoPoint + cp qc,1 ; bish. Phase muá eins sein + jrl ne,Error + ld qc,2 ; neue Phase eintragen + set 0,qb ; Nachkomma darf kein Vorzeichen haben + ld xde,(Tenth) ; im Nachkomma durch 10 teilen + jr ReadLoop +NoPoint: + cp a,'e' ; kleines und groáes E zulassen + jr eq,IsE + cp a,'E' + jr ne,NoE +IsE: cp qc,3 ; vorherige Phase muá 1 oder 2 sein + jr eq,Error + ld qc,3 ; vermerken + res 0,qb ; Vorzeichen wieder zugelassen + jr ReadLoop +NoE: + sub a,'0' ; jetzt nur noch 0..9 zugelassen + jr c,Error + cp a,9 + jr ugt,Error + set 0,qb ; nach Ziffern kein Vorzeichen mehr zulassen + + cp qc,1 ; Phase 1 (Mantisse) : + jr ne,NoPhase1 + push xwa ; Zeichen retten + ld xwa,xde ; bish. Mantisse * 10 + call fmul + ld xhl,xwa + pop xwa ; Zahl nach Float wandeln + call fitof + call fadd ; dazuaddieren + ld xhl,xwa ; Mantisse zurcklegen + jrl ReadLoop +NoPhase1: + cp qc,2 ; Phase 2 (Nachkomma) : + jr ne,NoPhase2 + call fitof ; Stelle nach Float wandeln + push xhl ; Mantisse retten + ld xhl,xde ; Stelle mit Zehnerpotenz skalieren + call fmul + pop xhl ; zur Mantisse addieren + call fadd + push xwa ; Zwischenergebnis retten + ld xwa,xde ; n„chste Skalierungspotenz ausrechnen + ld xhl,(Tenth) + call fmul + ld xde,xwa ; alles wieder zurck + pop xhl + jrl ReadLoop +NoPhase2: + mul bc,10 ; Exponent heraufmultiplizieren + add bc,wa + cp bc,45 ; Minimum ist 1e-45 + jr ugt,Error + jrl ReadLoop + +Combine: bit 2,qb ; Exponent negativ ? + jr z,ExpPos + neg bc +ExpPos: call fPot10 ; Zehnerpotenz des Exponenten bilden + call fmul ; mit Mantisse kombinieren + bit 1,qb ; Mantisse negativ ? + jr z,ManPos + set 15,qwa +ManPos: rcf ; Ende ohne Fehler + + pop xix ; Register zurck + pop xhl + pop xde + pop xbc + ret + +Error: ld xwa,xix ; Endzeiger laden + pop xix + pop xhl + sub xwa,xhl ; rel. Position des fehlerhaften Zeichens berechnen + pop xde + pop xbc + scf ; Ende mit Fehler + ret + + endp + +;------------------------------------------------------------------------------ +; gemeinsames Ende + + endsection + diff --git a/tests/t_fl900/macros.inc b/tests/t_fl900/macros.inc new file mode 100644 index 0000000..951a117 --- /dev/null +++ b/tests/t_fl900/macros.inc @@ -0,0 +1,16 @@ +; MACROS.INC +;****************************************************************************** +;* šberall gebrauchte Makros * +;* * +;* Alfred Arnold, Oktober 1993 * +;****************************************************************************** + +proc macro name ; Prozedureintritt + section name + public name +name label $ + endm + +endp macro name ; Prozeduraustritt + endsection name + endm diff --git a/tests/t_fl900/t_fl900.asm b/tests/t_fl900/t_fl900.asm new file mode 100644 index 0000000..72510c2 --- /dev/null +++ b/tests/t_fl900/t_fl900.asm @@ -0,0 +1,166 @@ +; FTEST.ASM +;****************************************************************************** +;* Testet Gleitkommabibliothek fr TLCS900 * +;* * +;* Hardware: Micro-ICE TLCS900 * +;* Software: AS 1.39p1 oder h”her * +;* Includes MACROS.INC, FLOAT.INC, CONOUT.INC, CPU_TIME.INC * +;* * +;* šbersetzen mit AS ftest oder beiliegendem Makefile * +;* * +;****************************************************************************** + + cpu 96c141 + + org 1000h ; Startadresse User-RAM + +;------------------------------------------------------------------------------ + +CR equ 13 +LF equ 10 +Format_Tab equ 0000100000000110b ; fftoa-Format fr tab. Ausgabe +Format_Min equ 0010001100000101b ; fftoa-Format fr minimale L„nge +; ³<Â>³³<ÄÄÂÄÄÄ> +; ³ ³ ³³ ³ +; ³ ³ ³³ ÀÄÄÄÄÄÄ Maximalzahl Nachkommastellen +; ³ ³ ³ÀÄÄÄÄÄÄÄÄÄÄ Mantissenpluszeichen unterdrcken +; ³ ³ ÀÄÄÄÄÄÄÄÄÄÄÄ Exponentenpluszeichen unterdrcken +; ³ ÀÄÄÄÄÄÄÄÄÄÄÄÄÄ Minimalstellenzahl Exponent +; ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ anh„ngende Nullen Mantisse l”schen +Format equ Format_Tab ; gew„hltes fftoa-Format + + supmode on ; Vorgaben + maxmode on + macexp off + page 0 ; keine FFs + include macros.inc + +;------------------------------------------------------------------------------ +; Hauptroutine, Test + +; kleine Schreiberleichterung: + +bench macro op,arg1,arg2,arg3,msg + call PSTR ; Kennmeldung ausgeben + db msg,StrTerm + call CPU_TIME ; Uhr starten + ld xwa,arg1 ; Operanden holen + if "ARG2"<>"" ; 2. Operanden evtl. weglassen + ld xhl,arg2 + endif + if "ARG3"<>"" ; dito 3. Operanden + ld bc,arg3 + endif + call op ; Probanden laufen lassen + ld (xiz),xwa ; Ergebnis weglegen... + call CPU_STOP ; Uhr anhalten, Zeit ausgeben + if ("OP"<>"FNOP")&&("OP"<>"FFTOI") + call PSTR ; etwas Platz + db ", Ergebnis: ",StrTerm + ld xwa,(xiz+) ; Wert ausgeben + lda xhl,(Buffer) + ld bc,Format + call fftoa + call TXTAUS + endif + call PSTR + db CR,LF,StrTerm + endm + + proc Main + + max ; ohne das macht das keinen Spaá ! + lda xsp,(Stack) ; etwas brauchen wir schon... + lda xiz,(Ergs) ; Zeiger auf Ergebnisfeld + call CPU_TI_INI ; Timer initialisieren + + ; Overhead messen + bench fnop,(FConst1),(FConst1),,"Overhead : " + + ; Addition zweier fast gleicher Zahlen + bench fadd,(FConst1),(FConst2),,"Laufzeit 1+2 : " + + ; Addition zweier unterschiedl. groáer Zahlen + bench fadd,(FConst1),(FConst100000),,"Laufzeit 1+100000 : " + + ; Subtraktion zweier fast gleicher Zahlen + bench fsub,(FConst1),(FConst2),,"Laufzeit 1-2 : " + + ; Subtraktion zweier unterschiedl. groáer Zahlen + bench fsub,(FConst1),(FConst100000),,"Laufzeit 1-100000 : " + + ; Multiplikation + bench fmul,(FConst2),(FConstPi),,"Laufzeit 2*Pi : " + + ; Division + bench fdiv,(FConst2),(FConstPi),,"Laufzeit 2/Pi : " + + ; Multiplikation mit 2er-Potenz + bench fmul2,(FConstPi),,10,"Laufzeit Pi*2^(10) : " + + ; Division durch 2er-Potenz + bench fmul2,(FConstPi),,-10,"Laufzeit Pi*2^(-10) : " + + ; kleine Zahl nach Float wandeln + bench fitof,1,,,"Laufzeit 1-->Float : " + + ; groáe Zahl nach Float wandeln + bench fitof,100000,,,"Laufzeit 1E5-->Float: " + + ; kleine Zahl nach Int wandeln + bench fftoi,(FConst1),,,"Laufzeit 1-->Int : " + + ; groáe Zahl nach Int wandeln + bench fftoi,(FConst100000),,,"Laufzeit 1E5-->Int : " + + ; Wurzel + bench fsqrt,(FConst2),,,"Laufzeit SQRT(2) : " + + call PSTR + db "Eingabe: ",StrTerm + lda xhl,(InpBuffer) + call TXTAUS + call fatof + call PSTR + db ", Ergebnis: ",StrTerm + lda xhl,(Buffer) + ld bc,Format + call fftoa + call TXTAUS + call PSTR + db 13,10,StrTerm + + swi 7 ; zum Monitor zurck + + endp + +fnop: ld xwa,0 ; Dummy + ret + + include "float.inc" + include "conout.inc" + include "cpu_time.inc" + +;------------------------------------------------------------------------------ +; Gleitkommakonstanten + + align 4 ; fr schnelleren Zugriff + +FConst1 dd 1.0 +FConst2 dd 2.0 +FConst100000 dd 100000.0 +FConstM1 dd -1.0 +FConstM2 dd -2.0 +FConstPi dd 40490fdbh ; um Vergleichsfehler durch Rundung zu + ; vermeiden +Ergs dd 30 dup (?) ; Platz fr Ergebnisse + +Buffer: db 20 dup (?) +InpBuffer: db "12.3456E-12",0 + +;------------------------------------------------------------------------------ +; Stack + + db 200 dup (?) +Stack: + diff --git a/tests/t_fl900/t_fl900.doc b/tests/t_fl900/t_fl900.doc new file mode 100644 index 0000000..4e7cf63 --- /dev/null +++ b/tests/t_fl900/t_fl900.doc @@ -0,0 +1,6 @@ ++------------------------ Test Application FL900 ----------------------------+ +| | +| This is an IEEE single precision floating point library for the Toshiba | +| TLCS-900 microcontroller, embedded into a small test program. | +| | ++-----------------------------------------------------------------------------+ diff --git a/tests/t_fl900/t_fl900.inc b/tests/t_fl900/t_fl900.inc new file mode 100644 index 0000000..4a02c1e --- /dev/null +++ b/tests/t_fl900/t_fl900.inc @@ -0,0 +1,2 @@ +; t_fl900.asm-Includefile für Assembler-Programm +; Ende Includefile für Assembler-Programm diff --git a/tests/t_fl900/t_fl900.ori b/tests/t_fl900/t_fl900.ori new file mode 100755 index 0000000..74929d8 Binary files /dev/null and b/tests/t_fl900/t_fl900.ori differ diff --git a/tests/t_full09/asflags b/tests/t_full09/asflags new file mode 100644 index 0000000..27cc2fa --- /dev/null +++ b/tests/t_full09/asflags @@ -0,0 +1 @@ +-D __6309__ diff --git a/tests/t_full09/t_full09.asm b/tests/t_full09/t_full09.asm new file mode 100644 index 0000000..4b39d38 --- /dev/null +++ b/tests/t_full09/t_full09.asm @@ -0,0 +1,1604 @@ + cpu 6309 + +list macro + listing on + endm + +nolist macro + listing off + endm + +db macro op + byt (op) + endm + +fcb macro op + byt (op) + endm + +fcc macro op + byt (op) + endm + +dw macro op + adr (op) + endm + +fdb macro op + adr (op) + endm + +fcw macro op + adr (op) + endm + +ds macro op + dfs (op) + endm + +rmb macro op + rept op + db 0 + endm + endm + +dd macro op + adr (op)>>16,(op)&$ffff + endm + +fcd macro op + adr (op)>>16,(op)&$ffff + endm + +direct macro num + if num=-1 + assume dpr:nothing + elseif num>255 + assume dpr:num>>8 + elseif + assume dpr:num + endif + endm + +page macro + newpage + endm + +opt macro + endm + +noopt macro + endm + +nop macro cnt + if "CNT"="" +__cnt set 1 + elseif +__cnt set cnt + endif + rept __cnt + !nop + endm + endm + +momseg set 0 +segsave_code set 0 +segsave_data set 0 +segsave_bss set 0 + +saveseg macro + switch momseg + case 0 +segsave_code set * + case 1 +segsave_data set * + case 2 +segsave_bss set * + endcase + endm + +data macro + saveseg + org segsave_data +momseg set 1 + endm + +code macro + saveseg + org segsave_code +momseg set 0 + endm + +bss macro + saveseg + org segsave_bss +momseg set 2 + endm + +;-------------------------------------------------------------------------- + +; <:t17,25,41,45:> +; +=====================================================================+ +; | | +; | TESTCASE.A09 | +; | | +; | Test case for 6809/6309 assembler. | +; | | +; | Copyright 1993, Frank A. Vorstenbosch | +; | | +; +=====================================================================+ +; +; File created 13-oct-93 + + title "Test case for 6809/6309 assembler" + + list + +; +---------------------------------------------------------------------+ +; | | +; | Options. | +; | | +; +---------------------------------------------------------------------+ + +; -dERRORS check error handling +; -n disable optimizations + + +; +---------------------------------------------------------------------+ +; | | +; | Assembler pseudo instructions. | +; | | +; +---------------------------------------------------------------------+ + +; ----- expressions ----------------------------------------------------- + + data + org 4 + bss + org 1634 + +TEST equ 2+*/2 + ifdef ERRORS +TEST equ TEST+1 + endif + +Constant8 equ -43 +Constant16 equ 16383 +Constant32 equ 96285725 +Address equ $bb5a + +ANOTHER set 3|24&8 +ANOTHER set (3|24)&8 +ANOTHER set 4*(3>5) +ANOTHER set 4*~~(3<5) +ANOTHER set 15<<4 +ANOTHER set ANOTHER+1 +ANOTHER set ANOTHER+1 ; shorthand for SET + +CHAR equ "a" +DOUBLECHAR equ "xy" +QUADCHAR equ "quad" + + ifdef ERRORS +TRIPLE equ "abc" +TOOMUCH equ "abcde" + endif + + data +AddressFour dw TEST + dw **5 + + org $800 + + direct $8 + direct $0800 + + ds 14 +DirectByte db 123 + align 32 +DirectWord dw 12345 + align 48 +DirectLong dd 123456789 + align 79 +DirectCode rts + + dw 1234#12 + dw %1010100101 + dw (1+2)#8 + dw 1010101#%1010101 + + bss +Unin_1 db 0 +Unin_2 dw 4256 +Unin_3 dd 34568957 + + code + org $200 + + page + + ifdef ERRORS +1 + equ 123 + psscht + ! + endif + +; ----- range checking on immediate values ------------------------------ + + lda #10 + lda #100 + ifdef ERRORS + lda #1000 + lda #10000 + lda #100000 + lda #1000000 + lda #10000000 + lda #100000000 + lda #1000000000 + endif + + ldx #10 + ldx #100 + ldx #1000 + ldx #10000 + ifdef ERRORS + ldx #100000 + ldx #1000000 + ldx #10000000 + ldx #100000000 + ldx #1000000000 + endif + + ifdef __6309__ + ldq #10 + ldq #100 + ldq #1000 + ldq #10000 + ldq #100000 + ldq #1000000 + ldq #10000000 + ldq #100000000 + ldq #1000000000 + endif + + page 10 ; keep 10 lines togethre + +; ----- align ----------------------------------------------------------- + + align 16 + align 32 + + +; ----- code, data, org ------------------------------------------------- + + code + org $1300 + data + org $1180 + + code + lda #1 + + data +Table db 1,2,3 + + code + ldx #Table + + +; ----- db, fcb, fcc ---------------------------------------------------- + +Message1 db 7,"Error",13,10,0 + +Message2 fcb 7 + fcc "Error" + fcb 13,10,0 + + +; ----- ds, rmb --------------------------------------------------------- + + ds 10 + rmb 10 + + +; ----- dw, fcw, fdb ---------------------------------------------------- + + dw 23457 + fcw 13462 + fdb 6235 + + +; ----- if ... else ... endif ------------------------------------------- + + if 5=6 + db 0 + if 0 + db 1 + else + db 2 + endif + db 3 + else + db 4 + if 1 + db 5 + else + db 6 + endif + db 7 + endif + + +; ----- list, nolist ---------------------------------------------------- + + nolist + ; comment not listed + db 10 + + list + ; comment is listed + db 10 + + +; ----- opt, noopt ------------------------------------------------------ + + noopt + + opt + + +; ----- nop ------------------------------------------------------------- + + nop + nop 3 + + +; ----- struct ---------------------------------------------------------- + +; struct ListNode +; dw LN_Next +; dw LN_Previous +; db LN_Type +; end struct + + +; ----- number bases ---------------------------------------------------- + + dd 1 + dd 10 + dd 100 + dd 1000 + + dd $1 + dd $10 + dd $100 + dd $1000 + + dd %1 + dd %10 + dd %100 + dd %1000 + + dd @1 + dd @10 + dd @100 + dd @1000 + + dd 2#1 + dd 2#10 + dd 2#100 + dd 2#1000 + + dd 3#1 + dd 3#10 + dd 3#100 + dd 3#1000 + dd 3#12 + + dd 4#1 + dd 4#10 + dd 4#100 + dd 4#1000 + dd 4#123 + + dd 5#1 + dd 5#10 + dd 5#100 + dd 5#1000 + dd 5#1234 + + dd 6#1 + dd 6#10 + dd 6#100 + dd 6#1000 + dd 6#2345 + + dd 7#1 + dd 7#10 + dd 7#100 + dd 7#1000 + dd 7#3456 + + dd 8#1 + dd 8#10 + dd 8#100 + dd 8#1000 + dd 8#4567 + + dd 9#1 + dd 9#10 + dd 9#100 + dd 9#1000 + dd 9#5678 + + dd 10#1 + dd 10#10 + dd 10#100 + dd 10#1000 + dd 10#6789 + + dd 11#1 + dd 11#10 + dd 11#100 + dd 11#1000 +; dd 11#789a + + dd 12#1 + dd 12#10 + dd 12#100 + dd 12#1000 +; dd 12#89ab + + dd 13#1 + dd 13#10 + dd 13#100 + dd 13#1000 +; dd 13#9abc + + dd 14#1 + dd 14#10 + dd 14#100 + dd 14#1000 +; dd 14#abcd + + dd 15#1 + dd 15#10 + dd 15#100 + dd 15#1000 +; dd 15#bcde + + dd 16#1 + dd 16#10 + dd 16#100 + dd 16#1000 +; dd 16#cdef + + dd 17#1 + dd 17#10 + dd 17#100 + dd 17#1000 +; dd 17#defg + + dd 18#1 + dd 18#10 + dd 18#100 + dd 18#1000 +; dd 18#efgh + + dd 19#1 + dd 19#10 + dd 19#100 + dd 19#1000 +; dd 19#fghi + + dd 20#1 + dd 20#10 + dd 20#100 + dd 20#1000 +; dd 20#ghij + + dd 21#1 + dd 21#10 + dd 21#100 + dd 21#1000 +; dd 21#hijk + + dd 22#1 + dd 22#10 + dd 22#100 + dd 22#1000 +; dd 22#ijkl + + dd 23#1 + dd 23#10 + dd 23#100 + dd 23#1000 +; dd 23#jklm + + dd 24#1 + dd 24#10 + dd 24#100 + dd 24#1000 +; dd 24#klmn + + dd 25#1 + dd 25#10 + dd 25#100 + dd 25#1000 +; dd 25#lmno + + dd 26#1 + dd 26#10 + dd 26#100 + dd 26#1000 +; dd 26#mnop + + dd 27#1 + dd 27#10 + dd 27#100 + dd 27#1000 +; dd 27#nopq + + dd 28#1 + dd 28#10 + dd 28#100 + dd 28#1000 +; dd 28#opqr + + dd 29#1 + dd 29#10 + dd 29#100 + dd 29#1000 +; dd 29#pqrs + + dd 30#1 + dd 30#10 + dd 30#100 + dd 30#1000 +; dd 30#qrst + + dd 31#1 + dd 31#10 + dd 31#100 + dd 31#1000 +; dd 31#rstu + + dd 32#1 + dd 32#10 + dd 32#100 + dd 32#1000 +; dd 32#stuv + + dd 33#1 + dd 33#10 + dd 33#100 + dd 33#1000 +; dd 33#tuvw + + dd 34#1 + dd 34#10 + dd 34#100 + dd 34#1000 +; dd 34#uvwx + + dd 35#1 + dd 35#10 + dd 35#100 + dd 35#1000 +; dd 35#vwxy + + dd 36#1 + dd 36#10 + dd 36#100 + dd 36#1000 +; dd 36#wxyz + + ifdef ERRORS + dd 37#1 + dd 37#10 + dd 37#100 + dd 37#1000 + + dd 1#1 + dd 1#10 + dd 1#100 + dd 1#1000 + + dd 0#1 + dd 0#10 + dd 0#100 + dd 0#1000 + endif + + +; ----- garbage in inactive if-clause ----------------------------------- + + if 0 + !"#$%&'()*+,-./ +0123456789:;<=>? +@ABCDEFGHIJKLMNO +PQRSTUVWXYZ[\]^_ +`abcdefghijklmno +pqrstuvwxyz{|}~ +€‚ƒ„…†‡ˆ‰Š‹ŒŽ +‘’“”•–—˜™š›œžŸ + ¡¢£¤¥¦§¨©ª«¬­®¯ +°±²|´µ¶·¸¹|+¼½¾¿ +ÀÁÂÃ-ÅÆÇÈ+ÊËÌ=ÎÏ +ÐÑÒÓÔÕÖ×ØÙÚÛÜÝÞß +àáâãäåæçèéêëìíîï +ðñòóôõö÷øùúûüýþ + endif + + +; +=====================================================================+ +; | | +; | Instructions. | +; | | +; È=====================================================================¼ + +; Ú---------------------------------------------------------------------¿ +; | | +; | Register to register operations. | +; | | +; À---------------------------------------------------------------------Ù + +Start tfr a,a ; NOP + tfr a,b + tfr a,cc + tfr a,ccr + tfr a,dp + tfr a,dpr + + tfr b,a + tfr b,b ; NOP + tfr b,cc + tfr b,ccr + tfr b,dp + tfr b,dpr + + tfr d,d ; NOP + tfr d,x + tfr d,y + tfr d,u + tfr d,s + tfr d,sp + + tfr x,d + tfr x,x ; NOP + tfr x,y + tfr x,u + tfr x,s + tfr x,sp + + tfr y,d + tfr y,x + tfr y,y ; NOP + tfr y,u + tfr y,s + tfr y,sp + + tfr u,d + tfr u,x + tfr u,y + tfr u,u ; NOP + tfr u,s + tfr u,sp + + tfr s,d + tfr s,x + tfr s,y + tfr s,u + tfr s,s ; NOP + tfr s,sp ; NOP + + tfr sp,d + tfr sp,x + tfr sp,y + tfr sp,u + tfr sp,s ; NOP + tfr sp,sp ; NOP + + tfr pc,d + tfr pc,x + tfr pc,y + tfr pc,u + tfr pc,s + tfr pc,sp + + ifdef __6309__ + tfr a,e + tfr a,f + tfr b,e + tfr b,f + + tfr e,a + tfr e,b + tfr e,cc + tfr e,ccr + tfr e,dp + tfr e,dpr + tfr e,e ; NOP + tfr e,f + + tfr f,a + tfr f,b + tfr f,cc + tfr f,ccr + tfr f,dp + tfr f,dpr + tfr f,e + tfr f,f ; NOP + + tfr d,v + tfr d,w + + tfr v,d + tfr v,v ; NOP + tfr v,w + tfr v,x + tfr v,y + tfr v,u + tfr v,s + tfr v,sp + + tfr w,d + tfr w,v + tfr w,w ; NOP + tfr w,x + tfr w,y + tfr w,u + tfr w,s + tfr w,sp + + tfr x,v + tfr x,w + tfr y,v + tfr y,w + tfr u,v + tfr u,w + tfr s,v + tfr s,w + tfr pc,v + tfr pc,w + + tfr z,a + tfr z,b + tfr z,cc + tfr z,ccr + tfr z,dp + tfr z,dpr + tfr z,e + tfr z,f + tfr z,d + tfr z,v + tfr z,w + tfr z,x + tfr z,y + tfr z,u + tfr z,s + tfr z,sp + + tfr a,z + tfr b,z + tfr cc,z + tfr ccr,z + tfr dp,z + tfr dpr,z + tfr e,z + tfr f,z + tfr d,z + tfr v,z + tfr w,z + tfr x,z + tfr y,z + tfr u,z + tfr s,z + tfr sp,z + tfr pc,z + endif + + ifdef ERRORS + tfm a,b + tfr a,d + tfr a,v + tfr a,w + tfr a,x + tfr a,y + tfr a,u + tfr a,s + tfr a,sp + + tfr b,d + tfr b,v + tfr b,w + tfr b,x + tfr b,y + tfr b,u + tfr b,s + tfr b,sp + endif + + +; +---------------------------------------------------------------------+ +; | | +; | Addressing modes. | +; | | +; +---------------------------------------------------------------------+ + + lda #0 + lda DirectByte + lda >DirectByte + lda AddressFour + ifdef ERRORS + lda 0,x + lda 1,x + lda <1,x + lda <<1,x + lda >1,x + lda 15,x + lda -16,x + lda 16,x + lda -17,x + lda 127,x + lda -128,x + lda 128,x + lda -129,x + lda FORWARD5,x + lda NearData,pc] + lda [AddressFour,pc] + ifdef ERRORS + lda ["" + MOV R2,PARA1 +Parameteranzahl SET Parameteranzahl+1 + ENDIF + IF "PARA2"<>"" + MOV R3,PARA2 +Parameteranzahl SET Parameteranzahl+1 + ENDIF + IF "PARA3"<>"" + MOV R4,PARA3 +Parameteranzahl SET Parameteranzahl+1 + ENDIF + IF "PARA4"<>"" + MOV R5,PARA4 +Parameteranzahl SET Parameteranzahl+1 + ENDIF + IF "PARA5"<>"" + MOV R6,PARA5 +Parameteranzahl SET Parameteranzahl+1 + ENDIF + IF "PARA6"<>"" + MOV R7,PARA6 +Parameteranzahl SET Parameteranzahl+1 + ENDIF + + PUSH DPL + PUSH DPH + MOV DPTR,#ModulNetAdr_Tab + MOV A,Modul + MOVC A,@A+DPTR + POP DPH + POP DPL + MOV R0,Modul + MOV R1,Msg + MOV B,#Parameteranzahl + PUSH ACC +WAIT_NET: LCALL READ_STATUS + JB ACC.1,WAIT_NET + POP ACC + LCALL SEND_MESSAGE ; Message ins Netz + + POP B + POP ACC + + endm + +;--------------------------------------------------------------------- +; Funktion : Message ausgeben +; Aufrufparameter : wie definiert +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +TEST_MESSAGE_HEX MACRO POS + + PUSH ACC + MOV A,#POS + LCALL LCD_SET_DD_RAM_ADDRESS + POP ACC + PUSH ACC + LCALL A_LCD + MOV A,#' ' + LCALL LCD_WRITE_CHAR + MOV A,B + LCALL A_LCD + MOV A,#' ' + LCALL LCD_WRITE_CHAR + MOV A,R0 + LCALL A_LCD + MOV A,#' ' + LCALL LCD_WRITE_CHAR + MOV A,R1 + LCALL A_LCD + MOV A,#' ' + LCALL LCD_WRITE_CHAR + MOV A,R2 + LCALL A_LCD + MOV A,#' ' + LCALL LCD_WRITE_CHAR + MOV A,R3 + LCALL A_LCD + MOV A,#' ' + LCALL LCD_WRITE_CHAR + MOV A,R4 + LCALL A_LCD + MOV A,#' ' + LCALL LCD_WRITE_CHAR + MOV A,R5 + LCALL A_LCD + MOV A,#' ' + LCALL LCD_WRITE_CHAR + MOV A,R6 + LCALL A_LCD + MOV A,#' ' + LCALL LCD_WRITE_CHAR + MOV A,R7 + LCALL A_LCD + POP ACC + + ENDM + +;--------------------------------------------------------------------- +; Funktion : Fehlerbehandlung +; Aufrufparameter : Fehlernr. +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +ERROR MACRO NR + + + ENDM + +;--------------------------------------------------------------------- + + + + + + + + + + +;--------------------------------------------------------------------- +TEST_MESSAGE MACRO POS,SCHALTER + + IF SCHALTER<=TEST_LEVEL + PUSH ACC + MOV A,#POS + LCALL LCD_SET_DD_RAM_ADDRESS + MOV A,R0 + LCALL LCD_WRITE_CHAR + MOV A,R1 + LCALL LCD_WRITE_CHAR + MOV A,R2 + LCALL LCD_WRITE_CHAR + MOV A,R3 + LCALL LCD_WRITE_CHAR + MOV A,R4 + LCALL LCD_WRITE_CHAR + MOV A,R5 + LCALL LCD_WRITE_CHAR + MOV A,R6 + LCALL LCD_WRITE_CHAR + MOV A,R7 + LCALL LCD_WRITE_CHAR + POP ACC + ENDIF + ENDM +;--------------------------------------------------------------------- +MAKE_MESSAGE MACRO ADR,STRG + + IF 0=0 + MOV A,#0 + MOV DPTR,#STR_ADR + MOVC A,@A+DPTR + MOV R0,A + MOV A,#0 + INC DPTR + MOVC A,@A+DPTR + MOV R1,A + MOV A,#0 + INC DPTR + MOVC A,@A+DPTR + MOV R2,A + MOV A,#0 + INC DPTR + MOVC A,@A+DPTR + MOV R3,A + MOV A,#0 + INC DPTR + MOVC A,@A+DPTR + MOV R4,A + MOV A,#0 + INC DPTR + MOVC A,@A+DPTR + MOV R5,A + MOV A,#0 + INC DPTR + MOVC A,@A+DPTR + MOV R6,A + MOV A,#0 + INC DPTR + MOVC A,@A+DPTR + MOV R7,A + MOV A,#ADR + MOV B,#8 + LJMP WEITER + +STR_ADR DB STRG + +WEITER: NOP + ENDIF + ENDM + +;--------------------------------------------------------------------- +MAKE_MESSAGE_HEX MACRO ADR,L,A0,A1,A2,A3,A4,A5,A6,A7 + + IF 0=0 + MOV R0,#A0 + MOV R1,#A1 + MOV R2,#A2 + MOV R3,#A3 + MOV R4,#A4 + MOV R5,#A5 + MOV R6,#A6 + MOV R7,#A7 + MOV A,#ADR + MOV B,#L + ENDIF + ENDM + +;--------------------------------------------------------------------- + diff --git a/tests/t_mic51/MEM1.ASM b/tests/t_mic51/MEM1.ASM new file mode 100644 index 0000000..05fb409 --- /dev/null +++ b/tests/t_mic51/MEM1.ASM @@ -0,0 +1,727 @@ + +; Aufgabe Nr.: Speichermodul fuer uP- Praktikum II +; Autor: Joerg Vollandt +; erstellt am : 21.05.1994 +; letzte Aenderung am : 02.08.1994 +; Bemerkung : Routinen fuer die Speicherverwaltung +; +; Dateiname : mem1.asm +; + +;===================================================================== +; Definitionen der Funktionen des Seichermoduls + +;INIT_MEM Initialisieren des Speichermoduls +;DEINIT_MEM Deinitialisieren des Speichermoduls +;CLEAR_MEM Speicher loeschen +;RESET_MEM Speicher zum lesen zuruecksetzen +;PUT_ELEMENT_MEM Element anf naechste freie Position schreiben +;GET_ELEMENT_MEM Element von akt. Position lesen +;WR_MEM_PC Speicher auf dem PC speichern. +;RD_MEM_PC Speicher vom PC laden. + +;------------------------------------------------------------------------------ + +;Messagedefinitionen + +;1.Dateityp (Bit 0 und Bit 1) +Msg_PC_To_Net equ 00b ;direkte Eingabe von Hex-Messages fr das Netz +Msg_Frs_Datei equ 01b ;Fr„stischdatei +Msg_Rob_Teach_Datei equ 10b ;Roboter-Teach-In-Datei +Msg_Frs_Teach_Datei equ 11b ;Fr„stisch-Teach-In-Datei + +;2.Aktion (Bit 2 und Bit 3) +Msg_PC_Get equ 0000b ;Rekordanfrage an PC +Msg_PC_Put equ 0100b ;Rekordspeichern Slave=>PC, Rekordausgabe PC=>Slave +Msg_PC_Reset equ 1000b ;PC Datei ”ffnen zum Lesen +Msg_PC_Rewrite equ 1100b ;PC Datei ”ffnen zum Schreiben + +;3.Slaveadresse Slave=>PC ; Msg_From_PC PC=>Slave +Msg_From_PC equ 00000000b ;Antwort auf Anfrage + +EOF_Record equ 0ffffh ; +PC_Slave_Adr equ 0eh ; + +;------------------------------------------------------------------------------ +; Speicherdefinitionen + + + SEGMENT DATA + +CHECKSUMME DW ? + + + SEGMENT XDATA + +POINTER DW ? ; fuer Test +NEXT_FREE DW ? +RD_POINTER DW ? +BLOCKNR DW ? + +MEM_ANF DB 1000 DUP (?) ; Speichergroesse in Bytes +MEM_ENDE + +;--------------------------------------------------------------------- + SEGMENT CODE +;--------------------------------------------------------------------- +; Funktion : Initialisieren des Speichermoduls +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +INIT_MEM: + PUSH PSW + PUSH_DPTR + MOV DPTR,#MEM_ANF + SET_16 NEXT_FREE + SET_16 RD_POINTER + MOV CHECKSUMME,#0 + MOV CHECKSUMME+1,#0 + CLR READY + CLR CRC + + POP_DPTR + POP PSW + RET + +;--------------------------------------------------------------------- +; Funktion : Deinitialisieren des Speichermoduls +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +DEINIT_MEM: + + RET + +;--------------------------------------------------------------------- +; Funktion : Speicher loeschen +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +CLEAR_MEM: + PUSH PSW + PUSH_DPTR + MOV DPTR,#MEM_ANF + SET_16 NEXT_FREE + SET_16 RD_POINTER + MOV CHECKSUMME,#0 + MOV CHECKSUMME+1,#0 + CLR READY + CLR CRC + + POP_DPTR + POP PSW + RET + +;--------------------------------------------------------------------- +; Funktion : Speicher zum lesen zuruecksetzen +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +RESET_MEM: + PUSH_DPTR + MOV DPTR,#MEM_ANF + SET_16 RD_POINTER + + POP_DPTR + RET + +;--------------------------------------------------------------------- +; Funktion : Speicher von MEM_ANF bis NEXT_FREE auf dem PC speichern. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +WR_MEM_PC: + PUSH_ALL + ; MOV A,#MSG_PC_REWRITE+MY_SLAVE_ADR1*16 + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_REWRITE + MOVB ACC.0,P3.5 ; Datei fuer Roboter oder Fraese + SETB ACC.1 + MOV R0,A + MOV A,#PC_Slave_Adr ; Datei oeffnen + MOV B,#8 + SEND_NET + + ; MOV A,#MSG_PC_PUT+MY_SLAVE_ADR1*16 + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_PUT + MOVB ACC.0,P3.5 ; Datei fuer Roboter oder Fraese + SETB ACC.1 + MOV R0,A + MOV A,#PC_Slave_Adr ; Header zusammenstellen + MOV B,#8 + MOV DPTR,#0 + SET_16 BLOCKNR ; Blocknr.=0 setzen + MOV R1,DPL ; Blocknr. + MOV R2,DPH + GET_16 NEXT_FREE + SUBB_DPTR MEM_ANF + MOV R3,DPL ; Anzahl Bytes + MOV R4,DPH + LCALL CHECK_SUM + MOV R5,CHECKSUMME ; Pruefsumme + MOV R6,CHECKSUMME+1 + SEND_NET ; Header senden + + MOV DPTR,#MEM_ANF + SET_16 POINTER ; Zeiger auf MEM_ANF setzen + +WR_MEM_MSG: + LCALL CHECK_RD_POINTER ; Pointer in DPTR!!! + JNC WR_MEM_MSG1 + LJMP WR_MEM_CLOSE ; keine Bytes mehr -> close datei +WR_MEM_MSG1: + LCALL ACC_RD_MEM ; Byte aus MEM lesen + MOV R3,A ; Message aufbauen + LCALL CHECK_RD_POINTER ; Pointer in DPTR!!! + JNC WR_MEM_MSG2 + LJMP WR_MEM_REST ; keine Bytes mehr -> Rest schreiben +WR_MEM_MSG2: + LCALL ACC_RD_MEM ; Byte aus MEM lesen + MOV R4,A ; Message aufbauen + LCALL CHECK_RD_POINTER ; Pointer in DPTR!!! + JNC WR_MEM_MSG3 + LJMP WR_MEM_REST ; keine Bytes mehr -> Rest schreiben +WR_MEM_MSG3: + LCALL ACC_RD_MEM ; Byte aus MEM lesen + MOV R5,A ; Message aufbauen + LCALL CHECK_RD_POINTER ; Pointer in DPTR!!! + JNC WR_MEM_MSG4 + LJMP WR_MEM_REST ; keine Bytes mehr -> Rest schreiben +WR_MEM_MSG4: + LCALL ACC_RD_MEM ; Byte aus MEM lesen + MOV R6,A ; Message aufbauen + LCALL CHECK_RD_POINTER ; Pointer in DPTR!!! + JNC WR_MEM_MSG5 + LJMP WR_MEM_REST ; keine Bytes mehr -> Rest schreiben +WR_MEM_MSG5: + LCALL ACC_RD_MEM ; Byte aus MEM lesen + MOV R7,A ; Message aufbauen + PUSH_DPTR + GET_16 BLOCKNR + INC DPTR + SET_16 BLOCKNR ; Blocknr.=+1 setzen + MOV R1,DPL ; Blocknr. + MOV R2,DPH + POP_DPTR + ; MOV A,#MSG_PC_PUT+MY_SLAVE_ADR1*16 + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_PUT + MOVB ACC.0,P3.5 ; Datei fuer Roboter oder Fraese + SETB ACC.1 + MOV R0,A + MOV A,#PC_Slave_Adr + MOV B,#8 + SEND_NET ; Message senden + LJMP WR_MEM_MSG ; naechste Message + +WR_MEM_REST: + PUSH_DPTR ; nicht volle MSG schreiben + GET_16 BLOCKNR + INC DPTR + SET_16 BLOCKNR ; Blocknr.=+1 setzen + MOV R1,DPL ; Blocknr. + MOV R2,DPH + POP_DPTR + ; MOV A,#MSG_PC_PUT+MY_SLAVE_ADR1*16 + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_PUT + MOVB ACC.0,P3.5 ; Datei fuer Roboter oder Fraese + SETB ACC.1 + MOV R0,A + MOV A,#PC_Slave_Adr + MOV B,#8 + SEND_NET ; Message senden + +WR_MEM_CLOSE: + ; MOV A,#MSG_PC_PUT+MY_SLAVE_ADR1*16 + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_PUT + MOVB ACC.0,P3.5 ; Datei fuer Roboter oder Fraese + SETB ACC.1 + MOV R0,A + MOV A,#PC_Slave_Adr ; Datei schlieáen + MOV B,#8 + MOV R1,#(EOF_RECORD#256) + MOV R2,#(EOF_RECORD/256) + SEND_NET + POP_ALL + RET + +;--------------------------------------------------------------------- +; Funktion : Speicher vom PC laden. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +RD_MEM_PC: + PUSH_ALL + ; MOV A,#MSG_PC_RESET+MY_SLAVE_ADR1*16 + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_RESET + MOVB ACC.0,P3.5 ; Datei fuer Roboter oder Fraese + SETB ACC.1 + MOV R0,A + MOV A,#PC_Slave_Adr ; Datei oeffnen + MOV B,#8 + SEND_NET + ; MOV A,#MSG_PC_GET+MY_SLAVE_ADR1*16 + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_GET + MOVB ACC.0,P3.5 ; Datei fuer Roboter oder Fraese + SETB ACC.1 + MOV R0,A + MOV A,#PC_Slave_Adr ; Header laden + MOV B,#8 + MOV DPTR,#0 + SET_16 BLOCKNR ; Blocknr.=0 setzen + MOV R1,DPL ; Blocknr. + MOV R2,DPH + SEND_NET ; Header anfordern + POP_ALL + RET + + +GET_FROM_PC: + PUSH_ALL + CJNE R1,#0,GET_NO_HEADER1 ; wenn Blocknr.=0, dann + CJNE R2,#0,GET_NO_HEADER1 ; Header + LJMP GET_HEADER +GET_NO_HEADER1: + LJMP GET_NO_HEADER +GET_HEADER: + CJNE R3,#0,GET_NOT_EMPTY_JMP ; testen ob 0 Bytes in Datei + CJNE R4,#0,GET_NOT_EMPTY_JMP + LJMP GET_EMPTY +GET_NOT_EMPTY_JMP: + LJMP GET_NOT_EMPTY + +GET_EMPTY: ; Datei leer + LCALL INIT_MEM ; Speicherreset + ; MOV A,#MSG_PC_PUT+MY_SLAVE_ADR1*16 + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_PUT + MOVB ACC.0,P3.5 ; Datei fuer Roboter oder Fraese + SETB ACC.1 + MOV R0,A + MOV A,#PC_Slave_Adr ; und Datei schlieáen + MOV B,#8 + MOV R1,#(EOF_RECORD#256) + MOV R2,#(EOF_RECORD/256) + SEND_NET + POP_ALL + SETB READY + LCD 40H,"Teachin- Datei leer. " + RET + +GET_NOT_EMPTY: ; Datei nicht leer + MOV DPL,R3 ; Groesse nach DPTR + MOV DPH,R4 + ADD_DPTR MEM_ANF + SET_16 NEXT_FREE ; neues Speicherende setzen + MOV CHECKSUMME,R5 ; neue Checksumme laden + MOV CHECKSUMME+1,R6 + PUSH_DPTR + GET_16 BLOCKNR + INC DPTR + SET_16 BLOCKNR ; Blocknr.=+1 setzen + MOV R1,DPL ; Blocknr. + MOV R2,DPH + POP_DPTR + ; MOV A,#MSG_PC_GET+MY_SLAVE_ADR1*16 + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_GET + MOVB ACC.0,P3.5 ; Datei fuer Roboter oder Fraese + SETB ACC.1 + MOV R0,A + MOV A,#PC_Slave_Adr + MOV B,#8 + SEND_NET ; 1. Block anfordern + + MOV DPTR,#MEM_ANF + SET_16 POINTER ; Zeiger auf MEM_ANF setzen + + POP_ALL + RET + +GET_NO_HEADER: + GET_16 POINTER ; Schreibzeiger laden + MOV A,R3 + LCALL ACC_WR_MEM ; in den Speicher schreiben + LCALL CHECK_RD_POINTER ; pruefen ob noch Bytes in der Datei + JNC GET_MORE2 + LJMP GET_CLOSE ; wenn nicht Datei schliessen +GET_MORE2: + MOV A,R4 + LCALL ACC_WR_MEM ; in den Speicher schreiben + LCALL CHECK_RD_POINTER ; pruefen ob noch Bytes in der Datei + JNC GET_MORE3 + LJMP GET_CLOSE ; wenn nicht Datei schliessen +GET_MORE3: + MOV A,R5 + LCALL ACC_WR_MEM ; in den Speicher schreiben + LCALL CHECK_RD_POINTER ; pruefen ob noch Bytes in der Datei + JNC GET_MORE4 + LJMP GET_CLOSE ; wenn nicht Datei schliessen +GET_MORE4: + MOV A,R6 + LCALL ACC_WR_MEM ; in den Speicher schreiben + LCALL CHECK_RD_POINTER ; pruefen ob noch Bytes in der Datei + JNC GET_MORE5 + LJMP GET_CLOSE ; wenn nicht Datei schliessen +GET_MORE5: + MOV A,R7 + LCALL ACC_WR_MEM ; in den Speicher schreiben + LCALL CHECK_RD_POINTER ; pruefen ob noch Bytes in der Datei + JNC GET_MORE6 + LJMP GET_CLOSE ; wenn nicht Datei schliessen +GET_MORE6: + SET_16 POINTER + GET_16 BLOCKNR + INC DPTR + SET_16 BLOCKNR ; Blocknr.=+1 setzen + MOV R1,DPL ; Blocknr. + MOV R2,DPH + ; MOV A,#MSG_PC_GET+MY_SLAVE_ADR1*16 + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_GET + MOVB ACC.0,P3.5 ; Datei fuer Roboter oder Fraese + SETB ACC.1 + MOV R0,A + MOV A,#PC_Slave_Adr + MOV B,#8 + SEND_NET ; naechsten Block anfordern + POP_ALL + RET + + +GET_CLOSE: + ; MOV A,#MSG_PC_PUT+MY_SLAVE_ADR1*16 + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_PUT + MOVB ACC.0,P3.5 ; Datei fuer Roboter oder Fraese + SETB ACC.1 + MOV R0,A + MOV A,#PC_Slave_Adr ; und Datei schlieáen + MOV B,#8 + MOV R1,#(EOF_RECORD#256) + MOV R2,#(EOF_RECORD/256) + SEND_NET + MOV R0,CHECKSUMME + MOV A,CHECKSUMME+1 + LCALL CHECK_SUM + CJNE A,CHECKSUMME+1,GET_CRC_ERROR + MOV A,R0 + CJNE A,CHECKSUMME,GET_CRC_ERROR + POP_ALL + CLR CRC + SETB READY + LCD 40H,"Teachin- Datei fehlerfrei geladen. " + RET + +GET_CRC_ERROR: + POP_ALL + SETB CRC + SETB READY + LCD 40H,"FEHLER bei Laden der Teachin- Datei. " + RET + +;--------------------------------------------------------------------- +; Funktion : Testen ob DPTR zum LESEN auf belegten Speicher zeigt. +; C=0 ==> MEM_ANF <= DPTR < NEXT_FREE +; C=1 ==> sonst +; Aufrufparameter : DPTR = Pointer +; Ruechgabeparameter : - +; Veraenderte Register : PSW +; Stackbedarf : +; Zeitbedarf : +; + +CHECK_RD_POINTER: + PUSH PSW + PUSH ACC + MOV A,#((MEM_ANF-1)/256) + CJNE A,DPH,CH_RD1 ; Test ob Pointer >= MEM_ANF +CH_RD1: JC CH_RD_OK1 + CJNE A,DPH,CH_RD_ERROR ; + MOV A,#((MEM_ANF-1)#256) + CJNE A,DPL,CH_RD2 +CH_RD2: JC CH_RD_OK1 + LJMP CH_RD_ERROR ; +CH_RD_OK1: + PUSH_DPTR + MOV DPTR,#(NEXT_FREE+1) + MOVX A,@DPTR + POP_DPTR + CJNE A,DPH,CH_RD3 ; Test ob Pointer < NEXT_FREE +CH_RD3: JC CH_RD_ERROR + CJNE A,DPH,CH_RD_OK2 ; + PUSH_DPTR + MOV DPTR,#NEXT_FREE + MOVX A,@DPTR + POP_DPTR + CJNE A,DPL,CH_RD4 +CH_RD4: JC CH_RD_ERROR + CJNE A,DPL,CH_RD_OK2 + LJMP CH_RD_ERROR ; + +CH_RD_OK2: + POP ACC + POP PSW + CLR C ; o.k. + RET + +CH_RD_ERROR: + POP ACC + POP PSW + SETB C ; Fehler + RET + +;--------------------------------------------------------------------- +; Funktion : Testen ob DPTR zum SCHREIBEN auf belegten Speicher zeigt. +; C=0 ==> MEM_ANF <= DPTR <= NEXT_FREE +; C=1 ==> sonst +; Aufrufparameter : DPTR = Pointer +; Ruechgabeparameter : - +; Veraenderte Register : PSW +; Stackbedarf : +; Zeitbedarf : +; + +CHECK_WR_POINTER: + PUSH PSW + PUSH ACC + MOV A,#((MEM_ANF-1)/256) + CJNE A,DPH,CH_WR1 ; Test ob Pointer >= MEM_ANF +CH_WR1: JC CH_WR_OK1 + CJNE A,DPH,CH_WR_ERROR ; + MOV A,#((MEM_ANF-1)#256) + CJNE A,DPL,CH_WR2 +CH_WR2: JC CH_WR_OK1 + LJMP CH_WR_ERROR ; +CH_WR_OK1: + PUSH_DPTR + MOV DPTR,#(NEXT_FREE+1) + MOVX A,@DPTR + POP_DPTR + CJNE A,DPH,CH_WR3 ; Test ob Pointer <= NEXT_FREE +CH_WR3: JC CH_WR_ERROR + CJNE A,DPH,CH_WR_OK2 ; + PUSH_DPTR + MOV DPTR,#NEXT_FREE + MOVX A,@DPTR + POP_DPTR + CJNE A,DPL,CH_WR4 +CH_WR4: JNC CH_WR_OK2 + LJMP CH_WR_ERROR ; + +CH_WR_OK2: + POP ACC + POP PSW + CLR C ; o.k. + RET + +CH_WR_ERROR: + POP ACC + POP PSW + SETB C ; Fehler + RET + +;--------------------------------------------------------------------- +; Funktion : Testen ob DPTR < MEM_ENDE. +; C=0 ==> DPTR < MEM_ENDE +; C=1 ==> sonst +; Aufrufparameter : DPTR = Pointer +; Ruechgabeparameter : - +; Veraenderte Register : PSW +; Stackbedarf : +; Zeitbedarf : +; + +CHECK_EOM_POINTER: + PUSH PSW + PUSH ACC + MOV A,#(MEM_ENDE/256) + CJNE A,DPH,CH_EOM3 ; Test ob Pointer < MEM_ENDE +CH_EOM3: JC CH_EOM_ERROR + CJNE A,DPH,CH_EOM_OK2 ; + MOV A,#(MEM_ENDE#256) + CJNE A,DPL,CH_EOM4 +CH_EOM4: JC CH_EOM_ERROR + CJNE A,DPL,CH_EOM_OK2 + LJMP CH_EOM_ERROR ; + +CH_EOM_OK2: + POP ACC + POP PSW + CLR C ; o.k. + RET + +CH_EOM_ERROR: + POP ACC + POP PSW + SETB C ; Fehler + RET + +;--------------------------------------------------------------------- +; Funktion : ACC in den Speicher schreiben, DPTR increminieren. +; Aufrufparameter : ACC = Wert, DPTR = Pointer +; Ruechgabeparameter : - +; Veraenderte Register : DPTR +; Stackbedarf : +; Zeitbedarf : +; + +ACC_WR_MEM: + MOVX @DPTR,A + INC DPTR + RET + + +;--------------------------------------------------------------------- +; Funktion : ACC aus dem Speicher lesen, DPTR increminieren. +; Aufrufparameter : DPTR = Pointer +; Ruechgabeparameter : ACC = Wert +; Veraenderte Register : ACC, DPTR +; Stackbedarf : +; Zeitbedarf : +; + +ACC_RD_MEM: + MOVX A,@DPTR + INC DPTR + RET + +;--------------------------------------------------------------------- +; Funktion : Pruefsumme ueber den Speicher bilden. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +CHECK_SUM: + PUSH PSW + PUSH ACC + PUSH_DPTR + MOV CHECKSUMME,#0 + MOV CHECKSUMME+1,#0 + MOV DPTR,#MEM_ANF ; Pointer auf MEM_ANF setzen +CHECK_SUM1: + LCALL CHECK_RD_POINTER ; Pointer in DPTR!!! + JC CHECK_SUM_ENDE + LCALL ACC_RD_MEM ; Byte aus MEM lesen + ADD A,CHECKSUMME + MOV CHECKSUMME,A + MOV A,#0 + ADDC A,CHECKSUMME+1 + MOV CHECKSUMME+1,A + LJMP CHECK_SUM1 + +CHECK_SUM_ENDE: + POP_DPTR + POP ACC + POP PSW + RET + +;--------------------------------------------------------------------- +; Funktion : Element in den Speicher auf die naechste frei Position schreiben. +; Aufrufparameter : ACC = Wert +; Ruechgabeparameter : C=0 ==> o.k., C=1 ==> Speicherueberlauf +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +PUT_ELEMENT_MEM: + PUSH PSW + GET_16 NEXT_FREE + LCALL CHECK_EOM_POINTER ; testen ob DPTR < MEM_ENDE + JC GET_ELEMENT_ERROR ; wenn nicht Fehler + LCALL CHECK_WR_POINTER ; testen ob MEM_ANF <= DPTR <= NEXT_FREE + JC PUT_ELEMENT_ERROR ; wenn nicht Fehler + LCALL ACC_WR_MEM ; Byte aus MEM lesen + SET_16 NEXT_FREE + +PUT_EL_OK1: + POP PSW + CLR C + RET + +PUT_ELEMENT_ERROR: + POP PSW + SETB C + RET + + RET + +;--------------------------------------------------------------------- +; Funktion : Element von der akt. Position aus dem Speicher lesen. +; Aufrufparameter : - +; Ruechgabeparameter : ACC = Wert +; C=0 ==> o.k., C=1 ==> Schreib- gleich Lesezeiger +; oder Lesezeiger ausserhalb des gueltigen Bereiches +; Veraenderte Register : ACC, PSW +; Stackbedarf : +; Zeitbedarf : +; + +GET_ELEMENT_MEM: + PUSH PSW + GET_16 RD_POINTER + LCALL CHECK_EOM_POINTER ; testen ob DPTR < MEM_ENDE + JC GET_ELEMENT_ERROR ; wenn nicht Fehler + LCALL CHECK_RD_POINTER ; testen ob MEM_ANF <= DPTR < NEXT_FREE + JC GET_ELEMENT_ERROR ; wenn nicht Fehler + LCALL ACC_RD_MEM ; Byte aus MEM lesen + SET_16 RD_POINTER + +GET_EL_OK1: + POP PSW + CLR C + RET + +GET_ELEMENT_ERROR: + POP PSW + SETB C + RET + +;===================================================================== +; END +;--------------------------------------------------------------------- + diff --git a/tests/t_mic51/RUN1.ASM b/tests/t_mic51/RUN1.ASM new file mode 100644 index 0000000..690e68b --- /dev/null +++ b/tests/t_mic51/RUN1.ASM @@ -0,0 +1,773 @@ +; +; Aufgabe Nr.: Speichermodul fuer uP- Praktikum II +; Autor: Joerg Vollandt +; erstellt am : 01.07.1994 +; letzte Aenderung am : 02.08.1994 +; Bemerkung : +; +; Dateiname : run1.asm +; + +;--------------------------------------------------------------------- +Definitionen + +ENDE_MARKE EQU 0FFH +SYNC_MARKE EQU 0FEH +READY_MARKE EQU 0FDH +DRILL_MARKE EQU 0FCH + +PenUp EQU 000H +PenDown EQU 0FFH +d_z EQU 200 ; Schritte fuer Auf-/Ab +Queue_Const EQU 10 ; je Befehle ein GibReady an Frs + +;--------------------------------------------------------------------- + SEGMENT CODE +;--------------------------------------------------------------------- +; Funktion : Initialisierung +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +INIT_RUN: + CLR RUNNINGBIT + CLR Sync_Waiting + CLR Ready_Waiting + CLR Drilling + CLR Drill_down + CLR FrsWarning + CLR PAUSE + CLR SingleStep + CLR Break + MOV R_Sync_Counter,#0 + MOV Queue_Counter,#Queue_Const + RET + +;--------------------------------------------------------------------- +; Funktion : Runmodul liesst ein Fkt.-Byte oder eine komplette Msg. +; aus dem Speicher und schickt diese ins Netz. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +RUN_MODUL: + PUSH_ALL + JNB Break,RUN1 + LJMP RUN_ENDE +RUN1: LCALL GET_ELEMENT_MEM ; Anzahl Bytes + JNC RUN4 ; Speicher leer + LJMP RUN_LEER +RUN4: CJNE A,#ENDE_MARKE,RUN5 ; Ende -MARKE im Speicher + GET_16 RD_POINTER + DEC_DPTR + SET_16 RD_POINTER + LJMP RUN_ENDE ; erkannt +RUN5: CJNE A,#SYNC_MARKE,RUN6 ; Sync -MARKE im Speicher + LJMP RUN_SYNC ; erkannt +RUN6: CJNE A,#READY_MARKE,RUN7 ; Ready -MARKE im Speicher + LJMP RUN_READY ; erkannt +RUN7: CJNE A,#DRILL_MARKE,RUN8 ; Drill -MARKE im Speicher + LJMP RUN_DRILL ; erkannt +RUN8: + LCD 40h,"Ablauf der Teachin- Datei. " + PUSH ACC + MOV B,A + USING 1 ; Msg. + MOV R0,#AR0 ; aus Speicher nach Bank 1 + USING 0 +RUN_Next_Byte: + LCALL GET_ELEMENT_MEM ; Bytes aus Speicher + MOV @R0,A ; holen + INC R0 + DJNZ B,RUN_Next_Byte + + POP B + PUSH PSW + CLR RS1 ; Bank 1 + SETB RS0 + MOV DPTR,#ModulNetAdr_Tab + MOV A,R0 + MOVC A,@A+DPTR + SEND_NET ; Msg senden + POP PSW ; alte Bank + POP_ALL + JNB SingleStep,RUN_Next_Ende + PUSH_ALL + LJMP RUN_READY +RUN_Next_Ende: + RET ; fertig ! + + +RUN_READY: + LCD 40h,"Warten bis Geraet fertig. " + JNB P3.5,RUN_READY_FRS + post_message2 #Frs,#GibReady,#MemFrs,#GetFrsReady,#0 ; Ready-Anforderung + LJMP RUN_READY_WEITER ; schicken +RUN_READY_FRS: + post_message2 #Rob,#RobGibReady,#MemRob,#GetRobReady +RUN_READY_WEITER: + SETB Ready_Waiting + POP_ALL + RET + + +RUN_SYNC: + LCD 40h,"Warten auf Synchronisationspunkt Nr.: " + LCALL GET_ELEMENT_MEM ; Sync_Counter aus Speicher + LCALL A_LCD + JB P3.5,RUN_SYNC_FRS + post_message2 #MemFrs,#GetFrsSync,A ; Sync.-Meldung an Partner + LJMP RUN_SYNC0 ; schicken +RUN_SYNC_FRS: + post_message2 #MemRob,#GetRobSync,A +RUN_SYNC0: + MOV B,A + MOV A,R_Sync_Counter + CJNE A,B,RUN_SYNC1 +RUN_SYNC1: JNC RUN_SYNC_ENDE + SETB Sync_Waiting +RUN_SYNC_ENDE: + POP_ALL + RET + + +RUN_DRILL: + JNB P3.5,RUN_DRILL_ROB + LJMP RUN_DRILL_FRS +RUN_DRILL_ROB: + LCD 40h,"Roboter kann nicht fraesen! Abbruch. " + CLR RUNNINGBIT + POP_ALL + LCALL INIT_TEACH + LCALL RESET_TEACH + RET + +RUN_DRILL_FRS: + LCD 40h,"Fraesdatei wird abgearbeitet. " + SETB Drilling + LCALL GET_ELEMENT_MEM ; Fraestiefe aus Speicher + MOV Frs_Ref_Tiefe,A + LCALL GET_ELEMENT_MEM + MOV Frs_Ref_Tiefe+1,A + post_message2 #Frs,#FrsVelocityDraw,#fast ; schnelle Bewegung + post_message2 #Frs,#GoPieceRefPos ; Werkstueckreferenz + post_message2 #Frs,#MoveRZ,#(d_z/256),#(d_z#256) ; Pen up + post_message2 #Frs,#DRILL,#on ; Motor an + clr DRILL_DOWN + SETB DRILL_DOWN + + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_RESET+Msg_Frs_Datei + MOV R0,A + MOV A,#PC_Slave_Adr ; Datei oeffnen + MOV B,#8 + SEND_NET + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_GET+Msg_Frs_Datei + MOV R0,A + MOV A,#PC_Slave_Adr ; + MOV B,#8 + MOV DPTR,#0 + SET_16 BLOCKNR ; Blocknr.=0 setzen + MOV R1,DPL ; Blocknr. + MOV R2,DPH + SEND_NET ; 0. Block laden + POP_ALL + RET + + +RUN_LEER: + LCD 40h,"Speicherinhalt defeckt. " + CLR RUNNINGBIT + POP_ALL + LCALL INIT_TEACH + LCALL RESET_TEACH + RET + + +RUN_ENDE: + LCD 40h,"Ablauf beendet. " + GET_16 NEXT_FREE + DEC_DPTR + SET_16 NEXT_FREE ; Ende- MARKE entfernen + CLR RUNNINGBIT ; Ablaufbeenden + MOV A,R_Sync_Counter + MOV T_Sync_Counter,A + GET_16 RD_POINTER + SET_16 NEXT_FREE + POP_ALL + CLR Break + RET + +;--------------------------------------------------------------------- +; Funktion : Start des Runmoduls. Schreibt die Endemarke in den Speicher, +; setzt den Speicher zurueck und setzt das Bit RUNNINBIT. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +START_RUNNING: + JB READY,START_R + LJMP START_NICHT_BEREIT +START_R: PUSH ACC + MOV A,#ENDE_MARKE + LCALL PUT_ELEMENT_MEM + POP ACC + LCALL RESET_MEM + SETB RUNNINGBIT + CLR Sync_Waiting + CLR Ready_Waiting + MOV R_Sync_Counter,#0 + RET + +START_NICHT_BEREIT: + LCD 40H,"Modul nicht bereit fuer Ablauf. " + RET + + ;--------------------------------------------------------------------- +; Funktion : Piece-Ref-Position der Fraese speichern. 1. Teil: Position +; anforndern. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +STORE_PIECE_REF: + PUSH PSW + PUSH ACC + PUSH AR0 + JNB READY,STORE_P_REF_ENDE ; Fertig und Fraese? + JNB P3.5,STORE_P_REF_ENDE + +; MOV B,#4 ; Msg. an Frs um Pos. +; MOV R2,#MemFrs ; Empfaenger angeben +; MOV R3,#FrsPieceRef ; Msg.-Nr. Empfaenger angeben +; post_message1 Frs,GibFrsPos1 ; zu erfragen + post_message2 #Frs,#GibFrsPos1,#MemFrs,#FrsPieceRef + +STORE_P_REF_ENDE: + CLR READY ; Teach- In nicht bereit + POP AR0 + POP ACC + POP PSW + RET + + ;--------------------------------------------------------------------- +; Funktion : Piece-Ref-Position der Fraese speichern. 2. Teil: Position +; in x,y,z speichern, Ref_Flag setzen. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +PIECE_REF_FROM_FRS: + PUSH PSW + PUSH ACC + PUSH AR0 + JNB READY,P_REF_FRS_DO ; NICHT Fertig und Roboter ? + JB P3.5,P_REF_FRS_DO + LJMP P_REF_FRS_ENDE +P_REF_FRS_DO: + MOV Frs_Ref_x,R2 ; Position speichern + MOV Frs_Ref_x+1,R3 ; Position speichern + MOV Frs_Ref_y,R4 ; Position speichern + MOV Frs_Ref_y+1,R5 ; Position speichern + MOV Frs_Ref_z,R6 ; Position speichern + MOV Frs_Ref_z+1,R7 ; Position speichern + +P_REF_FRS_ENDE: + POP AR0 + POP ACC + POP PSW + SETB READY ; Teach- In wieder bereit + SETB Ref_Flag + RET + + ;--------------------------------------------------------------------- +; Funktion : Fraestiefe der Fraese speichern. 1. Teil: Position +; anforndern. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +STORE_TIEFE: + PUSH PSW + PUSH ACC + PUSH AR0 + JNB READY,STORE_TIEFE_ENDE ; Fertig und Fraese? + JNB P3.5,STORE_TIEFE_ENDE + +; MOV B,#4 ; Msg. an Frs um Pos. +; MOV R2,#MemFrs ; Empfaenger angeben +; MOV R3,#FrsTiefe ; Msg.-Nr. Empfaenger angeben +; post_message1 Frs,GibFrsPos1 ; zu erfragen + post_message2 #Frs,#GibFrsPos1,#MemFrs,#FrsTiefe + +STORE_TIEFE_ENDE: + CLR READY ; Teach- In nicht bereit + POP AR0 + POP ACC + POP PSW + RET + + ;--------------------------------------------------------------------- +; Funktion : Fraestiefe der Fraese speichern. 2. Teil: Tiefe berechnen +; und in Frs_Ref_Tiefe speichern, Tiefe_Flag setzen. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +TIEFE_FROM_FRS: + PUSH PSW + PUSH ACC + PUSH AR0 + JNB READY,TIEFE_FRS_DO ; NICHT Fertig und Roboter ? + JB P3.5,TIEFE_FRS_DO + LJMP TIEFE_FRS_ENDE +TIEFE_FRS_DO: +; MOV A,AR7 ; Fraestiefe berechnen +; CLR C ; und speichern +; SUBB A,Frs_Ref_Tiefe+1 + MOV Frs_Ref_Tiefe+1,AR7 +; 7 +; MOV A,AR6 +; SUBB A,Frs_Ref_Tiefe + MOV Frs_Ref_Tiefe,AR6 +TIEFE_FRS_ENDE: + POP AR0 + POP ACC + POP PSW + SETB READY ; Teach- In wieder bereit + SETB Tiefe_Flag + RET + +;--------------------------------------------------------------------- +; Funktion : Flags abfragen, nur wenn Ref_Flag und Tiefe_Flag low weiter. +; SetPieceRef Msg. in Speicher ablegen, Drill Marke ablegen, +; Tiefe ablegen. +; Aufrrameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +STORE_DRILL: + PUSH PSW + PUSH ACC + JNB Ref_Flag,STORE_DRILL_ERROR ; PieceRefPos und Tiefe + JNB Tiefe_Flag,STORE_DRILL_ERROR ; definiert + LJMP STORE_DRILL_OK + +STORE_DRILL_ERROR: + LCD 40h,"Fehler: RefPos/ Tiefe nicht definiert. " + POP ACC + POP PSW + RET + +STORE_DRILL_OK: + MOV A,#8 ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Msg.-Laenge) + ERROR 0 + MOV A,#Frs ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Modulnr.) + ERROR 0 + MOV A,#SetPieceRef ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Msg.- Nr.) + ERROR 0 + MOV A,Frs_Ref_x ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 1 High) + ERROR 0 + MOV A,Frs_Ref_x+1 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 1 Low) + ERROR 0 + MOV A,Frs_Ref_y ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 2 High) + ERROR 0 + MOV A,Frs_Ref_y+1 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 2 Low) + ERROR 0 + MOV A,Frs_Ref_z ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 3 High) + ERROR 0 + MOV A,Frs_Ref_z+1 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 3 Low) + ERROR 0 + + MOV A,#DRILL_MARKE + LCALL PUT_ELEMENT_MEM + + MOV A,Frs_Ref_Tiefe ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 3 High) + ERROR 0 + MOV A,Frs_Ref_Tiefe+1 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 3 Low) + ERROR 0 + + POP ACC + POP PSW + RET + +;--------------------------------------------------------------------- +; Funktion : Speichert die Ready-MARKE im Speicher +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +STORE_READY: + PUSH ACC + MOV A,#READY_MARKE + LCALL PUT_ELEMENT_MEM + POP ACC + RET + +;--------------------------------------------------------------------- +; Funktion : Speichert das Sync.-MARKE und den Sync.-Counter im Speicher +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +STORE_SYNC: + PUSH ACC + MOV A,#SYNC_MARKE + LCALL PUT_ELEMENT_MEM + INC T_Sync_Counter ; Sync_Counter +1 + MOV A,T_Sync_Counter + LCALL PUT_ELEMENT_MEM + LCD 29,"Sync.-Nr." + LCALL A_LCD + POP ACC + RET + +;--------------------------------------------------------------------- +; Funktion : Ready-Msg. erhalten und bearbeiten. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +GET_READY_MSG: + LCD 40H," " + CLR Ready_Waiting + RET + +;--------------------------------------------------------------------- +; Funktion : Sync.-Msg. erhalten und bearbeiten. Bricht Running ab +; wenn von Partner Sync.-Nr. 0 kommt. Wenn eigenes Modul +; noch nicht getstartet wird Sync.-Msg. mit #0 an Partner +; geschickt. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +GET_SYNC_MSG: + JNB RunningBit,G_S_1 + LJMP G_S_2 +G_S_1: PUSH B + MOV B,#3 ; Msg. + MOV R2,#0 ; mit #0 + JB P3.5,G_S_FRS + post_message1 MemFrs,GetFrsSync ; Sync.-Meldung an Partner + POP B + RET ; schicken +G_S_FRS: post_message1 MemRob,GetRobSync + POP B + RET + +G_S_2: PUSH PSW + PUSH ACC + INC R_Sync_Counter + MOV A,R2 ; Sync_Counter aus Msg. holen + CJNE A,#0,G_S_KEIN_ABBRUCH ; Abbruch bei #0 + LJMP G_S_ABBRUCH +G_S_KEIN_ABBRUCH: + CJNE A,R_Sync_Counter,G_S_ERROR ; Fehler wenn ungleich + CLR Sync_Waiting + POP ACC + POP PSW + RET + +G_S_ABBRUCH: + LCD 40h,"Partner nicht bereit. Abbruch. " + CLR RUNNINGBIT + POP ACC + POP PSW + LCALL INIT_TEACH + LCALL RESET_TEACH + RET + +G_S_ERROR: + LCD 40h,"Synchronisationsfehler. " + CLR RUNNINGBIT + POP ACC + POP PSW + LCALL INIT_TEACH + LCALL RESET_TEACH + RET + +;--------------------------------------------------------------------- +; Funktion : Testen ob Queue- Warnung von Frs gekommen ist. Wenn ja, +; GibReady an die Fraese schicken und warten bis kommt. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +queue_test macro + +Q_T_Main_Loop: + LCALL MAIN_EVENT_LOOP + JB PAUSE,Q_T_Main_Loop ; Pause aktiv + JB READY_WAITING,Q_T_Main_Loop ; warten auf Ready von Frs + LCALL READ_STATUS + JB ACC.1,Q_T_Main_Loop + + endm + +;--------------------------------------------------------------------- +; Funktion : Daten aus der Fraesdatei vom PC empfangen, konvertieren +; und an die Fraese schicken. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + + +GET_WORKFR_FROM_PC: + PUSH_ALL + JB RUNNINGBIT,GET_WORKFR_FROM_PC_START + LJMP GET_WORKFR_FROM_PC_ABBRUCH +GET_WORKFR_FROM_PC_START: + MOV A,R1 ; testen ob Dateiende + CJNE A,#0ffh,GET_WORKFR_FROM_PC_NEXT + MOV A,R2 + CJNE A,#0ffh,GET_WORKFR_FROM_PC_NEXT + LJMP GET_WORKFR_FROM_PC_ENDE + +GET_WORKFR_FROM_PC_NEXT: ; naechste Msg. von PC + PUSH_ALL ; konvertieren und an Frs + queue_test + MOV A,AR7 ; schicken + CJNE A,#PenDown,G_W_PenUp ; Auf- oder Abbewegung? + ljmp G_W_PenDown +G_W_PenUp: + jb drill_down,G_W_Make_Up + ljmp G_W_Pen_Ready ; ist schon oben +G_W_Make_Up: + post_message2 #Frs,#MoveZ,Frs_Ref_z,Frs_Ref_z+1 ; Pen aus Werkstueck ziehen + queue_test + post_message2 #Frs,#FrsVelocityDraw,#fast ; schnelle Bewegung + queue_test + post_message2 #Frs,#MoveRZ,#(d_z/256),#(d_z#256) ; Pen up + clr DRILL_DOWN + queue_test + LJMP G_W_Pen_Ready ; fertig + +G_W_PenDown: + jnb drill_down,G_W_Make_Down + ljmp G_W_Pen_Ready ; ist schon unten +G_W_Make_Down: + post_message2 #Frs,#MoveRZ,#(((-d_z) & 0ffffh) / 256),#(((-d_z) & 0ffffh) # 256) ; Ab + queue_test + post_message2 #Frs,#FrsVelocityDraw,#slow ; langsame Bewegung + queue_test + post_message2 #Frs,#MoveZ,Frs_Ref_Tiefe,Frs_Ref_Tiefe+1 ; Pen aus Werkstueck ziehen + queue_test + SETB DRILL_DOWN +G_W_Pen_Ready: ; Pen fertig ! + + POP_ALL + post_message2 #Frs,#MovePR,AR4,AR3,AR6,AR5,#0,#0 ; rel. Bewegung + queue_test + +; DJNZ Queue_Counter,G_W_Send_no_Ready +; MOV Queue_Counter,#Queue_Const +; PUSH_ALL +; post_message2 #Frs,#GibReady,#MemFrs,#GetFrsReady,#0 +; POP_ALL + +G_W_Send_no_Ready: + + GET_16 BLOCKNR + INC DPTR + SET_16 BLOCKNR ; Blocknr.=+1 setzen + MOV R1,DPL ; Blocknr. + MOV R2,DPH + MOV A,MY_SLAVE_ADR + SWAP A ; *16 + ADD A,#MSG_PC_GET+Msg_Frs_Datei + MOV R0,A + MOV A,#PC_Slave_Adr + MOV B,#8 + SEND_NET ; naechsten Block anfordern + POP_ALL + RET + +GET_WORKFR_FROM_PC_ENDE: + post_message2 #Frs,#DRILL,#off ; + CLR Drilling + + POP_ALL + LCD 40h,"Fraesdatei fertig. " + RET + +GET_WORKFR_FROM_PC_ABBRUCH: + CLR Drilling + POP_ALL + RET + +;--------------------------------------------------------------------- +; Funktion : Warnung von Frs erhalten und verarbeiten. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +Get_Warning_From_Frs: + LCD 40h,"Warnung Fraese: " + PUSH ACC + PUSH PSW + PUSH B + PUSH_DPTR + + MOV A,AR2 + IFMAKE QUEUE_WARNING,SETB FrsWarning ; Queue Fraese laeuf ueber + + MOV DPTR,#ParamStr_Tab ; Tabellenbasis laden +GWFF_NEXT: + MOV A,#0 + MOVC A,@A+DPTR ; Wert laden + PUSH ACC ; retten + MOV A,#1 + MOVC A,@A+DPTR ; Stringlaenge laden + MOV B,A + POP ACC ; Wert mit empfangenem + CJNE A,AR2,GWFF_LOOP ; vergleichen + LJMP GWFF_AUSGABE +GWFF_LOOP: + MOV A,B ; Stringlaende auf Tabellen- + ADD A,DPL ; zeiger addieren + MOV DPL,A + MOV A,#0 + ADDC A,DPH + MOV DPH,A + LJMP GWFF_NEXT + +GWFF_AUSGABE: + MOV A,#50h ; LCD- Position + LCALL LCD_SET_DD_RAM_ADDRESS + INC DPTR + INC DPTR + LCALL LCD_WRITE_STRING ; Meldung ausgeben + MOV A,#0h ; LCD- Position + LCALL LCD_SET_DD_RAM_ADDRESS + + POP_DPTR + POP B + POP PSW + POP ACC + RET + +;--------------------------------------------------------------------- +; Funktion : Fehler von Frs erhalten und verarbeiten. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +Get_Error_From_Frs: + LCD 40h,"Fehler Fraese: " + PUSH ACC + PUSH PSW + PUSH B + PUSH_DPTR + MOV DPTR,#ParamStr_Tab ; Tabellenbasis laden +GEFF_NEXT: + MOV A,#0 + MOVC A,@A+DPTR ; Wert laden + PUSH ACC + MOV A,#1 + MOVC A,@A+DPTR ; Stringlaenge laden + MOV B,A + POP ACC ; Wert mit empfangenem + CJNE A,AR2,GEFF_LOOP ; vergleichen + LJMP GEFF_AUSGABE +GEFF_LOOP: + MOV A,B ; Stringlaende auf Tabellen- + ADD A,DPL ; zeiger addieren + MOV DPL,A + MOV A,#0 + ADDC A,DPH + MOV DPH,A + LJMP GEFF_NEXT + +GEFF_AUSGABE: + MOV A,#4Fh ; LCD- Position + LCALL LCD_SET_DD_RAM_ADDRESS + INC DPTR + INC DPTR + LCALL LCD_WRITE_STRING ; Meldung ausgeben + MOV A,#0h ; LCD- Position + LCALL LCD_SET_DD_RAM_ADDRESS + + POP_DPTR + POP B + POP PSW + POP ACC + RET + +;--------------------------------------------------------------------- +; Funktion : +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +;===================================================================== +; END +;--------------------------------------------------------------------- + + + diff --git a/tests/t_mic51/TAST1.ASM b/tests/t_mic51/TAST1.ASM new file mode 100644 index 0000000..0a34ecb --- /dev/null +++ b/tests/t_mic51/TAST1.ASM @@ -0,0 +1,250 @@ + +; Aufgabe Nr.: Speichermodul fuer uP- Praktikum II +; Autor: Joerg Vollandt +; erstellt am : 21.05.1994 +; letzte Aenderung am : +; Bemerkung : Routinen fuer ASCII- Tastatur +; +; Dateiname : tast1.asm +; + +;--------------------------------------------------------------------- +; Definitionen + + SEGMENT DATA + +ZEICHEN DB ? + + SEGMENT BITDATA + +STROB DB ? + +;--------------------------------------------------------------------- + SEGMENT CODE +;===================================================================== +; Funktion : Tastaturinterrupt initialisieren +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +INIT_TASTATUR: + Init_Vektor INT0_VEKTOR,TASTATUR_INT + SETB IT0 + CLR IE0 + SETB EX0 + RET + +;--------------------------------------------------------------------- +; Funktion : Interruptroutine fuer Tastatur, setzt bei Tastaturstrob +; das Bit STROB und schreibt das Zeichen von der Tastatur +; nach ZEICHEN. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +TASTATUR_INT: + MOV ZEICHEN,P1 + SETB STROB + RETI + +;--------------------------------------------------------------------- +; Funktion : Klein- in Grossbuchstaben umwandeln. +; Aufrufparameter : ACC = Zeichen +; Ruechgabeparameter : ACC = Zeichen +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + + ifdef joerg + +UPCASE: PUSH PSW + CJNE A,#'a',UPCASE1 +UPCASE1: JC UPCASE2 + CJNE A,#07bh,UPCASE3 +UPCASE3: JNC UPCASE2 + CLR C + SUBB A,#32 +UPCASE2: POP PSW + RET + + endif + +;--------------------------------------------------------------------- +; Funktion : Warten bis Tastendruck und Zeichen verwerfen. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +WAIT_KEY: + ifdef joerg + + JNB STROB,$ + CLR STROB + RET + + elseif + + JNB KB_CHAR_READY,$ + CLR KB_CHAR_READY + RET + + endif +;--------------------------------------------------------------------- +; Funktion : Warten bis Tastendruck und Zeichen nach ACC von der +; Tastatur einlesen. +; Aufrufparameter : - +; Ruechgabeparameter : ACC = Zeichen +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +CHAR_ACC: + ifdef joerg + + JNB STROB,$ + CLR STROB + MOV A,ZEICHEN + RET + + elseif + + JNB KB_CHAR_READY,$ + CLR KB_CHAR_READY + MOV A,KB_CHAR_BUFFER + RET + + endif + +;--------------------------------------------------------------------- +; Funktion : ACC in hex von der Tastatur einlesen. +; Aufrufparameter : - +; Ruechgabeparameter : ACC = Wert +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +IN_ACC: + PUSH PSW + PUSH B + LCALL CHAR_ACC + LCALL LCD_WRITE_CHAR + LCALL UPCASE + CJNE A,#'A',IN_ACC1 +IN_ACC1: JC IN_ACC2 + CJNE A,#'G',IN_ACC3 +IN_ACC3: JNC IN_ACC2 + CLR C + SUBB A,#7 +IN_ACC2: CLR C + SUBB A,#30h + SWAP A + MOV B,A + LCALL CHAR_ACC + LCALL LCD_WRITE_CHAR + LCALL UPCASE + CJNE A,#'A',IN_ACC11 +IN_ACC11: JC IN_ACC12 + CJNE A,#'G',IN_ACC13 +IN_ACC13: JNC IN_ACC12 + CLR C + SUBB A,#7 +IN_ACC12: CLR C + SUBB A,#30h + ORL A,B + POP B + POP PSW + RET + +;--------------------------------------------------------------------- +; Funktion : DPTR in hex von der Tastatur einlesen. +; Aufrufparameter : - +; Ruechgabeparameter : DPTR = Wert +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +IN_DPTR: + PUSH ACC + LCALL IN_ACC + MOV DPH,A + LCALL IN_ACC + MOV DPL,A + POP ACC + RET + +;--------------------------------------------------------------------- +; Funktion : ACC in hex auf LCD ausgeben. +; Aufrufparameter : ACC = Wert +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +A_LCD: PUSH ACC + PUSH ACC + SWAP A + ANL A,#00001111B + ADD A,#'0' + CJNE A,#':',A_LCD1 +A_LCD1: JC A_LCD2 + ADD A,#7 +A_LCD2: LCALL LCD_WRITE_CHAR + POP ACC + ANL A,#00001111B + ADD A,#'0' + CJNE A,#':',A_LCD3 +A_LCD3: JC A_LCD4 + ADD A,#7 +A_LCD4: LCALL LCD_WRITE_CHAR + POP ACC + RET + +;--------------------------------------------------------------------- +; Funktion : DPTR in hex auf LCD ausgeben. +; Aufrufparameter : DPTR = Wert +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +DPTR_LCD: + PUSH ACC + MOV A,DPH + LCALL A_LCD + MOV A,DPL + LCALL A_LCD + POP ACC + RET + +;--------------------------------------------------------------------- +; Funktion : Setzt LCD- Status neu +; Aufrufparameter : A = Status +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +LCD_SET_STATUS: + + RET + +;===================================================================== +; END +;--------------------------------------------------------------------- + diff --git a/tests/t_mic51/TEACH1.ASM b/tests/t_mic51/TEACH1.ASM new file mode 100644 index 0000000..3618062 --- /dev/null +++ b/tests/t_mic51/TEACH1.ASM @@ -0,0 +1,504 @@ + +; Aufgabe Nr.: Teach- In Einheit fuer uP- Praktikum II +; Autor: Joerg Vollandt +; erstellt am : 31.05.1994 +; letzte Aenderung am : 14.07.1994 +; Bemerkung : +; +; Dateiname : teach1.asm +; + +;===================================================================== +; Definitionen der Funktionen der Teach- In Einheit + +;INIT_TEACH Initialisieren der Teach- In Einheit +;DEINIT_TEACH Deinitialisieren der Teach- In Einheit +;CLEAR_TEACH Speicher loeschen +;RESET_TEACH Speicher zum lesen zuruecksetzen +;STORE_ROB Position Roboter speichern +;STORE_FRAES Position Fraese speichern +;SYNC +;LOAD_ROB Roboter Teach- In Datei von PC laden +;LOAD_FRAES Fraese- Teach- In Datei von PC laden +;LOAD Beide Teach- In Dateien von PC laden +;SAVE_ROB Roboter Teach- In Datei auf PC speichern +;SAVE_FRAES Fraese- Teach- In Datei auf PC speichern + +;------------------------------------------------------------------------------ + SEGMENT CODE +;--------------------------------------------------------------------- +; Funktion : Initialisieren der Error- und Warningeinspruenge fuer die +; Fraese. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +INIT_FRS: + JB P3.5,INIT_FRAES_START + LJMP INIT_FRAES_ENDE +INIT_FRAES_START: + PUSH_ALL +; MOV B,#5 ; Msg. Frs +; MOV AR2,#MemFrs ; meine Adr. +; MOV AR3,#GetFrsError ; Fehlereinsprung +; MOV AR4,#GetFrsWarning ; Warnungeinsprung +; post_message1 Frs,SetMasterAdress ; Ready-Anfordrung + post_message2 #Frs,#SetMasterAdress,#MemFrs,#GetFrsError,#GetFrsWarning + POP_ALL +INIT_FRAES_ENDE: + RET + +;--------------------------------------------------------------------- +; Funktion : Initialisieren der Teach- In Einheit +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +INIT_TEACH: + CLR READY + CLR CRC + LCALL INIT_MEM + MOV T_Sync_Counter,#0 + MOV Frs_Ref_x,#0 + MOV Frs_Ref_x+1,#0 + MOV Frs_Ref_y,#0 + MOV Frs_Ref_y+1,#0 + MOV Frs_Ref_z,#0 + MOV Frs_Ref_z+1,#0 + MOV Frs_Ref_Tiefe,#0 + MOV Frs_Ref_Tiefe+1,#0 + CLR Ref_Flag + CLR Tiefe_Flag + RET + +;--------------------------------------------------------------------- +; Funktion : Deinitialisieren der Teach- In Einheit +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +DEINIT_TEACH: + CLR READY + CLR CRC + LCALL DEINIT_MEM + + RET + +;--------------------------------------------------------------------- +; Funktion : Speicher der Teach- In Einheit loeschen +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +CLEAR_TEACH: + + RET + +;--------------------------------------------------------------------- +; Funktion : Teach- In Einheit zuruecksetzen +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +RESET_TEACH: + LCALL RESET_MEM + SETB READY + + RET + +;--------------------------------------------------------------------- +; Funktion : Roboter Teach- In Datei von PC laden +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +LOAD_ROB: + JB P3.5,LOAD_ROB_ENDE + CLR READY + LCD 40H,"Roboter- Teachin- Datei wird geladen. " + LCALL RD_MEM_PC +LOAD_ROB_ENDE: + RET + +;--------------------------------------------------------------------- +; Funktion : Fraese- Teach- In Datei von PC laden +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +LOAD_FRAES: + JNB P3.5,LOAD_FRAES_ENDE + CLR READY + LCD 40H,"Fraese- Teachin- Datei wird geladen. " + LCALL RD_MEM_PC +LOAD_FRAES_ENDE: + RET + +;--------------------------------------------------------------------- +; Funktion : Roboter Teach- In Datei auf PC speichern +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +SAVE_ROB: + JB READY,SAVE_ROB_START + JNB P3.5,SAVE_ROB_START + LJMP SAVE_ROB_ENDE +SAVE_ROB_START: + LCD 40H,"Roboter- Teachin- Datei wird gespeichert" + LCALL WR_MEM_PC + JNC SAVE_ROB_OK + LCD 40H,"FEHLER bei Speichern. " + RET + +SAVE_ROB_OK: + LCD 40H,"Datei gespeichert. " + RET + +SAVE_ROB_ENDE: + RET + +;--------------------------------------------------------------------- +; Funktion : Fraese- Teach- In Datei auf PC speichern +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +SAVE_FRAES: + JB READY,SAVE_FRAES_START + JB P3.5,SAVE_FRAES_START + LJMP SAVE_FRAES_ENDE +SAVE_FRAES_START: + LCALL WR_MEM_PC + JNC SAVE_FRAES_OK + LCD 40H,"FEHLER bei Speichern. " + RET + +SAVE_FRAES_OK: + LCD 40H,"Datei gespeichert. " + RET + +SAVE_FRAES_ENDE: + RET + +;--------------------------------------------------------------------- +; Funktion : Position des Roboters speichern. 1. Teil: Msg- Header +; in MEM speichern und ersten Teil der Position vom Roboter +; anfordern. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +STORE_ROB: + PUSH PSW + PUSH ACC + PUSH AR0 + JNB READY,STORE_ROB_ENDE ; Fertig und Roboter ? + JB P3.5,STORE_ROB_ENDE + + MOV B,#4 ; Msg. an Roboter um Pos. + MOV R2,#MemRob ; Empfaenger angeben + MOV R3,#RobPos1 ; Msg.-Nr. Empfaenger angeben + post_message1 Rob,GibPos1 ; zu erfragen + +STORE_ROB_ENDE: + CLR READY ; Teach- In nicht bereit + POP AR0 + POP ACC + POP PSW + RET + +;--------------------------------------------------------------------- +; Funktion : Position des Roboters speichern. 2. Teil: 1. Teil Position +; in MEM speichern und zweiten Teil der Position vom Roboter +; anfordern. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +FIRST_FROM_ROB: + PUSH PSW + PUSH ACC + PUSH AR0 + JB READY,FIRST_ROB_ENDE ; NICHT Fertig und Roboter ? + JB P3.5,FIRST_ROB_ENDE + MOV A,#8 ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Msg.-Laenge) + ERROR 0 + MOV A,#Rob ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Modulnr.) + ERROR 0 + MOV A,#MoveAPos1 ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Msg.- Nr.) + ERROR 0 + MOV A,R2 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 1 High) + ERROR 0 + MOV A,R3 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 1 Low) + ERROR 0 + MOV A,R4 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 2 High) + ERROR 0 + MOV A,R5 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 2 Low) + ERROR 0 + MOV A,R6 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 3 High) + ERROR 0 + MOV A,R7 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 3 Low) + ERROR 0 + + MOV B,#4 ; Msg. an Roboter um Pos. + MOV R2,#MemRob ; Empfaenger angeben + MOV R3,#RobPos2 ; Msg.-Nr. Empfaenger angeben + post_message1 Rob,GibPos2 ; zu erfragen + +FIRST_ROB_ENDE: + POP AR0 + POP ACC + POP PSW + + RET + +;--------------------------------------------------------------------- +; Funktion : Position des Roboters speichern. 3. Teil: 2. Teil Position +; in MEM speichern. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +SECOND_FROM_ROB: + PUSH PSW + PUSH ACC + PUSH AR0 + JB READY,SECOND_ROB_ENDE ; NICHT Fertig und Roboter ? + JB P3.5,SECOND_ROB_ENDE + MOV A,#8 ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Msg.-Laenge) + ERROR 0 + MOV A,#Rob ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Modulnr.) + ERROR 0 + MOV A,#MoveAPos2 ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Msg.- Nr.) + ERROR 0 + MOV A,R2 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 1 High) + ERROR 0 + MOV A,R3 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 1 Low) + ERROR 0 + MOV A,R4 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 2 High) + ERROR 0 + MOV A,R5 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 2 Low) + ERROR 0 + MOV A,R6 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 3 High) + ERROR 0 + MOV A,R7 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 3 Low) + ERROR 0 + +SECOND_ROB_ENDE: + POP AR0 + POP ACC + POP PSW + SETB READY ; Teach- In wieder bereit + RET + +;--------------------------------------------------------------------- +; Funktion : Position der Fraese speichern. 1. Teil: Msg- Header +; in MEM speichern und ersten Teil der Position von Fraese +; anfordern. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +STORE_FRAES: + PUSH PSW + PUSH ACC + PUSH AR0 + JNB READY,STORE_FRS_ENDE ; Fertig und Fraese? + JNB P3.5,STORE_FRS_ENDE + + MOV B,#4 ; Msg. an Roboter um Pos. + MOV R2,#MemFrs ; Empfaenger angeben + MOV R3,#FrsPos1 ; Msg.-Nr. Empfaenger angeben + post_message1 Frs,GibFrsPos1 ; zu erfragen + +STORE_FRS_ENDE: + CLR READY ; Teach- In nicht bereit + POP AR0 + POP ACC + POP PSW + RET + +;--------------------------------------------------------------------- +; Funktion : Position der Fraese speichern. 2. Teil: 1. Teil Position +; in MEM speichern und zweiten Teil der Position von Fraese +; anfordern. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +FIRST_FROM_FRS: + PUSH PSW + PUSH ACC + PUSH AR0 + JB READY,FIRST_FRS_ENDE ; NICHT Fertig und Roboter ? + JNB P3.5,FIRST_FRS_ENDE + MOV A,#8 ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Msg.-Laenge) + ERROR 0 + MOV A,#Frs ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Modulnr.) + ERROR 0 + MOV A,#MoveAPos ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Msg.- Nr.) + ERROR 0 + MOV A,R2 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 1 High) + ERROR 0 + MOV A,R3 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 1 Low) + ERROR 0 + MOV A,R4 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 2 High) + ERROR 0 + MOV A,R5 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 2 Low) + ERROR 0 + MOV A,R6 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 3 High) + ERROR 0 + MOV A,R7 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 3 Low) + ERROR 0 + + MOV B,#4 ; Msg. an Roboter um Pos. + MOV R2,#MemFrs ; Empfaenger angeben + MOV R3,#FrsPos2 ; Msg.-Nr. Empfaenger angeben + post_message1 Frs,GibFrsPos2 ; zu erfragen + +FIRST_FRS_ENDE: + POP AR0 + POP ACC + POP PSW + + RET + +;--------------------------------------------------------------------- +; Funktion : Position der Fraese speichern. 3. Teil: 2. Teil Position +; in MEM speichern. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +SECOND_FROM_FRS: + PUSH PSW + PUSH ACC + PUSH AR0 + JB READY,SECOND_FRS_ENDE ; NICHT Fertig und Roboter ? + JNB P3.5,SECOND_FRS_ENDE + + MOV A,#4 ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Msg.-Laenge) + ERROR 0 + MOV A,#Frs ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Modulnr.) + ERROR 0 + MOV A,#MoveV ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Msg.- Nr.) + ERROR 0 + MOV A,R2 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 1 High) + ERROR 0 + MOV A,R3 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 1 Low) + ERROR 0 + + MOV A,#3 ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Msg.-Laenge) + ERROR 0 + MOV A,#Frs ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Modulnr.) + ERROR 0 + MOV A,#Drill ; Msg- Header speichern + LCALL PUT_ELEMENT_MEM ; (Msg.- Nr.) + ERROR 0 + MOV A,R4 ; Position speichern + LCALL PUT_ELEMENT_MEM ; (Parameter 2 High) + ERROR 0 + +SECOND_FRS_ENDE: + POP AR0 + POP ACC + POP PSW + SETB READY ; Teach- In wieder bereit + RET + +;--------------------------------------------------------------------- +; Funktion : +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + + + RET + +;===================================================================== +; END +;--------------------------------------------------------------------- + diff --git a/tests/t_mic51/asflags b/tests/t_mic51/asflags new file mode 100644 index 0000000..d0334c2 --- /dev/null +++ b/tests/t_mic51/asflags @@ -0,0 +1 @@ +-c -A \ No newline at end of file diff --git a/tests/t_mic51/defKey.inc b/tests/t_mic51/defKey.inc new file mode 100644 index 0000000..aac5ab1 --- /dev/null +++ b/tests/t_mic51/defKey.inc @@ -0,0 +1,83 @@ +; ***************************************************************************** +; Definition des Tastenfeldes der Teach-In Einheit +; Format: +; DefKey {On,Off}, {P4,P5}, , +; +; Es muss genau 8 Elemente pro Kategorie eingetragen werden +; Wenn leerer String, wird keine Message durch das Netz gesendet + + + DefKey On, P4, TeachRob, "Rob MoveCHL" ; Hand links + DefKey On, P4, TeachRob, "Rob MoveCHR" ; Hand rechts + DefKey On, P4, TeachRob, "Rob MoveCHO" ; Hand oeffnen + DefKey On, P4, TeachRob, "Rob MoveCHC" ; Hand schliessen + DefKey On, P4, TeachRob, "MemRob StoreRobPos" ; STORE + DefKey On, P4, TeachRob, "MemRob StoreRobReady" ; AUX1 + DefKey On, P4, TeachRob, "MemRob StoreRobSync" ; AUX2 + DefKey On, P4, TeachRob, "Rob RobVelocity Fast" ; FAST + + DefKey Off, P4, TeachRob, "Rob StopCHT" + DefKey Off, P4, TeachRob, "Rob StopCHT" + DefKey Off, P4, TeachRob, "Rob StopCH" + DefKey Off, P4, TeachRob, "Rob StopCH" + DefKey Off, P4, TeachRob, "" + DefKey Off, P4, TeachRob, "" + DefKey Off, P4, TeachRob, "" + DefKey Off, P4, TeachRob, "Rob RobVelocity Slow" + + DefKey On, P5, TeachRob, "Rob MoveCBL" ; Rumpf links + DefKey On, P5, TeachRob, "Rob MoveCBR" ; Rumpf rechts + DefKey On, P5, TeachRob, "Rob MoveCSU" ; Oberarm heben + DefKey On, P5, TeachRob, "Rob MoveCSD" ; Oberarm senken + DefKey On, P5, TeachRob, "Rob MoveCEU" ; Unterarm heben + DefKey On, P5, TeachRob, "Rob MoveCED" ; Unterarm senken + DefKey On, P5, TeachRob, "Rob MoveCHU" ; Hand heben + DefKey On, P5, TeachRob, "Rob MoveCHD" ; Hand senken + + DefKey Off, P5, TeachRob, "Rob StopCB" + DefKey Off, P5, TeachRob, "Rob StopCB" + DefKey Off, P5, TeachRob, "Rob StopCS" + DefKey Off, P5, TeachRob, "Rob StopCS" + DefKey Off, P5, TeachRob, "Rob StopCE" + DefKey Off, P5, TeachRob, "Rob StopCE" + DefKey Off, P5, TeachRob, "Rob StopCHP" + DefKey Off, P5, TeachRob, "Rob StopCHP" + + DefKey On, P4, TeachFrs, "Frs Drill on" ; Fraesmotor ein + DefKey On, P4, TeachFrs, "Frs Drill off" ; Fraesmotor aus + DefKey On, P4, TeachFrs, "MemFrs StoreFrsPos" ; STORE + DefKey On, P4, TeachFrs, "Frs FrsVelocity fast" ; FAST + DefKey On, P4, TeachFrs, "MemFrs StoreFrsReady" ; AUX1 + DefKey On, P4, TeachFrs, "MemFrs StoreFrsSync" ; AUX2 + DefKey On, P4, TeachFrs, "MemFrs StoreFrsDrill" ; AUX3 + DefKey On, P4, TeachFrs, "" ; AUX4 + + DefKey Off, P4, TeachFrs, "" + DefKey Off, P4, TeachFrs, "" + DefKey Off, P4, TeachFrs, "" + DefKey Off, P4, TeachFrs, "Frs FrsVelocity slow" + DefKey Off, P4, TeachFrs, "" + DefKey Off, P4, TeachFrs, "" + DefKey Off, P4, TeachFrs, "" + DefKey Off, P4, TeachFrs, "" + + DefKey On, P5, TeachFrs, "Frs MoveCX +" ; X+ + DefKey On, P5, TeachFrs, "Frs MoveCX -" ; X- + DefKey On, P5, TeachFrs, "Frs MoveCY +" ; Y+ + DefKey On, P5, TeachFrs, "Frs MoveCY -" ; Y- + DefKey On, P5, TeachFrs, "Frs MoveCZ +" ; Z+ + DefKey On, P5, TeachFrs, "Frs MoveCZ -" ; Z- + DefKey On, P5, TeachFrs, "Frs MoveCV +" ; Schraubstock auf + DefKey On, P5, TeachFrs, "Frs MoveCV -" ; Schraubstock zu + + DefKey Off, P5, TeachFrs, "Frs StopCX +" + DefKey Off, P5, TeachFrs, "Frs StopCX -" + DefKey Off, P5, TeachFrs, "Frs StopCY +" + DefKey Off, P5, TeachFrs, "Frs StopCY -" + DefKey Off, P5, TeachFrs, "Frs StopCZ +" + DefKey Off, P5, TeachFrs, "Frs StopCZ -" + DefKey Off, P5, TeachFrs, "Frs StopCV +" + DefKey Off, P5, TeachFrs, "Frs StopCV -" + +; +; ***************************************************************************** diff --git a/tests/t_mic51/defModul.inc b/tests/t_mic51/defModul.inc new file mode 100644 index 0000000..98682ca --- /dev/null +++ b/tests/t_mic51/defModul.inc @@ -0,0 +1,18 @@ +; **************************************************************************** +; Definition der Modulnamen +; Format: +; defModul , +; +; Dem wird eine eindeutige Zahl zugeordnet. +; + defModul Rob, uC_Rob + defModul Frs, uC_Frs + defModul TeachRob, uC_Teach_Rob + defModul TeachFrs, uC_Teach_Frs + defModul TeachKey, uC_Teach_Key + defModul MemRob, uC_Teach_Rob + defModul MemFrs, uC_Teach_Frs + defModul PC_SIO, uC_PC_SIO + +; +; **************************************************************************** diff --git a/tests/t_mic51/defMsg.inc b/tests/t_mic51/defMsg.inc new file mode 100644 index 0000000..420c19e --- /dev/null +++ b/tests/t_mic51/defMsg.inc @@ -0,0 +1,141 @@ +; **************************************************************************** +; Definition der Parameter - Pattern +; +;NoParamSingle +;ParamSingle1 +;ParamSingle2 +;ParamSingle3 +;ParamSingle4 +;ParamSingle5 +;ParamSingle6 + +; +; **************************************************************************** +; Definition der Messages +; Format: +; DefMsg , , , +; + DefMsg Rob, MoveAB , 1, NoParamSingle + DefMsg Rob, MoveAS , 1, NoParamSingle + DefMsg Rob, MoveAE , 1, NoParamSingle + DefMsg Rob, MoveARW , 1, NoParamSingle + DefMsg Rob, MoveALW , 1, NoParamSingle + DefMsg Rob, MoveAH , 1, NoParamSingle + DefMsg Rob, MoveAPos1 , 3, NoParamSingle + DefMsg Rob, MoveAPos2 , 3, NoParamSingle + DefMsg Rob, MoveRB , 1, NoParamSingle + DefMsg Rob, MoveRS , 1, NoParamSingle + DefMsg Rob, MoveRE , 1, NoParamSingle + DefMsg Rob, MoveRRW , 1, NoParamSingle + DefMsg Rob, MoveRLW , 1, NoParamSingle + DefMsg Rob, MoveRH , 1, NoParamSingle + DefMsg Rob, MoveRPos1 , 3, NoParamSingle + DefMsg Rob, MoveRPos2 , 3, NoParamSingle + DefMsg Rob, MoveCBL , 0, NoParamSingle + DefMsg Rob, MoveCBR , 0, NoParamSingle + DefMsg Rob, StopCB , 0, NoParamSingle + DefMsg Rob, MoveCSU , 0, NoParamSingle + DefMsg Rob, MoveCSD , 0, NoParamSingle + DefMsg Rob, StopCS , 0, NoParamSingle + DefMsg Rob, MoveCEU , 0, NoParamSingle + DefMsg Rob, MoveCED , 0, NoParamSingle + DefMsg Rob, StopCE , 0, NoParamSingle + DefMsg Rob, MoveCHU , 0, NoParamSingle + DefMsg Rob, MoveCHD , 0, NoParamSingle + DefMsg Rob, StopCHP , 0, NoParamSingle + DefMsg Rob, MoveCHL , 0, NoParamSingle + DefMsg Rob, MoveCHR , 0, NoParamSingle + DefMsg Rob, StopCHT , 0, NoParamSingle + DefMsg Rob, MoveCHO , 0, NoParamSingle + DefMsg Rob, MoveCHC , 0, NoParamSingle + DefMsg Rob, StopCH , 0, NoParamSingle + DefMsg Rob, RobVelocity , 1, ParamSingle1 + DefMsg Rob, RobGoHome , 0, NoParamSingle + DefMsg Rob, SetHome , 0, NoParamSingle + DefMsg Rob, GibPos1 , 2, ParamSingle1+ParamSingle2 + DefMsg Rob, GibPos2 , 2, ParamSingle1+ParamSingle2 + DefMsg Rob, RobGibReady , 2, ParamSingle1+ParamSingle2 + DefMsg Rob, RobInit , 0, NoParamSingle + DefMsg Rob, RobDeInit , 0, NoParamSingle + + DefMsg Frs, Init , 0, NoParamSingle + DefMsg Frs, DeInit , 0, NoParamSingle + DefMsg Frs, MoveCX , 1, ParamSingle1 + DefMsg Frs, MoveCY , 1, ParamSingle1 + DefMsg Frs, MoveCZ , 1, ParamSingle1 + DefMsg Frs, MoveCV , 1, ParamSingle1 + DefMsg Frs, StopCX , 1, ParamSingle1 + DefMsg Frs, StopCY , 1, ParamSingle1 + DefMsg Frs, StopCZ , 1, ParamSingle1 + DefMsg Frs, StopCV , 1, ParamSingle1 + DefMsg Frs, FrsVelocity , 1, ParamSingle1 + DefMsg Frs, FrsVelocityDraw , 1, ParamSingle1 + DefMsg Frs, FrsGoHome , 0, NoParamSingle + DefMsg Frs, RefFahrt , 0, NoParamSingle + DefMsg Frs, SetDrillRef , 0, NoParamSingle + DefMsg Frs, SetPieceRef , 3, NoParamSingle + DefMsg Frs, MoveX , 1, NoParamSingle + DefMsg Frs, MoveY , 1, NoParamSingle + DefMsg Frs, MoveZ , 1, NoParamSingle + DefMsg Frs, MoveAPos , 3, NoParamSingle + DefMsg Frs, MoveRX , 1, NoParamSingle + DefMsg Frs, MoveRY , 1, NoParamSingle + DefMsg Frs, MoveRZ , 1, NoParamSingle + DefMsg Frs, MoveRV , 1, NoParamSingle + DefMsg Frs, MoveRPos , 3, NoParamSingle + DefMsg Frs, MoveVOpen , 0, NoParamSingle + DefMsg Frs, MoveVClose , 0, NoParamSingle + DefMsg Frs, MoveV , 1, NoParamSingle + DefMsg Frs, GoPieceRefPos , 0, NoParamSingle + DefMsg Frs, MovePR , 3, NoParamSingle + DefMsg Frs, Drill , 1, ParamSingle1 + DefMsg Frs, SetMasterAdress , 3, ParamSingle1+ParamSingle2+ParamSingle3 + DefMsg Frs, GibFrsPos1 , 2, ParamSingle1+ParamSingle2 + DefMsg Frs, GibFrsPos2 , 2, ParamSingle1+ParamSingle2 + DefMsg Frs, GibPosP , 2, ParamSingle1+ParamSingle2 + DefMsg Frs, GibStatus , 2, ParamSingle1+ParamSingle2 + DefMsg Frs, GibReady , 3, ParamSingle1+ParamSingle2+ParamSingle3 + + DefMsg MemRob,LoadRob,0, NoParamSingle + DefMsg MemRob,SaveRob,0, NoParamSingle + DefMsg MemRob,StartRobRun,0, NoParamSingle + DefMsg MemRob,StoreRobPos,0, NoParamSingle + DefMsg MemRob,StoreRobSync,0, NoParamSingle + DefMsg MemRob,StoreRobReady,0, NoParamSingle + DefMsg MemRob,InitRobTeach,0, NoParamSingle + DefMsg MemRob,DeinitRobTeach,0, NoParamSingle + DefMsg MemRob,ClearRobTeach,0, NoParamSingle + DefMsg MemRob,ResetRobTeach,0, NoParamSingle + DefMsg MemRob,GetRobSync,1,ParamSingle1 + DefMsg MemRob,GetRobReady,0, NoParamSingle + DefMsg MemRob,RobPos1,3, NoParamSingle + DefMsg MemRob,RobPos2,3, NoParamSingle + DefMsg MemRob,DebugRob,0, NoParamSingle + + DefMsg MemFrs,LoadFrs,0, NoParamSingle + DefMsg MemFrs,SaveFrs,0, NoParamSingle + DefMsg MemFrs,StartFrsRun,0, NoParamSingle + DefMsg MemFrs,StoreFrsPos,0, NoParamSingle + DefMsg MemFrs,StoreFrsSync,0, NoParamSingle + DefMsg MemFrs,StoreFrsReady,0, NoParamSingle + DefMsg MemFrs,StoreFrsPieceRef,0, NoParamSingle + DefMsg MemFrs,StoreFrsTiefe,0, NoParamSingle + DefMsg MemFrs,StoreFrsDrill,0, NoParamSingle + DefMsg MemFrs,InitFrsTeach,0, NoParamSingle + DefMsg MemFrs,DeinitFrsTeach,0, NoParamSingle + DefMsg MemFrs,ClearFrsTeach,0, NoParamSingle + DefMsg MemFrs,ResetFrsTeach,0, NoParamSingle + DefMsg MemFrs,GetFrsSync,1,ParamSingle1 + DefMsg MemFrs,GetFrsReady,0, NoParamSingle + DefMsg MemFrs,FrsPos1,3, NoParamSingle + DefMsg MemFrs,FrsPos2,3, NoParamSingle + DefMsg MemFrs,FrsPieceRef,3, NoParamSingle + DefMsg MemFrs,FrsTiefe,3, NoParamSingle + DefMsg MemFrs,GetFrsError,1, ParamSingle1 + DefMsg MemFrs,GetFrsWarning,1, ParamSingle1 + DefMsg MemFrs,DebugFrs,0, NoParamSingle + + DefMsg TeachFrs,Bug,0,NoParamSingle + +; +; **************************************************************************** diff --git a/tests/t_mic51/defParam.inc b/tests/t_mic51/defParam.inc new file mode 100644 index 0000000..8d7e9d5 --- /dev/null +++ b/tests/t_mic51/defParam.inc @@ -0,0 +1,46 @@ +; ***************************************************************************** +; Definition der Parameter +; Format: +; DefParam , , +; soll der String gleichlautend wie der Parametername sein dann reicht "" +; + + DefParam On, 001H, "" + DefParam Off, 000H, "" + DefParam Plus, 001H, "+" + DefParam Minus, 000H, "-" + DefParam Fast, 001H, "" + DefParam Slow, 000H, "" + DefParam Superslow, 002H, "" + +; Hier kommen die Warning-Codes fr die Fr„se + + DefParam Queue_Warning, 081H, "Queue Warning" + +; Hier kommen die Error-Codes fr die Fr„se + + DefParam Queue_Full, 061H, "Queue Full" + DefParam Undef_Par, 062H, "Undefined Parameter" + DefParam Undef_Piece_Ref, 063H, "Undefined Piece Reference" + DefParam Undef_Drill_Ref, 064H, "Undefined Drill Reference" + DefParam Undef_Koord_Ref, 065H, "Undefined Koord Reference" + DefParam Internal_Error, 066H, "Internal Error" + + DefParam End_X_Plus, 067H, "Software End X+" + DefParam End_Y_Plus, 068H, "Software End Y+" + DefParam End_Z_Plus, 069H, "Software End Z+" + DefParam End_V_Plus, 06AH, "Software End V+" + DefParam End_X_Minus, 070H, "Software End X-" + DefParam End_Y_Minus, 071H, "Software End Y-" + DefParam End_Z_Minus, 072H, "Software End Z-" + DefParam End_V_Minus, 073H, "Software End V-" + + DefParam Hard_End_X_Plus, 074H, "Hardware End X+" + DefParam Hard_End_Y_Plus, 075H, "Hardware End Y+" + DefParam Hard_End_Z_Plus, 076H, "Hardware End Z+" + DefParam Hard_End_V_Plus, 077H, "Hardware End V+" + DefParam Hard_End_X_Minus, 078H, "Hardware End X-" + DefParam Hard_End_Y_Minus, 079H, "Hardware End Y-" + DefParam Hard_End_Z_Minus, 07AH, "Hardware End Z-" + DefParam Hard_End_V_Minus, 07BH, "Hardware End V-" +; ***************************************************************************** diff --git a/tests/t_mic51/defgequ.inc b/tests/t_mic51/defgequ.inc new file mode 100644 index 0000000..c77f9b1 --- /dev/null +++ b/tests/t_mic51/defgequ.inc @@ -0,0 +1,48 @@ +; **************************************************************************** +; EQU - Anweisungen fuer alle Module +; **************************************************************************** + + ifndef defgequ_inc +defgequ_inc equ 000H + +; ---------------------------------------------------------------------------- +StringEnde equ 000H +TableEnd equ 0FFH +TableAnf equ 0FEH +Rob_NextMsg set 001H +Frs_NextMsg set 001H +TeachRob_NextMsg set 001H +TeachFrs_NextMsg set 001H +MemRob_NextMsg set 001H +MemFrs_NextMsg set 001H +NextModul set 010H ; Modul < 10H : = Message from PC!! + ; Doku beachten. +; ---------------------------------------------------------------------------- +; Definition der Netzwerkadressen +; +uC_Rob equ 001H ; Microcontroller des Roboters +uC_Frs equ 002H ; Microcontroller der Fraese +uC_Teach_Rob equ 003H ; Microcontroller Teach-In Roboter +uC_Teach_Frs equ 004H ; Microcontroller Teach-In Fraese +uC_Teach_Key equ 005H ; Microcontroller Teach-In Tastatur + +uC_PC_SIO equ 00EH ; Microcontroller PC + +; ---------------------------------------------------------------------------- + + elseif + fatal "Die Datei DEFGEQU.INC ist mehrmals eingebunden" + endif + +; ---------------------------------------------------------------------------- + +NoParamSingle equ 000H +ParamSingle1 equ 001H +ParamSingle2 equ 002H +ParamSingle3 equ 004H +ParamSingle4 equ 008H +ParamSingle5 equ 010H +ParamSingle6 equ 020H + +; +; **************************************************************************** diff --git a/tests/t_mic51/defint.inc b/tests/t_mic51/defint.inc new file mode 100644 index 0000000..2ea07c5 --- /dev/null +++ b/tests/t_mic51/defint.inc @@ -0,0 +1,234 @@ +;**************************************************************************** +; Definition der Interrupts und des Timers 2 +; + +Falling_Edge EQU True +Low_Level EQU False +Negative_Trans EQU False +Positive_Trans EQU True + +Param_On EQU True +Param_Off EQU False + +Nope EQU False + +Tm2_Off EQU 0 ; +Tm2_Timer EQU 1 ; Input selection +Tm2_Counter EQU 2 ; +Tm2_Gated EQU 3 ; + +Tm2_Reload_Off EQU 0 ; +Tm2_Reload_Ov EQU 2 ; Reload mode +Tm2_Reload_Ext EQU 3 ; + +Tm2_Comp_Mode0 EQU False ; Compare mode +Tm2_Comp_Mode1 EQU True ; + +Tm2_Slow EQU True ; Prescaler selection +Tm2_Normal EQU False ; + +Tm2_CC_Off EQU 0 +Tm2_CC_Capt_Ext EQU 1 +Tm2_CC_Comp_On EQU 2 +Tm2_CC_Capt_CRCL EQU 3 + +;----------------------------------------------------------------------------- + +Init_Interrupt MACRO PInterrupt, PTrig, PState + IFNDEF PInterrupt + FATAL "unbekannter Interrupt" + ELSEIF + + SWITCH PInterrupt + CASE INT0_VEKTOR ; INT0 + IF PTrig + SETB IT0 + ELSEIF + CLR IT0 + ENDIF + + CASE INT1_VEKTOR ; INT1 + IF PTrig + SETB IT1 + ELSEIF + CLR IT1 + ENDIF + + CASE INT2_VEKTOR ; INT2 + IF PTrig + SETB I2FR + ELSEIF + CLR I2FR + ENDIF + + CASE INT3_VEKTOR ; INT3 + IF PTrig + SETB I3FR + ELSEIF + CLR I3FR + ENDIF + + ELSECASE + ENDCASE + + IF PState + Int_On PInterrupt + ELSEIF + Int_Off PInterrupt + ENDIF + + ENDIF + ENDM + + +;----------------------------------------------------------------------------- + +Int_On MACRO PInterrupt + IFNDEF PInterrupt + FATAL "unbekannter Interrupt" + ELSEIF + SWITCH PInterrupt + CASE INT0_VEKTOR + CLR IE0 + SETB EX0 + CASE ICT0_VEKTOR + CLR TF0 + SETB ET0 + CASE INT1_VEKTOR + CLR IE1 + SETB EX1 + CASE ICT1_VEKTOR + CLR TF1 + SETB ET1 + CASE ICT2_VEKTOR + CLR TF2 + CLR EXF2 + SETB ET2 + CASE AD_I_VEKTOR + CLR IADC + SETB EADC + CASE INT2_VEKTOR + CLR IEX2 + SETB EX2 + CASE INT3_VEKTOR + CLR IEX3 + SETB EX3 + CASE INT4_VEKTOR + CLR IEX4 + SETB EX4 + CASE INT5_VEKTOR + CLR IEX5 + SETB EX5 + CASE INT6_VEKTOR + CLR IEX6 + SETB EX6 + ENDCASE + ENDIF + ENDM + +;----------------------------------------------------------------------------- + +Int_Off MACRO PInterrupt + IFNDEF PInterrupt + FATAL "unbekannter Interrupt" + ELSEIF + SWITCH PInterrupt + CASE INT0_VEKTOR + CLR EX0 + CLR IE0 + CASE ICT0_VEKTOR + CLR ET0 + CLR TF0 + CASE INT1_VEKTOR + CLR EX1 + CLR IE1 + CASE ICT1_VEKTOR + CLR ET1 + CLR TF1 + CASE ICT2_VEKTOR + CLR ET2 + CLR TF2 + CLR EXF2 + CASE AD_I_VEKTOR + CLR EADC + CLR IADC + CASE INT2_VEKTOR + CLR EX2 + CLR IEX2 + CASE INT3_VEKTOR + CLR EX3 + CLR IEX3 + CASE INT4_VEKTOR + CLR EX4 + CLR IEX4 + CASE INT5_VEKTOR + CLR EX5 + CLR IEX5 + CASE INT6_VEKTOR + CLR EX6 + CLR IEX6 + ENDCASE + ENDIF + ENDM + +;----------------------------------------------------------------------------- + +Init_Timer2 MACRO PInput, PReloadMode, PCompareMode, PPrescaler, PReloadValue + + SWITCH PInput + CASE Tm2_Off + CLR T2I1 + CLR T2I0 + CASE Tm2_Timer + CLR T2I1 + SETB T2I0 + CASE Tm2_Counter + SETB T2I1 + CLR T2I0 + CASE Tm2_Gated + SETB T2I1 + SETB T2I0 + ENDCASE + + SWITCH PReloadMode + CASE Tm2_Reload_Off + CLR T2R1 + CLR T2R0 + CASE Tm2_Reload_Ov + SETB T2R1 + CLR T2R0 + CASE Tm2_Reload_Ext + SETB T2R1 + SETB T2R0 + ENDCASE + + IF PCompareMode + SETB T2CM + ELSEIF + CLR T2CM + ENDIF + + IF PPrescaler + SETB T2PS + ELSEIF + CLR T2PS + ENDIF + + MOV CRCL, #(PReloadValue # 256) + MOV CRCH, #(PReloadValue / 256) + + ENDM + + + +Init_Comp_Timer2 MACRO PMode1, PMode2, PMode3, PValue1, PValue2, PValue3 + + MOV CCEN, #(PMode1*4+PMode2*16+PMode3*64) + MOV CCL1, #(PValue1 # 256) + MOV CCH1, #(PValue1 / 256) + MOV CCL2, #(PValue1 # 256) + MOV CCH2, #(PValue1 / 256) + MOV CCL3, #(PValue1 # 256) + MOV CCH3, #(PValue1 / 256) + + ENDM diff --git a/tests/t_mic51/defmacro.inc b/tests/t_mic51/defmacro.inc new file mode 100644 index 0000000..f5b710d --- /dev/null +++ b/tests/t_mic51/defmacro.inc @@ -0,0 +1,175 @@ + +; *************************************************************************** +; Definition einer Tabelle aus den MSG - Includedateien + +Create_IncOffsTab macro TabName, IncDatei +TabName_Tab: label $ +FStr: db TableAnf + db FStrEnd - FStr, StringEnde, FStrEnd - FStr +FStrEnd: + include IncDatei +TabName_Tend: label $ + db TableEnd + endm + + +Create_IncTab macro TabName, IncDatei +TabName_Tab: label $ + include IncDatei +TabName_Tend: label $ + endm + + +Create_IncKeyTab macro State, Port, Modul, IncDatei +Key_Counter set 0 +State_Port_Modul_Tab: label $ + include IncDatei +State_Port_Modul_Tend: label $ + if Key_Counter <> 8 + fatal "Inkorrekte Anzahl von Elementen in Key-Tabelle" + endif + endm + + +Create_MsgJmpTab macro Modul, IncDatei +Modul_MsgCall_Tab: label $ + include IncDatei +Modul_MsgCall_Tend: label $ + db TableEnd + endm + + + +; *************************************************************************** +; + +DefModul macro Modul, NetAdr + + ifndef Modul +Modul equ NextModul +Net_Modul equ NetAdr +NextModul set NextModul + 1 + + SHARED Modul,NetAdr + + endif + + ifdef ModulNetAdr_Tab + ifndef ModulNetAdr_TEND + if (ModulNetAdr_Tab + Modul - $) < 0 + Fatal "NetAdr Tabelle inkonsistent" + elseif + org ModulNetAdr_Tab + Modul + endif + + db NetAdr + endif + endif + +; ------------------------- + + ifdef ModulStr_Tab + ifndef ModulStr_TEnd + +strdef: db Modul, strdefnext - strdef, "MODUL", StringEnde, strdefnext - strdef +strdefnext: + + endif + endif + + endm + +; +; *************************************************************************** +; + +DefParam macro Param, Wert, String + + ifndef Param +Param equ Wert + + SHARED Param + + endif + + ifdef ParamStr_Tab + ifndef ParamStr_TEnd +strdef: db Wert + db strdefnext - strdef + if String = "" + db "PARAM", StringEnde + elseif + db String, StringEnde + endif +strdefnext: + endif + endif + + endm + +; +; *************************************************************************** +; + +DefKey macro Status, Port, Modul, String + + ifdef Status_Port_Modul_Tab + ifndef Status_Port_Modul_TEnd +strdef: db strdefnext - strdef + db String,StringEnde +strdefnext: +Key_Counter set Key_Counter + 1 + endif + endif + + endm + +; +; *************************************************************************** +; + +DefMsg macro Modul, MsgName, ParamCount, ParamPattern + +; --------------------------------------------------------------------------- +; Definition der Message-Nummern + + ifndef MsgName +MsgName equ Modul_NextMsg +Modul_NextMsg set Modul_NextMsg + 1 + + SHARED MsgName + + endif +; --------------------------------------------------------------------------- +; Aufbau der Tabelle fuer den Message-Handler + + ifdef Modul_MsgCall_Tab + ifndef Modul_MsgCall_Tend + if (Modul_MsgCall_Tab + (2 * MsgName) - $) < 0 + Fatal "Msg-Call Tabelle inkonsistent" + elseif + org Modul_MsgCall_Tab + (2 * MsgName) + endif + + db Adr_MsgName # 256 + db Adr_MsgName / 256 + endif + endif + +; --------------------------------------------------------------------------- +; Aufbau der Stringtabelle + + ifdef MsgStr_Tab + ifndef MsgStr_TEnd + +strdef: db Modul, strdefnext - strdef, MsgName, "MSGNAME", StringEnde, ParamCount, ParamPattern + db strdefnext - strdef +strdefnext: + endif + endif + + endm +; +; *************************************************************************** + + diff --git a/tests/t_mic51/net_lcd.inc b/tests/t_mic51/net_lcd.inc new file mode 100644 index 0000000..6a0cabc --- /dev/null +++ b/tests/t_mic51/net_lcd.inc @@ -0,0 +1,33 @@ +; D:\USER\MEM\NET_LCD.ASM-Includefile fr Assembler-Programm +LCD_HOME equ 0108H +LCD_CR equ 0126H +LCD_LF equ 0172H +LCD_CLEAR equ 01C0H +LCD_WRITE_CHAR equ 01DEH +LCD_WRITE_STRING equ 01FAH +LCD_SET_DD_RAM_ADDRESS equ 022AH +LCD_STATUS equ 0248H +LCD_CURSER_ONOFF equ 025BH +SET_MY_ADRESS equ 061DH +SET_CALLBACK_ADRESS equ 0622H +READ_STATUS equ 0629H +READ_MESSAGE equ 063AH +READ_SPECIAL_MESSAGE equ 0662H +SEND_MESSAGE equ 0693H +INT0_VEKTOR equ 0FF00H +ICT0_VEKTOR equ 0FF03H +INT1_VEKTOR equ 0FF06H +ICT1_VEKTOR equ 0FF09H +ICT2_VEKTOR equ 0FF0CH +AD_I_VEKTOR equ 0FF0FH +INT2_VEKTOR equ 0FF12H +INT3_VEKTOR equ 0FF15H +INT4_VEKTOR equ 0FF18H +INT5_VEKTOR equ 0FF1BH +INT6_VEKTOR equ 0FF1EH +DATA_START equ 03CH +X_DATA_START equ 010H +I_DATA_START equ 080H +BIT_DATA_START equ 0BH +CODE_START equ 01000H +; Ende Includefile fr Assembler-Programm diff --git a/tests/t_mic51/t_mic51.asm b/tests/t_mic51/t_mic51.asm new file mode 100644 index 0000000..ce29ab1 --- /dev/null +++ b/tests/t_mic51/t_mic51.asm @@ -0,0 +1,2197 @@ +;Program: TEACH-IN EINHEIT +; +;Autor: Laurent Savary +; +;Datum: 9.5.94 +; +;letze Aenderung: 23.6.94 +; +; +;Dateiname: TEACHIN.ASM +; +;------------------------------------------------------------------------------ + +Init_Vektor macro Vektor,Routine + +; mov Vektor+0,#(Routine/256) ;der Interruptvektor wird +; mov Vektor+1,#(Routine#256) ;ins interne RAM geladen + + push acc + push dph + push dpl + mov dptr,#Vektor + mov a,#00000010b ; LJMP + movx @dptr,a + inc dptr + mov a,#(Routine/256) + movx @dptr,a + inc dptr + mov a,#(Routine#256) + movx @dptr,a + pop dpl + pop dph + pop acc + + endm + +DEC_DPTR MACRO + INC DPL + DJNZ DPL,DEC_DPTR1 + DEC DPH +DEC_DPTR1: DEC DPL + ENDM + + +INC_R0R1 MACRO + INC R0 + INC R0 + DJNZ R0,INC_R0R1_End + INC R1 +INC_R0R1_End: + ENDM + + +DEC_R0R1: MACRO + INC R0 + DJNZ R0,DEC_R0R1_End + DEC R1 +DEC_R0R1_End: DEC R0 + ENDM + +;--------------------------------------------------------------------- + +post_Message macro + push acc +SEND_NET1: LCALL READ_STATUS + JB ACC.1,SEND_NET1 + pop acc + LCALL SEND_MESSAGE + endm + +Take_Message macro + push acc +RECEIVE_NET1: LCALL READ_STATUS + JNB ACC.0,RECEIVE_NET1 + pop acc + LCALL READ_MESSAGE + endm + +;------------------------------------------------------------------------------ + + cpu 80515 + include stddef51.inc + include net_lcd.inc + include defint.inc + include defgequ.inc + include defmacro.inc + + USING 0 + +;------------------------ Konstanten ------------------------------------------ + +Ass_Keyboard_Only EQU False ; Wenn True, TI-Einheit lauft nur mit + ; der Tastatur (kein Tastenfeld) + +Last_Code EQU 0FFFFh ; Endeadressen +Last_Bit_Data EQU 07Fh ; der Speicher- +Last_Data EQU 07Fh ; bereiche +Last_IData EQU 0FFh ; bestimmen +Last_XData EQU 0FFFFh + +Kb_Max_Length EQU 40 ; Hoechstlaenge der anzuzeigenden Strings +TI_Sample_Valid_Time EQU 30 ; Gueltige Druckdauer in ms + +ASCII_Space EQU 32 ; +ASCII_Left EQU 19 ; +ASCII_Right EQU 4 ; +ASCII_Up EQU 5 ; +ASCII_Down EQU 24 ; ASCII-Code fuer die +ASCII_CR EQU 13 ; Tastatur +ASCII_Esc EQU 27 ; +ASCII_DEL EQU 127 ; +ASCII_BkSpc EQU 8 ; +ASCII_LWord EQU 1 ; +ASCII_RWord EQU 6 ; +ASCII_Search EQU 12 ; + +KSS_Off EQU 0 +KSS_Mod EQU 1 +KSS_Mod_Top EQU 2 +KSS_Mod_Bot EQU 3 +KSS_Msg EQU 4 +KSS_Msg_Top EQU 5 +KSS_Msg_Bot EQU 6 +KSS_Inc_Mod EQU 7 +KSS_No_Choice EQU 8 + +R0_Bk1 EQU 08h +R1_Bk1 EQU 09h +R2_Bk1 EQU 0Ah +R3_Bk1 EQU 0Bh +R4_Bk1 EQU 0Ch +R5_Bk1 EQU 0Dh +R6_Bk1 EQU 0Eh +R7_Bk1 EQU 0Fh + +;------------------------------------------------------------------------------ + + segment data + org Data_Start + +Save_P4 DB ? ; +Save_P5 DB ? ; +Old_P4 DB ? ; +Old_P5 DB ? ; +Temp_P4 DB ? ; benoetigte Variablen fuer +Temp_P5 DB ? ; Teach_In_Sampler +TI_On_P4 DB ? ; +TI_Off_P4 DB ? ; +TI_On_P5 DB ? ; +TI_Off_P5 DB ? ; +TI_Sample_Counter DB ? ; + +Text_Dec_Status DB ? +Kb_Char_Buffer DB ? +Kb_Str_Pointer DB ? +Kb_Cursor DB ? +ASCII_Low_Byte DB ? +ASCII_High_Byte DB ? +Rcv_Msg_Length DB ? +My_Slave_Adr DB ? ; Physikalische Adresse dieses Moduls + +Kb_Search_Status DB ? ; +Kb_Search_DPL DB ? ; +Kb_Search_DPH DB ? ; Benoetigte Variablen fuer +KS_Actual_Word DB ? ; Keyboard Search +KS_Actual_Module DB ? ; +KS_Cursor DB ? ; + +Stat_Code DB ? ; +Stat_Address DB ? ; +Stat_Num_Param DB ? ; Benoetigte Variablen fuer +Stat_Picture DB ? ; Text_Decoder +Stat_Module DB ? ; +Stat_Length DB ? ; + + if $ > Last_Data + then fatal "Data-Bereichgrenze ueberschritten" + endif + + +;------------------------------------------------------------------------------ + + segment xdata + org X_Data_Start + +Kb_Str_Buffer DB Kb_Max_Length dup (?) ; Text Buffer (fuer die Tastatur) +Token_Str DB Kb_Max_Length dup (?) ; Ergebnis von Get_Token +Net_Rcv_Str DB Kb_Max_Length dup (?) ; Empfangene Message vom Teach-In Modul + + if $ > Last_XData + then fatal "XData-Bereichgrenze ueberschritten" + endif + +;------------------------------------------------------------------------------ + + segment idata + org I_Data_Start + +Msg_Registers DB 8 dup (?) ; Register-Buffer fur die zu sendenden Messages + + if $ > Last_IData + then fatal "IData-Bereichgrenze ueberschritten" + endif + + +;------------------------------------------------------------------------------ + + segment bitdata + org Bit_Data_Start + +Kb_Str_Ready DB ? ; -> Text_Decoder +Kb_Char_Ready DB ? ; -> Keyb_Controller +TI_Sample_Chg_Flg DB ? ; -> TeachIn_Decoder +TD_Status_Ready DB ? ; -> LCD_Controller +TD_Send_Ready DB ? ; -> Send_Manager +Receive_Ready DB ? ; -> Receive_Manager +TD_Next_Flg DB ? ; -> Kb_Controller +KS_Status_Ready DB ? ; -> LCD_Controller +KS_Active_Flg DB ? ; -> KB_Search_Up / _Down +Kb_Dsp_Ready DB ? ; -> LCD_Controller +Ext_Dsp_Ready DB ? ; -> LCD_Controller +System_Error DB ? +Sys_Robot_Mode DB ? +Sys_Keyboard_Mode DB ? +TID_Done_Flg DB ? ; -> TeachIn_Sampler + + if $ > Last_Bit_Data + then fatal "Bit_Data-Bereichgrenze ueberschritten" + endif + + +;------------------------------------------------------------------------------ + + segment code + org Code_Start + +;====================== H A U P T P R O G R A M M ============================= + + segment code + +Main_Prog: CLR EAL ;alle Interrupts sperren + MOV SP,#Stack-1 ;Stackpointer setzen + + LCALL Init_Data + LCALL Init_IData + LCALL Init_BitData + LCALL Init_XData + LCALL Init_Timer + LCALL Init_Mode +Main_Error: JB System_Error,Main_Error + + LCALL Init_Net + LCALL LCD_Clear + MOV A,#1 + LCALL LCD_Curser_OnOff + LCALL Init_Int + SETB EAL + + CLR TESTBIT + CLR MSG + MOV Sp_MSG_Buffer,#0 + CLR Sp_MSG + LCALL INIT_TEACH + LCALL INIT_RUN + LCALL RESET_TEACH + LCALL INIT_FRS + +Main_Loop: LCALL Main_Manager + LCALL Main_Event_Loop + SJMP Main_Loop + + +;------------------------------------------------------------------------------ + +Adr_Table: Create_IncTab ModulNetAdr, "defModul.inc" +Module_Table: Create_IncOffsTab ModulStr, "defModul.inc" +Symbol_Table: Create_IncOffsTab ParamStr, "defParam.inc" +Stat_Table: Create_IncOffsTab MsgStr, "defMsg.inc" + +KOn_P4_Rob: Create_IncKeyTab On, P4, TeachRob, "defKey.inc" +KOff_P4_Rob: Create_IncKeyTab Off, P4, TeachRob, "defKey.inc" +KOn_P5_Rob: Create_IncKeyTab On, P5, TeachRob, "defKey.inc" +KOff_P5_Rob: Create_IncKeyTab Off, P5, TeachRob, "defKey.inc" +KOn_P4_Frs: Create_IncKeyTab On, P4, TeachFrs, "defKey.inc" +KOff_P4_Frs: Create_IncKeyTab Off, P4, TeachFrs, "defKey.inc" +KOn_P5_Frs: Create_IncKeyTab On, P5, TeachFrs, "defKey.inc" +KOff_P5_Frs: Create_IncKeyTab Off, P5, TeachFrs, "defKey.inc" + +;-------------------------------------------------------------------------- + include t_mod1.asm ; +;------------------------------------------------------------------------------ + +Main_Manager: JNB Kb_Char_Ready,MM_Txt_Dec + LCALL Keyb_Controller + +MM_Txt_Dec: JNB Kb_Str_Ready,MM_TI_Dec + LCALL Text_Decoder + +MM_TI_Dec: JNB TI_Sample_Chg_Flg,MM_Send_Mng + LCALL TeachIn_Decoder + +MM_Send_Mng: JNB TD_Send_Ready,MM_Receive_Mng + LCALL Send_Manager + +MM_Receive_Mng: JNB Receive_Ready,MM_LCD_Ctrl + LCALL Receive_Manager + +MM_LCD_Ctrl: JB Ext_Dsp_Ready,MM_LCD_Ctrl2 + JB Kb_Dsp_Ready,MM_LCD_Ctrl2 + JB TD_Status_Ready,MM_LCD_Ctrl2 + JB KS_Status_Ready,MM_LCD_Ctrl2 + SJMP MM_End +MM_LCD_Ctrl2: LCALL LCD_Controller + +MM_End: RET + +;-------------------------------------------------------------------------- + +Init_Data: + MOV Save_P4,#0FFh + MOV Save_P5,#0FFh + MOV Old_P4,#0FFh + MOV Old_P5,#0FFh + MOV Temp_P4,#0FFh + MOV Temp_P5,#0FFh + MOV TI_On_P4,#00 + MOV TI_Off_P4,#00 + MOV TI_On_P5,#00 + MOV TI_Off_P5,#00 + MOV TI_Sample_Counter,#00 + MOV Rcv_Msg_Length,#00 + MOV My_Slave_Adr,#00 + + MOV Text_Dec_Status,#00 + MOV Kb_Char_Buffer,#00 + MOV Kb_Str_Pointer,#00 + MOV Kb_Cursor,#00 + MOV ASCII_Low_Byte,#00 + MOV ASCII_High_Byte,#00 + + MOV Kb_Search_DPL,#00 + MOV Kb_Search_DPH,#00 + MOV KS_Actual_Word,#00 + MOV KS_Actual_Module,#00 + MOV KS_Cursor,#00 + MOV Kb_Search_Status,#00 + + MOV Stat_Code,#00 + MOV Stat_Address,#00 + MOV Stat_Num_Param,#00 + MOV Stat_Picture,#00 + MOV Stat_Module,#00 + MOV Stat_Length,#00 + RET + + +Init_IData: LCALL Clr_Msg_Buffer + RET + + +Init_XData: PUSH DPL + PUSH DPH + PUSH Acc + + MOV DPTR,#Kb_Str_Buffer + MOV A,#ASCII_Space + LCALL Clear_Str + MOV DPTR,#Token_Str + MOV A,#StringEnde + LCALL Clear_Str + + POP Acc + POP DPH + POP DPL + RET + + +Init_BitData: CLR Kb_Str_Ready + CLR Kb_Char_Ready + CLR TI_Sample_Chg_Flg + CLR TD_Status_Ready + CLR TD_Send_Ready + CLR Receive_Ready + SETB TD_Next_Flg + CLR KS_Active_Flg + CLR KS_Status_Ready + CLR Kb_Dsp_Ready + CLR Ext_Dsp_Ready + CLR System_Error + CLR Sys_Robot_Mode + CLR Sys_Keyboard_Mode + CLR TID_Done_Flg + RET + +;-------------------------------------------------------------------------- +; Routine : Init_Mode +; Parameter : - +; Rueckgabeparameter : Sys_Robot_Mode, Sys_Keyboard_Mode,System_Error +; +; entscheidet, ob das Programm im TI-Roboter, TI-Fraese oder TI-Tastatur +; laufen muss. (SRM /SKM) (/SRM /SKM) (SKM) + + +Init_Mode: PUSH PSW + PUSH DPL + PUSH DPH + + CLR System_Error + + if Ass_Keyboard_Only + SJMP IM_Keyboard + elseif + CLR Sys_Robot_Mode + CLR Sys_Keyboard_Mode + LCALL LCD_Clear + MOV DPTR,#Screen_Title + LCALL LCD_Write_String + JNB P3.5,IM_Robot + JB P3.4,IM_Error + MOV DPTR,#Screen_Drill + SJMP IM_End + endif + +IM_Robot: JNB P3.4,IM_Keyboard + SETB Sys_Robot_Mode + MOV DPTR,#Screen_Robot + SJMP IM_End + +IM_Keyboard: SETB Sys_Keyboard_Mode + MOV DPTR,#Screen_Key + SJMP IM_End + +IM_Error: SETB System_Error + MOV DPTR,#Screen_Error + +IM_End: LCALL LCD_Write_String + LCALL Wait_2s + + POP DPH + POP DPL + POP PSW + RET + +Screen_Title: DB "**** TEACH-IN UNIT v1.0 ****",00 +Screen_Drill: DB " Drill mode",00 +Screen_Robot: DB " Robot mode",00 +Screen_Key: DB " Keyboard mode",00 +Screen_Error: DB " ERROR : Incorrect micro-controller",00 + +;-------------------------------------------------------------------------- + +Init_Int: Init_Vektor INT0_VEKTOR,Keyb_Sampler + Init_Interrupt INT0_VEKTOR,Falling_Edge,Param_On + Init_Vektor ICT0_VEKTOR,TeachIn_Sampler + Init_Interrupt ICT0_VEKTOR,Nope,Param_On + RET + +;-------------------------------------------------------------------------- + + +Init_Net: PUSH Acc + PUSH DPL + PUSH DPH + + MOV DPTR,#MESSAGE_INTERRUPT ;Receive_Sampler + LCALL Set_CallBack_Adress + MOV DPTR,#Adr_Table + JB Sys_Keyboard_Mode,Init_Net_Key + JNB Sys_Robot_Mode,Init_Net_Frs + +Init_Net_Rob: MOV A,#TeachRob + SJMP Init_Net_End + +Init_Net_Frs: MOV A,#TeachFrs + SJMP Init_Net_End + +Init_Net_Key: MOV A,#TeachKey + +Init_Net_End: MOVC A,@A+DPTR + MOV My_Slave_Adr,A + LCALL Set_My_Adress + + POP DPH + POP DPL + POP Acc + RET + +;-------------------------------------------------------------------------- + +Init_Timer: MOV TH0,#00 + MOV TL0,#00 + MOV TMOD,#00110001b ; T1 : Off, T0 : 16 Bit Timer + SETB TR0 ; T0 einschalten + RET + +;-------------------------------------------------------------------------- +; Routine : LCD_Controller +; Parameter : Ext_Dsp_Ready -> DPTR +; TD_Status_Ready -> Text_Dec_Status +; KS_Status_Ready -> Kb_Search_Status +; Rueckgabeparameter : - +; wenn Ext_Dsp_Ready gesetzt wird, zeigt den mit DPTR gezeigten String +; auf den Bildschirm an. +; wenn TD_Status_Ready (bzw KS_Status_Ready) gesetzt wird, zeigt die +; entsprechende Meldung von Text_Dec_Status (bzw Kb_Search_Status) +; + +LCD_Controller: PUSH PSW + PUSH Acc + PUSH AR0 + PUSH AR1 + PUSH DPL + PUSH DPH + LCALL LCD_Home + + JNB Ext_Dsp_Ready,LCD_Str_Buffer + CLR Ext_Dsp_Ready + MOV A,#40h + LCALL LCD_Set_DD_RAM_Address + MOV R1,#Kb_Max_Length + +LCD_Ext_Loop: MOVX A,@DPTR + LCALL LCD_Write_Char + INC DPTR + DJNZ R1,LCD_Ext_Loop + LCALL LCD_Home + +LCD_Str_Buffer: JNB Kb_Dsp_Ready,LCD_TD_Status + CLR Kb_Dsp_Ready + MOV DPTR,#Kb_Str_Buffer + MOV R1,#Kb_Max_Length + +LCD_Str_Loop: MOVX A,@DPTR + LCALL LCD_Write_Char + INC DPTR + DJNZ R1,LCD_Str_Loop + +LCD_TD_Status: JNB TD_Status_Ready,LCD_KS_Status + CLR TD_Status_Ready + + MOV A,#40 + LCALL LCD_Set_DD_RAM_Address + MOV DPTR,#LCD_TD_Table + MOV R0,Text_Dec_Status + CJNE R0,#00,LCD_TD_Loop + SJMP LCD_TD_Cont + +LCD_TD_Loop: MOV A,#41 + ADD A,DPL + MOV DPL,A + MOV A,DPH + ADDC A,#00 + MOV DPH,A + DJNZ R0,LCD_TD_Loop + +LCD_TD_Cont: LCALL LCD_Write_String + +LCD_KS_Status: JNB KS_Status_Ready,LCD_End + CLR KS_Status_Ready + + MOV A,#40 + LCALL LCD_Set_DD_RAM_Address + MOV DPTR,#LCD_KS_Table + MOV R0,Kb_Search_Status + CJNE R0,#00,LCD_KS_Loop + SJMP LCD_KS_Cont + +LCD_KS_Loop: MOV A,#41 + ADD A,DPL + MOV DPL,A + MOV A,DPH + ADDC A,#00 + MOV DPH,A + DJNZ R0,LCD_KS_Loop + +LCD_KS_Cont: LCALL LCD_Write_String + +LCD_End: MOV A,Kb_Cursor + LCALL LCD_Set_DD_RAM_Address + + POP DPH + POP DPL + POP AR1 + POP AR0 + POP Acc + POP PSW + RET + +LCD_TD_Table: DB "Edit OK : Sending ",00 + DB "Edit ERROR : message waited ",00 + DB "Edit ERROR : incorrect message ",00 + DB "Edit ERROR : more parameters waited ",00 + DB "Edit ERROR : parameter range ",00 + DB "Edit ERROR : module name waited ",00 + DB "Edit ERROR : incorrect module name ",00 + DB "Edit WARNING : too many parameters ",00 + +LCD_KS_Table: DB "Text editing ",00 + DB "Search : Choose a module ",00 + DB "Search : Choose a module, reached TOP ",00 + DB "Search : Choose a module, reached BOTT. ",00 + DB "Search : Choose a message ",00 + DB "Search : Choose a message, reached TOP ",00 + DB "Search : Choose a message, reached BOTT.",00 + DB "Search : Incorrect module ",00 + DB "Search : No choice available ",00 + +;-------------------------------------------------------------------------- + +Keyb_Sampler: + MOV Kb_Char_Buffer,P1 + SETB Kb_Char_Ready + RETI + +;-------------------------------------------------------------------------- +; Routine : Keyb_Controller +; Parameter : Kb_Char_Ready ; (Buchstabe im Buffer) +; Kb_Char_Buffer ; (zu verarbeitender Buchstabe) +; Kb_Cursor ; (Cursorposition auf LCD) +; KS_Active_Flg ; (Keyb. Search Modus) +; Kb_Str_Buffer ; (Text Buffer f. Tastatur) +; TD_Next_Flg ; Text_Decoder ist fertig +; Rueckgabeparameter : Kb_Cursor +; KS_Active_Flg +; Kb_Str_Buffer +; Kb_Str_Ready ; (->Text_Decoder : String verarbeiten) +; Kb_Search_Status ; (Keyb. Search Zustand) +; KS_Status_Ready ; (-> LCD : Zustand anzeigen) +; +; Verwaltet Kb_Str_Buffer nach der Tastatur-Eingaben + + +Keyb_Controller: + PUSH Acc + PUSH PSW + PUSH DPL + PUSH DPH + + CLR Kb_Char_Ready + MOV A,Kb_Char_Buffer + + JNB TD_Next_Flg,Kb_Ctrl_UP + CLR TD_Next_Flg +Kb_Ctrl_Test1: CJNE A,#ASCII_Left,Kb_Ctrl_Test2 + SJMP Kb_Ctrl_Old +Kb_Ctrl_Test2: CJNE A,#ASCII_Right,Kb_Ctrl_Test3 + SJMP Kb_Ctrl_Old +Kb_Ctrl_Test3: CJNE A,#ASCII_BkSpc,Kb_Ctrl_Test4 + SJMP Kb_Ctrl_Old +Kb_Ctrl_Test4: CJNE A,#ASCII_CR,Kb_Ctrl_New + + +Kb_Ctrl_Old: MOV Kb_Search_Status,#KSS_Off + SETB KS_Status_Ready + LJMP Kb_Ctrl_Up + +Kb_Ctrl_New: PUSH Acc + MOV A,#ASCII_Space + MOV DPTR,#Kb_Str_Buffer + LCALL Clear_Str + MOV Kb_Cursor,#00 + MOV Kb_Search_Status,#KSS_Off + SETB KS_Status_Ready + POP Acc + +Kb_Ctrl_UP: CJNE A,#ASCII_Up,Kb_Ctrl_DOWN + LCALL Kb_Search_Up + LJMP Kb_Ctrl_End + +Kb_Ctrl_DOWN: CJNE A,#ASCII_Down,Kb_Ctrl_RET + LCALL Kb_Search_Down + LJMP Kb_Ctrl_End + +Kb_Ctrl_RET: CLR KS_Active_Flg + CJNE A,#ASCII_CR,Kb_Ctrl_LEFT + SETB Kb_Str_Ready + LJMP Kb_Ctrl_End + +Kb_Ctrl_LEFT: CJNE A,#ASCII_Left,Kb_Ctrl_RIGHT + LCALL Exe_LEFT + LJMP Kb_Ctrl_End + +Kb_Ctrl_RIGHT: CJNE A,#ASCII_Right,Kb_Ctrl_DEL + LCALL Exe_RIGHT + LJMP Kb_Ctrl_End + +Kb_Ctrl_DEL: CJNE A,#ASCII_Del,Kb_Ctrl_BKSPC + LCALL Exe_DEL + LJMP Kb_Ctrl_End + +Kb_Ctrl_BKSPC: CJNE A,#ASCII_BkSpc,Kb_Ctrl_ESC + LCALL Exe_LEFT + LCALL Exe_DEL + LJMP Kb_Ctrl_End + +Kb_Ctrl_ESC: CJNE A,#ASCII_Esc,Kb_Ctrl_Alpha + MOV DPTR,#Kb_Str_Buffer + MOV A,#ASCII_Space + LCALL Clear_Str + MOV Kb_Cursor,#00 + LJMP Kb_Ctrl_End + +Kb_Ctrl_Alpha: LCALL Exe_Set_Actual_Letter + MOV A,Kb_Char_Buffer + MOVX @DPTR,A + LCALL Exe_RIGHT + +Kb_Ctrl_End: SETB Kb_Dsp_Ready + POP DPH + POP DPL + POP PSW + POP Acc + RET + +;-------------------------------------------------------------------------- + +Exe_Set_Actual_Letter: ; laedt in DPTR die externale Adresse + PUSH Acc ; des vom Kb_Cursor gezeigten Zeichens + PUSH PSW + MOV A,Kb_Cursor + MOV DPTR,#Kb_Str_Buffer + ADD A,DPL + MOV DPL,A + JNC ESAL_End + INC DPH +ESAL_End: POP PSW + POP Acc + RET + +Exe_LEFT: PUSH AR1 ; dekr. Kb_Cursor + DEC Kb_Cursor + MOV R1,Kb_Cursor + CJNE R1,#0FFh,Exe_LEFT_End + MOV Kb_Cursor,#00 +Exe_LEFT_End: POP AR1 + RET + +Exe_RIGHT: PUSH Acc ; inkr. Kb_Cursor + PUSH PSW + INC Kb_Cursor + CLR C + MOV A,#Kb_Max_Length-1 + SUBB A,Kb_Cursor + JNC Exe_RIGHT_End + MOV Kb_Cursor,#Kb_Max_Length-1 +Exe_RIGHT_End: POP PSW + POP Acc + RET + +Exe_DEL: PUSH Acc ; loescht aktuelles Zeichen + LCALL Exe_Set_Actual_Letter + MOV A,#ASCII_Space + MOVX @DPTR,A + POP Acc + RET + +;-------------------------------------------------------------------------- +; Routine : Kb_Init_Search +; Parameter : Kb_Str_Buffer +; Kb_Cursor +; Rueckgabeparameter : KS_Status_Ready +; Kb_Search_Status +; KS_Active_Flg +; KS_Actual_Module +; Kb_Search_DPL +; Kb_Search_DPH +; KS_Cursor +; +; Sucht, auf welchem Wort der Cursor sich befindet und zeigt das erste ent- +; sprechende Element aus der Search-Menu-Tabelle (zB : wenn Cursor auf Message, +; sucht die erste Message fuer das schon eingetragene Modul). + + +Kb_Init_Search: PUSH Acc + PUSH B + PUSH PSW + PUSH DPL + PUSH DPH + + LCALL Kb_Valid_Word + MOV A,KS_Actual_Word + CJNE A,#1,KIS_Msg ; Cursor auf 1. Wort -> Modul + + MOV Kb_Search_DPL,#(Module_Table # 256) + MOV Kb_Search_DPH,#(Module_Table / 256) + LCALL Search_Next_Module + JC KIS_No_Choice ; springt wenn noch kein Modul in der Tabelle + MOV DPTR,#Kb_Str_Buffer ; + MOV A,#ASCII_Space ; loescht Kb_Str_Buffer + LCALL Clear_Str ; + MOV Kb_Cursor,#00 ; + MOV DPL,Kb_Search_DPL + MOV DPH,Kb_Search_DPH + INC DPTR + INC DPTR + MOV Kb_Search_Status,#KSS_Mod + SJMP KIS_Found + +KIS_Msg: CJNE A,#2,KIS_No_Choice + MOV Kb_Str_Pointer,#00 ; Cursor auf 2. Wort -> Message + LCALL Get_Token + LCALL Is_Token_Module + JNC KIS_Mod_Corr + MOV Kb_Search_Status,#KSS_Inc_Mod ; erstes Wort kein Korrektes Modul + SJMP KIS_End + +KIS_Mod_Corr: MOV Kb_Cursor,Kb_Str_Pointer + LCALL Exe_Right ; ein Leerzeichen nach dem 1. Wort lassen + MOV KS_Actual_Module,A ; Modulnummer abspeichern + MOV Kb_Search_DPL,#(Stat_Table # 256) + MOV Kb_Search_DPH,#(Stat_Table / 256) + LCALL Search_Next_Msg + JC KIS_No_Choice ; existiert Message fuer dieses Modul ? + MOV DPTR,#Kb_Str_Buffer ; Ja -> Mess. in Textbuffer kopieren + MOV A,#ASCII_Space + MOV B,Kb_Cursor + LCALL Clear_Pos_Str ; Kb_Str_Buffer ab der Cursorposition loeschen + MOV DPL,Kb_Search_DPL + MOV DPH,Kb_Search_DPH + INC DPTR + INC DPTR + INC DPTR + MOV Kb_Search_Status,#KSS_Msg + SJMP KIS_Found + +KIS_No_Choice: MOV Kb_Search_Status,#KSS_No_Choice ; Nein -> Fehlermeldung + SJMP KIS_End + +KIS_Found: MOV KS_Cursor,Kb_Cursor ; kopiert das gefundene Element + LCALL Copy_Pos_Buffer ; in Kb_Str_Buffer ab KS_Cursor + SETB KS_Active_Flg ; + +KIS_End: SETB KS_Status_Ready + POP DPH + POP DPL + POP PSW + POP B + POP Acc + RET + +;-------------------------------------------------------------------------- +; Routine : Kb_Valid_Word +; Parameter : Kb_Str_Buffer +; Kb_Cursor +; Rueckgabeparameter : KS_Actual_Word +; +; Sucht auf welchem Wort der Cursor sich befindet + + +Kb_Valid_Word: PUSH Acc + PUSH PSW + PUSH DPL + PUSH DPH + + MOV DPTR,#Kb_Str_Buffer + MOV Kb_Str_Pointer,#00 + MOV KS_Actual_Word,#00 + +KVW_Loop: LCALL Get_Token + INC KS_Actual_Word + CLR C + MOV A,Kb_Str_Pointer + SUBB A,Kb_Cursor ; wenn Kb_Str_Pointer > Kb_Cursor + JC KVW_Loop ; hat man das richtige Wort gefunden + + POP DPH + POP DPL + POP PSW + POP Acc + RET + +;-------------------------------------------------------------------------- +; Routine : Kb_Search_Up +; Parameter : KS_Active_Flg +; Kb_Search_DPL +; Kb_Search_DPH +; KS_Cursor +; Rueckgabeparameter : KS_Active_Flg +; Kb_Search_DPL +; Kb_Search_DPH +; +; Legt fest, ob die Search-Routinen initialisiert werden muessen, ob das vorhergehende +; Modul, oder Message, abgeholt werden muss. + + +Kb_Search_Up: PUSH Acc + PUSH PSW + PUSH DPL + PUSH DPH + + JB KS_Active_Flg,KSU_Choose ; Schon im Search-Modus ? + LCALL Kb_Init_Search ; Nein -> Initialisierung + SJMP KSU_End + +KSU_Choose: MOV A,KS_Actual_Word ; Ja -> auf welchem Wort liegt der Cursor ? + CJNE A,#1,KSU_Msg + LCALL Search_Prev_Module ; 1. Wort -> sucht Modul + JC KSU_Mod_Top ; gefunden ? + MOV Kb_Search_Status,#KSS_Mod ; Ja -> DPTR retten + MOV DPL,Kb_Search_DPL + MOV DPH,Kb_Search_DPH + INC DPTR + INC DPTR + SJMP KSU_Show + +KSU_Mod_Top: MOV Kb_Search_Status,#KSS_Mod_Top ; Nein -> Top of list + SJMP KSU_End + +KSU_Msg: LCALL Search_Prev_Msg ; 2. Wort -> sucht Message + JC KSU_Msg_Top ; gefunden ? + MOV Kb_Search_Status,#KSS_Msg ; Ja -> DPTR retten + MOV DPL,Kb_Search_DPL + MOV DPH,Kb_Search_DPH + INC DPTR + INC DPTR + INC DPTR + SJMP KSU_Show + +KSU_Msg_Top: MOV Kb_Search_Status,#KSS_Msg_Top ; Nein -> Top of list + SJMP KSU_End + +KSU_Show: MOV Kb_Cursor,KS_Cursor ; gefundenes Wort in Textbuffer + PUSH DPL ; kopieren + PUSH DPH + MOV DPTR,#Kb_Str_Buffer + MOV A,#ASCII_Space + MOV B,Kb_Cursor + LCALL Clear_Pos_Str + POP DPH + POP DPL + LCALL Copy_Pos_Buffer + +KSU_End: SETB KS_Status_Ready + POP DPH + POP DPL + POP PSW + POP Acc + RET + +;-------------------------------------------------------------------------- +; Routine : Kb_Search_Down +; Parameter : KS_Active_Flg +; Kb_Search_DPL +; Kb_Search_DPH +; KS_Cursor +; Rueckgabeparameter : KS_Active_Flg +; Kb_Search_DPL +; Kb_Search_DPH +; +; Legt fest, ob die Search-Routinen initialisiert werden muessen, ob das naechste +; Modul, oder Message, abgeholt werden muss. + + +Kb_Search_Down: PUSH Acc + PUSH PSW + PUSH DPL + PUSH DPH + + JB KS_Active_Flg,KSD_Choose ; schon im Search Modus ? + LCALL Kb_Init_Search ; Nein -> Initialisierung + SJMP KSD_End + +KSD_Choose: MOV A,KS_Actual_Word ; Ja -> welches Wort ? + CJNE A,#1,KSD_Msg + LCALL Search_Next_Module ; 1. Wort -> sucht naechstes Modul + JC KSD_Mod_Bot ; gefunden ? + MOV Kb_Search_Status,#KSS_Mod ; Ja -> DPTR retten + MOV DPL,Kb_Search_DPL + MOV DPH,Kb_Search_DPH + INC DPTR + INC DPTR + SJMP KSD_Show + +KSD_Mod_Bot: MOV Kb_Search_Status,#KSS_Mod_Bot ; Nein -> bottom of list + SJMP KSD_End + +KSD_Msg: LCALL Search_Next_Msg ; 2. Wort -> sucht naechste Message + JC KSD_Msg_Bot ; gefunden ? + MOV Kb_Search_Status,#KSS_Msg ; Ja -> DPTR retten + MOV DPL,Kb_Search_DPL + MOV DPH,Kb_Search_DPH + INC DPTR + INC DPTR + INC DPTR + SJMP KSD_Show + +KSD_Msg_Bot: MOV Kb_Search_Status,#KSS_Msg_Bot ; Nein -> bottom of list + SJMP KSD_End + +KSD_Show: MOV Kb_Cursor,KS_Cursor ; gefundenes Wort in Textbuffer + PUSH DPL ; kopieren + PUSH DPH + MOV DPTR,#Kb_Str_Buffer + MOV A,#ASCII_Space + MOV B,Kb_Cursor + LCALL Clear_Pos_Str + POP DPH + POP DPL + LCALL Copy_Pos_Buffer + +KSD_End: SETB KS_Status_Ready + POP DPH + POP DPL + POP PSW + POP Acc + RET + +;-------------------------------------------------------------------------- +; Routine : Search_Next_Module +; Parameter : Kb_Search_DPL +; Kb_Search_DPH +; Rueckgabeparameter : C (gesetzt -> nicht gefunden) +; Kb_Search_DPL +; Kb_Search_DPH +; +; Sucht naechstes Modul ab aktueller Position in der Tabelle (durch KB_Search_DPL +; (DPH) gespeichert) + + +Search_Next_Module: + PUSH Acc + PUSH DPL + PUSH DPH + + MOV DPL,Kb_Search_DPL ; aktuelle Pos. in DPTR laden + MOV DPH,Kb_Search_DPH + MOV A,#1 + MOVC A,@A+DPTR + ADD A,DPL ; DPTR mit Offset addieren + MOV DPL,A + JNC SNMod_Cont + INC DPH +SNMod_Cont: CLR C + CLR A + MOVC A,@A+DPTR + XRL A,#TableEnd + JZ SNMod_End ; Ende der Tabelle ? + MOV Kb_Search_DPL,DPL ; Nein -> DPTR retten + MOV Kb_Search_DPH,DPH + CPL C + +SNMod_End: CPL C ; Ja -> nicht gefunden + POP DPH + POP DPL + POP Acc + RET + +;-------------------------------------------------------------------------- +; Routine : Search_Prev_Module +; Parameter : Kb_Search_DPL +; Kb_Search_DPH +; Rueckgabeparameter : C (gesetzt -> nicht gefunden) +; Kb_Search_DPL +; Kb_Search_DPH +; +; Sucht vorhergehendes Modul ab aktueller Position in der Tabelle (durch KB_Search_DPL +; (DPH) gespeichert). Analog zu Search_Next_Module + + +Search_Prev_Module: + PUSH Acc + PUSH AR1 + PUSH DPL + PUSH DPH + + MOV DPL,Kb_Search_DPL + MOV DPH,Kb_Search_DPH + DEC_DPTR + CLR A + MOVC A,@A+DPTR + INC DPTR + CLR C + MOV R1,A + MOV A,DPL + SUBB A,R1 + MOV DPL,A + JNC SPMod_Cont + DEC DPH +SPMod_Cont: CLR C + CLR A + MOVC A,@A+DPTR + XRL A,#TableAnf + JZ SPMod_End + MOV Kb_Search_DPL,DPL + MOV Kb_Search_DPH,DPH + CPL C + +SPMod_End: CPL C + POP DPH + POP DPL + POP AR1 + POP Acc + RET + +;-------------------------------------------------------------------------- +; Routine : Search_Next_Msg +; Parameter : Kb_Search_DPL +; Kb_Search_DPH +; KS_Actual_Module +; Rueckgabeparameter : C (gesetzt -> nicht gefunden) +; Kb_Search_DPL +; Kb_Search_DPH +; +; Sucht naechste Message ab aktueller Position in der Tabelle (durch KB_Search_DPL +; (DPH) gespeichert), die KS_Actual_Module entspricht + + +Search_Next_Msg: + PUSH Acc + PUSH DPL + PUSH DPH + + MOV DPL,Kb_Search_DPL ; aktuelle Pos. in DPTR laden + MOV DPH,Kb_Search_DPH + +SNMsg_Loop: MOV A,#1 + MOVC A,@A+DPTR + ADD A,DPL ; DPTR und Offset addieren + MOV DPL,A + JNC SNMsg_Cont + INC DPH +SNMsg_Cont: CLR C + CLR A + MOVC A,@A+DPTR + CJNE A,#TableEnd,SNMsg_Mod ; Ende der Tabelle ? + SETB C ; Ja -> nicht gefunden + SJMP SNMsg_End +SNMsg_Mod: CJNE A,KS_Actual_Module,SNMsg_Loop ; Nein -> Modulnummer korrekt ? + ; Nein -> sucht weiter + MOV Kb_Search_DPL,DPL ; Ja -> DPTR retten + MOV Kb_Search_DPH,DPH + CLR C + +SNMsg_End: POP DPH + POP DPL + POP Acc + RET + +;-------------------------------------------------------------------------- +; Routine : Search_Prev_Msg +; Parameter : Kb_Search_DPL +; Kb_Search_DPH +; KS_Actual_Module +; Rueckgabeparameter : C (gesetzt -> nicht gefunden) +; Kb_Search_DPL +; Kb_Search_DPH +; +; Sucht vorhergehende Message ab aktueller Position in der Tabelle (durch KB_Search_DPL +; (DPH) gespeichert), die KS_Actual_Module entspricht. Analog zu Search_Next_Msg + + +Search_Prev_Msg: + PUSH Acc + PUSH DPL + PUSH DPH + PUSH AR1 + + MOV DPL,Kb_Search_DPL + MOV DPH,Kb_Search_DPH + +SPMsg_Loop: DEC_DPTR + CLR A + MOVC A,@A+DPTR + INC DPTR + CLR C + MOV R1,A + MOV A,DPL + SUBB A,R1 + MOV DPL,A + JNC SPMsg_Cont + DEC DPH +SPMsg_Cont: CLR C + CLR A + MOVC A,@A+DPTR + CJNE A,#TableAnf,SPMsg_Mod + SETB C + SJMP SPMsg_End +SPMsg_Mod: CJNE A,KS_Actual_Module,SPMsg_Loop + MOV Kb_Search_DPL,DPL + MOV Kb_Search_DPH,DPH + CLR C + +SPMsg_End: POP AR1 + POP DPH + POP DPL + POP Acc + RET + +;-------------------------------------------------------------------------- +; Routine : Text_Decoder +; Parameter : Kb_Str_Buffer +; Rueckgabeparameter : Msg_Registers +; Text_Dec_Status +; TD_Status_Ready +; TD_Send_Ready +; Stat_Module +; Stat_Num_Param +; Stat_Picture +; Stat_Length +; Stat_Code +; +; Interpretiert den im Kb_Str_Buffer liegenden Text und legt die entsprechenden +; Werte in Msg_Registers und Stat_ Variablen ab. Wenn korrekter Text, setzt das +; TD_Send_Ready-Flag (ready to send). + + +Text_Decoder: PUSH AR0 + PUSH AR1 + PUSH AR2 + PUSH Acc + PUSH PSW + PUSH DPL + PUSH DPH + + LCALL Clr_Msg_Buffer + MOV Stat_Length,#02 + + CLR Kb_Str_Ready + MOV Kb_Str_Pointer,#00 + LCALL Get_Token ; sucht 1. Wort + JNC TD_Module ; gefunden ? + MOV Text_Dec_Status,#5 ; Nein -> Fehler (fehlendes Modul) + LJMP TD_End + +TD_Module: LCALL Is_Token_Module ; Ja -> ist das Modul korrekt ? + JNC TD_Statement + MOV Text_Dec_Status,#6 ; Nein -> Fehler (inkorrektes Modul) + LJMP TD_End + +TD_Statement: MOV Stat_Module,A ; Ja -> Modulnummer abspeichern + LCALL Get_Token ; sucht 2. Wort + JNC TD_Stat_Cont ; gefunden ? + MOV Text_Dec_Status,#1 ; Nein -> Fehler (fehlende Message) + LJMP TD_End + +TD_Stat_Cont: MOV R0,#(Token_Str # 256) ; Ja -> sucht Message in der Tabelle + MOV R1,#(Token_Str / 256) + MOV DPTR,#Stat_Table + +TD_Stat_Loop: CLR A ; + MOVC A,@A+DPTR ; + CJNE A,#TableEnd,TD_Stat_Cont2 + MOV Text_Dec_Status,#2 ; nur die Messages der Tabelle, die + LJMP TD_End ; das aktuelle Modul entsprechen, muessen + ; betrachtet werden +TD_Stat_Cont2: XRL A,Stat_Module ; + JZ TD_Stat_Check ; + +TD_Stat_Next: MOV A,#01 ; + MOVC A,@A+DPTR ; + ADD A,DPL ; sucht naechste Message in der + MOV DPL,A ; Tabelle + JNC TD_Stat_Loop ; + INC DPH ; + SJMP TD_Stat_Loop ; + +TD_Stat_Check: INC DPTR + INC DPTR + CLR A + MOVC A,@A+DPTR + MOV Stat_Code,A + INC DPTR + + LCALL Compare_Str ; Text und Message in der Tabelle + JNC TD_Parameters ; vergleichen + DEC_DPTR + DEC_DPTR + DEC_DPTR + SJMP TD_Stat_Next ; nicht gleich -> next one ! + +TD_Parameters: LCALL Jump_Blank_Str ; gleich -> Parameter dekodieren + MOV R0,#Msg_Registers + MOV @R0,Stat_Module + + INC R0 + MOV @R0,Stat_Code + + INC DPTR + CLR A + MOVC A,@A+DPTR + MOV Stat_Num_Param,A + MOV R1,A + JZ TD_Send + + INC DPTR + CLR A + MOVC A,@A+DPTR + MOV Stat_Picture,A + INC R0 + +TD_Par_Loop: LCALL Get_Token + JNC TD_Par_Symbol + MOV Text_Dec_Status,#3 + LJMP TD_End + +TD_Par_Symbol: CLR C + LCALL Is_Token_Symbol + JC TD_Par_Digit + MOV ASCII_Low_Byte,A + MOV ASCII_High_Byte,#00 + SJMP TD_Par_Load + +TD_Par_Digit: CLR C + LCALL ASCII_To_Bin + JNC TD_Par_Load + MOV Text_Dec_Status,#4 + SJMP TD_End + +TD_Par_Load: MOV A,Stat_Picture + JB Acc.0,TD_Par_Single + MOV @R0,ASCII_High_Byte + MOV ASCII_High_Byte,#00 + INC R0 + INC Stat_Length + +TD_Par_Single: MOV R2,ASCII_High_Byte + CJNE R2,#00,TD_Par_Error + MOV @R0,ASCII_Low_Byte + INC R0 + INC Stat_Length + RR A + MOV Stat_Picture,A + DJNZ R1,TD_Par_Loop + +TD_Send: MOV Text_Dec_Status,#0 + SETB TD_Send_Ready + LCALL Get_Token + JC TD_End + MOV Text_Dec_Status,#7 + SJMP TD_End + +TD_Par_Error: MOV Text_Dec_Status,#4 + +TD_End: SETB TD_Status_Ready + SETB TD_Next_Flg + POP DPH + POP DPL + POP PSW + POP Acc + POP AR2 + POP AR1 + POP AR0 + RET + +;-------------------------------------------------------------------------- + +Get_Token: PUSH Acc + PUSH P2 + PUSH DPL + PUSH DPH + PUSH AR0 + PUSH AR1 + PUSH AR2 + + MOV DPTR,#Token_Str + CLR A + LCALL Clear_Str + MOV DPTR,#Kb_Str_Buffer + MOV A,#Kb_Max_Length ; + CLR C ; + SUBB A,Kb_Str_Pointer ; + JNZ GT_Cont ; R2 = Anzahl der noch + SETB C ; zuverarbeitenden + SJMP GT_End ; Buchstaben + ; +GT_Cont: MOV R2,A ; + MOV A,DPL + ADD A,Kb_Str_Pointer + MOV DPL,A + JNC GT_Blank_Loop + INC DPH + +GT_Blank_Loop: MOVX A,@DPTR + CJNE A,#ASCII_Space,GT_Text + INC DPTR + INC Kb_Str_Pointer + DJNZ R2,GT_Blank_Loop + SETB C + SJMP GT_End + +GT_Text: MOV R0,#(Token_Str # 256) + MOV R1,#(Token_Str / 256) + +GT_Text_Loop: MOVX A,@DPTR + CJNE A,#ASCII_Space,GT_Text_Add + CLR C + SJMP GT_End + +GT_Text_Add: LCALL UpCase + MOV P2,R1 + MOVX @R0,A + INC Kb_Str_Pointer + INC_R0R1 + INC DPTR + DJNZ R2,GT_Text_Loop + CLR C + +GT_End: POP AR2 + POP AR1 + POP AR0 + POP DPH + POP DPL + POP P2 + POP Acc + RET + +;-------------------------------------------------------------------------- + +Compare_Str: IRP Source,Acc,P2,DPL,DPH,AR0,AR1,AR2,AR3 + PUSH Source + ENDM + + CLR C + MOV R2,#Kb_Max_Length + + CLR A + MOVC A,@A+DPTR + CJNE A,#StringEnde,Comp_Loop + SJMP Comp_False + +Comp_Loop: MOV R3,A + MOV P2,R1 + MOVX A,@R0 + XRL A,R3 + JNZ Comp_False + MOV A,R3 + JZ Comp_End + INC DPTR + INC_R0R1 + CLR A + MOVC A,@A+DPTR + DJNZ R2,Comp_Loop + CPL C + +Comp_False: CPL C + +Comp_End: IRP Target,AR3,AR2,AR1,AR0,DPH,DPL,P2,Acc + POP Target + ENDM + RET + +;-------------------------------------------------------------------------- +TeachIn_Sampler: + PUSH Acc + PUSH PSW + PUSH AR1 + MOV TH0,#0FCh + + MOV Temp_P4,P4 + MOV Temp_P5,P5 + MOV A,Temp_P4 + XRL A,Save_P4 + JNZ TI_Smp_Edge + MOV A,Temp_P5 + XRL A,Save_P5 + JZ TI_Smp_Inc + +TI_Smp_Edge: MOV TI_Sample_Counter,#00 + MOV Save_P4,Temp_P4 + MOV Save_P5,Temp_P5 + SJMP TI_Smp_End + +TI_Smp_Inc: INC TI_Sample_Counter + MOV A,TI_Sample_Counter + CJNE A,#TI_Sample_Valid_Time,TI_Smp_End + MOV TI_Sample_Counter,#00 + MOV A,Old_P4 + XRL A,Save_P4 + JNZ TI_Smp_Change + MOV A,Old_P5 + XRL A,Save_P5 + JZ TI_Smp_End + +TI_Smp_Change: SETB TI_Sample_Chg_Flg + JNB TID_Done_Flg,TISC_No_Init + CLR TID_Done_Flg + MOV TI_On_P4,#00 + MOV TI_Off_P4,#00 + MOV TI_On_P5,#00 + MOV TI_Off_P5,#00 + +TISC_No_Init: MOV A,Old_P4 + XRL A,Save_P4 + MOV R1,A ; R1 = Save_P4 + MOV A,Save_P4 + CPL A + ANL A,R1 + ORL A,TI_On_P4 + MOV TI_On_P4,A + + MOV A,Save_P4 + ANL A,R1 + MOV TI_Off_P4,A + MOV A,Old_P5 + XRL A,Save_P5 + MOV R1,A + MOV A,Save_P5 + CPL A + ANL A,R1 + MOV TI_On_P5,A + MOV A,Save_P5 + ANL A,R1 + MOV TI_Off_P5,A + + MOV Old_P4,Save_P4 + MOV Old_P5,Save_P5 + +TI_Smp_End: POP AR1 + POP PSW + POP Acc + RETI + +;-------------------------------------------------------------------------- + +TeachIn_Decoder: + PUSH Acc + PUSH DPL + PUSH DPH + + CLR TI_Sample_Chg_Flg + MOV A,TI_On_P4 + JZ TID_Table2 + JB Sys_Robot_Mode,TID_T1_Rob + MOV DPTR,#KOn_P4_Frs + LCALL TID_Main + SJMP TID_Table2 + +TID_T1_Rob: MOV DPTR,#KOn_P4_Rob + LCALL TID_Main + +TID_Table2: MOV A,TI_Off_P4 + JZ TID_Table3 + JB Sys_Robot_Mode,TID_T2_Rob + MOV DPTR,#KOff_P4_Frs + LCALL TID_Main + SJMP TID_Table3 + +TID_T2_Rob: MOV DPTR,#KOff_P4_Rob + LCALL TID_Main + +TID_Table3: MOV A,TI_On_P5 + JZ TID_Table4 + JB Sys_Robot_Mode,TID_T3_Rob + MOV DPTR,#KOn_P5_Frs + LCALL TID_Main + SJMP TID_Table4 + +TID_T3_Rob: MOV DPTR,#KOn_P5_Rob + LCALL TID_Main + +TID_Table4: MOV A,TI_Off_P5 + JZ TID_End + JB Sys_Robot_Mode,TID_T4_Rob + MOV DPTR,#KOff_P5_Frs + LCALL TID_Main + SJMP TID_End + +TID_T4_Rob: MOV DPTR,#KOff_P5_Rob + LCALL TID_Main + +TID_End: SETB TID_Done_Flg + + POP DPH + POP DPL + POP Acc + RET + +;-------------------------------------------------------------------------- + +TID_Main: PUSH Acc + PUSH PSW + PUSH DPL + PUSH DPH + PUSH AR0 + PUSH AR1 + + MOV R1,#8 +TID_Main_Loop: CLR C + RRC A + JNC TID_Main_Next + + PUSH Acc + MOV A,#1 + MOVC A,@A+DPTR + MOV R0,A + POP Acc + CJNE R0,#StringEnde,TID_Main_Msg + SJMP TID_Main_Next + +TID_Main_Msg: PUSH DPL + PUSH DPH + PUSH Acc + MOV DPTR,#Kb_Str_Buffer + MOV A,#ASCII_Space + LCALL Clear_Str + POP Acc + POP DPH + POP DPL + + INC DPTR + MOV Kb_Cursor,#00 + LCALL Copy_Pos_Buffer + SETB Kb_Str_Ready + SETB Kb_Dsp_Ready + CLR KS_Active_Flg + DEC_DPTR + LCALL Main_Manager + +TID_Main_Next: PUSH Acc + CLR A + MOVC A,@A+DPTR + ADD A,DPL + MOV DPL,A + JNC TIDM_Next_Cont + INC DPH + +TIDM_Next_Cont: POP Acc + DJNZ R1,TID_Main_Loop + + POP AR1 + POP AR0 + POP DPH + POP DPL + POP PSW + POP Acc + RET + +;-------------------------------------------------------------------------- + +Send_Manager: PUSH Acc + PUSH B + PUSH DPL + PUSH DPH + PUSH AR0 + PUSH PSW + + CLR TD_Send_Ready + +Send_Mng_Load: MOV R0,#Msg_Registers + MOV R0_Bk1,@R0 + MOV A,@R0 ; logische Adresse + INC R0 + MOV R1_Bk1,@R0 + INC R0 + MOV R2_Bk1,@R0 + INC R0 + MOV R3_Bk1,@R0 + INC R0 + MOV R4_Bk1,@R0 + INC R0 + MOV R5_Bk1,@R0 + INC R0 + MOV R6_Bk1,@R0 + INC R0 + MOV R7_Bk1,@R0 + + MOV DPTR,#Adr_Table + MOVC A,@A+DPTR + MOV B,Stat_Length + SETB RS0 + CLR RS1 + + Post_Message + + POP PSW + POP AR0 + POP DPH + POP DPL + POP B + POP Acc + RET +;-------------------------------------------------------------------------- + +Receive_Sampler: + lcall MESSAGE_INTERRUPT +; SETB Receive_Ready + RET + + +Receive_Manager: + PUSH Acc + PUSH B + PUSH PSW + + CLR Receive_Ready + SETB RS0 + CLR RS1 + + Take_Message + CLR RS0 + MOV Rcv_Msg_Length,A + MOV DPTR,#Net_Rcv_Str + MOV A,#ASCII_Space + LCALL Clear_Str + + MOV A,R1_Bk1 + LCALL Bin_To_ASCII + MOVX @DPTR,A + INC DPTR + MOV A,B + MOVX @DPTR,A + INC DPTR + MOV A,#ASCII_Space + MOVX @DPTR,A + INC DPTR + + MOV A,R2_Bk1 + LCALL Bin_To_ASCII + MOVX @DPTR,A + INC DPTR + MOV A,B + MOVX @DPTR,A + INC DPTR + MOV A,#ASCII_Space + MOVX @DPTR,A + INC DPTR + + MOV A,R3_Bk1 + LCALL Bin_To_ASCII + MOVX @DPTR,A + INC DPTR + MOV A,B + MOVX @DPTR,A + INC DPTR + MOV A,#ASCII_Space + MOVX @DPTR,A + INC DPTR + + MOV A,R4_Bk1 + LCALL Bin_To_ASCII + MOVX @DPTR,A + INC DPTR + MOV A,B + MOVX @DPTR,A + INC DPTR + MOV A,#ASCII_Space + MOVX @DPTR,A + INC DPTR + + MOV A,R5_Bk1 + LCALL Bin_To_ASCII + MOVX @DPTR,A + INC DPTR + MOV A,B + MOVX @DPTR,A + INC DPTR + MOV A,#ASCII_Space + MOVX @DPTR,A + INC DPTR + + MOV A,R6_Bk1 + LCALL Bin_To_ASCII + MOVX @DPTR,A + INC DPTR + MOV A,B + MOVX @DPTR,A + INC DPTR + MOV A,#ASCII_Space + MOVX @DPTR,A + INC DPTR + + MOV A,R7_Bk1 + LCALL Bin_To_ASCII + MOVX @DPTR,A + INC DPTR + MOV A,B + MOVX @DPTR,A + INC DPTR + MOV A,#ASCII_Space + MOVX @DPTR,A + + MOV DPTR,#Net_Rcv_Str + SETB Ext_Dsp_Ready + + POP PSW + POP B + POP Acc + RET + +;=============================== Tools ==================================== + +Is_Token_Symbol: + PUSH AR0 + PUSH AR1 + PUSH AR2 + PUSH AR3 + PUSH DPL + PUSH DPH + + CLR C + MOV DPTR,#Symbol_Table + MOV R0,#(Token_Str # 256) + MOV R1,#(Token_Str / 256) + +Is_Symb_Loop: CLR A + MOVC A,@A+DPTR + MOV R3,A ; Symbolwert + XRL A,#TableEnd + JZ Is_Symb_Not_Found + + INC DPTR + CLR A + MOVC A,@A+DPTR + MOV R2,A ; Offset + + INC DPTR + LCALL Compare_Str + JNC Is_Symb_Found + + DEC_DPTR + DEC_DPTR + MOV A,DPL + ADD A,R2 + MOV DPL,A + JNC Is_Symb_Loop + INC DPH + SJMP Is_Symb_Loop + +Is_Symb_Found: MOV A,R3 + CLR C + SJMP Is_Symb_End + +Is_Symb_Not_Found: + SETB C + +Is_Symb_End: POP DPH + POP DPL + POP AR3 + POP AR2 + POP AR1 + POP AR0 + RET + +;-------------------------------------------------------------------------- + +Is_Token_Module: + PUSH AR0 + PUSH AR1 + PUSH AR2 + PUSH AR3 + PUSH DPL + PUSH DPH + + CLR C + MOV DPTR,#Module_Table + MOV R0,#(Token_Str # 256) + MOV R1,#(Token_Str / 256) + +Is_Mod_Loop: CLR A + MOVC A,@A+DPTR + MOV R3,A ; Modulname + XRL A,#TableEnd + JZ Is_Mod_Not_Found + + INC DPTR + CLR A + MOVC A,@A+DPTR + MOV R2,A ; Offset + + INC DPTR + LCALL Compare_Str + JNC Is_Mod_Found + + DEC_DPTR + DEC_DPTR + MOV A,DPL + ADD A,R2 + MOV DPL,A + JNC Is_Mod_Loop + INC DPH + SJMP Is_Mod_Loop + +Is_Mod_Found: MOV A,R3 + CLR C + SJMP Is_Mod_End + +Is_Mod_Not_Found: + SETB C + +Is_Mod_End: POP DPH + POP DPL + POP AR3 + POP AR2 + POP AR1 + POP AR0 + RET + +;-------------------------------------------------------------------------- + +Bin_To_ASCII: PUSH AR0 + PUSH DPL + PUSH DPH + + MOV DPTR,#BTA_Table + MOV B,#16 + DIV AB + MOVC A,@A+DPTR + MOV R0,A + MOV A,B + MOVC A,@A+DPTR + MOV B,A + MOV A,R0 + + POP DPH + POP DPL + POP AR0 + RET + +BTA_Table: DB "0123456789ABCDEF" + +;-------------------------------------------------------------------------- + +ASCII_To_Bin: IRP Source,Acc,P2,DPL,DPH,AR0,AR1,AR2,AR3 + PUSH Source + ENDM + + MOV R0,#(Token_Str # 256) + MOV R1,#(Token_Str / 256) + MOV DPTR,#ATB_Table + MOV ASCII_Low_Byte,#00 + MOV ASCII_High_Byte,#00 + MOV R2,#00 + +ATB_Search: INC_R0R1 + INC R2 + MOV P2,R1 + MOVX A,@R0 + JNZ ATB_Search + + DEC_R0R1 + +ATB_Loop: CLR C + MOV P2,R1 + MOVX A,@R0 + LCALL Is_Digit + JC ATB_Not_Digit + MOV R3,A + JZ ATB_Next + +ATB_Add_Loop: CLR A + MOVC A,@A+DPTR + CJNE A,#0FFh,ATB_Add_Cont + SJMP ATB_False +ATB_Add_Cont: ADD A,ASCII_Low_Byte + MOV ASCII_Low_Byte,A + MOV A,#01 + MOVC A,@A+DPTR + ADDC A,ASCII_High_Byte + JC ATB_End + MOV ASCII_High_Byte,A + DJNZ R3,ATB_Add_Loop + +ATB_Next: INC DPTR + INC DPTR + DEC_R0R1 + DJNZ R2,ATB_Loop + + CLR C ; + MOV A,ASCII_High_Byte ; Overflow (+) ? + MOV C,Acc.7 ; + SJMP ATB_End ; + +ATB_Not_Digit: CJNE A,#45,ATB_False + CJNE R2,#1,ATB_False + CLR C + CLR A + SUBB A,ASCII_Low_Byte + MOV ASCII_Low_Byte,A + CLR A + SUBB A,ASCII_High_Byte + MOV ASCII_High_Byte,A + + CLR C ; + MOV A,ASCII_High_Byte ; + MOV C,Acc.7 ; Overflow (-) ? + CPL C ; + SJMP ATB_End ; + +ATB_False: SETB C + +ATB_End: IRP Target,AR3,AR2,AR1,AR0,DPH,DPL,P2,Acc + POP Target + ENDM + RET + +ATB_Table: DB 001h,000h + DB 00Ah,000h + DB 064h,000h + DB 0E8h,003h + DB 010h,027h + DB 0FFh + +;-------------------------------------------------------------------------- + +Jump_Blank_Str: + PUSH Acc + +JB_Loop: MOV A,#00 + MOVC A,@A+DPTR + JZ JB_End + INC DPTR + SJMP JB_Loop + +JB_End: POP Acc + RET + +;-------------------------------------------------------------------------- +;Routine : Clear_Str +;Parameter: A (Loeschzeichen) +; DPTR (zu loeschender String) + +Clear_Str: PUSH DPL + PUSH DPH + PUSH AR1 + MOV R1,#Kb_Max_Length +Clear_Str_Loop: MOVX @DPTR,A + INC DPTR + DJNZ R1,Clear_Str_Loop + POP AR1 + POP DPH + POP DPL + RET + +;-------------------------------------------------------------------------- +;Routine : Clear_Pos_Str (loescht einen String von Startposition bis Ende) +;Parameter: DPTR (zu loeschender String) +; A (Loeschzeichen) +; B (Startposition) + + +Clear_Pos_Str: PUSH Acc + PUSH PSW + PUSH DPL + PUSH DPH + PUSH AR1 + + MOV R1,B + CJNE R1,#Kb_Max_Length,CPS_Cont + SJMP CPS_End +CPS_Cont: PUSH Acc + MOV A,B + ADD A,DPL + MOV DPL,A + JNC CPS_Cont2 + INC DPH + +CPS_Cont2: CLR C + MOV A,#Kb_Max_Length + SUBB A,B + MOV R1,A + POP Acc + JC CPS_End +CPS_Loop: MOVX @DPTR,A + INC DPTR + DJNZ R1,CPS_Loop + +CPS_End: POP AR1 + POP DPH + POP DPL + POP PSW + POP Acc + RET + +;-------------------------------------------------------------------------- +; Routine : Copy_Pos_Buffer (kopiert einen String in Kb_Str_Buffer +; ab Kb_Cursor; dieser zeigt dann nach +; dem letzten Zeichen des Strings) +; Parameter: DPTR (zu kopierender String) + + +Copy_Pos_Buffer: + PUSH Acc + PUSH PSW + PUSH P2 + PUSH DPL + PUSH DPH + PUSH AR0 + PUSH AR1 + + MOV R0,#(Kb_Str_Buffer # 256) + MOV R1,#(Kb_Str_Buffer / 256) + MOV A,R0 + ADD A,Kb_Cursor + MOV R0,A + JNC CPB_Loop + INC R1 + +CPB_Loop: MOV A,Kb_Cursor + CJNE A,#Kb_Max_Length,CPB_Loop_Cont + DEC Kb_Cursor + SJMP CPB_End + +CPB_Loop_Cont: CLR A + MOVC A,@A+DPTR + JZ CPB_End + MOV P2,R1 + MOVX @R0,A + INC DPTR + INC Kb_Cursor + INC_R0R1 + SJMP CPB_Loop + +CPB_End: POP AR1 + POP AR0 + POP DPH + POP DPL + POP P2 + POP PSW + POP Acc + RET + +;-------------------------------------------------------------------------- + +UpCase: PUSH PSW + PUSH AR0 + + MOV R0,A + CLR C + SUBB A,#97 + JC UpCase_Rest + MOV A,#122 + SUBB A,R0 + JC UpCase_Rest + MOV A,R0 + SUBB A,#32 + SJMP UpCase_End +UpCase_Rest: MOV A,R0 + +UpCase_End: POP AR0 + POP PSW + RET + +;-------------------------------------------------------------------------- + +Is_Digit: PUSH AR0 + + CLR C + MOV R0,A + SUBB A,#48 + JC Is_Digit_Rest + MOV A,#57 + SUBB A,R0 + JC Is_Digit_Rest + MOV A,R0 + SUBB A,#48 + SJMP Is_Digit_End + +Is_Digit_Rest: MOV A,R0 + +Is_Digit_End: POP AR0 + RET + +;-------------------------------------------------------------------------- + +Wait_2s: PUSH AR0 + PUSH AR1 + PUSH AR2 + + MOV R2,#12 +Wait_Loop2: MOV R1,#250 +Wait_Loop1: MOV R0,#250 +Wait_Loop0: DJNZ R0,Wait_Loop0 + DJNZ R1,Wait_Loop1 + DJNZ R2,Wait_Loop2 + + POP AR2 + POP AR1 + POP AR0 + RET + +;-------------------------------------------------------------------------- + +Clr_Msg_Buffer: PUSH AR0 + PUSH AR1 + + MOV R1,#8 + MOV R0,#Msg_Registers +Clr_Msg_Loop: MOV @R0,#00 + INC R0 + DJNZ R1,Clr_Msg_Loop + + POP AR1 + POP AR0 + RET + +;------------------------------------------------------------------------------ + +;Stackarea in idata nach oben nur durch Prozessorram begrenzt!! +;Dieses Segment muá IMMER als letztes stehen!!! + + segment idata + +Stack: db ? ;ab hier liegt der Stack + +;------------------------------------------------------------------------------ + + end diff --git a/tests/t_mic51/t_mic51.doc b/tests/t_mic51/t_mic51.doc new file mode 100644 index 0000000..94ba34e --- /dev/null +++ b/tests/t_mic51/t_mic51.doc @@ -0,0 +1,6 @@ ++---------------------- Test Application MIC51 ----------------------------+ +| | +| This is a student's program from RWTH Aachen's microprocessor course. It | +| tests the MCS51 (not 251!) codegenerator and makes heavy use of macros. | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_mic51/t_mic51.inc b/tests/t_mic51/t_mic51.inc new file mode 100644 index 0000000..27d4051 --- /dev/null +++ b/tests/t_mic51/t_mic51.inc @@ -0,0 +1,165 @@ +; t_mic51.asm-Includefile für Assembler-Programm +ROB equ 10H +UC_ROB equ 1H +FRS equ 11H +UC_FRS equ 2H +TEACHROB equ 12H +UC_TEACH_ROB equ 3H +TEACHFRS equ 13H +UC_TEACH_FRS equ 4H +TEACHKEY equ 14H +UC_TEACH_KEY equ 5H +MEMROB equ 15H +UC_TEACH_ROB equ 3H +MEMFRS equ 16H +UC_TEACH_FRS equ 4H +PC_SIO equ 17H +UC_PC_SIO equ 0EH +ON equ 1H +OFF equ 0H +PLUS equ 1H +MINUS equ 0H +FAST equ 1H +SLOW equ 0H +SUPERSLOW equ 2H +QUEUE_WARNING equ 81H +QUEUE_FULL equ 61H +UNDEF_PAR equ 62H +UNDEF_PIECE_REF equ 63H +UNDEF_DRILL_REF equ 64H +UNDEF_KOORD_REF equ 65H +INTERNAL_ERROR equ 66H +END_X_PLUS equ 67H +END_Y_PLUS equ 68H +END_Z_PLUS equ 69H +END_V_PLUS equ 6AH +END_X_MINUS equ 70H +END_Y_MINUS equ 71H +END_Z_MINUS equ 72H +END_V_MINUS equ 73H +HARD_END_X_PLUS equ 74H +HARD_END_Y_PLUS equ 75H +HARD_END_Z_PLUS equ 76H +HARD_END_V_PLUS equ 77H +HARD_END_X_MINUS equ 78H +HARD_END_Y_MINUS equ 79H +HARD_END_Z_MINUS equ 7AH +HARD_END_V_MINUS equ 7BH +MOVEAB equ 1H +MOVEAS equ 2H +MOVEAE equ 3H +MOVEARW equ 4H +MOVEALW equ 5H +MOVEAH equ 6H +MOVEAPOS1 equ 7H +MOVEAPOS2 equ 8H +MOVERB equ 9H +MOVERS equ 0AH +MOVERE equ 0BH +MOVERRW equ 0CH +MOVERLW equ 0DH +MOVERH equ 0EH +MOVERPOS1 equ 0FH +MOVERPOS2 equ 10H +MOVECBL equ 11H +MOVECBR equ 12H +STOPCB equ 13H +MOVECSU equ 14H +MOVECSD equ 15H +STOPCS equ 16H +MOVECEU equ 17H +MOVECED equ 18H +STOPCE equ 19H +MOVECHU equ 1AH +MOVECHD equ 1BH +STOPCHP equ 1CH +MOVECHL equ 1DH +MOVECHR equ 1EH +STOPCHT equ 1FH +MOVECHO equ 20H +MOVECHC equ 21H +STOPCH equ 22H +ROBVELOCITY equ 23H +ROBGOHOME equ 24H +SETHOME equ 25H +GIBPOS1 equ 26H +GIBPOS2 equ 27H +ROBGIBREADY equ 28H +ROBINIT equ 29H +ROBDEINIT equ 2AH +INIT equ 1H +DEINIT equ 2H +MOVECX equ 3H +MOVECY equ 4H +MOVECZ equ 5H +MOVECV equ 6H +STOPCX equ 7H +STOPCY equ 8H +STOPCZ equ 9H +STOPCV equ 0AH +FRSVELOCITY equ 0BH +FRSVELOCITYDRAW equ 0CH +FRSGOHOME equ 0DH +REFFAHRT equ 0EH +SETDRILLREF equ 0FH +SETPIECEREF equ 10H +MOVEX equ 11H +MOVEY equ 12H +MOVEZ equ 13H +MOVEAPOS equ 14H +MOVERX equ 15H +MOVERY equ 16H +MOVERZ equ 17H +MOVERV equ 18H +MOVERPOS equ 19H +MOVEVOPEN equ 1AH +MOVEVCLOSE equ 1BH +MOVEV equ 1CH +GOPIECEREFPOS equ 1DH +MOVEPR equ 1EH +DRILL equ 1FH +SETMASTERADRESS equ 20H +GIBFRSPOS1 equ 21H +GIBFRSPOS2 equ 22H +GIBPOSP equ 23H +GIBSTATUS equ 24H +GIBREADY equ 25H +LOADROB equ 1H +SAVEROB equ 2H +STARTROBRUN equ 3H +STOREROBPOS equ 4H +STOREROBSYNC equ 5H +STOREROBREADY equ 6H +INITROBTEACH equ 7H +DEINITROBTEACH equ 8H +CLEARROBTEACH equ 9H +RESETROBTEACH equ 0AH +GETROBSYNC equ 0BH +GETROBREADY equ 0CH +ROBPOS1 equ 0DH +ROBPOS2 equ 0EH +DEBUGROB equ 0FH +LOADFRS equ 1H +SAVEFRS equ 2H +STARTFRSRUN equ 3H +STOREFRSPOS equ 4H +STOREFRSSYNC equ 5H +STOREFRSREADY equ 6H +STOREFRSPIECEREF equ 7H +STOREFRSTIEFE equ 8H +STOREFRSDRILL equ 9H +INITFRSTEACH equ 0AH +DEINITFRSTEACH equ 0BH +CLEARFRSTEACH equ 0CH +RESETFRSTEACH equ 0DH +GETFRSSYNC equ 0EH +GETFRSREADY equ 0FH +FRSPOS1 equ 10H +FRSPOS2 equ 11H +FRSPIECEREF equ 12H +FRSTIEFE equ 13H +GETFRSERROR equ 14H +GETFRSWARNING equ 15H +DEBUGFRS equ 16H +BUG equ 1H +; Ende Includefile für Assembler-Programm diff --git a/tests/t_mic51/t_mic51.ori b/tests/t_mic51/t_mic51.ori new file mode 100755 index 0000000..e9ce88f Binary files /dev/null and b/tests/t_mic51/t_mic51.ori differ diff --git a/tests/t_mic51/t_mod1.asm b/tests/t_mic51/t_mod1.asm new file mode 100644 index 0000000..fb91ac8 --- /dev/null +++ b/tests/t_mic51/t_mod1.asm @@ -0,0 +1,487 @@ + +; Aufgabe Nr.: Teach- In Einheit fuer uP- Praktikum II +; --- Link- Modul --- +; Autor: Joerg Vollandt +; erstellt am : 13.06.1994 +; letzte Aenderung am : 02.08.1994 +; Bemerkung : +; +; Dateiname : t_mod1.asm +; +;===================================================================== + SEGMENT CODE + USING 0 + + INCLUDE MAKRO1.ASM + INCLUDE TAST1.ASM + INCLUDE MEM1.ASM + INCLUDE TEACH1.ASM + INCLUDE RUN1.ASM + INCLUDE DEBUG.ASM +;===================================================================== +; Definitionen der Funktionen der Teach- In Einheit + +Adr_InitRobTeach EQU INIT_TEACH ; Initialisieren der Teach- In Einheit +Adr_InitFrsTeach EQU INIT_TEACH ; Initialisieren der Teach- In Einheit +Adr_DeinitRobTeach EQU DEINIT_TEACH ; Deinitialisieren der Teach- In Einheit +Adr_DeinitFrsTeach EQU DEINIT_TEACH ; Deinitialisieren der Teach- In Einheit +Adr_ClearRobTeach EQU CLEAR_TEACH ; Speicher loeschen +Adr_ClearFrsTeach EQU CLEAR_TEACH ; Speicher loeschen +Adr_ResetRobTeach EQU RESET_TEACH ; Speicher zum lesen zuruecksetzen +Adr_ResetFrsTeach EQU RESET_TEACH ; Speicher zum lesen zuruecksetzen +Adr_StoreRobPos EQU STORE_ROB ; Position Roboter speichern +Adr_StoreFrsPos EQU STORE_FRAES ; Position Fraese speichern +Adr_StoreRobSync EQU STORE_SYNC ; Synchronisation speichern +Adr_StoreFrsSync EQU STORE_SYNC ; Synchronisation speichern +Adr_StoreRobReady EQU STORE_READY ; Warten auf Geraet speichern +Adr_StoreFrsReady EQU STORE_READY ; Warten auf Geraet speichern +Adr_StoreFrsPieceRef EQU STORE_PIECE_REF ; Werkstueck Nullpkt. festlegen +Adr_StoreFrsTiefe EQU STORE_TIEFE ; Fraestiefe festlegen +Adr_StoreFrsDrill EQU STORE_DRILL ; Fraesdatei bearbeiten +Adr_GetRobSync EQU GET_SYNC_MSG ; Synchronisation empfangen +Adr_GetFrsSync EQU GET_SYNC_MSG ; Synchronisation empfangen +Adr_GetRobReady EQU GET_READY_MSG ; Ready empfangen +Adr_GetFrsReady EQU GET_READY_MSG ; Ready empfangen +Adr_LoadRob EQU LOAD_ROB ; Roboter Teach- In Datei von PC laden +Adr_LoadFrs EQU LOAD_FRAES ; Fraese- Teach- In Datei von PC laden +Adr_SaveRob EQU SAVE_ROB ; Roboter Teach- In Datei auf PC speichern +Adr_SaveFrs EQU SAVE_FRAES ; Fraese- Teach- In Datei auf PC speichern + +Adr_RobPos1 EQU FIRST_FROM_ROB ; Position von Roboter 1. Teil +Adr_RobPos2 EQU SECOND_FROM_ROB ; Position von Roboter 2. Teil +Adr_FrsPos1 EQU FIRST_FROM_FRS ; Position von Fraese 1. Teil +Adr_FrsPos2 EQU SECOND_FROM_FRS ; Position von Fraese 2. Teil +Adr_FrsPieceRef EQU PIECE_REF_FROM_FRS ; Position von Fraese +Adr_FrsTiefe EQU TIEFE_FROM_FRS ; Position von Fraese + +Adr_DebugRob EQU DEBUG_MEM ; Position von Roboter 2. Teil +Adr_DebugFrs EQU DEBUG_MEM ; Position von Roboter 2. Teil +Adr_StartRobRun EQU START_RUNNING ; Runmanager starten +Adr_StartFrsRun EQU START_RUNNING ; Runmanager starten + +Adr_GetFrsError EQU Get_Error_from_frs ; +Adr_GetFrsWarning EQU Get_Warning_from_frs ; + + +MemRob_MsgCall_Tab: + include defMsg.inc +MemRob_MsgCall_Tend: + +MemFrs_MsgCall_Tab: + include defMsg.inc +MemFrs_MsgCall_Tend: + +;------------------------------------------------------------------------------ +; Speicherdefinitionen + + + SEGMENT BITDATA + +MSG DB ? +Sp_MSG DB ? +READY DB ? +CRC DB ? + +TESTBIT DB ? +RUNNINGBIT DB ? +Sync_Waiting DB ? +Ready_Waiting DB ? +Drilling DB ? +Drill_down DB ? +PAUSE DB ? +FrsWarning DB ? +SingleStep DB ? +Break DB ? + +Ref_Flag DB ? +Tiefe_Flag DB ? + + SEGMENT DATA + +Sp_MSG_Buffer DB ? +T_Sync_Counter DB ? +R_Sync_Counter DB ? +Queue_Counter DB ? + +Frs_Ref_x DW ? +Frs_Ref_y DW ? +Frs_Ref_z DW ? +Frs_Ref_Tiefe DW ? + +;--------------------------------------------------------------------- + SEGMENT CODE +;--------------------------------------------------------------------- +; Funktion : CALL_BACK- Fkt. wird nach Empfang einer Message +; aufgerufen. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +MESSAGE_BIT BIT ACC.0 ; Message Bits +SPECIAL_MESSAGE_BIT BIT ACC.2 +START_BIT BIT ACC.0 ; Special- Message Bits +STOP_BIT BIT ACC.1 +RESET_BIT BIT ACC.3 +PAUSE_BIT BIT ACC.2 +AUX1_BIT BIT ACC.4 +AUX2_BIT BIT ACC.5 + +MESSAGE_INTERRUPT: + PUSH ACC + LCALL READ_STATUS + JNB SPECIAL_MESSAGE_BIT,MESSAGE_INTERRUPT1 + LCALL READ_SPECIAL_MESSAGE ; Special_Message lesen + MOV Sp_MSG_Buffer,A ; und retten + SETB Sp_MSG + POP ACC + RET + +MESSAGE_INTERRUPT1: + JNB MESSAGE_BIT,MESSAGE_INTERRUPT2 + SETB MSG ; Normale Msg.empfangen +MESSAGE_INTERRUPT2: + POP ACC + RET + + +;--------------------------------------------------------------------- +; Funktion : Message- Scheduler fuer Speichermodul. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; +; **************************************************************************** +; R0 Empf„nger (logische Adresse) +; R1 Message +; R2 - R7 Parameter +; **************************************************************************** + +Message_Handler MACRO Modul + + push PSW + push ACC + push DPH + push DPL + + mov DPTR,#Msg_Hndl_Ret ; Ruecksprungadresse vom indirekten + push DPL ; Jump ergibt indirekten Call + push DPH + mov DPTR,#Modul_MsgCall_Tab + mov A,AR1 + clr C + rlc A + mov AR1,A + jnc No_inc + inc DPH +No_inc: movc A,@A+DPTR + push ACC + inc DPTR + mov A,AR1 + movc A,@A+DPTR + push ACC + ret ; indireckter Sprung + +Msg_Hndl_Ret: + pop DPL + pop DPH +Msg_Ha_Exit: + pop ACC + pop PSW + + ENDM + +;--------------------------------------------------------------------- +; Funktion : Message- Scheduler fuer PC- Messages. +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +MEM_SCHEDULER: + PUSH PSW + PUSH ACC + CLR MSG + MOV A,R0 + IFCALL 02h,GET_FROM_PC ; TI-Datei von PC an Roboter + IFCALL 03h,GET_FROM_PC ; TI-Datei von PC an Fraese + IFCALL 01h,GET_WORKFR_FROM_PC ; Fraesdatei von PC + POP ACC + POP PSW + RET + +;--------------------------------------------------------------------- +; Funktion : Message auf die Module verteilen +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : - +; Stackbedarf : +; Zeitbedarf : +; + +Dispatch_Msg: + PUSH PSW + PUSH ACC + MOV A,R0 + CJNE A,#10h,Dis_Msg0 ; Msg.-Nr. <=10h sind von PC +Dis_Msg0: JC Dis_Msg01 ; und werden von MEM_SCHEDULER + LJMP Dis_Msg02 ; bearbeitet +Dis_Msg01: + LCALL MEM_SCHEDULER + LJMP Dis_Msg_Ret + +Dis_Msg02: + cjne A,#TeachRob,Dis_Msg10 + LJMP Dis_Msg11 +Dis_Msg10: LJMP Dis_Msg2 +Dis_Msg11: + ifdef TeachRob_MsgCall_Tab + Message_Handler TeachRob + endif + ljmp Dis_Msg_Ret + +Dis_Msg2: cjne A,#TeachFrs,Dis_Msg20 + LJMP Dis_Msg21 +Dis_Msg20: LJMP Dis_Msg3 +Dis_Msg21: + ifdef TeachFrs_MsgCall_Tab + Message_Handler TeachFrs + endif + ljmp Dis_Msg_Ret + +Dis_Msg3: cjne A,#Rob,Dis_Msg30 + LJMP Dis_Msg31 +Dis_Msg30: LJMP Dis_Msg4 +Dis_Msg31: + ifdef Rob_MsgCall_Tab + Message_Handler Rob + endif + ljmp Dis_Msg_Ret + +Dis_Msg4: cjne A,#Frs,Dis_Msg40 + LJMP Dis_Msg41 +Dis_Msg40: LJMP Dis_Msg5 +Dis_Msg41: + ifdef Frs_MsgCall_Tab + Message_Handler Frs + endif + ljmp Dis_Msg_Ret + +Dis_Msg5: cjne A,#MemFrs,Dis_Msg50 + LJMP Dis_Msg51 +Dis_Msg50: LJMP Dis_Msg6 +Dis_Msg51: + ifdef MemFrs_MsgCall_Tab + Message_Handler MemFrs + endif + ljmp Dis_Msg_Ret + +Dis_Msg6: cjne A,#MemRob,Dis_Msg60 + LJMP Dis_Msg61 +Dis_Msg60: LJMP Dis_Msg7 +Dis_Msg61: + ifdef MemRob_MsgCall_Tab + Message_Handler MemRob + endif + ljmp Dis_Msg_Ret + +Dis_Msg7: + +Dis_Msg_Ret: + POP ACC + POP PSW + RET + +;--------------------------------------------------------------------- +; Funktion : START-Routine +; Aufrufparameter : Wird durch die globale Message "START" ausgeloesst +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; +GLOBAL_START: + ;LCD 40H,"START-Routine " + LCALL START_RUNNING + RET + +;--------------------------------------------------------------------- +; Funktion : NOTAUS-Routine +; Aufrufparameter : Wird durch die globale Message "STOP" ausgeloesst +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; +GLOBAL_NOTAUS: + LCD 40H,"NOTAUS!!! Abbruch. " + CLR RUNNINGBIT + LCALL INIT_TEACH + LCALL RESET_TEACH + RET + +;--------------------------------------------------------------------- +; Funktion : RESET-Routine +; Aufrufparameter : Wird durch die globale Message "RESET" ausgeloesst +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; +GLOBAL_RESET: + LCD 40H,"Teachin- u. Runmanager initialisiert. " + LCALL INIT_TEACH + LCALL INIT_RUN + LCALL RESET_TEACH + LCALL INIT_FRS + CLR TESTBIT + + RET + +;--------------------------------------------------------------------- +; Funktion : PAUSE-Routine +; Aufrufparameter : Wird durch die globale Message "PAUSE" ausgeloesst +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; +GLOBAL_PAUSE: + JB RUNNINGBIT,GLOBAL_PAUSE_1 + LJMP GLOBAL_PAUSE_ENDE +GLOBAL_PAUSE_1: + CPL PAUSE + JNB PAUSE,GLOBAL_PAUSE_AUS + LCD 40H,"Pausemodus. Weiter mit . " + RET +GLOBAL_PAUSE_AUS: + LCD 40H,"Pausemodus aufgehoben. " + RET +GLOBAL_PAUSE_ENDE: + RET + +;--------------------------------------------------------------------- +; Funktion : AUX1-Routine +; Aufrufparameter : Wird durch die globale Message "AUX1" ausgeloesst +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; +GLOBAL_AUX1: + LCD 40H,"AUX1-Routine " + SETB SingleStep + JNB Ready_Waiting,GLOBAL_AUX1_ENDE + SETB Break +GLOBAL_AUX1_ENDE + RET + +;--------------------------------------------------------------------- +; Funktion : AUX2-Routine +; Aufrufparameter : Wird durch die globale Message "AUX2" ausgeloesst +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; +GLOBAL_AUX2: + ;LCD 40H,"AUX2-Routine " + LCD 40H,"Teachin- Datei wird gelaeden. " + LCALL LOAD_ROB + LCALL LOAD_FRAES + RET + +;--------------------------------------------------------------------- +; Funktion : Hauptprogramm fuer das Speichermodul +; Aufrufparameter : - +; Ruechgabeparameter : - +; Veraenderte Register : +; Stackbedarf : +; Zeitbedarf : +; + +Main_Event_Loop: + JNB Sp_MSG,No_Sp_Msg + LCALL Do_Sp_Msg + JB Sp_MSG,Main_Event_Loop +No_Sp_Msg: + JNB MSG,No_Msg + LCALL Do_Msg + JB MSG,Main_Event_Loop +No_Msg: + JNB RUNNINGBIT,No_Runnig + LCALL Do_Runnig +No_Runnig: + JB Sp_MSG,Main_Event_Loop + JB MSG,Main_Event_Loop + + RET + + +Do_Msg: CLR MSG + PUSH_ALL + LCALL READ_MESSAGE + LCALL Dispatch_Msg + POP_ALL + RET + +Do_Sp_Msg: + CLR Sp_MSG + PUSH ACC + MOV A,Sp_MSG_Buffer +SM_START: JNB START_BIT,SM_NOTAUS ; Special- Message Fkt. + LCALL GLOBAL_START ; aufrufen + POP ACC + RET +SM_NOTAUS: JNB STOP_BIT,SM_RESET + LCALL GLOBAL_NOTAUS + POP ACC + RET +SM_RESET: JNB RESET_BIT,SM_PAUSE + LCALL GLOBAL_RESET + POP ACC + RET +SM_PAUSE: JNB PAUSE_BIT,SM_AUX1 + LCALL GLOBAL_PAUSE + POP ACC + RET +SM_AUX1: JNB AUX1_BIT,SM_AUX2 + LCALL GLOBAL_AUX1 + POP ACC + RET +SM_AUX2: JNB AUX2_BIT,SM_ENDE + LCALL GLOBAL_AUX2 + POP ACC + RET +SM_ENDE: POP ACC + RET + +Do_Runnig: + JB Drilling,Do_Drilling + JB PAUSE,Do_Waiting + JB Sync_Waiting,Do_Waiting + JB Ready_Waiting,Do_Waiting + LCALL RUN_MODUL +Do_Waiting: + RET + +Do_Drilling: + JNB FrsWarning,No_FrsWarning ; Queue- Warnung von Frs + PUSH_ALL + post_message2 #Frs,#GibReady,#MemFrs,#GetFrsReady,#0 + POP_ALL + CLR FrsWarning + SETB READY_WAITING +No_FrsWarning: + RET + +;===================================================================== +; END +;--------------------------------------------------------------------- + diff --git a/tests/t_msp/asflags b/tests/t_msp/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_msp/t_msp.asm b/tests/t_msp/t_msp.asm new file mode 100644 index 0000000..c0bb12c --- /dev/null +++ b/tests/t_msp/t_msp.asm @@ -0,0 +1,116 @@ + cpu msp430 + + include regmsp.inc + +ede equ 0f016h +toni equ 01114h + + mov r12,r7 + mov pc,r7 + mov sp,r7 + mov sr,r7 + + mov 2(r5),6(r6) + + mov ede,toni + + mov &ede,&toni + + mov @r10,0(r11) + + mov @r10+,0(r11) + + mov #45,toni + mov #0,toni + mov #1,toni + mov #2,toni + mov #4,toni + mov #8,toni + mov #-1,toni + + dadd #45,r4 + + rrc r5 + rra.b toni + push pc + swpb &ede + call 1234h + sxt @r5+ + + reti + + jmp 234h + jne $ + jn $+2 + +;---------------------------------- +; emulierte Befehle + + adc r6 + adc.w r6 + adc.b r6 + dadc @r4 + dadc.w @r4 + dadc.b @r4 + dec toni + dec.w toni + dec.b toni + decd &toni + decd.w &toni + decd.b &toni + inc ede + inc.w ede + inc.b ede + incd &ede + incd.w &ede + incd.b &ede + sbc 55h(r9) + sbc.w 55h(r9) + sbc.b 55h(r9) + + inv @r6 + inv.w @r6 + inv.b @r6 + rla r5 + rla.w r5 + rla.b r5 + rlc @r14 + rlc.w @r14 + rlc.b @r14 + + clr 0(r10) + clr.w 0(r10) + clr.b 0(r10) + clrc + clrn + clrz + pop sr + setc + setn + setz + tst toni + tst.w toni + tst.b toni + + br r5 + dint + eint + nop + ret + + padding on + .byte 1,2,3,4 + .byte "Hello world" + .byte "Hello world!" + .word 1,2,3,4 + .bss 20 + .bss 21 + + padding off + .byte 1,2,3,4 + .byte "Hello world" + .byte "Hello world!" + .word 1,2,3,4 + .bss 20 + .bss 21 + diff --git a/tests/t_msp/t_msp.doc b/tests/t_msp/t_msp.doc new file mode 100644 index 0000000..da3085d --- /dev/null +++ b/tests/t_msp/t_msp.doc @@ -0,0 +1,5 @@ ++-------------------------- Test Application MSP ----------------------------+ +| | +| This is a (synthetic) test of the MSP430 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_msp/t_msp.ori b/tests/t_msp/t_msp.ori new file mode 100644 index 0000000..4278619 Binary files /dev/null and b/tests/t_msp/t_msp.ori differ diff --git a/tests/t_parsys/asflags b/tests/t_parsys/asflags new file mode 100644 index 0000000..01f6552 --- /dev/null +++ b/tests/t_parsys/asflags @@ -0,0 +1 @@ +-c \ No newline at end of file diff --git a/tests/t_parsys/float.i68 b/tests/t_parsys/float.i68 new file mode 100644 index 0000000..fbfc1e9 --- /dev/null +++ b/tests/t_parsys/float.i68 @@ -0,0 +1,1226 @@ +; FLOAT.I68 +;----------------------------------------------------------------------------- +; Fliesskommaroutinen fuer den PC-PAR 68000, Version ohne 68881 +; entnommen mc 11/88, c't... + +;----------------------------------------------------------------------------- +; Definitionen + +vorz equ 0 +subflag equ 1 +maxexpo equ 255 +bias equ 127 +extend equ $10 +e equ $402df854 ; exp(1) +ln2 equ $3f317218 ; ln(2) +ln10 equ $40135d8e ; ln(10) +eins equ $3f800000 ; 1.0 +zwei equ $40000000 ; 2.0 +pi2 equ $40c90fdb ; Pi*2 +pi equ $40490fdb ; Pi +pihalf equ $3fc90fdb ; Pi/2 + +;----------------------------------------------------------------------------- +; Librarykopf: + + +S_FloatLib: dc.l S_floatlibend-S_floatlibstart ; Laenge +S_floatlibstart: + dc.l -1 ; Speicher fuer Zeiger + dc.b "FLOAT",0 ; Name + ds 0 + + + +;----------------------------------------------------------------------------- +; Sprungtabelle: + + bra.l S_fadd + bra.l S_fsub + bra.l S_fmul + bra.l S_fdiv + bra.l S_fmul2 + bra.l S_fsqrt + bra.l S_fabs + bra.l S_floatlibnop + bra.l S_fcmp + bra.l S_fitof + bra.l S_fftoi + bra.l S_floatlibnop + bra.l S_floatlibnop + bra.l S_floatlibnop + bra.l S_floatlibnop + bra.l S_floatlibnop + bra.l S_fexp + bra.l S_fsinh + bra.l S_fcosh + bra.l S_ftanh + bra.l S_fcoth + bra.l S_floatlibnop + bra.l S_floatlibnop + bra.l S_floatlibnop + bra.l S_fln + bra.l S_flog + bra.l S_fasinh + bra.l S_facosh + bra.l S_fatanh + bra.l S_facoth + bra.l S_floatlibnop + bra.l S_floatlibnop + bra.l S_fsin + bra.l S_fcos + bra.l S_ftan + bra.l S_fcot + bra.l S_floatlibnop + bra.l S_floatlibnop + bra.l S_floatlibnop + bra.l S_floatlibnop + bra.l S_fasin + bra.l S_facos + bra.l S_fatan + bra.l S_facot + + +;----------------------------------------------------------------------------- +; Konstanten : + +S_Const1 dc.s 1.0 + +;----------------------------------------------------------------------------- +; Nullprozedur : + +S_floatlibnop: rts + +;----------------------------------------------------------------------------- +; Addition : D0.S = D0.S + D1.S + + ds 0 +S_fadd: + addq.l #1,_fadd_cnt.w + movem.l d1-d5,-(a7) ; benoetigte Register retten + rol.l #1,d0 ; Operanden rotieren und in Form + rol.l #1,d1 ; eeee eeee ffff ... fffs bringen + move.l d0,d2 + sub.l d1,d2 ; Differenz beider Zahlen bilden + bcc.s fadd_1 + exg d0,d1 ; ggf. vertauschen, so dass der +fadd_1: move.b d0,d3 ; kleinere in Register D1 steht + and.b #1,d3 ; maskiere das Vorzeichenbit + btst #vorz,d2 ; haben beide gleiches Vorzeichen ? + beq.s fadd_2 ; bei verschiedenen Vorzeichen + bset #subflag,d3 ; Flag fuer Subtraktion setzen +fadd_2: rol.l #8,d0 ; Form: ffff ... fffs eeee eeee + clr.w d4 ; Exponent der ersten Zahl + move.b d0,d4 ; wird im Register D4 aufgebaut + sne d0 ; falls ungleich Null, dann + ror.l #1,d0 ; implizite Eins, sonst implizite + clr.b d0 ; Null erzeugen, neu positionieren + + rol.l #8,d1 ; jetzt das gleiche fuer den + clr.w d5 ; zweiten Operanden, der Exponent + move.b d1,d5 ; kommt ins Register D5 + sne d1 + ror.l #1,d1 + clr.b d1 + +; In den Registern D0 und D1 stehen jetzt nur noch die Mantissen +; im Format ffff ... ffff 0000 0000, also linksbuendig, wobei die +; ehemals implizite Null bzw. Eins nun explizit an erster Stelle steht. +; In den Registern D4 und D5 stehen die Exponenten der beiden Zahlen. +; Das Vorzeichen des Ergebnisses sowie die Subtraktionsflags sind im +; Register D3 zwischengespeichert. + + move.w d4,d2 ; Jetzt Differenz der Exponenten + sub.w d5,d2 ; berechnen + cmp.w #24,d2 ; groesser als 24 ? + bgt.s fadd_rnd ; ja, --> Ergebnis ist groessere Zahl + lsr.l d2,d1 ; Mantisse um (D2)-Bits verschieben + btst #subflag,d3 ; Subtraktion oder Addition ? + bne.s fadd_subtr ; ggf. zur Subtraktion springen + add.l d1,d0 ; die beiden Mantissen addieren + bcc.s fadd_rnd ; kein Ueberlauf --> zum Runden + roxr.l #1,d0 ; Ueberlauf einschieben + addq.w #1,d4 ; Exponent korrigieren + bra.s fadd_rnd ; und zum Runden + +fadd_subtr: sub.l d1,d0 ; die beiden Mantissen subtrahieren + beq.s fadd_zero ; bei Null ist das Gesamtergebnis Null + bmi.s fadd_rnd ; bei fuehrender Eins zum Runden +fadd_nrm: tst.w d4 ; Exponent ist schon Null ? + beq.s fadd_rnd ; dann ist Ergebnis denormalisiert + subq.w #1,d4 ; Exponent erniedrigen + lsl.l #1,d0 ; Mantisse normalisieren bis + bpl.s fadd_nrm ; fuehrende Eins auftaucht + +fadd_rnd: add.l #$80,d0 ; jetzt Runden auf Bit hinter + bcc.s fadd_nov ; Mantisse + roxr.l #1,d0 ; bei Ueberlauf Mantisse normalisieren + addq.w #1,d4 ; und Exponent korrigieren +fadd_nov: clr.b d0 ; Rest-Mantisse loeschen + tst.l d0 ; Ist die Mantisse komplett Null ? + beq.s fadd_zero ; ja, dann ist Ergebnis auch Null + cmp.w #maxexpo,d4 ; Exponent-Ueberlauf ? + blt.s fadd_nue + move.w #maxexpo,d4 ; Unendlich Exponent = maxexpo + clr.l d0 ; Mantisse = Null + bra.s fadd_den + +fadd_nue: tst.w d4 ; Exponent Null ( Zahl denormalisiert? ) + beq.s fadd_den ; ja --> + lsl.l #1,d0 ; fuehrendes Bit wird nicht gespeichert +fadd_den: move.b d4,d0 ; Exponent einsetzen + ror.l #8,d0 ; Form: eeee eeee ffff ... fffx + roxr.b #1,d3 ; Vorzeichen in Carry schieben + roxr.l #1,d0 ; Form: seee eeee efff ... ffff + +fadd_zero: + movem.l (a7)+,d1-d5 ; Register restaurieren + rts ; Ende, Ergebnis steht in D0.L + +;----------------------------------------------------------------------------- +; Subtraktion : D0.S = D0.S - D1.S + + ds 0 +S_fsub: + bchg #31,d1 ; Vorzeichen des zweiten Operanden + bra S_fadd ; invertieren und zur Addition springen + + +;----------------------------------------------------------------------------- +; Multiplikation : D0.S = D0.S * D1.S + + ds 0 +S_fmul: + addq.l #1,_fmul_cnt.w + movem.l d1-d5,-(a7) ; benoetigte Register retten + move.l d0,d2 ; Operand 1 kopieren + eor.l d1,d2 ; EXOR um Vorzeichen zu bestimmen + + swap d0 ; Registerhaelften Operand 1 vertauschen + move.l d0,d3 ; Operand 1 ab jetzt in Register D3 + and.w #$7f,d3 ; Exponent und Vorzeichen loeschen + and.w #$7f80,d0 ; Exponent maskieren + beq.s fmul_dn1 ; gleich Null: Zahl ist denormalisiert + bset #7,d3 ; implizite Eins einsetzen + sub.w #$0080,d0 ; Bias kompensieren + +fmul_dn1: swap d1 ; jetzt Operand 2 behandeln + move.w d1,d4 + and.w #$7f,d1 + and.w #$7f80,d4 + beq.s fmul_dn2 + bset #7,d1 + sub.w #$0080,d4 ; Bias kompensieren + +fmul_dn2: add.w d0,d4 ; Exponenten addieren + lsr.w #7,d4 ; richtig positionieren + sub.w #bias-3,d4 ; Bias-3 subtrahieren + cmp.w #-24,d4 ; totaler Unterlauf ? + blt.s fmul_zero ; ja, dann ist Ergebnis Null + + move.w d3,d0 ; oberes Mantissenwort von Operand 1 + mulu d1,d0 ; mal oberem Mantissenwort von Op2 + swap d0 ; entspricht Verschiebung um 16 Bit + +; Das obere Wort von D0 ist nach der Multiplikation auf jeden Fall Null, +; da die oberen Mantissenworte nur im Bereich 0 ... 255 liegen. +; Das groete moegliche Ergebnis ist also 255 x 255 = 65025 = 0000FE01. +; Nach der Vertauschung erhalten wir also eine Zahl der xxxx 0000. +; Die untere Registerhaelfte von D0 koennen wir kurzzeitig als Zwischen- +; speicher verwenden. + + move.w d3,d0 ; oberes Wort von Operand 1 merken + swap d3 ; jetzt unteres Wort Op1 mal oberes Op2 + move.w d1,d5 + mulu d3,d5 ; Ergebnis steht im D5 + swap d1 ; jetzt unteres Wort Op1 mal unteres Op2 + mulu d1,d3 ; Ergebnis steht im D3 + swap d3 ; entspricht Verschiebung um 16 Bit + mulu d0,d1 ; jetzt oberes Wort Op1 mal unteres Op2 + + move.w d3,d0 ; zum ersten Zwischenergebnis dazu + add.l d5,d0 ; jetzt alles aufaddieren + add.l d1,d0 + beq.s fmul_res ; falls Mantisse Null auch Ergebnis Null + bmi.s fmul_rnd ; fuehrende Eins? dann zum Runden + +; Im Register D0.L befinden sich die oberen 32 Bit des Produktes, +; im oberen Wort von D3 die restlichen 16 Bit. + + tst.w d4 ; Exponent ist negativ ? + bmi.s fmul_unt ; ggf. Unterlauf behandeln + +fmul_nor: tst.w d4 ; Exponent = Null ? + beq.s fmul_rnd ; falls Null, dann zum Runden + roxl.l #1,d3 ; Im oberen Wort von D3 sind die + roxl.l #1,d0 ; niedrigsten Bits des Produktes + subq.w #1,d4 ; Exponent korrigieren + tst.l d0 ; Mantisse testen + bpl.s fmul_nor ; bis fuehrende Eins auftaucht + +fmul_rnd: add.l #$80,d0 ; Rundung + bcc.s fmul_nov + roxr.l #1,d0 ; Ueberlauf einschieben + addq.w #1,d4 ; Exponent korrigieren +fmul_nov: cmp.w #maxexpo,d4 ; Exponent-Ueberlauf ? + blt.s fmul_nue +fdiv_err: move.w #maxexpo,d4 ; Ueberlauf: Exponent = Maxexpo + clr.l d0 ; Mantisse = Null + bra.s fmul_den + +fmul_nue: tst.w d4 ; Exponent = Null ? + beq.s fmul_den ; falls Null, dann denormalisiert + lsl.l #1,d0 ; fuehrende Eins wird nicht abgespeichert + +fmul_den: move.b d4,d0 ; Exponent einsetzen + ror.l #8,d0 ; Form: eeee eeee ffff ... fffx + roxl.l #1,d2 ; Vorzeichen in Carry schieben + roxr.l #1,d0 ; und ins Ergebnis einsetzen + +fmul_res: movem.l (a7)+,d1-d5 ; Register restaurieren + rts + +fmul_zero: clr.l d0 ; Null erzeugen + bra.s fmul_res ; Ende, Ergebnis steht in D0.L + +fmul_unt: cmp.w #-24,d4 ; totaler Unterlauf ? + ble.s fmul_zero ; Dann ist das Ergebnis auf jeden Fall Null + neg.w d4 ; sonst Shift-Zaehler erzeugen + lsr.l d4,d0 ; und Zahl denormalisieren + clr.w d4 ; Exponent ist Null als Kennzeichen + bra.s fmul_rnd ; fuer eine denormalisierte Zahl + +;----------------------------------------------------------------------------- +; Division : D0.S = D0.S / D1.S + + ds 0 +S_fdiv: + addq.l #1,_fdiv_cnt.w + movem.l d1-d5,-(a7) ; benoetigte Register retten + move.l d0,d2 ; Operand 1 kopieren + eor.l d1,d2 ; EXOR um Vorzeichen zu bestimmen + + swap d0 ; Registerhaelften Operand 1 vertauschen + move.l d0,d3 ; Operand 1 ab jetzt in Register D3 + and.w #$7f,d3 ; Exponent und Vorzeichen loeschen + and.w #$7f80,d0 ; Exponent maskieren + beq.s fdiv_dn1 ; gleich Null: Zahl ist denormalisiert + bset #7,d3 ; implizite Eins einsetzen + sub.w #$0080,d0 ; Bias kompensieren + +fdiv_dn1: swap d1 ; jetzt Operand 2 behandeln + move.w d1,d4 + and.w #$7f,d1 + and.w #$7f80,d4 + beq.s fdiv_dn2 + bset #7,d1 + sub.w #$0080,d4 + +fdiv_dn2: sub.w d4,d0 ; Exponenten subtrahieren + move.w d0,d4 ; Exponent nach D4 kopieren + asr.w #7,d4 ; richtig positionieren + add.w #bias,d4 ; Bias addieren + cmp.w #-24,d4 ; totaler Ueberlauf ? + blt.s fmul_zero ; ja, dann ist Ergebnis Null + + swap d1 ; Form: 0fff ... ffff 0000 0000 + beq.s fdiv_err ; falls Divisor Null, dann wird + lsl.l #7,d1 ; als Ergebnis unendlich ausgegeben + swap d3 + beq.s fmul_zero ; falls Divident Null --> Ergebnis Null + lsl.l #7,d3 + +fdiv_nlp: btst #30,d1 ; ist der Divisor normalisiert ? + bne.s fdiv_nor ; ja, --> + addq.w #1,d4 ; nein, Exponent erhoehen + lsl.l #1,d1 ; Divisor verschieben bis Form 01ff .. + bra.s fdiv_nlp + +fdiv_nor: clr.l d0 ; Ergebnis vorbesetzen + add.w #25,d4 ; Exponent ist nicht groesser als Null + +fdiv_lop: move.l d3,d5 ; Divident zwischenspeichern + sub.l d1,d3 ; Divisor abziehen + eori #extend,ccr ; X-Bit invertieren + bcc.s fdiv_one ; kein Carry: Divisor passt + move.l d5,d3 ; zurueckkopieren (X-Bit unveraendert!) +fdiv_one: roxl.l #1,d0 ; Ergebnis aufbauen + lsl.l #1,d3 ; Divident verschieben + subq.w #1,d4 ; Exponent erniedrigen + beq.s fdiv_den ; falls Null, dann denormalisiert + btst #24,d0 ; fuehrende Eins in Ergebnis-Mantisse? + beq.s fdiv_lop ; nein, weiter rechnen + +fdiv_den: lsl.l #7,d0 ; Mantisse positionieren + beq fmul_res ; Null ? + bra fmul_rnd ; zum Runden +;----------------------------------------------------------------------------- +; Multiplikation mit einer Zweierpotenz: D0.S=D0.S * 2^(D1.W) + + ds 0 +S_fmul2: + addq.l #1,_fmul_cnt.w + movem.l d1-d2,-(a7) ; Register retten + move.l d0,d2 ; Vorzeichen in D2 Bit 31 merken + lsl.l #1,d0 ; Vorzeichen rausschieben + beq.s fmul2_zero ; falls Null, dann ist Ergebnis Null + rol.l #8,d0 ; Form: ffff ... fff0 eeee eeee + clr.w d2 ; auf Wort vorbereiten + move.b d0,d2 ; Exponent in D2 + beq.s fmul2_den + tst.w d1 ; Multiplikation oder Division? + bmi.s fmul2_div ; (neg. Exponent entspr. Div.) + + add.w d1,d2 ; Summe der Exponenten bilden + cmp.w #maxexpo,d2 ; Ueberlauf? + bge.s fmul2_over ; ja, Ergebnis ist unendlich +fmul2_res: move.b d2,d0 ; Ergebnisexponent einsetzen + ror.l #8,d0 ; Form: eeee eeee ffff ... fffx + roxl.l #1,d2 ; Vorzeichen ins X-Bit + roxr.l #1,d0 ; und ins Ergebnis einschieben +fmul2_zero: movem.l (a7)+,d1-d2 ; Register restaurieren + rts + +fmul2_over: move.w #maxexpo,d2 ; Unendlich: Exponent = maxexpo + clr.l d0 ; Mantisse = Null + bra.s fmul2_res + +fmul2_div: add.w d1,d2 ; Summe der Exponenten bilden + bgt.s fmul2_res ; Unterlauf? nein --> Ergebnis + ori #Extend,ccr ; implizite Eins real machen + roxr.l #1,d0 ; Form: 1fff ... ffff xxxx xxxx +fmul2_dnr: tst.w d2 ; Exponent = Null ? + beq.s fmul2_res ; ja, Ergebnis ist denormalisiert + lsr.l #1,d0 ; Mantisse denormalisieren + beq.s fmul2_zero ; totaler Unterlauf: Ergebnis ist Null + addq.w #1,d2 ; Exponent korrigieren + bra.s fmul2_dnr +fmul2_ddd: add.w d1,d2 ; Summe der Exponenten bilden + bra.s fmul2_dnr ; mit denormalisiereter Eingabe bearbeiten + +fmul2_den: tst.w d1 ; Multiplikation oder Division + bmi.s fmul2_ddd + clr.b d0 ; Form: ffff ... fff0 0000 0000 +fmul2_nor: lsl.l #1,d0 ; Mantisse nach links schieben + bcs.s fmul2_stp ; bis fuehrende Eins auftaucht + subq.w #1,d1 ; oder zweiter Exponent Null wird + bne.s fmul2_nor + bra.s fmul2_res ; Ergebnis abliefern +fmul2_stp: add.w d1,d2 ; Rest zum Exponenten addieren + bra.s fmul2_res ; Bias stimmt auch ( jetzt 127 statt 126) + +;----------------------------------------------------------------------------- +; Vergleich zweier Zahlen: cmp d0,d1 + +S_fcmp: + bclr #31,d0 ; Zahl 1 >=0 ? + bne.s fcmp_2 +fcmp_1: + bclr #31,d1 ; Zahl 2 >=0 ? + bne.s fcmp_12 +fcmp_11: + cmp.l d1,d0 ; beide Zahlen >=0 + rts ; dann Betraege vergleichen +fcmp_12: + moveq.l #1,d0 ; Zahl 1 >=0 und Zahl 2 <0 + cmp.l #-1,d0 + rts +fcmp_2: + bclr #31,d1 ; Zahl 2 >=0 ? + bne.s fcmp_22 +fcmp_21: + moveq.l #-1,d0 ; Zahl 1 <0 und Zahl 2 >=0 + cmp.w #1,d0 ; dann kleiner + rts +fcmp_22: + neg.l d0 + neg.l d1 + cmp.l d1,d0 ; beide Zahlen <0, dann ver- + rts ; kehrtherum vergleichen + + +;----------------------------------------------------------------------------- +; Longint-->Gleitkomma +; D0.L --> D0.S + +S_fitof: + movem.l d1-d2,-(a7) ; Register retten + tst.l d0 ; Integer ist Null ? + beq.s fitof_res; Ergebnis ist auch Null + smi d1 ; Vorzeichen in D1 merken + bpl.s fitof_pos + neg.l d0 ; ggf. Integer negieren +fitof_pos: move.w #bias+32,d2 ; Exponent vorbesetzen +fitof_shift: subq.w #1,d2 ; Mantisse verschieben + lsl.l #1,d0 ; bis fuehrende Eins rausfliegt + bcc.s fitof_shift + move.b d2,d0 ; Exponent einsetzen + ror.l #8,d0 ; Zahl positionieren + roxr.b #1,d1 ; Vorzeichen in X-Bit + roxr.l #1,d0 ; und ins Ergebnis +fitof_res: movem.l (a7)+,d1-d2 ; fertig + rts + +;----------------------------------------------------------------------------- +; Gleitkomma --> Longint: +; D0.S --> D0.L + +S_fftoi: + movem.l d1-d2,-(a7) ; Register retten + roxl.l #1,d0 ; Vorzeichen in Carry + scs d1 ; in D1 merken + rol.l #8,d0 ; Form: ffff ... fffx eeee eeee + move.b d0,d2 ; Exponent extrahieren + sub.b #bias,d2 ; Bias subtrahieren + bmi.s fftoi_zero ; kleiner Null -> Ergebnis = Null + cmp.b #31,d2 ; Ueberlauf? + bge.s fftoi_over + ori #extend,ccr ; Implizite Eins explizit machen + roxr.l #1,d0 + clr.b d0 ; Form: 1fff ... ffff 0000 0000 +fftoi_shft: + lsr.l #1,d0 ; jetzt Verschiebung bis + addq.b #1,d2 ; Exponent stimmt + cmp.b #31,d2 + bne.s fftoi_shft + tst.b d1 ; Zahl negativ ? + bpl.s fftoi_pos + neg.l d0 ; ggf. Ergebnis negieren +fftoi_pos: + movem.l (a7)+,d1-d2 ; Register wieder holen + rts +fftoi_zero: + clr.l d0 ; Unterlauf; Ergebnis ist Null + bra.s fftoi_pos +fftoi_over: + move.l #$7fffffff,d0 ; Ueberlauf: Maxint zurueckgeben + tst.b d1 ; positiv oder negativ ? + bpl.s fftoi_pos + not.l d0 ; Einser-Komplement erzeugt Minint + bra.s fftoi_pos + +;----------------------------------------------------------------------------- +; Quadratwurzel : D0.S-->D0.S + + ds 0 +fsqrt_domainerror: + move.l #$ffc00000,d0 ; -NAN zurueckgeben + movem.l (a7)+,d1-d4 + rts +fsqrt_sq0: + clr.l d0 + movem.l (a7)+,d1-d4 + rts +S_fsqrt: + addq.l #1,_fsqrt_cnt.w + movem.l d1-d4,-(a7) ; D1-D4 werden sonst zerstoert + move.l d0,d4 + bmi.s fsqrt_domainerror ; Fehler bei negativem Argument + swap d4 ; MSW des Arguments + and.l #$7f80,d4 ; Exponent isolieren + beq.s fsqrt_sq0 ; Zahl ist 0, wenn Exponent 0 + and.l #$007fffff,d0 ; Mantisse isolieren + sub.w #$7f*$80,d4 ; Exponent im Zweierkomplement + bclr #7,d4 ; Exponent ungerade? (und LSB auf 0) + beq.s fsqrt_evenexp + add.l d0,d0 ; ja: Mantisse * 2 + add.l #$01000000-$00800000,d0 ; Hidden Bit setzen, 1.Iteration + +fsqrt_evenexp: + ; 1. Iteration fuer geraden Exponenten: Hidden Bit nicht setzen + asr.w #1,d4 ; Exponent/2 mit Vorzeichen + add.w #$7f*$80,d4 ; Exponent wieder in Offset-Darst. + swap d4 ; neuen Exponenten im MSW aufheben + lsl.l #7,d0 ; x ausrichten + move.l #$40000000,d2 ; xroot nach erster Iteration + move.l #$10000000,d3 ; m2=2 << (MaxBit-1); +fsqrt_loop10: + move.l d0,d1 ; xx2 = x +fsqrt_loop11: + sub.l d2,d1 ; xx2 -= root + lsr.l #1,d2 ; xroot >>= 1 + sub.l d3,d1 ; x2 -= m2 + bmi.s fsqrt_dontset1 + move.l d1,d0 ; x = xx2 + or.l d3,d2 ; xroot += m2 + lsr.l #2,d3 ; m2 >>= 2 + bne.s fsqrt_loop11 + bra.s fsqrt_d0d1same +fsqrt_dontset1: + lsr.l #2,d3 ; m2 >>= 2 + bne.s fsqrt_loop10 ; Schleife 15* abarbeiten + ; Bit 22..8 + ; 17. Iteration (Bit 7) mit separatem Code durchfuehren: + move.l d0,d1 ; xx2 = x +fsqrt_d0d1same: + sub.l d2,d1 ; xx2 -= root + ror.l #1,d2 ; xroot >>= 1 mitsamt Carry... + swap d2 ; auf neues Alignment umstellen + subq.l #1,d1 ; Carry von 0-0x4000: x2 -= m2 + ; Teil 1 + bmi.s fsqrt_dontset7 + or.l #-$40000000,d1 ; 0 - 0x4000: x2 -= m2, Teil 2 + move.l d1,d0 ; x = xx2 + or.w #$4000,d2 ; xroot += m2 +fsqrt_dontset7: + swap d0 ; x auf neues Alignment umstellen + + move.w #$1000,d3 ; m2 - Bit 16..31 bereits 0 +fsqrt_loop20: + move.l d0,d1 ; xx2 = x +fsqrt_loop21: + sub.l d2,d1 ; xx2 -= xroot + lsr.l #1,d2 ; xroot >>= 1 + sub.l d3,d1 ; x2 -= m2 + bmi.s fsqrt_dontset2 + move.l d1,d0 ; x = xx2 + or.w d3,d2 ; xroot += m2 + lsr.w #2,d3 ; m2 >>= 2 + bne.s fsqrt_loop21 + bra.s fsqrt_finish +fsqrt_dontset2: + lsr.w #2,d3 ; m2 >>= 2 + bne.s fsqrt_loop20 ; Schleife 7 * abarbeiten (n=6..0) +fsqrt_finish: + sub.l d2,d0 ; Aufrunden notwendig ? + bls.s fsqrt_noinc + addq.l #1,d2 ; wenn ja, durchfuehren +fsqrt_noinc: + bclr #23,d2 ; Hidden Bit loeschen + or.l d4,d2 ; Exponent und Mantisse kombinieren + move.l d2,d0 ; Ergebnis + movem.l (a7)+,d1-d4 + rts ; Z-,S-, und V-Flag o.k. + +;----------------------------------------------------------------------------- +; Absolutbetrag: D0.S--> D0.S + + ds 0 + +S_fabs: bclr #31,d0 ; ganz einfach... + rts + +;----------------------------------------------------------------------------- +; Exponentialfunktion: D0.S--> D0.S + +; Die "krummen" Konstanten legen wir als hex ab, damit es keine Vergleichs- +; fehler durch Rundungsvarianzen gibt. + +S_fexp_Const0: dc.l $3FB8AA3B ; ld(exp(1.0)) = ld(e) = 1/ln(2) +S_fexp_ConstA: dc.l $3D0DF4E0 ; 0.034657359038 Polynomkonstanten +S_fexp_ConstB: dc.l $411F4606 ; 9.9545957821 +S_fexp_ConstC: dc.l $441A7E3A ; 617.97226953 +S_fexp_ConstD: dc.l $42AED5C2 ; 87.417498202 + + ds 0 +S_fexp: movem.l d1-d5,-(sp) + + bclr #31,d0 ; Vorzeichen loeschen und nach D2 retten + sne d2 + + move.l S_fexp_Const0(pc),d1 ; auf 2erpotenz umrechnen + bsr S_fmul + + move.l d0,d3 ; in Ganzzahlanteil und Nach- + bsr S_fftoi ; kommastellen (z) zerlegen + move.l d0,d4 ; Ganzzahlanteil nach D4 + bsr S_fitof + move.l d0,d1 + move.l d3,d0 + bsr S_fsub + move.l d0,d3 + + move.l d0,d1 ; z^2 berechnen + bsr S_fmul + move.l d0,d5 ; noch zu gebrauchen + + move.l S_fexp_ConstD(pc),d1 ; --> D+z^2 + bsr S_fadd + move.l d0,d1 ; --> C/(..) + move.l S_fexp_ConstC(pc),d0 + bsr S_fdiv + move.l d0,d1 ; --> B-(..) + move.l S_fexp_ConstB(pc),d0 + bsr S_fsub + move.l d3,d1 ; --> (..)-z + bsr S_fsub + exg d0,d5 ; Ergebnis retten + move.l S_fexp_ConstA(pc),d1 ; A*z^2 berechnen + bsr S_fmul + move.l d5,d1 ; ergibt Nenner + bsr S_fadd + move.l d0,d1 ; Quotient bilden + move.l d3,d0 + bsr S_fdiv + moveq #1,d1 ; verdoppeln + bsr S_fmul2 + move.l S_Const1(pc),d1 ; 1 addieren + bsr S_fadd + move.l d4,d1 ; Potenzieren + bsr S_fmul2 + + tst.b d2 ; war Argument negativ ? + beq.s S_fexp_ArgPos + move.l d0,d1 ; dann Kehrwert bilden + move.l S_Const1(pc),d0 + bsr S_fdiv + +Terminate: +S_fexp_ArgPos: movem.l (sp)+,d1-d5 + + rts + +;------------------------------------------------------------------------------ +; Sinus hyperbolicus: D0.S-->D0.S + +S_fsinh: + movem.l d1-d2,-(a7) ; Register retten + bsr S_fexp ; exp(x) berechnen + move.l d0,d2 ; in D2 merken + move.l d0,d1 ; exp(-x)=1/exp(x) berechnen + move.l #eins,d0 + bsr S_fdiv + move.l d0,d1 ; Teilergebnisse subtrahieren + move.l d2,d0 + bsr S_fsub + move.w #-1,d1 ; halbieren + bsr S_fmul2 + movem.l (a7)+,d1-d2 ; Register zurueck + rts + +;------------------------------------------------------------------------------ +; Cosinus hyperbolicus: D0.S-->D0.S + +S_fcosh: + movem.l d1-d2,-(a7) ; Register retten + bsr S_fexp ; exp(x) berechnen + move.l d0,d2 ; in D2 merken + move.l d0,d1 ; exp(-x)=1/exp(x) berechnen + move.l #eins,d0 + bsr S_fdiv + move.l d2,d1 ; Teilergebnisse addieren + bsr S_fadd + move.w #-1,d1 ; halbieren + bsr S_fmul2 + movem.l (a7)+,d1-d2 ; Register zurueck + rts + +;----------------------------------------------------------------------------- +; Tangens hyperbolicus: D0.S-->D0.S + +S_ftanh: + movem.l d1-d3,-(a7) ; Register sichern + bsr S_fexp ; exp(x) berechnen + move.l d0,d2 ; in D2 merken + move.l d0,d1 ; exp(-x)=1/exp(x) berechnen + move.l #eins,d0 + bsr S_fdiv + move.l d0,d3 ; in D3 merken + move.l d2,d1 ; Summe=Nenner berechnen + bsr S_fadd + exg d0,d2 ; jetzt exp(x) in D0, Nenner + move.l d3,d1 ; in D2 + bsr S_fsub ; Zaehler berechnen + move.l d2,d1 ; Quotient berechnen + bsr S_fdiv + movem.l (a7)+,d1-d3 ; Register zurueck + rts + +;----------------------------------------------------------------------------- +; Cotangens hyperbolicus: D0.S-->D0.S + +S_fcoth: + tst.l d0 ; Argument Null ? + beq.s S_fcoth_valerr ; dann zur Fehlerroutine + movem.l d1-d3,-(a7) ; Register sichern + bsr S_fexp ; exp(x) berechnen + move.l d0,d2 ; in D2 merken + move.l d0,d1 ; exp(-x)=1/exp(x) berechnen + move.l #eins,d0 + bsr S_fdiv + move.l d0,d3 ; in D3 merken + move.l d0,d1 ; Differenz=Nenner berechnen + move.l d2,d0 + bsr S_fsub + exg d0,d2 ; jetzt exp(x) in D0, Nenner + move.l d3,d1 ; in D2 + bsr S_fadd ; Zaehler berechnen + move.l d2,d1 ; Quotient berechnen + bsr S_fdiv + movem.l (a7)+,d1-d3 ; Register zurueck + rts +S_fcoth_valerr: + move.l #$7f800000,d0 ; +INF zurueckgeben + rts + +;----------------------------------------------------------------------------- +; nat. Logarithmus: D0.S-->D0.S + + ds 0 +S_fln: + tst.l d0 ; Argument <=0 ? + ble S_fln_errval + movem.l d1-d7,-(a7) ; Register retten + move.l d0,d3 ; Argument sichern + + move.l #eins,d1 ; Zahl>1? + bsr S_fsub ; ( dies ist sinnvoll bei + tst.l d0 ; Zahlen <<1 ); + smi d7 ; und die Vorzeichenumkehr merken + bpl.s S_fln_gr1 ; ja-->o.k. + move.l d3,d1 ; ansonsten Kehrwert bilden + move.l #eins,d0 + bsr S_fdiv + move.l d0,d3 + +S_fln_gr1: + clr.l d2 ; Merker = Null +S_fln_nrm: + move.l d3,d0 ; Zahl > 1 ? + move.l #eins,d1 + bsr S_fsub + bmi.s S_fln_isok + beq.s S_fln_isok + sub.l #$00800000,d3 ; ja-->Zahl durch 2 teilen... + addq.w #1,d2 ; ...und Merker erhoehen + bra.s S_fln_nrm ; nochmal probieren +S_fln_isok: + move.l d0,d3 ; Zahl um Eins erniedrigt abspeichern + move.l d0,d4 ; yz:=y + moveq.l #1,d6 ; zaehler:=1 + clr.l d5 ; Summe:=0 + bchg #31,d3 ; Multiplikator negativ +S_fln_loop: + move.l d6,d0 ; Zaehler in Gleitkomma wandeln + bsr S_fitof + move.l d0,d1 ; s:=s+yz/zaehler*vz + move.l d4,d0 + bsr S_fdiv + move.l d5,d1 + bsr S_fadd + cmp.l d5,d0 ; noch signifikant ? + beq.s S_fln_loopend + move.l d0,d5 + addq.w #1,d6 ; zaehler:=zaehler+1 + cmp.w #10,d6 ; Schleife fertig ? + beq.s S_fln_loopend + move.l d4,d0 ; yz:=yz*y + move.l d3,d1 + bsr S_fmul + move.l d0,d4 + bra.s S_fln_loop +S_fln_loopend: + move.l d2,d0 ; Merker in Gleitkomma + bsr S_fitof + move.l #ln2,d1 ; * ln(2) + bsr S_fmul + move.l d5,d1 ; s:=s+merker + bsr S_fadd + + tst.b d7 ; noch Vorzeichen tauschen ? + beq.s S_fln_end + bchg #31,d0 +S_fln_end: + movem.l (a7)+,d1-d7 ; Register zurueck + rts +S_fln_errval: + move.l #$ffc00000,d0 ; -NAN zurueckgeben + rts + +;----------------------------------------------------------------------------- +; 10er-Logarithmus : D0.S --> D0.S + +S_flog: + tst.l d0 ; Argument <=0 ? + ble.s S_flog_errval + bsr S_fln ; nat. Logarithmus bilden + move.l #ln10,d1 ; umrechnen + bsr S_fdiv + rts +S_flog_errval: + move.l #$ffc00000,d0 ; -NAN zurueckgeben + rts + +;----------------------------------------------------------------------------- +; Areasinus hyperbolicus: D0.S-->D0.S == ln[x+sqrt(x*x+1)] + +S_fasinh: + movem.l d1-d2,-(a7) + move.l d0,d2 ; Argument sichern + move.l d0,d1 ; quadrieren + bsr S_fmul + move.l #eins,d1 ; 1 addieren + bsr S_fadd + bsr S_fsqrt ; Wurzel ziehen + move.l d2,d1 ; Argument addieren + bsr S_fadd + bsr S_fln ; Logarithmus des ganzen + movem.l (a7)+,d1-d2 + rts + +;----------------------------------------------------------------------------- +; Areacosinus hyperbolicus: D0.S-->D0.S == ln[x+sqrt(x*x-1)] + +S_facosh: + movem.l d1-d2,-(a7) ; Register sichern + move.l d0,d2 ; Argument sichern + move.l #eins,d1 ; Argument <1 ? + bsr S_fcmp + bmi.s S_facosh_errval + move.l d2,d0 ; Argument zurueck + move.l d0,d1 ; quadrieren + bsr S_fmul + move.l #eins,d1 ; 1 abziehen + bsr S_fsub + bsr S_fsqrt ; Wurzel ziehen + move.l d2,d1 ; Argument addieren + bsr S_fadd + bsr S_fln ; Logarithmus des ganzen + movem.l (a7)+,d1-d2 ; Register zurueck + rts +S_facosh_errval: + movem.l (a7)+,d1-d2 ; Register zurueck + move.l #$ffc00000,d0 ; NAN zurueckgeben + rts + +;----------------------------------------------------------------------------- +; Areatangens hyperbolicus: D0.S-->D0.S == 0.5*ln((1+x)/(1-x)) + +S_fatanh: + movem.l d1-d2,-(a7) ; Register sichern + move.l d0,d2 ; Argument sichern + bclr #31,d0 ; Vorzeichen weg + cmp.l #eins,d0 + beq.s S_fatanh_inf ; =1-->INF + bhi.s S_fatanh_errval ; >1-->NAN + move.l d2,d1 ; Nenner berechnen + move.l #eins,d0 + bsr S_fsub + exg d0,d2 ; Zaehler berechnen + move.l #eins,d1 + bsr S_fadd + move.l d2,d1 ; Quotient daraus + bsr S_fdiv + bsr S_fln ; logarithmieren + move.w #-1,d1 ; halbieren + bsr S_fmul2 + movem.l (a7)+,d1-d2 ; Register zurueck + rts +S_fatanh_inf: + move.l #$ff000000,d0 ; vorzeichenbehaftete Unend- + roxr.l #1,d0 ; lichkeit + movem.l (a7)+,d1-d2 ; Register zurueck + rts +S_fatanh_errval: + move.l #$7fc00000,d0 ; NAN geben + movem.l (a7)+,d1-d2 ; Register zurueck + rts + +;----------------------------------------------------------------------------- +; Areakotangens hyperbolicus: D0.S--> D0.S == 0.5*ln((1+x)/(x-1)) + +S_facoth: + movem.l d1-d2,-(a7) ; Register sichern + move.l d0,d2 ; Argument sichern + roxl.l #1,d0 ; Vorzeichen in X-Flag + cmp.l #eins*2,d0 + beq.s S_facoth_inf ; =1-->INF + bmi.s S_facoth_errval ; <1-->NAN + move.l d2,d0 ; Nenner berechnen + move.l #eins,d1 + bsr S_fsub + exg d0,d2 ; Zaehler berechnen + move.l #eins,d1 + bsr S_fadd + move.l d2,d1 ; Quotient daraus + bsr S_fdiv + bsr S_fln ; logarithmieren + move.w #-1,d1 ; halbieren + bsr S_fmul2 + movem.l (a7)+,d1-d2 ; Register zurueck + rts +S_facoth_inf: + move.l #$ff000000,d0 ; vorzeichenbehaftete Unend- + roxr.l #1,d0 ; lichkeit + movem.l (a7)+,d1-d2 ; Register zurueck + rts +S_facoth_errval: + move.l #$7fc00000,d0 ; NAN geben + movem.l (a7)+,d1-d2 ; Register zurueck + rts + +;----------------------------------------------------------------------------- +; Kosinusfunktion: D0.S--> D0.S + + ds 0 +S_fcos: + movem.l d1-d6,-(a7) ; Register retten + bclr #31,d0 ; cos(-x)=cos(x) + + move.l #pi2,d1 ; auf Bereich 0..2*Pi reduzieren +S_fcos_subtr: + cmp.l d1,d0 ; x>=2*Pi ? + blo.s S_fcos_subend ; ja-->Ende + bchg #31,d1 ; fuer Subtraktion + bsr S_fadd ; reduzieren + bchg #31,d1 ; Subtrahend wieder richtig + bra.s S_fcos_subtr +S_fcos_subend: + cmp.l #pi,d0 ; x>Pi ? + blo.s S_fcos_nosub + exg d0,d1 ; ja-->cos(x)=cos(2*Pi-x) + bsr S_fsub +S_fcos_nosub: + move.l d0,d1 ; wir brauchen nur x^2 + bsr S_fmul + bset #31,d0 + move.l d0,d3 ; -x^2 in D3 + move.l d0,d4 ; D4 enthaelt laufende Potenz von x^2 + ; inkl. Vorzeichen + move.l #zwei,d5 ; D5 enthaelt laufende Fakultaet + move.l #eins,d2 ; D2 enthaelt Summe + moveq.l #2,d6 ; D6 enthaelt Zaehler +S_fcos_loop: + move.l d5,d1 ; s:=s+yz/zaehler + move.l d4,d0 + bsr S_fdiv + move.l d2,d1 + bsr S_fadd + cmp.l d2,d0 ; Veraendert sich Summe noch ? + beq.s S_fcos_end + move.l d0,d2 + addq.b #2,d6 ; i:=i+1 + cmp.b #22,d6 ; i=11 ? + beq.s S_fcos_end + move.w d6,d0 ; Fakultaet erhhen: *(2n-1)*(2n) + mulu.w d6,d0 ; =4*n^2-2*n + sub.w d6,d0 + bsr S_fitof ; dazumultiplizieren + move.l d5,d1 + bsr S_fmul + move.l d0,d5 + move.l d4,d0 ; yz:=yz*y + move.l d3,d1 + bsr S_fmul + move.l d0,d4 + bra.s S_fcos_loop +S_fcos_end: + ; Ergebnis bereits in D0 + movem.l (a7)+,d1-d6 ; Register zurueck + rts + +;---------------------------------------------------------------------------- +; Sinus : D0.S-->D0.S + +S_fsin: + move.l d1,-(a7) ; Register retten + move.l #pihalf,d1 ; sin(x)=cos(x-pi/2) + bsr S_fsub + bsr S_fcos + move.l (a7)+,d1 ; Register zurueck + rts + +;----------------------------------------------------------------------------- +; Tangens: D0.S-->D0.S + +S_ftan: + movem.l d1-d4,-(a7) ; Register retten + tst.l d0 ; Vorzeichen merken + smi d4 + bclr #31,d0 + move.l #pi,d1 ; auf Bereich 0..Pi reduzieren +S_ftan_subtr: + cmp.l d1,d0 ; x>=Pi ? + blo.s S_ftan_subend ; ja-->Ende + bchg #31,d1 ; fuer Subtraktion + bsr S_fadd ; reduzieren + bchg #31,d1 ; Subtrahend wieder richtig + bra.s S_ftan_subtr +S_ftan_subend: + move.l d0,d2 ; Argument merken + bsr S_fcos ; Nenner rechnen + move.l d0,d3 ; Nenner merken + move.l d0,d1 ; sqr(1-x^2) rechnen + bsr S_fmul + move.l d0,d1 + move.l #eins,d0 + bsr S_fsub + bsr S_fsqrt + move.l d3,d1 + bsr S_fdiv ; Quotient + tst.b d4 ; Vorzeichen dazu + beq.s S_ftan_noneg + bchg #31,d0 +S_ftan_noneg: + movem.l (a7)+,d1-d4 ; Register zurueck + rts + +;----------------------------------------------------------------------------- +; Kotangens: D0.S-->D0.S + +S_fcot: + movem.l d1-d4,-(a7) ; Register retten + tst.l d0 ; Vorzeichen merken + smi d4 + bclr #31,d0 + move.l #pi,d1 ; auf Bereich 0..Pi reduzieren +S_fcot_subtr: + cmp.l d1,d0 ; x>=Pi ? + blo.s S_fcot_subend ; ja-->Ende + bchg #31,d1 ; fuer Subtraktion + bsr S_fadd ; reduzieren + bchg #31,d1 ; Subtrahend wieder richtig + bra.s S_fcot_subtr +S_fcot_subend: + move.l d0,d2 ; Argument merken + bsr S_fcos ; Zaehler rechnen + move.l d0,d3 ; Zaehler merken + move.l d0,d1 ; sqr(1-x^2) rechnen + bsr S_fmul + move.l d0,d1 + move.l #eins,d0 + bsr S_fsub + bsr S_fsqrt + move.l d0,d1 + move.l d3,d0 + bsr S_fdiv ; Quotient + tst.b d4 ; Vorzeichen dazu + beq.s S_fcot_noneg + bchg #31,d0 +S_fcot_noneg: + movem.l (a7)+,d1-d4 ; Register zurueck + rts + +;----------------------------------------------------------------------------- +; Arcustangens: D0.S-->D0.S + +S_fatan: + movem.l d1-d6,-(a7) ; Register sichern + subq.l #2,a7 ; Platz fuer Hilfsvariablen + tst.l d0 ; Vorzeichen merken... + smi (a7) + bclr #31,d0 ; ...und loeschen + cmp.l #eins,d0 ; Argument>1 ? + shi 1(a7) ; ja : + bls.s S_fatan_no1 ; nein : + move.l d0,d1 ; ja : Kehrwert bilden + move.l #eins,d0 + bsr S_fdiv +S_fatan_no1: + move.l #3,d2 ; Zaehler initialisieren + move.l d0,d5 ; Summe initialisieren + move.l d0,d4 ; laufende Potenz = x^1 + move.l d0,d1 ; x^2 berechnen + bsr S_fmul + move.l d0,d3 + bset #31,d3 ; immer mit -x^2 multiplizieren +S_fatan_loop: + move.l d4,d0 ; naechste Potenz ausrechnen + move.l d3,d1 + bsr S_fmul + move.l d0,d4 + move.l d2,d0 ; Nenner in Gleitkomma + bsr S_fitof + move.l d0,d1 ; Division ausfuehren + move.l d4,d0 + bsr S_fdiv + move.l d5,d1 ; zur Summe addieren + bsr S_fadd + cmp.l d0,d5 ; noch signifikant ? + beq.s S_fatan_endloop ; nein-->Ende + move.l d0,d5 + addq.l #2,d2 ; Zaehler erhoehen + cmp.l #61,d2 ; fertig ? + bne.s S_fatan_loop +S_fatan_endloop: + move.l d5,d0 ; Ergebnis in D0 bringen + tst.b 1(a7) ; war Argument < 1 ? + beq.s S_fatan_not2 + bchg #31,d0 ; ja : Erg.=Pi/2-Erg + move.l #pihalf,d1 + bsr S_fadd +S_fatan_not2: + tst.b (a7) ; Vorzeichen dazu + beq.s S_fatan_not1 + bset #31,d0 +S_fatan_not1: + addq.l #2,a7 ; Hilfsvar. abraeumen + movem.l (a7)+,d1-d6 ; Register zurueck + rts + +;----------------------------------------------------------------------------- +; Arcuskotangens: D0.S-->D0.S + +S_facot: + move.l d1,-(a7) ; Register sichern + bsr S_fatan ; acot(x)=pi/2-atan(x) + bchg #31,d0 + move.l #pihalf,d1 + bsr S_fadd + move.l (a7)+,d1 ; Register zurueck + rts + +;----------------------------------------------------------------------------- +; Arcussinus: D0.S --> D0.S + +S_fasin: + movem.l d1-d2,-(a7) ; Register retten + move.l d0,d2 ; Argument merken + move.l d0,d1 ; Quadrat berechnen + bsr S_fmul + bset #31,d0 ; 1-x^2 bilden + move.l #eins,d1 + bsr S_fadd + tst.l d0 ; Sonderfaelle abfangen + bmi.s S_fasin_errval ; <0 geht nicht + beq.s S_fasin_inf ; Endwerte + bsr S_fsqrt ; Wurzel ... + move.l d0,d1 ; ... und Quotient + move.l d2,d0 + bsr S_fdiv + bsr S_fatan ; zuletzt das wichtigste + movem.l (a7)+,d1-d2 ; Register zurueck + rts +S_fasin_errval: + move.l #$7fc00000,d0 ; NAN zurueckgeben + movem.l (a7)+,d1-d2 ; Register zurueck + rts +S_fasin_inf: + move.l #pihalf,d0 ; +- pi/2 zurueckgeben + and.l #$80000000,d2 ; Vorzeichen dazu + or.l d2,d0 + movem.l (a7)+,d1-d2 ; Register zurueck + rts + +;----------------------------------------------------------------------------- +; Arcuskosinus: D0.S --> D0.S + +S_facos: + tst.l d0 ; Argument=0 ? + beq.s S_facos_inf + move.l d0,d2 ; Argument merken + move.l d0,d1 ; Quadrat berechnen + bsr S_fmul + bset #31,d0 ; 1-x^2 bilden + move.l #eins,d1 + bsr S_fadd + tst.l d0 ; Sonderfaelle abfangen + bmi.s S_facos_errval ; <0 geht nicht + bsr S_fsqrt ; Wurzel ... + move.l d2,d1 ; ... und Quotient + bsr S_fdiv + bsr S_fatan ; zuletzt das wichtigste + movem.l (a7)+,d1-d2 ; Register zurueck + rts +S_facos_errval: + move.l #$7fc00000,d0 ; NAN zurueckgeben + movem.l (a7)+,d1-d2 ; Register zurueck + rts +S_facos_inf: + move.l #pihalf,d0 ; +- pi/2 zurueckgeben + and.l #$80000000,d2 ; Vorzeichen dazu + or.l d2,d0 + movem.l (a7)+,d1-d2 ; Register zurueck + rts + +S_floatlibend: diff --git a/tests/t_parsys/float81.i68 b/tests/t_parsys/float81.i68 new file mode 100644 index 0000000..ed5a3dc --- /dev/null +++ b/tests/t_parsys/float81.i68 @@ -0,0 +1,293 @@ +;---------------------------------------------------------------------------- +; Fliesskommaroutinen fuer den PcPar68000 - Version mit 68881 + +;----------------------------------------------------------------------------- +; Definitionen: + +CoConst1 equ $32 ; Offsets im Konstantenrom +CoConstPi equ 0 ; des 6888x + +;----------------------------------------------------------------------------- +; Librarykopf: + + +S_Float81Lib: dc.l S_float81libend-S_float81libstart ; Laenge +S_float81libstart: + dc.l -1 ; Speicher fuer Zeiger + dc.b "FLOAT",0 ; Name + ds 0 + + +;----------------------------------------------------------------------------- +; Sprungtabelle: + + bra.l S_fadd_co68 + bra.l S_fsub_co68 + bra.l S_fmul_co68 + bra.l S_fdiv_co68 + bra.l S_fsqrt_co68 + bra.l S_float81libnop + bra.l S_float81libnop + bra.l S_fcmp_co68 + bra.l S_fitof_co68 + bra.l S_fftoi_co68 + bra.l S_fabs_co68 + bra.l S_float81libnop + bra.l S_float81libnop + bra.l S_float81libnop + bra.l S_float81libnop + bra.l S_fexp_co68 + bra.l S_fsinh_co68 + bra.l S_fcosh_co68 + bra.l S_ftanh_co68 + bra.l S_fcoth_co68 + bra.l S_float81libnop + bra.l S_float81libnop + bra.l S_float81libnop + bra.l S_fln_co68 + bra.l S_flog_co68 + bra.l S_fasinh_co68 + bra.l S_facosh_co68 + bra.l S_fatanh_co68 + bra.l S_facoth_co68 + bra.l S_float81libnop + bra.l S_float81libnop + bra.l S_fsin_co68 + bra.l S_fcos_co68 + bra.l S_ftan_co68 + bra.l S_fcot_co68 + bra.l S_float81libnop + bra.l S_float81libnop + bra.l S_float81libnop + bra.l S_float81libnop + bra.l S_fasin_co68 + bra.l S_facos_co68 + bra.l S_fatan_co68 + bra.l S_facot_co68 + +S_float81libnop: rts + +;---------------------------------------------------------------------------- + + fpu on +S_fadd_co68: + addq.l #1,_fadd_cnt.w + fmove.s d0,fp0 + fadd.s d1,fp0 + fmove.s fp0,d0 + rts + + +S_fsub_co68: + addq.l #1,_fadd_cnt.w + fmove.s d0,fp0 + fsub.s d1,fp0 + fmove.s fp0,d0 + rts + + +S_fmul_co68: + addq.l #1,_fmul_cnt.w + fmove.s d0,fp0 + fsglmul.s d1,fp0 + fmove.s fp0,d0 + rts + + +S_fdiv_co68: + addq.l #1,_fdiv_cnt.w + fmove.s d0,fp0 + fsgldiv.s d1,fp0 + fmove.s fp0,d0 + rts + + +S_fmul2_co68: + addq.l #1,_fmul_cnt.w + fmove.s d0,fp0 + fscale.w d1,fp0 + fmove.s fp0,d0 + rts + + +S_fitof_co68: + fmove.l d0,fp0 + fmove.s fp0,d0 + rts + + +S_fftoi_co68: + fmove.s d0,fp0 + fmove.l fp0,d0 + rts + + +S_fsqrt_co68: + addq.l #1,_fsqrt_cnt.w + fsqrt.s d0,fp0 + fmove.s fp0,d0 + rts + + +S_fabs_co68: bclr #31,d0 ; ganz einfach... + rts + + +S_fcmp_co68: + fmove.s d0,fp0 + fcmp.s d1,fp0 + fbeq.l S_fcmp_coeq ; Variante 1:gleich + fbgt.l S_fcmp_cogt ; Variante 2:groeer + + moveq #1,d0 ; Bedingung "kleiner" + cmp.w #2,d0 ; erzeugen + rts +S_fcmp_cogt: + moveq #2,d0 ; Bedingung "groesser" + cmp.w #1,d0 ; erzeugen + rts +S_fcmp_coeq: + cmp.w d0,d0 ; Bedingung "gleich" + rts ; erzeugen + + +S_fexp_co68: + fetox.s d0,fp0 + fmove.s fp0,d0 + rts + + +S_fsinh_co68: + fsinh.s d0,fp0 + fmove.s fp0,d0 + rts + + +S_fcosh_co68: + fcosh.s d0,fp0 + fmove.s fp0,d0 + rts + + +S_ftanh_co68: + ftanh.s d0,fp0 + fmove.s fp0,d0 + rts + + +S_fcoth_co68: + fmove.s d0,fp0 + fsinh.x fp0,fp1 + fcosh.x fp0 + fsgldiv.x fp1,fp0 + fmove.s fp0,d0 + rts + + +S_fln_co68: + flogn.s d0,fp0 + fmove.s fp0,d0 + rts + + +S_flog_co68: + flog10.s d0,fp0 + fmove.s fp0,d0 + rts + + +S_fasinh_co68: + fmove.s d0,fp0 + fmove.x fp0,fp1 + fmul.x fp1,fp0 + fmovecr.x #CoConst1,fp2 + fadd.x fp2,fp0 + fsqrt.x fp0 + fadd.x fp1,fp0 + flogn.x fp0 + fmove.s fp0,d0 + rts + + +S_facosh_co68: + fmove.s d0,fp0 + fmove.x fp0,fp1 + fmul.x fp1,fp0 + fmovecr.x #CoConst1,fp2 + fsub.x fp2,fp0 + fsqrt.x fp0 + fadd.x fp1,fp0 + flogn.x fp0 + fmove.s fp0,d0 + rts + + +S_fatanh_co68: + fatanh.s d0,fp0 + fmove.s fp0,d0 + rts + + +S_facoth_co68: + fmovecr.x #CoConst1,fp0 + fdiv.s d0,fp0 + fatanh.x fp0 + fmove.s fp0,d0 + rts + + +S_fcos_co68: + fcos.s d0,fp0 + fmove.x fp0,d0 + rts + + +S_fsin_co68: + fsin.s d0,fp0 + fmove.s fp0,d0 + rts + + +S_ftan_co68: + ftan.s d0,fp0 + fmove.s fp0,d0 + rts + + +S_fcot_co68: + fsincos.s d0,fp0:fp1 + fsgldiv.x fp1,fp0 + fmove.s fp0,d0 + rts + + +S_fatan_co68: + fatan.s d0,fp0 + fmove.s fp0,d0 + rts + + +S_facot_co68: + fatan.s d0,fp1 + fmovecr.x #CoConstPi,fp0 + fscale.w #-1,fp0 + fsub.x fp1,fp0 + fmove.s fp0,d0 + rts + + +S_fasin_co68: + fasin.s d0,fp0 + fmove.s fp0,d0 + rts + + +S_facos_co68: + facos.s d0,fp0 + fmove.s fp0,d0 + rts + +S_float81libend: + + fpu off + diff --git a/tests/t_parsys/parsys.i68 b/tests/t_parsys/parsys.i68 new file mode 100644 index 0000000..e5a2569 --- /dev/null +++ b/tests/t_parsys/parsys.i68 @@ -0,0 +1,115 @@ +; Includedatei PcPar-System +; vor dem Programm mit include einbinden + +;---------------------------------------------------------------------------- +; offizieller Datenbereich: + + shared S_RegSave,S_MemEnd,S_ParNo,S_CPUNo + shared _fadd_cnt,_fmul_cnt,_fdiv_cnt,_fsqrt_cnt + + org $400 +S_MemEnd: + ds.l 1 ; Speicherende ( Default 64K ) +S_SysStart: + ds.l 1 ; Anfang des Systemcodes +S_ParNo: ; vom PC geschiebene Werte + ds.w 1 ; Parallelrechneradresse +S_LibAdr: ; Adresse der Library- + ds.l 1 ; sprungtabelle +_fadd_cnt: ; Anzahl ausgefuehrter Gleit- + ds.l 1 ; kommaadditionen/subtraktion +_fmul_cnt: ; dito Multiplikation + ds.l 1 +_fdiv_cnt: ; dito Division + ds.l 1 +_fsqrt_cnt: ; dito Quadratwurzel + ds.l 1 +S_FreeMemEnd: + ds.l 1 ; Ende freien Speichers +S_CPUNo: + ds.w 1 ; CPU-Typ: 0 = 68008 + ; 1 = 68000 + ; 2 = 68010 + ; 3 = 68020 + ; 4 = 68030 + ; Byte 1 : $01 = 68881 + ; $02 = 68882 + ; $10 = 68851 + org $600 + +S_SSPEnd: + ds.l 1 ; Anfang des Systemstacks +S_ResVecSave: ; Sicherung Resetvektor + ds.l 1 +S_RegSave: ; Registersicherung + ds.l 17 ; wird vom PC veraendert +S_ExVec: ; Exceptionvektor + ds.w 1 +S_LibStart: + ds.l 1 ; Anfang Librarykette + org $800 + +;----------------------------------------------------------------------------- +; Libraryoffsets : + +fadd equ $0000 +fsub equ $0004 +fmul equ $0008 +fdiv equ $000c +fmul2 equ $0010 +fsqrt equ $0014 +fabs equ $0018 + +fcmp equ $0020 +fitof equ $0024 +fftoi equ $0028 + +fexp equ $0040 +fsinh equ $0044 +fcosh equ $0048 +ftanh equ $004c +fcoth equ $0050 + +fln equ $0060 +flog equ $0064 +fasinh equ $0068 +facosh equ $006c +fatanh equ $0070 +facoth equ $0074 + +fsin equ $0080 +fcos equ $0084 +ftan equ $0088 +fcot equ $008c + +fasin equ $00a0 +facos equ $00a4 +fatan equ $00a8 +facot equ $00ac + +;---------------------------------------------------------------------------- +; Konstanten fuer Betriebssystemaufrufe: + +TrapProgEnd equ 15 ; Trap fuer Programmende + +TrapTglSStep equ 14 ; Trap Einzelschritt an/aus + +TrapLibCtrl equ 13 ; Trap Libraryverwaltung +LibCtrlInstall equ 0 +LibCtrlGetAdr equ 1 + +;---------------------------------------------------------------------------- +; andere Konstanten: + +S_Latch equ $fffffffe ; Adresse der I/O-Latches + +is68008 equ $00 ; Prozessorcode 68008 +is68000 equ $01 ; " 68000 +is68010 equ $02 ; " 68010 +is68020 equ $03 ; " 68020 +is68030 equ $04 ; " 68030 +has68881 equ $01 ; " 68881 +has68882 equ $02 ; " 68882 +hasMMU equ $10 ; " 68851 +intMMU equ $20 ; " interne MMU + diff --git a/tests/t_parsys/t_parsys.asm b/tests/t_parsys/t_parsys.asm new file mode 100644 index 0000000..8afe6f3 --- /dev/null +++ b/tests/t_parsys/t_parsys.asm @@ -0,0 +1,994 @@ + include parsys.i68 + + page 60 + cpu 68000 + +;----------------------------------------------------------------------------- +; Die Exceptionvektoren: + + supmode on + + org $00000000 ; Die Vektoren + dc.l 0 ; Adresse vom Stack (Dummy) + dc.l Start ; erster Start + dc.l ex_vec2 ; Busfehler + dc.l ex_vec3 ; Adressfehler + dc.l ex_vec4 ; Illegaler Befehl + dc.l ex_vec5 ; Division durch Null + dc.l ex_vec6 ; Befehl CHK + dc.l ex_vec7 ; Befehl TRAPV + dc.l ex_vec8 ; Privilegverletzung + dc.l StepProc ; Ablaufverfolgung + dc.l ex_vec10 ; Line-A --> Gleitkomma + dc.l S_LineF ; Line-F --> 68881-Emulator + dc.l ex_vec12 ; Reserviert + dc.l ex_vec13 ; Koprozessor-Protokollfehler + dc.l ex_vec14 ; illegaler FRESTORE-Frame + dc.l ex_vec15 ; nicht initialisierter Unterbrechungsvektor + dc.l ex_vec16 ; Reserviert + dc.l ex_vec17 ; Reserviert + dc.l ex_vec18 ; Reserviert + dc.l ex_vec19 ; Reserviert + dc.l ex_vec20 ; Reserviert + dc.l ex_vec21 ; Reserviert + dc.l ex_vec22 ; Reserviert + dc.l ex_vec23 ; Reserviert + dc.l ex_vec24 ; Unechte Unterbrechung + dc.l ex_vec25 ; autovektoriell 1 + dc.l ex_vec26 ; autovektoriell 2 + dc.l ex_vec27 ; autovektoriell 3 + dc.l ex_vec28 ; autovektoriell 4 + dc.l ex_vec29 ; autovektoriell 5 + dc.l ex_vec30 ; autovektoriell 6 + dc.l ex_vec31 ; autovektoriell 7 + dc.l PcSysCall ; Trap #0 --> PC-Kommunikation + dc.l ex_vec33 ; Trap #1 + dc.l ex_vec34 ; Trap #2 + dc.l ex_vec35 ; Trap #3 + dc.l ex_vec36 ; Trap #4 + dc.l ex_vec37 ; Trap #5 + dc.l ex_vec38 ; Trap #6 + dc.l ex_vec39 ; Trap #7 + dc.l ex_vec40 ; Trap #8 + dc.l ex_vec41 ; Trap #9 + dc.l ex_vec42 ; Trap #10 + dc.l ex_vec43 ; Trap #11 + dc.l ex_vec44 ; Trap #12 + dc.l S_LibFun ; Trap #13 --> Libraryverwaltung + dc.l S_StepTgl ; Trap #14 --> Trace an/aus + dc.l S_ProgEnd ; Trap #15 --> Programmende + dc.l ex_vec48 ; BSUN in FPU gesetzt + dc.l ex_vec49 ; FPU inexaktes Ergebnis + dc.l ex_vec50 ; FPU Division durch 0 + dc.l ex_vec51 ; FPU Unterlauf + dc.l ex_vec52 ; FPU Operandenfehler + dc.l ex_vec53 ; FPU Ueberlauf + dc.l ex_vec54 ; FPU signaling NAN + dc.l ex_vec55 ; reserviert + dc.l ex_vec56 ; MMU Konfigurationsfehler + dc.l ex_vec57 ; MMU Illegale Operation + dc.l ex_vec58 ; MMU Zugriffsfehler + ; Vektoren 59..255 frei + +;---------------------------------------------------------------------------- +; Installationssequenz: + + org $800 +start: + clr.w S_Latch.w ; Port nullen + + and.b #$fc,S_MemEnd+3.w ; Speichergroesse auf Lang- + ; wortadresse ausrichten + move.l S_MemEnd.w,a7 ; SSP setzen + + lea -256(a7),a0 ; SSP-Anfang in A0 + move.l a0,S_SSPEnd.w ; sichern + + lea S_End.w,a1 ; Codelaenge berechnen + lea S_Start.w,a2 + sub.l a2,a1 ; A1=Laenge Systemcode + moveq #4,d0 ; auf mehrfaches von 4 aus- + sub.w a1,d0 ; richten + and.l #3,d0 + add.l d0,a1 + + sub.l a1,a0 ; Start des Systemcodes rechnen + move.l a0,S_SysStart.w ; sichern + move.l a0,$4.w ; =Programmstart + + move.l a1,d0 ; Systemcode umkopieren + lsr.l #2,d0 ; =Zahl Langworttransfers + subq.w #1,d0 ; wg. DBRA +S_SysCopy: move.l (a2)+,(a0)+ + dbra d0,S_SysCopy + + sub.l a2,a0 ; Verschiebedifferenz rechnen + move.l a0,d1 + + lea 8.w,a1 ; alle Vektoren relozieren + moveq #45,d0 +S_RelVec: add.l d1,(a1)+ + dbra d0,S_RelVec + + move.l S_SysStart.w,a1 ; obere Speichergrenze in USP... + move a1,usp + move.l a1,S_FreeMemEnd.w ; und Variable + + move.l #-1,S_LibStart.w; Librarykette leer + + lea S_floatlib.w,a0 ; passende FloatLib installieren + btst #0,S_Latch+1.w ; 68881 vorhanden ? + bne.s S_NoCo81 + lea S_float81lib.w,a0 ; ja-->andere Library +S_NoCo81: moveq #LibCtrlInstall,d0 ; einschreiben + trap #TrapLibCtrl + + moveq #LibCtrlGetAdr,d0 ; Adresse holen + lea S_LibName.w,a0 + trap #TrapLibCtrl + move.l d0,S_LibAdr.w + + move.l 4*4.w,a4 ; Exceptionvektoren 4 und 11 retten + move.l 11*4.w,a5 + move.l sp,a6 ; SP retten + move.l #S_NoCPU,4*4.w ; neue Exceptionhandler einschreiben + move.l #S_NoMMU,11*4.w + moveq #is68008,d1 ; Prozessorcode loeschen + + cpu 68030 ; fuer zus. Befehle + + ori #1,ccr ; 68008 ausfiltern + moveq #is68000,d1 + + movec vbr,d0 ; geht erst ab 68010 + moveq #is68010,d1 + + extb d0 ; geht erst ab 68020 + moveq #is68020,d1 + + cpu 68000 ; nicht mehr gebraucht + fpu on ; dafuer dies + +S_NoCPU: btst #0,S_Latch+1.w ; FPU vorhanden ? + bne.s S_NoFPU ; nein--> + or.w #has68881,d1 ; ja : 68881 annehmen + fnop ; FPU idle machen, damit im folgenden + fsave -(sp) ; ein idle frame gespeichert wird + cmp.b #$18,1(sp) ; Framelaenge=$18 fuer 68881, $38 fuer 882 + beq.s S_NoFPU + add.w #(has68882-has68881),d1 ; 68882 eintragen + + fpu off ; FPU nicht mehr gebraucht + pmmu on ; dafuer die MMU + +S_NoFPU: move.l a4,4*4.w ; Exception 4 zuruecksetzen + pflusha ; dies versteht auch die 68030-MMU + add.w #hasMMU,d1 ; gefunden: Flag dazu + move.l #S_SmallMMU,11*4.w ; testen ob Schmalspur-MMU + psave -(sp) + bra.s S_NoMMU ; Ergebnis 68020/68851 + +S_SmallMMU: move.b #is68030,d1 ; 68030 eintragen (nicht MOVEQ!!) + add.w #(intMMU-hasMMU),d1 ; Code interne MMU + +S_NoMMU: move.l a5,11*4.w ; Line-F-Vektor zuruecksetzen + move.l a6,sp ; SP restaurieren + move.w d1,S_CPUNo.w ; Ergebnis einschreiben + + trap #TrapProgEnd + +S_LibName: dc.b "FLOAT",0 + +;---------------------------------------------------------------------------- +; Gleitkommalibrary, ohne 68881: + + supmode off + + include float.i68 + +;---------------------------------------------------------------------------- +; Gleitkommalibrary, mit 68881: + + supmode off + + include float81.i68 + +;---------------------------------------------------------------------------- +; Die Startsequenz: + + supmode on + +S_Start: clr.w S_Latch.w ; Ports loeschen + clr.l _fadd_cnt.w ; Zielvariablen loeschen + clr.l _fmul_cnt.w + clr.l _fdiv_cnt.w + clr.l _fsqrt_cnt.w + + move.l S_MemEnd.w,d0 ; SSP an Speicherende legen + move.l d0,$0.w ; Neben Resetvekor vermerken + move.l d0,a7 ; SSP setzen + move.l S_FreeMemEnd.w,a0 ; USP liegt am Speicherende + move a0,usp + + andi #$dfff,sr ; In Usermodus schalten + jmp Start.w ; zum Programmstart + +;---------------------------------------------------------------------------- +; Die Ausnahmebehandlungsprozeduren: + +ex_vec2: + move.w #2,S_ExVec.w + bra.l ex_handle +ex_vec3: + move.w #3,S_ExVec.w + bra.l ex_handle +ex_vec4: + move.w #4,S_ExVec.w + bra.l ex_handle +ex_vec5: + move.w #5,S_ExVec.w + bra.l ex_handle +ex_vec6: + move.w #6,S_ExVec.w + bra.l ex_handle +ex_vec7: + move.w #7,S_ExVec.w + bra.l ex_handle +ex_vec8: + move.w #8,S_ExVec.w + bra.l ex_handle +ex_vec10: + move.w #10,S_ExVec.w + bra.l ex_handle +ex_vec11: + move.w #0,S_Control+S_Response.w ; FPU resetten + move.w #11,S_ExVec.w + bra.l ex_handle +ex_vec12: + move.w #12,S_ExVec.w + bra.l ex_handle +ex_vec13: + move.w #13,S_ExVec.w + bra.l ex_handle +ex_vec14: + move.w #14,S_ExVec.w + bra.l ex_handle +ex_vec15: + move.w #15,S_ExVec.w + bra.l ex_handle +ex_vec16: + move.w #16,S_ExVec.w + bra.l ex_handle +ex_vec17: + move.w #17,S_ExVec.w + bra.l ex_handle +ex_vec18: + move.w #18,S_ExVec.w + bra.l ex_handle +ex_vec19: + move.w #19,S_ExVec.w + bra.l ex_handle +ex_vec20: + move.w #20,S_ExVec.w + bra.l ex_handle +ex_vec21: + move.w #21,S_ExVec.w + bra.l ex_handle +ex_vec22: + move.w #22,S_ExVec.w + bra.l ex_handle +ex_vec23: + move.w #23,S_ExVec.w + bra.l ex_handle +ex_vec24: + move.w #24,S_ExVec.w + bra.l ex_handle +ex_vec25: + move.w #25,S_ExVec.w + bra.l ex_handle +ex_vec26: + move.w #26,S_ExVec.w + bra.l ex_handle +ex_vec27: + move.w #27,S_ExVec.w + bra.l ex_handle +ex_vec28: + move.w #28,S_ExVec.w + bra.l ex_handle +ex_vec29: + move.w #29,S_ExVec.w + bra.l ex_handle +ex_vec30: + move.w #30,S_ExVec.w + bra.l ex_handle +ex_vec31: + move.w #31,S_ExVec.w + bra.l ex_handle +ex_vec33: + move.w #33,S_ExVec.w + bra.l ex_handle +ex_vec34: + move.w #34,S_ExVec.w + bra.l ex_handle +ex_vec35: + move.w #35,S_ExVec.w + bra.l ex_handle +ex_vec36: + move.w #36,S_ExVec.w + bra.l ex_handle +ex_vec37: + move.w #37,S_ExVec.w + bra.l ex_handle +ex_vec38: + move.w #38,S_ExVec.w + bra.l ex_handle +ex_vec39: + move.w #39,S_ExVec.w + bra.l ex_handle +ex_vec40: + move.w #40,S_ExVec.w + bra.l ex_handle +ex_vec41: + move.w #41,S_ExVec.w + bra.l ex_handle +ex_vec42: + move.w #42,S_ExVec.w + bra.l ex_handle +ex_vec43: + move.w #43,S_ExVec.w + bra.l ex_handle +ex_vec44: + move.w #44,S_ExVec.w + bra.l ex_handle +ex_vec48: + move.w #48,S_ExVec.w + bra.l ex_handle +ex_vec49: + move.w #49,S_ExVec.w + bra.l ex_handle +ex_vec50: + move.w #50,S_ExVec.w + bra.l ex_handle +ex_vec51: + move.w #51,S_ExVec.w + bra.l ex_handle +ex_vec52: + move.w #52,S_ExVec.w + bra.l ex_handle +ex_vec53: + move.w #53,S_ExVec.w + bra.l ex_handle +ex_vec54: + move.w #54,S_ExVec.w + bra.l ex_handle +ex_vec55: + move.w #55,S_ExVec.w + bra.l ex_handle +ex_vec56: + move.w #56,S_ExVec.w + bra.l ex_handle +ex_vec57: + move.w #57,S_ExVec.w + bra.l ex_handle +ex_vec58: + move.w #58,S_ExVec.w + +ex_handle: + movem.l d0-d7/a0-a7,S_RegSave.w ; Wert der Register abspeichern + move usp,a0 + move.l a0,S_RegSave+64.w + lea S_Latch.w,a0 + move.w S_ExVec.w,d0 ; Vektornr. holen + move.b d0,1(a0) ; Fehlernr. ausgeben +ex_infinite: + move.b d0,d1 ; Die LED n-mal blinken lassen ; Die LED n-mal blinken lassen +ex_blink: + bset #0,(a0) ; LED an + bsr.s ex_wait + bclr #0,(a0) ; LED aus + bsr.s ex_wait + subq.b #1,d1 + bne.s ex_blink + move.b #$05,d1 ; eine Pause einlegen +ex_pause: + bsr.s ex_wait + subq.b #1,d1 + bne.s ex_pause + bra.s ex_handle ; und alles von vorne + +ex_wait: + move.l d0,-(a7) ; Register retten + move.l #$50000,d0 ; ungefaehr 1/2 Sekunde +ex_wloop: ; Register herunterzaehlen + subq.l #1,d0 + bne.s ex_wloop + move.l (a7)+,d0 ; D0 wieder zurueck + rts + +;---------------------------------------------------------------------------- +; Einzelschrittverfolgung: + +StepProc: + clr.b S_Latch+1.w + movem.l d0-d7/a0-a7,S_RegSave.w ; Register retten + move usp,a0 + move.l a0,S_RegSave+64.w + move.l $4.w,S_ResVecSave.w ; Resetvektor sichern + lea S_Restart(pc),a0 ; am Punkt S_StepBack wacht + move.l a0,$4.w ; der PcPar wieder auf + move.b #9,S_Latch+1.w ; ParMon-Aufruf ausgeben + stop #$2000 ; hier geht es nur mit einem + ; Reset weiter + +;---------------------------------------------------------------------------- +; Routinen zur Kommunikation mit dem PC (Trap 0) + +PcSysCall: + clr.b S_Latch+1.w + movem.l d0-d7/a0-a7,S_RegSave.w ; Register retten + move usp,a0 + move.l a0,S_RegSave+64.w + move.l $4.w,S_ResVecSave.w ; Resetvektor sichern + lea S_Restart(pc),a0 ; am Punkt S_Restart wacht + move.l a0,$4.w ; der PcPar wieder auf + move.b #$40,S_Latch+1.w ; PC-Aufruf ausgeben + stop #$2000 ; hier geht es nur mit einem + +S_Restart: + clr.b S_Latch+1.w ; Systemanfrage loeschen + move.l S_ResVecSave.w,$4.w ; Resetvektor zurueck + move.l S_RegSave+64.w,a0 + move a0,usp + movem.l S_RegSave.w,d0-d7/a0-a7 ; Register zurueckholen + rte ; das war's + +;---------------------------------------------------------------------------- +; Libraryverwaltung : Trap #13 +; +; Struktur einer Library : +; +; Adresse 0: Laenge in Bytes (1 <= Laenge <= 256k) +; Adresse 4: Dummyzeiger =-1 (vom System verwendet) \ +; Adresse 8: Libraryname als ASCIIZ-String | kopierter Block +; Adresse n: Sprungtabelle | +; Adresse m: Librarycode, private Daten / +; +; der gesamte Librarycode muss lageunabhaengig geschrieben sein ! +; +; definierte Unterfunktionen: +; +; D0.L=0 : Library installieren +; D0.L=1 : Libraryzeiger holen +; +;---------------------------------------------------------------------------- + +; Subfunktion 0: Library von Adresse 0 installieren: +; Eingabe: A0=Startadresse der Library +; Ausgabe: keine + +S_LibFun: movem.l d1-d2/a1-a2,-(a7) ; Register sichern + tst.l d0 ; ist es Funktion 0 ? + bne.s S_LibFun1 ; nein-->bei Funktion 1 weitertesten + + move.l (a0),d0 ; Laenge Library holen + addq.l #3,d0 ; auf Doppelworte aufrunden + and.b #$fc,d0 + moveq #1,d1 + cmp.l #$40000,d0 ; Maximalgroesse ueberschritten ? + bge.l S_LibErr ; ja-->Ende mit Fehler Nr.1 + + move usp,a1 ; Userstack holen + move.l S_FreeMemEnd.w,d2 ; mom. belegte Stackmenge berechnen + sub.l a1,d2 + move.l a1,a2 ; neue Untergrenze in A2 rechnen + sub.l d0,a2 + moveq #2,d1 + cmp.l #$800,a2 ; unter abs. Untergrenze gesunken ? + ble.l S_LibErr ; ja-->Ende mit Fehler Nr.2 + + move a2,usp ; neuen Userstack einschreiben + lsr.l #1,d2 ; Stackgroesse in Worten + bra.s S_LibStckEnd ; damit Ende, falls kein Stack belegt + +S_LibStckCpy: move.w (a1)+,(a2)+ ; Userstack umkopieren +S_LibStckEnd: dbra d2,S_LibStckCpy + + move.l S_FreeMemEnd.w,a1 ; Startadresse der Library rechnen + sub.l d0,a1 ; =altes Speicherende-Laenge + addq.l #4,a0 ; Quellzeiger weitersetzen + move.l S_LibStart.w,d1 ; bisheriges Ende der Kette holen + move.l d1,(a0) ; in neue Library eintragen + move.l a1,S_FreeMemEnd.w ; Speichergrenze heruntersetzen + move.l a1,S_LibStart.w ; neuen Kettenanfang eintragen + + lsr.l #2,d0 ; Laenge in Doppelworte umrechnen + subq.w #1,d0 ; wg. DBRA + +S_LibInstLoop: move.l (a0)+,(a1)+ ; Library umkopieren + dbra d0,S_LibInstLoop + + bra.l S_LibOK ; Ende ohne Fehler + +; Subfunktion 1: Library finden, deren Name ab (A0) als ASCIIZ steht: +; Eingabe: A0=Startadresse des ASCIIZ-Strings +; Ausgabe: D0=Startadresse der Sprungtabelle + +S_LibFun1: subq.l #1,d0 ; ist es Funktion 1 ? + bne.s S_LibFun2 ; nein-->bei Funktion 2 weitertesten + + move.l S_LibStart.w,a2 ; Wurzelzeiger der Kette holen + +S_LibGetLoop: moveq #3,d1 ; Kettenende erreicht ? + move.l a2,d0 + addq.l #1,d0 ; wird durch -1 angezeigt + beq.l S_LibErr ; ja-->Ende mit Fehler + + move.l a0,d0 ; Startadresse Vergleichsstring retten + lea 4(a2),a1 ; A1 zeigt auf zu testenden Namen +S_LibGetComp: cmpm.b (a0)+,(a1)+ ; ein Zeichen vergleichen + bne.s S_LibGetNext ; ungleich-->weiter in Kette + tst.b -1(a0) ; War das das Ende ? + beq.s S_LibGetFnd ; ja-->Heureka! + bra.s S_LibGetComp ; ansonsten naechstes Zeichen vergleichen + +S_LibGetNext: move.l (a2),a2 ; weiter auf Nachfolger in Kette + move.l d0,a0 ; A0 auf Referenzstringanfang + bra.s S_LibGetLoop + +S_LibGetFnd: move.l a1,d0 ; Libraryadresse gerade machen + addq.l #1,d0 + bclr #0,d0 + + bra.l S_LibOK ; Ende ohne Fehler + +S_LibFun2: moveq #127,d1 ; unbekannte Funktion: + bra.l S_LibErr + +S_LibErr: move.l d1,d0 ; Fehlercode in D0 holen + movem.l (a7)+,d1-d2/a1-a2 ; Register zurueck + or.b #1,1(a7) ; Carry setzen + rte + +S_LibOK: movem.l (a7)+,d1-d2/a1-a2 ; Register zurueck + and.b #$fe,1(a7) ; Carry loeschen + rte + +;---------------------------------------------------------------------------- +; Tracemode ein/aus: + +S_StepTgl: + andi #$7fff,sr ; bitte hier kein Trace! + bclr #7,(a7) ; altes T-Flag loeschen + btst #0,1(a7) + bne.s S_StepOn ; C=1-->Tracemodus an + rte ; C=0-->fertig +S_StepOn: + bset #7,(a7) ; T-Flag setzen + rte + +;---------------------------------------------------------------------------- +; Programmende (Trap 15) + +S_ProgEnd: lea S_Start(pc),a0 ; Startvektor zurueck + move.l a0,4.w + move.b #$ff,S_Latch+1.w ; "Ich bin fertig" + stop #$2000 ; und Ende + +;---------------------------------------------------------------------------- +; Line-F-Exception + +S_Response equ $fffffe00 ; In a6 (Coprozessor-Register) +S_Control equ $02 ; Alle weiteren Register relativ +S_Save equ $04 ; zu "Response" +S_Restore equ $06 +S_Command equ $0a ; in a5 +S_Condition equ $0e +S_Operand equ $10 ; in a4 +S_Reg_Selec equ $14 +S_Ins_Add equ $18 + + supmode on + +S_LineF: btst #0,S_Latch+1.w ; Ist ein Koprozessor vorhanden ? + bne ex_vec11 ; nein-->normaler Line-F + + movem.l d0-d7/a0-a6,S_RegSave.w ; Register retten + move.l usp,a0 ; USP retten + move.l a0,S_RegSave+60.w ; (geht nur ueber Umweg) + lea S_Response.w,a6 ; #response nach A6 + lea S_Command(a6),a5 ; #command nach A5 + lea S_Operand(a6),a6 ; #operand nach A4 + lea S_RegSave.w,a3 ; #dregs nach A3 + move.l 2(a7),a0 ; PC nach A0 + move.w (a0),d1 ; Kommando nach D1 +S_again: ; Einsprung fuer weitere FPU-Befehle + and.w #%0000000111000000,d1 ; Spezialteil ausmaskieren + bne S_spezial ; Ein Bit gesetzt-->Spezialbefehl + move.w 2(a0),d1 ; zweiten Befehlsteil in D1 merken + move.w d1,(a5) ; Befehl in FPU schr. (A5==#command) +S_do_ca: ; Einsprung fuer weitere Nachfragen an FPU + move.w (a6),d0 ; Response lesen + btst #12,d0 ; Erstes Modusbit testen + bne S_rw_1x ; ==1 --> springen + btst #11,d0 ; Zweites Modusbit testen + beq.s S_rw_00 ; ==0 --> springen +; ----- %xxx01, Null-Primitive/Transfer Single CPU Register + btst #10,d0 ; Register uebertragen ? + bne.s S_rw_sngl ; Ja--> Transfer Single CPU-Register + btst #15,d0 ; CA (Come Again) gesetzt ? + bne.s S_do_ca ; Ja--> weiter fragen, sonst fertig + addq.l #4,a0 ; A0 um reine Befehlslaenge weiter + ; ( alles andere wurde in calc_add erledigt ) + move.w (a0),d1 ; erstes Befehlswort holen + move.w d1,d0 ; und nach D0 + and.w #$f000,d0 ; Wieder COP-Befehl ? + eor.w #$f000,d0 + beq.s S_again ; Ja-->direkt weitermachen + move.l a0,2(a7) ; Neuen PC eintragen + move.l S_RegSave+60.w,a0 ; USP wiederherstellen + move.l a0,usp ; (geht nur ueber Umweg) + movem.l (a3),d0-a6 ; Register wiederherstellen + rte ; Trap beenden +S_rw_sngl: + and.w #%1110000,d1 ; Registernummer ausmaskieren ( nur Dn ) + lsr.w #2,d1 ; D1=Nummer*4 + move.l 0(a3,d1.w),(a4) ; Register uebertragen (a4==#operand, a3==#dregs) + bra.s S_do_ca ; danach kommt immer noch etwas +;-----%xxx00, Transfer multiple coprocessor Reg. +S_rw_00: + bsr S_calc_add ; Operandenadresse nach A1 holen + move.w S_Reg_Selec(a6),d4 ; Registerliste nach D4 holen + btst #13,d0 ; Dr-Bit testen + beq.s S_w_00 ; ==0--> Daten in FPU schreiben + btst #12,d0 ; Predekrementmodus ? + beq.s S_r_pred ; ==0--> Ja,springen + moveq #7,d0 ; Schleifenzaehler fuer 8 Bits +S_11: + lsl.w #1,d4 ; Ein Bit ins Carry + bcc.s S_21 ; nur bei Bit==1 etwas machen + move.l (a4),(a1)+ ; 1 (A4==#operand) + move.l (a4),(a1)+ ; 2 + move.l (a4),(a1)+ ; 3 Langworte fuer jedes Register +S_21: + dbra d0,S_11 ; Fuer alle 8 Bits + bra.s S_do_ca ; Nochmal FPU befragen +S_r_Pred: + moveq #7,d0 ; Schleifenzaehler fuer 8 Bits +S_12: + lsl.w #1,d4 ; Ein Bit ins Carry + bcc.s S_22 ; nur bei Bit=1 etwas machen + move.l (a4),(a1)+ ; 1 (A4==#operand) + move.l (a4),(a1)+ ; 2 + move.l (a4),(a1)+ ; 3 Langworte fuer jedes Register + suba.w #24,a1 ; Dekrement durchfuehren +S_22: + dbra d0,S_12 ; Fuer alle 8 Bits + adda.w #12,a1 ; A1 wieder auf letztes Register + move.l a1,(a2) ; A1 als Registerinhalt abspeichern + bra S_do_ca ; Nochmal FPU befragen +S_w_00: + move.w (a0),d0 ; erstes Befehlswort holen + and.b #%111000,d0 ; Adressierungsart maskieren + cmp.b #%011000,d0 ; Gleich (An)+ ? + beq.s S_w_Post ; Ja-->Postinkrementiermodus + moveq #7,d0 ; Schleifenzaehler fuer 8 Bits +S_13: + lsl.w #1,d4 ; Ein Bit ins Carry + bcc.s S_23 ; Nur bei Bit==1 etwas machen + move.l (a1)+,(a4) ; 1 (A4==#operand) + move.l (a1)+,(a4) ; 2 + move.l (a1)+,(a4) ; 3 Langworte fuer jedes Register +S_23: + dbra d0,S_13 ; Fuer alle 8 Bits + bra S_do_ca ; Nochmal FPU befragen +S_w_Post: + suba.w #12,a1 ; Inkrement von calc_add aufheben + moveq #7,d0 ; Schleifenzaehler fuer 8 Bits +S_14: + lsl.w #1,d4 ; Ein Bit ins Carry + bcc.s S_24 ; nur bei Bit==1 etwas machen + move.l (a1)+,(a4) ; 1 (A4==#operand) + move.l (a1)+,(a4) ; 2 + move.l (a1)+,(a4) ; 3 Langworte fuer jedes Register +S_24: + dbra d0,S_14 ; Fuer alle 8 Bits + move.l a1,(a2) ; A1 als Registerinhalt abspeichern + bra S_do_ca ; Nochmal FPU befragen + +S_rw_1x: + btst #11,d0 ; zweites Modusbit testen + bne.s S_rw_11 ; ==1 --> springen (Trap,Error) + btst #13,d0 ; DR-Bit testen + beq.s S_w_10 ; ==0 --> Daten an FPU schreiben +;----- %xx110, evaluate effective adress and transfer data + bsr S_calc_add ; Operandenadresse berechnen + ; A1=Operandenadresse, d1.l=Operandenl„nge + cmp.w #2,d1 ; Laenge-2 + ble.s S_r_bw ; <=2 --> Wort-oder-Byteoperand +S_r_11: + move.l (a4),(a1)+ ; ein Langwort lesen (A4==#operand) + subq.l #4,d1 ; und runterzaehlen + bgt.s S_r_11 ; >0 --> weiter uebertragen + bra S_do_ca ; Nochmal FPU befragen +S_r_bw: + btst #0,d1 ; Byte ? + bne.s S_r_byte ; Ja! + move.w (a4),(a1) ; Wort-Operand lesen (A4==#operand) + bra S_do_ca ; Nochmal FPU befragen +S_r_byte: + move.b (a4),(a1) ; Byte-Operand lesen (A4==#operand) + bra.l S_do_ca ; Nochmal FPU befragen + +;----- %xx101, evaluate effective adress and transfer data +S_w_10: + bsr S_calc_add ; Operandenadresse berechnen + ; A1=Operandenadresse, d1.l=Operandenl„nge + cmp.w #2,d1 ; Laenge-2 + ble.s S_w_bw ; <=2 --> Wort-oder-Byteoperand +S_w_11: + move.l (a1)+,(a4) ; ein Langwort lesen (A4==#operand) + subq.l #4,d1 ; und runterzaehlen + bgt.s S_w_11 ; >0 --> weiter uebertragen + bra S_do_ca ; Nochmal FPU befragen +S_w_bw: + btst #0,d1 ; Byte ? + bne.s S_w_byte ; Ja! + move.w (a1),(a4) ; Wort-Operand lesen (A4==#operand) + bra S_do_ca ; Nochmal FPU befragen +S_w_byte: + move.b (a1),(a4) ; Byte-Operand lesen (A4==#operand) + bra.l S_do_ca ; Nochmal FPU befragen + +;----- %xxx11, take pre-instruction exception +S_rw_11: + bra ex_vec11 ; Error-Handler anspringen +; ( hier koennte man eine genauere Fehleranalyse machen ) + +S_spezial: ; Sprungbefehle etc. + cmp.w #%001000000,d1 ; FScc,FDBcc oder FTRAPcc + beq.s S_s_trap + cmp.w #%010000000,d1 ; Branch mit 16-Bit-Offset + beq.l S_s_br16 + cmp.w #%011000000,d1 ; Branch mit 32-Bit-Offset + beq.l S_s_br32 + bra ex_vec11 ; FSAVE/FRESTORE nicht unterstuetzt +S_s_trap: + move.w (a0),d0 ; Erstes Befehlswort nach D0 + move.w d0,d1 ; und nach D1 retten + and.w #%111000,d0 ; Wichtige Bits ausmaskieren + cmp.w #%001000,d0 ; FDBcc ? + beq.s S_s_fdbcc ; Ja-->springen + cmp.w #%111000,d0 ; FTRAP ? + beq ex_vec11 ; Ja-->Fehler (nicht unterstuetzt) + ; sonst FScc + move.w 2(a0),S_condition(a6) ; Bedingung an FPU schicken + moveq #1,d0 ; Operandenlaenge=1 (fuer calc_add) + bsr S_calc_add ; Operandenadresse berechnen +S_15: + move.w (a6),d0 ; Response lesen + btst #8,d0 ; IA-Bit testen + beq.s S_25 ; ==0 --> fertig + and.w #%1100000000000,d0 ; Bits 11 und 12 ausmaskieren + eor.w #%1100000000000,d0 ; Beide gesetzt ? + bne.s S_15 ; Nicht beide==1 --> warten + bra ex_vec11 ; Sonst ist Exception aufgetreten +S_25: + btst #0,d0 ; Antwortbit testen + sne (a1) ; Je nach Bit setzen/loeschen + bra S_do_ca ; Nochmal FPU befragen +S_s_fdbcc: + move.w 2(a0),S_condition(a6) ; Bedingung an FPU schicken + and.w #%111,d1 ; Registernummer maskieren (D1=(A0)) + lsl.w #2,d1 ; D1=Nummer*4 + lea 0(a3,d1.w),a1 ; A1 enthaelt Adresse des Datenreg. + move.l (a1),d1 ; Dn holen + subq.w #1,d1 ; Dn=Dn-1 + move.l d1,(a1) ; Dn zurueckschreiben + move.l a0,a2 ; alten PC nach A2 holen + addq.l #2,a0 ; PC 2 weiter ( fuer "nicht springen") +S_16: + move.w (a6),d0 ; Response lesen + btst #8,d0 ; IA-Bit testen + beq.s S_26 ; ==0 --> fertig + and.w #%1100000000000,d0 ; Bits 11 und 12 ausmaskieren + eor.w #%1100000000000,d0 ; Beide gesetzt ? + bne.s S_16 ; Nicht beide==1 --> warten + bra ex_vec11 ; Sonst ist Exception aufgetreten +S_26: + btst #0,d0 ; Antwortbit testen + bne S_do_ca ; True-->das war's schon + adda.w 2(a2),a2 ; 16-Bit-Sprungdist. add. (A2=PC) + addq.w #1,d1 ; Dn=-1 ? + beq S_do_ca ; Ja-->kein Sprung (Schleifenende) + move.l a2,a0 ; Sonst "Sprung" (neuen PC laden) + bra S_do_ca ; nochmal FPU befragen +S_s_br16: + move.w (a0),S_Condition(a6) ; Bedingung an FPU schicken +S_17: + move.w (a6),d0 ; Response lesen + btst #8,d0 ; IA-Bit testen + beq.s S_27 ; ==0 --> fertig + and.w #%1100000000000,d0 ; Bits 11 und 12 ausmaskieren + eor.w #%1100000000000,d0 ; Beide gesetzt ? + bne.s S_17 ; Nicht beide==1 --> warten + bra ex_vec11 ; Sonst ist Exception aufgetreten +S_27: + btst #0,d0 ; Antwortbit testen + beq S_do_ca ; False--> das war's schon + adda.w 2(a0),a0 ; 16-Bit-Sprungdistanz addieren + subq.l #2,a0 ; Ein Wort zurueck ( weil spaeter + ; noch 4 addiert wird und und nur 2 addiert werden muesste ) + bra S_do_ca ; Nochmal FPU befragen +S_s_br32: + move.w (a0),S_Condition(a6) ; Bedingung an FPU schicken +S_18: + move.w (a6),d0 ; Response lesen + btst #8,d0 ; IA-Bit testen + beq.s S_28 ; ==0 --> fertig + and.w #%1100000000000,d0 ; Bits 11 und 12 ausmaskieren + eor.w #%1100000000000,d0 ; Beide gesetzt ? + bne.s S_18 ; Nicht beide==1 --> warten + bra ex_vec11 ; Sonst ist Exception aufgetreten +S_28: + addq.l #2,a0 ; Befehl ist 3 Worte lang + ; (jetzt : (A0)=Distanz) + btst #0,d0 ; Antwortbit testen + beq S_do_ca ; False--> das war's schon + adda.l (a0),a0 ; 32-Bit-Sprungdistanz addieren + subq.l #4,a0 ; Zwei Worte zurueck ( weil spaeter + ; noch 4 addiert wird, 2 wurden schon addiert ) + bra S_do_ca ; Nochmal FPU befragen +S_calc_add: + ; Operandenadresse berechnen. A0 muss die Adresse des Line-F- + ; Befehls enthalten, D0 im unteren Byte die Operandenlaenge. + ; die zu berechnende Adresse wird in A1 abgelegt. A0 wird + ; um die Laenge der zusaetzlichen Daten erhaelt. + ; Zusaetzlich wird in D1 die Laenge des Operanden zurueckge- + ; geben (in Bytes, als Langwort). D2,D3,A3 werden zerstoert. + ; Bei den Adressierungsarten -(An),(An)+ steht in A2 ein + ; Zeiger auf die Stelle, in der der Inhalt des Adressregisters + ; gisters An steht (wird fuer FMOVEM gebraucht). + + clr.l d1 ; Laenge als Langwort loeschen + move.b d0,d1 ; und Byte umkopieren + move.w (a0),d2 ; erstes Befehlswort nach D2 + move.w d2,d3 ; und D3 retten + and.w #%111000,d3 ; Adressierungsart ausmaskieren + lsr.w #1,d3 ; D3=Adressierungsart*4 (Langworte) + lea S_cs_tab(pc),a1 ; Sprungtabellenadresse nach A1 + move.l 0(a1,d3.w),a1 ; Adresse der Routine nach A1 + jmp (a1) ; und Routine anspringen +S_c_drd: ; %000 Data Register Direct: Dn +S_c_ard: ; %001 Address Register Direct: An + lea (a3),a1 ; A1 auf Registerfeld + and.w #%1111,d2 ; Registernummer ausmaskieren +; ( und ein Bit vom Modus, 0 fuer Daten-,1 fuer Adressregister ) + lsl.w #2,d2 ; D2="Registernummer"*4 (+Modusbit) + addq.w #4,d2 ; +4 (fuer Operandenlaenge) + sub.w d1,d2 ; Wahre Laenge abziehen + adda.w d2,a1 ; Offset auf Registerfeldanfang add. + rts +S_c_ari: ; %010 Address Register indirect: (An) + and.w #%111,d2 ; Registernummer ausmaskieren + lsl.w #2,d2 ; D2=Registernummer*4 + move.l 32(a3,d2.w),a1 ; Adresse nach A1 + rts +S_c_arpo: ; %011 Adressregister indirect with Postincrement: (An)+ + and.w #%111,d2 ; Registernummer ausmaskieren + lsl.w #2,d2 ; D2=Registernummer*4 + lea 32(a3,d2.w),a2 ; Adresse Adressregister nach A2 + move.l (a2),a1 ; Adresse (Inhalt A.-Reg.) nach A1 + btst #0,d1 ; D1 ungerade ? (Byteoperand) + bne.s S_29 ; Ja-->Spezialbehandlung +S_19: + add.l d1,(a2) ; Inkrement durchfuehren + rts +S_29: + cmp.w #4*7,d2 ; Ist A7 gemeint ? + bne.s S_19 ; nein-->normal vorgehen + addq.l #2,(a2) ; Sonst (bei Byte) 2 addieren, + rts ; damit Stack gerade bleibt! +S_c_arpr: ; %100 Adressregister Indirect with Predekrement: -(An) + and.w #%111,d2 ; Registernummer ausmaskieren + lsl.w #2,d2 ; D2=Registernummer*4 + lea 32(a3,d2.w),a2 ; Adresse des Adressreg. nach A2 + btst #0,d1 ; D1 ungerade? (Byteoperand) + bne.s S_210 ; Ja-->Spezialbehandlung +S_110: + sub.l d1,(a2) ; Dekrement durchfuehren + move.l (a2),a1 ; Adresse (Inhalt des A.-Reg) nach A1 + rts +S_210: + cmp.w #4*7,d2 ; Ist A7 gemeint? + bne.s S_110 ; nein-->normal vorgehen + subq.l #2,(a2) ; Sonst (bei Byte) 2 addieren, + ; damit Stack gerade bleibt ! + move.l (a2),a1 ; Adresse (Inhalt des A.-Reg) nach A1 + rts +S_c_ar16: ; %101 Addressregister Indirect with Displacement: d16(An) + and.w #%111,d2 ; Registernummer ausmaskieren + lsl.w #2,d2 ; D2=Registernummer*4 + move.l 32(a3,d2.w),a1 ; Adresse nach A1 + move.w 4(a0),d2 ; 3.Befehlswort nach D2 (Offset) + adda.w d2,a1 ; Offset auf Adresse addieren + addq.l #2,a0 ; A0 ein Wort (d16) weiter + rts +S_c_ar08: ; %110 Addressregister Indirect with Index : d8(An,Xn) + and.w #%111,d2 ; Registernummer ausmaskieren + lsl.w #2,d2 ; D2=Registernummer*4 + move.l 32(a3,d2.w),a1 ; Adresse nach A1 + move.w 4(a0),d2 ; 3.Befehlswort nach D2 (Byte-Offset) + move.w d2,d3 ; und nach D3 + and.w #$ff,d3 ; Byte ausmaskieren (Byte-Offset) + adda.w d3,a1 ; Offset auf Adresse addieren + btst #11,d2 ; 1=long; 0=word + bne.s S_c_ar81 + and.w #%1111000000000000,d2 ; Nummer von Dn und Modusbit + lsr.w #5,d2 ; maskieren + lsr.w #5,d2 ; D2=Registernummer*4 (und modusbit) + adda.w 2(a3,d2.w),a1 ; 16-Bit-Index auf A1 addieren + addq.l #2,a0 ; A0 ein Wort (Kram & d8) weiter + rts +S_c_ar81: + and.w #%1111000000000000,d2 ; Nummer von Dn und Modusbit + lsr.w #5,d2 ; maskieren + lsr.w #5,d2 ; D2=Registernummer*4 (und modusbit) + adda.w 0(a3,d2.w),a1 ; 32-Bit-Index auf A1 addieren + addq.l #2,a0 ; A0 ein Wort (Kram & d8) weiter + rts +S_c_pc: ; %111 absolut short/long, PC-relativ (ohne/mit Index) \ oder direkt + btst #2,d2 ; Immidiate ? + bne.s S_immi ; <>0 --> Ja! + btst #1,d2 ; PC-relativ ? + bne.s S_pc_rel ; <>0 --> Ja! + btst #0,d2 ; Long ? + bne.s S_c_long ; <>0 --> Ja! + ; sonst short + move.w 4(a0),d2 ; Wortadresse holen + ext.l d2 ; Auf Langwort erweitern + move.l d2,a1 ; und als Operandenadresse merken + addq.l #2,a0 ; A0 ein Wort (Short-A.) weiter + rts +S_c_long: + move.l 4(a0),a1 ; Langwortadresse holen + addq.l #4,a0 ; A0 zwei Worte (Long-A.) weiter + rts +S_immi: + move.l a0,a1 ; Befehlsadresse nach A1 + add.l d1,a0 ; A0 ueber Operand hinwegsetzen + rts +S_pc_rel: + btst #0,d2 ; mit Index ? + bne.s S_pc_idx ; <>0 --> Ja! + move.l a0,a1 ; PC nach A1 + adda.w 4(a0),a1 ; Offset addieren + addq.l #4,a1 ; +4 fuer Laenge des FPU-Befehls + addq.l #2,a0 ; A0 zwei (16-Bit-Offset) weiter + rts +S_pc_idx: + move.l a0,a1 ; PC nach A1 + clr.w d2 ; Oberes Byte loeschen + move.b 5(a0),d2 ; Offset nach D2 + adda.w d2,a1 ; und addieren + addq.l #4,a1 ; +4 fuer Laenge des FPU-Befehls + move.b 4(a0),d2 ; D2=Registernummer*16 und Modusbit + ; ( high-Byte ist noch 0 ) + btst #3,d2 ; Long-Bit testen + bne.s S_pc_i_l ; <>0 -->Long-Index + and.b #%11110000,d2 ; Registerinformation ausblenden + lsr.w #2,d2 ; D2=Registernummer*4 (und Modusbit) + adda.w 2(a3,d2.w),a1 ; Word-Index addieren + addq.l #2,a0 ; A0 zwei (8-Bit-Offset & Kram) weiter + rts +S_pc_i_l: + and.b #%11110000,d2 ; Restinformation ausblenden + lsr.w #2,d2 ; D2=Registernummer*4 (und Modusbit) + adda.l 0(a3,d2.w),a1 ; Long-Index addieren + addq.l #2,a0 ; A0 zwei (8-Bit-Offset & Kram) weiter + rts ; Ende von S_calc_add + +S_cs_tab: + dc.l S_c_drd,S_c_ard,S_c_ari,S_c_arpo ; Sprungtabelle fuer + dc.l S_c_arpr,S_c_ar16,S_c_ar08,S_c_pc ; Adressierungsarten +S_End: + diff --git a/tests/t_parsys/t_parsys.doc b/tests/t_parsys/t_parsys.doc new file mode 100644 index 0000000..10d31c7 --- /dev/null +++ b/tests/t_parsys/t_parsys.doc @@ -0,0 +1,8 @@ ++---------------------- Test Application PARSYS ----------------------------+ +| | +| Back to the roots! This is the "operating system" of my 68000-based par- | +| allel computer I built several years ago and which was the main reason to | +| write my own assembler because the original one from RDK was too buggy to | +| work reliably with it. Contains also a lot of FPU orders. | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_parsys/t_parsys.inc b/tests/t_parsys/t_parsys.inc new file mode 100644 index 0000000..7ffd805 --- /dev/null +++ b/tests/t_parsys/t_parsys.inc @@ -0,0 +1,10 @@ +(* tests/t_parsys/t_parsys.asm-Includefile für CONST-Sektion *) +S_RegSave = $608; +S_MemEnd = $400; +S_ParNo = $408; +S_CPUNo = $422; +_fadd_cnt = $40E; +_fmul_cnt = $412; +_fdiv_cnt = $416; +_fsqrt_cnt = $41A; +(* Ende Includefile für CONST-Sektion *) diff --git a/tests/t_parsys/t_parsys.ori b/tests/t_parsys/t_parsys.ori new file mode 100644 index 0000000..d26be99 Binary files /dev/null and b/tests/t_parsys/t_parsys.ori differ diff --git a/tests/t_scmp/asflags b/tests/t_scmp/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_scmp/t_scmp.asm b/tests/t_scmp/t_scmp.asm new file mode 100644 index 0000000..0fdc8ca --- /dev/null +++ b/tests/t_scmp/t_scmp.asm @@ -0,0 +1,59 @@ + cpu sc/mp + + lde + xae + ane + ore + xre + dae + ade + cae + + sio + sr + srl + rr + rrl + + halt + ccl + scl + dint + ien + csa + cas + nop + + ldi 0x12 + ani 0x23 + ori 0x34 + xri 0x45 + dai 0x56 + adi 0x67 + cai 0x78 + dly 0x89 + + xpal pc + xpah p2 + xppc p1 + + ld e(pc) + st @e(p2) + and 10(p1) + or @-20(p3) + xor vari +vari: dad -30(p2) + add @40(p1) + cad vari + + jmp vari + jp 10(p2) + jz vari + jnz vari + + ild vari + dld -5(p2) + +; org 0xfff +; ldi 0x20 + diff --git a/tests/t_scmp/t_scmp.doc b/tests/t_scmp/t_scmp.doc new file mode 100644 index 0000000..8c863b8 --- /dev/null +++ b/tests/t_scmp/t_scmp.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application SCMP ----------------------------+ +| | +| This is a (synthetic) test of the SC/MP code generator | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_scmp/t_scmp.ori b/tests/t_scmp/t_scmp.ori new file mode 100755 index 0000000..75684f1 Binary files /dev/null and b/tests/t_scmp/t_scmp.ori differ diff --git a/tests/t_secdrive/asflags b/tests/t_secdrive/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_secdrive/lowlevel.inc b/tests/t_secdrive/lowlevel.inc new file mode 120000 index 0000000..968acf7 --- /dev/null +++ b/tests/t_secdrive/lowlevel.inc @@ -0,0 +1 @@ +wd1003at.inc \ No newline at end of file diff --git a/tests/t_secdrive/secparam.inc b/tests/t_secdrive/secparam.inc new file mode 100644 index 0000000..8bf8381 --- /dev/null +++ b/tests/t_secdrive/secparam.inc @@ -0,0 +1,1619 @@ +;***************************************************************************** +;* Sekund„rlaufwerkstreiber, Modul SecParam * +;* liefert Laufwerksparameter, falls fehlend im Bootsektor * +;* stellt das ganze Formatiermen zur Verfgung * +;***************************************************************************** + + section SecParam + +;***************************************************************************** +;* gemeinsam benutzte Meldungen * +;***************************************************************************** + +TrackMsg db "Spur (0..Spurzahl-1) : $" +HeadMsg db "Kopf (0..Kopfzahl-1) : $" +ConfirmMsg db "Sind Sie sicher ?$" +InterleaveMsg db "Interleave (1..Sektorzahl-1) : $" + +;***************************************************************************** +;* Routine BreakOnESC * +;* schaut nach, ob ESC gedrckt wurde * +;* Ausgabe: C=1, falls ja * +;***************************************************************************** + + GlobProc BreakOnESC + + push ax ; Register retten + mov ah,1 ; Tastaturpuffer antesten + int INT_Keyboard + clc ; Annahme nicht gedrckt + jz Ende + mov ah,0 ; Zeichen da: dies abholen + int INT_Keyboard + cmp al,ESC ; ist es ESC ? + clc ; Annahme nein + jne Ende + stc ; jawoll! +Ende: pop ax ; Register zurck + ret + + endp + +;***************************************************************************** +;* Routine YesNo * +;* fragt nach Ja oder Nein * +;* Ausgabe: C=0, falls ja * +;***************************************************************************** + + proc YesNo + + push ax ; Register retten + +QueryLoop: mov ah,DOS_RdChar ; ein Zeichen lesen + int INT_DOS + + cmp al,'a' ; Kleinbuchstaben ? + jb Upper + cmp al,'z' + ja Upper + add al,'A' + sub al,'a' +Upper: + cmp al,'J' ; akzeptierte Zeichen fr Ja + clc + je YNDone + cmp al,'Y' + clc + je YNDone + cmp al,'N' ; akzeptierte Zeichen fr Nein + stc + je YNDone + + PrChar BEL ; alles andere anmeckern + jmp QueryLoop + +YNDone: PrChar al ; Zeichen als Echo ausgeben + PrChar CR ; Zeilenvorschub + PrChar LF + pop ax ; Register zurck + + ret + + endp + +;***************************************************************************** +;* Routine ReadNumber * +;* liest einen Wert von 0..n in AX ein * +;* Eingabe: AX = Maximalwert * +;* DI = Zeiger auf Meldung * +;* Ausgabe: AX = eingelesene Zahl * +;***************************************************************************** + + proc ReadNumber + + push bx ; Register retten + push cx + push dx + push si + + mov si,ax ; Maximalwert retten +InLoop: mov dx,di ; Meldung ausgeben + mov ah,DOS_WrString + int INT_DOS + lea dx,[KeyBuffer] ; Zahl als String einlesen + mov ah,DOS_RdString + int INT_DOS + PrChar CR + PrChar LF + mov ax,0 ; jetzt Zeichen verarbeiten + mov cl,[KeyBuffer+1] + mov ch,0 + lea bx,[KeyBuffer+2] + jcxz InvFormat ; Nullschleife abfangen +ConvLoop: mov dx,10 ; bisheriges Ergebnis hochmultiplizieren + mul dx + mov dl,[bx] ; ein Zeichen holen + inc bx + sub dl,'0' ; ASCII-Offset abziehen + jc InvFormat ; bei Formatfehler abbrechen + cmp dl,9 ; nur 0..9 erlaubt + ja InvFormat + add al,dl ; dazuaddieren + adc ah,0 + loop ConvLoop + jmp ChkRange ; fertig: weiter zur Bereichsprfung +InvFormat: PrMsg InvMsg ; wenn fehlerhaft, meckern + jmp InLoop ; und nochmal versuchen +ChkRange: cmp ax,si ; auáerhalb Bereich ? + jbe OK + PrMsg OverMsg ; ja: meckern... + jmp InLoop ; ...und auf ein neues + +OK: pop si ; Register zurck + pop dx + pop cx + pop bx + + ret + +KeyBufferLen equ 30 ; 30 Zeichen sollten fr Zahlen reichen... +KeyBuffer db KeyBufferLen ; Maimall„nge fr DOS + db 0 ; effektive L„nge Eingabe + db KeyBufferLen dup (0) ; Platz fr Eingabe +InvMsg db "Ungltiges Zahlenformat",CR,LF,'$' +OverMsg db "Bereichsberschreitung",CR,LF,'$' + + endp + +;****************************************************************************** +;* eine Anzahl Leerzeichen ausgeben * +;* In : CX = Anzahl * +;****************************************************************************** + + globproc WriteSpc + + push dx ; Register retten + + jcxz NULL ; Nullschleife abfangen +Loop: mov ah,DOS_WrChar + mov dl,' ' + int INT_DOS + loop Loop + +NULL: pop dx ; Register zurck + ret + + endp + +;****************************************************************************** +;* vorzeichenlose Zahl dezimal ausgeben * +;* In : AX = Zahl * +;* CL = min. Stellenzahl * +;****************************************************************************** + + globproc WriteDec + + push di ; Register retten + push cx + push dx + + mov ch,0 ; CH z„hlt effektive Zeichenzahl +InLoop: sub dx,dx ; Stellendivision + mov di,10 ; gewnschtes Zahlensystem + div di + mov di,ax ; war es vorher 0 ? + or di,dx ; (wenn Quotient & Rest 0) + jnz NZero ; nein-->normal ausgeben + or ch,ch ; noch erste Stelle ? + jz NZero ; dann auf jeden Fall 0 ausgeben + mov dl,0f0h ; ansonsten Leerzeichen fr leading 0 +NZero: push dx ; Zeichen speichern... + inc ch ; ...und mitz„hlen + cmp ch,cl ; Mindestzahl ausgegeben ? + jb InLoop ; nein-->weiter + or ax,ax ; ansonsten: 0 ? + jnz InLoop ; nein, weitermachen + + shr cx,8 ; effektive Zahl nach CX +OLoop: pop dx ; ein Zeichen runterholen + add dl,'0' ; in ASCII konvertieren + mov ah,DOS_WrChar ; ber DOS ausgeben + int INT_DOS + loop OLoop + + pop dx + pop cx + pop di ; Register zurck + ret + + endp + +;****************************************************************************** +;* vorzeichenlose Zahl hexadezimal ausgeben * +;* In : AX = Zahl * +;* CL = min. Stellenzahl * +;****************************************************************************** + + globproc WriteHex + + push di ; Register retten + push cx + push dx + + mov ch,0 ; CH z„hlt effektive Zeichenzahl +InLoop: sub dx,dx ; Stellendivision + mov di,16 ; gewnschtes Zahlensystem + div di + mov di,ax ; war es vorher 0 ? + or di,dx ; (wenn Quotient & Rest 0) + jnz NZero ; nein-->normal ausgeben + or ch,ch ; noch erste Stelle ? + jz NZero ; dann auf jeden Fall 0 ausgeben + mov dl,0f0h ; ansonsten Leerzeichen fr leading 0 +NZero: push dx ; Zeichen speichern... + inc ch ; ...und mitz„hlen + cmp ch,cl ; Mindestzahl ausgegeben ? + jb InLoop ; nein-->weiter + or ax,ax ; ansonsten: 0 ? + jnz InLoop ; nein, weitermachen + + shr cx,8 ; effektive Zahl nach CX +OLoop: pop dx ; ein Zeichen runterholen + add dl,'0' ; in ASCII konvertieren + cmp dl,'9' + jbe NoHex + add dl,7 +NoHex: mov ah,DOS_WrChar ; ber DOS ausgeben + int INT_DOS + loop OLoop + + pop dx + pop cx + pop di ; Register zurck + ret + + endp + +;***************************************************************************** +;* Routine GeometryDefined - stellt fest, ob Geometrie fr ei Laufwerk defi- * +;* niert ist * +;* Eingabe: AL = Laufwerksnummer * +;* Ausgabe: C = 0, falls OK * +;***************************************************************************** + + proc GeometryDefined + + push di ; Register retten + call GetPTabAdr ; Tabellenadresse bilden + cmp word ptr[di+DrPar_Cyls],0 ; Zylinderzahl 0 ? + stc + je Fin + cmp byte ptr[di+DrPar_Heads],0 ; Kopfzahl 0 ? + stc + je Fin + cmp byte ptr[di+DrPar_NSecs],0 ; Sektorzahl 0 ? + stc + je Fin + clc ; alles OK +Fin: pop di ; Register zurck + ret + + endp + +;***************************************************************************** +;* Routine QueryRedefine - fragt nach, ob Geometrie neu definert werden soll * +;* Eingabe: AL = Laufwerk * +;* Ausgabe: C = 0, falls ja * +;***************************************************************************** + + proc QueryRedefine + + add al,'1' ; Laufwerksnummer in ASCII umrechnen + mov [UndefMsg2],al ; in Meldung einschreiben + PrMsg UndefMsg + PrMsg DoQueryMsg ; nachfragen, ob Definition erwnscht + call YesNo + ret + +UndefMsg db "Geometrie fr Laufwerk " +UndefMsg2 db " undefiniert.",CR,LF,"$" +DoQueryMsg db "Geometrie neu definieren ? $" + + endp + +;***************************************************************************** +;* Routine ReadGeomety - liest Laufwerksgeometrie vom Benutzer ein * +;* Eingabe: AL = phys. Laufwerksnummer * +;***************************************************************************** + + proc ReadGeometry + + push ax ; Register retten + push si + push di + + call GetPTabAdr ; Zeiger auf Parametertabelle holen + mov si,di + + lea di,[CylInpMsg] ; Zylinderzahl erfragen + mov ax,1024 + call ReadNumber + mov [si+DrPar_Cyls],ax + + lea di,[HeadInpMsg] ; Kopfzahl erfragen + mov ax,16 + call ReadNumber + mov [si+DrPar_Heads],al + + lea di,[RWCInpMsg] ; RWC-Zylinder erfragen + mov ax,65535 + call ReadNumber + mov [si+DrPar_RedWr],ax + + lea di,[PreInpMsg] ; Pr„kompensations-Zylinder erfragen + mov ax,65535 + call ReadNumber + mov [si+DrPar_PrComp],ax + + lea di,[ECCInpMsg] ; ECC-L„nge erfragen + mov ax,11 + call ReadNumber + mov [si+DrPar_ECCLen],ax + + mov al,[si+DrPar_Heads] ; Steuerbyte Bit 3=1, falls Platte + dec al + and al,8 ; mehr als 8 K”pfe hat + mov [si+DrPar_CByte],al + + mov al,0 ; Timeouts unbenutzt + mov [si+DrPar_TOut],al + mov [si+DrPar_FTOut],al + mov [si+DrPar_CTOut],al + + mov ax,[si+DrPar_Cyls] ; Parkzylinder=Zylinderzahl+1 + inc ax + mov [si+DrPar_LZone],ax + + lea di,[SecInpMsg] ; Sektorzahl erfragen + mov ax,255 + call ReadNumber + mov [si+DrPar_NSecs],al + + pop di ; Register zurck + pop si + pop ax + ret + +CylInpMsg db "Anzahl Zylinder (max. 1024) : $" +HeadInpMsg db "Anzahl K”pfe (max. 16) : $" +RWCInpMsg db "Startzylinder fr reduzierten Schreibstrom (max. 65535) : $" +PreInpMsg db "Startzylinder fr Pr„kompensation (max. 65535) : $" +ECCInpMsg db "max. ECC-Fehlerburstl„nge (5 oder 11) : $" +SecInpMsg db "Sektorzahl (max. 255) : $" + + endp + +;***************************************************************************** +;* Routine WriteGeoToDisk - schreibt Laufwerksgeometrie auf Platte * +;* Eingabe: AL = phys. Laufwerksnummer * +;* Ausgabe: C+AX = Fehlerstatus * +;***************************************************************************** + + proc WriteGeoToDisk + + push bx ; Register retten + push cx + push dx + push si + push di + push es + + mov dx,ds ; alles im folgenden im Datensegment + mov es,dx + + mov dl,al ; Laufwerksnummer retten + mov ah,0 ; Kopf 0, + sub bx,bx ; Spur 0, + mov cx,0101h ; Sektor 1 lesen + lea di,[SectorBuffer] + call ReadSectors + jc GeoError ; Abbruch bei Fehler + + mov al,dl ; Geometrietabelle adressieren + call GetPTabAdr + mov si,di ; selbige in MBR einschreiben + lea di,[SectorBuffer+DrPar_Offset] + mov cx,DrPar_Len/2 + cld + rep movsw + + mov al,dl ; jetzt den ganzen Kram zurckschreiben + mov ah,0 + sub bx,bx + mov cx,0101h + lea si,[SectorBuffer] + call WriteSectors + jc GeoError + +Fin: pop es ; Register zurck + pop di + pop si + pop dx + pop cx + pop bx + ret + +GeoError: mov ah,bl ; Fehlerausgabe + call WrErrorCode + jmp Fin + + endp + +;***************************************************************************** +;* Routine QueryParams * +;* Eingabe: AL = Laufwerksnummer * +;* AH = 1, falls Rckschreiben erlaubt * +;* Ausgabe: AL = 0: Laufwerk vergessen * +;* AL = 1: Mastersektor neu lesen * +;* AL = 2: Tabelle nur transient eingetragen, kein Neulesen * +;***************************************************************************** + + globproc QueryParams + + push bx ; Register retten + push cx + push dx + push si + push di + push es + + mov bx,ax ; Laufwerksnummer retten + call QueryRedefine ; nachfragen, ob Neudefinition erwnscht + mov al,0 ; Abbruch bei Nein + ljc Terminate + + mov al,bl ; Geometrie einlesen + call ReadGeometry + + shr bh,1 ; Rckschreiben erlaubt ? + cmc ; C=1-->verboten + jc NoWriteBack + + PrMsg WriteBackMsg ; nachfragen, ob Rckschreiben erwnscht + call YesNo +NoWriteBack: mov al,2 ; Neulesen bei Nein verhindern + jc Terminate + + mov al,bl + call WriteGeoToDisk + jc WrError + + mov al,1 ; Ergebnis: MBR-Lesen wiederholen + jmp Terminate +WrError: mov al,0 ; Schreibfehler: Laufwerk ignorieren + +Terminate: pop es ; Register zurck + pop di + pop si + pop dx + pop cx + pop bx + + ret + +WriteBackMsg db "Parametersatz zurckschreiben ? $" + + endp + +;**************************************************************************** +;* Laufwerksnummer einlesen * +;* Ausgabe: AL = Laufwerksnummer * +;**************************************************************************** + + proc InputDrive + + push dx ; Register retten + +RdLoop: PrMsg PromptMsg ; Anfrage ausgeben + mov ah,DOS_RdChar ; ein Zeichen holen + int INT_DOS + mov dl,al ; Zeichen retten + PrChar dl ; Laufwerk als Echo zurckgeben + PrChar CR + PrChar LF + sub dl,'1' ; nur 1 oder 2 erlaubt + jc RdLoop + cmp dl,MaxPDrives + jae RdLoop + mov al,dl ; Laufwerk in AL zurckgeben + + pop dx ; Register zurck + ret + +PromptMsg db "Laufwerksnummer (1 oder 2) : $" + + endp + +;**************************************************************************** +;* Men fr Plattenfunktionen * +;**************************************************************************** + + proc SelectDisk + + push ax ; Register sichern + push bx + push cx + push dx + push si + push di + push es + + mov dh,ah ; Rckschreibeflag sichern + call InputDrive + mov dl,al ; Laufwerksnummer sichern + + mov al,dl ; Geometrie noch undefiniert ? + call GeometryDefined + jnc IsOK ; Nein, alles in Butter + + mov al,dl ; nicht definiert: versuchen, + mov ah,0 ; Geometrie vom MBR zu lesen + mov bx,ds + mov es,bx + sub bx,bx + mov cx,0101h + lea di,[SectorBuffer] + call ReadSectors + jnc CopyTable ; kein Fehler->Tabelle auslesen + mov dh,0 ; wenn Fehler, nie zurckschreiben + jmp ReadManual ; und manuell probieren +CopyTable: lea si,[SectorBuffer+DrPar_Offset] + mov al,dl + call GetPTabAdr + mov cx,DrPar_Len/2 + cld + rep movsw + mov al,dl ; Geometrie jetzt da ? + call GeometryDefined + jnc IsOK ; falls ja, Ende + +ReadManual: mov al,dl ; fragen, ob Redefinition erwnscht + call QueryRedefine + jc NotOK ; falls nein, Abbruch + mov al,dl ; ansonsten einlesen + call ReadGeometry + shr dh,1 ; zurckschreiben ? + jnc IsOK + mov al,dl ; ja... + call WriteGeoToDisk ; Fehler ignorieren + +IsOK: mov [MomDrive],dl ; Laufwerk akzeptiert + +NotOK: pop es ; Register zurck + pop di + pop si + pop dx + pop cx + pop bx + pop ax + + ret + + endp + +;---------------------------------------------------------------------------- + + proc ChangeGeometry + + cmp [MomDrive],-1 ; Laufwerk berhaupt schon definiert ? + jne DriveDefined + call InputDrive ; nein: lesen & einschreiben + mov [MomDrive],al +DriveDefined: mov al,[MomDrive] ; neue Geometrie einlesen + call ReadGeometry + mov al,[MomDrive] + call WriteGeoToDisk ; die auch gleich zu schreiben versuchen + + ret + + endp + +;---------------------------------------------------------------------------- + + proc VerifyDisk + + pusha ; restlos alles... + + mov al,[MomDrive] ; erstmal sicherstellen, daá der + call SetDriveParams ; Kontroller die Geometrie kennt + + mov al,[MomDrive] ; die Geometrie brauchen wir auch + call GetPTabAdr + + PrMsg ESCMsg + sub bp,bp ; Fehlerz„hler + mov si,bp ; Zylinderz„hler + mov dx,bp ; Folgefehlerz„hler +CylLoop: mov dl,0 ; Kopfz„hler +HeadLoop: PrMsg CylMsg ; zu testende Spur ausgeben + mov ax,si + mov cl,4 + call WriteDec + PrMsg HeadMsg + mov al,dl + mov ah,0 + mov cl,2 + call WriteDec + PrChar CR + + mov al,[MomDrive] ; eine Spur testen + mov ah,dl + mov bx,si + mov cl,[di+DrPar_NSecs] + mov ch,1 + call VeriSectors + + jnc NoError ; evtl. Fehlerbehandlung + push ax + PrChar LF + pop ax + mov ah,[MomDrive] + call WrErrorCode + inc bp ; Fehlerz„hler rauf + inc dh + test dh,7 ; alle 8 Fehler in Reihe nachfragen + jnz NextTrack + PrMsg GoOnMsg + call YesNo + jc Terminate + jmp NextTrack +NoError: mov dh,0 ; eine Spur gut->Folgenz„hler l”schen +NextTrack: call BreakONESC ; Abbruch ? + jc Terminate + inc dl ; n„chster Kopf + cmp dl,[di+DrPar_Heads] + jb HeadLoop + inc si ; n„chster Zylinder + cmp si,[di+DrPar_Cyls] + ljb CylLoop + +Terminate: mov ax,bp ; Fehlerzahl ausgeben + mov cl,5 + call WriteDec + PrMsg ErrorMsg + + popa ; Register zurck + + ret + +EscMsg db "Verifizieren..",CR,LF,"Abbruch mit ",CR,LF,'$' +CylMsg db "Zylinder $" +HeadMsg db ", Kopf $" +GoOnMsg db "Test fortsetzen? $" +ErrorMsg: db " Fehler gefunden ",CR,LF,'$' + + endp + +;---------------------------------------------------------------------------- + + proc FormatDisk + + push ax ; Register retten + push bx + push cx + push di + push es + + mov al,[MomDrive] ; erstmal sicherstellen, daá der + call SetDriveParams ; Kontroller die Geometrie kennt + + mov al,[MomDrive] + call GetPTabAdr +InterLoop: mov al,[di+DrPar_NSecs] ; Maximum=Sektorzahl-1 + dec al + mov ah,0 + lea di,[InterleaveMsg] ; Interleave erfragen + call ReadNumber + or ax,ax ; Null wollen wir nicht + jz InterLoop + mov bl,al ; Interleave retten + PrMsg ConfirmMsg ; sicherheitshalber nachfragen + call YesNo + jc Fin + PrMsg NewLine + PrMsg FormatMsg + mov ah,bl ; Interleave zurck + mov al,[MomDrive] + call FormatUnit + jc FormatError ; Fehler beim Formatieren ? + +NoFormatError: PrMsg WriteMsg + lea di,[SectorBuffer] ; MBR erzeugen + cld + mov cx,SecSize/2-1 ; letztes Wort anders! + mov ax,ds + mov es,ax + sub ax,ax ; prinzipiell erstmal alles Nullen + rep stosw + mov word ptr[di],0aa55h ; Gltigkeitsflag am Ende + mov al,[MomDrive] ; Geometrietabelle eintragen + call GetPTabAdr + mov si,di + lea di,[SectorBuffer+DrPar_Offset] + mov cx,DrPar_Len/2 + rep movsw + mov al,[MomDrive] ; Sektor schreiben + mov ah,0 ; MBR auf Kopf 0, + mov bx,0 ; Spur 0, + mov cx,0101h ; Sektor 1 + lea si,[SectorBuffer] + call WriteSectors + jc FormatError ; Fehler beim Schreiben ? + +Fin: pop es ; Register zurck + pop di + pop cx + pop bx + pop ax + ret + +FormatError: cmp al,DErr_UserTerm ; Abbruch durch Benutzer ? + je Fin ; dann nicht meckern + push ax ; Fehlercode retten + pushf + PrMsg NewLine + popf + pop ax + mov ah,[MomDrive] ; Fehlermeldung ausgeben + call WrErrorCode + jmp Fin + +FormatMsg db "Formatieren...",CR,LF,'$' +WriteMsg db "MBR schreiben...",CR,LF,'$' + + endp + +;---------------------------------------------------------------------------- + + proc BadTrack + + push bx + push si + push di + + mov al,[MomDrive] ; Zeiger auf Geometrietabelle + call GetPTabAdr ; holen + mov si,di + + lea di,[TrackMsg] ; Spurnummer abfragen + mov ax,[si+DrPar_Cyls] + dec ax + call ReadNumber + mov bx,ax + lea di,[HeadMsg] ; Kopfnummer abfragen + mov ax,[si+DrPar_Heads] + dec ax + call ReadNumber + mov ah,al + push ax ; sicherheitshalber noch best„tigen + PrMsg ConfirmMsg + call YesNo + pop ax + jc NoError + mov al,[MomDrive] ; Spur markieren + call MarkBad + jnc NoError + push ax ; Fehlercode retten + pushf + PrMsg NewLine + popf + pop ax + mov ah,[MomDrive] + call WrErrorCode +NoError: + pop di + pop si + pop bx + + ret + + endp + +;---------------------------------------------------------------------------- + + proc FormTrack + + push bx + push si + push di + + mov al,[MomDrive] ; Zeiger auf Geometrietabelle + call GetPTabAdr ; holen + mov si,di + + lea di,[TrackMsg] ; Spurnummer abfragen + mov ax,[si+DrPar_Cyls] + dec ax + call ReadNumber + mov bx,ax + lea di,[HeadMsg] ; Kopfnummer abfragen + mov ax,[si+DrPar_Heads] + dec ax + call ReadNumber + mov ah,al + push ax ; Kopf retten +InterLoop: mov al,[si+DrPar_NSecs] ; Interleave-Maximum=Sektorzahl-1 + dec al + mov ah,0 + lea di,[InterleaveMsg] ; Interleave erfragen + call ReadNumber + or ax,ax ; Null wollen wir nicht + jz InterLoop + mov cl,al ; Interleave passend ablegen + PrMsg ConfirmMsg ; nochmal nachfragen + call YesNo + pop ax + jc NoError + mov al,[MomDrive] ; Kopf zurck + call FormatTrack + jnc NoError + push ax ; Fehlercode retten + pushf + PrMsg NewLine + popf + pop ax + mov ah,[MomDrive] + call WrErrorCode +NoError: + pop di + pop si + pop bx + + ret + + endp + +;---------------------------------------------------------------------------- + +; packt eine Sektorkoordinate ins BIOS-Format +; -->Zylinder=BX, Kopf=AH, Sektor=AL +; <--Zylinder/Sektor=BX, Kopf=AH + + proc PackCoordinate + + shl bh,6 + or bh,al + xchg bl,bh + ret + + endp + + proc UnpackCoordinate + + xchg bh,bl ; Zylinderbytes in richtige Reihenfolge + mov al,bh ; Sektor ausmaskieren + and al,00111111b + shr bh,6 ; Zylinder korrigieren + + ret + + endp + +; berechnet aus einer Sektorkoordinate die lineare Sektornummer +; -->Zylinder/Sektor=BX, Kopf=AH, Geometriezeiger=SI +; <--Sektornummer=DX/AX + + proc LinearizeCoordinate + + push bx + push cx + + mov cx,ax ; Kopf retten + mov al,bh ; Zylinder rekonstruieren + mov ah,bl + shr ah,6 + mov dl,[si+DrPar_Heads] + mov dh,0 + mul dx ; = Anzahl Spuren bis Zylinderbeginn + add al,ch ; Startkopf dazuaddieren + adc ah,0 ; bisher hoffentlich nur 16 Bit... + mov dl,[si+DrPar_NSecs] + mov dh,0 + mul dx ; = Anzahl Spuren bis Spurbeginn + and bl,3fh ; letztendlich Sektor-1 dazu + dec bl + add al,bl + adc ah,0 + adc dx,0 + + pop cx + pop bx + + ret + + endp + + proc MakePart + + push bx + push cx + push dx + push si + push di + push es + + PrMsg ConfirmMsg ; sind wir sicher ? + call YesNo + ljc End + + mov al,[MomDrive] ; Laufwerk rekalibrieren + call Recalibrate + ljc PartError + + mov al,[MomDrive] ; alten MBR auslesen + mov ah,0 + mov bx,0 + mov cx,0101h + mov si,ds + mov es,si + lea di,[SectorBuffer] + call ReadSectors + ljc PartError + + mov al,[MomDrive] ; Plattengeometrie holen + call GetPTabAdr + mov si,di + + lea di,[SectorBuffer+ParTab_Offset] ; an erste Tabelle schreiben + mov byte ptr [di+ParTab_BFlag],80h ; Partition aktiv + cmp byte ptr[si+DrPar_Heads],1 ; nur ein Kopf ? + ja MoreHeads + mov bx,1 ; ja: Start auf Zyl. 1, Kopf 0 + mov ah,0 + jmp WriteStart +MoreHeads: sub bx,bx ; nein: Start auf Zyl. 0, Kopf 1 + mov ah,1 +WriteStart: mov al,01h ; Startsektor immer 1 + call PackCoordinate + mov [di+ParTab_FHead],ah + mov [di+ParTab_FSecCyl],bx + call LinearizeCoordinate ; linearen Start schreiben + mov [di+ParTab_LinSec],ax + mov [di+ParTab_LinSec+2],dx + push dx + push ax + mov bx,[si+DrPar_Cyls] ; Ende: Zylinder n-2, Kopf n-1, Sektor n + sub bx,2 + mov ah,[si+DrPar_Heads] + dec ah + mov al,[si+DrPar_NSecs] + call PackCoordinate + mov [di+ParTab_LHead],ah + mov [di+ParTab_LSecCyl],bx + call LinearizeCoordinate ; Sektorzahl berechnen + pop bx ; dazu Start abziehen + sub ax,bx + pop bx + sbb dx,bx + add ax,1 ; !!! L„nge=Stop-Start+1 + adc dx,0 + mov [di+ParTab_NSecs],ax + mov [di+ParTab_NSecs+2],dx + or dx,dx ; falls >64K Sektoren, + jz NoBigDOS ; eine BigDOS-Partition + mov bl,6 + jmp TypeFound +NoBigDOS: cmp ax,32679 ; ab 32680 Sektoren 16-Bit-FAT + jb NoFAT16 + mov bl,04 + jmp TypeFound +NoFAT16: mov bl,1 ; kleine 12-Bit-Partition +TypeFound: mov [di+ParTab_Type],bl + add di,ParTab_Len ; die anderen 3 Partitionen l”schen + mov cx,3*(ParTab_Len/2) + sub ax,ax + cld + rep stosw + + mov al,[MomDrive] ; neuen MBR schreiben + mov ah,0 + mov bx,0 + mov cx,0101h + lea si,[SectorBuffer] + call WriteSectors + ljc PartError + +End: pop es + pop di + pop si + pop dx + pop cx + pop bx + + ret + +PartError: push ax ; Fehlercode retten + pushf + PrMsg NewLine + popf + pop ax + mov ah,[MomDrive] ; Fehlermeldung ausgeben + call WrErrorCode + jmp End + +ConfirmMsg: db "ACHTUNG! Alle bisherigen Partitionen auf der",CR,LF + db "Festplatte werden gel”scht! Fortfahren? $" + + endp + +;---------------------------------------------------------------------------- + + proc FormatPart + + pusha + + mov ax,ds ; wir arbeiten nur im Datensegment + mov es,ax + + PrMsg ConfirmMsg ; vorher nachfragen + call YesNo + ljc Ende + + mov al,[MomDrive] ; Laufwerk rekalibrieren + call Recalibrate + ljc LFormError + +; Schritt 1: MBR lesen + + mov al,[MomDrive] ; MBR auslesen, um Partitions- + mov ah,0 ; daten zu bekommen + mov bx,0 + mov cx,0101h + lea di,[SectorBuffer] + call ReadSectors + ljc LFormError + +; Schritt 2: Partitionsdaten in BPB kopieren + + lea di,[SectorBuffer+ParTab_Offset] ; auf Partitionsdaten + mov al,[di+ParTab_Type] ; muá prim„re Partition sein + cmp al,1 ; DOS 2.x FAT12? + je ParTypeOK + cmp al,4 ; DOS 3.x FAT16? + je ParTypeOK + cmp al,6 ; DOS 4.x BIGDOS? + je ParTypeOK + PrMsg InvParTypeMsg ; nichts dergleichen: Abbruch + jmp Ende +ParTypeOK: mov word ptr[BPB_SysID],'AF' ; FAT-Kennung in BPB eintragen + mov word ptr[BPB_SysID+2],'1T' ; FAT12/FAT16 + mov word ptr[BPB_SysID+5],' ' + mov ah,'2' ; Annahme FAT12 + cmp al,1 + je ParIsFAT12 ; wenn Typ=1, OK + mov ah,'6' ; ansonsten FAT16 +ParIsFAT12: mov byte ptr[BPB_SysID+4],ah + mov ax,[di+ParTab_NSecs] ; Sektorzahl in BPB schreiben + mov dx,[di+ParTab_NSecs+2] + mov word ptr[BPB_NumSecs32],ax + mov word ptr[BPB_NumSecs32+2],dx + or dx,dx ; falls < 64K Sektoren, + jz ParIsNotBig ; Gr”áe auch unten eintragen, + sub ax,ax ; ansonsten 0 +ParIsNotBig: mov [BPB_NumSecs16],ax + mov ax,word ptr[di+ParTab_LinSec] ; Startsektor umkopieren + mov dx,word ptr[di+ParTab_LinSec+2] + mov word ptr[BPB_LinStart],ax + mov word ptr[BPB_LinStart+2],dx + +; Schritt 3: Partitionsdaten in Partitionstabelle kopieren, damit wir die +; linearen Schreib/Lesefunktionen nutzen k”nnen + + mov [DrCnt],1 ; nur ein Laufwerk belegt + mov ah,[di+ParTab_FHead] ; Startkoordinate ablegen + mov bx,[di+ParTab_FSecCyl] + call UnpackCoordinate + mov [DrTab+DrTab_StartHead],ah + mov word ptr [DrTab+DrTab_StartCyl],bx + mov [DrTab+DrTab_StartSec],al + mov ax,[di+ParTab_LinSec] + mov word ptr [DrTab+DrTab_LinStart],ax + mov ax,[di+ParTab_LinSec+2] + mov word ptr [DrTab+DrTab_LinStart+2],ax + mov ax,[di+ParTab_NSecs] + mov word ptr [DrTab+DrTab_SecCnt],ax + mov ax,[di+ParTab_NSecs+2] + mov word ptr [DrTab+DrTab_SecCnt+2],ax + mov al,[MomDrive] ; Laufwerk einschreiben + mov [DrTab+DrTab_Drive],al + mov byte ptr[DrTab+DrTab_BPB],0 ; kein BPB + +; Schritt 4: konstante Felder in BPB eintragen + + mov [BPB_SecSize],SecSize ; Sektorgr”áe konstant 512 Byte + mov [BPB_ResvdSecs],1 ; nur Bootsektor reserviert + mov [BPB_NumFATs],2 ; 2 FATs ist DOS-Standard + mov [BPB_MediaID],0f8h ; Media-Byte fr Platten konstant + mov al,[MomDrive] + call GetPTabAdr + mov ah,0 + mov al,[di+DrPar_NSecs]; Plattenzylinder und -k”pfe + mov [BPB_SecsPerTrk],ax + mov al,[di+DrPar_Heads] + mov [BPB_Heads],ax + mov al,[MomDrive] ; Plattennummer+80h + add al,80h + mov [BPB_PhysNo],ax + mov [BPB_ExtID],29h ; Erkennung, daá erw. BPB gltig + mov ah,0 ; Seriennummer=Uhrzeit + int INT_Clock + mov word ptr[BPB_SerialNo],cx + mov word ptr[BPB_SerialNo+2],dx + lea di,[BPB_Name] ; Name ist leer + mov cx,11 + mov al,' ' + cld + rep stosb + +; Schritt 5: einige Sachen vom Anwender erfragen + +DirEntLoop: mov ax,1024 ; mehr ist wohl kaum sinnvoll + lea di,[DirEntriesMsg] + call ReadNumber + cmp ax,SecSize/32 ; weniger als ein Sektor ergibt + jb DirEntLoop ; keinen Sinn + mov [BPB_DirLen],ax ; Anzahl in BPB eintragen + mov dx,0 ; Directory-Sektorzahl berechnen + mov bx,SecSize/32 + div bx + or dx,dx ; ggfs. aufrunden + jz DirLenEven + inc ax +DirLenEven: mov [DirLen],ax + +; Schritt 6: Clusterl„nge berechnen + + mov ax,word ptr[BPB_NumSecs32] ; # Sektoren in Datenfeld + mov dx,word ptr[BPB_NumSecs32+2] ; und FATs berechnen + sub ax,[BPB_ResvdSecs] + sbb dx,0 + sub ax,[DirLen] + sbb dx,0 + mov bl,1 ; Annahme: m”glichst wenig Sektoren pro Cluster +ClusterLoop: or dx,dx ; wenn noch mehr als 64K Cluster, + jnz ClusterNxtLoop ; auf jeden Fall zu groá + cmp ax,4080 ; bei weniger als 4K Clustern + jb ClusterEndLoop ; auf jeden Fall OK + cmp [BPB_SysID+4],'2' ; sonst bei FAT12 + je ClusterNxtLoop ; auf jeden Fall zu viel + cmp ax,65510 ; bei FAT16 Vergleich auf 64K + jb ClusterEndLoop +ClusterNxtLoop: shl bl,1 ; zu viel: Cluster verdoppeln + js ClusterEndLoop ; bei 128 Sektoren/Cluster abbrechen + shr dx,1 ; Clusterzahl halbiert sich + rcr ax,1 + jmp ClusterLoop +ClusterEndLoop: mov [BPB_SecsPerClust],bl ; Ergebnis einschreiben + add ax,2 ; Dummy-Eintr„ge in FAT + adc dx,0 + mov bx,341 ; Anzahl FAT-Sektoren berechnen + cmp [BPB_SysID+4],'2' + jz Cluster12 + mov bx,256 +Cluster12: div bx + or dx,dx ; Sektorzahl aufrunden + jz FATLenEven + inc ax +FATLenEven: mov [BPB_SecsPerFAT],ax ; Anzahl FAT-Sektoren einschreiben + +; Schritt 7: Bootsektor aufbauen + + PrMsg WrBootSectMsg + lea di,[SectorBuffer] + cld + mov al,0ebh ; Dummy-Sprung einschreiben + stosb + mov al,0feh + stosb + mov al,90h + stosb + mov ax,'ES' ; OEM-ID einschreiben + stosw + mov ax,'DC' + stosw + mov ax,'IR' + stosw + mov ax,'EV' + stosw + lea si,[BPBBuffer] ; BPB einschreiben + mov cx,BPB_Length + rep movsb + mov cx,SectorBuffer+SecSize ; Rest vom Bootsektor nullen + sub cx,di + mov al,0 + rep stosb + mov ax,0 ; Bootsektor ist log. Sektor 0 + mov dx,ax + mov bl,0 ; Partition 0 + call TranslateParams + mov cl,1 ; nur ein Sektor + lea si,[SectorBuffer] + call WriteSectors + ljc LFormError + +; Schritt 8: Directory & FATs ausnullen + + lea di,[SectorBuffer] ; Sektorpuffer wird benutzt + mov cx,SecSize/2 + cld + sub ax,ax + rep stosw + PrMsg WrFATMsg + mov ax,[BPB_ResvdSecs] ; Startsektor FATs holen + sub dx,dx + lea si,[SectorBuffer] + mov cx,[BPB_SecsPerFAT] + add cx,cx ; beide FATs nullen +FATZeroLoop: push ax ; Sektornummer und -zahl retten + push cx + push dx + mov bl,0 + call TranslateParams + mov cl,1 + call WriteSectors + pop dx + pop cx + pop ax + ljc LFormError + add ax,1 ; n„chster Sektor + adc dx,0 + loop FATZeroLoop + push ax ; !!! PrMsg zerst”rt AX-Register + PrMsg WrDirMsg + pop ax + mov cx,[DirLen] ; dito fr Directory +DirZeroLoop: push ax + push cx + push dx + mov bl,0 + call TranslateParams + mov cl,1 + call WriteSectors + pop dx + pop cx + pop ax + ljc LFormError + add ax,1 ; n„chster Sektor + adc dx,0 + loop DirZeroLoop + +; Schritt 9: Sektoren testen und FAT initialisieren + + mov ax,[BPB_ResvdSecs] ; Datensektorbeginn berechnen + sub dx,dx + mov [FAT1Pos],ax ; Beginn 1. FAT hinter Bootsektor + mov [FAT1Pos+2],dx + add ax,[BPB_SecsPerFAT] ; Beginn 2. FAT hinter 1. FAT + adc dx,0 + mov [FAT2Pos],ax + mov [FAT2Pos+2],dx + add ax,[BPB_SecsPerFAT] + adc dx,0 + add ax,[DirLen] ; Datenbeginn hinter Directory + adc dx,0 + mov [DataPos],ax ; diesen Startsektor retten + mov [DataPos+2],dx + + mov ax,word ptr[BPB_NumSecs32] ; Anzahl Cluster berechnen + mov dx,word ptr[BPB_NumSecs32+2] + sub ax,[DataPos] + sbb dx,[DataPos+2] + mov bl,[BPB_SecsPerClust] ; / SecsPerCluster + mov bh,0 + div bx + mov [ClusterCnt],ax + + call ClearFATBuffer ; erste Elemente in FAT schreiben + mov ah,0ffh + mov al,[BPB_MediaID] + call WriteFAT + mov al,0ffh + call WriteFAT + PrMsg ESCMsg + mov ax,[DataPos] ; Schleifenvorbereitung + mov dx,[DataPos+2] + mov cx,[ClusterCnt] +VerifyLoop: push ax ; Z„hler retten + mov bp,cx + push dx + mov bl,0 ; immer Laufwerk 0 + call TranslateParams ; Cluster testlesen + mov cl,[BPB_SecsPerClust] + test bp,15 ; nur alle 16 Cluster schreiben + jnz NoWriteVeri + push ax ; Clusternummer ausgeben + push cx + PrMsg ClusterMsg + mov ax,[ClusterCnt] + sub ax,bp + add ax,2 ; erster Datencluster hat Nummer 2 + mov cl,5 + call WriteDec + PrChar CR + pop cx + pop ax +NoWriteVeri: call VeriSectors + mov ax,0 ; Annahme OK (SUB wrde C l”schen...) + jnc Verify_OK + mov ax,0fff7h +Verify_OK: call WriteFAT + pop dx ; Z„hler zurck + mov cx,bp + pop ax + add al,[BPB_SecsPerClust] + adc ah,0 + adc dx,0 + call BreakOnESC ; Abbruch durch Benutzer ? + jc Ende + loop VerifyLoop + cmp [FATBufferFill],0 ; Puffer rausschreiben + je NoFATFlush + call FlushFATBuffer +NoFATFlush: + +Ende: PrMsg NewLine + mov [DrCnt],0 ; sonst kommt jemand ins Schleudern... + popa + ret + +LFormError: push ax ; Fehlercode retten + pushf + PrMsg NewLine + popf + pop ax + mov ah,[MomDrive] ; Fehlermeldung ausgeben + call WrErrorCode + jmp Ende + +WriteFAT: push bx ; einen FAT-Eintrag schreiben + mov bx,ax + call WriteFATNibble ; Bit 0..3 schreiben + mov al,bl ; Bit 4..7 schreiben + shr al,4 + call WriteFATNIbble + mov al,bh ; Bit 8..11 schreiben + call WriteFATNibble + cmp [BPB_SysID+4],'2' ; evtl. Bit 12..15 schreiben + je WriteFAT12 + mov al,bh + shr al,4 + call WriteFATNibble +WriteFAT12: pop bx + ret + +WriteFATNibble: push bx + and al,15 ; Bit 0..3 ausmaskieren + jz SkipWriteNibble ; Nullen brauchen wir nicht schreiben + mov [MustFlushFAT],1 ; vermerken, daá Puffer nicht genullt ist + mov bx,[FATBufferFill] ; Bit 1.. enthalten Adresse + shr bx,1 + jnc WriteFATLower ; oben oder unten schreiben + shl al,4 +WriteFATLower: or FATBuffer[bx],al +SkipWriteNibble:inc [FATBufferFill] + cmp [FATBufferFill],SecSize*2 ; Sektor voll ? + jne WriteFAT_NFlush + call FlushFATBuffer +WriteFAT_NFlush:pop bx + ret + +FlushFATBuffer: push bx + push cx + push dx + push si + cmp [MustFlushFAT],0 ; nix zu tun ? + je SkipFlushDisk + mov ax,[FAT1Pos] ; erste FAT schreiben + mov dx,[FAT1Pos+2] + mov bl,0 + call TranslateParams + mov cl,1 + lea si,[FATBuffer] + call WriteSectors + mov ax,[FAT2Pos] ; zweite FAT schreiben + mov dx,[FAT2Pos+2] + mov bl,0 + call TranslateParams + mov cl,1 + lea si,[FATBuffer] + call WriteSectors +SkipFlushDisk: call ClearFATBuffer ; Zeiger wieder auf 0 + add [FAT1Pos],1 ; FAT-Sektornummern weiterz„hlen + adc [FAT1Pos+2],0 + add [FAT2Pos],1 + adc [FAT2Pos+2],0 + pop si + pop dx + pop cx + pop bx + ret + + +ClearFATBuffer: push cx + push di + cld + lea di,[FATBuffer] + mov cx,SecSize/2 + sub ax,ax + rep stosw + pop di + pop cx + mov [FATBufferFill],ax + mov [MustFlushFAT],al + ret + +ConfirmMsg db "ACHTUNG! Alle Daten gehen verloren! Fortfahren? $" +InvParTypeMsg db CR,LF,"Partition 1 hat ungltigen Typ oder ist undefiniert!",CR,LF,'$' +DirEntriesMsg db "Anzahl Eintr„ge im Wurzelverzeichnis (16..1024) : $" +WrBootSectMsg db "Schreibe Boot-Sektor...",CR,LF,'$' +WrFATMsg db "Initialisiere FATs...",CR,LF,'$' +WrDirMsg db "Initialisiere Wurzelverzeichnis...",CR,LF,'$' +ESCMsg db "Abbruch mit ",CR,LF,'$' +ClusterMsg db "Teste Cluster $" + +DirLen dw ? ; # Directory-Sektoren +ClusterCnt dw ? +FAT1Pos dw 2 dup (?) ; speichern Sektorz„hler w„hrend Test +FAT2Pos dw 2 dup (?) +DataPos dw 2 dup (?) + +BPBBuffer: ; Zwischenspeicher fr BPB +BPB_SecSize dw ? ; Sektorgr”áe in Bytes +BPB_SecsPerClust db ? ; Sektoren pro Cluster +BPB_ResvdSecs dw ? ; reservierte Sektoren (Bootsektor) +BPB_NumFATs db ? ; Anzahl FATs +BPB_DirLen dw ? ; Anzahl Eintr„ge im Directory +BPB_NumSecs16 dw ? ; Anzahl Sektoren, falls <32 MByte +BPB_MediaID db ? ; Media-Erkennungsbyte +BPB_SecsPerFAT dw ? ; Sektoren pro FAT +BPB_SecsPerTrk dw ? ; Sektoren pro Spur +BPB_Heads dw ? ; Anzahl K”pfe +BPB_LinStart dd ? ; linearer Startsektor auf Laufwerk +BPB_NumSecs32 dd ? ; Anzahl Sektoren, falls >=32 MByte +BPB_PhysNo dw ? ; physikalische Laufwerks-Nummer +BPB_ExtID db ? ; Erkennung, daá es ein erweiterter Boot-Record ist +BPB_SerialNo dd ? ; Seriennummer +BPB_Name db 11 dup (?) ; Name +BPB_SysID db 7 dup (?) ; Systemerkennung +BPB_Length equ $-BPBBuffer ; L„nge BPB + +FATBuffer db SecSize dup (?) ; Puffer, um FATs aufzubauen +MustFlushFAT db ? ; Flag, ob FAT-Puffer geschrieben werden muá +FATBufferFill dw ? ; Anzahl Nibbles in FAT-Puffer + + endp + +;---------------------------------------------------------------------------- + + globproc DiskMenu + + push ax ; Register retten + push cx + push di + + mov [spsave],sp ; Stack umschalten + mov [sssave],ss + mov ax,cs + mov ss,ax + lea sp,[Stack] + +MenuLoop: mov al,[MomDrive] ; Festplatten-Nr. in Kopfmeldung einschreiben + add al,'1' + cmp al,'0' + jnz DrivePresent ; falls Laufwerk noch undefiniert, - ausgeben + mov al,'-' +DrivePresent: mov [MenuMsg_Drv],al + PrMsg MenuMsg + mov al,[MomDrive] + cmp al,-1 ; falls <>-1, Geometrie ausgeben + je NoDrivePresent + call GetPTabAdr ; dazu Tabelle holen + mov ax,[di+DrPar_Cyls] + mov cl,5 + call WriteDec + PrMsg CylMsg + mov al,[di+DrPar_Heads] + mov ah,0 + mov cl,3 + call WriteDec + PrMsg HeadMsg + mov al,[di+DrPar_NSecs] + mov ah,0 + mov cl,3 + call WriteDec + PrMsg SecMsg +NoDrivePresent: + PrMsg MenuList + mov ah,DOS_RdChar + int INT_DOS + push ax + PrChar al + PrMsg TwoLines + pop ax + + cmp al,'0' ; 0 = Men verlassen + lje MenuEnd + + cmp al,'1' ; 1 = Platte wechseln + jne NoSelectDisk + mov ah,1 ; Rckschreiben erlaubt + call SelectDisk + jmp MenuLoop +NoSelectDisk: + cmp al,'2' ; 2 = Geometrie wechseln + jne NoChangeGeometry + call ChangeGeometry + jmp MenuLoop +NoChangeGeometry: + cmp [MomDrive],-1 ; fr alles weitere muá Platte gesetzt sein + jne DiskIsSelected + push ax + shl ax,8 ; Annahme: Geometrie nicht zurckschreiben + cmp ah,'3' + je NoWriteBack + inc al ; fr alles auáer low-level schon +NoWriteBack: call SelectDisk ; implizit Laufwerk erfragen + PrMsg NewLine + pop ax + cmp [MomDrive],-1 + lje MenuLoop ; wenn immer noch nicht gesetzt, Abbruch +DiskIsSelected: + cmp al,'3' ; 3 = Platte low-leveln + jne NoFormatDisk + call FormatDisk + jmp MenuLoop +NoFormatDisk: + cmp al,'4' ; 4 = Spur formatieren + jne NoFormTrack + call FormTrack + jmp MenuLoop +NoFormTrack: + cmp al,'5' ; 5 = Platte prflesen + jne NoBadTrack + call BadTrack + jmp MenuLoop +NoBadTrack: + cmp al,'6' ; 6 = Platte verifizieren + jne NoVerifyDisk + call VerifyDisk + jmp MenuLoop +NoVerifyDisk: + cmp al,'7' ; 7 = Partition anlegen + jne NoMakePart + call MakePart + jmp MenuLoop +NoMakePart: + cmp al,'8' ; 8 = Partition formatieren + jne NoFormatPart + call FormatPart + jmp MenuLoop +NoFormatPart: PrChar BEL ; alle anderen Angaben anmeckern + jmp MenuLoop +MenuEnd: mov ss,[sssave] ; Stack zurck + mov sp,[spsave] + + pop di + pop cx + pop ax ; Register zurck + + ret + +MenuMsg db CR,LF,"SECDRIVE Men Platte:" +MenuMsg_Drv db '-',CR,LF,'$' +CylMsg db " Zylinder,$" +HeadMsg db " K”pfe,$" +SecMsg db " Sektoren",CR,LF,'$' +MenuList db CR,LF + db "1 = Platte wechseln",CR,LF + db "2 = Geometrie neu definieren",CR,LF + db "3 = Platte formatieren",CR,LF + db "4 = Spur formatieren",CR,LF + db "5 = Defekte Spuren markieren",CR,LF + db "6 = Platte verifizieren",CR,LF + db "7 = Partition erstellen",CR,LF + db "8 = Partition log. formatieren",CR,LF + db "------------------------",CR,LF + db "0 = Men verlassen",CR,LF,'$' +spsave dw ? +sssave dw ? + + db 1024 dup (?) ; Programmstack +Stack: + + endp + +MomDrive db -1 +TwoLines: db CR,LF +NewLine: db CR,LF,'$' + + endsection diff --git a/tests/t_secdrive/t_secdrive.asm b/tests/t_secdrive/t_secdrive.asm new file mode 100644 index 0000000..4fc82c9 --- /dev/null +++ b/tests/t_secdrive/t_secdrive.asm @@ -0,0 +1,1476 @@ +;****************************************************************************** +;* * +;* SECDRIVE - Treiber fr einen 2. HD-Kontroller im PC * +;* * +;* Historie: 12. 8.1993 Grundsteinlegung, Definitionen * +;* 16. 8.1993 Dispatcher * +;* Basislesefunktionen * +;* 17. 8.1993 Partitionsinformationen zusammenkratzen * +;* 18. 8.1993 Laufwerksparameter initialisieren * +;* 19. 8.1993 Zylinder/Sektorregister setzen * +;* Partitiossektorbaum durchgehen * +;* 24. 8.1993 BPB aufbauen * +;* 25. 8.1993 Parameterbersetzung * +;* Einlesen * +;* Sektoren schreiben * +;* 26. 8.1993 Fehlerbehandlung * +;* Verify * +;* 1. Restore-Versuch mit Seek * +;* 7. 9.1993 Versuch Version 1.39 mit Proc's * +;* 28. 9.1993 etwas gekrzt * +;* 27.12.1994 leichte Korrekturen im Restore * +;* 28.12.1994 Trennung Low-Level-Routinen begonnen * +;* 19. 1.1995 Fehlermeldungen im Klartext * +;* * +;****************************************************************************** + +;****************************************************************************** +;* globale Definitionen * +;****************************************************************************** + +; A C H T U N G : Mono.SYS muá fr Debugging geladen sein !!!! + +debug equ 0 +debug2 equ 0 + + include bitfuncs.inc + + cpu 80186 ; WD 1003 fordert min. 80286 + +Diag_NoError equ 01h ; Selbstdiagnosecodes: kein Fehler +Diag_ContError equ 02h ; Controller-Fehler +Diag_SBufError equ 03h ; Sektorpuffer defekt +Diag_ECCError equ 04h ; Fehlerkorrektor defekt +Diag_ProcError equ 05h ; Steuerprozessor defekt +Diag_Timeout equ 06h ; Controller antwortet nicht + +ParTab struct +BFlag db ? ; Partitionseintrag: Partition aktiv ? +FHead db ? ; Startkopf +FSecCyl dw ? ; Startzylinder/sektor +Type db ? ; Partitionstyp +LHead db ? ; Endkopf +LSecCyl dw ? ; Endzylinder/sektor +LinSec dd ? ; Anzahl Sektoren +NSecs dd ? ; linearer Startsektor + endstruct + +DErr_WrProtect equ 00h ; Treiberfehlercodes: Schreibschutz +DErr_InvUnit equ 01h ; unbekannte Ger„tenummer +DErr_NotReady equ 02h ; Laufwerk nicht bereit +DErr_Unknown equ 03h ; Unbekannes Treiberkommando +DErr_CRCError equ 04h ; Prfsummenfehler +DErr_InvBlock equ 05h ; ungltiger Request-Header +DErr_TrkNotFnd equ 06h ; Spur nicht gefunden +DErr_InvMedia equ 07h ; Unbekanntes Tr„gerformat +DErr_SecNotFnd equ 08h ; Sektor nicht gefunden +DErr_PaperEnd equ 09h ; Papierende im Drucker +DErr_WrError equ 0ah ; allg. Schreibfehler +DErr_RdError equ 0bh ; allg. Schreibfehler +DErr_GenFail equ 0ch ; allg. Fehler +DErr_InvChange equ 0fh ; unerlaubter Diskettenwechsel + +DErr_UserTerm equ 0ffh ; Fehlercode Abbruch durch Benutzer + +SecSize equ 512 ; Sektorgr”áe in Bytes +MaxPDrives equ 2 ; Maximalzahl physikalischer Laufwerke +MaxDrives equ 10 ; Maximalzahl verwaltbarer Laufwerke +MaxParts equ 4 ; Maximalzahl Partitionen in einem Sektor +MaxRetry equ 2 ; max. 2 Lese/Schreibversuche +StackSize equ 512 ; etwas mehr wg. Rekursion + +DrPar_Offset equ 1aeh ; Offset Parametertabelle im Part.-Sektor +ParTab_Offset equ 1beh ; Offset Partitionstabelle " " " +ParSecID_Offset equ 1feh ; Offset Partitionssektorflag (55aa) +BPBOfs equ 11 ; Offset BPB im Bootsektor + +INT_DOS equ 21h ; DOS-Funktionsaufruf +INT_Mono equ 60h ; Haken zum VT100-Treiber +INT_Clock equ 1ah ; BIOS-Uhreneinstieg +INT_Keyboard equ 16h ; BIOS-Tastatureinstieg + +DOS_WrString equ 9 ; DOS-Funktionen +DOS_WrChar equ 6 +DOS_RdString equ 10 +DOS_RdChar equ 8 + +HD_ID equ 0f8h ; Media-ID fr Festplatten + +CR equ 13 +LF equ 10 +BEL equ 7 +ESC equ 27 + +;****************************************************************************** +; Makros * +;****************************************************************************** + +;jmp macro adr +; !jmp long adr +; endm + +beep macro + push ax + mov ax,0e07h + int 10h + pop ax + endm + +PrMsg macro Adr ; Meldung ausgeben + push dx ; Register retten + lea dx,[Adr] + mov ah,DOS_WrString + int INT_DOS + pop dx ; Register zurck + endm + +PrChar macro Zeichen ; Zeichen ausgeben + push dx ; Register retten + push ax + mov dl,Zeichen + mov ah,DOS_WrChar + int INT_DOS + pop ax + pop dx ; Register zurck + endm + +;------------------------------------------------------------------------------ + +btst macro op,bit ; ein einzelnes Bit testen + test op,(1<ausgeben... + jmp Adr ; ...Abbruch +GoOn: + endm + +;****************************************************************************** +;* Treiberkopf * +;****************************************************************************** + + + assume cs:code,ds:nothing,ss:nothing,es:nothing + + org 0 + +DriverHead: dd -1 ; Zeiger auf Nachfolger + dw 0000100000000010b ; Attribut +; ^ ^ ^ +; ³ ³ ÀÄ kann 32-Bit-Setornummern verarbeiten +; ³ ÀÄÄÄÄÄÄÄÄÄÄÄ kennt Close/Open/Removeable +; ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Blocktreiber + dw StrategyProc ; Zeiger auf Strategieroutine + dw InterruptProc ; Zeiger auf eigentlichen Treibercode +NrOfVols: db 0 ; Zahl log. Laufwerke + db "SECDRIV" ; bei Blocktreibern unbenutzt + +;****************************************************************************** +;* residente Daten * +;****************************************************************************** + +Rh_Ptr dd ? ; Speicher fr Request-Header + +JmpTable dw Init ; Sprungtabelle: Initialisierung + dw MediaCheck ; Medium gewechselt ? + dw BuildBPB ; Parameterblock laden + dw IOCTLRead ; Steuerdaten vom Treiber + dw Read ; Daten lesen + dw ND_Read ; Lesen, ohne Pufferstatus zu „ndern + dw InputStatus ; Daten im Eingabepuffer ? + dw InputFlush ; Eingabepuffer l”schen + dw Write ; Daten schreiben + dw Write_Verify ; Daten mit Prflesen schreiben + dw OutputStat ; Ausgabepuffer leer ? + dw OutputFlush ; Ausgabepuffer l”schen + dw IOCTLWrite ; Steuerdaten zum Treiber + dw DeviceOpen ; DOS hat eine Datei darauf ge”ffnet + dw DeviceClose ; DOS hat eine Datei darauf geschlossen + dw Removeable ; Ist Datentr„ger wechselbar ? + dw OutputTillBusy ; Ausgabe, bis Puffer voll + dw GenIOCTL ; genormtes IOCTL + dw GetLogical ; Laufwerkszuordnung lesen + dw SetLogical ; Laufwerkszuordnung setzen + dw IOCTLQuery ; Abfrage, ob GenIOCTL untersttzt + +SectorBuffer: db SecSize dup (?) ; Sektorpuffer fr Treiber selber + + db StackSize dup (?) ; Treiberstack +DriverStack: + +BPBSize equ 36 +DrTab struct ; Laufwerkstabelle: +StartHead db ? ; Startkopf +StartCyl dw ? ; Startzylinder +StartSec db ? ; Startsektor +LinStart dd ? ; lin. Startsektor +SecCnt dd ? ; Gesamtsektorzahl +Drive db ? ; Laufwerk +BPB db BPBSize dup (?) ; BPB + endstruct + +DrTab db DrTab_Len*MaxDrives dup (?) +DrTab_BPBs dd 2*MaxDrives dup (?) +DrCnt db 0 ; Anzahl gefundener Laufwerke +DrOfs db 0 ; erster freier Laufwerksbuchstabe + +DrPar struct ; Plattenparametersatz: +Cyls dw ? ; Zylinderzahl +Heads db ? ; Kopfzahl +RedWr dw ? ; Startzylinder reduzierter Schreibstrom +PrComp dw ? ; Startzylinder Pr„kompensation +ECCLen db ? ; max. korrigierbarer Fehlerburst (Bits) +CByte db ? ; Wert frs Plattensteuerregister +TOut db ? ; genereller Timeout +FTOut db ? ; Timeout Formatierung +CTOut db ? ; Timeout fr Prfung +LZone dw ? ; Landezylinder +NSecs db ? ; Sektorzahl +Dummy db ? ; unbenutzt + endstruct + +DrPars db DrPar_Len*MaxPDrives dup (0) + +;****************************************************************************** +;* Strategieroutine * +;****************************************************************************** + +StrategyProc: mov word ptr [Rh_Ptr],bx ; Zeiger speichern + mov word ptr [Rh_Ptr+2],es + retf + +;****************************************************************************** +;* Treiberdispatcher * +;****************************************************************************** + +Rh struct +Size db ? ; gemeinsame Headerteile: L„nge Block +Unit db ? ; angesprochenes Laufwerk +Func db ? ; Treibersubfunktion +Status dw ? ; Ergebnis +Resvd db 8 dup (?) ; unbenutzt + endstruct + +InterruptProc: pusha ; alle Register retten + + cli ; Stack umschalten + mov si,ss ; alten zwischenspeichern + mov di,sp + mov ax,cs ; neuen setzen + mov ss,ax + lea sp,[DriverStack] + push di ; alten auf neuem (!) speichern + push si + sti + + mov ax,cs ; DS auf Treibersegment + mov ds,ax + assume ds:code + + les bx,[Rh_Ptr] ; Zeiger laden + mov word ptr es:[bx+Rh_Status],0 ; Status l”schen + + mov al,es:[bx+Rh_Func] ; Subfunktion ausrechnen + if debug + call PrByte + endif + mov ah,0 + add ax,ax + mov si,ax + jmp JmpTable[si] + + jmp Init + +;****************************************************************************** +;* gemeinsames Ende * +;****************************************************************************** + +StateError: btst al,1 ; Bit 1: Spur 0 nicht gefunden + jz StateError_N1 + mov al,DErr_TrkNotFnd + jmp StateError_End +StateError_N1: btst al,2 ; Bit 2: abgebrochenes Kommando + jz StateError_N2 + btst ah,5 ; Bit S5: Schreibfehler + jz StateError_N21 + mov al,DErr_WrError + jmp StateError_End +StateError_N21: btst ah,4 ; Bit S4: Positionierung nicht vollst„ndig + jnz StateError_N22 + mov al,DErr_TrkNotFnd + jmp StateError_End +StateError_N22: btst ah,6 ; Bit S6: Laufwerk nicht bereit + jnz StateError_N23 + mov al,DErr_NotReady + jmp StateError_End +StateError_N23: mov al,DErr_GenFail ; Notnagel 1 + jmp StateError_End +StateError_N2: test al,11h ; Bit 0/4: Sektor nicht gefunden + jz StateError_N3 + mov al,DErr_SecNotFnd + jmp StateError_End +StateError_N3: btst al,6 ; Bit 6: Prfsummenfehler + jz StateError_N4 + mov al,DErr_CRCError + jmp StateError_End +StateError_N4: mov al,DErr_GenFail ; Notnagel 2 +StateError_End: les bx,[Rh_Ptr] ; Code einspeichern + mov es:[bx+Rh_Status],al + jmp Error + +Unknown: les bx,[Rh_Ptr] + mov byte ptr es:[bx+Rh_Status],DErr_Unknown ; unbek. Funktion + +Error: or byte ptr es:[bx+Rh_Status+1],80h ; Fehler-Flag setzen + jmp Done + +Busy: les bx,[Rh_Ptr] + or byte ptr es:[bx+Rh_Status+1],2 ; Busy-Flag setzen + +Done: les bx,[Rh_Ptr] + or byte ptr es:[bx+Rh_Status+1],1 ; Done-Flag setzen + + if debug + call NxtLine + endif + + cli ; Stack zurckschalten + pop si + pop di ; alten in SI:DI laden + mov sp,di ; einschreiben + mov ss,si + sti + + popa ; Register zurck + retf + +;****************************************************************************** +;* Debugginghilfe * +;****************************************************************************** + + if debug||debug2 + +HexTab db "0123456789ABCDEF" + +PrByte: push es ; Register retten + push di + push bx + push ax + + lea bx,[HexTab] + + + db 0d4h,10h ; AAM 16 + push ax + mov al,ah + xlat + mov ah,0eh + int 10h + pop ax + xlat + mov ah,0eh + int 10h + + pop ax ; Register zurck + pop bx + pop di + pop es + ret + +PrWord: xchg ah,al ; Hi-Byte + call PrByte + xchg ah,al + call PrByte + ret + +PrChar: push ax + mov ah,0eh + int 10h + pop ax + ret + +NxtLine: push ax ; Register retten + push bx + push dx + + mov ax,0e0dh + int 10h + mov ax,0e0ah + int 10h + + pop dx ; Register zurck + pop bx + pop ax + + endif + +;****************************************************************************** +;* residente Subfunktionen * +;****************************************************************************** + +;****************************************************************************** +;* eine logische Laufwerksnummer berprfen * +;* In : AL = Laufwerk * +;* Out : C = 1, falls Fehler * +;****************************************************************************** + + proc ChkDrive + + cmp al,[DrCnt] ; C=1, falls < (d.h. OK) + cmc ; Deshalb noch einmal drehen + jnc OK ; C=0, alles in Butter + les bx,[Rh_Ptr] ; ansonsten Fehlerstatus setzen + mov byte ptr es:[bx+Rh_Status],DErr_InvUnit +OK: ret + + endp + +;****************************************************************************** +;* Adresse der phys. Laufwerkstabelle errechnen * +;* In : AL = Laufwerk * +;* Out : DI = Adresse * +;****************************************************************************** + + proc GetPTabAdr + + mov ah,DrPar_Len ; relative Adresse berechnen + mul ah + lea di,[DrPars] ; Offset dazu + add di,ax + ret + + endp + +;****************************************************************************** +;* Adresse eines Partitionsdeskriptors errechnen * +;* In : AL = log. Laufwerk * +;* Out : DI = Adresse * +;****************************************************************************** + + proc GetTabAdr + + mov ah,DrTab_Len ; relative Adresse berechnen + mul ah + lea di,[DrTab] ; Offset dazu + add di,ax + ret + + endp + +;****************************************************************************** +;* logische Parameter in physikalische bersetzen * +;* In : BL = log. Laufwerk * +;* DX:AX = relative Sektornummer * +;* Out : AL = phys. Laufwerk * +;* AH = Kopf * +;* BX = Zylinder * +;* CH = Sektor * +;****************************************************************************** + + proc TranslateParams + + push di ; Register retten + + xchg bx,ax ; Adresse Parametertabelle holen + call GetTabAdr + + add bx,[di+DrTab_LinStart] ; in absolute Sektornummer + adc dx,[di+DrTab_LinStart+2] ; umrechnen + mov al,[di+DrTab_Drive] ; phys. Laufwerksnummer holen + push ax ; bis zum Ende retten + + call GetPTabAdr ; von dieser phys. Platte die Tabelle holen + mov ax,bx ; Sektor# wieder nach DX:AX + mov bl,[di+DrPar_NSecs] ; Sektorzahl auf 16 Bit + mov bh,0 ; aufblasen + div bx + mov ch,dl ; Modulo-Rest ist Sektornummer auf + inc ch ; Spur: Vorsicht, Numerierung ab 1 !!! + sub dx,dx ; wieder auf 32 Bit erweitern + mov bl,[di+DrPar_Heads] ; Kopfnummer herausfummeln + div bx + mov bx,ax ; Quotient ist Zylinder + pop ax ; Laufwerk zurck + mov ah,dl ; Rest ist Kopf + + pop di ; Register zurck + ret + + endp + +;****************************************************************************** +;* Einbindung Low-Level-Routinen * +;****************************************************************************** + +; definiert werden mssen: + +; LowLevelIdent: Meldung ber untersttzte Hardware ausgeben +; ContDiag: Kontroller-Selbsttest durchfhren +; Ergebniskode in AL +; Recalibrate: Laufwerk [AL] auf Zylinder 0 fahren +; Fehlerflag in C, Fehlerkode in AX +; SetDriveParams: dem Kontroller die Geometrie fr Laufwerk [AL] einbleuen +; Fehlerflag in C +; ReadSectors: von Laufwerk [AL] ab Zylinder [BX], Kopf [AH], Sektor [CH] +; [CL] Sektoren in Puffer ab ES:DI lesen +; Fehlerflag in C, Fehlerkode in AX +; WriteSectors: auf Laufwerk [AL] ab Zylinder [BX], Kopf [AH], Sektor [CH] +; [CL] Sektoren von Puffer ab ES:SI schreiben +; Fehlerflag in C, Fehlerkode in AX +; VeriSectors: auf Laufwerk [AL] ab Zylinder [BX], Kopf [AH], Sektor [CH] +; [CL] Sektoren verifizieren +; Fehlerflag in C, Fehlerkode in AX +; FormatUnit: Laufwerk [AL] mit Interleave [AH] formatieren, Fehlerkode +; in AX +; FormatTrack: Zylinder [BX], Kopf [AH] auf Laufwerk [AL] mit Interleave +; [CL] formatieren, Fehlerkode in AX +; MarkBad: Zylinder [BX], Kopf [AH] auf Laufwerk [AL] als defekt +; markieren, Fehlerkode in AX + + include "lowlevel.inc" + +;****************************************************************************** +;* Bootsektor eines log. Laufwerkes lesen * +;* In : AL = Laufwerksnummer * +;* Out : C+AX = Fehlerstatus * +;****************************************************************************** + + proc ReadBootSec + + push es ; Register retten + push bx + push cx + push di + + call GetTabAdr ; Eintrag in Laufwerkstabelle ermitteln + mov al,[di+DrTab_Drive] ; davon ersten Sektor lesen + mov ah,[di+DrTab_StartHead] + mov bx,[di+DrTab_StartCyl] + mov cl,1 + mov ch,[di+DrTab_StartSec] + mov di,cs + mov es,di + lea di,[SectorBuffer] + call ReadSectors + + pop di ; Register zurck + pop cx + pop bx + pop es + ret + + endp + +;****************************************************************************** +;* Funktion 1: Test, ob Medium gewechselt * +;****************************************************************************** + + proc MediaCheck + +Rh_MediaID equ Rh_Resvd+8 ; erwartetes Media-ID +Rh_Return equ Rh_MediaID+1 ; Ergebnis-Flag +Rh_VolName equ Rh_Return+1 ; Adresse alter Laufwerksname + + cmp byte ptr es:[bx+Rh_MediaID],HD_ID ; gltige ID ? + je OK + mov byte ptr es:[bx+Rh_Status],DErr_InvMedia ; nein... + jmp Error +OK: mov byte ptr es:[bx+Rh_Return],1 ; nie gewechselt + jmp Done + + endp + +;****************************************************************************** +;* Funktion 2: BPB aufbauen * +;****************************************************************************** + + proc BuildBPB + +Rh2 struct + db Rh_Len dup (?) +MediaID db ? ; erwartetes Media-ID +FATSector dd ? ; Pufferadresse 1. FAT-Sektor +BPBAddress dd ? ; Adresse neuer BPB + endstruct + + mov al,es:[bx+Rh_Unit] + call ChkDrive ; Laufwerksnummer gltig ? + ljc Error ; nein-->Fehler & Ende + + call ReadBootSec ; Bootsektor lesen + ljc StateError ; bei Fehlern Ende + + les bx,[Rh_Ptr] ; Zeiger neu laden + mov al,es:[bx+Rh_Unit] ; Tabellenadresse aufbauen + call GetTabAdr + lea di,[di+DrTab_BPB] ; DI auf BPB-Speicher + mov es:[bx+Rh2_BPBAddress],di ; BPB-Zeiger abspeichern + mov es:[bx+Rh2_BPBAddress+2],cs + + mov si,cs ; BPB umkopieren + mov es,si + lea si,[SectorBuffer+BPBOfs] + cld + mov cx,BPBSize + rep movsb + + jmp Done + + endp + +;****************************************************************************** + +IOCTLRead: jmp Unknown + +;****************************************************************************** +;* Funktion 4: Sektoren lesen * +;****************************************************************************** + +Rh4 struct + db Rh_len dup (?) +MediaID db ? ; Media-ID Laufwerk +BufOfs dw ? ; Adresse Datenpuffer +BufSeg dw ? +NSecs dw ? ; Anzahl zu lesender Bl”cke +FirstSec dw ? ; Startsektor bzw. $FFFF fr 32-Bit-Nummern +VolID dd ? ; Adresse Laufwerksname +LFirstSec dw ? ; lange Startsektornummer +HFirstSec dw ? + endstruct + +Read: mov al,es:[bx+Rh_Unit] ; Laufwerksnummer prfen + call ChkDrive + ljc Error + + mov ch,al ; Laufwerksnummer retten + mov ax,es:[bx+Rh4_FirstSec] ; Sektor holen (BIGDOS beachten) + sub dx,dx + cmp ax,-1 + jne Read_SmallSec + mov ax,es:[bx+Rh4_LFirstSec] + mov dx,es:[bx+Rh4_HFirstSec] +Read_SmallSec: mov cl,es:[bx+Rh4_NSecs] ; Sektorzahl laden (muá <=128 sein) + les di,es:[bx+Rh4_BufOfs] ; Zieladresse laden + mov bl,ch ; Laufwerksnummer nach BL + + if debug + push ax + push cx + mov cx,ax + mov al,' ' + call PrChar + mov al,bl ; Laufwerksnummer + call PrByte + mov al,' ' + call PrChar + mov ax,dx ; Startsektor + call PrWord + mov ax,cx + call PrWord + mov al,' ' + call PrChar + pop cx + mov al,cl ; Sektorzahl + call PrByte + mov al,' ' + call PrChar + mov ax,es ; Startadresse + call PrWord + mov al,':' + call PrChar + mov ax,di + call PrWord + pop ax + endif + + call TranslateParams ; umrechnen lassen + call ReadSectors ; der eigentliche Lesevorgang + + ljc StateError ; bei Fehlern... + jmp Done ; ansonsten o.k. + +;****************************************************************************** + +ND_Read: jmp Unknown + +InputStatus: jmp Unknown + +InputFlush: jmp Unknown + +;****************************************************************************** +;* Funktion 8: Sektoren schreiben * +;****************************************************************************** + +Rh8 struct + db Rh_len dup (?) +MediaID db ? ; Media-ID Laufwerk +BufOfs dw ? ; Adresse Datenpuffer +BufSeg dw ? +NSecs dw ? ; Anzahl zu lesender Bl”cke +FirstSec dw ? ; Startsektor bzw. $FFFF fr 32-Bit-Nummern +VolID dd ? ; Adresse Laufwerksname +LFirstSec dw ? ; lange Startsektornummer +HFirstSec dw ? + endstruct + +DoWrite: if debug2 + mov al,es:[bx+Rh_Unit] + call PrByte + mov al,' ' + call PrChar + mov ax,es:[bx+Rh8_FirstSec] + call PrWord + mov al,' ' + mov ax,es:[bx+Rh8_HFirstSec] + call PrWord + mov ax,es:[bx+Rh8_LFirstSec] + call PrWord + call NxtLine + endif + + mov al,es:[bx+Rh_Unit] + mov ch,al ; Laufwerksnummer retten + mov ax,es:[bx+Rh8_FirstSec] ; Sektor holen (BIGDOS beachten) + sub dx,dx + cmp ax,-1 + jne DWrite_SmallSec + mov ax,es:[bx+Rh8_LFirstSec] + mov dx,es:[bx+Rh8_HFirstSec] +DWrite_SmallSec:mov cl,es:[bx+Rh8_NSecs] ; Sektorzahl laden (muá <=128 sein) + les si,es:[bx+Rh8_BufOfs] ; Zieladresse laden + mov bl,ch ; Laufwerksnummer nach BL + + if debug + push ax + push cx + mov cx,ax + mov al,' ' + call PrChar + mov al,bl ; Laufwerksnummer + call PrByte + mov al,' ' + call PrChar + mov ax,dx ; Startsektor + call PrWord + mov ax,cx + call PrWord + mov al,' ' + call PrChar + pop cx + mov al,cl ; Sektorzahl + call PrByte + mov al,' ' + call PrChar + mov ax,es ; Startadresse + call PrWord + mov al,':' + call PrChar + mov ax,si + call PrWord + pop ax + endif + + call TranslateParams ; umrechnen lassen + call WriteSectors ; der eigentliche Lesevorgang + + ret + +Write: mov al,es:[bx+Rh_Unit] ; Laufwerksnummer prfen + call ChkDrive + ljc Error + + call DoWrite + + ljc StateError ; bei Fehlern... + jmp Done ; ansonsten o.k. + + +;****************************************************************************** +;* Funktion 9: Sektoren schreiben mit šberprfung * +;****************************************************************************** + +Rh9 struct + db Rh_len dup (?) +MediaID db ? ; Media-ID Laufwerk +BufOfs dw ? ; Adresse Datenpuffer +BufSeg dw ? +NSecs dw ? ; Anzahl zu lesender Bl”cke +FirstSec dw ? ; Startsektor bzw. $FFFF fr 32-Bit-Nummern +VolID dd ? ; Adresse Laufwerksname +LFirstSec dw ? ; lange Startsektornummer +HFirstSec dw ? + endstruct + +Write_Verify: mov al,es:[bx+Rh_Unit] ; Laufwerksnummer prfen + call ChkDrive + ljc Error + + call DoWrite ; schreiben + + ljc StateError ; bei Fehlern vorher abbrechen + + les bx,[Rh_Ptr] ; Parameter nochmal fr Verify laden + mov al,es:[bx+Rh_Unit] + mov ch,al + mov ax,es:[bx+Rh9_FirstSec] + sub dx,dx + cmp ax,-1 + jne VWrite_SmallSec + mov ax,es:[bx+Rh9_LFirstSec] + mov dx,es:[bx+Rh9_HFirstSec] +VWrite_SmallSec:mov cl,es:[bx+Rh9_NSecs] + mov bl,ch + + call TranslateParams ; nochmal umrechen... + call VeriSectors ; und prflesen + + jmp Done ; alles gut gegangen + +;****************************************************************************** + +OutputStat: jmp Unknown + +OutputFlush: jmp Unknown + +IOCTLWrite: jmp Unknown + +;****************************************************************************** +;* kein Device wechselbar, ™ffnen/Schleáen interessiert nicht * +;****************************************************************************** + +DeviceOpen: jmp Done + +DeviceClose: jmp Done + +Removeable: jmp Done + +;****************************************************************************** + +OutputTillBusy: jmp Unknown + +GenIOCTL: jmp Unknown + +GetLogical: jmp Unknown + +SetLogical: jmp Unknown + +IOCTLQuery: jmp Unknown + +;****************************************************************************** +;* Funktion 0: Initialisierung * +;****************************************************************************** + + include "secparam.inc" + +Rh0 struct + db Rh_len dup (?) +Units db ? ; Zahl bedienter Laufwerke +EndOfs dw ? ; Endadresse Offset +EndSeg dw ? ; Endadresse Segment +ParamOfs dw ? ; Parameter Offsetadresse +ParamSeg dw ? ; Parameter Segmentadresse +FirstDrive db ? ; erstes freies Laufwerk +MsgFlag db ? ; Flag, ob DOS Fehler ausgeben darf + endstruct + +Init: PrMsg HelloMsg ; Meldung ausgeben + call LowLevelIdent ; Startmeldung des Low-Level-Treibers + + mov byte ptr es:[bx+Rh0_Units],0 ; noch keine Laufwerke + + mov al,es:[bx+Rh0_FirstDrive] ; Startlaufwerk retten + mov [DrOfs],al + + mov ax,cs ; ES auf gem. Segment + mov es,ax + +; Schritt 1: Controller prfen + + PrMsg DiagMsg0 + call ContDiag ; Diagnose ausfhren + sub al,Diag_NoError + cmp al,6 ; auáerhalb ? + jae Diag_Over + add al,al ; Meldung ausrechnen + mov ah,0 + mov si,ax + mov dx,DiagMsgTable[si] + mov ah,9 + int INT_DOS + or si,si ; fehlerfrei ? + ljnz Init_Err ; Nein, Fehler + jmp Init_ChkDrives ; Ja, weiter zum Laufwerkstest + +Diag_Over: push ax + PrMsg UndefDiagMsg ; undefinierter Fehlercode + pop ax + add al,Diag_NoError ; Meldung rckkorrigieren + db 0d4h,10h ; AAM 16 + add ax,'00' + push ax + mov al,ah + mov ah,14 + int 10h + pop ax + mov ah,14 + int 10h + PrChar CR + PrChar LF + jmp Init_Err + + +; Schritt 2: Laufwerke testen + +; Menaufruf? + +Init_ChkDrives: mov ax,40h ; CTRL gedrckt ? + mov es,ax + btst byte ptr es:[17h],2 + jz Init_Menu + call DiskMenu + +; Schritt 2a: Laufwerk rekalibrieren + +Init_Menu: mov al,[MomDrive] + call Recalibrate + ljc Init_NextDrive ; Fehler: Laufwerk berspringen + +; Schritt 2b: Masterpartitionssektor lesen + +ReadMaster: mov al,[MomDrive] + mov ah,0 ; Kopf... + sub bx,bx ; ...Zylinder... + mov cx,0101h ; ...ein Sektor ab Sektor 1 + mov di,ds + mov es,di + lea di,[SectorBuffer] ; in den Sektorpuffer + call ReadSectors + JmpOnError [MomDrive],Init_NextDrive ; Fehler ? + +; Schritt 2c: Laufwerksparameter initialisieren + + lea si,[SectorBuffer+DrPar_Offset] ; Quelladresse im Sektor + mov al,[MomDrive] ; Zieladresse ausrechnen + call GetPTabAdr + mov cx,DrPar_Len + cld + rep movsb + + sub di,DrPar_Len ; Laufwerk nicht initialisiert ? + cmp word ptr[di+DrPar_Cyls],0 + je DoQuery + cmp byte ptr[di+DrPar_Heads],0 + je DoQuery + cmp byte ptr[di+DrPar_NSecs],0 + jne NoQuery +DoQuery: mov al,[MomDrive] ; wenn ja, dann nachfragen + mov ah,1 ; Rckschreiben hier erlaubt + call QueryParams + or al,al ; =0-->Laufwerk ignorieren + jz Init_NextDrive + dec al ; =1-->nochmal lesen + jz ReadMaster ; ansonsten weitermachen + +NoQuery: mov al,[MomDrive] ; Laufwerksparameter ausgeben... + call PrintPDrive + mov al,[MomDrive] ; ...und dem Controller einbleuen + call SetDriveParams + JmpOnError [MomDrive],Init_NextDrive + mov al,[MomDrive] + call Recalibrate + JmpOnError [MomDrive],Init_NextDrive + +; Schritt 2d: durch die Partitionssektoren hangeln + + mov al,[MomDrive] ; Laufwerk : momentanes + cbw ; Kopf : 0 + push ax + sub ax,ax + push ax ; Zylinder : 0 + inc ax ; Sektor : 1 + push ax + dec ax + push ax ; lin. Sektornummer 0 + push ax + call ScanParts + +Init_NextDrive: inc [MomDrive] ; Z„hler weitersetzen + cmp [MomDrive],MaxPDrives + ljb Init_ChkDrives + + cmp [DrCnt],0 ; keine Partitionen gefunden ? + jne Init_PDrives + PrMsg ErrMsgNoDrives ; ja: meckern + jmp Init_Err + +Init_PDrives: PrMsg LDriveMsg + mov [MomDrive],0 ; Parameter der Partitionen ausgeben + lea bp,[DrTab_BPBs] ; und BPB-Tabelle aufbauen + cld + +Init_PLDrives: mov al,[MomDrive] + call PrintLDrive + + mov al,[MomDrive] ; Bootsdektor lesen + call ReadBootSec + lea si,[SectorBuffer+BPBOfs] ; BPB rauskopieren + mov al,[MomDrive] + call GetTabAdr + lea di,[di+DrTab_BPB] + mov ax,cs + mov es,ax + mov ds:[bp],di ; Adresse nebenbei ablegen + add bp,2 + mov cx,BPBSize + rep movsb + + inc [MomDrive] + mov al,[MomDrive] + cmp al,[DrCnt] + jb Init_PLDrives + + PrChar LF ; sieht besser aus... + + les bx,[Rh_Ptr] ; Zeiger auf BPB-Zeiger einschreiben + lea ax,[DrTab_BPBs] + mov es:[bx+Rh0_ParamOfs],ax + mov es:[bx+Rh0_ParamSeg],cs + jmp Init_OK ; Initialisierung erfolgeich zu Ende + +Init_Err: PrMsg WKeyMsg + xor ah,ah ; damit Meldung lesbar bleibt + int 16h + sub ax,ax ; Treiber aus Speicher entfernen + jmp Init_End + +Init_OK: mov al,[DrCnt] ; Laufwerkszahl holen + les bx,[Rh_Ptr] + mov es:[bx+Rh0_Units],al ; im Request Header eintragen + mov [NrOfVols],al ; im Treiberkopf eintragen + lea ax,[Init] ; residenten Teil installieren + +Init_End: les bx,[Rh_Ptr] + mov es:[bx+Rh0_EndOfs],ax ; Endadresse setzen + mov es:[bx+Rh0_EndSeg],cs + + jmp Done + +;****************************************************************************** +;* transiente Unterroutinen * +;****************************************************************************** + +;****************************************************************************** +;* Partitionsbaum durchgehen * +;* In : dw Kopf/Laufwerk * +;* dw Zylinder * +;* dw Sektor * +;* dd lineare Nummer des Sektors * +;****************************************************************************** + +ScParts_DrHd equ 12 ; Parameteradressen auf Stack +ScParts_Cyl equ 10 +ScParts_Sec equ 8 +ScParts_LinSec equ 4 +ScParts_ParTab equ 0-(MaxParts*ParTab_Len) ; Kopie Partitionstabelle +ScParts_LocSize equ 0-ScParts_ParTab ; belegter Stack + +ScanParts: enter ScParts_LocSize,0 + +; Partitionssektor lesen + + mov ax,[bp+ScParts_DrHd] + mov bx,[bp+ScParts_Cyl] + mov ch,[bp+ScParts_Sec] + mov cl,1 + mov di,cs + mov es,di + lea di,[SectorBuffer] + call ReadSectors + JmpOnError [MomDrive],ScanParts_End + +; Partitionssektorkennung o.k. ? + + cmp word ptr SectorBuffer[ParSecID_Offset],0aa55h + ljne ScanParts_End + +; Partitionstabelle auslesen + + lea si,[SectorBuffer+ParTab_Offset] ; Quelladresse + mov di,ss ; Zieladresse auf Stack + mov es,di + lea di,[bp+ScParts_ParTab] + mov cx,MaxParts*ParTab_Len ; L„nge + cld + rep movsb + +; Partitionstabelle durchgehen + + mov si,ScParts_ParTab ; vorne anfangen + mov cx,MaxParts ; alle durchgehen +ScanParts_Scan: push cx + + mov al,[bp+si+ParTab_Type] ; Typ der Partition lesen + lea bx,[AccPartTypes-1] ; auf Suchtabelle +ScanParts_LAcc: inc bx ; einen Eintrag weiter + cmp byte ptr [bx],0 ; Tabellenende ? + je ScanParts_Next ; ja-->war nix + cmp al,[bx] ; gefunden ? + jne ScanParts_LAcc ; + + mov bx,[bp+si+ParTab_LinSec] ; linearen Startsektor ausrechnen + mov cx,[bp+si+ParTab_LinSec+2] + add bx,[bp+ScParts_LinSec] ; in CX:BX + adc cx,[bp+ScParts_LinSec+2] + + cmp al,5 ; extended partition ? + jne ScanParts_Enter + + push si ; ja: Zeiger fr Rekursion retten + mov al,[bp+ScParts_DrHd] ; Laufwerk & Kopf zusammenbauen + mov ah,[bp+si+ParTab_FHead] + push ax + mov ax,[bp+si+ParTab_FSecCyl] ; Zylinder ausfiltern + xchg ah,al + shr ah,6 + push ax + mov al,[bp+si+ParTab_FSecCyl] ; Sektor ausfiltern + and ax,63 + push ax + push cx + push bx + call ScanParts + pop si ; Zeiger zurck + jmp ScanParts_Next + +ScanParts_Enter:mov al,[DrCnt] ; Partition in Tabelle eintragen + call GetTabAdr ; dazu Adresse neuen Eintrags holen + cld + mov ax,cs ; Ziel im Segment + mov es,ax + mov al,[bp+si+ParTab_FHead] ; Kopf kopieren + stosb + mov ax,[bp+si+ParTab_FSecCyl] ; Zylinder kopieren + xchg ah,al + shr ah,6 + stosw + mov al,[bp+si+ParTab_FSecCyl] ; Sektor kopieren + and al,63 + stosb + mov ax,bx ; linearen Startsektor kopieren + stosw + mov ax,cx + stosw + mov ax,[bp+si+ParTab_NSecs] ; Sektorzahl kopieren + stosw + mov ax,[bp+si+ParTab_NSecs+2] + stosw + mov al,[bp+ScParts_DrHd] ; Laufwerksnummer kopieren + stosb + inc [DrCnt] ; ein log. Laufwerk mehr + +ScanParts_Next: add si,ParTab_Len ; auf n„chste Partition + pop cx + dec cx + ljnz ScanParts_Scan + +ScanParts_End: leave + ret 10 + +;****************************************************************************** +;* Daten eines physikalischen Laufwerks ausgeben * +;* In : AL = Laufwerk * +;****************************************************************************** + + proc PrintPDrive + + push cx ; Register retten + push dx + push di + + cbw ; AH l”schen + push ax ; Laufwerk ausgeben + PrMsg PDriveMsg1 + pop ax + push ax + inc ax + mov cl,1 + call WriteDec + PrMsg PDriveMsg2 + + pop ax ; Adresse Laufwerkstabelle berechnen + call GetPTabAdr + + mov ax,[di+DrPar_Cyls] ; Zylinder ausgeben + mov cl,5 + call WriteDec + PrMsg PDriveMsg3 + + mov al,[di+DrPar_Heads] ; K”pfe ausgeben + mov ah,0 + mov cl,3 + call WriteDec + PrMsg PDriveMsg4 + + mov al,[di+DrPar_NSecs] ; Sektoren ausgeben + mov ah,0 + mov cl,4 + call WriteDec + PrMsg PDriveMsg5 + + mov al,[di+DrPar_Heads] ; Gesamtsektorzahl berechnen + mul byte ptr [di+DrPar_NSecs] + mul word ptr [di+DrPar_Cyls] + call WriteMBytes + PrMsg PDriveMsg6 + + pop di ; Register zurck + pop dx + pop cx + ret + + endp + +;****************************************************************************** +;* Daten eines logischen Laufwerks ausgeben * +;* In : AL = Laufwerk * +;****************************************************************************** + + proc PrintLDrive + + push cx ; Register retten + push dx + push di + + mov dx,ax ; Laufwerk retten + push dx + mov cx,3 ; ausgeben + call WriteSpc + add dl,[DrOfs] + add dl,'A' + mov ah,DOS_WrChar + int INT_DOS + PrChar ':' + + pop ax ; Tabelle holen + call GetTabAdr + + mov al,[di+DrTab_Drive] ; Laufwerk ausgeben... + inc al + cbw + mov cl,9 + call WriteDec + + mov ax,[di+DrTab_StartCyl] ; ...Zylinder... + mov cl,10 + call WriteDec + + mov al,[di+DrTab_StartHead] ; ...Kopf... + cbw + mov cl,7 + call WriteDec + + mov al,[di+DrTab_StartSec] ; ...Sektor... + cbw + mov cl,8 + call WriteDec + + mov cx,2 + call WriteSpc + mov ax,[di+DrTab_SecCnt] ; ...Gr”áe + mov dx,[di+DrTab_SecCnt+2] + call WriteMBytes + + PrMsg PDriveMsg6 ; Meldung wiederverwertet... + + pop di ; Register zurck + pop dx + pop cx + ret + + endp + +;****************************************************************************** +;* Fehlercode eines Laufwerks ausgeben * +;* In : AL = Fehlercode * +;* AH = Laufwerksnummer (0,1...) * +;****************************************************************************** + + proc WrErrorCode + + push bx ; Register retten + push cx + push dx + + add ah,'1' ; LW-Nummer in ASCII umrechnen... + mov [DrvErrorMsg2],ah ; ...und einschreiben + mov ch,al ; Kode sichern + PrMsg DrvErrorMsg + mov cl,7 ; bei Bit 0 anfangen +ErrLoop: rol ch,1 ; fagl. Bit in Carry + jnc NoErrBit + mov bl,cl ; Bit gefunden: Index ausrechnen + mov bh,0 + add bx,bx + mov dx,[bx+Pointers] + mov ah,DOS_WrString + int INT_DOS +NoErrBit: dec cl ; n„chstes Bit + jnz ErrLoop + + pop dx ; Register zurck + pop cx + pop bx + + ret + +DrvErrorMsg: db "Fehler auf Festplatte " +DrvErrorMsg2: db "0:",CR,LF,'$' + +Pointers dw Msg0,Msg1,Msg2,Msg3,Msg4,Msg5,Msg6,Msg7 +Msg0 db " Adreámarke nicht gefunden",CR,LF,'$' +Msg1 db " Spur 0 nicht gefunden",CR,LF,'$' +Msg2 db " Kommandoabbruch",CR,LF,'$' +Msg3 db "$" +Msg4 db " Sektor nicht gefunden",CR,LF,'$' +Msg5 db "$" +Msg6 db " Datenfehler",CR,LF,'$' +Msg7 db " Sektor als defekt markiert",CR,LF,'$' + + endp + +;****************************************************************************** +;* Sektorenzahl als MBytes ausgeben * +;* In: DX:AX = Sektorzahl * +;****************************************************************************** + + proc WriteMBytes + +SecsPerMByte equ (2^20)/SecSize + + push cx ; Register retten + push dx + + add ax,SecsPerMByte/20 ; wg. Rundung + adc dx,0 + + mov cx,SecsPerMByte ; durch 2048 teilen = MByte + div cx + push dx ; Nachkommastellen retten + mov cl,6 + call WriteDec + + PrChar '.' ; Nachkommastelle + pop ax ; holen + cwd + mov cx,SecsPerMByte/10 ; Sektoren pro 100 KByte + div cx + mov cl,1 ; ausgeben + call WriteDec + + pop dx ; Register zurck + pop cx + ret + + endp + +;****************************************************************************** +;* transiente Daten * +;****************************************************************************** + +HelloMsg: db CR,LF,"Sekund„rlaufwerkstreiber V0.4",CR,LF,'$' + +ErrMsgNoDrives: db CR,LF,"Fehler: keine Partitionen gefunden",CR,LF,'$' + +DiagMsg0: db CR,LF,"Controller-Selbsttest: ",'$' +DiagMsg1: db "OK",CR,LF,'$' +DiagMsg2: db "Controller fehlerhaft",CR,LF,'$' +DiagMsg3: db "Sektorpuffer defekt",CR,LF,'$' +DiagMsg4: db "Fehlerkorrektur defekt",CR,LF,'$' +DiagMsg5: db "Steuerprozessor defekt",CR,LF,'$' +DiagMsg6: db "Timeout",CR,LF,'$' +DiagMsgTable dw DiagMsg1,DiagMsg2,DiagMsg3,DiagMsg4,DiagMsg5,DiagMsg6 +UndefDiagMsg db "Unbekannter Fehlercode #$" +WKeyMsg: db "Weiter mit beliebiger Taste...",CR,LF,'$' + +PDriveMsg1: db "Festplatte $" +PDriveMsg2: db " :$" +PDriveMsg3: db " Zylinder,$" +PDriveMsg4: db " K”pfe,$" +PDriveMsg5: db " Sektoren,$" +PDriveMsg6: db " MByte",CR,LF,'$' + +LDriveMsg: db CR,LF,"vorhandene Partitionen:",CR,LF + db "Laufwerk Platte Zylinder Kopf" + db " Sektor Kapazit„t",CR,LF,'$' + +AccPartTypes db 1 ; akzeptierte Partitionstypen: DOS 2.x FAT12 + db 4 ; DOS 3.x FAT16 + db 5 ; DOS 3.3 extended + db 6 ; DOS 3.31 >32 MByte + db 0 ; Tabellenende + +MomDrive db 0 ; momentan gescanntes Laufwerk + + end diff --git a/tests/t_secdrive/t_secdrive.doc b/tests/t_secdrive/t_secdrive.doc new file mode 100644 index 0000000..0aece08 --- /dev/null +++ b/tests/t_secdrive/t_secdrive.doc @@ -0,0 +1,9 @@ ++----------------------- Test Application SECDRIVE --------------------------+ +| | +| YUCK! 8086/MSDOS-Code ;-) | +| This is a MSDOS driver for a secondary MFM/RLL/ESDI/IDE controller I | +| wrote a few years ago - just to get another 40MB of storage (which was | +| a lot at that time...) | +| This app also demonstrates the usage of the newly introduced structures. | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_secdrive/t_secdrive.ori b/tests/t_secdrive/t_secdrive.ori new file mode 100755 index 0000000..0538002 Binary files /dev/null and b/tests/t_secdrive/t_secdrive.ori differ diff --git a/tests/t_secdrive/wd1002xt.inc b/tests/t_secdrive/wd1002xt.inc new file mode 100644 index 0000000..7dd1268 --- /dev/null +++ b/tests/t_secdrive/wd1002xt.inc @@ -0,0 +1,773 @@ +;****************************************************************************** +;* * +;* Includedatei fr SECMAIN.ASM * +;* liefert low-level-Routinen fr SecMain * +;* Version hier fr WD1002XT-kompatible Kontroller: * +;* MFM, RLL (?) * +;* * +;* Historie: 28.12.1994 * +;* 26. 3.1994 Formatierroutinen * +;* 8. 4.1994 defekte Spuren markieren * +;* * +;****************************************************************************** + + section wd1002xt + +;------------------------------------------------------------------------------ +; Portadressen + +Port_Base equ 320h ; prim„re Basisadresse +Port_Data equ Port_Base+0 ; Datenregister (R+W) +Port_Status equ Port_Base+1 ; Statusregister (R) +Port_Reset equ Port_Base+1 ; Reset ausl”sen (W) +Port_Config equ Port_Base+2 ; Jumper auslesen (R) +Port_Select equ Port_Base+2 ; Kontroller selektieren (W) +Port_IRQDRQ equ Port_Base+3 ; IRQ/DRQ-Leitungen freigeben (W) + +;------------------------------------------------------------------------------ +; Kommandocodes + +Cmd_Diagnose equ 0e4h ; Kommando: Kontroller-Selbsttest +Cmd_GetStatus equ 003h ; Status letzter Operation lesen +Cmd_TestReady equ 000h ; Test, ob Laufwerk bereit +Cmd_Restore equ 001h ; Laufwerk rekalibrieren +Cmd_SetParams equ 00ch ; Laufwerksparameter setzen +Cmd_Seek equ 00bh ; Spur anfahren +Cmd_Read equ 008h ; Sektoren lesen +Cmd_Write equ 00ah ; Sektoren schreiben +Cmd_Verify equ 005h ; Sektoren auf Lesbarkeit prfen +Cmd_WriteBuffer equ 00fh ; Sektorpuffer beschreiben +Cmd_FormatDisk equ 004h ; Laufwerk formatieren +Cmd_FormatTrack equ 006h ; Spur formatieren +Cmd_FormatBad equ 007h ; Spur als defekt markieren + +;------------------------------------------------------------------------------ +; I/O-Bremse + +IODelay macro + jmp $+2 + endm + +;------------------------------------------------------------------------------ +; Puffer + +CmdBufSize equ 6 ; enth„lt Kommandoblock fr WD1002 +CmdBuf db CmdBufSize dup (0) + +StatBufSize equ 4 ; enth„lt Statusinfo vom WD1002 +StatBuf db StatBufSize dup (0) + +GeomBufSize equ 8 ; enth„lt Parametertabelle fr Laufwerk +GeomBuf db GeomBufSize dup (0) + +;****************************************************************************** +;* Kommandopuffer initialisieren * +;****************************************************************************** + + proc InitCmdBuf + + push ax ; Register retten + + sub ax,ax ; mit Nullen initialisieren + mov word ptr[CmdBuf],ax + mov word ptr[CmdBuf+2],ax + mov ah,45h ; Retry on, 70us Steprate + mov word ptr[CmdBuf+4],ax + + pop ax ; Register zurck + + ret + + endp + +;****************************************************************************** +;* einen Datenblock an den Kontroller schicken * +;* In : ES:SI = Datenblock * +;* CX = Anzahl Bytes * +;* Out : C=1 bei Protokollfehler * +;****************************************************************************** + + proc SendBlock + + push ax ; Register retten + push cx + push dx + push si + + mov dx,Port_Status + jcxz ZeroLoop ; Nullschleife abfangen + cld ; !!! +OutLoop: in al,dx ; Status lesen + btst al,0 ; warten, bis REQ-Bit auf 1 + jz OutLoop + btst al,1 ; IO-Bit muá 0 sein + stc + jnz ErrEnd + mov dl,Lo(Port_Data); ein Byte auf Datenport ausgeben + seges + outsb + mov dl,Lo(Port_Status) ; zurck fr n„chsten Durchlauf + loop OutLoop +ZeroLoop: clc ; Ende ohne Fehler +ErrEnd: + pop si ; Register zurck + pop dx + pop cx + pop ax + + ret + + endp + +;****************************************************************************** +;* einen Datenblock vom Kontroller lesen * +;* In : ES:DI = Datenblock * +;* CX = Anzahl Bytes * +;* Out : C=1 bei Protokollfehler * +;****************************************************************************** + + proc RecvBlock + + push ax ; Register retten + push cx + push dx + push di + + mov dx,Port_Status + jcxz ZeroLoop ; Nullschleife abfangen + cld ; !!! +InLoop: in al,dx ; Status lesen + btst al,0 ; warten, bis REQ-Bit auf 1 + jz InLoop + btst al,1 ; IO-Bit muá 1 sein + stc + jz ErrEnd + mov dl,Lo(Port_Data); ein Byte von Datenport einlesen + insb + mov dl,Lo(Port_Status) ; zurck fr n„chsten Durchlauf + loop InLoop +ZeroLoop: clc ; Ende ohne Fehler +ErrEnd: + pop di ; Register zurck + pop dx + pop cx + pop ax + + ret + + endp + +;****************************************************************************** +;* Status bilden * +;* Out : C+AX = Status * +;****************************************************************************** + + proc BuildStatus + + push dx ; Register retten + + mov dx,Port_Status ; auf Datum warten +Loop: in al,dx + btst al,0 ; bis REQ=1 + jz Loop + btst al,1 ; und IO=1 + jz Loop + mov dl,Lo(Port_Data); CCB auslesen + in al,dx + mov ah,al ; retten fr Fehlerabfrage + and al,2 ; Bit 1 ausmaskieren + clc + ljz End ; wenn = 0, kein Fehler und AL=0 + + push cx ; zus„tzliche Register retten + push si + push di + push es + + call InitCmdBuf ; ansonsten Kommando absetzen, um + mov [CmdBuf],Cmd_GetStatus ; Status zu lesen + and ah,20h ; Status fr korr. Laufwerk abfragen + mov [CmdBuf+1],ah + mov dx,Port_Status +WaitNBusy: in al,dx + btst al,3 + jnz WaitNBusy + mov ax,ds ; NICHT ExecCmd benutzen, da sonst + mov es,ax ; Rekursion ! + lea si,[CmdBuf] + mov cx,CmdBufSize + mov dl,Lo(Port_Select) + out dx,al + call SendBlock + lea di,[StatBuf] ; 4 Statusbytes auslesen + mov cx,StatBufSize + call RecvBlock + mov dl,Lo(Port_Status); CCB nicht vergessen!! +Loop2: in al,dx + btst al,0 ; bis REQ=1 + jz Loop2 + btst al,1 ; und IO=1 + jz Loop2 + mov dl,Lo(Port_Data) + in al,dx + mov al,[StatBuf] ; Fehlercode = 1.Byte, + and al,7fh ; Bit 0..6 + stc ; Carry signalisiert Fehler + pop es ; zus„tzliche Register zurck + pop di + pop si + pop cx + +End: mov ah,0 ; MSB ohne Bedeutung + pop dx ; Register zurck + ret + + endp + +;****************************************************************************** +;* XT- in AT-Fehlerkode umsetzen * +;* Eingabe: AL = XT-Fehlerkode * +;* Ausgabe: C+AX = AT-Fehlerstatus * +;****************************************************************************** + + proc TranslateStatus + + push bx + push si + + mov bl,al ; alten Status sichern + mov bh,-1 + lea si,[TransTable] + cld +TransLoop: lodsw ; einen Eintrag laden + cmp al,bh ; Tabellenende? + je TransEnd + cmp al,bl ; Treffer? + jne TransLoop ; nein, weitersuchen + mov al,ah ; bersetzten Code laden + cmp al,0 ; Code fr kein Fehler? + clc + je Ende ; ja, C=0 + jmp TransErr ; ansonsten C=1 +TransEnd: mov al,04h ; Aborted Command annehmen +TransErr: stc ; Fehlerflag setzen + +Ende: pop si ; Register zurck + pop bx + + ret + +TransTable: db 00h,00h ; kein Fehler + db 02h,02h ; kein Seek Complete-Signal + db 03h,04h ; Write Fault + db 04h,04h ; Laufwerk nicht bereit + db 06h,02h ; Spur 0 nicht gefunden + db 08h,02h ; Laufwerk positioniert noch + db 11h,40h ; unkorrigierbarer Datenfehler + db 12h,01h ; Adreámarke nicht gefunden + db 15h,10h ; Positionierfehler + db 18h,00h ; korrigierbarer Fehler (ignoriert) + db 19h,80h ; Spur als defekt markiert + db -1,-1 ; Tabellenende + + endp + +;****************************************************************************** +;* ein Kommando ausfhren * +;* In : AL = Kommando * +;****************************************************************************** + + proc ExecCmd + + push cx ; Register retten + push ax + push dx + push si + push es + + mov [CmdBuf],al ; Kommandokode in Datenblock einschreiben + mov dx,Port_Status ; warten, bis Kontroller frei +WaitNBusy: in al,dx + btst al,3 + jnz WaitNBusy + mov dx,Port_Select ; Kontroller selektieren + out dx,al + mov ax,ds ; Adresse Kommandoblock + mov es,ax + lea si,[CmdBuf] + mov cx,CmdBufSize ; L„nge Kommandoblock + call SendBlock ; Kommandoblock abschicken + + pop es ; Register zurck + pop si + pop dx + pop ax + pop cx + + ret + + endp + +;****************************************************************************** +;* Laufwerk und Sonderwerte in Kommandoblock einprogrammieren * +;* In : AL = Laufwerk * +;* AH = Kopf * +;****************************************************************************** + + proc SetDriveEnv + + push ax ; Register retten + + + shl al,5 ; Laufwerksbit an Stelle 5 + or al,ah + mov [CmdBuf+1],al ; als 2. Byte im Kommandopuffer schreiben + + pop ax ; Register zurck + + ret + + endp + +;****************************************************************************** +;* Zylinder- und Sektorparameter an Kontroller ausgeben * +;* In : BX = Startzylinder * +;* CL = Sektorzahl/Interleave * +;* CH = Startsektor * +;****************************************************************************** + + proc SetTransParams + + push ax ; Register retten + + mov [CmdBuf+3],bl ; LSB Startzylinder + mov al,bh ; MSB Startzylinder + shl al,6 ; in Bit 6..7 schieben + add al,ch ; Sektor dazu + dec al ; !!! Sektoren ab 0 + mov [CmdBuf+2],al + mov [CmdBuf+4],cl ; Sektorzahl + + pop ax ; Register zurck + ret + + endp + +;****************************************************************************** +;* Begráungsmeldung ausgeben: * +;****************************************************************************** + + globproc LowLevelIdent + + push ax ; Register retten + + PrMsg IdentMsg + + pop ax + + ret + +IdentMsg db "Low-Level-Routinen fr WD1002S-WX2 und kompatible Controller",CR,LF,'$' + + endp + +;****************************************************************************** +;* Controller-Diagnose: * +;* Out : AL = Diagnosecode * +;****************************************************************************** + + globproc ContDiag + + push cx ; Register retten + push bx + push dx + + sub cx,cx + mov dx,Port_Status ; auf Status +BWait: in al,dx + btst al,3 ; auf NOT BUSY warten + loopnz BWait ; oder bis 64K Durchl„ufe durch + or cx,cx ; Timeout ? + jne NTOut + mov al,Diag_Timeout ; ja: Fehlercode setzen... + jmp End ; ...und Feierabend + +NTOut: call InitCmdBuf ; Kommando Selbsttest ausfhren + mov al,Cmd_Diagnose + call ExecCmd + call BuildStatus ; Status holen + + cmp al,5 ; WD1002 definiert nur Code 0..5 + jb DoTrans + mov al,7 ; "undefinierter Code" + jmp End +DoTrans: lea bx,[TransTbl] ; ansonsten umsetzen + xlat + +End: pop dx ; Register zurck + pop bx + pop cx + ret + +TransTbl: db Diag_NoError ; Code 0: kein Fehler + db Diag_ContError ; Code 1: WD1010 fehlerhaft + db Diag_ECCError ; Code 2: WD11C00 fehlerhaft + db Diag_SBufError ; Code 3: Sektorpuffer defekt + db Diag_ProcError ; Code 4: WD1015 RAM defekt + db Diag_ProcError ; Code 5: WD1015 ROM defekt + + + endp + +;****************************************************************************** +;* Laufwerk rekalibrieren, gleichzeitig Test, ob vorhanden * +;* In : AL = Laufwerk * +;* Out : C + AX = Status * +;****************************************************************************** + + + globproc Recalibrate + + push ax ; Register retten + push cx + + call InitCmdBuf ; testen, ob Laufwerk bereit + mov ah,0 ; Kopf dafr unwichtig + call SetDriveEnv + mov dl,al ; Laufwerksnummer retten, gleichzeitig + mov dh,0 ; Kopf auf 0 setzen + mov al,Cmd_TestReady + call ExecCmd + call BuildStatus + jc TotEnde ; C=1 --> Ende mit Fehler + + call InitCmdBuf ; sanfte Tour: Spur 0 mit Seek anfahren + mov ax,dx + call SetDriveEnv + mov al,0 ; Zylinder lo=0 + mov [CmdBuf+3],al + inc al ; Zylinder Hi=0, Startsektor=1 + mov [CmdBuf+2],al + mov al,Cmd_Seek + call ExecCmd + call BuildStatus + jnc TotEnde ; kein Fehler, alles in Butter + + call InitCmdBuf ; ansonsten echtes Restore versuchen + mov ax,dx + call SetDriveEnv + mov al,Cmd_Restore + call ExecCmd + call BuildStatus + call TranslateStatus + +TotEnde: pop dx ; Register zurck + pop ax + + ret + + endp + +;****************************************************************************** +;* Dem Kontroller die Laufwerksgeometrie mitteilen * +;* In : AL = Laufwerk * +;* Out : C = 1-->Fehler * +;****************************************************************************** + + globproc SetDriveParams + + push cx ; Register retten + push si + push es + + call GetPTabAdr ; Adresse Parametertabelle holen + call InitCmdBuf ; Kommando anstoáen + call SetDriveEnv + mov al,Cmd_SetParams + call ExecCmd + + + mov ax,[di+DrPar_Cyls] ; Parametertabelle aufbauen + xchg ah,al + mov word ptr [GeomBuf],ax + mov al,[di+DrPar_Heads] + mov byte ptr[GeomBuf+2],al + mov ax,[di+DrPar_RedWr] + xchg ah,al + mov word ptr[GeomBuf+3],ax + mov ax,[di+DrPar_PrComp] + xchg ah,al + mov word ptr[GeomBuf+5],ax + mov al,[di+DrPar_ECCLen] + mov byte ptr[GeomBuf+7],al + lea si,[GeomBuf] ; Block abschicken + mov cx,GeomBufSize + mov ax,ds + mov es,ax + call SendBlock + call BuildStatus + call TranslateStatus + + pop es ; Register zurck + pop si + pop cx + + ret + + endp + +;****************************************************************************** +;* Sektor(en) lesen * +;* In : AL = Laufwerk * +;* AH = Startkopf * +;* BX = Startzylinder * +;* CL = Sektorzahl * +;* CH = Startsektor * +;* ES:DI = Zeiger auf Datenpuffer * +;* Out : C+AX = Fehlerstatus * +;****************************************************************************** + + globproc ReadSectors + + push bx ; Register retten + push cx + push dx + push di + push es + + call InitCmdBuf ; Puffer initialisieren + call SetDriveEnv + call SetTransParams + mov al,Cmd_Read ; Lesen triggern + PrChar '1' + call ExecCmd + PrChar '2' + +SecLoop: mov dx,Port_Status ; warten, bis Request-Bit gesetzt +RLoop: in al,dx + btst al,0 + jz RLoop + btst al,2 ; Daten oder Status ? + jnz ErrEnd ; wenn jetzt Status, ist etwas schief gelaufen + push cx ; ansonsten Sektor auslesen + mov cx,SecSize + PrChar '3' + call RecvBlock + PrChar '4' + pop cx + dec cl + add di,SecSize + jnz RLoop ; und n„chsten Sektor verarbeiten + +ErrEnd: PrChar '5' + call BuildStatus + PrChar '6' + call TranslateStatus + + pop es ; Register zurck + pop di + pop dx + pop cx + pop bx + + ret + + endp + +;****************************************************************************** +;* Sektor(en) verifizieren * +;* In : AL = Laufwerk * +;* AH = Startkopf * +;* BX = Startzylinder * +;* CL = Sektorzahl * +;* CH = Startsektor * +;* Out : C+AX = Fehlerstatus * +;****************************************************************************** + + globproc VeriSectors + + push bx ; Register retten + push cx + push dx + + call InitCmdBuf ; Puffer initialisieren + call SetDriveEnv + call SetTransParams + mov al,Cmd_Verify ; Verifikation triggern + call ExecCmd + + call BuildStatus + call TranslateStatus + + pop dx ; Register zurck + pop cx + pop bx + + ret + + endp + +;****************************************************************************** +;* Sektor(en) schreiben * +;* In : AL = Laufwerk * +;* AH = Startkopf * +;* BX = Startzylinder * +;* CL = Sektorzahl * +;* CH = Startsektor * +;* ES:SI = Zeiger auf Datenpuffer * +;* Out : C+AX = Fehlerstatus * +;****************************************************************************** + + globproc WriteSectors + + push bx ; Register retten + push cx + push dx + push si + push es + + + call InitCmdBuf ; Puffer initialisieren + call SetDriveEnv + call SetTransParams + mov al,Cmd_Write ; Lesen triggern + call ExecCmd + +SecLoop: mov dx,Port_Status ; warten, bis Request-Bit gesetzt +WLoop: in al,dx + btst al,0 + jz WLoop + btst al,2 ; Daten oder Status ? + jnz ErrEnd ; wenn jetzt Status, ist etwas schief gelaufen + push cx ; ansonsten Sektor auslesen + mov cx,SecSize + call SendBlock + pop cx + dec cl + add si,SecSize + jnz WLoop ; und n„chsten Sektor verarbeiten + +ErrEnd: call BuildStatus + call TranslateStatus + + pop es ; Register zurck + pop si + pop dx + pop cx + pop bx + + ret + + endp + +;****************************************************************************** +;* Laufwerk formatieren * +;* In : AL = Laufwerk * +;* AH = Interleave * +;* Out : C+AX = Fehlerstatus * +;****************************************************************************** + + globproc FormatUnit + + push bx ; Register retten + push cx + push dx + push si + push di + push es + + mov bx,ax ; Interleave & Laufwerk retten + + mov ax,ds ; vorher noch den Sektorpuffer im + mov es,ax ; Controller ausnullen + lea di,[SectorBuffer] + mov cx,SecSize/2 + sub ax,ax + rep stosw + call InitCmdBuf + mov al,Cmd_WriteBuffer + call ExecCmd + lea si,[SectorBuffer] + mov cx,SecSize + call SendBlock + call BuildStatus + jc End ; unwahrscheinlich, aber... + + call InitCmdBuf ; Puffer initialisieren + mov al,bl ; Laufwerk wieder zurck + mov ah,0 ; Startkopf ist 0 + call SetDriveEnv + mov [CmdBuf+4],bh ; Interleave einschreiben + mov al,Cmd_FormatDisk ; Formatieren triggern + call ExecCmd + +ErrEnd: call BuildStatus +End: call TranslateStatus + + pop es ; Register zurck + pop di + pop si + pop dx + pop cx + pop bx + + ret + + endp + +;****************************************************************************** +;* Spur formatieren * +;* In : AL = Laufwerk * +;* AH = Kopf * +;* BX = Zylinder * +;* CL = Interleave * +;* Out : C+AX = Fehlerstatus * +;****************************************************************************** + + globproc FormatTrack + + push bx + push cx + + call InitCmdBuf ; Parameter einschreiben + call SetDriveEnv + mov ch,1 ; Sektorinformation muá nur gltig sein + call SetTransParams + mov al,Cmd_FormatTrack + call ExecCmd + call BuildStatus + + pop cx + pop bx + ret + + endp + +;****************************************************************************** +;* Spur als defekt markieren * +;* In : AL = Laufwerk * +;* AH = Kopf * +;* BX = Zylinder * +;* Out : C+AX = Fehlerstatus * +;****************************************************************************** + + globproc MarkBad + + push bx + push cx + + call InitCmdBuf ; Parameter einschreiben + call SetDriveEnv + mov cx,0103h ; Sektorinformation muá nur gltig sein + call SetTransParams + mov al,Cmd_FormatBad + call ExecCmd + call BuildStatus + + pop cx + pop bx + ret + + endp + + endsection diff --git a/tests/t_secdrive/wd1003at.inc b/tests/t_secdrive/wd1003at.inc new file mode 100644 index 0000000..7714eec --- /dev/null +++ b/tests/t_secdrive/wd1003at.inc @@ -0,0 +1,952 @@ +;****************************************************************************** +;* * +;* Includedatei fr SECMAIN.ASM * +;* liefert low-level-Routinen fr SecMain * +;* Version hier fr WD1003-kompatible Kontroller: * +;* MFM, RLL, ESDI, AT-Bus * +;* * +;* Historie: 28.12.1994 herberkopiert aus Hauptmodul * +;* 30.12.1994 LowLevelIdent * +;* 19. 1.1995 Workaround fr LCS6220 * +;****************************************************************************** + + section wd1003at + +Base1 equ 170h ; Basisadresse Task-File +Base2 equ 370h ; Basisadresse Floppy-Teil +Task_Data equ Base1+0 ; Datentransferregister (R/W) +Task_Error equ Base1+1 ; genauerer Fehlercode (R) +Task_PreComp equ Base1+1 ; erster Zylinder Pr„komp. (/4, nur W) +Task_SecCnt equ Base1+2 ; Zahl zu transferierender Sektoren (R/W) +Task_SecNum equ Base1+3 ; Startsektor (R/W) +Task_CylLo equ Base1+4 ; Startzylinder Bit 0..7 (R/W) +Task_CylHi equ Base1+5 ; Startzylinder Bit 8..n (R/W) +Task_DrHead equ Base1+6 ; Laufwerk/Startkopf (R/W) +Task_Status equ Base1+7 ; Status Laufwerk & Controller (R) +Task_Command equ Base1+7 ; Kommando Controller (W) +Task_FDiskReg equ Base2+6 ; Bit 3=1: >8 K”pfe + +Cmd_Restore equ 10h ; Kommando: Rekalibrieren +Cmd_Seek equ 70h ; Kommando: Zylinder anfahren +Cmd_Read equ 20h ; Kommando: Sektoren lesen +Cmd_Write equ 30h ; Kommando: Sektoren schreiben +Cmd_Format equ 50h ; Kommando: Spur formatieren +Cmd_Verify equ 40h ; Kommando: Sektoren auf Lesbarkeit prfen +Cmd_Diagnose equ 90h ; Kommando: Selbsttest +Cmd_SetParams equ 91h ; Kommando: Laufwerksparameter setzen + + proc WriteParams + + mov [axsave],ax + mov [cxsave],cx + PrChar ' ' + mov ax,bx + mov cl,5 + call WriteDec + PrChar ' ' + mov al,byte ptr[axsave+1] + mov ah,0 + mov cl,2 + call WriteDec + PrChar ' ' + mov al,byte ptr[cxsave+1] + mov ah,0 + mov cl,2 + call WriteDec + PrChar ' ' + mov al,byte ptr[cxsave] + mov ah,0 + mov cl,2 + call WriteDec + PrChar ' ' + mov ax,es + mov cl,4 + call WriteHex + PrChar ':' + mov ax,bp + mov cl,4 + call WriteHex + mov ax,[axsave] + mov cx,[cxsave] + ret + +cxsave dw ? +axsave dw ? + + endp + +;****************************************************************************** +;* Workaround fr LCS6220: Wird direkt nach dem Einschalten ein Seek ausge- * +;* fhrt, gibt der Kontroller f„lschlicherweise Daten aus und blockiert alle * +;* weiteren Kommandos. Diese Routine r„umt einfach den Puffer leer... * +;****************************************************************************** + + proc ClearBuffer + + push dx ; Register retten + push ax + +RdLoop: mov dx,Task_Status ; Bit 3 noch gesetzt ? + in al,dx + btst al,3 + jz RdLoopEnd ; nein --> fertig + mov dx,Task_Data + in ax,dx + jmp RdLoop +RdLoopEnd: + pop ax ; Register zurck + pop dx + + ret + + endp + +;****************************************************************************** +;* Interleave-Tabelle berechnen * +;* In : AL = Sektorzahl * +;* AH = Interleave * +;* DH = Bad-Flag * +;****************************************************************************** + + proc SetInterleaveBuffer + + pusha ; Register retten + push es + + push ax ; Sektorpuffer initialisieren + mov ax,ds + mov es,ax + sub ax,ax + lea di,[SectorBuffer] + mov cx,SecSize/2 + cld + rep stosw + pop ax + + sub di,di ; DI=Adresse in Puffer=(phys. Sektor-1)*2 + mov dl,dh ; DL = Bad-Flag + mov dh,1 ; DH=log. Sektornummer + mov cl,al ; CX=Schleifenz„hler + mov ch,0 + mov bl,al ; Sektorzahl*2 nach BX + mov bh,0 + add bx,bx + mov si,ax ; Interleave*2 nach SI + shr si,8 + add si,si +InterLoop: cmp byte ptr SectorBuffer[di],0 ; Eintrag frei ? + je Inter_FreeFound ; ja, beenden + add di,2 ; nein, linear weitersuchen + cmp di,bx + jb InterLoop + mov di,0 ; Wrap-Around bercksichtigen + jmp InterLoop +Inter_FreeFound:mov word ptr SectorBuffer[di],dx ; Sektor einschreiben + add di,si ; Interleave-Sprung dazu + cmp di,bx ; Modulo Sektorzahl + jb Inter_NoWrap + sub di,bx +Inter_NoWrap: inc dh ; n„chster log. Sektor + loop InterLoop + + pop es ; Register zurck + popa + + ret + + endp + +;****************************************************************************** +;* Laufwerk und Sonderwerte einprogrammieren * +;* In : AL = Laufwerk * +;* AH = Kopf * +;****************************************************************************** + + proc SetDriveEnv + + push di ; Register retten + push dx + mov dx,ax ; Laufwerk/Kopf retten + + call GetPTabAdr ; Tabellenadresse holen + + mov al,dl ; Laufwerk und Kopf zusammenbauen + shl al,4 + or al,dh + or al,0a0h + mov dx,Task_DrHead + out dx,al + mov ax,[di+DrPar_PrComp] ; Startzylinder Pr„kompensation + shr ax,2 + mov dl,Lo(Task_PreComp) + out dx,al + mov al,[di+DrPar_CByte] ; Wert fr Fixed Disk Register + mov dx,Task_FDiskReg + out dx,al + call WaitBusy + + clc ; Ende ohne Fehler + pop dx + pop di + ret + + endp + +;****************************************************************************** +;* Zylinder- und Sektorparameter an Kontroller ausgeben * +;* In : BX = Startzylinder * +;* CL = Sektorzahl * +;* CH = Startsektor * +;****************************************************************************** + + proc SetTransParams + + push dx ; Register retten + + mov dx,Task_CylLo ; Startzylinder programmieren + mov al,bl + out dx,al + mov dx,Task_CylHi ;*** + mov al,bh + out dx,al + mov dx,Task_SecNum ; Startsektor... ;*** + mov al,ch + out dx,al + mov dx,Task_SecCnt ; ...und Sektorzahl ;*** + mov al,cl + out dx,al + + pop dx ; Register zurck + ret + + endp + +;****************************************************************************** +;* warten, bis Controller bereit oder Fehler * +;* Out : AL = letzter Status * +;****************************************************************************** + + proc WaitBusy + + push dx ; Register retten + mov dx,Task_Status ; auf Statusregister +Loop: in al,dx ; Status lesen + btst al,7 ; Bit 7 noch gesetzt ? + jnz Loop ; ja--> weiter pollen + pop dx ; Register zurck + ret + + endp + +;****************************************************************************** +;* warten, bis Laufwerk bereit * +;* Out : AL = letzter Status * +;****************************************************************************** + + proc WaitDrive + + push dx ; Register retten + mov dx,Task_Status ; auf Statusregister +Loop: in al,dx ; Status lesen + btst al,7 ; Bit 7 = 0 ? ( Controller Busy ) + jnz Loop + btst al,6 ; Bit 6 = 1 ? ( Drive not Ready ) + jz Loop + btst al,4 ; Bit 4 = 1 ? ( Seek not complete ) + jz Loop + pop dx + ret + + endp + +;****************************************************************************** +;* warten, bis Datentransfer erforderlich * +;* Out : AL = letzter Status * +;* C = 1, falls Fehler * +;****************************************************************************** + + proc WaitData + + push dx ; Register retten + mov dx,Task_Status ; auf Statusregister +Loop: in al,dx ; Status lesen + btst al,7 ; Bit 7 = 0 ? + jnz Loop + btst al,3 ; Bit 3 = 1 ? + jz Loop + pop dx ; Register zurck + ret + + endp + +;****************************************************************************** +;* Status bilden * +;* Out : C+AX = Status * +;****************************************************************************** + + proc BuildError + + push dx ; Register retten + + mov dx,Task_Status ; Statusregister lesen + in al,dx + mov ah,al + btst ah,0 ; Fehlerflag gesetzt ? + clc + jz End ; kein Fehler + + mov dx,Task_Error ; ja: Error-Register lesen ;*** + in al,dx + stc + +End: pop dx ; Register zurck + ret + + endp + +;****************************************************************************** +;* Begráungsmeldung ausgeben: * +;****************************************************************************** + + globproc LowLevelIdent + + push ax ; Register retten + + PrMsg IdentMsg + + pop ax + + ret + +IdentMsg db "Low-Level-Routinen fr WD1003-WAH und kompatible Controller",CR,LF,'$' + + endp + +;****************************************************************************** +;* Controller-Diagnose: * +;* Out : AL = Diagnosecode * +;****************************************************************************** + + globproc ContDiag + + push cx ; Register retten + push dx + + mov dx,Task_Status ; das erste Mal mit Timeout warten + sub cx,cx +BWait: in al,dx + btst al,7 ; auf NOT BUSY warten + loopnz BWait ; oder bis 64K Durchl„ufe durch + or cx,cx ; Timeout ? + jne NTOut + mov al,Diag_Timeout ; ja: Fehlercode setzen... + jmp End ; ...und Feierabend + +NTOut: mov al,CMD_Diagnose ; Selbsttest starten + mov dl,Lo(Task_Command) + out dx,al + call WaitBusy ; auf Fertigstellung warten + mov dl,Lo(Task_Error) ; Ergebnis laden + in al,dx + +End: pop dx ; Register zurck + pop cx + ret + + endp + +;****************************************************************************** +;* Dem Kontroller die Laufwerksgeometrie mitteilen * +;* In : AL = Laufwerk * +;* Out : C = 1-->Fehler * +;****************************************************************************** + + globproc SetDriveParams + + push di ; Register retten + push dx + mov dl,al ; Laufwerk retten + + call GetPTabAdr ; Adresse Parametertabelle holen + + call WaitBusy ; Kontroller muá frei sein + + mov al,dl ; Kopfzahl/Laufwerk vorbesetzen + shl al,4 + mov ah,[di+DrPar_Heads] + dec ah ; Maximalnummer anstelle Gesamtzahl + or al,ah + or al,0a0h + mov dx,Task_DrHead + out dx,al + mov dl,Lo(Task_SecCnt) ; Sektorzahl setzen + mov al,[di+DrPar_NSecs] + out dx,al + + mov dl,Lo(Task_Command) ; Parameter bertragen + mov al,Cmd_SetParams + out dx,al + + call WaitBusy ; auf Fertigstellung warten + + clc ; Ende ohne Fehler + pop dx + pop di + ret + + endp + +;****************************************************************************** +;* Laufwerk rekalibrieren, gleichzeitig Test, ob vorhanden * +;* In : AL = Laufwerk * +;* Out : C + AX = Status * +;****************************************************************************** + + globproc Recalibrate + + push cx ; Register retten + push dx + + mov cx,ax ; Laufwerk retten + call WaitBusy ; warten, bis Controller frei + + mov dx,Task_DrHead ; Laufwerk eintragen + mov al,cl + shl al,4 + add al,0a0h + out dx,al + + mov dl,Lo(Task_Status) ; Laufwerk muss jetzt bereit sein, + in al,dx ; da sich einige Kontroller sonst im + and al,50h ; folgenden aufh„ngen, falls + cmp al,50h ; keine Platte angeschlossen ist. + stc ; falls nicht bereit, Fehler simulieren + mov al,4 ; "Aborted Command" + jne TotEnde + mov al,0 + mov dl,Lo(Task_CylLo) ; erstmal auf die sanfte Tour: + out dx,al ; Spur 0 anfahren + mov dl,Lo(Task_CylHi) + out dx,al + mov dl,Lo(Task_Command) + mov al,Cmd_Seek + out dx,al + call WaitBusy + call BuildError + jnc Ende ; wenn OK: fertig + + call ClearBuffer ; falls sich der Longshine verheddert... + mov dl,Lo(Task_Command) ; 2. Anlauf: echtes Restore + mov al,Cmd_Restore + out dx,al + + call WaitBusy ; auf Controller warten + +Ende: call BuildError ; Status einlesen +TotEnde: + pop dx ; Register zurck + pop cx + ret + + endp + +;****************************************************************************** +;* Sektor(en) lesen * +;* In : AL = Laufwerk * +;* AH = Startkopf * +;* BX = Startzylinder * +;* CL = Sektorzahl * +;* CH = Startsektor * +;* ES:DI = Zeiger auf Datenpuffer * +;* Out : C+AX = Fehlerstatus * +;****************************************************************************** + + globproc ReadSectors + + push si ; Register sichern + push dx + push bp + + if debug + PrChar 'R' + mov bp,di + call WriteParams + endif + + sub bp,bp ; Fehlerz„hler auf 0 + +Retry: push ax ; Parameter sichern + push bx + push cx + push di + + mov si,ax ; Laufwerk/Kopf retten + call WaitBusy ; warten, bis Ruhe im Wald + + mov ax,si + call SetDriveEnv ; Laufwerk jetzt schon setzen, damit + ; korr. Ready-Signal abgefragt wird + call WaitDrive ; bis Laufwerk bereit + + call SetTransParams ; restliche Parameter ausgeben + + mov ch,0 ; Sektorzahl nach SI + mov si,cx + mov dx,Task_Command ; Kommando triggern + mov al,Cmd_Read + out dx,al + + mov dx,Task_Data ; Vorbereitung fr INSW + cld +Loop: call WaitBusy ; auf gelesenen Sektor warten + btst al,0 ; Fehler ? + jnz Again ; -->neu aufsetzen + call WaitData + btst al,0 + jnz Again + call WaitDrive + btst al,0 + jnz Again + mov cx,SecSize/2 ; Daten transferieren + rep insw ; bagger, schaufel + dec si ; n„chster Sektor + jnz Loop + +End: pop di ; Parameter nicht mehr gebraucht + pop cx + pop bx + pop ax +Term: if debug + PrChar CR + PrChar LF + endif + call BuildError + pop bp + pop dx + pop si + + ret + +Again: inc bp ; Fehlerz„hler rauf + cmp bp,MaxRetry ; zu oft aufgetreten ? + jae End + + pop di ; nein: Parameter vom Stack + pop cx + pop bx + pop ax + mov si,ax ; Laufwerk retten + call Recalibrate ; auf Spur 0 zurck + jc Term ; bei erneutem Fehler Abbruch + mov ax,si + call SetDriveParams ; Parameter neu initialisieren + mov ax,si + jmp Retry ; neuer Versuch + + + endp + +;****************************************************************************** +;* Sektor(en) verifizieren * +;* In : AL = Laufwerk * +;* AH = Startkopf * +;* BX = Startzylinder * +;* CL = Sektorzahl * +;* CH = Startsektor * +;* Out : C+AX = Fehlerstatus * +;****************************************************************************** + + globproc VeriSectors + + push si ; Register sichern + push dx + push bp + + if debug + PrChar 'V' + mov bp,0 + call WriteParams + endif + + sub bp,bp ; Fehlerz„hler auf 0 + +Retry: push ax ; Parameter sichern + push bx + push cx + + mov si,ax ; Laufwerk/Kopf retten + call WaitBusy ; warten, bis Ruhe im Wald + + mov ax,si + call SetDriveEnv ; Laufwerk jetzt schon setzen, damit + ; korr. Ready-Signal abgefragt wird + call WaitDrive ; bis Laufwerk bereit + + call SetTransParams ; restliche Parameter ausgeben + + mov dx,Task_Command ; Kommando triggern + mov al,Cmd_Verify + out dx,al + + call WaitBusy ; auf Fertigstellung warten + mov cx,16 ; einige Kontroller brauchen +DelStat: loop DelStat ; etwas fr das Fehlerflag + mov dx,Task_Status + in al,dx + btst al,0 ; Fehler ? + jnz Again ; -->neu aufsetzen + call WaitDrive + btst al,0 + jnz Again + +Ende: pop cx ; Parameter nicht mehr gebraucht + pop bx + pop ax +Term: if debug + PrChar CR + PrChar LF + endif + call BuildError + pop bp + pop dx + pop si + + ret + +Again: inc bp ; Fehlerz„hler rauf + cmp bp,MaxRetry ; zu oft aufgetreten ? + jae Ende + + pop cx ; nein: Parameter vom Stack + pop bx + pop ax + mov si,ax ; Laufwerk retten + call Recalibrate ; auf Spur 0 zurck + jc Term ; bei erneutem Fehler Abbruch + mov ax,si + call SetDriveParams ; Parameter neu initialisieren + mov ax,si + jmp Retry ; neuer Versuch + mov ax,si + endp + +;****************************************************************************** +;* Sektor(en) schreiben * +;* In : AL = Laufwerk * +;* AH = Startkopf * +;* BX = Startzylinder * +;* CL = Sektorzahl * +;* CH = Startsektor * +;* ES:SI = Zeiger auf Datenpuffer * +;* Out : C+AX = Fehlerstatus * +;****************************************************************************** + + globproc WriteSectors + + push di ; Register sichern + push dx + push bp + + if debug + PrChar 'W' + mov bp,si + call WriteParams + endif + + xor bp,bp ; Fehlerz„hler auf 0 + +Retry: push ax ; Parameter sichern + push bx + push cx + push si + + mov di,ax ; Laufwerk/Kopf retten + call WaitBusy ; warten, bis Ruhe im Wald + + mov ax,di + call SetDriveEnv ; Laufwerk jetzt schon setzen, damit + ; korr. Ready-Signal abgefragt wird + call WaitDrive ; bis Laufwerk bereit + + call SetTransParams ; restliche Parameter ausgeben + + mov ch,0 ; Sektorzahl nach DI + mov di,cx + mov dx,Task_Command ; Kommando triggern + mov al,Cmd_Write + out dx,al + + mov dx,Task_Data ; Vorbereitung fr OUTSW + cld +Loop: call WaitBusy ; auf Datenbereitschaft warten + btst al,0 ; Fehler ? + jnz Again ; ja-->neu aufsetzen + call WaitData + btst al,0 + jnz Again + call WaitDrive + btst al,0 + jnz Again + mov cx,SecSize/2 ; Daten transferieren + seges + rep outsw ; bagger, schaufel + call WaitBusy ; warten, bis Transfer fertig + btst al,0 + jnz Again + dec di ; n„chster Sektor + jnz Loop + +End: pop si ; Parameter nicht mehr gebraucht + pop cx + pop bx + pop ax +Term: if debug + PrChar CR + PrChar LF + endif + call BuildError + pop bp + pop dx + pop di + + ret + +Again: inc bp ; Fehlerz„hler rauf + cmp bp,MaxRetry ; zu oft aufgetreten ? + jae End + + pop si ; nein: Parameter vom Stack + pop cx + pop bx + pop ax + mov di,ax ; Laufwerk retten + call Recalibrate ; auf Spur 0 zurck + jc Term ; bei erneutem Fehler Abbruch + mov ax,di + call SetDriveParams ; Parameter neu initialisieren + mov ax,di + jmp Retry ; neuer Versuch + + endp + +;****************************************************************************** +;* Laufwerk formatieren * +;* In : AL = Laufwerk * +;* AH = Interleave * +;* Out : C+AX = Fehlerstatus * +;****************************************************************************** + + globproc FormatUnit + + push bx + push cx + push dx + push si + push di + push bp + + mov bx,ax ; Interleave retten + PrMsg ESCMsg + mov ax,bx + call GetPTabAdr ; Parametertabelle->DI + mov ax,bx + mov dh,0 ; gute Spuren schreiben + mov al,[di+DrPar_NSecs] + call SetInterleaveBuffer ; Tabelle berechnen + mov ax,bx + call Recalibrate ; Kontroller reinitialisieren + jc Fin + mov ax,bx + mov bp,[di+DrPar_Cyls] ; Zylinderz„hler in BP (abw„rts) + dec bp + mov dl,al ; Laufwerk in DL + cld +CylLoop: mov dh,0 ; Kopf in dh +HeadLoop: call WaitBusy ; warten, bis WD1003 frei + call WriteCoords ; Bildschirmausgabe + mov ax,dx ; Laufwerk+Kopf progr. + call SetDriveEnv + mov bx,bp ; Zylinder+Sektor progr. + mov cl,[di+DrPar_NSecs] + mov ch,1 + call SetTransParams + mov bx,dx + mov dx,Task_Command + mov al,Cmd_Format + out dx,al + call WaitData ; Sektortabelle schicken + mov cx,SecSize/2 + mov dx,Task_Data + lea si,[SectorBuffer] + rep outsw + call WaitBusy ; warten, bis Kontroller fertig + shr al,1 ; Fehlerbit in Carry laden + jnc GoOn + PrMsg ErrorMsg ; falls Fehler, Meldung ausgeben + mov dx,bx + call WriteCoords + PrChar LF +GoOn: mov dx,bx ; Laufwerk und Kopf zurck + call BreakOnESC ; will der Benutzer abbrechen ? + jc UserTerm ; ja, Abbruch + inc dh ; n„chster Kopf + cmp dh,[di+DrPar_Heads] + jb HeadLoop + dec bp ; n„chster Zylinder + jns CylLoop +TermLoop: mov al,dl ; damit die Seek-Rate wieder stimmt + call Recalibrate + +Fin: push ax ; Fehlerstatus halten + pushf + PrChar LF + popf ; Fehlerstatus zurck + pop ax + pop bp + pop di + pop si + pop dx + pop cx + pop bx + ret + +UserTerm: mov al,dl ; Abbruch durch Benutzer: noch schnell + call Recalibrate ; rekalibrieren + jc Fin ; Fehler dabei ? + stc ; Ansonsten Sonderfehlercode + mov al,DErr_UserTerm + jmp Fin + +WriteCoords: push ax ; Kopf/Zylinder ausgeben + push cx + + PrMsg CylMsg + mov ax,bp + mov cl,6 + call WriteDec + PrMsg HeadMsg + mov al,dh + mov ah,0 + mov cl,3 + call WriteDec + PrChar CR + + pop cx + pop ax + ret + +ESCMsg: db "Abbruch mit ",CR,LF,'$' +CylMsg: db "Zylinder $" +HeadMsg: db ", Kopf $" +ErrorMsg: db "Formatierfehler auf $" + + endp + +;****************************************************************************** +;* Spur formatieren * +;* In : AL = Laufwerk * +;* AH = Kopf * +;* BX = Zylinder * +;* CL = Interleave * +;* Out : C+AX = Fehlerstatus * +;****************************************************************************** + + globproc FormatTrack + + push bx ; Register retten + push cx + push dx + push si + push di + push bp + + mov bp,ax ; Laufwerk & Kopf retten + call Recalibrate ; Laufwerk sicherheitshalber rekalibrieren + mov ax,bp + call GetPTabAdr ; Sektortabelle aufbauen + mov dh,0 ; fehlerhafte Sektoren schreiben + mov ah,cl ; Interleave vorgeben + mov al,[di+DrPar_NSecs] + call SetInterleaveBuffer + mov ax,bp ; Laufwerk und Kopf zurck + call SetDriveEnv ; in Kontroller einprogrammieren + mov cl,[di+DrPar_NSecs] ; Sektor& Zylinder einschreiben + mov ch,1 + call SetTransParams + mov dx,Task_Command ; Kommando schicken + mov al,Cmd_Format + out dx,al + call WaitData ; Sektortabelle schicken + mov cx,SecSize/2 + mov dx,Task_Data + lea si,[SectorBuffer] + rep outsw + call WaitBusy ; warten, bis Kontroller fertig + jc Fin ; Abbruch bei Fehler + mov ax,bp ; Laufwerk nochmal rekalibrieren + call Recalibrate ; damit Steprate stimmt + +Fin: pop bp + pop di + pop si + pop dx + pop cx + pop bx + ret + + endp + +;****************************************************************************** +;* Spur als defekt markieren * +;* In : AL = Laufwerk * +;* AH = Kopf * +;* BX = Zylinder * +;* Out : C+AX = Fehlerstatus * +;****************************************************************************** + + globproc MarkBad + + push bx ; Register retten + push cx + push dx + push si + push di + push bp + + mov bp,ax ; Laufwerk & Kopf retten + call Recalibrate ; Laufwerk sicherheitshalber rekalibrieren + mov ax,bp + call GetPTabAdr ;Sektortabelle aufbauen + mov dh,80h ; fehlerhafte Sektoren schreiben + mov ah,3 ; Interleave ist ziemlich egal... + mov al,[di+DrPar_NSecs] + call SetInterleaveBuffer + mov ax,bp ; Laufwerk und Kopf zurck + call SetDriveEnv ; in Kontroller einprogrammieren + mov cl,[di+DrPar_NSecs] ; Sektor& Zylinder einschreiben + mov ch,1 + call SetTransParams + mov dx,Task_Command ; Kommando schicken + mov al,Cmd_Format + out dx,al + call WaitData ; Sektortabelle schicken + mov cx,SecSize/2 + mov dx,Task_Data + lea si,[SectorBuffer] + rep outsw + call WaitBusy ; warten, bis Kontroller fertig + jc Fin ; Abbruch bei Fehler + mov ax,bp ; Laufwerk nochmal rekalibrieren + call Recalibrate ; damit Steprate stimmt + +Fin: pop bp + pop di + pop si + pop dx + pop cx + pop bx + ret + + endp + + endsection diff --git a/tests/t_st6/asflags b/tests/t_st6/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_st6/t_st6.asm b/tests/t_st6/t_st6.asm new file mode 100755 index 0000000..7cbdc2b --- /dev/null +++ b/tests/t_st6/t_st6.asm @@ -0,0 +1,82 @@ + cpu st6225 + + nop + ret + reti + stop + wait + + jrz pc + jrnz pc+1 + jrc pc+2 + jrnc pc+3 + + ld a,v + ld a,w + ld a,x + ld a,y + ld a,12h + ld a,(x) + ld a,(y) + ld v,a + ld 12h,a + ld (x),a + ld (y),a + + ldi a,12h + ldi v,12h + ldi 12h,12h + + jp 123h + call 123h + + add a,v + add a,12h + add a,(x) + add a,(y) + + and a,v + and a,12h + and a,(x) + and a,(y) + + cp a,v + cp a,12h + cp a,(x) + cp a,(y) + + sub a,v + sub a,12h + sub a,(x) + sub a,(y) + + addi a,12h + andi a,12h + cpi a,12h + subi a,12h + + clr a + clr v + clr 12h + + com a + rlc a + sla a + + inc a + inc v + inc 12h + inc (x) + inc (y) + + dec a + dec v + dec 12h + dec (x) + dec (y) + + set 3,v + res 5,12h + + jrs 3,v,pc + jrr 5,12h,pc+1 diff --git a/tests/t_st6/t_st6.doc b/tests/t_st6/t_st6.doc new file mode 100644 index 0000000..311bc51 --- /dev/null +++ b/tests/t_st6/t_st6.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application ST6 -----------------------------+ +| | +| This is a (synthetic) test of the ST6's instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_st6/t_st6.ori b/tests/t_st6/t_st6.ori new file mode 100755 index 0000000..c7e305a Binary files /dev/null and b/tests/t_st6/t_st6.ori differ diff --git a/tests/t_st7/asflags b/tests/t_st7/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_st7/t_st7.asm b/tests/t_st7/t_st7.asm new file mode 100644 index 0000000..c371c84 --- /dev/null +++ b/tests/t_st7/t_st7.asm @@ -0,0 +1,561 @@ + cpu st7 + page 0 + + halt + iret + nop + rcf + ret + rim + rsp + scf + sim + trap + wfi + + adc a,#$15 + adc a,$12 + adc a,$12.w + adc a,$1234 + adc a,(x) + adc a,($12,x) + adc a,($12.w,x) + adc a,($1234,x) + adc a,(y) + adc a,($12,y) + adc a,($12.w,y) + adc a,($1234,y) + adc a,[$12] + adc a,[$12.w] + adc a,([$12],x) + adc a,([$12.w],x) + adc a,([$12],y) + adc a,([$12.w],y) + + add a,#$15 + add a,$12 + add a,$12.w + add a,$1234 + add a,(x) + add a,($12,x) + add a,($12.w,x) + add a,($1234,x) + add a,(y) + add a,($12,y) + add a,($12.w,y) + add a,($1234,y) + add a,[$12] + add a,[$12.w] + add a,([$12],x) + add a,([$12.w],x) + add a,([$12],y) + add a,([$12.w],y) + + and a,#$15 + and a,$12 + and a,$12.w + and a,$1234 + and a,(x) + and a,($12,x) + and a,($12.w,x) + and a,($1234,x) + and a,(y) + and a,($12,y) + and a,($12.w,y) + and a,($1234,y) + and a,[$12] + and a,[$12.w] + and a,([$12],x) + and a,([$12.w],x) + and a,([$12],y) + and a,([$12.w],y) + + bcp a,#$15 + bcp a,$12 + bcp a,$12.w + bcp a,$1234 + bcp a,(x) + bcp a,($12,x) + bcp a,($12.w,x) + bcp a,($1234,x) + bcp a,(y) + bcp a,($12,y) + bcp a,($12.w,y) + bcp a,($1234,y) + bcp a,[$12] + bcp a,[$12.w] + bcp a,([$12],x) + bcp a,([$12.w],x) + bcp a,([$12],y) + bcp a,([$12.w],y) + + or a,#$15 + or a,$12 + or a,$12.w + or a,$1234 + or a,(x) + or a,($12,x) + or a,($12.w,x) + or a,($1234,x) + or a,(y) + or a,($12,y) + or a,($12.w,y) + or a,($1234,y) + or a,[$12] + or a,[$12.w] + or a,([$12],x) + or a,([$12.w],x) + or a,([$12],y) + or a,([$12.w],y) + + sbc a,#$15 + sbc a,$12 + sbc a,$12.w + sbc a,$1234 + sbc a,(x) + sbc a,($12,x) + sbc a,($12.w,x) + sbc a,($1234,x) + sbc a,(y) + sbc a,($12,y) + sbc a,($12.w,y) + sbc a,($1234,y) + sbc a,[$12] + sbc a,[$12.w] + sbc a,([$12],x) + sbc a,([$12.w],x) + sbc a,([$12],y) + sbc a,([$12.w],y) + + sub a,#$15 + sub a,$12 + sub a,$12.w + sub a,$1234 + sub a,(x) + sub a,($12,x) + sub a,($12.w,x) + sub a,($1234,x) + sub a,(y) + sub a,($12,y) + sub a,($12.w,y) + sub a,($1234,y) + sub a,[$12] + sub a,[$12.w] + sub a,([$12],x) + sub a,([$12.w],x) + sub a,([$12],y) + sub a,([$12.w],y) + + xor a,#$15 + xor a,$12 + xor a,$12.w + xor a,$1234 + xor a,(x) + xor a,($12,x) + xor a,($12.w,x) + xor a,($1234,x) + xor a,(y) + xor a,($12,y) + xor a,($12.w,y) + xor a,($1234,y) + xor a,[$12] + xor a,[$12.w] + xor a,([$12],x) + xor a,([$12.w],x) + xor a,([$12],y) + xor a,([$12.w],y) + + call $12 + call $12.w + call $1234 + call (x) + call ($12,x) + call ($12.w,x) + call ($1234,x) + call (y) + call ($12,y) + call ($12.w,y) + call ($1234,y) + call [$12] + call [$12.w] + call ([$12],x) + call ([$12.w],x) + call ([$12],y) + call ([$12.w],y) + + jp $12 + jp $12.w + jp $1234 + jp (x) + jp ($12,x) + jp ($12.w,x) + jp ($1234,x) + jp (y) + jp ($12,y) + jp ($12.w,y) + jp ($1234,y) + jp [$12] + jp [$12.w] + jp ([$12],x) + jp ([$12.w],x) + jp ([$12],y) + jp ([$12.w],y) + + clr a + clr x + clr y + clr $12 + clr (x) + clr ($12,x) + clr (y) + clr ($12,y) + clr [$12] + clr ([$12],x) + clr ([$12],y) + + cpl a + cpl x + cpl y + cpl $12 + cpl (x) + cpl ($12,x) + cpl (y) + cpl ($12,y) + cpl [$12] + cpl ([$12],x) + cpl ([$12],y) + + dec a + dec x + dec y + dec $12 + dec (x) + dec ($12,x) + dec (y) + dec ($12,y) + dec [$12] + dec ([$12],x) + dec ([$12],y) + + inc a + inc x + inc y + inc $12 + inc (x) + inc ($12,x) + inc (y) + inc ($12,y) + inc [$12] + inc ([$12],x) + inc ([$12],y) + + neg a + neg x + neg y + neg $12 + neg (x) + neg ($12,x) + neg (y) + neg ($12,y) + neg [$12] + neg ([$12],x) + neg ([$12],y) + + rlc a + rlc x + rlc y + rlc $12 + rlc (x) + rlc ($12,x) + rlc (y) + rlc ($12,y) + rlc [$12] + rlc ([$12],x) + rlc ([$12],y) + + rrc a + rrc x + rrc y + rrc $12 + rrc (x) + rrc ($12,x) + rrc (y) + rrc ($12,y) + rrc [$12] + rrc ([$12],x) + rrc ([$12],y) + + sla a + sla x + sla y + sla $12 + sla (x) + sla ($12,x) + sla (y) + sla ($12,y) + sla [$12] + sla ([$12],x) + sla ([$12],y) + + sll a + sll x + sll y + sll $12 + sll (x) + sll ($12,x) + sll (y) + sll ($12,y) + sll [$12] + sll ([$12],x) + sll ([$12],y) + + sra a + sra x + sra y + sra $12 + sra (x) + sra ($12,x) + sra (y) + sra ($12,y) + sra [$12] + sra ([$12],x) + sra ([$12],y) + + srl a + srl x + srl y + srl $12 + srl (x) + srl ($12,x) + srl (y) + srl ($12,y) + srl [$12] + srl ([$12],x) + srl ([$12],y) + + swap a + swap x + swap y + swap $12 + swap (x) + swap ($12,x) + swap (y) + swap ($12,y) + swap [$12] + swap ([$12],x) + swap ([$12],y) + + tnz a + tnz x + tnz y + tnz $12 + tnz (x) + tnz ($12,x) + tnz (y) + tnz ($12,y) + tnz [$12] + tnz ([$12],x) + tnz ([$12],y) + + cp a,#$12 + cp a,$12 + cp a,$12.w + cp a,$1234 + cp a,(x) + cp a,($12,x) + cp a,($12.w,x) + cp a,($1234,x) + cp a,(y) + cp a,($12,y) + cp a,($12.w,y) + cp a,($1234,y) + cp a,[$12] + cp a,[$12.w] + cp a,([$12],x) + cp a,([$12.w],x) + cp a,([$12],y) + cp a,([$12.w],y) + cp x,#$12 + cp x,$12 + cp x,$12.w + cp x,$1234 + cp x,(x) + cp x,($12,x) + cp x,($12.w,x) + cp x,($1234,x) + cp x,[$12] + cp x,[$12.w] + cp x,([$12],x) + cp x,([$12.w],x) + cp y,#$12 + cp y,$12 + cp y,$12.w + cp y,$1234 + cp y,(y) + cp y,($12,y) + cp y,($12.w,y) + cp y,($1234,y) + cp y,[$12] + cp y,[$12.w] + cp y,([$12],y) + cp y,([$12.w],y) + + ld a,#$12 + ld a,$12 + ld a,$12.w + ld a,$1234 + ld a,(x) + ld a,($12,x) + ld a,($12.w,x) + ld a,($1234,x) + ld a,(y) + ld a,($12,y) + ld a,($12.w,y) + ld a,($1234,y) + ld a,[$12] + ld a,[$12.w] + ld a,([$12],x) + ld a,([$12.w],x) + ld a,([$12],y) + ld a,([$12.w],y) + ld a,x + ld a,y + ld a,s + ld x,#$12 + ld x,$12 + ld x,$12.w + ld x,$1234 + ld x,(x) + ld x,($12,x) + ld x,($12.w,x) + ld x,($1234,x) + ld x,[$12] + ld x,[$12.w] + ld x,([$12],x) + ld x,([$12.w],x) + ld x,a + ld x,y + ld x,s + ld y,#$12 + ld y,$12 + ld y,$12.w + ld y,$1234 + ld y,(y) + ld y,($12,y) + ld y,($12.w,y) + ld y,($1234,y) + ld y,[$12] + ld y,[$12.w] + ld y,([$12],y) + ld y,([$12.w],y) + ld y,a + ld y,x + ld y,s + ld s,a + ld s,x + ld s,y + ld $12,a + ld $12.w,a + ld $1234,a + ld (x),a + ld ($12,x),a + ld ($12.w,x),a + ld ($1234,x),a + ld (y),a + ld ($12,y),a + ld ($12.w,y),a + ld ($1234,y),a + ld [$12],a + ld [$12.w],a + ld ([$12],x),a + ld ([$12.w],x),a + ld ([$12],y),a + ld ([$12.w],y),a + ld $12,x + ld $12.w,x + ld $1234,x + ld (x),x + ld ($12,x),x + ld ($12.w,x),x + ld ($1234,x),x + ld [$12],x + ld [$12.w],x + ld ([$12],x),x + ld ([$12.w],x),x + ld $12,y + ld $12.w,y + ld $1234,y + ld (y),y + ld ($12,y),y + ld ($12.w,y),y + ld ($1234,y),y + ld [$12],y + ld [$12.w],y + ld ([$12],y),y + ld ([$12.w],y),y + + bres $12,#5 + bres [$12],#2 + bset $12,#5 + bset [$12],#2 + + btjf $12,#5,pc + btjf [$12],#2,pc + btjt $12,#5,pc + btjt [$12],#2,pc + + callr pc + jra pc + jrc pc + jreq pc + jrf pc + jrh pc + jrih pc + jril pc + jrm pc + jrmi pc + jrnc pc + jrne pc + jrnh pc + jrnm pc + jrpl pc + jrt pc + jruge pc + jrugt pc + jrule pc + jrult pc + + callr [$12] + jra [$12] + jrc [$12] + jreq [$12] + jrf [$12] + jrh [$12] + jrih [$12] + jril [$12] + jrm [$12] + jrmi [$12] + jrnc [$12] + jrne [$12] + jrnh [$12] + jrnm [$12] + jrpl [$12] + jrt [$12] + jruge [$12] + jrugt [$12] + jrule [$12] + jrult [$12] + + mul x,a + mul y,a + + push a + push x + push y + push cc + pop a + pop x + pop y + pop cc + + diff --git a/tests/t_st7/t_st7.doc b/tests/t_st7/t_st7.doc new file mode 100644 index 0000000..d318126 --- /dev/null +++ b/tests/t_st7/t_st7.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application ST7 -----------------------------+ +| | +| This is a (synthetic) test of the ST7's instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_st7/t_st7.ori b/tests/t_st7/t_st7.ori new file mode 100644 index 0000000..8813d35 Binary files /dev/null and b/tests/t_st7/t_st7.ori differ diff --git a/tests/t_st9/asflags b/tests/t_st9/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_st9/t_st9.asm b/tests/t_st9/t_st9.asm new file mode 100644 index 0000000..f2a3714 --- /dev/null +++ b/tests/t_st9/t_st9.asm @@ -0,0 +1,1243 @@ + cpu st9040 + page 0 + + include regst9 + + ccf + di + ei + halt + iret + nop + rcf + ret + scf + sdm + spm + wfi + +;---------------------------------------- + + adc r5,r13 + adc r7,(r12) + adc R100,R130 + adc r7,R22 + adc R70,r11 + adc (r7),R32 + adc (r7),r11 + + adc R32,(r5) + adc R13,(rr4) + adc r13,(rr4) + adc R13,(rr4)+ + adc r13,(rr4)+ + adc R13,-(rr4) + adc r13,-(rr4) + adc r10,rr12(rr6) + adc R11,123(rr8) + adc r11,123(rr8) + adc r3,1234h + adc R11,1234(rr8) + adc r11,1234(rr8) + + adc (rr4),R13 + adc (rr4),r13 + adc (rr4)+,R13 + adc (rr4)+,r13 + adc -(rr4),R13 + adc -(rr4),r13 + adc rr12(rr6),r10 + adc 123(rr8),R11 + adc 123(rr8),r11 + adc 1234h,r3 + adc 1234(rr8),R11 + adc 1234(rr8),r11 + + adc (RR4),(rr8) + adc (rr4),(rr8) + + adc R14,#12h + adc r14,#12h + adc (rr6),#12h + adc 1234h,#12h + + + adcw rr4,rr12 + adcw RR100,RR130 + adcw rr6,RR22 + adcw RR70,rr10 + adcw (r7),RR32 + adcw (r7),rr10 + adcw RR32,(r5) + adcw rr6,(r12) + + adcw rr12,(rr4) + adcw RR12,(rr4) + adcw RR12,(rr4)+ + adcw rr12,(rr4)+ + adcw RR12,-(rr4) + adcw rr12,-(rr4) + adcw rr10,rr12(rr6) + adcw RR10,123(rr8) + adcw rr10,123(rr8) + adcw rr2,1234h + adcw RR10,1234(rr8) + adcw rr10,1234(rr8) + + adcw (rr4),rr12 + adcw (rr4),RR12 + adcw (rr4)+,RR12 + adcw (rr4)+,rr12 + adcw -(rr4),RR12 + adcw -(rr4),rr12 + adcw rr12(rr6),rr10 + adcw 123(rr8),RR10 + adcw 123(rr8),rr10 + adcw 1234h,rr2 + adcw 1234(rr8),RR10 + adcw 1234(rr8),rr10 + + adcw (rr4),(rr8) + + adcw RR14,#1234h + adcw rr14,#1234h + adcw (rr6),#1234h + adcw 123(rr6),#1234h + adcw 1234(rr6),#1234h + adcw 1234h,#1234h + +;--------------------------------------------- + + add r5,r13 + add r7,(r12) + add R100,R130 + add r7,R22 + add R70,r11 + add (r7),R32 + add (r7),r11 + add R32,(r5) + + add R13,(rr4) + add r13,(rr4) + add R13,(rr4)+ + add r13,(rr4)+ + add R13,-(rr4) + add r13,-(rr4) + add r10,rr12(rr6) + add R11,123(rr8) + add r11,123(rr8) + add r3,1234h + add R11,1234(rr8) + add r11,1234(rr8) + + add (rr4),R13 + add (rr4),r13 + add (rr4)+,R13 + add (rr4)+,r13 + add -(rr4),R13 + add -(rr4),r13 + add rr12(rr6),r10 + add 123(rr8),R11 + add 123(rr8),r11 + add 1234h,r3 + add 1234(rr8),R11 + add 1234(rr8),r11 + + add (RR4),(rr8) + add (rr4),(rr8) + + add R14,#12h + add r14,#12h + add (rr6),#12h + add 1234h,#12h + + + addw rr4,rr12 + addw RR100,RR130 + addw rr6,RR22 + addw RR70,rr10 + addw (r7),RR32 + addw (r7),rr10 + addw RR32,(r5) + addw rr6,(r12) + + addw rr12,(rr4) + addw RR12,(rr4) + addw RR12,(rr4)+ + addw rr12,(rr4)+ + addw RR12,-(rr4) + addw rr12,-(rr4) + addw rr10,rr12(rr6) + addw RR10,123(rr8) + addw rr10,123(rr8) + addw rr2,1234h + addw RR10,1234(rr8) + addw rr10,1234(rr8) + + addw (rr4),rr12 + addw (rr4),RR12 + addw (rr4)+,RR12 + addw (rr4)+,rr12 + addw -(rr4),RR12 + addw -(rr4),rr12 + addw rr12(rr6),rr10 + addw 123(rr8),RR10 + addw 123(rr8),rr10 + addw 1234h,rr2 + addw 1234(rr8),RR10 + addw 1234(rr8),rr10 + + addw (rr4),(rr8) + + addw RR14,#1234h + addw rr14,#1234h + addw (rr6),#1234h + addw 123(rr6),#1234h + addw 1234(rr6),#1234h + addw 1234h,#1234h + +;--------------------------------------------- + + and r5,r13 + and r7,(r12) + and R100,R130 + and r7,R22 + and R70,r11 + and (r7),R32 + and (r7),r11 + and R32,(r5) + + and R13,(rr4) + and r13,(rr4) + and R13,(rr4)+ + and r13,(rr4)+ + and R13,-(rr4) + and r13,-(rr4) + and r10,rr12(rr6) + and R11,123(rr8) + and r11,123(rr8) + and r3,1234h + and R11,1234(rr8) + and r11,1234(rr8) + + and (rr4),R13 + and (rr4),r13 + and (rr4)+,R13 + and (rr4)+,r13 + and -(rr4),R13 + and -(rr4),r13 + and rr12(rr6),r10 + and 123(rr8),R11 + and 123(rr8),r11 + and 1234h,r3 + and 1234(rr8),R11 + and 1234(rr8),r11 + + and (RR4),(rr8) + and (rr4),(rr8) + + and R14,#12h + and r14,#12h + and (rr6),#12h + and 1234h,#12h + + + andw rr4,rr12 + andw RR100,RR130 + andw rr6,RR22 + andw RR70,rr10 + andw (r7),RR32 + andw (r7),rr10 + andw RR32,(r5) + andw rr6,(r12) + + andw rr12,(rr4) + andw RR12,(rr4) + andw RR12,(rr4)+ + andw rr12,(rr4)+ + andw RR12,-(rr4) + andw rr12,-(rr4) + andw rr10,rr12(rr6) + andw RR10,123(rr8) + andw rr10,123(rr8) + andw rr2,1234h + andw RR10,1234(rr8) + andw rr10,1234(rr8) + + andw (rr4),rr12 + andw (rr4),RR12 + andw (rr4)+,RR12 + andw (rr4)+,rr12 + andw -(rr4),RR12 + andw -(rr4),rr12 + andw rr12(rr6),rr10 + andw 123(rr8),RR10 + andw 123(rr8),rr10 + andw 1234h,rr2 + andw 1234(rr8),RR10 + andw 1234(rr8),rr10 + + andw (rr4),(rr8) + + andw RR14,#1234h + andw rr14,#1234h + andw (rr6),#1234h + andw 123(rr6),#1234h + andw 1234(rr6),#1234h + andw 1234h,#1234h + +;--------------------------------------------- + + cp r5,r13 + cp r7,(r12) + cp R100,R130 + cp r7,R22 + cp R70,r11 + cp (r7),R32 + cp (r7),r11 + cp R32,(r5) + + cp R13,(rr4) + cp r13,(rr4) + cp R13,(rr4)+ + cp r13,(rr4)+ + cp R13,-(rr4) + cp r13,-(rr4) + cp r10,rr12(rr6) + cp R11,123(rr8) + cp r11,123(rr8) + cp r3,1234h + cp R11,1234(rr8) + cp r11,1234(rr8) + + cp (rr4),R13 + cp (rr4),r13 + cp (rr4)+,R13 + cp (rr4)+,r13 + cp -(rr4),R13 + cp -(rr4),r13 + cp rr12(rr6),r10 + cp 123(rr8),R11 + cp 123(rr8),r11 + cp 1234h,r3 + cp 1234(rr8),R11 + cp 1234(rr8),r11 + + cp (RR4),(rr8) + cp (rr4),(rr8) + + cp R14,#12h + cp r14,#12h + cp (rr6),#12h + cp 1234h,#12h + + + cpw rr4,rr12 + cpw RR100,RR130 + cpw rr6,RR22 + cpw RR70,rr10 + cpw (r7),RR32 + cpw (r7),rr10 + cpw RR32,(r5) + cpw rr6,(r12) + + cpw rr12,(rr4) + cpw RR12,(rr4) + cpw RR12,(rr4)+ + cpw rr12,(rr4)+ + cpw RR12,-(rr4) + cpw rr12,-(rr4) + cpw rr10,rr12(rr6) + cpw RR10,123(rr8) + cpw rr10,123(rr8) + cpw rr2,1234h + cpw RR10,1234(rr8) + cpw rr10,1234(rr8) + + cpw (rr4),rr12 + cpw (rr4),RR12 + cpw (rr4)+,RR12 + cpw (rr4)+,rr12 + cpw -(rr4),RR12 + cpw -(rr4),rr12 + cpw rr12(rr6),rr10 + cpw 123(rr8),RR10 + cpw 123(rr8),rr10 + cpw 1234h,rr2 + cpw 1234(rr8),RR10 + cpw 1234(rr8),rr10 + + cpw (rr4),(rr8) + + cpw RR14,#1234h + cpw rr14,#1234h + cpw (rr6),#1234h + cpw 123(rr6),#1234h + cpw 1234(rr6),#1234h + cpw 1234h,#1234h + +;--------------------------------------------- + + or r5,r13 + or r7,(r12) + or R100,R130 + or r7,R22 + or R70,r11 + or (r7),R32 + or (r7),r11 + or R32,(r5) + + or R13,(rr4) + or r13,(rr4) + or R13,(rr4)+ + or r13,(rr4)+ + or R13,-(rr4) + or r13,-(rr4) + or r10,rr12(rr6) + or R11,123(rr8) + or r11,123(rr8) + or r3,1234h + or R11,1234(rr8) + or r11,1234(rr8) + + or (rr4),R13 + or (rr4),r13 + or (rr4)+,R13 + or (rr4)+,r13 + or -(rr4),R13 + or -(rr4),r13 + or rr12(rr6),r10 + or 123(rr8),R11 + or 123(rr8),r11 + or 1234h,r3 + or 1234(rr8),R11 + or 1234(rr8),r11 + + or (RR4),(rr8) + or (rr4),(rr8) + + or R14,#12h + or r14,#12h + or (rr6),#12h + or 1234h,#12h + + + orw rr4,rr12 + orw RR100,RR130 + orw rr6,RR22 + orw RR70,rr10 + orw (r7),RR32 + orw (r7),rr10 + orw RR32,(r5) + orw rr6,(r12) + + orw rr12,(rr4) + orw RR12,(rr4) + orw RR12,(rr4)+ + orw rr12,(rr4)+ + orw RR12,-(rr4) + orw rr12,-(rr4) + orw rr10,rr12(rr6) + orw RR10,123(rr8) + orw rr10,123(rr8) + orw rr2,1234h + orw RR10,1234(rr8) + orw rr10,1234(rr8) + + orw (rr4),rr12 + orw (rr4),RR12 + orw (rr4)+,RR12 + orw (rr4)+,rr12 + orw -(rr4),RR12 + orw -(rr4),rr12 + orw rr12(rr6),rr10 + orw 123(rr8),RR10 + orw 123(rr8),rr10 + orw 1234h,rr2 + orw 1234(rr8),RR10 + orw 1234(rr8),rr10 + + orw (rr4),(rr8) + + orw RR14,#1234h + orw rr14,#1234h + orw (rr6),#1234h + orw 123(rr6),#1234h + orw 1234(rr6),#1234h + orw 1234h,#1234h + +;--------------------------------------------- + + sbc r5,r13 + sbc r7,(r12) + sbc R100,R130 + sbc r7,R22 + sbc R70,r11 + sbc (r7),R32 + sbc (r7),r11 + sbc R32,(r5) + + sbc R13,(rr4) + sbc r13,(rr4) + sbc R13,(rr4)+ + sbc r13,(rr4)+ + sbc R13,-(rr4) + sbc r13,-(rr4) + sbc r10,rr12(rr6) + sbc R11,123(rr8) + sbc r11,123(rr8) + sbc r3,1234h + sbc R11,1234(rr8) + sbc r11,1234(rr8) + + sbc (rr4),R13 + sbc (rr4),r13 + sbc (rr4)+,R13 + sbc (rr4)+,r13 + sbc -(rr4),R13 + sbc -(rr4),r13 + sbc rr12(rr6),r10 + sbc 123(rr8),R11 + sbc 123(rr8),r11 + sbc 1234h,r3 + sbc 1234(rr8),R11 + sbc 1234(rr8),r11 + + sbc (RR4),(rr8) + sbc (rr4),(rr8) + + sbc R14,#12h + sbc r14,#12h + sbc (rr6),#12h + sbc 1234h,#12h + + + sbcw rr4,rr12 + sbcw RR100,RR130 + sbcw rr6,RR22 + sbcw RR70,rr10 + sbcw (r7),RR32 + sbcw (r7),rr10 + sbcw RR32,(r5) + sbcw rr6,(r12) + + sbcw rr12,(rr4) + sbcw RR12,(rr4) + sbcw RR12,(rr4)+ + sbcw rr12,(rr4)+ + sbcw RR12,-(rr4) + sbcw rr12,-(rr4) + sbcw rr10,rr12(rr6) + sbcw RR10,123(rr8) + sbcw rr10,123(rr8) + sbcw rr2,1234h + sbcw RR10,1234(rr8) + sbcw rr10,1234(rr8) + + sbcw (rr4),rr12 + sbcw (rr4),RR12 + sbcw (rr4)+,RR12 + sbcw (rr4)+,rr12 + sbcw -(rr4),RR12 + sbcw -(rr4),rr12 + sbcw rr12(rr6),rr10 + sbcw 123(rr8),RR10 + sbcw 123(rr8),rr10 + sbcw 1234h,rr2 + sbcw 1234(rr8),RR10 + sbcw 1234(rr8),rr10 + + sbcw (rr4),(rr8) + + sbcw RR14,#1234h + sbcw rr14,#1234h + sbcw (rr6),#1234h + sbcw 123(rr6),#1234h + sbcw 1234(rr6),#1234h + sbcw 1234h,#1234h + +;--------------------------------------------- + + sub r5,r13 + sub r7,(r12) + sub R100,R130 + sub r7,R22 + sub R70,r11 + sub (r7),R32 + sub (r7),r11 + sub R32,(r5) + + sub R13,(rr4) + sub r13,(rr4) + sub R13,(rr4)+ + sub r13,(rr4)+ + sub R13,-(rr4) + sub r13,-(rr4) + sub r10,rr12(rr6) + sub R11,123(rr8) + sub r11,123(rr8) + sub r3,1234h + sub R11,1234(rr8) + sub r11,1234(rr8) + + sub (rr4),R13 + sub (rr4),r13 + sub (rr4)+,R13 + sub (rr4)+,r13 + sub -(rr4),R13 + sub -(rr4),r13 + sub rr12(rr6),r10 + sub 123(rr8),R11 + sub 123(rr8),r11 + sub 1234h,r3 + sub 1234(rr8),R11 + sub 1234(rr8),r11 + + sub (RR4),(rr8) + sub (rr4),(rr8) + + sub R14,#12h + sub r14,#12h + sub (rr6),#12h + sub 1234h,#12h + + + subw rr4,rr12 + subw RR100,RR130 + subw rr6,RR22 + subw RR70,rr10 + subw (r7),RR32 + subw (r7),rr10 + subw RR32,(r5) + subw rr6,(r12) + + subw rr12,(rr4) + subw RR12,(rr4) + subw RR12,(rr4)+ + subw rr12,(rr4)+ + subw RR12,-(rr4) + subw rr12,-(rr4) + subw rr10,rr12(rr6) + subw RR10,123(rr8) + subw rr10,123(rr8) + subw rr2,1234h + subw RR10,1234(rr8) + subw rr10,1234(rr8) + + subw (rr4),rr12 + subw (rr4),RR12 + subw (rr4)+,RR12 + subw (rr4)+,rr12 + subw -(rr4),RR12 + subw -(rr4),rr12 + subw rr12(rr6),rr10 + subw 123(rr8),RR10 + subw 123(rr8),rr10 + subw 1234h,rr2 + subw 1234(rr8),RR10 + subw 1234(rr8),rr10 + + subw (rr4),(rr8) + + subw RR14,#1234h + subw rr14,#1234h + subw (rr6),#1234h + subw 123(rr6),#1234h + subw 1234(rr6),#1234h + subw 1234h,#1234h + +;--------------------------------------------- + + tcm r5,r13 + tcm r7,(r12) + tcm R100,R130 + tcm r7,R22 + tcm R70,r11 + tcm (r7),R32 + tcm (r7),r11 + tcm R32,(r5) + + tcm R13,(rr4) + tcm r13,(rr4) + tcm R13,(rr4)+ + tcm r13,(rr4)+ + tcm R13,-(rr4) + tcm r13,-(rr4) + tcm r10,rr12(rr6) + tcm R11,123(rr8) + tcm r11,123(rr8) + tcm r3,1234h + tcm R11,1234(rr8) + tcm r11,1234(rr8) + + tcm (rr4),R13 + tcm (rr4),r13 + tcm (rr4)+,R13 + tcm (rr4)+,r13 + tcm -(rr4),R13 + tcm -(rr4),r13 + tcm rr12(rr6),r10 + tcm 123(rr8),R11 + tcm 123(rr8),r11 + tcm 1234h,r3 + tcm 1234(rr8),R11 + tcm 1234(rr8),r11 + + tcm (RR4),(rr8) + tcm (rr4),(rr8) + + tcm R14,#12h + tcm r14,#12h + tcm (rr6),#12h + tcm 1234h,#12h + + + tcmw rr4,rr12 + tcmw RR100,RR130 + tcmw rr6,RR22 + tcmw RR70,rr10 + tcmw (r7),RR32 + tcmw (r7),rr10 + tcmw RR32,(r5) + tcmw rr6,(r12) + + tcmw rr12,(rr4) + tcmw RR12,(rr4) + tcmw RR12,(rr4)+ + tcmw rr12,(rr4)+ + tcmw RR12,-(rr4) + tcmw rr12,-(rr4) + tcmw rr10,rr12(rr6) + tcmw RR10,123(rr8) + tcmw rr10,123(rr8) + tcmw rr2,1234h + tcmw RR10,1234(rr8) + tcmw rr10,1234(rr8) + + tcmw (rr4),rr12 + tcmw (rr4),RR12 + tcmw (rr4)+,RR12 + tcmw (rr4)+,rr12 + tcmw -(rr4),RR12 + tcmw -(rr4),rr12 + tcmw rr12(rr6),rr10 + tcmw 123(rr8),RR10 + tcmw 123(rr8),rr10 + tcmw 1234h,rr2 + tcmw 1234(rr8),RR10 + tcmw 1234(rr8),rr10 + + tcmw (rr4),(rr8) + + tcmw RR14,#1234h + tcmw rr14,#1234h + tcmw (rr6),#1234h + tcmw 123(rr6),#1234h + tcmw 1234(rr6),#1234h + tcmw 1234h,#1234h + +;--------------------------------------------- + + tm r5,r13 + tm r7,(r12) + tm R100,R130 + tm r7,R22 + tm R70,r11 + tm (r7),R32 + tm (r7),r11 + tm R32,(r5) + + tm R13,(rr4) + tm r13,(rr4) + tm R13,(rr4)+ + tm r13,(rr4)+ + tm R13,-(rr4) + tm r13,-(rr4) + tm r10,rr12(rr6) + tm R11,123(rr8) + tm r11,123(rr8) + tm r3,1234h + tm R11,1234(rr8) + tm r11,1234(rr8) + + tm (rr4),R13 + tm (rr4),r13 + tm (rr4)+,R13 + tm (rr4)+,r13 + tm -(rr4),R13 + tm -(rr4),r13 + tm rr12(rr6),r10 + tm 123(rr8),R11 + tm 123(rr8),r11 + tm 1234h,r3 + tm 1234(rr8),R11 + tm 1234(rr8),r11 + + tm (RR4),(rr8) + tm (rr4),(rr8) + + tm R14,#12h + tm r14,#12h + tm (rr6),#12h + tm 1234h,#12h + + + tmw rr4,rr12 + tmw RR100,RR130 + tmw rr6,RR22 + tmw RR70,rr10 + tmw (r7),RR32 + tmw (r7),rr10 + tmw RR32,(r5) + tmw rr6,(r12) + + tmw rr12,(rr4) + tmw RR12,(rr4) + tmw RR12,(rr4)+ + tmw rr12,(rr4)+ + tmw RR12,-(rr4) + tmw rr12,-(rr4) + tmw rr10,rr12(rr6) + tmw RR10,123(rr8) + tmw rr10,123(rr8) + tmw rr2,1234h + tmw RR10,1234(rr8) + tmw rr10,1234(rr8) + + tmw (rr4),rr12 + tmw (rr4),RR12 + tmw (rr4)+,RR12 + tmw (rr4)+,rr12 + tmw -(rr4),RR12 + tmw -(rr4),rr12 + tmw rr12(rr6),rr10 + tmw 123(rr8),RR10 + tmw 123(rr8),rr10 + tmw 1234h,rr2 + tmw 1234(rr8),RR10 + tmw 1234(rr8),rr10 + + tmw (rr4),(rr8) + + tmw RR14,#1234h + tmw rr14,#1234h + tmw (rr6),#1234h + tmw 123(rr6),#1234h + tmw 1234(rr6),#1234h + tmw 1234h,#1234h + +;--------------------------------------------- + + xor r5,r13 + xor r7,(r12) + xor R100,R130 + xor r7,R22 + xor R70,r11 + xor (r7),R32 + xor (r7),r11 + xor R32,(r5) + + xor R13,(rr4) + xor r13,(rr4) + xor R13,(rr4)+ + xor r13,(rr4)+ + xor R13,-(rr4) + xor r13,-(rr4) + xor r10,rr12(rr6) + xor R11,123(rr8) + xor r11,123(rr8) + xor r3,1234h + xor R11,1234(rr8) + xor r11,1234(rr8) + + xor (rr4),R13 + xor (rr4),r13 + xor (rr4)+,R13 + xor (rr4)+,r13 + xor -(rr4),R13 + xor -(rr4),r13 + xor rr12(rr6),r10 + xor 123(rr8),R11 + xor 123(rr8),r11 + xor 1234h,r3 + xor 1234(rr8),R11 + xor 1234(rr8),r11 + + xor (RR4),(rr8) + xor (rr4),(rr8) + + xor R14,#12h + xor r14,#12h + xor (rr6),#12h + xor 1234h,#12h + + + xorw rr4,rr12 + xorw RR100,RR130 + xorw rr6,RR22 + xorw RR70,rr10 + xorw (r7),RR32 + xorw (r7),rr10 + xorw RR32,(r5) + xorw rr6,(r12) + + xorw rr12,(rr4) + xorw RR12,(rr4) + xorw RR12,(rr4)+ + xorw rr12,(rr4)+ + xorw RR12,-(rr4) + xorw rr12,-(rr4) + xorw rr10,rr12(rr6) + xorw RR10,123(rr8) + xorw rr10,123(rr8) + xorw rr2,1234h + xorw RR10,1234(rr8) + xorw rr10,1234(rr8) + + xorw (rr4),rr12 + xorw (rr4),RR12 + xorw (rr4)+,RR12 + xorw (rr4)+,rr12 + xorw -(rr4),RR12 + xorw -(rr4),rr12 + xorw rr12(rr6),rr10 + xorw 123(rr8),RR10 + xorw 123(rr8),rr10 + xorw 1234h,rr2 + xorw 1234(rr8),RR10 + xorw 1234(rr8),rr10 + + xorw (rr4),(rr8) + + xorw RR14,#1234h + xorw rr14,#1234h + xorw (rr6),#1234h + xorw 123(rr6),#1234h + xorw 1234(rr6),#1234h + xorw 1234h,#1234h + +;--------------------------------------------- + + ld r13,R230 + ld r4,r12 + ld R123,r5 + ld (r6),r12 + ld r12,(r6) + ld (r9),R56 + ld (r10),r11 + ld R100,(r7) + ld 72(r5),r8 + ld r8,72(r5) + ld R120,R130 + + ld r10,(rr12) + ld (r4)+,(rr6)+ + ld R240,(rr2)+ + ld r10,(rr2)+ + ld R4,-(rr6) + ld r4,-(rr6) + ld R230,(rr8) + ld r2,rr6(rr4) + ld R14,123(rr6) + ld r14,123(rr6) + ld r12,1234h + ld R12,1234(rr8) + ld r12,1234(rr8) + + ld (rr4)+,(r6)+ + ld (rr12),(r10) + ld (rr2)+,R240 + ld (rr2)+,r10 + ld -(rr6),R4 + ld -(rr6),r4 + ld (rr8),R230 + ld rr6(rr4),r2 + ld 123(rr6),R14 + ld 123(rr6),r14 + ld 1234h,r12 + ld 1234(rr8),R12 + ld 1234(rr8),r12 + + ld (RR4),(rr6) + ld (rr4),(rr6) + + ld r8,#242 + ld R8,#123 + ld (rr6),#23h + ld 1234h,#56h + + + ldw rr10,rr14 + ldw (r7),RR128 + ldw (r9),rr4 + ldw RR40,(r5) + ldw rr6,(r5) + ldw 123(r7),rr8 + ldw rr10,123(r5) + ldw RR40,RR120 + ldw rr12,RR136 + ldw RR136,rr12 + + ldw rr8,(rr6) + ldw RR20,(rr10)+ + ldw rr12,(rr10)+ + ldw RR124,-(rr2) + ldw rr4,-(rr2) + ldw RR8,(rr6) + ldw rr10,rr2(rr6) + ldw RR20,123(rr8) + ldw rr8,123(rr8) + ldw rr4,1234h + ldw RR20,1234(rr8) + ldw rr8,1234(rr8) + + ldw (rr6),rr8 + ldw (rr10)+,RR20 + ldw (rr10)+,rr12 + ldw -(rr2),RR124 + ldw -(rr2),rr4 + ldw (rr6),RR8 + ldw rr2(rr6),rr10 + ldw 123(rr8),RR20 + ldw 123(rr8),rr8 + ldw 1234h,rr4 + ldw 1234(rr8),RR20 + ldw 1234(rr8),rr8 + + ldw (rr6),(rr10) + + ldw rr8,#2345h + ldw RR100,#4268 + ldw (rr6),#1234h + ldw 123(rr6),#1234h + ldw 1234(rr6),#1234h + ldw 1234h,#1234h + +;----------------------------------- + + clr R32 + clr r2 + clr (R32) + clr (r2) + + cpl R32 + cpl r2 + cpl (R32) + cpl (r2) + + da R32 + da r2 + da (R32) + da (r2) + + dec R32 + dec r2 + dec (R32) + dec (r2) + + inc R32 + inc r2 + inc (R32) + inc (r2) + + pop R32 + pop r2 + pop (R32) + pop (r2) + + popu R32 + popu r2 + popu (R32) + popu (r2) + + rlc R32 + rlc r2 + rlc (R32) + rlc (r2) + + rol R32 + rol r2 + rol (R32) + rol (r2) + + ror R32 + ror r2 + ror (R32) + ror (r2) + + rrc R32 + rrc r2 + rrc (R32) + rrc (r2) + + sra R32 + sra r2 + sra (R32) + sra (r2) + + swap R32 + swap r2 + swap (R32) + swap (r2) + + decw RR32 + decw rr2 + + ext RR10 + ext rr10 + + incw RR32 + incw rr2 + + popuw RR32 + popuw rr2 + + popw RR32 + popw rr2 + + rlcw RR32 + rlcw rr2 + + rrcw RR32 + rrcw rr2 + + sraw RR32 + sraw rr2 + +;------------------------------ + + band r4.5,r8.2 + band r4.5,r8.!2 + + bld r4.5,r8.!2 + bld r4.5,r8.2 + + bor r4.5,r8.2 + bor r4.5,r8.!2 + + bxor r4.5,r8.2 + bxor r4.5,r8.!2 + +;------------------------------ + + bcpl r4.5 + + bres r4.5 + + bset r4.5 + + btset r4.5 + btset (rr4).5 + + btjf r10.2,pc + btjt r10.2,pc + +;------------------------------ + + call (RR30) + call (rr6) + call 3521h + + jp (RR30) + jp (rr6) + jp 1024 + + jpeq 1024 + + jreq pc + +;------------------------------ + + cpjfi r2,(rr14),pc + cpjti r2,(rr14),pc + + djnz r6,pc + dwjnz RR6,pc + dwjnz rr6,pc + +;------------------------------ + + div rr8,r6 + mul rr6,r8 + divws rr6,rr8,RR10 + +;------------------------------ + + ldpp (rr8)+,(rr12)+ + lddp (rr8)+,(rr12)+ + ldpd (rr8)+,(rr12)+ + lddd (rr8)+,(rr12)+ + +;------------------------------ + + pea 16(RR32) + pea 16(rr2) + pea 1600(RR32) + pea 1600(rr2) + + peau 16(RR32) + peau 16(rr2) + peau 1600(RR32) + peau 1600(rr2) + +;------------------------------ + + push R32 + push r2 + push (R32) + push (r2) + push #23h + + pushu R32 + pushu r2 + pushu (R32) + pushu (r2) + pushu #23h + + pushuw RR32 + pushuw rr2 + pushuw #1234h + + pushw RR32 + pushw rr2 + pushw #1234h + +;------------------------------ + + sla r6 + sla R6 + sla (rr6) + + slaw rr4 + slaw RR4 + slaw (rr4) + +;------------------------------ + + spp #5 + srp #3 + srp0 #3 + srp1 #3 + +;------------------------------ + + xch r2,r4 + +dvar equ 1234h,data +cvar label 2345h + + assume dp:0 +; ld r0,dvar + ld r0,cvar + assume dp:1 + ld r0,dvar +; ld r0,cvar + +bit1 bit r5.1 +bit2 bit r6.!7 +bit3 bit bit1 +bit4 bit bit1+1 + + bld r0.0,bit3 + bld r0.1,!bit3 + diff --git a/tests/t_st9/t_st9.doc b/tests/t_st9/t_st9.doc new file mode 100644 index 0000000..8068250 --- /dev/null +++ b/tests/t_st9/t_st9.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application ST9 -----------------------------+ +| | +| This is a (synthetic) test of the ST9's instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_st9/t_st9.ori b/tests/t_st9/t_st9.ori new file mode 100755 index 0000000..b2bc395 Binary files /dev/null and b/tests/t_st9/t_st9.ori differ diff --git a/tests/t_tms7/asflags b/tests/t_tms7/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_tms7/t_tms7.asm b/tests/t_tms7/t_tms7.asm new file mode 100755 index 0000000..efd4e0a --- /dev/null +++ b/tests/t_tms7/t_tms7.asm @@ -0,0 +1,364 @@ + cpu tms70c08 + + page 0 + + include reg7000 + +; additional syntax options marked with *** + + adc b,a + adc r10,a + adc r20,b + adc r30,r40 + adc %20,a + adc #20,a ; *** + adc %30,b + adc #30,b ; *** + adc %40,r50 + adc #40,r50 ; *** + + add b,a + add r10,a + add r20,b + add r30,r40 + add %20,a + add #20,a ; *** + add %30,b + add #30,b ; *** + add %40,r50 + add #40,r50 ; *** + + and b,a + and r10,a + and r20,b + and r30,r40 + and %20,a + and #20,a ; *** + and %30,b + and #30,b ; *** + and %40,r50 + and #40,r50 ; *** + andp a,p20 + and a,p20 ; *** + andp b,p30 + and b,p30 ; *** + andp #50,p40 + and #50,p40 ; *** + + btjo b,a,$ + btjo r10,a,$ + btjo r20,b,$ + btjo r30,r40,$ + btjo %20,a,$ + btjo #20,a,$ ; *** + btjo %30,b,$ + btjo #30,b,$ ; *** + btjo %40,r50,$ + btjo #40,r50,$ ; *** + btjop a,p20,$ + btjo a,p20,$ ; *** + btjop b,p30,$ + btjo b,p30,$ ; *** + btjop #50,p40,$ + btjo #50,p40,$ ; *** + + btjz b,a,$ + btjz r10,a,$ + btjz r20,b,$ + btjz r30,r40,$ + btjz %20,a,$ + btjz #20,a,$ ; *** + btjz %30,b,$ + btjz #30,b,$ ; *** + btjz %40,r50,$ + btjz #40,r50,$ ; *** + btjzp a,p20,$ + btjz a,p20,$ ; *** + btjzp b,p30,$ + btjz b,p30,$ ; *** + btjzp #50,p40,$ + btjz #50,p40,$ ; *** + + br @1234h + br 1234h ; *** + br @1234h(b) + br 1234h(b) ; *** + br *r30 + + call @1234h + call 1234h ; *** + call @1234h(b) + call 1234h(b) ; *** + call *r30 + + clr a + clr b + clr r10 + + clrc + + cmp b,a + cmp r10,a + cmp r20,b + cmp r30,r40 + cmp %20,a + cmp #20,a ; *** + cmp %30,b + cmp #30,b ; *** + cmp %40,r50 + cmp #40,r50 ; *** + cmpa @1234h + cmpa 1234h ; *** + cmp @1234h,a ; *** + cmp 1234h,a ; *** + cmpa @1234h(b) + cmpa 1234h(b) ; *** + cmp @1234h(b),a ; *** + cmp 1234h(b),a ; *** + cmpa *r60 + cmp *r60,a ; *** + + dac b,a + dac r10,a + dac r20,b + dac r30,r40 + dac %20,a + dac #20,a ; *** + dac %30,b + dac #30,b ; *** + dac %40,r50 + dac #40,r50 ; *** + + dec a + dec b + dec r10 + + decd a + decd b + decd r10 + + dint + + djnz a,$ + djnz b,$ + djnz r10,$ + + dsb b,a + dsb r10,a + dsb r20,b + dsb r30,r40 + dsb %20,a + dsb #20,a ; *** + dsb %30,b + dsb #30,b ; *** + dsb %40,r50 + dsb #40,r50 ; *** + + eint + + idle + + inc a + inc b + inc r10 + + inv a + inv b + inv r10 + + jmp $ + jc $ + jeq $ + jhs $ + jl $ + jn $ + jnc $ + jne $ + jnz $ + jp $ + jpz $ + jz $ + + lda @1234h + lda 1234h ; *** + mov @1234h,a ; *** + mov 1234h,a ; *** + lda @1234h(b) + lda 1234h(b) ; *** + mov @1234h(b),a ; *** + mov 1234h(b),a ; *** + lda *r10 + mov *r10,a ; *** + + ldsp + + mov a,b + mov a,r10 + mov b,a + mov b,r20 + mov r30,a + mov r40,b + mov r50,r60 + mov %10,a + mov #10,a ; *** + mov %20,b + mov #20,b ; *** + mov %30,r70 + mov #30,r70 ; *** + + movd %1234h,r10 + movd #1234h,r10 ; *** + movd %1234h(b),r20 + movd #1234h(b),r20 ; *** + movd r30,r40 + + movw %1234h,r10 ; *** + movw #1234h,r10 ; *** + movw %1234h(b),r20 ; *** + movw #1234h(b),r20 ; *** + movw r30,r40 ; *** + + movp a,p10 + mov a,p10 ; *** + movp b,p20 + mov b,p20 ; *** + movp %10,p30 + movp #10,p30 ; *** + mov %10,p30 ; *** + mov #10,p30 ; *** + movp p40,a + mov p40,a ; *** + movp p50,b + mov p50,b ; *** + + mpy b,a + mpy r10,a + mpy r20,b + mpy r30,r40 + mpy %20,a + mpy #20,a ; *** + mpy %30,b + mpy #30,b ; *** + mpy %40,r50 + mpy #40,r50 ; *** + + nop + + or b,a + or r10,a + or r20,b + or r30,r40 + or %20,a + or #20,a ; *** + or %30,b + or #30,b ; *** + or %40,r50 + or #40,r50 ; *** + orp a,p20 + or a,p20 ; *** + orp b,p30 + or b,p30 ; *** + orp #50,p40 + or #50,p40 ; *** + + pop a + pop b + pop r10 + pop st + + push a + push b + push r10 + push st + + reti + rti ; *** + + rets + rts ; *** + + rl a + rl b + rl r10 + + rlc a + rlc b + rlc r10 + + rr a + rr b + rr r10 + + rrc a + rrc b + rrc r10 + + sbb b,a + sbb r10,a + sbb r20,b + sbb r30,r40 + sbb %20,a + sbb #20,a ; *** + sbb %30,b + sbb #30,b ; *** + sbb %40,r50 + sbb #40,r50 ; *** + + setc + + sta @1234h + sta 1234h ; *** + mov a,@1234h ; *** + mov a,1234h ; *** + sta @1234h(b) + sta 1234h(b) ; *** + mov a,@1234h(b) ; *** + mov a,1234h(b) ; *** + sta *r10 + mov a,*r10 ; *** + + stsp + + sub b,a + sub r10,a + sub r20,b + sub r30,r40 + sub %20,a + sub #20,a ; *** + sub %30,b + sub #30,b ; *** + sub %40,r50 + sub #40,r50 ; *** + + swap a + swap b + swap r10 + + trap 0 + trap 23 + + tsta + tst a ; *** + tstb + tst b ; *** + + xchb a + xchb b ; *** + xchb r10 + + xor b,a + xor r10,a + xor r20,b + xor r30,r40 + xor %20,a + xor #20,a ; *** + xor %30,b + xor #30,b ; *** + xor %40,r50 + xor #40,r50 ; *** + xorp a,p20 + xor a,p20 ; *** + xorp b,p30 + xor b,p30 ; *** + xorp #50,p40 + xor #50,p40 ; *** diff --git a/tests/t_tms7/t_tms7.doc b/tests/t_tms7/t_tms7.doc new file mode 100644 index 0000000..8729cc7 --- /dev/null +++ b/tests/t_tms7/t_tms7.doc @@ -0,0 +1,5 @@ ++-------------------------- Test Application TMS7 ---------------------------+ +| | +| This is a (synthetic) test of the TMS7000 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_tms7/t_tms7.ori b/tests/t_tms7/t_tms7.ori new file mode 100755 index 0000000..c8d60c7 Binary files /dev/null and b/tests/t_tms7/t_tms7.ori differ diff --git a/tests/t_xa/asflags b/tests/t_xa/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_xa/t_xa.asm b/tests/t_xa/t_xa.asm new file mode 100644 index 0000000..68800d2 --- /dev/null +++ b/tests/t_xa/t_xa.asm @@ -0,0 +1,603 @@ + cpu xag3 + + page 0 + + include stddefxa + + segment io + +port1 ds.b 1 +port2 ds.b 1 + + segment code + + supmode on + +regbit1 bit r3l.4 +regbit2 bit sp.5 +regbit3 bit r5h.5 +regbit4 bit sp.14 +membit1 bit 22h.5 +membit2 bit 50023h.5 +iobit1 bit port1.2 +regbit5 bit regbit4+1 + + add.b r4h,r1l + add.w r5,r3 + add.b r5l,[r6] + add.w r4,[sp] + add.b [r6],r5l + add.w [sp],r4 + add.b r3h,[r6+2] + add.w r4,[r3+100] + add.b [r6+2],r3h + add.w [r3+100],r4 + add.b r3h,[r6+200] + add.w r4,[r3+1000] + add.b [r6+200],r3h + add.w [r3+1000],r4 + add.b r4h,[r1+] + add.w r5,[r6+] + add.b [r1+],r4h + add.w [r6+],r5 + add.b 200h,r2l + add.w 123h,r6 + add.b r2l,200h + add.w r6,123h + add.b r5h,#34h + add.w r3,#1234h + add.b [r5],#34h + add.w [r3],#1234h + add.b [r5+],#34h + add.w [r3+],#1234h + add.b [r5+2],#34h + add.w [r3+100],#1234h + add.b [r5+200],#34h + add.w [r3+1000],#1234h + add.b 200h,#34h + add.w 123h,#1234h + + addc.b r4h,r1l + addc.w r5,r3 + addc.b r5l,[r6] + addc.w r4,[sp] + addc.b [r6],r5l + addc.w [sp],r4 + addc.b r3h,[r6+2] + addc.w r4,[r3+100] + addc.b [r6+2],r3h + addc.w [r3+100],r4 + addc.b r3h,[r6+200] + addc.w r4,[r3+1000] + addc.b [r6+200],r3h + addc.w [r3+1000],r4 + addc.b r4h,[r1+] + addc.w r5,[r6+] + addc.b [r1+],r4h + addc.w [r6+],r5 + addc.b 200h,r2l + addc.w 123h,r6 + addc.b r2l,200h + addc.w r6,123h + addc.b r5h,#34h + addc.w r3,#1234h + addc.b [r5],#34h + addc.w [r3],#1234h + addc.b [r5+],#34h + addc.w [r3+],#1234h + addc.b [r5+2],#34h + addc.w [r3+100],#1234h + addc.b [r5+200],#34h + addc.w [r3+1000],#1234h + addc.b 200h,#34h + addc.w 123h,#1234h + + adds.b r5h,#3 + adds.w r6,#5 + adds.b [r4],#3 + adds.w [sp],#5 + adds.b [r4+],#3 + adds.w [sp+],#5 + adds.b [r4+20],#3 + adds.w [sp+20],#5 + adds.b [r4-200],#3 + adds.w [sp-200],#5 + adds.b 200h,#3 + adds.w 123h,#5 + + and.b r4h,r1l + and.w r5,r3 + and.b r5l,[r6] + and.w r4,[sp] + and.b [r6],r5l + and.w [sp],r4 + and.b r3h,[r6+2] + and.w r4,[r3+100] + and.b [r6+2],r3h + and.w [r3+100],r4 + and.b r3h,[r6+200] + and.w r4,[r3+1000] + and.b [r6+200],r3h + and.w [r3+1000],r4 + and.b r4h,[r1+] + and.w r5,[r6+] + and.b [r1+],r4h + and.w [r6+],r5 + and.b 200h,r2l + and.w 123h,r6 + and.b r2l,200h + and.w r6,123h + and.b r5h,#34h + and.w r3,#1234h + and.b [r5],#34h + and.w [r3],#1234h + and.b [r5+],#34h + and.w [r3+],#1234h + and.b [r5+2],#34h + and.w [r3+100],#1234h + and.b [r5+200],#34h + and.w [r3+1000],#1234h + and.b 200h,#34h + and.w 123h,#1234h + + anl c,regbit1 + anl c,/iobit1 + anl c,r5.12 + anl c,/r4h.1 + + asl.b r4h,r1l + asl.w r6,r3h + asl.d r2,r4l + asl.b r4h,#6 + asl.w r6,#12 + asl.d r2,#24 + + asr.b r4h,r1l + asr.w r6,r3h + asr.d r2,r4l + asr.b r4h,#6 + asr.w r6,#12 + asr.d r2,#24 + + bcc label1 + nop + bcc label2 + nop + bcs label1 + beq label1 + bg label1 + bge label1 + bgt label1 + ble label1 + blt label1 + bmi label1 + bne label1 + bnv label1 + bov label1 + bpl label1 + br label1 + + call label1 + call label1 + call [r4] + + cjne r5l,123h,label1 + cjne r6,456h,label1 + cjne r5l,#34h,label1 + cjne r6,#1234h,label1 + cjne.b [r6],#34h,label1 + cjne.w [r6],#1234h,label1 + +label1: nop +label2: nop + + clr regbit1 + + cmp.b r4h,r1l + cmp.w r5,r3 + cmp.b r5l,[r6] + cmp.w r4,[sp] + cmp.b [r6],r5l + cmp.w [sp],r4 + cmp.b r3h,[r6+2] + cmp.w r4,[r3+100] + cmp.b [r6+2],r3h + cmp.w [r3+100],r4 + cmp.b r3h,[r6+200] + cmp.w r4,[r3+1000] + cmp.b [r6+200],r3h + cmp.w [r3+1000],r4 + cmp.b r4h,[r1+] + cmp.w r5,[r6+] + cmp.b [r1+],r4h + cmp.w [r6+],r5 + cmp.b 200h,r2l + cmp.w 123h,r6 + cmp.b r2l,200h + cmp.w r6,123h + cmp.b r5h,#34h + cmp.w r3,#1234h + cmp.b [r5],#34h + cmp.w [r3],#1234h + cmp.b [r5+],#34h + cmp.w [r3+],#1234h + cmp.b [r5+2],#34h + cmp.w [r3+100],#1234h + cmp.b [r5+200],#34h + cmp.w [r3+1000],#1234h + cmp.b 200h,#34h + cmp.w 123h,#1234h + + cpl r4l + cpl sp + + da r4l + + div.w r4,r1h + div.w r5,#23 + div.d r2,r5 + div.d r6,#1234h + + divu.b r4l,r5l + divu.b r4l,#23 + divu.w r4,r1h + divu.w r5,#23 + divu.d r2,r5 + divu.d r6,#1234h + +d1: djnz r5l,d1 +d2: djnz.b 123h,d2 +d3: djnz r5,d3 +d4: djnz.w 123h,d4 + + fcall 123456h + + fjmp 123456h + + jb regbit1,d1 + jbc regbit1,d2 + + jmp 1234h + jmp [r3] + jmp [a+dptr] + jmp [[r5+]] + + jnb regbit1,d3 + + jnz d3 + + jz d3 + + lea r5,r4+4 + lea r6,r1+1000 + + lsr.b r4h,r1l + lsr.w r6,r3h + lsr.d r2,r4l + lsr.b r4h,#6 + lsr.w r6,#12 + lsr.d r2,#24 + + mov c,regbit1 + mov regbit1,c + mov usp,r4 + mov sp,usp + mov.b r4h,r1l + mov.w r5,r3 + mov.b r5l,[r6] + mov.w r4,[sp] + mov.b [r6],r5l + mov.w [sp],r4 + mov.b r3h,[r6+2] + mov.w r4,[r3+100] + mov.b [r6+2],r3h + mov.w [r3+100],r4 + mov.b r3h,[r6+200] + mov.w r4,[r3+1000] + mov.b [r6+200],r3h + mov.w [r3+1000],r4 + mov.b r4h,[r1+] + mov.w r5,[r6+] + mov.b [r1+],r4h + mov.w [r6+],r5 + mov.b [r3+],[r4+] + mov.w [r3+],[r4+] + mov.b 200h,r2l + mov.w 123h,r6 + mov.b r2l,200h + mov.w r6,123h + mov.b 123h,[r5] + mov.w 456h,[sp] + mov.b [r5],123h + mov.w [sp],456h + mov.b r5h,#34h + mov.w r3,#1234h + mov.b [r5],#34h + mov.w [r3],#1234h + mov.b [r5+],#34h + mov.w [r3+],#1234h + mov.b [r5+2],#34h + mov.w [r3+100],#1234h + mov.b [r5+200],#34h + mov.w [r3+1000],#1234h + mov.b 200h,#34h + mov.w 123h,#1234h + mov.b 123h,200h + mov.w 123h,200h + + movc r4l,[r5+] + movc r4,[r5+] + movc a,[a+dptr] + movc a,[a+pc] + + movs.b r5h,#3 + movs.w r6,#5 + movs.b [r4],#3 + movs.w [sp],#5 + movs.b [r4+],#3 + movs.w [sp+],#5 + movs.b [r4+20],#3 + movs.w [sp+20],#5 + movs.b [r4-200],#3 + movs.w [sp-200],#5 + movs.b 200h,#3 + movs.w 123h,#5 + + movx r3l,[r6] + movx r3,[sp] + movx [r6],r3l + movx [sp],r3 + + mul r0,r5 + mul r6,#1234h + + mulu r3l,r4h + mulu r5l,#100 + mulu r0,r5 + mulu r6,#1234h + + neg r4l + neg sp + + nop + + norm.b r4h,r1l + norm.w r6,r3h + norm.d r2,r4l + + or.b r4h,r1l + or.w r5,r3 + or.b r5l,[r6] + or.w r4,[sp] + or.b [r6],r5l + or.w [sp],r4 + or.b r3h,[r6+2] + or.w r4,[r3+100] + or.b [r6+2],r3h + or.w [r3+100],r4 + or.b r3h,[r6+200] + or.w r4,[r3+1000] + or.b [r6+200],r3h + or.w [r3+1000],r4 + or.b r4h,[r1+] + or.w r5,[r6+] + or.b [r1+],r4h + or.w [r6+],r5 + or.b 200h,r2l + or.w 123h,r6 + or.b r2l,200h + or.w r6,123h + or.b r5h,#34h + or.w r3,#1234h + or.b [r5],#34h + or.w [r3],#1234h + or.b [r5+],#34h + or.w [r3+],#1234h + or.b [r5+2],#34h + or.w [r3+100],#1234h + or.b [r5+200],#34h + or.w [r3+1000],#1234h + or.b 200h,#34h + or.w 123h,#1234h + + orl c,regbit1 + orl c,/iobit1 + orl c,r5.12 + orl c,/r4h.1 + + pop.b 123h + pop.w 200h + pop r2l + pop r2l,r3l + pop r4h + pop r4h,r5h + pop r2l,r3l,r4h,r5h + pop r1 + pop r2,r5;,sp + + popu.b 123h + popu.w 200h + popu r2l + popu r2l,r3l + popu r4h + popu r4h,r5h + popu r2l,r3l,r4h,r5h + popu r1 + popu r2,r5,sp + + push.b 123h + push.w 200h + push r2l + push r2l,r3l + push r4h + push r4h,r5h + push r2l,r3l,r4h,r5h + push r1 + push r2,r5,sp + + pushu.b 123h + pushu.w 200h + pushu r2l + pushu r2l,r3l + pushu r4h + pushu r4h,r5h + pushu r2l,r3l,r4h,r5h + pushu r1 + pushu r2,r5,sp + + reset + + ret + + reti + + rl r3h,#3 + rl r5,#12 + + rlc r3h,#3 + rlc r5,#12 + + rr r3h,#3 + rr r5,#12 + + rrc r3h,#3 + rrc r5,#12 + + setb regbit1 + + sext r1l + sext r2 + + sub.b r4h,r1l + sub.w r5,r3 + sub.b r5l,[r6] + sub.w r4,[sp] + sub.b [r6],r5l + sub.w [sp],r4 + sub.b r3h,[r6+2] + sub.w r4,[r3+100] + sub.b [r6+2],r3h + sub.w [r3+100],r4 + sub.b r3h,[r6+200] + sub.w r4,[r3+1000] + sub.b [r6+200],r3h + sub.w [r3+1000],r4 + sub.b r4h,[r1+] + sub.w r5,[r6+] + sub.b [r1+],r4h + sub.w [r6+],r5 + sub.b 200h,r2l + sub.w 123h,r6 + sub.b r2l,200h + sub.w r6,123h + sub.b r5h,#34h + sub.w r3,#1234h + sub.b [r5],#34h + sub.w [r3],#1234h + sub.b [r5+],#34h + sub.w [r3+],#1234h + sub.b [r5+2],#34h + sub.w [r3+100],#1234h + sub.b [r5+200],#34h + sub.w [r3+1000],#1234h + sub.b 200h,#34h + sub.w 123h,#1234h + + subb.b r4h,r1l + subb.w r5,r3 + subb.b r5l,[r6] + subb.w r4,[sp] + subb.b [r6],r5l + subb.w [sp],r4 + subb.b r3h,[r6+2] + subb.w r4,[r3+100] + subb.b [r6+2],r3h + subb.w [r3+100],r4 + subb.b r3h,[r6+200] + subb.w r4,[r3+1000] + subb.b [r6+200],r3h + subb.w [r3+1000],r4 + subb.b r4h,[r1+] + subb.w r5,[r6+] + subb.b [r1+],r4h + subb.w [r6+],r5 + subb.b 200h,r2l + subb.w 123h,r6 + subb.b r2l,200h + subb.w r6,123h + subb.b r5h,#34h + subb.w r3,#1234h + subb.b [r5],#34h + subb.w [r3],#1234h + subb.b [r5+],#34h + subb.w [r3+],#1234h + subb.b [r5+2],#34h + subb.w [r3+100],#1234h + subb.b [r5+200],#34h + subb.w [r3+1000],#1234h + subb.b 200h,#34h + subb.w 123h,#1234h + + trap #5 + + xch r3h,r5l + xch r5l,r3h + xch r3,r5 + xch r5,r3 + xch r3h,[r5] + xch [r5],r3h + xch r3,[r5] + xch [r5],r3 + xch r3h,123h + xch 123h,r3h + xch r3,200h + xch 200h,r3 + + xor.b r4h,r1l + xor.w r5,r3 + xor.b r5l,[r6] + xor.w r4,[sp] + xor.b [r6],r5l + xor.w [sp],r4 + xor.b r3h,[r6+2] + xor.w r4,[r3+100] + xor.b [r6+2],r3h + xor.w [r3+100],r4 + xor.b r3h,[r6+200] + xor.w r4,[r3+1000] + xor.b [r6+200],r3h + xor.w [r3+1000],r4 + xor.b r4h,[r1+] + xor.w r5,[r6+] + xor.b [r1+],r4h + xor.w [r6+],r5 + xor.b 200h,r2l + xor.w 123h,r6 + xor.b r2l,200h + xor.w r6,123h + xor.b r5h,#34h + xor.w r3,#1234h + xor.b [r5],#34h + xor.w [r3],#1234h + xor.b [r5+],#34h + xor.w [r3+],#1234h + xor.b [r5+2],#34h + xor.w [r3+100],#1234h + xor.b [r5+200],#34h + xor.w [r3+1000],#1234h + xor.b 200h,#34h + xor.w 123h,#1234h + + mov.b [r5+],[r5+] + xch r4l,r4l + pop r7 + norm.b r4l,r4l + norm.w r4,r4h + norm.d r4,r5l + mov [r4+],r4l + mov r4h,[r4+] + movc r4h,[r4+] + add [r4+],r4l + add r4h,[r4+] + mov r5,[r5+] + diff --git a/tests/t_xa/t_xa.doc b/tests/t_xa/t_xa.doc new file mode 100644 index 0000000..3a7edf8 --- /dev/null +++ b/tests/t_xa/t_xa.doc @@ -0,0 +1,5 @@ ++--------------------------- Test Application XA ----------------------------+ +| | +| This is a (synthetic) test of the Philips XA instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_xa/t_xa.ori b/tests/t_xa/t_xa.ori new file mode 100644 index 0000000..edfa696 Binary files /dev/null and b/tests/t_xa/t_xa.ori differ diff --git a/tests/t_z380/asflags b/tests/t_z380/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_z380/t_z380.asm b/tests/t_z380/t_z380.asm new file mode 100644 index 0000000..a681044 --- /dev/null +++ b/tests/t_z380/t_z380.asm @@ -0,0 +1,677 @@ + cpu z380 + include regz380 + + extmode on + + page 0 + relaxed on + + ddir w + ddir ib,w + ddir iw,w + ddir ib + ddir lw + ddir ib,lw + ddir iw,lw + ddir iw + + cpl + cpl a + neg + neg a + + ei + ei $40 + di + di $bf + + btest + exall + exxx + exxy + indw + indrw + iniw + inirw + lddw + lddrw + ldiw + ldirw + mtest + otdrw + otirw + outdw + outiw + retb + + cplw + cplw hl + negw + negw hl + + ret + ret nz + ret z + ret nc + ret c + ret po + ret nv + ret pe + ret v + ret p + ret ns + ret m + ret s + + jp 1234h + jp 123456h + ddir ib + jp 123456h + ddir iw + jp 123456h + ddir w + jp 123456h + ddir lw + jp 123456h + ddir w,iw + jp 123456h + jp 12345678h + ddir lw + jp 12345678h + jp z,4321h + jp nc,654321h + jp pe,87654321h + jp (hl) + jp (ix) + jp (iy) + + call $1234 + call $123456 + call $12345678 + call nz,$4321 + call m,$654321 + call po,$87654321 + + jr $+20 + jr c,$-20 + jr $-200 + jr z,$+200 + jr $+$200000 + jr nc,$-$200000 + + calr $+20 + calr c,$-20 + calr $-200 + calr z,$+200 + calr $+$200000 + calr nc,$-$200000 + + djnz $+20 + djnz $-200 + djnz $+$200000 + + exts a + exts + extsw hl + extsw + + and a + and a,b + and a,c + and a,d + and a,e + and a,h + and a,l + and a,ixl + and a,ixu + and a,iyl + and a,iyu + and a,$55 + and a,(hl) + and a,(ix+20) + and a,(iy-300) + and a,(ix+100000) + + andw ix + andw hl,ix + andw hl,iy + andw hl,bc + andw hl,de + andw hl,hl + andw hl,(ix+5) + andw hl,(iy-200) + andw hl,55aah + + cp a + cp a,b + cp a,c + cp a,d + cp a,e + cp a,h + cp a,l + cp a,ixl + cp a,ixu + cp a,iyl + cp a,iyu + cp a,$34 + cp a,(hl) + cp a,(ix-20) + cp a,(iy+$300) + cp a,(ix+100000h) + + cpw ix + cpw hl,ix + cpw hl,iy + cpw hl,bc + cpw hl,de + cpw hl,hl + cpw hl,(ix+17) + cpw hl,(iy-200) + cpw hl,$aa55 + + or a + or a,b + or a,c + or a,d + or a,e + or a,h + or a,l + or a,ixl + or a,ixu + or a,iyl + or a,iyu + or a,$34 + or a,(hl) + or a,(ix-20) + or a,(iy+$300) + or a,(ix+100000h) + + orw ix + orw hl,ix + orw hl,iy + orw hl,bc + orw hl,de + orw hl,hl + orw hl,(ix+17) + orw hl,(iy-200) + orw hl,$aa55 + + xor a + xor a,b + xor a,c + xor a,d + xor a,e + xor a,h + xor a,l + xor a,ixl + xor a,ixu + xor a,iyl + xor a,iyu + xor a,$34 + xor a,(hl) + xor a,(ix-20) + xor a,(iy+$300) + xor a,(ix+100000h) + + xorw ix + xorw hl,ix + xorw hl,iy + xorw hl,bc + xorw hl,de + xorw hl,hl + xorw hl,(ix+17) + xorw hl,(iy-200) + xorw hl,$aa55 + + sub a + sub a,b + sub a,c + sub a,d + sub a,e + sub a,h + sub a,l + sub a,ixl + sub a,ixu + sub a,iyl + sub a,iyu + sub a,$34 + sub a,(hl) + sub a,(ix-20) + sub a,(iy+$300) + sub a,(ix+100000h) + + sub hl,(1234h) + sub hl,(123456h) + sub hl,(12345678h) + sub sp,3412o + + subw ix + subw hl,ix + subw hl,iy + subw hl,bc + subw hl,de + subw hl,hl + subw hl,(ix+17) + subw hl,(iy-200) + subw hl,$aa55 + + add a,b + add a,iyu + add a,' ' + add a,(hl) + add a,(ix+10) + add a,(ix+1000) + add hl,bc + add ix,de + add iy,iy + add ix,sp + add hl,(12345678h) + add sp,3412o + + addw bc + addw hl,hl + addw hl,iy + addw hl,2314h + addw hl,(ix+128) + + adc a,h + adc a,ixu + adc a,20 + adc a,(hl) + adc a,(ix-500) + adc hl,sp + + adcw hl,bc + adcw hl,iy + adcw hl,$abcd + adcw hl,(iy-30) + + sbc a,d + sbc a,iyl + sbc a,20h + sbc a,(hl) + sbc a,(ix+500) + sbc hl,sp + + sbcw hl,bc + sbcw hl,iy + sbcw hl,$abcd + sbcw hl,(iy-30) + + dec a + dec (hl) + dec ixu + dec (ix+35) + + decw de + dec iy + + inc a + inc (hl) + inc ixu + inc (ix+35) + + incw de + inc iy + + rl d + rl (hl) + rl (ix+200) + rlw ix + rlw iy + rlw de + rlw hl + rlw (hl) + rlw (iy+$100000) + + rlc d + rlc (hl) + rlc (ix+200) + rlcw ix + rlcw iy + rlcw de + rlcw hl + rlcw (hl) + rlcw (iy+$100000) + + rr d + rr (hl) + rr (ix+200) + rrw ix + rrw iy + rrw de + rrw hl + rrw (hl) + rrw (iy+$100000) + + rrc d + rrc (hl) + rrc (ix+200) + rrcw ix + rrcw iy + rrcw de + rrcw hl + rrcw (hl) + rrcw (iy+$100000) + + sla d + sla (hl) + sla (ix+200) + slaw ix + slaw iy + slaw de + slaw hl + slaw (hl) + slaw (iy+$100000) + + sra d + sra (hl) + sra (ix+200) + sraw ix + sraw iy + sraw de + sraw hl + sraw (hl) + sraw (iy+$100000) + + srl d + srl (hl) + srl (ix+200) + srlw ix + srlw iy + srlw de + srlw hl + srlw (hl) + srlw (iy+$100000) + + bit 5,a + bit 6,(hl) + bit 3,(ix+67) + + res 5,a + res 6,(hl) + res 3,(ix+67) + + set 5,a + set 6,(hl) + set 3,(ix+67) + + mlt bc + mlt hl + mlt sp + + ld a,c + ld a,h + ld a,iyu + ld a,ixl + ld a,(hl) + ld a,(ix+20) + ld a,(iy-300) + ld a,(bc) + ld a,(de) + ld a,'A' + ld a,(2000h) + ld a,(10000h) + ld a,r + ld a,i + ld d,a + ld d,e + ld d,ixl + ld d,(hl) + ld d,(iy+15) + ld d,'D' + ld ixl,a + ld iyu,'I' + ld iyl,iyu + ld ixu,ixl + ld ixl,e + ld (hl),a + ld (hl),c + ld (ix+100),a + ld (iy-200),d + ld (hl),'H' + ld (ix),'X' + ld (hl),hl + ld (hl),de + ld (hl),bc + ld (hl),ix + ld (hl),iy + ld (ix),hl + ld (ix),de + ld (ix),bc + ld (iy),hl + ld (iy),de + ld (iy),bc + ld (iy),ix + ld (ix+123456h),iy + ld sp,hl + ld sp,iy + ddir lw + ld sp,123456h + ld sp,(6) + ld bc,(hl) + ld de,(hl) + ld hl,(hl) + ld bc,(ix) + ld de,(ix) + ld hl,(ix) + ld bc,(iy) + ld de,(iy) + ld hl,(iy) + ld bc,hl + ld de,bc + ld de,ix + ld hl,iy + ld de,(bc) + ld hl,(de) + ld hl,2000h + ddir lw + ld hl,12345687h + ld hl,(2000h) + ld de,(20000h) + ld hl,(sp+5) + ld de,(sp-200) + ld ix,(hl) + ld iy,(hl) + ld ix,(iy) + ld iy,(ix) + ld iy,hl + ld ix,bc + ld ix,iy + ld iy,ix + ld ix,(bc) + ld iy,(de) + ddir lw + ld ix,123456h + ld iy,0 + ld ix,(2000h) + ld iy,(87654321h) + ld ix,(sp) + ld (bc),a + ld (de),a + ld (bc),de + ld (de),hl + ld (de),iy + ld ($20001),a + ld (123456h),hl + ld (123456h),ix + ld (123456h),de + ld (123456h),sp + ld i,a + ld i,hl + ld r,a + ld hl,i + ld (sp),de + ld (sp),ix + ld (hl),10 + ldw (hl),1000 + ddir lw + ldw (hl),100000 + ldw (bc),30 + ldw (de),40 + + pop af + pop sr + pop bc + pop de + pop hl + pop ix + pop iy + push af + push sr + push 300 + push bc + push de + push hl + push ix + push iy + + ex af,af' + ex (sp),hl + ex hl,(sp) + ex (sp),ix + ex ix,(sp) + ex (sp),iy + ex iy,(sp) + ex de,hl + ex hl,de + ex a,a' + ex c,c' + ex a,h + ex d,a + ex a,(hl) + ex (hl),a + ex bc,de + ex bc,hl + ex bc,ix + ex bc,iy + ex de,bc + ex de,hl + ex de,ix + ex de,iy + ex hl,bc + ex hl,de + ex hl,ix + ex hl,iy + ex ix,bc + ex ix,de + ex ix,hl + ex ix,iy + ex iy,bc + ex iy,de + ex iy,hl + ex iy,ix + ex bc,bc' + ex de,de' + ex hl,hl' + ex ix,ix' + ex iy,iy' + + im 0 + im 1 + im 2 + im 3 + + in a,(12h) + out (12h),a + in c,(c) + out (c),c + out (c),12h + + inw bc,(c) + outw (c),bc + inw de,(c) + outw (c),de + inw hl,(c) + outw (c),hl + outw (c),$2002 + + in0 d,(20h) + in0 (20h) + out0 (20h),e + + ina a,(12h) + inaw hl,(1234h) + outa (123456h),a + outaw (12345678h),hl + + tstio 1<<7 + + tst a + tst (hl) + tst 33h + + divuw (ix+5) + multw hl,(iy-3) + multuw hl,(iy+100) + divuw hl,bc + multw hl,de + multuw hl,hl + divuw hl,ix + multw hl,iy + multuw hl,ix + divuw hl,10 + multw hl,100 + multuw hl,1000 + + ldctl sr,a + ldctl xsr,a + ldctl a,xsr + ldctl dsr,a + ldctl a,dsr + ldctl ysr,a + ldctl a,ysr + ldctl sr,20h + ldctl xsr,31h + ldctl dsr,42h + ldctl ysr,53h + ldctl sr,hl + ldctl hl,sr + + resc lw + setc lw + resc lck + setc lck + setc xm + + swap bc + swap de + swap hl + swap ix + swap iy + + out (c),0 + + cpu z80undoc + + slia d + slia (ix+5) + slia (hl) + slia a + inc ixl + inc iyu + dec ixu + dec iyl + ld iyl,'a' + ld b,ixl + ld ixu,c + ld iyl,iyu + add a,ixl + adc a,ixu + sub a,iyl + sbc a,iyu + and a,ixl + xor a,ixu + or a,iyl + cp a,iyu + rlc (ix+3) + rrc b,(iy-3) + slia a,(ix-100) + res 5,h + set 6,(ix+6) + bit 3,(hl) + res c,4,(ix-1) + set l,6,(iy+17) + out (c),0 + in (c) + tsti diff --git a/tests/t_z380/t_z380.doc b/tests/t_z380/t_z380.doc new file mode 100644 index 0000000..b9b1af3 --- /dev/null +++ b/tests/t_z380/t_z380.doc @@ -0,0 +1,5 @@ ++------------------------- Test Application Z380 ----------------------------+ +| | +| This is a (synthetic) test of the Z80/Z380/Z80UNDOC instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_z380/t_z380.ori b/tests/t_z380/t_z380.ori new file mode 100644 index 0000000..83a5d92 Binary files /dev/null and b/tests/t_z380/t_z380.ori differ diff --git a/tests/t_z8/asflags b/tests/t_z8/asflags new file mode 100644 index 0000000..e69de29 diff --git a/tests/t_z8/t_z8.asm b/tests/t_z8/t_z8.asm new file mode 100644 index 0000000..a2f46c7 --- /dev/null +++ b/tests/t_z8/t_z8.asm @@ -0,0 +1,116 @@ + cpu z8601 + + ccf + rcf + scf + + di + ei + + halt + stop + + wdh + wdt + + iret + ret + + nop + + and r7,r13 + and r5,vari + and vari,r4 + + and r3,@r14 + and r2,@vari + and vari,@r6 + + and r3,#5 + and vari,#77 + and @r9,#35h + and @vari,#10011b + + add 2,5 + adc r5,#4 + sub @r0,#20 + sbc r7,vari + or vari,@r5 + tcm r0,@r8 + tm @vari,#00001000b + cp vari,#20 + xor r5,#255 + + inc r5 + inc @r12 + inc vari + + dec r6 + dec vari + dec @r5 + dec @vari + decw rr6 + decw vari + decw @r5 + decw @vari + decw @r5 + +test1: jr test1 + jr f,test1 + jr uge,test1 + + djnz r5,test1 + + call test1 + call @vari + call @rr10 + + jp test1 + jp c,test1 + jp @vari + jp @rr6 + + + ld r3,r4 + ld r5,vari + ld r6,@r7 + ld r8,@vari + ld r9,vari(r10) + ld r11,#45 + + ld vari,r12 + ld vari,vari + ld vari,@r13 + ld vari,@vari + ld vari,#67 + + ld @r14,r15 + ld @r0,vari + ld @r1,#89 + + ld @vari,r2 + ld @vari,vari + ld @vari,#01 + + ld vari(r3),r4 + + + ldc r5,@rr6 + ldc @rr8,r7 + lde r9,@rr10 + lde @rr12,r11 + + ldci @r13,@rr14 + ldci @rr0,@r15 + ldei @r1,@rr2 + ldei @rr4,@r3 + + + srp #0 + + + segment data + + org 0aah +vari: + diff --git a/tests/t_z8/t_z8.doc b/tests/t_z8/t_z8.doc new file mode 100644 index 0000000..c6cc2b5 --- /dev/null +++ b/tests/t_z8/t_z8.doc @@ -0,0 +1,5 @@ ++-------------------------- Test Application Z8 -----------------------------+ +| | +| This is a (synthetic) test of the Z8 instruction set | +| | ++----------------------------------------------------------------------------+ diff --git a/tests/t_z8/t_z8.ori b/tests/t_z8/t_z8.ori new file mode 100644 index 0000000..ffe9e81 Binary files /dev/null and b/tests/t_z8/t_z8.ori differ diff --git a/tests/testall b/tests/testall new file mode 100755 index 0000000..15bb2d1 --- /dev/null +++ b/tests/testall @@ -0,0 +1,38 @@ +#!/bin/sh + +echo executing self tests... +echo "=================================================================" > ../testlog +echo "Summaric results:" >> ../testlog +SUMPASS="0" +SUMFAIL="0" +if [ "$1" = "" ]; then + SUBDIRS=t_* +else + SUBDIRS="$1" +fi +for t in $SUBDIRS; do + cd $t + cat $t.doc + ../../asl `cat asflags` -i ../../include $t.asm | tee $t.log + ../../p2bin -k -l 0 -r 0x-0x $t + echo +---------------------------------------------------------------+ + if cmp $t.ori $t.bin; then + echo "Test $t succeeded!" + SUMPASS=`expr $SUMPASS + 1` + echo "$t : OK" >> ../../testlog + else + echo "Test $t failed!" + SUMFAIL=`expr $SUMFAIL + 1` + echo "$t : failed" >> ../../testlog + fi + grep assembly $t.log >> ../../testlog + grep Assemblierzeit $t.log >> ../../testlog + echo +---------------------------------------------------------------+ + rm -f $t.bin + rm -f $t.log + rm -f $t.h + cd .. +done +echo "successes: $SUMPASS" >> ../testlog +echo "failures : $SUMFAIL" >> ../testlog +cat ../testlog diff --git a/tests/testall.bat b/tests/testall.bat new file mode 100644 index 0000000..8d81cc8 --- /dev/null +++ b/tests/testall.bat @@ -0,0 +1,117 @@ +@echo off +if "%1"=="" goto main + +cd %1 +type %1.doc | ..\..\addcr +set ASCMD=@asflags +..\..\asl -i ..\..\include -L +t 31 %1.asm +set ASCMD= +..\..\p2bin -k -l 0 -r $-$ %1 +..\..\bincmp %1.bin %1.ori +if errorlevel 1 goto errcond +echo Test %1 succeeded! +set SUMPASS=%SUMPASS%! +echo %1 : OK >> ..\..\testlog +:goon +echo +---------------------------------------------------------------+ +type %1.lst | find "assembly" >> ..\..\testlog +type %1.lst | find "Assemblierzeit" >> ..\..\testlog +if exist %1.lst del %1.lst >nul +if exist %1.inc del %1.inc >nul +if exist %1.bin del %1.bin >nul +cd .. +goto end + +:errcond +echo Test %1 failed! +set SUMFAIL=%SUMFAIL%- +echo %1 : failed >> ..\..\testlog +goto goon + +:main +if exist ..\addcr.exe goto nocomp +bcc -e..\addcr.exe -ml ..\addcr.c +del addcr.obj +:nocomp +if exist ..\bincmp.exe goto nocomp2 +bcc -e..\bincmp.exe -ml ..\bincmp.c +del bincmp.obj +:nocomp2 +echo executing self tests... +echo ================================================================= >..\testlog +echo Summaric results: >> ..\testlog +set SUMPASS= +set SUMFAIL= +call testall t_166 +call testall t_16c5x +call testall t_16c84 +call testall t_17c42 +call testall t_251 +call testall t_296 +call testall t_29k +call testall t_32 +call testall t_3201x +call testall t_3203x +call testall t_3205x +call testall t_3206x +call testall t_370 +call testall t_4004 +call testall t_403 +call testall t_4500 +call testall t_47c00 +call testall t_48 +call testall t_56000 +call testall t_56300 +call testall t_65 +call testall t_6502u +call testall t_6804 +call testall t_68040 +call testall t_6805 +call testall t_6808 +call testall t_6812 +call testall t_6816 +call testall t_7000 +call testall t_75k0 +call testall t_7700 +call testall t_7720 +call testall t_77230 +call testall t_7725 +call testall t_78c1x +call testall t_78k0 +call testall t_85 +call testall t_87c800 +call testall t_8X30x +call testall t_96 +call testall t_960 +call testall t_97c241 +call testall t_9900 +call testall t_ace +call testall t_avr +call testall t_bas52 +call testall t_buf32 +call testall t_cop8 +call testall t_f2mc8l +call testall t_fl90 +call testall t_fl900 +call testall t_full09 +call testall t_h8_3 +call testall t_h8_5 +call testall t_m16c +call testall t_mcore +call testall t_mic51 +call testall t_msp +call testall t_parsys +call testall t_scmp +call testall t_secdri +call testall t_st6 +call testall t_st7 +call testall t_st9 +call testall t_tms7 +call testall t_xa +call testall t_z380 +call testall t_z8 +echo successes: %SUMPASS% >> ..\testlog +echo failures: %SUMFAIL% >> ..\testlog +type ..\testlog + +:end diff --git a/tests/testall.cmd b/tests/testall.cmd new file mode 100644 index 0000000..667dc39 --- /dev/null +++ b/tests/testall.cmd @@ -0,0 +1,117 @@ +@echo off +if "%1"=="" goto main + +cd %1 +type %1.doc | ..\..\addcr +set ASCMD=@asflags +..\..\asl -i ..\..\include -L +t 31 %1.asm +set ASCMD= +..\..\p2bin -k -l 0 -r $-$ %1 +..\..\bincmp %1.bin %1.ori +if errorlevel 1 goto errcond +echo Test %1 succeeded! +set SUMPASS=%SUMPASS%+ +echo %1 : OK >> ..\..\testlog +:goon +echo +---------------------------------------------------------------+ +type %1.lst | find "assembly" >> ..\..\testlog +type %1.lst | find "Assemblierzeit" >> ..\..\testlog +if exist %1.lst del %1.lst >nul +if exist %1.inc del %1.inc >nul +if exist %1.bin del %1.bin >nul +cd .. +goto end + +:errcond +echo Test %1 failed! +set SUMFAIL=%SUMFAIL%- +echo %1 : failed >> ..\..\testlog +goto goon + +:main +if exist ..\addcr.exe goto nocomp +echo Compiling 'addcr'... +gcc -o ..\addcr.exe ..\addcr.c +:nocomp +if exist ..\bincmp.exe goto nocomp2 +echo Compiling 'bincmp'... +gcc -o ..\bincmp.exe ..\bincmp.c +:nocomp2 +echo executing self tests... +echo "=================================================================" >..\testlog +echo Summaric results: >> ..\testlog +set SUMPASS= +set SUMFAIL= +call testall t_166 +call testall t_16c5x +call testall t_16c84 +call testall t_17c42 +call testall t_251 +call testall t_296 +call testall t_29k +call testall t_32 +call testall t_3201x +call testall t_3203x +call testall t_3205x +call testall t_3206x +call testall t_370 +call testall t_4004 +call testall t_403 +call testall t_4500 +call testall t_47c00 +call testall t_48 +call testall t_56000 +call testall t_56300 +call testall t_65 +call testall t_6502u +call testall t_6804 +call testall t_68040 +call testall t_6805 +call testall t_6808 +call testall t_6812 +call testall t_6816 +call testall t_7000 +call testall t_75k0 +call testall t_7700 +call testall t_7720 +call testall t_77230 +call testall t_7725 +call testall t_78c1x +call testall t_78k0 +call testall t_85 +call testall t_87c800 +call testall t_8X30x +call testall t_96 +call testall t_960 +call testall t_97c241 +call testall t_9900 +call testall t_ace +call testall t_avr +call testall t_bas52 +call testall t_buf32 +call testall t_cop8 +call testall t_f2mc8l +call testall t_fl90 +call testall t_fl900 +call testall t_full09 +call testall t_h8_3 +call testall t_h8_5 +call testall t_m16c +call testall t_mcore +call testall t_mic51 +call testall t_msp +call testall t_parsys +call testall t_scmp +call testall t_secdrive +call testall t_st6 +call testall t_st7 +call testall t_st9 +call testall t_tms7 +call testall t_xa +call testall t_z380 +call testall t_z8 +echo successes: %SUMPASS% >> ..\testlog +echo failures: %SUMFAIL% >> ..\testlog +type ..\testlog + +:end diff --git a/tests/warnlog.DE b/tests/warnlog.DE new file mode 100644 index 0000000..f75bc00 --- /dev/null +++ b/tests/warnlog.DE @@ -0,0 +1,35 @@ +t_166.asm(175) : Warnung : moegliche Pipelining-Effekte +t_166.asm(181) : Warnung : moegliche Pipelining-Effekte +t_166.asm(181) : Warnung : moegliche Pipelining-Effekte +t_166.asm(185) : Warnung : moegliche Pipelining-Effekte +t_166.asm(226) : Warnung : Seite moeglicherweise nicht adressierbar +t_166.asm(231) : Warnung : Seite moeglicherweise nicht adressierbar +t_16c84.asm(9) : Warnung : veralteter Befehl +t_16c84.asm(50) : Warnung : veralteter Befehl +t_3203x.asm(259) : Warnung : mehrfache Adressregisterbenutzung in einer Anweisung +t_3203x.asm(259) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_3203x.asm(261) : Warnung : mehrfache Adressregisterbenutzung in einer Anweisung +t_7000.asm(95) : Warnung : moegliche Pipelining-Effekte +t_7000.asm(96) : Warnung : moegliche Pipelining-Effekte +t_7000.asm(97) : Warnung : moegliche Pipelining-Effekte +t_7000.asm(98) : Warnung : moegliche Pipelining-Effekte +t_7000.asm(99) : Warnung : moegliche Pipelining-Effekte +t_75k0.asm(186) : Warnung : Seite moeglicherweise nicht adressierbar +t_87c800.asm(134) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_87c800.asm(135) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_87c800.asm(167) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_96.asm(155) : Warnung : kurzer Sprung moeglich +t_96.asm(159) : Warnung : kurzer Sprung moeglich +t_cop8.asm(112) : Warnung : Distanz 0 nicht bei Kurzsprung erlaubt (NOP erzeugt) +t_xa.asm(591) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_xa.asm(592) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_xa.asm(593) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_xa.asm(594) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_xa.asm(595) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_xa.asm(596) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_xa.asm(597) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_xa.asm(598) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_xa.asm(599) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_xa.asm(600) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_xa.asm(601) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung +t_xa.asm(602) : Warnung : nicht vorhersagbare Ausfuehrung dieser Anweisung diff --git a/tests/warnlog.EN b/tests/warnlog.EN new file mode 100644 index 0000000..5e7afe3 --- /dev/null +++ b/tests/warnlog.EN @@ -0,0 +1,35 @@ +t_166.asm(175) : warning : possible pipelining effects +t_166.asm(181) : warning : possible pipelining effects +t_166.asm(181) : warning : possible pipelining effects +t_166.asm(185) : warning : possible pipelining effects +t_166.asm(226) : warning : page might not be addressable +t_166.asm(231) : warning : page might not be addressable +t_16c84.asm(9) : warning : obsolete instruction, usage discouraged +t_16c84.asm(50) : warning : obsolete instruction, usage discouraged +t_3203x.asm(259) : warning : multiple use of address register in one instruction +t_3203x.asm(259) : warning : unpredictable execution of this instruction +t_3203x.asm(261) : warning : multiple use of address register in one instruction +t_7000.asm(95) : warning : possible pipelining effects +t_7000.asm(96) : warning : possible pipelining effects +t_7000.asm(97) : warning : possible pipelining effects +t_7000.asm(98) : warning : possible pipelining effects +t_7000.asm(99) : warning : possible pipelining effects +t_75k0.asm(186) : warning : page might not be addressable +t_87c800.asm(134) : warning : unpredictable execution of this instruction +t_87c800.asm(135) : warning : unpredictable execution of this instruction +t_87c800.asm(167) : warning : unpredictable execution of this instruction +t_96.asm(155) : warning : short jump possible +t_96.asm(159) : warning : short jump possible +t_cop8.asm(112) : warning : distance of 0 not allowed for short jump (NOP created instead) +t_xa.asm(591) : warning : unpredictable execution of this instruction +t_xa.asm(592) : warning : unpredictable execution of this instruction +t_xa.asm(593) : warning : unpredictable execution of this instruction +t_xa.asm(594) : warning : unpredictable execution of this instruction +t_xa.asm(595) : warning : unpredictable execution of this instruction +t_xa.asm(596) : warning : unpredictable execution of this instruction +t_xa.asm(597) : warning : unpredictable execution of this instruction +t_xa.asm(598) : warning : unpredictable execution of this instruction +t_xa.asm(599) : warning : unpredictable execution of this instruction +t_xa.asm(600) : warning : unpredictable execution of this instruction +t_xa.asm(601) : warning : unpredictable execution of this instruction +t_xa.asm(602) : warning : unpredictable execution of this instruction -- cgit v1.2.3