formats.c revision 4a49301e
1/*
2 * Mesa 3-D graphics library
3 * Version:  7.7
4 *
5 * Copyright (C) 1999-2008  Brian Paul   All Rights Reserved.
6 * Copyright (c) 2008-2009  VMware, Inc.
7 *
8 * Permission is hereby granted, free of charge, to any person obtaining a
9 * copy of this software and associated documentation files (the "Software"),
10 * to deal in the Software without restriction, including without limitation
11 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
12 * and/or sell copies of the Software, and to permit persons to whom the
13 * Software is furnished to do so, subject to the following conditions:
14 *
15 * The above copyright notice and this permission notice shall be included
16 * in all copies or substantial portions of the Software.
17 *
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
19 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
21 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
22 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
23 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24 */
25
26
27#include "imports.h"
28#include "formats.h"
29#include "config.h"
30
31
32/**
33 * Information about texture formats.
34 */
35struct gl_format_info
36{
37   gl_format Name;
38
39   /** text name for debugging */
40   const char *StrName;
41
42   /**
43    * Base format is one of GL_RGB, GL_RGBA, GL_ALPHA, GL_LUMINANCE,
44    * GL_LUMINANCE_ALPHA, GL_INTENSITY, GL_YCBCR_MESA, GL_COLOR_INDEX,
45    * GL_DEPTH_COMPONENT, GL_STENCIL_INDEX, GL_DEPTH_STENCIL.
46    */
47   GLenum BaseFormat;
48
49   /**
50    * Logical data type: one of  GL_UNSIGNED_NORMALIZED, GL_SIGNED_NORMALED,
51    * GL_UNSIGNED_INT, GL_SIGNED_INT, GL_FLOAT.
52    */
53   GLenum DataType;
54
55   GLubyte RedBits;
56   GLubyte GreenBits;
57   GLubyte BlueBits;
58   GLubyte AlphaBits;
59   GLubyte LuminanceBits;
60   GLubyte IntensityBits;
61   GLubyte IndexBits;
62   GLubyte DepthBits;
63   GLubyte StencilBits;
64
65   /**
66    * To describe compressed formats.  If not compressed, Width=Height=1.
67    */
68   GLubyte BlockWidth, BlockHeight;
69   GLubyte BytesPerBlock;
70};
71
72
73/**
74 * Info about each format.
75 * These must be in the same order as the MESA_FORMAT_* enums so that
76 * we can do lookups without searching.
77 */
78static struct gl_format_info format_info[MESA_FORMAT_COUNT] =
79{
80   {
81      MESA_FORMAT_NONE,            /* Name */
82      "MESA_FORMAT_NONE",          /* StrName */
83      GL_NONE,                     /* BaseFormat */
84      GL_NONE,                     /* DataType */
85      0, 0, 0, 0,                  /* Red/Green/Blue/AlphaBits */
86      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
87      0, 0, 0                      /* BlockWidth/Height,Bytes */
88   },
89   {
90      MESA_FORMAT_RGBA8888,        /* Name */
91      "MESA_FORMAT_RGBA8888",      /* StrName */
92      GL_RGBA,                     /* BaseFormat */
93      GL_UNSIGNED_NORMALIZED,      /* DataType */
94      8, 8, 8, 8,                  /* Red/Green/Blue/AlphaBits */
95      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
96      1, 1, 4                      /* BlockWidth/Height,Bytes */
97   },
98   {
99      MESA_FORMAT_RGBA8888_REV,    /* Name */
100      "MESA_FORMAT_RGBA8888_REV",  /* StrName */
101      GL_RGBA,                     /* BaseFormat */
102      GL_UNSIGNED_NORMALIZED,      /* DataType */
103      8, 8, 8, 8,                  /* Red/Green/Blue/AlphaBits */
104      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
105      1, 1, 4                      /* BlockWidth/Height,Bytes */
106   },
107   {
108      MESA_FORMAT_ARGB8888,        /* Name */
109      "MESA_FORMAT_ARGB8888",      /* StrName */
110      GL_RGBA,                     /* BaseFormat */
111      GL_UNSIGNED_NORMALIZED,      /* DataType */
112      8, 8, 8, 8,                  /* Red/Green/Blue/AlphaBits */
113      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
114      1, 1, 4                      /* BlockWidth/Height,Bytes */
115   },
116   {
117      MESA_FORMAT_ARGB8888_REV,    /* Name */
118      "MESA_FORMAT_ARGB8888_REV",  /* StrName */
119      GL_RGBA,                     /* BaseFormat */
120      GL_UNSIGNED_NORMALIZED,      /* DataType */
121      8, 8, 8, 8,                  /* Red/Green/Blue/AlphaBits */
122      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
123      1, 1, 4                      /* BlockWidth/Height,Bytes */
124   },
125   {
126      MESA_FORMAT_XRGB8888,        /* Name */
127      "MESA_FORMAT_XRGB8888",      /* StrName */
128      GL_RGB,                      /* BaseFormat */
129      GL_UNSIGNED_NORMALIZED,      /* DataType */
130      8, 8, 8, 0,                  /* Red/Green/Blue/AlphaBits */
131      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
132      1, 1, 4                      /* BlockWidth/Height,Bytes */
133   },
134   {
135      MESA_FORMAT_XRGB8888_REV,    /* Name */
136      "MESA_FORMAT_XRGB8888_REV",  /* StrName */
137      GL_RGB,                      /* BaseFormat */
138      GL_UNSIGNED_NORMALIZED,      /* DataType */
139      8, 8, 8, 0,                  /* Red/Green/Blue/AlphaBits */
140      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
141      1, 1, 4                      /* BlockWidth/Height,Bytes */
142   },
143   {
144      MESA_FORMAT_RGB888,          /* Name */
145      "MESA_FORMAT_RGB888",        /* StrName */
146      GL_RGB,                      /* BaseFormat */
147      GL_UNSIGNED_NORMALIZED,      /* DataType */
148      8, 8, 8, 0,                  /* Red/Green/Blue/AlphaBits */
149      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
150      1, 1, 3                      /* BlockWidth/Height,Bytes */
151   },
152   {
153      MESA_FORMAT_BGR888,          /* Name */
154      "MESA_FORMAT_BGR888",        /* StrName */
155      GL_RGB,                      /* BaseFormat */
156      GL_UNSIGNED_NORMALIZED,      /* DataType */
157      8, 8, 8, 0,                  /* Red/Green/Blue/AlphaBits */
158      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
159      1, 1, 3                      /* BlockWidth/Height,Bytes */
160   },
161   {
162      MESA_FORMAT_RGB565,          /* Name */
163      "MESA_FORMAT_RGB565",        /* StrName */
164      GL_RGB,                      /* BaseFormat */
165      GL_UNSIGNED_NORMALIZED,      /* DataType */
166      5, 6, 5, 0,                  /* Red/Green/Blue/AlphaBits */
167      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
168      1, 1, 2                      /* BlockWidth/Height,Bytes */
169   },
170   {
171      MESA_FORMAT_RGB565_REV,      /* Name */
172      "MESA_FORMAT_RGB565_REV",    /* StrName */
173      GL_RGB,                      /* BaseFormat */
174      GL_UNSIGNED_NORMALIZED,      /* DataType */
175      5, 6, 5, 0,                  /* Red/Green/Blue/AlphaBits */
176      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
177      1, 1, 2                      /* BlockWidth/Height,Bytes */
178   },
179   {
180      MESA_FORMAT_ARGB4444,        /* Name */
181      "MESA_FORMAT_ARGB4444",      /* StrName */
182      GL_RGBA,                     /* BaseFormat */
183      GL_UNSIGNED_NORMALIZED,      /* DataType */
184      4, 4, 4, 4,                  /* Red/Green/Blue/AlphaBits */
185      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
186      1, 1, 2                      /* BlockWidth/Height,Bytes */
187   },
188   {
189      MESA_FORMAT_ARGB4444_REV,    /* Name */
190      "MESA_FORMAT_ARGB4444_REV",  /* StrName */
191      GL_RGBA,                     /* BaseFormat */
192      GL_UNSIGNED_NORMALIZED,      /* DataType */
193      4, 4, 4, 4,                  /* Red/Green/Blue/AlphaBits */
194      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
195      1, 1, 2                      /* BlockWidth/Height,Bytes */
196   },
197   {
198      MESA_FORMAT_RGBA5551,        /* Name */
199      "MESA_FORMAT_RGBA5551",      /* StrName */
200      GL_RGBA,                     /* BaseFormat */
201      GL_UNSIGNED_NORMALIZED,      /* DataType */
202      5, 5, 5, 1,                  /* Red/Green/Blue/AlphaBits */
203      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
204      1, 1, 2                      /* BlockWidth/Height,Bytes */
205   },
206   {
207      MESA_FORMAT_ARGB1555,        /* Name */
208      "MESA_FORMAT_ARGB1555",      /* StrName */
209      GL_RGBA,                     /* BaseFormat */
210      GL_UNSIGNED_NORMALIZED,      /* DataType */
211      5, 5, 5, 1,                  /* Red/Green/Blue/AlphaBits */
212      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
213      1, 1, 2                      /* BlockWidth/Height,Bytes */
214   },
215   {
216      MESA_FORMAT_ARGB1555_REV,    /* Name */
217      "MESA_FORMAT_ARGB1555_REV",  /* StrName */
218      GL_RGBA,                     /* BaseFormat */
219      GL_UNSIGNED_NORMALIZED,      /* DataType */
220      5, 5, 5, 1,                  /* Red/Green/Blue/AlphaBits */
221      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
222      1, 1, 2                      /* BlockWidth/Height,Bytes */
223   },
224   {
225      MESA_FORMAT_AL88,            /* Name */
226      "MESA_FORMAT_AL88",          /* StrName */
227      GL_LUMINANCE_ALPHA,          /* BaseFormat */
228      GL_UNSIGNED_NORMALIZED,      /* DataType */
229      0, 0, 0, 8,                  /* Red/Green/Blue/AlphaBits */
230      8, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
231      1, 1, 2                      /* BlockWidth/Height,Bytes */
232   },
233   {
234      MESA_FORMAT_AL88_REV,        /* Name */
235      "MESA_FORMAT_AL88_REV",      /* StrName */
236      GL_LUMINANCE_ALPHA,          /* BaseFormat */
237      GL_UNSIGNED_NORMALIZED,      /* DataType */
238      0, 0, 0, 8,                  /* Red/Green/Blue/AlphaBits */
239      8, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
240      1, 1, 2                      /* BlockWidth/Height,Bytes */
241   },
242   {
243      MESA_FORMAT_AL1616,          /* Name */
244      "MESA_FORMAT_AL1616",        /* StrName */
245      GL_LUMINANCE_ALPHA,          /* BaseFormat */
246      GL_UNSIGNED_NORMALIZED,      /* DataType */
247      0, 0, 0, 16,                 /* Red/Green/Blue/AlphaBits */
248      16, 0, 0, 0, 0,              /* Lum/Int/Index/Depth/StencilBits */
249      1, 1, 4                      /* BlockWidth/Height,Bytes */
250   },
251   {
252      MESA_FORMAT_AL1616_REV,      /* Name */
253      "MESA_FORMAT_AL1616_REV",    /* StrName */
254      GL_LUMINANCE_ALPHA,          /* BaseFormat */
255      GL_UNSIGNED_NORMALIZED,      /* DataType */
256      0, 0, 0, 16,                 /* Red/Green/Blue/AlphaBits */
257      16, 0, 0, 0, 0,              /* Lum/Int/Index/Depth/StencilBits */
258      1, 1, 4                      /* BlockWidth/Height,Bytes */
259   },
260   {
261      MESA_FORMAT_RGB332,          /* Name */
262      "MESA_FORMAT_RGB332",        /* StrName */
263      GL_RGB,                      /* BaseFormat */
264      GL_UNSIGNED_NORMALIZED,      /* DataType */
265      3, 3, 2, 0,                  /* Red/Green/Blue/AlphaBits */
266      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
267      1, 1, 1                      /* BlockWidth/Height,Bytes */
268   },
269   {
270      MESA_FORMAT_A8,              /* Name */
271      "MESA_FORMAT_A8",            /* StrName */
272      GL_ALPHA,                    /* BaseFormat */
273      GL_UNSIGNED_NORMALIZED,      /* DataType */
274      0, 0, 0, 8,                  /* Red/Green/Blue/AlphaBits */
275      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
276      1, 1, 1                      /* BlockWidth/Height,Bytes */
277   },
278   {
279      MESA_FORMAT_L8,              /* Name */
280      "MESA_FORMAT_L8",            /* StrName */
281      GL_LUMINANCE,                /* BaseFormat */
282      GL_UNSIGNED_NORMALIZED,      /* DataType */
283      0, 0, 0, 0,                  /* Red/Green/Blue/AlphaBits */
284      8, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
285      1, 1, 1                      /* BlockWidth/Height,Bytes */
286   },
287   {
288      MESA_FORMAT_I8,              /* Name */
289      "MESA_FORMAT_I8",            /* StrName */
290      GL_INTENSITY,                /* BaseFormat */
291      GL_UNSIGNED_NORMALIZED,      /* DataType */
292      0, 0, 0, 0,                  /* Red/Green/Blue/AlphaBits */
293      0, 8, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
294      1, 1, 1                      /* BlockWidth/Height,Bytes */
295   },
296   {
297      MESA_FORMAT_CI8,             /* Name */
298      "MESA_FORMAT_CI8",           /* StrName */
299      GL_COLOR_INDEX,              /* BaseFormat */
300      GL_UNSIGNED_INT,             /* DataType */
301      0, 0, 0, 0,                  /* Red/Green/Blue/AlphaBits */
302      0, 0, 8, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
303      1, 1, 1                      /* BlockWidth/Height,Bytes */
304   },
305   {
306      MESA_FORMAT_YCBCR,           /* Name */
307      "MESA_FORMAT_YCBCR",         /* StrName */
308      GL_YCBCR_MESA,               /* BaseFormat */
309      GL_UNSIGNED_NORMALIZED,      /* DataType */
310      0, 0, 0, 0,                  /* Red/Green/Blue/AlphaBits */
311      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
312      1, 1, 2                      /* BlockWidth/Height,Bytes */
313   },
314   {
315      MESA_FORMAT_YCBCR_REV,       /* Name */
316      "MESA_FORMAT_YCBCR_REV",     /* StrName */
317      GL_YCBCR_MESA,               /* BaseFormat */
318      GL_UNSIGNED_NORMALIZED,      /* DataType */
319      0, 0, 0, 0,                  /* Red/Green/Blue/AlphaBits */
320      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
321      1, 1, 2                      /* BlockWidth/Height,Bytes */
322   },
323   {
324      MESA_FORMAT_Z24_S8,          /* Name */
325      "MESA_FORMAT_Z24_S8",        /* StrName */
326      GL_DEPTH_STENCIL,            /* BaseFormat */
327      GL_UNSIGNED_INT,             /* DataType */
328      0, 0, 0, 0,                  /* Red/Green/Blue/AlphaBits */
329      0, 0, 0, 24, 8,              /* Lum/Int/Index/Depth/StencilBits */
330      1, 1, 4                      /* BlockWidth/Height,Bytes */
331   },
332   {
333      MESA_FORMAT_S8_Z24,          /* Name */
334      "MESA_FORMAT_S8_Z24",        /* StrName */
335      GL_DEPTH_STENCIL,            /* BaseFormat */
336      GL_UNSIGNED_INT,             /* DataType */
337      0, 0, 0, 0,                  /* Red/Green/Blue/AlphaBits */
338      0, 0, 0, 24, 8,              /* Lum/Int/Index/Depth/StencilBits */
339      1, 1, 4                      /* BlockWidth/Height,Bytes */
340   },
341   {
342      MESA_FORMAT_Z16,             /* Name */
343      "MESA_FORMAT_Z16",           /* StrName */
344      GL_DEPTH_COMPONENT,          /* BaseFormat */
345      GL_UNSIGNED_INT,             /* DataType */
346      0, 0, 0, 0,                  /* Red/Green/Blue/AlphaBits */
347      0, 0, 0, 16, 0,              /* Lum/Int/Index/Depth/StencilBits */
348      1, 1, 2                      /* BlockWidth/Height,Bytes */
349   },
350   {
351      MESA_FORMAT_X8_Z24,          /* Name */
352      "MESA_FORMAT_X8_Z24",        /* StrName */
353      GL_DEPTH_COMPONENT,          /* BaseFormat */
354      GL_UNSIGNED_INT,             /* DataType */
355      0, 0, 0, 0,                  /* Red/Green/Blue/AlphaBits */
356      0, 0, 0, 24, 0,              /* Lum/Int/Index/Depth/StencilBits */
357      1, 1, 4                      /* BlockWidth/Height,Bytes */
358   },
359   {
360      MESA_FORMAT_Z24_X8,          /* Name */
361      "MESA_FORMAT_Z24_X8",        /* StrName */
362      GL_DEPTH_COMPONENT,          /* BaseFormat */
363      GL_UNSIGNED_INT,             /* DataType */
364      0, 0, 0, 0,                  /* Red/Green/Blue/AlphaBits */
365      0, 0, 0, 24, 0,              /* Lum/Int/Index/Depth/StencilBits */
366      1, 1, 4                      /* BlockWidth/Height,Bytes */
367   },
368   {
369      MESA_FORMAT_Z32,             /* Name */
370      "MESA_FORMAT_Z32",           /* StrName */
371      GL_DEPTH_COMPONENT,          /* BaseFormat */
372      GL_UNSIGNED_INT,             /* DataType */
373      0, 0, 0, 0,                  /* Red/Green/Blue/AlphaBits */
374      0, 0, 0, 32, 0,              /* Lum/Int/Index/Depth/StencilBits */
375      1, 1, 4                      /* BlockWidth/Height,Bytes */
376   },
377   {
378      MESA_FORMAT_S8,              /* Name */
379      "MESA_FORMAT_S8",            /* StrName */
380      GL_STENCIL_INDEX,            /* BaseFormat */
381      GL_UNSIGNED_INT,             /* DataType */
382      0, 0, 0, 0,                  /* Red/Green/Blue/AlphaBits */
383      0, 0, 0, 0, 8,               /* Lum/Int/Index/Depth/StencilBits */
384      1, 1, 1                      /* BlockWidth/Height,Bytes */
385   },
386   {
387      MESA_FORMAT_SRGB8,
388      "MESA_FORMAT_SRGB8",
389      GL_RGB,
390      GL_UNSIGNED_NORMALIZED,
391      8, 8, 8, 0,
392      0, 0, 0, 0, 0,
393      1, 1, 3
394   },
395   {
396      MESA_FORMAT_SRGBA8,
397      "MESA_FORMAT_SRGBA8",
398      GL_RGBA,
399      GL_UNSIGNED_NORMALIZED,
400      8, 8, 8, 8,
401      0, 0, 0, 0, 0,
402      1, 1, 4
403   },
404   {
405      MESA_FORMAT_SARGB8,
406      "MESA_FORMAT_SARGB8",
407      GL_RGBA,
408      GL_UNSIGNED_NORMALIZED,
409      8, 8, 8, 8,
410      0, 0, 0, 0, 0,
411      1, 1, 4
412   },
413   {
414      MESA_FORMAT_SL8,
415      "MESA_FORMAT_SL8",
416      GL_LUMINANCE,
417      GL_UNSIGNED_NORMALIZED,
418      0, 0, 0, 0,
419      8, 0, 0, 0, 0,
420      1, 1, 1
421   },
422   {
423      MESA_FORMAT_SLA8,
424      "MESA_FORMAT_SLA8",
425      GL_LUMINANCE_ALPHA,
426      GL_UNSIGNED_NORMALIZED,
427      0, 0, 0, 8,
428      8, 0, 0, 0, 0,
429      1, 1, 2
430   },
431   {
432      MESA_FORMAT_SRGB_DXT1,       /* Name */
433      "MESA_FORMAT_SRGB_DXT1",     /* StrName */
434      GL_RGB,                      /* BaseFormat */
435      GL_UNSIGNED_NORMALIZED,      /* DataType */
436      4, 4, 4, 0,                  /* approx Red/Green/Blue/AlphaBits */
437      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
438      4, 4, 8                      /* 8 bytes per 4x4 block */
439   },
440   {
441      MESA_FORMAT_SRGBA_DXT1,
442      "MESA_FORMAT_SRGBA_DXT1",
443      GL_RGBA,
444      GL_UNSIGNED_NORMALIZED,
445      4, 4, 4, 4,
446      0, 0, 0, 0, 0,
447      4, 4, 8                      /* 8 bytes per 4x4 block */
448   },
449   {
450      MESA_FORMAT_SRGBA_DXT3,
451      "MESA_FORMAT_SRGBA_DXT3",
452      GL_RGBA,
453      GL_UNSIGNED_NORMALIZED,
454      4, 4, 4, 4,
455      0, 0, 0, 0, 0,
456      4, 4, 16                     /* 16 bytes per 4x4 block */
457   },
458   {
459      MESA_FORMAT_SRGBA_DXT5,
460      "MESA_FORMAT_SRGBA_DXT5",
461      GL_RGBA,
462      GL_UNSIGNED_NORMALIZED,
463      4, 4, 4, 4,
464      0, 0, 0, 0, 0,
465      4, 4, 16                     /* 16 bytes per 4x4 block */
466   },
467
468   {
469      MESA_FORMAT_RGB_FXT1,
470      "MESA_FORMAT_RGB_FXT1",
471      GL_RGB,
472      GL_UNSIGNED_NORMALIZED,
473      4, 4, 4, 0,                  /* approx Red/Green/BlueBits */
474      0, 0, 0, 0, 0,
475      8, 4, 16                     /* 16 bytes per 8x4 block */
476   },
477   {
478      MESA_FORMAT_RGBA_FXT1,
479      "MESA_FORMAT_RGBA_FXT1",
480      GL_RGBA,
481      GL_UNSIGNED_NORMALIZED,
482      4, 4, 4, 1,                  /* approx Red/Green/Blue/AlphaBits */
483      0, 0, 0, 0, 0,
484      8, 4, 16                     /* 16 bytes per 8x4 block */
485   },
486
487   {
488      MESA_FORMAT_RGB_DXT1,        /* Name */
489      "MESA_FORMAT_RGB_DXT1",      /* StrName */
490      GL_RGB,                      /* BaseFormat */
491      GL_UNSIGNED_NORMALIZED,      /* DataType */
492      4, 4, 4, 0,                  /* approx Red/Green/Blue/AlphaBits */
493      0, 0, 0, 0, 0,               /* Lum/Int/Index/Depth/StencilBits */
494      4, 4, 8                      /* 8 bytes per 4x4 block */
495   },
496   {
497      MESA_FORMAT_RGBA_DXT1,
498      "MESA_FORMAT_RGBA_DXT1",
499      GL_RGBA,
500      GL_UNSIGNED_NORMALIZED,
501      4, 4, 4, 4,
502      0, 0, 0, 0, 0,
503      4, 4, 8                      /* 8 bytes per 4x4 block */
504   },
505   {
506      MESA_FORMAT_RGBA_DXT3,
507      "MESA_FORMAT_RGBA_DXT3",
508      GL_RGBA,
509      GL_UNSIGNED_NORMALIZED,
510      4, 4, 4, 4,
511      0, 0, 0, 0, 0,
512      4, 4, 16                     /* 16 bytes per 4x4 block */
513   },
514   {
515      MESA_FORMAT_RGBA_DXT5,
516      "MESA_FORMAT_RGBA_DXT5",
517      GL_RGBA,
518      GL_UNSIGNED_NORMALIZED,
519      4, 4, 4, 4,
520      0, 0, 0, 0, 0,
521      4, 4, 16                     /* 16 bytes per 4x4 block */
522   },
523   {
524      MESA_FORMAT_RGBA_FLOAT32,
525      "MESA_FORMAT_RGBA_FLOAT32",
526      GL_RGBA,
527      GL_FLOAT,
528      32, 32, 32, 32,
529      0, 0, 0, 0, 0,
530      1, 1, 16
531   },
532   {
533      MESA_FORMAT_RGBA_FLOAT16,
534      "MESA_FORMAT_RGBA_FLOAT16",
535      GL_RGBA,
536      GL_FLOAT,
537      16, 16, 16, 16,
538      0, 0, 0, 0, 0,
539      1, 1, 8
540   },
541   {
542      MESA_FORMAT_RGB_FLOAT32,
543      "MESA_FORMAT_RGB_FLOAT32",
544      GL_RGB,
545      GL_FLOAT,
546      32, 32, 32, 0,
547      0, 0, 0, 0, 0,
548      1, 1, 12
549   },
550   {
551      MESA_FORMAT_RGB_FLOAT16,
552      "MESA_FORMAT_RGB_FLOAT16",
553      GL_RGB,
554      GL_FLOAT,
555      16, 16, 16, 0,
556      0, 0, 0, 0, 0,
557      1, 1, 6
558   },
559   {
560      MESA_FORMAT_ALPHA_FLOAT32,
561      "MESA_FORMAT_ALPHA_FLOAT32",
562      GL_ALPHA,
563      GL_FLOAT,
564      0, 0, 0, 32,
565      0, 0, 0, 0, 0,
566      1, 1, 4
567   },
568   {
569      MESA_FORMAT_ALPHA_FLOAT16,
570      "MESA_FORMAT_ALPHA_FLOAT16",
571      GL_ALPHA,
572      GL_FLOAT,
573      0, 0, 0, 16,
574      0, 0, 0, 0, 0,
575      1, 1, 2
576   },
577   {
578      MESA_FORMAT_LUMINANCE_FLOAT32,
579      "MESA_FORMAT_LUMINANCE_FLOAT32",
580      GL_ALPHA,
581      GL_FLOAT,
582      0, 0, 0, 0,
583      32, 0, 0, 0, 0,
584      1, 1, 4
585   },
586   {
587      MESA_FORMAT_LUMINANCE_FLOAT16,
588      "MESA_FORMAT_LUMINANCE_FLOAT16",
589      GL_ALPHA,
590      GL_FLOAT,
591      0, 0, 0, 0,
592      16, 0, 0, 0, 0,
593      1, 1, 2
594   },
595   {
596      MESA_FORMAT_LUMINANCE_ALPHA_FLOAT32,
597      "MESA_FORMAT_LUMINANCE_ALPHA_FLOAT32",
598      GL_LUMINANCE_ALPHA,
599      GL_FLOAT,
600      0, 0, 0, 32,
601      32, 0, 0, 0, 0,
602      1, 1, 8
603   },
604   {
605      MESA_FORMAT_LUMINANCE_ALPHA_FLOAT16,
606      "MESA_FORMAT_LUMINANCE_ALPHA_FLOAT16",
607      GL_LUMINANCE_ALPHA,
608      GL_FLOAT,
609      0, 0, 0, 16,
610      16, 0, 0, 0, 0,
611      1, 1, 4
612   },
613   {
614      MESA_FORMAT_INTENSITY_FLOAT32,
615      "MESA_FORMAT_INTENSITY_FLOAT32",
616      GL_INTENSITY,
617      GL_FLOAT,
618      0, 0, 0, 0,
619      0, 32, 0, 0, 0,
620      1, 1, 4
621   },
622   {
623      MESA_FORMAT_INTENSITY_FLOAT16,
624      "MESA_FORMAT_INTENSITY_FLOAT16",
625      GL_INTENSITY,
626      GL_FLOAT,
627      0, 0, 0, 0,
628      0, 16, 0, 0, 0,
629      1, 1, 2
630   },
631   {
632      MESA_FORMAT_DUDV8,
633      "MESA_FORMAT_DUDV8",
634      GL_DUDV_ATI,
635      GL_SIGNED_NORMALIZED,
636      0, 0, 0, 0,
637      0, 0, 0, 0, 0,
638      1, 1, 2
639   },
640   {
641      MESA_FORMAT_SIGNED_RGBA8888,
642      "MESA_FORMAT_SIGNED_RGBA8888",
643      GL_RGBA,
644      GL_SIGNED_NORMALIZED,
645      8, 8, 8, 8,
646      0, 0, 0, 0, 0,
647      1, 1, 4
648   },
649   {
650      MESA_FORMAT_SIGNED_RGBA8888_REV,
651      "MESA_FORMAT_SIGNED_RGBA8888_REV",
652      GL_RGBA,
653      GL_SIGNED_NORMALIZED,
654      8, 8, 8, 8,
655      0, 0, 0, 0, 0,
656      1, 1, 4
657   },
658   {
659      MESA_FORMAT_SIGNED_RGBA_16,
660      "MESA_FORMAT_SIGNED_RGBA_16",
661      GL_RGBA,
662      GL_SIGNED_NORMALIZED,
663      16, 16, 16, 16,
664      0, 0, 0, 0, 0,
665      1, 1, 8
666   }
667};
668
669
670
671static const struct gl_format_info *
672_mesa_get_format_info(gl_format format)
673{
674   const struct gl_format_info *info = &format_info[format];
675   assert(info->Name == format);
676   return info;
677}
678
679
680/** Return string name of format (for debugging) */
681const char *
682_mesa_get_format_name(gl_format format)
683{
684   const struct gl_format_info *info = _mesa_get_format_info(format);
685   ASSERT(info->BytesPerBlock);
686   return info->StrName;
687}
688
689
690
691/**
692 * Return bytes needed to store a block of pixels in the given format.
693 * Normally, a block is 1x1 (a single pixel).  But for compressed formats
694 * a block may be 4x4 or 8x4, etc.
695 */
696GLuint
697_mesa_get_format_bytes(gl_format format)
698{
699   const struct gl_format_info *info = _mesa_get_format_info(format);
700   ASSERT(info->BytesPerBlock);
701   return info->BytesPerBlock;
702}
703
704
705/**
706 * Return bits per component for the given format.
707 * \param format  one of MESA_FORMAT_x
708 * \param pname  the component, such as GL_RED_BITS, GL_TEXTURE_BLUE_BITS, etc.
709 */
710GLint
711_mesa_get_format_bits(gl_format format, GLenum pname)
712{
713   const struct gl_format_info *info = _mesa_get_format_info(format);
714
715   switch (pname) {
716   case GL_RED_BITS:
717   case GL_TEXTURE_RED_SIZE:
718   case GL_RENDERBUFFER_RED_SIZE_EXT:
719   case GL_FRAMEBUFFER_ATTACHMENT_RED_SIZE:
720      return info->RedBits;
721   case GL_GREEN_BITS:
722   case GL_TEXTURE_GREEN_SIZE:
723   case GL_RENDERBUFFER_GREEN_SIZE_EXT:
724   case GL_FRAMEBUFFER_ATTACHMENT_GREEN_SIZE:
725      return info->GreenBits;
726   case GL_BLUE_BITS:
727   case GL_TEXTURE_BLUE_SIZE:
728   case GL_RENDERBUFFER_BLUE_SIZE_EXT:
729   case GL_FRAMEBUFFER_ATTACHMENT_BLUE_SIZE:
730      return info->BlueBits;
731   case GL_ALPHA_BITS:
732   case GL_TEXTURE_ALPHA_SIZE:
733   case GL_RENDERBUFFER_ALPHA_SIZE_EXT:
734   case GL_FRAMEBUFFER_ATTACHMENT_ALPHA_SIZE:
735      return info->AlphaBits;
736   case GL_TEXTURE_INTENSITY_SIZE:
737      return info->IntensityBits;
738   case GL_TEXTURE_LUMINANCE_SIZE:
739      return info->LuminanceBits;
740   case GL_INDEX_BITS:
741   case GL_TEXTURE_INDEX_SIZE_EXT:
742      return info->IndexBits;
743   case GL_DEPTH_BITS:
744   case GL_TEXTURE_DEPTH_SIZE_ARB:
745   case GL_RENDERBUFFER_DEPTH_SIZE_EXT:
746   case GL_FRAMEBUFFER_ATTACHMENT_DEPTH_SIZE:
747      return info->DepthBits;
748   case GL_STENCIL_BITS:
749   case GL_TEXTURE_STENCIL_SIZE_EXT:
750   case GL_RENDERBUFFER_STENCIL_SIZE_EXT:
751   case GL_FRAMEBUFFER_ATTACHMENT_STENCIL_SIZE:
752      return info->StencilBits;
753   default:
754      _mesa_problem(NULL, "bad pname in _mesa_get_format_bits()");
755      return 0;
756   }
757}
758
759
760/**
761 * Return the data type (or more specifically, the data representation)
762 * for the given format.
763 * The return value will be one of:
764 *    GL_UNSIGNED_NORMALIZED = unsigned int representing [0,1]
765 *    GL_SIGNED_NORMALIZED = signed int representing [-1, 1]
766 *    GL_UNSIGNED_INT = an ordinary unsigned integer
767 *    GL_FLOAT = an ordinary float
768 */
769GLenum
770_mesa_get_format_datatype(gl_format format)
771{
772   const struct gl_format_info *info = _mesa_get_format_info(format);
773   return info->DataType;
774}
775
776
777/**
778 * Return the basic format for the given type.  The result will be
779 * one of GL_RGB, GL_RGBA, GL_ALPHA, GL_LUMINANCE, GL_LUMINANCE_ALPHA,
780 * GL_INTENSITY, GL_YCBCR_MESA, GL_COLOR_INDEX, GL_DEPTH_COMPONENT,
781 * GL_STENCIL_INDEX, GL_DEPTH_STENCIL.
782 */
783GLenum
784_mesa_get_format_base_format(gl_format format)
785{
786   const struct gl_format_info *info = _mesa_get_format_info(format);
787   return info->BaseFormat;
788}
789
790
791/**
792 * Return the block size (in pixels) for the given format.  Normally
793 * the block size is 1x1.  But compressed formats will have block sizes
794 * of 4x4 or 8x4 pixels, etc.
795 * \param bw  returns block width in pixels
796 * \param bh  returns block height in pixels
797 */
798void
799_mesa_get_format_block_size(gl_format format, GLuint *bw, GLuint *bh)
800{
801   const struct gl_format_info *info = _mesa_get_format_info(format);
802   *bw = info->BlockWidth;
803   *bh = info->BlockHeight;
804}
805
806
807/** Is the given format a compressed format? */
808GLboolean
809_mesa_is_format_compressed(gl_format format)
810{
811   const struct gl_format_info *info = _mesa_get_format_info(format);
812   return info->BlockWidth > 1 || info->BlockHeight > 1;
813}
814
815
816/**
817 * Return color encoding for given format.
818 * \return GL_LINEAR or GL_SRGB
819 */
820GLenum
821_mesa_get_format_color_encoding(gl_format format)
822{
823   /* XXX this info should be encoded in gl_format_info */
824   switch (format) {
825   case MESA_FORMAT_SRGB8:
826   case MESA_FORMAT_SRGBA8:
827   case MESA_FORMAT_SARGB8:
828   case MESA_FORMAT_SL8:
829   case MESA_FORMAT_SLA8:
830   case MESA_FORMAT_SRGB_DXT1:
831   case MESA_FORMAT_SRGBA_DXT1:
832   case MESA_FORMAT_SRGBA_DXT3:
833   case MESA_FORMAT_SRGBA_DXT5:
834      return GL_SRGB;
835   default:
836      return GL_LINEAR;
837   }
838}
839
840
841/**
842 * Return number of bytes needed to store an image of the given size
843 * in the given format.
844 */
845GLuint
846_mesa_format_image_size(gl_format format, GLsizei width,
847                        GLsizei height, GLsizei depth)
848{
849   const struct gl_format_info *info = _mesa_get_format_info(format);
850   /* Strictly speaking, a conditional isn't needed here */
851   if (info->BlockWidth > 1 || info->BlockHeight > 1) {
852      /* compressed format */
853      const GLuint bw = info->BlockWidth, bh = info->BlockHeight;
854      const GLuint wblocks = (width + bw - 1) / bw;
855      const GLuint hblocks = (height + bh - 1) / bh;
856      const GLuint sz = wblocks * hblocks * info->BytesPerBlock;
857      return sz;
858   }
859   else {
860      /* non-compressed */
861      const GLuint sz = width * height * depth * info->BytesPerBlock;
862      return sz;
863   }
864}
865
866
867
868GLint
869_mesa_format_row_stride(gl_format format, GLsizei width)
870{
871   const struct gl_format_info *info = _mesa_get_format_info(format);
872   /* Strictly speaking, a conditional isn't needed here */
873   if (info->BlockWidth > 1 || info->BlockHeight > 1) {
874      /* compressed format */
875      const GLuint bw = info->BlockWidth;
876      const GLuint wblocks = (width + bw - 1) / bw;
877      const GLint stride = wblocks * info->BytesPerBlock;
878      return stride;
879   }
880   else {
881      const GLint stride = width * info->BytesPerBlock;
882      return stride;
883   }
884}
885
886
887
888/**
889 * Do sanity checking of the format info table.
890 */
891void
892_mesa_test_formats(void)
893{
894   GLuint i;
895
896   assert(Elements(format_info) == MESA_FORMAT_COUNT);
897
898   for (i = 0; i < MESA_FORMAT_COUNT; i++) {
899      const struct gl_format_info *info = _mesa_get_format_info(i);
900      assert(info);
901
902      assert(info->Name == i);
903
904      if (info->Name == MESA_FORMAT_NONE)
905         continue;
906
907      if (info->BlockWidth == 1 && info->BlockHeight == 1) {
908         if (info->RedBits > 0) {
909            GLuint t = info->RedBits + info->GreenBits
910               + info->BlueBits + info->AlphaBits;
911            assert(t / 8 == info->BytesPerBlock);
912            (void) t;
913         }
914      }
915
916      assert(info->DataType == GL_UNSIGNED_NORMALIZED ||
917             info->DataType == GL_SIGNED_NORMALIZED ||
918             info->DataType == GL_UNSIGNED_INT ||
919             info->DataType == GL_FLOAT);
920
921      if (info->BaseFormat == GL_RGB) {
922         assert(info->RedBits > 0);
923         assert(info->GreenBits > 0);
924         assert(info->BlueBits > 0);
925         assert(info->AlphaBits == 0);
926         assert(info->LuminanceBits == 0);
927         assert(info->IntensityBits == 0);
928      }
929      else if (info->BaseFormat == GL_RGBA) {
930         assert(info->RedBits > 0);
931         assert(info->GreenBits > 0);
932         assert(info->BlueBits > 0);
933         assert(info->AlphaBits > 0);
934         assert(info->LuminanceBits == 0);
935         assert(info->IntensityBits == 0);
936      }
937      else if (info->BaseFormat == GL_LUMINANCE) {
938         assert(info->RedBits == 0);
939         assert(info->GreenBits == 0);
940         assert(info->BlueBits == 0);
941         assert(info->AlphaBits == 0);
942         assert(info->LuminanceBits > 0);
943         assert(info->IntensityBits == 0);
944      }
945      else if (info->BaseFormat == GL_INTENSITY) {
946         assert(info->RedBits == 0);
947         assert(info->GreenBits == 0);
948         assert(info->BlueBits == 0);
949         assert(info->AlphaBits == 0);
950         assert(info->LuminanceBits == 0);
951         assert(info->IntensityBits > 0);
952      }
953
954   }
955}
956
957
958
959/**
960 * Return datatype and number of components per texel for the given gl_format.
961 * Only used for mipmap generation code.
962 */
963void
964_mesa_format_to_type_and_comps(gl_format format,
965                               GLenum *datatype, GLuint *comps)
966{
967   switch (format) {
968   case MESA_FORMAT_RGBA8888:
969   case MESA_FORMAT_RGBA8888_REV:
970   case MESA_FORMAT_ARGB8888:
971   case MESA_FORMAT_ARGB8888_REV:
972   case MESA_FORMAT_XRGB8888:
973      *datatype = GL_UNSIGNED_BYTE;
974      *comps = 4;
975      return;
976   case MESA_FORMAT_RGB888:
977   case MESA_FORMAT_BGR888:
978      *datatype = GL_UNSIGNED_BYTE;
979      *comps = 3;
980      return;
981   case MESA_FORMAT_RGB565:
982   case MESA_FORMAT_RGB565_REV:
983      *datatype = GL_UNSIGNED_SHORT_5_6_5;
984      *comps = 3;
985      return;
986
987   case MESA_FORMAT_ARGB4444:
988   case MESA_FORMAT_ARGB4444_REV:
989      *datatype = GL_UNSIGNED_SHORT_4_4_4_4;
990      *comps = 4;
991      return;
992
993   case MESA_FORMAT_ARGB1555:
994   case MESA_FORMAT_ARGB1555_REV:
995      *datatype = GL_UNSIGNED_SHORT_1_5_5_5_REV;
996      *comps = 4;
997      return;
998
999   case MESA_FORMAT_AL88:
1000   case MESA_FORMAT_AL88_REV:
1001      *datatype = GL_UNSIGNED_BYTE;
1002      *comps = 2;
1003      return;
1004
1005   case MESA_FORMAT_AL1616:
1006   case MESA_FORMAT_AL1616_REV:
1007      *datatype = GL_UNSIGNED_SHORT;
1008      *comps = 2;
1009      return;
1010
1011   case MESA_FORMAT_RGB332:
1012      *datatype = GL_UNSIGNED_BYTE_3_3_2;
1013      *comps = 3;
1014      return;
1015
1016   case MESA_FORMAT_A8:
1017   case MESA_FORMAT_L8:
1018   case MESA_FORMAT_I8:
1019   case MESA_FORMAT_CI8:
1020      *datatype = GL_UNSIGNED_BYTE;
1021      *comps = 1;
1022      return;
1023
1024   case MESA_FORMAT_YCBCR:
1025   case MESA_FORMAT_YCBCR_REV:
1026      *datatype = GL_UNSIGNED_SHORT;
1027      *comps = 2;
1028      return;
1029
1030   case MESA_FORMAT_Z24_S8:
1031      *datatype = GL_UNSIGNED_INT;
1032      *comps = 1; /* XXX OK? */
1033      return;
1034
1035   case MESA_FORMAT_S8_Z24:
1036      *datatype = GL_UNSIGNED_INT;
1037      *comps = 1; /* XXX OK? */
1038      return;
1039
1040   case MESA_FORMAT_Z16:
1041      *datatype = GL_UNSIGNED_SHORT;
1042      *comps = 1;
1043      return;
1044
1045   case MESA_FORMAT_X8_Z24:
1046      *datatype = GL_UNSIGNED_INT;
1047      *comps = 1;
1048      return;
1049
1050   case MESA_FORMAT_Z24_X8:
1051      *datatype = GL_UNSIGNED_INT;
1052      *comps = 1;
1053      return;
1054
1055   case MESA_FORMAT_Z32:
1056      *datatype = GL_UNSIGNED_INT;
1057      *comps = 1;
1058      return;
1059
1060   case MESA_FORMAT_DUDV8:
1061      *datatype = GL_BYTE;
1062      *comps = 2;
1063      return;
1064
1065   case MESA_FORMAT_SIGNED_RGBA8888:
1066   case MESA_FORMAT_SIGNED_RGBA8888_REV:
1067      *datatype = GL_BYTE;
1068      *comps = 4;
1069      return;
1070   case MESA_FORMAT_SIGNED_RGBA_16:
1071      *datatype = GL_SHORT;
1072      *comps = 4;
1073      return;
1074
1075#if FEATURE_EXT_texture_sRGB
1076   case MESA_FORMAT_SRGB8:
1077      *datatype = GL_UNSIGNED_BYTE;
1078      *comps = 3;
1079      return;
1080   case MESA_FORMAT_SRGBA8:
1081   case MESA_FORMAT_SARGB8:
1082      *datatype = GL_UNSIGNED_BYTE;
1083      *comps = 4;
1084      return;
1085   case MESA_FORMAT_SL8:
1086      *datatype = GL_UNSIGNED_BYTE;
1087      *comps = 1;
1088      return;
1089   case MESA_FORMAT_SLA8:
1090      *datatype = GL_UNSIGNED_BYTE;
1091      *comps = 2;
1092      return;
1093#endif
1094
1095#if FEATURE_texture_fxt1
1096   case MESA_FORMAT_RGB_FXT1:
1097   case MESA_FORMAT_RGBA_FXT1:
1098#endif
1099#if FEATURE_texture_s3tc
1100   case MESA_FORMAT_RGB_DXT1:
1101   case MESA_FORMAT_RGBA_DXT1:
1102   case MESA_FORMAT_RGBA_DXT3:
1103   case MESA_FORMAT_RGBA_DXT5:
1104#if FEATURE_EXT_texture_sRGB
1105   case MESA_FORMAT_SRGB_DXT1:
1106   case MESA_FORMAT_SRGBA_DXT1:
1107   case MESA_FORMAT_SRGBA_DXT3:
1108   case MESA_FORMAT_SRGBA_DXT5:
1109#endif
1110      /* XXX generate error instead? */
1111      *datatype = GL_UNSIGNED_BYTE;
1112      *comps = 0;
1113      return;
1114#endif
1115
1116   case MESA_FORMAT_RGBA_FLOAT32:
1117      *datatype = GL_FLOAT;
1118      *comps = 4;
1119      return;
1120   case MESA_FORMAT_RGBA_FLOAT16:
1121      *datatype = GL_HALF_FLOAT_ARB;
1122      *comps = 4;
1123      return;
1124   case MESA_FORMAT_RGB_FLOAT32:
1125      *datatype = GL_FLOAT;
1126      *comps = 3;
1127      return;
1128   case MESA_FORMAT_RGB_FLOAT16:
1129      *datatype = GL_HALF_FLOAT_ARB;
1130      *comps = 3;
1131      return;
1132   case MESA_FORMAT_LUMINANCE_ALPHA_FLOAT32:
1133      *datatype = GL_FLOAT;
1134      *comps = 2;
1135      return;
1136   case MESA_FORMAT_LUMINANCE_ALPHA_FLOAT16:
1137      *datatype = GL_HALF_FLOAT_ARB;
1138      *comps = 2;
1139      return;
1140   case MESA_FORMAT_ALPHA_FLOAT32:
1141   case MESA_FORMAT_LUMINANCE_FLOAT32:
1142   case MESA_FORMAT_INTENSITY_FLOAT32:
1143      *datatype = GL_FLOAT;
1144      *comps = 1;
1145      return;
1146   case MESA_FORMAT_ALPHA_FLOAT16:
1147   case MESA_FORMAT_LUMINANCE_FLOAT16:
1148   case MESA_FORMAT_INTENSITY_FLOAT16:
1149      *datatype = GL_HALF_FLOAT_ARB;
1150      *comps = 1;
1151      return;
1152
1153   default:
1154      _mesa_problem(NULL, "bad format in _mesa_format_to_type_and_comps");
1155      *datatype = 0;
1156      *comps = 1;
1157   }
1158}
1159