cmsCmap.c revision 1ab64890
11ab64890Smrg/* $Xorg: cmsCmap.c,v 1.3 2000/08/17 19:45:09 cpqbld Exp $ */
21ab64890Smrg
31ab64890Smrg/*
41ab64890Smrg * Code and supporting documentation (c) Copyright 1990 1991 Tektronix, Inc.
51ab64890Smrg * 	All Rights Reserved
61ab64890Smrg *
71ab64890Smrg * This file is a component of an X Window System-specific implementation
81ab64890Smrg * of Xcms based on the TekColor Color Management System.  Permission is
91ab64890Smrg * hereby granted to use, copy, modify, sell, and otherwise distribute this
101ab64890Smrg * software and its documentation for any purpose and without fee, provided
111ab64890Smrg * that this copyright, permission, and disclaimer notice is reproduced in
121ab64890Smrg * all copies of this software and in supporting documentation.  TekColor
131ab64890Smrg * is a trademark of Tektronix, Inc.
141ab64890Smrg *
151ab64890Smrg * Tektronix makes no representation about the suitability of this software
161ab64890Smrg * for any purpose.  It is provided "as is" and with all faults.
171ab64890Smrg *
181ab64890Smrg * TEKTRONIX DISCLAIMS ALL WARRANTIES APPLICABLE TO THIS SOFTWARE,
191ab64890Smrg * INCLUDING THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
201ab64890Smrg * PARTICULAR PURPOSE.  IN NO EVENT SHALL TEKTRONIX BE LIABLE FOR ANY
211ab64890Smrg * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
221ab64890Smrg * RESULTING FROM LOSS OF USE, DATA, OR PROFITS, WHETHER IN AN ACTION OF
231ab64890Smrg * CONTRACT, NEGLIGENCE, OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
241ab64890Smrg * CONNECTION WITH THE USE OR THE PERFORMANCE OF THIS SOFTWARE.
251ab64890Smrg *
261ab64890Smrg *
271ab64890Smrg *	NAME
281ab64890Smrg *		XcmsCmap.c - Client Colormap Management Routines
291ab64890Smrg *
301ab64890Smrg *	DESCRIPTION
311ab64890Smrg *		Routines that store additional information about
321ab64890Smrg *		colormaps being used by the X Client.
331ab64890Smrg *
341ab64890Smrg *
351ab64890Smrg */
361ab64890Smrg/* $XFree86$ */
371ab64890Smrg
381ab64890Smrg#define NEED_EVENTS
391ab64890Smrg#define NEED_REPLIES
401ab64890Smrg#ifdef HAVE_CONFIG_H
411ab64890Smrg#include <config.h>
421ab64890Smrg#endif
431ab64890Smrg#include "Xlibint.h"
441ab64890Smrg#include "Xcmsint.h"
451ab64890Smrg#include "Xutil.h"
461ab64890Smrg#include "Cmap.h"
471ab64890Smrg#include "Cv.h"
481ab64890Smrg
491ab64890Smrg/*
501ab64890Smrg *      FORWARD DECLARATIONS
511ab64890Smrg */
521ab64890Smrgstatic void _XcmsFreeClientCmaps(Display *dpy);
531ab64890Smrg
541ab64890Smrg
551ab64890Smrg/************************************************************************
561ab64890Smrg *									*
571ab64890Smrg *			PRIVATE INTERFACES				*
581ab64890Smrg *									*
591ab64890Smrg ************************************************************************/
601ab64890Smrg
611ab64890Smrg/*
621ab64890Smrg *	NAME
631ab64890Smrg *		CmapRecForColormap
641ab64890Smrg *
651ab64890Smrg *	SYNOPSIS
661ab64890Smrg */
671ab64890Smrgstatic XcmsCmapRec *
681ab64890SmrgCmapRecForColormap(
691ab64890Smrg    Display *dpy,
701ab64890Smrg    Colormap cmap)
711ab64890Smrg/*
721ab64890Smrg *	DESCRIPTION
731ab64890Smrg *		Find the corresponding XcmsCmapRec for cmap.  In not found
741ab64890Smrg *		this routines attempts to create one.
751ab64890Smrg *
761ab64890Smrg *	RETURNS
771ab64890Smrg *		Returns NULL if failed; otherwise the address to
781ab64890Smrg *		the corresponding XcmsCmapRec.
791ab64890Smrg *
801ab64890Smrg */
811ab64890Smrg{
821ab64890Smrg    XcmsCmapRec *pRec;
831ab64890Smrg    int nScrn;
841ab64890Smrg    int i, j;
851ab64890Smrg    XVisualInfo visualTemplate;	/* Template of the visual we want */
861ab64890Smrg    XVisualInfo *visualList;	/* List for visuals that match */
871ab64890Smrg    int nVisualsMatched;	/* Number of visuals that match */
881ab64890Smrg    Window tmpWindow;
891ab64890Smrg    Visual *vp;
901ab64890Smrg    unsigned long border = 0;
911ab64890Smrg    _XAsyncHandler async;
921ab64890Smrg    _XAsyncErrorState async_state;
931ab64890Smrg
941ab64890Smrg    for (pRec = (XcmsCmapRec *)dpy->cms.clientCmaps; pRec != NULL;
951ab64890Smrg	    pRec = pRec->pNext) {
961ab64890Smrg	if (pRec->cmapID == cmap) {
971ab64890Smrg	    return(pRec);
981ab64890Smrg	}
991ab64890Smrg    }
1001ab64890Smrg
1011ab64890Smrg    /*
1021ab64890Smrg     * Can't find an XcmsCmapRec associated with cmap in our records.
1031ab64890Smrg     * Let's try to see if its a default colormap
1041ab64890Smrg     */
1051ab64890Smrg    nScrn = ScreenCount(dpy);
1061ab64890Smrg    for (i = 0; i < nScrn; i++) {
1071ab64890Smrg	if (cmap == DefaultColormap(dpy, i)) {
1081ab64890Smrg	    /* It is ... lets go ahead and store that info */
1091ab64890Smrg	    if ((pRec = _XcmsAddCmapRec(dpy, cmap, RootWindow(dpy, i),
1101ab64890Smrg		    DefaultVisual(dpy, i))) == NULL) {
1111ab64890Smrg		return((XcmsCmapRec *)NULL);
1121ab64890Smrg	    }
1131ab64890Smrg	    pRec->ccc = XcmsCreateCCC(
1141ab64890Smrg		    dpy,
1151ab64890Smrg		    i,			/* screenNumber */
1161ab64890Smrg		    DefaultVisual(dpy, i),
1171ab64890Smrg		    (XcmsColor *)NULL,	/* clientWhitePt */
1181ab64890Smrg		    (XcmsCompressionProc)NULL,  /* gamutCompProc */
1191ab64890Smrg		    (XPointer)NULL,	/* gamutCompClientData */
1201ab64890Smrg		    (XcmsWhiteAdjustProc)NULL,  /* whitePtAdjProc */
1211ab64890Smrg		    (XPointer)NULL	/* whitePtAdjClientData */
1221ab64890Smrg		    );
1231ab64890Smrg	    return(pRec);
1241ab64890Smrg	}
1251ab64890Smrg    }
1261ab64890Smrg
1271ab64890Smrg    /*
1281ab64890Smrg     * Nope, its not a default colormap, so it's probably a foreign color map
1291ab64890Smrg     * of which we have no specific details.  Let's go through the
1301ab64890Smrg     * rigorous process of finding this colormap:
1311ab64890Smrg     *        for each screen
1321ab64890Smrg     *            for each screen's visual types
1331ab64890Smrg     *                create a window with cmap specified as the colormap
1341ab64890Smrg     *                if successful
1351ab64890Smrg     *                    Add a CmapRec
1361ab64890Smrg     *                    Create an XcmsCCC
1371ab64890Smrg     *                    return the CmapRec
1381ab64890Smrg     *                else
1391ab64890Smrg     *                    continue
1401ab64890Smrg     */
1411ab64890Smrg
1421ab64890Smrg    async_state.error_code = 0; /* don't care */
1431ab64890Smrg    async_state.major_opcode = X_CreateWindow;
1441ab64890Smrg    async_state.minor_opcode = 0;
1451ab64890Smrg    for (i = 0; i < nScrn; i++) {
1461ab64890Smrg	visualTemplate.screen = i;
1471ab64890Smrg	visualList = XGetVisualInfo(dpy, VisualScreenMask, &visualTemplate,
1481ab64890Smrg	    &nVisualsMatched);
1491ab64890Smrg	if (visualList == NULL) {
1501ab64890Smrg	    continue;
1511ab64890Smrg	}
1521ab64890Smrg
1531ab64890Smrg	/*
1541ab64890Smrg	 * Attempt to create a window with cmap
1551ab64890Smrg	 */
1561ab64890Smrg	j = 0;
1571ab64890Smrg	do {
1581ab64890Smrg	    vp = (visualList+j)->visual;
1591ab64890Smrg	    LockDisplay(dpy);
1601ab64890Smrg	    {
1611ab64890Smrg		register xCreateWindowReq *req;
1621ab64890Smrg
1631ab64890Smrg		GetReq(CreateWindow, req);
1641ab64890Smrg		async_state.min_sequence_number = dpy->request;
1651ab64890Smrg		async_state.max_sequence_number = dpy->request;
1661ab64890Smrg		async_state.error_count = 0;
1671ab64890Smrg		async.next = dpy->async_handlers;
1681ab64890Smrg		async.handler = _XAsyncErrorHandler;
1691ab64890Smrg		async.data = (XPointer)&async_state;
1701ab64890Smrg		dpy->async_handlers = &async;
1711ab64890Smrg		req->parent = RootWindow(dpy, i);
1721ab64890Smrg		req->x = 0;
1731ab64890Smrg		req->y = 0;
1741ab64890Smrg		req->width = 1;
1751ab64890Smrg		req->height = 1;
1761ab64890Smrg		req->borderWidth = 0;
1771ab64890Smrg		req->depth = (visualList+j)->depth;
1781ab64890Smrg		req->class = CopyFromParent;
1791ab64890Smrg		req->visual = vp->visualid;
1801ab64890Smrg		tmpWindow = req->wid = XAllocID(dpy);
1811ab64890Smrg		req->mask = CWBorderPixel | CWColormap;
1821ab64890Smrg		req->length += 2;
1831ab64890Smrg		Data32 (dpy, (long *) &border, 4);
1841ab64890Smrg		Data32 (dpy, (long *) &cmap, 4);
1851ab64890Smrg	    }
1861ab64890Smrg	    {
1871ab64890Smrg		xGetInputFocusReply rep;
1881ab64890Smrg		register xReq *req;
1891ab64890Smrg
1901ab64890Smrg		GetEmptyReq(GetInputFocus, req);
1911ab64890Smrg		(void) _XReply (dpy, (xReply *)&rep, 0, xTrue);
1921ab64890Smrg	    }
1931ab64890Smrg	    DeqAsyncHandler(dpy, &async);
1941ab64890Smrg	    UnlockDisplay(dpy);
1951ab64890Smrg	    SyncHandle();
1961ab64890Smrg	} while (async_state.error_count > 0 && ++j < nVisualsMatched);
1971ab64890Smrg
1981ab64890Smrg	Xfree((char *)visualList);
1991ab64890Smrg
2001ab64890Smrg	/*
2011ab64890Smrg	 * if successful
2021ab64890Smrg	 */
2031ab64890Smrg	if (j < nVisualsMatched) {
2041ab64890Smrg	    if ((pRec = _XcmsAddCmapRec(dpy, cmap, tmpWindow, vp)) == NULL)
2051ab64890Smrg		return((XcmsCmapRec *)NULL);
2061ab64890Smrg	    pRec->ccc = XcmsCreateCCC(
2071ab64890Smrg		    dpy,
2081ab64890Smrg		    i,			/* screenNumber */
2091ab64890Smrg		    vp,
2101ab64890Smrg		    (XcmsColor *)NULL,	/* clientWhitePt */
2111ab64890Smrg		    (XcmsCompressionProc)NULL,  /* gamutCompProc */
2121ab64890Smrg		    (XPointer)NULL,	/* gamutCompClientData */
2131ab64890Smrg		    (XcmsWhiteAdjustProc)NULL,  /* whitePtAdjProc */
2141ab64890Smrg		    (XPointer)NULL	/* whitePtAdjClientData */
2151ab64890Smrg		    );
2161ab64890Smrg	    XDestroyWindow(dpy, tmpWindow);
2171ab64890Smrg	    return(pRec);
2181ab64890Smrg	}
2191ab64890Smrg    }
2201ab64890Smrg
2211ab64890Smrg    return(NULL);
2221ab64890Smrg}
2231ab64890Smrg
2241ab64890Smrg
2251ab64890Smrg
2261ab64890Smrg/************************************************************************
2271ab64890Smrg *									*
2281ab64890Smrg *			API PRIVATE INTERFACES				*
2291ab64890Smrg *									*
2301ab64890Smrg ************************************************************************/
2311ab64890Smrg
2321ab64890Smrg/*
2331ab64890Smrg *	NAME
2341ab64890Smrg *		_XcmsAddCmapRec
2351ab64890Smrg *
2361ab64890Smrg *	SYNOPSIS
2371ab64890Smrg */
2381ab64890SmrgXcmsCmapRec *
2391ab64890Smrg_XcmsAddCmapRec(
2401ab64890Smrg    Display *dpy,
2411ab64890Smrg    Colormap cmap,
2421ab64890Smrg    Window windowID,
2431ab64890Smrg    Visual *visual)
2441ab64890Smrg/*
2451ab64890Smrg *	DESCRIPTION
2461ab64890Smrg *		Create an XcmsCmapRec for the specified cmap, windowID,
2471ab64890Smrg *		and visual, then adds it to its list of CmapRec's.
2481ab64890Smrg *
2491ab64890Smrg *	RETURNS
2501ab64890Smrg *		Returns NULL if failed; otherwise the address to
2511ab64890Smrg *		the added XcmsCmapRec.
2521ab64890Smrg *
2531ab64890Smrg */
2541ab64890Smrg{
2551ab64890Smrg    XcmsCmapRec *pNew;
2561ab64890Smrg
2571ab64890Smrg    if ((pNew = (XcmsCmapRec *) Xcalloc(1, (unsigned) sizeof(XcmsCmapRec)))
2581ab64890Smrg	    == NULL) {
2591ab64890Smrg	return((XcmsCmapRec *)NULL);
2601ab64890Smrg    }
2611ab64890Smrg
2621ab64890Smrg    pNew->cmapID = cmap;
2631ab64890Smrg    pNew->dpy = dpy;
2641ab64890Smrg    pNew->windowID = windowID;
2651ab64890Smrg    pNew->visual = visual;
2661ab64890Smrg    pNew->pNext = (XcmsCmapRec *)dpy->cms.clientCmaps;
2671ab64890Smrg    dpy->cms.clientCmaps = (XPointer)pNew;
2681ab64890Smrg    dpy->free_funcs->clientCmaps = _XcmsFreeClientCmaps;
2691ab64890Smrg
2701ab64890Smrg    /*
2711ab64890Smrg     * Note, we don't create the XcmsCCC for pNew->ccc here because
2721ab64890Smrg     * it may require the use of XGetWindowAttributes (a round trip request)
2731ab64890Smrg     * to determine the screen.
2741ab64890Smrg     */
2751ab64890Smrg    return(pNew);
2761ab64890Smrg}
2771ab64890Smrg
2781ab64890Smrg
2791ab64890Smrg/*
2801ab64890Smrg *	NAME
2811ab64890Smrg *		_XcmsCopyCmapRecAndFree
2821ab64890Smrg *
2831ab64890Smrg *	SYNOPSIS
2841ab64890Smrg */
2851ab64890SmrgXcmsCmapRec *
2861ab64890Smrg_XcmsCopyCmapRecAndFree(
2871ab64890Smrg    Display *dpy,
2881ab64890Smrg    Colormap src_cmap,
2891ab64890Smrg    Colormap copy_cmap)
2901ab64890Smrg/*
2911ab64890Smrg *	DESCRIPTION
2921ab64890Smrg *		Augments Xlib's XCopyColormapAndFree() to copy
2931ab64890Smrg *		XcmsCmapRecs.
2941ab64890Smrg *
2951ab64890Smrg *	RETURNS
2961ab64890Smrg *		Returns NULL if failed; otherwise the address to
2971ab64890Smrg *		the copy XcmsCmapRec.
2981ab64890Smrg *
2991ab64890Smrg */
3001ab64890Smrg{
3011ab64890Smrg    XcmsCmapRec *pRec_src;
3021ab64890Smrg    XcmsCmapRec *pRec_copy;
3031ab64890Smrg
3041ab64890Smrg    if ((pRec_src = CmapRecForColormap(dpy, src_cmap)) != NULL) {
3051ab64890Smrg	pRec_copy =_XcmsAddCmapRec(dpy, copy_cmap, pRec_src->windowID,
3061ab64890Smrg		pRec_src->visual);
3071ab64890Smrg	if (pRec_copy != NULL && pRec_src->ccc) {
3081ab64890Smrg	    pRec_copy->ccc = (XcmsCCC)Xcalloc(1, (unsigned) sizeof(XcmsCCCRec));
3091ab64890Smrg	    memcpy((char *)pRec_copy->ccc, (char *)pRec_src->ccc,
3101ab64890Smrg		   sizeof(XcmsCCCRec));
3111ab64890Smrg	}
3121ab64890Smrg	return(pRec_copy);
3131ab64890Smrg    }
3141ab64890Smrg    return((XcmsCmapRec *)NULL);
3151ab64890Smrg}
3161ab64890Smrg
3171ab64890Smrg
3181ab64890Smrg/*
3191ab64890Smrg *	NAME
3201ab64890Smrg *		_XcmsDeleteCmapRec
3211ab64890Smrg *
3221ab64890Smrg *	SYNOPSIS
3231ab64890Smrg */
3241ab64890Smrgvoid
3251ab64890Smrg_XcmsDeleteCmapRec(
3261ab64890Smrg    Display *dpy,
3271ab64890Smrg    Colormap cmap)
3281ab64890Smrg/*
3291ab64890Smrg *	DESCRIPTION
3301ab64890Smrg *		Removes and frees the specified XcmsCmapRec structure
3311ab64890Smrg *		from the linked list of structures.
3321ab64890Smrg *
3331ab64890Smrg *	RETURNS
3341ab64890Smrg *		void
3351ab64890Smrg *
3361ab64890Smrg */
3371ab64890Smrg{
3381ab64890Smrg    XcmsCmapRec **pPrevPtr;
3391ab64890Smrg    XcmsCmapRec *pRec;
3401ab64890Smrg    int scr;
3411ab64890Smrg
3421ab64890Smrg    /* If it is the default cmap for a screen, do not delete it,
3431ab64890Smrg     * because the server will not actually free it */
3441ab64890Smrg    for (scr = ScreenCount(dpy); --scr >= 0; ) {
3451ab64890Smrg	if (cmap == DefaultColormap(dpy, scr))
3461ab64890Smrg	    return;
3471ab64890Smrg    }
3481ab64890Smrg
3491ab64890Smrg    /* search for it in the list */
3501ab64890Smrg    pPrevPtr = (XcmsCmapRec **)&dpy->cms.clientCmaps;
3511ab64890Smrg    while ((pRec = *pPrevPtr) && (pRec->cmapID != cmap)) {
3521ab64890Smrg	pPrevPtr = &pRec->pNext;
3531ab64890Smrg    }
3541ab64890Smrg
3551ab64890Smrg    if (pRec) {
3561ab64890Smrg	if (pRec->ccc) {
3571ab64890Smrg	    XcmsFreeCCC(pRec->ccc);
3581ab64890Smrg	}
3591ab64890Smrg	*pPrevPtr = pRec->pNext;
3601ab64890Smrg	Xfree((char *)pRec);
3611ab64890Smrg    }
3621ab64890Smrg}
3631ab64890Smrg
3641ab64890Smrg
3651ab64890Smrg/*
3661ab64890Smrg *	NAME
3671ab64890Smrg *		_XcmsFreeClientCmaps
3681ab64890Smrg *
3691ab64890Smrg *	SYNOPSIS
3701ab64890Smrg */
3711ab64890Smrgstatic void
3721ab64890Smrg_XcmsFreeClientCmaps(
3731ab64890Smrg    Display *dpy)
3741ab64890Smrg/*
3751ab64890Smrg *	DESCRIPTION
3761ab64890Smrg *		Frees all XcmsCmapRec structures in the linked list
3771ab64890Smrg *		and sets dpy->cms.clientCmaps to NULL.
3781ab64890Smrg *
3791ab64890Smrg *	RETURNS
3801ab64890Smrg *		void
3811ab64890Smrg *
3821ab64890Smrg */
3831ab64890Smrg{
3841ab64890Smrg    XcmsCmapRec *pRecNext, *pRecFree;
3851ab64890Smrg
3861ab64890Smrg    pRecNext = (XcmsCmapRec *)dpy->cms.clientCmaps;
3871ab64890Smrg    while (pRecNext != NULL) {
3881ab64890Smrg	pRecFree = pRecNext;
3891ab64890Smrg	pRecNext = pRecNext->pNext;
3901ab64890Smrg	if (pRecFree->ccc) {
3911ab64890Smrg	    /* Free the XcmsCCC structure */
3921ab64890Smrg	    XcmsFreeCCC(pRecFree->ccc);
3931ab64890Smrg	}
3941ab64890Smrg	/* Now free the XcmsCmapRec structure */
3951ab64890Smrg	Xfree((char *)pRecFree);
3961ab64890Smrg    }
3971ab64890Smrg    dpy->cms.clientCmaps = (XPointer)NULL;
3981ab64890Smrg}
3991ab64890Smrg
4001ab64890Smrg
4011ab64890Smrg
4021ab64890Smrg/************************************************************************
4031ab64890Smrg *									*
4041ab64890Smrg *			PUBLIC INTERFACES				*
4051ab64890Smrg *									*
4061ab64890Smrg ************************************************************************/
4071ab64890Smrg
4081ab64890Smrg/*
4091ab64890Smrg *	NAME
4101ab64890Smrg *		XcmsCCCOfColormap
4111ab64890Smrg *
4121ab64890Smrg *	SYNOPSIS
4131ab64890Smrg */
4141ab64890SmrgXcmsCCC
4151ab64890SmrgXcmsCCCOfColormap(
4161ab64890Smrg    Display *dpy,
4171ab64890Smrg    Colormap cmap)
4181ab64890Smrg/*
4191ab64890Smrg *	DESCRIPTION
4201ab64890Smrg *		Finds the XcmsCCC associated with the specified colormap.
4211ab64890Smrg *
4221ab64890Smrg *	RETURNS
4231ab64890Smrg *		Returns NULL if failed; otherwise the address to
4241ab64890Smrg *		the associated XcmsCCC structure.
4251ab64890Smrg *
4261ab64890Smrg */
4271ab64890Smrg{
4281ab64890Smrg    XWindowAttributes windowAttr;
4291ab64890Smrg    XcmsCmapRec *pRec;
4301ab64890Smrg    int nScrn = ScreenCount(dpy);
4311ab64890Smrg    int i;
4321ab64890Smrg
4331ab64890Smrg    if ((pRec = CmapRecForColormap(dpy, cmap)) != NULL) {
4341ab64890Smrg	if (pRec->ccc) {
4351ab64890Smrg	    /* XcmsCmapRec already has a XcmsCCC */
4361ab64890Smrg	    return(pRec->ccc);
4371ab64890Smrg	}
4381ab64890Smrg
4391ab64890Smrg	/*
4401ab64890Smrg	 * The XcmsCmapRec does not have a XcmsCCC yet, so let's create
4411ab64890Smrg	 * one.  But first, we need to know the screen associated with
4421ab64890Smrg	 * cmap, so use XGetWindowAttributes() to extract that
4431ab64890Smrg	 * information.  Unless, of course there is only one screen!!
4441ab64890Smrg	 */
4451ab64890Smrg	if (nScrn == 1) {
4461ab64890Smrg	    /* Assume screenNumber == 0 */
4471ab64890Smrg	    return(pRec->ccc = XcmsCreateCCC(
4481ab64890Smrg		    dpy,
4491ab64890Smrg		    0,			/* screenNumber */
4501ab64890Smrg		    pRec->visual,
4511ab64890Smrg		    (XcmsColor *)NULL,	/* clientWhitePt */
4521ab64890Smrg		    (XcmsCompressionProc)NULL,  /* gamutCompProc */
4531ab64890Smrg		    (XPointer)NULL,	/* gamutCompClientData */
4541ab64890Smrg		    (XcmsWhiteAdjustProc)NULL,  /* whitePtAdjProc */
4551ab64890Smrg		    (XPointer)NULL	/* whitePtAdjClientData */
4561ab64890Smrg		    ));
4571ab64890Smrg	} else {
4581ab64890Smrg	    if (XGetWindowAttributes(dpy, pRec->windowID, &windowAttr)) {
4591ab64890Smrg		for (i = 0; i < nScrn; i++) {
4601ab64890Smrg		    if (ScreenOfDisplay(dpy, i) == windowAttr.screen) {
4611ab64890Smrg			return(pRec->ccc = XcmsCreateCCC(
4621ab64890Smrg				dpy,
4631ab64890Smrg				i,		   /* screenNumber */
4641ab64890Smrg				pRec->visual,
4651ab64890Smrg				(XcmsColor *)NULL, /* clientWhitePt */
4661ab64890Smrg				(XcmsCompressionProc)NULL, /* gamutCompProc */
4671ab64890Smrg				(XPointer)NULL,	   /* gamutCompClientData */
4681ab64890Smrg				(XcmsWhiteAdjustProc)NULL, /* whitePtAdjProc */
4691ab64890Smrg				(XPointer)NULL	   /* whitePtAdjClientData */
4701ab64890Smrg				));
4711ab64890Smrg		    }
4721ab64890Smrg		}
4731ab64890Smrg	    }
4741ab64890Smrg	}
4751ab64890Smrg    }
4761ab64890Smrg
4771ab64890Smrg    /*
4781ab64890Smrg     * No such cmap
4791ab64890Smrg     */
4801ab64890Smrg    return(NULL);
4811ab64890Smrg}
4821ab64890Smrg
4831ab64890SmrgXcmsCCC XcmsSetCCCOfColormap(
4841ab64890Smrg    Display *dpy,
4851ab64890Smrg    Colormap cmap,
4861ab64890Smrg    XcmsCCC ccc)
4871ab64890Smrg{
4881ab64890Smrg    XcmsCCC prev_ccc = NULL;
4891ab64890Smrg    XcmsCmapRec *pRec;
4901ab64890Smrg
4911ab64890Smrg    pRec = CmapRecForColormap(dpy, cmap);
4921ab64890Smrg    if (pRec) {
4931ab64890Smrg	prev_ccc = pRec->ccc;
4941ab64890Smrg	pRec->ccc = ccc;
4951ab64890Smrg    }
4961ab64890Smrg    return prev_ccc;
4971ab64890Smrg}
498