diff options
Diffstat (limited to 'xorg-server/miext/cw/cw_ops.c')
-rw-r--r-- | xorg-server/miext/cw/cw_ops.c | 478 |
1 files changed, 478 insertions, 0 deletions
diff --git a/xorg-server/miext/cw/cw_ops.c b/xorg-server/miext/cw/cw_ops.c new file mode 100644 index 000000000..9ae56cb6c --- /dev/null +++ b/xorg-server/miext/cw/cw_ops.c @@ -0,0 +1,478 @@ +/* + * Copyright © 2004 Eric Anholt + * + * 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 Eric Anholt not be used in + * advertising or publicity pertaining to distribution of the software without + * specific, written prior permission. Eric Anholt makes no + * representations about the suitability of this software for any purpose. It + * is provided "as is" without express or implied warranty. + * + * ERIC ANHOLT DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, + * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO + * EVENT SHALL ERIC ANHOLT 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_DIX_CONFIG_H +#include <dix-config.h> +#endif + +#include <stdlib.h> + +#include "gcstruct.h" +#include "pixmapstr.h" +#include "cw.h" +#include "mi.h" + +#define SETUP_BACKING_DST(_pDst, _pGC) \ + cwGCPtr pGCPrivate = getCwGC (_pGC); \ + int dst_off_x, dst_off_y; \ + DrawablePtr pBackingDst = cwGetBackingDrawable(pDst, &dst_off_x, \ + &dst_off_y); \ + GCPtr pBackingGC = pGCPrivate->pBackingGC ? pGCPrivate->pBackingGC : _pGC + +#define SETUP_BACKING_SRC(pSrc, pGC) \ + int src_off_x, src_off_y; \ + DrawablePtr pBackingSrc = cwGetBackingDrawable(pSrc, &src_off_x, \ + &src_off_y) + +#define PROLOGUE(pGC) do { \ + if (pBackingGC->serialNumber != pBackingDst->serialNumber) { \ + ValidateGC(pBackingDst, pBackingGC); \ + } \ + pGC->funcs = pGCPrivate->wrapFuncs;\ + pGC->ops = pGCPrivate->wrapOps;\ +} while (0) + +#define EPILOGUE(pGC) do { \ + pGCPrivate->wrapFuncs = (pGC)->funcs; \ + pGCPrivate->wrapOps = (pGC)->ops; \ + (pGC)->funcs = &cwGCFuncs; \ + (pGC)->ops = &cwGCOps; \ +} while (0) + +extern GCFuncs cwGCFuncs; + +/* + * GC ops -- wrap each GC operation with our own function + */ + +static void cwFillSpans(DrawablePtr pDst, GCPtr pGC, int nInit, + DDXPointPtr pptInit, int *pwidthInit, int fSorted); +static void cwSetSpans(DrawablePtr pDst, GCPtr pGC, char *psrc, + DDXPointPtr ppt, int *pwidth, int nspans, int fSorted); +static void cwPutImage(DrawablePtr pDst, GCPtr pGC, int depth, + int x, int y, int w, int h, int leftPad, int format, + char *pBits); +static RegionPtr cwCopyArea(DrawablePtr pSrc, DrawablePtr pDst, GCPtr pGC, + int srcx, int srcy, int w, int h, + int dstx, int dsty); +static RegionPtr cwCopyPlane(DrawablePtr pSrc, DrawablePtr pDst, GCPtr pGC, + int srcx, int srcy, int w, int h, + int dstx, int dsty, unsigned long plane); +static void cwPolyPoint(DrawablePtr pDst, GCPtr pGC, int mode, int npt, + xPoint *pptInit); +static void cwPolylines(DrawablePtr pDst, GCPtr pGC, int mode, int npt, + DDXPointPtr pptInit); +static void cwPolySegment(DrawablePtr pDst, GCPtr pGC, int nseg, + xSegment *pSegs); +static void cwPolyRectangle(DrawablePtr pDst, GCPtr pGC, + int nrects, xRectangle *pRects); +static void cwPolyArc(DrawablePtr pDst, GCPtr pGC, int narcs, xArc *parcs); +static void cwFillPolygon(DrawablePtr pDst, GCPtr pGC, int shape, int mode, + int count, DDXPointPtr pPts); +static void cwPolyFillRect(DrawablePtr pDst, GCPtr pGC, + int nrectFill, xRectangle *prectInit); +static void cwPolyFillArc(DrawablePtr pDst, GCPtr pGC, + int narcs, xArc *parcs); +static int cwPolyText8(DrawablePtr pDrawable, GCPtr pGC, int x, int y, + int count, char *chars); +static int cwPolyText16(DrawablePtr pDst, GCPtr pGC, int x, int y, + int count, unsigned short *chars); +static void cwImageText8(DrawablePtr pDst, GCPtr pGC, int x, int y, + int count, char *chars); +static void cwImageText16(DrawablePtr pDst, GCPtr pGC, int x, int y, + int count, unsigned short *chars); +static void cwImageGlyphBlt(DrawablePtr pDst, GCPtr pGC, int x, int y, + unsigned int nglyph, CharInfoPtr *ppci, + pointer pglyphBase); +static void cwPolyGlyphBlt(DrawablePtr pDst, GCPtr pGC, int x, int y, + unsigned int nglyph, CharInfoPtr *ppci, + pointer pglyphBase); +static void cwPushPixels(GCPtr pGC, PixmapPtr pBitMap, DrawablePtr pDst, + int w, int h, int x, int y); + +GCOps cwGCOps = { + cwFillSpans, + cwSetSpans, + cwPutImage, + cwCopyArea, + cwCopyPlane, + cwPolyPoint, + cwPolylines, + cwPolySegment, + cwPolyRectangle, + cwPolyArc, + cwFillPolygon, + cwPolyFillRect, + cwPolyFillArc, + cwPolyText8, + cwPolyText16, + cwImageText8, + cwImageText16, + cwImageGlyphBlt, + cwPolyGlyphBlt, + cwPushPixels +}; + +static void +cwFillSpans(DrawablePtr pDst, GCPtr pGC, int nspans, DDXPointPtr ppt, + int *pwidth, int fSorted) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_XYPOINTS(ppt, nspans); + + (*pBackingGC->ops->FillSpans)(pBackingDst, pBackingGC, nspans, ppt, + pwidth, fSorted); + + EPILOGUE(pGC); +} + +static void +cwSetSpans(DrawablePtr pDst, GCPtr pGC, char *psrc, DDXPointPtr ppt, + int *pwidth, int nspans, int fSorted) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_XYPOINTS(ppt, nspans); + + (*pBackingGC->ops->SetSpans)(pBackingDst, pBackingGC, psrc, ppt, pwidth, + nspans, fSorted); + + EPILOGUE(pGC); +} + +static void +cwPutImage(DrawablePtr pDst, GCPtr pGC, int depth, int x, int y, int w, int h, + int leftPad, int format, char *pBits) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_XY_DST(x, y); + + (*pBackingGC->ops->PutImage)(pBackingDst, pBackingGC, depth, x, y, w, h, + leftPad, format, pBits); + + EPILOGUE(pGC); +} + +static RegionPtr +cwCopyArea(DrawablePtr pSrc, DrawablePtr pDst, GCPtr pGC, int srcx, int srcy, + int w, int h, int dstx, int dsty) +{ + int odstx, odsty; + int osrcx, osrcy; + SETUP_BACKING_DST(pDst, pGC); + SETUP_BACKING_SRC(pSrc, pGC); + + PROLOGUE(pGC); + + odstx = dstx; + odsty = dsty; + osrcx = srcx; + osrcy = srcy; + CW_OFFSET_XY_DST(dstx, dsty); + CW_OFFSET_XY_SRC(srcx, srcy); + + (*pBackingGC->ops->CopyArea)(pBackingSrc, pBackingDst, + pBackingGC, srcx, srcy, w, h, + dstx, dsty); + + EPILOGUE(pGC); + + return miHandleExposures(pSrc, pDst, pGC, + osrcx, osrcy, w, h, + odstx, odsty, 0); +} + +static RegionPtr +cwCopyPlane(DrawablePtr pSrc, DrawablePtr pDst, GCPtr pGC, int srcx, int srcy, + int w, int h, int dstx, int dsty, unsigned long plane) +{ + int odstx, odsty; + int osrcx, osrcy; + SETUP_BACKING_DST(pDst, pGC); + SETUP_BACKING_SRC(pSrc, pGC); + + PROLOGUE(pGC); + + odstx = dstx; + odsty = dsty; + osrcx = srcx; + osrcy = srcy; + CW_OFFSET_XY_DST(dstx, dsty); + CW_OFFSET_XY_SRC(srcx, srcy); + + (*pBackingGC->ops->CopyPlane)(pBackingSrc, pBackingDst, + pBackingGC, srcx, srcy, w, h, + dstx, dsty, plane); + + EPILOGUE(pGC); + + return miHandleExposures(pSrc, pDst, pGC, + osrcx, osrcy, w, h, + odstx, odsty, plane); +} + +static void +cwPolyPoint(DrawablePtr pDst, GCPtr pGC, int mode, int npt, xPoint *ppt) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + if (mode == CoordModeOrigin) + CW_OFFSET_XYPOINTS(ppt, npt); + else + CW_OFFSET_XYPOINTS(ppt, 1); + + (*pBackingGC->ops->PolyPoint)(pBackingDst, pBackingGC, mode, npt, ppt); + + EPILOGUE(pGC); +} + +static void +cwPolylines(DrawablePtr pDst, GCPtr pGC, int mode, int npt, DDXPointPtr ppt) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + if (mode == CoordModeOrigin) + CW_OFFSET_XYPOINTS(ppt, npt); + else + CW_OFFSET_XYPOINTS(ppt, 1); + + (*pBackingGC->ops->Polylines)(pBackingDst, pBackingGC, mode, npt, ppt); + + EPILOGUE(pGC); +} + +static void +cwPolySegment(DrawablePtr pDst, GCPtr pGC, int nseg, xSegment *pSegs) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_XYPOINTS(pSegs, nseg * 2); + + (*pBackingGC->ops->PolySegment)(pBackingDst, pBackingGC, nseg, pSegs); + + EPILOGUE(pGC); +} + +static void +cwPolyRectangle(DrawablePtr pDst, GCPtr pGC, int nrects, xRectangle *pRects) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_RECTS(pRects, nrects); + + (*pBackingGC->ops->PolyRectangle)(pBackingDst, pBackingGC, nrects, pRects); + + EPILOGUE(pGC); +} + +static void +cwPolyArc(DrawablePtr pDst, GCPtr pGC, int narcs, xArc *pArcs) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_RECTS(pArcs, narcs); + + (*pBackingGC->ops->PolyArc)(pBackingDst, pBackingGC, narcs, pArcs); + + EPILOGUE(pGC); +} + +static void +cwFillPolygon(DrawablePtr pDst, GCPtr pGC, int shape, int mode, int npt, + DDXPointPtr ppt) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + if (mode == CoordModeOrigin) + CW_OFFSET_XYPOINTS(ppt, npt); + else + CW_OFFSET_XYPOINTS(ppt, 1); + + (*pBackingGC->ops->FillPolygon)(pBackingDst, pBackingGC, shape, mode, npt, + ppt); + + EPILOGUE(pGC); +} + +static void +cwPolyFillRect(DrawablePtr pDst, GCPtr pGC, int nrects, xRectangle *pRects) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_RECTS(pRects, nrects); + + (*pBackingGC->ops->PolyFillRect)(pBackingDst, pBackingGC, nrects, pRects); + + EPILOGUE(pGC); +} + +static void +cwPolyFillArc(DrawablePtr pDst, GCPtr pGC, int narcs, xArc *parcs) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_RECTS(parcs, narcs); + + (*pBackingGC->ops->PolyFillArc)(pBackingDst, pBackingGC, narcs, parcs); + + EPILOGUE(pGC); +} + +static int +cwPolyText8(DrawablePtr pDst, GCPtr pGC, int x, int y, int count, char *chars) +{ + int result; + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_XY_DST(x, y); + + result = (*pBackingGC->ops->PolyText8)(pBackingDst, pBackingGC, x, y, + count, chars); + + EPILOGUE(pGC); + + return result; +} + +static int +cwPolyText16(DrawablePtr pDst, GCPtr pGC, int x, int y, int count, + unsigned short *chars) +{ + int result; + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_XY_DST(x, y); + + result = (*pBackingGC->ops->PolyText16)(pBackingDst, pBackingGC, x, y, + count, chars); + + EPILOGUE(pGC); + return result; +} + +static void +cwImageText8(DrawablePtr pDst, GCPtr pGC, int x, int y, int count, char *chars) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_XY_DST(x, y); + + (*pBackingGC->ops->ImageText8)(pBackingDst, pBackingGC, x, y, count, + chars); + + EPILOGUE(pGC); +} + +static void +cwImageText16(DrawablePtr pDst, GCPtr pGC, int x, int y, int count, + unsigned short *chars) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_XY_DST(x, y); + + (*pBackingGC->ops->ImageText16)(pBackingDst, pBackingGC, x, y, count, + chars); + + EPILOGUE(pGC); +} + +static void +cwImageGlyphBlt(DrawablePtr pDst, GCPtr pGC, int x, int y, unsigned int nglyph, + CharInfoPtr *ppci, pointer pglyphBase) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_XY_DST(x, y); + + (*pBackingGC->ops->ImageGlyphBlt)(pBackingDst, pBackingGC, x, y, nglyph, + ppci, pglyphBase); + + EPILOGUE(pGC); +} + +static void +cwPolyGlyphBlt(DrawablePtr pDst, GCPtr pGC, int x, int y, unsigned int nglyph, + CharInfoPtr *ppci, pointer pglyphBase) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_XY_DST(x, y); + + (*pBackingGC->ops->PolyGlyphBlt)(pBackingDst, pBackingGC, x, y, nglyph, + ppci, pglyphBase); + + EPILOGUE(pGC); +} + +static void +cwPushPixels(GCPtr pGC, PixmapPtr pBitMap, DrawablePtr pDst, int w, int h, + int x, int y) +{ + SETUP_BACKING_DST(pDst, pGC); + + PROLOGUE(pGC); + + CW_OFFSET_XY_DST(x, y); + + (*pBackingGC->ops->PushPixels)(pBackingGC, pBitMap, pBackingDst, w, h, + x, y); + + EPILOGUE(pGC); +} + |