;* ;* ;* * * * * * * * * * * * * * * * * * * * * * * * * * * * ;* * * * * * * * * * * * * * * * * * * * * * * * * * * * ;* * * * ;* * M U S T B E O N P A G E B O U N D A R Y * * ;* * * * ;* * * * * * * * * * * * * * * * * * * * * * * * * * * * ;* * * * * * * * * * * * * * * * * * * * * * * * * * * * ;* * ;* ProDOS DISK ][ Formatter Device Driver * ;* * ;* Copyright Apple Computer, Inc., 1982-1984 * ;* * ;* Enter with ProDOS device number in A-register: * ;* Zero = bits 0, 1, 2, 3 * ;* Slot No.= bits 4, 5, 6 * ;* Drive 1 = bit 7 off * ;* Drive 2 = bit 7 on * ;* * ;* Error codes returned in A-register: * ;* $00 : Good completion * ;* $27 : Unable to format * ;* $2B : Write-Protected * ;* $33 : Drive too SLOW * ;* $34 : Drive too FAST * ;* NOTE: Carry flag is set if error occured. * ;* * ;* Uses zero page locations $D0 thru $DD * ;* * ;* - - - - - - - - - - - - - - - - - - - - - - - - - - * ;* Modified 15 December 1983 to disable interrupts * ;* Modified 20 December 1983 to increase tolerance * ;* of disk speed check * ;* Modified 30 March 1983 to increase tolerance of * ;* disk speed * ;* * * * * * * * * * * * * * * * * * * * * * * * * * * * ; ; Disassembly and annotations by TC (Nov. 2017) ; . disassembly from prodos_utility.dsk (ProDOS 1.1.1) ; ; ; Entrypoint ; Pre: A=slot*16, ($DE)=#$01=volume# ; 7900- 08 PHP 7901- 78 SEI ; interrupt disable 7902- 20 3A 79 JSR $793A 7905- 28 PLP ; restore interrupt ena/dis state 7906- C9 00 CMP #$00 7908- D0 02 BNE $790C 790A- 18 CLC ; res=OK 790B- 60 RTS ; error: 790C- C9 02 CMP #$02 790E- D0 05 BNE $7915 7910- A9 2B LDA #$2B ; MLI error: write protected 7912- 4C 21 79 JMP $7921 ; 7915- C9 01 CMP #$01 7917- D0 05 BNE $791E 7919- A9 27 LDA #$27 ; MLI error: I/O error 791B- 4C 21 79 JMP $7921 ; 791E- 18 CLC 791F- 69 30 ADC #$30 ; =>$33 or $34 7921- 38 SEC ; res=ERROR 7922- 60 RTS ; end ; Seek to track ; Pre: A=trk#, X=slot*16 7923- 0A ASL ; A=half track 7924- 0E 24 7D ASL $7D24 7927- 8D 36 7D STA $7D36 792A- 8A TXA 792B- 4A LSR 792C- 4A LSR 792D- 4A LSR 792E- 4A LSR ; A=slot 792F- A8 TAY ; Y=slot 7930- AD 36 7D LDA $7D36 7933- 20 C6 7A JSR $7AC6 7936- 4E 24 7D LSR $7D24 7939- 60 RTS ; ??? (end) ; FormatDisk (called from Entrypoint) ; Pre: A=slot*16, A.b7=drive# 793A- AA TAX 793B- 29 70 AND #$70 793D- 8D 23 7D STA $7D23 ; set slot*16 7940- 8A TXA 7941- AE 23 7D LDX $7D23 7944- 2A ROL ; C=drive# 7945- A9 00 LDA #$00 7947- 2A ROL 7948- D0 06 BNE $7950 794A- BD 8A C0 LDA $C08A,X ; select drive-1 794D- 4C 53 79 JMP $7953 7950- BD 8B C0 LDA $C08B,X ; select drive-2 ; 7953- BD 89 C0 LDA $C089,X ; motor on 7956- A9 D7 LDA #$D7 7958- 85 DA STA $DA ; ($DA) = #$D7 795A- A9 50 LDA #$50 795C- 8D 24 7D STA $7D24 ; ($7D24) = 80 ; Seek to track 0 795F- A9 00 LDA #$00 7961- 20 23 79 JSR $7923 ; Wait (until motor up to speed?) 7964- A5 DA LDA $DA ; read_vol 7966- F0 06 BEQ $796E 7968- 20 3A 7C JSR $7C3A ; Wait incs read_vol 796B- 4C 64 79 JMP $7964 ; Init vars/consts 796E- A5 DE LDA $DE 7970- 85 D3 STA $D3 ; ($D3) = write_vol = 1 (constant) 7972- A9 AA LDA #$AA 7974- 85 D0 STA $D0 ; ($D0) = #$AA (constant) 7976- AD 20 7D LDA $7D20 ; max_gap3 7979- 18 CLC 797A- 69 02 ADC #$02 797C- 85 D4 STA $D4 ; ($D4) = max_gap3 + 2 797E- A9 00 LDA #$00 7980- 85 D1 STA $D1 ; ($D1) = write_trk = 0 ; Write next track 7982- A5 D1 LDA $D1 7984- AE 23 7D LDX $7D23 7987- 20 23 79 JSR $7923 798A- AE 23 7D LDX $7D23 798D- BD 8D C0 LDA $C08D,X ; load disk write prot to latch(b7=1 => write protected) 7990- BD 8E C0 LDA $C08E,X ; set read mode & read latch 7993- A8 TAY 7994- BD 8E C0 LDA $C08E,X ; set read mode 7997- BD 8C C0 LDA $C08C,X ; read nib to latch & read latch 799A- 98 TYA 799B- 10 05 BPL $79A2 799D- A9 02 LDA #$02 ; Error = write protected 799F- 4C F9 79 JMP $79F9 ; Write track 79A2- 20 63 7C JSR $7C63 79A5- 90 0E BCC $79B5 ; Error... 79A7- A9 01 LDA #$01 79A9- A4 D4 LDY $D4 79AB- CC 1F 7D CPY $7D1F 79AE- B0 02 BCS $79B2 79B0- A9 04 LDA #$04 79B2- 4C F9 79 JMP $79F9 ; error code = 4 (Drive too FAST) ; Succeeded writing track, now check gap3_count tolerance 79B5- A4 D4 LDY $D4 79B7- CC 1F 7D CPY $7D1F 79BA- B0 05 BCS $79C1 79BC- A9 04 LDA #$04 79BE- 4C F9 79 JMP $79F9 ; error code = 4 (Drive too FAST) ; 79C1- CC 20 7D CPY $7D20 79C4- 90 05 BCC $79CB 79C6- A9 03 LDA #$03 79C8- 4C F9 79 JMP $79F9 ; error code = 3 (Drive too SLOW) ; Read a max of 15 (not 16) address fields, looking for sector 0 79CB- AD 22 7D LDA $7D22 ; A = #$10 (constant) 79CE- 8D 25 7D STA $7D25 ; 79D1- CE 25 7D DEC $7D25 79D4- D0 05 BNE $79DB 79D6- A9 01 LDA #$01 79D8- 4C F9 79 JMP $79F9 ; error code = 1 (I/O error) 79DB- AE 23 7D LDX $7D23 79DE- 20 6A 7A JSR $7A6A ; Read address field 79E1- B0 EE BCS $79D1 79E3- A5 D8 LDA $D8 ; sector 0? 79E5- D0 EA BNE $79D1 ; ... no, so keep reading ; Got address field for sector 0: ; Verify sector 79E7- AE 23 7D LDX $7D23 79EA- 20 07 7A JSR $7A07 ; ??? 79ED- B0 E2 BCS $79D1 ; Prep for formatting next track 79EF- E6 D1 INC $D1 ; inc write_trk 79F1- A5 D1 LDA $D1 79F3- C9 23 CMP #$23 ; done 35 tracks? 79F5- 90 8B BCC $7982 ; ... no, so write next track 79F7- A9 00 LDA #$00 ; res = OK 79F9- 48 PHA ; push error code 79FA- AE 23 7D LDX $7D23 79FD- BD 88 C0 LDA $C088,X 7A00- A9 00 LDA #$00 7A02- 20 23 79 JSR $7923 7A05- 68 PLA ; pop error code 7A06- 60 RTS ; end ; ; Verify sector ; ; Read data prologue (D5 AA AD) within 32 nibbles 7A07- A0 20 LDY #$20 7A09- 88 DEY 7A0A- F0 5C BEQ $7A68 7A0C- BD 8C C0 LDA $C08C,X 7A0F- 10 FB BPL $7A0C 7A11- 49 D5 EOR #$D5 7A13- D0 F4 BNE $7A09 7A15- EA NOP 7A16- BD 8C C0 LDA $C08C,X 7A19- 10 FB BPL $7A16 7A1B- C9 AA CMP #$AA 7A1D- D0 F2 BNE $7A11 7A1F- A0 56 LDY #$56 ; Y=#$56 7A21- BD 8C C0 LDA $C08C,X 7A24- 10 FB BPL $7A21 7A26- C9 AD CMP #$AD 7A28- D0 E7 BNE $7A11 ; Read data 7A2A- A9 00 LDA #$00 ; ($D5) = #$FF = Number of #$96 nibbles to read 7A2C- 88 DEY 7A2D- 84 D5 STY $D5 7A2F- BD 8C C0 LDA $C08C,X 7A32- 10 FB BPL $7A2F 7A34- C9 96 CMP #$96 7A36- D0 30 BNE $7A68 7A38- A4 D5 LDY $D5 7A3A- D0 F0 BNE $7A2C ; 7A3C- 84 D5 STY $D5 7A3E- BD 8C C0 LDA $C08C,X 7A41- 10 FB BPL $7A3E 7A43- C9 96 CMP #$96 7A45- D0 21 BNE $7A68 7A47- A4 D5 LDY $D5 7A49- C8 INY 7A4A- D0 F0 BNE $7A3C ; 7A4C- BD 8C C0 LDA $C08C,X 7A4F- 10 FB BPL $7A4C 7A51- C9 96 CMP #$96 7A53- D0 13 BNE $7A68 ; Read data epilogue (DE AA) 7A55- BD 8C C0 LDA $C08C,X 7A58- 10 FB BPL $7A55 7A5A- C9 DE CMP #$DE 7A5C- D0 0A BNE $7A68 ; error 7A5E- EA NOP 7A5F- BD 8C C0 LDA $C08C,X 7A62- 10 FB BPL $7A5F 7A64- C9 AA CMP #$AA 7A66- F0 5C BEQ $7AC4 ; CLC & RTS 7A68- 38 SEC ; error 7A69- 60 RTS ; end ; ; Read address field ; ; Post: ; ($D7) = Chksum ; ($D8) = Sec ; ($D9) = Trk ; ($DA) = Vol ; ; Carry set => error: ; . max nibble count read before addr prologue ; . chksum error ; . addr epilogue not correct ; ; Init: nibble count until error: 3+3*256 = 3+768 = 771 7A6A- A0 FC LDY #$FC 7A6C- 84 DC STY $DC ; Read until address prologue (D5 AA 96) 7A6E- C8 INY 7A6F- D0 04 BNE $7A75 7A71- E6 DC INC $DC 7A73- F0 F3 BEQ $7A68 ; error 7A75- BD 8C C0 LDA $C08C,X 7A78- 10 FB BPL $7A75 7A7A- C9 D5 CMP #$D5 7A7C- D0 F0 BNE $7A6E 7A7E- EA NOP 7A7F- BD 8C C0 LDA $C08C,X 7A82- 10 FB BPL $7A7F 7A84- C9 AA CMP #$AA 7A86- D0 F2 BNE $7A7A 7A88- A0 03 LDY #$03 ; Y=3 7A8A- BD 8C C0 LDA $C08C,X 7A8D- 10 FB BPL $7A8A 7A8F- C9 96 CMP #$96 7A91- D0 E7 BNE $7A7A ; Read 4&4 ; ($D7) = Chksum ; ($D8) = Sec ; ($D9) = Trk ; ($DA) = Vol 7A93- A9 00 LDA #$00 7A95- 85 DB STA $DB ; update chksum 7A97- BD 8C C0 LDA $C08C,X 7A9A- 10 FB BPL $7A97 7A9C- 2A ROL 7A9D- 85 DD STA $DD 7A9F- BD 8C C0 LDA $C08C,X 7AA2- 10 FB BPL $7A9F 7AA4- 25 DD AND $DD 7AA6- 99 D7 00 STA $00D7,Y 7AA9- 45 DB EOR $DB 7AAB- 88 DEY 7AAC- 10 E7 BPL $7A95 ; 7AAE- A8 TAY 7AAF- D0 B7 BNE $7A68 ; chksum error ; Read epilogue (DE AA) 7AB1- BD 8C C0 LDA $C08C,X 7AB4- 10 FB BPL $7AB1 7AB6- C9 DE CMP #$DE 7AB8- D0 AE BNE $7A68 ; error 7ABA- EA NOP 7ABB- BD 8C C0 LDA $C08C,X 7ABE- 10 FB BPL $7ABB 7AC0- C9 AA CMP #$AA 7AC2- D0 A4 BNE $7A68 ; error 7AC4- 18 CLC ; res = OK 7AC5- 60 RTS ; end ; Seek to half track ; Pre: A=half track#, X=slot*16, Y=slot 7AC6- 8E 37 7D STX $7D37 7AC9- 8D 36 7D STA $7D36 7ACC- CD 24 7D CMP $7D24 7ACF- F0 5C BEQ $7B2D 7AD1- A9 00 LDA #$00 7AD3- 8D 38 7D STA $7D38 7AD6- AD 24 7D LDA $7D24 7AD9- 8D 39 7D STA $7D39 7ADC- 38 SEC 7ADD- ED 36 7D SBC $7D36 7AE0- F0 37 BEQ $7B19 7AE2- B0 07 BCS $7AEB 7AE4- 49 FF EOR #$FF 7AE6- EE 24 7D INC $7D24 7AE9- 90 05 BCC $7AF0 7AEB- 69 FE ADC #$FE 7AED- CE 24 7D DEC $7D24 7AF0- CD 38 7D CMP $7D38 7AF3- 90 03 BCC $7AF8 7AF5- AD 38 7D LDA $7D38 7AF8- C9 0C CMP #$0C 7AFA- B0 01 BCS $7AFD 7AFC- A8 TAY 7AFD- 38 SEC 7AFE- 20 1D 7B JSR $7B1D 7B01- B9 4B 7C LDA $7C4B,Y 7B04- 20 3A 7C JSR $7C3A 7B07- AD 39 7D LDA $7D39 7B0A- 18 CLC 7B0B- 20 20 7B JSR $7B20 7B0E- B9 57 7C LDA $7C57,Y 7B11- 20 3A 7C JSR $7C3A 7B14- EE 38 7D INC $7D38 7B17- D0 BD BNE $7AD6 7B19- 20 3A 7C JSR $7C3A 7B1C- 18 CLC 7B1D- AD 24 7D LDA $7D24 7B20- 29 03 AND #$03 7B22- 2A ROL 7B23- 0D 37 7D ORA $7D37 7B26- AA TAX 7B27- BD 80 C0 LDA $C080,X 7B2A- AE 37 7D LDX $7D37 7B2D- 60 RTS ; end ; ; Write gap2, Data field, data ; 7B2E- 20 0E 7D JSR $7D0E 7B31- BD 8D C0 LDA $C08D,X 7B34- BD 8E C0 LDA $C08E,X ; Write gap2 (5x 10-bit FF) 7B37- A9 FF LDA #$FF 7B39- 9D 8F C0 STA $C08F,X 7B3C- DD 8C C0 CMP $C08C,X 7B3F- 48 PHA 7B40- 68 PLA 7B41- EA NOP 7B42- A0 04 LDY #$04 7B44- 48 PHA 7B45- 68 PLA 7B46- 20 A5 7B JSR $7BA5 7B49- 88 DEY 7B4A- D0 F8 BNE $7B44 ; Write Data prologue (D5 AA AD) 7B4C- A9 D5 LDA #$D5 7B4E- 20 A4 7B JSR $7BA4 7B51- A9 AA LDA #$AA 7B53- 20 A4 7B JSR $7BA4 7B56- A9 AD LDA #$AD 7B58- 20 A4 7B JSR $7BA4 ; Write 86 x #$96 7B5B- A0 56 LDY #$56 7B5D- EA NOP 7B5E- EA NOP 7B5F- EA NOP 7B60- D0 03 BNE $7B65 7B62- 20 0E 7D JSR $7D0E ; RTS 7B65- EA NOP 7B66- EA NOP 7B67- A9 96 LDA #$96 7B69- 9D 8D C0 STA $C08D,X 7B6C- DD 8C C0 CMP $C08C,X 7B6F- 88 DEY 7B70- D0 F0 BNE $7B62 ; Write 256 x #$96 7B72- 24 00 BIT $00 7B74- EA NOP 7B75- 20 0E 7D JSR $7D0E ; RTS 7B78- A9 96 LDA #$96 7B7A- 9D 8D C0 STA $C08D,X 7B7D- DD 8C C0 CMP $C08C,X 7B80- A9 96 LDA #$96 7B82- EA NOP 7B83- C8 INY 7B84- D0 EF BNE $7B75 ; Write Data epilogue (DE AA EB FF) 7B86- 20 A4 7B JSR $7BA4 7B89- A9 DE LDA #$DE 7B8B- 20 A4 7B JSR $7BA4 7B8E- A9 AA LDA #$AA 7B90- 20 A4 7B JSR $7BA4 7B93- A9 EB LDA #$EB 7B95- 20 A4 7B JSR $7BA4 7B98- A9 FF LDA #$FF 7B9A- 20 A4 7B JSR $7BA4 ; 7B9D- BD 8E C0 LDA $C08E,X ; read latch (and set read mode) 7BA0- BD 8C C0 LDA $C08C,X ; read latch 7BA3- 60 RTS ; Write nibble 7BA4- EA NOP ; Write nibble 7BA5- 48 PHA 7BA6- 68 PLA 7BA7- 9D 8D C0 STA $C08D,X 7BAA- DD 8C C0 CMP $C08C,X 7BAD- 60 RTS ; ; Write gap1(sector-0) or gap3 & address field ; Pre: X=slot*16, Y=gap count ; ; Check if disk is write enabled 7BAE- 38 SEC ; ? (2 cycles) 7BAF- BD 8D C0 LDA $C08D,X ; load write protect to latch (b7) 7BB2- BD 8E C0 LDA $C08E,X ; read latch (and set read mode) 7BB5- 30 5E BMI $7C15 ; branch if write protected ; Gap1 or Gap3: Initial 10-bit FF sync byte 7BB7- A9 FF LDA #$FF 7BB9- 9D 8F C0 STA $C08F,X ; set write mode & write data to latch 7BBC- DD 8C C0 CMP $C08C,X ; start writing latch (start shifting) 7BBF- 48 PHA 7BC0- 68 PLA ; Gap1 or Gap3: 10-bit FF sync byte (40 cycle loop) ; Pre: A=#$FF, Y=gap count 7BC1- 20 1B 7C JSR $7C1B ; RTS 7BC4- 20 1B 7C JSR $7C1B ; RTS 7BC7- 9D 8D C0 STA $C08D,X ; write data to latch 7BCA- DD 8C C0 CMP $C08C,X ; start writing latch (start shifting) 7BCD- EA NOP 7BCE- 88 DEY 7BCF- D0 F0 BNE $7BC1 ; NB. branch taken cross pages ; Write address prologue (D5 AA 96) 7BD1- A9 D5 LDA #$D5 7BD3- 20 2D 7C JSR $7C2D 7BD6- A9 AA LDA #$AA 7BD8- 20 2D 7C JSR $7C2D 7BDB- A9 96 LDA #$96 7BDD- 20 2D 7C JSR $7C2D ; Write address field 7BE0- A5 D3 LDA $D3 ; Vol=01 7BE2- 20 1C 7C JSR $7C1C 7BE5- A5 D1 LDA $D1 ; Trk 7BE7- 20 1C 7C JSR $7C1C 7BEA- A5 D2 LDA $D2 ; Sec 7BEC- 20 1C 7C JSR $7C1C 7BEF- A5 D3 LDA $D3 7BF1- 45 D1 EOR $D1 7BF3- 45 D2 EOR $D2 7BF5- 48 PHA ; Chksum 7BF6- 4A LSR 7BF7- 05 D0 ORA $D0 ; OR with #$AA ; write 4&4 chksum in A 7BF9- 9D 8D C0 STA $C08D,X 7BFC- BD 8C C0 LDA $C08C,X 7BFF- 68 PLA 7C00- 09 AA ORA #$AA 7C02- 20 2C 7C JSR $7C2C ; write address epilogue (DE AA EB) 7C05- A9 DE LDA #$DE 7C07- 20 2D 7C JSR $7C2D 7C0A- A9 AA LDA #$AA 7C0C- 20 2D 7C JSR $7C2D 7C0F- A9 EB LDA #$EB 7C11- 20 2D 7C JSR $7C2D 7C14- 18 CLC 7C15- BD 8E C0 LDA $C08E,X 7C18- BD 8C C0 LDA $C08C,X 7C1B- 60 RTS ; write 4&4 byte in A 7C1C- 48 PHA 7C1D- 4A LSR 7C1E- 05 D0 ORA $D0 7C20- 9D 8D C0 STA $C08D,X 7C23- DD 8C C0 CMP $C08C,X 7C26- 68 PLA 7C27- EA NOP 7C28- EA NOP 7C29- EA NOP 7C2A- 09 AA ORA #$AA 7C2C- EA NOP ; fall through... ; 32 cycle write 7C2D- EA NOP 7C2E- 48 PHA 7C2F- 68 PLA 7C30- 9D 8D C0 STA $C08D,X 7C33- DD 8C C0 CMP $C08C,X 7C36- 60 RTS ; end ; ??? (unused) 7C37- C8 INY 7C38- A0 C3 LDY #$C3 ; ??? (end) ; Wait: A * (2 + (5*16) + 5+3+5+2+2+3) = A * 102 cycles (roughly) ; Pre: A = wait value 7C3A- A2 11 LDX #$11 ; 2cy 7C3C- CA DEX ; 2cy 7C3D- D0 FD BNE $7C3C ; 2+1 (branch taken) 7C3F- E6 D9 INC $D9 ; 5cy / read_trk++ 7C41- D0 02 BNE $7C45 ; 2+1 (branch taken) 7C43- E6 DA INC $DA ; 5cy / read_vol++ 7C45- 38 SEC ; 2cy 7C46- E9 01 SBC #$01 ; 2cy 7C48- D0 F0 BNE $7C3A ; 2+1 (branch taken) 7C4A- 60 RTS ; end .data 7C4B: ; 12 bytes !byte $01,$30,$28 !byte $24,$20,$1E !byte $1D,$1C,$1C !byte $1C,$1C,$1C 7C57: ; 12 bytes !byte $70,$2C,$26 !byte $22,$1F,$1E !byte $1D,$1C,$1C !byte $1C,$1C,$1C .code ; ; Write track and verify track ; ; write gap1 & address field 7C63- AD 21 7D LDA $7D21 7C66- 85 D6 STA $D6 ; ($D6) = 3 = timeout * 256? ; 7C68- A0 80 LDY #$80 ; gap1 has gap count = 128 7C6A- A9 00 LDA #$00 7C6C- 85 D2 STA $D2 ; sector = 0 7C6E- 4C 73 7C JMP $7C73 ; write gap3 & address field 7C71- A4 D4 LDY $D4 ; gap3_count ; 7C73- AE 23 7D LDX $7D23 ; slot*16 7C76- 20 AE 7B JSR $7BAE ; write gap1|3 & address field 7C79- 90 03 BCC $7C7E ; error: 7C7B- 4C 0E 7D JMP $7D0E ; success: ; write gap2, data field, data 7C7E- AE 23 7D LDX $7D23 7C81- 20 2E 7B JSR $7B2E 7C84- E6 D2 INC $D2 ; inc write_sector 7C86- A5 D2 LDA $D2 7C88- C9 10 CMP #$10 ; done 16 sectors? 7C8A- 90 E5 BCC $7C71 ; ... no, write next gap3 & sector ; ; verify track ; 7C8C- A0 0F LDY #$0F 7C8E- 84 D2 STY $D2 ; write_sector = 15 (used as sector loop counter) 7C90- AD 22 7D LDA $7D22 ; A = #$10 (constant) 7C93- 8D 25 7D STA $7D25 ; Set retry count = #$10 ; Fill sector_flag struct with #$10 7C96- 99 26 7D STA $7D26,Y 7C99- 88 DEY 7C9A- 10 FA BPL $7C96 7C9C- A5 D4 LDA $D4 ; gap3_count 7C9E- 38 SEC 7C9F- E9 05 SBC #$05 7CA1- A8 TAY ; Delay for: (gap3_count-5) * 40 cycles 7CA2- 20 0E 7D JSR $7D0E ; 12cy / RTS 7CA5- 20 0E 7D JSR $7D0E ; 12cy / RTS 7CA8- 48 PHA ; 3 7CA9- 68 PLA ; 4 7CAA- EA NOP ; 2 7CAB- EA NOP ; 2 7CAC- 88 DEY ; 2 7CAD- D0 F3 BNE $7CA2 ; 3 (taken) ; = 40 cycles 7CAF- AE 23 7D LDX $7D23 7CB2- 20 6A 7A JSR $7A6A ; Read address field 7CB5- B0 3C BCS $7CF3 7CB7- A5 D8 LDA $D8 7CB9- F0 13 BEQ $7CCE ; read sector 0? ; ... No: 7CBB- C6 D4 DEC $D4 ; gap3_count-- 7CBD- A5 D4 LDA $D4 7CBF- CD 1F 7D CMP $7D1F 7CC2- B0 2F BCS $7CF3 ; rewrite track 7CC4- 38 SEC ; error: gap3_count too small 7CC5- 60 RTS ; Verify next sector 7CC6- AE 23 7D LDX $7D23 7CC9- 20 6A 7A JSR $7A6A ; Read address field 7CCC- B0 1A BCS $7CE8 ; 7CCE- AE 23 7D LDX $7D23 7CD1- 20 07 7A JSR $7A07 ; Read sector data 7CD4- B0 12 BCS $7CE8 7CD6- A4 D8 LDY $D8 ; Y=read sector# 7CD8- B9 26 7D LDA $7D26,Y 7CDB- 30 0B BMI $7CE8 ; -ve if already read this sector 7CDD- A9 FF LDA #$FF 7CDF- 99 26 7D STA $7D26,Y ; sector_flag[Y] := #$FF 7CE2- C6 D2 DEC $D2 ; write_sector-- 7CE4- 10 E0 BPL $7CC6 7CE6- 18 CLC ; res = OK 7CE7- 60 RTS ; 7CE8- CE 25 7D DEC $7D25 ; retry_count-- 7CEB- D0 D9 BNE $7CC6 7CED- C6 D6 DEC $D6 7CEF- D0 02 BNE $7CF3 7CF1- 38 SEC ; error (timeout) 7CF2- 60 RTS ; Retry 32 times to read sector #$0F ; On success: rewrite track 7CF3- AD 22 7D LDA $7D22 ; A = #$10 (constant) 7CF6- 0A ASL ; A = #$20 7CF7- 8D 25 7D STA $7D25 ; Set retry count = #$20 ; 7CFA- AE 23 7D LDX $7D23 7CFD- 20 6A 7A JSR $7A6A ; Read address field 7D00- B0 06 BCS $7D08 7D02- A5 D8 LDA $D8 7D04- C9 0F CMP #$0F ; read sector == #$0F? (ie. last sector on track) 7D06- F0 07 BEQ $7D0F ; ... yes: wait & rewrite track 7D08- CE 25 7D DEC $7D25 7D0B- D0 ED BNE $7CFA 7D0D- 38 SEC ; error 7D0E- 60 RTS ; ; wait for 214 x 32-cycle nibbles 7D0F- A2 D6 LDX #$D6 ; = 214 7D11- 20 0E 7D JSR $7D0E ; 12cy / RTS 7D14- 20 0E 7D JSR $7D0E ; 12cy / RTS 7D17- 24 00 BIT $00 ; 3cy 7D19- CA DEX ; 2cy 7D1A- D0 F5 BNE $7D11 ; 3cy (2+1taken) ; = 32 ; JMP to Write track and verify track 7D1C- 4C 68 7C JMP $7C68 ; end .data 7D1F: 0E ; min gap3 7D20: 1B ; max gap3 (gap3 >= 0x1B means DRIVE TOO SLOW) 7D21: 03 ; timeout * 256 7D22: 10 ; a constant 7D23: 80 ; slot*10 7D24: A0 ; gets init'd to #$50 (80) 7D25: A0 ; retry count ; sector_flag[16]: 7D26: A0 B1 C5 A0 7D2A: A0 C4 A0 B0 7D2E: 80 A0 A0 C3 7D32: A0 A0 A0 A0 7D36: A0 7D37: A0 7D38: A0 7D39: A0 ; Symbol table: D0 kAA D1 w_Track D2 w_Sector D3 w_Volume D4 w_Gap3Count D5 r_Nib96Count D6 r_NibCount1Hi D7 r_Chksum D8 r_Sector D9 r_Track DA r_Volume DB r_TmpChksum DC r_NibCount2Hi DD r_Tmp4and4 DE kVolNum01 7900 FormatterDiskII 7923 SeekTrack 793A FormatDisk 7982 WriteNextTrack 79A2 WriteTrack 79B5 CheckGap3Count 79CB FindSector00Init 79D1 FindSector00Cont 79E7 VerifySector 79EF NextTrack 79F9 Done 7A07 ReadSectorData 7A6A ReadAddressField 7AC6 SeekHalfTrack 7B2E WriteGap2AndData 7BA4 WriteNibble1a 7BA5 WriteNibble1b 7BAE CheckWriteProt 7BB7 WriteGap0Or3AndAddress 7C2C WriteNibble2a 7C2D WriteNibble2b 7C37 Unused3 7C3A WaitA 7C4B Data12_1 7C57 Data12_2 7C63 WriteAndVerifyTrack 7C68 WriteGap1AndAddress2 7C71 WriteGap3AndAddress 7C8C VerifyTrack 7C96 ResetSectorFlags 7CA2 WaitGap3Count 7CBB DecGap3Count 7CC6 VerifyNextSector 7CCE VerifyNextSector2 7CE8 Retry 7CF3 Retry2 7CFA FindSector0FCont 7D0E RTS 7D0F RetryWait 7D1F kMinGap3 7D20 kMaxGap3 7D21 kNibCountHi 7D22 k10 7D23 Slotx16 7D24 HalfTrack 7D25 RetryCount 7D26 SectorFlags