From c6e7cb4c7cfa486eb8ef1c008d03579c287764d6 Mon Sep 17 00:00:00 2001 From: Joshua Bell Date: Fri, 24 Nov 2017 23:12:12 -0800 Subject: [PATCH] Add separate sys source; resolves #1, #2 --- .gitignore | 7 ++ Makefile | 4 +- cricket.system.s | 141 ++++++++++++++++++++++++++++++++++++++ cricket.s => prodos.mod.s | 15 ++-- 4 files changed, 158 insertions(+), 9 deletions(-) create mode 100644 .gitignore create mode 100644 cricket.system.s rename cricket.s => prodos.mod.s (92%) diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..8bb62f8 --- /dev/null +++ b/.gitignore @@ -0,0 +1,7 @@ +# Reference copy of original binary +orig + +# Output files +*.SYS +*.BIN +*.list diff --git a/Makefile b/Makefile index b292002..6e8e67c 100644 --- a/Makefile +++ b/Makefile @@ -3,7 +3,7 @@ CC65 = ~/dev/cc65/bin CAFLAGS = --target apple2enh --list-bytes 0 CCFLAGS = --config apple2-asm.cfg -TARGETS = cricket.SYS +TARGETS = cricket.system.SYS prodos.mod.BIN .PHONY: clean all all: $(TARGETS) @@ -17,5 +17,5 @@ clean: %.o: %.s $(HEADERS) $(CC65)/ca65 $(CAFLAGS) --listing $(basename $@).list -o $@ $< -%.SYS: %.o +%.BIN %.SYS: %.o $(CC65)/ld65 $(CCFLAGS) -o $@ $< diff --git a/cricket.system.s b/cricket.system.s new file mode 100644 index 0000000..43a1516 --- /dev/null +++ b/cricket.system.s @@ -0,0 +1,141 @@ +;;; The Cricket Clock - ProDOS System +;;; Adapted from /CRICKET/PRODOS.MOD +;;; Original: Street Electronics Corporation (C) 1984 + + .setcpu "6502" + .include "apple2.inc" + + .org $2000 ; System files start at $2000 + + ;; ProDOS System Global Page +PRODOS := $BF00 ; MLI entry point +DATETIME := $BF06 ; CLOCK CALENDAR ROUTINE. +DATELO := $BF90 ; BITS 15-9=YR, 8-5=MO, 4-0=DAY +TIMELO := $BF92 ; BITS 12-8=HR, 5-0=MIN; LOW-HI FORMAT. + + ;; SSC I/O Registers (for Slot 2) +TDREG := $C088 + $20 ; ACIA Transmit Register (write) +RDREG := $C088 + $20 ; ACIA Receive Register (read) +STATUS := $C089 + $20 ; ACIA Status/Reset Register +COMMAND := $C08A + $20 ; ACIA Command Register (read/write) +CONTROL := $C08B + $20 ; ACIA Control Register (read/write) + +.proc install + ptr := $42 + + ;; Copy driver to target in ProDOS + lda DATETIME+1 + sta ptr + lda DATETIME+2 + sta ptr+1 + lda #$4C ; JMP opcode + sta DATETIME + lda ROMIN ; Write bank 2 + lda ROMIN + ldy #sizeof_driver-1 +loop: lda driver,y + sta (ptr),y + dey + bpl loop + + ;; Exit via ProDOS to chain to next .SYSTEM file on startup +exit: jsr PRODOS ; Call the MLI + .byte $65 ; CALL TYPE = QUIT + .addr parmtable ; Pointer to parameter table +parmtable: + .byte 4 ; Number of parameters is 4 + .byte 0 ; 0 is the only quit type + .word 0000 ; Pointer reserved for future use + .byte 0 ; Byte reserved for future use + .word 0000 ; Pointer reserved for future use +.endproc + + ;; Driver - relocatable code. Called by ProDOS to update date/time bytes +.proc driver + scratch := $3A ; ZP scratch location + + ;; Initialize + php + sei + lda COMMAND ; save status of command register + pha + + ;; Configure SSC + lda #%00001011 + sta COMMAND + lda #%10011110 ; 9600 baud, 8 data bits, 2 stop bits + sta CONTROL +: lda STATUS + and #(1 << 4) ; transmit register empty? (bit 4) + beq :- ; nope, keep waiting + + ;; Send command + lda #('@' | $80) ; '@' command + sta TDREG + + read_len := 7 ; read 7 bytes (w/m/d/y/H/M/S) + + ;; Read response, pushing to stack + ldy #(read_len-1) + +rloop: ldx #0 ; x = retry loop counter low byte + lda #3 ; scratch = retry loop counter high byte + sta scratch ; ($300 iterations total) + +check: lda STATUS ; did we get it? + and #(1 << 3) ; receive register full? (bit 3) + bne ready ; yes, we read the value + + inx ; not yet, so keep trying + bne check ; until counter runs out + dec scratch + bne check + + ;; Read failed - restore stack and exit +reset: cpy #(read_len-1) ; anything left to restore? + beq done ; nope, exit + pla ; yep, clear it off the stack + iny + bne reset + + ;; Read succeeded - stuff it on the stack and continue +ready: lda RDREG + pha + dey + bpl rloop + + ;; Convert pushed response to ProDOS time field + pla ; day of week (unused) + + pla ; minute + sta TIMELO ; -- stored as-is (TIMELO 5-0) + + pla ; hour + sta TIMELO+1 ; -- stored as-is (TIMELO 12-8) + + pla ; year + sta DATELO+1 ; -- will be shifted up by 1 (DATELO 15-9) + + pla ; day + and #%00011111 ; -- masked, stored as is (DATELO 4-0) + sta DATELO + + pla ; month + asl a ; -- shifted up (DATELO 8-5) + asl a + asl a + asl a + asl a + ora DATELO ; -- merge low 5 bits + sta DATELO + rol DATELO+1 + + pla ; seconds (unused) + + ;; Restore prior state +done: pla ; restore saved command state + sta COMMAND + plp + rts +.endproc + sizeof_driver := .sizeof(driver) diff --git a/cricket.s b/prodos.mod.s similarity index 92% rename from cricket.s rename to prodos.mod.s index 200bec3..71ba047 100644 --- a/cricket.s +++ b/prodos.mod.s @@ -1,13 +1,10 @@ -;;; The Cricket Clock Driver -;;; Adapted from /CRICKET/PRODOS.MOD +;;; The Cricket Clock - ProDOS Patcher +;;; Disassembled from /CRICKET/PRODOS.MOD ;;; Original: Street Electronics Corporation (C) 1984 .setcpu "6502" .include "apple2.inc" - ;; TODO: - ;; * Move ORG to $2000 - ;; * Exit installer with MLI QUIT call .org $300 ;; ProDOS System Global Page @@ -25,22 +22,26 @@ CONTROL := $C08B + $20 ; ACIA Control Register (read/write) .proc install ptr := $42 + ;; Copy driver to target in ProDOS lda DATETIME+1 sta ptr lda DATETIME+2 sta ptr+1 lda #$4C ; JMP opcode sta DATETIME - lda ROMIN + lda ROMIN ; Write bank 2 lda ROMIN ldy #sizeof_driver-1 loop: lda driver,y sta (ptr),y dey bpl loop - rts ; TODO: Replace with MLI QUIT call + + ;; Simple exit when BRUN + rts .endproc + ;; Driver - relocatable code. Called by ProDOS to update date/time bytes .proc driver scratch := $3A ; ZP scratch location