diff --git a/test-server/android/README b/test-server/android/README new file mode 100644 index 00000000..09599b7b --- /dev/null +++ b/test-server/android/README @@ -0,0 +1,51 @@ +/* + * libwebsockets Android client - libwebsockets test application for Android + * + * Copyright (C) 2016 Alexander Bruines + * + * This file is made available under the Creative Commons CC0 1.0 + * Universal Public Domain Dedication. + * + * The person who associated a work with this deed has dedicated + * the work to the public domain by waiving all of his or her rights + * to the work worldwide under copyright law, including all related + * and neighboring rights, to the extent allowed by law. You can copy, + * modify, distribute and perform the work, even for commercial purposes, + * all without asking permission. + * + * The test apps are intended to be adapted for use in your code, which + * may be proprietary. So unlike the library itself, they are licensed + * Public Domain. + */ + +This directory contains an Android Studio (2.1.1) project that builds +libwebsockets (+ openssl + zlib) and an Android application that is able +to connect to the 'dumb-increment-protocol' of the libwebsockets test server. + +Building the native libraries requires the Android NDK which can be +installed using the SDK manager. + +The app/src/main/jni/NativeLibs.mk is fully integraded with Gradle but will +only work on Linux and requires the following applications to be available +in addition to the NDK: + + awk cmake egrep git tar wget makedepend + +(makedepend can be installed from (Debian) xutils-dev) + +To build the project: + +- Open an 'existing project' with Android Studio and select this directory. + (answer yes/ok to the question to integrate with Gradle). + +- Open the file app/src/main/jni/Application.mk and make sure NDK_ROOT + is set correctly and that APP_PLATFORM is set to the appropriate API level. + +- Build the project with CTRL+F9 + (open the gradle console to follow the build progress). + +- Install APK to device and run. + +- Connect to libwebsockets test server. + + diff --git a/test-server/android/app/app.iml b/test-server/android/app/app.iml new file mode 100644 index 00000000..67ff95aa --- /dev/null +++ b/test-server/android/app/app.iml @@ -0,0 +1,115 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/test-server/android/app/build.gradle b/test-server/android/app/build.gradle new file mode 100644 index 00000000..48069c89 --- /dev/null +++ b/test-server/android/app/build.gradle @@ -0,0 +1,42 @@ +apply plugin: 'com.android.application' + +android { + compileSdkVersion 23 + buildToolsVersion "23.0.3" + + defaultConfig { + applicationId "org.libwebsockets.client" + minSdkVersion 17 + targetSdkVersion 23 + versionCode 1 + versionName "1.0" + } + buildTypes { + release { + minifyEnabled false + proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' + } + } + sourceSets { + main { + jni.srcDirs = [] + } + } +} + +dependencies { + compile fileTree(dir: 'libs', include: ['*.jar']) + testCompile 'junit:junit:4.12' + compile 'com.android.support:appcompat-v7:23.3.0' +} + +task buildNativeLibs(type: Exec, description: "compile the native libraries") { + commandLine 'make', '-f', 'NativeLibs.mk', '-C', 'src/main/jni', 'all' +} + +task cleanNativeLibs(type: Exec, description: "clean the native libraries source tree") { + commandLine 'make', '-f', 'NativeLibs.mk', '-C', 'src/main/jni', 'clean-ndk' +} + +tasks.withType(JavaCompile) { compileTask -> compileTask.dependsOn buildNativeLibs } +clean.dependsOn 'cleanNativeLibs' diff --git a/test-server/android/app/src/main/AndroidManifest.xml b/test-server/android/app/src/main/AndroidManifest.xml new file mode 100644 index 00000000..8e3b744d --- /dev/null +++ b/test-server/android/app/src/main/AndroidManifest.xml @@ -0,0 +1,29 @@ + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/test-server/android/app/src/main/java/org/libwebsockets/client/LwsService.java b/test-server/android/app/src/main/java/org/libwebsockets/client/LwsService.java new file mode 100644 index 00000000..19f234bb --- /dev/null +++ b/test-server/android/app/src/main/java/org/libwebsockets/client/LwsService.java @@ -0,0 +1,132 @@ +/* + * LwsService.java - libwebsockets test service for Android + * + * Copyright (C) 2016 Alexander Bruines + * + * This file is made available under the Creative Commons CC0 1.0 + * Universal Public Domain Dedication. + * + * The person who associated a work with this deed has dedicated + * the work to the public domain by waiving all of his or her rights + * to the work worldwide under copyright law, including all related + * and neighboring rights, to the extent allowed by law. You can copy, + * modify, distribute and perform the work, even for commercial purposes, + * all without asking permission. + * + * The test apps are intended to be adapted for use in your code, which + * may be proprietary. So unlike the library itself, they are licensed + * Public Domain. + */ + +package org.libwebsockets.client; + +import android.os.Message; +import android.os.RemoteException; +import android.util.Log; + +public class LwsService extends ThreadService { + + /** + * Commands that can be send to this service + */ + public final static int MSG_SET_CONNECTION_PARAMETERS = 1; + + /** + * Messages that may be send to output Messenger + * Clients should handle these messages. + **/ + public final static int MSG_DUMB_INCREMENT_PROTOCOL_COUNTER = 1; + public final static int MSG_LWS_CALLBACK_CLIENT_CONNECTION_ERROR = 2; + public final static int MSG_LWS_CALLBACK_CLIENT_ESTABLISHED = 3; + + public static class ConnectionParameters { + String serverAddress; + int serverPort; + + ConnectionParameters( + String serverAddress, + int serverPort + ){ + this.serverAddress = serverAddress; + this.serverPort = serverPort; + } + } + + /** + * Handle incoming messages from clients of this service + */ + @Override + public void handleInputMessage(Message msg) { + Message m; + switch(msg.what) { + case MSG_SET_CONNECTION_PARAMETERS: { + LwsService.ConnectionParameters parameters = (ConnectionParameters) msg.obj; + setConnectionParameters( + parameters.serverAddress, + parameters.serverPort + ); + break; + } + default: + super.handleInputMessage(msg); + break; + } + } + + /** + * The run() function for the thread. + * For this test we implement a very long lived task + * that sends many messages back to the client. + * **/ + public void workerThreadRun() { + + initLws(); + connectLws(); + + while(true) { + + // service the websockets + serviceLws(); + + // Check if we must quit or suspend + synchronized (mThreadLock){ + while(mMustSuspend) { + // We are asked to suspend the thread + try { + mThreadLock.wait(); + + } catch (InterruptedException e) {} + } + if(mMustQuit) { + // The signal to quit was given + break; + } + } + + // Throttle the loop so that it iterates once every 50ms + try { + Thread.sleep(50); + } + catch (InterruptedException e) { + e.printStackTrace(); + } + + } + exitLws(); + } + + /** Load the native libwebsockets code */ + static { + try { + System.loadLibrary("lwsservice"); + } + catch(UnsatisfiedLinkError ule) { + Log.e("LwsService", "Warning: Could not load native library: " + ule.getMessage()); + } + } + public native boolean initLws(); + public native void exitLws(); + public native void serviceLws(); + public native void setConnectionParameters(String serverAddress, int serverPort); + public native boolean connectLws(); +} diff --git a/test-server/android/app/src/main/java/org/libwebsockets/client/MainActivity.java b/test-server/android/app/src/main/java/org/libwebsockets/client/MainActivity.java new file mode 100644 index 00000000..b46f5e8e --- /dev/null +++ b/test-server/android/app/src/main/java/org/libwebsockets/client/MainActivity.java @@ -0,0 +1,246 @@ +/* + * MainActivity.java - libwebsockets test service for Android + * + * Copyright (C) 2016 Alexander Bruines + * + * This file is made available under the Creative Commons CC0 1.0 + * Universal Public Domain Dedication. + * + * The person who associated a work with this deed has dedicated + * the work to the public domain by waiving all of his or her rights + * to the work worldwide under copyright law, including all related + * and neighboring rights, to the extent allowed by law. You can copy, + * modify, distribute and perform the work, even for commercial purposes, + * all without asking permission. + * + * The test apps are intended to be adapted for use in your code, which + * may be proprietary. So unlike the library itself, they are licensed + * Public Domain. + */ + +package org.libwebsockets.client; + + +import android.content.ComponentName; +import android.content.Context; +import android.content.DialogInterface; +import android.content.Intent; +import android.content.ServiceConnection; +import android.os.IBinder; +import android.os.Message; +import android.os.Messenger; +import android.os.RemoteException; +import android.support.v7.app.AlertDialog; +import android.support.v7.app.AppCompatActivity; +import android.os.Bundle; +import android.util.Log; +import android.view.inputmethod.InputMethodManager; +import android.view.View; +import android.widget.EditText; +import android.widget.TextView; + +public class MainActivity extends AppCompatActivity implements LwsService.OutputInterface { + + /** This is the Messenger that handles output from the Service */ + private Messenger mMessenger = null; + + /** The Messenger for sending commands to the Service */ + private Messenger mService = null; + private ServiceConnection mServiceConnection = null; + + private boolean mThreadIsRunning = false; + private boolean mThreadIsSuspended = false; + + private TextView tvCounter; + private EditText etServer; + private EditText etPort; + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_main); + + // Get the layout items + tvCounter = (TextView) findViewById(R.id.textView_counter); + etServer = (EditText) findViewById(R.id.editText_serverLocation); + etPort = (EditText) findViewById(R.id.editText_portNumber); + + // Create the Messenger for handling output from the service + mMessenger = new Messenger(new LwsService.OutputHandler(this)); + + // Restore state from the Bundle when restarting due to a device change. + if(savedInstanceState!=null) { + mThreadIsRunning = savedInstanceState.getBoolean("mThreadIsRunning"); + } + + mServiceConnection = new ServiceConnection() { + @Override + public void onServiceConnected(ComponentName name, IBinder service) { + mService = new Messenger(service); + try { + // Set the output messenger by starting the thread + Message msg = Message.obtain(null, LwsService.MSG_SET_OUTPUT_HANDLER, 0, 0); + msg.replyTo = mMessenger; + mService.send(msg); + if(mThreadIsRunning){ + // If the thread is already running at this point it means + // that the application was restarted after a device change. + // This implies that the thread was suspended by the onStop method. + msg = Message.obtain(null, LwsService.MSG_THREAD_RESUME, 0, 0); + mService.send(msg); + mThreadIsSuspended = false; + } + } + catch(RemoteException e) { + e.printStackTrace(); + } + } + + @Override + public void onServiceDisconnected(ComponentName name) { + Log.e("MainActivity","onServiceDisconnected !"); + mService = null; + } + }; + + if(savedInstanceState==null){ + startService(new Intent(getBaseContext(), LwsService.class)); + } + } + + @Override + protected void onSaveInstanceState(Bundle outState) { + super.onSaveInstanceState(outState); + outState.putBoolean("mThreadIsRunning", mThreadIsRunning); + } + + @Override + protected void onStart() { + super.onStart(); + bindService(new Intent(getBaseContext(), LwsService.class), mServiceConnection, Context.BIND_AUTO_CREATE); + } + + @Override + protected void onStop() { + super.onStop(); + if(mThreadIsRunning) { + if (!mThreadIsSuspended) { + try { + mService.send(Message.obtain(null, LwsService.MSG_THREAD_SUSPEND, 0, 0)); + } catch (RemoteException e) { + e.printStackTrace(); + } + mThreadIsSuspended = true; + } + } + unbindService(mServiceConnection); + } + + @Override + protected void onDestroy() { + super.onDestroy(); + if(isFinishing()){ + stopService(new Intent(getBaseContext(), LwsService.class)); + } + } + + /** Implement the interface to receive output from the LwsService */ + @Override + public void handleOutputMessage(Message message) { + switch(message.what) { + case LwsService.MSG_DUMB_INCREMENT_PROTOCOL_COUNTER: + tvCounter.setText((String)message.obj); + break; + case LwsService.MSG_LWS_CALLBACK_CLIENT_CONNECTION_ERROR: + connectErrorListener(); + break; + case LwsService.MSG_LWS_CALLBACK_CLIENT_ESTABLISHED: + break; + case LwsService.MSG_THREAD_STARTED: + // The thread was started + mThreadIsRunning = true; + mThreadIsSuspended = false; + break; + case LwsService.MSG_THREAD_STOPPED: + // The thread was stopped + mThreadIsRunning = false; + mThreadIsSuspended = false; + break; + case LwsService.MSG_THREAD_SUSPENDED: + // The thread is suspended + mThreadIsRunning = true; + mThreadIsSuspended = true; + break; + case LwsService.MSG_THREAD_RESUMED: + // the thread was resumed + mThreadIsRunning = true; + mThreadIsSuspended = false; + break; + default: + break; + } + } + + private void connectErrorListener(){ + try { + Message msg; + if(mThreadIsRunning) { + msg = Message.obtain(null, LwsService.MSG_THREAD_STOP); + mService.send(msg); + } + AlertDialog.Builder adb = new AlertDialog.Builder(this); + adb.setTitle("Error"); + adb.setPositiveButton("OK", new DialogInterface.OnClickListener() { + public void onClick(DialogInterface dialog, int which) { + } + }); + adb.setMessage("Could not connect to the server."); + adb.show(); + } + catch (RemoteException e){} + } + + /** + * Start/Stop Button Handler + */ + + public void clickStart(View v) { + if(!mThreadIsRunning) { + View view = this.getCurrentFocus(); + if (view != null) { + InputMethodManager imm = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE); + imm.hideSoftInputFromWindow(view.getWindowToken(), 0); + } + mThreadIsRunning = true; + mThreadIsSuspended = false; + try { + Message msg = Message.obtain(null, LwsService.MSG_SET_CONNECTION_PARAMETERS, 0, 0); + int port = 0; + if(!etPort.getText().toString().equals("")) // prevent NumberformatException + port = Integer.parseInt(etPort.getText().toString()); + LwsService.ConnectionParameters parameters = new LwsService.ConnectionParameters( + etServer.getText().toString(), + port + ); + msg.obj = parameters; + mService.send(msg); + msg = Message.obtain(null, LwsService.MSG_THREAD_START, 0, 0); + mService.send(msg); + } + catch(RemoteException e) { + e.printStackTrace(); + } + } + else { + try { + mService.send(Message.obtain(null, LwsService.MSG_THREAD_STOP, 0, 0)); + } + catch(RemoteException e) { + e.printStackTrace(); + } + mThreadIsRunning = false; + mThreadIsSuspended = false; + } + } + +} diff --git a/test-server/android/app/src/main/java/org/libwebsockets/client/ThreadService.java b/test-server/android/app/src/main/java/org/libwebsockets/client/ThreadService.java new file mode 100644 index 00000000..b9ae8632 --- /dev/null +++ b/test-server/android/app/src/main/java/org/libwebsockets/client/ThreadService.java @@ -0,0 +1,284 @@ +/* + * ThreadService.java - libwebsockets test service for Android + * + * Copyright (C) 2016 Alexander Bruines + * + * This file is made available under the Creative Commons CC0 1.0 + * Universal Public Domain Dedication. + * + * The person who associated a work with this deed has dedicated + * the work to the public domain by waiving all of his or her rights + * to the work worldwide under copyright law, including all related + * and neighboring rights, to the extent allowed by law. You can copy, + * modify, distribute and perform the work, even for commercial purposes, + * all without asking permission. + * + * The test apps are intended to be adapted for use in your code, which + * may be proprietary. So unlike the library itself, they are licensed + * Public Domain. + */ + +package org.libwebsockets.client; + +import android.app.Service; +import android.content.Intent; +import android.os.Handler; +import android.os.IBinder; +import android.os.Message; +import android.os.Messenger; +import android.os.RemoteException; +import android.util.Log; + +import java.lang.ref.WeakReference; + +public abstract class ThreadService extends Service { + /** Messages that can be send to the Service: **/ + public final static int MSG_SET_OUTPUT_HANDLER = 1001; + public final static int MSG_THREAD_START = 1002; + public final static int MSG_THREAD_STOP = 1003; + public final static int MSG_THREAD_SUSPEND = 1004; + public final static int MSG_THREAD_RESUME = 1005; + + /** + * Messages that may be send from the Service + * (Clients should handle these messages) + **/ + public final static int MSG_THREAD_STARTED = 2001; + public final static int MSG_THREAD_STOPPED = 2002; + public final static int MSG_THREAD_SUSPENDED = 2003; + public final static int MSG_THREAD_RESUMED = 2004; + + /** Data accessed by both worker thread and the UI-thread must be synchronized **/ + public final Object mThreadLock = new Object();; + public volatile boolean mMustQuit; + public volatile boolean mWorkThreadIsRunning; + public volatile boolean mMustSuspend; + + /** Handler for incoming messages **/ + public static class InputHandler extends Handler { + private final WeakReference mService; + InputHandler(ThreadService service) { + mService = new WeakReference(service); + } + @Override + public void handleMessage(Message msg) { + ThreadService service = mService.get(); + if(service != null) { + service.handleInputMessage(msg); + } + } + } + + /** + * Interface and Handler for outgoing messages to clients of this service. + * (Must be implemented by the client.) + */ + public interface OutputInterface { + void handleOutputMessage(Message message); + } + public static class OutputHandler extends Handler { + // Notice that we do NOT use a WeakReference here + // (If we did the service would lose mOutputMessenger the moment + // that garbage collection is performed by the Java VM) + private final OutputInterface mInterface; + OutputHandler(OutputInterface object) { + mInterface = object; + } + @Override + public void handleMessage(Message msg) { + mInterface.handleOutputMessage(msg); + } + } + + /** The Messengers used to communicate with the clients of this service **/ + public final Messenger mInputMessenger = new Messenger(new InputHandler(this)); + public Messenger mOutputMessenger; + + /** The worker thread and its runnable **/ + public static class WorkerThreadRunnable implements Runnable { + private final WeakReference mService; + WorkerThreadRunnable(ThreadService service){ + mService = new WeakReference(service); + } + @Override + public void run() { + ThreadService service = mService.get(); + if(service != null) { + service.mWorkThreadIsRunning = true; + service.workerThreadRun(); + service.mWorkThreadIsRunning = false; + } + } + } + public Thread mWorkerThread; + + /** Handle incoming messages from the client **/ + public void handleInputMessage(Message msg) { + try { + Message m; + switch(msg.what) { + case MSG_SET_OUTPUT_HANDLER: + // set the output messenger then + // send a message indicating the thread status + mOutputMessenger = msg.replyTo; + break; + case MSG_THREAD_START: + try { + // reset thread vars + synchronized (mThreadLock) { + // thread allready running? + if(!mWorkThreadIsRunning){ + // no, start it + mMustQuit = false; + mMustSuspend = false; + mWorkerThread = new Thread(new WorkerThreadRunnable(this)); + mWorkerThread.start(); + } + else { + // yes, resume it + mMustQuit = false; + mMustSuspend = false; + mThreadLock.notifyAll(); + } + } + } + catch(NullPointerException e) { + e.printStackTrace(); + } + if(mOutputMessenger != null) { + m = Message.obtain(null, MSG_THREAD_STARTED, 0, 0); + mOutputMessenger.send(m); + } + break; + case MSG_THREAD_STOP: + try { + synchronized(mThreadLock) { + if(mWorkThreadIsRunning) { + mMustQuit = true; + mMustSuspend = false; + mThreadLock.notifyAll(); + } + } + mWorkerThread.join(); + } + catch(InterruptedException e) { + Log.e("ThreadService","handleInputMessage join() interrupted"); + } + if(mOutputMessenger != null) { + m = Message.obtain(null, MSG_THREAD_STOPPED, 0, 0); + mOutputMessenger.send(m); + } + break; + case MSG_THREAD_SUSPEND: + synchronized (mThreadLock) { + if(mWorkThreadIsRunning) { + mMustSuspend = true; + } + } + if(mOutputMessenger != null) { + m = Message.obtain(null, MSG_THREAD_SUSPENDED, 0, 0); + mOutputMessenger.send(m); + } + break; + case MSG_THREAD_RESUME: + synchronized (mThreadLock) { + if(mWorkThreadIsRunning) { + mMustSuspend = false; + mThreadLock.notifyAll(); + } + } + if(mOutputMessenger != null) { + m = Message.obtain(null, MSG_THREAD_RESUMED, 0, 0); + mOutputMessenger.send(m); + } + break; + default: + break; + } + } + catch(RemoteException e) { + e.printStackTrace(); + } + } + + /** + * This can be called from the JNI functions to send output messages to the client + */ + public void sendMessage(int msg, Object obj){ + Message m = Message.obtain(null, msg, 0, 0); + m.obj = obj; + try { + mOutputMessenger.send(m); + } + catch(RemoteException e) { + e.printStackTrace(); + } + } + + /** The run() function for the worker thread **/ + public abstract void workerThreadRun(); + + /** + * Called when the service is being created. + * ie. When the first client calls bindService() or startService(). + **/ + @Override + public void onCreate() { + super.onCreate(); + // initialize variables + mWorkThreadIsRunning = false; + mMustQuit = false; + mOutputMessenger = null; + mWorkerThread = null; + } + + /** + * Called when the first client is binding to the service with bindService() + * + * If the service was started with bindService() it will automatically stop when the last + * client unbinds from the service. If you want the service to continue running even if it + * is not bound to anything then start the service with startService() before + * calling bindService(). In this case stopService() must be called after unbinding + * to stop the service. + */ + @Override + public IBinder onBind(Intent intent) { + return mInputMessenger.getBinder(); + } + + /** Called if the service is started with startService(). */ + @Override + public int onStartCommand(Intent intent, int flags, int startId) { + return START_STICKY; + } + + /** Called when the first client is binds to the service with bindService() */ + @Override + public void onRebind(Intent intent) {} + + /** Called when all clients have unbound with unbindService() */ + @Override + public boolean onUnbind(Intent intent) { + //mOutputMessenger = null; + return false; // do not allow to rebind. + } + + /** Called when the service is no longer used and is being destroyed */ + @Override + public void onDestroy() { + super.onDestroy(); + try { + if(mWorkThreadIsRunning){ + synchronized(mThreadLock) { + mMustQuit = true; + mMustSuspend = false; + mThreadLock.notifyAll(); + } + mWorkerThread.join(); + } + } + catch(NullPointerException | InterruptedException e) { + e.printStackTrace(); + } + } +} diff --git a/test-server/android/app/src/main/jni/Android.mk b/test-server/android/app/src/main/jni/Android.mk new file mode 100644 index 00000000..80720ceb --- /dev/null +++ b/test-server/android/app/src/main/jni/Android.mk @@ -0,0 +1,41 @@ +# get current directory +LOCAL_PATH := $(call my-dir) + +# libz.a +# +include $(CLEAR_VARS) +LOCAL_MODULE := libz +LOCAL_SRC_FILES := $(TARGET_ARCH_ABI)/lib/libz.a +include $(PREBUILT_STATIC_LIBRARY) + +# libssl.a +# +include $(CLEAR_VARS) +LOCAL_MODULE := libssl +LOCAL_SRC_FILES := $(TARGET_ARCH_ABI)/lib/libssl.a +include $(PREBUILT_STATIC_LIBRARY) + +# libcrypto.a +# +include $(CLEAR_VARS) +LOCAL_MODULE := libcrypto +LOCAL_SRC_FILES := $(TARGET_ARCH_ABI)/lib/libcrypto.a +include $(PREBUILT_STATIC_LIBRARY) + +# libwebsockets.a +# +include $(CLEAR_VARS) +LOCAL_MODULE := libwebsockets +LOCAL_SRC_FILES := $(TARGET_ARCH_ABI)/lib/libwebsockets.a +include $(PREBUILT_STATIC_LIBRARY) + +# liblwsservice.so +# +include $(CLEAR_VARS) +LOCAL_DISABLE_FATAL_LINKER_WARNINGS := true +LOCAL_MODULE := lwsservice +LOCAL_SRC_FILES := LwsService.cpp +LOCAL_C_INCLUDES := $(LOCAL_PATH) $(TARGET_ARCH_ABI)/include +LOCAL_STATIC_LIBRARIES := websockets z ssl crypto +LOCAL_LDLIBS := -llog +include $(BUILD_SHARED_LIBRARY) diff --git a/test-server/android/app/src/main/jni/Application.mk b/test-server/android/app/src/main/jni/Application.mk new file mode 100644 index 00000000..cc638ca1 --- /dev/null +++ b/test-server/android/app/src/main/jni/Application.mk @@ -0,0 +1,49 @@ +# +# Zlib, OpenSSL and libwebsockets will be downloaded automatically unless you place +# their source .tar.gz files in the jni directory... +# + +# The location of the NDK +# +NDK_ROOT := /opt/Android/Sdk/ndk-bundle + +# Update these to the latest versions before building +# +ZLIB_VERSION := 1.2.8 +OPENSSL_VERSION := 1.0.2h + +# This will be executed as 'git clone $(LIBWEBSOCKETS_GIT_URL)' +# +LIBWEBSOCKETS_GIT_URL := --branch master https://github.com/warmcat/libwebsockets.git + +# +# Note: If you build for API level 21 or higher in APP_PLATFORM, +# the resulting application will only run on API 21+ devices. +# Even if minSdkVersion has been set to a lower level! +# This is the result of API changes for the native signal() function. +# The recommended solution is to build two packages, one for API 17+ and the other for API 21+ devices. +# http://stackoverflow.com/questions/28740315/android-ndk-getting-java-lang-unsatisfiedlinkerror-dlopen-failed-cannot-loca +# +# Note: If you change the API level the JNI code must be rebuild completely. +# (Run 'make clean' from the app/src/main/jni directory.) +# +APP_PLATFORM := android-23 + +# Builds for armeabi armeabi-v7a x86 mips arm64-v8a x86_64 mips64 +# +#APP_ABI := all + +# The same as above. +# +#APP_ABI := armeabi armeabi-v7a x86 mips arm64-v8a x86_64 mips64 + +# Good enough for most current devices + x86 AVD +# +APP_ABI := armeabi-v7a x86 + +# Enable (GNU) c++11 extentions +APP_CPPFLAGS += -std=gnu++11 + +# Use the GNU standard template library +APP_STL := gnustl_shared + diff --git a/test-server/android/app/src/main/jni/LwsService.cpp b/test-server/android/app/src/main/jni/LwsService.cpp new file mode 100644 index 00000000..769011b6 --- /dev/null +++ b/test-server/android/app/src/main/jni/LwsService.cpp @@ -0,0 +1,307 @@ +/* + * LwsService.cpp - libwebsockets test service for Android + * + * Copyright (C) 2016 Alexander Bruines + * + * This file is made available under the Creative Commons CC0 1.0 + * Universal Public Domain Dedication. + * + * The person who associated a work with this deed has dedicated + * the work to the public domain by waiving all of his or her rights + * to the work worldwide under copyright law, including all related + * and neighboring rights, to the extent allowed by law. You can copy, + * modify, distribute and perform the work, even for commercial purposes, + * all without asking permission. + * + * The test apps are intended to be adapted for use in your code, which + * may be proprietary. So unlike the library itself, they are licensed + * Public Domain. + */ + +#include + +#include +#include +#define printf(...) __android_log_print(ANDROID_LOG_VERBOSE, "LwsService", ##__VA_ARGS__) + +///////////////////////////////////////////////////////// +// Code executed when loading the dynamic link library // +///////////////////////////////////////////////////////// + +// The Java class the native functions shall be part of +#define JNIREG_CLASS "org/libwebsockets/client/LwsService" + +JavaVM* gJvm = NULL; +JNIEnv* gEnv = 0; + +JNIEXPORT jboolean JNICALL jni_initLws(JNIEnv *env, jobject obj); +JNIEXPORT void JNICALL jni_exitLws(JNIEnv *env, jobject obj); +JNIEXPORT void JNICALL jni_serviceLws(JNIEnv *env, jobject obj); +JNIEXPORT void JNICALL jni_setConnectionParameters(JNIEnv *env, jobject obj, jstring serverAddress, jint serverPort); +JNIEXPORT jboolean JNICALL jni_connectLws(JNIEnv *env, jobject obj); + +static JNINativeMethod gMethods[] = { + { "initLws", "()Z", (void*)jni_initLws }, + { "exitLws", "()V", (void*)jni_exitLws }, + { "serviceLws", "()V", (void*)jni_serviceLws }, + { "setConnectionParameters", "(Ljava/lang/String;I)V", (void*)jni_setConnectionParameters }, + { "connectLws", "()Z", (void*)jni_connectLws }, +}; + +static int registerNativeMethods(JNIEnv* env, const char* className, JNINativeMethod* gMethods, int numMethods) +{ + jclass cls; + cls = env->FindClass(className); + if(cls == NULL) { + return JNI_FALSE; + } + if (env->RegisterNatives(cls, gMethods, numMethods) < 0) { + return JNI_FALSE; + } + + return JNI_TRUE; +} + +static int registerNatives(JNIEnv* env) +{ + if(!registerNativeMethods(env, JNIREG_CLASS, gMethods, sizeof(gMethods) / sizeof(gMethods[0]))) { + return JNI_FALSE; + } + return JNI_TRUE; +} + +JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM* vm, void * reserved) { + jint result = -1; + + gJvm = vm; + if(vm->GetEnv((void**)&gEnv, JNI_VERSION_1_6) != JNI_OK) goto bail; + if(vm->AttachCurrentThread(&gEnv, NULL) < 0) goto bail; + if(registerNatives(gEnv) != JNI_TRUE) goto bail; + + result = JNI_VERSION_1_6; + +bail: + return result; +} + +JNIEXPORT void JNICALL JNI_OnUnload(JavaVM *vm, void *reserved) { + gJvm = NULL; +} + +//////////////////////////////////////////////////// +// JNI functions to export: // +//////////////////////////////////////////////////// + +static jclass gLwsServiceCls; +static jobject gLwsServiceObj; +static jmethodID sendMessageId; + +static const int MSG_DUMB_INCREMENT_PROTOCOL_COUNTER = 1; +static const int MSG_LWS_CALLBACK_CLIENT_CONNECTION_ERROR = 2; +static const int MSG_LWS_CALLBACK_CLIENT_ESTABLISHED = 3; + +#define BUFFER_SIZE 4096 + +static struct lws_context *context = NULL; +static struct lws_context_creation_info info; +static struct lws *wsi = NULL; + +// prevents sending messages after jni_exitLws had been called +static int isExit = 0; + +enum websocket_protocols { + PROTOCOL_DUMB_INCREMENT = 0, + PROTOCOL_COUNT +}; + +struct per_session_data { + ;// no data +}; + +static int callback( struct lws *wsi, enum lws_callback_reasons reason, void *user, void *in, size_t len ); + +static struct lws_protocols protocols[] = { + { + "dumb-increment-protocol", + callback, + sizeof( struct per_session_data ), + BUFFER_SIZE, + }, + { NULL, NULL, 0, 0 } // end of list +}; + +static const struct lws_extension exts[] = { + { + "deflate-frame", + lws_extension_callback_pm_deflate, + "deflate_frame" + }, + { NULL, NULL, NULL } +}; + +static int port = 0; +static int use_ssl = 0; +static int use_ssl_client = 0; +static char address[8192]; + +static char ca_cert[8192]; +static char client_cert[8192]; +static char client_cert_key[8192]; + +static int deny_deflate = 0; +static int deny_mux = 0; + +// Logging function for libwebsockets +static void emit_log(int level, const char *msg) +{ + printf("%s", msg); +} + + +JNIEXPORT jboolean JNICALL jni_initLws(JNIEnv *env, jobject obj) +{ + if(context) return JNI_TRUE; + + // Attach the java virtual machine to this thread + gJvm->AttachCurrentThread(&gEnv, NULL); + + // Set java global references to the class and object + jclass cls = env->GetObjectClass(obj); + gLwsServiceCls = (jclass) env->NewGlobalRef(cls); + gLwsServiceObj = env->NewGlobalRef(obj); + + // Get the sendMessage method from the LwsService class (inherited from class ThreadService) + sendMessageId = gEnv->GetMethodID(gLwsServiceCls, "sendMessage", "(ILjava/lang/Object;)V"); + + memset(&info, 0, sizeof(info)); + info.port = CONTEXT_PORT_NO_LISTEN; + info.protocols = protocols; +#ifndef LWS_NO_EXTENSIONS + info.extensions = exts; +#endif + info.gid = -1; + info.uid = -1; + + lws_set_log_level( LLL_NOTICE | LLL_INFO | LLL_ERR | LLL_WARN | LLL_CLIENT, emit_log ); + + context = lws_create_context(&info); + if( context == NULL ){ + emit_log(LLL_ERR, "Creating libwebsocket context failed"); + return JNI_FALSE; + } + + isExit = 0; + + return JNI_TRUE; +} + +// Send a message to the client of the service +// (must call jni_initLws() first) +static inline void sendMessage(int id, jobject obj) +{ + if(!isExit) gEnv->CallVoidMethod(gLwsServiceObj, sendMessageId, id, obj); +} + +JNIEXPORT void JNICALL jni_exitLws(JNIEnv *env, jobject obj) +{ + if(context){ + isExit = 1; + lws_context_destroy(context); + context = NULL; + env->DeleteGlobalRef(gLwsServiceObj); + env->DeleteGlobalRef(gLwsServiceCls); + } +} + +static int callback( + struct lws *wsi, + enum lws_callback_reasons reason, + void *user, + void *in, + size_t len +) +{ + switch(reason){ + + case LWS_CALLBACK_CLIENT_CONNECTION_ERROR: + sendMessage(MSG_LWS_CALLBACK_CLIENT_CONNECTION_ERROR, NULL); + break; + + case LWS_CALLBACK_CLIENT_ESTABLISHED: + sendMessage(MSG_LWS_CALLBACK_CLIENT_ESTABLISHED, NULL); + break; + + case LWS_CALLBACK_CLIENT_RECEIVE: + ((char *)in)[len] = '\0'; + sendMessage(MSG_DUMB_INCREMENT_PROTOCOL_COUNTER, gEnv->NewStringUTF((const char*)in)); + break; + + case LWS_CALLBACK_CLIENT_CONFIRM_EXTENSION_SUPPORTED: + if ((strcmp((const char*)in, "deflate-stream") == 0) && deny_deflate) { + emit_log(LLL_ERR, "websocket: denied deflate-stream extension"); + return 1; + } + if ((strcmp((const char*)in, "deflate-frame") == 0) && deny_deflate) { + emit_log(LLL_ERR, "websocket: denied deflate-frame extension"); + return 1; + } + if ((strcmp((const char*)in, "x-google-mux") == 0) && deny_mux) { + emit_log(LLL_ERR, "websocket: denied x-google-mux extension"); + return 1; + } + break; + + default: + break; + } + + return 0; +} + +JNIEXPORT void JNICALL jni_serviceLws(JNIEnv *env, jobject obj) +{ + if(context){ + lws_service( context, 0 ); + } +} + +JNIEXPORT void JNICALL jni_setConnectionParameters( + JNIEnv *env, + jobject obj, + jstring serverAddress, + jint serverPort +) +{ + address[0] = 0; + port = serverPort; + use_ssl = 0; + use_ssl_client = 0; + snprintf(address, sizeof(address), "%s", env->GetStringUTFChars(serverAddress, 0)); +} + +JNIEXPORT jboolean JNICALL jni_connectLws(JNIEnv *env, jobject obj) +{ + struct lws_client_connect_info info_ws; + memset(&info_ws, 0, sizeof(info_ws)); + + info_ws.port = port; + info_ws.address = address; + info_ws.path = "/"; + info_ws.context = context; + info_ws.ssl_connection = use_ssl; + info_ws.host = address; + info_ws.origin = address; + info_ws.ietf_version_or_minus_one = -1; + info_ws.client_exts = exts; + info_ws.protocol = protocols[PROTOCOL_DUMB_INCREMENT].name; + + // connect + wsi = lws_client_connect_via_info(&info_ws); + if(wsi == NULL ){ + // Error + emit_log(LLL_ERR, "Protocol failed to connect."); + return JNI_FALSE; + } + + return JNI_TRUE; +} diff --git a/test-server/android/app/src/main/jni/NativeLibs.mk b/test-server/android/app/src/main/jni/NativeLibs.mk new file mode 100644 index 00000000..cec82be2 --- /dev/null +++ b/test-server/android/app/src/main/jni/NativeLibs.mk @@ -0,0 +1,1257 @@ +# +# GNU Make makefile for building static libraries for use with the Android NDK +# Copyright (C) 2016, Alexander Bruines +# +# This file is made available under the Creative Commons CC0 1.0 +# Universal Public Domain Dedication. +# +# The person who associated a work with this deed has dedicated +# the work to the public domain by waiving all of his or her rights +# to the work worldwide under copyright law, including all related +# and neighboring rights, to the extent allowed by law. You can copy, +# modify, distribute and perform the work, even for commercial purposes, +# all without asking permission. +# +# The test apps are intended to be adapted for use in your code, which +# may be proprietary. So unlike the library itself, they are licensed +# Public Domain. +# + +# +# This makefile is fully intergrated with this Android Studio project and +# it will be called automaticaly when you build the project with Gradle. +# +# The source packages for the libraries will be automaticaly downloaded. +# Alternativly you can provide your own sources by placing the following +# files in the 'jni' directory: +# +# zlib-1.2.8.tar.gz +# openssl-1.0.2g.tar.gz +# libwebsockets.tar.gz +# +# This makefile was tested with the latest NDK/SDK and Android Studio at the +# time of this writing. As these software packages evolve changes to this +# makefile may be needed or it may become obselete... +# +# This makefile was made for use in Linux but you may be able to edit it +# and make it work under Windows. +# +# At least on Debian, building openssl requires package xutils-dev +# for makedepend. Ofcourse the standard development packages must also be +# installed, but xutils-dev is not that obvious in this case... +# +# Makedepend will most likely print a lot of warnings during the 'make depend' +# stage of building openssl. In this case these warnings can be safely ignored. +# + +# Include Application.mk but do not complain if it is not found +# +ifeq ($(MAKE_NO_INCLUDES),) +-include Application.mk +endif + +# Location of the NDK. +# +ifeq ($(NDK_ROOT),) +NDK_ROOT := /opt/Android/SDK/ndk-bundle +endif + +# Select the ABIs to compile for +# +NDK_APP_ABI = $(APP_ABI) +ifeq ($(NDK_APP_ABI),) +# Set to 'all' if APP_ABI is undefined +NDK_APP_ABI = all +endif +ifeq ($(NDK_APP_ABI),all) +# Translate 'all' to the individual targets +NDK_APP_ABI = armeabi armeabi-v7a arm64-v8a mips mips64 x86 x86_64 +else +# Use the targets from APP_ABI +NDK_APP_ABI = $(APP_ABI) +endif + +# Select the Android platform to compile for +# +ifeq ($(APP_PLATFORM),) +# use a level that supports all specified ABIs if none was specified +APP_PLATFORM = android-21 +endif + +NDK_MAKE_TOOLCHAIN := $(NDK_ROOT)/build/tools/make-standalone-toolchain.sh + +# +# The source packages we want/need +# Zlib and openssl should be defined in Application.mk, libwebsockets is +# cloned from github +# + +ifeq ($(ZLIB_VERSION),) +ZLIB_VERSION := 1.2.8 +endif +ifeq ($(OPENSSL_VERSION),) +OPENSSL_VERSION := 1.0.2g +endif + +ifeq ($(ZLIB_TGZ_SOURCE),) +ZLIB_TGZ_SOURCE := zlib-$(ZLIB_VERSION).tar.gz +endif +ifeq ($(OPENSSL_TGZ_SOURCE),) +OPENSSL_TGZ_SOURCE := openssl-$(OPENSSL_VERSION).tar.gz +endif +LIBWEBSOCKETS_TGZ_SOURCE := libwebsockets.tar.gz + +# The names of the directories in the source tgz files +ZLIB_DIR := $(basename $(basename $(ZLIB_TGZ_SOURCE))) +OPENSSL_DIR := $(basename $(basename $(OPENSSL_TGZ_SOURCE))) +LIBWEBSOCKETS_DIR := $(basename $(basename $(LIBWEBSOCKETS_TGZ_SOURCE))) + +# The URLs used to fetch the source tgz files +ZLIB_TGZ_URL := http://prdownloads.sourceforge.net/libpng/$(ZLIB_TGZ_SOURCE) +OPENSSL_TGZ_URL := https://openssl.org/source/$(OPENSSL_TGZ_SOURCE) +ifeq ($(LIBWEBSOCKETS_GIT_URL),) +LIBWEBSOCKETS_GIT_URL := https://github.com/warmcat/libwebsockets.git +endif + +# These values are the same as the values for $TARGET_ARCH_ABI in Android.mk +# This way 'make $TARGET_ARCH_ABI' builds libraries for that ABI. +# This is also the name for the directory where the libraries are installed to. +# +TARGET_X86 := x86 +TARGET_X86_64 := x86_64 +TARGET_ARM := armeabi +TARGET_ARM_V7A := armeabi-v7a +TARGET_ARM_V7A_HARD := armeabi-v7a-hard +TARGET_ARM64_V8A := arm64-v8a +TARGET_MIPS := mips +TARGET_MIPS64 := mips64 + +# The Android NDK API version to build the libraries with. +# +# android-9 ... android-19 support arm mips and x86 +# android-21 and higher also support arm64 mips64 and x86_64 +# +# These should be set to the same value as APP_PLATFORM (Application.mk) +# +# http://developer.android.com/ndk/guides/stable_apis.html +# +# If you change these or APP_PLATFORM you must do a 'make clean' +# +# Note: +# libraries compiled for android-21 and upwards are incompatible with devices below that version! +# http://stackoverflow.com/questions/28740315/android-ndk-getting-java-lang-unsatisfiedlinkerror-dlopen-failed-cannot-loca +# +TARGET_X86_NDK_API := $(APP_PLATFORM) +TARGET_X86_64_NDK_API := $(APP_PLATFORM) +TARGET_ARM_NDK_API := $(APP_PLATFORM) +TARGET_ARM_V7A_NDK_API := $(APP_PLATFORM) +TARGET_ARM_V7A_HARD_NDK_API := $(APP_PLATFORM) +TARGET_ARM64_V8A_NDK_API := $(APP_PLATFORM) +TARGET_MIPS_NDK_API := $(APP_PLATFORM) +TARGET_MIPS64_NDK_API := $(APP_PLATFORM) + +# The configure arguments to pass to the OpenSSL Configure script +# (--prefix and --openssldir are added automaticaly). +# (note: use no-asm on x86 and x86_64 to generate fully position independent code) +# +# x86 +TARGET_X86_OPENSSL_CONFIG_TARGET := android-x86 +TARGET_X86_OPENSSL_CONFIG := no-asm no-shared no-idea no-mdc2 no-rc5 no-zlib no-zlib-dynamic enable-tlsext no-ssl2 no-ssl3 enable-ec enable-ecdh enable-ecp +# x86_64 +TARGET_X86_64_OPENSSL_CONFIG_TARGET := linux-x86_64 +TARGET_X86_64_OPENSSL_CONFIG := no-asm no-shared no-idea no-mdc2 no-rc5 no-zlib no-zlib-dynamic enable-tlsext no-ssl2 no-ssl3 enable-ec enable-ecdh enable-ecp enable-ec_nistp_64_gcc_128 +# armeabi +TARGET_ARM_OPENSSL_CONFIG_TARGET := android +TARGET_ARM_OPENSSL_CONFIG := no-shared no-idea no-mdc2 no-rc5 no-zlib no-zlib-dynamic enable-tlsext no-ssl2 no-ssl3 enable-ec enable-ecdh enable-ecp +# armeabi-v7a +TARGET_ARM_V7A_OPENSSL_CONFIG_TARGET := android-armv7 +TARGET_ARM_V7A_OPENSSL_CONFIG := no-shared no-idea no-mdc2 no-rc5 no-zlib no-zlib-dynamic enable-tlsext no-ssl2 no-ssl3 enable-ec enable-ecdh enable-ecp +# armeabi-v7a-hard +TARGET_ARM_V7A_HARD_OPENSSL_CONFIG_TARGET := android-armv7 +TARGET_ARM_V7A_HARD_OPENSSL_CONFIG := no-shared no-idea no-mdc2 no-rc5 no-zlib no-zlib-dynamic enable-tlsext no-ssl2 no-ssl3 enable-ec enable-ecdh enable-ecp +# arm64-v8a +TARGET_ARM64_V8A_OPENSSL_CONFIG_TARGET := android +TARGET_ARM64_V8A_OPENSSL_CONFIG := no-shared no-idea no-mdc2 no-rc5 no-zlib no-zlib-dynamic enable-tlsext no-ssl2 no-ssl3 enable-ec enable-ecdh enable-ecp +# mips +TARGET_MIPS_OPENSSL_CONFIG_TARGET := android-mips +TARGET_MIPS_OPENSSL_CONFIG := no-shared no-idea no-mdc2 no-rc5 no-zlib no-zlib-dynamic enable-tlsext no-ssl2 no-ssl3 enable-ec enable-ecdh enable-ecp +# mips64 +TARGET_MIPS64_OPENSSL_CONFIG_TARGET := android +TARGET_MIPS64_OPENSSL_CONFIG := no-shared no-idea no-mdc2 no-rc5 no-zlib no-zlib-dynamic enable-tlsext no-ssl2 no-ssl3 enable-ec enable-ecdh enable-ecp + +# The cmake configuration options for libwebsockets per target ABI, +# --prefix and openssl library/header paths are set automaticaly and +# the location of zlib should be picked up by CMake +# x86 +TARGET_X86_LWS_OPTIONS = \ + -DCMAKE_C_COMPILER=$(shell pwd)/$(TOOLCHAIN_X86)/bin/$(TOOLCHAIN_X86_PREFIX)-gcc \ + -DCMAKE_AR=$(shell pwd)/$(TOOLCHAIN_X86)/bin/$(TOOLCHAIN_X86_PREFIX)-ar \ + -DCMAKE_RANLIB=$(shell pwd)/$(TOOLCHAIN_X86)/bin/$(TOOLCHAIN_X86_PREFIX)-ranlib \ + -DCMAKE_C_FLAGS="$$CFLAGS" \ + -DLWS_WITH_SHARED=OFF \ + -DLWS_WITH_STATIC=ON \ + -DLWS_WITHOUT_DAEMONIZE=ON \ + -DLWS_WITHOUT_TESTAPPS=ON \ + -DLWS_IPV6=OFF \ + -DLWS_USE_BUNDLED_ZLIB=OFF \ + -DLWS_WITH_SSL=ON \ + -DLWS_WITH_HTTP2=ON \ + -DCMAKE_BUILD_TYPE=Release +# x86_64 +TARGET_X86_64_LWS_OPTIONS = \ + -DCMAKE_C_COMPILER=$(shell pwd)/$(TOOLCHAIN_X86_64)/bin/$(TOOLCHAIN_X86_64_PREFIX)-gcc \ + -DCMAKE_AR=$(shell pwd)/$(TOOLCHAIN_X86_64)/bin/$(TOOLCHAIN_X86_64_PREFIX)-ar \ + -DCMAKE_RANLIB=$(shell pwd)/$(TOOLCHAIN_X86_64)/bin/$(TOOLCHAIN_X86_64_PREFIX)-ranlib \ + -DCMAKE_C_FLAGS="$$CFLAGS" \ + -DLWS_WITH_SHARED=OFF \ + -DLWS_WITH_STATIC=ON \ + -DLWS_WITHOUT_DAEMONIZE=ON \ + -DLWS_WITHOUT_TESTAPPS=ON \ + -DLWS_IPV6=OFF \ + -DLWS_USE_BUNDLED_ZLIB=OFF \ + -DLWS_WITH_SSL=ON \ + -DLWS_WITH_HTTP2=ON \ + -DCMAKE_BUILD_TYPE=Release +# armeabi +TARGET_ARM_LWS_OPTIONS = \ + -DCMAKE_C_COMPILER=$(shell pwd)/$(TOOLCHAIN_ARM)/bin/$(TOOLCHAIN_ARM_PREFIX)-gcc \ + -DCMAKE_AR=$(shell pwd)/$(TOOLCHAIN_ARM)/bin/$(TOOLCHAIN_ARM_PREFIX)-ar \ + -DCMAKE_RANLIB=$(shell pwd)/$(TOOLCHAIN_ARM)/bin/$(TOOLCHAIN_ARM_PREFIX)-ranlib \ + -DCMAKE_C_FLAGS="$$CFLAGS" \ + -DLWS_WITH_SHARED=OFF \ + -DLWS_WITH_STATIC=ON \ + -DLWS_WITHOUT_DAEMONIZE=ON \ + -DLWS_WITHOUT_TESTAPPS=ON \ + -DLWS_IPV6=OFF \ + -DLWS_USE_BUNDLED_ZLIB=OFF \ + -DLWS_WITH_SSL=ON \ + -DLWS_WITH_HTTP2=ON \ + -DCMAKE_BUILD_TYPE=Release +# armeabi-v7a +TARGET_ARM_V7A_LWS_OPTIONS = \ + -DCMAKE_C_COMPILER=$(shell pwd)/$(TOOLCHAIN_ARM_V7A)/bin/$(TOOLCHAIN_ARM_V7A_PREFIX)-gcc \ + -DCMAKE_AR=$(shell pwd)/$(TOOLCHAIN_ARM_V7A)/bin/$(TOOLCHAIN_ARM_V7A_PREFIX)-ar \ + -DCMAKE_RANLIB=$(shell pwd)/$(TOOLCHAIN_ARM_V7A)/bin/$(TOOLCHAIN_ARM_V7A_PREFIX)-ranlib \ + -DCMAKE_C_FLAGS="$$CFLAGS" \ + -DLWS_WITH_SHARED=OFF \ + -DLWS_WITH_STATIC=ON \ + -DLWS_WITHOUT_DAEMONIZE=ON \ + -DLWS_WITHOUT_TESTAPPS=ON \ + -DLWS_IPV6=OFF \ + -DLWS_USE_BUNDLED_ZLIB=OFF \ + -DLWS_WITH_SSL=ON \ + -DLWS_WITH_HTTP2=ON \ + -DCMAKE_BUILD_TYPE=Release +# armeabi-v7a-hard +TARGET_ARM_V7A_HARD_LWS_OPTIONS = \ + -DCMAKE_C_COMPILER=$(shell pwd)/$(TOOLCHAIN_ARM_V7A_HARD)/bin/$(TOOLCHAIN_ARM_V7A_HARD_PREFIX)-gcc \ + -DCMAKE_AR=$(shell pwd)/$(TOOLCHAIN_ARM_V7A_HARD)/bin/$(TOOLCHAIN_ARM_V7A_HARD_PREFIX)-ar \ + -DCMAKE_RANLIB=$(shell pwd)/$(TOOLCHAIN_ARM_V7A_HARD)/bin/$(TOOLCHAIN_ARM_V7A_HARD_PREFIX)-ranlib \ + -DCMAKE_C_FLAGS="$$CFLAGS" \ + -DLWS_WITH_SHARED=OFF \ + -DLWS_WITH_STATIC=ON \ + -DLWS_WITHOUT_DAEMONIZE=ON \ + -DLWS_WITHOUT_TESTAPPS=ON \ + -DLWS_IPV6=OFF \ + -DLWS_USE_BUNDLED_ZLIB=OFF \ + -DLWS_WITH_SSL=ON \ + -DLWS_WITH_HTTP2=ON \ + -DCMAKE_BUILD_TYPE=Release +# arm64-v8a +TARGET_ARM64_V8A_LWS_OPTIONS = \ + -DCMAKE_C_COMPILER=$(shell pwd)/$(TOOLCHAIN_ARM64_V8A)/bin/$(TOOLCHAIN_ARM64_V8A_PREFIX)-gcc \ + -DCMAKE_AR=$(shell pwd)/$(TOOLCHAIN_ARM64_V8A)/bin/$(TOOLCHAIN_ARM64_V8A_PREFIX)-ar \ + -DCMAKE_RANLIB=$(shell pwd)/$(TOOLCHAIN_ARM64_V8A)/bin/$(TOOLCHAIN_ARM64_V8A_PREFIX)-ranlib \ + -DCMAKE_C_FLAGS="$$CFLAGS" \ + -DLWS_WITH_SHARED=OFF \ + -DLWS_WITH_STATIC=ON \ + -DLWS_WITHOUT_DAEMONIZE=ON \ + -DLWS_WITHOUT_TESTAPPS=ON \ + -DLWS_IPV6=OFF \ + -DLWS_USE_BUNDLED_ZLIB=OFF \ + -DLWS_WITH_SSL=ON \ + -DLWS_WITH_HTTP2=ON \ + -DCMAKE_BUILD_TYPE=Release +# mips +TARGET_MIPS_LWS_OPTIONS = \ + -DCMAKE_C_COMPILER=$(shell pwd)/$(TOOLCHAIN_MIPS)/bin/$(TOOLCHAIN_MIPS_PREFIX)-gcc \ + -DCMAKE_AR=$(shell pwd)/$(TOOLCHAIN_MIPS)/bin/$(TOOLCHAIN_MIPS_PREFIX)-ar \ + -DCMAKE_RANLIB=$(shell pwd)/$(TOOLCHAIN_MIPS)/bin/$(TOOLCHAIN_MIPS_PREFIX)-ranlib \ + -DCMAKE_C_FLAGS="$$CFLAGS" \ + -DLWS_WITH_SHARED=OFF \ + -DLWS_WITH_STATIC=ON \ + -DLWS_WITHOUT_DAEMONIZE=ON \ + -DLWS_WITHOUT_TESTAPPS=ON \ + -DLWS_IPV6=OFF \ + -DLWS_USE_BUNDLED_ZLIB=OFF \ + -DLWS_WITH_SSL=ON \ + -DLWS_WITH_HTTP2=ON \ + -DCMAKE_BUILD_TYPE=Release +# mips64 +TARGET_MIPS64_LWS_OPTIONS = \ + -DCMAKE_C_COMPILER=$(shell pwd)/$(TOOLCHAIN_MIPS64)/bin/$(TOOLCHAIN_MIPS64_PREFIX)-gcc \ + -DCMAKE_AR=$(shell pwd)/$(TOOLCHAIN_MIPS64)/bin/$(TOOLCHAIN_MIPS64_PREFIX)-ar \ + -DCMAKE_RANLIB=$(shell pwd)/$(TOOLCHAIN_MIPS64)/bin/$(TOOLCHAIN_MIPS64_PREFIX)-ranlib \ + -DCMAKE_C_FLAGS="$$CFLAGS" \ + -DLWS_WITH_SHARED=OFF \ + -DLWS_WITH_STATIC=ON \ + -DLWS_WITHOUT_DAEMONIZE=ON \ + -DLWS_WITHOUT_TESTAPPS=ON \ + -DLWS_IPV6=OFF \ + -DLWS_USE_BUNDLED_ZLIB=OFF \ + -DLWS_WITH_SSL=ON \ + -DLWS_WITH_HTTP2=ON \ + -DCMAKE_BUILD_TYPE=Release + +# +# Toolchain configuration +# + +# The directory names for the different toolchains +TOOLCHAIN_X86 := toolchains/x86 +TOOLCHAIN_X86_64 := toolchains/x86_64 +TOOLCHAIN_ARM := toolchains/arm +TOOLCHAIN_ARM_V7A := toolchains/arm-v7a +TOOLCHAIN_ARM_V7A_HARD := toolchains/arm-v7a-hard +TOOLCHAIN_ARM64_V8A := toolchains/arm64-v8a +TOOLCHAIN_MIPS := toolchains/mips +TOOLCHAIN_MIPS64 := toolchains/mips64 + +# The arch names for the different toolchains +TOOLCHAIN_X86_ARCH := x86 +TOOLCHAIN_X86_64_ARCH := x86_64 +TOOLCHAIN_ARM_ARCH := arm-linux-androideabi +TOOLCHAIN_ARM_V7A_ARCH := arm-linux-androideabi +TOOLCHAIN_ARM_V7A_HARD_ARCH := arm-linux-androideabi +TOOLCHAIN_ARM64_V8A_ARCH := aarch64-linux-android +TOOLCHAIN_MIPS_ARCH := mipsel-linux-android +TOOLCHAIN_MIPS64_ARCH := mips64el-linux-android + +# Other (global) toolchain settings +TOOLCHAIN_GCC_VERSION := 4.9 + +# The settings to use for the individual toolchains: +# x86 +TOOLCHAIN_X86_PLATFORM := $(TARGET_X86_NDK_API) +TOOLCHAIN_X86_PREFIX := i686-linux-android +TOOLCHAIN_X86_FLAGS := -march=i686 -msse3 -mstackrealign -mfpmath=sse +TOOLCHAIN_X86_LINK := +TOOLCHAIN_X86_PLATFORM_HEADERS := $(shell pwd)/$(TOOLCHAIN_X86)/sysroot/usr/include +TOOLCHAIN_X86_PLATFORM_LIBS := $(shell pwd)/$(TOOLCHAIN_X86)/sysroot/usr/lib +# x86_64 +TOOLCHAIN_X86_64_PLATFORM := $(TARGET_X86_64_NDK_API) +TOOLCHAIN_X86_64_PREFIX := x86_64-linux-android +TOOLCHAIN_X86_64_FLAGS := +TOOLCHAIN_X86_64_LINK := +TOOLCHAIN_X86_64_PLATFORM_HEADERS := $(shell pwd)/$(TOOLCHAIN_X86_64)/sysroot/usr/include +TOOLCHAIN_X86_64_PLATFORM_LIBS := $(shell pwd)/$(TOOLCHAIN_X86_64)/sysroot/usr/lib +# arm +TOOLCHAIN_ARM_PLATFORM := $(TARGET_ARM_NDK_API) +TOOLCHAIN_ARM_PREFIX := arm-linux-androideabi +TOOLCHAIN_ARM_FLAGS := -mthumb +TOOLCHAIN_ARM_LINK := +TOOLCHAIN_ARM_PLATFORM_HEADERS := $(shell pwd)/$(TOOLCHAIN_ARM)/sysroot/usr/include +TOOLCHAIN_ARM_PLATFORM_LIBS := $(shell pwd)/$(TOOLCHAIN_ARM)/sysroot/usr/lib +# arm-v7a +TOOLCHAIN_ARM_V7A_PLATFORM := $(TARGET_ARM_V7A_NDK_API) +TOOLCHAIN_ARM_V7A_PREFIX := arm-linux-androideabi +TOOLCHAIN_ARM_V7A_FLAGS := -march=armv7-a -mfloat-abi=softfp -mfpu=vfpv3-d16 +TOOLCHAIN_ARM_V7A_LINK := -march=armv7-a -Wl,--fix-cortex-a8 +TOOLCHAIN_ARM_V7A_PLATFORM_HEADERS := $(shell pwd)/$(TOOLCHAIN_ARM_V7A)/sysroot/usr/include +TOOLCHAIN_ARM_V7A_PLATFORM_LIBS := $(shell pwd)/$(TOOLCHAIN_ARM_V7A)/sysroot/usr/lib +# arm-v7a-hard +TOOLCHAIN_ARM_V7A_HARD_PLATFORM := $(TARGET_ARM_V7A_HARD_NDK_API) +TOOLCHAIN_ARM_V7A_HARD_PREFIX := arm-linux-androideabi +TOOLCHAIN_ARM_V7A_HARD_FLAGS := -march=armv7-a -mfpu=vfpv3-d16 -mhard-float -mfloat-abi=hard -D_NDK_MATH_NO_SOFTFP=1 +TOOLCHAIN_ARM_V7A_HARD_LINK := -march=armv7-a -Wl,--fix-cortex-a8 -Wl,--no-warn-mismatch -lm_hard +TOOLCHAIN_ARM_V7A_HARD_PLATFORM_HEADERS := $(shell pwd)/$(TOOLCHAIN_ARM_V7A_HARD)/sysroot/usr/include +TOOLCHAIN_ARM_V7A_HARD_PLATFORM_LIBS := $(shell pwd)/$(TOOLCHAIN_ARM_V7A_HARD)/sysroot/usr/lib +# arm64-v8a +TOOLCHAIN_ARM64_V8A_PLATFORM := $(TARGET_ARM64_V8A_NDK_API) +TOOLCHAIN_ARM64_V8A_PREFIX := aarch64-linux-android +TOOLCHAIN_ARM64_V8A_FLAGS := +TOOLCHAIN_ARM64_V8A_LINK := +TOOLCHAIN_ARM64_V8A_PLATFORM_HEADERS := $(shell pwd)/$(TOOLCHAIN_ARM64_V8A)/sysroot/usr/include +TOOLCHAIN_ARM64_V8A_PLATFORM_LIBS := $(shell pwd)/$(TOOLCHAIN_ARM64_V8A)/sysroot/usr/lib +# mips +TOOLCHAIN_MIPS_PLATFORM := $(TARGET_MIPS_NDK_API) +TOOLCHAIN_MIPS_PREFIX := mipsel-linux-android +TOOLCHAIN_MIPS_FLAGS := +TOOLCHAIN_MIPS_LINK := +TOOLCHAIN_MIPS_PLATFORM_HEADERS := $(shell pwd)/$(TOOLCHAIN_MIPS)/sysroot/usr/include +TOOLCHAIN_MIPS_PLATFORM_LIBS := $(shell pwd)/$(TOOLCHAIN_MIPS)/sysroot/usr/lib +# mips64 +TOOLCHAIN_MIPS64_PLATFORM := $(TARGET_MIPS64_NDK_API) +TOOLCHAIN_MIPS64_PREFIX := mips64el-linux-android +TOOLCHAIN_MIPS64_FLAGS := +TOOLCHAIN_MIPS64_LINK := +TOOLCHAIN_MIPS64_PLATFORM_HEADERS := $(shell pwd)/$(TOOLCHAIN_MIPS64)/sysroot/usr/include +TOOLCHAIN_MIPS64_PLATFORM_LIBS := $(shell pwd)/$(TOOLCHAIN_MIPS64)/sysroot/usr/lib + +# Environment variables to set while compiling for each ABI +# x86 +TOOLCHAIN_X86_ENV = \ + ANDROID_DEV="$(shell pwd)/$(TOOLCHAIN_X86)/bin" \ + CC=$(TOOLCHAIN_X86_PREFIX)-gcc \ + CXX=$(TOOLCHAIN_X86_PREFIX)-g++ \ + LINK=$(TOOLCHAIN_X86_PREFIX)-g++ \ + LD=$(TOOLCHAIN_X86_PREFIX)-ld \ + AR=$(TOOLCHAIN_X86_PREFIX)-ar \ + RANLIB=$(TOOLCHAIN_X86_PREFIX)-ranlib \ + STRIP=$(TOOLCHAIN_X86_PREFIX)-strip \ + ARCH_FLAGS="$(TOOLCHAIN_X86_FLAGS)" \ + ARCH_LINK="$(TOOLCHAIN_X86_LINK)" \ + CPPFLAGS="-I. $(TOOLCHAIN_X86_FLAGS) -I$(TOOLCHAIN_X86_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + CXXFLAGS="-I. $(TOOLCHAIN_X86_FLAGS) -I$(TOOLCHAIN_X86_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64 -frtti -fexceptions" \ + CFLAGS="-I. $(TOOLCHAIN_X86_FLAGS) -I$(TOOLCHAIN_X86_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + LDFLAGS="$(TOOLCHAIN_X86_LINK)" \ + PATH="$(shell pwd)/$(TOOLCHAIN_X86)/bin:$$PATH" +# x86_64 +TOOLCHAIN_X86_64_ENV = \ + ANDROID_DEV="$(shell pwd)/$(TOOLCHAIN_X86_64)/bin" \ + CC=$(TOOLCHAIN_X86_64_PREFIX)-gcc \ + CXX=$(TOOLCHAIN_X86_64_PREFIX)-g++ \ + LINK=$(TOOLCHAIN_X86_64_PREFIX)-g++ \ + LD=$(TOOLCHAIN_X86_64_PREFIX)-ld \ + AR=$(TOOLCHAIN_X86_64_PREFIX)-ar \ + RANLIB=$(TOOLCHAIN_X86_64_PREFIX)-ranlib \ + STRIP=$(TOOLCHAIN_X86_64_PREFIX)-strip \ + ARCH_FLAGS="$(TOOLCHAIN_X86_64_FLAGS)" \ + ARCH_LINK="$(TOOLCHAIN_X86_64_LINK)" \ + CPPFLAGS="-I. $(TOOLCHAIN_X86_64_FLAGS) -I$(TOOLCHAIN_X86_64_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + CXXFLAGS="-I. $(TOOLCHAIN_X86_64_FLAGS) -I$(TOOLCHAIN_X86_64_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64 -frtti -fexceptions" \ + CFLAGS="-I. $(TOOLCHAIN_X86_64_FLAGS) -I$(TOOLCHAIN_X86_64_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + LDFLAGS="$(TOOLCHAIN_X86_64_LINK)" \ + PATH="$(shell pwd)/$(TOOLCHAIN_X86_64)/bin:$$PATH" +# arm +TOOLCHAIN_ARM_ENV = \ + ANDROID_DEV="$(shell pwd)/$(TOOLCHAIN_ARM)/bin" \ + CC=$(TOOLCHAIN_ARM_PREFIX)-gcc \ + CXX=$(TOOLCHAIN_ARM_PREFIX)-g++ \ + LINK=$(TOOLCHAIN_ARM_PREFIX)-g++ \ + LD=$(TOOLCHAIN_ARM_PREFIX)-ld \ + AR=$(TOOLCHAIN_ARM_PREFIX)-ar \ + RANLIB=$(TOOLCHAIN_ARM_PREFIX)-ranlib \ + STRIP=$(TOOLCHAIN_ARM_PREFIX)-strip \ + ARCH_FLAGS="$(TOOLCHAIN_ARM_FLAGS)" \ + ARCH_LINK="$(TOOLCHAIN_ARM_LINK)" \ + CPPFLAGS="-I. $(TOOLCHAIN_ARM_FLAGS) -I$(TOOLCHAIN_ARM_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + CXXFLAGS="-I. $(TOOLCHAIN_ARM_FLAGS) -I$(TOOLCHAIN_ARM_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64 -frtti -fexceptions" \ + CFLAGS="-I. $(TOOLCHAIN_ARM_FLAGS) -I$(TOOLCHAIN_ARM_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + LDFLAGS="$(TOOLCHAIN_ARM_LINK)" \ + PATH="$(shell pwd)/$(TOOLCHAIN_ARM)/bin:$$PATH" +# arm-v7a +TOOLCHAIN_ARM_V7A_ENV = \ + ANDROID_DEV="$(shell pwd)/$(TOOLCHAIN_ARM_V7A)/bin" \ + CC=$(TOOLCHAIN_ARM_V7A_PREFIX)-gcc \ + CXX=$(TOOLCHAIN_ARM_V7A_PREFIX)-g++ \ + LINK=$(TOOLCHAIN_ARM_V7A_PREFIX)-g++ \ + LD=$(TOOLCHAIN_ARM_V7A_PREFIX)-ld \ + AR=$(TOOLCHAIN_ARM_V7A_PREFIX)-ar \ + RANLIB=$(TOOLCHAIN_ARM_V7A_PREFIX)-ranlib \ + STRIP=$(TOOLCHAIN_ARM_V7A_PREFIX)-strip \ + ARCH_FLAGS="$(TOOLCHAIN_ARM_V7A_FLAGS)" \ + ARCH_LINK="$(TOOLCHAIN_ARM_V7A_LINK)" \ + CPPFLAGS="-I. $(TOOLCHAIN_ARM_V7A_FLAGS) -I$(TOOLCHAIN_ARM_V7A_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + CXXFLAGS="-I. $(TOOLCHAIN_ARM_V7A_FLAGS) -I$(TOOLCHAIN_ARM_V7A_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64 -frtti -fexceptions" \ + CFLAGS="-I. $(TOOLCHAIN_ARM_V7A_FLAGS) -I$(TOOLCHAIN_ARM_V7A_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + LDFLAGS="$(TOOLCHAIN_ARM_V7A_LINK)" \ + PATH="$(shell pwd)/$(TOOLCHAIN_ARM_V7A)/bin:$$PATH" +# arm-v7a-hard +TOOLCHAIN_ARM_V7A_HARD_ENV = \ + ANDROID_DEV="$(shell pwd)/$(TOOLCHAIN_ARM_V7A_HARD)/bin" \ + CC=$(TOOLCHAIN_ARM_V7A_HARD_PREFIX)-gcc \ + CXX=$(TOOLCHAIN_ARM_V7A_HARD_PREFIX)-g++ \ + LINK=$(TOOLCHAIN_ARM_V7A_HARD_PREFIX)-g++ \ + LD=$(TOOLCHAIN_ARM_V7A_HARD_PREFIX)-ld \ + AR=$(TOOLCHAIN_ARM_V7A_HARD_PREFIX)-ar \ + RANLIB=$(TOOLCHAIN_ARM_V7A_HARD_PREFIX)-ranlib \ + STRIP=$(TOOLCHAIN_ARM_V7A_HARD_PREFIX)-strip \ + ARCH_FLAGS="$(TOOLCHAIN_ARM_V7A_HARD_FLAGS)" \ + ARCH_LINK="$(TOOLCHAIN_ARM_V7A_HARD_LINK)" \ + CPPFLAGS="-I. $(TOOLCHAIN_ARM_V7A_HARD_FLAGS) -I$(TOOLCHAIN_ARM_V7A_HARD_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + CXXFLAGS="-I. $(TOOLCHAIN_ARM_V7A_HARD_FLAGS) -I$(TOOLCHAIN_ARM_V7A_HARD_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64 -frtti -fexceptions" \ + CFLAGS="-I. $(TOOLCHAIN_ARM_V7A_HARD_FLAGS) -I$(TOOLCHAIN_ARM_V7A_HARD_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + LDFLAGS="$(TOOLCHAIN_ARM_V7A_HARD_LINK)" \ + PATH="$(shell pwd)/$(TOOLCHAIN_ARM_V7A_HARD)/bin:$$PATH" +# arm64-v8a +TOOLCHAIN_ARM64_V8A_ENV = \ + ANDROID_DEV="$(shell pwd)/$(TOOLCHAIN_ARM64_V8A)/bin" \ + CC=$(TOOLCHAIN_ARM64_V8A_PREFIX)-gcc \ + CXX=$(TOOLCHAIN_ARM64_V8A_PREFIX)-g++ \ + LINK=$(TOOLCHAIN_ARM64_V8A_PREFIX)-g++ \ + LD=$(TOOLCHAIN_ARM64_V8A_PREFIX)-ld \ + AR=$(TOOLCHAIN_ARM64_V8A_PREFIX)-ar \ + RANLIB=$(TOOLCHAIN_ARM64_V8A_PREFIX)-ranlib \ + STRIP=$(TOOLCHAIN_ARM64_V8A_PREFIX)-strip \ + ARCH_FLAGS="$(TOOLCHAIN_ARM64_V8A_FLAGS)" \ + ARCH_LINK="$(TOOLCHAIN_ARM64_V8A_LINK)" \ + CPPFLAGS="-I. $(TOOLCHAIN_ARM64_V8A_FLAGS) -I$(TOOLCHAIN_ARM64_V8A_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + CXXFLAGS="-I. $(TOOLCHAIN_ARM64_V8A_FLAGS) -I$(TOOLCHAIN_ARM64_V8A_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64 -frtti -fexceptions" \ + CFLAGS="-I. $(TOOLCHAIN_ARM64_V8A_FLAGS) -I$(TOOLCHAIN_ARM64_V8A_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + LDFLAGS="$(TOOLCHAIN_ARM64_V8A_LINK)" \ + PATH="$(shell pwd)/$(TOOLCHAIN_ARM64_V8A)/bin:$$PATH" +# mips +TOOLCHAIN_MIPS_ENV = \ + ANDROID_DEV="$(shell pwd)/$(TOOLCHAIN_MIPS)/bin" \ + CC=$(TOOLCHAIN_MIPS_PREFIX)-gcc \ + CXX=$(TOOLCHAIN_MIPS_PREFIX)-g++ \ + LINK=$(TOOLCHAIN_MIPS_PREFIX)-g++ \ + LD=$(TOOLCHAIN_MIPS_PREFIX)-ld \ + AR=$(TOOLCHAIN_MIPS_PREFIX)-ar \ + RANLIB=$(TOOLCHAIN_MIPS_PREFIX)-ranlib \ + STRIP=$(TOOLCHAIN_MIPS_PREFIX)-strip \ + ARCH_FLAGS="$(TOOLCHAIN_MIPS_FLAGS)" \ + ARCH_LINK="$(TOOLCHAIN_MIPS_LINK)" \ + CPPFLAGS="-I. $(TOOLCHAIN_MIPS_FLAGS) -I$(TOOLCHAIN_MIPS_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + CXXFLAGS="-I. $(TOOLCHAIN_MIPS_FLAGS) -I$(TOOLCHAIN_MIPS_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64 -frtti -fexceptions" \ + CFLAGS="-I. $(TOOLCHAIN_MIPS_FLAGS) -I$(TOOLCHAIN_MIPS_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + LDFLAGS="$(TOOLCHAIN_MIPS_LINK)" \ + PATH="$(shell pwd)/$(TOOLCHAIN_MIPS)/bin:$$PATH" +# mips64 +TOOLCHAIN_MIPS64_ENV = \ + ANDROID_DEV="$(shell pwd)/$(TOOLCHAIN_MIPS64)/bin" \ + CC=$(TOOLCHAIN_MIPS64_PREFIX)-gcc \ + CXX=$(TOOLCHAIN_MIPS64_PREFIX)-g++ \ + LINK=$(TOOLCHAIN_MIPS64_PREFIX)-g++ \ + LD=$(TOOLCHAIN_MIPS64_PREFIX)-ld \ + AR=$(TOOLCHAIN_MIPS64_PREFIX)-ar \ + RANLIB=$(TOOLCHAIN_MIPS64_PREFIX)-ranlib \ + STRIP=$(TOOLCHAIN_MIPS64_PREFIX)-strip \ + ARCH_FLAGS="$(TOOLCHAIN_MIPS64_FLAGS)" \ + ARCH_LINK="$(TOOLCHAIN_MIPS64_LINK)" \ + CPPFLAGS="-I. $(TOOLCHAIN_MIPS64_FLAGS) -I$(TOOLCHAIN_MIPS64_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + CXXFLAGS="-I. $(TOOLCHAIN_MIPS64_FLAGS) -I$(TOOLCHAIN_MIPS64_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64 -frtti -fexceptions" \ + CFLAGS="-I. $(TOOLCHAIN_MIPS64_FLAGS) -I$(TOOLCHAIN_MIPS64_PLATFORM_HEADERS) -fpic -ffunction-sections -funwind-tables -fstack-protector -fno-strict-aliasing -finline-limit=64" \ + LDFLAGS="$(TOOLCHAIN_MIPS64_LINK)" \ + PATH="$(shell pwd)/$(TOOLCHAIN_MIPS64)/bin:$$PATH" + +# +# All the external tools we use in this Makefile +# + +AWK := awk +CD := cd +CMAKE := cmake +ECHO := echo +EGREP := egrep +GIT := git +LN := ln +MKDIR := mkdir +RM := rm +SORT := sort +TAR := tar +WGET := wget + +# +# End of user configurable options. +# + +.PHONY: \ + all \ + all-x86 \ + all-x86_64 \ + all-armeabi \ + all-armeabi-v7a \ + all-armeabi-v7a-hard \ + all-arm64-v8a \ + all-mips \ + all-mips64 \ + common \ + sources \ + toolchains \ + toolchain-x86 \ + toolchain-x86_64 \ + toolchain-armeabi \ + toolchain-armeabi-v7a \ + toolchain-armeabi-v7a-hard \ + toolchain-arm64-v8a \ + toolchain-mips \ + toolchain-mips64 \ + zlib \ + zlib-x86 \ + zlib-x86_64 \ + zlib-armeabi \ + zlib-armeabi-v7a \ + zlib-armeabi-v7a-hard \ + zlib-arm64-v8a \ + zlib-mips \ + zlib-mips64 \ + openssl \ + openssl-x86 \ + openssl-x86_64 \ + openssl-armeabi \ + openssl-armeabi-v7a \ + openssl-armeabi-v7a-hard \ + openssl-arm64-v8a \ + openssl-mips \ + openssl-mips64 \ + libwebsockets \ + libwebsockets-x86 \ + libwebsockets-x86_64 \ + libwebsockets-armeabi \ + libwebsockets-armeabi-v7a \ + libwebsockets-armeabi-v7a-hard \ + libwebsockets-arm64-v8a \ + libwebsockets-mips \ + libwebsockets-mips64 \ + clean-ndk \ + clean \ + dist-clean \ + clean-targets \ + clean-target-x86 \ + clean-target-x86_64 \ + clean-target-armeabi \ + clean-target-armeabi-v7a \ + clean-target-armeabi-v7a-hard \ + clean-target-arm64-v8a \ + clean-target-mips \ + clean-target-mips64 \ + clean-sources \ + clean-source-zlib \ + clean-source-openssl \ + clean-source-libwebsockets \ + clean-toolchains \ + clean-toolchain-x86 \ + clean-toolchain-x86_64 \ + clean-toolchain-armeabi \ + clean-toolchain-armeabi-v7a \ + clean-toolchain-armeabi-v7a-hard \ + clean-toolchain-arm64-v8a \ + clean-toolchain-mips \ + clean-toolchain-mips64 \ + list-targets + +# Default rule: build the libraries for all ABIs defined in NDK_APP_ABI then run ndk-build +all: $(NDK_APP_ABI) + $(NDK_ROOT)/ndk-build clean + $(NDK_ROOT)/ndk-build + +# Libraries may also be build per ABI +all-x86: $(TARGET_X86) +all-x86_64: $(TARGET_X86_64) +all-armeabi: $(TARGET_ARM) +all-armeabi-v7a: $(TARGET_ARM_V7A) +all-armeabi-v7a-hard: $(TARGET_ARM_V7A_HARD) +all-arm64-v8a: $(TARGET_ARM64_V8A) +all-mips: $(TARGET_MIPS) +all-mips64: $(TARGET_MIPS64) + +# Common rule all targets depend on +common: ../jniLibs + +# These rules are called from Android.mk when executing ndk-build +$(TARGET_X86): common zlib-x86 openssl-x86 libwebsockets-x86 +$(TARGET_X86_64): common zlib-x86_64 openssl-x86_64 libwebsockets-x86_64 +$(TARGET_ARM): common zlib-armeabi openssl-armeabi libwebsockets-armeabi +$(TARGET_ARM_V7A): common zlib-armeabi-v7a openssl-armeabi-v7a libwebsockets-armeabi-v7a +$(TARGET_ARM_V7A_HARD): common zlib-armeabi-v7a-hard openssl-armeabi-v7a-hard libwebsockets-armeabi-v7a-hard +$(TARGET_ARM64_V8A): common zlib-arm64-v8a openssl-arm64-v8a libwebsockets-arm64-v8a +$(TARGET_MIPS): common zlib-mips openssl-mips libwebsockets-mips +$(TARGET_MIPS64): common zlib-mips64 openssl-mips64 libwebsockets-mips64 + +# +# A rule to ensure ../jniLibs points to ../libs +# (ndk-build creates ../libs but Gradle looks for ../jniLibs) +# + +../libs: + $(MKDIR) ../libs + +../jniLibs: ../libs + $(CD) .. && $(LN) -s libs jniLibs + +# +# Some rules to download the sources +# + +sources: $(ZLIB_TGZ_SOURCE) $(OPENSSL_TGZ_SOURCE) $(LIBWEBSOCKETS_TGZ_SOURCE) + +$(ZLIB_TGZ_SOURCE): + $(WGET) -q $(ZLIB_TGZ_URL) + +$(OPENSSL_TGZ_SOURCE): + $(WGET) -q $(OPENSSL_TGZ_URL) + +$(LIBWEBSOCKETS_TGZ_SOURCE): + if [ -d $(LIBWEBSOCKETS_DIR) ]; then $(RM) -fr $(LIBWEBSOCKETS_DIR); fi + $(GIT) clone $(LIBWEBSOCKETS_GIT_URL) + $(TAR) caf $(LIBWEBSOCKETS_TGZ_SOURCE) $(LIBWEBSOCKETS_DIR) + $(RM) -fR $(LIBWEBSOCKETS_DIR) + +# +# Some rules to install the required toolchains +# + +toolchains: \ + toolchain-x86 \ + toolchain-x86_64 \ + toolchain-armeabi \ + toolchain-armeabi-v7a \ + toolchain-armeabi-v7a-hard \ + toolchain-arm64-v8a \ + toolchain-mips \ + toolchain-mips64 + +toolchain-x86: $(TOOLCHAIN_X86) +toolchain-x86_64: $(TOOLCHAIN_X86_64) +toolchain-armeabi: $(TOOLCHAIN_ARM) +toolchain-armeabi-v7a: $(TOOLCHAIN_ARM_V7A) +toolchain-armeabi-v7a-hard: $(TOOLCHAIN_ARM_V7A_HARD) +toolchain-arm64-v8a: $(TOOLCHAIN_ARM64_V8A) +toolchain-mips: $(TOOLCHAIN_MIPS) +toolchain-mips64: $(TOOLCHAIN_MIPS64) + +$(TOOLCHAIN_X86): + $(NDK_MAKE_TOOLCHAIN) \ + --platform=$(TOOLCHAIN_X86_PLATFORM) \ + --toolchain=$(TOOLCHAIN_X86_ARCH)-$(TOOLCHAIN_GCC_VERSION) \ + --install-dir=$(shell pwd)/$(TOOLCHAIN_X86) + +$(TOOLCHAIN_X86_64): + $(NDK_MAKE_TOOLCHAIN) \ + --platform=$(TOOLCHAIN_X86_64_PLATFORM) \ + --toolchain=$(TOOLCHAIN_X86_64_ARCH)-$(TOOLCHAIN_GCC_VERSION) \ + --install-dir=$(shell pwd)/$(TOOLCHAIN_X86_64) + +$(TOOLCHAIN_ARM): + $(NDK_MAKE_TOOLCHAIN) \ + --platform=$(TOOLCHAIN_ARM_PLATFORM) \ + --toolchain=$(TOOLCHAIN_ARM_ARCH)-$(TOOLCHAIN_GCC_VERSION) \ + --install-dir=$(shell pwd)/$(TOOLCHAIN_ARM) + +$(TOOLCHAIN_ARM_V7A): + $(NDK_MAKE_TOOLCHAIN) \ + --platform=$(TOOLCHAIN_ARM_V7A_PLATFORM) \ + --toolchain=$(TOOLCHAIN_ARM_V7A_ARCH)-$(TOOLCHAIN_GCC_VERSION) \ + --install-dir=$(shell pwd)/$(TOOLCHAIN_ARM_V7A) + +$(TOOLCHAIN_ARM_V7A_HARD): + $(NDK_MAKE_TOOLCHAIN) \ + --platform=$(TOOLCHAIN_ARM_V7A_HARD_PLATFORM) \ + --toolchain=$(TOOLCHAIN_ARM_V7A_HARD_ARCH)-$(TOOLCHAIN_GCC_VERSION) \ + --install-dir=$(shell pwd)/$(TOOLCHAIN_ARM_V7A_HARD) + +$(TOOLCHAIN_ARM64_V8A): + $(NDK_MAKE_TOOLCHAIN) \ + --platform=$(TOOLCHAIN_ARM64_V8A_PLATFORM) \ + --toolchain=$(TOOLCHAIN_ARM64_V8A_ARCH)-$(TOOLCHAIN_GCC_VERSION) \ + --install-dir=$(shell pwd)/$(TOOLCHAIN_ARM64_V8A) + +$(TOOLCHAIN_MIPS): + $(NDK_MAKE_TOOLCHAIN) \ + --platform=$(TOOLCHAIN_MIPS_PLATFORM) \ + --toolchain=$(TOOLCHAIN_MIPS_ARCH)-$(TOOLCHAIN_GCC_VERSION) \ + --install-dir=$(shell pwd)/$(TOOLCHAIN_MIPS) + +$(TOOLCHAIN_MIPS64): + $(NDK_MAKE_TOOLCHAIN) \ + --platform=$(TOOLCHAIN_MIPS64_PLATFORM) \ + --toolchain=$(TOOLCHAIN_MIPS64_ARCH)-$(TOOLCHAIN_GCC_VERSION) \ + --install-dir=$(shell pwd)/$(TOOLCHAIN_MIPS64) + +# +# Rules to build zlib +# + +zlib: \ + zlib-x86 \ + zlib-x86_64 \ + zlib-armeabi \ + zlib-armeabi-v7a \ + zlib-armeabi-v7a-hard \ + zlib-arm64-v8a \ + zlib-mips \ + zlib-mips64 + +zlib-x86: $(TARGET_X86)/lib/libz.a +zlib-x86_64: $(TARGET_X86_64)/lib/libz.a +zlib-armeabi: $(TARGET_ARM)/lib/libz.a +zlib-armeabi-v7a: $(TARGET_ARM_V7A)/lib/libz.a +zlib-armeabi-v7a-hard: $(TARGET_ARM_V7A_HARD)/lib/libz.a +zlib-arm64-v8a: $(TARGET_ARM64_V8A)/lib/libz.a +zlib-mips: $(TARGET_MIPS)/lib/libz.a +zlib-mips64: $(TARGET_MIPS64)/lib/libz.a + +# Extracting/configuring sources + +$(TARGET_X86)/src/$(ZLIB_DIR): $(ZLIB_TGZ_SOURCE) $(TOOLCHAIN_X86) + -$(MKDIR) -p $(TARGET_X86)/src + $(TAR) xf $(ZLIB_TGZ_SOURCE) -C $(TARGET_X86)/src + $(CD) $(TARGET_X86)/src/$(ZLIB_DIR) && $(TOOLCHAIN_X86_ENV) \ + ./configure --static --prefix=$(shell pwd)/$(TARGET_X86) + +$(TARGET_X86_64)/src/$(ZLIB_DIR): $(ZLIB_TGZ_SOURCE) $(TOOLCHAIN_X86_64) + -$(MKDIR) -p $(TARGET_X86_64)/src + $(TAR) xf $(ZLIB_TGZ_SOURCE) -C $(TARGET_X86_64)/src + $(CD) $(TARGET_X86_64)/src/$(ZLIB_DIR) && $(TOOLCHAIN_X86_64_ENV) \ + ./configure --static --prefix=$(shell pwd)/$(TARGET_X86_64) + +$(TARGET_ARM)/src/$(ZLIB_DIR): $(ZLIB_TGZ_SOURCE) $(TOOLCHAIN_ARM) + -$(MKDIR) -p $(TARGET_ARM)/src + $(TAR) xf $(ZLIB_TGZ_SOURCE) -C $(TARGET_ARM)/src + $(CD) $(TARGET_ARM)/src/$(ZLIB_DIR) && $(TOOLCHAIN_ARM_ENV) \ + ./configure --static --prefix=$(shell pwd)/$(TARGET_ARM) + +$(TARGET_ARM_V7A)/src/$(ZLIB_DIR): $(ZLIB_TGZ_SOURCE) $(TOOLCHAIN_ARM_V7A) + -$(MKDIR) -p $(TARGET_ARM_V7A)/src + $(TAR) xf $(ZLIB_TGZ_SOURCE) -C $(TARGET_ARM_V7A)/src + $(CD) $(TARGET_ARM_V7A)/src/$(ZLIB_DIR) && $(TOOLCHAIN_ARM_V7A_ENV) \ + ./configure --static --prefix=$(shell pwd)/$(TARGET_ARM_V7A) + +$(TARGET_ARM_V7A_HARD)/src/$(ZLIB_DIR): $(ZLIB_TGZ_SOURCE) $(TOOLCHAIN_ARM_V7A_HARD) + -$(MKDIR) -p $(TARGET_ARM_V7A_HARD)/src + $(TAR) xf $(ZLIB_TGZ_SOURCE) -C $(TARGET_ARM_V7A_HARD)/src + $(CD) $(TARGET_ARM_V7A_HARD)/src/$(ZLIB_DIR) && $(TOOLCHAIN_ARM_V7A_HARD_ENV) \ + ./configure --static --prefix=$(shell pwd)/$(TARGET_ARM_V7A_HARD) + +$(TARGET_ARM64_V8A)/src/$(ZLIB_DIR): $(ZLIB_TGZ_SOURCE) $(TOOLCHAIN_ARM64_V8A) + -$(MKDIR) -p $(TARGET_ARM64_V8A)/src + $(TAR) xf $(ZLIB_TGZ_SOURCE) -C $(TARGET_ARM64_V8A)/src + $(CD) $(TARGET_ARM64_V8A)/src/$(ZLIB_DIR) && $(TOOLCHAIN_ARM64_V8A_ENV) \ + ./configure --static --prefix=$(shell pwd)/$(TARGET_ARM64_V8A) + +$(TARGET_MIPS)/src/$(ZLIB_DIR): $(ZLIB_TGZ_SOURCE) $(TOOLCHAIN_MIPS) + -$(MKDIR) -p $(TARGET_MIPS)/src + $(TAR) xf $(ZLIB_TGZ_SOURCE) -C $(TARGET_MIPS)/src + $(CD) $(TARGET_MIPS)/src/$(ZLIB_DIR) && $(TOOLCHAIN_MIPS_ENV) \ + ./configure --static --prefix=$(shell pwd)/$(TARGET_MIPS) + +$(TARGET_MIPS64)/src/$(ZLIB_DIR): $(ZLIB_TGZ_SOURCE) $(TOOLCHAIN_MIPS64) + -$(MKDIR) -p $(TARGET_MIPS64)/src + $(TAR) xf $(ZLIB_TGZ_SOURCE) -C $(TARGET_MIPS64)/src + $(CD) $(TARGET_MIPS64)/src/$(ZLIB_DIR) && $(TOOLCHAIN_MIPS64_ENV) \ + ./configure --static --prefix=$(shell pwd)/$(TARGET_MIPS64) + +# Build/install library + +$(TARGET_X86)/lib/libz.a: $(TARGET_X86)/src/$(ZLIB_DIR) + $(CD) $(TARGET_X86)/src/$(ZLIB_DIR) && $(TOOLCHAIN_X86_ENV) $(MAKE) libz.a + $(CD) $(TARGET_X86)/src/$(ZLIB_DIR) && $(TOOLCHAIN_X86_ENV) $(MAKE) install + +$(TARGET_X86_64)/lib/libz.a: $(TARGET_X86_64)/src/$(ZLIB_DIR) + $(CD) $(TARGET_X86_64)/src/$(ZLIB_DIR) && $(TOOLCHAIN_X86_64_ENV) $(MAKE) libz.a + $(CD) $(TARGET_X86_64)/src/$(ZLIB_DIR) && $(TOOLCHAIN_X86_64_ENV) $(MAKE) install + +$(TARGET_ARM)/lib/libz.a: $(TARGET_ARM)/src/$(ZLIB_DIR) + $(CD) $(TARGET_ARM)/src/$(ZLIB_DIR) && $(TOOLCHAIN_ARM_ENV) $(MAKE) libz.a + $(CD) $(TARGET_ARM)/src/$(ZLIB_DIR) && $(TOOLCHAIN_ARM_ENV) $(MAKE) install + +$(TARGET_ARM_V7A)/lib/libz.a: $(TARGET_ARM_V7A)/src/$(ZLIB_DIR) + $(CD) $(TARGET_ARM_V7A)/src/$(ZLIB_DIR) && $(TOOLCHAIN_ARM_V7A_ENV) $(MAKE) libz.a + $(CD) $(TARGET_ARM_V7A)/src/$(ZLIB_DIR) && $(TOOLCHAIN_ARM_V7A_ENV) $(MAKE) install + +$(TARGET_ARM_V7A_HARD)/lib/libz.a: $(TARGET_ARM_V7A_HARD)/src/$(ZLIB_DIR) + $(CD) $(TARGET_ARM_V7A_HARD)/src/$(ZLIB_DIR) && $(TOOLCHAIN_ARM_V7A_HARD_ENV) $(MAKE) libz.a + $(CD) $(TARGET_ARM_V7A_HARD)/src/$(ZLIB_DIR) && $(TOOLCHAIN_ARM_V7A_HARD_ENV) $(MAKE) install + +$(TARGET_ARM64_V8A)/lib/libz.a: $(TARGET_ARM64_V8A)/src/$(ZLIB_DIR) + $(CD) $(TARGET_ARM64_V8A)/src/$(ZLIB_DIR) && $(TOOLCHAIN_ARM64_V8A_ENV) $(MAKE) libz.a + $(CD) $(TARGET_ARM64_V8A)/src/$(ZLIB_DIR) && $(TOOLCHAIN_ARM64_V8A_ENV) $(MAKE) install + +$(TARGET_MIPS)/lib/libz.a: $(TARGET_MIPS)/src/$(ZLIB_DIR) + $(CD) $(TARGET_MIPS)/src/$(ZLIB_DIR) && $(TOOLCHAIN_MIPS_ENV) $(MAKE) libz.a + $(CD) $(TARGET_MIPS)/src/$(ZLIB_DIR) && $(TOOLCHAIN_MIPS_ENV) $(MAKE) install + +$(TARGET_MIPS64)/lib/libz.a: $(TARGET_MIPS64)/src/$(ZLIB_DIR) + $(CD) $(TARGET_MIPS64)/src/$(ZLIB_DIR) && $(TOOLCHAIN_MIPS64_ENV) $(MAKE) libz.a + $(CD) $(TARGET_MIPS64)/src/$(ZLIB_DIR) && $(TOOLCHAIN_MIPS64_ENV) $(MAKE) install + +# +# Rules to build OpenSSL +# + +openssl: \ + openssl-x86 \ + openssl-x86_64 \ + openssl-armeabi \ + openssl-armeabi-v7a \ + openssl-armeabi-v7a-hard \ + openssl-arm64-v8a \ + openssl-mips \ + openssl-mips64 + +openssl-x86: $(TARGET_X86)/lib/libssl.a +openssl-x86_64: $(TARGET_X86_64)/lib/libssl.a +openssl-armeabi: $(TARGET_ARM)/lib/libssl.a +openssl-armeabi-v7a: $(TARGET_ARM_V7A)/lib/libssl.a +openssl-armeabi-v7a-hard: $(TARGET_ARM_V7A_HARD)/lib/libssl.a +openssl-arm64-v8a: $(TARGET_ARM64_V8A)/lib/libssl.a +openssl-mips: $(TARGET_MIPS)/lib/libssl.a +openssl-mips64: $(TARGET_MIPS64)/lib/libssl.a + +# Extracting/configuring sources + +$(TARGET_X86)/src/$(OPENSSL_DIR): $(OPENSSL_TGZ_SOURCE) $(TOOLCHAIN_X86) + -$(MKDIR) -p $(TARGET_X86)/src + $(TAR) xf $(OPENSSL_TGZ_SOURCE) -C $(TARGET_X86)/src + $(CD) $(TARGET_X86)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_X86_ENV) \ + ./Configure $(TARGET_X86_OPENSSL_CONFIG_TARGET) \ + --prefix=$(shell pwd)/$(TARGET_X86) \ + --openssldir=$(shell pwd)/$(TARGET_X86)/lib/ssl \ + $(TARGET_X86_OPENSSL_CONFIG) + +$(TARGET_X86_64)/src/$(OPENSSL_DIR): $(OPENSSL_TGZ_SOURCE) $(TOOLCHAIN_X86_64) + -$(MKDIR) -p $(TARGET_X86_64)/src + $(TAR) xf $(OPENSSL_TGZ_SOURCE) -C $(TARGET_X86_64)/src + $(CD) $(TARGET_X86_64)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_X86_64_ENV) \ + ./Configure $(TARGET_X86_64_OPENSSL_CONFIG_TARGET) \ + --prefix=$(shell pwd)/$(TARGET_X86_64) \ + --openssldir=$(shell pwd)/$(TARGET_X86_64)/lib/ssl \ + $(TARGET_X86_64_OPENSSL_CONFIG) + +$(TARGET_ARM)/src/$(OPENSSL_DIR): $(OPENSSL_TGZ_SOURCE) $(TOOLCHAIN_ARM) + -$(MKDIR) -p $(TARGET_ARM)/src + $(TAR) xf $(OPENSSL_TGZ_SOURCE) -C $(TARGET_ARM)/src + $(CD) $(TARGET_ARM)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM_ENV) \ + ./Configure $(TARGET_ARM_OPENSSL_CONFIG_TARGET) \ + --prefix=$(shell pwd)/$(TARGET_ARM) \ + --openssldir=$(shell pwd)/$(TARGET_ARM)/lib/ssl \ + $(TARGET_ARM_OPENSSL_CONFIG) + +$(TARGET_ARM_V7A)/src/$(OPENSSL_DIR): $(OPENSSL_TGZ_SOURCE) $(TOOLCHAIN_ARM_V7A) + -$(MKDIR) -p $(TARGET_ARM_V7A)/src + $(TAR) xf $(OPENSSL_TGZ_SOURCE) -C $(TARGET_ARM_V7A)/src + $(CD) $(TARGET_ARM_V7A)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM_V7A_ENV) \ + ./Configure $(TARGET_ARM_V7A_OPENSSL_CONFIG_TARGET) \ + --prefix=$(shell pwd)/$(TARGET_ARM_V7A) \ + --openssldir=$(shell pwd)/$(TARGET_ARM_V7A)/lib/ssl \ + $(TARGET_ARM_V7A_OPENSSL_CONFIG) + +$(TARGET_ARM_V7A_HARD)/src/$(OPENSSL_DIR): $(OPENSSL_TGZ_SOURCE) $(TOOLCHAIN_ARM_V7A_HARD) + -$(MKDIR) -p $(TARGET_ARM_V7A_HARD)/src + $(TAR) xf $(OPENSSL_TGZ_SOURCE) -C $(TARGET_ARM_V7A_HARD)/src + $(CD) $(TARGET_ARM_V7A_HARD)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM_V7A_HARD_ENV) \ + ./Configure $(TARGET_ARM_V7A_HARD_OPENSSL_CONFIG_TARGET) \ + --prefix=$(shell pwd)/$(TARGET_ARM_V7A_HARD) \ + --openssldir=$(shell pwd)/$(TARGET_ARM_V7A_HARD)/lib/ssl \ + $(TARGET_ARM_V7A_HARD_OPENSSL_CONFIG) + +$(TARGET_ARM64_V8A)/src/$(OPENSSL_DIR): $(OPENSSL_TGZ_SOURCE) $(TOOLCHAIN_ARM64_V8A) + -$(MKDIR) -p $(TARGET_ARM64_V8A)/src + $(TAR) xf $(OPENSSL_TGZ_SOURCE) -C $(TARGET_ARM64_V8A)/src + $(CD) $(TARGET_ARM64_V8A)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM64_V8A_ENV) \ + ./Configure $(TARGET_ARM64_V8A_OPENSSL_CONFIG_TARGET) \ + --prefix=$(shell pwd)/$(TARGET_ARM64_V8A) \ + --openssldir=$(shell pwd)/$(TARGET_ARM64_V8A)/lib/ssl \ + $(TARGET_ARM64_V8A_OPENSSL_CONFIG) + +$(TARGET_MIPS)/src/$(OPENSSL_DIR): $(OPENSSL_TGZ_SOURCE) $(TOOLCHAIN_MIPS) + -$(MKDIR) -p $(TARGET_MIPS)/src + $(TAR) xf $(OPENSSL_TGZ_SOURCE) -C $(TARGET_MIPS)/src + $(CD) $(TARGET_MIPS)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_MIPS_ENV) \ + ./Configure $(TARGET_MIPS_OPENSSL_CONFIG_TARGET) \ + --prefix=$(shell pwd)/$(TARGET_MIPS) \ + --openssldir=$(shell pwd)/$(TARGET_MIPS)/lib/ssl \ + $(TARGET_MIPS_OPENSSL_CONFIG) + +$(TARGET_MIPS64)/src/$(OPENSSL_DIR): $(OPENSSL_TGZ_SOURCE) $(TOOLCHAIN_MIPS64) + -$(MKDIR) -p $(TARGET_MIPS64)/src + $(TAR) xf $(OPENSSL_TGZ_SOURCE) -C $(TARGET_MIPS64)/src + $(CD) $(TARGET_MIPS64)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_MIPS64_ENV) \ + ./Configure $(TARGET_MIPS64_OPENSSL_CONFIG_TARGET) \ + --prefix=$(shell pwd)/$(TARGET_MIPS64) \ + --openssldir=$(shell pwd)/$(TARGET_MIPS64)/lib/ssl \ + $(TARGET_MIPS64_OPENSSL_CONFIG) + +# Build/install library + +$(TARGET_X86)/lib/libssl.a: $(TARGET_X86)/src/$(OPENSSL_DIR) + $(CD) $(TARGET_X86)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_X86_ENV) $(MAKE) depend + $(CD) $(TARGET_X86)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_X86_ENV) $(MAKE) build_libs + $(CD) $(TARGET_X86)/src/$(OPENSSL_DIR) && $(ECHO) '#!/bin/sh\n\nfalse\n' > apps/openssl + $(CD) $(TARGET_X86)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_X86_ENV) $(MAKE) install_sw + +$(TARGET_X86_64)/lib/libssl.a: $(TARGET_X86_64)/src/$(OPENSSL_DIR) + $(CD) $(TARGET_X86_64)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_X86_64_ENV) $(MAKE) depend + $(CD) $(TARGET_X86_64)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_X86_64_ENV) $(MAKE) build_libs + $(CD) $(TARGET_X86_64)/src/$(OPENSSL_DIR) && $(ECHO) '#!/bin/sh\n\nfalse\n' > apps/openssl + $(CD) $(TARGET_X86_64)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_X86_64_ENV) $(MAKE) install_sw + +$(TARGET_ARM)/lib/libssl.a: $(TARGET_ARM)/src/$(OPENSSL_DIR) + $(CD) $(TARGET_ARM)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM_ENV) $(MAKE) depend + $(CD) $(TARGET_ARM)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM_ENV) $(MAKE) build_libs + $(CD) $(TARGET_ARM)/src/$(OPENSSL_DIR) && $(ECHO) '#!/bin/sh\n\nfalse\n' > apps/openssl + $(CD) $(TARGET_ARM)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM_ENV) $(MAKE) install_sw + +$(TARGET_ARM_V7A)/lib/libssl.a: $(TARGET_ARM_V7A)/src/$(OPENSSL_DIR) + $(CD) $(TARGET_ARM_V7A)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM_V7A_ENV) $(MAKE) depend + $(CD) $(TARGET_ARM_V7A)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM_V7A_ENV) $(MAKE) build_libs + $(CD) $(TARGET_ARM_V7A)/src/$(OPENSSL_DIR) && $(ECHO) '#!/bin/sh\n\nfalse\n' > apps/openssl + $(CD) $(TARGET_ARM_V7A)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM_V7A_ENV) $(MAKE) install_sw + +$(TARGET_ARM_V7A_HARD)/lib/libssl.a: $(TARGET_ARM_V7A_HARD)/src/$(OPENSSL_DIR) + $(CD) $(TARGET_ARM_V7A_HARD)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM_V7A_HARD_ENV) $(MAKE) depend + $(CD) $(TARGET_ARM_V7A_HARD)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM_V7A_HARD_ENV) $(MAKE) build_libs + $(CD) $(TARGET_ARM_V7A_HARD)/src/$(OPENSSL_DIR) && $(ECHO) '#!/bin/sh\n\nfalse\n' > apps/openssl + $(CD) $(TARGET_ARM_V7A_HARD)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM_V7A_HARD_ENV) $(MAKE) install_sw + +$(TARGET_ARM64_V8A)/lib/libssl.a: $(TARGET_ARM64_V8A)/src/$(OPENSSL_DIR) + $(CD) $(TARGET_ARM64_V8A)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM64_V8A_ENV) $(MAKE) depend + $(CD) $(TARGET_ARM64_V8A)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM64_V8A_ENV) $(MAKE) build_libs + $(CD) $(TARGET_ARM64_V8A)/src/$(OPENSSL_DIR) && $(ECHO) '#!/bin/sh\n\nfalse\n' > apps/openssl + $(CD) $(TARGET_ARM64_V8A)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_ARM64_V8A_ENV) $(MAKE) install_sw + +$(TARGET_MIPS)/lib/libssl.a: $(TARGET_MIPS)/src/$(OPENSSL_DIR) + $(CD) $(TARGET_MIPS)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_MIPS_ENV) $(MAKE) depend + $(CD) $(TARGET_MIPS)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_MIPS_ENV) $(MAKE) build_libs + $(CD) $(TARGET_MIPS)/src/$(OPENSSL_DIR) && $(ECHO) '#!/bin/sh\n\nfalse\n' > apps/openssl + $(CD) $(TARGET_MIPS)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_MIPS_ENV) $(MAKE) install_sw + +$(TARGET_MIPS64)/lib/libssl.a: $(TARGET_MIPS64)/src/$(OPENSSL_DIR) + $(CD) $(TARGET_MIPS64)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_MIPS64_ENV) $(MAKE) depend + $(CD) $(TARGET_MIPS64)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_MIPS64_ENV) $(MAKE) build_libs + $(CD) $(TARGET_MIPS64)/src/$(OPENSSL_DIR) && $(ECHO) '#!/bin/sh\n\nfalse\n' > apps/openssl + $(CD) $(TARGET_MIPS64)/src/$(OPENSSL_DIR) && $(TOOLCHAIN_MIPS64_ENV) $(MAKE) install_sw + +# +# Rules to build libwebsockets +# + +libwebsockets: \ + libwebsockets-x86 \ + libwebsockets-x86_64 \ + libwebsockets-armeabi \ + libwebsockets-armeabi-v7a \ + libwebsockets-armeabi-v7a-hard \ + libwebsockets-arm64-v8a \ + libwebsockets-mips \ + libwebsockets-mips64 \ + +libwebsockets-x86: $(TARGET_X86)/lib/libwebsockets.a +libwebsockets-x86_64: $(TARGET_X86_64)/lib/libwebsockets.a +libwebsockets-armeabi: $(TARGET_ARM)/lib/libwebsockets.a +libwebsockets-armeabi-v7a: $(TARGET_ARM_V7A)/lib/libwebsockets.a +libwebsockets-armeabi-v7a-hard: $(TARGET_ARM_V7A_HARD)/lib/libwebsockets.a +libwebsockets-arm64-v8a: $(TARGET_ARM64_V8A)/lib/libwebsockets.a +libwebsockets-mips: $(TARGET_MIPS)/lib/libwebsockets.a +libwebsockets-mips64: $(TARGET_MIPS64)/lib/libwebsockets.a + +# Extracting/configuring sources + +$(TARGET_X86)/src/$(LIBWEBSOCKETS_DIR): $(LIBWEBSOCKETS_TGZ_SOURCE) $(TOOLCHAIN_X86) $(TARGET_X86)/lib/libssl.a $(TARGET_X86)/lib/libz.a + -$(MKDIR) -p $(TARGET_X86)/src + $(TAR) xf $(LIBWEBSOCKETS_TGZ_SOURCE) -C $(TARGET_X86)/src + -$(MKDIR) -p $(TARGET_X86)/src/$(LIBWEBSOCKETS_DIR)/build + $(CD) $(TARGET_X86)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_X86_ENV) \ + $(CMAKE) $(TARGET_X86_LWS_OPTIONS) \ + -DCMAKE_INSTALL_PREFIX=$(shell pwd)/$(TARGET_X86) \ + -DLWS_OPENSSL_LIBRARIES="$(shell pwd)/$(TARGET_X86)/lib/libssl.a;$(shell pwd)/$(TARGET_X86)/lib/libcrypto.a" \ + -DLWS_OPENSSL_INCLUDE_DIRS="$(shell pwd)/$(TARGET_X86)/include" \ + .. + +$(TARGET_X86_64)/src/$(LIBWEBSOCKETS_DIR): $(LIBWEBSOCKETS_TGZ_SOURCE) $(TOOLCHAIN_X86_64) $(TARGET_X86_64)/lib/libssl.a $(TARGET_X86_64)/lib/libz.a + -$(MKDIR) -p $(TARGET_X86_64)/src + $(TAR) xf $(LIBWEBSOCKETS_TGZ_SOURCE) -C $(TARGET_X86_64)/src + -$(MKDIR) -p $(TARGET_X86_64)/src/$(LIBWEBSOCKETS_DIR)/build + $(CD) $(TARGET_X86_64)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_X86_64_ENV) \ + $(CMAKE) $(TARGET_X86_64_LWS_OPTIONS) \ + -DCMAKE_INSTALL_PREFIX=$(shell pwd)/$(TARGET_X86_64) \ + -DLWS_OPENSSL_LIBRARIES="$(shell pwd)/$(TARGET_X86_64)/lib/libssl.a;$(shell pwd)/$(TARGET_X86_64)/lib/libcrypto.a" \ + -DLWS_OPENSSL_INCLUDE_DIRS="$(shell pwd)/$(TARGET_X86_64)/include" \ + .. + +$(TARGET_ARM)/src/$(LIBWEBSOCKETS_DIR): $(LIBWEBSOCKETS_TGZ_SOURCE) $(TOOLCHAIN_ARM) $(TARGET_ARM)/lib/libssl.a $(TARGET_ARM)/lib/libz.a + -$(MKDIR) -p $(TARGET_ARM)/src + $(TAR) xf $(LIBWEBSOCKETS_TGZ_SOURCE) -C $(TARGET_ARM)/src + -$(MKDIR) -p $(TARGET_ARM)/src/$(LIBWEBSOCKETS_DIR)/build + $(CD) $(TARGET_ARM)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_ARM_ENV) \ + $(CMAKE) $(TARGET_ARM_LWS_OPTIONS) \ + -DCMAKE_INSTALL_PREFIX=$(shell pwd)/$(TARGET_ARM) \ + -DLWS_OPENSSL_LIBRARIES="$(shell pwd)/$(TARGET_ARM)/lib/libssl.a;$(shell pwd)/$(TARGET_ARM)/lib/libcrypto.a" \ + -DLWS_OPENSSL_INCLUDE_DIRS="$(shell pwd)/$(TARGET_ARM)/include" \ + .. + +$(TARGET_ARM_V7A)/src/$(LIBWEBSOCKETS_DIR): $(LIBWEBSOCKETS_TGZ_SOURCE) $(TOOLCHAIN_ARM_V7A) $(TARGET_ARM_V7A)/lib/libssl.a $(TARGET_ARM_V7A)/lib/libz.a + -$(MKDIR) -p $(TARGET_ARM_V7A)/src + $(TAR) xf $(LIBWEBSOCKETS_TGZ_SOURCE) -C $(TARGET_ARM_V7A)/src + -$(MKDIR) -p $(TARGET_ARM_V7A)/src/$(LIBWEBSOCKETS_DIR)/build + $(CD) $(TARGET_ARM_V7A)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_ARM_V7A_ENV) \ + $(CMAKE) $(TARGET_ARM_V7A_LWS_OPTIONS) \ + -DCMAKE_INSTALL_PREFIX=$(shell pwd)/$(TARGET_ARM_V7A) \ + -DLWS_OPENSSL_LIBRARIES="$(shell pwd)/$(TARGET_ARM_V7A)/lib/libssl.a;$(shell pwd)/$(TARGET_ARM_V7A)/lib/libcrypto.a" \ + -DLWS_OPENSSL_INCLUDE_DIRS="$(shell pwd)/$(TARGET_ARM_V7A)/include" \ + .. + +$(TARGET_ARM_V7A_HARD)/src/$(LIBWEBSOCKETS_DIR): $(LIBWEBSOCKETS_TGZ_SOURCE) $(TOOLCHAIN_ARM_V7A_HARD) $(TARGET_ARM_V7A_HARD)/lib/libssl.a $(TARGET_ARM_V7A_HARD)/lib/libz.a + -$(MKDIR) -p $(TARGET_ARM_V7A_HARD)/src + $(TAR) xf $(LIBWEBSOCKETS_TGZ_SOURCE) -C $(TARGET_ARM_V7A_HARD)/src + -$(MKDIR) -p $(TARGET_ARM_V7A_HARD)/src/$(LIBWEBSOCKETS_DIR)/build + $(CD) $(TARGET_ARM_V7A_HARD)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_ARM_V7A_HARD_ENV) \ + $(CMAKE) $(TARGET_ARM_V7A_HARD_LWS_OPTIONS) \ + -DCMAKE_INSTALL_PREFIX=$(shell pwd)/$(TARGET_ARM_V7A_HARD) \ + -DLWS_OPENSSL_LIBRARIES="$(shell pwd)/$(TARGET_ARM_V7A_HARD)/lib/libssl.a;$(shell pwd)/$(TARGET_ARM_V7A_HARD)/lib/libcrypto.a" \ + -DLWS_OPENSSL_INCLUDE_DIRS="$(shell pwd)/$(TARGET_ARM_V7A_HARD)/include" \ + .. + +$(TARGET_ARM64_V8A)/src/$(LIBWEBSOCKETS_DIR): $(LIBWEBSOCKETS_TGZ_SOURCE) $(TOOLCHAIN_ARM64_V8A) $(TARGET_ARM64_V8A)/lib/libssl.a $(TARGET_ARM64_V8A)/lib/libz.a + -$(MKDIR) -p $(TARGET_ARM64_V8A)/src + $(TAR) xf $(LIBWEBSOCKETS_TGZ_SOURCE) -C $(TARGET_ARM64_V8A)/src + -$(MKDIR) -p $(TARGET_ARM64_V8A)/src/$(LIBWEBSOCKETS_DIR)/build + $(CD) $(TARGET_ARM64_V8A)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_ARM64_V8A_ENV) \ + $(CMAKE) $(TARGET_ARM64_V8A_LWS_OPTIONS) \ + -DCMAKE_INSTALL_PREFIX=$(shell pwd)/$(TARGET_ARM64_V8A) \ + -DLWS_OPENSSL_LIBRARIES="$(shell pwd)/$(TARGET_ARM64_V8A)/lib/libssl.a;$(shell pwd)/$(TARGET_ARM64_V8A)/lib/libcrypto.a" \ + -DLWS_OPENSSL_INCLUDE_DIRS="$(shell pwd)/$(TARGET_ARM64_V8A)/include" \ + .. + +$(TARGET_MIPS)/src/$(LIBWEBSOCKETS_DIR): $(LIBWEBSOCKETS_TGZ_SOURCE) $(TOOLCHAIN_MIPS) $(TARGET_MIPS)/lib/libssl.a $(TARGET_MIPS)/lib/libz.a + -$(MKDIR) -p $(TARGET_MIPS)/src + $(TAR) xf $(LIBWEBSOCKETS_TGZ_SOURCE) -C $(TARGET_MIPS)/src + -$(MKDIR) -p $(TARGET_MIPS)/src/$(LIBWEBSOCKETS_DIR)/build + $(CD) $(TARGET_MIPS)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_MIPS_ENV) \ + $(CMAKE) $(TARGET_MIPS_LWS_OPTIONS) \ + -DCMAKE_INSTALL_PREFIX=$(shell pwd)/$(TARGET_MIPS) \ + -DLWS_OPENSSL_LIBRARIES="$(shell pwd)/$(TARGET_MIPS)/lib/libssl.a;$(shell pwd)/$(TARGET_MIPS)/lib/libcrypto.a" \ + -DLWS_OPENSSL_INCLUDE_DIRS="$(shell pwd)/$(TARGET_MIPS)/include" \ + .. + +$(TARGET_MIPS64)/src/$(LIBWEBSOCKETS_DIR): $(LIBWEBSOCKETS_TGZ_SOURCE) $(TOOLCHAIN_MIPS64) $(TARGET_MIPS64)/lib/libssl.a $(TARGET_MIPS64)/lib/libz.a + -$(MKDIR) -p $(TARGET_MIPS64)/src + $(TAR) xf $(LIBWEBSOCKETS_TGZ_SOURCE) -C $(TARGET_MIPS64)/src + -$(MKDIR) -p $(TARGET_MIPS64)/src/$(LIBWEBSOCKETS_DIR)/build + $(CD) $(TARGET_MIPS64)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_MIPS64_ENV) \ + $(CMAKE) $(TARGET_MIPS64_LWS_OPTIONS) \ + -DCMAKE_INSTALL_PREFIX=$(shell pwd)/$(TARGET_MIPS64) \ + -DLWS_OPENSSL_LIBRARIES="$(shell pwd)/$(TARGET_MIPS64)/lib/libssl.a;$(shell pwd)/$(TARGET_MIPS64)/lib/libcrypto.a" \ + -DLWS_OPENSSL_INCLUDE_DIRS="$(shell pwd)/$(TARGET_MIPS64)/include" \ + .. + +# Build/install library + +$(TARGET_X86)/lib/libwebsockets.a: $(TARGET_X86)/src/$(LIBWEBSOCKETS_DIR) + $(CD) $(TARGET_X86)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_X86_ENV) $(MAKE) + $(CD) $(TARGET_X86)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_X86_ENV) $(MAKE) install + +$(TARGET_X86_64)/lib/libwebsockets.a: $(TARGET_X86_64)/src/$(LIBWEBSOCKETS_DIR) + $(CD) $(TARGET_X86_64)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_X86_64_ENV) $(MAKE) + $(CD) $(TARGET_X86_64)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_X86_64_ENV) $(MAKE) install + +$(TARGET_ARM)/lib/libwebsockets.a: $(TARGET_ARM)/src/$(LIBWEBSOCKETS_DIR) + $(CD) $(TARGET_ARM)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_ARM_ENV) $(MAKE) + $(CD) $(TARGET_ARM)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_ARM_ENV) $(MAKE) install + +$(TARGET_ARM_V7A)/lib/libwebsockets.a: $(TARGET_ARM_V7A)/src/$(LIBWEBSOCKETS_DIR) + $(CD) $(TARGET_ARM_V7A)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_ARM_V7A_ENV) $(MAKE) + $(CD) $(TARGET_ARM_V7A)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_ARM_V7A_ENV) $(MAKE) install + +$(TARGET_ARM_V7A_HARD)/lib/libwebsockets.a: $(TARGET_ARM_V7A_HARD)/src/$(LIBWEBSOCKETS_DIR) + $(CD) $(TARGET_ARM_V7A_HARD)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_ARM_V7A_HARD_ENV) $(MAKE) + $(CD) $(TARGET_ARM_V7A_HARD)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_ARM_V7A_HARD_ENV) $(MAKE) install + +$(TARGET_ARM64_V8A)/lib/libwebsockets.a: $(TARGET_ARM64_V8A)/src/$(LIBWEBSOCKETS_DIR) + $(CD) $(TARGET_ARM64_V8A)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_ARM64_V8A_ENV) $(MAKE) + $(CD) $(TARGET_ARM64_V8A)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_ARM64_V8A_ENV) $(MAKE) install + +$(TARGET_MIPS)/lib/libwebsockets.a: $(TARGET_MIPS)/src/$(LIBWEBSOCKETS_DIR) + $(CD) $(TARGET_MIPS)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_MIPS_ENV) $(MAKE) + $(CD) $(TARGET_MIPS)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_MIPS_ENV) $(MAKE) install + +$(TARGET_MIPS64)/lib/libwebsockets.a: $(TARGET_MIPS64)/src/$(LIBWEBSOCKETS_DIR) + $(CD) $(TARGET_MIPS64)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_MIPS64_ENV) $(MAKE) + $(CD) $(TARGET_MIPS64)/src/$(LIBWEBSOCKETS_DIR)/build && $(TOOLCHAIN_MIPS64_ENV) $(MAKE) install + +# +# Some rules for housekeeping +# + +clean-ndk: + $(NDK_ROOT)/ndk-build clean + +clean: clean-targets clean-toolchains + +dist-clean: clean clean-sources + +clean-targets: \ + clean-target-x86 \ + clean-target-x86_64 \ + clean-target-armeabi \ + clean-target-armeabi-v7a \ + clean-target-armeabi-v7a-hard \ + clean-target-arm64-v8a \ + clean-target-mips \ + clean-target-mips64 + +clean-target-x86: + -$(RM) -fr $(TARGET_X86) + +clean-target-x86_64: + -$(RM) -fr $(TARGET_X86_64) + +clean-target-armeabi: + -$(RM) -fr $(TARGET_ARM) + +clean-target-armeabi-v7a: + -$(RM) -fr $(TARGET_ARM_V7A) + +clean-target-armeabi-v7a-hard: + -$(RM) -fr $(TARGET_ARM_V7A_HARD) + +clean-target-arm64-v8a: + -$(RM) -fr $(TARGET_ARM64_V8A) + +clean-target-mips: + -$(RM) -fr $(TARGET_MIPS) + +clean-target-mips64: + -$(RM) -fr $(TARGET_MIPS64) + +clean-sources: \ + clean-source-zlib \ + clean-source-openssl \ + clean-source-libwebsockets + +clean-source-zlib: + -$(RM) $(ZLIB_TGZ_SOURCE) + +clean-source-openssl: + -$(RM) $(OPENSSL_TGZ_SOURCE) + +clean-source-libwebsockets: + -$(RM) $(LIBWEBSOCKETS_TGZ_SOURCE) + +clean-toolchains: \ + clean-toolchain-x86 \ + clean-toolchain-x86_64 \ + clean-toolchain-armeabi \ + clean-toolchain-armeabi-v7a \ + clean-toolchain-armeabi-v7a-hard \ + clean-toolchain-arm64-v8a \ + clean-toolchain-mips \ + clean-toolchain-mips64 + -$(RM) -fr toolchains + +clean-toolchain-x86: + -$(RM) -fr $(TOOLCHAIN_X86) + +clean-toolchain-x86_64: + -$(RM) -fr $(TOOLCHAIN_X86_64) + +clean-toolchain-armeabi: + -$(RM) -fr $(TOOLCHAIN_ARM) + +clean-toolchain-armeabi-v7a: + -$(RM) -fr $(TOOLCHAIN_ARM_V7A) + +clean-toolchain-armeabi-v7a-hard: + -$(RM) -fr $(TOOLCHAIN_ARM_V7A_HARD) + +clean-toolchain-arm64-v8a: + -$(RM) -fr $(TOOLCHAIN_ARM64_V8A) + +clean-toolchain-mips: + -$(RM) -fr $(TOOLCHAIN_MIPS) + +clean-toolchain-mips64: + -$(RM) -fr $(TOOLCHAIN_MIPS64) + +# 'make list-targets' prints a list of all targets. +# Thanks to: http://stackoverflow.com/questions/4219255/how-do-you-get-the-list-of-targets-in-a-makefile +# Modified to allow us to include files in this Makefile. +list-targets: MAKE_NO_INCLUDES := 1 +export MAKE_NO_INCLUDES +list-targets: + @$(MAKE) -s list-targets-no-includes +list-targets-no-includes: + @$(MAKE) -pRrq -f $(lastword $(MAKEFILE_LIST)) : 2>/dev/null | $(AWK) -v RS= -F: '/^# File/,/^# Finished Make data base/ {if ($$1 !~ "^[#.]") {print $$1}}' | $(SORT) | $(EGREP) -v -e '^[^[:alnum:]]' -e '^$@$$' + diff --git a/test-server/android/app/src/main/libs/placeholder b/test-server/android/app/src/main/libs/placeholder new file mode 100644 index 00000000..e69de29b diff --git a/test-server/android/app/src/main/res/drawable/warmcat.png b/test-server/android/app/src/main/res/drawable/warmcat.png new file mode 100644 index 00000000..2060a10c Binary files /dev/null and b/test-server/android/app/src/main/res/drawable/warmcat.png differ diff --git a/test-server/android/app/src/main/res/layout/activity_main.xml b/test-server/android/app/src/main/res/layout/activity_main.xml new file mode 100644 index 00000000..a852e979 --- /dev/null +++ b/test-server/android/app/src/main/res/layout/activity_main.xml @@ -0,0 +1,81 @@ + + + + + + + + + + + +