[SCM] lwjgl - Lightweight Java Game Library branch, master, updated. debian/2.4.2+dfsg-1-15-g9e1325c

Gabriele Giacone gg0-guest at alioth.debian.org
Sat Jul 31 15:30:05 UTC 2010


This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "lwjgl - Lightweight Java Game Library".

The branch, master has been updated
       via  9e1325c6030cdee67037e90c5735cfe9724c8c3b (commit)
       via  d9138ee0e15fe98c6f957b8eeb16b4ed0af2d79a (commit)
       via  717a871a07ab61e4df5755b044e0f130125eebae (commit)
       via  5b99a42275eecc2a705bcb6577c5ec67169533a3 (commit)
       via  afc97edc2e4d07895a320e7197543c181195f55c (commit)
       via  f601bd75291461b758bdfc2090020e9ed276481e (commit)
       via  e7a25b8d7abe3a948b80a3f2f5492ab7f4871a35 (commit)
      from  c18443d43190319e8fb0bb926d7863b9ad1f9e58 (commit)

Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.

- Log -----------------------------------------------------------------
commit 9e1325c6030cdee67037e90c5735cfe9724c8c3b
Author: Gabriele Giacone <1o5g4r8o at gmail.com>
Date:   Sat Jul 31 17:21:46 2010 +0200

    dch

-----------------------------------------------------------------------

Summary of changes:
 build.xml                                          |    3 +-
 debian/changelog                                   |    7 +
 debian/control                                     |    2 +-
 debian/patches/00nomacosx                          |   99 ---
 debian/patches/01allarchs                          |   74 --
 debian/patches/02systemjinput                      |   23 -
 debian/patches/03javadoc                           |   13 -
 debian/patches/series                              |    4 -
 debian/rules                                       |    3 +
 platform_build/build-definitions.xml               |    2 +-
 platform_build/build-generator.xml                 |    6 +-
 platform_build/build-webstart.xml                  |   61 ++-
 src/java/org/lwjgl/BufferChecks.java               |   76 ++-
 src/java/org/lwjgl/LWJGLUtil.java                  |    8 +-
 src/java/org/lwjgl/Sys.java                        |    6 +-
 src/java/org/lwjgl/input/Mouse.java                |   16 +-
 src/java/org/lwjgl/openal/AL.java                  |   22 +-
 src/java/org/lwjgl/openal/ALC11.java               |    3 +
 src/java/org/lwjgl/openal/EFXUtil.java             |  225 ++++++
 .../org/lwjgl/opengl/AMDDebugOutputCallback.java   |  162 +++++
 src/java/org/lwjgl/opengl/AMDDebugOutputUtil.java  |   59 ++
 src/java/org/lwjgl/opengl/APIUtils.java            |    1 +
 src/java/org/lwjgl/opengl/AWTGLCanvas.java         |   39 +-
 src/java/org/lwjgl/opengl/AbstractDrawable.java    |   81 +++
 src/java/org/lwjgl/opengl/BaseReferences.java      |   22 +-
 src/java/org/lwjgl/opengl/Context.java             |   13 +-
 src/java/org/lwjgl/opengl/ContextAttribs.java      |   20 +-
 src/java/org/lwjgl/opengl/Display.java             |  148 ++---
 src/java/org/lwjgl/opengl/Drawable.java            |   24 +-
 src/java/org/lwjgl/opengl/DrawableLWJGL.java       |   24 +
 src/java/org/lwjgl/opengl/GLChecks.java            |   56 +-
 src/java/org/lwjgl/opengl/GLContext.java           |   20 +-
 src/java/org/lwjgl/opengl/LinuxDisplay.java        |  247 +++++++-
 src/java/org/lwjgl/opengl/MacOSXDisplay.java       |    7 +-
 src/java/org/lwjgl/opengl/Pbuffer.java             |   63 +--
 src/java/org/lwjgl/opengl/PixelFormat.java         |   53 ++-
 ...WTGLCanvasPeerInfo.java => SharedDrawable.java} |   24 +-
 src/java/org/lwjgl/opengl/WindowsDisplay.java      |    7 +-
 src/java/org/lwjgl/opengl/XRandR.java              |  285 +++++---
 src/java/org/lwjgl/test/openal/EFX10Test.java      |  464 ++++++++++++
 src/java/org/lwjgl/test/openal/OpenALInfo.java     |   74 ++-
 .../lwjgl/test/opengl/FullScreenWindowedTest.java  |    7 +-
 src/java/org/lwjgl/test/opengl/VBOIndexTest.java   |    5 +-
 src/java/org/lwjgl/test/opengl/VersionTest.java    |  137 +++-
 src/java/org/lwjgl/test/opengl/awt/DemoBox.java    |    4 +-
 .../BackgroundLoadTest.java}                       |  229 +++----
 .../test/opengl/multithread/BackgroundLoader.java  |  189 +++++
 src/java/org/lwjgl/util/WaveData.java              |    6 +-
 src/java/org/lwjgl/util/applet/AppletLoader.java   |  349 ++++++++--
 .../util/generator/{Extension.java => Alias.java}  |   25 +-
 src/java/org/lwjgl/util/generator/AutoSize.java    |    5 +-
 .../generator/ContextCapabilitiesGenerator.java    |   54 ++-
 .../org/lwjgl/util/generator/FieldsGenerator.java  |   85 ++-
 src/java/org/lwjgl/util/generator/GLpointer.java   |    1 +
 .../org/lwjgl/util/generator/GeneratorVisitor.java |   17 +-
 .../lwjgl/util/generator/JavaMethodsGenerator.java |   29 +-
 src/java/org/lwjgl/util/generator/Utils.java       |    8 +-
 src/native/common/extgl.h                          |    3 +
 src/native/common/org_lwjgl_openal_ALC10.c         |   13 +-
 .../org_lwjgl_opengl_AMDDebugOutputCallback.c}     |   59 +-
 src/native/linux/context.c                         |   20 +-
 src/native/linux/extgl_glx.c                       |    1 +
 src/native/linux/extgl_glx.h                       |    6 +
 src/native/linux/org_lwjgl_opengl_LinuxPeerInfo.c  |   30 +-
 src/native/linux/org_lwjgl_opengl_Pbuffer.c        |   30 +-
 src/native/windows/context.c                       |   22 +-
 src/native/windows/extgl_wgl.c                     |    1 +
 src/native/windows/extgl_wgl.h                     |   10 +
 src/native/windows/org_lwjgl_opengl_Pbuffer.c      |   34 +-
 .../windows/org_lwjgl_opengl_WindowsPeerInfo.c     |    7 +-
 src/templates/org/lwjgl/openal/AL10.java           |   29 +-
 src/templates/org/lwjgl/openal/EFX10.java          |  738 ++++++++++++++++++++
 .../org/lwjgl/opengl/AMD_debug_output.java         |   99 +++
 ...orm_feedback3.java => AMD_name_gen_delete.java} |   32 +-
 ...> AMD_transform_feedback3_lines_triangles.java} |    4 +-
 .../opengl/ARB_texture_buffer_object_rgb32.java    |    3 +
 .../lwjgl/opengl/ARB_texture_compression_bptc.java |    2 +
 .../org/lwjgl/opengl/ATI_vertex_array_object.java  |    5 +
 .../org/lwjgl/opengl/EXT_direct_state_access.java  |   32 +-
 src/templates/org/lwjgl/opengl/GL11.java           |    8 +-
 src/templates/org/lwjgl/opengl/GL15.java           |    2 +-
 src/templates/org/lwjgl/opengl/NV_fence.java       |    7 +
 ...on_query2.java => NV_multisample_coverage.java} |    9 +-
 83 files changed, 3790 insertions(+), 1112 deletions(-)

diff --git a/build.xml b/build.xml
index d625767..857af24 100644
--- a/build.xml
+++ b/build.xml
@@ -124,7 +124,6 @@
 			<fileset refid="lwjgl.fileset" />
 			<manifest>
 				<attribute name="Sealed" value="true"/>
-				<attribute name="Trusted-Library" value="true"/>
 			</manifest>
 		</jar>
 		
@@ -133,7 +132,6 @@
 			<fileset refid="lwjgl_util_applet.fileset" />
 			<manifest>
 				<attribute name="Sealed" value="true"/>
-				<attribute name="Trusted-Library" value="true"/>
 			</manifest>
 		</jar>
 
@@ -253,6 +251,7 @@
 			<class name="org.lwjgl.openal.AL" />
 			<class name="org.lwjgl.opengl.GLContext" />
 			<class name="org.lwjgl.opengl.Pbuffer" />
+			<class name="org.lwjgl.opengl.AMDDebugOutputCallback" />
 		</javah>
 	</target>
 	
diff --git a/debian/changelog b/debian/changelog
index eda8a3d..d429960 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -1,3 +1,10 @@
+lwjgl (2.5+dfsg-1) unstable; urgency=low
+
+  * New upstream release.
+  * Standards version to 3.9.1.
+
+ -- Gabriele Giacone <1o5g4r8o at gmail.com>  Sat, 31 Jul 2010 17:21:04 +0200
+
 lwjgl (2.4.2+dfsg2-1) unstable; urgency=low
 
   * +dfsg2: Removed trailing CRs from sources.
diff --git a/debian/control b/debian/control
index 47adc17..94e7594 100644
--- a/debian/control
+++ b/debian/control
@@ -7,7 +7,7 @@ Build-Depends: debhelper (>= 7.0.50~), javahelper, ant, ant-optional,
  default-jdk, libjinput-java, libxrandr-dev, libxxf86vm-dev, libxcursor-dev,
  libxt-dev
 Build-Depends-Indep: default-jdk-doc
-Standards-Version: 3.9.0
+Standards-Version: 3.9.1
 Vcs-Git: git://git.debian.org/pkg-java/lwjgl.git
 Vcs-Browser: http://git.debian.org/?p=pkg-java/lwjgl.git
 Homepage: http://lwjgl.org/
diff --git a/debian/patches/00nomacosx b/debian/patches/00nomacosx
deleted file mode 100644
index a565322..0000000
--- a/debian/patches/00nomacosx
+++ /dev/null
@@ -1,99 +0,0 @@
-Description: Removes references to macosx-related classes.
-Author: Gabriele Giacone <1o5g4r8o at gmail.com>
-
---- a/build.xml
-+++ b/build.xml
-@@ -234,7 +234,7 @@
- 			<class name="org.lwjgl.opengl.WindowsContextImplementation" />
- 		</javah>
- 		
--		<javah classpath="${lwjgl.bin}" destdir="${lwjgl.src.native}/macosx" force="yes">
-+<!--		<javah classpath="${lwjgl.bin}" destdir="${lwjgl.src.native}/macosx" force="yes">
- 			<class name="org.lwjgl.MacOSXSysImplementation" />
- 			<class name="org.lwjgl.opengl.MacOSXMouseEventQueue" />
- 			<class name="org.lwjgl.opengl.MacOSXCanvasPeerInfo" />
-@@ -242,7 +242,7 @@
- 			<class name="org.lwjgl.opengl.MacOSXPbufferPeerInfo" />
- 			<class name="org.lwjgl.opengl.MacOSXDisplay" />
- 			<class name="org.lwjgl.opengl.MacOSXContextImplementation" />
--		</javah>
-+		</javah>	-->
- 		
- 		<javah classpath="${lwjgl.bin}" destdir="${lwjgl.src.headers}" force="yes">
- 			<class name="org.lwjgl.opengl.AWTSurfaceLock" />
-@@ -298,13 +298,13 @@
- 				</tokenfilter>
- 			</filterchain>
- 		</loadfile>				
--		<loadfile srcfile="${lwjgl.src.native}/macosx/org_lwjgl_MacOSXSysImplementation.h" property="lwjgl.native.macosx.version">
-+<!--		<loadfile srcfile="${lwjgl.src.native}/macosx/org_lwjgl_MacOSXSysImplementation.h" property="lwjgl.native.macosx.version">
- 			<filterchain>
- 				<tokenfilter>
- 	    		<containsstring contains="#define org_lwjgl_MacOSXSysImplementation_JNI_VERSION"/>
- 				</tokenfilter>
- 			</filterchain>
--		</loadfile>
-+		</loadfile>	-->
- 		<echo>
- 			lwjgl.java.windows.version = ${lwjgl.java.windows.version}
- 			lwjgl.native.windows.version = ${lwjgl.native.windows.version}			
---- a/platform_build/build-applet.xml
-+++ b/platform_build/build-applet.xml
-@@ -1,7 +1,7 @@
- <project name="applet">
- 
- 	<!-- Create our packer task -->
--	<taskdef name="pack200" classname="com.sun.tools.apache.ant.pack200.Pack200Task" classpath="platform_build/Pack200Task.jar"/>
-+<!--	<taskdef name="pack200" classname="com.sun.tools.apache.ant.pack200.Pack200Task" classpath="platform_build/Pack200Task.jar"/>	-->
- 
- 	<target name="applet" depends="all">
- 		<antcall target="-applet">
---- a/src/java/org/lwjgl/MacOSXSysImplementation.java
-+++ b/src/java/org/lwjgl/MacOSXSysImplementation.java
-@@ -33,7 +33,7 @@
- 
- import java.awt.Toolkit;
- 
--import com.apple.eio.FileManager;
-+//import com.apple.eio.FileManager;
- 
- /**
-  *
-@@ -55,7 +55,7 @@
- 
- 	public boolean openURL(String url) {
- 		try {
--			FileManager.openURL(url);
-+//			FileManager.openURL(url);
- 			return true;
- 		} catch (Exception e) {
- 			LWJGLUtil.log("Exception occurred while trying to invoke browser: " + e);
---- a/src/java/org/lwjgl/opengl/MacOSXDisplay.java
-+++ b/src/java/org/lwjgl/opengl/MacOSXDisplay.java
-@@ -54,9 +54,9 @@
- import org.lwjgl.LWJGLException;
- import org.lwjgl.LWJGLUtil;
- 
--import com.apple.eawt.Application;
--import com.apple.eawt.ApplicationAdapter;
--import com.apple.eawt.ApplicationEvent;
-+//import com.apple.eawt.Application;
-+//import com.apple.eawt.ApplicationAdapter;
-+//import com.apple.eawt.ApplicationEvent;
- 
- final class MacOSXDisplay implements DisplayImplementation {
- 	private static final int PBUFFER_HANDLE_SIZE = 24;
-@@ -77,11 +77,11 @@
- 		try {
- 			AccessController.doPrivileged(new PrivilegedExceptionAction() {
- 				public Object run() throws Exception {
--					Application.getApplication().addApplicationListener(new ApplicationAdapter() {
-+/*					Application.getApplication().addApplicationListener(new ApplicationAdapter() {
- 						public final void handleQuit(ApplicationEvent event) {
- 							doHandleQuit();
- 						}
--					});
-+					});	*/
- 					return null;
- 				}
- 			});
diff --git a/debian/patches/01allarchs b/debian/patches/01allarchs
deleted file mode 100644
index 3faa8c5..0000000
--- a/debian/patches/01allarchs
+++ /dev/null
@@ -1,74 +0,0 @@
-Description: To build on all archs
-Author: Gabriele Giacone <1o5g4r8o at gmail.com>
-
---- a/platform_build/linux_ant/build.xml
-+++ b/platform_build/linux_ant/build.xml
-@@ -6,12 +6,14 @@
- 	<property name="libname64" value="liblwjgl64.so"/>
- 	<property name="libs32" value="-L/usr/X11R6/lib -L/usr/X11/lib -lm -lX11 -lXext -lXcursor -lXrandr -lpthread -L${java.home}/lib/i386 -ljawt" />
- 	<property name="libs64" value="-L/usr/X11R6/lib64 -L/usr/X11/lib64 -lm -lX11 -lXext -lXcursor -lXrandr -lXxf86vm -lpthread -L${java.home}/lib/amd64 -ljawt" />
-+	<property name="libs" value="-L/usr/X11R6/lib -L/usr/X11/lib -lm -lX11 -lXext -lXcursor -lXrandr -lXxf86vm -lpthread -L${java.home}/lib/${os.arch} -ljawt" />
- 	<property name="cflags32" value="-O2 -Wall -c -fPIC -std=c99 -Wunused"/>
- 
- 	<target name="clean">
- 		<delete>
- 			<fileset dir="x32"/>
- 			<fileset dir="x64"/>
-+			<fileset dir="deb"/>
- 			<fileset dir="." includes="*.o"/>
- 			<fileset dir="." includes="*.so"/>
- 		</delete>
-@@ -41,6 +43,7 @@
- 
- 		<property name="linker_flags32" value="${version_script_flags32} -shared -O2 -Wall -o ${libname32} ${libs32} ${xf86vm_lib}"/>
- 		<property name="linker_flags64" value="${version_script_flags64} -shared -O2 -Wall -o ${libname64} ${libs64} ${xf86vm_lib}"/>
-+		<property name="linker_flagsdeb" value="${version_script_flags32} -shared -O2 -Wall -o ${libname32} ${libs} ${xf86vm_lib}"/>
- 
-     	<condition property="build.32bit.only">
-     		<not>
-@@ -58,9 +61,12 @@
-     			<equals arg1="${hwplatform}" arg2="x86_64"/>
-     		</and>
-     	</condition>
-+
-+    	<condition property="build.debian">
-+    			<os name="Linux"/>
-+    	</condition>
-     	
--    	<antcall target="compile32"/>
--    	<antcall target="compile64"/>
-+    	<antcall target="compiledeb"/>
-     </target>
- 	
-     <target name="compile32" unless="build.64bit.only">
-@@ -114,4 +120,30 @@
- 			<fileset file="${libname64}"/>
- 		</apply>
-     </target>
-+
-+    <target name="compiledeb">    	
-+    	<mkdir dir="deb"/>
-+    	<apply dir="deb" executable="gcc" skipemptyfilesets="true" failonerror="true">
-+			<arg line="${cflags32} ${cflags_pthread}"/>
-+			<arg value="-I${java.home}/include"/>
-+			<arg value="-I${java.home}/include/linux"/>
-+			<arg value="-I${java.home}/../include"/>
-+			<arg value="-I${java.home}/../include/linux"/>
-+			<arg value="-I${java.home}/../include/solaris"/>
-+			<arg value="-I${native}/common"/>
-+			<arg value="-I${native}/linux"/>
-+			<mapper type="glob" from="*.c" to="*.o"/>
-+			<fileset dir="${native}/linux" includes="*.c"/>
-+			<fileset dir="${native}/generated" includes="*.c"/>
-+			<fileset dir="${native}/common" includes="*.c"/>
-+		</apply>
-+		<apply dir="." parallel="true" executable="gcc" failonerror="true">
-+			<srcfile/>
-+			<arg line="${linker_flagsdeb}"/>
-+			<fileset dir="deb" includes="*.o"/>
-+		</apply>
-+		<apply dir="." parallel="true" executable="strip" failonerror="true">
-+			<fileset file="${libname32}"/>
-+		</apply>
-+    </target>
- </project>
diff --git a/debian/patches/02systemjinput b/debian/patches/02systemjinput
deleted file mode 100644
index 6b6a6dc..0000000
--- a/debian/patches/02systemjinput
+++ /dev/null
@@ -1,23 +0,0 @@
-Description: To find system jinput libraries
-Author: Gabriele Giacone <1o5g4r8o at gmail.com>
-
---- a/build.xml
-+++ b/build.xml
-@@ -340,7 +340,7 @@
- 	
- 	<!-- Compiles the Java source code -->
- 	<target name="compile" description="Compiles the java source code" depends="-initialize">
--		<javac debug="yes" destdir="${lwjgl.bin}" source="1.4" target="1.4" classpath="${lwjgl.lib}/jinput.jar:${lwjgl.lib}/AppleJavaExtensions.jar" taskname="core">
-+		<javac debug="yes" destdir="${lwjgl.bin}" source="1.4" target="1.4" classpath="/usr/share/java/jinput.jar:/usr/share/java/jutils.jar:${lwjgl.lib}/AppleJavaExtensions.jar" taskname="core">
- 			<src path="${lwjgl.src}/java/"/>
- 			<src path="${lwjgl.src}/generated/"/>
- 			<include name="org/lwjgl/*.java"/>
-@@ -481,7 +481,7 @@
- 			<os name="Mac OS X" />
- 		</condition>
- 		<property name="native_path_expanded" location="${native_path}"/>
--		<java classname="${test.mainclass}" classpath="res:${lwjgl.lib}/lwjgl.jar:${lwjgl.lib}/lwjgl_util.jar:${lwjgl.lib}/lwjgl_test.jar:${lwjgl.lib}/jinput.jar" fork="true">
-+		<java classname="${test.mainclass}" classpath="res:${lwjgl.lib}/lwjgl.jar:${lwjgl.lib}/lwjgl_util.jar:${lwjgl.lib}/lwjgl_test.jar:/usr/share/java/jinput.jar:/usr/share/java/jutils.jar" fork="true">
- 			<sysproperty key="org.lwjgl.util.Debug" value="true"/>
- 			<sysproperty key="java.library.path" value="${native_path_expanded}"/>
- 			<arg line="${args}"/>
diff --git a/debian/patches/03javadoc b/debian/patches/03javadoc
deleted file mode 100644
index 1091f6f..0000000
--- a/debian/patches/03javadoc
+++ /dev/null
@@ -1,13 +0,0 @@
-Description: Upstream changes introduced in version 2.4.2+dfsg-4
-Author: Gabriele Giacone <1o5g4r8o at gmail.com>
-
---- lwjgl-2.4.2+dfsg.orig/build.xml
-+++ lwjgl-2.4.2+dfsg/build.xml
-@@ -491,6 +491,7 @@
- 	<!-- Creates the Javadoc -->
- 	<target name="javadoc" description="Creates javadoc from java source code">
- 		<javadoc destdir="${lwjgl.docs}/javadoc" classpath="${lwjgl.lib}/jinput.jar" author="true" version="true" use="true" source="1.4" windowtitle="LWJGL API" useexternalfile="true">
-+			<link href="/usr/share/doc/default-jdk-doc/api/" />
- 			<fileset refid="lwjgl.javadoc.fileset" />
- 			<doctitle><![CDATA[<h1>Lightweight Java Game Toolkit</h1>]]></doctitle>
- 			<bottom><![CDATA[<i>Copyright &#169; 2002-2009 lwjgl.org. All Rights Reserved.</i>]]></bottom>
diff --git a/debian/patches/series b/debian/patches/series
deleted file mode 100644
index 23dbd68..0000000
--- a/debian/patches/series
+++ /dev/null
@@ -1,4 +0,0 @@
-00nomacosx
-01allarchs
-02systemjinput
-03javadoc
diff --git a/debian/rules b/debian/rules
index 077bca8..c879aa0 100755
--- a/debian/rules
+++ b/debian/rules
@@ -1,5 +1,8 @@
 #!/usr/bin/make -f
 
+TG_BRANCHES=p/nomacosx p/allarchs p/systemjinput p/javadoc
+-include /usr/share/topgit/tg2quilt.mk
+
 NAME    := $(shell dpkg-parsechangelog| sed -n '/^Source/{s/Source: \(.*\)/\1/p}')
 VERSION := $(shell dpkg-parsechangelog| sed -n '/^Version/{s/Version: \(.*\)-[0-9]*$$/\1/;s/+dfsg//p}')
 TMPDIR  := $(NAME)-$(VERSION)
diff --git a/platform_build/build-definitions.xml b/platform_build/build-definitions.xml
index bca0657..c977dc4 100644
--- a/platform_build/build-definitions.xml
+++ b/platform_build/build-definitions.xml
@@ -12,7 +12,7 @@
 	<property name="lwjgl.docs" 					location="doc" />
 	<property name="lwjgl.temp" 					location="temp" />
 	<property name="lwjgl.res" 						location="res" />
-	<property name="lwjgl.version" 				value="2.4.2" />
+	<property name="lwjgl.version" 				value="2.5" />
 
 	<property name="opengl-template-pattern" value="org/lwjgl/opengl/GL*.java,org/lwjgl/opengl/ARB*.java,org/lwjgl/opengl/AMD*.java,org/lwjgl/opengl/APPLE*.java,org/lwjgl/opengl/ATI*.java,org/lwjgl/opengl/EXT*.java,org/lwjgl/opengl/NV*.java,org/lwjgl/opengl/NVX*.java,org/lwjgl/opengl/HP*.java,org/lwjgl/opengl/IBM*.java,org/lwjgl/opengl/SUN*.java,org/lwjgl/opengl/SGIS*.java,org/lwjgl/opengl/GREMEDY*.java"/>
 	<!-- ================================================================== -->
diff --git a/platform_build/build-generator.xml b/platform_build/build-generator.xml
index 8e9a596..b9bac2d 100644
--- a/platform_build/build-generator.xml
+++ b/platform_build/build-generator.xml
@@ -13,8 +13,10 @@
 		<javac debug="yes" srcdir="${lwjgl.src}/java/" destdir="${lwjgl.bin}" includes="org/lwjgl/util/generator/**.java" source="1.5" target="1.5" taskname="generator">
 			<compilerarg value="-Xlint:all"/>
 		</javac>
+        <!-- Compile helper classes used by the templates -->
 		<javac debug="yes" srcdir="${lwjgl.src}/java/" destdir="${lwjgl.bin}" source="1.4" target="1.4" taskname="generator">
 			<include name="org/lwjgl/opengl/GLSync.java"/>
+            <include name="org/lwjgl/opengl/AMDDebugOutputCallback.java"/>
 			<include name="org/lwjgl/opengl/PointerWrapper.java"/>
 		</javac>
 	</target>
@@ -37,7 +39,7 @@
 			<arg value="-d"/>
 			<arg path="${lwjgl.src.native}/generated"/>
 			<arg value="-Atypemap=org.lwjgl.util.generator.ALTypeMap"/>
-			<fileset dir="${lwjgl.src.templates}" includes="org/lwjgl/openal/AL10.java, org/lwjgl/openal/AL11.java"/>
+			<fileset dir="${lwjgl.src.templates}" includes="org/lwjgl/openal/AL10.java, org/lwjgl/openal/AL11.java, org/lwjgl/openal/EFX10.java"/>
 		</apply>
 	</target>
 	
@@ -55,7 +57,7 @@
 			<arg path="${lwjgl.src.native}/generated"/>
 			<arg value="-Atypemap=org.lwjgl.util.generator.ALTypeMap"/>
 			<arg value="-Ageneratechecks"/>
-			<fileset dir="${lwjgl.src.templates}" includes="org/lwjgl/openal/AL10.java, org/lwjgl/openal/AL11.java"/>
+			<fileset dir="${lwjgl.src.templates}" includes="org/lwjgl/openal/AL10.java, org/lwjgl/openal/AL11.java, org/lwjgl/openal/EFX10.java"/>
 		</apply>
 	</target>
 
diff --git a/platform_build/build-webstart.xml b/platform_build/build-webstart.xml
index 875254c..96aec03 100644
--- a/platform_build/build-webstart.xml
+++ b/platform_build/build-webstart.xml
@@ -7,7 +7,7 @@
 		  </antcall>
 	</target>
 	
-	<target name="webstart_demo-release" depends="jars">
+	<target name="webstart_demo-release">
 		<input 	message="Please type the password for the keystore" addproperty="sign.pwd"/>
 
 		<antcall target="-webstart_demo">
@@ -25,6 +25,8 @@
 		
 		<!-- unzip common files -->
 		<unzip src="${lwjgl.dist}/lwjgl-${lwjgl.version}.zip" dest="${lwjgl.temp}/jnlp/temp" overwrite="true"/>
+		<copy file="${lwjgl.lib}/lwjgl_test.jar" tofile="${lwjgl.temp}/jnlp/temp/lwjgl-${lwjgl.version}/lwjgl_test.jar"/>
+		<copy file="${lwjgl.lib}/lwjgl_util.jar" tofile="${lwjgl.temp}/jnlp/temp/lwjgl-${lwjgl.version}/lwjgl_util.jar"/>
 		
 		<!-- move files to unified structure -->
 		<move todir="${lwjgl.temp}/jnlp/temp">
@@ -36,18 +38,62 @@
 		<!-- move relevant files to root -->
 		<move todir="${lwjgl.temp}/jnlp/" flatten="true">
 			<fileset dir="${lwjgl.temp}/jnlp/temp">
-				<include name="**/**.jar"/>
+				<include name="**/jinput.jar"/>
+				<include name="**/lwjgl*.jar"/>
 			</fileset>
 		</move>
 		
+		<!-- update Trusted-Library -->
+		<jar destfile="${lwjgl.temp}/jnlp/lwjgl.jar" update="true">
+			<manifest>
+				<attribute name="Sealed" value="true"/>
+				<attribute name="Trusted-Library" value="true"/>
+			</manifest>
+		</jar>
+		
+		<jar destfile="${lwjgl.temp}/jnlp/jinput.jar" update="true">
+			<manifest>
+				<attribute name="Sealed" value="true"/>
+			</manifest>
+		</jar>
+		
+		<jar destfile="${lwjgl.temp}/jnlp/lwjgl_util.jar" update="true">
+			<manifest>
+				<attribute name="Sealed" value="true"/>
+			</manifest>
+		</jar>		
+		
 		<!-- create native jars -->
-		<jar destfile="${lwjgl.temp}/jnlp/native_windows.jar" basedir="${lwjgl.temp}/jnlp/temp/native/windows"/>
-		<jar destfile="${lwjgl.temp}/jnlp/native_linux.jar" basedir="${lwjgl.temp}/jnlp/temp/native/linux"/>
-		<jar destfile="${lwjgl.temp}/jnlp/native_macosx.jar" basedir="${lwjgl.temp}/jnlp/temp/native/macosx"/>
-		<jar destfile="${lwjgl.temp}/jnlp/native_solaris.jar" basedir="${lwjgl.temp}/jnlp/temp/native/solaris"/>
+		<jar destfile="${lwjgl.temp}/jnlp/native_windows.jar" basedir="${lwjgl.temp}/jnlp/temp/native/windows">
+			<manifest>
+				<attribute name="Sealed" value="true"/>
+			</manifest>		
+		</jar>
+		
+		<jar destfile="${lwjgl.temp}/jnlp/native_linux.jar" basedir="${lwjgl.temp}/jnlp/temp/native/linux">
+			<manifest>
+				<attribute name="Sealed" value="true"/>
+			</manifest>		
+		</jar>
+		
+		<jar destfile="${lwjgl.temp}/jnlp/native_macosx.jar" basedir="${lwjgl.temp}/jnlp/temp/native/macosx">
+			<manifest>
+				<attribute name="Sealed" value="true"/>
+			</manifest>		
+		</jar>
+		
+		<jar destfile="${lwjgl.temp}/jnlp/native_solaris.jar" basedir="${lwjgl.temp}/jnlp/temp/native/solaris">
+			<manifest>
+				<attribute name="Sealed" value="true"/>
+			</manifest>		
+		</jar>
 		
 		<!-- create media jar -->
-		<jar destfile="${lwjgl.temp}/jnlp/media.jar" basedir="${lwjgl.res}"/>	
+		<jar destfile="${lwjgl.temp}/jnlp/media.jar" basedir="${lwjgl.res}">
+			<manifest>
+				<attribute name="Sealed" value="true"/>
+			</manifest>		
+		</jar>
 	
 		<!-- sign 'em -->
 		<signjar jar="${lwjgl.temp}/jnlp/lwjgl.jar" 		alias="${alias}" keystore="${keystore}" storepass="${password}"/>
@@ -57,5 +103,6 @@
 		<signjar jar="${lwjgl.temp}/jnlp/native_macosx.jar" alias="${alias}" keystore="${keystore}" storepass="${password}"/>
 		<signjar jar="${lwjgl.temp}/jnlp/native_windows.jar" 	alias="${alias}" keystore="${keystore}" storepass="${password}"/>
 		<signjar jar="${lwjgl.temp}/jnlp/jinput.jar" 		alias="${alias}" keystore="${keystore}" storepass="${password}"/>
+		<signjar jar="${lwjgl.temp}/jnlp/media.jar" 		alias="${alias}" keystore="${keystore}" storepass="${password}"/>
 	</target>
 </project>
\ No newline at end of file
diff --git a/src/java/org/lwjgl/BufferChecks.java b/src/java/org/lwjgl/BufferChecks.java
index e982e8b..b35a4a4 100644
--- a/src/java/org/lwjgl/BufferChecks.java
+++ b/src/java/org/lwjgl/BufferChecks.java
@@ -48,8 +48,8 @@ import java.nio.LongBuffer;
  * </p>
  * @author cix_foo <cix_foo at users.sourceforge.net>
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 3279 $
- * $Id: BufferChecks.java 3279 2010-03-11 21:06:49Z spasi $
+ * @version $Revision: 3334 $
+ * $Id: BufferChecks.java 3334 2010-04-22 23:21:48Z spasi $
  */
 public class BufferChecks {
 	/** Static methods only! */
@@ -60,7 +60,7 @@ public class BufferChecks {
 	 * Helper methods to ensure a function pointer is not-null (0)
 	 */
 	public static void checkFunctionAddress(long pointer) {
-		if (pointer == 0) {
+		if (LWJGLUtil.CHECKS && pointer == 0) {
 			throw new IllegalStateException("Function is not supported");
 		}
 	}
@@ -69,20 +69,22 @@ public class BufferChecks {
 	 * Helper methods to ensure a ByteBuffer is null-terminated
 	 */
 	public static void checkNullTerminated(ByteBuffer buf) {
-		if (buf.get(buf.limit() - 1) != 0) {
+		if ( LWJGLUtil.CHECKS && buf.get(buf.limit() - 1) != 0) {
 			throw new IllegalArgumentException("Missing null termination");
 		}
 	}
 
 	public static void checkNullTerminated(ByteBuffer buf, int count) {
-		int nullFound = 0;
-		for ( int i = buf.position(); i < buf.limit(); i++ ) {
-			if ( buf.get(i) == 0 )
-				nullFound++;
+		if ( LWJGLUtil.CHECKS ) {
+			int nullFound = 0;
+			for ( int i = buf.position(); i < buf.limit(); i++ ) {
+				if ( buf.get(i) == 0 )
+					nullFound++;
+			}
+
+			if ( nullFound < count )
+				throw new IllegalArgumentException("Missing null termination");
 		}
-
-		if ( nullFound < count )
-			throw new IllegalArgumentException("Missing null termination");
 	}
 
 	/** Helper methods to ensure an IntBuffer is null-terminated */
@@ -93,7 +95,7 @@ public class BufferChecks {
 	}
 
 	public static void checkNotNull(Object o) {
-		if (o == null)
+		if ( LWJGLUtil.CHECKS && o == null)
 			throw new IllegalArgumentException("Null argument");
 	}
 
@@ -101,37 +103,37 @@ public class BufferChecks {
 	 * Helper methods to ensure a buffer is direct (and, implicitly, non-null).
 	 */
 	public static void checkDirect(ByteBuffer buf) {
-		if (!buf.isDirect()) {
+		if ( LWJGLUtil.CHECKS && !buf.isDirect()) {
 			throw new IllegalArgumentException("ByteBuffer is not direct");
 		}
 	}
 
 	public static void checkDirect(ShortBuffer buf) {
-		if (!buf.isDirect()) {
+		if ( LWJGLUtil.CHECKS && !buf.isDirect()) {
 			throw new IllegalArgumentException("ShortBuffer is not direct");
 		}
 	}
 
 	public static void checkDirect(IntBuffer buf) {
-		if (!buf.isDirect()) {
+		if ( LWJGLUtil.CHECKS && !buf.isDirect()) {
 			throw new IllegalArgumentException("IntBuffer is not direct");
 		}
 	}
 
 	public static void checkDirect(LongBuffer buf) {
-		if (!buf.isDirect()) {
+		if ( LWJGLUtil.CHECKS && !buf.isDirect()) {
 			throw new IllegalArgumentException("LongBuffer is not direct");
 		}
 	}
 
 	public static void checkDirect(FloatBuffer buf) {
-		if (!buf.isDirect()) {
+		if ( LWJGLUtil.CHECKS && !buf.isDirect()) {
 			throw new IllegalArgumentException("FloatBuffer is not direct");
 		}
 	}
 
 	public static void checkDirect(DoubleBuffer buf) {
-		if (!buf.isDirect()) {
+		if ( LWJGLUtil.CHECKS && !buf.isDirect()) {
 			throw new IllegalArgumentException("DoubleBuffer is not direct");
 		}
 	}
@@ -154,38 +156,50 @@ public class BufferChecks {
 	 * @throws IllegalArgumentException
 	 */
 	public static void checkBufferSize(Buffer buf, int size) {
-		if (buf.remaining() < size) {
+		if ( LWJGLUtil.CHECKS && buf.remaining() < size) {
 			throwBufferSizeException(buf, size);
 		}
 	}
 
 	public static void checkBuffer(ByteBuffer buf, int size) {
-		checkBufferSize(buf, size);
-		checkDirect(buf);
+		if ( LWJGLUtil.CHECKS ) {
+			checkBufferSize(buf, size);
+			checkDirect(buf);
+		}
 	}
 
 	public static void checkBuffer(ShortBuffer buf, int size) {
-		checkBufferSize(buf, size);
-		checkDirect(buf);
+		if ( LWJGLUtil.CHECKS ) {
+			checkBufferSize(buf, size);
+			checkDirect(buf);
+		}
 	}
 
 	public static void checkBuffer(IntBuffer buf, int size) {
-		checkBufferSize(buf, size);
-		checkDirect(buf);
+		if ( LWJGLUtil.CHECKS ) {
+			checkBufferSize(buf, size);
+			checkDirect(buf);
+		}
 	}
 
 	public static void checkBuffer(LongBuffer buf, int size) {
-		checkBufferSize(buf, size);
-		checkDirect(buf);
+		if ( LWJGLUtil.CHECKS ) {
+			checkBufferSize(buf, size);
+			checkDirect(buf);
+		}
 	}
 
 	public static void checkBuffer(FloatBuffer buf, int size) {
-		checkBufferSize(buf, size);
-		checkDirect(buf);
+		if ( LWJGLUtil.CHECKS ) {
+			checkBufferSize(buf, size);
+			checkDirect(buf);
+		}
 	}
 
 	public static void checkBuffer(DoubleBuffer buf, int size) {
-		checkBufferSize(buf, size);
-		checkDirect(buf);
+		if ( LWJGLUtil.CHECKS ) {
+			checkBufferSize(buf, size);
+			checkDirect(buf);
+		}
 	}
 }
diff --git a/src/java/org/lwjgl/LWJGLUtil.java b/src/java/org/lwjgl/LWJGLUtil.java
index 86ab4f6..ad4e82f 100644
--- a/src/java/org/lwjgl/LWJGLUtil.java
+++ b/src/java/org/lwjgl/LWJGLUtil.java
@@ -49,8 +49,8 @@ import java.util.StringTokenizer;
  * </p>
  *
  * @author Brian Matzon <brian at matzon.dk>
- * @version $Revision: 2983 $
- * $Id: LWJGLUtil.java 2983 2008-04-07 18:36:09Z matzon $
+ * @version $Revision: 3334 $
+ * $Id: LWJGLUtil.java 3334 2010-04-22 23:21:48Z spasi $
  */
 public class LWJGLUtil {
 	public static final int PLATFORM_LINUX 				= 1;
@@ -266,7 +266,9 @@ public class LWJGLUtil {
 
 	/** Debug flag. */
 	public static final boolean DEBUG = getPrivilegedBoolean("org.lwjgl.util.Debug");
-	
+
+	public static final boolean CHECKS = !getPrivilegedBoolean("org.lwjgl.util.NoChecks");
+
 	static {
 		LWJGLIcon16x16.flip();
 		LWJGLIcon32x32.flip();
diff --git a/src/java/org/lwjgl/Sys.java b/src/java/org/lwjgl/Sys.java
index c1e0344..7b2c528 100644
--- a/src/java/org/lwjgl/Sys.java
+++ b/src/java/org/lwjgl/Sys.java
@@ -46,15 +46,15 @@ import org.lwjgl.input.Mouse;
  * System class (named Sys so as not to conflict with java.lang.System)
  * </p>
  * @author cix_foo <cix_foo at users.sourceforge.net>
- * @version $Revision: 3328 $
- * $Id: Sys.java 3328 2010-04-15 18:03:54Z matzon $
+ * @version $Revision: 3353 $
+ * $Id: Sys.java 3353 2010-05-24 22:39:06Z matzon $
  */
 public final class Sys {
 	/** The native library name */
 	private static final String JNI_LIBRARY_NAME = "lwjgl";
 
 	/** Current version of library */
-	private static final String VERSION = "2.4.2";
+	private static final String VERSION = "2.5";
 
 	/** The implementation instance to delegate platform specific behavior to */
 	private final static SysImplementation implementation;
diff --git a/src/java/org/lwjgl/input/Mouse.java b/src/java/org/lwjgl/input/Mouse.java
index 028d8e7..06cabc8 100644
--- a/src/java/org/lwjgl/input/Mouse.java
+++ b/src/java/org/lwjgl/input/Mouse.java
@@ -59,8 +59,8 @@ import org.lwjgl.opengl.InputImplementation;
  * @author cix_foo <cix_foo at users.sourceforge.net>
  * @author elias_naur <elias_naur at users.sourceforge.net>
  * @author Brian Matzon <brian at matzon.dk>
- * @version $Revision: 3297 $
- * $Id: Mouse.java 3297 2010-03-27 16:04:30Z kappa1 $
+ * @version $Revision: 3337 $
+ * $Id: Mouse.java 3337 2010-04-29 17:37:18Z matzon $
  */
 public class Mouse {
 	/** Internal use - event size in bytes */
@@ -467,7 +467,7 @@ public class Mouse {
 	}
 
 	/**
-	 * @return Current events delta x. Only valid when the mouse is grabbed.
+	 * @return Current events delta x.
 	 */
 	public static int getEventDX() {
 		synchronized (OpenGLPackageAccess.global_lock) {
@@ -476,7 +476,7 @@ public class Mouse {
 	}
 
 	/**
-	 * @return Current events delta y. Only valid when the mouse is grabbed.
+	 * @return Current events delta y.
 	 */
 	public static int getEventDY() {
 		synchronized (OpenGLPackageAccess.global_lock) {
@@ -485,7 +485,7 @@ public class Mouse {
 	}
 
 	/**
-	 * @return Current events absolute x. Only valid when the mouse is not grabbed.
+	 * @return Current events absolute x.
 	 */
 	public static int getEventX() {
 		synchronized (OpenGLPackageAccess.global_lock) {
@@ -494,7 +494,7 @@ public class Mouse {
 	}
 
 	/**
-	 * @return Current events absolute y. Only valid when the mouse is not grabbed.
+	 * @return Current events absolute y.
 	 */
 	public static int getEventY() {
 		synchronized (OpenGLPackageAccess.global_lock) {
@@ -550,7 +550,7 @@ public class Mouse {
 	}
 
 	/**
-	 * @return Movement on the x axis since last time getDX() was called. Only valid when the mouse is grabbed.
+	 * @return Movement on the x axis since last time getDX() was called.
 	 */
 	public static int getDX() {
 		synchronized (OpenGLPackageAccess.global_lock) {
@@ -561,7 +561,7 @@ public class Mouse {
 	}
 
 	/**
-	 * @return Movement on the y axis since last time getDY() was called. Only valid when the mouse is grabbed.
+	 * @return Movement on the y axis since last time getDY() was called.
 	 */
 	public static int getDY() {
 		synchronized (OpenGLPackageAccess.global_lock) {
diff --git a/src/java/org/lwjgl/openal/AL.java b/src/java/org/lwjgl/openal/AL.java
index a689880..9c9bc70 100644
--- a/src/java/org/lwjgl/openal/AL.java
+++ b/src/java/org/lwjgl/openal/AL.java
@@ -42,8 +42,8 @@ import org.lwjgl.Sys;
  * </p>
  *
  * @author Brian Matzon <brian at matzon.dk>
- * @version $Revision: 3182 $
- * $Id: AL.java 3182 2009-03-17 21:36:18Z matzon $
+ * @version $Revision: 3348 $
+ * $Id: AL.java 3348 2010-05-24 21:54:37Z matzon $
  */
 public final class AL {
 	/** ALCdevice instance. */
@@ -160,8 +160,9 @@ public final class AL {
 			
 			if(openDevice) {
 				device = ALC10.alcOpenDevice(deviceArguments);
-				if (device == null)
+				if (device == null) {
 					throw new LWJGLException("Could not open ALC device");
+				}
 	
 				if (contextFrequency == -1) {
 					context = ALC10.alcCreateContext(device, null);
@@ -177,7 +178,18 @@ public final class AL {
 			throw e;
 		}
 				
-		ALC11.initialize();				
+		ALC11.initialize();
+
+		// Load EFX10 native stubs if ALC_EXT_EFX is supported.
+		// Is there any situation where the current device supports ALC_EXT_EFX and one
+		// later created by the user does not?
+		// Do we have to call resetNativeStubs(EFX10.class); somewhere? Not done for AL11
+		// either.
+		// This can either be here or in ALC11, since ALC_EXT_EFX indirectly requires AL 1.1
+		// for functions like alSource3i.
+		if (ALC10.alcIsExtensionPresent(device, EFX10.ALC_EXT_EFX_NAME)){
+		    EFX10.initNativeStubs();
+		}
 	}
 
 	/**
@@ -205,8 +217,10 @@ public final class AL {
 			device = null;
 		}
 		resetNativeStubs(AL10.class);
+		resetNativeStubs(AL11.class);
 		resetNativeStubs(ALC10.class);
 		resetNativeStubs(ALC11.class);
+		resetNativeStubs(EFX10.class);
 
 		if (created)
 			nDestroy();
diff --git a/src/java/org/lwjgl/openal/ALC11.java b/src/java/org/lwjgl/openal/ALC11.java
index b470440..1f7f88d 100644
--- a/src/java/org/lwjgl/openal/ALC11.java
+++ b/src/java/org/lwjgl/openal/ALC11.java
@@ -59,6 +59,9 @@ public final class ALC11 {
 	public static final int ALC_CAPTURE_DEFAULT_DEVICE_SPECIFIER		= 0x311;
 	public static final int ALC_CAPTURE_SAMPLES							= 0x312;
 	
+	public static final int ALC_MONO_SOURCES							= 0x1010;
+	public static final int ALC_STEREO_SOURCES							= 0x1011;
+	
 	/**
 	 * The alcCaptureOpenDevice function allows the application to connect to a capture
 	 * device. To obtain a list of all available capture devices, use getCaptureDevices a list of all
diff --git a/src/java/org/lwjgl/openal/EFXUtil.java b/src/java/org/lwjgl/openal/EFXUtil.java
new file mode 100644
index 0000000..780e3f6
--- /dev/null
+++ b/src/java/org/lwjgl/openal/EFXUtil.java
@@ -0,0 +1,225 @@
+/* 
+ * Copyright (c) 2002-2010 LWJGL Project
+ * All rights reserved.
+ * 
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are 
+ * met:
+ * 
+ * * Redistributions of source code must retain the above copyright 
+ *   notice, this list of conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ *
+ * * Neither the name of 'LWJGL' nor the names of 
+ *   its contributors may be used to endorse or promote products derived 
+ *   from this software without specific prior written permission.
+ * 
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR 
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package org.lwjgl.openal;
+
+/**
+ * Utility class for the OpenAL extension ALC_EXT_EFX. Provides functions to check for the extension
+ * and support of various effects and filters.
+ * <p>
+ * Currently supports ALC_EXT_EFX version 1.0 effects and filters.
+ *
+ * @author Ciardhubh <ciardhubh[at]ciardhubh.de>
+ * @version $Revision$
+ * $Id$
+ */
+public final class EFXUtil {
+
+    /** Constant for testSupportGeneric to check an effect. */
+    private static final int EFFECT = 1111;
+    /** Constant for testSupportGeneric to check a filter. */
+    private static final int FILTER = 2222;
+
+    /** Utility class, hidden contructor. */
+    private EFXUtil() {
+    }
+
+    /**
+     * Checks if OpenAL implementation is loaded and supports ALC_EXT_EFX.
+     *
+     * @return True if ALC_EXT_EFX is supported, false if not.
+     * @throws OpenALException If OpenAL has not been created yet.
+     */
+    public static boolean isEfxSupported() {
+        if (!AL.isCreated()) {
+            throw new OpenALException("OpenAL has not been created.");
+        }
+        return ALC10.alcIsExtensionPresent(AL.getDevice(), EFX10.ALC_EXT_EFX_NAME);
+    }
+
+    /**
+     * Tests OpenAL to see whether the given effect type is supported. This is done by creating an
+     * effect of the given type. If creation succeeds the effect is supported.
+     *
+     * @param effectType Type of effect whose support is to be tested, e.g. AL_EFFECT_REVERB.
+     * @return True if it is supported, false if not.
+     * @throws OpenALException If the request fails due to an AL_OUT_OF_MEMORY error or OpenAL has
+     * not been created yet.
+     * @throws IllegalArgumentException effectType is not a valid effect type.
+     */
+    public static boolean isEffectSupported(final int effectType) {
+        // Make sure type is a real effect.
+        switch (effectType) {
+            case EFX10.AL_EFFECT_NULL:
+            case EFX10.AL_EFFECT_EAXREVERB:
+            case EFX10.AL_EFFECT_REVERB:
+            case EFX10.AL_EFFECT_CHORUS:
+            case EFX10.AL_EFFECT_DISTORTION:
+            case EFX10.AL_EFFECT_ECHO:
+            case EFX10.AL_EFFECT_FLANGER:
+            case EFX10.AL_EFFECT_FREQUENCY_SHIFTER:
+            case EFX10.AL_EFFECT_VOCAL_MORPHER:
+            case EFX10.AL_EFFECT_PITCH_SHIFTER:
+            case EFX10.AL_EFFECT_RING_MODULATOR:
+            case EFX10.AL_EFFECT_AUTOWAH:
+            case EFX10.AL_EFFECT_COMPRESSOR:
+            case EFX10.AL_EFFECT_EQUALIZER:
+                break;
+            default:
+                throw new IllegalArgumentException("Unknown or invalid effect type: " + effectType);
+        }
+
+        return testSupportGeneric(EFFECT, effectType);
+    }
+
+    /**
+     * Tests OpenAL to see whether the given filter type is supported. This is done by creating a
+     * filter of the given type. If creation succeeds the filter is supported.
+     *
+     * @param filterType Type of filter whose support is to be tested, e.g. AL_FILTER_LOWPASS.
+     * @return True if it is supported, false if not.
+     * @throws OpenALException If the request fails due to an AL_OUT_OF_MEMORY error or OpenAL has
+     * not been created yet.
+     * @throws IllegalArgumentException filterType is not a valid filter type.
+     */
+    public static boolean isFilterSupported(final int filterType) {
+        // Make sure type is a real filter.
+        switch (filterType) {
+            case EFX10.AL_FILTER_NULL:
+            case EFX10.AL_FILTER_LOWPASS:
+            case EFX10.AL_FILTER_HIGHPASS:
+            case EFX10.AL_FILTER_BANDPASS:
+                break;
+            default:
+                throw new IllegalArgumentException("Unknown or invalid filter type: " + filterType);
+        }
+
+        return testSupportGeneric(FILTER, filterType);
+    }
+
+    /**
+     * Generic test function to see if an EFX object supports a given kind of type. Works for
+     * effects and filters.
+     *
+     * @param objectType Type of object to test. Must be either EFXUtil.EFFECT or EFXUtil.FILTER.
+     * @param typeValue OpenAL type the object should be tested for support, e.g. AL_FILTER_LOWPASS
+     * or AL_EFFECT_REVERB.
+     * @return True if object supports typeValue, false else.
+     */
+    private static boolean testSupportGeneric(final int objectType, final int typeValue) {
+        // Check for supported objectType.
+        switch (objectType) {
+            case EFFECT:
+            case FILTER:
+                break;
+            default:
+                throw new IllegalArgumentException("Invalid objectType: " + objectType);
+        }
+
+        boolean supported = false;
+        if (isEfxSupported()) {
+
+            // Try to create object in order to check AL's response.
+            AL10.alGetError();
+            int genError;
+            int testObject = 0;
+            try {
+                switch (objectType) { // Create object based on type
+                    case EFFECT:
+                        testObject = EFX10.alGenEffects();
+                        break;
+                    case FILTER:
+                        testObject = EFX10.alGenFilters();
+                        break;
+                    default:
+                        throw new IllegalArgumentException("Invalid objectType: " + objectType);
+                }
+                genError = AL10.alGetError();
+            } catch (final OpenALException debugBuildException) {
+                // Hack because OpenALException hides the original error code (short of parsing the
+                // error message String which would break if it gets changed).
+                if (debugBuildException.getMessage().contains("AL_OUT_OF_MEMORY")) {
+                    genError = AL10.AL_OUT_OF_MEMORY;
+                } else {
+                    genError = AL10.AL_INVALID_OPERATION;
+                }
+            }
+
+            if (genError == AL10.AL_NO_ERROR) {
+                // Successfully created, now try to set type.
+                AL10.alGetError();
+                int setError;
+                try {
+                    switch (objectType) { // Set based on object type
+                        case EFFECT:
+                            EFX10.alEffecti(testObject, EFX10.AL_EFFECT_TYPE, typeValue);
+                            break;
+                        case FILTER:
+                            EFX10.alFilteri(testObject, EFX10.AL_FILTER_TYPE, typeValue);
+                            break;
+                        default:
+                            throw new IllegalArgumentException("Invalid objectType: " + objectType);
+                    }
+                    setError = AL10.alGetError();
+                } catch (final OpenALException debugBuildException) {
+                    // Hack because OpenALException hides the original error code (short of parsing
+                    // the error message String which would break when it gets changed).
+                    setError = AL10.AL_INVALID_VALUE;
+                }
+
+                if (setError == AL10.AL_NO_ERROR) {
+                    supported = true;
+                }
+
+                // Cleanup
+                try {
+                    switch (objectType) { // Set based on object type
+                        case EFFECT:
+                            EFX10.alDeleteEffects(testObject);
+                            break;
+                        case FILTER:
+                            EFX10.alDeleteFilters(testObject);
+                            break;
+                        default:
+                            throw new IllegalArgumentException("Invalid objectType: " + objectType);
+                    }
+                } catch (final OpenALException debugBuildException) {
+                    // Don't care about cleanup errors.
+                }
+
+            } else if (genError == AL10.AL_OUT_OF_MEMORY) {
+                throw new OpenALException(genError);
+            }
+        }
+
+        return supported;
+    }
+}
diff --git a/src/java/org/lwjgl/opengl/AMDDebugOutputCallback.java b/src/java/org/lwjgl/opengl/AMDDebugOutputCallback.java
new file mode 100644
index 0000000..0038161
--- /dev/null
+++ b/src/java/org/lwjgl/opengl/AMDDebugOutputCallback.java
@@ -0,0 +1,162 @@
+/*
+ * Copyright (c) 2002-2008 LWJGL Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * * Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ *
+ * * Neither the name of 'LWJGL' nor the names of
+ *   its contributors may be used to endorse or promote products derived
+ *   from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package org.lwjgl.opengl;
+
+/**
+ * Instances of this class are needed to use the callback functionality of the AMD_debug_output extension.
+ * A debug context must be current before creating instances of this class. Users of this class may provide
+ * implementations of the {@code Handler} interface to receive notifications. The same {@code Handler}
+ * instance may be used by different contexts but it is not recommended. Handler notifications are synchronized.
+ *
+ * @author Spasi
+ */
+public final class AMDDebugOutputCallback implements PointerWrapper {
+
+	/** Severity levels. */
+	private static final int GL_DEBUG_SEVERITY_HIGH_AMD = 0x9146,
+		GL_DEBUG_SEVERITY_MEDIUM_AMD = 0x9147,
+		GL_DEBUG_SEVERITY_LOW_AMD = 0x9148;
+
+	/** Categories */
+	private static final int GL_DEBUG_CATEGORY_API_ERROR_AMD = 0x9149,
+		GL_DEBUG_CATEGORY_WINDOW_SYSTEM_AMD = 0x914A,
+		GL_DEBUG_CATEGORY_DEPRECATION_AMD = 0x914B,
+		GL_DEBUG_CATEGORY_UNDEFINED_BEHAVIOR_AMD = 0x914C,
+		GL_DEBUG_CATEGORY_PERFORMANCE_AMD = 0x914D,
+		GL_DEBUG_CATEGORY_SHADER_COMPILER_AMD = 0x914E,
+		GL_DEBUG_CATEGORY_APPLICATION_AMD = 0x914F,
+		GL_DEBUG_CATEGORY_OTHER_AMD = 0x9150;
+
+	private final long pointer;
+
+	/**
+	 * Creates a AMDDebugOutputCallback with a default callback handler.
+	 * The default handler will simply print the message on System.err.
+	 */
+	public AMDDebugOutputCallback() {
+		this(new Handler() {
+			public void handleMessage(final int id, final int category, final int severity, final String message) {
+				System.err.println("[LWJGL] AMD_debug_output message");
+				System.err.println("\tID: " + id);
+
+				String description;
+				switch ( category ) {
+					case GL_DEBUG_CATEGORY_API_ERROR_AMD:
+						description = "API ERROR";
+						break;
+					case GL_DEBUG_CATEGORY_WINDOW_SYSTEM_AMD:
+						description = "WINDOW SYSTEM";
+						break;
+					case GL_DEBUG_CATEGORY_DEPRECATION_AMD:
+						description = "DEPRECATION";
+						break;
+					case GL_DEBUG_CATEGORY_UNDEFINED_BEHAVIOR_AMD:
+						description = "UNDEFINED BEHAVIOR";
+						break;
+					case GL_DEBUG_CATEGORY_PERFORMANCE_AMD:
+						description = "PERFORMANCE";
+						break;
+					case GL_DEBUG_CATEGORY_SHADER_COMPILER_AMD:
+						description = "SHADER COMPILER";
+						break;
+					case GL_DEBUG_CATEGORY_APPLICATION_AMD:
+						description = "APPLICATION";
+						break;
+					case GL_DEBUG_CATEGORY_OTHER_AMD:
+						description = "OTHER";
+						break;
+					default:
+						description = "Unknown (" + Integer.toHexString(category) + ")";
+				}
+				System.err.println("\tCategory: " + description);
+
+				switch ( severity ) {
+					case GL_DEBUG_SEVERITY_HIGH_AMD:
+						description = "HIGH";
+						break;
+					case GL_DEBUG_SEVERITY_MEDIUM_AMD:
+						description = "MEDIUM";
+						break;
+					case GL_DEBUG_SEVERITY_LOW_AMD:
+						description = "LOW";
+						break;
+					default:
+						description = "Unknown (" + Integer.toHexString(category) + ")";
+				}
+				System.err.println("\tSeverity: " + description);
+
+				System.err.println("\tMessage: " + message);
+			}
+		});
+	}
+
+	/**
+	 * Creates a AMDDebugOutputCallback with the specified callback handlers.
+	 * The handler's {@code handleMessage} method will be called whenever
+	 * debug output is generated by the GL.
+	 *
+	 * @param handler the callback handler
+	 */
+	public AMDDebugOutputCallback(final Handler handler) {
+		try {
+			// We have to call registerHandler reflectively because we need this class to compile before we run the Generator.
+			// The registerHandler method depends on org.lwjgl.opengl.Context, if we touched that we would need to compile
+			// the whole library (which is not possible).
+			Class.forName("org.lwjgl.opengl.AMDDebugOutputUtil").getMethod("registerHandler", new Class[] { Handler.class }).invoke(null, new Object[] { handler });
+		} catch (Exception e) {
+			throw new RuntimeException(e.getCause() != null ? e.getCause() : e);
+		}
+		this.pointer = getFunctionPointer();
+	}
+
+	public long getPointer() {
+		return pointer;
+	}
+
+	private static native long getFunctionPointer();
+
+	/** Implementations of this interface can be used to receive AMD_debug_output notifications. */
+	public interface Handler {
+
+		/**
+		 * This method will be called when an AMD_debug_output message is generated.
+		 *
+		 * @param id       the message ID
+		 * @param category the message category
+		 * @param severity the message severity
+		 * @param message  the string representation of the message.
+		 */
+		void handleMessage(int id, int category, int severity, String message);
+
+	}
+
+}
diff --git a/src/java/org/lwjgl/opengl/AMDDebugOutputUtil.java b/src/java/org/lwjgl/opengl/AMDDebugOutputUtil.java
new file mode 100644
index 0000000..1227833
--- /dev/null
+++ b/src/java/org/lwjgl/opengl/AMDDebugOutputUtil.java
@@ -0,0 +1,59 @@
+package org.lwjgl.opengl;
+
+import org.lwjgl.opengl.AMDDebugOutputCallback.Handler;
+
+import java.nio.ByteBuffer;
+import java.util.Map;
+import java.util.WeakHashMap;
+
+/**
+ * This class handles AMDDebugOutputCallback.Handler registration and notification.
+ * We could have put this in AMDDebugOutputCallback, but we need to compile it for
+ * the generator. Registration is done reflectively in the AMDDebugOutputCallback
+ * constructor.
+ *
+ * @author Spasi
+ */
+final class AMDDebugOutputUtil {
+
+	private static final Map handlers = new WeakHashMap();
+
+	private AMDDebugOutputUtil() {}
+
+	public static void registerHandler(final Handler handler) {
+		final Context ctx = Context.getCurrentContext();
+		if ( ctx == null )
+			throw new IllegalStateException("No context is current.");
+
+		if ( !ctx.getContextAttribs().isDebug() )
+			throw new IllegalStateException("The current context is not a debug context.");
+
+		if ( !GLContext.getCapabilities().GL_AMD_debug_output  )
+			throw new IllegalStateException("AMD_debug_output is not supported.");
+
+		handlers.put(ctx, handler);
+	}
+
+	/**
+	 * This method is called by native code. If finds the callback handler associated
+	 * with the current Thread and calls its {@code handleMessage} method.
+	 *
+	 * @param id        the message ID
+	 * @param category  the message category
+	 * @param severity  the message severity
+	 * @param message   the string representation of the message.
+	 * @param userParam the user-specified data specified in glDebugMessageCallbackAMD. For the current implementation this is always null and we ignore it.
+	 */
+	private static void messageCallback(final int id, final int category, final int severity, final String message, final ByteBuffer userParam) {
+		synchronized ( GlobalLock.lock ) {
+			final Context ctx = Context.getCurrentContext();
+			if ( ctx == null )
+				return;
+
+			final Handler handler = (Handler)handlers.get(ctx);
+			if ( handler != null )
+				handler.handleMessage(id, category, severity, message);
+		}
+	}
+
+}
diff --git a/src/java/org/lwjgl/opengl/APIUtils.java b/src/java/org/lwjgl/opengl/APIUtils.java
index 730b801..51ded17 100644
--- a/src/java/org/lwjgl/opengl/APIUtils.java
+++ b/src/java/org/lwjgl/opengl/APIUtils.java
@@ -158,6 +158,7 @@ final class APIUtils {
 		final InfiniteCharSequence infiniteSeq = getInfiniteSeq();
 		infiniteSeq.setString(string);
 		encoder.encode(infiniteSeq.buffer, buffer, true);
+		infiniteSeq.clear();
 	}
 
 	/**
diff --git a/src/java/org/lwjgl/opengl/AWTGLCanvas.java b/src/java/org/lwjgl/opengl/AWTGLCanvas.java
index 466b41b..d19f76d 100644
--- a/src/java/org/lwjgl/opengl/AWTGLCanvas.java
+++ b/src/java/org/lwjgl/opengl/AWTGLCanvas.java
@@ -47,10 +47,10 @@ import java.awt.event.HierarchyListener;
  * <p/>
  *
  * @author $Author: spasi $
- *         $Id: AWTGLCanvas.java 3116 2008-08-19 16:46:03Z spasi $
- * @version $Revision: 3116 $
+ *         $Id: AWTGLCanvas.java 3334 2010-04-22 23:21:48Z spasi $
+ * @version $Revision: 3334 $
  */
-public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener, HierarchyListener {
+public class AWTGLCanvas extends Canvas implements DrawableLWJGL, ComponentListener, HierarchyListener {
 
 	private static final long serialVersionUID = 1L;
 
@@ -109,6 +109,15 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
 		return context;
 	}
 
+	/** This method should only be called internally. */
+	public Context createSharedContext() throws LWJGLException {
+		synchronized ( SYNC_LOCK ) {
+			if ( context == null ) throw new IllegalStateException("Canvas not yet displayable");
+
+			return new Context(peer_info, context.getContextAttribs(), context);
+		}
+	}
+
 	/** Constructor using the default PixelFormat. */
 	public AWTGLCanvas() throws LWJGLException {
 		this(new PixelFormat());
@@ -175,7 +184,7 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
 		 */
 	public void removeNotify() {
 		synchronized ( SYNC_LOCK ) {
-			destroyContext();
+			destroy();
 			super.removeNotify();
 		}
 	}
@@ -203,12 +212,11 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
 		}
 	}
 
-	public void releaseContext() throws LWJGLException {
+	public boolean isCurrent() throws LWJGLException {
 		synchronized ( SYNC_LOCK ) {
-			if ( context == null )
-				throw new IllegalStateException("Canvas not yet displayable");
-			if ( context.isCurrent() )
-				Context.releaseCurrentContext();
+			if ( context == null ) throw new IllegalStateException("Canvas not yet displayable");
+
+			return context.isCurrent();
 		}
 	}
 
@@ -224,8 +232,17 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
 		}
 	}
 
+	public void releaseContext() throws LWJGLException {
+		synchronized ( SYNC_LOCK ) {
+			if ( context == null )
+				throw new IllegalStateException("Canvas not yet displayable");
+			if ( context.isCurrent() )
+				Context.releaseCurrentContext();
+		}
+	}
+
 	/** Destroy the OpenGL context. This happens when the component becomes undisplayable */
-	private void destroyContext() {
+	public final void destroy() {
 		synchronized ( SYNC_LOCK ) {
 			try {
 				if ( context != null ) {
@@ -269,7 +286,7 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
 				peer_info.lockAndGetHandle();
 				try {
 					if ( context == null ) {
-						this.context = new Context(peer_info, attribs, drawable != null ? drawable.getContext() : null);
+						this.context = new Context(peer_info, attribs, drawable != null ? ((DrawableLWJGL)drawable).getContext() : null);
 						first_run = true;
 					}
 
diff --git a/src/java/org/lwjgl/opengl/AbstractDrawable.java b/src/java/org/lwjgl/opengl/AbstractDrawable.java
new file mode 100644
index 0000000..18778a8
--- /dev/null
+++ b/src/java/org/lwjgl/opengl/AbstractDrawable.java
@@ -0,0 +1,81 @@
+package org.lwjgl.opengl;
+
+import org.lwjgl.LWJGLException;
+import org.lwjgl.LWJGLUtil;
+
+/**
+ * @author Spasi
+ */
+abstract class AbstractDrawable implements DrawableLWJGL {
+
+	/** Handle to the native GL rendering context */
+	protected PeerInfo peer_info;
+
+	/** The OpenGL Context. */
+	protected Context context;
+
+	protected AbstractDrawable() {
+	}
+
+	public Context getContext() {
+		synchronized ( GlobalLock.lock ) {
+			return context;
+		}
+	}
+
+	public Context createSharedContext() throws LWJGLException {
+		synchronized ( GlobalLock.lock ) {
+			checkDestroyed();
+			return new Context(peer_info, context.getContextAttribs(), context);
+		}
+	}
+
+	public boolean isCurrent() throws LWJGLException {
+		synchronized ( GlobalLock.lock ) {
+			checkDestroyed();
+			return context.isCurrent();
+		}
+	}
+
+	public void makeCurrent() throws LWJGLException {
+		synchronized ( GlobalLock.lock ) {
+			checkDestroyed();
+			context.makeCurrent();
+		}
+	}
+
+	public void releaseContext() throws LWJGLException {
+		synchronized ( GlobalLock.lock ) {
+			checkDestroyed();
+			if ( context.isCurrent() )
+				Context.releaseCurrentContext();
+		}
+	}
+
+	public void destroy() {
+		synchronized ( GlobalLock.lock ) {
+			if ( context == null )
+				return;
+
+			try {
+				releaseContext();
+
+				context.forceDestroy();
+				context = null;
+
+				if ( peer_info != null ) {
+					peer_info.destroy();
+					peer_info = null;
+				}
+			} catch (LWJGLException e) {
+				LWJGLUtil.log("Exception occurred while destroying Drawable: " + e);
+			}
+		}
+	}
+
+	protected final void checkDestroyed() {
+		if ( context == null )
+			throw new IllegalStateException("The Drawable has no context available.");
+	}
+
+}
diff --git a/src/java/org/lwjgl/opengl/BaseReferences.java b/src/java/org/lwjgl/opengl/BaseReferences.java
index 343b2c9..7058cce 100644
--- a/src/java/org/lwjgl/opengl/BaseReferences.java
+++ b/src/java/org/lwjgl/opengl/BaseReferences.java
@@ -32,7 +32,6 @@
 package org.lwjgl.opengl;
 
 import java.nio.Buffer;
-import java.nio.IntBuffer;
 import java.util.Arrays;
 
 class BaseReferences {
@@ -49,24 +48,19 @@ class BaseReferences {
 	int indirectBuffer;
 
 	BaseReferences(ContextCapabilities caps) {
-        IntBuffer temp = caps.scratch_int_buffer;
-
 		int max_vertex_attribs;
-		if (caps.OpenGL20 || caps.GL_ARB_vertex_shader) {
-	        GL11.glGetInteger(ARBVertexShader.GL_MAX_VERTEX_ATTRIBS_ARB, temp);
-			max_vertex_attribs = temp.get(0);
-		} else
+		if (caps.OpenGL20 || caps.GL_ARB_vertex_shader)
+			max_vertex_attribs = GL11.glGetInteger(ARBVertexShader.GL_MAX_VERTEX_ATTRIBS_ARB);
+		else
 			max_vertex_attribs = 0;
         glVertexAttribPointer_buffer = new Buffer[max_vertex_attribs];
 
 		int max_texture_units;
-		if (caps.OpenGL20) {
-			GL11.glGetInteger(GL20.GL_MAX_TEXTURE_IMAGE_UNITS, temp);
-			max_texture_units = temp.get(0);
-		} else if (caps.OpenGL13 || caps.GL_ARB_multitexture) {
-        	GL11.glGetInteger(GL13.GL_MAX_TEXTURE_UNITS, temp);
-			max_texture_units = temp.get(0);
-		} else
+		if (caps.OpenGL20)
+			max_texture_units = GL11.glGetInteger(GL20.GL_MAX_TEXTURE_IMAGE_UNITS);
+		else if (caps.OpenGL13 || caps.GL_ARB_multitexture)
+			max_texture_units = GL11.glGetInteger(GL13.GL_MAX_TEXTURE_UNITS);
+		else
 			max_texture_units = 1;
         glTexCoordPointer_buffer = new Buffer[max_texture_units];
     }
diff --git a/src/java/org/lwjgl/opengl/Context.java b/src/java/org/lwjgl/opengl/Context.java
index c07c966..1933558 100644
--- a/src/java/org/lwjgl/opengl/Context.java
+++ b/src/java/org/lwjgl/opengl/Context.java
@@ -46,8 +46,8 @@ import java.nio.IntBuffer;
  * This class is thread-safe.
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 3117 $
- *          $Id: Context.java 3117 2008-08-19 17:47:24Z spasi $
+ * @version $Revision: 3332 $
+ *          $Id: Context.java 3332 2010-04-20 18:21:05Z spasi $
  */
 final class Context {
 
@@ -61,7 +61,7 @@ final class Context {
 	private final ByteBuffer handle;
 	private final PeerInfo peer_info;
 
-	private final IntBuffer attribList;
+	private final ContextAttribs contextAttribs;
 	private final boolean forwardCompatible;
 
 	/** Whether the context has been destroyed */
@@ -94,6 +94,10 @@ final class Context {
 		return peer_info;
 	}
 
+	ContextAttribs getContextAttribs() {
+		return contextAttribs;
+	}
+
 	static Context getCurrentContext() {
 		return (Context)current_context_local.get();
 	}
@@ -109,6 +113,9 @@ final class Context {
 			GLContext.loadOpenGLLibrary();
 			try {
 				this.peer_info = peer_info;
+				this.contextAttribs = attribs;
+
+				IntBuffer attribList;
 				if ( attribs != null ) {
 					attribList = attribs.getAttribList();
 					forwardCompatible = attribs.isForwardCompatible();
diff --git a/src/java/org/lwjgl/opengl/ContextAttribs.java b/src/java/org/lwjgl/opengl/ContextAttribs.java
index 59d951f..a056b64 100644
--- a/src/java/org/lwjgl/opengl/ContextAttribs.java
+++ b/src/java/org/lwjgl/opengl/ContextAttribs.java
@@ -37,16 +37,16 @@ import org.lwjgl.LWJGLUtil;
 import java.nio.IntBuffer;
 
 /**
- * This class represents the context attributes passed to CreateContextAttribs of the XGL_create_context extension.
+ * This class represents the context attributes passed to CreateContextAttribs of the ARB_create_context and
+ * ARB_create_context_profile extensions.
  * These attributes can be used to indicate at context creation which OpenGL interface will be used. This includes the
  * OpenGL version, the layer plane on which rendering takes place and also optional debug and forward combatibility modes.
- * (read the XGL_create_context spec for details)
+ * (read the ARB_create_context spec for details)
  * <p/>
  * Use of this class is optional. If an OpenGL context is created without passing an instance of this class
- * (or XGL_create_context is not supported), the old context creation code will be used. Use of ContextAttribs is required
- * to create an OpenGL 3.0 or newer context. Support for debug and forward compatible mobes is not guaranteed by the OpenGL
- * implementation. Developers may encounter debug contexts being the same as non-debug contexts or forward compatible
- * contexts having support for deprecated functionality.
+ * (or ARB_create_context is not supported), the old context creation code will be used. Support for debug and forward
+ * compatible mobes is not guaranteed by the OpenGL implementation. Developers may encounter debug contexts being the same
+ * as non-debug contexts or forward compatible contexts having support for deprecated functionality.
  * <p/>
  * If the forwardCompatible
  * attribute is used, LWJGL will not load the deprecated functionality (as defined in the OpenGL 3.0 specification). This
@@ -72,10 +72,10 @@ public final class ContextAttribs {
 	}
 
 	public ContextAttribs(final int majorVersion, final int minorVersion) {
-		if ( majorVersion < 0 ||
-		     3 < majorVersion ||
+		if ( majorVersion < 0 || 4 < majorVersion ||
 		     minorVersion < 0 ||
-		     (majorVersion == 3 && 2 < minorVersion) ||
+		     (majorVersion == 4 && 0 < minorVersion) ||
+		     (majorVersion == 3 && 3 < minorVersion) ||
 		     (majorVersion == 2 && 1 < minorVersion) ||
 		     (majorVersion == 1 && 5 < minorVersion) )
 			throw new IllegalArgumentException("Invalid OpenGL version specified: " + majorVersion + '.' + minorVersion);
@@ -88,7 +88,7 @@ public final class ContextAttribs {
 		this.debug = false;
 		this.forwardCompatible = false;
 
-		this.profileCore = 3 < majorVersion || (majorVersion == 3 && 2 <= minorVersion) ? true : false;
+		this.profileCore = false;
 		this.profileCompatibility = false;
 	}
 
diff --git a/src/java/org/lwjgl/opengl/Display.java b/src/java/org/lwjgl/opengl/Display.java
index b344ef1..e90db80 100644
--- a/src/java/org/lwjgl/opengl/Display.java
+++ b/src/java/org/lwjgl/opengl/Display.java
@@ -106,14 +106,10 @@ public final class Display {
 	/** Swap interval */
 	private static int swap_interval;
 
-	/** A unique context object, so we can track different contexts between creates() and destroys() */
-	private static PeerInfo peer_info;
-	private static Context context;
-
 	/** The Drawable instance that tracks the current Display context */
-	private final static Drawable drawable;
+	private static final AbstractDrawable drawable;
 
-	private static boolean window_created = false;
+	private static boolean window_created;
 
 	private static boolean parent_resized;
 
@@ -137,10 +133,19 @@ public final class Display {
 		} catch (LWJGLException e) {
 			throw new RuntimeException(e);
 		}
-		drawable = new Drawable() {
-			public Context getContext() {
+		drawable = new AbstractDrawable() {
+			public void destroy() {
 				synchronized ( GlobalLock.lock ) {
-					return isCreated() ? context : null;
+					if ( !isCreated() )
+						return;
+
+					releaseDrawable();
+					super.destroy();
+					destroyWindow();
+					x = y = -1;
+					cached_icons = null;
+					reset();
+					removeShutdownHook();
 				}
 			}
 		};
@@ -238,24 +243,23 @@ public final class Display {
 	 * @throws LWJGLException if the display mode could not be set
 	 */
 	public static void setDisplayMode(DisplayMode mode) throws LWJGLException {
-		synchronized (GlobalLock.lock) {
-			if (mode == null)
+		synchronized ( GlobalLock.lock ) {
+			if ( mode == null )
 				throw new NullPointerException("mode must be non-null");
 			boolean was_fullscreen = isFullscreen();
 			current_mode = mode;
-			if (isCreated()) {
+			if ( isCreated() ) {
 				destroyWindow();
 				// If mode is not fullscreen capable, make sure we are in windowed mode
 				try {
-					if (was_fullscreen && !isFullscreen())
+					if ( was_fullscreen && !isFullscreen() )
 						display_impl.resetDisplayMode();
-					else if (isFullscreen())
+					else if ( isFullscreen() )
 						switchDisplayMode();
 					createWindow();
 					makeCurrentAndSetSwapInterval();
 				} catch (LWJGLException e) {
-					destroyContext();
-					destroyPeerInfo();
+					drawable.destroy();
 					display_impl.resetDisplayMode();
 					throw e;
 				}
@@ -268,9 +272,9 @@ public final class Display {
 	}
 
 	private static int getWindowX() {
-		if (!isFullscreen() && parent == null) {
+		if ( !isFullscreen() && parent == null ) {
 			// if no display location set, center window
-			if (x == -1) {
+			if ( x == -1 ) {
 				return Math.max(0, (initial_mode.getWidth() - current_mode.getWidth()) / 2);
 			} else {
 				return x;
@@ -281,7 +285,7 @@ public final class Display {
 	}
 
 	private static int getWindowY() {
-		if (!isFullscreen() && parent == null) {
+		if ( !isFullscreen() && parent == null ) {
 			// if no display location set, center window
 			if ( y == -1 ) {
 				return Math.max(0, (initial_mode.getHeight() - current_mode.getHeight()) / 2);
@@ -324,6 +328,7 @@ public final class Display {
 
 	private static void releaseDrawable() {
 		try {
+			Context context = drawable.context;
 			if ( context != null && context.isCurrent() ) {
 				Context.releaseCurrentContext();
 				context.releaseDrawable();
@@ -419,12 +424,13 @@ public final class Display {
 			savedTimeLate = timeLate;
 		}
 
-		while ( gapTo > timeNow + savedTimeLate ) {
-			try {
+		try {
+			while ( gapTo > timeNow + savedTimeLate ) {
 				Thread.sleep(1);
-			} catch (InterruptedException e) {
+				timeNow = Sys.getTime();
 			}
-			timeNow = Sys.getTime();
+		} catch (InterruptedException e) {
+			Thread.currentThread().interrupt();
 		}
 
 		synchronized ( GlobalLock.lock ) {
@@ -463,13 +469,13 @@ public final class Display {
 	 */
 	public static void setParent(Canvas parent) throws LWJGLException {
 		synchronized ( GlobalLock.lock ) {
-			if (Display.parent != parent) {
+			if ( Display.parent != parent ) {
 				Display.parent = parent;
 				if ( !isCreated() )
 					return;
 				destroyWindow();
 				try {
-					if (isFullscreen()) {
+					if ( isFullscreen() ) {
 						switchDisplayMode();
 					} else {
 						display_impl.resetDisplayMode();
@@ -477,8 +483,7 @@ public final class Display {
 					createWindow();
 					makeCurrentAndSetSwapInterval();
 				} catch (LWJGLException e) {
-					destroyContext();
-					destroyPeerInfo();
+					drawable.destroy();
 					display_impl.resetDisplayMode();
 					throw e;
 				}
@@ -519,18 +524,18 @@ public final class Display {
 
 	private static void setDisplayModeAndFullscreenInternal(boolean fullscreen, DisplayMode mode) throws LWJGLException {
 		synchronized ( GlobalLock.lock ) {
-			if (mode == null)
+			if ( mode == null )
 				throw new NullPointerException("mode must be non-null");
 			DisplayMode old_mode = current_mode;
 			current_mode = mode;
 			boolean was_fullscreen = isFullscreen();
 			Display.fullscreen = fullscreen;
-			if (was_fullscreen != isFullscreen() || !mode.equals(old_mode)) {
-				if (!isCreated())
+			if ( was_fullscreen != isFullscreen() || !mode.equals(old_mode) ) {
+				if ( !isCreated() )
 					return;
 				destroyWindow();
 				try {
-					if (isFullscreen()) {
+					if ( isFullscreen() ) {
 						switchDisplayMode();
 					} else {
 						display_impl.resetDisplayMode();
@@ -538,8 +543,7 @@ public final class Display {
 					createWindow();
 					makeCurrentAndSetSwapInterval();
 				} catch (LWJGLException e) {
-					destroyContext();
-					destroyPeerInfo();
+					drawable.destroy();
 					display_impl.resetDisplayMode();
 					throw e;
 				}
@@ -549,7 +553,7 @@ public final class Display {
 
 	/** @return whether the Display is in fullscreen mode */
 	public static boolean isFullscreen() {
-		synchronized (GlobalLock.lock) {
+		synchronized ( GlobalLock.lock ) {
 			return fullscreen && current_mode.isFullscreenCapable();
 		}
 	}
@@ -651,7 +655,6 @@ public final class Display {
 	 * Update the window. If the window is visible clears
 	 * the dirty flag and calls swapBuffers() and finally
 	 * polls the input devices.
-	 *
 	 */
 	public static void update() {
 		update(true);
@@ -710,12 +713,12 @@ public final class Display {
 	 * @throws LWJGLException If the context could not be released
 	 */
 	public static void releaseContext() throws LWJGLException {
-		synchronized ( GlobalLock.lock ) {
-			if ( !isCreated() )
-				throw new IllegalStateException("Display is not created");
-			if ( context.isCurrent() )
-				Context.releaseCurrentContext();
-		}
+		drawable.releaseContext();
+	}
+
+	/** Returns true if the Display's context is current in the current thread. */
+	public static boolean isCurrent() throws LWJGLException {
+		return drawable.isCurrent();
 	}
 
 	/**
@@ -724,11 +727,7 @@ public final class Display {
 	 * @throws LWJGLException If the context could not be made current
 	 */
 	public static void makeCurrent() throws LWJGLException {
-		synchronized ( GlobalLock.lock ) {
-			if ( !isCreated() )
-				throw new IllegalStateException("Display is not created");
-			context.makeCurrent();
-		}
+		drawable.makeCurrent();
 	}
 
 	private static void removeShutdownHook() {
@@ -848,19 +847,19 @@ public final class Display {
 				throw new NullPointerException("pixel_format cannot be null");
 			removeShutdownHook();
 			registerShutdownHook();
-			if (isFullscreen())
+			if ( isFullscreen() )
 				switchDisplayMode();
 			try {
-				peer_info = display_impl.createPeerInfo(pixel_format);
+				drawable.peer_info = display_impl.createPeerInfo(pixel_format);
 				try {
 					createWindow();
 					try {
-						context = new Context(peer_info, attribs, shared_drawable != null ? shared_drawable.getContext() : null);
+						drawable.context = new Context(drawable.peer_info, attribs, shared_drawable != null ? ((AbstractDrawable)shared_drawable).getContext() : null);
 						try {
 							makeCurrentAndSetSwapInterval();
 							initContext();
 						} catch (LWJGLException e) {
-							destroyContext();
+							drawable.destroy();
 							throw e;
 						}
 					} catch (LWJGLException e) {
@@ -868,7 +867,7 @@ public final class Display {
 						throw e;
 					}
 				} catch (LWJGLException e) {
-					destroyPeerInfo();
+					drawable.destroy();
 					throw e;
 				}
 			} catch (LWJGLException e) {
@@ -879,13 +878,13 @@ public final class Display {
 	}
 
 	/**
-	*  Set the initial color of the Display. This method is called before the Display is created and will set the
-	*  background color to the one specified in this method.
-	*
-	*  @param red - color value between 0 - 1
-	*  @param green - color value between 0 - 1
-	*  @param blue - color value between 0 - 1
-	*/
+	 * Set the initial color of the Display. This method is called before the Display is created and will set the
+	 * background color to the one specified in this method.
+	 *
+	 * @param red   - color value between 0 - 1
+	 * @param green - color value between 0 - 1
+	 * @param blue  - color value between 0 - 1
+	 */
 	public static void setInitialBackground(float red, float green, float blue) {
 		r = red;
 		g = green;
@@ -957,41 +956,14 @@ public final class Display {
 	 * regardless of whether the Display was the current rendering context.
 	 */
 	public static void destroy() {
-		synchronized ( GlobalLock.lock ) {
-			if ( !isCreated() ) {
-				return;
-			}
-
-			releaseDrawable();
-			destroyContext();
-			destroyWindow();
-			destroyPeerInfo();
-			x = y = -1;
-			cached_icons = null;
-			reset();
-			removeShutdownHook();
-		}
-	}
-
-	private static void destroyPeerInfo() {
-		peer_info.destroy();
-		peer_info = null;
-	}
-
-	private static void destroyContext() {
-		try {
-			context.forceDestroy();
-		} catch (LWJGLException e) {
-			throw new RuntimeException(e);
-		} finally {
-			context = null;
-		}
+		drawable.destroy();
 	}
 
 	/*
 	 * Reset display mode if fullscreen. This method is also called from the shutdown hook added
 	 * in the static constructor
 	 */
+
 	private static void reset() {
 		display_impl.resetDisplayMode();
 		current_mode = initial_mode;
@@ -1050,7 +1022,7 @@ public final class Display {
 			y = new_y;
 
 			// offset if already created
-			if (isCreated() && !isFullscreen()) {
+			if ( isCreated() && !isFullscreen() ) {
 				reshape();
 			}
 		}
diff --git a/src/java/org/lwjgl/opengl/Drawable.java b/src/java/org/lwjgl/opengl/Drawable.java
index 8e542f1..84327aa 100644
--- a/src/java/org/lwjgl/opengl/Drawable.java
+++ b/src/java/org/lwjgl/opengl/Drawable.java
@@ -31,6 +31,8 @@
  */
 package org.lwjgl.opengl;
 
+import org.lwjgl.LWJGLException;
+
 /**
  * The Drawable interface describes an OpenGL drawable with an associated
  * Context.
@@ -39,5 +41,25 @@ package org.lwjgl.opengl;
  */
 
 public interface Drawable {
-	Context getContext();
+
+	/** Returns true if the Drawable's context is current in the current thread. */
+	boolean isCurrent() throws LWJGLException;
+
+	/**
+	 * Makes the Drawable's context current in the current thread.
+	 *
+	 * @throws LWJGLException
+	 */
+	void makeCurrent() throws LWJGLException;
+
+	/**
+	 * If the Drawable's context is current in the current thread, no context will be current after a call to this method.
+	 *
+	 * @throws LWJGLException
+	 */
+	void releaseContext() throws LWJGLException;
+
+	/** Destroys the Drawable. */
+	void destroy();
+
 }
diff --git a/src/java/org/lwjgl/opengl/DrawableLWJGL.java b/src/java/org/lwjgl/opengl/DrawableLWJGL.java
new file mode 100644
index 0000000..b79c806
--- /dev/null
+++ b/src/java/org/lwjgl/opengl/DrawableLWJGL.java
@@ -0,0 +1,24 @@
+package org.lwjgl.opengl;
+
+import org.lwjgl.LWJGLException;
+
+/**
+ * @author Spasi
+ */
+interface DrawableLWJGL extends Drawable {
+
+	/**
+	 * [INTERNAL USE ONLY] Returns the Drawable's Context.
+	 *
+	 * @return the Drawable's Context
+	 */
+	Context getContext();
+
+	/**
+	 * [INTERNAL USE ONLY] Creates a new Context that is shared with the Drawable's Context.
+	 *
+	 * @return a Context shared with the Drawable's Context.
+	 */
+	Context createSharedContext() throws LWJGLException;
+
+}
diff --git a/src/java/org/lwjgl/opengl/GLChecks.java b/src/java/org/lwjgl/opengl/GLChecks.java
index b2d2339..ca0116e 100644
--- a/src/java/org/lwjgl/opengl/GLChecks.java
+++ b/src/java/org/lwjgl/opengl/GLChecks.java
@@ -35,6 +35,7 @@ import java.nio.Buffer;
 import java.nio.IntBuffer;
 
 import org.lwjgl.BufferUtils;
+import org.lwjgl.LWJGLUtil;
 
 /**
  * A class to check buffer boundaries in GL methods. Many GL
@@ -46,8 +47,8 @@ import org.lwjgl.BufferUtils;
  * Thrown by the debug build library of the LWJGL if any OpenGL operation causes an error.
  *
  * @author cix_foo <cix_foo at users.sourceforge.net>
- * @version $Revision: 3279 $
- * $Id: GLChecks.java 3279 2010-03-11 21:06:49Z spasi $
+ * @version $Revision: 3334 $
+ * $Id: GLChecks.java 3334 2010-04-22 23:21:48Z spasi $
  */
 class GLChecks {
 
@@ -60,93 +61,78 @@ class GLChecks {
 	}
 
 	static int getBufferObjectSize(ContextCapabilities caps, int buffer_enum) {
-		IntBuffer scratch_buffer = caps.scratch_int_buffer;
-		GL15.glGetBufferParameter(buffer_enum, GL15.GL_BUFFER_SIZE, scratch_buffer);
-		return scratch_buffer.get(0);
+		return GL15.glGetBufferParameter(buffer_enum, GL15.GL_BUFFER_SIZE);
 	}
 
 	static int getBufferObjectSizeARB(ContextCapabilities caps, int buffer_enum) {
-		IntBuffer scratch_buffer = caps.scratch_int_buffer;
-		ARBBufferObject.glGetBufferParameterARB(buffer_enum, ARBBufferObject.GL_BUFFER_SIZE_ARB, scratch_buffer);
-		return scratch_buffer.get(0);
+		return ARBBufferObject.glGetBufferParameterARB(buffer_enum, ARBBufferObject.GL_BUFFER_SIZE_ARB);
 	}
 
 	static int getBufferObjectSizeATI(ContextCapabilities caps, int buffer) {
-		IntBuffer scratch_buffer = caps.scratch_int_buffer;
-		ATIVertexArrayObject.glGetObjectBufferATI(buffer, ATIVertexArrayObject.GL_OBJECT_BUFFER_SIZE_ATI, scratch_buffer);
-		return scratch_buffer.get(0);
+		return ATIVertexArrayObject.glGetObjectBufferATI(buffer, ATIVertexArrayObject.GL_OBJECT_BUFFER_SIZE_ATI);
 	}
 
 	static int getNamedBufferObjectSize(ContextCapabilities caps, int buffer) {
-		IntBuffer scratch_buffer = caps.scratch_int_buffer;
-		EXTDirectStateAccess.glGetNamedBufferParameterEXT(buffer, GL15.GL_BUFFER_SIZE, scratch_buffer);
-		return scratch_buffer.get(0);
-	}
-
-	private static boolean checkBufferObject(ContextCapabilities caps, int buffer_enum, boolean state) {
-		IntBuffer scratch_buffer = caps.scratch_int_buffer;
-		GL11.glGetInteger(buffer_enum, scratch_buffer);
-		boolean is_enabled = scratch_buffer.get(0) != 0;
-		return state == is_enabled;
+		return EXTDirectStateAccess.glGetNamedBufferParameterEXT(buffer, GL15.GL_BUFFER_SIZE);
 	}
 
 	/** Helper method to ensure that array buffer objects are disabled. If they are enabled, we'll throw an OpenGLException */
 	static void ensureArrayVBOdisabled(ContextCapabilities caps) {
-		if(StateTracker.getReferencesStack(caps).getReferences().arrayBuffer != 0)
+		if( LWJGLUtil.CHECKS && StateTracker.getReferencesStack(caps).getReferences().arrayBuffer != 0 )
 			throw new OpenGLException("Cannot use Buffers when Array Buffer Object is enabled");
 	}
 
 	/** Helper method to ensure that array buffer objects are enabled. If they are disabled, we'll throw an OpenGLException */
 	static void ensureArrayVBOenabled(ContextCapabilities caps) {
-		if(StateTracker.getReferencesStack(caps).getReferences().arrayBuffer == 0)
+		if( LWJGLUtil.CHECKS && StateTracker.getReferencesStack(caps).getReferences().arrayBuffer == 0 )
 			throw new OpenGLException("Cannot use offsets when Array Buffer Object is disabled");
 	}
 
 	/** Helper method to ensure that element array buffer objects are disabled. If they are enabled, we'll throw an OpenGLException */
 	static void ensureElementVBOdisabled(ContextCapabilities caps) {
-		if(StateTracker.getReferencesStack(caps).getReferences().elementArrayBuffer != 0)
+		if( LWJGLUtil.CHECKS && StateTracker.getReferencesStack(caps).getReferences().elementArrayBuffer != 0 )
 			throw new OpenGLException("Cannot use Buffers when Element Array Buffer Object is enabled");
 	}
 
 	/** Helper method to ensure that element array buffer objects are enabled. If they are disabled, we'll throw an OpenGLException */
 	static void ensureElementVBOenabled(ContextCapabilities caps) {
-		if(StateTracker.getReferencesStack(caps).getReferences().elementArrayBuffer == 0)
+		if( LWJGLUtil.CHECKS && StateTracker.getReferencesStack(caps).getReferences().elementArrayBuffer == 0 )
 			throw new OpenGLException("Cannot use offsets when Element Array Buffer Object is disabled");
 	}
 
 	/** Helper method to ensure that array buffer objects are disabled. If they are enabled, we'll throw an OpenGLException */
 	static void ensureIndirectBOdisabled(ContextCapabilities caps) {
-		if ( StateTracker.getReferencesStack(caps).getReferences().indirectBuffer != 0 )
+		if ( LWJGLUtil.CHECKS && StateTracker.getReferencesStack(caps).getReferences().indirectBuffer != 0 )
 			throw new OpenGLException("Cannot use Buffers when Draw Indirect Object is enabled");
 	}
 
 	/** Helper method to ensure that array buffer objects are enabled. If they are disabled, we'll throw an OpenGLException */
 	static void ensureIndirectBOenabled(ContextCapabilities caps) {
-		if ( StateTracker.getReferencesStack(caps).getReferences().indirectBuffer == 0 )
+		if ( LWJGLUtil.CHECKS && StateTracker.getReferencesStack(caps).getReferences().indirectBuffer == 0 )
 			throw new OpenGLException("Cannot use offsets when Draw Indirect Object is disabled");
 	}
 
 	/** Helper method to ensure that pixel pack buffer objects are disabled. If they are enabled, we'll throw an OpenGLException */
 	static void ensurePackPBOdisabled(ContextCapabilities caps) {
-		if ( StateTracker.getReferencesStack(caps).getReferences().pixelPackBuffer != 0 )
+		if ( LWJGLUtil.CHECKS && StateTracker.getReferencesStack(caps).getReferences().pixelPackBuffer != 0 )
 			throw new OpenGLException("Cannot use Buffers when Pixel Pack Buffer Object is enabled");
 	}
 
 	/** Helper method to ensure that pixel pack buffer objects are enabled. If they are disabled, we'll throw an OpenGLException */
 	static void ensurePackPBOenabled(ContextCapabilities caps) {
-		if ( StateTracker.getReferencesStack(caps).getReferences().pixelPackBuffer == 0 )
+		if ( LWJGLUtil.CHECKS && StateTracker.getReferencesStack(caps).getReferences().pixelPackBuffer == 0 )
 			throw new OpenGLException("Cannot use offsets when Pixel Pack Buffer Object is disabled");
 	}
 
 	/** Helper method to ensure that pixel unpack buffer objects are disabled. If they are enabled, we'll throw an OpenGLException */
 	static void ensureUnpackPBOdisabled(ContextCapabilities caps) {
-		if ( StateTracker.getReferencesStack(caps).getReferences().pixelUnpackBuffer != 0 )
+		if ( LWJGLUtil.CHECKS && StateTracker.getReferencesStack(caps).getReferences().pixelUnpackBuffer != 0 )
 			throw new OpenGLException("Cannot use Buffers when Pixel Unpack Buffer Object is enabled");
 	}
 
 	/** Helper method to ensure that pixel unpack buffer objects are enabled. If they are disabled, we'll throw an OpenGLException */
 	static void ensureUnpackPBOenabled(ContextCapabilities caps) {
-		if ( StateTracker.getReferencesStack(caps).getReferences().pixelUnpackBuffer == 0 )
+		if ( LWJGLUtil.CHECKS && StateTracker.getReferencesStack(caps).getReferences().pixelUnpackBuffer == 0 )
 			throw new OpenGLException("Cannot use offsets when Pixel Unpack Buffer Object is disabled");
 	}
 
@@ -162,19 +148,19 @@ class GLChecks {
 	 * @return the size, in elements, of the image
 	 */
 	static int calculateImageStorage(Buffer buffer, int format, int type, int width, int height, int depth) {
-		return calculateImageStorage(format, type, width, height, depth) >> BufferUtils.getElementSizeExponent(buffer);
+		return LWJGLUtil.CHECKS ? calculateImageStorage(format, type, width, height, depth) >> BufferUtils.getElementSizeExponent(buffer) : 0;
 	}
 
 	static int calculateTexImage1DStorage(Buffer buffer, int format, int type, int width) {
-		return calculateTexImage1DStorage(format, type, width) >> BufferUtils.getElementSizeExponent(buffer);
+		return LWJGLUtil.CHECKS ? calculateTexImage1DStorage(format, type, width) >> BufferUtils.getElementSizeExponent(buffer) : 0;
 	}
 
 	static int calculateTexImage2DStorage(Buffer buffer, int format, int type, int width, int height) {
-		return calculateTexImage2DStorage(format, type, width, height) >> BufferUtils.getElementSizeExponent(buffer);
+		return LWJGLUtil.CHECKS ? calculateTexImage2DStorage(format, type, width, height) >> BufferUtils.getElementSizeExponent(buffer) : 0;
 	}
 
 	static int calculateTexImage3DStorage(Buffer buffer, int format, int type, int width, int height, int depth) {
-		return calculateTexImage3DStorage(format, type, width, height, depth) >> BufferUtils.getElementSizeExponent(buffer);
+		return LWJGLUtil.CHECKS ? calculateTexImage3DStorage(format, type, width, height, depth) >> BufferUtils.getElementSizeExponent(buffer) : 0;
 	}
 
 	/**
diff --git a/src/java/org/lwjgl/opengl/GLContext.java b/src/java/org/lwjgl/opengl/GLContext.java
index f98c41f..f315894 100644
--- a/src/java/org/lwjgl/opengl/GLContext.java
+++ b/src/java/org/lwjgl/opengl/GLContext.java
@@ -54,8 +54,8 @@ import java.util.*;
  * That way, multiple threads can have multiple contexts current and render to them concurrently.
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 3279 $
- *          $Id: GLContext.java 3279 2010-03-11 21:06:49Z spasi $
+ * @version $Revision: 3355 $
+ *          $Id: GLContext.java 3355 2010-05-27 22:56:29Z spasi $
  */
 public final class GLContext {
 
@@ -169,6 +169,22 @@ public final class GLContext {
 		return 0;
 	}
 
+	/**
+	 * Helper method to get a pointer to a named function with aliases in the OpenGL library.
+	 *
+	 * @param aliases the function name aliases.
+	 *
+	 * @return the function pointer address
+	 */
+	static long getFunctionAddress(String[] aliases) {
+		for ( int i = 0; i < aliases.length; i++ ) {
+			long address = getFunctionAddress(aliases[i]);
+			if ( address != 0 )
+				return address;
+		}
+		return 0;
+	}
+
 	/** Helper method to get a pointer to a named function in the OpenGL library */
 	static native long getFunctionAddress(String name);
 
diff --git a/src/java/org/lwjgl/opengl/LinuxDisplay.java b/src/java/org/lwjgl/opengl/LinuxDisplay.java
index 61332e8..6721692 100644
--- a/src/java/org/lwjgl/opengl/LinuxDisplay.java
+++ b/src/java/org/lwjgl/opengl/LinuxDisplay.java
@@ -39,6 +39,9 @@ package org.lwjgl.opengl;
  */
 
 import java.awt.Canvas;
+import java.io.BufferedReader;
+import java.io.IOException;
+import java.io.InputStreamReader;
 import java.nio.ByteBuffer;
 import java.nio.FloatBuffer;
 import java.nio.IntBuffer;
@@ -48,6 +51,12 @@ import org.lwjgl.LWJGLException;
 import org.lwjgl.LWJGLUtil;
 import org.lwjgl.opengl.XRandR.Screen;
 
+import java.security.AccessController;
+import java.security.PrivilegedAction;
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
 final class LinuxDisplay implements DisplayImplementation {
 	/* X11 constants */
 	public final static int CurrentTime = 0;
@@ -407,7 +416,15 @@ final class LinuxDisplay implements DisplayImplementation {
 				ByteBuffer handle = peer_info.lockAndGetHandle();
 				try {
 					current_window_mode = getWindowMode(Display.isFullscreen());
-					boolean undecorated = Display.getPrivilegedBoolean("org.lwjgl.opengl.Window.undecorated") || current_window_mode != WINDOWED;
+					// Try to enable Lecagy FullScreen Support in Compiz, else
+					// we may have trouble with stuff overlapping our fullscreen window.
+					if ( current_window_mode != WINDOWED )
+						Compiz.setLegacyFullscreenSupport(true);
+					// Setting _MOTIF_WM_HINTS in fullscreen mode is problematic for certain window
+					// managers. We do not set MWM_HINTS_DECORATIONS in fullscreen mode anymore,
+					// unless org.lwjgl.opengl.Window.undecorated_fs has been specified.
+					// See native/linux/org_lwjgl_opengl_Display.c, createWindow function.
+					boolean undecorated = Display.getPrivilegedBoolean("org.lwjgl.opengl.Window.undecorated") || (current_window_mode != WINDOWED && Display.getPrivilegedBoolean("org.lwjgl.opengl.Window.undecorated_fs"));
 					this.parent = parent;
 					parent_window = parent != null ? getHandle(parent) : getRootWindow(getDisplay(), getDefaultScreen());
 					current_window = nCreateWindow(getDisplay(), getDefaultScreen(), handle, mode, current_window_mode, x, y, undecorated, parent_window);
@@ -441,7 +458,7 @@ final class LinuxDisplay implements DisplayImplementation {
 	private static native void mapRaised(long display, long window);
 	private static native void reparentWindow(long display, long window, long parent, int x, int y);
 
-	private boolean isAncestorXEmbedded(long window) throws LWJGLException {
+	private static boolean isAncestorXEmbedded(long window) throws LWJGLException {
 		long xembed_atom = internAtom("_XEMBED_INFO", true);
 		if (xembed_atom != None) {
 			long w = window;
@@ -483,6 +500,9 @@ final class LinuxDisplay implements DisplayImplementation {
 			ungrabKeyboard();
 			nDestroyWindow(getDisplay(), getWindow());
 			decDisplay();
+
+			if ( current_window_mode != WINDOWED )
+				Compiz.setLegacyFullscreenSupport(false);
 		} finally {
 			unlockAWT();
 		}
@@ -524,7 +544,12 @@ final class LinuxDisplay implements DisplayImplementation {
 		try {
 			if( current_displaymode_extension == XRANDR && savedXrandrConfig.length > 0 )
 			{
-				XRandR.setConfiguration( savedXrandrConfig );
+				AccessController.doPrivileged(new PrivilegedAction() {
+					public Object run() {
+						XRandR.setConfiguration( savedXrandrConfig );
+						return null;
+					}
+				});
 			}
 			else
 			{
@@ -532,6 +557,8 @@ final class LinuxDisplay implements DisplayImplementation {
 			}
 			if (isXF86VidModeSupported())
 				doSetGamma(saved_gamma);
+
+			Compiz.setLegacyFullscreenSupport(false);
 		} catch (LWJGLException e) {
 			LWJGLUtil.log("Caught exception while resetting mode: " + e);
 		} finally {
@@ -606,6 +633,8 @@ final class LinuxDisplay implements DisplayImplementation {
 	public DisplayMode init() throws LWJGLException {
 		lockAWT();
 		try {
+			Compiz.init();
+
 			delete_atom = internAtom("WM_DELETE_WINDOW", false);
 			current_displaymode_extension = getBestDisplayModeExtension();
 			if (current_displaymode_extension == NONE)
@@ -615,7 +644,11 @@ final class LinuxDisplay implements DisplayImplementation {
 				throw new LWJGLException("No modes available");
 			switch (current_displaymode_extension) {
 				case XRANDR:
-					savedXrandrConfig = XRandR.getConfiguration();
+					savedXrandrConfig = (Screen[])AccessController.doPrivileged(new PrivilegedAction() {
+						public Object run() {
+							return XRandR.getConfiguration();
+						}
+					});
 					saved_mode = getCurrentXRandrMode();
 					break;
 				case XF86VIDMODE:
@@ -847,12 +880,12 @@ final class LinuxDisplay implements DisplayImplementation {
 				setInputFocusUnsafe(current_window);
 			}
 			else if (xembedded) {
-				setInputFocusUnsafe(0);
+				setInputFocusUnsafe(1);
 			}
 		}
-		else if (parent_focus && !focused) {
-			setInputFocusUnsafe(current_window);
-		}
+		//else if (parent_focus && !focused && !xembedded) {
+		//	setInputFocusUnsafe(current_window);
+		//}
 	}
 
 	private void setFocused(boolean got_focus, int focus_detail) {
@@ -890,7 +923,12 @@ final class LinuxDisplay implements DisplayImplementation {
 			try {
 				if( current_displaymode_extension == XRANDR && savedXrandrConfig.length > 0 )
 				{
-					XRandR.setConfiguration( savedXrandrConfig );
+					AccessController.doPrivileged(new PrivilegedAction() {
+						public Object run() {
+							XRandR.setConfiguration( savedXrandrConfig );
+							return null;
+						}
+					});
 				}
 				else
 				{
@@ -1212,4 +1250,193 @@ final class LinuxDisplay implements DisplayImplementation {
         public boolean isInsideWindow() {
             return true;
         }
-}
+
+	/**
+	 * Helper class for managing Compiz's workarounds. We need this to enable Legacy
+	 * Fullscreen Support in Compiz, else we'll have trouble with fullscreen windows
+	 * when Compiz effects are enabled.
+	 *
+	 * Implementation Note: This code is probably too much for an inner class, but
+	 * keeping it here until we're sure we cannot find a better solution.
+	 */
+	private static final class Compiz {
+
+		private static boolean applyFix;
+
+		private static Provider provider;
+
+		private Compiz() {
+		}
+
+		static void init() {
+			if ( Display.getPrivilegedBoolean("org.lwjgl.opengl.Window.nocompiz_lfs") )
+				return;
+
+			AccessController.doPrivileged(new PrivilegedAction() {
+				public Object run() {
+					try {
+						// Check if Compiz is active
+						if ( !isProcessActive("compiz") )
+							return null;
+
+						provider = null;
+
+						String providerName = null;
+
+						// Check if Dbus is available
+						if ( isProcessActive("dbus-daemon") ) {
+							providerName = "Dbus";
+							provider = new Provider() {
+
+								private static final String KEY = "/org/freedesktop/compiz/workarounds/allscreens/legacy_fullscreen";
+
+								public boolean hasLegacyFullscreenSupport() throws LWJGLException {
+									final List output = Compiz.run(new String[] {
+										"dbus-send", "--print-reply", "--type=method_call", "--dest=org.freedesktop.compiz", KEY, "org.freedesktop.compiz.get"
+									});
+
+									if ( output == null || output.size() < 2 )
+										throw new LWJGLException("Invalid Dbus reply.");
+
+									String line = (String)output.get(0);
+
+									if ( !line.startsWith("method return") )
+										throw new LWJGLException("Invalid Dbus reply.");
+
+									line = ((String)output.get(1)).trim(); // value
+									if ( !line.startsWith("boolean") || line.length() < 12)
+										throw new LWJGLException("Invalid Dbus reply.");
+
+									return "true".equalsIgnoreCase(line.substring("boolean".length() + 1));
+								}
+
+								public void setLegacyFullscreenSupport(final boolean state) throws LWJGLException {
+									if ( Compiz.run(new String[] {
+										"dbus-send", "--type=method_call", "--dest=org.freedesktop.compiz", KEY, "org.freedesktop.compiz.set", "boolean:" + Boolean.toString(state)
+									}) == null )
+										throw new LWJGLException("Failed to apply Compiz LFS workaround.");
+								}
+							};
+						} else {
+							try {
+								// Check if Gconf is available
+								Runtime.getRuntime().exec("gconftool");
+
+								providerName = "gconftool";
+								provider = new Provider() {
+
+									private static final String KEY = "/apps/compiz/plugins/workarounds/allscreens/options/legacy_fullscreen";
+
+									public boolean hasLegacyFullscreenSupport() throws LWJGLException {
+										final List output = Compiz.run(new String[] {
+											"gconftool", "-g", KEY
+										});
+
+										if ( output == null || output.size() == 0 )
+											throw new LWJGLException("Invalid gconftool reply.");
+
+										return Boolean.parseBoolean(((String)output.get(0)).trim());
+									}
+
+									public void setLegacyFullscreenSupport(final boolean state) throws LWJGLException {
+										if ( Compiz.run(new String[] {
+											"gconftool", "-s", KEY, "-s", Boolean.toString(state), "-t", "bool"
+										}) == null )
+											throw new LWJGLException("Failed to apply Compiz LFS workaround.");
+
+										if ( state ) {
+											try {
+												// gconftool will not apply the workaround immediately, sleep a bit
+												// to make sure it will be ok when we create the window.
+												Thread.sleep(200); // 100 is too low, 150 works, set to 200 to be safe.
+											} catch (InterruptedException e) {
+												e.printStackTrace();
+											}
+										}
+									}
+								};
+							} catch (IOException e) {
+								// Ignore
+							}
+						}
+
+						if ( provider != null && !provider.hasLegacyFullscreenSupport() ) { // No need to do anything if LFS is already enabled.
+							applyFix = true;
+							LWJGLUtil.log("Using " + providerName + " to apply Compiz LFS workaround.");
+						}
+					} catch (LWJGLException e) {
+						// Ignore
+					} finally {
+						return null;
+					}
+				}
+			});
+		}
+
+		static void setLegacyFullscreenSupport(final boolean enabled) {
+			if ( !applyFix )
+				return;
+
+			AccessController.doPrivileged(new PrivilegedAction() {
+				public Object run() {
+					try {
+						provider.setLegacyFullscreenSupport(enabled);
+					} catch (LWJGLException e) {
+						LWJGLUtil.log("Failed to change Compiz Legacy Fullscreen Support. Reason: " + e.getMessage());
+					}
+					return null;
+				}
+			});
+		}
+
+		private static List run(final String[] command) throws LWJGLException {
+			final List output = new ArrayList();
+
+			try {
+				final Process p = Runtime.getRuntime().exec(command);
+				try {
+					final int exitValue = p.waitFor();
+					if ( exitValue != 0 )
+						return null;
+				} catch (InterruptedException e) {
+					throw new LWJGLException("Process interrupted.", e);
+				}
+
+				final BufferedReader br = new BufferedReader(new InputStreamReader(p.getInputStream()));
+
+				String line;
+				while ( (line = br.readLine()) != null )
+					output.add(line);
+
+				br.close();
+			} catch (final IOException e) {
+				throw new LWJGLException("Process failed.", e);
+			}
+
+			return output;
+		}
+
+		private static boolean isProcessActive(final String processName) throws LWJGLException {
+			final List output = run(new String[] { "ps", "-C", processName });
+			if ( output == null )
+				return false;
+
+			for ( Iterator iter = output.iterator(); iter.hasNext(); ) {
+				final String line = (String)iter.next();
+				if ( line.contains(processName) );
+					return true;
+			}
+
+			return false;
+		}
+
+		private interface Provider {
+
+			boolean hasLegacyFullscreenSupport() throws LWJGLException;
+
+			void setLegacyFullscreenSupport(boolean state) throws LWJGLException;
+
+		}
+	}
+
+}
\ No newline at end of file
diff --git a/src/java/org/lwjgl/opengl/MacOSXDisplay.java b/src/java/org/lwjgl/opengl/MacOSXDisplay.java
index 25be1ba..ea58d0e 100644
--- a/src/java/org/lwjgl/opengl/MacOSXDisplay.java
+++ b/src/java/org/lwjgl/opengl/MacOSXDisplay.java
@@ -78,7 +78,7 @@ final class MacOSXDisplay implements DisplayImplementation {
 			AccessController.doPrivileged(new PrivilegedExceptionAction() {
 				public Object run() throws Exception {
 					Application.getApplication().addApplicationListener(new ApplicationAdapter() {
-						public final void handleQuit(ApplicationEvent event) {
+						public void handleQuit(ApplicationEvent event) {
 							doHandleQuit();
 						}
 					});
@@ -271,15 +271,16 @@ final class MacOSXDisplay implements DisplayImplementation {
 		 *
 		 * - elias
 		 */
+		AbstractDrawable drawable = (AbstractDrawable)Display.getDrawable();
 		if (Display.isFullscreen() && (frame != null && frame.getCanvas().syncCanvasPainted() || should_update)) {
 			try {
-				MacOSXContextImplementation.resetView(Display.getDrawable().getContext().getPeerInfo(), Display.getDrawable().getContext());
+				MacOSXContextImplementation.resetView(drawable.peer_info, drawable.context);
 			} catch (LWJGLException e) {
 				LWJGLUtil.log("Failed to reset context: " + e);
 			}
 		}
 		if (should_update) {
-			Display.getDrawable().getContext().update();
+			drawable.context.update();
 			/* This is necessary to make sure the context won't "forget" about the view size */
 			GL11.glGetInteger(GL11.GL_VIEWPORT, current_viewport);
 			GL11.glViewport(current_viewport.get(0), current_viewport.get(1), current_viewport.get(2), current_viewport.get(3));
diff --git a/src/java/org/lwjgl/opengl/Pbuffer.java b/src/java/org/lwjgl/opengl/Pbuffer.java
index 877b192..e11b7c6 100644
--- a/src/java/org/lwjgl/opengl/Pbuffer.java
+++ b/src/java/org/lwjgl/opengl/Pbuffer.java
@@ -35,7 +35,6 @@ import java.nio.IntBuffer;
 
 import org.lwjgl.BufferUtils;
 import org.lwjgl.LWJGLException;
-import org.lwjgl.LWJGLUtil;
 import org.lwjgl.Sys;
 
 /**
@@ -46,10 +45,10 @@ import org.lwjgl.Sys;
  * This class is thread-safe.
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 3116 $
- * $Id: Pbuffer.java 3116 2008-08-19 16:46:03Z spasi $
+ * @version $Revision: 3334 $
+ * $Id: Pbuffer.java 3334 2010-04-22 23:21:48Z spasi $
  */
-public final class Pbuffer implements Drawable {
+public final class Pbuffer extends AbstractDrawable {
 	/**
 	 * Indicates that Pbuffers can be created.
 	 */
@@ -136,11 +135,6 @@ public final class Pbuffer implements Drawable {
 	public static final int DEPTH_BUFFER = RenderTexture.WGL_DEPTH_COMPONENT_NV;
 
 	/**
-	 * Handle to the native GL rendering context
-	 */
-	private final PeerInfo peer_info;
-
-	/**
 	 * Width
 	 */
 	private final int width;
@@ -150,10 +144,6 @@ public final class Pbuffer implements Drawable {
 	 */
 	private final int height;
 
-	private final Context context;
-
-	private boolean destroyed;
-
 	static {
 		Sys.initialize();
 	}
@@ -227,14 +217,11 @@ public final class Pbuffer implements Drawable {
 		this.width = width;
 		this.height = height;
 		this.peer_info = createPbuffer(width, height, pixel_format, renderTexture);
-		Context shared_context = null;
-		if (shared_drawable != null) {
-			shared_context = shared_drawable.getContext();
-		} else {
-			Drawable display_drawable = Display.getDrawable();
-			if (display_drawable != null)
-				shared_context = display_drawable.getContext();
-		}
+		Context shared_context;
+		if (shared_drawable != null)
+			shared_context = ((DrawableLWJGL)shared_drawable).getContext();
+		else
+			shared_context = ((DrawableLWJGL)Display.getDrawable()).getContext(); // May be null
 		this.context = new Context(peer_info, attribs, shared_context);
 	}
 
@@ -251,15 +238,6 @@ public final class Pbuffer implements Drawable {
 					renderTexture.pBufferAttribs);
 	}
 
-	public Context getContext() {
-		return context;
-	}
-
-	private void checkDestroyed() {
-		if (destroyed)
-			throw new IllegalStateException("Pbuffer is destroyed");
-	}
-
 	/**
 	 * Method to test for validity of the buffer. If this function returns true, the buffer contents is lost. The buffer can still
 	 * be used, but the results are undefined. The application is expected to release the buffer if needed, destroy it and recreate
@@ -273,15 +251,6 @@ public final class Pbuffer implements Drawable {
 	}
 
 	/**
-	 * Method to make the Pbuffer context current. All subsequent OpenGL calls will go to this buffer.
-	 * @throws LWJGLException if the context could not be made current
-	 */
-	public synchronized void makeCurrent() throws LWJGLException {
-		checkDestroyed();
-		context.makeCurrent();
-	}
-
-	/**
 	 * Gets the Pbuffer capabilities.
 	 *
 	 * @return a bitmask of Pbuffer capabilities.
@@ -290,22 +259,6 @@ public final class Pbuffer implements Drawable {
 		return Display.getImplementation().getPbufferCapabilities();
 	}
 
-	/**
-	 * Destroys the Pbuffer. After this call, there will be no valid GL rendering context - regardless of whether this Pbuffer was
-	 * the current rendering context or not.
-	 */
-	public synchronized void destroy() {
-		if (destroyed)
-			return;
-		try {
-			context.forceDestroy();
-			peer_info.destroy();
-			destroyed = true;
-		} catch (LWJGLException e) {
-			LWJGLUtil.log("Exception occurred while destroying pbuffer: " + e);
-		}
-	}
-
 	// -----------------------------------------------------------------------------------------
 	// ------------------------------- Render-to-Texture Methods -------------------------------
 	// -----------------------------------------------------------------------------------------
diff --git a/src/java/org/lwjgl/opengl/PixelFormat.java b/src/java/org/lwjgl/opengl/PixelFormat.java
index 5219367..7c11bfb 100644
--- a/src/java/org/lwjgl/opengl/PixelFormat.java
+++ b/src/java/org/lwjgl/opengl/PixelFormat.java
@@ -45,7 +45,7 @@ package org.lwjgl.opengl;
  * pixel format selection path, which could trigger a crash.
  *
  * @author elias_naur at sourceforge.net
- * @version $Revision: 3116 $
+ * @version $Revision: 3355 $
  */
 
 public final class PixelFormat {
@@ -66,6 +66,14 @@ public final class PixelFormat {
 	 * 0 means that anti-aliasing is disabled.
 	 */
 	private int samples;
+	/**
+	 * The number of COLOR_SAMPLES_NV to use for Coverage Sample Anti-aliasing (CSAA).
+	 * When this number is greater than 0, the {@code samples} property will be treated
+	 * as if it were the COVERAGE_SAMPLES_NV property.
+	 * <p/>
+	 * This property is currently a no-op for the MacOS implementation.
+	 */
+	private int colorSamples;
 	/** The number of auxiliary buffers */
 	private int num_aux_buffers;
 	/** The number of bits per pixel in the accumulation buffer */
@@ -76,9 +84,15 @@ public final class PixelFormat {
 	private boolean stereo;
 	/** Whether this format specifies a floating point format */
 	private boolean floating_point;
-	/** Whether this format specifies a packed floating point format (32 bit unsigned - R11F_G11F_B10F) */
+	/**
+	 * Whether this format specifies a packed floating point format (32 bit unsigned - R11F_G11F_B10F)
+	 * This property is currently a no-op for the MacOS implementation.
+	 */
 	private boolean floating_point_packed;
-	/** Whether this format specifies an sRGB format */
+	/**
+	 * Whether this format specifies an sRGB format
+	 * This property is currently a no-op for the MacOS implementation.
+	 */
 	private boolean sRGB;
 
 	/**
@@ -132,6 +146,7 @@ public final class PixelFormat {
 		this.stencil = pf.stencil;
 
 		this.samples = pf.samples;
+		this.colorSamples = pf.colorSamples;
 
 		this.num_aux_buffers = pf.num_aux_buffers;
 
@@ -245,6 +260,38 @@ public final class PixelFormat {
 		return pf;
 	}
 
+	/**
+	 * Returns a new PixelFormat object with the same properties as this PixelFormat and the new color samples values.
+	 * A value greater than 0 is valid only if the {@code samples} property is also greater than 0. Additionally, the
+	 * color samples value needs to be lower than or equal to the {@code samples} property.
+	 *
+	 * @param colorSamples    the new color samples value.
+	 *
+	 * @return the new PixelFormat
+	 */
+	public PixelFormat withCoverageSamples(final int colorSamples) {
+		return withCoverageSamples(colorSamples, samples);
+	}
+
+	/**
+	 * Returns a new PixelFormat object with the same properties as this PixelFormat and the new color samples
+	 * and coverage samples values.
+	 *
+	 * @param colorSamples    the new color samples value. This value must be lower than or equal to the coverage samples value.
+	 * @param coverageSamples the new coverage samples value.
+	 *
+	 * @return the new PixelFormat
+	 */
+	public PixelFormat withCoverageSamples(final int colorSamples, final int coverageSamples) {
+		if ( coverageSamples < 0 || colorSamples < 0 || (coverageSamples == 0 && 0 < colorSamples) || coverageSamples < colorSamples  )
+			throw new IllegalArgumentException("Invalid number of coverage samples specified: " + coverageSamples + " - " + colorSamples);
+
+		final PixelFormat pf = new PixelFormat(this);
+		pf.samples = coverageSamples;
+		pf.colorSamples = colorSamples;
+		return pf;
+	}
+
 	public int getAuxBuffers() {
 		return num_aux_buffers;
 	}
diff --git a/src/java/org/lwjgl/opengl/MacOSXAWTGLCanvasPeerInfo.java b/src/java/org/lwjgl/opengl/SharedDrawable.java
similarity index 74%
copy from src/java/org/lwjgl/opengl/MacOSXAWTGLCanvasPeerInfo.java
copy to src/java/org/lwjgl/opengl/SharedDrawable.java
index 50a8f00..f96d0f6 100644
--- a/src/java/org/lwjgl/opengl/MacOSXAWTGLCanvasPeerInfo.java
+++ b/src/java/org/lwjgl/opengl/SharedDrawable.java
@@ -33,23 +33,25 @@ package org.lwjgl.opengl;
 
 import org.lwjgl.LWJGLException;
 
-import java.awt.Canvas;
+/**
+ * @author Spasi
+ */
 
 /**
+ * A Drawable implementation that shares its context with another Drawable. This is useful
+ * for background loading of resources. See org.lwjgl.test.opengl.multithread.BackgroundLoad
+ * for an example.
  *
- * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 3116 $
- * $Id: MacOSXAWTGLCanvasPeerInfo.java 3116 2008-08-19 16:46:03Z spasi $
+ * @author Spasi
  */
-final class MacOSXAWTGLCanvasPeerInfo extends MacOSXCanvasPeerInfo {
-	private final Canvas component;
+public final class SharedDrawable extends AbstractDrawable {
 
-	MacOSXAWTGLCanvasPeerInfo(Canvas component, PixelFormat pixel_format, boolean support_pbuffer) throws LWJGLException {
-		super(pixel_format, support_pbuffer);
-		this.component = component;
+	public SharedDrawable(final Drawable drawable) throws LWJGLException {
+		this.context = ((DrawableLWJGL)drawable).createSharedContext();
 	}
 
-	protected void doLockAndInitHandle() throws LWJGLException {
-		initHandle(component);
+	public Context createSharedContext() {
+		throw new UnsupportedOperationException();
 	}
+
 }
diff --git a/src/java/org/lwjgl/opengl/WindowsDisplay.java b/src/java/org/lwjgl/opengl/WindowsDisplay.java
index 24b56fb..6a32c3c 100644
--- a/src/java/org/lwjgl/opengl/WindowsDisplay.java
+++ b/src/java/org/lwjgl/opengl/WindowsDisplay.java
@@ -437,8 +437,9 @@ final class WindowsDisplay implements DisplayImplementation {
 			 * is maximized helps some gfx cards recover from fullscreen
 			 */
 			try {
-				if (Display.getDrawable().getContext() != null && Display.getDrawable().getContext().isCurrent())
-					Display.getDrawable().getContext().makeCurrent();
+				Context context = ((DrawableLWJGL)Display.getDrawable()).getContext();
+				if (context != null && context.isCurrent())
+					context.makeCurrent();
 			} catch (LWJGLException e) {
 				LWJGLUtil.log("Exception occurred while trying to make context current: " + e);
 			}
@@ -973,4 +974,4 @@ final class WindowsDisplay implements DisplayImplementation {
 			return "Rect: top = " + top + " bottom = " + bottom + " left = " + left + " right = " + right;
 		}
 	}
-}
+}
\ No newline at end of file
diff --git a/src/java/org/lwjgl/opengl/XRandR.java b/src/java/org/lwjgl/opengl/XRandR.java
index 4a6fd85..519ef62 100644
--- a/src/java/org/lwjgl/opengl/XRandR.java
+++ b/src/java/org/lwjgl/opengl/XRandR.java
@@ -1,33 +1,28 @@
 /*
- * Copyright (c) 2002-2010 LWJGL Project
- * All rights reserved.
- *
+ * Copyright (c) 2002-2010 LWJGL Project All rights reserved.
  * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- *   notice, this list of conditions and the following disclaimer.
- *
- * * Redistributions in binary form must reproduce the above copyright
- *   notice, this list of conditions and the following disclaimer in the
- *   documentation and/or other materials provided with the distribution.
- *
- * * Neither the name of 'LWJGL' nor the names of
- *   its contributors may be used to endorse or promote products derived
- *   from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
- * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
- * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * modification, are permitted provided that the following conditions
+ * are met: * Redistributions of source code must retain the above
+ * copyright notice, this list of conditions and the following
+ * disclaimer. * Redistributions in binary form must reproduce the
+ * above copyright notice, this list of conditions and the following
+ * disclaimer in the documentation and/or other materials provided
+ * with the distribution. * Neither the name of 'LWJGL' nor the names
+ * of its contributors may be used to endorse or promote products
+ * derived from this software without specific prior written
+ * permission. THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
+ * CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
+ * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
+ * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
- * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
- * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
- * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
+ * USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
+ * DAMAGE.
  */
 
 package org.lwjgl.opengl;
@@ -39,9 +34,10 @@ import java.util.ArrayList;
 import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
+import java.util.regex.Matcher;
 import java.util.regex.Pattern;
-import java.security.AccessController;
-import java.security.PrivilegedAction;
+
+import org.lwjgl.LWJGLUtil;
 
 /**
  * Utility for working with the xrandr commmand-line utility. Assumes
@@ -49,53 +45,65 @@ import java.security.PrivilegedAction;
  * 
  * @author ryanm
  */
-public class XRandR {
-
-	private static Screen[]	current;
+public class XRandR
+{
+	private static Screen[] current;
 
-	private static Map		/* <String, Screen[]> */screens;
+	private static Map /* <String, Screen[]> */screens;
 
-	private static void populate() {
-		if (screens == null) {
+	private static void populate()
+	{
+		if( screens == null )
+		{
 			screens = new HashMap/* <String, Screen[]> */();
 
 			// ProcessBuilder pb = new ProcessBuilder( "xrandr", "-q" );
 			// pb.redirectErrorStream();
-			try {
+			try
+			{
 				// Process p= pb.start();
-				Process p = Runtime.getRuntime().exec(new String[] { "xrandr", "-q"});
+				Process p = Runtime.getRuntime().exec( new String[] { "xrandr", "-q" } );
 
 				List/* <Screen> */currentList = new ArrayList/* <Screen> */();
 				List/* <Screen> */possibles = new ArrayList/* <Screen> */();
 				String name = null;
 
-				BufferedReader br = new BufferedReader(new InputStreamReader(p.getInputStream()));
+				BufferedReader br = new BufferedReader( new InputStreamReader( p.getInputStream() ) );
 				String line;
-				while ((line = br.readLine()) != null) {
+				while( ( line = br.readLine() ) != null )
+				{
 					line = line.trim();
-					String[] sa = line.split("\\s+");
+					String[] sa = line.split( "\\s+" );
 
-					if (sa[1].equals("connected")) {
+					if( sa[ 1 ].equals( "connected" ) )
+					{
 						// found a new screen block
-						if (name != null) {
-							screens.put(name, possibles.toArray(new Screen[possibles.size()]));
+						if( name != null )
+						{
+							screens.put( name, possibles.toArray( new Screen[ possibles.size() ] ) );
 							possibles.clear();
 						}
-						name = sa[0];
+						name = sa[ 0 ];
 
 						// record the current config
-						currentList.add(new Screen(name, sa[2]));
-					} else if (Pattern.matches("\\d*x\\d*", sa[0])) {
+						parseScreen( currentList, name, sa[ 2 ] );
+					}
+					else if( Pattern.matches( "\\d*x\\d*", sa[ 0 ] ) )
+					{
 						// found a new mode line
-						possibles.add(new Screen(name, sa[0]));
+						parseScreen( possibles, name, sa[ 0 ] );
 					}
 				}
 
-				screens.put(name, possibles.toArray(new Screen[possibles.size()]));
+				screens.put( name, possibles.toArray( new Screen[ possibles.size() ] ) );
 
 				current = (Screen[]) currentList.toArray(new Screen[currentList.size()]);
-			} catch (IOException e) {
-				e.printStackTrace();
+			}
+			catch( Throwable e )
+			{
+				LWJGLUtil.log( "Exception in XRandR.populate(): " + e.getMessage() );
+				screens.clear();
+				current = new Screen[ 0 ];
 			}
 		}
 	}
@@ -104,13 +112,9 @@ public class XRandR {
 	 * @return The current screen configuration, or an empty array if
 	 *         xrandr is not supported
 	 */
-	public static Screen[] getConfiguration() {
-		AccessController.doPrivileged(new PrivilegedAction() {
-			public Object run() {
-				populate();
-				return null;
-			}
-		});
+	public static Screen[] getConfiguration()
+	{
+		populate();
 
 		return (Screen[]) current.clone();
 	}
@@ -118,62 +122,76 @@ public class XRandR {
 	/**
 	 * @param screens
 	 *           The desired screen set, may not be <code>null</code>
+	 * @throws IllegalArgumentException
+	 *            if no screens are specified
 	 */
-	public static void setConfiguration(Screen[]/* ... */screens) {
-		if (screens.length == 0) {
-			throw new IllegalArgumentException("Must specify at least one screen");
+	public static void setConfiguration( Screen[]/* ... */screens )
+	{
+		if( screens.length == 0 )
+		{
+			throw new IllegalArgumentException( "Must specify at least one screen" );
 		}
 
 		List/* <String> */cmd = new ArrayList/* <String> */();
-		cmd.add("xrandr");
+		cmd.add( "xrandr" );
 
 		// switch off those in the current set not in the new set
-		for (int i = 0; i < current.length; i++) {
+		for( int i = 0; i < current.length; i++ )
+		{
 			boolean found = false;
-			for (int j = 0; j < screens.length; j++) {
-				if (screens[j].name.equals(current[i].name)) {
+			for( int j = 0; j < screens.length; j++ )
+			{
+				if( screens[ j ].name.equals( current[ i ].name ) )
+				{
 					found = true;
 					break;
 				}
 			}
 
-			if (!found) {
-				cmd.add("--output");
-				cmd.add(current[i].name);
-				cmd.add("--off");
+			if( !found )
+			{
+				cmd.add( "--output" );
+				cmd.add( current[ i ].name );
+				cmd.add( "--off" );
 			}
 		}
 
 		// set up new set
-		for (int i = 0; i < screens.length; i++) {
-			screens[i].getArgs(cmd);
+		for( int i = 0; i < screens.length; i++ )
+		{
+			screens[ i ].getArgs( cmd );
 		}
 
-		try {
+		try
+		{
 			// ProcessBuilder pb = new ProcessBuilder( cmd );
 			// pb.redirectErrorStream();
 			// Process p = pb.start();
-			Process p = Runtime.getRuntime().exec((String[]) cmd.toArray(new String[cmd.size()]));
+			Process p =
+					Runtime.getRuntime().exec( ( String[] ) cmd.toArray( new String[ cmd.size() ] ) );
 			// no output is expected, but check anyway
-			BufferedReader br = new BufferedReader(new InputStreamReader(p.getInputStream()));
+			BufferedReader br = new BufferedReader( new InputStreamReader( p.getInputStream() ) );
 			String line;
-			while ((line = br.readLine()) != null) {
-				System.out.println(line);
+			while( ( line = br.readLine() ) != null )
+			{
+				LWJGLUtil.log( "Unexpected output from xrandr process: " + line );
 			}
 			current = screens;
-		} catch (IOException e) {
-			e.printStackTrace();
 		}
-
+		catch( IOException e )
+		{
+			LWJGLUtil.log( "XRandR exception in setConfiguration(): " + e.getMessage() );
+		}
 	}
 
 	/**
 	 * @return the name of connected screens, or an empty array if
 	 *         xrandr is not supported
 	 */
-	public static String[] getScreenNames() {
+	public static String[] getScreenNames()
+	{
 		populate();
-		return (String[]) screens.keySet().toArray(new String[screens.size()]);
+		return ( String[] ) screens.keySet().toArray( new String[ screens.size() ] );
 	}
 
 	/**
@@ -181,77 +199,114 @@ public class XRandR {
 	 * @return the possible resolutions of the named screen, or
 	 *         <code>null</code> if there is no such screen
 	 */
-	public static Screen[] getResolutions(String name) {
+	public static Screen[] getResolutions( String name )
+	{
 		populate();
 		// clone the array to prevent held copies being altered
 		return (Screen[]) ((Screen[]) screens.get(name)).clone();
 	}
 
+	private static final Pattern SCREEN_PATTERN1 =
+			Pattern.compile( "^(\\d+)x(\\d+)\\+(\\d+)\\+(\\d+)$" );
+
+	private static final Pattern SCREEN_PATTERN2 = Pattern.compile( "^(\\d+)x(\\d+)$" );
+
+	/**
+	 * Parses a screen configuration and adds it to the list if it's
+	 * valid.
+	 * 
+	 * @param list
+	 *           the list to add the Screen to if it's valid
+	 * @param name
+	 *           the name of this screen
+	 * @param what
+	 *           config string, format either widthxheight or
+	 *           widthxheight+xPos+yPos
+	 */
+	private static void parseScreen( List /* <Screen> */list, String name, String what )
+	{
+		Matcher m = SCREEN_PATTERN1.matcher( what );
+		if( !m.matches() )
+		{
+			m = SCREEN_PATTERN2.matcher( what );
+			if( !m.matches() )
+			{
+				LWJGLUtil.log( "Did not match: " + what );
+				return;
+			}
+		}
+		int width = Integer.parseInt( m.group( 1 ) );
+		int height = Integer.parseInt( m.group( 2 ) );
+		int xpos, ypos;
+		if( m.groupCount() > 3 )
+		{
+			xpos = Integer.parseInt( m.group( 3 ) );
+			ypos = Integer.parseInt( m.group( 4 ) );
+		}
+		else
+		{
+			xpos = 0;
+			ypos = 0;
+		}
+		list.add( new Screen( name, width, height, xpos, ypos ) );
+	}
+
 	/**
 	 * Encapsulates the configuration of a monitor. Resolution is
 	 * fixed, position is mutable
 	 * 
 	 * @author ryanm
 	 */
-	public static class Screen implements Cloneable {
-
+	public static class Screen implements Cloneable
+	{
 		/**
 		 * Name for this output
 		 */
-		public final String	name;
+		public final String name;
 
 		/**
 		 * Width in pixels
 		 */
-		public final int	width;
+		public final int width;
 
 		/**
 		 * Height in pixels
 		 */
-		public final int	height;
+		public final int height;
 
 		/**
 		 * Position on the x-axis, in pixels
 		 */
-		public int			xPos	= 0;
+		public int xPos = 0;
 
 		/**
 		 * Position on the y-axis, in pixels
 		 */
-		public int			yPos	= 0;
+		public int yPos = 0;
 
-		/**
-		 * @param name
-		 *           name of the screen
-		 * @param conf
-		 *           config string, format either widthxheight or
-		 *           widthxheight+xPos+yPos
-		 */
-		private Screen(String name, String conf) {
+		private Screen( String name, int width, int height, int xPos, int yPos )
+		{
 			this.name = name;
-
-			String[] sa = conf.split("\\D");
-			width = Integer.parseInt(sa[0]);
-			height = Integer.parseInt(sa[1]);
-
-			if (sa.length > 2) {
-				xPos = Integer.parseInt(sa[2]);
-				yPos = Integer.parseInt(sa[3]);
-			}
+			this.width = width;
+			this.height = height;
+			this.xPos = xPos;
+			this.yPos = yPos;
 		}
 
-		private void getArgs(List/* <String> */argList) {
-			argList.add("--output");
-			argList.add(name);
-			argList.add("--mode");
-			argList.add(width + "x" + height);
-			argList.add("--pos");
-			argList.add(xPos + "x" + yPos);
+		private void getArgs( List/* <String> */argList )
+		{
+			argList.add( "--output" );
+			argList.add( name );
+			argList.add( "--mode" );
+			argList.add( width + "x" + height );
+			argList.add( "--pos" );
+			argList.add( xPos + "x" + yPos );
 		}
 
-		// @Override
-		public String toString() {
+		//@Override
+		public String toString()
+		{
 			return name + " " + width + "x" + height + " @ " + xPos + "x" + yPos;
 		}
 	}
-}
+}
\ No newline at end of file
diff --git a/src/java/org/lwjgl/test/openal/EFX10Test.java b/src/java/org/lwjgl/test/openal/EFX10Test.java
new file mode 100644
index 0000000..a0ce4a5
--- /dev/null
+++ b/src/java/org/lwjgl/test/openal/EFX10Test.java
@@ -0,0 +1,464 @@
+/* 
+ * Copyright (c) 2002-2010 LWJGL Project
+ * All rights reserved.
+ * 
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are 
+ * met:
+ * 
+ * * Redistributions of source code must retain the above copyright 
+ *   notice, this list of conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ *
+ * * Neither the name of 'LWJGL' nor the names of 
+ *   its contributors may be used to endorse or promote products derived 
+ *   from this software without specific prior written permission.
+ * 
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR 
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package org.lwjgl.test.openal;
+
+import java.nio.IntBuffer;
+
+import org.lwjgl.BufferUtils;
+import org.lwjgl.openal.AL;
+import org.lwjgl.openal.AL10;
+import org.lwjgl.openal.AL11;
+import org.lwjgl.openal.ALC10;
+import org.lwjgl.openal.ALCcontext;
+import org.lwjgl.openal.ALCdevice;
+import org.lwjgl.openal.EFX10;
+import org.lwjgl.openal.EFXUtil;
+import org.lwjgl.util.WaveData;
+
+/**
+ * Class with a few examples testing and demonstrating the use of the OpenAL extension ALC_EXT_EFX.
+ * <p>
+ * This class is not compatible with the LWJGL debug build (lwjgl-debug.jar), as the debug build
+ * throws exceptions instead of alGetError checks. The redundant exception handling code was not
+ * added in order to keep these examples simple.
+ *
+ * @author Ciardhubh <ciardhubh[at]ciardhubh.de>
+ * @version $Revision$
+ * $Id$
+ */
+public final class EFX10Test {
+
+    public static void main(final String[] args) throws Exception {
+        silentTests();
+        playbackTest();
+        efxUtilTest();
+    }
+
+    /**
+     * Loads OpenAL and makes sure ALC_EXT_EFX is supported.
+     */
+    private static void setupEfx() throws Exception {
+        // Load and create OpenAL
+        if (!AL.isCreated()) {
+            AL.create();
+        }
+        // Query for Effect Extension
+        if (!ALC10.alcIsExtensionPresent(AL.getDevice(), EFX10.ALC_EXT_EFX_NAME)) {
+            throw new Exception("No ALC_EXT_EFX supported by driver.");
+        }
+        System.out.println("ALC_EXT_EFX found.");
+    }
+
+    /**
+     * Runs a series of API calls similar to the tutorials in the Effects Extension Guide of the
+     * OpenAL SDK. Nothing is played in this method.
+     */
+    private static void silentTests() throws Exception {
+        setupEfx();
+
+        final ALCdevice device = AL.getDevice();
+
+        // Create context (only necessary if LWJGL context isn't sufficient, done as example)
+        final IntBuffer contextAttribList = BufferUtils.createIntBuffer(8);
+        contextAttribList.put(ALC10.ALC_FREQUENCY);
+        contextAttribList.put(44100);
+        contextAttribList.put(ALC10.ALC_REFRESH);
+        contextAttribList.put(60);
+        contextAttribList.put(ALC10.ALC_SYNC);
+        contextAttribList.put(ALC10.ALC_FALSE);
+        contextAttribList.rewind();
+        // ALC_MAX_AUXILIARY_SENDS won't go above compile-time max. Set to compile-time max if
+        // greater.
+        contextAttribList.put(EFX10.ALC_MAX_AUXILIARY_SENDS);
+        contextAttribList.put(2);
+        final ALCcontext newContext = ALC10.alcCreateContext(device, contextAttribList);
+        if (newContext == null) {
+            throw new Exception("Failed to create context.");
+        }
+        final int contextCurResult = ALC10.alcMakeContextCurrent(newContext);
+        if (contextCurResult == ALC10.ALC_FALSE) {
+            throw new Exception("Failed to make context current.");
+        }
+
+        // Query EFX ALC values
+        System.out.println("AL_VERSION: " + AL10.alGetString(AL10.AL_VERSION));
+        final IntBuffer buff = BufferUtils.createIntBuffer(1);
+        ALC10.alcGetInteger(device, EFX10.ALC_EFX_MAJOR_VERSION, buff);
+        System.out.println("ALC_EFX_MAJOR_VERSION: " + buff.get(0));
+        ALC10.alcGetInteger(device, EFX10.ALC_EFX_MINOR_VERSION, buff);
+        System.out.println("ALC_EFX_MINOR_VERSION: " + buff.get(0));
+        ALC10.alcGetInteger(device, EFX10.ALC_MAX_AUXILIARY_SENDS, buff);
+        final int maxAuxSends = buff.get(0);
+        System.out.println("ALC_MAX_AUXILIARY_SENDS: " + maxAuxSends);
+
+
+        // Try to create 4 Auxiliary Effect Slots
+        int numAuxSlots = 0;
+        final int[] auxEffectSlots = new int[4]; // try more to test
+        AL10.alGetError();
+        for (numAuxSlots = 0; numAuxSlots < 4; numAuxSlots++) {
+            auxEffectSlots[numAuxSlots] = EFX10.alGenAuxiliaryEffectSlots();
+            if (AL10.alGetError() != AL10.AL_NO_ERROR) {
+                break;
+            }
+        }
+        System.out.println("Created " + numAuxSlots + " aux effect slots.");
+
+        // Try to create 2 Effects
+        int numEffects = 0;
+        final int[] effects = new int[2];
+        for (numEffects = 0; numEffects < 2; numEffects++) {
+            effects[numEffects] = EFX10.alGenEffects();
+            if (AL10.alGetError() != AL10.AL_NO_ERROR) {
+                break;
+            }
+        }
+        System.out.println("Created " + numEffects + " effects.");
+
+        // Set first Effect Type to Reverb and change Decay Time
+        AL10.alGetError();
+        if (EFX10.alIsEffect(effects[0])) {
+            EFX10.alEffecti(effects[0], EFX10.AL_EFFECT_TYPE, EFX10.AL_EFFECT_REVERB);
+            if (AL10.alGetError() != AL10.AL_NO_ERROR) {
+                System.out.println("Reverb effect not supported.");
+            } else {
+                EFX10.alEffectf(effects[0], EFX10.AL_REVERB_DECAY_TIME, 5.0f);
+                System.out.println("Reverb effect created.");
+            }
+        } else {
+            throw new Exception("First effect not a valid effect.");
+        }
+
+        // Set second Effect Type to Flanger and change Phase
+        AL10.alGetError();
+        if (EFX10.alIsEffect(effects[1])) {
+            EFX10.alEffecti(effects[1], EFX10.AL_EFFECT_TYPE, EFX10.AL_EFFECT_FLANGER);
+            if (AL10.alGetError() != AL10.AL_NO_ERROR) {
+                System.out.println("Flanger effect not support.");
+            } else {
+                EFX10.alEffecti(effects[1], EFX10.AL_FLANGER_PHASE, 180);
+                System.out.println("Flanger effect created.");
+            }
+        } else {
+            throw new Exception("Second effect not a valid effect.");
+        }
+
+        // Try to create a Filter
+        AL10.alGetError();
+        final int filter = EFX10.alGenFilters();
+        if (AL10.alGetError() != AL10.AL_NO_ERROR) {
+            throw new Exception("Failed to create filter.");
+        }
+        System.out.println("Generated a filter.");
+        if (EFX10.alIsFilter(filter)) {
+            // Set Filter type to Low-Pass and set parameters
+            EFX10.alFilteri(filter, EFX10.AL_FILTER_TYPE, EFX10.AL_FILTER_LOWPASS);
+            if (AL10.alGetError() != AL10.AL_NO_ERROR) {
+                System.out.println("Low pass filter not supported.");
+            } else {
+                EFX10.alFilterf(filter, EFX10.AL_LOWPASS_GAIN, 0.5f);
+                EFX10.alFilterf(filter, EFX10.AL_LOWPASS_GAINHF, 0.5f);
+                System.out.println("Low pass filter created.");
+            }
+        }
+
+        // Attach Effect to Auxiliary Effect Slot
+        AL10.alGetError();
+        EFX10.alAuxiliaryEffectSloti(auxEffectSlots[0], EFX10.AL_EFFECTSLOT_EFFECT, effects[0]);
+        if (AL10.alGetError() != AL10.AL_NO_ERROR) {
+            throw new Exception("Failed to attach effect to aux effect slot.");
+        }
+        System.out.println("Successfully loaded effect into effect slot.");
+
+        // Configure Source Auxiliary Effect Slot Sends
+        final int source = AL10.alGenSources();
+        // Set Source Send 0 to feed auxEffectSlots[0] without filtering
+        AL11.alSource3i(source, EFX10.AL_AUXILIARY_SEND_FILTER, auxEffectSlots[0], 0,
+                EFX10.AL_FILTER_NULL);
+        if (AL10.alGetError() != AL10.AL_NO_ERROR) {
+            throw new Exception("Failed to configure Source Send 0");
+        }
+        System.out.println("Linked aux effect slot to soutce slot 0");
+        // Set Source Send 1 to feed uiEffectSlot[1] with filter filter
+        AL11.alSource3i(source, EFX10.AL_AUXILIARY_SEND_FILTER, auxEffectSlots[1], 1, filter);
+        if (AL10.alGetError() != AL10.AL_NO_ERROR) {
+            // e.g. if only 1 send per source is available
+            throw new Exception("Failed to configure Source Send 1");
+        }
+        System.out.println("Linked aux effect slot to soutce slot 1");
+        // Disable Send 0
+        AL11.alSource3i(source, EFX10.AL_AUXILIARY_SEND_FILTER, EFX10.AL_EFFECTSLOT_NULL, 0,
+                EFX10.AL_FILTER_NULL);
+        if (AL10.alGetError() != AL10.AL_NO_ERROR) {
+            throw new Exception("Failed to disable Source Send 0");
+        }
+        System.out.println("Disabled source send 0");
+        // Disable Send 1
+        AL11.alSource3i(source, EFX10.AL_AUXILIARY_SEND_FILTER, EFX10.AL_EFFECTSLOT_NULL, 1,
+                EFX10.AL_FILTER_NULL);
+        if (AL10.alGetError() != AL10.AL_NO_ERROR) {
+            throw new Exception("Failed to disable Source Send 1");
+        }
+        System.out.println("Disabled source send 1");
+
+
+        // Filter 'source', a generated Source
+        AL10.alSourcei(source, EFX10.AL_DIRECT_FILTER, filter);
+        if (AL10.alGetError() == AL10.AL_NO_ERROR) {
+            {
+                System.out.println("Successfully applied a direct path filter");
+                // Remove filter from 'source'
+                AL10.alSourcei(source, EFX10.AL_DIRECT_FILTER, EFX10.AL_FILTER_NULL);
+                if (AL10.alGetError() == AL10.AL_NO_ERROR) {
+                    System.out.println("Successfully removed direct filter");
+                }
+            }
+            // Filter the Source send 0 from 'source' to Auxiliary Effect Slot auxEffectSlot[0]
+            // using Filter uiFilter[0]
+            AL11.alSource3i(source, EFX10.AL_AUXILIARY_SEND_FILTER, auxEffectSlots[0], 0, filter);
+            if (AL10.alGetError() == AL10.AL_NO_ERROR) {
+                {
+                    System.out.println("Successfully applied aux send filter");
+                    // Remove Filter from Source Auxiliary Send
+                    AL11.alSource3i(source, EFX10.AL_AUXILIARY_SEND_FILTER, auxEffectSlots[0], 0,
+                            EFX10.AL_FILTER_NULL);
+                    if (AL10.alGetError() == AL10.AL_NO_ERROR) {
+                        System.out.println("Successfully removed filter");
+                    }
+                }
+            }
+        }
+
+        // Set Source Cone Outer Gain HF value
+        AL10.alSourcef(source, EFX10.AL_CONE_OUTER_GAINHF, 0.5f);
+        if (AL10.alGetError() == AL10.AL_NO_ERROR) {
+            System.out.println("Successfully set cone outside gain filter");
+        }
+
+        // Set distance units to be in feet
+        AL10.alListenerf(EFX10.AL_METERS_PER_UNIT, 0.3f);
+        if (AL10.alGetError() == AL10.AL_NO_ERROR) {
+            System.out.println("Successfully set distance units");
+        }
+
+        // Cleanup
+        final IntBuffer auxEffectSlotsBuf = (IntBuffer) BufferUtils.createIntBuffer(
+                auxEffectSlots.length).put(auxEffectSlots).rewind();
+        EFX10.alDeleteAuxiliaryEffectSlots(auxEffectSlotsBuf);
+        final IntBuffer effectsBuf = (IntBuffer) BufferUtils.createIntBuffer(
+                effects.length).put(effects).rewind();
+        EFX10.alDeleteEffects(effectsBuf);
+        EFX10.alDeleteFilters(filter);
+        AL.destroy();
+    }
+
+    /**
+     * Plays a sound with various effects applied to it.
+     */
+    private static void playbackTest() throws Exception {
+        setupEfx();
+
+        // Create a source and buffer audio data
+        final int source = AL10.alGenSources();
+        final int buffer = AL10.alGenBuffers();
+        WaveData waveFile = WaveData.create(WaveData.class.getClassLoader().getResourceAsStream("Footsteps.wav"));
+        if (waveFile == null) {
+            System.out.println("Failed to load Footsteps.wav! Skipping playback test.");
+            AL.destroy();
+            return;
+        }
+        AL10.alBufferData(buffer, waveFile.format, waveFile.data, waveFile.samplerate);
+        waveFile.dispose();
+        AL10.alSourcei(source, AL10.AL_BUFFER, buffer);
+        AL10.alSourcei(source, AL10.AL_LOOPING, AL10.AL_TRUE);
+
+        System.out.println("Playing sound unaffected by EFX ...");
+        AL10.alSourcePlay(source);
+        Thread.sleep(7500);
+
+        // Add reverb effect
+        final int effectSlot = EFX10.alGenAuxiliaryEffectSlots();
+        final int reverbEffect = EFX10.alGenEffects();
+        EFX10.alEffecti(reverbEffect, EFX10.AL_EFFECT_TYPE, EFX10.AL_EFFECT_REVERB);
+        EFX10.alEffectf(reverbEffect, EFX10.AL_REVERB_DECAY_TIME, 5.0f);
+        EFX10.alAuxiliaryEffectSloti(effectSlot, EFX10.AL_EFFECTSLOT_EFFECT, reverbEffect);
+        AL11.alSource3i(source, EFX10.AL_AUXILIARY_SEND_FILTER, effectSlot, 0,
+                EFX10.AL_FILTER_NULL);
+
+        System.out.println("Playing sound with reverb ...");
+        AL10.alSourcePlay(source);
+        Thread.sleep(7500);
+
+        // Add low-pass filter directly to source
+        final int filter = EFX10.alGenFilters();
+        EFX10.alFilteri(filter, EFX10.AL_FILTER_TYPE, EFX10.AL_FILTER_LOWPASS);
+        EFX10.alFilterf(filter, EFX10.AL_LOWPASS_GAIN, 0.5f);
+        EFX10.alFilterf(filter, EFX10.AL_LOWPASS_GAINHF, 0.5f);
+        AL10.alSourcei(source, EFX10.AL_DIRECT_FILTER, filter);
+
+        System.out.println("Playing sound with reverb and direct low pass filter ...");
+        AL10.alSourcePlay(source);
+        Thread.sleep(7500);
+        AL10.alSourcei(source, EFX10.AL_DIRECT_FILTER, EFX10.AL_FILTER_NULL);
+
+        // Add low-pass filter to source send
+        //AL11.alSource3i(source, EFX10.AL_AUXILIARY_SEND_FILTER, effectSlot, 0, filter);
+        //
+        //System.out.println("Playing sound with reverb and aux send low pass filter ...");
+        //AL10.alSourcePlay(source);
+        //Thread.sleep(7500);
+
+        // Cleanup
+        AL11.alSource3i(source, EFX10.AL_AUXILIARY_SEND_FILTER, EFX10.AL_EFFECTSLOT_NULL, 0,
+                EFX10.AL_FILTER_NULL);
+        EFX10.alAuxiliaryEffectSloti(effectSlot, EFX10.AL_EFFECTSLOT_EFFECT, EFX10.AL_EFFECT_NULL);
+        EFX10.alDeleteEffects(reverbEffect);
+        EFX10.alDeleteFilters(filter);
+
+        // Echo effect
+        final int echoEffect = EFX10.alGenEffects();
+        EFX10.alEffecti(echoEffect, EFX10.AL_EFFECT_TYPE, EFX10.AL_EFFECT_ECHO);
+        //EFX10.alEffectf(echoEffect, EFX10.AL_ECHO_DELAY, 5.0f);
+        EFX10.alAuxiliaryEffectSloti(effectSlot, EFX10.AL_EFFECTSLOT_EFFECT, echoEffect);
+        AL11.alSource3i(source, EFX10.AL_AUXILIARY_SEND_FILTER, effectSlot, 0,
+                EFX10.AL_FILTER_NULL);
+
+        System.out.println("Playing sound with echo effect ...");
+        AL10.alSourcePlay(source);
+        Thread.sleep(7500);
+
+        AL.destroy();
+    }
+
+    /**
+     * Checks OpenAL for every EFX 1.0 effect and filter and prints the result to the console.
+     */
+    private static void efxUtilTest() throws Exception {
+        setupEfx();
+
+        System.out.println();
+        System.out.println("Checking supported effects ...");
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_NULL)) {
+            System.out.println("AL_EFFECT_NULL is supported.");
+        } else {
+            System.out.println("AL_EFFECT_NULL is NOT supported.");
+        }
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_EAXREVERB)) {
+            System.out.println("AL_EFFECT_EAXREVERB is supported.");
+        } else {
+            System.out.println("AL_EFFECT_EAXREVERB is NOT supported.");
+        }
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_REVERB)) {
+            System.out.println("AL_EFFECT_REVERB is supported.");
+        } else {
+            System.out.println("AL_EFFECT_REVERB is NOT supported.");
+        }
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_CHORUS)) {
+            System.out.println("AL_EFFECT_CHORUS is supported.");
+        } else {
+            System.out.println("AL_EFFECT_CHORUS is NOT supported.");
+        }
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_DISTORTION)) {
+            System.out.println("AL_EFFECT_DISTORTION is supported.");
+        } else {
+            System.out.println("AL_EFFECT_DISTORTION is NOT supported.");
+        }
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_ECHO)) {
+            System.out.println("AL_EFFECT_ECHO is supported.");
+        } else {
+            System.out.println("AL_EFFECT_ECHO is NOT supported.");
+        }
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_FLANGER)) {
+            System.out.println("AL_EFFECT_FLANGER is supported.");
+        } else {
+            System.out.println("AL_EFFECT_FLANGER is NOT supported.");
+        }
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_FREQUENCY_SHIFTER)) {
+            System.out.println("AL_EFFECT_FREQUENCY_SHIFTER is supported.");
+        } else {
+            System.out.println("AL_EFFECT_FREQUENCY_SHIFTER is NOT supported.");
+        }
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_VOCAL_MORPHER)) {
+            System.out.println("AL_EFFECT_VOCAL_MORPHER is supported.");
+        } else {
+            System.out.println("AL_EFFECT_VOCAL_MORPHER is NOT supported.");
+        }
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_PITCH_SHIFTER)) {
+            System.out.println("AL_EFFECT_PITCH_SHIFTER is supported.");
+        } else {
+            System.out.println("AL_EFFECT_PITCH_SHIFTER is NOT supported.");
+        }
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_RING_MODULATOR)) {
+            System.out.println("AL_EFFECT_RING_MODULATOR is supported.");
+        } else {
+            System.out.println("AL_EFFECT_RING_MODULATOR is NOT supported.");
+        }
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_AUTOWAH)) {
+            System.out.println("AL_EFFECT_AUTOWAH is supported.");
+        } else {
+            System.out.println("AL_EFFECT_AUTOWAH is NOT supported.");
+        }
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_COMPRESSOR)) {
+            System.out.println("AL_EFFECT_COMPRESSOR is supported.");
+        } else {
+            System.out.println("AL_EFFECT_COMPRESSOR is NOT supported.");
+        }
+        if (EFXUtil.isEffectSupported(EFX10.AL_EFFECT_EQUALIZER)) {
+            System.out.println("AL_EFFECT_EQUALIZER is supported.");
+        } else {
+            System.out.println("AL_EFFECT_EQUALIZER is NOT supported.");
+        }
+
+        System.out.println();
+        System.out.println("Checking supported filters ...");
+        if (EFXUtil.isFilterSupported(EFX10.AL_FILTER_NULL)) {
+            System.out.println("AL_FILTER_NULL is supported.");
+        } else {
+            System.out.println("AL_FILTER_NULL is NOT supported.");
+        }
+        if (EFXUtil.isFilterSupported(EFX10.AL_FILTER_LOWPASS)) {
+            System.out.println("AL_FILTER_LOWPASS is supported.");
+        } else {
+            System.out.println("AL_FILTER_LOWPASS is NOT supported.");
+        }
+        if (EFXUtil.isFilterSupported(EFX10.AL_FILTER_HIGHPASS)) {
+            System.out.println("AL_FILTER_HIGHPASS is supported.");
+        } else {
+            System.out.println("AL_FILTER_HIGHPASS is NOT supported.");
+        }
+        if (EFXUtil.isFilterSupported(EFX10.AL_FILTER_BANDPASS)) {
+            System.out.println("AL_FILTER_BANDPASS is supported.");
+        } else {
+            System.out.println("AL_FILTER_BANDPASS is NOT supported.");
+        }
+    }
+}
diff --git a/src/java/org/lwjgl/test/openal/OpenALInfo.java b/src/java/org/lwjgl/test/openal/OpenALInfo.java
index 20c919a..9a2ec72 100644
--- a/src/java/org/lwjgl/test/openal/OpenALInfo.java
+++ b/src/java/org/lwjgl/test/openal/OpenALInfo.java
@@ -32,6 +32,11 @@
 package org.lwjgl.test.openal;
 
 import java.nio.IntBuffer;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.Set;
+import java.util.Map.Entry;
 
 import org.lwjgl.BufferUtils;
 import org.lwjgl.LWJGLException;
@@ -40,6 +45,8 @@ import org.lwjgl.openal.AL10;
 import org.lwjgl.openal.ALC10;
 import org.lwjgl.openal.ALC11;
 import org.lwjgl.openal.ALCdevice;
+import org.lwjgl.openal.EFX10;
+import org.lwjgl.openal.EFXUtil;
 
 /**
  *
@@ -70,6 +77,7 @@ public class OpenALInfo {
 		
 		printALCInfo();
 		printALInfo();
+		printEFXInfo();
 		
 		checkForErrors();
 		
@@ -94,7 +102,7 @@ public class OpenALInfo {
 		device = ALC10.alcGetContextsDevice(ALC10.alcGetCurrentContext());
 		checkForErrors();
 		
-	    System.out.println("Default device: " + ALC10.alcGetString(device, ALC10.ALC_DEFAULT_DEVICE_SPECIFIER));
+	    System.out.println("Default playback device: " + ALC10.alcGetString(device, ALC10.ALC_DEFAULT_DEVICE_SPECIFIER));
 
 	    System.out.println("Default capture device: " + ALC10.alcGetString(device, ALC11.ALC_CAPTURE_DEFAULT_DEVICE_SPECIFIER));
 
@@ -130,6 +138,70 @@ public class OpenALInfo {
 	    checkForErrors();		
 	}
 	
+	private void printEFXInfo() {
+		if(!EFXUtil.isEfxSupported()) {
+			System.out.println("EFX not available");
+			return;
+		}
+		
+		ALCdevice device = AL.getDevice();		
+        IntBuffer major = BufferUtils.createIntBuffer(1);
+        IntBuffer minor = BufferUtils.createIntBuffer(1);
+        IntBuffer sends = BufferUtils.createIntBuffer(1);
+        ALC10.alcGetInteger(device, EFX10.ALC_EFX_MAJOR_VERSION, major);
+        ALC10.alcGetInteger(device, EFX10.ALC_EFX_MINOR_VERSION, minor);
+        if(ALC10.alcGetError(device) == ALC10.ALC_NO_ERROR) {
+        	System.out.println("EFX version: " + major.get() + "." + minor.get());
+        }
+        
+        ALC10.alcGetInteger(device, EFX10.ALC_MAX_AUXILIARY_SENDS, sends);
+        if(ALC10.alcGetError(device) == ALC10.ALC_NO_ERROR) {
+        	System.out.println("Max auxiliary sends: " + sends.get());
+        }
+        
+        System.out.println("Supported filters: ");
+        HashMap filters = new HashMap();
+        filters.put("Low-pass", 		new Integer(EFX10.AL_FILTER_LOWPASS));
+        filters.put("High-pass", 		new Integer(EFX10.AL_FILTER_HIGHPASS));
+        filters.put("Band-pass", 		new Integer(EFX10.AL_FILTER_BANDPASS));
+
+        Set entries = filters.entrySet();
+        for(Iterator i = entries.iterator(); i.hasNext();) {
+        	Map.Entry entry = (Entry) i.next();
+        	int value = ((Integer)entry.getValue()).intValue();
+        	String key = (String) entry.getKey();
+        	if(EFXUtil.isFilterSupported(value)) {
+        		System.out.println("    " + key);
+        	}
+        }
+        
+        System.out.println("Supported effects: ");
+        HashMap effects = new HashMap();
+        effects.put("EAX Reverb", 			new Integer(EFX10.AL_EFFECT_EAXREVERB));
+        effects.put("Reverb", 				new Integer(EFX10.AL_EFFECT_REVERB));
+        effects.put("Chorus", 				new Integer(EFX10.AL_EFFECT_CHORUS));
+        effects.put("Distortion", 			new Integer(EFX10.AL_EFFECT_DISTORTION));
+        effects.put("Echo", 				new Integer(EFX10.AL_EFFECT_ECHO));
+        effects.put("Flanger", 				new Integer(EFX10.AL_EFFECT_FLANGER));
+        effects.put("Frequency Shifter", 	new Integer(EFX10.AL_EFFECT_FREQUENCY_SHIFTER));
+        effects.put("Vocal Morpher", 		new Integer(EFX10.AL_EFFECT_VOCAL_MORPHER));
+        effects.put("Pitch Shifter", 		new Integer(EFX10.AL_EFFECT_PITCH_SHIFTER));
+        effects.put("Ring Modulator", 		new Integer(EFX10.AL_EFFECT_RING_MODULATOR));
+        effects.put("Autowah", 				new Integer(EFX10.AL_EFFECT_AUTOWAH));
+        effects.put("Compressor", 			new Integer(EFX10.AL_EFFECT_COMPRESSOR));
+        effects.put("Equalizer", 			new Integer(EFX10.AL_EFFECT_EQUALIZER));
+
+        entries = effects.entrySet();
+        for(Iterator i = entries.iterator(); i.hasNext();) {
+        	Map.Entry entry = (Entry) i.next();
+        	int value = ((Integer)entry.getValue()).intValue();
+        	String key = (String) entry.getKey();
+        	if(EFXUtil.isEffectSupported(value)) {
+        		System.out.println("    " + key);
+        	}
+        }
+	}
+	
 	private void printDevices(int which, String kind) {
 		String[] devices = ALC10.alcGetString(null, which).split("\0");
 		checkForErrors();
diff --git a/src/java/org/lwjgl/test/opengl/FullScreenWindowedTest.java b/src/java/org/lwjgl/test/opengl/FullScreenWindowedTest.java
index d05ef3e..22892f0 100644
--- a/src/java/org/lwjgl/test/opengl/FullScreenWindowedTest.java
+++ b/src/java/org/lwjgl/test/opengl/FullScreenWindowedTest.java
@@ -33,6 +33,7 @@ package org.lwjgl.test.opengl;
 
 import org.lwjgl.LWJGLException;
 import org.lwjgl.input.Keyboard;
+import org.lwjgl.input.Mouse;
 import org.lwjgl.opengl.Display;
 import org.lwjgl.opengl.DisplayMode;
 import org.lwjgl.opengl.GL11;
@@ -44,8 +45,8 @@ import org.lwjgl.util.vector.Vector2f;
  * Tests switching between windowed and fullscreen
  * 
  * @author Brian Matzon <brian at matzon.dk>
- * @version $Revision: 3172 $
- * $Id: FullScreenWindowedTest.java 3172 2008-12-28 19:30:43Z elias_naur $
+ * @version $Revision: 3365 $
+ * $Id: FullScreenWindowedTest.java 3365 2010-07-04 18:24:53Z spasi $
  */
 public class FullScreenWindowedTest {
 	/** Intended deiplay mode */
@@ -222,6 +223,8 @@ public class FullScreenWindowedTest {
 		if (angleRotation > MAX_SPEED) {
 			angleRotation = MAX_SPEED;
 		}
+
+		while ( Mouse.next() );
 	}
 	/**
 	 * Cleans up the test
diff --git a/src/java/org/lwjgl/test/opengl/VBOIndexTest.java b/src/java/org/lwjgl/test/opengl/VBOIndexTest.java
index c563730..841e832 100644
--- a/src/java/org/lwjgl/test/opengl/VBOIndexTest.java
+++ b/src/java/org/lwjgl/test/opengl/VBOIndexTest.java
@@ -31,12 +31,12 @@
  */
 
 /**
- * $Id: VBOIndexTest.java 2983 2008-04-07 18:36:09Z matzon $
+ * $Id: VBOIndexTest.java 3344 2010-05-22 16:53:49Z spasi $
  *
  * Simple java test program.
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 2983 $
+ * @version $Revision: 3344 $
  */
 
 package org.lwjgl.test.opengl;
@@ -179,6 +179,7 @@ public final class VBOIndexTest {
 		                                                   mapped_indices_buffer);
 		if ( new_mapped_buffer != mapped_indices_buffer )
 			mapped_indices_int_buffer = new_mapped_buffer.order(ByteOrder.nativeOrder()).asIntBuffer();
+		mapped_indices_buffer = new_mapped_buffer;
 
 		mapped_float_buffer.rewind();
 		vertices.rewind();
diff --git a/src/java/org/lwjgl/test/opengl/VersionTest.java b/src/java/org/lwjgl/test/opengl/VersionTest.java
index b5172bc..6f4855c 100644
--- a/src/java/org/lwjgl/test/opengl/VersionTest.java
+++ b/src/java/org/lwjgl/test/opengl/VersionTest.java
@@ -29,13 +29,6 @@
  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
-/*
- * Created by LWJGL.
- * User: spasi
- * Date: 2009-04-04
- * Time: 21:20:24 pm
- */
-
 package org.lwjgl.test.opengl;
 
 import org.lwjgl.LWJGLException;
@@ -44,6 +37,11 @@ import org.lwjgl.opengl.*;
 import java.util.StringTokenizer;
 import java.util.regex.Pattern;
 
+/**
+ * Tests the ARB_create_context extension through the use of the ContextAttribs class.
+ *
+ * @author Spasi
+ */
 public final class VersionTest {
 
 	private VersionTest() {
@@ -110,46 +108,105 @@ public final class VersionTest {
 
 		System.out.println("\n---------\n");
 
+		System.out.println("Requested " + ca);
+
 		final String version = GL11.glGetString(GL11.GL_VERSION);
 
-		System.out.print("GL Version requested: " + majorInput + '.' + minorInput);
-		if ( ca.isProfileCore() )
-			System.out.print(" - Core Profile");
-		else if ( ca.isProfileCompatibility() )
-			System.out.print(" - Compatibility Profile");
-		System.out.println("\nGL Version returned : " + version);
+		boolean deprecated = false;
+		try {
+			GL11.glVertex3f(0.0f, 0.0f, 0.0f);
+			deprecated = true;
+		} catch (Throwable t) {}
 
 		final StringTokenizer version_tokenizer = new StringTokenizer(version, ". ");
 
 		int majorVersion = Integer.parseInt(version_tokenizer.nextToken());
 		int minorVersion = Integer.parseInt(version_tokenizer.nextToken());
 
-		if ( majorVersion != majorInput || minorVersion != minorInput ) {
-			if ( majorInput == 1 && minorInput == 0 )
-				System.out.println("\tThe maximum supported version has been returned. The driver is well-behaved. :)");
-			else if ( majorInput < 3 && majorVersion < 3 )
-				System.out.println("\tThe maximum supported version pre-3.0 has been returned. The driver is well-behaved. :)");
-			else
-				System.out.println("\tThe requested version was not returned. The driver is buggy! :(");
-		} else
-			System.out.println("\tThe requested version was returned. :)");
+		final boolean compatibilityProfile;
+		final boolean coreProfile;
 
-		if ( ca.isProfileCompatibility() && !GLContext.getCapabilities().GL_ARB_compatibility )
-			System.out.println("\tThe driver does not support the Compatibility Profile.");
+		if ( 3 < majorVersion || (majorVersion == 3 && 2 <= minorVersion) ) {
+			final int profileMask = GL11.glGetInteger(GL32.GL_CONTEXT_PROFILE_MASK);
 
-		System.out.println("\n---------\n");
+			compatibilityProfile = (profileMask & GL32.GL_CONTEXT_COMPATIBILITY_PROFILE_BIT) != 0;
+			coreProfile = (profileMask & GL32.GL_CONTEXT_CORE_PROFILE_BIT) != 0;
+		} else {
+			compatibilityProfile = false;
+			coreProfile = false;
+		}
 
-		System.out.println("Debug mode: " + ca.isDebug());
-		System.out.println("Forward compatible mode: " + ca.isForwardCompatible());
-		System.out.println("ARB_compatibility: " + GLContext.getCapabilities().GL_ARB_compatibility);
-		try {
-			GL11.glVertex3f(0.0f, 0.0f, 0.0f);
-			System.out.println("Deprecated functionality present: " + true);
-		} catch (Throwable t) {
-			System.out.println("Deprecated functionality present: " + false);
-			if ( GLContext.getCapabilities().GL_ARB_compatibility ) {
-				System.out.println("\tARB_compatibility is present, but LWJGL has enabled pseudo-forward compatible mode.");
-			}
+		System.out.println("\nGL_VERSION returned : " + version);
+		System.out.println("\tCore profile: " + coreProfile);
+		System.out.println("\tCompatibility profile: " + compatibilityProfile);
+		System.out.println("ARB_compatibility present: " + GLContext.getCapabilities().GL_ARB_compatibility);
+		System.out.println("Deprecated functionality present: " + deprecated);
+		if ( !deprecated && GLContext.getCapabilities().GL_ARB_compatibility )
+			System.out.println("\tARB_compatibility is present, but LWJGL has enabled pseudo-forward compatible mode.");
+
+		System.out.println("\n---------");
+
+		boolean success = false;
+		boolean check;
+		if ( majorInput < 3 || (majorInput == 3 && minorInput == 0) ) {
+			System.out.println("\nA version less than or equal to 3.0 is requested, the context\n" +
+			                   "returned may implement any of the following versions:");
+
+			System.out.println("\n1) Any version no less than that requested and no greater than 3.0.");
+			check = (majorInput < majorVersion || (majorInput == majorVersion && minorInput <= minorVersion)) // Satisfies requested version
+			        && (majorVersion < 3 || (majorVersion == 3 && minorVersion == 0)); // 3.0 or earlier
+			System.out.println("\t" + check);
+			success |= check;
+
+			System.out.println("\n2) Version 3.1, if the GL_ARB_compatibility extension is also implemented.");
+			check = majorVersion == 3 && minorVersion == 1 && GLContext.getCapabilities().GL_ARB_compatibility;
+			System.out.println("\t" + check);
+			success |= check;
+
+			System.out.println("\n3) The compatibility profile of version 3.2 or greater.");
+			check = compatibilityProfile; // No need to check version, profiles are only available with 3.2+.
+			System.out.println("\t" + check);
+			success |= check;
+
+			System.out.println("\nTEST " + (success ? "SUCCEEDED" : "FAILED"));
+			if ( !success && ca.isForwardCompatible() )
+				System.out.println("\t(probably because the forward compatible flag was set)");
+		} else if ( majorInput == 3 && minorInput == 1 ) {
+			System.out.println("\nVersion 3.1 is requested, the context returned may implement\n" +
+			                   "any of the following versions:");
+
+			System.out.println("\n1) Version 3.1. The GL_ARB_compatibility extension may or may not\n" +
+			                   "be implemented, as determined by the implementation.");
+			check = majorVersion == 3 && minorVersion == 1;
+			System.out.println("\t" + check);
+			success |= check;
+
+			System.out.println("\n2) The core profile of version 3.2 or greater.");
+			check = coreProfile; // No need to check version, profiles are only available with 3.2+.
+			System.out.println("\t" + check);
+			success |= check;
+
+			System.out.println("\nTEST " + (success ? "SUCCEEDED" : "FAILED"));
+		} else {
+			System.out.println("\nVersion 3.2 or greater is requested, the context returned may\n" +
+			                   "implement any of the following versions:");
+
+			System.out.println("\n1) The requested profile of the requested version.");
+			check = majorInput == majorVersion && minorInput == minorVersion
+			        && (!ca.isProfileCompatibility() || compatibilityProfile)
+			        && (!ca.isProfileCore() || coreProfile);
+			System.out.println("\t" + check);
+			success |= check;
+
+			System.out.println("\n2) The requested profile of any later version, so long as no\n" +
+			                   "features have been removed from that later version and profile.");
+			check = majorInput < majorVersion || (majorInput == majorVersion && minorInput < minorVersion)
+			                                     && (!ca.isProfileCompatibility() || compatibilityProfile)
+			                                     && (!ca.isProfileCore() || coreProfile);
+			System.out.println("\t" + check);
+			success |= check;
+
+			System.out.println("\nTEST " + (success ? "SUCCEEDED" : "FAILED"));
 		}
 	}
 
@@ -174,12 +231,14 @@ public final class VersionTest {
 
 	private static void argsError(final String msg) {
 		System.out.println("\nInvalid arguments error: " + msg);
-		System.out.println("\nUsage: VersionTest <majorVersion> <minorVersion> {<layer>, 'debug', 'fc'}:\n");
+		System.out.println("\nUsage: VersionTest <majorVersion> <minorVersion> {'core'|'compatibility', <layer>, 'debug', 'fc'}:\n");
 		System.out.println("majorVersion\t- Major OpenGL version.");
 		System.out.println("majorVersion\t- Minor OpenGL version.");
+		System.out.println("core\t- Sets the Core Profile bit (optional, requires 3.2+).");
+		System.out.println("compatibility\t- Sets the Compatibility Profile bit (optional, requires 3.2+).");
 		System.out.println("layer\t- Layer plane (optional).");
 		System.out.println("debug\t- Enables debug mode (optional).");
-		System.out.println("fc\t- Enables forward compatibility mode (optional).");
+		System.out.println("fc\t- Enables forward compatibility mode (optional, requires 3.0+).");
 
 		cleanup();
 		System.exit(-1);
@@ -193,4 +252,4 @@ public final class VersionTest {
 		System.exit(-1);
 	}
 
-}
\ No newline at end of file
+}
diff --git a/src/java/org/lwjgl/test/opengl/awt/DemoBox.java b/src/java/org/lwjgl/test/opengl/awt/DemoBox.java
index b0250ac..9604b4b 100644
--- a/src/java/org/lwjgl/test/opengl/awt/DemoBox.java
+++ b/src/java/org/lwjgl/test/opengl/awt/DemoBox.java
@@ -150,7 +150,7 @@ public class DemoBox extends Frame {
 		addWindowListener(new WindowAdapter() {
 
 			public void windowClosing(WindowEvent e) {
-				demoCanvas.destroy();
+				demoCanvas.destroyCanvas();
 				dispose();
 				System.exit(0);
 			}
@@ -269,7 +269,7 @@ public class DemoBox extends Frame {
 			}
 		}
 
-		public void destroy() {
+		public void destroyCanvas() {
 			setActiveDemo(null);
 			renderThread = null;
 		}
diff --git a/src/java/org/lwjgl/test/opengl/shaders/ShadersTest.java b/src/java/org/lwjgl/test/opengl/multithread/BackgroundLoadTest.java
similarity index 53%
copy from src/java/org/lwjgl/test/opengl/shaders/ShadersTest.java
copy to src/java/org/lwjgl/test/opengl/multithread/BackgroundLoadTest.java
index e7a977e..c068b60 100644
--- a/src/java/org/lwjgl/test/opengl/shaders/ShadersTest.java
+++ b/src/java/org/lwjgl/test/opengl/multithread/BackgroundLoadTest.java
@@ -29,77 +29,67 @@
  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
-/*
- * Created by LWJGL.
- * User: spasi
- * Date: 2004-03-30
- * Time: 8:41:42 pm
- */
-
-package org.lwjgl.test.opengl.shaders;
-
-import java.nio.FloatBuffer;
+package org.lwjgl.test.opengl.multithread;
 
 import org.lwjgl.BufferUtils;
 import org.lwjgl.LWJGLException;
-import org.lwjgl.Sys;
 import org.lwjgl.input.Keyboard;
 import org.lwjgl.input.Mouse;
 import org.lwjgl.opengl.*;
 import org.lwjgl.util.glu.GLU;
 import org.lwjgl.util.glu.Sphere;
 
-public final class ShadersTest {
+import java.nio.FloatBuffer;
 
-	private static DisplayMode displayMode;
+/**
+ * A test of loading textures in a background thread. This can be achieved in 2 ways:
+ * <br>
+ * a) A dummy Pbuffer is created and its context shares the rendering context.<br>
+ * b) A SharedDrawable is used.<br>
+ * <br>
+ * When the test starts, there's no texture created and rendering is done with texturing disabled.
+ * 2 seconds later a "dummy" texture is created in the background thread and texturing is enabled. This dummy texture
+ * can by anything the developer wants to have as a placeholder while textures are being loaded.
+ * Finally, 5 seconds later the "true" texture is loaded and displayed. This texture will change every 5 seconds after
+ * that, until the test is terminated (ESC key).
+ *
+ * @author Spasi
+ */
+public final class BackgroundLoadTest {
 
 	private static boolean run = true;
 
-	private static final FloatBuffer vectorBuffer = BufferUtils.createFloatBuffer(4);
+	private static BackgroundLoader backgroundLoader;
 
 	private static Sphere sphere;
 
-	private static Shader shader;
-
-	private static float frameTime;
-
-	private static float angle;
-	private static float sin;
-	private static int specularity = 4;
-
-	private ShadersTest() {
+	private BackgroundLoadTest() {
 	}
 
 	public static void main(String[] args) {
 		initialize(args);
 
-		long frameStart;
-		long lastFrameTime = 0;
+		Util.checkGLError();
+
+		try {
+			backgroundLoader.start();
+		} catch (LWJGLException e) {
+			kill("Failed to start background thread.", e);
+		}
+
+		Util.checkGLError();
 
 		while ( run ) {
-			if (!Display.isVisible() )
+			if ( !Display.isVisible() )
 				Thread.yield();
 			else {
-				// This is the current frame time.
-				frameStart = Sys.getTime();
-
-				// How many seconds passed since last frame.
-				frameTime = (float)((frameStart - lastFrameTime) / (double)Sys.getTimerResolution());
-
-				lastFrameTime = frameStart;
-
-				//angle += frameTime * 90.0f;
-				angle += 0.1f;
-				sin = (float)Math.sin(Math.toRadians(angle));
-
 				handleIO();
 
 				GL11.glClear(GL11.GL_COLOR_BUFFER_BIT | GL11.GL_DEPTH_BUFFER_BIT);
 
-				if ( shader != null )
-					shader.render();
-				else
-					renderObject();
+				renderObject();
+
+				Util.checkGLError();
 
 				// Restore camera position.
 				GL11.glPopMatrix();
@@ -120,11 +110,11 @@ public final class ShadersTest {
 		if ( args.length != 1 )
 			argsError();
 
+		DisplayMode displayMode = null;
+
 		try {
 			DisplayMode[] modes = Display.getAvailableDisplayModes();
 
-			DisplayMode displayMode;
-
 			displayMode = chooseMode(modes, 1024, 768);
 			if ( displayMode == null )
 				displayMode = chooseMode(modes, 800, 600);
@@ -135,49 +125,12 @@ public final class ShadersTest {
 
 			System.out.println("Setting display mode to: " + displayMode);
 			Display.setDisplayMode(displayMode);
-			Display.create(new PixelFormat(8, 24, 0), "UNI".equalsIgnoreCase(args[0]) ? new ContextAttribs(3, 1) : null);
-			ShadersTest.displayMode = displayMode;
+			Display.setTitle("Background Loading Test");
+			Display.create(new PixelFormat(8, 24, 0));
 		} catch (LWJGLException e) {
 			kill(e.getMessage());
 		}
 
-		final ContextCapabilities caps = GLContext.getCapabilities();
-
-		if ( "NONE".equalsIgnoreCase(args[0]) ) {
-			shader = null;
-		} else if ( "VP".equalsIgnoreCase(args[0]) ) {
-			if ( !caps.GL_ARB_vertex_program )
-				kill("The ARB_vertex_program extension is not supported.");
-
-			shader = new ShaderVP("shaderVP.vp");
-		} else if ( "FP".equalsIgnoreCase(args[0]) ) {
-			if ( !caps.GL_ARB_vertex_program )
-				kill("The ARB_vertex_program extension is not supported.");
-			if ( !caps.GL_ARB_fragment_program )
-				kill("The ARB_fragment_program extension is not supported.");
-
-			shader = new ShaderFP("shaderFP.vp", "shaderFP.fp");
-		} else if ( "VSH".equalsIgnoreCase(args[0]) ) {
-			if ( !caps.GL_ARB_vertex_shader )
-				kill("The ARB_vertex_shader extension is not supported.");
-
-			shader = new ShaderVSH("shaderVSH.vsh");
-		} else if ( "FSH".equalsIgnoreCase(args[0]) ) {
-			if ( !caps.GL_ARB_vertex_shader )
-				kill("The ARB_vertex_shader extension is not supported.");
-			if ( !caps.GL_ARB_fragment_shader )
-				kill("The ARB_fragment_shader extension is not supported.");
-
-			shader = new ShaderFSH("shaderFSH.vsh", "shaderFSH.fsh");
-		} else if ("UNI".equalsIgnoreCase(args[0]) ) {
-			if ( !(caps.OpenGL31 || caps.GL_ARB_uniform_buffer_object) )
-				kill("Neither OpenGL version 3.1 nor ARB_uniform_buffer_object are supported.");
-
-			shader = new ShaderUNI("shaderUNI.vsh");
-		} else {
-			argsError();
-		}
-
 		GL11.glViewport(0, 0, displayMode.getWidth(), displayMode.getHeight());
 
 		GL11.glMatrixMode(GL11.GL_PROJECTION);
@@ -189,7 +142,7 @@ public final class ShadersTest {
 
 		// Setup camera position.
 		GL11.glTranslatef(0.0f, 0.0f, -4.0f);
-		GL11.glRotatef(15.0f, 1.0f, 0.0f, 0.0f);
+		GL11.glRotatef(90.0f, 1.0f, 0.0f, 0.0f);
 		GL11.glPushMatrix();
 
 		GL11.glClearDepth(1.0f);
@@ -203,42 +156,52 @@ public final class ShadersTest {
 		GL11.glCullFace(GL11.GL_BACK);
 		GL11.glEnable(GL11.GL_CULL_FACE);
 
-		GL11.glAlphaFunc(GL11.GL_NOTEQUAL, 0.0f);
+		GL11.glAlphaFunc(GL11.GL_GREATER, 0.0f);
 		GL11.glEnable(GL11.GL_ALPHA_TEST);
 
 		GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-		GL11.glEnable(GL11.GL_BLEND);
+		GL11.glDisable(GL11.GL_BLEND);
 
-		// Setup lighting for when we have fixed function fragment rendering.
 		GL11.glShadeModel(GL11.GL_SMOOTH);
 
-		if ( shader == null ) {
-			GL11.glEnable(GL11.GL_LIGHTING);
-			GL11.glEnable(GL11.GL_LIGHT0);
-		}
+		final FloatBuffer vectorBuffer = BufferUtils.createFloatBuffer(4);
 
 		vectorBuffer.clear();
-		vectorBuffer.put(1.0f).put(1.0f).put(1.0f).put(1.0f);
-		vectorBuffer.clear();
+		vectorBuffer.put(0, 1.0f).put(1, 1.0f).put(2, 1.0f).put(3, 1.0f);
 		GL11.glLight(GL11.GL_LIGHT0, GL11.GL_DIFFUSE, vectorBuffer);
 
-		vectorBuffer.put(1.0f).put(1.0f).put(1.0f).put(1.0f);
-		vectorBuffer.clear();
+		vectorBuffer.put(0, 1.0f).put(1, 1.0f).put(2, 1.0f).put(3, 1.0f);
 		GL11.glLight(GL11.GL_LIGHT0, GL11.GL_AMBIENT, vectorBuffer);
 
-		vectorBuffer.put(1.0f).put(1.0f).put(0.5f).put(1.0f);
-		vectorBuffer.clear();
+		vectorBuffer.put(0, 1.0f).put(1, 1.0f).put(2, 0.5f).put(3, 1.0f);
 		GL11.glLight(GL11.GL_LIGHT0, GL11.GL_SPECULAR, vectorBuffer);
 
-		vectorBuffer.put(-1.0f / 3.0f).put(1.0f / 3.0f).put(1.0f / 3.0f).put(0.0f); // Infinite
-		vectorBuffer.clear();
+		vectorBuffer.put(0, -1.0f / 3.0f).put(1, 1.0f / 3.0f).put(2, 1.0f / 3.0f).put(3, 0.0f); // Infinite
 		GL11.glLight(GL11.GL_LIGHT0, GL11.GL_POSITION, vectorBuffer);
 
-		vectorBuffer.put(0.2f).put(0.2f).put(0.2f).put(1.0f);
-		vectorBuffer.clear();
+		vectorBuffer.put(0, 0.2f).put(1, 0.2f).put(2, 0.2f).put(3, 1.0f);
 		GL11.glLightModel(GL11.GL_LIGHT_MODEL_AMBIENT, vectorBuffer);
 
+		GL11.glEnable(GL11.GL_LIGHT0);
+		GL11.glEnable(GL11.GL_LIGHTING);
+
 		sphere = new Sphere();
+
+		if ( "PB".equalsIgnoreCase(args[0]) ) {
+			backgroundLoader = new BackgroundLoader() {
+				Drawable getDrawable() throws LWJGLException {
+					return new Pbuffer(2, 2, new PixelFormat(8, 24, 0), Display.getDrawable());
+				}
+			};
+		} else if ( "SD".equalsIgnoreCase(args[0]) ) {
+			backgroundLoader = new BackgroundLoader() {
+				Drawable getDrawable() throws LWJGLException {
+					return new SharedDrawable(Display.getDrawable());
+				}
+			};
+		} else {
+			argsError();
+		}
 	}
 
 	private static void handleIO() {
@@ -248,14 +211,6 @@ public final class ShadersTest {
 					continue;
 
 				switch ( Keyboard.getEventKey() ) {
-					case Keyboard.KEY_EQUALS:
-						if ( specularity < 8 )
-							specularity++;
-						break;
-					case Keyboard.KEY_MINUS:
-						if ( specularity > 1 )
-							specularity--;
-						break;
 					case Keyboard.KEY_ESCAPE:
 						run = false;
 						break;
@@ -266,25 +221,25 @@ public final class ShadersTest {
 		while ( Mouse.next() ) ;
 	}
 
-	static int getDisplayWidth() {
-		return displayMode.getWidth();
-	}
-
-	static int getDisplayHeight() {
-		return displayMode.getHeight();
-	}
-
-	static float getSin() {
-		return sin;
-	}
+	static void renderObject() {
+		GL11.glColor3f(1.0f, 1.0f, 1.0f);
 
-	static int getSpecularity() {
-		return specularity;
-	}
+		int texID = backgroundLoader.getTexID();
+		if ( texID == 0 ) {
+			sphere.setTextureFlag(false);
+			GL11.glDisable(GL11.GL_TEXTURE_2D);
+		} else {
+			sphere.setTextureFlag(true);
+			GL11.glEnable(GL11.GL_TEXTURE_2D);
+			GL11.glBindTexture(GL11.GL_TEXTURE_2D, texID);
+		}
 
-	static void renderObject() {
-		GL11.glColor3b((byte)255, (byte)255, (byte)255);
 		sphere.draw(1.0f, 32, 32);
+
+		if ( texID != 0 ) { // Unbind so we can update from the background thread.
+			GL11.glBindTexture(GL11.GL_TEXTURE_2D, 0);
+			GL11.glDisable(GL11.GL_TEXTURE_2D);
+		}
 	}
 
 	private static DisplayMode chooseMode(DisplayMode[] modes, int width, int height) {
@@ -302,9 +257,9 @@ public final class ShadersTest {
 	}
 
 	private static void cleanup() {
-		// This is not necessary, just showing how to properly delete a program/shader.
-		if ( shader != null )
-			shader.cleanup();
+		backgroundLoader.cleanup();
+
+		Thread.yield(); // Let background thread finish.
 
 		if ( Display.isCreated() )
 			Display.destroy();
@@ -312,20 +267,16 @@ public final class ShadersTest {
 
 	private static void argsError() {
 		System.out.println("\nInvalid program arguments.");
-		System.out.println("\nUsage: ShadersTest <shaderType>, where <shaderType> argument can be one of the following:\n");
-		System.out.println("none\t- Use fixed function rendering.");
-		System.out.println("vp\t- Use ARB_vertex_program (low-level) only.");
-		System.out.println("vsh\t- Use ARB_vertex_shader (GLSL) only.");
-		System.out.println("fp\t- Use ARB_vertex_program + ARB_fragment_program (low-level).");
-		System.out.println("fsh\t- Use ARB_vertex_shader + ARB_fragment_shader (GLSL).");
-		System.out.println("uni\t- Use ARB_uniform_buffer_object to update shader uniforms (GLSL).");
+		System.out.println("\nUsage: BackgroundLoadTest <testType>, where <testType> argument can be one of the following:\n");
+		System.out.println("PB\t- Use a Pbuffer context for the background thread.");
+		System.out.println("SD\t- Use a SharedDrawable context for the background thread.");
 
 		cleanup();
 		System.exit(-1);
 	}
 
 	static void kill(String reason) {
-		System.out.println("The ShaderTest program was terminated because an error occured.\n");
+		System.out.println("The BackgroundLoadTest program was terminated because an error occured.\n");
 		System.out.println("Reason: " + (reason == null ? "Unknown" : reason));
 
 		cleanup();
@@ -333,8 +284,8 @@ public final class ShadersTest {
 	}
 
 	static void kill(String reason, Throwable t) {
-		System.out.println("The ShaderTest program was terminated because an exception occured.\n");
-		System.out.println("Reason: " + reason == null ? "Unknown" : reason);
+		System.out.println("The BackgroundLoadTest program was terminated because an exception occured.\n");
+		System.out.println("Reason: " + (reason == null ? "Unknown" : reason));
 
 		System.out.println("Exception message: " + t.getMessage());
 
@@ -342,4 +293,4 @@ public final class ShadersTest {
 		System.exit(-1);
 	}
 
-}
+}
\ No newline at end of file
diff --git a/src/java/org/lwjgl/test/opengl/multithread/BackgroundLoader.java b/src/java/org/lwjgl/test/opengl/multithread/BackgroundLoader.java
new file mode 100644
index 0000000..475e336
--- /dev/null
+++ b/src/java/org/lwjgl/test/opengl/multithread/BackgroundLoader.java
@@ -0,0 +1,189 @@
+/*
+ * Copyright (c) 2002-2008 LWJGL Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * * Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ *
+ * * Neither the name of 'LWJGL' nor the names of
+ *   its contributors may be used to endorse or promote products derived
+ *   from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+/*
+ * Created by LWJGL.
+ * User: spasi
+ * Date: 2004-03-30
+ * Time: 8:41:42 pm
+ */
+package org.lwjgl.test.opengl.multithread;
+
+import org.lwjgl.BufferUtils;
+import org.lwjgl.LWJGLException;
+import org.lwjgl.opengl.Drawable;
+import org.lwjgl.opengl.GL11;
+import org.lwjgl.util.Color;
+import org.lwjgl.util.ReadableColor;
+
+import java.nio.ByteBuffer;
+
+abstract class BackgroundLoader {
+
+	private static final int WIDTH = 32;
+	private static final int HEIGHT = 32;
+
+	private static final Object lock = new Object();
+
+	private Drawable drawable;
+
+	private boolean running;
+
+	private ByteBuffer texture;
+	private int texID;
+
+	protected BackgroundLoader() {
+		running = true;
+		texture = BufferUtils.createByteBuffer(WIDTH * HEIGHT * 3);
+	}
+
+	abstract Drawable getDrawable() throws LWJGLException;
+
+	void cleanup() {
+		running = false;
+	}
+
+	void start() throws LWJGLException {
+		new Thread(new Runnable() {
+			public void run() {
+				System.out.println("-- Background Thread started --");
+
+				System.out.println("** Sleeping, no texture created yet **");
+
+				try {
+					Thread.sleep(2000);
+				} catch (InterruptedException e) {
+					e.printStackTrace();
+				}
+
+				try {
+					drawable = getDrawable();
+					drawable.makeCurrent();
+				} catch (LWJGLException e) {
+					throw new RuntimeException(e);
+				}
+
+				System.out.println("** Drawable created **");
+
+				synchronized ( lock ) {
+					// Create a "dummy" texture while we wait for texture IO
+					createCheckerTexture(Color.RED, Color.WHITE, 2);
+
+					texID = GL11.glGenTextures();
+					GL11.glBindTexture(GL11.GL_TEXTURE_2D, texID);
+					GL11.glTexImage2D(GL11.GL_TEXTURE_2D, 0, GL11.GL_RGB, WIDTH, HEIGHT, 0, GL11.GL_RGB, GL11.GL_UNSIGNED_BYTE, texture);
+
+					GL11.glTexParameterf(GL11.GL_TEXTURE_2D, GL11.GL_TEXTURE_MIN_FILTER, GL11.GL_NEAREST);
+					GL11.glTexParameterf(GL11.GL_TEXTURE_2D, GL11.GL_TEXTURE_MAG_FILTER, GL11.GL_NEAREST);
+
+					GL11.glBindTexture(GL11.GL_TEXTURE_2D, 0);
+				}
+
+				System.out.println("** Dummy texture created **");
+
+				long lastTextureCreated = System.currentTimeMillis(); // Delay first texture creation
+				int count = 0;
+				while ( running ) {
+					long time = System.currentTimeMillis();
+					if ( time - lastTextureCreated < 5000 ) { // Update the texture every 5 seconds
+						try {
+							Thread.sleep(200);
+						} catch (InterruptedException e) {
+							e.printStackTrace();
+						}
+						continue;
+					}
+
+					// Create the "true" texture
+					if ( count % 2 == 0 )
+						createGradientTexture(Color.RED, Color.BLUE);
+					else
+						createGradientTexture(Color.GREEN, Color.YELLOW);
+
+					GL11.glBindTexture(GL11.GL_TEXTURE_2D, texID);
+					GL11.glTexImage2D(GL11.GL_TEXTURE_2D, 0, GL11.GL_RGB, WIDTH, HEIGHT, 0, GL11.GL_RGB, GL11.GL_UNSIGNED_BYTE, texture);
+
+					GL11.glTexParameterf(GL11.GL_TEXTURE_2D, GL11.GL_TEXTURE_MIN_FILTER, GL11.GL_LINEAR);
+					GL11.glTexParameterf(GL11.GL_TEXTURE_2D, GL11.GL_TEXTURE_MAG_FILTER, GL11.GL_LINEAR);
+
+					GL11.glBindTexture(GL11.GL_TEXTURE_2D, 0);
+
+					System.out.println("** Created new gradient texture **");
+
+					lastTextureCreated = System.currentTimeMillis();
+					count++;
+				}
+
+				drawable.destroy();
+
+				System.out.println("-- Background Thread finished --");
+			}
+		}).start();
+	}
+
+	int getTexID() {
+		synchronized ( lock ) {
+			return texID;
+		}
+	}
+
+	private void createCheckerTexture(final ReadableColor a, final ReadableColor b, final int size) {
+		int i = 0;
+		for ( int y = 0; y < HEIGHT; y++ ) {
+			for ( int x = 0; x < WIDTH; x++ ) {
+				ReadableColor c = (x / size) % 2 == 0 ? ((y / size) % 2 == 0 ? a : b) : ((y / size) % 2 == 0 ? b : a);
+				texture.put(i + 0, c.getRedByte());
+				texture.put(i + 1, c.getGreenByte());
+				texture.put(i + 2, c.getBlueByte());
+				i += 3;
+			}
+		}
+	}
+
+	private void createGradientTexture(final ReadableColor a, final ReadableColor b) {
+		float l = 0.0f;
+		int i = 0;
+		for ( int y = 0; y < HEIGHT; y++ ) {
+			for ( int x = 0; x < WIDTH; x++ ) {
+				texture.put(i + 0, lerp(a.getRed(), b.getRed(), l));
+				texture.put(i + 1, lerp(a.getGreen(), b.getGreen(), l));
+				texture.put(i + 2, lerp(a.getBlue(), b.getBlue(), l));
+				i += 3;
+			}
+			l += (1.0f / (HEIGHT - 1));
+		}
+	}
+
+	private static byte lerp(final int a, final int b, final float l) {
+		return (byte)Math.round(((1.0f - l) * a + l * b));
+	}
+
+}
\ No newline at end of file
diff --git a/src/java/org/lwjgl/util/WaveData.java b/src/java/org/lwjgl/util/WaveData.java
index d6928e7..d1389aa 100644
--- a/src/java/org/lwjgl/util/WaveData.java
+++ b/src/java/org/lwjgl/util/WaveData.java
@@ -51,8 +51,8 @@ import org.lwjgl.openal.AL10;
  * Utitlity class for loading wavefiles.
  *
  * @author Brian Matzon <brian at matzon.dk>
- * @version $Revision: 3274 $
- * $Id: WaveData.java 3274 2010-02-20 10:43:22Z matzon $
+ * @version $Revision: 3336 $
+ * $Id: WaveData.java 3336 2010-04-26 21:52:59Z matzon $
  */
 public class WaveData {
 	/** actual wave data */
@@ -108,7 +108,7 @@ public class WaveData {
 	 * @return WaveData containing data, or null if a failure occured
 	 */
 	public static WaveData create(String path) {
-		return create(WaveData.class.getClassLoader().getResource(path));
+		return create(Thread.currentThread().getContextClassLoader().getResource(path));
 	}
 	
 	/**
diff --git a/src/java/org/lwjgl/util/applet/AppletLoader.java b/src/java/org/lwjgl/util/applet/AppletLoader.java
index d9778b8..88b6b55 100644
--- a/src/java/org/lwjgl/util/applet/AppletLoader.java
+++ b/src/java/org/lwjgl/util/applet/AppletLoader.java
@@ -39,6 +39,7 @@ import java.awt.FontMetrics;
 import java.awt.Graphics;
 import java.awt.Image;
 import java.awt.MediaTracker;
+import java.awt.image.ImageObserver;
 import java.io.DataInputStream;
 import java.io.DataOutputStream;
 import java.io.File;
@@ -47,6 +48,8 @@ import java.io.FileOutputStream;
 import java.io.FilePermission;
 import java.io.IOException;
 import java.io.InputStream;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
 import java.io.OutputStream;
 import java.io.PrintWriter;
 import java.io.StringWriter;
@@ -68,6 +71,7 @@ import java.security.PrivilegedExceptionAction;
 import java.security.SecureClassLoader;
 import java.security.cert.Certificate;
 import java.util.Enumeration;
+import java.util.HashMap;
 import java.util.StringTokenizer;
 import java.util.Vector;
 import java.util.jar.JarEntry;
@@ -106,11 +110,17 @@ import sun.security.util.SecurityConstants;
  * <ul>
  * <li>al_version - [int or float] Version of deployment. If this is specified, the jars will be cached and 
  * reused if the version matches. If version doesn't match all of the files are reloaded.</li>
- * <li>al_bgcolor - [String] Hex formated color to use as background. <i>Default: ffffff</i>.</li>
- * <li>al_fgcolor - [String] Hex formated color to use as foreground. <i>Default: 000000</i>.</li>
- * <li>al_errorcolor - [String] Hex formated color to use as foreground color on error. <i>Default: ff0000</i>.</li>
+ * <li>al_cache - [boolean] Whether to use cache system. <i>Default: true</i>.</li>
  * <li>al_debug - [boolean] Whether to enable debug mode. <i>Default: false</i>.</li>
  * <li>al_prepend_host - [boolean] Whether to limit caching to this domain, disable if your applet is hosted on multple domains and needs to share the cache. <i>Default: true</i>.</li>
+ * <ul>
+ * <li>al_windows64 - [String] If specified it will be used instead of al_windows on 64bit windows systems.</li>
+ * <li>al_windows32 - [String] If specifed it will be used instead of al_windows on 32bit windows systems.</li>
+ * <li>al_linux64 - [String] If specifed it will be used instead of al_linux on 64bit linux systems.</li>
+ * <li>al_linux32 - [String] If specifed it will be used instead of al_linux on 32bit linux systems.</li>
+ * <ul>
+ * <li>boxbgcolor - [String] any String AWT color ("red", "blue", etc), RGB (0-255) or hex formated color (#RRGGBB) to use as background. <i>Default: #ffffff</i>.</li>
+ * <li>boxfgcolor - [String] any String AWT color ("red", "blue", etc), RGB (0-255) or hex formated color (#RRGGBB) to use as foreground. <i>Default: #000000</i>.</li>
  * </ul>
  * </p>
  * @author kappaOne
@@ -166,19 +176,19 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 	protected int		totalSizeExtract; 
 	
 	/** logo to be shown while loading */
-	protected Image		logo;
+	protected Image		logo, logoBuffer;
 
 	/** progressbar to render while loading */
-	protected Image		progressbar;
+	protected Image		progressbar, progressbarBuffer;
 	
 	/** offscreen image used */
 	protected Image 	offscreen;
 	
+	/** set to true while painting is done */
+	protected boolean 	painting;
+	
 	/** background color of applet */
 	protected Color		bgColor 	= Color.white;
-	
-	/** Color to write errors in */
-	protected Color		errorColor 	= Color.red;
 
 	/** color to write foreground in */
 	protected Color		fgColor 	= Color.black;	
@@ -210,6 +220,15 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 	/** whether to prepend host to cache path */
 	protected boolean 	prependHost;
 	
+	/** Used to store file names with lastModified time */
+	protected HashMap 	filesLastModified;
+	
+	/** Sizes of files to download */
+	protected int[] 	fileSizes;
+	
+	/** whether to use caching system, only download files that have changed */
+	protected boolean 	cacheEnabled;
+	
 	/** String to display as a subtask */
 	protected String	subtaskMessage = "";
 
@@ -252,7 +271,10 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 				return;				
 			}
 		}
-
+		
+		// whether to use cache system
+		cacheEnabled	= getBooleanParameter("al_cache", true);
+		
 		// whether to run in debug mode
 		debugMode 		= getBooleanParameter("al_debug", false);
 		
@@ -260,11 +282,9 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 		prependHost 	= getBooleanParameter("al_prepend_host", true);
 		
 		// get colors of applet
-		bgColor 		= getColor("al_bgcolor", Color.white);
+		bgColor 		= getColor("boxbgcolor", Color.white);
 		setBackground(bgColor);
-
-		fgColor 		= getColor("al_fgcolor", Color.black);
-		errorColor 		= getColor("al_errorcolor", Color.red);		
+		fgColor 		= getColor("boxfgcolor", Color.black);	
 
 		// load logos
 		logo 			= getImage(getParameter("al_logo"));
@@ -339,7 +359,6 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 		if (lwjglApplet != null) {
 			lwjglApplet.stop();
 		}
-		super.stop();
 	}
 	
 	/*
@@ -353,7 +372,8 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 		progressbar = null;
 		logo 		= null;
 		
-		super.destroy();
+		logoBuffer = null;
+		progressbarBuffer = null;
 	}
 	
 	/**
@@ -390,22 +410,34 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 		// create offscreen if missing
 		if (offscreen == null) {
 			offscreen = createImage(getWidth(), getHeight());
+			
+			// create buffers for animated gifs
+			logoBuffer = createImage(logo.getWidth(null), logo.getHeight(null));
+			progressbarBuffer = createImage(logo.getWidth(null), logo.getHeight(null));
+			
+			// add image observer, it will notify when next animated gif frame is ready 
+			offscreen.getGraphics().drawImage(logo, 0, 0, this);
+			offscreen.getGraphics().drawImage(progressbar, 0, 0, this);
+			
+			// in case image is not animated fill image buffers once
+			imageUpdate(logo, ImageObserver.FRAMEBITS, 0, 0, 0, 0);
+			imageUpdate(progressbar, ImageObserver.FRAMEBITS, 0, 0, 0, 0);
 		}
 
 		// draw everything onto an image before drawing to avoid flicker
 		Graphics og = offscreen.getGraphics();
 		FontMetrics fm = og.getFontMetrics();
 
-		// set background color
+		// clear background color
 		og.setColor(bgColor);
-		og.fillRect(0, 0, getWidth(), getHeight());
+		og.fillRect(0, 0, offscreen.getWidth(null), offscreen.getHeight(null));
 
 		// get logo position so its in the middle of applet
 		int x = 0, y = 0;
 		
 		if(logo != null && !fatalError) {
-			x = (getWidth() - logo.getWidth(this)) / 2;
-			y = (getHeight() - logo.getHeight(this)) / 2;
+			x = (offscreen.getWidth(null) - logo.getWidth(null)) / 2;
+			y = (offscreen.getHeight(null) - logo.getHeight(null)) / 2;
 		}
 
 		og.setColor(fgColor);
@@ -421,41 +453,79 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 			
 			for(int i=0; i<errorMessage.length; i++) {
 				if(errorMessage[i] != null) {
-					int messageX = (getWidth() - fm.stringWidth(errorMessage[i])) / 2;
-					int messageY = (getHeight() - (fm.getHeight() * errorMessage.length)) / 2;
+					int messageX = (offscreen.getWidth(null) - fm.stringWidth(errorMessage[i])) / 2;
+					int messageY = (offscreen.getHeight(null) - (fm.getHeight() * errorMessage.length)) / 2;
 					
-					og.setColor(errorColor);
 					og.drawString(errorMessage[i], messageX, messageY + i*fm.getHeight());
 				}
 			}
 		} else {
 			og.setColor(fgColor);
-
+			
+			painting = true;
+			
 			// draw logo
-			og.drawImage(logo, x, y, null);
+			og.drawImage(logoBuffer, x, y, this);
 			
 			// draw message
-			int messageX = (getWidth() - fm.stringWidth(message)) / 2;
-			int messageY = y + logo.getHeight(null) + 20;
+			int messageX = (offscreen.getWidth(null) - fm.stringWidth(message)) / 2;
+			int messageY = y + logoBuffer.getHeight(null) + 20;
 			og.drawString(message, messageX, messageY);
 			
 			// draw subtaskmessage, if any
 			if(subtaskMessage.length() > 0) {
-				messageX = (getWidth() - fm.stringWidth(subtaskMessage)) / 2;
+				messageX = (offscreen.getWidth(null) - fm.stringWidth(subtaskMessage)) / 2;
 				og.drawString(subtaskMessage, messageX, messageY+20);
 			}
 
 			// draw loading bar, clipping it depending on percentage done
-			int barSize = (progressbar.getWidth(this) * percentage) / 100;
-			og.clipRect(0, 0, x + barSize, getHeight());
-			og.drawImage(progressbar, x, y, null);
+			int barSize = (progressbarBuffer.getWidth(null) * percentage) / 100;
+			og.clipRect(0, 0, x + barSize, offscreen.getHeight(null));
+			og.drawImage(progressbarBuffer, x, y, this);
+			
+			painting = false;
 		}
 		
 		og.dispose();
-
-		// finally draw it all
-		g.drawImage(offscreen, 0, 0, null);
-	}	
+		
+		// finally draw it all centred
+		g.drawImage(offscreen, (getWidth() - offscreen.getWidth(null))/2, (getHeight() - offscreen.getHeight(null))/2, null);
+	}
+	
+	/**
+	 * When an animated gif frame is ready to be drawn the ImageObserver 
+	 * will call this method.
+	 * 
+	 * The Image frame is copied into a buffer, which is then drawn. 
+	 * This is done to prevent image tearing on gif animations.
+	 */
+	public boolean imageUpdate(Image img, int flag, int x, int y, int width, int height) {
+		
+		// if image frame is ready to be drawn and is currently not being painted
+		if (flag == ImageObserver.FRAMEBITS && !painting) {
+			Image buffer;
+			
+			// select which buffer to fill
+			if (img == logo) buffer = logoBuffer;
+			else buffer = progressbarBuffer;
+			
+			Graphics g = buffer.getGraphics();
+			
+			// clear background on buffer
+			g.setColor(bgColor);
+			g.fillRect(0, 0, buffer.getWidth(null), buffer.getHeight(null));
+			
+			// buffer background is cleared, so draw logo under progressbar
+			if (img == progressbar) g.drawImage(logoBuffer, 0, 0, null);
+			
+			g.drawImage(img, 0, 0, this);
+			g.dispose();
+			
+			repaint();
+		}
+		
+		return true;
+	}
 
 	/**
 	 * @return string describing the state of the loader
@@ -467,7 +537,7 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 			case STATE_DETERMINING_PACKAGES:
 				return "Determining packages to load";
 			case STATE_CHECKING_CACHE:
-				return "Checking cache for existing files";
+				return "Calculating download size";
 			case STATE_DOWNLOADING:
 				return "Downloading packages";
 			case STATE_EXTRACTING_PACKAGES:
@@ -534,9 +604,31 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 		String nativeJar 	= null;
 		
 		if (osName.startsWith("Win")) {
-			nativeJar = getParameter("al_windows");
+			
+			// check if arch specific natives have been specified
+			if (System.getProperty("os.arch").endsWith("64")) {
+				nativeJar = getParameter("al_windows64");
+			} else {
+				nativeJar = getParameter("al_windows32");
+			}
+			
+			if (nativeJar == null) {
+				nativeJar = getParameter("al_windows");
+			}
+			
 		} else if (osName.startsWith("Linux")) {
-			nativeJar = getParameter("al_linux");
+			
+			// check if arch specific natives have been specified
+			if (System.getProperty("os.arch").endsWith("64")) {
+				nativeJar = getParameter("al_linux64");
+			} else {
+				nativeJar = getParameter("al_linux32");
+			}
+			
+			if (nativeJar == null) {
+				nativeJar = getParameter("al_linux");
+			}
+			
 		} else if (osName.startsWith("Mac")) {
 			nativeJar = getParameter("al_mac");
 		} else if (osName.startsWith("Solaris") || osName.startsWith("SunOS")) {
@@ -598,10 +690,11 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 			if (!dir.exists()) {
 				dir.mkdirs();
 			}
-			dir = new File(dir, "version");
-
-			// if applet already available don't download anything
-			boolean cacheAvailable = false;
+			
+			File versionFile = new File(dir, "version");
+			
+			// if specified applet version already available don't download anything
+			boolean versionAvailable = false;
 
 			// version of applet
 			String version = getParameter("al_version");
@@ -613,10 +706,10 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 				latestVersion = Float.parseFloat(version);
 
 				// if version file exists
-				if (dir.exists()) {
+				if (versionFile.exists()) {
 					// compare to new version
-					if (latestVersion <= readVersionFile(dir)) {
-						cacheAvailable = true;
+					if (latestVersion <= readVersionFile(versionFile)) {
+						versionAvailable = true;
 						percentage = 90;
 						
 						if(debugMode) {
@@ -628,9 +721,12 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 			}
 
 			// if jars not available or need updating download them
-			if (!cacheAvailable) {
+			if (!versionAvailable) {
+				// get jars file sizes and check cache
+				getJarInfo(dir);		// 5-15%
+				
 				// downloads jars from the server
-				downloadJars(path);		// 10-55%
+				downloadJars(path);		// 15-55%
 				
 				// Extract Pack and LZMA files
 				extractJars(path);		// 55-65%
@@ -638,11 +734,14 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 				// Extracts Native Files
 				extractNatives(path);	// 65-85%
 
-				// add version information once jars downloaded successfully
+				// save version information once jars downloaded successfully
 				if (version != null) {
 					percentage = 90;
 					writeVersionFile(dir, latestVersion);
 				}
+				
+				// save file names with last modified info once downloaded successfully
+				writeCacheFile(new File(dir, "cache"), filesLastModified);
 			}
 
 			// add the downloaded jars and natives to classpath
@@ -688,6 +787,33 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 		dos.writeFloat(version);
 		dos.close();
 	}
+	
+	/**
+	 * read the current cache file
+	 * 
+	 * @param file the file to read
+	 * @return the hashmap containing the files names and lastModified times
+	 * @throws Exception if it fails to read hashmap
+	 */
+	protected HashMap readCacheFile(File file) throws Exception {
+		ObjectInputStream dis = new ObjectInputStream(new FileInputStream(file));
+		HashMap hashMap = (HashMap)dis.readObject();
+		dis.close();
+		return hashMap;
+	}
+
+	/**
+	 * write out cache file of applet
+	 * 
+	 * @param file the file to write out to
+	 * @param filesLastModified the hashmap containing files names and lastModified times
+	 * @throws Exception if it fails to write file
+	 */
+	protected void writeCacheFile(File file, HashMap filesLastModified) throws Exception {
+		ObjectOutputStream dos = new ObjectOutputStream(new FileOutputStream(file));
+		dos.writeObject(filesLastModified);
+		dos.close();
+	}
 
 	/**
 	 * Edits the ClassPath at runtime to include the jars
@@ -765,7 +891,7 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 	 * Due to the way applets on plugin1 work, one jvm must
 	 * be used for all applets. We need to use multiple 
 	 * classloaders in the same jvm due to LWJGL's static 
-	 * nature. I order to solver this we simply remove the 
+	 * nature. I order to solve this we simply remove the 
 	 * natives from a previous classloader allowing a new 
 	 * classloader to use those natives in the same jvm.
 	 * 
@@ -830,22 +956,32 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 		state = STATE_START_REAL_APPLET;
 		lwjglApplet.start();
 	}
-
+	
 	/**
-	 * Will download the jars from the server using the list of urls
-	 * in urlList, while at the same time updating progress bar
+	 * This method will get the files sizes of the files to download.
+	 * It wil further get the lastModified time of files
+	 * and save it in a hashmap, if cache is enabled it will mark
+	 * those files that have not changed since last download to not
+	 * redownloaded.
 	 * 
-	 * @param path location of the directory to save to
-	 * @throws Exception if download fails
+	 * @param dir - location to read cache file from
+	 * @throws Exception - if fails to get infomation
 	 */
-	protected void downloadJars(String path) throws Exception {
+	protected void getJarInfo(File dir) throws Exception {
+		
+		filesLastModified = new HashMap();
+		
+		// store file sizes and mark which files not to download
+		fileSizes = new int[urlList.length];
 		
-		state = STATE_DOWNLOADING;
-
 		URLConnection urlconnection;
 		
-		// store file sizes, used for download verification
-		int[] fileSizes = new int[urlList.length];
+		File cacheFile = new File(dir, "cache");
+		
+		// if cache file exists, load it
+		if (cacheFile.exists()) {
+			filesLastModified = readCacheFile(cacheFile);
+		}
 		
 		// calculate total size of jars to download
 		for (int i = 0; i < urlList.length; i++) {
@@ -854,16 +990,57 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 			if (urlconnection instanceof HttpURLConnection) {
 				((HttpURLConnection) urlconnection).setRequestMethod("HEAD");
 			}
+			
 			fileSizes[i] = urlconnection.getContentLength();
-			totalSizeDownload += fileSizes[i];
+			
+			long lastModified = urlconnection.getLastModified();
+			String fileName = getFileName(urlList[i]);
+			
+			
+			if (cacheEnabled && lastModified != 0 && 
+					filesLastModified.containsKey(fileName)) {
+				long savedLastModified = ((Long)filesLastModified.get(fileName)).longValue();
+				
+				// if lastModifed time is the same, don't redownload
+				if (savedLastModified == lastModified) {
+					fileSizes[i] = -2; // mark it to not redownload
+				}
+			}
+			
+			if (fileSizes[i] >= 0) {
+				totalSizeDownload += fileSizes[i];
+			}
+			
+			// put key and value in the hashmap
+			filesLastModified.put(fileName, new Long(lastModified));
+			
+			// update progress bar
+			percentage = 5 + (int)(10 * i/(float)urlList.length);
 		}
+	}
+	
+	/**
+	 * Will download the jars from the server using the list of urls
+	 * in urlList, while at the same time updating progress bar
+	 * 
+	 * @param path location of the directory to save to
+	 * @throws Exception if download fails
+	 */
+	protected void downloadJars(String path) throws Exception {
 		
-		int initialPercentage = percentage = 10;
+		state = STATE_DOWNLOADING;
+
+		URLConnection urlconnection;
+		
+		int initialPercentage = percentage = 15;
 
 		// download each jar
 		byte buffer[] = new byte[65536];
 		for (int i = 0; i < urlList.length; i++) {
 			
+			// skip file if marked as -2 (already downloaded and not changed)
+			if (fileSizes[i] == -2) continue;
+			
 			int unsuccessfulAttempts = 0;
 			int maxUnsuccessfulAttempts = 3;
 			boolean downloadFile = true;
@@ -909,7 +1086,7 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 						// round to two decimal places
 						downloadSpeed = ((int)(downloadSpeed*100))/100f;
 						// set current speed message
-						downloadSpeedMessage = " @ " + downloadSpeed + " KB/sec";
+						downloadSpeedMessage = " - " + downloadSpeed + " KB/sec";
 						// reset downloaded amount
 						downloadedAmount = 0;
 						// reset start time
@@ -1067,6 +1244,10 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 		float increment = (float) 10.0 / urlList.length;
 		// extract all lzma and pack.lzma files
 		for (int i = 0; i < urlList.length; i++) {
+			
+			// if file has not changed, skip it
+			if (fileSizes[i] == -2) continue;
+			
 			percentage = 55 + (int) (increment * (i+1));
 			String filename = getFileName(urlList[i]);
 			
@@ -1102,6 +1283,11 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 	 */
 	protected void extractNatives(String path) throws Exception {
 
+		// if no new native jar was downloaded, no extracting needed
+		if (fileSizes[fileSizes.length-1] == -2) {
+			return;
+		}
+		
 		state = STATE_EXTRACTING_PACKAGES;
 		
 		int initialPercentage = percentage;
@@ -1293,12 +1479,39 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 	 * @param defaultColor Default color to use if no color to load
 	 * @return Color to use
 	 */
-	protected Color getColor(String color, Color defaultColor) {
-		String param_color = getParameter(color);
-		if (param_color != null) {
-			return new Color(Integer.parseInt(param_color, 16));
-		}
-		return defaultColor;
+	protected Color getColor(String param, Color defaultColor) {
+		String color = getParameter(param);
+		
+		if (color == null) return defaultColor;
+		
+		// Check if RGB format
+        if (color.indexOf(",") != -1) {
+            StringTokenizer st = new StringTokenizer(color, ",");
+            
+            // We've got three components for the color
+            try {
+            	return new Color(Integer.parseInt(st.nextToken().trim()), 
+    							 Integer.parseInt(st.nextToken().trim()), 
+    							 Integer.parseInt(st.nextToken().trim()));
+            } catch (Exception e) {
+                // failed to parse
+            	return defaultColor;
+            }
+        }
+        
+        // Check & decode if the color is in hexadecimal color format (i.e. #808000)
+        try {
+        	return Color.decode(color);
+        } catch (NumberFormatException e) {
+        	// ignore exception
+        }
+        
+        // Get the color by name if it exists
+        try {
+        	return (Color)Color.class.getField(color).get(null);
+        } catch (Exception e) {
+        	return defaultColor;
+        }
 	}
 	
 	/**
@@ -1322,7 +1535,7 @@ public class AppletLoader extends Applet implements Runnable, AppletStub {
 	 */
 	protected void fatalErrorOccured(String error, Exception e) {
 		fatalError = true;
-		fatalErrorDescription = "Fatal error occured (" + state + "): " + error;
+		fatalErrorDescription = "This occurred while '" + getDescriptionForState() + "'";
 		System.out.println(fatalErrorDescription);
 		if(e != null) {
 			System.out.println(generateStacktrace(e));
diff --git a/src/java/org/lwjgl/util/generator/Extension.java b/src/java/org/lwjgl/util/generator/Alias.java
similarity index 80%
copy from src/java/org/lwjgl/util/generator/Extension.java
copy to src/java/org/lwjgl/util/generator/Alias.java
index fb074b2..c6776be 100644
--- a/src/java/org/lwjgl/util/generator/Extension.java
+++ b/src/java/org/lwjgl/util/generator/Alias.java
@@ -32,18 +32,23 @@
 package org.lwjgl.util.generator;
 
 /**
+ * This annotation can be used for extensions that have aliases
+ * with the exact same functionality.
+ * <p/>
+ * This is currently only implemented for context-specific functionality.
  *
- * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 2983 $
- * $Id: Extension.java 2983 2008-04-07 18:36:09Z matzon $
+ * @author Spasi <spasi at users.sourceforge.net>
  */
-
-import java.lang.annotation.Target;
 import java.lang.annotation.ElementType;
+import java.lang.annotation.Target;
 
 @Target(ElementType.TYPE)
-public @interface Extension {
-	String className() default "";
-	boolean isFinal() default true;
-	String postfix();
-}
+public @interface Alias {
+
+	/** The aliased extension name. */
+	String value();
+
+	/** The function name postfix for the aliased version. (optional) */
+	String postfix() default "";
+
+}
\ No newline at end of file
diff --git a/src/java/org/lwjgl/util/generator/AutoSize.java b/src/java/org/lwjgl/util/generator/AutoSize.java
index 8ea4716..726abd2 100644
--- a/src/java/org/lwjgl/util/generator/AutoSize.java
+++ b/src/java/org/lwjgl/util/generator/AutoSize.java
@@ -37,8 +37,8 @@ package org.lwjgl.util.generator;
  * according to the remaining() of a Buffer parameter.
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 2983 $
- * $Id: AutoSize.java 2983 2008-04-07 18:36:09Z matzon $
+ * @version $Revision: 3355 $
+ * $Id: AutoSize.java 3355 2010-05-27 22:56:29Z spasi $
  */
 
 import java.lang.annotation.Target;
@@ -49,4 +49,5 @@ import java.lang.annotation.ElementType;
 public @interface AutoSize {
 	String value(); // The name of the Buffer parameter
 	String expression() default ""; // This value is added after the argument
+	boolean canBeNull() default false; // When this is true and the Buffer parameter is null, 0 will be used.
 }
diff --git a/src/java/org/lwjgl/util/generator/ContextCapabilitiesGenerator.java b/src/java/org/lwjgl/util/generator/ContextCapabilitiesGenerator.java
index 4feba92..d762aad 100644
--- a/src/java/org/lwjgl/util/generator/ContextCapabilitiesGenerator.java
+++ b/src/java/org/lwjgl/util/generator/ContextCapabilitiesGenerator.java
@@ -46,24 +46,23 @@ import com.sun.mirror.type.InterfaceType;
  * Generator visitor for the context capabilities generator tool
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 3316 $
- *          $Id: ContextCapabilitiesGenerator.java 3316 2010-04-09 23:57:40Z spasi $
+ * @version $Revision: 3355 $
+ *          $Id: ContextCapabilitiesGenerator.java 3355 2010-05-27 22:56:29Z spasi $
  */
 public class ContextCapabilitiesGenerator {
 
-	private final static String STUBS_LOADED_NAME = "loaded_stubs";
-	private final static String ALL_INIT_METHOD_NAME = "initAllStubs";
-	private final static String POINTER_INITIALIZER_POSTFIX = "_initNativeFunctionAddresses";
-	private final static String CACHED_EXTS_VAR_NAME = "supported_extensions";
-	private final static String PROFILE_MASK_VAR_NAME = "profileMask";
-	private final static String EXTENSION_PREFIX = "GL_";
-	private final static String CORE_PREFIX = "Open";
+	private static final String STUBS_LOADED_NAME = "loaded_stubs";
+	private static final String ALL_INIT_METHOD_NAME = "initAllStubs";
+	private static final String POINTER_INITIALIZER_POSTFIX = "_initNativeFunctionAddresses";
+	private static final String CACHED_EXTS_VAR_NAME = "supported_extensions";
+	private static final String PROFILE_MASK_VAR_NAME = "profileMask";
+	private static final String EXTENSION_PREFIX = "GL_";
+	private static final String CORE_PREFIX = "Open";
 
 	public static void generateClassPrologue(PrintWriter writer, boolean context_specific, boolean generate_error_checks) {
 		writer.println("public class " + Utils.CONTEXT_CAPS_CLASS_NAME + " {");
 		writer.println("\tstatic final boolean DEBUG = " + Boolean.toString(generate_error_checks) + ";");
 		writer.println("\tfinal StateTracker tracker = new StateTracker();");
-		writer.println("\tfinal IntBuffer scratch_int_buffer = BufferUtils.createIntBuffer(16);");
 		writer.println();
 		if ( !context_specific ) {
 			writer.println("\tprivate static boolean " + STUBS_LOADED_NAME + " = false;");
@@ -109,6 +108,12 @@ public class ContextCapabilitiesGenerator {
 			writer.print("\t\t\t&& " + CACHED_EXTS_VAR_NAME + ".contains(\"");
 			writer.print(translateFieldName(super_interface.getDeclaration().getSimpleName()) + "\")");
 		}
+		Alias alias_annotation = d.getAnnotation(Alias.class);
+		if ( alias_annotation != null ) {
+			writer.println();
+			writer.print("\t\t\t|| " + CACHED_EXTS_VAR_NAME + ".contains(\"");
+			writer.print(translateFieldName(alias_annotation.value()) + "\")");
+		}
 		writer.println(";");
 	}
 
@@ -165,10 +170,19 @@ public class ContextCapabilitiesGenerator {
 	public static void generateInitStubs(PrintWriter writer, InterfaceDeclaration d, boolean context_specific) {
 		if ( d.getMethods().size() > 0 ) {
 			if ( context_specific ) {
+				final Alias alias_annotation = d.getAnnotation(Alias.class);
+
 				if ( d.getAnnotation(ForceInit.class) != null )
 					writer.println("\t\t" + CACHED_EXTS_VAR_NAME + ".add(\"" + translateFieldName(d.getSimpleName()) + "\");");
-				writer.print("\t\tif (" + CACHED_EXTS_VAR_NAME + ".contains(\"");
+				writer.print("\t\tif (");
+				if ( alias_annotation != null )
+					writer.print("(");
+				writer.print(CACHED_EXTS_VAR_NAME + ".contains(\"");
 				writer.print(translateFieldName(d.getSimpleName()) + "\")");
+				if ( alias_annotation != null ) {
+					writer.print(" || " + CACHED_EXTS_VAR_NAME + ".contains(\"");
+					writer.print(translateFieldName(alias_annotation.value()) + "\"))");
+				}
 				writer.print(" && !" + getAddressesInitializerName(d.getSimpleName()) + "(");
 				if ( d.getAnnotation(DeprecatedGL.class) != null )
 					writer.print("forwardCompatible");
@@ -177,10 +191,16 @@ public class ContextCapabilitiesGenerator {
 						writer.print(",");
 					writer.print("supported_extensions");
 				}
-				writer.println("))");
-				//writer.print("\t\t\t" + CACHED_EXTS_VAR_NAME + ".remove(\"");
+				if ( alias_annotation != null ) {
+					writer.println(")) {");
+					writer.print("\t\t\tremove(" + CACHED_EXTS_VAR_NAME + ", \"");
+					writer.println(translateFieldName(alias_annotation.value()) + "\");");
+				} else
+					writer.println("))");
 				writer.print("\t\t\tremove(" + CACHED_EXTS_VAR_NAME + ", \"");
 				writer.println(translateFieldName(d.getSimpleName()) + "\");");
+				if ( alias_annotation != null )
+					writer.println("\t\t}");
 			} else {
 				writer.print("\t\tGLContext." + Utils.STUB_INITIALIZER_NAME + "(" + Utils.getSimpleClassName(d));
 				writer.println(".class, " + CACHED_EXTS_VAR_NAME + ", \"" + translateFieldName(d.getSimpleName()) + "\");");
@@ -211,6 +231,9 @@ public class ContextCapabilitiesGenerator {
 			writer.print("Set supported_extensions");
 		}
 
+		Alias alias_annotation = d.getAnnotation(Alias.class);
+		boolean aliased = alias_annotation != null && alias_annotation.postfix().length() > 0;
+
 		writer.println(") {");
 		writer.println("\t\treturn ");
 
@@ -267,9 +290,12 @@ public class ContextCapabilitiesGenerator {
 						writer.print(", ");
 				}
 				writer.print("}, ");
+			} else if ( aliased ) {
+				writer.print("GLContext.getFunctionAddress(new String[] {\"" + method.getSimpleName() + "\",\"" + method.getSimpleName() + alias_annotation.postfix() + "\"})) != 0");
 			} else
 				writer.print("GLContext.getFunctionAddress(");
-			writer.print("\"" + method.getSimpleName() + "\")) != 0");
+			if ( !aliased )
+				writer.print("\"" + method.getSimpleName() + "\")) != 0");
 			if ( deprecated || dependent != null )
 				writer.print(')');
 			if ( optional )
diff --git a/src/java/org/lwjgl/util/generator/FieldsGenerator.java b/src/java/org/lwjgl/util/generator/FieldsGenerator.java
index 689390b..a8a6d4b 100644
--- a/src/java/org/lwjgl/util/generator/FieldsGenerator.java
+++ b/src/java/org/lwjgl/util/generator/FieldsGenerator.java
@@ -32,47 +32,90 @@
 
 package org.lwjgl.util.generator;
 
-import com.sun.mirror.declaration.*;
-import com.sun.mirror.type.*;
+import java.io.PrintWriter;
+import java.util.Collection;
 
-import java.io.*;
-import java.util.*;
+import com.sun.mirror.declaration.FieldDeclaration;
+import com.sun.mirror.declaration.Modifier;
+import com.sun.mirror.type.PrimitiveType;
+import com.sun.mirror.type.TypeMirror;
 
 public class FieldsGenerator {
+
 	private static void validateField(FieldDeclaration field) {
+		// Check if field is "public static final"
 		Collection<Modifier> modifiers = field.getModifiers();
-		if (modifiers.size() != 3 || !modifiers.contains(Modifier.PUBLIC) || !modifiers.contains(Modifier.STATIC) ||
-				!modifiers.contains(Modifier.FINAL))
+		if ( modifiers.size() != 3
+		     || !modifiers.contains(Modifier.PUBLIC)
+		     || !modifiers.contains(Modifier.STATIC)
+		     || !modifiers.contains(Modifier.FINAL) ) {
 			throw new RuntimeException("Field " + field.getSimpleName() + " is not declared public static final");
+		}
+
+		// Check suported types (int, long, float, String)
 		TypeMirror field_type = field.getType();
-		if (!(field_type instanceof PrimitiveType))
-			throw new RuntimeException("Field " + field.getSimpleName() + " is not a primitive type");
-		PrimitiveType field_type_prim = (PrimitiveType)field_type;
-		if (field_type_prim.getKind() != PrimitiveType.Kind.INT && field_type_prim.getKind() != PrimitiveType.Kind.LONG)
-			throw new RuntimeException("Field " + field.getSimpleName() + " is not of type 'int' or 'long'");
+		if ( field_type instanceof PrimitiveType ) {
+			PrimitiveType field_type_prim = (PrimitiveType)field_type;
+			PrimitiveType.Kind field_kind = field_type_prim.getKind();
+			if ( field_kind != PrimitiveType.Kind.INT
+			     && field_kind != PrimitiveType.Kind.LONG
+			     && field_kind != PrimitiveType.Kind.FLOAT ) {
+				throw new RuntimeException("Field " + field.getSimpleName() + " is not of type 'int', 'long' or 'float'");
+			}
+		} else if ( "java.lang.String".equals(field_type.toString()) ) {
+		} else {
+			throw new RuntimeException("Field " + field.getSimpleName() + " is not a primitive type or String");
+		}
+
 		Object field_value = field.getConstantValue();
-		if (field_value == null)
+		if ( field_value == null ) {
 			throw new RuntimeException("Field " + field.getSimpleName() + " has no initial value");
+		}
 	}
 
-	private static void generateField(PrintWriter writer, FieldDeclaration field) {
+	private static void generateField(PrintWriter writer, FieldDeclaration field, FieldDeclaration prev_field) {
 		validateField(field);
 
 		Object value = field.getConstantValue();
 		String field_value_string;
-		if ( value.getClass().equals(Integer.class) )
-			field_value_string = Integer.toHexString((Integer)field.getConstantValue());
-		else
-			field_value_string = Long.toHexString((Long)field.getConstantValue()) + 'l';
+		Class field_value_class = value.getClass();
+		if ( field_value_class.equals(Integer.class) ) {
+			field_value_string = "0x" + Integer.toHexString((Integer)field.getConstantValue()).toUpperCase();
+		} else if ( field_value_class.equals(Long.class) ) {
+			field_value_string = "0x" + Long.toHexString((Long)field.getConstantValue()).toUpperCase() + 'L';
+		} else if ( field_value_class.equals(Float.class) ) {
+			field_value_string = field.getConstantValue() + "f";
+		} else if ( field_value_class.equals(String.class) ) {
+			field_value_string = "\"" + field.getConstantValue() + "\"";
+		} else {
+			throw new RuntimeException("Field is of unexpected type. This means there is a bug in validateField().");
+		}
+
+		boolean hadDoc = prev_field != null && prev_field.getDocComment() != null;
+		boolean hasDoc = field.getDocComment() != null;
+		boolean newBatch = prev_field == null || !prev_field.getType().equals(field.getType()) || (!hadDoc && field.getDocComment() != null) || (hadDoc && hasDoc && !prev_field.getDocComment().equals(field.getDocComment()));
 
-		Utils.printDocComment(writer, field);
 		// Print field declaration
-		writer.println("\tpublic static final " + field.getType().toString() + " " + field.getSimpleName() + " = 0x" + field_value_string + ";");
+		if ( newBatch ) {
+			if ( prev_field != null )
+				writer.println(";\n");
+
+			Utils.printDocComment(writer, field);
+			writer.print("\tpublic static final " + field.getType().toString() + " " + field.getSimpleName() + " = " + field_value_string);
+		} else
+			writer.print(",\n\t\t" + field.getSimpleName() + " = " + field_value_string);
 	}
 
 	public static void generateFields(PrintWriter writer, Collection<FieldDeclaration> fields) {
-		for (FieldDeclaration field : fields)
-			generateField(writer, field);
+		if ( 0 < fields.size() ) {
+			writer.println();
+			FieldDeclaration prev_field = null;
+			for ( FieldDeclaration field : fields ) {
+				generateField(writer, field, prev_field);
+				prev_field = field;
+			}
+			writer.println(";");
+		}
 	}
 
 }
diff --git a/src/java/org/lwjgl/util/generator/GLpointer.java b/src/java/org/lwjgl/util/generator/GLpointer.java
index d11370e..a961fdf 100644
--- a/src/java/org/lwjgl/util/generator/GLpointer.java
+++ b/src/java/org/lwjgl/util/generator/GLpointer.java
@@ -40,4 +40,5 @@ import java.lang.annotation.ElementType;
 @Target({ElementType.PARAMETER, ElementType.METHOD})
 public @interface GLpointer {
 	String value(); // The native pointer type.
+	boolean canBeNull() default false; // Whether the pointer may be null.
 }
\ No newline at end of file
diff --git a/src/java/org/lwjgl/util/generator/GeneratorVisitor.java b/src/java/org/lwjgl/util/generator/GeneratorVisitor.java
index f9f171f..6cdd397 100644
--- a/src/java/org/lwjgl/util/generator/GeneratorVisitor.java
+++ b/src/java/org/lwjgl/util/generator/GeneratorVisitor.java
@@ -50,8 +50,8 @@ import java.nio.*;
  * Generator visitor for the generator tool
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 3299 $
- * $Id: GeneratorVisitor.java 3299 2010-03-31 15:46:16Z spasi $
+ * @version $Revision: 3355 $
+ * $Id: GeneratorVisitor.java 3355 2010-05-27 22:56:29Z spasi $
  */
 public class GeneratorVisitor extends SimpleDeclarationVisitor {
 	private final AnnotationProcessorEnvironment env;
@@ -180,10 +180,7 @@ public class GeneratorVisitor extends SimpleDeclarationVisitor {
 		java_writer.println();
 		java_writer.println("package " + d.getPackage().getQualifiedName() + ";");
 		java_writer.println();
-		java_writer.println("import org.lwjgl.LWJGLException;");
-		java_writer.println("import org.lwjgl.BufferChecks;");
-		// DISABLED: indirect buffer support
-		//java_writer.println("import org.lwjgl.NondirectBufferWrapper;");
+		java_writer.println("import org.lwjgl.*;");
 		java_writer.println("import java.nio.*;");
 		java_writer.println();
 		Utils.printDocComment(java_writer, d);
@@ -204,12 +201,12 @@ public class GeneratorVisitor extends SimpleDeclarationVisitor {
 		java_writer.println();
 		if (is_final) {
 			// Write private constructor to avoid instantiation
-			java_writer.println("\tprivate " + Utils.getSimpleClassName(d) + "() {");
-			java_writer.println("\t}");
-			java_writer.println();
+			java_writer.println("\tprivate " + Utils.getSimpleClassName(d) + "() {}");
 		}
-		if (d.getMethods().size() > 0 && !context_specific)
+		if (d.getMethods().size() > 0 && !context_specific) {
+			java_writer.println();
 			java_writer.println("\tstatic native void " + Utils.STUB_INITIALIZER_NAME + "() throws LWJGLException;");
+		}
 		JavaMethodsGenerator.generateMethodsJava(env, type_map, java_writer, d, generate_error_checks, context_specific);
 		java_writer.println("}");
 		java_writer.close();
diff --git a/src/java/org/lwjgl/util/generator/JavaMethodsGenerator.java b/src/java/org/lwjgl/util/generator/JavaMethodsGenerator.java
index cabbd90..7897978 100644
--- a/src/java/org/lwjgl/util/generator/JavaMethodsGenerator.java
+++ b/src/java/org/lwjgl/util/generator/JavaMethodsGenerator.java
@@ -37,8 +37,8 @@ package org.lwjgl.util.generator;
  * This class generates the methods in the generated java source files.
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 3293 $
- * $Id: JavaMethodsGenerator.java 3293 2010-03-23 12:43:44Z spasi $
+ * @version $Revision: 3355 $
+ * $Id: JavaMethodsGenerator.java 3355 2010-05-27 22:56:29Z spasi $
  */
 
 import com.sun.mirror.apt.*;
@@ -261,9 +261,12 @@ public class JavaMethodsGenerator {
 		// DISABLED: indirect buffer support
 		//printNondirectParameterCopies(writer, method, mode);
 		if (has_result) {
-			if ( method.getAnnotation(GLreturn.class) == null )
-				writer.println("\t\treturn " + Utils.RESULT_VAR_NAME + ";");
-			else
+			if ( method.getAnnotation(GLreturn.class) == null ) {
+				if ( ByteBuffer.class.equals(Utils.getJavaType(result_type)) )
+					writer.println("\t\treturn " + Utils.RESULT_VAR_NAME + ".order(ByteOrder.nativeOrder());"); // safeNewBuffer returns a direct ByteBuffer with BIG_ENDIAN order.
+				else
+					writer.println("\t\treturn " + Utils.RESULT_VAR_NAME + ";");
+			} else
 				Utils.printGLReturnPost(writer, method, method.getAnnotation(GLreturn.class));
 		}
 		writer.println("\t}");
@@ -384,7 +387,10 @@ public class JavaMethodsGenerator {
 				String auto_parameter_name = auto_type_annotation.value();
 				ParameterDeclaration auto_target_param = Utils.findParameter(method, auto_parameter_name);
 				TypeInfo auto_target_type_info = typeinfos_instance.get(auto_target_param);
-				writer.print("(" + auto_parameter_name + ".remaining()");
+				if ( auto_type_annotation.canBeNull() )
+					writer.print("((" + auto_parameter_name + " == null ? 0 : " + auto_parameter_name + ".remaining())");
+				else
+					writer.print("(" + auto_parameter_name + ".remaining()");
 				// Shift the remaining if the target parameter is multityped and there's no AutoType to track type
 				boolean shift_remaining = !hasAnyParameterAutoTypeAnnotation(method, auto_target_param) && Utils.isParameterMultiTyped(auto_target_param);
 				if (shift_remaining) {
@@ -443,8 +449,13 @@ public class JavaMethodsGenerator {
 						writer.print(offset == null ? "0" : offset);
 					} else
 						writer.print("0");
-				} else if ( param.getAnnotation(GLpointer.class) != null ) {
-					writer.print(".getPointer()");
+				} else {
+					GLpointer pointer_annotation = param.getAnnotation(GLpointer.class);
+					if ( pointer_annotation != null ) {
+						if ( pointer_annotation.canBeNull() )
+							writer.print(" == null ? 0 : " + param.getSimpleName());
+						writer.print(".getPointer()");
+					}
 				}
 			}
 		}
@@ -490,7 +501,7 @@ public class JavaMethodsGenerator {
                                         cachedReference != null &&
 					(mode != Mode.BUFFEROBJECT || param.getAnnotation(BufferObject.class) == null) &&
 					param.getAnnotation(Result.class) == null) {
-				writer.print("\t\t" + Utils.CHECKS_CLASS_NAME + ".getReferences(caps).");
+				writer.print("\t\tif ( LWJGLUtil.CHECKS ) " + Utils.CHECKS_CLASS_NAME + ".getReferences(caps).");
                                 if(cachedReference.name().length() > 0) {
                                     writer.print(cachedReference.name());
                                 } else {
diff --git a/src/java/org/lwjgl/util/generator/Utils.java b/src/java/org/lwjgl/util/generator/Utils.java
index 3d6aad8..dd2e2fa 100644
--- a/src/java/org/lwjgl/util/generator/Utils.java
+++ b/src/java/org/lwjgl/util/generator/Utils.java
@@ -36,8 +36,8 @@ package org.lwjgl.util.generator;
  * Various utility methods to the generator.
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 3299 $
- * $Id: Utils.java 3299 2010-03-31 15:46:16Z spasi $
+ * @version $Revision: 3339 $
+ * $Id: Utils.java 3339 2010-05-07 17:03:36Z spasi $
  */
 
 import java.io.PrintWriter;
@@ -166,7 +166,9 @@ public class Utils {
 		return null;
 	}
 
+	// DISABLED: We always generate indirect methods. (affects OpenAL only at the time of this change)
 	public static boolean isMethodIndirect(boolean generate_error_checks, boolean context_specific, MethodDeclaration method) {
+		/*
 		for (ParameterDeclaration param : method.getParameters()) {
 			if (isAddressableType(param.getType()) || getParameterAutoAnnotation(param) != null ||
 					param.getAnnotation(Constant.class) != null)
@@ -176,6 +178,8 @@ public class Utils {
 			method.getAnnotation(CachedResult.class) != null ||
 			(generate_error_checks && method.getAnnotation(NoErrorCheck.class) == null) ||
 			context_specific;
+		*/
+		return true;
 	}
 
 	public static String getNativeQualifiedName(String qualified_name) {
diff --git a/src/native/common/extgl.h b/src/native/common/extgl.h
index b26b92b..4bec56a 100644
--- a/src/native/common/extgl.h
+++ b/src/native/common/extgl.h
@@ -133,6 +133,9 @@ typedef int64_t GLint64;
 typedef uint64_t GLuint64;
 typedef struct __GLsync *GLsync;
 
+/* AMD_debug_output callback function pointer. */
+typedef void (APIENTRY *GLDEBUGPROCAMD)(GLuint id, GLenum category, GLenum severity, GLsizei length, const GLchar* message, GLvoid* userParam);
+
 /* helper stuff */
 
 /* initializes everything, call this right after the rc is created. the function returns true if successful */
diff --git a/src/native/common/org_lwjgl_openal_ALC10.c b/src/native/common/org_lwjgl_openal_ALC10.c
index 33b9b81..be1b871 100644
--- a/src/native/common/org_lwjgl_openal_ALC10.c
+++ b/src/native/common/org_lwjgl_openal_ALC10.c
@@ -86,7 +86,7 @@ static jstring JNICALL Java_org_lwjgl_openal_ALC10_nalcGetString (JNIEnv *env, j
 	int length;
 	int i=1;
 
-	if(alcString == NULL) {
+	if (alcString == NULL) {
 		return NULL;
 	}
 
@@ -94,14 +94,21 @@ static jstring JNICALL Java_org_lwjgl_openal_ALC10_nalcGetString (JNIEnv *env, j
 	// These are encoded using \0 between elements and a finishing \0\0
 	switch(token) {
 		case 0x1005:	// ALC_DEVICE_SPECIFIER
-		case 0x310:		// ALC_CAPTURE_DEVICE_SPECIFIER
+		case 0x310:	// ALC_CAPTURE_DEVICE_SPECIFIER
+			// If deviceaddress is not 0, OpenAL returns a single device terminated by a
+			// single \0 character, if token is ALC_DEVICE_SPECIFIER or
+			// ALC_CAPTURE_DEVICE_SPECIFIER.
+			if (deviceaddress != 0) {
+				length = strlen(alcString);
+				break;
+			}
 		case 0x1013:	// ALC_ALL_DEVICES_SPECIFIER
 			while (alcString[i - 1] != '\0' || alcString[i] != '\0') { 
 				i++; 
 			}
 			length = i + 1;
 			break;
-		default:
+		default:	// e.g. ALC_DEFAULT_ALL_DEVICES_SPECIFIER
 			length = strlen(alcString);
 	}
 	return NewStringNativeWithLength(env, alcString, length);
diff --git a/src/java/org/lwjgl/LinuxSysImplementation.java b/src/native/common/org_lwjgl_opengl_AMDDebugOutputCallback.c
similarity index 56%
copy from src/java/org/lwjgl/LinuxSysImplementation.java
copy to src/native/common/org_lwjgl_opengl_AMDDebugOutputCallback.c
index 8d57248..231b4bd 100644
--- a/src/java/org/lwjgl/LinuxSysImplementation.java
+++ b/src/native/common/org_lwjgl_opengl_AMDDebugOutputCallback.c
@@ -29,48 +29,39 @@
  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
-package org.lwjgl;
-
 
 /**
+ * JNI implementation of the AMD_debug_output function callback.
  *
- * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 3298 $
- * $Id: LinuxSysImplementation.java 3298 2010-03-28 23:11:17Z matzon $
+ * @author Spasi
  */
-final class LinuxSysImplementation extends J2SESysImplementation {
-	private final static int JNI_VERSION = 18;
-
-	static {
-		java.awt.Toolkit.getDefaultToolkit(); // This will make sure libjawt.so is loaded
-	}
-
-	public int getRequiredJNIVersion() {
-		return JNI_VERSION;
-	}
 
-	public boolean openURL(final String url) {
-		// Linux may as well resort to pure Java hackery, as there's no Linux native way of doing it
-		// right anyway.
+#include <jni.h>
+#include "common_tools.h"
+#include "extgl.h"
+#include "org_lwjgl_opengl_AMDDebugOutputCallback.h"
 
-		String[] browsers = {"xdg-open", "firefox", "mozilla", "opera", "konqueror", "nautilus", "galeon", "netscape"};
-
-		for (int i = 0; i < browsers.length; i ++) {
-			final String browser = browsers[i];
-			try {
-				LWJGLUtil.execPrivileged(new String[] { browser, url });
-				return true;
-			} catch (Exception e) {
-				// Ignore
-				e.printStackTrace(System.err);
+static void APIENTRY debugOutputCallback(GLuint id, GLenum category, GLenum severity, GLsizei length, const GLchar* message, GLvoid* userParam) {
+    jclass callback_class;
+	jmethodID callback_method;
+	JNIEnv *env = getThreadEnv();
+	if (env != NULL && !(*env)->ExceptionOccurred(env)) {
+		callback_class = (*env)->FindClass(env, "org/lwjgl/opengl/AMDDebugOutputUtil");
+		if ( callback_class != NULL ) {
+			callback_method = (*env)->GetStaticMethodID(env, callback_class, "messageCallback", "(IIILjava/lang/String;Ljava/nio/ByteBuffer;)V");
+			if ( callback_method != NULL ) {
+				(*env)->CallStaticVoidMethod(env, callback_class, callback_method,
+                            (jint)id,
+				            (jint)category,
+				            (jint)severity,
+                            NewStringNativeWithLength(env, message, length),
+				            NULL
+                );
 			}
 		}
-
-		// Seems to have failed
-		return false;
 	}
+}
 
-	public boolean has64Bit() {
-		return true;
-	}
+JNIEXPORT jlong JNICALL Java_org_lwjgl_opengl_AMDDebugOutputCallback_getFunctionPointer(JNIEnv *env, jclass clazz) {
+    return (jlong)(intptr_t)&debugOutputCallback;
 }
diff --git a/src/native/linux/context.c b/src/native/linux/context.c
index 32af315..c4a7388 100644
--- a/src/native/linux/context.c
+++ b/src/native/linux/context.c
@@ -31,12 +31,12 @@
  */
 
 /**
- * $Id: context.c 3116 2008-08-19 16:46:03Z spasi $
+ * $Id: context.c 3357 2010-06-02 23:35:38Z spasi $
  *
  * Include file to access public window features
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 3116 $
+ * @version $Revision: 3357 $
  */
 
 #include <jni.h>
@@ -119,6 +119,7 @@ static GLXFBConfig *chooseVisualGLX13FromBPP(JNIEnv *env, Display *disp, int scr
 	int depth = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "depth", "I"));
 	int stencil = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "stencil", "I"));
 	int samples = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "samples", "I"));
+	int colorSamples = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "colorSamples", "I"));
 	int num_aux_buffers = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "num_aux_buffers", "I"));
 	int accum_bpp = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "accum_bpp", "I"));
 	int accum_alpha = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "accum_alpha", "I"));
@@ -161,7 +162,10 @@ static GLXFBConfig *chooseVisualGLX13FromBPP(JNIEnv *env, Display *disp, int scr
 	// Assume the caller has checked support for multisample
 	if (samples > 0) {
 		putAttrib(&attrib_list, GLX_SAMPLE_BUFFERS_ARB); putAttrib(&attrib_list, 1);
-		putAttrib(&attrib_list, GLX_SAMPLES_ARB); putAttrib(&attrib_list, samples);
+		putAttrib(&attrib_list, GLX_SAMPLES_ARB); putAttrib(&attrib_list, samples); // GLX_COVERAGE_SAMPLES_NV if colorSamples > 0
+        if ( colorSamples > 0 ) {
+            putAttrib(&attrib_list, GLX_COLOR_SAMPLES_NV); putAttrib(&attrib_list, colorSamples);
+        }
 	}
 	if (sRGB) {
 		putAttrib(&attrib_list, GLX_FRAMEBUFFER_SRGB_CAPABLE_ARB); putAttrib(&attrib_list, True);
@@ -199,6 +203,7 @@ static XVisualInfo *chooseVisualGLXFromBPP(JNIEnv *env, Display *disp, int scree
 	int depth = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "depth", "I"));
 	int stencil = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "stencil", "I"));
 	int samples = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "samples", "I"));
+	int colorSamples = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "colorSamples", "I"));
 	int num_aux_buffers = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "num_aux_buffers", "I"));
 	int accum_bpp = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "accum_bpp", "I"));
 	int accum_alpha = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "accum_alpha", "I"));
@@ -228,7 +233,9 @@ static XVisualInfo *chooseVisualGLXFromBPP(JNIEnv *env, Display *disp, int scree
 	// Assume the caller has checked support for multisample
 	if (samples > 0) {
 		putAttrib(&attrib_list, GLX_SAMPLE_BUFFERS_ARB); putAttrib(&attrib_list, 1);
-		putAttrib(&attrib_list, GLX_SAMPLES_ARB); putAttrib(&attrib_list, samples);
+		putAttrib(&attrib_list, GLX_SAMPLES_ARB); putAttrib(&attrib_list, samples); // GLX_COVERAGE_SAMPLES_NV if colorSamples > 0
+        if ( colorSamples > 0 )
+            putAttrib(&attrib_list, GLX_COLOR_SAMPLES_NV); putAttrib(&attrib_list, colorSamples);
 	}
 	if (sRGB)
 		putAttrib(&attrib_list, GLX_FRAMEBUFFER_SRGB_CAPABLE_ARB);
@@ -289,6 +296,11 @@ bool initPeerInfo(JNIEnv *env, jobject peer_info_handle, Display *display, int s
 		throwException(env, "Samples > 0 specified but there's no support for GLX_ARB_multisample");
 		return false;
 	}
+	int colorSamples = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "colorSamples", "I"));
+	if (colorSamples > 0 && !extension_flags.GLX_NV_multisample_coverage) {
+		throwException(env, "Color samples > 0 specified but there's no support for GLX_NV_multisample_coverage");
+		return false;
+	}
 	bool floating_point = (bool)(*env)->GetBooleanField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "floating_point", "Z"));
 	if (floating_point && !(extension_flags.GLX13 && extension_flags.GLX_ARB_fbconfig_float)) { // We need GLX13 to support floating point
 		throwException(env, "Floating point specified but there's no support for GLX_ARB_fbconfig_float");
diff --git a/src/native/linux/extgl_glx.c b/src/native/linux/extgl_glx.c
index 1d8fc6c..7e07d48 100644
--- a/src/native/linux/extgl_glx.c
+++ b/src/native/linux/extgl_glx.c
@@ -160,6 +160,7 @@ static void extgl_InitGLXSupportedExtensions(Display *disp, int screen, GLXExten
 	extension_flags->GLX_EXT_fbconfig_packed_float = GLXQueryExtension(disp, screen, "GLX_EXT_fbconfig_packed_float");
 	extension_flags->GLX_ARB_framebuffer_sRGB = GLXQueryExtension(disp, screen, "GLX_ARB_framebuffer_sRGB") || GLXQueryExtension(disp, screen, "GLX_EXT_framebuffer_sRGB");
 	extension_flags->GLX_ARB_create_context = GLXQueryExtension(disp, screen, "GLX_ARB_create_context");
+	extension_flags->GLX_NV_multisample_coverage = GLXQueryExtension(disp, screen, "GLX_NV_multisample_coverage");
 }
 
 bool extgl_Open(JNIEnv *env) {
diff --git a/src/native/linux/extgl_glx.h b/src/native/linux/extgl_glx.h
index 56b9860..0ee85d8 100644
--- a/src/native/linux/extgl_glx.h
+++ b/src/native/linux/extgl_glx.h
@@ -271,6 +271,11 @@
 #define GLX_CONTEXT_DEBUG_BIT_ARB				0x0001
 #define GLX_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB	0x0002
 
+/* GLX_NV_multisample_coverage  */
+#define GLX_COVERAGE_SAMPLES_NV              100001
+#define GLX_COLOR_SAMPLES_NV                 0x20B3
+
+
 typedef XID GLXContextID;
 typedef XID GLXPixmap;
 typedef XID GLXDrawable;
@@ -346,6 +351,7 @@ typedef struct {
 	bool GLX_EXT_fbconfig_packed_float;
 	bool GLX_ARB_framebuffer_sRGB;
 	bool GLX_ARB_create_context;
+	bool GLX_NV_multisample_coverage;
 } GLXExtensions;
 
 /* Add _ to global symbols to avoid symbol clash with the OpenGL library */
diff --git a/src/native/linux/org_lwjgl_opengl_LinuxPeerInfo.c b/src/native/linux/org_lwjgl_opengl_LinuxPeerInfo.c
index 0e9636f..08db112 100644
--- a/src/native/linux/org_lwjgl_opengl_LinuxPeerInfo.c
+++ b/src/native/linux/org_lwjgl_opengl_LinuxPeerInfo.c
@@ -1,40 +1,40 @@
-/* 
+/*
  * Copyright (c) 2002-2008 LWJGL Project
  * All rights reserved.
- * 
+ *
  * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are 
+ * modification, are permitted provided that the following conditions are
  * met:
- * 
- * * Redistributions of source code must retain the above copyright 
+ *
+ * * Redistributions of source code must retain the above copyright
  *   notice, this list of conditions and the following disclaimer.
  *
  * * Redistributions in binary form must reproduce the above copyright
  *   notice, this list of conditions and the following disclaimer in the
  *   documentation and/or other materials provided with the distribution.
  *
- * * Neither the name of 'LWJGL' nor the names of 
- *   its contributors may be used to endorse or promote products derived 
+ * * Neither the name of 'LWJGL' nor the names of
+ *   its contributors may be used to endorse or promote products derived
  *   from this software without specific prior written permission.
- * 
+ *
  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR 
- * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
- * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 
 /**
- * $Id: org_lwjgl_opengl_LinuxPeerInfo.c 2985 2008-04-07 18:42:36Z matzon $
+ * $Id: org_lwjgl_opengl_LinuxPeerInfo.c 3358 2010-06-03 15:49:26Z spasi $
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 2985 $
+ * @version $Revision: 3358 $
  */
 
 #include <jni.h>
diff --git a/src/native/linux/org_lwjgl_opengl_Pbuffer.c b/src/native/linux/org_lwjgl_opengl_Pbuffer.c
index 63a4f61..dfcc964 100644
--- a/src/native/linux/org_lwjgl_opengl_Pbuffer.c
+++ b/src/native/linux/org_lwjgl_opengl_Pbuffer.c
@@ -1,42 +1,42 @@
-/* 
+/*
  * Copyright (c) 2002-2008 LWJGL Project
  * All rights reserved.
- * 
+ *
  * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are 
+ * modification, are permitted provided that the following conditions are
  * met:
- * 
- * * Redistributions of source code must retain the above copyright 
+ *
+ * * Redistributions of source code must retain the above copyright
  *   notice, this list of conditions and the following disclaimer.
  *
  * * Redistributions in binary form must reproduce the above copyright
  *   notice, this list of conditions and the following disclaimer in the
  *   documentation and/or other materials provided with the distribution.
  *
- * * Neither the name of 'LWJGL' nor the names of 
- *   its contributors may be used to endorse or promote products derived 
+ * * Neither the name of 'LWJGL' nor the names of
+ *   its contributors may be used to endorse or promote products derived
  *   from this software without specific prior written permission.
- * 
+ *
  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR 
- * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
- * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 
 /**
- * $Id: org_lwjgl_opengl_Pbuffer.c 2985 2008-04-07 18:42:36Z matzon $
+ * $Id: org_lwjgl_opengl_Pbuffer.c 3358 2010-06-03 15:49:26Z spasi $
  *
  * Linux Pbuffer.
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 2985 $
+ * @version $Revision: 3358 $
  */
 
 #include <stdlib.h>
diff --git a/src/native/windows/context.c b/src/native/windows/context.c
index e658f91..0342081 100644
--- a/src/native/windows/context.c
+++ b/src/native/windows/context.c
@@ -31,10 +31,10 @@
  */
 
 /**
- * $Id: context.c 3139 2008-10-28 09:53:16Z elias_naur $
+ * $Id: context.c 3377 2010-07-12 12:04:56Z matzon $
  *
  * @author elias_naue <elias_naur at users.sourceforge.net>
- * @version $Revision: 3139 $
+ * @version $Revision: 3377 $
  */
 
 #include <malloc.h>
@@ -187,6 +187,7 @@ static int findPixelFormatARBFromBPP(JNIEnv *env, HDC hdc, WGLExtensions *extens
 	int depth = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "depth", "I"));
 	int stencil = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "stencil", "I"));
 	int samples = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "samples", "I"));
+	int colorSamples = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "colorSamples", "I"));
 	int num_aux_buffers = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "num_aux_buffers", "I"));
 	int accum_bpp = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "accum_bpp", "I"));
 	int accum_alpha = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "accum_alpha", "I"));
@@ -220,8 +221,9 @@ static int findPixelFormatARBFromBPP(JNIEnv *env, HDC hdc, WGLExtensions *extens
 	if (pbuffer) {
 		putAttrib(&attrib_list, WGL_DRAW_TO_PBUFFER_ARB); putAttrib(&attrib_list, TRUE);
 	}
-	if (!getBooleanProperty(env, "org.lwjgl.opengl.Display.allowSoftwareOpenGL"))
+	if (!getBooleanProperty(env, "org.lwjgl.opengl.Display.allowSoftwareOpenGL")) {
 		putAttrib(&attrib_list, WGL_ACCELERATION_ARB); putAttrib(&attrib_list, WGL_FULL_ACCELERATION_ARB);
+	}
 	putAttrib(&attrib_list, WGL_PIXEL_TYPE_ARB); putAttrib(&attrib_list, pixel_type);
 	putAttrib(&attrib_list, WGL_DOUBLE_BUFFER_ARB); putAttrib(&attrib_list, double_buffer ? TRUE : FALSE);
 	putAttrib(&attrib_list, WGL_SUPPORT_OPENGL_ARB); putAttrib(&attrib_list, TRUE);
@@ -234,7 +236,10 @@ static int findPixelFormatARBFromBPP(JNIEnv *env, HDC hdc, WGLExtensions *extens
 	// Assume caller checked extension availability
 	if (samples > 0) {
 		putAttrib(&attrib_list, WGL_SAMPLE_BUFFERS_ARB); putAttrib(&attrib_list, 1);
-		putAttrib(&attrib_list, WGL_SAMPLES_ARB); putAttrib(&attrib_list, samples);
+	    putAttrib(&attrib_list, WGL_SAMPLES_ARB); putAttrib(&attrib_list, samples); // WGL_COVERAGE_SAMPLES_NV if colorSamples > 0
+	    if ( colorSamples > 0 ) {
+	        putAttrib(&attrib_list, WGL_COLOR_SAMPLES_NV); putAttrib(&attrib_list, colorSamples);
+        }
 	}
 	putAttrib(&attrib_list, WGL_ACCUM_BITS_ARB); putAttrib(&attrib_list, accum_bpp);
 	putAttrib(&attrib_list, WGL_ACCUM_ALPHA_BITS_ARB); putAttrib(&attrib_list, accum_alpha);
@@ -385,7 +390,7 @@ static int findPixelFormatDefault(JNIEnv *env, HDC hdc, jobject pixel_format, bo
 	return findPixelFormatFromBPP(env, hdc, pixel_format, bpp, double_buffer);
 }
 
-static bool validateAndGetExtensions(JNIEnv *env, WGLExtensions *extensions, HDC dummy_hdc, HGLRC dummy_hglrc, int samples, bool floating_point, bool floating_point_packed, bool sRGB, jobject pixelFormatCaps) {
+static bool validateAndGetExtensions(JNIEnv *env, WGLExtensions *extensions, HDC dummy_hdc, HGLRC dummy_hglrc, int samples, int colorSamples, bool floating_point, bool floating_point_packed, bool sRGB, jobject pixelFormatCaps) {
 	if (!wglMakeCurrent(dummy_hdc, dummy_hglrc)) {
 		throwException(env, "Could not bind context to dummy window");
 		return false;
@@ -400,6 +405,10 @@ static bool validateAndGetExtensions(JNIEnv *env, WGLExtensions *extensions, HDC
 		throwException(env, "No support for WGL_ARB_multisample");
 		return false;
 	}
+	if (colorSamples > 0 && !extensions->WGL_NV_multisample_coverage) {
+	    throwException(env, "No support for WGL_NV_multisample_coverage");
+		return false;
+	}
 	/*
 	 * Apparently, some drivers don't report WGL_ARB_pixel_format_float
 	 * even though GL_ARB_color_buffer_float and WGL_ATI_color_format_float
@@ -435,6 +444,7 @@ int findPixelFormatOnDC(JNIEnv *env, HDC hdc, int origin_x, int origin_y, jobjec
 	jclass cls_pixel_format = (*env)->GetObjectClass(env, pixel_format);
 	
 	int samples = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "samples", "I"));
+	int colorSamples = (int)(*env)->GetIntField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "colorSamples", "I"));
 	bool floating_point = (bool)(*env)->GetBooleanField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "floating_point", "Z"));
 	bool floating_point_packed = (bool)(*env)->GetBooleanField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "floating_point_packed", "Z"));
 	bool sRGB = (bool)(*env)->GetBooleanField(env, pixel_format, (*env)->GetFieldID(env, cls_pixel_format, "sRGB", "Z"));
@@ -461,7 +471,7 @@ int findPixelFormatOnDC(JNIEnv *env, HDC hdc, int origin_x, int origin_y, jobjec
 		// Save the current HDC and HGLRC to avoid disruption
 		saved_current_hdc = wglGetCurrentDC();
 		saved_current_hglrc = wglGetCurrentContext();
-		if (validateAndGetExtensions(env, &extensions, dummy_hdc, dummy_hglrc, samples, floating_point, floating_point_packed, sRGB, pixelFormatCaps)) {
+		if (validateAndGetExtensions(env, &extensions, dummy_hdc, dummy_hglrc, samples, colorSamples, floating_point, floating_point_packed, sRGB, pixelFormatCaps)) {
 			pixel_format_id = findPixelFormatARB(env, hdc, &extensions, pixel_format, pixelFormatCaps, use_hdc_bpp, window, pbuffer, double_buffer);
 		}
 		wglMakeCurrent(saved_current_hdc, saved_current_hglrc);
diff --git a/src/native/windows/extgl_wgl.c b/src/native/windows/extgl_wgl.c
index 75d8c6a..b8432b4 100644
--- a/src/native/windows/extgl_wgl.c
+++ b/src/native/windows/extgl_wgl.c
@@ -152,6 +152,7 @@ static void extgl_InitSupportedWGLExtensions(WGLExtensions *extensions) {
 	extensions->WGL_ARB_framebuffer_sRGB = WGLQueryExtension(extensions, "WGL_ARB_framebuffer_sRGB") || WGLQueryExtension(extensions, "WGL_EXT_framebuffer_sRGB");
 	extensions->WGL_EXT_pixel_format_packed_float = WGLQueryExtension(extensions, "WGL_EXT_pixel_format_packed_float");
 	extensions->WGL_ARB_create_context = WGLQueryExtension(extensions, "WGL_ARB_create_context");
+	extensions->WGL_NV_multisample_coverage = WGLQueryExtension(extensions, "WGL_NV_multisample_coverage");
 }
 
 static void extgl_InitWGLEXTExtensionsString(WGLExtensions *extensions) {
diff --git a/src/native/windows/extgl_wgl.h b/src/native/windows/extgl_wgl.h
index 43c06b4..e0ca55b 100644
--- a/src/native/windows/extgl_wgl.h
+++ b/src/native/windows/extgl_wgl.h
@@ -200,6 +200,15 @@ typedef HDC (APIENTRY * wglGetCurrentReadDCARBPROC) (void);
 
 typedef HGLRC (APIENTRY * wglCreateContextAttribsARBPROC) (HDC hDC, HGLRC hShareContext, const int *attribList);
 
+/*---------------------------------------------------------------------*/
+/*------------ WGL_NV_multisample_coverage ----------------------------*/
+/*---------------------------------------------------------------------*/
+
+#define WGL_COVERAGE_SAMPLES_NV                                 0x2042
+#define WGL_COLOR_SAMPLES_NV                                    0x20B9
+
+/*---------------------------------------------------------------------*/
+
 typedef struct {
     bool WGL_ARB_buffer_region;
     bool WGL_ARB_extensions_string;
@@ -217,6 +226,7 @@ typedef struct {
     bool WGL_ARB_framebuffer_sRGB;
 	bool WGL_EXT_pixel_format_packed_float;
     bool WGL_ARB_create_context;
+    bool WGL_NV_multisample_coverage;
 
 	wglGetExtensionsStringEXTPROC wglGetExtensionsStringEXT;
 
diff --git a/src/native/windows/org_lwjgl_opengl_Pbuffer.c b/src/native/windows/org_lwjgl_opengl_Pbuffer.c
index 9090f2f..92b3545 100644
--- a/src/native/windows/org_lwjgl_opengl_Pbuffer.c
+++ b/src/native/windows/org_lwjgl_opengl_Pbuffer.c
@@ -1,42 +1,42 @@
-/* 
+/*
  * Copyright (c) 2002-2008 LWJGL Project
  * All rights reserved.
- * 
+ *
  * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are 
+ * modification, are permitted provided that the following conditions are
  * met:
- * 
- * * Redistributions of source code must retain the above copyright 
+ *
+ * * Redistributions of source code must retain the above copyright
  *   notice, this list of conditions and the following disclaimer.
  *
  * * Redistributions in binary form must reproduce the above copyright
  *   notice, this list of conditions and the following disclaimer in the
  *   documentation and/or other materials provided with the distribution.
  *
- * * Neither the name of 'LWJGL' nor the names of 
- *   its contributors may be used to endorse or promote products derived 
+ * * Neither the name of 'LWJGL' nor the names of
+ *   its contributors may be used to endorse or promote products derived
  *   from this software without specific prior written permission.
- * 
+ *
  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR 
- * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
- * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 
 /**
- * $Id: org_lwjgl_opengl_Pbuffer.c 3149 2008-11-22 14:54:15Z elias_naur $
+ * $Id: org_lwjgl_opengl_Pbuffer.c 3358 2010-06-03 15:49:26Z spasi $
  *
  * Windows Pbuffer.
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 3149 $
+ * @version $Revision: 3358 $
  */
 
 #include <stdlib.h>
@@ -61,7 +61,7 @@ static bool getExtensions(JNIEnv *env, WGLExtensions *extensions, jobject pixel_
 	HDC saved_hdc;
 	HGLRC saved_context;
 	int pixel_format_id;
-	
+
 	dummy_hwnd = createDummyWindow(origin_x, origin_y);
 	if (dummy_hwnd == NULL) {
 		throwException(env, "Could not create dummy window");
@@ -136,7 +136,7 @@ JNIEXPORT void JNICALL Java_org_lwjgl_opengl_WindowsPbufferPeerInfo_nCreate
 	const int *pBufferAttribs_ptr;
 	WindowsPeerInfo *peer_info = (WindowsPeerInfo *)(*env)->GetDirectBufferAddress(env, peer_info_handle);
 	int pixel_format_id;
-	
+
 	if ( pBufferAttribs != NULL ) {
 		pBufferAttribs_ptr = (const int *)(*env)->GetDirectBufferAddress(env, pBufferAttribs);
 	} else {
diff --git a/src/native/windows/org_lwjgl_opengl_WindowsPeerInfo.c b/src/native/windows/org_lwjgl_opengl_WindowsPeerInfo.c
index 6508932..d0d9d12 100644
--- a/src/native/windows/org_lwjgl_opengl_WindowsPeerInfo.c
+++ b/src/native/windows/org_lwjgl_opengl_WindowsPeerInfo.c
@@ -31,10 +31,10 @@
  */
 
 /**
- * $Id: org_lwjgl_opengl_WindowsPeerInfo.c 3148 2008-11-22 14:51:36Z elias_naur $
+ * $Id: org_lwjgl_opengl_WindowsPeerInfo.c 3358 2010-06-03 15:49:26Z spasi $
  *
  * @author elias_naur <elias_naur at users.sourceforge.net>
- * @version $Revision: 3148 $
+ * @version $Revision: 3358 $
  */
 
 #include <jni.h>
@@ -42,8 +42,7 @@
 #include "context.h"
 #include "common_tools.h"
 
-JNIEXPORT jobject JNICALL Java_org_lwjgl_opengl_WindowsPeerInfo_createHandle
-  (JNIEnv *env, jclass clazz) {
+JNIEXPORT jobject JNICALL Java_org_lwjgl_opengl_WindowsPeerInfo_createHandle(JNIEnv *env, jclass clazz) {
 	return newJavaManagedByteBuffer(env, sizeof(WindowsPeerInfo));
 }
 
diff --git a/src/templates/org/lwjgl/openal/AL10.java b/src/templates/org/lwjgl/openal/AL10.java
index 26cc390..6a221a2 100644
--- a/src/templates/org/lwjgl/openal/AL10.java
+++ b/src/templates/org/lwjgl/openal/AL10.java
@@ -44,8 +44,8 @@ import org.lwjgl.util.generator.*;
  * AL.h version 1.0
  *
  * @author Brian Matzon <brian at matzon.dk>
- * @version $Revision: 3288 $
- * $Id: AL10.java 3288 2010-03-16 17:58:48Z spasi $
+ * @version $Revision: 3380 $
+ * $Id: AL10.java 3380 2010-07-14 13:12:24Z matzon $
  */
 public interface AL10 {
 	/** Bad value */
@@ -250,35 +250,28 @@ public interface AL10 {
 	int AL_FREQUENCY = 0x2001;
 
 	/**
-	 * Sound buffers: frequency, in units of Hertz [Hz].
-	 * This is the number of samples per second. Half of the
-	 * sample frequency marks the maximum significant
-	 * frequency component.
+	 * Sound buffers: The number of bits per sample for the
+	 * data contained in the buffer.
 	 */
 	int AL_BITS = 0x2002;
 
 	/**
-	 * Sound buffers: frequency, in units of Hertz [Hz].
-	 * This is the number of samples per second. Half of the
-	 * sample frequency marks the maximum significant
-	 * frequency component.
+	 * Sound buffers: The number of channels for the data
+	 * contained in the buffer.
 	 */
 	int AL_CHANNELS = 0x2003;
 
 	/**
-	 * Sound buffers: frequency, in units of Hertz [Hz].
-	 * This is the number of samples per second. Half of the
-	 * sample frequency marks the maximum significant
-	 * frequency component.
+	 * Sound buffers: Size in bytes of the buffer data.
 	 */
 	int AL_SIZE = 0x2004;
 
 	/**
-	 * Sound buffers: frequency, in units of Hertz [Hz].
-	 * This is the number of samples per second. Half of the
-	 * sample frequency marks the maximum significant
-	 * frequency component.
+	 * @deprecated This token is a relict of the early OpenAL days and is
+	 * no longer supported. Neither the OpenAL spec nor OpenAL Soft define
+	 * it.
 	 */
+	@Deprecated
 	int AL_DATA = 0x2005;
 
 	/**
diff --git a/src/templates/org/lwjgl/openal/EFX10.java b/src/templates/org/lwjgl/openal/EFX10.java
new file mode 100644
index 0000000..700edf3
--- /dev/null
+++ b/src/templates/org/lwjgl/openal/EFX10.java
@@ -0,0 +1,738 @@
+/*
+ * Copyright (c) 2002-2010 LWJGL Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * * Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ *
+ * * Neither the name of 'LWJGL' nor the names of
+ *   its contributors may be used to endorse or promote products derived
+ *   from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package org.lwjgl.openal;
+
+import java.nio.FloatBuffer;
+import java.nio.IntBuffer;
+
+import org.lwjgl.util.generator.ALenum;
+import org.lwjgl.util.generator.ALsizei;
+import org.lwjgl.util.generator.ALuint;
+import org.lwjgl.util.generator.ALvoid;
+import org.lwjgl.util.generator.Alternate;
+import org.lwjgl.util.generator.AutoSize;
+import org.lwjgl.util.generator.Check;
+import org.lwjgl.util.generator.Const;
+import org.lwjgl.util.generator.Constant;
+import org.lwjgl.util.generator.Indirect;
+import org.lwjgl.util.generator.OutParameter;
+import org.lwjgl.util.generator.Result;
+import org.lwjgl.util.generator.StripPostfix;
+
+/**
+ * Implementation of the OpenAL extension ALC_EXT_EFX (version 1.0). Contains necessary fields,
+ * methods and a range of supplementary fields containing minimum, maximum and default values of
+ * the former fields.
+ * <p>
+ * On top of regular functions defined in the ALC_EXT_EFX, there are also several convenience
+ * functions. Namely alGen... and alDelete... which do not take a Java buffer parameter and
+ * automatically create or delete a single object, without the overhead of using a buffer.
+ * <p>
+ * For comments and specification of functions and fields, refer to the "Effects Extension Guide"
+ * which is part of the OpenAL SDK and can be downloaded from:
+ * http://connect.creativelabs.com/openal/Downloads/Forms/AllItems.aspx
+ *
+ * @author Ciardhubh <ciardhubh[at]ciardhubh.de>
+ * @version $Revision$
+ * $Id$
+ */
+public interface EFX10 {
+
+    // ALC properties
+    String ALC_EXT_EFX_NAME = "ALC_EXT_EFX";
+    int ALC_EFX_MAJOR_VERSION = 0x20001;
+    int ALC_EFX_MINOR_VERSION = 0x20002;
+    int ALC_MAX_AUXILIARY_SENDS = 0x20003;
+
+    // Listener properties
+    int AL_METERS_PER_UNIT = 0x20004;
+
+    // Source properties
+    int AL_DIRECT_FILTER = 0x20005;
+    int AL_AUXILIARY_SEND_FILTER = 0x20006;
+    int AL_AIR_ABSORPTION_FACTOR = 0x20007;
+    int AL_ROOM_ROLLOFF_FACTOR = 0x20008;
+    int AL_CONE_OUTER_GAINHF = 0x20009;
+    int AL_DIRECT_FILTER_GAINHF_AUTO = 0x2000A;
+    int AL_AUXILIARY_SEND_FILTER_GAIN_AUTO = 0x2000B;
+    int AL_AUXILIARY_SEND_FILTER_GAINHF_AUTO = 0x2000C;
+
+    // Auxiliary effect slot properties
+    int AL_EFFECTSLOT_EFFECT = 0x0001;
+    int AL_EFFECTSLOT_GAIN = 0x0002;
+    int AL_EFFECTSLOT_AUXILIARY_SEND_AUTO = 0x0003;
+    // NULL auxiliary slot ID to disable a source send
+    int AL_EFFECTSLOT_NULL = 0x0000;
+
+    // Effect parameters
+    // Reverb
+    int AL_REVERB_DENSITY = 0x0001;
+    int AL_REVERB_DIFFUSION = 0x0002;
+    int AL_REVERB_GAIN = 0x0003;
+    int AL_REVERB_GAINHF = 0x0004;
+    int AL_REVERB_DECAY_TIME = 0x0005;
+    int AL_REVERB_DECAY_HFRATIO = 0x0006;
+    int AL_REVERB_REFLECTIONS_GAIN = 0x0007;
+    int AL_REVERB_REFLECTIONS_DELAY = 0x0008;
+    int AL_REVERB_LATE_REVERB_GAIN = 0x0009;
+    int AL_REVERB_LATE_REVERB_DELAY = 0x000A;
+    int AL_REVERB_AIR_ABSORPTION_GAINHF = 0x000B;
+    int AL_REVERB_ROOM_ROLLOFF_FACTOR = 0x000C;
+    int AL_REVERB_DECAY_HFLIMIT = 0x000D;
+    // EAX Reverb
+    int AL_EAXREVERB_DENSITY = 0x0001;
+    int AL_EAXREVERB_DIFFUSION = 0x0002;
+    int AL_EAXREVERB_GAIN = 0x0003;
+    int AL_EAXREVERB_GAINHF = 0x0004;
+    int AL_EAXREVERB_GAINLF = 0x0005;
+    int AL_EAXREVERB_DECAY_TIME = 0x0006;
+    int AL_EAXREVERB_DECAY_HFRATIO = 0x0007;
+    int AL_EAXREVERB_DECAY_LFRATIO = 0x0008;
+    int AL_EAXREVERB_REFLECTIONS_GAIN = 0x0009;
+    int AL_EAXREVERB_REFLECTIONS_DELAY = 0x000A;
+    int AL_EAXREVERB_REFLECTIONS_PAN = 0x000B;
+    int AL_EAXREVERB_LATE_REVERB_GAIN = 0x000C;
+    int AL_EAXREVERB_LATE_REVERB_DELAY = 0x000D;
+    int AL_EAXREVERB_LATE_REVERB_PAN = 0x000E;
+    int AL_EAXREVERB_ECHO_TIME = 0x000F;
+    int AL_EAXREVERB_ECHO_DEPTH = 0x0010;
+    int AL_EAXREVERB_MODULATION_TIME = 0x0011;
+    int AL_EAXREVERB_MODULATION_DEPTH = 0x0012;
+    int AL_EAXREVERB_AIR_ABSORPTION_GAINHF = 0x0013;
+    int AL_EAXREVERB_HFREFERENCE = 0x0014;
+    int AL_EAXREVERB_LFREFERENCE = 0x0015;
+    int AL_EAXREVERB_ROOM_ROLLOFF_FACTOR = 0x0016;
+    int AL_EAXREVERB_DECAY_HFLIMIT = 0x0017;
+    // Chorus
+    int AL_CHORUS_WAVEFORM = 0x0001;
+    int AL_CHORUS_PHASE = 0x0002;
+    int AL_CHORUS_RATE = 0x0003;
+    int AL_CHORUS_DEPTH = 0x0004;
+    int AL_CHORUS_FEEDBACK = 0x0005;
+    int AL_CHORUS_DELAY = 0x0006;
+    // Distortion
+    int AL_DISTORTION_EDGE = 0x0001;
+    int AL_DISTORTION_GAIN = 0x0002;
+    int AL_DISTORTION_LOWPASS_CUTOFF = 0x0003;
+    int AL_DISTORTION_EQCENTER = 0x0004;
+    int AL_DISTORTION_EQBANDWIDTH = 0x0005;
+    // Echo
+    int AL_ECHO_DELAY = 0x0001;
+    int AL_ECHO_LRDELAY = 0x0002;
+    int AL_ECHO_DAMPING = 0x0003;
+    int AL_ECHO_FEEDBACK = 0x0004;
+    int AL_ECHO_SPREAD = 0x0005;
+    // Flanger
+    int AL_FLANGER_WAVEFORM = 0x0001;
+    int AL_FLANGER_PHASE = 0x0002;
+    int AL_FLANGER_RATE = 0x0003;
+    int AL_FLANGER_DEPTH = 0x0004;
+    int AL_FLANGER_FEEDBACK = 0x0005;
+    int AL_FLANGER_DELAY = 0x0006;
+    // Frequency shifter
+    int AL_FREQUENCY_SHIFTER_FREQUENCY = 0x0001;
+    int AL_FREQUENCY_SHIFTER_LEFT_DIRECTION = 0x0002;
+    int AL_FREQUENCY_SHIFTER_RIGHT_DIRECTION = 0x0003;
+    // Vocal morpher
+    int AL_VOCAL_MORPHER_PHONEMEA = 0x0001;
+    int AL_VOCAL_MORPHER_PHONEMEA_COARSE_TUNING = 0x0002;
+    int AL_VOCAL_MORPHER_PHONEMEB = 0x0003;
+    int AL_VOCAL_MORPHER_PHONEMEB_COARSE_TUNING = 0x0004;
+    int AL_VOCAL_MORPHER_WAVEFORM = 0x0005;
+    int AL_VOCAL_MORPHER_RATE = 0x0006;
+    // Pitch shifter
+    int AL_PITCH_SHIFTER_COARSE_TUNE = 0x0001;
+    int AL_PITCH_SHIFTER_FINE_TUNE = 0x0002;
+    // Ring modulator
+    int AL_RING_MODULATOR_FREQUENCY = 0x0001;
+    int AL_RING_MODULATOR_HIGHPASS_CUTOFF = 0x0002;
+    int AL_RING_MODULATOR_WAVEFORM = 0x0003;
+    // Autowah
+    int AL_AUTOWAH_ATTACK_TIME = 0x0001;
+    int AL_AUTOWAH_RELEASE_TIME = 0x0002;
+    int AL_AUTOWAH_RESONANCE = 0x0003;
+    int AL_AUTOWAH_PEAK_GAIN = 0x0004;
+    // Compressor
+    int AL_COMPRESSOR_ONOFF = 0x0001;
+    // Equalizer
+    int AL_EQUALIZER_LOW_GAIN = 0x0001;
+    int AL_EQUALIZER_LOW_CUTOFF = 0x0002;
+    int AL_EQUALIZER_MID1_GAIN = 0x0003;
+    int AL_EQUALIZER_MID1_CENTER = 0x0004;
+    int AL_EQUALIZER_MID1_WIDTH = 0x0005;
+    int AL_EQUALIZER_MID2_GAIN = 0x0006;
+    int AL_EQUALIZER_MID2_CENTER = 0x0007;
+    int AL_EQUALIZER_MID2_WIDTH = 0x0008;
+    int AL_EQUALIZER_HIGH_GAIN = 0x0009;
+    int AL_EQUALIZER_HIGH_CUTOFF = 0x000A;
+    // Effect type
+    int AL_EFFECT_FIRST_PARAMETER = 0x0000;
+    int AL_EFFECT_LAST_PARAMETER = 0x8000;
+    int AL_EFFECT_TYPE = 0x8001;
+    // Effect types, used with AL_EFFECT_TYPE
+    int AL_EFFECT_NULL = 0x0000;
+    int AL_EFFECT_REVERB = 0x0001;
+    int AL_EFFECT_CHORUS = 0x0002;
+    int AL_EFFECT_DISTORTION = 0x0003;
+    int AL_EFFECT_ECHO = 0x0004;
+    int AL_EFFECT_FLANGER = 0x0005;
+    int AL_EFFECT_FREQUENCY_SHIFTER = 0x0006;
+    int AL_EFFECT_VOCAL_MORPHER = 0x0007;
+    int AL_EFFECT_PITCH_SHIFTER = 0x0008;
+    int AL_EFFECT_RING_MODULATOR = 0x0009;
+    int AL_EFFECT_AUTOWAH = 0x000A;
+    int AL_EFFECT_COMPRESSOR = 0x000B;
+    int AL_EFFECT_EQUALIZER = 0x000C;
+    int AL_EFFECT_EAXREVERB = 0x8000;
+
+    // Filter properties
+    // Lowpass
+    int AL_LOWPASS_GAIN = 0x0001;
+    int AL_LOWPASS_GAINHF = 0x0002;
+    // Highpass
+    int AL_HIGHPASS_GAIN = 0x0001;
+    int AL_HIGHPASS_GAINLF = 0x0002;
+    // Bandpass
+    int AL_BANDPASS_GAIN = 0x0001;
+    int AL_BANDPASS_GAINLF = 0x0002;
+    int AL_BANDPASS_GAINHF = 0x0003;
+    // Filter type
+    int AL_FILTER_FIRST_PARAMETER = 0x0000;
+    int AL_FILTER_LAST_PARAMETER = 0x8000;
+    int AL_FILTER_TYPE = 0x8001;
+    // Filter types, used with the AL_FILTER_TYPE property
+    int AL_FILTER_NULL = 0x0000;
+    int AL_FILTER_LOWPASS = 0x0001;
+    int AL_FILTER_HIGHPASS = 0x0002;
+    int AL_FILTER_BANDPASS = 0x0003;
+
+    // Auxiliary effect slot object functions
+    @ALvoid
+    void alGenAuxiliaryEffectSlots(@AutoSize("auxiliaryeffectslots") @ALsizei int n, @OutParameter @ALuint IntBuffer auxiliaryeffectslots);
+
+    @Alternate(value = "alGenAuxiliaryEffectSlots", nativeAlt = true)
+    @ALvoid
+    void alGenAuxiliaryEffectSlots2(@Constant("1") @ALsizei int n, @Result @ALuint int auxiliaryeffectslot);
+
+    @ALvoid
+    void alDeleteAuxiliaryEffectSlots(@AutoSize("auxiliaryeffectslots") @ALsizei int n, @OutParameter @ALuint IntBuffer auxiliaryeffectslots);
+
+    @Alternate(value = "alDeleteAuxiliaryEffectSlots", nativeAlt = true)
+    @ALvoid
+    void alDeleteAuxiliaryEffectSlots2(@Constant("1") @ALsizei int n, @Indirect @ALuint int auxiliaryeffectslot);
+
+    boolean alIsAuxiliaryEffectSlot(@ALuint int auxiliaryeffectslot);
+
+    @ALvoid
+    void alAuxiliaryEffectSloti(@ALuint int auxiliaryeffectslot, @ALenum int param, int value);
+
+    @StripPostfix("values")
+    @ALvoid
+    void alAuxiliaryEffectSlotiv(@ALuint int auxiliaryeffectslot, @ALenum int param, @Check("1") @Const IntBuffer values);
+
+    @ALvoid
+    void alAuxiliaryEffectSlotf(@ALuint int auxiliaryeffectslot, @ALenum int param, float value);
+
+    @StripPostfix("values")
+    @ALvoid
+    void alAuxiliaryEffectSlotfv(@ALuint int auxiliaryeffectslot, @ALenum int param, @Check("1") @Const FloatBuffer values);
+
+    @ALvoid
+    void alGetAuxiliaryEffectSloti(@ALuint int auxiliaryeffectslot, @ALenum int param, @Result int value);
+
+    @StripPostfix("intdata")
+    @ALvoid
+    void alGetAuxiliaryEffectSlotiv(@ALuint int auxiliaryeffectslot, @ALenum int param, @OutParameter @Check("1") IntBuffer intdata);
+
+    @ALvoid
+    void alGetAuxiliaryEffectSlotf(@ALuint int auxiliaryeffectslot, @ALenum int param, @Result float value);
+
+    @StripPostfix("floatdata")
+    @ALvoid
+    void alGetAuxiliaryEffectSlotfv(@ALuint int auxiliaryeffectslot, @ALenum int param, @OutParameter @Check("1") FloatBuffer floatdata);
+
+    // Effect object functions
+    @ALvoid
+    void alGenEffects(@AutoSize("effects") @ALsizei int n, @OutParameter @ALuint IntBuffer effects);
+
+    @Alternate(value = "alGenEffects", nativeAlt = true)
+    @ALvoid
+    void alGenEffects2(@Constant("1") @ALsizei int n, @Result @ALuint int effect);
+
+    @ALvoid
+    void alDeleteEffects(@AutoSize("effects") @ALsizei int n, @OutParameter @ALuint IntBuffer effects);
+
+    @Alternate(value = "alDeleteEffects", nativeAlt = true)
+    @ALvoid
+    void alDeleteEffects2(@Constant("1") @ALsizei int n, @Indirect @ALuint int effect);
+
+    boolean alIsEffect(@ALuint int effect);
+
+    @ALvoid
+    void alEffecti(@ALuint int effect, @ALenum int param, int value);
+
+    @StripPostfix("values")
+    @ALvoid
+    void alEffectiv(@ALuint int effect, @ALenum int param, @Check("1") @Const IntBuffer values);
+
+    @ALvoid
+    void alEffectf(@ALuint int effect, @ALenum int param, float value);
+
+    @StripPostfix("values")
+    @ALvoid
+    void alEffectfv(@ALuint int effect, @ALenum int param, @Check("1") @Const FloatBuffer values);
+
+    @ALvoid
+    void alGetEffecti(@ALuint int effect, @ALenum int param, @Result int value);
+
+    @StripPostfix("intdata")
+    @ALvoid
+    void alGetEffectiv(@ALuint int effect, @ALenum int param, @OutParameter @Check("1") IntBuffer intdata);
+
+    @ALvoid
+    void alGetEffectf(@ALuint int effect, @ALenum int param, @Result float value);
+
+    @StripPostfix("floatdata")
+    @ALvoid
+    void alGetEffectfv(@ALuint int effect, @ALenum int param, @OutParameter @Check("1") FloatBuffer floatdata);
+
+    // Filter object functions
+    @ALvoid
+    void alGenFilters(@AutoSize("filters") @ALsizei int n, @OutParameter @ALuint IntBuffer filters);
+
+    @Alternate(value = "alGenFilters", nativeAlt = true)
+    @ALvoid
+    void alGenFilters2(@Constant("1") @ALsizei int n, @Result @ALuint int filter);
+
+    @ALvoid
+    void alDeleteFilters(@AutoSize("filters") @ALsizei int n, @OutParameter @ALuint IntBuffer filters);
+
+    @Alternate(value = "alDeleteFilters", nativeAlt = true)
+    @ALvoid
+    void alDeleteFilters2(@Constant("1") @ALsizei int n, @Indirect @ALuint int filter);
+
+    boolean alIsFilter(@ALuint int filter);
+
+    @ALvoid
+    void alFilteri(@ALuint int filter, @ALenum int param, int value);
+
+    @StripPostfix("values")
+    @ALvoid
+    void alFilteriv(@ALuint int filter, @ALenum int param, @Check("1") @Const IntBuffer values);
+
+    @ALvoid
+    void alFilterf(@ALuint int filter, @ALenum int param, float value);
+
+    @StripPostfix("values")
+    @ALvoid
+    void alFilterfv(@ALuint int filter, @ALenum int param, @Check("1") @Const FloatBuffer values);
+
+    @ALvoid
+    void alGetFilteri(@ALuint int filter, @ALenum int param, @Result int value);
+
+    @StripPostfix("intdata")
+    @ALvoid
+    void alGetFilteriv(@ALuint int filter, @ALenum int param, @OutParameter @Check("1") IntBuffer intdata);
+
+    @ALvoid
+    void alGetFilterf(@ALuint int filter, @ALenum int param, @Result float value);
+
+    @StripPostfix("floatdata")
+    @ALvoid
+    void alGetFilterfv(@ALuint int filter, @ALenum int param, @OutParameter @Check("1") FloatBuffer floatdata);
+
+    // Source property value ranges and defaults
+    float AL_MIN_AIR_ABSORPTION_FACTOR = 0.0f;
+    float AL_MAX_AIR_ABSORPTION_FACTOR = 10.0f;
+    float AL_DEFAULT_AIR_ABSORPTION_FACTOR = 0.0f;
+    float AL_MIN_ROOM_ROLLOFF_FACTOR = 0.0f;
+    float AL_MAX_ROOM_ROLLOFF_FACTOR = 10.0f;
+    float AL_DEFAULT_ROOM_ROLLOFF_FACTOR = 0.0f;
+    float AL_MIN_CONE_OUTER_GAINHF = 0.0f;
+    float AL_MAX_CONE_OUTER_GAINHF = 1.0f;
+    float AL_DEFAULT_CONE_OUTER_GAINHF = 1.0f;
+    int AL_MIN_DIRECT_FILTER_GAINHF_AUTO = AL10.AL_FALSE;
+    int AL_MAX_DIRECT_FILTER_GAINHF_AUTO = AL10.AL_TRUE;
+    int AL_DEFAULT_DIRECT_FILTER_GAINHF_AUTO = AL10.AL_TRUE;
+    int AL_MIN_AUXILIARY_SEND_FILTER_GAIN_AUTO = AL10.AL_FALSE;
+    int AL_MAX_AUXILIARY_SEND_FILTER_GAIN_AUTO = AL10.AL_TRUE;
+    int AL_DEFAULT_AUXILIARY_SEND_FILTER_GAIN_AUTO = AL10.AL_TRUE;
+    int AL_MIN_AUXILIARY_SEND_FILTER_GAINHF_AUTO = AL10.AL_FALSE;
+    int AL_MAX_AUXILIARY_SEND_FILTER_GAINHF_AUTO = AL10.AL_TRUE;
+    int AL_DEFAULT_AUXILIARY_SEND_FILTER_GAINHF_AUTO = AL10.AL_TRUE;
+
+    // Listener property value ranges and defaults
+    float AL_MIN_METERS_PER_UNIT = Float.MIN_VALUE;
+    float AL_MAX_METERS_PER_UNIT = Float.MAX_VALUE;
+    float AL_DEFAULT_METERS_PER_UNIT = 1.0f;
+
+    // Effect parameter ranges and defaults
+    // Reverb
+    float AL_REVERB_MIN_DENSITY = 0.0f;
+    float AL_REVERB_MAX_DENSITY = 1.0f;
+    float AL_REVERB_DEFAULT_DENSITY = 1.0f;
+    float AL_REVERB_MIN_DIFFUSION = 0.0f;
+    float AL_REVERB_MAX_DIFFUSION = 1.0f;
+    float AL_REVERB_DEFAULT_DIFFUSION = 1.0f;
+    float AL_REVERB_MIN_GAIN = 0.0f;
+    float AL_REVERB_MAX_GAIN = 1.0f;
+    float AL_REVERB_DEFAULT_GAIN = 0.32f;
+    float AL_REVERB_MIN_GAINHF = 0.0f;
+    float AL_REVERB_MAX_GAINHF = 1.0f;
+    float AL_REVERB_DEFAULT_GAINHF = 0.89f;
+    float AL_REVERB_MIN_DECAY_TIME = 0.1f;
+    float AL_REVERB_MAX_DECAY_TIME = 20.0f;
+    float AL_REVERB_DEFAULT_DECAY_TIME = 1.49f;
+    float AL_REVERB_MIN_DECAY_HFRATIO = 0.1f;
+    float AL_REVERB_MAX_DECAY_HFRATIO = 2.0f;
+    float AL_REVERB_DEFAULT_DECAY_HFRATIO = 0.83f;
+    float AL_REVERB_MIN_REFLECTIONS_GAIN = 0.0f;
+    float AL_REVERB_MAX_REFLECTIONS_GAIN = 3.16f;
+    float AL_REVERB_DEFAULT_REFLECTIONS_GAIN = 0.05f;
+    float AL_REVERB_MIN_REFLECTIONS_DELAY = 0.0f;
+    float AL_REVERB_MAX_REFLECTIONS_DELAY = 0.3f;
+    float AL_REVERB_DEFAULT_REFLECTIONS_DELAY = 0.007f;
+    float AL_REVERB_MIN_LATE_REVERB_GAIN = 0.0f;
+    float AL_REVERB_MAX_LATE_REVERB_GAIN = 10.0f;
+    float AL_REVERB_DEFAULT_LATE_REVERB_GAIN = 1.26f;
+    float AL_REVERB_MIN_LATE_REVERB_DELAY = 0.0f;
+    float AL_REVERB_MAX_LATE_REVERB_DELAY = 0.1f;
+    float AL_REVERB_DEFAULT_LATE_REVERB_DELAY = 0.011f;
+    float AL_REVERB_MIN_AIR_ABSORPTION_GAINHF = 0.892f;
+    float AL_REVERB_MAX_AIR_ABSORPTION_GAINHF = 1.0f;
+    float AL_REVERB_DEFAULT_AIR_ABSORPTION_GAINHF = 0.994f;
+    float AL_REVERB_MIN_ROOM_ROLLOFF_FACTOR = 0.0f;
+    float AL_REVERB_MAX_ROOM_ROLLOFF_FACTOR = 10.0f;
+    float AL_REVERB_DEFAULT_ROOM_ROLLOFF_FACTOR = 0.0f;
+    int AL_REVERB_MIN_DECAY_HFLIMIT = AL10.AL_FALSE;
+    int AL_REVERB_MAX_DECAY_HFLIMIT = AL10.AL_TRUE;
+    int AL_REVERB_DEFAULT_DECAY_HFLIMIT = AL10.AL_TRUE;
+    // EAX reverb
+    float AL_EAXREVERB_MIN_DENSITY = 0.0f;
+    float AL_EAXREVERB_MAX_DENSITY = 1.0f;
+    float AL_EAXREVERB_DEFAULT_DENSITY = 1.0f;
+    float AL_EAXREVERB_MIN_DIFFUSION = 0.0f;
+    float AL_EAXREVERB_MAX_DIFFUSION = 1.0f;
+    float AL_EAXREVERB_DEFAULT_DIFFUSION = 1.0f;
+    float AL_EAXREVERB_MIN_GAIN = 0.0f;
+    float AL_EAXREVERB_MAX_GAIN = 1.0f;
+    float AL_EAXREVERB_DEFAULT_GAIN = 0.32f;
+    float AL_EAXREVERB_MIN_GAINHF = 0.0f;
+    float AL_EAXREVERB_MAX_GAINHF = 1.0f;
+    float AL_EAXREVERB_DEFAULT_GAINHF = 0.89f;
+    float AL_EAXREVERB_MIN_GAINLF = 0.0f;
+    float AL_EAXREVERB_MAX_GAINLF = 1.0f;
+    float AL_EAXREVERB_DEFAULT_GAINLF = 1.0f;
+    float AL_EAXREVERB_MIN_DECAY_TIME = 0.1f;
+    float AL_EAXREVERB_MAX_DECAY_TIME = 20.0f;
+    float AL_EAXREVERB_DEFAULT_DECAY_TIME = 1.49f;
+    float AL_EAXREVERB_MIN_DECAY_HFRATIO = 0.1f;
+    float AL_EAXREVERB_MAX_DECAY_HFRATIO = 2.0f;
+    float AL_EAXREVERB_DEFAULT_DECAY_HFRATIO = 0.83f;
+    float AL_EAXREVERB_MIN_DECAY_LFRATIO = 0.1f;
+    float AL_EAXREVERB_MAX_DECAY_LFRATIO = 2.0f;
+    float AL_EAXREVERB_DEFAULT_DECAY_LFRATIO = 1.0f;
+    float AL_EAXREVERB_MIN_REFLECTIONS_GAIN = 0.0f;
+    float AL_EAXREVERB_MAX_REFLECTIONS_GAIN = 3.16f;
+    float AL_EAXREVERB_DEFAULT_REFLECTIONS_GAIN = 0.05f;
+    float AL_EAXREVERB_MIN_REFLECTIONS_DELAY = 0.0f;
+    float AL_EAXREVERB_MAX_REFLECTIONS_DELAY = 0.3f;
+    float AL_EAXREVERB_DEFAULT_REFLECTIONS_DELAY = 0.007f;
+    float AL_EAXREVERB_DEFAULT_REFLECTIONS_PAN_XYZ = 0.0f;
+    float AL_EAXREVERB_MIN_LATE_REVERB_GAIN = 0.0f;
+    float AL_EAXREVERB_MAX_LATE_REVERB_GAIN = 10.0f;
+    float AL_EAXREVERB_DEFAULT_LATE_REVERB_GAIN = 1.26f;
+    float AL_EAXREVERB_MIN_LATE_REVERB_DELAY = 0.0f;
+    float AL_EAXREVERB_MAX_LATE_REVERB_DELAY = 0.1f;
+    float AL_EAXREVERB_DEFAULT_LATE_REVERB_DELAY = 0.011f;
+    float AL_EAXREVERB_DEFAULT_LATE_REVERB_PAN_XYZ = 0.0f;
+    float AL_EAXREVERB_MIN_ECHO_TIME = 0.075f;
+    float AL_EAXREVERB_MAX_ECHO_TIME = 0.25f;
+    float AL_EAXREVERB_DEFAULT_ECHO_TIME = 0.25f;
+    float AL_EAXREVERB_MIN_ECHO_DEPTH = 0.0f;
+    float AL_EAXREVERB_MAX_ECHO_DEPTH = 1.0f;
+    float AL_EAXREVERB_DEFAULT_ECHO_DEPTH = 0.0f;
+    float AL_EAXREVERB_MIN_MODULATION_TIME = 0.04f;
+    float AL_EAXREVERB_MAX_MODULATION_TIME = 4.0f;
+    float AL_EAXREVERB_DEFAULT_MODULATION_TIME = 0.25f;
+    float AL_EAXREVERB_MIN_MODULATION_DEPTH = 0.0f;
+    float AL_EAXREVERB_MAX_MODULATION_DEPTH = 1.0f;
+    float AL_EAXREVERB_DEFAULT_MODULATION_DEPTH = 0.0f;
+    float AL_EAXREVERB_MIN_AIR_ABSORPTION_GAINHF = 0.892f;
+    float AL_EAXREVERB_MAX_AIR_ABSORPTION_GAINHF = 1.0f;
+    float AL_EAXREVERB_DEFAULT_AIR_ABSORPTION_GAINHF = 0.994f;
+    float AL_EAXREVERB_MIN_HFREFERENCE = 1000.0f;
+    float AL_EAXREVERB_MAX_HFREFERENCE = 20000.0f;
+    float AL_EAXREVERB_DEFAULT_HFREFERENCE = 5000.0f;
+    float AL_EAXREVERB_MIN_LFREFERENCE = 20.0f;
+    float AL_EAXREVERB_MAX_LFREFERENCE = 1000.0f;
+    float AL_EAXREVERB_DEFAULT_LFREFERENCE = 250.0f;
+    float AL_EAXREVERB_MIN_ROOM_ROLLOFF_FACTOR = 0.0f;
+    float AL_EAXREVERB_MAX_ROOM_ROLLOFF_FACTOR = 10.0f;
+    float AL_EAXREVERB_DEFAULT_ROOM_ROLLOFF_FACTOR = 0.0f;
+    int AL_EAXREVERB_MIN_DECAY_HFLIMIT = AL10.AL_FALSE;
+    int AL_EAXREVERB_MAX_DECAY_HFLIMIT = AL10.AL_TRUE;
+    int AL_EAXREVERB_DEFAULT_DECAY_HFLIMIT = AL10.AL_TRUE;
+    // Chorus
+    int AL_CHORUS_WAVEFORM_SINUSOID = 0;
+    int AL_CHORUS_WAVEFORM_TRIANGLE = 1;
+    int AL_CHORUS_MIN_WAVEFORM = 0;
+    int AL_CHORUS_MAX_WAVEFORM = 1;
+    int AL_CHORUS_DEFAULT_WAVEFORM = 1;
+    int AL_CHORUS_MIN_PHASE = -180;
+    int AL_CHORUS_MAX_PHASE = 180;
+    int AL_CHORUS_DEFAULT_PHASE = 90;
+    float AL_CHORUS_MIN_RATE = 0.0f;
+    float AL_CHORUS_MAX_RATE = 10.0f;
+    float AL_CHORUS_DEFAULT_RATE = 1.1f;
+    float AL_CHORUS_MIN_DEPTH = 0.0f;
+    float AL_CHORUS_MAX_DEPTH = 1.0f;
+    float AL_CHORUS_DEFAULT_DEPTH = 0.1f;
+    float AL_CHORUS_MIN_FEEDBACK = -1.0f;
+    float AL_CHORUS_MAX_FEEDBACK = 1.0f;
+    float AL_CHORUS_DEFAULT_FEEDBACK = 0.25f;
+    float AL_CHORUS_MIN_DELAY = 0.0f;
+    float AL_CHORUS_MAX_DELAY = 0.016f;
+    float AL_CHORUS_DEFAULT_DELAY = 0.016f;
+    // Distortion
+    float AL_DISTORTION_MIN_EDGE = 0.0f;
+    float AL_DISTORTION_MAX_EDGE = 1.0f;
+    float AL_DISTORTION_DEFAULT_EDGE = 0.2f;
+    float AL_DISTORTION_MIN_GAIN = 0.01f;
+    float AL_DISTORTION_MAX_GAIN = 1.0f;
+    float AL_DISTORTION_DEFAULT_GAIN = 0.05f;
+    float AL_DISTORTION_MIN_LOWPASS_CUTOFF = 80.0f;
+    float AL_DISTORTION_MAX_LOWPASS_CUTOFF = 24000.0f;
+    float AL_DISTORTION_DEFAULT_LOWPASS_CUTOFF = 8000.0f;
+    float AL_DISTORTION_MIN_EQCENTER = 80.0f;
+    float AL_DISTORTION_MAX_EQCENTER = 24000.0f;
+    float AL_DISTORTION_DEFAULT_EQCENTER = 3600.0f;
+    float AL_DISTORTION_MIN_EQBANDWIDTH = 80.0f;
+    float AL_DISTORTION_MAX_EQBANDWIDTH = 24000.0f;
+    float AL_DISTORTION_DEFAULT_EQBANDWIDTH = 3600.0f;
+    // Echo
+    float AL_ECHO_MIN_DELAY = 0.0f;
+    float AL_ECHO_MAX_DELAY = 0.207f;
+    float AL_ECHO_DEFAULT_DELAY = 0.1f;
+    float AL_ECHO_MIN_LRDELAY = 0.0f;
+    float AL_ECHO_MAX_LRDELAY = 0.404f;
+    float AL_ECHO_DEFAULT_LRDELAY = 0.1f;
+    float AL_ECHO_MIN_DAMPING = 0.0f;
+    float AL_ECHO_MAX_DAMPING = 0.99f;
+    float AL_ECHO_DEFAULT_DAMPING = 0.5f;
+    float AL_ECHO_MIN_FEEDBACK = 0.0f;
+    float AL_ECHO_MAX_FEEDBACK = 1.0f;
+    float AL_ECHO_DEFAULT_FEEDBACK = 0.5f;
+    float AL_ECHO_MIN_SPREAD = -1.0f;
+    float AL_ECHO_MAX_SPREAD = 1.0f;
+    float AL_ECHO_DEFAULT_SPREAD = -1.0f;
+    // Flanger
+    int AL_FLANGER_WAVEFORM_SINUSOID = 0;
+    int AL_FLANGER_WAVEFORM_TRIANGLE = 1;
+    int AL_FLANGER_MIN_WAVEFORM = 0;
+    int AL_FLANGER_MAX_WAVEFORM = 1;
+    int AL_FLANGER_DEFAULT_WAVEFORM = 1;
+    int AL_FLANGER_MIN_PHASE = -180;
+    int AL_FLANGER_MAX_PHASE = 180;
+    int AL_FLANGER_DEFAULT_PHASE = 0;
+    float AL_FLANGER_MIN_RATE = 0.0f;
+    float AL_FLANGER_MAX_RATE = 10.0f;
+    float AL_FLANGER_DEFAULT_RATE = 0.27f;
+    float AL_FLANGER_MIN_DEPTH = 0.0f;
+    float AL_FLANGER_MAX_DEPTH = 1.0f;
+    float AL_FLANGER_DEFAULT_DEPTH = 1.0f;
+    float AL_FLANGER_MIN_FEEDBACK = -1.0f;
+    float AL_FLANGER_MAX_FEEDBACK = 1.0f;
+    float AL_FLANGER_DEFAULT_FEEDBACK = -0.5f;
+    float AL_FLANGER_MIN_DELAY = 0.0f;
+    float AL_FLANGER_MAX_DELAY = 0.004f;
+    float AL_FLANGER_DEFAULT_DELAY = 0.002f;
+    // Frequency shifter
+    float AL_FREQUENCY_SHIFTER_MIN_FREQUENCY = 0.0f;
+    float AL_FREQUENCY_SHIFTER_MAX_FREQUENCY = 24000.0f;
+    float AL_FREQUENCY_SHIFTER_DEFAULT_FREQUENCY = 0.0f;
+    int AL_FREQUENCY_SHIFTER_MIN_LEFT_DIRECTION = 0;
+    int AL_FREQUENCY_SHIFTER_MAX_LEFT_DIRECTION = 2;
+    int AL_FREQUENCY_SHIFTER_DEFAULT_LEFT_DIRECTION = 0;
+    int AL_FREQUENCY_SHIFTER_DIRECTION_DOWN = 0;
+    int AL_FREQUENCY_SHIFTER_DIRECTION_UP = 1;
+    int AL_FREQUENCY_SHIFTER_DIRECTION_OFF = 2;
+    int AL_FREQUENCY_SHIFTER_MIN_RIGHT_DIRECTION = 0;
+    int AL_FREQUENCY_SHIFTER_MAX_RIGHT_DIRECTION = 2;
+    int AL_FREQUENCY_SHIFTER_DEFAULT_RIGHT_DIRECTION = 0;
+    // Vocal morpher
+    int AL_VOCAL_MORPHER_MIN_PHONEMEA = 0;
+    int AL_VOCAL_MORPHER_MAX_PHONEMEA = 29;
+    int AL_VOCAL_MORPHER_DEFAULT_PHONEMEA = 0;
+    int AL_VOCAL_MORPHER_MIN_PHONEMEA_COARSE_TUNING = -24;
+    int AL_VOCAL_MORPHER_MAX_PHONEMEA_COARSE_TUNING = 24;
+    int AL_VOCAL_MORPHER_DEFAULT_PHONEMEA_COARSE_TUNING = 0;
+    int AL_VOCAL_MORPHER_MIN_PHONEMEB = 0;
+    int AL_VOCAL_MORPHER_MAX_PHONEMEB = 29;
+    int AL_VOCAL_MORPHER_DEFAULT_PHONEMEB = 10;
+    int AL_VOCAL_MORPHER_MIN_PHONEMEB_COARSE_TUNING = -24;
+    int AL_VOCAL_MORPHER_MAX_PHONEMEB_COARSE_TUNING = 24;
+    int AL_VOCAL_MORPHER_DEFAULT_PHONEMEB_COARSE_TUNING = 0;
+    int AL_VOCAL_MORPHER_PHONEME_A = 0;
+    int AL_VOCAL_MORPHER_PHONEME_E = 1;
+    int AL_VOCAL_MORPHER_PHONEME_I = 2;
+    int AL_VOCAL_MORPHER_PHONEME_O = 3;
+    int AL_VOCAL_MORPHER_PHONEME_U = 4;
+    int AL_VOCAL_MORPHER_PHONEME_AA = 5;
+    int AL_VOCAL_MORPHER_PHONEME_AE = 6;
+    int AL_VOCAL_MORPHER_PHONEME_AH = 7;
+    int AL_VOCAL_MORPHER_PHONEME_AO = 8;
+    int AL_VOCAL_MORPHER_PHONEME_EH = 9;
+    int AL_VOCAL_MORPHER_PHONEME_ER = 10;
+    int AL_VOCAL_MORPHER_PHONEME_IH = 11;
+    int AL_VOCAL_MORPHER_PHONEME_IY = 12;
+    int AL_VOCAL_MORPHER_PHONEME_UH = 13;
+    int AL_VOCAL_MORPHER_PHONEME_UW = 14;
+    int AL_VOCAL_MORPHER_PHONEME_B = 15;
+    int AL_VOCAL_MORPHER_PHONEME_D = 16;
+    int AL_VOCAL_MORPHER_PHONEME_F = 17;
+    int AL_VOCAL_MORPHER_PHONEME_G = 18;
+    int AL_VOCAL_MORPHER_PHONEME_J = 19;
+    int AL_VOCAL_MORPHER_PHONEME_K = 20;
+    int AL_VOCAL_MORPHER_PHONEME_L = 21;
+    int AL_VOCAL_MORPHER_PHONEME_M = 22;
+    int AL_VOCAL_MORPHER_PHONEME_N = 23;
+    int AL_VOCAL_MORPHER_PHONEME_P = 24;
+    int AL_VOCAL_MORPHER_PHONEME_R = 25;
+    int AL_VOCAL_MORPHER_PHONEME_S = 26;
+    int AL_VOCAL_MORPHER_PHONEME_T = 27;
+    int AL_VOCAL_MORPHER_PHONEME_V = 28;
+    int AL_VOCAL_MORPHER_PHONEME_Z = 29;
+    int AL_VOCAL_MORPHER_WAVEFORM_SINUSOID = 0;
+    int AL_VOCAL_MORPHER_WAVEFORM_TRIANGLE = 1;
+    int AL_VOCAL_MORPHER_WAVEFORM_SAWTOOTH = 2;
+    int AL_VOCAL_MORPHER_MIN_WAVEFORM = 0;
+    int AL_VOCAL_MORPHER_MAX_WAVEFORM = 2;
+    int AL_VOCAL_MORPHER_DEFAULT_WAVEFORM = 0;
+    float AL_VOCAL_MORPHER_MIN_RATE = 0.0f;
+    float AL_VOCAL_MORPHER_MAX_RATE = 10.0f;
+    float AL_VOCAL_MORPHER_DEFAULT_RATE = 1.41f;
+    // Pitch shifter
+    int AL_PITCH_SHIFTER_MIN_COARSE_TUNE = -12;
+    int AL_PITCH_SHIFTER_MAX_COARSE_TUNE = 12;
+    int AL_PITCH_SHIFTER_DEFAULT_COARSE_TUNE = 12;
+    int AL_PITCH_SHIFTER_MIN_FINE_TUNE = -50;
+    int AL_PITCH_SHIFTER_MAX_FINE_TUNE = 50;
+    int AL_PITCH_SHIFTER_DEFAULT_FINE_TUNE = 0;
+    // Ring modulator
+    float AL_RING_MODULATOR_MIN_FREQUENCY = 0.0f;
+    float AL_RING_MODULATOR_MAX_FREQUENCY = 8000.0f;
+    float AL_RING_MODULATOR_DEFAULT_FREQUENCY = 440.0f;
+    float AL_RING_MODULATOR_MIN_HIGHPASS_CUTOFF = 0.0f;
+    float AL_RING_MODULATOR_MAX_HIGHPASS_CUTOFF = 24000.0f;
+    float AL_RING_MODULATOR_DEFAULT_HIGHPASS_CUTOFF = 800.0f;
+    int AL_RING_MODULATOR_SINUSOID = 0;
+    int AL_RING_MODULATOR_SAWTOOTH = 1;
+    int AL_RING_MODULATOR_SQUARE = 2;
+    int AL_RING_MODULATOR_MIN_WAVEFORM = 0;
+    int AL_RING_MODULATOR_MAX_WAVEFORM = 2;
+    int AL_RING_MODULATOR_DEFAULT_WAVEFORM = 0;
+    // Autowah
+    float AL_AUTOWAH_MIN_ATTACK_TIME = 0.0001f;
+    float AL_AUTOWAH_MAX_ATTACK_TIME = 1.0f;
+    float AL_AUTOWAH_DEFAULT_ATTACK_TIME = 0.06f;
+    float AL_AUTOWAH_MIN_RELEASE_TIME = 0.0001f;
+    float AL_AUTOWAH_MAX_RELEASE_TIME = 1.0f;
+    float AL_AUTOWAH_DEFAULT_RELEASE_TIME = 0.06f;
+    float AL_AUTOWAH_MIN_RESONANCE = 2.0f;
+    float AL_AUTOWAH_MAX_RESONANCE = 1000.0f;
+    float AL_AUTOWAH_DEFAULT_RESONANCE = 1000.0f;
+    float AL_AUTOWAH_MIN_PEAK_GAIN = 0.00003f;
+    float AL_AUTOWAH_MAX_PEAK_GAIN = 31621.0f;
+    float AL_AUTOWAH_DEFAULT_PEAK_GAIN = 11.22f;
+    // Compressor
+    int AL_COMPRESSOR_MIN_ONOFF = 0;
+    int AL_COMPRESSOR_MAX_ONOFF = 1;
+    int AL_COMPRESSOR_DEFAULT_ONOFF = 1;
+    // Equalizer
+    float AL_EQUALIZER_MIN_LOW_GAIN = 0.126f;
+    float AL_EQUALIZER_MAX_LOW_GAIN = 7.943f;
+    float AL_EQUALIZER_DEFAULT_LOW_GAIN = 1.0f;
+    float AL_EQUALIZER_MIN_LOW_CUTOFF = 50.0f;
+    float AL_EQUALIZER_MAX_LOW_CUTOFF = 800.0f;
+    float AL_EQUALIZER_DEFAULT_LOW_CUTOFF = 200.0f;
+    float AL_EQUALIZER_MIN_MID1_GAIN = 0.126f;
+    float AL_EQUALIZER_MAX_MID1_GAIN = 7.943f;
+    float AL_EQUALIZER_DEFAULT_MID1_GAIN = 1.0f;
+    float AL_EQUALIZER_MIN_MID1_CENTER = 200.0f;
+    float AL_EQUALIZER_MAX_MID1_CENTER = 3000.0f;
+    float AL_EQUALIZER_DEFAULT_MID1_CENTER = 500.0f;
+    float AL_EQUALIZER_MIN_MID1_WIDTH = 0.01f;
+    float AL_EQUALIZER_MAX_MID1_WIDTH = 1.0f;
+    float AL_EQUALIZER_DEFAULT_MID1_WIDTH = 1.0f;
+    float AL_EQUALIZER_MIN_MID2_GAIN = 0.126f;
+    float AL_EQUALIZER_MAX_MID2_GAIN = 7.943f;
+    float AL_EQUALIZER_DEFAULT_MID2_GAIN = 1.0f;
+    float AL_EQUALIZER_MIN_MID2_CENTER = 1000.0f;
+    float AL_EQUALIZER_MAX_MID2_CENTER = 8000.0f;
+    float AL_EQUALIZER_DEFAULT_MID2_CENTER = 3000.0f;
+    float AL_EQUALIZER_MIN_MID2_WIDTH = 0.01f;
+    float AL_EQUALIZER_MAX_MID2_WIDTH = 1.0f;
+    float AL_EQUALIZER_DEFAULT_MID2_WIDTH = 1.0f;
+    float AL_EQUALIZER_MIN_HIGH_GAIN = 0.126f;
+    float AL_EQUALIZER_MAX_HIGH_GAIN = 7.943f;
+    float AL_EQUALIZER_DEFAULT_HIGH_GAIN = 1.0f;
+    float AL_EQUALIZER_MIN_HIGH_CUTOFF = 4000.0f;
+    float AL_EQUALIZER_MAX_HIGH_CUTOFF = 16000.0f;
+    float AL_EQUALIZER_DEFAULT_HIGH_CUTOFF = 6000.0f;
+
+    // Filter parameter ranges and defaults
+    // Lowpass
+    float LOWPASS_MIN_GAIN = 0.0f;
+    float LOWPASS_MAX_GAIN = 1.0f;
+    float LOWPASS_DEFAULT_GAIN = 1.0f;
+    float LOWPASS_MIN_GAINHF = 0.0f;
+    float LOWPASS_MAX_GAINHF = 1.0f;
+    float LOWPASS_DEFAULT_GAINHF = 1.0f;
+    // Highpass
+    float HIGHPASS_MIN_GAIN = 0.0f;
+    float HIGHPASS_MAX_GAIN = 1.0f;
+    float HIGHPASS_DEFAULT_GAIN = 1.0f;
+    float HIGHPASS_MIN_GAINLF = 0.0f;
+    float HIGHPASS_MAX_GAINLF = 1.0f;
+    float HIGHPASS_DEFAULT_GAINLF = 1.0f;
+    // Bandpass
+    float BANDPASS_MIN_GAIN = 0.0f;
+    float BANDPASS_MAX_GAIN = 1.0f;
+    float BANDPASS_DEFAULT_GAIN = 1.0f;
+    float BANDPASS_MIN_GAINHF = 0.0f;
+    float BANDPASS_MAX_GAINHF = 1.0f;
+    float BANDPASS_DEFAULT_GAINHF = 1.0f;
+    float BANDPASS_MIN_GAINLF = 0.0f;
+    float BANDPASS_MAX_GAINLF = 1.0f;
+    float BANDPASS_DEFAULT_GAINLF = 1.0f;
+}
diff --git a/src/templates/org/lwjgl/opengl/AMD_debug_output.java b/src/templates/org/lwjgl/opengl/AMD_debug_output.java
new file mode 100644
index 0000000..662612b
--- /dev/null
+++ b/src/templates/org/lwjgl/opengl/AMD_debug_output.java
@@ -0,0 +1,99 @@
+/*
+ * Copyright (c) 2002-2008 LWJGL Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * * Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ *
+ * * Neither the name of 'LWJGL' nor the names of
+ *   its contributors may be used to endorse or promote products derived
+ *   from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package org.lwjgl.opengl;
+
+import org.lwjgl.util.generator.*;
+
+import java.nio.ByteBuffer;
+import java.nio.IntBuffer;
+
+ at Alias(value = "AMDX_debug_output", postfix = "X")
+public interface AMD_debug_output {
+
+	/** Tokens accepted by GetIntegerv: */
+	int GL_MAX_DEBUG_MESSAGE_LENGTH_AMD = 0x9143,
+		GL_MAX_DEBUG_LOGGED_MESSAGES_AMD = 0x9144,
+		GL_DEBUG_LOGGED_MESSAGES_AMD = 0x9145;
+
+	/**
+	 * Tokens accepted by DebugMessageEnableAMD, GetDebugMessageLogAMD,
+	 * DebugMessageInsertAMD, and DEBUGPROCAMD callback function
+	 * for &lt;severity&gt;:
+	 */
+	int GL_DEBUG_SEVERITY_HIGH_AMD = 0x9146,
+		GL_DEBUG_SEVERITY_MEDIUM_AMD = 0x9147,
+		GL_DEBUG_SEVERITY_LOW_AMD = 0x9148;
+
+	/**
+	 * Tokens accepted by DebugMessageEnableAMD, GetDebugMessageLogAMD,
+	 * and DEBUGPROCAMD callback function for &lt;category&gt;:
+	 */
+	int GL_DEBUG_CATEGORY_API_ERROR_AMD = 0x9149,
+		GL_DEBUG_CATEGORY_WINDOW_SYSTEM_AMD = 0x914A,
+		GL_DEBUG_CATEGORY_DEPRECATION_AMD = 0x914B,
+		GL_DEBUG_CATEGORY_UNDEFINED_BEHAVIOR_AMD = 0x914C,
+		GL_DEBUG_CATEGORY_PERFORMANCE_AMD = 0x914D,
+		GL_DEBUG_CATEGORY_SHADER_COMPILER_AMD = 0x914E,
+		GL_DEBUG_CATEGORY_APPLICATION_AMD = 0x914F,
+		GL_DEBUG_CATEGORY_OTHER_AMD = 0x9150;
+
+	void glDebugMessageEnableAMD(@GLenum int category, @GLenum int severity, @AutoSize(value = "ids", canBeNull = true) @GLsizei int count, @Check(canBeNull = true) @Const @GLuint IntBuffer ids, boolean enabled);
+
+	void glDebugMessageInsertAMD(@GLenum int category, @GLenum int severity, @GLuint int id, @AutoSize("buf") @GLsizei int length, @Const @GLchar ByteBuffer buf);
+
+	@Alternate("glDebugMessageInsertAMD")
+	void glDebugMessageInsertAMD(@GLenum int category, @GLenum int severity, @GLuint int id, @Constant("buf.length()") @GLsizei int length, CharSequence buf);
+
+	/**
+	 * The {@code AMDDebugOutputCallback.Handler} implementation passed to this method will be used for
+	 * AMD_debug_output messages. If callback is null, any previously registered handler for the current
+	 * thread will be unregistered and stop receiving messages.
+	 * <p/>
+	 * The userParam buffer will be passed to the GL, but the current implementation will ignore it and
+	 * never return it to the handler. Instead, users are encouraged to use a custom callback handler
+	 * implentation to store context-specific data.
+	 *
+	 * @param callback  the callback function to use
+	 * @param userParam the user-specified data
+	 */
+	void glDebugMessageCallbackAMD(@GLpointer(value = "GLDEBUGPROCAMD", canBeNull = true) AMDDebugOutputCallback callback, @Check(canBeNull = true) @GLvoid ByteBuffer userParam);
+
+	@GLuint
+	int glGetDebugMessageLogAMD(@GLuint int count,
+	                            @AutoSize(value = "messageLog", canBeNull = true) @GLsizei int logSize,
+	                            @Check(value = "count", canBeNull = true) @GLenum IntBuffer categories,
+	                            @Check(value = "count", canBeNull = true) @GLuint IntBuffer severities,
+	                            @Check(value = "count", canBeNull = true) @GLuint IntBuffer ids,
+	                            @Check(value = "count", canBeNull = true) @GLsizei IntBuffer lengths,
+	                            @Check(canBeNull = true) @OutParameter @GLchar ByteBuffer messageLog);
+
+}
\ No newline at end of file
diff --git a/src/templates/org/lwjgl/opengl/ARB_transform_feedback3.java b/src/templates/org/lwjgl/opengl/AMD_name_gen_delete.java
similarity index 63%
copy from src/templates/org/lwjgl/opengl/ARB_transform_feedback3.java
copy to src/templates/org/lwjgl/opengl/AMD_name_gen_delete.java
index da2e9cb..89094ea 100644
--- a/src/templates/org/lwjgl/opengl/ARB_transform_feedback3.java
+++ b/src/templates/org/lwjgl/opengl/AMD_name_gen_delete.java
@@ -35,28 +35,26 @@ import org.lwjgl.util.generator.*;
 
 import java.nio.IntBuffer;
 
- at Extension(postfix = "")
-public interface ARB_transform_feedback3 {
+public interface AMD_name_gen_delete {
 
-	/**
-	 * Accepted by the &lt;pname&gt; parameter of GetBooleanv, GetDoublev, GetIntegerv,
-	 * and GetFloatv:
-	 */
-	int GL_MAX_TRANSFORM_FEEDBACK_BUFFERS = 0x8E70;
-	int GL_MAX_VERTEX_STREAMS = 0x8E71;
+	/** Accepted as the &lt;identifier&gt; parameter of GenNamesAMD and DeleteNamesAMD: */
+	int GL_DATA_BUFFER_AMD = 0x9151,
+		GL_PERFORMANCE_MONITOR_AMD = 0x9152,
+		GL_QUERY_OBJECT_AMD = 0x9153,
+		GL_VERTEX_ARRAY_OBJECT_AMD = 0x9154,
+		GL_SAMPLER_OBJECT_AMD = 0x9155;
 
-	void glDrawTransformFeedbackStream(@GLenum int mode, @GLuint int id, @GLuint int stream);
+	void glGenNamesAMD(@GLenum int identifier, @AutoSize("names") @GLuint int num, @OutParameter @GLuint IntBuffer names);
 
-	void glBeginQueryIndexed(@GLenum int target, @GLuint int index, @GLuint int id);
+	@Alternate("glGenNamesAMD")
+	@GLreturn("names")
+	void glGenNamesAMD2(@GLenum int identifier, @Constant("1") @GLsizei int num, @OutParameter @GLuint IntBuffer names);
 
-	void glEndQueryIndexed(@GLenum int target, @GLuint int index);
+	void glDeleteNamesAMD(@GLenum int identifier, @AutoSize("names") @GLsizei int num, @Const @GLuint IntBuffer names);
 
-	@StripPostfix("params")
-	void glGetQueryIndexediv(@GLenum int target, @GLuint int index, @GLenum int pname, @OutParameter @Check("1") IntBuffer params);
+	@Alternate("glDeleteNamesAMD")
+	void glDeleteNamesAMD(@GLenum int identifier, @Constant("1") @GLsizei int num, @Constant(value = "APIUtils.getBufferInt().put(0, name), 0", keepParam = true) int name);
 
-	@Alternate("glGetQueryIndexediv")
-	@GLreturn("params")
-	@StripPostfix("params")
-	void glGetQueryIndexediv2(@GLenum int target, @GLuint int index, @GLenum int pname, @OutParameter IntBuffer params);
+	boolean glIsNameAMD(@GLenum int identifier, @GLuint int name);
 
 }
\ No newline at end of file
diff --git a/src/templates/org/lwjgl/opengl/ARB_fragment_program_shadow.java b/src/templates/org/lwjgl/opengl/AMD_transform_feedback3_lines_triangles.java
similarity index 96%
copy from src/templates/org/lwjgl/opengl/ARB_fragment_program_shadow.java
copy to src/templates/org/lwjgl/opengl/AMD_transform_feedback3_lines_triangles.java
index 458345c..ef91a3b 100644
--- a/src/templates/org/lwjgl/opengl/ARB_fragment_program_shadow.java
+++ b/src/templates/org/lwjgl/opengl/AMD_transform_feedback3_lines_triangles.java
@@ -31,6 +31,6 @@
  */
 package org.lwjgl.opengl;
 
-public interface ARB_fragment_program_shadow {
+public interface AMD_transform_feedback3_lines_triangles {
 
-}
+}
\ No newline at end of file
diff --git a/src/templates/org/lwjgl/opengl/ARB_texture_buffer_object_rgb32.java b/src/templates/org/lwjgl/opengl/ARB_texture_buffer_object_rgb32.java
index 3a0a868..301ed5e 100644
--- a/src/templates/org/lwjgl/opengl/ARB_texture_buffer_object_rgb32.java
+++ b/src/templates/org/lwjgl/opengl/ARB_texture_buffer_object_rgb32.java
@@ -31,5 +31,8 @@
  */
 package org.lwjgl.opengl;
 
+import org.lwjgl.util.generator.Alias;
+
+ at Alias("EXT_texture_buffer_object_rgb32")
 public interface ARB_texture_buffer_object_rgb32 {
 }
\ No newline at end of file
diff --git a/src/templates/org/lwjgl/opengl/ARB_texture_compression_bptc.java b/src/templates/org/lwjgl/opengl/ARB_texture_compression_bptc.java
index 9ea5ab7..0687da1 100644
--- a/src/templates/org/lwjgl/opengl/ARB_texture_compression_bptc.java
+++ b/src/templates/org/lwjgl/opengl/ARB_texture_compression_bptc.java
@@ -31,9 +31,11 @@
  */
 package org.lwjgl.opengl;
 
+import org.lwjgl.util.generator.Alias;
 import org.lwjgl.util.generator.Extension;
 
 @Extension(postfix = "ARB", className = "ARBTextureCompressionBPTC")
+ at Alias("EXT_texture_compression_bptc")
 public interface ARB_texture_compression_bptc {
 
 	/**
diff --git a/src/templates/org/lwjgl/opengl/ATI_vertex_array_object.java b/src/templates/org/lwjgl/opengl/ATI_vertex_array_object.java
index 3b387cc..d351007 100644
--- a/src/templates/org/lwjgl/opengl/ATI_vertex_array_object.java
+++ b/src/templates/org/lwjgl/opengl/ATI_vertex_array_object.java
@@ -71,6 +71,11 @@ public interface ATI_vertex_array_object {
 	@StripPostfix("params")
 	void glGetObjectBufferivATI(@GLuint int buffer, @GLenum int pname, @OutParameter @Check IntBuffer params);
 
+	@Alternate("glGetObjectBufferivATI")
+	@GLreturn("params")
+	@StripPostfix("params")
+	void glGetObjectBufferivATI2(@GLuint int buffer, @GLenum int pname, @OutParameter IntBuffer params);
+
 	void glFreeObjectBufferATI(@GLuint int buffer);
 
 	void glArrayObjectATI(@GLenum int array, int size, @GLenum int type, @GLsizei int stride, @GLuint int buffer, @GLuint int offset);
diff --git a/src/templates/org/lwjgl/opengl/EXT_direct_state_access.java b/src/templates/org/lwjgl/opengl/EXT_direct_state_access.java
index baf8d98..7b9beb0 100644
--- a/src/templates/org/lwjgl/opengl/EXT_direct_state_access.java
+++ b/src/templates/org/lwjgl/opengl/EXT_direct_state_access.java
@@ -519,11 +519,11 @@ public interface EXT_direct_state_access {
     value parameters
 	 */
 
-	@Optional(reason = "AMD does not expose this (last driver checked: 10.3)")
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	void glEnableClientStateiEXT(@GLenum int array, @GLuint int index);
 
-	@Optional(reason = "AMD does not expose this (last driver checked: 10.3)")
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	void glDisableClientStateiEXT(@GLenum int array, @GLuint int index);
 
@@ -565,7 +565,7 @@ public interface EXT_direct_state_access {
     and before state value parameters
 	 */
 
-	@Optional(reason = "AMD does not expose this (last driver checked: 10.3)")
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@StripPostfix("params")
 	void glGetFloati_vEXT(@GLenum int pname, @GLuint int index, @OutParameter @Check("16") FloatBuffer params);
@@ -576,7 +576,7 @@ public interface EXT_direct_state_access {
 	@StripPostfix("params")
 	void glGetFloati_vEXT2(@GLenum int pname, @GLuint int index, @OutParameter FloatBuffer params);
 
-	@Optional(reason = "AMD does not expose this (last driver checked: 10.3)")
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@StripPostfix("params")
 	void glGetDoublei_vEXT(@GLenum int pname, @GLuint int index, @OutParameter @Check("16") DoubleBuffer params);
@@ -587,7 +587,7 @@ public interface EXT_direct_state_access {
 	@StripPostfix("params")
 	void glGetDoublei_vEXT2(@GLenum int pname, @GLuint int index, @OutParameter DoubleBuffer params);
 
-	@Optional(reason = "AMD does not expose this (last driver checked: 10.3)")
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@StripPostfix(value = "params", hasPostfix = false)
 	void glGetPointeri_vEXT(@GLenum int pname, @GLuint int index, @Result @GLvoid ByteBuffer params);
@@ -1343,6 +1343,7 @@ public interface EXT_direct_state_access {
 	OpenGL 3.1: New buffer data copy command
 	 */
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL31,GL_ARB_copy_buffer")
 	void glNamedCopyBufferSubDataEXT(@GLuint int readBuffer, @GLuint int writeBuffer, @GLintptr long readoffset, @GLintptr long writeoffset, @GLsizeiptr long size);
 
@@ -1386,44 +1387,55 @@ public interface EXT_direct_state_access {
 	and change the final parameter from "const void *" to "intptr offset"
 	 */
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@DeprecatedGL
 	void glVertexArrayVertexOffsetEXT(@GLuint int vaobj, @GLuint int buffer, int size, @GLenum int type, @GLsizei int stride, @GLintptr long offset);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@DeprecatedGL
 	void glVertexArrayColorOffsetEXT(@GLuint int vaobj, @GLuint int buffer, int size, @GLenum int type, @GLsizei int stride, @GLintptr long offset);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@DeprecatedGL
 	void glVertexArrayEdgeFlagOffsetEXT(@GLuint int vaobj, @GLuint int buffer, @GLsizei int stride, @GLintptr long offset);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	void glVertexArrayIndexOffsetEXT(@GLuint int vaobj, @GLuint int buffer, @GLenum int type, @GLsizei int stride, @GLintptr long offset);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@DeprecatedGL
 	void glVertexArrayNormalOffsetEXT(@GLuint int vaobj, @GLuint int buffer, @GLenum int type, @GLsizei int stride, @GLintptr long offset);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@DeprecatedGL
 	void glVertexArrayTexCoordOffsetEXT(@GLuint int vaobj, @GLuint int buffer, int size, @GLenum int type, @GLsizei int stride, @GLintptr long offset);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@DeprecatedGL
 	void glVertexArrayMultiTexCoordOffsetEXT(@GLuint int vaobj, @GLuint int buffer, @GLenum int texunit, int size, @GLenum int type, @GLsizei int stride, @GLintptr long offset);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@DeprecatedGL
 	void glVertexArrayFogCoordOffsetEXT(@GLuint int vaobj, @GLuint int buffer, @GLenum int type, @GLsizei int stride, @GLintptr long offset);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@DeprecatedGL
 	void glVertexArraySecondaryColorOffsetEXT(@GLuint int vaobj, @GLuint int buffer, int size, @GLenum int type, @GLsizei int stride, @GLintptr long offset);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	void glVertexArrayVertexAttribOffsetEXT(@GLuint int vaobj, @GLuint int buffer, @GLuint int index, int size, @GLenum int type, boolean normalized, @GLsizei int stride, @GLintptr long offset);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	void glVertexArrayVertexAttribIOffsetEXT(@GLuint int vaobj, @GLuint int buffer, @GLuint int index, int size, @GLenum int type, @GLsizei int stride, @GLintptr long offset);
 
@@ -1433,9 +1445,11 @@ public interface EXT_direct_state_access {
 	"uint vaobj" parameter
 	 */
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	void glEnableVertexArrayEXT(@GLuint int vaobj, @GLenum int array);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	void glDisableVertexArrayEXT(@GLuint int vaobj, @GLenum int array);
 
@@ -1445,9 +1459,11 @@ public interface EXT_direct_state_access {
 	and add an initial "uint vaobj" parameter
 	 */
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	void glEnableVertexArrayAttribEXT(@GLuint int vaobj, @GLuint int index);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	void glDisableVertexArrayAttribEXT(@GLuint int vaobj, @GLuint int index);
 
@@ -1455,6 +1471,7 @@ public interface EXT_direct_state_access {
 	OpenGL 3.0: New queries for vertex array objects
 	 */
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@StripPostfix("param")
 	void glGetVertexArrayIntegervEXT(@GLuint int vaobj, @GLenum int pname, @OutParameter @Check("16") IntBuffer param);
@@ -1465,10 +1482,12 @@ public interface EXT_direct_state_access {
 	@StripPostfix("param")
 	void glGetVertexArrayIntegervEXT2(@GLuint int vaobj, @GLenum int pname, @OutParameter IntBuffer param);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@StripPostfix("param")
 	void glGetVertexArrayPointervEXT(@GLuint int vaobj, @GLenum int pname, @Result @GLvoid ByteBuffer param);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@StripPostfix(value = "param")
 	void glGetVertexArrayIntegeri_vEXT(@GLuint int vaobj, @GLuint int index, @GLenum int pname, @OutParameter @Check("16") IntBuffer param);
@@ -1479,6 +1498,7 @@ public interface EXT_direct_state_access {
 	@StripPostfix(value = "param", postfix = "_v")
 	void glGetVertexArrayIntegeri_vEXT2(@GLuint int vaobj, @GLuint int index, @GLenum int pname, @OutParameter IntBuffer param);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@StripPostfix(value = "param")
 	void glGetVertexArrayPointeri_vEXT(@GLuint int vaobj, @GLuint int index, @GLenum int pname, @Result @GLvoid ByteBuffer param);
@@ -1502,12 +1522,14 @@ public interface EXT_direct_state_access {
 	 *
 	 * @return A ByteBuffer representing the mapped buffer memory.
 	 */
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	@CachedResult(isRange = true)
 	@GLvoid
 	@AutoResultSize("length")
 	ByteBuffer glMapNamedBufferRangeEXT(@GLuint int buffer, @GLintptr long offset, @GLsizeiptr long length, @GLbitfield int access);
 
+	@Optional(reason = "AMD does not expose this (last driver checked: 10.5)")
 	@Dependent("OpenGL30")
 	void glFlushMappedNamedBufferRangeEXT(@GLuint int buffer, @GLintptr long offset, @GLsizeiptr long length);
 
diff --git a/src/templates/org/lwjgl/opengl/GL11.java b/src/templates/org/lwjgl/opengl/GL11.java
index 249dd78..f648caa 100644
--- a/src/templates/org/lwjgl/opengl/GL11.java
+++ b/src/templates/org/lwjgl/opengl/GL11.java
@@ -39,8 +39,8 @@ import java.nio.*;
  * The core OpenGL1.1 API.
  *
  * @author cix_foo <cix_foo at users.sourceforge.net>
- * @version $Revision: 3316 $
- *          $Id: GL11.java 3316 2010-04-09 23:57:40Z spasi $
+ * @version $Revision: 3338 $
+ *          $Id: GL11.java 3338 2010-05-01 09:19:00Z spasi $
  */
 @DeprecatedGL
 public interface GL11 {
@@ -1147,7 +1147,7 @@ public interface GL11 {
 	String glGetString(int name);
 
 	@DeprecatedGL
-	void glGetPolygonStipple(@OutParameter @BufferObject(BufferKind.PackPBO) @Check("1024") @GLubyte ByteBuffer mask);
+	void glGetPolygonStipple(@OutParameter @BufferObject(BufferKind.PackPBO) @Check("128") @GLubyte ByteBuffer mask);
 
 	@DeprecatedGL
 	boolean glIsList(@GLuint int list);
@@ -1252,7 +1252,7 @@ public interface GL11 {
 	void glMatrixMode(@GLenum int mode);
 
 	@DeprecatedGL
-	void glPolygonStipple(@BufferObject(BufferKind.UnpackPBO) @Check("1024") @Const @GLubyte ByteBuffer mask);
+	void glPolygonStipple(@BufferObject(BufferKind.UnpackPBO) @Check("128") @Const @GLubyte ByteBuffer mask);
 
 	void glPolygonOffset(float factor, float units);
 
diff --git a/src/templates/org/lwjgl/opengl/GL15.java b/src/templates/org/lwjgl/opengl/GL15.java
index f88f7d3..bc9adf0 100644
--- a/src/templates/org/lwjgl/opengl/GL15.java
+++ b/src/templates/org/lwjgl/opengl/GL15.java
@@ -74,7 +74,7 @@ public interface GL15 {
 	int GL_BUFFER_MAPPED = 0x88BC;
 	int GL_BUFFER_MAP_POINTER = 0x88BD;
 
-	int FOG_COORD_SRC = GL14.GL_FOG_COORDINATE_SOURCE;
+	int GL_FOG_COORD_SRC = GL14.GL_FOG_COORDINATE_SOURCE;
 	int GL_FOG_COORD = GL14.GL_FOG_COORDINATE;
 	int GL_CURRENT_FOG_COORD = GL14.GL_CURRENT_FOG_COORDINATE;
 	int GL_FOG_COORD_ARRAY_TYPE = GL14.GL_FOG_COORDINATE_ARRAY_TYPE;
diff --git a/src/templates/org/lwjgl/opengl/NV_fence.java b/src/templates/org/lwjgl/opengl/NV_fence.java
index 6822f70..a5a5e89 100644
--- a/src/templates/org/lwjgl/opengl/NV_fence.java
+++ b/src/templates/org/lwjgl/opengl/NV_fence.java
@@ -42,8 +42,15 @@ public interface NV_fence {
 
 	void glGenFencesNV(@AutoSize("piFences") @GLsizei int n, @OutParameter @GLuint IntBuffer piFences);
 
+	@Alternate("glGenFencesNV")
+	@GLreturn("piFences")
+	void glGenFencesNV2(@Constant("1") @GLsizei int n, @OutParameter @GLuint IntBuffer piFences);
+
 	void glDeleteFencesNV(@AutoSize("piFences") @GLsizei int n, @Const @GLuint IntBuffer piFences);
 
+	@Alternate("glDeleteFencesNV")
+	void glDeleteFencesNV(@Constant("1") @GLsizei int n, @Const @GLuint @Constant(value = "APIUtils.getBufferInt().put(0, fence), 0", keepParam = true) int fence);
+
 	void glSetFenceNV(@GLuint int fence, @GLenum int condition);
 
 	boolean glTestFenceNV(@GLuint int fence);
diff --git a/src/templates/org/lwjgl/opengl/ARB_occlusion_query2.java b/src/templates/org/lwjgl/opengl/NV_multisample_coverage.java
similarity index 87%
copy from src/templates/org/lwjgl/opengl/ARB_occlusion_query2.java
copy to src/templates/org/lwjgl/opengl/NV_multisample_coverage.java
index ee020fb..fcdfbf0 100644
--- a/src/templates/org/lwjgl/opengl/ARB_occlusion_query2.java
+++ b/src/templates/org/lwjgl/opengl/NV_multisample_coverage.java
@@ -31,12 +31,13 @@
  */
 package org.lwjgl.opengl;
 
-public interface ARB_occlusion_query2 {
+public interface NV_multisample_coverage {
 
 	/**
-	 * Accepted by the &lt;target&gt; parameter of BeginQuery, EndQuery,
-	 * and GetQueryiv:
+	 * Accepted by the &lt;pname&gt; parameter of GetBooleanv, GetDoublev,
+	 * GetIntegerv, and GetFloatv:
 	 */
-	int GL_ANY_SAMPLES_PASSED = 0x8C2F;
+	int GL_COVERAGE_SAMPLES_NV = 0x80A9;
+	int GL_COLOR_SAMPLES_NV = 0x8E20;
 
 }
\ No newline at end of file


hooks/post-receive
-- 
lwjgl - Lightweight Java Game Library



More information about the pkg-java-commits mailing list