1/**************************************************************************
2 *
3 * Copyright 2010 VMware, Inc.
4 * All Rights Reserved.
5 *
6 * Permission is hereby granted, free of charge, to any person obtaining a
7 * copy of this software and associated documentation files (the
8 * "Software"), to deal in the Software without restriction, including
9 * without limitation the rights to use, copy, modify, merge, publish,
10 * distribute, sub license, and/or sell copies of the Software, and to
11 * permit persons to whom the Software is furnished to do so, subject to
12 * the following conditions:
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
17 * THE COPYRIGHT HOLDERS, AUTHORS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM,
18 * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
19 * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
20 * USE OR OTHER DEALINGS IN THE SOFTWARE.
21 *
22 * The above copyright notice and this permission notice (including the
23 * next paragraph) shall be included in all copies or substantial portions
24 * of the Software.
25 *
26 **************************************************************************/
27
28
29/**
30 * @file
31 * YUV and RGB subsampled formats conversion.
32 *
33 * @author Jose Fonseca <jfonseca@vmware.com>
34 */
35
36
37#include "util/u_format_yuv.h"
38
39
40void
41util_format_r8g8_b8g8_unorm_unpack_rgba_float(float *dst_row, unsigned dst_stride,
42                                         const uint8_t *src_row, unsigned src_stride,
43                                         unsigned width, unsigned height)
44{
45   unsigned x, y;
46
47   for (y = 0; y < height; y += 1) {
48      float *dst = dst_row;
49      const uint32_t *src = (const uint32_t *)src_row;
50      uint32_t value;
51      float r, g0, g1, b;
52
53      for (x = 0; x + 1 < width; x += 2) {
54         value = *src++;
55
56#ifdef PIPE_ARCH_BIG_ENDIAN
57         value = util_bswap32(value);
58#endif
59
60         r  = ubyte_to_float((value >>  0) & 0xff);
61         g0 = ubyte_to_float((value >>  8) & 0xff);
62         b  = ubyte_to_float((value >> 16) & 0xff);
63         g1 = ubyte_to_float((value >> 24) & 0xff);
64
65         dst[0] = r;    /* r */
66         dst[1] = g0;   /* g */
67         dst[2] = b;    /* b */
68         dst[3] = 1.0f; /* a */
69         dst += 4;
70
71         dst[0] = r;    /* r */
72         dst[1] = g1;   /* g */
73         dst[2] = b;    /* b */
74         dst[3] = 1.0f; /* a */
75         dst += 4;
76      }
77
78      if (x < width) {
79         value = *src;
80
81#ifdef PIPE_ARCH_BIG_ENDIAN
82         value = util_bswap32(value);
83#endif
84
85         r  = ubyte_to_float((value >>  0) & 0xff);
86         g0 = ubyte_to_float((value >>  8) & 0xff);
87         b  = ubyte_to_float((value >> 16) & 0xff);
88         g1 = ubyte_to_float((value >> 24) & 0xff);
89
90         dst[0] = r;    /* r */
91         dst[1] = g0;   /* g */
92         dst[2] = b;    /* b */
93         dst[3] = 1.0f; /* a */
94      }
95
96      src_row += src_stride/sizeof(*src_row);
97      dst_row += dst_stride/sizeof(*dst_row);
98   }
99}
100
101
102void
103util_format_r8g8_b8g8_unorm_unpack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
104                                          const uint8_t *src_row, unsigned src_stride,
105                                          unsigned width, unsigned height)
106{
107   unsigned x, y;
108
109   for (y = 0; y < height; y += 1) {
110      uint8_t *dst = dst_row;
111      const uint32_t *src = (const uint32_t *)src_row;
112      uint32_t value;
113      uint8_t r, g0, g1, b;
114
115      for (x = 0; x + 1 < width; x += 2) {
116         value = *src++;
117
118#ifdef PIPE_ARCH_BIG_ENDIAN
119         value = util_bswap32(value);
120#endif
121
122         r  = (value >>  0) & 0xff;
123         g0 = (value >>  8) & 0xff;
124         b  = (value >> 16) & 0xff;
125         g1 = (value >> 24) & 0xff;
126
127         dst[0] = r;    /* r */
128         dst[1] = g0;   /* g */
129         dst[2] = b;    /* b */
130         dst[3] = 0xff; /* a */
131         dst += 4;
132
133         dst[0] = r;    /* r */
134         dst[1] = g1;   /* g */
135         dst[2] = b;    /* b */
136         dst[3] = 0xff; /* a */
137         dst += 4;
138      }
139
140      if (x < width) {
141         value = *src;
142
143#ifdef PIPE_ARCH_BIG_ENDIAN
144         value = util_bswap32(value);
145#endif
146
147         r  = (value >>  0) & 0xff;
148         g0 = (value >>  8) & 0xff;
149         b  = (value >> 16) & 0xff;
150         g1 = (value >> 24) & 0xff;
151
152         dst[0] = r;    /* r */
153         dst[1] = g0;   /* g */
154         dst[2] = b;    /* b */
155         dst[3] = 0xff; /* a */
156      }
157
158      src_row += src_stride/sizeof(*src_row);
159      dst_row += dst_stride/sizeof(*dst_row);
160   }
161}
162
163
164void
165util_format_r8g8_b8g8_unorm_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride,
166                                       const float *src_row, unsigned src_stride,
167                                       unsigned width, unsigned height)
168{
169   unsigned x, y;
170
171   for (y = 0; y < height; y += 1) {
172      const float *src = src_row;
173      uint32_t *dst = (uint32_t *)dst_row;
174      float r, g0, g1, b;
175      uint32_t value;
176
177      for (x = 0; x + 1 < width; x += 2) {
178         r  = 0.5f*(src[0] + src[4]);
179         g0 = src[1];
180         g1 = src[5];
181         b  = 0.5f*(src[2] + src[6]);
182
183         value  = float_to_ubyte(r);
184         value |= float_to_ubyte(g0) <<  8;
185         value |= float_to_ubyte(b)  << 16;
186         value |= float_to_ubyte(g1) << 24;
187
188#ifdef PIPE_ARCH_BIG_ENDIAN
189         value = util_bswap32(value);
190#endif
191
192         *dst++ = value;
193
194         src += 8;
195      }
196
197      if (x < width) {
198         r  = src[0];
199         g0 = src[1];
200         g1 = 0;
201         b  = src[2];
202
203         value  = float_to_ubyte(r);
204         value |= float_to_ubyte(g0) <<  8;
205         value |= float_to_ubyte(b)  << 16;
206         value |= float_to_ubyte(g1) << 24;
207
208#ifdef PIPE_ARCH_BIG_ENDIAN
209         value = util_bswap32(value);
210#endif
211
212         *dst = value;
213      }
214
215      dst_row += dst_stride/sizeof(*dst_row);
216      src_row += src_stride/sizeof(*src_row);
217   }
218}
219
220
221void
222util_format_r8g8_b8g8_unorm_pack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
223                                        const uint8_t *src_row, unsigned src_stride,
224                                        unsigned width, unsigned height)
225{
226   unsigned x, y;
227
228   for (y = 0; y < height; y += 1) {
229      const uint8_t *src = src_row;
230      uint32_t *dst = (uint32_t *)dst_row;
231      uint32_t r, g0, g1, b;
232      uint32_t value;
233
234      for (x = 0; x + 1 < width; x += 2) {
235         r  = (src[0] + src[4] + 1) >> 1;
236         g0 = src[1];
237         g1 = src[5];
238         b  = (src[2] + src[6] + 1) >> 1;
239
240         value  = r;
241         value |= g0 <<  8;
242         value |= b  << 16;
243         value |= g1 << 24;
244
245#ifdef PIPE_ARCH_BIG_ENDIAN
246         value = util_bswap32(value);
247#endif
248
249         *dst++ = value;
250
251         src += 8;
252      }
253
254      if (x < width) {
255         r  = src[0];
256         g0 = src[1];
257         g1 = 0;
258         b  = src[2];
259
260         value  = r;
261         value |= g0 <<  8;
262         value |= b  << 16;
263         value |= g1 << 24;
264
265#ifdef PIPE_ARCH_BIG_ENDIAN
266         value = util_bswap32(value);
267#endif
268
269         *dst = value;
270      }
271
272      dst_row += dst_stride/sizeof(*dst_row);
273      src_row += src_stride/sizeof(*src_row);
274   }
275}
276
277
278void
279util_format_r8g8_b8g8_unorm_fetch_rgba_float(float *dst, const uint8_t *src,
280                                        unsigned i, unsigned j)
281{
282   assert(i < 2);
283   assert(j < 1);
284
285   dst[0] = ubyte_to_float(src[0]);             /* r */
286   dst[1] = ubyte_to_float(src[1 + 2*i]);       /* g */
287   dst[2] = ubyte_to_float(src[2]);             /* b */
288   dst[3] = 1.0f;                               /* a */
289}
290
291
292void
293util_format_g8r8_g8b8_unorm_unpack_rgba_float(float *dst_row, unsigned dst_stride,
294                                         const uint8_t *src_row, unsigned src_stride,
295                                         unsigned width, unsigned height)
296{
297   unsigned x, y;
298
299   for (y = 0; y < height; y += 1) {
300      float *dst = dst_row;
301      const uint32_t *src = (const uint32_t *)src_row;
302      uint32_t value;
303      float r, g0, g1, b;
304
305      for (x = 0; x + 1 < width; x += 2) {
306         value = *src++;
307
308#ifdef PIPE_ARCH_BIG_ENDIAN
309         value = util_bswap32(value);
310#endif
311
312         g0 = ubyte_to_float((value >>  0) & 0xff);
313         r  = ubyte_to_float((value >>  8) & 0xff);
314         g1 = ubyte_to_float((value >> 16) & 0xff);
315         b  = ubyte_to_float((value >> 24) & 0xff);
316
317         dst[0] = r;    /* r */
318         dst[1] = g0;   /* g */
319         dst[2] = b;    /* b */
320         dst[3] = 1.0f; /* a */
321         dst += 4;
322
323         dst[0] = r;    /* r */
324         dst[1] = g1;   /* g */
325         dst[2] = b;    /* b */
326         dst[3] = 1.0f; /* a */
327         dst += 4;
328      }
329
330      if (x < width) {
331         value = *src;
332
333#ifdef PIPE_ARCH_BIG_ENDIAN
334         value = util_bswap32(value);
335#endif
336
337         g0 = ubyte_to_float((value >>  0) & 0xff);
338         r  = ubyte_to_float((value >>  8) & 0xff);
339         g1 = ubyte_to_float((value >> 16) & 0xff);
340         b  = ubyte_to_float((value >> 24) & 0xff);
341
342         dst[0] = r;    /* r */
343         dst[1] = g0;   /* g */
344         dst[2] = b;    /* b */
345         dst[3] = 1.0f; /* a */
346      }
347
348      src_row += src_stride/sizeof(*src_row);
349      dst_row += dst_stride/sizeof(*dst_row);
350   }
351}
352
353
354void
355util_format_g8r8_g8b8_unorm_unpack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
356                                          const uint8_t *src_row, unsigned src_stride,
357                                          unsigned width, unsigned height)
358{
359   unsigned x, y;
360
361   for (y = 0; y < height; y += 1) {
362      uint8_t *dst = dst_row;
363      const uint32_t *src = (const uint32_t *)src_row;
364      uint32_t value;
365      uint8_t r, g0, g1, b;
366
367      for (x = 0; x + 1 < width; x += 2) {
368         value = *src++;
369
370#ifdef PIPE_ARCH_BIG_ENDIAN
371         value = util_bswap32(value);
372#endif
373
374         g0 = (value >>  0) & 0xff;
375         r  = (value >>  8) & 0xff;
376         g1 = (value >> 16) & 0xff;
377         b  = (value >> 24) & 0xff;
378
379         dst[0] = r;    /* r */
380         dst[1] = g0;   /* g */
381         dst[2] = b;    /* b */
382         dst[3] = 0xff; /* a */
383         dst += 4;
384
385         dst[0] = r;    /* r */
386         dst[1] = g1;   /* g */
387         dst[2] = b;    /* b */
388         dst[3] = 0xff; /* a */
389         dst += 4;
390      }
391
392      if (x < width) {
393         value = *src;
394
395#ifdef PIPE_ARCH_BIG_ENDIAN
396         value = util_bswap32(value);
397#endif
398
399         g0 = (value >>  0) & 0xff;
400         r  = (value >>  8) & 0xff;
401         g1 = (value >> 16) & 0xff;
402         b  = (value >> 24) & 0xff;
403
404         dst[0] = r;    /* r */
405         dst[1] = g0;   /* g */
406         dst[2] = b;    /* b */
407         dst[3] = 0xff; /* a */
408      }
409
410      src_row += src_stride/sizeof(*src_row);
411      dst_row += dst_stride/sizeof(*dst_row);
412   }
413}
414
415
416void
417util_format_g8r8_g8b8_unorm_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride,
418                                       const float *src_row, unsigned src_stride,
419                                       unsigned width, unsigned height)
420{
421   unsigned x, y;
422
423   for (y = 0; y < height; y += 1) {
424      const float *src = src_row;
425      uint32_t *dst = (uint32_t *)dst_row;
426      float r, g0, g1, b;
427      uint32_t value;
428
429      for (x = 0; x + 1 < width; x += 2) {
430         r  = 0.5f*(src[0] + src[4]);
431         g0 = src[1];
432         g1 = src[5];
433         b  = 0.5f*(src[2] + src[6]);
434
435         value  = float_to_ubyte(g0);
436         value |= float_to_ubyte(r)  <<  8;
437         value |= float_to_ubyte(g1) << 16;
438         value |= float_to_ubyte(b)  << 24;
439
440#ifdef PIPE_ARCH_BIG_ENDIAN
441         value = util_bswap32(value);
442#endif
443
444         *dst++ = value;
445
446         src += 8;
447      }
448
449      if (x < width) {
450         r  = src[0];
451         g0 = src[1];
452         g1 = 0;
453         b  = src[2];
454
455         value  = float_to_ubyte(g0);
456         value |= float_to_ubyte(r)  <<  8;
457         value |= float_to_ubyte(g1) << 16;
458         value |= float_to_ubyte(b)  << 24;
459
460#ifdef PIPE_ARCH_BIG_ENDIAN
461         value = util_bswap32(value);
462#endif
463
464         *dst = value;
465      }
466
467      dst_row += dst_stride/sizeof(*dst_row);
468      src_row += src_stride/sizeof(*src_row);
469   }
470}
471
472
473void
474util_format_g8r8_g8b8_unorm_pack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
475                                        const uint8_t *src_row, unsigned src_stride,
476                                        unsigned width, unsigned height)
477{
478   unsigned x, y;
479
480   for (y = 0; y < height; y += 1) {
481      const uint8_t *src = src_row;
482      uint32_t *dst = (uint32_t *)dst_row;
483      uint32_t r, g0, g1, b;
484      uint32_t value;
485
486      for (x = 0; x + 1 < width; x += 2) {
487         r  = (src[0] + src[4] + 1) >> 1;
488         g0 = src[1];
489         g1 = src[5];
490         b  = (src[2] + src[6] + 1) >> 1;
491
492         value  = g0;
493         value |= r  <<  8;
494         value |= g1 << 16;
495         value |= b  << 24;
496
497#ifdef PIPE_ARCH_BIG_ENDIAN
498         value = util_bswap32(value);
499#endif
500
501         *dst++ = value;
502
503         src += 8;
504      }
505
506      if (x < width) {
507         r  = src[0];
508         g0 = src[1];
509         g1 = 0;
510         b  = src[2];
511
512         value  = g0;
513         value |= r  <<  8;
514         value |= g1 << 16;
515         value |= b  << 24;
516
517#ifdef PIPE_ARCH_BIG_ENDIAN
518         value = util_bswap32(value);
519#endif
520
521         *dst = value;
522      }
523
524      dst_row += dst_stride/sizeof(*dst_row);
525      src_row += src_stride/sizeof(*src_row);
526   }
527}
528
529
530void
531util_format_g8r8_g8b8_unorm_fetch_rgba_float(float *dst, const uint8_t *src,
532                                        unsigned i, unsigned j)
533{
534   assert(i < 2);
535   assert(j < 1);
536
537   dst[0] = ubyte_to_float(src[1]);             /* r */
538   dst[1] = ubyte_to_float(src[0 + 2*i]);       /* g */
539   dst[2] = ubyte_to_float(src[3]);             /* b */
540   dst[3] = 1.0f;                               /* a */
541}
542
543
544void
545util_format_uyvy_unpack_rgba_float(float *dst_row, unsigned dst_stride,
546                              const uint8_t *src_row, unsigned src_stride,
547                              unsigned width, unsigned height)
548{
549   unsigned x, y;
550
551   for (y = 0; y < height; y += 1) {
552      float *dst = dst_row;
553      const uint32_t *src = (const uint32_t *)src_row;
554      uint32_t value;
555      uint8_t y0, y1, u, v;
556
557      for (x = 0; x + 1 < width; x += 2) {
558         value = *src++;
559
560#ifdef PIPE_ARCH_BIG_ENDIAN
561         value = util_bswap32(value);
562#endif
563
564         u  = (value >>  0) & 0xff;
565         y0 = (value >>  8) & 0xff;
566         v  = (value >> 16) & 0xff;
567         y1 = (value >> 24) & 0xff;
568
569         util_format_yuv_to_rgb_float(y0, u, v, &dst[0], &dst[1], &dst[2]);
570         dst[3] = 1.0f; /* a */
571         dst += 4;
572
573         util_format_yuv_to_rgb_float(y1, u, v, &dst[0], &dst[1], &dst[2]);
574         dst[3] = 1.0f; /* a */
575         dst += 4;
576      }
577
578      if (x < width) {
579         value = *src;
580
581#ifdef PIPE_ARCH_BIG_ENDIAN
582         value = util_bswap32(value);
583#endif
584
585         u  = (value >>  0) & 0xff;
586         y0 = (value >>  8) & 0xff;
587         v  = (value >> 16) & 0xff;
588         y1 = (value >> 24) & 0xff;
589
590         util_format_yuv_to_rgb_float(y0, u, v, &dst[0], &dst[1], &dst[2]);
591         dst[3] = 1.0f; /* a */
592      }
593
594      src_row += src_stride/sizeof(*src_row);
595      dst_row += dst_stride/sizeof(*dst_row);
596   }
597}
598
599
600void
601util_format_uyvy_unpack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
602                               const uint8_t *src_row, unsigned src_stride,
603                               unsigned width, unsigned height)
604{
605   unsigned x, y;
606
607   for (y = 0; y < height; y += 1) {
608      uint8_t *dst = dst_row;
609      const uint32_t *src = (const uint32_t *)src_row;
610      uint32_t value;
611      uint8_t y0, y1, u, v;
612
613      for (x = 0; x + 1 < width; x += 2) {
614         value = *src++;
615
616#ifdef PIPE_ARCH_BIG_ENDIAN
617         value = util_bswap32(value);
618#endif
619
620         u  = (value >>  0) & 0xff;
621         y0 = (value >>  8) & 0xff;
622         v  = (value >> 16) & 0xff;
623         y1 = (value >> 24) & 0xff;
624
625         util_format_yuv_to_rgb_8unorm(y0, u, v, &dst[0], &dst[1], &dst[2]);
626         dst[3] = 0xff; /* a */
627         dst += 4;
628
629         util_format_yuv_to_rgb_8unorm(y1, u, v, &dst[0], &dst[1], &dst[2]);
630         dst[3] = 0xff; /* a */
631         dst += 4;
632      }
633
634      if (x < width) {
635         value = *src;
636
637#ifdef PIPE_ARCH_BIG_ENDIAN
638         value = util_bswap32(value);
639#endif
640
641         u  = (value >>  0) & 0xff;
642         y0 = (value >>  8) & 0xff;
643         v  = (value >> 16) & 0xff;
644         y1 = (value >> 24) & 0xff;
645
646         util_format_yuv_to_rgb_8unorm(y0, u, v, &dst[0], &dst[1], &dst[2]);
647         dst[3] = 0xff; /* a */
648      }
649
650      src_row += src_stride/sizeof(*src_row);
651      dst_row += dst_stride/sizeof(*dst_row);
652   }
653}
654
655
656void
657util_format_uyvy_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride,
658                            const float *src_row, unsigned src_stride,
659                            unsigned width, unsigned height)
660{
661   unsigned x, y;
662
663   for (y = 0; y < height; y += 1) {
664      const float *src = src_row;
665      uint32_t *dst = (uint32_t *)dst_row;
666      uint8_t y0, y1, u, v;
667      uint32_t value;
668
669      for (x = 0; x + 1 < width; x += 2) {
670         uint8_t y0, y1, u0, u1, v0, v1, u, v;
671
672         util_format_rgb_float_to_yuv(src[0], src[1], src[2],
673                                      &y0, &u0, &v0);
674         util_format_rgb_float_to_yuv(src[4], src[5], src[6],
675                                      &y1, &u1, &v1);
676
677         u = (u0 + u1 + 1) >> 1;
678         v = (v0 + v1 + 1) >> 1;
679
680         value  = u;
681         value |= y0 <<  8;
682         value |= v  << 16;
683         value |= y1 << 24;
684
685#ifdef PIPE_ARCH_BIG_ENDIAN
686         value = util_bswap32(value);
687#endif
688
689         *dst++ = value;
690
691         src += 8;
692      }
693
694      if (x < width) {
695         util_format_rgb_float_to_yuv(src[0], src[1], src[2],
696                                      &y0, &u, &v);
697         y1 = 0;
698
699         value  = u;
700         value |= y0 <<  8;
701         value |= v  << 16;
702         value |= y1 << 24;
703
704#ifdef PIPE_ARCH_BIG_ENDIAN
705         value = util_bswap32(value);
706#endif
707
708         *dst = value;
709      }
710
711      dst_row += dst_stride/sizeof(*dst_row);
712      src_row += src_stride/sizeof(*src_row);
713   }
714}
715
716
717void
718util_format_uyvy_pack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
719                             const uint8_t *src_row, unsigned src_stride,
720                             unsigned width, unsigned height)
721{
722   unsigned x, y;
723
724   for (y = 0; y < height; y += 1) {
725      const uint8_t *src = src_row;
726      uint32_t *dst = (uint32_t *)dst_row;
727      uint8_t y0, y1, u, v;
728      uint32_t value;
729
730      for (x = 0; x + 1 < width; x += 2) {
731         uint8_t y0, y1, u0, u1, v0, v1, u, v;
732
733         util_format_rgb_8unorm_to_yuv(src[0], src[1], src[2],
734                                       &y0, &u0, &v0);
735         util_format_rgb_8unorm_to_yuv(src[4], src[5], src[6],
736                                       &y1, &u1, &v1);
737
738         u = (u0 + u1 + 1) >> 1;
739         v = (v0 + v1 + 1) >> 1;
740
741         value  = u;
742         value |= y0 <<  8;
743         value |= v  << 16;
744         value |= y1 << 24;
745
746#ifdef PIPE_ARCH_BIG_ENDIAN
747         value = util_bswap32(value);
748#endif
749
750         *dst++ = value;
751
752         src += 8;
753      }
754
755      if (x < width) {
756         util_format_rgb_8unorm_to_yuv(src[0], src[1], src[2],
757                                       &y0, &u, &v);
758         y1 = 0;
759
760         value  = u;
761         value |= y0 <<  8;
762         value |= v  << 16;
763         value |= y1 << 24;
764
765#ifdef PIPE_ARCH_BIG_ENDIAN
766         value = util_bswap32(value);
767#endif
768
769         *dst = value;
770      }
771
772      dst_row += dst_stride/sizeof(*dst_row);
773      src_row += src_stride/sizeof(*src_row);
774   }
775}
776
777
778void
779util_format_uyvy_fetch_rgba_float(float *dst, const uint8_t *src,
780                             unsigned i, unsigned j)
781{
782   uint8_t y, u, v;
783
784   assert(i < 2);
785   assert(j < 1);
786
787   y = src[1 + i*2];
788   u = src[0];
789   v = src[2];
790
791   util_format_yuv_to_rgb_float(y, u, v, &dst[0], &dst[1], &dst[2]);
792
793   dst[3] = 1.0f;
794}
795
796
797void
798util_format_yuyv_unpack_rgba_float(float *dst_row, unsigned dst_stride,
799                              const uint8_t *src_row, unsigned src_stride,
800                              unsigned width, unsigned height)
801{
802   unsigned x, y;
803
804   for (y = 0; y < height; y += 1) {
805      float *dst = dst_row;
806      const uint32_t *src = (const uint32_t *)src_row;
807      uint32_t value;
808      uint8_t y0, y1, u, v;
809
810      for (x = 0; x + 1 < width; x += 2) {
811         value = *src++;
812
813#ifdef PIPE_ARCH_BIG_ENDIAN
814         value = util_bswap32(value);
815#endif
816
817         y0 = (value >>  0) & 0xff;
818         u  = (value >>  8) & 0xff;
819         y1 = (value >> 16) & 0xff;
820         v  = (value >> 24) & 0xff;
821
822         util_format_yuv_to_rgb_float(y0, u, v, &dst[0], &dst[1], &dst[2]);
823         dst[3] = 1.0f; /* a */
824         dst += 4;
825
826         util_format_yuv_to_rgb_float(y1, u, v, &dst[0], &dst[1], &dst[2]);
827         dst[3] = 1.0f; /* a */
828         dst += 4;
829      }
830
831      if (x < width) {
832         value = *src;
833
834#ifdef PIPE_ARCH_BIG_ENDIAN
835         value = util_bswap32(value);
836#endif
837
838         y0 = (value >>  0) & 0xff;
839         u  = (value >>  8) & 0xff;
840         y1 = (value >> 16) & 0xff;
841         v  = (value >> 24) & 0xff;
842
843         util_format_yuv_to_rgb_float(y0, u, v, &dst[0], &dst[1], &dst[2]);
844         dst[3] = 1.0f; /* a */
845      }
846
847      src_row += src_stride/sizeof(*src_row);
848      dst_row += dst_stride/sizeof(*dst_row);
849   }
850}
851
852
853void
854util_format_yuyv_unpack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
855                               const uint8_t *src_row, unsigned src_stride,
856                               unsigned width, unsigned height)
857{
858   unsigned x, y;
859
860   for (y = 0; y < height; y += 1) {
861      uint8_t *dst = dst_row;
862      const uint32_t *src = (const uint32_t *)src_row;
863      uint32_t value;
864      uint8_t y0, y1, u, v;
865
866      for (x = 0; x + 1 < width; x += 2) {
867         value = *src++;
868
869#ifdef PIPE_ARCH_BIG_ENDIAN
870         value = util_bswap32(value);
871#endif
872
873         y0 = (value >>  0) & 0xff;
874         u  = (value >>  8) & 0xff;
875         y1 = (value >> 16) & 0xff;
876         v  = (value >> 24) & 0xff;
877
878         util_format_yuv_to_rgb_8unorm(y0, u, v, &dst[0], &dst[1], &dst[2]);
879         dst[3] = 0xff; /* a */
880         dst += 4;
881
882         util_format_yuv_to_rgb_8unorm(y1, u, v, &dst[0], &dst[1], &dst[2]);
883         dst[3] = 0xff; /* a */
884         dst += 4;
885      }
886
887      if (x < width) {
888         value = *src;
889
890#ifdef PIPE_ARCH_BIG_ENDIAN
891         value = util_bswap32(value);
892#endif
893
894         y0 = (value >>  0) & 0xff;
895         u  = (value >>  8) & 0xff;
896         y1 = (value >> 16) & 0xff;
897         v  = (value >> 24) & 0xff;
898
899         util_format_yuv_to_rgb_8unorm(y0, u, v, &dst[0], &dst[1], &dst[2]);
900         dst[3] = 0xff; /* a */
901      }
902
903      src_row += src_stride/sizeof(*src_row);
904      dst_row += dst_stride/sizeof(*dst_row);
905   }
906}
907
908
909void
910util_format_yuyv_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride,
911                            const float *src_row, unsigned src_stride,
912                            unsigned width, unsigned height)
913{
914   unsigned x, y;
915
916   for (y = 0; y < height; y += 1) {
917      const float *src = src_row;
918      uint32_t *dst = (uint32_t *)dst_row;
919      uint8_t y0, y1, u, v;
920      uint32_t value;
921
922      for (x = 0; x + 1 < width; x += 2) {
923         uint8_t y0, y1, u0, u1, v0, v1, u, v;
924
925         util_format_rgb_float_to_yuv(src[0], src[1], src[2],
926                                      &y0, &u0, &v0);
927         util_format_rgb_float_to_yuv(src[4], src[5], src[6],
928                                      &y1, &u1, &v1);
929
930         u = (u0 + u1 + 1) >> 1;
931         v = (v0 + v1 + 1) >> 1;
932
933         value  = y0;
934         value |= u  <<  8;
935         value |= y1 << 16;
936         value |= v  << 24;
937
938#ifdef PIPE_ARCH_BIG_ENDIAN
939         value = util_bswap32(value);
940#endif
941
942         *dst++ = value;
943
944         src += 8;
945      }
946
947      if (x < width) {
948         util_format_rgb_float_to_yuv(src[0], src[1], src[2],
949                                      &y0, &u, &v);
950         y1 = 0;
951
952         value  = y0;
953         value |= u  <<  8;
954         value |= y1 << 16;
955         value |= v  << 24;
956
957#ifdef PIPE_ARCH_BIG_ENDIAN
958         value = util_bswap32(value);
959#endif
960
961         *dst = value;
962      }
963
964      dst_row += dst_stride/sizeof(*dst_row);
965      src_row += src_stride/sizeof(*src_row);
966   }
967}
968
969
970void
971util_format_yuyv_pack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
972                             const uint8_t *src_row, unsigned src_stride,
973                             unsigned width, unsigned height)
974{
975   unsigned x, y;
976
977   for (y = 0; y < height; y += 1) {
978      const uint8_t *src = src_row;
979      uint32_t *dst = (uint32_t *)dst_row;
980      uint8_t y0, y1, u, v;
981      uint32_t value;
982
983      for (x = 0; x + 1 < width; x += 2) {
984         uint8_t y0, y1, u0, u1, v0, v1, u, v;
985
986         util_format_rgb_8unorm_to_yuv(src[0], src[1], src[2],
987                                       &y0, &u0, &v0);
988         util_format_rgb_8unorm_to_yuv(src[4], src[5], src[6],
989                                       &y1, &u1, &v1);
990
991         u = (u0 + u1 + 1) >> 1;
992         v = (v0 + v1 + 1) >> 1;
993
994         value  = y0;
995         value |= u  <<  8;
996         value |= y1 << 16;
997         value |= v  << 24;
998
999#ifdef PIPE_ARCH_BIG_ENDIAN
1000         value = util_bswap32(value);
1001#endif
1002
1003         *dst++ = value;
1004
1005         src += 8;
1006      }
1007
1008      if (x < width) {
1009         util_format_rgb_8unorm_to_yuv(src[0], src[1], src[2],
1010                                       &y0, &u, &v);
1011         y1 = 0;
1012
1013         value  = y0;
1014         value |= u  <<  8;
1015         value |= y1 << 16;
1016         value |= v  << 24;
1017
1018#ifdef PIPE_ARCH_BIG_ENDIAN
1019         value = util_bswap32(value);
1020#endif
1021
1022         *dst = value;
1023      }
1024
1025      dst_row += dst_stride/sizeof(*dst_row);
1026      src_row += src_stride/sizeof(*src_row);
1027   }
1028}
1029
1030
1031void
1032util_format_yuyv_fetch_rgba_float(float *dst, const uint8_t *src,
1033                             unsigned i, unsigned j)
1034{
1035   uint8_t y, u, v;
1036
1037   assert(i < 2);
1038   assert(j < 1);
1039
1040   y = src[0 + i*2];
1041   u = src[1];
1042   v = src[3];
1043
1044   util_format_yuv_to_rgb_float(y, u, v, &dst[0], &dst[1], &dst[2]);
1045
1046   dst[3] = 1.0f;
1047}
1048
1049/* XXX: Stubbed for now */
1050void
1051util_format_yv12_unpack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1052                             const uint8_t *src_row, unsigned src_stride,
1053                             unsigned width, unsigned height) {}
1054void
1055util_format_yv12_pack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1056                             const uint8_t *src_row, unsigned src_stride,
1057                             unsigned width, unsigned height) {}
1058void
1059util_format_yv12_unpack_rgba_float(float *dst_row, unsigned dst_stride,
1060                             const uint8_t *src_row, unsigned src_stride,
1061                             unsigned width, unsigned height) {}
1062void
1063util_format_yv12_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride,
1064                             const float *src_row, unsigned src_stride,
1065                             unsigned width, unsigned height) {}
1066void
1067util_format_yv12_fetch_rgba_float(float *dst, const uint8_t *src,
1068                             unsigned i, unsigned j) {}
1069void
1070util_format_yv16_unpack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1071                             const uint8_t *src_row, unsigned src_stride,
1072                             unsigned width, unsigned height) {}
1073void
1074util_format_yv16_pack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1075                             const uint8_t *src_row, unsigned src_stride,
1076                             unsigned width, unsigned height) {}
1077void
1078util_format_yv16_unpack_rgba_float(float *dst_row, unsigned dst_stride,
1079                             const uint8_t *src_row, unsigned src_stride,
1080                             unsigned width, unsigned height) {}
1081void
1082util_format_yv16_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride,
1083                             const float *src_row, unsigned src_stride,
1084                             unsigned width, unsigned height) {}
1085void
1086util_format_yv16_fetch_rgba_float(float *dst, const uint8_t *src,
1087                             unsigned i, unsigned j) {}
1088void
1089util_format_iyuv_unpack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1090                             const uint8_t *src_row, unsigned src_stride,
1091                             unsigned width, unsigned height) {}
1092void
1093util_format_iyuv_pack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1094                             const uint8_t *src_row, unsigned src_stride,
1095                             unsigned width, unsigned height) {}
1096void
1097util_format_iyuv_unpack_rgba_float(float *dst_row, unsigned dst_stride,
1098                             const uint8_t *src_row, unsigned src_stride,
1099                             unsigned width, unsigned height) {}
1100void
1101util_format_iyuv_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride,
1102                             const float *src_row, unsigned src_stride,
1103                             unsigned width, unsigned height) {}
1104void
1105util_format_iyuv_fetch_rgba_float(float *dst, const uint8_t *src,
1106                             unsigned i, unsigned j) {}
1107void
1108util_format_nv12_unpack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1109                             const uint8_t *src_row, unsigned src_stride,
1110                             unsigned width, unsigned height) {}
1111void
1112util_format_nv12_pack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1113                             const uint8_t *src_row, unsigned src_stride,
1114                             unsigned width, unsigned height) {}
1115void
1116util_format_nv12_unpack_rgba_float(float *dst_row, unsigned dst_stride,
1117                             const uint8_t *src_row, unsigned src_stride,
1118                             unsigned width, unsigned height) {}
1119void
1120util_format_nv12_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride,
1121                             const float *src_row, unsigned src_stride,
1122                             unsigned width, unsigned height) {}
1123void
1124util_format_nv12_fetch_rgba_float(float *dst, const uint8_t *src,
1125                             unsigned i, unsigned j) {}
1126void
1127util_format_nv21_unpack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1128                             const uint8_t *src_row, unsigned src_stride,
1129                             unsigned width, unsigned height) {}
1130void
1131util_format_nv21_pack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1132                             const uint8_t *src_row, unsigned src_stride,
1133                             unsigned width, unsigned height) {}
1134void
1135util_format_nv21_unpack_rgba_float(float *dst_row, unsigned dst_stride,
1136                             const uint8_t *src_row, unsigned src_stride,
1137                             unsigned width, unsigned height) {}
1138void
1139util_format_nv21_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride,
1140                             const float *src_row, unsigned src_stride,
1141                             unsigned width, unsigned height) {}
1142void
1143util_format_nv21_fetch_rgba_float(float *dst, const uint8_t *src,
1144                             unsigned i, unsigned j) {}
1145
1146void
1147util_format_r8g8_r8b8_unorm_unpack_rgba_float(float *dst_row, unsigned dst_stride,
1148                                         const uint8_t *src_row, unsigned src_stride,
1149                                         unsigned width, unsigned height) {}
1150
1151void
1152util_format_r8g8_r8b8_unorm_unpack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1153                                          const uint8_t *src_row, unsigned src_stride,
1154                                          unsigned width, unsigned height) {}
1155
1156void
1157util_format_r8g8_r8b8_unorm_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride,
1158                                       const float *src_row, unsigned src_stride,
1159                                       unsigned width, unsigned height) {}
1160
1161void
1162util_format_r8g8_r8b8_unorm_pack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1163                                        const uint8_t *src_row, unsigned src_stride,
1164                                        unsigned width, unsigned height) {}
1165
1166void
1167util_format_r8g8_r8b8_unorm_fetch_rgba_float(float *dst, const uint8_t *src,
1168                                        unsigned i, unsigned j) {}
1169
1170void
1171util_format_g8r8_b8r8_unorm_unpack_rgba_float(float *dst_row, unsigned dst_stride,
1172                                         const uint8_t *src_row, unsigned src_stride,
1173                                         unsigned width, unsigned height) {}
1174
1175void
1176util_format_g8r8_b8r8_unorm_unpack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1177                                          const uint8_t *src_row, unsigned src_stride,
1178                                          unsigned width, unsigned height) {}
1179
1180void
1181util_format_g8r8_b8r8_unorm_pack_rgba_float(uint8_t *dst_row, unsigned dst_stride,
1182                                       const float *src_row, unsigned src_stride,
1183                                       unsigned width, unsigned height) {}
1184
1185void
1186util_format_g8r8_b8r8_unorm_pack_rgba_8unorm(uint8_t *dst_row, unsigned dst_stride,
1187                                        const uint8_t *src_row, unsigned src_stride,
1188                                        unsigned width, unsigned height) {}
1189
1190void
1191util_format_g8r8_b8r8_unorm_fetch_rgba_float(float *dst, const uint8_t *src,
1192                                        unsigned i, unsigned j) {}
1193