v12i095: kterm - kanji xterm, Part14/18

mleisher at NMSU.Edu mleisher at NMSU.Edu
Sat May 11 10:51:31 AEST 1991


Submitted-by: mleisher at NMSU.Edu
Posting-number: Volume 12, Issue 95
Archive-name: kterm/part14

#!/bin/sh
# this is kt412.14 (part 14 of kterm-4.1.2)
# do not concatenate these parts, unpack them in order with /bin/sh
# file kterm-4.1.2/main.c continued
#
if test ! -r _shar_seq_.tmp; then
	echo 'Please unpack part 1 first!'
	exit 1
fi
(read Scheck
 if test "$Scheck" != 14; then
	echo Please unpack part "$Scheck" next!
	exit 1
 else
	exit 0
 fi
) < _shar_seq_.tmp || exit 1
if test ! -f _shar_wnt_.tmp; then
	echo 'x - still skipping kterm-4.1.2/main.c'
else
echo 'x - continuing file kterm-4.1.2/main.c'
sed 's/^X//' << 'SHAR_EOF' >> 'kterm-4.1.2/main.c' &&
X		bcopy((char *)environ, (char *)envnew, i * sizeof(char *));
X		environ = envnew;
X		Setenv ("TERM=", TermName);
X		if(!TermName)
X			*newtc = 0;
X
X		sprintf (buf, "%lu", screen->TekEmu ? 
X			 ((unsigned long) XtWindow (XtParent(tekWidget))) :
X			 ((unsigned long) XtWindow (XtParent(term))));
X		Setenv ("WINDOWID=", buf);
X		/* put the display into the environment of the shell*/
X		Setenv ("DISPLAY=", XDisplayString (screen->display));
X
X		signal(SIGTERM, SIG_DFL);
X
X		/* this is the time to go and set up stdin, out, and err
X		 */
X		{
X		    /* dup the tty */
X		    for (i = 0; i <= 2; i++)
X			if (i != tty) {
X			    (void) close(i);
X			    (void) dup(tty);
X			}
X
#ifndef att
X		    /* and close the tty */
X		    if (tty > 2)
X			(void) close(tty);
#endif
X		}
X
#ifndef	USE_SYSV_PGRP
#ifdef TIOCSCTTY
X		setsid();
X		ioctl(0, TIOCSCTTY, 0);
#endif
X		ioctl(0, TIOCSPGRP, (char *)&pgrp);
X		setpgrp(0,0);
X		close(open(ttydev, O_WRONLY, 0));
X		setpgrp (0, pgrp);
#endif /* USE_SYSV_PGRP */
X
#ifdef UTMP
#ifdef USE_SYSV_UTMP
X		/* Set up our utmp entry now.  We need to do it here
X		** for the following reasons:
X		**   - It needs to have our correct process id (for
X		**     login).
X		**   - If our parent was to set it after the fork(),
X		**     it might make it out before we need it.
X		**   - We need to do it before we go and change our
X		**     user and group id's.
X		*/
X
X		(void) setutent ();
X		/* set up entry to search for */
X		(void) strncpy(utmp.ut_id,ttydev + strlen(ttydev) - 2,
X		 sizeof (utmp.ut_id));
X		utmp.ut_type = DEAD_PROCESS;
X
X		/* position to entry in utmp file */
X		(void) getutid(&utmp);
X
X		/* set up the new entry */
X		pw = getpwuid(screen->uid);
X		utmp.ut_type = USER_PROCESS;
X		utmp.ut_exit.e_exit = 2;
X		(void) strncpy(utmp.ut_user,
X			       (pw && pw->pw_name) ? pw->pw_name : "????",
X			       sizeof(utmp.ut_user));
X		    
X		(void) strncpy(utmp.ut_id, ttydev + strlen(ttydev) - 2,
X			sizeof(utmp.ut_id));
X		(void) strncpy (utmp.ut_line,
X			ttydev + strlen("/dev/"), sizeof (utmp.ut_line));
#ifdef HAS_UTMP_UT_HOST
X		(void) strncpy(utmp.ut_host, DisplayString(screen->display),
X			       sizeof(utmp.ut_host));
#endif
X		(void) strncpy(utmp.ut_name, pw->pw_name, 
X			       sizeof(utmp.ut_name));
X
X		utmp.ut_pid = getpid();
X		utmp.ut_time = time ((long *) 0);
X
X		/* write out the entry */
X		if (!resource.utmpInhibit) (void) pututline(&utmp);
X
X		/* close the file */
X		(void) endutent();
X
#else	/* USE_SYSV_UTMP */
X		/* We can now get our ttyslot!  We can also set the initial
X		 * UTMP entry.
X		 */
X		tslot = ttyslot();
X		added_utmp_entry = False;
X		{
X			if ((pw = getpwuid(screen->uid)) &&
X			    !resource.utmpInhibit &&
X			    (i = open(etc_utmp, O_WRONLY)) >= 0) {
X				bzero((char *)&utmp, sizeof(struct utmp));
X				(void) strncpy(utmp.ut_line,
X					       ttydev + strlen("/dev/"),
X					       sizeof(utmp.ut_line));
X				(void) strncpy(utmp.ut_name, pw->pw_name,
X					       sizeof(utmp.ut_name));
#ifdef HAS_UTMP_UT_HOST
X				(void) strncpy(utmp.ut_host, 
X					       XDisplayString (screen->display),
X					       sizeof(utmp.ut_host));
#endif
X				time(&utmp.ut_time);
X				lseek(i, (long)(tslot * sizeof(struct utmp)), 0);
X				write(i, (char *)&utmp, sizeof(struct utmp));
X				close(i);
X				added_utmp_entry = True;
#ifdef WTMP
X				if (term->misc.login_shell &&
X				(i = open(etc_wtmp, O_WRONLY|O_APPEND)) >= 0) {
X				    write(i, (char *)&utmp,
X					sizeof(struct utmp));
X				close(i);
X				}
#endif /* WTMP */
#ifdef LASTLOG
X				if (term->misc.login_shell &&
X				(i = open(etc_lastlog, O_WRONLY)) >= 0) {
X				    bzero((char *)&lastlog,
X					sizeof (struct lastlog));
X				    (void) strncpy(lastlog.ll_line, ttydev +
X					sizeof("/dev"),
X					sizeof (lastlog.ll_line));
X				    (void) strncpy(lastlog.ll_host, 
X					  XDisplayString (screen->display),
X					  sizeof (lastlog.ll_host));
X				    time(&lastlog.ll_time);
X				    lseek(i, (long)(screen->uid *
X					sizeof (struct lastlog)), 0);
X				    write(i, (char *)&lastlog,
X					sizeof (struct lastlog));
X				    close(i);
X				}
#endif /* LASTLOG */
X			} else
X				tslot = -tslot;
X		}
X
X		/* Let's pass our ttyslot to our parent so that it can
X		 * clean up after us.
X		 */
#ifdef USE_HANDSHAKE
X		handshake.tty_slot = tslot;
#endif /* USE_HANDSHAKE */
#endif /* USE_SYSV_UTMP */
X
#ifdef USE_HANDSHAKE
X		/* Let our parent know that we set up our utmp entry
X		 * so that it can clean up after us.
X		 */
X		handshake.status = UTMP_ADDED;
X		handshake.error = 0;
X		strcpy(handshake.buffer, ttydev);
X		(void) write(cp_pipe[1], &handshake, sizeof(handshake));
#endif /* USE_HANDSHAKE */
#endif/* UTMP */
X
X		(void) setgid (screen->gid);
#ifdef HAS_BSD_GROUPS
X		if (geteuid() == 0 && pw)
X		  initgroups (pw->pw_name, pw->pw_gid);
#endif
X		(void) setuid (screen->uid);
X
#ifdef USE_HANDSHAKE
X		/* mark the pipes as close on exec */
X		fcntl(cp_pipe[1], F_SETFD, 1);
X		fcntl(pc_pipe[0], F_SETFD, 1);
X
X		/* We are at the point where we are going to
X		 * exec our shell (or whatever).  Let our parent
X		 * know we arrived safely.
X		 */
X		handshake.status = PTY_GOOD;
X		handshake.error = 0;
X		(void) strcpy(handshake.buffer, ttydev);
X		(void) write(cp_pipe[1], &handshake, sizeof(handshake));
X
X		if (waiting_for_initial_map) {
X		    i = read (pc_pipe[0], (char *) &handshake,
X			      sizeof(handshake));
X		    if (i != sizeof(handshake) ||
X			handshake.status != PTY_EXEC) {
X			/* some very bad problem occurred */
X			exit (ERROR_PTY_EXEC);
X		    }
X		    screen->max_row = handshake.rows;
X		    screen->max_col = handshake.cols;
#ifdef sun
#ifdef TIOCSSIZE
X		    ts.ts_lines = screen->max_row + 1;
X		    ts.ts_cols = screen->max_col + 1;
#endif /* TIOCSSIZE */
#else /* !sun */
#ifdef TIOCSWINSZ
X		    ws.ws_row = screen->max_row + 1;
X		    ws.ws_col = screen->max_col + 1;
X		    ws.ws_xpixel = FullWidth(screen);
X		    ws.ws_ypixel = FullHeight(screen);
#endif /* TIOCSWINSZ */
#endif /* sun else !sun */
X		}
#endif /* USE_HANDSHAKE */
X
#ifdef USE_SYSV_ENVVARS
X		sprintf (numbuf, "%d", screen->max_col + 1);
X		Setenv("COLUMNS=", numbuf);
X		sprintf (numbuf, "%d", screen->max_row + 1);
X		Setenv("LINES=", numbuf);
#else
X		if(!screen->TekEmu) {
X		    strcpy (termcap, newtc);
X		    resize (screen, TermName, termcap, newtc);
X		}
X		if (term->misc.titeInhibit) {
X		    remove_termcap_entry (newtc, ":ti=");
X		    remove_termcap_entry (newtc, ":te=");
X		}
X		Setenv ("TERMCAP=", newtc);
#endif /* USE_SYSV_ENVVAR */
X
X
X		/* need to reset after all the ioctl bashing we did above */
#ifdef sun
#ifdef TIOCSSIZE
X		ioctl  (0, TIOCSSIZE, &ts);
#endif	/* TIOCSSIZE */
#else	/* not sun */
#ifdef TIOCSWINSZ
X		ioctl (0, TIOCSWINSZ, (char *)&ws);
#endif	/* TIOCSWINSZ */
#endif	/* sun */
X
X		signal(SIGHUP, SIG_DFL);
X		if (command_to_exec) {
X			execvp(*command_to_exec, command_to_exec);
X			/* print error message on screen */
X			fprintf(stderr, "%s: Can't execvp %s\n", xterm_name,
X			 *command_to_exec);
X		} 
X
#ifdef att
X		/* fix pts sh hanging around */
X		signal (SIGHUP, SIG_DFL);
#endif
X
#ifdef UTMP
X		if(((ptr = getenv("SHELL")) == NULL || *ptr == 0) &&
X		 ((pw == NULL && (pw = getpwuid(screen->uid)) == NULL) ||
X		 *(ptr = pw->pw_shell) == 0))
#else	/* UTMP */
X		if(((ptr = getenv("SHELL")) == NULL || *ptr == 0) &&
X		 ((pw = getpwuid(screen->uid)) == NULL ||
X		 *(ptr = pw->pw_shell) == 0))
#endif	/* UTMP */
X			ptr = "/bin/sh";
X		if(shname = rindex(ptr, '/'))
X			shname++;
X		else
X			shname = ptr;
X		shname_minus = malloc(strlen(shname) + 2);
X		(void) strcpy(shname_minus, "-");
X		(void) strcat(shname_minus, shname);
#ifndef USE_SYSV_TERMIO
X		ldisc = XStrCmp("csh", shname + strlen(shname) - 3) == 0 ?
X		 NTTYDISC : 0;
X		ioctl(0, TIOCSETD, (char *)&ldisc);
#endif	/* !USE_SYSV_TERMIO */
X
#ifdef USE_LOGIN_DASH_P
X		if (term->misc.login_shell && pw && added_utmp_entry)
X		  execl (bin_login, "login", "-p", "-f", pw->pw_name, 0);
#endif
X		execlp (ptr, (term->misc.login_shell ? shname_minus : shname),
X			0);
X
X		/* Exec failed. */
X		fprintf (stderr, "%s: Could not exec %s!\n", xterm_name, ptr);
X		sleep(5);
X		exit(ERROR_EXEC);
X	    }				/* end if in child after fork */
X
#ifdef USE_HANDSHAKE
X	    /* Parent process.  Let's handle handshaked requests to our
X	     * child process.
X	     */
X
X	    /* close childs's sides of the pipes */
X	    close (cp_pipe[1]);
X	    close (pc_pipe[0]);
X
X	    for (done = 0; !done; ) {
X		if (read(cp_pipe[0], &handshake, sizeof(handshake)) <= 0) {
X			/* Our child is done talking to us.  If it terminated
X			 * due to an error, we will catch the death of child
X			 * and clean up.
X			 */
X			break;
X		}
X
X		switch(handshake.status) {
X		case PTY_GOOD:
X			/* Success!  Let's free up resources and
X			 * continue.
X			 */
X			done = 1;
X			break;
X
X		case PTY_BAD:
X			/* The open of the pty failed!  Let's get
X			 * another one.
X			 */
X			(void) close(screen->respond);
X			if (get_pty(&screen->respond)) {
X			    /* no more ptys! */
X			    (void) fprintf(stderr,
X				   "%s: no available ptys\n", xterm_name);
X			    handshake.status = PTY_NOMORE;
X			    write(pc_pipe[1], &handshake, sizeof(handshake));
X			    exit (ERROR_PTYS);
X			}
X			handshake.status = PTY_NEW;
X			(void) strcpy(handshake.buffer, ttydev);
X			write(pc_pipe[1], &handshake, sizeof(handshake));
X			break;
X
X		case PTY_FATALERROR:
X			errno = handshake.error;
X			close(cp_pipe[0]);
X			close(pc_pipe[1]);
X			SysError(handshake.fatal_error);
X
X		case UTMP_ADDED:
X			/* The utmp entry was set by our slave.  Remember
X			 * this so that we can reset it later.
X			 */
X			added_utmp_entry = True;
#ifndef	USE_SYSV_UTMP
X			tslot = handshake.tty_slot;
#endif	/* USE_SYSV_UTMP */
X			free(ttydev);
X			ttydev = malloc((unsigned) strlen(handshake.buffer) + 1);
X			strcpy(ttydev, handshake.buffer);
X			break;
X		}
X	    }
X	    /* close our sides of the pipes */
X	    if (!waiting_for_initial_map) {
X		close (cp_pipe[0]);
X		close (pc_pipe[1]);
X	    }
#endif /* USE_HANDSHAKE */
X	}				/* end if no slave */
X
X	/*
X	 * still in parent (xterm process)
X	 */
X
#ifdef att
X	/* hung sh problem? */
X	signal (SIGHUP, SIG_DFL);
#else
X	signal (SIGHUP,SIG_IGN);
#endif
X
/*
X * Unfortunately, System V seems to have trouble divorcing the child process
X * from the process group of xterm.  This is a problem because hitting the 
X * INTR or QUIT characters on the keyboard will cause xterm to go away if we
X * don't ignore the signals.  This is annoying.
X */
X
#if defined(USE_SYSV_SIGNALS) && !defined(SIGTSTP)
X	signal (SIGINT, SIG_IGN);
X
#ifndef att
X	/* hung shell problem */
X	signal (SIGQUIT, SIG_IGN);
#endif
X	signal (SIGTERM, SIG_IGN);
#else /* else is bsd or has job control */
#ifdef SYSV
X	/* if we were spawned by a jobcontrol smart shell (like ksh or csh),
X	 * then our pgrp and pid will be the same.  If we were spawned by
X	 * a jobcontrol dump shell (like /bin/sh), then we will be in out
X	 * parents pgrp, and we must ignore keyboard signals, or will will
X	 * tank on everything.
X	 */
X	if (getpid() == getpgrp()) {
X	    (void) signal(SIGINT, Exit);
X	    (void) signal(SIGQUIT, Exit);
X	    (void) signal(SIGTERM, Exit);
X	} else {
X	    (void) signal(SIGINT, SIG_IGN);
X	    (void) signal(SIGQUIT, SIG_IGN);
X	    (void) signal(SIGTERM, SIG_IGN);
X	}
#else	/* SYSV */
X	signal (SIGINT, Exit);
X	signal (SIGQUIT, Exit);
X	signal (SIGTERM, Exit);
#endif	/* SYSV */
#endif /* USE_SYSV_SIGNALS and not SIGTSTP */
X
X	return;
}							/* end spawn */
X
SIGNAL_T Exit(n)
X	int n;
{
X	register TScreen *screen = &term->screen;
X        int pty = term->screen.respond;  /* file descriptor of pty */
#ifdef UTMP
#ifdef USE_SYSV_UTMP
X	struct utmp utmp;
X	struct utmp *utptr;
#ifdef WTMP
X	int fd;			/* for /etc/wtmp */
#endif
X	/* cleanup the utmp entry we forged earlier */
X	if (!resource.utmpInhibit && added_utmp_entry) {
#ifdef CRAY
#define PTYCHARLEN 4
#else
#define PTYCHARLEN 2
#endif
X	    utmp.ut_type = USER_PROCESS;
X	    (void) strncpy(utmp.ut_id, ttydev + strlen(ttydev) - PTYCHARLEN,
X		    sizeof(utmp.ut_id));
X	    (void) setutent();
X	    utptr = getutid(&utmp);
X	    /* write it out only if it exists, and the pid's match */
X	    if (utptr && (utptr->ut_pid = screen->pid)) {
X		    utptr->ut_type = DEAD_PROCESS;
X		    utptr->ut_time = time((long *) 0);
X		    (void) pututline(utptr);
#ifdef WTMP
X		    /* set wtmp entry if wtmp file exists */
X		    if ((fd = open(etc_wtmp, O_WRONLY | O_APPEND)) >= 0) {
X		      (void) write(fd, utptr, sizeof(utmp));
X		      (void) close(fd);
X		    }
#endif
X
X	    }
X	    (void) endutent();
X	}
#else	/* not USE_SYSV_UTMP */
X	register int i;
X	struct utmp utmp;
X
X	if (!resource.utmpInhibit && added_utmp_entry &&
X	    (!am_slave && tslot > 0 && (i = open(etc_utmp, O_WRONLY)) >= 0)) {
X		bzero((char *)&utmp, sizeof(struct utmp));
X		lseek(i, (long)(tslot * sizeof(struct utmp)), 0);
X		write(i, (char *)&utmp, sizeof(struct utmp));
X		close(i);
#ifdef WTMP
X		if (term->misc.login_shell &&
X		    (i = open(etc_wtmp, O_WRONLY | O_APPEND)) >= 0) {
X			(void) strncpy(utmp.ut_line, ttydev +
X			    sizeof("/dev"), sizeof (utmp.ut_line));
X			time(&utmp.ut_time);
X			write(i, (char *)&utmp, sizeof(struct utmp));
X			close(i);
X		}
#endif /* WTMP */
X	}
#endif	/* USE_SYSV_UTMP */
#endif	/* UTMP */
X        close(pty); /* close explicitly to avoid race with slave side */
X	if(screen->logging)
X		CloseLog(screen);
X
X	if (!am_slave) {
X		/* restore ownership of tty and pty */
X		chown (ttydev, 0, 0);
X		chown (ptydev, 0, 0);
X
X		/* restore modes of tty and pty */
X		chmod (ttydev, 0666);
X		chmod (ptydev, 0666);
X	}
X	exit(n);
X	SIGNAL_RETURN;
}
X
/* ARGSUSED */
resize(screen, TermName, oldtc, newtc)
TScreen *screen;
char *TermName;
register char *oldtc, *newtc;
{
#ifndef USE_SYSV_ENVVARS
X	register char *ptr1, *ptr2;
X	register int i;
X	register int li_first = 0;
X	register char *temp;
X	char *index();
X
X	if ((ptr1 = strindex (oldtc, "co#")) == NULL){
X		strcat (oldtc, "co#80:");
X		ptr1 = strindex (oldtc, "co#");
X	}
X	if ((ptr2 = strindex (oldtc, "li#")) == NULL){
X		strcat (oldtc, "li#24:");
X		ptr2 = strindex (oldtc, "li#");
X	}
X	if(ptr1 > ptr2) {
X		li_first++;
X		temp = ptr1;
X		ptr1 = ptr2;
X		ptr2 = temp;
X	}
X	ptr1 += 3;
X	ptr2 += 3;
X	strncpy (newtc, oldtc, i = ptr1 - oldtc);
X	newtc += i;
X	sprintf (newtc, "%d", li_first ? screen->max_row + 1 :
X	 screen->max_col + 1);
X	newtc += strlen(newtc);
X	ptr1 = index (ptr1, ':');
X	strncpy (newtc, ptr1, i = ptr2 - ptr1);
X	newtc += i;
X	sprintf (newtc, "%d", li_first ? screen->max_col + 1 :
X	 screen->max_row + 1);
X	ptr2 = index (ptr2, ':');
X	strcat (newtc, ptr2);
#endif /* USE_SYSV_ENVVARS */
}
X
static SIGNAL_T reapchild ()
{
#if defined(USE_SYSV_SIGNALS) && !defined(SIGTSTP)
X	int status, pid;
X
X	pid = wait(&status);
X	if (pid == -1) {
X		(void) signal(SIGCHLD, reapchild);
X		SIGNAL_RETURN;
X	}
#else	/* defined(USE_SYSV_SIGNALS) && !defined(SIGTSTP) */
X	union wait status;
X	register int pid;
X	
#ifdef DEBUG
X	if (debug) fputs ("Exiting\n", stderr);
#endif	/* DEBUG */
X	pid  = wait3 (&status, WNOHANG, (struct rusage *)NULL);
X	if (!pid) {
#ifdef USE_SYSV_SIGNALS
X		(void) signal(SIGCHLD, reapchild);
#endif /* USE_SYSV_SIGNALS */
X		SIGNAL_RETURN;
X	}
#endif	/* defined(USE_SYSV_SIGNALS) && !defined(SIGTSTP) */
X
#ifdef PUCC_PTYD
X		closepty(ttydev, ptydev, (resource.utmpInhibit ?  OPTY_NOP : OPTY_LOGIN), Ptyfd);
#endif /* PUCC_PTYD */
X
X	if (pid != term->screen.pid) {
#ifdef USE_SYSV_SIGNALS
X		(void) signal(SIGCHLD, reapchild);
#endif	/* USE_SYSV_SIGNALS */
X		SIGNAL_RETURN;
X	}
X	
X	/*
X	 * Use pid instead of process group (which would have to get before
X	 * the wait call above) so that we don't accidentally hose other
X	 * applications.  Otherwise, somebody could write a program which put
X	 * itself in somebody else's process group.  Also, we call Exit instead
X	 * of Cleanup so that we don't do a killpg on -1 by accident.  Some
X	 * operating systems seem to do very nasty things with that.
X	 */
X	if (pid > 1) {
X	    killpg (pid, SIGHUP);
X	}
X	Exit (0);
X	SIGNAL_RETURN;
}
X
/* VARARGS1 */
consolepr(fmt,x0,x1,x2,x3,x4,x5,x6,x7,x8,x9)
char *fmt;
{
X	extern int errno;
X	extern char *SysErrorMsg();
X	int oerrno;
X	int f;
X 	char buf[ BUFSIZ ];
X
X	oerrno = errno;
X 	strcpy(buf, "xterm: ");
X 	sprintf(buf+strlen(buf), fmt, x0,x1,x2,x3,x4,x5,x6,x7,x8,x9);
X 	strcat(buf, ": ");
X 	strcat(buf, SysErrorMsg (oerrno));
X 	strcat(buf, "\n");	
X	f = open("/dev/console",O_WRONLY);
X	write(f, buf, strlen(buf));
X	close(f);
#ifdef TIOCNOTTY
X	if ((f = open("/dev/tty", 2)) >= 0) {
X		ioctl(f, TIOCNOTTY, (char *)NULL);
X		close(f);
X	}
#endif	/* TIOCNOTTY */
}
X
X
remove_termcap_entry (buf, str)
X    char *buf;
X    char *str;
{
X    register char *strinbuf;
X
X    strinbuf = strindex (buf, str);
X    if (strinbuf) {
X        register char *colonPtr = index (strinbuf+1, ':');
X        if (colonPtr) {
X            while (*colonPtr) {
X                *strinbuf++ = *colonPtr++;      /* copy down */
X            }
X            *strinbuf = '\0';
X        } else {
X            strinbuf[1] = '\0';
X        }
X    }
X    return;
}
X
/*
X * parse_tty_modes accepts lines of the following form:
X *
X *         [SETTING] ...
X *
X * where setting consists of the words in the modelist followed by a character
X * or ^char.
X */
static int parse_tty_modes (s, modelist, nmodes)
X    char *s;
X    struct _xttymodes *modelist;
X    int nmodes;
{
X    struct _xttymodes *mp;
X    int c, i;
X    int count = 0;
X
X    while (1) {
X	while (*s && isascii(*s) && isspace(*s)) s++;
X	if (!*s) return count;
X
X	for (mp = modelist, i = 0; mp->name; mp++, i++) {
X	    if (strncmp (s, mp->name, mp->len) == 0) break;
X	}
X	if (!mp->name) return -1;
X
X	s += mp->len;
X	while (*s && isascii(*s) && isspace(*s)) s++;
X	if (!*s) return -1;
X
X	if (*s == '^') {
X	    s++;
X	    c = ((*s == '?') ? 0177 : *s & 31);	 /* keep control bits */
X	} else {
X	    c = *s;
X	}
X	mp->value = c;
X	mp->set = 1;
X	count++;
X	s++;
X    }
}
X
X
int GetBytesAvailable (fd)
X    int fd;
{
#ifdef FIONREAD
X    static long arg;
X    ioctl (fd, FIONREAD, (char *) &arg);
X    return (int) arg;
#else
X    struct pollfd pollfds[1];
X
X    pollfds[0].fd = fd;
X    pollfds[0].events = POLLIN;
X    return poll (pollfds, 1, 0);
#endif
}
X
SHAR_EOF
echo 'File kterm-4.1.2/main.c is complete' &&
chmod 0664 kterm-4.1.2/main.c ||
echo 'restore of kterm-4.1.2/main.c failed'
Wc_c="`wc -c < 'kterm-4.1.2/main.c'`"
test 73676 -eq "$Wc_c" ||
	echo 'kterm-4.1.2/main.c: original size 73676, current size' "$Wc_c"
