!!!Sweet 16 for Bibo Assembler
General Information
Author: Steve "Woz" Wozniak \\
Assembler: BiboAssembler \\
Published: 1977 \\
see also Original [Sweet 16]
* The ATARI uses the zero page registers at $E0-$FF instead of $00-$1F
* the "save" and "restore" routines are not in ROM, but in the source
Download:
{{{
00000 .LI OFF
00010 ***************************
00020 * *
00030 * APPLE II PSEUDO MACHINE *
00040 * INTERPRETER *
00050 * *
00060 * COPYRIGHT (C) 1977 *
00070 * APPLE COMPUTER INC. *
00080 * *
00090 * STEVE WOZNIAK *
00100 * *
00110 ***************************
00120 * TITLE: SWEET 16 INTERPRETER
00130 ;
00140 R0L = $E0
00150 R0H = $E1
00160 R14H = $FD
00170 R15L = $FE
00180 R15H = $FF
00190 ;
00200 .OR $7889
00210 ; .OF D:SWEET16.COM
00220 ;
00230 ; PRESERVE 6502 REG CONTENT
00240 ;
00250 SW16 JSR SAVE
00260 ;
00270 ; INIT SWEET16 PC
00280 ; FROM RETURN ADDRESS
00290 ;
00300 SW16A PLA
00310 STA R15L
00320 PLA
00330 STA R15H
00340 ;
00350 ; INTERPRET AND EXECUTE
00360 ; ONE SWEET16 INSTRUCTION
00370 ;
00380 SW16B JSR SW16C
00390 JMP SW16B
00400 ;
00410 ; INCREMENT SWEET16 PC
00420 ; FOR FETCH
00430 ;
00440 SW16C INC R15L
00450 BNE SW16D
00460 INC R15H
00470 ;
00480 ; COMMON HIG BZTE FOR ALL
00490 ; ROUTINES, PUSH ON STACK FOR
00500 ; RTS
00510 SW16D LDA /SET
00520 PHA
00530 ;
00540 ; FETCH INSTRUCTION
00550 ;
00560 LDY #$0
00570 LDA (R15L),Y
00580 ;
00590 ; MASK REGISTER SPECIFICATION
00600 ;
00610 AND #$F
00620 ;
00630 ; DOUBLE FOR TWO BYTE REGISTERS
00640 ;
00650 ASL
00660 ;
00670 ; TO X REGISTER FOR INDEXING
00680 ;
00690 TAX
00700 LSR
00710 ;
00720 ; NOW HAVE OPCODE
00730 ;
00740 EOR (R15L),Y
00750 ;
00760 ; IF ZERO THEN NO REG OPCODE
00770 ;
00780 BEQ TOBR
00790 ;
00800 ; INDICATE PRIOR RESULT REG
00810 ;
00820 STX R14H
00830 ;
00840 ; OPCODE * 2 TO LSB'S
00850 ;
00860 LSR
00870 LSR
00880 LSR
00890 ;
00900 ; TO Y REGISTER FOR INDEXING
00910 ;
00920 TAY
00930 ;
00940 ; LOW ORDER ADR BYTE ON STACK
00950 ;
00960 LDA OPTBL-2,Y
00970 PHA
00980 ;
00990 ; GOTO REG-OPCODE ROUTINE
01000 ;
01010 RTS
01020 ;
01030 ; INCREMENT PC
01040 ;
01050 TOBR INC R15L
01060 BNE TOBR2
01070 INC R15H
01080 ;
01090 ; LOW ORDER ADR BYTE ONTO
01100 ; STACK FOR NON-REG OPCODE
01110 ;
01120 TOBR2 LDA BRTBL,X
01130 PHA
01140 ;
01150 ; PRIOR RESULT REG INDEX
01160 ;
01170 LDA R14H
01180 ;
01190 ; PREPARE CARRY FOR BC. BNC.
01200 ;
01210 LSR
01220 ;
01230 ; GOTO NON-REG OPCODE ROUTINE
01240 ;
01250 RTS
01260 ;
01270 ; RETURN TO 6502 MODE ROUTINE
01280 ;
01290 ; POP RETURN ADDRESS
01300 ;
01310 RTNZ PLA
01320 PLA
01330 ;
01340 ; RESTORE 6502 REG CONTENT
01350 ;
01360 JSR RESTORE
01370 ;
01380 ; RETURN TO 6502 CODE VIA PC
01390 ;
01400 JMP (R15L)
01410 ;
01420 ; SET REGISTER ROUTINE
01430 ;
01440 ; GET HIGH BYTE OF CONSTANT
01450 ;
01460 SETZ LDA (R15L),Y
01470 STA R0H,X
01480 DEY
01490 ;
01500 ; GET LOW BYTE OF CONSTANT
01510 ;
01520 LDA (R15L),Y
01530 STA R0L,X
01540 ;
01550 ; Y REG CONTAINS 1
01560 ;
01570 TYA
01580 ;
01590 ; ADD 2 TO PC
01600 ;
01610 SEC
01620 ADC R15L
01630 STA R15L
01640 BCC SET2
01650 INC R15H
01660 SET2 RTS
01670 ;
01680 ; OPCODE TABLE
01690 ;
01700 OPTBL .DA #SET-1 ; 1X
01710 BRTBL .DA #RTN-1 ; 0
01720 .DA #LD-1 ; 2X
01730 .DA #BR-1 ; 1
01740 .DA #ST-1 ; 3X
01750 .DA #BNC-1 ; 2
01760 .DA #LDAT-1 ; 4X
01770 .DA #BC-1 ; 3
01780 .DA #STAT-1 ; 5X
01790 .DA #BP-1 ; 4
01800 .DA #LDDAT-1 ; 6X
01810 .DA #BM-1 ; 5
01820 .DA #STDAT-1 ; 7X
01830 .DA #BZ-1 ; 6
01840 .DA #POP-1 ; 8X
01850 .DA #BNZ-1 ; 7
01860 .DA #STPAT-1 ; 9X
01870 .DA #BM1-1 ; 8
01880 .DA #ADD-1 ; AX
01890 .DA #BNM1-1 ; 9
01900 .DA #SUB-1 ; BX
01910 .DA #BK-1 ; A
01920 .DA #POPD-1 ; CX
01930 .DA #RS-1 ; B
01940 .DA #CPR-1 ; DX
01950 .DA #BS-1 ; C
01960 .DA #INR-1 ; EX
01970 .DA #NUL-1 ; D
01980 .DA #DCR-1 ; FX
01990 .DA #NUL-1 ; E
02000 .DA #NUL-1 ; UNUSED
02010 .DA #NUL-1 ; F
02020 ;
02030 ; THE FOLLOWING CODE MUST
02040 ; BE CONTAINED IN A SINGLE PAGE
02050 ;
02060 SET JMP SETZ ; ALWAYS
02070 LD LDA R0L,X
02080 BK = LD+1
02090 STA R0L
02100 ;
02110 ; MOV RX TO R0
02120 ;
02130 LDA R0H,X
02140 STA R0H
02150 RTS
02160 ;
02170 ST LDA R0L
02180 ;
02190 ; MOV R0 TO RX
02200 ;
02210 STA R0L,X
02220 LDA R0H
02230 STA R0H,X
02240 RTS
02250 ;
02260 ; STORE BYTE INDEIRECT
02270 ;
02280 STAT LDA R0L
02290 STAT2 STA (R0L,X)
02300 LDY #$0
02310 ;
02320 ; INDICATE R0 IS RESULT NEG
02330 ;
02340 STAT3 STY R14H
02350 INR INC R0L,X
02360 BNE INR2 ; INC RX
02370 INC R0H,X
02380 INR2 RTS
02390 ;
02400 ; LOAD INDIRECT (RX) TO R0
02410 ;
02420 LDAT LDA (R0L,X)
02430 STA R0L
02440 ;
02450 ; ZERO HIGH ORDER R0 BYTE
02460 ;
02470 LDY #$0
02480 STY R0H
02490 BEQ STAT3 ; ALWAYS
02500 ;
02510 ; HIGH ORDER BYTE = 0
02520 ;
02530 POP LDY #$0
02540 BEQ POP2 ; ALWAYS
02550 POPD JSR DCR ; DECR RX
02560 ;
02570 ; POP HIGH ORDER BYTE @RX
02580 ; AND SAV IN Y REG
02590 ;
02600 LDA (R0L,X)
02610 TAY
02620 POP2 JSR DCR ; DECR RX
02630 ;
02640 ; LOW ORDER BYTE TO R0
02650 ;
02660 LDA (R0L,X)
02670 STA R0L
02680 STY R0H
02690 ;
02700 ; INDICATE R0 AS LAST RES. REG
02710 ;
02720 POP3 LDY #$0
02730 STY R14H
02740 RTS
02750 ;
02760 ; LOW ORDER BYTE TO R0, INC RX
02770 ;
02780 LDDAT JSR LDAT
02790 ;
02800 ; HIGH ORDER BYTE TO R0
02810 LDA (R0L,X)
02820 STA R0H
02830 JMP INR ; INC RX
02840 ;
02850 ; STORE INDIRECT LOW ORDER
02860 ; BYTE AND INC RX THEN
02870 ; STORE HIGH ORDER BYTE,
02880 ; INC RX AND RETURN
02890 ;
02900 STDAT JSR LDAT
02910 LDA R0H
02920 STA (R0L,X)
02930 JMP INR
02940 STPAT JSR DCR ; DEC RX
02950 LDA R0L
02960 ;
02970 ; STORE R0 LOW BYTE @RX
02980 ;
02990 STA (R0L,X)
03000 ;
03010 ; INDICATE R0 AS LAST RES REG
03020 ;
03030 JMP POP3
03040 ;
03050 DCR LDA R0L,X
03060 BNE DCR2 ; DEC RX
03070 DEC R0H,X
03080 DCR2 DEC R0L,X
03090 RTS
03100 ;
03110 ; RESULT TO R0
03120 ;
03130 SUB LDY #$0
03140 ;
03150 ; NOTE Y REG = 13 * 2 FOR CPR
03160 ;
03170 CPR SEC
03180 LDA R0L
03190 SBC R0L,X
03200 STA R0L,Y ; RY=R0-RX
03210 LDA R0H
03220 SBC R0H,X
03230 SUB2 STA R0H,Y
03240 ;
03250 ; LAST RESULT REG * 2
03260 ;
03270 TYA
03280 ;
03290 ; CARRY TO LSB
03300 ;
03310 ADC #$0
03320 STA R14H
03330 RTS
03340 ;
03350 ADD LDA R0L
03360 ADC R0L,X
03370 STA R0L ; R0=RX+R0
03380 LDA R0H
03390 ADC R0H,X
03400 ;
03410 ; R0 FOR RESULT
03420 ;
03430 LDY #$0
03440 ; FINISH ADD
03450 BEQ SUB2
03460 ;
03470 ; NOTE X REG IS 12 * 2 !
03480 ;
03490 BS LDA R15L
03500 ;
03510 ; PUSH LOW PC BYTE VIA R12
03520 ;
03530 JSR STAT2
03540 LDA R15H
03550 ;
03560 ; PUSH HIGH PC BYTE
03570 ;
03580 JSR STAT2
03590 BR CLC
03600 BNC BCS BNC2 ; NO CARRY TEST
03610 ;
03620 ; DISPLACEMENT BYTE
03630 ;
03640 BR1 LDA (R15L),Y
03650 BPL BR2
03660 DEY
03670 ;
03680 ; ADD TO PC
03690 ;
03700 BR2 ADC R15L
03710 STA R15L
03720 TYA
03730 ADC R15H
03740 STA R15H
03750 BNC2 RTS
03760 BC BCS BR
03770 RTS
03780 ;
03790 ; DOUBLE RESULT REG INDEX
03800 ;
03810 BP ASL
03820 ;
03830 ; TO X REG FOR INDEX
03840 ;
03850 TAX
03860 ; TEST FOR PLUS, BRANCH IF SO
03870 ;
03880 LDA R0H,X
03890 BPL BR1
03900 RTS
03910 ;
03920 ; DOUBLE RESULT REG INDEX
03930 ;
03940 BM ASL
03950 TAX
03960 ;
03970 ; TEST FOR MINUS
03980 ;
03990 LDA R0H,X
04000 BMI BR1
04010 RTS
04020 ;
04030 ; DOUBLE RESULT REG INDEX
04040 ;
04050 BZ ASL
04060 TAX
04070 ;
04080 ; TEST FOR ZERO (BOTH BYTES)
04090 ;
04100 LDA R0L,X
04110 ORA R0H,X
04120 BEQ BR1
04130 RTS
04140 ;
04150 ; DOUBLE RESULT REG INDEX
04160 ;
04170 BNZ ASL
04180 TAX
04190 ;
04200 ; TEST FOR NON-ZERO (BOTH)
04210 ;
04220 LDA R0L,X
04230 ORA R0H,X
04240 BNE BR1
04250 RTS
04260 ;
04270 ; DOUBLE RESULT REG INDEX
04280 ;
04290 BM1 ASL
04300 TAX
04310 ;
04320 ; TEST FOR $FF (-1) BOTH BYTES
04330 ;
04340 LDA R0L,X
04350 AND R0H,X
04360 EOR #$FF
04370 BEQ BR1
04380 RTS
04390 ;
04400 ; DOUBLE RESULT REG
04410 ;
04420 BNM1 ASL
04430 TAX
04440 ;
04450 ; TEST FOR NO $FF
04460 ;
04470 LDA R0L,X
04480 AND R0H,X
04490 EOR #$FF
04500 BNE BR1
04510 NUL RTS
04520 ; 12*2 FOR R12 AS STACK POINTER
04530 ;
04540 RS LDX #$18
04550 ;
04560 ; DECR STACK POINTER
04570 ;
04580 JSR DCR
04590 ;
04600 ; POP HIGHRETURN ADDRESS TO PC
04610 ;
04620 LDA (R0L,X)
04630 STA R15H
04640 ;
04650 ; SAME WITH LOW ORDER BYTE
04660 ;
04670 JSR DCR
04680 LDA (R0L,X)
04690 STA R15L
04700 RTS
04710 RTN JMP RTNZ
04720 ------------------------------
04730 SAVE
04740 STA ACC
04750 STX XREG
04760 STY YREG
04770 PHP
04780 PLA
04790 STA STATUS
04800 CLD
04810 RTS
04820 ------------------------------
04830 RESTORE LDA STATUS
04840 PHA
04850 LDA ACC
04860 LDX XREG
04870 LDY YREG
04880 PLP
04890 RTS
04900 ------------------------------
04910 ACC .HX 00
04920 XREG .HX 00
04930 YREG .HX 00
04940 STATUS .HX 00
04950 ------------------------------
04960 TEST
04970 JSR SW16
04980 .HX 1100F0 ; SET R1
04990 .HX 120040 ; SET R2
05000 .HX 130002 ; SET R3
05010 .HX 41 ; LD @R1
05020 .HX 52 ; ST @R2
05030 .HX F3 ; DCR R3
05040 .HX 07FB ; BNZ -4
05050 .HX 00 ; RTN
05060 RTS
05070 ------------------------------
}}}