diff options
Diffstat (limited to 'libXrender/src')
-rw-r--r-- | libXrender/src/AddTrap.c | 68 | ||||
-rw-r--r-- | libXrender/src/Color.c | 92 | ||||
-rw-r--r-- | libXrender/src/Composite.c | 67 | ||||
-rw-r--r-- | libXrender/src/Cursor.c | 79 | ||||
-rw-r--r-- | libXrender/src/FillRect.c | 106 | ||||
-rw-r--r-- | libXrender/src/FillRects.c | 79 | ||||
-rw-r--r-- | libXrender/src/Filter.c | 153 | ||||
-rw-r--r-- | libXrender/src/Glyph.c | 712 | ||||
-rw-r--r-- | libXrender/src/Makefile.am | 27 | ||||
-rw-r--r-- | libXrender/src/Picture.c | 372 | ||||
-rw-r--r-- | libXrender/src/Poly.c | 302 | ||||
-rw-r--r-- | libXrender/src/Trap.c | 74 | ||||
-rw-r--r-- | libXrender/src/Tri.c | 169 | ||||
-rw-r--r-- | libXrender/src/Xrender.c | 889 | ||||
-rw-r--r-- | libXrender/src/Xrenderint.h | 114 |
15 files changed, 3303 insertions, 0 deletions
diff --git a/libXrender/src/AddTrap.c b/libXrender/src/AddTrap.c new file mode 100644 index 000000000..421463def --- /dev/null +++ b/libXrender/src/AddTrap.c @@ -0,0 +1,68 @@ +/* + * Copyright © 2004 Keith Packard + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of Keith Packard not be used in + * advertising or publicity pertaining to distribution of the software without + * specific, written prior permission. Keith Packard makes no + * representations about the suitability of this software for any purpose. It + * is provided "as is" without express or implied warranty. + * + * KEITH PACKARD DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, + * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO + * EVENT SHALL KEITH PACKARD 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. + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "Xrenderint.h" + +#define NLOCAL 256 + +void +XRenderAddTraps (Display *dpy, + Picture picture, + int xOff, + int yOff, + _Xconst XTrap *traps, + int ntrap) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderAddTrapsReq *req; + int n; + long len; + unsigned long max_req = dpy->bigreq_size ? dpy->bigreq_size : dpy->max_request_size; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + while (ntrap) + { + GetReq(RenderAddTraps, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderAddTraps; + req->picture = picture; + req->xOff = xOff; + req->yOff = yOff; + n = ntrap; + len = ((long) n) * (SIZEOF (xTrap) >> 2); + if (len > (max_req - req->length)) { + n = (max_req - req->length) / (SIZEOF (xTrap) >> 2); + len = ((long)n) * (SIZEOF (xTrap) >> 2); + } + SetReqLen (req, len, len); + len <<= 2; + DataInt32 (dpy, (int *) traps, len); + ntrap -= n; + traps += n; + } + UnlockDisplay(dpy); + SyncHandle(); +} diff --git a/libXrender/src/Color.c b/libXrender/src/Color.c new file mode 100644 index 000000000..4f934f038 --- /dev/null +++ b/libXrender/src/Color.c @@ -0,0 +1,92 @@ +/* + * + * Copyright © 2002 Keith Packard + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of Keith Packard not be used in + * advertising or publicity pertaining to distribution of the software without + * specific, written prior permission. Keith Packard makes no + * representations about the suitability of this software for any purpose. It + * is provided "as is" without express or implied warranty. + * + * KEITH PACKARD DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, + * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO + * EVENT SHALL KEITH PACKARD 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. + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "Xrenderint.h" + +Status +XRenderParseColor(Display *dpy, char *spec, XRenderColor *def) +{ + + if (!strncmp (spec, "rgba:", 5)) + { + unsigned short elements[4]; + unsigned short *pShort; + int i, n; + char c; + + spec += 5; + /* + * Attempt to parse the value portion. + */ + pShort = elements; + for (i = 0; i < 4; i++, pShort++, spec++) { + n = 0; + *pShort = 0; + while (*spec != '/' && *spec != '\0') { + if (++n > 4) { + return 0; + } + c = *spec++; + *pShort <<= 4; + if (c >= '0' && c <= '9') + *pShort |= c - '0'; + /* assume string in lowercase + else if (c >= 'A' && c <= 'F') + *pShort |= c - ('A' - 10); + */ + else if (c >= 'a' && c <= 'f') + *pShort |= c - ('a' - 10); + else return 0; + } + if (n == 0) + return 0; + if (n < 4) { + *pShort = ((unsigned long)*pShort * 0xFFFF) / ((1 << n*4) - 1); + } + } + def->red = elements[0]; + def->green = elements[1]; + def->blue = elements[2]; + def->alpha = elements[3]; + } + else + { + XColor coreColor; + Colormap colormap; + + colormap = DefaultColormap (dpy, DefaultScreen (dpy)); + if (!XParseColor (dpy, colormap, spec, &coreColor)) + return 0; + def->red = coreColor.red; + def->green = coreColor.green; + def->blue = coreColor.blue; + def->alpha = 0xffff; + } + def->red = (def->red * def->alpha) / 65535; + def->green = (def->green * def->alpha) / 65535; + def->blue = (def->blue * def->alpha) / 65535; + return 1; +} diff --git a/libXrender/src/Composite.c b/libXrender/src/Composite.c new file mode 100644 index 000000000..07151ded9 --- /dev/null +++ b/libXrender/src/Composite.c @@ -0,0 +1,67 @@ +/* + * + * Copyright © 2000 SuSE, Inc. + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of SuSE not be used in advertising or + * publicity pertaining to distribution of the software without specific, + * written prior permission. SuSE makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * SuSE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL SuSE + * 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. + * + * Author: Keith Packard, SuSE, Inc. + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "Xrenderint.h" + +void +XRenderComposite (Display *dpy, + int op, + Picture src, + Picture mask, + Picture dst, + int src_x, + int src_y, + int mask_x, + int mask_y, + int dst_x, + int dst_y, + unsigned int width, + unsigned int height) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderCompositeReq *req; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + GetReq(RenderComposite, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderComposite; + req->op = (CARD8) op; + req->src = src; + req->mask = mask; + req->dst = dst; + req->xSrc = src_x; + req->ySrc = src_y; + req->xMask = mask_x; + req->yMask = mask_y; + req->xDst = dst_x; + req->yDst = dst_y; + req->width = width; + req->height = height; + UnlockDisplay(dpy); + SyncHandle(); +} diff --git a/libXrender/src/Cursor.c b/libXrender/src/Cursor.c new file mode 100644 index 000000000..2679a9eaa --- /dev/null +++ b/libXrender/src/Cursor.c @@ -0,0 +1,79 @@ +/* + * + * Copyright © 2002 Keith Packard + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of Keith Packard not be used in + * advertising or publicity pertaining to distribution of the software without + * specific, written prior permission. Keith Packard makes no + * representations about the suitability of this software for any purpose. It + * is provided "as is" without express or implied warranty. + * + * KEITH PACKARD DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, + * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO + * EVENT SHALL KEITH PACKARD 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. + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "Xrenderint.h" + +Cursor +XRenderCreateCursor (Display *dpy, + Picture source, + unsigned int x, + unsigned int y) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + Cursor cid; + xRenderCreateCursorReq *req; + + RenderCheckExtension (dpy, info, 0); + LockDisplay(dpy); + GetReq(RenderCreateCursor, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCreateCursor; + req->cid = cid = XAllocID (dpy); + req->src = source; + req->x = x; + req->y = y; + + UnlockDisplay(dpy); + SyncHandle(); + return cid; +} + +Cursor +XRenderCreateAnimCursor (Display *dpy, + int ncursor, + XAnimCursor *cursors) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + Cursor cid; + xRenderCreateAnimCursorReq *req; + long len; + + RenderCheckExtension (dpy, info, 0); + LockDisplay(dpy); + GetReq(RenderCreateAnimCursor, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCreateAnimCursor; + req->cid = cid = XAllocID (dpy); + + len = (long) ncursor * SIZEOF (xAnimCursorElt) >> 2; + SetReqLen (req, len, len); + len <<= 2; + Data32 (dpy, (long *) cursors, len); + + UnlockDisplay(dpy); + SyncHandle(); + return cid; +} diff --git a/libXrender/src/FillRect.c b/libXrender/src/FillRect.c new file mode 100644 index 000000000..319c35d57 --- /dev/null +++ b/libXrender/src/FillRect.c @@ -0,0 +1,106 @@ +/* + * + * Copyright © 2000 SuSE, Inc. + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of SuSE not be used in advertising or + * publicity pertaining to distribution of the software without specific, + * written prior permission. SuSE makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * SuSE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL SuSE + * 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. + * + * Author: Keith Packard, SuSE, Inc. + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "Xrenderint.h" + +/* precompute the maximum size of batching request allowed */ + +#define size (SIZEOF(xRenderFillRectanglesReq) + FRCTSPERBATCH * SIZEOF(xRectangle)) + +void +XRenderFillRectangle (Display *dpy, + int op, + Picture dst, + _Xconst XRenderColor *color, + int x, + int y, + unsigned int width, + unsigned int height) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRectangle *rect; + xRenderFillRectanglesReq *req; +#ifdef MUSTCOPY + xRectangle rectdata; + long len = SIZEOF(xRectangle); + + rect = &rectdata; +#endif /* MUSTCOPY */ + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + + req = (xRenderFillRectanglesReq *) dpy->last_req; + /* if same as previous request, with same drawable, batch requests */ + if (req->reqType == info->codes->major_opcode && + req->renderReqType == X_RenderFillRectangles && + req->op == op && + req->dst == dst && + req->color.red == color->red && + req->color.green == color->green && + req->color.blue == color->blue && + req->color.alpha == color->alpha && + dpy->bufptr + SIZEOF(xRectangle) <= dpy->bufmax && + (char *)dpy->bufptr - (char *)req < size) + { + req->length += SIZEOF(xRectangle) >> 2; +#ifndef MUSTCOPY + rect = (xRectangle *) dpy->bufptr; + dpy->bufptr += SIZEOF(xRectangle); +#endif /* not MUSTCOPY */ + } + else + { + GetReqExtra(RenderFillRectangles, SIZEOF(xRectangle), req); + + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderFillRectangles; + req->op = op; + req->dst = dst; + req->color.red = color->red; + req->color.green = color->green; + req->color.blue = color->blue; + req->color.alpha = color->alpha; + +#ifdef MUSTCOPY + dpy->bufptr -= SIZEOF(xRectangle); +#else + rect = (xRectangle *) NEXTPTR(req,xRenderFillRectanglesReq); +#endif /* MUSTCOPY */ + } + rect->x = x; + rect->y = y; + rect->width = width; + rect->height = height; + +#ifdef MUSTCOPY + Data (dpy, (char *) rect, len); +#endif /* MUSTCOPY */ + UnlockDisplay(dpy); + SyncHandle(); +} + diff --git a/libXrender/src/FillRects.c b/libXrender/src/FillRects.c new file mode 100644 index 000000000..517eeb0dc --- /dev/null +++ b/libXrender/src/FillRects.c @@ -0,0 +1,79 @@ +/* + * + * Copyright © 2000 SuSE, Inc. + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of SuSE not be used in advertising or + * publicity pertaining to distribution of the software without specific, + * written prior permission. SuSE makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * SuSE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL SuSE + * 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. + * + * Author: Keith Packard, SuSE, Inc. + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "Xrenderint.h" + +/* precompute the maximum size of batching request allowed */ + +#define size (SIZEOF(xRenderFillRectanglesReq) + FRCTSPERBATCH * SIZEOF(xRectangle)) + +void +XRenderFillRectangles (Display *dpy, + int op, + Picture dst, + _Xconst XRenderColor *color, + _Xconst XRectangle *rectangles, + int n_rects) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderFillRectanglesReq *req; + long len; + int n; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + + while (n_rects) + { + GetReq(RenderFillRectangles, req); + + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderFillRectangles; + req->op = op; + req->dst = dst; + req->color.red = color->red; + req->color.green = color->green; + req->color.blue = color->blue; + req->color.alpha = color->alpha; + + n = n_rects; + len = ((long)n) << 1; + if (!dpy->bigreq_size && len > (dpy->max_request_size - req->length)) + { + n = (dpy->max_request_size - req->length) >> 1; + len = ((long)n) << 1; + } + SetReqLen(req, len, len); + len <<= 2; /* watch out for macros... */ + Data16 (dpy, (short *) rectangles, len); + n_rects -= n; + rectangles += n; + } + UnlockDisplay(dpy); + SyncHandle(); +} + diff --git a/libXrender/src/Filter.c b/libXrender/src/Filter.c new file mode 100644 index 000000000..3ac660a40 --- /dev/null +++ b/libXrender/src/Filter.c @@ -0,0 +1,153 @@ +/* + * + * Copyright © 2002 Keith Packard + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of Keith Packard not be used in + * advertising or publicity pertaining to distribution of the software without + * specific, written prior permission. Keith Packard makes no + * representations about the suitability of this software for any purpose. It + * is provided "as is" without express or implied warranty. + * + * KEITH PACKARD DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, + * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO + * EVENT SHALL KEITH PACKARD 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. + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "Xrenderint.h" + +XFilters * +XRenderQueryFilters (Display *dpy, Drawable drawable) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + XRenderInfo *xri; + xRenderQueryFiltersReq *req; + xRenderQueryFiltersReply rep; + XFilters *filters; + char *name; + char len; + int i; + long nbytes, nbytesAlias, nbytesName; + + if (!RenderHasExtension (info)) + return NULL; + + if (!XRenderQueryFormats (dpy)) + return NULL; + + xri = info->info; + if (xri->minor_version < 6) + return NULL; + + LockDisplay (dpy); + GetReq (RenderQueryFilters, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderQueryFilters; + req->drawable = drawable; + if (!_XReply (dpy, (xReply *) &rep, 0, xFalse)) + { + UnlockDisplay (dpy); + SyncHandle (); + return NULL; + } + /* + * Compute total number of bytes for filter names + */ + nbytes = (long)rep.length << 2; + nbytesAlias = rep.numAliases * 2; + if (rep.numAliases & 1) + nbytesAlias += 2; + nbytesName = nbytes - nbytesAlias; + + /* + * Allocate one giant block for the whole data structure + */ + filters = Xmalloc (sizeof (XFilters) + + rep.numFilters * sizeof (char *) + + rep.numAliases * sizeof (short) + + nbytesName); + + if (!filters) + { + _XEatData (dpy, (unsigned long) rep.length << 2); + UnlockDisplay (dpy); + SyncHandle (); + return NULL; + } + + /* + * Layout: + * XFilters + * numFilters char * pointers to filter names + * numAliases short alias values + * nbytesName char strings + */ + + filters->nfilter = rep.numFilters; + filters->nalias = rep.numAliases; + filters->filter = (char **) (filters + 1); + filters->alias = (short *) (filters->filter + rep.numFilters); + name = (char *) (filters->alias + rep.numAliases); + + /* + * Read the filter aliases + */ + _XRead16Pad (dpy, filters->alias, 2 * rep.numAliases); + + /* + * Read the filter names + */ + for (i = 0; i < rep.numFilters; i++) + { + int l; + _XRead (dpy, &len, 1); + l = len & 0xff; + filters->filter[i] = name; + _XRead (dpy, name, l); + name[l] = '\0'; + name += l + 1; + } + i = name - (char *) (filters->alias + rep.numAliases); + + if (i & 3) + _XEatData (dpy, 4 - (i & 3)); + + UnlockDisplay (dpy); + SyncHandle (); + return filters; +} + +void +XRenderSetPictureFilter (Display *dpy, + Picture picture, + const char *filter, + XFixed *params, + int nparams) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderSetPictureFilterReq *req; + int nbytes = strlen (filter); + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + GetReq(RenderSetPictureFilter, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderSetPictureFilter; + req->picture = picture; + req->nbytes = nbytes; + req->length += ((nbytes + 3) >> 2) + nparams; + Data (dpy, filter, nbytes); + Data (dpy, (_Xconst char *)params, nparams << 2); + UnlockDisplay(dpy); + SyncHandle(); +} diff --git a/libXrender/src/Glyph.c b/libXrender/src/Glyph.c new file mode 100644 index 000000000..894bb77f2 --- /dev/null +++ b/libXrender/src/Glyph.c @@ -0,0 +1,712 @@ +/* + * + * Copyright © 2000 SuSE, Inc. + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of SuSE not be used in advertising or + * publicity pertaining to distribution of the software without specific, + * written prior permission. SuSE makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * SuSE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL SuSE + * 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. + * + * Author: Keith Packard, SuSE, Inc. + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "Xrenderint.h" + +GlyphSet +XRenderCreateGlyphSet (Display *dpy, _Xconst XRenderPictFormat *format) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + GlyphSet gsid; + xRenderCreateGlyphSetReq *req; + + RenderCheckExtension (dpy, info, 0); + LockDisplay(dpy); + GetReq(RenderCreateGlyphSet, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCreateGlyphSet; + req->gsid = gsid = XAllocID(dpy); + req->format = format->id; + UnlockDisplay(dpy); + SyncHandle(); + return gsid; +} + +GlyphSet +XRenderReferenceGlyphSet (Display *dpy, GlyphSet existing) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + GlyphSet gsid; + xRenderReferenceGlyphSetReq *req; + + RenderCheckExtension (dpy, info, 0); + LockDisplay(dpy); + GetReq(RenderReferenceGlyphSet, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderReferenceGlyphSet; + req->gsid = gsid = XAllocID(dpy); + req->existing = existing; + UnlockDisplay(dpy); + SyncHandle(); + return gsid; +} + +void +XRenderFreeGlyphSet (Display *dpy, GlyphSet glyphset) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderFreeGlyphSetReq *req; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + GetReq(RenderFreeGlyphSet, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderFreeGlyphSet; + req->glyphset = glyphset; + UnlockDisplay(dpy); + SyncHandle(); +} + +void +XRenderAddGlyphs (Display *dpy, + GlyphSet glyphset, + _Xconst Glyph *gids, + _Xconst XGlyphInfo *glyphs, + int nglyphs, + _Xconst char *images, + int nbyte_images) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderAddGlyphsReq *req; + long len; + + if (nbyte_images & 3) + nbyte_images += 4 - (nbyte_images & 3); + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + GetReq(RenderAddGlyphs, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderAddGlyphs; + req->glyphset = glyphset; + req->nglyphs = nglyphs; + len = (nglyphs * (SIZEOF (xGlyphInfo) + 4) + nbyte_images) >> 2; + SetReqLen(req, len, len); + Data32 (dpy, (long *) gids, nglyphs * 4); + Data16 (dpy, (short *) glyphs, nglyphs * SIZEOF (xGlyphInfo)); + Data (dpy, images, nbyte_images); + UnlockDisplay(dpy); + SyncHandle(); +} + +void +XRenderFreeGlyphs (Display *dpy, + GlyphSet glyphset, + _Xconst Glyph *gids, + int nglyphs) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderFreeGlyphsReq *req; + long len; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + GetReq(RenderFreeGlyphs, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderFreeGlyphs; + req->glyphset = glyphset; + len = nglyphs; + SetReqLen(req, len, len); + len <<= 2; + Data32 (dpy, (long *) gids, len); + UnlockDisplay(dpy); + SyncHandle(); +} + +void +XRenderCompositeString8 (Display *dpy, + int op, + Picture src, + Picture dst, + _Xconst XRenderPictFormat *maskFormat, + GlyphSet glyphset, + int xSrc, + int ySrc, + int xDst, + int yDst, + _Xconst char *string, + int nchar) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderCompositeGlyphs8Req *req; + long len; + xGlyphElt *elt; + int nbytes; + + if (!nchar) + return; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + + GetReq(RenderCompositeGlyphs8, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCompositeGlyphs8; + req->op = op; + req->src = src; + req->dst = dst; + req->maskFormat = maskFormat ? maskFormat->id : None; + req->glyphset = glyphset; + req->xSrc = xSrc; + req->ySrc = ySrc; + + /* + * xGlyphElt must be aligned on a 32-bit boundary; this is + * easily done by filling no more than 252 glyphs in each + * bucket + */ + +#define MAX_8 252 + + len = SIZEOF(xGlyphElt) * ((nchar + MAX_8-1) / MAX_8) + nchar; + + req->length += (len + 3)>>2; /* convert to number of 32-bit words */ + + /* + * If the entire request does not fit into the remaining space in the + * buffer, flush the buffer first. + */ + + if (dpy->bufptr + len > dpy->bufmax) + _XFlush (dpy); + + while(nchar > MAX_8) + { + nbytes = MAX_8 + SIZEOF(xGlyphElt); + BufAlloc (xGlyphElt *, elt, nbytes); + elt->len = MAX_8; + elt->deltax = xDst; + elt->deltay = yDst; + xDst = 0; + yDst = 0; + memcpy ((char *) (elt + 1), string, MAX_8); + nchar = nchar - MAX_8; + string += MAX_8; + } + + if (nchar) + { + nbytes = (nchar + SIZEOF(xGlyphElt) + 3) & ~3; + BufAlloc (xGlyphElt *, elt, nbytes); + elt->len = nchar; + elt->deltax = xDst; + elt->deltay = yDst; + memcpy ((char *) (elt + 1), string, nchar); + } +#undef MAX_8 + + UnlockDisplay(dpy); + SyncHandle(); +} +void +XRenderCompositeString16 (Display *dpy, + int op, + Picture src, + Picture dst, + _Xconst XRenderPictFormat *maskFormat, + GlyphSet glyphset, + int xSrc, + int ySrc, + int xDst, + int yDst, + _Xconst unsigned short *string, + int nchar) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderCompositeGlyphs8Req *req; + long len; + xGlyphElt *elt; + int nbytes; + + if (!nchar) + return; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + + GetReq(RenderCompositeGlyphs16, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCompositeGlyphs16; + req->op = op; + req->src = src; + req->dst = dst; + req->maskFormat = maskFormat ? maskFormat->id : None; + req->glyphset = glyphset; + req->xSrc = xSrc; + req->ySrc = ySrc; + +#define MAX_16 254 + + len = SIZEOF(xGlyphElt) * ((nchar + MAX_16-1) / MAX_16) + nchar * 2; + + req->length += (len + 3)>>2; /* convert to number of 32-bit words */ + + /* + * If the entire request does not fit into the remaining space in the + * buffer, flush the buffer first. + */ + + if (dpy->bufptr + len > dpy->bufmax) + _XFlush (dpy); + + while(nchar > MAX_16) + { + nbytes = MAX_16 * 2 + SIZEOF(xGlyphElt); + BufAlloc (xGlyphElt *, elt, nbytes); + elt->len = MAX_16; + elt->deltax = xDst; + elt->deltay = yDst; + xDst = 0; + yDst = 0; + memcpy ((char *) (elt + 1), (char *) string, MAX_16 * 2); + nchar = nchar - MAX_16; + string += MAX_16; + } + + if (nchar) + { + nbytes = (nchar * 2 + SIZEOF(xGlyphElt) + 3) & ~3; + BufAlloc (xGlyphElt *, elt, nbytes); + elt->len = nchar; + elt->deltax = xDst; + elt->deltay = yDst; + memcpy ((char *) (elt + 1), (char *) string, nchar * 2); + } +#undef MAX_16 + + UnlockDisplay(dpy); + SyncHandle(); +} + +void +XRenderCompositeString32 (Display *dpy, + int op, + Picture src, + Picture dst, + _Xconst XRenderPictFormat *maskFormat, + GlyphSet glyphset, + int xSrc, + int ySrc, + int xDst, + int yDst, + _Xconst unsigned int *string, + int nchar) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderCompositeGlyphs8Req *req; + long len; + xGlyphElt *elt; + int nbytes; + + if (!nchar) + return; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + + GetReq(RenderCompositeGlyphs32, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCompositeGlyphs32; + req->op = op; + req->src = src; + req->dst = dst; + req->maskFormat = maskFormat ? maskFormat->id : None; + req->glyphset = glyphset; + req->xSrc = xSrc; + req->ySrc = ySrc; + +#define MAX_32 254 + + len = SIZEOF(xGlyphElt) * ((nchar + MAX_32-1) / MAX_32) + nchar * 4; + + req->length += (len + 3)>>2; /* convert to number of 32-bit words */ + + /* + * If the entire request does not fit into the remaining space in the + * buffer, flush the buffer first. + */ + + if (dpy->bufptr + len > dpy->bufmax) + _XFlush (dpy); + + while(nchar > MAX_32) + { + nbytes = MAX_32 * 4 + SIZEOF(xGlyphElt); + BufAlloc (xGlyphElt *, elt, nbytes); + elt->len = MAX_32; + elt->deltax = xDst; + elt->deltay = yDst; + xDst = 0; + yDst = 0; + memcpy ((char *) (elt + 1), (char *) string, MAX_32 * 4); + nchar = nchar - MAX_32; + string += MAX_32; + } + + if (nchar) + { + nbytes = nchar * 4 + SIZEOF(xGlyphElt); + BufAlloc (xGlyphElt *, elt, nbytes); + elt->len = nchar; + elt->deltax = xDst; + elt->deltay = yDst; + memcpy ((char *) (elt + 1), (char *) string, nchar * 4); + } +#undef MAX_32 + + UnlockDisplay(dpy); + SyncHandle(); +} + +void +XRenderCompositeText8 (Display *dpy, + int op, + Picture src, + Picture dst, + _Xconst XRenderPictFormat *maskFormat, + int xSrc, + int ySrc, + int xDst, + int yDst, + _Xconst XGlyphElt8 *elts, + int nelt) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderCompositeGlyphs8Req *req; + GlyphSet glyphset; + long len; + long elen; + xGlyphElt *elt; + int i; + _Xconst char *chars; + int nchars; + + if (!nelt) + return; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + + GetReq(RenderCompositeGlyphs8, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCompositeGlyphs8; + req->op = op; + req->src = src; + req->dst = dst; + req->maskFormat = maskFormat ? maskFormat->id : None; + req->glyphset = elts[0].glyphset; + req->xSrc = xSrc; + req->ySrc = ySrc; + + /* + * Compute the space necessary + */ + len = 0; + +#define MAX_8 252 + + glyphset = elts[0].glyphset; + for (i = 0; i < nelt; i++) + { + /* + * Check for glyphset change + */ + if (elts[i].glyphset != glyphset) + { + glyphset = elts[i].glyphset; + len += (SIZEOF (xGlyphElt) + 4) >> 2; + } + nchars = elts[i].nchars; + /* + * xGlyphElt must be aligned on a 32-bit boundary; this is + * easily done by filling no more than 252 glyphs in each + * bucket + */ + elen = SIZEOF(xGlyphElt) * ((nchars + MAX_8-1) / MAX_8) + nchars; + len += (elen + 3) >> 2; + } + + req->length += len; + + /* + * Send the glyphs + */ + glyphset = elts[0].glyphset; + for (i = 0; i < nelt; i++) + { + /* + * Switch glyphsets + */ + if (elts[i].glyphset != glyphset) + { + glyphset = elts[i].glyphset; + BufAlloc (xGlyphElt *, elt, SIZEOF (xGlyphElt)); + elt->len = 0xff; + elt->deltax = 0; + elt->deltay = 0; + Data32(dpy, &glyphset, 4); + } + nchars = elts[i].nchars; + xDst = elts[i].xOff; + yDst = elts[i].yOff; + chars = elts[i].chars; + while (nchars) + { + int this_chars = nchars > MAX_8 ? MAX_8 : nchars; + + BufAlloc (xGlyphElt *, elt, SIZEOF(xGlyphElt)) + elt->len = this_chars; + elt->deltax = xDst; + elt->deltay = yDst; + xDst = 0; + yDst = 0; + Data (dpy, chars, this_chars); + nchars -= this_chars; + chars += this_chars; + } + } +#undef MAX_8 + + UnlockDisplay(dpy); + SyncHandle(); +} + +void +XRenderCompositeText16 (Display *dpy, + int op, + Picture src, + Picture dst, + _Xconst XRenderPictFormat *maskFormat, + int xSrc, + int ySrc, + int xDst, + int yDst, + _Xconst XGlyphElt16 *elts, + int nelt) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderCompositeGlyphs16Req *req; + GlyphSet glyphset; + long len; + long elen; + xGlyphElt *elt; + int i; + _Xconst unsigned short *chars; + int nchars; + + if (!nelt) + return; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + + GetReq(RenderCompositeGlyphs16, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCompositeGlyphs16; + req->op = op; + req->src = src; + req->dst = dst; + req->maskFormat = maskFormat ? maskFormat->id : None; + req->glyphset = elts[0].glyphset; + req->xSrc = xSrc; + req->ySrc = ySrc; + + /* + * Compute the space necessary + */ + len = 0; + +#define MAX_16 254 + + glyphset = elts[0].glyphset; + for (i = 0; i < nelt; i++) + { + /* + * Check for glyphset change + */ + if (elts[i].glyphset != glyphset) + { + glyphset = elts[i].glyphset; + len += (SIZEOF (xGlyphElt) + 4) >> 2; + } + nchars = elts[i].nchars; + /* + * xGlyphElt must be aligned on a 32-bit boundary; this is + * easily done by filling no more than 254 glyphs in each + * bucket + */ + elen = SIZEOF(xGlyphElt) * ((nchars + MAX_16-1) / MAX_16) + nchars * 2; + len += (elen + 3) >> 2; + } + + req->length += len; + + glyphset = elts[0].glyphset; + for (i = 0; i < nelt; i++) + { + /* + * Switch glyphsets + */ + if (elts[i].glyphset != glyphset) + { + glyphset = elts[i].glyphset; + BufAlloc (xGlyphElt *, elt, SIZEOF (xGlyphElt)); + elt->len = 0xff; + elt->deltax = 0; + elt->deltay = 0; + Data32(dpy, &glyphset, 4); + } + nchars = elts[i].nchars; + xDst = elts[i].xOff; + yDst = elts[i].yOff; + chars = elts[i].chars; + while (nchars) + { + int this_chars = nchars > MAX_16 ? MAX_16 : nchars; + int this_bytes = this_chars * 2; + + BufAlloc (xGlyphElt *, elt, SIZEOF(xGlyphElt)) + elt->len = this_chars; + elt->deltax = xDst; + elt->deltay = yDst; + xDst = 0; + yDst = 0; + Data16 (dpy, chars, this_bytes); + nchars -= this_chars; + chars += this_chars; + } + } +#undef MAX_16 + + UnlockDisplay(dpy); + SyncHandle(); +} + +void +XRenderCompositeText32 (Display *dpy, + int op, + Picture src, + Picture dst, + _Xconst XRenderPictFormat *maskFormat, + int xSrc, + int ySrc, + int xDst, + int yDst, + _Xconst XGlyphElt32 *elts, + int nelt) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderCompositeGlyphs32Req *req; + GlyphSet glyphset; + long len; + long elen; + xGlyphElt *elt; + int i; + _Xconst unsigned int *chars; + int nchars; + + if (!nelt) + return; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + + + GetReq(RenderCompositeGlyphs32, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCompositeGlyphs32; + req->op = op; + req->src = src; + req->dst = dst; + req->maskFormat = maskFormat ? maskFormat->id : None; + req->glyphset = elts[0].glyphset; + req->xSrc = xSrc; + req->ySrc = ySrc; + + /* + * Compute the space necessary + */ + len = 0; + +#define MAX_32 254 + + glyphset = elts[0].glyphset; + for (i = 0; i < nelt; i++) + { + /* + * Check for glyphset change + */ + if (elts[i].glyphset != glyphset) + { + glyphset = elts[i].glyphset; + len += (SIZEOF (xGlyphElt) + 4) >> 2; + } + nchars = elts[i].nchars; + elen = SIZEOF(xGlyphElt) * ((nchars + MAX_32) / MAX_32) + nchars *4; + len += (elen + 3) >> 2; + } + + req->length += len; + + glyphset = elts[0].glyphset; + for (i = 0; i < nelt; i++) + { + /* + * Switch glyphsets + */ + if (elts[i].glyphset != glyphset) + { + glyphset = elts[i].glyphset; + BufAlloc (xGlyphElt *, elt, SIZEOF (xGlyphElt)); + elt->len = 0xff; + elt->deltax = 0; + elt->deltay = 0; + Data32(dpy, &glyphset, 4); + } + nchars = elts[i].nchars; + xDst = elts[i].xOff; + yDst = elts[i].yOff; + chars = elts[i].chars; + while (nchars) + { + int this_chars = nchars > MAX_32 ? MAX_32 : nchars; + int this_bytes = this_chars * 4; + BufAlloc (xGlyphElt *, elt, SIZEOF(xGlyphElt)) + elt->len = this_chars; + elt->deltax = xDst; + elt->deltay = yDst; + xDst = 0; + yDst = 0; + DataInt32 (dpy, chars, this_bytes); + nchars -= this_chars; + chars += this_chars; + } + } +#undef MAX_32 + + UnlockDisplay(dpy); + SyncHandle(); +} diff --git a/libXrender/src/Makefile.am b/libXrender/src/Makefile.am new file mode 100644 index 000000000..7474b43a8 --- /dev/null +++ b/libXrender/src/Makefile.am @@ -0,0 +1,27 @@ +AM_CFLAGS = $(CWARNFLAGS) $(RENDER_CFLAGS) $(MALLOC_ZERO_CFLAGS) +AM_CPPFLAGS = -I$(top_srcdir) -I$(top_srcdir)/include/X11/extensions + +lib_LTLIBRARIES = libXrender.la + +libXrender_la_SOURCES = AddTrap.c \ + Color.c \ + Composite.c \ + Cursor.c \ + FillRect.c \ + FillRects.c \ + Filter.c \ + Glyph.c \ + Picture.c \ + Poly.c \ + Trap.c \ + Tri.c \ + Xrender.c \ + Xrenderint.h + +libXrender_la_LIBADD = $(RENDER_LIBS) + +# -version-number requires libtool >= 1.5 +libXrender_la_LDFLAGS = -version-number 1:3:0 -no-undefined + +libXrenderincludedir = $(includedir)/X11/extensions +libXrenderinclude_HEADERS = $(top_srcdir)/include/X11/extensions/Xrender.h diff --git a/libXrender/src/Picture.c b/libXrender/src/Picture.c new file mode 100644 index 000000000..509a83580 --- /dev/null +++ b/libXrender/src/Picture.c @@ -0,0 +1,372 @@ +/* + * + * Copyright © 2000 SuSE, Inc. + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of SuSE not be used in advertising or + * publicity pertaining to distribution of the software without specific, + * written prior permission. SuSE makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * SuSE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL SuSE + * 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. + * + * Author: Keith Packard, SuSE, Inc. + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "Xrenderint.h" +#include <X11/Xregion.h> + +static void +_XRenderProcessPictureAttributes (Display *dpy, + xRenderChangePictureReq *req, + unsigned long valuemask, + _Xconst XRenderPictureAttributes *attributes) +{ + unsigned long values[32]; + register unsigned long *value = values; + unsigned int nvalues; + + if (valuemask & CPRepeat) + *value++ = attributes->repeat; + if (valuemask & CPAlphaMap) + *value++ = attributes->alpha_map; + if (valuemask & CPAlphaXOrigin) + *value++ = attributes->alpha_x_origin; + if (valuemask & CPAlphaYOrigin) + *value++ = attributes->alpha_y_origin; + if (valuemask & CPClipXOrigin) + *value++ = attributes->clip_x_origin; + if (valuemask & CPClipYOrigin) + *value++ = attributes->clip_y_origin; + if (valuemask & CPClipMask) + *value++ = attributes->clip_mask; + if (valuemask & CPGraphicsExposure) + *value++ = attributes->graphics_exposures; + if (valuemask & CPSubwindowMode) + *value++ = attributes->subwindow_mode; + if (valuemask & CPPolyEdge) + *value++ = attributes->poly_edge; + if (valuemask & CPPolyMode) + *value++ = attributes->poly_mode; + if (valuemask & CPDither) + *value++ = attributes->dither; + if (valuemask & CPComponentAlpha) + *value++ = attributes->component_alpha; + + req->length += (nvalues = value - values); + + nvalues <<= 2; /* watch out for macros... */ + Data32 (dpy, (long *) values, (long)nvalues); +} + +Picture +XRenderCreatePicture (Display *dpy, + Drawable drawable, + _Xconst XRenderPictFormat *format, + unsigned long valuemask, + _Xconst XRenderPictureAttributes *attributes) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + Picture pid; + xRenderCreatePictureReq *req; + + RenderCheckExtension (dpy, info, 0); + LockDisplay(dpy); + GetReq(RenderCreatePicture, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCreatePicture; + req->pid = pid = XAllocID(dpy); + req->drawable = drawable; + req->format = format->id; + if ((req->mask = valuemask)) + _XRenderProcessPictureAttributes (dpy, + (xRenderChangePictureReq *) req, + valuemask, + attributes); + UnlockDisplay(dpy); + SyncHandle(); + return pid; +} + +void +XRenderChangePicture (Display *dpy, + Picture picture, + unsigned long valuemask, + _Xconst XRenderPictureAttributes *attributes) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderChangePictureReq *req; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + GetReq(RenderChangePicture, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderChangePicture; + req->picture = picture; + req->mask = valuemask; + _XRenderProcessPictureAttributes (dpy, + req, + valuemask, + attributes); + UnlockDisplay(dpy); + SyncHandle(); +} + +static void +_XRenderSetPictureClipRectangles (Display *dpy, + XRenderExtDisplayInfo *info, + Picture picture, + int xOrigin, + int yOrigin, + _Xconst XRectangle *rects, + int n) +{ + xRenderSetPictureClipRectanglesReq *req; + long len; + + GetReq (RenderSetPictureClipRectangles, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderSetPictureClipRectangles; + req->picture = picture; + req->xOrigin = xOrigin; + req->yOrigin = yOrigin; + len = ((long) n) << 1; + SetReqLen (req, len, 1); + len <<= 2; + Data16 (dpy, (short *) rects, len); +} + +void +XRenderSetPictureClipRectangles (Display *dpy, + Picture picture, + int xOrigin, + int yOrigin, + _Xconst XRectangle *rects, + int n) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + _XRenderSetPictureClipRectangles (dpy, info, picture, + xOrigin, yOrigin, rects, n); + UnlockDisplay (dpy); + SyncHandle (); +} + +void +XRenderSetPictureClipRegion (Display *dpy, + Picture picture, + Region r) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + int i; + XRectangle *xr, *pr; + BOX *pb; + unsigned long total; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + total = r->numRects * sizeof (XRectangle); + if ((xr = (XRectangle *) _XAllocTemp(dpy, total))) { + for (pr = xr, pb = r->rects, i = r->numRects; --i >= 0; pr++, pb++) { + pr->x = pb->x1; + pr->y = pb->y1; + pr->width = pb->x2 - pb->x1; + pr->height = pb->y2 - pb->y1; + } + } + if (xr || !r->numRects) + _XRenderSetPictureClipRectangles (dpy, info, picture, 0, 0, + xr, r->numRects); + if (xr) + _XFreeTemp(dpy, (char *)xr, total); + UnlockDisplay(dpy); + SyncHandle(); +} + +void +XRenderSetPictureTransform (Display *dpy, + Picture picture, + XTransform *transform) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderSetPictureTransformReq *req; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay (dpy); + GetReq(RenderSetPictureTransform, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderSetPictureTransform; + req->picture = picture; + req->transform.matrix11 = transform->matrix[0][0]; + req->transform.matrix12 = transform->matrix[0][1]; + req->transform.matrix13 = transform->matrix[0][2]; + req->transform.matrix21 = transform->matrix[1][0]; + req->transform.matrix22 = transform->matrix[1][1]; + req->transform.matrix23 = transform->matrix[1][2]; + req->transform.matrix31 = transform->matrix[2][0]; + req->transform.matrix32 = transform->matrix[2][1]; + req->transform.matrix33 = transform->matrix[2][2]; + UnlockDisplay(dpy); + SyncHandle(); + +} + +void +XRenderFreePicture (Display *dpy, + Picture picture) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderFreePictureReq *req; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + GetReq(RenderFreePicture, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderFreePicture; + req->picture = picture; + UnlockDisplay(dpy); + SyncHandle(); +} + + +Picture XRenderCreateSolidFill(Display *dpy, + const XRenderColor *color) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + Picture pid; + xRenderCreateSolidFillReq *req; + + RenderCheckExtension (dpy, info, 0); + LockDisplay(dpy); + GetReq(RenderCreateSolidFill, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCreateSolidFill; + + req->pid = pid = XAllocID(dpy); + req->color.red = color->red; + req->color.green = color->green; + req->color.blue = color->blue; + req->color.alpha = color->alpha; + + UnlockDisplay(dpy); + SyncHandle(); + return pid; +} + + +Picture XRenderCreateLinearGradient(Display *dpy, + const XLinearGradient *gradient, + const XFixed *stops, + const XRenderColor *colors, + int nStops) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + Picture pid; + xRenderCreateLinearGradientReq *req; + long len; + + RenderCheckExtension (dpy, info, 0); + LockDisplay(dpy); + GetReq(RenderCreateLinearGradient, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCreateLinearGradient; + + req->pid = pid = XAllocID(dpy); + req->p1.x = gradient->p1.x; + req->p1.y = gradient->p1.y; + req->p2.x = gradient->p2.x; + req->p2.y = gradient->p2.y; + + req->nStops = nStops; + len = (long) nStops * 3; + SetReqLen (req, len, 6); + DataInt32(dpy, stops, nStops * 4); + Data16(dpy, colors, nStops * 8); + + UnlockDisplay(dpy); + SyncHandle(); + return pid; +} + +Picture XRenderCreateRadialGradient(Display *dpy, + const XRadialGradient *gradient, + const XFixed *stops, + const XRenderColor *colors, + int nStops) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + Picture pid; + xRenderCreateRadialGradientReq *req; + long len; + + RenderCheckExtension (dpy, info, 0); + LockDisplay(dpy); + GetReq(RenderCreateRadialGradient, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCreateRadialGradient; + + req->pid = pid = XAllocID(dpy); + req->inner.x = gradient->inner.x; + req->inner.y = gradient->inner.y; + req->outer.x = gradient->outer.x; + req->outer.y = gradient->outer.y; + req->inner_radius = gradient->inner.radius; + req->outer_radius = gradient->outer.radius; + + req->nStops = nStops; + len = (long) nStops * 3; + SetReqLen (req, len, 6); + DataInt32(dpy, stops, nStops * 4); + Data16(dpy, colors, nStops * 8); + + UnlockDisplay(dpy); + SyncHandle(); + return pid; +} + +Picture XRenderCreateConicalGradient(Display *dpy, + const XConicalGradient *gradient, + const XFixed *stops, + const XRenderColor *colors, + int nStops) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + Picture pid; + xRenderCreateConicalGradientReq *req; + long len; + + RenderCheckExtension (dpy, info, 0); + LockDisplay(dpy); + GetReq(RenderCreateConicalGradient, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderCreateConicalGradient; + + req->pid = pid = XAllocID(dpy); + req->center.x = gradient->center.x; + req->center.y = gradient->center.y; + req->angle = gradient->angle; + + req->nStops = nStops; + len = (long) nStops * 3; + SetReqLen (req, len, 6); + DataInt32(dpy, stops, nStops * 4); + Data16(dpy, colors, nStops * 8); + + UnlockDisplay(dpy); + SyncHandle(); + return pid; +} diff --git a/libXrender/src/Poly.c b/libXrender/src/Poly.c new file mode 100644 index 000000000..16599b22e --- /dev/null +++ b/libXrender/src/Poly.c @@ -0,0 +1,302 @@ +/* + * + * Copyright © 2002 Keith Packard + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of Keith Packard not be used in + * advertising or publicity pertaining to distribution of the software without + * specific, written prior permission. Keith Packard makes no + * representations about the suitability of this software for any purpose. It + * is provided "as is" without express or implied warranty. + * + * KEITH PACKARD DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, + * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO + * EVENT SHALL KEITH PACKARD 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. + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "Xrenderint.h" + +typedef struct _Edge Edge; + +struct _Edge { + XLineFixed edge; + XFixed current_x; + Bool clockWise; + Edge *next, *prev; +}; + +static int +CompareEdge (const void *o1, const void *o2) +{ + const Edge *e1 = o1, *e2 = o2; + + return e1->edge.p1.y - e2->edge.p1.y; +} + +static XFixed +XRenderComputeX (XLineFixed *line, XFixed y) +{ + XFixed dx = line->p2.x - line->p1.x; + double ex = (double) (y - line->p1.y) * (double) dx; + XFixed dy = line->p2.y - line->p1.y; + + return (XFixed) line->p1.x + (XFixed) (ex / dy); +} + +static double +XRenderComputeInverseSlope (XLineFixed *l) +{ + return (XFixedToDouble (l->p2.x - l->p1.x) / + XFixedToDouble (l->p2.y - l->p1.y)); +} + +static double +XRenderComputeXIntercept (XLineFixed *l, double inverse_slope) +{ + return XFixedToDouble (l->p1.x) - inverse_slope * XFixedToDouble (l->p1.y); +} + +static XFixed +XRenderComputeIntersect (XLineFixed *l1, XLineFixed *l2) +{ + /* + * x = m1y + b1 + * x = m2y + b2 + * m1y + b1 = m2y + b2 + * y * (m1 - m2) = b2 - b1 + * y = (b2 - b1) / (m1 - m2) + */ + double m1 = XRenderComputeInverseSlope (l1); + double b1 = XRenderComputeXIntercept (l1, m1); + double m2 = XRenderComputeInverseSlope (l2); + double b2 = XRenderComputeXIntercept (l2, m2); + + return XDoubleToFixed ((b2 - b1) / (m1 - m2)); +} + +static int +XRenderComputeTrapezoids (Edge *edges, + int nedges, + int winding, + XTrapezoid *traps) +{ + int ntraps = 0; + int inactive; + Edge *active; + Edge *e, *en, *next; + XFixed y, next_y, intersect; + + qsort (edges, nedges, sizeof (Edge), CompareEdge); + + y = edges[0].edge.p1.y; + active = NULL; + inactive = 0; + while (active || inactive < nedges) + { + /* insert new active edges into list */ + while (inactive < nedges) + { + e = &edges[inactive]; + if (e->edge.p1.y > y) + break; + /* move this edge into the active list */ + inactive++; + e->next = active; + e->prev = NULL; + if (active) + active->prev = e; + active = e; + } + /* compute x coordinates along this group */ + for (e = active; e; e = e->next) + e->current_x = XRenderComputeX (&e->edge, y); + + /* sort active list */ + for (e = active; e; e = next) + { + next = e->next; + /* + * Find one later in the list that belongs before the + * current one + */ + for (en = next; en; en = en->next) + { + if (en->current_x < e->current_x || + (en->current_x == e->current_x && + en->edge.p2.x < e->edge.p2.x)) + { + /* + * insert en before e + * + * extract en + */ + en->prev->next = en->next; + if (en->next) + en->next->prev = en->prev; + /* + * insert en + */ + if (e->prev) + e->prev->next = en; + else + active = en; + en->prev = e->prev; + e->prev = en; + en->next = e; + /* + * start over at en + */ + next = en; + break; + } + } + } +#if 0 + printf ("y: %6.3g:", y / 65536.0); + for (e = active; e; e = e->next) + { + printf (" %6.3g", e->current_x / 65536.0); + } + printf ("\n"); +#endif + /* find next inflection point */ + next_y = active->edge.p2.y; + for (e = active; e; e = en) + { + if (e->edge.p2.y < next_y) + next_y = e->edge.p2.y; + en = e->next; + /* check intersect */ + if (en && e->edge.p2.x > en->edge.p2.x) + { + intersect = XRenderComputeIntersect (&e->edge, &e->next->edge); + /* make sure this point is below the actual intersection */ + intersect = intersect + 1; + if (intersect < next_y) + next_y = intersect; + } + } + /* check next inactive point */ + if (inactive < nedges && edges[inactive].edge.p1.y < next_y) + next_y = edges[inactive].edge.p1.y; + + /* walk the list generating trapezoids */ + for (e = active; e && (en = e->next); e = en->next) + { + traps->top = y; + traps->bottom = next_y; + traps->left = e->edge; + traps->right = en->edge; + traps++; + ntraps++; + } + + y = next_y; + + /* delete inactive edges from list */ + for (e = active; e; e = next) + { + next = e->next; + if (e->edge.p2.y <= y) + { + if (e->prev) + e->prev->next = e->next; + else + active = e->next; + if (e->next) + e->next->prev = e->prev; + } + } + } + return ntraps; +} + +void +XRenderCompositeDoublePoly (Display *dpy, + int op, + Picture src, + Picture dst, + _Xconst XRenderPictFormat *maskFormat, + int xSrc, + int ySrc, + int xDst, + int yDst, + _Xconst XPointDouble *fpoints, + int npoints, + int winding) +{ + Edge *edges; + XTrapezoid *traps; + int i, nedges, ntraps; + XFixed x, y, prevx = 0, prevy = 0, firstx = 0, firsty = 0; + XFixed top = 0, bottom = 0; /* GCCism */ + + edges = (Edge *) Xmalloc (npoints * sizeof (Edge) + + (npoints * npoints * sizeof (XTrapezoid))); + if (!edges) + return; + traps = (XTrapezoid *) (edges + npoints); + nedges = 0; + for (i = 0; i <= npoints; i++) + { + if (i == npoints) + { + x = firstx; + y = firsty; + } + else + { + x = XDoubleToFixed (fpoints[i].x); + y = XDoubleToFixed (fpoints[i].y); + } + if (i) + { + if (y < top) + top = y; + else if (y > bottom) + bottom = y; + if (prevy < y) + { + edges[nedges].edge.p1.x = prevx; + edges[nedges].edge.p1.y = prevy; + edges[nedges].edge.p2.x = x; + edges[nedges].edge.p2.y = y; + edges[nedges].clockWise = True; + nedges++; + } + else if (prevy > y) + { + edges[nedges].edge.p1.x = x; + edges[nedges].edge.p1.y = y; + edges[nedges].edge.p2.x = prevx; + edges[nedges].edge.p2.y = prevy; + edges[nedges].clockWise = False; + nedges++; + } + /* drop horizontal edges */ + } + else + { + top = y; + bottom = y; + firstx = x; + firsty = y; + } + prevx = x; + prevy = y; + } + ntraps = XRenderComputeTrapezoids (edges, nedges, winding, traps); + /* XXX adjust xSrc/xDst */ + XRenderCompositeTrapezoids (dpy, op, src, dst, maskFormat, xSrc, ySrc, traps, ntraps); + Xfree (edges); +} diff --git a/libXrender/src/Trap.c b/libXrender/src/Trap.c new file mode 100644 index 000000000..919aaef53 --- /dev/null +++ b/libXrender/src/Trap.c @@ -0,0 +1,74 @@ +/* + * + * Copyright © 2002 Keith Packard + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of Keith Packard not be used in + * advertising or publicity pertaining to distribution of the software without + * specific, written prior permission. Keith Packard makes no + * representations about the suitability of this software for any purpose. It + * is provided "as is" without express or implied warranty. + * + * KEITH PACKARD DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, + * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO + * EVENT SHALL KEITH PACKARD 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. + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "Xrenderint.h" + +void +XRenderCompositeTrapezoids (Display *dpy, + int op, + Picture src, + Picture dst, + _Xconst XRenderPictFormat *maskFormat, + int xSrc, + int ySrc, + _Xconst XTrapezoid *traps, + int ntrap) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderTrapezoidsReq *req; + int n; + long len; + unsigned long max_req = dpy->bigreq_size ? dpy->bigreq_size : dpy->max_request_size; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + while (ntrap) + { + GetReq(RenderTrapezoids, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderTrapezoids; + req->op = (CARD8) op; + req->src = src; + req->dst = dst; + req->maskFormat = maskFormat ? maskFormat->id : 0; + req->xSrc = xSrc; + req->ySrc = ySrc; + n = ntrap; + len = ((long) n) * (SIZEOF (xTrapezoid) >> 2); + if (len > (max_req - req->length)) { + n = (max_req - req->length) / (SIZEOF (xTrapezoid) >> 2); + len = ((long)n) * (SIZEOF (xTrapezoid) >> 2); + } + SetReqLen (req, len, len); + len <<= 2; + DataInt32 (dpy, (int *) traps, len); + ntrap -= n; + traps += n; + } + UnlockDisplay(dpy); + SyncHandle(); +} + diff --git a/libXrender/src/Tri.c b/libXrender/src/Tri.c new file mode 100644 index 000000000..155f2ce14 --- /dev/null +++ b/libXrender/src/Tri.c @@ -0,0 +1,169 @@ +/* + * + * Copyright © 2002 Keith Packard + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of Keith Packard not be used in + * advertising or publicity pertaining to distribution of the software without + * specific, written prior permission. Keith Packard makes no + * representations about the suitability of this software for any purpose. It + * is provided "as is" without express or implied warranty. + * + * KEITH PACKARD DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, + * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO + * EVENT SHALL KEITH PACKARD 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. + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "Xrenderint.h" + +void +XRenderCompositeTriangles (Display *dpy, + int op, + Picture src, + Picture dst, + _Xconst XRenderPictFormat *maskFormat, + int xSrc, + int ySrc, + _Xconst XTriangle *triangles, + int ntriangle) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderTrianglesReq *req; + int n; + long len; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + while (ntriangle) + { + GetReq(RenderTriangles, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderTriangles; + req->op = (CARD8) op; + req->src = src; + req->dst = dst; + req->maskFormat = maskFormat ? maskFormat->id : 0; + req->xSrc = xSrc; + req->ySrc = ySrc; + n = ntriangle; + len = ((long) n) * (SIZEOF (xTriangle) >> 2); + if (!dpy->bigreq_size && len > (dpy->max_request_size - req->length)) { + n = (dpy->max_request_size - req->length) / (SIZEOF (xTriangle) >> 2); + len = ((long)n) * (SIZEOF (xTriangle) >> 2); + } + SetReqLen (req, len, len); + len <<= 2; + DataInt32 (dpy, (int *) triangles, len); + ntriangle -= n; + triangles += n; + } + UnlockDisplay(dpy); + SyncHandle(); +} + +void +XRenderCompositeTriStrip (Display *dpy, + int op, + Picture src, + Picture dst, + _Xconst XRenderPictFormat *maskFormat, + int xSrc, + int ySrc, + _Xconst XPointFixed *points, + int npoint) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderTriStripReq *req; + int n; + long len; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + while (npoint > 2) + { + GetReq(RenderTriStrip, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderTriStrip; + req->op = (CARD8) op; + req->src = src; + req->dst = dst; + req->maskFormat = maskFormat ? maskFormat->id : 0; + req->xSrc = xSrc; + req->ySrc = ySrc; + n = npoint; + len = ((long) n) * (SIZEOF (xPointFixed) >> 2); + if (!dpy->bigreq_size && len > (dpy->max_request_size - req->length)) { + n = (dpy->max_request_size - req->length) / (SIZEOF (xPointFixed) >> 2); + len = ((long)n) * (SIZEOF (xPointFixed) >> 2); + } + SetReqLen (req, len, len); + len <<= 2; + DataInt32 (dpy, (int *) points, len); + npoint -= (n - 2); + points += (n - 2); + } + UnlockDisplay(dpy); + SyncHandle(); +} + +void +XRenderCompositeTriFan (Display *dpy, + int op, + Picture src, + Picture dst, + _Xconst XRenderPictFormat *maskFormat, + int xSrc, + int ySrc, + _Xconst XPointFixed *points, + int npoint) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + _Xconst XPointFixed *first = points; + xPointFixed *p; + xRenderTriFanReq *req; + int n; + long len; + + RenderSimpleCheckExtension (dpy, info); + LockDisplay(dpy); + points++; + npoint--; + while (npoint > 1) + { + GetReqExtra(RenderTriFan, SIZEOF (xPointFixed), req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderTriFan; + req->op = (CARD8) op; + req->src = src; + req->dst = dst; + req->maskFormat = maskFormat ? maskFormat->id : 0; + req->xSrc = xSrc; + req->ySrc = ySrc; + p = (xPointFixed *) (req + 1); + p->x = first->x; + p->y = first->y; + n = npoint; + len = ((long) n) * (SIZEOF (xPointFixed) >> 2); + if (!dpy->bigreq_size && len > (dpy->max_request_size - req->length)) { + n = (dpy->max_request_size - req->length) / (SIZEOF (xPointFixed) >> 2); + len = ((long)n) * (SIZEOF (xPointFixed) >> 2); + } + SetReqLen (req, len, len); + len <<= 2; + DataInt32 (dpy, (int *) points, len); + npoint -= (n - 1); + points += (n - 1); + } + UnlockDisplay(dpy); + SyncHandle(); +} diff --git a/libXrender/src/Xrender.c b/libXrender/src/Xrender.c new file mode 100644 index 000000000..c7630766f --- /dev/null +++ b/libXrender/src/Xrender.c @@ -0,0 +1,889 @@ +/* + * + * Copyright © 2000 SuSE, Inc. + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of SuSE not be used in advertising or + * publicity pertaining to distribution of the software without specific, + * written prior permission. SuSE makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * SuSE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL SuSE + * 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. + * + * Author: Keith Packard, SuSE, Inc. + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "Xrenderint.h" + +XRenderExtInfo XRenderExtensionInfo; +char XRenderExtensionName[] = RENDER_NAME; + +static int XRenderCloseDisplay (Display *dpy, XExtCodes *codes); + +/* + * XRenderExtFindDisplay - look for a display in this extension; keeps a + * cache of the most-recently used for efficiency. (Replaces + * XextFindDisplay.) + */ +static XRenderExtDisplayInfo * +XRenderExtFindDisplay (XRenderExtInfo *extinfo, + Display *dpy) +{ + XRenderExtDisplayInfo *dpyinfo; + + /* + * see if this was the most recently accessed display + */ + if ((dpyinfo = extinfo->cur) && dpyinfo->display == dpy) + return dpyinfo; + + /* + * look for display in list + */ + _XLockMutex(_Xglobal_lock); + for (dpyinfo = extinfo->head; dpyinfo; dpyinfo = dpyinfo->next) { + if (dpyinfo->display == dpy) { + extinfo->cur = dpyinfo; /* cache most recently used */ + _XUnlockMutex(_Xglobal_lock); + return dpyinfo; + } + } + _XUnlockMutex(_Xglobal_lock); + + return NULL; +} + +/* + * If the server is missing support for any of the required depths on + * any screen, tell the application that Render is not present. + */ + +#define DEPTH_MASK(d) (1 << ((d) - 1)) + +/* + * Render requires support for depth 1, 4, 8, 24 and 32 pixmaps + */ + +#define REQUIRED_DEPTHS (DEPTH_MASK(1) | \ + DEPTH_MASK(4) | \ + DEPTH_MASK(8) | \ + DEPTH_MASK(24) | \ + DEPTH_MASK(32)) + +typedef struct _DepthCheckRec { + struct _DepthCheckRec *next; + Display *dpy; + CARD32 missing; + unsigned long serial; +} DepthCheckRec, *DepthCheckPtr; + +static DepthCheckPtr depthChecks; + +static int +XRenderDepthCheckErrorHandler (Display *dpy, XErrorEvent *evt) +{ + if (evt->request_code == X_CreatePixmap && evt->error_code == BadValue) + { + DepthCheckPtr d; + _XLockMutex(_Xglobal_lock); + for (d = depthChecks; d; d = d->next) + if (d->dpy == dpy) + { + if ((long) (evt->serial - d->serial) >= 0) + d->missing |= DEPTH_MASK(evt->resourceid); + break; + } + _XUnlockMutex (_Xglobal_lock); + } + return 0; +} + +static Bool +XRenderHasDepths (Display *dpy) +{ + int s; + + for (s = 0; s < ScreenCount (dpy); s++) + { + CARD32 depths = 0; + CARD32 missing; + Screen *scr = ScreenOfDisplay (dpy, s); + int d; + + for (d = 0; d < scr->ndepths; d++) + depths |= DEPTH_MASK(scr->depths[d].depth); + missing = ~depths & REQUIRED_DEPTHS; + if (missing) + { + DepthCheckRec dc, **dp; + XErrorHandler previousHandler; + + /* + * Ok, this is ugly. It should be sufficient at this + * point to just return False, but Xinerama is broken at + * this point and only advertises depths which have an + * associated visual. Of course, the other depths still + * work, but the only way to find out is to try them. + */ + dc.dpy = dpy; + dc.missing = 0; + dc.serial = XNextRequest (dpy); + _XLockMutex(_Xglobal_lock); + dc.next = depthChecks; + depthChecks = &dc; + _XUnlockMutex (_Xglobal_lock); + /* + * I suspect this is not really thread safe, but Xlib doesn't + * provide a lot of options here + */ + previousHandler = XSetErrorHandler (XRenderDepthCheckErrorHandler); + /* + * Try each missing depth and see if pixmap creation succeeds + */ + for (d = 1; d <= 32; d++) + /* don't check depth 1 == Xcursor recurses... */ + if ((missing & DEPTH_MASK(d)) && d != 1) + { + Pixmap p; + p = XCreatePixmap (dpy, RootWindow (dpy, s), 1, 1, d); + XFreePixmap (dpy, p); + } + XSync (dpy, False); + XSetErrorHandler (previousHandler); + /* + * Unhook from the list of depth check records + */ + _XLockMutex(_Xglobal_lock); + for (dp = &depthChecks; *dp; dp = &(*dp)->next) + { + if (*dp == &dc) + { + *dp = dc.next; + break; + } + } + _XUnlockMutex (_Xglobal_lock); + if (dc.missing) + return False; + } + } + return True; +} + +/* + * XRenderExtAddDisplay - add a display to this extension. (Replaces + * XextAddDisplay) + */ +static XRenderExtDisplayInfo * +XRenderExtAddDisplay (XRenderExtInfo *extinfo, + Display *dpy, + char *ext_name) +{ + XRenderExtDisplayInfo *dpyinfo; + + dpyinfo = (XRenderExtDisplayInfo *) Xmalloc (sizeof (XRenderExtDisplayInfo)); + if (!dpyinfo) return NULL; + dpyinfo->display = dpy; + dpyinfo->info = NULL; + + if (XRenderHasDepths (dpy)) + dpyinfo->codes = XInitExtension (dpy, ext_name); + else + dpyinfo->codes = NULL; + + /* + * if the server has the extension, then we can initialize the + * appropriate function vectors + */ + if (dpyinfo->codes) { + XESetCloseDisplay (dpy, dpyinfo->codes->extension, + XRenderCloseDisplay); + } else { + /* The server doesn't have this extension. + * Use a private Xlib-internal extension to hang the close_display + * hook on so that the "cache" (extinfo->cur) is properly cleaned. + * (XBUG 7955) + */ + XExtCodes *codes = XAddExtension(dpy); + if (!codes) { + XFree(dpyinfo); + return NULL; + } + XESetCloseDisplay (dpy, codes->extension, XRenderCloseDisplay); + } + + /* + * now, chain it onto the list + */ + _XLockMutex(_Xglobal_lock); + dpyinfo->next = extinfo->head; + extinfo->head = dpyinfo; + extinfo->cur = dpyinfo; + extinfo->ndisplays++; + _XUnlockMutex(_Xglobal_lock); + return dpyinfo; +} + + +/* + * XRenderExtRemoveDisplay - remove the indicated display from the + * extension object. (Replaces XextRemoveDisplay.) + */ +static int +XRenderExtRemoveDisplay (XRenderExtInfo *extinfo, Display *dpy) +{ + XRenderExtDisplayInfo *dpyinfo, *prev; + + /* + * locate this display and its back link so that it can be removed + */ + _XLockMutex(_Xglobal_lock); + prev = NULL; + for (dpyinfo = extinfo->head; dpyinfo; dpyinfo = dpyinfo->next) { + if (dpyinfo->display == dpy) break; + prev = dpyinfo; + } + if (!dpyinfo) { + _XUnlockMutex(_Xglobal_lock); + return 0; /* hmm, actually an error */ + } + + /* + * remove the display from the list; handles going to zero + */ + if (prev) + prev->next = dpyinfo->next; + else + extinfo->head = dpyinfo->next; + + extinfo->ndisplays--; + if (dpyinfo == extinfo->cur) extinfo->cur = NULL; /* flush cache */ + _XUnlockMutex(_Xglobal_lock); + + Xfree ((char *) dpyinfo); + return 1; +} + + + +XRenderExtDisplayInfo * +XRenderFindDisplay (Display *dpy) +{ + XRenderExtDisplayInfo *dpyinfo; + + dpyinfo = XRenderExtFindDisplay (&XRenderExtensionInfo, dpy); + if (!dpyinfo) + dpyinfo = XRenderExtAddDisplay (&XRenderExtensionInfo, dpy, + XRenderExtensionName); + return dpyinfo; +} + +static int +XRenderCloseDisplay (Display *dpy, XExtCodes *codes) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + if (info && info->info) XFree (info->info); + + return XRenderExtRemoveDisplay (&XRenderExtensionInfo, dpy); +} + +/**************************************************************************** + * * + * Render public interfaces * + * * + ****************************************************************************/ + +Bool XRenderQueryExtension (Display *dpy, int *event_basep, int *error_basep) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + + if (RenderHasExtension(info)) { + *event_basep = info->codes->first_event; + *error_basep = info->codes->first_error; + return True; + } else { + return False; + } +} + + +Status XRenderQueryVersion (Display *dpy, + int *major_versionp, + int *minor_versionp) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + XRenderInfo *xri; + + if (!RenderHasExtension (info)) + return 0; + + if (!XRenderQueryFormats (dpy)) + return 0; + + xri = info->info; + *major_versionp = xri->major_version; + *minor_versionp = xri->minor_version; + return 1; +} + +static XRenderPictFormat * +_XRenderFindFormat (XRenderInfo *xri, PictFormat format) +{ + int nf; + + for (nf = 0; nf < xri->nformat; nf++) + if (xri->format[nf].id == format) + return &xri->format[nf]; + return NULL; +} + +static Visual * +_XRenderFindVisual (Display *dpy, VisualID vid) +{ + return _XVIDtoVisual (dpy, vid); +} + +typedef struct _renderVersionState { + unsigned long version_seq; + Bool error; + int major_version; + int minor_version; + +} _XrenderVersionState; + +static Bool +_XRenderVersionHandler (Display *dpy, + xReply *rep, + char *buf, + int len, + XPointer data) +{ + xRenderQueryVersionReply replbuf; + xRenderQueryVersionReply *repl; + _XrenderVersionState *state = (_XrenderVersionState *) data; + + if (dpy->last_request_read != state->version_seq) + return False; + if (rep->generic.type == X_Error) + { + state->error = True; + return False; + } + repl = (xRenderQueryVersionReply *) + _XGetAsyncReply(dpy, (char *)&replbuf, rep, buf, len, + (SIZEOF(xRenderQueryVersionReply) - SIZEOF(xReply)) >> 2, + True); + state->major_version = repl->majorVersion; + state->minor_version = repl->minorVersion; + return True; +} + +Status +XRenderQueryFormats (Display *dpy) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + _XAsyncHandler async; + _XrenderVersionState async_state; + xRenderQueryVersionReq *vreq; + xRenderQueryPictFormatsReply rep; + xRenderQueryPictFormatsReq *req; + XRenderInfo *xri; + XRenderPictFormat *format; + XRenderScreen *screen; + XRenderDepth *depth; + XRenderVisual *visual; + xPictFormInfo *xFormat; + xPictScreen *xScreen; + xPictDepth *xDepth; + xPictVisual *xVisual; + CARD32 *xSubpixel; + void *xData; + int nf, ns, nd, nv; + int rlength; + int nbytes; + + RenderCheckExtension (dpy, info, 0); + LockDisplay (dpy); + if (info->info) + { + UnlockDisplay (dpy); + return 1; + } + GetReq (RenderQueryVersion, vreq); + vreq->reqType = info->codes->major_opcode; + vreq->renderReqType = X_RenderQueryVersion; + vreq->majorVersion = RENDER_MAJOR; + vreq->minorVersion = RENDER_MINOR; + + async_state.version_seq = dpy->request; + async_state.error = False; + async.next = dpy->async_handlers; + async.handler = _XRenderVersionHandler; + async.data = (XPointer) &async_state; + dpy->async_handlers = &async; + + GetReq (RenderQueryPictFormats, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderQueryPictFormats; + + if (!_XReply (dpy, (xReply *) &rep, 0, xFalse)) + { + DeqAsyncHandler (dpy, &async); + UnlockDisplay (dpy); + SyncHandle (); + return 0; + } + DeqAsyncHandler (dpy, &async); + if (async_state.error) + { + UnlockDisplay(dpy); + SyncHandle(); + return 0; + } + /* + * Check for the lack of sub-pixel data + */ + if (async_state.major_version == 0 && async_state.minor_version < 6) + rep.numSubpixel = 0; + + xri = (XRenderInfo *) Xmalloc (sizeof (XRenderInfo) + + rep.numFormats * sizeof (XRenderPictFormat) + + rep.numScreens * sizeof (XRenderScreen) + + rep.numDepths * sizeof (XRenderDepth) + + rep.numVisuals * sizeof (XRenderVisual)); + rlength = (rep.numFormats * sizeof (xPictFormInfo) + + rep.numScreens * sizeof (xPictScreen) + + rep.numDepths * sizeof (xPictDepth) + + rep.numVisuals * sizeof (xPictVisual) + + rep.numSubpixel * 4); + xData = (void *) Xmalloc (rlength); + nbytes = (int) rep.length << 2; + + if (!xri || !xData || nbytes < rlength) + { + if (xri) Xfree (xri); + if (xData) Xfree (xData); + _XEatData (dpy, nbytes); + UnlockDisplay (dpy); + SyncHandle (); + return 0; + } + xri->major_version = async_state.major_version; + xri->minor_version = async_state.minor_version; + xri->format = (XRenderPictFormat *) (xri + 1); + xri->nformat = rep.numFormats; + xri->screen = (XRenderScreen *) (xri->format + rep.numFormats); + xri->nscreen = rep.numScreens; + xri->depth = (XRenderDepth *) (xri->screen + rep.numScreens); + xri->ndepth = rep.numDepths; + xri->visual = (XRenderVisual *) (xri->depth + rep.numDepths); + xri->nvisual = rep.numVisuals; + _XRead (dpy, (char *) xData, rlength); + format = xri->format; + xFormat = (xPictFormInfo *) xData; + for (nf = 0; nf < rep.numFormats; nf++) + { + format->id = xFormat->id; + format->type = xFormat->type; + format->depth = xFormat->depth; + format->direct.red = xFormat->direct.red; + format->direct.redMask = xFormat->direct.redMask; + format->direct.green = xFormat->direct.green; + format->direct.greenMask = xFormat->direct.greenMask; + format->direct.blue = xFormat->direct.blue; + format->direct.blueMask = xFormat->direct.blueMask; + format->direct.alpha = xFormat->direct.alpha; + format->direct.alphaMask = xFormat->direct.alphaMask; + format->colormap = xFormat->colormap; + format++; + xFormat++; + } + xScreen = (xPictScreen *) xFormat; + screen = xri->screen; + depth = xri->depth; + visual = xri->visual; + for (ns = 0; ns < xri->nscreen; ns++) + { + screen->depths = depth; + screen->ndepths = xScreen->nDepth; + screen->fallback = _XRenderFindFormat (xri, xScreen->fallback); + screen->subpixel = SubPixelUnknown; + xDepth = (xPictDepth *) (xScreen + 1); + for (nd = 0; nd < screen->ndepths; nd++) + { + depth->depth = xDepth->depth; + depth->nvisuals = xDepth->nPictVisuals; + depth->visuals = visual; + xVisual = (xPictVisual *) (xDepth + 1); + for (nv = 0; nv < depth->nvisuals; nv++) + { + visual->visual = _XRenderFindVisual (dpy, xVisual->visual); + visual->format = _XRenderFindFormat (xri, xVisual->format); + visual++; + xVisual++; + } + depth++; + xDepth = (xPictDepth *) xVisual; + } + screen++; + xScreen = (xPictScreen *) xDepth; + } + xSubpixel = (CARD32 *) xScreen; + screen = xri->screen; + for (ns = 0; ns < rep.numSubpixel; ns++) + { + screen->subpixel = *xSubpixel; + xSubpixel++; + screen++; + } + info->info = xri; + /* + * Skip any extra data + */ + if (nbytes > rlength) + _XEatData (dpy, (unsigned long) (nbytes - rlength)); + + UnlockDisplay (dpy); + SyncHandle (); + Xfree (xData); + return 1; +} + +int +XRenderQuerySubpixelOrder (Display *dpy, int screen) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + XRenderInfo *xri; + + if (!RenderHasExtension (info)) + return SubPixelUnknown; + + if (!XRenderQueryFormats (dpy)) + return SubPixelUnknown; + + xri = info->info; + return xri->screen[screen].subpixel; +} + +Bool +XRenderSetSubpixelOrder (Display *dpy, int screen, int subpixel) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + XRenderInfo *xri; + + if (!RenderHasExtension (info)) + return False; + + if (!XRenderQueryFormats (dpy)) + return False; + + xri = info->info; + xri->screen[screen].subpixel = subpixel; + return True; +} + +XRenderPictFormat * +XRenderFindVisualFormat (Display *dpy, _Xconst Visual *visual) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + int nv; + XRenderInfo *xri; + XRenderVisual *xrv; + + RenderCheckExtension (dpy, info, NULL); + if (!XRenderQueryFormats (dpy)) + return NULL; + xri = info->info; + for (nv = 0, xrv = xri->visual; nv < xri->nvisual; nv++, xrv++) + if (xrv->visual == visual) + return xrv->format; + return NULL; +} + +XRenderPictFormat * +XRenderFindFormat (Display *dpy, + unsigned long mask, + _Xconst XRenderPictFormat *template, + int count) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + int nf; + XRenderInfo *xri; + + RenderCheckExtension (dpy, info, NULL); + if (!XRenderQueryFormats (dpy)) + return NULL; + xri = info->info; + for (nf = 0; nf < xri->nformat; nf++) + { + if (mask & PictFormatID) + if (template->id != xri->format[nf].id) + continue; + if (mask & PictFormatType) + if (template->type != xri->format[nf].type) + continue; + if (mask & PictFormatDepth) + if (template->depth != xri->format[nf].depth) + continue; + if (mask & PictFormatRed) + if (template->direct.red != xri->format[nf].direct.red) + continue; + if (mask & PictFormatRedMask) + if (template->direct.redMask != xri->format[nf].direct.redMask) + continue; + if (mask & PictFormatGreen) + if (template->direct.green != xri->format[nf].direct.green) + continue; + if (mask & PictFormatGreenMask) + if (template->direct.greenMask != xri->format[nf].direct.greenMask) + continue; + if (mask & PictFormatBlue) + if (template->direct.blue != xri->format[nf].direct.blue) + continue; + if (mask & PictFormatBlueMask) + if (template->direct.blueMask != xri->format[nf].direct.blueMask) + continue; + if (mask & PictFormatAlpha) + if (template->direct.alpha != xri->format[nf].direct.alpha) + continue; + if (mask & PictFormatAlphaMask) + if (template->direct.alphaMask != xri->format[nf].direct.alphaMask) + continue; + if (mask & PictFormatColormap) + if (template->colormap != xri->format[nf].colormap) + continue; + if (count-- == 0) + return &xri->format[nf]; + } + return NULL; +} + +XRenderPictFormat * +XRenderFindStandardFormat (Display *dpy, + int format) +{ + static struct { + XRenderPictFormat templ; + unsigned long mask; + } standardFormats[PictStandardNUM] = { + /* PictStandardARGB32 */ + { + { + 0, /* id */ + PictTypeDirect, /* type */ + 32, /* depth */ + { /* direct */ + 16, /* direct.red */ + 0xff, /* direct.redMask */ + 8, /* direct.green */ + 0xff, /* direct.greenMask */ + 0, /* direct.blue */ + 0xff, /* direct.blueMask */ + 24, /* direct.alpha */ + 0xff, /* direct.alphaMask */ + }, + 0, /* colormap */ + }, + PictFormatType | + PictFormatDepth | + PictFormatRed | + PictFormatRedMask | + PictFormatGreen | + PictFormatGreenMask | + PictFormatBlue | + PictFormatBlueMask | + PictFormatAlpha | + PictFormatAlphaMask, + }, + /* PictStandardRGB24 */ + { + { + 0, /* id */ + PictTypeDirect, /* type */ + 24, /* depth */ + { /* direct */ + 16, /* direct.red */ + 0xff, /* direct.redMask */ + 8, /* direct.green */ + 0xff, /* direct.greenMask */ + 0, /* direct.blue */ + 0xff, /* direct.blueMask */ + 0, /* direct.alpha */ + 0x00, /* direct.alphaMask */ + }, + 0, /* colormap */ + }, + PictFormatType | + PictFormatDepth | + PictFormatRed | + PictFormatRedMask | + PictFormatGreen | + PictFormatGreenMask | + PictFormatBlue | + PictFormatBlueMask | + PictFormatAlphaMask, + }, + /* PictStandardA8 */ + { + { + 0, /* id */ + PictTypeDirect, /* type */ + 8, /* depth */ + { /* direct */ + 0, /* direct.red */ + 0x00, /* direct.redMask */ + 0, /* direct.green */ + 0x00, /* direct.greenMask */ + 0, /* direct.blue */ + 0x00, /* direct.blueMask */ + 0, /* direct.alpha */ + 0xff, /* direct.alphaMask */ + }, + 0, /* colormap */ + }, + PictFormatType | + PictFormatDepth | + PictFormatRedMask | + PictFormatGreenMask | + PictFormatBlueMask | + PictFormatAlpha | + PictFormatAlphaMask, + }, + /* PictStandardA4 */ + { + { + 0, /* id */ + PictTypeDirect, /* type */ + 4, /* depth */ + { /* direct */ + 0, /* direct.red */ + 0x00, /* direct.redMask */ + 0, /* direct.green */ + 0x00, /* direct.greenMask */ + 0, /* direct.blue */ + 0x00, /* direct.blueMask */ + 0, /* direct.alpha */ + 0x0f, /* direct.alphaMask */ + }, + 0, /* colormap */ + }, + PictFormatType | + PictFormatDepth | + PictFormatRedMask | + PictFormatGreenMask | + PictFormatBlueMask | + PictFormatAlpha | + PictFormatAlphaMask, + }, + /* PictStandardA1 */ + { + { + 0, /* id */ + PictTypeDirect, /* type */ + 1, /* depth */ + { /* direct */ + 0, /* direct.red */ + 0x00, /* direct.redMask */ + 0, /* direct.green */ + 0x00, /* direct.greenMask */ + 0, /* direct.blue */ + 0x00, /* direct.blueMask */ + 0, /* direct.alpha */ + 0x01, /* direct.alphaMask */ + }, + 0, /* colormap */ + }, + PictFormatType | + PictFormatDepth | + PictFormatRedMask | + PictFormatGreenMask | + PictFormatBlueMask | + PictFormatAlpha | + PictFormatAlphaMask, + }, + }; + + if (0 <= format && format < PictStandardNUM) + return XRenderFindFormat (dpy, + standardFormats[format].mask, + &standardFormats[format].templ, + 0); + return NULL; +} + +XIndexValue * +XRenderQueryPictIndexValues(Display *dpy, + _Xconst XRenderPictFormat *format, + int *num) +{ + XRenderExtDisplayInfo *info = XRenderFindDisplay (dpy); + xRenderQueryPictIndexValuesReq *req; + xRenderQueryPictIndexValuesReply rep; + XIndexValue *values; + int nbytes, nread, rlength, i; + + RenderCheckExtension (dpy, info, NULL); + + LockDisplay (dpy); + GetReq (RenderQueryPictIndexValues, req); + req->reqType = info->codes->major_opcode; + req->renderReqType = X_RenderQueryPictIndexValues; + req->format = format->id; + if (!_XReply (dpy, (xReply *) &rep, 0, xFalse)) + { + UnlockDisplay (dpy); + SyncHandle (); + return NULL; + } + + /* request data length */ + nbytes = (long)rep.length << 2; + /* bytes of actual data in the request */ + nread = rep.numIndexValues * SIZEOF (xIndexValue); + /* size of array returned to application */ + rlength = rep.numIndexValues * sizeof (XIndexValue); + + /* allocate returned data */ + values = (XIndexValue *)Xmalloc (rlength); + if (!values) + { + _XEatData (dpy, nbytes); + UnlockDisplay (dpy); + SyncHandle (); + return NULL; + } + + /* read the values one at a time and convert */ + *num = rep.numIndexValues; + for(i = 0; i < rep.numIndexValues; i++) + { + xIndexValue value; + + _XRead (dpy, (char *) &value, SIZEOF (xIndexValue)); + values[i].pixel = value.pixel; + values[i].red = value.red; + values[i].green = value.green; + values[i].blue = value.blue; + values[i].alpha = value.alpha; + } + /* skip any padding */ + if(nbytes > nread) + { + _XEatData (dpy, (unsigned long) (nbytes - nread)); + } + UnlockDisplay (dpy); + SyncHandle (); + return values; +} diff --git a/libXrender/src/Xrenderint.h b/libXrender/src/Xrenderint.h new file mode 100644 index 000000000..49a294b14 --- /dev/null +++ b/libXrender/src/Xrenderint.h @@ -0,0 +1,114 @@ +/* + * + * Copyright © 2000 SuSE, Inc. + * + * Permission to use, copy, modify, distribute, and sell this software and its + * documentation for any purpose is hereby granted without fee, provided that + * the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of SuSE not be used in advertising or + * publicity pertaining to distribution of the software without specific, + * written prior permission. SuSE makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * SuSE DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL SuSE + * 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. + * + * Author: Keith Packard, SuSE, Inc. + */ + +#ifndef _XRENDERINT_H_ +#define _XRENDERINT_H_ + +#include "config.h" +#define NEED_EVENTS +#define NEED_REPLIES +#include <X11/Xlibint.h> +#include <X11/Xutil.h> +#include <X11/extensions/renderproto.h> +#include "Xrender.h" + +typedef struct { + Visual *visual; + XRenderPictFormat *format; +} XRenderVisual; + +typedef struct { + int depth; + int nvisuals; + XRenderVisual *visuals; +} XRenderDepth; + +typedef struct { + XRenderDepth *depths; + int ndepths; + XRenderPictFormat *fallback; + int subpixel; +} XRenderScreen; + +typedef struct _XRenderInfo { + int major_version; + int minor_version; + XRenderPictFormat *format; + int nformat; + XRenderScreen *screen; + int nscreen; + XRenderDepth *depth; + int ndepth; + XRenderVisual *visual; + int nvisual; + int *subpixel; + int nsubpixel; + char **filter; + int nfilter; + short *filter_alias; + int nfilter_alias; +} XRenderInfo; + +/* replaces XRenderExtDisplayInfo */ +typedef struct _XRenderExtDisplayInfo { + struct _XRenderExtDisplayInfo *next; /* keep a linked list */ + Display *display; /* which display this is */ + XExtCodes *codes; /* the extension protocol codes */ + XRenderInfo *info; /* extra data for the extension to use */ +} XRenderExtDisplayInfo; + +/* replaces XExtensionInfo */ +typedef struct _XRenderExtInfo { + XRenderExtDisplayInfo *head; /* start of the list */ + XRenderExtDisplayInfo *cur; /* most recently used */ + int ndisplays; /* number of displays */ +} XRenderExtInfo; + +extern XRenderExtInfo XRenderExtensionInfo; +extern char XRenderExtensionName[]; + +XRenderExtDisplayInfo * +XRenderFindDisplay (Display *dpy); + +#define RenderHasExtension(i) ((i) && ((i)->codes)) + +#define RenderCheckExtension(dpy,i,val) \ + if (!RenderHasExtension(i)) { return val; } + +#define RenderSimpleCheckExtension(dpy,i) \ + if (!RenderHasExtension(i)) { return; } + +/* + * Xlib uses long for 32-bit values. Xrender uses int. This + * matters on alpha. Note that this macro assumes that int is 32 bits + * except on WORD64 machines where it is 64 bits. + */ + +#ifdef WORD64 +#define DataInt32(dpy,d,len) Data32(dpy,(long *) (d),len) +#else +#define DataInt32(dpy,d,len) Data(dpy,(char *) (d),len) +#endif + +#endif /* _XRENDERINT_H_ */ |