Unity3D .NET API and documentation update

This commit is contained in:
Joseph Henry
2016-08-25 17:08:48 -07:00
parent 18ad4c79b7
commit e8b840d7ce
22 changed files with 798 additions and 247 deletions

View File

@@ -1,4 +1,4 @@
ZeroTier SDK (alpha) ZeroTier SDK (beta)
====== ======
ZeroTier-enabled apps. Virtual network access embedded directly into applications and games. ZeroTier-enabled apps. Virtual network access embedded directly into applications and games.

View File

@@ -22,7 +22,9 @@ For more support on these integrations, or if you'd like help creating a new int
*** ***
## Current Integrations ## Current Integrations
### Apple `make apple` ### Apple
- For everything: `make apple`
##### iOS ##### iOS
- [Embedding within an app](apple/example_app/iOS) `make ios_app_framework` -> `build/ios_app_framework/*` - [Embedding within an app](apple/example_app/iOS) `make ios_app_framework` -> `build/ios_app_framework/*`
- Unity3D plugin `make ios_unity3d_bundle` -> `build/ios_unity3d_bundle/*` - Unity3D plugin `make ios_unity3d_bundle` -> `build/ios_unity3d_bundle/*`
@@ -38,7 +40,9 @@ For more support on these integrations, or if you'd like help creating a new int
- [Dynamic-linking into an app/service at runtime](../docs/linux_zt_sdk.md) `make linux_shared_lib` - [Dynamic-linking into an app/service at runtime](../docs/linux_zt_sdk.md) `make linux_shared_lib`
- [Using the SDK with Docker](docker) - [Using the SDK with Docker](docker)
### Android `make android` ### Android
- For everything: `make android`
- [Embedding within an app](android) `make android_jni_lib` -> `build/android_jni_lib/YOUR_ARCH/libZeroTierOneJNI.so` - [Embedding within an app](android) `make android_jni_lib` -> `build/android_jni_lib/YOUR_ARCH/libZeroTierOneJNI.so`
- [Unity 3D plugin](../docs/android_unity3d_zt_sdk.md) `make android_unity3d_plugin` -> `build/android_unity3d_plugin/*` - [Unity 3D plugin](../docs/android_unity3d_zt_sdk.md) `make android_unity3d_plugin` -> `build/android_unity3d_plugin/*`

View File

@@ -16,11 +16,11 @@ This short tutorial will show you how to enable ZeroTier functionality for your
**Step 2: Integrate SDK into project** **Step 2: Integrate SDK into project**
- Add the resultant framework package to your project - Add the resultant framework package to your project
- Add `zerotiersdk/src` directory to `Build Settings -> Header Search Paths` - Add `src` directory to *Build Settings -> Header Search Paths*
- Add `build/ios_app_framework/Release-iphoneos/` to *Build Settings -> Framework Search Paths* - Add `build/ios_app_framework/Release-iphoneos/` to *Build Settings -> Framework Search Paths*
- Add `ZeroTierSDK.frameworkiOS` to *General->Embedded Binaries* - Add `ZeroTierSDK.frameworkiOS` to *General->Embedded Binaries*
- Add `src/SDK_XcodeWrapper.cpp` and `src/SDK_XcodeWrapper.hpp` to your project: - Add `src/SDK_XcodeWrapper.cpp` and `src/SDK_XcodeWrapper.hpp` to your project:
- Set `src/SDK_Apple-Bridging-Header.h` as your bridging-header in `Build Settings -> Objective-C Bridging-header` - Set `src/SDK_Apple-Bridging-Header.h` as your bridging-header in *Build Settings -> Objective-C Bridging-header*
**Step 3: Start the ZeroTier service** **Step 3: Start the ZeroTier service**
@@ -43,16 +43,12 @@ dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0), {
}); });
``` ```
*NOTE: If you enabled the proxy service via `-DUSE_SOCKS_PROXY` it will start automatically and be reachable at `0.0.0.0:1337`*
**Step 4: Pick an API** **Step 4: Pick an API**
The following APIs are available for this integration: The following APIs are available for this integration:
- `Hook of BSD-like sockets`: Use BSD-like sockets as you normally would.
- `Proxy of NSStream`: Create NSStream. Configure stream for SOCKS5 Proxy. Use stream.
- `Direct Call`: Consult [src/SDK_Apple-Bridging-Header.h](../../../../src/SDK_Apple-Bridging-Header.h). - `Direct Call`: Consult [src/SDK_Apple-Bridging-Header.h](../../../../src/SDK_Apple-Bridging-Header.h).
- `Hook of BSD-like sockets`: Use BSD-like sockets as you normally would. This likely won't work for calls used by a third-party library.
If functional interposition isn't available for the API or library you've chosen to use, ZeroTier offers a SOCKS5 proxy server which can allow connectivity to your virtual network as long as your client API supports the SOCKS5 protocol. This proxy service will run alongside the tap service and can be turned on by compiling with the `-DUSE_SOCKS_PROXY` flag in *Build Settings->Other C Flags*. By default, the proxy service is available at `0.0.0.0:1337`. - `Proxy of NSStream`: Create NSStream. Configure stream for SOCKS5 Proxy (127.0.0.1:PORT). Start Proxy. Use stream.
**Step 5: Join a network!** **Step 5: Join a network!**

View File

@@ -11,53 +11,57 @@ This short tutorial will show you how to enable ZeroTier functionality for your
## Via Traditional Linking (Everything bundled) ## Via Traditional Linking (Everything bundled)
- Use this if you'd like everything included in a single easy-to-use library.
``` ```
make osx_shared_lib` make osx_shared_lib`
g++ myapp.cpp -o myapp libztosx.so g++ app.cpp -o app libztosx.so
./myapp ./app
``` ```
## Via Traditional Linking (Service+Intercept model) ## Via Traditional Linking (Service+Intercept model)
- Use this model if you'd like multiple applications to talk to the same ZeroTierSDK service instance. Often the *intercept-model* is used when you don't have access to the source of an app and you'd like to re-direct its network calls.
Example: Example:
gcc myapp.c -o myapp libztintercept.so gcc app.c -o app libztintercept.so
export ZT_NC_NETWORK=/tmp/sdk-test-home/nc_8056c2e21c000001 export ZT_NC_NETWORK=/tmp/sdk-test-home/nc_8056c2e21c000001
Start service Start service
./zerotier-sdk-service -d -p8000 /tmp/sdk-test-home ./zerotier-sdk-service -d -p8000 /tmp/sdk-test-home &
Run application Run application
./myapp ./app
## Via App Framework in XCode ## Via App Framework in XCode
*** ***
**Step 1: Build iOS framework** **Step 1: Build OSX framework**
- `make ios_app_framework` - `make osx_app_framework`
- This will output to `build/ios_app_framework/Release-iphoneos/ZeroTierSDK_iOS.framework` - This will output to `build/osx_app_framework/Release/ZeroTierSDK_OSX.framework`
**Step 2: Integrate SDK into project** **Step 2: Integrate SDK into project**
- Add the resultant framework package to your project - Add the resultant framework package to your project
- Add `zerotiersdk/src` directory to `Build Settings -> Header Search Paths` - Add `src` directory to *Build Settings -> Header Search Paths*
- Add `build/osx_app_framework/Release-iphoneos/` to *Build Settings -> Framework Search Paths* - Add `build/osx_app_framework/Release/` to *Build Settings -> Framework Search Paths*
- Add `ZeroTierSDK.frameworkiOS` to *General->Embedded Binaries* - Add `ZeroTierSDK.frameworkOSX` to *General->Embedded Binaries*
- Add `src/SDK_XcodeWrapper.cpp` and `src/SDK_XcodeWrapper.hpp` to your project: - Add `src/SDK_XcodeWrapper.cpp` and `src/SDK_XcodeWrapper.hpp` to your project:
- Set `src/SDK_Apple-Bridging-Header.h` as your bridging-header in `Build Settings -> Objective-C Bridging-header` - Set `src/SDK_Apple-Bridging-Header.h` as your bridging-header in *Build Settings -> Objective-C Bridging-header*
**Step 3: Start the ZeroTier service** **Step 3: Start the ZeroTier service**
Now find a place in your code to set up the ZeroTier service thread: Set up the ZeroTier service thread:
``` ```
var service_thread : NSThread! var service_thread : NSThread!
func zt_start_service() { func zt_start_service() {
let path = NSSearchPathForDirectoriesInDomains(NSSearchPathDirectory.DocumentDirectory, NSSearchPathDomainMask.UserDomainMask, true) let path = NSSearchPathForDirectoriesInDomains(NSSearchPathDirectory.DocumentDirectory, NSSearchPathDomainMask.UserDomainMask, true)
start_service(path[0]) start_service(".") // "." path will tell ZeroTier to write its config data to the same directory as the binary
} }
``` ```
@@ -70,16 +74,12 @@ dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0), {
}); });
``` ```
*NOTE: If you enabled the proxy service via `-DUSE_SOCKS_PROXY` it will start automatically and be reachable at `0.0.0.0:1337`*
**Step 4: Pick an API** **Step 4: Pick an API**
The following APIs are available for this integration: The following APIs are available for this integration:
- `Hook of BSD-like sockets`: Use BSD-like sockets as you normally would.
- `Proxy of NSStream`: Create NSStream. Configure stream for SOCKS5 Proxy. Use stream.
- `Direct Call`: Consult [src/SDK_Apple-Bridging-Header.h](../../../../src/SDK_Apple-Bridging-Header.h). - `Direct Call`: Consult [src/SDK_Apple-Bridging-Header.h](../../../../src/SDK_Apple-Bridging-Header.h).
- `Hook of BSD-like sockets`: Use BSD-like sockets as you normally would.
If functional interposition isn't available for the API or library you've chosen to use, ZeroTier offers a SOCKS5 proxy server which can allow connectivity to your virtual network as long as your client API supports the SOCKS5 protocol. This proxy service will run alongside the tap service and can be turned on by compiling with the `-DUSE_SOCKS_PROXY` flag in *Build Settings->Other C Flags*. By default, the proxy service is available at `0.0.0.0:1337`. - `Proxy of NSStream`: Create NSStream. Configure stream for SOCKS5 Proxy (127.0.0.1:PORT). Start Proxy. Use stream.
**Step 5: Join a network!** **Step 5: Join a network!**

