Newsgroups: comp.sources.unix From: mlschroe@immd4.informatik.uni-erlangen.de (Michael Schroeder) Subject: v26i301: screen-3.5 - screen manager with VT100/ANSI terminal emulation, V3.5, Part02/10 Sender: unix-sources-moderator@gw.home.vix.com Approved: vixie@gw.home.vix.com Submitted-By: mlschroe@immd4.informatik.uni-erlangen.de (Michael Schroeder) Posting-Number: Volume 26, Issue 301 Archive-Name: screen-3.5/part02 #! /bin/sh # This is a shell archive. Remove anything before this line, then unpack # it by saving it into a file and typing "sh file". To overwrite existing # files, type "sh file -c". You can also feed this as standard input via # unshar, or by typing "sh 'ChangeLog' <<'END_OF_FILE' X13.05.93 -- 3.3.3 X================= X X* defautonuke, silence commands added. X X* exec command added. X X* hardcopydir, logdir commands added. X X* Made a superb configure script. X X* BROKEN_PIPE, SOCK_NOT_IN_FS added for braindamaged systems. X X* multi display, multi user support. X X* process command. CS, CE switch cursorkeycap in application mode. X X* lockprg pow_detaches on SIGHUP X X* ins_reg copy_reg commands. X X* new iscreenrc syntax. X X* split up screen.c and ansi.c X X21.10.92 -- 3.2.9 X================ X X* ChangeLog: replaces CHANGES and is in GNUish format. X X* Makefile (CFLAGS, M_CFLAGS, LIBS, OPTIONS): moved user config here, X merged all Makefiles, GNUified X X* socket.c (FindSocket): ignoring bad files in $SCREENDIR X X* config/config.linux: ported. X X* utmp.c, exec.c, loadav.c: split apart from screen.c/fileio.c X X15.07.92 -- 3.2.8 X================= X X* ansi.c (WriteString): automatic character set switching for 8bit support X X3.2.3-3.2.7 X=========== X X* concept changes: Display structure, Multi attacher X X... X X3.2.2 X===== X X* screen.c (main): -m option, "_M_ake always new session", ignore $STY X X* screen.c (main): -Ssessionname X* fileio.c (RcLine): ^A:sessionname give your session a nicer name. X X* screen.c (main): supporting detached startup via screen -d -m -Ssockname X X* fileio.c (stripdev): moved, could not compile X X* overlay.h: "stackable overlay concept" X X* search.c: vi-like / and ? search AND emacs-like ^S and ^R incremental search X in scrollback X X* mark.c: I meant BSDI not BSD X X* concept change: struct display and struct newwin introduced. X X* screen.c (main): -v option prints version. X X* screen.c (MakeWindow): ^A:screen /dev/ttya opens a character device X instead of forking ShellProg with a pty pair. X X3.2.0 X===== X XUltrix port X XIrix 3.3 SGI port X Xshadow password suite supported X Xdata loss on stdin overflow fixed X X"refresh off" keyword added. X X3.1.1 X------ X XiScreen is now under the GNU copyleft license. See file COPYING. X Xcommand line option -A. $LINES, $COLUMNS improved. X XC-A : vbellwait X XXENIX support (Ronald Khoo) X XSYSV has uname() instead of gethostname(). X Xhpux has setresuid. X XClearScreen now saves image to scrollback buffer. X Xmips has setenv. X Xnumerous bugfixes. X X3.1 finally released version. X============================= X X3.0.99: last minute changes: X---------------------------- X XMIPS support (J{rvinen Markku) X XSVR4 support (Marc Boucher) X Xsecopen() secfopen() calls replace stat/access/open. XC-a : echo improved. X'register int' X XChanges up to Screen 3.0 Patchlevel 7 X===================================== X XBetter terminfo support: Screen now checks if a termcap/info Xentry which the name "screen.$TERM" does exist. Look in the X"VIRTUAL TERMINAL" section of the manual for more details. X XMany security improvements. X XScrollRegion() bug fixed which caused slow scrolling if AL Xor DL was used. X XPyramid and Ultrix support added. (Tim and Larry) X XENVIRONMENT support. X /local/etc/screenrc checks for $SYSSCREENRC X $HOME/.screenrc checks for $ISCREENRC and $SCREENRC X /local/screens checks for $ISCREENDIR and $SCREENDIR X .screenrc understands ${VAR} and $VAR . X Xscreen 3.0 Patchlevel 6 X======================= X X.screenrc: X screen now only opens the windows you explicitly ask for. if you X specify none, you still get one window, of course. X Xscreen 3.0. Patchlevel 5 X======================== X XAnsi prototyping by Christos. X Xcopy mode: CTRL-U / CTRL-D exchanged. code cleanup. X Xchanges to screen 3.0 patchlevel 4 X================================== X Xmarkkeys "string" X allows to rebind the keys used in copy/history mode. X string is made up of pairs "=" which are separated X by a colon. Oldchar and newchar are either single ascii characters, X or the two character sequence ^x, where x is an ascii character, or X a 3 digit octal value prepended with '\'. the string "\040=.:^M=q" X rebinds '.' to set marks, and the return rey will abort copy mode. X Xset scrollback 100 X resizes the scrollback history buffer to 100 lines. a default of 50 X is installed. X XA Howard Chu like scrollback history is installed. Many vi-like keys X are added to the copy mode. The '?' key reports on cursor position. X Xscreen 3.0 Patchlevel 3 X======================= X XWriteString fixed, it did kill the display variable. X XYet another LP bugfix. X Xnon vt100 semi-graphics character support. X Xwaynes patch fixed X Xscreen 3.0 Patchlevel 2 X======================= X Xwayne patches cursor motion outside scrollregions. X X.screenrc X monitor on|off X Xchanges in Screen 3.0 Patchlevel 1 X================================== X Xscreen -wipe X X^A : set vbell_msg "Wuff Wuff" X XThousand enhancements: help resizible, copy'n'paste in main X socket loop, and no more '\0' hackin'. :WS=\E8;%d;%dt: X Xscreen can now resize windows under sunview. X X^A : set crlf on|off X effects markroutine join. X Xscreen learned about sized windows under X X Xscreen -ls (-d) -q X quiet option. We count the number of detached (attached) sessions and set X a return value of 10+n. The -q option inhibits all startup X warnings/messages. i.e. screen -R -q may return with code 12 or higher X or start a new/old session. X Xpow_detach_msg "text string" X new command, allows messages, terminal reset, etc. on logout caused X by pow_detach. X X^A : learned a new keyword "set": X commands like "login on" , "vbell off", ... affect the default for X windows to be created. But commands like "set login off" affect X the actual setting of this window. and not the default. X such commands may be bound to keys. example: X bind 'O' set login off X is valid in your .screenrc as well as typed at the ':' prompt. X a bonus is ":set all" which is synonym to ":help". X At the Colon prompt also KeyNames can be entered, alothough that makes X not always sense. X X^A x uses a builtin lockprg, if X a) we don't find our lockprg, or X b) user supplies us with the environmet variable LOCKPRG set to "builtin" X the builtin locks until your login password is typed. on systems using X "shadow password files" you are prompted for a password. X Xmarkroutine can append joined. X Xscreen removes the "controlling tty" from utmp while ptys are attached. X Xmarkroutine performs CR+NL when '\n' is pressed X Xscreen may die quietly, when no TERMCAP entry for "screen" is Xfound, and screen is run under X-windows X X_SEQUENT_ marks sequent386_ptx X Xscreen runs now under SunOS4.1.1 (we need setsid()!). X Xbug in SetForeWindow fixed. X Xrare markroutine bug fixed. X Xwe dont open every file the attacher tells us. X Xwe have now our wonderful "Wuff, Wuff" visual_bell X Xwe have now the interprocess-communication-buffer. secure version. X X'^A =' removes the interprocess-communication-buffer. X Xmarkroutine as in 2.1 X Xmarkroutine: 'a' toggles append mode, X '>' like ' ', but immediately WriteFile(DUMP_EXCHANGE) then. X 'A' like ' ', but first switch to append mode. X X.screenrc understands "screen 2:faui09 rlogin faui09 -l jnweiger" X and "password none" X and "vbell [on|off]" X X'^A :' allows .screenrc commands "online". X Xscreen now receives new $TERM from attacher, when it is reattached X XMakeClientSocket() fifo version does now test for access. X X.screenrc learns "hardstatus {on|off}" X Xtermcap's VB is used for vbell if available. X XAttach() code rewritten: X screen now lists socket directory, if it does not find a suitable socket X screen -d [host.tty] detaches a running screen. X Xscreen -[ls|list] X list all sockets that we find in our sockdir X Xwhen the socket has been removed, send a SIGCHLD to the poor SCREEN Xprocess and it will try to recover. then try a 'screen -r' again. Xall the socket stuff lives now in an extra file. X XMajor changes in version 2.4: X============================= X X* Test version that presents the erlangen extensions from 2.0 in a 2.3 X screen. X X* window resize support X X* screen locking C-a x X X* support for SYSV X X* password protection X X* copy & paste across screens X X* remote detach and power detach X XMajor changes in version 2.3: X X* Terminal emulation has been significantly enhanced and bugfixed. X X* We now fully update the last character on the screen for true auto- X margin terminals, though there may be some delay before the character X can be safely added to the screen. If your terminal has character X insert it will be used to shorten the delay. X X* Added the "termcap" .screenrc command to tweak your terminal's termcap X entry AND to customize the termcap generated for the virtual terminals. X See also the -L and -O command-line options, and the SCREENCAP environ- X ment variable. X X* Fixed screen's character handling when detached or suspended to NOT block X the child processes in their windows -- output continues to be processed X in the background. X X* Added a.k.a.s (window-name aliases) that allow you to customize the X window-information line, including being able to change the name on- X the-fly to reflect what's currently running in the window (see the X -k option, shellaka command, and ALSO KNOWN AS discussion in the doc). X X* Added the ability to log the output of a window to a file (see the X "C-a H" (log) command). X X* Flow-control can now be set for each window and switched interactively X (see the "flow" command, -f option, and FLOW CONTROL discussion). X X* Individual windows can be included or excluded from mention in the X /etc/utmp file (see the "login" command and -l option). X X* Added an activity monitor, which allows you to have a window watched for X the start of any output and alert you when it occurs (see the "C-a M" X (monitor) command). X X* Enhanced the information in the window-information line to keep track of X windows that have: logging turned on '(L)'; beeped in the background '!'; X became active while being monitored '@' (see the "C-a w" (windows) command). X X* Added an on-line help display that lists all the commands and their X key bindings (see the "C-a ?" (help) command). X X* Extended handling of the beep message (and also the new activity message) X to allow '~' to specify a literal beep (see the "beep" and "activity" X .screenrc commands). X X* You can now set the default action on receipt of a hangup signal: detach X or terminate (see the "autodetach" .screenrc command). X X* Routing of characters to their virtual terminals has been enhanced to X not drop characters nor (in rare circumstances) hang up screen. X X* The NFS compatibility has been enhanced. X XMajor changes in version 2.0a: X X* Screen allows you to `detach' the "screen" session from the physical X terminal and resume it at a later point in time (possibly on a X different terminal or in a different login session). X X To get an impression of this functionality do the following: X X - call "screen" and create a couple of windows X - type Control-A Control-D (screen terminates; you are back X in the shell) X - call "screen -r" to resume the detached screen X X* Screen supports multiple character sets and the ISO 2022 control X functions to designate and switch between character sets. X This allows you, for instance, to make use of the VT100 graphics X character set or national character sets. END_OF_FILE if test 11159 -ne `wc -c <'ChangeLog'`; then echo shar: \"'ChangeLog'\" unpacked with wrong size! fi # end of 'ChangeLog' fi if test -f 'Makefile.in' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'Makefile.in'\" else echo shar: Extracting \"'Makefile.in'\" \(10044 characters\) sed "s/^X//" >'Makefile.in' <<'END_OF_FILE' X# X# Makefile template for screen X# X# See machine dependant config.h for more configuration options. X# X Xsrcdir = @srcdir@ XVPATH = @srcdir@ X X# Where to install screen. X Xprefix = /usr/local Xexec_prefix = $(prefix) X Xbindir = $(exec_prefix)/bin Xmandir = $(prefix)/man X XVERSION = @VERSION@ X XETCSCREENRC = `sed < config.h -n -e '/^.define ETCSCREENRC/s/^.*"\([^"]*\)"/\1/p'` X XCC = @CC@ XCFLAGS = -O XLDFLAGS = XLIBS = @LIBS@ X XCPP_DEPEND=/lib/cpp -MM X XINSTALL = @INSTALL@ XINSTALL_PROGRAM = @INSTALL_PROGRAM@ XINSTALL_DATA = @INSTALL_DATA@ X XAWK = @AWK@ X X### Chose some debug configuration options: X# -DDEBUG X# Turn on really heavy debug output. This is written to X# /tmp/debug/screen.{front,back} Look at these files and quote X# questionable sections when sending bug-reports to the author. X# -DTMPTEST X# Change the socket directory to a location that does not interfere X# with the (suid-root) installed screen version. Use that in X# combination with -DDEBUG X# -DDUMPSHADOW X# With shadow-pw screen would never dump core. Use this option if you X# still want to have a core. Use only for debugging. X# -DFORKDEBUG X# Swap roles of father and son when forking the SCREEN process. X# Useful only for debugging. XOPTIONS= X#OPTIONS= -DDEBUG -DTMPTEST X X X###### X###### X###### The following lines should be obsolete because of the 'configure' script. X###### X###### X X X### If you choose to compile with the tried and true: X#CC= cc X#CFLAGS= -O X#CFLAGS= -g X### gcc specific CFLAGS: X#CC= gcc X# If your system include files are bad, don't use -Wall X#CFLAGS= -O6 -g #-Wall X#CFLAGS = -g -fstrength-reduce -fcombine-regs -finline-functions #-Wall X X### On some machines special CFLAGS are required: X#M_CFLAGS= X#M_CFLAGS= -Dapollo -A cpu,mathchip -A nansi # Apollo DN3000/4000/4500 X#M_CFLAGS= -DBSDI # bsd386 X#M_CFLAGS= -DISC -D_POSIX_SOURCE # isc X#M_CFLAGS= -systype bsd43 -DMIPS # mips X#M_CFLAGS= -fforce-mem -fforce-addr\ X# -fomit-frame-pointer -finline-functions -bsd # NeXT X#M_CFLAGS= -qlanglvl=ansi # RS6000/AIX X#M_CFLAGS= -qlanglvl=ansi -D_AIX32 # RS6000/AIX 3.2 X#M_CFLAGS= -ansi # sgi/IRIX 3.x ansi X#M_CFLAGS= -xansi # sgi/IRIX 4.x ext ansi X#M_CFLAGS= -YBSD # Ultrix 4.x X#M_CFLAGS= -DSVR4=1 # Bob Kline rvk@blink.att.com 80386 Unix SVR4.0 X#M_CFLAGS= -D_CX_UX # Ken Beal kbeal@amber.ssd.csd.harris.com Harris CX/UX X X### Choose one of the LIBS setting below: X#LIBS= -ltermcap -lc -lsocket -linet -lsec -lseq # Sequent/ptx X#LIBS= -ltermcap # SunOS, Linux, Apollo, X# gould_np1, NeXT, Ultrix X#LIBS= -ltermcap -lelf # SVR4 X#LIBS= -ltermlib -linet -lcposix # isc X#LIBS= -ltermcap -lmld # mips (nlist is in mld) X#LIBS= -ltermlib -lsun -lmld #-lc_s # sgi/IRIX X#LIBS= -lcurses # RS6000/AIX X#LIBS= -lcrypt_d -ltinfo # sco32 X#LIBS= -lcrypt_i -ltinfo # sco32 X#LIBS= -lcrypt -lsec # sco322 (msilano@sra.com) X#LIBS= -ltermcap -lcrypt.o -ldir -lx # SCO XENIX 2.3.4 X#LIBS= -ltermcap -lcrypt -ldir -l2.3 -lx # SCO UNIX XENIX cross dev. X#LIBS= -ltermcap -lelf -lcrypt -lsocket -lnet -lnsl # Bob Kline SVR4 X X###### X###### X###### end of obsolete lines X###### X###### X X XSHELL=/bin/sh X XCFILES= screen.c ansi.c fileio.c mark.c misc.c resize.c socket.c \ X search.c tty.c term.c window.c utmp.c loadav.c putenv.c help.c \ X termcap.c input.c attacher.c pty.c process.c display.c comm.c acl.c XOFILES= screen.o ansi.o fileio.o mark.o misc.o resize.o socket.o \ X search.o tty.o term.o window.o utmp.o loadav.o putenv.o help.o \ X termcap.o input.o attacher.o pty.o process.o display.o comm.o acl.o X Xall: screen X Xscreen: $(OFILES) X $(CC) $(LDFLAGS) -o $@ $(OFILES) $(LIBS) X X.c.o: X $(CC) -c $(CFLAGS) $(M_CFLAGS) $(DEFS) $(OPTIONS) $< X Xinstall_bin: screen X $(INSTALL_PROGRAM) screen $(bindir)/screen-$(VERSION) X -chown root $(bindir)/screen-$(VERSION) X -chmod 4755 $(bindir)/screen-$(VERSION) X -if [ -f $(bindir)/screen ] && [ ! -f $(bindir)/screen.old ]; then mv $(bindir)/screen $(bindir)/screen.old; fi X rm -f $(bindir)/screen X ln -s $(bindir)/screen-$(VERSION) $(bindir)/screen X Xinstall: install_bin X -$(INSTALL_DATA) etcscreenrc $(ETCSCREENRC) X -$(INSTALL_DATA) doc/screen.1 $(mandir)/man1/screen.1 X -tic terminfo/screeninfo.src X# Better do this by hand. E.g. under RCS... X# cat terminfo/screencap >> /etc/termcap X Xuninstall: X rm -f $(bindir)/screen-$(VERSION) X rm -f $(bindir)/screen X mv $(bindir)/screen.old $(bindir)/screen X rm -f $(ETCSCREENRC) X rm -f $(mandir)/man1/screen.1 X Xshadow: X mkdir shadow; X cd shadow; ln -s ../*.[ch] ../*.in ../*.sh ../configure ../doc ../terminfo . X rm -f shadow/term.h shadow/tty.c shadow/comm.h X Xterm.h: term.c term.sh X AWK=$(AWK) ; . ./term.sh X Xtty.c: tty.sh X sh tty.sh tty.c X Xcomm.h: comm.c comm.sh config.h X AWK=$(AWK) ; CC="$(CC)" ; . ./comm.sh X Xdocs: X cd doc; $(MAKE) X Xdvi: X cd doc; $(MAKE) dvi X Xinfo: X cd doc; $(MAKE) info X Xclean celan: X rm -f $(OFILES) tty.c term.h comm.h screen X X# Delete all files from the current directory that are created by X# configuring or building the program. X# building of term.h/comm.h requires awk. Keep it in the distribution X# we keep config.h, as this file knows where 'make dist' finds the ETCSCREENRC. Xdistclean: mostlyclean X rm -f screen-$(VERSION).tar screen-$(VERSION).TZ X rm -f config.status Makefile X X# Delete everything from the current directory that can be X# reconstructed with this Makefile. Xrealclean: distclean X rm -f config.h X Xmostlyclean: X rm -f $(OFILES) screen X XTAGS: $(CFILES) X ctags $(CFILES) *.h X ctags -e $(CFILES) *.h X Xdist: screen-$(VERSION).tar.z X Xscreen-$(VERSION).tar: term.h comm.h tty.c X -rm -rf dist X mkdir dist X mkdir dist/screen-$(VERSION) X ln acl.h ansi.h display.h extern.h mark.h os.h overlay.h \ X patchlevel.h rcs.h screen.h window.h \ X term.sh tty.sh comm.sh newsyntax \ X acl.c ansi.c attacher.c comm.c display.c window.c fileio.c help.c \ X input.c loadav.c mark.c misc.c process.c pty.c putenv.c \ X screen.c search.c socket.c term.c termcap.c utmp.c resize.c \ X ChangeLog COPYING INSTALLATION WHAT-IS-NEW \ X dist/screen-$(VERSION) X ln configure.in configure dist/screen-$(VERSION) X sed -e 's/"\/local/"\/usr\/local/g' < config.h.in > dist/screen-$(VERSION)/config.h.in X sed -e 's/[ ]\/local/ \/usr\/local/g' -e 's/^CFLAGS = -g/CFLAGS = -O/' < Makefile.in > dist/screen-$(VERSION)/Makefile.in X ln term.h dist/screen-$(VERSION)/term.h.dist X ln comm.h dist/screen-$(VERSION)/comm.h.dist X ln tty.c dist/screen-$(VERSION)/tty.c.dist X mkdir dist/screen-$(VERSION)/terminfo X cd terminfo; ln 8bits README checktc.c screen-sco.mail screencap \ X screeninfo.src test.txt tetris.c \ X ../dist/screen-$(VERSION)/terminfo X sed -e 's/^startup/#startup/' -e 's/^autodetach/#autodetach/' < $(ETCSCREENRC) > dist/screen-$(VERSION)/etcscreenrc X cp $(HOME)/.iscreenrc dist/screen-$(VERSION)/.iscreenrc X mkdir dist/screen-$(VERSION)/doc X ln doc/fdpat.ips dist/screen-$(VERSION)/doc/fdpat.ps X cd doc; ln Makefile readme.quick screen.1 screen.texinfo \ X ../dist/screen-$(VERSION)/doc X cd dist; tar chf ../screen-$(VERSION).tar screen-$(VERSION) X rm -rf dist X Xscreen-$(VERSION).tar.z: screen-$(VERSION).tar X gzip -f screen-$(VERSION).tar X X# Perform self-tests (if any). Xcheck: X Xlint: X lint -I. $(CFILES) X Xsaber: X #load $(CFLAGS) screen.c ansi.c $(LIBS) X Xmdepend: $(CFILES) term.h X @rm -f DEPEND ; \ X for i in ${CFILES} ; do \ X echo "$$i" ; \ X echo `echo "$$i" | sed -e 's/.c$$/.o/'`": $$i" `\ X cc -E $$i |\ X grep '^# .*"\./.*\.h"' |\ X sort -t'"' -u +1 -2 |\ X sed -e 's/.*"\.\/\(.*\)".*/\1/'\ X ` >> DEPEND ; \ X done X X Xdepend: $(CFILES) term.h X cp Makefile Makefile~ X sed -e '/\#\#\# Dependencies/q' < Makefile > tmp_make X for i in $(CFILES); do echo $$i; $(CPP_DEPEND) $$i >> tmp_make; done X mv tmp_make Makefile X X X### Dependencies: Xscreen.o: screen.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h patchlevel.h extern.h Xansi.o: ansi.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h extern.h Xfileio.o: fileio.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h extern.h Xmark.o: mark.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h mark.h extern.h Xmisc.o: misc.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h extern.h Xresize.o: resize.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h extern.h Xsocket.o: socket.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h extern.h Xsearch.o: search.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h mark.h extern.h Xtty.o: tty.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h extern.h Xterm.o: term.c rcs.h term.h Xwindow.o: window.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h extern.h Xutmp.o: utmp.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h extern.h Xloadav.o: loadav.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h extern.h Xputenv.o: putenv.c rcs.h config.h Xhelp.o: help.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h extern.h Xtermcap.o: termcap.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h \ X term.h display.h window.h extern.h Xinput.o: input.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h extern.h Xattacher.o: attacher.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h \ X term.h display.h window.h extern.h Xpty.o: pty.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h extern.h Xprocess.o: process.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h \ X term.h display.h window.h extern.h Xdisplay.o: display.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h \ X term.h display.h window.h extern.h Xcomm.o: comm.c rcs.h config.h comm.h Xacl.o: acl.c rcs.h config.h screen.h os.h ansi.h comm.h overlay.h term.h \ X display.h window.h extern.h acl.h END_OF_FILE if test 10044 -ne `wc -c <'Makefile.in'`; then echo shar: \"'Makefile.in'\" unpacked with wrong size! fi # end of 'Makefile.in' fi if test -f 'acl.c' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'acl.c'\" else echo shar: Extracting \"'acl.c'\" \(11329 characters\) sed "s/^X//" >'acl.c' <<'END_OF_FILE' X/* Copyright (c) 1993 X * Juergen Weigert (jnweiger@immd4.informatik.uni-erlangen.de) X * Michael Schroeder (mlschroe@immd4.informatik.uni-erlangen.de) X * Copyright (c) 1987 Oliver Laumann X * X * This program is free software; you can redistribute it and/or modify X * it under the terms of the GNU General Public License as published by X * the Free Software Foundation; either version 2, or (at your option) X * any later version. X * X * This program is distributed in the hope that it will be useful, X * but WITHOUT ANY WARRANTY; without even the implied warranty of X * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the X * GNU General Public License for more details. X * X * You should have received a copy of the GNU General Public License X * along with this program (see the file COPYING); if not, write to the X * Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. X * X **************************************************************** X */ X#include "rcs.h" XRCS_ID("$Id: acl.c,v 1.5 1993/07/16 14:04:12 mlschroe Exp $ FAU") X X#include "config.h" X#include "screen.h" /* includes acl.h */ X#include "extern.h" X X X/************************************************************************ X * user managing code, this does not really belong into the acl stuff * X ************************************************************************/ X Xextern struct comm comms[]; Xextern struct win *windows, *wtab[]; Xextern struct display *display, *displays; Xstatic struct user *userroot; X X#ifdef MULTIUSER X/* record given user ids here */ Xstatic AclBits userbits; X X/* rights a new unknown user will have on windows and cmds */ Xstatic char default_w_bit[ACL_BITS_PER_WIN] = X{ X 1, /* EXEC */ X 1, /* WRITE */ X 1 /* READ */ X}; X Xstatic char default_c_bit[ACL_BITS_PER_CMD] = X{ X 1 /* EXEC */ X}; X X/* rights of all users per newly created window */ Xstatic AclBits default_w_userbits[ACL_BITS_PER_WIN]; X X/* Xstatic AclBits default_c_userbits[ACL_BITS_PER_CMD]; X*/ X Xstatic int maxusercount = 0; X Xstatic int GrowBitfield __P((AclBits *, int, int, int)); X X X Xstatic int XGrowBitfield(bfp, len, delta, defaultbit) XAclBits *bfp; Xint len, delta, defaultbit; X{ X AclBits n, o = *bfp; X int i; X X if (!(n = (AclBits)calloc(1, (unsigned long)(&ACLBYTE((char *)0, len + delta + 1))))) X return -1; X for (i = 0; i < (len + delta); i++) X { X if (((i < len) && (ACLBIT(i) & ACLBYTE(o, i))) || X ((i >= len) && (defaultbit))) X ACLBYTE(n, i) |= ACLBIT(i); X } X if (len) X free(o); X *bfp = n; X return 0; X} X X#endif /* MULTIUSER */ X X/* X * Returns an nonzero Address. Its contents is either a User-ptr, X * or NULL which may be replaced by a User-ptr to create the entry. X */ Xstruct user ** XFindUserPtr(name) Xchar *name; X{ X struct user **u; X X for (u = &userroot; *u; u = &(*u)->u_next) X if (!strcmp((*u)->u_name, name)) X break; X#ifdef MULTIUSER X debug3("FindUserPtr %s %sfound, id %d\n", name, (*u)?"":"not ", X (*u)?(*u)->id:-1); X#else X debug2("FindUserPtr %s %sfound\n", name, (*u)?"":"not "); X#endif X return u; X} X X/* X * Add a new user. His password may be NULL or "" if none. X * He is in no groups and thus has no rights. X */ Xint XUserAdd(name, pass, up) Xchar *name, *pass; Xstruct user **up; X{ X if (!up) X up = FindUserPtr(name); X if (*up) X return 1; /* he is already there */ X *up = (struct user *)calloc(1, sizeof(struct user)); X if (!*up) X return -1; /* he still does not exist */ X strncpy((*up)->u_name, name, 20); X if (pass) X strncpy((*up)->u_password, pass, 20); X X#ifdef MULTIUSER X /* now find an unused index */ X for ((*up)->id = 0; (*up)->id < maxusercount; (*up)->id++) X if (!(ACLBIT((*up)->id) & ACLBYTE(userbits, (*up)->id))) X break; X debug2("UserAdd %s id %d\n", name, (*up)->id); X if ((*up)->id == maxusercount) X { X int i, j; X struct win *w; X X debug2("growing all bitfields %d += %d\n", maxusercount, USER_CHUNK); X /* the bitfields are full, grow a chunk */ X /* first, the used_uid_indicator: */ X if (GrowBitfield(&userbits, maxusercount, USER_CHUNK, 0)) X { X free(*up); *up = NULL; return -1; X } X /* second, default command bits */ X /* (only if we generate commands dynamically) */ X/* X for (j = 0; j < ACL_BITS_PER_CMD; j++) X if (GrowBitfield(&default_c_userbits[j], maxusercount, USER_CHUNK, X default_c_bit[j])) X { X free(*up); *up = NULL; return -1; X } X*/ X /* third, the bits for each commands */ X for (i = 0; i <= RC_LAST; i++) X for (j = 0; j < ACL_BITS_PER_CMD; j++) X if (GrowBitfield(&comms[i].userbits[j], maxusercount, USER_CHUNK, X default_c_bit[j])) X { X free(*up); *up = NULL; return -1; X } X /* fourth, default window and bits */ X for (j = 0; j < ACL_BITS_PER_WIN; j++) X if (GrowBitfield(&default_w_userbits[j], maxusercount, USER_CHUNK, X default_w_bit[j])) X { X free(*up); *up = NULL; return -1; X } X /* fifth, the bits for each window */ X for (w = windows; w; w = w->w_next) X for (j = 0; j < ACL_BITS_PER_WIN; j++) X if (GrowBitfield(&w->w_userbits[j], maxusercount, USER_CHUNK, X default_w_bit[j])) X { X free(*up); *up = NULL; return -1; X } X maxusercount += USER_CHUNK; X } X ACLBYTE(userbits, (*up)->id) |= ACLBIT((*up)->id); X#else /* MULTIUSER */ X debug1("UserAdd %s\n", name); X#endif /* MULTIUSER */ X return 0; X} X X/* change user's password */ Xint XUserSetPass(name, pass, up) Xchar *name, *pass; Xstruct user **up; X{ X if (!up) X up = FindUserPtr(name); X if (!*up) X return UserAdd(name, pass, up); X strncpy((*up)->u_password, pass ? pass : "", 20); X (*up)->u_password[20] = '\0'; X return 0; X} X X/* X * Remove a user from the list. X * Decrease reference count of all his groups X * Free his grouplist. X */ Xint XUserDel(name, up) Xchar *name; Xstruct user **up; X{ X struct user *u; X struct display *old, *next; X X if (!up) X up = FindUserPtr(name); X if (!(u = *up)) X return -1; /* he who does not exist cannot be removed */ X old = display; X for (display = displays; display; display = next) X { X next = display->_d_next; X if (d_user != u) X continue; X if (display == old) X old = 0; X Detach(D_REMOTE); X } X display = old; X *up = u->u_next; X#ifdef MULTIUSER X ACLBYTE(userbits, u->id) &= ~ACLBIT(u->id); X AclSetPerm(u, "-rwx", "#?"); X#endif X debug1("FREEING user structure for %s\n", u->u_name); X free(u); X return 0; X} X X/************************************************************************ X * end of user managing code * X ************************************************************************/ X X X#ifdef MULTIUSER X Xextern char *multi; /* username */ X X/* This gives the users default rights to the new window */ Xint XNewWindowAcl(w) Xstruct win *w; X{ X int i, j; X X debug1("NewWindowAcl default_w_userbits for window %d\n", w->w_number); X for (j = 0; j < ACL_BITS_PER_WIN; j++) X { X /* we start with len 0 for the new bitfield size and add maxusercount */ X if (GrowBitfield(&w->w_userbits[j], 0, maxusercount, 0)) X { X while (--j >= 0) X free(w->w_userbits[j]); X return -1; X } X for (i = 0; i < maxusercount; i++) X if (ACLBIT(i) & ACLBYTE(default_w_userbits[j], i)) X ACLBYTE(w->w_userbits[j], i) |= ACLBIT(i); X } X return 0; X} X X/* if mode starts with '-' we remove the users exec bit for cmd */ Xint XAclSetPermCmd(u, mode, cmd) Xstruct user *u; Xchar *mode; Xstruct comm *cmd; X{ X int neg = 0; X X if (!multi) X return 0; X debug3("AclSetPermCmd %s %s %s\n", u->u_name, mode, cmd->name); X while (*mode) X { X switch (*mode++) X { X case '-': X neg = 1; X continue; X case '+': X neg = 0; X continue; X case 'e': X case 'x': X if (neg) X ACLBYTE(cmd->userbits[ACL_EXEC], u->id) &= ~ACLBIT(u->id); X else X ACLBYTE(cmd->userbits[ACL_EXEC], u->id) |= ACLBIT(u->id); X break; X case 'r': X case 'w': X break; X default: X return -1; X } X } X return 0; X} X X/* mode strings of the form +rwx -w+rx r -wx are parsed and evaluated */ Xint XAclSetPermWin(u, mode, win) Xstruct user *u; Xchar *mode; Xstruct win *win; X{ X int neg = 0; X int bit; X X if (!multi) X return 0; X debug3("AclSetPermWin %s %s %d\n", u->u_name, mode, win->w_number); X while (*mode) X { X switch (*mode++) X { X case '-': X neg = 1; X continue; X case '+': X neg = 0; X continue; X case 'r': X bit = ACL_READ; X break; X case 'w': X bit = ACL_WRITE; X break; X case 'x': X bit = ACL_EXEC; X break; X default: X return -1; X } X if (neg) X ACLBYTE(win->w_userbits[bit], u->id) &= ~ACLBIT(u->id); X else X ACLBYTE(win->w_userbits[bit], u->id) |= ACLBIT(u->id); X } X return 0; X} X X/* string is broken down into comand and window names, mode applies */ Xint XAclSetPerm(u, mode, s) Xstruct user *u; Xchar *mode, *s; X{ X struct win *w; X int i; X char *p; X X while (*s) X { X switch (*s) X { X case '*': /* all windows and all commands */ X return AclSetPerm(u, mode, "#?"); X case '#': /* all windows */ X for (w = windows; w; w = w->w_next) X AclSetPermWin(u, mode, w); X s++; X break; X case '?': /* all windows and all commands */ X for (i = 0; i <= RC_LAST; i++) X AclSetPermCmd(u, mode, &comms[i]); X s++; X break; X default: X for (p = s; *p && *p != ' ' && *p != '\t' && *p != ','; p++) X ; X if (*p) X *p++ = '\0'; X else X *p = '\0'; X if ((i = FindCommnr(s)) != RC_ILLEGAL) X AclSetPermCmd(u, mode, &comms[i]); X else if (((i = WindowByNoN(s)) >= 0) && wtab[i]) X AclSetPermWin(u, mode, wtab[i]); X else X /* checking group name */ X return -1; X s = p; X } X } X return 0; X} X X#if 0 Xvoid XAclWinSwap(a, b) Xint a, b; X{ X int a_bit = 0, b_bit = 0; X AclGroupList **g; X AclBits p; X X debug2("acl lists swapping windows %d and %d\n", a, b); X X for (g = &aclgrouproot; *g; g = &(*g)->next) X { X p = (*g)->group->winbits; X /* see if there was a bit for window a. zap it */ X if (a >= 0) X if ((a_bit = ACLBIT(a) & ACLBYTE(p, a))) X ACLBYTE(p, a) &= ~ACLBIT(a); X /* see if there was a bit for window b. zap it */ X if (b >= 0) X if ((b_bit = ACLBIT(b) & ACLBYTE(p, b))) X ACLBYTE(p, b) &= ~ACLBIT(b); X /* b may cause a set */ X if (b_bit && a >= 0) X ACLBYTE(p, a) |= ACLBIT(a); X /* a may cause b set */ X if (a_bit && b >= 0) X ACLBYTE(p, b) |= ACLBIT(b); X } X} X#else Xvoid XAclWinSwap(a, b) Xint a, b; X{ X debug2("AclWinSwap(%d, %d) DUMMY\n", a, b); X} X#endif X Xint XAclCheckPermWin(u, mode, w) Xstruct user *u; Xint mode; Xstruct win *w; X{ X if (!multi) X return 0; X if (mode < 0 || mode >= ACL_BITS_PER_WIN) X return -1; X debug3("AclCheckPermWin(%s, %d, %d) = ", u->u_name, mode, w->w_number); X debug1("%d\n", !(ACLBYTE(w->w_userbits[mode], u->id) & ACLBIT(u->id))); X return !(ACLBYTE(w->w_userbits[mode], u->id) & ACLBIT(u->id)); X} X Xint XAclCheckPermCmd(u, mode, c) Xstruct user *u; Xint mode; Xstruct comm *c; X{ X if (!multi) X return 0; X if (mode < 0 || mode >= ACL_BITS_PER_CMD) X return -1; X debug3("AclCheckPermCmd(%s %d %s) = ", u->u_name, mode, c->name); X debug1("%d\n", !(ACLBYTE(c->userbits[mode], u->id) & ACLBIT(u->id))); X return !(ACLBYTE(c->userbits[mode], u->id) & ACLBIT(u->id)); X} X X#endif /* MULTIUSER */ END_OF_FILE if test 11329 -ne `wc -c <'acl.c'`; then echo shar: \"'acl.c'\" unpacked with wrong size! fi # end of 'acl.c' fi if test -f 'config.h' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'config.h'\" else echo shar: Extracting \"'config.h'\" \(10841 characters\) sed "s/^X//" >'config.h' <<'END_OF_FILE' X/* config.h. Generated automatically by configure. */ X/* Copyright (c) 1993 X * Juergen Weigert (jnweiger@immd4.informatik.uni-erlangen.de) X * Michael Schroeder (mlschroe@immd4.informatik.uni-erlangen.de) X * Copyright (c) 1987 Oliver Laumann X * X * This program is free software; you can redistribute it and/or modify X * it under the terms of the GNU General Public License as published by X * the Free Software Foundation; either version 2, or (at your option) X * any later version. X * X * This program is distributed in the hope that it will be useful, X * but WITHOUT ANY WARRANTY; without even the implied warranty of X * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the X * GNU General Public License for more details. X * X * You should have received a copy of the GNU General Public License X * along with this program (see the file COPYING); if not, write to the X * Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. X * X **************************************************************** X * $Id: config.h.in,v 1.4 1993/06/28 16:00:32 mlschroe Exp $ FAU X */ X X X X X X/********************************************************************** X * X * User Configuration Section X */ X X X X/* X * Define HOMESOCKDIR if you want screen to put the named sockets in X * the user's home directory. Notice that this can cause you problems X * if some user's HOME directories are NFS-mounted and don't support X * named sockets. In such a case do not define HOMESOCKDIR and screen X * will create the socket directories in SOCKDIR. This should be in a X * common subdirectory, such as /local or /tmp. It makes things a X * little more secure if you choose a directory which is not writable X * by everyone or where the "sticky" bit is on, but this isn't required. X * Screen will name the subdirectories "S-$USER" (e.g /tmp/S-davison). X * Do not define TMPTEST unless it's for debugging purpose. X */ X#undef HOMESOCKDIR X X#ifndef HOMESOCKDIR X# ifndef TMPTEST X# define SOCKDIR "/usr/local/screens" X# else X# define SOCKDIR "/tmp/testscreens" X# endif X#endif X X/* X * Screen sources two startup files. First a global file with a path X * specified here, second your local $HOME/.screenrc X * Don't define this, if you don't want it. X */ X#define ETCSCREENRC "/usr/local/etc/screenrc" X X/* X * define PTYMODE if you do not like the default of 0622, which allows X * public write to your pty. X * define PTYGROUP to some numerical group-id if you do not want the X * tty to be in "your" group. X * Note, screen is unable to change mode or group of the pty if it X * is not installed with sufficient privilege. (e.g. set-uid-root) X */ X#undef PTYMODE X#undef PTYGROUP X X/* X * If screen is NOT installed set-uid root, screen can provide tty X * security by exclusively locking the ptys. While this keeps other X * users from opening your ptys, it also keeps your own subprocesses X * from being able to open /dev/tty. Define LOCKPTY to add this X * exclusive locking. X */ X#undef LOCKPTY X X/* X * If you'd rather see the status line on the first line of your X * terminal rather than the last, define TOPSTAT. X */ X#undef TOPSTAT X X/* X * here come the erlangen extensions to screen: X * define LOCK if you want to use a lock program for a screenlock. X * define PASSWORD for secure reattach of your screen. X * define COPY_PASTE to use the famous hacker's treasure zoo. X * define POW_DETACH to have a detach_and_logout key. X * define REMOTE_DETACH (-d option) to move screen between terminals. X * define AUTO_NUKE to enable Tim MacKenzies clear screen nuking X * define PSEUDOS to allow window input/output filtering X * define MULTI to allow multiple attaches. X * define MULTIUSER to allow other users attach to your session X * (if they are in the acl, of course) X * (jw) X */ X#undef SIMPLESCREEN X#ifndef SIMPLESCREEN X# define LOCK X# define PASSWORD X# define COPY_PASTE X# define REMOTE_DETACH X# define POW_DETACH X# define AUTO_NUKE X# define PSEUDOS X# define MULTI X# define MULTIUSER X#endif /* SIMPLESCREEN */ X X/* X * As error messages are mostly meaningless to the user, we X * try to throw out phrases that are somewhat more familiar X * to ...well, at least familiar to us NetHack players. X */ X#ifndef NONETHACK X# define NETHACK X#endif /* NONETHACK */ X X/* X * If screen is installed with permissions to update /etc/utmp (such X * as if it is installed set-uid root), define UTMPOK. X */ X#define UTMPOK X X/* Set LOGINDEFAULT to one (1) X * if you want entries added to /etc/utmp by default, else set it to X * zero (0). X */ X#define LOGINDEFAULT 1 X X X/* X * If UTMPOK is defined and your system (incorrectly) counts logins by X * counting non-null entries in /etc/utmp (instead of counting non-null X * entries with no hostname that are not on a pseudo tty), define USRLIMIT X * to have screen put an upper-limit on the number of entries to write X * into /etc/utmp. This helps to keep you from exceeding a limited-user X * license. X */ X#undef USRLIMIT X X X X/********************************************************************** X * X * End of User Configuration Section X * X * Rest of this file is modified by 'configure' X * Change at your own risk! X * X */ X X/* X * Some defines to identify special unix variants X */ X#ifndef SVR4 X#undef SVR4 X#endif X#ifndef MIPS X#undef MIPS X#endif X X/* X * Define POSIX if your system supports IEEE Std 1003.1-1988 (POSIX). X */ X#define POSIX 1 X X/* X * Define BSDJOBS if you have BSD-style job control (both process X * groups and a tty that deals correctly with them). X */ X#define BSDJOBS 1 X X/* X * Define TERMIO if you have struct termio instead of struct sgttyb. X * This is usually the case for SVID systems, where BSD uses sgttyb. X * POSIX systems should define this anyway, even though they use X * struct termios. X */ X#define TERMIO 1 X X/* X * Define TERMINFO if your machine emulates the termcap routines X * with the terminfo database. X * Thus the .screenrc file is parsed for X * the command 'terminfo' and not 'termcap'. X */ X#undef TERMINFO X X/* X * If your library does not define ospeed, define this. X */ X#undef NEED_OSPEED X X/* X * Define SYSV if your machine is SYSV complient (Sys V, HPUX, A/UX) X */ X#ifndef SYSV X#undef SYSV X#endif X X/* X * Define SIGVOID if your signal handlers return void. On older X * systems, signal returns int, but on newer ones, it returns void. X */ X#define SIGVOID 1 X X/* X * Define USESIGSET if you have sigset for BSD 4.1 reliable signals. X */ X#undef USESIGSET X X/* X * Define SYSVSIGS if signal handlers must be reinstalled after X * they have been called. X */ X#undef SYSVSIGS X X/* X * Define BSDWAIT if your system defines a 'union wait' in X * X * Only allow BSDWAIT i.e. wait3 on nonposix systems, since X * posix implies wait(3) and waitpid(3). vdlinden@fwi.uva.nl X * X */ X#ifndef POSIX X#define BSDWAIT 1 X#endif X X/* X * On RISCOS we prefer wait2() over wait3(). rouilj@sni-usa.com X */ X#ifdef BSDWAIT X#undef USE_WAIT2 X#endif X X/* X * Define DIRENT if your system has instead of X */ X#define DIRENT 1 X X/* X * If your system has getutent(), pututline(), etc. to write to the X * utmp file, define GETUTENT. X */ X#undef GETUTENT X X/* X * Define UTHOST if the utmp file has a host field. X */ X#define UTHOST 1 X X/* X * If ttyslot() breaks getlogin() by returning indexes to utmp entries X * of type DEAD_PROCESS, then our getlogin() replacement should be X * selected by defining BUGGYGETLOGIN. X */ X#undef BUGGYGETLOGIN X X/* X * If your system does not have the calls setreuid() and setregid(), X * define NOREUID to force screen to use a forked process to safely X * create output files without retaining any special privileges. X * (Output logging will be disabled, however.) X */ X#undef NOREUID X X/* X * If you want the "time" command to display the current load average X * define LOADAV. Maybe you must install screen with the needed X * privileges to read /dev/kmem. X * Note that NLIST_ stuff is only checked, when getloadavg() is not available. X */ X#undef LOADAV X X#define LOADAV_NUM 3 X#define LOADAV_TYPE double X#define LOADAV_SCALE 1 X#undef LOADAV_GETLOADAVG X#undef LOADAV_UNIX X#undef LOADAV_AVENRUN X X#undef NLIST_STRUCT X#undef NLIST_NAME_UNION X X/* X * If your system has the new format /etc/ttys (like 4.3 BSD) and the X * getttyent(3) library functions, define GETTTYENT. X */ X#define GETTTYENT 1 X X/* X * Define USEBCOPY if the bcopy/memcpy from your system's C library X * supports the overlapping of source and destination blocks. When X * undefined, screen uses its own (probably slower) version of bcopy(). X * X * SYSV machines may have a working memcpy() -- Oh, this is X * quite unlikely. Tell me if you see one. (Juergen) X * But then, memmove() should work, if at all available. X */ X#define USEBCOPY 1 X#define USEMEMCPY 1 X#define USEMEMMOVE 1 X X/* X * If your system has vsprintf() and requires the use of the macros in X * "varargs.h" to use functions with variable arguments, X * define USEVARARGS. X */ X#undef USEVARARGS X X/* X * If the select return value doesn't treat a descriptor that is X * usable for reading and writing as two hits, define SELECT_BROKEN. X */ X#undef SELECT_BROKEN X X/* X * Define this if your system supports named pipes. X */ X#undef NAMEDPIPE X X/* X * Define this if your system exits select() immediatly if a pipe is X * opened read-only and no writer has opened it. X */ X#undef BROKEN_PIPE X X/* X * Define this if the unix-domain socket implementation doesn't X * create a socket in the filesystem. X */ X#undef SOCK_NOT_IN_FS X X/* X * If your system has setenv() and unsetenv() define USESETENV X */ X#define USESETENV 1 X X/* X * If your system does not come with a setenv()/putenv()/getenv() X * functions, you may bring in our own code by defining NEEDPUTENV. X */ X#undef NEEDPUTENV X X/* X * If the passwords are stored in a shadow file and you want the X * builtin lock to work properly, define SHADOWPW. X */ X#undef SHADOWPW X X/* X * If you are on a SYS V machine that restricts filename length to 14 X * characters, you may need to enforce that by setting NAME_MAX to 14 X */ X#undef NAME_MAX /* KEEP_UNDEF_HERE override system value */ X#undef NAME_MAX X X/* X * define PTYRANGE0 and or PTYRANGE1 if you want to adapt screen X * to unusual environments. E.g. For SunOs the defaults are "qpr" and X * "0123456789abcdef". For SunOs 4.1.2 X * #define PTYRANGE0 "pqrstuvwxyzPQRST" X * is recommended by Dan Jacobson. X */ X#define PTYRANGE0 "pqv" X#define PTYRANGE1 "0123456789abcdef" X X/* X * some defines to prevent redeclarations/retypedefs X */ X#define CRYPT_DECLARED 1 X#define GETHOSTNAME_DECLARED 1 X#define KILLSTUFF_DECLARED 1 X#define MEMFUNCS_DECLARED 1 X#undef MKNOD_DECLARED X#undef NLIST_DECLARED X#define PUTENV_DECLARED 1 X#define REUID_DECLARED 1 X#define SETPGID_DECLARED 1 X#define VPRNT_DECLARED 1 X#define WAITSTUFF_DECLARED 1 X#define GETDTABLESIZE_DECLARED 1 X#define SELECT_DECLARED 1 X#define INDEX_DECLARED 1 X X#define SIG_T_DEFINED 1 X#define PID_T_DEFINED 1 X#define UID_T_DEFINED 1 END_OF_FILE if test 10841 -ne `wc -c <'config.h'`; then echo shar: \"'config.h'\" unpacked with wrong size! fi # end of 'config.h' fi if test -f 'config.h.in' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'config.h.in'\" else echo shar: Extracting \"'config.h.in'\" \(10663 characters\) sed "s/^X//" >'config.h.in' <<'END_OF_FILE' X/* Copyright (c) 1993 X * Juergen Weigert (jnweiger@immd4.informatik.uni-erlangen.de) X * Michael Schroeder (mlschroe@immd4.informatik.uni-erlangen.de) X * Copyright (c) 1987 Oliver Laumann X * X * This program is free software; you can redistribute it and/or modify X * it under the terms of the GNU General Public License as published by X * the Free Software Foundation; either version 2, or (at your option) X * any later version. X * X * This program is distributed in the hope that it will be useful, X * but WITHOUT ANY WARRANTY; without even the implied warranty of X * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the X * GNU General Public License for more details. X * X * You should have received a copy of the GNU General Public License X * along with this program (see the file COPYING); if not, write to the X * Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. X * X **************************************************************** X * $Id: config.h.in,v 1.4 1993/06/28 16:00:32 mlschroe Exp $ FAU X */ X X X X X X/********************************************************************** X * X * User Configuration Section X */ X X X X/* X * Define HOMESOCKDIR if you want screen to put the named sockets in X * the user's home directory. Notice that this can cause you problems X * if some user's HOME directories are NFS-mounted and don't support X * named sockets. In such a case do not define HOMESOCKDIR and screen X * will create the socket directories in SOCKDIR. This should be in a X * common subdirectory, such as /local or /tmp. It makes things a X * little more secure if you choose a directory which is not writable X * by everyone or where the "sticky" bit is on, but this isn't required. X * Screen will name the subdirectories "S-$USER" (e.g /tmp/S-davison). X * Do not define TMPTEST unless it's for debugging purpose. X */ X#undef HOMESOCKDIR X X#ifndef HOMESOCKDIR X# ifndef TMPTEST X# define SOCKDIR "/usr/local/screens" X# else X# define SOCKDIR "/tmp/testscreens" X# endif X#endif X X/* X * Screen sources two startup files. First a global file with a path X * specified here, second your local $HOME/.screenrc X * Don't define this, if you don't want it. X */ X#define ETCSCREENRC "/usr/local/etc/screenrc" X X/* X * define PTYMODE if you do not like the default of 0622, which allows X * public write to your pty. X * define PTYGROUP to some numerical group-id if you do not want the X * tty to be in "your" group. X * Note, screen is unable to change mode or group of the pty if it X * is not installed with sufficient privilege. (e.g. set-uid-root) X */ X#undef PTYMODE X#undef PTYGROUP X X/* X * If screen is NOT installed set-uid root, screen can provide tty X * security by exclusively locking the ptys. While this keeps other X * users from opening your ptys, it also keeps your own subprocesses X * from being able to open /dev/tty. Define LOCKPTY to add this X * exclusive locking. X */ X#undef LOCKPTY X X/* X * If you'd rather see the status line on the first line of your X * terminal rather than the last, define TOPSTAT. X */ X#undef TOPSTAT X X/* X * here come the erlangen extensions to screen: X * define LOCK if you want to use a lock program for a screenlock. X * define PASSWORD for secure reattach of your screen. X * define COPY_PASTE to use the famous hacker's treasure zoo. X * define POW_DETACH to have a detach_and_logout key. X * define REMOTE_DETACH (-d option) to move screen between terminals. X * define AUTO_NUKE to enable Tim MacKenzies clear screen nuking X * define PSEUDOS to allow window input/output filtering X * define MULTI to allow multiple attaches. X * define MULTIUSER to allow other users attach to your session X * (if they are in the acl, of course) X * (jw) X */ X#undef SIMPLESCREEN X#ifndef SIMPLESCREEN X# define LOCK X# define PASSWORD X# define COPY_PASTE X# define REMOTE_DETACH X# define POW_DETACH X# define AUTO_NUKE X# define PSEUDOS X# define MULTI X# define MULTIUSER X#endif /* SIMPLESCREEN */ X X/* X * As error messages are mostly meaningless to the user, we X * try to throw out phrases that are somewhat more familiar X * to ...well, at least familiar to us NetHack players. X */ X#ifndef NONETHACK X# define NETHACK X#endif /* NONETHACK */ X X/* X * If screen is installed with permissions to update /etc/utmp (such X * as if it is installed set-uid root), define UTMPOK. X */ X#define UTMPOK X X/* Set LOGINDEFAULT to one (1) X * if you want entries added to /etc/utmp by default, else set it to X * zero (0). X */ X#define LOGINDEFAULT 1 X X X/* X * If UTMPOK is defined and your system (incorrectly) counts logins by X * counting non-null entries in /etc/utmp (instead of counting non-null X * entries with no hostname that are not on a pseudo tty), define USRLIMIT X * to have screen put an upper-limit on the number of entries to write X * into /etc/utmp. This helps to keep you from exceeding a limited-user X * license. X */ X#undef USRLIMIT X X X X/********************************************************************** X * X * End of User Configuration Section X * X * Rest of this file is modified by 'configure' X * Change at your own risk! X * X */ X X/* X * Some defines to identify special unix variants X */ X#ifndef SVR4 X#undef SVR4 X#endif X#ifndef MIPS X#undef MIPS X#endif X X/* X * Define POSIX if your system supports IEEE Std 1003.1-1988 (POSIX). X */ X#undef POSIX X X/* X * Define BSDJOBS if you have BSD-style job control (both process X * groups and a tty that deals correctly with them). X */ X#undef BSDJOBS X X/* X * Define TERMIO if you have struct termio instead of struct sgttyb. X * This is usually the case for SVID systems, where BSD uses sgttyb. X * POSIX systems should define this anyway, even though they use X * struct termios. X */ X#undef TERMIO X X/* X * Define TERMINFO if your machine emulates the termcap routines X * with the terminfo database. X * Thus the .screenrc file is parsed for X * the command 'terminfo' and not 'termcap'. X */ X#undef TERMINFO X X/* X * If your library does not define ospeed, define this. X */ X#undef NEED_OSPEED X X/* X * Define SYSV if your machine is SYSV complient (Sys V, HPUX, A/UX) X */ X#ifndef SYSV X#undef SYSV X#endif X X/* X * Define SIGVOID if your signal handlers return void. On older X * systems, signal returns int, but on newer ones, it returns void. X */ X#undef SIGVOID X X/* X * Define USESIGSET if you have sigset for BSD 4.1 reliable signals. X */ X#undef USESIGSET X X/* X * Define SYSVSIGS if signal handlers must be reinstalled after X * they have been called. X */ X#undef SYSVSIGS X X/* X * Define BSDWAIT if your system defines a 'union wait' in X * X * Only allow BSDWAIT i.e. wait3 on nonposix systems, since X * posix implies wait(3) and waitpid(3). vdlinden@fwi.uva.nl X * X */ X#ifndef POSIX X#undef BSDWAIT X#endif X X/* X * On RISCOS we prefer wait2() over wait3(). rouilj@sni-usa.com X */ X#ifdef BSDWAIT X#undef USE_WAIT2 X#endif X X/* X * Define DIRENT if your system has instead of X */ X#undef DIRENT X X/* X * If your system has getutent(), pututline(), etc. to write to the X * utmp file, define GETUTENT. X */ X#undef GETUTENT X X/* X * Define UTHOST if the utmp file has a host field. X */ X#undef UTHOST X X/* X * If ttyslot() breaks getlogin() by returning indexes to utmp entries X * of type DEAD_PROCESS, then our getlogin() replacement should be X * selected by defining BUGGYGETLOGIN. X */ X#undef BUGGYGETLOGIN X X/* X * If your system does not have the calls setreuid() and setregid(), X * define NOREUID to force screen to use a forked process to safely X * create output files without retaining any special privileges. X * (Output logging will be disabled, however.) X */ X#undef NOREUID X X/* X * If you want the "time" command to display the current load average X * define LOADAV. Maybe you must install screen with the needed X * privileges to read /dev/kmem. X * Note that NLIST_ stuff is only checked, when getloadavg() is not available. X */ X#undef LOADAV X X#undef LOADAV_NUM X#undef LOADAV_TYPE X#undef LOADAV_SCALE X#undef LOADAV_GETLOADAVG X#undef LOADAV_UNIX X#undef LOADAV_AVENRUN X X#undef NLIST_STRUCT X#undef NLIST_NAME_UNION X X/* X * If your system has the new format /etc/ttys (like 4.3 BSD) and the X * getttyent(3) library functions, define GETTTYENT. X */ X#undef GETTTYENT X X/* X * Define USEBCOPY if the bcopy/memcpy from your system's C library X * supports the overlapping of source and destination blocks. When X * undefined, screen uses its own (probably slower) version of bcopy(). X * X * SYSV machines may have a working memcpy() -- Oh, this is X * quite unlikely. Tell me if you see one. (Juergen) X * But then, memmove() should work, if at all available. X */ X#undef USEBCOPY X#undef USEMEMCPY X#undef USEMEMMOVE X X/* X * If your system has vsprintf() and requires the use of the macros in X * "varargs.h" to use functions with variable arguments, X * define USEVARARGS. X */ X#undef USEVARARGS X X/* X * If the select return value doesn't treat a descriptor that is X * usable for reading and writing as two hits, define SELECT_BROKEN. X */ X#undef SELECT_BROKEN X X/* X * Define this if your system supports named pipes. X */ X#undef NAMEDPIPE X X/* X * Define this if your system exits select() immediatly if a pipe is X * opened read-only and no writer has opened it. X */ X#undef BROKEN_PIPE X X/* X * Define this if the unix-domain socket implementation doesn't X * create a socket in the filesystem. X */ X#undef SOCK_NOT_IN_FS X X/* X * If your system has setenv() and unsetenv() define USESETENV X */ X#undef USESETENV X X/* X * If your system does not come with a setenv()/putenv()/getenv() X * functions, you may bring in our own code by defining NEEDPUTENV. X */ X#undef NEEDPUTENV X X/* X * If the passwords are stored in a shadow file and you want the X * builtin lock to work properly, define SHADOWPW. X */ X#undef SHADOWPW X X/* X * If you are on a SYS V machine that restricts filename length to 14 X * characters, you may need to enforce that by setting NAME_MAX to 14 X */ X#undef NAME_MAX /* KEEP_UNDEF_HERE override system value */ X#undef NAME_MAX X X/* X * define PTYRANGE0 and or PTYRANGE1 if you want to adapt screen X * to unusual environments. E.g. For SunOs the defaults are "qpr" and X * "0123456789abcdef". For SunOs 4.1.2 X * #define PTYRANGE0 "pqrstuvwxyzPQRST" X * is recommended by Dan Jacobson. X */ X#undef PTYRANGE0 X#undef PTYRANGE1 X X/* X * some defines to prevent redeclarations/retypedefs X */ X#undef CRYPT_DECLARED X#undef GETHOSTNAME_DECLARED X#undef KILLSTUFF_DECLARED X#undef MEMFUNCS_DECLARED X#undef MKNOD_DECLARED X#undef NLIST_DECLARED X#undef PUTENV_DECLARED X#undef REUID_DECLARED X#undef SETPGID_DECLARED X#undef VPRNT_DECLARED X#undef WAITSTUFF_DECLARED X#undef GETDTABLESIZE_DECLARED X#undef SELECT_DECLARED X#undef INDEX_DECLARED X X#undef SIG_T_DEFINED X#undef PID_T_DEFINED X#undef UID_T_DEFINED END_OF_FILE if test 10663 -ne `wc -c <'config.h.in'`; then echo shar: \"'config.h.in'\" unpacked with wrong size! fi # end of 'config.h.in' fi if test -f 'extern.h' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'extern.h'\" else echo shar: Extracting \"'extern.h'\" \(13269 characters\) sed "s/^X//" >'extern.h' <<'END_OF_FILE' X/* Copyright (c) 1993 X * Juergen Weigert (jnweiger@immd4.informatik.uni-erlangen.de) X * Michael Schroeder (mlschroe@immd4.informatik.uni-erlangen.de) X * Copyright (c) 1987 Oliver Laumann X * X * This program is free software; you can redistribute it and/or modify X * it under the terms of the GNU General Public License as published by X * the Free Software Foundation; either version 2, or (at your option) X * any later version. X * X * This program is distributed in the hope that it will be useful, X * but WITHOUT ANY WARRANTY; without even the implied warranty of X * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the X * GNU General Public License for more details. X * X * You should have received a copy of the GNU General Public License X * along with this program (see the file COPYING); if not, write to the X * Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. X * X **************************************************************** X * $Id: extern.h,v 1.1 1993/07/23 14:41:32 vixie Exp vixie $ FAU X */ X X/**************************************************************** X * Thanks to Christos S. Zoulas (christos@ee.cornell.edu) who X * mangled the screen source through 'gcc -Wall'. X **************************************************************** X */ X X#ifndef MEMFUNCS_DECLARED /* bsd386 */ X# ifndef SYSV Xextern void bzero __P((char *, int)); Xextern void bcopy __P((char *, char *, int)); X# else Xextern char *memset __P((char *, int, size_t)); Xextern char *memcpy __P((char *, char *, int)); X# ifdef USEBCOPY Xextern void bcopy __P((char *, char *, int)); X# endif X# endif X#endif /* MEMFUNCS_DECLARED */ X#ifndef WAITSTUFF_DECLARED X# ifdef BSDWAIT Xstruct rusage; Xunion wait; Xextern int wait3 __P((union wait *, int, struct rusage *)); X# else /* BSDWAIT */ Xextern pid_t waitpid __P((int, int *, int)); X# endif /* BSDWAIT */ X#endif /* WAITSTUFF_DECLARED */ X#ifndef GETDTABLESIZE_DECLARED Xextern int getdtablesize __P((void)); X#endif /* GETDTABLESIZE_DECLARED */ X#ifndef REUID_DECLARED X# if !defined(NOREUID) X# ifdef hpux Xextern int setresuid __P((uid_t, uid_t, uid_t)); Xextern int setresgid __P((gid_t, gid_t, gid_t)); X# else Xextern int setreuid __P((uid_t, uid_t)); Xextern int setregid __P((gid_t, gid_t)); X# endif X# endif X#endif /* REUID_DECLARED */ X#ifndef CRYPT_DECLARED Xextern char *crypt __P((char *, char *)); X#endif /* CRYPT_DECLARED */ X#ifdef sun X# ifdef SVR4 /* Solaris 2 */ Xextern pid_t getpgrp __P((int)); X# else Xextern int getpgrp __P((int)); X# endif X#endif X#ifndef MKNOD_DECLARED X# ifdef POSIX Xextern int mknod __P((const char *, mode_t, dev_t)); X# else Xextern int mknod __P((char *, int, int)); X# endif X#endif /* MKNOD_DECLARED */ X#ifndef PUTENV_DECLARED Xextern int putenv __P((char *)); X#endif /* PUTENV_DECLARED */ X#ifndef KILLSTUFF_DECLARED Xextern int kill __P((int, int)); X# ifndef SYSV Xextern int killpg __P((int, int)); X# endif X#endif /* KILLSTUFF_DECLARED */ Xextern int tgetent __P((char *, char *)); Xextern int tgetnum __P((char *)); Xextern int tgetflag __P((char *)); Xextern void tputs __P((char *, int, void (*)(int))); X# ifdef POSIX Xextern pid_t setsid __P((void)); X# ifndef SETPGID_DECLARED Xextern int setpgid __P((int, int)); X# endif /* SETPGID_DECLARED */ X# if defined(BSDI) || defined(__386BSD__) || defined(_CX_UX) || defined(SVR4) Xextern int tcsetpgrp __P((int, pid_t)); X# else Xextern int tcsetpgrp __P((int, int)); X# endif Xextern pid_t getpid __P((void)); X# endif /* POSIX */ X#ifndef __STDC__ Xextern uid_t getuid __P((void)); Xextern uid_t geteuid __P((void)); X#endif Xextern gid_t getgid __P((void)); Xextern gid_t getegid __P((void)); Xextern int isatty __P((int)); X#ifdef notdef Xextern int chown __P((const char *, uid_t, gid_t)); X#endif X#ifndef GETHOSTNAME_DECLARED Xextern int gethostname __P((char *, size_t)); X#endif /* GETHOSTNAME_DECLARED */ X#ifndef __STDC__ Xextern off_t lseek __P((int, off_t, int)); X#endif X#ifndef POSIX X# if defined(sun) && !defined(__GNUC__) /* sun's exit returns ??? */ Xextern int exit __P((int)); X# else Xextern void exit __P((int)); X# endif X#endif /*POSIX*/ Xextern char *getwd __P((char *)); X#ifndef POSIX Xextern char *getenv __P((const char *)); X#endif X#ifndef __STDC__ Xextern time_t time __P((time_t *)); X#endif X X#ifndef _AIX /* should be GETPASS_DEFINED */ X# if defined(linux) || defined(SVR4) || defined(__386BSD__) || defined(BSDI) Xextern char *getpass __P((const char *)); X# else Xextern char *getpass __P((char *)); X# endif X#endif Xextern char *getlogin(), *ttyname(); Xextern int fflush(); X#if !defined(__STDC__) || !defined(POSIX) Xextern char *malloc(), *realloc(); X#endif X X#ifndef INDEX_DECLARED X# if defined(SVR4) && defined(sun) Xextern char *index __P((const char *, int)); Xextern char *rindex __P((const char *, int)); X# else Xextern char *index __P((char *, int)); Xextern char *rindex __P((char *, int)); X# endif X#endif /* INDEX_DECLARED */ X X X/************************************************************ X * Screens function declarations X */ X X/* screen.c */ Xextern void main __P((int, char **)); Xextern sig_t SigHup __P(SIGPROTOARG); Xextern void eexit __P((int)); Xextern void Detach __P((int)); Xextern void Kill __P((int, int)); X#ifdef USEVARARGS Xextern void Msg __P((int, char *, ...)) X# ifdef __GNUC__ X__attribute__ ((format (printf, 2, 3))) X# endif X; Xextern void Panic __P((int, char *, ...)) X# ifdef __GNUC__ X__attribute__ ((format (printf, 2, 3))) X# endif X; X#else Xextern void Msg __P(()); Xextern void Panic __P(()); X#endif Xextern void DisplaySleep __P((int)); Xextern sig_t Finit __P((int)); Xextern void MakeNewEnv __P((void)); X X/* ansi.c */ Xextern void Activate __P((int)); Xextern void ResetWindow __P((struct win *)); Xextern void WriteString __P((struct win *, char *, int)); Xextern void NewAutoFlow __P((struct win *, int)); Xextern void Redisplay __P((int)); Xextern void CheckLP __P((int)); Xextern void MakeBlankLine __P((char *, int)); Xextern void SetCurr __P((struct win *)); Xextern void ChangeAKA __P((struct win *, char *, int)); Xextern void AddLineToHist __P((struct win *, char **, char **, char **)); X X/* fileio.c */ Xextern void StartRc __P((char *)); Xextern void FinishRc __P((char *)); Xextern void RcLine __P((char *)); Xextern FILE *secfopen __P((char *, char *)); Xextern int secopen __P((char *, int, int)); Xextern void WriteFile __P((int)); Xextern void ReadFile __P((void)); Xextern void KillBuffers __P((void)); Xextern char *expand_vars __P((char *)); X X/* tty.c */ Xextern int OpenTTY __P((char *)); Xextern void InitTTY __P((struct mode *, int)); Xextern void GetTTY __P((int, struct mode *)); Xextern void SetTTY __P((int, struct mode *)); Xextern void SetMode __P((struct mode *, struct mode *)); Xextern void SetFlow __P((int)); Xextern void SendBreak __P((struct win *, int, int)); Xextern int TtyGrabConsole __P((int, int, char *)); X#ifdef DEBUG Xextern void DebugTTY __P((struct mode *)); X#endif /* DEBUG */ Xextern int fgtty __P((int)); Xextern void brktty __P((int)); X X/* mark.c */ Xextern int GetHistory __P((void)); Xextern void MarkRoutine __P((void)); Xextern void revto_line __P((int, int, int)); Xextern void revto __P((int, int)); X X/* search.c */ Xextern void Search __P((int)); Xextern void ISearch __P((int)); X X/* input.c */ Xextern void inp_setprompt __P((char *, char *)); Xextern void Input __P((char *, int, void (*)(), int)); X X/* help.c */ Xextern void exit_with_usage __P((char *)); Xextern void display_help __P((void)); Xextern void display_copyright __P((void)); X X/* window.c */ Xextern int MakeWindow __P((struct NewWindow *)); Xextern void FreeWindow __P((struct win *)); X#ifdef PSEUDOS Xextern int winexec __P((char **)); Xextern void FreePseudowin __P((struct win *)); X#endif Xextern void nwin_compose __P((struct NewWindow *, struct NewWindow *, struct NewWindow *)); X X/* utmp.c */ X#ifdef UTMPOK Xextern void InitUtmp __P((void)); Xextern void RemoveLoginSlot __P((void)); Xextern void RestoreLoginSlot __P((void)); Xextern int SetUtmp __P((struct win *)); Xextern int RemoveUtmp __P((struct win *)); X#endif /* UTMPOK */ Xextern void SlotToggle __P((int)); X#ifdef USRLIMIT Xextern int CountUsers __P((void)); X#endif X X/* loadav.c */ X#ifdef LOADAV Xextern void InitLoadav __P((void)); Xextern void AddLoadav __P((char *)); X#endif X X/* pty.c */ Xextern int OpenPTY __P((char **)); X X/* process.c */ Xextern void InitKeytab __P((void)); Xextern void ProcessInput __P((char *, int)); Xextern int FindCommnr __P((char *)); Xextern void DoAction __P((struct action *, int)); Xextern void KillWindow __P((struct win *)); Xextern void SetForeWindow __P((struct win *)); Xextern int Parse __P((char *, char **)); Xextern int ParseEscape __P((char *)); Xextern void DoScreen __P((char *, char **)); Xextern void ShowWindows __P((void)); Xextern int WindowByNoN __P((char *)); X#ifdef COPY_PASTE Xextern int CompileKeys __P((char *, char *)); X#endif X X/* termcap.c */ Xextern int InitTermcap __P((int, int)); Xextern char *MakeTermcap __P((int)); Xextern char *gettermcapstring __P((char *)); X X/* attacher.c */ Xextern int Attach __P((int)); Xextern void Attacher __P((void)); Xextern sig_t AttacherFinit __P(SIGPROTOARG); X X/* display.c */ Xextern struct display *MakeDisplay __P((char *, char *, char *, int, int, struct mode *)); Xextern void FreeDisplay __P((void)); Xextern void DefProcess __P((char **, int *)); Xextern void DefRedisplayLine __P((int, int, int, int)); Xextern void DefClearLine __P((int, int, int)); Xextern int DefRewrite __P((int, int, int, int)); Xextern void DefSetCursor __P((void)); Xextern int DefResize __P((int, int)); Xextern void DefRestore __P((void)); Xextern void PutStr __P((char *)); Xextern void CPutStr __P((char *, int)); Xextern void InitTerm __P((int)); Xextern void FinitTerm __P((void)); Xextern void INSERTCHAR __P((int)); Xextern void PUTCHAR __P((int)); Xextern void PUTCHARLP __P((int)); Xextern void RAW_PUTCHAR __P((int)); Xextern void ClearDisplay __P((void)); Xextern void Clear __P((int, int, int, int)); Xextern void RefreshLine __P((int, int, int, int)); Xextern void DisplayLine __P((char *, char *, char *, char *, char *, char *, int, int, int)); Xextern void FixLP __P((int, int)); Xextern void GotoPos __P((int, int)); Xextern int CalcCost __P((char *)); Xextern void ScrollRegion __P((int, int, int)); Xextern void ChangeScrollRegion __P((int, int)); Xextern void InsertMode __P((int)); Xextern void KeypadMode __P((int)); Xextern void CursorkeysMode __P((int)); Xextern void SetFont __P((int)); Xextern void SetAttr __P((int)); Xextern void SetAttrFont __P((int, int)); Xextern void MakeStatus __P((char *)); Xextern void RemoveStatus __P((void)); Xextern void SetLastPos __P((int, int)); Xextern int ResizeDisplay __P((int, int)); Xextern int InitOverlayPage __P((int, struct LayFuncs *, int)); Xextern void ExitOverlayPage __P((void)); Xextern void AddStr __P((char *)); Xextern void AddStrn __P((char *, int)); Xextern void Flush __P((void)); Xextern void freetty __P((void)); Xextern void Resize_obuf __P((void)); X#ifdef AUTO_NUKE Xextern void NukePending __P((void)); X#endif X X/* resize.c */ Xextern int ChangeScrollback __P((struct win *, int, int)); Xextern int ChangeWindowSize __P((struct win *, int, int)); Xextern void ChangeScreenSize __P((int, int, int)); Xextern void CheckScreenSize __P((int)); Xextern void DoResize __P((int, int)); Xextern char *xrealloc __P((char *, int)); X X/* socket.c */ Xextern int FindSocket __P((int, int *)); Xextern int MakeClientSocket __P((int, char *)); Xextern int MakeServerSocket __P((void)); Xextern int RecoverSocket __P((void)); Xextern int chsock __P((void)); Xextern void ReceiveMsg __P(()); Xextern void SendCreateMsg __P((int, struct NewWindow *)); X#ifdef USEVARARGS Xextern void SendErrorMsg __P((char *, ...)) X# ifdef __GNUC__ X__attribute__ ((format (printf, 1, 2))) X# endif X; X#else Xextern void SendErrorMsg __P(()); X#endif X X/* misc.c */ Xextern char *SaveStr __P((const char *)); Xextern void centerline __P((char *)); Xextern char *Filename __P((char *)); Xextern char *stripdev __P((char *)); X#if !defined(MEMFUNCS_DECLARED) && !defined(bcopy) Xextern void bcopy __P((char *, char *, int)); X#endif /* !MEMFUNCS_DECLARED && !bcopy */ Xextern void bclear __P((char *, int)); Xextern void closeallfiles __P((int)); Xextern int UserContext __P((void)); Xextern void UserReturn __P((int)); Xextern int UserStatus __P((void)); X X/* acl.c */ X#ifdef MULTIUSER Xextern int AclInit __P((char *)); Xextern int AclSetPass __P((char *, char *)); Xextern int AclDelUser __P((char *)); Xextern int AclAddGroup __P((char *)); Xextern int AclSetGroupPerm __P((char *, char *)); Xextern int AclDelGroup __P((char *)); Xextern int AclUserAddGroup __P((char *, char *)); Xextern int AclUserDelGroup __P((char *, char *)); Xextern int AclCheckPermWin __P((struct user *, int, struct win *)); Xextern int AclCheckPermCmd __P((struct user *, int, struct comm *)); Xextern int AclSetPerm __P((struct user *, char *, char *)); Xextern void AclWinSwap __P((int, int)); Xextern int NewWindowAcl __P((struct win *)); X#endif /* MULTIUSER */ Xextern struct user **FindUserPtr __P((char *)); Xextern int UserAdd __P((char *, char *, struct user **)); Xextern int UserDel __P((char *, struct user **)); END_OF_FILE if test 13269 -ne `wc -c <'extern.h'`; then echo shar: \"'extern.h'\" unpacked with wrong size! fi # end of 'extern.h' fi if test -f 'os.h' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'os.h'\" else echo shar: Extracting \"'os.h'\" \(7722 characters\) sed "s/^X//" >'os.h' <<'END_OF_FILE' X/* Copyright (c) 1993 X * Juergen Weigert (jnweiger@immd4.informatik.uni-erlangen.de) X * Michael Schroeder (mlschroe@immd4.informatik.uni-erlangen.de) X * Copyright (c) 1987 Oliver Laumann X * X * This program is free software; you can redistribute it and/or modify X * it under the terms of the GNU General Public License as published by X * the Free Software Foundation; either version 2, or (at your option) X * any later version. X * X * This program is distributed in the hope that it will be useful, X * but WITHOUT ANY WARRANTY; without even the implied warranty of X * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the X * GNU General Public License for more details. X * X * You should have received a copy of the GNU General Public License X * along with this program (see the file COPYING); if not, write to the X * Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. X * X **************************************************************** X * $Id: os.h,v 1.1 1993/07/23 15:59:24 vixie Exp vixie $ FAU X */ X X#include X#include X#include X X#if defined(BSDI) || defined(__386BSD__) || defined(_CX_UX) X# include X#endif /* BSDI || __386BSD__ || _CX_UX */ X X#ifdef ISC X# ifdef ENAMETOOLONG X# undef ENAMETOOLONG X# endif X# ifdef ENOTEMPTY X# undef ENOTEMPTY X# endif X# include X#endif X X#ifdef hpux X# ifndef GETUTENT X# define GETUTENT 1 X# endif X#endif X X#if defined(pyr) || defined(MIPS) || defined(GOULD_NP1) || defined(B43) Xextern int errno; X#endif X#ifndef linux /* all done in */ Xextern int sys_nerr; Xextern char *sys_errlist[]; X#endif /* linux */ X X#ifdef sun X# define getpgrp __getpgrp X# define exit __exit X#endif X X#ifdef POSIX X# include X# if defined(__STDC__) X# include X# endif /* __STDC__ */ X#endif /* POSIX */ X X#ifdef sun X# undef getpgrp X# undef exit X#endif /* sun */ X X#ifdef POSIX X# include X# ifdef hpux X# include X# endif /* hpux */ X#else /* POSIX */ X# ifdef TERMIO X# include X# else /* TERMIO */ X# include X# endif /* TERMIO */ X#endif /* POSIX */ X X#ifndef SYSV X# ifdef NEWSOS X# define strlen ___strlen___ X# include X# undef strlen X# else /* NEWSOS */ X# include X# endif /* NEWSOS */ X#else /* BSD */ X# if defined(SVR4) || defined(NEWSOS) X# define strlen ___strlen___ X# include X# undef strlen X# ifndef NEWSOS X extern size_t strlen(const char *); X# endif /* NEWSOS */ X# else /* SVR4 */ X# include X# endif /* SVR4 */ X#endif /* BSD */ X X#if (defined(TIOCGWINSZ) || defined(TIOCSWINSZ)) && defined(M_UNIX) X# include X# include X#endif X X#ifdef UTMPOK X# ifdef SVR4 X# include X# define UTMPFILE UTMPX_FILE X# define utmp utmpx X# define getutent getutxent X# define getutid getutxid X# define getutline getutxline X# define pututline pututxline X# define setutent setutxent X# define endutent endutxent X# ifdef sun X# define ut_time ut_xtime X# endif X# else /* SVR4 */ X# include X# endif /* SVR4 */ X# if defined(apollo) || defined(linux) X /* X * We don't have GETUTENT, so we dig into utmp ourselves. X * But we save the permanent filedescriptor and X * open utmp just when we need to. X * This code supports an unsorted utmp. jw. X */ X# define UTNOKEEP X# endif /* apollo || linux */ X#endif X X#ifndef UTMPFILE X# ifdef UTMP_FILE X# define UTMPFILE UTMP_FILE X# else X# ifdef _PATH_UTMP X# define UTMPFILE _PATH_UTMP X# else X# define UTMPFILE "/etc/utmp" X# endif /* _PATH_UTMP */ X# endif X#endif X X#ifndef UTMPOK X# ifdef USRLIMIT X# undef USRLIMIT X# endif X#endif X X#ifndef LOGINDEFAULT X# define LOGINDEFAULT 0 X#endif X X#ifndef F_OK X#define F_OK 0 X#endif X#ifndef X_OK X#define X_OK 1 X#endif X#ifndef W_OK X#define W_OK 2 X#endif X#ifndef R_OK X#define R_OK 4 X#endif X X#ifndef S_IFIFO X#define S_IFIFO 0010000 X#endif X#ifndef S_IREAD X#define S_IREAD 0000400 X#endif X#ifndef S_IWRITE X#define S_IWRITE 0000200 X#endif X#ifndef S_IEXEC X#define S_IEXEC 0000100 X#endif X X#if defined(S_IFIFO) && defined(S_IFMT) && !defined(S_ISFIFO) X#define S_ISFIFO(mode) ((mode & S_IFMT) == S_IFIFO) X#endif X#if defined(S_IFSOCK) && defined(S_IFMT) && !defined(S_ISSOCK) X#define S_ISSOCK(mode) ((mode & S_IFMT) == S_IFSOCK) X#endif X X#ifndef TERMCAP_BUFSIZE X# define TERMCAP_BUFSIZE 1024 X#endif X X#ifndef MAXPATHLEN X# define MAXPATHLEN 1024 X#endif X X#ifndef SIG_T_DEFINED X# ifdef SIGVOID X# if defined(ultrix) X# define sig_t void X# else /* nice compilers: */ X typedef void sig_t; X# endif X# else X typedef int sig_t; /* (* sig_t) */ X# endif X#endif /* SIG_T_DEFINED */ X X#if defined(SVR4) || (defined(SYSV) && defined(ISC)) || defined(_AIX) || defined(linux) || defined(ultrix) || defined(__386BSD__) || defined(BSDI) X# define SIGPROTOARG (int) X# define SIGDEFARG int sigsig X# define SIGARG 0 X#else X# define SIGPROTOARG (void) X# define SIGDEFARG X# define SIGARG X#endif X X#ifndef SIGCHLD X#define SIGCHLD SIGCLD X#endif X X#ifdef USESIGSET X# define signal sigset X#endif /* USESIGSET */ X X#ifndef PID_T_DEFINED Xtypedef int pid_t; X#endif X X#ifndef UID_T_DEFINED Xtypedef int gid_t; Xtypedef int uid_t; X#endif X X#ifdef GETUTENT X typedef char *slot_t; X#else X typedef int slot_t; X#endif X X#ifdef SYSV X# define index strchr X# define rindex strrchr X# define bzero(poi,len) memset(poi,0,len) X# define bcmp memcmp X# define killpg(pgrp,sig) kill( -(pgrp), sig) X#endif /* SYSV */ X X#ifndef USEBCOPY X# ifdef USEMEMCPY X# define bcopy(s,d,len) memcpy(d,s,len) X# else X# ifdef USEMEMMOVE X# define bcopy(s,d,len) memmove(d,s,len) X# else X# define NEED_OWN_BCOPY X# endif X# endif X#endif X X#if defined(_POSIX_SOURCE) && defined(ISC) X# ifndef O_NDELAY X# define O_NDELAY O_NONBLOCK X# endif X#endif X X#ifdef hpux X# define setreuid(ruid, euid) setresuid(ruid, euid, -1) X# define setregid(rgid, egid) setresgid(rgid, egid, -1) X#endif X X#if !defined(m68k) && !defined(M_XENIX) X# include X#endif X X#ifndef WTERMSIG X# ifndef BSDWAIT /* if wait is NOT a union: */ X# define WTERMSIG(status) (status & 0177) X# else X# define WTERMSIG(status) status.w_T.w_Termsig X# endif X#endif X X#ifndef WSTOPSIG X# ifndef BSDWAIT /* if wait is NOT a union: */ X# define WSTOPSIG(status) ((status >> 8) & 0377) X# else X# define WSTOPSIG(status) status.w_S.w_Stopsig X# endif X#endif X X/* NET-2 uses WCOREDUMP */ X#if defined(WCOREDUMP) && !defined(WIFCORESIG) X# define WIFCORESIG(status) WCOREDUMP(status) X#endif X X#ifndef WIFCORESIG X# ifndef BSDWAIT /* if wait is NOT a union: */ X# define WIFCORESIG(status) (status & 0200) X# else X# define WIFCORESIG(status) status.w_T.w_Coredump X# endif X#endif X X#ifndef WEXITSTATUS X# ifndef BSDWAIT /* if wait is NOT a union: */ X# define WEXITSTATUS(status) ((status >> 8) & 0377) X# else X# define WEXITSTATUS(status) status.w_T.w_Retcode X# endif X#endif X X#if defined(sgi) X/* on IRIX, regardless of the stream head's read mode (RNORM/RMSGN/RMSGD) X * TIOCPKT mode causes data loss if our buffer is too small (IOSIZE) X * to hold the whole packet at first read(). X * (Marc Boucher) X */ X# undef TIOCPKT X#endif X X#if !defined(VDISABLE) X# ifdef _POSIX_VDISABLE X# define VDISABLE _POSIX_VDISABLE X# else X# define VDISABLE 0377 X# endif /* _POSIX_VDISABLE */ X#endif /* !VDISABLE */ X X#if !defined(FNDELAY) && defined(O_NDELAY) X# define FNDELAY O_NDELAY X#endif X X/*typedef long off_t; */ /* Someone might need this */ X X X/* X * 4 <= IOSIZE <=1000 X * you may try to vary this value. Use low values if your (VMS) system X * tends to choke when pasting. Use high values if you want to test X * how many characters your pty's can buffer. X */ X#define IOSIZE 4096 X X/* used in screen.c and attacher.c */ X#if !defined(NSIG) /* kbeal needs these w/o SYSV */ X# define NSIG 32 X#endif /* !NSIG */ X END_OF_FILE if test 7722 -ne `wc -c <'os.h'`; then echo shar: \"'os.h'\" unpacked with wrong size! fi # end of 'os.h' fi if test -f 'patchlevel.h' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'patchlevel.h'\" else echo shar: Extracting \"'patchlevel.h'\" \(7442 characters\) sed "s/^X//" >'patchlevel.h' <<'END_OF_FILE' X/* Copyright (c) 1993 X * Juergen Weigert (jnweiger@immd4.informatik.uni-erlangen.de) X * Michael Schroeder (mlschroe@immd4.informatik.uni-erlangen.de) X * Copyright (c) 1987 Oliver Laumann X * X * This program is free software; you can redistribute it and/or modify X * it under the terms of the GNU General Public License as published by X * the Free Software Foundation; either version 2, or (at your option) X * any later version. X * X * This program is distributed in the hope that it will be useful, X * but WITHOUT ANY WARRANTY; without even the implied warranty of X * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the X * GNU General Public License for more details. X * X * You should have received a copy of the GNU General Public License X * along with this program (see the file COPYING); if not, write to the X * Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. X * X **************************************************************** X * $Id: patchlevel.h,v 1.4 1993/07/21 15:43:16 mlschroe Exp $ FAU X */ X X/**************************************************************** X * X * patchlevel.h: Our life story. X * X * 08.07.91 -- 3.00.01 -wipe and a 'setenv TERM dumb' bugfix. X * 17.07.91 -- 3.00.02 another patchlevel by Wayne Davison X * 31.07.91 -- 3.00.03 E0, S0, C0 for flexible semi-graphics, nonblocking X * window title input and 'C-a :' command input. X * 10.08.91 -- 3.00.04 scrollback, markkeys and some bugfixes. X * 13.08.91 -- 3.00.05 mark routine improved, ansi prototypes added. X * 20.08.91 -- 3.00.06 screen -h, faster GotoPos in overlay, termcap %. X * instead of %c X * 28.08.91 -- 3.00.07 environment variable support. security. terminfo. X * pyramid and ultrix support. X * 07.09.91 -- 3.00.99 secopen(), MIPS support, SVR4 support. X * 09.09.91 -- 3.01.00 backspace bug fixed. X * 03.10.91 -- 3.01.01 ansi.c: null-ptr fixed, CLS now saves to scrollback. X * Using setresuid on hpux. Memory leak fixed. X * Better GotoPos(). Support for IC. Another resize bug. X * Detach() w/o fore crashed. -T and -A(dapt) option. X * GNU copyleft. X * 19.12.91 -- 3.01.02 flow now really automatic (autoflow killed). X * 7 bit restriction removed from WriteString(). X * 09.01.92 -- 3.01.03 flow reattach bug fixed. VDISCARD bug fixed. X * 13.01.92 -- 3.01.04 new flow concept: ^Af toggles now three states X * 21.01.92 -- 3.01.05 '^A:screen 11' bug fixed. aflag in DoScreen(). X * Some code cleanup. attach_tty and display_tty[] X * added. X * 26.01.92 -- 3.01.06 apollo support, "hardcopy_append on", "bufferfile", X * SECURITY PROBLEM cleared.. X * 28.01.92 -- 3.01.07 screen after su allowed. Pid became part of X * SockName. sysvish 14 character restriction considered. X * 31.01.92 -- 3.02.00 Ultrix port, Irix 3.3 SGI port, shadow pw support, X * data loss on stdin overflow fixed. "refresh off". X * 12.02.92 -- 3.02.02 stripdev() moved, -S introduced, bufferfile improved, X * ShellProg coredump cleared. SVR4 bugfixes. X * I/O code speedup added. X * 24.04.92 -- 3.02.03 perfectly stackable overlays. One scrollback per window, X * not per display. X * 05.05.92 -- 3.02.04 very nasty initialisation bug fixed. X * 09.05.92 -- 3.02.05 parsing for $:cl: termcap strings and \012 octal notation X * in screenrc file. More structuring. Detached startup X * with 'screen -d -m -S...' bugfixed. X * 11.05.92 -- 3.02.06 setreuid() bugs cleared, C-a : setenv added. X * "xn" capability in TERMCAP needed since "am" is there. X * 25.06.92 -- 3.02.07 The multi display test version. Have merci. X * 15.07.92 -- 3.02.08 :B8: supports automatic charset switching for 8-bit X * 26.09.92 -- 3.02.09 Ported to linux. Ignoring bad files in $SCREENDIR X * 22.10.92 -- 3.02.10 screen.c/ansi.c splitted in several pieces. X * Better ISearch. Cleanup of loadav.c X * 29.10.92 -- 3.02.11 Key mechanism rewritten. New command names. X * New iscreenrc syntax. X * 02.11.92 -- 3.02.12 'bind g copy_reg' and 'bind x ins_reg' as suggested by X * stillson@tsfsrv.mitre.org (Ken Stillson). X * 03.11.92 -- 3.02.13 Ported to SunOs 4.1.2. Gulp. Some NULL ptrs fixed and X * misc. braindamage fixed. X * 03.11.92 -- 3.02.14 Argument number checking, AKA fixed. X * 05.11.92 -- 3.02.15 Memory leaks in Detach() and KillWindow() fixed. X * Lockprg powerdetaches on SIGHUP. X * 12.11.92 -- 3.02.16 Introduced two new termcaps: "CS" and "CE". X * (Switch cursorkeys in application mode) X * Tim's async output patch. X * Fixed an ugly bug in WriteString(). X * New command: 'process' X * 16.11.92 -- 3.02.17 Nuking unsent tty output is now optional, (toxic X * ESC radiation). X * 30.11.92 -- 3.02.18 Lots of multi display bugs fixed. New layer X * function 'Restore'. MULTIUSER code cleanup. X * Rudimental acls added for multiuser. X * No more error output, when output gives write errors. X * 02.12.92 -- 3.02.19 BROKEN_PIPE and SOCK_NOT_IN_FS defines added for X * braindead systems. Bug in recover socket code fixed. X * Can create windows again from shell. X * 22.12.92 -- 3.02.20 Made a superb configure script. STY and break fixed. X * 01.02.93 -- 3.02.21 Coredump bug fixed: 8-bit output in background windows. X * Console grabbing somewhat more useable. X * 23.02.93 -- 3.02.22 Added ^:exec command, but not tested at all. X * 23.02.93 -- 3.02.23 Added 'hardcopydir' and 'logdir' commands. X * 11.03.93 -- 3.02.24 Prefixed display and window structure elements. X * Screen now handles autowrapped lines correctly X * in the redisplay and mark function. X * 19.03.93 -- 3.03.00 Patched for BSD386. pseudos work. X * 31.03.93 -- 3.03.01 Don't allocate so much empty attr and font lines. X * 04.04.93 -- 3.03.02 fixed :exec !..| less and :|less, patched BELL_DONE & X * ^B/^F. Fixed auto_nuke attribute resetting. Better linux X * configure. ^AW shows '&' when window has other attacher. X * MAXWIN > 10 patch. KEEP_UNDEF in config.h.in, shellaka X * bug fixed. dec alpha port. Solaris port. X * 02.05.93 -- 3.03.03 Configure tweaked for sgi. Update environment with X * setenv command. Silence on|off, silencewait , X * defautonuke commands added. Manual page updated. X * 13.05.93 -- 3.03.04 exit in newsyntax script, finished _CX_UX port. X * Texinfo page added by Jason Merrill. Much longish debug X * output removed. Select window by title (or number). X * 16.06.93 -- 3.04.00 Replaced ^A- by ^A^H to be complementary to ^A SPACE. X * Moved into CVS. Yacc. X * 28.06.93 -- 3.04.01 Fixed selecting windows with numeric title. Silence X * now works without nethackoption set. X * 01.07.93 -- 3.04.02 Implementing real acls. X * 22.07.93 -- 3.05.00 Fixed SVR4, some multiuser bugs, -- DISTRIBUTED X */ X X#define ORIGIN "FAU" X#define REV 3 X#define VERS 5 X#define PATCHLEVEL 0 X#define DATE "22-Jul-93" X#define STATE "" END_OF_FILE if test 7442 -ne `wc -c <'patchlevel.h'`; then echo shar: \"'patchlevel.h'\" unpacked with wrong size! fi # end of 'patchlevel.h' fi if test -f 'resize.c' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'resize.c'\" else echo shar: Extracting \"'resize.c'\" \(13707 characters\) sed "s/^X//" >'resize.c' <<'END_OF_FILE' X/* Copyright (c) 1993 X * Juergen Weigert (jnweiger@immd4.informatik.uni-erlangen.de) X * Michael Schroeder (mlschroe@immd4.informatik.uni-erlangen.de) X * Copyright (c) 1987 Oliver Laumann X * X * This program is free software; you can redistribute it and/or modify X * it under the terms of the GNU General Public License as published by X * the Free Software Foundation; either version 2, or (at your option) X * any later version. X * X * This program is distributed in the hope that it will be useful, X * but WITHOUT ANY WARRANTY; without even the implied warranty of X * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the X * GNU General Public License for more details. X * X * You should have received a copy of the GNU General Public License X * along with this program (see the file COPYING); if not, write to the X * Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. X * X **************************************************************** X */ X X#include "rcs.h" XRCS_ID("$Id: resize.c,v 1.2 1993/06/23 22:49:14 mlschroe Exp $ FAU") X X#include X#include X#include X#ifndef sun X#include X#endif X X#ifdef ISC X# include X# include X# include X#endif X X#include "config.h" X#include "screen.h" X#include "extern.h" X Xstatic void CheckMaxSize __P((int)); Xstatic int ResizeScreenArray __P((struct win *, char ***, int, int, int)); Xstatic void FreeArray __P((char ***, int)); X#ifdef COPY_PASTE Xstatic int ResizeHistArray __P((struct win *, char ***, int, int, int)); Xstatic void FreeScrollback __P((struct win *)); X#endif X Xextern int maxwidth; Xextern struct display *display, *displays; Xextern char *blank, *null, *OldImage, *OldAttr; Xextern char *OldFont; Xextern struct win *windows; Xextern int Z0width, Z1width; X X#ifdef NETHACK Xextern int nethackflag; X#endif X X#if defined(TIOCGWINSZ) || defined(TIOCSWINSZ) X struct winsize glwz; X#endif X X/* X * ChangeFlag: 0: try to modify no window X * 1: modify fore (and try to modify no d_other) + redisplay X * 2: modify all windows X * X * Note: Activate() is only called if change_flag == 1 X * i.e. on a WINCH event X */ X Xvoid XCheckScreenSize(change_flag) Xint change_flag; X{ X int wi, he; X struct win *p; X struct layer *oldlay; X X if (display == 0) X { X debug("CheckScreenSize: No display -> no check.\n"); X return; X } X oldlay = d_lay; X#ifdef TIOCGWINSZ X if (ioctl(d_userfd, TIOCGWINSZ, &glwz) != 0) X { X debug2("CheckScreenSize: ioctl(%d, TIOCGWINSZ) errno %d\n", d_userfd, errno); X wi = CO; X he = LI; X } X else X { X wi = glwz.ws_col; X he = glwz.ws_row; X if (wi == 0) X wi = CO; X if (he == 0) X he = LI; X } X#else X wi = CO; X he = LI; X#endif X X debug2("CheckScreenSize: screen is (%d,%d)\n", wi, he); X X if (change_flag == 2) X { X debug("Trying to adapt all windows (-A)\n"); X for (p = windows; p; p = p->w_next) X if (p->w_display == 0 || p->w_display == display) X ChangeWindowSize(p, wi, he); X } X if (d_width == wi && d_height == he) X { X debug("CheckScreenSize: No change -> return.\n"); X return; X } X ChangeScreenSize(wi, he, change_flag); X if (change_flag == 1) X Activate(d_fore ? d_fore->w_norefresh : 0); X if (d_lay != oldlay) X { X#ifdef NETHACK X if (nethackflag) X Msg(0, "KAABLAMM!!! You triggered a land mine!"); X else X#endif X Msg(0, "Aborted because of window size change."); X } X} X Xvoid XChangeScreenSize(wi, he, change_fore) Xint wi, he; Xint change_fore; X{ X struct win *p; X int wwi; X X if (d_width == wi && d_height == he) X { X debug("ChangeScreenSize: no change\n"); X return; X } X debug2("ChangeScreenSize from (%d,%d) ", d_width, d_height); X debug3("to (%d,%d) (change_fore: %d)\n",wi, he, change_fore); X d_width = wi; X d_height = he; X X CheckMaxSize(wi); X if (CWS) X { X d_defwidth = CO; X d_defheight = LI; X } X else X { X if (CZ0 && (wi == Z0width || wi == Z1width) && X (CO == Z0width || CO == Z1width)) X d_defwidth = CO; X else X d_defwidth = wi; X d_defheight = he; X } X debug2("Default size: (%d,%d)\n", d_defwidth, d_defheight); X if (change_fore) X DoResize(wi, he); X if (CWS == NULL && displays->_d_next == 0) X { X /* adapt all windows - to be removed ? */ X for (p = windows; p; p = p->w_next) X { X debug1("Trying to change window %d.\n", p->w_number); X wwi = wi; X if (CZ0 && (wi == Z0width || wi == Z1width)) X { X if (p->w_width > (Z0width + Z1width) / 2) X wwi = Z0width; X else X wwi = Z1width; X } X ChangeWindowSize(p, wwi, he); X } X } X} X Xvoid XDoResize(wi, he) Xint wi, he; X{ X struct layer *oldlay; X int q = 0; X X for(;;) X { X oldlay = d_lay; X for (; d_lay; d_lay = d_lay->l_next) X { X d_layfn = d_lay->l_layfn; X if ((q = Resize(wi, he))) X break; X } X d_lay = oldlay; X d_layfn = d_lay->l_layfn; X if (q == 0) X break; X ExitOverlayPage(); X } X} X X#ifdef COPY_PASTE X Xint XChangeScrollback(p, histheight, histwidth) Xstruct win *p; Xint histheight, histwidth; X{ X if (histheight > MAXHISTHEIGHT) X histheight = MAXHISTHEIGHT; X debug2("ChangeScrollback(..., %d, %d)\n", histheight, histwidth); X debug2(" was %d, %d\n", p->w_histheight, p->w_width); X X if (histheight == 0) X { X FreeScrollback(p); X return 0; X } X X if (ResizeHistArray(p, &p->w_ihist, histwidth, histheight, 1) X || ResizeHistArray(p, &p->w_ahist, histwidth, histheight, 0) X || ResizeHistArray(p, &p->w_fhist, histwidth, histheight, 0)) X { X debug(" failed, removing all histbuf\n"); X FreeScrollback(p); X Msg(0, strnomem); X return -1; X } X if (p->w_histheight != histheight) X p->w_histidx = 0; X p->w_histheight = histheight; X X return 0; X} X Xstatic void XFreeScrollback(p) Xstruct win *p; X{ X FreeArray(&p->w_ihist, p->w_histheight); X FreeArray(&p->w_ahist, p->w_histheight); X FreeArray(&p->w_fhist, p->w_histheight); X p->w_histheight = 0; X} X Xstatic int XResizeHistArray(p, arr, wi, hi, fillblank) Xstruct win *p; Xchar ***arr; Xint wi, hi, fillblank; X{ X char **narr, **np, **onp, **onpe; X int t, x, first; X X if (p->w_width == wi && p->w_histheight == hi) X return(0); X if (p->w_histheight != hi) X { X if ((narr = (char **)calloc(sizeof(char *), hi)) == NULL) X { X FreeArray(arr, p->w_histheight); X return(-1); X } X np = narr; X onp = (*arr) + p->w_histidx; X onpe = (*arr) + p->w_histheight; X first = p->w_histheight - hi; X if (first < 0) X np -= first; X for(t = 0; t < p->w_histheight; t++) X { X ASSERT(*onp); X if (t - first >= 0 && t - first < hi) X *np++ = *onp; X else if (*onp != null) X free(*onp); X if (++onp == onpe) X onp = *arr; X } X if (*arr) X free(*arr); X } X else X narr = *arr; X X for (t=0, np=narr; t < hi; t++, np++) X { X if ((!fillblank && *np == 0) || *np == null) X { X *np = null; X continue; X } X x = p->w_width; X if (*np == 0) X { X *np = (char *)malloc(wi + 1); X x = 0; X } X else if (p->w_width != wi) X { X *np = (char *)xrealloc(*np, wi + 1); X } X if (*np == 0) X { X FreeArray(&narr, hi); X return -1; X } X if (x > wi) X x = wi; X if (fillblank) X bclear(*np + x, wi + 1 - x); X else X bzero(*np + x, wi + 1 - x); X } X *arr = narr; X return 0; X} X#endif /* COPY_PASTE */ X X Xstatic int XResizeScreenArray(p, arr, wi, hi, fillblank) Xstruct win *p; Xchar ***arr; Xint wi, hi, fillblank; X{ X int minr; X char **cp; X X if (p->w_width == wi && p->w_height == hi) X return(0); X X if (hi > p->w_height) X minr = p->w_height; X else X minr = hi; X X if (p->w_height > hi) X { X for (cp = *arr; cp < *arr + (p->w_height - hi); cp++) X if (*cp != null) X free(*cp); X bcopy((char *)(*arr + (p->w_height - hi)), (char *)(*arr), X hi * sizeof(char *)); X } X if (*arr && p->w_width != wi) X for (cp = *arr; cp < *arr + minr; cp++) X { X int x = p->w_width; X X if (*cp == null) X continue; X if ((*cp = (char *)xrealloc(*cp, (unsigned) wi + 1)) == 0) X { X FreeArray(arr, p->w_height); X return(-1); X } X if (x > wi) X x = wi; X if (fillblank) X bclear(*cp + x, wi + 1 - x); X else X bzero(*cp + x, wi + 1 - x); X } X if (*arr) X *arr = (char **) xrealloc((char *) *arr, (unsigned) hi * sizeof(char *)); X else X *arr = (char **) malloc((unsigned) hi * sizeof(char *)); X if (*arr == NULL) X return -1; X for (cp = *arr + p->w_height; cp < *arr + hi; cp++) X { X if (!fillblank) X { X *cp = null; X continue; X } X if ((*cp = malloc((unsigned) wi + 1)) == 0) X { X while (--cp >= *arr) X free(*cp); X free(*arr); X *arr = NULL; X return -1; X } X bclear(*cp, wi + 1); X } X return 0; X} X Xstatic void XFreeArray(arr, hi) Xchar ***arr; Xint hi; X{ X register char **p; X register int t; X X if (*arr == 0) X return; X for (t = hi, p = *arr; t--; p++) X if (*p && *p != null) X free(*p); X free(*arr); X *arr = 0; X} X X Xstatic void XCheckMaxSize(wi) Xint wi; X{ X char *oldnull = null; X struct win *p; X int i; X X wi = ((wi + 1) + 255) & ~255; X if (wi <= maxwidth) X return; X maxwidth = wi; X debug1("New maxwidth: %d\n", maxwidth); X if (blank == 0) X blank = malloc((unsigned) maxwidth); X else X blank = xrealloc(blank, (unsigned) maxwidth); X if (null == 0) X null = malloc((unsigned) maxwidth); X else X null = xrealloc(null, (unsigned) maxwidth); X if (OldImage == 0) X OldImage = malloc((unsigned) maxwidth); X else X OldImage = xrealloc(OldImage, (unsigned) maxwidth); X if (OldAttr == 0) X OldAttr = malloc((unsigned) maxwidth); X else X OldAttr = xrealloc(OldAttr, (unsigned) maxwidth); X if (OldFont == 0) X OldFont = malloc((unsigned) maxwidth); X else X OldFont = xrealloc(OldFont, (unsigned) maxwidth); X if (!(blank && null && OldImage && OldAttr && OldFont)) X { X Panic(0, "Out of memory -> Game over!!"); X /*NOTREACHED*/ X } X MakeBlankLine(blank, maxwidth); X bzero(null, maxwidth); X X /* We have to run through all windows to substitute X * the null references. X */ X for (p = windows; p; p = p->w_next) X { X for (i = 0; i < p->w_height; i++) X { X if (p->w_attr[i] == oldnull) X p->w_attr[i] = null; X if (p->w_font[i] == oldnull) X p->w_font[i] = null; X } X#ifdef COPY_PASTE X for (i = 0; i < p->w_histheight; i++) X { X if (p->w_ahist[i] == oldnull) X p->w_ahist[i] = null; X if (p->w_fhist[i] == oldnull) X p->w_fhist[i] = null; X } X#endif X } X} X X Xint XChangeWindowSize(p, wi, he) Xstruct win *p; Xint wi, he; X{ X int t, scr; X X CheckMaxSize(wi); X X if (wi == p->w_width && he == p->w_height) X { X debug("ChangeWindowSize: No change.\n"); X return 0; X } X X debug2("ChangeWindowSize from (%d,%d) to ", p->w_width, p->w_height); X debug2("(%d,%d)\n", wi, he); X if (p->w_lay != &p->w_winlay) X { X debug("ChangeWindowSize: No resize because of overlay.\n"); X return -1; X } X if (wi == 0 && he == 0) X { X FreeArray(&p->w_image, p->w_height); X FreeArray(&p->w_attr, p->w_height); X FreeArray(&p->w_font, p->w_height); X if (p->w_tabs) X free(p->w_tabs); X p->w_tabs = NULL; X p->w_width = 0; X p->w_height = 0; X#ifdef COPY_PASTE X FreeScrollback(p); X#endif X return 0; X } X X /* when window gets smaller, scr is the no. of lines we scroll up */ X scr = p->w_height - he; X if (scr < 0) X scr = 0; X#ifdef COPY_PASTE X for (t = 0; t < scr; t++) X AddLineToHist(p, p->w_image+t, p->w_attr+t, p->w_font+t); X#endif X if (ResizeScreenArray(p, &p->w_image, wi, he, 1) X || ResizeScreenArray(p, &p->w_attr, wi, he, 0) X || ResizeScreenArray(p, &p->w_font, wi, he, 0)) X { Xnomem: KillWindow(p); X Msg(0, "Out of memory -> Window destroyed !!"); X return -1; X } X /* this won't change the d_height of the scrollback history buffer, but X * it will check the d_width of the lines. X */ X#ifdef COPY_PASTE X ChangeScrollback(p, p->w_histheight, wi); X#endif X X if (p->w_tabs == 0) X { X /* tabs get d_width+1 because 0 <= x <= wi */ X if ((p->w_tabs = malloc((unsigned) wi + 1)) == 0) X goto nomem; X t = 8; X } X else X { X if ((p->w_tabs = xrealloc(p->w_tabs, (unsigned) wi + 1)) == 0) X goto nomem; X t = p->w_width; X } X for (t = (t + 7) & 8; t < wi; t += 8) X p->w_tabs[t] = 1; X p->w_height = he; X p->w_width = wi; X if (p->w_x >= wi) X p->w_x = wi - 1; X if ((p->w_y -= scr) < 0) X p->w_y = 0; X if (p->w_Saved_x >= wi) X p->w_Saved_x = wi - 1; X if ((p->w_Saved_y -= scr) < 0) X p->w_Saved_y = 0; X if (p->w_autoaka > 0) X if ((p->w_autoaka -= scr) < 1) X p->w_autoaka = 1; X p->w_top = 0; X p->w_bot = he - 1; X#ifdef TIOCSWINSZ X if (p->w_ptyfd && p->w_pid) X { X glwz.ws_col = wi; X glwz.ws_row = he; X debug("Setting pty winsize.\n"); X if (ioctl(p->w_ptyfd, TIOCSWINSZ, &glwz)) X debug2("SetPtySize: errno %d (fd:%d)\n", errno, p->w_ptyfd); X# if defined(STUPIDTIOCSWINSZ) && defined(SIGWINCH) X# ifdef POSIX X pgrp = tcgetpgrp(p->w_ptyfd); X# else /* POSIX */ X if (ioctl(p->w_ptyfd, TIOCGPGRP, &pgrp)) X pgrp = 0; X# endif /* POSIX */ X if (pgrp) X { X debug1("Sending SIGWINCH to pgrp %d.\n", pgrp); X if (killpg(pgrp, SIGWINCH)) X debug1("killpg: errno %d\n", errno); X } X else X debug1("Could not get pgrp: errno %d\n", errno); X# endif /* STUPIDTIOCSWINSZ */ X } X#endif /* TIOCSWINSZ */ X return 0; X} X X Xchar * Xxrealloc(mem, len) Xchar *mem; Xint len; X{ X register char *nmem; X X if ((nmem = realloc(mem, len))) X return(nmem); X free(mem); X return((char *)0); X} END_OF_FILE if test 13707 -ne `wc -c <'resize.c'`; then echo shar: \"'resize.c'\" unpacked with wrong size! fi # end of 'resize.c' fi if test -f 'search.c' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'search.c'\" else echo shar: Extracting \"'search.c'\" \(7998 characters\) sed "s/^X//" >'search.c' <<'END_OF_FILE' X/* Copyright (c) 1993 X * Juergen Weigert (jnweiger@immd4.informatik.uni-erlangen.de) X * Michael Schroeder (mlschroe@immd4.informatik.uni-erlangen.de) X * Copyright (c) 1987 Oliver Laumann X * X * This program is free software; you can redistribute it and/or modify X * it under the terms of the GNU General Public License as published by X * the Free Software Foundation; either version 2, or (at your option) X * any later version. X * X * This program is distributed in the hope that it will be useful, X * but WITHOUT ANY WARRANTY; without even the implied warranty of X * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the X * GNU General Public License for more details. X * X * You should have received a copy of the GNU General Public License X * along with this program (see the file COPYING); if not, write to the X * Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. X * X **************************************************************** X */ X X#include "rcs.h" XRCS_ID("$Id: search.c,v 1.1.1.1 1993/06/16 23:51:17 jnweiger Exp $ FAU") X X#include X X#include "config.h" X#include "screen.h" X#include "mark.h" X#include "extern.h" X X#ifdef COPY_PASTE X Xextern struct win *fore; Xextern struct display *display; X X/******************************************************************** X * VI style Search X */ X Xstatic int matchword __P((char *, int, int, int)); Xstatic void searchend __P((char *, int)); Xstatic void backsearchend __P((char *, int)); X Xvoid XSearch(dir) Xint dir; X{ X struct markdata *markdata; X if (dir == 0) X { X markdata = (struct markdata *)d_lay->l_data; X if (markdata->isdir > 0) X searchend(0, 0); X else if (markdata->isdir < 0) X backsearchend(0, 0); X else X Msg(0, "No previous pattern"); X } X else X Input((dir > 0 ? "/" : "?"), sizeof(markdata->isstr)-1, (dir > 0 ? searchend : backsearchend), INP_COOKED); X} X Xstatic void Xsearchend(buf, len) Xchar *buf; Xint len; X{ X int x = 0, sx, ex, y; X struct markdata *markdata; X X markdata = (struct markdata *)d_lay->l_data; X markdata->isdir = 1; X if (len) X strcpy(markdata->isstr, buf); X sx = markdata->cx + 1; X ex = d_width - 1; X for (y = markdata->cy; y < fore->w_histheight + d_height; y++, sx = 0) X { X if ((x = matchword(markdata->isstr, y, sx, ex)) >= 0) X break; X } X if (y >= fore->w_histheight + d_height) X { X GotoPos(markdata->cx, W2D(markdata->cy)); X Msg(0, "Pattern not found"); X } X else X revto(x, y); X} X Xstatic void Xbacksearchend(buf, len) Xchar *buf; Xint len; X{ X int sx, ex, x = -1, y; X struct markdata *markdata; X X markdata = (struct markdata *)d_lay->l_data; X markdata->isdir = -1; X if (len) X strcpy(markdata->isstr, buf); X ex = markdata->cx - 1; X for (y = markdata->cy; y >= 0; y--, ex = d_width - 1) X { X sx = 0; X while ((sx = matchword(markdata->isstr, y, sx, ex)) >= 0) X x = sx++; X if (x >= 0) X break; X } X if (y < 0) X { X GotoPos(markdata->cx, W2D(markdata->cy)); X Msg(0, "Pattern not found"); X } X else X revto(x, y); X} X Xstatic int Xmatchword(pattern, y, sx, ex) Xchar *pattern; Xint y, sx, ex; X{ X char *ip, *ipe, *cp, *pp; X X ip = iWIN(y) + sx; X ipe = iWIN(y) + d_width; X for (;sx <= ex; sx++) X { X cp = ip++; X pp = pattern; X while (*cp++ == *pp++) X if (*pp == 0) X return sx; X else if (cp == ipe) X break; X } X return -1; X} X X X/******************************************************************** X * Emacs style ISearch X */ X Xstatic char *isprompts[] = { X "I-search backward: ", "failing I-search backward: ", X "I-search: ", "failing I-search: " X}; X X Xstatic int is_redo __P((struct markdata *)); Xstatic void is_process __P((char *, int)); Xstatic int is_bm __P((char *, int, int, int, int)); X X Xstatic int Xis_bm(str, l, p, end, dir) Xchar *str; Xint l, p, end, dir; X{ X int tab[256]; X int i, q; X char *s, c; X int w = d_width; X X debug2("is_bm: searching for %s len %d\n", str, l); X debug3("start at %d end %d dir %d\n", p, end, dir); X if (p < 0 || p + l > end) X return -1; X if (l == 0) X return p; X if (dir < 0) X str += l - 1; X for (i = 0; i < 256; i++) X tab[i] = l * dir; X for (i = 0; i < l - 1; i++, str += dir) X tab[(int)(unsigned char) *str] = (l - 1 - i) * dir; X if (dir > 0) X p += l - 1; X debug1("first char to match: %c\n", *str); X while (p >= 0 && p < end) X { X q = p; X s = str; X for (i = 0;;) X { X c = iWIN(q / w)[q % w]; X if (i == 0) X p += tab[(int)(unsigned char) c]; X if (c != *s) X break; X q -= dir; X s -= dir; X if (++i == l) X return q + (dir > 0 ? 1 : -l); X } X } X return -1; X} X X X/*ARGSUSED*/ Xstatic void Xis_process(p, n) Xchar *p; Xint n; X{ X int pos, x, y, dir; X struct markdata *markdata; X X if (n == 0) X return; X markdata = (struct markdata *)d_lay->l_next->l_data; X ASSERT(p); X X pos = markdata->cx + markdata->cy * d_width; X GotoPos(markdata->cx, W2D(markdata->cy)); X X switch (*p) X { X case '\007': /* CTRL-G */ X pos = markdata->isstartpos; X /*FALLTHROUGH*/ X case '\033': /* ESC */ X *p = 0; X break; X case '\013': /* CTRL-K */ X case '\027': /* CTRL-W */ X markdata->isistrl = 1; X /*FALLTHROUGH*/ X case '\b': X case '\177': X if (markdata->isistrl == 0) X return; X markdata->isistrl--; X pos = is_redo(markdata); X *p = '\b'; X break; X case '\023': /* CTRL-S */ X case '\022': /* CTRL-R */ X if (markdata->isistrl >= sizeof(markdata->isistr)) X return; X dir = (*p == '\023') ? 1 : -1; X pos += dir; X if (markdata->isdir == dir && markdata->isistrl == 0) X { X strcpy(markdata->isistr, markdata->isstr); X markdata->isistrl = markdata->isstrl = strlen(markdata->isstr); X break; X } X markdata->isdir = dir; X markdata->isistr[markdata->isistrl++] = *p; X break; X default: X if (*p < ' ' || markdata->isistrl >= sizeof(markdata->isistr) X || markdata->isstrl >= sizeof(markdata->isstr) - 1) X return; X markdata->isstr[markdata->isstrl++] = *p; X markdata->isistr[markdata->isistrl++] = *p; X markdata->isstr[markdata->isstrl] = 0; X debug2("New char: %c - left %d\n", *p, sizeof(markdata->isistr) - markdata->isistrl); X } X if (*p && *p != '\b') X pos = is_bm(markdata->isstr, markdata->isstrl, pos, d_width * (fore->w_histheight + d_height), markdata->isdir); X if (pos >= 0) X { X x = pos % d_width; X y = pos / d_width; X LAY_CALL_UP X ( X RefreshLine(STATLINE, 0, d_width - 1, 0); X revto(x, y); X if (W2D(markdata->cy) == STATLINE) X { X revto_line(markdata->cx, markdata->cy, STATLINE > 0 ? STATLINE - 1 : 1); X } X ); X } X if (*p) X inp_setprompt(isprompts[markdata->isdir + (pos < 0) + 1], markdata->isstrl ? markdata->isstr : ""); X GotoPos(markdata->cx, W2D(markdata->cy)); X} X Xstatic int Xis_redo(markdata) Xstruct markdata *markdata; X{ X int i, pos, dir; X char c; X X pos = markdata->isstartpos; X dir = markdata->isstartdir; X markdata->isstrl = 0; X for (i = 0; i < markdata->isistrl; i++) X { X c = markdata->isistr[i]; X if (c == '\022') X pos += (dir = -1); X else if (c == '\023') X pos += (dir = 1); X else X markdata->isstr[markdata->isstrl++] = c; X if (pos >= 0) X pos = is_bm(markdata->isstr, markdata->isstrl, pos, d_width * (fore->w_histheight + d_height), dir); X } X markdata->isstr[markdata->isstrl] = 0; X markdata->isdir = dir; X return pos; X} X Xvoid XISearch(dir) Xint dir; X{ X struct markdata *markdata; X markdata = (struct markdata *)d_lay->l_data; X markdata->isdir = markdata->isstartdir = dir; X markdata->isstartpos = markdata->cx + markdata->cy * d_width; X markdata->isistrl = markdata->isstrl = 0; X if (W2D(markdata->cy) == STATLINE) X { X revto_line(markdata->cx, markdata->cy, STATLINE > 0 ? STATLINE - 1 : 1); X } X Input(isprompts[dir + 1], sizeof(markdata->isstr) - 1, is_process, INP_RAW); X GotoPos(markdata->cx, W2D(markdata->cy)); X} X X#endif /* COPY_PASTE */ END_OF_FILE if test 7998 -ne `wc -c <'search.c'`; then echo shar: \"'search.c'\" unpacked with wrong size! fi # end of 'search.c' fi echo shar: End of archive 2 \(of 10\). cp /dev/null ark2isdone MISSING="" for I in 1 2 3 4 5 6 7 8 9 10 ; do if test ! -f ark${I}isdone ; then MISSING="${MISSING} ${I}" fi done if test "${MISSING}" = "" ; then echo You have unpacked all 10 archives. rm -f ark[1-9]isdone ark[1-9][0-9]isdone else echo You still need to unpack the following archives: echo " " ${MISSING} fi ## End of shell archive. exit 0