This is the mail archive of the
java@gcc.gnu.org
mailing list for the Java project.
Re: gcc/gcj 3.4 - bug report
- From: rezaei at promail dot com
- To: java at gcc dot gnu dot org
- Date: Wed, 23 Jul 2003 22:09:35 -0400
- Subject: Re: gcc/gcj 3.4 - bug report
- References: <3F1846F5.14206.4E956C8@localhost>
- Reply-to: rezaei at promail dot com
Success! thanks for the help. details below.
> It's usually better to build to .o and then link as a separate step.
> The above is probably a bug -- feel free to put it in bugzilla.
> (Preferably with the full -v output...) Still, this will be low
> priority, I think.
>
> Try:
>
> gcj ... -fPIC -shared -o collections.so .../collections.jar
> [ repeat for each .jar ]
> gcj --main=... -o test.exe collections.so ...other .so files... -lswt
>
Thanks for the tip. I was able to compile a jar to a static .a (gcj -c -o blah.a
blah.jar). for the final compile, I did have to put all the jars on the classpath as
well as the .o's for linking. (It didn't solve the problem, but does reduce my
build time).
> Probably this is a static linking problem. I'm not sure, since I
> haven't tried your program. But make sure that the image loaders are
> in fact linked into your final executable.
hmm... how do I do that? I can do an nm on a .o or .a file, but it doesn't work
on .exe files.
> Search this list's
> archives for lots of talk about the problems of static linking, most
> likely including discussions about this exact problem involving SWT.
You hit the nail on the head here. This is the code swt uses to load images:
static final String FORMAT_PACKAGE =
"org.eclipse.swt.internal.image";
static final String FORMAT_SUFFIX = "FileFormat";
static final String[] FORMATS = {"WinBMP", "WinBMP", "GIF",
"WinICO", "JPEG", "PNG"};
for (int i = 1; i < FORMATS.length; i++) {
if (FORMATS[i] != null) {
try {
Class clazz =
Class.forName(FORMAT_PACKAGE + '.' + FORMATS[i] +
FORMAT_SUFFIX);
fileFormat = (FileFormat)
clazz.newInstance();
if (fileFormat.isFileFormat(stream)) {
isSupported = true;
break;
}
} catch (ClassNotFoundException e) {
FORMATS[i] = null;
} catch (Exception e) {
}
}
}
if (!isSupported)
SWT.error(SWT.ERROR_UNSUPPORTED_FORMAT);
As you can see, it does some dynamic class loading via Class.forName.
BTW, a lot of java code works like this. I guess ld was just optimizing too
much and removing those classes because they were not invoked directly
anywhere. The solution was a simple class (I had to put it in the the eclipse
package, because those classes are package private).
For anyone who's interested:
package org.eclipse.swt.internal.image;
public class ForceClassLoader /* not part of eclipse. fixes gcj ld issue */
{
static
{
GIFFileFormat x = new GIFFileFormat();
PNGFileFormat y = new PNGFileFormat();
JPEGFileFormat z = new JPEGFileFormat();
WinBMPFileFormat q = new WinBMPFileFormat();
WinICOFileFormat p = new WinICOFileFormat();
}
}
Note to Mohan: you might want to put that class in your builds and add it as a
.o for linking.
> >> Exception in thread "Thread-1" java.awt.AWTError: Cannot load AWT toolkit:
>
> AWT isn't available yet. I'm surprised that an SWT application would
> try to use it.
Sorry about the confusing message. When I *removed* the SWT loaders and
tried to do it via AWT, it failed as above. I know AWT is not done, which is
one of the reasons I'm using SWT. I was kinda hoping the "invisible" parts
(things like loading an image, but not displaying anything) were somewhat in
place.
Thanks for help.
Moh