View File

@@ -1,4 +1,4 @@
ZeroTier SDK (alpha) ZeroTier SDK (beta)
====== ======
ZeroTier-enabled apps. Virtual network access embedded directly into applications and games. ZeroTier-enabled apps. Virtual network access embedded directly into applications and games.

View File

@@ -22,7 +22,9 @@ For more support on these integrations, or if you'd like help creating a new int
*** ***
## Current Integrations ## Current Integrations
### Apple `make apple` ### Apple
- For everything: `make apple`
##### iOS ##### iOS
- [Embedding within an app](apple/example_app/iOS) `make ios_app_framework` -> `build/ios_app_framework/*` - [Embedding within an app](apple/example_app/iOS) `make ios_app_framework` -> `build/ios_app_framework/*`
- Unity3D plugin `make ios_unity3d_bundle` -> `build/ios_unity3d_bundle/*` - Unity3D plugin `make ios_unity3d_bundle` -> `build/ios_unity3d_bundle/*`
@@ -38,7 +40,9 @@ For more support on these integrations, or if you'd like help creating a new int
- [Dynamic-linking into an app/service at runtime](../docs/linux_zt_sdk.md) `make linux_shared_lib` - [Dynamic-linking into an app/service at runtime](../docs/linux_zt_sdk.md) `make linux_shared_lib`
- [Using the SDK with Docker](docker) - [Using the SDK with Docker](docker)
### Android `make android` ### Android
- For everything: `make android`
- [Embedding within an app](android) `make android_jni_lib` -> `build/android_jni_lib/YOUR_ARCH/libZeroTierOneJNI.so` - [Embedding within an app](android) `make android_jni_lib` -> `build/android_jni_lib/YOUR_ARCH/libZeroTierOneJNI.so`
- [Unity 3D plugin](../docs/android_unity3d_zt_sdk.md) `make android_unity3d_plugin` -> `build/android_unity3d_plugin/*` - [Unity 3D plugin](../docs/android_unity3d_zt_sdk.md) `make android_unity3d_plugin` -> `build/android_unity3d_plugin/*`

View File

@@ -62,9 +62,8 @@
<Compile Include="Assets\OBJ-IO\Plugins\Mesh\OBJ\OBJMaterial.cs" /> <Compile Include="Assets\OBJ-IO\Plugins\Mesh\OBJ\OBJMaterial.cs" />
<Compile Include="Assets\OBJ-IO\Plugins\Utils\Int32Converter.cs" /> <Compile Include="Assets\OBJ-IO\Plugins\Utils\Int32Converter.cs" />
<Compile Include="Assets\WorldMain.cs" /> <Compile Include="Assets\WorldMain.cs" />
<Compile Include="Assets\ZeroTierNetworkInterface.cs" /> <Compile Include="Assets\ZTSDK.cs" />
<Compile Include="Assets\ZeroTierSockets_Demo.cs" /> <Compile Include="Assets\ZeroTierSockets_Demo.cs" />
<Compile Include="Assets\ZeroTierUtils.cs" />
<None Include="Assets\OBJ-IO\Readme.txt" /> <None Include="Assets\OBJ-IO\Readme.txt" />
<Reference Include="UnityEngine.Networking"> <Reference Include="UnityEngine.Networking">
<HintPath>/Applications/Unity/Unity.app/Contents/UnityExtensions/Unity/Networking/UnityEngine.Networking.dll</HintPath> <HintPath>/Applications/Unity/Unity.app/Contents/UnityExtensions/Unity/Networking/UnityEngine.Networking.dll</HintPath>

View File

@@ -0,0 +1,46 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>BuildMachineOSBuild</key>
<string>15F34</string>
<key>CFBundleDevelopmentRegion</key>
<string>en</string>
<key>CFBundleExecutable</key>
<string>ZeroTierSDK_Unity3D_OSX</string>
<key>CFBundleIdentifier</key>
<string>zerotier.ZeroTierSDK-Unity3D-OSX</string>
<key>CFBundleInfoDictionaryVersion</key>
<string>6.0</string>
<key>CFBundleName</key>
<string>ZeroTierSDK_Unity3D_OSX</string>
<key>CFBundlePackageType</key>
<string>BNDL</string>
<key>CFBundleShortVersionString</key>
<string>1.0</string>
<key>CFBundleSignature</key>
<string>????</string>
<key>CFBundleSupportedPlatforms</key>
<array>
<string>MacOSX</string>
</array>
<key>CFBundleVersion</key>
<string>1</string>
<key>DTCompiler</key>
<string>com.apple.compilers.llvm.clang.1_0</string>
<key>DTPlatformBuild</key>
<string>7D1014</string>
<key>DTPlatformVersion</key>
<string>GM</string>
<key>DTSDKBuild</key>
<string>15E60</string>
<key>DTSDKName</key>
<string>macosx10.11</string>
<key>DTXcode</key>
<string>0731</string>
<key>DTXcodeBuild</key>
<string>7D1014</string>
<key>NSHumanReadableCopyright</key>
<string>Copyright © 2016 ZeroTier Inc. All rights reserved.</string>
</dict>
</plist>

View File

@@ -0,0 +1,105 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>files</key>
<dict/>
<key>files2</key>
<dict/>
<key>rules</key>
<dict>
<key>^Resources/</key>
<true/>
<key>^Resources/.*\.lproj/</key>
<dict>
<key>optional</key>
<true/>
<key>weight</key>
<real>1000</real>
</dict>
<key>^Resources/.*\.lproj/locversion.plist$</key>
<dict>
<key>omit</key>
<true/>
<key>weight</key>
<real>1100</real>
</dict>
<key>^version.plist$</key>
<true/>
</dict>
<key>rules2</key>
<dict>
<key>.*\.dSYM($|/)</key>
<dict>
<key>weight</key>
<real>11</real>
</dict>
<key>^(.*/)?\.DS_Store$</key>
<dict>
<key>omit</key>
<true/>
<key>weight</key>
<real>2000</real>
</dict>
<key>^(Frameworks|SharedFrameworks|PlugIns|Plug-ins|XPCServices|Helpers|MacOS|Library/(Automator|Spotlight|LoginItems))/</key>
<dict>
<key>nested</key>
<true/>
<key>weight</key>
<real>10</real>
</dict>
<key>^.*</key>
<true/>
<key>^Info\.plist$</key>
<dict>
<key>omit</key>
<true/>
<key>weight</key>
<real>20</real>
</dict>
<key>^PkgInfo$</key>
<dict>
<key>omit</key>
<true/>
<key>weight</key>
<real>20</real>
</dict>
<key>^Resources/</key>
<dict>
<key>weight</key>
<real>20</real>
</dict>
<key>^Resources/.*\.lproj/</key>
<dict>
<key>optional</key>
<true/>
<key>weight</key>
<real>1000</real>
</dict>
<key>^Resources/.*\.lproj/locversion.plist$</key>
<dict>
<key>omit</key>
<true/>
<key>weight</key>
<real>1100</real>
</dict>
<key>^[^/]+$</key>
<dict>
<key>nested</key>
<true/>
<key>weight</key>
<real>10</real>
</dict>
<key>^embedded\.provisionprofile$</key>
<dict>
<key>weight</key>
<real>20</real>
</dict>
<key>^version\.plist$</key>
<dict>
<key>weight</key>
<real>20</real>
</dict>
</dict>
</dict>
</plist>

View File

