• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Mesa 3-D graphics library
3  *
4  * Copyright (C) 1999-2008  Brian Paul   All Rights Reserved.
5  * Copyright (C) 2009-2010  VMware, Inc.  All Rights Reserved.
6  *
7  * Permission is hereby granted, free of charge, to any person obtaining a
8  * copy of this software and associated documentation files (the "Software"),
9  * to deal in the Software without restriction, including without limitation
10  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
11  * and/or sell copies of the Software, and to permit persons to whom the
12  * Software is furnished to do so, subject to the following conditions:
13  *
14  * The above copyright notice and this permission notice shall be included
15  * in all copies or substantial portions of the Software.
16  *
17  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
18  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
20  * THEA AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
21  * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
22  * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23  */
24 
25 
26 /**
27  * \file pack.c
28  * Image and pixel span packing and unpacking.
29  */
30 
31 
32 /*
33  * XXX: MSVC takes forever to compile this module for x86_64 unless we disable
34  * this global optimization.
35  *
36  * See also:
37  * - http://msdn.microsoft.com/en-us/library/1yk3ydd7.aspx
38  * - http://msdn.microsoft.com/en-us/library/chh3fb0k.aspx
39  */
40 #if defined(_MSC_VER) && defined(_M_X64)
41 #  pragma optimize( "g", off )
42 #endif
43 
44 
45 #include "errors.h"
46 #include "glheader.h"
47 #include "enums.h"
48 #include "image.h"
49 
50 #include "macros.h"
51 #include "mtypes.h"
52 #include "pack.h"
53 #include "pixeltransfer.h"
54 
55 #include "glformats.h"
56 #include "format_utils.h"
57 #include "format_pack.h"
58 #include "format_unpack.h"
59 #include "util/format/u_format.h"
60 
61 /**
62  * Flip the 8 bits in each byte of the given array.
63  *
64  * \param p array.
65  * \param n number of bytes.
66  *
67  * \todo try this trick to flip bytes someday:
68  * \code
69  *  v = ((v & 0x55555555) << 1) | ((v >> 1) & 0x55555555);
70  *  v = ((v & 0x33333333) << 2) | ((v >> 2) & 0x33333333);
71  *  v = ((v & 0x0f0f0f0f) << 4) | ((v >> 4) & 0x0f0f0f0f);
72  * \endcode
73  */
74 static void
flip_bytes(GLubyte * p,GLuint n)75 flip_bytes( GLubyte *p, GLuint n )
76 {
77    GLuint i, a, b;
78    for (i = 0; i < n; i++) {
79       b = (GLuint) p[i];        /* words are often faster than bytes */
80       a = ((b & 0x01) << 7) |
81 	  ((b & 0x02) << 5) |
82 	  ((b & 0x04) << 3) |
83 	  ((b & 0x08) << 1) |
84 	  ((b & 0x10) >> 1) |
85 	  ((b & 0x20) >> 3) |
86 	  ((b & 0x40) >> 5) |
87 	  ((b & 0x80) >> 7);
88       p[i] = (GLubyte) a;
89    }
90 }
91 
92 
93 
94 /*
95  * Unpack a 32x32 pixel polygon stipple from user memory using the
96  * current pixel unpack settings.
97  */
98 void
_mesa_unpack_polygon_stipple(const GLubyte * pattern,GLuint dest[32],const struct gl_pixelstore_attrib * unpacking)99 _mesa_unpack_polygon_stipple( const GLubyte *pattern, GLuint dest[32],
100                               const struct gl_pixelstore_attrib *unpacking )
101 {
102    GLubyte *ptrn = (GLubyte *) _mesa_unpack_image(2, 32, 32, 1, GL_COLOR_INDEX,
103                                                   GL_BITMAP, pattern, unpacking);
104    if (ptrn) {
105       /* Convert pattern from GLubytes to GLuints and handle big/little
106        * endian differences
107        */
108       GLubyte *p = ptrn;
109       GLint i;
110       for (i = 0; i < 32; i++) {
111          dest[i] = (p[0] << 24)
112                  | (p[1] << 16)
113                  | (p[2] <<  8)
114                  | (p[3]      );
115          p += 4;
116       }
117       free(ptrn);
118    }
119 }
120 
121 
122 /*
123  * Pack polygon stipple into user memory given current pixel packing
124  * settings.
125  */
126 void
_mesa_pack_polygon_stipple(const GLuint pattern[32],GLubyte * dest,const struct gl_pixelstore_attrib * packing)127 _mesa_pack_polygon_stipple( const GLuint pattern[32], GLubyte *dest,
128                             const struct gl_pixelstore_attrib *packing )
129 {
130    /* Convert pattern from GLuints to GLubytes to handle big/little
131     * endian differences.
132     */
133    GLubyte ptrn[32*4];
134    GLint i;
135    for (i = 0; i < 32; i++) {
136       ptrn[i * 4 + 0] = (GLubyte) ((pattern[i] >> 24) & 0xff);
137       ptrn[i * 4 + 1] = (GLubyte) ((pattern[i] >> 16) & 0xff);
138       ptrn[i * 4 + 2] = (GLubyte) ((pattern[i] >> 8 ) & 0xff);
139       ptrn[i * 4 + 3] = (GLubyte) ((pattern[i]      ) & 0xff);
140    }
141 
142    _mesa_pack_bitmap(32, 32, ptrn, dest, packing);
143 }
144 
145 
146 /*
147  * Pack bitmap data.
148  */
149 void
_mesa_pack_bitmap(GLint width,GLint height,const GLubyte * source,GLubyte * dest,const struct gl_pixelstore_attrib * packing)150 _mesa_pack_bitmap( GLint width, GLint height, const GLubyte *source,
151                    GLubyte *dest, const struct gl_pixelstore_attrib *packing )
152 {
153    GLint row, width_in_bytes;
154    const GLubyte *src;
155 
156    if (!source)
157       return;
158 
159    width_in_bytes = DIV_ROUND_UP( width, 8 );
160    src = source;
161    for (row = 0; row < height; row++) {
162       GLubyte *dst = (GLubyte *) _mesa_image_address2d(packing, dest,
163                        width, height, GL_COLOR_INDEX, GL_BITMAP, row, 0);
164       if (!dst)
165          return;
166 
167       if ((packing->SkipPixels & 7) == 0) {
168          memcpy( dst, src, width_in_bytes );
169          if (packing->LsbFirst) {
170             flip_bytes( dst, width_in_bytes );
171          }
172       }
173       else {
174          /* handling SkipPixels is a bit tricky (no pun intended!) */
175          GLint i;
176          if (packing->LsbFirst) {
177             GLubyte srcMask = 128;
178             GLubyte dstMask = 1 << (packing->SkipPixels & 0x7);
179             const GLubyte *s = src;
180             GLubyte *d = dst;
181             *d = 0;
182             for (i = 0; i < width; i++) {
183                if (*s & srcMask) {
184                   *d |= dstMask;
185                }
186                if (srcMask == 1) {
187                   srcMask = 128;
188                   s++;
189                }
190                else {
191                   srcMask = srcMask >> 1;
192                }
193                if (dstMask == 128) {
194                   dstMask = 1;
195                   d++;
196                   *d = 0;
197                }
198                else {
199                   dstMask = dstMask << 1;
200                }
201             }
202          }
203          else {
204             GLubyte srcMask = 128;
205             GLubyte dstMask = 128 >> (packing->SkipPixels & 0x7);
206             const GLubyte *s = src;
207             GLubyte *d = dst;
208             *d = 0;
209             for (i = 0; i < width; i++) {
210                if (*s & srcMask) {
211                   *d |= dstMask;
212                }
213                if (srcMask == 1) {
214                   srcMask = 128;
215                   s++;
216                }
217                else {
218                   srcMask = srcMask >> 1;
219                }
220                if (dstMask == 1) {
221                   dstMask = 128;
222                   d++;
223                   *d = 0;
224                }
225                else {
226                   dstMask = dstMask >> 1;
227                }
228             }
229          }
230       }
231       src += width_in_bytes;
232    }
233 }
234 
235 
236 #define SWAP2BYTE(VALUE)			\
237    {						\
238       GLubyte *bytes = (GLubyte *) &(VALUE);	\
239       GLubyte tmp = bytes[0];			\
240       bytes[0] = bytes[1];			\
241       bytes[1] = tmp;				\
242    }
243 
244 #define SWAP4BYTE(VALUE)			\
245    {						\
246       GLubyte *bytes = (GLubyte *) &(VALUE);	\
247       GLubyte tmp = bytes[0];			\
248       bytes[0] = bytes[3];			\
249       bytes[3] = tmp;				\
250       tmp = bytes[1];				\
251       bytes[1] = bytes[2];			\
252       bytes[2] = tmp;				\
253    }
254 
255 
256 static void
extract_uint_indexes(GLuint n,GLuint indexes[],GLenum srcFormat,GLenum srcType,const GLvoid * src,const struct gl_pixelstore_attrib * unpack)257 extract_uint_indexes(GLuint n, GLuint indexes[],
258                      GLenum srcFormat, GLenum srcType, const GLvoid *src,
259                      const struct gl_pixelstore_attrib *unpack )
260 {
261    assert(srcFormat == GL_COLOR_INDEX || srcFormat == GL_STENCIL_INDEX);
262 
263    assert(srcType == GL_BITMAP ||
264           srcType == GL_UNSIGNED_BYTE ||
265           srcType == GL_BYTE ||
266           srcType == GL_UNSIGNED_SHORT ||
267           srcType == GL_SHORT ||
268           srcType == GL_UNSIGNED_INT ||
269           srcType == GL_INT ||
270           srcType == GL_UNSIGNED_INT_24_8_EXT ||
271           srcType == GL_HALF_FLOAT_ARB ||
272           srcType == GL_HALF_FLOAT_OES ||
273           srcType == GL_FLOAT ||
274           srcType == GL_FLOAT_32_UNSIGNED_INT_24_8_REV);
275 
276    switch (srcType) {
277       case GL_BITMAP:
278          {
279             GLubyte *ubsrc = (GLubyte *) src;
280             if (unpack->LsbFirst) {
281                GLubyte mask = 1 << (unpack->SkipPixels & 0x7);
282                GLuint i;
283                for (i = 0; i < n; i++) {
284                   indexes[i] = (*ubsrc & mask) ? 1 : 0;
285                   if (mask == 128) {
286                      mask = 1;
287                      ubsrc++;
288                   }
289                   else {
290                      mask = mask << 1;
291                   }
292                }
293             }
294             else {
295                GLubyte mask = 128 >> (unpack->SkipPixels & 0x7);
296                GLuint i;
297                for (i = 0; i < n; i++) {
298                   indexes[i] = (*ubsrc & mask) ? 1 : 0;
299                   if (mask == 1) {
300                      mask = 128;
301                      ubsrc++;
302                   }
303                   else {
304                      mask = mask >> 1;
305                   }
306                }
307             }
308          }
309          break;
310       case GL_UNSIGNED_BYTE:
311          {
312             GLuint i;
313             const GLubyte *s = (const GLubyte *) src;
314             for (i = 0; i < n; i++)
315                indexes[i] = s[i];
316          }
317          break;
318       case GL_BYTE:
319          {
320             GLuint i;
321             const GLbyte *s = (const GLbyte *) src;
322             for (i = 0; i < n; i++)
323                indexes[i] = s[i];
324          }
325          break;
326       case GL_UNSIGNED_SHORT:
327          {
328             GLuint i;
329             const GLushort *s = (const GLushort *) src;
330             if (unpack->SwapBytes) {
331                for (i = 0; i < n; i++) {
332                   GLushort value = s[i];
333                   SWAP2BYTE(value);
334                   indexes[i] = value;
335                }
336             }
337             else {
338                for (i = 0; i < n; i++)
339                   indexes[i] = s[i];
340             }
341          }
342          break;
343       case GL_SHORT:
344          {
345             GLuint i;
346             const GLshort *s = (const GLshort *) src;
347             if (unpack->SwapBytes) {
348                for (i = 0; i < n; i++) {
349                   GLshort value = s[i];
350                   SWAP2BYTE(value);
351                   indexes[i] = value;
352                }
353             }
354             else {
355                for (i = 0; i < n; i++)
356                   indexes[i] = s[i];
357             }
358          }
359          break;
360       case GL_UNSIGNED_INT:
361          {
362             GLuint i;
363             const GLuint *s = (const GLuint *) src;
364             if (unpack->SwapBytes) {
365                for (i = 0; i < n; i++) {
366                   GLuint value = s[i];
367                   SWAP4BYTE(value);
368                   indexes[i] = value;
369                }
370             }
371             else {
372                for (i = 0; i < n; i++)
373                   indexes[i] = s[i];
374             }
375          }
376          break;
377       case GL_INT:
378          {
379             GLuint i;
380             const GLint *s = (const GLint *) src;
381             if (unpack->SwapBytes) {
382                for (i = 0; i < n; i++) {
383                   GLint value = s[i];
384                   SWAP4BYTE(value);
385                   indexes[i] = value;
386                }
387             }
388             else {
389                for (i = 0; i < n; i++)
390                   indexes[i] = s[i];
391             }
392          }
393          break;
394       case GL_FLOAT:
395          {
396             GLuint i;
397             const GLfloat *s = (const GLfloat *) src;
398             if (unpack->SwapBytes) {
399                for (i = 0; i < n; i++) {
400                   GLfloat value = s[i];
401                   SWAP4BYTE(value);
402                   indexes[i] = (GLuint) value;
403                }
404             }
405             else {
406                for (i = 0; i < n; i++)
407                   indexes[i] = (GLuint) s[i];
408             }
409          }
410          break;
411       case GL_HALF_FLOAT_ARB:
412       case GL_HALF_FLOAT_OES:
413          {
414             GLuint i;
415             const GLhalfARB *s = (const GLhalfARB *) src;
416             if (unpack->SwapBytes) {
417                for (i = 0; i < n; i++) {
418                   GLhalfARB value = s[i];
419                   SWAP2BYTE(value);
420                   indexes[i] = (GLuint) _mesa_half_to_float(value);
421                }
422             }
423             else {
424                for (i = 0; i < n; i++)
425                   indexes[i] = (GLuint) _mesa_half_to_float(s[i]);
426             }
427          }
428          break;
429       case GL_UNSIGNED_INT_24_8_EXT:
430          {
431             GLuint i;
432             const GLuint *s = (const GLuint *) src;
433             if (unpack->SwapBytes) {
434                for (i = 0; i < n; i++) {
435                   GLuint value = s[i];
436                   SWAP4BYTE(value);
437                   indexes[i] = value & 0xff;  /* lower 8 bits */
438                }
439             }
440             else {
441                for (i = 0; i < n; i++)
442                   indexes[i] = s[i] & 0xff;  /* lower 8 bits */
443             }
444          }
445          break;
446       case GL_FLOAT_32_UNSIGNED_INT_24_8_REV:
447          {
448             GLuint i;
449             const GLuint *s = (const GLuint *) src;
450             if (unpack->SwapBytes) {
451                for (i = 0; i < n; i++) {
452                   GLuint value = s[i*2+1];
453                   SWAP4BYTE(value);
454                   indexes[i] = value & 0xff;  /* lower 8 bits */
455                }
456             }
457             else {
458                for (i = 0; i < n; i++)
459                   indexes[i] = s[i*2+1] & 0xff;  /* lower 8 bits */
460             }
461          }
462          break;
463 
464       default:
465          unreachable("bad srcType in extract_uint_indexes");
466    }
467 }
468 
469 
470 /*
471  * Unpack a row of stencil data from a client buffer according to
472  * the pixel unpacking parameters.
473  * This is (or will be) used by glDrawPixels
474  *
475  * Args:  ctx - the context
476  *        n - number of pixels
477  *        dstType - destination data type
478  *        dest - destination array
479  *        srcType - source pixel type
480  *        source - source data pointer
481  *        srcPacking - pixel unpacking parameters
482  *        transferOps - apply offset/bias/lookup ops?
483  */
484 void
_mesa_unpack_stencil_span(struct gl_context * ctx,GLuint n,GLenum dstType,GLvoid * dest,GLenum srcType,const GLvoid * source,const struct gl_pixelstore_attrib * srcPacking,GLbitfield transferOps)485 _mesa_unpack_stencil_span( struct gl_context *ctx, GLuint n,
486                            GLenum dstType, GLvoid *dest,
487                            GLenum srcType, const GLvoid *source,
488                            const struct gl_pixelstore_attrib *srcPacking,
489                            GLbitfield transferOps )
490 {
491    assert(srcType == GL_BITMAP ||
492           srcType == GL_UNSIGNED_BYTE ||
493           srcType == GL_BYTE ||
494           srcType == GL_UNSIGNED_SHORT ||
495           srcType == GL_SHORT ||
496           srcType == GL_UNSIGNED_INT ||
497           srcType == GL_INT ||
498           srcType == GL_UNSIGNED_INT_24_8_EXT ||
499           srcType == GL_HALF_FLOAT_ARB ||
500           srcType == GL_HALF_FLOAT_OES ||
501           srcType == GL_FLOAT ||
502           srcType == GL_FLOAT_32_UNSIGNED_INT_24_8_REV);
503 
504    assert(dstType == GL_UNSIGNED_BYTE ||
505           dstType == GL_UNSIGNED_SHORT ||
506           dstType == GL_UNSIGNED_INT ||
507           dstType == GL_FLOAT_32_UNSIGNED_INT_24_8_REV);
508 
509    /* only shift and offset apply to stencil */
510    transferOps &= IMAGE_SHIFT_OFFSET_BIT;
511 
512    /*
513     * Try simple cases first
514     */
515    if (transferOps == 0 &&
516        !ctx->Pixel.MapStencilFlag &&
517        srcType == GL_UNSIGNED_BYTE &&
518        dstType == GL_UNSIGNED_BYTE) {
519       memcpy(dest, source, n * sizeof(GLubyte));
520    }
521    else if (transferOps == 0 &&
522             !ctx->Pixel.MapStencilFlag &&
523             srcType == GL_UNSIGNED_INT &&
524             dstType == GL_UNSIGNED_INT &&
525             !srcPacking->SwapBytes) {
526       memcpy(dest, source, n * sizeof(GLuint));
527    }
528    else {
529       /*
530        * general solution
531        */
532       GLuint *indexes = malloc(n * sizeof(GLuint));
533 
534       if (!indexes) {
535          _mesa_error(ctx, GL_OUT_OF_MEMORY, "stencil unpacking");
536          return;
537       }
538 
539       extract_uint_indexes(n, indexes, GL_STENCIL_INDEX, srcType, source,
540                            srcPacking);
541 
542       if (transferOps & IMAGE_SHIFT_OFFSET_BIT) {
543          /* shift and offset indexes */
544          _mesa_shift_and_offset_ci(ctx, n, indexes);
545       }
546 
547       if (ctx->Pixel.MapStencilFlag) {
548          /* Apply stencil lookup table */
549          const GLuint mask = ctx->PixelMaps.StoS.Size - 1;
550          GLuint i;
551          for (i = 0; i < n; i++) {
552             indexes[i] = (GLuint)ctx->PixelMaps.StoS.Map[ indexes[i] & mask ];
553          }
554       }
555 
556       /* convert to dest type */
557       switch (dstType) {
558          case GL_UNSIGNED_BYTE:
559             {
560                GLubyte *dst = (GLubyte *) dest;
561                GLuint i;
562                for (i = 0; i < n; i++) {
563                   dst[i] = (GLubyte) (indexes[i] & 0xff);
564                }
565             }
566             break;
567          case GL_UNSIGNED_SHORT:
568             {
569                GLuint *dst = (GLuint *) dest;
570                GLuint i;
571                for (i = 0; i < n; i++) {
572                   dst[i] = (GLushort) (indexes[i] & 0xffff);
573                }
574             }
575             break;
576          case GL_UNSIGNED_INT:
577             memcpy(dest, indexes, n * sizeof(GLuint));
578             break;
579          case GL_FLOAT_32_UNSIGNED_INT_24_8_REV:
580             {
581                GLuint *dst = (GLuint *) dest;
582                GLuint i;
583                for (i = 0; i < n; i++) {
584                   dst[i*2+1] = indexes[i] & 0xff; /* lower 8 bits */
585                }
586             }
587             break;
588          default:
589             unreachable("bad dstType in _mesa_unpack_stencil_span");
590       }
591 
592       free(indexes);
593    }
594 }
595 
596 
597 void
_mesa_pack_stencil_span(struct gl_context * ctx,GLuint n,GLenum dstType,GLvoid * dest,const GLubyte * source,const struct gl_pixelstore_attrib * dstPacking)598 _mesa_pack_stencil_span( struct gl_context *ctx, GLuint n,
599                          GLenum dstType, GLvoid *dest, const GLubyte *source,
600                          const struct gl_pixelstore_attrib *dstPacking )
601 {
602    GLubyte *stencil = malloc(n * sizeof(GLubyte));
603 
604    if (!stencil) {
605       _mesa_error(ctx, GL_OUT_OF_MEMORY, "stencil packing");
606       return;
607    }
608 
609    if (ctx->Pixel.IndexShift || ctx->Pixel.IndexOffset ||
610        ctx->Pixel.MapStencilFlag) {
611       /* make a copy of input */
612       memcpy(stencil, source, n * sizeof(GLubyte));
613       _mesa_apply_stencil_transfer_ops(ctx, n, stencil);
614       source = stencil;
615    }
616 
617    switch (dstType) {
618    case GL_UNSIGNED_BYTE:
619       memcpy(dest, source, n);
620       break;
621    case GL_BYTE:
622       {
623          GLbyte *dst = (GLbyte *) dest;
624          GLuint i;
625          for (i=0;i<n;i++) {
626             dst[i] = (GLbyte) (source[i] & 0x7f);
627          }
628       }
629       break;
630    case GL_UNSIGNED_SHORT:
631       {
632          GLushort *dst = (GLushort *) dest;
633          GLuint i;
634          for (i=0;i<n;i++) {
635             dst[i] = (GLushort) source[i];
636          }
637          if (dstPacking->SwapBytes) {
638             _mesa_swap2( (GLushort *) dst, n );
639          }
640       }
641       break;
642    case GL_SHORT:
643       {
644          GLshort *dst = (GLshort *) dest;
645          GLuint i;
646          for (i=0;i<n;i++) {
647             dst[i] = (GLshort) source[i];
648          }
649          if (dstPacking->SwapBytes) {
650             _mesa_swap2( (GLushort *) dst, n );
651          }
652       }
653       break;
654    case GL_UNSIGNED_INT:
655       {
656          GLuint *dst = (GLuint *) dest;
657          GLuint i;
658          for (i=0;i<n;i++) {
659             dst[i] = (GLuint) source[i];
660          }
661          if (dstPacking->SwapBytes) {
662             _mesa_swap4( (GLuint *) dst, n );
663          }
664       }
665       break;
666    case GL_INT:
667       {
668          GLint *dst = (GLint *) dest;
669          GLuint i;
670          for (i=0;i<n;i++) {
671             dst[i] = (GLint) source[i];
672          }
673          if (dstPacking->SwapBytes) {
674             _mesa_swap4( (GLuint *) dst, n );
675          }
676       }
677       break;
678    case GL_FLOAT:
679       {
680          GLfloat *dst = (GLfloat *) dest;
681          GLuint i;
682          for (i=0;i<n;i++) {
683             dst[i] = (GLfloat) source[i];
684          }
685          if (dstPacking->SwapBytes) {
686             _mesa_swap4( (GLuint *) dst, n );
687          }
688       }
689       break;
690    case GL_HALF_FLOAT_ARB:
691    case GL_HALF_FLOAT_OES:
692       {
693          GLhalfARB *dst = (GLhalfARB *) dest;
694          GLuint i;
695          for (i=0;i<n;i++) {
696             dst[i] = _mesa_float_to_half( (float) source[i] );
697          }
698          if (dstPacking->SwapBytes) {
699             _mesa_swap2( (GLushort *) dst, n );
700          }
701       }
702       break;
703    case GL_BITMAP:
704       if (dstPacking->LsbFirst) {
705          GLubyte *dst = (GLubyte *) dest;
706          GLint shift = 0;
707          GLuint i;
708          for (i = 0; i < n; i++) {
709             if (shift == 0)
710                *dst = 0;
711             *dst |= ((source[i] != 0) << shift);
712             shift++;
713             if (shift == 8) {
714                shift = 0;
715                dst++;
716             }
717          }
718       }
719       else {
720          GLubyte *dst = (GLubyte *) dest;
721          GLint shift = 7;
722          GLuint i;
723          for (i = 0; i < n; i++) {
724             if (shift == 7)
725                *dst = 0;
726             *dst |= ((source[i] != 0) << shift);
727             shift--;
728             if (shift < 0) {
729                shift = 7;
730                dst++;
731             }
732          }
733       }
734       break;
735    default:
736       unreachable("bad type in _mesa_pack_index_span");
737    }
738 
739    free(stencil);
740 }
741 
742 #define DEPTH_VALUES(GLTYPE, GLTYPE2FLOAT)                              \
743     do {                                                                \
744         GLuint i;                                                       \
745         const GLTYPE *src = (const GLTYPE *)source;                     \
746         for (i = 0; i < n; i++) {                                       \
747             GLTYPE value = src[i];                                      \
748             if (srcPacking->SwapBytes) {                                \
749                 if (sizeof(GLTYPE) == 2) {                              \
750                     SWAP2BYTE(value);                                   \
751                 } else if (sizeof(GLTYPE) == 4) {                       \
752                     SWAP4BYTE(value);                                   \
753                 }                                                       \
754             }                                                           \
755             depthValues[i] = GLTYPE2FLOAT(value);                       \
756         }                                                               \
757     } while (0)
758 
759 
760 /**
761  * Unpack a row of depth/z values from memory, returning GLushort, GLuint
762  * or GLfloat values.
763  * The glPixelTransfer (scale/bias) params will be applied.
764  *
765  * \param dstType  one of GL_UNSIGNED_SHORT, GL_UNSIGNED_INT, GL_FLOAT
766  * \param depthMax  max value for returned GLushort or GLuint values
767  *                  (ignored for GLfloat).
768  */
769 void
_mesa_unpack_depth_span(struct gl_context * ctx,GLuint n,GLenum dstType,GLvoid * dest,GLuint depthMax,GLenum srcType,const GLvoid * source,const struct gl_pixelstore_attrib * srcPacking)770 _mesa_unpack_depth_span( struct gl_context *ctx, GLuint n,
771                          GLenum dstType, GLvoid *dest, GLuint depthMax,
772                          GLenum srcType, const GLvoid *source,
773                          const struct gl_pixelstore_attrib *srcPacking )
774 {
775    GLfloat *depthTemp = NULL, *depthValues;
776    GLboolean needClamp = GL_FALSE;
777 
778    /* Look for special cases first.
779     * Not only are these faster, they're less prone to numeric conversion
780     * problems.  Otherwise, converting from an int type to a float then
781     * back to an int type can introduce errors that will show up as
782     * artifacts in things like depth peeling which uses glCopyTexImage.
783     */
784    if (ctx->Pixel.DepthScale == 1.0F && ctx->Pixel.DepthBias == 0.0F) {
785       if (srcType == GL_UNSIGNED_INT && dstType == GL_UNSIGNED_SHORT) {
786          const GLuint *src = (const GLuint *) source;
787          GLushort *dst = (GLushort *) dest;
788          GLuint i;
789          for (i = 0; i < n; i++) {
790             dst[i] = src[i] >> 16;
791          }
792          return;
793       }
794       if (srcType == GL_UNSIGNED_SHORT
795           && dstType == GL_UNSIGNED_INT
796           && depthMax == 0xffffffff) {
797          const GLushort *src = (const GLushort *) source;
798          GLuint *dst = (GLuint *) dest;
799          GLuint i;
800          for (i = 0; i < n; i++) {
801             dst[i] = src[i] | (src[i] << 16);
802          }
803          return;
804       }
805       if (srcType == GL_UNSIGNED_INT_24_8
806           && dstType == GL_UNSIGNED_INT
807           && depthMax == 0xffffff) {
808          const GLuint *src = (const GLuint *) source;
809          GLuint *dst = (GLuint *) dest;
810          GLuint i;
811          for (i = 0; i < n; i++) {
812             dst[i] = src[i] >> 8;
813          }
814          return;
815       }
816       /* XXX may want to add additional cases here someday */
817    }
818 
819    /* general case path follows */
820 
821    if (dstType == GL_FLOAT) {
822       depthValues = (GLfloat *) dest;
823    }
824    else {
825       depthTemp = malloc(n * sizeof(GLfloat));
826       if (!depthTemp) {
827          _mesa_error(ctx, GL_OUT_OF_MEMORY, "pixel unpacking");
828          return;
829       }
830 
831       depthValues = depthTemp;
832    }
833 
834    /* Convert incoming values to GLfloat.  Some conversions will require
835     * clamping, below.
836     */
837    switch (srcType) {
838       case GL_BYTE:
839          DEPTH_VALUES(GLbyte, BYTE_TO_FLOATZ);
840          needClamp = GL_TRUE;
841          break;
842       case GL_UNSIGNED_BYTE:
843          DEPTH_VALUES(GLubyte, UBYTE_TO_FLOAT);
844          break;
845       case GL_SHORT:
846          DEPTH_VALUES(GLshort, SHORT_TO_FLOATZ);
847          needClamp = GL_TRUE;
848          break;
849       case GL_UNSIGNED_SHORT:
850          DEPTH_VALUES(GLushort, USHORT_TO_FLOAT);
851          break;
852       case GL_INT:
853          DEPTH_VALUES(GLint, INT_TO_FLOAT);
854          needClamp = GL_TRUE;
855          break;
856       case GL_UNSIGNED_INT:
857          DEPTH_VALUES(GLuint, UINT_TO_FLOAT);
858          break;
859       case GL_UNSIGNED_INT_24_8_EXT: /* GL_EXT_packed_depth_stencil */
860          if (dstType == GL_UNSIGNED_INT_24_8_EXT &&
861              depthMax == 0xffffff &&
862              ctx->Pixel.DepthScale == 1.0F &&
863              ctx->Pixel.DepthBias == 0.0F) {
864             const GLuint *src = (const GLuint *) source;
865             GLuint *zValues = (GLuint *) dest;
866             GLuint i;
867             for (i = 0; i < n; i++) {
868                 GLuint value = src[i];
869                 if (srcPacking->SwapBytes) {
870                     SWAP4BYTE(value);
871                 }
872                 zValues[i] = value & 0xffffff00;
873             }
874             free(depthTemp);
875             return;
876          }
877          else {
878             const GLuint *src = (const GLuint *) source;
879             const GLfloat scale = 1.0f / 0xffffff;
880             GLuint i;
881             for (i = 0; i < n; i++) {
882                 GLuint value = src[i];
883                 if (srcPacking->SwapBytes) {
884                     SWAP4BYTE(value);
885                 }
886                 depthValues[i] = (value >> 8) * scale;
887             }
888          }
889          break;
890       case GL_FLOAT_32_UNSIGNED_INT_24_8_REV:
891          {
892             GLuint i;
893             const GLfloat *src = (const GLfloat *)source;
894             for (i = 0; i < n; i++) {
895                GLfloat value = src[i * 2];
896                if (srcPacking->SwapBytes) {
897                   SWAP4BYTE(value);
898                }
899                depthValues[i] = value;
900             }
901             needClamp = GL_TRUE;
902          }
903          break;
904       case GL_FLOAT:
905          DEPTH_VALUES(GLfloat, 1*);
906          needClamp = GL_TRUE;
907          break;
908       case GL_HALF_FLOAT_ARB:
909       case GL_HALF_FLOAT_OES:
910          {
911             GLuint i;
912             const GLhalfARB *src = (const GLhalfARB *) source;
913             for (i = 0; i < n; i++) {
914                GLhalfARB value = src[i];
915                if (srcPacking->SwapBytes) {
916                   SWAP2BYTE(value);
917                }
918                depthValues[i] = _mesa_half_to_float(value);
919             }
920             needClamp = GL_TRUE;
921          }
922          break;
923       default:
924          _mesa_problem(NULL, "bad type in _mesa_unpack_depth_span()");
925          free(depthTemp);
926          return;
927    }
928 
929    /* apply depth scale and bias */
930    {
931       const GLfloat scale = ctx->Pixel.DepthScale;
932       const GLfloat bias = ctx->Pixel.DepthBias;
933       if (scale != 1.0F || bias != 0.0F) {
934          GLuint i;
935          for (i = 0; i < n; i++) {
936             depthValues[i] = depthValues[i] * scale + bias;
937          }
938          needClamp = GL_TRUE;
939       }
940    }
941 
942    /* clamp to [0, 1] */
943    if (needClamp) {
944       GLuint i;
945       for (i = 0; i < n; i++) {
946          depthValues[i] = CLAMP(depthValues[i], 0.0F, 1.0F);
947       }
948    }
949 
950    /*
951     * Convert values to dstType
952     */
953    if (dstType == GL_UNSIGNED_INT) {
954       GLuint *zValues = (GLuint *) dest;
955       GLuint i;
956       if (depthMax <= 0xffffff) {
957          /* no overflow worries */
958          for (i = 0; i < n; i++) {
959             zValues[i] = (GLuint) (depthValues[i] * (GLfloat) depthMax);
960          }
961       }
962       else {
963          /* need to use double precision to prevent overflow problems */
964          for (i = 0; i < n; i++) {
965             GLdouble z = depthValues[i] * (GLdouble) depthMax;
966             if (z >= (GLdouble) 0xffffffff)
967                zValues[i] = 0xffffffff;
968             else
969                zValues[i] = (GLuint) z;
970          }
971       }
972    }
973    else if (dstType == GL_UNSIGNED_SHORT) {
974       GLushort *zValues = (GLushort *) dest;
975       GLuint i;
976       assert(depthMax <= 0xffff);
977       for (i = 0; i < n; i++) {
978          zValues[i] = (GLushort) (depthValues[i] * (GLfloat) depthMax);
979       }
980    }
981    else if (dstType == GL_FLOAT) {
982       /* Nothing to do. depthValues is pointing to dest. */
983    }
984    else if (dstType == GL_FLOAT_32_UNSIGNED_INT_24_8_REV) {
985       GLfloat *zValues = (GLfloat*) dest;
986       GLuint i;
987       for (i = 0; i < n; i++) {
988          zValues[i*2] = depthValues[i];
989       }
990    }
991    else {
992       assert(0);
993    }
994 
995    free(depthTemp);
996 }
997 
998 
999 /*
1000  * Pack an array of depth values.  The values are floats in [0,1].
1001  */
1002 void
_mesa_pack_depth_span(struct gl_context * ctx,GLuint n,GLvoid * dest,GLenum dstType,const GLfloat * depthSpan,const struct gl_pixelstore_attrib * dstPacking)1003 _mesa_pack_depth_span( struct gl_context *ctx, GLuint n, GLvoid *dest,
1004                        GLenum dstType, const GLfloat *depthSpan,
1005                        const struct gl_pixelstore_attrib *dstPacking )
1006 {
1007    GLfloat *depthCopy = malloc(n * sizeof(GLfloat));
1008    if (!depthCopy) {
1009       _mesa_error(ctx, GL_OUT_OF_MEMORY, "pixel packing");
1010       return;
1011    }
1012 
1013    if (ctx->Pixel.DepthScale != 1.0F || ctx->Pixel.DepthBias != 0.0F) {
1014       memcpy(depthCopy, depthSpan, n * sizeof(GLfloat));
1015       _mesa_scale_and_bias_depth(ctx, n, depthCopy);
1016       depthSpan = depthCopy;
1017    }
1018 
1019    switch (dstType) {
1020    case GL_UNSIGNED_BYTE:
1021       {
1022          GLubyte *dst = (GLubyte *) dest;
1023          GLuint i;
1024          for (i = 0; i < n; i++) {
1025             dst[i] = FLOAT_TO_UBYTE( depthSpan[i] );
1026          }
1027       }
1028       break;
1029    case GL_BYTE:
1030       {
1031          GLbyte *dst = (GLbyte *) dest;
1032          GLuint i;
1033          for (i = 0; i < n; i++) {
1034             dst[i] = FLOAT_TO_BYTE( depthSpan[i] );
1035          }
1036       }
1037       break;
1038    case GL_UNSIGNED_SHORT:
1039       {
1040          GLushort *dst = (GLushort *) dest;
1041          GLuint i;
1042          for (i = 0; i < n; i++) {
1043             CLAMPED_FLOAT_TO_USHORT(dst[i], depthSpan[i]);
1044          }
1045          if (dstPacking->SwapBytes) {
1046             _mesa_swap2( (GLushort *) dst, n );
1047          }
1048       }
1049       break;
1050    case GL_SHORT:
1051       {
1052          GLshort *dst = (GLshort *) dest;
1053          GLuint i;
1054          for (i = 0; i < n; i++) {
1055             dst[i] = FLOAT_TO_SHORT( depthSpan[i] );
1056          }
1057          if (dstPacking->SwapBytes) {
1058             _mesa_swap2( (GLushort *) dst, n );
1059          }
1060       }
1061       break;
1062    case GL_UNSIGNED_INT_24_8:
1063       {
1064          const GLdouble scale = (GLdouble) 0xffffff;
1065          GLuint *dst = (GLuint *) dest;
1066          GLuint i;
1067          for (i = 0; i < n; i++) {
1068             GLuint z = (GLuint) (depthSpan[i] * scale);
1069             assert(z <= 0xffffff);
1070             dst[i] = (z << 8);
1071          }
1072          if (dstPacking->SwapBytes) {
1073             _mesa_swap4( (GLuint *) dst, n );
1074          }
1075          break;
1076       }
1077    case GL_UNSIGNED_INT:
1078       {
1079          GLuint *dst = (GLuint *) dest;
1080          GLuint i;
1081          for (i = 0; i < n; i++) {
1082             dst[i] = FLOAT_TO_UINT( depthSpan[i] );
1083          }
1084          if (dstPacking->SwapBytes) {
1085             _mesa_swap4( (GLuint *) dst, n );
1086          }
1087       }
1088       break;
1089    case GL_INT:
1090       {
1091          GLint *dst = (GLint *) dest;
1092          GLuint i;
1093          for (i = 0; i < n; i++) {
1094             dst[i] = FLOAT_TO_INT( depthSpan[i] );
1095          }
1096          if (dstPacking->SwapBytes) {
1097             _mesa_swap4( (GLuint *) dst, n );
1098          }
1099       }
1100       break;
1101    case GL_FLOAT:
1102       {
1103          GLfloat *dst = (GLfloat *) dest;
1104          GLuint i;
1105          for (i = 0; i < n; i++) {
1106             dst[i] = depthSpan[i];
1107          }
1108          if (dstPacking->SwapBytes) {
1109             _mesa_swap4( (GLuint *) dst, n );
1110          }
1111       }
1112       break;
1113    case GL_HALF_FLOAT_ARB:
1114    case GL_HALF_FLOAT_OES:
1115       {
1116          GLhalfARB *dst = (GLhalfARB *) dest;
1117          GLuint i;
1118          for (i = 0; i < n; i++) {
1119             dst[i] = _mesa_float_to_half(depthSpan[i]);
1120          }
1121          if (dstPacking->SwapBytes) {
1122             _mesa_swap2( (GLushort *) dst, n );
1123          }
1124       }
1125       break;
1126    default:
1127       unreachable("bad type in _mesa_pack_depth_span()");
1128    }
1129 
1130    free(depthCopy);
1131 }
1132 
1133 
1134 
1135 /**
1136  * Pack depth and stencil values as GL_DEPTH_STENCIL (GL_UNSIGNED_INT_24_8 etc)
1137  */
1138 void
_mesa_pack_depth_stencil_span(struct gl_context * ctx,GLuint n,GLenum dstType,GLuint * dest,const GLfloat * depthVals,const GLubyte * stencilVals,const struct gl_pixelstore_attrib * dstPacking)1139 _mesa_pack_depth_stencil_span(struct gl_context *ctx,GLuint n,
1140                               GLenum dstType, GLuint *dest,
1141                               const GLfloat *depthVals,
1142                               const GLubyte *stencilVals,
1143                               const struct gl_pixelstore_attrib *dstPacking)
1144 {
1145    GLfloat *depthCopy = malloc(n * sizeof(GLfloat));
1146    GLubyte *stencilCopy = malloc(n * sizeof(GLubyte));
1147    GLuint i;
1148 
1149    if (!depthCopy || !stencilCopy) {
1150       _mesa_error(ctx, GL_OUT_OF_MEMORY, "pixel packing");
1151       free(depthCopy);
1152       free(stencilCopy);
1153       return;
1154    }
1155 
1156    if (ctx->Pixel.DepthScale != 1.0F || ctx->Pixel.DepthBias != 0.0F) {
1157       memcpy(depthCopy, depthVals, n * sizeof(GLfloat));
1158       _mesa_scale_and_bias_depth(ctx, n, depthCopy);
1159       depthVals = depthCopy;
1160    }
1161 
1162    if (ctx->Pixel.IndexShift ||
1163        ctx->Pixel.IndexOffset ||
1164        ctx->Pixel.MapStencilFlag) {
1165       memcpy(stencilCopy, stencilVals, n * sizeof(GLubyte));
1166       _mesa_apply_stencil_transfer_ops(ctx, n, stencilCopy);
1167       stencilVals = stencilCopy;
1168    }
1169 
1170    switch (dstType) {
1171    case GL_UNSIGNED_INT_24_8:
1172       for (i = 0; i < n; i++) {
1173          GLuint z = (GLuint) (depthVals[i] * 0xffffff);
1174          dest[i] = (z << 8) | (stencilVals[i] & 0xff);
1175       }
1176       break;
1177    case GL_FLOAT_32_UNSIGNED_INT_24_8_REV:
1178       for (i = 0; i < n; i++) {
1179          ((GLfloat*)dest)[i*2] = depthVals[i];
1180          dest[i*2+1] = stencilVals[i] & 0xff;
1181       }
1182       break;
1183    }
1184 
1185    if (dstPacking->SwapBytes) {
1186       _mesa_swap4(dest, n);
1187    }
1188 
1189    free(depthCopy);
1190    free(stencilCopy);
1191 }
1192 
1193 
1194 
1195 /**
1196  * Unpack image data.  Apply byte swapping, byte flipping (bitmap).
1197  * Return all image data in a contiguous block.  This is used when we
1198  * compile glDrawPixels, glTexImage, etc into a display list.  We
1199  * need a copy of the data in a standard format.
1200  */
1201 void *
_mesa_unpack_image(GLuint dimensions,GLsizei width,GLsizei height,GLsizei depth,GLenum format,GLenum type,const GLvoid * pixels,const struct gl_pixelstore_attrib * unpack)1202 _mesa_unpack_image( GLuint dimensions,
1203                     GLsizei width, GLsizei height, GLsizei depth,
1204                     GLenum format, GLenum type, const GLvoid *pixels,
1205                     const struct gl_pixelstore_attrib *unpack )
1206 {
1207    GLint bytesPerRow, compsPerRow;
1208    GLboolean flipBytes, swap2, swap4;
1209 
1210    if (!pixels)
1211       return NULL;  /* not necessarily an error */
1212 
1213    if (width <= 0 || height <= 0 || depth <= 0)
1214       return NULL;  /* generate error later */
1215 
1216    if (type == GL_BITMAP) {
1217       bytesPerRow = (width + 7) >> 3;
1218       flipBytes = unpack->LsbFirst;
1219       swap2 = swap4 = GL_FALSE;
1220       compsPerRow = 0;
1221    }
1222    else {
1223       const GLint bytesPerPixel = _mesa_bytes_per_pixel(format, type);
1224       GLint components = _mesa_components_in_format(format);
1225       GLint bytesPerComp;
1226 
1227       if (_mesa_type_is_packed(type))
1228           components = 1;
1229 
1230       if (bytesPerPixel <= 0 || components <= 0)
1231          return NULL;   /* bad format or type.  generate error later */
1232       bytesPerRow = bytesPerPixel * width;
1233       bytesPerComp = bytesPerPixel / components;
1234       flipBytes = GL_FALSE;
1235       swap2 = (bytesPerComp == 2) && unpack->SwapBytes;
1236       swap4 = (bytesPerComp == 4) && unpack->SwapBytes;
1237       compsPerRow = components * width;
1238       assert(compsPerRow >= width);
1239    }
1240 
1241    {
1242       GLubyte *destBuffer
1243          = malloc(bytesPerRow * height * depth);
1244       GLubyte *dst;
1245       GLint img, row;
1246       if (!destBuffer)
1247          return NULL;   /* generate GL_OUT_OF_MEMORY later */
1248 
1249       dst = destBuffer;
1250       for (img = 0; img < depth; img++) {
1251          for (row = 0; row < height; row++) {
1252             const GLvoid *src = _mesa_image_address(dimensions, unpack, pixels,
1253                                width, height, format, type, img, row, 0);
1254 
1255             if ((type == GL_BITMAP) && (unpack->SkipPixels & 0x7)) {
1256                GLint i;
1257                flipBytes = GL_FALSE;
1258                if (unpack->LsbFirst) {
1259                   GLubyte srcMask = 1 << (unpack->SkipPixels & 0x7);
1260                   GLubyte dstMask = 128;
1261                   const GLubyte *s = src;
1262                   GLubyte *d = dst;
1263                   *d = 0;
1264                   for (i = 0; i < width; i++) {
1265                      if (*s & srcMask) {
1266                         *d |= dstMask;
1267                      }
1268                      if (srcMask == 128) {
1269                         srcMask = 1;
1270                         s++;
1271                      }
1272                      else {
1273                         srcMask = srcMask << 1;
1274                      }
1275                      if (dstMask == 1) {
1276                         dstMask = 128;
1277                         d++;
1278                         *d = 0;
1279                      }
1280                      else {
1281                         dstMask = dstMask >> 1;
1282                      }
1283                   }
1284                }
1285                else {
1286                   GLubyte srcMask = 128 >> (unpack->SkipPixels & 0x7);
1287                   GLubyte dstMask = 128;
1288                   const GLubyte *s = src;
1289                   GLubyte *d = dst;
1290                   *d = 0;
1291                   for (i = 0; i < width; i++) {
1292                      if (*s & srcMask) {
1293                         *d |= dstMask;
1294                      }
1295                      if (srcMask == 1) {
1296                         srcMask = 128;
1297                         s++;
1298                      }
1299                      else {
1300                         srcMask = srcMask >> 1;
1301                      }
1302                      if (dstMask == 1) {
1303                         dstMask = 128;
1304                         d++;
1305                         *d = 0;
1306                      }
1307                      else {
1308                         dstMask = dstMask >> 1;
1309                      }
1310                   }
1311                }
1312             }
1313             else {
1314                memcpy(dst, src, bytesPerRow);
1315             }
1316 
1317             /* byte flipping/swapping */
1318             if (flipBytes) {
1319                flip_bytes((GLubyte *) dst, bytesPerRow);
1320             }
1321             else if (swap2) {
1322                _mesa_swap2((GLushort*) dst, compsPerRow);
1323             }
1324             else if (swap4) {
1325                _mesa_swap4((GLuint*) dst, compsPerRow);
1326             }
1327             dst += bytesPerRow;
1328          }
1329       }
1330       return destBuffer;
1331    }
1332 }
1333 
1334 void
_mesa_pack_luminance_from_rgba_float(GLuint n,GLfloat rgba[][4],GLvoid * dstAddr,GLenum dst_format,GLbitfield transferOps)1335 _mesa_pack_luminance_from_rgba_float(GLuint n, GLfloat rgba[][4],
1336                                      GLvoid *dstAddr, GLenum dst_format,
1337                                      GLbitfield transferOps)
1338 {
1339    int i;
1340    GLfloat *dst = (GLfloat *) dstAddr;
1341 
1342    switch (dst_format) {
1343    case GL_LUMINANCE:
1344       if (transferOps & IMAGE_CLAMP_BIT) {
1345          for (i = 0; i < n; i++) {
1346             GLfloat sum = rgba[i][RCOMP] + rgba[i][GCOMP] + rgba[i][BCOMP];
1347             dst[i] = CLAMP(sum, 0.0F, 1.0F);
1348          }
1349       } else {
1350          for (i = 0; i < n; i++) {
1351             dst[i] = rgba[i][RCOMP] + rgba[i][GCOMP] + rgba[i][BCOMP];
1352          }
1353       }
1354       return;
1355    case GL_LUMINANCE_ALPHA:
1356       if (transferOps & IMAGE_CLAMP_BIT) {
1357          for (i = 0; i < n; i++) {
1358             GLfloat sum = rgba[i][RCOMP] + rgba[i][GCOMP] + rgba[i][BCOMP];
1359             dst[2*i] = CLAMP(sum, 0.0F, 1.0F);
1360             dst[2*i+1] = rgba[i][ACOMP];
1361          }
1362       } else {
1363          for (i = 0; i < n; i++) {
1364             dst[2*i] = rgba[i][RCOMP] + rgba[i][GCOMP] + rgba[i][BCOMP];
1365             dst[2*i+1] = rgba[i][ACOMP];
1366          }
1367       }
1368       return;
1369    default:
1370       assert(!"Unsupported format");
1371    }
1372 }
1373 
1374 static int32_t
clamp_sint64_to_sint32(int64_t src)1375 clamp_sint64_to_sint32(int64_t src)
1376 {
1377    return CLAMP(src, INT32_MIN, INT32_MAX);
1378 }
1379 
1380 static int32_t
clamp_sint64_to_uint32(int64_t src)1381 clamp_sint64_to_uint32(int64_t src)
1382 {
1383    return CLAMP(src, 0, UINT32_MAX);
1384 }
1385 
1386 static int32_t
clamp_uint64_to_uint32(uint64_t src)1387 clamp_uint64_to_uint32(uint64_t src)
1388 {
1389    return MIN2(src, UINT32_MAX);
1390 }
1391 
1392 static int32_t
clamp_uint64_to_sint32(uint64_t src)1393 clamp_uint64_to_sint32(uint64_t src)
1394 {
1395    return MIN2(src, INT32_MAX);
1396 }
1397 
1398 static int32_t
convert_integer_luminance64(int64_t src64,int bits,bool dst_is_signed,bool src_is_signed)1399 convert_integer_luminance64(int64_t src64, int bits,
1400                             bool dst_is_signed, bool src_is_signed)
1401 {
1402    int32_t src32;
1403 
1404    /* Clamp Luminance value from 64-bit to 32-bit. Consider if we need
1405     * any signed<->unsigned conversion too.
1406     */
1407    if (src_is_signed && dst_is_signed)
1408       src32 = clamp_sint64_to_sint32(src64);
1409    else if (src_is_signed && !dst_is_signed)
1410       src32 = clamp_sint64_to_uint32(src64);
1411    else if (!src_is_signed && dst_is_signed)
1412       src32 = clamp_uint64_to_sint32(src64);
1413    else
1414       src32 = clamp_uint64_to_uint32(src64);
1415 
1416    /* If the dst type is < 32-bit, we need an extra clamp */
1417    if (bits == 32) {
1418       return src32;
1419    } else {
1420       if (dst_is_signed)
1421          return _mesa_signed_to_signed(src32, bits);
1422       else
1423          return _mesa_unsigned_to_unsigned(src32, bits);
1424    }
1425 }
1426 
1427 static int32_t
convert_integer(int32_t src,int bits,bool dst_is_signed,bool src_is_signed)1428 convert_integer(int32_t src, int bits, bool dst_is_signed, bool src_is_signed)
1429 {
1430    if (src_is_signed && dst_is_signed)
1431       return _mesa_signed_to_signed(src, bits);
1432    else if (src_is_signed && !dst_is_signed)
1433       return _mesa_signed_to_unsigned(src, bits);
1434    else if (!src_is_signed && dst_is_signed)
1435       return _mesa_unsigned_to_signed(src, bits);
1436    else
1437       return _mesa_unsigned_to_unsigned(src, bits);
1438 }
1439 
1440 void
_mesa_pack_luminance_from_rgba_integer(GLuint n,GLuint rgba[][4],bool rgba_is_signed,GLvoid * dstAddr,GLenum dst_format,GLenum dst_type)1441 _mesa_pack_luminance_from_rgba_integer(GLuint n,
1442                                        GLuint rgba[][4], bool rgba_is_signed,
1443                                        GLvoid *dstAddr,
1444                                        GLenum dst_format,
1445                                        GLenum dst_type)
1446 {
1447    int i;
1448    int64_t lum64;
1449    int32_t lum32, alpha;
1450    bool dst_is_signed;
1451    int dst_bits;
1452 
1453    assert(dst_format == GL_LUMINANCE_INTEGER_EXT ||
1454           dst_format == GL_LUMINANCE_ALPHA_INTEGER_EXT);
1455 
1456    /* We first compute luminance values as a 64-bit addition of the
1457     * 32-bit R,G,B components, then we clamp the result to the dst type size.
1458     *
1459     * Notice that this operation involves casting the 32-bit R,G,B components
1460     * to 64-bit before the addition. Since rgba is defined as a GLuint array
1461     * we need to be careful when rgba packs signed data and make sure
1462     * that we cast to a 32-bit signed integer values before casting them to
1463     * 64-bit signed integers.
1464     */
1465    dst_is_signed = (dst_type == GL_BYTE || dst_type == GL_SHORT ||
1466                     dst_type == GL_INT);
1467 
1468    dst_bits = _mesa_sizeof_type(dst_type) * 8;
1469    assert(dst_bits > 0);
1470 
1471    switch (dst_format) {
1472    case GL_LUMINANCE_INTEGER_EXT:
1473       for (i = 0; i < n; i++) {
1474          if (!rgba_is_signed) {
1475             lum64 = (uint64_t) rgba[i][RCOMP] +
1476                     (uint64_t) rgba[i][GCOMP] +
1477                     (uint64_t) rgba[i][BCOMP];
1478          } else {
1479             lum64 = (int64_t) ((int32_t) rgba[i][RCOMP]) +
1480                     (int64_t) ((int32_t) rgba[i][GCOMP]) +
1481                     (int64_t) ((int32_t) rgba[i][BCOMP]);
1482          }
1483          lum32 = convert_integer_luminance64(lum64, dst_bits,
1484                                              dst_is_signed, rgba_is_signed);
1485          switch (dst_type) {
1486          case GL_BYTE:
1487          case GL_UNSIGNED_BYTE: {
1488             GLbyte *dst = (GLbyte *) dstAddr;
1489             dst[i] = lum32;
1490             break;
1491          }
1492          case GL_SHORT:
1493          case GL_UNSIGNED_SHORT: {
1494             GLshort *dst = (GLshort *) dstAddr;
1495             dst[i] = lum32;
1496             break;
1497          }
1498          case GL_INT:
1499          case GL_UNSIGNED_INT: {
1500             GLint *dst = (GLint *) dstAddr;
1501             dst[i] = lum32;
1502             break;
1503          }
1504          }
1505       }
1506       return;
1507    case GL_LUMINANCE_ALPHA_INTEGER_EXT:
1508       for (i = 0; i < n; i++) {
1509          if (!rgba_is_signed) {
1510             lum64 = (uint64_t) rgba[i][RCOMP] +
1511                     (uint64_t) rgba[i][GCOMP] +
1512                     (uint64_t) rgba[i][BCOMP];
1513          } else {
1514             lum64 = (int64_t) ((int32_t) rgba[i][RCOMP]) +
1515                     (int64_t) ((int32_t) rgba[i][GCOMP]) +
1516                     (int64_t) ((int32_t) rgba[i][BCOMP]);
1517          }
1518          lum32 = convert_integer_luminance64(lum64, dst_bits,
1519                                              dst_is_signed, rgba_is_signed);
1520          alpha = convert_integer(rgba[i][ACOMP], dst_bits,
1521                                  dst_is_signed, rgba_is_signed);
1522          switch (dst_type) {
1523          case GL_BYTE:
1524          case GL_UNSIGNED_BYTE: {
1525             GLbyte *dst = (GLbyte *) dstAddr;
1526             dst[2*i] = lum32;
1527             dst[2*i+1] = alpha;
1528             break;
1529          }
1530          case GL_SHORT:
1531          case GL_UNSIGNED_SHORT: {
1532             GLshort *dst = (GLshort *) dstAddr;
1533             dst[i] = lum32;
1534             dst[2*i+1] = alpha;
1535             break;
1536          }
1537          case GL_INT:
1538          case GL_UNSIGNED_INT: {
1539             GLint *dst = (GLint *) dstAddr;
1540             dst[i] = lum32;
1541             dst[2*i+1] = alpha;
1542             break;
1543          }
1544          }
1545       }
1546       return;
1547    }
1548 }
1549 
1550 GLfloat *
_mesa_unpack_color_index_to_rgba_float(struct gl_context * ctx,GLuint dims,const void * src,GLenum srcFormat,GLenum srcType,int srcWidth,int srcHeight,int srcDepth,const struct gl_pixelstore_attrib * srcPacking,GLbitfield transferOps)1551 _mesa_unpack_color_index_to_rgba_float(struct gl_context *ctx, GLuint dims,
1552                                        const void *src, GLenum srcFormat, GLenum srcType,
1553                                        int srcWidth, int srcHeight, int srcDepth,
1554                                        const struct gl_pixelstore_attrib *srcPacking,
1555                                        GLbitfield transferOps)
1556 {
1557    int count, img;
1558    GLuint *indexes;
1559    GLfloat *rgba, *dstPtr;
1560 
1561    count = srcWidth * srcHeight;
1562    indexes = malloc(count * sizeof(GLuint));
1563    if (!indexes) {
1564       _mesa_error(ctx, GL_OUT_OF_MEMORY, "pixel unpacking");
1565       return NULL;
1566    }
1567 
1568    rgba = malloc(4 * count * srcDepth * sizeof(GLfloat));
1569    if (!rgba) {
1570       free(indexes);
1571       _mesa_error(ctx, GL_OUT_OF_MEMORY, "pixel unpacking");
1572       return NULL;
1573    }
1574 
1575    /* Convert indexes to RGBA float */
1576    dstPtr = rgba;
1577    for (img = 0; img < srcDepth; img++) {
1578       const GLubyte *srcPtr =
1579          (const GLubyte *) _mesa_image_address(dims, srcPacking, src,
1580                                                srcWidth, srcHeight,
1581                                                srcFormat, srcType,
1582                                                img, 0, 0);
1583 
1584       extract_uint_indexes(count, indexes, srcFormat, srcType, srcPtr, srcPacking);
1585 
1586       if (transferOps & IMAGE_SHIFT_OFFSET_BIT)
1587          _mesa_shift_and_offset_ci(ctx, count, indexes);
1588 
1589       _mesa_map_ci_to_rgba(ctx, count, indexes, (float (*)[4])dstPtr);
1590 
1591       /* Don't do RGBA scale/bias or RGBA->RGBA mapping if starting
1592        * with color indexes.
1593        */
1594       transferOps &= ~(IMAGE_SCALE_BIAS_BIT | IMAGE_MAP_COLOR_BIT);
1595       _mesa_apply_rgba_transfer_ops(ctx, transferOps, count, (float (*)[4])dstPtr);
1596 
1597       dstPtr += srcHeight * srcWidth * 4;
1598    }
1599 
1600    free(indexes);
1601 
1602    return rgba;
1603 }
1604 
1605 GLubyte *
_mesa_unpack_color_index_to_rgba_ubyte(struct gl_context * ctx,GLuint dims,const void * src,GLenum srcFormat,GLenum srcType,int srcWidth,int srcHeight,int srcDepth,const struct gl_pixelstore_attrib * srcPacking,GLbitfield transferOps)1606 _mesa_unpack_color_index_to_rgba_ubyte(struct gl_context *ctx, GLuint dims,
1607                                        const void *src, GLenum srcFormat, GLenum srcType,
1608                                        int srcWidth, int srcHeight, int srcDepth,
1609                                        const struct gl_pixelstore_attrib *srcPacking,
1610                                        GLbitfield transferOps)
1611 {
1612    GLfloat *rgba;
1613    GLubyte *dst;
1614    int count, i;
1615 
1616    transferOps |= IMAGE_CLAMP_BIT;
1617    rgba = _mesa_unpack_color_index_to_rgba_float(ctx, dims,
1618                                                  src, srcFormat, srcType,
1619                                                  srcWidth, srcHeight, srcDepth,
1620                                                  srcPacking, transferOps);
1621 
1622    count = srcWidth * srcHeight * srcDepth;
1623    dst = malloc(count * 4 * sizeof(GLubyte));
1624    for (i = 0; i < count; i++) {
1625       CLAMPED_FLOAT_TO_UBYTE(dst[i * 4 + 0], rgba[i * 4 + 0]);
1626       CLAMPED_FLOAT_TO_UBYTE(dst[i * 4 + 1], rgba[i * 4 + 1]);
1627       CLAMPED_FLOAT_TO_UBYTE(dst[i * 4 + 2], rgba[i * 4 + 2]);
1628       CLAMPED_FLOAT_TO_UBYTE(dst[i * 4 + 3], rgba[i * 4 + 3]);
1629    }
1630 
1631    free(rgba);
1632 
1633    return dst;
1634 }
1635 
1636 void
_mesa_unpack_ubyte_rgba_row(mesa_format format,uint32_t n,const void * src,uint8_t dst[][4])1637 _mesa_unpack_ubyte_rgba_row(mesa_format format, uint32_t n,
1638                             const void *src, uint8_t dst[][4])
1639 {
1640    const struct util_format_unpack_description *unpack =
1641       util_format_unpack_description((enum pipe_format)format);
1642 
1643    if (unpack->unpack_rgba_8unorm) {
1644       unpack->unpack_rgba_8unorm((uint8_t *)dst, src, n);
1645    } else {
1646       /* get float values, convert to ubyte */
1647       {
1648          float *tmp = malloc(n * 4 * sizeof(float));
1649          if (tmp) {
1650             uint32_t i;
1651             _mesa_unpack_rgba_row(format, n, src, (float (*)[4]) tmp);
1652             for (i = 0; i < n; i++) {
1653                dst[i][0] = _mesa_float_to_unorm(tmp[i*4+0], 8);
1654                dst[i][1] = _mesa_float_to_unorm(tmp[i*4+1], 8);
1655                dst[i][2] = _mesa_float_to_unorm(tmp[i*4+2], 8);
1656                dst[i][3] = _mesa_float_to_unorm(tmp[i*4+3], 8);
1657             }
1658             free(tmp);
1659          }
1660       }
1661    }
1662 }
1663 
1664 /** Helper struct for MESA_FORMAT_Z32_FLOAT_S8X24_UINT */
1665 struct z32f_x24s8
1666 {
1667    float z;
1668    uint32_t x24s8;
1669 };
1670 
1671 
1672 static void
unpack_uint_24_8_depth_stencil_Z24_UNORM_S8_UINT(const uint32_t * src,uint32_t * dst,uint32_t n)1673 unpack_uint_24_8_depth_stencil_Z24_UNORM_S8_UINT(const uint32_t *src, uint32_t *dst, uint32_t n)
1674 {
1675    uint32_t i;
1676 
1677    for (i = 0; i < n; i++) {
1678       uint32_t val = src[i];
1679       dst[i] = val >> 24 | val << 8;
1680    }
1681 }
1682 
1683 static void
unpack_uint_24_8_depth_stencil_Z32_S8X24(const uint32_t * src,uint32_t * dst,uint32_t n)1684 unpack_uint_24_8_depth_stencil_Z32_S8X24(const uint32_t *src,
1685                                          uint32_t *dst, uint32_t n)
1686 {
1687    uint32_t i;
1688 
1689    for (i = 0; i < n; i++) {
1690       /* 8 bytes per pixel (float + uint32) */
1691       float zf = ((float *) src)[i * 2 + 0];
1692       uint32_t z24 = (uint32_t) (zf * (float) 0xffffff);
1693       uint32_t s = src[i * 2 + 1] & 0xff;
1694       dst[i] = (z24 << 8) | s;
1695    }
1696 }
1697 
1698 static void
unpack_uint_24_8_depth_stencil_S8_UINT_Z24_UNORM(const uint32_t * src,uint32_t * dst,uint32_t n)1699 unpack_uint_24_8_depth_stencil_S8_UINT_Z24_UNORM(const uint32_t *src, uint32_t *dst, uint32_t n)
1700 {
1701    memcpy(dst, src, n * 4);
1702 }
1703 
1704 /**
1705  * Unpack depth/stencil returning as GL_UNSIGNED_INT_24_8.
1706  * \param format  the source data format
1707  */
1708 void
_mesa_unpack_uint_24_8_depth_stencil_row(mesa_format format,uint32_t n,const void * src,uint32_t * dst)1709 _mesa_unpack_uint_24_8_depth_stencil_row(mesa_format format, uint32_t n,
1710                                          const void *src, uint32_t *dst)
1711 {
1712    switch (format) {
1713    case MESA_FORMAT_S8_UINT_Z24_UNORM:
1714       unpack_uint_24_8_depth_stencil_S8_UINT_Z24_UNORM(src, dst, n);
1715       break;
1716    case MESA_FORMAT_Z24_UNORM_S8_UINT:
1717       unpack_uint_24_8_depth_stencil_Z24_UNORM_S8_UINT(src, dst, n);
1718       break;
1719    case MESA_FORMAT_Z32_FLOAT_S8X24_UINT:
1720       unpack_uint_24_8_depth_stencil_Z32_S8X24(src, dst, n);
1721       break;
1722    default:
1723       unreachable("bad format %s in _mesa_unpack_uint_24_8_depth_stencil_row");
1724    }
1725 }
1726 
1727 static void
unpack_float_32_uint_24_8_Z24_UNORM_S8_UINT(const uint32_t * src,uint32_t * dst,uint32_t n)1728 unpack_float_32_uint_24_8_Z24_UNORM_S8_UINT(const uint32_t *src,
1729                                             uint32_t *dst, uint32_t n)
1730 {
1731    uint32_t i;
1732    struct z32f_x24s8 *d = (struct z32f_x24s8 *) dst;
1733    const double scale = 1.0 / (double) 0xffffff;
1734 
1735    for (i = 0; i < n; i++) {
1736       const uint32_t z24 = src[i] & 0xffffff;
1737       d[i].z = z24 * scale;
1738       d[i].x24s8 = src[i] >> 24;
1739       assert(d[i].z >= 0.0f);
1740       assert(d[i].z <= 1.0f);
1741    }
1742 }
1743 
1744 static void
unpack_float_32_uint_24_8_Z32_FLOAT_S8X24_UINT(const uint32_t * src,uint32_t * dst,uint32_t n)1745 unpack_float_32_uint_24_8_Z32_FLOAT_S8X24_UINT(const uint32_t *src,
1746                                                uint32_t *dst, uint32_t n)
1747 {
1748    memcpy(dst, src, n * sizeof(struct z32f_x24s8));
1749 }
1750 
1751 static void
unpack_float_32_uint_24_8_S8_UINT_Z24_UNORM(const uint32_t * src,uint32_t * dst,uint32_t n)1752 unpack_float_32_uint_24_8_S8_UINT_Z24_UNORM(const uint32_t *src,
1753                                             uint32_t *dst, uint32_t n)
1754 {
1755    uint32_t i;
1756    struct z32f_x24s8 *d = (struct z32f_x24s8 *) dst;
1757    const double scale = 1.0 / (double) 0xffffff;
1758 
1759    for (i = 0; i < n; i++) {
1760       const uint32_t z24 = src[i] >> 8;
1761       d[i].z = z24 * scale;
1762       d[i].x24s8 = src[i] & 0xff;
1763       assert(d[i].z >= 0.0f);
1764       assert(d[i].z <= 1.0f);
1765    }
1766 }
1767 
1768 /**
1769  * Unpack depth/stencil returning as GL_FLOAT_32_UNSIGNED_INT_24_8_REV.
1770  * \param format  the source data format
1771  *
1772  * In GL_FLOAT_32_UNSIGNED_INT_24_8_REV lower 4 bytes contain float
1773  * component and higher 4 bytes contain packed 24-bit and 8-bit
1774  * components.
1775  *
1776  *    31 30 29 28 ... 4 3 2 1 0    31 30 29 ... 9 8 7 6 5 ... 2 1 0
1777  *    +-------------------------+  +--------------------------------+
1778  *    |    Float Component      |  | Unused         | 8 bit stencil |
1779  *    +-------------------------+  +--------------------------------+
1780  *          lower 4 bytes                  higher 4 bytes
1781  */
1782 void
_mesa_unpack_float_32_uint_24_8_depth_stencil_row(mesa_format format,uint32_t n,const void * src,uint32_t * dst)1783 _mesa_unpack_float_32_uint_24_8_depth_stencil_row(mesa_format format, uint32_t n,
1784                                                   const void *src, uint32_t *dst)
1785 {
1786    switch (format) {
1787    case MESA_FORMAT_S8_UINT_Z24_UNORM:
1788       unpack_float_32_uint_24_8_S8_UINT_Z24_UNORM(src, dst, n);
1789       break;
1790    case MESA_FORMAT_Z24_UNORM_S8_UINT:
1791       unpack_float_32_uint_24_8_Z24_UNORM_S8_UINT(src, dst, n);
1792       break;
1793    case MESA_FORMAT_Z32_FLOAT_S8X24_UINT:
1794       unpack_float_32_uint_24_8_Z32_FLOAT_S8X24_UINT(src, dst, n);
1795       break;
1796    default:
1797       unreachable("bad format %s in _mesa_unpack_uint_24_8_depth_stencil_row");
1798    }
1799 }
1800