mirror of
https://github.com/PDP-10/its.git
synced 2026-04-25 11:51:38 +00:00
490 lines
11 KiB
Plaintext
490 lines
11 KiB
Plaintext
;
|
||
; C10MIO - C I/O ROUTINES WRITTEN IN MIDAS
|
||
;
|
||
; This file is ITS dependent.
|
||
;
|
||
|
||
TITLE MIO
|
||
.INSRT NC
|
||
.INSRT NM
|
||
|
||
; INCLUDES:
|
||
;
|
||
; CGETC - CIO GET CHARACTER
|
||
; CPUTC - CIO PUT CHARACTER
|
||
; CGETI - CIO GET INTEGER (IMAGE)
|
||
; CPUTI - CIO PUT INTEGER (IMAGE)
|
||
; CEOF - CIO TEST FOR END-OF-FILE
|
||
; CFLUSH - CIO FLUSH BUFFER
|
||
; REW - REWIND INPUT FILE
|
||
; CLOSALL - CIO CLOSE ALL FILES
|
||
; CCLOSE - CIO CLOSE FILE
|
||
; ISTTY - IS FILE A TTY?
|
||
; CISFD - IS PTR AN ACTUAL FILE DESCRIPTOR?
|
||
; ITSCHAN - RETURN ACTUAL ITS CHANNEL
|
||
;
|
||
|
||
; REGISTERS
|
||
|
||
FP==3 ; FILE CONTROL BLOCK POINTER
|
||
T1==4 ; TEMPORARY
|
||
|
||
; VALUES
|
||
|
||
NL==12
|
||
CR==15
|
||
|
||
; FILE CONTROL BLOCK ENTRIES
|
||
|
||
FBUFFP==0 ; (LEFT HALF) POINTER TO BUFFER (OR ZERO IF NOT BUFFERED)
|
||
FCHAN: 160400,,(FP) ; ITS CHANNEL NUMBER
|
||
FDEVIC: 100600,,(FP) ; DEVICE CODE
|
||
FFLAG==0 ; (RIGHTMOST 8 BITS) FLAGS
|
||
PHYEOF==1 ; PHYSICAL EOF REACHED (BUFFERED INPUT)
|
||
%OPEN==2 ; FILE IS OPEN
|
||
%WRITE==4 ; FILE IS OPEN FOR WRITE
|
||
%TTY==10 ; FILE IS TTY
|
||
%UNSET==20 ; DEVICE AND CHANNEL NOT SET YET
|
||
FBPTR==1 ; POINTER TO NEXT CHAR/WORD OR CHAR/WORD POSITION
|
||
FBCNT==2 ; NUMBER OF CHARS/WORDS OR AVAILABLE POSITIONS IN BUFFER
|
||
FUCNT==3 ; (LEFT HALF) NUMBER OF CHARS IN UNGETC BUFFER
|
||
FUPTR==3 ; (RIGHT HALF) POINTER TO UNGETC BUFFER
|
||
FCLSR==4 ; (LEFT HALF) ADDRESS OF CLOSE ROUTINE
|
||
FNGETR==4 ; (RIGHT HALF) ADDRESS OF NORMAL GETC ROUTINE
|
||
FGETCR==5 ; ADDRESS OF CGETC ROUTINE
|
||
FPUTCR==6 ; ADDRESS OF CPUTC ROUTINE
|
||
FCBSIZ==7 ; SIZE OF FILE CONTROL BLOCK
|
||
|
||
; CONSTANTS
|
||
|
||
IBFSIZ==200
|
||
NCHAN==10.
|
||
UBFFSZ==20.
|
||
|
||
CENTRY CGETC,[FD]
|
||
XENTRY GETC,CGETC
|
||
XENTRY CGETI,CGETC
|
||
XENTRY GETI,CGETC
|
||
|
||
HRRZ FP,FD ; FILE DESCRIPTOR
|
||
GO @FGETCR(FP) ; JUMP TO APPROPRIATE ROUTINE
|
||
|
||
GETBUF: SOSGE FBCNT(FP) ; HERE FOR BUFFERED CHAR INPUT
|
||
JSP B,GTBUF1 ; BUFFER EMPTY, GO FILL IT
|
||
ILDB A,FBPTR(FP) ; GET NEXT CHAR FROM BUFFER
|
||
CAIN A,CR ; IGNORE INCOMING CR
|
||
GO GETBUF
|
||
RETURN
|
||
|
||
GETBIN: SOSGE FBCNT(FP) ; HERE FOR BINARY INPUT
|
||
GO GTBIN1 ; BUFFER EMPTY, REFILL IT
|
||
MOVE A,@FBPTR(FP) ; GET NEXT WORD FROM BUFFER
|
||
AOS FBPTR(FP) ; INCR POINTER
|
||
RETURN
|
||
|
||
GETSTR: MOVE A,@FBPTR(FP) ; HERE FOR STRING INPUT
|
||
AOS FBPTR(FP) ; INCR POINTER
|
||
JUMPE A,NEWEOF
|
||
RETURN
|
||
|
||
GETTTY: CALL TYI ; HERE FOR TTY INPUT
|
||
HRRZ FP,FD ; RESTORE FP
|
||
JUMPE A,NEWEOF
|
||
RETURN
|
||
|
||
IENTRY GC$BAD
|
||
CROAK BAD CALL TO CGETC/CGETI
|
||
SETO A,
|
||
RETURN
|
||
|
||
GETUN: HLRZ B,FUCNT(FP) ; HERE WHEN CHAR IN UNGETC BUFFER
|
||
JUMPLE B,CODE [ ; IS UNGETC BUFFER EMPTY?
|
||
HRRZ A,FNGETR(FP) ; YES
|
||
MOVEM A,FGETCR(FP) ; RESTORE CGETC ROUTINE
|
||
GO (A) ; GET NEXT CHAR
|
||
]
|
||
HRRZ A,FUPTR(FP)
|
||
ADD A,B
|
||
HRRZ A,(A) ; GET CHAR
|
||
SUBI B,1 ; DECR COUNT
|
||
HRLM B,FUCNT(FP)
|
||
RETURN
|
||
|
||
NEWEOF: MOVEI A,EOF ; HERE ON NEWLY DISCOVERED EOF
|
||
MOVEM A,FGETCR(FP)
|
||
HRRM A,FNGETR(FP) ; SET CGETC ROUTINE TO EOF
|
||
EOF: SETZ A,
|
||
RETURN
|
||
|
||
; BUFFERED CHARACTER INPUT - BUFFER READ ROUTINE
|
||
;
|
||
; CONTAINS HACKERY WHICH ALLOWS DETECTION OF LAST WORD
|
||
; OF FILE. TRAILING CONTROL-C'S ARE REMOVED FROM THIS
|
||
; WORD. CALLED VIA JSP B,
|
||
;
|
||
|
||
GTBUF1: HRRZ T1,FFLAG(FP) ; HERE TO FILL OR REFILL BUFFER
|
||
TRNE T1,PHYEOF ; HAS END OF FILE BEEN REACHED?
|
||
GO NEWEOF ; YES, ANNOUNCE IT
|
||
MOVN A,FBCNT(FP) ; OLD CHARACTER COUNT (CHECKED LATER)
|
||
MOVEI T1,5*<IBFSIZ-1> ; RESET CHARACTER COUNT
|
||
MOVEM T1,FBCNT(FP) ; (LAST WORD SAVED FOR NEXT BUFFER)
|
||
HLRZ T1,FBUFFP(FP) ; RESET CHARACTER POINTER
|
||
HRLI T1,440700 ; TO BEGINNING OF BUFFER
|
||
MOVEM T1,FBPTR(FP)
|
||
CAIE A,2 ; CHECK OLD COUNT FOR SPECIAL VALUE
|
||
GO GTBUF2 ; NORMAL (NOT INIT) CASE
|
||
HLRZ T1,FBUFFP(FP) ; FIRST TIME - FILL ENTIRE BUFFER
|
||
HRLI T1,-IBFSIZ
|
||
GO GTBUF3
|
||
|
||
GTBUF2: HLRZ T1,FBUFFP(FP) ; NORMAL CASE - ONE WORD SAVED FROM LAST READ
|
||
MOVE A,IBFSIZ-1(T1) ; GET LAST WORD OF BUFFER (UNREAD)
|
||
MOVEM A,(T1) ; MAKE FIRST WORD OF BUFFER
|
||
ADDI T1,1 ; ADJUST CPTR TO FILL REST OF BUFFER
|
||
HRLI T1,-IBFSIZ+1
|
||
|
||
GTBUF3: LDB A,FCHAN ; ITS CHANNEL NUMBER
|
||
LSH A,23.
|
||
IOR A,[.IOT T1]
|
||
XCT A ; EXECUTE .IOT
|
||
JUMPGE T1,-2(B) ; BUFFER WAS FILLED, NO MORE TO DO
|
||
HLRES T1
|
||
ADDI T1,IBFSIZ ; NUMBER OF WORDS READ
|
||
HLRZ A,FBUFFP(FP)
|
||
ADDI A,-1(T1) ; POINTER TO WORD LAST READ
|
||
IMULI T1,5 ; NUMBER OF CHARS READ
|
||
PPUSH B
|
||
MOVEI B,5 ; CHECK FOR AT MOST 5 TRAILING ^C'S
|
||
HRLI A,010700 ; BYTE POINTER TO LAST CHAR
|
||
GTBUF4: LDB 0,A ; GRAB CHARACTER
|
||
ADD A,[070000,,0] ; DECREMENT BYTE POINTER
|
||
CAIE 0,3 ; IS IT A ^C
|
||
GO GTBUF5 ; NO
|
||
SUBI T1,1 ; DECREMENT CHARACTER COUNT
|
||
SOJG B,GTBUF4 ; KEEP LOOKING
|
||
GTBUF5: PPOP B
|
||
MOVEM T1,FBCNT(FP) ; SET CHARACTER COUNT
|
||
MOVEI T1,PHYEOF
|
||
IORM T1,FFLAG(FP) ; SET PHYSICAL EOF FLAG
|
||
GO -2(B) ; THAT'S IT!
|
||
|
||
;
|
||
; GTBIN1 - INTERNAL CODE FOR BINARY BUFFER GET
|
||
;
|
||
GTBIN1: HRRZ T1,FFLAG(FP) ; HERE TO REFILL BUFFER IN BINARY MODE
|
||
TRNE T1,PHYEOF ; HAS END OF FILE BEEN REACHED?
|
||
GO NEWEOF ; YES, ANNOUNCE IT
|
||
MOVEI T1,IBFSIZ
|
||
MOVEM T1,FBCNT(FP) ; RESET COUNTER
|
||
HLRZ T1,FBUFFP(FP) ; BUFFER POINTER
|
||
MOVEM T1,FBPTR(FP) ; RESET POINTER
|
||
HRLI T1,-IBFSIZ ; COUNTING POINTER FOR IOT
|
||
LDB A,FCHAN
|
||
LSH A,23.
|
||
IOR A,[.IOT T1] ; SET UP .IOT INSTRUCTION
|
||
XCT A ; EXECUTE .IOT INSTRUCTION
|
||
JUMPGE T1,GETBIN ; BUFFER WAS FILLED, RESUME
|
||
HLRES T1
|
||
ADDI T1,IBFSIZ ; NUMBER OF WORDS ACTUALLY READ
|
||
MOVEM T1,FBCNT(FP) ; SET COUNTER
|
||
MOVEI T1,PHYEOF
|
||
IORM T1,FFLAG(FP) ; SET PHYSICAL EOF FLAG
|
||
GO GETBIN ; RESUME
|
||
|
||
CENTRY CPUTC,[CC,FD]
|
||
XENTRY PUTC,CPUTC
|
||
XENTRY CPUTI,CPUTC
|
||
XENTRY PUTI,CPUTC
|
||
|
||
HRRZ FP,FD ; FILE DESCRIPTOR
|
||
MOVE A,CC ; CHARACTER (OR INTEGER) TO BE WRITTEN
|
||
GO @FPUTCR(FP) ; JUMP TO APPROPRIATE ROUTINE
|
||
|
||
PUTBUF: CAIN A,NL ; HERE FOR BUFFERED CHAR OUTPUT
|
||
GO CODE [
|
||
CALL CPUTC,[[[CR]],FP]
|
||
HRRZ FP,FD
|
||
MOVEI A,NL
|
||
GO PF$1
|
||
]
|
||
JUMPE A,PC$RET ; DONT WRITE NULLS
|
||
PF$1: IDPB A,FBPTR(FP) ; STORE CHAR
|
||
SOSG FBCNT(FP) ; BUFFER FULL?
|
||
GO CODE [ ; YES
|
||
MCALL FLUSHB,[FP,[[IBFSIZ]]] ; FLUSH ENTIRE BUFFER
|
||
GO PC$RET
|
||
]
|
||
PC$RET: RETURN ; NO, RETURN
|
||
|
||
PUTBIN: MOVEM A,@FBPTR(FP) ; HERE ON BINARY OUTPUT
|
||
AOS FBPTR(FP)
|
||
SOSLE FBCNT(FP)
|
||
GO PC$RET
|
||
HLRZ T1,FBUFFP(FP)
|
||
HRLI T1,-IBFSIZ ; SET UP COUNTING POINTER FOR .IOT
|
||
LDB A,FCHAN ; GET ITS CHANNEL NUMBER
|
||
LSH A,23.
|
||
IOR A,[.IOT T1] ; PREPARE .IOT INSTRUCTION
|
||
XCT A ; EXECUTE .IOT INSTRUCTION
|
||
MOVEI T1,IBFSIZ
|
||
MOVEM T1,FBCNT(FP) ; RESET COUNTER
|
||
HLRZ T1,FBUFFP(FP)
|
||
MOVEM T1,FBPTR(FP) ; RESET POINTER
|
||
GO PC$RET
|
||
|
||
PUTSTR: MOVEM A,@FBPTR(FP) ; HERE ON STRING OUTPUT
|
||
AOS FBPTR(FP)
|
||
GO PC$RET
|
||
|
||
PUTTTY: CAIN A,NL ; HERE ON TTY OUTPUT
|
||
MOVEI A,CR ; OUTPUT NEWLINES AS CR'S
|
||
CALL TYO,[A]
|
||
GO PC$RET
|
||
|
||
IENTRY PC$BAD
|
||
CROAK BAD CALL TO CPUTC/CPUTI
|
||
SETO A,
|
||
GO PC$RET
|
||
|
||
CENTRY CEOF,[FD]
|
||
|
||
HRRZ FP,FD
|
||
SETZ A,
|
||
HRRZ B,FGETCR(FP)
|
||
CAIN B,EOF
|
||
MOVEI A,1
|
||
CAIN B,GC$BAD
|
||
SETO A,
|
||
RETURN
|
||
|
||
CENTRY UNGETC,[CC,FD]
|
||
|
||
HRRZ FP,FD ; FILE DESCRIPTOR
|
||
MOVE A,CC ; CHARACTER
|
||
HLRZ T1,FUCNT(FP) ; NUMBER OF CHARS IN BUFFER
|
||
ADDI T1,1
|
||
CAIL T1,UBFFSZ ; TOO MANY?
|
||
GO CODE [
|
||
SETO A,
|
||
GO UN$RET
|
||
]
|
||
HRLM T1,FUCNT(FP)
|
||
HRRZ B,FUPTR(FP)
|
||
ADD T1,B
|
||
MOVEM A,(T1) ; STORE CHAR
|
||
MOVEI B,GETUN
|
||
MOVEM B,FGETCR(FP) ; SET UP GETC ROUTINE
|
||
UN$RET: RETURN
|
||
|
||
CENTRY CFLUSH,[FD]
|
||
|
||
MCALL FLUSHP,[FD,[[0]]]
|
||
RETURN
|
||
|
||
MENTRY FLUSHP,[FD,PADC]
|
||
|
||
HRRZ FP,FD
|
||
HRRZ A,FPUTCR(FP) ; OUTPUT ROUTINE
|
||
CAIE A,PUTBUF
|
||
GO FL$RET
|
||
HRRZ T1,PADC ; PAD CHARACTER
|
||
MOVEI A,5*IBFSIZ ; NUMBER OF CHAR POSITIONS
|
||
SUB A,FBCNT(FP) ; NUMBER OF ACTUAL CHARS IN BUFFER
|
||
JUMPLE A,FL$RET ; BUFFER IS EMPTY
|
||
IDIVI A,5
|
||
JUMPE B,FL$1 ; NO PARTIALLY FILLED WORDS
|
||
MOVN B,B
|
||
ADDI B,5
|
||
IDPB T1,FBPTR(FP) ; FILL OUT WITH ^C'S
|
||
SOJG B,.-1
|
||
ADDI A,1
|
||
FL$1: MCALL FLUSHB,[FP,A]
|
||
FL$RET: RETURN
|
||
|
||
MENTRY FLUSHB,[FD,SIZE]
|
||
|
||
MOVE FP,FD ; FILE POINTER
|
||
MOVN T1,SIZE ; SIZE OF FILLED PART OF BUFFER
|
||
HRLZ T1,T1 ; CONSTRUCT
|
||
HLR T1,FBUFFP(FP) ; .IOT POINTER
|
||
LDB B,FCHAN
|
||
LSH B,23.
|
||
IOR B,[.IOT T1] ; PREPARE .IOT INSTRUCTION
|
||
XCT B ; EXECUTE .IOT INSTRUCTION
|
||
MOVEI T1,5*IBFSIZ
|
||
MOVEM T1,FBCNT(FP) ; RESET COUNTER
|
||
HLRZ T1,FBUFFP(FP)
|
||
HRLI T1,440700
|
||
MOVEM T1,FBPTR(FP) ; RESET ABPTR
|
||
RETURN
|
||
|
||
CENTRY REW,[FD]
|
||
|
||
HRRZ FP,FD
|
||
SETOM FBCNT(FP)
|
||
HRRZ A,FFLAG(FP)
|
||
TRZ A,PHYEOF
|
||
HRRM A,FFLAG(FP)
|
||
MOVE A,GETTAB+1
|
||
MOVEM A,FGETCR(FP)
|
||
LDB A,FCHAN
|
||
.CALL [SETZ ? 'ACCESS ? A ? 401000,,0]
|
||
CROAK REW: ACCESS FAILED
|
||
RETURN
|
||
|
||
CENTRY CLOSALL,,[COUNTER] ; CLOSE ALL C FILES
|
||
|
||
MOVEI A,NCHAN-1
|
||
MOVEM A,COUNTER
|
||
MOVE A,COUNTER
|
||
CA$1: CALL CCLOSE,[FCBTBL(A)]
|
||
SOSL A,COUNTER
|
||
GO CA$1
|
||
RETURN
|
||
|
||
CENTRY CCLOSE,[FD]
|
||
|
||
HRRZ FP,FD
|
||
HLRZ A,FCLSR(FP)
|
||
GO (A) ; JUMP TO APPROPRIATE ROUTINE
|
||
|
||
CLOBUF: MCALL FLUSHP,[FP,[[3]]]
|
||
GO CLIBUF
|
||
|
||
CLOBIN: MOVE A,FBCNT(FP) ; HERE ON BINARY OUTPUT
|
||
SUBI A,IBFSIZ
|
||
JUMPGE A,CLIBUF
|
||
HRLZ A,A
|
||
HLR A,FBUFFP(FP)
|
||
LDB B,FCHAN
|
||
LSH B,23.
|
||
IOR B,[.IOT A]
|
||
XCT B ; FLUSH BUFFER
|
||
|
||
CLIBUF: LDB A,FCHAN ; HERE ON BUFFERED AND BINARY INPUT
|
||
; ALSO FALL THROUGH FROM BUFFERED AND BINARY OUTPUT
|
||
CALL MCLOSE,[A]
|
||
MOVE FP,FD
|
||
|
||
CLTTY: SETZ A, ; HERE ON TTY AND FALL THROUGH
|
||
|
||
CLOSE2: MOVEI T1,%OPEN ; HERE TO CLEAR %OPEN BIT
|
||
ANDCAM T1,FFLAG(FP)
|
||
MOVEI T1,GC$BAD ; SET ROUTINES TO BAD
|
||
MOVEM T1,FGETCR(FP)
|
||
MOVEI T1,PC$BAD
|
||
MOVEM T1,FPUTCR(FP)
|
||
MOVE T1,[CL$BAD,,GC$BAD]
|
||
MOVEM T1,FCLSR(FP)
|
||
CL$RET: RETURN
|
||
|
||
CLOSTR: MOVE A,FBPTR(FP) ; HERE ON STRING OUTPUT
|
||
SETZM (A) ; APPEND NULL ONTO STRING
|
||
GO CLOSE2 ; RETURN POINTER TO NULL CHAR
|
||
|
||
IENTRY CL$BAD
|
||
SETO A,
|
||
GO CL$RET
|
||
|
||
CENTRY ISTTY,[FD]
|
||
|
||
HRRZ FP,FD
|
||
HRRZ A,FFLAG(FP)
|
||
TRNE A,%UNSET ; IS DEVICE CODE VALID?
|
||
GO IS$RET ; NO -- MUST BE A TTY
|
||
LDB A,FDEVICE ; GET IT
|
||
CAILE A,2 ; TEST FOR TTY DEVICES
|
||
SETZ A,
|
||
IS$RET: RETURN
|
||
|
||
; INTERNAL ROUTINE TO SET DEVICE AND CHANNEL
|
||
; MUST BE THE TTY INPUT OR OUTPUT CHANNEL
|
||
; RETURN DEVICE CODE
|
||
|
||
MENTRY SETDEV,[FD]
|
||
|
||
HRRZ FP,FD
|
||
MOVE A,FFLAG(FP)
|
||
TRNE A,%WRITE
|
||
MOVEI B,ZTYOOPN"
|
||
TRNN A,%WRITE
|
||
MOVEI B,ZTYIOPN"
|
||
VCALL (B)
|
||
JUMPL A,SD$RET ; VALID CHANNEL RETURNED?
|
||
HRRZ FP,FD
|
||
DPB A,FCHAN ; YES - STORE IT
|
||
LSH A,23.
|
||
IOR A,[.STATUS A]
|
||
XCT A
|
||
ANDI A,77 ; GET DEVICE FROM CHANNEL STATUS
|
||
DPB A,FDEVIC ; STORE DEVICE
|
||
MOVEI T1,%UNSET ; CLEAR %UNSET BIT
|
||
ANDCAM T1,FFLAG(FP)
|
||
SD$RET: RETURN
|
||
|
||
CENTRY CISFD,[FD]
|
||
|
||
MOVE A,FD
|
||
CAIGE A,C0FCBS+1
|
||
GO ISF$NO
|
||
CAIL A,C0FCBS+1+NCHAN*FCBSIZ
|
||
GO ISF$NO
|
||
MOVEI A,1
|
||
RETURN
|
||
ISF$NO: SETZ A,
|
||
RETURN
|
||
|
||
CENTRY ITSCHAN,[FD]
|
||
|
||
HRRZ FP,FD
|
||
HRRZ A,FFLAG(FP)
|
||
TRNN A,%UNSET ; IS CHANNEL CODE VALID?
|
||
GO IC$1 ; YES - GET IT
|
||
MCALL SETDEV,[FD] ; NO -- SET IT AND RETURN IT
|
||
RETURN
|
||
IC$1: LDB A,FCHAN ; GET CHANNEL
|
||
RETURN
|
||
|
||
.PDATA
|
||
MDATA GETTAB
|
||
GETTTY
|
||
GETBUF
|
||
GETBIN
|
||
GETSTR
|
||
GC$BAD
|
||
GC$BAD
|
||
GC$BAD
|
||
GC$BAD
|
||
|
||
MDATA PUTTAB
|
||
PC$BAD
|
||
PC$BAD
|
||
PC$BAD
|
||
PC$BAD
|
||
PUTTTY
|
||
PUTBUF
|
||
PUTBIN
|
||
PUTSTR
|
||
|
||
MDATA CLOTAB
|
||
CLTTY
|
||
CLIBUF
|
||
CLIBUF
|
||
CLTTY
|
||
CLTTY
|
||
CLOBUF
|
||
CLOBIN
|
||
CLOSTR
|
||
|
||
; STATIC DATA AREAS
|
||
|
||
.UDATA
|
||
MDATA C0FCBS
|
||
BLOCK NCHAN*FCBSIZ+1
|
||
|
||
MDATA FCBTBL
|
||
REPEAT NCHAN C0FCBS+1+.RPCNT*FCBSIZ
|
||
|
||
END
|
||
|