/************************************************************ Copyright 1987 by Digital Equipment Corporation, Maynard, Massachusetts, and the Massachusetts Institute of Technology, Cambridge, 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 names of Digital or MIT 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. ********************************************************/ /* * XXX - gag, choke, puke - XXX */ asm(" export XCRoutines"); #include "X.h" #define NEED_REPLIES #define NEED_EVENTS #include "Xproto.h" #include "Xprotostr.h" #include "windowstr.h" #include "fontstruct.h" #include "dixfontstr.h" #include "gcstruct.h" #include "osstruct.h" #include "resource.h" #include "selection.h" #include "colormapst.h" #include "dixstruct.h" #include "extension.h" #include "input.h" #include "cursorstr.h" #include "scrnintstr.h" #include "opaque.h" extern WindowRec WindowTable[]; extern xConnSetupPrefix connSetupPrefix; extern char *ConnectionInfo; extern char *SwappedConnInfo; extern void ValidateGC(); extern void WriteSConnectionInfo(); extern Selection *CurrentSelections; extern int NumCurrentSelections; extern long ScreenSaverTime; extern long ScreenSaverInterval; extern int ScreenSaverBlanking; extern int ScreenSaverAllowExposures; extern ClientPtr onlyClient; extern Bool grabbingClient; extern long *checkForInput[2]; extern Bool clientsDoomed; extern int (* ProcVector[256]) (); extern int (* SwappedProcVector[256]) (); extern void (* EventSwapVector[128]) (); extern void (* ReplySwapVector[256]) (); void KillAllClients(); /* buffers for clients. legal values below */ extern int nextFreeClientID; /* 0 is for the server */ extern int nClients; /* number active clients */ extern int ProcBadRequest(); #define SAME_SCREENS(a, b) (\ (a.pScreen == b.pScreen)) #define VALIDATE(pGC, pDraw, rt) {\ if (pGC->serialNumber != pDraw->serialNumber)\ {\ ValidateGC(pDraw, pGC);\ } \ } #define LEGAL_NEW_RESOURCE(id)\ if ((LookupID(id, RT_ANY, RC_CORE) != 0) || (id & SERVER_BIT) \ || (client->clientAsMask != CLIENT_BITS(id)))\ return(BadIDChoice) #define LOOKUP_DRAWABLE(did, client)\ ((client->lastDrawableID == did) ? \ (DrawablePtr)client->lastDrawable : (DrawablePtr)LookupDrawable(did, client)) #define VERIFY_GC(pGC, rid, client)\ if (client->lastGCID == rid)\ {\ pGC = (GC *) client->lastGC;\ }\ else\ {\ pGC = (GC *)LookupID(rid, RT_GC, RC_CORE);\ if (!pGC)\ {\ client->errorValue = rid;\ return (BadGC);\ }\ } #define VALIDATE_DRAWABLE_AND_GC(drawID, pDraw, pGC, client)\ if ((client->lastDrawableID != drawID) || (client->lastGCID != stuff->gc))\ {\ if (client->lastDrawableID != drawID)\ {\ pDraw = (DrawablePtr)LookupID(drawID, RT_DRAWABLE, RC_CORE);\ if (!pDraw)\ {\ client->errorValue = drawID; \ return (BadDrawable);\ }\ if ((pDraw->type == DRAWABLE_WINDOW) || \ (pDraw->type == DRAWABLE_PIXMAP))\ {\ client->lastDrawable = (pointer)pDraw;\ client->lastDrawableID = drawID;\ }\ else\ {\ client->errorValue = drawID;\ return (BadDrawable);\ }\ }\ else\ pDraw = (DrawablePtr)client->lastDrawable;\ if (client->lastGCID != stuff->gc)\ {\ pGC = (GC *)LookupID(stuff->gc, RT_GC, RC_CORE);\ if (!pGC)\ {\ client->errorValue = stuff->gc;\ return (BadGC);\ }\ client->lastGC = (pointer)pGC;\ client->lastGCID = stuff->gc;\ }\ else\ pGC = (GC *) client->lastGC;\ if ((pGC->depth != pDraw->depth) || (pGC->pScreen != pDraw->pScreen))\ {\ client->errorValue = stuff->gc;\ client->lastGCID = -1;\ return (BadMatch);\ }\ }\ else\ {\ pGC = (GC *) client->lastGC;\ pDraw = (DrawablePtr)client->lastDrawable;\ }\ if (pGC->serialNumber != pDraw->serialNumber)\ { \ ValidateGC(pDraw, pGC);\ } int ProcImageText(client) register ClientPtr client; { register DrawablePtr pDraw; register GC *pGC; REQUEST(xImageTextReq); REQUEST_AT_LEAST_SIZE(xImageTextReq); VALIDATE_DRAWABLE_AND_GC(stuff->drawable, pDraw, pGC, client); (*((stuff->reqType == X_ImageText8) ? pGC->ImageText8 : pGC->ImageText16)) (pDraw, pGC, stuff->x, stuff->y, stuff->nChars, (char *)&stuff[1]); return (client->noClientException); } int ProcCreateColormap(client) register ClientPtr client; { VisualPtr pVisual; ColormapPtr pmap; long mid; register WindowPtr pWin; REQUEST(xCreateColormapReq); int result; REQUEST_SIZE_MATCH(xCreateColormapReq); if ((stuff->alloc != AllocNone) && (stuff->alloc != AllocAll)) return(BadValue); mid = stuff->mid; LEGAL_NEW_RESOURCE(mid); pWin = (WindowPtr)LookupWindow(stuff->window, client); if (!pWin) return(BadWindow); if(stuff->visual == CopyFromParent) if(pWin->parent) stuff->visual = pWin->parent->visual; else stuff->visual = pWin->visual; pVisual = (VisualPtr)LookupID(stuff->visual, RT_VISUALID, RC_CORE); if ((!pVisual) || pVisual->screen != pWin->drawable.pScreen->myNum) { client->errorValue = stuff->visual; return(BadValue); } result = CreateColormap(mid, pWin->drawable.pScreen, pVisual, &pmap, (int)stuff->alloc, (unsigned int)client->index); if (client->noClientException != Success) return(client->noClientException); else return(result); } int ProcFreeColormap(client) register ClientPtr client; { ColormapPtr pmap; REQUEST(xResourceReq); REQUEST_SIZE_MATCH(xResourceReq); pmap = (ColormapPtr )LookupID(stuff->id, RT_COLORMAP, RC_CORE); if (pmap) { FreeColormap(pmap, client->index); FreeResource(stuff->id, RC_NONE); return (client->noClientException); } else { client->errorValue = stuff->id; return (BadColor); } } int ProcCopyColormapAndFree(client) register ClientPtr client; { int mid; ColormapPtr pSrcMap; REQUEST(xCopyColormapAndFreeReq); int result; REQUEST_SIZE_MATCH(xCopyColormapAndFreeReq); mid = stuff->mid; LEGAL_NEW_RESOURCE(mid); if(pSrcMap = (ColormapPtr )LookupID(stuff->srcCmap, RT_COLORMAP, RC_CORE)) { result = CopyColormapAndFree(mid, pSrcMap, client->index); if (client->noClientException != Success) return(client->noClientException); else return(result); } else { client->errorValue = stuff->srcCmap; return(BadColor); } } int ProcInstallColormap(client) register ClientPtr client; { ColormapPtr pcmp; REQUEST(xResourceReq); REQUEST_SIZE_MATCH(xResourceReq); pcmp = (ColormapPtr )LookupID(stuff->id, RT_COLORMAP, RC_CORE); if (pcmp) { (*(pcmp->pScreen->InstallColormap)) (pcmp); return (client->noClientException); } else { client->errorValue = stuff->id; return (BadColor); } } int ProcUninstallColormap(client) register ClientPtr client; { ColormapPtr pcmp; REQUEST(xResourceReq); REQUEST_SIZE_MATCH(xResourceReq); pcmp = (ColormapPtr )LookupID(stuff->id, RT_COLORMAP, RC_CORE); if (pcmp) { if(pcmp->mid != pcmp->pScreen->defColormap) (*(pcmp->pScreen->UninstallColormap)) (pcmp); return (client->noClientException); } else { client->errorValue = stuff->id; return (BadColor); } } int ProcListInstalledColormaps(client) register ClientPtr client; { xListInstalledColormapsReply *preply; int nummaps; WindowPtr pWin; REQUEST(xResourceReq); REQUEST_SIZE_MATCH(xResourceReq); pWin = (WindowPtr)LookupWindow(stuff->id, client); if (!pWin) return(BadWindow); preply = (xListInstalledColormapsReply *) ALLOCATE_LOCAL(sizeof(xListInstalledColormapsReply) + pWin->drawable.pScreen->maxInstalledCmaps * sizeof(Colormap)); if(!preply) return(client->noClientException = BadAlloc); preply->type = X_Reply; preply->sequenceNumber = client->sequence; nummaps = (*pWin->drawable.pScreen->ListInstalledColormaps) (pWin->drawable.pScreen, (Colormap *)&preply[1]); preply->nColormaps = nummaps; preply->length = nummaps; WriteReplyToClient(client, sizeof (xListInstalledColormapsReply), preply); WriteReplyToClient(client, nummaps * sizeof(Colormap), &preply[1]); DEALLOCATE_LOCAL(preply); return(client->noClientException); } int ProcAllocColor (client) register ClientPtr client; { ColormapPtr pmap; int retval; xAllocColorReply acr; REQUEST(xAllocColorReq); REQUEST_SIZE_MATCH(xAllocColorReq); pmap = (ColormapPtr )LookupID(stuff->cmap, RT_COLORMAP, RC_CORE); if (pmap) { acr.type = X_Reply; acr.length = 0; acr.sequenceNumber = client->sequence; acr.red = stuff->red; acr.green = stuff->green; acr.blue = stuff->blue; if(retval = AllocColor(pmap, &acr.red, &acr.green, &acr.blue, &acr.pixel, client->index)) { if (client->noClientException != Success) return(client->noClientException); else return (retval); } WriteReplyToClient(client, sizeof(xAllocColorReply), &acr); return (client->noClientException); } else { client->errorValue = stuff->cmap; return (BadColor); } } int ProcAllocNamedColor (client) register ClientPtr client; { ColormapPtr pcmp; REQUEST(xAllocNamedColorReq); REQUEST_AT_LEAST_SIZE(xAllocNamedColorReq); pcmp = (ColormapPtr )LookupID(stuff->cmap, RT_COLORMAP, RC_CORE); if (pcmp) { int retval; xAllocNamedColorReply ancr; ancr.type = X_Reply; ancr.length = 0; ancr.sequenceNumber = client->sequence; if(OsLookupColor(pcmp->pScreen->myNum, (char *)&stuff[1], stuff->nbytes, &ancr.exactRed, &ancr.exactGreen, &ancr.exactBlue)) { ancr.screenRed = ancr.exactRed; ancr.screenGreen = ancr.exactGreen; ancr.screenBlue = ancr.exactBlue; if(retval = AllocColor(pcmp, &ancr.screenRed, &ancr.screenGreen, &ancr.screenBlue, &ancr.pixel, client->index)) { if (client->noClientException != Success) return(client->noClientException); else return(retval); } WriteReplyToClient(client, sizeof (xAllocNamedColorReply), &ancr); return (client->noClientException); } else return(BadName); } else { client->errorValue = stuff->cmap; return (BadColor); } } int ProcAllocColorCells (client) register ClientPtr client; { ColormapPtr pcmp; REQUEST(xAllocColorCellsReq); REQUEST_SIZE_MATCH(xAllocColorCellsReq); pcmp = (ColormapPtr )LookupID(stuff->cmap, RT_COLORMAP, RC_CORE); if (pcmp) { xAllocColorCellsReply accr; int npixels, nmasks, retval; unsigned long *ppixels, *pmasks; npixels = stuff->colors; nmasks = stuff->planes; ppixels = (unsigned long *)ALLOCATE_LOCAL(npixels * sizeof(long) + nmasks * sizeof(long)); if(!ppixels) return(client->noClientException = BadAlloc); pmasks = ppixels + npixels; if(retval = AllocColorCells(client->index, pcmp, npixels, nmasks, (Bool)stuff->contiguous, ppixels, pmasks)) { if (client->noClientException != Success) return(client->noClientException); else return(retval); } accr.type = X_Reply; accr.length = ( (npixels + nmasks) * sizeof(long)) >> 2; accr.sequenceNumber = client->sequence; accr.nPixels = npixels; accr.nMasks = nmasks; WriteReplyToClient(client, sizeof (xAllocColorCellsReply), &accr); WriteReplyToClient(client, (npixels + nmasks) * sizeof (long), ppixels); DEALLOCATE_LOCAL(ppixels); return (client->noClientException); } else { client->errorValue = stuff->cmap; return (BadColor); } } int ProcAllocColorPlanes(client) register ClientPtr client; { ColormapPtr pcmp; REQUEST(xAllocColorPlanesReq); REQUEST_SIZE_MATCH(xAllocColorPlanesReq); pcmp = (ColormapPtr )LookupID(stuff->cmap, RT_COLORMAP, RC_CORE); if (pcmp) { xAllocColorPlanesReply acpr; int npixels, retval; unsigned long *ppixels; npixels = stuff->colors; acpr.type = X_Reply; acpr.sequenceNumber = client->sequence; acpr.nPixels = npixels; npixels *= sizeof(long); ppixels = (unsigned long *)ALLOCATE_LOCAL(npixels); if(!ppixels) return(client->noClientException = BadAlloc); if(retval = AllocColorPlanes(client->index, pcmp, (int)stuff->colors, (int)stuff->red, (int)stuff->green, (int)stuff->blue, (Bool)stuff->contiguous, ppixels, &acpr.redMask, &acpr.greenMask, &acpr.blueMask)) { DEALLOCATE_LOCAL(ppixels); if (client->noClientException != Success) return(client->noClientException); else return(retval); } acpr.length = npixels >> 2; WriteReplyToClient(client, sizeof(xAllocColorPlanesReply), &acpr); WriteReplyToClient(client, npixels, ppixels); DEALLOCATE_LOCAL(ppixels); return (client->noClientException); } else { client->errorValue = stuff->cmap; return (BadColor); } } int ProcFreeColors (client) register ClientPtr client; { ColormapPtr pcmp; REQUEST(xFreeColorsReq); REQUEST_AT_LEAST_SIZE(xFreeColorsReq); pcmp = (ColormapPtr )LookupID(stuff->cmap, RT_COLORMAP, RC_CORE); if (pcmp) { int count; int retval; if(pcmp->flags & AllAllocated) return(BadAccess); count = ((stuff->length << 2)- sizeof(xFreeColorsReq)) >> 2; retval = FreeColors(pcmp, client->index, count, (unsigned long *)&stuff[1], stuff->planeMask); if (client->noClientException != Success) return(client->noClientException); else return(retval); } else { client->errorValue = stuff->cmap; return (BadColor); } } int ProcStoreColors (client) register ClientPtr client; { ColormapPtr pcmp; REQUEST(xStoreColorsReq); REQUEST_AT_LEAST_SIZE(xStoreColorsReq); pcmp = (ColormapPtr )LookupID(stuff->cmap, RT_COLORMAP, RC_CORE); if (pcmp) { int count; int retval; if(pcmp->flags & AllAllocated) if(CLIENT_ID(stuff->cmap) != client->index) return(BadAccess); count = ((stuff->length << 2) - sizeof(xStoreColorsReq)) / sizeof(xColorItem); retval = StoreColors(pcmp, count, (xColorItem *)&stuff[1]); if (client->noClientException != Success) return(client->noClientException); else return(retval); } else { client->errorValue = stuff->cmap; return (BadColor); } } int ProcStoreNamedColor (client) register ClientPtr client; { ColormapPtr pcmp; REQUEST(xStoreNamedColorReq); REQUEST_AT_LEAST_SIZE(xStoreNamedColorReq); pcmp = (ColormapPtr )LookupID(stuff->cmap, RT_COLORMAP, RC_CORE); if (pcmp) { xColorItem def; int retval; if(pcmp->flags & AllAllocated) if(CLIENT_ID(stuff->cmap) != client->index) return(BadAccess); if(OsLookupColor(pcmp->pScreen->myNum, (char *)&stuff[1], stuff->nbytes, &def.red, &def.green, &def.blue)) { def.flags = stuff->flags; retval = StoreColors(pcmp, 1, &def); if (client->noClientException != Success) return(client->noClientException); else return(retval); } return (BadName); } else { client->errorValue = stuff->cmap; return (BadColor); } } int ProcQueryColors(client) register ClientPtr client; { ColormapPtr pcmp; REQUEST(xQueryColorsReq); REQUEST_AT_LEAST_SIZE(xQueryColorsReq); pcmp = (ColormapPtr )LookupID(stuff->cmap, RT_COLORMAP, RC_CORE); if (pcmp) { int count, retval; xrgb *prgbs; xQueryColorsReply qcr; count = ((stuff->length << 2) - sizeof(xQueryColorsReq)) >> 2; if(!(prgbs = (xrgb *)ALLOCATE_LOCAL(count * sizeof(xrgb)))) return(client->noClientException = BadAlloc); if(retval = QueryColors(pcmp, count, (unsigned long *)&stuff[1], prgbs)) { DEALLOCATE_LOCAL(prgbs); if (client->noClientException != Success) return(client->noClientException); else return (retval); } qcr.type = X_Reply; qcr.length = (count * sizeof(xrgb)) >> 2; qcr.sequenceNumber = client->sequence; qcr.nColors = count; WriteReplyToClient(client, sizeof(xQueryColorsReply), &qcr); WriteReplyToClient(client, count * sizeof(xrgb), prgbs); DEALLOCATE_LOCAL(prgbs); return(client->noClientException); } else { client->errorValue = stuff->cmap; return (BadColor); } } int ProcLookupColor(client) register ClientPtr client; { ColormapPtr pcmp; REQUEST(xLookupColorReq); REQUEST_AT_LEAST_SIZE(xLookupColorReq); pcmp = (ColormapPtr )LookupID(stuff->cmap, RT_COLORMAP, RC_CORE); if (pcmp) { xLookupColorReply lcr; if(OsLookupColor(pcmp->pScreen->myNum, (char *)&stuff[1], stuff->nbytes, &lcr.exactRed, &lcr.exactGreen, &lcr.exactBlue)) { lcr.type = X_Reply; lcr.length = 0; lcr.sequenceNumber = client->sequence; lcr.screenRed = lcr.exactRed; lcr.screenGreen = lcr.exactGreen; lcr.screenBlue = lcr.exactBlue; (*pcmp->pScreen->ResolveColor)(&lcr.screenRed, &lcr.screenGreen, &lcr.screenBlue); WriteReplyToClient(client, sizeof(xLookupColorReply), &lcr); return(client->noClientException); } return (BadName); } else { client->errorValue = stuff->cmap; return (BadColor); } } int ProcCreateCursor( client) register ClientPtr client; { CursorPtr pCursor; register PixmapPtr src; register PixmapPtr msk; unsigned int * srcbits; unsigned int * mskbits; int width, height; CursorMetricRec cm; REQUEST(xCreateCursorReq); REQUEST_SIZE_MATCH(xCreateCursorReq); LEGAL_NEW_RESOURCE(stuff->cid); src = (PixmapPtr)LookupID( stuff->source, RT_PIXMAP, RC_CORE); msk = (PixmapPtr)LookupID( stuff->mask, RT_PIXMAP, RC_CORE); if ( src == (PixmapPtr)NULL) return (BadPixmap); if ( msk == (PixmapPtr)NULL) msk = src; if ( src->width != msk->width || src->height != msk->height || src->drawable.depth != 1 || msk->drawable.depth != 1) return (BadMatch); width = src->width; height = src->height; if ( stuff->x > width || stuff->y > height ) return (BadMatch); srcbits = (unsigned int *)Xalloc( PixmapBytePad(width, 1)*height); mskbits = (unsigned int *)Xalloc( PixmapBytePad(width, 1)*height); (* src->drawable.pScreen->GetImage)( src, 0, 0, width, height, XYBitmap, 0xffff, srcbits); (* msk->drawable.pScreen->GetImage)( msk, 0, 0, width, height, XYBitmap, 0xffff, mskbits); cm.width = width; cm.height = height; cm.xhot = stuff->x; cm.yhot = stuff->y; pCursor = AllocCursor( (unsigned char *)srcbits, (unsigned char *)mskbits, &cm, stuff->foreRed, stuff->foreGreen, stuff->foreBlue, stuff->backRed, stuff->backGreen, stuff->backBlue); AddResource( stuff->cid, RT_CURSOR, (pointer)pCursor, FreeCursor, RC_CORE); return (client->noClientException); } /* * protocol requires positioning of glyphs so hot-spots are coincident XXX */ int ProcCreateGlyphCursor( client) register ClientPtr client; { FontPtr sourcefont; FontPtr maskfont; char *srcbits; char *mskbits; CursorPtr pCursor; CursorMetricRec cm; int res; REQUEST(xCreateGlyphCursorReq); REQUEST_SIZE_MATCH(xCreateGlyphCursorReq); LEGAL_NEW_RESOURCE(stuff->cid); sourcefont = (FontPtr) LookupID(stuff->source, RT_FONT, RC_CORE); maskfont = (FontPtr) LookupID(stuff->mask, RT_FONT, RC_CORE); if (sourcefont == (FontPtr) NULL) return(BadFont); if (!CursorMetricsFromGlyph(maskfont,(int) stuff->maskChar, &cm)) return BadValue; if (res = ServerBitsFromGlyph(stuff->source, sourcefont, stuff->sourceChar, &cm, (unsigned char **)&srcbits)) return res; if (res = ServerBitsFromGlyph(stuff->mask, maskfont, stuff->maskChar, &cm, (unsigned char **)&mskbits)) return res; pCursor = AllocCursor((unsigned char *)srcbits, (unsigned char *)mskbits, &cm, stuff->foreRed, stuff->foreGreen, stuff->foreBlue, stuff->backRed, stuff->backGreen, stuff->backBlue); AddResource(stuff->cid, RT_CURSOR, (pointer)pCursor, FreeCursor, RC_CORE); return client->noClientException; } int ProcFreeCursor(client) register ClientPtr client; { CursorPtr pCursor; REQUEST(xResourceReq); REQUEST_SIZE_MATCH(xResourceReq); pCursor = (CursorPtr)LookupID(stuff->id, RT_CURSOR, RC_CORE); if (pCursor) { FreeResource( stuff->id, RC_NONE); return (client->noClientException); } else { return (BadCursor); } } int ProcQueryBestSize (client) register ClientPtr client; { xQueryBestSizeReply reply; register DrawablePtr pDraw; ScreenPtr pScreen; REQUEST(xQueryBestSizeReq); REQUEST_SIZE_MATCH(xQueryBestSizeReq); if ((stuff->class != CursorShape) && (stuff->class != TileShape) && (stuff->class != StippleShape)) return(BadValue); if (!(pDraw = LOOKUP_DRAWABLE(stuff->drawable, client))) { client->errorValue = stuff->drawable; return (BadDrawable); } pScreen = pDraw->pScreen; (* pScreen->QueryBestSize)(stuff->class, &stuff->width, &stuff->height); reply.type = X_Reply; reply.length = 0; reply.sequenceNumber = client->sequence; reply.width = stuff->width; reply.height = stuff->height; WriteReplyToClient(client, sizeof(xQueryBestSizeReply), &reply); return (client->noClientException); } int ProcSetScreenSaver (client) register ClientPtr client; { int blankingOption, exposureOption; REQUEST(xSetScreenSaverReq); REQUEST_SIZE_MATCH(xSetScreenSaverReq); blankingOption = stuff->preferBlank; if ((blankingOption != DontPreferBlanking) && (blankingOption != PreferBlanking) && (blankingOption != DefaultBlanking)) return BadMatch; exposureOption = stuff->allowExpose; if ((exposureOption != DontAllowExposures) && (exposureOption != AllowExposures) && (exposureOption != DefaultExposures)) return BadMatch; if ((stuff->timeout < -1) || (stuff->interval < -1)) return BadMatch; ScreenSaverBlanking = blankingOption; ScreenSaverAllowExposures = exposureOption; if (stuff->timeout >= 0) ScreenSaverTime = stuff->timeout * MILLI_PER_SECOND; else ScreenSaverTime = DEFAULT_SCREEN_SAVER_TIME; if (stuff->interval > 0) ScreenSaverInterval = stuff->interval * MILLI_PER_SECOND; else ScreenSaverInterval = DEFAULT_SCREEN_SAVER_TIME; return (client->noClientException); } int ProcGetScreenSaver(client) register ClientPtr client; { xGetScreenSaverReply rep; rep.type = X_Reply; rep.length = 0; rep.sequenceNumber = client->sequence; rep.timeout = ScreenSaverTime / MILLI_PER_SECOND; rep.interval = ScreenSaverInterval / MILLI_PER_SECOND; rep.preferBlanking = ScreenSaverBlanking; rep.allowExposures = ScreenSaverAllowExposures; WriteReplyToClient(client, sizeof(xGetScreenSaverReply), &rep); return (client->noClientException); } int ProcChangeHosts(client) register ClientPtr client; { REQUEST(xChangeHostsReq); int result; REQUEST_AT_LEAST_SIZE(xChangeHostsReq); if(stuff->mode == HostInsert) result = AddHost(client, stuff->hostFamily, stuff->hostLength, &stuff[1]); else if (stuff->mode == HostDelete) result = RemoveHost(client, stuff->hostFamily, stuff->hostLength, &stuff[1]); else return BadValue; return (result || client->noClientException); } int ProcListHosts(client) register ClientPtr client; { extern int GetHosts(); xListHostsReply reply; int len, nHosts; char *pdata; Bool tmp_enabled; REQUEST(xListHostsReq); REQUEST_SIZE_MATCH(xListHostsReq); if((len = GetHosts(&pdata, &nHosts, &tmp_enabled)) < 0) return(BadImplementation); reply.enabled = tmp_enabled; reply.type = X_Reply; reply.sequenceNumber = client->sequence; reply.nHosts = nHosts; reply.length = len >> 2; WriteReplyToClient(client, sizeof(xListHostsReply), &reply); WriteReplyToClient(client, len, pdata); Xfree(pdata); return (client->noClientException); } int ProcChangeAccessControl(client) register ClientPtr client; { REQUEST(xSetAccessControlReq); REQUEST_SIZE_MATCH(xSetAccessControlReq); if ((stuff->mode != EnableAccess) && (stuff->mode != DisableAccess)) return BadValue; ChangeAccessControl(client, stuff->mode == EnableAccess); return (client->noClientException); } int ProcKillClient(client) register ClientPtr client; { REQUEST(xResourceReq); pointer *pResource; REQUEST_SIZE_MATCH(xResourceReq); if (stuff->id == AllTemporary) { CloseDownRetainedResources(); return (client->noClientException); } pResource = (pointer *)LookupID(stuff->id, RT_ANY, RC_CORE); if ((CLIENT_ID(stuff->id)) && pResource) { CloseDownClient(client); return (client->noClientException); } else /* can't kill client 0, which is server */ { client->errorValue = stuff->id; return (BadValue); } } int ProcSetFontPath(client) register ClientPtr client; { REQUEST(xSetFontPathReq); REQUEST_AT_LEAST_SIZE(xSetFontPathReq); SetFontPath((int)stuff->nFonts, (int)stuff->length, (char *)&stuff[1]); return (client->noClientException); } int ProcGetFontPath(client) register ClientPtr client; { FontPathPtr pFP; xGetFontPathReply reply; int stringLens, i; char *bufferStart; register char *bufptr; REQUEST (xReq); REQUEST_SIZE_MATCH(xReq); pFP = GetFontPath(); stringLens = 0; for (i=0; inpaths; i++) stringLens += pFP->length[i]; reply.type = X_Reply; reply.sequenceNumber = client->sequence; reply.length = (stringLens + pFP->npaths + 3) >> 2; reply.nPaths = pFP->npaths; bufptr = bufferStart = (char *)ALLOCATE_LOCAL((int)reply.length << 2); if(!bufptr) return(client->noClientException = BadAlloc); /* since WriteToClient long word aligns things, copy to temp buffer and write all at once */ for (i=0; inpaths; i++) { *bufptr++ = pFP->length[i]; bcopy(pFP->paths[i], bufptr, pFP->length[i]); bufptr += pFP->length[i]; } WriteReplyToClient(client, sizeof(xGetFontPathReply), &reply); WriteReplyToClient(client, reply.length << 2, bufferStart); DEALLOCATE_LOCAL(bufferStart); return(client->noClientException); } int ProcChangeCloseDownMode(client) register ClientPtr client; { REQUEST(xSetCloseDownModeReq); REQUEST_SIZE_MATCH(xSetCloseDownModeReq); if ((stuff->mode == AllTemporary) || (stuff->mode == RetainPermanent) || (stuff->mode == RetainTemporary)) { client->closeDownMode = stuff->mode; return (client->noClientException); } else { client->errorValue = stuff->mode; return (BadValue); } } int ProcForceScreenSaver(client) register ClientPtr client; { REQUEST(xForceScreenSaverReq); REQUEST_SIZE_MATCH(xForceScreenSaverReq); if ((stuff->mode != ScreenSaverReset) && (stuff->mode != ScreenSaverActive)) return BadValue; SaveScreens(SCREEN_SAVER_FORCER, (int)stuff->mode); return client->noClientException; } int ProcNoOperation(client) register ClientPtr client; { REQUEST(xReq); REQUEST_AT_LEAST_SIZE(xReq); /* noop -- don't do anything */ return(client->noClientException); } void InitProcVectors() { int i; for (i = 0; i<256; i++) { if(!ProcVector[i]) { ProcVector[i] = SwappedProcVector[i] = ProcBadRequest; ReplySwapVector[i] = NotImplemented; } } for(i = LASTEvent; i < 128; i++) { EventSwapVector[i] = NotImplemented; } } /********************** * CloseDownClient * * Client can either mark his resources destroy or retain. If retained and * then killed again, the client is really destroyed. *********************/ void CloseDownClient(client) register ClientPtr client; { register int i; /* ungrab server if grabbing client dies */ if (grabbingClient && (onlyClient == client)) { grabbingClient = FALSE; ListenToAllClients(); } ReleaseActiveGrabs(client); if (client->closeDownMode == DestroyAll) { client->clientGone = TRUE; /* so events aren't sent to client */ CloseDownConnection(client); FreeClientResources(client); for (i=0; iclientGone) { FreeClientResources(client); for (i=0; iclientGone = TRUE; CloseDownConnection(client); } } void KillAllClients() { int i; for (i=1; iclientGone) CloseDownClient(clients[i]); } void KillServerResources() { int i; KillAllClients(); CloseDownDevices((int)0, (long)0); for (i = 0; i < screenInfo.numScreens; i++) (*screenInfo.screen[i].CloseScreen)(i, &screenInfo.screen[i]); } /********************* * CloseDownRetainedResources * * Find all clients that are gone and have terminated in RetainTemporary * and destroy their resources. *********************/ CloseDownRetainedResources() { register int i; register ClientPtr client; for (i=1; icloseDownMode == RetainTemporary) && (client->clientGone)) { FreeClientResources(client); nextFreeClientID = i; Xfree(client); clients[i] = NullClient; } } } /************************ * int NextAvailableClientID() * * OS depedent portion can't assign client id's because of CloseDownModes. * Returns -1 if the there are no free clients. *************************/ /* * XXX - gag, choke, puke - XXX */ asm(" exportproc _NextAvailableClient, XCRoutines"); ClientPtr NextAvailableClient() { long i; ClientPtr client; if (nextFreeClientID >= currentMaxClients) nextFreeClientID = 1; if (!clients[nextFreeClientID]) { i = nextFreeClientID; nextFreeClientID++; } else { i = 1; while ((iindex = i; client->sequence = 0; client->clientAsMask = i << CLIENTOFFSET; client->closeDownMode = DestroyAll; client->clientGone = FALSE; client->lastDrawable = (pointer) NULL; client->lastDrawableID = -1; client->lastGC = (pointer) NULL; client->lastGCID = -1; client->numSaved = 0; client->saveSet = (pointer *)NULL; client->noClientException = Success; return(client); } SendConnectionSetupInfo(client) ClientPtr client; { xConnSetup *setup; /* if (client->swapped) setup = (xConnSetup *) SwappedConnInfo; else */ setup = (xConnSetup *)ConnectionInfo; client->pSwapReplyFunc = (void (*) ()) NULL; setup->ridBase = (client->clientAsMask); setup->ridMask = 0xfffff; WriteConnToClient(client, (int)sizeof(xConnSetupPrefix), (xConnSetupPrefix *)&connSetupPrefix); WriteSConnectionInfo(client, (int)connSetupPrefix.length << 2, (char *)ConnectionInfo); } /***************** * Oops * Send an Error back to the client. *****************/ Oops (client, reqCode, minorCode, status) ClientPtr client; char reqCode, minorCode, status; { xError rep; register int i; rep.type = X_Error; rep.sequenceNumber = client->sequence; rep.errorCode = status; rep.majorCode = reqCode; rep.minorCode = minorCode; rep.resourceID = client->errorValue; for (i=0; inoClientException = -1; } /* Byte swap a list of longs */ SwapLongs (list, count) register long *list; register int count; { register int n; while (count >= 8) { swapl(list+0, n); swapl(list+1, n); swapl(list+2, n); swapl(list+3, n); swapl(list+4, n); swapl(list+5, n); swapl(list+6, n); swapl(list+7, n); list += 8; count -= 8; } while (--count >= 0) { swapl(list, n); list++; } } /* Byte swap a list of shorts */ SwapShorts (list, count) register short *list; register int count; { register int n; while (count >= 16) { swaps(list+0, n); swaps(list+1, n); swaps(list+2, n); swaps(list+3, n); swaps(list+4, n); swaps(list+5, n); swaps(list+6, n); swaps(list+7, n); swaps(list+8, n); swaps(list+9, n); swaps(list+10, n); swaps(list+11, n); swaps(list+12, n); swaps(list+13, n); swaps(list+14, n); swaps(list+15, n); list += 16; count -= 16; } while (--count >= 0) { swaps(list, n); list++; } }