1*4882a593Smuzhiyun /*
2*4882a593Smuzhiyun * Copyright © 2009 Intel Corporation
3*4882a593Smuzhiyun *
4*4882a593Smuzhiyun * Permission is hereby granted, free of charge, to any person obtaining a
5*4882a593Smuzhiyun * copy of this software and associated documentation files (the "Software"),
6*4882a593Smuzhiyun * to deal in the Software without restriction, including without limitation
7*4882a593Smuzhiyun * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8*4882a593Smuzhiyun * and/or sell copies of the Software, and to permit persons to whom the
9*4882a593Smuzhiyun * Software is furnished to do so, subject to the following conditions:
10*4882a593Smuzhiyun *
11*4882a593Smuzhiyun * The above copyright notice and this permission notice (including the next
12*4882a593Smuzhiyun * paragraph) shall be included in all copies or substantial portions of the
13*4882a593Smuzhiyun * Software.
14*4882a593Smuzhiyun *
15*4882a593Smuzhiyun * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16*4882a593Smuzhiyun * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17*4882a593Smuzhiyun * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18*4882a593Smuzhiyun * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19*4882a593Smuzhiyun * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20*4882a593Smuzhiyun * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
21*4882a593Smuzhiyun * IN THE SOFTWARE.
22*4882a593Smuzhiyun *
23*4882a593Smuzhiyun * Authors:
24*4882a593Smuzhiyun * Junyan He <junyan.he@linux.intel.com>
25*4882a593Smuzhiyun *
26*4882a593Smuzhiyun */
27*4882a593Smuzhiyun
28*4882a593Smuzhiyun /** @file glamor_trapezoid.c
29*4882a593Smuzhiyun *
30*4882a593Smuzhiyun * Trapezoid acceleration implementation
31*4882a593Smuzhiyun */
32*4882a593Smuzhiyun
33*4882a593Smuzhiyun #include "glamor_priv.h"
34*4882a593Smuzhiyun
35*4882a593Smuzhiyun #include "mipict.h"
36*4882a593Smuzhiyun #include "fbpict.h"
37*4882a593Smuzhiyun
38*4882a593Smuzhiyun /**
39*4882a593Smuzhiyun * Creates an appropriate picture for temp mask use.
40*4882a593Smuzhiyun */
41*4882a593Smuzhiyun static PicturePtr
glamor_create_mask_picture(ScreenPtr screen,PicturePtr dst,PictFormatPtr pict_format,CARD16 width,CARD16 height)42*4882a593Smuzhiyun glamor_create_mask_picture(ScreenPtr screen,
43*4882a593Smuzhiyun PicturePtr dst,
44*4882a593Smuzhiyun PictFormatPtr pict_format,
45*4882a593Smuzhiyun CARD16 width, CARD16 height)
46*4882a593Smuzhiyun {
47*4882a593Smuzhiyun PixmapPtr pixmap;
48*4882a593Smuzhiyun PicturePtr picture;
49*4882a593Smuzhiyun int error;
50*4882a593Smuzhiyun
51*4882a593Smuzhiyun if (!pict_format) {
52*4882a593Smuzhiyun if (dst->polyEdge == PolyEdgeSharp)
53*4882a593Smuzhiyun pict_format = PictureMatchFormat(screen, 1, PICT_a1);
54*4882a593Smuzhiyun else
55*4882a593Smuzhiyun pict_format = PictureMatchFormat(screen, 8, PICT_a8);
56*4882a593Smuzhiyun if (!pict_format)
57*4882a593Smuzhiyun return 0;
58*4882a593Smuzhiyun }
59*4882a593Smuzhiyun
60*4882a593Smuzhiyun pixmap = glamor_create_pixmap(screen, 0, 0,
61*4882a593Smuzhiyun pict_format->depth,
62*4882a593Smuzhiyun GLAMOR_CREATE_PIXMAP_CPU);
63*4882a593Smuzhiyun
64*4882a593Smuzhiyun if (!pixmap)
65*4882a593Smuzhiyun return 0;
66*4882a593Smuzhiyun picture = CreatePicture(0, &pixmap->drawable, pict_format,
67*4882a593Smuzhiyun 0, 0, serverClient, &error);
68*4882a593Smuzhiyun glamor_destroy_pixmap(pixmap);
69*4882a593Smuzhiyun return picture;
70*4882a593Smuzhiyun }
71*4882a593Smuzhiyun
72*4882a593Smuzhiyun /**
73*4882a593Smuzhiyun * glamor_trapezoids will generate trapezoid mask accumulating in
74*4882a593Smuzhiyun * system memory.
75*4882a593Smuzhiyun */
76*4882a593Smuzhiyun void
glamor_trapezoids(CARD8 op,PicturePtr src,PicturePtr dst,PictFormatPtr mask_format,INT16 x_src,INT16 y_src,int ntrap,xTrapezoid * traps)77*4882a593Smuzhiyun glamor_trapezoids(CARD8 op,
78*4882a593Smuzhiyun PicturePtr src, PicturePtr dst,
79*4882a593Smuzhiyun PictFormatPtr mask_format, INT16 x_src, INT16 y_src,
80*4882a593Smuzhiyun int ntrap, xTrapezoid *traps)
81*4882a593Smuzhiyun {
82*4882a593Smuzhiyun ScreenPtr screen = dst->pDrawable->pScreen;
83*4882a593Smuzhiyun BoxRec bounds;
84*4882a593Smuzhiyun PicturePtr picture;
85*4882a593Smuzhiyun INT16 x_dst, y_dst;
86*4882a593Smuzhiyun INT16 x_rel, y_rel;
87*4882a593Smuzhiyun int width, height, stride;
88*4882a593Smuzhiyun PixmapPtr pixmap;
89*4882a593Smuzhiyun pixman_image_t *image = NULL;
90*4882a593Smuzhiyun
91*4882a593Smuzhiyun /* If a mask format wasn't provided, we get to choose, but behavior should
92*4882a593Smuzhiyun * be as if there was no temporary mask the traps were accumulated into.
93*4882a593Smuzhiyun */
94*4882a593Smuzhiyun if (!mask_format) {
95*4882a593Smuzhiyun if (dst->polyEdge == PolyEdgeSharp)
96*4882a593Smuzhiyun mask_format = PictureMatchFormat(screen, 1, PICT_a1);
97*4882a593Smuzhiyun else
98*4882a593Smuzhiyun mask_format = PictureMatchFormat(screen, 8, PICT_a8);
99*4882a593Smuzhiyun for (; ntrap; ntrap--, traps++)
100*4882a593Smuzhiyun glamor_trapezoids(op, src, dst, mask_format, x_src,
101*4882a593Smuzhiyun y_src, 1, traps);
102*4882a593Smuzhiyun return;
103*4882a593Smuzhiyun }
104*4882a593Smuzhiyun
105*4882a593Smuzhiyun miTrapezoidBounds(ntrap, traps, &bounds);
106*4882a593Smuzhiyun
107*4882a593Smuzhiyun if (bounds.y1 >= bounds.y2 || bounds.x1 >= bounds.x2)
108*4882a593Smuzhiyun return;
109*4882a593Smuzhiyun
110*4882a593Smuzhiyun x_dst = traps[0].left.p1.x >> 16;
111*4882a593Smuzhiyun y_dst = traps[0].left.p1.y >> 16;
112*4882a593Smuzhiyun
113*4882a593Smuzhiyun width = bounds.x2 - bounds.x1;
114*4882a593Smuzhiyun height = bounds.y2 - bounds.y1;
115*4882a593Smuzhiyun stride = PixmapBytePad(width, mask_format->depth);
116*4882a593Smuzhiyun
117*4882a593Smuzhiyun picture = glamor_create_mask_picture(screen, dst, mask_format,
118*4882a593Smuzhiyun width, height);
119*4882a593Smuzhiyun if (!picture)
120*4882a593Smuzhiyun return;
121*4882a593Smuzhiyun
122*4882a593Smuzhiyun image = pixman_image_create_bits(picture->format,
123*4882a593Smuzhiyun width, height, NULL, stride);
124*4882a593Smuzhiyun if (!image) {
125*4882a593Smuzhiyun FreePicture(picture, 0);
126*4882a593Smuzhiyun return;
127*4882a593Smuzhiyun }
128*4882a593Smuzhiyun
129*4882a593Smuzhiyun for (; ntrap; ntrap--, traps++)
130*4882a593Smuzhiyun pixman_rasterize_trapezoid(image,
131*4882a593Smuzhiyun (pixman_trapezoid_t *) traps,
132*4882a593Smuzhiyun -bounds.x1, -bounds.y1);
133*4882a593Smuzhiyun
134*4882a593Smuzhiyun pixmap = glamor_get_drawable_pixmap(picture->pDrawable);
135*4882a593Smuzhiyun
136*4882a593Smuzhiyun screen->ModifyPixmapHeader(pixmap, width, height,
137*4882a593Smuzhiyun mask_format->depth,
138*4882a593Smuzhiyun BitsPerPixel(mask_format->depth),
139*4882a593Smuzhiyun PixmapBytePad(width,
140*4882a593Smuzhiyun mask_format->depth),
141*4882a593Smuzhiyun pixman_image_get_data(image));
142*4882a593Smuzhiyun
143*4882a593Smuzhiyun x_rel = bounds.x1 + x_src - x_dst;
144*4882a593Smuzhiyun y_rel = bounds.y1 + y_src - y_dst;
145*4882a593Smuzhiyun
146*4882a593Smuzhiyun CompositePicture(op, src, picture, dst,
147*4882a593Smuzhiyun x_rel, y_rel,
148*4882a593Smuzhiyun 0, 0,
149*4882a593Smuzhiyun bounds.x1, bounds.y1,
150*4882a593Smuzhiyun bounds.x2 - bounds.x1, bounds.y2 - bounds.y1);
151*4882a593Smuzhiyun
152*4882a593Smuzhiyun if (image)
153*4882a593Smuzhiyun pixman_image_unref(image);
154*4882a593Smuzhiyun
155*4882a593Smuzhiyun FreePicture(picture, 0);
156*4882a593Smuzhiyun }
157