C64 ROM | Routines |
Prev: F8E2 | Up: Map | Next: FA60 |
On Commodore computers, the streams consist of four kinds of symbols that denote different kinds of low-to-high-to-low transitions on the read or write signals of the Commodore cassette interface.
The actual interpretation of the serial data takes a little more work to explain. The typical ROM tape loader (and the turbo loaders) will initialize a timer with a specified value and start it counting down. If either the tape data changes or the timer runs out, an IRQ will occur. The loader will determine which condition caused the IRQ. If the tape data changed before the timer ran out, we have a short pulse, or a "0" bit. If the timer ran out first, we have a long pulse, or a "1" bit. Doing this continuously and we decode the entire file.
|
||||
read T2C which has been counting down from $FFFF. subtract this from $FFFF
|
||||
F92C | AE 07 DC | LDX $DC07 | read VIA 1 timer B high byte | |
F92F | A0 FF | LDY #$FF | set $FF | |
F931 | 98 | TYA | A = $FF | |
F932 | ED 06 DC | SBC $DC06 | subtract VIA 1 timer B low byte | |
F935 | EC 07 DC | CPX $DC07 | compare it with VIA 1 timer B high byte | |
F938 | D0 F2 | BNE $F92C | if timer low byte rolled over loop | |
F93A | 86 B1 | STX $B1 | save tape timing constant max byte | |
F93C | AA | TAX | copy $FF - T2C_l | |
F93D | 8C 06 DC | STY $DC06 | save VIA 1 timer B low byte | |
F940 | 8C 07 DC | STY $DC07 | save VIA 1 timer B high byte | |
F943 | A9 19 | LDA #$19 | load timer B, timer B single shot, start timer B | |
F945 | 8D 0F DC | STA $DC0F | save VIA 1 CRB | |
F948 | AD 0D DC | LDA $DC0D | read VIA 1 ICR | |
F94B | 8D A3 02 | STA $02A3 | save VIA 1 ICR shadow copy | |
F94E | 98 | TYA | Y = $FF | |
F94F | E5 B1 | SBC $B1 | subtract tape timing constant max byte | |
A = $FF - T2C_h
|
||||
F951 | 86 B1 | STX $B1 | save tape timing constant max byte | |
$B1 = $FF - T2C_l
|
||||
F953 | 4A | LSR A | A = $FF - T2C_h >> 1 | |
F954 | 66 B1 | ROR $B1 | shift tape timing constant max byte | |
$B1 = $FF - T2C_l >> 1
|
||||
F956 | 4A | LSR A | A = $FF - T2C_h >> 1 | |
F957 | 66 B1 | ROR $B1 | shift tape timing constant max byte | |
$B1 = $FF - T2C_l >> 1
|
||||
F959 | A5 B0 | LDA $B0 | get tape timing constant min byte | |
F95B | 18 | CLC | clear carry for add | |
F95C | 69 3C | ADC #$3C | ||
F95E | C5 B1 | CMP $B1 | compare with tape timing constant max byte | |
compare with ($FFFF - T2C) >> 2
|
||||
F960 | B0 4A | BCS $F9AC | branch if min + $3C >= ($FFFF - T2C) >> 2 | |
min + $3C < ($FFFF - T2C) >> 2
|
||||
F962 | A6 9C | LDX $9C | get byte received flag | |
F964 | F0 03 | BEQ $F969 | if not byte received ?? | |
F966 | 4C 60 FA | JMP $FA60 | store the tape character | |
F969 | A6 A3 | LDX $A3 | get EOI flag byte | |
F96B | 30 1B | BMI $F988 | ||
F96D | A2 00 | LDX #$00 | ||
F96F | 69 30 | ADC #$30 | ||
F971 | 65 B0 | ADC $B0 | add tape timing constant min byte | |
F973 | C5 B1 | CMP $B1 | compare with tape timing constant max byte | |
F975 | B0 1C | BCS $F993 | ||
F977 | E8 | INX | ||
F978 | 69 26 | ADC #$26 | ||
F97A | 65 B0 | ADC $B0 | add tape timing constant min byte | |
F97C | C5 B1 | CMP $B1 | compare with tape timing constant max byte | |
F97E | B0 17 | BCS $F997 | ||
F980 | 69 2C | ADC #$2C | ||
F982 | 65 B0 | ADC $B0 | add tape timing constant min byte | |
F984 | C5 B1 | CMP $B1 | compare with tape timing constant max byte | |
F986 | 90 03 | BCC $F98B | ||
F988 | 4C 10 FA | JMP $FA10 | ||
F98B | A5 B4 | LDA $B4 | get the bit count | |
F98D | F0 1D | BEQ $F9AC | if all done go ?? | |
F98F | 85 A8 | STA $A8 | save receiver bit count in | |
F991 | D0 19 | BNE $F9AC | branch always | |
F993 | E6 A9 | INC $A9 | increment ?? start bit check flag | |
F995 | B0 02 | BCS $F999 | ||
F997 | C6 A9 | DEC $A9 | decrement ?? start bit check flag | |
F999 | 38 | SEC | ||
F99A | E9 13 | SBC #$13 | ||
F99C | E5 B1 | SBC $B1 | subtract tape timing constant max byte | |
F99E | 65 92 | ADC $92 | add timing constant for tape | |
F9A0 | 85 92 | STA $92 | save timing constant for tape | |
F9A2 | A5 A4 | LDA $A4 | get tape bit cycle phase | |
F9A4 | 49 01 | EOR #%00000001 | ||
F9A6 | 85 A4 | STA $A4 | save tape bit cycle phase | |
F9A8 | F0 2B | BEQ $F9D5 | ||
F9AA | 86 D7 | STX $D7 | ||
F9AC | A5 B4 | LDA $B4 | get the bit count | |
F9AE | F0 22 | BEQ $F9D2 | if all done go ?? | |
F9B0 | AD A3 02 | LDA $02A3 | read VIA 1 ICR shadow copy | |
F9B3 | 29 01 | AND #%00000001 | mask 0000 000x, timer A interrupt enabled | |
F9B5 | D0 05 | BNE $F9BC | if timer A is enabled go ?? | |
F9B7 | AD A4 02 | LDA $02A4 | read VIA 1 CRA shadow copy | |
F9BA | D0 16 | BNE $F9D2 | if ?? just exit | |
F9BC | A9 00 | LDA #$00 | clear A | |
F9BE | 85 A4 | STA $A4 | clear the tape bit cycle phase | |
F9C0 | 8D A4 02 | STA $02A4 | save VIA 1 CRA shadow copy | |
F9C3 | A5 A3 | LDA $A3 | get EOI flag byte | |
F9C5 | 10 30 | BPL $F9F7 | ||
F9C7 | 30 BF | BMI $F988 | ||
F9C9 | A2 A6 | LDX #$A6 | set timimg max byte | |
F9CB | 20 E2 F8 | JSR $F8E2 | set timing | |
F9CE | A5 9B | LDA $9B | ||
F9D0 | D0 B9 | BNE $F98B | ||
F9D2 | 4C BC FE | JMP $FEBC | restore registers and exit interrupt | |
F9D5 | A5 92 | LDA $92 | get timing constant for tape | |
F9D7 | F0 07 | BEQ $F9E0 | ||
F9D9 | 30 03 | BMI $F9DE | ||
F9DB | C6 B0 | DEC $B0 | decrement tape timing constant min byte | |
F9DD | .BYTE $2C | makes next line BIT $B0E6 | ||
F9DE | E6 B0 | INC $B0 | increment tape timing constant min byte | |
F9E0 | A9 00 | LDA #$00 | ||
F9E2 | 85 92 | STA $92 | clear timing constant for tape | |
F9E4 | E4 D7 | CPX $D7 | ||
F9E6 | D0 0F | BNE $F9F7 | ||
F9E8 | 8A | TXA | ||
F9E9 | D0 A0 | BNE $F98B | ||
F9EB | A5 A9 | LDA $A9 | get start bit check flag | |
F9ED | 30 BD | BMI $F9AC | ||
F9EF | C9 10 | CMP #$10 | ||
F9F1 | 90 B9 | BCC $F9AC | ||
F9F3 | 85 96 | STA $96 | save cassette block synchronization number | |
F9F5 | B0 B5 | BCS $F9AC | ||
F9F7 | 8A | TXA | ||
F9F8 | 45 9B | EOR $9B | ||
F9FA | 85 9B | STA $9B | ||
F9FC | A5 B4 | LDA $B4 | ||
F9FE | F0 D2 | BEQ $F9D2 | ||
FA00 | C6 A3 | DEC $A3 | decrement EOI flag byte | |
FA02 | 30 C5 | BMI $F9C9 | ||
FA04 | 46 D7 | LSR $D7 | ||
FA06 | 66 BF | ROR $BF | parity count | |
FA08 | A2 DA | LDX #$DA | set timimg max byte | |
FA0A | 20 E2 F8 | JSR $F8E2 | set timing | |
FA0D | 4C BC FE | JMP $FEBC | restore registers and exit interrupt | |
FA10 | A5 96 | LDA $96 | get cassette block synchronization number | |
FA12 | F0 04 | BEQ $FA18 | ||
FA14 | A5 B4 | LDA $B4 | ||
FA16 | F0 07 | BEQ $FA1F | ||
FA18 | A5 A3 | LDA $A3 | get EOI flag byte | |
FA1A | 30 03 | BMI $FA1F | ||
FA1C | 4C 97 F9 | JMP $F997 | ||
FA1F | 46 B1 | LSR $B1 | shift tape timing constant max byte | |
FA21 | A9 93 | LDA #$93 | ||
FA23 | 38 | SEC | ||
FA24 | E5 B1 | SBC $B1 | subtract tape timing constant max byte | |
FA26 | 65 B0 | ADC $B0 | add tape timing constant min byte | |
FA28 | 0A | ASL A | ||
FA29 | AA | TAX | copy timimg high byte | |
FA2A | 20 E2 F8 | JSR $F8E2 | set timing | |
FA2D | E6 9C | INC $9C | ||
FA2F | A5 B4 | LDA $B4 | ||
FA31 | D0 11 | BNE $FA44 | ||
FA33 | A5 96 | LDA $96 | get cassette block synchronization number | |
FA35 | F0 26 | BEQ $FA5D | ||
FA37 | 85 A8 | STA $A8 | save receiver bit count in | |
FA39 | A9 00 | LDA #$00 | clear A | |
FA3B | 85 96 | STA $96 | clear cassette block synchronization number | |
FA3D | A9 81 | LDA #$81 | enable timer A interrupt | |
FA3F | 8D 0D DC | STA $DC0D | save VIA 1 ICR | |
FA42 | 85 B4 | STA $B4 | ||
FA44 | A5 96 | LDA $96 | get cassette block synchronization number | |
FA46 | 85 B5 | STA $B5 | ||
FA48 | F0 09 | BEQ $FA53 | ||
FA4A | A9 00 | LDA #$00 | ||
FA4C | 85 B4 | STA $B4 | ||
FA4E | A9 01 | LDA #$01 | disable timer A interrupt | |
FA50 | 8D 0D DC | STA $DC0D | save VIA 1 ICR | |
FA53 | A5 BF | LDA $BF | parity count | |
FA55 | 85 BD | STA $BD | save RS232 parity byte | |
FA57 | A5 A8 | LDA $A8 | get receiver bit count in | |
FA59 | 05 A9 | ORA $A9 | OR with start bit check flag | |
FA5B | 85 B6 | STA $B6 | ||
FA5D | 4C BC FE | JMP $FEBC | restore registers and exit interrupt |
Prev: F8E2 | Up: Map | Next: FA60 |