Forum Xamarin.Android

Binding Library .aar and Static Native Methods Question

Hi guys,

I'm binding the following library and have made some success, however am now a little uncertain about the following methods and why they are not appearing in the resulting assembly / returning a error message during runtime.

The IO.Realm.Internal.Core.DescriptorOrdering.class (Packaged in realm-android-library-6.0.2.aar) has the following definition.

Namespace is io.realm.internal.core.DescriptorOrdering.class

package io.realm.internal.core;

import io.realm.internal.NativeObject;

public class DescriptorOrdering implements NativeObject {
  private static final long nativeFinalizerMethodPtr = nativeGetFinalizerMethodPtr();

  private final long nativePtr;

  private boolean sortDefined = false;

  private boolean distinctDefined = false;

  private boolean limitDefined = false;

  public DescriptorOrdering() {
    this.nativePtr = nativeCreate();
  }

  public long getNativePtr() {
    return this.nativePtr;
  }

  public long getNativeFinalizerPtr() {
    return nativeFinalizerMethodPtr;
  }

  public void appendSort(QueryDescriptor descriptor) {
    if (this.sortDefined)
      throw new IllegalStateException("A sorting order was already defined. It cannot be redefined"); 
    nativeAppendSort(this.nativePtr, descriptor);
    this.sortDefined = true;
  }

  public void appendDistinct(QueryDescriptor descriptor) {
    if (this.distinctDefined)
      throw new IllegalStateException("A distinct field was already defined. It cannot be redefined"); 
    nativeAppendDistinct(this.nativePtr, descriptor);
    this.distinctDefined = true;
  }

  public void setLimit(long limit) {
    if (this.limitDefined)
      throw new IllegalStateException("A limit was already set. It cannot be redefined."); 
    nativeAppendLimit(this.nativePtr, limit);
    this.limitDefined = true;
  }

  public void appendIncludes(IncludeDescriptor descriptor) {
    nativeAppendInclude(this.nativePtr, descriptor.getNativePtr());
  }

  public boolean isEmpty() {
    return nativeIsEmpty(this.nativePtr);
  }

  private static native long nativeGetFinalizerMethodPtr();

  private static native long nativeCreate();

  private static native void nativeAppendSort(long paramLong, QueryDescriptor paramQueryDescriptor);

  private static native void nativeAppendDistinct(long paramLong, QueryDescriptor paramQueryDescriptor);

  private static native void nativeAppendLimit(long paramLong1, long paramLong2);

  private static native void nativeAppendInclude(long paramLong1, long paramLong2);

  private static native boolean nativeIsEmpty(long paramLong);
}

At the bottom you will notice the following native methods that are defined.

  private static native long nativeGetFinalizerMethodPtr();

  private static native long nativeCreate();

  private static native void nativeAppendSort(long paramLong, QueryDescriptor paramQueryDescriptor);

  private static native void nativeAppendDistinct(long paramLong, QueryDescriptor paramQueryDescriptor);

  private static native void nativeAppendLimit(long paramLong1, long paramLong2);

  private static native void nativeAppendInclude(long paramLong1, long paramLong2);

  private static native boolean nativeIsEmpty(long paramLong);

What i am not quite yet understanding though, is that in the output assembly created, there are no mention of these native methods. Now, i think this may make sense, in that the .aar library attempts to run the native JNI methods when it is run on Android, but when creating a binding library through xamarin i don't quite understand how this works.

Here is the output assembly.

During runtime, the following 'Java.Lnag.UnsatisfiedlInkError' exception is thrown - indicating to me that this hasn't either been built in the output assembly, or is simply not present. And i don't quite understand how to make this work because there is no path=? reference that i can use in the .aar file to bind this section?

