diff --git a/integrations/android/android_jni_lib/java/jni/Android.mk b/integrations/android/android_jni_lib/java/jni/Android.mk index 8b5d5a7..fd3eb7c 100644 --- a/integrations/android/android_jni_lib/java/jni/Android.mk +++ b/integrations/android/android_jni_lib/java/jni/Android.mk @@ -24,7 +24,7 @@ LOCAL_SRC_FILES := \ $(ZTSDK)/SDK_Proxy.cpp \ $(ZTSDK)/SDK_Sockets.c \ $(ZTSDK)/SDK_Debug.c \ - $(ZTSDK)/SDK_ServiceSetup.cpp \ + $(ZTSDK)/SDK_Service.cpp \ $(ZTSDK)/SDK_EthernetTap.cpp # ZeroTierOne ext files diff --git a/make-mac.mk b/make-mac.mk index a27a858..2455a53 100644 --- a/make-mac.mk +++ b/make-mac.mk @@ -99,7 +99,7 @@ remove_only_intermediates: -find . -type f \( -name '*.o' -o -name '*.so' \) -delete osx_shared_lib: remove_only_intermediates $(OBJS) - $(CXX) $(CXXFLAGS) $(LDFLAGS) -DSDK -DZT_ONE_NO_ROOT_CHECK -Iext/lwip/src/include -Iext/lwip/src/include/ipv4 -Iext/lwip/src/include/ipv6 -Izerotierone/osdep -Izerotierone/node -Izerotierone/service -Isrc -shared -o $(BUILD)/libztosx.so $(OBJS) zerotierone/service/OneService.cpp src/SDK_ServiceSetup.cpp src/SDK_EthernetTap.cpp src/SDK_Proxy.cpp zerotierone/one.cpp -x c src/SDK_Sockets.c src/SDK_Intercept.c src/SDK_Debug.c src/SDK_RPC.c $(LDLIBS) -ldl + $(CXX) $(CXXFLAGS) $(LDFLAGS) -DSDK -DZT_ONE_NO_ROOT_CHECK -Iext/lwip/src/include -Iext/lwip/src/include/ipv4 -Iext/lwip/src/include/ipv6 -Izerotierone/osdep -Izerotierone/node -Izerotierone/service -Isrc -shared -o $(BUILD)/libztosx.so $(OBJS) zerotierone/service/OneService.cpp src/SDK_Service.cpp src/SDK_EthernetTap.cpp src/SDK_Proxy.cpp zerotierone/one.cpp -x c src/SDK_Sockets.c src/SDK_Intercept.c src/SDK_Debug.c src/SDK_RPC.c $(LDLIBS) -ldl osx_service_and_intercept: remove_only_intermediates $(OBJS) # Need to selectively rebuild one.cpp and OneService.cpp with ZT_SERVICE_NETCON and ZT_ONE_NO_ROOT_CHECK defined, and also NetconEthernetTap @@ -153,7 +153,7 @@ clean: -rm -rf $(INT)/Unity3D/Assets/Plugins/* -rm -rf zerotier-cli zerotier-idtool -find . -type f \( -name 'zerotier-one' -o -name 'zerotier-sdk-service' \) -delete - -find . -type f \( -name '*.o' -o -name '*.so' -o -name '*.o.d' -o -name '*.out' -o -name '*.log' \) -delete + -find . -type f \( -name '*.o' -o -name '*.so' -o -name '*.o.d' -o -name '*.out' -o -name '*.log' -o -name '*.dSYM' \) -delete # android JNI lib project test -s /usr/bin/javac || { echo "Javac not found"; exit 1; } diff --git a/src/SDK.h b/src/SDK.h index 341ec8b..70087bf 100644 --- a/src/SDK.h +++ b/src/SDK.h @@ -82,6 +82,23 @@ extern char *debug_logfile; // - Depending on the target, the API will be exposed as zt_* in // the specific way needed for that platform, but will be implemented // in terms of zts_* + +// NOTE: Each platform specific exposed API will be implemented in terms of zts_* +// SOCKS5 Proxy Controls +int zts_start_proxy_server(const char *nwid, struct sockaddr_storage *addr); +int zts_stop_proxy_server(const char *nwid); +int zts_get_proxy_server_address(const char * nwid, struct sockaddr_storage *addr); +// ZT Service Controls +void zts_join_network(const char * nwid); +void zts_leave_network(const char * nwid); +bool zts_is_running(); +void zts_get_addresses(const char * nwid, char * addrstr); +int zts_get_device_id(); +void zts_terminate(); +bool zts_is_relayed(); +// ZT Intercept/RPC Controls +void set_intercept_status(int mode); /* TODO: Rethink this */ + int zts_socket(SOCKET_SIG); int zts_connect(CONNECT_SIG); int zts_bind(BIND_SIG); @@ -95,6 +112,7 @@ int zts_getsockopt(GETSOCKOPT_SIG); int zts_getsockname(GETSOCKNAME_SIG); int zts_getpeername(GETPEERNAME_SIG); int zts_close(CLOSE_SIG); +int zts_fcntl(FCNTL_SIG); ssize_t zts_sendto(SENDTO_SIG); ssize_t zts_sendmsg(SENDMSG_SIG); @@ -104,37 +122,54 @@ ssize_t zts_recvmsg(RECVMSG_SIG); #if defined(__UNITY_3D__) ssize_t zts_recv(int fd, void *buf, int len); ssize_t zts_send(int fd, void *buf, int len); - int zts_set_nonblock(int fd); + int zts_set_nonblock(int fd); /* TODO combine with fcntl() */ #endif // Android JNI Direct-call API -// - Implemented in terms of zt_* direct calls +// JNI naming convention: Java_PACKAGENAME_CLASSNAME_METHODNAME +/* If you define anything else in this file it that you wish to expose to your Android + Java application you *must* follow that convention and any corresponding Java package/classes + in your Android project must match this as well */ #if defined(__ANDROID__) + // Exported JNI : ZT SERVICE CONTROLS + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1start_1service(JNIEnv *env, jobject thisObj, jstring path); + JNIEXPORT void JNICALL Java_ZeroTier_SDK_zt_1join_1network(JNIEnv *env, jobject thisObj, jstring nwid); + JNIEXPORT void JNICALL Java_ZeroTier_SDK_zt_1leave_1network(JNIEnv *env, jobject thisObj, jstring nwid); + JNIEXPORT jboolean JNICALL Java_ZeroTier_SDK_zt_1running(JNIEnv *env, jobject thisObj); + JNIEXPORT jobject JNICALL Java_ZeroTier_SDK_zt_1get_1addresses(JNIEnv *env, jobject thisObj, jstring nwid); + JNIEXPORT jboolean JNICALL Java_ZeroTier_SDK_zt_1is_1relayed(); + JNIEXPORT jboolean JNICALL Java_ZeroTier_SDK_zt_1terminate_service(); + // Exported JNI : SOCKS5 PROXY SERVER CONTROLS + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1start_1proxy_1server(JNIEnv *env, jobject thisObj, jstring nwid, jobject zaddr); + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1stop_1proxy_1server(JNIEnv *env, jobject thisObj, jstring nwid); + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1get_1proxy_1server_1address(JNIEnv *env, jobject thisObj, jstring nwid, jobject zaddr); + // Exported JNI : SOCKET API JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1socket(JNIEnv *env, jobject thisObj, jint family, jint type, jint protocol); JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1connect(JNIEnv *env, jobject thisObj, jint fd, jstring addrstr, jint port); JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1bind(JNIEnv *env, jobject thisObj, jint fd, jstring addrstr, jint port); JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1accept4(JNIEnv *env, jobject thisObj, jint fd, jstring addrstr, jint port, jint flags); JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1accept(JNIEnv *env, jobject thisObj, jint fd, jstring addrstr, jint port); JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1listen(JNIEnv *env, jobject thisObj, jint fd, int backlog); - //JNIEXPORT void JNICALL Java_ZeroTier_SDK_zt_1setsockopt(JNIEnv *env, jobject thisObj); - //JNIEXPORT void JNICALL Java_ZeroTier_SDK_zt_1getsockopt(JNIEnv *env, jobject thisObj); - //JNIEXPORT void JNICALL Java_ZeroTier_SDK_zt_1getsockname(JNIEnv *env, jobject thisObj); - JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1close(JNIEnv *env, jobject thisObj, jint fd); // TCP JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1write(JNIEnv *env, jobject thisObj, jint fd, jarray buf, jint len); JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1read(JNIEnv *env, jobject thisObj, jint fd, jarray buf, jint len); - JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1send(JNIEnv *env, jobject thisObj, jint fd, jarray buf, jint len, int flags); - // UDP JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1sendto(JNIEnv *env, jobject thisObj, jint fd, jarray buf, jint len, jint flags, jobject ztaddr); JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1recvfrom(JNIEnv *env, jobject thisObj, jint fd, jarray buf, jint len, jint flags, jobject ztaddr); - + // GENERAL UTILITY + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1close(JNIEnv *env, jobject thisObj, jint fd); JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1fcntl(JNIEnv *env, jobject thisObj, jint socket, jint cmd, jint flags); - - // Takes a given numerical file descriptor and manufactures a java FileDescriptor object for use in javaland - JNIEXPORT jobject JNICALL Java_ZeroTier_SDK_zt_1getFileDescriptor(JNIEnv *env, jobject thisObj, jint fd); + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1setsockopt(JNIEnv *env, jobject thisObj, jint fd, jint level, jint optname, jint optval, jint optlen); + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1getsockopt(JNIEnv *env, jobject thisObj, jint fd, jint level, jint optname, jint optval, jint optlen); + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1getsockname(JNIEnv *env, jobject thisObj, jint fd, jobject ztaddr); + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1getpeername(JNIEnv *env, jobject thisObj, jint fd, jobject ztaddr); +#else + void * zt_start_service(void *thread_id); + void init_service(int key, const char * path); + void init_service_and_rpc(int key, const char * path, const char * nwid); + void init_intercept(int key); #endif diff --git a/integrations/android/example_app/app/src/main/java/ZeroTier/SDK.java b/src/SDK.java similarity index 98% rename from integrations/android/example_app/app/src/main/java/ZeroTier/SDK.java rename to src/SDK.java index 8d2d6ed..7f0c817 100644 --- a/integrations/android/example_app/app/src/main/java/ZeroTier/SDK.java +++ b/src/SDK.java @@ -86,7 +86,7 @@ public class SDK { ArrayList addresses; while (err < 0) { try { - Thread.sleep(500); + Thread.sleep(100); } catch (InterruptedException e) { } addresses = zt_get_addresses(nwid); @@ -134,7 +134,7 @@ public class SDK { ArrayList addresses; while (err < 0) { try { - Thread.sleep(500); + Thread.sleep(100); } catch (InterruptedException e) { } addresses = zt_get_addresses(nwid); @@ -161,7 +161,7 @@ public class SDK { ArrayList addresses; while (err < 0) { try { - Thread.sleep(500); + Thread.sleep(100); } catch (InterruptedException e) { } addresses = zt_get_addresses(nwid); diff --git a/src/SDK_Apple-Bridging-Header.h b/src/SDK_Apple-Bridging-Header.h index 83248ab..f4d512d 100644 --- a/src/SDK_Apple-Bridging-Header.h +++ b/src/SDK_Apple-Bridging-Header.h @@ -5,23 +5,29 @@ #ifndef Example_OSX_Bridging_Header_h #define Example_OSX_Bridging_Header_h -int start_intercept(); -void start_service(const char * path); -void start_service_and_rpc(const char * path, const char * nwid); -void join_network(const char * nwid); -void disable_intercept(); -void enable_intercept(); - #include #include "SDK_Signatures.h" +// ZT INTERCEPT/RPC CONTROLS +int zt_init_rpc(const char *path, const char *nwid); +int start_intercept(); +void disable_intercept(); +void enable_intercept(); + +// ZT SERVICE CONTROLS +void start_service(const char * path); +void start_service_and_rpc(const char * path, const char * nwid); void zt_join_network(const char *nwid); void zt_leave_network(const char *nwid); +void zt_is_running(const char *nwid); void zt_get_addresses(const char *nwid, char * addrstr); -// Direct Call ZT API -// These functions will provide direct access to ZT-enabled sockets with no hassle -int zt_init_rpc(const char *path, const char *nwid); +// SOCKS5 PROXY CONTROLS +void zt_start_proxy_server(const char *nwid, struct sockaddr_storage addr); +void zt_stop_proxy_server(const char *nwid); +void zt_get_proxy_server_address(const char *nwid, struct sockaddr_storage addr); + +// SOCKET API int zt_connect(CONNECT_SIG); int zt_bind(BIND_SIG); int zt_accept(ACCEPT_SIG); @@ -31,6 +37,7 @@ int zt_setsockopt(SETSOCKOPT_SIG); int zt_getsockopt(GETSOCKOPT_SIG); int zt_close(CLOSE_SIG); int zt_getsockname(GETSOCKNAME_SIG); +int zt_getpeername(GETPEERNAME_SIG); #endif /* Example_OSX_Bridging_Header_h */ diff --git a/src/SDK_EthernetTap.cpp b/src/SDK_EthernetTap.cpp index 78e5cb3..1b25c08 100644 --- a/src/SDK_EthernetTap.cpp +++ b/src/SDK_EthernetTap.cpp @@ -58,7 +58,7 @@ #include "lwip/udp.h" #include "SDK_Debug.c" -#include "SDK_ServiceSetup.hpp" +#include "SDK.h" #if !defined(__IOS__) && !defined(__ANDROID__) && !defined(__UNITY_3D__) && !defined(__XCODE__) const ip_addr_t ip_addr_any = { IPADDR_ANY }; diff --git a/src/SDK_JNI_Java_Wapper.java b/src/SDK_JNI_Java_Wapper.java index d633a7e..7f0c817 100644 --- a/src/SDK_JNI_Java_Wapper.java +++ b/src/SDK_JNI_Java_Wapper.java @@ -26,37 +26,250 @@ */ package ZeroTier; -import java.net.SocketAddress; +import java.io.FileDescriptor; +import java.io.FileInputStream; +import java.io.FileOutputStream; +import java.util.ArrayList; +import java.util.zip.ZipError; + +import android.os.ParcelFileDescriptor; +import android.util.Log; +import android.util.Pair; public class SDK { // Socket families - public int AF_UNIX = 1; - public int AF_INET = 2; + public static int AF_UNIX = 1; + public static int AF_INET = 2; // Socket types - public int SOCK_STREAM = 1; - public int SOCK_DGRAM = 2; + public static int SOCK_STREAM = 1; + public static int SOCK_DGRAM = 2; + + // fcntl flags + public static int O_APPEND = 1024; + public static int O_NONBLOCK = 2048; + public static int O_ASYNC = 8192; + public static int O_DIRECT = 65536; + public static int O_NOATIME = 262144; + + // fcntl cmds + public static int F_GETFL = 3; + public static int F_SETFL = 4; // Loads JNI code static { System.loadLibrary("ZeroTierOneJNI"); } // ZeroTier service controls public native void zt_start_service(String homeDir); - public native void zt_join_network(String nwid); - public native void zt_leave_network(String nwid); - public native boolean zt_running(); + public void start_service(String homeDir) { + zt_start_service(homeDir); + } + + public native void zt_join_network(String nwid); + public void join_network(String nwid) { + zt_join_network(nwid); + } + + public native void zt_leave_network(String nwid); + public void leave_network(String nwid) { + zt_leave_network(nwid); + } + + // ------------------------------------------------------------------------------ + // ------------------------------- get_addresses() ------------------------------ + // ------------------------------------------------------------------------------ + + public native ArrayList zt_get_addresses(String nwid); + public ArrayList get_addresses(String nwid) { + int err = -1; + ArrayList addresses; + while (err < 0) { + try { + Thread.sleep(100); + } catch (InterruptedException e) { + } + addresses = zt_get_addresses(nwid); + if (addresses.size() > 0) { + return addresses; + } + } + return null; + } + + public native int zt_get_proxy_port(String nwid); + public int get_proxy_port(String nwid) { + return zt_get_proxy_port(nwid); + } + + public native boolean zt_running(); + public boolean running() { + return zt_running(); + } + + + // ------------------------------------------------------------------------------ + // ----------------------------------- socket() --------------------------------- + // ------------------------------------------------------------------------------ - // Direct-call API - // --- These calls skip the intercept and interface directly via the RPC mechanism public native int zt_socket(int family, int type, int protocol); + public int socket(int family, int type, int protocol) { + return zt_socket(family, type, protocol); + } + + + // ------------------------------------------------------------------------------ + // ----------------------------------- connect() -------------------------------- + // ------------------------------------------------------------------------------ + public native int zt_connect(int fd, String addr, int port); + + public int connect(int sock, ZTAddress zaddr, String nwid) { + return connect(sock, zaddr.Address(), zaddr.Port(), nwid); + } + + public int connect(int sock, String addr, int port, String nwid) + { + int err = -1; + ArrayList addresses; + while (err < 0) { + try { + Thread.sleep(100); + } catch (InterruptedException e) { + } + addresses = zt_get_addresses(nwid); + if (addresses.size() > 0) { + if(!addresses.get(0).startsWith("-1.-1.-1.-1/-1")) { + err = zt_connect(sock, addr, port); + } + } + } + return err; + } + + // ------------------------------------------------------------------------------ + // ------------------------------------ bind() ---------------------------------- + // ------------------------------------------------------------------------------ + public native int zt_bind(int fd, String addr, int port); + + public int bind(int sock, ZTAddress zaddr, String nwid) { + return bind(sock, zaddr.Address(), zaddr.Port(), nwid); + } + public int bind(int sock, String addr, int port, String nwid) { + int err = -1; + ArrayList addresses; + while (err < 0) { + try { + Thread.sleep(100); + } catch (InterruptedException e) { + } + addresses = zt_get_addresses(nwid); + if (addresses.size() > 0) { + if(!addresses.get(0).startsWith("-1.-1.-1.-1/-1")) { + err = zt_bind(sock, addr, port); + } + } + } + return err; + } + + + // ------------------------------------------------------------------------------ + // ---------------------------------- accept4() --------------------------------- + // ------------------------------------------------------------------------------ + public native int zt_accept4(int fd, String addr, int port); - public native int zt_accept(int fd, String addr, int port, int flags); + public int accept4(int fd, String addr, int port) { + return zt_accept4(fd,addr,port); + } + + + // ------------------------------------------------------------------------------ + // ---------------------------------- accept() ---------------------------------- + // ------------------------------------------------------------------------------ + + public native int zt_accept(int fd, ZeroTier.ZTAddress addr); + public int accept(int fd, ZeroTier.ZTAddress addr) { + return zt_accept(fd, addr); + } + + // ------------------------------------------------------------------------------ + // ----------------------------------- listen() --------------------------------- + // ------------------------------------------------------------------------------ + public native int zt_listen(int fd, int backlog); - //public native int zt_getsockopt(int fd, int type, int protocol); - //public native int zt_setsockopt(int fd, int type, int protocol); - //public native int zt_getsockname(int fd, int type, int protocol); + public int listen(int fd, int backlog) { + return zt_listen(fd,backlog); + } + + // ------------------------------------------------------------------------------ + // ----------------------------------- close() ---------------------------------- + // ------------------------------------------------------------------------------ + public native int zt_close(int fd); + public int close(int fd) { + return close(fd); + } + + + // ------------------------------------------------------------------------------ + // ------------------------------------ read() ---------------------------------- + // ------------------------------------------------------------------------------ + + public native int zt_read(int fd, byte[] buf, int len); + public int read(int fd, byte[] buf, int len) { + return zt_read(fd, buf, len); + } + + // ------------------------------------------------------------------------------ + // ----------------------------------- write() ---------------------------------- + // ------------------------------------------------------------------------------ + + public native int zt_write(int fd, byte[] buf, int len); + public int write(int fd, byte[] buf, int len) { + return zt_write(fd, buf, len); + } + + // ------------------------------------------------------------------------------ + // ----------------------------------- sendto() --------------------------------- + // ------------------------------------------------------------------------------ + + public native int zt_sendto(int fd, byte[] buf, int len, int flags, ZeroTier.ZTAddress addr); + public int sendto(int fd, byte[] buf, int len, int flags, ZeroTier.ZTAddress addr){ + return zt_sendto(fd,buf,len,flags,addr); + } + + // ------------------------------------------------------------------------------ + // ----------------------------------- send() ----------------------------------- + // ------------------------------------------------------------------------------ + + public native int zt_send(int fd, byte[] buf, int len, int flags); + public int send(int fd, byte[] buf, int len, int flags) { + return zt_send(fd, buf, len, flags); + } + + // ------------------------------------------------------------------------------ + // ---------------------------------- recvfrom() -------------------------------- + // ------------------------------------------------------------------------------ + + public native int zt_recvfrom(int fd, byte[] buf, int len, int flags, ZeroTier.ZTAddress addr); + public int recvfrom(int fd, byte[] buf, int len, int flags, ZeroTier.ZTAddress addr){ + return zt_recvfrom(fd,buf,len,flags,addr); + } + + // ------------------------------------------------------------------------------ + // ---------------------------------- recvfrom() -------------------------------- + // ------------------------------------------------------------------------------ + + public native int zt_fcntl(int sock, int cmd, int flag); + public int fcntl(int sock, int cmd, int flag) { + return zt_fcntl(sock, F_SETFL, O_NONBLOCK); + } + + + + //public static native int zt_getsockopt(int fd, int type, int protocol); + //public static native int zt_setsockopt(int fd, int type, int protocol); + //public static native int zt_getsockname(int fd, int type, int protocol); } \ No newline at end of file diff --git a/src/SDK_ServiceSetup.cpp b/src/SDK_Service.cpp similarity index 87% rename from src/SDK_ServiceSetup.cpp rename to src/SDK_Service.cpp index ac6a145..dc50034 100644 --- a/src/SDK_ServiceSetup.cpp +++ b/src/SDK_Service.cpp @@ -49,7 +49,6 @@ #include "SDK_EthernetTap.hpp" #include "SDK.h" #include "SDK_Debug.h" -#include "SDK_ServiceSetup.hpp" std::string service_path; pthread_t intercept_thread; @@ -138,6 +137,7 @@ void zts_get_addresses(const char * nwid, char *addrstr) return ip_strings; */ } +int zts_get_device_id() { /* TODO */ return 0; } bool zts_is_relayed() { // TODO @@ -145,15 +145,26 @@ bool zts_is_relayed() { return false; } -int zts_get_proxy_port(const char * nwid) { - uint64_t nwid_int = strtoull(nwid, NULL, 16); - return zt1Service->getTaps()[nwid_int]->proxyListenPort; +int zts_start_proxy_server(const char * nwid, struct sockaddr_storage * addr) { + //uint64_t nwid_int = strtoull(nwid, NULL, 16); + //return zt1Service->getTaps()[nwid_int]->proxyListenPort; + return 0; +} +int zts_stop_proxy_server(const char * nwid) { + //uint64_t nwid_int = strtoull(nwid, NULL, 16); + //return zt1Service->getTaps()[nwid_int]->proxyListenPort; + return 0; +} +int zts_get_proxy_server_address(const char * nwid, struct sockaddr_storage * addr) { + //uint64_t nwid_int = strtoull(nwid, NULL, 16); + //zt1Service->getTaps()[nwid_int]->proxyListenPort; + return 0; } - // Android JNI wrapper // JNI naming convention: Java_PACKAGENAME_CLASSNAME_METHODNAME #if defined(__ANDROID__) + // Join a network JNIEXPORT void JNICALL Java_ZeroTier_SDK_zt_1join_1network(JNIEnv *env, jobject thisObj, jstring nwid) { const char *nwidstr; if(nwid) { @@ -161,6 +172,7 @@ int zts_get_proxy_port(const char * nwid) { zts_join_network(nwidstr); } } + // Leave a network JNIEXPORT void JNICALL Java_ZeroTier_SDK_zt_1leave_1network(JNIEnv *env, jobject thisObj, jstring nwid) { const char *nwidstr; if(nwid) { @@ -168,14 +180,18 @@ int zts_get_proxy_port(const char * nwid) { zts_leave_network(nwidstr); } } + // Returns whether the ZeroTier service is running JNIEXPORT jboolean JNICALL Java_ZeroTier_SDK_zt_1running(JNIEnv *env, jobject thisObj) { if(zt1Service) return zts_is_running(); return false; } - JNIEXPORT void JNICALL Java_ZeroTier_SDK_zt_1terminate(JNIEnv *env, jobject thisObj) { + // Shuts down ZeroTier service and SOCKS5 Proxy server + JNIEXPORT void JNICALL Java_ZeroTier_SDK_zt_1terminate_1service(JNIEnv *env, jobject thisObj) { if(zt1Service) zts_terminate(); + // TODO: Also terminate SOCKS5 Proxy + // zts_stop_proxy_server(); } // FIXME: Re-implemented to make it play nicer with the C-linkage required for Xcode integrations // Now only returns first assigned address per network. Shouldn't normally be a problem @@ -207,12 +223,30 @@ int zts_get_proxy_port(const char * nwid) { return addresses; */ } + // Returns the device is in integer form + JNIEXPORT jint Java_ZeroTier_SDK_zt_1get_1device_1id() { + return zts_get_device_id(); + } + // Returns whether the path to an endpoint is currently relayed by a root server JNIEXPORT jboolean JNICALL Java_ZeroTier_SDK_zt_1is_1relayed() { return zts_is_relayed(); } - JNIEXPORT int JNICALL Java_ZeroTier_SDK_zt_1get_1proxy_1port(JNIEnv *env, jobject thisObj, jstring nwid) { - const char *nwid_str = env->GetStringUTFChars(nwid, NULL); - return zts_get_proxy_port(nwid_str); + // Returns the local address of the SOCKS5 Proxy server + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1get_1proxy_1server_1address(JNIEnv *env, jobject thisObj, jstring nwid, jobject ztaddr) { + // TODO + //const char *nwid_str = env->GetStringUTFChars(nwid, NULL); + //return zts_get_proxy_server_address(nwid_str, addr); + return 0; + } + // Starts a SOCKS5 proxy server for a given ZeroTier network + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1start_1proxy_1server(JNIEnv *env, jobject thisObj, jstring nwid, jobject ztaddr) { + // TODO + return 0; + } + // Stops the SOCKS5 proxy server for a given ZeroTier network + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1stop_1proxy_1server(JNIEnv *env, jobject thisObj, jstring nwid) { + // TODO + return 0; } #endif diff --git a/src/SDK_ServiceSetup.hpp b/src/SDK_ServiceSetup.hpp deleted file mode 100644 index c0bd1f9..0000000 --- a/src/SDK_ServiceSetup.hpp +++ /dev/null @@ -1,81 +0,0 @@ -/* - * ZeroTier One - Network Virtualization Everywhere - * Copyright (C) 2011-2015 ZeroTier, Inc. - * - * This program is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see . - * - * -- - * - * ZeroTier may be used and distributed under the terms of the GPLv3, which - * are available at: http://www.gnu.org/licenses/gpl-3.0.html - * - * If you would like to embed ZeroTier into a commercial application or - * redistribute it in a modified binary form, please contact ZeroTier Networks - * LLC. Start here: http://www.zerotier.com/ - */ - -#ifdef __cplusplus -extern "C" { -#endif - -#if defined(__ANDROID__) - #include -#endif - -//#include - -#ifndef ONE_SERVICE_SETUP_HPP -#define ONE_SERVICE_SETUP_HPP - -#define INTERCEPT_ENABLED 111 -#define INTERCEPT_DISABLED 222 - -#if defined(__ANDROID__) - // JNI naming convention: Java_PACKAGENAME_CLASSNAME_METHODNAME - /* If you define anything else in this file it that you wish to expose to your Android - Java application you *must* follow that convention and any corresponding Java package/classes - in your Android project must match this as well */ - JNIEXPORT void JNICALL Java_ZeroTier_SDK_zt_1join_1network(JNIEnv *env, jobject thisObj, jstring nwid); - JNIEXPORT void JNICALL Java_ZeroTier_SDK_zt_1leave_1network(JNIEnv *env, jobject thisObj, jstring nwid); - JNIEXPORT jboolean JNICALL Java_ZeroTier_SDK_zt_1running(JNIEnv *env, jobject thisObj); - JNIEXPORT jobject JNICALL Java_ZeroTier_SDK_zt_1get_1addresses(JNIEnv *env, jobject thisObj, jstring nwid); - JNIEXPORT jboolean JNICALL Java_ZeroTier_SDK_zt_1is_1relayed(); - JNIEXPORT int JNICALL Java_ZeroTier_SDK_zt_1get_1proxy_1port(JNIEnv *env, jobject thisObj, jstring nwid); -#else - void init_service(int key, const char * path); - void init_service_and_rpc(int key, const char * path, const char * nwid); - void init_intercept(int key); -#endif - -#if defined (__ANDROID__) - JNIEXPORT int JNICALL Java_ZeroTier_SDK_zt_1start_1service(JNIEnv *env, jobject thisObj, jstring path); -#else - void * zt_start_service(void *thread_id); -#endif - -void set_intercept_status(int mode); -void zts_join_network(const char * nwid); -void zts_leave_network(const char * nwid); -bool zts_is_running(); -void zts_terminate(); -void zts_get_addresses(const char * nwid, char * addrstr); -//std::vector zts_get_addresses(std::string nwid); -bool zts_is_relayed(); -int zts_get_proxy_port(const char * nwid); - -#endif - -#ifdef __cplusplus -} -#endif \ No newline at end of file diff --git a/src/SDK_Signatures.h b/src/SDK_Signatures.h index aa4d172..d06083c 100644 --- a/src/SDK_Signatures.h +++ b/src/SDK_Signatures.h @@ -30,7 +30,7 @@ #include -#define SETSOCKOPT_SIG int socket, int level, int option_name, const void *option_value, socklen_t option_len +#define SETSOCKOPT_SIG int socket, int level, int optname, const void *optval, socklen_t optlen #define GETSOCKOPT_SIG int sockfd, int level, int optname, void *optval, socklen_t *optlen #define SENDMSG_SIG int socket, const struct msghdr *message, int flags diff --git a/src/SDK_Sockets.c b/src/SDK_Sockets.c index c8b49af..3f857b5 100644 --- a/src/SDK_Sockets.c +++ b/src/SDK_Sockets.c @@ -378,13 +378,20 @@ int (*realclose)(CLOSE_SIG); return read_bytes; } #endif - + // ------------------------------------------------------------------------------ // --------------------------------- setsockopt() ------------------------------- // ------------------------------------------------------------------------------ // int socket, int level, int option_name, const void *option_value, // socklen_t option_len +#if defined(__ANDROID__) + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1setsockopt( + JNIEnv *env, jobject thisObj, jint fd, jint level, jint optname, jint optval, jint optlen) { + return zts_setsockopt(fd, level, optname, optval, optlen); + } +#endif + #ifdef DYNAMIC_LIB int zt_setsockopt(SETSOCKOPT_SIG) #else @@ -401,6 +408,12 @@ int (*realclose)(CLOSE_SIG); // int sockfd, int level, int optname, void *optval, // socklen_t *optlen +#if defined(__ANDROID__) + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1getsockopt( + JNIEnv *env, jobject thisObj, jint fd, jint level, jint optname, jint optval, jint optlen) { + return zts_getsockopt(fd, level, optname, optval, optlen); + } +#endif #ifdef DYNAMIC_LIB int zt_getsockopt(GETSOCKOPT_SIG) @@ -694,6 +707,20 @@ int (*realclose)(CLOSE_SIG); // ------------------------------------------------------------------------------ // int sockfd, struct sockaddr *addr, socklen_t *addrlen +#if defined(__ANDROID__) + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1getsockname(JNIEnv *env, jobject thisObj, jint fd, jobject ztaddr) { + struct sockaddr_in addr; + int err = zts_getsockname(fd, &addr, sizeof(struct sockaddr)); + jfieldID fid; + jclass cls = (*env)->GetObjectClass(env, ztaddr); + fid = (*env)->GetFieldID(env, cls, "port", "I"); + (*env)->SetIntField(env, ztaddr, fid, addr.sin_port); + fid = (*env)->GetFieldID(env, cls,"_rawAddr", "J"); + (*env)->SetLongField(env, ztaddr, fid,addr.sin_addr.s_addr); + return err; + } +#endif + #ifdef DYNAMIC_LIB int zt_getsockname(GETSOCKNAME_SIG) #else @@ -742,6 +769,20 @@ int (*realclose)(CLOSE_SIG); // ------------------------------------------------------------------------------ // int sockfd, struct sockaddr *addr, socklen_t *addrlen +#if defined(__ANDROID__) + JNIEXPORT jint JNICALL Java_ZeroTier_SDK_zt_1getpeername(JNIEnv *env, jobject thisObj, jint fd, jobject ztaddr) { + struct sockaddr_in addr; + int err = zts_getpeername(fd, &addr, sizeof(struct sockaddr)); + jfieldID fid; + jclass cls = (*env)->GetObjectClass(env, ztaddr); + fid = (*env)->GetFieldID(env, cls, "port", "I"); + (*env)->SetIntField(env, ztaddr, fid, addr.sin_port); + fid = (*env)->GetFieldID(env, cls,"_rawAddr", "J"); + (*env)->SetLongField(env, ztaddr, fid,addr.sin_addr.s_addr); + return err; + } +#endif + #ifdef DYNAMIC_LIB int zt_getpeername(GETSOCKNAME_SIG) #else diff --git a/src/SDK_XcodeWrapper.cpp b/src/SDK_XcodeWrapper.cpp index fd16b7c..df28161 100755 --- a/src/SDK_XcodeWrapper.cpp +++ b/src/SDK_XcodeWrapper.cpp @@ -32,8 +32,7 @@ #define INTERCEPT_ENABLED 111 #define INTERCEPT_DISABLED 222 -#include "SDK_ServiceSetup.hpp" - +// ZEROTIER CONTROLS // Starts a ZeroTier service at the specified path // This will only support SOCKS5 Proxy extern "C" void start_service(const char * path) { @@ -61,6 +60,21 @@ extern "C" void zt_get_addresses(const char * nwid, char * addrstr) { zts_get_addresses(nwid, addrstr); } +// +extern "C" void zt_start_proxy_server(const char *nwid, struct sockaddr_storage *addr) { + zts_start_proxy_server(nwid, addr); +} + +// +extern "C" void zt_stop_proxy_server(const char *nwid) { + zts_stop_proxy_server(nwid); +} + +// +extern "C" void zt_get_proxy_server_address(const char *nwid, struct sockaddr_storage *addr) { + zts_get_proxy_server_address(nwid, addr); +} + // Explicit ZT API wrappers #if !defined(__IOS__) // This isn't available for iOS since function interposition isn't as reliable @@ -69,6 +83,8 @@ extern "C" void zt_get_addresses(const char * nwid, char * addrstr) { } #endif + +// SOCKET API extern "C" int zt_socket(SOCKET_SIG) { return zts_socket(socket_family, socket_type, protocol); } @@ -85,7 +101,7 @@ extern "C" int zt_listen(LISTEN_SIG) { return zts_listen(sockfd, backlog); } extern "C" int zt_setsockopt(SETSOCKOPT_SIG) { - return zts_setsockopt(socket, level, option_name, option_value, option_len); + return zts_setsockopt(socket, level, optname, optval, optlen); } extern "C" int zt_getsockopt(GETSOCKOPT_SIG) { return zts_getsockopt(sockfd, level, optname, optval, optlen); @@ -96,3 +112,9 @@ extern "C" int zt_close(CLOSE_SIG) { extern "C" int zt_getsockname(GETSOCKNAME_SIG) { return zts_getsockname(sockfd, addr, addrlen); } +extern "C" int zt_getpeername(GETPEERNAME_SIG) { + return zts_getpeername(sockfd, addr, addrlen); +} +extern "C" int zt_fcntl(FCNTL_SIG) { + return zts_fcntl(fd, cmd, flags); +} \ No newline at end of file diff --git a/integrations/android/example_app/app/src/main/java/ZeroTier/ZTAddress.java b/src/SDK_ZTAddress.java similarity index 92% rename from integrations/android/example_app/app/src/main/java/ZeroTier/ZTAddress.java rename to src/SDK_ZTAddress.java index 1407849..b347dbb 100644 --- a/integrations/android/example_app/app/src/main/java/ZeroTier/ZTAddress.java +++ b/src/SDK_ZTAddress.java @@ -6,6 +6,13 @@ import java.net.InetSocketAddress; import java.net.UnknownHostException; import java.util.regex.Pattern; +/* + +The ZTAddress object is merely a convenience object for moving address information +across the JNI memory border. + +*/ + public class ZTAddress { // int -> byte array @@ -34,7 +41,7 @@ public class ZTAddress try { return InetAddress.getByAddress(toIPByteArray(_rawAddr)).getHostAddress(); } catch (UnknownHostException e) { - //should never happen + // should never happen return null; } }