@@ -37,6 +37,7 @@ using System.Net.Sockets;
using System.Net; using System.Net;
using System.IO; using System.IO;
using System.Collections.Generic; using System.Collections.Generic;
using System.Globalization;
// TODO: // TODO:
/* /*
@@ -49,7 +50,7 @@ using System.Collections.Generic;
* */ * */
// Provides a bare-bones interface to ZeroTier-administered sockets // Provides a bare-bones interface to ZeroTier-administered sockets
public class ZeroTierNetworkInterface { public class ZTSDK {
// ZeroTier background thread // ZeroTier background thread
protected Thread ztThread; protected Thread ztThread;
@@ -91,47 +92,45 @@ public class ZeroTierNetworkInterface {
private static extern int unity_start_service(string path); private static extern int unity_start_service(string path);
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
private static extern int unity_start_service_and_rpc(string path, string nwid); private static extern int unity_start_service_and_rpc(string path, string nwid);
[DllImport (DLL_PATH)]
protected static extern bool zts_is_running();
[DllImport (DLL_PATH)]
protected static extern void zts_stop_service();
// Connection calls // Connection calls
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
protected static extern int zt_socket(int family, int type, int protocol); protected static extern int zts_socket(int family, int type, int protocol);
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
unsafe protected static extern int zt_bind(int sockfd, System.IntPtr addr, int addrlen); unsafe protected static extern int zts_bind(int sockfd, System.IntPtr addr, int addrlen);
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
unsafe protected static extern int zt_connect(int sockfd, System.IntPtr addr, int addrlen); unsafe protected static extern int zts_connect(int sockfd, System.IntPtr addr, int addrlen);
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
protected static extern int zt_accept(int sockfd); protected static extern int zts_accept(int sockfd);
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
protected static extern int zt_listen(int sockfd, int backlog); protected static extern int zts_listen(int sockfd, int backlog);
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
protected static extern int zt_close(int sockfd); protected static extern int zts_close(int sockfd);
// RX / TX // RX / TX
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
unsafe protected static extern int zt_recv(int sockfd, [In, Out] IntPtr buf, int len); unsafe protected static extern int zts_recv(int sockfd, [In, Out] IntPtr buf, int len);
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
unsafe protected static extern int zt_send(int sockfd, IntPtr buf, int len); unsafe protected static extern int zts_send(int sockfd, IntPtr buf, int len);
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
unsafe protected static extern int zt_set_nonblock(int sockfd); unsafe protected static extern int zts_set_nonblock(int sockfd);
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
unsafe protected static extern int zt_sendto(int fd, IntPtr buf, int len, int flags, System.IntPtr addr, int addrlen); unsafe protected static extern int zts_sendto(int fd, IntPtr buf, int len, int flags, System.IntPtr addr, int addrlen);
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
unsafe protected static extern int zt_recvfrom(int fd, [In, Out] IntPtr buf, int len, int flags, System.IntPtr addr, int addrlen); unsafe protected static extern int zts_recvfrom(int fd, [In, Out] IntPtr buf, int len, int flags, System.IntPtr addr, int addrlen);
// ZT Thread controls
[DllImport (DLL_PATH)]
protected static extern bool zt_is_running();
[DllImport (DLL_PATH)]
protected static extern void zt_terminate();
// ZT Network controls // ZT Network controls
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
protected static extern bool zt_join_network(string nwid); protected static extern void zts_join_network(string nwid);
[DllImport (DLL_PATH)] [DllImport (DLL_PATH)]
protected static extern void zt_leave_network(string nwid); protected static extern void zts_leave_network(string nwid);
#endregion #endregion
// Interop structures // Interop structures
@@ -208,19 +207,21 @@ public class ZeroTierNetworkInterface {
} }
// Initialize the ZeroTier service with a given path // Initialize the ZeroTier service with a given path
public ZeroTierNetworkInterface(string path, string nwid) { public ZTSDK(string path, string nwid) {
Debug.Log("ZTSDK(): " + nwid);
this.path = path; this.path = path;
this.nwid = nwid; this.nwid = nwid;
Init(); Init();
} }
public ZeroTierNetworkInterface (string path) { public ZTSDK (string path) {
this.path = path; this.path = path;
Init(); Init();
} }
// Initialize the ZeroTier service // Initialize the ZeroTier service
public ZeroTierNetworkInterface() { public ZTSDK() {
Init(); Init();
} }
@@ -229,7 +230,7 @@ public class ZeroTierNetworkInterface {
public bool JoinNetwork(string nwid) public bool JoinNetwork(string nwid)
{ {
if(!joined_to_network) { if(!joined_to_network) {
zt_join_network(nwid); zts_join_network(nwid);
return true; return true;
} }
return false; return false;
@@ -242,7 +243,7 @@ public class ZeroTierNetworkInterface {
return false; return false;
} }
else { else {
zt_leave_network(nwid); zts_leave_network(nwid);
return true; return true;
} }
} }
@@ -251,28 +252,28 @@ public class ZeroTierNetworkInterface {
// Creates a new ZeroTier-administered socket // Creates a new ZeroTier-administered socket
public int Socket(int family, int type, int protocol) public int Socket(int family, int type, int protocol)
{ {
return zt_socket (family, type, protocol); return zts_socket (family, type, protocol);
} }
// Binds to a specific address // Binds to a specific address
public int Bind(int fd, string addr, int port) public int Bind(int fd, string addr, int port)
{ {
GCHandle sockaddr_ptr = ZeroTierUtils.Generate_unmananged_sockaddr(addr + ":" + port); GCHandle sockaddr_ptr = Generate_unmananged_sockaddr(addr + ":" + port);
IntPtr pSockAddr = sockaddr_ptr.AddrOfPinnedObject (); IntPtr pSockAddr = sockaddr_ptr.AddrOfPinnedObject ();
int addrlen = Marshal.SizeOf (pSockAddr); int addrlen = Marshal.SizeOf (pSockAddr);
return zt_bind (fd, pSockAddr, addrlen); return zts_bind (fd, pSockAddr, addrlen);
} }
// Listens for an incoming connection request // Listens for an incoming connection request
public int Listen(int fd, int backlog) public int Listen(int fd, int backlog)
{ {
return zt_listen(fd, backlog); return zts_listen(fd, backlog);
} }
// Accepts an incoming connection // Accepts an incoming connection
public int Accept(int fd) public int Accept(int fd)
{ {
return zt_accept (fd); return zts_accept (fd);
} }
// Closes a connection // Closes a connection
@@ -284,17 +285,17 @@ public class ZeroTierNetworkInterface {
// Connects to a remote host // Connects to a remote host
public int Connect(int fd, string addr, int port) public int Connect(int fd, string addr, int port)
{ {
GCHandle sockaddr_ptr = ZeroTierUtils.Generate_unmananged_sockaddr(addr + ":" + port); GCHandle sockaddr_ptr = Generate_unmananged_sockaddr(addr + ":" + port);
IntPtr pSockAddr = sockaddr_ptr.AddrOfPinnedObject (); IntPtr pSockAddr = sockaddr_ptr.AddrOfPinnedObject ();
int addrlen = Marshal.SizeOf (pSockAddr); int addrlen = Marshal.SizeOf (pSockAddr);
return zt_connect (fd, pSockAddr, addrlen); return zts_connect (fd, pSockAddr, addrlen);
} }
public int Read(int fd, ref char[] buf, int len) public int Read(int fd, ref char[] buf, int len)
{ {
GCHandle handle = GCHandle.Alloc(buf, GCHandleType.Pinned); GCHandle handle = GCHandle.Alloc(buf, GCHandleType.Pinned);
IntPtr ptr = handle.AddrOfPinnedObject(); IntPtr ptr = handle.AddrOfPinnedObject();
int bytes_read = zt_recv (fd, ptr, len*2); int bytes_read = zts_recv (fd, ptr, len*2);
string str = Marshal.PtrToStringAuto(ptr); string str = Marshal.PtrToStringAuto(ptr);
//Marshal.Copy (ptr, buf, 0, bytes_read); //Marshal.Copy (ptr, buf, 0, bytes_read);
buf = Marshal.PtrToStringAnsi(ptr).ToCharArray(); buf = Marshal.PtrToStringAnsi(ptr).ToCharArray();
@@ -308,7 +309,7 @@ public class ZeroTierNetworkInterface {
//error = 0; //error = 0;
int bytes_written; int bytes_written;
// FIXME: Sending a length of 2X the buffer size seems to fix the object pinning issue // FIXME: Sending a length of 2X the buffer size seems to fix the object pinning issue
if((bytes_written = zt_send(fd, ptr, len*2)) < 0) { if((bytes_written = zts_send(fd, ptr, len*2)) < 0) {
//error = (byte)bytes_written; //error = (byte)bytes_written;
} }
return bytes_written; return bytes_written;
@@ -322,11 +323,11 @@ public class ZeroTierNetworkInterface {
int bytes_written; int bytes_written;
// Form address structure // Form address structure
GCHandle sockaddr_ptr = ZeroTierUtils.Generate_unmananged_sockaddr(addr + ":" + port); GCHandle sockaddr_ptr = Generate_unmananged_sockaddr(addr + ":" + port);
IntPtr pSockAddr = sockaddr_ptr.AddrOfPinnedObject (); IntPtr pSockAddr = sockaddr_ptr.AddrOfPinnedObject ();
int addrlen = Marshal.SizeOf (pSockAddr); int addrlen = Marshal.SizeOf (pSockAddr);
if((bytes_written = zt_sendto(fd, ptr, len*2, flags, pSockAddr, addrlen)) < 0) { if((bytes_written = zts_sendto(fd, ptr, len*2, flags, pSockAddr, addrlen)) < 0) {
//error = (byte)bytes_written; //error = (byte)bytes_written;
} }
return bytes_written; return bytes_written;
@@ -339,11 +340,11 @@ public class ZeroTierNetworkInterface {
IntPtr ptr = handle.AddrOfPinnedObject(); IntPtr ptr = handle.AddrOfPinnedObject();
// Form address structure // Form address structure
GCHandle sockaddr_ptr = ZeroTierUtils.Generate_unmananged_sockaddr(addr + ":" + port); GCHandle sockaddr_ptr = Generate_unmananged_sockaddr(addr + ":" + port);
IntPtr pSockAddr = sockaddr_ptr.AddrOfPinnedObject (); IntPtr pSockAddr = sockaddr_ptr.AddrOfPinnedObject ();
int addrlen = Marshal.SizeOf (pSockAddr); int addrlen = Marshal.SizeOf (pSockAddr);
int bytes_read = zt_recvfrom(fd, ptr, len*2, flags, pSockAddr, addrlen); int bytes_read = zts_recvfrom(fd, ptr, len*2, flags, pSockAddr, addrlen);
string str = Marshal.PtrToStringAuto(ptr); string str = Marshal.PtrToStringAuto(ptr);
//Marshal.Copy (ptr, buf, 0, bytes_read); //Marshal.Copy (ptr, buf, 0, bytes_read);
buf = Marshal.PtrToStringAnsi(ptr).ToCharArray(); buf = Marshal.PtrToStringAnsi(ptr).ToCharArray();
@@ -354,13 +355,63 @@ public class ZeroTierNetworkInterface {
// Returns whether the ZeroTier service is currently running // Returns whether the ZeroTier service is currently running
public bool IsRunning() public bool IsRunning()
{ {
return zt_is_running (); return zts_is_running ();
} }
// Terminates the ZeroTier service // Terminates the ZeroTier service
public void Terminate() public void Terminate()
{ {
zt_terminate (); zts_stop_service ();
} }
#endregion #endregion
// --- Utilities ---
// Handles IPv4 and IPv6 notation.
public static IPEndPoint CreateIPEndPoint(string endPoint)
{
string[] ep = endPoint.Split(':');
if (ep.Length < 2) throw new FormatException("Invalid endpoint format");
IPAddress ip;
if (ep.Length > 2) {
if (!IPAddress.TryParse(string.Join(":", ep, 0, ep.Length - 1), out ip)) {
throw new FormatException("Invalid ip-adress");
}
}
else {
if (!IPAddress.TryParse(ep[0], out ip)) {
throw new FormatException("Invalid ip-adress");
}
}
int port;
if (!int.TryParse(ep[ep.Length - 1], NumberStyles.None, NumberFormatInfo.CurrentInfo, out port)) {
throw new FormatException("Invalid port");
}
return new IPEndPoint(ip, port);
}
// Generates an unmanaged sockaddr structure from a string-formatted endpoint
public static GCHandle Generate_unmananged_sockaddr(string endpoint_str)
{
IPEndPoint ipEndPoint;
ipEndPoint = CreateIPEndPoint (endpoint_str);
SocketAddress socketAddress = ipEndPoint.Serialize ();
// use an array of bytes instead of the sockaddr structure
byte[] sockAddrStructureBytes = new byte[socketAddress.Size];
GCHandle sockAddrHandle = GCHandle.Alloc (sockAddrStructureBytes, GCHandleType.Pinned);
for (int i = 0; i < socketAddress.Size; ++i) {
sockAddrStructureBytes [i] = socketAddress [i];
}
return sockAddrHandle;
}
public static GCHandle Generate_unmanaged_buffer(byte[] buf)
{
// use an array of bytes instead of the sockaddr structure
GCHandle sockAddrHandle = GCHandle.Alloc (buf, GCHandleType.Pinned);
return sockAddrHandle;
}
} }

View File

@@ -43,7 +43,7 @@ public class ZeroTierSockets_Demo : MonoBehaviour
{ {
public float speed = 300f; public float speed = 300f;
private ZeroTierNetworkInterface zt; private ZTSDK zt;
string nwid = ""; string nwid = "";
int sock; // The "connection id" int sock; // The "connection id"
@@ -222,7 +222,7 @@ public class ZeroTierSockets_Demo : MonoBehaviour
GameObject go; GameObject go;
go = GameObject.Find ("inputNetworkID"); go = GameObject.Find ("inputNetworkID");
input = go.GetComponents<InputField> () [0]; input = go.GetComponents<InputField> () [0];
input.text = "XXXXXXXXXXXXXXXX"; input.text = "8056c2e21c000001";
go = GameObject.Find ("inputServerAddress"); go = GameObject.Find ("inputServerAddress");
input = go.GetComponents<InputField> () [0]; input = go.GetComponents<InputField> () [0];
input.text = "10.9.9.203"; input.text = "10.9.9.203";
@@ -234,7 +234,7 @@ public class ZeroTierSockets_Demo : MonoBehaviour
input.text = "Welcome to the machine"; input.text = "Welcome to the machine";
// Create new instance of ZeroTier in separate thread // Create new instance of ZeroTier in separate thread
zt = new ZeroTierNetworkInterface ("/Users/ztest", "XXXXXXXXXXXXXXXX"); zt = new ZTSDK (".", "8056c2e21c000001");
} }
// Terminate the ZeroTier service when the application quits // Terminate the ZeroTier service when the application quits

View File

@@ -1,82 +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 <http://www.gnu.org/licenses/>.
*
* --
*
* 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/
*/
using UnityEngine;
using System.Collections;
using System.Net;
using System;
using System.Globalization;
using System.Runtime.InteropServices;
public class ZeroTierUtils {
// Handles IPv4 and IPv6 notation.
public static IPEndPoint CreateIPEndPoint(string endPoint)
{
string[] ep = endPoint.Split(':');
if (ep.Length < 2) throw new FormatException("Invalid endpoint format");
IPAddress ip;
if (ep.Length > 2) {
if (!IPAddress.TryParse(string.Join(":", ep, 0, ep.Length - 1), out ip)) {
throw new FormatException("Invalid ip-adress");
}
}
else {
if (!IPAddress.TryParse(ep[0], out ip)) {
throw new FormatException("Invalid ip-adress");
}
}
int port;
if (!int.TryParse(ep[ep.Length - 1], NumberStyles.None, NumberFormatInfo.CurrentInfo, out port)) {
throw new FormatException("Invalid port");
}
return new IPEndPoint(ip, port);
}
// Generates an unmanaged sockaddr structure from a string-formatted endpoint
public static GCHandle Generate_unmananged_sockaddr(string endpoint_str)
{
IPEndPoint ipEndPoint;
ipEndPoint = ZeroTierUtils.CreateIPEndPoint (endpoint_str);
SocketAddress socketAddress = ipEndPoint.Serialize ();
// use an array of bytes instead of the sockaddr structure
byte[] sockAddrStructureBytes = new byte[socketAddress.Size];
GCHandle sockAddrHandle = GCHandle.Alloc (sockAddrStructureBytes, GCHandleType.Pinned);
for (int i = 0; i < socketAddress.Size; ++i) {
sockAddrStructureBytes [i] = socketAddress [i];
}
return sockAddrHandle;
}
public static GCHandle Generate_unmanaged_buffer(byte[] buf)
{
// use an array of bytes instead of the sockaddr structure
GCHandle sockAddrHandle = GCHandle.Alloc (buf, GCHandleType.Pinned);
return sockAddrHandle;
}
}

View File

@@ -37,7 +37,7 @@ public class MainActivity extends AppCompatActivity {
while(!zt.running()) { } while(!zt.running()) { }
// client/server mode toggle // client/server mode toggle
int mode = 2, err; int mode = 4, err;
// Listen to incoming connections // Listen to incoming connections
if(mode==1) if(mode==1)
@@ -46,38 +46,38 @@ public class MainActivity extends AppCompatActivity {
int sock = zt.socket(SDK.AF_INET, SDK.SOCK_STREAM, 0); int sock = zt.socket(SDK.AF_INET, SDK.SOCK_STREAM, 0);
if((err = zt.bind(sock, "0.0.0.0", 8080, nwid)) < 0) if((err = zt.bind(sock, "0.0.0.0", 8080, nwid)) < 0)
Log.d("ZT-TEST", "bind_err = " + err + "\n"); Log.d("ZTSDK", "bind_err = " + err + "\n");
if((err = zt.listen(sock,1)) < 0) if((err = zt.listen(sock,1)) < 0)
Log.d("ZT-TEST", "listen_err = " + err); Log.d("ZTSDK", "listen_err = " + err);
if((err = zt.accept(sock,null)) < 0) if((err = zt.accept(sock,null)) < 0)
Log.d("ZT-TEST", "accept_err = " + err); Log.d("ZTSDK", "accept_err = " + err);
Log.d("ZT-TEST", "Waiting to accept connection..."); Log.d("ZTSDK", "Waiting to accept connection...");
// ... // ...
} }
// TCP Echo ZT-TEST (CLIENT) // TCP Echo ZTSDK (CLIENT)
if(mode==2) if(mode==2)
{ {
Log.d("ZT-TEST", "\n\nStarting TCP Echo ZT-TEST\n\n"); Log.d("ZTSDK", "\n\nStarting TCP Echo ZTSDK\n\n");
zt.join_network(nwid); zt.join_network(nwid);
int sock = zt.socket(SDK.AF_INET, SDK.SOCK_STREAM, 0); int sock = zt.socket(SDK.AF_INET, SDK.SOCK_STREAM, 0);
String msg = "Welcome to the machine!"; String msg = "Welcome to the machine!";
err = zt.connect(sock, "28.206.65.211", 8099, nwid); err = zt.connect(sock, "28.206.65.211", 8099, nwid);
Log.d("ZT-TEST", "err = " + err + "\n"); Log.d("ZTSDK", "err = " + err + "\n");
return; //return;
// ECHO // ECHO
while(true) while(true)
{ {
// TX // TX
if((err = zt.write(sock, msg.getBytes(), msg.length())) > 0) { if((err = zt.write(sock, msg.getBytes(), msg.length())) > 0) {
Log.d("ZT-TEST", "TX: " + msg + " --- " + err + " bytes"); Log.d("ZTSDK", "TX: " + msg + " --- " + err + " bytes");
} }
// RX // RX
@@ -85,14 +85,14 @@ public class MainActivity extends AppCompatActivity {
Arrays.fill(buffer, (byte)0); Arrays.fill(buffer, (byte)0);
if((err = zt.read(sock, buffer, buffer.length)) > 0) { if((err = zt.read(sock, buffer, buffer.length)) > 0) {
String bufStr = new String(buffer).substring(0, err); String bufStr = new String(buffer).substring(0, err);
Log.d("ZT-TEST", "RX: " + bufStr + " --- " + err + " bytes"); Log.d("ZTSDK", "RX: " + bufStr + " --- " + err + " bytes");
} }
} }
// zt.stop_service(); // zt.stop_service();
} }
// SOCKS5 Proxy ZT-TEST // SOCKS5 Proxy ZTSDK
if(mode==3) if(mode==3)
{ {
zt.join_network(nwid); zt.join_network(nwid);
@@ -102,18 +102,18 @@ public class MainActivity extends AppCompatActivity {
Log.d("ZTSDK", "Setting up connection to SDK proxy server"); Log.d("ZTSDK", "Setting up connection to SDK proxy server");
SocketAddress proxyAddr = new InetSocketAddress("127.0.0.1", proxyPort); SocketAddress proxyAddr = new InetSocketAddress("127.0.0.1", proxyPort);
Proxy proxy = new Proxy(Proxy.Type.SOCKS, proxyAddr); Proxy proxy = new Proxy(Proxy.Type.SOCKS, proxyAddr);
Log.d("ZT-TEST", "toString() = " + proxy.toString()); Log.d("ZTSDK", "toString() = " + proxy.toString());
final Socket s = new Socket(proxy); final Socket s = new Socket(proxy);
final SocketAddress remoteAddr = new InetSocketAddress("10.9.9.100", 8080); final SocketAddress remoteAddr = new InetSocketAddress("10.9.9.100", 8080);
// Wait for address to be assigned // Wait for address to be assigned
ArrayList<String> addresses = zt.get_addresses(nwid); ArrayList<String> addresses = zt.get_addresses(nwid);
for(int i=0; i<addresses.size(); i++) { for(int i=0; i<addresses.size(); i++) {
Log.d("ZT-TEST", "Address = " + addresses.get(i)); Log.d("ZTSDK", "Address = " + addresses.get(i));
} }
while(addresses.size() > 0 && addresses.get(0).equals("-1.-1.-1.-1/-1")) { while(addresses.size() > 0 && addresses.get(0).equals("-1.-1.-1.-1/-1")) {
try { try {
Log.d("ZT-TEST", "waiting for address"); Log.d("ZTSDK", "waiting for address");
Thread.sleep(100); Thread.sleep(100);
} catch (java.lang.InterruptedException e) { } catch (java.lang.InterruptedException e) {
} }
@@ -127,36 +127,36 @@ public class MainActivity extends AppCompatActivity {
s.connect(remoteAddr, 1000); s.connect(remoteAddr, 1000);
} }
catch(java.io.IOException e) { catch(java.io.IOException e) {
Log.d("ZT-TEST", "Unable to establish connection to SOCKS5 Proxy server\n"); Log.d("ZTSDK", "Unable to establish connection to SOCKS5 Proxy server\n");
} }
} }
}).start(); }).start();
} }
// UDP Echo ZT-TEST // UDP Echo ZTSDK
if(mode==4) if(mode==4)
{ {
// Remote server address (will be populated by recvfrom() // Remote server address (will be populated by recvfrom()
ZTAddress remoteServer = new ZTAddress(); ZTAddress remoteServer = new ZTAddress();
ZTAddress bindAddr = new ZTAddress("0.0.0.0", 8080); ZTAddress bindAddr = new ZTAddress("0.0.0.0", 8080);
Log.d("ZT-TEST", "\n\nStarting UDP Echo ZT-TEST\n\n"); Log.d("ZTSDK", "\n\nStarting UDP Echo ZTSDK\n\n");
nwid = "8056c2e21c000001"; nwid = "8056c2e21c000001";
zt.join_network(nwid); zt.join_network(nwid);
int sock = zt.socket(SDK.AF_INET, SDK.SOCK_DGRAM, 0); int sock = zt.socket(SDK.AF_INET, SDK.SOCK_DGRAM, 0);
Log.d("ZT-TEST", "binding..."); Log.d("ZTSDK", "binding...");
if((err = zt.bind(sock, bindAddr, nwid)) < 0) if((err = zt.bind(sock, bindAddr, nwid)) < 0)
Log.d("ZT-TEST", "bind_err = " + err + "\n"); Log.d("ZTSDK", "bind_err = " + err + "\n");
if((err = zt.listen(sock, 0)) < 0) if((err = zt.listen(sock, 0)) < 0)
Log.d("ZT-TEST", "listen_err = " + err); Log.d("ZTSDK", "listen_err = " + err);
ArrayList<String> addresses = zt.get_addresses(nwid); ArrayList<String> addresses = zt.get_addresses(nwid);
if(addresses.size() < 0) { if(addresses.size() < 0) {
Log.d("ZT-TEST", "unable to obtain ZT address"); Log.d("ZTSDK", "unable to obtain ZT address");
return; return;
} }
else { else {
Log.d("ZT-TEST", "IPV4 = " + addresses.get(0)); Log.d("ZTSDK", "App IP = " + addresses.get(0));
} }
String bufStr; String bufStr;
@@ -170,16 +170,16 @@ public class MainActivity extends AppCompatActivity {
// RX // RX
if((err = zt.recvfrom(sock, buffer, 32, 0, remoteServer)) > 0) { if((err = zt.recvfrom(sock, buffer, 32, 0, remoteServer)) > 0) {
bufStr = new String(buffer).substring(0, err); bufStr = new String(buffer).substring(0, err);
Log.d("ZT-TEST", "read (" + err + ") bytes from " + remoteServer.Address() + " : " + remoteServer.Port() + ", msg = " + bufStr); Log.d("ZTSDK", "read (" + err + ") bytes from " + remoteServer.Address() + " : " + remoteServer.Port() + ", msg = " + bufStr);
// TX // TX
String msg = "Welcome response from android\n"; String msg = "Welcome response from android\n";
err = zt.sendto(sock, msg.getBytes(), msg.length(), 0, remoteServer); err = zt.sendto(sock, msg.getBytes(), msg.length(), 0, remoteServer);
if (err < 0) if (err < 0)
Log.d("ZT-TEST", "sendto_err = " + err); Log.d("ZTSDK", "sendto_err = " + err);
} }
} }
//Log.d("ZT-TEST", "leaving network"); //Log.d("ZTSDK", "leaving network");
//zt.leave_network(nwid); //zt.leave_network(nwid);
} }
} }

View File

@@ -9,6 +9,7 @@
/* Begin PBXBuildFile section */ /* Begin PBXBuildFile section */
7C0252A51D62945B005D5FD8 /* SDK_Service.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CAA03DE1D628E88003F9B1A /* SDK_Service.cpp */; }; 7C0252A51D62945B005D5FD8 /* SDK_Service.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CAA03DE1D628E88003F9B1A /* SDK_Service.cpp */; };
7C6F654E1D6F6BA1004F6CDF /* SDK_Service.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CAA03DE1D628E88003F9B1A /* SDK_Service.cpp */; }; 7C6F654E1D6F6BA1004F6CDF /* SDK_Service.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CAA03DE1D628E88003F9B1A /* SDK_Service.cpp */; };
7C9587951D6FB4C80014AF6B /* SDK_Service.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CAA03DE1D628E88003F9B1A /* SDK_Service.cpp */; };
7CAA03DF1D628E88003F9B1A /* SDK_Service.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CAA03DE1D628E88003F9B1A /* SDK_Service.cpp */; }; 7CAA03DF1D628E88003F9B1A /* SDK_Service.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CAA03DE1D628E88003F9B1A /* SDK_Service.cpp */; };
7CC003261D1216E3003E68DC /* ZeroTierSDK_iOS.h in Headers */ = {isa = PBXBuildFile; fileRef = 7CC003251D1216E3003E68DC /* ZeroTierSDK_iOS.h */; settings = {ATTRIBUTES = (Public, ); }; }; 7CC003261D1216E3003E68DC /* ZeroTierSDK_iOS.h in Headers */ = {isa = PBXBuildFile; fileRef = 7CC003251D1216E3003E68DC /* ZeroTierSDK_iOS.h */; settings = {ATTRIBUTES = (Public, ); }; };
7CC003501D12178D003E68DC /* SDK_Debug.c in Sources */ = {isa = PBXBuildFile; fileRef = 7CC003421D12178D003E68DC /* SDK_Debug.c */; }; 7CC003501D12178D003E68DC /* SDK_Debug.c in Sources */ = {isa = PBXBuildFile; fileRef = 7CC003421D12178D003E68DC /* SDK_Debug.c */; };
@@ -1193,6 +1194,7 @@
isa = PBXSourcesBuildPhase; isa = PBXSourcesBuildPhase;
buildActionMask = 2147483647; buildActionMask = 2147483647;
files = ( files = (
7C9587951D6FB4C80014AF6B /* SDK_Service.cpp in Sources */,
7CC005201D1324B3003E68DC /* lz4.c in Sources */, 7CC005201D1324B3003E68DC /* lz4.c in Sources */,
7CC005211D1324B3003E68DC /* http_parser.c in Sources */, 7CC005211D1324B3003E68DC /* http_parser.c in Sources */,
7CC004FD1D1324AB003E68DC /* etharp.c in Sources */, 7CC004FD1D1324AB003E68DC /* etharp.c in Sources */,

View File

@@ -268,7 +268,7 @@
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
CLANG_ENABLE_MODULES = YES; CLANG_ENABLE_MODULES = YES;
COMBINE_HIDPI_IMAGES = YES; COMBINE_HIDPI_IMAGES = YES;
FRAMEWORK_SEARCH_PATHS = "$(PROJECT_DIR)/../../../../build/OSX_app_framework/Debug"; FRAMEWORK_SEARCH_PATHS = "$(PROJECT_DIR)/../../../../build/OSX_app_framework/Release";
HEADER_SEARCH_PATHS = "$(SRCROOT)/../../../../src"; HEADER_SEARCH_PATHS = "$(SRCROOT)/../../../../src";
INFOPLIST_FILE = Example_OSX_App/Info.plist; INFOPLIST_FILE = Example_OSX_App/Info.plist;
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks"; LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks";
@@ -286,7 +286,7 @@
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
CLANG_ENABLE_MODULES = YES; CLANG_ENABLE_MODULES = YES;
COMBINE_HIDPI_IMAGES = YES; COMBINE_HIDPI_IMAGES = YES;
FRAMEWORK_SEARCH_PATHS = "$(PROJECT_DIR)/../../../../build/OSX_app_framework/Debug"; FRAMEWORK_SEARCH_PATHS = "$(PROJECT_DIR)/../../../../build/OSX_app_framework/Release";
HEADER_SEARCH_PATHS = "$(SRCROOT)/../../../../src"; HEADER_SEARCH_PATHS = "$(SRCROOT)/../../../../src";
INFOPLIST_FILE = Example_OSX_App/Info.plist; INFOPLIST_FILE = Example_OSX_App/Info.plist;
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks"; LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks";

View File

@@ -11,53 +11,57 @@ This short tutorial will show you how to enable ZeroTier functionality for your
## Via Traditional Linking (Everything bundled) ## Via Traditional Linking (Everything bundled)
- Use this if you'd like everything included in a single easy-to-use library.
``` ```
make osx_shared_lib` make osx_shared_lib`
g++ myapp.cpp -o myapp libztosx.so g++ app.cpp -o app libztosx.so
./myapp ./app
``` ```
## Via Traditional Linking (Service+Intercept model) ## Via Traditional Linking (Service+Intercept model)
- Use this model if you'd like multiple applications to talk to the same ZeroTierSDK service instance. Often the *intercept-model* is used when you don't have access to the source of an app and you'd like to re-direct its network calls.
Example: Example:
gcc myapp.c -o myapp libztintercept.so gcc app.c -o app libztintercept.so
export ZT_NC_NETWORK=/tmp/sdk-test-home/nc_8056c2e21c000001 export ZT_NC_NETWORK=/tmp/sdk-test-home/nc_8056c2e21c000001
Start service Start service
./zerotier-sdk-service -d -p8000 /tmp/sdk-test-home ./zerotier-sdk-service -d -p8000 /tmp/sdk-test-home &
Run application Run application
./myapp ./app
## Via App Framework in XCode ## Via App Framework in XCode
*** ***
**Step 1: Build iOS framework** **Step 1: Build OSX framework**
- `make ios_app_framework` - `make osx_app_framework`
- This will output to `build/ios_app_framework/Release-iphoneos/ZeroTierSDK_iOS.framework` - This will output to `build/osx_app_framework/Release/ZeroTierSDK_OSX.framework`
**Step 2: Integrate SDK into project** **Step 2: Integrate SDK into project**
- Add the resultant framework package to your project - Add the resultant framework package to your project
- Add `zerotiersdk/src` directory to `Build Settings -> Header Search Paths` - Add `src` directory to *Build Settings -> Header Search Paths*
- Add `build/osx_app_framework/Release-iphoneos/` to *Build Settings -> Framework Search Paths* - Add `build/osx_app_framework/Release/` to *Build Settings -> Framework Search Paths*
- Add `ZeroTierSDK.frameworkiOS` to *General->Embedded Binaries* - Add `ZeroTierSDK.frameworkOSX` to *General->Embedded Binaries*
- Add `src/SDK_XcodeWrapper.cpp` and `src/SDK_XcodeWrapper.hpp` to your project: - Add `src/SDK_XcodeWrapper.cpp` and `src/SDK_XcodeWrapper.hpp` to your project:
- Set `src/SDK_Apple-Bridging-Header.h` as your bridging-header in `Build Settings -> Objective-C Bridging-header` - Set `src/SDK_Apple-Bridging-Header.h` as your bridging-header in *Build Settings -> Objective-C Bridging-header*
**Step 3: Start the ZeroTier service** **Step 3: Start the ZeroTier service**
Now find a place in your code to set up the ZeroTier service thread: Set up the ZeroTier service thread:
``` ```
var service_thread : NSThread! var service_thread : NSThread!
func zt_start_service() { func zt_start_service() {
let path = NSSearchPathForDirectoriesInDomains(NSSearchPathDirectory.DocumentDirectory, NSSearchPathDomainMask.UserDomainMask, true) let path = NSSearchPathForDirectoriesInDomains(NSSearchPathDirectory.DocumentDirectory, NSSearchPathDomainMask.UserDomainMask, true)
start_service(path[0]) start_service(".") // "." path will tell ZeroTier to write its config data to the same directory as the binary
} }
``` ```
@@ -70,16 +74,12 @@ dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0), {
}); });
``` ```
*NOTE: If you enabled the proxy service via `-DUSE_SOCKS_PROXY` it will start automatically and be reachable at `0.0.0.0:1337`*
**Step 4: Pick an API** **Step 4: Pick an API**
The following APIs are available for this integration: The following APIs are available for this integration:
- `Hook of BSD-like sockets`: Use BSD-like sockets as you normally would.
- `Proxy of NSStream`: Create NSStream. Configure stream for SOCKS5 Proxy. Use stream.
- `Direct Call`: Consult [src/SDK_Apple-Bridging-Header.h](../../../../src/SDK_Apple-Bridging-Header.h). - `Direct Call`: Consult [src/SDK_Apple-Bridging-Header.h](../../../../src/SDK_Apple-Bridging-Header.h).
- `Hook of BSD-like sockets`: Use BSD-like sockets as you normally would.
If functional interposition isn't available for the API or library you've chosen to use, ZeroTier offers a SOCKS5 proxy server which can allow connectivity to your virtual network as long as your client API supports the SOCKS5 protocol. This proxy service will run alongside the tap service and can be turned on by compiling with the `-DUSE_SOCKS_PROXY` flag in *Build Settings->Other C Flags*. By default, the proxy service is available at `0.0.0.0:1337`. - `Proxy of NSStream`: Create NSStream. Configure stream for SOCKS5 Proxy (127.0.0.1:PORT). Start Proxy. Use stream.
**Step 5: Join a network!** **Step 5: Join a network!**

