It seems like there's a bug which sometimes causes passing lists of
ints to Java int[]s to generate a SIGSEGV.

The crash occurs in Python's listitem.c while iterating over a list
(verified by comparing the RIP reported in the hs_err_pid<pid> file
against a disassembly).  It tries to access a->ob_item[i], which turns
out to be NULL, and thus faults when trying to increment the reference
count with y_INCREF(a->ob_item[i]);

I've verified this by looking through the list with gdb on a core
dump: the list pointer is available in a register, the object header
of the list has the right reference count, length, and type, and the
other elements in the list seem to have the right refcount (1), type 
(PyInt_Type), and plausible integer values.

This occurs for me under ubuntu/x86_64 with the Hotspot JVM
(reproduced on both gutsy/sun-java6-jdk/python2.4 and
intrepid/openjdk-6-jdk/python2.5.2), probably more often on
multicore/multiprocessor machines.  Building JCC with or without
NO_SHARED doesn't seem to make any difference.  It seems to happen
both with -Xcheck:jni as a VM option, and without, and with JCC
versions as late as r740966.

I'm attaching a test case (python and java files) to this email: I've
also put a tarball at http://www.pobox.com/~asl2/jcc-jarray.tar.bz2
which has a prebuilt jar, a build.sh script to build both the jar and
the JCC wrapper, a run.sh script to repeatedly run the test code
(it doesn't always fault, but I'd expect that if it doesn't do so
after 50-100 tries, it's not going to in that environment), and a sample
hs_err_pid logfile.

Does this reproduce for anyone, or sound familiar?

   Thanks,
   Aaron Lav (a...@pobox.com)



import _testjcc
import random

def setupEnv():
    if not _testjcc.getVMEnv():
        _testjcc.initVM(classpath='.', vmargs="-Xcheck:jni")

def test():
    count = 2000000
    a = [int(random.randrange(-1, 70000)) for _ in range(count)]
    b = [int(random.randrange(-1, 32)) for _ in range(count)]
    
    factory = _testjcc.TestJcc(a,b)


if __name__ == '__main__':
    setupEnv()
    test()

package org.dyndns.asl2.TestJcc;

public class TestJcc {
    public TestJcc(int a[], int b[]) {
    }
}


Reply via email to