glsl: Streamline the built-in type handling code.
authorKenneth Graunke <kenneth@whitecape.org>
Tue, 18 Jun 2013 11:22:33 +0000 (04:22 -0700)
committerKenneth Graunke <kenneth@whitecape.org>
Wed, 26 Jun 2013 18:25:12 +0000 (11:25 -0700)
commit4563dfe23a300f0fc1652a609f5ad9e9a755fb99
tree0ca947ae4eedef1de1006eb336bef41b3675b23c
parent818da74af542f50aa9c32c7471de58185c7de541
glsl: Streamline the built-in type handling code.

Over the last few years, the compiler has grown to support 7 different
language versions and 6 extensions that add new built-in types.  With
more and more features being added, some of our core code has devolved
into an unmaintainable spaghetti of sorts.

A few problems with the old code:
1. Built-in types are declared...where exactly?

   The types in builtin_types.h were organized in arrays by the language
   version or extension they were introduced in.  It's factored out to
   avoid duplicates---every type only exists in one array.  But that
   means that sampler1D is declared in 110, sampler2D is in core types,
   sampler3D is a unique global not in a list...and so on.

2. Spaghetti call-chains with weird parameters:

   generate_300ES_types calls generate_130_types which calls
   generate_120_types and generate_EXT_texture_array_types, which calls
   generate_110_types, which calls generate_100ES_types...and more

   Except that ES doesn't want 1D types, so we have a skip_1d parameter.
   add_deprecated also falls into this category.

3. Missing type accessors.

   Common types have convenience pointers (like glsl_type::vec4_type),
   but others may not be accessible at all without a symbol table (for
   example, sampler types).

4. Global variable declarations in a header file?

   #include "builtin_types.h" in two C++ files would break the build.

The new code addresses these problems.  All built-in types are declared
together in a single table, independent of when they were introduced.
The macro that declares a new built-in type also creates a convenience
pointer, so every type is available and it won't get out of sync.

The code to populate a symbol table with the appropriate types for a
particular language version and set of extensions is now a single
table-driven function.  The table lists the type name and GL/ES versions
when it was introduced (similar to how the lexer handles reserved
words).  A single loop adds types based on the language version.
Explicit extension checks then add additional types.  If they were
already added based on the language version, glsl_symbol_table simply
ignores the request to add them a second time, meaning we don't need
to worry about duplicates and can simply list types where they belong.

v2: Mark uvecs and shadow samplers as ES3 only, and 1DArrayShadow as
    unsupported in ES entirely.  Add a touch more doxygen.

Signed-off-by: Kenneth Graunke <kenneth@whitecape.org>
Reviewed-by: Eric Anholt <eric@anholt.net>
src/glsl/Makefile.sources
src/glsl/builtin_type_macros.h [new file with mode: 0644]
src/glsl/builtin_types.cpp [new file with mode: 0644]
src/glsl/builtin_types.h [deleted file]
src/glsl/glsl_types.cpp
src/glsl/glsl_types.h