summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKenneth Russel <[email protected]>2006-02-16 02:49:30 +0000
committerKenneth Russel <[email protected]>2006-02-16 02:49:30 +0000
commit945e2ae3d234815b43f83049c9d597cb61585797 (patch)
treee5967c06c09bddd9068e0807573da34d6dfa2fa0
parentf50877b19f5a3cb4deb1b26395ce357f3ebfd3f0 (diff)
Fixed problems with lack of hardware acceleration on Linux
distributions using DRI drivers. Hacked around limitations of the current DRI implementation by manually dlopen'ing libGL.so.1; avoids changing glue code generation for core OpenGL 1.1 routines which do not otherwise need to be called through function pointers on any platform. git-svn-id: file:///usr/local/projects/SUN/JOGL/git-svn/svn-server-sync/jogl/trunk@614 232f8b59-042b-4e1e-8c03-345bb8c30851
-rw-r--r--make/build.xml46
-rw-r--r--src/classes/com/sun/opengl/impl/NativeLibLoader.java19
-rw-r--r--src/classes/com/sun/opengl/impl/x11/DRIHack.java109
-rw-r--r--src/classes/com/sun/opengl/impl/x11/X11GLDrawableFactory.java5
-rwxr-xr-xsrc/classes/com/sun/opengl/util/JOGLAppletLauncher.java34
-rw-r--r--src/native/jogl/drihack.c59
6 files changed, 258 insertions, 14 deletions
diff --git a/make/build.xml b/make/build.xml
index d013e4181..7bb467612 100644
--- a/make/build.xml
+++ b/make/build.xml
@@ -262,25 +262,25 @@
<target name="declare.win32.vc6" if="isVC6">
<echo message="Win32.VC6" />
<property name="compiler.cfg.id" value="compiler.cfg.win32.msvc" />
- <property name="linker.cfg.id" value="linker.cfg.win32.msvc" />
+ <property name="linker.cfg.id.core" value="linker.cfg.win32.msvc" />
</target>
<target name="declare.win32.vc7" if="isVC7">
<echo message="Win32.VC7" />
<property name="compiler.cfg.id" value="compiler.cfg.win32.msvc" />
- <property name="linker.cfg.id" value="linker.cfg.win32.msvc" />
+ <property name="linker.cfg.id.core" value="linker.cfg.win32.msvc" />
</target>
<target name="declare.win32.vc8" if="isVC8">
<echo message="Win32.VC8" />
<property name="compiler.cfg.id" value="compiler.cfg.win32.msvc" />
- <property name="linker.cfg.id" value="linker.cfg.win32.msvc" />
+ <property name="linker.cfg.id.core" value="linker.cfg.win32.msvc" />
</target>
<target name="declare.win32.mingw" if="isMingW">
<echo message="Win32.MingW" />
<property name="compiler.cfg.id" value="compiler.cfg.win32.mingw" />
- <property name="linker.cfg.id" value="linker.cfg.win32.mingw" />
+ <property name="linker.cfg.id.core" value="linker.cfg.win32.mingw" />
</target>
<target name="declare.win32" depends="declare.win32.vc6,declare.win32.vc7,declare.win32.vc8,declare.win32.mingw" if="isWindows">
@@ -332,7 +332,8 @@
<property name="java.lib.dir.platform" value="${java.lib.dir.linux}" />
<property name="compiler.cfg.id" value="compiler.cfg.linux" />
- <property name="linker.cfg.id" value="linker.cfg.linux" />
+ <property name="linker.cfg.id.core" value="linker.cfg.linux" />
+ <property name="linker.cfg.id.drihack" value="linker.cfg.linux.drihack" />
</target>
<target name="declare.linux.amd64" if="isLinuxAMD64">
@@ -341,7 +342,8 @@
<property name="java.lib.dir.platform" value="${java.lib.dir.linux.amd64}" />
<property name="compiler.cfg.id" value="compiler.cfg.linux.amd64" />
- <property name="linker.cfg.id" value="linker.cfg.linux.amd64" />
+ <property name="linker.cfg.id.core" value="linker.cfg.linux.amd64" />
+ <property name="linker.cfg.id.drihack" value="linker.cfg.linux.drihack" />
</target>
<target name="declare.linux.ia64" if="isLinuxIA64">
@@ -350,7 +352,8 @@
<property name="java.lib.dir.platform" value="${java.lib.dir.linux.ia64}" />
<property name="compiler.cfg.id" value="compiler.cfg.linux" />
- <property name="linker.cfg.id" value="linker.cfg.linux" />
+ <property name="linker.cfg.id.core" value="linker.cfg.linux" />
+ <property name="linker.cfg.id.drihack" value="linker.cfg.linux.drihack" />
</target>
<target name="declare.linux" depends="declare.linux.x86,declare.linux.amd64,declare.linux.ia64,declare.x11" if="isLinux" />
@@ -361,7 +364,8 @@
<property name="java.lib.dir.platform" value="${java.lib.dir.solaris}" />
<property name="compiler.cfg.id" value="compiler.cfg.solaris" />
- <property name="linker.cfg.id" value="linker.cfg.solaris" />
+ <property name="linker.cfg.id.core" value="linker.cfg.solaris" />
+ <property name="linker.cfg.id.drihack" value="linker.cfg.solaris.drihack" />
</target>
<target name="declare.macosx" if="isOSX">
@@ -387,7 +391,7 @@
<property name="javadoc.dev.packagenames.platform" value="${javadoc.dev.packagenames.macosx}" />
<property name="compiler.cfg.id" value="compiler.cfg.macosx" />
- <property name="linker.cfg.id" value="linker.cfg.macosx" />
+ <property name="linker.cfg.id.core" value="linker.cfg.macosx" />
</target>
<target name="declare.freebsd" depends="declare.x11" if="isFreeBSD">
@@ -396,7 +400,8 @@
<property name="java.lib.dir.platform" value="${java.lib.dir.linux}" />
<property name="compiler.cfg.id" value="compiler.cfg.freebsd" />
- <property name="linker.cfg.id" value="linker.cfg.linux" />
+ <property name="linker.cfg.id.core" value="linker.cfg.linux" />
+ <property name="linker.cfg.id.drihack" value="linker.cfg.linux.drihack" />
</target>
<!-- ================================================================== -->
@@ -715,6 +720,8 @@
<syslibset dir="${x11.cg.lib}" libs="Cg, CgGL" if="c.compiler.use-cglib"/>
</linker>
+ <linker id="linker.cfg.linux.drihack" name="gcc" />
+
<linker id="linker.cfg.linux.amd64" name="gcc">
<syslibset dir="/usr/X11R6/lib64" libs="GL, X11"/>
<syslibset dir="/usr/X11R6/lib64" libs="Xxf86vm" />
@@ -725,6 +732,8 @@
<syslibset libs="GL, X11"/>
</linker>
+ <linker id="linker.cfg.solaris.drihack" name="suncc" />
+
<linker id="linker.cfg.win32.mingw" name="gcc" incremental="false">
<linkerarg value="-Wl,--kill-at" /> <!-- remove @ from function names -->
<syslibset libs="opengl32, glu32, gdi32, kernel32"/>
@@ -765,6 +774,10 @@
<include name="${rootrel.generated.c.jogl}/JAWT*.c"/>
</patternset>
+ <patternset id="c.src.files.jogl.drihack">
+ <include name="${rootrel.src.c.jogl}/drihack.c"/>
+ </patternset>
+
<patternset id="c.src.files.cg">
<include name="${rootrel.generated.c.cg}/*.c"/>
</patternset>
@@ -840,6 +853,7 @@
<antcall target="c.build" inheritRefs="true">
<param name="c.compiler.src.files" value="c.src.files.jogl"/>
<param name="output.lib.name" value="jogl"/>
+ <param name="linker.cfg.id" value="${linker.cfg.id.core}"/>
</antcall>
</target>
@@ -848,6 +862,7 @@
<param name="c.compiler.src.files" value="c.src.files.jogl_awt"/>
<param name="c.compiler.use-jawt" value="true"/>
<param name="output.lib.name" value="jogl_awt"/>
+ <param name="linker.cfg.id" value="${linker.cfg.id.core}"/>
</antcall>
<antcall target="c.manifest" inheritRefs="true" />
</target>
@@ -857,9 +872,18 @@
<param name="c.compiler.src.files" value="c.src.files.cg"/>
<param name="c.compiler.use-cglib" value="true"/>
<param name="output.lib.name" value="jogl_cg"/>
+ <param name="linker.cfg.id" value="${linker.cfg.id.core}"/>
</antcall>
</target>
+ <target name="c.build.jogl.drihack" if="isX11">
+ <antcall target="c.build" inheritRefs="true">
+ <param name="c.compiler.src.files" value="c.src.files.jogl.drihack"/>
+ <param name="output.lib.name" value="jogl_drihack"/>
+ <param name="linker.cfg.id" value="${linker.cfg.id.drihack}"/>
+ </antcall>
+ </target>
+
<target name="c.manifest" if="isVC8">
<!-- exec mt, the Microsoft Manifest Tool, to include DLL manifests in order to resolve the location of msvcr80.dll -->
<exec executable="mt">
@@ -874,7 +898,7 @@
</exec>
</target>
- <target name="c.build.jogl" depends="c.build.jogl.core,c.build.jogl.awt,c.build.jogl.cg">
+ <target name="c.build.jogl" depends="c.build.jogl.core,c.build.jogl.awt,c.build.jogl.drihack,c.build.jogl.cg">
<antcall target="c.rename.jogl.libs.mingw" inheritRefs="true" />
<antcall target="c.rename.jogl.libs.macosx" inheritRefs="true" />
<antcall target="c.manifest" inheritRefs="true" />
diff --git a/src/classes/com/sun/opengl/impl/NativeLibLoader.java b/src/classes/com/sun/opengl/impl/NativeLibLoader.java
index 1a3d5c277..9331b2f72 100644
--- a/src/classes/com/sun/opengl/impl/NativeLibLoader.java
+++ b/src/classes/com/sun/opengl/impl/NativeLibLoader.java
@@ -55,6 +55,7 @@ public class NativeLibLoader {
private static volatile boolean loadedCore = false;
private static volatile boolean loadedAWTImpl = false;
+ private static volatile boolean loadedDRIHack = false;
public static void loadCore() {
if (doLoading && !loadedCore) {
@@ -104,4 +105,22 @@ public class NativeLibLoader {
}
}
}
+
+ // See DRIHack.java in com/sun/opengl/impl/x11/ for description of
+ // why this is needed
+ public static void loadDRIHack() {
+ if (doLoading && !loadedDRIHack) {
+ synchronized (NativeLibLoader.class) {
+ if (!loadedDRIHack) {
+ AccessController.doPrivileged(new PrivilegedAction() {
+ public Object run() {
+ System.loadLibrary("jogl_drihack");
+ return null;
+ }
+ });
+ loadedDRIHack = true;
+ }
+ }
+ }
+ }
}
diff --git a/src/classes/com/sun/opengl/impl/x11/DRIHack.java b/src/classes/com/sun/opengl/impl/x11/DRIHack.java
new file mode 100644
index 000000000..181210982
--- /dev/null
+++ b/src/classes/com/sun/opengl/impl/x11/DRIHack.java
@@ -0,0 +1,109 @@
+/*
+ * Copyright (c) 2006 Sun Microsystems, Inc. All Rights Reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * - Redistribution of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *
+ * - Redistribution 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 Sun Microsystems, Inc. or the names of
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * This software is provided "AS IS," without a warranty of any kind. ALL
+ * EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND WARRANTIES,
+ * INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, FITNESS FOR A
+ * PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY EXCLUDED. SUN
+ * MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL NOT BE LIABLE FOR
+ * ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING OR
+ * DISTRIBUTING THIS SOFTWARE OR ITS DERIVATIVES. IN NO EVENT WILL SUN OR
+ * ITS LICENSORS BE LIABLE FOR ANY LOST REVENUE, PROFIT OR DATA, OR FOR
+ * DIRECT, INDIRECT, SPECIAL, CONSEQUENTIAL, INCIDENTAL OR PUNITIVE
+ * DAMAGES, HOWEVER CAUSED AND REGARDLESS OF THE THEORY OF LIABILITY,
+ * ARISING OUT OF THE USE OF OR INABILITY TO USE THIS SOFTWARE, EVEN IF
+ * SUN HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.
+ *
+ * You acknowledge that this software is not designed or intended for use
+ * in the design, construction, operation or maintenance of any nuclear
+ * facility.
+ *
+ * Sun gratefully acknowledges that this software was originally authored
+ * and developed by Kenneth Bradley Russell and Christopher John Kline.
+ */
+
+package com.sun.opengl.impl.x11;
+
+import java.io.*;
+import java.security.*;
+import com.sun.opengl.impl.*;
+
+/**
+ * Helper class for working around problems with open-source DRI
+ * drivers. In the current DRI implementation it is required that the
+ * symbols in libGL.so.1.2 be globally visible to be accessible from
+ * other libraries that are dynamically loaded by the implementation.
+ * Applications may typically satisfy this need either by linking
+ * against libGL.so on the command line (-lGL) or by dlopen'ing
+ * libGL.so.1.2 with the RTLD_GLOBAL flag. The JOGL implementation
+ * links against libGL on all platforms rather than forcing all OpenGL
+ * entry points to be called through a function pointer. This allows
+ * the JOGL library to link directly to core 1.1 OpenGL entry points
+ * like glVertex3f, while calling through function pointers for entry
+ * points from later OpenGL versions as well as from
+ * extensions. However, because libjogl.so (which links against
+ * libGL.so) is loaded by the JVM, and because the JVM implicitly uses
+ * RTLD_LOCAL in the implementation of System.loadLibrary(), this
+ * means via transitivity that the symbols for libGL.so have only
+ * RTLD_LOCAL visibility to the rest of the application, so the DRI
+ * drivers can not find the symbols required. <P>
+ *
+ * There are at least two possible solutions. One would be to change
+ * the JOGL implementation to call through function pointers uniformly
+ * so that it does not need to link against libGL.so. This is
+ * possible, but requires changes to GlueGen and also is not really
+ * necessary in any other situation than with the DRI drivers. Another
+ * solution is to force the first load of libGL.so.1.2 to be done
+ * dynamically with RTLD_GLOBAL before libjogl.so is loaded and causes
+ * libGL.so.1.2 to be loaded again. This requires the C APIs dlopen
+ * and dlclose to be made available before libjogl.so is loaded. This
+ * is the solution currently chosen and is called the "DRI hack"
+ * because again it is needed only in this situation.
+ */
+
+public class DRIHack {
+ public static native long dlopen(String name);
+ public static native int dlclose(long handle);
+
+ private static boolean driHackNeeded;
+ private static long libGLHandle;
+
+ public static void begin() {
+ AccessController.doPrivileged(new PrivilegedAction() {
+ public Object run() {
+ driHackNeeded = new File("/usr/lib/dri").exists();
+ return null;
+ }
+ });
+
+ if (driHackNeeded) {
+ System.err.println("Beginning DRI hack");
+
+ NativeLibLoader.loadDRIHack();
+ libGLHandle = dlopen("/usr/lib/libGL.so.1");
+ }
+ }
+
+ public static void end() {
+ if (libGLHandle != 0) {
+ System.err.println("Ending DRI hack");
+
+ dlclose(libGLHandle);
+ }
+ }
+}
diff --git a/src/classes/com/sun/opengl/impl/x11/X11GLDrawableFactory.java b/src/classes/com/sun/opengl/impl/x11/X11GLDrawableFactory.java
index c7b0e1a0c..aa26f133e 100644
--- a/src/classes/com/sun/opengl/impl/x11/X11GLDrawableFactory.java
+++ b/src/classes/com/sun/opengl/impl/x11/X11GLDrawableFactory.java
@@ -57,8 +57,13 @@ public class X11GLDrawableFactory extends GLDrawableFactoryImpl {
private static boolean isLinuxAMD64;
static {
+ // See DRIHack.java for an explanation of why this is necessary
+ DRIHack.begin();
+
NativeLibLoader.loadCore();
+ DRIHack.end();
+
AccessController.doPrivileged(new PrivilegedAction() {
public Object run() {
String os = System.getProperty("os.name").toLowerCase();
diff --git a/src/classes/com/sun/opengl/util/JOGLAppletLauncher.java b/src/classes/com/sun/opengl/util/JOGLAppletLauncher.java
index 7a9f8ab74..6db8d39be 100755
--- a/src/classes/com/sun/opengl/util/JOGLAppletLauncher.java
+++ b/src/classes/com/sun/opengl/util/JOGLAppletLauncher.java
@@ -181,6 +181,10 @@ public class JOGLAppletLauncher extends Applet {
// The signatures of these native libraries are checked before
// installing them.
private String[] nativeLibNames;
+ // Whether the "DRI hack" native library is present and whether we
+ // therefore might need to run the DRIHack during loading of the
+ // native libraries
+ private boolean driHackPresent;
/** The applet we have to start */
private Applet subApplet;
@@ -524,6 +528,9 @@ public class JOGLAppletLauncher extends Applet {
JarEntry entry = (JarEntry) e.nextElement();
if (nativeLibInfo.matchesNativeLib(entry.getName())) {
list.add(entry.getName());
+ if (entry.getName().indexOf("jogl_drihack") >= 0) {
+ driHackPresent = true;
+ }
}
}
if (list.isEmpty()) {
@@ -615,9 +622,33 @@ public class JOGLAppletLauncher extends Applet {
public void run() {
displayMessage("Loading native libraries");
+ // disable JOGL loading from elsewhere
+ com.sun.opengl.impl.NativeLibLoader.disableLoading();
+
+ Class driHackClass = null;
+ if (driHackPresent) {
+ // Load DRI hack library and run the DRI hack itself
+ loadLibrary(nativeLibDir, "jogl_drihack");
+ try {
+ driHackClass = Class.forName("com.sun.opengl.impl.x11.DRIHack");
+ driHackClass.getMethod("begin", new Class[] {}).invoke(null, new Object[] {});
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ }
+
// Load core JOGL native library
loadLibrary(nativeLibDir, "jogl");
+ if (driHackPresent) {
+ // End DRI hack
+ try {
+ driHackClass.getMethod("end", new Class[] {}).invoke(null, new Object[] {});
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ }
+
if (!nativeLibInfo.isMacOS()) { // borrowed from NativeLibLoader
// Must pre-load JAWT on all non-Mac platforms to
// ensure references from jogl_awt shared object
@@ -638,9 +669,6 @@ public class JOGLAppletLauncher extends Applet {
// Load AWT-specific native code
loadLibrary(nativeLibDir, "jogl_awt");
- // disable JOGL loading from elsewhere
- com.sun.opengl.impl.NativeLibLoader.disableLoading();
-
displayMessage("Starting applet " + subAppletDisplayName);
// start the subapplet
diff --git a/src/native/jogl/drihack.c b/src/native/jogl/drihack.c
new file mode 100644
index 000000000..912b11800
--- /dev/null
+++ b/src/native/jogl/drihack.c
@@ -0,0 +1,59 @@
+/*
+ * Copyright (c) 2003 Sun Microsystems, Inc. All Rights Reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * - Redistribution of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *
+ * - Redistribution 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 Sun Microsystems, Inc. or the names of
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * This software is provided "AS IS," without a warranty of any kind. ALL
+ * EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND WARRANTIES,
+ * INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, FITNESS FOR A
+ * PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY EXCLUDED. SUN
+ * MIDROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL NOT BE LIABLE FOR
+ * ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING OR
+ * DISTRIBUTING THIS SOFTWARE OR ITS DERIVATIVES. IN NO EVENT WILL SUN OR
+ * ITS LICENSORS BE LIABLE FOR ANY LOST REVENUE, PROFIT OR DATA, OR FOR
+ * DIRECT, INDIRECT, SPECIAL, CONSEQUENTIAL, INCIDENTAL OR PUNITIVE
+ * DAMAGES, HOWEVER CAUSED AND REGARDLESS OF THE THEORY OF LIABILITY,
+ * ARISING OUT OF THE USE OF OR INABILITY TO USE THIS SOFTWARE, EVEN IF
+ * SUN HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.
+ *
+ * You acknowledge that this software is not designed or intended for use
+ * in the design, construction, operation or maintenance of any nuclear
+ * facility.
+ *
+ * Sun gratefully acknowledges that this software was originally authored
+ * and developed by Kenneth Bradley Russell and Christopher John Kline.
+ */
+
+#include <jni.h>
+
+#include <inttypes.h>
+#include <dlfcn.h>
+
+JNIEXPORT jlong JNICALL
+Java_com_sun_opengl_impl_x11_DRIHack_dlopen(JNIEnv* env, jclass unused, jstring name) {
+ const jbyte* chars;
+ void* res;
+ chars = (*env)->GetStringUTFChars(env, name, NULL);
+ res = dlopen(chars, RTLD_LAZY | RTLD_GLOBAL);
+ (*env)->ReleaseStringUTFChars(env, name, chars);
+ return (jlong) ((intptr_t) res);
+}
+
+JNIEXPORT int JNICALL
+Java_com_sun_opengl_impl_x11_DRIHack_dlclose(JNIEnv* env, jclass unused, jlong handle)
+{
+ return dlclose((void*) ((intptr_t) handle));
+}