.TITLE CHKCMD - CHECK AND PROCESS VALID LIST COMMANDS .IDENT /04.4/ .ENABL LC ;+ ; ; ; Free software BY ; Project Software & Development, Inc. ; ; This software is furnished for free and may be used and copied as ; desired. This software or any other copies thereof may be provided ; or otherwise made available to any other person. No title to and ; ownership of the software is hereby transferred or allowed. ; ; The information in this software is subject to change without notice ; and should not be construed as a commitment by PROJECT SOFTWARE ; AND DEVELOPMENT, INC. ; ; PROJECT SOFTWARE assumes no responsibility for the use or reliability ; of this software on any equipment whatsoever. ; ; Project Software & Development, Inc. ; 14 Story St. ; Cambridge, Ma. 02138 ; 617-661-1444 ; ; ; Title: CHKCMD ; Author: Robin Miller ; Date: October 27, 1981 ; ; Description: ; ; This module is used to check the valid LIST commands. If the ; command is valid, then it is executed before returned to list any ; further lines in the file. If it is invalid, it is simply ignored. ; ; ; Modification History: ; ;- .ENABL AMA .MCALL DIR$, QIOW$S .SBTTL LOCAL EQUATES/STORAGE ; ; Local equates. ; BELL = 7 ; ASCII FOR BELL HT = 11 ; ASCII FOR HORIZONTAL TAB LF = 12 ; ASCII FOR LINE FEED CR = 15 ; ASCII FOR CARRIAGE RETURN SPACE = 40 ; ASCII FOR SPACE DEFCNT = 8. ; DEFAULT COUNT FOR LEFT/RIGHT TXTBIT = 1 ; INCLUDE TEXT OF MESSAGE MIDBIT = 2 ; INCLUDE MESSAGE ID SEVBIT = 4 ; INCLUDE SEVERITY LEVEL FACBIT = 10 ; INCLUDE FACILITY NAME ; ; Local storage. ; NEGFLG: .BYTE 0 ; NEGATION FLAG <> 0 = TRUE RULFLG: .BYTE 0 ; RULER ON SCREEN FLAG SWFLG: .BYTE 0 ; SWITCH "/" FLAG <> 0 = TRUE .EVEN BCKCNT:: .WORD 0 ; NUMBER OF LINES TO BACKUP LINES: .WORD 0 ; NUMBER OF LINES ON SCREEN SCRCNT: .WORD 15. ; NUMBER OF LINES TO SCROLL RULADR: .WORD 0 ; LAST RULER DISPLAYED CMD:: .BLKB 132. ; COMMAND INPUT BUFFER CMDL == .-CMD ; LENGTH OF BUFFER NOTFND: .ASCII %String was not found - % FNDBUF: .BLKB CMDL ; SEARCH STRING BUFFER ; Argument block for error messages. ERRBLK: .BYTE 6,0 ; ARG BLOCK FOR GETMSG .WORD ERRCOD ; ADDRESS OF ERROR CODE .WORD TYOBUF ; ADDRESS OF OUTPUT BUFFER .WORD MSGFLG ; ADDRESS OF FLAG WORD .WORD -1 ; NO FACILITY NAME WANTED .WORD STACOD ; ADDRESS FOR STATUS RETURN .WORD -1 ; ADDRESS OF MESSAGE FACILITY ERRCOD: .WORD 0 ; ERROR MESSAGE CODE MSGFLG: .WORD TXTBIT ; TEXT OF MESSAGE ONLY STACOD: .WORD 0 ; STATUS CODE RETURN .EVEN .SBTTL COMMAND DISPATCH TABLE ;+ ; ; This table contains a list of the valid commands: ; ;- CMDTBL: .BYTE 'A,0 .WORD ADVANC ; SET ADVANCE MODE .BYTE 'B,0 .WORD BOTTOM ; BOTTOM OF FILE (BACKWARD) .BYTE 'D,0 .WORD DELETE ; DELETE FILE .BYTE 'E,0 .WORD EXIT ; EXIT FROM LISTING .BYTE 'F,0 .WORD FIND ; FIND SEARCH STRING (FULL) .BYTE 'H,0 .WORD HELP ; DISPLAY SOME HELP (HALF) .BYTE '?,0 .WORD HELP ; DISPLAY SOME HELP .BYTE 'K,0 .WORD KEYHLP ; VT100 KEYPAD HELP .BYTE 'L,0 .WORD LEFT ; MOVE MARGIN LEFT .BYTE 'N,0 .WORD NEXT ; DISPLAY NEXT FILE (NARROW) .BYTE 'P,0 .WORD PAGE ; FIND NEXT PAGE (PRINT) .BYTE 'R,0 .WORD RIGHT ; MOVE MARGIN RIGHT (REFRESH,RULER) .BYTE 'S,0 .WORD SEEALL ; SEEALL NON-PRINTABLES .BYTE 'T,0 .WORD TOP ; TOP OF FILE .BYTE 'V,0 .WORD VFU ; TOGGLE VFU SWITCH .BYTE 'W,0 .WORD WIDE ; DISPLAY WIDE LISTING .BYTE '.,0 .WORD DOT ; MOVE DOT + or - LINES .BYTE '+,0 .WORD PLUS ; DISPLAY +n LINES FORWARD .BYTE '-,0 .WORD MINUS ; DISPLAY -n LINES BACKWARD .BYTE 0,0 ; END OF COMMAND TABLE ; ; Local messages. ; .NLIST BEX DELMSG: .ASCIZ %Really DELETE this file ? % FNDMSG: .ASCIZ %Search for: % NOTDEF: .ASCIZ %Key is not defined% HLPMSG: .BYTE .ASCII %The following commands may be used in LIST:% .BYTE ,,, .ASCII % A(dvance) - Lists forward through file (default).% .ASCII % B(ottom) - Lists the bottom of the file.% .ASCII % BA(ckward)- Lists backward through file.% .ASCII % D(elete) - Deletes the current file.% .ASCII % E(xit) - Exits from listing.% .ASCII % F(ind) - Searches forward for specified string.% .ASCII % FN(ext) - Finds next occurance of search string.% .ASCII % FU(ll) - Lists full pages (default).% ; .ASCII % H(elp) or ? - Displays this help frame.% .ASCII % HA(lf) n - Lists half pages (default = 15).% .ASCII % L(eft) n - Moves window left 'n' positions.% .ASCII % N(ext) - Starts listing of the next file.% .ASCII % NA(rrow) - Lists file on a narrow screen.% .ASCII % P(age) - Starts listing at the next formfeed.% .ASCII % PR(int) - Prints the current file.% .ASCII % R(ight) n - Moves window right 'n' positions.% .ASCII % RU(ler) - Displays ruler on top of screen.% .ASCII % S(eeall) - Displays non-printable characters.% .ASCII % T(op) - Lists the top of the file.% .ASCII % W(ide) - Lists file on a wide screen.% .ASCII % record n - Starts listing at record # 'n'.% ; .ASCII % .+n or -n - Starts listing forward/backward n records.% .BYTE , .ASCIZ %Press the RETURN key to continue: % ; Two different rulers for ruler command. RULTWO: .ASCII %1 5 10 15 20 25 30 35 40 45 5% .ASCII %0 55 60 65 70 75 80 85 90 95 1% .ASCII %00 105 110 115 120 125 130 135 140 145 1% .ASCII %50 155 160 165 170 175 180 185 190 195 2% .ASCII %00 205 210 215 220 225 230 235 240 245 2% .ASCIZ %50 255 260 265 270 275 280 285 290 295 300% RULONE: .ASCII %123456789 123456789 123456789 123456789 123456789 % .ASCII %123456789 123456789 123456789 123456789 123456789 % .ASCII %123456789 123456789 123456789 123456789 123456789 % .ASCII %123456789 123456789 123456789 123456789 123456789 % .ASCII %123456789 123456789 123456789 123456789 123456789 % .ASCIZ %123456789 123456789 123456789 123456789 123456789 % .EVEN ;+ ; ; CHKCMD - Check for a valid list control command. ; ; This routine is called to check for various list control commands. ; ; Inputs: ; OLDREC = Record number of previous page. ; CURREC = Record number at bottom of page. ; ; Outputs: ; All registers are destroyed. ;- CHKCMD:: CLR LINCNT ; INIT CURRENT LINE COUNT CLR SWFLG ; INITIALIZE SWITCH FLAG MOV CURREC+2,LINES ; COPY THE CURRENT RECORD SUB OLDREC+2,LINES ; CALCULATE LINES ON SCREEN MOV CURREC,WTGREC ; COPY CURRENT RECORD MOV CURREC+2,WTGREC+2 ; TO WTG RECORD # BIC #B.BACK,STATUS ; INIT BACKUP PARTIAL PAGE CALL WRTEOS ; WRITE END OF SCREEN SEQUENCE BR DOPRMT ; WRITE THE PROMPT NXTCMD::CALL POSEOS ; POSITION FOR NEXT COMMAND DOPRMT: CALL ADDATR ; ADD VT100 ATTRIBUTES MOV #PROMPT,R4 ; PROMPT STRING ADDRESS CALL WRITE ; WRITE THE MESSAGE CALL GETCMD ; REQUEST COMMAND FROM USER TST R1 ; DID WE GET ANYTHING ? BNE 10$ ; IF NE, YES BIC #B.PINV,STATUS ; FORCE VALID PAGE MARKER JMP RET ; ELSE, RETURN ... ; Check for escape sequence. If escape sequence, and byte count is ; greater then escape sequence size (3), presume keypad was used ; to terminate a normal LIST command at bottom of screen. 10$: CMP TIOSB,#IS.ESQ ; ESCAPE SEQUENCE ? BNE 20$ ; IF NE, NO CMP TIOSB+2,#3 ; CHECK FOR NORMAL COMMAND BGT 20$ ; IF GT, PROCESS NORMALLY ADD R1,R0 ; POINT TO END OF INPUT DEC R0 ; POINT TO LAST BYTE CALL KEYPAD ; CHECK KEYPAD COMMAND BCC CHKTBL ; IF CC, VALID KEY CALL WRTEOS ; DO END OF SCREEN SEQUENCE MOV #NOTDEF,R4 ; "Key is not defined" CALL WRTERR ; WRITE THE ERROR MESSAGE BR NXTCMD ; GET THE NEXT COMMAND ; Check for negate flag. 20$: CLRB NEGFLG ; PRESUME NO NEGATE CMPB (R0),#'- ; NEGATE WANTED ? BNE SLASH ; IF NE, NO INC R0 ; PRESUME COMMAND NEXT INCB NEGFLG ; SHOW NEGATION ; If slash specified for switch, skip it so command still works. SLASH: CMPB (R0),#'/ ; SLASH FOR SWITCH ? BNE CHKTBL ; IF NE, NO INC SWFLG ; YES, SET SWITCH FLAG INC R0 ; POINT PAST SLASH ; Check command table for valid command. CHKTBL: MOV #CMDTBL,R1 ; START OF COMMAND TABLE 10$: CMPB (R0),(R1) ; IS THIS THE COMMAND ? BEQ 20$ ; IF EQ, YES (DO IT) ADD #4,R1 ; POINT TO NEXT ENTRY TST (R1) ; END OF TABLE ? BNE 10$ ; IF NE, NO CMPB -(R0),#'- ; SPECIAL CASE FOR -n BEQ CHKTBL ; IF EQ, FIND ENTRY INC R0 ; POINT TO POSSIBLE # JMP NUMBER ; YES, CHECK FOR NUMBER ; Found a valid command, now jump to it. 20$: TST (R1)+ ; POINT TO THE ADDRESS JMP @(R1)+ ; JUMP TO THE ROUTINE ; A(dvance). Advance through the file. ADVANC: BIS #B.FORW,STATUS ; SET FORWARD DIRECTION JMP CHKCMD ; GET NEXT COMMAND ... ; B(ottom) command. Position at bottom of file. BOTTOM: CMPB 1(R0),#'A ; BACKWARD SCROLL ? BEQ BACKWD ; IF EQ, YES ; BIC #B.FORW,STATUS ; SET SCROLL BACKWARD MOV #-1,WTGREC ; SET HIGHEST MOV #-1,WTGREC+2 ; RECORD NUMBER JMP DOIT ; AND POINT TO IT ; BA(ckward). List backward through file. BACKWD: BIC #B.FORW!B.EOF,STATUS ; SHOW LISTING BACKWARD JMP CHKCMD ; GET NEXT COMMAND ... ; D(elete) command. Delete the current file. DELETE: CALL WRTMSG ; PREPARE FOR MESSAGE MOV #DELMSG,R4 ; SET MESSAGE ADDRESS CALL WRITE ; AND WRITE IT CALL GETCMD ; GET RESPONSE FROM USER CMPB (R0),#'Y ; REALLY DELETE FILE ? BNE 50$ ; IF NE, NO MOV FDBADR,R0 ; COPY THE FDB ADDRESS CALL .DLFNB ; DELETE THE FILE BCS 10$ ; IF CS, FAILED BIS #B.KILL!B.NEXT,STATUS ; SHOW FILE DELETED RETURN ; AND RETURN ... 10$: MOV FDBADR,R0 ; COPY THE FDB ADDRESS MOV F.ERR(R0),ERRCOD ; NOW COPY THE ERROR CODE MOV #ERRBLK,R5 ; SET ERROR ARGUMENT BLOCK CALL GETMSG ; AND GET THE ERROR MESSAGE MOV #TYOBUF,R4 ; SET BUFFER ADDRESS MOV R4,R3 ; COPY THE BUFFER ADDRESS ADD STACOD,R3 ; POINT TO END OF MESSAGE MOVB #BELL,(R3)+ ; RING BELL ON ERROR CLRB (R3) ; SET TERMINATOR CALL WRTERR ; WRITE THE ERROR MESSAGE CALL GETCMD ; WAIT FOR RESPONSE BIS #B.NEXT,STATUS ; GO ON TO NEXT FILE RETURN ; AND RETURN ... 50$: JMP CHKCMD ; READ COMMAND AGAIN ; E(xit) command. Exit from LISTing. EXIT: BIS #B.EXIT,STATUS ; SHOW TIME TO EXIT RETURN ; F(ind) command. Find specified search string. FIND: CMPB 1(R0),#'O ; FORWARD COMMAND ? BEQ ADVANC ; IF EQ, YES CMPB 1(R0),#'U ; FULL COMMAND ? BEQ FULL ; IF EQ, YES CMPB 1(R0),#'E ; FORCE EXIT ? BEQ FEXIT ; IF EQ, YES CMPB 1(R0),#'F ; PASS FORFEED ? BEQ FFSSW ; IF EQ, YES CMPB 1(R0),#'N ; FIND NEXT ? BEQ 30$ ; IF EQ, YES CALL SKIP ; SKIP PAST COMMAND BCC 10$ ; IF CC, GOT STRING 5$: CALL WRTEOS ; WRITE END OF SCREEN SEQUENCE MOV #FNDMSG,R4 ; PROMPT STRING CALL WRITE ; WRITE THE MESSAGE CALL GETCMD ; REQUEST SEARCH STRING TST R1 ; DID WE GET ONE BNE 10$ ; IF NE, YES JMP CHKCMD ; NOPE, PROMPT AGAIN 10$: MOV #FNDBUF,R2 ; SEARCH STRING BUFFER 20$: MOVB (R0)+,(R2)+ ; COPY THE SEARCH STRING BNE 20$ ; BR TILL DONE 30$: TSTB FNDBUF ; GOT A SEARCH STRING ? BEQ 5$ ; IF EQ, NO (GET ONE) CALL MRKSAV ; SAVE CURRENT DOT ; If search string active, start next search from end of last. BIT #B.SRCH,STATUS ; IS SEARCH STRING ACTIVE ? BEQ 40$ ; IF EQ, NO CMP SRECRD,OLDREC ; POSSIBLY THIS RECORD ? BNE 40$ ; IF NE, NO CMP SRECRD+2,OLDREC+2 ; IS SEARCH STRING ON SCREEN ? BLOS 40$ ; IF LOS, NO CMP SRECRD,CURREC ; POSSIBLY THIS RECORD ? BNE 40$ ; IF NE, NO CMP SRECRD+2,CURREC+2 ; REALLY ON THE SCREEN ? BHI 40$ ; IF HI, NO MOV SRECRD,WTGREC ; COPY SEARCH MOV SRECRD+2,WTGREC+2 ; STRING RECORD ADD #1,WTGREC+2 ; START AT ADC WTGREC ; SEARCH RECORD +1 CALL POINTR ; POINT TO IT BR 50$ ; NOW DO THE SEARCH ; Search string not active or not on the screen, start at top of page. 40$: CALL PNTDOT ; POSITION TO TOP RECORD 50$: MOV #FNDBUF,R2 ; SEARCH STRING BUFFER CALL SEARCH ; GO SEARCH FOR IT BCC 60$ ; IF CC, GOT IT CALL PNTSAV ; REPOSITION LAST DOT BIC #B.SRCH,STATUS ; NO SEARCH STRING ACTIVE CALL WRTEOS ; WRITE END OF SCREEN SEQUENCE MOV #NOTFND,R4 ; "String was not found - " CALL WRTERR ; WRITE THE ERROR MESSAGE JMP NXTCMD ; GET THE NEXT COMMAND 60$: BIS #B.SRCH,STATUS ; SHOW SEARCH STRING ACTIVE MOV MAXLIN,R1 ; BACKUP HALF A PAGE TO ASR R1 ; CENTER SEARCH STRING JMP ADJPAG ; GO ADJUST THE PAGE ; FE or /FE. Force exit switch (only exit on EXIT or NEXT command). FEXIT: MOV #FESW,R0 ; SWITCH TO SET OR CLEAR CALL SWITCH ; GO DO IT JMP CHKCMD ; ASK FOR NEXT COMMAND ; FF or /FF. Pass formfeed to terminal (for VT100 printer port option). FFSSW: MOV #FFSW,R0 ; SWITCH TO SET OR CLEAR CALL SWITCH ; GO DO IT CALL PNTDOT ; SET TO REDISPLAY PAGE JMP CLEAR ; AND GO DO IT ; FU(ll) command. Display full pages. FULL: BIS #B.FULL,STATUS ; SHOW DISPLAY FULL PAGE MOV MAXLIN,SCRCNT ; SET FULL SCROLL COUNT JMP CHKCMD ; GET NEXT COMMAND ... ; H(elp) command. Display the Help frame. ; K(eypad) command. Display VT100 keypad. .ENABL LSB HELP: CMPB 1(R0),#'A ; HALF PAGES COMMAND ? BEQ HALF ; IF EQ, YES MOV #HLPMSG,R4 ; HELP MESSAGE (1ST PART) BR 10$ ; AND CONTINUE ... KEYHLP: MOV #PAD,R4 ; VT100 KEYPAD HELP 10$: CALL CLRSCR ; CLEAR THE SCREEN CALL SETNAR ; RESET VT100 TO NARROW CALL WRITE ; AND DO IT CALL GETCMD ; GET RESPONSE JMP REFRSH ; REFRESH CURRENT PAGE .DSABL LSB ; HA(lf) command. Display half pages. HALF: BIC #B.FULL,STATUS ; SHOW HALF PAGES CALL SKIP ; SKIP PAST COMMAND CALL CONVRT ; CONVERT COUNT (IF ANY) BCC 10$ ; IF CC, GOT NUMBER MOV MAXLIN,R1 ; COPY MAXIMUM # OF LINES SUB #6,R1 ; LEAVE 6 LINES ON SCREEN 10$: MOV R1,SCRCNT ; SAVE THE SCROLL COUNT JMP CHKCMD ; GET NEXT COMMAND ... ; L(eft) command. Move the margin left. LEFT: CALL SKIP ; SKIP PAST COMMAND BCS 20$ ; IF CS, END OF LINE CALL CONVRT ; CONVERT TO DECIMAL BCS 40$ ; IS CS, BAD NUMBER TST R1 ; SPECIFY ZERO ? BNE 30$ ; IF NE, NO 10$: CLR MARGIN ; SET FOR NO MARGIN BR 40$ ; AND CONTINUE ... 20$: MOV #DEFCNT,R1 ; SETUP DEFAULT COUNT 30$: SUB R1,MARGIN ; MOVE MARGIN LEFT BLT 10$ ; IF LT, TOO FAR 40$: CALL PNTDOT ; SET TO REDISPLAY PAGE CALL CHKRUL ; CHECK FOR RULER JMP CLEAR ; GO CLEAR THE PAGE ; N(ext) command. Display the next file. NEXT: CMPB 1(R0),#'A ; NARROW COMMAND ? BEQ NARROW ; IF EQ, YES BIS #B.NEXT,STATUS ; SHOW DO NEXT FILE RETURN ; NA(rrow) command. List file in narrow format. NARROW: TSTB NEGFLG ; NEGATION SPECIFIED ? BEQ NAROW1 ; IF EQ, NO JMP WIDE1 ; -NA MEANS WIDE NAROW1: BIC #WISW,SWMASK ; CLEAR THE WIDE SWITCH BIS #NASW,SWMASK ; SET THE NARROW SWITCH CALL SETUP ; DO SETUP (WRITES FILENAME) CALL CHKRUL ; CHECK THE RULER CALL PNTDOT ; SET TO REDISPLAY PAGE RETURN ; P(age) command. Start displaying at next formfeed. PAGE: CMPB 1(R0),#'R ; IS THIS A PRINT COMMAND ? BEQ PRINT ; IF EQ, YES CALL PNTDOT ; POSITION TO TOP RECORD ; The top record is skipped incase it contains a formfeed. CALL GET ; SKIP OVER THE FIRST RECORD BCS 10$ ; IF CS, HAD A ERROR CALL MARKER ; SEE IF RECORD NEEDS MARKED MOV R0,R2 ; COPY BUFFER ADDRESS MOVB #FF,(R0)+ ; SEARCH FOR FORMFEED CLRB (R0) ; TERMINATOR CALL SEARCH ; GO SEARCH FOR IT BCS 20$ ; IF CS, NOT FOUND BIC #B.SRCH,STATUS ; NO SEARCH STRING ACTIVE CALL CLRPAG ; CLEAR THE ENTIRE PAGE MOV SBEGIN,R1 ; START OF STRING FOUND CMPB (R1),#FF ; WAS IT REALLY A FORMFEED ? BNE 10$ ; IF NE, NO (MUST BE VFU SKIP) ; Now check for a formfeed at the end of the line: ; - by itself will start print at next line. ; text - " " " " ; text - the current line is printed (macro/bliss listings). MOV FDBADR,R0 ; COPY THE FDB ADDRESS MOV F.NRBD+2(R0),R1 ; COPY THE BUFFER ADDRESS ADD F.NRBD(R0),R1 ; POSITION TO END OF RECORD DEC R1 ; POINT TO THE LAST BYTE CMPB (R1),#FF ; IS LAST BYTE A FORMFEED ? BEQ 10$ ; IF EQ, YES (SKIP WRITE) CALL WRTBUF ; WRITE CURRENT RECORD CALL SETINV ; SET PAGE MARK INVALID 10$: RETURN 20$: JMP ATEOF ; WE'RE NOW AT EOF ; PR(int) command. Send current file to the printer. PRINT: MOV FDBADR,R0 ; COPY THE FDB ADDRESS CALL .PRINT ; SEND IT TO THE PRINTER BIS #B.NEXT,STATUS ; SHOW GO TO NEXT FILE RETURN ; R(ight) command. Move the margin right. RIGHT: CMPB 1(R0),#'U ; DISPLAY RULER COMMAND ? BNE 5$ ; IF NE, NO (RIGHT) CALL RULER ; WRITE THE RULER JMP CHKCMD ; READ COMMAND AGAIN 5$: CMPB 1(R0),#'E ; REFRESH COMMAND ? BEQ REFRSH ; IF EQ, YES CALL SKIP ; SKIP PAST COMMAND BCC 10$ ; IF CS, END OF LINE MOV #DEFCNT,R1 ; SETUP DEFAULT COUNT BR 20$ ; AND CONTINUE ... 10$: CALL CONVRT ; CONVERT TO DECIMAL BCS 30$ ; IS CS, BAD NUMBER 20$: BIC #177000,R1 ; NOT TOO BIG NOW ... ADD R1,MARGIN ; INDENT THE MARGIN 30$: CALL PNTDOT ; SET TO REDISPLAY PAGE CALL CHKRUL ; CHECK FOR RULER JMP CLEAR ; GO CLEAR THE PAGE ; RE(fresh) command. Redisplay current page (including filename). REFRSH: CALL WRTHDR ; WRITE THE FILE HEADER CALL CHKRUL ; CHECK FOR A RULER CALL PNTDOT ; SET TO REDISPLAY PAGE RETURN ; RU(ler) command. Display a ruler on top of the screen. RULER: CALL SETTOP ; POSITION TO TOP OF SCREEN TSTB NEGFLG ; NEGATION SPECIFIED ? BEQ 2$ ; IF EQ, NO CLRB RULFLG ; SHOW RULER REMOVED BR 50$ ; AND CONTINUE ... 2$: MOV #TYOBUF,R4 ; TERMINAL OUTPUT BUFFER CMPB (R0),#'R ; WAS THIS A RULER COMMAND ? BEQ 3$ ; IF EQ, YES MOV RULADR,R5 ; USE PREVIOUS RULER BR 5$ ; AND CONTINUE ... 3$: MOVB #1,RULFLG ; SHOW RULER ON SCREEN MOV #RULONE,R5 ; SET DEFAULT RULER CALL SKIP ; SKIP PAST COMMAND CALL CONVRT ; CONVERT NUMBER BCS 5$ ; IS CS, USE DEFAULT TST R1 ; SPECIFY ZERO ? BNE 4$ ; IF NE, NO BISB #377,RULFLG ; SET FLAG NEGATIVE MOV RULADR,R5 ; USE CURRENT RULER BNE 4$ ; IF NE, THERE WAS ONE MOV #RULONE,R5 ; OTHERWISE, USE DEFAULT BR 5$ ; AND CONTINUE ... 4$: CMP R1,#2 ; WANT RULER 2 ? BNE 5$ ; IF NE, NO MOV #RULTWO,R5 ; SET TO RULER 2 5$: MOV R5,RULADR ; SAVE RULER ADDRESS TSTB RULFLG ; DISABLE INDENT ? BMI 20$ ; IF MI, YES MOV MARGIN,R2 ; GET MARGIN COUNT BEQ 20$ ; IF EQ, NONE 10$: TSTB (R5)+ ; ADJUST THE RULER SOB R2,10$ ; LOOP TILL DONE 20$: MOV LINWID,R2 ; SIZE OF RULER 30$: MOVB (R5)+,(R4)+ ; MOVE IN THE RULER BEQ 40$ ; IF EQ, TOO MANY SOB R2,30$ ; LOOP TILL DONE 40$: MOVB #CR,(R4)+ ; GET TO LEFT MARGIN CLRB (R4) ; SHOW END OF MESSAGE CALL ADDREV ; ADD REVERSE VIDEO MOV #TYOBUF,R4 ; SET THE BUFFER ADDR CALL WRITE ; AND GO DO IT CALL REMATR ; REMOVE ATTRIBUTES CMPB #O.TEK,TERM ; IS THIS A TEKTRONIX ? BNE 50$ ; IF NE, NO CALL PNTDOT ; YES, REDISPLAY PAGE TST (SP)+ ; FORCE BACK TO MAINLINE 50$: RETURN ; SEC(tion). Advance or backup a section on the screen. SECTIN: MOV SCRCNT,R1 ; GET COUNT TO SCROLL BIT #B.FORW,STATUS ; ARE WE LISTING FORWARD ? BNE PLUS1 ; IF NE, YES BR MINUS1 ; NO, LISTING BACKWARD ; S(eeall) command. Enable see-all mode. SEEALL: CMPB 2(R0),#'C ; SECTION COMMAND ? BEQ SECTIN ; IF EQ, YES MOV #SESW,R0 ; SWITCH TO SET OR CLEAR CALL SWITCH ; GO DO IT CALL PNTDOT ; SET TO REDISPLAY PAGE JMP CLEAR ; GO CLEAR PAGE ; T(op) command. Postion at top of file. TOP: BIC #B.SRCH,STATUS ; FORCE SEARCH FROM TOP CLR WTGREC ; SET TO GO CLR WTGREC+2 ; TO RECORD 1. BR DOIT ; AND DO IT ; V(fu) command. Toggles the VFU switch. VFU: MOV #VFSW,R0 ; SWITCH TO SET OR CLEAR CALL SWITCH ; GO DO IT CALL PNTDOT ; SET TO REDISPLAY PAGE JMP CLEAR ; GO CLEAR THE PAGE ; W(ide) command. Set terminal to wide mode. WIDE: TSTB NEGFLG ; NEGATION SPECIFIED ? BEQ WIDE1 ; IF EQ, NO JMP NAROW1 ; -WI MEANS NARROW WIDE1: BIC #NASW,SWMASK ; CLEAR NARROW SWITCH BIS #WISW,SWMASK ; SET WIDE SWITCH CALL SETUP ; DO SETUP (WRITES FILENAME) CALL CHKRUL ; CHECK THE RULER CALL PNTDOT ; SET TO REDISPLAY PAGE RETURN ; . (dot) command. Starts listing + or - records from current record. DOT: CMPB 1(R0),#'- ; IS IT MINUS SIGN ? BEQ MINUS ; IF EQ, YES CMPB 1(R0),#'+ ; IS IT A PLUS SIGN ? BEQ PLUS ; IF EQ, YES BIT #B.FORW,STATUS ; ARE WE LISTING FORWARD ? BNE PLUS ; IF NE, YES ; Dot (.) plus negative number. MINUS: CALL SKIP ; SKIP TO NUMBER (OVER -) CALL CONVRT ; CONVERT THE NUMBER BCC MINUS1 ; IF CC, OK MOV #1,R1 ; DEFAULT TO 1 MINUS1: ; R1 = # OF RECORDS TO BACKUP BIC #B.BACK,STATUS ; PRESUME NOT PARTIAL BACKUP CMP R1,MAXLIN ; BACK MORE THAN A PAGE ? BGT 20$ ; IF GT, YES MOV R1,BCKCNT ; SAVE COUNT BACKING UP DEC R1 ; BIASED BY -1 IN POINTR ADD MAXLIN,R1 ; BACKUP -n LINES CMPB #T.V100,TTYPE ; ARE WE ON A VT100 ? BNE 20$ ; IF NE, NO PARTIAL BACKUP BIS #B.BACK,STATUS ; SHOW WE ARE BACKING UP 20$: JMP ADJPAG ; GO ADJUST THE PAGE ; dot (.) plus positive number. PLUS: CALL SKIP ; SKIP TO NUMBER (OVER +) CALL CONVRT ; CONVERT THE NUMBER BCC PLUS1 ; IF CC, OK MOV #1,R1 ; DEFAULT TO 1 PLUS1: ; R1 = # OF RECORDS TO ADVANCE CMP R1,MAXLIN ; FORWARD LESS THAN PAGE ? BGT 30$ ; IF GT, NO CMPB #T.V100,TTYPE ; IS THIS A VT100 ? BNE 20$ ; IF NE, NO MOV MAXLIN,LINCNT ; RESET MAXIMUM LINE COUNT SUB R1,LINCNT ; VT100 WILL SCROLL UP INC R1 ; BIASED BY -1 IN POINTR ADD R1,OLDREC+2 ; ADJUST SAVED RECORD # ADC OLDREC ; AND THE CARRY (IF ANY) BIS #B.PINV,STATUS ; SHOW PAGE MARKER INVALID JMP RET1 ; PROCESS LIKE NEXT PAGE 20$: INC R1 ; BIASED BY -1 IN POINTR SUB MAXLIN,WTGREC+2 ; ADJUST WHERE TO GO SBC WTGREC ; AND THE CARRY 30$: ADD R1,WTGREC+2 ; ADD TO CURRENT RECORD ADC WTGREC ; AND THE CARRY JMP DOIT ; POSITION TO IT ; Numeric input. Position at specified record number. NUMBER: CMPB (R0),#'0 ; POSSIBLE NUMBER ? BLT RET ; IF LT, NO CMPB (R0),#'9 ; REALLY A NUMBER ? BGT RET ; IF GT, NO MOV #WTGREC,R3 ; SETUP OUTPUT ADDRESS MOV TIOSB+2,R4 ; SETUP THE BYTE COUNT MOV #CMD,R5 ; ADDR OF STRING TO CONVERT CALL .DD2CT ; CONVERT IT TO BINARY BCS RET ; IF CS, BAD NUMBER DOIT: ; POINT TO A RECORD NUMBER TST WTGREC ; ARE WE GOING TO THE TOP ? BNE 10$ ; IF NE, NO CMP WTGREC+2,#1 ; GOING TO RECORD 0 OR 1 ? BHI 10$ ; IF HI, NO BIS #B.FORW,STATUS ; YES, SET FORWARD DIRECTION 10$: BIC #B.PINV,STATUS ; FORCE VALID PAGE MARKER CALL POINTR ; AND POINT TO THE RECORD BIT #B.EOF,STATUS ; END OF FILE DETECTED ? BEQ CLEAR ; IF EQ, NO ATEOF: ; PRINT FULL PAGE AT EOF TST CURREC ; LARGER THAN MAX LINES ? BNE 30$ ; IF NE, YES CMP CURREC+2,MAXLIN ; LESS THAN MAX LINES ? BLOS CLEAR ; IF LOS, YES (DON'T POINT) 30$: MOV CURREC,WTGREC ; COPY LAST RECORD # MOV CURREC+2,WTGREC+2 ; AND THE SECOND WORD MOV MAXLIN,R0 ; COPY MAX # OF LINES MOV #2,R2 ; DEFAULT # TO ADJUST MOV FDBADR,R1 ; GET THE FDB ADDRESS BITB #FD.CR!FD.FTN,F.RATT(R1); NORMAL OR FORTRAN CONTROL ? BNE 40$ ; IF NE, YES (USE DEFAULT) CLR R2 ; CLEAR THE HIGH BITS MOV R0,R3 ; COPY MAXIMUM # OF LINES DIV #3,R2 ; GET 1/3 OF SCREEN SIZE 40$: SUB R2,R0 ; DISPLAY ONLY 2/3 OF SCREEN SUB R0,WTGREC+2 ; SET TO DISPLAY FULL PAGE SBC WTGREC ; SUBTRACT CARRY (IF ANY) CALL POINTR ; GO POINT TO IT CLEAR: BIT #B.BACK,STATUS ; ARE WE BACKING UP ? BEQ 10$ ; IF EQ, NO CMPB #T.V100,TTYPE ; IS THIS A VT100 ? BNE 10$ ; IF NE, NO MOV BCKCNT,R2 ; NUMBER OF LINES TO SCROLL BEQ 10$ ; SHOULD NEVER BE ZERO CALL SCRDWN ; SCROLL SCREEN DOWN BR 20$ ; AND CONTINUE ... 10$: CALL CLRPAG ; CLEAR THE CURRENT PAGE 20$: RETURN ; Jump here if no command, or invalid command. RET: BIT #B.EOF,STATUS ; END OF FILE DETECTED ? BNE RET2 ; IF NE, YES MOV SCRCNT,R1 ; COPY THE SCROLL COUNT BNE 10$ ; IF NE, GOT ONE MOV MAXLIN,R1 ; FORCE COUNT TO MAXIMUM 10$: BIT #B.FULL,STATUS ; DISPLAYING FULL PAGES ? BEQ 20$ ; IF EQ, NO (HALF PAGES) BIT #B.FORW,STATUS ; ARE WE LISTING FORWARD ? BNE RET1 ; IF NE, YES (NORMAL MODE) 20$: BIT #B.FORW,STATUS ; ARE WE LISTING FORWARD ? BEQ 30$ ; IF EQ, NO (BACKWARD) JMP PLUS1 ; PROCESS LIKE +n RECORDS 30$: JMP MINUS1 ; PROCESS LIKE -n RECORDS RET1: CALL NXTPAG ; DO NEXT PAGE PROCESSING RET2: RETURN ; Rewrites the ruler if there was one on the screen. CHKRUL:: TSTB RULFLG ; RULER ON THE SCREEN ? BEQ 10$ ; IF EQ, NO CALL RULER ; YES, WRITE NEW ONE 10$: RETURN ; Adjusts page backward. R1 = number of lines to backup. ADJPAG: MOV CURREC,WTGREC ; COPY CURRENT RECORD MOV CURREC+2,WTGREC+2 ; TO WTG RECORD # TST WTGREC ; WILL WE UNDERFLOW ? BNE 15$ ; IF NE, NO CMP R1,WTGREC+2 ; GOING BACK TOO FAR ? BLO 15$ ; IF LOS, NO MOV WTGREC+2,R1 ; TO TOP OF FILE THEN BIC #B.BACK,STATUS ; DISPLAY ENTIRE PAGE 15$: SUB R1,WTGREC+2 ; SUBTRACT FROM CURRENT SBC WTGREC ; AND CARRY 20$: JMP DOIT ; POSITION TO IT ; Save current record number and set page marker invalid. ; This is needed when the marker set by MRKDOT is not going to ; position us to the current top of page. Instead, the record ; number stored in OLDREC will be used to position to top of page. SETINV: MOV CURREC,OLDREC ; COPY THE CURRENT MOV CURREC+2,OLDREC+2 ; RECORD NUMBER BIS #B.PINV,STATUS ; SHOW PAGE MARKER INVALID RETURN .SBTTL SKIP - SKIP PAST COMMAND ;+ ; ; SKIP - Skip past the command and any tabs/spaces. ; ; Inputs: ; R0 = Buffer address (pointing to 1st byte of command). ; ; Outputs: ; R0 = Points to number, next keyword of command ; or end of line (NULL). ; C set if end of line encountered, else clear. ; ;- SKIP:: ; Skip past rest of command (if any). 10$: INC R0 ; POINT TO NEXT BYTE TSTB (R0) ; END OF STRING ? BEQ 90$ ; IF EQ, YES CMPB (R0),#SPACE ; IS THIS A SPACE ? BEQ 30$ ; IF EQ, YES CMPB (R0),#HT ; HORIZONTAL TAB ? BEQ 30$ ; IF EQ, YES CMPB (R0),#'0 ; POSSIBLE NUMBER ? BLT 10$ ; IF LT, NO (SKIP) CMPB (R0),#'9 ; REALLY A NUMBER ? BGT 10$ ; IF GT, NO (SKIP) BR 40$ ; YES, RETURN ; Found space or tab, now skip all of those. 30$: INC R0 ; UPDATE POINTER TSTB (R0) ; END OF LINE ? BEQ 90$ ; IF EQ, YES CMPB (R0),#SPACE ; IS THIS A SPACE ? BEQ 30$ ; IF EQ, YES (SKIP) CMPB (R0),#HT ; HORIZONTAL TAB ? BEQ 30$ ; IF EQ, YES (SKIP) 40$: CLC ; SHOW SUCCESS BR 100$ ; AND RETURN... 90$: SEC ; END OF LINE SEEN 100$: RETURN .SBTTL WRTERR - WRITE AN ERROR MESSAGE TO THE SCREEN ;+ ; ; WRTERR - Write an error message to the screen. ; ; Inputs: ; R4 = Address of error message. ; ;- WRTERR: CALL WRTMSG ; PREPARE TO WRITE MESSAGE CALL WRITE ; WRITE THE ERROR MESSAGE RETURN ; Write end of screen sequence. WRTEOS: CALL POSEOS ; POSITION TO END OF SCREEN CALL CLREOL ; CLEAR TO END OF SCREEN CALL ADDATR ; ADD VT100 ATTRIBUTES RETURN .SBTTL SWITCH - SET OR CLEAR SPECIFIED SWITCH ;+ ; ; SWITCH - Set or clear specified switch in the switch mask. ; ; Inputs: ; R0 = The switch value to check. ; ;- SWITCH: BIS R0,SWMASK ; PRESUME SETTING SWITCH TSTB NEGFLG ; NEGATION SPEICIFIED ? BEQ 10$ ; IF EQ, NO (SWITCH SET) BIC R0,SWMASK ; YES, SO CLEAR SWITCH 10$: RETURN .END