Skip to content

Commit

Permalink
Merge branch 'master' into staging-client
Browse files Browse the repository at this point in the history
  • Loading branch information
rod-hynes committed Aug 3, 2018
2 parents 8e56c66 + db01705 commit 4866cfd
Show file tree
Hide file tree
Showing 105 changed files with 5,124 additions and 157,934 deletions.
31 changes: 31 additions & 0 deletions ClientLibrary/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
# Dockerfile to build the Psiphon Client Library for multiple platforms.
#
# See README.md for usage instructions.

FROM ubuntu:16.04

# Install system-level dependencies.
ENV DEBIAN_FRONTEND=noninteractive
RUN apt-get update -y && apt-get install -y --no-install-recommends \
build-essential \
ca-certificates \
curl \
gcc-mingw-w64-i686 \
gcc-mingw-w64-x86-64 \
gcc-multilib \
git \
python \
unzip \
&& apt-get clean \
&& rm -rf /var/lib/apt/lists/*

# Install Go.
# NOTE: Go 1.10+ is required to build c-shared for windows (https://github.com/golang/go/commit/bb0bfd002ada7e3eb9198d4287b32c2fed6e8da6)
ENV GOVERSION=go1.10.3 GOROOT=/usr/local/go GOPATH=/go PATH=$PATH:/usr/local/go/bin:/go/bin CGO_ENABLED=1

RUN curl -L https://storage.googleapis.com/golang/$GOVERSION.linux-amd64.tar.gz -o /tmp/go.tar.gz \
&& tar -C /usr/local -xzf /tmp/go.tar.gz \
&& rm /tmp/go.tar.gz \
&& echo $GOVERSION > $GOROOT/VERSION

WORKDIR $GOPATH/src/github.com/Psiphon-Labs/psiphon-tunnel-core/ClientLibrary
76 changes: 68 additions & 8 deletions ClientLibrary/PsiphonTunnel.go
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package main

// #include <stdlib.h>
import "C"

import (
Expand All @@ -9,6 +10,7 @@ import (
"fmt"
"sync"
"time"
"unsafe"

"github.com/Psiphon-Labs/psiphon-tunnel-core/psiphon"
"github.com/Psiphon-Labs/psiphon-tunnel-core/psiphon/common"
Expand Down Expand Up @@ -46,7 +48,17 @@ type psiphonTunnel struct {

var tunnel psiphonTunnel

// Memory managed by PsiphonTunnel which is allocated in Start and freed in Stop
var managedStartResult *C.char

//export Start
//
// ******************************* WARNING ********************************
// The underlying memory referenced by the return value of Start is managed
// by PsiphonTunnel and attempting to free it explicitly will cause the
// program to crash. This memory is freed once Stop is called.
// ************************************************************************
//
// Start starts the controller and returns once either of the following has occured: an active tunnel has been
// established, the timeout has elapsed before an active tunnel could be established or an error has occured.
//
Expand All @@ -72,9 +84,33 @@ var tunnel psiphonTunnel
// "error": <error message>
// }
//
// networkID should be not be blank and should follow the format specified by
// clientPlatform should be of the form OS_OSVersion_BundleIdentifier where both the OSVersion and BundleIdentifier
// fields are optional. If clientPlatform is set to an empty string the "ClientPlatform" field in the provided json
// config will be used instead.
//
// Provided below are links to platform specific code which can be used to find some of the above fields:
// Android:
// - OSVersion: https://github.com/Psiphon-Labs/psiphon-tunnel-core/blob/3d344194d21b250e0f18ededa4b4459a373b0690/MobileLibrary/Android/PsiphonTunnel/PsiphonTunnel.java#L573
// - BundleIdentifier: https://github.com/Psiphon-Labs/psiphon-tunnel-core/blob/3d344194d21b250e0f18ededa4b4459a373b0690/MobileLibrary/Android/PsiphonTunnel/PsiphonTunnel.java#L575
// iOS:
// - OSVersion: https://github.com/Psiphon-Labs/psiphon-tunnel-core/blob/3d344194d21b250e0f18ededa4b4459a373b0690/MobileLibrary/iOS/PsiphonTunnel/PsiphonTunnel/PsiphonTunnel.m#L612
// - BundleIdentifier: https://github.com/Psiphon-Labs/psiphon-tunnel-core/blob/3d344194d21b250e0f18ededa4b4459a373b0690/MobileLibrary/iOS/PsiphonTunnel/PsiphonTunnel/PsiphonTunnel.m#L622
//
// Some examples of valid client platform strings are:
//
// "Android_4.2.2_com.example.exampleApp"
// "iOS_11.4_com.example.exampleApp"
// "Windows"
//
// networkID must be a non-empty string and follow the format specified by
// https://godoc.org/github.com/Psiphon-Labs/psiphon-tunnel-core/psiphon#NetworkIDGetter.
func Start(configJSON, embeddedServerEntryList, networkID string, timeout int64) *C.char {
//
// Provided below are links to platform specific code which can be used to generate valid network identifier strings:
// Android:
// - https://github.com/Psiphon-Labs/psiphon-tunnel-core/blob/3d344194d21b250e0f18ededa4b4459a373b0690/MobileLibrary/Android/PsiphonTunnel/PsiphonTunnel.java#L371
// iOS:
// - https://github.com/Psiphon-Labs/psiphon-tunnel-core/blob/3d344194d21b250e0f18ededa4b4459a373b0690/MobileLibrary/iOS/PsiphonTunnel/PsiphonTunnel/PsiphonTunnel.m#L1105
func Start(configJSON, embeddedServerEntryList, clientPlatform, networkID string, timeout int64) *C.char {

// Load provided config

Expand All @@ -89,8 +125,13 @@ func Start(configJSON, embeddedServerEntryList, networkID string, timeout int64)
config.NetworkID = networkID
}

// All config fields should be set before calling commit
// Set client platform

if clientPlatform != "" {
config.ClientPlatform = clientPlatform
}

// All config fields should be set before calling commit
err = config.Commit()
if err != nil {
return startErrorJson(err)
Expand Down Expand Up @@ -137,7 +178,7 @@ func Start(configJSON, embeddedServerEntryList, networkID string, timeout int64)

// Initialize data store

err = psiphon.InitDataStore(config)
err = psiphon.OpenDataStore(config)
if err != nil {
return startErrorJson(err)
}
Expand Down Expand Up @@ -213,9 +254,13 @@ func Start(configJSON, embeddedServerEntryList, networkID string, timeout int64)
tunnel.stopController()
}

// Free previous result
freeManagedStartResult()

// Return result
managedStartResult = marshalStartResult(result)

return marshalstartResult(result)
return managedStartResult
}

//export Stop
Expand All @@ -224,10 +269,15 @@ func Start(configJSON, embeddedServerEntryList, networkID string, timeout int64)
// Stop should always be called after a successful call to Start to ensure the
// controller is not left running.
func Stop() {
freeManagedStartResult()

if tunnel.stopController != nil {
tunnel.stopController()
}

tunnel.controllerWaitGroup.Wait()

psiphon.CloseDataStore()
}

// secondsBeforeNow returns the delta seconds of the current time subtract startTime.
Expand All @@ -236,9 +286,9 @@ func secondsBeforeNow(startTime time.Time) float64 {
return delta.Seconds()
}

// marshalstartResult serializes a startResult object as a JSON string in the form
// marshalStartResult serializes a startResult object as a JSON string in the form
// of a null-terminated buffer of C chars.
func marshalstartResult(result startResult) *C.char {
func marshalStartResult(result startResult) *C.char {
resultJSON, err := json.Marshal(result)
if err != nil {
return C.CString(fmt.Sprintf("{\"result_code\":%d, \"error\": \"%s\"}", startResultCodeOtherError, err.Error()))
Expand All @@ -261,7 +311,17 @@ func startErrorJson(err error) *C.char {
result.Code = startResultCodeOtherError
result.ErrorString = err.Error()

return marshalstartResult(result)
return marshalStartResult(result)
}

// freeManagedStartResult frees the memory on the heap pointed to by managedStartResult.
func freeManagedStartResult() {
if managedStartResult != nil {
managedMemory := unsafe.Pointer(managedStartResult)
if managedMemory != nil {
C.free(managedMemory)
}
}
}

// main is a stub required by cgo.
Expand Down
80 changes: 80 additions & 0 deletions ClientLibrary/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,3 +7,83 @@ If you are planning to embed Psiphon in a mobile application, please use the [Mo
## Usage

If you are using the Library in your app, please read the [USAGE.md](USAGE.md) instructions.

## Building for Darwin (iOS, MacOS)

Note that you will need to have Xcode installed on a machine running MacOS.

##### Run the build:

*Ensure that the command below is run from within the `ClientLibrary` directory*

```
./build-darwin.sh all
```

This command can also be modified by:
- replacing `all` with `ios` or `macos` as the first parameter to `build-darwin.sh` (as in `./build-darwin.sh ios`) to only build binaries for the operating system of choice

When that command completes, the compiled binaries will be located in the `build` directory. The structure will be:

```
build
└── darwin
└── ios
│ └── PsiphonTunnel-ios-arm.h
│ └── PsiphonTunnel-ios-arm.dylib
│ └── PsiphonTunnel-ios-arm64.h
│ └── PsiphonTunnel-ios-arm64.dylib
└── macos
└── PsiphonTunnel-macos-386.dylib
└── PsiphonTunnel-macos-386.dylib
└── PsiphonTunnel-macos-amd64.dylib
└── PsiphonTunnel-macos-amd64.dylib
```

## Building with Docker (Android, Linux, Windows)

Note that you may need to use `sudo docker` below, depending on your OS.

##### Create the build image:

1. While in the `ClientLibrary` directory, run the command: `docker build --no-cache=true -t psiclientlibrary-builder .`

2. Once completed, verify that you see an image named `psiclientlibrary-builder` when running: `docker images`

##### Run the build:

*Ensure that the command below is run from within the `ClientLibrary` directory*

```bash
cd .. && \
docker run \
--rm \
-v $PWD:/go/src/github.com/Psiphon-Labs/psiphon-tunnel-core \
psiclientlibrary-builder \
/bin/bash -c './make.bash all' \
; cd -
```

This command can also be modified by:
- replacing `all` with `android`, `linux`, or `windows` as the first parameter to `make.bash` (as in `./make.bash windows`) to only build binaries for the operating system of choice

When that command completes, the compiled binaries will be located in the `build` directory (`./build`, and everything under it will likely be owned by root, so be sure to `chown` to an appropriate user) under the current directory. The structure will be:

```
build
├── android
│ └── PsiphonTunnel-android-arm7.h
│ └── PsiphonTunnel-android-arm7.so
│ └── PsiphonTunnel-android-arm64.h
│ └── PsiphonTunnel-android-arm64.so
├── linux
│ └── PsiphonTunnel-linux-386.h
│ └── PsiphonTunnel-linux-386.so
│ └── PsiphonTunnel-linux-amd64.h
│ └── PsiphonTunnel-linux-amd64.so
└── windows
└── PsiphonTunnel-windows-386.h
└── PsiphonTunnel-windows-386.dll
└── PsiphonTunnel-windows-amd64.h
└── PsiphonTunnel-windows-amd64.dll
```
Loading

0 comments on commit 4866cfd

Please sign in to comment.