/OS/8 RX01 DEVICE DRIVER (BYTE MODE) C.E.S.D. /THIS IS A NON-SYSTEM DEVICE DRIVER FOR THE RX01 DISKS /THAT DRIVES THE RX8 FLOPPY DISKS IN BYTE MODE, UTILIZING /TRACK 0, YEILDING SUBSTANTIALLY MORE STORAGE ON THE FLOPPY DISK: /A NON-SYSTEM DISCETTE WILL HOLD 667 OS/8 BLOCKS /FURTHERMORE, A SECTOR INTERLACE FACTOR OF TWO IS STILL MAINTAINED /WHICH MEANS THAT THE EFFECTIVE SPEED OF THE I/O TRANSFER IS /ALSO INCREASED. /COPYRIGHT (C) 1976, BY: DEWAR INFORMATION SYSTEMS CORPORATION /THIS SOFTWARE IS FURNISHED TO THE PURCHASER UNDER A LICENSE /FOR USE ONLY ON COMPUTERS AT PURCHASER'S PLACE OF BUSINESS AND CAN /BE COPIED (WITH INCLUSION OF DISC'S COPYRIGHT NOTICE) ONLY FOR USE /IN SUCH SYSTEMS, EXCEPT AS MAY BE OTHERWISE PROVIDED FOR IN WRITING /BY DISC. /NOTE: THIS HANDLER USES TRACK ZERO. TO SKIP TRACK ZERO, CHANGE THE /INSTRUCTION AT THE TAG 'TRACK0' TO READ 'CLA IAC' /BUG WITH FULL FIELD TRANSFERS FIXED BY J.V.Z. VERSION B (9-AUG-78) /IN ORDER TO ZERO THE DIRECTORY OF A DEVICE, THE FOLLOWING CHANGE /MUST BE MADE TO THE OS/8 PIP.SV PROGRAM: / .GET SYS PIP / .ODT / 13650/XXXX 6545 -# OF LAST BLOCK ON DEVICE / ^C / .SAVE SYS PIP / / HEADER BLOCK DEFINITION PAGE 0 -2 /TWO HANDLERS, R0: AND R1: DEVICE RX8 /GROUP NAME FOR HANDLER DEVICE R0 /DEVICE NAME 4500 /FILE-STRUCTURED, DEVICE TYPE 50 4001 /TWO-PAGE HANDLER, ENTRY POINT AT 1 0 /THIS WORD IS ALWAYS ZERO 0 /(ZERO SINCE NOT A SYSTEM HANDLER) DEVICE RX8 /ALL THE SAME AS THE ABOVE DEVICE R1 /EXCEPT THE NAME IS DIFFERENT 4500 4006 /AND THE ENTRY POINT IS AT LOCATION 6 ZBLOCK 2 / DEFINE I/O INSTRUCTION CODES RX8= 75^10 /DEFINE DEVICE ADDRESS LCD= 1 /LOAD COMMAND REGISTER XDR= 2 /TRANSFER DATA STR= 3 /SKIP ON TRANSFER FLAG UP, CLEAR FLAG SER= 4 /SKIP ON ERRORR SDN= 5 /SKIP ON DONE FLAG, CLEAR DONE FLAG INIT= 7 /GENERATE INITIAALIZE PULSE PAGE / FIRST PAGE OF I/O HANDLER P3700, 3700 /CONSTANT / ENTER BELOW FOR 'R0' DRIVER DRIVE, /DRIVE INFORMATION SHARES CELL RX8A, 2 /VERSION ID P7600, 7600 /CONSTANT, ALSO CLEARS AC (GROUP 2 'CLA') TAD RX8A /GET CALLING ADDRESS DCA RX8B /SIMULATE CALL TO 'R1' DRIVER JMP IF /OFF TO SET UNIT ZERO / ENTER HERE FOR THE 'R1' DRIVER RX8B, 2 /VERSION NO. CLA /ENSURE AC IS CLEAR TAD P20 /SET DRIVE NUMBER TO DRIVE 1 IF, TAD P104 /SET BYTE MODE, DEFAULT TO WRITE FUNCTION DCA DRIVE /MERGE HERE TO SET NUMBER TO DRIVE ZERO RDF /GET CALLING FIELD TAD PCDI /BUILD 'CDI' RETURN INSTRUCTION DCA REXIT /STORE FOR RETURN RDF /SET AGAIN FOR LOOPING ON ERROR TAD PCDF /BUILD CDF TO CALLER'S FIELD DCA AGAIN /AND STORE IT D0, JMS TEMP /INITIALIZE FIRST TIME THROUGH, ZAPPED LATER RETDO, STA CLL RTL /SET FOR THREE RETRIES ON ERROR DCA REPEAT / MERGE BACK HERE WITH MINUS 3 IN THE AC TO REPEAT AFTER AN / ERROR; THIS ALLOWS ALL THE ARGUMENTS TO BE RECONSTITUTED AGAIN, HLT /SET 'CDF' TO CALLER'S FIELD NOW TAD RX8B /RESET ARGUMENT POINTER IF NECESSARY DCA RX8B /... / GET WORD COUNT FOR THE TRANSFER TAD I RX8B /GET FUNCTION WORD AND P3700 /ISOLATE RECORD COUNT SNA /ZERO? STL RAR /SET UP FOR FULL FIELD CIA /NEGATE AND SET AS DCA WC /WORD COUNT (DIVIDED BY TWO) / GET MEMORY FIELD FOR DATA TRANSFER, ALSO SET/CLEAR LINK AT / THIS POINT TO INDICATE WHETHER WE ARE READING OR WRITING CLA STL RAR /PREPARE TO SET/CLEAR LINK BASED ON FUNCTION TAD I RX8B /ADD IN FUNCTION WORD (LINK=1 NOW FOR WRITE) AND P70 /ISOLATE THE MEMORY FIELD TAD PCDF /BUILD 'CDF' INSTRUCTION TO THAT FIELD DCA SETFLD /STORE MEMORY FIELD NOW ISZ RX8B /STEP TO NEXT ARGUMENT TAD I RX8B /GET BUFFER ADDRESS FOR TRANSFER DCA BUF /AND SAVE IT ISZ RX8B /STEP TO NEXT ARGUMENT (BLOCK NUMBER) TAD I RX8B /TIMES THREE TO GET LOGICAL SECTOR NUMBER TAD I RX8B /... TAD I RX8B /... PCDI, CDF CIF 0 /ONLY 'CDF' USED, 'CIF' DOES NO HARM HERE DCA I XSECTOR /SAVE SECTOR NUMBER ONTO PAGE 2 ISZ RX8B /STEP POINTER NOW TO THE ERROR RETURN ADDRESS SETFLD, PBAD-TEMP /SET TO BUFFER MEMORY FIELD NOW / LINK HAS NOT CHANGED; IT INDICATES WHETHER WE ARE / GOING TO READ OR WRITE SZL /SKIP IF READ JMP WRITE /ELSE OFF TO WRITE / RX8 READ CIRCUIT / HERE FOR READ OPERATION, FIRST JOB IS TO READ IN THE SECTOR TAD DRIVE /PASS OVER THE DRIVE INFORMATION TOO JMS I XREAD /SET UP FOR READING / LOOP HERE READING THREE BYTES AT A TIME AND PACKING THEM UP / INTO MEMORY, TWO WORDS AT A TIME. THE BYTES ARE PACKED AND / UNPACKED INTO MEMORY IN OS8 FORMAT SINCE THIS IS ABOUT AS / EFFICIENT AS ANY OTHER WAY. IB, JMS I XGETB /GET FIRST BYTE DCA PSAVE /TEMP SAVE JMS I XGETB /GET SECOND BYTE DCA BYT2 /SAVE IT JMS I XGETB /GET THIRD BYTE CLL RTL /SHIFT HALF WAY DCA TEMP /AND COPY TO TEMPORARY TAD TEMP RTL /CONTINUE SHIFT AND P7400 /ISOLATE HIGH NIBBLE TAD PSAVE /MERGE IN FIRST BYTE DCA I BUF /AND STORE IT ISZ BUF /STEP BUFFER POINTER P7400, 7400 /INSTRUCTION CONSTANT AND ALSO GROUP 2 'NOP' TAD TEMP /REGET SHIFTED BYTE AGAIN BSW /SHIFT UP TO LEFTMOST NIBBLE AND P7400 /ISOLATE THE NIBBLE TAD BYT2 /MERGE IN SECOND BYTE DCA I BUF /STORE INTO THE BUFFER ISZ BUF /STEP POINTER P104, 104 /CONSTANT, ALSO PROTECTS 'ISZ' ISZ WC /MORE WORDS TO TRANSFER? JMP IB /YES - CONTINUE NOW / NASTY PROBLEM, IF WE ARE ONLY READING 1 OS/8 RECORD, WE WILL / END UP IN THE MIDDLE OF THE SECTOR WITH THE DONE FLAG DOWN / WITHOUT DETAILS ON THE RX01 I DON'T SEE ANY CLEAN WAY OF / OVERCOMING THIS PROBLEM WITHOUT FLUSHING OUT THE BUFFER. / APPARENTLY FORCING A DUMMY NOP COMMAND DOES NOT WORK JMS I XFLUSH /FLUSH OUT REMAINDER OF BUFFER IF ANY / HERE TO EXIT FROM HANDLER ISZ RX8B /STEP TO NORMAL RETURN REXIT, HLT /RETURN 'CDI' INSTRUCTION STORED HERE JMP I RX8B /RETURN NOW / HERE ON ERROR BAD, ISZ REPEAT /TRIED THREE TIMES YET? JMP AGAIN /NOT YET, DO IT ALL FROM THE TOP JMP REXIT /FATAL ERROR - RETURN TO CALL NOW / RX8 WRITE CIRCUIT / HERE TO WRITE SECTORS TO THE FLOPPY DISK BUFFER / NOTE THAT 'DRIVE' ALREADY HAS FUNCTION CODE 4 BUILT IN / NOTE ALSO THAT LINK IS ALWAYS 1 ON ENTRY HERE WRITE, TAD DRIVE /PASS DRIVE NUMBER OVER TO PAGE 2 JMS I XDWRITE /SET FUNCTION, BUT DON'T WRITE (LINK=1) / LOOP HERE TO WRITE BYTES TO THE BUFFER WRLOOP, TAD I BUF /GET FIRST BYTE JMS I XPUTB /SEND IT CLL RTR /SHIFT OVER DCA TEMP /AND SAVE IT ISZ BUF /STEP BUFFER POINTER P70, 70 /CONSTANT, PROTECTS 'ISZ' TAD I BUF /GET THE SECOND BYTE JMS I XPUTB /STORE IT CLL BSW /SHIFT OVER TAD TEMP /MERGE IN HIGH NIBBLE RTR /SHIFT DOWN TO RIGHT JUSTIFY JMS I XPUTB /INSERT INTO BUFFER ISZ BUF /STEP POINTER AGAIN P20, 20 /CONSTANT, PROTECTS 'ISZ' ISZ WC /MORE WORDS TO TRANSFER? JMP WRLOOP /YES - CONTINUE HERE / MUST CALL 'FLUSH' TO ENSURE THAT WE END ON A SECTOR BOUNDARY / IN CASE WE ARE ONLY WRITING HALF AN OS/8 BLOCK JMS I XFLUSH /IF 1/2 BLOCK, FILL REST OF SECTOR WITH ZEROES / HERE AT END, MAKE FINAL CALL TO WRITE OUT THE LAST SECTOR TAD DRIVE /WE MUST PASS DRIVE INFORMATION AGAIN JMS I XXSECT /WRITE OUT THE LAST SECTOR NOW JMP REXIT-1 /QUIT NOW - ALL DONE / RELOCATABLE SECTION HERE PBAD, BAD-RETDO /(THIS IS ON CURRENT PAGE) XGETB, GETB-RETDO /THESE ARE ALL ON THE FOLLOWING PAGE XREAD, READ-RETDO XPUTB, PUTB-RETDO XDWRITE,DWRITE-RETDO XERROR, ERROR-RETDO XSECTOR,SECTOR-RETDO XXSECT, XSECT-RETDO XFLUSH, FLUSH-RETDO / HERE FOR THE ONCE-ONLY INITIALIZATION CODE / NOTE THAT VARIBLE STORAGE OVERLAYS THIS SECTION TEMP, 0 /ADDRESS SAVED HERE BECAUSE OF 'JMS' REPEAT, TAD TEMP /LOOP HERE TO MODIFY ADDRESSES P1, TAD PBAD /##INSTRUCTION MODIFIED## P2, DCA PBAD /##INSTRUCTION MODIFIED## WC, ISZ P1 /STEP ADDRESSES IN INSTRUCTIONS BUF, ISZ P2 /AS ABOVE BYT2, ISZ SETFLD /DONE? PSAVE, JMP REPEAT /LOOP FOR NEXT / HERE WHEN DONE, JUST SET UP ERROR RETURN FROM SECOND PAGE IDONE, TAD PBAD /GET ERROR ADDRESS FOR THIS PAGE PCDF, CDF 0 /(HANDLER ALWAYS IN FIELD 0) DCA I XERROR /STORE FOR SECOND PAGE USAGE DCA D0 /DON'T INITIALIZE AGAIN NOW JMP RETDO /OK - LOAD UP THE ARGUMENTS NOW PAGE / SECTOR BUFFER I/O ROUTINE / HERE TO READ OR WRITE THE SECTOR TO/FROM THE DISK / CALL: / AC=4 /6 FOR READ, 4 FOR WRITE / JMS XSECT /CALL ROUTINE / (RETURN) /RETURN - NO ERRORS XSECT, 0 JMS LCMND /SET THAT FUNCTION NOW / NOW COMPUTE THE ACTUAL PHYSICAL TRACK AND SECTOR ADDRESSES / FROM THE LOGICAL SECTOR NUMBER / WE CANNOT AFFORD TO BE SLOPPY HERE, BECAUSE OF CRITICAL / TIMING IN BYTE MODE. WE THEREFORE USE A SPECIAL HIGH-SPEED / DIVIDE ROUTINE WHICH ASSURES THE CALCULATION IN A MINIMUM / AMOUNT OF TIME TAD TADDIV /SET INSTRUCTION UP IN ROUTINE DCA DVLOOP+1 TAD SECTOR /COPY SECTOR OVER DCA TEMP3 /... CLL /CLEAR LINK FOR DIVIDE LOOP / LOOP HERE TO DO THE FAST DIVIDE DVLOOP, DCA TRACK /ZERO/UPDATE TRACK NUMBER TAD DIVT /##INSTRUCTION MODIFIED## SNA /TEST FOR SENTINEL ON TABLE JMP VDONE /OK - ALL DONE HERE TAD TEMP3 /COMPARE WITH REMAINDER LEFT SZL /SKIP IF SUBTRACT FAILED DCA TEMP3 /SUCCESSFUL - UPDATE RESULT CLA /IGNORE AC (IN CASE UNSUCCESSFUL) TAD TRACK /GET PARTIAL RESULT RAL /SHIFT OVER ISZ DVLOOP+1 /STEP ADDRESS PART OF INSTRUCTION ABOVE JMP DVLOOP /AND LOOP / PARTITION VALUES FOR THE DIVIDE DECIMAL DIVT, -26^64 -26^32 -26^16 -26^8 -26^4 -26^2 -26^1 0 OCTAL TADDIV, TAD DIVT /INSTRUCTION CONSTANT HERE / LITTLE SUBROUTINE TO SET DRIVE INFORMATION DWRITE, 0 DCA XDRIVE /SAVE THE DRIVE NUMBER (IN CASE FROM PAGE 1) TAD XDRIVE /REGET SNL /IF LINK=1, DON'T WRITE JMS XSECT /OK, WRITE THE BUFFER CLA CLL IAC BSW /SET FUNCTION TO FILL BUFFER JMS LCMND /... TAD M129 /RESET BUFFER COUNTER DCA BCOUNT /... JMP I DWRITE /RETURN TO CALL / HERE TO PUT BYTES INTO THE SECTOR BUFFER PUTB, 0 ISZ BCOUNT /IS SECTOR BUFFER NOW FULL? JMP PUTB2 /NOT YET - CONTINUE DCA FLUSH /YES FULL, SAVE CURRENT BYTE CLL /CLEAR LINK TO FORCE WRITE OF SECTOR TAD XDRIVE /DRIVE WAS SET FIRST TIME THROUGH (LINK=0) JMS DWRITE /WRITE OUT THE SECTOR TAD FLUSH /REGET THE BYTE TO STORE JMP PUTB+1 /LOOP BACK NOW PUTB2, IOT RX8 STR /READY TO RECEIVE THE BYTE YET? JMP PUTB2 /NOT YET - SO WAIT IOT RX8 XDR /TRANSFER THE DATA BYTE AND X7400 /JUST RETURN BITS 0-3 IN THE AC JMP I PUTB / SUBROUTINE TO LOAD THE COMMAND BUFFER. THE 'DONE' FLAG MUST / BE SET (OR MUST BE IN A POSITION WHERE IT WILL BECOME SET) LCMND, 0 IOT RX8 SDN /WAIT FOR DONE FLAG TO COME UP JMP .-1 /WAIT FOR IT IOT RX8 LCD /LOAD THE COMMAND UP NOW JMP I LCMND /RETURN NOW TO CALL / HERE TO SETUP FOR READ OPERATION / NOTE THAT FUNCTION CODE ALREADY HAS 4 BUILT IN, SO WE ONLY / HAVE TO ADD 2 TO GET THE FUNCTION COE OF 6 READ, 0 SZA /SKIP IF SECOND TIME THRU (ALREADY HAVE DRIVE) DCA XDRIVE /SAVE DRIVE INFORMATION ON THIS PAGE CLA CLL IAC RAL /FUNCTION CODE 6 FOR READ TO BUFFER TAD XDRIVE /RETRIEVE DRIVE INFORMATION JMS XSECT /READ THAT NOW TAD M129 /SET COUNT FOR BUFFER DCA BCOUNT /... TAD P102 /FUNCTION IS READ BUFFER, BYTE MODE JMS LCMND /LOAD THAT COMMAND NOW JMP I READ /RETURN NOW / SUBROUTINE TO GET NEXT BYTE OUT OF THE BUFFER GETB, 0 ISZ BCOUNT /READ 128 BYTES ALREADY? JMP .+3 /NOT YET JMS READ /READ NEXT SECTOR JMP GETB+1 /CONTINUE IOT RX8 STR /SKIP ON TRANSFER FLAG UP JMP .-1 /NOT UP - WAIT FOR IT IOT RX8 XDR /READ A DATA BYTE JMP I GETB /AND RETURN IT IN THE AC / HERE AT END OF OPERATION. IF WE ARE NOT AT THE END OF THE / SECTOR BUFFER, JUST KEEP CALLING 'GETB' UNTIL ALL BYTES ARE / FLUSHED OUT. THIS ENSURES THAT RX01 IS RE-INITIALIZED PRO- / PERLY AND THAT THE DONE FLAG COMES UP. THERE MUST BE A BETTER / WAY OF DOING THIS, BUT THERE IS ROOM HERE FOR THE FUNCTION. / NOTE THAT THIS IS DONE FOR BOTH READ AND WRITE OPERATIONS. FLUSH, 0 CLA CLL IAC /CLEAR AC TWO TAD BCOUNT /TEST FOR COUNT WITH VALUE OF -1 SNA CLA /SKIP IF NOT AT END JMP I FLUSH /ALL DONE HERE JMS GETB /FLUSH OUT ANOUTHER BYTE JMP FLUSH+1 /AND LOOP TILL BUFFER CLEAR / NOW COMPUTE ACTUAL PHYSICAL SECTOR BY CONVERTING LOGICAL / SECTOR OFFSET TO PHYSICAL SECTOR BASED ON SECTOR INTERLACE / FACTOR OF TWO / CALCULATION IS: / (SECTOR.MOD.13)*3 + (SECTOR/13) + 1 VDONE, DCA TEMP2 /SET SECTOR ADDRESS TO ZERO TAD TEMP3 /GET LOGICAL SECTOR OFFSET TO TRACK / LOOP HERE TO COMPUTE ACTUAL PHYSICAL SECTOR ADDRESS CLOOP, TAD M13 /FIRST DIVIDE BY 13 ISZ TEMP2 /COUNT THE SUBTRACTIONS HERE SMA /TEST FOR END OF DIVIDE JMP CLOOP /NOT DONE YET SO LOOP ON IT TAD P13 /SAVE RESULT MODULO 13 CLL RAL /MULTIPLY BY TWO (SECTOR INTERLACE FACTOR) TAD TEMP2 /ADD IN SECTOR/13 + 1 IOT RX8 STR /WAIT FOR CONTROLLER READY JMP .-1 /... IOT RX8 XDR /LOAD IT NOW / CHANGE THE INSTRUCTION BELOW TO 'CLA IAC' TO SKIP TRACK ZERO / COMPLETELY TRACK0, CLA /(XDR DOES NOT CLEAR AC) TAD TRACK /GET PHYSICAL TRACK NUMBER IOT RX8 STR /WAIT ON CONTROLLER AGAIN JMP .-1 IOT RX8 XDR /TRANSFER THE TRACK NUMBER NOW CLA /MUST CLEAR AC AGAIN / NOW WAIT FOR OPERATION TO COMPLETE IOT RX8 SDN /WAIT FOR IT JMP .-1 /... /EXECUTE DUMMY INSTRUCTION NOW TO FORCE DONE FLAG TO COME UP AGAIN TAD P10 /THIS IS A 'NOP' INSTRUCTION TO CONTROLLER IOT RX8 LCD /EXECUTE DIRECTLY (SINCE DONE FLAG IS DOWN) ISZ SECTOR /UPDATE CURRENT LOGICAL SECTOR NUMBER IOT RX8 SER /SKIP ON ANY ERRORS JMP I XSECT /RETURN - ALL DONE HERE / HERE ON ERROR. JUST INITIALIZE AND TRY AGAIN FROM THE TOP IOT RX8 INIT /RE-INITIALIZE THE DISK NOW CLA CLL CMA RTL /SET AC NOW IN CASE RECOVERABLE, NON-RECOVERABLE JMP I ERROR /RETURN NOW TEMP2, 0 TEMP3, 0 SAVE, 0 X7400, 7400 XDRIVE, 0 BCOUNT, 0 SECTOR, 0 TRACK, 0 M13, -15 P13, +15 P10, 10 M129, -201 P102, 102 ERROR, 0 /WILL POINT TO 'BAD' AFTER INITIALIZE DONE PAGE /MUST NOT BE UP TO HERE $