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

📄 srvfunc.c

📁 一个linux下的根文件系统的源码
💻 C
📖 第 1 页 / 共 5 页
字号:
/* * Copyright (c) 1999, 2000, 2001, 2002, 2003 Greg Haerr <greg@censoft.com> * Portions Copyright (c) 2002 by Koninklijke Philips Electronics N.V. * Copyright (c) 2000 Alex Holden <alex@linuxhacker.org> * Copyright (c) 1991 David I. Bell * Permission is granted to use, distribute, or modify this source, * provided that this copyright notice remains intact. */#include <stdio.h>#include <stdlib.h>#include <string.h>#define MWINCLUDECOLORS#include "serv.h"static int	nextid = GR_ROOT_WINDOW_ID + 1;static void CheckNextEvent(GR_EVENT *ep, GR_BOOL doCheckEvent); /* * Return information about the screen for clients to use. */void GrGetScreenInfo(GR_SCREEN_INFO *sip){	SERVER_LOCK();	GdGetScreenInfo(rootwp->psd, sip);	/* set virtual screen sizing (for PDA emulation on desktop)*/	sip->vs_width = nxres? nxres: sip->cols;	sip->vs_height = nyres? nyres: sip->rows;	/* set workspace equal to virtual screen area minus 22 pixel taskbar*/	sip->ws_width = sip->vs_width;	sip->ws_height = sip->vs_height - 22;	SERVER_UNLOCK();}/* * Return the size of a text string for the font in a graphics context. * This is the width of the string, the height of the string, * and the height above the bottom of the font of the baseline for the font. */void GrGetGCTextSize(GR_GC_ID gc, void *str, int count, GR_TEXTFLAGS flags,	GR_SIZE *retwidth, GR_SIZE *retheight, GR_SIZE *retbase){	GR_GC		*gcp;	GR_FONT		*fontp;	PMWFONT		pf;	SERVER_LOCK();	gcp = GsFindGC(gc);	if (gcp == NULL)		fontp = NULL;	else		fontp = GsFindFont(gcp->fontid);	pf = fontp? fontp->pfont: stdfont;	GdGetTextSize(pf, str, count, retwidth, retheight, retbase, flags);	SERVER_UNLOCK();}#if NONETWORK/* * Return the next waiting event for a client, or wait for one if there * is none yet.  The event is copied into the specified structure, and * then is moved from the event queue to the free event queue.  If there * is an error event waiting, it is delivered before any other events. */voidGrGetNextEvent(GR_EVENT *ep){	GrGetNextEventTimeout(ep, 0L);}/* * Return the next event from the event queue, or * wait for a new one if one is not ready.  If timeout * is nonzero, return timeout event if time elapsed. */voidGrGetNextEventTimeout(GR_EVENT *ep, GR_TIMEOUT timeout){	SERVER_LOCK();	/* If no event ready, wait for one*/	/* Note: won't work for multiple clients*/	/* This is OK, since only static linked apps call this function*/	while(curclient->eventhead == NULL)		GsSelect(timeout);	CheckNextEvent(ep, GR_FALSE);	SERVER_UNLOCK();}/* * Wait until an event is available for a client, and then peek at it. */voidGrPeekWaitEvent(GR_EVENT *ep){	SERVER_LOCK();	while(curclient->eventhead == NULL)		GsSelect(0L);	GrPeekEvent(ep);	SERVER_UNLOCK();}#endif/* * Return the next event from the event queue if one is ready. * If one is not ready, then the type GR_EVENT_TYPE_NONE is returned. * If it is an error event, then a user-specified routine is called * if it was defined, otherwise we clean up and exit. */voidGrCheckNextEvent(GR_EVENT *ep){	SERVER_LOCK();	CheckNextEvent(ep, GR_TRUE);	SERVER_UNLOCK();}static voidCheckNextEvent(GR_EVENT *ep, GR_BOOL doCheckEvent){	GR_EVENT_LIST *	elp;#if 0 /* was NONETWORK*/	/* NOTE: select() now called through GrPeekEvent when bound to server*/	if (doCheckEvent)		GsSelect(1L);#endif	/* Copy first event if any*/	if(!GrPeekEvent(ep))		return;	/* Get first event again*/	elp = curclient->eventhead;#if NONETWORK	/* if GrCheckEvent, turn timeouts into no event*/	if (doCheckEvent && elp->event.type == GR_EVENT_TYPE_TIMEOUT)		ep->type = GR_EVENT_TYPE_NONE;#endif	/* Remove first event from queue*/	curclient->eventhead = elp->next;	if (curclient->eventtail == elp)		curclient->eventtail = NULL;	elp->next = eventfree;	eventfree = elp;}/* * Peek at the event queue for the current client to see if there are any * outstanding events.  Returns the event at the head of the queue, or * else a null event type.  The event is still left in the queue, however. */intGrPeekEvent(GR_EVENT *ep){	GR_EVENT_LIST *	elp;	SERVER_LOCK();	elp = curclient->eventhead;#if NONETWORK	/* if no events on queue, force select() event check*/	if (elp == NULL) {		GsSelect(-1L);	/* poll*/		elp = curclient->eventhead;	}#endif	if(elp == NULL) {		ep->type = GR_EVENT_TYPE_NONE;		SERVER_UNLOCK();		return 0;	}	/* copy event out*/	*ep = elp->event;	SERVER_UNLOCK();	return 1;}/* * Return information about a window id. */voidGrGetWindowInfo(GR_WINDOW_ID wid, GR_WINDOW_INFO *infoptr){	GR_WINDOW	*wp;		/* window structure */	GR_PIXMAP	*pp;	GR_EVENT_CLIENT	*evp;		/* event-client structure */	SERVER_LOCK();	/* first check window list*/	wp = GsFindWindow(wid);	if (wp) {		infoptr->wid = wid;		/* report parent-relative x,y coordinates*/		infoptr->x = wp->x - (wp->parent ? wp->parent->x : 0);		infoptr->y = wp->y - (wp->parent ? wp->parent->y : 0);		infoptr->width = wp->width;		infoptr->height = wp->height;		infoptr->parent = wp->parent? wp->parent->id: 0;		infoptr->child = wp->children? wp->children->id: 0;		infoptr->sibling = wp->siblings? wp->siblings->id: 0;		infoptr->mapped = wp->mapped;		infoptr->realized = wp->realized;		infoptr->inputonly = !wp->output;		infoptr->bordersize = wp->bordersize;		infoptr->bordercolor = wp->bordercolor;		infoptr->background = wp->background;		infoptr->props = wp->props;		infoptr->cursor = wp->cursorid;		infoptr->processid = wp->owner? wp->owner->processid: 0;		infoptr->eventmask = 0;		for (evp = wp->eventclients; evp; evp = evp->next) {			if (evp->client == curclient)				infoptr->eventmask = evp->eventmask;		}		SERVER_UNLOCK();		return;	}	/* then pixmap list*/	pp = GsFindPixmap(wid);	if (pp) {		infoptr->wid = wid;		infoptr->x = pp->x;		infoptr->y = pp->y;		infoptr->width = pp->width;		infoptr->height = pp->height;		infoptr->parent = 0;		infoptr->child = 0;		infoptr->sibling = 0;		infoptr->mapped = GR_FALSE;		infoptr->realized = GR_TRUE;		infoptr->inputonly = GR_FALSE;		infoptr->bordersize = 0;		infoptr->bordercolor = 0;		infoptr->background = 0;		infoptr->eventmask = 0;		infoptr->cursor = 0;		infoptr->processid = pp->owner? pp->owner->processid: 0;		SERVER_UNLOCK();		return;	}	/* No error if window id is invalid.*/	memset(infoptr, 0, sizeof(GR_WINDOW_INFO));	SERVER_UNLOCK();}/* * Destroy an existing window and all of its children. * Also used to destroy a pixmap. */voidGrDestroyWindow(GR_WINDOW_ID wid){	GR_WINDOW	*wp;		/* window structure */	GR_PIXMAP	*pp;	GR_PIXMAP	*prevpp;	PSD		psd;	SERVER_LOCK();	wp = GsFindWindow(wid);	if (wp) {		GsWpDestroyWindow(wp);	} else {		pp = GsFindPixmap(wid);		if (pp) {			psd = pp->psd;			/* deallocate pixmap memory*/			if (psd->flags & PSF_ADDRMALLOC)				free(psd->addr);			/* deallocate mem gc*/			psd->FreeMemGC(psd);			/*			 * Remove this pixmap from the complete list of pixmaps.			 */			prevpp = listpp;			if (prevpp == pp)				listpp = pp->next;			else {				while (prevpp->next != pp)					prevpp = prevpp->next;				prevpp->next = pp->next;			}			/*			 * Forget various information if they related to this			 * pixmap.  Then finally free the structure.			 */			if (pp == cachepp) {				cachepixmapid = 0;				cachepp = NULL;			}			free(pp);		}	}	SERVER_UNLOCK();}/* * Raise a window to the highest level among its siblings. */voidGrRaiseWindow(GR_WINDOW_ID wid){	GR_WINDOW	*wp;		/* window structure */	GR_WINDOW	*prevwp;	/* previous window pointer */	GR_BOOL		overlap;	/* TRUE if there was overlap */	SERVER_LOCK();	wp = GsFindWindow(wid);	if ((wp == NULL) || (wp == rootwp)) {		SERVER_UNLOCK();		return;	}	/*	 * If this is already the highest window then we are done.	 */	prevwp = wp->parent->children;	if (prevwp == wp) {		SERVER_UNLOCK();		return;	}	/*	 * Find the sibling just before this window so we can unlink it.	 * Also, determine if any sibling ahead of us overlaps the window.	 * Remember that for exposure events.	 */	overlap = GR_FALSE;	while (prevwp->siblings != wp) {		overlap |= GsCheckOverlap(prevwp, wp);		prevwp = prevwp->siblings;	}	overlap |= GsCheckOverlap(prevwp, wp);	/*	 * Now unlink the window and relink it in at the front of the	 * sibling chain.	 */	prevwp->siblings = wp->siblings;	wp->siblings = wp->parent->children;	wp->parent->children = wp;	/*	 * Finally redraw the window if necessary.	 */	if (overlap) {		GsDrawBorder(wp);		GsExposeArea(wp, wp->x, wp->y, wp->width, wp->height, NULL);	}	SERVER_UNLOCK();}/* * Lower a window to the lowest level among its siblings. */voidGrLowerWindow(GR_WINDOW_ID wid){	GR_WINDOW	*wp;		/* window structure */	GR_WINDOW	*prevwp;	/* previous window pointer */	GR_WINDOW	*sibwp;		/* sibling window */	GR_WINDOW	*expwp;		/* siblings being exposed */	SERVER_LOCK();	wp = GsFindWindow(wid);	if ((wp == NULL) || (wp == rootwp)) {		SERVER_UNLOCK();		return;	}	if (wp->siblings == NULL) {		SERVER_UNLOCK();		return;	}	/*	 * Find the sibling just before this window so we can unlink us.	 */	prevwp = wp->parent->children;	if (prevwp != wp) {		while (prevwp->siblings != wp)			prevwp = prevwp->siblings;	}	/*	 * Remember the first sibling that is after us, so we can	 * generate exposure events for the remaining siblings.  Then	 * walk down the sibling chain looking for the last sibling.	 */	expwp = wp->siblings;	sibwp = wp;	while (sibwp->siblings)		sibwp = sibwp->siblings;	/*	 * Now unlink the window and relink it in at the end of the	 * sibling chain.	 */	if (prevwp == wp)		wp->parent->children = wp->siblings;	else		prevwp->siblings = wp->siblings;	sibwp->siblings = wp;	wp->siblings = NULL;	/*	 * Finally redraw the sibling windows which this window covered	 * if they overlapped our window.	 */	while (expwp && (expwp != wp)) {		if (GsCheckOverlap(wp, expwp)) {			GsExposeArea(expwp, wp->x - wp->bordersize,				wp->y - wp->bordersize,				wp->width + wp->bordersize * 2,				wp->height + wp->bordersize * 2, NULL);		}		expwp = expwp->siblings;	}	SERVER_UNLOCK();}/* Offset a window position and all children by offx,offy*/static voidOffsetWindow(GR_WINDOW *wp, GR_COORD offx, GR_COORD offy){	GR_WINDOW	*cp;	wp->x += offx;	wp->y += offy;	for(cp=wp->children; cp; cp=cp->siblings)		OffsetWindow(cp, offx, offy);}/* deliver an update move event to window and all children*/static voidDeliverUpdateMoveEventAndChildren(GR_WINDOW *wp){	GR_WINDOW *	childwp;	GsDeliverUpdateEvent(wp, GR_UPDATE_MOVE, wp->x, wp->y,		wp->width, wp->height);	for (childwp = wp->children; childwp; childwp = childwp->siblings)		DeliverUpdateMoveEventAndChildren(childwp);}/* * Move the window to the specified position relative to its parent. */voidGrMoveWindow(GR_WINDOW_ID wid, GR_COORD x, GR_COORD y){	GR_WINDOW	*wp;		/* window structure */	GR_COORD	offx, offy;	SERVER_LOCK();	wp = GsFindWindow(wid);	if (wp == NULL) {		SERVER_UNLOCK();		return;	}	if (wp == rootwp) {		GsError(GR_ERROR_ILLEGAL_ON_ROOT_WINDOW, wid);		SERVER_UNLOCK();		return;	}	x += wp->parent->x;	y += wp->parent->y;	offx = x - wp->x;	offy = y - wp->y;	if (wp->x == x && wp->y == y) {		SERVER_UNLOCK();		return;	}	/* * move algorithms not requiring unmap/map ***/#if 1	/* perform screen blit if topmost and mapped - no flicker!*/	if (wp->mapped && wp == wp->parent->children		&& wp->parent->id == GR_ROOT_WINDOW_ID		/* temp don't blit in portrait mode, still buggy*/		/* *&& !(wp->psd->portrait & (MWPORTRAIT_LEFT|MWPORTRAIT_RIGHT))***/		/* don't blit if window has custom frame, background not right*/		&& !wp->clipregion	   ) {		int 		oldx = wp->x;		int 		oldy = wp->y;		GR_WINDOW_ID 	pixid = GrNewPixmap(wp->width, wp->height,NULL);		GR_GC_ID	gc = GrNewGC();		GR_WINDOW * 	stopwp = wp;		int		X, Y, W, H;		/* must hide cursor first or GdFixCursor() will show it*/		GdHideCursor(rootwp->psd);		/* turn off clipping of root's children*/		GrSetGCMode(gc, GR_MODE_COPY|GR_MODE_EXCLUDECHILDREN);		/* copy topmost window contents offscreen*/		GrCopyArea(pixid, gc, 0, 0, wp->width, wp->height,			GR_ROOT_WINDOW_ID, oldx, oldy, MWROP_COPY);		/* calc new window offsets*/		OffsetWindow(wp, offx, offy);		/* force recalc of clip region*/		clipwp = NULL;		/* copy window bits to new location*/		GrCopyArea(GR_ROOT_WINDOW_ID, gc, wp->x, wp->y, wp->width,			wp->height, pixid, 0, 0, MWROP_COPY);		/*		 * If any portion of the window was offscreen		 * and is coming onscreen, must send expose events		 * to this window as well.		 */		if ((oldx < 0 && wp->x > oldx) ||		    (oldy < 0 && wp->y > oldy) ||		    (oldx+wp->width > rootwp->width && wp->x < oldx) ||		    (oldy+wp->height > rootwp->height && wp->y < oldy))			stopwp = NULL;		/* 		 * Calculate bounded exposed area and		 * redraw anything lower than stopwp window.		 */		X = MWMIN(oldx, wp->x);		Y = MWMIN(oldy, wp->y);		W = MWMAX(oldx, wp->x) + wp->width - X;		H = MWMAX(oldy, wp->y) + wp->height - Y;		GsExposeArea(rootwp, X, Y, W, H, stopwp);		GdShowCursor(rootwp->psd);		GrDestroyGC(gc);		GrDestroyWindow(pixid);		DeliverUpdateMoveEventAndChildren(wp);		SERVER_UNLOCK();		return;	}#endif#if 0	/* perform quick move and expose if topmost and mapped - no blit*/	if (wp->mapped && wp == wp->parent->children) {		int	oldx = wp->x;		int	oldy = wp->y;		int	X, Y, W, H;		OffsetWindow(wp, offx, offy);		/* force recalc of clip region*/		clipwp = NULL;		X = MWMIN(oldx, wp->x);		Y = MWMIN(oldy, wp->y);		W = MWMAX(oldx, wp->x) + wp->width - X;		H = MWMAX(oldy, wp->y) + wp->height - Y;		GsExposeArea(rootwp, X, Y, W, H, NULL);		DeliverUpdateMoveEventAndChildren(wp);		SERVER_UNLOCK();		return;	}#endif	/*	 * This method will redraw the window entirely,	 * resulting in considerable flicker.	 */	GsWpUnrealizeWindow(wp, GR_TRUE);	OffsetWindow(wp, offx, offy);	GsWpRealizeWindow(wp, GR_FALSE);	DeliverUpdateMoveEventAndChildren(wp);	SERVER_UNLOCK();	return;}/* * Resize the window to be the specified size. */voidGrResizeWindow(GR_WINDOW_ID wid, GR_SIZE width, GR_SIZE height){	GR_WINDOW	*wp;		/* window structure */	SERVER_LOCK();	wp = GsFindWindow(wid);	if (wp == NULL) {		SERVER_UNLOCK();		return;	}	if (wp == rootwp) {		GsError(GR_ERROR_ILLEGAL_ON_ROOT_WINDOW, wid);		SERVER_UNLOCK();		return;	}	if ((width <= 0) || (height <= 0)) {		GsError(GR_ERROR_BAD_WINDOW_SIZE, wid);		SERVER_UNLOCK();		return;	}	if ((wp->width == width) && (wp->height == height)) {		SERVER_UNLOCK();		return;	}	if (!wp->realized || !wp->output) {		wp->width = width;		wp->height = height;		SERVER_UNLOCK();		return;	}	/*	 * This should be optimized to not require redrawing of the window	 * when possible.	 */	GsWpUnrealizeWindow(wp, GR_TRUE);	wp->width = width;	wp->height = height;	/* send size update before expose event*/	GsDeliverUpdateEvent(wp, GR_UPDATE_SIZE, wp->x, wp->y, width, height);

⌨️ 快捷键说明

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