rm -f _shar_wnt_.tmp
fi
# ============= kterm-4.1.2/main.h ==============
if test -f 'kterm-4.1.2/main.h' -a X"$1" != X"-c"; then
	echo 'x - skipping kterm-4.1.2/main.h (File already exists)'
	rm -f _shar_wnt_.tmp
else
> _shar_wnt_.tmp
echo 'x - extracting kterm-4.1.2/main.h (Text)'
sed 's/^X//' << 'SHAR_EOF' > 'kterm-4.1.2/main.h' &&
/*
X *	$XConsortium: main.h,v 1.3 88/09/06 17:08:12 jim Exp $
X */
X
X
#include <X11/copyright.h>
X
/*
X * Copyright 1987 by Digital Equipment Corporation, Maynard, Massachusetts.
X *
X *                         All Rights Reserved
X *
X * Permission to use, copy, modify, and distribute this software and its
X * documentation for any purpose and without fee is hereby granted,
X * provided that the above copyright notice appear in all copies and that
X * both that copyright notice and this permission notice appear in
X * supporting documentation, and that the name of Digital Equipment
X * Corporation not be used in advertising or publicity pertaining to
X * distribution of the software without specific, written prior permission.
X *
X *
X * DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
X * ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
X * DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
X * ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
X * WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
X * ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
X * SOFTWARE.
X */
X
/* @(#)main.h\tX10/6.6\t11/10/86 */
X
#define	DEFBOLDFONT		"fixed"
#define	DEFBORDER		2
#define	DEFBORDERWIDTH		2
#define	DEFFONT			"fixed"
SHAR_EOF
chmod 0664 kterm-4.1.2/main.h ||
echo 'restore of kterm-4.1.2/main.h failed'
Wc_c="`wc -c < 'kterm-4.1.2/main.h'`"
test 1328 -eq "$Wc_c" ||
	echo 'kterm-4.1.2/main.h: original size 1328, current size' "$Wc_c"