View File

@@ -16,11 +16,11 @@ This short tutorial will show you how to enable ZeroTier functionality for your
**Step 2: Integrate SDK into project** **Step 2: Integrate SDK into project**
- Add the resultant framework package to your project - Add the resultant framework package to your project
- Add `zerotiersdk/src` directory to `Build Settings -> Header Search Paths` - Add `src` directory to *Build Settings -> Header Search Paths*
- Add `build/ios_app_framework/Release-iphoneos/` to *Build Settings -> Framework Search Paths* - Add `build/ios_app_framework/Release-iphoneos/` to *Build Settings -> Framework Search Paths*
- Add `ZeroTierSDK.frameworkiOS` to *General->Embedded Binaries* - Add `ZeroTierSDK.frameworkiOS` to *General->Embedded Binaries*
- Add `src/SDK_XcodeWrapper.cpp` and `src/SDK_XcodeWrapper.hpp` to your project: - Add `src/SDK_XcodeWrapper.cpp` and `src/SDK_XcodeWrapper.hpp` to your project:
- Set `src/SDK_Apple-Bridging-Header.h` as your bridging-header in `Build Settings -> Objective-C Bridging-header` - Set `src/SDK_Apple-Bridging-Header.h` as your bridging-header in *Build Settings -> Objective-C Bridging-header*
**Step 3: Start the ZeroTier service** **Step 3: Start the ZeroTier service**
@@ -43,16 +43,12 @@ dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0), {
}); });
``` ```
*NOTE: If you enabled the proxy service via `-DUSE_SOCKS_PROXY` it will start automatically and be reachable at `0.0.0.0:1337`*
**Step 4: Pick an API** **Step 4: Pick an API**
The following APIs are available for this integration: The following APIs are available for this integration:
- `Hook of BSD-like sockets`: Use BSD-like sockets as you normally would.
- `Proxy of NSStream`: Create NSStream. Configure stream for SOCKS5 Proxy. Use stream.
- `Direct Call`: Consult [src/SDK_Apple-Bridging-Header.h](../../../../src/SDK_Apple-Bridging-Header.h). - `Direct Call`: Consult [src/SDK_Apple-Bridging-Header.h](../../../../src/SDK_Apple-Bridging-Header.h).
- `Hook of BSD-like sockets`: Use BSD-like sockets as you normally would. This likely won't work for calls used by a third-party library.
If functional interposition isn't available for the API or library you've chosen to use, ZeroTier offers a SOCKS5 proxy server which can allow connectivity to your virtual network as long as your client API supports the SOCKS5 protocol. This proxy service will run alongside the tap service and can be turned on by compiling with the `-DUSE_SOCKS_PROXY` flag in *Build Settings->Other C Flags*. By default, the proxy service is available at `0.0.0.0:1337`. - `Proxy of NSStream`: Create NSStream. Configure stream for SOCKS5 Proxy (127.0.0.1:PORT). Start Proxy. Use stream.
**Step 5: Join a network!** **Step 5: Join a network!**

View File

@@ -68,21 +68,25 @@ android: android_jni_lib
# TODO: CHECK if XCODE TOOLS are installed # TODO: CHECK if XCODE TOOLS are installed
# Build frameworks for application development # Build frameworks for application development
osx_app_framework: osx_app_framework:
cd $(INT)/apple/ZeroTierSDK_Apple; xcodebuild -scheme ZeroTierSDK_OSX build SYMROOT="../../../$(BUILD)/osx_app_framework" cd $(INT)/apple/ZeroTierSDK_Apple; xcodebuild -configuration Release -scheme ZeroTierSDK_OSX build SYMROOT="../../../$(BUILD)/osx_app_framework"
cd $(INT)/apple/ZeroTierSDK_Apple; xcodebuild -configuration Debug -scheme ZeroTierSDK_OSX build SYMROOT="../../../$(BUILD)/osx_app_framework"
cp docs/osx_zt_sdk.md $(BUILD)/osx_app_framework/README.md cp docs/osx_zt_sdk.md $(BUILD)/osx_app_framework/README.md
ios_app_framework: ios_app_framework:
cd $(INT)/apple/ZeroTierSDK_Apple; xcodebuild -scheme ZeroTierSDK_iOS build SYMROOT="../../../$(BUILD)/ios_app_framework" cd $(INT)/apple/ZeroTierSDK_Apple; xcodebuild -configuration Release -scheme ZeroTierSDK_iOS build SYMROOT="../../../$(BUILD)/ios_app_framework"
cd $(INT)/apple/ZeroTierSDK_Apple; xcodebuild -configuration Debug -scheme ZeroTierSDK_iOS build SYMROOT="../../../$(BUILD)/ios_app_framework"
cp docs/ios_zt_sdk.md $(BUILD)/ios_app_framework/README.md cp docs/ios_zt_sdk.md $(BUILD)/ios_app_framework/README.md
# Build bundles for Unity integrations # Build bundles for Unity integrations
osx_unity3d_bundle: osx_unity3d_bundle:
cd $(INT)/apple/ZeroTierSDK_Apple; xcodebuild -scheme ZeroTierSDK_Unity3D_OSX build SYMROOT="../../../$(BUILD)/osx_unity3d_bundle" cd $(INT)/apple/ZeroTierSDK_Apple; xcodebuild -configuration Release -scheme ZeroTierSDK_Unity3D_OSX build SYMROOT="../../../$(BUILD)/osx_unity3d_bundle"
cd $(INT)/apple/ZeroTierSDK_Apple; xcodebuild -configuration Debug -scheme ZeroTierSDK_Unity3D_OSX build SYMROOT="../../../$(BUILD)/osx_unity3d_bundle"
cp docs/osx_unity3d_zt_sdk.md $(BUILD)/osx_unity3d_bundle/README.md cp docs/osx_unity3d_zt_sdk.md $(BUILD)/osx_unity3d_bundle/README.md
chmod 755 $(BUILD)/osx_unity3d_bundle/Debug/ZeroTierSDK_Unity3D_OSX.bundle chmod 755 $(BUILD)/osx_unity3d_bundle/Debug/ZeroTierSDK_Unity3D_OSX.bundle
cp -p -R $(BUILD)/osx_unity3d_bundle/Debug/ZeroTierSDK_Unity3D_OSX.bundle $(INT)/Unity3D/Assets/Plugins cp -p -R $(BUILD)/osx_unity3d_bundle/Debug/ZeroTierSDK_Unity3D_OSX.bundle $(INT)/Unity3D/Assets/Plugins
ios_unity3d_bundle: ios_unity3d_bundle:
cd $(INT)/apple/ZeroTierSDK_Apple; xcodebuild -scheme ZeroTierSDK_Unity3D_iOS build SYMROOT="../../../$(BUILD)/ios_unity3d_bundle" cd $(INT)/apple/ZeroTierSDK_Apple; xcodebuild -configuration Release -scheme ZeroTierSDK_Unity3D_iOS build SYMROOT="../../../$(BUILD)/ios_unity3d_bundle"
cd $(INT)/apple/ZeroTierSDK_Apple; xcodebuild -configuration Debug -scheme ZeroTierSDK_Unity3D_iOS build SYMROOT="../../../$(BUILD)/ios_unity3d_bundle"
cp docs/ios_unity3d_zt_sdk.md $(BUILD)/ios_unity3d_bundle/README.md cp docs/ios_unity3d_zt_sdk.md $(BUILD)/ios_unity3d_bundle/README.md
# TODO: CHECK if ANDROID/GRADLE TOOLS are installed # TODO: CHECK if ANDROID/GRADLE TOOLS are installed
@@ -150,6 +154,9 @@ tests: $(TEST_OBJDIR) $(TEST_TARGETS)
JAVAC := $(shell which javac) JAVAC := $(shell which javac)
clean_unity:
clean_android: clean_android:
# android JNI lib project # android JNI lib project
test -s /usr/bin/javac || { echo "Javac not found"; exit 1; } test -s /usr/bin/javac || { echo "Javac not found"; exit 1; }
@@ -170,6 +177,12 @@ clean: clean_basic clean_android
clean_for_production: clean_for_production:
-find . -type f \( -name '*.identity'\) -delete -find . -type f \( -name '*.identity'\) -delete
## --- BELOW ARE DEVELOPMENT AIDS ---
# Copy and rename source files into example projects to follow local ordinances
update_examples:
cp src/SDK_DotNetWrapper.cs integrations/Unity3D/Assets/ZTSDK.cs
cp src/SDK_JavaWrapper.java integrations/android/example_app/app/src/main/java/ZeroTier/ZTSDK.java
# For authors # For authors
# Copies documentation to all of the relevant directories to make viewing in the repo a little easier # Copies documentation to all of the relevant directories to make viewing in the repo a little easier

417
src/SDK_DotNetWrapper.cs Executable file
View File

@@ -0,0 +1,417 @@
/*
* 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 <http://www.gnu.org/licenses/>.
*
* --
*
* 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/
*/
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.Networking;
using System;
using System.Collections;
using System.Runtime.InteropServices;
using System.Threading;
using System.Net.Sockets;
using System.Net;
using System.IO;
using System.Collections.Generic;
using System.Globalization;
// TODO:
/*
* check for mem leaks surrounding managed/unmanaged barrier
* find root of 2X buffer size requirement issue
* check that cross-thread oprations are handled correctly
* check that .IsRunning() doesn't bork the entire system anymore
* Allow max packet size configuration
* Handle exceptions from unmanaged code
* */
// Provides a bare-bones interface to ZeroTier-administered sockets
public class ZTSDK {
// ZeroTier background thread
protected Thread ztThread;
protected List<int> connections = new List<int> ();
protected int MaxPacketSize;
// Only allow one network at a time for BETA
protected bool joined_to_network = false;
protected string nwid = "";
protected string path = "";
// Platform-specific paths and bundle/libary names
#if UNITY_STANDALONE_OSX || UNITY_EDITOR_OSX
const string DLL_PATH = "ZeroTierSDK_Unity3D_OSX";
protected string rpc_path = "/Library/Application\\ Support/ZeroTier/SDK/";
#endif
#if UNITY_IOS || UNITY_IPHONE
const string DLL_PATH = "ZeroTierSDK_Unity3D_iOS";
protected string rpc_path = "ZeroTier/One/";
#endif
#if UNITY_STANDALONE_WIN || UNITY_EDITOR_WIN
const string DLL_PATH = "ZeroTierSDK_Unity3D_WIN";
protected string rpc_path = "";
#endif
#if UNITY_STANDALONE_LINUX
const string DLL_PATH = "ZeroTierSDK_Unity3D_LINUX";
protected string rpc_path = "";
#endif
#if UNITY_ANDROID
const string DLL_PATH = "ZeroTierSDK_Unity3D_ANDROID";
protected string rpc_path = "ZeroTier/One/";
#endif
#region DLL Imports
// ZeroTier service / debug initialization
[DllImport (DLL_PATH)]
public static extern void SetDebugFunction( IntPtr fp );
[DllImport (DLL_PATH)]
private static extern int unity_start_service(string path);
[DllImport (DLL_PATH)]
private static extern int unity_start_service_and_rpc(string path, string nwid);
[DllImport (DLL_PATH)]
protected static extern bool zts_is_running();
[DllImport (DLL_PATH)]
protected static extern void zts_stop_service();
// Connection calls
[DllImport (DLL_PATH)]
protected static extern int zts_socket(int family, int type, int protocol);
[DllImport (DLL_PATH)]
unsafe protected static extern int zts_bind(int sockfd, System.IntPtr addr, int addrlen);
[DllImport (DLL_PATH)]
unsafe protected static extern int zts_connect(int sockfd, System.IntPtr addr, int addrlen);
[DllImport (DLL_PATH)]
protected static extern int zts_accept(int sockfd);
[DllImport (DLL_PATH)]
protected static extern int zts_listen(int sockfd, int backlog);
[DllImport (DLL_PATH)]
protected static extern int zts_close(int sockfd);
// RX / TX
[DllImport (DLL_PATH)]
unsafe protected static extern int zts_recv(int sockfd, [In, Out] IntPtr buf, int len);
[DllImport (DLL_PATH)]
unsafe protected static extern int zts_send(int sockfd, IntPtr buf, int len);
[DllImport (DLL_PATH)]
unsafe protected static extern int zts_set_nonblock(int sockfd);
[DllImport (DLL_PATH)]
unsafe protected static extern int zts_sendto(int fd, IntPtr buf, int len, int flags, System.IntPtr addr, int addrlen);
[DllImport (DLL_PATH)]
unsafe protected static extern int zts_recvfrom(int fd, [In, Out] IntPtr buf, int len, int flags, System.IntPtr addr, int addrlen);
// ZT Network controls
[DllImport (DLL_PATH)]
protected static extern void zts_join_network(string nwid);
[DllImport (DLL_PATH)]
protected static extern void zts_leave_network(string nwid);
#endregion
// Interop structures
[System.Runtime.InteropServices.StructLayoutAttribute(System.Runtime.InteropServices.LayoutKind.Sequential, CharSet=System.Runtime.InteropServices.CharSet.Ansi)]
public struct sockaddr {
/// u_short->unsigned short
public ushort sa_family;
/// char[14]
[System.Runtime.InteropServices.MarshalAsAttribute(System.Runtime.InteropServices.UnmanagedType.ByValTStr, SizeConst=14)]
public string sa_data;
}
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
public delegate void MyDelegate(string str);
// Debug output callback
static void CallBackFunction(string str) {
Debug.Log("ZeroTier: " + str);
}
// Returns a path for RPC communications to the service
private string rpcCommPath()
{
if(path != "" && nwid != "") {
return path + "nc_" + nwid;
}
return "";
}
// Thread which starts the ZeroTier service
protected void zt_service_thread()
{
// Set up debug callback
MyDelegate callback_delegate = new MyDelegate( CallBackFunction );
IntPtr intptr_delegate = Marshal.GetFunctionPointerForDelegate(callback_delegate);
SetDebugFunction( intptr_delegate );
// Start service
/* This new instance will communicate via a named pipe, so any
* API calls (ZeroTier.Connect(), ZeroTier.Send(), etc) will be sent to the service
* via this pipe.
*/
if(nwid.Length > 0) {
unity_start_service_and_rpc (path, nwid);
}
else {
unity_start_service(rpcCommPath());
}
}
// Returns the nwid of the network you're currently connected to
public string GetNetworkID() {
return nwid;
}
// Returns whether you're currently connected to a network
public bool IsConnected() {
return nwid != "";
}
// Start the ZeroTier service
protected void Init()
{
ztThread = new Thread(() => {
try {
zt_service_thread();
} catch(Exception e) {
Debug.Log(e.Message.ToString());
}
});
ztThread.IsBackground = true; // Allow the thread to be aborted safely
ztThread.Start();
}
// Initialize the ZeroTier service with a given path
public ZTSDK(string path, string nwid) {
Debug.Log("ZTSDK(): " + nwid);
this.path = path;
this.nwid = nwid;
Init();
}
public ZTSDK (string path) {
this.path = path;
Init();
}
// Initialize the ZeroTier service
public ZTSDK() {
Init();
}
#region Network Handling
// Joins a ZeroTier virtual network
public bool JoinNetwork(string nwid)
{
if(!joined_to_network) {
zts_join_network(nwid);
return true;
}
return false;
}
// Leaves a ZeroTier virtual network
public bool LeaveNetwork(string nwid)
{
if(!joined_to_network) {
return false;
}
else {
zts_leave_network(nwid);
return true;
}
}
#endregion
// Creates a new ZeroTier-administered socket
public int Socket(int family, int type, int protocol)
{
return zts_socket (family, type, protocol);
}
// Binds to a specific address
public int Bind(int fd, string addr, int port)
{
GCHandle sockaddr_ptr = Generate_unmananged_sockaddr(addr + ":" + port);
IntPtr pSockAddr = sockaddr_ptr.AddrOfPinnedObject ();
int addrlen = Marshal.SizeOf (pSockAddr);
return zts_bind (fd, pSockAddr, addrlen);
}
// Listens for an incoming connection request
public int Listen(int fd, int backlog)
{
return zts_listen(fd, backlog);
}
// Accepts an incoming connection
public int Accept(int fd)
{
return zts_accept (fd);
}
// Closes a connection
public int Close(int fd)
{
return Close (fd);
}
// Connects to a remote host
public int Connect(int fd, string addr, int port)
{
GCHandle sockaddr_ptr = Generate_unmananged_sockaddr(addr + ":" + port);
IntPtr pSockAddr = sockaddr_ptr.AddrOfPinnedObject ();
int addrlen = Marshal.SizeOf (pSockAddr);
return zts_connect (fd, pSockAddr, addrlen);
}
public int Read(int fd, ref char[] buf, int len)
{
GCHandle handle = GCHandle.Alloc(buf, GCHandleType.Pinned);
IntPtr ptr = handle.AddrOfPinnedObject();
int bytes_read = zts_recv (fd, ptr, len*2);
string str = Marshal.PtrToStringAuto(ptr);
//Marshal.Copy (ptr, buf, 0, bytes_read);
buf = Marshal.PtrToStringAnsi(ptr).ToCharArray();
return bytes_read;
}
public int Write(int fd, char[] buf, int len)
{
GCHandle handle = GCHandle.Alloc(buf, GCHandleType.Pinned);
IntPtr ptr = handle.AddrOfPinnedObject();
//error = 0;
int bytes_written;
// FIXME: Sending a length of 2X the buffer size seems to fix the object pinning issue
if((bytes_written = zts_send(fd, ptr, len*2)) < 0) {
//error = (byte)bytes_written;
}
return bytes_written;
}
// Sends data to an address
public int SendTo(int fd, char[] buf, int len, int flags, string addr, int port)
{
GCHandle handle = GCHandle.Alloc(buf, GCHandleType.Pinned);
IntPtr ptr = handle.AddrOfPinnedObject();
int bytes_written;
// Form address structure
GCHandle sockaddr_ptr = Generate_unmananged_sockaddr(addr + ":" + port);
IntPtr pSockAddr = sockaddr_ptr.AddrOfPinnedObject ();
int addrlen = Marshal.SizeOf (pSockAddr);
if((bytes_written = zts_sendto(fd, ptr, len*2, flags, pSockAddr, addrlen)) < 0) {
//error = (byte)bytes_written;
}
return bytes_written;
}
// Receives data from an address
public int RecvFrom(int fd, ref char[] buf, int len, int flags, string addr, int port)
{
GCHandle handle = GCHandle.Alloc(buf, GCHandleType.Pinned);
IntPtr ptr = handle.AddrOfPinnedObject();
// Form address structure
GCHandle sockaddr_ptr = Generate_unmananged_sockaddr(addr + ":" + port);
IntPtr pSockAddr = sockaddr_ptr.AddrOfPinnedObject ();
int addrlen = Marshal.SizeOf (pSockAddr);
int bytes_read = zts_recvfrom(fd, ptr, len*2, flags, pSockAddr, addrlen);
string str = Marshal.PtrToStringAuto(ptr);
//Marshal.Copy (ptr, buf, 0, bytes_read);
buf = Marshal.PtrToStringAnsi(ptr).ToCharArray();
return bytes_read;
}
#region Service-Related calls
// Returns whether the ZeroTier service is currently running
public bool IsRunning()
{
return zts_is_running ();
}
// Terminates the ZeroTier service
public void Terminate()
{
zts_stop_service ();
}
#endregion
// --- Utilities ---
// Handles IPv4 and IPv6 notation.
public static IPEndPoint CreateIPEndPoint(string endPoint)
{
string[] ep = endPoint.Split(':');
if (ep.Length < 2) throw new FormatException("Invalid endpoint format");
IPAddress ip;
if (ep.Length > 2) {
if (!IPAddress.TryParse(string.Join(":", ep, 0, ep.Length - 1), out ip)) {
throw new FormatException("Invalid ip-adress");
}
}
else {
if (!IPAddress.TryParse(ep[0], out ip)) {
throw new FormatException("Invalid ip-adress");
}
}
int port;
if (!int.TryParse(ep[ep.Length - 1], NumberStyles.None, NumberFormatInfo.CurrentInfo, out port)) {
throw new FormatException("Invalid port");
}
return new IPEndPoint(ip, port);
}
// Generates an unmanaged sockaddr structure from a string-formatted endpoint
public static GCHandle Generate_unmananged_sockaddr(string endpoint_str)
{
IPEndPoint ipEndPoint;
ipEndPoint = CreateIPEndPoint (endpoint_str);
SocketAddress socketAddress = ipEndPoint.Serialize ();
// use an array of bytes instead of the sockaddr structure
byte[] sockAddrStructureBytes = new byte[socketAddress.Size];
GCHandle sockAddrHandle = GCHandle.Alloc (sockAddrStructureBytes, GCHandleType.Pinned);
for (int i = 0; i < socketAddress.Size; ++i) {
sockAddrStructureBytes [i] = socketAddress [i];
}
return sockAddrHandle;
}
public static GCHandle Generate_unmanaged_buffer(byte[] buf)
{
// use an array of bytes instead of the sockaddr structure
GCHandle sockAddrHandle = GCHandle.Alloc (buf, GCHandleType.Pinned);
return sockAddrHandle;
}
}

View File

@@ -74,33 +74,9 @@ void *zts_start_service(void *thread_id);
void zts_init_rpc(const char * path, const char * nwid); void zts_init_rpc(const char * path, const char * nwid);
void dwr(int level, const char *fmt, ... ); void dwr(int level, const char *fmt, ... );
#if defined(__UNITY_3D__)
// .NET Interop-friendly debug mechanism
typedef void (*FuncPtr)( const char * );
FuncPtr Debug;
void SetDebugFunction( FuncPtr fp ) { Debug = fp; }
// Starts a ZeroTier service at the given path
void unity_start_service(char * path, int len) {
std::string dstr = std::string(path);
dstr = "unity_start_service(): path = " + dstr;
Debug(dstr.c_str());
init_service(INTERCEPT_DISABLED, path);
}
// Starts a ZeroTier service and RPC
void unity_start_service_and_rpc(char * path, char *nwid, int len) {
std::string dstr = std::string(path);
dstr = "unity_start_service_and_rpc(): path = " + dstr;
Debug(dstr.c_str());
init_service_and_rpc(INTERCEPT_DISABLED, path, nwid);
}
#endif
int zts_start_proxy_server(const char *homepath, const char * nwid, struct sockaddr_storage * addr) { int zts_start_proxy_server(const char *homepath, const char * nwid, struct sockaddr_storage * addr) {
LOGV("zts_start_proxy_server\n"); LOGV("zts_start_proxy_server\n");
dwr(MSG_DEBUG, "zts_start_proxy_server()\n");
dwr(MSG_DEBUG, "zts_start_proxy_server()");
uint64_t nwid_int = strtoull(nwid, NULL, 16); uint64_t nwid_int = strtoull(nwid, NULL, 16);
ZeroTier::NetconEthernetTap * tap = zt1Service->getTaps()[nwid_int]; ZeroTier::NetconEthernetTap * tap = zt1Service->getTaps()[nwid_int];
if(tap) { if(tap) {
@@ -199,6 +175,30 @@ char *zts_get_homepath() {
return (char*)givenHomeDir.c_str(); return (char*)givenHomeDir.c_str();
} }
#if defined(__UNITY_3D__)
// .NET Interop-friendly debug mechanism
typedef void (*FuncPtr)( const char * );
FuncPtr Debug;
void SetDebugFunction( FuncPtr fp ) { Debug = fp; }
// Starts a ZeroTier service at the given path
void unity_start_service(char * path, int len) {
std::string dstr = std::string(path);
dstr = "unity_start_service(): path = " + dstr;
Debug(dstr.c_str());
init_service(INTERCEPT_DISABLED, path);
}
// Starts a ZeroTier service and RPC
void unity_start_service_and_rpc(char * path, char *nwid, int len) {
std::string dstr = std::string(path);
dstr = "unity_start_service_and_rpc(): path = " + dstr;
Debug(dstr.c_str());
init_service_and_rpc(INTERCEPT_DISABLED, path, nwid);
}
#endif
// Android JNI wrapper // Android JNI wrapper
// JNI naming convention: Java_PACKAGENAME_CLASSNAME_METHODNAME // JNI naming convention: Java_PACKAGENAME_CLASSNAME_METHODNAME
#if defined(__ANDROID__) #if defined(__ANDROID__)