Question

I'm trying to build an applet with JNLP. I wrote an Ant script to compile java classes, to build jar files and to sign them. I signed all jars with same keystore that I built by Ant. I gave permission in Java Control Panel to show self-signed applets. If I run JNLP file directly, everything works well, but if I put this applet in a web page, I get UnsatisfiedLinkError.

Here is error that I got :

java.lang.reflect.InvocationTargetException
    at java.awt.EventQueue.invokeAndWait(Unknown Source)
    at java.awt.EventQueue.invokeAndWait(Unknown Source)
    at javax.swing.SwingUtilities.invokeAndWait(Unknown Source)
    at polygon.Example.init(Unknown Source)
    at com.sun.deploy.uitoolkit.impl.awt.AWTAppletAdapter.init(Unknown Source)
    at sun.plugin2.applet.Plugin2Manager$AppletExecutionRunnable.run(Unknown Source)
    at java.lang.Thread.run(Unknown Source)
Caused by: java.lang.UnsatisfiedLinkError: no gluegen-rt in java.library.path
    at java.lang.ClassLoader.loadLibrary(Unknown Source)
    at java.lang.Runtime.loadLibrary0(Unknown Source)
    at java.lang.System.loadLibrary(Unknown Source)
    at com.jogamp.common.jvm.JNILibLoaderBase.loadLibraryInternal(JNILibLoaderBase.java:454)
    at com.jogamp.common.jvm.JNILibLoaderBase.access$000(JNILibLoaderBase.java:59)
    at com.jogamp.common.jvm.JNILibLoaderBase$DefaultAction.loadLibrary(JNILibLoaderBase.java:90)
    at com.jogamp.common.jvm.JNILibLoaderBase.loadLibrary(JNILibLoaderBase.java:328)
    at com.jogamp.common.os.DynamicLibraryBundle$GlueJNILibLoader.loadLibrary(DynamicLibraryBundle.java:390)
    at com.jogamp.common.os.Platform$2.run(Platform.java:249)
    at java.security.AccessController.doPrivileged(Native Method)
    at com.jogamp.common.os.Platform.loadGlueGenRTImpl(Platform.java:231)
    at com.jogamp.common.os.Platform.<clinit>(Platform.java:183)
    at javax.media.opengl.GLProfile.<clinit>(GLProfile.java:99)
    ...

Every jar files that I built according to operation system contain gluegen-rt.dll but it couldn't load it. Jar files of my native libraries consist of DLL files. It looks like:

  • win64.jar
    • gluegen-rt.dll
    • jogl_cl.dll

My folder hierarchy look like :

  • WebContent
    • applet.jnlp
    • applet
      • applet.jar
      • some other jar files ...
      • lib
      • native
        • win32.jar

Here is my Ant script :

<project name="Project" default="signJar">
<path id="libraries.path">
    <fileset dir="${lib.dir}" includes="**/*.jar"/>
</path>

<path id="maps.path">
    <fileset dir="${maps.dir}"/>
</path>

<target name="clean">
    <delete dir="${classes.dir}" />
    <delete dir="${jar.dir}" />
    <delete dir="${build.dir}" />
</target>

<target name="init" depends="clean">
    <mkdir dir="${build.dir}" />
    <mkdir dir="${classes.dir}" />
    <mkdir dir="${dist.dir}" />
</target>

<target name="compile" depends="init">
    <javac srcdir="${src.dir}" destdir="${classes.dir}" includeantruntime="true" verbose="true" classpathref="libraries.path" encoding="ISO-8859-9" />
</target>

<target name="dist" depends="compile">

    <pathconvert property="mf.classpath" pathsep=" ">
        <path refid="libraries.path" />
        <flattenmapper />
    </pathconvert>

    <tstamp/><!-- needed for TODAY -->
    <manifest file="MANIFEST.MF">
        <attribute name="Built-By" value="${manifest.built.by}"/>
        <attribute name="Created-By" value="${manifest.created.by}"/>
        <attribute name="Main-Class" value="polygon.MainApplet"/>
        <attribute name="Implementation-Version" value="${version.number}-b${build.number}"/>   
        <attribute name="Built-Date" value="${TODAY}" />
        <attribute name="Class-Path" value="${maps.dir} ${mf.classpath}" />
        <attribute name="Permissions" value="all-permissions" />
        <attribute name="Codebase" value="*" />
        <attribute name="Application-Name" value="Applet Application in Manifest" />
        <attribute name="Trusted-Only" value="true" />
    </manifest>

    <jar jarfile="${dist.dir}/applet.jar" basedir="${classes.dir}" manifest="MANIFEST.MF" />

    <jar jarfile="${dist.dir}/${native.libraries.dir}/linux.jar" basedir="${native.libraries.dir}/linux" />
    <jar jarfile="${dist.dir}/${native.libraries.dir}/linux64.jar" basedir="${native.libraries.dir}/linux64" />
    <jar jarfile="${dist.dir}/${native.libraries.dir}/macos_64.jar" basedir="${native.libraries.dir}/macos_64" />
    <jar jarfile="${dist.dir}/${native.libraries.dir}/macos_ppc.jar" basedir="${native.libraries.dir}/macos_ppc" />
    <jar jarfile="${dist.dir}/${native.libraries.dir}/macos_x86.jar" basedir="${native.libraries.dir}/macos_x86" />
    <jar jarfile="${dist.dir}/${native.libraries.dir}/solaris_amd64.jar" basedir="${native.libraries.dir}/solaris_amd64" />
    <jar jarfile="${dist.dir}/${native.libraries.dir}/solaris_i586.jar" basedir="${native.libraries.dir}/solaris_i586" />
    <jar jarfile="${dist.dir}/${native.libraries.dir}/solaris_sparc.jar" basedir="${native.libraries.dir}/solaris_sparc" />
    <jar jarfile="${dist.dir}/${native.libraries.dir}/solaris_sparc64.jar" basedir="${native.libraries.dir}/solaris_sparc64" />
    <jar jarfile="${dist.dir}/${native.libraries.dir}/win32.jar" basedir="${native.libraries.dir}/win32" />
    <jar jarfile="${dist.dir}/${native.libraries.dir}/win64.jar" basedir="${native.libraries.dir}/win64" />

    <jar jarfile="${dist.dir}/maps.jar" basedir="${lib.dir}/maps" />

    <copy todir="${dist.dir}">
        <fileset dir="${lib.dir}">
            <include name="*.jar"/>
        </fileset>
    </copy>

