; Uploaded to simtel-20 by Ralph Hyre (ralphw@c.cs.cmu.edu) ; Sent to Ralph by Chris Peck (chris@bingvaxb.bitnet) ; You will need one of the follwing items to use these drivers: ; the PCPI OEM package (bucks involved - order from PCPI) ; the assembled output of the PCPI OEM package assembler. ; (this will be made available here as soon as I can assemble it) .TITLE "VISTA A800 DEVICE DRIVER" ;****************************** ;FILE: VISTA.A65 ;PURP: DEVICE DRIVER FOR VISTA A800 CONTROLLER ; AND 8" DISK DRIVES ; ; ;CHANGES: ; ; 01/16/83 (DJH) ; COMPATABILITY MODE ; ; 12/31/82 (DJH) ; ERROR RECOVERY FIXES ; ; 12/12/82 (DJH) ; CREATED ;******************************* ; BASEP0 .QUERY "ENTER BASE OF PAGE 0: " MODE .QUERY "MODE: 0=NORMAL, 1=COMPATABILITY ?" LENP0 .EQU 4 PAGE0W0 .EQU BASEP0 PAGE0W1 .EQU BASEP0+2 .NOLIST .INCLUDE B:DRVREQUS.A65 .LIST ;EQUATES TRUE .EQU 1 FLASE .EQU 0 SOFTVID .EQU TRUE FDSK .EQU 0 ;DEFAULT FIRST DISK IS A READC .EQU 1 WRITEC .EQU 2 ERRCARD .EQU 1 ;ERROR CODE A800 CARD NOT FOUND ERRAUTO .EQU 2 ;ERROR FROM SELECT ERRWR .EQU 3 ;ERROR FROM WRITE/READ ; VISTA A800 3.0 ROM EQUATES ; ;PAGE ZERO ; PZ0 .EQU 02CH PZ1 .EQU 02DH PZ2 .EQU 02EH PZ3 .EQU 035H PZ4 .EQU 03CH PZ5 .EQU 048H ; ;CP/M PARAMETER PASSING AREA ; CPARM .EQU 03E0H PTRACK .EQU 03E0H PSECT .EQU 03E1H PVOL .EQU 03E2H POVOL .EQU 03E3H PDRV .EQU 03E4H PODRV .EQU 03E5H PSLOT .EQU 03E6H POSLOT .EQU 03E7H PBUFL .EQU 03E8H PBUFH .EQU 03E9H PERROR .EQU 03EAH PCMMD .EQU 03EBH ; ;ROM ENTRY POINTS ; CAUTO .EQU 0C8F4H CRWTS .EQU 0C8FAH ROMVERS .EQU 0C900H .PAGE "DRIVER HEADER BLOCK" BEGDRVR: .WORD 0 ;LOAD ADDRESS (0=RELOCATE) .WORD ((ENDDRVR-BEGDRVR)+0FFH) AND 0FF00H ;LENGTH .BYTE LENP0 ;LENGTH OF PAGE 0 DATA .BYTE 0 ;TAG FIELD (RESERVED -0-) FDISK: .WORD FDSK ;FIRST DISK MDISK: .WORD 8 ;MAXIMUM NUMBER OF DRIVES .WORD INIT ;INITIALIZE .WORD READ ;READ A SECTOR .WORD WRITE ;WRITE A SECTOR .WORD OTHER ;OTHER .WORD POLL ;POLL .WORD 3 ;VERSION NUMBER .IF MODE NAME: .BYTE 15,"VISTA A800 1.2C" ;DRIVER NAME .ELSE NAME: .BYTE 14,"VISTA A800 1.2",0 ;DRIVER NAME .ENDC ;BUFFER SIZE, CHECK SIZE AND ALLOCATION SIZE ; OF EACH DRIVE DEFINED ; .WORD 256 ;HOST BUFFER SIZE .WORD 64 ;CHECK VECTOR SIZE .WORD 72 ;ALLOCATION VECTOR SIZE .WORD 256 ;HOST BUFFER SIZE .WORD 64 ;CHECK VECTOR SIZE .WORD 72 ;ALLOCATION VECTOR SIZE .WORD 256 ;HOST BUFFER SIZE .WORD 64 ;CHECK VECTOR SIZE .WORD 72 ;ALLOCATION VECTOR SIZE .WORD 256 ;HOST BUFFER SIZE .WORD 64 ;CHECK VECTOR SIZE .WORD 72 ;ALLOCATION VECTOR SIZE .WORD 256 ;HOST BUFFER SIZE .WORD 64 ;CHECK VECTOR SIZE .WORD 72 ;ALLOCATION VECTOR SIZE .WORD 256 ;HOST BUFFER SIZE .WORD 64 ;CHECK VECTOR SIZE .WORD 72 ;ALLOCATION VECTOR SIZE .WORD 256 ;HOST BUFFER SIZE .WORD 64 ;CHECK VECTOR SIZE .WORD 72 ;ALLOCATION VECTOR SIZE .WORD 256 ;HOST BUFFER SIZE .WORD 64 ;CHECK VECTOR SIZE .WORD 72 ;ALLOCATION VECTOR SIZE ; MODIFIED BY SETSEEK PROGRAM SEEKRATE: .BYTE 02 ;TRACK TO TRACK SEEK SPEED .PAGE "INITIALIZATION ROUTINE" ;****************************** ;ROUTINE: INIT ;PURP: INITIALIZE ENTRY POINT ;ENTRY: NONE ;EXIT: IF NO ERRORS THEN ; CLC ; ELSE ; SEC ;USED: ALL ;****************************** ;INITIIALIZE INIT: LDA #0 STA CURDISK ;CLEAR CURRENT POINTER STA VISTAFLG ;CLEAR CONTROLLER FLAG LDY MDISK DEY $1: STA TYPEDISK,Y ;CLEAR TYPE TABLE DEY BNE $1 JSR FINDER ;FIND VISTA CONTROLLER CARD JMP EXIT FINDER: LDY #7 FLOOP1: .IF SOFTVID LDA TYPECARD,Y CMP #2 ;IS IT A DISK CONTROL? BNE FLOOP2 ;NO TRY NEXT CARD .ENDC JSR FOUND ;CHECK FOR A800 BCS FLOOP2 ;NO, TRY NEXT CARD RTS ;GOOD -- GOT IT FLOOP2: DEY BNE FLOOP1 LDA #ERRCARD SEC ;NO DISK CARD RTS FOUND: BIT 0CFFFH ;TURN OFF COMMON ROM TYA ;SAVE SLOT # ORA #0C0H ;SET UP ADDR HI .IF SOFTVID .ELSE STA $A+2 .ENDC STA SLOTON STA *+5 ;FIXUP TURN ON CMMD LDA 0C000H ;TURN ON COMMON ROM .IF SOFTVID .ELSE LDX #7 $A: LDA 0C000H,X ;GET TYPE BYTE CMP DISKID,X ;IS IT A DISK? BEQ $B ;YES, KEEP GOING SEC RTS $B: DEX ;CHECK NEXT ID BYTE DEX BPL $A .ENDC ; FOUND A DISK ; IS IT AN A800? ; $0: LDA CAUTO CMP #04CH ;IS IT A JUMP? BEQ $1 ;YES KEEP GOING SEC RTS $1: LDA CRWTS CMP #04CH ;IS IT A JUMP BEQ $2 ;YES, KEEP GOING SEC RTS $2: LDA ROMVERS ;GET ROM VERSION BYTE CMP #030H ;IS IT 3.0? BEQ $3 ;YES, THIS IS IT CMP #010H ;BINARY VERSION? BEQ $3 ;YES, STILL OK SEC ;BAD ROM VERSION RTS $3: STY VISTAFLG ;SET CARD LOCATED FLAG TYA ASL A ASL A ASL A ASL A STA SLOT ;SAVE SLOT * 16 CLC RTS .PAGE "READ/WRITE I/O ROUTINES" ;****************************** ;ROUTINE: READ, WRITE ;PURP: READ AND/OR WRITE A SECTOR ;ENTRY: A = HIGH BYTE OF PARAMETERS ; Y = LOW BYTE OF PARAMETERS ; PARM[OCURDSK] = DRIVE ; PARM[OCURTRK] = TRACK LOW BYTE ; PARM[OCURTRK+1] = TRACK HIGH BYTE ; PARM[OCURSEC] = SECTOR LOW BYTE ; PARM[OCURSEC+1] = SECTOR HIGH BYTE (CURRENTLY 0) ; PARM[OCURDMA] = BUFFER ADDRESS LOW BYTE ; PARM[OCURDMA+1] = BUFFER ADDRESS HIGH BYTE ;EXIT: IF NO ERRORS THEN ; CLC ; ELSE ; SEC ;USED: ALL ;****************************** READ: LDX #READC JMP VIO WRITE: LDX #WRITEC JMP VIO VIO: STY PAGE0W0 ;SAVE PARAM TABLE ADDR STA PAGE0W0+1 LDA VISTAFLG ;GET CONTROLLER FLAG BNE $1 ; LDA #ERRCARD SEC ;ERROR - NO CARD JMP EXIT $1: JSR SAVELOCS ;SAVE PAGE ZERO JSR SETUP ;FORMAT PARAMS FOR ROM BCS $2 ;EXIT IF ERROR JSR CRWTS ;GO TO ROM TO DO I/O LDA PERROR ;GET RETURNED ERROR BNE $2 ;YES, ERROR CLC JMP $3 $2: LDA #ERRWR ;INDICATE ERROR SEC $3: JSR RESTLOCS ;RESTORE PAGE ZERO JMP EXIT .PAGE "EXECUTER 'OTHER' COMMAND" ;****************************** ;ROUTINE: OTHER ;PURP: OTHER COMMANDS ;ENTRY: PARAMETERS ARE READ DIRECTLY FROM Z-80 ;EXIT: IF NO ERRORS THEN ; A = 0 ; ELSE ; A = ERROR NUMBER ;USED: ALL ;****************************** ;OTHER COMMANDS ; OTHER PARAMETERS ARE DEPENDENT ON WHICH ENTRY IS CALLED OTHER: CMP #SNDPRMCMD ;IS THIS THE SEND PARAMETERS COMMAND BNE CHKFRMT ;BIF NOT SEND PARMATERS ;SEND THE HOST AND DISK PARAMETERS ; ENTRY PARAMETERS: ; THE DRIVE NUMBER (1 BYTE) ; EXIT PARAMETERS: ; ERROR CODE (1 BYTE) JSR RD1Z80BYTE ;GET DRIVE # STA CURDISK LDA VISTAFLG ;IS CARD INSTALLED? BNE $1 ;YES, SKIP LDY #00 ;DEFAULT DISK TYPE DS DD JSR SENDBLK ;TRANSMIT PARAM BLOCK LDA #ERRCARD JMP EXIT $1: JSR SAVELOCS ; LDA CURDISK ;GET DRIVE # JSR SELDSK ;SELECT DISK DRIVE LDA SLOT STA PSLOT ;SLOT TO IOB JSR CAUTO ;PERFORM SENSE LDA PERROR ;GET RETURN FROM IOB BPL $2 ;NO ERROR, SKIP LDY #00 ;DEFAULT DISK TYPE DS DD JSR SENDBLK ;TRANSMIT PARAM BLOCK LDA #ERRAUTO JSR RESTLOCS JMP EXIT $2: AND #0F0H ;MASK OFF DRIVE # LDX CURDISK STA TYPEDISK,X ;SAVE DISK TYPE FOR LATER TAX JSR RESTLOCS TXA ;CALCULATE DISK TYPE LSR A ;START 0 SS SD X 0 0 0 0 LSR A LSR A ;FINAL 0 0 0 0 0 SS SD 0 LSR A ; (DISKTYPE * 2) ; LSR A ; ASL A TAY JSR SENDBLK ;SEND THE PARAM BLOCK CLC JMP EXIT SENDBLK: LDA ADRPARMS,Y STA PAGE0W0 LDA ADRPARMS+1,Y STA PAGE0W0+1 LDY #0 STY IDX $1: LDA (PAGE0W0),Y JSR WR1Z80BYTE ;SEND THE NEXT BYTE INC IDX ;INCREMENT TO NEXT BYTE LDY IDX CPY #SZPARMS ;ARE WE DONE ? BNE $1 ;BIF NOT DONE RTS .PAGE CHKFRMT: CMP #FRMTCMD ;FORMAT COMMAND ? BNE CHKNAME ;BIF NOT ;FORMAT A DRIVE ; ENTRY PARAMETERS: ; THE DRIVE NUMBER (1 BYTE) ; EXIT PARAMETERS: ; ERROR CODE (1 BYTE) JSR RD1Z80BYTE ;GET DRIVE LDA #0FFH SEC ;INDICATE AN ERROR (NO FORMTING) JMP EXIT ;CHECK FOR SEND NAME COMMAND CHKNAME: CMP #SNDNAMECMD ;SEND NAME COMMAND ? BNE CHKOTHR ; BIF NOT ; ENTRY PARAMETERS: ; NONE ; EXIT PARAMETERS: ; SEND THE LENGTH OF THE NAME (1 BYTE) ; FOLLOWED BYTE THE NAME (LENGTH NUMBER OF BYTES) ; ERROR CODE (1 BYTE) LDA NAME ;GET LENGTH STA CNT ;SAVE AS COUNT JSR WR1Z80BYTE ;SEND IT TO HOST LDA #1 STA IDX $LP: LDX IDX LDA NAME,X ;GET NEXT CHARACTER JSR WR1Z80BYTE ;WRITE THE NEXT CHARACTER INC IDX DEC CNT BNE $LP ;CONTINUE UNTIL ALL BYTES ARE SENT CLC JMP EXIT CHKOTHR: SEC JMP EXIT .PAGE "POLL ENTRY" ;*********************************** ;ROUTINE: POLLENTRY ;PURP: HANDLE POLLING, THIS ENTRY POINT ; IS CALLED PERIODICALY WHILE THE APPLE IS ; WAITING FOR A COMMAND FROM THE Z-80. THIS ; CODE SHOULD BE VERY SHORT AS THE Z-80 IS ; IGNORED WHILE THIS CODE IS BEING EXECUTED ;ENTRY: NONE ;EXIT: NONE ;USED: ALL ;*********************************** POLL: RTS .PAGE "GENERAL PURPOSE SUBROUTINES" ;************************************ EXIT: BCS ERRXIT LDA #0 ;NO ERRORS RTS ERRXIT: TAY BNE RET ;IF A <> 0 THEN RETURN ; THE SUBROUTINES ERROR CODE ERROR: LDA #0FFH RET: RTS SETUP: STX PCMMD ;COMMAND TO IOB LDA #00 STA PERROR ;CLEAR IOB ERROR STA DENSITY ;DOUBLE DENSITY DEFAULT ;CALCULATE CURDISK LDY #OCURDSK LDA (PAGE0W0),Y ;GET CURRENT DISK JSR SELDSK ;SELECT DISK DRIVE LDA SLOT STA PSLO SLOTNO ;SKIP QUERY IF SLOTNO <> 0 BNE PRESET JSR SETVECTOR ;SET UP VECTORS TO SFTVIDEO R/W MESS: LDY #00 $1: INY LDA MESSAGE,Y ;GET A LETTER FROM MESSAGE JSR APPLEOUT ;DISPLAY IT CPY MESSAGE ;= LENGTH OF MESSAGE? BNE $1 $2: LDA #07 ;BELL CHAR. JSR APPLEOUT JSR APPLEIN ;GET CHARACTER CMP #31H ;LESS THAN ASCII "1"? BCC $2 ;TRY AGAIN CMP #38H ;>= ASCII "8"? BCS $2 ;TRY AGAIN PHA ;APPLEOUT DOESN'T PRESERVE "A" JSR APPLEOUT ;DISPLAY CHOICE PLA SEC SBC #30H ;CONVERT ASCII TO BINARY STA SLOTNO ;AND SET SLOT # ;SET UP ABSOLUTE SLOT ADDRESSES PRESET: LDA SLOTNO ;GET SLOT NUMBER ASL A ASL A ASL A ASL A ;*16 CLC ADC #80H ;ADD 80H FOR TOTAL SLOT OFFSET TAY STY SLTBASE ;INITIALIZE SLTBASE FOR LATER USE STY C0X0A+1 STY C0X0B+1 STY C0X0C+1 STY C0X0D+1 STY C0X0E+1 ;INITIALIZE LOW-ORDER SSD ADDRESS BYTE INY STY C0X1A+1 STY C0X1B+1 STY C0X1C+1 STY C0X1D+1 STY C0X1E+1 ;INITIALIZE HI-ORDER SSD ADDRESS BYTE INY STY C0X2A+1 STY C0X2B+1 STY C0X2C+1 ;BLOCK TO R/W DURING DIRECTORY INITIALIZATION ;TEST THE FIRST 32 BYTES OF SSD BLOCK #1, PAGE #1 (DIRECTORY!) FOR PRESCENCE ;OF THE RAMDISK ID STRING LDA #00 C0X1A: STA 0C081H ;SET HI-BYTE LDY #00 C0X0A: STY 0C080H ;AND LO-BYTE TO 0 C0X2A: LDA 0C082H ;READ BLOCK 1 CMP RAMID,Y ;LOOP UNTIL 16 BYTES OR TEST FAILS BNE $2 ;TEST FAILED, INITIALIZE DIRECTORY INY CPY #32 BNE C0X0A ;FALL THRU IF WE PASSED THE TEST AND RETURN JMP IDONE $2: LDA #0E5H ;FILL THE FIRST 8 PAGES WITH "E5'S" LDX #00 C0X1B: STX 0C081H LDY #00 C0X0B: STY 0C080H C0X2B: STA 0C082H INY BNE C0X0B INX ;DONE WITH 256 BYTES, NEXT PAGE .... CPX #08 BNE C0X1B ;COPY RAMDISK ID OVER THE FIRST 32 BYTES SO A COLDBOOT WON'T REINITIALIZE C0X1C: STY 0C081H ;Y IS ZERO, STy Steven Hirsch w/ acknowledgement s to: * ;* * ;* Wink (Winthrop Saville) * ;* Fred Meyer * ;* Doug Laing * ;* Albert F. Woodhull * ;* * ;************************************************************************ FALSE .EQU 0 ;ASSEMBLY TIME FALSE TRUE .EQU NOT FALSE SIZE144 .EQU FALSE ;SET TRUE TO ASSEMBLE FOR 144K SYNETIX CARD! BASEP0 .QUERY "ENTER BASE OF PAGE 0: " LENP0 .EQU 4 PAGE0W0 .EQU BASEP0 PAGE0W1 .EQU BASEP0+2 ;GET SYSTEM EQUATES .NOLIST .INCLUDE DRVREQUS.A65 .LIST ;EQUATES FDSK .EQU 0 ;DEFAULT FIRST DISK IS A ; ;PAGE ZERO ; RWDMA .EQU 0FEH ;THIS LOCATION WILL HAVE TO BE SAVED ; CONDEV .EQU 19 ;CONSOLE IS DEVICE #19 ;HEADER BEGDRVR: .WORD 0 ;LOAD ADDRESS (0=RELOCATE) .WORD ((ENDDRVR-BEGDRVR)+0FFH) AND 0FF00H ;LENGTH .BYTE LENP0 ;LENGTH OF PAGE 0 DATA .BYTE 0 ;TAG FIELD (FOR FUTURE MUST BE ZERO) FDISK: .WORD FDSK ;FIRST DISK MDISK: .WORD 1 ;MAXIMUM NUMBER OF DRIVES .WORD INIT ;INITIALIZE .WORD READ ;READ A SECTOR .WORD WRITE ;WRITE A SECTOR .WORD OTHER ;OTHER .WORD POLL ;POLL .WORD 6 ;VERSION NUMBER NAME: .BYTE 15,"SYNETIX RAMDISK" ;NAME (MUST BE 15 BYTES PLUS THE ; LENGTH BYTE) ;BUFFER SIZE, CHECK SIZE, AND ALLOCATION SIZE .WORD 256 ;HOST BUFFER SIZE .WORD 0 ;CHECK VECTOR SIZE .WORD 18 ;ALLOCATION VECTOR SIZE ;****************************** ;ROUTINE: INIT ;PURP: INITIALIZE ENTRY POINT ;ENTRY: NONE ;EXIT: IF NO ERRORS THEN ; A = 0 ; ELSE ; A = 0FFH ;USED: ALL ;****************************** ;INITIIALIZE INIT: LDYORE IT IN BOTH LATCHES... C0X0C: STY 0C080H LDA RAMID,Y C0X2C: STA 0C082H INY CPY #32 BNE C0X0C IDONE: LDA #00 ;NO ERRORS RTS ;****************************** ;ROUTINE: READ / WRITE ;PURP: READ OR WRITE A SECTOR ;ENTRY: A = HIGH BYTE OF PARAMETERS ; Y = LOW BYTE OF PARAMETERS ; PARM[OCURDSK] = DRIVE ; PARM[OCURTRK] = TRACK LOW BYTE ; PARM[OCURTRK+1] = TRACK HIGH BYTE ; PARM[OCURSEC] = SECTOR LOW BYTE ; PARM[OCURSEC+1] = SECTOR HIGH BYTE (CURRENTLY 0) ; PARM[OCURDMA] = BUFFER ADDRESS LOW BYTE ; PARM[OCURDMA+1] = BUFFER ADDRESS HIGH BYTE ;EXIT: IF NO ERRORS THEN ; CLC ; ELSE ; SEC ;USED: ALL ;****************************** READ: LDX #00 ;CODE FOR READ OPERATION STX RWFLAG ;SET FLAG JMP RWMAIN WRITE: LDX #01 ;WRITE OPERATION STX RWFLAG ;SET FLAG RWMAIN: STY PAGE0W0 STA PAGE0W0+1 ;SAVE PARAMETER BLOCK ADDRESS JSR SAVELOCS ;SAVE PAGE 0 LOCATIONS JSR SETUP ;SET UP SSD BLOCK#, PAGE OFFSET, AND DMA BCS RWERR LDA PAGENO ;GET PAGE OFFSET LDY FLAG16K ;IS IT IN A 16K BLOCK? BNE RW16K ;64K BLOCK R/W LOOP C0X1D: STA 0C081H ;SET UP HIGH ORDER ADDRESS LATCH LDY #00 ;WE WILL ALWAYS START ON A PAGE BOUNDRY C0X0D: STY 0C080H ;SO SET LOW ORDER LATCH TO ZERO JSR RWCOMM INY BNE C0X0D ;LOOP UNTIL WE TRANSFER 256 BYTES CLC JMP RWDONE ;16K BLOCK R/W LOO