root / hw / pxa2xx_template.h @ 4487fd34
History | View | Annotate | Download (11.2 kB)
1 |
/*
|
---|---|
2 |
* Intel XScale PXA255/270 LCDC emulation.
|
3 |
*
|
4 |
* Copyright (c) 2006 Openedhand Ltd.
|
5 |
* Written by Andrzej Zaborowski <balrog@zabor.org>
|
6 |
*
|
7 |
* This code is licensed under the GPLv2.
|
8 |
*
|
9 |
* Framebuffer format conversion routines.
|
10 |
*/
|
11 |
|
12 |
# define SKIP_PIXEL(to) to += deststep
|
13 |
#if BITS == 8 |
14 |
# define COPY_PIXEL(to, from) *to = from; SKIP_PIXEL(to)
|
15 |
#elif BITS == 15 || BITS == 16 |
16 |
# define COPY_PIXEL(to, from) *(uint16_t *) to = from; SKIP_PIXEL(to)
|
17 |
#elif BITS == 24 |
18 |
# define COPY_PIXEL(to, from) \
|
19 |
*(uint16_t *) to = from; *(to + 2) = (from) >> 16; SKIP_PIXEL(to) |
20 |
#elif BITS == 32 |
21 |
# define COPY_PIXEL(to, from) *(uint32_t *) to = from; SKIP_PIXEL(to)
|
22 |
#else
|
23 |
# error unknown bit depth
|
24 |
#endif
|
25 |
|
26 |
#ifdef WORDS_BIGENDIAN
|
27 |
# define SWAP_WORDS 1 |
28 |
#endif
|
29 |
|
30 |
#define FN_2(x) FN(x + 1) FN(x) |
31 |
#define FN_4(x) FN_2(x + 2) FN_2(x) |
32 |
|
33 |
static void glue(pxa2xx_draw_line2_, BITS)(uint32_t *palette, |
34 |
uint8_t *dest, const uint8_t *src, int width, int deststep) |
35 |
{ |
36 |
uint32_t data; |
37 |
while (width > 0) { |
38 |
data = *(uint32_t *) src; |
39 |
#define FN(x) COPY_PIXEL(dest, palette[(data >> ((x) * 2)) & 3]); |
40 |
#ifdef SWAP_WORDS
|
41 |
FN_4(12)
|
42 |
FN_4(8)
|
43 |
FN_4(4)
|
44 |
FN_4(0)
|
45 |
#else
|
46 |
FN_4(0)
|
47 |
FN_4(4)
|
48 |
FN_4(8)
|
49 |
FN_4(12)
|
50 |
#endif
|
51 |
#undef FN
|
52 |
width -= 16;
|
53 |
src += 4;
|
54 |
} |
55 |
} |
56 |
|
57 |
static void glue(pxa2xx_draw_line4_, BITS)(uint32_t *palette, |
58 |
uint8_t *dest, const uint8_t *src, int width, int deststep) |
59 |
{ |
60 |
uint32_t data; |
61 |
while (width > 0) { |
62 |
data = *(uint32_t *) src; |
63 |
#define FN(x) COPY_PIXEL(dest, palette[(data >> ((x) * 4)) & 0xf]); |
64 |
#ifdef SWAP_WORDS
|
65 |
FN_2(6)
|
66 |
FN_2(4)
|
67 |
FN_2(2)
|
68 |
FN_2(0)
|
69 |
#else
|
70 |
FN_2(0)
|
71 |
FN_2(2)
|
72 |
FN_2(4)
|
73 |
FN_2(6)
|
74 |
#endif
|
75 |
#undef FN
|
76 |
width -= 8;
|
77 |
src += 4;
|
78 |
} |
79 |
} |
80 |
|
81 |
static void glue(pxa2xx_draw_line8_, BITS)(uint32_t *palette, |
82 |
uint8_t *dest, const uint8_t *src, int width, int deststep) |
83 |
{ |
84 |
uint32_t data; |
85 |
while (width > 0) { |
86 |
data = *(uint32_t *) src; |
87 |
#define FN(x) COPY_PIXEL(dest, palette[(data >> (x)) & 0xff]); |
88 |
#ifdef SWAP_WORDS
|
89 |
FN(24)
|
90 |
FN(16)
|
91 |
FN(8)
|
92 |
FN(0)
|
93 |
#else
|
94 |
FN(0)
|
95 |
FN(8)
|
96 |
FN(16)
|
97 |
FN(24)
|
98 |
#endif
|
99 |
#undef FN
|
100 |
width -= 4;
|
101 |
src += 4;
|
102 |
} |
103 |
} |
104 |
|
105 |
static void glue(pxa2xx_draw_line16_, BITS)(uint32_t *palette, |
106 |
uint8_t *dest, const uint8_t *src, int width, int deststep) |
107 |
{ |
108 |
uint32_t data; |
109 |
unsigned int r, g, b; |
110 |
while (width > 0) { |
111 |
data = *(uint32_t *) src; |
112 |
#ifdef SWAP_WORDS
|
113 |
data = bswap32(data); |
114 |
#endif
|
115 |
b = (data & 0x1f) << 3; |
116 |
data >>= 5;
|
117 |
g = (data & 0x3f) << 2; |
118 |
data >>= 6;
|
119 |
r = (data & 0x1f) << 3; |
120 |
data >>= 5;
|
121 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
122 |
b = (data & 0x1f) << 3; |
123 |
data >>= 5;
|
124 |
g = (data & 0x3f) << 2; |
125 |
data >>= 6;
|
126 |
r = (data & 0x1f) << 3; |
127 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
128 |
width -= 2;
|
129 |
src += 4;
|
130 |
} |
131 |
} |
132 |
|
133 |
static void glue(pxa2xx_draw_line16t_, BITS)(uint32_t *palette, |
134 |
uint8_t *dest, const uint8_t *src, int width, int deststep) |
135 |
{ |
136 |
uint32_t data; |
137 |
unsigned int r, g, b; |
138 |
while (width > 0) { |
139 |
data = *(uint32_t *) src; |
140 |
#ifdef SWAP_WORDS
|
141 |
data = bswap32(data); |
142 |
#endif
|
143 |
b = (data & 0x1f) << 3; |
144 |
data >>= 5;
|
145 |
g = (data & 0x1f) << 3; |
146 |
data >>= 5;
|
147 |
r = (data & 0x1f) << 3; |
148 |
data >>= 5;
|
149 |
if (data & 1) |
150 |
SKIP_PIXEL(dest); |
151 |
else
|
152 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
153 |
data >>= 1;
|
154 |
b = (data & 0x1f) << 3; |
155 |
data >>= 5;
|
156 |
g = (data & 0x1f) << 3; |
157 |
data >>= 5;
|
158 |
r = (data & 0x1f) << 3; |
159 |
if (data & 1) |
160 |
SKIP_PIXEL(dest); |
161 |
else
|
162 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
163 |
width -= 2;
|
164 |
src += 4;
|
165 |
} |
166 |
} |
167 |
|
168 |
static void glue(pxa2xx_draw_line18_, BITS)(uint32_t *palette, |
169 |
uint8_t *dest, const uint8_t *src, int width, int deststep) |
170 |
{ |
171 |
uint32_t data; |
172 |
unsigned int r, g, b; |
173 |
while (width > 0) { |
174 |
data = *(uint32_t *) src; |
175 |
#ifdef SWAP_WORDS
|
176 |
data = bswap32(data); |
177 |
#endif
|
178 |
b = (data & 0x3f) << 2; |
179 |
data >>= 6;
|
180 |
g = (data & 0x3f) << 2; |
181 |
data >>= 6;
|
182 |
r = (data & 0x3f) << 2; |
183 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
184 |
width -= 1;
|
185 |
src += 4;
|
186 |
} |
187 |
} |
188 |
|
189 |
/* The wicked packed format */
|
190 |
static void glue(pxa2xx_draw_line18p_, BITS)(uint32_t *palette, |
191 |
uint8_t *dest, const uint8_t *src, int width, int deststep) |
192 |
{ |
193 |
uint32_t data[3];
|
194 |
unsigned int r, g, b; |
195 |
while (width > 0) { |
196 |
data[0] = *(uint32_t *) src;
|
197 |
src += 4;
|
198 |
data[1] = *(uint32_t *) src;
|
199 |
src += 4;
|
200 |
data[2] = *(uint32_t *) src;
|
201 |
src += 4;
|
202 |
#ifdef SWAP_WORDS
|
203 |
data[0] = bswap32(data[0]); |
204 |
data[1] = bswap32(data[1]); |
205 |
data[2] = bswap32(data[2]); |
206 |
#endif
|
207 |
b = (data[0] & 0x3f) << 2; |
208 |
data[0] >>= 6; |
209 |
g = (data[0] & 0x3f) << 2; |
210 |
data[0] >>= 6; |
211 |
r = (data[0] & 0x3f) << 2; |
212 |
data[0] >>= 12; |
213 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
214 |
b = (data[0] & 0x3f) << 2; |
215 |
data[0] >>= 6; |
216 |
g = ((data[1] & 0xf) << 4) | (data[0] << 2); |
217 |
data[1] >>= 4; |
218 |
r = (data[1] & 0x3f) << 2; |
219 |
data[1] >>= 12; |
220 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
221 |
b = (data[1] & 0x3f) << 2; |
222 |
data[1] >>= 6; |
223 |
g = (data[1] & 0x3f) << 2; |
224 |
data[1] >>= 6; |
225 |
r = ((data[2] & 0x3) << 6) | (data[1] << 2); |
226 |
data[2] >>= 8; |
227 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
228 |
b = (data[2] & 0x3f) << 2; |
229 |
data[2] >>= 6; |
230 |
g = (data[2] & 0x3f) << 2; |
231 |
data[2] >>= 6; |
232 |
r = data[2] << 2; |
233 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
234 |
width -= 4;
|
235 |
} |
236 |
} |
237 |
|
238 |
static void glue(pxa2xx_draw_line19_, BITS)(uint32_t *palette, |
239 |
uint8_t *dest, const uint8_t *src, int width, int deststep) |
240 |
{ |
241 |
uint32_t data; |
242 |
unsigned int r, g, b; |
243 |
while (width > 0) { |
244 |
data = *(uint32_t *) src; |
245 |
#ifdef SWAP_WORDS
|
246 |
data = bswap32(data); |
247 |
#endif
|
248 |
b = (data & 0x3f) << 2; |
249 |
data >>= 6;
|
250 |
g = (data & 0x3f) << 2; |
251 |
data >>= 6;
|
252 |
r = (data & 0x3f) << 2; |
253 |
data >>= 6;
|
254 |
if (data & 1) |
255 |
SKIP_PIXEL(dest); |
256 |
else
|
257 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
258 |
width -= 1;
|
259 |
src += 4;
|
260 |
} |
261 |
} |
262 |
|
263 |
/* The wicked packed format */
|
264 |
static void glue(pxa2xx_draw_line19p_, BITS)(uint32_t *palette, |
265 |
uint8_t *dest, const uint8_t *src, int width, int deststep) |
266 |
{ |
267 |
uint32_t data[3];
|
268 |
unsigned int r, g, b; |
269 |
while (width > 0) { |
270 |
data[0] = *(uint32_t *) src;
|
271 |
src += 4;
|
272 |
data[1] = *(uint32_t *) src;
|
273 |
src += 4;
|
274 |
data[2] = *(uint32_t *) src;
|
275 |
src += 4;
|
276 |
# ifdef SWAP_WORDS
|
277 |
data[0] = bswap32(data[0]); |
278 |
data[1] = bswap32(data[1]); |
279 |
data[2] = bswap32(data[2]); |
280 |
# endif
|
281 |
b = (data[0] & 0x3f) << 2; |
282 |
data[0] >>= 6; |
283 |
g = (data[0] & 0x3f) << 2; |
284 |
data[0] >>= 6; |
285 |
r = (data[0] & 0x3f) << 2; |
286 |
data[0] >>= 6; |
287 |
if (data[0] & 1) |
288 |
SKIP_PIXEL(dest); |
289 |
else
|
290 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
291 |
data[0] >>= 6; |
292 |
b = (data[0] & 0x3f) << 2; |
293 |
data[0] >>= 6; |
294 |
g = ((data[1] & 0xf) << 4) | (data[0] << 2); |
295 |
data[1] >>= 4; |
296 |
r = (data[1] & 0x3f) << 2; |
297 |
data[1] >>= 6; |
298 |
if (data[1] & 1) |
299 |
SKIP_PIXEL(dest); |
300 |
else
|
301 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
302 |
data[1] >>= 6; |
303 |
b = (data[1] & 0x3f) << 2; |
304 |
data[1] >>= 6; |
305 |
g = (data[1] & 0x3f) << 2; |
306 |
data[1] >>= 6; |
307 |
r = ((data[2] & 0x3) << 6) | (data[1] << 2); |
308 |
data[2] >>= 2; |
309 |
if (data[2] & 1) |
310 |
SKIP_PIXEL(dest); |
311 |
else
|
312 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
313 |
data[2] >>= 6; |
314 |
b = (data[2] & 0x3f) << 2; |
315 |
data[2] >>= 6; |
316 |
g = (data[2] & 0x3f) << 2; |
317 |
data[2] >>= 6; |
318 |
r = data[2] << 2; |
319 |
data[2] >>= 6; |
320 |
if (data[2] & 1) |
321 |
SKIP_PIXEL(dest); |
322 |
else
|
323 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
324 |
width -= 4;
|
325 |
} |
326 |
} |
327 |
|
328 |
static void glue(pxa2xx_draw_line24_, BITS)(uint32_t *palette, |
329 |
uint8_t *dest, const uint8_t *src, int width, int deststep) |
330 |
{ |
331 |
uint32_t data; |
332 |
unsigned int r, g, b; |
333 |
while (width > 0) { |
334 |
data = *(uint32_t *) src; |
335 |
#ifdef SWAP_WORDS
|
336 |
data = bswap32(data); |
337 |
#endif
|
338 |
b = data & 0xff;
|
339 |
data >>= 8;
|
340 |
g = data & 0xff;
|
341 |
data >>= 8;
|
342 |
r = data & 0xff;
|
343 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
344 |
width -= 1;
|
345 |
src += 4;
|
346 |
} |
347 |
} |
348 |
|
349 |
static void glue(pxa2xx_draw_line24t_, BITS)(uint32_t *palette, |
350 |
uint8_t *dest, const uint8_t *src, int width, int deststep) |
351 |
{ |
352 |
uint32_t data; |
353 |
unsigned int r, g, b; |
354 |
while (width > 0) { |
355 |
data = *(uint32_t *) src; |
356 |
#ifdef SWAP_WORDS
|
357 |
data = bswap32(data); |
358 |
#endif
|
359 |
b = (data & 0x7f) << 1; |
360 |
data >>= 7;
|
361 |
g = data & 0xff;
|
362 |
data >>= 8;
|
363 |
r = data & 0xff;
|
364 |
data >>= 8;
|
365 |
if (data & 1) |
366 |
SKIP_PIXEL(dest); |
367 |
else
|
368 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
369 |
width -= 1;
|
370 |
src += 4;
|
371 |
} |
372 |
} |
373 |
|
374 |
static void glue(pxa2xx_draw_line25_, BITS)(uint32_t *palette, |
375 |
uint8_t *dest, const uint8_t *src, int width, int deststep) |
376 |
{ |
377 |
uint32_t data; |
378 |
unsigned int r, g, b; |
379 |
while (width > 0) { |
380 |
data = *(uint32_t *) src; |
381 |
#ifdef SWAP_WORDS
|
382 |
data = bswap32(data); |
383 |
#endif
|
384 |
b = data & 0xff;
|
385 |
data >>= 8;
|
386 |
g = data & 0xff;
|
387 |
data >>= 8;
|
388 |
r = data & 0xff;
|
389 |
data >>= 8;
|
390 |
if (data & 1) |
391 |
SKIP_PIXEL(dest); |
392 |
else
|
393 |
COPY_PIXEL(dest, glue(rgb_to_pixel, BITS)(r, g, b)); |
394 |
width -= 1;
|
395 |
src += 4;
|
396 |
} |
397 |
} |
398 |
|
399 |
/* Overlay planes disabled, no transparency */
|
400 |
static drawfn glue(pxa2xx_draw_fn_, BITS)[16] = |
401 |
{ |
402 |
[0 ... 0xf] = 0, |
403 |
[pxa_lcdc_2bpp] = glue(pxa2xx_draw_line2_, BITS), |
404 |
[pxa_lcdc_4bpp] = glue(pxa2xx_draw_line4_, BITS), |
405 |
[pxa_lcdc_8bpp] = glue(pxa2xx_draw_line8_, BITS), |
406 |
[pxa_lcdc_16bpp] = glue(pxa2xx_draw_line16_, BITS), |
407 |
[pxa_lcdc_18bpp] = glue(pxa2xx_draw_line18_, BITS), |
408 |
[pxa_lcdc_18pbpp] = glue(pxa2xx_draw_line18p_, BITS), |
409 |
[pxa_lcdc_24bpp] = glue(pxa2xx_draw_line24_, BITS), |
410 |
}; |
411 |
|
412 |
/* Overlay planes enabled, transparency used */
|
413 |
static drawfn glue(glue(pxa2xx_draw_fn_, BITS), t)[16] = |
414 |
{ |
415 |
[0 ... 0xf] = 0, |
416 |
[pxa_lcdc_4bpp] = glue(pxa2xx_draw_line4_, BITS), |
417 |
[pxa_lcdc_8bpp] = glue(pxa2xx_draw_line8_, BITS), |
418 |
[pxa_lcdc_16bpp] = glue(pxa2xx_draw_line16t_, BITS), |
419 |
[pxa_lcdc_19bpp] = glue(pxa2xx_draw_line19_, BITS), |
420 |
[pxa_lcdc_19pbpp] = glue(pxa2xx_draw_line19p_, BITS), |
421 |
[pxa_lcdc_24bpp] = glue(pxa2xx_draw_line24t_, BITS), |
422 |
[pxa_lcdc_25bpp] = glue(pxa2xx_draw_line25_, BITS), |
423 |
}; |
424 |
|
425 |
#undef BITS
|
426 |
#undef COPY_PIXEL
|
427 |
#undef SKIP_PIXEL
|
428 |
|
429 |
#ifdef SWAP_WORDS
|
430 |
# undef SWAP_WORDS
|
431 |
#endif
|