{Java.Lang.UnsatisfiedLinkError: No implementation found for long io.realm.internal.core.DescriptorOrdering.nativeGetFinalizerMethodPtr() (tried Java_io_realm_internal_core_DescriptorOrdering_nativeGetFinalizerMethodPtr and Java_io_realm_internal_core_DescriptorOrdering_nativeGetFinalizerMethodPtr__)
  at Java.Interop.JniEnvironment+StaticMethods.CallStaticVoidMethod (Java.Interop.JniObjectReference type, Java.Interop.JniMethodInfo method, Java.Interop.JniArgumentValue* args) [0x0006e] in <e7e2d009b69d4e5f9a00e6ee600b8a8e>:0 
  at Java.Interop.JniPeerMembers+JniStaticMethods.InvokeVoidMethod (System.String encodedMember, Java.Interop.JniArgumentValue* parameters) [0x00018] in <e7e2d009b69d4e5f9a00e6ee600b8a8e>:0 
  at UK.CO.Referencepoint.Android.Smartcard.Sdk.SmartcardClient.Init (Android.Content.Context context, UK.CO.Referencepoint.Android.Smartcard.Sdk.Client.ISmartcardClientEventHandler taskEvents, UK.CO.Referencepoint.Android.Smartcard.Sdk.Client.InitTaskParams initTaskParams) [0x00075] in C:\Users\username\source\repos\CSCS_CardReader_BindingLibraries\obj\Debug\generated\src\UK.CO.Referencepoint.Android.Smartcard.Sdk.SmartcardClient.cs:88 
  at CSCSXamarinTest.MainActivity.initSDK () [0x00032] in C:\Users\username\source\repos\CSCSXamarinTest\MainActivity.cs:149 
  --- End of managed Java.Lang.UnsatisfiedLinkError stack trace ---
java.lang.UnsatisfiedLinkError: No implementation found for long io.realm.internal.core.DescriptorOrdering.nativeGetFinalizerMethodPtr() (tried Java_io_realm_internal_core_DescriptorOrdering_nativeGetFinalizerMethodPtr and Java_io_realm_internal_core_DescriptorOrdering_nativeGetFinalizerMethodPtr__)
    at io.realm.internal.core.DescriptorOrdering.nativeGetFinalizerMethodPtr(Native Method)
    at io.realm.internal.core.DescriptorOrdering.<clinit>(DescriptorOrdering.java:32)
    at io.realm.RealmQuery.<init>(RealmQuery.java:79)
    at io.realm.RealmQuery.createQuery(RealmQuery.java:94)
    at io.realm.Realm.where(Realm.java:1431)
    at uk.co.referencepoint.android.smartcard.sdk.implementation.RealmManager.getSDKConfig(SourceFile:652)
    at uk.co.referencepoint.android.smartcard.sdk.SmartcardClient.a(SourceFile:332)
    at uk.co.referencepoint.android.smartcard.sdk.SmartcardClient.init(SourceFile:126)
    at uk.co.referencepoint.android.smartcard.sdk.SmartcardClient.init(SourceFile:95)
    at crc6407d72197f03059e3.MainActivity.n_onCreate(Native Method)
    at crc6407d72197f03059e3.MainActivity.onCreate(MainActivity.java:32)
    at android.app.Activity.performCreate(Activity.java:7458)
    at android.app.Activity.performCreate(Activity.java:7448)
    at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1286)
    at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:3409)
    at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3614)
    at android.app.servertransaction.LaunchActivityItem.execute(LaunchActivityItem.java:86)
    at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:108)
    at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:68)
    at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2199)
    at android.os.Handler.dispatchMessage(Handler.java:112)
    at android.os.Looper.loop(Looper.java:216)
    at android.app.ActivityThread.main(ActivityThread.java:7625)
    at java.lang.reflect.Method.invoke(Native Method)
    at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:524)
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:987)
}

Can anyone provide me a little further insight to this please, as to if this is expected behaviour, or if there is something that i am missing. So far the Xamarin Library compiles fine, runs the android application until the SDK i am using tries to initialize itselfs and then comes to this issue with IO.Realm. The 'native static long / void' methods and the fact i can't see them in the output has me doubting that i've done this correctly, or misunderstood how to make the native side of this work.

Any help would be greatly appreciate.

Thank you.

Sign In or Register to comment.