⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 misc.c

📁 源码,标准c++用力
💻 C
📖 第 1 页 / 共 2 页
字号:
/* *	$XConsortium: misc.c,v 1.95.1.1 93/11/04 08:56:48 gildea Exp $ *//* * Copyright 1987 by Digital Equipment Corporation, Maynard, Massachusetts. * *                         All Rights Reserved * * Permission to use, copy, modify, and distribute this software and its * documentation for any purpose and without fee is hereby granted, * provided that the above copyright notice appear in all copies and that * both that copyright notice and this permission notice appear in * supporting documentation, and that the name of Digital Equipment * Corporation not be used in advertising or publicity pertaining to * distribution of the software without specific, written prior permission. * * * DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING * ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL * DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR * ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, * WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, * ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS * SOFTWARE. */#include "ptyx.h"		/* X headers included here. */#include <X11/Xos.h>#include <stdio.h>#include <setjmp.h>#include <signal.h>#include <ctype.h>#include <pwd.h>#include <errno.h>#include <X11/Xatom.h>#include <X11/cursorfont.h>#include <X11/Shell.h>#include <X11/Xmu/Error.h>#include <X11/Xmu/SysUtil.h>#include <X11/Xmu/WinUtil.h>#include "data.h"#include "error.h"#include "menu.h"extern jmp_buf Tekend;extern jmp_buf VTend;#ifndef X_NOT_STDC_ENV#include <stdlib.h>#elseextern char *malloc();extern char *getenv();#endif#if defined(macII) && !defined(__STDC__)  /* stdlib.h fails to define these */char *malloc();#endif /* macII */static void DoSpecialEnterNotify();static void DoSpecialLeaveNotify();extern XtAppContext app_con;xevents(){	XEvent event;	XtInputMask input_mask;	register TScreen *screen = &term->screen;	if(screen->scroll_amt)		FlushScroll(screen);	/*	 * process timeouts, relying on the fact that XtAppProcessEvent	 * will process the timeout and return without blockng on the	 * XEvent queue.  Other sources i.e. the pty are handled elsewhere	 * with select().	 */	while ((input_mask = XtAppPending(app_con)) & XtIMTimer)		XtAppProcessEvent(app_con, XtIMTimer);	/*	 * If there's no XEvents, don't wait around...	 */	if ((input_mask & XtIMXEvent) != XtIMXEvent)	    return;	do {		if (waitingForTrackInfo)			return;		XtAppNextEvent (app_con, &event);		/*		 * Hack to get around problems with the toolkit throwing away		 * eventing during the exclusive grab of the menu popup.  By		 * looking at the event ourselves we make sure that we can		 * do the right thing.		 */		if(event.type == EnterNotify &&		   (event.xcrossing.window == XtWindow(XtParent(term)) ||		    (tekWidget &&		     event.xcrossing.window == XtWindow(XtParent(tekWidget)))))		  DoSpecialEnterNotify (&event.xcrossing);		else 		if(event.type == LeaveNotify &&		   (event.xcrossing.window == XtWindow(XtParent(term)) ||		    (tekWidget &&		     event.xcrossing.window == XtWindow(XtParent(tekWidget)))))		  DoSpecialLeaveNotify (&event.xcrossing);		if (!event.xany.send_event ||		    screen->allowSendEvents ||		    ((event.xany.type != KeyPress) &&		     (event.xany.type != KeyRelease) &&		     (event.xany.type != ButtonPress) &&		     (event.xany.type != ButtonRelease)))		    XtDispatchEvent(&event);	} while ((input_mask = XtAppPending(app_con)) & XtIMXEvent);}Cursor make_colored_cursor (cursorindex, fg, bg)	int cursorindex;			/* index into font */	unsigned long fg, bg;			/* pixel value */{	register TScreen *screen = &term->screen;	Cursor c;	register Display *dpy = screen->display;		c = XCreateFontCursor (dpy, cursorindex);	if (c == (Cursor) 0) return (c);	recolor_cursor (c, fg, bg);	return (c);}/* ARGSUSED */void HandleKeyPressed(w, event, params, nparams)    Widget w;    XEvent *event;    String *params;    Cardinal *nparams;{    register TScreen *screen = &term->screen;#ifdef ACTIVEWINDOWINPUTONLY    if (w == (screen->TekEmu ? (Widget)tekWidget : (Widget)term))#endif	Input (&term->keyboard, screen, &event->xkey, False);}/* ARGSUSED */void HandleEightBitKeyPressed(w, event, params, nparams)    Widget w;    XEvent *event;    String *params;    Cardinal *nparams;{    register TScreen *screen = &term->screen;#ifdef ACTIVEWINDOWINPUTONLY    if (w == (screen->TekEmu ? (Widget)tekWidget : (Widget)term))#endif	Input (&term->keyboard, screen, &event->xkey, True);}/* ARGSUSED */void HandleStringEvent(w, event, params, nparams)    Widget w;    XEvent *event;    String *params;    Cardinal *nparams;{    register TScreen *screen = &term->screen;#ifdef ACTIVEWINDOWINPUTONLY    if (w != (screen->TekEmu ? (Widget)tekWidget : (Widget)term)) return;#endif    if (*nparams != 1) return;    if ((*params)[0] == '0' && (*params)[1] == 'x' && (*params)[2] != '\0') {	char c, *p, hexval[2];	hexval[0] = hexval[1] = 0;	for (p = *params+2; (c = *p); p++) {	    hexval[0] *= 16;	    if (isupper(c)) c = tolower(c);	    if (c >= '0' && c <= '9')		hexval[0] += c - '0';	    else if (c >= 'a' && c <= 'f')		hexval[0] += c - 'a' + 10;	    else break;	}	if (c == '\0')	    StringInput (screen, hexval, 1);    }    else {	StringInput (screen, *params, strlen(*params));    }}static void DoSpecialEnterNotify (ev)    register XEnterWindowEvent *ev;{    register TScreen *screen = &term->screen;#ifdef ACTIVEWINDOWINPUTONLY    if (ev->window == XtWindow(XtParent(screen->TekEmu ?					(Widget)tekWidget : (Widget)term)))#endif      if (((ev->detail) != NotifyInferior) &&	  ev->focus &&	  !(screen->select & FOCUS))	selectwindow(screen, INWINDOW);}/*ARGSUSED*/void HandleEnterWindow(w, eventdata, event)Widget w;register XEnterWindowEvent *event;caddr_t eventdata;{    /* NOP since we handled it above */}static void DoSpecialLeaveNotify (ev)    register XEnterWindowEvent *ev;{    register TScreen *screen = &term->screen;#ifdef ACTIVEWINDOWINPUTONLY    if (ev->window == XtWindow(XtParent(screen->TekEmu ?					(Widget)tekWidget : (Widget)term)))#endif      if (((ev->detail) != NotifyInferior) &&	  ev->focus &&	  !(screen->select & FOCUS))	unselectwindow(screen, INWINDOW);}/*ARGSUSED*/void HandleLeaveWindow(w, eventdata, event)Widget w;register XEnterWindowEvent *event;caddr_t eventdata;{    /* NOP since we handled it above */}/*ARGSUSED*/void HandleFocusChange(w, eventdata, event)Widget w;register XFocusChangeEvent *event;caddr_t eventdata;{        register TScreen *screen = &term->screen;        if(event->type == FocusIn)                selectwindow(screen,			     (event->detail == NotifyPointer) ? INWINDOW :								FOCUS);        else {                unselectwindow(screen,			       (event->detail == NotifyPointer) ? INWINDOW :								  FOCUS);		if (screen->grabbedKbd && (event->mode == NotifyUngrab)) {		    XBell(screen->display, 100);		    ReverseVideo(term);		    screen->grabbedKbd = FALSE;		    update_securekbd();		}	}}selectwindow(screen, flag)register TScreen *screen;register int flag;{	if(screen->TekEmu) {		if(!Ttoggled)			TCursorToggle(TOGGLE);		screen->select |= flag;		if(!Ttoggled)			TCursorToggle(TOGGLE);		return;	} else {		if(screen->cursor_state &&		   (screen->cursor_col != screen->cur_col ||		    screen->cursor_row != screen->cur_row))		    HideCursor();		screen->select |= flag;		if(screen->cursor_state)			ShowCursor();		return;	}}unselectwindow(screen, flag)register TScreen *screen;register int flag;{    if (screen->always_highlight) return;    if(screen->TekEmu) {	if(!Ttoggled) TCursorToggle(TOGGLE);	screen->select &= ~flag;	if(!Ttoggled) TCursorToggle(TOGGLE);    } else {	screen->select &= ~flag;	if(screen->cursor_state &&	   (screen->cursor_col != screen->cur_col ||	    screen->cursor_row != screen->cur_row))	      HideCursor();	if(screen->cursor_state)	  ShowCursor();    }}static long lastBellTime;	/* in milliseconds */Bell(){    extern XtermWidget term;    register TScreen *screen = &term->screen;    struct timeval curtime;    long now_msecs;    /* has enough time gone by that we are allowed to ring       the bell again? */    if(screen->bellSuppressTime) {	if(screen->bellInProgress) {	    if (XtAppPending(app_con) ||		GetBytesAvailable (ConnectionNumber(screen->display)) > 0)		xevents();	    if(screen->bellInProgress) { /* even after new events? */		return;	    }	}	gettimeofday(&curtime, NULL);	now_msecs = 1000*curtime.tv_sec + curtime.tv_usec/1000;	if(lastBellTime != 0  &&  now_msecs - lastBellTime >= 0  &&	   now_msecs - lastBellTime < screen->bellSuppressTime) {	    return;	}	lastBellTime = now_msecs;    }    if (screen->visualbell)	VisualBell();    else	XBell(screen->display, 0);    if(screen->bellSuppressTime) {	/* now we change a property and wait for the notify event to come	   back.  If the server is suspending operations while the bell	   is being emitted (problematic for audio bell), this lets us	   know when the previous bell has finished */	Widget w = screen->TekEmu ? (Widget) tekWidget : (Widget) term;	XChangeProperty(XtDisplay(w), XtWindow(w),			XA_NOTICE, XA_NOTICE, 8, PropModeAppend, NULL, 0);	screen->bellInProgress = TRUE;    }}VisualBell(){    extern XtermWidget term;    register TScreen *screen = &term->screen;    register Pixel xorPixel = screen->foreground ^ term->core.background_pixel;    XGCValues gcval;    GC visualGC;    gcval.function = GXxor;    gcval.foreground = xorPixel;    visualGC = XtGetGC((Widget)term, GCFunction+GCForeground, &gcval);    if(screen->TekEmu) {	XFillRectangle(		       screen->display,		       TWindow(screen), 		       visualGC,		       0, 0,		       (unsigned) TFullWidth(screen),		       (unsigned) TFullHeight(screen));	XFlush(screen->display);	XFillRectangle(		       screen->display,		       TWindow(screen), 		       visualGC,		       0, 0,		       (unsigned) TFullWidth(screen),		       (unsigned) TFullHeight(screen));    } else {	XFillRectangle(		       screen->display,		       VWindow(screen), 		       visualGC,		       0, 0,		       (unsigned) FullWidth(screen),		       (unsigned) FullHeight(screen));	XFlush(screen->display);	XFillRectangle(		       screen->display,		       VWindow(screen), 		       visualGC,		       0, 0,		       (unsigned) FullWidth(screen),		       (unsigned) FullHeight(screen));    }}/* ARGSUSED */void HandleBellPropertyChange(w, data, ev, more)    Widget w;    XtPointer data;    XEvent *ev;    Boolean *more;{    register TScreen *screen = &term->screen;    if (ev->xproperty.atom == XA_NOTICE) {	screen->bellInProgress = FALSE;    }}Redraw(){	extern XtermWidget term;	register TScreen *screen = &term->screen;	XExposeEvent event;	event.type = Expose;	event.display = screen->display;	event.x = 0;	event.y = 0;	event.count = 0; 		if(VWindow(screen)) {	        event.window = VWindow(screen);		event.width = term->core.width;		event.height = term->core.height;		(*term->core.widget_class->core_class.expose)((Widget)term, (XEvent *)&event, NULL);		if(screen->scrollbar) 			(*screen->scrollWidget->core.widget_class->core_class.expose)(screen->scrollWidget, (XEvent *)&event, NULL);		}	if(TWindow(screen) && screen->Tshow) {	        event.window = TWindow(screen);		event.width = tekWidget->core.width;		event.height = tekWidget->core.height;		TekExpose (tekWidget, &event, NULL);	}}#if defined(ALLOWLOGGING) || defined(DEBUG)#ifndef X_NOT_POSIX#define HAS_WAITPID#endif/* * create a file only if we could with the permissions of the real user id. * We could emulate this with careful use of access() and following * symbolic links, but that is messy and has race conditions. * Forking is messy, too, but we can't count on setreuid() or saved set-uids * being available. */voidcreat_as(uid, gid, pathname, mode)    int uid;    int gid;    char *pathname;    int mode;{    int fd;    int waited;    int pid;#ifndef HAS_WAITPID    int (*chldfunc)();    chldfunc = signal(SIGCHLD, SIG_DFL);#endif    pid = fork();    switch (pid)    {    case 0:			/* child */	setgid(gid);	setuid(uid);	fd = open(pathname, O_WRONLY|O_CREAT|O_APPEND, mode);	if (fd >= 0) {	    close(fd);	    _exit(0);	} else	    _exit(1);    case -1:			/* error */	return;    default:			/* parent */#ifdef HAS_WAITPID	waitpid(pid, NULL, 0);#else	waited = wait(NULL);	signal(SIGCHLD, chldfunc);	/*	  Since we had the signal handler uninstalled for a while,	  we might have missed the termination of our screen child.	  If we can check for this possibility without hanging, do so.	*/	do	    if (waited == term->screen.pid)		Cleanup(0);	while ( (waited=nonblocking_wait()) > 0);#endif    }}#endif#ifdef ALLOWLOGGING/* * logging is a security hole, since it allows a setuid program to * write arbitrary data to an arbitrary file.  So it is disabled * by default. */ StartLog(screen)register TScreen *screen;{	register char *cp;	register int i;	static char *log_default;#ifdef ALLOWLOGFILEEXEC	void logpipe();#ifdef SYSV	/* SYSV has another pointer which should be part of the	** FILE structure but is actually a separate array.	*/	unsigned char *old_bufend;#endif	/* SYSV */#endif /* ALLOWLOGFILEEXEC */	if(screen->logging || (screen->inhibit & I_LOG))		return;	if(screen->logfile == NULL || *screen->logfile == 0) {		if(screen->logfile)			free(screen->logfile);		if(log_default == NULL)			log_default = log_def_name;			mktemp(log_default);		if((screen->logfile = malloc((unsigned)strlen(log_default) + 1)) == NULL)			return;		strcpy(screen->logfile, log_default);	}	if(*screen->logfile == '|') {	/* exec command */#ifdef ALLOWLOGFILEEXEC		/*		 * Warning, enabling this "feature" allows arbitrary programs		 * to be run.  If ALLOWLOGFILECHANGES is enabled, this can be		 * done through escape sequences....  You have been warned.		 */		int p[2];		static char *shell;		if(pipe(p) < 0 || (i = fork()) < 0)			return;		if(i == 0) {	/* child */			close(p[1]);			dup2(p[0], 0);			close(p[0]);			dup2(fileno(stderr), 1);			dup2(fileno(stderr), 2);#ifdef SYSV			old_bufend = _bufend(stderr);#endif	/* SYSV */			close(fileno(stderr));			stderr->_file = 2;#ifdef SYSV			_bufend(stderr) = old_bufend;#endif	/* SYSV */			close(ConnectionNumber(screen->display));			close(screen->respond);			if(!shell) {				register struct passwd *pw;				struct passwd *getpwuid();				if(((cp = getenv("SHELL")) == NULL || *cp == 0)				 && ((pw = getpwuid(screen->uid)) == NULL ||				 *(cp = pw->pw_shell) == 0) ||				 (shell = malloc((unsigned) strlen(cp) + 1)) == NULL)					shell = "/bin/sh";				else					strcpy(shell, cp);			}			signal(SIGHUP, SIG_DFL);			signal(SIGCHLD, SIG_DFL);			setgid(screen->gid);			setuid(screen->uid);			execl(shell, shell, "-c", &screen->logfile[1], 0);			fprintf(stderr, "%s: Can't exec `%s'\n", xterm_name,			 &screen->logfile[1]);			exit(ERROR_LOGEXEC);		}		close(p[0]);		screen->logfd = p[1];		signal(SIGPIPE, logpipe);#else		Bell();		Bell();		return;#endif	} else {		if(access(screen->logfile, F_OK) != 0) {		    if (errno == ENOENT)			creat_as(screen->uid, screen->gid,				 screen->logfile, 0644);		    else

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -