Skip to content

Commit

Permalink
[monodroid] Prevent a segfault when Java class name is unavailable
Browse files Browse the repository at this point in the history
Context: dotnet#5619

It appears that Xamarin.Android application uploaded to Google Console
internal Test Track can fail the pre-launch test because the
`MonodroidRuntime::get_java_class_name_for_TypeManager` method, can
sometimes get a `nullptr` Java class name from JNI:

    Build fingerprint: 'google/blueline/blueline:9/PQ3A.190801.002/5670241:user/release-keys'
    Revision: 'MP1.0'
    ABI: 'arm64'
    pid: 15773, tid: 15773, name: com.Myapp  >>> com.Myapp<<<
    signal 11 (SIGSEGV), code 1 (SEGV_MAPERR), fault addr 0x0
    Cause: null pointer dereference
        x0  0000000000000000  x1  0000000000000000  x2  0000000000000000  x3  00000000000000e1
        x4  0000000000000000  x5  0000000000000305  x6  0000000000000006  x7  0000000000000010
        x8  0101010101010101  x9  4adfd1b7ed2e23e2  x10 0000000000430000  x11 000000000000000a
        x12 0000000000000002  x13 0000000000000001  x14 00000000000000a8  x15 000000000000000a
        x16 0000007f703f00f8  x17 0000007f7031f290  x18 0000000000000008  x19 0000000000000000
        x20 0000007eecae0460  x21 0000000000000000  x22 0000000000000000  x23 0000000000000099
        x24 0000000000000085  x25 0000007eecb30010  x26 0000000000000099  x27 0000000000000000
        x28 0000007f724255e0  x29 0000007fe01ad010
        sp  0000007fe01acff0  lr  0000007f7036f3b4  pc  0000007f7031f2a0
    backtrace:
        #00 pc 000000000001e2a0  /system/lib64/libc.so (strlen+16)
        #1 pc 000000000006e3b0  /system/lib64/libc.so (strdup+20)
        #2 pc 000000000000d4e8  /data/app/com.Myapp-1lufsJe3FIZ0YHoEAB08KA==/split_config.arm64_v8a.apk (offset 0x165d000) (xamarin::android::internal::MonodroidRuntime::get_java_class_name_for_TypeManager(_jclass*)+92)
        #3 pc 000000000005f6d0  <anonymous:0000007ecc4ac000>

This can happen if either one of the below points is true:

  1. The Java	[`Class.getName`](https://developer.android.com/reference/java/lang/Class?hl=en#getName())
     method is absent
  2. `Class.getName` returns `nullptr` (a nameless class?)
  3. `env->GetStringUTFChars` returns `nullptr` (a memory allocation
     failure?)

Out of these, 3. appears to be most probable and this commit adds a
check for a `nullptr` pointer there, failing gracefully instead of
segfaulting.  This is NOT a fix for the original problem as we don't
know by what it is caused but, nevertheless, the `nullptr` check should
be there.
  • Loading branch information
grendello committed Feb 16, 2021
1 parent a8a30f3 commit 57051a5
Showing 1 changed file with 10 additions and 0 deletions.
10 changes: 10 additions & 0 deletions src/monodroid/jni/monodroid-glue.cc
Original file line number Diff line number Diff line change
Expand Up @@ -2027,7 +2027,17 @@ MonodroidRuntime::get_java_class_name_for_TypeManager (jclass klass)

JNIEnv *env = osBridge.ensure_jnienv ();
jstring name = reinterpret_cast<jstring> (env->CallObjectMethod (klass, Class_getName));
if (name == nullptr) {
log_error (LOG_DEFAULT, "Failed to obtain Java class name for object at %p", klass);
return nullptr;
}

const char *mutf8 = env->GetStringUTFChars (name, nullptr);
if (mutf8 == nullptr) {
log_error (LOG_DEFAULT, "Failed to convert Java class name to UTF8 (out of memory?)");
env->DeleteLocalRef (name);
return nullptr;
}
char *ret = strdup (mutf8);

env->ReleaseStringUTFChars (name, mutf8);
Expand Down

0 comments on commit 57051a5

Please sign in to comment.