</target>

<target name="signJar" depends="dist">
    <delete dir="${dist.dir}/.keystore" />

    <genkey alias="keystorealias" verbose="true" storepass="storepass" 
            keypass="keypass"
            validity="365"
            keystore="${dist.dir}/.keystore">
            <dname>
                <param name="CN" value="CN"/>
                <param name="OU" value="OU"/>
                <param name="O"  value="O"/>
                <param name="C"  value="TR"/>
            </dname>
        </genkey>

        <signjar
            alias="keystorealias" keystore="${dist.dir}/.keystore"
            storepass="storepass"
            keypass="keypass">
          <path>
            <fileset dir="${dist.dir}" includes="**/*.jar" />
          </path>
        </signjar>
    </target>
</project>

I didn't write my properties. I need some native libraries to run application, as you can see in Ant script I put them into a jar according to OS. Also I need some other jar files in lib folder, but I put them into Manifest file. I didn't write them in JNLP file.

Here is my JNLP :

<?xml version="1.0" encoding="UTF-8"?>

<jnlp spec="1.0+">
    <information>
        <title>Demo</title>
        <vendor>Team</vendor>
        <offline-allowed />
    </information>
    <security>
        <all-permissions/>
    </security>
    <resources>
        <j2se version="1.7+" initial-heap-size="256M" max-heap-size="512M" />

        <jar href="applet/applet.jar" main="true" />
        <jar href="applet/maps.jar" />
    </resources>

    <resources os="Linux" arch="x86">
        <nativelib href="applet/lib/native/linux_x86.jar" />
    </resources>

    <resources os="Linux" arch="amd64">
        <nativelib href="applet/lib/native/linux_x64.jar" />
    </resources>

    <resources os="Windows" arch="x86">
        <nativelib href="applet/lib/native/win32.jar" />
    </resources>

    <resources os="Windows" arch="amd64">
        <nativelib href="applet/lib/native/win64.jar" />
    </resources>

    <applet-desc name="Applet Application in Applet" main-class="polygon.Example" width="800" height="600" />
    <update check="background" policy="prompt-update" />
</jnlp>sources>

    <resources os="Linux" arch="x86">
        <nativelib href="applet/lib/native/linux_x86.jar" />
    </resources>

    <resources os="Linux" arch="amd64">
        <nativelib href="applet/lib/native/linux_x64.jar" />
    </resources>

    <resources os="Windows" arch="x86">
        <nativelib href="applet/lib/native/win32.jar" />
    </resources>

    <resources os="Windows" arch="amd64">
        <nativelib href="applet/lib/native/win64.jar" />
    </resources>

    <applet-desc name="Applet Application" main-class="polygon.Example" width="800" height="600" />
    <update check="background" policy="prompt-update" />
</jnlp>

And also here is my HTML code to add the applet in the web page :

<applet width="800" height="500" codebase="applet" code="polygon.Example" archive="applet.jar">
<param name="jnlp_ref" value="applet.jnlp" />
</applet>

I tried to access gluegen-rt.dll in my applet by using File class and I could reach it. Why my applet can load native libraries if I run JNLP directly and why it can not load them if I put it in the web page?

Note that I don't want add libraries that I mentioned above to classpath in my computer because another users will not be able to run it if they don't add. So it is not possible to add it to classpath in all users computers. It will not good solution for my case.

Was it helpful?

Solution

I figured out that it causes because applet has to be added by different tag instead of applet tag. In my case I should change applet tag to following lines to add the applet.

<script src="http://www.java.com/js/deployJava.js"></script>
<script>
    var attributes = {code: 'polygon.Example', width: 800, height: 600};
    var params = {jnlp_href: 'applet.jnlp'};
    deployJava.runApplet( attributes, params, '1.7' );
</script>
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top