diff options
Diffstat (limited to 'mesalib')
-rw-r--r-- | mesalib/src/mapi/glapi/gen/gl_table.py | 481 | ||||
-rw-r--r-- | mesalib/src/mesa/main/es_generator.py | 1524 | ||||
-rw-r--r-- | mesalib/src/mesa/main/formats.c | 3698 | ||||
-rw-r--r-- | mesalib/src/mesa/main/formats.h | 534 |
4 files changed, 3120 insertions, 3117 deletions
diff --git a/mesalib/src/mapi/glapi/gen/gl_table.py b/mesalib/src/mapi/glapi/gen/gl_table.py index 3f1707218..c3cc6164f 100644 --- a/mesalib/src/mapi/glapi/gen/gl_table.py +++ b/mesalib/src/mapi/glapi/gen/gl_table.py @@ -1,238 +1,243 @@ -#!/usr/bin/python2
-
-# (C) Copyright IBM Corporation 2004
-# All Rights Reserved.
-#
-# Permission is hereby granted, free of charge, to any person obtaining a
-# copy of this software and associated documentation files (the "Software"),
-# to deal in the Software without restriction, including without limitation
-# on the rights to use, copy, modify, merge, publish, distribute, sub
-# license, and/or sell copies of the Software, and to permit persons to whom
-# the Software is furnished to do so, subject to the following conditions:
-#
-# The above copyright notice and this permission notice (including the next
-# paragraph) shall be included in all copies or substantial portions of the
-# Software.
-#
-# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-# FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
-# IBM AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
-# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
-# IN THE SOFTWARE.
-#
-# Authors:
-# Ian Romanick <idr@us.ibm.com>
-
-import gl_XML
-import license
-import sys, getopt
-
-class PrintGlTable(gl_XML.gl_print_base):
- def __init__(self, es=False):
- gl_XML.gl_print_base.__init__(self)
-
- self.es = es
- self.header_tag = '_GLAPI_TABLE_H_'
- self.name = "gl_table.py (from Mesa)"
- self.license = license.bsd_license_template % ( \
-"""Copyright (C) 1999-2003 Brian Paul All Rights Reserved.
-(C) Copyright IBM Corporation 2004""", "BRIAN PAUL, IBM")
- return
-
-
- def printBody(self, api):
- for f in api.functionIterateByOffset():
- arg_string = f.get_parameter_string()
- print ' %s (GLAPIENTRYP %s)(%s); /* %d */' % (f.return_type, f.name, arg_string, f.offset)
-
-
- def printRealHeader(self):
- print '#ifndef GLAPIENTRYP'
- print '# ifndef GLAPIENTRY'
- print '# define GLAPIENTRY'
- print '# endif'
- print ''
- print '# define GLAPIENTRYP GLAPIENTRY *'
- print '#endif'
- print ''
- print ''
- print 'struct _glapi_table'
- print '{'
- return
-
-
- def printRealFooter(self):
- print '};'
- return
-
-
-class PrintRemapTable(gl_XML.gl_print_base):
- def __init__(self, es=False):
- gl_XML.gl_print_base.__init__(self)
-
- self.es = es
- self.header_tag = '_GLAPI_DISPATCH_H_'
- self.name = "gl_table.py (from Mesa)"
- self.license = license.bsd_license_template % ("(C) Copyright IBM Corporation 2005", "IBM")
- return
-
-
- def printRealHeader(self):
- print """
-/* this file should not be included directly in mesa */
-
-/**
- * \\file glapidispatch.h
- * Macros for handling GL dispatch tables.
- *
- * For each known GL function, there are 3 macros in this file. The first
- * macro is named CALL_FuncName and is used to call that GL function using
- * the specified dispatch table. The other 2 macros, called GET_FuncName
- * can SET_FuncName, are used to get and set the dispatch pointer for the
- * named function in the specified dispatch table.
- */
-"""
-
- return
-
- def printBody(self, api):
- print '#define CALL_by_offset(disp, cast, offset, parameters) \\'
- print ' (*(cast (GET_by_offset(disp, offset)))) parameters'
- print '#define GET_by_offset(disp, offset) \\'
- print ' (offset >= 0) ? (((_glapi_proc *)(disp))[offset]) : NULL'
- print '#define SET_by_offset(disp, offset, fn) \\'
- print ' do { \\'
- print ' if ( (offset) < 0 ) { \\'
- print ' /* fprintf( stderr, "[%s:%u] SET_by_offset(%p, %d, %s)!\\n", */ \\'
- print ' /* __func__, __LINE__, disp, offset, # fn); */ \\'
- print ' /* abort(); */ \\'
- print ' } \\'
- print ' else { \\'
- print ' ( (_glapi_proc *) (disp) )[offset] = (_glapi_proc) fn; \\'
- print ' } \\'
- print ' } while(0)'
- print ''
-
- functions = []
- abi_functions = []
- alias_functions = []
- count = 0
- for f in api.functionIterateByOffset():
- if not f.is_abi():
- functions.append( [f, count] )
- count += 1
- else:
- abi_functions.append( [f, -1] )
-
- if self.es:
- # remember functions with aliases
- if len(f.entry_points) > 1:
- alias_functions.append(f)
-
- print '/* total number of offsets below */'
- print '#define _gloffset_COUNT %d' % (len(abi_functions + functions))
- print ''
-
- for f, index in abi_functions:
- print '#define _gloffset_%s %d' % (f.name, f.offset)
-
- print ''
- print '#if !defined(_GLAPI_USE_REMAP_TABLE)'
- print ''
-
- for f, index in functions:
- print '#define _gloffset_%s %d' % (f.name, f.offset)
-
- print ''
- print '#else /* !_GLAPI_USE_REMAP_TABLE */'
- print ''
-
- print '#define driDispatchRemapTable_size %u' % (count)
- print 'extern int driDispatchRemapTable[ driDispatchRemapTable_size ];'
- print ''
-
- for f, index in functions:
- print '#define %s_remap_index %u' % (f.name, index)
-
- print ''
-
- for f, index in functions:
- print '#define _gloffset_%s driDispatchRemapTable[%s_remap_index]' % (f.name, f.name)
-
- print ''
- print '#endif /* _GLAPI_USE_REMAP_TABLE */'
- print ''
-
- for f, index in abi_functions + functions:
- arg_string = gl_XML.create_parameter_string( f.parameters, 0 )
-
- print 'typedef %s (GLAPIENTRYP _glptr_%s)(%s);' % (f.return_type, f.name, arg_string)
- print '#define CALL_%s(disp, parameters) \\' % (f.name)
- print ' (* GET_%s(disp)) parameters' % (f.name)
- print 'static INLINE _glptr_%s GET_%s(struct _glapi_table *disp) {' % (f.name, f.name)
- print ' return (_glptr_%s) (GET_by_offset(disp, _gloffset_%s));' % (f.name, f.name)
- print '}'
- print
- print 'static INLINE void SET_%s(struct _glapi_table *disp, %s (GLAPIENTRYP fn)(%s)) {' % (f.name, f.return_type, arg_string)
- print ' SET_by_offset(disp, _gloffset_%s, fn);' % (f.name)
- print '}'
- print
-
- if alias_functions:
- print ''
- print '/* define aliases for compatibility */'
- for f in alias_functions:
- for name in f.entry_points:
- if name != f.name:
- print '#define CALL_%s(disp, parameters) CALL_%s(disp, parameters)' % (name, f.name)
- print '#define GET_%s(disp) GET_%s(disp)' % (name, f.name)
- print '#define SET_%s(disp, fn) SET_%s(disp, fn)' % (name, f.name)
- print ''
-
- print '#if defined(_GLAPI_USE_REMAP_TABLE)'
- for f in alias_functions:
- for name in f.entry_points:
- if name != f.name:
- print '#define %s_remap_index %s_remap_index' % (name, f.name)
- print '#endif /* defined(_GLAPI_USE_REMAP_TABLE) */'
- print ''
-
- return
-
-
-def show_usage():
- print "Usage: %s [-f input_file_name] [-m mode] [-c]" % sys.argv[0]
- print " -m mode Mode can be 'table' or 'remap_table'."
- print " -c Enable compatibility with OpenGL ES."
- sys.exit(1)
-
-if __name__ == '__main__':
- file_name = "gl_API.xml"
-
- try:
- (args, trail) = getopt.getopt(sys.argv[1:], "f:m:c")
- except Exception,e:
- show_usage()
-
- mode = "table"
- es = False
- for (arg,val) in args:
- if arg == "-f":
- file_name = val
- elif arg == "-m":
- mode = val
- elif arg == "-c":
- es = True
-
- if mode == "table":
- printer = PrintGlTable(es)
- elif mode == "remap_table":
- printer = PrintRemapTable(es)
- else:
- show_usage()
-
- api = gl_XML.parse_GL_API( file_name )
-
- printer.Print( api )
+#!/usr/bin/python2 + +# (C) Copyright IBM Corporation 2004 +# All Rights Reserved. +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# on the rights to use, copy, modify, merge, publish, distribute, sub +# license, and/or sell copies of the Software, and to permit persons to whom +# the Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice (including the next +# paragraph) shall be included in all copies or substantial portions of the +# Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL +# IBM AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS +# IN THE SOFTWARE. +# +# Authors: +# Ian Romanick <idr@us.ibm.com> + +import gl_XML +import license +import sys, getopt + +class PrintGlTable(gl_XML.gl_print_base): + def __init__(self, es=False): + gl_XML.gl_print_base.__init__(self) + + self.es = es + self.header_tag = '_GLAPI_TABLE_H_' + self.name = "gl_table.py (from Mesa)" + self.license = license.bsd_license_template % ( \ +"""Copyright (C) 1999-2003 Brian Paul All Rights Reserved. +(C) Copyright IBM Corporation 2004""", "BRIAN PAUL, IBM") + return + + + def printBody(self, api): + for f in api.functionIterateByOffset(): + arg_string = f.get_parameter_string() + print ' %s (GLAPIENTRYP %s)(%s); /* %d */' % (f.return_type, f.name, arg_string, f.offset) + + + def printRealHeader(self): + print '#ifndef GLAPIENTRYP' + print '# ifndef GLAPIENTRY' + print '# define GLAPIENTRY' + print '# endif' + print '' + print '# define GLAPIENTRYP GLAPIENTRY *' + print '#endif' + print '' + print '' + print 'struct _glapi_table' + print '{' + return + + + def printRealFooter(self): + print '};' + return + + +class PrintRemapTable(gl_XML.gl_print_base): + def __init__(self, es=False): + gl_XML.gl_print_base.__init__(self) + + self.es = es + self.header_tag = '_GLAPI_DISPATCH_H_' + self.name = "gl_table.py (from Mesa)" + self.license = license.bsd_license_template % ("(C) Copyright IBM Corporation 2005", "IBM") + return + + + def printRealHeader(self): + print """ +/* this file should not be included directly in mesa */ + +/** + * \\file glapidispatch.h + * Macros for handling GL dispatch tables. + * + * For each known GL function, there are 3 macros in this file. The first + * macro is named CALL_FuncName and is used to call that GL function using + * the specified dispatch table. The other 2 macros, called GET_FuncName + * can SET_FuncName, are used to get and set the dispatch pointer for the + * named function in the specified dispatch table. + */ +""" + + return + + def printBody(self, api): + print '#define CALL_by_offset(disp, cast, offset, parameters) \\' + print ' (*(cast (GET_by_offset(disp, offset)))) parameters' + print '#define GET_by_offset(disp, offset) \\' + print ' (offset >= 0) ? (((_glapi_proc *)(disp))[offset]) : NULL' + print '#define SET_by_offset(disp, offset, fn) \\' + print ' do { \\' + print ' if ( (offset) < 0 ) { \\' + print ' /* fprintf( stderr, "[%s:%u] SET_by_offset(%p, %d, %s)!\\n", */ \\' + print ' /* __func__, __LINE__, disp, offset, # fn); */ \\' + print ' /* abort(); */ \\' + print ' } \\' + print ' else { \\' + print ' ( (_glapi_proc *) (disp) )[offset] = (_glapi_proc) fn; \\' + print ' } \\' + print ' } while(0)' + print '' + + functions = [] + abi_functions = [] + alias_functions = [] + count = 0 + for f in api.functionIterateByOffset(): + if not f.is_abi(): + functions.append( [f, count] ) + count += 1 + else: + abi_functions.append( [f, -1] ) + + if self.es: + # remember functions with aliases + if len(f.entry_points) > 1: + alias_functions.append(f) + + print '/* total number of offsets below */' + print '#define _gloffset_COUNT %d' % (len(abi_functions + functions)) + print '' + + for f, index in abi_functions: + print '#define _gloffset_%s %d' % (f.name, f.offset) + + print '' + print '#if !defined(_GLAPI_USE_REMAP_TABLE)' + print '' + + for f, index in functions: + print '#define _gloffset_%s %d' % (f.name, f.offset) + + print '' + print '#else /* !_GLAPI_USE_REMAP_TABLE */' + print '' + + print '#define driDispatchRemapTable_size %u' % (count) + print 'extern int driDispatchRemapTable[ driDispatchRemapTable_size ];' + print '' + print '#if FEATURE_remap_table' + print '#define driDispatchRemapTable remap_table' + print 'static int remap_table[driDispatchRemapTable_size];' + print '#endif' + print '' + + for f, index in functions: + print '#define %s_remap_index %u' % (f.name, index) + + print '' + + for f, index in functions: + print '#define _gloffset_%s driDispatchRemapTable[%s_remap_index]' % (f.name, f.name) + + print '' + print '#endif /* _GLAPI_USE_REMAP_TABLE */' + print '' + + for f, index in abi_functions + functions: + arg_string = gl_XML.create_parameter_string( f.parameters, 0 ) + + print 'typedef %s (GLAPIENTRYP _glptr_%s)(%s);' % (f.return_type, f.name, arg_string) + print '#define CALL_%s(disp, parameters) \\' % (f.name) + print ' (* GET_%s(disp)) parameters' % (f.name) + print 'static INLINE _glptr_%s GET_%s(struct _glapi_table *disp) {' % (f.name, f.name) + print ' return (_glptr_%s) (GET_by_offset(disp, _gloffset_%s));' % (f.name, f.name) + print '}' + print + print 'static INLINE void SET_%s(struct _glapi_table *disp, %s (GLAPIENTRYP fn)(%s)) {' % (f.name, f.return_type, arg_string) + print ' SET_by_offset(disp, _gloffset_%s, fn);' % (f.name) + print '}' + print + + if alias_functions: + print '' + print '/* define aliases for compatibility */' + for f in alias_functions: + for name in f.entry_points: + if name != f.name: + print '#define CALL_%s(disp, parameters) CALL_%s(disp, parameters)' % (name, f.name) + print '#define GET_%s(disp) GET_%s(disp)' % (name, f.name) + print '#define SET_%s(disp, fn) SET_%s(disp, fn)' % (name, f.name) + print '' + + print '#if defined(_GLAPI_USE_REMAP_TABLE)' + for f in alias_functions: + for name in f.entry_points: + if name != f.name: + print '#define %s_remap_index %s_remap_index' % (name, f.name) + print '#endif /* defined(_GLAPI_USE_REMAP_TABLE) */' + print '' + + return + + +def show_usage(): + print "Usage: %s [-f input_file_name] [-m mode] [-c]" % sys.argv[0] + print " -m mode Mode can be 'table' or 'remap_table'." + print " -c Enable compatibility with OpenGL ES." + sys.exit(1) + +if __name__ == '__main__': + file_name = "gl_API.xml" + + try: + (args, trail) = getopt.getopt(sys.argv[1:], "f:m:c") + except Exception,e: + show_usage() + + mode = "table" + es = False + for (arg,val) in args: + if arg == "-f": + file_name = val + elif arg == "-m": + mode = val + elif arg == "-c": + es = True + + if mode == "table": + printer = PrintGlTable(es) + elif mode == "remap_table": + printer = PrintRemapTable(es) + else: + show_usage() + + api = gl_XML.parse_GL_API( file_name ) + + printer.Print( api ) diff --git a/mesalib/src/mesa/main/es_generator.py b/mesalib/src/mesa/main/es_generator.py index 0776cf9a6..87d8bd316 100644 --- a/mesalib/src/mesa/main/es_generator.py +++ b/mesalib/src/mesa/main/es_generator.py @@ -1,764 +1,760 @@ -#*************************************************************************
-# Copyright 2008 Tungsten Graphics, Inc., Cedar Park, Texas.
-# All Rights Reserved.
-#
-# Permission is hereby granted, free of charge, to any person obtaining a
-# copy of this software and associated documentation files (the "Software"),
-# to deal in the Software without restriction, including without limitation
-# the rights to use, copy, modify, merge, publish, distribute, sublicense,
-# and/or sell copies of the Software, and to permit persons to whom the
-# Software is furnished to do so, subject to the following conditions:
-#
-# The above copyright notice and this permission notice shall be included
-# in all copies or substantial portions of the Software.
-#
-# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
-# OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
-# TUNGSTEN GRAPHICS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
-# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
-# OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
-# SOFTWARE.
-#*************************************************************************
-
-
-import sys, os
-import APIspecutil as apiutil
-
-# These dictionary entries are used for automatic conversion.
-# The string will be used as a format string with the conversion
-# variable.
-Converters = {
- 'GLfloat': {
- 'GLdouble': "(GLdouble) (%s)",
- 'GLfixed' : "(GLint) (%s * 65536)",
- },
- 'GLfixed': {
- 'GLfloat': "(GLfloat) (%s / 65536.0f)",
- 'GLdouble': "(GLdouble) (%s / 65536.0)",
- },
- 'GLdouble': {
- 'GLfloat': "(GLfloat) (%s)",
- 'GLfixed': "(GLfixed) (%s * 65536)",
- },
- 'GLclampf': {
- 'GLclampd': "(GLclampd) (%s)",
- 'GLclampx': "(GLclampx) (%s * 65536)",
- },
- 'GLclampx': {
- 'GLclampf': "(GLclampf) (%s / 65536.0f)",
- 'GLclampd': "(GLclampd) (%s / 65536.0)",
- },
- 'GLubyte': {
- 'GLfloat': "(GLfloat) (%s / 255.0f)",
- },
-}
-
-def GetBaseType(type):
- typeTokens = type.split(' ')
- baseType = None
- typeModifiers = []
- for t in typeTokens:
- if t in ['const', '*']:
- typeModifiers.append(t)
- else:
- baseType = t
- return (baseType, typeModifiers)
-
-def ConvertValue(value, fromType, toType):
- """Returns a string that represents the given parameter string,
- type-converted if necessary."""
-
- if not Converters.has_key(fromType):
- print >> sys.stderr, "No base converter for type '%s' found. Ignoring." % fromType
- return value
-
- if not Converters[fromType].has_key(toType):
- print >> sys.stderr, "No converter found for type '%s' to type '%s'. Ignoring." % (fromType, toType)
- return value
-
- # This part is simple. Return the proper conversion.
- conversionString = Converters[fromType][toType]
- return conversionString % value
-
-FormatStrings = {
- 'GLenum' : '0x%x',
- 'GLfloat' : '%f',
- 'GLint' : '%d',
- 'GLbitfield' : '0x%x',
-}
-def GetFormatString(type):
- if FormatStrings.has_key(type):
- return FormatStrings[type]
- else:
- return None
-
-
-######################################################################
-# Version-specific values to be used in the main script
-# header: which header file to include
-# api: what text specifies an API-level function
-VersionSpecificValues = {
- 'GLES1.1' : {
- 'description' : 'GLES1.1 functions',
- 'header' : 'GLES/gl.h',
- 'extheader' : 'GLES/glext.h',
- 'shortname' : 'es1'
- },
- 'GLES2.0': {
- 'description' : 'GLES2.0 functions',
- 'header' : 'GLES2/gl2.h',
- 'extheader' : 'GLES2/gl2ext.h',
- 'shortname' : 'es2'
- }
-}
-
-
-######################################################################
-# Main code for the script begins here.
-
-# Get the name of the program (without the directory part) for use in
-# error messages.
-program = os.path.basename(sys.argv[0])
-
-# Set default values
-verbose = 0
-functionList = "APIspec.xml"
-version = "GLES1.1"
-
-# Allow for command-line switches
-import getopt, time
-options = "hvV:S:"
-try:
- optlist, args = getopt.getopt(sys.argv[1:], options)
-except getopt.GetoptError, message:
- sys.stderr.write("%s: %s. Use -h for help.\n" % (program, message))
- sys.exit(1)
-
-for option, optarg in optlist:
- if option == "-h":
- sys.stderr.write("Usage: %s [-%s]\n" % (program, options))
- sys.stderr.write("Parse an API specification file and generate wrapper functions for a given GLES version\n")
- sys.stderr.write("-h gives help\n")
- sys.stderr.write("-v is verbose\n")
- sys.stderr.write("-V specifies GLES version to generate [%s]:\n" % version)
- for key in VersionSpecificValues.keys():
- sys.stderr.write(" %s - %s\n" % (key, VersionSpecificValues[key]['description']))
- sys.stderr.write("-S specifies API specification file to use [%s]\n" % functionList)
- sys.exit(1)
- elif option == "-v":
- verbose += 1
- elif option == "-V":
- version = optarg
- elif option == "-S":
- functionList = optarg
-
-# Beyond switches, we support no further command-line arguments
-if len(args) > 0:
- sys.stderr.write("%s: only switch arguments are supported - use -h for help\n" % program)
- sys.exit(1)
-
-# If we don't have a valid version, abort.
-if not VersionSpecificValues.has_key(version):
- sys.stderr.write("%s: version '%s' is not valid - use -h for help\n" % (program, version))
- sys.exit(1)
-
-# Grab the version-specific items we need to use
-versionHeader = VersionSpecificValues[version]['header']
-versionExtHeader = VersionSpecificValues[version]['extheader']
-shortname = VersionSpecificValues[version]['shortname']
-
-# If we get to here, we're good to go. The "version" parameter
-# directs GetDispatchedFunctions to only allow functions from
-# that "category" (version in our parlance). This allows
-# functions with different declarations in different categories
-# to exist (glTexImage2D, for example, is different between
-# GLES1 and GLES2).
-keys = apiutil.GetAllFunctions(functionList, version)
-
-allSpecials = apiutil.AllSpecials()
-
-print """/* DO NOT EDIT *************************************************
- * THIS FILE AUTOMATICALLY GENERATED BY THE %s SCRIPT
- * API specification file: %s
- * GLES version: %s
- * date: %s
- */
-""" % (program, functionList, version, time.strftime("%Y-%m-%d %H:%M:%S"))
-
-# The headers we choose are version-specific.
-print """
-#include "%s"
-#include "%s"
-#include "main/mfeatures.h"
-#include "main/compiler.h"
-#include "main/api_exec.h"
-
-#if FEATURE_%s
-
-#ifndef GLAPIENTRYP
-#define GLAPIENTRYP GL_APIENTRYP
-#endif
-""" % (versionHeader, versionExtHeader, shortname.upper())
-
-# Everyone needs these types.
-print """
-/* These types are needed for the Mesa veneer, but are not defined in
- * the standard GLES headers.
- */
-typedef double GLdouble;
-typedef double GLclampd;
-
-/* Mesa error handling requires these */
-extern void *_mesa_get_current_context(void);
-extern void _mesa_error(void *ctx, GLenum error, const char *fmtString, ... );
-"""
-
-# Finally we get to the all-important functions
-print """/*************************************************************
- * Generated functions begin here
- */
-"""
-for funcName in keys:
- if verbose > 0: sys.stderr.write("%s: processing function %s\n" % (program, funcName))
-
- # start figuring out what this function will look like.
- returnType = apiutil.ReturnType(funcName)
- props = apiutil.Properties(funcName)
- params = apiutil.Parameters(funcName)
- declarationString = apiutil.MakeDeclarationString(params)
-
- # In case of error, a function may have to return. Make
- # sure we have valid return values in this case.
- if returnType == "void":
- errorReturn = "return"
- elif returnType == "GLboolean":
- errorReturn = "return GL_FALSE"
- else:
- errorReturn = "return (%s) 0" % returnType
-
- # These are the output of this large calculation block.
- # passthroughDeclarationString: a typed set of parameters that
- # will be used to create the "extern" reference for the
- # underlying Mesa or support function. Note that as generated
- # these have an extra ", " at the beginning, which will be
- # removed before use.
- #
- # passthroughDeclarationString: an untyped list of parameters
- # that will be used to call the underlying Mesa or support
- # function (including references to converted parameters).
- # This will also be generated with an extra ", " at the
- # beginning, which will be removed before use.
- #
- # variables: C code to create any local variables determined to
- # be necessary.
- # conversionCodeOutgoing: C code to convert application parameters
- # to a necessary type before calling the underlying support code.
- # May be empty if no conversion is required.
- # conversionCodeIncoming: C code to do the converse: convert
- # values returned by underlying Mesa code to the types needed
- # by the application.
- # Note that *either* the conversionCodeIncoming will be used (for
- # generated query functions), *or* the conversionCodeOutgoing will
- # be used (for generated non-query functions), never both.
- passthroughFuncName = ""
- passthroughDeclarationString = ""
- passthroughCallString = ""
- prefixOverride = None
- variables = []
- conversionCodeOutgoing = []
- conversionCodeIncoming = []
- switchCode = []
-
- # Calculate the name of the underlying support function to call.
- # By default, the passthrough function is named _mesa_<funcName>.
- # We're allowed to override the prefix and/or the function name
- # for each function record, though. The "ConversionFunction"
- # utility is poorly named, BTW...
- if funcName in allSpecials:
- # perform checks and pass through
- funcPrefix = "_check_"
- aliasprefix = "_es_"
- else:
- funcPrefix = "_es_"
- aliasprefix = apiutil.AliasPrefix(funcName)
- alias = apiutil.ConversionFunction(funcName)
- prefixOverride = apiutil.FunctionPrefix(funcName)
- if prefixOverride != "_mesa_":
- aliasprefix = apiutil.FunctionPrefix(funcName)
- if not alias:
- # There may still be a Mesa alias for the function
- if apiutil.Alias(funcName):
- passthroughFuncName = "%s%s" % (aliasprefix, apiutil.Alias(funcName))
- else:
- passthroughFuncName = "%s%s" % (aliasprefix, funcName)
- else: # a specific alias is provided
- passthroughFuncName = "%s%s" % (aliasprefix, alias)
-
- # Look at every parameter: each one may have only specific
- # allowed values, or dependent parameters to check, or
- # variant-sized vector arrays to calculate
- for (paramName, paramType, paramMaxVecSize, paramConvertToType, paramValidValues, paramValueConversion) in params:
- # We'll need this below if we're doing conversions
- (paramBaseType, paramTypeModifiers) = GetBaseType(paramType)
-
- # Conversion management.
- # We'll handle three cases, easiest to hardest: a parameter
- # that doesn't require conversion, a scalar parameter that
- # requires conversion, and a vector parameter that requires
- # conversion.
- if paramConvertToType == None:
- # Unconverted parameters are easy, whether they're vector
- # or scalar - just add them to the call list. No conversions
- # or anything to worry about.
- passthroughDeclarationString += ", %s %s" % (paramType, paramName)
- passthroughCallString += ", %s" % paramName
-
- elif paramMaxVecSize == 0: # a scalar parameter that needs conversion
- # A scalar to hold a converted parameter
- variables.append(" %s converted_%s;" % (paramConvertToType, paramName))
-
- # Outgoing conversion depends on whether we have to conditionally
- # perform value conversion.
- if paramValueConversion == "none":
- conversionCodeOutgoing.append(" converted_%s = (%s) %s;" % (paramName, paramConvertToType, paramName))
- elif paramValueConversion == "some":
- # We'll need a conditional variable to keep track of
- # whether we're converting values or not.
- if (" int convert_%s_value = 1;" % paramName) not in variables:
- variables.append(" int convert_%s_value = 1;" % paramName)
-
- # Write code based on that conditional.
- conversionCodeOutgoing.append(" if (convert_%s_value) {" % paramName)
- conversionCodeOutgoing.append(" converted_%s = %s;" % (paramName, ConvertValue(paramName, paramBaseType, paramConvertToType)))
- conversionCodeOutgoing.append(" } else {")
- conversionCodeOutgoing.append(" converted_%s = (%s) %s;" % (paramName, paramConvertToType, paramName))
- conversionCodeOutgoing.append(" }")
- else: # paramValueConversion == "all"
- conversionCodeOutgoing.append(" converted_%s = %s;" % (paramName, ConvertValue(paramName, paramBaseType, paramConvertToType)))
-
- # Note that there can be no incoming conversion for a
- # scalar parameter; changing the scalar will only change
- # the local value, and won't ultimately change anything
- # that passes back to the application.
-
- # Call strings. The unusual " ".join() call will join the
- # array of parameter modifiers with spaces as separators.
- passthroughDeclarationString += ", %s %s %s" % (paramConvertToType, " ".join(paramTypeModifiers), paramName)
- passthroughCallString += ", converted_%s" % paramName
-
- else: # a vector parameter that needs conversion
- # We'll need an index variable for conversions
- if " register unsigned int i;" not in variables:
- variables.append(" register unsigned int i;")
-
- # This variable will hold the (possibly variant) size of
- # this array needing conversion. By default, we'll set
- # it to the maximal size (which is correct for functions
- # with a constant-sized vector parameter); for true
- # variant arrays, we'll modify it with other code.
- variables.append(" unsigned int n_%s = %d;" % (paramName, paramMaxVecSize))
-
- # This array will hold the actual converted values.
- variables.append(" %s converted_%s[%d];" % (paramConvertToType, paramName, paramMaxVecSize))
-
- # Again, we choose the conversion code based on whether we
- # have to always convert values, never convert values, or
- # conditionally convert values.
- if paramValueConversion == "none":
- conversionCodeOutgoing.append(" for (i = 0; i < n_%s; i++) {" % paramName)
- conversionCodeOutgoing.append(" converted_%s[i] = (%s) %s[i];" % (paramName, paramConvertToType, paramName))
- conversionCodeOutgoing.append(" }")
- elif paramValueConversion == "some":
- # We'll need a conditional variable to keep track of
- # whether we're converting values or not.
- if (" int convert_%s_value = 1;" % paramName) not in variables:
- variables.append(" int convert_%s_value = 1;" % paramName)
- # Write code based on that conditional.
- conversionCodeOutgoing.append(" if (convert_%s_value) {" % paramName)
- conversionCodeOutgoing.append(" for (i = 0; i < n_%s; i++) {" % paramName)
- conversionCodeOutgoing.append(" converted_%s[i] = %s;" % (paramName, ConvertValue("%s[i]" % paramName, paramBaseType, paramConvertToType)))
- conversionCodeOutgoing.append(" }")
- conversionCodeOutgoing.append(" } else {")
- conversionCodeOutgoing.append(" for (i = 0; i < n_%s; i++) {" % paramName)
- conversionCodeOutgoing.append(" converted_%s[i] = (%s) %s[i];" % (paramName, paramConvertToType, paramName))
- conversionCodeOutgoing.append(" }")
- conversionCodeOutgoing.append(" }")
- else: # paramValueConversion == "all"
- conversionCodeOutgoing.append(" for (i = 0; i < n_%s; i++) {" % paramName)
- conversionCodeOutgoing.append(" converted_%s[i] = %s;" % (paramName, ConvertValue("%s[i]" % paramName, paramBaseType, paramConvertToType)))
-
- conversionCodeOutgoing.append(" }")
-
- # If instead we need an incoming conversion (i.e. results
- # from Mesa have to be converted before handing back
- # to the application), this is it. Fortunately, we don't
- # have to worry about conditional value conversion - the
- # functions that do (e.g. glGetFixedv()) are handled
- # specially, outside this code generation.
- #
- # Whether we use incoming conversion or outgoing conversion
- # is determined later - we only ever use one or the other.
-
- if paramValueConversion == "none":
- conversionCodeIncoming.append(" for (i = 0; i < n_%s; i++) {" % paramName)
- conversionCodeIncoming.append(" %s[i] = (%s) converted_%s[i];" % (paramName, paramConvertToType, paramName))
- conversionCodeIncoming.append(" }")
- elif paramValueConversion == "some":
- # We'll need a conditional variable to keep track of
- # whether we're converting values or not.
- if (" int convert_%s_value = 1;" % paramName) not in variables:
- variables.append(" int convert_%s_value = 1;" % paramName)
-
- # Write code based on that conditional.
- conversionCodeIncoming.append(" if (convert_%s_value) {" % paramName)
- conversionCodeIncoming.append(" for (i = 0; i < n_%s; i++) {" % paramName)
- conversionCodeIncoming.append(" %s[i] = %s;" % (paramName, ConvertValue("converted_%s[i]" % paramName, paramConvertToType, paramBaseType)))
- conversionCodeIncoming.append(" }")
- conversionCodeIncoming.append(" } else {")
- conversionCodeIncoming.append(" for (i = 0; i < n_%s; i++) {" % paramName)
- conversionCodeIncoming.append(" %s[i] = (%s) converted_%s[i];" % (paramName, paramBaseType, paramName))
- conversionCodeIncoming.append(" }")
- conversionCodeIncoming.append(" }")
- else: # paramValueConversion == "all"
- conversionCodeIncoming.append(" for (i = 0; i < n_%s; i++) {" % paramName)
- conversionCodeIncoming.append(" %s[i] = %s;" % (paramName, ConvertValue("converted_%s[i]" % paramName, paramConvertToType, paramBaseType)))
- conversionCodeIncoming.append(" }")
-
- # Call strings. The unusual " ".join() call will join the
- # array of parameter modifiers with spaces as separators.
- passthroughDeclarationString += ", %s %s %s" % (paramConvertToType, " ".join(paramTypeModifiers), paramName)
- passthroughCallString += ", converted_%s" % paramName
-
- # endif conversion management
-
- # Parameter checking. If the parameter has a specific list of
- # valid values, we have to make sure that the passed-in values
- # match these, or we make an error.
- if len(paramValidValues) > 0:
- # We're about to make a big switch statement with an
- # error at the end. By default, the error is GL_INVALID_ENUM,
- # unless we find a "case" statement in the middle with a
- # non-GLenum value.
- errorDefaultCase = "GL_INVALID_ENUM"
-
- # This parameter has specific valid values. Make a big
- # switch statement to handle it. Note that the original
- # parameters are always what is checked, not the
- # converted parameters.
- switchCode.append(" switch(%s) {" % paramName)
-
- for valueIndex in range(len(paramValidValues)):
- (paramValue, dependentVecSize, dependentParamName, dependentValidValues, errorCode, valueConvert) = paramValidValues[valueIndex]
-
- # We're going to need information on the dependent param
- # as well.
- if dependentParamName:
- depParamIndex = apiutil.FindParamIndex(params, dependentParamName)
- if depParamIndex == None:
- sys.stderr.write("%s: can't find dependent param '%s' for function '%s'\n" % (program, dependentParamName, funcName))
-
- (depParamName, depParamType, depParamMaxVecSize, depParamConvertToType, depParamValidValues, depParamValueConversion) = params[depParamIndex]
- else:
- (depParamName, depParamType, depParamMaxVecSize, depParamConvertToType, depParamValidValues, depParamValueConversion) = (None, None, None, None, [], None)
-
- # This is a sneaky trick. It's valid syntax for a parameter
- # that is *not* going to be converted to be declared
- # with a dependent vector size; but in this case, the
- # dependent vector size is unused and unnecessary.
- # So check for this and ignore the dependent vector size
- # if the parameter is not going to be converted.
- if depParamConvertToType:
- usedDependentVecSize = dependentVecSize
- else:
- usedDependentVecSize = None
-
- # We'll peek ahead at the next parameter, to see whether
- # we can combine cases
- if valueIndex + 1 < len(paramValidValues) :
- (nextParamValue, nextDependentVecSize, nextDependentParamName, nextDependentValidValues, nextErrorCode, nextValueConvert) = paramValidValues[valueIndex + 1]
- if depParamConvertToType:
- usedNextDependentVecSize = nextDependentVecSize
- else:
- usedNextDependentVecSize = None
-
- # Create a case for this value. As a mnemonic,
- # if we have a dependent vector size that we're ignoring,
- # add it as a comment.
- if usedDependentVecSize == None and dependentVecSize != None:
- switchCode.append(" case %s: /* size %s */" % (paramValue, dependentVecSize))
- else:
- switchCode.append(" case %s:" % paramValue)
-
- # If this is not a GLenum case, then switch our error
- # if no value is matched to be GL_INVALID_VALUE instead
- # of GL_INVALID_ENUM. (Yes, this does get confused
- # if there are both values and GLenums in the same
- # switch statement, which shouldn't happen.)
- if paramValue[0:3] != "GL_":
- errorDefaultCase = "GL_INVALID_VALUE"
-
- # If all the remaining parameters are identical to the
- # next set, then we're done - we'll just create the
- # official code on the next pass through, and the two
- # cases will share the code.
- if valueIndex + 1 < len(paramValidValues) and usedDependentVecSize == usedNextDependentVecSize and dependentParamName == nextDependentParamName and dependentValidValues == nextDependentValidValues and errorCode == nextErrorCode and valueConvert == nextValueConvert:
- continue
-
- # Otherwise, we'll have to generate code for this case.
- # Start off with a check: if there is a dependent parameter,
- # and a list of valid values for that parameter, we need
- # to generate an error if something other than one
- # of those values is passed.
- if len(dependentValidValues) > 0:
- conditional=""
-
- # If the parameter being checked is actually an array,
- # check only its first element.
- if depParamMaxVecSize == 0:
- valueToCheck = dependentParamName
- else:
- valueToCheck = "%s[0]" % dependentParamName
-
- for v in dependentValidValues:
- conditional += " && %s != %s" % (valueToCheck, v)
- switchCode.append(" if (%s) {" % conditional[4:])
- if errorCode == None:
- errorCode = "GL_INVALID_ENUM"
- switchCode.append(' _mesa_error(_mesa_get_current_context(), %s, "gl%s(%s=0x%s)", %s);' % (errorCode, funcName, paramName, "%x", paramName))
- switchCode.append(" %s;" % errorReturn)
- switchCode.append(" }")
- # endif there are dependent valid values
-
- # The dependent parameter may require conditional
- # value conversion. If it does, and we don't want
- # to convert values, we'll have to generate code for that
- if depParamValueConversion == "some" and valueConvert == "noconvert":
- switchCode.append(" convert_%s_value = 0;" % dependentParamName)
-
- # If there's a dependent vector size for this parameter
- # that we're actually going to use (i.e. we need conversion),
- # mark it.
- if usedDependentVecSize:
- switchCode.append(" n_%s = %s;" % (dependentParamName, dependentVecSize))
-
- # In all cases, break out of the switch if any valid
- # value is found.
- switchCode.append(" break;")
-
-
- # Need a default case to catch all the other, invalid
- # parameter values. These will all generate errors.
- switchCode.append(" default:")
- if errorCode == None:
- errorCode = "GL_INVALID_ENUM"
- formatString = GetFormatString(paramType)
- if formatString == None:
- switchCode.append(' _mesa_error(_mesa_get_current_context(), %s, "gl%s(%s)");' % (errorCode, funcName, paramName))
- else:
- switchCode.append(' _mesa_error(_mesa_get_current_context(), %s, "gl%s(%s=%s)", %s);' % (errorCode, funcName, paramName, formatString, paramName))
- switchCode.append(" %s;" % errorReturn)
-
- # End of our switch code.
- switchCode.append(" }")
-
- # endfor every recognized parameter value
-
- # endfor every param
-
- # Here, the passthroughDeclarationString and passthroughCallString
- # are complete; remove the extra ", " at the front of each.
- passthroughDeclarationString = passthroughDeclarationString[2:]
- passthroughCallString = passthroughCallString[2:]
- if not passthroughDeclarationString:
- passthroughDeclarationString = "void"
-
- # The Mesa functions are scattered across all the Mesa
- # header files. The easiest way to manage declarations
- # is to create them ourselves.
- if funcName in allSpecials:
- print "/* this function is special and is defined elsewhere */"
- print "extern %s GL_APIENTRY %s(%s);" % (returnType, passthroughFuncName, passthroughDeclarationString)
-
- # A function may be a core function (i.e. it exists in
- # the core specification), a core addition (extension
- # functions added officially to the core), a required
- # extension (usually an extension for an earlier version
- # that has been officially adopted), or an optional extension.
- #
- # Core functions have a simple category (e.g. "GLES1.1");
- # we generate only a simple callback for them.
- #
- # Core additions have two category listings, one simple
- # and one compound (e.g. ["GLES1.1", "GLES1.1:OES_fixed_point"]).
- # We generate the core function, and also an extension function.
- #
- # Required extensions and implemented optional extensions
- # have a single compound category "GLES1.1:OES_point_size_array".
- # For these we generate just the extension function.
- for categorySpec in apiutil.Categories(funcName):
- compoundCategory = categorySpec.split(":")
-
- # This category isn't for us, if the base category doesn't match
- # our version
- if compoundCategory[0] != version:
- continue
-
- # Otherwise, determine if we're writing code for a core
- # function (no suffix) or an extension function.
- if len(compoundCategory) == 1:
- # This is a core function
- extensionName = None
- extensionSuffix = ""
- else:
- # This is an extension function. We'll need to append
- # the extension suffix.
- extensionName = compoundCategory[1]
- extensionSuffix = extensionName.split("_")[0]
- fullFuncName = funcPrefix + funcName + extensionSuffix
-
- # Now the generated function. The text used to mark an API-level
- # function, oddly, is version-specific.
- if extensionName:
- print "/* Extension %s */" % extensionName
-
- if (not variables and
- not switchCode and
- not conversionCodeOutgoing and
- not conversionCodeIncoming):
- # pass through directly
- print "#define %s %s" % (fullFuncName, passthroughFuncName)
- print
- continue
-
- print "static %s GL_APIENTRY %s(%s)" % (returnType, fullFuncName, declarationString)
- print "{"
-
- # Start printing our code pieces. Start with any local
- # variables we need. This unusual syntax joins the
- # lines in the variables[] array with the "\n" separator.
- if len(variables) > 0:
- print "\n".join(variables) + "\n"
-
- # If there's any sort of parameter checking or variable
- # array sizing, the switch code will contain it.
- if len(switchCode) > 0:
- print "\n".join(switchCode) + "\n"
-
- # In the case of an outgoing conversion (i.e. parameters must
- # be converted before calling the underlying Mesa function),
- # use the appropriate code.
- if "get" not in props and len(conversionCodeOutgoing) > 0:
- print "\n".join(conversionCodeOutgoing) + "\n"
-
- # Call the Mesa function. Note that there are very few functions
- # that return a value (i.e. returnType is not "void"), and that
- # none of them require incoming translation; so we're safe
- # to generate code that directly returns in those cases,
- # even though it's not completely independent.
-
- if returnType == "void":
- print " %s(%s);" % (passthroughFuncName, passthroughCallString)
- else:
- print " return %s(%s);" % (passthroughFuncName, passthroughCallString)
-
- # If the function is one that returns values (i.e. "get" in props),
- # it might return values of a different type than we need, that
- # require conversion before passing back to the application.
- if "get" in props and len(conversionCodeIncoming) > 0:
- print "\n".join(conversionCodeIncoming)
-
- # All done.
- print "}"
- print
- # end for each category provided for a function
-
-# end for each function
-
-print """
-#include "glapi/glapi.h"
-
-#if FEATURE_remap_table
-
-/* cannot include main/dispatch.h here */
-#define _GLAPI_USE_REMAP_TABLE
-#include "%sapi/main/glapidispatch.h"
-
-#define need_MESA_remap_table
-#include "%sapi/main/remap_helper.h"
-
-/* force SET_* macros to use the local remap table */
-#define driDispatchRemapTable remap_table
-static int remap_table[driDispatchRemapTable_size];
-
-static void
-init_remap_table(void)
-{
- _glthread_DECLARE_STATIC_MUTEX(mutex);
- static GLboolean initialized = GL_FALSE;
- const struct gl_function_pool_remap *remap = MESA_remap_table_functions;
- int i;
-
- _glthread_LOCK_MUTEX(mutex);
- if (initialized) {
- _glthread_UNLOCK_MUTEX(mutex);
- return;
- }
-
- for (i = 0; i < driDispatchRemapTable_size; i++) {
- GLint offset;
- const char *spec;
-
- /* sanity check */
- ASSERT(i == remap[i].remap_index);
- spec = _mesa_function_pool + remap[i].pool_index;
-
- offset = _mesa_map_function_spec(spec);
- remap_table[i] = offset;
- }
- initialized = GL_TRUE;
- _glthread_UNLOCK_MUTEX(mutex);
-}
-
-#else /* FEATURE_remap_table */
-
-/* cannot include main/dispatch.h here */
-#include "%sapi/main/glapidispatch.h"
-
-static INLINE void
-init_remap_table(void)
-{
-}
-
-#endif /* FEATURE_remap_table */
-
-struct _glapi_table *
-_mesa_create_exec_table_%s(void)
-{
- struct _glapi_table *exec;
-
- exec = _mesa_alloc_dispatch_table(_gloffset_COUNT);
- if (exec == NULL)
- return NULL;
-
- init_remap_table();
-""" % (shortname, shortname, shortname, shortname)
-
-for func in keys:
- prefix = "_es_" if func not in allSpecials else "_check_"
- for spec in apiutil.Categories(func):
- ext = spec.split(":")
- # version does not match
- if ext.pop(0) != version:
- continue
- entry = func
- if ext:
- suffix = ext[0].split("_")[0]
- entry += suffix
- print " SET_%s(exec, %s%s);" % (entry, prefix, entry)
-print ""
-print " return exec;"
-print "}"
-
-print """
-#endif /* FEATURE_%s */""" % (shortname.upper())
+#************************************************************************* +# Copyright 2008 Tungsten Graphics, Inc., Cedar Park, Texas. +# All Rights Reserved. +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# the rights to use, copy, modify, merge, publish, distribute, sublicense, +# and/or sell copies of the Software, and to permit persons to whom the +# Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included +# in all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS +# OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +# TUNGSTEN GRAPHICS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF +# OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +# SOFTWARE. +#************************************************************************* + + +import sys, os +import APIspecutil as apiutil + +# These dictionary entries are used for automatic conversion. +# The string will be used as a format string with the conversion +# variable. +Converters = { + 'GLfloat': { + 'GLdouble': "(GLdouble) (%s)", + 'GLfixed' : "(GLint) (%s * 65536)", + }, + 'GLfixed': { + 'GLfloat': "(GLfloat) (%s / 65536.0f)", + 'GLdouble': "(GLdouble) (%s / 65536.0)", + }, + 'GLdouble': { + 'GLfloat': "(GLfloat) (%s)", + 'GLfixed': "(GLfixed) (%s * 65536)", + }, + 'GLclampf': { + 'GLclampd': "(GLclampd) (%s)", + 'GLclampx': "(GLclampx) (%s * 65536)", + }, + 'GLclampx': { + 'GLclampf': "(GLclampf) (%s / 65536.0f)", + 'GLclampd': "(GLclampd) (%s / 65536.0)", + }, + 'GLubyte': { + 'GLfloat': "(GLfloat) (%s / 255.0f)", + }, +} + +def GetBaseType(type): + typeTokens = type.split(' ') + baseType = None + typeModifiers = [] + for t in typeTokens: + if t in ['const', '*']: + typeModifiers.append(t) + else: + baseType = t + return (baseType, typeModifiers) + +def ConvertValue(value, fromType, toType): + """Returns a string that represents the given parameter string, + type-converted if necessary.""" + + if not Converters.has_key(fromType): + print >> sys.stderr, "No base converter for type '%s' found. Ignoring." % fromType + return value + + if not Converters[fromType].has_key(toType): + print >> sys.stderr, "No converter found for type '%s' to type '%s'. Ignoring." % (fromType, toType) + return value + + # This part is simple. Return the proper conversion. + conversionString = Converters[fromType][toType] + return conversionString % value + +FormatStrings = { + 'GLenum' : '0x%x', + 'GLfloat' : '%f', + 'GLint' : '%d', + 'GLbitfield' : '0x%x', +} +def GetFormatString(type): + if FormatStrings.has_key(type): + return FormatStrings[type] + else: + return None + + +###################################################################### +# Version-specific values to be used in the main script +# header: which header file to include +# api: what text specifies an API-level function +VersionSpecificValues = { + 'GLES1.1' : { + 'description' : 'GLES1.1 functions', + 'header' : 'GLES/gl.h', + 'extheader' : 'GLES/glext.h', + 'shortname' : 'es1' + }, + 'GLES2.0': { + 'description' : 'GLES2.0 functions', + 'header' : 'GLES2/gl2.h', + 'extheader' : 'GLES2/gl2ext.h', + 'shortname' : 'es2' + } +} + + +###################################################################### +# Main code for the script begins here. + +# Get the name of the program (without the directory part) for use in +# error messages. +program = os.path.basename(sys.argv[0]) + +# Set default values +verbose = 0 +functionList = "APIspec.xml" +version = "GLES1.1" + +# Allow for command-line switches +import getopt, time +options = "hvV:S:" +try: + optlist, args = getopt.getopt(sys.argv[1:], options) +except getopt.GetoptError, message: + sys.stderr.write("%s: %s. Use -h for help.\n" % (program, message)) + sys.exit(1) + +for option, optarg in optlist: + if option == "-h": + sys.stderr.write("Usage: %s [-%s]\n" % (program, options)) + sys.stderr.write("Parse an API specification file and generate wrapper functions for a given GLES version\n") + sys.stderr.write("-h gives help\n") + sys.stderr.write("-v is verbose\n") + sys.stderr.write("-V specifies GLES version to generate [%s]:\n" % version) + for key in VersionSpecificValues.keys(): + sys.stderr.write(" %s - %s\n" % (key, VersionSpecificValues[key]['description'])) + sys.stderr.write("-S specifies API specification file to use [%s]\n" % functionList) + sys.exit(1) + elif option == "-v": + verbose += 1 + elif option == "-V": + version = optarg + elif option == "-S": + functionList = optarg + +# Beyond switches, we support no further command-line arguments +if len(args) > 0: + sys.stderr.write("%s: only switch arguments are supported - use -h for help\n" % program) + sys.exit(1) + +# If we don't have a valid version, abort. +if not VersionSpecificValues.has_key(version): + sys.stderr.write("%s: version '%s' is not valid - use -h for help\n" % (program, version)) + sys.exit(1) + +# Grab the version-specific items we need to use +versionHeader = VersionSpecificValues[version]['header'] +versionExtHeader = VersionSpecificValues[version]['extheader'] +shortname = VersionSpecificValues[version]['shortname'] + +# If we get to here, we're good to go. The "version" parameter +# directs GetDispatchedFunctions to only allow functions from +# that "category" (version in our parlance). This allows +# functions with different declarations in different categories +# to exist (glTexImage2D, for example, is different between +# GLES1 and GLES2). +keys = apiutil.GetAllFunctions(functionList, version) + +allSpecials = apiutil.AllSpecials() + +print """/* DO NOT EDIT ************************************************* + * THIS FILE AUTOMATICALLY GENERATED BY THE %s SCRIPT + * API specification file: %s + * GLES version: %s + * date: %s + */ +""" % (program, functionList, version, time.strftime("%Y-%m-%d %H:%M:%S")) + +# The headers we choose are version-specific. +print """ +#include "%s" +#include "%s" +#include "main/mfeatures.h" +#include "main/compiler.h" +#include "main/api_exec.h" + +#if FEATURE_%s + +#ifndef GLAPIENTRYP +#define GLAPIENTRYP GL_APIENTRYP +#endif +""" % (versionHeader, versionExtHeader, shortname.upper()) + +# Everyone needs these types. +print """ +/* These types are needed for the Mesa veneer, but are not defined in + * the standard GLES headers. + */ +typedef double GLdouble; +typedef double GLclampd; + +/* Mesa error handling requires these */ +extern void *_mesa_get_current_context(void); +extern void _mesa_error(void *ctx, GLenum error, const char *fmtString, ... ); +""" + +# Finally we get to the all-important functions +print """/************************************************************* + * Generated functions begin here + */ +""" +for funcName in keys: + if verbose > 0: sys.stderr.write("%s: processing function %s\n" % (program, funcName)) + + # start figuring out what this function will look like. + returnType = apiutil.ReturnType(funcName) + props = apiutil.Properties(funcName) + params = apiutil.Parameters(funcName) + declarationString = apiutil.MakeDeclarationString(params) + + # In case of error, a function may have to return. Make + # sure we have valid return values in this case. + if returnType == "void": + errorReturn = "return" + elif returnType == "GLboolean": + errorReturn = "return GL_FALSE" + else: + errorReturn = "return (%s) 0" % returnType + + # These are the output of this large calculation block. + # passthroughDeclarationString: a typed set of parameters that + # will be used to create the "extern" reference for the + # underlying Mesa or support function. Note that as generated + # these have an extra ", " at the beginning, which will be + # removed before use. + # + # passthroughDeclarationString: an untyped list of parameters + # that will be used to call the underlying Mesa or support + # function (including references to converted parameters). + # This will also be generated with an extra ", " at the + # beginning, which will be removed before use. + # + # variables: C code to create any local variables determined to + # be necessary. + # conversionCodeOutgoing: C code to convert application parameters + # to a necessary type before calling the underlying support code. + # May be empty if no conversion is required. + # conversionCodeIncoming: C code to do the converse: convert + # values returned by underlying Mesa code to the types needed + # by the application. + # Note that *either* the conversionCodeIncoming will be used (for + # generated query functions), *or* the conversionCodeOutgoing will + # be used (for generated non-query functions), never both. + passthroughFuncName = "" + passthroughDeclarationString = "" + passthroughCallString = "" + prefixOverride = None + variables = [] + conversionCodeOutgoing = [] + conversionCodeIncoming = [] + switchCode = [] + + # Calculate the name of the underlying support function to call. + # By default, the passthrough function is named _mesa_<funcName>. + # We're allowed to override the prefix and/or the function name + # for each function record, though. The "ConversionFunction" + # utility is poorly named, BTW... + if funcName in allSpecials: + # perform checks and pass through + funcPrefix = "_check_" + aliasprefix = "_es_" + else: + funcPrefix = "_es_" + aliasprefix = apiutil.AliasPrefix(funcName) + alias = apiutil.ConversionFunction(funcName) + prefixOverride = apiutil.FunctionPrefix(funcName) + if prefixOverride != "_mesa_": + aliasprefix = apiutil.FunctionPrefix(funcName) + if not alias: + # There may still be a Mesa alias for the function + if apiutil.Alias(funcName): + passthroughFuncName = "%s%s" % (aliasprefix, apiutil.Alias(funcName)) + else: + passthroughFuncName = "%s%s" % (aliasprefix, funcName) + else: # a specific alias is provided + passthroughFuncName = "%s%s" % (aliasprefix, alias) + + # Look at every parameter: each one may have only specific + # allowed values, or dependent parameters to check, or + # variant-sized vector arrays to calculate + for (paramName, paramType, paramMaxVecSize, paramConvertToType, paramValidValues, paramValueConversion) in params: + # We'll need this below if we're doing conversions + (paramBaseType, paramTypeModifiers) = GetBaseType(paramType) + + # Conversion management. + # We'll handle three cases, easiest to hardest: a parameter + # that doesn't require conversion, a scalar parameter that + # requires conversion, and a vector parameter that requires + # conversion. + if paramConvertToType == None: + # Unconverted parameters are easy, whether they're vector + # or scalar - just add them to the call list. No conversions + # or anything to worry about. + passthroughDeclarationString += ", %s %s" % (paramType, paramName) + passthroughCallString += ", %s" % paramName + + elif paramMaxVecSize == 0: # a scalar parameter that needs conversion + # A scalar to hold a converted parameter + variables.append(" %s converted_%s;" % (paramConvertToType, paramName)) + + # Outgoing conversion depends on whether we have to conditionally + # perform value conversion. + if paramValueConversion == "none": + conversionCodeOutgoing.append(" converted_%s = (%s) %s;" % (paramName, paramConvertToType, paramName)) + elif paramValueConversion == "some": + # We'll need a conditional variable to keep track of + # whether we're converting values or not. + if (" int convert_%s_value = 1;" % paramName) not in variables: + variables.append(" int convert_%s_value = 1;" % paramName) + + # Write code based on that conditional. + conversionCodeOutgoing.append(" if (convert_%s_value) {" % paramName) + conversionCodeOutgoing.append(" converted_%s = %s;" % (paramName, ConvertValue(paramName, paramBaseType, paramConvertToType))) + conversionCodeOutgoing.append(" } else {") + conversionCodeOutgoing.append(" converted_%s = (%s) %s;" % (paramName, paramConvertToType, paramName)) + conversionCodeOutgoing.append(" }") + else: # paramValueConversion == "all" + conversionCodeOutgoing.append(" converted_%s = %s;" % (paramName, ConvertValue(paramName, paramBaseType, paramConvertToType))) + + # Note that there can be no incoming conversion for a + # scalar parameter; changing the scalar will only change + # the local value, and won't ultimately change anything + # that passes back to the application. + + # Call strings. The unusual " ".join() call will join the + # array of parameter modifiers with spaces as separators. + passthroughDeclarationString += ", %s %s %s" % (paramConvertToType, " ".join(paramTypeModifiers), paramName) + passthroughCallString += ", converted_%s" % paramName + + else: # a vector parameter that needs conversion + # We'll need an index variable for conversions + if " register unsigned int i;" not in variables: + variables.append(" register unsigned int i;") + + # This variable will hold the (possibly variant) size of + # this array needing conversion. By default, we'll set + # it to the maximal size (which is correct for functions + # with a constant-sized vector parameter); for true + # variant arrays, we'll modify it with other code. + variables.append(" unsigned int n_%s = %d;" % (paramName, paramMaxVecSize)) + + # This array will hold the actual converted values. + variables.append(" %s converted_%s[%d];" % (paramConvertToType, paramName, paramMaxVecSize)) + + # Again, we choose the conversion code based on whether we + # have to always convert values, never convert values, or + # conditionally convert values. + if paramValueConversion == "none": + conversionCodeOutgoing.append(" for (i = 0; i < n_%s; i++) {" % paramName) + conversionCodeOutgoing.append(" converted_%s[i] = (%s) %s[i];" % (paramName, paramConvertToType, paramName)) + conversionCodeOutgoing.append(" }") + elif paramValueConversion == "some": + # We'll need a conditional variable to keep track of + # whether we're converting values or not. + if (" int convert_%s_value = 1;" % paramName) not in variables: + variables.append(" int convert_%s_value = 1;" % paramName) + # Write code based on that conditional. + conversionCodeOutgoing.append(" if (convert_%s_value) {" % paramName) + conversionCodeOutgoing.append(" for (i = 0; i < n_%s; i++) {" % paramName) + conversionCodeOutgoing.append(" converted_%s[i] = %s;" % (paramName, ConvertValue("%s[i]" % paramName, paramBaseType, paramConvertToType))) + conversionCodeOutgoing.append(" }") + conversionCodeOutgoing.append(" } else {") + conversionCodeOutgoing.append(" for (i = 0; i < n_%s; i++) {" % paramName) + conversionCodeOutgoing.append(" converted_%s[i] = (%s) %s[i];" % (paramName, paramConvertToType, paramName)) + conversionCodeOutgoing.append(" }") + conversionCodeOutgoing.append(" }") + else: # paramValueConversion == "all" + conversionCodeOutgoing.append(" for (i = 0; i < n_%s; i++) {" % paramName) + conversionCodeOutgoing.append(" converted_%s[i] = %s;" % (paramName, ConvertValue("%s[i]" % paramName, paramBaseType, paramConvertToType))) + + conversionCodeOutgoing.append(" }") + + # If instead we need an incoming conversion (i.e. results + # from Mesa have to be converted before handing back + # to the application), this is it. Fortunately, we don't + # have to worry about conditional value conversion - the + # functions that do (e.g. glGetFixedv()) are handled + # specially, outside this code generation. + # + # Whether we use incoming conversion or outgoing conversion + # is determined later - we only ever use one or the other. + + if paramValueConversion == "none": + conversionCodeIncoming.append(" for (i = 0; i < n_%s; i++) {" % paramName) + conversionCodeIncoming.append(" %s[i] = (%s) converted_%s[i];" % (paramName, paramConvertToType, paramName)) + conversionCodeIncoming.append(" }") + elif paramValueConversion == "some": + # We'll need a conditional variable to keep track of + # whether we're converting values or not. + if (" int convert_%s_value = 1;" % paramName) not in variables: + variables.append(" int convert_%s_value = 1;" % paramName) + + # Write code based on that conditional. + conversionCodeIncoming.append(" if (convert_%s_value) {" % paramName) + conversionCodeIncoming.append(" for (i = 0; i < n_%s; i++) {" % paramName) + conversionCodeIncoming.append(" %s[i] = %s;" % (paramName, ConvertValue("converted_%s[i]" % paramName, paramConvertToType, paramBaseType))) + conversionCodeIncoming.append(" }") + conversionCodeIncoming.append(" } else {") + conversionCodeIncoming.append(" for (i = 0; i < n_%s; i++) {" % paramName) + conversionCodeIncoming.append(" %s[i] = (%s) converted_%s[i];" % (paramName, paramBaseType, paramName)) + conversionCodeIncoming.append(" }") + conversionCodeIncoming.append(" }") + else: # paramValueConversion == "all" + conversionCodeIncoming.append(" for (i = 0; i < n_%s; i++) {" % paramName) + conversionCodeIncoming.append(" %s[i] = %s;" % (paramName, ConvertValue("converted_%s[i]" % paramName, paramConvertToType, paramBaseType))) + conversionCodeIncoming.append(" }") + + # Call strings. The unusual " ".join() call will join the + # array of parameter modifiers with spaces as separators. + passthroughDeclarationString += ", %s %s %s" % (paramConvertToType, " ".join(paramTypeModifiers), paramName) + passthroughCallString += ", converted_%s" % paramName + + # endif conversion management + + # Parameter checking. If the parameter has a specific list of + # valid values, we have to make sure that the passed-in values + # match these, or we make an error. + if len(paramValidValues) > 0: + # We're about to make a big switch statement with an + # error at the end. By default, the error is GL_INVALID_ENUM, + # unless we find a "case" statement in the middle with a + # non-GLenum value. + errorDefaultCase = "GL_INVALID_ENUM" + + # This parameter has specific valid values. Make a big + # switch statement to handle it. Note that the original + # parameters are always what is checked, not the + # converted parameters. + switchCode.append(" switch(%s) {" % paramName) + + for valueIndex in range(len(paramValidValues)): + (paramValue, dependentVecSize, dependentParamName, dependentValidValues, errorCode, valueConvert) = paramValidValues[valueIndex] + + # We're going to need information on the dependent param + # as well. + if dependentParamName: + depParamIndex = apiutil.FindParamIndex(params, dependentParamName) + if depParamIndex == None: + sys.stderr.write("%s: can't find dependent param '%s' for function '%s'\n" % (program, dependentParamName, funcName)) + + (depParamName, depParamType, depParamMaxVecSize, depParamConvertToType, depParamValidValues, depParamValueConversion) = params[depParamIndex] + else: + (depParamName, depParamType, depParamMaxVecSize, depParamConvertToType, depParamValidValues, depParamValueConversion) = (None, None, None, None, [], None) + + # This is a sneaky trick. It's valid syntax for a parameter + # that is *not* going to be converted to be declared + # with a dependent vector size; but in this case, the + # dependent vector size is unused and unnecessary. + # So check for this and ignore the dependent vector size + # if the parameter is not going to be converted. + if depParamConvertToType: + usedDependentVecSize = dependentVecSize + else: + usedDependentVecSize = None + + # We'll peek ahead at the next parameter, to see whether + # we can combine cases + if valueIndex + 1 < len(paramValidValues) : + (nextParamValue, nextDependentVecSize, nextDependentParamName, nextDependentValidValues, nextErrorCode, nextValueConvert) = paramValidValues[valueIndex + 1] + if depParamConvertToType: + usedNextDependentVecSize = nextDependentVecSize + else: + usedNextDependentVecSize = None + + # Create a case for this value. As a mnemonic, + # if we have a dependent vector size that we're ignoring, + # add it as a comment. + if usedDependentVecSize == None and dependentVecSize != None: + switchCode.append(" case %s: /* size %s */" % (paramValue, dependentVecSize)) + else: + switchCode.append(" case %s:" % paramValue) + + # If this is not a GLenum case, then switch our error + # if no value is matched to be GL_INVALID_VALUE instead + # of GL_INVALID_ENUM. (Yes, this does get confused + # if there are both values and GLenums in the same + # switch statement, which shouldn't happen.) + if paramValue[0:3] != "GL_": + errorDefaultCase = "GL_INVALID_VALUE" + + # If all the remaining parameters are identical to the + # next set, then we're done - we'll just create the + # official code on the next pass through, and the two + # cases will share the code. + if valueIndex + 1 < len(paramValidValues) and usedDependentVecSize == usedNextDependentVecSize and dependentParamName == nextDependentParamName and dependentValidValues == nextDependentValidValues and errorCode == nextErrorCode and valueConvert == nextValueConvert: + continue + + # Otherwise, we'll have to generate code for this case. + # Start off with a check: if there is a dependent parameter, + # and a list of valid values for that parameter, we need + # to generate an error if something other than one + # of those values is passed. + if len(dependentValidValues) > 0: + conditional="" + + # If the parameter being checked is actually an array, + # check only its first element. + if depParamMaxVecSize == 0: + valueToCheck = dependentParamName + else: + valueToCheck = "%s[0]" % dependentParamName + + for v in dependentValidValues: + conditional += " && %s != %s" % (valueToCheck, v) + switchCode.append(" if (%s) {" % conditional[4:]) + if errorCode == None: + errorCode = "GL_INVALID_ENUM" + switchCode.append(' _mesa_error(_mesa_get_current_context(), %s, "gl%s(%s=0x%s)", %s);' % (errorCode, funcName, paramName, "%x", paramName)) + switchCode.append(" %s;" % errorReturn) + switchCode.append(" }") + # endif there are dependent valid values + + # The dependent parameter may require conditional + # value conversion. If it does, and we don't want + # to convert values, we'll have to generate code for that + if depParamValueConversion == "some" and valueConvert == "noconvert": + switchCode.append(" convert_%s_value = 0;" % dependentParamName) + + # If there's a dependent vector size for this parameter + # that we're actually going to use (i.e. we need conversion), + # mark it. + if usedDependentVecSize: + switchCode.append(" n_%s = %s;" % (dependentParamName, dependentVecSize)) + + # In all cases, break out of the switch if any valid + # value is found. + switchCode.append(" break;") + + + # Need a default case to catch all the other, invalid + # parameter values. These will all generate errors. + switchCode.append(" default:") + if errorCode == None: + errorCode = "GL_INVALID_ENUM" + formatString = GetFormatString(paramType) + if formatString == None: + switchCode.append(' _mesa_error(_mesa_get_current_context(), %s, "gl%s(%s)");' % (errorCode, funcName, paramName)) + else: + switchCode.append(' _mesa_error(_mesa_get_current_context(), %s, "gl%s(%s=%s)", %s);' % (errorCode, funcName, paramName, formatString, paramName)) + switchCode.append(" %s;" % errorReturn) + + # End of our switch code. + switchCode.append(" }") + + # endfor every recognized parameter value + + # endfor every param + + # Here, the passthroughDeclarationString and passthroughCallString + # are complete; remove the extra ", " at the front of each. + passthroughDeclarationString = passthroughDeclarationString[2:] + passthroughCallString = passthroughCallString[2:] + if not passthroughDeclarationString: + passthroughDeclarationString = "void" + + # The Mesa functions are scattered across all the Mesa + # header files. The easiest way to manage declarations + # is to create them ourselves. + if funcName in allSpecials: + print "/* this function is special and is defined elsewhere */" + print "extern %s GL_APIENTRY %s(%s);" % (returnType, passthroughFuncName, passthroughDeclarationString) + + # A function may be a core function (i.e. it exists in + # the core specification), a core addition (extension + # functions added officially to the core), a required + # extension (usually an extension for an earlier version + # that has been officially adopted), or an optional extension. + # + # Core functions have a simple category (e.g. "GLES1.1"); + # we generate only a simple callback for them. + # + # Core additions have two category listings, one simple + # and one compound (e.g. ["GLES1.1", "GLES1.1:OES_fixed_point"]). + # We generate the core function, and also an extension function. + # + # Required extensions and implemented optional extensions + # have a single compound category "GLES1.1:OES_point_size_array". + # For these we generate just the extension function. + for categorySpec in apiutil.Categories(funcName): + compoundCategory = categorySpec.split(":") + + # This category isn't for us, if the base category doesn't match + # our version + if compoundCategory[0] != version: + continue + + # Otherwise, determine if we're writing code for a core + # function (no suffix) or an extension function. + if len(compoundCategory) == 1: + # This is a core function + extensionName = None + extensionSuffix = "" + else: + # This is an extension function. We'll need to append + # the extension suffix. + extensionName = compoundCategory[1] + extensionSuffix = extensionName.split("_")[0] + fullFuncName = funcPrefix + funcName + extensionSuffix + + # Now the generated function. The text used to mark an API-level + # function, oddly, is version-specific. + if extensionName: + print "/* Extension %s */" % extensionName + + if (not variables and + not switchCode and + not conversionCodeOutgoing and + not conversionCodeIncoming): + # pass through directly + print "#define %s %s" % (fullFuncName, passthroughFuncName) + print + continue + + print "static %s GL_APIENTRY %s(%s)" % (returnType, fullFuncName, declarationString) + print "{" + + # Start printing our code pieces. Start with any local + # variables we need. This unusual syntax joins the + # lines in the variables[] array with the "\n" separator. + if len(variables) > 0: + print "\n".join(variables) + "\n" + + # If there's any sort of parameter checking or variable + # array sizing, the switch code will contain it. + if len(switchCode) > 0: + print "\n".join(switchCode) + "\n" + + # In the case of an outgoing conversion (i.e. parameters must + # be converted before calling the underlying Mesa function), + # use the appropriate code. + if "get" not in props and len(conversionCodeOutgoing) > 0: + print "\n".join(conversionCodeOutgoing) + "\n" + + # Call the Mesa function. Note that there are very few functions + # that return a value (i.e. returnType is not "void"), and that + # none of them require incoming translation; so we're safe + # to generate code that directly returns in those cases, + # even though it's not completely independent. + + if returnType == "void": + print " %s(%s);" % (passthroughFuncName, passthroughCallString) + else: + print " return %s(%s);" % (passthroughFuncName, passthroughCallString) + + # If the function is one that returns values (i.e. "get" in props), + # it might return values of a different type than we need, that + # require conversion before passing back to the application. + if "get" in props and len(conversionCodeIncoming) > 0: + print "\n".join(conversionCodeIncoming) + + # All done. + print "}" + print + # end for each category provided for a function + +# end for each function + +print """ +#include "glapi/glapi.h" + +#if FEATURE_remap_table + +/* cannot include main/dispatch.h here */ +#define _GLAPI_USE_REMAP_TABLE +#include "%sapi/main/glapidispatch.h" + +#define need_MESA_remap_table +#include "%sapi/main/remap_helper.h" + +static void +init_remap_table(void) +{ + _glthread_DECLARE_STATIC_MUTEX(mutex); + static GLboolean initialized = GL_FALSE; + const struct gl_function_pool_remap *remap = MESA_remap_table_functions; + int i; + + _glthread_LOCK_MUTEX(mutex); + if (initialized) { + _glthread_UNLOCK_MUTEX(mutex); + return; + } + + for (i = 0; i < driDispatchRemapTable_size; i++) { + GLint offset; + const char *spec; + + /* sanity check */ + ASSERT(i == remap[i].remap_index); + spec = _mesa_function_pool + remap[i].pool_index; + + offset = _mesa_map_function_spec(spec); + remap_table[i] = offset; + } + initialized = GL_TRUE; + _glthread_UNLOCK_MUTEX(mutex); +} + +#else /* FEATURE_remap_table */ + +/* cannot include main/dispatch.h here */ +#include "%sapi/main/glapidispatch.h" + +static INLINE void +init_remap_table(void) +{ +} + +#endif /* FEATURE_remap_table */ + +struct _glapi_table * +_mesa_create_exec_table_%s(void) +{ + struct _glapi_table *exec; + + exec = _mesa_alloc_dispatch_table(_gloffset_COUNT); + if (exec == NULL) + return NULL; + + init_remap_table(); +""" % (shortname, shortname, shortname, shortname) + +for func in keys: + prefix = "_es_" if func not in allSpecials else "_check_" + for spec in apiutil.Categories(func): + ext = spec.split(":") + # version does not match + if ext.pop(0) != version: + continue + entry = func + if ext: + suffix = ext[0].split("_")[0] + entry += suffix + print " SET_%s(exec, %s%s);" % (entry, prefix, entry) +print "" +print " return exec;" +print "}" + +print """ +#endif /* FEATURE_%s */""" % (shortname.upper()) diff --git a/mesalib/src/mesa/main/formats.c b/mesalib/src/mesa/main/formats.c index f0f30fe0a..e88ba4397 100644 --- a/mesalib/src/mesa/main/formats.c +++ b/mesalib/src/mesa/main/formats.c @@ -1,1848 +1,1850 @@ -/*
- * Mesa 3-D graphics library
- * Version: 7.7
- *
- * Copyright (C) 1999-2008 Brian Paul All Rights Reserved.
- * Copyright (c) 2008-2009 VMware, Inc.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included
- * in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
- * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
- * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
- * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
- * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- */
-
-
-#include "imports.h"
-#include "formats.h"
-#include "mfeatures.h"
-
-
-/**
- * Information about texture formats.
- */
-struct gl_format_info
-{
- gl_format Name;
-
- /** text name for debugging */
- const char *StrName;
-
- /**
- * Base format is one of GL_RED, GL_RG, GL_RGB, GL_RGBA, GL_ALPHA,
- * GL_LUMINANCE, GL_LUMINANCE_ALPHA, GL_INTENSITY, GL_YCBCR_MESA,
- * GL_COLOR_INDEX, GL_DEPTH_COMPONENT, GL_STENCIL_INDEX,
- * GL_DEPTH_STENCIL, GL_DUDV_ATI.
- */
- GLenum BaseFormat;
-
- /**
- * Logical data type: one of GL_UNSIGNED_NORMALIZED, GL_SIGNED_NORMALED,
- * GL_UNSIGNED_INT, GL_INT, GL_FLOAT.
- */
- GLenum DataType;
-
- GLubyte RedBits;
- GLubyte GreenBits;
- GLubyte BlueBits;
- GLubyte AlphaBits;
- GLubyte LuminanceBits;
- GLubyte IntensityBits;
- GLubyte IndexBits;
- GLubyte DepthBits;
- GLubyte StencilBits;
-
- /**
- * To describe compressed formats. If not compressed, Width=Height=1.
- */
- GLubyte BlockWidth, BlockHeight;
- GLubyte BytesPerBlock;
-};
-
-
-/**
- * Info about each format.
- * These must be in the same order as the MESA_FORMAT_* enums so that
- * we can do lookups without searching.
- */
-static struct gl_format_info format_info[MESA_FORMAT_COUNT] =
-{
- {
- MESA_FORMAT_NONE, /* Name */
- "MESA_FORMAT_NONE", /* StrName */
- GL_NONE, /* BaseFormat */
- GL_NONE, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 0, 0, 0 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_RGBA8888, /* Name */
- "MESA_FORMAT_RGBA8888", /* StrName */
- GL_RGBA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 8, 8, 8, 8, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 4 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_RGBA8888_REV, /* Name */
- "MESA_FORMAT_RGBA8888_REV", /* StrName */
- GL_RGBA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 8, 8, 8, 8, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 4 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_ARGB8888, /* Name */
- "MESA_FORMAT_ARGB8888", /* StrName */
- GL_RGBA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 8, 8, 8, 8, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 4 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_ARGB8888_REV, /* Name */
- "MESA_FORMAT_ARGB8888_REV", /* StrName */
- GL_RGBA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 8, 8, 8, 8, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 4 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_XRGB8888, /* Name */
- "MESA_FORMAT_XRGB8888", /* StrName */
- GL_RGB, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 8, 8, 8, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 4 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_XRGB8888_REV, /* Name */
- "MESA_FORMAT_XRGB8888_REV", /* StrName */
- GL_RGB, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 8, 8, 8, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 4 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_RGB888, /* Name */
- "MESA_FORMAT_RGB888", /* StrName */
- GL_RGB, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 8, 8, 8, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 3 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_BGR888, /* Name */
- "MESA_FORMAT_BGR888", /* StrName */
- GL_RGB, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 8, 8, 8, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 3 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_RGB565, /* Name */
- "MESA_FORMAT_RGB565", /* StrName */
- GL_RGB, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 5, 6, 5, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_RGB565_REV, /* Name */
- "MESA_FORMAT_RGB565_REV", /* StrName */
- GL_RGB, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 5, 6, 5, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_ARGB4444, /* Name */
- "MESA_FORMAT_ARGB4444", /* StrName */
- GL_RGBA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 4, 4, 4, 4, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_ARGB4444_REV, /* Name */
- "MESA_FORMAT_ARGB4444_REV", /* StrName */
- GL_RGBA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 4, 4, 4, 4, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_RGBA5551, /* Name */
- "MESA_FORMAT_RGBA5551", /* StrName */
- GL_RGBA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 5, 5, 5, 1, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_ARGB1555, /* Name */
- "MESA_FORMAT_ARGB1555", /* StrName */
- GL_RGBA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 5, 5, 5, 1, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_ARGB1555_REV, /* Name */
- "MESA_FORMAT_ARGB1555_REV", /* StrName */
- GL_RGBA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 5, 5, 5, 1, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_AL44, /* Name */
- "MESA_FORMAT_AL44", /* StrName */
- GL_LUMINANCE_ALPHA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 0, 0, 0, 4, /* Red/Green/Blue/AlphaBits */
- 4, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 1 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_AL88, /* Name */
- "MESA_FORMAT_AL88", /* StrName */
- GL_LUMINANCE_ALPHA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 0, 0, 0, 8, /* Red/Green/Blue/AlphaBits */
- 8, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_AL88_REV, /* Name */
- "MESA_FORMAT_AL88_REV", /* StrName */
- GL_LUMINANCE_ALPHA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 0, 0, 0, 8, /* Red/Green/Blue/AlphaBits */
- 8, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_AL1616, /* Name */
- "MESA_FORMAT_AL1616", /* StrName */
- GL_LUMINANCE_ALPHA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 0, 0, 0, 16, /* Red/Green/Blue/AlphaBits */
- 16, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 4 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_AL1616_REV, /* Name */
- "MESA_FORMAT_AL1616_REV", /* StrName */
- GL_LUMINANCE_ALPHA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 0, 0, 0, 16, /* Red/Green/Blue/AlphaBits */
- 16, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 4 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_RGB332, /* Name */
- "MESA_FORMAT_RGB332", /* StrName */
- GL_RGB, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 3, 3, 2, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 1 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_A8, /* Name */
- "MESA_FORMAT_A8", /* StrName */
- GL_ALPHA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 0, 0, 0, 8, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 1 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_A16, /* Name */
- "MESA_FORMAT_A16", /* StrName */
- GL_ALPHA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 0, 0, 0, 16, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_L8, /* Name */
- "MESA_FORMAT_L8", /* StrName */
- GL_LUMINANCE, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 8, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 1 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_L16, /* Name */
- "MESA_FORMAT_L16", /* StrName */
- GL_LUMINANCE, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 16, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_I8, /* Name */
- "MESA_FORMAT_I8", /* StrName */
- GL_INTENSITY, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 8, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 1 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_I16, /* Name */
- "MESA_FORMAT_I16", /* StrName */
- GL_INTENSITY, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 16, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_CI8, /* Name */
- "MESA_FORMAT_CI8", /* StrName */
- GL_COLOR_INDEX, /* BaseFormat */
- GL_UNSIGNED_INT, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 8, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 1 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_YCBCR, /* Name */
- "MESA_FORMAT_YCBCR", /* StrName */
- GL_YCBCR_MESA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_YCBCR_REV, /* Name */
- "MESA_FORMAT_YCBCR_REV", /* StrName */
- GL_YCBCR_MESA, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_R8,
- "MESA_FORMAT_R8",
- GL_RED,
- GL_UNSIGNED_NORMALIZED,
- 8, 0, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 1
- },
- {
- MESA_FORMAT_RG88,
- "MESA_FORMAT_RG88",
- GL_RG,
- GL_UNSIGNED_NORMALIZED,
- 8, 8, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_RG88_REV,
- "MESA_FORMAT_RG88_REV",
- GL_RG,
- GL_UNSIGNED_NORMALIZED,
- 8, 8, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_R16,
- "MESA_FORMAT_R16",
- GL_RED,
- GL_UNSIGNED_NORMALIZED,
- 16, 0, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_RG1616,
- "MESA_FORMAT_RG1616",
- GL_RG,
- GL_UNSIGNED_NORMALIZED,
- 16, 16, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_RG1616_REV,
- "MESA_FORMAT_RG1616_REV",
- GL_RG,
- GL_UNSIGNED_NORMALIZED,
- 16, 16, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_ARGB2101010,
- "MESA_FORMAT_ARGB2101010",
- GL_RGBA,
- GL_UNSIGNED_NORMALIZED,
- 10, 10, 10, 2,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_Z24_S8, /* Name */
- "MESA_FORMAT_Z24_S8", /* StrName */
- GL_DEPTH_STENCIL, /* BaseFormat */
- GL_UNSIGNED_INT, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 24, 8, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 4 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_S8_Z24, /* Name */
- "MESA_FORMAT_S8_Z24", /* StrName */
- GL_DEPTH_STENCIL, /* BaseFormat */
- GL_UNSIGNED_INT, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 24, 8, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 4 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_Z16, /* Name */
- "MESA_FORMAT_Z16", /* StrName */
- GL_DEPTH_COMPONENT, /* BaseFormat */
- GL_UNSIGNED_INT, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 16, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 2 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_X8_Z24, /* Name */
- "MESA_FORMAT_X8_Z24", /* StrName */
- GL_DEPTH_COMPONENT, /* BaseFormat */
- GL_UNSIGNED_INT, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 24, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 4 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_Z24_X8, /* Name */
- "MESA_FORMAT_Z24_X8", /* StrName */
- GL_DEPTH_COMPONENT, /* BaseFormat */
- GL_UNSIGNED_INT, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 24, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 4 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_Z32, /* Name */
- "MESA_FORMAT_Z32", /* StrName */
- GL_DEPTH_COMPONENT, /* BaseFormat */
- GL_UNSIGNED_INT, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 32, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 4 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_S8, /* Name */
- "MESA_FORMAT_S8", /* StrName */
- GL_STENCIL_INDEX, /* BaseFormat */
- GL_UNSIGNED_INT, /* DataType */
- 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 8, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 1 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_SRGB8,
- "MESA_FORMAT_SRGB8",
- GL_RGB,
- GL_UNSIGNED_NORMALIZED,
- 8, 8, 8, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 3
- },
- {
- MESA_FORMAT_SRGBA8,
- "MESA_FORMAT_SRGBA8",
- GL_RGBA,
- GL_UNSIGNED_NORMALIZED,
- 8, 8, 8, 8,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_SARGB8,
- "MESA_FORMAT_SARGB8",
- GL_RGBA,
- GL_UNSIGNED_NORMALIZED,
- 8, 8, 8, 8,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_SL8,
- "MESA_FORMAT_SL8",
- GL_LUMINANCE,
- GL_UNSIGNED_NORMALIZED,
- 0, 0, 0, 0,
- 8, 0, 0, 0, 0,
- 1, 1, 1
- },
- {
- MESA_FORMAT_SLA8,
- "MESA_FORMAT_SLA8",
- GL_LUMINANCE_ALPHA,
- GL_UNSIGNED_NORMALIZED,
- 0, 0, 0, 8,
- 8, 0, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_SRGB_DXT1, /* Name */
- "MESA_FORMAT_SRGB_DXT1", /* StrName */
- GL_RGB, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 4, 4, 4, 0, /* approx Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 4, 4, 8 /* 8 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_SRGBA_DXT1,
- "MESA_FORMAT_SRGBA_DXT1",
- GL_RGBA,
- GL_UNSIGNED_NORMALIZED,
- 4, 4, 4, 4,
- 0, 0, 0, 0, 0,
- 4, 4, 8 /* 8 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_SRGBA_DXT3,
- "MESA_FORMAT_SRGBA_DXT3",
- GL_RGBA,
- GL_UNSIGNED_NORMALIZED,
- 4, 4, 4, 4,
- 0, 0, 0, 0, 0,
- 4, 4, 16 /* 16 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_SRGBA_DXT5,
- "MESA_FORMAT_SRGBA_DXT5",
- GL_RGBA,
- GL_UNSIGNED_NORMALIZED,
- 4, 4, 4, 4,
- 0, 0, 0, 0, 0,
- 4, 4, 16 /* 16 bytes per 4x4 block */
- },
-
- {
- MESA_FORMAT_RGB_FXT1,
- "MESA_FORMAT_RGB_FXT1",
- GL_RGB,
- GL_UNSIGNED_NORMALIZED,
- 4, 4, 4, 0, /* approx Red/Green/BlueBits */
- 0, 0, 0, 0, 0,
- 8, 4, 16 /* 16 bytes per 8x4 block */
- },
- {
- MESA_FORMAT_RGBA_FXT1,
- "MESA_FORMAT_RGBA_FXT1",
- GL_RGBA,
- GL_UNSIGNED_NORMALIZED,
- 4, 4, 4, 1, /* approx Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0,
- 8, 4, 16 /* 16 bytes per 8x4 block */
- },
-
- {
- MESA_FORMAT_RGB_DXT1, /* Name */
- "MESA_FORMAT_RGB_DXT1", /* StrName */
- GL_RGB, /* BaseFormat */
- GL_UNSIGNED_NORMALIZED, /* DataType */
- 4, 4, 4, 0, /* approx Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 4, 4, 8 /* 8 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_RGBA_DXT1,
- "MESA_FORMAT_RGBA_DXT1",
- GL_RGBA,
- GL_UNSIGNED_NORMALIZED,
- 4, 4, 4, 4,
- 0, 0, 0, 0, 0,
- 4, 4, 8 /* 8 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_RGBA_DXT3,
- "MESA_FORMAT_RGBA_DXT3",
- GL_RGBA,
- GL_UNSIGNED_NORMALIZED,
- 4, 4, 4, 4,
- 0, 0, 0, 0, 0,
- 4, 4, 16 /* 16 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_RGBA_DXT5,
- "MESA_FORMAT_RGBA_DXT5",
- GL_RGBA,
- GL_UNSIGNED_NORMALIZED,
- 4, 4, 4, 4,
- 0, 0, 0, 0, 0,
- 4, 4, 16 /* 16 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_RGBA_FLOAT32,
- "MESA_FORMAT_RGBA_FLOAT32",
- GL_RGBA,
- GL_FLOAT,
- 32, 32, 32, 32,
- 0, 0, 0, 0, 0,
- 1, 1, 16
- },
- {
- MESA_FORMAT_RGBA_FLOAT16,
- "MESA_FORMAT_RGBA_FLOAT16",
- GL_RGBA,
- GL_FLOAT,
- 16, 16, 16, 16,
- 0, 0, 0, 0, 0,
- 1, 1, 8
- },
- {
- MESA_FORMAT_RGB_FLOAT32,
- "MESA_FORMAT_RGB_FLOAT32",
- GL_RGB,
- GL_FLOAT,
- 32, 32, 32, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 12
- },
- {
- MESA_FORMAT_RGB_FLOAT16,
- "MESA_FORMAT_RGB_FLOAT16",
- GL_RGB,
- GL_FLOAT,
- 16, 16, 16, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 6
- },
- {
- MESA_FORMAT_ALPHA_FLOAT32,
- "MESA_FORMAT_ALPHA_FLOAT32",
- GL_ALPHA,
- GL_FLOAT,
- 0, 0, 0, 32,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_ALPHA_FLOAT16,
- "MESA_FORMAT_ALPHA_FLOAT16",
- GL_ALPHA,
- GL_FLOAT,
- 0, 0, 0, 16,
- 0, 0, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_LUMINANCE_FLOAT32,
- "MESA_FORMAT_LUMINANCE_FLOAT32",
- GL_LUMINANCE,
- GL_FLOAT,
- 0, 0, 0, 0,
- 32, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_LUMINANCE_FLOAT16,
- "MESA_FORMAT_LUMINANCE_FLOAT16",
- GL_LUMINANCE,
- GL_FLOAT,
- 0, 0, 0, 0,
- 16, 0, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_LUMINANCE_ALPHA_FLOAT32,
- "MESA_FORMAT_LUMINANCE_ALPHA_FLOAT32",
- GL_LUMINANCE_ALPHA,
- GL_FLOAT,
- 0, 0, 0, 32,
- 32, 0, 0, 0, 0,
- 1, 1, 8
- },
- {
- MESA_FORMAT_LUMINANCE_ALPHA_FLOAT16,
- "MESA_FORMAT_LUMINANCE_ALPHA_FLOAT16",
- GL_LUMINANCE_ALPHA,
- GL_FLOAT,
- 0, 0, 0, 16,
- 16, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_INTENSITY_FLOAT32,
- "MESA_FORMAT_INTENSITY_FLOAT32",
- GL_INTENSITY,
- GL_FLOAT,
- 0, 0, 0, 0,
- 0, 32, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_INTENSITY_FLOAT16,
- "MESA_FORMAT_INTENSITY_FLOAT16",
- GL_INTENSITY,
- GL_FLOAT,
- 0, 0, 0, 0,
- 0, 16, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_R_FLOAT32,
- "MESA_FORMAT_R_FLOAT32",
- GL_RED,
- GL_FLOAT,
- 32, 0, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_R_FLOAT16,
- "MESA_FORMAT_R_FLOAT16",
- GL_RED,
- GL_FLOAT,
- 16, 0, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_RG_FLOAT32,
- "MESA_FORMAT_RG_FLOAT32",
- GL_RG,
- GL_FLOAT,
- 32, 32, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 8
- },
- {
- MESA_FORMAT_RG_FLOAT16,
- "MESA_FORMAT_RG_FLOAT16",
- GL_RG,
- GL_FLOAT,
- 16, 16, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
-
- /* unnormalized signed int formats */
- {
- MESA_FORMAT_RGBA_INT8,
- "MESA_FORMAT_RGBA_INT8",
- GL_RGBA,
- GL_INT,
- 8, 8, 8, 8,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_RGBA_INT16,
- "MESA_FORMAT_RGBA_INT16",
- GL_RGBA,
- GL_INT,
- 16, 16, 16, 16,
- 0, 0, 0, 0, 0,
- 1, 1, 8
- },
- {
- MESA_FORMAT_RGBA_INT32,
- "MESA_FORMAT_RGBA_INT32",
- GL_RGBA,
- GL_INT,
- 32, 32, 32, 32,
- 0, 0, 0, 0, 0,
- 1, 1, 16
- },
-
- /* unnormalized unsigned int formats */
- {
- MESA_FORMAT_RGBA_UINT8,
- "MESA_FORMAT_RGBA_UINT8",
- GL_RGBA,
- GL_UNSIGNED_INT,
- 8, 8, 8, 8,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_RGBA_UINT16,
- "MESA_FORMAT_RGBA_UINT16",
- GL_RGBA,
- GL_UNSIGNED_INT,
- 16, 16, 16, 16,
- 0, 0, 0, 0, 0,
- 1, 1, 8
- },
- {
- MESA_FORMAT_RGBA_UINT32,
- "MESA_FORMAT_RGBA_UINT32",
- GL_RGBA,
- GL_UNSIGNED_INT,
- 32, 32, 32, 32,
- 0, 0, 0, 0, 0,
- 1, 1, 16
- },
-
-
- {
- MESA_FORMAT_DUDV8,
- "MESA_FORMAT_DUDV8",
- GL_DUDV_ATI,
- GL_SIGNED_NORMALIZED,
- 0, 0, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 2
- },
-
- /* Signed 8 bits / channel */
- {
- MESA_FORMAT_SIGNED_R8, /* Name */
- "MESA_FORMAT_SIGNED_R8", /* StrName */
- GL_RED, /* BaseFormat */
- GL_SIGNED_NORMALIZED, /* DataType */
- 8, 0, 0, 0, /* Red/Green/Blue/AlphaBits */
- 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */
- 1, 1, 1 /* BlockWidth/Height,Bytes */
- },
- {
- MESA_FORMAT_SIGNED_RG88_REV,
- "MESA_FORMAT_SIGNED_RG88_REV",
- GL_RG,
- GL_SIGNED_NORMALIZED,
- 8, 8, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_SIGNED_RGBX8888,
- "MESA_FORMAT_SIGNED_RGBX8888",
- GL_RGB,
- GL_SIGNED_NORMALIZED,
- 8, 8, 8, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 4 /* 4 bpp, but no alpha */
- },
- {
- MESA_FORMAT_SIGNED_RGBA8888,
- "MESA_FORMAT_SIGNED_RGBA8888",
- GL_RGBA,
- GL_SIGNED_NORMALIZED,
- 8, 8, 8, 8,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_SIGNED_RGBA8888_REV,
- "MESA_FORMAT_SIGNED_RGBA8888_REV",
- GL_RGBA,
- GL_SIGNED_NORMALIZED,
- 8, 8, 8, 8,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
-
- /* Signed 16 bits / channel */
- {
- MESA_FORMAT_SIGNED_R16,
- "MESA_FORMAT_SIGNED_R16",
- GL_RED,
- GL_SIGNED_NORMALIZED,
- 16, 0, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_SIGNED_GR1616,
- "MESA_FORMAT_SIGNED_GR1616",
- GL_RG,
- GL_SIGNED_NORMALIZED,
- 16, 16, 0, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_SIGNED_RGB_16,
- "MESA_FORMAT_SIGNED_RGB_16",
- GL_RGB,
- GL_SIGNED_NORMALIZED,
- 16, 16, 16, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 6
- },
- {
- MESA_FORMAT_SIGNED_RGBA_16,
- "MESA_FORMAT_SIGNED_RGBA_16",
- GL_RGBA,
- GL_SIGNED_NORMALIZED,
- 16, 16, 16, 16,
- 0, 0, 0, 0, 0,
- 1, 1, 8
- },
- {
- MESA_FORMAT_RGBA_16,
- "MESA_FORMAT_RGBA_16",
- GL_RGBA,
- GL_UNSIGNED_NORMALIZED,
- 16, 16, 16, 16,
- 0, 0, 0, 0, 0,
- 1, 1, 8
- },
- {
- MESA_FORMAT_RED_RGTC1,
- "MESA_FORMAT_RED_RGTC1",
- GL_RED,
- GL_UNSIGNED_NORMALIZED,
- 4, 0, 0, 0,
- 0, 0, 0, 0, 0,
- 4, 4, 8 /* 8 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_SIGNED_RED_RGTC1,
- "MESA_FORMAT_SIGNED_RED_RGTC1",
- GL_RED,
- GL_SIGNED_NORMALIZED,
- 4, 0, 0, 0,
- 0, 0, 0, 0, 0,
- 4, 4, 8 /* 8 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_RG_RGTC2,
- "MESA_FORMAT_RG_RGTC2",
- GL_RG,
- GL_UNSIGNED_NORMALIZED,
- 4, 4, 0, 0,
- 0, 0, 0, 0, 0,
- 4, 4, 16 /* 16 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_SIGNED_RG_RGTC2,
- "MESA_FORMAT_SIGNED_RG_RGTC2",
- GL_RG,
- GL_SIGNED_NORMALIZED,
- 4, 4, 0, 0,
- 0, 0, 0, 0, 0,
- 4, 4, 16 /* 16 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_L_LATC1,
- "MESA_FORMAT_L_LATC1",
- GL_LUMINANCE,
- GL_UNSIGNED_NORMALIZED,
- 0, 0, 0, 0,
- 4, 0, 0, 0, 0,
- 4, 4, 8 /* 8 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_SIGNED_L_LATC1,
- "MESA_FORMAT_SIGNED_L_LATC1",
- GL_LUMINANCE,
- GL_SIGNED_NORMALIZED,
- 0, 0, 0, 0,
- 4, 0, 0, 0, 0,
- 4, 4, 8 /* 8 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_LA_LATC2,
- "MESA_FORMAT_LA_LATC2",
- GL_LUMINANCE_ALPHA,
- GL_UNSIGNED_NORMALIZED,
- 0, 0, 0, 4,
- 4, 0, 0, 0, 0,
- 4, 4, 16 /* 16 bytes per 4x4 block */
- },
- {
- MESA_FORMAT_SIGNED_LA_LATC2,
- "MESA_FORMAT_SIGNED_LA_LATC2",
- GL_LUMINANCE_ALPHA,
- GL_SIGNED_NORMALIZED,
- 0, 0, 0, 4,
- 4, 0, 0, 0, 0,
- 4, 4, 16 /* 16 bytes per 4x4 block */
- },
-
- /* Signed formats from EXT_texture_snorm that are not in GL3.1 */
- {
- MESA_FORMAT_SIGNED_A8,
- "MESA_FORMAT_SIGNED_A8",
- GL_ALPHA,
- GL_SIGNED_NORMALIZED,
- 0, 0, 0, 8,
- 0, 0, 0, 0, 0,
- 1, 1, 1
- },
- {
- MESA_FORMAT_SIGNED_L8,
- "MESA_FORMAT_SIGNED_L8",
- GL_LUMINANCE,
- GL_SIGNED_NORMALIZED,
- 0, 0, 0, 0,
- 8, 0, 0, 0, 0,
- 1, 1, 1
- },
- {
- MESA_FORMAT_SIGNED_AL88,
- "MESA_FORMAT_SIGNED_AL88",
- GL_LUMINANCE_ALPHA,
- GL_SIGNED_NORMALIZED,
- 0, 0, 0, 8,
- 8, 0, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_SIGNED_I8,
- "MESA_FORMAT_SIGNED_I8",
- GL_INTENSITY,
- GL_SIGNED_NORMALIZED,
- 0, 0, 0, 0,
- 0, 8, 0, 0, 0,
- 1, 1, 1
- },
- {
- MESA_FORMAT_SIGNED_A16,
- "MESA_FORMAT_SIGNED_A16",
- GL_ALPHA,
- GL_SIGNED_NORMALIZED,
- 0, 0, 0, 16,
- 0, 0, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_SIGNED_L16,
- "MESA_FORMAT_SIGNED_L16",
- GL_LUMINANCE,
- GL_SIGNED_NORMALIZED,
- 0, 0, 0, 0,
- 16, 0, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_SIGNED_AL1616,
- "MESA_FORMAT_SIGNED_AL1616",
- GL_LUMINANCE_ALPHA,
- GL_SIGNED_NORMALIZED,
- 0, 0, 0, 16,
- 16, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_SIGNED_I16,
- "MESA_FORMAT_SIGNED_I16",
- GL_INTENSITY,
- GL_SIGNED_NORMALIZED,
- 0, 0, 0, 0,
- 0, 16, 0, 0, 0,
- 1, 1, 2
- },
- {
- MESA_FORMAT_RGB9_E5_FLOAT,
- "MESA_FORMAT_RGB9_E5",
- GL_RGB,
- GL_FLOAT,
- 9, 9, 9, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
- {
- MESA_FORMAT_R11_G11_B10_FLOAT,
- "MESA_FORMAT_R11_G11_B10_FLOAT",
- GL_RGB,
- GL_FLOAT,
- 11, 11, 10, 0,
- 0, 0, 0, 0, 0,
- 1, 1, 4
- },
-};
-
-
-
-static const struct gl_format_info *
-_mesa_get_format_info(gl_format format)
-{
- const struct gl_format_info *info = &format_info[format];
- assert(info->Name == format);
- return info;
-}
-
-
-/** Return string name of format (for debugging) */
-const char *
-_mesa_get_format_name(gl_format format)
-{
- const struct gl_format_info *info = _mesa_get_format_info(format);
- return info->StrName;
-}
-
-
-
-/**
- * Return bytes needed to store a block of pixels in the given format.
- * Normally, a block is 1x1 (a single pixel). But for compressed formats
- * a block may be 4x4 or 8x4, etc.
- */
-GLuint
-_mesa_get_format_bytes(gl_format format)
-{
- const struct gl_format_info *info = _mesa_get_format_info(format);
- ASSERT(info->BytesPerBlock);
- return info->BytesPerBlock;
-}
-
-
-/**
- * Return bits per component for the given format.
- * \param format one of MESA_FORMAT_x
- * \param pname the component, such as GL_RED_BITS, GL_TEXTURE_BLUE_BITS, etc.
- */
-GLint
-_mesa_get_format_bits(gl_format format, GLenum pname)
-{
- const struct gl_format_info *info = _mesa_get_format_info(format);
-
- switch (pname) {
- case GL_RED_BITS:
- case GL_TEXTURE_RED_SIZE:
- case GL_RENDERBUFFER_RED_SIZE_EXT:
- case GL_FRAMEBUFFER_ATTACHMENT_RED_SIZE:
- return info->RedBits;
- case GL_GREEN_BITS:
- case GL_TEXTURE_GREEN_SIZE:
- case GL_RENDERBUFFER_GREEN_SIZE_EXT:
- case GL_FRAMEBUFFER_ATTACHMENT_GREEN_SIZE:
- return info->GreenBits;
- case GL_BLUE_BITS:
- case GL_TEXTURE_BLUE_SIZE:
- case GL_RENDERBUFFER_BLUE_SIZE_EXT:
- case GL_FRAMEBUFFER_ATTACHMENT_BLUE_SIZE:
- return info->BlueBits;
- case GL_ALPHA_BITS:
- case GL_TEXTURE_ALPHA_SIZE:
- case GL_RENDERBUFFER_ALPHA_SIZE_EXT:
- case GL_FRAMEBUFFER_ATTACHMENT_ALPHA_SIZE:
- return info->AlphaBits;
- case GL_TEXTURE_INTENSITY_SIZE:
- return info->IntensityBits;
- case GL_TEXTURE_LUMINANCE_SIZE:
- return info->LuminanceBits;
- case GL_INDEX_BITS:
- case GL_TEXTURE_INDEX_SIZE_EXT:
- return info->IndexBits;
- case GL_DEPTH_BITS:
- case GL_TEXTURE_DEPTH_SIZE_ARB:
- case GL_RENDERBUFFER_DEPTH_SIZE_EXT:
- case GL_FRAMEBUFFER_ATTACHMENT_DEPTH_SIZE:
- return info->DepthBits;
- case GL_STENCIL_BITS:
- case GL_TEXTURE_STENCIL_SIZE_EXT:
- case GL_RENDERBUFFER_STENCIL_SIZE_EXT:
- case GL_FRAMEBUFFER_ATTACHMENT_STENCIL_SIZE:
- return info->StencilBits;
- default:
- _mesa_problem(NULL, "bad pname in _mesa_get_format_bits()");
- return 0;
- }
-}
-
-
-/**
- * Return the data type (or more specifically, the data representation)
- * for the given format.
- * The return value will be one of:
- * GL_UNSIGNED_NORMALIZED = unsigned int representing [0,1]
- * GL_SIGNED_NORMALIZED = signed int representing [-1, 1]
- * GL_UNSIGNED_INT = an ordinary unsigned integer
- * GL_INT = an ordinary signed integer
- * GL_FLOAT = an ordinary float
- */
-GLenum
-_mesa_get_format_datatype(gl_format format)
-{
- const struct gl_format_info *info = _mesa_get_format_info(format);
- return info->DataType;
-}
-
-
-/**
- * Return the basic format for the given type. The result will be
- * one of GL_RGB, GL_RGBA, GL_ALPHA, GL_LUMINANCE, GL_LUMINANCE_ALPHA,
- * GL_INTENSITY, GL_YCBCR_MESA, GL_COLOR_INDEX, GL_DEPTH_COMPONENT,
- * GL_STENCIL_INDEX, GL_DEPTH_STENCIL.
- */
-GLenum
-_mesa_get_format_base_format(gl_format format)
-{
- const struct gl_format_info *info = _mesa_get_format_info(format);
- return info->BaseFormat;
-}
-
-
-/**
- * Return the block size (in pixels) for the given format. Normally
- * the block size is 1x1. But compressed formats will have block sizes
- * of 4x4 or 8x4 pixels, etc.
- * \param bw returns block width in pixels
- * \param bh returns block height in pixels
- */
-void
-_mesa_get_format_block_size(gl_format format, GLuint *bw, GLuint *bh)
-{
- const struct gl_format_info *info = _mesa_get_format_info(format);
- *bw = info->BlockWidth;
- *bh = info->BlockHeight;
-}
-
-
-/** Is the given format a compressed format? */
-GLboolean
-_mesa_is_format_compressed(gl_format format)
-{
- const struct gl_format_info *info = _mesa_get_format_info(format);
- return info->BlockWidth > 1 || info->BlockHeight > 1;
-}
-
-
-/**
- * Determine if the given format represents a packed depth/stencil buffer.
- */
-GLboolean
-_mesa_is_format_packed_depth_stencil(gl_format format)
-{
- const struct gl_format_info *info = _mesa_get_format_info(format);
-
- return info->BaseFormat == GL_DEPTH_STENCIL;
-}
-
-
-/**
- * Is the given format a signed/unsigned integer color format?
- */
-GLboolean
-_mesa_is_format_integer_color(gl_format format)
-{
- const struct gl_format_info *info = _mesa_get_format_info(format);
- return (info->DataType == GL_INT || info->DataType == GL_UNSIGNED_INT) &&
- info->BaseFormat != GL_DEPTH_COMPONENT &&
- info->BaseFormat != GL_DEPTH_STENCIL &&
- info->BaseFormat != GL_STENCIL_INDEX;
-}
-
-
-/**
- * Return color encoding for given format.
- * \return GL_LINEAR or GL_SRGB
- */
-GLenum
-_mesa_get_format_color_encoding(gl_format format)
-{
- /* XXX this info should be encoded in gl_format_info */
- switch (format) {
- case MESA_FORMAT_SRGB8:
- case MESA_FORMAT_SRGBA8:
- case MESA_FORMAT_SARGB8:
- case MESA_FORMAT_SL8:
- case MESA_FORMAT_SLA8:
- case MESA_FORMAT_SRGB_DXT1:
- case MESA_FORMAT_SRGBA_DXT1:
- case MESA_FORMAT_SRGBA_DXT3:
- case MESA_FORMAT_SRGBA_DXT5:
- return GL_SRGB;
- default:
- return GL_LINEAR;
- }
-}
-
-
-/**
- * For an sRGB format, return the corresponding linear color space format.
- * For non-sRGB formats, return the format as-is.
- */
-gl_format
-_mesa_get_srgb_format_linear(gl_format format)
-{
- switch (format) {
- case MESA_FORMAT_SRGB8:
- format = MESA_FORMAT_RGB888;
- break;
- case MESA_FORMAT_SRGBA8:
- format = MESA_FORMAT_RGBA8888;
- break;
- case MESA_FORMAT_SARGB8:
- format = MESA_FORMAT_ARGB8888;
- break;
- case MESA_FORMAT_SL8:
- format = MESA_FORMAT_L8;
- break;
- case MESA_FORMAT_SLA8:
- format = MESA_FORMAT_AL88;
- break;
- case MESA_FORMAT_SRGB_DXT1:
- format = MESA_FORMAT_RGB_DXT1;
- break;
- case MESA_FORMAT_SRGBA_DXT1:
- format = MESA_FORMAT_RGBA_DXT1;
- break;
- case MESA_FORMAT_SRGBA_DXT3:
- format = MESA_FORMAT_RGBA_DXT3;
- break;
- case MESA_FORMAT_SRGBA_DXT5:
- format = MESA_FORMAT_RGBA_DXT5;
- break;
- default:
- break;
- }
- return format;
-}
-
-
-/**
- * Return number of bytes needed to store an image of the given size
- * in the given format.
- */
-GLuint
-_mesa_format_image_size(gl_format format, GLsizei width,
- GLsizei height, GLsizei depth)
-{
- const struct gl_format_info *info = _mesa_get_format_info(format);
- /* Strictly speaking, a conditional isn't needed here */
- if (info->BlockWidth > 1 || info->BlockHeight > 1) {
- /* compressed format (2D only for now) */
- const GLuint bw = info->BlockWidth, bh = info->BlockHeight;
- const GLuint wblocks = (width + bw - 1) / bw;
- const GLuint hblocks = (height + bh - 1) / bh;
- const GLuint sz = wblocks * hblocks * info->BytesPerBlock;
- assert(depth == 1);
- return sz;
- }
- else {
- /* non-compressed */
- const GLuint sz = width * height * depth * info->BytesPerBlock;
- return sz;
- }
-}
-
-
-/**
- * Same as _mesa_format_image_size() but returns a 64-bit value to
- * accomodate very large textures.
- */
-uint64_t
-_mesa_format_image_size64(gl_format format, GLsizei width,
- GLsizei height, GLsizei depth)
-{
- const struct gl_format_info *info = _mesa_get_format_info(format);
- /* Strictly speaking, a conditional isn't needed here */
- if (info->BlockWidth > 1 || info->BlockHeight > 1) {
- /* compressed format (2D only for now) */
- const uint64_t bw = info->BlockWidth, bh = info->BlockHeight;
- const uint64_t wblocks = (width + bw - 1) / bw;
- const uint64_t hblocks = (height + bh - 1) / bh;
- const uint64_t sz = wblocks * hblocks * info->BytesPerBlock;
- assert(depth == 1);
- return sz;
- }
- else {
- /* non-compressed */
- const uint64_t sz = ((uint64_t) width *
- (uint64_t) height *
- (uint64_t) depth *
- info->BytesPerBlock);
- return sz;
- }
-}
-
-
-
-GLint
-_mesa_format_row_stride(gl_format format, GLsizei width)
-{
- const struct gl_format_info *info = _mesa_get_format_info(format);
- /* Strictly speaking, a conditional isn't needed here */
- if (info->BlockWidth > 1 || info->BlockHeight > 1) {
- /* compressed format */
- const GLuint bw = info->BlockWidth;
- const GLuint wblocks = (width + bw - 1) / bw;
- const GLint stride = wblocks * info->BytesPerBlock;
- return stride;
- }
- else {
- const GLint stride = width * info->BytesPerBlock;
- return stride;
- }
-}
-
-
-/**
- * Debug/test: check that all formats are handled in the
- * _mesa_format_to_type_and_comps() function. When new pixel formats
- * are added to Mesa, that function needs to be updated.
- * This is a no-op after the first call.
- */
-static void
-check_format_to_type_and_comps(void)
-{
- gl_format f;
-
- for (f = MESA_FORMAT_NONE + 1; f < MESA_FORMAT_COUNT; f++) {
- GLenum datatype = 0;
- GLuint comps = 0;
- /* This function will emit a problem/warning if the format is
- * not handled.
- */
- _mesa_format_to_type_and_comps(f, &datatype, &comps);
- }
-}
-
-
-/**
- * Do sanity checking of the format info table.
- */
-void
-_mesa_test_formats(void)
-{
- GLuint i;
-
- assert(Elements(format_info) == MESA_FORMAT_COUNT);
-
- for (i = 0; i < MESA_FORMAT_COUNT; i++) {
- const struct gl_format_info *info = _mesa_get_format_info(i);
- assert(info);
-
- assert(info->Name == i);
-
- if (info->Name == MESA_FORMAT_NONE)
- continue;
-
- if (info->BlockWidth == 1 && info->BlockHeight == 1) {
- if (info->RedBits > 0) {
- GLuint t = info->RedBits + info->GreenBits
- + info->BlueBits + info->AlphaBits;
- assert(t / 8 <= info->BytesPerBlock);
- (void) t;
- }
- }
-
- assert(info->DataType == GL_UNSIGNED_NORMALIZED ||
- info->DataType == GL_SIGNED_NORMALIZED ||
- info->DataType == GL_UNSIGNED_INT ||
- info->DataType == GL_INT ||
- info->DataType == GL_FLOAT);
-
- if (info->BaseFormat == GL_RGB) {
- assert(info->RedBits > 0);
- assert(info->GreenBits > 0);
- assert(info->BlueBits > 0);
- assert(info->AlphaBits == 0);
- assert(info->LuminanceBits == 0);
- assert(info->IntensityBits == 0);
- }
- else if (info->BaseFormat == GL_RGBA) {
- assert(info->RedBits > 0);
- assert(info->GreenBits > 0);
- assert(info->BlueBits > 0);
- assert(info->AlphaBits > 0);
- assert(info->LuminanceBits == 0);
- assert(info->IntensityBits == 0);
- }
- else if (info->BaseFormat == GL_RG) {
- assert(info->RedBits > 0);
- assert(info->GreenBits > 0);
- assert(info->BlueBits == 0);
- assert(info->AlphaBits == 0);
- assert(info->LuminanceBits == 0);
- assert(info->IntensityBits == 0);
- }
- else if (info->BaseFormat == GL_RED) {
- assert(info->RedBits > 0);
- assert(info->GreenBits == 0);
- assert(info->BlueBits == 0);
- assert(info->AlphaBits == 0);
- assert(info->LuminanceBits == 0);
- assert(info->IntensityBits == 0);
- }
- else if (info->BaseFormat == GL_LUMINANCE) {
- assert(info->RedBits == 0);
- assert(info->GreenBits == 0);
- assert(info->BlueBits == 0);
- assert(info->AlphaBits == 0);
- assert(info->LuminanceBits > 0);
- assert(info->IntensityBits == 0);
- }
- else if (info->BaseFormat == GL_INTENSITY) {
- assert(info->RedBits == 0);
- assert(info->GreenBits == 0);
- assert(info->BlueBits == 0);
- assert(info->AlphaBits == 0);
- assert(info->LuminanceBits == 0);
- assert(info->IntensityBits > 0);
- }
- }
-
- check_format_to_type_and_comps();
-}
-
-
-
-/**
- * Return datatype and number of components per texel for the given gl_format.
- * Only used for mipmap generation code.
- */
-void
-_mesa_format_to_type_and_comps(gl_format format,
- GLenum *datatype, GLuint *comps)
-{
- switch (format) {
- case MESA_FORMAT_RGBA8888:
- case MESA_FORMAT_RGBA8888_REV:
- case MESA_FORMAT_ARGB8888:
- case MESA_FORMAT_ARGB8888_REV:
- case MESA_FORMAT_XRGB8888:
- case MESA_FORMAT_XRGB8888_REV:
- *datatype = GL_UNSIGNED_BYTE;
- *comps = 4;
- return;
- case MESA_FORMAT_RGB888:
- case MESA_FORMAT_BGR888:
- *datatype = GL_UNSIGNED_BYTE;
- *comps = 3;
- return;
- case MESA_FORMAT_RGB565:
- case MESA_FORMAT_RGB565_REV:
- *datatype = GL_UNSIGNED_SHORT_5_6_5;
- *comps = 3;
- return;
-
- case MESA_FORMAT_ARGB4444:
- case MESA_FORMAT_ARGB4444_REV:
- *datatype = GL_UNSIGNED_SHORT_4_4_4_4;
- *comps = 4;
- return;
-
- case MESA_FORMAT_ARGB1555:
- case MESA_FORMAT_ARGB1555_REV:
- *datatype = GL_UNSIGNED_SHORT_1_5_5_5_REV;
- *comps = 4;
- return;
-
- case MESA_FORMAT_ARGB2101010:
- *datatype = GL_UNSIGNED_INT_2_10_10_10_REV;
- *comps = 4;
- return;
-
- case MESA_FORMAT_RGBA5551:
- *datatype = GL_UNSIGNED_SHORT_5_5_5_1;
- *comps = 4;
- return;
-
- case MESA_FORMAT_AL44:
- *datatype = MESA_UNSIGNED_BYTE_4_4;
- *comps = 2;
- return;
-
- case MESA_FORMAT_AL88:
- case MESA_FORMAT_AL88_REV:
- case MESA_FORMAT_RG88:
- case MESA_FORMAT_RG88_REV:
- *datatype = GL_UNSIGNED_BYTE;
- *comps = 2;
- return;
-
- case MESA_FORMAT_AL1616:
- case MESA_FORMAT_AL1616_REV:
- case MESA_FORMAT_RG1616:
- case MESA_FORMAT_RG1616_REV:
- *datatype = GL_UNSIGNED_SHORT;
- *comps = 2;
- return;
-
- case MESA_FORMAT_R16:
- case MESA_FORMAT_A16:
- case MESA_FORMAT_L16:
- case MESA_FORMAT_I16:
- *datatype = GL_UNSIGNED_SHORT;
- *comps = 1;
- return;
-
- case MESA_FORMAT_RGB332:
- *datatype = GL_UNSIGNED_BYTE_3_3_2;
- *comps = 3;
- return;
-
- case MESA_FORMAT_A8:
- case MESA_FORMAT_L8:
- case MESA_FORMAT_I8:
- case MESA_FORMAT_CI8:
- case MESA_FORMAT_R8:
- case MESA_FORMAT_S8:
- *datatype = GL_UNSIGNED_BYTE;
- *comps = 1;
- return;
-
- case MESA_FORMAT_YCBCR:
- case MESA_FORMAT_YCBCR_REV:
- *datatype = GL_UNSIGNED_SHORT;
- *comps = 2;
- return;
-
- case MESA_FORMAT_Z24_S8:
- *datatype = GL_UNSIGNED_INT;
- *comps = 1; /* XXX OK? */
- return;
-
- case MESA_FORMAT_S8_Z24:
- *datatype = GL_UNSIGNED_INT;
- *comps = 1; /* XXX OK? */
- return;
-
- case MESA_FORMAT_Z16:
- *datatype = GL_UNSIGNED_SHORT;
- *comps = 1;
- return;
-
- case MESA_FORMAT_X8_Z24:
- *datatype = GL_UNSIGNED_INT;
- *comps = 1;
- return;
-
- case MESA_FORMAT_Z24_X8:
- *datatype = GL_UNSIGNED_INT;
- *comps = 1;
- return;
-
- case MESA_FORMAT_Z32:
- *datatype = GL_UNSIGNED_INT;
- *comps = 1;
- return;
-
- case MESA_FORMAT_DUDV8:
- *datatype = GL_BYTE;
- *comps = 2;
- return;
-
- case MESA_FORMAT_SIGNED_R8:
- case MESA_FORMAT_SIGNED_A8:
- case MESA_FORMAT_SIGNED_L8:
- case MESA_FORMAT_SIGNED_I8:
- *datatype = GL_BYTE;
- *comps = 1;
- return;
- case MESA_FORMAT_SIGNED_RG88_REV:
- case MESA_FORMAT_SIGNED_AL88:
- *datatype = GL_BYTE;
- *comps = 2;
- return;
- case MESA_FORMAT_SIGNED_RGBA8888:
- case MESA_FORMAT_SIGNED_RGBA8888_REV:
- case MESA_FORMAT_SIGNED_RGBX8888:
- *datatype = GL_BYTE;
- *comps = 4;
- return;
-
- case MESA_FORMAT_RGBA_16:
- *datatype = GL_UNSIGNED_SHORT;
- *comps = 4;
- return;
-
- case MESA_FORMAT_SIGNED_R16:
- case MESA_FORMAT_SIGNED_A16:
- case MESA_FORMAT_SIGNED_L16:
- case MESA_FORMAT_SIGNED_I16:
- *datatype = GL_SHORT;
- *comps = 1;
- return;
- case MESA_FORMAT_SIGNED_GR1616:
- case MESA_FORMAT_SIGNED_AL1616:
- *datatype = GL_SHORT;
- *comps = 2;
- return;
- case MESA_FORMAT_SIGNED_RGB_16:
- *datatype = GL_SHORT;
- *comps = 3;
- return;
- case MESA_FORMAT_SIGNED_RGBA_16:
- *datatype = GL_SHORT;
- *comps = 4;
- return;
-
-#if FEATURE_EXT_texture_sRGB
- case MESA_FORMAT_SRGB8:
- *datatype = GL_UNSIGNED_BYTE;
- *comps = 3;
- return;
- case MESA_FORMAT_SRGBA8:
- case MESA_FORMAT_SARGB8:
- *datatype = GL_UNSIGNED_BYTE;
- *comps = 4;
- return;
- case MESA_FORMAT_SL8:
- *datatype = GL_UNSIGNED_BYTE;
- *comps = 1;
- return;
- case MESA_FORMAT_SLA8:
- *datatype = GL_UNSIGNED_BYTE;
- *comps = 2;
- return;
-#endif
-
-#if FEATURE_texture_fxt1
- case MESA_FORMAT_RGB_FXT1:
- case MESA_FORMAT_RGBA_FXT1:
-#endif
-#if FEATURE_texture_s3tc
- case MESA_FORMAT_RGB_DXT1:
- case MESA_FORMAT_RGBA_DXT1:
- case MESA_FORMAT_RGBA_DXT3:
- case MESA_FORMAT_RGBA_DXT5:
-#if FEATURE_EXT_texture_sRGB
- case MESA_FORMAT_SRGB_DXT1:
- case MESA_FORMAT_SRGBA_DXT1:
- case MESA_FORMAT_SRGBA_DXT3:
- case MESA_FORMAT_SRGBA_DXT5:
-#endif
-#endif
- case MESA_FORMAT_RED_RGTC1:
- case MESA_FORMAT_SIGNED_RED_RGTC1:
- case MESA_FORMAT_RG_RGTC2:
- case MESA_FORMAT_SIGNED_RG_RGTC2:
- case MESA_FORMAT_L_LATC1:
- case MESA_FORMAT_SIGNED_L_LATC1:
- case MESA_FORMAT_LA_LATC2:
- case MESA_FORMAT_SIGNED_LA_LATC2:
- /* XXX generate error instead? */
- *datatype = GL_UNSIGNED_BYTE;
- *comps = 0;
- return;
-
- case MESA_FORMAT_RGBA_FLOAT32:
- *datatype = GL_FLOAT;
- *comps = 4;
- return;
- case MESA_FORMAT_RGBA_FLOAT16:
- *datatype = GL_HALF_FLOAT_ARB;
- *comps = 4;
- return;
- case MESA_FORMAT_RGB_FLOAT32:
- *datatype = GL_FLOAT;
- *comps = 3;
- return;
- case MESA_FORMAT_RGB_FLOAT16:
- *datatype = GL_HALF_FLOAT_ARB;
- *comps = 3;
- return;
- case MESA_FORMAT_LUMINANCE_ALPHA_FLOAT32:
- case MESA_FORMAT_RG_FLOAT32:
- *datatype = GL_FLOAT;
- *comps = 2;
- return;
- case MESA_FORMAT_LUMINANCE_ALPHA_FLOAT16:
- case MESA_FORMAT_RG_FLOAT16:
- *datatype = GL_HALF_FLOAT_ARB;
- *comps = 2;
- return;
- case MESA_FORMAT_ALPHA_FLOAT32:
- case MESA_FORMAT_LUMINANCE_FLOAT32:
- case MESA_FORMAT_INTENSITY_FLOAT32:
- case MESA_FORMAT_R_FLOAT32:
- *datatype = GL_FLOAT;
- *comps = 1;
- return;
- case MESA_FORMAT_ALPHA_FLOAT16:
- case MESA_FORMAT_LUMINANCE_FLOAT16:
- case MESA_FORMAT_INTENSITY_FLOAT16:
- case MESA_FORMAT_R_FLOAT16:
- *datatype = GL_HALF_FLOAT_ARB;
- *comps = 1;
- return;
-
- case MESA_FORMAT_RGBA_INT8:
- *datatype = GL_BYTE;
- *comps = 4;
- return;
- case MESA_FORMAT_RGBA_INT16:
- *datatype = GL_SHORT;
- *comps = 4;
- return;
- case MESA_FORMAT_RGBA_INT32:
- *datatype = GL_INT;
- *comps = 4;
- return;
-
- /**
- * \name Non-normalized unsigned integer formats.
- */
- case MESA_FORMAT_RGBA_UINT8:
- *datatype = GL_UNSIGNED_BYTE;
- *comps = 4;
- return;
- case MESA_FORMAT_RGBA_UINT16:
- *datatype = GL_UNSIGNED_SHORT;
- *comps = 4;
- return;
- case MESA_FORMAT_RGBA_UINT32:
- *datatype = GL_UNSIGNED_INT;
- *comps = 4;
- return;
-
- case MESA_FORMAT_RGB9_E5_FLOAT:
- *datatype = GL_UNSIGNED_INT_5_9_9_9_REV;
- *comps = 3;
- return;
-
- case MESA_FORMAT_R11_G11_B10_FLOAT:
- *datatype = GL_UNSIGNED_INT_10F_11F_11F_REV;
- *comps = 3;
- return;
-
- case MESA_FORMAT_COUNT:
- assert(0);
- return;
-
- case MESA_FORMAT_NONE:
- /* For debug builds, warn if any formats are not handled */
-#ifdef DEBUG
- default:
-#endif
- _mesa_problem(NULL, "bad format %s in _mesa_format_to_type_and_comps",
- _mesa_get_format_name(format));
- *datatype = 0;
- *comps = 1;
- }
-}
+/* + * Mesa 3-D graphics library + * Version: 7.7 + * + * Copyright (C) 1999-2008 Brian Paul All Rights Reserved. + * Copyright (c) 2008-2009 VMware, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN + * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + */ + + +#include "imports.h" +#include "formats.h" +#include "mfeatures.h" + + +/** + * Information about texture formats. + */ +struct gl_format_info +{ + gl_format Name; + + /** text name for debugging */ + const char *StrName; + + /** + * Base format is one of GL_RED, GL_RG, GL_RGB, GL_RGBA, GL_ALPHA, + * GL_LUMINANCE, GL_LUMINANCE_ALPHA, GL_INTENSITY, GL_YCBCR_MESA, + * GL_COLOR_INDEX, GL_DEPTH_COMPONENT, GL_STENCIL_INDEX, + * GL_DEPTH_STENCIL, GL_DUDV_ATI. + */ + GLenum BaseFormat; + + /** + * Logical data type: one of GL_UNSIGNED_NORMALIZED, GL_SIGNED_NORMALED, + * GL_UNSIGNED_INT, GL_INT, GL_FLOAT. + */ + GLenum DataType; + + GLubyte RedBits; + GLubyte GreenBits; + GLubyte BlueBits; + GLubyte AlphaBits; + GLubyte LuminanceBits; + GLubyte IntensityBits; + GLubyte IndexBits; + GLubyte DepthBits; + GLubyte StencilBits; + + /** + * To describe compressed formats. If not compressed, Width=Height=1. + */ + GLubyte BlockWidth, BlockHeight; + GLubyte BytesPerBlock; +}; + + +/** + * Info about each format. + * These must be in the same order as the MESA_FORMAT_* enums so that + * we can do lookups without searching. + */ +static struct gl_format_info format_info[MESA_FORMAT_COUNT] = +{ + { + MESA_FORMAT_NONE, /* Name */ + "MESA_FORMAT_NONE", /* StrName */ + GL_NONE, /* BaseFormat */ + GL_NONE, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 0, 0, 0 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_RGBA8888, /* Name */ + "MESA_FORMAT_RGBA8888", /* StrName */ + GL_RGBA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 8, 8, 8, 8, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 4 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_RGBA8888_REV, /* Name */ + "MESA_FORMAT_RGBA8888_REV", /* StrName */ + GL_RGBA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 8, 8, 8, 8, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 4 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_ARGB8888, /* Name */ + "MESA_FORMAT_ARGB8888", /* StrName */ + GL_RGBA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 8, 8, 8, 8, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 4 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_ARGB8888_REV, /* Name */ + "MESA_FORMAT_ARGB8888_REV", /* StrName */ + GL_RGBA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 8, 8, 8, 8, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 4 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_XRGB8888, /* Name */ + "MESA_FORMAT_XRGB8888", /* StrName */ + GL_RGB, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 8, 8, 8, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 4 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_XRGB8888_REV, /* Name */ + "MESA_FORMAT_XRGB8888_REV", /* StrName */ + GL_RGB, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 8, 8, 8, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 4 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_RGB888, /* Name */ + "MESA_FORMAT_RGB888", /* StrName */ + GL_RGB, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 8, 8, 8, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 3 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_BGR888, /* Name */ + "MESA_FORMAT_BGR888", /* StrName */ + GL_RGB, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 8, 8, 8, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 3 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_RGB565, /* Name */ + "MESA_FORMAT_RGB565", /* StrName */ + GL_RGB, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 5, 6, 5, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_RGB565_REV, /* Name */ + "MESA_FORMAT_RGB565_REV", /* StrName */ + GL_RGB, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 5, 6, 5, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_ARGB4444, /* Name */ + "MESA_FORMAT_ARGB4444", /* StrName */ + GL_RGBA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 4, 4, 4, 4, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_ARGB4444_REV, /* Name */ + "MESA_FORMAT_ARGB4444_REV", /* StrName */ + GL_RGBA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 4, 4, 4, 4, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_RGBA5551, /* Name */ + "MESA_FORMAT_RGBA5551", /* StrName */ + GL_RGBA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 5, 5, 5, 1, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_ARGB1555, /* Name */ + "MESA_FORMAT_ARGB1555", /* StrName */ + GL_RGBA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 5, 5, 5, 1, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_ARGB1555_REV, /* Name */ + "MESA_FORMAT_ARGB1555_REV", /* StrName */ + GL_RGBA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 5, 5, 5, 1, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_AL44, /* Name */ + "MESA_FORMAT_AL44", /* StrName */ + GL_LUMINANCE_ALPHA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 0, 0, 0, 4, /* Red/Green/Blue/AlphaBits */ + 4, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 1 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_AL88, /* Name */ + "MESA_FORMAT_AL88", /* StrName */ + GL_LUMINANCE_ALPHA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 0, 0, 0, 8, /* Red/Green/Blue/AlphaBits */ + 8, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_AL88_REV, /* Name */ + "MESA_FORMAT_AL88_REV", /* StrName */ + GL_LUMINANCE_ALPHA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 0, 0, 0, 8, /* Red/Green/Blue/AlphaBits */ + 8, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_AL1616, /* Name */ + "MESA_FORMAT_AL1616", /* StrName */ + GL_LUMINANCE_ALPHA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 0, 0, 0, 16, /* Red/Green/Blue/AlphaBits */ + 16, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 4 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_AL1616_REV, /* Name */ + "MESA_FORMAT_AL1616_REV", /* StrName */ + GL_LUMINANCE_ALPHA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 0, 0, 0, 16, /* Red/Green/Blue/AlphaBits */ + 16, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 4 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_RGB332, /* Name */ + "MESA_FORMAT_RGB332", /* StrName */ + GL_RGB, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 3, 3, 2, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 1 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_A8, /* Name */ + "MESA_FORMAT_A8", /* StrName */ + GL_ALPHA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 0, 0, 0, 8, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 1 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_A16, /* Name */ + "MESA_FORMAT_A16", /* StrName */ + GL_ALPHA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 0, 0, 0, 16, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_L8, /* Name */ + "MESA_FORMAT_L8", /* StrName */ + GL_LUMINANCE, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 8, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 1 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_L16, /* Name */ + "MESA_FORMAT_L16", /* StrName */ + GL_LUMINANCE, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 16, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_I8, /* Name */ + "MESA_FORMAT_I8", /* StrName */ + GL_INTENSITY, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 8, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 1 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_I16, /* Name */ + "MESA_FORMAT_I16", /* StrName */ + GL_INTENSITY, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 16, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_CI8, /* Name */ + "MESA_FORMAT_CI8", /* StrName */ + GL_COLOR_INDEX, /* BaseFormat */ + GL_UNSIGNED_INT, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 8, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 1 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_YCBCR, /* Name */ + "MESA_FORMAT_YCBCR", /* StrName */ + GL_YCBCR_MESA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_YCBCR_REV, /* Name */ + "MESA_FORMAT_YCBCR_REV", /* StrName */ + GL_YCBCR_MESA, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_R8, + "MESA_FORMAT_R8", + GL_RED, + GL_UNSIGNED_NORMALIZED, + 8, 0, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 1 + }, + { + MESA_FORMAT_RG88, + "MESA_FORMAT_RG88", + GL_RG, + GL_UNSIGNED_NORMALIZED, + 8, 8, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_RG88_REV, + "MESA_FORMAT_RG88_REV", + GL_RG, + GL_UNSIGNED_NORMALIZED, + 8, 8, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_R16, + "MESA_FORMAT_R16", + GL_RED, + GL_UNSIGNED_NORMALIZED, + 16, 0, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_RG1616, + "MESA_FORMAT_RG1616", + GL_RG, + GL_UNSIGNED_NORMALIZED, + 16, 16, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_RG1616_REV, + "MESA_FORMAT_RG1616_REV", + GL_RG, + GL_UNSIGNED_NORMALIZED, + 16, 16, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_ARGB2101010, + "MESA_FORMAT_ARGB2101010", + GL_RGBA, + GL_UNSIGNED_NORMALIZED, + 10, 10, 10, 2, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_Z24_S8, /* Name */ + "MESA_FORMAT_Z24_S8", /* StrName */ + GL_DEPTH_STENCIL, /* BaseFormat */ + GL_UNSIGNED_INT, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 24, 8, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 4 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_S8_Z24, /* Name */ + "MESA_FORMAT_S8_Z24", /* StrName */ + GL_DEPTH_STENCIL, /* BaseFormat */ + GL_UNSIGNED_INT, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 24, 8, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 4 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_Z16, /* Name */ + "MESA_FORMAT_Z16", /* StrName */ + GL_DEPTH_COMPONENT, /* BaseFormat */ + GL_UNSIGNED_INT, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 16, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 2 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_X8_Z24, /* Name */ + "MESA_FORMAT_X8_Z24", /* StrName */ + GL_DEPTH_COMPONENT, /* BaseFormat */ + GL_UNSIGNED_INT, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 24, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 4 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_Z24_X8, /* Name */ + "MESA_FORMAT_Z24_X8", /* StrName */ + GL_DEPTH_COMPONENT, /* BaseFormat */ + GL_UNSIGNED_INT, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 24, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 4 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_Z32, /* Name */ + "MESA_FORMAT_Z32", /* StrName */ + GL_DEPTH_COMPONENT, /* BaseFormat */ + GL_UNSIGNED_INT, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 32, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 4 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_S8, /* Name */ + "MESA_FORMAT_S8", /* StrName */ + GL_STENCIL_INDEX, /* BaseFormat */ + GL_UNSIGNED_INT, /* DataType */ + 0, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 8, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 1 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_SRGB8, + "MESA_FORMAT_SRGB8", + GL_RGB, + GL_UNSIGNED_NORMALIZED, + 8, 8, 8, 0, + 0, 0, 0, 0, 0, + 1, 1, 3 + }, + { + MESA_FORMAT_SRGBA8, + "MESA_FORMAT_SRGBA8", + GL_RGBA, + GL_UNSIGNED_NORMALIZED, + 8, 8, 8, 8, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_SARGB8, + "MESA_FORMAT_SARGB8", + GL_RGBA, + GL_UNSIGNED_NORMALIZED, + 8, 8, 8, 8, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_SL8, + "MESA_FORMAT_SL8", + GL_LUMINANCE, + GL_UNSIGNED_NORMALIZED, + 0, 0, 0, 0, + 8, 0, 0, 0, 0, + 1, 1, 1 + }, + { + MESA_FORMAT_SLA8, + "MESA_FORMAT_SLA8", + GL_LUMINANCE_ALPHA, + GL_UNSIGNED_NORMALIZED, + 0, 0, 0, 8, + 8, 0, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_SRGB_DXT1, /* Name */ + "MESA_FORMAT_SRGB_DXT1", /* StrName */ + GL_RGB, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 4, 4, 4, 0, /* approx Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 4, 4, 8 /* 8 bytes per 4x4 block */ + }, + { + MESA_FORMAT_SRGBA_DXT1, + "MESA_FORMAT_SRGBA_DXT1", + GL_RGBA, + GL_UNSIGNED_NORMALIZED, + 4, 4, 4, 4, + 0, 0, 0, 0, 0, + 4, 4, 8 /* 8 bytes per 4x4 block */ + }, + { + MESA_FORMAT_SRGBA_DXT3, + "MESA_FORMAT_SRGBA_DXT3", + GL_RGBA, + GL_UNSIGNED_NORMALIZED, + 4, 4, 4, 4, + 0, 0, 0, 0, 0, + 4, 4, 16 /* 16 bytes per 4x4 block */ + }, + { + MESA_FORMAT_SRGBA_DXT5, + "MESA_FORMAT_SRGBA_DXT5", + GL_RGBA, + GL_UNSIGNED_NORMALIZED, + 4, 4, 4, 4, + 0, 0, 0, 0, 0, + 4, 4, 16 /* 16 bytes per 4x4 block */ + }, + + { + MESA_FORMAT_RGB_FXT1, + "MESA_FORMAT_RGB_FXT1", + GL_RGB, + GL_UNSIGNED_NORMALIZED, + 4, 4, 4, 0, /* approx Red/Green/BlueBits */ + 0, 0, 0, 0, 0, + 8, 4, 16 /* 16 bytes per 8x4 block */ + }, + { + MESA_FORMAT_RGBA_FXT1, + "MESA_FORMAT_RGBA_FXT1", + GL_RGBA, + GL_UNSIGNED_NORMALIZED, + 4, 4, 4, 1, /* approx Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, + 8, 4, 16 /* 16 bytes per 8x4 block */ + }, + + { + MESA_FORMAT_RGB_DXT1, /* Name */ + "MESA_FORMAT_RGB_DXT1", /* StrName */ + GL_RGB, /* BaseFormat */ + GL_UNSIGNED_NORMALIZED, /* DataType */ + 4, 4, 4, 0, /* approx Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 4, 4, 8 /* 8 bytes per 4x4 block */ + }, + { + MESA_FORMAT_RGBA_DXT1, + "MESA_FORMAT_RGBA_DXT1", + GL_RGBA, + GL_UNSIGNED_NORMALIZED, + 4, 4, 4, 4, + 0, 0, 0, 0, 0, + 4, 4, 8 /* 8 bytes per 4x4 block */ + }, + { + MESA_FORMAT_RGBA_DXT3, + "MESA_FORMAT_RGBA_DXT3", + GL_RGBA, + GL_UNSIGNED_NORMALIZED, + 4, 4, 4, 4, + 0, 0, 0, 0, 0, + 4, 4, 16 /* 16 bytes per 4x4 block */ + }, + { + MESA_FORMAT_RGBA_DXT5, + "MESA_FORMAT_RGBA_DXT5", + GL_RGBA, + GL_UNSIGNED_NORMALIZED, + 4, 4, 4, 4, + 0, 0, 0, 0, 0, + 4, 4, 16 /* 16 bytes per 4x4 block */ + }, + { + MESA_FORMAT_RGBA_FLOAT32, + "MESA_FORMAT_RGBA_FLOAT32", + GL_RGBA, + GL_FLOAT, + 32, 32, 32, 32, + 0, 0, 0, 0, 0, + 1, 1, 16 + }, + { + MESA_FORMAT_RGBA_FLOAT16, + "MESA_FORMAT_RGBA_FLOAT16", + GL_RGBA, + GL_FLOAT, + 16, 16, 16, 16, + 0, 0, 0, 0, 0, + 1, 1, 8 + }, + { + MESA_FORMAT_RGB_FLOAT32, + "MESA_FORMAT_RGB_FLOAT32", + GL_RGB, + GL_FLOAT, + 32, 32, 32, 0, + 0, 0, 0, 0, 0, + 1, 1, 12 + }, + { + MESA_FORMAT_RGB_FLOAT16, + "MESA_FORMAT_RGB_FLOAT16", + GL_RGB, + GL_FLOAT, + 16, 16, 16, 0, + 0, 0, 0, 0, 0, + 1, 1, 6 + }, + { + MESA_FORMAT_ALPHA_FLOAT32, + "MESA_FORMAT_ALPHA_FLOAT32", + GL_ALPHA, + GL_FLOAT, + 0, 0, 0, 32, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_ALPHA_FLOAT16, + "MESA_FORMAT_ALPHA_FLOAT16", + GL_ALPHA, + GL_FLOAT, + 0, 0, 0, 16, + 0, 0, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_LUMINANCE_FLOAT32, + "MESA_FORMAT_LUMINANCE_FLOAT32", + GL_LUMINANCE, + GL_FLOAT, + 0, 0, 0, 0, + 32, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_LUMINANCE_FLOAT16, + "MESA_FORMAT_LUMINANCE_FLOAT16", + GL_LUMINANCE, + GL_FLOAT, + 0, 0, 0, 0, + 16, 0, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_LUMINANCE_ALPHA_FLOAT32, + "MESA_FORMAT_LUMINANCE_ALPHA_FLOAT32", + GL_LUMINANCE_ALPHA, + GL_FLOAT, + 0, 0, 0, 32, + 32, 0, 0, 0, 0, + 1, 1, 8 + }, + { + MESA_FORMAT_LUMINANCE_ALPHA_FLOAT16, + "MESA_FORMAT_LUMINANCE_ALPHA_FLOAT16", + GL_LUMINANCE_ALPHA, + GL_FLOAT, + 0, 0, 0, 16, + 16, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_INTENSITY_FLOAT32, + "MESA_FORMAT_INTENSITY_FLOAT32", + GL_INTENSITY, + GL_FLOAT, + 0, 0, 0, 0, + 0, 32, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_INTENSITY_FLOAT16, + "MESA_FORMAT_INTENSITY_FLOAT16", + GL_INTENSITY, + GL_FLOAT, + 0, 0, 0, 0, + 0, 16, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_R_FLOAT32, + "MESA_FORMAT_R_FLOAT32", + GL_RED, + GL_FLOAT, + 32, 0, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_R_FLOAT16, + "MESA_FORMAT_R_FLOAT16", + GL_RED, + GL_FLOAT, + 16, 0, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_RG_FLOAT32, + "MESA_FORMAT_RG_FLOAT32", + GL_RG, + GL_FLOAT, + 32, 32, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 8 + }, + { + MESA_FORMAT_RG_FLOAT16, + "MESA_FORMAT_RG_FLOAT16", + GL_RG, + GL_FLOAT, + 16, 16, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + + /* unnormalized signed int formats */ + { + MESA_FORMAT_RGBA_INT8, + "MESA_FORMAT_RGBA_INT8", + GL_RGBA, + GL_INT, + 8, 8, 8, 8, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_RGBA_INT16, + "MESA_FORMAT_RGBA_INT16", + GL_RGBA, + GL_INT, + 16, 16, 16, 16, + 0, 0, 0, 0, 0, + 1, 1, 8 + }, + { + MESA_FORMAT_RGBA_INT32, + "MESA_FORMAT_RGBA_INT32", + GL_RGBA, + GL_INT, + 32, 32, 32, 32, + 0, 0, 0, 0, 0, + 1, 1, 16 + }, + + /* unnormalized unsigned int formats */ + { + MESA_FORMAT_RGBA_UINT8, + "MESA_FORMAT_RGBA_UINT8", + GL_RGBA, + GL_UNSIGNED_INT, + 8, 8, 8, 8, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_RGBA_UINT16, + "MESA_FORMAT_RGBA_UINT16", + GL_RGBA, + GL_UNSIGNED_INT, + 16, 16, 16, 16, + 0, 0, 0, 0, 0, + 1, 1, 8 + }, + { + MESA_FORMAT_RGBA_UINT32, + "MESA_FORMAT_RGBA_UINT32", + GL_RGBA, + GL_UNSIGNED_INT, + 32, 32, 32, 32, + 0, 0, 0, 0, 0, + 1, 1, 16 + }, + + + { + MESA_FORMAT_DUDV8, + "MESA_FORMAT_DUDV8", + GL_DUDV_ATI, + GL_SIGNED_NORMALIZED, + 0, 0, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 2 + }, + + /* Signed 8 bits / channel */ + { + MESA_FORMAT_SIGNED_R8, /* Name */ + "MESA_FORMAT_SIGNED_R8", /* StrName */ + GL_RED, /* BaseFormat */ + GL_SIGNED_NORMALIZED, /* DataType */ + 8, 0, 0, 0, /* Red/Green/Blue/AlphaBits */ + 0, 0, 0, 0, 0, /* Lum/Int/Index/Depth/StencilBits */ + 1, 1, 1 /* BlockWidth/Height,Bytes */ + }, + { + MESA_FORMAT_SIGNED_RG88_REV, + "MESA_FORMAT_SIGNED_RG88_REV", + GL_RG, + GL_SIGNED_NORMALIZED, + 8, 8, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_SIGNED_RGBX8888, + "MESA_FORMAT_SIGNED_RGBX8888", + GL_RGB, + GL_SIGNED_NORMALIZED, + 8, 8, 8, 0, + 0, 0, 0, 0, 0, + 1, 1, 4 /* 4 bpp, but no alpha */ + }, + { + MESA_FORMAT_SIGNED_RGBA8888, + "MESA_FORMAT_SIGNED_RGBA8888", + GL_RGBA, + GL_SIGNED_NORMALIZED, + 8, 8, 8, 8, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_SIGNED_RGBA8888_REV, + "MESA_FORMAT_SIGNED_RGBA8888_REV", + GL_RGBA, + GL_SIGNED_NORMALIZED, + 8, 8, 8, 8, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + + /* Signed 16 bits / channel */ + { + MESA_FORMAT_SIGNED_R16, + "MESA_FORMAT_SIGNED_R16", + GL_RED, + GL_SIGNED_NORMALIZED, + 16, 0, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_SIGNED_GR1616, + "MESA_FORMAT_SIGNED_GR1616", + GL_RG, + GL_SIGNED_NORMALIZED, + 16, 16, 0, 0, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_SIGNED_RGB_16, + "MESA_FORMAT_SIGNED_RGB_16", + GL_RGB, + GL_SIGNED_NORMALIZED, + 16, 16, 16, 0, + 0, 0, 0, 0, 0, + 1, 1, 6 + }, + { + MESA_FORMAT_SIGNED_RGBA_16, + "MESA_FORMAT_SIGNED_RGBA_16", + GL_RGBA, + GL_SIGNED_NORMALIZED, + 16, 16, 16, 16, + 0, 0, 0, 0, 0, + 1, 1, 8 + }, + { + MESA_FORMAT_RGBA_16, + "MESA_FORMAT_RGBA_16", + GL_RGBA, + GL_UNSIGNED_NORMALIZED, + 16, 16, 16, 16, + 0, 0, 0, 0, 0, + 1, 1, 8 + }, + { + MESA_FORMAT_RED_RGTC1, + "MESA_FORMAT_RED_RGTC1", + GL_RED, + GL_UNSIGNED_NORMALIZED, + 4, 0, 0, 0, + 0, 0, 0, 0, 0, + 4, 4, 8 /* 8 bytes per 4x4 block */ + }, + { + MESA_FORMAT_SIGNED_RED_RGTC1, + "MESA_FORMAT_SIGNED_RED_RGTC1", + GL_RED, + GL_SIGNED_NORMALIZED, + 4, 0, 0, 0, + 0, 0, 0, 0, 0, + 4, 4, 8 /* 8 bytes per 4x4 block */ + }, + { + MESA_FORMAT_RG_RGTC2, + "MESA_FORMAT_RG_RGTC2", + GL_RG, + GL_UNSIGNED_NORMALIZED, + 4, 4, 0, 0, + 0, 0, 0, 0, 0, + 4, 4, 16 /* 16 bytes per 4x4 block */ + }, + { + MESA_FORMAT_SIGNED_RG_RGTC2, + "MESA_FORMAT_SIGNED_RG_RGTC2", + GL_RG, + GL_SIGNED_NORMALIZED, + 4, 4, 0, 0, + 0, 0, 0, 0, 0, + 4, 4, 16 /* 16 bytes per 4x4 block */ + }, + { + MESA_FORMAT_L_LATC1, + "MESA_FORMAT_L_LATC1", + GL_LUMINANCE, + GL_UNSIGNED_NORMALIZED, + 0, 0, 0, 0, + 4, 0, 0, 0, 0, + 4, 4, 8 /* 8 bytes per 4x4 block */ + }, + { + MESA_FORMAT_SIGNED_L_LATC1, + "MESA_FORMAT_SIGNED_L_LATC1", + GL_LUMINANCE, + GL_SIGNED_NORMALIZED, + 0, 0, 0, 0, + 4, 0, 0, 0, 0, + 4, 4, 8 /* 8 bytes per 4x4 block */ + }, + { + MESA_FORMAT_LA_LATC2, + "MESA_FORMAT_LA_LATC2", + GL_LUMINANCE_ALPHA, + GL_UNSIGNED_NORMALIZED, + 0, 0, 0, 4, + 4, 0, 0, 0, 0, + 4, 4, 16 /* 16 bytes per 4x4 block */ + }, + { + MESA_FORMAT_SIGNED_LA_LATC2, + "MESA_FORMAT_SIGNED_LA_LATC2", + GL_LUMINANCE_ALPHA, + GL_SIGNED_NORMALIZED, + 0, 0, 0, 4, + 4, 0, 0, 0, 0, + 4, 4, 16 /* 16 bytes per 4x4 block */ + }, + + /* Signed formats from EXT_texture_snorm that are not in GL3.1 */ + { + MESA_FORMAT_SIGNED_A8, + "MESA_FORMAT_SIGNED_A8", + GL_ALPHA, + GL_SIGNED_NORMALIZED, + 0, 0, 0, 8, + 0, 0, 0, 0, 0, + 1, 1, 1 + }, + { + MESA_FORMAT_SIGNED_L8, + "MESA_FORMAT_SIGNED_L8", + GL_LUMINANCE, + GL_SIGNED_NORMALIZED, + 0, 0, 0, 0, + 8, 0, 0, 0, 0, + 1, 1, 1 + }, + { + MESA_FORMAT_SIGNED_AL88, + "MESA_FORMAT_SIGNED_AL88", + GL_LUMINANCE_ALPHA, + GL_SIGNED_NORMALIZED, + 0, 0, 0, 8, + 8, 0, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_SIGNED_I8, + "MESA_FORMAT_SIGNED_I8", + GL_INTENSITY, + GL_SIGNED_NORMALIZED, + 0, 0, 0, 0, + 0, 8, 0, 0, 0, + 1, 1, 1 + }, + { + MESA_FORMAT_SIGNED_A16, + "MESA_FORMAT_SIGNED_A16", + GL_ALPHA, + GL_SIGNED_NORMALIZED, + 0, 0, 0, 16, + 0, 0, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_SIGNED_L16, + "MESA_FORMAT_SIGNED_L16", + GL_LUMINANCE, + GL_SIGNED_NORMALIZED, + 0, 0, 0, 0, + 16, 0, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_SIGNED_AL1616, + "MESA_FORMAT_SIGNED_AL1616", + GL_LUMINANCE_ALPHA, + GL_SIGNED_NORMALIZED, + 0, 0, 0, 16, + 16, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_SIGNED_I16, + "MESA_FORMAT_SIGNED_I16", + GL_INTENSITY, + GL_SIGNED_NORMALIZED, + 0, 0, 0, 0, + 0, 16, 0, 0, 0, + 1, 1, 2 + }, + { + MESA_FORMAT_RGB9_E5_FLOAT, + "MESA_FORMAT_RGB9_E5", + GL_RGB, + GL_FLOAT, + 9, 9, 9, 0, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, + { + MESA_FORMAT_R11_G11_B10_FLOAT, + "MESA_FORMAT_R11_G11_B10_FLOAT", + GL_RGB, + GL_FLOAT, + 11, 11, 10, 0, + 0, 0, 0, 0, 0, + 1, 1, 4 + }, +}; + + + +static const struct gl_format_info * +_mesa_get_format_info(gl_format format) +{ + const struct gl_format_info *info = &format_info[format]; + assert(info->Name == format); + return info; +} + + +/** Return string name of format (for debugging) */ +const char * +_mesa_get_format_name(gl_format format) +{ + const struct gl_format_info *info = _mesa_get_format_info(format); + return info->StrName; +} + + + +/** + * Return bytes needed to store a block of pixels in the given format. + * Normally, a block is 1x1 (a single pixel). But for compressed formats + * a block may be 4x4 or 8x4, etc. + * + * Note: not GLuint, so as not to coerce math to unsigned. cf. fdo #37351 + */ +GLint +_mesa_get_format_bytes(gl_format format) +{ + const struct gl_format_info *info = _mesa_get_format_info(format); + ASSERT(info->BytesPerBlock); + return info->BytesPerBlock; +} + + +/** + * Return bits per component for the given format. + * \param format one of MESA_FORMAT_x + * \param pname the component, such as GL_RED_BITS, GL_TEXTURE_BLUE_BITS, etc. + */ +GLint +_mesa_get_format_bits(gl_format format, GLenum pname) +{ + const struct gl_format_info *info = _mesa_get_format_info(format); + + switch (pname) { + case GL_RED_BITS: + case GL_TEXTURE_RED_SIZE: + case GL_RENDERBUFFER_RED_SIZE_EXT: + case GL_FRAMEBUFFER_ATTACHMENT_RED_SIZE: + return info->RedBits; + case GL_GREEN_BITS: + case GL_TEXTURE_GREEN_SIZE: + case GL_RENDERBUFFER_GREEN_SIZE_EXT: + case GL_FRAMEBUFFER_ATTACHMENT_GREEN_SIZE: + return info->GreenBits; + case GL_BLUE_BITS: + case GL_TEXTURE_BLUE_SIZE: + case GL_RENDERBUFFER_BLUE_SIZE_EXT: + case GL_FRAMEBUFFER_ATTACHMENT_BLUE_SIZE: + return info->BlueBits; + case GL_ALPHA_BITS: + case GL_TEXTURE_ALPHA_SIZE: + case GL_RENDERBUFFER_ALPHA_SIZE_EXT: + case GL_FRAMEBUFFER_ATTACHMENT_ALPHA_SIZE: + return info->AlphaBits; + case GL_TEXTURE_INTENSITY_SIZE: + return info->IntensityBits; + case GL_TEXTURE_LUMINANCE_SIZE: + return info->LuminanceBits; + case GL_INDEX_BITS: + case GL_TEXTURE_INDEX_SIZE_EXT: + return info->IndexBits; + case GL_DEPTH_BITS: + case GL_TEXTURE_DEPTH_SIZE_ARB: + case GL_RENDERBUFFER_DEPTH_SIZE_EXT: + case GL_FRAMEBUFFER_ATTACHMENT_DEPTH_SIZE: + return info->DepthBits; + case GL_STENCIL_BITS: + case GL_TEXTURE_STENCIL_SIZE_EXT: + case GL_RENDERBUFFER_STENCIL_SIZE_EXT: + case GL_FRAMEBUFFER_ATTACHMENT_STENCIL_SIZE: + return info->StencilBits; + default: + _mesa_problem(NULL, "bad pname in _mesa_get_format_bits()"); + return 0; + } +} + + +/** + * Return the data type (or more specifically, the data representation) + * for the given format. + * The return value will be one of: + * GL_UNSIGNED_NORMALIZED = unsigned int representing [0,1] + * GL_SIGNED_NORMALIZED = signed int representing [-1, 1] + * GL_UNSIGNED_INT = an ordinary unsigned integer + * GL_INT = an ordinary signed integer + * GL_FLOAT = an ordinary float + */ +GLenum +_mesa_get_format_datatype(gl_format format) +{ + const struct gl_format_info *info = _mesa_get_format_info(format); + return info->DataType; +} + + +/** + * Return the basic format for the given type. The result will be + * one of GL_RGB, GL_RGBA, GL_ALPHA, GL_LUMINANCE, GL_LUMINANCE_ALPHA, + * GL_INTENSITY, GL_YCBCR_MESA, GL_COLOR_INDEX, GL_DEPTH_COMPONENT, + * GL_STENCIL_INDEX, GL_DEPTH_STENCIL. + */ +GLenum +_mesa_get_format_base_format(gl_format format) +{ + const struct gl_format_info *info = _mesa_get_format_info(format); + return info->BaseFormat; +} + + +/** + * Return the block size (in pixels) for the given format. Normally + * the block size is 1x1. But compressed formats will have block sizes + * of 4x4 or 8x4 pixels, etc. + * \param bw returns block width in pixels + * \param bh returns block height in pixels + */ +void +_mesa_get_format_block_size(gl_format format, GLuint *bw, GLuint *bh) +{ + const struct gl_format_info *info = _mesa_get_format_info(format); + *bw = info->BlockWidth; + *bh = info->BlockHeight; +} + + +/** Is the given format a compressed format? */ +GLboolean +_mesa_is_format_compressed(gl_format format) +{ + const struct gl_format_info *info = _mesa_get_format_info(format); + return info->BlockWidth > 1 || info->BlockHeight > 1; +} + + +/** + * Determine if the given format represents a packed depth/stencil buffer. + */ +GLboolean +_mesa_is_format_packed_depth_stencil(gl_format format) +{ + const struct gl_format_info *info = _mesa_get_format_info(format); + + return info->BaseFormat == GL_DEPTH_STENCIL; +} + + +/** + * Is the given format a signed/unsigned integer color format? + */ +GLboolean +_mesa_is_format_integer_color(gl_format format) +{ + const struct gl_format_info *info = _mesa_get_format_info(format); + return (info->DataType == GL_INT || info->DataType == GL_UNSIGNED_INT) && + info->BaseFormat != GL_DEPTH_COMPONENT && + info->BaseFormat != GL_DEPTH_STENCIL && + info->BaseFormat != GL_STENCIL_INDEX; +} + + +/** + * Return color encoding for given format. + * \return GL_LINEAR or GL_SRGB + */ +GLenum +_mesa_get_format_color_encoding(gl_format format) +{ + /* XXX this info should be encoded in gl_format_info */ + switch (format) { + case MESA_FORMAT_SRGB8: + case MESA_FORMAT_SRGBA8: + case MESA_FORMAT_SARGB8: + case MESA_FORMAT_SL8: + case MESA_FORMAT_SLA8: + case MESA_FORMAT_SRGB_DXT1: + case MESA_FORMAT_SRGBA_DXT1: + case MESA_FORMAT_SRGBA_DXT3: + case MESA_FORMAT_SRGBA_DXT5: + return GL_SRGB; + default: + return GL_LINEAR; + } +} + + +/** + * For an sRGB format, return the corresponding linear color space format. + * For non-sRGB formats, return the format as-is. + */ +gl_format +_mesa_get_srgb_format_linear(gl_format format) +{ + switch (format) { + case MESA_FORMAT_SRGB8: + format = MESA_FORMAT_RGB888; + break; + case MESA_FORMAT_SRGBA8: + format = MESA_FORMAT_RGBA8888; + break; + case MESA_FORMAT_SARGB8: + format = MESA_FORMAT_ARGB8888; + break; + case MESA_FORMAT_SL8: + format = MESA_FORMAT_L8; + break; + case MESA_FORMAT_SLA8: + format = MESA_FORMAT_AL88; + break; + case MESA_FORMAT_SRGB_DXT1: + format = MESA_FORMAT_RGB_DXT1; + break; + case MESA_FORMAT_SRGBA_DXT1: + format = MESA_FORMAT_RGBA_DXT1; + break; + case MESA_FORMAT_SRGBA_DXT3: + format = MESA_FORMAT_RGBA_DXT3; + break; + case MESA_FORMAT_SRGBA_DXT5: + format = MESA_FORMAT_RGBA_DXT5; + break; + default: + break; + } + return format; +} + + +/** + * Return number of bytes needed to store an image of the given size + * in the given format. + */ +GLuint +_mesa_format_image_size(gl_format format, GLsizei width, + GLsizei height, GLsizei depth) +{ + const struct gl_format_info *info = _mesa_get_format_info(format); + /* Strictly speaking, a conditional isn't needed here */ + if (info->BlockWidth > 1 || info->BlockHeight > 1) { + /* compressed format (2D only for now) */ + const GLuint bw = info->BlockWidth, bh = info->BlockHeight; + const GLuint wblocks = (width + bw - 1) / bw; + const GLuint hblocks = (height + bh - 1) / bh; + const GLuint sz = wblocks * hblocks * info->BytesPerBlock; + assert(depth == 1); + return sz; + } + else { + /* non-compressed */ + const GLuint sz = width * height * depth * info->BytesPerBlock; + return sz; + } +} + + +/** + * Same as _mesa_format_image_size() but returns a 64-bit value to + * accomodate very large textures. + */ +uint64_t +_mesa_format_image_size64(gl_format format, GLsizei width, + GLsizei height, GLsizei depth) +{ + const struct gl_format_info *info = _mesa_get_format_info(format); + /* Strictly speaking, a conditional isn't needed here */ + if (info->BlockWidth > 1 || info->BlockHeight > 1) { + /* compressed format (2D only for now) */ + const uint64_t bw = info->BlockWidth, bh = info->BlockHeight; + const uint64_t wblocks = (width + bw - 1) / bw; + const uint64_t hblocks = (height + bh - 1) / bh; + const uint64_t sz = wblocks * hblocks * info->BytesPerBlock; + assert(depth == 1); + return sz; + } + else { + /* non-compressed */ + const uint64_t sz = ((uint64_t) width * + (uint64_t) height * + (uint64_t) depth * + info->BytesPerBlock); + return sz; + } +} + + + +GLint +_mesa_format_row_stride(gl_format format, GLsizei width) +{ + const struct gl_format_info *info = _mesa_get_format_info(format); + /* Strictly speaking, a conditional isn't needed here */ + if (info->BlockWidth > 1 || info->BlockHeight > 1) { + /* compressed format */ + const GLuint bw = info->BlockWidth; + const GLuint wblocks = (width + bw - 1) / bw; + const GLint stride = wblocks * info->BytesPerBlock; + return stride; + } + else { + const GLint stride = width * info->BytesPerBlock; + return stride; + } +} + + +/** + * Debug/test: check that all formats are handled in the + * _mesa_format_to_type_and_comps() function. When new pixel formats + * are added to Mesa, that function needs to be updated. + * This is a no-op after the first call. + */ +static void +check_format_to_type_and_comps(void) +{ + gl_format f; + + for (f = MESA_FORMAT_NONE + 1; f < MESA_FORMAT_COUNT; f++) { + GLenum datatype = 0; + GLuint comps = 0; + /* This function will emit a problem/warning if the format is + * not handled. + */ + _mesa_format_to_type_and_comps(f, &datatype, &comps); + } +} + + +/** + * Do sanity checking of the format info table. + */ +void +_mesa_test_formats(void) +{ + GLuint i; + + assert(Elements(format_info) == MESA_FORMAT_COUNT); + + for (i = 0; i < MESA_FORMAT_COUNT; i++) { + const struct gl_format_info *info = _mesa_get_format_info(i); + assert(info); + + assert(info->Name == i); + + if (info->Name == MESA_FORMAT_NONE) + continue; + + if (info->BlockWidth == 1 && info->BlockHeight == 1) { + if (info->RedBits > 0) { + GLuint t = info->RedBits + info->GreenBits + + info->BlueBits + info->AlphaBits; + assert(t / 8 <= info->BytesPerBlock); + (void) t; + } + } + + assert(info->DataType == GL_UNSIGNED_NORMALIZED || + info->DataType == GL_SIGNED_NORMALIZED || + info->DataType == GL_UNSIGNED_INT || + info->DataType == GL_INT || + info->DataType == GL_FLOAT); + + if (info->BaseFormat == GL_RGB) { + assert(info->RedBits > 0); + assert(info->GreenBits > 0); + assert(info->BlueBits > 0); + assert(info->AlphaBits == 0); + assert(info->LuminanceBits == 0); + assert(info->IntensityBits == 0); + } + else if (info->BaseFormat == GL_RGBA) { + assert(info->RedBits > 0); + assert(info->GreenBits > 0); + assert(info->BlueBits > 0); + assert(info->AlphaBits > 0); + assert(info->LuminanceBits == 0); + assert(info->IntensityBits == 0); + } + else if (info->BaseFormat == GL_RG) { + assert(info->RedBits > 0); + assert(info->GreenBits > 0); + assert(info->BlueBits == 0); + assert(info->AlphaBits == 0); + assert(info->LuminanceBits == 0); + assert(info->IntensityBits == 0); + } + else if (info->BaseFormat == GL_RED) { + assert(info->RedBits > 0); + assert(info->GreenBits == 0); + assert(info->BlueBits == 0); + assert(info->AlphaBits == 0); + assert(info->LuminanceBits == 0); + assert(info->IntensityBits == 0); + } + else if (info->BaseFormat == GL_LUMINANCE) { + assert(info->RedBits == 0); + assert(info->GreenBits == 0); + assert(info->BlueBits == 0); + assert(info->AlphaBits == 0); + assert(info->LuminanceBits > 0); + assert(info->IntensityBits == 0); + } + else if (info->BaseFormat == GL_INTENSITY) { + assert(info->RedBits == 0); + assert(info->GreenBits == 0); + assert(info->BlueBits == 0); + assert(info->AlphaBits == 0); + assert(info->LuminanceBits == 0); + assert(info->IntensityBits > 0); + } + } + + check_format_to_type_and_comps(); +} + + + +/** + * Return datatype and number of components per texel for the given gl_format. + * Only used for mipmap generation code. + */ +void +_mesa_format_to_type_and_comps(gl_format format, + GLenum *datatype, GLuint *comps) +{ + switch (format) { + case MESA_FORMAT_RGBA8888: + case MESA_FORMAT_RGBA8888_REV: + case MESA_FORMAT_ARGB8888: + case MESA_FORMAT_ARGB8888_REV: + case MESA_FORMAT_XRGB8888: + case MESA_FORMAT_XRGB8888_REV: + *datatype = GL_UNSIGNED_BYTE; + *comps = 4; + return; + case MESA_FORMAT_RGB888: + case MESA_FORMAT_BGR888: + *datatype = GL_UNSIGNED_BYTE; + *comps = 3; + return; + case MESA_FORMAT_RGB565: + case MESA_FORMAT_RGB565_REV: + *datatype = GL_UNSIGNED_SHORT_5_6_5; + *comps = 3; + return; + + case MESA_FORMAT_ARGB4444: + case MESA_FORMAT_ARGB4444_REV: + *datatype = GL_UNSIGNED_SHORT_4_4_4_4; + *comps = 4; + return; + + case MESA_FORMAT_ARGB1555: + case MESA_FORMAT_ARGB1555_REV: + *datatype = GL_UNSIGNED_SHORT_1_5_5_5_REV; + *comps = 4; + return; + + case MESA_FORMAT_ARGB2101010: + *datatype = GL_UNSIGNED_INT_2_10_10_10_REV; + *comps = 4; + return; + + case MESA_FORMAT_RGBA5551: + *datatype = GL_UNSIGNED_SHORT_5_5_5_1; + *comps = 4; + return; + + case MESA_FORMAT_AL44: + *datatype = MESA_UNSIGNED_BYTE_4_4; + *comps = 2; + return; + + case MESA_FORMAT_AL88: + case MESA_FORMAT_AL88_REV: + case MESA_FORMAT_RG88: + case MESA_FORMAT_RG88_REV: + *datatype = GL_UNSIGNED_BYTE; + *comps = 2; + return; + + case MESA_FORMAT_AL1616: + case MESA_FORMAT_AL1616_REV: + case MESA_FORMAT_RG1616: + case MESA_FORMAT_RG1616_REV: + *datatype = GL_UNSIGNED_SHORT; + *comps = 2; + return; + + case MESA_FORMAT_R16: + case MESA_FORMAT_A16: + case MESA_FORMAT_L16: + case MESA_FORMAT_I16: + *datatype = GL_UNSIGNED_SHORT; + *comps = 1; + return; + + case MESA_FORMAT_RGB332: + *datatype = GL_UNSIGNED_BYTE_3_3_2; + *comps = 3; + return; + + case MESA_FORMAT_A8: + case MESA_FORMAT_L8: + case MESA_FORMAT_I8: + case MESA_FORMAT_CI8: + case MESA_FORMAT_R8: + case MESA_FORMAT_S8: + *datatype = GL_UNSIGNED_BYTE; + *comps = 1; + return; + + case MESA_FORMAT_YCBCR: + case MESA_FORMAT_YCBCR_REV: + *datatype = GL_UNSIGNED_SHORT; + *comps = 2; + return; + + case MESA_FORMAT_Z24_S8: + *datatype = GL_UNSIGNED_INT; + *comps = 1; /* XXX OK? */ + return; + + case MESA_FORMAT_S8_Z24: + *datatype = GL_UNSIGNED_INT; + *comps = 1; /* XXX OK? */ + return; + + case MESA_FORMAT_Z16: + *datatype = GL_UNSIGNED_SHORT; + *comps = 1; + return; + + case MESA_FORMAT_X8_Z24: + *datatype = GL_UNSIGNED_INT; + *comps = 1; + return; + + case MESA_FORMAT_Z24_X8: + *datatype = GL_UNSIGNED_INT; + *comps = 1; + return; + + case MESA_FORMAT_Z32: + *datatype = GL_UNSIGNED_INT; + *comps = 1; + return; + + case MESA_FORMAT_DUDV8: + *datatype = GL_BYTE; + *comps = 2; + return; + + case MESA_FORMAT_SIGNED_R8: + case MESA_FORMAT_SIGNED_A8: + case MESA_FORMAT_SIGNED_L8: + case MESA_FORMAT_SIGNED_I8: + *datatype = GL_BYTE; + *comps = 1; + return; + case MESA_FORMAT_SIGNED_RG88_REV: + case MESA_FORMAT_SIGNED_AL88: + *datatype = GL_BYTE; + *comps = 2; + return; + case MESA_FORMAT_SIGNED_RGBA8888: + case MESA_FORMAT_SIGNED_RGBA8888_REV: + case MESA_FORMAT_SIGNED_RGBX8888: + *datatype = GL_BYTE; + *comps = 4; + return; + + case MESA_FORMAT_RGBA_16: + *datatype = GL_UNSIGNED_SHORT; + *comps = 4; + return; + + case MESA_FORMAT_SIGNED_R16: + case MESA_FORMAT_SIGNED_A16: + case MESA_FORMAT_SIGNED_L16: + case MESA_FORMAT_SIGNED_I16: + *datatype = GL_SHORT; + *comps = 1; + return; + case MESA_FORMAT_SIGNED_GR1616: + case MESA_FORMAT_SIGNED_AL1616: + *datatype = GL_SHORT; + *comps = 2; + return; + case MESA_FORMAT_SIGNED_RGB_16: + *datatype = GL_SHORT; + *comps = 3; + return; + case MESA_FORMAT_SIGNED_RGBA_16: + *datatype = GL_SHORT; + *comps = 4; + return; + +#if FEATURE_EXT_texture_sRGB + case MESA_FORMAT_SRGB8: + *datatype = GL_UNSIGNED_BYTE; + *comps = 3; + return; + case MESA_FORMAT_SRGBA8: + case MESA_FORMAT_SARGB8: + *datatype = GL_UNSIGNED_BYTE; + *comps = 4; + return; + case MESA_FORMAT_SL8: + *datatype = GL_UNSIGNED_BYTE; + *comps = 1; + return; + case MESA_FORMAT_SLA8: + *datatype = GL_UNSIGNED_BYTE; + *comps = 2; + return; +#endif + +#if FEATURE_texture_fxt1 + case MESA_FORMAT_RGB_FXT1: + case MESA_FORMAT_RGBA_FXT1: +#endif +#if FEATURE_texture_s3tc + case MESA_FORMAT_RGB_DXT1: + case MESA_FORMAT_RGBA_DXT1: + case MESA_FORMAT_RGBA_DXT3: + case MESA_FORMAT_RGBA_DXT5: +#if FEATURE_EXT_texture_sRGB + case MESA_FORMAT_SRGB_DXT1: + case MESA_FORMAT_SRGBA_DXT1: + case MESA_FORMAT_SRGBA_DXT3: + case MESA_FORMAT_SRGBA_DXT5: +#endif +#endif + case MESA_FORMAT_RED_RGTC1: + case MESA_FORMAT_SIGNED_RED_RGTC1: + case MESA_FORMAT_RG_RGTC2: + case MESA_FORMAT_SIGNED_RG_RGTC2: + case MESA_FORMAT_L_LATC1: + case MESA_FORMAT_SIGNED_L_LATC1: + case MESA_FORMAT_LA_LATC2: + case MESA_FORMAT_SIGNED_LA_LATC2: + /* XXX generate error instead? */ + *datatype = GL_UNSIGNED_BYTE; + *comps = 0; + return; + + case MESA_FORMAT_RGBA_FLOAT32: + *datatype = GL_FLOAT; + *comps = 4; + return; + case MESA_FORMAT_RGBA_FLOAT16: + *datatype = GL_HALF_FLOAT_ARB; + *comps = 4; + return; + case MESA_FORMAT_RGB_FLOAT32: + *datatype = GL_FLOAT; + *comps = 3; + return; + case MESA_FORMAT_RGB_FLOAT16: + *datatype = GL_HALF_FLOAT_ARB; + *comps = 3; + return; + case MESA_FORMAT_LUMINANCE_ALPHA_FLOAT32: + case MESA_FORMAT_RG_FLOAT32: + *datatype = GL_FLOAT; + *comps = 2; + return; + case MESA_FORMAT_LUMINANCE_ALPHA_FLOAT16: + case MESA_FORMAT_RG_FLOAT16: + *datatype = GL_HALF_FLOAT_ARB; + *comps = 2; + return; + case MESA_FORMAT_ALPHA_FLOAT32: + case MESA_FORMAT_LUMINANCE_FLOAT32: + case MESA_FORMAT_INTENSITY_FLOAT32: + case MESA_FORMAT_R_FLOAT32: + *datatype = GL_FLOAT; + *comps = 1; + return; + case MESA_FORMAT_ALPHA_FLOAT16: + case MESA_FORMAT_LUMINANCE_FLOAT16: + case MESA_FORMAT_INTENSITY_FLOAT16: + case MESA_FORMAT_R_FLOAT16: + *datatype = GL_HALF_FLOAT_ARB; + *comps = 1; + return; + + case MESA_FORMAT_RGBA_INT8: + *datatype = GL_BYTE; + *comps = 4; + return; + case MESA_FORMAT_RGBA_INT16: + *datatype = GL_SHORT; + *comps = 4; + return; + case MESA_FORMAT_RGBA_INT32: + *datatype = GL_INT; + *comps = 4; + return; + + /** + * \name Non-normalized unsigned integer formats. + */ + case MESA_FORMAT_RGBA_UINT8: + *datatype = GL_UNSIGNED_BYTE; + *comps = 4; + return; + case MESA_FORMAT_RGBA_UINT16: + *datatype = GL_UNSIGNED_SHORT; + *comps = 4; + return; + case MESA_FORMAT_RGBA_UINT32: + *datatype = GL_UNSIGNED_INT; + *comps = 4; + return; + + case MESA_FORMAT_RGB9_E5_FLOAT: + *datatype = GL_UNSIGNED_INT_5_9_9_9_REV; + *comps = 3; + return; + + case MESA_FORMAT_R11_G11_B10_FLOAT: + *datatype = GL_UNSIGNED_INT_10F_11F_11F_REV; + *comps = 3; + return; + + case MESA_FORMAT_COUNT: + assert(0); + return; + + case MESA_FORMAT_NONE: + /* For debug builds, warn if any formats are not handled */ +#ifdef DEBUG + default: +#endif + _mesa_problem(NULL, "bad format %s in _mesa_format_to_type_and_comps", + _mesa_get_format_name(format)); + *datatype = 0; + *comps = 1; + } +} diff --git a/mesalib/src/mesa/main/formats.h b/mesalib/src/mesa/main/formats.h index c9fd0baab..0640bbc4a 100644 --- a/mesalib/src/mesa/main/formats.h +++ b/mesalib/src/mesa/main/formats.h @@ -1,267 +1,267 @@ -/*
- * Mesa 3-D graphics library
- * Version: 7.7
- *
- * Copyright (C) 1999-2008 Brian Paul All Rights Reserved.
- * Copyright (c) 2008-2009 VMware, Inc.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included
- * in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
- * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
- * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
- * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
- * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- */
-
-/*
- * Authors:
- * Brian Paul
- */
-
-
-#ifndef FORMATS_H
-#define FORMATS_H
-
-
-#include <GL/gl.h>
-
-/* OpenGL doesn't have GL_UNSIGNED_BYTE_4_4, so we must define our own type
- * for GL_LUMINANCE4_ALPHA4. */
-#define MESA_UNSIGNED_BYTE_4_4 (GL_UNSIGNED_BYTE<<1)
-
-
-/**
- * Mesa texture/renderbuffer image formats.
- */
-typedef enum
-{
- MESA_FORMAT_NONE = 0,
-
- /**
- * \name Basic hardware formats
- */
- /*@{*/
- /* msb <------ TEXEL BITS -----------> lsb */
- /* ---- ---- ---- ---- ---- ---- ---- ---- */
- MESA_FORMAT_RGBA8888, /* RRRR RRRR GGGG GGGG BBBB BBBB AAAA AAAA */
- MESA_FORMAT_RGBA8888_REV, /* AAAA AAAA BBBB BBBB GGGG GGGG RRRR RRRR */
- MESA_FORMAT_ARGB8888, /* AAAA AAAA RRRR RRRR GGGG GGGG BBBB BBBB */
- MESA_FORMAT_ARGB8888_REV, /* BBBB BBBB GGGG GGGG RRRR RRRR AAAA AAAA */
- MESA_FORMAT_XRGB8888, /* xxxx xxxx RRRR RRRR GGGG GGGG BBBB BBBB */
- MESA_FORMAT_XRGB8888_REV, /* BBBB BBBB GGGG GGGG RRRR RRRR xxxx xxxx */
- MESA_FORMAT_RGB888, /* RRRR RRRR GGGG GGGG BBBB BBBB */
- MESA_FORMAT_BGR888, /* BBBB BBBB GGGG GGGG RRRR RRRR */
- MESA_FORMAT_RGB565, /* RRRR RGGG GGGB BBBB */
- MESA_FORMAT_RGB565_REV, /* GGGB BBBB RRRR RGGG */
- MESA_FORMAT_ARGB4444, /* AAAA RRRR GGGG BBBB */
- MESA_FORMAT_ARGB4444_REV, /* GGGG BBBB AAAA RRRR */
- MESA_FORMAT_RGBA5551, /* RRRR RGGG GGBB BBBA */
- MESA_FORMAT_ARGB1555, /* ARRR RRGG GGGB BBBB */
- MESA_FORMAT_ARGB1555_REV, /* GGGB BBBB ARRR RRGG */
- MESA_FORMAT_AL44, /* AAAA LLLL */
- MESA_FORMAT_AL88, /* AAAA AAAA LLLL LLLL */
- MESA_FORMAT_AL88_REV, /* LLLL LLLL AAAA AAAA */
- MESA_FORMAT_AL1616, /* AAAA AAAA AAAA AAAA LLLL LLLL LLLL LLLL */
- MESA_FORMAT_AL1616_REV, /* LLLL LLLL LLLL LLLL AAAA AAAA AAAA AAAA */
- MESA_FORMAT_RGB332, /* RRRG GGBB */
- MESA_FORMAT_A8, /* AAAA AAAA */
- MESA_FORMAT_A16, /* AAAA AAAA AAAA AAAA */
- MESA_FORMAT_L8, /* LLLL LLLL */
- MESA_FORMAT_L16, /* LLLL LLLL LLLL LLLL */
- MESA_FORMAT_I8, /* IIII IIII */
- MESA_FORMAT_I16, /* IIII IIII IIII IIII */
- MESA_FORMAT_CI8, /* CCCC CCCC */
- MESA_FORMAT_YCBCR, /* YYYY YYYY UorV UorV */
- MESA_FORMAT_YCBCR_REV, /* UorV UorV YYYY YYYY */
- MESA_FORMAT_R8, /* RRRR RRRR */
- MESA_FORMAT_RG88, /* RRRR RRRR GGGG GGGG */
- MESA_FORMAT_RG88_REV, /* GGGG GGGG RRRR RRRR */
- MESA_FORMAT_R16, /* RRRR RRRR RRRR RRRR */
- MESA_FORMAT_RG1616, /* RRRR RRRR RRRR RRRR GGGG GGGG GGGG GGGG */
- MESA_FORMAT_RG1616_REV, /* GGGG GGGG GGGG GGGG RRRR RRRR RRRR RRRR */
- MESA_FORMAT_ARGB2101010, /* AARR RRRR RRRR GGGG GGGG GGBB BBBB BBBB */
- MESA_FORMAT_Z24_S8, /* ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ SSSS SSSS */
- MESA_FORMAT_S8_Z24, /* SSSS SSSS ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ */
- MESA_FORMAT_Z16, /* ZZZZ ZZZZ ZZZZ ZZZZ */
- MESA_FORMAT_X8_Z24, /* xxxx xxxx ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ */
- MESA_FORMAT_Z24_X8, /* ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ xxxx xxxx */
- MESA_FORMAT_Z32, /* ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ */
- MESA_FORMAT_S8, /* SSSS SSSS */
- /*@}*/
-
- /**
- * \name 8-bit/channel sRGB formats
- */
- /*@{*/
- MESA_FORMAT_SRGB8,
- MESA_FORMAT_SRGBA8,
- MESA_FORMAT_SARGB8,
- MESA_FORMAT_SL8,
- MESA_FORMAT_SLA8,
- MESA_FORMAT_SRGB_DXT1,
- MESA_FORMAT_SRGBA_DXT1,
- MESA_FORMAT_SRGBA_DXT3,
- MESA_FORMAT_SRGBA_DXT5,
- /*@}*/
-
- /**
- * \name Compressed texture formats.
- */
- /*@{*/
- MESA_FORMAT_RGB_FXT1,
- MESA_FORMAT_RGBA_FXT1,
- MESA_FORMAT_RGB_DXT1,
- MESA_FORMAT_RGBA_DXT1,
- MESA_FORMAT_RGBA_DXT3,
- MESA_FORMAT_RGBA_DXT5,
- /*@}*/
-
- /**
- * \name Floating point texture formats.
- */
- /*@{*/
- MESA_FORMAT_RGBA_FLOAT32,
- MESA_FORMAT_RGBA_FLOAT16,
- MESA_FORMAT_RGB_FLOAT32,
- MESA_FORMAT_RGB_FLOAT16,
- MESA_FORMAT_ALPHA_FLOAT32,
- MESA_FORMAT_ALPHA_FLOAT16,
- MESA_FORMAT_LUMINANCE_FLOAT32,
- MESA_FORMAT_LUMINANCE_FLOAT16,
- MESA_FORMAT_LUMINANCE_ALPHA_FLOAT32,
- MESA_FORMAT_LUMINANCE_ALPHA_FLOAT16,
- MESA_FORMAT_INTENSITY_FLOAT32,
- MESA_FORMAT_INTENSITY_FLOAT16,
- MESA_FORMAT_R_FLOAT32,
- MESA_FORMAT_R_FLOAT16,
- MESA_FORMAT_RG_FLOAT32,
- MESA_FORMAT_RG_FLOAT16,
- /*@}*/
-
- /**
- * \name Non-normalized signed integer formats.
- * XXX Note: these are just stand-ins for some better hardware
- * formats TBD such as BGRA or ARGB.
- */
- MESA_FORMAT_RGBA_INT8,
- MESA_FORMAT_RGBA_INT16,
- MESA_FORMAT_RGBA_INT32,
-
- /**
- * \name Non-normalized unsigned integer formats.
- */
- MESA_FORMAT_RGBA_UINT8,
- MESA_FORMAT_RGBA_UINT16,
- MESA_FORMAT_RGBA_UINT32,
-
- /* msb <------ TEXEL BITS -----------> lsb */
- /* ---- ---- ---- ---- ---- ---- ---- ---- */
- /**
- * \name Signed fixed point texture formats.
- */
- /*@{*/
- MESA_FORMAT_DUDV8, /* DUDU DUDU DVDV DVDV */
- MESA_FORMAT_SIGNED_R8, /* RRRR RRRR */
- MESA_FORMAT_SIGNED_RG88_REV, /* GGGG GGGG RRRR RRRR */
- MESA_FORMAT_SIGNED_RGBX8888, /* RRRR RRRR GGGG GGGG BBBB BBBB xxxx xxxx */
- MESA_FORMAT_SIGNED_RGBA8888, /* RRRR RRRR GGGG GGGG BBBB BBBB AAAA AAAA */
- MESA_FORMAT_SIGNED_RGBA8888_REV,/*AAAA AAAA BBBB BBBB GGGG GGGG RRRR RRRR */
- MESA_FORMAT_SIGNED_R16, /* RRRR RRRR RRRR RRRR */
- MESA_FORMAT_SIGNED_GR1616, /* GGGG GGGG GGGG GGGG RRRR RRRR RRRR RRRR */
- MESA_FORMAT_SIGNED_RGB_16, /* ushort[0]=R, ushort[1]=G, ushort[2]=B */
- MESA_FORMAT_SIGNED_RGBA_16, /* ... */
- MESA_FORMAT_RGBA_16, /* ... */
- /*@}*/
-
- /*@{*/
- MESA_FORMAT_RED_RGTC1,
- MESA_FORMAT_SIGNED_RED_RGTC1,
- MESA_FORMAT_RG_RGTC2,
- MESA_FORMAT_SIGNED_RG_RGTC2,
- /*@}*/
-
- /*@{*/
- MESA_FORMAT_L_LATC1,
- MESA_FORMAT_SIGNED_L_LATC1,
- MESA_FORMAT_LA_LATC2,
- MESA_FORMAT_SIGNED_LA_LATC2,
- /*@}*/
-
- MESA_FORMAT_SIGNED_A8, /* AAAA AAAA */
- MESA_FORMAT_SIGNED_L8, /* LLLL LLLL */
- MESA_FORMAT_SIGNED_AL88, /* AAAA AAAA LLLL LLLL */
- MESA_FORMAT_SIGNED_I8, /* IIII IIII */
- MESA_FORMAT_SIGNED_A16, /* AAAA AAAA AAAA AAAA */
- MESA_FORMAT_SIGNED_L16, /* LLLL LLLL LLLL LLLL */
- MESA_FORMAT_SIGNED_AL1616, /* AAAA AAAA AAAA AAAA LLLL LLLL LLLL LLLL */
- MESA_FORMAT_SIGNED_I16, /* IIII IIII IIII IIII */
-
- MESA_FORMAT_RGB9_E5_FLOAT,
- MESA_FORMAT_R11_G11_B10_FLOAT,
-
- MESA_FORMAT_COUNT
-} gl_format;
-
-
-extern const char *
-_mesa_get_format_name(gl_format format);
-
-extern GLuint
-_mesa_get_format_bytes(gl_format format);
-
-extern GLint
-_mesa_get_format_bits(gl_format format, GLenum pname);
-
-extern GLenum
-_mesa_get_format_datatype(gl_format format);
-
-extern GLenum
-_mesa_get_format_base_format(gl_format format);
-
-extern void
-_mesa_get_format_block_size(gl_format format, GLuint *bw, GLuint *bh);
-
-extern GLboolean
-_mesa_is_format_compressed(gl_format format);
-
-extern GLboolean
-_mesa_is_format_packed_depth_stencil(gl_format format);
-
-extern GLboolean
-_mesa_is_format_integer_color(gl_format format);
-
-extern GLenum
-_mesa_get_format_color_encoding(gl_format format);
-
-extern GLuint
-_mesa_format_image_size(gl_format format, GLsizei width,
- GLsizei height, GLsizei depth);
-
-extern uint64_t
-_mesa_format_image_size64(gl_format format, GLsizei width,
- GLsizei height, GLsizei depth);
-
-extern GLint
-_mesa_format_row_stride(gl_format format, GLsizei width);
-
-extern void
-_mesa_format_to_type_and_comps(gl_format format,
- GLenum *datatype, GLuint *comps);
-
-extern void
-_mesa_test_formats(void);
-
-extern gl_format
-_mesa_get_srgb_format_linear(gl_format format);
-
-#endif /* FORMATS_H */
+/* + * Mesa 3-D graphics library + * Version: 7.7 + * + * Copyright (C) 1999-2008 Brian Paul All Rights Reserved. + * Copyright (c) 2008-2009 VMware, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN + * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + */ + +/* + * Authors: + * Brian Paul + */ + + +#ifndef FORMATS_H +#define FORMATS_H + + +#include <GL/gl.h> + +/* OpenGL doesn't have GL_UNSIGNED_BYTE_4_4, so we must define our own type + * for GL_LUMINANCE4_ALPHA4. */ +#define MESA_UNSIGNED_BYTE_4_4 (GL_UNSIGNED_BYTE<<1) + + +/** + * Mesa texture/renderbuffer image formats. + */ +typedef enum +{ + MESA_FORMAT_NONE = 0, + + /** + * \name Basic hardware formats + */ + /*@{*/ + /* msb <------ TEXEL BITS -----------> lsb */ + /* ---- ---- ---- ---- ---- ---- ---- ---- */ + MESA_FORMAT_RGBA8888, /* RRRR RRRR GGGG GGGG BBBB BBBB AAAA AAAA */ + MESA_FORMAT_RGBA8888_REV, /* AAAA AAAA BBBB BBBB GGGG GGGG RRRR RRRR */ + MESA_FORMAT_ARGB8888, /* AAAA AAAA RRRR RRRR GGGG GGGG BBBB BBBB */ + MESA_FORMAT_ARGB8888_REV, /* BBBB BBBB GGGG GGGG RRRR RRRR AAAA AAAA */ + MESA_FORMAT_XRGB8888, /* xxxx xxxx RRRR RRRR GGGG GGGG BBBB BBBB */ + MESA_FORMAT_XRGB8888_REV, /* BBBB BBBB GGGG GGGG RRRR RRRR xxxx xxxx */ + MESA_FORMAT_RGB888, /* RRRR RRRR GGGG GGGG BBBB BBBB */ + MESA_FORMAT_BGR888, /* BBBB BBBB GGGG GGGG RRRR RRRR */ + MESA_FORMAT_RGB565, /* RRRR RGGG GGGB BBBB */ + MESA_FORMAT_RGB565_REV, /* GGGB BBBB RRRR RGGG */ + MESA_FORMAT_ARGB4444, /* AAAA RRRR GGGG BBBB */ + MESA_FORMAT_ARGB4444_REV, /* GGGG BBBB AAAA RRRR */ + MESA_FORMAT_RGBA5551, /* RRRR RGGG GGBB BBBA */ + MESA_FORMAT_ARGB1555, /* ARRR RRGG GGGB BBBB */ + MESA_FORMAT_ARGB1555_REV, /* GGGB BBBB ARRR RRGG */ + MESA_FORMAT_AL44, /* AAAA LLLL */ + MESA_FORMAT_AL88, /* AAAA AAAA LLLL LLLL */ + MESA_FORMAT_AL88_REV, /* LLLL LLLL AAAA AAAA */ + MESA_FORMAT_AL1616, /* AAAA AAAA AAAA AAAA LLLL LLLL LLLL LLLL */ + MESA_FORMAT_AL1616_REV, /* LLLL LLLL LLLL LLLL AAAA AAAA AAAA AAAA */ + MESA_FORMAT_RGB332, /* RRRG GGBB */ + MESA_FORMAT_A8, /* AAAA AAAA */ + MESA_FORMAT_A16, /* AAAA AAAA AAAA AAAA */ + MESA_FORMAT_L8, /* LLLL LLLL */ + MESA_FORMAT_L16, /* LLLL LLLL LLLL LLLL */ + MESA_FORMAT_I8, /* IIII IIII */ + MESA_FORMAT_I16, /* IIII IIII IIII IIII */ + MESA_FORMAT_CI8, /* CCCC CCCC */ + MESA_FORMAT_YCBCR, /* YYYY YYYY UorV UorV */ + MESA_FORMAT_YCBCR_REV, /* UorV UorV YYYY YYYY */ + MESA_FORMAT_R8, /* RRRR RRRR */ + MESA_FORMAT_RG88, /* RRRR RRRR GGGG GGGG */ + MESA_FORMAT_RG88_REV, /* GGGG GGGG RRRR RRRR */ + MESA_FORMAT_R16, /* RRRR RRRR RRRR RRRR */ + MESA_FORMAT_RG1616, /* RRRR RRRR RRRR RRRR GGGG GGGG GGGG GGGG */ + MESA_FORMAT_RG1616_REV, /* GGGG GGGG GGGG GGGG RRRR RRRR RRRR RRRR */ + MESA_FORMAT_ARGB2101010, /* AARR RRRR RRRR GGGG GGGG GGBB BBBB BBBB */ + MESA_FORMAT_Z24_S8, /* ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ SSSS SSSS */ + MESA_FORMAT_S8_Z24, /* SSSS SSSS ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ */ + MESA_FORMAT_Z16, /* ZZZZ ZZZZ ZZZZ ZZZZ */ + MESA_FORMAT_X8_Z24, /* xxxx xxxx ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ */ + MESA_FORMAT_Z24_X8, /* ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ xxxx xxxx */ + MESA_FORMAT_Z32, /* ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ ZZZZ */ + MESA_FORMAT_S8, /* SSSS SSSS */ + /*@}*/ + + /** + * \name 8-bit/channel sRGB formats + */ + /*@{*/ + MESA_FORMAT_SRGB8, + MESA_FORMAT_SRGBA8, + MESA_FORMAT_SARGB8, + MESA_FORMAT_SL8, + MESA_FORMAT_SLA8, + MESA_FORMAT_SRGB_DXT1, + MESA_FORMAT_SRGBA_DXT1, + MESA_FORMAT_SRGBA_DXT3, + MESA_FORMAT_SRGBA_DXT5, + /*@}*/ + + /** + * \name Compressed texture formats. + */ + /*@{*/ + MESA_FORMAT_RGB_FXT1, + MESA_FORMAT_RGBA_FXT1, + MESA_FORMAT_RGB_DXT1, + MESA_FORMAT_RGBA_DXT1, + MESA_FORMAT_RGBA_DXT3, + MESA_FORMAT_RGBA_DXT5, + /*@}*/ + + /** + * \name Floating point texture formats. + */ + /*@{*/ + MESA_FORMAT_RGBA_FLOAT32, + MESA_FORMAT_RGBA_FLOAT16, + MESA_FORMAT_RGB_FLOAT32, + MESA_FORMAT_RGB_FLOAT16, + MESA_FORMAT_ALPHA_FLOAT32, + MESA_FORMAT_ALPHA_FLOAT16, + MESA_FORMAT_LUMINANCE_FLOAT32, + MESA_FORMAT_LUMINANCE_FLOAT16, + MESA_FORMAT_LUMINANCE_ALPHA_FLOAT32, + MESA_FORMAT_LUMINANCE_ALPHA_FLOAT16, + MESA_FORMAT_INTENSITY_FLOAT32, + MESA_FORMAT_INTENSITY_FLOAT16, + MESA_FORMAT_R_FLOAT32, + MESA_FORMAT_R_FLOAT16, + MESA_FORMAT_RG_FLOAT32, + MESA_FORMAT_RG_FLOAT16, + /*@}*/ + + /** + * \name Non-normalized signed integer formats. + * XXX Note: these are just stand-ins for some better hardware + * formats TBD such as BGRA or ARGB. + */ + MESA_FORMAT_RGBA_INT8, + MESA_FORMAT_RGBA_INT16, + MESA_FORMAT_RGBA_INT32, + + /** + * \name Non-normalized unsigned integer formats. + */ + MESA_FORMAT_RGBA_UINT8, + MESA_FORMAT_RGBA_UINT16, + MESA_FORMAT_RGBA_UINT32, + + /* msb <------ TEXEL BITS -----------> lsb */ + /* ---- ---- ---- ---- ---- ---- ---- ---- */ + /** + * \name Signed fixed point texture formats. + */ + /*@{*/ + MESA_FORMAT_DUDV8, /* DUDU DUDU DVDV DVDV */ + MESA_FORMAT_SIGNED_R8, /* RRRR RRRR */ + MESA_FORMAT_SIGNED_RG88_REV, /* GGGG GGGG RRRR RRRR */ + MESA_FORMAT_SIGNED_RGBX8888, /* RRRR RRRR GGGG GGGG BBBB BBBB xxxx xxxx */ + MESA_FORMAT_SIGNED_RGBA8888, /* RRRR RRRR GGGG GGGG BBBB BBBB AAAA AAAA */ + MESA_FORMAT_SIGNED_RGBA8888_REV,/*AAAA AAAA BBBB BBBB GGGG GGGG RRRR RRRR */ + MESA_FORMAT_SIGNED_R16, /* RRRR RRRR RRRR RRRR */ + MESA_FORMAT_SIGNED_GR1616, /* GGGG GGGG GGGG GGGG RRRR RRRR RRRR RRRR */ + MESA_FORMAT_SIGNED_RGB_16, /* ushort[0]=R, ushort[1]=G, ushort[2]=B */ + MESA_FORMAT_SIGNED_RGBA_16, /* ... */ + MESA_FORMAT_RGBA_16, /* ... */ + /*@}*/ + + /*@{*/ + MESA_FORMAT_RED_RGTC1, + MESA_FORMAT_SIGNED_RED_RGTC1, + MESA_FORMAT_RG_RGTC2, + MESA_FORMAT_SIGNED_RG_RGTC2, + /*@}*/ + + /*@{*/ + MESA_FORMAT_L_LATC1, + MESA_FORMAT_SIGNED_L_LATC1, + MESA_FORMAT_LA_LATC2, + MESA_FORMAT_SIGNED_LA_LATC2, + /*@}*/ + + MESA_FORMAT_SIGNED_A8, /* AAAA AAAA */ + MESA_FORMAT_SIGNED_L8, /* LLLL LLLL */ + MESA_FORMAT_SIGNED_AL88, /* AAAA AAAA LLLL LLLL */ + MESA_FORMAT_SIGNED_I8, /* IIII IIII */ + MESA_FORMAT_SIGNED_A16, /* AAAA AAAA AAAA AAAA */ + MESA_FORMAT_SIGNED_L16, /* LLLL LLLL LLLL LLLL */ + MESA_FORMAT_SIGNED_AL1616, /* AAAA AAAA AAAA AAAA LLLL LLLL LLLL LLLL */ + MESA_FORMAT_SIGNED_I16, /* IIII IIII IIII IIII */ + + MESA_FORMAT_RGB9_E5_FLOAT, + MESA_FORMAT_R11_G11_B10_FLOAT, + + MESA_FORMAT_COUNT +} gl_format; + + +extern const char * +_mesa_get_format_name(gl_format format); + +extern GLint +_mesa_get_format_bytes(gl_format format); + +extern GLint +_mesa_get_format_bits(gl_format format, GLenum pname); + +extern GLenum +_mesa_get_format_datatype(gl_format format); + +extern GLenum +_mesa_get_format_base_format(gl_format format); + +extern void +_mesa_get_format_block_size(gl_format format, GLuint *bw, GLuint *bh); + +extern GLboolean +_mesa_is_format_compressed(gl_format format); + +extern GLboolean +_mesa_is_format_packed_depth_stencil(gl_format format); + +extern GLboolean +_mesa_is_format_integer_color(gl_format format); + +extern GLenum +_mesa_get_format_color_encoding(gl_format format); + +extern GLuint +_mesa_format_image_size(gl_format format, GLsizei width, + GLsizei height, GLsizei depth); + +extern uint64_t +_mesa_format_image_size64(gl_format format, GLsizei width, + GLsizei height, GLsizei depth); + +extern GLint +_mesa_format_row_stride(gl_format format, GLsizei width); + +extern void +_mesa_format_to_type_and_comps(gl_format format, + GLenum *datatype, GLuint *comps); + +extern void +_mesa_test_formats(void); + +extern gl_format +_mesa_get_srgb_format_linear(gl_format format); + +#endif /* FORMATS_H */ |