home *** CD-ROM | disk | FTP | other *** search
/ Oakland CPM Archive / oakcpm.iso / cpm / parasol / asm-a86.ark / ASM-A86.SRC < prev   
Text File  |  1986-10-07  |  22KB  |  818 lines

  1.     [number match level address]
  2. ASM.to.A86.translator:
  3. begin
  4. {-------------------------------------------------------------
  5. {
  6. {    A program to convert CP/M ASM files into MSDOS ASM files
  7. {
  8. {        This program is invoked with the following command:
  9. {
  10. {    A>ASM-A86 sourcename
  11. {
  12. {        Note that source-name should have NO file-type specified.
  13. {
  14. {        The input file is assumed to have a file-type of .ASM
  15. {    The output file will be given a filetype of .A86
  16. {
  17. {        This program does only a surface-level translation.  It
  18. {    does not do the exhaustive analysis that XLT-86 (from DRI)
  19. {    does.  You will likely need to do quite a bit of editing on
  20. {    the A86 file to make it useable.  Conditional jumps are not
  21. {    checked to see that they are within range, etc.  When the 8080
  22. {    code does a PUSH PSW, this program does a PUSH AX.  This will
  23. {    usually work, but will fail when the PUSH PSW was intended to
  24. {    save the condition-codes rather than simply preserving the value
  25. {    in the accumulator.
  26. {        Still, considering the cost of XLT-86, it's not such a
  27. {    bad deal.
  28. {
  29. {    Copyright (C) 1986 by Shay O. Walters and Para-Soft.
  30. {
  31. {    Permission is granted for this program to be used without
  32. {    restriction for private non-commercial use.
  33. {
  34. {---------------------------------------------------------------------
  35. byte        source.char;
  36. string        source.line    133;
  37. word        source.line.num    value 0;
  38. pointer to byte source.line.ptr value #source.line;
  39. string        source.buf    512;
  40.  
  41. file    source,
  42.     file1,
  43.     text,
  44.     disk,
  45.     record source.char,
  46.     buffer source.buf,
  47.     value    "X.ASM";
  48.  
  49.  
  50.  
  51. byte        output.char;
  52. string        output.line 133;
  53. pointer to byte    output.line.ptr value #output.line;
  54. string        output.buff    256;
  55. byte        output.line.colm;
  56.  
  57. file    output.file,
  58.     disk, file1,
  59.     text,
  60.     record output.char,
  61.     buffer    output.buff,
  62.     value    "X.A86";
  63.  
  64.  
  65.  
  66.  
  67.  
  68. {--------miscellaneous variables----------}
  69.  
  70.  
  71. string    output.word    81;
  72. word    word.length;
  73.  
  74. string    work.word    81;
  75. string    curr.address    5;
  76.  
  77.  
  78. byte    curr.delim;
  79. byte            value 0;    {-string ender-}
  80.  
  81.  
  82.  
  83.  
  84. bit    flag;
  85. bit    equ.flag;
  86. bit    blank.address;
  87.  
  88.  
  89. word    generated.label.num    value    1000;
  90. string    decimal.work    8;
  91. string    gen.lbl.char    2    value    "X";
  92.  
  93. string    high.value.word 2;
  94.                 redefine high.value.word;
  95. byte    value ^hff,    value 0;
  96.                 endredef;
  97.  
  98.  
  99.  
  100. string    delimiters    24;
  101.                 redefine delimiters;
  102. byte
  103. value " "    ,value "("    ,value "+"    ,value ";"
  104. ,value ^h09    ,value ")"    ,value "-"    ,value "="
  105. ,value ^h0d    ,value "<"    ,value "*"    ,value ":"
  106. ,value ^h0a    ,value ">"    ,value "/"    ,value ","
  107. ,value '!'    ,value '['    ,value ']'
  108. ,value ^h1a    ,value "'"    ,value '"'    ,value 0;
  109.  
  110.                 endredef;
  111.  
  112.  
  113. byte        wk.byte;
  114. pointer to byte    wk.bp;
  115.  
  116. external label    entry    address 5;
  117. external word bdos.ptr address 6;
  118. external byte    cmd.gen.char    address    ^h6d;
  119.  
  120.  
  121. {---reserved word table---}
  122.  
  123. record    reserved.word.table;
  124. string 4 value 'ACI';        byte value 1;
  125. string 4 value 'ADC';        byte value 2;
  126. string 4 value 'ADD';        byte value 2;
  127. string 4 value 'ADI';        byte value 1;
  128. string 4 value 'ANA';        byte value 2;
  129. string 4 value 'ANI';        byte value 1;
  130. string 5 value 'CALL';        byte value 4;
  131. string 3 value 'CC';        byte value 9;
  132. string 3 value 'CM';        byte value 9;
  133. string 4 value 'CMA';        byte value 3;
  134. string 4 value 'CMC';        byte value 3;
  135. string 4 value 'CMP';        byte value 2;
  136. string 4 value 'CNC';        byte value 9;
  137. string 4 value 'CNZ';        byte value 9;
  138. string 3 value 'CP';        byte value 9;
  139. string 4 value 'CPE';        byte value 9;
  140. string 4 value 'CPI';        byte value 1;
  141. string 4 value 'CPO';        byte value 9;
  142. string 3 value 'CZ';        byte value 9;
  143. string 4 value 'DAA';        byte value 3;
  144. string 4 value 'DAD';        byte value 10;
  145. string 4 value 'DCR';        byte value 16;
  146. string 4 value 'DCX';        byte value 10;
  147. string 3 value 'DI';        byte value 3;
  148. string 3 value 'EI';        byte value 3;
  149. string 4 value 'HLT';        byte value 3;
  150. string 3 value 'IN';        byte value 1;
  151. string 4 value 'INR';        byte value 16;
  152. string 4 value 'INX';        byte value 10;
  153. string 3 value 'JC';        byte value 4;
  154. string 3 value 'JM';        byte value 4;
  155. string 4 value 'JMP';        byte value 4;
  156. string 4 value 'JNC';        byte value 4;
  157. string 4 value 'JNZ';        byte value 4;
  158. string 3 value 'JP';        byte value 4;
  159. string 4 value 'JPE';        byte value 4;
  160. string 4 value 'JPO';        byte value 4;
  161. string 3 value 'JZ';        byte value 4;
  162. string 4 value 'LDA';        byte value 4;
  163. string 5 value 'LDAX';        byte value 11;
  164. string 5 value 'LHLD';        byte value 4;
  165. string 4 value 'LXI';        byte value 13;
  166. string 4 value 'MOV';        byte value 7;
  167. string 4 value 'MVI';        byte value 15;
  168. string 4 value 'NOP';        byte value 3;
  169. string 4 value 'ORA';        byte value 2;
  170. string 4 value 'ORI';        byte value 1;
  171. string 4 value 'OUT';        byte value 0;    {-don't bother-}
  172. string 5 value 'PCHL';        byte value 3;
  173. string 4 value 'POP';        byte value 10;
  174. string 5 value 'PUSH';        byte value 10;
  175. string 4 value 'RAL';        byte value 3;
  176. string 4 value 'RAR';        byte value 3;
  177. string 3 value 'RC';        byte value 8;
  178. string 4 value 'RET';        byte value 3;
  179. string 4 value 'RLC';        byte value 3;
  180. string 3 value 'RM';        byte value 8;
  181. string 4 value 'RNC';        byte value 8;
  182. string 4 value 'RNZ';        byte value 8;
  183. string 3 value 'RP';        byte value 8;
  184. string 4 value 'RPE';        byte value 8;
  185. string 4 value 'RPO';        byte value 8;
  186. string 4 value 'RRC';        byte value 3;
  187. string 4 value 'RST';        byte value 0;    {-don't bother-}
  188. string 3 value 'RZ';        byte value 8;
  189. string 4 value 'SBB';        byte value 2;
  190. string 4 value 'SBI';        byte value 1;
  191. string 5 value 'SHLD';        byte value 6;
  192. string 5 value 'SPHL';        byte value 3;
  193. string 4 value 'STA';        byte value 5;
  194. string 4 value 'STC';        byte value 3;
  195. string 5 value 'STAX';        byte value 12;
  196. string 4 value 'SUB';        byte value 2;
  197. string 4 value 'SUI';        byte value 1;
  198. string 5 value 'XCHG';        byte value 3;
  199. string 4 value 'XRA';        byte value 2;
  200. string 4 value 'XRI';        byte value 1;
  201. string 5 value 'XTHL';        byte value 3;
  202. string 4 value 'EQU';        byte value 0;
  203. string 3 value 'DB';        byte value 0;
  204. string 3 value 'DW';        byte value 0;
  205. string 3 value 'DS';        byte value 14;
  206. string 4 value 'ORG';        byte value 0;
  207. string 4 value 'END';        byte value 0;
  208. string 5 value "~FFFFFFFF~";
  209. endrec;
  210.  
  211. pointer to string rsvd.wd.tbl.ptr;
  212. byte    rsvd.wd.length;
  213. byte    rsvd.word.found;
  214. byte    op.class;
  215.  
  216. {-------- start of procedures --------}
  217.  
  218.  
  219. procedure    get.source.line:
  220. begin
  221.     fill output.word with 0;
  222.     fill source.line with 0;
  223.     while    source.char = ^h0a
  224.     do
  225.         read source;
  226.         od;
  227.     while    source.char = ^h00
  228.     do
  229.         read source;
  230.         od;
  231.     move #source.line to source.line.ptr;
  232.     while source.char <> ^h0d
  233.     and source.char <> "!"
  234.     do
  235.         move source.char to @source.line.ptr;
  236.         add 1 to source.line.ptr;
  237.         if source.char = ^h0a then
  238.             read source;
  239.             move ^h0a to source.char;
  240.             fi;
  241.         if source.char = ^h1a
  242.         then
  243.             move ^h00 to @source.line.ptr;
  244.             move #source.line to source.line.ptr;
  245.             exit;
  246.             fi;
  247.         read source;
  248.         od;
  249.     read source;            {-skip c/r or "!"-}
  250.     move ^h00 to @source.line.ptr;
  251.     move #source.line to source.line.ptr;
  252.     end;
  253.  
  254. {----------------------------------}
  255.  
  256. procedure    put.output.char:
  257. begin
  258.     write output.file;
  259.     mcall entry using 2,output.char;    {*debug*}
  260. end;
  261.  
  262. procedure    put.cr.lf:
  263. begin
  264.     move ^h0d to output.char;
  265.     call put.output.char;
  266.     move ^h0a to output.char;
  267.     call put.output.char;
  268.     move 1 to output.line.colm;
  269.     end;
  270.  
  271. {----------------------------------------}
  272. procedure    put.output.word:
  273. begin
  274.     mcall entry using 11 giving ,,,wk.byte;
  275.     if wk.byte <> 0 then
  276.         mcall entry using 1 giving ,,,wk.byte;
  277.         and wk.byte with ^h7f;
  278.         if wk.byte = ^h03 then
  279.             goto end;
  280.         fi;    fi;
  281.     move #output.word to wk.bp;
  282.     while @wk.bp <> 0 do
  283.         if @wk.bp = "." then
  284.             move "_" to @wk.bp;
  285.             fi;
  286.         move @wk.bp to output.char;
  287.         call put.output.char;
  288.         add 1 to wk.bp;
  289.         od;
  290. end;
  291.  
  292. {-------------------------------------------}
  293.  
  294.  
  295.  
  296. procedure    skip.white.space:
  297. begin
  298.     while @source.line.ptr[bp] = " "
  299.     or @source.line.ptr[bp] = ^h09 do
  300.         add 1 to source.line.ptr;
  301.         od;
  302. end;
  303.  
  304. procedure    get.next.output.word:
  305. begin
  306.     call skip.white.space;
  307.     scan @source.line.ptr[sp] for any " ,!;:()~090d~" giving word.length;
  308.     move @source.line.ptr[sp] to output.word length word.length;
  309.     add word.length to source.line.ptr;
  310.     add word.length to #output.word giving wk.bp;
  311.     move 0 to @wk.bp;
  312. end;
  313. procedure    copy.rest.of.line:
  314. begin
  315.     while @source.line.ptr[bp] <> ^h0d
  316.     and @source.line.ptr[bp] <> 0
  317.     and @source.line.ptr[bp] <> ^h0a
  318.     and @source.line.ptr[bp] <> ^h1a do
  319.         if @source.line.ptr[bp] = '.' then
  320.             move "_" to @source.line.ptr[bp];
  321.             fi;
  322.         move @source.line.ptr[bp] to output.char;
  323.         call put.output.char;
  324.         add 1 to source.line.ptr;
  325.         od;
  326.     call put.cr.lf;
  327. end;
  328. procedure    output.8.bit.reg:
  329. begin
  330.     convert output.word to upper case;
  331.     switch on output.word:
  332.         "A":    move "al" to output.word;
  333.         "B":    move "ch" to output.word;
  334.         "C":    move "cl" to output.word;
  335.         "D":    move "dh" to output.word;
  336.         "E":    move "dl" to output.word;
  337.         "H":    move "bh" to output.word;
  338.         "L":    move "bl" to output.word;
  339.         "M":    move "[bx]" to output.word;
  340.         endswitch;
  341.     call put.output.word;
  342. end;
  343. procedure    output.16.bit.reg:
  344. begin
  345.     convert output.word to upper case;
  346.     switch on output.word:
  347.         "H":    move "bx" to output.word;
  348.         "B":    move "cx" to output.word;
  349.         "D":    move "dx" to output.word;
  350.         "PSW":    move "ax" to output.word;
  351.         "SP":    move "sp" to output.word;
  352.         endswitch;
  353.     call put.output.word;
  354. end;
  355.  
  356.  
  357.  
  358. {---------- main program ----------}
  359.  
  360.     if cmd.gen.char <> " " then
  361.         move cmd.gen.char to gen.lbl.char[byte];
  362.         fi;
  363.     open source input
  364.     error begin
  365.         display "no source file found";
  366.         goto end;
  367.         end;
  368.     open output.file output
  369.     error begin
  370.         display "output file open error";
  371.         goto end;
  372.         end;
  373.     read source;
  374. get.next.source.line:
  375.     call get.source.line;
  376.     {--------------------------------------
  377.     {    Skip over any label
  378.     {--------------------------------------
  379. restart.this.line:
  380.     if @source.line.ptr[bp] = ^h1a then
  381.         goto translation.finished;
  382.         fi;
  383.     if @source.line.ptr[bp] = 0 then
  384.         goto get.next.source.line;
  385.         fi;
  386.     if @source.line.ptr[bp] >= "A"
  387.     and @source.line.ptr[bp] <= "z" then
  388.         scan @source.line.ptr[sp] for any " :;~090d0a~"
  389.             giving word.length;
  390.         move @source.line.ptr[sp] to output.word
  391.             length word.length;
  392.         add word.length to #output.word giving wk.bp;
  393.         move 0 to @wk.bp;
  394.         call put.output.word;
  395.         add word.length to source.line.ptr;
  396.         if @source.line.ptr = ":" then
  397.             move ":" to output.char;
  398.             call put.output.char;
  399.             add 1 to source.line.ptr;
  400.             if @source.line.ptr[bp] <> " "
  401.             and @source.line.ptr[bp] <> 0
  402.             and @source.line.ptr[bp] <> ^h09
  403.             and @source.line.ptr[bp] <> ^h0d then
  404.                 subtract 1 from source.line.ptr;
  405.                 move ^h09 to @source.line.ptr[bp];
  406.             fi;    fi;
  407.         if  @source.line.ptr[bp] <> " "
  408.         and @source.line.ptr[bp] <> ^h09 then
  409.             call put.cr.lf;
  410.             fi;
  411.         goto restart.this.line;
  412.         fi;
  413.     {------------------------------------------------
  414.     {    skip any leading white space
  415.     {------------------------------------------------
  416.     while @source.line.ptr[bp] = " "
  417.     or @source.line.ptr[bp] = ^h09 do
  418.         move @source.line.ptr[bp] to output.char;
  419.         call put.output.char;
  420.         add 1 to source.line.ptr;
  421.         od;
  422.     {-----------------------------------------------
  423.     {    Check for comment line
  424.     {-----------------------------------------------
  425.     if @source.line.ptr[bp] = ";" then
  426.         call copy.rest.of.line;
  427.         goto get.next.source.line;
  428.         fi;
  429.     {--------------------------------------------
  430.     {    Check for null line
  431.     {--------------------------------------------
  432.     if @source.line.ptr[bp] = ^h0d then
  433.         call put.cr.lf;
  434.         goto get.next.source.line;
  435.         fi;
  436.     {--------------------------------------------
  437.     {  it's not a label, white space or comment
  438.     {  it must be an op-code
  439.     {--------------------------------------------
  440.     scan @source.line.ptr[sp] for any " ;:()~090d~" giving word.length;
  441.     move @source.line.ptr[sp] to output.word length word.length;
  442.     add word.length to source.line.ptr;
  443.     add word.length to #output.word giving wk.bp;
  444.     move 0 to @wk.bp;
  445.  
  446.     move output.word to work.word;
  447.     convert work.word to upper case;
  448.     move "N" to rsvd.word.found;
  449.     move #reserved.word.table to rsvd.wd.tbl.ptr;
  450.     do
  451.         if @rsvd.wd.tbl.ptr = work.word
  452.             size @rsvd.wd.tbl.ptr giving rsvd.wd.length;
  453.             add rsvd.wd.length to rsvd.wd.tbl.ptr;
  454.             add 1 to rsvd.wd.tbl.ptr;
  455.             move @rsvd.wd.tbl.ptr[bp] to op.class;
  456.             move "Y" to rsvd.word.found;
  457.             exitdo;
  458.             fi;
  459.         size @rsvd.wd.tbl.ptr giving rsvd.wd.length;
  460.         add rsvd.wd.length to rsvd.wd.tbl.ptr;
  461.         add 2              to rsvd.wd.tbl.ptr;
  462.         od until @rsvd.wd.tbl.ptr[bp] = 0;
  463.     {------------------------------------------
  464.     {    don't know what it is.
  465.     {    output it and start over
  466.     {-----------------------------------------
  467.     if rsvd.word.found = "N" then
  468.         call put.output.word;
  469.         goto restart.this.line;
  470.         fi;
  471.     {------------------------------------------
  472.     {    found a reserved word - translate it
  473.     {------------------------------------------
  474.     switch on op.class:
  475.     1: begin
  476.         {-----------------------------
  477.         { ACI, ADI, etc. (also IN)
  478.         {------------------------------
  479.         switch on work.word:
  480.             "ACI":    move "adc" to output.word;
  481.             "ADI":    move "add" to output.word;
  482.             "ANI":    move "and" to output.word;
  483.             "CPI":    move "cmp" to output.word;
  484.             "IN":    move "in"  to output.word;
  485.             "ORI":    move "or"  to output.word;
  486.             "SBI":    move "sbb" to output.word;
  487.             "SUI":    move "sub" to output.word;
  488.             "XRI":    move "xor" to output.word;
  489.             endswitch;
  490.         append "~09~al," to output.word;
  491.         call put.output.word;
  492.         call skip.white.space;
  493.         call copy.rest.of.line;
  494.         goto get.next.source.line;
  495.         end;
  496.  
  497.     2: begin
  498.         {-----------------------------
  499.         { ADC ADD etc.
  500.         {------------------------------
  501.         switch on work.word:
  502.             "ADC":    move "adc" to output.word;
  503.             "ADD":    move "add" to output.word;
  504.             "ANA":    move "and" to output.word;
  505.             "CMP":    move "cmp" to output.word;
  506.             "ORA":    move "or"  to output.word;
  507.             "SBB":    move "sbb" to output.word;
  508.             "SUB":    move "sub" to output.word;
  509.             "XRA":    move "xor" to output.word;
  510.             endswitch;
  511.         append "~09~al," to output.word;
  512.         call put.output.word;
  513.         call skip.white.space;
  514.         call get.next.output.word;
  515.         call output.8.bit.reg;
  516.         call copy.rest.of.line;
  517.         goto get.next.source.line;
  518.         end;
  519.  
  520.     3: begin
  521.         {-----------------------------
  522.         { op's with no arguments
  523.         {------------------------------
  524.         switch on work.word:
  525.             "CMA":    move "not~09~al"    to output.word;
  526.             "CMC":    move "cmc"        to output.word;
  527.             "DAA":    move "daa"        to output.word;
  528.             "DI":    move "cli"        to output.word;
  529.             "EI":    move "sti"        to output.word;
  530.             "HLT":    move "halt"        to output.word;
  531.             "NOP":    move "nop"        to output.word;
  532.             "PCHL":    move "jmp~09~bx"    to output.word;
  533.             "RAL":    move "rcl~09~al,1"    to output.word;
  534.             "RAR":    move "rcr~09~al,1"    to output.word;
  535.             "RET":    move "ret"        to output.word;
  536.             "RLC":    move "rol~09~al,1"    to output.word;
  537.             "RRC":    move "ror~09~al,1"    to output.word;
  538.             "SPHL":    move "mov~09~sp,bx"    to output.word;
  539.             "XCHG":    move "xchg~09~bx,dx"    to output.word;
  540.             "XTHL":    move "pop bp ! push bx ! mov bx,bp"
  541.                             to output.word;
  542.             endswitch;
  543.         call put.output.word;
  544.         call copy.rest.of.line;
  545.         goto get.next.source.line;
  546.         end;
  547.  
  548.     4: begin
  549.         {-----------------------------------
  550.         { op with single label
  551.         {-----------------------------------
  552.         switch on work.word:
  553.             "CALL":    move "call~09~"        to output.word;
  554.             "JMP":    move "jmp~09~"        to output.word;
  555.             "JC":    move "jc~09~"        to output.word;
  556.             "JM":    move "js~09~"        to output.word;
  557.             "JNC":    move "jnc~09~"        to output.word;
  558.             "JNZ":    move "jnz~09~"        to output.word;
  559.             "JP":    move "jns~09~"        to output.word;
  560.             "JPE":    move "jpe~09~"        to output.word;
  561.             "JPO":    move "jpo~09~"        to output.word;
  562.             "JZ":    move "jz~09~"        to output.word;
  563.             "LDA":    move "mov~09~al,"    to output.word;
  564.             "LHLD":    move "mov~09~bx,"    to output.word;
  565.             endswitch;
  566.         call put.output.word;
  567.         call skip.white.space;
  568.         call copy.rest.of.line;
  569.         goto get.next.source.line;
  570.         end;
  571.  
  572.     5: begin
  573.         {-----------------------------------
  574.         {    STA
  575.         {-----------------------------------
  576.         move "mov~09~" to output.word;
  577.         call put.output.word;
  578.         call skip.white.space;
  579.         call get.next.output.word;
  580.         call put.output.word;
  581.         move ",al" to output.word;
  582.         call put.output.word;
  583.         call copy.rest.of.line;
  584.         goto get.next.source.line;
  585.         end;
  586.  
  587.     6: begin
  588.         {-----------------------------------
  589.         {    SHLD
  590.         {-----------------------------------
  591.         move "mov~09~" to output.word;
  592.         call put.output.word;
  593.         call skip.white.space;
  594.         call get.next.output.word;
  595.         call put.output.word;
  596.         move ",bx" to output.word;
  597.         call put.output.word;
  598.         call copy.rest.of.line;
  599.         goto get.next.source.line;
  600.         end;
  601.  
  602.     7: begin
  603.         {---------------------
  604.         {    MOV
  605.         {---------------------
  606.         move "mov~09~" to output.word;
  607.         call put.output.word;
  608.         call skip.white.space;
  609.         call get.next.output.word;
  610.         call output.8.bit.reg;
  611.         call skip.white.space;
  612.         if @source.line.ptr[bp] <> "," then    {--error--}
  613.             call copy.rest.of.line;
  614.             goto get.next.source.line;
  615.             fi;
  616.         move ',' to output.char;
  617.         call put.output.char;
  618.         add 1 to source.line.ptr;
  619.         call get.next.output.word;
  620.         call output.8.bit.reg;
  621.         call copy.rest.of.line;
  622.         goto get.next.source.line;
  623.         end;
  624.  
  625.     8: begin
  626.         {--------------------------------------
  627.         { conditional RETURN
  628.         {--------------------------------------
  629.         switch on work.word:
  630.             "RC":    move "jnc"    to output.word;
  631.             "RM":    move "jns"    to output.word;
  632.             "RNC":    move "jc"    to output.word;
  633.             "RNZ":    move "jz"    to output.word;
  634.             "RP":    move "js"    to output.word;
  635.             "RPE":    move "jpo"    to output.word;
  636.             "RPO":    move "jpe"    to output.word;
  637.             "RZ":    move "jnz"    to output.word;
  638.             endswitch;
  639.         append "~09~" to output.word;
  640.         append gen.lbl.char to output.word;
  641.         convert generated.label.num to decimal.work;
  642.         append decimal.work to output.word;
  643.         call put.output.word;
  644.         call put.cr.lf;
  645.         move "~09~ret" to output.word;
  646.         call put.output.word;
  647.         call copy.rest.of.line;
  648.         move gen.lbl.char[byte] to output.word[byte];
  649.         move decimal.work to output.word[+1];
  650.         append ":" to output.word;
  651.         call put.output.word;
  652.         call put.cr.lf;
  653.         add 1 to generated.label.num;
  654.         goto get.next.source.line;
  655.         end;
  656.  
  657.     9: begin
  658.         {--------------------------------------
  659.         { conditional CALL
  660.         {--------------------------------------
  661.         switch on work.word:
  662.             "CC":    move "jnc"    to output.word;
  663.             "CM":    move "jns"    to output.word;
  664.             "CNC":    move "jc"    to output.word;
  665.             "CNZ":    move "jz"    to output.word;
  666.             "CP":    move "js"    to output.word;
  667.             "CPE":    move "jpo"    to output.word;
  668.             "CPO":    move "jpe"    to output.word;
  669.             "CZ":    move "jnz"    to output.word;
  670.             endswitch;
  671.         append "~09~" to output.word;
  672.         append gen.lbl.char to output.word;
  673.         convert generated.label.num to decimal.work;
  674.         append decimal.work to output.word;
  675.         call put.output.word;
  676.         call put.cr.lf;
  677.         move "~09~call" to output.word;
  678.         call put.output.word;
  679.         call copy.rest.of.line;
  680.         move gen.lbl.char[byte] to output.word[byte];
  681.         move decimal.work to output.word[+1];
  682.         append ":" to output.word;
  683.         call put.output.word;
  684.         call put.cr.lf;
  685.         add 1 to generated.label.num;
  686.         goto get.next.source.line;
  687.         end;
  688.  
  689.     10: begin
  690.         {------------------------------
  691.         { op with single double-reg arg
  692.         {------------------------------
  693.         switch on work.word:
  694.             "DAD":    move "add~09~bx," to output.word;
  695.             "DCX":    move "dec~09~" to output.word;
  696.             "INX":    move "inc~09~" to output.word;
  697.             "POP":    move "pop~09~" to output.word;
  698.             "PUSH":    move "push~09~" to output.word;
  699.             endswitch;
  700.         call put.output.word;
  701.         call skip.white.space;
  702.         call get.next.output.word;
  703.         call output.16.bit.reg;
  704.         call copy.rest.of.line;
  705.         goto get.next.source.line;
  706.         end;
  707.  
  708.     11: begin
  709.         {-----------------
  710.         {    LDAX
  711.         {-----------------
  712.         call skip.white.space;
  713.         move "mov~09~si," to output.word;
  714.         call put.output.word;
  715.         call get.next.output.word;
  716.         call output.16.bit.reg;
  717.         move " ! mov al,[si]" to output.word;
  718.         call put.output.word;
  719.         call copy.rest.of.line;
  720.         goto get.next.source.line;
  721.         end;
  722.  
  723.     12: begin
  724.         {-----------------
  725.         {    STAX
  726.         {-----------------
  727.         call skip.white.space;
  728.         move "mov~09~di," to output.word;
  729.         call put.output.word;
  730.         call get.next.output.word;
  731.         call output.16.bit.reg;
  732.         move " ! mov [di],al" to output.word;
  733.         call put.output.word;
  734.         call copy.rest.of.line;
  735.         goto get.next.source.line;
  736.         end;
  737.  
  738.     13: begin
  739.         {-----------------
  740.         {    LXI
  741.         {-----------------
  742.         call skip.white.space;
  743.         move "mov~09~" to output.word;
  744.         call put.output.word;
  745.         call get.next.output.word;
  746.         call output.16.bit.reg;
  747.         if @source.line.ptr[bp] <> "," then
  748.             call copy.rest.of.line;
  749.             goto get.next.source.line;
  750.             fi;
  751.         add 1 to source.line.ptr;
  752.         move "," to output.char;
  753.         call put.output.char;
  754.         call skip.white.space;
  755.         if @source.line.ptr <> "-" then
  756.             if @source.line.ptr[bp] < "0"
  757.             or @source.line.ptr[bp] > "9" then
  758.                 move " offset " to output.word;
  759.                 call put.output.word;
  760.             fi;    fi;
  761.         call copy.rest.of.line;
  762.         goto get.next.source.line;
  763.         end;
  764.  
  765.     14: begin
  766.         {------------------------
  767.         {    DS
  768.         {------------------------
  769.         move "rs" to output.word;
  770.         call put.output.word;
  771.         call copy.rest.of.line;
  772.         goto get.next.source.line;
  773.         end;
  774.  
  775.     15: begin
  776.         {-----------------------------
  777.         { MVI
  778.         {------------------------------
  779.         move "mov~09~" to output.word;
  780.         call put.output.word;
  781.         call skip.white.space;
  782.         call get.next.output.word;
  783.         call output.8.bit.reg;
  784.         call skip.white.space;
  785.         call copy.rest.of.line;
  786.         goto get.next.source.line;
  787.         end;
  788.     16: begin
  789.         {-----------------------------
  790.         { INR DCR
  791.         {------------------------------
  792.         switch on work.word:
  793.             "DCR":    move "dec" to output.word;
  794.             "INR":    move "inc" to output.word;
  795.             endswitch;
  796.         append "~09~" to output.word;
  797.         call put.output.word;
  798.         call skip.white.space;
  799.         call get.next.output.word;
  800.         call output.8.bit.reg;
  801.         call copy.rest.of.line;
  802.         goto get.next.source.line;
  803.         end;
  804.  
  805.  
  806.  
  807.     endswitch;
  808.     call put.output.word;
  809.     call copy.rest.of.line;
  810.     goto get.next.source.line;
  811.  
  812.  
  813.  
  814. translation.finished:
  815.     close output.file;
  816.     display "finished";
  817. end;
  818.