/ ************* / * * / * OSCAR-8 * / * * / ************* / REAL TIME OPERATING SYSTEM FOR PDP-8 SERIES COMPUTERS / (C) J.E. WULFF 1977 / SYSTEM NUCLEUS / VERSION 1 3-NOV-72 / VERSION 4 30-MAY-77 / ACCUMULATORS LINK, MQ REGISTER AND PROGRAM COUNTER / ARE SAVED IN THE TASK CONTROL BLOCK FOR EACH TASK. / ALSO SAVED ARE LOCATIONS 16 TO 27 WHICH MAY BE USED / AS PRIVATE REGISTERS BY EACH TASK. LOCATIONS 16 AND / 17 ARE AUTO-INCREMENTING. LOCATION 15 IS USED BY / THE OPERATING SYSTEM AND SHOULD NOT BE USED. / TASK CONTROL BLOCK STRUCTURE / 0 ! AC ! ACCUMULATOR / 1 ! WC ! WAIT COUNT / 2 ! BP ! BACK POINTER / 3 ! LK ! LINK / 4 ! PC ! PROGRAM COUNTER / 5 ! MQ ! MULTIPLIER QUOTIENT / 6 ! 16 ! LOCATION 16 / . . .. . / / 17 ! 27 ! LOCATION 27 / 20 IPC INTIAL PROGRAM COUNTER / 21 ICW INITIALISATION CONTROL WORD / . . .. . OPTIONAL INITIAL VALUES, ONE FOR / . . .. . EVERY BIT OF THE ICW TL= 20 / TCB LENGTH MQA= 7501 / PDP8-E OPTIONS MQL= 7421 *200 / SYSTEM START-UP START, TAD FTLP / TASK LIST POINTER DCA 16 TAD FTP1 / TASK QUEUE POINTER DCA 17 TAD TQL / TASK QUEUE LENGTH DCA 20 SL1, TAD I 16 / TCB ADDRESS FROM TASK LIST DCA I 17 / INITIALISE TASK QUEUE ENTRY ISZ 20 / COUNT TASKS IN QUEUE JMP SL1 SL2, TAD I 16 / HIGHEST PRIORITY TCB DCA T1 / SAVE FOR INITIAL SCHEDULING TAD FTP1 DCA 17 / SCAN TASK QUEUE NOW TAD TQL / TASK QUEUE LENGTH DCA 20 SL3, STA / 7777 TAD I 17 / TCB ADDRESS - 1 DCA 16 TAD 16 TAD OFIPC / 21 DCA 15 DCA I 16 / CLEAR AC IN TCB DCA I 16 / CLEAR WC TAD 17 / CURRENT TASK QUEUE ADDRESS DCA I 16 / INITIALISE BACK POINTER DCA I 16 / CLEAR LINK TAD I 15 / VALUE OF PC FOR TASK DCA I 16 / INITIALISE PC TAD I 15 / INITIALISATIN CONTROL WORD DCA 21 TAD MTL / LENGTH FROM MQ TO 27 IN TCB DCA 22 SL4, TAD 21 CLL RAL / NEXT BIT DCA 21 SZL / TEST CONTROL BIT TAD I 15 / SET - GET INITIAL VALUE DCA I 16 / CLEAR OR PRESET INITIAL VALUE ISZ 22 JMP SL4 ISZ 20 / COUNT TASK QUEUE ENTRIES JMP SL3 JMP I .+1 / ENTER TASK SCHEDULER TS3 FTLP, TQ-1 TQL, TQ-TQA FTP1, TQA-1 OFIPC, 20 MTL, -13 / INTERRUPT SERVICE INTS, DCA I ATP / SAVE ACCUMULATOR IN TCB RSF / IS IT HIGH SPEED READER ? JMP PSFT / NO RRB / YES - CLEAR FLAGS FETCH CHAR. DCA RCHAR / STORE FOR READ ROUTINE JMS IPOST RECW PSFT, PSF / IS IT HIGH SPEED PUNCH ? JMP KSFT / NO PCF / YES - CLEAR FLAG JMS IPOST PECW KSFT, KSF / IS IT TTY IN ? JMP TSFT / NO KCC / YES - CLEAR FLAG (ALSO AC) JMS IPOST KECW TSFT, TSF / IS IT TTY OUT ? JMP UINT / NO TCF / YES - CLEAR FLAG JMS IPOST TECW UINT, HLT / UNKNOWN INTERRUPT JMP I RTI1 RTI1, RTI / TELETYPE KEYBOARD DRIVER RKGET, 0 / MAY BE USED BY ONLY ONE IOF / TASK AT A TIME JMS I WAIT KECW KRB / READ CHARACTER JMP I RKGET / TELETYPE PRINTER DRIVER RTPUT, 0 / CHARACTER PASSED IN AC IOF JMS I WAIT TECW TPC / PRINT CHARACTER CLA JMP I RTPUT / HIGH SPEED READER DRIVER RREAD, 0 IOF JMS I WAIT RECW CLA TAD RCHAR / FETCH CHARACTER RFC / START READER AGAIN NOW JMP I RREAD RCHAR, 0 / CHARACTER BUFFER / HIGH SPEED PUNCH DRIVER RPUNCH, 0 / CHAR. IN AC IOF JMS I WAIT PECW PPC / PUNCH CHARACTER CLA JMP I RPUNCH / POST AN EVENT FROM AN INTERRUPT SERVICE ROUTINE / CALLING SEQUENCE: / JMS IPOST / / RETURNS TO INTERRUPTED TASK *375 / DO NOT CHANGE IPOST, 0 / INTERRUPTS ARE OFF CLA TAD I IPOST / ADDRESS OF ECW JMP POST1 / THIS IS ON NEXT PAGE / POST AN EVENT / CALLING SEQUENCE: / IOF / JMS I POST / / / AC & LINK ARE SAVED RPOST, 0 / IOF BEFORE ENTRY DCA I ATP / SAVE AC & CLEAR TAD RPOST IAC DCA 0 / SAVE RETURN IN LOC 0 TAD I RPOST POST1, DCA T1 / ADDRESS OF ECW TAD T1 AND C7740 / IS ADDRESS < 40 ? SNA CLA JMS INDIR / YES - INDIRECT REFERENCE TAD I T1 / ECW DCA 15 TAD 15 CMA SNA / IS EVENT ALREADDY POSTED (ECW=7777) ? JMP I RTI2 / YES PROCEED WITH TASK (AC=0) CMA / NO SZA CLA / IS TASK WAITING (ECW=0) ? ISZ I 15 / YES - TEST WAIT COUNT JMP POST2 / NO OR WAIT COUNT WAS < -1 TAD I 15 / QUEUE ADDRESS FROM BACK POINTER DCA T2 TAD I T1 / ECW IS TCB ADDRESS DCA I T2 / STORE IN TQ TO ACTIVATE TASK JMP POST3 / EXECUTE THE FOLLOWING IN 'WAIT' / DCA I T1 / CLEAR ECW / JMP TS1 POST2, STA / 7777 DCA I T1 / POST EVENT (7777 ==> ECW) JMP I RTI2 / PROCEED WITH TASK OR INTERRUPTED PROGRAM / RAISE A SEMAPHORE / CALLING SEQUENCE: / IOF / JMS I RAISE / / / AC & LINK ARE SAVED RRAISE, 0 / IOF BEFORE ENTRY DCA I ATP / SAVE AC TAD RRAISE IAC DCA 0 / SAVE RETURN IN LOC 0 TAD I RRAISE DCA T1 / POINT TO SEM COUNTER TAD T1 AND C7740 / IS ADDRESS < 40 ? SNA CLA JMS INDIR / YES - INDIRECT REFERENCE TAD I T1 / OLD SEM COUNTER VALUE ISZ I T1 / INCREMENT SPA CLA SKP CLA / NOW ZERO OR MINUS JMP I RTI2 / POSITIVE - PROCEED WITH TASK ISZ T1 / POINT TO SEM LINK TAD I T1 / TCB ADDRESS FROM LINK DCA 15 TAD I 15 / NEXT TCB ADDRESS OR ZERO DCA RRAISE / SAVE TEMPORARILY TAD I 15 / TASK QUEUE ADDRESS FROM BP DCA T2 TAD I T1 / TCB ADDRESS FROM LINK AGAIN DCA I T2 / STORE IN TQ ENTRY TO ACTIVATE TAD RRAISE / NEXT TCB ADDRESS OR ZERO AGAIN JMP POST3 / EXECUTE THE FOLLOWING IN 'WAIT' / DCA I T1 / RE-LINK TCB CHAIN / JMP TS1 / LOWER A SEMAPHORE / CALLING SEQUENCE: / IOF / JMS I LOWER / / / AC & LINK ARE SAVED RLOWER, 0 DCA I ATP / SAVE AC TAD RLOWER IAC DCA 0 / SAVE RETURN IN LOC 0 TAD I RLOWER DCA T1 / ADDRESS OF SEM COUNTER TAD T1 AND C7740 / IS ADDRESS < 40 ? SNA CLA JMS INDIR / YES - INDIRECT REFERENCE TAD I T1 / OLD SEM COUNTER VALUE SZA CML / COMPLEMENT LINK UNLESS COUNTER =0 TAD C7777 / DECREMENT (LINK IS RESTORED) DCA I T1 / NEW COUNTER VALUE TAD I T1 SMA CLA / TEST IF ZERO OR POSITIVE JMP I RTI2 / YES PROCEED WITH TASK SKP / T1 POINTS TO SEMAPHORE LOW1, DCA T1 ISZ T1 / WILL POINT TO LINK (WC) TAD I T1 / NEXT LINK OR ZERO SZA / TEST IF ZERO JMP LOW1 / NO - SCAN FURTHER TAD ATP / YES - LINK THIS TASK DCA I T1 TAD ATP DCA 15 / PREPARE FOR MODIFYING LINK (WC) JMP LOW2 / EXECUTE THE FOLLOWING IN 'WAIT' / DCA I 15 / TAD I 15 / DCA T1 / DCA I T1; / JMP TS1 / THIS CODE ALLOWS RE-ENTRANT SUBROUTINE CALLS / CALLING SEQUENCE: / JMS 27 /
/ OR / STRUCTURE OF THE RE-ENTRANT SUBROUTINE: / , / ... / JMP I 27 / RETURN / NOTE: NESTED OR RECURSIVE CALLS ARE NOT ALLOWED / AC & LINK ARE SAVED. LOC 25 - 27 / ARE DESTROYED. THE AC CONTENTS IS AVAILABLE / IN LOC 26. S27, DCA 26 / SAVE AC TAD I 27 / SUBROUTINE ADDRESS DCA 25 / TEMP POINTER ISZ 27 / FIX RETURN TAD 26 / RESTORE AC JMP I 25 / ENTER SUBROUTINE / EVALUATE INDIRECT REFERENCE INDIR, 0 TAD I T1 DCA T1 JMP I INDIR RTI2, RTI C7740, 7740 C7777, 7777 T2, 0 / WAIT FOR AN EVENT / CALLING SEQUENCE: / IOF / JMS I WAIT / / / AC & LINK ARE SAVED *551 / DO NOT CHANGE RWAIT, 0 / IOF BEFORE ENTRY DCA I ATP / SAVE AC & CLEAR TAD RWAIT IAC DCA 0 / SAVE RETURN IN LOC 0 TAD I RWAIT DCA T1 / ADDRESS OF ECW TAD T1 AND C7740 / IS ADDRESS < 40 ? SNA CLA JMS INDIR / YES - INDIRECT REFERENCE ISZ I T1 / IS EVENT ALREADY POSTED SKP / NO JMP I RTI2 / YES PROCEED WITH TASK (AC=0) TAD ATP DCA I T1 / STORE TCB ADDRESS IN ECW TAD ATP DCA 15 STA / -1 LOW2, DCA I 15 / SET WAIT COUNT OR LINK TAD I 15 / QUEUE ADDRESS FROM BP DCA T1 POST3, DCA I T1 / CLEAR TASK QUEUE ENTRY / ENTER TASK SCHEDULER DIRECTLY (AC=0) / TASK SCHEDULER TS1, TAD FTP2 / FIRST TASK POINTER DCA 15 TS2, TAD I 15 / SCAN THE TASK QUEUE SNA JMP TS2 / TASK NOT READY DCA T1 / HIGHEST PRIORITY READY TASK TAD ATP TAD OFLK / ATCB + 2. POINT TO LINK DCA 15 RAL DCA I 15 / SAVE LINK TAD T1 CIA TAD ATP SNA CLA / IS CURRENT TASK HIGHEST PRIORITY JMP TS4 / YES - RESTORE CURRENT TASK TAD 0 DCA I 15 / SAVE PC MQA DCA I 15 / SAVE MQ TAD 16 DCA I 15 / SAVE PRIVATE REGISTERS 16 TO 27 TAD 17 DCA I 15 TAD 20 DCA I 15 TAD 21 DCA I 15 TAD 22 DCA I 15 TAD 23 DCA I 15 TAD 24 DCA I 15 TAD 25 DCA I 15 TAD 26 DCA I 15 TAD 27 DCA I 15 / SET UP NEW TASK TS3, TAD T1 DCA ATP / NEW TASK IS ACTIVE TAD ATP TAD OFPC / ATCB + 3. POINT TO PC DCA 15 TAD I 15 / RESTORE PC DCA 0 TAD I 15 / RESTORE MQ MQL TAD I 15 / RESTORE PRIVATE REGISTERS 16 TO 27 DCA 16 TAD I 15 DCA 17 TAD I 15 DCA 20 TAD I 15 DCA 21 TAD I 15 DCA 22 TAD I 15 DCA 23 TAD I 15 DCA 24 TAD I 15 DCA 25 TAD I 15 DCA 26 TAD I 15 DCA 27 TS4, TAD ATP TAD OFLK / ATCB + 2. POINT TO LINK DCA 15 TAD I 15 / RESTORE LINK CLL RAR RTI, TAD I ATP / RESTORE AC ION JMP I 0 / RETURN FTP2, TQA-1 OFLK, 2 OFPC, 3 / TASK QUEUE - ALLOWS 7 REAL-TIME TASKS TQ, TCBZZ / REPLACE WITH OTHER TCB ADDRESSES TCBZZ / IN ORDER OF PRIORITIES TCBZZ TCBZZ TCBZZ TCBZZ TCBZZ TCBZZ / LEAVE ONE AS TCBZZ TQA, 0 0 0 0 0 0 0 0 / DUMMY BACKGROUND TASK / THIS TASK IS ALWAYS ACTIVE. IT DISPLAYS THE CONTENTS / OF THE MEMORY LOCATION, WHOSE ADDRESS IS SET UP IN / THE SWITCH REGISTER, IN THE ACCUMULATOR DISPLAY. / THE LINK LIGHT FLASHES AT A 1 HERTZ RATE WHEN ONLY THIS / TASK IS ACTIVE. ANY REDUCTION OF THE FLASHING RATE GIVES / A MEASURE OF THE OCCUPANCY OF OTHER TASKS TCBZZ, *.+TL BG1 / INITIAL START 340 / INITIALISE 21 - 23 ISZ 27 / LOC 21 - WASTE TIME JMP 21 / LOC 22 JMP I 20 / LOC 23 BG0, LAS / READ ADDESS IN SWITCHES DCA 25 / STORE ADDRESS ISZ 26 / HIGH ORDER COUNT JMP BG2 / NOT ZERO BG1, TAD MX / PRESET HIGH ORDER COUNTER DCA 26 CML / FLASH THE LINK LIGHT BG2, TAD I 25 / DISPLAY CONTENTS IN AC JMS 20 / WASTE TIME JMP BG0 MX, -40 / ADJUSTED FOR PDP-8E / END OF PROGRAM OSCAR-8 *1 JMP I .+1 / INTERRUPT VECTOR INTS *30 / PAGE ZERO LOCATIONS FOR SYSTEM JMP I .+1 / VECTOR FOR "JMS 27" S27 ATP, 0 T1, 0 / SYSTEM SYNCHRONISING ROUTINES WAIT, RWAIT POST, RPOST LOWER, RLOWER RAISE, RRAISE / SYSTEM I/O ROUTINES KGET, RKGET / TTY IN (NO ECHO) TPUT, RTPUT / TTY OUT READ, RREAD / HIGH SPEED READER PUNCH, RPUNCH / HIGH SPEED PUNCH / EVENT CONTROL WORDS FOR I/O KECW, 0 / TTY IN TECW, 0 / TTY OUT RECW, 0 / HIGH SPEED READER PECW, 0 / HIGH SPEED PUNCH $