[Qt-jambi-interest] Jambi and JNI Integration

Adam Batkin adam at batkin.net
Mon Jul 7 18:50:09 CEST 2008


Hi,

I had posted a while back about wrapping the Poppler PDF library using QT Jambi, so that 
it could be used from Java. Although Poppler uses C++ Namespaces, I wrapped the 3 or 4 
functions that I wanted in my own class, used the Jambi Generator and everything was 
great. At the time, it was mentioned that better Namespace support was coming with 4.4 so 
I figured I would wait until then to "properly" wrap the entire library (without having to 
also write my own C++ classes to wrap ever Poppler class that I wanted).

Anyway, I've now set out to write my own JNI code to do what I want, instead of using the 
Jambi Generator. Everything was working nicely until trying to transfer a QImage from C++ 
to a Java/Jambi QImage. Back in February, Gunnar suggested stealing some logic from the 
generated Jambi code, in particular QPixmap::toImage():
     jobject jimg =
         qtjambi_from_object(env,
                             &image,
                             "QImage",
                             "com/trolltech/qt/gui/",
                             true);

This works -- almost. I get back a valid Java QImage object (System.err.println(image) 
prints something like com.trolltech.qt.gui.QImage at d0a5d9) but when I try to do anything 
with it (like call image.width()), the JVM crashes.

Now, the image object (QImage) that I'm getting back is on the stack (hence the address-of 
&). If I make a copy of it on the heap (QImage *copy = new QImage(image)) and then pass 
that copy pointer directly to the qtjambi_from_object function (i.e. no address-of 
operator & since it is naturally a pointer) then it doesn't crash -- so long as I don't 
delete the copy pointer (which makes that a big memory leak). (creating a copy, not 
deleting it, but using the original &image in qtjambi_from_object DOES crash the JVM (weird)).

Something else that is weird (though this may be a red-herring, i.e. luck) if I construct 
more than 1 QImage (in Java, i.e. QImage i1 = page.renderToImage(); QImage i2 = 
page.renderToImage();) calling i1.width() crashes the JVM but i2.width() does not! (i1 
being the first QImage created this way) In fact, just the line "new QPixmap().toImage()" 
seems to prevent a crash. Through some trial and error, I tried inlining a bunch of the 
code from qtjambi_from_object and it seems that just calling the following one line before 
calling qtjambi_from_object prevents a crash:
resolveClass(env, className, packageName);

Thoughts?

Thanks,

-Adam Batkin




More information about the Qt-jambi-interest mailing list