This commit is contained in:
Tor-Eirik Bakke Lunde 2020-02-29 23:19:40 +01:00
parent e4e412d659
commit a311c252ca
18 changed files with 3014 additions and 176 deletions

View File

@ -13,10 +13,10 @@
4C00- 16 VIA3 .EQ $4C00 ; GAME BOARD (VIA #3)
6000- 17 PORT0B .EQ VIA0
6002- 18 DDR0B .EQ VIA0+2
4C03- 19 DDR3A .EQ VIA3+3 ; USING RC-ONE ADDRESS DECODING SCHEME, PLACING
4C02- 20 DDR3B .EQ VIA3+2 ; VIA3 AT $CC00 BY DEFAULT (INSTEAD OF $AC00)
4C01- 21 PORT3A .EQ VIA3+1 ; TO FIT RC-ONE ADDRESS DECODING THOUGH ORIGINAL
4C00- 22 PORT3B .EQ VIA3 ; CAN BE JUMPERED IF NEEDED/WANTED.
4C03- 19 DDR3A .EQ VIA3+3
4C02- 20 DDR3B .EQ VIA3+2
4C01- 21 PORT3A .EQ VIA3+1
4C00- 22 PORT3B .EQ VIA3
0000- 23
8000- 24 .OR $8000
8000- 25 .TA $0000
@ -60,11 +60,12 @@
8036- I 30 ; SUBROUTINE 'INITKEY'
8036- I 31 ; TAKES CARE OF INITIALIZING VIA #3 FOR USING WITH THE GETKEY ROUTINE FROM
8036- I 32 ; THE CODE.
8036-A9 00 I 33 ( 2) INITKEY LDA #0
8038-8D 03 4C I 34 ( 4) STA DDR3A ; SET KEY STROBE PORT FOR INPUT
803B-A9 FF I 35 ( 2) LDA #$FF
803D-8D 02 4C I 36 ( 4) STA DDR3B ; SET KEYS FOR OUTPUT
8040-60 I 37 ( 6) RTS
8036- I 33 ;
8036-A9 00 I 34 ( 2) INITKEY LDA #0
8038-8D 03 4C I 35 ( 4) STA DDR3A ; SET KEY STROBE PORT FOR INPUT
803B-A9 FF I 36 ( 2) LDA #$FF
803D-8D 02 4C I 37 ( 4) STA DDR3B ; SET KEYS FOR OUTPUT
8040-60 I 38 ( 6) RTS
8041- 34 ;
8041- 35 ; STORE CPU INITIALIZATION VECTORS AT THE END OF THE EEPROM.
8041- 36 ;

View File

@ -1,4 +1,4 @@
.CR 6502
.CR 65C02
.TF music.hex,hex
.LF music.list
;
@ -8,10 +8,6 @@
;
VIA1 .EQ $4000 ; GAME BOARD (VIA #1)
VIA3 .EQ $4C00 ; GAME BOARD (VIA #3)
DDR3A .EQ VIA3+3
DDR3B .EQ VIA3+2
PORT3A .EQ VIA3+1
PORT3B .EQ VIA3
.OR $8000
.TA $0000

View File

@ -5,15 +5,11 @@
0000- 8 ;
4000- 9 VIA1 .EQ $4000 ; GAME BOARD (VIA #1)
4C00- 10 VIA3 .EQ $4C00 ; GAME BOARD (VIA #3)
4C03- 11 DDR3A .EQ VIA3+3
4C02- 12 DDR3B .EQ VIA3+2
4C01- 13 PORT3A .EQ VIA3+1
4C00- 14 PORT3B .EQ VIA3
0000- 15
8000- 16 .OR $8000
8000- 17 .TA $0000
8000-20 06 81 18 ( 6) BE6502 JSR INITKEY
8003- 19 .IN ../../common/CH02-Music/player.asm
0000- 11
8000- 12 .OR $8000
8000- 13 .TA $0000
8000-20 06 81 14 ( 6) BE6502 JSR INITKEY
8003- 15 .IN ../../common/CH02-Music/player.asm
8003- I 1 ; MUSIC PLAYER PROGRAM
8003- I 2 ; USES 16-KEY KEYBOARD AND BUFFERED SPEAKER
8003- I 3 ; PROGRAM PLAYS STORED MUSICAL NOTES. THERE ARE TWO MODES OF OPERATION: INPUT
@ -30,154 +26,158 @@
0300- I 14 TABEG .EQ $0300 ; TABLE TO STORE MUSIC
4C00- I 15 PORT3B .EQ VIA3 ; VIA OUTPUT PORT B
4C02- I 16 DDR3B .EQ VIA3+2 ; VIA PORT B DIRECTION REGISTER
8003- I 17 ;
8003- I 18 ; COMMAND LINE INTERPRETER
8003- I 19 ; $F AS INPUT MEANS RESET POINTERS, START OVER.
8003- I 20 ; $E MEANS PLAY CURRENTLY STORED NOTES
8003- I 21 ; ANYTHING ELSE IS STORED FOR REPLAY.
8003- I 22 ;
8003-A9 00 I 23 ( 2) START LDA #0 ; CLEAR NOTE LIST LENGTH
8005-85 00 I 24 ( 2) STA PILEN
8007-18 I 25 ( 2) CLC ; CLEAR NIBBLE MARKER
8008-20 E1 80 I 26 ( 6) NXKEY JSR GETKEY
800B-C9 0F I 27 ( 2) CMP #15 ; IS KEY #15?
800D-D0 05 I 28 (2**) BNE NXTST ; NO, DO NEXT TEST
800F-20 8A 80 I 29 ( 6) JSR BEEP3 ; TELL USER OF CLEARING
8012-90 EF I 30 (2**) BCC START ; CLEAR POINTERS AND START OVER
8014-C9 0E I 31 ( 2) NXTST CMP #14 ; IS KEY #14?
8016-D0 06 I 32 (2**) BNE NUMKEY ; NO, KEY IS NOTE NUMBER
8018-20 4B 80 I 33 ( 6) JSR PLAYEM ; PLAY NOTES
801B-18 I 34 ( 2) CLC
801C-90 EA I 35 (2**) BCC NXKEY ; GET NEXT COMMAND
801E- I 36 ;
801E- I 37 ; ROUTINE TO LOAD NOT LIST WITH NOTES
801E- I 38 ;
801E-85 01 I 39 ( 2) NUMKEY STA TEMP ; SAVE KEY, FREE A
8020-20 73 80 I 40 ( 6) JSR PLAYIT ; PLAY NOTE
8023-A5 00 I 41 ( 3) LDA PILEN ; GET LIST LENGTH
8025-C9 FF I 42 ( 2) CMP #$FF ; OVERFLOW?
8027-D0 05 I 43 (2**) BNE OK ; NO, ADD NOTE TO LIST
8029-20 8A 80 I 44 ( 6) JSR BEEP3 ; YES, WARN USER
802C-90 DA I 45 (2**) BCC NXKEY ; RETURN TO INPUT MODE
802E-4A I 46 ( 2) OK LSR A ; SHIFT LOW BIT INTO NIBBLE POINTER
802F-A8 I 47 ( 2) TAY ; USE SHIFTED NIBBLE POINTER AS BYTE INDEX
8030-A5 01 I 48 ( 3) LDA TEMP ; RESTORE KEY#
8032-B0 09 I 49 (2**) BCS FINBYT ; IF BYTE ALREADY HAS A NIBBLE, FINISH IT AND STORE
8034-29 0F I 50 ( 2) AND #%00001111 ; 1ST NIBBLE. MASK HIGH NIBBLE
8036-99 00 03 I 51 ( 5) STA TABEG,Y ; SAVE UNFINISHED 1/2 BYTE
8039-E6 00 I 52 ( 5) INC PILEN ; POINT TO NEXT NIBBLE
803B-90 CB I 53 (2**) BCC NXKEY ; GET NEXT KEYSTROKE
803D-0A I 54 ( 2) FINBYT ASL A ; SHIFT NIBBLE 2 TO HIGH ORDER
803E-0A I 55 ( 2) ASL A
803F-0A I 56 ( 2) ASL A
8040-0A I 57 ( 2) ASL A
8041-19 00 03 I 58 ( 4*) ORA TABEG,Y ; JOIN 2 NIBBLES AS BYTE
8044-99 00 03 I 59 ( 5) STA TABEG,Y ; ... AND STORE.
8047-E6 00 I 60 ( 5) INC PILEN ; POINT TO NEXT NIBBLE IN NEXT BYTE
8049-90 BD I 61 (2**) BCC NXKEY ; RETURN
804B- I 62 ;
804B- I 63 ; ROUTINE TO PLAY NOTES
804B- I 64 ;
804B-A2 00 I 65 ( 2) PLAYEM LDX #0 ; CLEAR POINTER
804D-86 02 I 66 ( 3) STX PTR
804F-A5 02 I 67 ( 3) LDA PTR ; LOAD ACCUMULATOR WITH CURRENT POINTER VALUE
8051-4A I 68 ( 2) LOOP LSR A ; SHIFT NIBBLE INDICATOR INTO CARRY
8052-AA I 69 ( 2) TAX ; USE SHIFTED NIBBLE POINTER AS BYTE POINTER
8053-BD 00 03 I 70 ( 4*) LDA TABEG,X ; LOAD NOTE TO PLAY
8056-B0 04 I 71 (2**) BCS ENDBYT ; LOW NIBBLE USED, GET HIGH
8058-29 0F I 72 ( 2) AND #%00001111 ; MASK OUT HIGH BITS
805A-90 06 I 73 (2**) BCC FINISH ; PLAY NOTE
805C-29 F0 I 74 ( 2) ENDBYT AND #%11110000 ; THROW AWAY LOW NIBBLE
805E-4A I 75 ( 2) LSR A ; SHIFT INTO LOW
805F-4A I 76 ( 2) LSR A
8060-4A I 77 ( 2) LSR A
8061-4A I 78 ( 2) LSR A
8062-20 73 80 I 79 ( 6) FINISH JSR PLAYIT ; CALCULATE CONSTANTS & PLAY
8065-A2 20 I 80 ( 2) LDX #$20 ; BETWEEN-NOTE DELAY
8067-20 9F 80 I 81 ( 6) JSR DELAY
806A-E6 02 I 82 ( 5) INC PTR ; ONE NIBBLE USED
806C-A5 02 I 83 ( 3) LDA PTR
806E-C5 00 I 84 ( 3) CMP PILEN ; END OF LIST?
8070-90 DF I 85 (2**) BCC LOOP ; NO, GET NEXT NOTE
8072-60 I 86 ( 6) RTS ; DONE
8073- I 87 ;
8073- I 88 ; ROUTINE TO DO TABLE LOOK UP, SEPARATE REST
8073- I 89 ;
8073-C9 0D I 90 ( 2) PLAYIT CMP #13 ; REST?
8075-D0 06 I 91 (2**) BNE SOUND ; NO.
8077-A2 54 I 92 ( 2) LDX #$54 ; DELAY = NOTE LENGTH = .21SEC
8079-20 9F 80 I 93 ( 6) JSR DELAY
807C-60 I 94 ( 6) RTS
807D-AA I 95 ( 2) SOUND TAX ; USE KEYS AS INDEX..
807E-BD D4 80 I 96 ( 4*) LDA DURTAB,X ; ... TO FIND DURATION.
8081-85 04 I 97 ( 2) STA DUR ; STORE DURATION FOR USE
8083-BD C7 80 I 98 ( 4*) LDA NOTAB,X ; LOAD NOTE VALUE
8086-20 AB 80 I 99 ( 6) JSR TONE
8089-60 I 100 ( 6) RTS
808A- I 101 ;
808A- I 102 ; ROUTINE TO MAKE 3 TONE SIGNAL
808A- I 103 ;
808A-A9 FF I 104 ( 2) BEEP3 LDA #$FF ; DURATION FOR BEEPS
808C-85 04 I 105 ( 2) STA DUR
808E-A9 4B I 106 ( 2) LDA #$4B ; CODE FOR E2
8090-20 AB 80 I 107 ( 6) JSR TONE ; 1ST NOTE
8093-A9 38 I 108 ( 2) LDA #$38 ; CODE FOR D2
8095-20 AB 80 I 109 ( 6) JSR TONE
8098-A9 4B I 110 ( 2) LDA #$4B
809A-20 AB 80 I 111 ( 6) JSR TONE
809D-18 I 112 ( 2) CLC
809E-60 I 113 ( 6) RTS
809F- I 114 ;
809F- I 115 ; VARIABLE-LENGTH DELAY
809F- I 116 ;
809F-A0 FF I 117 ( 2) DELAY LDY #$FF
80A1-EA I 118 ( 2) DLY NOP
80A2-D0 00 I 119 (2**) BNE DL0 ; (.+2 IN BOOK)
80A4-88 I 120 ( 2) DL0 DEY
80A5-D0 FA I 121 (2**) BNE DLY ; 10 US. LOOP
80A7-CA I 122 ( 2) DEX
80A8-D0 F5 I 123 (2**) BNE DELAY ; LOOP TIME = 2556*[X]
80AA-60 I 124 ( 6) RTS
80AB- I 125 ;
80AB- I 126 ; ROUTINE TO MAKE TONE: # OF 1/2 CYCLES IS IN 'DUR', AND 1/2 CYCLE TIME IS IN
80AB- I 127 ; ACCUMULATOR. LOOP TIME = 20*[A]+26 US SINCE TWO RUNS THROUGH THE OUTER LOOP
80AB- I 128 ; MAKES ONE CYCLE OF THE TONE.
4C03- I 17 DDR3A .EQ VIA3+3
4C01- I 18 PORT3A .EQ VIA3+1
4C00- I 19 PORT3B .EQ VIA3
8003- I 20
8003- I 21 ;
8003- I 22 ; COMMAND LINE INTERPRETER
8003- I 23 ; $F AS INPUT MEANS RESET POINTERS, START OVER.
8003- I 24 ; $E MEANS PLAY CURRENTLY STORED NOTES
8003- I 25 ; ANYTHING ELSE IS STORED FOR REPLAY.
8003- I 26 ;
8003-A9 00 I 27 ( 2) START LDA #0 ; CLEAR NOTE LIST LENGTH
8005-85 00 I 28 ( 3) STA PILEN
8007-18 I 29 ( 2) CLC ; CLEAR NIBBLE MARKER
8008-20 E1 80 I 30 ( 6) NXKEY JSR GETKEY
800B-C9 0F I 31 ( 2) CMP #15 ; IS KEY #15?
800D-D0 05 I 32 (2**) BNE NXTST ; NO, DO NEXT TEST
800F-20 8A 80 I 33 ( 6) JSR BEEP3 ; TELL USER OF CLEARING
8012-90 EF I 34 (2**) BCC START ; CLEAR POINTERS AND START OVER
8014-C9 0E I 35 ( 2) NXTST CMP #14 ; IS KEY #14?
8016-D0 06 I 36 (2**) BNE NUMKEY ; NO, KEY IS NOTE NUMBER
8018-20 4B 80 I 37 ( 6) JSR PLAYEM ; PLAY NOTES
801B-18 I 38 ( 2) CLC
801C-90 EA I 39 (2**) BCC NXKEY ; GET NEXT COMMAND
801E- I 40 ;
801E- I 41 ; ROUTINE TO LOAD NOT LIST WITH NOTES
801E- I 42 ;
801E-85 01 I 43 ( 3) NUMKEY STA TEMP ; SAVE KEY, FREE A
8020-20 73 80 I 44 ( 6) JSR PLAYIT ; PLAY NOTE
8023-A5 00 I 45 ( 3) LDA PILEN ; GET LIST LENGTH
8025-C9 FF I 46 ( 2) CMP #$FF ; OVERFLOW?
8027-D0 05 I 47 (2**) BNE OK ; NO, ADD NOTE TO LIST
8029-20 8A 80 I 48 ( 6) JSR BEEP3 ; YES, WARN USER
802C-90 DA I 49 (2**) BCC NXKEY ; RETURN TO INPUT MODE
802E-4A I 50 ( 2) OK LSR A ; SHIFT LOW BIT INTO NIBBLE POINTER
802F-A8 I 51 ( 2) TAY ; USE SHIFTED NIBBLE POINTER AS BYTE INDEX
8030-A5 01 I 52 ( 3) LDA TEMP ; RESTORE KEY#
8032-B0 09 I 53 (2**) BCS FINBYT ; IF BYTE ALREADY HAS A NIBBLE, FINISH IT AND STORE
8034-29 0F I 54 ( 2) AND #%00001111 ; 1ST NIBBLE. MASK HIGH NIBBLE
8036-99 00 03 I 55 ( 5) STA TABEG,Y ; SAVE UNFINISHED 1/2 BYTE
8039-E6 00 I 56 ( 5) INC PILEN ; POINT TO NEXT NIBBLE
803B-90 CB I 57 (2**) BCC NXKEY ; GET NEXT KEYSTROKE
803D-0A I 58 ( 2) FINBYT ASL A ; SHIFT NIBBLE 2 TO HIGH ORDER
803E-0A I 59 ( 2) ASL A
803F-0A I 60 ( 2) ASL A
8040-0A I 61 ( 2) ASL A
8041-19 00 03 I 62 ( 4*) ORA TABEG,Y ; JOIN 2 NIBBLES AS BYTE
8044-99 00 03 I 63 ( 5) STA TABEG,Y ; ... AND STORE.
8047-E6 00 I 64 ( 5) INC PILEN ; POINT TO NEXT NIBBLE IN NEXT BYTE
8049-90 BD I 65 (2**) BCC NXKEY ; RETURN
804B- I 66 ;
804B- I 67 ; ROUTINE TO PLAY NOTES
804B- I 68 ;
804B-A2 00 I 69 ( 2) PLAYEM LDX #0 ; CLEAR POINTER
804D-86 02 I 70 ( 3) STX PTR
804F-A5 02 I 71 ( 3) LDA PTR ; LOAD ACCUMULATOR WITH CURRENT POINTER VALUE
8051-4A I 72 ( 2) LOOP LSR A ; SHIFT NIBBLE INDICATOR INTO CARRY
8052-AA I 73 ( 2) TAX ; USE SHIFTED NIBBLE POINTER AS BYTE POINTER
8053-BD 00 03 I 74 ( 4*) LDA TABEG,X ; LOAD NOTE TO PLAY
8056-B0 04 I 75 (2**) BCS ENDBYT ; LOW NIBBLE USED, GET HIGH
8058-29 0F I 76 ( 2) AND #%00001111 ; MASK OUT HIGH BITS
805A-90 06 I 77 (2**) BCC FINISH ; PLAY NOTE
805C-29 F0 I 78 ( 2) ENDBYT AND #%11110000 ; THROW AWAY LOW NIBBLE
805E-4A I 79 ( 2) LSR A ; SHIFT INTO LOW
805F-4A I 80 ( 2) LSR A
8060-4A I 81 ( 2) LSR A
8061-4A I 82 ( 2) LSR A
8062-20 73 80 I 83 ( 6) FINISH JSR PLAYIT ; CALCULATE CONSTANTS & PLAY
8065-A2 20 I 84 ( 2) LDX #$20 ; BETWEEN-NOTE DELAY
8067-20 9F 80 I 85 ( 6) JSR DELAY
806A-E6 02 I 86 ( 5) INC PTR ; ONE NIBBLE USED
806C-A5 02 I 87 ( 3) LDA PTR
806E-C5 00 I 88 ( 3) CMP PILEN ; END OF LIST?
8070-90 DF I 89 (2**) BCC LOOP ; NO, GET NEXT NOTE
8072-60 I 90 ( 6) RTS ; DONE
8073- I 91 ;
8073- I 92 ; ROUTINE TO DO TABLE LOOK UP, SEPARATE REST
8073- I 93 ;
8073-C9 0D I 94 ( 2) PLAYIT CMP #13 ; REST?
8075-D0 06 I 95 (2**) BNE SOUND ; NO.
8077-A2 54 I 96 ( 2) LDX #$54 ; DELAY = NOTE LENGTH = .21SEC
8079-20 9F 80 I 97 ( 6) JSR DELAY
807C-60 I 98 ( 6) RTS
807D-AA I 99 ( 2) SOUND TAX ; USE KEYS AS INDEX..
807E-BD D4 80 I 100 ( 4*) LDA DURTAB,X ; ... TO FIND DURATION.
8081-85 04 I 101 ( 3) STA DUR ; STORE DURATION FOR USE
8083-BD C7 80 I 102 ( 4*) LDA NOTAB,X ; LOAD NOTE VALUE
8086-20 AB 80 I 103 ( 6) JSR TONE
8089-60 I 104 ( 6) RTS
808A- I 105 ;
808A- I 106 ; ROUTINE TO MAKE 3 TONE SIGNAL
808A- I 107 ;
808A-A9 FF I 108 ( 2) BEEP3 LDA #$FF ; DURATION FOR BEEPS
808C-85 04 I 109 ( 3) STA DUR
808E-A9 4B I 110 ( 2) LDA #$4B ; CODE FOR E2
8090-20 AB 80 I 111 ( 6) JSR TONE ; 1ST NOTE
8093-A9 38 I 112 ( 2) LDA #$38 ; CODE FOR D2
8095-20 AB 80 I 113 ( 6) JSR TONE
8098-A9 4B I 114 ( 2) LDA #$4B
809A-20 AB 80 I 115 ( 6) JSR TONE
809D-18 I 116 ( 2) CLC
809E-60 I 117 ( 6) RTS
809F- I 118 ;
809F- I 119 ; VARIABLE-LENGTH DELAY
809F- I 120 ;
809F-A0 FF I 121 ( 2) DELAY LDY #$FF
80A1-EA I 122 ( 2) DLY NOP
80A2-D0 00 I 123 (2**) BNE DL0 ; (.+2 IN BOOK)
80A4-88 I 124 ( 2) DL0 DEY
80A5-D0 FA I 125 (2**) BNE DLY ; 10 US. LOOP
80A7-CA I 126 ( 2) DEX
80A8-D0 F5 I 127 (2**) BNE DELAY ; LOOP TIME = 2556*[X]
80AA-60 I 128 ( 6) RTS
80AB- I 129 ;
80AB-85 03 I 130 ( 2) TONE STA FREQ ; FREQ IS TEMP FOR # OF CYCLES
80AD-A9 FF I 131 ( 2) LDA #$FF ; SET UP DATA DIRECTION REGISTER
80AF-8D 02 4C I 132 ( 4) STA DDR3B
80B2-A9 00 I 133 ( 2) LDA #$00 ; A IS SENT TO PORT, START HI
80B4-A6 04 I 134 ( 3) LDX DUR
80B6-A4 03 I 135 ( 3) FL2 LDY FREQ
80B8-88 I 136 ( 2) FL1 DEY
80B9-18 I 137 ( 2) CLC
80BA-90 00 I 138 (2**) BCC FL0 ; (.+2 IN BOOK)
80BC-D0 FA I 139 (2**) FL0 BNE FL1 ; INNER, 10 US LOOP.
80BE-49 FF I 140 ( 2) EOR #$FF ; COMPLEMENT I/O PORT
80C0-8D 00 4C I 141 ( 4) STA PORT3B ; ... AND SET IT
80C3-CA I 142 ( 2) DEX
80C4-D0 F0 I 143 (2**) BNE FL2 ; OUTER LOOP
80C6-60 I 144 ( 6) RTS
80C7- I 145 ;
80C7- I 146 ; TABLE OF NOTE CONSTANTS
80C7- I 147 ; CONTAINS:
80C7- I 148 ; [OCTAVE BELOW MIDDLE C] : G,A,BCC
80C7- I 149 ; [OCTAVE OF MIDDLE C] : C,D,E,F,F#,G,G#,A,B
80C7- I 150 ; [OCTAVE ABOVE MIDDLE C] : C
80C7- I 151 ;
80AB- I 130 ; ROUTINE TO MAKE TONE: # OF 1/2 CYCLES IS IN 'DUR', AND 1/2 CYCLE TIME IS IN
80AB- I 131 ; ACCUMULATOR. LOOP TIME = 20*[A]+26 US SINCE TWO RUNS THROUGH THE OUTER LOOP
80AB- I 132 ; MAKES ONE CYCLE OF THE TONE.
80AB- I 133 ;
80AB-85 03 I 134 ( 3) TONE STA FREQ ; FREQ IS TEMP FOR # OF CYCLES
80AD-A9 FF I 135 ( 2) LDA #$FF ; SET UP DATA DIRECTION REGISTER
80AF-8D 02 4C I 136 ( 4) STA DDR3B
80B2-A9 00 I 137 ( 2) LDA #$00 ; A IS SENT TO PORT, START HI
80B4-A6 04 I 138 ( 3) LDX DUR
80B6-A4 03 I 139 ( 3) FL2 LDY FREQ
80B8-88 I 140 ( 2) FL1 DEY
80B9-18 I 141 ( 2) CLC
80BA-90 00 I 142 (2**) BCC FL0 ; (.+2 IN BOOK)
80BC-D0 FA I 143 (2**) FL0 BNE FL1 ; INNER, 10 US LOOP.
80BE-49 FF I 144 ( 2) EOR #$FF ; COMPLEMENT I/O PORT
80C0-8D 00 4C I 145 ( 4) STA PORT3B ; ... AND SET IT
80C3-CA I 146 ( 2) DEX
80C4-D0 F0 I 147 (2**) BNE FL2 ; OUTER LOOP
80C6-60 I 148 ( 6) RTS
80C7- I 149 ;
80C7- I 150 ; TABLE OF NOTE CONSTANTS
80C7- I 151 ; CONTAINS:
80C7- I 152 ; [OCTAVE BELOW MIDDLE C] : G,A,BCC
80C7- I 153 ; [OCTAVE OF MIDDLE C] : C,D,E,F,F#,G,G#,A,B
80C7- I 154 ; [OCTAVE ABOVE MIDDLE C] : C
80C7- I 155 ;
80C7-FE E2 C9 BE
A9 96 8E 86
7E 77 70 64
5E I 152 NOTAB .HS FE.E2.C9.BE.A9.96.8E.86.7E.77.70.64.5E
80D4- I 153 ;
80D4- I 154 ; TABLE OF NOTE DURATIONS IN # OF 1/2 CYCLES SET FOR A NOTE LENGTH OF
80D4- I 155 ; ABOUT .21 SEC.
80D4- I 156 ;
5E I 156 NOTAB .HS FE.E2.C9.BE.A9.96.8E.86.7E.77.70.64.5E
80D4- I 157 ;
80D4- I 158 ; TABLE OF NOTE DURATIONS IN # OF 1/2 CYCLES SET FOR A NOTE LENGTH OF
80D4- I 159 ; ABOUT .21 SEC.
80D4- I 160 ;
80D4-55 60 6B 72
80 8F 94 A1
AA B5 BF D7
E4 I 157 DURTAB .HS 55.60.6B.72.80.8F.94.A1.AA.B5.BF.D7.E4
80E1- 20 .IN ../../common/CH01-Getkey/getkey_routine.asm
E4 I 161 DURTAB .HS 55.60.6B.72.80.8F.94.A1.AA.B5.BF.D7.E4
80E1- 16 .IN ../../common/CH01-Getkey/getkey_routine.asm
80E1- I 1 ; 'GETKEY' KEYBOARD INPUT ROUTINE READS AND DEBOUNCES KEYBOARD. RETURNS WITH
80E1- I 2 ; KEY NUMBER IN ACCUMULATOR IF KEY DOWN. OPERATION: SENDS NUMBERS 0-F TO 74154
80E1- I 3 ; (4 TO 16 LINE DECODER), WHICH GROUNDS ONE SIDE OF KEYSWITCHES ONE AT A TIME.
@ -210,15 +210,16 @@
8106- I 30 ; SUBROUTINE 'INITKEY'
8106- I 31 ; TAKES CARE OF INITIALIZING VIA #3 FOR USING WITH THE GETKEY ROUTINE FROM
8106- I 32 ; THE CODE.
8106-A9 00 I 33 ( 2) INITKEY LDA #0
8108-8D 03 4C I 34 ( 4) STA DDR3A ; SET KEY STROBE PORT FOR INPUT
810B-A9 FF I 35 ( 2) LDA #$FF
810D-8D 02 4C I 36 ( 4) STA DDR3B ; SET KEYS FOR OUTPUT
8110-60 I 37 ( 6) RTS
8111- 21 ;
8111- 22 ; STORE CPU INITIALIZATION VECTORS AT THE END OF THE EEPROM.
8111- 23 ;
FFFA 24 .NO $FFFA,$FF
FFFA-00 80 25 .DA BE6502 ; NMI VECTOR
FFFC-00 80 26 .DA BE6502 ; RESET VECTOR
FFFE-00 80 27 .DA BE6502 ; IRQ VECTOR
8106- I 33 ;
8106-A9 00 I 34 ( 2) INITKEY LDA #0
8108-8D 03 4C I 35 ( 4) STA DDR3A ; SET KEY STROBE PORT FOR INPUT
810B-A9 FF I 36 ( 2) LDA #$FF
810D-8D 02 4C I 37 ( 4) STA DDR3B ; SET KEYS FOR OUTPUT
8110-60 I 38 ( 6) RTS
8111- 17 ;
8111- 18 ; STORE CPU INITIALIZATION VECTORS AT THE END OF THE EEPROM.
8111- 19 ;
FFFA 20 .NO $FFFA,$FF
FFFA-00 80 21 .DA BE6502 ; NMI VECTOR
FFFC-00 80 22 .DA BE6502 ; RESET VECTOR
FFFE-00 80 23 .DA BE6502 ; IRQ VECTOR

View File

@ -0,0 +1,4 @@
@echo off
sbasm.py hexguess.asm
type hexguess.list
pause

View File

@ -0,0 +1,23 @@
.CR 65C02
.TF hexguess.hex,hex
.LF hexguess.list
;
; MUSIC PLAYER FOR THE BE6502 USING '6502 GAMES' HARDWARE. BOARD SHOULD BE
; JUMPERED WITH VIA CHIPS AT THE ADDRESSES SPECIFIED BELOW. OTHER THAN THAT
; THE CODE IS UNCHANGED FROM THE BOOK.
;
VIA1 .EQ $4000 ; GAME BOARD (VIA #1)
VIA3 .EQ $4C00 ; GAME BOARD (VIA #3)
.OR $8000
.TA $0000
BE6502 JSR INITKEY
.IN ../../common/CH04-Hexguess/game.asm
.IN ../../common/CH01-Getkey/getkey_routine.asm
;
; STORE CPU INITIALIZATION VECTORS AT THE END OF THE EEPROM.
;
.NO $FFFA,$FF
.DA BE6502 ; NMI VECTOR
.DA BE6502 ; RESET VECTOR
.DA BE6502 ; IRQ VECTOR

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,191 @@
0000- 4 ;
0000- 5 ; MUSIC PLAYER FOR THE BE6502 USING '6502 GAMES' HARDWARE. BOARD SHOULD BE
0000- 6 ; JUMPERED WITH VIA CHIPS AT THE ADDRESSES SPECIFIED BELOW. OTHER THAN THAT
0000- 7 ; THE CODE IS UNCHANGED FROM THE BOOK.
0000- 8 ;
4000- 9 VIA1 .EQ $4000 ; GAME BOARD (VIA #1)
4C00- 10 VIA3 .EQ $4C00 ; GAME BOARD (VIA #3)
0000- 11
8000- 12 .OR $8000
8000- 13 .TA $0000
8000-20 DE 80 14 ( 6) BE6502 JSR INITKEY
8003- 15 .IN ../../common/CH04-Hexguess/game.asm
8003- I 1 ; 'HEXGUESS'
8003- I 2 ; HEXADECIMAL NUMBER GUESSING GAME.
8003- I 3 ; THE OBJECT OF THE GAME IS TO GUESS A HEXADECIMAL NUMBER THAT THE COMPUTER HAS
8003- I 4 ; THOUGHT UP. WHEN THE COMPUTER 'BEEPS', A GUESS SHOULD BE ENTERED. GUESSES ARE
8003- I 5 ; TWO DIGIT HEXADECIMAL NUMBERS, WHEN TWO DIGITS HAVE BEEN RECEIVED THE
8003- I 6 ; COMPUTER WILL DISPLAY THE NEARNESS OF THE GUESS BY LIGHTING A NUMBER OF LEDS
8003- I 7 ; PROPORTIONAL TO THE CLOSENESS OF THE GUESS. TEN GUESSES ARE ALLOWED. IF A
8003- I 8 ; GUESS IS CORRECT, THEN THE COMPUTER WILL FLASH THE LEDS AND MAKE A WARBLING
8003- I 9 ; TONE.
8003- I 10 ;
8003- I 11 ;
8003- I 12 ; 6522 VIA #1 ADDRESSES:
4004- I 13 TIMER .EQ VIA1+4 ; LOW LATCH OF TIMER 1
4003- I 14 DDR1A .EQ VIA1+3 ; PORT A DATA DIRECTION REGISTER
4003- I 15 DDR1B .EQ VIA1+3 ; PORT B DATA DIRECTION REGISTER
4001- I 16 PORT1A .EQ VIA1+1 ; PORT A
4000- I 17 PORT1B .EQ VIA1 ; PORT B
8003- I 18 ; 6522 VIA #3 ADDRESSES:
4C01- I 19 DDR3A .EQ VIA3+1 ; PORT A DATA DIRECTION REGISTER
4C02- I 20 DDR3B .EQ VIA3+2 ; PORT B DATA DIRECTION REGISTER
4C00- I 21 PORT3B .EQ VIA3 ; PORT B
4C01- I 22 PORT3A .EQ VIA3+1 ; PORT A
8003- I 23 ; STORAGES:
0000- I 24 ZP .EQ $00
0000- I 25 GUESS .EQ ZP
0001- I 26 GUESSN .EQ ZP+1
0002- I 27 DUR .EQ ZP+2
0003- I 28 FREQ .EQ ZP+3
0004- I 29 NUMBER .EQ ZP+4
8003- I 30
8003-A9 FF I 31 ( 2) LDA #$FF ; SET UP DATA DIRECTION REGISTERS
8005-8D 03 40 I 32 ( 4) STA DDR1A
8008-8D 03 40 I 33 ( 4) STA DDR1B
800B-8D 02 4C I 34 ( 4) STA DDR3B
800E-85 02 I 35 ( 3) STA DUR ; SET UP TONE DURATIONS.
8010-A9 0A I 36 ( 2) START LDA #$0A ; 10 GUESSES ALLOWED
8012-85 01 I 37 ( 3) STA GUESSN
8014-A9 00 I 38 ( 2) LDA #0 ; BLANK LEDS
8016-8D 01 40 I 39 ( 4) STA PORT1A
8019-8D 00 40 I 40 ( 4) STA PORT1B
801C-AD 04 40 I 41 ( 4) LDA TIMER ; GET RANDOM NUMBER TO GUESS
801F-85 04 I 42 ( 3) STA NUMBER ; ... AND SAVE.
8021-A9 20 I 43 ( 2) GETGES LDA #$20 ; SET UP SHORT HIGH TONE TO SIGNAL USER TO
8023- I 44 ; INPUT GUESS.
8023-20 99 80 I 45 ( 6) JSR TONE ; MAKE BEEP.
8026-20 B9 80 I 46 ( 6) JSR GETKEY ; GET HIGH ORDER USER GUESS
8029-0A I 47 ( 2) ASL A ; SHIFT INTO HIGH ORDER POSITION
802A-0A I 48 ( 2) ASL A
802B-0A I 49 ( 2) ASL A
802C-0A I 50 ( 2) ASL A
802D-85 00 I 51 ( 3) STA GUESS ; SAVE
802F-20 B9 80 I 52 ( 6) JSR GETKEY ; GET LOW ORDER USER GUESS
8032-29 0F I 53 ( 2) AND #%00001111 ; MASK HIGH ORDER BITS.
8034-05 00 I 54 ( 3) ORA GUESS ; ADD HIGH ORDER NIBBLE.
8036-85 00 I 55 ( 3) STA GUESS ; FINAL PRODUCT SAVED.
8038-A5 04 I 56 ( 3) LDA NUMBER ; GET NUMBER FOR COMPARE
803A-38 I 57 ( 2) SEC ; SUBTRACT GUESS FROM NUMBER TO DETERMINE THE
803B-E5 00 I 58 ( 3) SBC GUESS ; NEARNESS OF THE GUESS.
803D-B0 05 I 59 (2**) BCS ALRIGHT ; POSITIVE VALUE NEEDS NO FIX.
803F-49 FF I 60 ( 2) EOR #%11111111 ; MAKE DISTANCE ABSOLUTE
8041-38 I 61 ( 2) SEC ; MAKE IT A TWO'S COMPLEMENT
8042-69 00 I 62 ( 2) ADC #00 ; ... NOT JUST A ONE'S COMPLEMENT.
8044-A2 00 I 63 ( 2) ALRIGHT LDX #00 ; SET CLOSENESS COUNTER TO DISTANT
8046-DD B0 80 I 64 ( 4*) LOOP CMP LIMITS,X ; COMPARE NEARNESS OF GUESS TO TABLE OF LIMITS
8049- I 65 ; TO SEE HOW MANY LIGHTS TO LIGHT.
8049-B0 27 I 66 (2**) BCS SIGNAL ; NEARNESS IS BIGGER THAN LIMIT, SO GO
804B- I 67 ; LIGHT INDICATOR INSTEAD.
804B-E8 I 68 ( 2) INX ; LOOK AT NEXT CLOSENESS LEVEL.
804C-E0 09 I 69 ( 2) CPX #9 ; ALL NINE LEVELS TRIED?
804E-D0 F6 I 70 (2**) BNE LOOP ; NO, TRY NEXT LEVEL.
8050-A9 0B I 71 ( 2) WIN LDA #11 ; YES; WIN! LOAD NUMBER OF BLINKS
8052-85 00 I 72 ( 3) STA GUESS ; USE GUESS AS TEMP
8054-A9 FF I 73 ( 2) LDA #$FF ; LIGHT LEDS
8056-8D 01 40 I 74 ( 4) STA PORT1A
8059-8D 00 40 I 75 ( 4) STA PORT1B
805C-A9 32 I 76 ( 2) WOW LDA #50 ; TONE VALUE
805E-20 99 80 I 77 ( 6) JSR TONE ; MAKE WIN SIGNAL
8061-A9 FF I 78 ( 2) LDA #$FF
8063-4D 01 40 I 79 ( 4) EOR PORT1A ; COMPLEMENT PORTS
8066-8D 01 40 I 80 ( 4) STA PORT1A
8069-8D 00 40 I 81 ( 4) STA PORT1B
806C-C6 00 I 82 ( 5) DEC GUESS ; BLINKS/TONES DONE?
806E-D0 EC I 83 (2**) BNE WOW ; NO, DO AGAIN.
8070-F0 9E I 84 (2**) BEQ START ; YES, START NEW GAME.
8072-E8 I 85 ( 2) SIGNAL INX ; INCREMENT CLOSENESS LEVEL COUNTER SO AT
8073- I 86 ; LEAST 1 LED IS LIT.
8073-A9 00 I 87 ( 2) LDA #0 ; CLEAR HIGH LED PORT
8075-8D 00 40 I 88 ( 4) STA PORT1B
8078-20 91 80 I 89 ( 6) JSR LITE ; GET LED PATTERN
807B-8D 01 40 I 90 ( 4) STA PORT1A ; SET LEDS
807E-90 05 I 91 (2**) BCC CC ; IF CARRY SET PB0 = 1
8080-A9 01 I 92 ( 2) LDA #01
8082-8D 00 40 I 93 ( 4) STA PORT1B
8085-C6 01 I 94 ( 5) CC DEC GUESSN ; ONE GUESS USED
8087-D0 98 I 95 (2**) BNE GETGES ; SOME LEFT, GET NEXT.
8089-A9 BE I 96 ( 2) LDA #$BE ; LOW TONE SIGNALS LOSE
808B-20 99 80 I 97 ( 6) JSR TONE
808E-4C 10 80 I 98 ( 3) JMP START ; NEW GAME
8091- I 99 ;
8091- I 100 ; SUBROUTINE 'LITE'
8091- I 101 ; ROUTINE TO MAKE PATTERN OF LIT LEDS BY SHIFTING A STRING OF ONES TO THE
8091- I 102 ; LEFT IN THE ACCUMULATOR UNTIL THE BIT POSITION CORRESPONDING TO THE NUMBER
8091- I 103 ; IN X IS REACHED.
8091- I 104 ;
8091-A9 00 I 105 ( 2) LITE LDA #0 ; CLEAR ACCUMULATOR FOR PATTERN
8093-38 I 106 ( 2) SHIFT SEC ; MAKE LOW BIT HIGH.
8094-2A I 107 ( 2) ROL A ; SHIFT IT IN
8095-CA I 108 ( 2) DEX ; ONE BIT DONE...
8096-D0 FB I 109 (2**) BNE SHIFT ; LOOP IF NOT DONE.
8098-60 I 110 ( 6) RTS ; RETURN
8099- I 111 ;
8099- I 112 ; SUBROUTINE 'TONE'
8099- I 113 ; TONE GENERATION ROUTINE.
8099- I 114 ;
8099-85 03 I 115 ( 3) TONE STA FREQ
809B-A9 00 I 116 ( 2) LDA #0
809D-A6 02 I 117 ( 3) LDX DUR
809F-A4 03 I 118 ( 3) FL2 LDY FREQ
80A1-88 I 119 ( 2) FL1 DEY
80A2-18 I 120 ( 2) CLC
80A3-90 00 I 121 (2**) BCC FL0 ; (.+2 IN BOOK)
80A5-D0 FA I 122 (2**) FL0 BNE FL1
80A7-49 FF I 123 ( 2) EOR #$FF
80A9-8D 00 4C I 124 ( 4) STA PORT3B
80AC-CA I 125 ( 2) DEX
80AD-D0 F0 I 126 (2**) BNE FL2
80AF-60 I 127 ( 6) RTS
80B0- I 128 ;
80B0- I 129 ; TABLE OF LIMITS FOR CLOSENESS LEVELS.
80B0- I 130 ;
80B0-C8 80 40 20
10 08 04 02
01 I 131 LIMITS .HS C8.80.40.20.10.08.04.02.01
80B9- 16 .IN ../../common/CH01-Getkey/getkey_routine.asm
80B9- I 1 ; 'GETKEY' KEYBOARD INPUT ROUTINE READS AND DEBOUNCES KEYBOARD. RETURNS WITH
80B9- I 2 ; KEY NUMBER IN ACCUMULATOR IF KEY DOWN. OPERATION: SENDS NUMBERS 0-F TO 74154
80B9- I 3 ; (4 TO 16 LINE DECODER), WHICH GROUNDS ONE SIDE OF KEYSWITCHES ONE AT A TIME.
80B9- I 4 ; IF A KEY IS DOWN, PA7 OF VIA #3 WILL BE GROUNDED, AND THE CURRENT VALUE
80B9- I 5 ; APPLIED TO THE 74154 BE THE KEY NUMBER. WHEN THE PROGRAM DETECTS A KEY CLOSE
80B9- I 6 ; CHECKS FOR KEY CLOSURE FOR 50 MS. TO ELIMINATE BOUNCE.
80B9- I 7 ; NOTE: IF NO KEY IS PRESSED, GETKEY WILL WAIT.
80B9- I 8 ;
80B9-2C 01 4C I 9 ( 4) GETKEY BIT PORT3A ; SEE IF KEY IS STILL DOWN FROM LAST KEY CLOSURE:
80BC- I 10 ; KEYSTROBE IN 'N' STATUS BIT.
80BC-10 FB I 11 (2**) BPL GETKEY ; IF YES, WAIT FOR KEY RELEASE
80BE-A2 0F I 12 ( 2) RSTART LDX #15 ; SET KEY COUNTER TO 15
80C0-8E 00 4C I 13 ( 4) NXTKEY STX PORT3B ; OUTPUT KEY # TO 74154
80C3-2C 01 4C I 14 ( 4) BIT PORT3A ; SEE IF KEY DOWN: STROBE IN 'N'
80C6-10 05 I 15 (2**) BPL BOUNCE ; IF YES, GO DEBOUNCE
80C8-CA I 16 ( 2) DEX ; DECREMENT KEY #
80C9-10 F5 I 17 (2**) BPL NXTKEY ; NO, DO NEXT KEY
80CB-30 F1 I 18 (2**) BMI RSTART ; START OVER
80CD-8A I 19 ( 2) BOUNCE TXA ; SAVE KEY NUMBER IN A
80CE-A0 12 I 20 ( 2) LDY #$12 ; OUTER LOOP CNT LOAD FOR DELAY OF 50 MS.
80D0-A2 FF I 21 ( 2) LP1 LDX #$FF ; INNER 11 US. LOOP
80D2-2C 01 4C I 22 ( 4) LP2 BIT PORT3A ; SEE IF KEY STILL DOWN
80D5-30 E7 I 23 (2**) BMI RSTART ; IF NOT, KEY NOT VALID, RESTART
80D7-CA I 24 ( 2) DEX
80D8-D0 F8 I 25 (2**) BNE LP2 ; THIS LOOP USES 2115*5 US.
80DA-88 I 26 ( 2) DEY
80DB-D0 F3 I 27 (2**) BNE LP1 ; OUTER LOOP: TOTAL IS 50 MS.
80DD-60 I 28 ( 6) RTS ; DONE: KEY IN A.
80DE- I 29 ;
80DE- I 30 ; SUBROUTINE 'INITKEY'
80DE- I 31 ; TAKES CARE OF INITIALIZING VIA #3 FOR USING WITH THE GETKEY ROUTINE FROM
80DE- I 32 ; THE CODE.
80DE- I 33 ;
80DE-A9 00 I 34 ( 2) INITKEY LDA #0
80E0-8D 01 4C I 35 ( 4) STA DDR3A ; SET KEY STROBE PORT FOR INPUT
80E3-A9 FF I 36 ( 2) LDA #$FF
80E5-8D 02 4C I 37 ( 4) STA DDR3B ; SET KEYS FOR OUTPUT
80E8-60 I 38 ( 6) RTS
80E9- 17 ;
80E9- 18 ; STORE CPU INITIALIZATION VECTORS AT THE END OF THE EEPROM.
80E9- 19 ;
FFFA 20 .NO $FFFA,$FF
FFFA-00 80 21 .DA BE6502 ; NMI VECTOR
FFFC-00 80 22 .DA BE6502 ; RESET VECTOR
FFFE-00 80 23 .DA BE6502 ; IRQ VECTOR

View File

@ -0,0 +1,4 @@
@echo off
sbasm.py hexguess.asm
type hexguess.list
pause

View File

@ -0,0 +1,15 @@
.CR 6502
.TF hexguess.hex,hex
.LF hexguess.list
;
; HEX GUESSING GAME FOR THE KIM-1 USING '6502 GAMES' HARDWARE. BOARD SHOULD BE
; JUMPERED WITH VIA CHIPS AT THE ADDRESSES SPECIFIED BELOW. OTHER THAN THAT
; THE CODE IS UNCHANGED FROM THE BOOK.
;
VIA1 .EQ $C000
VIA3 .EQ $CC00
.OR $0200
.TA $0200
.IN ../../common/CH04-Hexguess/game.asm
.IN ../../common/CH01-Getkey/getkey_routine.asm

View File

@ -0,0 +1,15 @@
A9FF8D03C08D03C08D02CC8502A90A85
01A9008D01C08D00C0AD04C08504A920
20960220B6020A0A0A0A850020B60229
0F05008500A50438E500B00549FF3869
00A200DDAD02B027E8E009D0F6A90B85
00A9FF8D01C08D00C0A932209602A9FF
4D01C08D01C08D00C0C600D0ECF09EE8
A9008D00C0208E028D01C09005A9018D
00C0C601D098A9BE2096024C0D02A900
382ACAD0FB608503A900A602A4038818
9000D0FA49FF8D00CCCAD0F060C88040
2010080402012C01CC10FBA20F8E00CC
2C01CC1005CA10F530F18AA012A2FF2C
01CC30E7CAD0F888D0F360A9008D01CC
A9FF8D02CC60

View File

@ -0,0 +1,183 @@
0000- 4 ;
0000- 5 ; HEX GUESSING GAME FOR THE KIM-1 USING '6502 GAMES' HARDWARE. BOARD SHOULD BE
0000- 6 ; JUMPERED WITH VIA CHIPS AT THE ADDRESSES SPECIFIED BELOW. OTHER THAN THAT
0000- 7 ; THE CODE IS UNCHANGED FROM THE BOOK.
0000- 8 ;
C000- 9 VIA1 .EQ $C000
CC00- 10 VIA3 .EQ $CC00
0000- 11
0200- 12 .OR $0200
0200- 13 .TA $0200
0200- 14 .IN ../../common/CH04-Hexguess/game.asm
0200- I 1 ; 'HEXGUESS'
0200- I 2 ; HEXADECIMAL NUMBER GUESSING GAME.
0200- I 3 ; THE OBJECT OF THE GAME IS TO GUESS A HEXADECIMAL NUMBER THAT THE COMPUTER HAS
0200- I 4 ; THOUGHT UP. WHEN THE COMPUTER 'BEEPS', A GUESS SHOULD BE ENTERED. GUESSES ARE
0200- I 5 ; TWO DIGIT HEXADECIMAL NUMBERS, WHEN TWO DIGITS HAVE BEEN RECEIVED THE
0200- I 6 ; COMPUTER WILL DISPLAY THE NEARNESS OF THE GUESS BY LIGHTING A NUMBER OF LEDS
0200- I 7 ; PROPORTIONAL TO THE CLOSENESS OF THE GUESS. TEN GUESSES ARE ALLOWED. IF A
0200- I 8 ; GUESS IS CORRECT, THEN THE COMPUTER WILL FLASH THE LEDS AND MAKE A WARBLING
0200- I 9 ; TONE.
0200- I 10 ;
0200- I 11 ;
0200- I 12 ; 6522 VIA #1 ADDRESSES:
C004- I 13 TIMER .EQ VIA1+4 ; LOW LATCH OF TIMER 1
C003- I 14 DDR1A .EQ VIA1+3 ; PORT A DATA DIRECTION REGISTER
C003- I 15 DDR1B .EQ VIA1+3 ; PORT B DATA DIRECTION REGISTER
C001- I 16 PORT1A .EQ VIA1+1 ; PORT A
C000- I 17 PORT1B .EQ VIA1 ; PORT B
0200- I 18 ; 6522 VIA #3 ADDRESSES:
CC01- I 19 DDR3A .EQ VIA3+1 ; PORT A DATA DIRECTION REGISTER
CC02- I 20 DDR3B .EQ VIA3+2 ; PORT B DATA DIRECTION REGISTER
CC00- I 21 PORT3B .EQ VIA3 ; PORT B
CC01- I 22 PORT3A .EQ VIA3+1 ; PORT A
0200- I 23 ; STORAGES:
0000- I 24 ZP .EQ $00
0000- I 25 GUESS .EQ ZP
0001- I 26 GUESSN .EQ ZP+1
0002- I 27 DUR .EQ ZP+2
0003- I 28 FREQ .EQ ZP+3
0004- I 29 NUMBER .EQ ZP+4
0200- I 30
0200-A9 FF I 31 ( 2) LDA #$FF ; SET UP DATA DIRECTION REGISTERS
0202-8D 03 C0 I 32 ( 4) STA DDR1A
0205-8D 03 C0 I 33 ( 4) STA DDR1B
0208-8D 02 CC I 34 ( 4) STA DDR3B
020B-85 02 I 35 ( 2) STA DUR ; SET UP TONE DURATIONS.
020D-A9 0A I 36 ( 2) START LDA #$0A ; 10 GUESSES ALLOWED
020F-85 01 I 37 ( 2) STA GUESSN
0211-A9 00 I 38 ( 2) LDA #0 ; BLANK LEDS
0213-8D 01 C0 I 39 ( 4) STA PORT1A
0216-8D 00 C0 I 40 ( 4) STA PORT1B
0219-AD 04 C0 I 41 ( 4) LDA TIMER ; GET RANDOM NUMBER TO GUESS
021C-85 04 I 42 ( 2) STA NUMBER ; ... AND SAVE.
021E-A9 20 I 43 ( 2) GETGES LDA #$20 ; SET UP SHORT HIGH TONE TO SIGNAL USER TO
0220- I 44 ; INPUT GUESS.
0220-20 96 02 I 45 ( 6) JSR TONE ; MAKE BEEP.
0223-20 B6 02 I 46 ( 6) JSR GETKEY ; GET HIGH ORDER USER GUESS
0226-0A I 47 ( 2) ASL A ; SHIFT INTO HIGH ORDER POSITION
0227-0A I 48 ( 2) ASL A
0228-0A I 49 ( 2) ASL A
0229-0A I 50 ( 2) ASL A
022A-85 00 I 51 ( 2) STA GUESS ; SAVE
022C-20 B6 02 I 52 ( 6) JSR GETKEY ; GET LOW ORDER USER GUESS
022F-29 0F I 53 ( 2) AND #%00001111 ; MASK HIGH ORDER BITS.
0231-05 00 I 54 ( 3) ORA GUESS ; ADD HIGH ORDER NIBBLE.
0233-85 00 I 55 ( 2) STA GUESS ; FINAL PRODUCT SAVED.
0235-A5 04 I 56 ( 3) LDA NUMBER ; GET NUMBER FOR COMPARE
0237-38 I 57 ( 2) SEC ; SUBTRACT GUESS FROM NUMBER TO DETERMINE THE
0238-E5 00 I 58 ( 3) SBC GUESS ; NEARNESS OF THE GUESS.
023A-B0 05 I 59 (2**) BCS ALRIGHT ; POSITIVE VALUE NEEDS NO FIX.
023C-49 FF I 60 ( 2) EOR #%11111111 ; MAKE DISTANCE ABSOLUTE
023E-38 I 61 ( 2) SEC ; MAKE IT A TWO'S COMPLEMENT
023F-69 00 I 62 ( 2) ADC #00 ; ... NOT JUST A ONE'S COMPLEMENT.
0241-A2 00 I 63 ( 2) ALRIGHT LDX #00 ; SET CLOSENESS COUNTER TO DISTANT
0243-DD AD 02 I 64 ( 4*) LOOP CMP LIMITS,X ; COMPARE NEARNESS OF GUESS TO TABLE OF LIMITS
0246- I 65 ; TO SEE HOW MANY LIGHTS TO LIGHT.
0246-B0 27 I 66 (2**) BCS SIGNAL ; NEARNESS IS BIGGER THAN LIMIT, SO GO
0248- I 67 ; LIGHT INDICATOR INSTEAD.
0248-E8 I 68 ( 2) INX ; LOOK AT NEXT CLOSENESS LEVEL.
0249-E0 09 I 69 ( 2) CPX #9 ; ALL NINE LEVELS TRIED?
024B-D0 F6 I 70 (2**) BNE LOOP ; NO, TRY NEXT LEVEL.
024D-A9 0B I 71 ( 2) WIN LDA #11 ; YES; WIN! LOAD NUMBER OF BLINKS
024F-85 00 I 72 ( 2) STA GUESS ; USE GUESS AS TEMP
0251-A9 FF I 73 ( 2) LDA #$FF ; LIGHT LEDS
0253-8D 01 C0 I 74 ( 4) STA PORT1A
0256-8D 00 C0 I 75 ( 4) STA PORT1B
0259-A9 32 I 76 ( 2) WOW LDA #50 ; TONE VALUE
025B-20 96 02 I 77 ( 6) JSR TONE ; MAKE WIN SIGNAL
025E-A9 FF I 78 ( 2) LDA #$FF
0260-4D 01 C0 I 79 ( 4) EOR PORT1A ; COMPLEMENT PORTS
0263-8D 01 C0 I 80 ( 4) STA PORT1A
0266-8D 00 C0 I 81 ( 4) STA PORT1B
0269-C6 00 I 82 ( 5) DEC GUESS ; BLINKS/TONES DONE?
026B-D0 EC I 83 (2**) BNE WOW ; NO, DO AGAIN.
026D-F0 9E I 84 (2**) BEQ START ; YES, START NEW GAME.
026F-E8 I 85 ( 2) SIGNAL INX ; INCREMENT CLOSENESS LEVEL COUNTER SO AT
0270- I 86 ; LEAST 1 LED IS LIT.
0270-A9 00 I 87 ( 2) LDA #0 ; CLEAR HIGH LED PORT
0272-8D 00 C0 I 88 ( 4) STA PORT1B
0275-20 8E 02 I 89 ( 6) JSR LITE ; GET LED PATTERN
0278-8D 01 C0 I 90 ( 4) STA PORT1A ; SET LEDS
027B-90 05 I 91 (2**) BCC CC ; IF CARRY SET PB0 = 1
027D-A9 01 I 92 ( 2) LDA #01
027F-8D 00 C0 I 93 ( 4) STA PORT1B
0282-C6 01 I 94 ( 5) CC DEC GUESSN ; ONE GUESS USED
0284-D0 98 I 95 (2**) BNE GETGES ; SOME LEFT, GET NEXT.
0286-A9 BE I 96 ( 2) LDA #$BE ; LOW TONE SIGNALS LOSE
0288-20 96 02 I 97 ( 6) JSR TONE
028B-4C 0D 02 I 98 ( 3) JMP START ; NEW GAME
028E- I 99 ;
028E- I 100 ; SUBROUTINE 'LITE'
028E- I 101 ; ROUTINE TO MAKE PATTERN OF LIT LEDS BY SHIFTING A STRING OF ONES TO THE
028E- I 102 ; LEFT IN THE ACCUMULATOR UNTIL THE BIT POSITION CORRESPONDING TO THE NUMBER
028E- I 103 ; IN X IS REACHED.
028E- I 104 ;
028E-A9 00 I 105 ( 2) LITE LDA #0 ; CLEAR ACCUMULATOR FOR PATTERN
0290-38 I 106 ( 2) SHIFT SEC ; MAKE LOW BIT HIGH.
0291-2A I 107 ( 2) ROL A ; SHIFT IT IN
0292-CA I 108 ( 2) DEX ; ONE BIT DONE...
0293-D0 FB I 109 (2**) BNE SHIFT ; LOOP IF NOT DONE.
0295-60 I 110 ( 6) RTS ; RETURN
0296- I 111 ;
0296- I 112 ; SUBROUTINE 'TONE'
0296- I 113 ; TONE GENERATION ROUTINE.
0296- I 114 ;
0296-85 03 I 115 ( 2) TONE STA FREQ
0298-A9 00 I 116 ( 2) LDA #0
029A-A6 02 I 117 ( 3) LDX DUR
029C-A4 03 I 118 ( 3) FL2 LDY FREQ
029E-88 I 119 ( 2) FL1 DEY
029F-18 I 120 ( 2) CLC
02A0-90 00 I 121 (2**) BCC FL0 ; (.+2 IN BOOK)
02A2-D0 FA I 122 (2**) FL0 BNE FL1
02A4-49 FF I 123 ( 2) EOR #$FF
02A6-8D 00 CC I 124 ( 4) STA PORT3B
02A9-CA I 125 ( 2) DEX
02AA-D0 F0 I 126 (2**) BNE FL2
02AC-60 I 127 ( 6) RTS
02AD- I 128 ;
02AD- I 129 ; TABLE OF LIMITS FOR CLOSENESS LEVELS.
02AD- I 130 ;
02AD-C8 80 40 20
10 08 04 02
01 I 131 LIMITS .HS C8.80.40.20.10.08.04.02.01
02B6- 15 .IN ../../common/CH01-Getkey/getkey_routine.asm
02B6- I 1 ; 'GETKEY' KEYBOARD INPUT ROUTINE READS AND DEBOUNCES KEYBOARD. RETURNS WITH
02B6- I 2 ; KEY NUMBER IN ACCUMULATOR IF KEY DOWN. OPERATION: SENDS NUMBERS 0-F TO 74154
02B6- I 3 ; (4 TO 16 LINE DECODER), WHICH GROUNDS ONE SIDE OF KEYSWITCHES ONE AT A TIME.
02B6- I 4 ; IF A KEY IS DOWN, PA7 OF VIA #3 WILL BE GROUNDED, AND THE CURRENT VALUE
02B6- I 5 ; APPLIED TO THE 74154 BE THE KEY NUMBER. WHEN THE PROGRAM DETECTS A KEY CLOSE
02B6- I 6 ; CHECKS FOR KEY CLOSURE FOR 50 MS. TO ELIMINATE BOUNCE.
02B6- I 7 ; NOTE: IF NO KEY IS PRESSED, GETKEY WILL WAIT.
02B6- I 8 ;
02B6-2C 01 CC I 9 ( 4) GETKEY BIT PORT3A ; SEE IF KEY IS STILL DOWN FROM LAST KEY CLOSURE:
02B9- I 10 ; KEYSTROBE IN 'N' STATUS BIT.
02B9-10 FB I 11 (2**) BPL GETKEY ; IF YES, WAIT FOR KEY RELEASE
02BB-A2 0F I 12 ( 2) RSTART LDX #15 ; SET KEY COUNTER TO 15
02BD-8E 00 CC I 13 ( 4) NXTKEY STX PORT3B ; OUTPUT KEY # TO 74154
02C0-2C 01 CC I 14 ( 4) BIT PORT3A ; SEE IF KEY DOWN: STROBE IN 'N'
02C3-10 05 I 15 (2**) BPL BOUNCE ; IF YES, GO DEBOUNCE
02C5-CA I 16 ( 2) DEX ; DECREMENT KEY #
02C6-10 F5 I 17 (2**) BPL NXTKEY ; NO, DO NEXT KEY
02C8-30 F1 I 18 (2**) BMI RSTART ; START OVER
02CA-8A I 19 ( 2) BOUNCE TXA ; SAVE KEY NUMBER IN A
02CB-A0 12 I 20 ( 2) LDY #$12 ; OUTER LOOP CNT LOAD FOR DELAY OF 50 MS.
02CD-A2 FF I 21 ( 2) LP1 LDX #$FF ; INNER 11 US. LOOP
02CF-2C 01 CC I 22 ( 4) LP2 BIT PORT3A ; SEE IF KEY STILL DOWN
02D2-30 E7 I 23 (2**) BMI RSTART ; IF NOT, KEY NOT VALID, RESTART
02D4-CA I 24 ( 2) DEX
02D5-D0 F8 I 25 (2**) BNE LP2 ; THIS LOOP USES 2115*5 US.
02D7-88 I 26 ( 2) DEY
02D8-D0 F3 I 27 (2**) BNE LP1 ; OUTER LOOP: TOTAL IS 50 MS.
02DA-60 I 28 ( 6) RTS ; DONE: KEY IN A.
02DB- I 29 ;
02DB- I 30 ; SUBROUTINE 'INITKEY'
02DB- I 31 ; TAKES CARE OF INITIALIZING VIA #3 FOR USING WITH THE GETKEY ROUTINE FROM
02DB- I 32 ; THE CODE.
02DB- I 33 ;
02DB-A9 00 I 34 ( 2) INITKEY LDA #0
02DD-8D 01 CC I 35 ( 4) STA DDR3A ; SET KEY STROBE PORT FOR INPUT
02E0-A9 FF I 36 ( 2) LDA #$FF
02E2-8D 02 CC I 37 ( 4) STA DDR3B ; SET KEYS FOR OUTPUT
02E5-60 I 38 ( 6) RTS

View File

@ -30,6 +30,7 @@ LP2 BIT PORT3A ; SEE IF KEY STILL DOWN
; SUBROUTINE 'INITKEY'
; TAKES CARE OF INITIALIZING VIA #3 FOR USING WITH THE GETKEY ROUTINE FROM
; THE CODE.
;
INITKEY LDA #0
STA DDR3A ; SET KEY STROBE PORT FOR INPUT
LDA #$FF

View File

@ -14,6 +14,10 @@ DUR .EQ $04 ; TEMP STORAGE FOR DURATION
TABEG .EQ $0300 ; TABLE TO STORE MUSIC
PORT3B .EQ VIA3 ; VIA OUTPUT PORT B
DDR3B .EQ VIA3+2 ; VIA PORT B DIRECTION REGISTER
DDR3A .EQ VIA3+3
PORT3A .EQ VIA3+1
PORT3B .EQ VIA3
;
; COMMAND LINE INTERPRETER
; $F AS INPUT MEANS RESET POINTERS, START OVER.

View File

@ -0,0 +1,4 @@
@echo off
sbasm.py hexguess.asm
type hexguess.list
pause

View File

@ -0,0 +1,131 @@
; 'HEXGUESS'
; HEXADECIMAL NUMBER GUESSING GAME.
; THE OBJECT OF THE GAME IS TO GUESS A HEXADECIMAL NUMBER THAT THE COMPUTER HAS
; THOUGHT UP. WHEN THE COMPUTER 'BEEPS', A GUESS SHOULD BE ENTERED. GUESSES ARE
; TWO DIGIT HEXADECIMAL NUMBERS, WHEN TWO DIGITS HAVE BEEN RECEIVED THE
; COMPUTER WILL DISPLAY THE NEARNESS OF THE GUESS BY LIGHTING A NUMBER OF LEDS
; PROPORTIONAL TO THE CLOSENESS OF THE GUESS. TEN GUESSES ARE ALLOWED. IF A
; GUESS IS CORRECT, THEN THE COMPUTER WILL FLASH THE LEDS AND MAKE A WARBLING
; TONE.
;
;
; 6522 VIA #1 ADDRESSES:
TIMER .EQ VIA1+4 ; LOW LATCH OF TIMER 1
DDR1A .EQ VIA1+3 ; PORT A DATA DIRECTION REGISTER
DDR1B .EQ VIA1+3 ; PORT B DATA DIRECTION REGISTER
PORT1A .EQ VIA1+1 ; PORT A
PORT1B .EQ VIA1 ; PORT B
; 6522 VIA #3 ADDRESSES:
DDR3A .EQ VIA3+1 ; PORT A DATA DIRECTION REGISTER
DDR3B .EQ VIA3+2 ; PORT B DATA DIRECTION REGISTER
PORT3B .EQ VIA3 ; PORT B
PORT3A .EQ VIA3+1 ; PORT A
; STORAGES:
ZP .EQ $00
GUESS .EQ ZP
GUESSN .EQ ZP+1
DUR .EQ ZP+2
FREQ .EQ ZP+3
NUMBER .EQ ZP+4
LDA #$FF ; SET UP DATA DIRECTION REGISTERS
STA DDR1A
STA DDR1B
STA DDR3B
STA DUR ; SET UP TONE DURATIONS.
START LDA #$0A ; 10 GUESSES ALLOWED
STA GUESSN
LDA #0 ; BLANK LEDS
STA PORT1A
STA PORT1B
LDA TIMER ; GET RANDOM NUMBER TO GUESS
STA NUMBER ; ... AND SAVE.
GETGES LDA #$20 ; SET UP SHORT HIGH TONE TO SIGNAL USER TO
; INPUT GUESS.
JSR TONE ; MAKE BEEP.
JSR GETKEY ; GET HIGH ORDER USER GUESS
ASL A ; SHIFT INTO HIGH ORDER POSITION
ASL A
ASL A
ASL A
STA GUESS ; SAVE
JSR GETKEY ; GET LOW ORDER USER GUESS
AND #%00001111 ; MASK HIGH ORDER BITS.
ORA GUESS ; ADD HIGH ORDER NIBBLE.
STA GUESS ; FINAL PRODUCT SAVED.
LDA NUMBER ; GET NUMBER FOR COMPARE
SEC ; SUBTRACT GUESS FROM NUMBER TO DETERMINE THE
SBC GUESS ; NEARNESS OF THE GUESS.
BCS ALRIGHT ; POSITIVE VALUE NEEDS NO FIX.
EOR #%11111111 ; MAKE DISTANCE ABSOLUTE
SEC ; MAKE IT A TWO'S COMPLEMENT
ADC #00 ; ... NOT JUST A ONE'S COMPLEMENT.
ALRIGHT LDX #00 ; SET CLOSENESS COUNTER TO DISTANT
LOOP CMP LIMITS,X ; COMPARE NEARNESS OF GUESS TO TABLE OF LIMITS
; TO SEE HOW MANY LIGHTS TO LIGHT.
BCS SIGNAL ; NEARNESS IS BIGGER THAN LIMIT, SO GO
; LIGHT INDICATOR INSTEAD.
INX ; LOOK AT NEXT CLOSENESS LEVEL.
CPX #9 ; ALL NINE LEVELS TRIED?
BNE LOOP ; NO, TRY NEXT LEVEL.
WIN LDA #11 ; YES; WIN! LOAD NUMBER OF BLINKS
STA GUESS ; USE GUESS AS TEMP
LDA #$FF ; LIGHT LEDS
STA PORT1A
STA PORT1B
WOW LDA #50 ; TONE VALUE
JSR TONE ; MAKE WIN SIGNAL
LDA #$FF
EOR PORT1A ; COMPLEMENT PORTS
STA PORT1A
STA PORT1B
DEC GUESS ; BLINKS/TONES DONE?
BNE WOW ; NO, DO AGAIN.
BEQ START ; YES, START NEW GAME.
SIGNAL INX ; INCREMENT CLOSENESS LEVEL COUNTER SO AT
; LEAST 1 LED IS LIT.
LDA #0 ; CLEAR HIGH LED PORT
STA PORT1B
JSR LITE ; GET LED PATTERN
STA PORT1A ; SET LEDS
BCC CC ; IF CARRY SET PB0 = 1
LDA #01
STA PORT1B
CC DEC GUESSN ; ONE GUESS USED
BNE GETGES ; SOME LEFT, GET NEXT.
LDA #$BE ; LOW TONE SIGNALS LOSE
JSR TONE
JMP START ; NEW GAME
;
; SUBROUTINE 'LITE'
; ROUTINE TO MAKE PATTERN OF LIT LEDS BY SHIFTING A STRING OF ONES TO THE
; LEFT IN THE ACCUMULATOR UNTIL THE BIT POSITION CORRESPONDING TO THE NUMBER
; IN X IS REACHED.
;
LITE LDA #0 ; CLEAR ACCUMULATOR FOR PATTERN
SHIFT SEC ; MAKE LOW BIT HIGH.
ROL A ; SHIFT IT IN
DEX ; ONE BIT DONE...
BNE SHIFT ; LOOP IF NOT DONE.
RTS ; RETURN
;
; SUBROUTINE 'TONE'
; TONE GENERATION ROUTINE.
;
TONE STA FREQ
LDA #0
LDX DUR
FL2 LDY FREQ
FL1 DEY
CLC
BCC FL0 ; (.+2 IN BOOK)
FL0 BNE FL1
EOR #$FF
STA PORT3B
DEX
BNE FL2
RTS
;
; TABLE OF LIMITS FOR CLOSENESS LEVELS.
;
LIMITS .HS C8.80.40.20.10.08.04.02.01

View File

@ -0,0 +1,17 @@
.CR 6502
.TF hexguess.hex,hex
.LF hexguess.list
;
; HEX GUESSING GAME USING '6502 GAMES' HARDWARE. BOARD SHOULD BE JUMPERED WITH
; VIA CHIPS AT THE ADDRESSES SPECIFIED BELOW. OTHER THAN THAT THE CODE IS SHOULD
; BE UNCHANGED FROM THE BOOK THOUGH THERE WILL BE SOME DIFFERENCES DUE TO
; ASSEMBLER USED.
;
VIA1 .EQ $C000
VIA3 .EQ $CC00
.OR $0200
.TA $0200
BEGIN JSR INITKEY
.IN game.asm
.IN ../CH01-Getkey/getkey_routine.asm

View File

@ -0,0 +1,15 @@
20DE02A9FF8D03C08D03C08D02CC8502
A90A8501A9008D01C08D00C0AD04C085
04A92020990220B9020A0A0A0A850020
B902290F05008500A50438E500B00549
FF386900A200DDB002B027E8E009D0F6
A90B8500A9FF8D01C08D00C0A9322099
02A9FF4D01C08D01C08D00C0C600D0EC
F09EE8A9008D00C02091028D01C09005
A9018D00C0C601D098A9BE2099024C10
02A900382ACAD0FB608503A900A602A4
0388189000D0FA49FF8D00CCCAD0F060
C880402010080402012C01CC10FBA20F
8E00CC2C01CC1005CA10F530F18AA012
A2FF2C01CC30E7CAD0F888D0F360A900
8D01CCA9FF8D02CC60

View File

@ -0,0 +1,185 @@
0000- 4 ;
0000- 5 ; HEX GUESSING GAME USING '6502 GAMES' HARDWARE. BOARD SHOULD BE JUMPERED WITH
0000- 6 ; VIA CHIPS AT THE ADDRESSES SPECIFIED BELOW. OTHER THAN THAT THE CODE IS SHOULD
0000- 7 ; BE UNCHANGED FROM THE BOOK THOUGH THERE WILL BE SOME DIFFERENCES DUE TO
0000- 8 ; ASSEMBLER USED.
0000- 9 ;
C000- 10 VIA1 .EQ $C000
CC00- 11 VIA3 .EQ $CC00
0000- 12
0200- 13 .OR $0200
0200- 14 .TA $0200
0200-20 DE 02 15 ( 6) BEGIN JSR INITKEY
0203- 16 .IN game.asm
0203- I 1 ; 'HEXGUESS'
0203- I 2 ; HEXADECIMAL NUMBER GUESSING GAME.
0203- I 3 ; THE OBJECT OF THE GAME IS TO GUESS A HEXADECIMAL NUMBER THAT THE COMPUTER HAS
0203- I 4 ; THOUGHT UP. WHEN THE COMPUTER 'BEEPS', A GUESS SHOULD BE ENTERED. GUESSES ARE
0203- I 5 ; TWO DIGIT HEXADECIMAL NUMBERS, WHEN TWO DIGITS HAVE BEEN RECEIVED THE
0203- I 6 ; COMPUTER WILL DISPLAY THE NEARNESS OF THE GUESS BY LIGHTING A NUMBER OF LEDS
0203- I 7 ; PROPORTIONAL TO THE CLOSENESS OF THE GUESS. TEN GUESSES ARE ALLOWED. IF A
0203- I 8 ; GUESS IS CORRECT, THEN THE COMPUTER WILL FLASH THE LEDS AND MAKE A WARBLING
0203- I 9 ; TONE.
0203- I 10 ;
0203- I 11 ;
0203- I 12 ; 6522 VIA #1 ADDRESSES:
C004- I 13 TIMER .EQ VIA1+4 ; LOW LATCH OF TIMER 1
C003- I 14 DDR1A .EQ VIA1+3 ; PORT A DATA DIRECTION REGISTER
C003- I 15 DDR1B .EQ VIA1+3 ; PORT B DATA DIRECTION REGISTER
C001- I 16 PORT1A .EQ VIA1+1 ; PORT A
C000- I 17 PORT1B .EQ VIA1 ; PORT B
0203- I 18 ; 6522 VIA #3 ADDRESSES:
CC01- I 19 DDR3A .EQ VIA3+1 ; PORT A DATA DIRECTION REGISTER
CC02- I 20 DDR3B .EQ VIA3+2 ; PORT B DATA DIRECTION REGISTER
CC00- I 21 PORT3B .EQ VIA3 ; PORT B
CC01- I 22 PORT3A .EQ VIA3+1 ; PORT A
0203- I 23 ; STORAGES:
0000- I 24 ZP .EQ $00
0000- I 25 GUESS .EQ ZP
0001- I 26 GUESSN .EQ ZP+1
0002- I 27 DUR .EQ ZP+2
0003- I 28 FREQ .EQ ZP+3
0004- I 29 NUMBER .EQ ZP+4
0203- I 30
0203-A9 FF I 31 ( 2) LDA #$FF ; SET UP DATA DIRECTION REGISTERS
0205-8D 03 C0 I 32 ( 4) STA DDR1A
0208-8D 03 C0 I 33 ( 4) STA DDR1B
020B-8D 02 CC I 34 ( 4) STA DDR3B
020E-85 02 I 35 ( 2) STA DUR ; SET UP TONE DURATIONS.
0210-A9 0A I 36 ( 2) START LDA #$0A ; 10 GUESSES ALLOWED
0212-85 01 I 37 ( 2) STA GUESSN
0214-A9 00 I 38 ( 2) LDA #0 ; BLANK LEDS
0216-8D 01 C0 I 39 ( 4) STA PORT1A
0219-8D 00 C0 I 40 ( 4) STA PORT1B
021C-AD 04 C0 I 41 ( 4) LDA TIMER ; GET RANDOM NUMBER TO GUESS
021F-85 04 I 42 ( 2) STA NUMBER ; ... AND SAVE.
0221-A9 20 I 43 ( 2) GETGES LDA #$20 ; SET UP SHORT HIGH TONE TO SIGNAL USER TO
0223- I 44 ; INPUT GUESS.
0223-20 99 02 I 45 ( 6) JSR TONE ; MAKE BEEP.
0226-20 B9 02 I 46 ( 6) JSR GETKEY ; GET HIGH ORDER USER GUESS
0229-0A I 47 ( 2) ASL A ; SHIFT INTO HIGH ORDER POSITION
022A-0A I 48 ( 2) ASL A
022B-0A I 49 ( 2) ASL A
022C-0A I 50 ( 2) ASL A
022D-85 00 I 51 ( 2) STA GUESS ; SAVE
022F-20 B9 02 I 52 ( 6) JSR GETKEY ; GET LOW ORDER USER GUESS
0232-29 0F I 53 ( 2) AND #%00001111 ; MASK HIGH ORDER BITS.
0234-05 00 I 54 ( 3) ORA GUESS ; ADD HIGH ORDER NIBBLE.
0236-85 00 I 55 ( 2) STA GUESS ; FINAL PRODUCT SAVED.
0238-A5 04 I 56 ( 3) LDA NUMBER ; GET NUMBER FOR COMPARE
023A-38 I 57 ( 2) SEC ; SUBTRACT GUESS FROM NUMBER TO DETERMINE THE
023B-E5 00 I 58 ( 3) SBC GUESS ; NEARNESS OF THE GUESS.
023D-B0 05 I 59 (2**) BCS ALRIGHT ; POSITIVE VALUE NEEDS NO FIX.
023F-49 FF I 60 ( 2) EOR #%11111111 ; MAKE DISTANCE ABSOLUTE
0241-38 I 61 ( 2) SEC ; MAKE IT A TWO'S COMPLEMENT
0242-69 00 I 62 ( 2) ADC #00 ; ... NOT JUST A ONE'S COMPLEMENT.
0244-A2 00 I 63 ( 2) ALRIGHT LDX #00 ; SET CLOSENESS COUNTER TO DISTANT
0246-DD B0 02 I 64 ( 4*) LOOP CMP LIMITS,X ; COMPARE NEARNESS OF GUESS TO TABLE OF LIMITS
0249- I 65 ; TO SEE HOW MANY LIGHTS TO LIGHT.
0249-B0 27 I 66 (2**) BCS SIGNAL ; NEARNESS IS BIGGER THAN LIMIT, SO GO
024B- I 67 ; LIGHT INDICATOR INSTEAD.
024B-E8 I 68 ( 2) INX ; LOOK AT NEXT CLOSENESS LEVEL.
024C-E0 09 I 69 ( 2) CPX #9 ; ALL NINE LEVELS TRIED?
024E-D0 F6 I 70 (2**) BNE LOOP ; NO, TRY NEXT LEVEL.
0250-A9 0B I 71 ( 2) WIN LDA #11 ; YES; WIN! LOAD NUMBER OF BLINKS
0252-85 00 I 72 ( 2) STA GUESS ; USE GUESS AS TEMP
0254-A9 FF I 73 ( 2) LDA #$FF ; LIGHT LEDS
0256-8D 01 C0 I 74 ( 4) STA PORT1A
0259-8D 00 C0 I 75 ( 4) STA PORT1B
025C-A9 32 I 76 ( 2) WOW LDA #50 ; TONE VALUE
025E-20 99 02 I 77 ( 6) JSR TONE ; MAKE WIN SIGNAL
0261-A9 FF I 78 ( 2) LDA #$FF
0263-4D 01 C0 I 79 ( 4) EOR PORT1A ; COMPLEMENT PORTS
0266-8D 01 C0 I 80 ( 4) STA PORT1A
0269-8D 00 C0 I 81 ( 4) STA PORT1B
026C-C6 00 I 82 ( 5) DEC GUESS ; BLINKS/TONES DONE?
026E-D0 EC I 83 (2**) BNE WOW ; NO, DO AGAIN.
0270-F0 9E I 84 (2**) BEQ START ; YES, START NEW GAME.
0272-E8 I 85 ( 2) SIGNAL INX ; INCREMENT CLOSENESS LEVEL COUNTER SO AT
0273- I 86 ; LEAST 1 LED IS LIT.
0273-A9 00 I 87 ( 2) LDA #0 ; CLEAR HIGH LED PORT
0275-8D 00 C0 I 88 ( 4) STA PORT1B
0278-20 91 02 I 89 ( 6) JSR LITE ; GET LED PATTERN
027B-8D 01 C0 I 90 ( 4) STA PORT1A ; SET LEDS
027E-90 05 I 91 (2**) BCC CC ; IF CARRY SET PB0 = 1
0280-A9 01 I 92 ( 2) LDA #01
0282-8D 00 C0 I 93 ( 4) STA PORT1B
0285-C6 01 I 94 ( 5) CC DEC GUESSN ; ONE GUESS USED
0287-D0 98 I 95 (2**) BNE GETGES ; SOME LEFT, GET NEXT.
0289-A9 BE I 96 ( 2) LDA #$BE ; LOW TONE SIGNALS LOSE
028B-20 99 02 I 97 ( 6) JSR TONE
028E-4C 10 02 I 98 ( 3) JMP START ; NEW GAME
0291- I 99 ;
0291- I 100 ; SUBROUTINE 'LITE'
0291- I 101 ; ROUTINE TO MAKE PATTERN OF LIT LEDS BY SHIFTING A STRING OF ONES TO THE
0291- I 102 ; LEFT IN THE ACCUMULATOR UNTIL THE BIT POSITION CORRESPONDING TO THE NUMBER
0291- I 103 ; IN X IS REACHED.
0291- I 104 ;
0291-A9 00 I 105 ( 2) LITE LDA #0 ; CLEAR ACCUMULATOR FOR PATTERN
0293-38 I 106 ( 2) SHIFT SEC ; MAKE LOW BIT HIGH.
0294-2A I 107 ( 2) ROL A ; SHIFT IT IN
0295-CA I 108 ( 2) DEX ; ONE BIT DONE...
0296-D0 FB I 109 (2**) BNE SHIFT ; LOOP IF NOT DONE.
0298-60 I 110 ( 6) RTS ; RETURN
0299- I 111 ;
0299- I 112 ; SUBROUTINE 'TONE'
0299- I 113 ; TONE GENERATION ROUTINE.
0299- I 114 ;
0299-85 03 I 115 ( 2) TONE STA FREQ
029B-A9 00 I 116 ( 2) LDA #0
029D-A6 02 I 117 ( 3) LDX DUR
029F-A4 03 I 118 ( 3) FL2 LDY FREQ
02A1-88 I 119 ( 2) FL1 DEY
02A2-18 I 120 ( 2) CLC
02A3-90 00 I 121 (2**) BCC FL0 ; (.+2 IN BOOK)
02A5-D0 FA I 122 (2**) FL0 BNE FL1
02A7-49 FF I 123 ( 2) EOR #$FF
02A9-8D 00 CC I 124 ( 4) STA PORT3B
02AC-CA I 125 ( 2) DEX
02AD-D0 F0 I 126 (2**) BNE FL2
02AF-60 I 127 ( 6) RTS
02B0- I 128 ;
02B0- I 129 ; TABLE OF LIMITS FOR CLOSENESS LEVELS.
02B0- I 130 ;
02B0-C8 80 40 20
10 08 04 02
01 I 131 LIMITS .HS C8.80.40.20.10.08.04.02.01
02B9- 17 .IN ../CH01-Getkey/getkey_routine.asm
02B9- I 1 ; 'GETKEY' KEYBOARD INPUT ROUTINE READS AND DEBOUNCES KEYBOARD. RETURNS WITH
02B9- I 2 ; KEY NUMBER IN ACCUMULATOR IF KEY DOWN. OPERATION: SENDS NUMBERS 0-F TO 74154
02B9- I 3 ; (4 TO 16 LINE DECODER), WHICH GROUNDS ONE SIDE OF KEYSWITCHES ONE AT A TIME.
02B9- I 4 ; IF A KEY IS DOWN, PA7 OF VIA #3 WILL BE GROUNDED, AND THE CURRENT VALUE
02B9- I 5 ; APPLIED TO THE 74154 BE THE KEY NUMBER. WHEN THE PROGRAM DETECTS A KEY CLOSE
02B9- I 6 ; CHECKS FOR KEY CLOSURE FOR 50 MS. TO ELIMINATE BOUNCE.
02B9- I 7 ; NOTE: IF NO KEY IS PRESSED, GETKEY WILL WAIT.
02B9- I 8 ;
02B9-2C 01 CC I 9 ( 4) GETKEY BIT PORT3A ; SEE IF KEY IS STILL DOWN FROM LAST KEY CLOSURE:
02BC- I 10 ; KEYSTROBE IN 'N' STATUS BIT.
02BC-10 FB I 11 (2**) BPL GETKEY ; IF YES, WAIT FOR KEY RELEASE
02BE-A2 0F I 12 ( 2) RSTART LDX #15 ; SET KEY COUNTER TO 15
02C0-8E 00 CC I 13 ( 4) NXTKEY STX PORT3B ; OUTPUT KEY # TO 74154
02C3-2C 01 CC I 14 ( 4) BIT PORT3A ; SEE IF KEY DOWN: STROBE IN 'N'
02C6-10 05 I 15 (2**) BPL BOUNCE ; IF YES, GO DEBOUNCE
02C8-CA I 16 ( 2) DEX ; DECREMENT KEY #
02C9-10 F5 I 17 (2**) BPL NXTKEY ; NO, DO NEXT KEY
02CB-30 F1 I 18 (2**) BMI RSTART ; START OVER
02CD-8A I 19 ( 2) BOUNCE TXA ; SAVE KEY NUMBER IN A
02CE-A0 12 I 20 ( 2) LDY #$12 ; OUTER LOOP CNT LOAD FOR DELAY OF 50 MS.
02D0-A2 FF I 21 ( 2) LP1 LDX #$FF ; INNER 11 US. LOOP
02D2-2C 01 CC I 22 ( 4) LP2 BIT PORT3A ; SEE IF KEY STILL DOWN
02D5-30 E7 I 23 (2**) BMI RSTART ; IF NOT, KEY NOT VALID, RESTART
02D7-CA I 24 ( 2) DEX
02D8-D0 F8 I 25 (2**) BNE LP2 ; THIS LOOP USES 2115*5 US.
02DA-88 I 26 ( 2) DEY
02DB-D0 F3 I 27 (2**) BNE LP1 ; OUTER LOOP: TOTAL IS 50 MS.
02DD-60 I 28 ( 6) RTS ; DONE: KEY IN A.
02DE- I 29 ;
02DE- I 30 ; SUBROUTINE 'INITKEY'
02DE- I 31 ; TAKES CARE OF INITIALIZING VIA #3 FOR USING WITH THE GETKEY ROUTINE FROM
02DE- I 32 ; THE CODE.
02DE- I 33 ;
02DE-A9 00 I 34 ( 2) INITKEY LDA #0
02E0-8D 01 CC I 35 ( 4) STA DDR3A ; SET KEY STROBE PORT FOR INPUT
02E3-A9 FF I 36 ( 2) LDA #$FF
02E5-8D 02 CC I 37 ( 4) STA DDR3B ; SET KEYS FOR OUTPUT
02E8-60 I 38 ( 6) RTS