/**
\defgroup module_glload GL Load

The OpenGL Loading Library (GL Load) is the Unofficial OpenGL SDK library for initializing OpenGL's functions. Because of the nature of how OpenGL is implemented, it is necessary to fetch function pointers from OpenGL implementations, rather than simply statically linking to a library. The GL Load library exists to automate this process and make it simple.

The GL Load library is distributed under the <a href="http://www.opensource.org/licenses/MIT">MIT License</a>.

@section glload_headers GL Load Headers

The GL Load library provides a number of header files. To include them, simply put the
glload/include directory in your build system's include path. It also comes with
a static library which needs to be built. Build the static library as part of the
SDK's build process, and link to them as is normal for your build system.

There are two interfaces for GL Load: the C interface and the C++ interface. Files that end in <tt>.hpp</tt> are for C++, and files that end in <tt>.h</tt> are for C. C++ programs can freely include and use the C interface files.

All header files except <tt>glload/gll.h</tt> and <tt>glload/gll.hpp</tt> expose OpenGL functions or functions in WGL/GLX. For regular OpenGL functions, you need to include one of the headers of the form <tt>glload/gl_*.h</tt> or <tt>.hpp</tt>, where * is the version of OpenGL that you are coding against. For example, <tt>glload/gl_3_3.h</tt> represents the header for OpenGL version 3.3. There are also <tt>_comp</tt> verisons, such as <tt>glload/gl_3_3_comp.hpp</tt>, which includes the C++ headers for the OpenGL 3.3 compatibility profile.

Regardless of version number or core/compatibility issues, all OpenGL headers contain
function for every extension.

The headers <tt>glload/gl_all.h</tt> and <tt>glload/gl_all.hpp</tt> contain every function and enum definition for everything that has ever been in OpenGL, core or compatibility. The headers <tt>glload/gl_core.h</tt> and <tt>glload/gl_core.hpp</tt> contain all core functions and enums for the most recent version of OpenGL, as well as those for extensions. These will be updated as OpenGL is updated.

You should not use <tt>GL/gl.h</tt> in conjunction with these headers. Nor should it be used in conjunction with @em any other OpenGL headers (<tt>gl3.h</tt>, <tt>gl_ext.h</tt>, etc). Many OpenGL libraries, such as FreeGLUT, will include <tt>GL/gl.h</tt> for you. In those cases, make sure to include those headers \em after the GL Load headers.

Also, for each source file, you should pick @em one GL Load header and include only that. A single source file should not include both <tt>glload/gl_3_3_comp.hpp</tt> and <tt>glload/gl_4_2.hpp</tt>, for example.

It \em is allowable to include different headers in different files. The GL Load initialization process will load only the available entrypoints. Which functions are loaded is independent of the header included. So, if your implementation supports 3.3, you can freely use a 2.1 header in one source file, and a 3.2 header in another. Attempting to use a 4.2 header if the implementation only supports 3.3 is asking for trouble.

For WGL or GLX extensions, there are <tt>glload/wgl_exts.h</tt> and <tt>glload/glx_exts.h</tt>. These provide the extensions for these APIs, but not the non-extension functions. So unlike regular OpenGL, you will still need to include <tt>GL/glx.h</tt> and <tt>wgl.h</tt>

@section glload_initialization Initialization

The headers themselves are not useful unless GL Load has been initialized. That is, you @em cannot call any function or use any variable in these headers until GL Load has been initialized.

GL Load relies on mechanisms that are part of OpenGL to function. Therefore, you must have a valid OpenGL context that has been made current before you can initialize GL Load.

The headers that contain the functions to initialize GL Load are <tt>glload/gll.h</tt> and <tt>glload/gll.hpp</tt>. These are the C and C++ interfaces to GL Load initialization. You will only need to include the header of your choice in your initialization code; you don't need to include it everywhere that you use OpenGL.

The two interface function identically, and have the exact same parameters and return values. The only difference is that the C++ functions are in the @ref glload namespace and the C ones are global.

To initialize the OpenGL functions, call LoadFunctions. This function will respect the context's version number as well as its core/compatibility flags (for contexts that make such a distinction). If you create a core 3.3 context, then GL Load will only load functions that are available in that context. And similarly for compatibility.

Platform-specific extensions can be loaded with LoadWinFunctions/LoadGLXFunctions, for WGL or GLX respectively.

There are also some convenience functions, to make dealing with versions slightly easier. The GetMajorVersion and GetMinorVersion functions retrieve the major and minor OpenGL functions. These can @em only be called after a successful call to LoadFunctions.

The function IsVersionGEQ can be used to test if the current OpenGL version is at least the given version. This is useful for testing to see if functionality from a particular version is available.

@section glload_extensions Extensions

GL Load has support for OpenGL extensions. The initialization routines will initialize OpenGL extensions just as it includes the core functions. The OpenGL (and WGL/GLX) headers have some additional, extension-specific functionality.

Integer variables are provided to query whether an extension is available. These variables are of the form:

<code>
glext_<em>extension_name</em>
</code>

For example, if you wish to check to see if the GL_ARB_vertex_array_object extension is defined, you would test <tt>glext_ARB_vertex_array_object</tt> after initializing GL Load. If it is non-zero, then the extension is present. If it is 0, then it is not. This works the same between C and C++. For WGL/GLX extensions, this becomes wglext/glxext_*.

These variables only gain valid values @em after GL Load has been properly initialized.

@section glload_interface C and C++ Interface Headers

As previously stated, there are two interfaces: C and C++. The C interface looks identical to the OpenGL definitions. All of the functions and enums are at global scope, as are all of the various internal declarations that are needed to make GL Load work.

The C interface defines function pointers as extern variables prefixed by <tt>__glext</tt> or <tt>glext</tt>.

C++ programs may freely use the C interface; this makes them more compatible with source code you would find online. However, they may use the C++ interface as well. This pushes as much of OpenGL as possible into the <tt>gl</tt> namespace. All OpenGL enumerators are actual members of an enumeration in the <tt>gl</tt> namespace. All of the OpenGL functions are in the <tt>gl</tt> namespace.

The function names are different as well. Since they are in the gl namespace, the function names are not prefixed with "gl" Therefore, this interface does not. Therefore, the function that is usually seen as <tt>glVertexAttribPointer</tt> becomes <tt>gl::VertexAttribPointer</tt>.

Note that this is purely for convenience. OpenGL is still exposed directly, at a low level, to the user. There are no C++ classes or other types, nor does this interface provide overloaded functions for functions like <tt>glVertex3f</tt>, <tt>glVertex4f</tt>, etc. It does not change the actual OpenGL interface; it just makes OpenGL clutter the global namespace much less, as well as make tool parsing a bit easier due to not having to use \#defines.

There are some declarations that cannot be moved to a namespace. The glext_ variables cannot be moved to the <tt>gl</tt> namespace. The OpenGL defined types (GLfloat, GLint, etc) also are not placed in the namespace.

Note that the two interfaces all ultimately call the same functions. So you can use them interchangeably (though this is not suggested). You could use the C interface to glload to initialize GL Load, and use C++ headers to access the functions. Or vice-versa.

@section glload_example Example

Here is an example of using the C interface.

\code
#include <glload/gl_3_3.h>
#include <glload/gll.h>

//Include headers for FreeGLUT/GLFW/other GL tools.

int main(int argc, char *argv[])
{
  //Initialize OpenGL and bind the context
  
  if(LoadFunctions() == LS_LOAD_FAILED)
    //exit in some way
	
  //Loading succeeded. Now use OpenGL functions.
  
  //Render stuff
  GLuint vertShader = glCreateShader(GL_VERTEX_SHADER);
  GLuint fragShader = glCreateShader(GL_FRAGMENT_SHADER);
  ...
}
\endcode
	
Here is the same code, but written for the C++ interface.

\code
#include <glload/gl_3_3.hpp>
#include <glload/gll.hpp>

//Include headers for FreeGLUT/GLFW/other GL tools.

int main(int argc, char *argv[])
{
  //Initialize OpenGL and bind the context
  
  if(glload::LoadFunctions() == glload::LS_LOAD_FAILED)
    //exit in some way
	
  //Loading succeeded. Now use OpenGL functions.
  
  //Render stuff
  GLuint vertShader = gl::CreateShader(gl::GL_VERTEX_SHADER);
  GLuint fragShader = gl::CreateShader(gl::GL_FRAGMENT_SHADER);
  ...
}
\endcode

\section module_glload_apientry APIENTRY Redefinition Warning

On Windows, if you include one of the GL Load OpenGL headers in the same file that you include <tt>windows.h</tt> (or any file that includes it, such as <tt>GL/glfw.h</tt> or <tt>GL/freeglut.h</tt>), you will get a redefinition warning about APIENTRY.

APIENTRY is a macro defined originally in <tt>windows.h</tt>. However, it has effectively become a part of OpenGL's API. The extensions GL_ARB_debug_output and GL_AMD_debug_output cannot be used without the definition. On Windows, it is defined to something, but on other platforms it is empty.

Because APIENTRY is essentially part of OpenGL now, GL Load defines and exposes it in its headers. GL Load cannot simply undefine it at the end of its headers, because if it did so, you would have problems in source files that don't have to include <tt>windows.h</tt> (or files that include it).

For example, you could have this scenario:

\code
//main.cpp
#include <glload/gl_3_3.hpp>
#include <glload/gll.hpp>
#include <GL/glfw.h>

int main(int argc, char *argv[])
{
  //Setup stuff.
  DrawTheScreen();
}

//draw.cpp
#include <glload/gl_3_3.hpp>

void DrawTheScreen()
{
  //Do some drawing.
}
\endcode

<tt>draw.cpp</tt> does not need to talk to GLFW, so it does not include that header. However, if it wanted to register a function with GL_ARB_debug_output, it would not be able to do so cross-platform without a define for APIENTRY.

If the warning bothers you, you can undefine the enum just before including the file that includes <tt>windows.h</tt>:

\code
#include <glload/gl_3_3.hpp>
#include <glload/gll.hpp>
#undef APIENTRY
#include <GL/glfw.h>

int main(int argc, char *argv[])
{
  //Setup stuff.
}
\endcode

**/

/**
\defgroup module_glload_cinter GL Load C interface

\brief The C interface for initializing OpenGL.

\ingroup module_glload
**/

/**
\defgroup module_glload_cppinter GL Load C++ interface

\brief The C++ interface for initializing OpenGL.

\ingroup module_glload
**/

