diff options
author | Jonathan Buchanan <jonathan.russ.buchanan@gmail.com> | 2021-06-30 22:37:04 -0400 |
---|---|---|
committer | Jonathan Buchanan <jonathan.russ.buchanan@gmail.com> | 2021-06-30 22:37:04 -0400 |
commit | bcb61657231354efe4d9034367ec5a80ca480345 (patch) | |
tree | 3923eb999a0ae306c9471bc7dabebcf209f8f199 | |
parent | a7e92ab02af0d560de29e5ddf29a48e0a13bd85a (diff) | |
download | taler-ios-bcb61657231354efe4d9034367ec5a80ca480345.tar.gz taler-ios-bcb61657231354efe4d9034367ec5a80ca480345.tar.bz2 taler-ios-bcb61657231354efe4d9034367ec5a80ca480345.zip |
use iono from iono.git
-rw-r--r-- | .gitmodules | 9 | ||||
-rw-r--r-- | Taler.xcodeproj/project.pbxproj | 74 | ||||
-rw-r--r-- | Taler/AppDelegate.swift | 11 | ||||
-rw-r--r-- | Taler/NodeWrapper.swift | 113 | ||||
-rw-r--r-- | Taler/Taler-Bridging-Header.h | 20 | ||||
-rw-r--r-- | Taler/node_wrapper.cpp | 312 | ||||
-rw-r--r-- | Taler/node_wrapper.h | 56 | ||||
-rw-r--r-- | TalerTests/NodeWrapperTests.swift | 63 | ||||
-rwxr-xr-x | bootstrap | 7 | ||||
m--------- | iono | 0 | ||||
m--------- | ios-node-v8 | 0 |
11 files changed, 55 insertions, 610 deletions
diff --git a/.gitmodules b/.gitmodules index 7cfee13..9d8bd13 100644 --- a/.gitmodules +++ b/.gitmodules @@ -1,6 +1,3 @@ -[submodule "wallet-kotlin"] - path = wallet-kotlin - url = https://git.taler.net/wallet-kotlin.git -[submodule "ios-node-v8"] - path = ios-node-v8 - url = git://git.taler.net/ios-node-v8.git +[submodule "iono"] + path = iono + url = ssh://git@git.taler.net/iono.git diff --git a/Taler.xcodeproj/project.pbxproj b/Taler.xcodeproj/project.pbxproj index a2cb920..b0f4d87 100644 --- a/Taler.xcodeproj/project.pbxproj +++ b/Taler.xcodeproj/project.pbxproj @@ -7,8 +7,6 @@ objects = { /* Begin PBXBuildFile section */ - D110857525B134420047F1B6 /* NodeWrapper.swift in Sources */ = {isa = PBXBuildFile; fileRef = D110857425B134420047F1B6 /* NodeWrapper.swift */; }; - D110857A25B13DF90047F1B6 /* NodeWrapperTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = D110857925B13DF90047F1B6 /* NodeWrapperTests.swift */; }; D14AFD2124D232B300C51073 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = D14AFD2024D232B300C51073 /* AppDelegate.swift */; }; D14AFD2324D232B300C51073 /* SceneDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = D14AFD2224D232B300C51073 /* SceneDelegate.swift */; }; D14AFD2524D232B300C51073 /* ContentView.swift in Sources */ = {isa = PBXBuildFile; fileRef = D14AFD2424D232B300C51073 /* ContentView.swift */; }; @@ -36,7 +34,7 @@ D17D8B8325ADB29B001BD43D /* libllhttp.a in Frameworks */ = {isa = PBXBuildFile; fileRef = D17D8B4D25ADB12C001BD43D /* libllhttp.a */; }; D17D8B8425ADB29B001BD43D /* libhistogram.a in Frameworks */ = {isa = PBXBuildFile; fileRef = D17D8B5625ADB130001BD43D /* libhistogram.a */; }; D17D8B8525ADB29B001BD43D /* libcares.a in Frameworks */ = {isa = PBXBuildFile; fileRef = D17D8B4825ADB12B001BD43D /* libcares.a */; }; - D1AB9647259EB24100DEAB23 /* node_wrapper.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D1AB9646259EB24100DEAB23 /* node_wrapper.cpp */; }; + D1AFF0F3268D59C200FBB744 /* libiono.a in Frameworks */ = {isa = PBXBuildFile; fileRef = D1AFF0F2268D59A500FBB744 /* libiono.a */; }; D1D6435F2681290200A22334 /* taler-wallet-ios.js in Resources */ = {isa = PBXBuildFile; fileRef = D1D6435E2681290200A22334 /* taler-wallet-ios.js */; }; /* End PBXBuildFile section */ @@ -58,8 +56,6 @@ /* End PBXContainerItemProxy section */ /* Begin PBXFileReference section */ - D110857425B134420047F1B6 /* NodeWrapper.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NodeWrapper.swift; sourceTree = "<group>"; }; - D110857925B13DF90047F1B6 /* NodeWrapperTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NodeWrapperTests.swift; sourceTree = "<group>"; }; D11DB44E25A5C487009CF0BC /* libnode.a */ = {isa = PBXFileReference; lastKnownFileType = archive.ar; name = libnode.a; path = "nodejs-mobile/out/Release/libnode.a"; sourceTree = "<group>"; }; D11DB45625A5C5C7009CF0BC /* libv8_initializers.a */ = {isa = PBXFileReference; lastKnownFileType = archive.ar; name = libv8_initializers.a; path = "nodejs-mobile/out/Release/libv8_initializers.a"; sourceTree = "<group>"; }; D11DB45725A5C5C7009CF0BC /* libv8_compiler.a */ = {isa = PBXFileReference; lastKnownFileType = archive.ar; name = libv8_compiler.a; path = "nodejs-mobile/out/Release/libv8_compiler.a"; sourceTree = "<group>"; }; @@ -138,9 +134,7 @@ D17D8B5625ADB130001BD43D /* libhistogram.a */ = {isa = PBXFileReference; lastKnownFileType = archive.ar; name = libhistogram.a; path = "ios-node-v8/taler-ios-build/compiled/node-arm64/libhistogram.a"; sourceTree = "<group>"; }; D17D8B5725ADB130001BD43D /* libtorque_base.a */ = {isa = PBXFileReference; lastKnownFileType = archive.ar; name = libtorque_base.a; path = "ios-node-v8/taler-ios-build/compiled/node-arm64/libtorque_base.a"; sourceTree = "<group>"; }; D1AB963B259EB13D00DEAB23 /* libnode.89.dylib */ = {isa = PBXFileReference; lastKnownFileType = "compiled.mach-o.dylib"; name = libnode.89.dylib; path = "ios-node-v8/taler-ios-build/compiled/x64-v8a/libnode.89.dylib"; sourceTree = "<group>"; }; - D1AB9644259EB22900DEAB23 /* node_wrapper.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = node_wrapper.h; sourceTree = "<group>"; }; - D1AB9645259EB24000DEAB23 /* Taler-Bridging-Header.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "Taler-Bridging-Header.h"; sourceTree = "<group>"; }; - D1AB9646259EB24100DEAB23 /* node_wrapper.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = node_wrapper.cpp; sourceTree = "<group>"; }; + D1AFF0F2268D59A500FBB744 /* libiono.a */ = {isa = PBXFileReference; lastKnownFileType = archive.ar; name = libiono.a; path = iono/compiled/x64/libiono.a; sourceTree = "<group>"; }; D1D6435E2681290200A22334 /* taler-wallet-ios.js */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.javascript; path = "taler-wallet-ios.js"; sourceTree = "<group>"; }; D1F0C22F25A958AE00C3179D /* libllhttp.a */ = {isa = PBXFileReference; lastKnownFileType = archive.ar; name = libllhttp.a; path = "ios-node-v8/tools/ios-framework/bin/x64/libllhttp.a"; sourceTree = "<group>"; }; D1F0C23025A958AE00C3179D /* libv8_initializers.a */ = {isa = PBXFileReference; lastKnownFileType = archive.ar; name = libv8_initializers.a; path = "ios-node-v8/tools/ios-framework/bin/x64/libv8_initializers.a"; sourceTree = "<group>"; }; @@ -198,6 +192,7 @@ D17D8B7425ADB29A001BD43D /* libv8_zlib.a in Frameworks */, D17D8B8525ADB29B001BD43D /* libcares.a in Frameworks */, D17D8B8125ADB29B001BD43D /* libnode.a in Frameworks */, + D1AFF0F3268D59C200FBB744 /* libiono.a in Frameworks */, D17D8B8325ADB29B001BD43D /* libllhttp.a in Frameworks */, D17D8B7B25ADB29B001BD43D /* libv8_compiler.a in Frameworks */, D17D8B7225ADB29A001BD43D /* libbrotli.a in Frameworks */, @@ -261,10 +256,6 @@ D14AFD2624D232B500C51073 /* Assets.xcassets */, D14AFD2B24D232B500C51073 /* LaunchScreen.storyboard */, D14AFD2E24D232B500C51073 /* Info.plist */, - D1AB9644259EB22900DEAB23 /* node_wrapper.h */, - D1AB9646259EB24100DEAB23 /* node_wrapper.cpp */, - D1AB9645259EB24000DEAB23 /* Taler-Bridging-Header.h */, - D110857425B134420047F1B6 /* NodeWrapper.swift */, ); path = Taler; sourceTree = "<group>"; @@ -274,7 +265,6 @@ children = ( D14AFD3724D232B500C51073 /* TalerTests.swift */, D14AFD3924D232B500C51073 /* Info.plist */, - D110857925B13DF90047F1B6 /* NodeWrapperTests.swift */, ); path = TalerTests; sourceTree = "<group>"; @@ -291,6 +281,7 @@ D1EFA41824D2619B0008B97F /* Frameworks */ = { isa = PBXGroup; children = ( + D1AFF0F2268D59A500FBB744 /* libiono.a */, D1F0C26625A9597700C3179D /* libbrotli.a */, D145D1EE25AC416B00CDD61B /* libbrotli.a */, D17D8B4F25ADB12D001BD43D /* libbrotli.a */, @@ -536,8 +527,6 @@ D14AFD2124D232B300C51073 /* AppDelegate.swift in Sources */, D14AFD2324D232B300C51073 /* SceneDelegate.swift in Sources */, D14AFD2524D232B300C51073 /* ContentView.swift in Sources */, - D1AB9647259EB24100DEAB23 /* node_wrapper.cpp in Sources */, - D110857525B134420047F1B6 /* NodeWrapper.swift in Sources */, ); runOnlyForDeploymentPostprocessing = 0; }; @@ -546,7 +535,6 @@ buildActionMask = 2147483647; files = ( D14AFD3824D232B500C51073 /* TalerTests.swift in Sources */, - D110857A25B13DF90047F1B6 /* NodeWrapperTests.swift in Sources */, ); runOnlyForDeploymentPostprocessing = 0; }; @@ -636,10 +624,11 @@ GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; GCC_WARN_UNUSED_FUNCTION = YES; GCC_WARN_UNUSED_VARIABLE = YES; - IPHONEOS_DEPLOYMENT_TARGET = 13.6; + IPHONEOS_DEPLOYMENT_TARGET = 14.5; MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE; MTL_FAST_MATH = YES; ONLY_ACTIVE_ARCH = YES; + OTHER_LDFLAGS = "-lc++"; SDKROOT = iphoneos; SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; SWIFT_OPTIMIZATION_LEVEL = "-Onone"; @@ -691,9 +680,10 @@ GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; GCC_WARN_UNUSED_FUNCTION = YES; GCC_WARN_UNUSED_VARIABLE = YES; - IPHONEOS_DEPLOYMENT_TARGET = 13.6; + IPHONEOS_DEPLOYMENT_TARGET = 14.5; MTL_ENABLE_DEBUG_INFO = NO; MTL_FAST_MATH = YES; + OTHER_LDFLAGS = "-lc++"; SDKROOT = iphoneos; SWIFT_COMPILATION_MODE = wholemodule; SWIFT_OPTIMIZATION_LEVEL = "-O"; @@ -713,9 +703,9 @@ ENABLE_PREVIEWS = YES; FRAMEWORK_SEARCH_PATHS = "$(inherited)"; HEADER_SEARCH_PATHS = ( - "$(PROJECT_DIR)/ios-node-v8/src", - "$(PROJECT_DIR)/ios-node-v8/deps/v8/include", - "$(PROJECT_DIR)/ios-node-v8/deps/uv/include", + "$(PROJECT_DIR)/iono/ios-node-v8/src", + "$(PROJECT_DIR)/iono/ios-node-v8/deps/v8/include", + "$(PROJECT_DIR)/iono/ios-node-v8/deps/uv/include", ); INFOPLIST_FILE = Taler/Info.plist; LD_RUNPATH_SEARCH_PATHS = ( @@ -725,14 +715,24 @@ LIBRARY_SEARCH_PATHS = ( "$(inherited)", "$(PROJECT_DIR)", + "$(PROJECT_DIR)/iono/compiled/x64", + ); + "LIBRARY_SEARCH_PATHS[sdk=iphoneos*]" = ( + "$(PROJECT_DIR)/iono/ios-node-v8/taler-ios-build/compiled/node-arm64", + "$(PROJECT_DIR)/iono/compiled/arm64", + ); + "LIBRARY_SEARCH_PATHS[sdk=iphonesimulator*]" = ( + "$(PROJECT_DIR)/iono/ios-node-v8/taler-ios-build/compiled/node-x64", + "$(PROJECT_DIR)/iono/compiled/x64", ); - "LIBRARY_SEARCH_PATHS[sdk=iphoneos*]" = "$(PROJECT_DIR)/ios-node-v8/taler-ios-build/compiled/node-arm64"; - "LIBRARY_SEARCH_PATHS[sdk=iphonesimulator*]" = "$(PROJECT_DIR)/ios-node-v8/taler-ios-build/compiled/node-x64"; OTHER_CFLAGS = ""; PRODUCT_BUNDLE_IDENTIFIER = com.taler.Taler; PRODUCT_NAME = "$(TARGET_NAME)"; PROVISIONING_PROFILE_SPECIFIER = ""; - SWIFT_OBJC_BRIDGING_HEADER = "Taler/Taler-Bridging-Header.h"; + SWIFT_INCLUDE_PATHS = "$(PROJECT_DIR)/iono/iono"; + "SWIFT_INCLUDE_PATHS[sdk=iphoneos*]" = "$(PROJECT_DIR)/iono/compiled/arm64"; + "SWIFT_INCLUDE_PATHS[sdk=iphonesimulator*]" = "$(PROJECT_DIR)/iono/compiled/x64"; + SWIFT_OBJC_BRIDGING_HEADER = ""; SWIFT_OPTIMIZATION_LEVEL = "-Onone"; SWIFT_VERSION = 5.0; TARGETED_DEVICE_FAMILY = "1,2"; @@ -752,9 +752,9 @@ ENABLE_PREVIEWS = YES; FRAMEWORK_SEARCH_PATHS = "$(inherited)"; HEADER_SEARCH_PATHS = ( - "$(PROJECT_DIR)/ios-node-v8/src", - "$(PROJECT_DIR)/ios-node-v8/deps/v8/include", - "$(PROJECT_DIR)/ios-node-v8/deps/uv/include", + "$(PROJECT_DIR)/iono/ios-node-v8/src", + "$(PROJECT_DIR)/iono/ios-node-v8/deps/v8/include", + "$(PROJECT_DIR)/iono/ios-node-v8/deps/uv/include", ); INFOPLIST_FILE = Taler/Info.plist; LD_RUNPATH_SEARCH_PATHS = ( @@ -764,14 +764,24 @@ LIBRARY_SEARCH_PATHS = ( "$(inherited)", "$(PROJECT_DIR)", + "$(PROJECT_DIR)/iono/compiled/x64", + ); + "LIBRARY_SEARCH_PATHS[sdk=iphoneos*]" = ( + "$(PROJECT_DIR)/iono/ios-node-v8/taler-ios-build/compiled/node-arm64", + "$(PROJECT_DIR)/iono/compiled/arm64", + ); + "LIBRARY_SEARCH_PATHS[sdk=iphonesimulator*]" = ( + "$(PROJECT_DIR)/iono/ios-node-v8/taler-ios-build/compiled/node-x64", + "$(PROJECT_DIR)/iono/compiled/x64", ); - "LIBRARY_SEARCH_PATHS[sdk=iphoneos*]" = "$(PROJECT_DIR)/ios-node-v8/taler-ios-build/compiled/node-arm64"; - "LIBRARY_SEARCH_PATHS[sdk=iphonesimulator*]" = "$(PROJECT_DIR)/ios-node-v8/taler-ios-build/compiled/node-x64"; OTHER_CFLAGS = ""; PRODUCT_BUNDLE_IDENTIFIER = com.taler.Taler; PRODUCT_NAME = "$(TARGET_NAME)"; PROVISIONING_PROFILE_SPECIFIER = ""; - SWIFT_OBJC_BRIDGING_HEADER = "Taler/Taler-Bridging-Header.h"; + SWIFT_INCLUDE_PATHS = "$(PROJECT_DIR)/iono/iono"; + "SWIFT_INCLUDE_PATHS[sdk=iphoneos*]" = "$(PROJECT_DIR)/iono/compiled/arm64"; + "SWIFT_INCLUDE_PATHS[sdk=iphonesimulator*]" = "$(PROJECT_DIR)/iono/compiled/x64"; + SWIFT_OBJC_BRIDGING_HEADER = ""; SWIFT_VERSION = 5.0; TARGETED_DEVICE_FAMILY = "1,2"; VALIDATE_WORKSPACE = YES; @@ -787,7 +797,7 @@ CODE_SIGN_STYLE = Automatic; DEVELOPMENT_TEAM = ""; INFOPLIST_FILE = TalerTests/Info.plist; - IPHONEOS_DEPLOYMENT_TARGET = 13.6; + IPHONEOS_DEPLOYMENT_TARGET = 14.5; LD_RUNPATH_SEARCH_PATHS = ( "$(inherited)", "@executable_path/Frameworks", @@ -810,7 +820,7 @@ CODE_SIGN_STYLE = Automatic; DEVELOPMENT_TEAM = ""; INFOPLIST_FILE = TalerTests/Info.plist; - IPHONEOS_DEPLOYMENT_TARGET = 13.6; + IPHONEOS_DEPLOYMENT_TARGET = 14.5; LD_RUNPATH_SEARCH_PATHS = ( "$(inherited)", "@executable_path/Frameworks", diff --git a/Taler/AppDelegate.swift b/Taler/AppDelegate.swift index bbb0952..075bf73 100644 --- a/Taler/AppDelegate.swift +++ b/Taler/AppDelegate.swift @@ -15,6 +15,7 @@ */ import UIKit +import iono @UIApplicationMain class AppDelegate: UIResponder, UIApplicationDelegate { @@ -25,13 +26,13 @@ class AppDelegate: UIResponder, UIApplicationDelegate { // Override point for customization after application launch. // TODO: generate 'taler-wallet-ios.js' from wallet-core instead of pasting it in. let js_path = URL(fileURLWithPath: Bundle.main.path(forResource: "taler-wallet-ios", ofType: "js")!) - let iono = Iono() + let nodeInstance = Iono() do { let js = try String(contentsOf: js_path, encoding: .utf8) - iono.putModuleCode(modName: "@gnu-taler/taler-wallet-ios", code: js) - iono.evalNodeCode(source: "require('iono');") - iono.evalNodeCode(source: "tw = require('@gnu-taler/taler-wallet-ios');") - iono.evalNodeCode(source: "tw.installIosWalletListener();") + nodeInstance.putModuleCode(modName: "@gnu-taler/taler-wallet-ios", code: js) + nodeInstance.evalNodeCode(source: "require('iono');") + nodeInstance.evalNodeCode(source: "tw = require('@gnu-taler/taler-wallet-ios');") + nodeInstance.evalNodeCode(source: "tw.installIosWalletListener();") } catch { } diff --git a/Taler/NodeWrapper.swift b/Taler/NodeWrapper.swift deleted file mode 100644 index 77a4ec5..0000000 --- a/Taler/NodeWrapper.swift +++ /dev/null @@ -1,113 +0,0 @@ -/* - * This file is part of GNU Taler - * (C) 2021 Taler Systems S.A. - * - * GNU Taler is free software; you can redistribute it and/or modify it under the - * terms of the GNU General Public License as published by the Free Software - * Foundation; either version 3, or (at your option) any later version. - * - * GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY - * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR - * A PARTICULAR PURPOSE. See the GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License along with - * GNU Taler; see the file COPYING. If not, see <http://www.gnu.org/licenses/> - */ - -import Foundation - -protocol IonoMessageHandler { - func handleMessage(message: String) -} - -func notification_callback(payload: Optional<UnsafePointer<Int8>>, - userdata: Optional<UnsafeMutableRawPointer>) { - let native = Unmanaged<Iono>.fromOpaque(userdata!).takeUnretainedValue() - let string = String(cString: payload!) - native.internalOnNotify(payload: string) -} - -class Iono { - var instance: OpaquePointer! - var work_queue: DispatchQueue - var initialization_group: DispatchGroup - var messageHandler: IonoMessageHandler? - - init() { - work_queue = DispatchQueue(label: "NodeQueue", qos: .userInitiated) - initialization_group = DispatchGroup() - initialization_group.notify(queue: work_queue) { - self.instance = __initNative() - __setNotifyHandler(self.instance, notification_callback, Unmanaged.passUnretained(self).toOpaque()) - } - } - - deinit { - __destroyNative(instance) - } - - private func scheduleNodeThreadAsync(block: @escaping () -> Void) { - initialization_group.wait() - work_queue.async(execute: block) - notifyNative() - } - - private func scheduleNodeThreadSync(block: @escaping () -> Void) { - initialization_group.wait() - work_queue.sync(execute: block) - notifyNative() - } - - func internalOnNotify(payload: String) { - if let handler = messageHandler { - handler.handleMessage(message: payload) - } - } - - func notifyNative() { - initialization_group.wait() - __notifyNative(instance) - } - - func evalSimpleJs(source: String) -> String { - var result: String? - scheduleNodeThreadSync { - let cResult = __evalJs(self.instance, source.cString(using: .utf8)) - if let cStr = cResult { - result = String(cString: cStr) - free(cResult) - } - } - return result! - } - - func evalNodeCode(source: String) { - scheduleNodeThreadAsync { - __makeCallbackNative(self.instance, source.cString(using: .utf8)) - } - } - - func sendMessage(message: String) { - let encoded = message.data(using: .utf8)!.base64EncodedString() - let source = """ - if (global.__iono_onMessage) { - const msg = (new Buffer('\(encoded)', 'base64')).toString('ascii'); - global.__iono_onMessage(msg); - } else { - console.log("WARN: no __iono_onMessage defined"); - } - """ - evalNodeCode(source: source) - } - - func waitStopped() { - - } - - func putModuleCode(modName: String, code: String) { - scheduleNodeThreadSync { - __putModuleCodeNative(self.instance, modName.cString(using: .utf8), - code.cString(using: .utf8)) - } - } -} diff --git a/Taler/Taler-Bridging-Header.h b/Taler/Taler-Bridging-Header.h deleted file mode 100644 index e7e117f..0000000 --- a/Taler/Taler-Bridging-Header.h +++ /dev/null @@ -1,20 +0,0 @@ -/* - * This file is part of GNU Taler - * (C) 2021 Taler Systems S.A. - * - * GNU Taler is free software; you can redistribute it and/or modify it under the - * terms of the GNU General Public License as published by the Free Software - * Foundation; either version 3, or (at your option) any later version. - * - * GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY - * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR - * A PARTICULAR PURPOSE. See the GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License along with - * GNU Taler; see the file COPYING. If not, see <http://www.gnu.org/licenses/> - */ - -// -// Use this file to import your target's public headers that you would like to expose to Swift. -// -#import "node_wrapper.h" diff --git a/Taler/node_wrapper.cpp b/Taler/node_wrapper.cpp deleted file mode 100644 index 42f3024..0000000 --- a/Taler/node_wrapper.cpp +++ /dev/null @@ -1,312 +0,0 @@ -/* - * This file is part of GNU Taler - * (C) 2021 Taler Systems S.A. - * - * GNU Taler is free software; you can redistribute it and/or modify it under the - * terms of the GNU General Public License as published by the Free Software - * Foundation; either version 3, or (at your option) any later version. - * - * GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY - * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR - * A PARTICULAR PURPOSE. See the GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License along with - * GNU Taler; see the file COPYING. If not, see <http://www.gnu.org/licenses/> - */ -#include "node_wrapper.h" - -#include <map> -#include <string> - -#include <node.h> -#include <uv.h> - -#define NODE_WANT_INTERNALS 1 -#include <node_binding.h> - -#include <iostream> - -std::map<std::string, std::string> modmap = std::map<std::string, std::string>(); - -struct __IonoInstance -{ - /* Node/V8 */ - static std::unique_ptr<node::MultiIsolatePlatform> platform; - std::unique_ptr<node::CommonEnvironmentSetup> setup; - v8::Isolate *isolate; - node::Environment *env; - uv_async_t async_notify; - - bool break_requested; - - /* Notifications to swift */ - __NotifyHandler notification_handler; - void *notification_userdata; - - __IonoInstance(); - - char * - evalJs(const char *js); - - void - runNode(); - - void - makeCallback(const char *callback); -}; - -#ifdef __cplusplus -extern "C" { -#endif - -struct __IonoInstance * -__initNative() -{ - __IonoInstance *instance = new __IonoInstance(); - return instance; -} - -void -__destroyNative(struct __IonoInstance *instance) -{ - delete instance; -} - -char * -__evalJs(struct __IonoInstance *instance, const char *js) -{ - return instance->evalJs(js); -} - -void -__putModuleCodeNative(struct __IonoInstance *instance, - const char *modName, const char *modCode) -{ - modmap[std::string(modName)] = std::string(modCode); -} - -void -__notifyNative(struct __IonoInstance *instance) -{ - uv_async_send(&instance->async_notify); -} - -void -__runNode(struct __IonoInstance *instance) -{ - instance->runNode(); -} - -void -__makeCallbackNative(struct __IonoInstance *instance, const char *source) -{ - instance->makeCallback(source); -} - -void -__setNotifyHandler(struct __IonoInstance *instance, __NotifyHandler handler, void *userdata) -{ - instance->notification_handler = handler; - instance->notification_userdata = userdata; -} - -#ifdef __cplusplus -} -#endif - -std::unique_ptr<node::MultiIsolatePlatform> __IonoInstance::platform = nullptr; - -static void -notifyCallback(uv_async_t *async); - -static void -sendMessageCallback(const v8::FunctionCallbackInfo<v8::Value> &args); - -static void -getModuleCode(const v8::FunctionCallbackInfo<v8::Value> &args); - -static const std::string main_code = "const publicRequire =" - " require('module').createRequire(process.cwd() + '/');" - " globalThis.require = publicRequire;" - " require('vm').runInThisContext(process.argv[1]);global.__node_run = (x) => {" - " 0 && console.log('running code', x);" - " global.eval(x);" - "};" - "" - "global.__iono_onMessage = (x) => {" - " 0 && console.log('got __iono_onMessage', x);" - "};"; - -static void -_register_iono(); - -__IonoInstance::__IonoInstance() : - break_requested(false), - notification_handler(nullptr) -{ - { - uv_loop_t *loop = uv_default_loop(); - uv_async_init(loop, &async_notify, ¬ifyCallback); - async_notify.data = this; - } - - std::vector<std::string> args = { "node" }; - std::vector<std::string> exec_args; - std::vector<std::string> errors; - - if (nullptr == platform) - { - int exit_code = node::InitializeNodeWithArgs(&args, &exec_args, &errors); - for (const std::string &error : errors) - { - fprintf(stderr, "%s: %s\n", args[0].c_str(), error.c_str()); - /*if (exit_code != 0) { - return exit_code;*/ - } - - platform = node::MultiIsolatePlatform::Create(4); - v8::V8::InitializePlatform(platform.get()); - v8::V8::Initialize(); - } - - setup = node::CommonEnvironmentSetup::Create(platform.get(), &errors, args, exec_args); - if (!setup) { - for (const std::string &err : errors) - fprintf(stderr, "%s: %s\n", args[0].c_str(), err.c_str()); - //return 1; - } - - isolate = setup->isolate(); - env = setup->env(); - - { - v8::Locker locker(isolate); - v8::Isolate::Scope isolate_scope(isolate); - v8::HandleScope handle_scope(isolate); - v8::Context::Scope context_scope(setup->context()); - - node::LoadEnvironment(env, main_code.c_str()); - - v8::Local<v8::ObjectTemplate> data_template = v8::ObjectTemplate::New(isolate); - data_template->SetInternalFieldCount(1); - v8::Local<v8::Object> data_object = data_template->NewInstance(setup->context()).ToLocalChecked(); - data_object->SetAlignedPointerInInternalField(0, this); - - v8::Local<v8::Function> sendMessageFunction = v8::Function::New(setup->context(), - sendMessageCallback, - data_object).ToLocalChecked(); - - v8::Local<v8::Object> global = setup->context()->Global(); - - global->Set(setup->context(), v8::String::NewFromUtf8(isolate, "__iono_sendMessage", - v8::NewStringType::kNormal).ToLocalChecked(), - sendMessageFunction).Check(); - _register_iono(); - } -} - -char * -__IonoInstance::evalJs(const char *js) -{ - v8::Locker locker(isolate); - v8::Isolate::Scope isolate_scope(isolate); - v8::HandleScope handle_scope(isolate); - v8::Context::Scope context_scope(setup->context()); - - // Create a string containing the JavaScript source code. - v8::Local<v8::String> source = - v8::String::NewFromUtf8(isolate, js, v8::NewStringType::kNormal).ToLocalChecked(); - - // Compile the source code. - v8::Local<v8::Script> script; - if (!v8::Script::Compile(setup->context(), source).ToLocal(&script)) { - return nullptr; - } - - // Run the script to get the result. - v8::Local<v8::Value> result; - if (!script->Run(setup->context()).ToLocal(&result)) { - return nullptr; - } - - // Convert the result to an UTF8 string and print it. - v8::String::Utf8Value utf8(isolate, result); - return strdup(*utf8); -} - -void -__IonoInstance::runNode() { - v8::Locker locker(isolate); - v8::Isolate::Scope isolate_scope(isolate); - v8::HandleScope handle_scope(isolate); - v8::Context::Scope context_scope(setup->context()); - break_requested = false; - while (true) { - uv_run(uv_default_loop(), UV_RUN_ONCE); - platform->DrainTasks(isolate); - if (break_requested) - break; - } -} - -void -__IonoInstance::makeCallback(const char *callback) -{ - v8::Locker locker(isolate); - v8::Isolate::Scope isolate_scope(isolate); - v8::HandleScope handle_scope(isolate); - v8::Context::Scope context_scope(setup->context()); - v8::Local<v8::Object> global = setup->context()->Global(); - v8::Local<v8::Value> argv[] = { - v8::String::NewFromUtf8(isolate, callback, - v8::NewStringType::kNormal).ToLocalChecked() - }; - node::MakeCallback(isolate, global, "__node_run", 1, argv, {0, 0}); -} - -static void -notifyCallback(uv_async_t *async) { - __IonoInstance *instance = (__IonoInstance *)async->data; - instance->break_requested = true; -} - -static void -sendMessageCallback(const v8::FunctionCallbackInfo<v8::Value> &args) { - v8::Isolate *isolate = args.GetIsolate(); - v8::Locker locker(isolate); - if (args.Length() < 1) - return; - v8::HandleScope scope(isolate); - v8::Local<v8::Value> arg = args[0]; - v8::String::Utf8Value value(isolate, arg); - - v8::Local<v8::Object> data = v8::Local<v8::Object>::Cast(args.Data()); - - __IonoInstance *instance = (__IonoInstance *)data->GetAlignedPointerFromInternalField(0); - instance->notification_handler(*value, instance->notification_userdata); -} - -static void -getModuleCode(const v8::FunctionCallbackInfo<v8::Value> &args) { - v8::Isolate *isolate = args.GetIsolate(); - v8::Locker locker(isolate); - if (args.Length() < 1) - return; - v8::HandleScope scope(isolate); - v8::Local<v8::Value> arg = args[0]; - v8::String::Utf8Value value(isolate, arg); - - v8::Local<v8::Object> data = v8::Local<v8::Object>::Cast(args.Data()); - args.GetReturnValue().Set(v8::String::NewFromUtf8(isolate, - modmap[*value].c_str()).ToLocalChecked()); -} - -static void -initializeIonoInternal(v8::Local<v8::Object> target, - v8::Local<v8::Value> unused, - v8::Local<v8::Context> context, - void *priv) { - NODE_SET_METHOD(target, "getModuleCode", getModuleCode); -} - -NODE_MODULE_CONTEXT_AWARE_INTERNAL(iono, initializeIonoInternal) diff --git a/Taler/node_wrapper.h b/Taler/node_wrapper.h deleted file mode 100644 index 4b9a4a1..0000000 --- a/Taler/node_wrapper.h +++ /dev/null @@ -1,56 +0,0 @@ -/* - * This file is part of GNU Taler - * (C) 2021 Taler Systems S.A. - * - * GNU Taler is free software; you can redistribute it and/or modify it under the - * terms of the GNU General Public License as published by the Free Software - * Foundation; either version 3, or (at your option) any later version. - * - * GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY - * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR - * A PARTICULAR PURPOSE. See the GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License along with - * GNU Taler; see the file COPYING. If not, see <http://www.gnu.org/licenses/> - */ -#ifndef node_wrapper_h -#define node_wrapper_h - -#ifdef __cplusplus -extern "C" { -#endif - -struct __IonoInstance; - -struct __IonoInstance * -__initNative(); - -void -__destroyNative(struct __IonoInstance *instance); - -char * -__evalJs(struct __IonoInstance *instance, const char *source); - -void -__putModuleCodeNative(struct __IonoInstance *instance, - const char *modName, const char *modCode); - -void -__notifyNative(struct __IonoInstance *instance); - -void -__runNode(struct __IonoInstance *instance); - -void -__makeCallbackNative(struct __IonoInstance *instance, const char *source); - -typedef void (* __NotifyHandler)(const char *payload, void *userdata); - -void -__setNotifyHandler(struct __IonoInstance *instance, __NotifyHandler handler, void *userdata); - -#ifdef __cplusplus -} -#endif - -#endif /* node_wrapper_h */ diff --git a/TalerTests/NodeWrapperTests.swift b/TalerTests/NodeWrapperTests.swift deleted file mode 100644 index 63ed937..0000000 --- a/TalerTests/NodeWrapperTests.swift +++ /dev/null @@ -1,63 +0,0 @@ -/* - * This file is part of GNU Taler - * (C) 2021 Taler Systems S.A. - * - * GNU Taler is free software; you can redistribute it and/or modify it under the - * terms of the GNU General Public License as published by the Free Software - * Foundation; either version 3, or (at your option) any later version. - * - * GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY - * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR - * A PARTICULAR PURPOSE. See the GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License along with - * GNU Taler; see the file COPYING. If not, see <http://www.gnu.org/licenses/> - */ - -import XCTest -@testable import Taler - -class MessageHandler: IonoMessageHandler { - var lastMessage: String? - var messageSemaphore: DispatchSemaphore - - init() { - messageSemaphore = DispatchSemaphore(value: 0) - } - - func handleMessage(message: String) { - lastMessage = message - messageSemaphore.signal() - } -} - -class NodeWrapperTests: XCTestCase { - var iono: Iono! - var handler: MessageHandler! - - override func setUpWithError() throws { - iono = Iono() - handler = MessageHandler() - - iono.messageHandler = handler - } - - override func tearDownWithError() throws { - - } - - func testEvalJS() throws { - XCTAssert("2" == iono.evalSimpleJs(source: "1 + 1")) - XCTAssert("36" == iono.evalSimpleJs(source: "6 * 6")) - XCTAssert("42" == iono.evalSimpleJs(source: "(()=>{let x = 42; return x;})()")) - XCTAssert("undefined" == iono.evalSimpleJs(source: "const myVal = 42")) - XCTAssert("43" == iono.evalSimpleJs(source: "myVal + 1")) - - iono.evalNodeCode(source: "global.__iono_onMessage = (x) => { global.__iono_sendMessage(x); }") - let message = "Hello IONO" - iono.sendMessage(message: message) - handler.messageSemaphore.wait() - XCTAssert(message == handler.lastMessage) - } - -} @@ -13,7 +13,8 @@ fi git submodule sync --recursive git submodule update --init --recursive -cd ios-node-v8 -./taler-ios-build/x64 -./taler-ios-build/arm64 +./iono/ios-node-v8/taler-ios-build/x64 +./iono/ios-node-v8/taler-ios-build/arm64 +cd iono +./bootstrap cd .. diff --git a/iono b/iono new file mode 160000 +Subproject f79f1ea181a04032818c98c367fece8222110d5 diff --git a/ios-node-v8 b/ios-node-v8 deleted file mode 160000 -Subproject 029315b48c8837b48e156f70a2362157716c8d3 |