summaryrefslogtreecommitdiff
path: root/v2.0/source/DEBASM.ASM
diff options
context:
space:
mode:
authorGravatar Rich Turner1983-08-12 17:53:34 -0700
committerGravatar Rich Turner2018-09-21 17:53:34 -0700
commit80ab2fddfdf30f09f0a0a637654cbb3cd5c7baa6 (patch)
treeee4357f7f3dd0f2ded59b9c6e7384432d85e7ec9 /v2.0/source/DEBASM.ASM
parentMS-DOS v1.25 Release (diff)
downloadms-dos-80ab2fddfdf30f09f0a0a637654cbb3cd5c7baa6.tar.gz
ms-dos-80ab2fddfdf30f09f0a0a637654cbb3cd5c7baa6.tar.xz
ms-dos-80ab2fddfdf30f09f0a0a637654cbb3cd5c7baa6.zip
MS-DOS v2.0 Release
Diffstat (limited to 'v2.0/source/DEBASM.ASM')
-rw-r--r--v2.0/source/DEBASM.ASM1264
1 files changed, 1264 insertions, 0 deletions
diff --git a/v2.0/source/DEBASM.ASM b/v2.0/source/DEBASM.ASM
new file mode 100644
index 0000000..a0fb0db
--- /dev/null
+++ b/v2.0/source/DEBASM.ASM
@@ -0,0 +1,1264 @@
1TITLE DEBASM
2
3; Code for the ASSEMble command in the debugger
4
5.xlist
6.xcref
7 INCLUDE DEBEQU.ASM
8 INCLUDE DOSSYM.ASM
9.cref
10.list
11
12
13CODE SEGMENT PUBLIC BYTE 'CODE'
14CODE ENDS
15
16CONST SEGMENT PUBLIC BYTE
17
18 EXTRN DBMN:BYTE,CSSAVE:WORD,REG8:BYTE,REG16:BYTE,SIZ8:BYTE
19 EXTRN SYNERR:BYTE,OPTAB:BYTE,MAXOP:ABS
20
21CONST ENDS
22
23DATA SEGMENT PUBLIC BYTE
24
25 EXTRN HINUM:WORD,LOWNUM:WORD,ASSEM_CNT:BYTE
26 EXTRN ASSEM1:BYTE,ASSEM2:BYTE,ASSEM3:BYTE,ASSEM4:BYTE,ASSEM5:BYTE
27 EXTRN ASSEM6:BYTE,OPBUF:BYTE,OPCODE:WORD,REGMEM:BYTE,INDEX:WORD
28 EXTRN ASMADD:BYTE,ASMSP:WORD,MOVFLG:BYTE,SEGFLG:BYTE,TSTFLG:BYTE
29 EXTRN NUMFLG:BYTE,DIRFLG:BYTE,BYTEBUF:BYTE,F8087:BYTE,DIFLG:BYTE
30 EXTRN SIFLG:BYTE,BXFLG:BYTE,BPFLG:BYTE,NEGFLG:BYTE,MEMFLG:BYTE
31 EXTRN REGFLG:BYTE,AWORD:BYTE,MIDFLD:BYTE,MODE:BYTE
32
33DATA ENDS
34
35DG GROUP CODE,CONST,DATA
36
37
38CODE SEGMENT PUBLIC BYTE 'CODE'
39ASSUME CS:DG,DS:DG,ES:DG,SS:DG
40
41 PUBLIC ASSEM
42 PUBLIC DB_OPER,DW_OPER,ASSEMLOOP,GROUP2,AA_OPER,DCINC_OPER
43 PUBLIC GROUP1,ESC_OPER,FGROUPP,FGROUPX,FDE_OPER,FGROUPZ
44 PUBLIC FD9_OPER,FGROUP,FDB_OPER,FGROUPB,FGROUP3,FGROUP3W
45 PUBLIC FGROUPDS,INT_OPER,IN_OPER,DISP8_OPER,JMP_OPER,NO_OPER
46 PUBLIC OUT_OPER,L_OPER,MOV_OPER,POP_OPER,PUSH_OPER,ROTOP
47 PUBLIC TST_OPER,EX_OPER,GET_DATA16,CALL_OPER
48
49 EXTRN INBUF:NEAR,SCANB:NEAR,SCANP:NEAR,GETHX:NEAR,GET_ADDRESS:NEAR
50 EXTRN DEFAULT:NEAR,OUTDI:NEAR,BLANK:NEAR,PRINTMES:NEAR,TAB:NEAR
51
52;
53; Line by line assembler
54;
55
56ASSEM:
57 MOV BP,[CSSAVE] ; Default code segment
58 MOV DI,OFFSET DG:ASMADD ; Default address
59 CALL DEFAULT
60 MOV WORD PTR [ASMADD],DX ; Displacement of disassembly
61 MOV WORD PTR [ASMADD+2],AX ; Segment
62 MOV [ASMSP],SP ; Save sp in case of error
63
64ASSEMLOOP:
65 MOV SP,[ASMSP] ; Restore sp in case of error
66 LES DI,DWORD PTR ASMADD ; GET PC
67 CALL OUTDI ; OUTPUT ADDRESS
68 CALL BLANK ; SKIP A SPACE
69 PUSH CS
70 POP ES
71 CALL INBUF ; GET A BUFFER
72 CALL SCANB
73 JNZ OPLOOK
74 RET ; IF EMPTY JUST RETURN
75;
76; At this point ds:si points to the opcode mnemonic...
77;
78OPLOOK: XOR CX,CX ; OP-CODE COUNT = 0
79 MOV DI,OFFSET DG:DBMN
80OPSCAN: XOR BX,BX
81OPLOOP: MOV AL,[DI+BX]
82 AND AL,7FH
83 CMP AL,[SI+BX]
84 JZ OPMATCH
85 INC CX ; INCREMENT OP-CODE COUNT
86 CMP CX,MAXOP ; CHECK FOR END OF LIST
87 JB OP1
88 JMP ASMERR
89OP1: INC DI ; SCAN FOR NEXT OP-CODE...
90 TEST BYTE PTR [DI-1],80H
91 JZ OP1
92 JMP OPSCAN
93
94OPMATCH:INC BX ; COMPARE NEXT CHAR
95 TEST BYTE PTR [DI+BX-1],80H ; ARE WE DONE?
96 JZ OPLOOP ; ..IF NOT KEEP COMPARING
97 XCHG BX,CX
98 MOV AX,BX
99 SHL AX,1
100 ADD AX,BX
101 ADD AX,OFFSET DG:OPTAB
102 MOV BX,AX
103;
104; CX = COUNT OF CHARS IN OPCODE
105; BX = POINTER INTO OPCODE TABLE
106;
107 XOR AX,AX
108 MOV BYTE PTR [AWORD],AL
109 MOV WORD PTR [MOVFLG],AX ; MOVFLG + TSTFLG
110 MOV BYTE PTR [SEGFLG],AL ; ZERO SEGMENT REGISTER FLAG
111 MOV AH,00001010B ; SET UP FOR AA_OPER
112 MOV AL,BYTE PTR [BX]
113 MOV WORD PTR [ASSEM1],AX
114 MOV BYTE PTR [ASSEM_CNT],1
115
116 ADD SI,CX ; SI POINTS TO OPERAND
117 JMP WORD PTR [BX+1]
118;
119; 8087 INSTRUCTIONS WITH NO OPERANDS
120;
121FDE_OPER:
122 MOV AH,0DEH
123 JMP SHORT FDX_OPER
124FDB_OPER:
125 MOV AH,0DBH
126 JMP SHORT FDX_OPER
127FD9_OPER:
128 MOV AH,0D9H
129FDX_OPER:
130 XCHG AL,AH
131 MOV WORD PTR [ASSEM1],AX
132;
133; aad and aam instrucions
134;
135AA_OPER:INC BYTE PTR [ASSEM_CNT]
136;
137; instructions with no operands
138;
139NO_OPER:
140 CALL STUFF_BYTES
141 CALL SCANP
142 PUSH CS
143 POP ES
144 JNZ OPLOOK
145 JMP ASSEMLOOP
146;
147; push instruction
148;
149PUSH_OPER:
150 MOV AH,11111111B
151 JMP SHORT POP1
152;
153; pop instruction
154;
155POP_OPER:
156 MOV AH,10001111B
157POP1: MOV [ASSEM1],AH
158 MOV [MIDFLD],AL
159 INC BYTE PTR [MOVFLG] ; ALLOW SEGMENT REGISTERS
160 MOV BYTE PTR [AWORD],2 ; MUST BE 16 BITS
161 CALL GETREGMEM
162 CALL BUILDIT
163 MOV AL,[DI+2]
164 CMP AL,11000000B
165 JB DATRET
166 MOV BYTE PTR [DI],1
167 CMP BYTE PTR [MOVFLG],2
168 JNZ POP2
169 AND AL,00011000B
170 OR AL,00000110B
171 CMP BYTE PTR [MIDFLD],0
172 JNZ POP3
173 OR AL,00000001B
174 JMP SHORT POP3
175
176POP2: AND AL,111B
177 OR AL,01010000B
178 CMP BYTE PTR [MIDFLD],0
179 JNZ POP3
180 OR AL,01011000B
181POP3: MOV BYTE PTR [DI+1],AL
182 JMP ASSEM_EXIT
183;
184; ret and retf instructions
185;
186GET_DATA16:
187 CALL SCANB
188 MOV CX,4
189 CALL GETHX
190 JC DATRET
191 DEC BYTE PTR [ASSEM1] ; CHANGE OP-CODE
192 ADD BYTE PTR [ASSEM_CNT],2 ; UPDATE LENGTH
193 MOV WORD PTR [ASSEM2],DX ; SAVE OFFSET
194DATRET: JMP ASSEM_EXIT
195;
196; int instruction
197;
198INT_OPER:
199 CALL SCANB
200 MOV CX,2
201 CALL GETHX
202 JC ERRV1
203 MOV AL,DL
204 CMP AL,3
205 JZ DATRET
206 INC BYTE PTR [ASSEM1]
207 JMP DISPX
208;
209; in instruction
210;
211IN_OPER:
212 CALL SCANB
213 LODSW
214 CMP AX,"A"+4C00H ; "AL"
215 JZ IN_1
216 CMP AX,"A"+5800H ; "AX"
217 JZ IN_0
218ERRV1: JMP ASMERR
219IN_0: INC BYTE PTR [ASSEM1]
220IN_1: CALL SCANP
221 CMP WORD PTR [SI],"D"+5800H ; "DX"
222 JZ DATRET
223 MOV CX,2
224 CALL GETHX
225 JC ERRV1
226 AND BYTE PTR [ASSEM1],11110111B
227 MOV AL,DL
228 JMP DISPX
229;
230; out instruction
231;
232OUT_OPER:
233 CALL SCANB
234 CMP WORD PTR [SI],"D"+5800H ; "DX"
235 JNZ OUT_0
236 INC SI
237 INC SI
238 JMP SHORT OUT_1
239OUT_0: AND BYTE PTR [ASSEM1],11110111B
240 MOV CX,2
241 CALL GETHX
242 JC ERRV1
243 INC BYTE PTR [ASSEM_CNT]
244 MOV BYTE PTR [ASSEM2],DL
245OUT_1: CALL SCANP
246 LODSW
247 CMP AX,"A"+4C00H ; "AL"
248 JZ DATRET
249 CMP AX,"A"+5800H ; "AX"
250 JNZ ERRV1
251 INC BYTE PTR [ASSEM1]
252 JMP DATRET
253
254;
255; jump instruction
256;
257JMP_OPER:
258 INC BYTE PTR [TSTFLG]
259;
260; call instruction
261;
262CALL_OPER:
263 MOV BYTE PTR [ASSEM1],11111111B
264 MOV BYTE PTR [MIDFLD],AL
265 CALL GETREGMEM
266 CALL BUILD3
267 CMP BYTE PTR [MEMFLG],0
268 JNZ CALLJ1
269 CMP BYTE PTR [REGMEM],-1
270 JZ CALLJ2
271;
272; INDIRECT JUMPS OR CALLS
273;
274CALLJ1: CMP BYTE PTR [AWORD],1
275ERRZ4: JZ ERRV1
276 CMP BYTE PTR [AWORD],4
277 JNZ ASMEX4
278 OR BYTE PTR [DI+2],1000B
279 JMP SHORT ASMEX4
280;
281; DIRECT JUMPS OR CALLS
282;
283CALLJ2: MOV AX,[LOWNUM]
284 MOV DX,[HINUM]
285 MOV BL,[AWORD]
286 CMP BYTE PTR [NUMFLG],0
287 JZ ERRZ4
288
289; BL = NUMBER OF BYTES IN JUMP
290; DX = OFFSET
291; AX = SEGMENT
292
293CALLJ3:
294 MOV BYTE PTR [DI],5
295 MOV [DI+2],AX
296 MOV [DI+4],DX
297
298 MOV AL,10011010B ; SET UP INTER SEGMENT CALL
299 CMP BYTE PTR [TSTFLG],0
300 JZ CALLJ5
301 MOV AL,11101010B ; FIX UP FOR JUMP
302CALLJ5: MOV BYTE PTR [DI+1],AL
303 CMP BL,4 ; FAR SPECIFIED?
304 JZ ASMEX4
305 OR BL,BL
306 JNZ CALLJ6
307 CMP DX,WORD PTR [ASMADD+2] ; DIFFERENT SEGMENT?
308 JNZ ASMEX4
309
310CALLJ6: MOV BYTE PTR [DI],3
311 MOV AL,11101000B ; SET UP FOR INTRASEGMENT
312 OR AL,[TSTFLG]
313 MOV BYTE PTR [DI+1],AL
314
315 MOV AX,[LOWNUM]
316 SUB AX,WORD PTR [ASMADD]
317 SUB AX,3
318 MOV [DI+2],AX
319 CMP BYTE PTR [TSTFLG],0
320 JZ ASMEX4
321 CMP BL,2
322 JZ ASMEX4
323
324 INC AX
325 MOV CX,AX
326 CBW
327 CMP AX,CX
328 JNZ ASMEX3
329 MOV BYTE PTR [DI+1],11101011B
330 MOV [DI+2],AX
331 DEC BYTE PTR [DI]
332ASMEX4: JMP ASSEM_EXIT
333;
334; conditional jumps and loop instructions
335;
336DISP8_OPER:
337 MOV BP,WORD PTR [ASMADD+2] ; GET DEFAULT DISPLACEMENT
338 CALL GET_ADDRESS
339 SUB DX,WORD PTR [ASMADD]
340 DEC DX
341 DEC DX
342 CALL CHKSIZ
343 CMP CL,1
344 JNZ ERRV2
345DISPX: INC [ASSEM_CNT]
346 MOV BYTE PTR [ASSEM2],AL
347ASMEX3: JMP ASSEM_EXIT
348;
349; lds, les, and lea instructions
350;
351L_OPER:
352 CALL SCANB
353 LODSW
354 MOV CX,8
355 MOV DI,OFFSET DG:REG16
356 CALL CHKREG
357 JZ ERRV2 ; CX = 0 MEANS NO REGISTER
358 SHL AL,1
359 SHL AL,1
360 SHL AL,1
361 MOV BYTE PTR [MIDFLD],AL
362 CALL SCANP
363 CALL GETREGMEM
364 CMP BYTE PTR [AWORD],0
365 JNZ ERRV2
366 CALL BUILD2
367 JMP SHORT ASEXV
368;
369; dec and inc instructions
370;
371DCINC_OPER:
372 MOV BYTE PTR [ASSEM1],11111110B
373 MOV BYTE PTR [MIDFLD],AL
374 CALL GETREGMEM
375 CALL BUILDIT
376 TEST BYTE PTR [DI+1],1
377 JZ ASEXV
378 MOV AL,[DI+2]
379 CMP AL,11000000B
380 JB ASEXV
381 AND AL,1111B
382 OR AL,01000000B
383 MOV [DI+1],AL
384 DEC BYTE PTR [DI]
385ASEXV: JMP ASSEM_EXIT
386
387ERRV2: JMP ASMERR
388;
389; esc instruction
390;
391ESC_OPER:
392 INC BYTE PTR [AWORD]
393 CALL SCANB
394 MOV CX,2
395 CALL GETHX
396 CMP DX,64
397 JAE ERRV2
398 CALL SCANP
399 MOV AX,DX
400 MOV CL,3
401 SHR DX,CL
402 OR [ASSEM1],DL
403 AND AL,111B
404 SHL AL,CL
405 JMP GROUPE
406;
407; 8087 arithmetic instuctions
408;
409
410;
411; OPERANDS THAT ALLOW THE REVERSE BIT
412;
413FGROUPDS:
414 CALL SETMID
415 CALL GETREGMEM2
416 CALL BUILD3
417 CMP BYTE PTR [MODE],11000000B
418 JNZ FGROUP1
419 MOV AL,[DIRFLG]
420 OR AL,AL
421 JZ FEXIT
422 OR [DI+1],AL ; IF D=1...
423 XOR BYTE PTR [DI+2],00001000B ; ...REVERSE THE SENSE OF R
424 JMP SHORT FEXIT
425
426;
427; Here when instruction could have memory or register operand
428;
429FGROUPX:
430 CALL SETMID ; THIS ENTRY POINT FOR 1 MEM OPER
431 MOV BYTE PTR [DIRFLG],0
432 JMP SHORT FGRP2
433FGROUP:
434 CALL SETMID
435FGRP2:
436 CALL GETREGMEM2
437 CALL BUILD3
438 CMP BYTE PTR [MODE],11000000B
439 JNZ FGROUP1
440 MOV AL,[DIRFLG]
441 OR [DI+1],AL
442 JMP SHORT FEXIT
443FGROUP1:CALL SETMF
444FEXIT: JMP ASSEM_EXIT
445;
446; These 8087 instructions require a memory operand
447;
448FGROUPB:
449 MOV AH,5 ; MUST BE TBYTE
450 JMP SHORT FGROUP3E
451FGROUP3W:
452 MOV AH,2 ; MUST BE WORD
453 JMP SHORT FGROUP3E
454FGROUP3:
455 MOV AH,-1 ; SIZE CANNOT BE SPECIFIED
456FGROUP3E:
457 MOV [AWORD],AH
458 CALL SETMID
459 CALL GETREGMEM
460 CMP BYTE PTR [MODE],11000000B
461 JZ FGRPERR
462FGRP:
463 CALL BUILD3
464 JMP FEXIT
465;
466; These 8087 instructions require a register operand
467;
468FGROUPP: ; 8087 POP OPERANDS
469 MOV BYTE PTR [AWORD],-1
470 CALL SETMID
471 CALL GETREGMEM2
472 CMP BYTE PTR [DIRFLG],0
473 JNZ FGRP
474FGRPERR:JMP ASMERR
475
476FGROUPZ: ; ENTRY POINT WHERE ARG MUST BE MEM
477 CALL SETMID
478 MOV BYTE PTR [DIRFLG],0
479 CALL GETREGMEM
480 CMP BYTE PTR [MODE],11000000B
481 JZ FGRPERR
482 CALL BUILD3
483 CALL SETMF
484 JMP FEXIT
485;
486; not, neg, mul, imul, div, and idiv instructions
487;
488GROUP1:
489 MOV [ASSEM1],11110110B
490GROUPE:
491 MOV BYTE PTR [MIDFLD],AL
492 CALL GETREGMEM
493 CALL BUILDIT
494 JMP FEXIT
495;
496; shift and rotate instructions
497;
498ROTOP:
499 MOV [ASSEM1],11010000B
500 MOV BYTE PTR [MIDFLD],AL
501 CALL GETREGMEM
502 CALL BUILDIT
503 CALL SCANP
504 CMP BYTE PTR [SI],"1"
505 JZ ASMEXV1
506 CMP WORD PTR [SI],"LC" ; CL
507 JZ ROTOP1
508ROTERR: JMP ASMERR
509ROTOP1: OR BYTE PTR [ASSEM1],10B
510ASMEXV1:JMP ASSEM_EXIT
511;
512; xchg instruction
513;
514EX_OPER:
515 INC BYTE PTR [TSTFLG]
516;
517; test instruction
518;
519TST_OPER:
520 INC BYTE PTR [TSTFLG]
521 JMP SHORT MOVOP
522;
523; mov instruction
524;
525MOV_OPER:
526 INC BYTE PTR [MOVFLG]
527MOVOP: XOR AX,AX
528 JMP SHORT GROUPM
529;
530; add, adc, sub, sbb, cmp, and, or, xor instructions
531;
532GROUP2:
533 MOV BYTE PTR [ASSEM1],10000000B
534GROUPM:
535 MOV BYTE PTR [MIDFLD],AL
536
537 PUSH AX
538 CALL GETREGMEM
539 CALL BUILD2
540 CALL SCANP ; POINT TO NEXT OPERAND
541 MOV AL,BYTE PTR [ASSEM_CNT]
542 PUSH AX
543 CALL GETREGMEM
544 POP AX
545 MOV BYTE PTR [DI],AL
546 POP AX
547 MOV BL,BYTE PTR [AWORD]
548 OR BL,BL
549 JZ ERRV5
550 DEC BL
551 AND BL,1
552 OR BYTE PTR [DI+1],BL
553
554 CMP BYTE PTR [MEMFLG],0
555 JNZ G21V
556 CMP BYTE PTR [NUMFLG],0 ; TEST FOR IMMEDIATE DATA
557 JZ G21V
558 CMP BYTE PTR [SEGFLG],0
559 JNZ ERRV5
560 CMP BYTE PTR [TSTFLG],2 ; XCHG?
561 JNZ IMMED1
562ERRV5: JMP ASMERR
563G21V: JMP GRP21
564;
565; SECOND OPERAND WAS IMMEDIATE
566;
567IMMED1: MOV AL,BYTE PTR [DI+2]
568 CMP BYTE PTR [MOVFLG],0
569 JZ NOTMOV1
570 AND AL,11000000B
571 CMP AL,11000000B
572 JNZ GRP23 ; not to a register
573 ; MOVE IMMEDIATE TO REGISTER
574 MOV AL,BYTE PTR [DI+1]
575 AND AL,1 ; SET SIZE
576 PUSHF
577 SHL AL,1
578 SHL AL,1
579 SHL AL,1
580 OR AL,BYTE PTR [DI+2] ; SET REGISTER
581 AND AL,00001111B
582 OR AL,10110000B
583 MOV BYTE PTR [DI+1],AL
584 MOV AX,WORD PTR [LOWNUM]
585 MOV WORD PTR [DI+2],AX
586 POPF
587 JZ EXVEC
588 INC BYTE PTR [DI]
589EXVEC: JMP GRPEX
590
591NOTMOV1:AND AL,11000111B
592 CMP AL,11000000B
593 JZ IMMACC ; IMMEDIATE TO ACC
594
595 CMP BYTE PTR [TSTFLG],0
596 JNZ GRP23
597 CMP BYTE PTR [MIDFLD],1*8 ; OR?
598 JZ GRP23
599 CMP BYTE PTR [MIDFLD],4*8 ; AND?
600 JZ GRP23
601 CMP BYTE PTR [MIDFLD],6*8 ; XOR?
602 JZ GRP23
603 TEST BYTE PTR [DI+1],1 ; TEST IF BYTE OPCODE
604 JZ GRP23
605
606 MOV AX,[LOWNUM]
607 MOV BX,AX
608 CBW
609 CMP AX,BX
610 JNZ GRP23 ; SMALL ENOUGH?
611
612 MOV BL,[DI]
613 DEC BYTE PTR [DI]
614 OR BYTE PTR [DI+1],10B
615 JMP SHORT GRP23X
616
617IMMACC: MOV AL,BYTE PTR [DI+1]
618 AND AL,1
619 CMP BYTE PTR [TSTFLG],0
620 JZ NOTTST
621 OR AL,10101000B
622 JMP SHORT TEST1
623NOTTST: OR AL,BYTE PTR [MIDFLD]
624 OR AL,100B
625TEST1: MOV BYTE PTR [DI+1],AL
626 DEC BYTE PTR [DI]
627
628GRP23: MOV BL,BYTE PTR [DI]
629GRP23X: XOR BH,BH
630 ADD BX,DI
631 INC BX
632 MOV AX,WORD PTR [LOWNUM]
633 MOV WORD PTR [BX],AX
634 INC BYTE PTR [DI]
635 TEST BYTE PTR [DI+1],1
636 JZ GRPEX1
637 INC BYTE PTR [DI]
638GRPEX1: JMP GRPEX
639;
640; SECOND OPERAND WAS MEMORY OR REGISTER
641;
642GRP21:
643 CMP BYTE PTR [SEGFLG],0
644 JZ GRP28 ; FIRST OPERAND WAS A SEGMENT REG
645 MOV AL,BYTE PTR [REGMEM]
646 TEST AL,10000B
647 JZ NOTSEG1
648ERRV3: JMP ASMERR
649NOTSEG1:AND AL,111B
650 OR BYTE PTR [DI+2],AL
651 AND BYTE PTR [DI+1],11111110B
652 CMP BYTE PTR [MEMFLG],0
653 JNZ G22V
654 JMP GRPEX
655
656GRP28: AND BYTE PTR [DI+2],11000111B
657 MOV AL,BYTE PTR [DI+1] ; GET FIRST OPCODE
658 AND AL,1B
659 CMP BYTE PTR [MOVFLG],0
660 JZ NOTMOV2
661 OR AL,10001000B
662 JMP SHORT MOV1
663NOTMOV2:CMP BYTE PTR [TSTFLG],0
664 JZ NOTTST2
665 OR AL,10000100B
666 CMP BYTE PTR [TSTFLG],2
667 JNZ NOTTST2
668 OR AL,10B
669NOTTST2:OR AL,BYTE PTR [MIDFLD] ; MIDFLD IS ZERO FOR TST
670MOV1: MOV BYTE PTR [DI+1],AL
671 CMP BYTE PTR [MEMFLG],0
672G22V: JNZ GRP22
673;
674; SECOND OPERAND WAS A REGISTER
675;
676 MOV AL,BYTE PTR [REGMEM]
677 TEST AL,10000B ; SEGMENT REGISTER?
678 JZ NOTSEG
679 CMP BYTE PTR [MOVFLG],0
680 JZ ERRV3
681 MOV BYTE PTR [DI+1],10001100B
682
683NOTSEG: AND AL,111B
684 SHL AL,1
685 SHL AL,1
686 SHL AL,1
687 OR BYTE PTR [DI+2],AL
688;
689; SPECIAL FORM OF THE EXCHANGE COMMAND
690;
691 CMP BYTE PTR [TSTFLG],2
692 JNZ GRPEX
693 TEST BYTE PTR [DI+1],1
694 JZ GRPEX
695 PUSH AX
696 MOV AL,BYTE PTR [DI+2]
697 AND AL,11000000B
698 CMP AL,11000000B ; MUST BE REGISTER TO REGISTER
699 POP AX
700 JB GRPEX
701 OR AL,AL
702 JZ SPECX
703 MOV AL,[DI+2]
704 AND AL,00000111B
705 JNZ GRPEX
706 MOV CL,3
707 SHR BYTE PTR [DI+2],CL
708SPECX: MOV AL,[DI+2]
709 AND AL,00000111B
710 OR AL,10010000B
711 MOV BYTE PTR [DI+1],AL
712 DEC BYTE PTR [DI]
713 JMP SHORT GRPEX
714;
715; SECOND OPERAND WAS A MEMORY REFERENCE
716;
717GRP22: CMP BYTE PTR [TSTFLG],0
718 JNZ TST2
719 OR BYTE PTR [DI+1],10B
720TST2: MOV AL,BYTE PTR [DI+2]
721 CMP AL,11000000B ; MUST BE A REGISTER
722 JB ASMERR
723 CMP BYTE PTR [SEGFLG],0
724 JZ GRP223
725 AND AL,00011000B
726 JMP SHORT GRP222
727GRP223: AND AL,111B
728 SHL AL,1
729 SHL AL,1
730 SHL AL,1
731GRP222: OR AL,BYTE PTR [MODE]
732 OR AL,BYTE PTR [REGMEM]
733 MOV BYTE PTR [DI+2],AL
734 MOV AX,WORD PTR [LOWNUM]
735 MOV WORD PTR [DI+3],AX
736GRPSIZ: MOV BYTE PTR [DI],2
737 MOV AL,BYTE PTR [DI+2]
738 AND AL,11000111B
739 CMP AL,00000110B
740 JZ GRP24
741 AND AL,11000000B
742 CMP AL,01000000B
743 JZ GRP25
744 CMP AL,10000000B
745 JNZ GRPEX
746GRP24: INC BYTE PTR [DI]
747GRP25: INC BYTE PTR [DI]
748
749GRPEX: CMP BYTE PTR [MOVFLG],0
750 JZ ASSEM_EXIT
751;
752; TEST FOR SPECIAL FORM OF MOV AX,[MEM] OR MOV [MEM],AX
753;
754 MOV AL,[DI+1] ; GET OP-CODE
755 AND AL,11111100B
756 CMP AL,10001000B
757 JNZ ASSEM_EXIT
758 CMP BYTE PTR [DI+2],00000110B ; MEM TO AX OR AX TO MEM
759 JNZ ASSEM_EXIT
760 MOV AL,BYTE PTR [DI+1]
761 AND AL,11B
762 XOR AL,10B
763 OR AL,10100000B
764 MOV BYTE PTR [DI+1],AL
765 DEC BYTE PTR [DI]
766 MOV AX,[DI+3]
767 MOV WORD PTR [DI+2],AX
768
769ASSEM_EXIT:
770 CALL STUFF_BYTES
771 JMP ASSEMLOOP
772
773; Assem error. SI points to character in the input buffer
774; which caused error. By subtracting from start of buffer,
775; we will know how far to tab over to appear directly below
776; it on the terminal. Then print "^ Error".
777
778ASMERR:
779 SUB SI,OFFSET DG:(BYTEBUF-10) ; How many char processed so far?
780 MOV CX,SI ; Parameter for TAB in CX
781 CALL TAB ; Directly below bad char
782 MOV SI,OFFSET DG:SYNERR ; Error message
783 CALL PRINTMES
784 JMP ASSEMLOOP
785;
786; assemble the different parts into an instruction
787;
788BUILDIT:
789 MOV AL,BYTE PTR [AWORD]
790 OR AL,AL
791 JNZ BUILD1
792BLDERR: JMP ASMERR
793
794BUILD1: DEC AL
795 OR BYTE PTR [DI+1],AL ; SET THE SIZE
796
797BUILD2: CMP BYTE PTR [NUMFLG],0 ; TEST FOR IMMEDIATE DATA
798 JZ BUILD3
799 CMP BYTE PTR [MEMFLG],0
800 JZ BLDERR
801
802BUILD3: MOV AL,BYTE PTR [REGMEM]
803 CMP AL,-1
804 JZ BLD1
805 TEST AL,10000B ; TEST IF SEGMENT REGISTER
806 JZ BLD1
807 CMP BYTE PTR [MOVFLG],0
808 JZ BLDERR
809 MOV WORD PTR [DI+1],10001110B
810 INC BYTE PTR [MOVFLG]
811 INC BYTE PTR [SEGFLG]
812 AND AL,00000011B
813 SHL AL,1
814 SHL AL,1
815 SHL AL,1
816 OR AL,BYTE PTR 11000000B
817 MOV BYTE PTR [DI+2],AL
818 RET
819
820BLD1: AND AL,00000111B
821BLD4: OR AL,BYTE PTR [MODE]
822 OR AL,BYTE PTR [MIDFLD]
823 MOV BYTE PTR [DI+2],AL
824 MOV AX,WORD PTR [LOWNUM]
825 MOV WORD PTR [DI+3],AX
826 RET
827
828GETREGMEM:
829 MOV BYTE PTR [F8087],0
830GETREGMEM2:
831 CALL SCANP
832 XOR AX,AX
833 MOV WORD PTR [LOWNUM],AX ; OFFSET
834 MOV WORD PTR [DIFLG],AX ; DIFLG+SIFLG
835 MOV WORD PTR [BXFLG],AX ; BXFLG+BPFLG
836 MOV WORD PTR [NEGFLG],AX ; NEGFLG+NUMFLG
837 MOV WORD PTR [MEMFLG],AX ; MEMFLG+REGFLG
838 DEC AL
839 CMP BYTE PTR [F8087],0
840 JZ PUTREG
841 MOV AL,1 ; DEFAULT 8087 REG IS 1
842PUTREG: MOV BYTE PTR [REGMEM],AL
843
844GETLOOP:MOV BYTE PTR [NEGFLG],0
845GETLOOP1:
846 MOV AX,WORD PTR [SI]
847 CMP AL,','
848 JZ GOMODE
849 CMP AL,13
850 JZ GOMODE
851 CMP AL,';'
852 JZ GOMODE
853 CMP AL,9
854 JZ GETTB
855 CMP AL,' '
856 JNZ GOGET
857GETTB: INC SI
858 JMP GETLOOP1
859GOGET: JMP GETINFO
860;
861; DETERMINE THE MODE BITS
862;
863GOMODE: MOV DI,OFFSET DG:ASSEM_CNT
864 MOV BYTE PTR [MODE],11000000B
865 MOV BYTE PTR [ASSEM_CNT],2
866 CMP BYTE PTR [MEMFLG],0
867 JNZ GOMODE1
868 MOV AL,[NUMFLG]
869 OR AL,[REGFLG]
870 JNZ MORET
871 OR AL,[F8087]
872 JZ ERRET
873 MOV AL,[DI+1]
874 OR AL,[DIRFLG]
875 CMP AL,0DCH ; ARITHMETIC?
876 JNZ MORET
877 MOV BYTE PTR [DI+1],0DEH ; ADD POP TO NULL ARG 8087
878MORET: RET
879ERRET: JMP ASMERR
880
881GOMODE1:MOV BYTE PTR [MODE],0
882 CMP BYTE PTR [NUMFLG],0
883 JZ GOREGMEM
884
885 MOV BYTE PTR [DI],4
886 MOV AX,WORD PTR [DIFLG]
887 OR AX,WORD PTR [BXFLG]
888 JNZ GOMODE2
889 MOV BYTE PTR [REGMEM],00000110B
890 RET
891
892GOMODE2:MOV BYTE PTR [MODE],10000000B
893 CALL CHKSIZ1
894 CMP CL,2
895 JZ GOREGMEM
896 DEC BYTE PTR [DI]
897 MOV BYTE PTR [MODE],01000000B
898;
899; DETERMINE THE REG-MEM BITS
900;
901GOREGMEM:
902 MOV BX,WORD PTR [BXFLG]
903 MOV CX,WORD PTR [DIFLG]
904 XOR DX,DX
905GOREG0:
906 MOV AL,BL ; BX
907 ADD AL,CH ; SI
908 CMP AL,2
909 JZ GOGO
910 INC DL
911 MOV AL,BL
912 ADD AL,CL
913 CMP AL,2
914 JZ GOGO
915 INC DL
916 MOV AL,BH
917 ADD AL,CH
918 CMP AL,2
919 JZ GOGO
920 INC DL
921 MOV AL,BH
922 ADD AL,CL
923 CMP AL,2
924 JZ GOGO
925 INC DL
926 OR CH,CH
927 JNZ GOGO
928 INC DL
929 OR CL,CL
930 JNZ GOGO
931 INC DL ; BP+DISP
932 OR BH,BH
933 JZ GOREG1
934 CMP BYTE PTR [MODE],0
935 JNZ GOGO
936 MOV BYTE PTR [MODE],01000000B
937 INC BYTE PTR [DI]
938 DEC DL
939GOREG1: INC DL ; BX+DISP
940GOGO: MOV BYTE PTR [REGMEM],DL
941 RET
942
943GETINFO:CMP AX,'EN' ; NEAR
944 JNZ GETREG3
945GETREG0:MOV DL,2
946GETRG01:CALL SETSIZ1
947GETREG1:CALL SCANS
948 MOV AX,WORD PTR [SI]
949 CMP AX,"TP" ; PTR
950 JZ GETREG1
951 JMP GETLOOP
952
953GETREG3:MOV CX,5
954 MOV DI,OFFSET DG:SIZ8
955 CALL CHKREG ; LOOK FOR BYTE, WORD, DWORD, ETC.
956 JZ GETREG41
957 INC AL
958 MOV DL,AL
959 JMP GETRG01
960
961GETREG41:
962 MOV AX,[SI]
963 CMP BYTE PTR [F8087],0
964 JZ GETREG5
965 CMP AX,"TS" ; 8087 STACK OPERAND
966 JNZ GETREG5
967 CMP BYTE PTR [SI+2],","
968 JNZ GETREG5
969 MOV BYTE PTR [DIRFLG],0
970 ADD SI,3
971 JMP GETLOOP
972
973GETREG5:CMP AX,"HS" ; SHORT
974 JZ GETREG1
975
976 CMP AX,"AF" ; FAR
977 JNZ GETRG51
978 CMP BYTE PTR [SI+2],"R"
979 JNZ GETRG51
980 ADD SI,3
981 MOV DL,4
982 JMP GETRG01
983
984GETRG51:CMP AL,'['
985 JNZ GETREG7
986GETREG6:INC BYTE PTR [MEMFLG]
987 INC SI
988 JMP GETLOOP
989
990GETREG7:CMP AL,']'
991 JZ GETREG6
992 CMP AL,'.'
993 JZ GETREG6
994 CMP AL,'+'
995 JZ GETREG6
996 CMP AL,'-'
997 JNZ GETREG8
998 INC BYTE PTR [NEGFLG]
999 INC SI
1000 JMP GETLOOP1
1001
1002GETREG8: ; LOOK FOR A REGISTER
1003 CMP BYTE PTR [F8087],0
1004 JZ GETREGREG
1005 CMP AX,"TS"
1006 JNZ GETREGREG
1007 CMP BYTE PTR [SI+2],"("
1008 JNZ GETREGREG
1009 CMP BYTE PTR [SI+4],")"
1010 JNZ ASMPOP
1011 MOV AL,[SI+3]
1012 SUB AL,"0"
1013 JB ASMPOP
1014 CMP AL,7
1015 JA ASMPOP
1016 MOV [REGMEM],AL
1017 INC BYTE PTR [REGFLG]
1018 ADD SI,5
1019 CMP WORD PTR [SI],"S,"
1020 JNZ ZLOOP
1021 CMP BYTE PTR [SI+2],"T"
1022 JNZ ZLOOP
1023 ADD SI,3
1024ZLOOP: JMP GETLOOP
1025
1026GETREGREG:
1027 MOV CX,20
1028 MOV DI,OFFSET DG:REG8
1029 CALL CHKREG
1030 JZ GETREG12 ; CX = 0 MEANS NO REGISTER
1031 MOV BYTE PTR [REGMEM],AL
1032 INC BYTE PTR [REGFLG] ; TELL EVERYONE WE FOUND A REG
1033 CMP BYTE PTR [MEMFLG],0
1034 JNZ NOSIZE
1035 CALL SETSIZ
1036INCSI2: ADD SI,2
1037 JMP GETLOOP
1038
1039NOSIZE: CMP AL,11 ; BX REGISTER?
1040 JNZ GETREG9
1041 CMP WORD PTR [BXFLG],0
1042 JZ GETOK
1043ASMPOP: JMP ASMERR
1044
1045GETOK: INC BYTE PTR [BXFLG]
1046 JMP INCSI2
1047GETREG9:
1048 CMP AL,13 ; BP REGISTER?
1049 JNZ GETREG10
1050 CMP WORD PTR [BXFLG],0
1051 JNZ ASMPOP
1052 INC BYTE PTR [BPFLG]
1053 JMP INCSI2
1054GETREG10:
1055 CMP AL,14 ; SI REGISTER?
1056 JNZ GETREG11
1057 CMP WORD PTR [DIFLG],0
1058 JNZ ASMPOP
1059 INC BYTE PTR [SIFLG]
1060 JMP INCSI2
1061GETREG11:
1062 CMP AL,15 ; DI REGISTER?
1063 JNZ ASMPOP ; *** error
1064 CMP WORD PTR [DIFLG],0
1065 JNZ ASMPOP
1066 INC BYTE PTR [DIFLG]
1067 JMP INCSI2
1068
1069GETREG12: ; BETTER BE A NUMBER!
1070 MOV BP,WORD PTR [ASMADD+2]
1071 CMP BYTE PTR [MEMFLG],0
1072 JZ GTRG121
1073GTRG119:MOV CX,4
1074GTRG120:CALL GETHX
1075 JMP SHORT GTRG122
1076GTRG121:MOV CX,2
1077 CMP BYTE PTR [AWORD],1
1078 JZ GTRG120
1079 CMP BYTE PTR [AWORD],CL
1080 JZ GTRG119
1081 CALL GET_ADDRESS
1082GTRG122:JC ASMPOP
1083 MOV [HINUM],AX
1084 CMP BYTE PTR [NEGFLG],0
1085 JZ GETREG13
1086 NEG DX
1087GETREG13:
1088 ADD WORD PTR [LOWNUM],DX
1089 INC BYTE PTR [NUMFLG]
1090GETLOOPV:
1091 JMP GETLOOP
1092
1093CHKREG: PUSH CX
1094 INC CX
1095 REPNZ SCASW
1096 POP AX
1097 SUB AX,CX
1098 OR CX,CX
1099 RET
1100
1101STUFF_BYTES:
1102 PUSH SI
1103 LES DI,DWORD PTR ASMADD
1104 MOV SI,OFFSET DG:ASSEM_CNT
1105 XOR AX,AX
1106 LODSB
1107 MOV CX,AX
1108 JCXZ STUFFRET
1109 REP MOVSB
1110 MOV WORD PTR [ASMADD],DI
1111STUFFRET:
1112 POP SI
1113 RET
1114
1115SETSIZ:
1116 MOV DL,1
1117 TEST AL,11000B ; 16 BIT OR SEGMENT REGISTER?
1118 JZ SETSIZ1
1119 INC DL
1120SETSIZ1:
1121 CMP BYTE PTR [AWORD],0
1122 JZ SETSIZ2
1123 CMP BYTE PTR [AWORD],DL
1124 JZ SETSIZ2
1125SETERR: POP DX
1126 JMP ASMPOP
1127SETSIZ2:MOV BYTE PTR [AWORD],DL
1128 RET
1129;
1130; DETERMINE IF NUMBER IN AX:DX IS 8 BITS, 16 BITS, OR 32 BITS
1131;
1132CHKSIZ: MOV CL,4
1133 CMP AX,BP
1134 JNZ RETCHK
1135CHKSIZ1:MOV CL,2
1136 MOV AX,DX
1137 CBW
1138 CMP AX,DX
1139 JNZ RETCHK
1140 DEC CL
1141RETCHK: RET
1142;
1143; get first character after first space
1144;
1145SCANS: CMP BYTE PTR [SI],13
1146 JZ RETCHK
1147 CMP BYTE PTR [SI],"["
1148 JZ RETCHK
1149 LODSB
1150 CMP AL," "
1151 JZ SCANBV
1152 CMP AL,9
1153 JNZ SCANS
1154SCANBV: JMP SCANB
1155;
1156; Set up for 8087 op-codes
1157;
1158SETMID:
1159 MOV BYTE PTR [ASSEM1],0D8H
1160 MOV AH,AL
1161 AND AL,111B ; SET MIDDLE BITS OF SECOND BYTE
1162 SHL AL,1
1163 SHL AL,1
1164 SHL AL,1
1165 MOV [MIDFLD],AL
1166 MOV AL,AH ; SET LOWER BITS OF FIRST BYTE
1167 SHR AL,1
1168 SHR AL,1
1169 SHR AL,1
1170 OR [ASSEM1],AL
1171 MOV BYTE PTR [F8087],1 ; INDICATE 8087 OPERAND
1172 MOV BYTE PTR [DIRFLG],100B
1173 RET
1174;
1175; Set MF bits for 8087 op-codes
1176;
1177SETMF: MOV AL,[AWORD]
1178 TEST BYTE PTR [DI+1],10B
1179 JNZ SETMFI
1180 AND BYTE PTR [DI+1],11111001B ; CLEAR MF BITS
1181 CMP AL,3 ; DWORD?
1182 JZ SETMFRET
1183 CMP AL,4 ; QWORD?
1184 JZ SETMFRET2
1185 TEST BYTE PTR [DI+1],1
1186 JZ SETMFERR
1187 CMP AL,5 ; TBYTE?
1188 JZ SETMFRET3
1189 JMP SHORT SETMFERR
1190
1191SETMFI: CMP AL,3 ; DWORD?
1192 JZ SETMFRET
1193 CMP AL,2 ; WORD?
1194 JZ SETMFRET2
1195 TEST BYTE PTR [DI+1],1
1196 JZ SETMFERR
1197 CMP AL,4 ; QWORD?
1198 JNZ SETMFERR
1199 OR BYTE PTR [DI+1],111B
1200SETMFRET3:
1201 OR BYTE PTR [DI+1],011B
1202 OR BYTE PTR [DI+2],101000B
1203 JMP SHORT SETMFRET
1204SETMFRET2:
1205 OR BYTE PTR [DI+1],100B
1206SETMFRET:
1207 RET
1208
1209SETMFERR:
1210 JMP ASMPOP
1211
1212
1213DW_OPER:
1214 MOV BP,1
1215 JMP SHORT DBEN
1216
1217DB_OPER:
1218 XOR BP,BP
1219DBEN: MOV DI,OFFSET DG:ASSEM_CNT
1220 DEC BYTE PTR [DI]
1221 INC DI
1222DB0: XOR BL,BL
1223 CALL SCANP
1224 JNZ DB1
1225DBEX: JMP ASSEM_EXIT
1226DB1: OR BL,BL
1227 JNZ DB3
1228 MOV BH,BYTE PTR [SI]
1229 CMP BH,"'"
1230 JZ DB2
1231 CMP BH,'"'
1232 JNZ DB4
1233DB2: INC SI
1234 INC BL
1235DB3: LODSB
1236 CMP AL,13
1237 JZ DBEX
1238 CMP AL,BH
1239 JZ DB0
1240 STOSB
1241 INC BYTE PTR [ASSEM_CNT]
1242 JMP DB3
1243DB4: MOV CX,2
1244 CMP BP,0
1245 JZ DB41
1246 MOV CL,4
1247DB41: PUSH BX
1248 CALL GETHX
1249 POP BX
1250 JNC DB5
1251 JMP ASMERR
1252DB5: MOV AX,DX
1253 CMP BP,0
1254 JZ DB6
1255 STOSW
1256 INC BYTE PTR [ASSEM_CNT]
1257 JMP SHORT DB7
1258DB6: STOSB
1259DB7: INC BYTE PTR [ASSEM_CNT]
1260 JMP DB0
1261
1262CODE ENDS
1263 END ASSEM
1264