diff options
Diffstat (limited to 'java')
-rw-r--r-- | java/jni/ZT1_jniutils.cpp | 166 | ||||
-rw-r--r-- | java/jni/ZT1_jniutils.h | 6 | ||||
-rw-r--r-- | java/jni/com_zerotierone_sdk_Node.cpp | 19 | ||||
-rw-r--r-- | java/src/com/zerotierone/sdk/MulticastGroup.java | 2 |
4 files changed, 175 insertions, 18 deletions
diff --git a/java/jni/ZT1_jniutils.cpp b/java/jni/ZT1_jniutils.cpp index 72f65447..87340f12 100644 --- a/java/jni/ZT1_jniutils.cpp +++ b/java/jni/ZT1_jniutils.cpp @@ -1,9 +1,21 @@ #include "ZT1_jniutils.h" +#include <string> +#include <assert.h> #ifdef __cplusplus extern "C" { #endif +namespace +{ + static jclass arrayListClass = NULL; + static jmethodID arrayList_constructor = NULL; + static jmethodID arrayList_add = NULL; + + static jclass inetAddressClass = NULL; + static jmethodID inetAddress_getByAddress = NULL; +} + jobject createResultObject(JNIEnv *env, ZT1_ResultCode code) { // cache the class so we don't have to @@ -172,30 +184,162 @@ jobject createVirtualNetworkType(JNIEnv *env, ZT1_VirtualNetworkType type) vntypeObject = env->GetStaticObjectField(vntypeClass, enumField); return vntypeObject; } - + jobject newArrayList(JNIEnv *env) { - return NULL; -} + if(arrayListClass == NULL) + { + arrayListClass = env->FindClass("java/util/ArrayList"); + if(arrayListClass == NULL) + { + return NULL; + } + } -jobject appendItemToArrayList(JNIEnv *env, jobject object) -{ - return NULL; + if(arrayList_constructor == NULL) + { + arrayList_constructor = env->GetMethodID( + arrayListClass, "<init>", "()V"); + if(arrayList_constructor == NULL) + { + return NULL; + } + } + + jobject arrayListObj = env->NewObject(arrayListClass, arrayList_constructor); + + return arrayListObj; } -jobject newIPV6Address(JNIEnv *env, char *addr) +bool appendItemToArrayList(JNIEnv *env, jobject array, jobject object) { - return NULL; + assert(array != NULL); + assert(object != NULL); + + if(arrayList_add == NULL) + { + arrayList_add = env->GetMethodID(arrayListClass, "add", "(Ljava.lang.Object;)Z"); + if(arrayList_add == NULL) + { + return false; + } + } + + return env->CallBooleanMethod(array, arrayList_add, object); } -jobject newIPV4Address(JNIEnv *env, char *addr) +jobject newInetAddress(JNIEnv *env, const sockaddr_storage &addr) { - return NULL; + if(inetAddressClass == NULL) + { + inetAddressClass = env->FindClass("java/net/InetAddress"); + if(inetAddressClass == NULL) + { + return NULL; + } + } + + if(inetAddress_getByAddress == NULL) + { + inetAddress_getByAddress = env->GetStaticMethodID( + inetAddressClass, "getByAddress", "([B)Ljava/net/InetAddress;"); + if(inetAddress_getByAddress == NULL) + { + return NULL; + } + } + + jobject inetAddressObj = NULL; + switch(addr.ss_family) + { + case AF_INET6: + { + sockaddr_in6 *ipv6 = (sockaddr_in6*)&addr; + jbyteArray buff = env->NewByteArray(16); + if(buff == NULL) + { + return NULL; + } + + env->SetByteArrayRegion(buff, 0, 16, (jbyte*)ipv6->sin6_addr.s6_addr); + inetAddressObj = env->CallStaticObjectMethod( + inetAddressClass, inetAddress_getByAddress, buff); + } + break; + case AF_INET: + { + sockaddr_in *ipv4 = (sockaddr_in*)&addr; + jbyteArray buff = env->NewByteArray(4); + if(buff == NULL) + { + return NULL; + } + + env->SetByteArrayRegion(buff, 0, 4, (jbyte*)&ipv4->sin_addr); + inetAddressObj = env->CallStaticObjectMethod( + inetAddressClass, inetAddress_getByAddress, buff); + } + break; + } + + return inetAddressObj; } jobject newMulticastGroup(JNIEnv *env, const ZT1_MulticastGroup &mc) { - return NULL; + static jclass multicastGroupClass = NULL; + static jmethodID multicastGroup_constructor = NULL; + + static jfieldID macField = NULL; + static jfieldID adiField = NULL; + + if(multicastGroupClass == NULL) + { + multicastGroupClass = env->FindClass("com/zerotierone/sdk/MulticastGroup"); + if(multicastGroupClass == NULL) + { + return NULL; + } + } + + if(multicastGroup_constructor == NULL) + { + multicastGroup_constructor = env->GetMethodID( + multicastGroupClass, "<init>", "()V"); + if(multicastGroup_constructor == NULL) + { + return NULL; + } + } + + jobject multicastGroupObj = env->NewObject(multicastGroupClass, multicastGroup_constructor); + if(multicastGroupObj == NULL) + { + return NULL; + } + + if(macField == NULL) + { + macField = env->GetFieldID(multicastGroupClass, "mac", "J"); + if(macField == NULL) + { + return NULL; + } + } + + if(adiField == NULL) + { + adiField = env->GetFieldID(multicastGroupClass, "adi", "J"); + if(adiField == NULL) + { + return NULL; + } + } + + env->SetLongField(multicastGroupObj, macField, mc.mac); + env->SetLongField(multicastGroupObj, adiField, mc.adi); + + return multicastGroupObj; } #ifdef __cplusplus diff --git a/java/jni/ZT1_jniutils.h b/java/jni/ZT1_jniutils.h index b6e3c45b..e881e394 100644 --- a/java/jni/ZT1_jniutils.h +++ b/java/jni/ZT1_jniutils.h @@ -9,13 +9,13 @@ extern "C" { jobject createResultObject(JNIEnv *env, ZT1_ResultCode code); jobject createVirtualNetworkStatus(JNIEnv *env, ZT1_VirtualNetworkStatus status); +jobject createVirtualNetworkType(JNIEnv *env, ZT1_VirtualNetworkType type); jobject createEvent(JNIEnv *env, ZT1_Event event); jobject newArrayList(JNIEnv *env); -jobject appendItemToArrayList(JNIEnv *env, jobject object); +bool appendItemToArrayList(JNIEnv *env, jobject array, jobject object); -jobject newIPV6Address(JNIEnv *env, char *addr); -jobject newIPV4Address(JNIEnv *env, char *addr); +jobject newInetAddress(JNIEnv *env, const sockaddr_storage &addr); jobject newMulticastGroup(JNIEnv *env, const ZT1_MulticastGroup &mc); #ifdef __cplusplus diff --git a/java/jni/com_zerotierone_sdk_Node.cpp b/java/jni/com_zerotierone_sdk_Node.cpp index 4d940076..b0a1bae8 100644 --- a/java/jni/com_zerotierone_sdk_Node.cpp +++ b/java/jni/com_zerotierone_sdk_Node.cpp @@ -933,16 +933,27 @@ JNIEXPORT jobject JNICALL Java_com_zerotierone_sdk_Node_networkConfig env->SetBooleanField(vnetConfigObj, portErrorField, vnetConfig->portError); - jobject mcastSubsArrayObj = NULL; - jobject assignedAddrArrayObj = NULL; + jobject mcastSubsArrayObj = newArrayList(env); + for(unsigned int i = 0; i < vnetConfig->multicastSubscriptionCount; ++i) + { + jobject mcastObj = newMulticastGroup(env, vnetConfig->multicastSubscriptions[i]); + appendItemToArrayList(env, mcastSubsArrayObj, mcastObj); + } + env->SetObjectField(vnetConfigObj, multicastSubscriptionsField, mcastSubsArrayObj); - env->SetObjectField(vnetConfigObj, multicastSubscriptionsField, mcastSubsArrayObj); + jobject assignedAddrArrayObj = newArrayList(env); + for(unsigned int i = 0; i < vnetConfig->assignedAddressCount; ++i) + { + jobject inetAddrObj = newInetAddress(env, vnetConfig->assignedAddresses[i]); + appendItemToArrayList(env, assignedAddrArrayObj, inetAddrObj); + } + env->SetObjectField(vnetConfigObj, assignedAddressesField, assignedAddrArrayObj); ZT1_Node_freeQueryResult(node, vnetConfig); vnetConfig = NULL; - + return vnetConfigObj; } diff --git a/java/src/com/zerotierone/sdk/MulticastGroup.java b/java/src/com/zerotierone/sdk/MulticastGroup.java index c1318d86..89ba206f 100644 --- a/java/src/com/zerotierone/sdk/MulticastGroup.java +++ b/java/src/com/zerotierone/sdk/MulticastGroup.java @@ -28,6 +28,8 @@ package com.zerotierone.sdk; public class MulticastGroup { + private MulticastGroup() {} + private long mac; private long adi; } |