Trailing-Edge
-
PDP-10 Archives
-
decuslib20-04
-
decus/20-0110/ptypkg.sai
There are 2 other files named ptypkg.sai in the archive. Click here to see a list.
Entry;
COMMENT
.SEC(PTYPKG.SAI - pseudo teletype package)
.index(PTYPKG.SAI - pseudo teletype package)
.;
Begin "PTYPKG.SAI"
Define # = "Comment";
Comment
Pseudo Teletype package for use with NIH SAIL
---------------------------------------------
Ron Black and Peter Lemkin*
DCRT
National Institutes of Health
Bethesda, Md. 20014
*Image Processing Unit
Division of Cancer Biology and Diagnosis
National Cancer Institute
National Institutes of Health
Bethesda, Md. 20014
Purpose
-------
This package consists of all the procedures necessary
to acquire and use a pseudo teletype channel called PTY from
SAIL.
To use this package, include a
REQUIRE "PTYPKG.REQ" SOURCE!FILE
in your program.
Procedure calls
---------------
This file contains four procedures for using a PTY from a sail
program. The four procedures require several global variables and
macro definitions Defined in ptydec.Sai.
[1] Integer Procedure GETPTY - gets a PTY and I/O channel
this procedure tries to open a PTY
and returns the following values
-2 if no PTY's are available
-1 if no channels are available
otherwise it returns the channel number
for the PTY
[2] Integer Procedure PTYSTS - gets the status of the PTY.
this procedure should be called before every
Input or output to a PTY, since a single call
To INPPTY may not get all the input from the
PTY. this procedure returns true if it's ok to
do an output to PTY false if program should do
an input on PTY.
[3] String Procedure INPPTY - inputs a string from the PTY
where the maximum length of the string is ptycnt.
[4] Procedure OUTPTY(String str) - will output a string
'str' to the PTY.
The calling conventions for each procedure is described
in the code
;
Integer ptychn, popblk, ptobuf, ptibuf, i;
COMMENT
.NEXT PAGE
.SS(PTYPKG MACRO DEFINITIONS)
.INDEX(PTYPKG MACRO DEFINITIONS)
.;
Internal Integer PSTATUS;
Comment some useful macros;
"PTYINP is true when program can do a INPPTY"
Define PTYINP="PSTATUS land '40000000000 neq 0";
"PTYOUT is true when program can do a OUTPTY"
Define PTYOUT="PSTATUS land '20000000000 neq 0";
Define CALLI="'47000000000";
Define P='17;
Define Crlf="'15&'12";
Comment ptybuf is where we store characters when reading the
PTY. Ptycnt is the number of characters that can be read by a
single call to OUTPTY. To change this merely change ptycnt
which is an assembly conditional;
Define ptycnt=200;
Integer Array ptybuf[1:ptycnt/5];
COMMENT
.next page
.ss(Procedure INPPTY)
.index(Procedure INPPTY)
.;
Internal String Procedure INPPTY;
Comment
-------------------------------------
this proceTdure gets a string from the PTY and returns it. It
will return either (1) when the buffer is filled or when the
PTY msg is completed;
Begin "INPPTY"
Label error, chk, all!done, loop, getbuf, inins, stsins;
String s;
Comment characters from the PTY will be put into
ptybuf (5 characters per word);
" zero buffers"
ARRCLR(ptybuf);
s_null;
Start!Code;
Comment set up String pointer to ptybuf;
HRLI 1,'440700;
HRR 1,ptybuf;
Comment register 2 points to input buffer ring;
MOVE 2,ptibuf;
Comment register 6 is a counter, we can only input 200
characters at a time (due to ptycnt);
SETZM 6;
loop:
SOSGE 2(2); Comment any characters there?;
JRST getbuf; Comment no, get a buffer;
ILDB 3,1(2); Comment load a char from buffer;
JUMPE 3,loop; Comment ignore nulls;
IDPB 3,1; Comment put it into ptybuf;
AOS 6; Comment increment our count;
CAIG 6,ptycnt; Comment have we reached ptycnt?;
JRST Loop; Comment no get another char;
JRST all!done; Comment yes, all finished;
Comment get a buffer from the monitor;
getbuf:
SKIPA 4,ptychn;
inins: IN 0,;
LSH 4,23;
ADD 4,inins;
XCT 4; Comment do an input UUO;
JRST Chk; Comment check to make sure buffer isn't empty;
Comment enter here when we get an error on input UUO;
JRST error;
Comment if count of buffer is 0, all finished;
chk: SKIPE 2(2);
JRST loop; Comment buffer has something;
JRST all!done; Comment buffer is empty, all finished;
End;
error:
outstr("Error while inputting to PTY STATUS bits -- "&
cvos(GETSTS(ptychn))&crlf);
Return(null);
Comment now take characters in ptybuf and make them into a real
string. Convert the 7-bit buffer to SAIL string.;
all!done:
For i_1 Step 1 Until ptycnt/5 Do
s_s&cvstr(ptybuf[i]);
Return(s);
End "INPPTY";
COMMENT
.next page
.ss(Procedure OUTPTY)
.index(Procedure OUTPTY)
.;
Internal Procedure OUTPTY(String str);
Comment
------------------------------------------------
this procedure outputs the string str to the pty;
Begin "PTYOUT"
Label all!done, loop, put, putbuf, outins, otfail;
String mystr;
Integer len;
" Get the string length and copy the string to be sent"
len_length((mystr_str));
" Set up the pointers"
Start!Code;
MOVE 1,len;
MOVE 2,mystr;
MOVE 4,ptobuf;
Comment register 1 has length of String, 2 has byte pointer
And 4 has address of output buffer ring
Register 3 will be used to store chars as
We get them from the string;
loop: ILDB 3,2; Comment get a charcter from the string;
PUSHJ P,put; Comment now output it;
SOSLE 1; Comment subtract one from length;
JRST Loop; Comment get another;
PUSHJ P,putbuf; Comment all finished, output buffer;
JRST all!done;
Comment routine to output a character to pty;
put:
Sosg 2(4); Comment check count;
PUSHJ P,putbuf; Comment no room in buffer, output buf first;
IDPB 3,1(4); Comment put char in buffer;
POPJ P,; Comment Return;
Comment Do an output UUO to flush buffer;
putbuf:
SKIPA 5,ptychn;
outins: OUT 0,;
LSH 5,23;
ADD 5,outins;
XCT 5; Comment output UUO instruction;
POPJ P,; Comment Return;
Comment fall through here on error on output;
JRST otfail;
" Successful output"
End;
all!done:
Return;
" output error"
otfail:
outstr ("Error while outputting to PTY STATUS bits -- "&
cvos(GETSTS(ptychn))&crlf);
End "PTYOUT";
COMMENT
.next page
.ss(Procedure PTYSTS)
.index(Procedure PTYSTS)
.;
Internal Integer Procedure PTYSTS;
Comment
------------------------
this procedure returns
true if it's ok to Do an output to pty
false if program should Do an input on pty
note:
The PTY may not be ready For input,
And may have nothing to output. In
This case, loop using hibernate UUO to wake every
Five seconds or when PTY STATUS
Changes;
Begin "PTYSTS"
Label hiber;
While true Do
Begin "loop"
Comment this code Does a JOBSTS UUO which we can use to
determine the state of the pty;
Quick!Code;
PUSH P,1;
MOVE 1,ptychn;
CALLI 1,'61;
JRST 4,0;
MOVEM 1,PSTATUS;
POP P,1;
End;
Comment PSTATUS now has JOBSTS ;
If PTYINP
Then Return(false)
Else If PTYOUT
Then Return(true)
Else Quick!Code;
Comment hibernate For 5 seconds or Until PTY changes PSTATUS;
PUSH P,1;
MOVSI 1,'40;
HRRI 1,5000;
hiber: CALLI 1,'72;
JRST 4,0;
POP P,1;
End;
End "loop";
End "PTYSTS";
COMMENT
.next page
.ss(Procedure GETSTS)
.index(Procedure GETSTS)
.;
Internal Integer Procedure GETPTY;
Comment
-------------------------
This procedure tries to open a pty and returns the following
values:
-2 if no PTY's are available
-1 if no channels are available
otherwise it returns the channel number for the pty;
Begin "GETPTY"
Integer j;
Label foo;
If (ptychn_GETCHAN) < 0 Then Return(-1);
" open ASCII PTY"
j_-1;
OPEN(ptychn,"PTY",0,1,1,100,0,j);
If j neq 0 Then Return(-2);
popblk_CHNCDB(ptychn); Comment get open block;
Comment we have opened a PTY successfully, now get open block
using sail call CHNCDB. From the open block we have the address
of the input and output buffer ring, save these addresses in
ptibuf, and ptobuf respectively;
Start!Code;
foo: MOVE 1,popblk;
MOVE 2,2(1);
HRRM 2,ptibuf;
HLRM 2,ptobuf;
End;
OUTPTY('15&'12); Comment prime pty;
Return (ptychn);
End "GETPTY";
End "PTYPKG.SAI";