1/*
2 *
3 * Copyright © 2000,2008 Keith Packard
4 *             2005 Zack Rusin, Trolltech
5 *
6 * Permission to use, copy, modify, distribute, and sell this software and its
7 * documentation for any purpose is hereby granted without fee, provided that
8 * the above copyright notice appear in all copies and that both that
9 * copyright notice and this permission notice appear in supporting
10 * documentation, and that the name of Keith Packard not be used in
11 * advertising or publicity pertaining to distribution of the software without
12 * specific, written prior permission.  Keith Packard makes no
13 * representations about the suitability of this software for any purpose.  It
14 * is provided "as is" without express or implied warranty.
15 *
16 * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
17 * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
18 * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
19 * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
20 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN
21 * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
22 * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
23 * SOFTWARE.
24 */
25
26#ifndef UXAPRIV_H
27#define UXAPRIV_H
28
29#ifdef HAVE_CONFIG_H
30#include <config.h>
31#endif
32#ifdef HAVE_DIX_CONFIG_H
33#include <dix-config.h>
34#else
35#include <xorg-server.h>
36#endif
37#include "xf86.h"
38
39#include "uxa.h"
40
41#include <X11/X.h>
42#define NEED_EVENTS
43#include <X11/Xproto.h>
44#ifdef MITSHM
45#ifdef HAVE_XEXTPROTO_71
46#include <X11/extensions/shm.h>
47#else
48#define _XSHM_SERVER_
49#include <X11/extensions/shmstr.h>
50#endif
51#endif
52#include "scrnintstr.h"
53#include "pixmapstr.h"
54#include "windowstr.h"
55#include "servermd.h"
56#include "colormapst.h"
57#include "gcstruct.h"
58#include "input.h"
59#include "mipointer.h"
60#include "mi.h"
61#include "dix.h"
62#include "fb.h"
63#include "fboverlay.h"
64#ifdef RENDER
65//#include "fbpict.h"
66#include "glyphstr.h"
67#endif
68#include "damage.h"
69
70/* Provide substitutes for gcc's __FUNCTION__ on other compilers */
71#if !defined(__GNUC__) && !defined(__FUNCTION__)
72# if defined(__STDC__) && (__STDC_VERSION__>=199901L) /* C99 */
73#  define __FUNCTION__ __func__
74# else
75#  define __FUNCTION__ ""
76# endif
77#endif
78
79
80/* 1.6 and earlier server compat */
81#ifndef miGetCompositeClip
82#define miCopyRegion fbCopyRegion
83#define miDoCopy fbDoCopy
84#endif
85
86#define DEBUG_MIGRATE		0
87#define DEBUG_PIXMAP		0
88#define DEBUG_OFFSCREEN		0
89#define DEBUG_GLYPH_CACHE	0
90
91#define UXA_FALLBACK(x)     					\
92if (uxa_get_screen(screen)->fallback_debug) {			\
93	ErrorF("UXA fallback at %s: ", __FUNCTION__);		\
94	ErrorF x;						\
95}
96
97char
98uxa_drawable_location(DrawablePtr pDrawable);
99
100#if DEBUG_PIXMAP
101#define DBG_PIXMAP(a) ErrorF a
102#else
103#define DBG_PIXMAP(a)
104#endif
105
106typedef struct {
107    unsigned char sha1[20];
108} uxa_cached_glyph_t;
109
110typedef struct {
111    /* The identity of the cache, statically configured at initialization */
112    unsigned int format;
113    int glyphWidth;
114    int glyphHeight;
115
116    int size; /* Size of cache; eventually this should be dynamically determined */
117
118    /* Hash table mapping from glyph sha1 to position in the glyph; we use
119     * open addressing with a hash table size determined based on size and large
120     * enough so that we always have a good amount of free space, so we can
121     * use linear probing. (Linear probing is preferrable to double hashing
122     * here because it allows us to easily remove entries.)
123     */
124    int *hashEntries;
125    int hashSize;
126
127    uxa_cached_glyph_t *glyphs;
128    int glyphCount; /* Current number of glyphs */
129
130    PicturePtr picture;   /* Where the glyphs of the cache are stored */
131    int yOffset;          /* y location within the picture where the cache starts */
132    int columns;          /* Number of columns the glyphs are layed out in */
133    int evictionPosition; /* Next random position to evict a glyph */
134} uxa_glyph_cache_t;
135
136#define UXA_NUM_GLYPH_CACHES 4
137
138typedef void (*EnableDisableFBAccessProcPtr)(int, Bool);
139typedef struct {
140    uxa_driver_t		*info;
141    CreateGCProcPtr 		 SavedCreateGC;
142    CloseScreenProcPtr 		 SavedCloseScreen;
143    GetImageProcPtr 		 SavedGetImage;
144    GetSpansProcPtr 		 SavedGetSpans;
145    CreatePixmapProcPtr 	 SavedCreatePixmap;
146    DestroyPixmapProcPtr 	 SavedDestroyPixmap;
147    CopyWindowProcPtr 		 SavedCopyWindow;
148    ChangeWindowAttributesProcPtr SavedChangeWindowAttributes;
149    BitmapToRegionProcPtr        SavedBitmapToRegion;
150#ifdef RENDER
151    CompositeProcPtr             SavedComposite;
152    TrianglesProcPtr		 SavedTriangles;
153    GlyphsProcPtr                SavedGlyphs;
154    TrapezoidsProcPtr            SavedTrapezoids;
155    AddTrapsProcPtr		 SavedAddTraps;
156#endif
157    EnableDisableFBAccessProcPtr SavedEnableDisableFBAccess;
158
159    Bool			 fallback_debug;
160    Bool			 swappedOut;
161    unsigned			 disableFbCount;
162    unsigned			 offScreenCounter;
163
164    uxa_glyph_cache_t             glyphCaches[UXA_NUM_GLYPH_CACHES];
165} uxa_screen_t;
166
167/*
168 * This is the only completely portable way to
169 * compute this info.
170 */
171#ifndef BitsPerPixel
172#define BitsPerPixel(d) (\
173    PixmapWidthPaddingInfo[d].notPower2 ? \
174    (PixmapWidthPaddingInfo[d].bytesPerPixel * 8) : \
175    ((1 << PixmapWidthPaddingInfo[d].padBytesLog2) * 8 / \
176    (PixmapWidthPaddingInfo[d].padRoundUp+1)))
177#endif
178
179extern DevPrivateKeyRec uxa_screen_index;
180static inline uxa_screen_t *
181uxa_get_screen(ScreenPtr screen)
182{
183#if HAS_DEVPRIVATEKEYREC
184    return dixGetPrivate(&screen->devPrivates, &uxa_screen_index);
185#else
186    return (uxa_screen_t *)dixLookupPrivate(&screen->devPrivates,
187					    &uxa_screen_index);
188#endif
189}
190
191/** Align an offset to an arbitrary alignment */
192#define UXA_ALIGN(offset, align) (((offset) + (align) - 1) - \
193	(((offset) + (align) - 1) % (align)))
194/** Align an offset to a power-of-two alignment */
195#define UXA_ALIGN2(offset, align) (((offset) + (align) - 1) & ~((align) - 1))
196
197typedef struct {
198    INT16 xSrc;
199    INT16 ySrc;
200    INT16 xDst;
201    INT16 yDst;
202    INT16 width;
203    INT16 height;
204} uxa_composite_rect_t;
205
206/**
207 * exaDDXDriverInit must be implemented by the DDX using EXA, and is the place
208 * to set EXA options or hook in screen functions to handle using EXA as the AA.
209  */
210void exaDDXDriverInit (ScreenPtr pScreen);
211
212Bool
213uxa_prepare_access_window(WindowPtr pWin);
214
215void
216uxa_finish_access_window(WindowPtr pWin);
217
218/* uxa-unaccel.c */
219Bool
220uxa_prepare_access_gc(GCPtr pGC);
221
222void
223uxa_finish_access_gc(GCPtr pGC);
224
225void
226uxa_check_fill_spans  (DrawablePtr pDrawable, GCPtr pGC, int nspans,
227		   DDXPointPtr ppt, int *pwidth, int fSorted);
228
229void
230uxa_check_set_spans (DrawablePtr pDrawable, GCPtr pGC, char *psrc,
231		 DDXPointPtr ppt, int *pwidth, int nspans, int fSorted);
232
233void
234uxa_check_put_image (DrawablePtr pDrawable, GCPtr pGC, int depth,
235		 int x, int y, int w, int h, int leftPad, int format,
236		 char *bits);
237
238RegionPtr
239uxa_check_copy_area (DrawablePtr pSrc, DrawablePtr pDst, GCPtr pGC,
240		 int srcx, int srcy, int w, int h, int dstx, int dsty);
241
242RegionPtr
243uxa_check_copy_plane (DrawablePtr pSrc, DrawablePtr pDst, GCPtr pGC,
244		  int srcx, int srcy, int w, int h, int dstx, int dsty,
245		  unsigned long bitPlane);
246
247void
248uxa_check_poly_point (DrawablePtr pDrawable, GCPtr pGC, int mode, int npt,
249		  DDXPointPtr pptInit);
250
251void
252uxa_check_poly_lines (DrawablePtr pDrawable, GCPtr pGC,
253		  int mode, int npt, DDXPointPtr ppt);
254
255void
256uxa_check_poly_segment (DrawablePtr pDrawable, GCPtr pGC,
257		    int nsegInit, xSegment *pSegInit);
258
259void
260uxa_check_poly_arc (DrawablePtr pDrawable, GCPtr pGC,
261		int narcs, xArc *pArcs);
262
263void
264uxa_check_poly_fill_rect (DrawablePtr pDrawable, GCPtr pGC,
265		     int nrect, xRectangle *prect);
266
267void
268uxa_check_image_glyph_blt (DrawablePtr pDrawable, GCPtr pGC,
269		      int x, int y, unsigned int nglyph,
270		      CharInfoPtr *ppci, pointer pglyphBase);
271
272void
273uxa_check_poly_glyph_blt (DrawablePtr pDrawable, GCPtr pGC,
274		     int x, int y, unsigned int nglyph,
275		     CharInfoPtr *ppci, pointer pglyphBase);
276
277void
278uxa_check_push_pixels (GCPtr pGC, PixmapPtr pBitmap,
279		   DrawablePtr pDrawable,
280		   int w, int h, int x, int y);
281
282void
283uxa_check_get_spans (DrawablePtr pDrawable,
284		 int wMax,
285		 DDXPointPtr ppt,
286		 int *pwidth,
287		 int nspans,
288		 char *pdstStart);
289
290void uxa_check_paint_window (WindowPtr pWin, RegionPtr pRegion, int what);
291
292void
293uxa_check_add_traps (PicturePtr	pPicture,
294		  INT16		x_off,
295		  INT16		y_off,
296		  int		ntrap,
297		  xTrap		*traps);
298
299/* uxa-accel.c */
300
301static _X_INLINE Bool
302uxa_gc_reads_destination(DrawablePtr pDrawable, unsigned long planemask,
303		      unsigned int fillStyle, unsigned char alu)
304{
305    return ((alu != GXcopy && alu != GXclear &&alu != GXset &&
306	     alu != GXcopyInverted) || fillStyle == FillStippled ||
307	    !UXA_PM_IS_SOLID(pDrawable, planemask));
308}
309
310void
311uxa_copy_window(WindowPtr pWin, DDXPointRec ptOldOrg, RegionPtr prgnSrc);
312
313Bool
314uxa_fill_region_tiled (DrawablePtr	pDrawable, RegionPtr pRegion, PixmapPtr pTile,
315		    DDXPointPtr pPatOrg, CARD32 planemask, CARD32 alu);
316
317void
318uxa_shm_put_image(DrawablePtr pDrawable, GCPtr pGC, int depth, unsigned int format,
319	       int w, int h, int sx, int sy, int sw, int sh, int dx, int dy,
320	       char *data);
321
322void uxa_paint_window(WindowPtr pWin, RegionPtr pRegion, int what);
323
324void
325uxa_get_image (DrawablePtr pDrawable, int x, int y, int w, int h,
326	     unsigned int format, unsigned long planeMask, char *d);
327
328extern const GCOps uxa_ops;
329
330#ifdef MITSHM
331/* XXX these come from shmint.h, which isn't exported by the server */
332
333#ifdef HAVE_XEXTPROTO_71
334#include "shmint.h"
335#else
336
337void
338ShmRegisterFuncs(ScreenPtr pScreen, ShmFuncsPtr funcs);
339
340void
341ShmSetPixmapFormat(ScreenPtr pScreen, int format);
342
343void
344fbShmPutImage(XSHM_PUT_IMAGE_ARGS);
345#endif
346
347extern ShmFuncs uxa_shm_funcs;
348
349#endif
350
351#ifdef RENDER
352
353/* XXX these are in fbpict.h, which is not installed */
354void
355fbComposite (CARD8      op,
356	     PicturePtr pSrc,
357	     PicturePtr pMask,
358	     PicturePtr pDst,
359	     INT16      xSrc,
360	     INT16      ySrc,
361	     INT16      xMask,
362	     INT16      yMask,
363	     INT16      xDst,
364	     INT16      yDst,
365	     CARD16     width,
366	     CARD16     height);
367
368void
369fbAddTraps (PicturePtr	pPicture,
370	    INT16	xOff,
371	    INT16	yOff,
372	    int		ntrap,
373	    xTrap	*traps);
374
375void
376uxa_check_composite (CARD8      op,
377		  PicturePtr pSrc,
378		  PicturePtr pMask,
379		  PicturePtr pDst,
380		  INT16      xSrc,
381		  INT16      ySrc,
382		  INT16      xMask,
383		  INT16      yMask,
384		  INT16      xDst,
385		  INT16      yDst,
386		  CARD16     width,
387		  CARD16     height);
388#endif
389
390/* uxa.c */
391Bool
392uxa_prepare_access(DrawablePtr pDrawable, uxa_access_t access);
393
394void
395uxa_finish_access(DrawablePtr pDrawable);
396
397void
398uxa_get_drawable_deltas (DrawablePtr pDrawable, PixmapPtr pPixmap,
399		      int *xp, int *yp);
400
401Bool
402uxa_drawable_is_offscreen (DrawablePtr pDrawable);
403
404Bool
405uxa_pixmap_is_offscreen(PixmapPtr p);
406
407PixmapPtr
408uxa_get_offscreen_pixmap (DrawablePtr pDrawable, int *xp, int *yp);
409
410PixmapPtr
411uxa_get_drawable_pixmap(DrawablePtr pDrawable);
412
413RegionPtr
414uxa_copy_area(DrawablePtr pSrcDrawable, DrawablePtr pDstDrawable, GCPtr pGC,
415	    int srcx, int srcy, int width, int height, int dstx, int dsty);
416
417void
418uxa_copy_n_to_n (DrawablePtr    pSrcDrawable,
419	     DrawablePtr    pDstDrawable,
420	     GCPtr	    pGC,
421	     BoxPtr	    pbox,
422	     int	    nbox,
423	     int	    dx,
424	     int	    dy,
425	     Bool	    reverse,
426	     Bool	    upsidedown,
427	     Pixel	    bitplane,
428	     void	    *closure);
429
430/* uxa_render.c */
431Bool
432uxa_op_reads_destination (CARD8 op);
433
434void
435uxa_composite(CARD8	op,
436	     PicturePtr pSrc,
437	     PicturePtr pMask,
438	     PicturePtr pDst,
439	     INT16	xSrc,
440	     INT16	ySrc,
441	     INT16	xMask,
442	     INT16	yMask,
443	     INT16	xDst,
444	     INT16	yDst,
445	     CARD16	width,
446	     CARD16	height);
447
448void
449uxa_composite_rects(CARD8	            op,
450		    PicturePtr		    pSrc,
451		    PicturePtr		    pDst,
452		    int			    nrect,
453		    uxa_composite_rect_t    *rects);
454
455void
456uxa_trapezoids (CARD8 op, PicturePtr pSrc, PicturePtr pDst,
457		PictFormatPtr maskFormat, INT16 xSrc, INT16 ySrc,
458		int ntrap, xTrapezoid *traps);
459
460void
461uxa_triangles (CARD8 op, PicturePtr pSrc, PicturePtr pDst,
462	       PictFormatPtr maskFormat, INT16 xSrc, INT16 ySrc,
463	       int ntri, xTriangle *tris);
464
465/* uxa_glyph.c */
466void
467uxa_glyphs_init(ScreenPtr pScreen);
468
469void
470uxa_glyphs_fini (ScreenPtr pScreen);
471
472void
473uxa_glyphs (CARD8	op,
474	  PicturePtr	pSrc,
475	  PicturePtr	pDst,
476	  PictFormatPtr	maskFormat,
477	  INT16		xSrc,
478	  INT16		ySrc,
479	  int		nlist,
480	  GlyphListPtr	list,
481	  GlyphPtr	*glyphs);
482
483#endif /* UXAPRIV_H */
484