Skip site navigation (1)Skip section navigation (2)
Date:      Mon, 24 Dec 2001 12:42:29 -0800
From:      Joe Kelsey <joe@zircon.seattle.wa.us>
To:        freebsd-java@freebsd.org
Subject:   RE: JNI, -pthread vs -lc_r
Message-ID:  <15399.37685.556086.133776@zircon.zircon.seattle.wa.us>
In-Reply-To: <200112232058.VAA10405@www.blender.nl>
References:  <200112232058.VAA10405@www.blender.nl>

next in thread | previous in thread | raw e-mail | index | archive | help
Hans Lambermont writes:
 > Joe wrote:
 > > Hans Lambermont writes:
 > >  > Linking a JNI .so with only -pthread seems insufficient. I get:
 > >  >     Exception in thread "main" java.lang.UnsatisfiedLinkError:
 > >  >     libblenderssr.so:
 > >  >     /usr/X11R6/lib/libGL.so.1: Undefined symbol "pthread_getspecific"
 > > 
 > > What exactly do you mean by "linking a JNI .so"?  Are you trying to
 > > produce a .so file or are you trying to produce an executable image?
 > > Are you using an existing .so produced by the port or are you trying to
 > > create your own?  It makes a huge difference in the answer.
 > 
 > Sorry that I was not clear. I created my own .so file and access
 > it from java by using the JNI.

The p5 version of the port has many problems in the area of creating .so
files, and these problems are related to a fundamental misunderstanding
that mnay people have over exactly how to create shared objects.

The fundamental thing to remember when creating a shared object is not
to be overly specific on the linker command line.  If your shared object
references things in another shared object, simply leave any mention of
the other shared object OFF the linker command line when creating your
own shared object.  (However there are important exceptions to this
rule, and Java is an important exception).

This is a nice rule to follow.  When creating a shared object, the only
things mentioned on the linker command line should be the objects which
make up your sharedobject and you should mention no libraries at all,
and especially do not use the -pthread option on your shared object
linker command line.

It is important to understand how Java starts up in order to decide
exactly how to create a shared object.  When using the p5 version of the
port, the only supported threading model is green threads, therefore JNI
objects will NOT work with the java executables created by the p5
version of the port.

When the p6 version of the port appears, native threads will be
supported and then you can use JNI objects safely.  However, due to the
fact that the pthreads library in FreeBSD is merely a different
implementation of the standard C library and not a separate object, it
is impossible to choose threading model at run time, as it is in other
operating systems.  In FreeBSD, you must know in advance whether or not
your executable will use native or green threads and link your main
program appropriately, using either -pthreads or not on your linker and
compiler command lines.

The only way around this situation is to either change the FreeBSD
pthreads implementation to be a separate object separate from the
standard C library or else to modify your main program so that it does
not make ANY C library calls until after choosing a threading model.
This is nearly impossible to do.

Therefore, any executable which creates a JVM needs to be linked with
either -pthreads or not, depending on which threading model it will
choose.  That means that we will have separate executables for all Java
standard programs depending on threading model.

Here is the dynamic behavior of an executable which creates a JVM:

1. load the appropriate version of libjvm.so (classic, hotspot client,
   hotspot server, other...

2. libjvm.so loads libhpi.so depending on threads model (green
   vs. native) chosen from the THREADS_FLAG environmental variable.
   This the the point that creates the problem.  The C library chosen
   when creating the master executable has already been chosen, and
   cannot be unchosen or replaced at runtime.  Therefore, the runtime
   choioce of threading model better match the link time model chosen
   for the executable...

3. The JVM continues on and starts loading the rest of Java dynamically,
   starting with the java and verify objects, then adding other objects
   as the running java program requests them.  This is the tricky part.
   If you want to use the AWT, the the AWT shared object has to include
   references to all of the X stuff it needs.  This is "sort of" an
   exception to the rule that no shared object should be linked with
   references outside of itself, since we have to automagically pull in
   the required X stuff at runtime when it is needed.  Unfortuantely,
   here we run into another runtime gotcha.  AWT is based on Motif, and
   Motif requires that it be loaded BEFORE ANY Xt calls are made, so
   that it can hook up to some sort of Xt magic and initialize all of
   its variable before any user Xt calls are made.  This causes problems
   in the Mozilla plugin, since part of the Mozilla plugin C code makes
   Xt calls BEFORE the AWT is loaded, therefore the Mozilla plugin needs
   to have Xm and Xt loaded at link time rather than at AWT load time.

I could be wrong about the JNI not working with green threads, but I
heard that on this list.

The real problem is that the FreeBSD pthreads implementation is
interwoven in the C library and cannot be unwoven.  Therefore it is
impossible to support threading model choice at runtime in FreeBSD.
Therefore, some part of Java compatibility has to be sacrificed.

/Joe

To Unsubscribe: send mail to majordomo@FreeBSD.org
with "unsubscribe freebsd-java" in the body of the message




Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?15399.37685.556086.133776>