JNI C calling java with String gets null pointer in Java

Discussion in 'Java' started by xingshan_he@hotmail.com, Oct 19, 2005.

  1. Guest

    I have a c program that calls a java method. When trying to access the
    string parms passed into the jave pointer, I get null pointer
    exception.

    Here is part of the code:

    char *urlChar = "http://this_host/service";
    char *userChar = "tester";
    char *passwordChar = "tester";
    char *phoneNumberChar = "1234567890";

    jmethodID mid = (*env)->GetStaticMethodID(env,
    cls, "getPhoneMessage",
    "(Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;");
    if (mid == NULL) {
    printf("unable to get method getPhoneMessage()...");
    return;
    }


    jobject result = (*env)->CallStaticObjectMethod(
    env, cls, mid, phoneNumberChar, urlChar, userChar, passwordChar);

    --- java class ---


    public class IVRPhoneUtil {
    public static String getPhoneMessage(String phoneNumber, String
    url, String userID, String password) throws Exception {
    System.out.println("java getPhoneMessage()");
    if (url == null) {
    System.out.println("url is null");
    }
    else {
    System.out.println("length " + url.length());
    System.out.println("url is " + url);
    }
    return "test message";
    }
    }

    -- error / stack trace ---
    Exception in thread "main" java.lang.NullPointerException
    at java.io.Writer.write(Writer.java:126)
    at java.io.PrintStream.write(PrintStream.java:303)
    at java.io.PrintStream.print(PrintStream.java:448)
    at java.io.PrintStream.println(PrintStream.java:585)
    at
    com.interop.ivr.IVRPhoneUtil.getPhoneMessage(IVRPhoneUtil.java:21)
    Segmentation fault (core dumped)

    The line that's causing the null pointer is where I tried to print out
    the length of the string.

    Any idea what's going wrong here?

    Thanks.

    XS
     
    , Oct 19, 2005
    #1
    1. Advertising

  2. Roedy Green Guest

    On 18 Oct 2005 16:47:15 -0700, wrote or quoted
    :

    >jmethodID mid = (*env)->GetStaticMethodID(env,


    You are a glutton for punishment with code like this. Do the
    Javaesque stuff like reflection in Java and the Cesque stuff in C.
    --
    Canadian Mind Products, Roedy Green.
    http://mindprod.com Again taking new Java programming contracts.
     
    Roedy Green, Oct 19, 2005
    #2
    1. Advertising

  3. Chris Uppal Guest

    wrote:

    > char *urlChar = "http://this_host/service";
    > char *userChar = "tester";
    > char *passwordChar = "tester";
    > char *phoneNumberChar = "1234567890";

    [...]
    > jobject result = (*env)->CallStaticObjectMethod(
    > env, cls, mid, phoneNumberChar, urlChar, userChar, passwordChar);


    You are passing four pointers to a nul-terminated array of 8-byte characters
    when the function is expecting 4 references to objects of type
    java.lang.String. These things are not even remotely similar.

    Create four java.lang.Strings from your char*s and pass those.

    -- chris
     
    Chris Uppal, Oct 19, 2005
    #3
  4. On 18 Oct 2005 16:47:15 -0700, wrote:
    > I have a c program that calls a java method. When trying to access the
    > string parms passed into the jave pointer, I get null pointer
    > exception.


    [...]

    > char *urlChar = "http://this_host/service";
    > char *userChar = "tester";
    > char *passwordChar = "tester";
    > char *phoneNumberChar = "1234567890";


    [...]

    > jobject result = (*env)->CallStaticObjectMethod(
    > env, cls, mid, phoneNumberChar, urlChar, userChar, passwordChar);



    You can't pass a char* where a java String is required. Use
    NewString() or NewStringUTF to create the necessary objects.

    /gordon

    --
    [ do not email me copies of your followups ]
    g o r d o n + n e w s @ b a l d e r 1 3 . s e
     
    Gordon Beaton, Oct 19, 2005
    #4
  5. Guest

    This is a great group with great programmers! Using advice given here,
    I got my stuff to work.
    Here is the change to get it working:

    Instead of doing this:
    jobject result = (*env)->CallStaticObjectMethod(
    env, cls, mid, phoneNumberChar, urlChar, userChar, passwordChar);


    I need to do this:

    jobject result = (*env)->CallStaticObjectMethod(
    env, cls, mid,
    (*env)->NewStringUTF(env, phoneNumberChar),
    (*env)->NewStringUTF(env, urlChar),
    (*env)->NewStringUTF(env, userChar),
    (*env)->NewStringUTF(env, passwordChar));

    It works great now. My c program calls a java program that does SOAP
    to a Tomcat server.

    Thanks alot folks!

    XS
     
    , Oct 19, 2005
    #5
  6. On 19 Oct 2005 15:46:33 -0700, wrote:
    > I tried a different way of creating jstring from char* and the result
    > is very different:
    >
    > This works as it successfully returns from Java method, but then it get
    > segmentation fault when I tried to get char* from the jstring:
    >
    > jstring result = (jstring)(*env)->CallStaticObjectMethod(
    > env, cls, mid, //I have seen people calling this method without the
    > 'env' here???


    In C++ env is automatically passed to the function. In C you need to
    pass it explicitly.

    > (*env)->NewStringUTF(env, phoneNumberChar),
    > (*env)->NewStringUTF(env, urlChar),
    > (*env)->NewStringUTF(env, userChar),
    > (*env)->NewStringUTF(env, passwordChar));
    > if (result != NULL) {
    > const char *str = (*env)->GetStringUTFChars(env, result, 0);


    > //here I get segmentation fault
    > printf("message returned is %s\n", str);


    If str is NULL after calling GetStringUTFChars(), you can't pass it to
    printf(). You should check first, and determine whether
    GetStringUTFChars() raised an exception before proceeding.

    Note that every call to GetStringUTFChars() should be matched with a
    call to ReleaseStringUTFChars(). If you are calling this method
    repeatedly it will ultimately fail otherwise.

    > While this causes segmentation fault when calling the java method:
    >
    > jstring phoneNumber = (jstring)(*env)->NewStringUTF(env,
    > phoneNumberChar);
    > jstring url = (jstring)(*env)->NewStringUTF(env, urlChar);
    > jstring user = (jstring)(*env)->NewStringUTF(env, userChar);
    > jstring password = (jstring)(*env)->NewStringUTF(env, passwordChar);
    >
    > jstring result = (jstring)(*env)->CallStaticObjectMethod(
    > env, cls, mid, phoneNumber, url, user, password);
    >
    > Can anyone explain why this is happening? What's the correct way of
    > doing this?


    None of the casts to (jstring) should be necessary, and the use of
    explicit typecasts should be considered a warning flag. Otherwise I
    can't see anything obviously wrong with the code you've posted,

    Your results seem a little erratic, so I wonder if you haven't done
    something wrong elsewhere in the native code. Check for array bounds
    errors, stray pointers, unitialized variables, unchecked return values
    and things like that.

    To help determine the location of the segmentation fault more
    accurately, use fprintf(stderr) rather than printf().

    /gordon

    --
    [ do not email me copies of your followups ]
    g o r d o n + n e w s @ b a l d e r 1 3 . s e
     
    Gordon Beaton, Oct 20, 2005
    #6
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Replies:
    5
    Views:
    26,701
    Mike Schilling
    Mar 29, 2006
  2. Dennis Allison

    interpreting a null pointer as an empty (null string)

    Dennis Allison, Mar 5, 2004, in forum: C Programming
    Replies:
    11
    Views:
    813
    Derk Gwen
    Mar 6, 2004
  3. aneuryzma
    Replies:
    3
    Views:
    717
    Jim Langston
    Jun 16, 2008
  4. Kai-Uwe Bux
    Replies:
    13
    Views:
    699
  5. Christopher
    Replies:
    4
    Views:
    445
    Ruben Safir
    Jul 9, 2011
Loading...

Share This Page