rm -f _shar_wnt_.tmp
fi
# ============= kterm-4.1.2/menu.c ==============
if test -f 'kterm-4.1.2/menu.c' -a X"$1" != X"-c"; then
	echo 'x - skipping kterm-4.1.2/menu.c (File already exists)'
	rm -f _shar_wnt_.tmp
else
> _shar_wnt_.tmp
echo 'x - extracting kterm-4.1.2/menu.c (Text)'
sed 's/^X//' << 'SHAR_EOF' > 'kterm-4.1.2/menu.c' &&
/* Copyright 1989 Massachusetts Institute of Technology */
/*
X *	$Kagotani: /usr/src.yoshi/X/KTerm/4.1.0/RCS/menu.c,v 1.1 90/06/27 09:39:19 kagotani Rel $
X *
X * $Header: /usr/local/src/X11/contrib/clients/kterm-4.1.2/RCS/menu.c,v 1.4 1991/01/30 00:11:37 mleisher Exp $
X */
X
/*
X * Modified for Hanzi support:
X * Mark Leisher mleisher at nmsu.edu Fri Nov  9 09:22:33 1990
X */
X
#include <stdio.h>
#include <X11/Intrinsic.h>
#include <X11/StringDefs.h>
#include <X11/Shell.h>
#include <X11/Xaw/SimpleMenu.h>
#include <X11/Xaw/SmeBSB.h>
#include <X11/Xaw/SmeLine.h>
#include "ptyx.h"
#include <setjmp.h>			/* for data.h */
#include "data.h"
#include "menu.h"
X
Arg menuArgs[2] = {{ XtNleftBitmap, (XtArgVal) 0 },
X		   { XtNsensitive, (XtArgVal) 0 }};
X
static void do_securekbd(), do_allowsends(), do_visualbell(), do_logging(),
X  do_redraw(), do_suspend(), do_continue(), do_interrupt(), do_hangup(),
X  do_terminate(), do_kill(), do_quit(), do_scrollbar(), do_jumpscroll(),
X  do_reversevideo(), do_autowrap(), do_reversewrap(), do_autolinefeed(),
X  do_appcursor(), do_appkeypad(), do_scrollkey(), do_scrollttyoutput(),
X  do_allow132(), do_cursesemul(), do_marginbell(), do_tekshow(), 
X  do_altscreen(), do_softreset(), do_hardreset(), do_tekmode(), do_vthide(), 
X  do_tektextlarge(), do_tektext2(), do_tektext3(), do_tektextsmall(), 
X  do_tekpage(), do_tekreset(), do_tekcopy(), do_vtshow(), do_vtmode(), 
X  do_tekhide(), do_vtfont();
#ifdef STATUSLINE
static void do_statusline(), do_reversestatus();
#endif /* STATUSLINE */
#ifdef KTERM_KANJI
static void do_eucmode();
static void do_sjismode();
#endif /* KTERM_KANJI */
#ifdef KTERM_HANZI
static void do_big5mode();
static void do_sgbmode();
#endif /* KTERM_HANZI */
#ifdef KTERM_HANGUL
static void do_ksmode();
static void do_nbmode();
#endif /* KTERM_HANGUL */
X
X
/*
X * The order entries MUST match the values given in menu.h
X */
MenuEntry mainMenuEntries[] = {
X    { "securekbd",	do_securekbd, NULL },		/*  0 */
X    { "allowsends",	do_allowsends, NULL },		/*  1 */
X    { "logging",	do_logging, NULL },		/*  2 */
X    { "redraw",		do_redraw, NULL },		/*  3 */
X    { "line1",		NULL, NULL },			/*  4 */
X    { "suspend",	do_suspend, NULL },		/*  5 */
X    { "continue",	do_continue, NULL },		/*  6 */
X    { "interrupt",	do_interrupt, NULL },		/*  7 */
X    { "hangup",		do_hangup, NULL },		/*  8 */
X    { "terminate",	do_terminate, NULL },		/*  9 */
X    { "kill",		do_kill, NULL },		/* 10 */
X    { "line2",		NULL, NULL },			/* 11 */
X    { "quit",		do_quit, NULL }};		/* 12 */
X
MenuEntry vtMenuEntries[] = {
X    { "scrollbar",	do_scrollbar, NULL },		/*  0 */
X    { "jumpscroll",	do_jumpscroll, NULL },		/*  1 */
X    { "reversevideo",	do_reversevideo, NULL },	/*  2 */
X    { "autowrap",	do_autowrap, NULL },		/*  3 */
X    { "reversewrap",	do_reversewrap, NULL },		/*  4 */
X    { "autolinefeed",	do_autolinefeed, NULL },	/*  5 */
X    { "appcursor",	do_appcursor, NULL },		/*  6 */
X    { "appkeypad",	do_appkeypad, NULL },		/*  7 */
X    { "scrollkey",	do_scrollkey, NULL },		/*  8 */
X    { "scrollttyoutput",	do_scrollttyoutput, NULL },	/*  9 */
X    { "allow132",	do_allow132, NULL },		/* 10 */
X    { "cursesemul",	do_cursesemul, NULL },		/* 11 */
X    { "visualbell",	do_visualbell, NULL },		/* 12 */
X    { "marginbell",	do_marginbell, NULL },		/* 13 */
X    { "altscreen",	do_altscreen, NULL },		/* 14 */
X    { "line1",		NULL, NULL },			/* 15 */
X    { "softreset",	do_softreset, NULL },		/* 16 */
X    { "hardreset",	do_hardreset, NULL },		/* 17 */
X    { "line2",		NULL, NULL },			/* 18 */
X    { "tekshow",	do_tekshow, NULL },		/* 19 */
X    { "tekmode",	do_tekmode, NULL },		/* 20 */
#if defined(STATUSLINE) || defined(KTERM_KANJI)
X    { "vthide",		do_vthide, NULL },		/* 21 */
X    { "line3",		NULL, NULL },			/* 22 */
#ifdef STATUSLINE
X    { "statusline",	do_statusline, NULL },
X    { "reversestatus",	do_reversestatus, NULL },
#endif /* STATUSLINE */
#ifdef KTERM_KANJI
X    { "eucmode",	do_eucmode, NULL },
X    { "sjismode",	do_sjismode, NULL },
#endif /* KTERM_KANJI */
#ifdef KTERM_HANZI
X    { "sgbmode",        do_sgbmode, NULL },
X    { "big5mode",       do_big5mode, NULL },
#endif /* KTERM_HANZI */
#ifdef KTERM_HANGUL
X    { "ksmode",		do_ksmode, NULL },
X    { "nbmode",		do_nbmode, NULL },
#endif /* KTERM_HANGUL */
X    };
#else /* !STATUSLINE && !KTERM_KANJI */
X    { "vthide",		do_vthide, NULL }};		/* 21 */
#endif /* !STATUSLINE && !KTERM_KANJI */
X
MenuEntry fontMenuEntries[] = {
X    { "fontdefault",	do_vtfont, NULL },		/*  0 */
X    { "font1",		do_vtfont, NULL },		/*  1 */
X    { "font2",		do_vtfont, NULL },		/*  2 */
X    { "font3",		do_vtfont, NULL },		/*  3 */
X    { "font4",		do_vtfont, NULL },		/*  4 */
X    { "fontescape",	do_vtfont, NULL },		/*  5 */
X    { "fontsel",	do_vtfont, NULL }};		/*  6 */
X    /* this should match NMENUFONTS in ptyx.h */
X
MenuEntry tekMenuEntries[] = {
X    { "tektextlarge",	do_tektextlarge, NULL },	/*  0 */
X    { "tektext2",	do_tektext2, NULL },		/*  1 */
X    { "tektext3",	do_tektext3, NULL },		/*  2 */
X    { "tektextsmall",	do_tektextsmall, NULL },	/*  3 */
X    { "line1",		NULL, NULL },			/*  4 */
X    { "tekpage",	do_tekpage, NULL },		/*  5 */
X    { "tekreset",	do_tekreset, NULL },		/*  6 */
X    { "tekcopy",	do_tekcopy, NULL },		/*  7 */
X    { "line2",		NULL, NULL },			/*  8 */
X    { "vtshow",		do_vtshow, NULL },		/*  9 */
X    { "vtmode",		do_vtmode, NULL },		/* 10 */
X    { "tekhide",	do_tekhide, NULL }};		/* 11 */
X
static Widget create_menu();
extern Widget toplevel;
X
X
/*
X * we really want to do these dynamically
X */
#define check_width 9
#define check_height 8
static char check_bits[] = {
X   0x00, 0x01, 0x80, 0x01, 0xc0, 0x00, 0x60, 0x00,
X   0x31, 0x00, 0x1b, 0x00, 0x0e, 0x00, 0x04, 0x00
};
X
X
/*
X * public interfaces
X */
X
static Bool domenu (w, event, params, param_count)
X    Widget w;
X    XEvent *event;              /* unused */
X    String *params;             /* mainMenu, vtMenu, or tekMenu */
X    Cardinal *param_count;      /* 0 or 1 */
{
X    TScreen *screen = &term->screen;
#ifdef KTERM
X    int fnum = F_ISO8859_1; /* menu_font_names */
#endif /* KTERM */
X
X    if (*param_count != 1) {
X	XBell (XtDisplay(w), 0);
X	return False;
X    }
X
X    switch (params[0][0]) {
X      case 'm':
X	if (!screen->mainMenu) {
X	    screen->mainMenu = create_menu (term, toplevel, "mainMenu",
X					    mainMenuEntries,
X					    XtNumber(mainMenuEntries));
X	    update_securekbd();
X	    update_allowsends();
#ifdef ENBUG /* kagotani */
X	    update_visualbell();
#endif
X	    update_logging();
#ifndef SIGTSTP
X	    set_sensitivity (screen->mainMenu,
X			     mainMenuEntries[mainMenu_suspend].widget, FALSE);
#endif
#ifndef SIGCONT
X	    set_sensitivity (screen->mainMenu, 
X			     mainMenuEntries[mainMenu_continue].widget, FALSE);
#endif
X	}
X	break;
X
X      case 'v':
X	if (!screen->vtMenu) {
X	    screen->vtMenu = create_menu (term, toplevel, "vtMenu",
X					  vtMenuEntries,
X					  XtNumber(vtMenuEntries));
X	    /* and turn off the alternate screen entry */
X	    set_altscreen_sensitivity (FALSE);
X	    update_scrollbar();
X	    update_jumpscroll();
X	    update_reversevideo();
X	    update_autowrap();
X	    update_reversewrap();
X	    update_autolinefeed();
X	    update_appcursor();
X	    update_appkeypad();
X	    update_scrollkey();
X	    update_scrollttyoutput();
X	    update_allow132();
X	    update_cursesemul();
#ifndef ENBUG /* kagotani */
X	    update_visualbell();
#endif
X	    update_marginbell();
#ifdef STATUSLINE
X	    update_statusline();
X	    set_reversestatus_sensitivity();
X	    update_reversestatus();
#endif /* STATUSLINE */
#ifdef KTERM_KANJI
X	    update_eucmode();
X	    update_sjismode();
#ifdef KTERM_HANZI
X            update_big5mode();
X            update_sgbmode();
#endif /* KTERM_HANZI */
#ifdef KTERM_HANGUL
X            update_ksmode();
X            update_nbmode();
#endif /* KTERM_HANGUL */
#endif /* KTERM_KANJI */
X	}
X	break;
X
X      case 'f':
X	if (!screen->fontMenu) {
X	    screen->fontMenu = create_menu (term, toplevel, "fontMenu",
X					    fontMenuEntries,
X					    NMENUFONTS);  
X	    set_menu_font (True);
X	    set_sensitivity (screen->fontMenu,
X			     fontMenuEntries[fontMenu_fontescape].widget,
X			     (screen->menu_font_names[fontMenu_fontescape]
X			      ? TRUE : FALSE));
X	}
X	FindFontSelection (NULL, True);
X	set_sensitivity (screen->fontMenu,
X			 fontMenuEntries[fontMenu_fontsel].widget,
X			 (screen->menu_font_names[fontMenu_fontsel]
X			  ? TRUE : FALSE));
X	break;
X
X      case 't':
X	if (!screen->tekMenu) {
X	    screen->tekMenu = create_menu (term, toplevel, "tekMenu",
X					   tekMenuEntries,
X					   XtNumber(tekMenuEntries));
X	    set_tekfont_menu_item (screen->cur.fontsize, TRUE);
X	}
X	break;
X
X      default:
X	XBell (XtDisplay(w), 0);
X	return False;
X    }
X
X    return True;
}
X
void HandleCreateMenu (w, event, params, param_count)
X    Widget w;
X    XEvent *event;              /* unused */
X    String *params;             /* mainMenu, vtMenu, or tekMenu */
X    Cardinal *param_count;      /* 0 or 1 */
{
X    (void) domenu (w, event, params, param_count);
}
X
void HandlePopupMenu (w, event, params, param_count)
X    Widget w;
X    XEvent *event;              /* unused */
X    String *params;             /* mainMenu, vtMenu, or tekMenu */
X    Cardinal *param_count;      /* 0 or 1 */
{
X    if (domenu (w, event, params, param_count)) {
X	XtCallActionProc (w, "XawPositionSimpleMenu", event, params, 1);
X	XtCallActionProc (w, "MenuPopup", event, params, 1);
X    }
}
X
X
/*
X * private interfaces - keep out!
X */
X
/*
X * create_menu - create a popup shell and stuff the menu into it.
X */
X
static Widget create_menu (xtw, toplevel, name, entries, nentries)
X    XtermWidget xtw;
X    Widget toplevel;
X    char *name;
X    struct _MenuEntry *entries;
X    int nentries;
{
X    Widget m;
X    TScreen *screen = &xtw->screen;
X    static XtCallbackRec cb[2] = { { NULL, NULL }, { NULL, NULL }};
X    static Arg arg = { XtNcallback, (XtArgVal) cb };
#ifdef KTERM_KANJI
X    Misc *misc = &xtw->misc;
X    int count;
#endif
X
X    if (screen->menu_item_bitmap == None) {
X	screen->menu_item_bitmap =
X	  XCreateBitmapFromData (XtDisplay(xtw),
X				 RootWindowOfScreen(XtScreen(xtw)),
X				 check_bits, check_width, check_height);
X    }
X
X    m = XtCreatePopupShell (name, simpleMenuWidgetClass, toplevel, NULL, 0);
X
#ifdef KTERM_KANJI
X    for (count = 0; count < nentries; count++) {
X        switch(misc->lang[0]) {
#ifdef KTERM_HANZI
X          case 'c':
X          case 'C':
X            if ((count >= vtMenu_jmodestart && count < vtMenu_hzmodestart) ||
X                count > vtMenu_hzmodeend)
X              continue;
X            break;
#endif /* KTERM_HANZI */
#ifdef KTERM_HANGUL
X          case 'k':
X          case 'K':
X            if ((count >= vtMenu_jmodestart && count < vtMenu_hgmodestart) ||
X                count > vtMenu_hgmodeend)
X              continue;
X            break;
#endif /* KTERM_HANGUL */
X          default:
X            if (count > vtMenu_jmodeend)
X              continue;
X            break;
X        }
X        cb[0].callback = (XtCallbackProc) entries[count].function;
X        cb[0].closure = (caddr_t) entries[count].name;
X        entries[count].widget =
X          XtCreateManagedWidget (entries[count].name, 
X                                 (entries[count].function ?
X                                  smeBSBObjectClass :
X                                  smeLineObjectClass), m,
X                                 &arg, (Cardinal) 1);
X    }
#else /* !KTERM_KANJI */
X    for (; nentries > 0; nentries--, entries++) {
X	cb[0].callback = (XtCallbackProc) entries->function;
X	cb[0].closure = (caddr_t) entries->name;
X	entries->widget = XtCreateManagedWidget (entries->name, 
X						 (entries->function ?
X						  smeBSBObjectClass :
X						  smeLineObjectClass), m,
X						 &arg, (Cardinal) 1);
X    }
#endif /* KTERM_KANJI */
X
X    /* do not realize at this point */
X    return m;
}
X
static void handle_send_signal (gw, sig)
X    Widget gw;
X    int sig;
{
X    register TScreen *screen = &term->screen;
X
X    if (screen->pid > 1) killpg (screen->pid, sig);
}
X
X
/*
X * action routines
X */
X
void DoSecureKeyboard (time)
X    Time time;
{
X    do_securekbd (term->screen.mainMenu, NULL, NULL);
}
X
static void do_securekbd (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X    Time time = CurrentTime;		/* XXX - wrong */
X
X    if (screen->grabbedKbd) {
X	XUngrabKeyboard (screen->display, time);
X	ReverseVideo (term);
X	screen->grabbedKbd = FALSE;
X    } else {
X	if (XGrabKeyboard (screen->display, term->core.parent->core.window,
X			   True, GrabModeAsync, GrabModeAsync, time)
X	    != GrabSuccess) {
X	    XBell (screen->display, 100);
X	} else {
X	    ReverseVideo (term);
X	    screen->grabbedKbd = TRUE;
X	}
X    }
X    update_securekbd();
}
X
X
static void do_allowsends (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    screen->allowSendEvents = !screen->allowSendEvents;
X    update_allowsends ();
}
X
X
static void do_visualbell (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    screen->visualbell = !screen->visualbell;
X    update_visualbell();
}
X
X
static void do_logging (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    if (screen->logging) {
X	CloseLog (screen);
X    } else {
X	StartLog (screen);
X    }
X    /* update_logging done by CloseLog and StartLog */
}
X
X
static void do_redraw (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    Redraw ();
}
X
X
/*
X * The following cases use the pid instead of the process group so that we
X * don't get hosed by programs that change their process group
X */
X
X
static void do_suspend (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
#ifdef SIGTSTP
X    handle_send_signal (gw, SIGTSTP);
#endif
}
X
X
static void do_continue (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
#ifdef SIGCONT
X    handle_send_signal (gw, SIGCONT);
#endif
}
X
X
static void do_interrupt (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    handle_send_signal (gw, SIGINT);
}
X
X
static void do_hangup (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    handle_send_signal (gw, SIGHUP);
}
X
X
static void do_terminate (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    handle_send_signal (gw, SIGTERM);
}
X
X
static void do_kill (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    handle_send_signal (gw, SIGKILL);
}
X
X
static void do_quit (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    Cleanup (0);
}
X
X
X
/*
X * vt menu callbacks
X */
X
static void do_scrollbar (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    if (screen->scrollbar) {
X	ScrollBarOff (screen);
X    } else {
X	ScrollBarOn (term, FALSE, FALSE);
X    }
X    update_scrollbar();
}
X
X
static void do_jumpscroll (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    term->flags ^= SMOOTHSCROLL;
X    if (term->flags & SMOOTHSCROLL) {
X	screen->jumpscroll = FALSE;
X	if (screen->scroll_amt) FlushScroll(screen);
X    } else {
X	screen->jumpscroll = TRUE;
X    }
X    update_jumpscroll();
}
X
X
static void do_reversevideo (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    term->flags ^= REVERSE_VIDEO;
X    ReverseVideo (term);
X    /* update_reversevideo done in ReverseVideo */
}
X
X
static void do_autowrap (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    term->flags ^= WRAPAROUND;
X    update_autowrap();
}
X
X
static void do_reversewrap (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    term->flags ^= REVERSEWRAP;
X    update_reversewrap();
}
X
X
static void do_autolinefeed (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    term->flags ^= LINEFEED;
X    update_autolinefeed();
}
X
X
static void do_appcursor (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    term->keyboard.flags ^= CURSOR_APL;
X    update_appcursor();
}
X
X
static void do_appkeypad (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    term->keyboard.flags ^= KYPD_APL;
X    update_appkeypad();
}
X
X
static void do_scrollkey (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    screen->scrollkey = !screen->scrollkey;
X    update_scrollkey();
}
X
X
static void do_scrollttyoutput (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    screen->scrollttyoutput = !screen->scrollttyoutput;
X    update_scrollttyoutput();
}
X
X
static void do_allow132 (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    screen->c132 = !screen->c132;
X    update_allow132();
}
X
X
static void do_cursesemul (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    screen->curses = !screen->curses;
X    update_cursesemul();
}
X
X
static void do_marginbell (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    if (!(screen->marginbell = !screen->marginbell)) screen->bellarmed = -1;
X    update_marginbell();
}
X
X
static void handle_tekshow (gw, allowswitch)
X    Widget gw;
X    Bool allowswitch;
{
X    register TScreen *screen = &term->screen;
X
X    if (!screen->Tshow) {		/* not showing, turn on */
X	set_tek_visibility (TRUE);
X    } else if (screen->Vshow || allowswitch) {  /* is showing, turn off */
X	set_tek_visibility (FALSE);
X	end_tek_mode ();		/* WARNING: this does a longjmp */
X    } else
X      Bell();
}
X
X
static void do_tekshow (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    handle_tekshow (gw, True);
}
X
X
static void do_tekonoff (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    handle_tekshow (gw, False);
}
X
X
static void do_altscreen (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    /* do nothing for now; eventually, will want to flip screen */
}
X
X
static void do_softreset (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    VTReset (FALSE);
}
X
X
static void do_hardreset (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    VTReset (TRUE);
}
X
X
static void switch_modes (tovt)
X    Bool tovt;				/* if true, then become vt mode */
{
X    if (tovt) {
X	if (TekRefresh) dorefresh();
X	end_tek_mode ();		/* WARNING: this does a longjmp... */
X    } else {
X	end_vt_mode ();			/* WARNING: this does a longjmp... */
X    }
}
X
X
static void do_tekmode (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    switch_modes (screen->TekEmu);	/* switch to tek mode */
}
X
static void do_vthide (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    set_vt_visibility (FALSE);
X    if (!screen->TekEmu) switch_modes (False);	/* switch to tek mode */
}
X
#ifdef STATUSLINE
static void do_statusline (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    if (screen->statusline) {
X	HideStatus();
X    } else {
X	ShowStatus();
X    }
X    update_statusline();
X    set_reversestatus_sensitivity();
}
X
X
static void do_reversestatus (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    screen->reversestatus = !screen->reversestatus;
X    update_reversestatus();
X    ScrnRefresh(screen, screen->max_row+1, 0, 1, screen->max_col+1, False);
}
#endif /* STATUSLINE */
#ifdef KTERM_KANJI
static void do_jismode (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    term->flags &= ~EUC_KANJI;
X    term->flags &= ~SJIS_KANJI;
X    screen->gsets[0] = GSET_ASCII;
X    screen->gsets[1] = GSET_KANA;
X    screen->gsets[2] = GSET_ASCII;
X    screen->curgr = 1;
X    update_eucmode();
X    update_sjismode();
}
X
X
static void do_eucmode (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    if (term->flags & EUC_KANJI) {
X	do_jismode(gw, closure, data);
X    } else {
X	term->flags |= EUC_KANJI;
X	term->flags &= ~SJIS_KANJI;
X	screen->gsets[0] = GSET_ASCII;
X	screen->gsets[1] = GSET_KANJI;
X	screen->gsets[2] = GSET_KANA;
X	screen->curgr = 1;
X	update_eucmode();
X	update_sjismode();
X    }
}
X
X
static void do_sjismode (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    if (term->flags & SJIS_KANJI) {
X	do_jismode(gw, closure, data);
X    } else {
X	term->flags &= ~EUC_KANJI;
X	term->flags |= SJIS_KANJI;
X	screen->gsets[0] = GSET_ASCII;
X	screen->gsets[1] = GSET_KANA;
X	screen->gsets[2] = GSET_ASCII;
X	screen->curgr = 1;
X	update_eucmode();
X	update_sjismode();
X    }
}
X
#ifdef KTERM_HANGUL
static void do_ksmode (gw, closure, data)
X     Widget gw;
X     caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    term->flags &= ~NBYTE_HANGUL;
X    term->flags |= KS_HANGUL;
X    screen->gsets[0] = GSET_ASCII;
X    screen->gsets[1] = GSET_HANGUL;
X    screen->gsets[2] = GSET_ASCII;
X    screen->curgr = 1;
X    update_ksmode();
X    update_nbmode();
}
X
static void do_nbmode (gw, closure, data)
X     Widget gw;
X     caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    term->flags &= ~KS_HANGUL;
X    term->flags |= NBYTE_HANGUL;
X    screen->gsets[0] = GSET_ASCII;
X    screen->gsets[1] = GSET_HANGUL;
X    screen->gsets[2] = GSET_ASCII;
X    screen->curgr = 1;
X    update_ksmode();
X    update_nbmode();
}
#endif /* KTERM_HANGUL */
#ifdef KTERM_HANZI
static void do_gbmode (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    term->flags &= ~BIG5_HANZI;
X    term->flags &= ~SGB_HANZI;
X    term->flags |= GUOBIAO_HANZI;
X    screen->gsets[0] = GSET_ASCII;
X    screen->gsets[1] = GSET_HANZI;
X    screen->gsets[2] = GSET_ASCII;
X    screen->curgr = 1;
X    update_big5mode();
X    update_sgbmode();
}
X
static void do_big5mode (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    if (term->flags & BIG5_HANZI) {
X	do_gbmode(gw, closure, data);
X    } else {
X        term->flags &= ~GUOBIAO_HANZI;
X	term->flags &= ~SGB_HANZI;
X	term->flags |= BIG5_HANZI;
X	screen->gsets[0] = GSET_ASCII;
X	screen->gsets[1] = GSET_HANZI;
X	screen->gsets[2] = GSET_ASCII;
X	screen->curgr = 1;
X	update_big5mode();
X        update_sgbmode();
X    }
}
X
static void do_sgbmode (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    if (term->flags & SGB_HANZI) {
X	do_gbmode(gw, closure, data);
X    } else {
X        term->flags &= ~GUOBIAO_HANZI;
X	term->flags &= ~BIG5_HANZI;
X	term->flags |= SGB_HANZI;
X	screen->gsets[0] = GSET_ASCII;
X	screen->gsets[1] = GSET_HANZI;
X	screen->gsets[2] = GSET_ASCII;
X	screen->curgr = 1;
X	update_big5mode();
X        update_sgbmode();
X    }
}
#endif /* KTERM_HANZI */
#endif /* KTERM_KANJI */
X
X
/*
X * vtfont menu
X */
X
static void do_vtfont (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    char *entryname = (char *) closure;
X    int i;
X
X    for (i = 0; i < NMENUFONTS; i++) {
X	if (strcmp (entryname, fontMenuEntries[i].name) == 0) {
X	    SetVTFont (i, True, NULL, NULL);
X	    return;
X	}
X    }
X    Bell();
}
X
X
/*
X * tek menu
X */
X
static void do_tektextlarge (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    TekSetFontSize (gw, tekMenu_tektextlarge);
}
X
X
static void do_tektext2 (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    TekSetFontSize (gw, tekMenu_tektext2);
}
X
X
static void do_tektext3 (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    TekSetFontSize (gw, tekMenu_tektext3);
}
X
X
static void do_tektextsmall (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X
X    TekSetFontSize (gw, tekMenu_tektextsmall);
}
X
X
static void do_tekpage (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    TekSimulatePageButton (False);
}
X
X
static void do_tekreset (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    TekSimulatePageButton (True);
}
X
X
static void do_tekcopy (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    TekCopy ();
}
X
X
static void handle_vtshow (gw, allowswitch)
X    Widget gw;
X    Bool allowswitch;
{
X    register TScreen *screen = &term->screen;
X
X    if (!screen->Vshow) {		/* not showing, turn on */
X	set_vt_visibility (TRUE);
X    } else if (screen->Tshow || allowswitch) {  /* is showing, turn off */
X	set_vt_visibility (FALSE);
X	if (!screen->TekEmu && TekRefresh) dorefresh ();
X	end_vt_mode ();
X    } else 
X      Bell();
}
X
static void do_vtshow (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    handle_vtshow (gw, True);
}
X
static void do_vtonoff (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    handle_vtshow (gw, False);
}
X
static void do_vtmode (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    switch_modes (screen->TekEmu);	/* switch to vt, or from */
}
X
X
static void do_tekhide (gw, closure, data)
X    Widget gw;
X    caddr_t closure, data;
{
X    register TScreen *screen = &term->screen;
X
X    set_tek_visibility (FALSE);
X    TekRefresh = (TekLink *)0;
X    if (screen->TekEmu) switch_modes (True);	/* does longjmp to vt mode */
}
X
X
X
/*
X * public handler routines
X */
X
static void handle_toggle (proc, var, params, nparams, w, closure, data)
X    void (*proc)();
X    int var;
X    String *params;
X    Cardinal nparams;
X    Widget w;
X    caddr_t closure, data;
{
X    int dir = -2;
X
X    switch (nparams) {
X      case 0:
X	dir = -1;
X      case 1:
X	if (XmuCompareISOLatin1 (params[0], "on") == 0) dir = 1;
X	else if (XmuCompareISOLatin1 (params[0], "off") == 0) dir = 0;
X	else if (XmuCompareISOLatin1 (params[0], "toggle") == 0) dir = -1;
X    }
X
X    switch (dir) {
X      case -2:
X	Bell();
X	break;
X
X      case -1:
X	(*proc) (w, closure, data);
X	break;
X
X      case 0:
X	if (var) (*proc) (w, closure, data);
X	else Bell();
X	break;
X
X      case 1:
X	if (!var) (*proc) (w, closure, data);
X	else Bell();
X	break;
X    }
X    return;
}
X
void HandleAllowSends(w, event, params, param_count)
X    Widget w;
X    XEvent *event;
X    String *params;
X    Cardinal *param_count;
{
X    handle_toggle (do_allowsends, (int) term->screen.allowSendEvents,
X		   params, *param_count, w, NULL, NULL);
}
X
void HandleVisualBell(w, event, params, param_count)
X    Widget w;
X    XEvent *event;
X    String *params;
X    Cardinal *param_count;
{
X    handle_toggle (do_visualbell, (int) term->screen.visualbell,
X		   params, *param_count, w, NULL, NULL);
}
X
void HandleLogging(w, event, params, param_count)
X    Widget w;
X    XEvent *event;
X    String *params;
X    Cardinal *param_count;
{
X    handle_toggle (do_logging, (int) term->screen.logging,
X		   params, *param_count, w, NULL, NULL);
}
X
void HandleRedraw(w, event, params, param_count)
X    Widget w;
X    XEvent *event;
X    String *params;
X    Cardinal *param_count;
{
X    do_redraw(w, NULL, NULL);
}
X
void HandleSendSignal(w, event, params, param_count)
X    Widget w;
X    XEvent *event;
X    String *params;
X    Cardinal *param_count;
{
X    static struct sigtab {
X	char *name;
X	int sig;
X    } signals[] = {
#ifdef SIGTSTP
X	{ "suspend",	SIGTSTP },
X	{ "tstp",	SIGTSTP },
#endif
#ifdef SIGCONT
X	{ "cont",	SIGCONT },
#endif
X	{ "int",	SIGINT },
X	{ "hup",	SIGHUP },
X	{ "term",	SIGTERM },
X	{ "kill",	SIGKILL },
X	{ NULL, 0 },
X    };
X
X    if (*param_count == 1) {
X	struct sigtab *st;
X
X	for (st = signals; st->name; st++) {
X	    if (XmuCompareISOLatin1 (st->name, params[0]) == 0) {
X		handle_send_signal (w, st->sig);
X		return;
X	    }
X	}
X	/* one could allow numeric values, but that would be a security hole */
X    }
X
X    Bell();
}
X
void HandleQuit(w, event, params, param_count)
X    Widget w;
X    XEvent *event;
SHAR_EOF
true || echo 'restore of kterm-4.1.2/menu.c failed'
fi
echo 'End of kterm-4.1.2 part 14'
echo 'File kterm-4.1.2/menu.c is continued in part 15'
echo 15 > _shar_seq_.tmp
exit 0


-----------------------------------------------------------------------------
mleisher at nmsu.edu                      "I laughed.
Mark Leisher                                I cried.
Computing Research Lab                          I fell down.
New Mexico State University                        It changed my life."
Las Cruces, NM                     - Rich [Cowboy Feng's Space Bar and Grille]

--
Dan Heller
O'Reilly && Associates       Z-Code Software    Comp-sources-x:
Senior Writer                President          comp-sources.x at uunet.uu.net
argv at ora.com                 argv at zipcode.com



More information about the Comp.sources.x mailing list