*DECK,NP$SENF
*IF,DEF,XFR
USETEXT NX$ACBF
USETEXT AIPDEF
USETEXT HEADER
USETEXT NP$STAT
USETEXT NP$DB
USETEXT NP$NWL
USETEXT NP$MODE
USETEXT NP$GETS
USETEXT NX$ACBX
PROC NP$SENF(NBACKTRIG);
BEGIN
#
*1DC NP$SENF
*
* 1. PROC NAME AUTHOR DATE
* NP$SENF Y. C. YIP 02/19/1985
*
* 2. FUNCTIONAL DESCRIPTION
* NP$SENF PERFORMS THE SENDING ACTION OF A FILE IN
* CHARACTER MODE TO THE RECEIVER. THE SAME MODULE IS
* USED IN INBTRAHOST FILE TRANSFER.
*
* 3. METHOD USED
*
* LEGEND: CHECKMARK WINDOW SIZE REFERS TO THE
* MAX NUMBER OF DATA BLOCKS THAT CAN BE NETPUT
* BEFORE A CHECKMARK MUST BE SENT IF MFACIL USED
*
* MAX-CHARK REACHED REFERS TO THE MAXIMUM NUMBER
* OF CHECKMARKS THAT CAN BE SENT BEFORE A MR IS
* RECEIVED FROM THE RECEIVER.
*
* UNTIL ABL WINDOW CLOSED OR MAX CHECKMARKS REACHED OR
* EOI REACHED
* PERFORM:
* IF CHECKMARK WINDOW OPEN
* READ FROM DISKBUFF
* TEST FOR DISK FET STATUS AND UPDATE
* FTTEOR, FTTEOI AND FTTLEV ACCORDINGLY.
* IF RESTART PENDING FLAG SET
* SET CHECKMARK RESTART INDEX
* SET DISK OUTFET ACCORDING TO THE
* OFFSET CONTAINED IN THE CHECKMARK BUFFER ASSOCIATED
* WITH RESTART INDEX
* CLEAR RESTART PENDING FLAG
* ENDIF
* SAVE CURRENT DISK FETOUT IN DISKOLDOUT
* IF TRANSLATION FLAG SET
* THEN
* CALL TRANSLATION SERVICE
* ELSE
* COPY CONTENTS OF DISK BUFF INTO NETWORK BUFFER
* AS A INTRAHOST FILE TRANSFER ACTION.
* ENDIF
* IF MFACIL SET (ONLY FOR INTERHOST)
* THEN
* CALL NP$UPRU TO UPDATE FTTWORD, FTTDBIT AND FTTPRU.
* ENDIF
* IF NETWORK BUFFER FULL OR EOR REACHED
* THEN
* SET LOC$HA AND LOC$TA
* SET ACN AND TLC
* IF DISK BUFFER ALSO EMPTY
* UPDATE TBH$TBC
* ENDIF
* IF FTTEOI SET
* SET NBACKTRIG TO TRIG-EOI
* EXIT LOOP
* ENDIF
* SET TBH IN THE HEADER
* NEPUT BLOCK.
* RESET NETBUF FET POINTERS
* RESET CMB$NBYTE, CMB$NCOUNT AND CMB$NBUF FLAG
* IF MFACIL USED (ONLY FOR INTERHOST)
* DECREMENT CHECKMARK WINDOW SIZE BY 1
* ENDIF
* ELSE
* PERFORM A SHORT TIME RECALL
* SET BACKTRIG TO SEND TRIGGER AGAIN
* ENDIF
* ELSE (MS WINDOW CLOSED)
* IF ABL WINDOW OPEN
* SEND CHECKMARK
* UPDATE CHECKMARK STATUS BUFFER FROM FTT
* ENDIF
* ENDIF
* END-LOOP (END OF UNTIL)
* IF ABL WINDOW CLOSED
* THEN
* SET FTTSTATE TO ABL-CLOSED-STATE
* ENDIF
* IF MAX-CHECKMARK REACHED
* SET FTTSTATE TO MAX-CHECKMARK-REACHED STATE
* ENDIF
* RETURN
*
* 4. ENTRY CONDITIONS
* FTTINDEX SET TO THE CURRENT FILE TRANSFER INDEX.
*
* 5. EXIT CONDITONS
* FTTLEV UPDATED.
* DISKFET UPDATED
* NBACKTRIG SET TO EOI=TRIGGER IF EOI REACHED
*
* 6. COMDECKS CALLED AND SYMPL TEXTS USED.
* NP$NWL, NX$ACBX
*
* 7. ROUTINES CALLED
* NP$CIO - CALLS CIO FUNCTIONS TO PERFORM READ
* NP$RCL - PERFORMS TIME RECALL
* NP$D2N - PERFORMS DISK TO NETBUF TRANSLATION
* NP$PUT - PERFORMS NETPUT
* NP$UPRU - PERFORMS UPDATING OF PRU NUMBER, WORD AND DBIT
* IN THE FTT.
* NP$BT
* NUMBERS.
* 8. DAYFILE MESSAGES
* NONE
*
#
#
****
#
XREF
BEGIN
PROC NP$CIO; # PROCEDURE TO PERFORM CIO FUNCTIONS#
PROC NP$D2N; # TRANSLATION SERVICE FROM DISK TO #
# NETWORK BUFFER #
PROC NP$RCL; # PROCEDURE TO PERFORM THE RECALL #
PROC NP$PUT; # INTERNAL PROCEDURE TO NETPUT BLOCK#
PROC NETPUT; # PROCEDURE TO NETPUT BLOCKS #
PROC NP$UPRU; # PROCEDURE TO UPDATE PRU,WORD AND #
# DBIT IN FTT #
PROC NP$BTO8; # PROC TO TRANSLATE INTEGER TO ASCII#
PROC NP$SHRK; # PROC TO SHRINK CHECKMARK TABLE #
END
#
****
#
DEF COLON # O"072"#; # DEFINITIONS FOR COLON 64 CHARSET #
DEF COLON3 # 3 #; # HALF BYTE OF 072 #
DEF COLON10 # 10 #; # LOWER HALF BYTE OF 072 #
ITEM NBACKTRIG; # BACK TRIGGER #
ITEM INDEX; # LOOP INDEX #
ITEM DONE B; # DONE FLAG #
ITEM CHKINDEX; # TEMPORARY CHECKMARK INDEX #
ITEM DISKOLDOUT; # OLD OUT POINTER OF DISK #
ITEM CONT B; # CONTINUATION FLAG #
ITEM INDEX1; # LOOP INDEX #
BASED ARRAY COPYAREA[0:0] S(1);
BEGIN
ITEM WORD U(00,00,60); # TEMPLATE FOR CHANGING MEMORY #
END
CONTROL EJECT;
# #
# CODE OF NP$SENF BEGINS HERE #
# #
P<CMB> = FTTCMV$BLK[FTTINDEX]; # SET CMB TEMPLATE TO CHARACTER #
# CONVERSION ADDRESS FROM FTT #
P<FET$CIO> = FTTFETADR[FTTINDEX]; # SET FET$CIO TEMPLATE TO #
# FET ADDRESS FROM FTT #
P<FET$WORK> = FTTFETW[FTTINDEX]; # SET NETWORK FET TO ADDRESS #
# FROM FTT #
P<CHK> = FTTCKTBL[FTTINDEX]; # CHECK MARK TABLE ADDRESS #
DONE = FALSE; # SET DONE FLAG TO FALSE #
P<TBH$HDR> = FETWFIRST[0]; # SET TBH TEMPLATE TO FIRST WORD #
# OF THE NETWORK BUFFER #
FOR INDEX = 0 WHILE (FTTCURBLK[FTTINDEX] GR 0) AND
( FTTOUTCWS[FTTINDEX] NQ FTTCWS[FTTINDEX]) AND
NOT DONE
DO # LOOP WHILE ABL WINDOW OPEN AND #
BEGIN # MAX CHECKMARKS NOT REACHED AND #
# EOI NOT YET READ FROM DISK #
IF FTTBLK$MS[FTTINDEX] GR 0 # IF MS WINDOW OPEN #
THEN
BEGIN
IF FETCOMP[0] AND FTTEORI[FTTINDEX] EQ 0 # IF CIO COMPLETE #
THEN # AND LAST STATUS FROM DISK NOT EOR #
BEGIN # OR EOI #
# GET DATA IS REQUIRED #
FETCODE[0] = 0; # CLEAR FETCODE #
NP$CIO(CIO$READ); # PERFORM CIO READ #
IF FETEC[0] NQ 0 AND FETSTATUS[0] NQ CIO$EOI
THEN # IF AT NQ 0 AND STATUS = 741031B #
BEGIN
NBACKTRIG = NSCTERR; # SET BACKTRIG TO CIO ERROR #
GOTO NPEXIT; # EXIT LOOP AND RETURN #
END
ELSE
BEGIN
IF FETCODE[0] EQ CIO$NORMAL # IF RETURN CODE = 11B #
THEN
BEGIN
FTTTBC[FTTINDEX] = 0; # CLEAR TBC FROM FTT #
END
ELSE
BEGIN
IF FETCODE[0] EQ CIO$EOR OR FETCODE[0] EQ CIO$EOF
THEN # IF EOR OR EOF FOUND IN CODE #
BEGIN
FTTEOR[FTTINDEX] = TRUE; # SET EOR FLAG IN FTT #
FTTLEV[FTTINDEX] = FETLEVEL[0]; # SAVE LEVEL NUMBER #
END
IF FETEC[0] EQ 1 # EOI IS FOUND #
THEN
BEGIN
FTTEOI[FTTINDEX] = TRUE; # SET EOI FLAG IN FTT #
FETEC[0] = 0; # CLEAR ERROR CODE #
END
END
END
END # GET DATA IS REQUIRED #
IF FTTRPND[FTTINDEX] # IF RESTART PENDING #
THEN
BEGIN
IF CHK$IDX[0] EQ CHK$START # IF A NON-ZERO CHECKMARK EXIST#
THEN
BEGIN
CHKINDEX = CHK$START; # SAVE POINTER TO CHECKMARK TABLE #
FETOUT[0] = FETOUT[0] + CHK$WORD[CHKINDEX];
END
ELSE
BEGIN
CHKINDEX = 1; # START FROM RR(0) #
END
FTTRPND[FTTINDEX]= FALSE; # CLEAR RESTART PENDING FLAG #
END # ENTRY #
DISKOLDOUT = FETOUT[0]; # SAVE OLD FET OUT POINTER #
IF NOT FTTNOTRAN[FTTINDEX] # IF TRANSLATION NEEDED #
THEN
BEGIN
NP$D2N(LOC(FETWFIRST[0]),LOC(FETFIR[0]),P<CMB>); # CALL TS#
END
ELSE
BEGIN # TRANSLATION NOT NEEDED #
P<COPYAREA> = 0;
IF FETWIN[0] EQ FETWFIRST[0] # BEGINNING OF BLOCK #
THEN
BEGIN
FETWIN[0] = FETWIN[0] + 1; # RESERVE ONE WORD FOR TBH #
END
IF (FTTEOI[FTTINDEX] OR # IF EOI SET #
FTTEOR[FTTINDEX]) AND
(FETIN[0] EQ FETOUT[0]) # DISK BUFFER EMPTIED #
THEN
BEGIN
CONT = FALSE; # DO NOT COPY FROM DISK BUFFER#
CMB$DBUF[0] = 1; # SET DISKBUF EMPTY FLAG #
END
ELSE
BEGIN
CONT = TRUE; # COPY FROM DISK BUFFER #
END
FOR INDEX1 = 0 WHILE CONT # COPY DATA INTO NETBUF #
DO
BEGIN
WORD[FETWIN[0]] = WORD[FETOUT[0]]; # COPY DISK DATA #
# INTO NETBUF #
FETWIN[0] = FETWIN[0] + 1; # BUMP IN PTR OF NETBUF #
FETOUT[0] = FETOUT[0] + 1; # BUMP OUT PTR OF DISK BUF #
IF FETOUT[0] EQ FETLIM[0] # WRAP AROUND DISKBUF #
THEN
BEGIN
FETOUT[0] = FETFIR[0]; # SET OUT PTR TO FIRST PTR #
END
IF FETIN[0] EQ FETOUT[0] # DISKBUF EMPTIED #
THEN
BEGIN
CMB$DBUF[0] = 1; # DISK BUFFER EMPTY #
FETIN[0] = FETFIR[0];
FETOUT[0] = FETFIR[0];
CONT = FALSE; # EXIT LOOP #
END
IF FETWIN[0] EQ FETWLIMIT[0] # NETBUF FILLED #
THEN
BEGIN
CONT = FALSE; # EXIT LOOP #
CMB$NBUF[0] = 1; # SET NETBUF TO BE FULL #
END
END # END FOR LOOP #
END # END IF #
IF FTTMFACIL[FTTINDEX] # IF MFACIL SPECIFIED #
THEN
BEGIN
NP$UPRU(DISKOLDOUT,FETOUT[0]);#UPDATE PRU NUMBER WITH OLD #
END # AND NEW DISK OUT PTR #
IF CMB$NBUF[0] EQ 1 OR # IF NET BUFFER IS FULL #
FTTEOR[FTTINDEX] # OR EOR IS TRUE FROM FTT #
THEN # PUT MSG PROCESSING BEGINS #
BEGIN
IF NOT FTTNOTRAN[FTTINDEX] # IF TRANSLATION NEEDED #
THEN
BEGIN
LOC$HA = LOC(OUT$DATA); # SET HEADER TO DATA HEADER #
LOC$TA = FETWFIRST[0]; # TA SET TO FIRST WORD ADDRESS#
# OF NETWORK BUFFER #
OUT$DAACN[0] = FTTACN[FTTINDEX]; # SET ADR IN HEADER #
OUT$DATLC[0] = CMB$NCOUNT[0];
END
ELSE
BEGIN # INTRHOST BINARY FILE XFR #
LOC$HA = LOC (OUT$INTRA);
# SET HEADER TO INTRHOST HDR #
LOC$TA = FETWFIRST[0]; # SET TEXT ADDRESS TO FIRST #
OUT$INTACN[0] = FTTACN[FTTINDEX]; # SET ADR #
OUT$INTTLC[0] = (FETWIN[0] - FETWFIRST[0])*15/2;
END # FOR ACT = 2 #
TBH$WRD[0] = 0; # CLEAR TBH #
IF CMB$DBUF[0] EQ 1 # IF DISK BUFFER EMPTY #
THEN
BEGIN
TBH$TBC[0] = FTTTBC[FTTINDEX]; # UPDATE TBC OF TBH #
# USING TBC FROM FTT #
FTTEOR[FTTINDEX] = FALSE; # CLEAR EOR BIT IN FTT #
P<COPYAREA> = 0;
IF CMB$STATE[0] NQ 0 # IF DAGGLING 00 OCCUR #
THEN
BEGIN
OUT$DATLC[0] = OUT$DATLC[0] + 1; # ADD 072B : #
CMB$NCOUNT[0] = CMB$NCOUNT[0] + 1;
IF CMB$NBYTE LS 0 # IF HALF BYTE AVAILABLE #
THEN
BEGIN
B<56,04>WORD[FETWIN[0]] = COLON3;
B<00,04>WORD[FETWIN[0] + 1] = COLON10;
END
ELSE
BEGIN # COMPLETE BYTE #
B<52 - CMB$NBYTE[0],8>WORD[FETWIN[0]] = COLON;
END
END
CMB$STATE[0] = 0; # CLEAR STATE FROM POSSIBLE #
# REMAINING GARBAGE #
IF FTTEOI[FTTINDEX] # EOI TRUE FROM FTT #
THEN
BEGIN
DONE = TRUE; # SET DONE FLAG TO TRUE #
NBACKTRIG = NSCTEOI; # SET BACK TRIG TO EOI TRIGGER#
END
END
TBH$TBN[0] = FTTTBN[FTTINDEX]; # SET SERIAL BLOCK NUMBER#
FTTTBN[FTTINDEX] = FTTTBN[FTTINDEX] + 1; # BUMP TBN IN FTT#
IF NOT FTTNOTRAN[FTTINDEX] # IF TRANSLATION NEEDED #
THEN
BEGIN
TBH$OLEN[0] = CMB$NCOUNT - TBH$LEN; # UPDATE OLEN IN TBC#
END
ELSE # INTRAHOST BINARY #
BEGIN
CMB$DBUF[0] = 0; # READY FOR NEXT READ AND SO #
# SET DISK BUFFER NOT EMPTY #
TBH$OLEN[0] = OUT$INTTLC[0]; # OLEN ACCORDING TO ACT =4 #
END
OPCODE = OP$PUT; # SET OPCODE IN NETPUT #
*IF DEF,STAT,1
IAM = TYPE"PUT"; # SET TYPE OF EXECUTING #
# ROUTINE #
NP$PUT; # NETPUT BLOCK #
FTTCURBLK[FTTINDEX] = FTTCURBLK[FTTINDEX] - 1;
# DECREASE ABL WINDOW #
FETWIN[0] = FETWFIRST[0]; # RESET IN POINTER FOR NETBUF #
FETWOUT[0] = FETWFIRST[0]; # RESET OUT POINTER FOR NETBUF#
TBH$FWD[0] = 0; # CLEAR FIRST WORD OF NETBUF #
CMB$NCOUNT[0] = TBH$LEN; # RESET CMB$NCOUNT TO 6 #
CMB$NBYTE[0] = INITNBYTE; # RESET CMB$NBYTE TO 4 #
CMB$NBUF[0] = 0; # SET NETFUF EMPTY FLAG #
IF FTTMFACIL[FTTINDEX] # IF MFACIL SPECIFIED #
THEN
BEGIN
FTTBLK$MS[FTTINDEX] = FTTBLK$MS[FTTINDEX] - 1;
END
END
ELSE
BEGIN # NETBUF NOT FULL OR DISK #
NP$RCL(0); # DISK BUFFER NOT EMPTY #
NBACKTRIG = NSCTSND; # AND NOT EOI #
# SET SEND DATA AS BACK TRIG #
IF FTTNOTRAN[FTTINDEX] # IF INTRAHOST BINARY XFR #
THEN
BEGIN
CMB$DBUF[0] = 0; # SET DISK BUFFER NOT EMPTY #
END
END # SET SEND TRIGGER AS BACKTRIG#
# SEND SEND DATA AS BACKTRIG #
END
ELSE
BEGIN
# MS WINDOW CLOSED NETPUT(MS)#
IF FTTMFACIL[FTTINDEX] # IF M FACIL SPECIFIED #
THEN
BEGIN
IF FTTCURBLK[FTTINDEX] GR 0 # IF ABL WINDOW OPEN #
THEN
BEGIN
FTTBLK$MS[FTTINDEX] = MSWINDOWSZ; # RESET MS WINDOW #
FTTOUTCWS[FTTINDEX] = FTTOUTCWS[FTTINDEX] + 1;
# BUMP OUTSTANDING CHECKMARK #
# COUNT #
FTTLCKSNT[FTTINDEX] = FTTLCKSNT[FTTINDEX] + 1;
NP$BTO8(FTTLCKSNT[FTTINDEX],CHKINDEX); # CONVERT TO ASCII#
ABH$L7ADR = FTTACN[FTTINDEX]; # SET ADR IN ABH #
L7$PFC = LEV7$MS; # SEND MS #
L7$DD = B<STARTBIT,DDLEN>CHKINDEX;
OPCODE = OP$PUT;
LOC$HA = LOC(ABH$LEV7); # SET HEADER ADDRESS #
LOC$TA = LOC(LV7$MSG); # SET TEXT ADDRESS #
*IF DEF,STAT,1
IAM = TYPE"PUT";
*IF DEF,DEBUG,1
DB$CALL = LOC(NETPUT); # COLLECT STATISTICS #
NP$PUT; # NETPUT MS #
FTTCURBLK[FTTINDEX] = FTTCURBLK[FTTINDEX] - 1;
CHK$IDX = CHK$IDX + 1; # BUMP LAST ENTRY OF CHECKMARK#
# TABLE #
CHK$MARK[CHK$IDX] = FTTLCKSNT[FTTINDEX];
CHK$WORD[CHK$IDX] = FTTWORD[FTTINDEX]; # CHECKMARK TABLE #
CHK$DBIT[CHK$IDX] = FTTDBIT[FTTINDEX];
CHK$PRUNO[CHK$IDX] = FTTCURPRU[FTTINDEX];#CURPRU UPDATED #
CHK$TBN[CHK$IDX] = FTTTBN[FTTINDEX]; # TBN SAVED #
END
END
END # TRANSLATION #
END # END WHILE #
IF FTTCURBLK[FTTINDEX] EQ 0 # IF ABL WINDOW CLOSED #
THEN
BEGIN
FTTSTATE[FTTINDEX] = NSCCABL; # NEW STATE IS ABL-CLOSED STAE #
END
IF FTTOUTCWS[FTTINDEX] EQ FTTCWS[FTTINDEX]
THEN
BEGIN # IF MAX CHECKMARKS REACHED #
NBACKTRIG = NSCTMCM; # SET BACK TRIGGER TO MAX CHECKMRKS #
END # REACHED TRIGGER #
NPEXIT: RETURN; # RETURN TO CALLER #
END # END OF PROC NP$SENF #
TERM
*ENDIF