.title SETTERM Set all terminal char's at boottime .sbttl Documentation .ident /V1.01/ ; ; This program sets all terminal characteristics for all terminals ; on a system. Meant to be run at boot time to set all the terminal ; characteristics that SYSGEN was MEANT to set -- as well as some that ; SYSGEN forgot to set. (i.e. the terminal NAME) Since this program ; sets ALL terminal characteristics, it should be run ONLY AT BOOT TIME! ; ; Eric F. Richards ; 4-Aug-86 ; Gould OSD VAXcluster VMS V4.4 ; .sbttl Macros and other constants .library /sys$library:lib/ ; use alternate macro library .enabl suppression ; clean up the listings .dsabl traceback, debug ; hands off w/ debugger $ucbdef ; define UCB status bits $devdef ; define device status bits $dvidef ; define GETDVI codes $iodef ; set QIO functions $syidef ; define $GETSYI codes $ssdef ; define system service codes $dcdef ; define device class info ttype = dt$_vt100 ; terminal type bufsiz = 1020 ; initial main buffer size trmsiz = 16 ; single terminal buffer maxbuf = 65535 ; max char buffer (limited by arch) assume bufsiz le maxbuf ; if not, it'll not work right .sbttl Main Code .page .psect $code, long, exe, nowrt, pic, shr .entry setterm, ^m ; ; With the exception of the terminal name, get the terminal ; characteristics from the SYSGEN parameters associated with ; it. So, we have to get the parameters, then load the terminals ; with those characteristics. The terminal type is set to VT100. ; clrq -(sp) ; make an all purpose I/O stat block movl sp, r10 ; save a pointer to it clrl -(sp) ; make a buffer for TTY_DEFCHAR2 movl sp, r1 ; save a pointer to it clrl -(sp) ; make a buffer for TTY_DEFCHAR movl sp, r0 ; save a pointer to it clrl -(sp) ; make a buffer for dev class, len, typ movl sp, r11 ; save a pointer to it buflen = 12 ; 3 longwords on the stack clrl -(sp) ; make a buffer for the channel movl sp, r6 ; save a pointer to it ; ; Get the terminal characteristics ; clrq -(sp) ; mark end of item list for GETSYI pushl r11 ; address of TTY_BUF pushl #!4 ; TTY_BUF is a word, but convention... clrl -(sp) ; length of TTY_DEFCHAR2 not needed pushl r1 ; write TTY_DEFCHAR2 here pushl #!4 ; request code for info clrl -(sp) ; length of TTY_DEFCHAR not needed pushl r0 ; write TTY_DEFCHAR here pushl #!4; request code for info movl sp, r0 ; save a pointer to the item list $getsyiw_s itmlst=(r0), - ; look up the characteristics iosb=(r10) ; use this status block blbc r0, 3$ ; on error fubar out movzwl (r10), r0 ; get status block error blbs r0, 5$ ; on error get out 3$: brw done ; jump to error handler 5$: movl r6, sp ; unwind the stack ashl #16, (r11), (r11) ; shift terminal size up a word movw #dc$_term!, (r11) ; set device class and type clrq -(sp) ; make room for STS, DEVCHAR movl sp, r3 ; save a pointer to it ; ; Build GETDVI item list. This will make sure that we don't mess ; with a device that we shouldn't touch. ; clrq -(sp) ; mark end of list, length not needed pushl r3 ; address of where to write STS pushl #!4 ; request STS in a longword clrl -(sp) ; length of next not needed pushal 4(r3) ; address of where to write DEVCHAR pushl #!4 ; request device characteristics movl sp, r8 ; save a pointer to this item list clrl -(sp) ; build a zeroed buffer for the context movl sp, r5 ; ...save a pointer to it movzwl #bufsiz, r9 ; set initial buffer size subl #trmsiz, sp ; make room for a single name pushl sp ; build descr for it as well pushl #trmsiz ; size of the buffer movl sp, r7 ; save a ptr to it ; ; We loop back here if our buffer is too small to hold all the terms ; retry: subl3 r9, r7, sp ; make room for all the terms pushl sp ; build descr for it pushl r9 ; size of the buffer movl sp, r4 ; save a ptr to the descr ; ; Call GETDISKS to get the terminals. This is the main loop. ; loop: movl #trmsiz, (r7) ; init terminal name descriptor pushab #dc$_term ; set TERMINAL characteristic pushl r7 ; the terminal length pushl r7 ; the name descr pushl r5 ; the usrbuf context pushl r4 ; the usrbuf descr calls #5, w^getdisks ; get the terminal name cmpw #ss$_normal, r0 ; did we get it? beql 10$ ; if so, continue cmpw #ss$_ivbuflen, r0 ; buffer size problems? bnequ 5$ ; if not, get out ashl #1, r9, r9 ; if so, double buffer size cmpl #maxbuf, r9 ; did we go too far? bgtr retry ; if so, error out 5$: brw done ; otherwise, reconstruct the buffers 10$: ; ; We now have a device name. let's assign a channel and beat some ; characteristics into it. ; $assign_s chan=(r6), - ; get a channel to the devnam=(r7) ; terminal line. blbc r0, error ; on error explain the problem. $getdviw_s itmlst=(r8), - ; get some info about the device iosb = (r10), - ; ...to decide whether or not to touch chan = (r6) ; ...it or not blbc r0, 15$ ; on error get out movzwl (r10), r0 ; get IOSB error status blbc r0, 15$ ; on error here get out, too ; ; Check the terminal characteristics that we have -- find out if ; we should touch this device or not ; bbc #dev$v_avl, 4(r3), 15$ ; don't set if marked unavail bbs #dev$v_mnt, 4(r3), 15$ ; don't set if mounted (RTxx) bbs #ucb$v_template, (r3), 15$ ; don't set if a template dev bbs #ucb$v_deleteucb, (r3), 15$ ; don't set if a temporary dev bbc #ucb$v_online, (r3), 15$ ; don't set if offline $qiow_s func = #io$_setchar, - ; set the terminal characteristics chan = (r6), - ; on the current terminal p1 = (r11), - ; characteristics buffer is here p2 = s^#buflen, - ; length is here iosb = (r10) ; use I/O status block blbc r0, 15$ ; on error report the problem movzwl (r10), r0 ; get I/O completion code 15$: movl r0, r2 ; save status $dassgn_s chan=(r6) ; deassign the channel blbs r2, 20$ ; was there a past error? movl r2, r0 ; retrieve error status 20$: blbc r0, error ; on success, skip error section brw loop ; otherwise, display error text .sbttl Pseudo-error handler .page ; ; This prints out the error message (fatal or otherwise) ; and continues execution. This will print a generic message ; that will have an extra parameter: the device name. ; error: movl sp, r2 ; save stack ptr for unwind pushl r0 ; error message status pushl r7 ; argument to FAO pushl #1 ; number of args pushl #st_cantset ; push generic error message header pushl #4 ; number of longword vectors movl sp, r0 ; save pointer to the vector $putmsg_s msgvec=(r0) ; output the error message movl r2, sp ; unwind the stack brw loop ; loop until done done: cmpw #ss$_nosuchdev, r0 ; is this a normal exit? bneq 30$ ; if not, return with error movzwl #ss$_normal, r0 ; else, set success 30$: ret ; all done, go home! .end setterm ; this is it!