/************************************************************
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; i<pFP->npaths; 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; i<pFP->npaths; 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; i<currentMaxClients; i++)
if (clients[i] == client)
{
nextFreeClientID = i;
clients[nextFreeClientID] = NullClient;
break;
}
Xfree(client);
if(--nClients == 0)
nClients = -1;
}
/* really kill resources this time */
else if (client->clientGone)
{
FreeClientResources(client);
for (i=0; i<currentMaxClients; i++)
if (clients[i] == client)
{
nextFreeClientID = i;
clients[nextFreeClientID] = NullClient;
break;
}
Xfree(client);
--nClients;
}
else
{
client->clientGone = TRUE;
CloseDownConnection(client);
}
}
void
KillAllClients()
{
int i;
for (i=1; i<currentMaxClients; i++)
if (clients[i] && !clients[i]->clientGone)
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; i<currentMaxClients; i++)
{
client = clients[i];
if (client && (client->closeDownMode == 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 ((i<currentMaxClients) && (clients[i]))
i++;
if (i < currentMaxClients)
nextFreeClientID = i;
else
{
clients = (ClientPtr *)Xrealloc(clients, i * sizeof(ClientRec));
currentMaxClients++;
}
}
clients[i] = client = (ClientPtr)Xalloc(sizeof(ClientRec));
client->index = 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; i<currentMaxClients; i++)
if (clients[i] == client) break;
ErrorF( "OOPS!!! to client %x\n", i);
ErrorF( " sequenceNumber = %d\n", rep.sequenceNumber);
ErrorF( " rep.errorCode= %d\n", rep.errorCode);
ErrorF( " rep.majorCode = %d\n", rep.majorCode);
ErrorF( " rep.resourceID = %x\n", rep.resourceID);
WriteEventToClient (client, 1, (pointer) &rep);
}
void
DeleteWindowFromAnySelections(pWin)
WindowPtr pWin;
{
int i = 0;
for (i = 0; i< NumCurrentSelections; i++)
if (CurrentSelections[i].pWin == pWin)
{
CurrentSelections[i].pWin = (WindowPtr)NULL;
CurrentSelections[i].window = None;
}
}
void
MarkClientException(client)
ClientPtr client;
{
client->noClientException = -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++;
}
}