forked from I2P_Developers/i2p.i2p
Mac OS X Launcher: more cleanup and some bugfixes.
This commit is contained in:
@@ -13,10 +13,10 @@
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#include <Cocoa/Cocoa.h>
|
#include <Cocoa/Cocoa.h>
|
||||||
|
#include "SBridge.h"
|
||||||
|
|
||||||
|
|
||||||
#include "RouterTask.h"
|
#include "RouterTask.h"
|
||||||
#include "JavaHelper.h"
|
|
||||||
|
|
||||||
|
|
||||||
#define DEF_I2P_VERSION "0.9.36"
|
#define DEF_I2P_VERSION "0.9.36"
|
||||||
@@ -34,8 +34,6 @@
|
|||||||
|
|
||||||
@class ExtractMetaInfo;
|
@class ExtractMetaInfo;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@interface ExtractMetaInfo : NSObject
|
@interface ExtractMetaInfo : NSObject
|
||||||
@property (copy) NSString* i2pBase;
|
@property (copy) NSString* i2pBase;
|
||||||
@property (copy) NSString* javaBinary;
|
@property (copy) NSString* javaBinary;
|
||||||
@@ -63,7 +61,7 @@ inline std::string getDefaultBaseDir()
|
|||||||
return i2pBaseDir;
|
return i2pBaseDir;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline void sendUserNotification(NSString* title, NSString* informativeText, NSImage* contentImage = NULL, bool makeSound = false) {
|
inline void sendUserNotification(NSString* title, NSString* informativeText, bool makeSound = false) {
|
||||||
NSUserNotification *userNotification = [[NSUserNotification alloc] init];
|
NSUserNotification *userNotification = [[NSUserNotification alloc] init];
|
||||||
|
|
||||||
userNotification.title = title;
|
userNotification.title = title;
|
||||||
@@ -80,32 +78,9 @@ inline void sendUserNotification(NSString* title, NSString* informativeText, NSI
|
|||||||
[[NSUserNotificationCenter defaultUserNotificationCenter] scheduleNotification:userNotification];
|
[[NSUserNotificationCenter defaultUserNotificationCenter] scheduleNotification:userNotification];
|
||||||
};
|
};
|
||||||
|
|
||||||
using maybeAnRouterRunner = I2PRouterTask*;
|
|
||||||
|
|
||||||
std::vector<std::string> buildClassPath(std::string basePath);
|
|
||||||
|
|
||||||
extern JvmListSharedPtr gRawJvmList;
|
|
||||||
|
|
||||||
// DO NOT ACCESS THIS GLOBAL VARIABLE DIRECTLY.
|
|
||||||
static std::mutex globalRouterStatusMutex;
|
|
||||||
static maybeAnRouterRunner globalRouterStatus = maybeAnRouterRunner{};
|
|
||||||
static bool isRuterRunning = false;
|
|
||||||
|
|
||||||
maybeAnRouterRunner getGlobalRouterObject();
|
|
||||||
void setGlobalRouterObject(I2PRouterTask* newRouter);
|
|
||||||
bool getGlobalRouterIsRunning();
|
|
||||||
void setGlobalRouterIsRunning(bool running);
|
|
||||||
|
|
||||||
#include "SBridge.h"
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@class MenuBarCtrl;
|
@interface AppDelegate : NSObject <NSUserNotificationCenterDelegate, NSApplicationDelegate>
|
||||||
|
|
||||||
@interface AppDelegate : NSObject <NSUserNotificationCenterDelegate, NSApplicationDelegate> {
|
|
||||||
@public
|
|
||||||
//NSImageView *imageCell;
|
|
||||||
}
|
|
||||||
@property BOOL enableLogging;
|
@property BOOL enableLogging;
|
||||||
@property BOOL enableVerboseLogging;
|
@property BOOL enableVerboseLogging;
|
||||||
@property (assign) SwiftMainDelegate *swiftRuntime;
|
@property (assign) SwiftMainDelegate *swiftRuntime;
|
||||||
@@ -118,12 +93,7 @@ void setGlobalRouterIsRunning(bool running);
|
|||||||
- (void) applicationDidFinishLaunching:(NSNotification *)aNotification;
|
- (void) applicationDidFinishLaunching:(NSNotification *)aNotification;
|
||||||
- (void) applicationWillTerminate:(NSNotification *)aNotification;
|
- (void) applicationWillTerminate:(NSNotification *)aNotification;
|
||||||
- (void) setApplicationDefaultPreferences;
|
- (void) setApplicationDefaultPreferences;
|
||||||
- (void) userChooseJavaHome;
|
|
||||||
- (AppDelegate *) initWithArgc:(int)argc argv:(const char **)argv;
|
- (AppDelegate *) initWithArgc:(int)argc argv:(const char **)argv;
|
||||||
#ifdef __cplusplus
|
|
||||||
- (void) startupI2PRouter;
|
|
||||||
- (NSString *) userSelectJavaHome:(JvmListPtr)rawJvmList;
|
|
||||||
#endif
|
|
||||||
- (BOOL) userNotificationCenter:(NSUserNotificationCenter *)center
|
- (BOOL) userNotificationCenter:(NSUserNotificationCenter *)center
|
||||||
shouldPresentNotification:(NSUserNotification *)notification;
|
shouldPresentNotification:(NSUserNotification *)notification;
|
||||||
@end
|
@end
|
||||||
|
@@ -26,29 +26,29 @@ import AppKit
|
|||||||
}
|
}
|
||||||
|
|
||||||
@objc func getRouterIsRunning() -> Bool {
|
@objc func getRouterIsRunning() -> Bool {
|
||||||
if (RouterProcessStatus.isRouterRunning) {
|
return RouterProcessStatus.isRouterRunning
|
||||||
return false;
|
|
||||||
} else {
|
|
||||||
let running: Bool = RouterProcessStatus.isRouterRunning
|
|
||||||
return running
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@objc func getJavaHome() -> String {
|
@objc func getJavaHome() -> String {
|
||||||
return RouterProcessStatus.knownJavaBinPath!
|
return RouterProcessStatus.knownJavaBinPath!
|
||||||
}
|
}
|
||||||
|
|
||||||
@objc func setJavaHome(_ home: String) {
|
|
||||||
NSLog("Setting known java to %s", home)
|
|
||||||
RouterProcessStatus.knownJavaBinPath = home
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
extension RouterProcessStatus {
|
extension RouterProcessStatus {
|
||||||
static var isRouterRunning : Bool = false
|
static var isRouterRunning : Bool = false
|
||||||
static var isRouterChildProcess : Bool = false
|
static var isRouterChildProcess : Bool = false
|
||||||
static var routerVersion : String? = Optional.none
|
static var routerVersion : String? = Optional.none
|
||||||
static var routerUptime : String? = Optional.none
|
static var routerUptime : String? = Optional.none{
|
||||||
|
//Called before the change
|
||||||
|
willSet(newValue){
|
||||||
|
print("RouterProcessStatus.routerUptime will change from ", (self.routerUptime ?? "nil"), " to "+(newValue ?? "nil"))
|
||||||
|
}
|
||||||
|
|
||||||
|
//Called after the change
|
||||||
|
didSet{
|
||||||
|
print("RouterProcessStatus.routerUptime did change to "+self.routerUptime!)
|
||||||
|
}
|
||||||
|
}
|
||||||
static var routerStartedAt : Date? = Optional.none
|
static var routerStartedAt : Date? = Optional.none
|
||||||
static var knownJavaBinPath : String? = Optional.none
|
static var knownJavaBinPath : String? = Optional.none
|
||||||
static var i2pDirectoryPath : String = NSHomeDirectory() + "/Library/I2P"
|
static var i2pDirectoryPath : String = NSHomeDirectory() + "/Library/I2P"
|
||||||
|
@@ -1,167 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
#ifdef __cplusplus
|
|
||||||
|
|
||||||
#include <memory.h>
|
|
||||||
#include <string.h>
|
|
||||||
#include <stdlib.h>
|
|
||||||
|
|
||||||
#include <Foundation/Foundation.h>
|
|
||||||
#include <CoreFoundation/CoreFoundation.h>
|
|
||||||
#include <CoreFoundation/CFStream.h>
|
|
||||||
#include <CoreFoundation/CFPropertyList.h>
|
|
||||||
#include <CoreFoundation/CFDictionary.h>
|
|
||||||
#include <CoreFoundation/CFArray.h>
|
|
||||||
#include <CoreFoundation/CFString.h>
|
|
||||||
|
|
||||||
#include "RouterTask.h"
|
|
||||||
|
|
||||||
|
|
||||||
#define DEF_MIN_JVM_VER "1.7+"
|
|
||||||
|
|
||||||
#include "include/strutil.hpp"
|
|
||||||
|
|
||||||
#include <functional>
|
|
||||||
#include <memory>
|
|
||||||
#include <list>
|
|
||||||
|
|
||||||
|
|
||||||
class JvmVersion
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
std::string JVMName;
|
|
||||||
std::string JVMHomePath;
|
|
||||||
std::string JVMPlatformVersion;
|
|
||||||
|
|
||||||
inline const char * ToCString()
|
|
||||||
{
|
|
||||||
std::stringstream ss;
|
|
||||||
ss << "JvmVersion(name=" << JVMName.c_str() << ",version=";
|
|
||||||
ss << JVMPlatformVersion.c_str() << ",home=" << JVMHomePath.c_str() << ")";
|
|
||||||
std::string s = ss.str();
|
|
||||||
return s.c_str();
|
|
||||||
}
|
|
||||||
|
|
||||||
inline bool HasContent()
|
|
||||||
{
|
|
||||||
return (
|
|
||||||
std::strlen(JVMName.c_str()) > 0 &&
|
|
||||||
std::strlen(JVMHomePath.c_str()) > 0 &&
|
|
||||||
std::strlen(JVMPlatformVersion.c_str()) > 0
|
|
||||||
);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
typedef std::shared_ptr<JvmVersion> JvmVersionPtr;
|
|
||||||
typedef std::shared_ptr<std::list<JvmVersionPtr> > JvmListPtr;
|
|
||||||
typedef std::shared_ptr<std::list<std::shared_ptr<JvmVersion> > > JvmListSharedPtr;
|
|
||||||
typedef void(^MenuBarControllerActionBlock)(BOOL active);
|
|
||||||
|
|
||||||
extern JvmListSharedPtr gRawJvmList;
|
|
||||||
|
|
||||||
class JvmHomeContext : public std::enable_shared_from_this<JvmHomeContext>
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
|
|
||||||
inline void setJvm(JvmVersionPtr* current)
|
|
||||||
{
|
|
||||||
mCurrent = *current;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline JvmListPtr getJvmList()
|
|
||||||
{
|
|
||||||
return gRawJvmList;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline std::shared_ptr<JvmHomeContext> getContext()
|
|
||||||
{
|
|
||||||
return shared_from_this();
|
|
||||||
}
|
|
||||||
|
|
||||||
inline std::string getJavaHome()
|
|
||||||
{
|
|
||||||
if (mCurrent)
|
|
||||||
{
|
|
||||||
return mCurrent->JVMHomePath;
|
|
||||||
}
|
|
||||||
return gRawJvmList->back()->JVMHomePath;
|
|
||||||
}
|
|
||||||
private:
|
|
||||||
JvmVersionPtr mCurrent;
|
|
||||||
};
|
|
||||||
|
|
||||||
static void processJvmEntry (const void* key, const void* value, void* context) {
|
|
||||||
//CFShow(key);
|
|
||||||
//CFShow(value);
|
|
||||||
|
|
||||||
// The reason for using strprintf is to "force" a copy of the values,
|
|
||||||
// since local variables gets deleted once this function returns.
|
|
||||||
auto currentJvm = reinterpret_cast<JvmVersion*>(context);
|
|
||||||
if (CFEqual((CFStringRef)key,CFSTR("JVMName"))) {
|
|
||||||
auto strVal = extractString((CFStringRef)value);
|
|
||||||
currentJvm->JVMName = strprintf("%s",strVal.c_str());
|
|
||||||
}
|
|
||||||
if (CFEqual((CFStringRef)key,CFSTR("JVMHomePath"))) {
|
|
||||||
auto strVal = extractString((CFStringRef)value);
|
|
||||||
currentJvm->JVMHomePath = strprintf("%s",strVal.c_str());
|
|
||||||
}
|
|
||||||
if (CFEqual((CFStringRef)key,CFSTR("JVMPlatformVersion"))) {
|
|
||||||
auto strVal = extractString((CFStringRef)value);
|
|
||||||
currentJvm->JVMPlatformVersion = strprintf("%s",strVal.c_str());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
static void processJvmPlistEntries (const void* item, void* context) {
|
|
||||||
CFDictionaryRef dict = CFDictionaryCreateCopy(kCFAllocatorDefault, (CFDictionaryRef)item);
|
|
||||||
|
|
||||||
JvmVersionPtr currentJvmPtr = std::shared_ptr<JvmVersion>(new JvmVersion());
|
|
||||||
struct CFunctional
|
|
||||||
{
|
|
||||||
static void applier(const void* key, const void* value, void* context){
|
|
||||||
// The reason for using strprintf is to "force" a copy of the values,
|
|
||||||
// since local variables gets deleted once this function returns.
|
|
||||||
auto currentJvm = static_cast<JvmVersion*>(context);
|
|
||||||
if (CFEqual((CFStringRef)key,CFSTR("JVMName"))) {
|
|
||||||
auto d = extractString((CFStringRef)value);
|
|
||||||
currentJvm->JVMName = trim_copy(d);
|
|
||||||
}
|
|
||||||
if (CFEqual((CFStringRef)key,CFSTR("JVMHomePath"))) {
|
|
||||||
auto d = extractString((CFStringRef)value);
|
|
||||||
currentJvm->JVMHomePath = trim_copy(d);
|
|
||||||
}
|
|
||||||
if (CFEqual((CFStringRef)key,CFSTR("JVMPlatformVersion"))) {
|
|
||||||
auto d = extractString((CFStringRef)value);
|
|
||||||
currentJvm->JVMPlatformVersion = trim_copy(d);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
CFDictionaryApplyFunction(dict, CFunctional::applier, (void*)currentJvmPtr.get());
|
|
||||||
|
|
||||||
if (currentJvmPtr->HasContent())
|
|
||||||
{
|
|
||||||
printf("Found JVM: %s\n\n", currentJvmPtr->ToCString());
|
|
||||||
gRawJvmList->push_back(currentJvmPtr);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static void listAllJavaInstallsAvailable()
|
|
||||||
{
|
|
||||||
auto javaHomeRes = check_output({"/usr/libexec/java_home","-v",DEF_MIN_JVM_VER,"-X"});
|
|
||||||
CFDataRef javaHomes = CFDataCreate(NULL, (const UInt8 *)javaHomeRes.buf.data(), strlen(javaHomeRes.buf.data()));
|
|
||||||
|
|
||||||
CFPropertyListRef propertyList = CFPropertyListCreateWithData(kCFAllocatorDefault, javaHomes, kCFPropertyListImmutable, NULL, NULL);
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
auto jCount = CFArrayGetCount((CFArrayRef)propertyList);
|
|
||||||
|
|
||||||
CFArrayApplyFunction((CFArrayRef)propertyList, CFRangeMake(0, jCount), processJvmPlistEntries, NULL);
|
|
||||||
//CFShow(propertyList);
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif
|
|
@@ -2,19 +2,13 @@
|
|||||||
|
|
||||||
#include <dispatch/dispatch.h>
|
#include <dispatch/dispatch.h>
|
||||||
#include <memory.h>
|
#include <memory.h>
|
||||||
#include <string.h>
|
|
||||||
|
|
||||||
#include <Cocoa/Cocoa.h>
|
#include <Cocoa/Cocoa.h>
|
||||||
#import <AppKit/AppKit.h>
|
#import <AppKit/AppKit.h>
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
#include "include/subprocess.hpp"
|
#include <vector>
|
||||||
|
#include <string>
|
||||||
using namespace subprocess;
|
|
||||||
class JavaRunner;
|
|
||||||
|
|
||||||
typedef std::function<void(void)> fp_t;
|
|
||||||
typedef std::function<void(JavaRunner *ptr)> fp_proc_t;
|
|
||||||
|
|
||||||
const std::vector<NSString*> defaultStartupFlags {
|
const std::vector<NSString*> defaultStartupFlags {
|
||||||
@"-Xmx512M",
|
@"-Xmx512M",
|
||||||
@@ -32,31 +26,6 @@ const std::vector<std::string> defaultFlagsForExtractorJob {
|
|||||||
"-Djava.awt.headless=true"
|
"-Djava.awt.headless=true"
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* class JavaRunner
|
|
||||||
*
|
|
||||||
**/
|
|
||||||
class JavaRunner
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
// copy fn
|
|
||||||
JavaRunner(std::string& javaBin, std::string& arguments, std::string& i2pBaseDir, const fp_proc_t& executingFn, const fp_t& cb);
|
|
||||||
~JavaRunner() = default;
|
|
||||||
|
|
||||||
void requestRouterShutdown();
|
|
||||||
|
|
||||||
std::future<int> execute();
|
|
||||||
std::shared_ptr<subprocess::Popen> javaProcess;
|
|
||||||
std::string javaBinaryPath;
|
|
||||||
std::string javaRouterArgs;
|
|
||||||
std::string execLine;
|
|
||||||
std::string _i2pBaseDir;
|
|
||||||
private:
|
|
||||||
const fp_proc_t& executingFn;
|
|
||||||
const fp_t& exitCallbackFn;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
@@ -9,6 +9,7 @@
|
|||||||
#import "I2PLauncher-Swift.h"
|
#import "I2PLauncher-Swift.h"
|
||||||
#include "AppDelegate.h"
|
#include "AppDelegate.h"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#include "include/PidWatcher.h"
|
#include "include/PidWatcher.h"
|
||||||
|
|
||||||
#import <AppKit/AppKit.h>
|
#import <AppKit/AppKit.h>
|
||||||
@@ -52,23 +53,13 @@
|
|||||||
[stdoutFileHandle waitForDataInBackgroundAndNotify];
|
[stdoutFileHandle waitForDataInBackgroundAndNotify];
|
||||||
|
|
||||||
[self.routerTask setTerminationHandler:^(NSTask* task) {
|
[self.routerTask setTerminationHandler:^(NSTask* task) {
|
||||||
|
// Cleanup
|
||||||
NSLog(@"termHandler triggered!");
|
NSLog(@"termHandler triggered!");
|
||||||
auto swiftRouterStatus = [[RouterProcessStatus alloc] init];
|
auto swiftRouterStatus = [[RouterProcessStatus alloc] init];
|
||||||
[swiftRouterStatus setRouterStatus: true];
|
[swiftRouterStatus setRouterStatus: false];
|
||||||
|
[swiftRouterStatus setRouterRanByUs: false];
|
||||||
sendUserNotification(APP_IDSTR, @"I2P Router has stopped");
|
sendUserNotification(APP_IDSTR, @"I2P Router has stopped");
|
||||||
// Cleanup
|
|
||||||
//self.isRouterRunning = NO;
|
|
||||||
}];
|
}];
|
||||||
/*
|
|
||||||
self.readLogHandle = [self.processPipe fileHandleForReading];
|
|
||||||
NSData *inData = nil;
|
|
||||||
self.totalLogData = [[[NSMutableData alloc] init] autorelease];
|
|
||||||
|
|
||||||
while ((inData = [self.readLogHandle availableData]) &&
|
|
||||||
[inData length]) {
|
|
||||||
[self.totalLogData appendData:inData];
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
return self;
|
return self;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -91,63 +82,25 @@
|
|||||||
- (int) execute
|
- (int) execute
|
||||||
{
|
{
|
||||||
@try {
|
@try {
|
||||||
[self.routerTask launch];
|
[self.routerTask launch];
|
||||||
watchPid([self.routerTask processIdentifier]);
|
watchPid([self.routerTask processIdentifier]);
|
||||||
self.isRouterRunning = YES;
|
self.isRouterRunning = YES;
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
@catch (NSException *e)
|
@catch (NSException *e)
|
||||||
{
|
{
|
||||||
NSLog(@"Expection occurred %@", [e reason]);
|
NSLog(@"Expection occurred %@", [e reason]);
|
||||||
return 0;
|
auto swiftRouterStatus = [[RouterProcessStatus alloc] init];
|
||||||
|
[swiftRouterStatus setRouterStatus: false];
|
||||||
|
[swiftRouterStatus setRouterRanByUs: false];
|
||||||
|
sendUserNotification(@"An error occured, can't start the I2P Router", [e reason]);
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
- (int) getPID
|
- (int) getPID
|
||||||
{
|
{
|
||||||
return [self.routerTask processIdentifier];
|
return [self.routerTask processIdentifier];
|
||||||
}
|
}
|
||||||
|
|
||||||
@end
|
@end
|
||||||
|
|
||||||
#ifdef __cplusplus
|
|
||||||
|
|
||||||
JavaRunner::JavaRunner(std::string& javaBin, std::string& arguments, std::string& i2pBaseDir, const fp_proc_t& execFn, const fp_t& cb)
|
|
||||||
: javaBinaryPath(javaBin), javaRouterArgs(arguments), _i2pBaseDir(i2pBaseDir), executingFn(execFn), exitCallbackFn(cb)
|
|
||||||
{
|
|
||||||
execLine = javaBinaryPath;
|
|
||||||
execLine += " " + std::string(javaRouterArgs.c_str());
|
|
||||||
printf("CLI: %s\n",execLine.c_str());
|
|
||||||
javaProcess = std::shared_ptr<Popen>(new Popen(execLine, environment{{
|
|
||||||
{"I2PBASE", _i2pBaseDir},
|
|
||||||
{"JAVA_OPTS", getenv("JAVA_OPTS")}
|
|
||||||
}}, defer_spawn{true}));
|
|
||||||
}
|
|
||||||
|
|
||||||
void JavaRunner::requestRouterShutdown()
|
|
||||||
{
|
|
||||||
// SIGHUP
|
|
||||||
javaProcess->kill(1);
|
|
||||||
}
|
|
||||||
|
|
||||||
std::future<int> JavaRunner::execute()
|
|
||||||
{
|
|
||||||
try {
|
|
||||||
auto executingFn = dispatch_block_create(DISPATCH_BLOCK_INHERIT_QOS_CLASS, ^{
|
|
||||||
this->executingFn(this);
|
|
||||||
});
|
|
||||||
dispatch_async(dispatch_get_global_queue( DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), executingFn);
|
|
||||||
dispatch_block_wait(executingFn, DISPATCH_TIME_FOREVER);
|
|
||||||
|
|
||||||
// Here, the process is done executing.
|
|
||||||
|
|
||||||
printf("Finished executingFn - Runs callbackFn\n");
|
|
||||||
this->exitCallbackFn();
|
|
||||||
return std::async(std::launch::async, []{ return 0; });
|
|
||||||
} catch (std::exception* ex) {
|
|
||||||
printf("ERROR: %s\n", ex->what());
|
|
||||||
return std::async(std::launch::async, []{ return 1; });
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
@@ -7,6 +7,51 @@
|
|||||||
//
|
//
|
||||||
|
|
||||||
#import <Foundation/Foundation.h>
|
#import <Foundation/Foundation.h>
|
||||||
|
#import <Cocoa/Cocoa.h>
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
#include <memory>
|
||||||
|
#include <future>
|
||||||
|
#include <glob.h>
|
||||||
|
#include <string>
|
||||||
|
#include <vector>
|
||||||
|
#include "include/fn.h"
|
||||||
|
std::future<int> startupRouter(NSString* javaBin, NSArray<NSString*>* arguments, NSString* i2pBaseDir);
|
||||||
|
|
||||||
|
|
||||||
|
namespace osx {
|
||||||
|
inline void openUrl(NSString* url)
|
||||||
|
{
|
||||||
|
[[NSWorkspace sharedWorkspace] openURL:[NSURL URLWithString: url]];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
inline std::vector<std::string> globVector(const std::string& pattern){
|
||||||
|
glob_t glob_result;
|
||||||
|
glob(pattern.c_str(),GLOB_TILDE,NULL,&glob_result);
|
||||||
|
std::vector<std::string> files;
|
||||||
|
for(unsigned int i=0;i<glob_result.gl_pathc;++i){
|
||||||
|
files.push_back(std::string(glob_result.gl_pathv[i]));
|
||||||
|
}
|
||||||
|
globfree(&glob_result);
|
||||||
|
return files;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline std::string buildClassPathForObjC(std::string basePath)
|
||||||
|
{
|
||||||
|
NSBundle *launcherBundle = [NSBundle mainBundle];
|
||||||
|
auto jarList = globVector(basePath+std::string("/lib/*.jar"));
|
||||||
|
|
||||||
|
std::string classpathStrHead = "-classpath";
|
||||||
|
std::string classpathStr = "";
|
||||||
|
classpathStr += [[launcherBundle pathForResource:@"launcher" ofType:@"jar"] UTF8String];
|
||||||
|
std::string prefix(basePath);
|
||||||
|
prefix += "/lib/";
|
||||||
|
for_each(jarList, [&classpathStr](std::string str){ classpathStr += std::string(":") + str; });
|
||||||
|
return classpathStr;
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
@interface SBridge : NSObject
|
@interface SBridge : NSObject
|
||||||
- (NSString*) buildClassPath:(NSString*)i2pPath;
|
- (NSString*) buildClassPath:(NSString*)i2pPath;
|
||||||
|
@@ -33,8 +33,6 @@ std::future<int> startupRouter(NSString* javaBin, NSArray<NSString*>* arguments,
|
|||||||
options.arguments = arguments;
|
options.arguments = arguments;
|
||||||
options.i2pBaseDir = i2pBaseDir;
|
options.i2pBaseDir = i2pBaseDir;
|
||||||
auto instance = [[I2PRouterTask alloc] initWithOptions: options];
|
auto instance = [[I2PRouterTask alloc] initWithOptions: options];
|
||||||
//setGlobalRouterObject(instance);
|
|
||||||
//NSThread *thr = [[NSThread alloc] initWithTarget:instance selector:@selector(execute) object:nil];
|
|
||||||
[instance execute];
|
[instance execute];
|
||||||
sendUserNotification(APP_IDSTR, @"The I2P router is starting up.");
|
sendUserNotification(APP_IDSTR, @"The I2P router is starting up.");
|
||||||
auto pid = [instance getPID];
|
auto pid = [instance getPID];
|
||||||
@@ -53,37 +51,6 @@ std::future<int> startupRouter(NSString* javaBin, NSArray<NSString*>* arguments,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
namespace osx {
|
|
||||||
inline void openUrl(NSString* url)
|
|
||||||
{
|
|
||||||
[[NSWorkspace sharedWorkspace] openURL:[NSURL URLWithString: url]];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
inline std::vector<std::string> globVector(const std::string& pattern){
|
|
||||||
glob_t glob_result;
|
|
||||||
glob(pattern.c_str(),GLOB_TILDE,NULL,&glob_result);
|
|
||||||
std::vector<std::string> files;
|
|
||||||
for(unsigned int i=0;i<glob_result.gl_pathc;++i){
|
|
||||||
files.push_back(std::string(glob_result.gl_pathv[i]));
|
|
||||||
}
|
|
||||||
globfree(&glob_result);
|
|
||||||
return files;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline std::string buildClassPathForObjC(std::string basePath)
|
|
||||||
{
|
|
||||||
NSBundle *launcherBundle = [NSBundle mainBundle];
|
|
||||||
auto jarList = globVector(basePath+std::string("/lib/*.jar"));
|
|
||||||
|
|
||||||
std::string classpathStrHead = "-classpath";
|
|
||||||
std::string classpathStr = "";
|
|
||||||
classpathStr += [[launcherBundle pathForResource:@"launcher" ofType:@"jar"] UTF8String];
|
|
||||||
std::string prefix(basePath);
|
|
||||||
prefix += "/lib/";
|
|
||||||
for_each(jarList, [&classpathStr](std::string str){ classpathStr += std::string(":") + str; });
|
|
||||||
return classpathStr;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
@implementation SBridge
|
@implementation SBridge
|
||||||
|
@@ -11,14 +11,6 @@
|
|||||||
|
|
||||||
#import <Foundation/Foundation.h>
|
#import <Foundation/Foundation.h>
|
||||||
#import <Foundation/NSFileManager.h>
|
#import <Foundation/NSFileManager.h>
|
||||||
|
|
||||||
|
|
||||||
#include <CoreFoundation/CoreFoundation.h>
|
|
||||||
#include <CoreFoundation/CFStream.h>
|
|
||||||
#include <CoreFoundation/CFPropertyList.h>
|
|
||||||
#include <CoreFoundation/CFDictionary.h>
|
|
||||||
#include <CoreFoundation/CFArray.h>
|
|
||||||
#include <CoreFoundation/CFString.h>
|
|
||||||
#include <CoreFoundation/CFPreferences.h>
|
#include <CoreFoundation/CFPreferences.h>
|
||||||
|
|
||||||
#import <objc/Object.h>
|
#import <objc/Object.h>
|
||||||
@@ -30,7 +22,6 @@
|
|||||||
|
|
||||||
#include "AppDelegate.h"
|
#include "AppDelegate.h"
|
||||||
#include "RouterTask.h"
|
#include "RouterTask.h"
|
||||||
#include "JavaHelper.h"
|
|
||||||
#include "include/fn.h"
|
#include "include/fn.h"
|
||||||
#include "include/portcheck.h"
|
#include "include/portcheck.h"
|
||||||
#import "SBridge.h"
|
#import "SBridge.h"
|
||||||
@@ -111,13 +102,6 @@ using namespace subprocess;
|
|||||||
cli.push_back(jarfile);
|
cli.push_back(jarfile);
|
||||||
cli.push_back("net.i2p.launchers.BaseExtractor");
|
cli.push_back("net.i2p.launchers.BaseExtractor");
|
||||||
auto rs = [[RouterProcessStatus alloc] init];
|
auto rs = [[RouterProcessStatus alloc] init];
|
||||||
NSString* jh = [rs getJavaHome];
|
|
||||||
if (jh != nil) {
|
|
||||||
NSLog(@"jh er %@", jh);
|
|
||||||
}
|
|
||||||
|
|
||||||
NSString* newString = [NSString stringWithFormat:@"file://%@", rs.getJavaHome];
|
|
||||||
NSURL *baseURL = [NSURL fileURLWithPath:newString];
|
|
||||||
|
|
||||||
std::string execStr = std::string([rs.getJavaHome UTF8String]);
|
std::string execStr = std::string([rs.getJavaHome UTF8String]);
|
||||||
for_each(cli, [&execStr](std::string str){ execStr += std::string(" ") + str; });
|
for_each(cli, [&execStr](std::string str){ execStr += std::string(" ") + str; });
|
||||||
@@ -132,9 +116,7 @@ using namespace subprocess;
|
|||||||
NSLog(@"Extraction exit code %@",[NSString stringWithUTF8String:(std::to_string(extractStatus)).c_str()]);
|
NSLog(@"Extraction exit code %@",[NSString stringWithUTF8String:(std::to_string(extractStatus)).c_str()]);
|
||||||
if (extractStatus == 0)
|
if (extractStatus == 0)
|
||||||
{
|
{
|
||||||
//success = YES;
|
NSLog(@"Extraction complete!");
|
||||||
NSLog(@"Time to detect I2P version in install directory");
|
|
||||||
[self.swiftRuntime findInstalledI2PVersion];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
} catch (subprocess::OSError &err) {
|
} catch (subprocess::OSError &err) {
|
||||||
@@ -146,7 +128,6 @@ using namespace subprocess;
|
|||||||
|
|
||||||
// All done. Assume success and error are already set.
|
// All done. Assume success and error are already set.
|
||||||
dispatch_async(dispatch_get_main_queue(), ^{
|
dispatch_async(dispatch_get_main_queue(), ^{
|
||||||
//sendUserNotification(APP_IDSTR, @"Extraction complete!", self.contentImage);
|
|
||||||
if (completion) {
|
if (completion) {
|
||||||
completion(success, error);
|
completion(success, error);
|
||||||
}
|
}
|
||||||
@@ -158,45 +139,15 @@ using namespace subprocess;
|
|||||||
NSLog(@"Exception: %@", errMsg);
|
NSLog(@"Exception: %@", errMsg);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
- (NSString *)userSelectJavaHome:(JvmListPtr)rawJvmList
|
|
||||||
{
|
|
||||||
NSString *appleScriptString = @"set jvmlist to {\"Newest\"";
|
|
||||||
for (auto item : *rawJvmList) {
|
|
||||||
auto str = strprintf(",\"%s\"", item->JVMName.c_str()).c_str();
|
|
||||||
NSString* tmp = [NSString stringWithUTF8String:str];
|
|
||||||
appleScriptString = [appleScriptString stringByAppendingString:tmp];
|
|
||||||
}
|
|
||||||
appleScriptString = [appleScriptString stringByAppendingString:@"}\nchoose from list jvmlist\n"];
|
|
||||||
NSAppleScript *theScript = [[NSAppleScript alloc] initWithSource:appleScriptString];
|
|
||||||
NSDictionary *theError = nil;
|
|
||||||
NSString* userResult = [[theScript executeAndReturnError: &theError] stringValue];
|
|
||||||
NSLog(@"User choosed %@.\n", userResult);
|
|
||||||
if (theError != nil)
|
|
||||||
{
|
|
||||||
NSLog(@"Error: %@.\n", theError);
|
|
||||||
}
|
|
||||||
return userResult;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
- (void)setApplicationDefaultPreferences {
|
- (void)setApplicationDefaultPreferences {
|
||||||
auto defaultJVMHome = check_output({"/usr/libexec/java_home","-v",DEF_MIN_JVM_VER});
|
|
||||||
auto tmpStdStr = std::string(defaultJVMHome.buf.data());
|
|
||||||
trim(tmpStdStr);
|
|
||||||
auto cfDefaultHome = CFStringCreateWithCString(NULL, const_cast<const char *>(tmpStdStr.c_str()), kCFStringEncodingUTF8);
|
|
||||||
[self.userPreferences registerDefaults:@{
|
[self.userPreferences registerDefaults:@{
|
||||||
@"javaHome" : (NSString *)cfDefaultHome,
|
|
||||||
@"lastI2PVersion" : (NSString *)CFSTR(DEF_I2P_VERSION),
|
|
||||||
@"enableLogging": @YES,
|
@"enableLogging": @YES,
|
||||||
@"enableVerboseLogging": @YES,
|
@"enableVerboseLogging": @YES,
|
||||||
@"autoStartRouter": @YES,
|
@"autoStartRouter": @YES,
|
||||||
@"i2pBaseDirectory": (NSString *)CFStringCreateWithCString(NULL, const_cast<const char *>(getDefaultBaseDir().c_str()), kCFStringEncodingUTF8)
|
@"i2pBaseDirectory": (NSString *)CFStringCreateWithCString(NULL, const_cast<const char *>(getDefaultBaseDir().c_str()), kCFStringEncodingUTF8)
|
||||||
}];
|
}];
|
||||||
if (self.enableVerboseLogging) NSLog(@"Default JVM home preference set to: %@", cfDefaultHome);
|
|
||||||
|
|
||||||
auto dict = [self.userPreferences dictionaryRepresentation];
|
auto dict = [self.userPreferences dictionaryRepresentation];
|
||||||
[self.userPreferences setPersistentDomain:dict forName:NSAPPDOMAIN];
|
[self.userPreferences setPersistentDomain:dict forName:NSAPPDOMAIN];
|
||||||
@@ -205,10 +156,9 @@ using namespace subprocess;
|
|||||||
CFPreferencesAppSynchronize(kCFPreferencesCurrentApplication);
|
CFPreferencesAppSynchronize(kCFPreferencesCurrentApplication);
|
||||||
|
|
||||||
if (self.enableVerboseLogging) NSLog(@"Default preferences stored!");
|
if (self.enableVerboseLogging) NSLog(@"Default preferences stored!");
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
- (void)applicationDidFinishLaunching:(NSNotification *)aNotification {
|
- (void)applicationDidFinishLaunching:(NSNotification *)aNotification {
|
||||||
@@ -231,7 +181,6 @@ using namespace subprocess;
|
|||||||
|
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
//gRawJvmList = std::make_shared<std::list<JvmVersionPtr> >(std::list<JvmVersionPtr>());
|
|
||||||
|
|
||||||
RouterProcessStatus* routerStatus = [[RouterProcessStatus alloc] init];
|
RouterProcessStatus* routerStatus = [[RouterProcessStatus alloc] init];
|
||||||
std::string i2pBaseDir(getDefaultBaseDir());
|
std::string i2pBaseDir(getDefaultBaseDir());
|
||||||
@@ -255,6 +204,7 @@ using namespace subprocess;
|
|||||||
|
|
||||||
|
|
||||||
NSBundle *launcherBundle = [NSBundle mainBundle];
|
NSBundle *launcherBundle = [NSBundle mainBundle];
|
||||||
|
auto sBridge = [[SBridge alloc] init];
|
||||||
|
|
||||||
// Helper object to hold statefull path information
|
// Helper object to hold statefull path information
|
||||||
self.metaInfo = [[ExtractMetaInfo alloc] init];
|
self.metaInfo = [[ExtractMetaInfo alloc] init];
|
||||||
@@ -269,8 +219,6 @@ using namespace subprocess;
|
|||||||
std::string jarfile("-cp ");
|
std::string jarfile("-cp ");
|
||||||
jarfile += [self.metaInfo.zipFile UTF8String];
|
jarfile += [self.metaInfo.zipFile UTF8String];
|
||||||
|
|
||||||
auto sBridge = [[SBridge alloc] init];
|
|
||||||
|
|
||||||
// Initialize the Swift environment (the UI components)
|
// Initialize the Swift environment (the UI components)
|
||||||
[self.swiftRuntime applicationDidFinishLaunching];
|
[self.swiftRuntime applicationDidFinishLaunching];
|
||||||
|
|
||||||
@@ -286,6 +234,8 @@ using namespace subprocess;
|
|||||||
sendUserNotification(@"I2P is done extracting", @"I2P is now installed and ready to run!");
|
sendUserNotification(@"I2P is done extracting", @"I2P is now installed and ready to run!");
|
||||||
NSLog(@"Done extracting I2P");
|
NSLog(@"Done extracting I2P");
|
||||||
|
|
||||||
|
NSLog(@"Time to detect I2P version in install directory");
|
||||||
|
[self.swiftRuntime findInstalledI2PVersion];
|
||||||
if (shouldAutoStartRouter) {
|
if (shouldAutoStartRouter) {
|
||||||
[sBridge startupI2PRouter:self.metaInfo.i2pBase javaBinPath:self.metaInfo.javaBinary];
|
[sBridge startupI2PRouter:self.metaInfo.i2pBase javaBinPath:self.metaInfo.javaBinary];
|
||||||
[routerStatus setRouterRanByUs: true];
|
[routerStatus setRouterRanByUs: true];
|
||||||
@@ -294,6 +244,8 @@ using namespace subprocess;
|
|||||||
|
|
||||||
} else {
|
} else {
|
||||||
// I2P was already found extracted
|
// I2P was already found extracted
|
||||||
|
NSLog(@"Time to detect I2P version in install directory");
|
||||||
|
[self.swiftRuntime findInstalledI2PVersion];
|
||||||
|
|
||||||
if (shouldAutoStartRouter) {
|
if (shouldAutoStartRouter) {
|
||||||
[sBridge startupI2PRouter:self.metaInfo.i2pBase javaBinPath:self.metaInfo.javaBinary];
|
[sBridge startupI2PRouter:self.metaInfo.i2pBase javaBinPath:self.metaInfo.javaBinary];
|
||||||
|
Reference in New Issue
Block a user