w32tex
About: TeX Live provides a comprehensive TeX system including all the major TeX-related programs, macro packages, and fonts that are free software. Windows sources.
  Fossies Dox: w32tex-src.tar.xz  ("unofficial" and yet experimental doxygen-generated source code documentation)  

pixman-access.c
Go to the documentation of this file.
1 /*
2  *
3  * Copyright © 2000 Keith Packard, member of The XFree86 Project, Inc.
4  * 2005 Lars Knoll & Zack Rusin, Trolltech
5  * 2008 Aaron Plattner, NVIDIA Corporation
6  *
7  * Permission to use, copy, modify, distribute, and sell this software and its
8  * documentation for any purpose is hereby granted without fee, provided that
9  * the above copyright notice appear in all copies and that both that
10  * copyright notice and this permission notice appear in supporting
11  * documentation, and that the name of Keith Packard not be used in
12  * advertising or publicity pertaining to distribution of the software without
13  * specific, written prior permission. Keith Packard makes no
14  * representations about the suitability of this software for any purpose. It
15  * is provided "as is" without express or implied warranty.
16  *
17  * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
18  * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
19  * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
20  * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
21  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN
22  * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
23  * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
24  * SOFTWARE.
25  */
26 
27 #ifdef HAVE_CONFIG_H
28 #include <config.h>
29 #endif
30 
31 #include <stdlib.h>
32 #include <string.h>
33 #include <assert.h>
34 #include <math.h>
35 
36 #include "pixman-accessor.h"
37 #include "pixman-private.h"
38 
39 #define CONVERT_RGB24_TO_Y15(s) \
40  (((((s) >> 16) & 0xff) * 153 + \
41  (((s) >> 8) & 0xff) * 301 + \
42  (((s) ) & 0xff) * 58) >> 2)
43 
44 #define CONVERT_RGB24_TO_RGB15(s) \
45  ((((s) >> 3) & 0x001f) | \
46  (((s) >> 6) & 0x03e0) | \
47  (((s) >> 9) & 0x7c00))
48 
49 /* Fetch macros */
50 
51 #ifdef WORDS_BIGENDIAN
52 #define FETCH_1(img,l,o) \
53  (((READ ((img), ((uint32_t *)(l)) + ((o) >> 5))) >> (0x1f - ((o) & 0x1f))) & 0x1)
54 #else
55 #define FETCH_1(img,l,o) \
56  ((((READ ((img), ((uint32_t *)(l)) + ((o) >> 5))) >> ((o) & 0x1f))) & 0x1)
57 #endif
58 
59 #define FETCH_8(img,l,o) (READ (img, (((uint8_t *)(l)) + ((o) >> 3))))
60 
61 #ifdef WORDS_BIGENDIAN
62 #define FETCH_4(img,l,o) \
63  (((4 * (o)) & 4) ? (FETCH_8 (img,l, 4 * (o)) & 0xf) : (FETCH_8 (img,l,(4 * (o))) >> 4))
64 #else
65 #define FETCH_4(img,l,o) \
66  (((4 * (o)) & 4) ? (FETCH_8 (img, l, 4 * (o)) >> 4) : (FETCH_8 (img, l, (4 * (o))) & 0xf))
67 #endif
68 
69 #ifdef WORDS_BIGENDIAN
70 #define FETCH_24(img,l,o) \
71  ((uint32_t)(READ (img, (((uint8_t *)(l)) + ((o) * 3) + 0)) << 16) | \
72  (uint32_t)(READ (img, (((uint8_t *)(l)) + ((o) * 3) + 1)) << 8) | \
73  (uint32_t)(READ (img, (((uint8_t *)(l)) + ((o) * 3) + 2)) << 0))
74 #else
75 #define FETCH_24(img,l,o) \
76  ((uint32_t)(READ (img, (((uint8_t *)(l)) + ((o) * 3) + 0)) << 0) | \
77  (uint32_t)(READ (img, (((uint8_t *)(l)) + ((o) * 3) + 1)) << 8) | \
78  (uint32_t)(READ (img, (((uint8_t *)(l)) + ((o) * 3) + 2)) << 16))
79 #endif
80 
81 /* Store macros */
82 
83 #ifdef WORDS_BIGENDIAN
84 #define STORE_1(img,l,o,v) \
85  do \
86  { \
87  uint32_t *__d = ((uint32_t *)(l)) + ((o) >> 5); \
88  uint32_t __m, __v; \
89  \
90  __m = 1U << (0x1f - ((o) & 0x1f)); \
91  __v = (v)? __m : 0; \
92  \
93  WRITE((img), __d, (READ((img), __d) & ~__m) | __v); \
94  } \
95  while (0)
96 #else
97 #define STORE_1(img,l,o,v) \
98  do \
99  { \
100  uint32_t *__d = ((uint32_t *)(l)) + ((o) >> 5); \
101  uint32_t __m, __v; \
102  \
103  __m = 1U << ((o) & 0x1f); \
104  __v = (v)? __m : 0; \
105  \
106  WRITE((img), __d, (READ((img), __d) & ~__m) | __v); \
107  } \
108  while (0)
109 #endif
110 
111 #define STORE_8(img,l,o,v) (WRITE (img, (uint8_t *)(l) + ((o) >> 3), (v)))
112 
113 #ifdef WORDS_BIGENDIAN
114 #define STORE_4(img,l,o,v) \
115  do \
116  { \
117  int bo = 4 * (o); \
118  int v4 = (v) & 0x0f; \
119  \
120  STORE_8 (img, l, bo, ( \
121  bo & 4 ? \
122  (FETCH_8 (img, l, bo) & 0xf0) | (v4) : \
123  (FETCH_8 (img, l, bo) & 0x0f) | (v4 << 4))); \
124  } while (0)
125 #else
126 #define STORE_4(img,l,o,v) \
127  do \
128  { \
129  int bo = 4 * (o); \
130  int v4 = (v) & 0x0f; \
131  \
132  STORE_8 (img, l, bo, ( \
133  bo & 4 ? \
134  (FETCH_8 (img, l, bo) & 0x0f) | (v4 << 4) : \
135  (FETCH_8 (img, l, bo) & 0xf0) | (v4))); \
136  } while (0)
137 #endif
138 
139 #ifdef WORDS_BIGENDIAN
140 #define STORE_24(img,l,o,v) \
141  do \
142  { \
143  uint8_t *__tmp = (l) + 3 * (o); \
144  \
145  WRITE ((img), __tmp++, ((v) & 0x00ff0000) >> 16); \
146  WRITE ((img), __tmp++, ((v) & 0x0000ff00) >> 8); \
147  WRITE ((img), __tmp++, ((v) & 0x000000ff) >> 0); \
148  } \
149  while (0)
150 #else
151 #define STORE_24(img,l,o,v) \
152  do \
153  { \
154  uint8_t *__tmp = (l) + 3 * (o); \
155  \
156  WRITE ((img), __tmp++, ((v) & 0x000000ff) >> 0); \
157  WRITE ((img), __tmp++, ((v) & 0x0000ff00) >> 8); \
158  WRITE ((img), __tmp++, ((v) & 0x00ff0000) >> 16); \
159  } \
160  while (0)
161 #endif
162 
163 /*
164  * YV12 setup and access macros
165  */
166 
167 #define YV12_SETUP(image) \
168  bits_image_t *__bits_image = (bits_image_t *)image; \
169  uint32_t *bits = __bits_image->bits; \
170  int stride = __bits_image->rowstride; \
171  int offset0 = stride < 0 ? \
172  ((-stride) >> 1) * ((__bits_image->height - 1) >> 1) - stride : \
173  stride * __bits_image->height; \
174  int offset1 = stride < 0 ? \
175  offset0 + ((-stride) >> 1) * ((__bits_image->height) >> 1) : \
176  offset0 + (offset0 >> 2)
177 
178 /* Note no trailing semicolon on the above macro; if it's there, then
179  * the typical usage of YV12_SETUP(image); will have an extra trailing ;
180  * that some compilers will interpret as a statement -- and then any further
181  * variable declarations will cause an error.
182  */
183 
184 #define YV12_Y(line) \
185  ((uint8_t *) ((bits) + (stride) * (line)))
186 
187 #define YV12_U(line) \
188  ((uint8_t *) ((bits) + offset1 + \
189  ((stride) >> 1) * ((line) >> 1)))
190 
191 #define YV12_V(line) \
192  ((uint8_t *) ((bits) + offset0 + \
193  ((stride) >> 1) * ((line) >> 1)))
194 
195 /* Misc. helpers */
196 
197 static force_inline void
199  int *a,
200  int *r,
201  int *g,
202  int *b)
203 {
204  switch (PIXMAN_FORMAT_TYPE (format))
205  {
206  case PIXMAN_TYPE_A:
207  *b = 0;
208  *g = 0;
209  *r = 0;
210  *a = 0;
211  break;
212 
213  case PIXMAN_TYPE_ARGB:
215  *b = 0;
216  *g = *b + PIXMAN_FORMAT_B (format);
217  *r = *g + PIXMAN_FORMAT_G (format);
218  *a = *r + PIXMAN_FORMAT_R (format);
219  break;
220 
221  case PIXMAN_TYPE_ABGR:
222  *r = 0;
223  *g = *r + PIXMAN_FORMAT_R (format);
224  *b = *g + PIXMAN_FORMAT_G (format);
225  *a = *b + PIXMAN_FORMAT_B (format);
226  break;
227 
228  case PIXMAN_TYPE_BGRA:
229  /* With BGRA formats we start counting at the high end of the pixel */
231  *g = *b - PIXMAN_FORMAT_B (format);
232  *r = *g - PIXMAN_FORMAT_G (format);
233  *a = *r - PIXMAN_FORMAT_R (format);
234  break;
235 
236  case PIXMAN_TYPE_RGBA:
237  /* With BGRA formats we start counting at the high end of the pixel */
239  *g = *r - PIXMAN_FORMAT_R (format);
240  *b = *g - PIXMAN_FORMAT_G (format);
241  *a = *b - PIXMAN_FORMAT_B (format);
242  break;
243 
244  default:
245  assert (0);
246  break;
247  }
248 }
249 
250 static force_inline uint32_t
252  int n_from_bits, int from_shift,
253  int n_to_bits, int to_shift)
254 {
255  uint32_t v;
256 
257  if (n_from_bits && n_to_bits)
258  v = unorm_to_unorm (pixel >> from_shift, n_from_bits, n_to_bits);
259  else if (n_to_bits)
260  v = def_value;
261  else
262  v = 0;
263 
264  return (v & ((1 << n_to_bits) - 1)) << to_shift;
265 }
266 
267 static force_inline uint32_t
269 {
270  int a_from_shift, r_from_shift, g_from_shift, b_from_shift;
271  int a_to_shift, r_to_shift, g_to_shift, b_to_shift;
272  uint32_t a, r, g, b;
273 
274  get_shifts (from, &a_from_shift, &r_from_shift, &g_from_shift, &b_from_shift);
275  get_shifts (to, &a_to_shift, &r_to_shift, &g_to_shift, &b_to_shift);
276 
277  a = convert_channel (pixel, ~0,
278  PIXMAN_FORMAT_A (from), a_from_shift,
279  PIXMAN_FORMAT_A (to), a_to_shift);
280 
281  r = convert_channel (pixel, 0,
282  PIXMAN_FORMAT_R (from), r_from_shift,
283  PIXMAN_FORMAT_R (to), r_to_shift);
284 
285  g = convert_channel (pixel, 0,
286  PIXMAN_FORMAT_G (from), g_from_shift,
287  PIXMAN_FORMAT_G (to), g_to_shift);
288 
289  b = convert_channel (pixel, 0,
290  PIXMAN_FORMAT_B (from), b_from_shift,
291  PIXMAN_FORMAT_B (to), b_to_shift);
292 
293  return a | r | g | b;
294 }
295 
296 static force_inline uint32_t
299  uint32_t pixel)
300 {
303  {
304  return image->indexed->rgba[pixel];
305  }
306  else
307  {
309  }
310 }
311 
312 static force_inline uint32_t
315 {
317  {
319 
320  return image->bits.indexed->ent[pixel & 0x7fff];
321  }
323  {
325 
326  return image->bits.indexed->ent[pixel & 0x7fff];
327  }
328  else
329  {
331  }
332 }
333 
334 static force_inline uint32_t
336  const uint8_t * bits,
337  int offset,
339 {
340  uint32_t pixel;
341 
342  switch (PIXMAN_FORMAT_BPP (format))
343  {
344  case 1:
345  pixel = FETCH_1 (image, bits, offset);
346  break;
347 
348  case 4:
349  pixel = FETCH_4 (image, bits, offset);
350  break;
351 
352  case 8:
353  pixel = READ (image, bits + offset);
354  break;
355 
356  case 16:
357  pixel = READ (image, ((uint16_t *)bits + offset));
358  break;
359 
360  case 24:
362  break;
363 
364  case 32:
365  pixel = READ (image, ((uint32_t *)bits + offset));
366  break;
367 
368  default:
369  pixel = 0xffff00ff; /* As ugly as possible to detect the bug */
370  break;
371  }
372 
374 }
375 
376 static force_inline void
378  uint8_t * dest,
379  int offset,
381  uint32_t pixel)
382 {
385 
386  switch (PIXMAN_FORMAT_BPP (format))
387  {
388  case 1:
389  STORE_1 (image, dest, offset, converted & 0x01);
390  break;
391 
392  case 4:
393  STORE_4 (image, dest, offset, converted & 0xf);
394  break;
395 
396  case 8:
397  WRITE (image, (dest + offset), converted & 0xff);
398  break;
399 
400  case 16:
401  WRITE (image, ((uint16_t *)dest + offset), converted & 0xffff);
402  break;
403 
404  case 24:
405  STORE_24 (image, dest, offset, converted);
406  break;
407 
408  case 32:
409  WRITE (image, ((uint32_t *)dest + offset), converted);
410  break;
411 
412  default:
413  *dest = 0x0;
414  break;
415  }
416 }
417 
418 #define MAKE_ACCESSORS(format) \
419  static void \
420  fetch_scanline_ ## format (bits_image_t *image, \
421  int x, \
422  int y, \
423  int width, \
424  uint32_t * buffer, \
425  const uint32_t *mask) \
426  { \
427  uint8_t *bits = \
428  (uint8_t *)(image->bits + y * image->rowstride); \
429  int i; \
430  \
431  for (i = 0; i < width; ++i) \
432  { \
433  *buffer++ = \
434  fetch_and_convert_pixel (image, bits, x + i, PIXMAN_ ## format); \
435  } \
436  } \
437  \
438  static void \
439  store_scanline_ ## format (bits_image_t * image, \
440  int x, \
441  int y, \
442  int width, \
443  const uint32_t *values) \
444  { \
445  uint8_t *dest = \
446  (uint8_t *)(image->bits + y * image->rowstride); \
447  int i; \
448  \
449  for (i = 0; i < width; ++i) \
450  { \
451  convert_and_store_pixel ( \
452  image, dest, i + x, PIXMAN_ ## format, values[i]); \
453  } \
454  } \
455  \
456  static uint32_t \
457  fetch_pixel_ ## format (bits_image_t *image, \
458  int offset, \
459  int line) \
460  { \
461  uint8_t *bits = \
462  (uint8_t *)(image->bits + line * image->rowstride); \
463  \
464  return fetch_and_convert_pixel ( \
465  image, bits, offset, PIXMAN_ ## format); \
466  } \
467  \
468  static const void *const __dummy__ ## format
469 
470 MAKE_ACCESSORS(a8r8g8b8);
471 MAKE_ACCESSORS(x8r8g8b8);
472 MAKE_ACCESSORS(a8b8g8r8);
473 MAKE_ACCESSORS(x8b8g8r8);
474 MAKE_ACCESSORS(x14r6g6b6);
475 MAKE_ACCESSORS(b8g8r8a8);
476 MAKE_ACCESSORS(b8g8r8x8);
477 MAKE_ACCESSORS(r8g8b8x8);
478 MAKE_ACCESSORS(r8g8b8a8);
483 MAKE_ACCESSORS(a1r5g5b5);
484 MAKE_ACCESSORS(x1r5g5b5);
485 MAKE_ACCESSORS(a1b5g5r5);
486 MAKE_ACCESSORS(x1b5g5r5);
487 MAKE_ACCESSORS(a4r4g4b4);
488 MAKE_ACCESSORS(x4r4g4b4);
489 MAKE_ACCESSORS(a4b4g4r4);
490 MAKE_ACCESSORS(x4b4g4r4);
496 MAKE_ACCESSORS(a2r2g2b2);
497 MAKE_ACCESSORS(a2b2g2r2);
504 MAKE_ACCESSORS(a1r1g1b1);
505 MAKE_ACCESSORS(a1b1g1r1);
508 
509 /********************************** Fetch ************************************/
510 /* Table mapping sRGB-encoded 8 bit numbers to linearly encoded
511  * floating point numbers. We assume that single precision
512  * floating point follows the IEEE 754 format.
513  */
514 static const uint32_t to_linear_u[256] =
515 {
516  0x00000000, 0x399f22b4, 0x3a1f22b4, 0x3a6eb40e, 0x3a9f22b4, 0x3ac6eb61,
517  0x3aeeb40e, 0x3b0b3e5d, 0x3b1f22b4, 0x3b33070b, 0x3b46eb61, 0x3b5b518a,
518  0x3b70f18a, 0x3b83e1c5, 0x3b8fe614, 0x3b9c87fb, 0x3ba9c9b5, 0x3bb7ad6d,
519  0x3bc63547, 0x3bd5635f, 0x3be539bd, 0x3bf5ba70, 0x3c0373b5, 0x3c0c6152,
520  0x3c15a703, 0x3c1f45bc, 0x3c293e68, 0x3c3391f4, 0x3c3e4149, 0x3c494d43,
521  0x3c54b6c7, 0x3c607eb1, 0x3c6ca5df, 0x3c792d22, 0x3c830aa8, 0x3c89af9e,
522  0x3c9085db, 0x3c978dc5, 0x3c9ec7c0, 0x3ca63432, 0x3cadd37d, 0x3cb5a601,
523  0x3cbdac20, 0x3cc5e639, 0x3cce54ab, 0x3cd6f7d2, 0x3cdfd00e, 0x3ce8ddb9,
524  0x3cf2212c, 0x3cfb9ac1, 0x3d02a569, 0x3d0798dc, 0x3d0ca7e4, 0x3d11d2ae,
525  0x3d171963, 0x3d1c7c2e, 0x3d21fb3a, 0x3d2796af, 0x3d2d4ebb, 0x3d332380,
526  0x3d39152b, 0x3d3f23e3, 0x3d454fd0, 0x3d4b991c, 0x3d51ffeb, 0x3d588466,
527  0x3d5f26b7, 0x3d65e6fe, 0x3d6cc564, 0x3d73c210, 0x3d7add25, 0x3d810b65,
528  0x3d84b793, 0x3d88732e, 0x3d8c3e48, 0x3d9018f4, 0x3d940343, 0x3d97fd48,
529  0x3d9c0714, 0x3da020b9, 0x3da44a48, 0x3da883d6, 0x3daccd70, 0x3db12728,
530  0x3db59110, 0x3dba0b38, 0x3dbe95b2, 0x3dc3308f, 0x3dc7dbe0, 0x3dcc97b4,
531  0x3dd1641c, 0x3dd6412a, 0x3ddb2eec, 0x3de02d75, 0x3de53cd3, 0x3dea5d16,
532  0x3def8e52, 0x3df4d091, 0x3dfa23e5, 0x3dff885e, 0x3e027f06, 0x3e05427f,
533  0x3e080ea2, 0x3e0ae376, 0x3e0dc104, 0x3e10a752, 0x3e139669, 0x3e168e50,
534  0x3e198f0e, 0x3e1c98ab, 0x3e1fab2e, 0x3e22c6a0, 0x3e25eb08, 0x3e29186a,
535  0x3e2c4ed0, 0x3e2f8e42, 0x3e32d6c4, 0x3e362861, 0x3e39831e, 0x3e3ce702,
536  0x3e405416, 0x3e43ca5e, 0x3e4749e4, 0x3e4ad2ae, 0x3e4e64c2, 0x3e520027,
537  0x3e55a4e6, 0x3e595303, 0x3e5d0a8a, 0x3e60cb7c, 0x3e6495e0, 0x3e6869bf,
538  0x3e6c4720, 0x3e702e08, 0x3e741e7f, 0x3e78188c, 0x3e7c1c34, 0x3e8014c0,
539  0x3e822039, 0x3e84308b, 0x3e8645b8, 0x3e885fc3, 0x3e8a7eb0, 0x3e8ca281,
540  0x3e8ecb3a, 0x3e90f8df, 0x3e932b72, 0x3e9562f6, 0x3e979f6f, 0x3e99e0e0,
541  0x3e9c274e, 0x3e9e72b8, 0x3ea0c322, 0x3ea31892, 0x3ea57308, 0x3ea7d28a,
542  0x3eaa3718, 0x3eaca0b7, 0x3eaf0f69, 0x3eb18332, 0x3eb3fc16, 0x3eb67a15,
543  0x3eb8fd34, 0x3ebb8576, 0x3ebe12de, 0x3ec0a56e, 0x3ec33d2a, 0x3ec5da14,
544  0x3ec87c30, 0x3ecb2380, 0x3ecdd008, 0x3ed081ca, 0x3ed338c9, 0x3ed5f508,
545  0x3ed8b68a, 0x3edb7d52, 0x3ede4962, 0x3ee11abe, 0x3ee3f168, 0x3ee6cd64,
546  0x3ee9aeb6, 0x3eec955d, 0x3eef815d, 0x3ef272ba, 0x3ef56976, 0x3ef86594,
547  0x3efb6717, 0x3efe6e02, 0x3f00bd2b, 0x3f02460c, 0x3f03d1a5, 0x3f055ff8,
548  0x3f06f105, 0x3f0884ce, 0x3f0a1b54, 0x3f0bb499, 0x3f0d509f, 0x3f0eef65,
549  0x3f1090ef, 0x3f12353c, 0x3f13dc50, 0x3f15862a, 0x3f1732cc, 0x3f18e237,
550  0x3f1a946d, 0x3f1c4970, 0x3f1e013f, 0x3f1fbbde, 0x3f21794c, 0x3f23398c,
551  0x3f24fca0, 0x3f26c286, 0x3f288b42, 0x3f2a56d3, 0x3f2c253d, 0x3f2df680,
552  0x3f2fca9d, 0x3f31a195, 0x3f337b6a, 0x3f35581e, 0x3f3737b1, 0x3f391a24,
553  0x3f3aff7a, 0x3f3ce7b2, 0x3f3ed2d0, 0x3f40c0d2, 0x3f42b1bc, 0x3f44a58e,
554  0x3f469c49, 0x3f4895ee, 0x3f4a9280, 0x3f4c91ff, 0x3f4e946c, 0x3f5099c8,
555  0x3f52a216, 0x3f54ad55, 0x3f56bb88, 0x3f58ccae, 0x3f5ae0cb, 0x3f5cf7de,
556  0x3f5f11ec, 0x3f612ef0, 0x3f634eef, 0x3f6571ea, 0x3f6797e1, 0x3f69c0d6,
557  0x3f6beccb, 0x3f6e1bc0, 0x3f704db6, 0x3f7282af, 0x3f74baac, 0x3f76f5ae,
558  0x3f7933b6, 0x3f7b74c6, 0x3f7db8de, 0x3f800000
559 };
560 
561 static const float * const to_linear = (const float *)to_linear_u;
562 
563 static uint8_t
564 to_srgb (float f)
565 {
566  uint8_t low = 0;
567  uint8_t high = 255;
568 
569  while (high - low > 1)
570  {
571  uint8_t mid = (low + high) / 2;
572 
573  if (to_linear[mid] > f)
574  high = mid;
575  else
576  low = mid;
577  }
578 
579  if (to_linear[high] - f < f - to_linear[low])
580  return high;
581  else
582  return low;
583 }
584 
585 static void
587  int x,
588  int y,
589  int width,
590  uint32_t * b,
591  const uint32_t *mask)
592 {
593  const uint32_t *bits = image->bits + y * image->rowstride;
594  const uint32_t *pixel = bits + x;
595  const uint32_t *end = pixel + width;
596  argb_t *buffer = (argb_t *)b;
597 
598  while (pixel < end)
599  {
600  uint32_t p = READ (image, pixel++);
601  argb_t *argb = buffer;
602 
603  argb->a = pixman_unorm_to_float ((p >> 24) & 0xff, 8);
604 
605  argb->r = to_linear [(p >> 16) & 0xff];
606  argb->g = to_linear [(p >> 8) & 0xff];
607  argb->b = to_linear [(p >> 0) & 0xff];
608 
609  buffer++;
610  }
611 }
612 
613 /* Expects a float buffer */
614 static void
616  int x,
617  int y,
618  int width,
619  uint32_t * b,
620  const uint32_t *mask)
621 {
622  const uint32_t *bits = image->bits + y * image->rowstride;
623  const uint32_t *pixel = bits + x;
624  const uint32_t *end = pixel + width;
625  argb_t *buffer = (argb_t *)b;
626 
627  while (pixel < end)
628  {
629  uint32_t p = READ (image, pixel++);
630  uint64_t a = p >> 30;
631  uint64_t r = (p >> 20) & 0x3ff;
632  uint64_t g = (p >> 10) & 0x3ff;
633  uint64_t b = p & 0x3ff;
634 
635  buffer->a = pixman_unorm_to_float (a, 2);
636  buffer->r = pixman_unorm_to_float (r, 10);
637  buffer->g = pixman_unorm_to_float (g, 10);
638  buffer->b = pixman_unorm_to_float (b, 10);
639 
640  buffer++;
641  }
642 }
643 
644 /* Expects a float buffer */
645 #ifndef PIXMAN_FB_ACCESSORS
646 static void
647 fetch_scanline_rgbf_float (bits_image_t *image,
648  int x,
649  int y,
650  int width,
651  uint32_t * b,
652  const uint32_t *mask)
653 {
654  const float *bits = (float *)image->bits + y * image->rowstride;
655  const float *pixel = bits + x * 3;
656  argb_t *buffer = (argb_t *)b;
657 
658  for (; width--; buffer++) {
659  buffer->r = *pixel++;
660  buffer->g = *pixel++;
661  buffer->b = *pixel++;
662  buffer->a = 1.f;
663  }
664 }
665 
666 static void
667 fetch_scanline_rgbaf_float (bits_image_t *image,
668  int x,
669  int y,
670  int width,
671  uint32_t * b,
672  const uint32_t *mask)
673 {
674  const float *bits = (float *)image->bits + y * image->rowstride;
675  const float *pixel = bits + x * 4;
676  argb_t *buffer = (argb_t *)b;
677 
678  for (; width--; buffer++) {
679  buffer->r = *pixel++;
680  buffer->g = *pixel++;
681  buffer->b = *pixel++;
682  buffer->a = *pixel++;
683  }
684 }
685 #endif
686 
687 static void
689  int x,
690  int y,
691  int width,
692  uint32_t * b,
693  const uint32_t *mask)
694 {
695  const uint32_t *bits = image->bits + y * image->rowstride;
696  const uint32_t *pixel = (uint32_t *)bits + x;
697  const uint32_t *end = pixel + width;
698  argb_t *buffer = (argb_t *)b;
699 
700  while (pixel < end)
701  {
702  uint32_t p = READ (image, pixel++);
703  uint64_t r = (p >> 20) & 0x3ff;
704  uint64_t g = (p >> 10) & 0x3ff;
705  uint64_t b = p & 0x3ff;
706 
707  buffer->a = 1.0;
708  buffer->r = pixman_unorm_to_float (r, 10);
709  buffer->g = pixman_unorm_to_float (g, 10);
710  buffer->b = pixman_unorm_to_float (b, 10);
711 
712  buffer++;
713  }
714 }
715 
716 /* Expects a float buffer */
717 static void
719  int x,
720  int y,
721  int width,
722  uint32_t * b,
723  const uint32_t *mask)
724 {
725  const uint32_t *bits = image->bits + y * image->rowstride;
726  const uint32_t *pixel = bits + x;
727  const uint32_t *end = pixel + width;
728  argb_t *buffer = (argb_t *)b;
729 
730  while (pixel < end)
731  {
732  uint32_t p = READ (image, pixel++);
733  uint64_t a = p >> 30;
734  uint64_t b = (p >> 20) & 0x3ff;
735  uint64_t g = (p >> 10) & 0x3ff;
736  uint64_t r = p & 0x3ff;
737 
738  buffer->a = pixman_unorm_to_float (a, 2);
739  buffer->r = pixman_unorm_to_float (r, 10);
740  buffer->g = pixman_unorm_to_float (g, 10);
741  buffer->b = pixman_unorm_to_float (b, 10);
742 
743  buffer++;
744  }
745 }
746 
747 /* Expects a float buffer */
748 static void
750  int x,
751  int y,
752  int width,
753  uint32_t * b,
754  const uint32_t *mask)
755 {
756  const uint32_t *bits = image->bits + y * image->rowstride;
757  const uint32_t *pixel = (uint32_t *)bits + x;
758  const uint32_t *end = pixel + width;
759  argb_t *buffer = (argb_t *)b;
760 
761  while (pixel < end)
762  {
763  uint32_t p = READ (image, pixel++);
764  uint64_t b = (p >> 20) & 0x3ff;
765  uint64_t g = (p >> 10) & 0x3ff;
766  uint64_t r = p & 0x3ff;
767 
768  buffer->a = 1.0;
769  buffer->r = pixman_unorm_to_float (r, 10);
770  buffer->g = pixman_unorm_to_float (g, 10);
771  buffer->b = pixman_unorm_to_float (b, 10);
772 
773  buffer++;
774  }
775 }
776 
777 static void
779  int x,
780  int line,
781  int width,
782  uint32_t * buffer,
783  const uint32_t *mask)
784 {
785  const uint32_t *bits = image->bits + image->rowstride * line;
786  int i;
787 
788  for (i = 0; i < width; i++)
789  {
790  int16_t y, u, v;
791  int32_t r, g, b;
792 
793  y = ((uint8_t *) bits)[(x + i) << 1] - 16;
794  u = ((uint8_t *) bits)[(((x + i) << 1) & - 4) + 1] - 128;
795  v = ((uint8_t *) bits)[(((x + i) << 1) & - 4) + 3] - 128;
796 
797  /* R = 1.164(Y - 16) + 1.596(V - 128) */
798  r = 0x012b27 * y + 0x019a2e * v;
799  /* G = 1.164(Y - 16) - 0.813(V - 128) - 0.391(U - 128) */
800  g = 0x012b27 * y - 0x00d0f2 * v - 0x00647e * u;
801  /* B = 1.164(Y - 16) + 2.018(U - 128) */
802  b = 0x012b27 * y + 0x0206a2 * u;
803 
804  *buffer++ = 0xff000000 |
805  (r >= 0 ? r < 0x1000000 ? r & 0xff0000 : 0xff0000 : 0) |
806  (g >= 0 ? g < 0x1000000 ? (g >> 8) & 0x00ff00 : 0x00ff00 : 0) |
807  (b >= 0 ? b < 0x1000000 ? (b >> 16) & 0x0000ff : 0x0000ff : 0);
808  }
809 }
810 
811 static void
813  int x,
814  int line,
815  int width,
816  uint32_t * buffer,
817  const uint32_t *mask)
818 {
819  YV12_SETUP (image);
820  uint8_t *y_line = YV12_Y (line);
821  uint8_t *u_line = YV12_U (line);
822  uint8_t *v_line = YV12_V (line);
823  int i;
824 
825  for (i = 0; i < width; i++)
826  {
827  int16_t y, u, v;
828  int32_t r, g, b;
829 
830  y = y_line[x + i] - 16;
831  u = u_line[(x + i) >> 1] - 128;
832  v = v_line[(x + i) >> 1] - 128;
833 
834  /* R = 1.164(Y - 16) + 1.596(V - 128) */
835  r = 0x012b27 * y + 0x019a2e * v;
836  /* G = 1.164(Y - 16) - 0.813(V - 128) - 0.391(U - 128) */
837  g = 0x012b27 * y - 0x00d0f2 * v - 0x00647e * u;
838  /* B = 1.164(Y - 16) + 2.018(U - 128) */
839  b = 0x012b27 * y + 0x0206a2 * u;
840 
841  *buffer++ = 0xff000000 |
842  (r >= 0 ? r < 0x1000000 ? r & 0xff0000 : 0xff0000 : 0) |
843  (g >= 0 ? g < 0x1000000 ? (g >> 8) & 0x00ff00 : 0x00ff00 : 0) |
844  (b >= 0 ? b < 0x1000000 ? (b >> 16) & 0x0000ff : 0x0000ff : 0);
845  }
846 }
847 
848 /**************************** Pixel wise fetching *****************************/
849 
850 #ifndef PIXMAN_FB_ACCESSORS
851 static argb_t
852 fetch_pixel_rgbf_float (bits_image_t *image,
853  int offset,
854  int line)
855 {
856  float *bits = (float *)image->bits + line * image->rowstride;
857  argb_t argb;
858 
859  argb.r = bits[offset * 3];
860  argb.g = bits[offset * 3 + 1];
861  argb.b = bits[offset * 3 + 2];
862  argb.a = 1.f;
863 
864  return argb;
865 }
866 
867 static argb_t
868 fetch_pixel_rgbaf_float (bits_image_t *image,
869  int offset,
870  int line)
871 {
872  float *bits = (float *)image->bits + line * image->rowstride;
873  argb_t argb;
874 
875  argb.r = bits[offset * 4];
876  argb.g = bits[offset * 4 + 1];
877  argb.b = bits[offset * 4 + 2];
878  argb.a = bits[offset * 4 + 3];
879 
880  return argb;
881 }
882 #endif
883 
884 static argb_t
886  int offset,
887  int line)
888 {
889  uint32_t *bits = image->bits + line * image->rowstride;
890  uint32_t p = READ (image, bits + offset);
891  uint64_t r = (p >> 20) & 0x3ff;
892  uint64_t g = (p >> 10) & 0x3ff;
893  uint64_t b = p & 0x3ff;
894  argb_t argb;
895 
896  argb.a = 1.0;
897  argb.r = pixman_unorm_to_float (r, 10);
898  argb.g = pixman_unorm_to_float (g, 10);
899  argb.b = pixman_unorm_to_float (b, 10);
900 
901  return argb;
902 }
903 
904 static argb_t
906  int offset,
907  int line)
908 {
909  uint32_t *bits = image->bits + line * image->rowstride;
910  uint32_t p = READ (image, bits + offset);
911  uint64_t a = p >> 30;
912  uint64_t r = (p >> 20) & 0x3ff;
913  uint64_t g = (p >> 10) & 0x3ff;
914  uint64_t b = p & 0x3ff;
915  argb_t argb;
916 
917  argb.a = pixman_unorm_to_float (a, 2);
918  argb.r = pixman_unorm_to_float (r, 10);
919  argb.g = pixman_unorm_to_float (g, 10);
920  argb.b = pixman_unorm_to_float (b, 10);
921 
922  return argb;
923 }
924 
925 static argb_t
927  int offset,
928  int line)
929 {
930  uint32_t *bits = image->bits + line * image->rowstride;
931  uint32_t p = READ (image, bits + offset);
932  uint64_t a = p >> 30;
933  uint64_t b = (p >> 20) & 0x3ff;
934  uint64_t g = (p >> 10) & 0x3ff;
935  uint64_t r = p & 0x3ff;
936  argb_t argb;
937 
938  argb.a = pixman_unorm_to_float (a, 2);
939  argb.r = pixman_unorm_to_float (r, 10);
940  argb.g = pixman_unorm_to_float (g, 10);
941  argb.b = pixman_unorm_to_float (b, 10);
942 
943  return argb;
944 }
945 
946 static argb_t
948  int offset,
949  int line)
950 {
951  uint32_t *bits = image->bits + line * image->rowstride;
952  uint32_t p = READ (image, bits + offset);
953  uint64_t b = (p >> 20) & 0x3ff;
954  uint64_t g = (p >> 10) & 0x3ff;
955  uint64_t r = p & 0x3ff;
956  argb_t argb;
957 
958  argb.a = 1.0;
959  argb.r = pixman_unorm_to_float (r, 10);
960  argb.g = pixman_unorm_to_float (g, 10);
961  argb.b = pixman_unorm_to_float (b, 10);
962 
963  return argb;
964 }
965 
966 static argb_t
968  int offset,
969  int line)
970 {
971  uint32_t *bits = image->bits + line * image->rowstride;
972  uint32_t p = READ (image, bits + offset);
973  argb_t argb;
974 
975  argb.a = pixman_unorm_to_float ((p >> 24) & 0xff, 8);
976 
977  argb.r = to_linear [(p >> 16) & 0xff];
978  argb.g = to_linear [(p >> 8) & 0xff];
979  argb.b = to_linear [(p >> 0) & 0xff];
980 
981  return argb;
982 }
983 
984 static uint32_t
986  int offset,
987  int line)
988 {
989  const uint32_t *bits = image->bits + image->rowstride * line;
990 
991  int16_t y, u, v;
992  int32_t r, g, b;
993 
994  y = ((uint8_t *) bits)[offset << 1] - 16;
995  u = ((uint8_t *) bits)[((offset << 1) & - 4) + 1] - 128;
996  v = ((uint8_t *) bits)[((offset << 1) & - 4) + 3] - 128;
997 
998  /* R = 1.164(Y - 16) + 1.596(V - 128) */
999  r = 0x012b27 * y + 0x019a2e * v;
1000 
1001  /* G = 1.164(Y - 16) - 0.813(V - 128) - 0.391(U - 128) */
1002  g = 0x012b27 * y - 0x00d0f2 * v - 0x00647e * u;
1003 
1004  /* B = 1.164(Y - 16) + 2.018(U - 128) */
1005  b = 0x012b27 * y + 0x0206a2 * u;
1006 
1007  return 0xff000000 |
1008  (r >= 0 ? r < 0x1000000 ? r & 0xff0000 : 0xff0000 : 0) |
1009  (g >= 0 ? g < 0x1000000 ? (g >> 8) & 0x00ff00 : 0x00ff00 : 0) |
1010  (b >= 0 ? b < 0x1000000 ? (b >> 16) & 0x0000ff : 0x0000ff : 0);
1011 }
1012 
1013 static uint32_t
1015  int offset,
1016  int line)
1017 {
1018  YV12_SETUP (image);
1019  int16_t y = YV12_Y (line)[offset] - 16;
1020  int16_t u = YV12_U (line)[offset >> 1] - 128;
1021  int16_t v = YV12_V (line)[offset >> 1] - 128;
1022  int32_t r, g, b;
1023 
1024  /* R = 1.164(Y - 16) + 1.596(V - 128) */
1025  r = 0x012b27 * y + 0x019a2e * v;
1026 
1027  /* G = 1.164(Y - 16) - 0.813(V - 128) - 0.391(U - 128) */
1028  g = 0x012b27 * y - 0x00d0f2 * v - 0x00647e * u;
1029 
1030  /* B = 1.164(Y - 16) + 2.018(U - 128) */
1031  b = 0x012b27 * y + 0x0206a2 * u;
1032 
1033  return 0xff000000 |
1034  (r >= 0 ? r < 0x1000000 ? r & 0xff0000 : 0xff0000 : 0) |
1035  (g >= 0 ? g < 0x1000000 ? (g >> 8) & 0x00ff00 : 0x00ff00 : 0) |
1036  (b >= 0 ? b < 0x1000000 ? (b >> 16) & 0x0000ff : 0x0000ff : 0);
1037 }
1038 
1039 /*********************************** Store ************************************/
1040 
1041 #ifndef PIXMAN_FB_ACCESSORS
1042 static void
1043 store_scanline_rgbaf_float (bits_image_t * image,
1044  int x,
1045  int y,
1046  int width,
1047  const uint32_t *v)
1048 {
1049  float *bits = (float *)image->bits + image->rowstride * y + 4 * x;
1050  const argb_t *values = (argb_t *)v;
1051 
1052  for (; width; width--, values++)
1053  {
1054  *bits++ = values->r;
1055  *bits++ = values->g;
1056  *bits++ = values->b;
1057  *bits++ = values->a;
1058  }
1059 }
1060 
1061 static void
1062 store_scanline_rgbf_float (bits_image_t * image,
1063  int x,
1064  int y,
1065  int width,
1066  const uint32_t *v)
1067 {
1068  float *bits = (float *)image->bits + image->rowstride * y + 3 * x;
1069  const argb_t *values = (argb_t *)v;
1070 
1071  for (; width; width--, values++)
1072  {
1073  *bits++ = values->r;
1074  *bits++ = values->g;
1075  *bits++ = values->b;
1076  }
1077 }
1078 #endif
1079 
1080 static void
1082  int x,
1083  int y,
1084  int width,
1085  const uint32_t *v)
1086 {
1087  uint32_t *bits = image->bits + image->rowstride * y;
1088  uint32_t *pixel = bits + x;
1089  argb_t *values = (argb_t *)v;
1090  int i;
1091 
1092  for (i = 0; i < width; ++i)
1093  {
1094  uint32_t a, r, g, b;
1095 
1096  a = pixman_float_to_unorm (values[i].a, 2);
1097  r = pixman_float_to_unorm (values[i].r, 10);
1098  g = pixman_float_to_unorm (values[i].g, 10);
1099  b = pixman_float_to_unorm (values[i].b, 10);
1100 
1101  WRITE (image, pixel++,
1102  (a << 30) | (r << 20) | (g << 10) | b);
1103  }
1104 }
1105 
1106 static void
1108  int x,
1109  int y,
1110  int width,
1111  const uint32_t *v)
1112 {
1113  uint32_t *bits = image->bits + image->rowstride * y;
1114  uint32_t *pixel = bits + x;
1115  argb_t *values = (argb_t *)v;
1116  int i;
1117 
1118  for (i = 0; i < width; ++i)
1119  {
1120  uint32_t r, g, b;
1121 
1122  r = pixman_float_to_unorm (values[i].r, 10);
1123  g = pixman_float_to_unorm (values[i].g, 10);
1124  b = pixman_float_to_unorm (values[i].b, 10);
1125 
1126  WRITE (image, pixel++,
1127  (r << 20) | (g << 10) | b);
1128  }
1129 }
1130 
1131 static void
1133  int x,
1134  int y,
1135  int width,
1136  const uint32_t *v)
1137 {
1138  uint32_t *bits = image->bits + image->rowstride * y;
1139  uint32_t *pixel = bits + x;
1140  argb_t *values = (argb_t *)v;
1141  int i;
1142 
1143  for (i = 0; i < width; ++i)
1144  {
1145  uint32_t a, r, g, b;
1146 
1147  a = pixman_float_to_unorm (values[i].a, 2);
1148  r = pixman_float_to_unorm (values[i].r, 10);
1149  g = pixman_float_to_unorm (values[i].g, 10);
1150  b = pixman_float_to_unorm (values[i].b, 10);
1151 
1152  WRITE (image, pixel++,
1153  (a << 30) | (b << 20) | (g << 10) | r);
1154  }
1155 }
1156 
1157 static void
1159  int x,
1160  int y,
1161  int width,
1162  const uint32_t *v)
1163 {
1164  uint32_t *bits = image->bits + image->rowstride * y;
1165  uint32_t *pixel = bits + x;
1166  argb_t *values = (argb_t *)v;
1167  int i;
1168 
1169  for (i = 0; i < width; ++i)
1170  {
1171  uint32_t r, g, b;
1172 
1173  r = pixman_float_to_unorm (values[i].r, 10);
1174  g = pixman_float_to_unorm (values[i].g, 10);
1175  b = pixman_float_to_unorm (values[i].b, 10);
1176 
1177  WRITE (image, pixel++,
1178  (b << 20) | (g << 10) | r);
1179  }
1180 }
1181 
1182 static void
1184  int x,
1185  int y,
1186  int width,
1187  const uint32_t *v)
1188 {
1189  uint32_t *bits = image->bits + image->rowstride * y;
1190  uint32_t *pixel = bits + x;
1191  argb_t *values = (argb_t *)v;
1192  int i;
1193 
1194  for (i = 0; i < width; ++i)
1195  {
1196  uint32_t a, r, g, b;
1197 
1198  a = pixman_float_to_unorm (values[i].a, 8);
1199  r = to_srgb (values[i].r);
1200  g = to_srgb (values[i].g);
1201  b = to_srgb (values[i].b);
1202 
1203  WRITE (image, pixel++,
1204  (a << 24) | (r << 16) | (g << 8) | b);
1205  }
1206 }
1207 
1208 /*
1209  * Contracts a floating point image to 32bpp and then stores it using a
1210  * regular 32-bit store proc. Despite the type, this function expects an
1211  * argb_t buffer.
1212  */
1213 static void
1215  int x,
1216  int y,
1217  int width,
1218  const uint32_t *values)
1219 {
1220  uint32_t *argb8_pixels;
1221 
1222  assert (image->common.type == BITS);
1223 
1224  argb8_pixels = pixman_malloc_ab (width, sizeof(uint32_t));
1225  if (!argb8_pixels)
1226  return;
1227 
1228  /* Contract the scanline. We could do this in place if values weren't
1229  * const.
1230  */
1231  pixman_contract_from_float (argb8_pixels, (argb_t *)values, width);
1232 
1233  image->store_scanline_32 (image, x, y, width, argb8_pixels);
1234 
1235  free (argb8_pixels);
1236 }
1237 
1238 static void
1240  int x,
1241  int y,
1242  int width,
1243  uint32_t * buffer,
1244  const uint32_t *mask)
1245 {
1246  image->fetch_scanline_32 (image, x, y, width, buffer, NULL);
1247 
1249 }
1250 
1251 /* The 32_sRGB paths should be deleted after narrow processing
1252  * is no longer invoked for formats that are considered wide.
1253  * (Also see fetch_pixel_generic_lossy_32) */
1254 static void
1256  int x,
1257  int y,
1258  int width,
1259  uint32_t *buffer,
1260  const uint32_t *mask)
1261 {
1262  const uint32_t *bits = image->bits + y * image->rowstride;
1263  const uint32_t *pixel = (uint32_t *)bits + x;
1264  const uint32_t *end = pixel + width;
1265  uint32_t tmp;
1266 
1267  while (pixel < end)
1268  {
1269  uint32_t a, r, g, b;
1270 
1271  tmp = READ (image, pixel++);
1272 
1273  a = (tmp >> 24) & 0xff;
1274  r = (tmp >> 16) & 0xff;
1275  g = (tmp >> 8) & 0xff;
1276  b = (tmp >> 0) & 0xff;
1277 
1278  r = to_linear[r] * 255.0f + 0.5f;
1279  g = to_linear[g] * 255.0f + 0.5f;
1280  b = to_linear[b] * 255.0f + 0.5f;
1281 
1282  *buffer++ = (a << 24) | (r << 16) | (g << 8) | (b << 0);
1283  }
1284 }
1285 
1286 static uint32_t
1288  int offset,
1289  int line)
1290 {
1291  uint32_t *bits = image->bits + line * image->rowstride;
1292  uint32_t tmp = READ (image, bits + offset);
1293  uint32_t a, r, g, b;
1294 
1295  a = (tmp >> 24) & 0xff;
1296  r = (tmp >> 16) & 0xff;
1297  g = (tmp >> 8) & 0xff;
1298  b = (tmp >> 0) & 0xff;
1299 
1300  r = to_linear[r] * 255.0f + 0.5f;
1301  g = to_linear[g] * 255.0f + 0.5f;
1302  b = to_linear[b] * 255.0f + 0.5f;
1303 
1304  return (a << 24) | (r << 16) | (g << 8) | (b << 0);
1305 }
1306 
1307 static void
1309  int x,
1310  int y,
1311  int width,
1312  const uint32_t *v)
1313 {
1314  uint32_t *bits = image->bits + image->rowstride * y;
1315  uint64_t *values = (uint64_t *)v;
1316  uint32_t *pixel = bits + x;
1317  uint64_t tmp;
1318  int i;
1319 
1320  for (i = 0; i < width; ++i)
1321  {
1322  uint32_t a, r, g, b;
1323 
1324  tmp = values[i];
1325 
1326  a = (tmp >> 24) & 0xff;
1327  r = (tmp >> 16) & 0xff;
1328  g = (tmp >> 8) & 0xff;
1329  b = (tmp >> 0) & 0xff;
1330 
1331  r = to_srgb (r * (1/255.0f));
1332  g = to_srgb (g * (1/255.0f));
1333  b = to_srgb (b * (1/255.0f));
1334 
1335  WRITE (image, pixel++, a | (r << 16) | (g << 8) | (b << 0));
1336  }
1337 }
1338 
1339 static argb_t
1341  int offset,
1342  int line)
1343 {
1344  uint32_t pixel32 = image->fetch_pixel_32 (image, offset, line);
1345  argb_t f;
1346 
1347  pixman_expand_to_float (&f, &pixel32, image->format, 1);
1348 
1349  return f;
1350 }
1351 
1352 /*
1353  * XXX: The transformed fetch path only works at 32-bpp so far. When all
1354  * paths have wide versions, this can be removed.
1355  *
1356  * WARNING: This function loses precision!
1357  */
1358 static uint32_t
1360  int offset,
1361  int line)
1362 {
1363  argb_t pixel64 = image->fetch_pixel_float (image, offset, line);
1364  uint32_t result;
1365 
1366  pixman_contract_from_float (&result, &pixel64, 1);
1367 
1368  return result;
1369 }
1370 
1371 typedef struct
1372 {
1380 } format_info_t;
1381 
1382 #define FORMAT_INFO(format) \
1383  { \
1384  PIXMAN_ ## format, \
1385  fetch_scanline_ ## format, \
1386  fetch_scanline_generic_float, \
1387  fetch_pixel_ ## format, \
1388  fetch_pixel_generic_float, \
1389  store_scanline_ ## format, \
1390  store_scanline_generic_float \
1391  }
1392 
1393 static const format_info_t accessors[] =
1394 {
1395 /* 32 bpp formats */
1396  FORMAT_INFO (a8r8g8b8),
1397  FORMAT_INFO (x8r8g8b8),
1398  FORMAT_INFO (a8b8g8r8),
1399  FORMAT_INFO (x8b8g8r8),
1400  FORMAT_INFO (b8g8r8a8),
1401  FORMAT_INFO (b8g8r8x8),
1402  FORMAT_INFO (r8g8b8a8),
1403  FORMAT_INFO (r8g8b8x8),
1404  FORMAT_INFO (x14r6g6b6),
1405 
1406 /* sRGB formats */
1411  },
1412 
1413 /* 24bpp formats */
1414  FORMAT_INFO (r8g8b8),
1415  FORMAT_INFO (b8g8r8),
1416 
1417 /* 16bpp formats */
1418  FORMAT_INFO (r5g6b5),
1419  FORMAT_INFO (b5g6r5),
1420 
1421  FORMAT_INFO (a1r5g5b5),
1422  FORMAT_INFO (x1r5g5b5),
1423  FORMAT_INFO (a1b5g5r5),
1424  FORMAT_INFO (x1b5g5r5),
1425  FORMAT_INFO (a4r4g4b4),
1426  FORMAT_INFO (x4r4g4b4),
1427  FORMAT_INFO (a4b4g4r4),
1428  FORMAT_INFO (x4b4g4r4),
1429 
1430 /* 8bpp formats */
1431  FORMAT_INFO (a8),
1432  FORMAT_INFO (r3g3b2),
1433  FORMAT_INFO (b2g3r3),
1434  FORMAT_INFO (a2r2g2b2),
1435  FORMAT_INFO (a2b2g2r2),
1436 
1437  FORMAT_INFO (c8),
1438 
1439  FORMAT_INFO (g8),
1440 
1441 #define fetch_scanline_x4c4 fetch_scanline_c8
1442 #define fetch_pixel_x4c4 fetch_pixel_c8
1443 #define store_scanline_x4c4 store_scanline_c8
1444  FORMAT_INFO (x4c4),
1445 
1446 #define fetch_scanline_x4g4 fetch_scanline_g8
1447 #define fetch_pixel_x4g4 fetch_pixel_g8
1448 #define store_scanline_x4g4 store_scanline_g8
1449  FORMAT_INFO (x4g4),
1450 
1451  FORMAT_INFO (x4a4),
1452 
1453 /* 4bpp formats */
1454  FORMAT_INFO (a4),
1455  FORMAT_INFO (r1g2b1),
1456  FORMAT_INFO (b1g2r1),
1457  FORMAT_INFO (a1r1g1b1),
1458  FORMAT_INFO (a1b1g1r1),
1459 
1460  FORMAT_INFO (c4),
1461 
1462  FORMAT_INFO (g4),
1463 
1464 /* 1bpp formats */
1465  FORMAT_INFO (a1),
1466  FORMAT_INFO (g1),
1467 
1468 /* Wide formats */
1469 #ifndef PIXMAN_FB_ACCESSORS
1471  NULL, fetch_scanline_rgbaf_float,
1472  fetch_pixel_generic_lossy_32, fetch_pixel_rgbaf_float,
1473  NULL, store_scanline_rgbaf_float },
1474 
1475  { PIXMAN_rgb_float,
1476  NULL, fetch_scanline_rgbf_float,
1477  fetch_pixel_generic_lossy_32, fetch_pixel_rgbf_float,
1478  NULL, store_scanline_rgbf_float },
1479 #endif
1480 
1485 
1490 
1495 
1500 
1501 /* YUV formats */
1502  { PIXMAN_yuy2,
1505  NULL, NULL },
1506 
1507  { PIXMAN_yv12,
1510  NULL, NULL },
1511 
1512  { PIXMAN_null },
1513 };
1514 
1515 static void
1517 {
1518  const format_info_t *info = accessors;
1519 
1520  while (info->format != PIXMAN_null)
1521  {
1522  if (info->format == image->format)
1523  {
1524  image->fetch_scanline_32 = info->fetch_scanline_32;
1525  image->fetch_scanline_float = info->fetch_scanline_float;
1526  image->fetch_pixel_32 = info->fetch_pixel_32;
1527  image->fetch_pixel_float = info->fetch_pixel_float;
1528  image->store_scanline_32 = info->store_scanline_32;
1529  image->store_scanline_float = info->store_scanline_float;
1530 
1531  return;
1532  }
1533 
1534  info++;
1535  }
1536 }
1537 
1538 #ifndef PIXMAN_FB_ACCESSORS
1539 void
1541 
1542 void
1544 {
1545  if (image->read_func || image->write_func)
1547  else
1549 }
1550 
1551 #else
1552 
1553 void
1555 {
1557 }
1558 
1559 #endif
void WRITE(T &t, UInt32 v)
Definition: Compiler.cpp:292
#define width(a)
Definition: aptex-macros.h:198
QUAD g8[4]
Definition: axohelp.c:815
#define b
Definition: jpegint.h:372
#define free(a)
Definition: decNumber.cpp:310
int v
Definition: dviconv.c:10
#define info
Definition: dviinfo.c:42
mpz_t * f
Definition: gen-fib.c:34
#define a1
#define a4
#define a(n)
Definition: gpos-common.c:148
assert(pcxLoadImage24((char *)((void *) 0), fp, pinfo, hdr))
#define NULL
Definition: ftobjs.h:61
small capitals from c petite p scientific f u
Definition: afcover.h:88
small capitals from c petite p
Definition: afcover.h:72
small capitals from c petite p scientific i
Definition: afcover.h:80
kerning y
Definition: ttdriver.c:212
signed short int16_t
Definition: stdint.h:76
unsigned short uint16_t
Definition: stdint.h:79
unsigned int uint32_t
Definition: stdint.h:80
signed int int32_t
Definition: stdint.h:77
unsigned char uint8_t
Definition: stdint.h:78
unsigned __int64 uint64_t
Definition: stdint.h:90
#define READ
Definition: config.h:50
#define dest
int low
Definition: combiners.h:904
int high
Definition: combiners.h:904
float x
Definition: cordic.py:15
unsigned int argb
static int format
Definition: pbmclean.c:15
static const uint32_t to_linear_u[256]
static const format_info_t accessors[]
#define FETCH_1(img, l, o)
Definition: pixman-access.c:55
static void store_scanline_a8r8g8b8_32_sRGB(bits_image_t *image, int x, int y, int width, const uint32_t *v)
static uint32_t fetch_pixel_a8r8g8b8_32_sRGB(bits_image_t *image, int offset, int line)
#define FORMAT_INFO(format)
static argb_t fetch_pixel_x2r10g10b10_float(bits_image_t *image, int offset, int line)
#define YV12_U(line)
static uint32_t convert_pixel(pixman_format_code_t from, pixman_format_code_t to, uint32_t pixel)
static uint32_t convert_channel(uint32_t pixel, uint32_t def_value, int n_from_bits, int from_shift, int n_to_bits, int to_shift)
static void setup_accessors(bits_image_t *image)
static uint32_t fetch_pixel_yuy2(bits_image_t *image, int offset, int line)
static void fetch_scanline_a8r8g8b8_32_sRGB(bits_image_t *image, int x, int y, int width, uint32_t *buffer, const uint32_t *mask)
static uint32_t convert_pixel_to_a8r8g8b8(bits_image_t *image, pixman_format_code_t format, uint32_t pixel)
static void store_scanline_a2b10g10r10_float(bits_image_t *image, int x, int y, int width, const uint32_t *v)
static void store_scanline_generic_float(bits_image_t *image, int x, int y, int width, const uint32_t *values)
static argb_t fetch_pixel_a8r8g8b8_sRGB_float(bits_image_t *image, int offset, int line)
static uint8_t to_srgb(float f)
#define STORE_24(img, l, o, v)
static uint32_t fetch_pixel_yv12(bits_image_t *image, int offset, int line)
static void get_shifts(pixman_format_code_t format, int *a, int *r, int *g, int *b)
static void store_scanline_a8r8g8b8_sRGB_float(bits_image_t *image, int x, int y, int width, const uint32_t *v)
static void convert_and_store_pixel(bits_image_t *image, uint8_t *dest, int offset, pixman_format_code_t format, uint32_t pixel)
#define YV12_Y(line)
static const float *const to_linear
static argb_t fetch_pixel_x2b10g10r10_float(bits_image_t *image, int offset, int line)
static void fetch_scanline_generic_float(bits_image_t *image, int x, int y, int width, uint32_t *buffer, const uint32_t *mask)
static argb_t fetch_pixel_generic_float(bits_image_t *image, int offset, int line)
static void fetch_scanline_yuy2(bits_image_t *image, int x, int line, int width, uint32_t *buffer, const uint32_t *mask)
static argb_t fetch_pixel_a2b10g10r10_float(bits_image_t *image, int offset, int line)
static void store_scanline_a2r10g10b10_float(bits_image_t *image, int x, int y, int width, const uint32_t *v)
static void fetch_scanline_x2b10g10r10_float(bits_image_t *image, int x, int y, int width, uint32_t *b, const uint32_t *mask)
#define YV12_V(line)
static uint32_t convert_pixel_from_a8r8g8b8(pixman_image_t *image, pixman_format_code_t format, uint32_t pixel)
#define MAKE_ACCESSORS(format)
static void fetch_scanline_yv12(bits_image_t *image, int x, int line, int width, uint32_t *buffer, const uint32_t *mask)
#define CONVERT_RGB24_TO_Y15(s)
Definition: pixman-access.c:39
static uint32_t fetch_and_convert_pixel(bits_image_t *image, const uint8_t *bits, int offset, pixman_format_code_t format)
#define YV12_SETUP(image)
static void fetch_scanline_a8r8g8b8_sRGB_float(bits_image_t *image, int x, int y, int width, uint32_t *b, const uint32_t *mask)
void _pixman_bits_image_setup_accessors_accessors(bits_image_t *image)
static void store_scanline_x2b10g10r10_float(bits_image_t *image, int x, int y, int width, const uint32_t *v)
static void fetch_scanline_a2r10g10b10_float(bits_image_t *image, int x, int y, int width, uint32_t *b, const uint32_t *mask)
#define FETCH_24(img, l, o)
Definition: pixman-access.c:75
static uint32_t fetch_pixel_generic_lossy_32(bits_image_t *image, int offset, int line)
static argb_t fetch_pixel_a2r10g10b10_float(bits_image_t *image, int offset, int line)
static void fetch_scanline_x2r10g10b10_float(bits_image_t *image, int x, int y, int width, uint32_t *b, const uint32_t *mask)
#define STORE_4(img, l, o, v)
static void store_scanline_x2r10g10b10_float(bits_image_t *image, int x, int y, int width, const uint32_t *v)
#define FETCH_4(img, l, o)
Definition: pixman-access.c:65
#define STORE_1(img, l, o, v)
Definition: pixman-access.c:97
static void fetch_scanline_a2b10g10r10_float(bits_image_t *image, int x, int y, int width, uint32_t *b, const uint32_t *mask)
#define force_inline
float pixman_unorm_to_float(uint16_t u, int n_bits)
Definition: pixman-utils.c:195
@ BITS
uint32_t(* fetch_pixel_32_t)(bits_image_t *image, int x, int y)
void(* store_scanline_t)(bits_image_t *image, int x, int y, int width, const uint32_t *values)
void pixman_contract_from_float(uint32_t *dst, const argb_t *src, int width)
Definition: pixman-utils.c:201
void * pixman_malloc_ab(unsigned int n, unsigned int b)
Definition: pixman-utils.c:61
argb_t(* fetch_pixel_float_t)(bits_image_t *image, int x, int y)
void pixman_expand_to_float(argb_t *dst, const uint32_t *src, pixman_format_code_t format, int width)
Definition: pixman-utils.c:118
void(* fetch_scanline_t)(bits_image_t *image, int x, int y, int width, uint32_t *buffer, const uint32_t *mask)
#define PIXMAN_null
void _pixman_bits_image_setup_accessors(bits_image_t *image)
uint16_t pixman_float_to_unorm(float f, int n_bits)
Definition: pixman-utils.c:189
static uint32_t unorm_to_unorm(uint32_t val, int from_bits, int to_bits)
#define PIXMAN_TYPE_RGBA
Definition: pixman.h:860
#define PIXMAN_TYPE_GRAY
Definition: pixman.h:856
#define PIXMAN_TYPE_ABGR
Definition: pixman.h:854
#define PIXMAN_FORMAT_BPP(f)
Definition: pixman.h:837
#define PIXMAN_FORMAT_G(f)
Definition: pixman.h:842
#define PIXMAN_FORMAT_A(f)
Definition: pixman.h:840
#define PIXMAN_FORMAT_TYPE(f)
Definition: pixman.h:839
#define PIXMAN_TYPE_A
Definition: pixman.h:852
#define PIXMAN_TYPE_COLOR
Definition: pixman.h:855
#define PIXMAN_TYPE_ARGB_SRGB
Definition: pixman.h:861
#define PIXMAN_FORMAT_B(f)
Definition: pixman.h:843
#define PIXMAN_TYPE_BGRA
Definition: pixman.h:859
pixman_format_code_t
Definition: pixman.h:871
@ PIXMAN_a8r8g8b8_sRGB
Definition: pixman.h:893
@ PIXMAN_a8r8g8b8
Definition: pixman.h:878
@ PIXMAN_x2b10g10r10
Definition: pixman.h:889
@ PIXMAN_yv12
Definition: pixman.h:944
@ PIXMAN_x2r10g10b10
Definition: pixman.h:887
@ PIXMAN_a2b10g10r10
Definition: pixman.h:890
@ PIXMAN_x1r5g5b5
Definition: pixman.h:904
@ PIXMAN_a2r10g10b10
Definition: pixman.h:888
@ PIXMAN_rgba_float
Definition: pixman.h:873
@ PIXMAN_rgb_float
Definition: pixman.h:875
@ PIXMAN_yuy2
Definition: pixman.h:943
#define PIXMAN_FORMAT_R(f)
Definition: pixman.h:841
#define PIXMAN_TYPE_ARGB
Definition: pixman.h:853
real to[600]
Definition: pmxab.c:87
unsigned long pixel
Definition: png22pnm.c:123
int g
Definition: ppmqvga.c:68
int r
Definition: ppmqvga.c:68
static int offset
Definition: ppmtogif.c:642
char line[1024]
Definition: process_score.c:29
#define mask(n)
Definition: lbitlib.c:93
Definition: namelist.c:170
Definition: utils.c:300
char * b
Definition: utils.c:303
fetch_pixel_float_t fetch_pixel_float
pixman_format_code_t format
fetch_pixel_32_t fetch_pixel_32
fetch_scanline_t fetch_scanline_32
store_scanline_t store_scanline_32
fetch_scanline_t fetch_scanline_float
store_scanline_t store_scanline_float
Definition: sd.h:76
Definition: bdf.c:133
Definition: ppm.h:33
#define buffer
Definition: xmlparse.c:611
#define end(cp)
Definition: zic.c:71