diff --git a/build.xml b/build.xml
index 19e66aa236fe906f7e595da4fa9719cba0e91dd9..5a89b01233e548b6ee83400b464ade88be6e9d15 100644
--- a/build.xml
+++ b/build.xml
@@ -31,8 +31,6 @@
         <echo message="  installer-windows: build the GUI installer (Windows only)" />
         <echo message="  installer-nowindows: build the GUI installer (all but Windows)" />
         <echo message="  installer5, installer5-linux, installer5-nowindows, installer5-windows: use IzPack 5" />
-        <echo message="  osxLauncher: build the Mac OS X router/GUI launcher (OSX only)" />
-        <echo message="  bbLauncher: build the Browser Bundle router launcher" />
         <echo message="  bundle:    (GIT ONLY!) generate a git bundle and a corresponding torrent." />
         <echo message="  tarball:   tar the full install into i2p.tar.bz2 (extracts to build a new clean install)" />
         <echo message="  git-bundle:    (GIT ONLY!) generate a git bundle and a corresponding torrent." />
@@ -313,28 +311,6 @@
         <echo message="Epoch is: ${epoch}" />
     </target>
 
-    <target name="bbLauncher" depends="build">
-        <sequential>
-            <exec executable="./sbt" dir="launchers" failonerror="true">
-                <arg value="browserbundle:clean" />
-            </exec>
-            <exec executable="./sbt" dir="launchers" failonerror="true">
-                <arg value="browserbundle:assembly" />
-            </exec>
-        </sequential>
-    </target>
-
-    <target name="osxLauncher" depends="build,preppkg-osx">
-        <sequential>
-            <exec executable="./sbt" dir="launchers" failonerror="true">
-                <arg value="macosx:cleanAllTask" />
-            </exec>
-            <exec executable="./sbt" dir="launchers" failonerror="true">
-                <arg value="macosx:buildAppBundleTask" />
-            </exec>
-        </sequential>
-    </target>
-
     <target name="buildBOB" depends="buildMinistreaming" >
         <ant dir="apps/BOB/" target="jar" />
         <copy file="apps/BOB/dist/BOB.jar" todir="build/" />
@@ -2804,7 +2780,6 @@
             <fileset dir="../i2p-${Extended.Version}/" includes="Docker*" />
             <file name="../i2p-${Extended.Version}/Makefile.gcj" />
             <fileset dir="../i2p-${Extended.Version}/docs" />
-            <fileset dir="../i2p-${Extended.Version}/launchers" />
             <file name="../i2p-${Extended.Version}/.travis.yml" />
             <file name="../i2p-${Extended.Version}/.gitignore" />
             <!-- gradle files -->
@@ -2881,7 +2856,6 @@
             <fileset dir="../i2p-${Extended.Version}/" includes="Docker*" />
             <file name="../i2p-${Extended.Version}/Makefile.gcj" />
             <fileset dir="../i2p-${Extended.Version}/docs" />
-            <fileset dir="../i2p-${Extended.Version}/launchers" />
             <file name="../i2p-${Extended.Version}/.travis.yml" />
             <file name="../i2p-${Extended.Version}/.gitignore" />
             <!-- gradle files -->
@@ -2961,7 +2935,6 @@
             <fileset dir="../i2p-${Extended.Version}/" includes="Docker*" />
             <file name="../i2p-${Extended.Version}/Makefile.gcj" />
             <fileset dir="../i2p-${Extended.Version}/docs" />
-            <fileset dir="../i2p-${Extended.Version}/launchers" />
             <file name="../i2p-${Extended.Version}/.travis.yml" />
             <file name="../i2p-${Extended.Version}/.gitignore" />
             <!-- gradle files -->
@@ -3028,7 +3001,6 @@
             <fileset dir="../i2p-${Extended.Version}/" includes="Docker*" />
             <file name="../i2p-${Extended.Version}/Makefile.gcj" />
             <fileset dir="../i2p-${Extended.Version}/docs" />
-            <fileset dir="../i2p-${Extended.Version}/launchers" />
             <file name="../i2p-${Extended.Version}/.travis.yml" />
             <file name="../i2p-${Extended.Version}/.gitignore" />
             <!-- gradle files -->
diff --git a/launchers/README.md b/launchers/README.md
deleted file mode 100644
index 379b30e36c6cf107d4a72b994ec148434c71cf80..0000000000000000000000000000000000000000
--- a/launchers/README.md
+++ /dev/null
@@ -1,11 +0,0 @@
-# The Launcher
-
-Here you'll find the code for the next generation Mac OS X launcher, as well as the Browser Bundle i2p launcher.
-
-Anyway, if you wanna build it and have fun, just do `./sbt`
-
-Scala isn't scary - it's java except the ;;;;;;;; ;)
-
-https://www.scala-lang.org/
-https://www.scala-sbt.org/
-
diff --git a/launchers/browserbundle/README.md b/launchers/browserbundle/README.md
deleted file mode 100644
index 1b700698e1c1f4b89562e0f4eec4ab0e8ff3e075..0000000000000000000000000000000000000000
--- a/launchers/browserbundle/README.md
+++ /dev/null
@@ -1,5 +0,0 @@
-# The browser bundle i2p launcher
-
-This code won't really make any sense for other than in the portable i2p that's shipped with the browser bundle.
-
-
diff --git a/launchers/browserbundle/build.sbt b/launchers/browserbundle/build.sbt
deleted file mode 100644
index 376dfad51db5336d431257806fd6534989174b31..0000000000000000000000000000000000000000
--- a/launchers/browserbundle/build.sbt
+++ /dev/null
@@ -1,23 +0,0 @@
-
-
-
-assemblyExcludedJars in assembly := {
-  val donts = List(
-    "BOB.jar",
-    "sam.jar",
-    "desktopgui.jar",
-    "i2ptunnel-ui.jar",
-    "i2psnark.jar",
-    "jetty-sslengine.jar"
-  )
-  val cp = (fullClasspath in assembly).value
-  cp filter { s => donts.contains(s.data.getName)}
-}
-
-// Unmanaged base will be included in a fat jar
-unmanagedBase := baseDirectory.value / ".." / ".." / "build"
-
-// Unmanaged classpath will be available at compile time
-unmanagedClasspath in Compile ++= Seq(
-  baseDirectory.value / ".." / ".." / "build" / "*.jar"
-)
diff --git a/launchers/browserbundle/src/main/scala/net/i2p/RouterLauncherApp.scala b/launchers/browserbundle/src/main/scala/net/i2p/RouterLauncherApp.scala
deleted file mode 100644
index 092471f7173500b8859deb5de4ad9ee6a035f3f9..0000000000000000000000000000000000000000
--- a/launchers/browserbundle/src/main/scala/net/i2p/RouterLauncherApp.scala
+++ /dev/null
@@ -1,108 +0,0 @@
-package net.i2p
-
-import java.io.{File, InputStream}
-
-//import net.i2p.Router
-import net.i2p.launchers.DeployProfile
-
-/**
-  *
-  * For java developers:
-  * A scala object is like an instance of a class.
-  * If you define a method inside an object, it's equals to
-  * java's static methods.
-  *
-  * Also, in scala, the body of a class/object is executed as it's
-  * constructor.
-  *
-  * Also noteworthy;
-  * val is immutable
-  * var is mutable
-  *
-  *
-  * @author Meeh
-  * @version 0.0.1
-  * @since 0.9.35
-  */
-object RouterLauncherApp extends App {
-
-  def toBytes(xs: Int*) = xs.map(_.toByte).toArray
-
-  def getInt(bytes: Array[Byte]): Int = (bytes(3) << 24) & 0xff000000 | (bytes(2) << 16) & 0x00ff0000 | (bytes(1) << 8) & 0x0000ff00 | (bytes(0) << 0) & 0x000000ff
-
-  /**
-    * Encodes bytes in "binary form" as mentioned in Native Messaging in the WebExtension API.
-    * @param length
-    * @return
-    */
-  def getBytes(length: Int): Array[Byte] = {
-    val bytes = new Array[Byte](4)
-    bytes(0) = (length & 0xFF).toByte
-    bytes(1) = ((length >> 8) & 0xFF).toByte
-    bytes(2) = ((length >> 16) & 0xFF).toByte
-    bytes(3) = ((length >> 24) & 0xFF).toByte
-    bytes
-  }
-
-  def readMessage(in: InputStream): String = {
-    val arr = new Array[Byte](4)
-    in.read(arr)
-    val bytes = new Array[Byte](getInt(arr))
-    in.read(bytes)
-    new String(bytes, "UTF-8")
-  }
-
-  def sendMessage(message: String): Unit = {
-    System.out.write(getBytes(message.length))
-    System.out.write(message.getBytes("UTF-8"))
-  }
-
-  // Executed at launch
-  val basePath = Option(System.getProperty("i2p.dir.base")).getOrElse(System.getenv("I2PBASE"))
-  val configPath = Option(System.getProperty("i2p.dir.config")).getOrElse(System.getenv("I2PCONFIG"))
-
-  println(s"basePath => ${basePath}\nconfigPath => ${configPath}")
-/*
-  object ErrorUtils {
-    def errorMessageInJson(message: String, solution: String) : JObject = JObject(
-      List(
-        ("error",
-          JObject(
-            ("message", JString(message)),
-            ("solution", JString(solution))
-          )
-        )
-      )
-    )
-
-    def printError(message: String, solution: String): Unit = {
-      println(compact(render( errorMessageInJson(message,solution) )))
-    }
-
-    def printErrorAndExit(message: String, solution: String, exitCode: Int = 1): Unit = {
-      printError(message, solution)
-      System.exit(exitCode)
-    }
-  }
-
-  // Path related error checking
-  if (basePath == null || basePath.isEmpty) ErrorUtils.printErrorAndExit("I2P Base path is missing", "set property i2p.dir.base or environment variable I2PBASE")
-  if (configPath  == null || configPath.isEmpty) ErrorUtils.printErrorAndExit("I2P Config path is missing", "set property i2p.dir.config or environment variable I2PCONFIG")
-  if (!new File(basePath).exists()) ErrorUtils.printErrorAndExit("I2P Base path don't exist", "Reinstall the Browser Bundle")
-  if (!new File(configPath).exists()) ErrorUtils.printErrorAndExit("I2P Config path don't exist", "Delete your config directory for the Browser Bundle")
-
-*/
-  val deployer = new DeployProfile(configPath,basePath)
-  deployer.verifyExistenceOfConfig()
-
-  // Required/mocked properties
-  System.setProperty("wrapper.version", "portable-1")
-  System.setProperty("i2p.dir.portableMode", "true")
-  System.setProperty("loggerFilenameOverride", "router-@.log")
-
-  //ErrorUtils.printError(s"Starting up with arguments ${(args mkString ", ")}",":)")
-
-  //Router.main(args)
-}
-
-
diff --git a/launchers/build.sbt b/launchers/build.sbt
deleted file mode 100644
index 528b94432a8e8e7a415c2067dc0b6966dd53f7dc..0000000000000000000000000000000000000000
--- a/launchers/build.sbt
+++ /dev/null
@@ -1,58 +0,0 @@
-import sbt._
-import Keys._
-
-scalaVersion in Global := "2.11.11"
-
-resolvers ++= Seq(
-  DefaultMavenRepository,
-  Resolver.mavenLocal,
-  Resolver.sonatypeRepo("releases"),
-  Resolver.typesafeRepo("releases"),
-  Resolver.sbtPluginRepo("releases")
-)
-
-lazy val commonSettings = Seq(
-  organization := "net.i2p",
-  scalaVersion := "2.11.11", // We have to use Scala 11 as long as we're going to support JRE 1.7
-  version      := "0.1.0-SNAPSHOT",
-  maintainer := "Meeh <mikalv@mikalv.net>",
-  packageSummary := "The Invisible Internet Project",
-  packageDescription := "Blabla"
-)
-
-lazy val common = (project in file("common"))
-  .settings(
-    commonSettings,
-    name         := "LauncherCommon"
-  )
-
-lazy val browserbundle = (project in file("browserbundle"))
-  .settings(
-    commonSettings,
-    name         := "RouterLaunchApp",
-    assemblyJarName in assembly := s"${name.value}-${version.value}.jar",
-    mainClass in assembly := Some("net.i2p.RouterLauncherApp"),
-    libraryDependencies ++= Seq(
-      "org.json4s" %% "json4s-native" % "3.5.3"
-    )
-  ).dependsOn(common)
-
-lazy val macosx = (project in file("macosx"))
-  .settings(
-    commonSettings,
-    name         := "routerLauncher",
-    mainClass in assembly := Some("net.i2p.launchers.SimpleOSXLauncher")
-  ).dependsOn(common)
-
-
-lazy val root = (project in file("."))
-  .aggregate(common, browserbundle, macosx)
-
-javacOptions ++= Seq("-source", "1.7", "-target", "1.7")
-scalacOptions in Compile := Seq("-deprecated","-target:jvm-1.7")
-
-fork := true
-
-run / javaOptions += "-Xmx512M"
-run / connectInput := true
-
diff --git a/launchers/common/build.sbt b/launchers/common/build.sbt
deleted file mode 100644
index 72e0f112228d2cbd38c6e1b05619f73d2dde9fc4..0000000000000000000000000000000000000000
--- a/launchers/common/build.sbt
+++ /dev/null
@@ -1 +0,0 @@
-libraryDependencies += "org.xeustechnologies" % "jcl-core" % "2.8"
diff --git a/launchers/common/src/main/scala/net/i2p/launchers/CaseClasses.scala b/launchers/common/src/main/scala/net/i2p/launchers/CaseClasses.scala
deleted file mode 100644
index 31a522fa1555aeec28c810718371f9ab22ff84b6..0000000000000000000000000000000000000000
--- a/launchers/common/src/main/scala/net/i2p/launchers/CaseClasses.scala
+++ /dev/null
@@ -1,45 +0,0 @@
-package net.i2p.launchers
-
-import java.io.{File, InputStream}
-
-/**
-  * This represent a file or a directory. A filesystem resource.
-  * It's used to handle a correct deployment of base files, even
-  * installer resources got kind of a flat list. (i.e geoip files
-  * is placed under a dir geoip)
-  *
-  * With this class we can now have a list containing both directories
-  * and files in a type safe list.
-  *
-  * @param path
-  * @param content
-  * @param files
-  * @since 0.9.35
-  */
-class FDObject(path: String, content: Option[InputStream], files: Option[List[File]] = None, subDirectories: Boolean = false) {
-  def isFile = files.isEmpty
-
-  def getPath = path
-
-  def filesIsDirectories = subDirectories
-
-  def getContent: Either[InputStream, List[File]] = {
-    if (files.isEmpty) return Left(content.get)
-    Right(files.get.map { f => new File(DeployProfile.pathJoin(path, f.getName)) })
-  }
-}
-
-
-class FDObjFile(file: String) extends FDObject(new File(file).getPath, Some(getClass.getResourceAsStream("/".concat(file))) )
-class FDObjDir(name: String, files: List[String],subDirectories:Boolean=false) extends FDObject(name, None, Some(files.map { s => new File(s) }),subDirectories)
-
-/**
-  *
-  * This is a case class, it's a Scala thing. Think of it as a type.
-  * If you're familiar with C, it's like a "typedef" even iirc Scala
-  * has a own function for that as well.
-  *
-  *
-  */
-
-
diff --git a/launchers/common/src/main/scala/net/i2p/launchers/CompleteDeployment.scala b/launchers/common/src/main/scala/net/i2p/launchers/CompleteDeployment.scala
deleted file mode 100644
index 42f9faf1273737e8385da39d15d27ddf61cd2aa8..0000000000000000000000000000000000000000
--- a/launchers/common/src/main/scala/net/i2p/launchers/CompleteDeployment.scala
+++ /dev/null
@@ -1,48 +0,0 @@
-package net.i2p.launchers
-
-import java.io.{File, FileInputStream, FileOutputStream, InputStream}
-import java.nio.file.Path
-import java.util.zip.ZipInputStream
-
-import scala.concurrent.Future
-import scala.concurrent.ExecutionContext.Implicits.global
-
-/**
-  *
-  * CompleteDeployment - In use to deploy base path for the Mac OS X Bundle release.
-  *
-  * @author Meeh
-  * @since 0.9.35
-  */
-class CompleteDeployment(val zipFile: File, val i2pBaseDir: File) {
-
-  if (!i2pBaseDir.exists()) {
-    i2pBaseDir.mkdirs()
-  } else {
-    // TODO: Check what version etc..
-  }
-
-  def unzip(zipFile: InputStream, destination: Path): Unit = {
-    val zis = new ZipInputStream(zipFile)
-
-    Stream.continually(zis.getNextEntry).takeWhile(_ != null).foreach { file =>
-      if (!file.isDirectory) {
-        val outPath = destination.resolve(file.getName)
-        val outPathParent = outPath.getParent
-        if (!outPathParent.toFile.exists()) {
-          outPathParent.toFile.mkdirs()
-        }
-
-        val outFile = outPath.toFile
-        val out = new FileOutputStream(outFile)
-        val buffer = new Array[Byte](4096)
-        Stream.continually(zis.read(buffer)).takeWhile(_ != -1).foreach(out.write(buffer, 0, _))
-      }
-    }
-  }
-
-  def makeDeployment : Future[Unit] = Future {
-    unzip(new FileInputStream(zipFile), i2pBaseDir.toPath)
-  }
-
-}
diff --git a/launchers/common/src/main/scala/net/i2p/launchers/DeployProfile.scala b/launchers/common/src/main/scala/net/i2p/launchers/DeployProfile.scala
deleted file mode 100644
index 5894d991dae0f54d863f51934dd3962be266da0a..0000000000000000000000000000000000000000
--- a/launchers/common/src/main/scala/net/i2p/launchers/DeployProfile.scala
+++ /dev/null
@@ -1,147 +0,0 @@
-package net.i2p.launchers
-
-import java.io.{File, IOException, InputStream}
-import java.nio.file.FileAlreadyExistsException
-
-
-/**
-  *
-  * This is a singleton ish style. It's an object - it was never a class.
-  * However it has a class-"brother/sister"
-  *
-  * objects like this should be considered like containers for java's
-  * public static methods.
-  *
-  * Many classes/objects benefits from pathJoin, so therefore it's defined
-  * as an "public static method".
-  *
-  * @since 0.9.35
-  */
-object DeployProfile {
-
-
-  /**
-    * This function will find the executing jar. "myself"
-    * @return
-    */
-  def executingJarFile = getClass().getProtectionDomain().getCodeSource().getLocation()
-
-  /**
-    * This joins two paths in a cross platform way. Meaning it takes care of either we use
-    * \\ or / as directory separator. It returns the resulting path in a string.
-    *
-    * @since 0.9.35
-    * @param parent The parent path
-    * @param child The child path to append
-    * @return String
-    */
-  def pathJoin(parent:String,child:String): String = new File(new File(parent), child).getPath
-}
-
-/**
-  *
-  * The purpose of this class is to copy files from the i2p "default config" directory
-  * and to a "current config" directory relative to the browser bundle - but this class is
-  * also used by the OSX launcher since it shares common properties like that the bundle has
-  * to be read only.
-  *
-  * @author Meeh
-  * @version 0.0.1
-  * @since 0.9.35
-  */
-class DeployProfile(val confDir: String, val baseDir: String) {
-  import java.nio.file.{Files, Paths}
-
-  /**
-    * This function copies resources from the fatjar to the config directory of i2p.
-    *
-    * @since 0.9.35
-    * @param fStr
-    * @return Unit
-    */
-  def copyFileResToDisk(fStr: String) = try { Files.copy(
-    getClass.getResource("/".concat(fStr)).getContent.asInstanceOf[InputStream],
-    Paths.get(DeployProfile.pathJoin(confDir, fStr)).normalize()
-  )} catch {
-    case _:FileAlreadyExistsException => {} // Ignored
-    case ex:IOException => println(s"Error! Exception ${ex}")
-  }
-
-
-  /**
-    * This function copies resources from the fatjar to the config directory of i2p.
-    *
-    * @since 0.9.35
-    * @param path
-    * @param is
-    * @return Unit
-    */
-  def copyBaseFileResToDisk(path: String, is: InputStream) = try { Files.copy(
-    is,
-    Paths.get(DeployProfile.pathJoin(baseDir, path)).normalize()
-  )} catch {
-    case _:FileAlreadyExistsException => {} // Ignored
-    case ex:IOException => println(s"Error! Exception ${ex}")
-  }
-
-  /**
-    * Filter function for finding missing required files.
-    *
-    * @since 0.9.35
-    * @param l1
-    * @param l2
-    * @return
-    */
-  def missingFiles(l1: List[String], l2: List[String]) = l1.filter { x => !l2.contains(x) }
-
-
-  val warFiles = List("routerconsole.war")
-
-  val staticFiles = List(
-    "blocklist.txt",
-    "clients.config",
-    "continents.txt",
-    "countries.txt",
-    "hosts.txt",
-    "geoip.txt",
-    "i2ptunnel.config",
-    "logger.config",
-    "router.config",
-    "webapps.config"
-  )
-
-  /**
-    *
-    * This function will check the existence of static files,
-    * and if any of them are lacking, it will be copied from the
-    * fat jar's resources.
-    *
-    * @since 0.9.35
-    * @return Unit (Null)
-    */
-  def verifyExistenceOfConfig() = {
-    val fDir = new File(confDir)
-    if (fDir.exists()) {
-      // We still check if files are in place
-      val currentDirContentList = fDir.list.toList
-      val missing = missingFiles(staticFiles, currentDirContentList)
-      if (!missing.isEmpty) {
-        missing.map(copyFileResToDisk)
-      }
-    } else {
-      // New deployment!
-      deployDefaultConfig()
-    }
-  }
-
-  /**
-    *
-    * This function does the default deployment of files,
-    * map is the same as a loop. we're looping over the file list.
-    *
-    * @since 0.9.35
-    * @return Unit
-    */
-  def deployDefaultConfig(): Unit = staticFiles.map(copyFileResToDisk)
-
-}
diff --git a/launchers/common/src/main/scala/net/i2p/launchers/OSXDefaults.scala b/launchers/common/src/main/scala/net/i2p/launchers/OSXDefaults.scala
deleted file mode 100644
index 42457cab1d7ae55a4ee76e0ed5d299866e3b663b..0000000000000000000000000000000000000000
--- a/launchers/common/src/main/scala/net/i2p/launchers/OSXDefaults.scala
+++ /dev/null
@@ -1,18 +0,0 @@
-package net.i2p.launchers
-
-import java.io.File
-
-/**
-  * Defaults object for Mac OS X
-  *
-  *
-  * @author Meeh
-  * @since 0.9.35
-  */
-object OSXDefaults {
-
-  def getOSXConfigDirectory = new File(DeployProfile.pathJoin(System.getProperty("user.home"), "Library/Application Support/i2p"))
-
-  def getOSXBaseDirectory = new File(DeployProfile.pathJoin(System.getProperty("user.home"),"Library/I2P"))
-
-}
diff --git a/launchers/common/src/main/scala/net/i2p/launchers/PartialDeployment.scala b/launchers/common/src/main/scala/net/i2p/launchers/PartialDeployment.scala
deleted file mode 100644
index 954c5c41d1e4c2c8ea644ebfdc8a772271e8d4d9..0000000000000000000000000000000000000000
--- a/launchers/common/src/main/scala/net/i2p/launchers/PartialDeployment.scala
+++ /dev/null
@@ -1,248 +0,0 @@
-package net.i2p.launchers
-
-import java.io.{File, IOException}
-import java.nio.file.FileAlreadyExistsException
-import java.util.zip.ZipFile
-
-import java.nio.file.StandardCopyOption.REPLACE_EXISTING
-import java.nio.file.Files.copy
-import java.nio.file.Paths.get
-
-import collection.JavaConverters._
-
-/**
-  *
-  * NOTE: Work in progress: Originally written for OSX launcher - but will be used in BB launcher.
-  *
-  * PartialXDeployment
-  *
-  * This class can be a bit new for java developers. In Scala, when inherit other classes,
-  * you would need to define their arguments if the super class only has constructors taking arguments.
-  *
-  * This child class don't take arguments, but rather get them from the signleton OSXDefaults.
-  *
-  * This class should be able to copy recursive resources into correct position for a normal deployment.
-  *
-  *
-  * This class might look like black magic for some. But what it does is to deploy a structure like for example:
-  * tree ~/Library/I2P
-  * /Users/mikalv/Library/I2P
-  * ├── blocklist.txt
-  * ├── certificates
-  * │   ├── family
-  * │   │   ├── gostcoin.crt
-  * │   │   ├── i2p-dev.crt
-  * │   │   ├── i2pd-dev.crt
-  * │   │   └── volatile.crt
-  * │   ├── i2ptunnel
-  * │   ├── news
-  * │   │   ├── ampernand_at_gmail.com.crt
-  * │   │   ├── echelon_at_mail.i2p.crt
-  * │   │   ├── str4d_at_mail.i2p.crt
-  * │   │   └── zzz_at_mail.i2p.crt
-  * │   ├── plugin
-  * │   │   ├── cacapo_at_mail.i2p.crt
-  * │   │   ├── str4d_at_mail.i2p.crt
-  * │   │   └── zzz-plugin_at_mail.i2p.crt
-  * │   ├── reseed
-  * │   │   ├── atomike_at_mail.i2p.crt
-  * │   │   ├── backup_at_mail.i2p.crt
-  * │   │   ├── bugme_at_mail.i2p.crt
-  * │   │   ├── creativecowpat_at_mail.i2p.crt
-  * │   │   ├── echelon_at_mail.i2p.crt
-  * │   │   ├── hottuna_at_mail.i2p.crt
-  * │   │   ├── igor_at_novg.net.crt
-  * │   │   ├── lazygravy_at_mail.i2p.crt
-  * │   │   ├── meeh_at_mail.i2p.crt
-  * │   │   └── zmx_at_mail.i2p.crt
-  * │   ├── revocations
-  * │   ├── router
-  * │   │   ├── echelon_at_mail.i2p.crt
-  * │   │   ├── str4d_at_mail.i2p.crt
-  * │   │   └── zzz_at_mail.i2p.crt
-  * │   └── ssl
-  * │       ├── echelon.reseed2017.crt
-  * │       ├── i2p.mooo.com.crt
-  * │       ├── i2pseed.creativecowpat.net.crt
-  * │       ├── isrgrootx1.crt
-  * │       └── reseed.onion.im.crt
-  * ├── clients.config
-  * ├── geoip
-  * │   ├── continents.txt
-  * │   ├── countries.txt
-  * │   ├── geoip.txt
-  * │   └── geoipv6.dat.gz
-  * ├── hosts.txt
-  * └── i2ptunnel.config
-  *
-  * @author Meeh
-  * @since 0.9.35
-  */
-class PartialDeployment extends
-  DeployProfile(
-    OSXDefaults.getOSXConfigDirectory.getAbsolutePath,
-    OSXDefaults.getOSXBaseDirectory.getAbsolutePath
-  ) {
-
-
-
-  /**
-    * This list is a micro DSL for how files should
-    * be deployed to the filesystem in the base
-    * directory.
-    */
-  val staticFilesFromResources = List(
-    new FDObjFile("blocklist.txt"),
-    new FDObjFile("clients.config"),
-    new FDObjFile("hosts.txt"),
-    new FDObjDir("geoip", files = List(
-      "continents.txt",
-      "countries.txt",
-      "geoip.txt",
-      "geoipv6.dat.gz")),
-    new FDObjFile("i2ptunnel.config"),
-    new FDObjDir("certificates", List(
-      "family",
-      "i2ptunnel",
-      "news",
-      "plugin",
-      "reseed",
-      "revocations",
-      "router",
-      "ssl"
-    ),subDirectories=true),
-    new FDObjDir("themes",List(
-      "console",
-      "imagegen",
-      "snark",
-      "susidns",
-      "susimail"
-    ),true)
-  )
-
-  /**
-    * This function copies an directory of files from the jar
-    * to the base directory defined in the launcher.
-    * @param dir
-    * @return
-    */
-  def copyDirFromRes(dir: File): Unit = {
-    // A small hack
-    try {
-      val zipFile = new ZipFile(DeployProfile.executingJarFile.getFile)
-      zipFile.entries().asScala.toList.filter(_.toString.startsWith(dir.getPath)).filter(!_.isDirectory).map { entry =>
-        new File(DeployProfile.pathJoin(baseDir,entry.getName)).getParentFile.mkdirs()
-        if (entry.isDirectory) {
-          createFileOrDirectory(new File(DeployProfile.pathJoin(baseDir,entry.getName)), true)
-        } else {
-          copyBaseFileResToDisk(entry.getName, getClass.getResourceAsStream("/".concat(entry.getName)))
-        }
-      }
-    } catch {
-      case _:FileAlreadyExistsException => {} // Ignored
-      case ex:IOException => println(s"Error! Exception ${ex}")
-    }
-  }
-
-  /**
-    * This function will depending on directory or not copy either the file
-    * or create the directory and copy directory content if any.
-    *
-    * @param file
-    * @param isDir
-    * @return
-    */
-  def createFileOrDirectory(file: File, isDir: Boolean = false): Unit = {
-    if (file != null) {
-      //println(s"createFileOrDirectory(${file},${isDir})")
-      try {
-        // Make sure subject exists if directory
-        if (!new File(DeployProfile.pathJoin(baseDir,file.getPath)).exists()) {
-          if (isDir) new File(DeployProfile.pathJoin(baseDir,file.getPath)).mkdirs()
-        }
-        if (isDir) {
-          // Handle dir
-          copyDirFromRes(file)
-        } else {
-          // Handle file
-          copyBaseFileResToDisk(file.getPath, getClass.getResourceAsStream("/".concat(file.getName)))
-        }
-      } catch {
-        case _:FileAlreadyExistsException => {} // Ignored
-        case ex:IOException => println(s"Error! Exception ${ex}")
-      }
-    }
-  }
-
-  if (!new File(baseDir).exists()) {
-    new File(baseDir).mkdirs()
-  }
-
-  implicit def toPath (filename: String) = get(filename)
-
-  val selfFile = new File(DeployProfile.executingJarFile.getFile)
-  val selfDir = selfFile.getParentFile
-  val resDir = new File(selfDir.getParent, "Resources")
-  val i2pBaseBundleDir = new File(resDir, "i2pbase")
-  val i2pBundleJarDir = new File(i2pBaseBundleDir, "lib")
-
-  val i2pBaseDir = OSXDefaults.getOSXBaseDirectory
-  val i2pDeployJarDir = new File(i2pBaseDir, "lib")
-  if (!i2pDeployJarDir.exists()) {
-    i2pDeployJarDir.mkdirs()
-    i2pBundleJarDir.list().toList.map {
-      jar => {
-        copy (
-          DeployProfile.pathJoin(i2pBundleJarDir.getAbsolutePath, jar),
-          DeployProfile.pathJoin(i2pDeployJarDir.getAbsolutePath, jar),
-          REPLACE_EXISTING)
-        println(s"Copied ${jar} to right place")
-      }
-    }
-  }
-
-  /**
-    * Please note that in Scala, the constructor body is same as class body.
-    * What's defined outside of methods is considered constructor code and
-    * executed as it.
-    *
-    *
-    *
-    * a map function work as a loop with some built in security
-    * for "null" objects.
-    * What happens here is "for each staticFilesFromResources" do =>
-    *
-    * Then, based upon if it's a file or a directory, different actions take place.
-    *
-    * the match case is controlling the flow based upon which type of object it is.
-    */
-  staticFilesFromResources.map {
-    fd => fd.getContent match {
-        // Case subject is a file/resource
-      case Left(is) => {
-        // Write file
-        val f = DeployProfile.pathJoin(baseDir, fd.getPath)
-        println(s"f: ${f.toString}")
-        if (!new File(f).exists()) {
-          //println(s"copyBaseFileResToDisk(${fd.getPath})")
-          try {
-            copyBaseFileResToDisk(fd.getPath, is)
-          } catch {
-            case ex:IOException => println(s"Error! Exception ${ex}")
-            case _:FileAlreadyExistsException => {} // Ignored
-          }
-        }
-      }
-        // Case subject is a directory
-      case Right(dir) => {
-        // Ensure directory
-        //println(s"Directory(${fd.getPath})")
-        if (!new File(DeployProfile.pathJoin(baseDir,fd.getPath)).exists()) {
-          new File(DeployProfile.pathJoin(baseDir,fd.getPath)).mkdirs()
-        }
-        dir.map { f => createFileOrDirectory(f,fd.filesIsDirectories) }
-      }
-    }
-  }
-
-}
diff --git a/launchers/common/src/main/scala/net/i2p/launchers/RouterLauncher.scala b/launchers/common/src/main/scala/net/i2p/launchers/RouterLauncher.scala
deleted file mode 100644
index dc40e9685e649fc47fd43bf0f38fe43ec6e034bd..0000000000000000000000000000000000000000
--- a/launchers/common/src/main/scala/net/i2p/launchers/RouterLauncher.scala
+++ /dev/null
@@ -1,19 +0,0 @@
-package net.i2p.launchers
-
-import java.io.File
-
-import scala.concurrent.Future
-import scala.sys.process.Process
-
-
-/**
-  * A abstract class is kind of like an java interface.
-  *
-  * @author Meeh
-  * @since 0.9.35
-  */
-abstract class RouterLauncher {
-  def runRouter(basePath: File, args: Array[String]): Future[Process]
-
-  def runRouter(args: Array[String]): Future[Process]
-}
diff --git a/launchers/macosx/.vscode/settings.json b/launchers/macosx/.vscode/settings.json
deleted file mode 100644
index 0245bc11832493b8c8ac0f018e85cd974a731f79..0000000000000000000000000000000000000000
--- a/launchers/macosx/.vscode/settings.json
+++ /dev/null
@@ -1,36 +0,0 @@
-{
-  "files.associations": {
-    "*.jsm": "javascript",
-    "*.grd": "xml",
-    "*.plist": "xml",
-    "*.jxa": "javascript",
-    "*.gni": "javascript",
-    "*.gn": "javascript",
-    "type_traits": "cpp",
-    "__config": "cpp",
-    "__nullptr": "cpp",
-    "cstddef": "cpp",
-    "exception": "cpp",
-    "initializer_list": "cpp",
-    "new": "cpp",
-    "stdexcept": "cpp",
-    "typeinfo": "cpp",
-    "algorithm": "cpp",
-    "ios": "cpp",
-    "iosfwd": "cpp",
-    "__split_buffer": "cpp",
-    "list": "cpp",
-    "string": "cpp",
-    "vector": "cpp",
-    "iterator": "cpp",
-    "optional": "cpp",
-    "memory": "cpp",
-    "map": "cpp",
-    "__mutex_base": "cpp",
-    "mutex": "cpp",
-    "functional": "cpp",
-    "__functional_03": "cpp",
-    "__string": "cpp",
-    "system_error": "cpp"
-  }
-}
\ No newline at end of file
diff --git a/launchers/macosx/16x16-Itoopie Transparent.png b/launchers/macosx/16x16-Itoopie Transparent.png
deleted file mode 100644
index 993c1b135e2c05248127c83ae79766836d6d7897..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/16x16-Itoopie Transparent.png and /dev/null differ
diff --git a/launchers/macosx/Carthage b/launchers/macosx/Carthage
deleted file mode 100644
index 7ebbd3a0f4d81a9730b09f8a205ce95af98a4f1a..0000000000000000000000000000000000000000
--- a/launchers/macosx/Carthage
+++ /dev/null
@@ -1,3 +0,0 @@
-github 'sparkle-project/Sparkle' == 1.21.0
-
-
diff --git a/launchers/macosx/Changes.md b/launchers/macosx/Changes.md
deleted file mode 100644
index 5e7c8f4bc703706e992c9cdcce1fd85b6f3e2be8..0000000000000000000000000000000000000000
--- a/launchers/macosx/Changes.md
+++ /dev/null
@@ -1,17 +0,0 @@
-# Change Log
-
-## 0.9.38
-
-* Initial alpha/beta ish.
-* Preferences dialog (unfinished).
-* Firefox detection.
-
-## 0.9.39
-
-* Fixed startup option so the launcher can start at OSX login/bootup.
-* Added I2P Browser to the list of "firefox" browsers to detect.
-* Changed hardcoded path lookup to native "registry" lookup for firefox application.
-* Made the advanced preferences table editable by the user.
-* Cleanup of old and/or unused code.
-* Bugfixes.
-
diff --git a/launchers/macosx/CommonCode/Browser/ConsoleWebView.storyboard b/launchers/macosx/CommonCode/Browser/ConsoleWebView.storyboard
deleted file mode 100644
index 84d0562766d7183c062ef604325ec1f46c3e6cc0..0000000000000000000000000000000000000000
--- a/launchers/macosx/CommonCode/Browser/ConsoleWebView.storyboard
+++ /dev/null
@@ -1,44 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<document type="com.apple.InterfaceBuilder3.Cocoa.Storyboard.XIB" version="3.0" toolsVersion="14460.31" targetRuntime="MacOSX.Cocoa" propertyAccessControl="none" useAutolayout="YES" initialViewController="oLh-xo-y8T">
-    <dependencies>
-        <deployment identifier="macosx"/>
-        <plugIn identifier="com.apple.InterfaceBuilder.CocoaPlugin" version="14460.31"/>
-        <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
-    </dependencies>
-    <scenes>
-        <!--Window Controller-->
-        <scene sceneID="g0w-9k-Acs">
-            <objects>
-                <windowController id="oLh-xo-y8T" sceneMemberID="viewController">
-                    <window key="window" title="Window" allowsToolTipsWhenApplicationIsInactive="NO" autorecalculatesKeyViewLoop="NO" releasedWhenClosed="NO" visibleAtLaunch="NO" frameAutosaveName="" animationBehavior="default" id="5Sr-7Y-gfA">
-                        <windowStyleMask key="styleMask" titled="YES" closable="YES" miniaturizable="YES" resizable="YES"/>
-                        <windowPositionMask key="initialPositionMask" leftStrut="YES" rightStrut="YES" topStrut="YES" bottomStrut="YES"/>
-                        <rect key="contentRect" x="294" y="362" width="480" height="270"/>
-                        <rect key="screenRect" x="0.0" y="0.0" width="1920" height="1177"/>
-                        <connections>
-                            <outlet property="delegate" destination="oLh-xo-y8T" id="Fxx-ke-F0n"/>
-                        </connections>
-                    </window>
-                    <connections>
-                        <segue destination="nXM-BR-Lxj" kind="relationship" relationship="window.shadowedContentViewController" id="3cB-Gf-aj2"/>
-                    </connections>
-                </windowController>
-                <customObject id="K5y-Qa-lNJ" userLabel="First Responder" customClass="NSResponder" sceneMemberID="firstResponder"/>
-            </objects>
-            <point key="canvasLocation" x="50" y="118"/>
-        </scene>
-        <!--Console View Controller-->
-        <scene sceneID="MSW-MZ-pqs">
-            <objects>
-                <viewController id="nXM-BR-Lxj" customClass="ConsoleViewController" customModule="I2PLauncher" customModuleProvider="target" sceneMemberID="viewController">
-                    <view key="view" id="Omy-Aq-Pw7">
-                        <rect key="frame" x="0.0" y="0.0" width="480" height="270"/>
-                        <autoresizingMask key="autoresizingMask"/>
-                    </view>
-                </viewController>
-                <customObject id="LZW-ak-seY" userLabel="First Responder" customClass="NSResponder" sceneMemberID="firstResponder"/>
-            </objects>
-            <point key="canvasLocation" x="757" y="93"/>
-        </scene>
-    </scenes>
-</document>
diff --git a/launchers/macosx/CommonCode/Browser/EmbeddedConsoleView.swift b/launchers/macosx/CommonCode/Browser/EmbeddedConsoleView.swift
deleted file mode 100644
index 63d06a64ec679e638d44501ecc76d1fea1efb7ec..0000000000000000000000000000000000000000
--- a/launchers/macosx/CommonCode/Browser/EmbeddedConsoleView.swift
+++ /dev/null
@@ -1,88 +0,0 @@
-//
-//  EmbeddedConsoleView.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 08/12/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import AppKit
-import WebKit
-
-/*
-protocol EConsoleViewWrapper {}
-
-class WebViewSource {
-  class func webView() -> EConsoleViewWrapper {
-    if #available(OSX 10.12, *) {
-      //
-      return EmbeddedConsoleView(coder: NSCoder())!
-    } else {
-      // Sorry
-      return EmbeddedConsoleViewDummy()
-    }
-  }
-}
-
-extension EConsoleViewWrapper {
-  static func instantiate(frame frameRect: NSRect) -> EConsoleViewWrapper {
-    return WebViewSource.webView()
-  }
-}
-*/
-
-class ConsoleWindowController: NSWindowController {
-  override func windowDidLoad() {
-    super.windowDidLoad()
-/*    let v: NSView = WebViewSource.webView() as! NSView
-    v.wantsLayer = true
-    self.window?.contentView?.addSubview(v)*/
-  }
-}
-
-class ConsoleViewController: NSViewController {
-  var webView: WKWebView!
-  let consoleWebUrl = URL(string: "http://127.0.0.1:7657")
-  
-  override func loadView() {
-    let webConfiguration = WKWebViewConfiguration()
-    webView = WKWebView(frame: .zero, configuration: webConfiguration)
-    //webView.uiDelegate = self
-    view = webView
-  }
-  override func viewDidLoad() {
-    super.viewDidLoad()
-    
-    webView.load(URLRequest(url: consoleWebUrl!))
-  }
-
-}
-
-/*
-@available(OSX 10.12, *)
-class EmbeddedConsoleView: WKWebView, EConsoleViewWrapper {
-  
-  let consoleWebUrl = URL(string: "http://127.0.0.1:7657")
-  
-  func setupWebViewForConsole(_ f: NSRect = NSRect(x: 0, y: 0, width: 800, height: 400)) {
-    self.allowsBackForwardNavigationGestures = true
-    self.configuration.preferences.javaScriptEnabled = true
-    self.configuration.preferences.plugInsEnabled = false
-    
-    self.load(URLRequest(url: consoleWebUrl!))
-  }
-  
-  override func viewWillDraw() {
-    super.viewWillDraw()
-  }
-  
-  required init?(coder decoder: NSCoder) {
-    super.init(coder: decoder)
-    self.setupWebViewForConsole()
-  }
-  
-}
-
-class EmbeddedConsoleViewDummy: NSView, EConsoleViewWrapper {}
-*/
-
diff --git a/launchers/macosx/CommonCode/Browser/FirefoxManager.swift b/launchers/macosx/CommonCode/Browser/FirefoxManager.swift
deleted file mode 100644
index 2dd205acc05665bc8efd546aa8b7b98029202575..0000000000000000000000000000000000000000
--- a/launchers/macosx/CommonCode/Browser/FirefoxManager.swift
+++ /dev/null
@@ -1,108 +0,0 @@
-//
-//  FirefoxManager.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 08/12/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-
-class FirefoxManager {
-  
-  var firefoxAppPath = ""
-  private var isFirefoxFound = false
-  private var isFirefoxProfileExtracted = false
-  
-  fileprivate func directoryExistsAtPath(_ path: String) -> Bool {
-    var isDirectory = ObjCBool(true)
-    let exists = FileManager.default.fileExists(atPath: path, isDirectory: &isDirectory)
-    return exists && isDirectory.boolValue
-  }
-  
-  func IsFirefoxFound() -> Bool {
-    return self.isFirefoxFound
-  }
-  
-  func IsProfileExtracted() -> Bool {
-    return self.isFirefoxProfileExtracted
-  }
-  
-  // Since we execute in the "unix/POSIX way", we need the full path of the binary.
-  func bundleExecutableSuffixPath() -> String {
-    return "/Contents/MacOS/firefox"
-  }
-  
-  func executeFirefox() -> Bool {
-    let fullExecPath = "\(self.firefoxAppPath)\(self.bundleExecutableSuffixPath())"
-    let firefoxProcess = Subprocess(executablePath: fullExecPath, arguments: [ "-profile", Preferences.shared()["I2Pref_firefoxProfilePath"] as! String, "http://127.0.0.1:7657/home" ])
-    DispatchQueue.global(qos: .background).async {
-      let _ = firefoxProcess.execute()
-    }
-    return true
-  }
-
-  /**
-   *
-   * First, try find I2P Browser, if  it fails, then try Firefox or Firefox Developer.
-   *
-   * Instead of using hardcoded paths, or file search we use OS X's internal "registry" API
-   * and detects I2P Browser or Firefox by bundle name. (or id, but name is more readable)
-   *
-   */
-  func tryAutoDetect() -> Bool {
-    var browserPath = NSWorkspace.shared.fullPath(forApplication: "I2P Browser")
-    if (browserPath == nil)
-    {
-      browserPath = NSWorkspace.shared.fullPath(forApplication: "Firefox")
-      if (browserPath == nil)
-      {
-        browserPath = NSWorkspace.shared.fullPath(forApplication: "Firefox Developer")
-      }
-    }
-   
-    self.isFirefoxProfileExtracted = directoryExistsAtPath(Preferences.shared()["I2Pref_firefoxProfilePath"] as! String)
-    
-    // If browserPath is still nil, then nothing above was found and we can return early.
-    if (browserPath == nil)
-    {
-      return false
-    }
-    
-    let result = directoryExistsAtPath(browserPath!)
-    self.isFirefoxFound = result
-    if (result) {
-      self.firefoxAppPath = browserPath!
-      return true
-    }
-    return false
-  }
-  
-  
-  private static var sharedFirefoxManager: FirefoxManager = {
-    let firefoxMgr = FirefoxManager()
-    
-    return firefoxMgr
-  }()
-  
-  
-  class func shared() -> FirefoxManager {
-    return sharedFirefoxManager
-  }
-}
-
-extension FirefoxManager {
-  func unzipProfile() -> Bool {
-    let resourceUrl = Bundle.main.url(forResource: "profile", withExtension: "tgz")
-    let profileTgz = resourceUrl!.path
-    let unzipProc = Subprocess(executablePath: "/usr/bin/tar", arguments: ["-xf",profileTgz,"-C",NSString(format: "%@/Library/Application Support/i2p", NSHomeDirectory()) as String])
-    DispatchQueue.global(qos: .background).async {
-      let proc = unzipProc.execute(captureOutput: true)
-      print("Firefox Profile Extraction Errors: \(proc?.errors ?? "false")")
-      print("Firefox Profile Extraction Output: \(proc?.output ?? "false")")
-    }
-    return false
-  }
-}
-
diff --git a/launchers/macosx/CommonCode/Utils/ArrayExtensions.swift b/launchers/macosx/CommonCode/Utils/ArrayExtensions.swift
deleted file mode 100644
index ccfc807b0c63cb39c272a9c3414d2fcebd9b08f2..0000000000000000000000000000000000000000
--- a/launchers/macosx/CommonCode/Utils/ArrayExtensions.swift
+++ /dev/null
@@ -1,29 +0,0 @@
-//
-//  ArrayExtension.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 17/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-
-extension Array where Element: NSAttributedString {
-  func joined2(separator: NSAttributedString) -> NSAttributedString {
-    var isFirst = true
-    return self.reduce(NSMutableAttributedString()) {
-      (r, e) in
-      if isFirst {
-        isFirst = false
-      } else {
-        r.append(separator)
-      }
-      r.append(e)
-      return r
-    }
-  }
-  
-}
-
-
diff --git a/launchers/macosx/CommonCode/Utils/DateTimeUtils.swift b/launchers/macosx/CommonCode/Utils/DateTimeUtils.swift
deleted file mode 100644
index 471dffc24168575cecc0939cfc28f5074ec655f4..0000000000000000000000000000000000000000
--- a/launchers/macosx/CommonCode/Utils/DateTimeUtils.swift
+++ /dev/null
@@ -1,87 +0,0 @@
-//
-//  DateTimeUtils.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 18/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-extension Date {
-  init(date: NSDate) {
-    self.init(timeIntervalSinceReferenceDate: date.timeIntervalSinceReferenceDate)
-  }
-}
-
-extension NSDate {
-  convenience init(date: Date) {
-    self.init(timeIntervalSinceReferenceDate: date.timeIntervalSinceReferenceDate)
-  }
-}
-
-class DateTimeUtils {
-  static func timeAgoSinceDate(date:NSDate, numericDates:Bool) -> String {
-    let calendar = NSCalendar.current
-    let unitFlags: Set<Calendar.Component> = [.minute, .hour, .day, .weekOfYear, .month, .year, .second]
-    let now = NSDate()
-    let earliest = now.earlierDate(date as Date)
-    let latest = (earliest == now as Date) ? date : now
-    let components = calendar.dateComponents(unitFlags, from: earliest as Date,  to: latest as Date)
-    
-    if (components.year! >= 2) {
-      return "\(components.year!) years ago"
-    } else if (components.year! >= 1){
-      if (numericDates){
-        return "1 year ago"
-      } else {
-        return "Last year"
-      }
-    } else if (components.month! >= 2) {
-      return "\(components.month!) months ago"
-    } else if (components.month! >= 1){
-      if (numericDates){
-        return "1 month ago"
-      } else {
-        return "Last month"
-      }
-    } else if (components.weekOfYear! >= 2) {
-      return "\(components.weekOfYear!) weeks ago"
-    } else if (components.weekOfYear! >= 1){
-      if (numericDates){
-        return "1 week ago"
-      } else {
-        return "Last week"
-      }
-    } else if (components.day! >= 2) {
-      return "\(components.day!) days ago"
-    } else if (components.day! >= 1){
-      if (numericDates){
-        return "1 day ago"
-      } else {
-        return "Yesterday"
-      }
-    } else if (components.hour! >= 2) {
-      return "\(components.hour!) hours ago"
-    } else if (components.hour! >= 1){
-      if (numericDates){
-        return "1 hour ago"
-      } else {
-        return "An hour ago"
-      }
-    } else if (components.minute! >= 2) {
-      return "\(components.minute!) minutes ago"
-    } else if (components.minute! >= 1){
-      if (numericDates){
-        return "1 minute ago"
-      } else {
-        return "A minute ago"
-      }
-    } else if (components.second! >= 3) {
-      return "\(components.second!) seconds ago"
-    } else {
-      return "Just now"
-    }
-    
-  }
-}
diff --git a/launchers/macosx/CommonCode/Utils/DispatchQueue+delay.swift b/launchers/macosx/CommonCode/Utils/DispatchQueue+delay.swift
deleted file mode 100644
index a334cbb18aa4edbde3bbe6d7afc3d94444e9cc73..0000000000000000000000000000000000000000
--- a/launchers/macosx/CommonCode/Utils/DispatchQueue+delay.swift
+++ /dev/null
@@ -1,15 +0,0 @@
-//
-//  DispatchQueue+delay.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 24/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-extension DispatchQueue {
-  static func delay(_ delay: DispatchTimeInterval, closure: @escaping () -> ()) {
-    DispatchQueue.main.asyncAfter(deadline: .now() + delay, execute: closure)
-  }
-}
diff --git a/launchers/macosx/CommonCode/Utils/EventManager.swift b/launchers/macosx/CommonCode/Utils/EventManager.swift
deleted file mode 100644
index 87b4d5f55553b578b380bba9b5c55028e6499c67..0000000000000000000000000000000000000000
--- a/launchers/macosx/CommonCode/Utils/EventManager.swift
+++ /dev/null
@@ -1,86 +0,0 @@
-//
-//  EventManager.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 22/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-// TODO: Log all events?
-
-class EventManager {
-  var listeners = Dictionary<String, NSMutableArray>();
-  
-  // Create a new event listener, not expecting information from the trigger
-  // @param eventName: Matching trigger eventNames will cause this listener to fire
-  // @param action: The function/lambda you want executed when the event triggers
-  func listenTo(eventName:String, action: @escaping (()->())) {
-    let newListener = EventListenerAction(callback: action)
-    addListener(eventName: eventName, newEventListener: newListener)
-  }
-  
-  // Create a new event listener, expecting information from the trigger
-  // @param eventName: Matching trigger eventNames will cause this listener to fire
-  // @param action: The function/lambda you want executed when the event triggers
-  func listenTo(eventName:String, action: @escaping ((Any?)->())) {
-    let newListener = EventListenerAction(callback: action)
-    addListener(eventName: eventName, newEventListener: newListener)
-  }
-  
-  internal func addListener(eventName:String, newEventListener:EventListenerAction) {
-    if let listenerArray = self.listeners[eventName] {
-      listenerArray.add(newEventListener)
-    } else {
-      self.listeners[eventName] = [newEventListener] as NSMutableArray
-    }
-  }
-  
-  // Removes all listeners by default, or specific listeners through paramters
-  // @param eventName: If an event name is passed, only listeners for that event will be removed
-  func removeListeners(eventNameToRemoveOrNil:String?) {
-    if let eventNameToRemove = eventNameToRemoveOrNil {
-      if let actionArray = self.listeners[eventNameToRemove] {
-        actionArray.removeAllObjects()
-      }
-    } else {
-      self.listeners.removeAll(keepingCapacity: false)
-    }
-  }
-  
-  // Triggers an event
-  // @param eventName: Matching listener eventNames will fire when this is called
-  // @param information: pass values to your listeners
-  func trigger(eventName:String, information:Any? = nil) {
-    print("Event: ", eventName, " will trigger ", self.listeners[eventName]?.count ?? 0, " listeners")
-    if let actionObjects = self.listeners[eventName] {
-      for actionObject in actionObjects {
-        if let actionToPerform = actionObject as? EventListenerAction {
-          if let methodToCall = actionToPerform.actionExpectsInfo {
-            methodToCall(information)
-          }
-          else if let methodToCall = actionToPerform.action {
-            methodToCall()
-          }
-        }
-      }
-    }
-  }
-}
-
-// Class to hold actions to live in NSMutableArray
-class EventListenerAction {
-  let action:(() -> ())?
-  let actionExpectsInfo:((Any?) -> ())?
-  
-  init(callback: @escaping (() -> ()) ) {
-    self.action = callback
-    self.actionExpectsInfo = nil
-  }
-  
-  init(callback: @escaping ((Any?) -> ()) ) {
-    self.actionExpectsInfo = callback
-    self.action = nil
-  }
-}
diff --git a/launchers/macosx/CommonCode/Utils/FolderContentMonitor.swift b/launchers/macosx/CommonCode/Utils/FolderContentMonitor.swift
deleted file mode 100644
index 168989344a900e2635b76e780c537c3afaea5533..0000000000000000000000000000000000000000
--- a/launchers/macosx/CommonCode/Utils/FolderContentMonitor.swift
+++ /dev/null
@@ -1,111 +0,0 @@
-//
-//  FolderContentMonitor.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 28/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-/*
- infix operator ~>
- 
- private let queue = DispatchQueue(label: "background")
- 
- func ~> <R> (
- backgroundClosure:   @escaping () -> R,
- mainClosure:         @escaping (_ result: R) -> ())
- {
- queue.async {
- let result = backgroundClosure()
- DispatchQueue.main.async(execute: {
- mainClosure(result)
- })
- }
- }
- */
-
-public struct Event: CustomStringConvertible {
-  
-  public let eventId: FSEventStreamEventId
-  public let eventPath: String
-  public let eventFlags: FSEventStreamEventFlags
-  
-  public var description: String {
-    return "\(eventId) - \(eventFlags) - \(eventPath)"
-  }
-}
-
-public class FolderContentMonitor {
-  
-  let callback: (Event) -> Void
-  
-  public init(pathsToWatch: [String], sinceWhen: FSEventStreamEventId = FSEventStreamEventId(kFSEventStreamEventIdSinceNow), callback: @escaping (Event) -> Void) {
-    
-    self.lastEventId = sinceWhen
-    self.pathsToWatch = pathsToWatch
-    self.callback = callback
-  }
-  
-  deinit {
-    stop()
-  }
-  
-  // MARK: - Private Properties
-  private let eventCallback: FSEventStreamCallback = {
-    (stream: ConstFSEventStreamRef,
-    contextInfo: UnsafeMutableRawPointer?,
-    numEvents: Int,
-    eventPaths: UnsafeMutableRawPointer,
-    eventFlags: UnsafePointer<FSEventStreamEventFlags>,
-    eventIds: UnsafePointer<FSEventStreamEventId>) in
-    
-    let fileSystemWatcher: FolderContentMonitor = unsafeBitCast(contextInfo, to: FolderContentMonitor.self)
-    
-    guard let paths = unsafeBitCast(eventPaths, to: NSArray.self) as? [String] else { return }
-    
-    for index in 0..<numEvents {
-      fileSystemWatcher.processEvent(eventId: eventIds[index], eventPath: paths[index], eventFlags: eventFlags[index])
-    }
-    
-    fileSystemWatcher.lastEventId = eventIds[numEvents - 1]
-  }
-  
-  private let pathsToWatch: [String]
-  private var started = false
-  private var streamRef: FSEventStreamRef!
-  
-  private func processEvent(eventId: FSEventStreamEventId, eventPath: String, eventFlags: FSEventStreamEventFlags) {
-    
-    let event = Event(eventId: eventId, eventPath: eventPath, eventFlags: eventFlags)
-    callback(event)
-  }
-  
-  public private(set) var lastEventId: FSEventStreamEventId
-  
-  public func start() {
-    guard started == false else { return }
-    
-    var context = FSEventStreamContext(version: 0, info: nil, retain: nil, release: nil, copyDescription: nil)
-    context.info = Unmanaged.passUnretained(self).toOpaque()
-    let flags = UInt32(kFSEventStreamCreateFlagUseCFTypes | kFSEventStreamCreateFlagFileEvents)
-    streamRef = FSEventStreamCreate(kCFAllocatorDefault, eventCallback, &context, pathsToWatch as CFArray, lastEventId, 0, flags)
-    
-    FSEventStreamScheduleWithRunLoop(streamRef, CFRunLoopGetMain(), CFRunLoopMode.defaultMode.rawValue)
-    FSEventStreamStart(streamRef)
-    
-    started = true
-  }
-  
-  public func stop() {
-    guard started == true else { return }
-    
-    FSEventStreamStop(streamRef)
-    FSEventStreamInvalidate(streamRef)
-    FSEventStreamRelease(streamRef)
-    streamRef = nil
-    
-    started = false
-  }
-}
diff --git a/launchers/macosx/CommonCode/Utils/Preferences.swift b/launchers/macosx/CommonCode/Utils/Preferences.swift
deleted file mode 100644
index c5efb941b893f1910cb154a4a6995913d98109d2..0000000000000000000000000000000000000000
--- a/launchers/macosx/CommonCode/Utils/Preferences.swift
+++ /dev/null
@@ -1,317 +0,0 @@
-//
-//  Preferences.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 01/12/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-class PreferenceRow {
-  var name: String?
-  var defaultValue: Any?
-  var selectedValue: Any?
-  
-  init(_ name: String, _ value: Any?, _ defaultVal: Any? = "") {
-    self.name = name
-    self.selectedValue = value
-    self.defaultValue = defaultVal
-  }
-  
-  func asRawValue() -> Any {
-    return self.selectedValue ?? self.defaultValue!
-  }
-}
-
-class Preferences  : NSObject {
-  
-  enum ShowAsMode {
-    case bothIcon
-    case menubarIcon
-    case dockIcon
-  }
-  
-  private var prefObject: Dictionary<String,Any> = Dictionary<String,Any>()
-  private var prefDict = Dictionary<String,PreferenceRow>()
-  private var prefDefaultDict: Dictionary<String,Any> = Dictionary<String,Any>()
-  
-  var notifyOnStatusChange: Bool {
-    get { return UserDefaults.standard.bool(forKey: "notifyOnStatusChange") }
-    set { UserDefaults.standard.set(newValue, forKey: "notifyOnStatusChange") }
-  }
-  
-  var count: Int = 0
-  
-  // Interface with a string setting in background
-  var showAsIconMode: ShowAsMode {
-    get {
-      var mode = self["I2Pref_showAsIconMode"]
-      if (mode == nil) {
-        mode = "bothIcon"
-      }
-      switch (mode as! String) {
-      case "bothIcon":
-        return ShowAsMode.bothIcon
-      case "dockIcon":
-        return ShowAsMode.dockIcon
-      case "menubarIcon":
-        return ShowAsMode.menubarIcon
-      default:
-        return ShowAsMode.bothIcon
-      }
-    }
-    set(newVal) {
-      //
-      var newMode: String = "bothIcon"
-      switch newVal {
-      case .bothIcon:
-        newMode = "bothIcon"
-      case .menubarIcon:
-        newMode = "menubarIcon"
-      case .dockIcon:
-        newMode = "dockIcon"
-      }
-      self["I2Pref_showAsIconMode"] = newMode
-      self.syncPref()
-    }
-  }
-
-  // Lookup by name
-  subscript(prefName:String) -> Any? {
-    get  {
-      let ret = prefObject[prefName]
-      if (ret != nil) {
-        return ret
-      }
-      return prefDefaultDict[prefName]
-    }
-    set(newValue) {
-      prefObject[prefName] = newValue
-      prefDict[prefName] = PreferenceRow(prefName, newValue, prefDefaultDict[prefName])
-      UserDefaults.standard.set(newValue, forKey: prefName)
-      self.syncPref()
-    }
-  }
-  
-  func syncPref() {
-    UserDefaults.standard.setPersistentDomain(self.prefObject, forName: Identifiers.applicationDomainId)
-    UserDefaults.standard.synchronize()
-  }
-  
-  // Lookup by index
-  subscript(index:Int) -> PreferenceRow? {
-    get  {
-      return prefDict[Array(prefDict.keys)[index]]
-    }
-    set(newValue) {
-      let pKey = Array(prefDefaultDict.keys)[index]
-      prefDict[pKey] = newValue!
-      prefObject[pKey] = newValue!.asRawValue()
-    }
-  }
-  
-  private static var sharedPreferences: Preferences = {
-    let preferences = Preferences()
-    
-    // Setup defaults
-    
-    var home = NSHomeDirectory()
-    // Add default values
-    var defaults = Dictionary<String,Any>()
-    defaults["I2Pref_enableLogging"] = true
-    defaults["I2Pref_enableVerboseLogging"] = true
-    defaults["I2Pref_autoStartRouterAtBoot"] = false
-    defaults["I2Pref_startLauncherAtLogin"] = false
-    defaults["I2Pref_startRouterAtStartup"] = true
-    defaults["I2Pref_stopRouterAtShutdown"] = true
-    defaults["I2Pref_letRouterLiveEvenLauncherDied"] = false
-    defaults["I2Pref_allowAdvancedPreferences"] = false
-    defaults["I2Pref_alsoStartFirefoxOnLaunch"] = true
-    defaults["I2Pref_useServiceManagementAsStartupTool"] = false
-    defaults["I2Pref_firefoxProfilePath"] = NSString(format: "%@/Library/Application Support/i2p/profile", home)
-    defaults["I2Pref_consolePortCheckNum"] = 7657
-    defaults["I2Pref_i2pBaseDirectory"] = NSString(format: "%@/Library/I2P", home)
-    defaults["I2Pref_i2pLogDirectory"] = NSString(format: "%@/Library/Logs/I2P", home)
-    defaults["I2Pref_showAsIconMode"] = "bothIcon"
-    defaults["I2Pref_javaCommandPath"] = "/usr/libexec/java_home -v 1.7+ --exec java "
-    defaults["I2Pref_javaCommandOptions"] = "-Xmx512M -Xms128m"
-    defaults["I2Pref_featureToggleExperimental"] = false
-    preferences.prefDefaultDict = defaults
-    
-    /*if (preferences.prefDict.isEmpty) {
-      print("Stored new user defaults")
-      preferences.addDictToPrefTable(defaults)
-    }*/
-    for name in Array(preferences.prefDefaultDict.keys) {
-      let potentialValue = UserDefaults.standard.object(forKey: name)
-      //preferences.prefDict[name] = PreferenceRow(name, potentialValue, preferences.prefDefaultDict[name])
-      preferences[name] = potentialValue
-    }
-    preferences.count = preferences.prefDict.keys.count
-    UserDefaults.standard.register(defaults: defaults)
-    UserDefaults.standard.setPersistentDomain(preferences.prefObject, forName: Identifiers.applicationDomainId)
-    UserDefaults.standard.synchronize()
-    
-    print("User Preferences loaded - Got \(preferences.count) items.")
-    
-    return preferences
-  }()
-  
-  // MARK: -
-  
-  func addDictToPrefTable(_ dict: Dictionary<String,Any>, _ emptyFirst: Bool = true) {
-    if (emptyFirst) {
-      self.prefDict.removeAll()
-    }
-    for (pKey, pVal) in dict {
-      if (pKey.starts(with: "I2P")) {
-        print("Preference -> \(pKey)")
-        self[pKey] = pVal
-      } else {
-        print("Skipping preference -> \(pKey)")
-      }
-    }
-  }
-  
-  // Initialization
-  
-  private override init() {
-    super.init()
-    let fromDisk = UserDefaults.standard.persistentDomain(forName: Identifiers.applicationDomainId) ?? Dictionary<String,Any>()
-    for (pKey, pVal) in fromDisk {
-      if (pKey.starts(with: "I2P")) {
-        print("Preference -> \(pKey)")
-        self[pKey] = pVal
-      } else {
-        print("Skipping preference -> \(pKey)")
-      }
-    }
-    print("Preferences size from disk is: \(prefObject.count).")
-    self.syncPref()
-  }
-  
-  // TODO: Make menubar icon optional
-  func getMenubarIconStateIsShowing() -> Bool {
-    return true
-  }
-  
-  // MARK: - Accessors
-  
-  class func shared() -> Preferences {
-    return sharedPreferences
-  }
-  
-  func redrawPrefTableItems() {
-    self.addDictToPrefTable(self.prefObject, false)
-  }
-  
-  
-  // MARK: - Accessors for Application Preferences
-  
-  var startRouterOnLauncherStart: Bool {
-    get {
-      let dfl = self.prefDefaultDict["I2Pref_startRouterAtStartup"] as! Bool
-      return (self["I2Pref_startRouterAtStartup"] as? Bool ?? dfl)
-    }
-    set(newValue) {
-      self["I2Pref_startRouterAtStartup"] = newValue
-      self.syncPref()
-    }
-  }
-  
-  var stopRouterOnLauncherShutdown: Bool {
-    get {
-      let dfl = self.prefDefaultDict["I2Pref_stopRouterAtShutdown"] as! Bool
-      return (self["I2Pref_stopRouterAtShutdown"] as? Bool ?? dfl)
-    }
-    set(newValue) {
-      self["I2Pref_stopRouterAtShutdown"] = newValue
-      self.syncPref()
-    }
-  }
-  
-  var allowAdvancedPreferenceEdit: Bool {
-    get {
-      let dfl = self.prefDefaultDict["I2Pref_allowAdvancedPreferences"] as! Bool
-      return (self["I2Pref_allowAdvancedPreferences"] as? Bool ?? dfl)
-    }
-    set(newValue) {
-      self["I2Pref_allowAdvancedPreferences"] = newValue
-      self.syncPref()
-    }
-  }
-  
-  var alsoStartFirefoxOnLaunch: Bool {
-    get {
-      let dfl = self.prefDefaultDict["I2Pref_alsoStartFirefoxOnLaunch"] as! Bool
-      return (self["I2Pref_alsoStartFirefoxOnLaunch"] as? Bool ?? dfl)
-    }
-    set(newValue) {
-      self["I2Pref_alsoStartFirefoxOnLaunch"] = newValue
-      self.syncPref()
-    }
-  }
-  
-  var featureToggleExperimental: Bool {
-    get {
-      let dfl = self.prefDefaultDict["I2Pref_featureToggleExperimental"] as! Bool
-      return (self["I2Pref_featureToggleExperimental"] as? Bool ?? dfl)
-    }
-    set(newValue) {
-      self["I2Pref_featureToggleExperimental"] = newValue
-      self.syncPref()
-    }
-  }
-  
-  var i2pBaseDirectory: String {
-    get {
-      let dfl = self.prefDefaultDict["I2Pref_i2pBaseDirectory"] as! String
-      return (self["I2Pref_i2pBaseDirectory"] as? String ?? dfl)
-    }
-    set(newValue) {
-      // TODO: Check if string is a valid directory path, and that it exists.
-      self["I2Pref_i2pBaseDirectory"] = newValue
-      self.syncPref()
-    }
-  }
-  
-  var i2pLogDirectory: String {
-    get {
-      let dfl = self.prefDefaultDict["I2Pref_i2pLogDirectory"] as! String
-      return (self["I2Pref_i2pLogDirectory"] as? String ?? dfl)
-    }
-    set(newValue) {
-      // TODO: Check if string is a valid java command path, check if it executes with -version.
-      self["I2Pref_i2pLogDirectory"] = newValue
-      self.syncPref()
-    }
-  }
-  
-  var javaCommandPath: String {
-    get {
-      let dfl = self.prefDefaultDict["I2Pref_javaCommandPath"] as! String
-      return (self["I2Pref_javaCommandPath"] as? String ?? dfl)
-    }
-    set(newValue) {
-      // TODO: Check if string is a valid java command path, check if it executes with -version.
-      self["I2Pref_javaCommandPath"] = newValue
-      self.syncPref()
-    }
-  }
-  
-  var javaCommandOptions: String {
-    get {
-      let dfl = self.prefDefaultDict["I2Pref_javaCommandOptions"] as! String
-      return (self["I2Pref_javaCommandOptions"] as? String ?? dfl)
-    }
-    set(newValue) {
-      // TODO: Check if string is a valid set of java options
-      self["I2Pref_javaCommandOptions"] = newValue
-      self.syncPref()
-    }
-  }
-  
-  
-}
-
diff --git a/launchers/macosx/CommonCode/Utils/ReflectionFunctions.swift b/launchers/macosx/CommonCode/Utils/ReflectionFunctions.swift
deleted file mode 100644
index cae4c6ad4198a0cc804eeb6c5829c0bcd3564157..0000000000000000000000000000000000000000
--- a/launchers/macosx/CommonCode/Utils/ReflectionFunctions.swift
+++ /dev/null
@@ -1,57 +0,0 @@
-//
-//  ReflectionFunctions.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 17/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-class ReflectionFunctions {
-  
-  /// Given pointer to first element of a C array, invoke a function for each element
-  func enumerateCArray<T>(array: UnsafePointer<T>, count: UInt32, f: (UInt32, T) -> ()) {
-    var ptr = array
-    for i in 0..<count {
-      f(i, ptr.pointee)
-      ptr = ptr.successor()
-    }
-  }
-  
-  /// Return name for a method
-  func methodName(m: Method) -> String? {
-    let sel = method_getName(m)
-    let nameCString = sel_getName(sel)
-    return String(cString: nameCString)
-  }
-  
-  /// Print the names for each method in a class
-  func printMethodNamesForClass(cls: AnyClass) {
-    var methodCount: UInt32 = 0
-    let methodList = class_copyMethodList(cls, &methodCount)
-    if methodList != nil && methodCount > 0 {
-      enumerateCArray(array: methodList!, count: methodCount) { i, m in
-        let name = methodName(m: m) ?? "unknown"
-        print("#\(i): \(name)")
-      }
-      
-      free(methodList)
-    }
-  }
-  
-  /// Print the names for each method in a class with a specified name
-  func printMethodNamesForClassNamed(classname: String) {
-    // NSClassFromString() is declared to return AnyClass!, but should be AnyClass?
-    let maybeClass: AnyClass? = NSClassFromString(classname)
-    if let cls: AnyClass = maybeClass {
-      printMethodNamesForClass(cls: cls)
-    }
-    else {
-      print("\(classname): no such class")
-    }
-  }
-}
-
-
-
diff --git a/launchers/macosx/CommonCode/Utils/Startup.swift b/launchers/macosx/CommonCode/Utils/Startup.swift
deleted file mode 100644
index 6e36193be252ccc906e5062caf590ad167aa24ea..0000000000000000000000000000000000000000
--- a/launchers/macosx/CommonCode/Utils/Startup.swift
+++ /dev/null
@@ -1,119 +0,0 @@
-//
-//  Startup.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 22/12/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-
-class Startup : NSObject {
-  
-  let loginItemsList : LSSharedFileList = LSSharedFileListCreate(nil, kLSSharedFileListSessionLoginItems.takeRetainedValue(), nil).takeRetainedValue();
-  
-  
-  
-  func addLoginItem(_ path: CFURL) -> Bool {
-    
-    if(getLoginItem(path) != nil) {
-      print("Login Item has already been added to the list.");
-      return true;
-    }
-    
-    let path : CFURL = CFURLCreateWithString(nil, Bundle.main.bundleURL.absoluteString as CFString, nil);
-    print("Path adding to Login Item list is: ", path);
-    
-    // add new Login Item at the end of Login Items list
-    if let loginItem = LSSharedFileListInsertItemURL(loginItemsList,
-                                                     getLastLoginItemInList(),
-                                                     nil, nil,
-                                                     path,
-                                                     nil, nil) {
-      print("Added login item is: ", loginItem);
-      return true;
-    }
-    
-    return false;
-  }
-  
-  
-  func removeLoginItem(_ path: CFURL) -> Bool {
-    
-    // remove Login Item from the Login Items list
-    if let oldLoginItem = getLoginItem(path) {
-      print("Old login item is: ", oldLoginItem);
-      if(LSSharedFileListItemRemove(loginItemsList, oldLoginItem) == noErr) {
-        return true;
-      }
-      return false;
-    }
-    print("Login Item for given path not found in the list.");
-    return true;
-  }
-  
-  
-  func getLoginItem(_ path : CFURL) -> LSSharedFileListItem! {
-    
-    let path : CFURL = CFURLCreateWithString(nil, Bundle.main.bundleURL.absoluteString as CFString, nil);
-    
-    
-    // Copy all login items in the list
-    let loginItems : NSArray = LSSharedFileListCopySnapshot(loginItemsList, nil).takeRetainedValue();
-    
-    var foundLoginItem : LSSharedFileListItem?;
-    var nextItemUrl : Unmanaged<CFURL>?;
-    
-    // Iterate through login items to find one for given path
-    print("App URL: ", path);
-    for var i in (0..<loginItems.count)  // CFArrayGetCount(loginItems)
-    {
-      
-      let nextLoginItem : LSSharedFileListItem = loginItems.object(at: i) as! LSSharedFileListItem; // CFArrayGetValueAtIndex(loginItems, i).;
-      
-      
-      if(LSSharedFileListItemResolve(nextLoginItem, 0, &nextItemUrl, nil) == noErr) {
-        
-        
-        
-        print("Next login item URL: ", nextItemUrl!.takeUnretainedValue());
-        // compare searched item URL passed in argument with next item URL
-        if(nextItemUrl!.takeRetainedValue() == path) {
-          foundLoginItem = nextLoginItem;
-        }
-      }
-    }
-    
-    return foundLoginItem;
-  }
-  
-  func getLastLoginItemInList() -> LSSharedFileListItem! {
-    
-    // Copy all login items in the list
-    let loginItems : NSArray = LSSharedFileListCopySnapshot(loginItemsList, nil).takeRetainedValue() as NSArray;
-    if(loginItems.count > 0) {
-      let lastLoginItem = loginItems.lastObject as! LSSharedFileListItem;
-      
-      print("Last login item is: ", lastLoginItem);
-      return lastLoginItem
-    }
-    
-    return kLSSharedFileListItemBeforeFirst.takeRetainedValue();
-  }
-  
-  func isLoginItemInList(_ path : CFURL) -> Bool {
-    
-    if(getLoginItem(path) != nil) {
-      return true;
-    }
-    
-    return false;
-  }
-  
-  static func appPath() -> CFURL {
-    
-    return NSURL.fileURL(withPath: Bundle.main.bundlePath) as CFURL;
-  }
-  
-}
diff --git a/launchers/macosx/CommonCode/Utils/StringExtensions.swift b/launchers/macosx/CommonCode/Utils/StringExtensions.swift
deleted file mode 100644
index 0264b64af8f0d36c64a506bdd2535bc94cb1ca8f..0000000000000000000000000000000000000000
--- a/launchers/macosx/CommonCode/Utils/StringExtensions.swift
+++ /dev/null
@@ -1,106 +0,0 @@
-//
-//  StringExtensions.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 17/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-extension String {
-  
-  func replace(target: String, withString: String) -> String
-  {
-    return self.replacingOccurrences(of: target, with: withString, options: NSString.CompareOptions.literal, range: nil)
-  }
-  
-  /// Returns an array of string obtained splitting self at each newline ("\n").
-  /// If the last character is a newline, it will be ignored (no empty string
-  /// will be appended at the end of the array)
-  public func splitByNewline() -> [String] {
-    return self.split { $0 == "\n" }.map(String.init)
-  }
-  
-  /// Returns an array of string obtained splitting self at each space, newline or TAB character
-  public func splitByWhitespace() -> [String] {
-    let whitespaces = Set<Character>([" ", "\n", "\t"])
-    return self.split { whitespaces.contains($0) }.map(String.init)
-  }
-  
-  public func splitByColon() -> [String] {
-    return self.split { $0 == ":" }.map(String.init)
-  }
-  
-  func leftPadding(toLength: Int, withPad character: Character) -> String {
-    let stringLength = self.count
-    if stringLength < toLength {
-      return String(repeatElement(character, count: toLength - stringLength)) + self
-    } else {
-      return String(self.suffix(toLength))
-    }
-  }
-}
-
-
-extension String {
-  subscript (i: Int) -> Character {
-    return self[index(startIndex, offsetBy: i)]
-  }
-  subscript (bounds: CountableRange<Int>) -> Substring {
-    let start = index(startIndex, offsetBy: bounds.lowerBound)
-    let end = index(startIndex, offsetBy: bounds.upperBound)
-    return self[start ..< end]
-  }
-  subscript (bounds: CountableClosedRange<Int>) -> Substring {
-    let start = index(startIndex, offsetBy: bounds.lowerBound)
-    let end = index(startIndex, offsetBy: bounds.upperBound)
-    return self[start ... end]
-  }
-  subscript (bounds: CountablePartialRangeFrom<Int>) -> Substring {
-    let start = index(startIndex, offsetBy: bounds.lowerBound)
-    let end = index(endIndex, offsetBy: -1)
-    return self[start ... end]
-  }
-  subscript (bounds: PartialRangeThrough<Int>) -> Substring {
-    let end = index(startIndex, offsetBy: bounds.upperBound)
-    return self[startIndex ... end]
-  }
-  subscript (bounds: PartialRangeUpTo<Int>) -> Substring {
-    let end = index(startIndex, offsetBy: bounds.upperBound)
-    return self[startIndex ..< end]
-  }
-}
-
-/*
- * This is functions for comparing version numbers.
- * Example usage:
- *   "3.0.0" >= "3.0.0.1" // false
- *   "3.0.0" > "3.0.0.1" // false
- *   "3.0.0" <= "3.0.0.1" // true
- *   "3.0.0.1" >= "3.0.0.1" // true
- */
-extension String {
-  
-  static func ==(lhs: String, rhs: String) -> Bool {
-    return lhs.compare(rhs, options: .numeric) == .orderedSame
-  }
-  
-  static func <(lhs: String, rhs: String) -> Bool {
-    return lhs.compare(rhs, options: .numeric) == .orderedAscending
-  }
-  
-  static func <=(lhs: String, rhs: String) -> Bool {
-    return lhs.compare(rhs, options: .numeric) == .orderedAscending || lhs.compare(rhs, options: .numeric) == .orderedSame
-  }
-  
-  static func >(lhs: String, rhs: String) -> Bool {
-    return lhs.compare(rhs, options: .numeric) == .orderedDescending
-  }
-  
-  static func >=(lhs: String, rhs: String) -> Bool {
-    return lhs.compare(rhs, options: .numeric) == .orderedDescending || lhs.compare(rhs, options: .numeric) == .orderedSame
-  }
-  
-}
-
diff --git a/launchers/macosx/I2PLauncher.xcodeproj/project.pbxproj b/launchers/macosx/I2PLauncher.xcodeproj/project.pbxproj
deleted file mode 100644
index 4e9fa57f9cc00b022aa778317a7f897ea184daab..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher.xcodeproj/project.pbxproj
+++ /dev/null
@@ -1,1796 +0,0 @@
-// !$*UTF8*$!
-{
-	archiveVersion = 1;
-	classes = {
-	};
-	objectVersion = 47;
-	objects = {
-
-/* Begin PBXBuildFile section */
-		55459244D38FD36955E91F82 /* Pods_I2PLauncher.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = AF1CEEADE02906132180EEE5 /* Pods_I2PLauncher.framework */; };
-		BF07789721506C810014EB07 /* Storyboard.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = BF07789621506C810014EB07 /* Storyboard.storyboard */; };
-		BF07789E21506D2B0014EB07 /* PopoverViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF07789C21506D2B0014EB07 /* PopoverViewController.swift */; };
-		BF0956E721EAD3590014EB07 /* profile.tgz in Resources */ = {isa = PBXBuildFile; fileRef = BF0956E621EAD3590014EB07 /* profile.tgz */; };
-		BF14B70F215C98DC0014EB07 /* LoggerWorker.cpp in Sources */ = {isa = PBXBuildFile; fileRef = BF14B70D215C98DC0014EB07 /* LoggerWorker.cpp */; };
-		BF14B710215C98DC0014EB07 /* Logger.mm in Sources */ = {isa = PBXBuildFile; fileRef = BF14B70E215C98DC0014EB07 /* Logger.mm */; };
-		BF14B712215D9E040014EB07 /* FolderContentMonitor.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF14B711215D9E040014EB07 /* FolderContentMonitor.swift */; };
-		BF1D6D8F21BB32460014EB07 /* Preferences.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = BF1D6D8E21BB32460014EB07 /* Preferences.storyboard */; };
-		BF1D6D9121BB344D0014EB07 /* Preferences.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6D9021BB344D0014EB07 /* Preferences.swift */; };
-		BF1D6D9321BB36880014EB07 /* PreferencesViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6D9221BB36880014EB07 /* PreferencesViewController.swift */; };
-		BF1D6D9521BB379A0014EB07 /* PreferencesWindowController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6D9421BB379A0014EB07 /* PreferencesWindowController.swift */; };
-		BF1D6D9921BB7DC10014EB07 /* FirefoxManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6D9821BB7DC10014EB07 /* FirefoxManager.swift */; };
-		BF1D6D9B21BB86520014EB07 /* ConsoleWebView.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = BF1D6D9A21BB86520014EB07 /* ConsoleWebView.storyboard */; };
-		BF1D6D9D21BB87000014EB07 /* EmbeddedConsoleView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6D9C21BB87000014EB07 /* EmbeddedConsoleView.swift */; };
-		BF1D6D9F21BBA1460014EB07 /* WebKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = BF1D6D9E21BBA1460014EB07 /* WebKit.framework */; settings = {ATTRIBUTES = (Weak, ); }; };
-		BF1D6DA321BBB8120014EB07 /* AdvancedTableView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6DA221BBB8120014EB07 /* AdvancedTableView.swift */; };
-		BF1D6DA521BBB84E0014EB07 /* PreferencesViewController+TableView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6DA421BBB84E0014EB07 /* PreferencesViewController+TableView.swift */; };
-		BF1EFA3A215140E60014EB07 /* SBridge.mm in Sources */ = {isa = PBXBuildFile; fileRef = BF1EFA39215140E60014EB07 /* SBridge.mm */; };
-		BF1EFA40215141110014EB07 /* main.mm in Sources */ = {isa = PBXBuildFile; fileRef = BF1EFA3D215141100014EB07 /* main.mm */; };
-		BF1EFA41215141110014EB07 /* RouterTask.mm in Sources */ = {isa = PBXBuildFile; fileRef = BF1EFA3E215141100014EB07 /* RouterTask.mm */; };
-		BF1EFA47215141640014EB07 /* base.zip in Resources */ = {isa = PBXBuildFile; fileRef = BF1EFA44215141630014EB07 /* base.zip */; };
-		BF1EFA48215141640014EB07 /* ItoopieTransparent.png in Resources */ = {isa = PBXBuildFile; fileRef = BF1EFA45215141640014EB07 /* ItoopieTransparent.png */; };
-		BF3143FE2160C1BD0014EB07 /* DownloadJavaViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF3143FD2160C1BD0014EB07 /* DownloadJavaViewController.swift */; };
-		BF5061702113C48E0014EB07 /* I2PLauncher.xcdatamodeld in Sources */ = {isa = PBXBuildFile; fileRef = BF50616E2113C48E0014EB07 /* I2PLauncher.xcdatamodeld */; };
-		BF5061722113C4900014EB07 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = BF5061712113C4900014EB07 /* Assets.xcassets */; };
-		BF5061752113C4900014EB07 /* UserInterfaces.xib in Resources */ = {isa = PBXBuildFile; fileRef = BF5061732113C4900014EB07 /* UserInterfaces.xib */; };
-		BF5061962113C84E0014EB07 /* Cocoa.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = BF5061952113C84E0014EB07 /* Cocoa.framework */; };
-		BF5315072150C55B0014EB07 /* RouterRunner.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF5315062150C55B0014EB07 /* RouterRunner.swift */; };
-		BF53150D2150CE310014EB07 /* DateTimeUtils.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF53150C2150CE310014EB07 /* DateTimeUtils.swift */; };
-		BF5315132150EB510014EB07 /* RouterProcessStatus+ObjectiveC.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF5315122150EB510014EB07 /* RouterProcessStatus+ObjectiveC.swift */; };
-		BF531515215105B40014EB07 /* LogViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF531514215105B40014EB07 /* LogViewController.swift */; };
-		BF650CA92152AC7D0014EB07 /* bumpInfoPlist.sh in Resources */ = {isa = PBXBuildFile; fileRef = BF650CA52152AC7D0014EB07 /* bumpInfoPlist.sh */; };
-		BF650CAB2152AC7D0014EB07 /* Deployer.mm in Sources */ = {isa = PBXBuildFile; fileRef = BF650CA72152AC7D0014EB07 /* Deployer.mm */; };
-		BF7506CB21509CFD0014EB07 /* RouterProcessStatus.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF7506CA21509CFD0014EB07 /* RouterProcessStatus.swift */; };
-		BF86541321515CA00014EB07 /* launcher.jar in Resources */ = {isa = PBXBuildFile; fileRef = BF1EFA46215141640014EB07 /* launcher.jar */; };
-		BF865417215182820014EB07 /* Foundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = BF865416215182820014EB07 /* Foundation.framework */; };
-		BF99FD3F227087A40014EB07 /* main.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF99FD3E227087A40014EB07 /* main.swift */; };
-		BF99FD4422708AB10014EB07 /* Identifiers.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF99FD4322708AB10014EB07 /* Identifiers.swift */; };
-		BF99FD4522708BA80014EB07 /* Identifiers.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF99FD4322708AB10014EB07 /* Identifiers.swift */; };
-		BF99FD4722708DA70014EB07 /* DispatchQueue+delay.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF99FD4622708DA70014EB07 /* DispatchQueue+delay.swift */; };
-		BFA392FC2259E89B0014EB07 /* NetworkUtil.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFA392FB2259E89B0014EB07 /* NetworkUtil.swift */; };
-		BFA5226221CD43480014EB07 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFA5226121CD43480014EB07 /* AppDelegate.swift */; };
-		BFA5226421CD434A0014EB07 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = BFA5226321CD434A0014EB07 /* Assets.xcassets */; };
-		BFA5226E21CD44740014EB07 /* StartupItemApp.app in CopyFiles */ = {isa = PBXBuildFile; fileRef = BFA5225F21CD43480014EB07 /* StartupItemApp.app */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
-		BFA5227021CDBF450014EB07 /* Startup.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFA5226F21CDBF450014EB07 /* Startup.swift */; };
-		BFAA37EA226891760014EB07 /* icon.icns in Resources */ = {isa = PBXBuildFile; fileRef = BFAA37E9226891760014EB07 /* icon.icns */; };
-		BFAA37EC226891760014EB07 /* ShareViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFAA37EB226891760014EB07 /* ShareViewController.swift */; };
-		BFAA37EF226891760014EB07 /* ShareViewController.xib in Resources */ = {isa = PBXBuildFile; fileRef = BFAA37ED226891760014EB07 /* ShareViewController.xib */; };
-		BFAA37F4226891760014EB07 /* I2PSnark-Share.appex in Embed App Extensions */ = {isa = PBXBuildFile; fileRef = BFAA37E7226891760014EB07 /* I2PSnark-Share.appex */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
-		BFAA37FA226892CA0014EB07 /* StringExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF52150428D0014EB07 /* StringExtensions.swift */; };
-		BFAA37FB226892CA0014EB07 /* ArrayExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF7215047FE0014EB07 /* ArrayExtensions.swift */; };
-		BFAA37FC226892CA0014EB07 /* DateTimeUtils.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF53150C2150CE310014EB07 /* DateTimeUtils.swift */; };
-		BFAA37FD226892CA0014EB07 /* EventManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFE16BF92156DAED0014EB07 /* EventManager.swift */; };
-		BFAA37FE226892CA0014EB07 /* FolderContentMonitor.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF14B711215D9E040014EB07 /* FolderContentMonitor.swift */; };
-		BFAD9C94227C92480014EB07 /* Preferences.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6D9021BB344D0014EB07 /* Preferences.swift */; };
-		BFAD9C95227C925F0014EB07 /* Identifiers.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF99FD4322708AB10014EB07 /* Identifiers.swift */; };
-		BFBDCAE9215040670014EB07 /* Subprocess.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAE8215040670014EB07 /* Subprocess.swift */; };
-		BFBDCAEB215041630014EB07 /* TaskPipeline.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAEA215041630014EB07 /* TaskPipeline.swift */; };
-		BFBDCAED215041C10014EB07 /* Subprocess+CompactAPI.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAEC215041C10014EB07 /* Subprocess+CompactAPI.swift */; };
-		BFBDCAEF215041E30014EB07 /* Error.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAEE215041E30014EB07 /* Error.swift */; };
-		BFBDCAF12150420C0014EB07 /* ExecutionResult.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF02150420C0014EB07 /* ExecutionResult.swift */; };
-		BFBDCAF4215042670014EB07 /* AppleStuffExceptionHandler.m in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF3215042670014EB07 /* AppleStuffExceptionHandler.m */; };
-		BFBDCAF62150428D0014EB07 /* StringExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF52150428D0014EB07 /* StringExtensions.swift */; };
-		BFBDCAF8215047FE0014EB07 /* ArrayExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF7215047FE0014EB07 /* ArrayExtensions.swift */; };
-		BFBDCAFA215050810014EB07 /* ReflectionFunctions.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF9215050810014EB07 /* ReflectionFunctions.swift */; };
-		BFBDCAFE2150567D0014EB07 /* SwiftApplicationDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAFD2150567D0014EB07 /* SwiftApplicationDelegate.swift */; };
-		BFBDCB0021505BEE0014EB07 /* AppKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = BFBDCAFF21505BED0014EB07 /* AppKit.framework */; };
-		BFBDCB02215060190014EB07 /* DetectJava.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCB01215060190014EB07 /* DetectJava.swift */; };
-		BFBDCB04215060970014EB07 /* StatusBarController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCB03215060970014EB07 /* StatusBarController.swift */; };
-		BFD289912277BEDA0014EB07 /* Sparkle.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = BFD289902277BED90014EB07 /* Sparkle.framework */; };
-		BFD289922277BEDA0014EB07 /* Sparkle.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = BFD289902277BED90014EB07 /* Sparkle.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; };
-		BFD2899A227810AF0014EB07 /* StatusBarController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCB03215060970014EB07 /* StatusBarController.swift */; };
-		BFD2899B227810AF0014EB07 /* ArrayExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF7215047FE0014EB07 /* ArrayExtensions.swift */; };
-		BFD2899C227810AF0014EB07 /* RouterRunner.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF5315062150C55B0014EB07 /* RouterRunner.swift */; };
-		BFD2899D227810AF0014EB07 /* Identifiers.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF99FD4322708AB10014EB07 /* Identifiers.swift */; };
-		BFD2899E227810AF0014EB07 /* EventManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFE16BF92156DAED0014EB07 /* EventManager.swift */; };
-		BFD2899F227810AF0014EB07 /* ExecutionResult.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF02150420C0014EB07 /* ExecutionResult.swift */; };
-		BFD289A0227810AF0014EB07 /* RouterStatusView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFE16BF72156C61E0014EB07 /* RouterStatusView.swift */; };
-		BFD289A1227810AF0014EB07 /* Error.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAEE215041E30014EB07 /* Error.swift */; };
-		BFD289A2227810AF0014EB07 /* RouterTask.mm in Sources */ = {isa = PBXBuildFile; fileRef = BF1EFA3E215141100014EB07 /* RouterTask.mm */; };
-		BFD289A3227810AF0014EB07 /* NetworkUtil.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFA392FB2259E89B0014EB07 /* NetworkUtil.swift */; };
-		BFD289A4227810AF0014EB07 /* RouterProcessStatus.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF7506CA21509CFD0014EB07 /* RouterProcessStatus.swift */; };
-		BFD289A5227810AF0014EB07 /* Subprocess.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAE8215040670014EB07 /* Subprocess.swift */; };
-		BFD289A6227810AF0014EB07 /* PreferencesViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6D9221BB36880014EB07 /* PreferencesViewController.swift */; };
-		BFD289A7227810AF0014EB07 /* FirefoxManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6D9821BB7DC10014EB07 /* FirefoxManager.swift */; };
-		BFD289A8227810AF0014EB07 /* ReflectionFunctions.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF9215050810014EB07 /* ReflectionFunctions.swift */; };
-		BFD289A9227810AF0014EB07 /* Subprocess+CompactAPI.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAEC215041C10014EB07 /* Subprocess+CompactAPI.swift */; };
-		BFD289AA227810AF0014EB07 /* DetectJava.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCB01215060190014EB07 /* DetectJava.swift */; };
-		BFD289AB227810AF0014EB07 /* PopoverViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF07789C21506D2B0014EB07 /* PopoverViewController.swift */; };
-		BFD289AC227810AF0014EB07 /* AdvancedTableView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6DA221BBB8120014EB07 /* AdvancedTableView.swift */; };
-		BFD289AD227810AF0014EB07 /* DispatchQueue+delay.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF99FD4622708DA70014EB07 /* DispatchQueue+delay.swift */; };
-		BFD289AE227810AF0014EB07 /* LaunchAgentManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD899462169F01B0014EB07 /* LaunchAgentManager.swift */; };
-		BFD289AF227810AF0014EB07 /* Deployer.mm in Sources */ = {isa = PBXBuildFile; fileRef = BF650CA72152AC7D0014EB07 /* Deployer.mm */; };
-		BFD289B0227810AF0014EB07 /* PreferencesViewController+TableView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6DA421BBB84E0014EB07 /* PreferencesViewController+TableView.swift */; };
-		BFD289B1227810AF0014EB07 /* main.mm in Sources */ = {isa = PBXBuildFile; fileRef = BF1EFA3D215141100014EB07 /* main.mm */; };
-		BFD289B2227810AF0014EB07 /* AppleStuffExceptionHandler.m in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF3215042670014EB07 /* AppleStuffExceptionHandler.m */; };
-		BFD289B3227810AF0014EB07 /* DownloadJavaViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF3143FD2160C1BD0014EB07 /* DownloadJavaViewController.swift */; };
-		BFD289B4227810AF0014EB07 /* PreferencesWindowController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6D9421BB379A0014EB07 /* PreferencesWindowController.swift */; };
-		BFD289B5227810AF0014EB07 /* LogViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF531514215105B40014EB07 /* LogViewController.swift */; };
-		BFD289B6227810AF0014EB07 /* Startup.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFA5226F21CDBF450014EB07 /* Startup.swift */; };
-		BFD289B7227810AF0014EB07 /* RouterProcessStatus+ObjectiveC.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF5315122150EB510014EB07 /* RouterProcessStatus+ObjectiveC.swift */; };
-		BFD289B8227810AF0014EB07 /* Preferences.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6D9021BB344D0014EB07 /* Preferences.swift */; };
-		BFD289B9227810AF0014EB07 /* LaunchAgent+Status.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD899442169EFE90014EB07 /* LaunchAgent+Status.swift */; };
-		BFD289BA227810AF0014EB07 /* FolderContentMonitor.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF14B711215D9E040014EB07 /* FolderContentMonitor.swift */; };
-		BFD289BB227810AF0014EB07 /* SwiftApplicationDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAFD2150567D0014EB07 /* SwiftApplicationDelegate.swift */; };
-		BFD289BC227810AF0014EB07 /* LaunchAgent.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD899422169EE9F0014EB07 /* LaunchAgent.swift */; };
-		BFD289BD227810AF0014EB07 /* RouterManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFDD81D92156B3E30014EB07 /* RouterManager.swift */; };
-		BFD289BE227810AF0014EB07 /* SBridge.mm in Sources */ = {isa = PBXBuildFile; fileRef = BF1EFA39215140E60014EB07 /* SBridge.mm */; };
-		BFD289BF227810AF0014EB07 /* LoggerWorker.cpp in Sources */ = {isa = PBXBuildFile; fileRef = BF14B70D215C98DC0014EB07 /* LoggerWorker.cpp */; };
-		BFD289C0227810AF0014EB07 /* EmbeddedConsoleView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6D9C21BB87000014EB07 /* EmbeddedConsoleView.swift */; };
-		BFD289C1227810AF0014EB07 /* Logger.mm in Sources */ = {isa = PBXBuildFile; fileRef = BF14B70E215C98DC0014EB07 /* Logger.mm */; };
-		BFD289C2227810AF0014EB07 /* StringExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF52150428D0014EB07 /* StringExtensions.swift */; };
-		BFD289C3227810AF0014EB07 /* I2PLauncher.xcdatamodeld in Sources */ = {isa = PBXBuildFile; fileRef = BF50616E2113C48E0014EB07 /* I2PLauncher.xcdatamodeld */; };
-		BFD289C4227810AF0014EB07 /* TaskPipeline.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAEA215041630014EB07 /* TaskPipeline.swift */; };
-		BFD289C5227810AF0014EB07 /* DateTimeUtils.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF53150C2150CE310014EB07 /* DateTimeUtils.swift */; };
-		BFD289C7227810AF0014EB07 /* WebKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = BF1D6D9E21BBA1460014EB07 /* WebKit.framework */; settings = {ATTRIBUTES = (Weak, ); }; };
-		BFD289C8227810AF0014EB07 /* CoreFoundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = BFE1CBAC2151908F0014EB07 /* CoreFoundation.framework */; };
-		BFD289C9227810AF0014EB07 /* Foundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = BF865416215182820014EB07 /* Foundation.framework */; };
-		BFD289CB227810AF0014EB07 /* AppKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = BFBDCAFF21505BED0014EB07 /* AppKit.framework */; };
-		BFD289CC227810AF0014EB07 /* Cocoa.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = BF5061952113C84E0014EB07 /* Cocoa.framework */; };
-		BFD289D0227810AF0014EB07 /* profile.tgz in Resources */ = {isa = PBXBuildFile; fileRef = BF0956E621EAD3590014EB07 /* profile.tgz */; };
-		BFD289D1227810AF0014EB07 /* launcher.jar in Resources */ = {isa = PBXBuildFile; fileRef = BF1EFA46215141640014EB07 /* launcher.jar */; };
-		BFD289D2227810AF0014EB07 /* bumpInfoPlist.sh in Resources */ = {isa = PBXBuildFile; fileRef = BF650CA52152AC7D0014EB07 /* bumpInfoPlist.sh */; };
-		BFD289D3227810AF0014EB07 /* Storyboard.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = BF07789621506C810014EB07 /* Storyboard.storyboard */; };
-		BFD289D4227810AF0014EB07 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = BF5061712113C4900014EB07 /* Assets.xcassets */; };
-		BFD289D5227810AF0014EB07 /* UserInterfaces.xib in Resources */ = {isa = PBXBuildFile; fileRef = BF5061732113C4900014EB07 /* UserInterfaces.xib */; };
-		BFD289D6227810AF0014EB07 /* ItoopieTransparent.png in Resources */ = {isa = PBXBuildFile; fileRef = BF1EFA45215141640014EB07 /* ItoopieTransparent.png */; };
-		BFD289D7227810AF0014EB07 /* base.zip in Resources */ = {isa = PBXBuildFile; fileRef = BF1EFA44215141630014EB07 /* base.zip */; };
-		BFD289D8227810AF0014EB07 /* Preferences.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = BF1D6D8E21BB32460014EB07 /* Preferences.storyboard */; };
-		BFD289D9227810AF0014EB07 /* ConsoleWebView.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = BF1D6D9A21BB86520014EB07 /* ConsoleWebView.storyboard */; };
-		BFD289DB227810AF0014EB07 /* StartupItemApp.app in CopyFiles */ = {isa = PBXBuildFile; fileRef = BFA5225F21CD43480014EB07 /* StartupItemApp.app */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
-		BFD289DD227810AF0014EB07 /* I2PSnark-Share.appex in Embed App Extensions */ = {isa = PBXBuildFile; fileRef = BFAA37E7226891760014EB07 /* I2PSnark-Share.appex */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
-		BFD289E7227812C10014EB07 /* SwitchableTableViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD289E6227812C10014EB07 /* SwitchableTableViewController.swift */; };
-		BFD289E9227812F20014EB07 /* ServiceTableViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD289E8227812F20014EB07 /* ServiceTableViewController.swift */; };
-		BFD289EB227813A60014EB07 /* BottomBar.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD289EA227813A60014EB07 /* BottomBar.swift */; };
-		BFD289ED227813EB0014EB07 /* AppearanceObserver.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD289EC227813EB0014EB07 /* AppearanceObserver.swift */; };
-		BFD289EF227814240014EB07 /* CustomScrollView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD289EE227814240014EB07 /* CustomScrollView.swift */; };
-		BFD289F12278144A0014EB07 /* Icons.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD289F02278144A0014EB07 /* Icons.swift */; };
-		BFD289F3227814AC0014EB07 /* Service.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD289F2227814AC0014EB07 /* Service.swift */; };
-		BFD289F5227818DA0014EB07 /* StatusIndicator.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD289F4227818DA0014EB07 /* StatusIndicator.swift */; };
-		BFD289F72278192B0014EB07 /* ServiceTableRowView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD289F62278192B0014EB07 /* ServiceTableRowView.swift */; };
-		BFD289F92278194D0014EB07 /* StatusTableCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD289F82278194D0014EB07 /* StatusTableCell.swift */; };
-		BFD289FD227821410014EB07 /* EditorTableCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD289FC227821410014EB07 /* EditorTableCell.swift */; };
-		BFD289FF227821690014EB07 /* EditorTableViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD289FE227821690014EB07 /* EditorTableViewController.swift */; };
-		BFD28A012278218F0014EB07 /* SectionHeaderView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD28A002278218F0014EB07 /* SectionHeaderView.swift */; };
-		BFD28A03227821D00014EB07 /* SettingsView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD28A02227821D00014EB07 /* SettingsView.swift */; };
-		BFD28A062278269A0014EB07 /* RouterServices.plist in Resources */ = {isa = PBXBuildFile; fileRef = BFD28A052278269A0014EB07 /* RouterServices.plist */; };
-		BFD28A09227830EF0014EB07 /* I2PRouterService.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD28A08227830EF0014EB07 /* I2PRouterService.swift */; };
-		BFD28A0B227833E80014EB07 /* HttpTunnelService.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD28A0A227833E80014EB07 /* HttpTunnelService.swift */; };
-		BFD28A0D227834120014EB07 /* IrcTunnelService.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD28A0C227834120014EB07 /* IrcTunnelService.swift */; };
-		BFD899432169EE9F0014EB07 /* LaunchAgent.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD899422169EE9F0014EB07 /* LaunchAgent.swift */; };
-		BFD899452169EFE90014EB07 /* LaunchAgent+Status.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD899442169EFE90014EB07 /* LaunchAgent+Status.swift */; };
-		BFD899472169F01B0014EB07 /* LaunchAgentManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFD899462169F01B0014EB07 /* LaunchAgentManager.swift */; };
-		BFDD81DA2156B3E30014EB07 /* RouterManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFDD81D92156B3E30014EB07 /* RouterManager.swift */; };
-		BFE16BF82156C61E0014EB07 /* RouterStatusView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFE16BF72156C61E0014EB07 /* RouterStatusView.swift */; };
-		BFE16BFA2156DAED0014EB07 /* EventManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFE16BF92156DAED0014EB07 /* EventManager.swift */; };
-		BFE1CBAD2151908F0014EB07 /* CoreFoundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = BFE1CBAC2151908F0014EB07 /* CoreFoundation.framework */; };
-		BFFDBCCF227B50410014EB07 /* StringExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF52150428D0014EB07 /* StringExtensions.swift */; };
-		BFFDBCD0227B50410014EB07 /* ArrayExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF7215047FE0014EB07 /* ArrayExtensions.swift */; };
-		BFFDBCD1227B50410014EB07 /* Preferences.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF1D6D9021BB344D0014EB07 /* Preferences.swift */; };
-		BFFDBCD2227B50410014EB07 /* DetectJava.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCB01215060190014EB07 /* DetectJava.swift */; };
-		BFFDBCD3227B50410014EB07 /* Subprocess.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAE8215040670014EB07 /* Subprocess.swift */; };
-		BFFDBCD4227B50410014EB07 /* TaskPipeline.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAEA215041630014EB07 /* TaskPipeline.swift */; };
-		BFFDBCD5227B50410014EB07 /* Subprocess+CompactAPI.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAEC215041C10014EB07 /* Subprocess+CompactAPI.swift */; };
-		BFFDBCD6227B50410014EB07 /* Error.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAEE215041E30014EB07 /* Error.swift */; };
-		BFFDBCD7227B50410014EB07 /* ExecutionResult.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF02150420C0014EB07 /* ExecutionResult.swift */; };
-		BFFDBCD8227B50410014EB07 /* AppleStuffExceptionHandler.h in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF22150422C0014EB07 /* AppleStuffExceptionHandler.h */; };
-		BFFDBCD9227B50410014EB07 /* AppleStuffExceptionHandler.m in Sources */ = {isa = PBXBuildFile; fileRef = BFBDCAF3215042670014EB07 /* AppleStuffExceptionHandler.m */; };
-		BFFDBCDB227B50EE0014EB07 /* I2PLauncher-Bridging-Header.h in Sources */ = {isa = PBXBuildFile; fileRef = BFF45818213C428E0014EB07 /* I2PLauncher-Bridging-Header.h */; };
-		BFFDBCDC227B50FB0014EB07 /* Identifiers.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF99FD4322708AB10014EB07 /* Identifiers.swift */; };
-/* End PBXBuildFile section */
-
-/* Begin PBXContainerItemProxy section */
-		BFAA37F2226891760014EB07 /* PBXContainerItemProxy */ = {
-			isa = PBXContainerItemProxy;
-			containerPortal = BF5061602113C48E0014EB07 /* Project object */;
-			proxyType = 1;
-			remoteGlobalIDString = BFAA37E6226891760014EB07;
-			remoteInfo = "I2PSnark-Share";
-		};
-		BFD28996227810AF0014EB07 /* PBXContainerItemProxy */ = {
-			isa = PBXContainerItemProxy;
-			containerPortal = BF5061602113C48E0014EB07 /* Project object */;
-			proxyType = 1;
-			remoteGlobalIDString = BFAA37E6226891760014EB07;
-			remoteInfo = "I2PSnark-Share";
-		};
-/* End PBXContainerItemProxy section */
-
-/* Begin PBXCopyFilesBuildPhase section */
-		BF99FD3A227087A40014EB07 /* CopyFiles */ = {
-			isa = PBXCopyFilesBuildPhase;
-			buildActionMask = 2147483647;
-			dstPath = /usr/share/man/man1/;
-			dstSubfolderSpec = 0;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 1;
-		};
-		BFA5226D21CD44610014EB07 /* CopyFiles */ = {
-			isa = PBXCopyFilesBuildPhase;
-			buildActionMask = 2147483647;
-			dstPath = Contents/Library/LoginItems;
-			dstSubfolderSpec = 1;
-			files = (
-				BFA5226E21CD44740014EB07 /* StartupItemApp.app in CopyFiles */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BFAA37F8226891760014EB07 /* Embed App Extensions */ = {
-			isa = PBXCopyFilesBuildPhase;
-			buildActionMask = 2147483647;
-			dstPath = "";
-			dstSubfolderSpec = 13;
-			files = (
-				BFAA37F4226891760014EB07 /* I2PSnark-Share.appex in Embed App Extensions */,
-			);
-			name = "Embed App Extensions";
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BFD289932277BEDA0014EB07 /* Embed Frameworks */ = {
-			isa = PBXCopyFilesBuildPhase;
-			buildActionMask = 2147483647;
-			dstPath = "";
-			dstSubfolderSpec = 10;
-			files = (
-				BFD289922277BEDA0014EB07 /* Sparkle.framework in Embed Frameworks */,
-			);
-			name = "Embed Frameworks";
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BFD289DA227810AF0014EB07 /* CopyFiles */ = {
-			isa = PBXCopyFilesBuildPhase;
-			buildActionMask = 2147483647;
-			dstPath = Contents/Library/LoginItems;
-			dstSubfolderSpec = 1;
-			files = (
-				BFD289DB227810AF0014EB07 /* StartupItemApp.app in CopyFiles */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BFD289DC227810AF0014EB07 /* Embed App Extensions */ = {
-			isa = PBXCopyFilesBuildPhase;
-			buildActionMask = 2147483647;
-			dstPath = "";
-			dstSubfolderSpec = 13;
-			files = (
-				BFD289DD227810AF0014EB07 /* I2PSnark-Share.appex in Embed App Extensions */,
-			);
-			name = "Embed App Extensions";
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-/* End PBXCopyFilesBuildPhase section */
-
-/* Begin PBXFileReference section */
-		46DE721B10FF505B06389B92 /* Pods-I2PLauncher.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-I2PLauncher.release.xcconfig"; path = "Pods/Target Support Files/Pods-I2PLauncher/Pods-I2PLauncher.release.xcconfig"; sourceTree = "<group>"; };
-		AF1CEEADE02906132180EEE5 /* Pods_I2PLauncher.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_I2PLauncher.framework; sourceTree = BUILT_PRODUCTS_DIR; };
-		BF07789621506C810014EB07 /* Storyboard.storyboard */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; path = Storyboard.storyboard; sourceTree = "<group>"; };
-		BF07789C21506D2B0014EB07 /* PopoverViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PopoverViewController.swift; sourceTree = "<group>"; };
-		BF0956E621EAD3590014EB07 /* profile.tgz */ = {isa = PBXFileReference; lastKnownFileType = file; path = profile.tgz; sourceTree = "<group>"; };
-		BF14B70B215C98DC0014EB07 /* LoggerWorker.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; name = LoggerWorker.hpp; path = I2PLauncher/ObjectiveC/LoggerWorker.hpp; sourceTree = SOURCE_ROOT; };
-		BF14B70C215C98DC0014EB07 /* Logger.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Logger.h; path = I2PLauncher/ObjectiveC/Logger.h; sourceTree = SOURCE_ROOT; };
-		BF14B70D215C98DC0014EB07 /* LoggerWorker.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = LoggerWorker.cpp; path = I2PLauncher/ObjectiveC/LoggerWorker.cpp; sourceTree = SOURCE_ROOT; };
-		BF14B70E215C98DC0014EB07 /* Logger.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = Logger.mm; path = I2PLauncher/ObjectiveC/Logger.mm; sourceTree = SOURCE_ROOT; };
-		BF14B711215D9E040014EB07 /* FolderContentMonitor.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FolderContentMonitor.swift; sourceTree = "<group>"; };
-		BF14B714215DA3330014EB07 /* version.h.tpl */ = {isa = PBXFileReference; lastKnownFileType = text; path = version.h.tpl; sourceTree = "<group>"; };
-		BF1D6D8E21BB32460014EB07 /* Preferences.storyboard */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; path = Preferences.storyboard; sourceTree = "<group>"; };
-		BF1D6D9021BB344D0014EB07 /* Preferences.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Preferences.swift; sourceTree = "<group>"; };
-		BF1D6D9221BB36880014EB07 /* PreferencesViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PreferencesViewController.swift; sourceTree = "<group>"; };
-		BF1D6D9421BB379A0014EB07 /* PreferencesWindowController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PreferencesWindowController.swift; sourceTree = "<group>"; };
-		BF1D6D9821BB7DC10014EB07 /* FirefoxManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FirefoxManager.swift; sourceTree = "<group>"; };
-		BF1D6D9A21BB86520014EB07 /* ConsoleWebView.storyboard */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; path = ConsoleWebView.storyboard; sourceTree = "<group>"; };
-		BF1D6D9C21BB87000014EB07 /* EmbeddedConsoleView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = EmbeddedConsoleView.swift; sourceTree = "<group>"; };
-		BF1D6D9E21BBA1460014EB07 /* WebKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = WebKit.framework; path = System/Library/Frameworks/WebKit.framework; sourceTree = SDKROOT; };
-		BF1D6DA221BBB8120014EB07 /* AdvancedTableView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AdvancedTableView.swift; sourceTree = "<group>"; };
-		BF1D6DA421BBB84E0014EB07 /* PreferencesViewController+TableView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "PreferencesViewController+TableView.swift"; sourceTree = "<group>"; };
-		BF1EFA38215140E60014EB07 /* SBridge.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = SBridge.h; path = I2PLauncher/ObjectiveC/SBridge.h; sourceTree = SOURCE_ROOT; };
-		BF1EFA39215140E60014EB07 /* SBridge.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = SBridge.mm; path = I2PLauncher/ObjectiveC/SBridge.mm; sourceTree = SOURCE_ROOT; };
-		BF1EFA3B215141100014EB07 /* RouterTask.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RouterTask.h; path = I2PLauncher/ObjectiveC/RouterTask.h; sourceTree = SOURCE_ROOT; };
-		BF1EFA3D215141100014EB07 /* main.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = main.mm; sourceTree = SOURCE_ROOT; };
-		BF1EFA3E215141100014EB07 /* RouterTask.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = RouterTask.mm; path = I2PLauncher/ObjectiveC/RouterTask.mm; sourceTree = SOURCE_ROOT; };
-		BF1EFA3F215141110014EB07 /* AppDelegate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = AppDelegate.h; path = I2PLauncher/ObjectiveC/AppDelegate.h; sourceTree = SOURCE_ROOT; };
-		BF1EFA42215141220014EB07 /* include */ = {isa = PBXFileReference; lastKnownFileType = folder; path = include; sourceTree = SOURCE_ROOT; };
-		BF1EFA44215141630014EB07 /* base.zip */ = {isa = PBXFileReference; lastKnownFileType = archive.zip; path = base.zip; sourceTree = "<group>"; };
-		BF1EFA45215141640014EB07 /* ItoopieTransparent.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = ItoopieTransparent.png; sourceTree = "<group>"; };
-		BF1EFA46215141640014EB07 /* launcher.jar */ = {isa = PBXFileReference; lastKnownFileType = archive.jar; path = launcher.jar; sourceTree = "<group>"; };
-		BF3143FD2160C1BD0014EB07 /* DownloadJavaViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DownloadJavaViewController.swift; sourceTree = "<group>"; };
-		BF3143FF2160CA350014EB07 /* logger_c.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = logger_c.h; sourceTree = "<group>"; };
-		BF5061682113C48E0014EB07 /* I2PLauncher.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = I2PLauncher.app; sourceTree = BUILT_PRODUCTS_DIR; };
-		BF50616F2113C48E0014EB07 /* I2PLauncher.xcdatamodel */ = {isa = PBXFileReference; lastKnownFileType = wrapper.xcdatamodel; path = I2PLauncher.xcdatamodel; sourceTree = "<group>"; };
-		BF5061712113C4900014EB07 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = "<group>"; };
-		BF5061742113C4900014EB07 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = Base; path = Base.lproj/UserInterfaces.xib; sourceTree = "<group>"; };
-		BF5061762113C4900014EB07 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
-		BF5061792113C4900014EB07 /* I2PLauncher.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = I2PLauncher.entitlements; sourceTree = "<group>"; };
-		BF5061952113C84E0014EB07 /* Cocoa.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Cocoa.framework; path = System/Library/Frameworks/Cocoa.framework; sourceTree = SDKROOT; };
-		BF5315062150C55B0014EB07 /* RouterRunner.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RouterRunner.swift; sourceTree = "<group>"; };
-		BF53150C2150CE310014EB07 /* DateTimeUtils.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DateTimeUtils.swift; sourceTree = "<group>"; };
-		BF5315122150EB510014EB07 /* RouterProcessStatus+ObjectiveC.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "RouterProcessStatus+ObjectiveC.swift"; sourceTree = "<group>"; };
-		BF531514215105B40014EB07 /* LogViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LogViewController.swift; sourceTree = "<group>"; };
-		BF650CA52152AC7D0014EB07 /* bumpInfoPlist.sh */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.script.sh; path = bumpInfoPlist.sh; sourceTree = SOURCE_ROOT; };
-		BF650CA72152AC7D0014EB07 /* Deployer.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = Deployer.mm; path = I2PLauncher/ObjectiveC/Deployer.mm; sourceTree = SOURCE_ROOT; };
-		BF650CA82152AC7D0014EB07 /* Deployer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Deployer.h; path = I2PLauncher/ObjectiveC/Deployer.h; sourceTree = SOURCE_ROOT; };
-		BF7506CA21509CFD0014EB07 /* RouterProcessStatus.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RouterProcessStatus.swift; sourceTree = "<group>"; };
-		BF865414215180F60014EB07 /* libswiftDarwin.tbd */ = {isa = PBXFileReference; lastKnownFileType = "sourcecode.text-based-dylib-definition"; name = libswiftDarwin.tbd; path = System/Library/PrivateFrameworks/Swift/libswiftDarwin.tbd; sourceTree = SDKROOT; };
-		BF865416215182820014EB07 /* Foundation.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Foundation.framework; path = System/Library/Frameworks/Foundation.framework; sourceTree = SDKROOT; };
-		BF99FD3C227087A40014EB07 /* RouterWrapper */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = RouterWrapper; sourceTree = BUILT_PRODUCTS_DIR; };
-		BF99FD3E227087A40014EB07 /* main.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = main.swift; sourceTree = "<group>"; };
-		BF99FD4322708AB10014EB07 /* Identifiers.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Identifiers.swift; sourceTree = "<group>"; };
-		BF99FD4622708DA70014EB07 /* DispatchQueue+delay.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "DispatchQueue+delay.swift"; sourceTree = "<group>"; };
-		BFA392FB2259E89B0014EB07 /* NetworkUtil.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NetworkUtil.swift; sourceTree = "<group>"; };
-		BFA5225F21CD43480014EB07 /* StartupItemApp.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = StartupItemApp.app; sourceTree = BUILT_PRODUCTS_DIR; };
-		BFA5226121CD43480014EB07 /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = "<group>"; };
-		BFA5226321CD434A0014EB07 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = "<group>"; };
-		BFA5226821CD434A0014EB07 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
-		BFA5226921CD434A0014EB07 /* StartupItemApp.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = StartupItemApp.entitlements; sourceTree = "<group>"; };
-		BFA5226F21CDBF450014EB07 /* Startup.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Startup.swift; sourceTree = "<group>"; };
-		BFAA37E7226891760014EB07 /* I2PSnark-Share.appex */ = {isa = PBXFileReference; explicitFileType = "wrapper.app-extension"; includeInIndex = 0; path = "I2PSnark-Share.appex"; sourceTree = BUILT_PRODUCTS_DIR; };
-		BFAA37E9226891760014EB07 /* icon.icns */ = {isa = PBXFileReference; lastKnownFileType = image.icns; path = icon.icns; sourceTree = "<group>"; };
-		BFAA37EB226891760014EB07 /* ShareViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ShareViewController.swift; sourceTree = "<group>"; };
-		BFAA37EE226891760014EB07 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = Base; path = Base.lproj/ShareViewController.xib; sourceTree = "<group>"; };
-		BFAA37F0226891760014EB07 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
-		BFAA37F1226891760014EB07 /* I2PSnark_Share.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = I2PSnark_Share.entitlements; sourceTree = "<group>"; };
-		BFBDCAE8215040670014EB07 /* Subprocess.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Subprocess.swift; sourceTree = "<group>"; };
-		BFBDCAEA215041630014EB07 /* TaskPipeline.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TaskPipeline.swift; sourceTree = "<group>"; };
-		BFBDCAEC215041C10014EB07 /* Subprocess+CompactAPI.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "Subprocess+CompactAPI.swift"; sourceTree = "<group>"; };
-		BFBDCAEE215041E30014EB07 /* Error.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Error.swift; sourceTree = "<group>"; };
-		BFBDCAF02150420C0014EB07 /* ExecutionResult.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ExecutionResult.swift; sourceTree = "<group>"; };
-		BFBDCAF22150422C0014EB07 /* AppleStuffExceptionHandler.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = AppleStuffExceptionHandler.h; sourceTree = "<group>"; };
-		BFBDCAF3215042670014EB07 /* AppleStuffExceptionHandler.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = AppleStuffExceptionHandler.m; sourceTree = "<group>"; };
-		BFBDCAF52150428D0014EB07 /* StringExtensions.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = StringExtensions.swift; sourceTree = "<group>"; };
-		BFBDCAF7215047FE0014EB07 /* ArrayExtensions.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ArrayExtensions.swift; sourceTree = "<group>"; };
-		BFBDCAF9215050810014EB07 /* ReflectionFunctions.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ReflectionFunctions.swift; sourceTree = "<group>"; };
-		BFBDCAFD2150567D0014EB07 /* SwiftApplicationDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SwiftApplicationDelegate.swift; sourceTree = "<group>"; };
-		BFBDCAFF21505BED0014EB07 /* AppKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = AppKit.framework; path = System/Library/Frameworks/AppKit.framework; sourceTree = SDKROOT; };
-		BFBDCB01215060190014EB07 /* DetectJava.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DetectJava.swift; sourceTree = "<group>"; };
-		BFBDCB03215060970014EB07 /* StatusBarController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = StatusBarController.swift; sourceTree = "<group>"; };
-		BFD289902277BED90014EB07 /* Sparkle.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; path = Sparkle.framework; sourceTree = "<group>"; };
-		BFD289E4227810AF0014EB07 /* I2PLauncher-Appstore.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = "I2PLauncher-Appstore.app"; sourceTree = BUILT_PRODUCTS_DIR; };
-		BFD289E5227810B00014EB07 /* I2PLauncher copy-Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; name = "I2PLauncher copy-Info.plist"; path = "/Volumes/localzfs/Projects/I2P/i2p.i2p/launchers/macosx/I2PLauncher copy-Info.plist"; sourceTree = "<absolute>"; };
-		BFD289E6227812C10014EB07 /* SwitchableTableViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SwitchableTableViewController.swift; sourceTree = "<group>"; };
-		BFD289E8227812F20014EB07 /* ServiceTableViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ServiceTableViewController.swift; sourceTree = "<group>"; };
-		BFD289EA227813A60014EB07 /* BottomBar.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = BottomBar.swift; sourceTree = "<group>"; };
-		BFD289EC227813EB0014EB07 /* AppearanceObserver.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppearanceObserver.swift; sourceTree = "<group>"; };
-		BFD289EE227814240014EB07 /* CustomScrollView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CustomScrollView.swift; sourceTree = "<group>"; };
-		BFD289F02278144A0014EB07 /* Icons.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Icons.swift; sourceTree = "<group>"; };
-		BFD289F2227814AC0014EB07 /* Service.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Service.swift; sourceTree = "<group>"; };
-		BFD289F4227818DA0014EB07 /* StatusIndicator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = StatusIndicator.swift; sourceTree = "<group>"; };
-		BFD289F62278192B0014EB07 /* ServiceTableRowView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ServiceTableRowView.swift; sourceTree = "<group>"; };
-		BFD289F82278194D0014EB07 /* StatusTableCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = StatusTableCell.swift; sourceTree = "<group>"; };
-		BFD289FC227821410014EB07 /* EditorTableCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = EditorTableCell.swift; sourceTree = "<group>"; };
-		BFD289FE227821690014EB07 /* EditorTableViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = EditorTableViewController.swift; sourceTree = "<group>"; };
-		BFD28A002278218F0014EB07 /* SectionHeaderView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SectionHeaderView.swift; sourceTree = "<group>"; };
-		BFD28A02227821D00014EB07 /* SettingsView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SettingsView.swift; sourceTree = "<group>"; };
-		BFD28A052278269A0014EB07 /* RouterServices.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = RouterServices.plist; sourceTree = "<group>"; };
-		BFD28A08227830EF0014EB07 /* I2PRouterService.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = I2PRouterService.swift; sourceTree = "<group>"; };
-		BFD28A0A227833E80014EB07 /* HttpTunnelService.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = HttpTunnelService.swift; sourceTree = "<group>"; };
-		BFD28A0C227834120014EB07 /* IrcTunnelService.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IrcTunnelService.swift; sourceTree = "<group>"; };
-		BFD899422169EE9F0014EB07 /* LaunchAgent.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LaunchAgent.swift; sourceTree = "<group>"; };
-		BFD899442169EFE90014EB07 /* LaunchAgent+Status.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "LaunchAgent+Status.swift"; sourceTree = "<group>"; };
-		BFD899462169F01B0014EB07 /* LaunchAgentManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LaunchAgentManager.swift; sourceTree = "<group>"; };
-		BFDD81D92156B3E30014EB07 /* RouterManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RouterManager.swift; sourceTree = "<group>"; };
-		BFE16BF72156C61E0014EB07 /* RouterStatusView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RouterStatusView.swift; sourceTree = "<group>"; };
-		BFE16BF92156DAED0014EB07 /* EventManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = EventManager.swift; sourceTree = "<group>"; };
-		BFE16BFD2156FD290014EB07 /* Sparkle.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; path = Sparkle.framework; sourceTree = "<group>"; };
-		BFE1CBAC2151908F0014EB07 /* CoreFoundation.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CoreFoundation.framework; path = System/Library/Frameworks/CoreFoundation.framework; sourceTree = SDKROOT; };
-		BFF45818213C428E0014EB07 /* I2PLauncher-Bridging-Header.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "I2PLauncher-Bridging-Header.h"; sourceTree = "<group>"; };
-		D96029CAD8BABBE8D621DBD0 /* Pods-I2PLauncher.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-I2PLauncher.debug.xcconfig"; path = "Pods/Target Support Files/Pods-I2PLauncher/Pods-I2PLauncher.debug.xcconfig"; sourceTree = "<group>"; };
-/* End PBXFileReference section */
-
-/* Begin PBXFrameworksBuildPhase section */
-		BF5061652113C48E0014EB07 /* Frameworks */ = {
-			isa = PBXFrameworksBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				BF1D6D9F21BBA1460014EB07 /* WebKit.framework in Frameworks */,
-				BFE1CBAD2151908F0014EB07 /* CoreFoundation.framework in Frameworks */,
-				BF865417215182820014EB07 /* Foundation.framework in Frameworks */,
-				BFD289912277BEDA0014EB07 /* Sparkle.framework in Frameworks */,
-				BFBDCB0021505BEE0014EB07 /* AppKit.framework in Frameworks */,
-				BF5061962113C84E0014EB07 /* Cocoa.framework in Frameworks */,
-				55459244D38FD36955E91F82 /* Pods_I2PLauncher.framework in Frameworks */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BF99FD39227087A40014EB07 /* Frameworks */ = {
-			isa = PBXFrameworksBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BFA5225C21CD43480014EB07 /* Frameworks */ = {
-			isa = PBXFrameworksBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BFAA37E4226891760014EB07 /* Frameworks */ = {
-			isa = PBXFrameworksBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BFD289C6227810AF0014EB07 /* Frameworks */ = {
-			isa = PBXFrameworksBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				BFD289C7227810AF0014EB07 /* WebKit.framework in Frameworks */,
-				BFD289C8227810AF0014EB07 /* CoreFoundation.framework in Frameworks */,
-				BFD289C9227810AF0014EB07 /* Foundation.framework in Frameworks */,
-				BFD289CB227810AF0014EB07 /* AppKit.framework in Frameworks */,
-				BFD289CC227810AF0014EB07 /* Cocoa.framework in Frameworks */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-/* End PBXFrameworksBuildPhase section */
-
-/* Begin PBXGroup section */
-		350F6D42FF1F2A6A9F60613D /* Pods */ = {
-			isa = PBXGroup;
-			children = (
-				D96029CAD8BABBE8D621DBD0 /* Pods-I2PLauncher.debug.xcconfig */,
-				46DE721B10FF505B06389B92 /* Pods-I2PLauncher.release.xcconfig */,
-			);
-			name = Pods;
-			sourceTree = "<group>";
-		};
-		BF0778A0215080910014EB07 /* subprocesses */ = {
-			isa = PBXGroup;
-			children = (
-				BFBDCAE8215040670014EB07 /* Subprocess.swift */,
-				BFBDCAEA215041630014EB07 /* TaskPipeline.swift */,
-				BFBDCAEC215041C10014EB07 /* Subprocess+CompactAPI.swift */,
-				BFBDCAEE215041E30014EB07 /* Error.swift */,
-				BFBDCAF02150420C0014EB07 /* ExecutionResult.swift */,
-				BFBDCAF22150422C0014EB07 /* AppleStuffExceptionHandler.h */,
-				BFBDCAF3215042670014EB07 /* AppleStuffExceptionHandler.m */,
-			);
-			path = subprocesses;
-			sourceTree = "<group>";
-		};
-		BF0778A12150897A0014EB07 /* userinterface */ = {
-			isa = PBXGroup;
-			children = (
-				BFD289FA227820670014EB07 /* Style2019 */,
-				BF1D6DA121BBAA420014EB07 /* preferences */,
-				BF07789C21506D2B0014EB07 /* PopoverViewController.swift */,
-				BFBDCB03215060970014EB07 /* StatusBarController.swift */,
-				BF531514215105B40014EB07 /* LogViewController.swift */,
-				BFE16BF72156C61E0014EB07 /* RouterStatusView.swift */,
-				BF3143FD2160C1BD0014EB07 /* DownloadJavaViewController.swift */,
-			);
-			path = userinterface;
-			sourceTree = "<group>";
-		};
-		BF1D6DA021BBA9910014EB07 /* Browser */ = {
-			isa = PBXGroup;
-			children = (
-				BF1D6D9C21BB87000014EB07 /* EmbeddedConsoleView.swift */,
-				BF1D6D9A21BB86520014EB07 /* ConsoleWebView.storyboard */,
-				BF1D6D9821BB7DC10014EB07 /* FirefoxManager.swift */,
-			);
-			path = Browser;
-			sourceTree = "<group>";
-		};
-		BF1D6DA121BBAA420014EB07 /* preferences */ = {
-			isa = PBXGroup;
-			children = (
-				BF1D6D9221BB36880014EB07 /* PreferencesViewController.swift */,
-				BF1D6DA421BBB84E0014EB07 /* PreferencesViewController+TableView.swift */,
-				BF1D6D9421BB379A0014EB07 /* PreferencesWindowController.swift */,
-				BF1D6DA221BBB8120014EB07 /* AdvancedTableView.swift */,
-			);
-			path = preferences;
-			sourceTree = "<group>";
-		};
-		BF1D6DA621BBB9F50014EB07 /* launchd */ = {
-			isa = PBXGroup;
-			children = (
-				BFD899422169EE9F0014EB07 /* LaunchAgent.swift */,
-				BFD899442169EFE90014EB07 /* LaunchAgent+Status.swift */,
-				BFD899462169F01B0014EB07 /* LaunchAgentManager.swift */,
-			);
-			path = launchd;
-			sourceTree = "<group>";
-		};
-		BF50615F2113C48E0014EB07 = {
-			isa = PBXGroup;
-			children = (
-				BFD289902277BED90014EB07 /* Sparkle.framework */,
-				BFAA380022689DFA0014EB07 /* CommonCode */,
-				BF0956E621EAD3590014EB07 /* profile.tgz */,
-				BF14B714215DA3330014EB07 /* version.h.tpl */,
-				BF1EFA44215141630014EB07 /* base.zip */,
-				BF1EFA45215141640014EB07 /* ItoopieTransparent.png */,
-				BF1EFA46215141640014EB07 /* launcher.jar */,
-				BF50616A2113C48E0014EB07 /* I2PLauncher */,
-				BFA5226021CD43480014EB07 /* StartupItemApp */,
-				BFAA37E8226891760014EB07 /* I2PSnark-Share */,
-				BF99FD3D227087A40014EB07 /* RouterWrapper */,
-				BF5061692113C48E0014EB07 /* Products */,
-				BF5061922113C6ED0014EB07 /* Frameworks */,
-				BFD289E5227810B00014EB07 /* I2PLauncher copy-Info.plist */,
-				350F6D42FF1F2A6A9F60613D /* Pods */,
-			);
-			sourceTree = "<group>";
-		};
-		BF5061692113C48E0014EB07 /* Products */ = {
-			isa = PBXGroup;
-			children = (
-				BF5061682113C48E0014EB07 /* I2PLauncher.app */,
-				BFA5225F21CD43480014EB07 /* StartupItemApp.app */,
-				BFAA37E7226891760014EB07 /* I2PSnark-Share.appex */,
-				BF99FD3C227087A40014EB07 /* RouterWrapper */,
-				BFD289E4227810AF0014EB07 /* I2PLauncher-Appstore.app */,
-			);
-			name = Products;
-			sourceTree = "<group>";
-		};
-		BF50616A2113C48E0014EB07 /* I2PLauncher */ = {
-			isa = PBXGroup;
-			children = (
-				BFFDBCDD227B5BB90014EB07 /* ObjectiveC */,
-				BF650CA52152AC7D0014EB07 /* bumpInfoPlist.sh */,
-				BF1EFA42215141220014EB07 /* include */,
-				BF1EFA3D215141100014EB07 /* main.mm */,
-				BF5315042150C4860014EB07 /* routermgmt */,
-				BF0778A12150897A0014EB07 /* userinterface */,
-				BF0778A0215080910014EB07 /* subprocesses */,
-				BF5061712113C4900014EB07 /* Assets.xcassets */,
-				BFF45818213C428E0014EB07 /* I2PLauncher-Bridging-Header.h */,
-				BF5061792113C4900014EB07 /* I2PLauncher.entitlements */,
-				BF50616E2113C48E0014EB07 /* I2PLauncher.xcdatamodeld */,
-				BF5061732113C4900014EB07 /* UserInterfaces.xib */,
-				BF5061762113C4900014EB07 /* Info.plist */,
-				BFD28A04227826640014EB07 /* Resources */,
-				BFBDCAFD2150567D0014EB07 /* SwiftApplicationDelegate.swift */,
-				BF99FD4322708AB10014EB07 /* Identifiers.swift */,
-			);
-			path = I2PLauncher;
-			sourceTree = "<group>";
-		};
-		BF5061922113C6ED0014EB07 /* Frameworks */ = {
-			isa = PBXGroup;
-			children = (
-				BF1D6D9E21BBA1460014EB07 /* WebKit.framework */,
-				BFE16BFD2156FD290014EB07 /* Sparkle.framework */,
-				BFE1CBAC2151908F0014EB07 /* CoreFoundation.framework */,
-				BF865416215182820014EB07 /* Foundation.framework */,
-				BF865414215180F60014EB07 /* libswiftDarwin.tbd */,
-				BFBDCAFF21505BED0014EB07 /* AppKit.framework */,
-				BF5061952113C84E0014EB07 /* Cocoa.framework */,
-				AF1CEEADE02906132180EEE5 /* Pods_I2PLauncher.framework */,
-			);
-			name = Frameworks;
-			sourceTree = "<group>";
-		};
-		BF5315042150C4860014EB07 /* routermgmt */ = {
-			isa = PBXGroup;
-			children = (
-				BFD28A07227830DB0014EB07 /* RouterServices */,
-				BF1D6DA621BBB9F50014EB07 /* launchd */,
-				BFBDCB01215060190014EB07 /* DetectJava.swift */,
-				BF7506CA21509CFD0014EB07 /* RouterProcessStatus.swift */,
-				BF5315122150EB510014EB07 /* RouterProcessStatus+ObjectiveC.swift */,
-				BF5315062150C55B0014EB07 /* RouterRunner.swift */,
-				BFDD81D92156B3E30014EB07 /* RouterManager.swift */,
-				BFA392FB2259E89B0014EB07 /* NetworkUtil.swift */,
-				BFD289F2227814AC0014EB07 /* Service.swift */,
-			);
-			path = routermgmt;
-			sourceTree = "<group>";
-		};
-		BF5315052150C4AB0014EB07 /* Utils */ = {
-			isa = PBXGroup;
-			children = (
-				BFBDCAF9215050810014EB07 /* ReflectionFunctions.swift */,
-				BFBDCAF52150428D0014EB07 /* StringExtensions.swift */,
-				BFBDCAF7215047FE0014EB07 /* ArrayExtensions.swift */,
-				BF53150C2150CE310014EB07 /* DateTimeUtils.swift */,
-				BFE16BF92156DAED0014EB07 /* EventManager.swift */,
-				BF14B711215D9E040014EB07 /* FolderContentMonitor.swift */,
-				BF1D6D9021BB344D0014EB07 /* Preferences.swift */,
-				BFA5226F21CDBF450014EB07 /* Startup.swift */,
-				BF99FD4622708DA70014EB07 /* DispatchQueue+delay.swift */,
-			);
-			path = Utils;
-			sourceTree = "<group>";
-		};
-		BF99FD3D227087A40014EB07 /* RouterWrapper */ = {
-			isa = PBXGroup;
-			children = (
-				BF99FD3E227087A40014EB07 /* main.swift */,
-			);
-			path = RouterWrapper;
-			sourceTree = "<group>";
-		};
-		BFA5226021CD43480014EB07 /* StartupItemApp */ = {
-			isa = PBXGroup;
-			children = (
-				BFA5226121CD43480014EB07 /* AppDelegate.swift */,
-				BFA5226321CD434A0014EB07 /* Assets.xcassets */,
-				BFA5226821CD434A0014EB07 /* Info.plist */,
-				BFA5226921CD434A0014EB07 /* StartupItemApp.entitlements */,
-			);
-			path = StartupItemApp;
-			sourceTree = "<group>";
-		};
-		BFAA37E8226891760014EB07 /* I2PSnark-Share */ = {
-			isa = PBXGroup;
-			children = (
-				BFAA37E9226891760014EB07 /* icon.icns */,
-				BFAA37EB226891760014EB07 /* ShareViewController.swift */,
-				BFAA37ED226891760014EB07 /* ShareViewController.xib */,
-				BFAA37F0226891760014EB07 /* Info.plist */,
-				BFAA37F1226891760014EB07 /* I2PSnark_Share.entitlements */,
-			);
-			path = "I2PSnark-Share";
-			sourceTree = "<group>";
-		};
-		BFAA380022689DFA0014EB07 /* CommonCode */ = {
-			isa = PBXGroup;
-			children = (
-				BF1D6DA021BBA9910014EB07 /* Browser */,
-				BF5315052150C4AB0014EB07 /* Utils */,
-			);
-			path = CommonCode;
-			sourceTree = "<group>";
-		};
-		BFD289FA227820670014EB07 /* Style2019 */ = {
-			isa = PBXGroup;
-			children = (
-				BFD289FB227821330014EB07 /* EditorTableView */,
-				BFD289EC227813EB0014EB07 /* AppearanceObserver.swift */,
-				BFD289EE227814240014EB07 /* CustomScrollView.swift */,
-				BFD289F02278144A0014EB07 /* Icons.swift */,
-				BFD289F4227818DA0014EB07 /* StatusIndicator.swift */,
-				BFD289E6227812C10014EB07 /* SwitchableTableViewController.swift */,
-				BFD289E8227812F20014EB07 /* ServiceTableViewController.swift */,
-				BFD289F62278192B0014EB07 /* ServiceTableRowView.swift */,
-				BFD289F82278194D0014EB07 /* StatusTableCell.swift */,
-				BFD289EA227813A60014EB07 /* BottomBar.swift */,
-			);
-			path = Style2019;
-			sourceTree = "<group>";
-		};
-		BFD289FB227821330014EB07 /* EditorTableView */ = {
-			isa = PBXGroup;
-			children = (
-				BFD289FC227821410014EB07 /* EditorTableCell.swift */,
-				BFD289FE227821690014EB07 /* EditorTableViewController.swift */,
-				BFD28A002278218F0014EB07 /* SectionHeaderView.swift */,
-				BFD28A02227821D00014EB07 /* SettingsView.swift */,
-			);
-			path = EditorTableView;
-			sourceTree = "<group>";
-		};
-		BFD28A04227826640014EB07 /* Resources */ = {
-			isa = PBXGroup;
-			children = (
-				BF1D6D8E21BB32460014EB07 /* Preferences.storyboard */,
-				BF07789621506C810014EB07 /* Storyboard.storyboard */,
-				BFD28A052278269A0014EB07 /* RouterServices.plist */,
-			);
-			path = Resources;
-			sourceTree = "<group>";
-		};
-		BFD28A07227830DB0014EB07 /* RouterServices */ = {
-			isa = PBXGroup;
-			children = (
-				BFD28A08227830EF0014EB07 /* I2PRouterService.swift */,
-				BFD28A0A227833E80014EB07 /* HttpTunnelService.swift */,
-				BFD28A0C227834120014EB07 /* IrcTunnelService.swift */,
-			);
-			path = RouterServices;
-			sourceTree = "<group>";
-		};
-		BFFDBCDD227B5BB90014EB07 /* ObjectiveC */ = {
-			isa = PBXGroup;
-			children = (
-				BF14B70E215C98DC0014EB07 /* Logger.mm */,
-				BF14B70C215C98DC0014EB07 /* Logger.h */,
-				BF650CA82152AC7D0014EB07 /* Deployer.h */,
-				BF650CA72152AC7D0014EB07 /* Deployer.mm */,
-				BF1EFA3B215141100014EB07 /* RouterTask.h */,
-				BF1EFA3E215141100014EB07 /* RouterTask.mm */,
-				BF1EFA3F215141110014EB07 /* AppDelegate.h */,
-				BF3143FF2160CA350014EB07 /* logger_c.h */,
-				BF1EFA38215140E60014EB07 /* SBridge.h */,
-				BF14B70D215C98DC0014EB07 /* LoggerWorker.cpp */,
-				BF14B70B215C98DC0014EB07 /* LoggerWorker.hpp */,
-				BF1EFA39215140E60014EB07 /* SBridge.mm */,
-			);
-			path = ObjectiveC;
-			sourceTree = "<group>";
-		};
-/* End PBXGroup section */
-
-/* Begin PBXNativeTarget section */
-		BF5061672113C48E0014EB07 /* I2PLauncher */ = {
-			isa = PBXNativeTarget;
-			buildConfigurationList = BF50617C2113C4900014EB07 /* Build configuration list for PBXNativeTarget "I2PLauncher" */;
-			buildPhases = (
-				F1677B10B8ACD49E0ACEC82A /* [CP] Check Pods Manifest.lock */,
-				BF14B713215DA1460014EB07 /* ShellScript */,
-				BF5061642113C48E0014EB07 /* Sources */,
-				BF5061652113C48E0014EB07 /* Frameworks */,
-				BF1EFA4B215142030014EB07 /* ShellScript */,
-				BF5061662113C48E0014EB07 /* Resources */,
-				BFA5226D21CD44610014EB07 /* CopyFiles */,
-				BFAA37F8226891760014EB07 /* Embed App Extensions */,
-				BFD289932277BEDA0014EB07 /* Embed Frameworks */,
-				C3823A85B1B52D669B6C412F /* [CP] Embed Pods Frameworks */,
-			);
-			buildRules = (
-			);
-			dependencies = (
-				BFAA37F3226891760014EB07 /* PBXTargetDependency */,
-			);
-			name = I2PLauncher;
-			productName = I2PLauncher;
-			productReference = BF5061682113C48E0014EB07 /* I2PLauncher.app */;
-			productType = "com.apple.product-type.application";
-		};
-		BF99FD3B227087A40014EB07 /* RouterWrapper */ = {
-			isa = PBXNativeTarget;
-			buildConfigurationList = BF99FD40227087A40014EB07 /* Build configuration list for PBXNativeTarget "RouterWrapper" */;
-			buildPhases = (
-				BF99FD38227087A40014EB07 /* Sources */,
-				BF99FD39227087A40014EB07 /* Frameworks */,
-				BF99FD3A227087A40014EB07 /* CopyFiles */,
-			);
-			buildRules = (
-			);
-			dependencies = (
-			);
-			name = RouterWrapper;
-			productName = RouterWrapper;
-			productReference = BF99FD3C227087A40014EB07 /* RouterWrapper */;
-			productType = "com.apple.product-type.tool";
-		};
-		BFA5225E21CD43480014EB07 /* StartupItemApp */ = {
-			isa = PBXNativeTarget;
-			buildConfigurationList = BFA5226C21CD434A0014EB07 /* Build configuration list for PBXNativeTarget "StartupItemApp" */;
-			buildPhases = (
-				BFA5225B21CD43480014EB07 /* Sources */,
-				BFA5225C21CD43480014EB07 /* Frameworks */,
-				BFA5225D21CD43480014EB07 /* Resources */,
-			);
-			buildRules = (
-			);
-			dependencies = (
-			);
-			name = StartupItemApp;
-			productName = StartupItemApp;
-			productReference = BFA5225F21CD43480014EB07 /* StartupItemApp.app */;
-			productType = "com.apple.product-type.application";
-		};
-		BFAA37E6226891760014EB07 /* I2PSnark-Share */ = {
-			isa = PBXNativeTarget;
-			buildConfigurationList = BFAA37F7226891760014EB07 /* Build configuration list for PBXNativeTarget "I2PSnark-Share" */;
-			buildPhases = (
-				BFAA37E3226891760014EB07 /* Sources */,
-				BFAA37E4226891760014EB07 /* Frameworks */,
-				BFAA37E5226891760014EB07 /* Resources */,
-			);
-			buildRules = (
-			);
-			dependencies = (
-			);
-			name = "I2PSnark-Share";
-			productName = "I2PSnark-Share";
-			productReference = BFAA37E7226891760014EB07 /* I2PSnark-Share.appex */;
-			productType = "com.apple.product-type.app-extension";
-		};
-		BFD28994227810AF0014EB07 /* I2PLauncher-Appstore */ = {
-			isa = PBXNativeTarget;
-			buildConfigurationList = BFD289E1227810AF0014EB07 /* Build configuration list for PBXNativeTarget "I2PLauncher-Appstore" */;
-			buildPhases = (
-				BFD28998227810AF0014EB07 /* ShellScript */,
-				BFD28999227810AF0014EB07 /* Sources */,
-				BFD289C6227810AF0014EB07 /* Frameworks */,
-				BFD289CE227810AF0014EB07 /* ShellScript */,
-				BFD289CF227810AF0014EB07 /* Resources */,
-				BFD289DA227810AF0014EB07 /* CopyFiles */,
-				BFD289DC227810AF0014EB07 /* Embed App Extensions */,
-			);
-			buildRules = (
-			);
-			dependencies = (
-				BFD28995227810AF0014EB07 /* PBXTargetDependency */,
-			);
-			name = "I2PLauncher-Appstore";
-			productName = I2PLauncher;
-			productReference = BFD289E4227810AF0014EB07 /* I2PLauncher-Appstore.app */;
-			productType = "com.apple.product-type.application";
-		};
-/* End PBXNativeTarget section */
-
-/* Begin PBXProject section */
-		BF5061602113C48E0014EB07 /* Project object */ = {
-			isa = PBXProject;
-			attributes = {
-				LastSwiftUpdateCheck = 1010;
-				LastUpgradeCheck = 1100;
-				ORGANIZATIONNAME = "The I2P Project";
-				TargetAttributes = {
-					BF5061672113C48E0014EB07 = {
-						CreatedOnToolsVersion = 9.4.1;
-						DevelopmentTeam = W3C42P2LA8;
-						LastSwiftMigration = 0940;
-						ProvisioningStyle = Manual;
-						SystemCapabilities = {
-							com.apple.ApplicationGroups.Mac = {
-								enabled = 0;
-							};
-							com.apple.HardenedRuntime = {
-								enabled = 1;
-							};
-							com.apple.NetworkExtensions = {
-								enabled = 0;
-							};
-							com.apple.Sandbox = {
-								enabled = 0;
-							};
-						};
-					};
-					BF99FD3B227087A40014EB07 = {
-						CreatedOnToolsVersion = 10.1;
-						DevelopmentTeam = W3C42P2LA8;
-						ProvisioningStyle = Manual;
-					};
-					BFA5225E21CD43480014EB07 = {
-						CreatedOnToolsVersion = 10.1;
-						DevelopmentTeam = W3C42P2LA8;
-						ProvisioningStyle = Manual;
-						SystemCapabilities = {
-							com.apple.ApplicationGroups.Mac = {
-								enabled = 1;
-							};
-						};
-					};
-					BFAA37E6226891760014EB07 = {
-						CreatedOnToolsVersion = 10.1;
-						DevelopmentTeam = W3C42P2LA8;
-						ProvisioningStyle = Manual;
-						SystemCapabilities = {
-							com.apple.ApplicationGroups.Mac = {
-								enabled = 1;
-							};
-							com.apple.Sandbox = {
-								enabled = 1;
-							};
-						};
-					};
-					BFD28994227810AF0014EB07 = {
-						DevelopmentTeam = W3C42P2LA8;
-						ProvisioningStyle = Manual;
-					};
-				};
-			};
-			buildConfigurationList = BF5061632113C48E0014EB07 /* Build configuration list for PBXProject "I2PLauncher" */;
-			compatibilityVersion = "Xcode 6.3";
-			developmentRegion = en;
-			hasScannedForEncodings = 0;
-			knownRegions = (
-				en,
-				Base,
-			);
-			mainGroup = BF50615F2113C48E0014EB07;
-			productRefGroup = BF5061692113C48E0014EB07 /* Products */;
-			projectDirPath = "";
-			projectRoot = "";
-			targets = (
-				BF5061672113C48E0014EB07 /* I2PLauncher */,
-				BFA5225E21CD43480014EB07 /* StartupItemApp */,
-				BFAA37E6226891760014EB07 /* I2PSnark-Share */,
-				BF99FD3B227087A40014EB07 /* RouterWrapper */,
-				BFD28994227810AF0014EB07 /* I2PLauncher-Appstore */,
-			);
-		};
-/* End PBXProject section */
-
-/* Begin PBXResourcesBuildPhase section */
-		BF5061662113C48E0014EB07 /* Resources */ = {
-			isa = PBXResourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				BF0956E721EAD3590014EB07 /* profile.tgz in Resources */,
-				BF86541321515CA00014EB07 /* launcher.jar in Resources */,
-				BF650CA92152AC7D0014EB07 /* bumpInfoPlist.sh in Resources */,
-				BF07789721506C810014EB07 /* Storyboard.storyboard in Resources */,
-				BF5061722113C4900014EB07 /* Assets.xcassets in Resources */,
-				BF5061752113C4900014EB07 /* UserInterfaces.xib in Resources */,
-				BF1EFA48215141640014EB07 /* ItoopieTransparent.png in Resources */,
-				BF1EFA47215141640014EB07 /* base.zip in Resources */,
-				BFD28A062278269A0014EB07 /* RouterServices.plist in Resources */,
-				BF1D6D8F21BB32460014EB07 /* Preferences.storyboard in Resources */,
-				BF1D6D9B21BB86520014EB07 /* ConsoleWebView.storyboard in Resources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BFA5225D21CD43480014EB07 /* Resources */ = {
-			isa = PBXResourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				BFA5226421CD434A0014EB07 /* Assets.xcassets in Resources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BFAA37E5226891760014EB07 /* Resources */ = {
-			isa = PBXResourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				BFAA37EF226891760014EB07 /* ShareViewController.xib in Resources */,
-				BFAA37EA226891760014EB07 /* icon.icns in Resources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BFD289CF227810AF0014EB07 /* Resources */ = {
-			isa = PBXResourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				BFD289D0227810AF0014EB07 /* profile.tgz in Resources */,
-				BFD289D1227810AF0014EB07 /* launcher.jar in Resources */,
-				BFD289D2227810AF0014EB07 /* bumpInfoPlist.sh in Resources */,
-				BFD289D3227810AF0014EB07 /* Storyboard.storyboard in Resources */,
-				BFD289D4227810AF0014EB07 /* Assets.xcassets in Resources */,
-				BFD289D5227810AF0014EB07 /* UserInterfaces.xib in Resources */,
-				BFD289D6227810AF0014EB07 /* ItoopieTransparent.png in Resources */,
-				BFD289D7227810AF0014EB07 /* base.zip in Resources */,
-				BFD289D8227810AF0014EB07 /* Preferences.storyboard in Resources */,
-				BFD289D9227810AF0014EB07 /* ConsoleWebView.storyboard in Resources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-/* End PBXResourcesBuildPhase section */
-
-/* Begin PBXShellScriptBuildPhase section */
-		BF14B713215DA1460014EB07 /* ShellScript */ = {
-			isa = PBXShellScriptBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			inputFileListPaths = (
-			);
-			inputPaths = (
-			);
-			outputFileListPaths = (
-			);
-			outputPaths = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-			shellPath = /bin/sh;
-			shellScript = "# Type a script or drag a script file from your workspace to insert its path.\nversion=`/usr/libexec/PlistBuddy -c \"Print I2PRouterVersion\" \"${INFOPLIST_FILE}\"`\ncommit=`mtn heads --branch=i2p.i2p | awk '{ print $1 }' | head -n 1`\nbuildinfo=\"Built $(date), $commit\"\n\n# Use cat to avoid any potential alias of cp asking for overwrite of file.\ncat $SRCROOT/version.h.tpl > $SRCROOT/version.h\nsed -i '' \"s#VERSION_REPLACED_BY_XCODE_BUILD_SCRIPT#$version#g\" $SRCROOT/version.h\nsed -i '' \"s#BUILD_INFO_REPLACED_BY_XCODE_BUILD_SCRIPT#$buildinfo#\" $SRCROOT/version.h\n\n$SRCROOT/check_latest_java.sh\n\n";
-		};
-		BF1EFA4B215142030014EB07 /* ShellScript */ = {
-			isa = PBXShellScriptBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			inputPaths = (
-			);
-			outputPaths = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-			shellPath = /bin/sh;
-			shellScript = "# Run from launchers/macosx\nset -x\n\n# Warning to keep clean files\nfind \"${SRCROOT}\" \\( -name \"*.h\" -or -name \"*.m\" \\) -print0 | xargs -0 wc -l | awk '$1 > 200 && $2 != \"total\" { print $2 \":1: warning: file more than 200 lines\" }'\n\nif [ ! -z \"${REPACK_I2P}\" ]; then\n    export BUILDDIR=$(pwd)\n    export MACOSX_SOURCE_DIR=$SRCROOT\n    export I2P_SOURCE_DIR=$(realpath $SRCROOT/../..)\n    echo \"I2P Source directory: ${I2P_SOURCE_DIR}\"\n    cd $MACOSX_SOURCE_DIR/..\n    # TODO: Find out why sbt hangs when executed in cli\n    #./sbt \";macosx:assembly\"\n    cd ..\n    cd $I2P_SOURCE_DIR\n    ant distclean preppkg-osx jbigi-osx-only\n    cp build/jbigi.jar pkg-temp/lib/jbigi.jar\n    cd pkg-temp\n    rm -f $BUILDDIR/base.zip\n    zip -r -v -9 $BUILDDIR/base.zip *\n    cd $MACOSX_SOURCE_DIR\n    cp $MACOSX_SOURCE_DIR/target/scala-2.11/routerLauncher-assembly-0.1.0-SNAPSHOT.jar $BUILDDIR/launcher.jar\nfi\n\necho $MARKETING_VERSION > $SRCROOT/.build_version\n";
-		};
-		BFD28998227810AF0014EB07 /* ShellScript */ = {
-			isa = PBXShellScriptBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			inputFileListPaths = (
-			);
-			inputPaths = (
-			);
-			outputFileListPaths = (
-			);
-			outputPaths = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-			shellPath = /bin/sh;
-			shellScript = "# Type a script or drag a script file from your workspace to insert its path.\nversion=`/usr/libexec/PlistBuddy -c \"Print I2PRouterVersion\" \"${INFOPLIST_FILE}\"`\ncommit=`mtn heads --branch=i2p.i2p | awk '{ print $1 }' | head -n 1`\nbuildinfo=\"Built $(date), $commit\"\n\n# Use cat to avoid any potential alias of cp asking for overwrite of file.\ncat $SRCROOT/version.h.tpl > $SRCROOT/version.h\nsed -i '' \"s#VERSION_REPLACED_BY_XCODE_BUILD_SCRIPT#$version#g\" $SRCROOT/version.h\nsed -i '' \"s#BUILD_INFO_REPLACED_BY_XCODE_BUILD_SCRIPT#$buildinfo#\" $SRCROOT/version.h\n\n$SRCROOT/check_latest_java.sh\n\n";
-		};
-		BFD289CE227810AF0014EB07 /* ShellScript */ = {
-			isa = PBXShellScriptBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			inputPaths = (
-			);
-			outputPaths = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-			shellPath = /bin/sh;
-			shellScript = "# Run from launchers/macosx\nset -x\n\n# Warning to keep clean files\nfind \"${SRCROOT}\" \\( -name \"*.h\" -or -name \"*.m\" \\) -print0 | xargs -0 wc -l | awk '$1 > 200 && $2 != \"total\" { print $2 \":1: warning: file more than 200 lines\" }'\n\nif [ ! -z \"${REPACK_I2P}\" ]; then\n    export BUILDDIR=$(pwd)\n    export MACOSX_SOURCE_DIR=$SRCROOT\n    export I2P_SOURCE_DIR=$(realpath $SRCROOT/../..)\n    cd $MACOSX_SOURCE_DIR/..\n    # TODO: Find out why sbt hangs when executed in cli\n    #./sbt \";macosx:assembly\"\n    cd ..\n    cd $I2P_SOURCE_DIR\n    ant preppkg-osx jbigi-osx-only\n    cp build/jbigi.jar pkg-temp/lib/jbigi.jar\n    cd pkg-temp\n    rm -f $BUILDDIR/base.zip\n    zip -r -v -9 $BUILDDIR/base.zip *\n    cd $MACOSX_SOURCE_DIR\n    cp $MACOSX_SOURCE_DIR/target/scala-2.11/routerLauncher-assembly-0.1.0-SNAPSHOT.jar $BUILDDIR/launcher.jar\nfi\n\n";
-		};
-		C3823A85B1B52D669B6C412F /* [CP] Embed Pods Frameworks */ = {
-			isa = PBXShellScriptBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			inputPaths = (
-				"${PODS_ROOT}/Target Support Files/Pods-I2PLauncher/Pods-I2PLauncher-frameworks.sh",
-				"${BUILT_PRODUCTS_DIR}/Kanna/Kanna.framework",
-				"${BUILT_PRODUCTS_DIR}/MBPopup/MBPopup.framework",
-				"${BUILT_PRODUCTS_DIR}/SnapKit/SnapKit.framework",
-				"${BUILT_PRODUCTS_DIR}/SwiftDate/SwiftDate.framework",
-			);
-			name = "[CP] Embed Pods Frameworks";
-			outputPaths = (
-				"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/Kanna.framework",
-				"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/MBPopup.framework",
-				"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/SnapKit.framework",
-				"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/SwiftDate.framework",
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-			shellPath = /bin/sh;
-			shellScript = "\"${PODS_ROOT}/Target Support Files/Pods-I2PLauncher/Pods-I2PLauncher-frameworks.sh\"\n";
-			showEnvVarsInLog = 0;
-		};
-		F1677B10B8ACD49E0ACEC82A /* [CP] Check Pods Manifest.lock */ = {
-			isa = PBXShellScriptBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			inputFileListPaths = (
-			);
-			inputPaths = (
-				"${PODS_PODFILE_DIR_PATH}/Podfile.lock",
-				"${PODS_ROOT}/Manifest.lock",
-			);
-			name = "[CP] Check Pods Manifest.lock";
-			outputFileListPaths = (
-			);
-			outputPaths = (
-				"$(DERIVED_FILE_DIR)/Pods-I2PLauncher-checkManifestLockResult.txt",
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-			shellPath = /bin/sh;
-			shellScript = "diff \"${PODS_PODFILE_DIR_PATH}/Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [ $? != 0 ] ; then\n    # print error to STDERR\n    echo \"error: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\" >&2\n    exit 1\nfi\n# This output is used by Xcode 'outputs' to avoid re-running this script phase.\necho \"SUCCESS\" > \"${SCRIPT_OUTPUT_FILE_0}\"\n";
-			showEnvVarsInLog = 0;
-		};
-/* End PBXShellScriptBuildPhase section */
-
-/* Begin PBXSourcesBuildPhase section */
-		BF5061642113C48E0014EB07 /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				BFBDCB04215060970014EB07 /* StatusBarController.swift in Sources */,
-				BFBDCAF8215047FE0014EB07 /* ArrayExtensions.swift in Sources */,
-				BF5315072150C55B0014EB07 /* RouterRunner.swift in Sources */,
-				BF99FD4422708AB10014EB07 /* Identifiers.swift in Sources */,
-				BFE16BFA2156DAED0014EB07 /* EventManager.swift in Sources */,
-				BFBDCAF12150420C0014EB07 /* ExecutionResult.swift in Sources */,
-				BFE16BF82156C61E0014EB07 /* RouterStatusView.swift in Sources */,
-				BFBDCAEF215041E30014EB07 /* Error.swift in Sources */,
-				BF1EFA41215141110014EB07 /* RouterTask.mm in Sources */,
-				BFA392FC2259E89B0014EB07 /* NetworkUtil.swift in Sources */,
-				BF7506CB21509CFD0014EB07 /* RouterProcessStatus.swift in Sources */,
-				BFD289F3227814AC0014EB07 /* Service.swift in Sources */,
-				BFBDCAE9215040670014EB07 /* Subprocess.swift in Sources */,
-				BF1D6D9321BB36880014EB07 /* PreferencesViewController.swift in Sources */,
-				BF1D6D9921BB7DC10014EB07 /* FirefoxManager.swift in Sources */,
-				BFBDCAFA215050810014EB07 /* ReflectionFunctions.swift in Sources */,
-				BFD289E7227812C10014EB07 /* SwitchableTableViewController.swift in Sources */,
-				BFD289F5227818DA0014EB07 /* StatusIndicator.swift in Sources */,
-				BFBDCAED215041C10014EB07 /* Subprocess+CompactAPI.swift in Sources */,
-				BFD28A0D227834120014EB07 /* IrcTunnelService.swift in Sources */,
-				BFBDCB02215060190014EB07 /* DetectJava.swift in Sources */,
-				BFD289F12278144A0014EB07 /* Icons.swift in Sources */,
-				BF07789E21506D2B0014EB07 /* PopoverViewController.swift in Sources */,
-				BF1D6DA321BBB8120014EB07 /* AdvancedTableView.swift in Sources */,
-				BF99FD4722708DA70014EB07 /* DispatchQueue+delay.swift in Sources */,
-				BFD899472169F01B0014EB07 /* LaunchAgentManager.swift in Sources */,
-				BF650CAB2152AC7D0014EB07 /* Deployer.mm in Sources */,
-				BF1D6DA521BBB84E0014EB07 /* PreferencesViewController+TableView.swift in Sources */,
-				BF1EFA40215141110014EB07 /* main.mm in Sources */,
-				BFD28A012278218F0014EB07 /* SectionHeaderView.swift in Sources */,
-				BFD28A0B227833E80014EB07 /* HttpTunnelService.swift in Sources */,
-				BFD289EB227813A60014EB07 /* BottomBar.swift in Sources */,
-				BFBDCAF4215042670014EB07 /* AppleStuffExceptionHandler.m in Sources */,
-				BFD289F92278194D0014EB07 /* StatusTableCell.swift in Sources */,
-				BFD289ED227813EB0014EB07 /* AppearanceObserver.swift in Sources */,
-				BFD289FF227821690014EB07 /* EditorTableViewController.swift in Sources */,
-				BF3143FE2160C1BD0014EB07 /* DownloadJavaViewController.swift in Sources */,
-				BF1D6D9521BB379A0014EB07 /* PreferencesWindowController.swift in Sources */,
-				BFD289E9227812F20014EB07 /* ServiceTableViewController.swift in Sources */,
-				BFD28A09227830EF0014EB07 /* I2PRouterService.swift in Sources */,
-				BFD289F72278192B0014EB07 /* ServiceTableRowView.swift in Sources */,
-				BF531515215105B40014EB07 /* LogViewController.swift in Sources */,
-				BFA5227021CDBF450014EB07 /* Startup.swift in Sources */,
-				BF5315132150EB510014EB07 /* RouterProcessStatus+ObjectiveC.swift in Sources */,
-				BF1D6D9121BB344D0014EB07 /* Preferences.swift in Sources */,
-				BFD899452169EFE90014EB07 /* LaunchAgent+Status.swift in Sources */,
-				BF14B712215D9E040014EB07 /* FolderContentMonitor.swift in Sources */,
-				BFBDCAFE2150567D0014EB07 /* SwiftApplicationDelegate.swift in Sources */,
-				BFD899432169EE9F0014EB07 /* LaunchAgent.swift in Sources */,
-				BFDD81DA2156B3E30014EB07 /* RouterManager.swift in Sources */,
-				BFD28A03227821D00014EB07 /* SettingsView.swift in Sources */,
-				BF1EFA3A215140E60014EB07 /* SBridge.mm in Sources */,
-				BF14B70F215C98DC0014EB07 /* LoggerWorker.cpp in Sources */,
-				BF1D6D9D21BB87000014EB07 /* EmbeddedConsoleView.swift in Sources */,
-				BFD289FD227821410014EB07 /* EditorTableCell.swift in Sources */,
-				BF14B710215C98DC0014EB07 /* Logger.mm in Sources */,
-				BFD289EF227814240014EB07 /* CustomScrollView.swift in Sources */,
-				BFBDCAF62150428D0014EB07 /* StringExtensions.swift in Sources */,
-				BF5061702113C48E0014EB07 /* I2PLauncher.xcdatamodeld in Sources */,
-				BFBDCAEB215041630014EB07 /* TaskPipeline.swift in Sources */,
-				BF53150D2150CE310014EB07 /* DateTimeUtils.swift in Sources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BF99FD38227087A40014EB07 /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				BFFDBCDC227B50FB0014EB07 /* Identifiers.swift in Sources */,
-				BFFDBCDB227B50EE0014EB07 /* I2PLauncher-Bridging-Header.h in Sources */,
-				BFFDBCCF227B50410014EB07 /* StringExtensions.swift in Sources */,
-				BFFDBCD0227B50410014EB07 /* ArrayExtensions.swift in Sources */,
-				BFFDBCD1227B50410014EB07 /* Preferences.swift in Sources */,
-				BFFDBCD2227B50410014EB07 /* DetectJava.swift in Sources */,
-				BFFDBCD3227B50410014EB07 /* Subprocess.swift in Sources */,
-				BFFDBCD4227B50410014EB07 /* TaskPipeline.swift in Sources */,
-				BFFDBCD5227B50410014EB07 /* Subprocess+CompactAPI.swift in Sources */,
-				BFFDBCD6227B50410014EB07 /* Error.swift in Sources */,
-				BFFDBCD7227B50410014EB07 /* ExecutionResult.swift in Sources */,
-				BFFDBCD8227B50410014EB07 /* AppleStuffExceptionHandler.h in Sources */,
-				BFFDBCD9227B50410014EB07 /* AppleStuffExceptionHandler.m in Sources */,
-				BF99FD3F227087A40014EB07 /* main.swift in Sources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BFA5225B21CD43480014EB07 /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				BF99FD4522708BA80014EB07 /* Identifiers.swift in Sources */,
-				BFA5226221CD43480014EB07 /* AppDelegate.swift in Sources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BFAA37E3226891760014EB07 /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				BFAD9C95227C925F0014EB07 /* Identifiers.swift in Sources */,
-				BFAD9C94227C92480014EB07 /* Preferences.swift in Sources */,
-				BFAA37FA226892CA0014EB07 /* StringExtensions.swift in Sources */,
-				BFAA37FB226892CA0014EB07 /* ArrayExtensions.swift in Sources */,
-				BFAA37FC226892CA0014EB07 /* DateTimeUtils.swift in Sources */,
-				BFAA37FD226892CA0014EB07 /* EventManager.swift in Sources */,
-				BFAA37FE226892CA0014EB07 /* FolderContentMonitor.swift in Sources */,
-				BFAA37EC226891760014EB07 /* ShareViewController.swift in Sources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BFD28999227810AF0014EB07 /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				BFD2899A227810AF0014EB07 /* StatusBarController.swift in Sources */,
-				BFD2899B227810AF0014EB07 /* ArrayExtensions.swift in Sources */,
-				BFD2899C227810AF0014EB07 /* RouterRunner.swift in Sources */,
-				BFD2899D227810AF0014EB07 /* Identifiers.swift in Sources */,
-				BFD2899E227810AF0014EB07 /* EventManager.swift in Sources */,
-				BFD2899F227810AF0014EB07 /* ExecutionResult.swift in Sources */,
-				BFD289A0227810AF0014EB07 /* RouterStatusView.swift in Sources */,
-				BFD289A1227810AF0014EB07 /* Error.swift in Sources */,
-				BFD289A2227810AF0014EB07 /* RouterTask.mm in Sources */,
-				BFD289A3227810AF0014EB07 /* NetworkUtil.swift in Sources */,
-				BFD289A4227810AF0014EB07 /* RouterProcessStatus.swift in Sources */,
-				BFD289A5227810AF0014EB07 /* Subprocess.swift in Sources */,
-				BFD289A6227810AF0014EB07 /* PreferencesViewController.swift in Sources */,
-				BFD289A7227810AF0014EB07 /* FirefoxManager.swift in Sources */,
-				BFD289A8227810AF0014EB07 /* ReflectionFunctions.swift in Sources */,
-				BFD289A9227810AF0014EB07 /* Subprocess+CompactAPI.swift in Sources */,
-				BFD289AA227810AF0014EB07 /* DetectJava.swift in Sources */,
-				BFD289AB227810AF0014EB07 /* PopoverViewController.swift in Sources */,
-				BFD289AC227810AF0014EB07 /* AdvancedTableView.swift in Sources */,
-				BFD289AD227810AF0014EB07 /* DispatchQueue+delay.swift in Sources */,
-				BFD289AE227810AF0014EB07 /* LaunchAgentManager.swift in Sources */,
-				BFD289AF227810AF0014EB07 /* Deployer.mm in Sources */,
-				BFD289B0227810AF0014EB07 /* PreferencesViewController+TableView.swift in Sources */,
-				BFD289B1227810AF0014EB07 /* main.mm in Sources */,
-				BFD289B2227810AF0014EB07 /* AppleStuffExceptionHandler.m in Sources */,
-				BFD289B3227810AF0014EB07 /* DownloadJavaViewController.swift in Sources */,
-				BFD289B4227810AF0014EB07 /* PreferencesWindowController.swift in Sources */,
-				BFD289B5227810AF0014EB07 /* LogViewController.swift in Sources */,
-				BFD289B6227810AF0014EB07 /* Startup.swift in Sources */,
-				BFD289B7227810AF0014EB07 /* RouterProcessStatus+ObjectiveC.swift in Sources */,
-				BFD289B8227810AF0014EB07 /* Preferences.swift in Sources */,
-				BFD289B9227810AF0014EB07 /* LaunchAgent+Status.swift in Sources */,
-				BFD289BA227810AF0014EB07 /* FolderContentMonitor.swift in Sources */,
-				BFD289BB227810AF0014EB07 /* SwiftApplicationDelegate.swift in Sources */,
-				BFD289BC227810AF0014EB07 /* LaunchAgent.swift in Sources */,
-				BFD289BD227810AF0014EB07 /* RouterManager.swift in Sources */,
-				BFD289BE227810AF0014EB07 /* SBridge.mm in Sources */,
-				BFD289BF227810AF0014EB07 /* LoggerWorker.cpp in Sources */,
-				BFD289C0227810AF0014EB07 /* EmbeddedConsoleView.swift in Sources */,
-				BFD289C1227810AF0014EB07 /* Logger.mm in Sources */,
-				BFD289C2227810AF0014EB07 /* StringExtensions.swift in Sources */,
-				BFD289C3227810AF0014EB07 /* I2PLauncher.xcdatamodeld in Sources */,
-				BFD289C4227810AF0014EB07 /* TaskPipeline.swift in Sources */,
-				BFD289C5227810AF0014EB07 /* DateTimeUtils.swift in Sources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-/* End PBXSourcesBuildPhase section */
-
-/* Begin PBXTargetDependency section */
-		BFAA37F3226891760014EB07 /* PBXTargetDependency */ = {
-			isa = PBXTargetDependency;
-			target = BFAA37E6226891760014EB07 /* I2PSnark-Share */;
-			targetProxy = BFAA37F2226891760014EB07 /* PBXContainerItemProxy */;
-		};
-		BFD28995227810AF0014EB07 /* PBXTargetDependency */ = {
-			isa = PBXTargetDependency;
-			target = BFAA37E6226891760014EB07 /* I2PSnark-Share */;
-			targetProxy = BFD28996227810AF0014EB07 /* PBXContainerItemProxy */;
-		};
-/* End PBXTargetDependency section */
-
-/* Begin PBXVariantGroup section */
-		BF5061732113C4900014EB07 /* UserInterfaces.xib */ = {
-			isa = PBXVariantGroup;
-			children = (
-				BF5061742113C4900014EB07 /* Base */,
-			);
-			name = UserInterfaces.xib;
-			sourceTree = "<group>";
-		};
-		BFAA37ED226891760014EB07 /* ShareViewController.xib */ = {
-			isa = PBXVariantGroup;
-			children = (
-				BFAA37EE226891760014EB07 /* Base */,
-			);
-			name = ShareViewController.xib;
-			sourceTree = "<group>";
-		};
-/* End PBXVariantGroup section */
-
-/* Begin XCBuildConfiguration section */
-		BF50617A2113C4900014EB07 /* Debug */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = "$(inherited)";
-				ALWAYS_SEARCH_USER_PATHS = "$(inherited)";
-				CLANG_ANALYZER_NONNULL = YES;
-				CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
-				CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
-				CLANG_CXX_LIBRARY = "libc++";
-				CLANG_ENABLE_MODULES = YES;
-				CLANG_ENABLE_OBJC_ARC = NO;
-				CLANG_ENABLE_OBJC_WEAK = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
-				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
-				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
-				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
-				CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
-				CLANG_WARN_EMPTY_BODY = YES;
-				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
-				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
-				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
-				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
-				CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
-				CLANG_WARN_UNREACHABLE_CODE = YES;
-				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
-				CODE_SIGN_IDENTITY = "Developer ID Application";
-				COPY_PHASE_STRIP = NO;
-				DEBUG_INFORMATION_FORMAT = dwarf;
-				ENABLE_STRICT_OBJC_MSGSEND = YES;
-				ENABLE_TESTABILITY = YES;
-				FRAMEWORK_SEARCH_PATHS = "$(inherited)";
-				GCC_C_LANGUAGE_STANDARD = gnu11;
-				GCC_DYNAMIC_NO_PIC = NO;
-				GCC_NO_COMMON_BLOCKS = YES;
-				GCC_OPTIMIZATION_LEVEL = 0;
-				GCC_PREPROCESSOR_DEFINITIONS = (
-					"DEBUG=1",
-					"$(inherited)",
-				);
-				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
-				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
-				GCC_WARN_UNDECLARED_SELECTOR = YES;
-				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
-				GCC_WARN_UNUSED_FUNCTION = NO;
-				GCC_WARN_UNUSED_VALUE = NO;
-				GCC_WARN_UNUSED_VARIABLE = NO;
-				MACOSX_DEPLOYMENT_TARGET = 10.12;
-				MTL_ENABLE_DEBUG_INFO = YES;
-				ONLY_ACTIVE_ARCH = YES;
-				SDKROOT = macosx;
-				VALID_ARCHS = x86_64;
-			};
-			name = Debug;
-		};
-		BF50617B2113C4900014EB07 /* Release */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = "$(inherited)";
-				ALWAYS_SEARCH_USER_PATHS = "$(inherited)";
-				CLANG_ANALYZER_NONNULL = YES;
-				CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
-				CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
-				CLANG_CXX_LIBRARY = "libc++";
-				CLANG_ENABLE_MODULES = YES;
-				CLANG_ENABLE_OBJC_ARC = NO;
-				CLANG_ENABLE_OBJC_WEAK = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
-				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
-				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
-				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
-				CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
-				CLANG_WARN_EMPTY_BODY = YES;
-				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
-				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
-				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
-				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
-				CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
-				CLANG_WARN_UNREACHABLE_CODE = YES;
-				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
-				CODE_SIGN_IDENTITY = "Developer ID Application";
-				COPY_PHASE_STRIP = NO;
-				DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
-				ENABLE_NS_ASSERTIONS = NO;
-				ENABLE_STRICT_OBJC_MSGSEND = YES;
-				FRAMEWORK_SEARCH_PATHS = "$(inherited)";
-				GCC_C_LANGUAGE_STANDARD = gnu11;
-				GCC_NO_COMMON_BLOCKS = YES;
-				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
-				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
-				GCC_WARN_UNDECLARED_SELECTOR = YES;
-				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
-				GCC_WARN_UNUSED_FUNCTION = NO;
-				GCC_WARN_UNUSED_VALUE = NO;
-				GCC_WARN_UNUSED_VARIABLE = NO;
-				MACOSX_DEPLOYMENT_TARGET = 10.12;
-				MTL_ENABLE_DEBUG_INFO = NO;
-				SDKROOT = macosx;
-				SWIFT_COMPILATION_MODE = wholemodule;
-				VALID_ARCHS = x86_64;
-			};
-			name = Release;
-		};
-		BF50617D2113C4900014EB07 /* Debug */ = {
-			isa = XCBuildConfiguration;
-			baseConfigurationReference = D96029CAD8BABBE8D621DBD0 /* Pods-I2PLauncher.debug.xcconfig */;
-			buildSettings = {
-				ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = "$(inherited)";
-				ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-				CODE_SIGN_ENTITLEMENTS = I2PLauncher/I2PLauncher.entitlements;
-				CODE_SIGN_IDENTITY = "Developer ID Application";
-				CODE_SIGN_STYLE = Manual;
-				COMBINE_HIDPI_IMAGES = YES;
-				COMPRESS_PNG_FILES = YES;
-				COPY_PHASE_STRIP = YES;
-				CURRENT_PROJECT_VERSION = 10;
-				DEAD_CODE_STRIPPING = YES;
-				DEFINES_MODULE = YES;
-				DEVELOPMENT_TEAM = W3C42P2LA8;
-				ENABLE_HARDENED_RUNTIME = YES;
-				FRAMEWORK_SEARCH_PATHS = (
-					"$(inherited)",
-					/Library/Frameworks,
-					/System/Library/Frameworks,
-					"$(PROJECT_DIR)",
-				);
-				GCC_WARN_ABOUT_DEPRECATED_FUNCTIONS = NO;
-				GCC_WARN_UNUSED_FUNCTION = NO;
-				GCC_WARN_UNUSED_VALUE = NO;
-				GCC_WARN_UNUSED_VARIABLE = NO;
-				HEADER_SEARCH_PATHS = (
-					"$(inherited)",
-					"$(SRCROOT)/include",
-					"$(SRCROOT)/../../../Sparkle/Sparkle",
-				);
-				INCLUDED_RECURSIVE_SEARCH_PATH_SUBDIRECTORIES = include;
-				INFOPLIST_FILE = I2PLauncher/Info.plist;
-				LD_NO_PIE = YES;
-				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks @executable_path/Frameworks @loader_path/../Frameworks";
-				MACOSX_DEPLOYMENT_TARGET = 10.12;
-				MARKETING_VERSION = 0.1.8;
-				PRODUCT_BUNDLE_IDENTIFIER = "net.i2p.bootstrap-macosx.I2PLauncher";
-				PRODUCT_NAME = "$(TARGET_NAME)";
-				PROVISIONING_PROFILE_SPECIFIER = "";
-				SDKROOT = macosx;
-				SWIFT_OBJC_BRIDGING_HEADER = "I2PLauncher/I2PLauncher-Bridging-Header.h";
-				SWIFT_OPTIMIZATION_LEVEL = "-Onone";
-				SWIFT_VERSION = 4.2;
-				SYSTEM_HEADER_SEARCH_PATHS = "$(SRCROOT)/include/**";
-				VALID_ARCHS = x86_64;
-			};
-			name = Debug;
-		};
-		BF50617E2113C4900014EB07 /* Release */ = {
-			isa = XCBuildConfiguration;
-			baseConfigurationReference = 46DE721B10FF505B06389B92 /* Pods-I2PLauncher.release.xcconfig */;
-			buildSettings = {
-				ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = "$(inherited)";
-				ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-				CODE_SIGN_ENTITLEMENTS = I2PLauncher/I2PLauncher.entitlements;
-				CODE_SIGN_IDENTITY = "Developer ID Application";
-				CODE_SIGN_STYLE = Manual;
-				COMBINE_HIDPI_IMAGES = YES;
-				COMPRESS_PNG_FILES = YES;
-				COPY_PHASE_STRIP = YES;
-				CURRENT_PROJECT_VERSION = 10;
-				DEAD_CODE_STRIPPING = YES;
-				DEFINES_MODULE = YES;
-				DEVELOPMENT_TEAM = W3C42P2LA8;
-				ENABLE_HARDENED_RUNTIME = YES;
-				FRAMEWORK_SEARCH_PATHS = (
-					"$(inherited)",
-					/Library/Frameworks,
-					/System/Library/Frameworks,
-					"$(PROJECT_DIR)",
-				);
-				GCC_WARN_ABOUT_DEPRECATED_FUNCTIONS = NO;
-				GCC_WARN_UNUSED_FUNCTION = NO;
-				GCC_WARN_UNUSED_VALUE = NO;
-				GCC_WARN_UNUSED_VARIABLE = NO;
-				HEADER_SEARCH_PATHS = (
-					"$(inherited)",
-					"$(SRCROOT)/include",
-					"$(SRCROOT)/../../../Sparkle/Sparkle",
-				);
-				INCLUDED_RECURSIVE_SEARCH_PATH_SUBDIRECTORIES = include;
-				INFOPLIST_FILE = I2PLauncher/Info.plist;
-				LD_NO_PIE = YES;
-				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks @executable_path/Frameworks @loader_path/../Frameworks";
-				MACOSX_DEPLOYMENT_TARGET = 10.12;
-				MARKETING_VERSION = 0.1.8;
-				PRODUCT_BUNDLE_IDENTIFIER = "net.i2p.bootstrap-macosx.I2PLauncher";
-				PRODUCT_NAME = "$(TARGET_NAME)";
-				PROVISIONING_PROFILE_SPECIFIER = "";
-				SDKROOT = macosx;
-				SWIFT_OBJC_BRIDGING_HEADER = "I2PLauncher/I2PLauncher-Bridging-Header.h";
-				SWIFT_VERSION = 4.2;
-				SYSTEM_HEADER_SEARCH_PATHS = "$(SRCROOT)/include/**";
-				VALID_ARCHS = x86_64;
-			};
-			name = Release;
-		};
-		BF99FD41227087A40014EB07 /* Debug */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CLANG_ENABLE_OBJC_ARC = YES;
-				CODE_SIGN_IDENTITY = "Developer ID Application";
-				CODE_SIGN_STYLE = Manual;
-				DEVELOPMENT_TEAM = W3C42P2LA8;
-				ENABLE_HARDENED_RUNTIME = YES;
-				GCC_WARN_ABOUT_DEPRECATED_FUNCTIONS = NO;
-				GCC_WARN_UNUSED_FUNCTION = YES;
-				GCC_WARN_UNUSED_VARIABLE = YES;
-				MACOSX_DEPLOYMENT_TARGET = 10.14;
-				MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
-				MTL_FAST_MATH = YES;
-				PRODUCT_NAME = "$(TARGET_NAME)";
-				PROVISIONING_PROFILE_SPECIFIER = "";
-				SDKROOT = macosx;
-				SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG;
-				SWIFT_OBJC_BRIDGING_HEADER = "I2PLauncher/I2PLauncher-Bridging-Header.h";
-				SWIFT_OPTIMIZATION_LEVEL = "-Onone";
-				SWIFT_VERSION = 4.2;
-			};
-			name = Debug;
-		};
-		BF99FD42227087A40014EB07 /* Release */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CLANG_ENABLE_OBJC_ARC = YES;
-				CODE_SIGN_IDENTITY = "Developer ID Application";
-				CODE_SIGN_STYLE = Manual;
-				DEVELOPMENT_TEAM = W3C42P2LA8;
-				ENABLE_HARDENED_RUNTIME = YES;
-				GCC_WARN_ABOUT_DEPRECATED_FUNCTIONS = NO;
-				GCC_WARN_UNUSED_FUNCTION = YES;
-				GCC_WARN_UNUSED_VARIABLE = YES;
-				MACOSX_DEPLOYMENT_TARGET = 10.14;
-				MTL_FAST_MATH = YES;
-				PRODUCT_NAME = "$(TARGET_NAME)";
-				PROVISIONING_PROFILE_SPECIFIER = "";
-				SDKROOT = macosx;
-				SWIFT_OBJC_BRIDGING_HEADER = "I2PLauncher/I2PLauncher-Bridging-Header.h";
-				SWIFT_OPTIMIZATION_LEVEL = "-O";
-				SWIFT_VERSION = 4.2;
-			};
-			name = Release;
-		};
-		BFA5226A21CD434A0014EB07 /* Debug */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-				CLANG_ENABLE_OBJC_ARC = YES;
-				CODE_SIGN_ENTITLEMENTS = StartupItemApp/StartupItemApp.entitlements;
-				CODE_SIGN_IDENTITY = "Developer ID Application";
-				CODE_SIGN_STYLE = Manual;
-				COMBINE_HIDPI_IMAGES = YES;
-				DEVELOPMENT_TEAM = W3C42P2LA8;
-				ENABLE_HARDENED_RUNTIME = YES;
-				GCC_WARN_UNUSED_FUNCTION = YES;
-				GCC_WARN_UNUSED_VARIABLE = YES;
-				INFOPLIST_FILE = StartupItemApp/Info.plist;
-				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks";
-				MACOSX_DEPLOYMENT_TARGET = 10.12;
-				MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
-				MTL_FAST_MATH = YES;
-				PRODUCT_BUNDLE_IDENTIFIER = "net.i2p.bootstrap-macosx.StartupItemApp";
-				PRODUCT_NAME = "$(TARGET_NAME)";
-				PROVISIONING_PROFILE_SPECIFIER = "";
-				SDKROOT = macosx;
-				SKIP_INSTALL = YES;
-				SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG;
-				SWIFT_OPTIMIZATION_LEVEL = "-Onone";
-				SWIFT_SWIFT3_OBJC_INFERENCE = Default;
-				SWIFT_VERSION = 4.2;
-			};
-			name = Debug;
-		};
-		BFA5226B21CD434A0014EB07 /* Release */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-				CLANG_ENABLE_OBJC_ARC = YES;
-				CODE_SIGN_ENTITLEMENTS = StartupItemApp/StartupItemApp.entitlements;
-				CODE_SIGN_IDENTITY = "Developer ID Application";
-				CODE_SIGN_STYLE = Manual;
-				COMBINE_HIDPI_IMAGES = YES;
-				DEVELOPMENT_TEAM = W3C42P2LA8;
-				ENABLE_HARDENED_RUNTIME = YES;
-				GCC_WARN_UNUSED_FUNCTION = YES;
-				GCC_WARN_UNUSED_VARIABLE = YES;
-				INFOPLIST_FILE = StartupItemApp/Info.plist;
-				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks";
-				MACOSX_DEPLOYMENT_TARGET = 10.12;
-				MTL_FAST_MATH = YES;
-				PRODUCT_BUNDLE_IDENTIFIER = "net.i2p.bootstrap-macosx.StartupItemApp";
-				PRODUCT_NAME = "$(TARGET_NAME)";
-				PROVISIONING_PROFILE_SPECIFIER = "";
-				SDKROOT = macosx;
-				SKIP_INSTALL = YES;
-				SWIFT_OPTIMIZATION_LEVEL = "-O";
-				SWIFT_SWIFT3_OBJC_INFERENCE = Default;
-				SWIFT_VERSION = 4.2;
-			};
-			name = Release;
-		};
-		BFAA37F5226891760014EB07 /* Debug */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CLANG_ENABLE_OBJC_ARC = YES;
-				CODE_SIGN_ENTITLEMENTS = "I2PSnark-Share/I2PSnark_Share.entitlements";
-				CODE_SIGN_IDENTITY = "Developer ID Application";
-				CODE_SIGN_STYLE = Manual;
-				COMBINE_HIDPI_IMAGES = YES;
-				DEVELOPMENT_TEAM = W3C42P2LA8;
-				ENABLE_HARDENED_RUNTIME = YES;
-				GCC_WARN_UNUSED_FUNCTION = YES;
-				GCC_WARN_UNUSED_VARIABLE = YES;
-				INFOPLIST_FILE = "I2PSnark-Share/Info.plist";
-				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks @executable_path/../../../../Frameworks";
-				MACOSX_DEPLOYMENT_TARGET = 10.12;
-				MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
-				MTL_FAST_MATH = YES;
-				PRODUCT_BUNDLE_IDENTIFIER = "net.i2p.bootstrap-macosx.I2PLauncher.I2PSnark-Share";
-				PRODUCT_NAME = "$(TARGET_NAME)";
-				PROVISIONING_PROFILE_SPECIFIER = "";
-				SDKROOT = macosx;
-				SKIP_INSTALL = YES;
-				SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG;
-				SWIFT_OPTIMIZATION_LEVEL = "-Onone";
-				SWIFT_VERSION = 4.2;
-			};
-			name = Debug;
-		};
-		BFAA37F6226891760014EB07 /* Release */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CLANG_ENABLE_OBJC_ARC = YES;
-				CODE_SIGN_ENTITLEMENTS = "I2PSnark-Share/I2PSnark_Share.entitlements";
-				CODE_SIGN_IDENTITY = "Developer ID Application";
-				CODE_SIGN_STYLE = Manual;
-				COMBINE_HIDPI_IMAGES = YES;
-				DEVELOPMENT_TEAM = W3C42P2LA8;
-				ENABLE_HARDENED_RUNTIME = YES;
-				GCC_WARN_UNUSED_FUNCTION = YES;
-				GCC_WARN_UNUSED_VARIABLE = YES;
-				INFOPLIST_FILE = "I2PSnark-Share/Info.plist";
-				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks @executable_path/../../../../Frameworks";
-				MACOSX_DEPLOYMENT_TARGET = 10.12;
-				MTL_FAST_MATH = YES;
-				PRODUCT_BUNDLE_IDENTIFIER = "net.i2p.bootstrap-macosx.I2PLauncher.I2PSnark-Share";
-				PRODUCT_NAME = "$(TARGET_NAME)";
-				PROVISIONING_PROFILE_SPECIFIER = "";
-				SDKROOT = macosx;
-				SKIP_INSTALL = YES;
-				SWIFT_OPTIMIZATION_LEVEL = "-O";
-				SWIFT_VERSION = 4.2;
-			};
-			name = Release;
-		};
-		BFD289E2227810AF0014EB07 /* Debug */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = "$(inherited)";
-				ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-				CODE_SIGN_ENTITLEMENTS = I2PLauncher/I2PLauncher.entitlements;
-				CODE_SIGN_IDENTITY = "Developer ID Application";
-				CODE_SIGN_STYLE = Manual;
-				COMBINE_HIDPI_IMAGES = YES;
-				COMPRESS_PNG_FILES = YES;
-				COPY_PHASE_STRIP = YES;
-				DEAD_CODE_STRIPPING = YES;
-				DEFINES_MODULE = YES;
-				DEVELOPMENT_TEAM = W3C42P2LA8;
-				ENABLE_HARDENED_RUNTIME = YES;
-				FRAMEWORK_SEARCH_PATHS = (
-					"$(inherited)",
-					/Library/Frameworks,
-					/System/Library/Frameworks,
-					"$(PROJECT_DIR)",
-				);
-				GCC_WARN_UNUSED_FUNCTION = NO;
-				GCC_WARN_UNUSED_VALUE = NO;
-				GCC_WARN_UNUSED_VARIABLE = NO;
-				HEADER_SEARCH_PATHS = (
-					"$(inherited)",
-					"$(SRCROOT)/include",
-					"$(SRCROOT)/../../../Sparkle/Sparkle",
-				);
-				INCLUDED_RECURSIVE_SEARCH_PATH_SUBDIRECTORIES = include;
-				INFOPLIST_FILE = "I2PLauncher copy-Info.plist";
-				LD_NO_PIE = YES;
-				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks @executable_path/Frameworks @loader_path/../Frameworks";
-				MACOSX_DEPLOYMENT_TARGET = 10.12;
-				PRODUCT_BUNDLE_IDENTIFIER = "net.i2p.bootstrap-macosx.I2PLauncher";
-				PRODUCT_NAME = "$(TARGET_NAME)";
-				PROVISIONING_PROFILE_SPECIFIER = "";
-				SDKROOT = macosx;
-				SWIFT_OBJC_BRIDGING_HEADER = "I2PLauncher/I2PLauncher-Bridging-Header.h";
-				SWIFT_OPTIMIZATION_LEVEL = "-Onone";
-				SWIFT_VERSION = 4.2;
-				SYSTEM_HEADER_SEARCH_PATHS = "$(SRCROOT)/include/**";
-			};
-			name = Debug;
-		};
-		BFD289E3227810AF0014EB07 /* Release */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = "$(inherited)";
-				ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-				CODE_SIGN_ENTITLEMENTS = I2PLauncher/I2PLauncher.entitlements;
-				CODE_SIGN_IDENTITY = "Developer ID Application";
-				CODE_SIGN_STYLE = Manual;
-				COMBINE_HIDPI_IMAGES = YES;
-				COMPRESS_PNG_FILES = YES;
-				COPY_PHASE_STRIP = YES;
-				DEAD_CODE_STRIPPING = YES;
-				DEFINES_MODULE = YES;
-				DEVELOPMENT_TEAM = W3C42P2LA8;
-				ENABLE_HARDENED_RUNTIME = YES;
-				FRAMEWORK_SEARCH_PATHS = (
-					"$(inherited)",
-					/Library/Frameworks,
-					/System/Library/Frameworks,
-					"$(PROJECT_DIR)",
-				);
-				GCC_WARN_UNUSED_FUNCTION = NO;
-				GCC_WARN_UNUSED_VALUE = NO;
-				GCC_WARN_UNUSED_VARIABLE = NO;
-				HEADER_SEARCH_PATHS = (
-					"$(inherited)",
-					"$(SRCROOT)/include",
-					"$(SRCROOT)/../../../Sparkle/Sparkle",
-				);
-				INCLUDED_RECURSIVE_SEARCH_PATH_SUBDIRECTORIES = include;
-				INFOPLIST_FILE = "I2PLauncher copy-Info.plist";
-				LD_NO_PIE = YES;
-				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks @executable_path/Frameworks @loader_path/../Frameworks";
-				MACOSX_DEPLOYMENT_TARGET = 10.12;
-				PRODUCT_BUNDLE_IDENTIFIER = "net.i2p.bootstrap-macosx.I2PLauncher";
-				PRODUCT_NAME = "$(TARGET_NAME)";
-				PROVISIONING_PROFILE_SPECIFIER = "";
-				SDKROOT = macosx;
-				SWIFT_OBJC_BRIDGING_HEADER = "I2PLauncher/I2PLauncher-Bridging-Header.h";
-				SWIFT_VERSION = 4.2;
-				SYSTEM_HEADER_SEARCH_PATHS = "$(SRCROOT)/include/**";
-			};
-			name = Release;
-		};
-/* End XCBuildConfiguration section */
-
-/* Begin XCConfigurationList section */
-		BF5061632113C48E0014EB07 /* Build configuration list for PBXProject "I2PLauncher" */ = {
-			isa = XCConfigurationList;
-			buildConfigurations = (
-				BF50617A2113C4900014EB07 /* Debug */,
-				BF50617B2113C4900014EB07 /* Release */,
-			);
-			defaultConfigurationIsVisible = 0;
-			defaultConfigurationName = Release;
-		};
-		BF50617C2113C4900014EB07 /* Build configuration list for PBXNativeTarget "I2PLauncher" */ = {
-			isa = XCConfigurationList;
-			buildConfigurations = (
-				BF50617D2113C4900014EB07 /* Debug */,
-				BF50617E2113C4900014EB07 /* Release */,
-			);
-			defaultConfigurationIsVisible = 0;
-			defaultConfigurationName = Release;
-		};
-		BF99FD40227087A40014EB07 /* Build configuration list for PBXNativeTarget "RouterWrapper" */ = {
-			isa = XCConfigurationList;
-			buildConfigurations = (
-				BF99FD41227087A40014EB07 /* Debug */,
-				BF99FD42227087A40014EB07 /* Release */,
-			);
-			defaultConfigurationIsVisible = 0;
-			defaultConfigurationName = Release;
-		};
-		BFA5226C21CD434A0014EB07 /* Build configuration list for PBXNativeTarget "StartupItemApp" */ = {
-			isa = XCConfigurationList;
-			buildConfigurations = (
-				BFA5226A21CD434A0014EB07 /* Debug */,
-				BFA5226B21CD434A0014EB07 /* Release */,
-			);
-			defaultConfigurationIsVisible = 0;
-			defaultConfigurationName = Release;
-		};
-		BFAA37F7226891760014EB07 /* Build configuration list for PBXNativeTarget "I2PSnark-Share" */ = {
-			isa = XCConfigurationList;
-			buildConfigurations = (
-				BFAA37F5226891760014EB07 /* Debug */,
-				BFAA37F6226891760014EB07 /* Release */,
-			);
-			defaultConfigurationIsVisible = 0;
-			defaultConfigurationName = Release;
-		};
-		BFD289E1227810AF0014EB07 /* Build configuration list for PBXNativeTarget "I2PLauncher-Appstore" */ = {
-			isa = XCConfigurationList;
-			buildConfigurations = (
-				BFD289E2227810AF0014EB07 /* Debug */,
-				BFD289E3227810AF0014EB07 /* Release */,
-			);
-			defaultConfigurationIsVisible = 0;
-			defaultConfigurationName = Release;
-		};
-/* End XCConfigurationList section */
-
-/* Begin XCVersionGroup section */
-		BF50616E2113C48E0014EB07 /* I2PLauncher.xcdatamodeld */ = {
-			isa = XCVersionGroup;
-			children = (
-				BF50616F2113C48E0014EB07 /* I2PLauncher.xcdatamodel */,
-			);
-			currentVersion = BF50616F2113C48E0014EB07 /* I2PLauncher.xcdatamodel */;
-			path = I2PLauncher.xcdatamodeld;
-			sourceTree = "<group>";
-			versionGroupType = wrapper.xcdatamodel;
-		};
-/* End XCVersionGroup section */
-	};
-	rootObject = BF5061602113C48E0014EB07 /* Project object */;
-}
diff --git a/launchers/macosx/I2PLauncher.xcodeproj/project.xcworkspace/contents.xcworkspacedata b/launchers/macosx/I2PLauncher.xcodeproj/project.xcworkspace/contents.xcworkspacedata
deleted file mode 100644
index 919434a6254f0e9651f402737811be6634a03e9c..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher.xcodeproj/project.xcworkspace/contents.xcworkspacedata
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<Workspace
-   version = "1.0">
-   <FileRef
-      location = "self:">
-   </FileRef>
-</Workspace>
diff --git a/launchers/macosx/I2PLauncher.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist b/launchers/macosx/I2PLauncher.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist
deleted file mode 100644
index 18d981003d68d0546c4804ac2ff47dd97c6e7921..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist
+++ /dev/null
@@ -1,8 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
-<plist version="1.0">
-<dict>
-	<key>IDEDidComputeMac32BitWarning</key>
-	<true/>
-</dict>
-</plist>
diff --git a/launchers/macosx/I2PLauncher.xcworkspace/contents.xcworkspacedata b/launchers/macosx/I2PLauncher.xcworkspace/contents.xcworkspacedata
deleted file mode 100644
index e9946374041f8baa14cabe230b5d3308b969ea4f..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher.xcworkspace/contents.xcworkspacedata
+++ /dev/null
@@ -1,10 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<Workspace
-   version = "1.0">
-   <FileRef
-      location = "group:I2PLauncher.xcodeproj">
-   </FileRef>
-   <FileRef
-      location = "group:Pods/Pods.xcodeproj">
-   </FileRef>
-</Workspace>
diff --git a/launchers/macosx/I2PLauncher.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist b/launchers/macosx/I2PLauncher.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist
deleted file mode 100644
index 18d981003d68d0546c4804ac2ff47dd97c6e7921..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist
+++ /dev/null
@@ -1,8 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
-<plist version="1.0">
-<dict>
-	<key>IDEDidComputeMac32BitWarning</key>
-	<true/>
-</dict>
-</plist>
diff --git a/launchers/macosx/I2PLauncher.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings b/launchers/macosx/I2PLauncher.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings
deleted file mode 100644
index 0c67376ebacb410fd873cac1d8d8dd431b262c02..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings
+++ /dev/null
@@ -1,5 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
-<plist version="1.0">
-<dict/>
-</plist>
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/128x128-Itoopie Transparent.imageset/128x128-Itoopie Transparent.png b/launchers/macosx/I2PLauncher/Assets.xcassets/128x128-Itoopie Transparent.imageset/128x128-Itoopie Transparent.png
deleted file mode 100644
index 6484936a817e5804aa0f73718ca1d454d2864e3f..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/128x128-Itoopie Transparent.imageset/128x128-Itoopie Transparent.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/128x128-Itoopie Transparent.imageset/128x128-Itoopie Transparent@2x.png b/launchers/macosx/I2PLauncher/Assets.xcassets/128x128-Itoopie Transparent.imageset/128x128-Itoopie Transparent@2x.png
deleted file mode 100644
index ede3adf3c93eb1110e0df7d84c5045f0a04dfee2..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/128x128-Itoopie Transparent.imageset/128x128-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/128x128-Itoopie Transparent.imageset/Contents.json b/launchers/macosx/I2PLauncher/Assets.xcassets/128x128-Itoopie Transparent.imageset/Contents.json
deleted file mode 100644
index 5910f0a48bd7f6a84db94d8ff74a6eacc9f3cef0..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Assets.xcassets/128x128-Itoopie Transparent.imageset/Contents.json	
+++ /dev/null
@@ -1,25 +0,0 @@
-{
-  "images" : [
-    {
-      "idiom" : "universal",
-      "filename" : "128x128-Itoopie Transparent.png",
-      "scale" : "1x"
-    },
-    {
-      "idiom" : "universal",
-      "filename" : "128x128-Itoopie Transparent@2x.png",
-      "scale" : "2x"
-    },
-    {
-      "idiom" : "universal",
-      "scale" : "3x"
-    }
-  ],
-  "info" : {
-    "version" : 1,
-    "author" : "xcode"
-  },
-  "properties" : {
-    "template-rendering-intent" : "template"
-  }
-}
\ No newline at end of file
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/16x16-Itoopie Transparent.imageset/16x16-Itoopie Transparent@2x.png b/launchers/macosx/I2PLauncher/Assets.xcassets/16x16-Itoopie Transparent.imageset/16x16-Itoopie Transparent@2x.png
deleted file mode 100644
index d31fa068d83e48debcb7e987450ea2d837efcf1c..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/16x16-Itoopie Transparent.imageset/16x16-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/16x16-Itoopie Transparent.imageset/Contents.json b/launchers/macosx/I2PLauncher/Assets.xcassets/16x16-Itoopie Transparent.imageset/Contents.json
deleted file mode 100644
index 2265ccf22b5dc54f2908b5f72705ca3f5732c0b3..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Assets.xcassets/16x16-Itoopie Transparent.imageset/Contents.json	
+++ /dev/null
@@ -1,24 +0,0 @@
-{
-  "images" : [
-    {
-      "idiom" : "universal",
-      "scale" : "1x"
-    },
-    {
-      "idiom" : "universal",
-      "filename" : "16x16-Itoopie Transparent@2x.png",
-      "scale" : "2x"
-    },
-    {
-      "idiom" : "universal",
-      "scale" : "3x"
-    }
-  ],
-  "info" : {
-    "version" : 1,
-    "author" : "xcode"
-  },
-  "properties" : {
-    "template-rendering-intent" : "template"
-  }
-}
\ No newline at end of file
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/256x256-Itoopie Transparent.imageset/256x256-Itoopie Transparent.png b/launchers/macosx/I2PLauncher/Assets.xcassets/256x256-Itoopie Transparent.imageset/256x256-Itoopie Transparent.png
deleted file mode 100644
index ede3adf3c93eb1110e0df7d84c5045f0a04dfee2..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/256x256-Itoopie Transparent.imageset/256x256-Itoopie Transparent.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/256x256-Itoopie Transparent.imageset/256x256-Itoopie Transparent@2x.png b/launchers/macosx/I2PLauncher/Assets.xcassets/256x256-Itoopie Transparent.imageset/256x256-Itoopie Transparent@2x.png
deleted file mode 100644
index 3fd1aa390f23aa8b376a15b46f87112c76a0eaea..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/256x256-Itoopie Transparent.imageset/256x256-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/256x256-Itoopie Transparent.imageset/Contents.json b/launchers/macosx/I2PLauncher/Assets.xcassets/256x256-Itoopie Transparent.imageset/Contents.json
deleted file mode 100644
index bdd8fea12a6ed187e605a86d68cdf49982090c5d..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Assets.xcassets/256x256-Itoopie Transparent.imageset/Contents.json	
+++ /dev/null
@@ -1,25 +0,0 @@
-{
-  "images" : [
-    {
-      "idiom" : "universal",
-      "filename" : "256x256-Itoopie Transparent.png",
-      "scale" : "1x"
-    },
-    {
-      "idiom" : "universal",
-      "filename" : "256x256-Itoopie Transparent@2x.png",
-      "scale" : "2x"
-    },
-    {
-      "idiom" : "universal",
-      "scale" : "3x"
-    }
-  ],
-  "info" : {
-    "version" : 1,
-    "author" : "xcode"
-  },
-  "properties" : {
-    "template-rendering-intent" : "template"
-  }
-}
\ No newline at end of file
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/32x32-Itoopie Transparent.imageset/32x32-Itoopie Transparent.png b/launchers/macosx/I2PLauncher/Assets.xcassets/32x32-Itoopie Transparent.imageset/32x32-Itoopie Transparent.png
deleted file mode 100644
index d31fa068d83e48debcb7e987450ea2d837efcf1c..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/32x32-Itoopie Transparent.imageset/32x32-Itoopie Transparent.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/32x32-Itoopie Transparent.imageset/32x32-Itoopie Transparent@2x.png b/launchers/macosx/I2PLauncher/Assets.xcassets/32x32-Itoopie Transparent.imageset/32x32-Itoopie Transparent@2x.png
deleted file mode 100644
index 9eac5605c18ad4e7c7c5f70f20349266743e412c..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/32x32-Itoopie Transparent.imageset/32x32-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/32x32-Itoopie Transparent.imageset/Contents.json b/launchers/macosx/I2PLauncher/Assets.xcassets/32x32-Itoopie Transparent.imageset/Contents.json
deleted file mode 100644
index fec5d6fdf47fc2abdad2f45cad71995d54a23517..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Assets.xcassets/32x32-Itoopie Transparent.imageset/Contents.json	
+++ /dev/null
@@ -1,22 +0,0 @@
-{
-  "images" : [
-    {
-      "idiom" : "universal",
-      "filename" : "32x32-Itoopie Transparent.png",
-      "scale" : "1x"
-    },
-    {
-      "idiom" : "universal",
-      "filename" : "32x32-Itoopie Transparent@2x.png",
-      "scale" : "2x"
-    },
-    {
-      "idiom" : "universal",
-      "scale" : "3x"
-    }
-  ],
-  "info" : {
-    "version" : 1,
-    "author" : "xcode"
-  }
-}
\ No newline at end of file
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/512x512-Itoopie Transparent.imageset/512x512-Itoopie Transparent.png b/launchers/macosx/I2PLauncher/Assets.xcassets/512x512-Itoopie Transparent.imageset/512x512-Itoopie Transparent.png
deleted file mode 100644
index 3fd1aa390f23aa8b376a15b46f87112c76a0eaea..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/512x512-Itoopie Transparent.imageset/512x512-Itoopie Transparent.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/512x512-Itoopie Transparent.imageset/512x512-Itoopie Transparent@2x.png b/launchers/macosx/I2PLauncher/Assets.xcassets/512x512-Itoopie Transparent.imageset/512x512-Itoopie Transparent@2x.png
deleted file mode 100644
index 61780fc9e3f821a1395b5182ea5c386eb233f015..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/512x512-Itoopie Transparent.imageset/512x512-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/512x512-Itoopie Transparent.imageset/Contents.json b/launchers/macosx/I2PLauncher/Assets.xcassets/512x512-Itoopie Transparent.imageset/Contents.json
deleted file mode 100644
index c5b355343fc4c58da705df0bc3d7d0a0cf79123c..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Assets.xcassets/512x512-Itoopie Transparent.imageset/Contents.json	
+++ /dev/null
@@ -1,25 +0,0 @@
-{
-  "images" : [
-    {
-      "idiom" : "universal",
-      "filename" : "512x512-Itoopie Transparent.png",
-      "scale" : "1x"
-    },
-    {
-      "idiom" : "universal",
-      "filename" : "512x512-Itoopie Transparent@2x.png",
-      "scale" : "2x"
-    },
-    {
-      "idiom" : "universal",
-      "scale" : "3x"
-    }
-  ],
-  "info" : {
-    "version" : 1,
-    "author" : "xcode"
-  },
-  "properties" : {
-    "template-rendering-intent" : "template"
-  }
-}
\ No newline at end of file
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/128x128-Itoopie Transparent.png b/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/128x128-Itoopie Transparent.png
deleted file mode 100644
index 6484936a817e5804aa0f73718ca1d454d2864e3f..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/128x128-Itoopie Transparent.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/128x128-Itoopie Transparent@2x.png b/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/128x128-Itoopie Transparent@2x.png
deleted file mode 100644
index ede3adf3c93eb1110e0df7d84c5045f0a04dfee2..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/128x128-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/256x256-Itoopie Transparent.png b/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/256x256-Itoopie Transparent.png
deleted file mode 100644
index ede3adf3c93eb1110e0df7d84c5045f0a04dfee2..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/256x256-Itoopie Transparent.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/256x256-Itoopie Transparent@2x.png b/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/256x256-Itoopie Transparent@2x.png
deleted file mode 100644
index 3fd1aa390f23aa8b376a15b46f87112c76a0eaea..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/256x256-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/32x32-Itoopie Transparent.png b/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/32x32-Itoopie Transparent.png
deleted file mode 100644
index d31fa068d83e48debcb7e987450ea2d837efcf1c..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/32x32-Itoopie Transparent.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/32x32-Itoopie Transparent@2x.png b/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/32x32-Itoopie Transparent@2x.png
deleted file mode 100644
index 9eac5605c18ad4e7c7c5f70f20349266743e412c..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/32x32-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/512x512-Itoopie Transparent.png b/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/512x512-Itoopie Transparent.png
deleted file mode 100644
index 3fd1aa390f23aa8b376a15b46f87112c76a0eaea..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/512x512-Itoopie Transparent.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/512x512-Itoopie Transparent@2x.png b/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/512x512-Itoopie Transparent@2x.png
deleted file mode 100644
index 61780fc9e3f821a1395b5182ea5c386eb233f015..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/512x512-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/Contents.json b/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/Contents.json
deleted file mode 100644
index 4953ff08135893b60551462f460fc3ba616b9e09..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Assets.xcassets/AppIcon.appiconset/Contents.json
+++ /dev/null
@@ -1,66 +0,0 @@
-{
-  "images" : [
-    {
-      "idiom" : "mac",
-      "size" : "16x16",
-      "scale" : "1x"
-    },
-    {
-      "idiom" : "mac",
-      "size" : "16x16",
-      "scale" : "2x"
-    },
-    {
-      "size" : "32x32",
-      "idiom" : "mac",
-      "filename" : "32x32-Itoopie Transparent.png",
-      "scale" : "1x"
-    },
-    {
-      "size" : "32x32",
-      "idiom" : "mac",
-      "filename" : "32x32-Itoopie Transparent@2x.png",
-      "scale" : "2x"
-    },
-    {
-      "size" : "128x128",
-      "idiom" : "mac",
-      "filename" : "128x128-Itoopie Transparent.png",
-      "scale" : "1x"
-    },
-    {
-      "size" : "128x128",
-      "idiom" : "mac",
-      "filename" : "128x128-Itoopie Transparent@2x.png",
-      "scale" : "2x"
-    },
-    {
-      "size" : "256x256",
-      "idiom" : "mac",
-      "filename" : "256x256-Itoopie Transparent.png",
-      "scale" : "1x"
-    },
-    {
-      "size" : "256x256",
-      "idiom" : "mac",
-      "filename" : "256x256-Itoopie Transparent@2x.png",
-      "scale" : "2x"
-    },
-    {
-      "size" : "512x512",
-      "idiom" : "mac",
-      "filename" : "512x512-Itoopie Transparent.png",
-      "scale" : "1x"
-    },
-    {
-      "size" : "512x512",
-      "idiom" : "mac",
-      "filename" : "512x512-Itoopie Transparent@2x.png",
-      "scale" : "2x"
-    }
-  ],
-  "info" : {
-    "version" : 1,
-    "author" : "xcode"
-  }
-}
\ No newline at end of file
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/Contents.json b/launchers/macosx/I2PLauncher/Assets.xcassets/Contents.json
deleted file mode 100644
index da4a164c918651cdd1e11dca5cc62c333f097601..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Assets.xcassets/Contents.json
+++ /dev/null
@@ -1,6 +0,0 @@
-{
-  "info" : {
-    "version" : 1,
-    "author" : "xcode"
-  }
-}
\ No newline at end of file
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/StatusBarButtonImage.imageset/32x32-Itoopie Transparent@2x.png b/launchers/macosx/I2PLauncher/Assets.xcassets/StatusBarButtonImage.imageset/32x32-Itoopie Transparent@2x.png
deleted file mode 100644
index 9eac5605c18ad4e7c7c5f70f20349266743e412c..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/StatusBarButtonImage.imageset/32x32-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/StatusBarButtonImage.imageset/Contents.json b/launchers/macosx/I2PLauncher/Assets.xcassets/StatusBarButtonImage.imageset/Contents.json
deleted file mode 100644
index 61ad03057b03aa3a3f17674580ec9cf1d6d382c3..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Assets.xcassets/StatusBarButtonImage.imageset/Contents.json
+++ /dev/null
@@ -1,22 +0,0 @@
-{
-  "images" : [
-    {
-      "idiom" : "universal",
-      "filename" : "ItoopieTransparent.png",
-      "scale" : "1x"
-    },
-    {
-      "idiom" : "universal",
-      "filename" : "32x32-Itoopie Transparent@2x.png",
-      "scale" : "2x"
-    },
-    {
-      "idiom" : "universal",
-      "scale" : "3x"
-    }
-  ],
-  "info" : {
-    "version" : 1,
-    "author" : "xcode"
-  }
-}
\ No newline at end of file
diff --git a/launchers/macosx/I2PLauncher/Assets.xcassets/StatusBarButtonImage.imageset/ItoopieTransparent.png b/launchers/macosx/I2PLauncher/Assets.xcassets/StatusBarButtonImage.imageset/ItoopieTransparent.png
deleted file mode 100644
index 5edecdc1a19c9f8d7da9f6e646018c408f2efdf6..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/I2PLauncher/Assets.xcassets/StatusBarButtonImage.imageset/ItoopieTransparent.png and /dev/null differ
diff --git a/launchers/macosx/I2PLauncher/Base.lproj/UserInterfaces.xib b/launchers/macosx/I2PLauncher/Base.lproj/UserInterfaces.xib
deleted file mode 100644
index 8612bf162add1a4f248af914b233f05b88f9eb61..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Base.lproj/UserInterfaces.xib
+++ /dev/null
@@ -1,89 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<document type="com.apple.InterfaceBuilder3.Cocoa.XIB" version="3.0" toolsVersion="14460.31" targetRuntime="MacOSX.Cocoa" propertyAccessControl="none" useAutolayout="YES" customObjectInstantitationMethod="direct">
-    <dependencies>
-        <deployment identifier="macosx"/>
-        <plugIn identifier="com.apple.InterfaceBuilder.CocoaPlugin" version="14460.31"/>
-    </dependencies>
-    <objects>
-        <customObject id="-2" userLabel="File's Owner" customClass="NSApplication">
-            <connections>
-                <outlet property="delegate" destination="Voe-Tx-rLC" id="GzC-gU-4Uq"/>
-            </connections>
-        </customObject>
-        <customObject id="-1" userLabel="First Responder" customClass="FirstResponder"/>
-        <customObject id="-3" userLabel="Application" customClass="NSObject"/>
-        <customObject id="Voe-Tx-rLC" customClass="AppDelegate"/>
-        <customObject id="YLy-65-1bz" customClass="NSFontManager"/>
-        <menu id="TTS-U7-WkT" userLabel="statusBarContextMenu">
-            <items>
-                <menuItem title="Open Console" id="cOe-UL-1TW">
-                    <modifierMask key="keyEquivalentModifierMask"/>
-                    <connections>
-                        <action selector="openConsoleClicked:" target="-1" id="uR3-lb-ikG"/>
-                    </connections>
-                </menuItem>
-                <menuItem title="Start I2P Router" id="RQ8-Q2-68A">
-                    <modifierMask key="keyEquivalentModifierMask"/>
-                    <connections>
-                        <action selector="startRouterClicked:" target="-1" id="Vl3-cC-77e"/>
-                    </connections>
-                </menuItem>
-                <menuItem title="Exit" id="hsL-CH-m3C">
-                    <modifierMask key="keyEquivalentModifierMask"/>
-                    <connections>
-                        <action selector="quickClicked:" target="-1" id="hiW-5d-nBX"/>
-                    </connections>
-                </menuItem>
-            </items>
-            <point key="canvasLocation" x="17" y="167"/>
-        </menu>
-        <menuItem title="Application" allowsKeyEquivalentWhenHidden="YES" id="84R-pF-Wt1">
-            <modifierMask key="keyEquivalentModifierMask"/>
-            <menu key="submenu" title="Application" id="Trv-j7-WYu">
-                <items>
-                    <menuItem title="About Application" id="XDp-94-iig">
-                        <modifierMask key="keyEquivalentModifierMask"/>
-                        <connections>
-                            <action selector="orderFrontStandardAboutPanel:" target="-1" id="gJe-90-jzd"/>
-                        </connections>
-                    </menuItem>
-                    <menuItem isSeparatorItem="YES" id="xT4-H9-l6g"/>
-                    <menuItem title="Preferences…" keyEquivalent="," id="2Kn-gO-qBP">
-                        <connections>
-                            <action selector="handleNativePrefMenuClicked:" target="-1" id="LFK-TI-TdY"/>
-                        </connections>
-                    </menuItem>
-                    <menuItem isSeparatorItem="YES" id="45f-s8-MiT"/>
-                    <menuItem title="Services" id="x2v-WG-Nuy">
-                        <modifierMask key="keyEquivalentModifierMask"/>
-                        <menu key="submenu" title="Services" systemMenu="services" id="DkL-DH-gJf"/>
-                    </menuItem>
-                    <menuItem isSeparatorItem="YES" id="T1H-h7-Sat"/>
-                    <menuItem title="Hide Application" keyEquivalent="h" id="uAA-NV-src">
-                        <connections>
-                            <action selector="hide:" target="-1" id="wFN-Nz-FpI"/>
-                        </connections>
-                    </menuItem>
-                    <menuItem title="Hide Others" keyEquivalent="h" id="ext-76-4lm">
-                        <modifierMask key="keyEquivalentModifierMask" option="YES" command="YES"/>
-                        <connections>
-                            <action selector="hideOtherApplications:" target="-1" id="KyT-0x-vod"/>
-                        </connections>
-                    </menuItem>
-                    <menuItem title="Show All" id="HmI-6K-eUt">
-                        <modifierMask key="keyEquivalentModifierMask"/>
-                        <connections>
-                            <action selector="unhideAllApplications:" target="-1" id="mXg-9c-azx"/>
-                        </connections>
-                    </menuItem>
-                    <menuItem isSeparatorItem="YES" id="xOX-eV-fcA"/>
-                    <menuItem title="Quit Application" keyEquivalent="q" id="Fap-30-HH0">
-                        <connections>
-                            <action selector="terminate:" target="-1" id="IM7-XC-JlF"/>
-                        </connections>
-                    </menuItem>
-                </items>
-            </menu>
-        </menuItem>
-    </objects>
-</document>
diff --git a/launchers/macosx/I2PLauncher/I2PLauncher-Bridging-Header.h b/launchers/macosx/I2PLauncher/I2PLauncher-Bridging-Header.h
deleted file mode 100644
index 1397ec4a829fae9e9880e17e2e26e5a2a6160950..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/I2PLauncher-Bridging-Header.h
+++ /dev/null
@@ -1,9 +0,0 @@
-//
-//  Use this file to import your target's public headers that you would like to expose to Swift.
-//
-#import "ObjectiveC/SBridge.h"
-#import "AppleStuffExceptionHandler.h"
-#import "ObjectiveC/AppDelegate.h"
-#import "ObjectiveC/RouterTask.h"
-#import "ObjectiveC/logger_c.h"
-#import <Webkit/Webkit.h>
diff --git a/launchers/macosx/I2PLauncher/I2PLauncher.entitlements b/launchers/macosx/I2PLauncher/I2PLauncher.entitlements
deleted file mode 100644
index ec14915f770f89f824d93f9971f594fc4faa9a46..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/I2PLauncher.entitlements
+++ /dev/null
@@ -1,14 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
-<plist version="1.0">
-<dict>
-	<key>com.apple.security.application-groups</key>
-	<array>
-		<string>$(TeamIdentifierPrefix).i2p</string>
-	</array>
-	<key>com.apple.security.cs.allow-jit</key>
-	<true/>
-	<key>com.apple.security.cs.debugger</key>
-	<true/>
-</dict>
-</plist>
diff --git a/launchers/macosx/I2PLauncher/I2PLauncher.xcdatamodeld/.xccurrentversion b/launchers/macosx/I2PLauncher/I2PLauncher.xcdatamodeld/.xccurrentversion
deleted file mode 100644
index f11bfda1c7c6bb9d67fa9845785807a6b20daef6..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/I2PLauncher.xcdatamodeld/.xccurrentversion
+++ /dev/null
@@ -1,8 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
-<plist version="1.0">
-<dict>
-	<key>_XCCurrentVersionName</key>
-	<string>I2PLauncher.xcdatamodel</string>
-</dict>
-</plist>
diff --git a/launchers/macosx/I2PLauncher/I2PLauncher.xcdatamodeld/I2PLauncher.xcdatamodel/contents b/launchers/macosx/I2PLauncher/I2PLauncher.xcdatamodeld/I2PLauncher.xcdatamodel/contents
deleted file mode 100644
index ad82c3b89c84208525fc5de86e953f9551bb0e92..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/I2PLauncher.xcdatamodeld/I2PLauncher.xcdatamodel/contents
+++ /dev/null
@@ -1,4 +0,0 @@
-<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
-<model type="com.apple.IDECoreDataModeler.DataModel" documentVersion="1.0" lastSavedToolsVersion="1" systemVersion="11A491" minimumToolsVersion="Automatic" sourceLanguage="Objective-C" userDefinedModelVersionIdentifier="">
-    <elements/>
-</model>
\ No newline at end of file
diff --git a/launchers/macosx/I2PLauncher/Identifiers.swift b/launchers/macosx/I2PLauncher/Identifiers.swift
deleted file mode 100644
index 0e0f2fea44e71ba513dfcadb511fdc91814522d5..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Identifiers.swift
+++ /dev/null
@@ -1,15 +0,0 @@
-//
-//  Identifiers.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 24/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-class Identifiers {
-  static let applicationDomainId = "net.i2p.bootstrap-macosx"
-  static let mainApplicationBundleId = "net.i2p.bootstrap-macosx.I2PLauncher"
-  static let launcherApplicationBundleId = "net.i2p.bootstrap-macosx.StartupItemApp"
-}
diff --git a/launchers/macosx/I2PLauncher/Info.plist b/launchers/macosx/I2PLauncher/Info.plist
deleted file mode 100644
index 8b037b47631051702e6f665fa653b4863dfa88fd..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Info.plist
+++ /dev/null
@@ -1,48 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
-<plist version="1.0">
-<dict>
-	<key>CFBundleDevelopmentRegion</key>
-	<string>$(DEVELOPMENT_LANGUAGE)</string>
-	<key>CFBundleExecutable</key>
-	<string>$(EXECUTABLE_NAME)</string>
-	<key>CFBundleIconFile</key>
-	<string></string>
-	<key>CFBundleIdentifier</key>
-	<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
-	<key>CFBundleInfoDictionaryVersion</key>
-	<string>6.0</string>
-	<key>CFBundleName</key>
-	<string>$(PRODUCT_NAME)</string>
-	<key>CFBundlePackageType</key>
-	<string>APPL</string>
-	<key>CFBundleShortVersionString</key>
-	<string>$(MARKETING_VERSION)</string>
-	<key>CFBundleVersion</key>
-	<string>$(CURRENT_PROJECT_VERSION)</string>
-	<key>I2PRouterVersion</key>
-	<string>0.9.45</string>
-	<key>LSApplicationCategoryType</key>
-	<string>public.app-category.utilities</string>
-	<key>LSMinimumSystemVersion</key>
-	<string>$(MACOSX_DEPLOYMENT_TARGET)</string>
-	<key>LSUIElement</key>
-	<true/>
-	<key>NSAppleScriptEnabled</key>
-	<true/>
-	<key>NSHumanReadableCopyright</key>
-	<string>Copyright © 2018-2019 The I2P Project. All rights reserved.</string>
-	<key>NSMainNibFile</key>
-	<string>UserInterfaces</string>
-	<key>NSPrincipalClass</key>
-	<string>NSApplication</string>
-	<key>NSServices</key>
-	<array>
-		<dict/>
-	</array>
-	<key>SUFeedURL</key>
-	<string>https://download.i2p2.de/macosx/sparkle/updates/v1/appcast.xml</string>
-	<key>SUPublicEDKey</key>
-	<string>mYg7wXploT0EGhSROqE8QX61T/6Igv622oZOy5jMCoE=</string>
-</dict>
-</plist>
diff --git a/launchers/macosx/I2PLauncher/ObjectiveC/AppDelegate.h b/launchers/macosx/I2PLauncher/ObjectiveC/AppDelegate.h
deleted file mode 100644
index 34cf93af7f39e6177796c6ba6afd00964ad5e4ee..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/ObjectiveC/AppDelegate.h
+++ /dev/null
@@ -1,112 +0,0 @@
-#ifndef __APPDELEGATE_H__
-#define __APPDELEGATE_H__
-
-
-#include <string.h>
-#include <memory.h>
-
-#ifdef __cplusplus
-#include <unistd.h>
-#include <sys/types.h>
-#include <pwd.h>
-#include <assert.h>
-#endif
-
-#include <Cocoa/Cocoa.h>
-#include "SBridge.h"
-
-
-#include "RouterTask.h"
-
-// TODO: Configure the project to avoid such includes.
-#include "../version.h"
-
-@class SwiftApplicationDelegate;
-@class I2PDeployer;
-
-@protocol SwiftMainDelegateProto
-- (void)applicationDidFinishLaunching:(NSNotification *)aNotification;
-@end
-
-
-@class ExtractMetaInfo;
-
-@interface ExtractMetaInfo : NSObject
-@property (copy) NSString* i2pBase;
-@property (copy) NSString* javaBinary;
-@property (copy) NSString* zipFile;
-@property (copy) NSString* jarFile;
-@end
-
-
-#ifdef __cplusplus
-
-inline const char* RealHomeDirectory() {
-  struct passwd *pw = getpwuid(getuid());
-  assert(pw);
-  return pw->pw_dir;
-}
-
-inline std::string getDefaultBaseDir()
-{
-  // Figure out base directory
-  auto homeDir = RealHomeDirectory();
-  const char* pathFromHome = "%s/Library/I2P";
-  char buffer[strlen(homeDir)+strlen(pathFromHome)];
-  sprintf(buffer, pathFromHome, homeDir);
-  std::string i2pBaseDir(buffer);
-  return i2pBaseDir;
-}
-
-inline std::string getDefaultLogDir()
-{
-  // Figure out log directory
-  auto homeDir = RealHomeDirectory();
-  const char* pathFromHome = "%s/Library/Logs/I2P";
-  char buffer[strlen(homeDir)+strlen(pathFromHome)];
-  sprintf(buffer, pathFromHome, homeDir);
-  std::string i2pBaseDir(buffer);
-  return i2pBaseDir;
-}
-
-inline void sendUserNotification(NSString* title, NSString* informativeText, bool makeSound = false) {
-  NSUserNotification *userNotification = [[NSUserNotification alloc] init];
-  
-  userNotification.title = title;
-  userNotification.informativeText = informativeText;
-  NSBundle *launcherBundle = [NSBundle mainBundle];
-  auto resPath = [launcherBundle resourcePath];
-  auto stdResPath = std::string([resPath UTF8String]);
-  stdResPath += "/AppImage.png";
-  auto nsString = [[NSString alloc] initWithUTF8String:(const char*)stdResPath.c_str()];
-  NSImage *appImage = [[NSImage alloc] initWithContentsOfFile:nsString];
-  userNotification.contentImage = appImage;
-  if (makeSound) userNotification.soundName = NSUserNotificationDefaultSoundName;
-  
-  [[NSUserNotificationCenter defaultUserNotificationCenter] scheduleNotification:userNotification];
-};
-
-#endif
-
-@interface AppDelegate : NSObject <NSUserNotificationCenterDelegate, NSApplicationDelegate>
-@property BOOL enableLogging;
-@property BOOL enableVerboseLogging;
-@property (assign) SwiftApplicationDelegate *swiftRuntime;
-@property (assign) NSUserDefaults *userPreferences;
-@property (assign) ExtractMetaInfo *metaInfo;
-@property (assign) I2PDeployer *deployer;
-@property (copy) NSImage *contentImage NS_AVAILABLE(10_9, NA);
-
-- (void) extractI2PBaseDir:(void(^)(BOOL success, NSError *error))completion;
-- (void) awakeFromNib;
-- (void) applicationDidFinishLaunching:(NSNotification *)aNotification;
-- (void) applicationWillTerminate:(NSNotification *)aNotification;
-- (AppDelegate *) initWithArgc:(int)argc argv:(const char **)argv;
-- (BOOL) userNotificationCenter:(NSUserNotificationCenter *)center
-                               shouldPresentNotification:(NSUserNotification *)notification;
-@end
-
-
-
-
-#endif
diff --git a/launchers/macosx/I2PLauncher/ObjectiveC/Deployer.h b/launchers/macosx/I2PLauncher/ObjectiveC/Deployer.h
deleted file mode 100644
index 96f6a20a8f68feb3b27a735401374bb23b0c500e..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/ObjectiveC/Deployer.h
+++ /dev/null
@@ -1,21 +0,0 @@
-//
-//  Deployer.h
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 19/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-#import <Foundation/Foundation.h>
-#import <Foundation/NSError.h>
-#import "AppDelegate.h"
-
-@class ExtractMetaInfo;
-
-
-@interface I2PDeployer : NSObject
-@property (assign) ExtractMetaInfo *metaInfo;
-- (I2PDeployer *) initWithMetaInfo:(ExtractMetaInfo*)mi;
-- (void) extractI2PBaseDir:(void(^)(BOOL success, NSError *error))completion;
-@end
-
diff --git a/launchers/macosx/I2PLauncher/ObjectiveC/Deployer.mm b/launchers/macosx/I2PLauncher/ObjectiveC/Deployer.mm
deleted file mode 100644
index d90ac143fe4ce87ef1ba86a65d08a003406e0d6c..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/ObjectiveC/Deployer.mm
+++ /dev/null
@@ -1,122 +0,0 @@
-//
-//  Deployer.m
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 19/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-#include <functional>
-#include <memory>
-#include <iostream>
-#include <algorithm>
-#include <string>
-#include <list>
-#include <sys/stat.h>
-#include <stdlib.h>
-#include <future>
-#include <vector>
-
-#import <Foundation/Foundation.h>
-#import <Foundation/NSFileManager.h>
-#include <CoreFoundation/CFPreferences.h>
-
-#import <objc/Object.h>
-#import <Cocoa/Cocoa.h>
-#import <AppKit/AppKit.h>
-#import <AppKit/NSApplication.h>
-
-#import "I2PLauncher-Swift.h"
-
-#include "AppDelegate.h"
-// TODO: Configure the project to avoid such includes.
-#include "../include/fn.h"
-#include "../include/subprocess.hpp"
-#include "../include/strutil.hpp"
-
-#import "SBridge.h"
-#include "logger_c.h"
-
-#include <string>
-
-
-#include "Logger.h"
-#include "LoggerWorker.hpp"
-
-#import "Deployer.h"
-
-#include <string.h>
-
-using namespace subprocess;
-
-@implementation I2PDeployer
-
-- (I2PDeployer *) initWithMetaInfo:(ExtractMetaInfo*)mi
-{
-  self.metaInfo = mi;
-  return self;
-}
-
-- (void) extractI2PBaseDir:(void(^)(BOOL success, NSError *error))completion
-{
-#ifdef __cplusplus
-  NSBundle *launcherBundle = [NSBundle mainBundle];
-  auto homeDir = RealHomeDirectory();
-  NSLog(@"Home directory is %s", homeDir);
-  
-  std::string basePath(homeDir);
-  basePath.append("/Library/I2P");
-  
-  self.metaInfo.zipFile = [launcherBundle pathForResource:@"base" ofType:@"zip"];
-  
-  NSParameterAssert(basePath.c_str());
-  NSError *error = NULL;
-  BOOL success = YES;
-  dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
-    
-    
-    try {
-      // Create directory
-      mkdir(basePath.c_str(), S_IRUSR | S_IWUSR | S_IXUSR);
-      
-      auto cli = defaultFlagsForExtractorJob;
-      setenv("I2PBASE", basePath.c_str(), true);
-      //setenv("DYLD_LIBRARY_PATH",".:/usr/lib:/lib:/usr/local/lib", true);
-      
-      chdir(basePath.c_str());
-      
-      // Everything behind --exec java - would be passed as arguments to the java executable.
-      std::string execStr = "/usr/bin/unzip -uo "; //std::string([rs.getJavaHome UTF8String]);
-      execStr += [self.metaInfo.zipFile UTF8String];
-      //for_each(cli, [&execStr](std::string str){ execStr += std::string(" ") + str; });
-      
-      NSLog(@"Trying cmd: %@", [NSString stringWithUTF8String:execStr.c_str()]);
-      sendUserNotification(APP_IDSTR, @"Please hold on while we extract I2P. You'll get a new message once done!");
-      int extractStatus = Popen(execStr.c_str(), environment{{
-        {"I2PBASE", basePath.c_str()}
-      }}).wait();
-      NSLog(@"Extraction exit code %@",[NSString stringWithUTF8String:(std::to_string(extractStatus)).c_str()]);
-      if (extractStatus == 0) {
-        NSLog(@"Extraction process done");
-      } else {
-        NSLog(@"Something went wrong");
-      }
-      
-      // All done. Assume success and error are already set.
-      dispatch_async(dispatch_get_main_queue(), ^{
-        if (completion) {
-          completion(YES, error);
-        }
-      });
-      
-      
-    } catch (OSError &err) {
-      auto errMsg = [NSString stringWithUTF8String:err.what()];
-      NSLog(@"Exception: %@", errMsg);
-      sendUserNotification(APP_IDSTR, [NSString stringWithFormat:@"Error: %@", errMsg]);
-    }
-  });
-#endif
-}
-
-@end
-
diff --git a/launchers/macosx/I2PLauncher/ObjectiveC/Logger.h b/launchers/macosx/I2PLauncher/ObjectiveC/Logger.h
deleted file mode 100644
index e67732a003e3782264142c78adad98eb1154799d..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/ObjectiveC/Logger.h
+++ /dev/null
@@ -1,263 +0,0 @@
-//
-//  Logger.h
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 27/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//  Imported/Refactored from earlier C++ project of Meeh
-//
-
-#ifndef Logger_h
-#define Logger_h
-
-#ifdef __cplusplus
-
-#include <string>
-#include <sstream>
-#include <iostream>
-#include <cstdarg>
-#include <chrono>
-#include <functional>
-#include <ctime>
-
-
-/**
- * For details please see this
- * REFERENCE: http://www.cppreference.com/wiki/io/c/printf_format
- * \verbatim
- *
- There are different %-codes for different variable types, as well as options to
- limit the length of the variables and whatnot.
- Code Format
- %[flags][width][.precision][length]specifier
- SPECIFIERS
- ----------
- %c character
- %d signed integers
- %i signed integers
- %e scientific notation, with a lowercase “e”
- %E scientific notation, with a uppercase “E”
- %f floating point
- %g use %e or %f, whichever is shorter
- %G use %E or %f, whichever is shorter
- %o octal
- %s a string of characters
- %u unsigned integer
- %x unsigned hexadecimal, with lowercase letters
- %X unsigned hexadecimal, with uppercase letters
- %p a pointer
- %n the argument shall be a pointer to an integer into which is placed the number of characters written so far
-
- */
-
-/*
- Usage:
- 
- SharedLogWorker logger(argv[0], path_to_log_file);
- MeehLog::initializeLogging(&logger);
- 
- MLOG(INFO) << "Test SLOG INFO";
- MLOG(DEBUG) << "Test SLOG DEBUG";
- 
- */
-
-
-class SharedLogWorker;
-
-#if !(defined(__PRETTY_FUNCTION__))
-#define __PRETTY_FUNCTION__   __FUNCTION__
-#endif
-
-const int ML_ANNOYING = 0;
-const int ML_DEBUG = 1;
-const int ML_INFO = 2;
-const int ML_WARN = 3;
-const int ML_ERROR = 4;
-const int ML_FATAL = 5;
-static const std::string kFatalLogExpression = "";
-
-#define MLOG_ANNOYING  MeehLog::internal::LogMessage(__FILE__,__LINE__,__PRETTY_FUNCTION__,"ML_ANNOYING")
-#define MLOG_DEBUG     MeehLog::internal::LogMessage(__FILE__,__LINE__,__PRETTY_FUNCTION__,"ML_DEBUG")
-#define MLOG_INFO      MeehLog::internal::LogMessage(__FILE__,__LINE__,__PRETTY_FUNCTION__,"ML_INFO")
-#define MLOG_WARN      MeehLog::internal::LogMessage(__FILE__,__LINE__,__PRETTY_FUNCTION__,"ML_WARN")
-#define MLOG_ERROR     MeehLog::internal::LogMessage(__FILE__,__LINE__,__PRETTY_FUNCTION__,"ML_ERROR")
-#define MLOG_FATAL     MeehLog::internal::LogContractMessage(__FILE__,__LINE__,__PRETTY_FUNCTION__,k_fatal_log_expression)
-
-// MLOG(level) is the API for the stream log
-#define MLOG(level) MLOG_##level.messageStream()
-
-// conditional stream log
-#define LOG_IF(level, boolean_expression)  \
-  if(true == boolean_expression)           \
-    MLOG_##level.messageStream()
-
-#define MASSERT(boolean_expression)                                                    \
-  if (false == (boolean_expression))                                                   \
-    MeehLog::internal::LogContractMessage(__FILE__, __LINE__, __PRETTY_FUNCTION__, #boolean_expression).messageStream()
-
-
-#define MLOGF_ANNOYING  MeehLog::internal::LogMessage(__FILE__, __LINE__, __PRETTY_FUNCTION__,"ML_ANNOYING")
-#define MLOGF_INFO      MeehLog::internal::LogMessage(__FILE__, __LINE__, __PRETTY_FUNCTION__,"ML_INFO")
-#define MLOGF_DEBUG     MeehLog::internal::LogMessage(__FILE__, __LINE__, __PRETTY_FUNCTION__,"ML_DEBUG")
-#define MLOGF_WARN      MeehLog::internal::LogMessage(__FILE__, __LINE__, __PRETTY_FUNCTION__,"ML_WARN")
-#define MLOGF_ERROR     MeehLog::internal::LogMessage(__FILE__, __LINE__, __PRETTY_FUNCTION__,"ML_ERROR")
-#define MLOGF_FATAL     MeehLog::internal::LogContractMessage(__FILE__, __LINE__, __PRETTY_FUNCTION__,k_fatal_log_expression)
-
-// MLOGF(level,msg,...) is the API for the "printf" like log
-#define MLOGF(level, printf_like_message, ...)                   \
-  MLOGF_##level.messageSave(printf_like_message, ##__VA_ARGS__)
-
-// conditional log printf syntax
-#define MLOGF_IF(level,boolean_expression, printf_like_message, ...) \
-  if(true == boolean_expression)                                    \
-    MLOG_##level.messageSave(printf_like_message, ##__VA_ARGS__)
-
-// Design By Contract, printf-like API syntax with variadic input parameters. Throws std::runtime_eror if contract breaks */
-#define MASSERTF(boolean_expression, printf_like_message, ...)                                     \
-  if (false == (boolean_expression))                                                               \
-    MeehLog::internal::LogContractMessage(__FILE__, __LINE__, __PRETTY_FUNCTION__,#boolean_expression).messageSave(printf_like_message, ##__VA_ARGS__)
-
-namespace MeehLog {
-  
-  
-  // PUBLIC API:
-  /** Install signal handler that catches FATAL C-runtime or OS signals
-   SIGABRT  ABORT (ANSI), abnormal termination
-   SIGFPE   Floating point exception (ANSI): http://en.wikipedia.org/wiki/SIGFPE
-   SIGILL   ILlegal instruction (ANSI)
-   SIGSEGV  Segmentation violation i.e. illegal memory reference
-   SIGTERM  TERMINATION (ANSI) */
-  void installSignalHandler();
-  
-  namespace internal {
-    
-    
-    /** \return signal_name. Ref: signum.h and \ref installSignalHandler */
-    std::string signalName(int signal_number);
-    
-    /** Re-"throw" a fatal signal, previously caught. This will exit the application
-     * This is an internal only function. Do not use it elsewhere. It is triggered
-     * from g2log, g2LogWorker after flushing messages to file */
-    void exitWithDefaultSignalHandler(int signal_number);
-    
-    std::time_t systemtime_now();
-    bool isLoggingInitialized();
-    
-    struct LogEntry {
-      LogEntry(std::string msg, std::time_t timestamp) : mMsg(msg), mTimestamp(timestamp) {}
-      LogEntry(const LogEntry& other): mMsg(other.mMsg), mTimestamp(other.mTimestamp) {}
-      LogEntry& operator=(const LogEntry& other) {
-        mMsg = other.mMsg;
-        mTimestamp = other.mTimestamp;
-        return *this;
-      }
-      
-      
-      std::string mMsg;
-      std::time_t mTimestamp;
-    };
-    
-    /** Trigger for flushing the message queue and exiting the application
-     A thread that causes a FatalMessage will sleep forever until the
-     application has exited (after message flush) */
-    struct FatalMessage {
-      enum FatalType {kReasonFatal, kReasonOS_FATAL_SIGNAL};
-      FatalMessage(LogEntry message, FatalType type, int signal_id);
-      ~FatalMessage() {};
-      FatalMessage& operator=(const FatalMessage& fatal_message);
-      
-      
-      LogEntry mMessage;
-      FatalType mType;
-      int mSignalId;
-    };
-    // Will trigger a FatalMessage sending
-    struct FatalTrigger {
-      FatalTrigger(const FatalMessage& message);
-      ~FatalTrigger();
-      FatalMessage mMessage;
-    };
-
-    // Log message for 'printf-like' or stream logging, it's a temporary message constructions
-    class LogMessage {
-    public:
-      LogMessage(const std::string& file, const int line, const std::string& function, const std::string& level);
-      virtual ~LogMessage(); // at destruction will flush the message
-      
-      std::ostringstream& messageStream() {return mStream;}
-      
-      // To generate warn on illegal printf format
-    #ifndef __GNUC__
-    #define  __attribute__(x)
-    #endif
-      // C++ get 'this' as first arg
-      void messageSave(const char* printf_like_message, ...)
-      __attribute__((format(printf, 2, 3) ));
-      
-    protected:
-      const std::string mFile;
-      const int mLine;
-      const std::string mFunction;
-      const std::string mLevel;
-      std::ostringstream mStream;
-      std::string mLogEntry;
-      std::time_t mTimestamp;
-    };
-
-    // 'Design-by-Contract' temporary messsage construction
-    class LogContractMessage : public LogMessage {
-    public:
-      LogContractMessage(const std::string& file, const int line,
-                         const std::string& function, const std::string& boolean_expression);
-      virtual ~LogContractMessage(); // at destruction will flush the message
-      
-    protected:
-      const std::string mExpression;
-    };
-    
-    //  wrap for std::chrono::system_clock::now()
-    std::time_t systemtime_now();
-    
-  } // namespace internal
-  
-  
-  
-  /** Should be called at very first startup of the software with \ref SharedLogWorker pointer.
-   * Ownership of the \ref SharedLogWorker is the responsibilkity of the caller */
-  void initializeLogging(SharedLogWorker* logger);
-  
-  /** Shutdown the logging by making the pointer to the background logger to nullptr
-   * The \ref pointer to the SharedLogWorker is owned by the instantniater \ref initializeLogging
-   * and is not deleted.
-   */
-  void shutDownLogging();
-  
-  /** Same as the Shutdown above but called by the destructor of the LogWorker, thus ensuring that no further
-   *  LOG(...) calls can happen to  a non-existing LogWorker.
-   *  @param active MUST BE the LogWorker initialized for logging. If it is not then this call is just ignored
-   *         and the logging continues to be active.
-   * @return true if the correct worker was given,. and shutDownLogging was called
-   */
-  bool shutDownLoggingForActiveOnly(SharedLogWorker* active);
-  
-  
-  typedef std::chrono::steady_clock::time_point steady_time_point;
-  typedef std::chrono::time_point<std::chrono::system_clock>  system_time_point;
-  typedef std::chrono::milliseconds milliseconds;
-  typedef std::chrono::microseconds microseconds;
-  
-  /** return time representing POD struct (ref ctime + wchar) that is normally
-   * retrieved with std::localtime. MeehLog::localtime is threadsafe which std::localtime is not.
-   * MeehLog::localtime is probably used together with @ref MeehLog::systemtime_now */
-  tm localtime(const std::time_t& time);
-  
-  /** format string must conform to std::put_time's demands.
-   * WARNING: At time of writing there is only so-so compiler support for
-   * std::put_time. A possible fix if your c++11 library is not updated is to
-   * modify this to use std::strftime instead */
-  std::string localtime_formatted(const std::time_t& time_snapshot, const std::string& time_format) ;
-} // namespace MeehLog
-
-#endif // __cplusplus
-
-#endif /* Logger_h */
diff --git a/launchers/macosx/I2PLauncher/ObjectiveC/Logger.mm b/launchers/macosx/I2PLauncher/ObjectiveC/Logger.mm
deleted file mode 100644
index 2c303cd9b575f39a2b2820567f9bc79f480519fd..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/ObjectiveC/Logger.mm
+++ /dev/null
@@ -1,370 +0,0 @@
-//
-//  Logger.cpp
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 27/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//  Imported/Refactored from earlier C++ project of Meeh
-//
-
-#include <iostream>
-#include <sstream>
-#include <string>
-#include <stdexcept> // exceptions
-#include <cstdio>    // vsnprintf
-#include <cassert>
-#include <mutex>
-#include <signal.h>
-#include <thread>
-
-#include <unistd.h>
-#include <execinfo.h>
-#include <cxxabi.h>
-#include <cstdlib>
-#include <sys/ucontext.h>
-
-#include "Logger.h"
-#include "LoggerWorker.hpp"
-
-namespace {
-  std::once_flag gIsInitialized;
-  std::once_flag gSetFirstUninitializedFlag;
-  std::once_flag gSaveFirstUnintializedFlag;
-  SharedLogWorker* gLoggerWorkerInstance = nullptr;
-  MeehLog::internal::LogEntry gFirstUnintializedMsg = {"", 0};
-  std::mutex gLoggerMasterMutex;
-  const std::string kTruncatedWarningText = "[...truncated...]";
-  
-  std::string splitFileName(const std::string& str) {
-    size_t found;
-    found = str.find_last_of("\\");
-    return str.substr(found + 1);
-  }
-  
-  void saveToLogger(const MeehLog::internal::LogEntry& logEntry) {
-    // Uninitialized messages are ignored but does not MASSERT/crash the logger
-    if (!MeehLog::internal::isLoggingInitialized()) {
-      std::string err("LOGGER NOT INITIALIZED: " + logEntry.mMsg);
-      std::call_once(gSetFirstUninitializedFlag,
-                     [&] { gFirstUnintializedMsg.mMsg += err;
-                       gFirstUnintializedMsg.mTimestamp = MeehLog::internal::systemtime_now();
-                     });
-      // dump to std::err all the non-initialized logs
-      std::cerr << err << std::endl;
-      return;
-    }
-    // Save the first uninitialized message, if any
-    std::call_once(gSaveFirstUnintializedFlag, [] {
-      if (!gFirstUnintializedMsg.mMsg.empty()) {
-        gLoggerWorkerInstance->save(gFirstUnintializedMsg);
-      }
-    });
-    
-    gLoggerWorkerInstance->save(logEntry);
-  }
-  void crashHandler(int signal_number, siginfo_t* info, void* unused_context) {
-    const size_t max_dump_size = 50;
-    void* dump[max_dump_size];
-    size_t size = backtrace(dump, max_dump_size);
-    char** messages = backtrace_symbols(dump, (int)size); // overwrite sigaction with caller's address
-    
-    std::ostringstream oss;
-    oss << "Received fatal signal: " << MeehLog::internal::signalName(signal_number);
-    oss << "(" << signal_number << ")" << std::endl;
-    oss << "PID: " << getpid() << std::endl;
-    
-    // dump stack: skip first frame, since that is here
-    for (size_t idx = 1; idx < size && messages != nullptr; ++idx) {
-      char* mangled_name = 0, *offset_begin = 0, *offset_end = 0;
-      // find parantheses and +address offset surrounding mangled name
-      for (char* p = messages[idx]; *p; ++p) {
-        if (*p == '(') {
-          mangled_name = p;
-        } else if (*p == '+') {
-          offset_begin = p;
-        } else if (*p == ')') {
-          offset_end = p;
-          break;
-        }
-      }
-      
-      // if the line could be processed, attempt to demangle the symbol
-      if (mangled_name && offset_begin && offset_end &&
-          mangled_name < offset_begin) {
-        *mangled_name++ = '\0';
-        *offset_begin++ = '\0';
-        *offset_end++ = '\0';
-        
-        int status;
-        char* real_name = abi::__cxa_demangle(mangled_name, 0, 0, &status);
-        // if demangling is successful, output the demangled function name
-        if (status == 0) {
-          oss << "stack dump [" << idx << "]  " << messages[idx] << " : " << real_name << "+";
-          oss << offset_begin << offset_end << std::endl;
-        }
-        // otherwise, output the mangled function name
-        else {
-          oss << "stack dump [" << idx << "]  " << messages[idx] << mangled_name << "+";
-          oss << offset_begin << offset_end << std::endl;
-        }
-        free(real_name); // mallocated by abi::__cxa_demangle(...)
-      } else {
-        // no demangling done -- just dump the whole line
-        oss << "stack dump [" << idx << "]  " << messages[idx] << std::endl;
-      }
-    } // END: for(size_t idx = 1; idx < size && messages != nullptr; ++idx)
-    
-    
-    
-    free(messages);
-    {
-      // Local scope, trigger send
-      using namespace MeehLog::internal;
-      std::ostringstream fatal_stream;
-      fatal_stream << "\n\n***** FATAL TRIGGER RECEIVED ******* " << std::endl;
-      fatal_stream << oss.str() << std::endl;
-      fatal_stream << "\n***** RETHROWING SIGNAL " << signalName(signal_number) << "(" << signal_number << ")" << std::endl;
-      
-      LogEntry entry = {fatal_stream.str(), systemtime_now()};
-      FatalMessage fatal_message(entry, FatalMessage::kReasonOS_FATAL_SIGNAL, signal_number);
-      FatalTrigger trigger(fatal_message);  std::ostringstream oss;
-      std::cerr << fatal_message.mMessage.mMsg << std::endl << std::flush;
-    } // message sent to SharedLogWorker
-    // wait to die -- will be inside the FatalTrigger
-  }
-} // End anonymous namespace
-
-
-
-namespace MeehLog {
-  
-  // signalhandler and internal clock is only needed to install once
-  // for unit testing purposes the initializeLogging might be called
-  // several times... for all other practical use, it shouldn't!
-  void initializeLogging(SharedLogWorker* bgworker) {
-    std::call_once(gIsInitialized, []() {
-      //installSignalHandler();
-    });
-    
-    std::lock_guard<std::mutex> lock(gLoggerMasterMutex);
-    MASSERT(!internal::isLoggingInitialized());
-    MASSERT(bgworker != nullptr);
-    gLoggerWorkerInstance = bgworker;
-  }
-  
-  
-  
-  void  shutDownLogging() {
-    std::lock_guard<std::mutex> lock(gLoggerMasterMutex);
-    gLoggerWorkerInstance = nullptr;
-  }
-  
-  
-  
-  bool shutDownLoggingForActiveOnly(SharedLogWorker* active) {
-    if (internal::isLoggingInitialized() && nullptr != active  &&
-        (dynamic_cast<void*>(active) != dynamic_cast<void*>(gLoggerWorkerInstance))) {
-      MLOG(WARN) << "\nShutting down logging, but the ID of the Logger is not the one that is active."
-      << "\nHaving multiple instances of the MeehLog::LogWorker is likely a BUG"
-      << "\nEither way, this call to shutDownLogging was ignored";
-      return false;
-    }
-    shutDownLogging();
-    return true;
-  }
-  
-  void installSignalHandler() {
-    struct sigaction action;
-    memset(&action, 0, sizeof(action));
-    sigemptyset(&action.sa_mask);
-    action.sa_sigaction = &crashHandler;  // callback to crashHandler for fatal signals
-    // sigaction to use sa_sigaction file. ref: http://www.linuxprogrammingblog.com/code-examples/sigaction
-    action.sa_flags = SA_SIGINFO;
-    
-    // do it verbose style - install all signal actions
-    if (sigaction(SIGABRT, &action, NULL) < 0)
-      perror("sigaction - SIGABRT");
-    if (sigaction(SIGFPE, &action, NULL) < 0)
-      perror("sigaction - SIGFPE");
-    if (sigaction(SIGILL, &action, NULL) < 0)
-      perror("sigaction - SIGILL");
-    if (sigaction(SIGSEGV, &action, NULL) < 0)
-      perror("sigaction - SIGSEGV");
-    if (sigaction(SIGTERM, &action, NULL) < 0)
-      perror("sigaction - SIGTERM");
-  }
-  
-  namespace internal {
-    
-    std::time_t systemtime_now()
-    {
-      system_time_point system_now = std::chrono::system_clock::now();
-      return std::chrono::system_clock::to_time_t(system_now);
-    }
-    
-    bool isLoggingInitialized() {
-      return gLoggerWorkerInstance != nullptr;
-    }
-    
-    LogContractMessage::LogContractMessage(const std::string& file, const int line,
-                                           const std::string& function, const std::string& boolean_expression)
-    : LogMessage(file, line, function, "FATAL")
-    , mExpression(boolean_expression)
-    {}
-    
-    LogContractMessage::~LogContractMessage() {
-      std::ostringstream oss;
-      if (0 == mExpression.compare(kFatalLogExpression)) {
-        oss << "\n[  *******\tEXIT trigger caused by MLOG(FATAL): \n";
-      } else {
-        oss << "\n[  *******\tEXIT trigger caused by broken Contract: MASSERT(" << mExpression << ")\n";
-      }
-      mLogEntry = oss.str();
-    }
-    
-    LogMessage::LogMessage(const std::string& file, const int line, const std::string& function, const std::string& level)
-    : mFile(file)
-    , mLine(line)
-    , mFunction(function)
-    , mLevel(level)
-    , mTimestamp(systemtime_now())
-    {}
-    
-    LogMessage::~LogMessage() {
-      using namespace internal;
-      std::ostringstream oss;
-      const bool fatal = (0 == mLevel.compare("FATAL"));
-      oss << mLevel << " [" << splitFileName(mFile);
-      if (fatal)
-        oss <<  " at function: " << mFunction ;
-        oss << " Line: " << mLine << "]";
-      
-      const std::string str(mStream.str());
-      if (!str.empty()) {
-        oss << '"' << str << '"';
-      }
-      mLogEntry += oss.str();
-      
-      
-      if (fatal) { // os_fatal is handled by crashhandlers
-        {
-          // local scope - to trigger FatalMessage sending
-          FatalMessage::FatalType fatal_type(FatalMessage::kReasonFatal);
-          FatalMessage fatal_message({mLogEntry, mTimestamp}, fatal_type, SIGABRT);
-          FatalTrigger trigger(fatal_message);
-          std::cerr  << mLogEntry << "\t*******  ]" << std::endl << std::flush;
-        } // will send to worker
-      }
-      
-      saveToLogger({mLogEntry, mTimestamp}); // message saved
-    }
-    
-    // represents the actual fatal message
-    FatalMessage::FatalMessage(LogEntry message, FatalType type, int signal_id)
-    : mMessage(message)
-    , mType(type)
-    , mSignalId(signal_id) {}
-    
-    
-    FatalMessage& FatalMessage::operator=(const FatalMessage& other) {
-      mMessage = other.mMessage;
-      mType = other.mType;
-      mSignalId = other.mSignalId;
-      return *this;
-    }
-    
-    std::string signalName(int signal_number) {
-      switch (signal_number) {
-        case SIGABRT: return "SIGABRT"; break;
-        case SIGFPE:  return "SIGFPE"; break;
-        case SIGSEGV: return "SIGSEGV"; break;
-        case SIGILL:  return "SIGILL"; break;
-        case SIGTERM: return "SIGTERM"; break;
-        default:
-          std::ostringstream oss;
-          oss << "UNKNOWN SIGNAL(" << signal_number << ")";
-          return oss.str();
-      }
-    }
-    
-    void exitWithDefaultSignalHandler(int signal_number) {
-      std::cerr << "Exiting - FATAL SIGNAL: " << signal_number << "   " << std::flush;
-      struct sigaction action;
-      memset(&action, 0, sizeof(action));  //
-      sigemptyset(&action.sa_mask);
-      action.sa_handler = SIG_DFL; // take default action for the signal
-      sigaction(signal_number, &action, NULL);
-      kill(getpid(), signal_number);
-      abort(); // should never reach this
-    }
-    
-    /** Fatal call saved to logger. This will trigger SIGABRT or other fatal signal
-     * to exit the program. After saving the fatal message the calling thread
-     * will sleep forever (i.e. until the background thread catches up, saves the fatal
-     * message and kills the software with the fatal signal.
-     */
-    void fatalCallToLogger(FatalMessage message) {
-      if (!isLoggingInitialized()) {
-        std::ostringstream error;
-        error << "FATAL CALL but logger is NOT initialized\n"
-        << "SIGNAL: " << MeehLog::internal::signalName(message.mSignalId)
-        << "\nMessage: \n" << message.mMessage.mMsg << std::flush;
-        std::cerr << error.str();
-        
-        //internal::exitWithDefaultSignalHandler(message.mSignalId);
-      }
-      gLoggerWorkerInstance->fatal(message);
-      while (true) {
-        std::this_thread::sleep_for(std::chrono::seconds(1));
-      }
-    }
-    
-    std::function<void(FatalMessage) > gFatalToMLogWorkerFunctionPtr = fatalCallToLogger;
-    
-    // used to RAII trigger fatal message sending to g2LogWorker
-    FatalTrigger::FatalTrigger(const FatalMessage& message)
-    :  mMessage(message) {}
-    
-    // at destruction, flushes fatal message to g2LogWorker
-    FatalTrigger::~FatalTrigger() {
-      // either we will stay here eternally, or it's in unit-test mode
-      gFatalToMLogWorkerFunctionPtr(mMessage);
-    }
-    
-    // This mimics the original "std::put_time(const std::tm* tmb, const charT* fmt)"
-    // This is needed since latest version (at time of writing) of gcc4.7 does not implement this library function yet.
-    // return value is SIMPLIFIED to only return a std::string
-    std::string put_time(const struct tm* tmb, const char* c_time_format)
-    {
-      const size_t size = 1024;
-      char buffer[size]; // IMPORTANT: check now and then for when gcc will implement std::put_time finns.
-      //                    ... also ... This is way more buffer space then we need
-      auto success = std::strftime(buffer, size, c_time_format, tmb);
-      if (0 == success)
-        return c_time_format; // For this hack it is OK but in case of more permanent we really should throw here, or even assert
-      return buffer;
-    }
-
-  } // ns internal
-  
-  
-  tm localtime(const std::time_t& time)
-  {
-    struct tm tm_snapshot;
-    localtime_r(&time, &tm_snapshot); // POSIX
-    return tm_snapshot;
-  }
-  
-  /// returns a std::string with content of time_t as localtime formatted by input format string
-  /// * format string must conform to std::put_time
-  /// This is similar to std::put_time(std::localtime(std::time_t*), time_format.c_str());
-  std::string localtime_formatted(const std::time_t& time_snapshot, const std::string& time_format)
-  {
-    std::tm t = localtime(time_snapshot); // could be const, but cannot due to VS2012 is non conformant for C++11's std::put_time (see above)
-    std::stringstream buffer;
-    buffer << MeehLog::internal::put_time(&t, time_format.c_str());  // format example: //"%Y/%m/%d %H:%M:%S");
-    return buffer.str();
-  }
-
-} // ns MeehLog
-
diff --git a/launchers/macosx/I2PLauncher/ObjectiveC/LoggerWorker.cpp b/launchers/macosx/I2PLauncher/ObjectiveC/LoggerWorker.cpp
deleted file mode 100644
index 0d5ce37c76095e4f938143fd6692a85b06197814..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/ObjectiveC/LoggerWorker.cpp
+++ /dev/null
@@ -1,320 +0,0 @@
-//
-//  LoggerWorker.cpp
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 27/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//  Imported/Refactored from earlier C++ project of Meeh
-//
-
-#include "LoggerWorker.hpp"
-#include "Logger.h"
-
-#include <fstream>
-#include <sstream>
-#include <cassert>
-#include <algorithm>
-#include <string>
-#include <chrono>
-#include <functional>
-#include <future>
-
-using namespace MeehLog;
-using namespace MeehLog::internal;
-
-Active::Active(): mDone(false){}
-
-Active::~Active() {
-  Callback quit_token = std::bind(&Active::doDone, this);
-  send(quit_token); // tell thread to exit
-  mThd.join();
-}
-
-// Add asynchronously a work-message to queue
-void Active::send(Callback msg_){
-  mMq.push(msg_);
-}
-
-
-// Will wait for msgs if queue is empty
-// A great explanation of how this is done (using Qt's library):
-// http://doc.qt.nokia.com/stable/qwaitcondition.html
-void Active::run() {
-  while (!mDone) {
-    // wait till job is available, then retrieve it and
-    // executes the retrieved job in this thread (background)
-    Callback func;
-    mMq.wait_and_pop(func);
-    func();
-  }
-}
-
-// Factory: safe construction of object before thread start
-std::unique_ptr<Active> Active::createActive(){
-  std::unique_ptr<Active> aPtr(new Active());
-  aPtr->mThd = std::thread(&Active::run, aPtr.get());
-  return aPtr;
-}
-
-namespace {
-  static const std::string date_formatted =  "%Y/%m/%d";
-  static const std::string time_formatted = "%H:%M:%S";
-  static const std::string file_name_time_formatted =  "%Y%m%d-%H%M%S";
-  
-  // check for filename validity -  filename should not be part of PATH
-  bool isValidFilename(const std::string prefix_filename) {
-    
-    std::string illegal_characters("/,|<>:#$%{}()[]\'\"^!?+* ");
-    size_t pos = prefix_filename.find_first_of(illegal_characters, 0);
-    if (pos != std::string::npos) {
-      std::cerr << "Illegal character [" << prefix_filename.at(pos) << "] in logname prefix: " << "[" << prefix_filename << "]" << std::endl;
-      return false;
-    } else if (prefix_filename.empty()) {
-      std::cerr << "Empty filename prefix is not allowed" << std::endl;
-      return false;
-    }
-    
-    return true;
-  }
-
-  // Clean up the path if put in by mistake in the prefix
-  std::string prefixSanityFix(std::string prefix) {
-    prefix.erase(std::remove_if(prefix.begin(), prefix.end(), ::isspace), prefix.end());
-    prefix.erase(std::remove( prefix.begin(), prefix.end(), '\\'), prefix.end()); // '\\'
-    prefix.erase(std::remove( prefix.begin(), prefix.end(), '.'), prefix.end());  // '.'
-    prefix.erase(std::remove(prefix.begin(), prefix.end(), ':'), prefix.end()); // ':'
-    
-    if (!isValidFilename(prefix)) {
-      return "";
-    }
-    return prefix;
-  }
-  std::string pathSanityFix(std::string path, std::string file_name) {
-    // Unify the delimeters,. maybe sketchy solution but it seems to work
-    // on at least win7 + ubuntu. All bets are off for older windows
-    std::replace(path.begin(), path.end(), '\\', '/');
-    
-    // clean up in case of multiples
-    auto contains_end = [&](std::string & in) -> bool {
-      size_t size = in.size();
-      if (!size) return false;
-      char end = in[size - 1];
-      return (end == '/' || end == ' ');
-    };
-    
-    while (contains_end(path)) { path.erase(path.size() - 1); }
-    if (!path.empty()) {
-      path.insert(path.end(), '/');
-    }
-    path.insert(path.size(), file_name);
-    return path;
-  }
-  
-  
-  std::string createLogFileName(const std::string& verified_prefix) {
-    std::stringstream ossName;
-    ossName.fill('0');
-    ossName << verified_prefix << MeehLog::localtime_formatted(systemtime_now(), file_name_time_formatted);
-    ossName << ".log";
-    return ossName.str();
-  }
-  
-  
-  bool openLogFile(const std::string& complete_file_with_path, std::ofstream& outstream) {
-    std::ios_base::openmode mode = std::ios_base::out; // for clarity: it's really overkill since it's an ofstream
-    mode |= std::ios_base::trunc;
-    outstream.open(complete_file_with_path, mode);
-    if (!outstream.is_open()) {
-      std::ostringstream ss_error;
-      ss_error << "FILE ERROR:  could not open log file:[" << complete_file_with_path << "]";
-      ss_error << "\nstd::ios_base state = " << outstream.rdstate();
-      std::cerr << ss_error.str().c_str() << std::endl << std::flush;
-      outstream.close();
-      return false;
-    }
-    std::ostringstream ss_entry;
-    //  Day Month Date Time Year: is written as "%a %b %d %H:%M:%S %Y" and formatted output as : Wed Aug 10 08:19:45 2014
-    ss_entry << "MeehLog created log file at: " << MeehLog::localtime_formatted(systemtime_now(), "%a %b %d %H:%M:%S %Y") << "\n";
-    ss_entry << "LOG format: [YYYY/MM/DD hh:mm:ss uuu* LEVEL FILE:LINE] message (uuu*: microsecond counter since initialization of log worker)\n\n";
-    outstream << ss_entry.str() << std::flush;
-    outstream.fill('0');
-    return true;
-  }
-  
-  
-  std::unique_ptr<std::ofstream> createLogFile(const std::string& file_with_full_path) {
-    std::unique_ptr<std::ofstream> out(new std::ofstream);
-    std::ofstream& stream(*(out.get()));
-    bool success_with_open_file = openLogFile(file_with_full_path, stream);
-    if (false == success_with_open_file) {
-      out.release(); // nullptr contained ptr<file> signals error in creating the log file
-    }
-    return out;
-  }
-}  // end anonymous namespace
-
-/** The Real McCoy Background worker, while g2LogWorker gives the
- * asynchronous API to put job in the background the g2LogWorkerImpl
- * does the actual background thread work */
-struct SharedLogWorkerImpl {
-  SharedLogWorkerImpl(const std::string& log_prefix, const std::string& log_directory);
-  ~SharedLogWorkerImpl();
-  
-  void backgroundFileWrite(MeehLog::internal::LogEntry message);
-  void backgroundExitFatal(MeehLog::internal::FatalMessage fatal_message);
-  std::string  backgroundChangeLogFile(const std::string& directory);
-  std::string  backgroundFileName();
-  
-  std::string log_file_with_path_;
-  std::string log_prefix_backup_; // needed in case of future log file changes of directory
-  std::unique_ptr<MeehLog::Active> mBg;
-  std::unique_ptr<std::ofstream> mOutptr;
-  steady_time_point steady_start_time_;
-  
-private:
-  SharedLogWorkerImpl& operator=(const SharedLogWorkerImpl&);
-  SharedLogWorkerImpl(const SharedLogWorkerImpl& other);
-  std::ofstream& filestream() {return *(mOutptr.get());}
-};
-
-//
-// Private API implementation : SharedLogWorkerImpl
-SharedLogWorkerImpl::SharedLogWorkerImpl(const std::string& log_prefix, const std::string& log_directory)
-: log_file_with_path_(log_directory)
-, log_prefix_backup_(log_prefix)
-, mBg(MeehLog::Active::createActive())
-, mOutptr(new std::ofstream)
-, steady_start_time_(std::chrono::steady_clock::now()) { // TODO: ha en timer function steadyTimer som har koll på start
-  log_prefix_backup_ = prefixSanityFix(log_prefix);
-  if (!isValidFilename(log_prefix_backup_)) {
-    // illegal prefix, refuse to start
-    std::cerr << "MeehLog: forced abort due to illegal log prefix [" << log_prefix << "]" << std::endl << std::flush;
-    abort();
-  }
-  
-  std::string file_name = createLogFileName(log_prefix_backup_);
-  log_file_with_path_ = pathSanityFix(log_file_with_path_, file_name);
-  mOutptr = createLogFile(log_file_with_path_);
-  if (!mOutptr) {
-    std::cerr << "Cannot write logfile to location, attempting current directory" << std::endl;
-    log_file_with_path_ = "./" + file_name;
-    mOutptr = createLogFile(log_file_with_path_);
-  }
-  assert((mOutptr) && "cannot open log file at startup");
-}
-
-
-SharedLogWorkerImpl::~SharedLogWorkerImpl() {
-  std::ostringstream ss_exit;
-  mBg.reset(); // flush the log queue
-  ss_exit << "\nMeehLog file shutdown at: " << MeehLog::localtime_formatted(systemtime_now(), time_formatted);
-  filestream() << ss_exit.str() << std::flush;
-}
-
-
-void SharedLogWorkerImpl::backgroundFileWrite(LogEntry message) {
-  using namespace std;
-  std::ofstream& out(filestream());
-  auto log_time = message.mTimestamp;
-  auto steady_time = std::chrono::steady_clock::now();
-  out << "\n" << MeehLog::localtime_formatted(log_time, date_formatted);
-  out << " " << MeehLog::localtime_formatted(log_time, time_formatted);
-  out << " " << chrono::duration_cast<std::chrono::microseconds>(steady_time - steady_start_time_).count();
-  out << "\t" << message.mMsg << std::flush;
-}
-
-
-void SharedLogWorkerImpl::backgroundExitFatal(FatalMessage fatal_message) {
-  backgroundFileWrite(fatal_message.mMessage);
-  LogEntry flushEntry{"Log flushed successfully to disk \nExiting", MeehLog::internal::systemtime_now()};
-  backgroundFileWrite(flushEntry);
-  std::cerr << "MeehLog exiting after receiving fatal event" << std::endl;
-  std::cerr << "Log file at: [" << log_file_with_path_ << "]\n" << std::endl << std::flush;
-  filestream().close();
-  MeehLog::shutDownLogging(); // only an initialized logger can recieve a fatal message. So shutting down logging now is fine.
-  //exitWithDefaultSignalHandler(fatal_message.mSignalId);
-  perror("MeehLog exited after receiving FATAL trigger. Flush message status: "); // should never reach this point
-}
-
-
-std::string SharedLogWorkerImpl::backgroundChangeLogFile(const std::string& directory) {
-  std::string file_name = createLogFileName(log_prefix_backup_);
-  std::string prospect_log = directory + file_name;
-  std::unique_ptr<std::ofstream> log_stream = createLogFile(prospect_log);
-  if (nullptr == log_stream) {
-    LogEntry error("Unable to change log file. Illegal filename or busy? Unsuccessful log name was:" + prospect_log, MeehLog::internal::systemtime_now());
-    backgroundFileWrite(error);
-    
-    return ""; // no success
-  }
-  
-  std::ostringstream ss_change;
-  ss_change << "\nChanging log file from : " << log_file_with_path_;
-  ss_change << "\nto new location: " << prospect_log << "\n";
-  backgroundFileWrite({ss_change.str().c_str(), MeehLog::internal::systemtime_now()});
-  ss_change.str("");
-  
-  // setting the new log as active
-  std::string old_log = log_file_with_path_;
-  log_file_with_path_ = prospect_log;
-  mOutptr = std::move(log_stream);
-  ss_change << "\nNew log file. The previous log file was at: ";
-  ss_change << old_log;
-  backgroundFileWrite({ss_change.str(), MeehLog::internal::systemtime_now()});
-  return log_file_with_path_;
-}
-
-std::string  SharedLogWorkerImpl::backgroundFileName() {
-  return log_file_with_path_;
-}
-
-
-// Public API implementation
-//
-SharedLogWorker::SharedLogWorker(const std::string& log_prefix, const std::string& log_directory)
-:  pimpl(new SharedLogWorkerImpl(log_prefix, log_directory))
-, logFileWithPath(pimpl->log_file_with_path_) {
-  assert((pimpl != nullptr) && "shouild never happen");
-}
-
-SharedLogWorker::~SharedLogWorker() {
-  pimpl.reset();
-  MeehLog::shutDownLoggingForActiveOnly(this);
-  std::cerr << "\nExiting, log location: " << logFileWithPath << std::endl << std::flush;
-}
-
-void SharedLogWorker::save(const MeehLog::internal::LogEntry& msg) {
-  pimpl->mBg->send(std::bind(&SharedLogWorkerImpl::backgroundFileWrite, pimpl.get(), msg));
-}
-
-void SharedLogWorker::fatal(MeehLog::internal::FatalMessage fatal_message) {
-  pimpl->mBg->send(std::bind(&SharedLogWorkerImpl::backgroundExitFatal, pimpl.get(), fatal_message));
-}
-
-
-#pragma GCC diagnostic push
-#pragma GCC diagnostic ignored "-Wpessimizing-move"
-
-std::future<std::string> SharedLogWorker::changeLogFile(const std::string& log_directory) {
-  MeehLog::Active* bgWorker = pimpl->mBg.get();
-  auto mBgcall =     [this, log_directory]() {return pimpl->backgroundChangeLogFile(log_directory);};
-  auto future_result = MeehLog::spawn_task(mBgcall, bgWorker);
-  return std::move(future_result);
-}
-
-
-std::future<void> SharedLogWorker::genericAsyncCall(std::function<void()> f) {
-  auto bgWorker = pimpl->mBg.get();
-  auto future_result = MeehLog::spawn_task(f, bgWorker);
-  return std::move(future_result);
-}
-
-std::future<std::string> SharedLogWorker::logFileName() {
-  MeehLog::Active* bgWorker = pimpl->mBg.get();
-  auto mBgcall = [&]() {return pimpl->backgroundFileName();};
-  auto future_result = MeehLog::spawn_task(mBgcall , bgWorker);
-  return std::move(future_result);
-}
-
-#pragma GCC diagnostic pop
-
diff --git a/launchers/macosx/I2PLauncher/ObjectiveC/LoggerWorker.hpp b/launchers/macosx/I2PLauncher/ObjectiveC/LoggerWorker.hpp
deleted file mode 100644
index 4db9a18f85611a9f53379081e0445ec078d94a3c..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/ObjectiveC/LoggerWorker.hpp
+++ /dev/null
@@ -1,144 +0,0 @@
-//
-//  LoggerWorker.hpp
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 27/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//  Imported/Refactored from earlier C++ project of Meeh
-//
-
-#ifndef LoggerWorker_hpp
-#define LoggerWorker_hpp
-
-#ifdef __cplusplus
-
-#include <memory>
-#include <thread>
-#include <mutex>
-#include <future>
-#include <string>
-#include <condition_variable>
-#include <functional>
-
-// TODO: Configure the project to avoid such includes.
-#include "../include/sharedqueue.h"
-#include "Logger.h"
-
-struct SharedLogWorkerImpl;
-
-
-namespace MeehLog {
-  typedef std::function<void()> Callback;
-  
-  class Active {
-  private:
-    Active(const Active&);
-    Active& operator=(const Active&);
-    Active();                         // Construction ONLY through factory createActive();
-    void doDone(){mDone = true;}
-    void run();
-    
-    shared_queue<Callback> mMq;
-    std::thread mThd;
-    bool mDone;  // finished flag to be set through msg queue by ~Active
-    
-    
-  public:
-    virtual ~Active();
-    void send(Callback msg_);
-    static std::unique_ptr<Active> createActive(); // Factory: safe construction & thread start
-  };
-  
-  
-  
-  // A straightforward technique to move around packaged_tasks.
-  //  Instances of std::packaged_task are MoveConstructible and MoveAssignable, but
-  //  not CopyConstructible or CopyAssignable. To put them in a std container they need
-  //  to be wrapped and their internals "moved" when tried to be copied.
-  template<typename Moveable>
-  struct MoveOnCopy {
-    mutable Moveable _move_only;
-    
-    explicit MoveOnCopy(Moveable&& m) : _move_only(std::move(m)) {}
-    MoveOnCopy(MoveOnCopy const& t) : _move_only(std::move(t._move_only)) {}
-    MoveOnCopy(MoveOnCopy&& t) : _move_only(std::move(t._move_only)) {}
-    
-    MoveOnCopy& operator=(MoveOnCopy const& other) {
-      _move_only = std::move(other._move_only);
-      return *this;
-    }
-    
-    MoveOnCopy& operator=(MoveOnCopy&& other) {
-      _move_only = std::move(other._move_only);
-      return *this;
-    }
-    
-    void operator()() { _move_only(); }
-    Moveable& get() { return _move_only; }
-    Moveable release() { return std::move(_move_only); }
-  };
-  
-  // Generic helper function to avoid repeating the steps for managing
-  // asynchronous task job (by active object) that returns a future results
-  // could of course be made even more generic if done more in the way of
-  // std::async, ref: http://en.cppreference.com/w/cpp/thread/async
-  //
-  // Example usage:
-  //  std::unique_ptr<Active> bgWorker{Active::createActive()};
-  //  ...
-  //  auto msg_call=[=](){return ("Hello from the Background");};
-  //  auto future_msg = g2::spawn_task(msg_lambda, bgWorker.get());
-  
-  template <typename Func>
-  std::future<typename std::result_of<Func()>::type> spawn_task(Func func, Active* worker) {
-    typedef typename std::result_of<Func()>::type result_type;
-    typedef std::packaged_task<result_type()> task_type;
-    task_type task(std::move(func));
-    std::future<result_type> result = task.get_future();
-    
-    worker->send(MoveOnCopy<task_type>(std::move(task)));
-    return std::move(result);
-  }
-}
-
-class SharedLogWorker {
-public:
-  /**
-   * \param log_prefix is the 'name' of the binary, this give the log name 'LOG-'name'-...
-   * \param log_directory gives the directory to put the log files */
-  SharedLogWorker(const std::string& log_prefix, const std::string& log_directory);
-  virtual ~SharedLogWorker();
-  
-  /// pushes in background thread (asynchronously) input messages to log file
-  void save(const MeehLog::internal::LogEntry& entry);
-  
-  /// Will push a fatal message on the queue, this is the last message to be processed
-  /// this way it's ensured that all existing entries were flushed before 'fatal'
-  /// Will abort the application!
-  void fatal(MeehLog::internal::FatalMessage fatal_message);
-  
-  /// Attempt to change the current log file to another name/location.
-  /// returns filename with full path if successful, else empty string
-  std::future<std::string> changeLogFile(const std::string& log_directory);
-  
-  /// Does an independent action in FIFO order, compared to the normal LOG statements
-  /// Example: auto threadID = [] { std::cout << "thread id: " << std::this_thread::get_id() << std::endl; };
-  ///          auto call = logger.genericAsyncCall(threadID);
-  ///          // this will print out the thread id of the background worker
-  std::future<void> genericAsyncCall(std::function<void()> f);
-  
-  /// Probably only needed for unit-testing or specific log management post logging
-  /// request to get log name is processed in FIFO order just like any other background job.
-  std::future<std::string> logFileName();
-  
-private:
-  std::unique_ptr<SharedLogWorkerImpl> pimpl;
-  const std::string logFileWithPath;
-  
-  SharedLogWorker(const SharedLogWorker&);
-  SharedLogWorker& operator=(const SharedLogWorker&);
-};
-
-#endif // __cplusplus
-
-#endif /* LoggerWorker_hpp */
diff --git a/launchers/macosx/I2PLauncher/ObjectiveC/RouterTask.h b/launchers/macosx/I2PLauncher/ObjectiveC/RouterTask.h
deleted file mode 100644
index 9f215d31ee9d5e4f50b81cef7653aa66bc1ecd12..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/ObjectiveC/RouterTask.h
+++ /dev/null
@@ -1,219 +0,0 @@
-#pragma once
-
-#include <dispatch/dispatch.h>
-#include <memory.h>
-#include <sys/sysctl.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include <Cocoa/Cocoa.h>
-#import <AppKit/AppKit.h>
-
-#ifdef __cplusplus
-#include <vector>
-#include <string>
-
-
-
-const std::vector<NSString*> defaultStartupFlags {
-  @"-Xmx512M",
-  @"-Xms128m",
-  @"-Djava.awt.headless=true",
-  @"-Dwrapper.logfile=/tmp/router.log",
-  @"-Dwrapper.logfile.loglevel=DEBUG",
-  @"-Dwrapper.java.pidfile=/tmp/routerjvm.pid",
-  @"-Dwrapper.console.loglevel=DEBUG"
-};
-
-const std::vector<std::string> defaultFlagsForExtractorJob {
-  "-Xmx512M",
-  "-Xms128m",
-  "-Djava.awt.headless=true"
-};
-
-#endif
-
-
-@class RTaskOptions;
-@interface RTaskOptions : NSObject
-@property (strong) NSString* binPath;
-@property (strong) NSArray<NSString *>* arguments;
-@property (strong) NSString* i2pBaseDir;
-@end
-
-@class I2PRouterTask;
-@interface I2PRouterTask : NSObject
-@property (strong) NSTask* routerTask;
-@property (strong) NSPipe *processPipe;
-@property (atomic) BOOL isRouterRunning;
-@property (atomic) BOOL userRequestedRestart;
-- (instancetype) initWithOptions : (RTaskOptions*) options;
-- (int) execute;
-- (void) requestShutdown;
-- (void) requestRestart;
-- (BOOL) isRunning;
-- (int) getPID;
-- (void)routerStdoutData:(NSNotification *)notification;
-@end
-
-
-@interface IIProcessInfo : NSObject {
-  
-@private
-  int numberOfProcesses;
-  NSMutableArray *processList;
-}
-- (id) init;
-- (int)numberOfProcesses;
-- (void)obtainFreshProcessList;
-- (BOOL)findProcessWithStringInNameOrArguments:(NSString *)procNameToSearch;
-@end
-
-#ifdef __cplusplus
-
-// Inspired by the "ps" util.
-
-inline std::string getArgvOfPid(int pid) {
-  int    mib[3], argmax, nargs, c = 0;
-  size_t    size;
-  char    *procargs, *sp, *np, *cp;
-  int show_args = 1;
-  mib[0] = CTL_KERN;
-  mib[1] = KERN_ARGMAX;
-  
-  size = sizeof(argmax);
-  if (sysctl(mib, 2, &argmax, &size, NULL, 0) == -1) {
-    return std::string("sorry");
-  }
-  
-  /* Allocate space for the arguments. */
-  procargs = (char *)malloc(argmax);
-  if (procargs == NULL) {
-    return std::string("sorry");
-  }
-  /*
-   * Make a sysctl() call to get the raw argument space of the process.
-   * The layout is documented in start.s, which is part of the Csu
-   * project.  In summary, it looks like:
-   *
-   * /---------------\ 0x00000000
-   * :               :
-   * :               :
-   * |---------------|
-   * | argc          |
-   * |---------------|
-   * | arg[0]        |
-   * |---------------|
-   * :               :
-   * :               :
-   * |---------------|
-   * | arg[argc - 1] |
-   * |---------------|
-   * | 0             |
-   * |---------------|
-   * | env[0]        |
-   * |---------------|
-   * :               :
-   * :               :
-   * |---------------|
-   * | env[n]        |
-   * |---------------|
-   * | 0             |
-   * |---------------| <-- Beginning of data returned by sysctl() is here.
-   * | argc          |
-   * |---------------|
-   * | exec_path     |
-   * |:::::::::::::::|
-   * |               |
-   * | String area.  |
-   * |               |
-   * |---------------| <-- Top of stack.
-   * :               :
-   * :               :
-   * \---------------/ 0xffffffff
-   */
-  mib[0] = CTL_KERN;
-  mib[1] = KERN_PROCARGS2;
-  mib[2] = pid;
-  
-  
-  size = (size_t)argmax;
-  if (sysctl(mib, 3, procargs, &size, NULL, 0) == -1) {
-    free(procargs);
-    return std::string("sorry");
-  }
-  
-  memcpy(&nargs, procargs, sizeof(nargs));
-  cp = procargs + sizeof(nargs);
-  
-  /* Skip the saved exec_path. */
-  for (; cp < &procargs[size]; cp++) {
-    if (*cp == '\0') {
-      /* End of exec_path reached. */
-      break;
-    }
-  }
-  if (cp == &procargs[size]) {
-    free(procargs);
-    return std::string("sorry");
-  }
-  
-  /* Skip trailing '\0' characters. */
-  for (; cp < &procargs[size]; cp++) {
-    if (*cp != '\0') {
-      /* Beginning of first argument reached. */
-      break;
-    }
-  }
-  if (cp == &procargs[size]) {
-    free(procargs);
-    return std::string("sorry");
-  }
-  /* Save where the argv[0] string starts. */
-  sp = cp;
-  
-  /*
-   * Iterate through the '\0'-terminated strings and convert '\0' to ' '
-   * until a string is found that has a '=' character in it (or there are
-   * no more strings in procargs).  There is no way to deterministically
-   * know where the command arguments end and the environment strings
-   * start, which is why the '=' character is searched for as a heuristic.
-   */
-  for (np = NULL; c < nargs && cp < &procargs[size]; cp++) {
-    if (*cp == '\0') {
-      c++;
-      if (np != NULL) {
-        /* Convert previous '\0'. */
-        *np = ' ';
-      } else {
-        /* *argv0len = cp - sp; */
-      }
-      /* Note location of current '\0'. */
-      np = cp;
-      
-      if (!show_args) {
-        /*
-         * Don't convert '\0' characters to ' '.
-         * However, we needed to know that the
-         * command name was terminated, which we
-         * now know.
-         */
-        break;
-      }
-    }
-  }
-  
-  /*
-   * sp points to the beginning of the arguments/environment string, and
-   * np should point to the '\0' terminator for the string.
-   */
-  if (np == NULL || np == sp) {
-    /* Empty or unterminated string. */
-    free(procargs);
-    return std::string("sorry");
-  }
-  return std::string(sp);
-}
-
-#endif
diff --git a/launchers/macosx/I2PLauncher/ObjectiveC/RouterTask.mm b/launchers/macosx/I2PLauncher/ObjectiveC/RouterTask.mm
deleted file mode 100644
index 9d2f3e8f0d2dd13fa7e34eb76e943a614046cd1a..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/ObjectiveC/RouterTask.mm
+++ /dev/null
@@ -1,242 +0,0 @@
-#include "RouterTask.h"
-
-#include <dispatch/dispatch.h>
-#include <future>
-#include <stdlib.h>
-
-#ifdef __cplusplus
-// TODO: Configure the project to avoid such includes.
-#include "../include/subprocess.hpp"
-#include "../include/PidWatcher.h"
-
-#import "I2PLauncher-Swift.h"
-#include "AppDelegate.h"
-
-#include <assert.h>
-#include <errno.h>
-#include <stdbool.h>
-#include <sys/sysctl.h>
-#endif
-
-
-#import <AppKit/AppKit.h>
-#import <Foundation/Foundation.h>
-
-@implementation RTaskOptions
-@end
-
-@implementation I2PRouterTask
-
-- (void)routerStdoutData:(NSNotification *)notification
-{
-    NSLog(@"%@", [[NSString alloc] initWithData:[notification.object availableData] encoding:NSUTF8StringEncoding]);
-    [notification.object waitForDataInBackgroundAndNotify];
-}
-
-- (instancetype) initWithOptions : (RTaskOptions*) options
-{
-  self.userRequestedRestart = NO;
-  self.isRouterRunning = NO;
-  self.routerTask = [NSTask new];
-  self.processPipe = [NSPipe new];
-  [self.routerTask setLaunchPath:options.binPath];
-  [self.routerTask setArguments:options.arguments];
-  NSDictionary *envDict = @{
-    @"I2PBASE": options.i2pBaseDir
-  };
-  [self.routerTask setEnvironment: envDict];
-  NSLog(@"Using environment variables: %@", envDict);
-  [self.routerTask setStandardOutput:self.processPipe];
-	[self.routerTask setStandardError:self.processPipe];
-
-  [self.routerTask setTerminationHandler:^(NSTask* task) {
-    // Cleanup
-    NSLog(@"termHandler triggered!");
-    [[[RouterProcessStatus alloc] init] triggerEventWithEn:@"router_stop" details:@"normal shutdown"];
-    [[SBridge sharedInstance] setCurrentRouterInstance:nil];
-    sendUserNotification(APP_IDSTR, @"I2P Router has stopped");
-  }];
-  return self;
-}
-
-- (void) requestShutdown
-{
-    [self.routerTask interrupt];
-}
-
-- (void) requestRestart
-
-{    self.userRequestedRestart = YES;
-    kill([self.routerTask processIdentifier], SIGHUP);
-}
-
-- (BOOL) isRunning
-{
-    return self.routerTask.running;
-}
-
-- (int) execute
-{
-    @try {
-      [self.routerTask launch];
-      self.isRouterRunning = YES;
-      return 1;
-    }
-    @catch (NSException *e)
-	{
-		NSLog(@"Expection occurred %@", [e reason]);
-    self.isRouterRunning = NO;
-    
-    [[[RouterProcessStatus alloc] init] triggerEventWithEn:@"router_exception" details:[e reason]];
-    
-    [[SBridge sharedInstance] setCurrentRouterInstance:nil];
-    sendUserNotification(@"An error occured, can't start the I2P Router", [e reason]);
-    return 0;
-	}
-}
-
-- (int) getPID
-{
-  return [self.routerTask processIdentifier];
-}
-
-@end
-
-typedef struct kinfo_proc kinfo_proc;
-
-@implementation IIProcessInfo
-- (id) init
-{
-  self = [super init];
-  if (self != nil)
-  {
-    numberOfProcesses = -1; // means "not initialized"
-    processList = NULL;
-  }
-  return self;
-}
-
-- (int)numberOfProcesses
-{
-  return numberOfProcesses;
-}
-
-- (void)setNumberOfProcesses:(int)num
-{
-  numberOfProcesses = num;
-}
-
-- (int)getBSDProcessList:(kinfo_proc **)procList
-   withNumberOfProcesses:(size_t *)procCount
-{
-#ifdef __cplusplus
-  int             err;
-  kinfo_proc *    result;
-  bool            done;
-  static const int    name[] = { CTL_KERN, KERN_PROC, KERN_PROC_ALL, 0 };
-  size_t          length;
-  
-  // a valid pointer procList holder should be passed
-  assert( procList != NULL );
-  // But it should not be pre-allocated
-  assert( *procList == NULL );
-  // a valid pointer to procCount should be passed
-  assert( procCount != NULL );
-  
-  *procCount = 0;
-  result = NULL;
-  done = false;
-  
-  do
-  {
-    assert( result == NULL );
-    
-    // Call sysctl with a NULL buffer to get proper length
-    length = 0;
-    err = sysctl((int *)name,(sizeof(name)/sizeof(*name))-1,NULL,&length,NULL,0);
-    if( err == -1 )
-      err = errno;
-    
-    // Now, proper length is optained
-    if( err == 0 )
-    {
-      result = (kinfo_proc *)malloc(length);
-      if( result == NULL )
-        err = ENOMEM;   // not allocated
-    }
-    
-    if( err == 0 )
-    {
-      err = sysctl( (int *)name, (sizeof(name)/sizeof(*name))-1, result, &length, NULL, 0);
-      if( err == -1 )
-        err = errno;
-      
-      if( err == 0 )
-        done = true;
-      else if( err == ENOMEM )
-      {
-        assert( result != NULL );
-        free( result );
-        result = NULL;
-        err = 0;
-      }
-    }
-  }while ( err == 0 && !done );
-  
-  // Clean up and establish post condition
-  if( err != 0 && result != NULL )
-  {
-    free(result);
-    result = NULL;
-  }
-  
-  *procList = result; // will return the result as procList
-  if( err == 0 )
-    *procCount = length / sizeof( kinfo_proc );
-  assert( (err == 0) == (*procList != NULL ) );
-  return err;
-}
-
-- (void)obtainFreshProcessList
-{
-  int i;
-  kinfo_proc *allProcs = 0;
-  size_t numProcs;
-  NSString *procName;
-  
-  int err =  [self getBSDProcessList:&allProcs withNumberOfProcesses:&numProcs];
-  if( err )
-  {
-    numberOfProcesses = -1;
-    processList = NULL;
-    
-    return;
-  }
-  
-  // Construct an array for ( process name, pid, arguments concat'ed )
-  processList = [NSMutableArray arrayWithCapacity:numProcs];
-  for( i = 0; i < numProcs; i++ )
-  {
-    int pid = (int)allProcs[i].kp_proc.p_pid;
-    procName = [NSString stringWithFormat:@"%s, pid %d, args: %s", allProcs[i].kp_proc.p_comm, pid, getArgvOfPid(pid).c_str()];
-    [processList addObject:procName];
-  }
-  
-  [self setNumberOfProcesses:(int)numProcs];
-  free( allProcs );
-#endif
-}
-
-
-- (BOOL)findProcessWithStringInNameOrArguments:(NSString *)procNameToSearch
-{
-  BOOL seenProcessThatMatch = NO;
-  for (NSString* processInfoStr in processList) {
-    if ([processInfoStr containsString:procNameToSearch]) {
-      seenProcessThatMatch = YES;
-      break;
-    }
-  }
-  return seenProcessThatMatch;
-}
-@end
diff --git a/launchers/macosx/I2PLauncher/ObjectiveC/SBridge.h b/launchers/macosx/I2PLauncher/ObjectiveC/SBridge.h
deleted file mode 100644
index ff3344cf055af016370734dc46fa78740edfa9e0..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/ObjectiveC/SBridge.h
+++ /dev/null
@@ -1,64 +0,0 @@
-//
-//  SBridge.h
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 18/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-#import <Foundation/Foundation.h>
-#import <Cocoa/Cocoa.h>
-
-#import "RouterTask.h"
-
-#ifdef __cplusplus
-#include <memory>
-#include <future>
-#include <glob.h>
-#include <string>
-#include <vector>
-// TODO: Configure the project to avoid such includes.
-#include "../include/fn.h"
-
-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
-@property (nonatomic, assign) I2PRouterTask* currentRouterInstance;
-- (void) openUrl:(NSString*)url;
-+ (void) logProxy:(int)level formattedMsg:(NSString*)formattedMsg;
-+ (void) sendUserNotification:(NSString*)title formattedMsg:(NSString*)formattedMsg;
-+ (instancetype)sharedInstance; // this makes it a singleton
-@end
diff --git a/launchers/macosx/I2PLauncher/ObjectiveC/SBridge.mm b/launchers/macosx/I2PLauncher/ObjectiveC/SBridge.mm
deleted file mode 100644
index 678e6a609c29f3f45829015b6f1f5f038bb97ddb..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/ObjectiveC/SBridge.mm
+++ /dev/null
@@ -1,63 +0,0 @@
-//
-//  SBridge.m
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 18/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-#import "SBridge.h"
-
-#ifdef __cplusplus
-#include <functional>
-#include <memory>
-#include <glob.h>
-#include <string>
-#include <list>
-#include <stdlib.h>
-#include <future>
-#include <vector>
-
-#import <AppKit/AppKit.h>
-#import "I2PLauncher-Swift.h"
-#include "LoggerWorker.hpp"
-#include "Logger.h"
-#include "logger_c.h"
-
-#include "AppDelegate.h"
-// TODO: Configure the project to avoid such includes.
-#include "../include/fn.h"
-
-
-@implementation SBridge
-
-// this makes it a singleton
-+ (instancetype)sharedInstance {
-  static SBridge *sharedInstance = nil;
-  static dispatch_once_t onceToken;
-  
-  dispatch_once(&onceToken, ^{
-    sharedInstance = [[SBridge alloc] init];
-  });
-  return sharedInstance;
-}
-
-+ (void) sendUserNotification:(NSString*)title formattedMsg:(NSString*)formattedMsg
-{
-  sendUserNotification(title, formattedMsg);
-}
-
-- (void) openUrl:(NSString*)url
-{
-  osx::openUrl(url);
-}
-
-+ (void) logProxy:(int)level formattedMsg:(NSString*)formattedMsg
-{
-  MLog(level, formattedMsg);
-}
-
-@end
-
-
-#endif
diff --git a/launchers/macosx/I2PLauncher/ObjectiveC/logger_c.h b/launchers/macosx/I2PLauncher/ObjectiveC/logger_c.h
deleted file mode 100644
index 102204b38f18bde1584459a1ecf24724739d9a32..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/ObjectiveC/logger_c.h
+++ /dev/null
@@ -1,88 +0,0 @@
-//
-//  logger_c.h
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 30/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-#ifndef logger_c_h
-#define logger_c_h
-
-#include "Logger.h"
-#include "LoggerWorker.hpp"
-
-/*
-void genericLogger(int loglevel, va_list params) {
-#ifdef __cplusplus
-  const char * paramArray[10];
-  int numParams = 0;
-  
-  NSString* arg = nil;
-  while ((arg = va_arg(params, NSString *))) {
-    paramArray[numParams++] = [arg cStringUsingEncoding:[NSString defaultCStringEncoding]];
-  }
-  
-  switch (loglevel) {
-    case 0:
-      MLOGF(ANNOYING) << params;
-      break;
-    case 1:
-      MLOGF(DEBUG) << params;
-      break;
-    case 2:
-      MLOGF(INFO) << params;
-      break;
-    case 3:
-      MLOGF(WARN) << params;
-      break;
-    default:
-      assert(false);
-  }
-#endif
-}
- */
-
-inline void MLog(int loglevel, NSString* format, ...)
-{
-#ifdef __cplusplus
-  
-  va_list vargs;
-  va_start(vargs, format);
-  NSString* formattedMessage = [[NSString alloc] initWithFormat:format arguments:vargs];
-  va_end(vargs);
-  
-  NSString* message = formattedMessage;
-  
-  switch (loglevel) {
-    case 0:
-      MLOG(ANNOYING) << [message UTF8String];
-      break;
-    case 1:
-      MLOG(DEBUG) << [message UTF8String];
-      break;
-    case 2:
-      MLOG(INFO) << [message UTF8String];
-      break;
-    case 3:
-      MLOG(WARN) << [message UTF8String];
-      break;
-    case 4:
-      MLOG(ERROR) << [message UTF8String];
-      break;
-    default:
-#if DEBUG
-      assert(false);
-#else
-      return;
-#endif
-  }
-  
-#endif
-}
-
-
-
-#define MMLog(format_string,...) ((MLog(1, [NSString stringWithFormat:format_string,##__VA_ARGS__])))
-
-#endif /* logger_c_h */
diff --git a/launchers/macosx/I2PLauncher/Resources/Preferences.storyboard b/launchers/macosx/I2PLauncher/Resources/Preferences.storyboard
deleted file mode 100644
index 49de4db2e22320451be83a3db9e4cf6872e4938c..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Resources/Preferences.storyboard
+++ /dev/null
@@ -1,388 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<document type="com.apple.InterfaceBuilder3.Cocoa.Storyboard.XIB" version="3.0" toolsVersion="14460.31" targetRuntime="MacOSX.Cocoa" propertyAccessControl="none" useAutolayout="YES" initialViewController="E2c-ib-a9d">
-    <dependencies>
-        <deployment identifier="macosx"/>
-        <plugIn identifier="com.apple.InterfaceBuilder.CocoaPlugin" version="14460.31"/>
-        <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
-    </dependencies>
-    <scenes>
-        <!--Window Controller-->
-        <scene sceneID="2xO-NO-0Hd">
-            <objects>
-                <windowController storyboardIdentifier="Preferences" id="E2c-ib-a9d" customClass="PreferencesWindowController" customModule="I2PLauncher" customModuleProvider="target" sceneMemberID="viewController">
-                    <window key="window" title="Window" allowsToolTipsWhenApplicationIsInactive="NO" autorecalculatesKeyViewLoop="NO" releasedWhenClosed="NO" visibleAtLaunch="NO" frameAutosaveName="" animationBehavior="default" id="7sM-0n-LvU">
-                        <windowStyleMask key="styleMask" titled="YES" closable="YES" miniaturizable="YES"/>
-                        <windowPositionMask key="initialPositionMask" leftStrut="YES" rightStrut="YES" topStrut="YES" bottomStrut="YES"/>
-                        <rect key="contentRect" x="294" y="362" width="480" height="270"/>
-                        <rect key="screenRect" x="0.0" y="0.0" width="1920" height="1177"/>
-                        <connections>
-                            <outlet property="delegate" destination="E2c-ib-a9d" id="0bv-to-0T8"/>
-                        </connections>
-                    </window>
-                    <connections>
-                        <segue destination="Gn4-1Z-ZmR" kind="relationship" relationship="window.shadowedContentViewController" id="awB-ye-0WY"/>
-                    </connections>
-                </windowController>
-                <customObject id="BZB-oK-A8Y" userLabel="First Responder" customClass="NSResponder" sceneMemberID="firstResponder"/>
-            </objects>
-            <point key="canvasLocation" x="-2004" y="208"/>
-        </scene>
-        <!--Tab View Controller-->
-        <scene sceneID="cDU-zb-AEX">
-            <objects>
-                <tabViewController selectedTabViewItemIndex="2" tabStyle="toolbar" id="Gn4-1Z-ZmR" sceneMemberID="viewController">
-                    <tabViewItems>
-                        <tabViewItem identifier="" image="NSInfo" id="IDv-FU-QPH"/>
-                        <tabViewItem identifier="" image="NSUser" id="zLE-4e-HMO"/>
-                        <tabViewItem image="NSAdvanced" id="1E7-3R-0EF"/>
-                    </tabViewItems>
-                    <viewControllerTransitionOptions key="transitionOptions" allowUserInteraction="YES"/>
-                    <tabView key="tabView" type="noTabsNoBorder" id="MwI-11-flE">
-                        <rect key="frame" x="0.0" y="0.0" width="450" height="300"/>
-                        <autoresizingMask key="autoresizingMask"/>
-                        <font key="font" metaFont="message"/>
-                        <connections>
-                            <outlet property="delegate" destination="Gn4-1Z-ZmR" id="Sqn-qQ-We5"/>
-                        </connections>
-                    </tabView>
-                    <connections>
-                        <outlet property="tabView" destination="MwI-11-flE" id="dDk-kJ-uqy"/>
-                        <segue destination="Ikw-G1-sbk" kind="relationship" relationship="tabItems" id="4gr-ZN-WkU"/>
-                        <segue destination="ZrJ-Ig-h1D" kind="relationship" relationship="tabItems" id="BRO-ke-swp"/>
-                        <segue destination="mVJ-sm-WjL" kind="relationship" relationship="tabItems" id="ksS-qq-FNs"/>
-                    </connections>
-                </tabViewController>
-                <customObject id="H0i-51-VWT" userLabel="First Responder" customClass="NSResponder" sceneMemberID="firstResponder"/>
-            </objects>
-            <point key="canvasLocation" x="-1263" y="201"/>
-        </scene>
-        <!--Launcher-->
-        <scene sceneID="aj7-2h-9Zl">
-            <objects>
-                <viewController title="Launcher" id="Ikw-G1-sbk" customClass="PreferencesViewController" customModule="I2PLauncher" customModuleProvider="target" sceneMemberID="viewController">
-                    <view key="view" id="oyR-x0-o8B">
-                        <rect key="frame" x="0.0" y="0.0" width="361" height="242"/>
-                        <autoresizingMask key="autoresizingMask"/>
-                        <subviews>
-                            <button verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="aAH-4e-tuf">
-                                <rect key="frame" x="18" y="198" width="325" height="26"/>
-                                <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                <buttonCell key="cell" type="check" title="Start the I2P Launcher at User login (Mac startup)" bezelStyle="regularSquare" imagePosition="left" inset="2" id="EOY-1C-aqa">
-                                    <behavior key="behavior" changeContents="YES" doesNotDimImage="YES" lightByContents="YES"/>
-                                    <font key="font" metaFont="system"/>
-                                </buttonCell>
-                                <connections>
-                                    <action selector="checkboxStartLauncherOnOSXStartupClicked:" target="Ikw-G1-sbk" id="rpo-MV-F0V"/>
-                                </connections>
-                            </button>
-                            <box fixedFrame="YES" boxType="custom" cornerRadius="4" title="Box" translatesAutoresizingMaskIntoConstraints="NO" id="KlH-NM-u60">
-                                <rect key="frame" x="20" y="66" width="321" height="86"/>
-                                <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                <view key="contentView" ambiguous="YES" id="UL7-aj-Mxj">
-                                    <rect key="frame" x="1" y="1" width="319" height="84"/>
-                                    <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
-                                    <subviews>
-                                        <textField horizontalHuggingPriority="251" verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="mgK-Va-AeP">
-                                            <rect key="frame" x="5" y="52" width="83" height="25"/>
-                                            <autoresizingMask key="autoresizingMask"/>
-                                            <textFieldCell key="cell" lineBreakMode="clipping" title="Show as:" id="19Z-jV-gnQ">
-                                                <font key="font" usesAppearanceFont="YES"/>
-                                                <color key="textColor" name="labelColor" catalog="System" colorSpace="catalog"/>
-                                                <color key="backgroundColor" name="textBackgroundColor" catalog="System" colorSpace="catalog"/>
-                                            </textFieldCell>
-                                        </textField>
-                                        <button verticalHuggingPriority="750" ambiguous="YES" translatesAutoresizingMaskIntoConstraints="NO" id="Edq-cq-ZrT">
-                                            <rect key="frame" x="6" y="27" width="83" height="18"/>
-                                            <buttonCell key="cell" type="radio" title="Dock Icon" bezelStyle="regularSquare" imagePosition="left" alignment="left" inset="2" id="ZTf-wy-Wod">
-                                                <behavior key="behavior" changeContents="YES" doesNotDimImage="YES" lightByContents="YES"/>
-                                                <font key="font" metaFont="system"/>
-                                            </buttonCell>
-                                            <connections>
-                                                <action selector="radioDockIconOnlySelected:" target="Ikw-G1-sbk" id="30f-en-hWz"/>
-                                            </connections>
-                                        </button>
-                                        <button verticalHuggingPriority="750" ambiguous="YES" translatesAutoresizingMaskIntoConstraints="NO" id="Y74-ti-gJ4">
-                                            <rect key="frame" x="238" y="27" width="51" height="18"/>
-                                            <buttonCell key="cell" type="radio" title="Both" bezelStyle="regularSquare" imagePosition="left" alignment="left" inset="2" id="TbR-qb-p7G">
-                                                <behavior key="behavior" changeContents="YES" doesNotDimImage="YES" lightByContents="YES"/>
-                                                <font key="font" metaFont="system"/>
-                                            </buttonCell>
-                                            <connections>
-                                                <action selector="radioBothIconSelected:" target="Ikw-G1-sbk" id="M8u-jZ-0ub"/>
-                                            </connections>
-                                        </button>
-                                        <button verticalHuggingPriority="750" ambiguous="YES" translatesAutoresizingMaskIntoConstraints="NO" id="hWQ-Fn-Au7">
-                                            <rect key="frame" x="107" y="27" width="105" height="18"/>
-                                            <buttonCell key="cell" type="radio" title="Menubar Icon" bezelStyle="regularSquare" imagePosition="left" alignment="left" inset="2" id="FSa-BS-LVr">
-                                                <behavior key="behavior" changeContents="YES" doesNotDimImage="YES" lightByContents="YES"/>
-                                                <font key="font" metaFont="system"/>
-                                            </buttonCell>
-                                            <connections>
-                                                <action selector="radioMenubarOnlySelected:" target="Ikw-G1-sbk" id="X24-j5-9sA"/>
-                                            </connections>
-                                        </button>
-                                    </subviews>
-                                    <constraints>
-                                        <constraint firstItem="Edq-cq-ZrT" firstAttribute="width" secondItem="Y74-ti-gJ4" secondAttribute="width" id="I3w-l3-2ZW"/>
-                                        <constraint firstItem="Edq-cq-ZrT" firstAttribute="width" secondItem="hWQ-Fn-Au7" secondAttribute="width" id="d1N-dE-tGj"/>
-                                        <constraint firstItem="Edq-cq-ZrT" firstAttribute="width" secondItem="Y74-ti-gJ4" secondAttribute="height" multiplier="5:1" id="dv4-dW-3FO"/>
-                                    </constraints>
-                                </view>
-                            </box>
-                            <button verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="XPH-xk-vMg">
-                                <rect key="frame" x="18" y="173" width="313" height="23"/>
-                                <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                <buttonCell key="cell" type="check" title="Start Firefox with a I2P enabled profile at launch" bezelStyle="regularSquare" imagePosition="left" state="on" inset="2" id="i7v-mQ-d1Y">
-                                    <behavior key="behavior" changeContents="YES" doesNotDimImage="YES" lightByContents="YES"/>
-                                    <font key="font" metaFont="system"/>
-                                </buttonCell>
-                                <connections>
-                                    <action selector="checkboxStartFirefoxAlsoAtLaunchClicked:" target="Ikw-G1-sbk" id="8L9-vJ-GyU"/>
-                                </connections>
-                            </button>
-                        </subviews>
-                    </view>
-                    <connections>
-                        <outlet property="checkboxStartFirefoxAlso" destination="XPH-xk-vMg" id="gzR-kC-XRa"/>
-                        <outlet property="checkboxStartWithOSX" destination="aAH-4e-tuf" id="Lui-vl-1cg"/>
-                        <outlet property="radioBothIcon" destination="Y74-ti-gJ4" id="tFQ-lh-RT8"/>
-                        <outlet property="radioDockIcon" destination="Edq-cq-ZrT" id="BQ8-gt-vhx"/>
-                        <outlet property="radioMenubarIcon" destination="hWQ-Fn-Au7" id="8p5-9H-RcJ"/>
-                    </connections>
-                </viewController>
-                <customObject id="6YO-uB-NC9" userLabel="First Responder" customClass="NSResponder" sceneMemberID="firstResponder"/>
-            </objects>
-            <point key="canvasLocation" x="-448.5" y="-209"/>
-        </scene>
-        <!--Router-->
-        <scene sceneID="D7p-Ep-rhA">
-            <objects>
-                <viewController title="Router" id="ZrJ-Ig-h1D" customClass="PreferencesViewController" customModule="I2PLauncher" customModuleProvider="target" sceneMemberID="viewController">
-                    <view key="view" id="ueb-yj-LIx">
-                        <rect key="frame" x="0.0" y="0.0" width="319" height="132"/>
-                        <autoresizingMask key="autoresizingMask"/>
-                        <subviews>
-                            <button verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="bWG-1q-47t">
-                                <rect key="frame" x="18" y="96" width="292" height="18"/>
-                                <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                <buttonCell key="cell" type="check" title="Start the router when the launcher is started" bezelStyle="regularSquare" imagePosition="left" state="on" inset="2" id="8aU-yf-Lzp">
-                                    <behavior key="behavior" changeContents="YES" doesNotDimImage="YES" lightByContents="YES"/>
-                                    <font key="font" metaFont="system"/>
-                                </buttonCell>
-                                <connections>
-                                    <action selector="checkboxStartRouterWithLauncherClicked:" target="ZrJ-Ig-h1D" id="uEH-nn-EuL"/>
-                                </connections>
-                            </button>
-                            <button verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="4Ii-hB-9X6">
-                                <rect key="frame" x="18" y="59" width="283" height="24"/>
-                                <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                <buttonCell key="cell" type="check" title="Stop the router when the launcher is exited" bezelStyle="regularSquare" imagePosition="left" state="on" inset="2" id="TgB-Sz-u2E">
-                                    <behavior key="behavior" changeContents="YES" doesNotDimImage="YES" lightByContents="YES"/>
-                                    <font key="font" metaFont="system"/>
-                                </buttonCell>
-                                <connections>
-                                    <action selector="checkboxStopRouterWithLauncherClicked:" target="ZrJ-Ig-h1D" id="IdO-17-off"/>
-                                </connections>
-                            </button>
-                            <button verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="1k4-dg-OqV">
-                                <rect key="frame" x="14" y="13" width="159" height="32"/>
-                                <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                <buttonCell key="cell" type="push" title="Reset configuration" bezelStyle="rounded" alignment="center" enabled="NO" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="y6O-Pw-sua">
-                                    <behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
-                                    <font key="font" metaFont="system"/>
-                                </buttonCell>
-                                <connections>
-                                    <action selector="buttonResetRouterConfigClicked:" target="ZrJ-Ig-h1D" id="hX2-JI-CrK"/>
-                                </connections>
-                            </button>
-                        </subviews>
-                    </view>
-                    <connections>
-                        <outlet property="buttonResetRouterConfig" destination="1k4-dg-OqV" id="eI9-Qx-foO"/>
-                        <outlet property="checkboxStartWithLauncher" destination="bWG-1q-47t" id="s1f-zJ-9CW"/>
-                        <outlet property="checkboxStopWithLauncher" destination="4Ii-hB-9X6" id="SUY-Nn-EkH"/>
-                    </connections>
-                </viewController>
-                <customObject id="HfJ-oO-OiU" userLabel="First Responder" customClass="NSResponder" sceneMemberID="firstResponder"/>
-            </objects>
-            <point key="canvasLocation" x="-455" y="-487"/>
-        </scene>
-        <!--Advanced-->
-        <scene sceneID="CCY-VE-I04">
-            <objects>
-                <viewController title="Advanced" id="mVJ-sm-WjL" customClass="PreferencesViewController" customModule="I2PLauncher" customModuleProvider="target" sceneMemberID="viewController">
-                    <view key="view" id="za6-Zc-Mi0">
-                        <rect key="frame" x="0.0" y="0.0" width="601" height="391"/>
-                        <autoresizingMask key="autoresizingMask"/>
-                        <subviews>
-                            <button verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="SSS-Fz-fYY">
-                                <rect key="frame" x="18" y="345" width="257" height="28"/>
-                                <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                <buttonCell key="cell" type="check" title="Yes, I want to edit advanced settings" bezelStyle="regularSquare" imagePosition="left" inset="2" id="UzU-4G-MLw">
-                                    <behavior key="behavior" changeContents="YES" doesNotDimImage="YES" lightByContents="YES"/>
-                                    <font key="font" metaFont="system"/>
-                                </buttonCell>
-                                <connections>
-                                    <action selector="checkboxEnableAdvancedPreferencesClicked:" target="mVJ-sm-WjL" id="6TH-cr-HJa"/>
-                                </connections>
-                            </button>
-                            <textField horizontalHuggingPriority="251" verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="jMA-gl-Wbw">
-                                <rect key="frame" x="264" y="330" width="319" height="51"/>
-                                <autoresizingMask key="autoresizingMask"/>
-                                <textFieldCell key="cell" id="ygn-Tg-kwS">
-                                    <font key="font" metaFont="system"/>
-                                    <string key="title">Note: Advanced settings are editable via the defaults command line tool. Features that are not ready are disabled in preferences.</string>
-                                    <color key="textColor" name="labelColor" catalog="System" colorSpace="catalog"/>
-                                    <color key="backgroundColor" name="textBackgroundColor" catalog="System" colorSpace="catalog"/>
-                                </textFieldCell>
-                            </textField>
-                            <scrollView identifier="ScollViewTableView" fixedFrame="YES" autohidesScrollers="YES" horizontalLineScroll="19" horizontalPageScroll="10" verticalLineScroll="19" verticalPageScroll="10" usesPredominantAxisScrolling="NO" translatesAutoresizingMaskIntoConstraints="NO" id="HtO-MW-DI8">
-                                <rect key="frame" x="20" y="11" width="561" height="311"/>
-                                <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                <clipView key="contentView" ambiguous="YES" id="D8u-eX-bBu">
-                                    <rect key="frame" x="1" y="0.0" width="559" height="310"/>
-                                    <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
-                                    <subviews>
-                                        <tableView identifier="AdvancedView" verticalHuggingPriority="750" allowsExpansionToolTips="YES" columnAutoresizingStyle="lastColumnOnly" alternatingRowBackgroundColors="YES" columnSelection="YES" multipleSelection="NO" autosaveColumns="NO" rowSizeStyle="automatic" headerView="M6Y-Yi-YWr" viewBased="YES" id="lzO-OC-oiQ" customClass="AdvancedTableView" customModule="I2PLauncher" customModuleProvider="target">
-                                            <rect key="frame" x="0.0" y="0.0" width="645" height="285"/>
-                                            <autoresizingMask key="autoresizingMask"/>
-                                            <size key="intercellSpacing" width="3" height="2"/>
-                                            <color key="backgroundColor" name="controlBackgroundColor" catalog="System" colorSpace="catalog"/>
-                                            <color key="gridColor" name="gridColor" catalog="System" colorSpace="catalog"/>
-                                            <tableColumns>
-                                                <tableColumn identifier="KeyColumnID" editable="NO" width="116" minWidth="40" maxWidth="1000" id="3Hj-6J-5ww">
-                                                    <tableHeaderCell key="headerCell" lineBreakMode="truncatingTail" borderStyle="border" title="Key">
-                                                        <font key="font" metaFont="smallSystem"/>
-                                                        <color key="textColor" name="headerTextColor" catalog="System" colorSpace="catalog"/>
-                                                        <color key="backgroundColor" name="headerColor" catalog="System" colorSpace="catalog"/>
-                                                    </tableHeaderCell>
-                                                    <textFieldCell key="dataCell" lineBreakMode="truncatingTail" selectable="YES" editable="YES" title="Text Cell" id="d5O-BO-cq8">
-                                                        <font key="font" metaFont="system"/>
-                                                        <color key="textColor" name="controlTextColor" catalog="System" colorSpace="catalog"/>
-                                                        <color key="backgroundColor" name="controlBackgroundColor" catalog="System" colorSpace="catalog"/>
-                                                    </textFieldCell>
-                                                    <tableColumnResizingMask key="resizingMask" resizeWithTable="YES" userResizable="YES"/>
-                                                    <prototypeCellViews>
-                                                        <tableCellView id="8Z2-cm-fKP">
-                                                            <rect key="frame" x="1" y="1" width="116" height="17"/>
-                                                            <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
-                                                            <subviews>
-                                                                <textField verticalHuggingPriority="750" horizontalCompressionResistancePriority="250" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="s7j-Qx-PVz">
-                                                                    <rect key="frame" x="0.0" y="0.0" width="116" height="17"/>
-                                                                    <autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMinY="YES"/>
-                                                                    <textFieldCell key="cell" lineBreakMode="truncatingTail" sendsActionOnEndEditing="YES" title="Table View Cell" id="tMT-gR-wu2">
-                                                                        <font key="font" metaFont="system"/>
-                                                                        <color key="textColor" name="controlTextColor" catalog="System" colorSpace="catalog"/>
-                                                                        <color key="backgroundColor" name="controlColor" catalog="System" colorSpace="catalog"/>
-                                                                    </textFieldCell>
-                                                                </textField>
-                                                            </subviews>
-                                                            <connections>
-                                                                <outlet property="textField" destination="s7j-Qx-PVz" id="Mt0-Gz-VEn"/>
-                                                            </connections>
-                                                        </tableCellView>
-                                                    </prototypeCellViews>
-                                                </tableColumn>
-                                                <tableColumn identifier="DefaultColumnID" editable="NO" width="120" minWidth="40" maxWidth="1000" id="xna-T0-L5h">
-                                                    <tableHeaderCell key="headerCell" lineBreakMode="truncatingTail" borderStyle="border" title="Default Value">
-                                                        <font key="font" metaFont="smallSystem"/>
-                                                        <color key="textColor" name="headerTextColor" catalog="System" colorSpace="catalog"/>
-                                                        <color key="backgroundColor" name="headerColor" catalog="System" colorSpace="catalog"/>
-                                                    </tableHeaderCell>
-                                                    <textFieldCell key="dataCell" lineBreakMode="truncatingTail" selectable="YES" editable="YES" title="Text Cell" id="MUm-Xs-FfY">
-                                                        <font key="font" metaFont="system"/>
-                                                        <color key="textColor" name="controlTextColor" catalog="System" colorSpace="catalog"/>
-                                                        <color key="backgroundColor" name="controlBackgroundColor" catalog="System" colorSpace="catalog"/>
-                                                    </textFieldCell>
-                                                    <tableColumnResizingMask key="resizingMask" resizeWithTable="YES" userResizable="YES"/>
-                                                    <prototypeCellViews>
-                                                        <tableCellView id="b5W-zl-l9T">
-                                                            <rect key="frame" x="120" y="1" width="120" height="17"/>
-                                                            <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
-                                                            <subviews>
-                                                                <textField verticalHuggingPriority="750" horizontalCompressionResistancePriority="250" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="K1c-BK-Dzb">
-                                                                    <rect key="frame" x="0.0" y="0.0" width="120" height="17"/>
-                                                                    <autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMinY="YES"/>
-                                                                    <textFieldCell key="cell" lineBreakMode="truncatingTail" sendsActionOnEndEditing="YES" title="Table View Cell" id="zRJ-Jw-vJZ">
-                                                                        <font key="font" metaFont="system"/>
-                                                                        <color key="textColor" name="controlTextColor" catalog="System" colorSpace="catalog"/>
-                                                                        <color key="backgroundColor" name="controlColor" catalog="System" colorSpace="catalog"/>
-                                                                    </textFieldCell>
-                                                                </textField>
-                                                            </subviews>
-                                                            <connections>
-                                                                <outlet property="textField" destination="K1c-BK-Dzb" id="824-qp-OmE"/>
-                                                            </connections>
-                                                        </tableCellView>
-                                                    </prototypeCellViews>
-                                                </tableColumn>
-                                                <tableColumn identifier="ValueColumnID" width="400" minWidth="10" maxWidth="3.4028234663852886e+38" id="hjb-YH-EoM">
-                                                    <tableHeaderCell key="headerCell" lineBreakMode="truncatingTail" borderStyle="border" alignment="left" title="Selected Value">
-                                                        <font key="font" metaFont="smallSystem"/>
-                                                        <color key="textColor" name="headerTextColor" catalog="System" colorSpace="catalog"/>
-                                                        <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
-                                                    </tableHeaderCell>
-                                                    <textFieldCell key="dataCell" lineBreakMode="truncatingTail" selectable="YES" editable="YES" alignment="left" title="Text Cell" id="adF-18-fTe">
-                                                        <font key="font" metaFont="system"/>
-                                                        <color key="textColor" name="controlTextColor" catalog="System" colorSpace="catalog"/>
-                                                        <color key="backgroundColor" name="controlBackgroundColor" catalog="System" colorSpace="catalog"/>
-                                                    </textFieldCell>
-                                                    <tableColumnResizingMask key="resizingMask" resizeWithTable="YES" userResizable="YES"/>
-                                                    <prototypeCellViews>
-                                                        <tableCellView id="zRg-yl-f2l">
-                                                            <rect key="frame" x="243" y="1" width="400" height="17"/>
-                                                            <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
-                                                            <subviews>
-                                                                <textField verticalHuggingPriority="750" horizontalCompressionResistancePriority="250" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="2ro-Gm-4DU">
-                                                                    <rect key="frame" x="0.0" y="0.0" width="400" height="17"/>
-                                                                    <autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMinY="YES"/>
-                                                                    <textFieldCell key="cell" lineBreakMode="truncatingTail" selectable="YES" editable="YES" sendsActionOnEndEditing="YES" title="Table View Cell" usesSingleLineMode="YES" id="Sj7-Se-KMC">
-                                                                        <font key="font" metaFont="system"/>
-                                                                        <color key="textColor" name="controlTextColor" catalog="System" colorSpace="catalog"/>
-                                                                        <color key="backgroundColor" name="controlColor" catalog="System" colorSpace="catalog"/>
-                                                                    </textFieldCell>
-                                                                    <connections>
-                                                                        <action selector="onEnterInTextField:" target="mVJ-sm-WjL" id="4y0-HJ-teb"/>
-                                                                    </connections>
-                                                                </textField>
-                                                            </subviews>
-                                                            <connections>
-                                                                <outlet property="textField" destination="2ro-Gm-4DU" id="bXs-LL-3SR"/>
-                                                            </connections>
-                                                        </tableCellView>
-                                                    </prototypeCellViews>
-                                                </tableColumn>
-                                            </tableColumns>
-                                        </tableView>
-                                    </subviews>
-                                </clipView>
-                                <scroller key="horizontalScroller" wantsLayer="YES" verticalHuggingPriority="750" horizontal="YES" id="Cnd-ra-6V7">
-                                    <rect key="frame" x="1" y="294" width="559" height="16"/>
-                                    <autoresizingMask key="autoresizingMask"/>
-                                </scroller>
-                                <scroller key="verticalScroller" hidden="YES" wantsLayer="YES" verticalHuggingPriority="750" horizontal="NO" id="Nnf-g8-3wh">
-                                    <rect key="frame" x="224" y="17" width="15" height="102"/>
-                                    <autoresizingMask key="autoresizingMask"/>
-                                </scroller>
-                                <tableHeaderView key="headerView" id="M6Y-Yi-YWr">
-                                    <rect key="frame" x="0.0" y="0.0" width="645" height="25"/>
-                                    <autoresizingMask key="autoresizingMask"/>
-                                </tableHeaderView>
-                            </scrollView>
-                        </subviews>
-                    </view>
-                    <connections>
-                        <outlet property="advPrefTableView" destination="lzO-OC-oiQ" id="VfI-ro-Bq5"/>
-                    </connections>
-                </viewController>
-                <customObject id="ASm-AK-p0y" userLabel="First Responder" customClass="NSResponder" sceneMemberID="firstResponder"/>
-            </objects>
-            <point key="canvasLocation" x="-397.5" y="254.5"/>
-        </scene>
-    </scenes>
-    <resources>
-        <image name="NSAdvanced" width="128" height="128"/>
-        <image name="NSInfo" width="128" height="128"/>
-        <image name="NSUser" width="128" height="128"/>
-    </resources>
-</document>
diff --git a/launchers/macosx/I2PLauncher/Resources/RouterServices.plist b/launchers/macosx/I2PLauncher/Resources/RouterServices.plist
deleted file mode 100644
index 56482cadf5bba61800470d5a50e2050b046dbea4..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Resources/RouterServices.plist
+++ /dev/null
@@ -1,12 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
-<plist version="1.0">
-<dict>
-	<key>services</key>
-	<array>
-		<string>I2PRouterService</string>
-		<string>HttpTunnelService</string>
-		<string>IrcTunnelService</string>
-	</array>
-</dict>
-</plist>
diff --git a/launchers/macosx/I2PLauncher/Resources/Storyboard.storyboard b/launchers/macosx/I2PLauncher/Resources/Storyboard.storyboard
deleted file mode 100644
index e86fbfa1bbcea44e875ef2de6b7ed045e746188e..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/Resources/Storyboard.storyboard
+++ /dev/null
@@ -1,188 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<document type="com.apple.InterfaceBuilder3.Cocoa.Storyboard.XIB" version="3.0" toolsVersion="14460.31" targetRuntime="MacOSX.Cocoa" propertyAccessControl="none" useAutolayout="YES">
-    <dependencies>
-        <deployment identifier="macosx"/>
-        <plugIn identifier="com.apple.InterfaceBuilder.CocoaPlugin" version="14460.31"/>
-        <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
-    </dependencies>
-    <scenes>
-        <!--PopoverController-->
-        <scene sceneID="4eF-i8-6L0">
-            <objects>
-                <viewController identifier="PopoverView" storyboardIdentifier="PopoverView" id="Ii7-Rb-Ls8" userLabel="PopoverController" customClass="PopoverViewController" customModule="I2PLauncher" customModuleProvider="target" sceneMemberID="viewController">
-                    <tabView key="view" drawsBackground="NO" allowsTruncatedLabels="NO" initialItem="Fle-u6-lgB" id="dmf-Go-6qY">
-                        <rect key="frame" x="0.0" y="0.0" width="450" height="333"/>
-                        <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                        <font key="font" metaFont="system"/>
-                        <tabViewItems>
-                            <tabViewItem label="Router Status &amp; Control" identifier="" id="Fle-u6-lgB">
-                                <view key="view" identifier="routerStatusTabView" canDrawConcurrently="YES" id="xXg-Bt-RWR" customClass="RouterStatusView" customModule="I2PLauncher" customModuleProvider="target">
-                                    <rect key="frame" x="10" y="33" width="430" height="287"/>
-                                    <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
-                                    <subviews>
-                                        <box fixedFrame="YES" boxType="secondary" title="Router information and status" translatesAutoresizingMaskIntoConstraints="NO" id="e8C-qI-SCp">
-                                            <rect key="frame" x="3" y="49" width="285" height="231"/>
-                                            <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                            <view key="contentView" id="zBB-wE-VXr">
-                                                <rect key="frame" x="3" y="3" width="279" height="213"/>
-                                                <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
-                                                <subviews>
-                                                    <textField identifier="RouterStatusLabel" horizontalHuggingPriority="251" verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="0Eo-re-5WK" userLabel="RouterStatusLabel">
-                                                        <rect key="frame" x="6" y="189" width="245" height="17"/>
-                                                        <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                                        <textFieldCell key="cell" scrollable="YES" lineBreakMode="clipping" sendsActionOnEndEditing="YES" title="Router status: Unknown" id="m7V-Se-tnf">
-                                                            <font key="font" metaFont="system"/>
-                                                            <color key="textColor" name="labelColor" catalog="System" colorSpace="catalog"/>
-                                                            <color key="backgroundColor" name="controlColor" catalog="System" colorSpace="catalog"/>
-                                                        </textFieldCell>
-                                                    </textField>
-                                                    <textField identifier="RouterVersionLabel" horizontalHuggingPriority="251" verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="sGy-NV-gmH" userLabel="RouterVersionLabel">
-                                                        <rect key="frame" x="6" y="170" width="245" height="17"/>
-                                                        <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                                        <textFieldCell key="cell" scrollable="YES" lineBreakMode="clipping" sendsActionOnEndEditing="YES" title="Router version: Unknown" id="Mda-Os-8O9">
-                                                            <font key="font" metaFont="system"/>
-                                                            <color key="textColor" name="labelColor" catalog="System" colorSpace="catalog"/>
-                                                            <color key="backgroundColor" name="controlColor" catalog="System" colorSpace="catalog"/>
-                                                        </textFieldCell>
-                                                    </textField>
-                                                    <textField identifier="RouterStartedByLabel" horizontalHuggingPriority="251" verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="tgG-IT-Ojg" userLabel="RouterStartedByLabel">
-                                                        <rect key="frame" x="6" y="151" width="245" height="17"/>
-                                                        <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                                        <textFieldCell key="cell" scrollable="YES" lineBreakMode="clipping" sendsActionOnEndEditing="YES" title="Router started by launcher? No" id="WBg-nH-kwu">
-                                                            <font key="font" metaFont="system"/>
-                                                            <color key="textColor" name="labelColor" catalog="System" colorSpace="catalog"/>
-                                                            <color key="backgroundColor" name="controlColor" catalog="System" colorSpace="catalog"/>
-                                                        </textFieldCell>
-                                                    </textField>
-                                                    <textField identifier="RouterUptimeLabel" horizontalHuggingPriority="251" verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="f2W-Kc-cxB" userLabel="RouterUptimeLabel">
-                                                        <rect key="frame" x="6" y="132" width="245" height="17"/>
-                                                        <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                                        <textFieldCell key="cell" scrollable="YES" lineBreakMode="clipping" sendsActionOnEndEditing="YES" title="Router uptime: Unknown" id="uQ0-cW-tYL">
-                                                            <font key="font" metaFont="system"/>
-                                                            <color key="textColor" name="labelColor" catalog="System" colorSpace="catalog"/>
-                                                            <color key="backgroundColor" name="controlColor" catalog="System" colorSpace="catalog"/>
-                                                        </textFieldCell>
-                                                    </textField>
-                                                    <textField identifier="RouterPIDLabel" horizontalHuggingPriority="251" verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="bmP-Ui-gyo" userLabel="RouterPIDLabel">
-                                                        <rect key="frame" x="6" y="113" width="245" height="17"/>
-                                                        <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                                        <textFieldCell key="cell" scrollable="YES" lineBreakMode="clipping" sendsActionOnEndEditing="YES" title="Router PID: Unknown" id="uFb-he-Wf3">
-                                                            <font key="font" metaFont="system"/>
-                                                            <color key="textColor" name="labelColor" catalog="System" colorSpace="catalog"/>
-                                                            <color key="backgroundColor" name="controlColor" catalog="System" colorSpace="catalog"/>
-                                                        </textFieldCell>
-                                                    </textField>
-                                                </subviews>
-                                            </view>
-                                        </box>
-                                        <box fixedFrame="YES" title="Quick Control" translatesAutoresizingMaskIntoConstraints="NO" id="IIP-Qi-7dp">
-                                            <rect key="frame" x="287" y="49" width="150" height="231"/>
-                                            <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                            <view key="contentView" identifier="QuickControlView" id="D8V-d8-0wT">
-                                                <rect key="frame" x="3" y="3" width="144" height="213"/>
-                                                <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
-                                                <subviews>
-                                                    <button identifier="startstopRouterButton" verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="1eu-Qw-TD9" userLabel="start-stop-button">
-                                                        <rect key="frame" x="10" y="175" width="126" height="32"/>
-                                                        <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                                        <buttonCell key="cell" type="push" title="Start/Stop Router" bezelStyle="rounded" alignment="center" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="OYN-sS-eQH">
-                                                            <behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
-                                                            <font key="font" metaFont="system"/>
-                                                        </buttonCell>
-                                                    </button>
-                                                    <button identifier="openConsoleButton" verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="XZi-oz-5gy" userLabel="open-console-button">
-                                                        <rect key="frame" x="10" y="149" width="126" height="32"/>
-                                                        <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                                        <buttonCell key="cell" type="push" title="Open Console" bezelStyle="rounded" alignment="center" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="Yh8-lj-JFi">
-                                                            <behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
-                                                            <font key="font" metaFont="system"/>
-                                                        </buttonCell>
-                                                    </button>
-                                                    <button verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="93P-Qg-IND">
-                                                        <rect key="frame" x="10" y="122" width="126" height="32"/>
-                                                        <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                                        <buttonCell key="cell" type="push" title="Preferences" bezelStyle="rounded" alignment="center" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="vab-yq-aBK">
-                                                            <behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
-                                                            <font key="font" metaFont="system"/>
-                                                        </buttonCell>
-                                                        <connections>
-                                                            <action selector="onPreferencesClick:" target="Ii7-Rb-Ls8" id="xzS-61-nx7"/>
-                                                        </connections>
-                                                    </button>
-                                                    <button verticalHuggingPriority="750" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="SQB-9F-cGZ">
-                                                        <rect key="frame" x="10" y="95" width="126" height="32"/>
-                                                        <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMinY="YES"/>
-                                                        <buttonCell key="cell" type="push" title="Launch Firefox" bezelStyle="rounded" alignment="center" enabled="NO" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="MDt-Na-H9e">
-                                                            <behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
-                                                            <font key="font" metaFont="system"/>
-                                                        </buttonCell>
-                                                    </button>
-                                                </subviews>
-                                            </view>
-                                        </box>
-                                    </subviews>
-                                    <accessibility identifier="routerStatusTabView"/>
-                                    <connections>
-                                        <outlet property="launchFirefoxButton" destination="SQB-9F-cGZ" id="Rp9-UH-O8q"/>
-                                        <outlet property="openConsoleButton" destination="XZi-oz-5gy" id="6xH-8v-63j"/>
-                                        <outlet property="quickControlView" destination="D8V-d8-0wT" id="4to-rN-2eL"/>
-                                        <outlet property="routerPIDLabel" destination="bmP-Ui-gyo" id="x5L-c1-yja"/>
-                                        <outlet property="routerStartStopButton" destination="1eu-Qw-TD9" id="FLt-MK-y5u"/>
-                                        <outlet property="routerStartedByLabel" destination="tgG-IT-Ojg" id="dA0-3w-cuF"/>
-                                        <outlet property="routerStatusLabel" destination="0Eo-re-5WK" id="7dm-Et-eSn"/>
-                                        <outlet property="routerUptimeLabel" destination="f2W-Kc-cxB" id="4Ya-qU-eb3"/>
-                                        <outlet property="routerVersionLabel" destination="sGy-NV-gmH" id="tM5-4M-DKy"/>
-                                    </connections>
-                                </view>
-                            </tabViewItem>
-                            <tabViewItem label="Router Log Viewer" identifier="" id="IFq-CR-cjD" customClass="LogViewerViewController" customModule="I2PLauncher" customModuleProvider="target">
-                                <view key="view" id="7U9-d7-IVr">
-                                    <rect key="frame" x="10" y="33" width="430" height="287"/>
-                                    <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
-                                    <subviews>
-                                        <scrollView identifier="LoggerTextScrollView" fixedFrame="YES" horizontalLineScroll="10" horizontalPageScroll="10" verticalLineScroll="10" verticalPageScroll="10" hasHorizontalScroller="NO" usesPredominantAxisScrolling="NO" translatesAutoresizingMaskIntoConstraints="NO" id="jca-Kn-cO2" userLabel="LoggerTextScrollView">
-                                            <rect key="frame" x="11" y="17" width="409" height="228"/>
-                                            <autoresizingMask key="autoresizingMask"/>
-                                            <clipView key="contentView" ambiguous="YES" drawsBackground="NO" id="E5l-WA-qOn">
-                                                <rect key="frame" x="1" y="1" width="407" height="226"/>
-                                                <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
-                                                <subviews>
-                                                    <textView identifier="LoggerTextView" ambiguous="YES" importsGraphics="NO" verticallyResizable="YES" usesFontPanel="YES" findStyle="panel" continuousSpellChecking="YES" allowsUndo="YES" usesRuler="YES" allowsNonContiguousLayout="YES" quoteSubstitution="YES" dashSubstitution="YES" spellingCorrection="YES" smartInsertDelete="YES" id="bgQ-8i-Xgb" userLabel="LoggerTextView">
-                                                        <rect key="frame" x="0.0" y="0.0" width="407" height="226"/>
-                                                        <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
-                                                        <color key="textColor" name="textColor" catalog="System" colorSpace="catalog"/>
-                                                        <color key="backgroundColor" name="textBackgroundColor" catalog="System" colorSpace="catalog"/>
-                                                        <size key="minSize" width="407" height="226"/>
-                                                        <size key="maxSize" width="463" height="10000000"/>
-                                                        <color key="insertionPointColor" name="textColor" catalog="System" colorSpace="catalog"/>
-                                                    </textView>
-                                                </subviews>
-                                            </clipView>
-                                            <scroller key="horizontalScroller" hidden="YES" wantsLayer="YES" verticalHuggingPriority="750" doubleValue="1" horizontal="YES" id="MRF-Wt-zdZ">
-                                                <rect key="frame" x="-100" y="-100" width="87" height="18"/>
-                                                <autoresizingMask key="autoresizingMask"/>
-                                            </scroller>
-                                            <scroller key="verticalScroller" wantsLayer="YES" verticalHuggingPriority="750" doubleValue="1" horizontal="NO" id="Xq6-ur-WuT">
-                                                <rect key="frame" x="392" y="1" width="16" height="226"/>
-                                                <autoresizingMask key="autoresizingMask"/>
-                                            </scroller>
-                                        </scrollView>
-                                    </subviews>
-                                </view>
-                                <connections>
-                                    <outlet property="scrollView" destination="jca-Kn-cO2" id="qAi-hi-PsC"/>
-                                    <outlet property="textFieldView" destination="bgQ-8i-Xgb" id="SbC-0r-xPR"/>
-                                </connections>
-                            </tabViewItem>
-                        </tabViewItems>
-                    </tabView>
-                    <connections>
-                        <outlet property="routerStatusViewOutlet" destination="xXg-Bt-RWR" id="L98-nF-i0n"/>
-                    </connections>
-                </viewController>
-                <customObject id="d8g-wS-Zts" userLabel="First Responder" customClass="NSResponder" sceneMemberID="firstResponder"/>
-            </objects>
-            <point key="canvasLocation" x="-823" y="165.5"/>
-        </scene>
-    </scenes>
-</document>
diff --git a/launchers/macosx/I2PLauncher/SwiftApplicationDelegate.swift b/launchers/macosx/I2PLauncher/SwiftApplicationDelegate.swift
deleted file mode 100644
index b1201513aa42e95a0596ddb9368849a6bfc776e7..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/SwiftApplicationDelegate.swift
+++ /dev/null
@@ -1,247 +0,0 @@
-//
-//  SwiftMainDelegate.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 17/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-import Cocoa
-import MBPopup
-
-extension Notification.Name {
-  static let killLauncher = Notification.Name("killStartupLauncher")
-  static let upgradeRouter = Notification.Name("upgradeRouter")
-  static let startRouter = Notification.Name("startRouter")
-  static let stopRouter = Notification.Name("stopRouter")
-}
-
-class Logger {
-  static func MLog<T>(level:Int32, _ object: T?,file:String = #file, function:String = #function, line:Int = #line) {
-    SBridge.logProxy(level, formattedMsg: "\(makeTag(function: function, file: file, line: line)) : \(String(describing: object))")
-  }
-  
-  private static func makeTag(function: String, file: String, line: Int) -> String{
-    let url = NSURL(fileURLWithPath: file)
-    let className:String! = url.lastPathComponent == nil ? file: url.lastPathComponent!
-    return "\(String(describing: className)) \(function)[\(line)]"
-  }
-  
-}
-
-
-@objc class SwiftApplicationDelegate : NSObject, NSApplicationDelegate, NSMenuDelegate {
-  
-  let statusBarController = StatusBarController()
-  let sharedRouterMgmr = RouterManager.shared()
-  //let popupController: MBPopupController
-  //let serviceTableViewController = ServiceTableViewController()
-  //let editorTableViewController: EditorTableViewController
-  
-  // Constructor, think of it like an early entrypoint.
-  override init() {
-    //self.popupController = MBPopupController(contentView: serviceTableViewController.contentView)
-    //self.editorTableViewController = serviceTableViewController.editorTableViewController
-    super.init()
-    
-    if (!DetectJava.shared().isJavaFound()) {
-    DetectJava.shared().findIt()
-      if (!DetectJava.shared().isJavaFound()) {
-        Logger.MLog(level:3, "Could not find java....")
-        terminate("No java..")
-      }
-    }
-    let javaBinPath = DetectJava.shared().javaBinary
-    Logger.MLog(level:1, "".appendingFormat("Found java home = %@", javaBinPath!))
-    
-    let (portIsNotTaken, _) = NetworkUtil.checkTcpPortForListen(port: 7657)
-    if (!portIsNotTaken) {
-      RouterProcessStatus.isRouterRunning = true
-      RouterProcessStatus.isRouterChildProcess = false
-      Logger.MLog(level:2, "I2P Router seems to be running")
-    } else {
-      RouterProcessStatus.isRouterRunning = false
-      Logger.MLog(level:2, "I2P Router seems to NOT be running")
-    }
-  } // End of init()
-  
-  // A function which detects the current installed I2P router version
-  // NOTE: The return value tells if the function fails to detect I2P or not, and not if I2P is installed or not.
-  @objc func findInstalledI2PVersion() -> Bool {
-    let jarPath = Preferences.shared().i2pBaseDirectory + "/lib/i2p.jar"
-    let subCmd = Preferences.shared().javaCommandPath + "-cp " + jarPath + " net.i2p.CoreVersion"
-    let cmdArgs:[String] = ["-c", subCmd]
-    
-    let sub:Subprocess = Subprocess.init(executablePath: "/bin/sh", arguments: cmdArgs)
-    let results:ExecutionResult = sub.execute(captureOutput: true)!
-    
-    if (results.didCaptureOutput) {
-      if (results.status == 0) {
-        let i2pVersion = results.outputLines.first?.replace(target: "I2P Core version: ", withString: "")
-        Logger.MLog(level: 1, "".appendingFormat("I2P version detected: %@",i2pVersion ?? "Unknown"))
-        RouterProcessStatus.routerVersion = i2pVersion
-        RouterManager.shared().eventManager.trigger(eventName: "router_version", information: i2pVersion)
-        return true
-      } else {
-        Logger.MLog(level: 2, "Non zero exit code from subprocess while trying to detect version number!")
-        for line in results.errorsLines {
-          Logger.MLog(level: 2, line)
-        }
-        return false
-      }
-    } else {
-      Logger.MLog(level: 1, "Warning: Version Detection did NOT captured output")
-    }
-    return false
-  }
-  
-  
-  // Helper functions for the optional dock icon
-  func triggerDockIconShowHide(showIcon state: Bool) -> Bool {
-    var result: Bool
-    if state {
-      result = NSApp.setActivationPolicy(NSApplication.ActivationPolicy.regular)
-    } else {
-      result = NSApp.setActivationPolicy(NSApplication.ActivationPolicy.accessory)
-    }
-    return result
-  }
-  
-  // Helper functions for the optional dock icon
-  func getDockIconStateIsShowing() -> Bool {
-    if NSApp.activationPolicy() == NSApplication.ActivationPolicy.regular {
-      return true
-    } else {
-      return false
-    }
-  }
-  
-  @objc func updateServices() {
-    /*
-    serviceTableViewController.updateServices { [weak self] in
-      let title = self?.serviceTableViewController.generalStatus == .crashed ? "-.-" : "I2PLauncher"
-      self?.popupController.statusItem.title = title
-      
-      if Preferences.shared().notifyOnStatusChange {
-        self?.serviceTableViewController.services.forEach { $0.notifyIfNecessary() }
-      }
-    }
-    */
-  }
-  
-  /**
-   *
-   * This is the swift "entrypoint". In C it would been "main(argc,argv)"
-   *
-   */
-  @objc func applicationDidFinishLaunching() {
-    switch Preferences.shared().showAsIconMode {
-    case .bothIcon, .dockIcon:
-      if (!getDockIconStateIsShowing()) {
-        let _ = triggerDockIconShowHide(showIcon: true)
-      }
-    default:
-      if (getDockIconStateIsShowing()) {
-        let _ = triggerDockIconShowHide(showIcon: false)
-      }
-    }
-    let runningApps = NSWorkspace.shared.runningApplications
-    let isRunning = !runningApps.filter { $0.bundleIdentifier == Identifiers.launcherApplicationBundleId }.isEmpty
-    // SMLoginItemSetEnabled(launcherAppId as CFString, true)
-    
-    if isRunning {
-      DistributedNotificationCenter.default().post(name: .killLauncher, object: Bundle.main.bundleIdentifier!)
-    }
-    
-    if (Preferences.shared().alsoStartFirefoxOnLaunch) {
-      DispatchQueue.delay(.seconds(120)) {
-        print("two minutes has passed, executing firefox manager")
-        let _ = FirefoxManager.shared().executeFirefox()
-      }
-    }
-    
-    if #available(OSX 10.14, *) {
-      Appearance.addObserver(self)
-    } else {
-      //popupController.backgroundView.backgroundColor = .white
-    }
-    
-    NSUserNotificationCenter.default.delegate = self
-    /*
-    popupController.statusItem.button?.image = NSImage(named:"StatusBarButtonImage")
-    popupController.statusItem.button?.toolTip = "I2P Launch Manager"
-    popupController.statusItem.button?.font = NSFont(name: "SF Mono Regular", size: 10) ?? NSFont.systemFont(ofSize: 12)
-    popupController.statusItem.length = 30
-    
-    popupController.contentView.wantsLayer = true
-    popupController.contentView.layer?.masksToBounds = true
-    
-    serviceTableViewController.setup()
-    
-    popupController.willOpenPopup = { [weak self] _ in
-      if self?.editorTableViewController.hidden == true {
-        self?.serviceTableViewController.willOpenPopup()
-      } else {
-        self?.editorTableViewController.willOpenPopup()
-      }
-    }
-    
-    popupController.didOpenPopup = { [weak self] in
-      if self?.editorTableViewController.hidden == false {
-        self?.editorTableViewController.didOpenPopup()
-      }
-    }
-    */
-  }
-  
-  @objc func listenForEvent(eventName: String, callbackActionFn: @escaping ((Any?)->()) ) {
-    RouterManager.shared().eventManager.listenTo(eventName: eventName, action: callbackActionFn )
-  }
-  
-  @objc func triggerEvent(en: String, details: String? = nil) {
-    RouterManager.shared().eventManager.trigger(eventName: en, information: details)
-  }
-  
-  @objc static func openLink(url: String) {
-    NSLog("Trying to open \(url)")
-    NSWorkspace.shared.open(NSURL(string: url)! as URL)
-  }
-  
-  /**
-   *
-   * This function will execute when the launcher shuts down for some reason.
-   * Could be either OS or user triggered.
-   *
-   */
-  @objc func applicationWillTerminate() {
-    // Shutdown stuff
-    if (Preferences.shared().stopRouterOnLauncherShutdown) {
-      RouterManager.shared().routerRunner.TeardownLaunchd()
-      sleep(2)
-      let status: AgentStatus? = RouterRunner.launchAgent?.status()
-      if status != .unloaded {
-        Logger.MLog(level:2, "Router service not yet stopped")
-        RouterManager.shared().routerRunner.TeardownLaunchd()
-        sleep(5)
-      }
-    }
-  }
-  
-  @objc func terminate(_ why: Any?) {
-    Logger.MLog(level:2, "".appendingFormat("Stopping cause of ", why! as! CVarArg))
-  }
-}
-
-extension SwiftApplicationDelegate: NSUserNotificationCenterDelegate {
-  func userNotificationCenter(_ center: NSUserNotificationCenter, didActivate notification: NSUserNotification) {
-    //popupController.openPopup()
-  }
-}
-
-extension SwiftApplicationDelegate: AppearanceObserver {
-  func changeAppearance(to newAppearance: NSAppearance) {
-    //popupController.backgroundView.backgroundColor = newAppearance.isDarkMode ? .windowBackgroundColor : .white
-  }
-}
-
diff --git a/launchers/macosx/I2PLauncher/routermgmt/DetectJava.swift b/launchers/macosx/I2PLauncher/routermgmt/DetectJava.swift
deleted file mode 100644
index 198e3bed86db908f17b2cfdb0d4c387de6894a64..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/routermgmt/DetectJava.swift
+++ /dev/null
@@ -1,182 +0,0 @@
-//
-//  DetectJava.swift
-//  JavaI2PWrapper
-//
-//  Created by Mikal Villa on 24/03/2018.
-//  Copyright © 2018 I2P. All rights reserved.
-//
-
-import Foundation
-
-
-@objc class DetectJava : NSObject {
-  
-  static var hasJRE : Bool = false
-  static var hasJDK : Bool = false
-  static var userWantJRE : Bool = false
-  static var userAcceptOracleEULA : Bool = false
-  
-  private static var sharedDetectJava: DetectJava = {
-    let javaDetector = DetectJava()
-    
-    // Configuration
-    // ...
-    return javaDetector
-  }()
-  
-  // Initialization
-  
-  private override init() {
-    super.init()
-  }
-  
-  // MARK: - Accessors
-  
-  
-  class func shared() -> DetectJava {
-    return sharedDetectJava
-  }
-  
-  @objc var javaBinary: String? {
-    didSet{
-      print("DetectJava.javaBinary was set to "+self.javaBinary!)
-    }
-  }
-  
-  // Java checks
-  @objc var javaHome: String = ""{
-    
-    //Called before the change
-    willSet(newValue){
-      print("DetectJava.javaHome will change from "+self.javaHome+" to "+newValue)
-    }
-    
-    //Called after the change
-    didSet{
-      DetectJava.hasJRE = true
-      // javaHome will have a trailing \n which we remove to not break the cli
-      self.javaBinary = (self.javaHome+"/bin/java").replace(target: "\n", withString: "")
-      print("DetectJava.javaHome did change to "+self.javaHome)
-      //RouterManager.shared().eventManager.trigger(eventName: "java_found", information: self.javaHome)
-    }
-  };
-  private var testedEnv : Bool = false
-  private var testedJH : Bool = false
-  private var testedDfl : Bool = false
-  
-  @objc func isJavaFound() -> Bool {
-    if !(self.javaHome.isEmpty) {
-      return true
-    }
-    return false
-  }
-  
-  /**
-   *
-   * The order of the code blocks will decide the order, which will define the preffered.
-   *
-   **/
-  @objc func findIt() {
-    if (DetectJava.hasJRE) {
-      return
-    }
-    print("Start with checking environment variable")
-    self.checkJavaEnvironmentVariable()
-    if !(self.javaHome.isEmpty) {
-      DetectJava.hasJRE = true
-      return
-    }
-    print("Checking with the java_home util")
-    self.runJavaHomeCmd()
-    if !(self.javaHome.isEmpty) {
-      DetectJava.hasJRE = true
-      return
-    }
-    print("Checking default JRE install path")
-    self.checkDefaultJREPath()
-    if !(self.javaHome.isEmpty) {
-      DetectJava.hasJRE = true
-      return
-    }
-  }
-  
-  @objc func getJavaViaLibexecBin() -> Array<String> {
-    return ["/usr/libexec/java_home", "-v", "1.7+", "--exec", "java"]
-  }
-  
-  @objc func runJavaHomeCmd() {
-    let task = Process()
-    task.launchPath = "/usr/libexec/java_home"
-    task.arguments = ["-v", "1.7+"]
-    let pipe = Pipe()
-    task.standardOutput = pipe
-    let outHandle = pipe.fileHandleForReading
-    outHandle.waitForDataInBackgroundAndNotify()
-    
-    var obs1 : NSObjectProtocol!
-    obs1 = NotificationCenter.default.addObserver(
-      forName: NSNotification.Name.NSFileHandleDataAvailable,
-      object: outHandle, queue: nil) {
-        notification -> Void in
-          let data = outHandle.availableData
-          if data.count > 0 {
-            let str = NSString(data: data, encoding: String.Encoding.utf8.rawValue)
-            if (str != nil) {
-              let stringVal = str! as String
-              print("got output: "+stringVal)
-              self.javaHome = stringVal
-            }
-            // TODO: Found something, check it out
-            outHandle.waitForDataInBackgroundAndNotify()
-          } else {
-            print("EOF on stdout from process")
-            NotificationCenter.default.removeObserver(obs1)
-            // No JRE so far
-          }
-    }
-    
-    var obs2 : NSObjectProtocol!
-    obs2 = NotificationCenter.default.addObserver(
-      forName: Process.didTerminateNotification,
-      object: task, queue: nil) {
-        notification -> Void in
-          print("terminated")
-          NotificationCenter.default.removeObserver(obs2)
-    }
-    
-    task.launch()
-    task.waitUntilExit()
-    self.testedJH = true
-  }
-  
-  
-  @objc func checkDefaultJREPath() {
-    var isDir : ObjCBool = false;
-    let defaultJREPath = "/Library/Internet Plug-Ins/JavaAppletPlugin.plugin/Contents/Home"
-    if (FileManager.default.fileExists(atPath: defaultJREPath, isDirectory:&isDir) && isDir.boolValue) {
-      // Found it!!
-      self.javaHome = defaultJREPath
-    }
-    self.testedDfl = true
-    // No JRE here
-  }
-  
-  @objc func getEnvironmentVar(_ name: String) -> String? {
-    guard let rawValue = getenv(name) else { return nil }
-    return String(utf8String: rawValue)
-  }
-  
-  @objc func checkJavaEnvironmentVariable() {
-    let dic = ProcessInfo.processInfo.environment
-    if let javaHomeEnv = dic["JAVA_HOME"] {
-      // Maybe we got an JRE
-      print("Found JAVA_HOME with value:")
-      print(javaHomeEnv)
-      self.javaHome = javaHomeEnv
-    }
-    self.testedEnv = true
-    print("JAVA HOME is not set")
-  }
-  
-  
-}
diff --git a/launchers/macosx/I2PLauncher/routermgmt/NetworkUtil.swift b/launchers/macosx/I2PLauncher/routermgmt/NetworkUtil.swift
deleted file mode 100644
index 0764b5113095b7b10493d96a90ec8e31324ce4de..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/routermgmt/NetworkUtil.swift
+++ /dev/null
@@ -1,50 +0,0 @@
-//
-//  NetworkUtil.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 07/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-class NetworkUtil {
-  static func checkTcpPortForListen(host: String = "127.0.0.1", port: in_port_t = 7657) -> (Bool, descr: String){
-    
-    let socketFileDescriptor = socket(AF_INET, SOCK_STREAM, 0)
-    if socketFileDescriptor == -1 {
-      return (false, "SocketCreationFailed, \(descriptionOfLastError())")
-    }
-    
-    var addr = sockaddr_in()
-    let sizeOfSockkAddr = MemoryLayout<sockaddr_in>.size
-    addr.sin_len = __uint8_t(sizeOfSockkAddr)
-    addr.sin_family = sa_family_t(AF_INET)
-    addr.sin_port = Int(OSHostByteOrder()) == OSLittleEndian ? _OSSwapInt16(port) : port
-    addr.sin_addr = in_addr(s_addr: inet_addr(host))
-    addr.sin_zero = (0, 0, 0, 0, 0, 0, 0, 0)
-    var bind_addr = sockaddr()
-    memcpy(&bind_addr, &addr, Int(sizeOfSockkAddr))
-    
-    if Darwin.bind(socketFileDescriptor, &bind_addr, socklen_t(sizeOfSockkAddr)) == -1 {
-      let details = descriptionOfLastError()
-      release(socket: socketFileDescriptor)
-      return (false, "\(port), BindFailed, \(details)")
-    }
-    if listen(socketFileDescriptor, SOMAXCONN ) == -1 {
-      let details = descriptionOfLastError()
-      release(socket: socketFileDescriptor)
-      return (false, "\(port), ListenFailed, \(details)")
-    }
-    release(socket: socketFileDescriptor)
-    return (true, "\(port) is free for use")
-  }
-  
-  static func release(socket: Int32) {
-    Darwin.shutdown(socket, SHUT_RDWR)
-    close(socket)
-  }
-  static func descriptionOfLastError() -> String {
-    return String(cString: UnsafePointer(strerror(errno)))
-  }
-}
diff --git a/launchers/macosx/I2PLauncher/routermgmt/RouterManager.swift b/launchers/macosx/I2PLauncher/routermgmt/RouterManager.swift
deleted file mode 100644
index b490f86f103993b225be8dfb334d6abd08ac96d5..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/routermgmt/RouterManager.swift
+++ /dev/null
@@ -1,184 +0,0 @@
-//
-//  RouterManager.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 22/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-
-enum ErrorsInRouterMgmr: Swift.Error {
-  case NoJavaFound
-  case InvalidVersion
-  case NotFound
-}
-
-class RouterManager : NSObject {
-  
-  // MARK: - Properties
-  
-  static let packedVersion : String = NSDEF_I2P_VERSION
-  
-  let eventManager = EventManager()
-  let routerRunner = RouterRunner()
-  
-  var logViewStorage: NSTextStorage?
-  var lastRouterPid : String? = nil
-  private var canRouterStart : Bool = false
-  
-  private static func handleRouterException(information:Any?) {
-    Logger.MLog(level:1,"event! - handle router exception")
-    Logger.MLog(level:1,information as? String)
-  }
-  private static func handleRouterStart(information:Any?) {
-    Logger.MLog(level:1,"event! - handle router start")
-    RouterProcessStatus.routerStartedAt = Date()
-    RouterProcessStatus.isRouterChildProcess = true
-    RouterProcessStatus.isRouterRunning = true
-  }
-  private static func handleRouterAlreadyStarted(information:Any?) {
-    Logger.MLog(level:1,"event! - handle router already started");
-  }
-  private static func handleRouterStop(information:Any?) {
-    Logger.MLog(level:1,"event! - handle router stop")
-    // TODO: Double check, check if pid stored exists
-    RouterProcessStatus.routerStartedAt = nil
-    RouterProcessStatus.isRouterChildProcess = false
-    RouterProcessStatus.isRouterRunning = false
-  }
-  private static func handleRouterPid(information:Any?) {
-    Logger.MLog(level:1,"".appendingFormat("event! - handle router pid: ", information as! String))
-    if (information != nil) {
-      let intPid = Int(information as! String)
-      print("Router pid is \(String(describing: intPid))..")
-    }
-  }
-  private static func handleRouterVersion(information:Any?) {
-    do {
-      Logger.MLog(level:1, "".appendingFormat("event! - handle router version: ", information as! String))
-      guard let currentVersion : String = information as? String else {
-        throw ErrorsInRouterMgmr.InvalidVersion
-      }
-      if (currentVersion == "Unknown") {
-        throw ErrorsInRouterMgmr.InvalidVersion
-      }
-      if (packedVersion.compare(currentVersion, options: .numeric) == .orderedDescending) {
-        Logger.MLog(level:1,"event! - router version: Packed version is newer, gonna re-deploy")
-        RouterManager.shared().eventManager.trigger(eventName: "router_must_upgrade", information: "got new version")
-      } else {
-        Logger.MLog(level:1,"event! - router version: No update needed")
-        RouterManager.shared().eventManager.trigger(eventName: "router_can_setup", information: "all ok")
-      }
-    } catch ErrorsInRouterMgmr.InvalidVersion {
-      // This is most likely due to an earlier extract got killed halfway or something
-      // Trigger an update
-      RouterManager.shared().eventManager.trigger(eventName: "router_must_upgrade", information: "invalid version found")
-    } catch {
-      // WTF
-      NSLog("Fatal error in RouterManager");
-      print(error)
-    }
-  }
-  
-  private static var sharedRouterManager: RouterManager = {
-    let routerManager = RouterManager(detectJavaInstance: DetectJava.shared())
-    
-    // Configuration
-    // ...
-    routerManager.updateState()
-    
-    routerManager.eventManager.listenTo(eventName: "router_start", action: handleRouterStart)
-    routerManager.eventManager.listenTo(eventName: "router_stop", action: handleRouterStop)
-    routerManager.eventManager.listenTo(eventName: "router_pid", action: handleRouterPid)
-    routerManager.eventManager.listenTo(eventName: "router_version", action: handleRouterVersion)
-    routerManager.eventManager.listenTo(eventName: "router_exception", action: handleRouterException)
-    routerManager.eventManager.listenTo(eventName: "router_already_running", action: handleRouterAlreadyStarted)
-    routerManager.eventManager.listenTo(eventName: "router_can_start", action: routerManager.setLauncherReadyToStartRouter)
-    routerManager.eventManager.listenTo(eventName: "router_can_setup", action: routerManager.routerRunner.SetupAgent)
-    
-    //routerManager.eventManager.listenTo(eventName: "launch_agent_running", action: routerManager.routerRunner.onLoadedAgent)
-    
-    routerManager.eventManager.listenTo(eventName: "launch_agent_running", action: {
-      let agent = RouterRunner.launchAgent!
-      let agentStatus = agent.status()
-      switch agentStatus {
-      case .running(let pid):
-        DispatchQueue.main.async {
-          routerManager.eventManager.trigger(eventName: "router_start", information: String(pid))
-          routerManager.routerRunner.routerStatus.setRouterStatus(true)
-          routerManager.routerRunner.routerStatus.setRouterRanByUs(true)
-          routerManager.eventManager.trigger(eventName: "router_pid", information: String(pid))
-        }
-        break
-        
-      default:
-        NSLog("wtf, agent status = \(agentStatus)")
-        break
-      }
-    })
-    return routerManager
-  }()
-  
-  // MARK: -
-  
-  let detectJava: DetectJava
-  private var routerInstance: I2PRouterTask?{
-    //Called after the change
-    didSet{
-      print("RouterManager.routerInstance did change to ", self.routerInstance ?? "null")
-      if (self.routerInstance != nil) {
-        RouterProcessStatus.isRouterRunning = (self.routerInstance?.isRouterRunning)!
-      }
-    }
-  };
-  
-  // Initialization
-  
-  private init(detectJavaInstance: DetectJava) {
-    self.detectJava = detectJavaInstance
-  }
-  
-  // MARK: - Accessors
-  
-  static func logInfo(format: String, messages: String...) {
-    //SBridge.sharedInstance().logMessageWithFormat(0, format, messages)func k(_ x: Int32, _ params: String...) {
-    /*withVaList(messages) {
-      genericLogger(x, $0)
-    }*/
-  }
-  
-  class func shared() -> RouterManager {
-    return sharedRouterManager
-  }
-  
-  func setLauncherReadyToStartRouter(_ information: Any?) {
-    self.canRouterStart = true
-    if (Preferences.shared().startRouterOnLauncherStart) {
-      // Trigger the actual start at launch time
-      print("Start router on launch preference is enabled - Starting")
-      self.routerRunner.StartAgent(information)
-    } else {
-      print("Start router on launch preference is disabled - Router ready when user are!")
-      SBridge.sendUserNotification("I2P Router Ready", formattedMsg: "The I2P Router is ready to be launched, however the autostart is disabled and require user input to start.")
-    }
-  }
-  
-  func checkIfRouterCanStart() -> Bool {
-    return self.canRouterStart
-  }
-  
-  func setRouterTask(router: I2PRouterTask) {
-    self.routerInstance = router
-  }
-  
-  func getRouterTask() -> I2PRouterTask? {
-    return self.routerInstance
-  }
-  
-  func updateState() {
-    self.routerInstance = SBridge.sharedInstance()?.currentRouterInstance
-  }
-  
-}
diff --git a/launchers/macosx/I2PLauncher/routermgmt/RouterProcessStatus+ObjectiveC.swift b/launchers/macosx/I2PLauncher/routermgmt/RouterProcessStatus+ObjectiveC.swift
deleted file mode 100644
index 8810883d5be7a95978cbda295ed6e3add781cea3..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/routermgmt/RouterProcessStatus+ObjectiveC.swift
+++ /dev/null
@@ -1,13 +0,0 @@
-//
-//  RouterProcessStatus+ObjectiveC.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 18/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-extension RouterProcessStatus {
-  
-}
diff --git a/launchers/macosx/I2PLauncher/routermgmt/RouterProcessStatus.swift b/launchers/macosx/I2PLauncher/routermgmt/RouterProcessStatus.swift
deleted file mode 100644
index 1516c097df483e5c0ba4433c8da273c3fc068d1d..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/routermgmt/RouterProcessStatus.swift
+++ /dev/null
@@ -1,58 +0,0 @@
-//
-//  RouterProcessStatus.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 18/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-import AppKit
-
-@objc class RouterProcessStatus : NSObject {
-  
-  /**
-   *
-   * Why the functions bellow? Because the Objective-C bridge is limited, it can't do Swift "static's" over it.
-   *
-   **/
- 
-  @objc func setRouterStatus(_ isRunning: Bool = false) {
-    RouterProcessStatus.isRouterRunning = isRunning
-  }
-  
-  @objc func setRouterRanByUs(_ ranByUs: Bool = false) {
-    RouterProcessStatus.isRouterChildProcess = ranByUs
-  }
-  
-  @objc func getRouterIsRunning() -> Bool {
-    return RouterProcessStatus.isRouterRunning
-  }
-  
-  @objc func getJavaHome() -> String {
-    return DetectJava.shared().javaHome
-  }
-  
-  @objc func getJavaViaLibexec() -> Array<String> {
-    return DetectJava.shared().getJavaViaLibexecBin()
-  }
-  
-  @objc func triggerEvent(en: String, details: String? = nil) {
-    RouterManager.shared().eventManager.trigger(eventName: en, information: details)
-  }
-
-  @objc func listenForEvent(eventName: String, callbackActionFn: @escaping ((Any?)->()) ) {
-    RouterManager.shared().eventManager.listenTo(eventName: eventName, action: callbackActionFn )
-  }
-}
-
-extension RouterProcessStatus {
-  static var isRouterRunning : Bool = (RouterManager.shared().getRouterTask() != nil)
-  static var isRouterChildProcess : Bool = (RouterManager.shared().getRouterTask() != nil)
-  static var routerVersion : String? = Optional.none
-  static var routerStartedAt : Date? = Optional.none
-  static var i2pDirectoryPath : String = Preferences.shared().i2pBaseDirectory
-  
-  
-}
-
diff --git a/launchers/macosx/I2PLauncher/routermgmt/RouterRunner.swift b/launchers/macosx/I2PLauncher/routermgmt/RouterRunner.swift
deleted file mode 100644
index b4e40e407e7251422df6b076693efeed587c06f0..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/routermgmt/RouterRunner.swift
+++ /dev/null
@@ -1,216 +0,0 @@
-//
-//  RouterRunner.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 18/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-class RouterRunner: NSObject {
-  
-  
-  var daemonPath: String?
-  var arguments: String?
-  
-  static var launchAgent: LaunchAgent?
-  let routerStatus: RouterProcessStatus = RouterProcessStatus()
-  
-  var currentRunningProcess: Subprocess?
-  var currentProcessResults: ExecutionResult?
-  
-  let domainLabel = String(NSString(format: "%@.I2PRouter", APPDOMAIN))
-  
-  let plistName = String(NSString(format: "%@.I2PRouter.plist", APPDOMAIN))
-  
-  let appSupportPath = FileManager.default.urls(for: FileManager.SearchPathDirectory.applicationSupportDirectory, in: FileManager.SearchPathDomainMask.userDomainMask)
-  
-  override init() {
-    super.init()
-  }
-  
-  func SetupAgent() {
-    let agent = SetupAndReturnAgent()
-    RouterRunner.launchAgent = agent
-  }
-  
-  typealias Async = (_ success: () -> Void, _ failure: (NSError) -> Void) -> Void
-  
-  func retry(numberOfTimes: Int, _ sleepForS: UInt32, task: () -> Async, success: () -> Void, failure: (NSError) -> Void) {
-    task()(success, { error in
-      if numberOfTimes > 1 {
-        sleep(sleepForS)
-        retry(numberOfTimes: numberOfTimes - 1, sleepForS, task: task, success: success, failure: failure)
-      } else {
-        failure(error)
-      }
-    })
-  }
-  
-  func SetupAndReturnAgent() -> LaunchAgent {
-    
-    let applicationsSupportPath: URL = FileManager.default.urls(for: .applicationSupportDirectory, in: .userDomainMask).first!
-    
-    let defaultStartupFlags:[String] = [
-      "-Djava.awt.headless=true",
-      "".appendingFormat("-Di2p.base.dir=%@", Preferences.shared().i2pBaseDirectory),
-      "".appendingFormat("-Dwrapper.logfile=%@/i2p/router.log", applicationsSupportPath.absoluteString),
-      "".appendingFormat("-Dwrapper.java.pidfile=%@/i2p/router.pid", applicationsSupportPath.absoluteString),
-      "-Dwrapper.logfile.loglevel=DEBUG", // TODO: Allow loglevel to be set from Preferences?
-      "-Dwrapper.console.loglevel=DEBUG",
-      "net.i2p.router.Router"
-    ]
-    
-    let javaCliArgs = Preferences.shared().javaCommandPath.splitByWhitespace()
-    
-    self.daemonPath = javaCliArgs[0]
-    self.arguments = defaultStartupFlags.joined(separator: " ")
-    
-    let basePath = Preferences.shared().i2pBaseDirectory
-    
-    let jars = try! FileManager.default.contentsOfDirectory(atPath: basePath+"/lib")
-    var classpath:String = "."
-    for jar in jars {
-      if (jar.hasSuffix(".jar")) {
-        classpath += ":"+basePath+"/lib/"+jar
-      }
-    }
-    
-    var cliArgs:[String] = [
-      self.daemonPath!,
-      ]
-    cliArgs.append(contentsOf: javaCliArgs.dropFirst())
-    cliArgs.append(contentsOf: [
-      "-cp",
-      classpath,
-      ])
-    // This allow java arguments to be passed from the settings
-    cliArgs.append(contentsOf: Preferences.shared().javaCommandOptions.splitByWhitespace())
-    cliArgs.append(contentsOf: defaultStartupFlags)
-    let agent = LaunchAgent(label: self.domainLabel,program: cliArgs)
-    agent.launchOnlyOnce = false
-    agent.keepAlive = false
-    agent.workingDirectory = basePath
-    agent.userName = NSUserName()
-    agent.standardErrorPath = NSString(format: "%@/router.stderr.log", Preferences.shared().i2pLogDirectory) as String
-    agent.standardOutPath = NSString(format: "%@/router.stdout.log", Preferences.shared().i2pLogDirectory) as String
-    agent.environmentVariables = [
-      "PATH": "/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin",
-      "I2PBASE": basePath,
-    ]
-    agent.disabled = false
-    agent.processType = ProcessType.adaptive
-    RouterRunner.launchAgent = agent
-    
-    // NOTE: I suspect this is better to solve in the application
-    agent.runAtLoad = false //Preferences.shared().startRouterOnLauncherStart
-    agent.keepAlive = true
-    DispatchQueue(label: "background_starter").async {
-      do {
-        // TODO: Find a better way than sleep
-        try LaunchAgentManager.shared.write(agent, called: self.plistName)
-        sleep(1)
-        try LaunchAgentManager.shared.load(agent)
-        sleep(1)
-        
-        let agentStatus = LaunchAgentManager.shared.status(agent)
-        switch agentStatus {
-        case .running:
-          break
-        case .loaded:
-          DispatchQueue.main.async {
-            RouterManager.shared().eventManager.trigger(eventName: "router_can_start", information: agent)
-          }
-          break
-        case .unloaded:
-          break
-        }
-      } catch {
-        DispatchQueue.main.async {
-          RouterManager.shared().eventManager.trigger(eventName: "router_setup_error", information: "\(error)")
-        }
-      }
-    }
-    return agent
-  }
-  
-  
-  func StartAgent(_ information:Any? = nil) {
-    if (RouterManager.shared().checkIfRouterCanStart()) {
-      let agent = RouterRunner.launchAgent ?? information as! LaunchAgent
-      DispatchQueue(label: "background_block").async {
-        LaunchAgentManager.shared.start(agent, { (proc) in
-          NSLog("Will call onLaunchdStarted")
-        })
-      }
-    } else {
-      SBridge.sendUserNotification("Whops! Please wait", formattedMsg: "I'm sorry but it's still something unresolved before we can start the I2P router. Please wait.")
-    }
-  }
-  
-  func StopAgent(_ callback: @escaping () -> () = {}) {
-    let agentStatus = LaunchAgentManager.shared.status(RouterRunner.launchAgent!)
-    DispatchQueue(label: "background_block").async {
-      do {
-        switch agentStatus {
-        case .running:
-          // For now we need to use unload to stop it.
-          try LaunchAgentManager.shared.unload(RouterRunner.launchAgent!, { (proc) in
-            // Called when stop is actually executed
-            proc.waitUntilExit()
-            DispatchQueue.main.async {
-              RouterManager.shared().eventManager.trigger(eventName: "router_stop", information: "ok")
-              callback()
-            }
-          })
-          try LaunchAgentManager.shared.load(RouterRunner.launchAgent!)
-          break
-        case .unloaded:
-          // Seems it sometimes get unloaded on stop, we load it again.
-          try! LaunchAgentManager.shared.load(RouterRunner.launchAgent!)
-          return
-        default: break
-        }
-      } catch {
-        NSLog("Error \(error)")
-      }
-    }
-  }
-  
-  func SetupLaunchd() {
-    do {
-      try LaunchAgentManager.shared.write(RouterRunner.launchAgent!, called: self.plistName)
-      try LaunchAgentManager.shared.load(RouterRunner.launchAgent!)
-    } catch {
-      RouterManager.shared().eventManager.trigger(eventName: "router_exception", information: error)
-    }
-  }
-  
-  func TeardownLaunchd() {
-    /*let status = LaunchAgentManager.shared.status(RouterRunner.launchAgent!)
-    switch status {
-    case .running:*/
-      do {
-        // Unload no matter previous state!
-        try LaunchAgentManager.shared.unload(RouterRunner.launchAgent!)
-        
-        let plistPath = NSHomeDirectory()+"/Library/LaunchAgents/"+self.plistName
-        
-        sleep(1)
-        if FileManager.default.fileExists(atPath: plistPath) {
-          try FileManager.default.removeItem(atPath: plistPath)
-        }
-      } catch LaunchAgentManagerError.urlNotSet(label: self.domainLabel) {
-        Logger.MLog(level:3, "URL not set in launch agent")
-      } catch {
-        Logger.MLog(level:3, "".appendingFormat("Error in launch agent: %s", error as CVarArg))
-        RouterManager.shared().eventManager.trigger(eventName: "router_exception", information: error)
-      }
-   /*   break
-    default: break
-    }
-    */
-  }
-  
-}
diff --git a/launchers/macosx/I2PLauncher/routermgmt/RouterServices/HttpTunnelService.swift b/launchers/macosx/I2PLauncher/routermgmt/RouterServices/HttpTunnelService.swift
deleted file mode 100644
index f502c3dbaeea6b5875470f92d64fa7e4a39dcd77..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/routermgmt/RouterServices/HttpTunnelService.swift
+++ /dev/null
@@ -1,42 +0,0 @@
-//
-//  HttpTunnelService.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 03/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Foundation
-import Kanna
-
-class HttpTunnelService : Service {
-  
-  let dataURL: URL = URL(string: "http://127.0.0.1:7657/i2ptunnel/")!
-  
-  override func updateStatus(callback: @escaping (BaseService) -> Void) {
-    URLSession.shared.dataTask(with: dataURL) { [weak self] data, _, error in
-      guard let strongSelf = self else { return }
-      defer { callback(strongSelf) }
-      
-      guard let doc = try? HTML(html: data!, encoding: .utf8) else { return /*strongSelf._fail("Couldn't parse response")*/ }
-      
-      _ = doc.css("table#clientTunnels > tr.tunnelProperties > td.tunnelStatus").first
-      let maxStatus: ServiceStatus = .started
-      strongSelf.status = maxStatus
-      
-      switch maxStatus {
-      case .waiting:
-        strongSelf.message = "Waiting on router"
-      case .started:
-        strongSelf.message = "Started"
-      case .stopped:
-        strongSelf.message = "Stopped"
-      case .undetermined:
-        strongSelf.message = "Undetermined"
-      default:
-        strongSelf.message = "Undetermined" /*downComponents.map { $0["name"] as? String }.compactMap { $0 }.joined(separator: ", ")*/
-      }
-    }.resume()
-  }
-  
-}
diff --git a/launchers/macosx/I2PLauncher/routermgmt/RouterServices/I2PRouterService.swift b/launchers/macosx/I2PLauncher/routermgmt/RouterServices/I2PRouterService.swift
deleted file mode 100644
index 50eb997d3f6dd85aa86f3ba21fbc6729f4a93847..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/routermgmt/RouterServices/I2PRouterService.swift
+++ /dev/null
@@ -1,23 +0,0 @@
-//
-//  I2PRouterService.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 03/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-class I2PRouterService : Service {
-  
-  override func updateStatus(callback: @escaping (BaseService) -> Void) {
-    //guard let strongSelf = self else { return }
-    defer { callback(self) }
-    DispatchQueue.main.async {
-      self.status = ServiceStatus(rawValue: 0)!
-      self.message = "Dead"
-    }
-    
-  }
-  
-}
diff --git a/launchers/macosx/I2PLauncher/routermgmt/RouterServices/IrcTunnelService.swift b/launchers/macosx/I2PLauncher/routermgmt/RouterServices/IrcTunnelService.swift
deleted file mode 100644
index e0dedc26e764c252e15af1dd906294d5dec1c16e..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/routermgmt/RouterServices/IrcTunnelService.swift
+++ /dev/null
@@ -1,20 +0,0 @@
-//
-//  IrcTunnelService.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 03/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-class IrcTunnelService : Service {
-  
-  override func updateStatus(callback: @escaping (BaseService) -> Void) {
-    defer { callback(self) }
-    
-    self.status = ServiceStatus(rawValue: 0)!
-    self.message = "Dead"
-  }
-  
-}
diff --git a/launchers/macosx/I2PLauncher/routermgmt/Service.swift b/launchers/macosx/I2PLauncher/routermgmt/Service.swift
deleted file mode 100644
index 89af6e83e9664c79232483b7fb1b573c8974509d..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/routermgmt/Service.swift
+++ /dev/null
@@ -1,132 +0,0 @@
-//
-//  Service.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 12/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-public enum ServiceStatus: Int, Comparable {
-  case undetermined
-  case waiting
-  case started
-  case notice
-  case killed
-  case crashed
-  case stopped
-  case restarting
-  
-  public static func < (lhs: ServiceStatus, rhs: ServiceStatus) -> Bool {
-    return lhs.rawValue < rhs.rawValue
-  }
-}
-
-protocol ComparableStatus: Comparable {
-  var serviceStatus: ServiceStatus { get }
-}
-
-extension ComparableStatus {
-  public static func < (lhs: Self, rhs: Self) -> Bool {
-    return lhs.serviceStatus < rhs.serviceStatus
-  }
-}
-
-typealias Service = BaseService & RequiredServiceProperties
-
-protocol RequiredServiceProperties {
-  var name: String { get }
-  //var url: URL { get }
-}
-
-extension RequiredServiceProperties {
-  // Default implementation of the property `name` is to return the class name
-  var name: String { return "\(type(of: self))" }
-}
-
-public class BaseService {
-  public var status: ServiceStatus = .undetermined {
-    didSet {
-      if oldValue == .undetermined || status == .undetermined || oldValue == status {
-        self.shouldNotify = false
-      } else if Preferences.shared().notifyOnStatusChange {
-        self.shouldNotify = true
-      }
-    }
-  }
-  var message: String = "Loading…"
-  var shouldNotify = false
-  
-  public static func all() -> [BaseService] {
-    guard let servicesPlist = Bundle.main.path(forResource: "RouterServices", ofType: "plist"),
-      let services = NSDictionary(contentsOfFile: servicesPlist)?["services"] as? [String] else {
-        fatalError("The RouterServices.plist file does not exist. The build phase script might have failed.")
-    }
-    
-    return services.map(BaseService.named).compactMap { $0 }
-  }
-  
-  static func named(_ name: String) -> BaseService? {
-    return (NSClassFromString("I2PLauncher.\(name)") as? Service.Type)?.init()
-  }
-  
-  public required init() {}
-  
-  public func updateStatus(callback: @escaping (BaseService) -> Void) {}
-  
-  func _fail(_ error: Error?) {
-    self.status = .undetermined
-    self.message = error.debugDescription// ?? "Unexpected error"
-  }
-  
-  func _fail(_ message: String) {
-    self.status = .undetermined
-    self.message = message
-  }
-  
-  func notifyIfNecessary() {
-    guard let realSelf = self as? Service else { fatalError("BaseService should not be used directly.") }
-    
-    guard shouldNotify else { return }
-    
-    self.shouldNotify = false
-    
-    let notification = NSUserNotification()
-    let possessiveS = realSelf.name.hasSuffix("s") ? "'" : "'s"
-    notification.title = "\(realSelf.name)\(possessiveS) status has changed"
-    notification.informativeText = message
-    
-    NSUserNotificationCenter.default.deliver(notification)
-  }
-}
-
-extension BaseService: Equatable {
-  public static func == (lhs: BaseService, rhs: BaseService) -> Bool {
-    guard
-      let lhs = lhs as? Service,
-      let rhs = rhs as? Service
-      else {
-        fatalError("BaseService should not be used directly.")
-    }
-    
-    return lhs.name == rhs.name
-  }
-}
-
-extension BaseService: Comparable {
-  public static func < (lhs: BaseService, rhs: BaseService) -> Bool {
-    guard
-      let lhs = lhs as? Service,
-      let rhs = rhs as? Service
-      else {
-        fatalError("BaseService should not be used directly.")
-    }
-    
-    let sameStatus = lhs.status == rhs.status
-    let differentStatus =
-      lhs.status != .started && lhs.status != .notice
-        && rhs.status == .started || rhs.status == .notice
-    return ((lhs.name < rhs.name) && sameStatus) || differentStatus
-  }
-}
diff --git a/launchers/macosx/I2PLauncher/routermgmt/launchd/LaunchAgent+Status.swift b/launchers/macosx/I2PLauncher/routermgmt/launchd/LaunchAgent+Status.swift
deleted file mode 100644
index 8e1a19245d2bc4c16a6439e0270bec8733a88798..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/routermgmt/launchd/LaunchAgent+Status.swift
+++ /dev/null
@@ -1,69 +0,0 @@
-//
-//  LaunchAgent+Status.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 05/10/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-public enum AgentStatus: Equatable {
-  
-  case running(pid: Int)
-  case loaded
-  case unloaded
-  
-  public static func ==(lhs: AgentStatus, rhs: AgentStatus) -> Bool {
-    switch (lhs, rhs) {
-    case ( let .running(lhpid), let .running(rhpid) ):
-      return lhpid == rhpid
-    case (.loaded, .loaded):
-      return true
-    case (.unloaded, .unloaded):
-      return true
-    default:
-      return false
-    }
-  }
-  
-}
-
-extension LaunchAgent {
-  
-  /// Run `launchctl start` on the agent
-  ///
-  /// Check the status of the job with `.status()`
-  public func start(_ callback: ((Process) -> Void)? = nil ) {
-    LaunchAgentManager.shared.start(self, callback)
-  }
-  
-  /// Run `launchctl stop` on the agent
-  ///
-  /// Check the status of the job with `.status()`
-  public func stop(_ callback: ((Process) -> Void)? = nil ) {
-    LaunchAgentManager.shared.stop(self, callback)
-  }
-  
-  /// Run `launchctl load` on the agent
-  ///
-  /// Check the status of the job with `.status()`
-  public func load() throws {
-    try LaunchAgentManager.shared.load(self)
-  }
-  
-  /// Run `launchctl unload` on the agent
-  ///
-  /// Check the status of the job with `.status()`
-  public func unload() throws {
-    try LaunchAgentManager.shared.unload(self)
-  }
-  
-  /// Retreives the status of the LaunchAgent from `launchctl`
-  ///
-  /// - Returns: the agent's status
-  public func status() -> AgentStatus {
-    return LaunchAgentManager.shared.status(self)
-  }
-  
-}
diff --git a/launchers/macosx/I2PLauncher/routermgmt/launchd/LaunchAgent.swift b/launchers/macosx/I2PLauncher/routermgmt/launchd/LaunchAgent.swift
deleted file mode 100644
index 8428a93a6ff61b3f3fac45af709552313ef3aa5c..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/routermgmt/launchd/LaunchAgent.swift
+++ /dev/null
@@ -1,124 +0,0 @@
-//
-//  LaunchAgent.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 05/10/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-public enum ProcessType: String, Codable {
-  case standard = "Standard"
-  case background = "Background"
-  case adaptive = "Adaptive"
-  case interactive = "Interactive"
-}
-
-public class LaunchAgent: Codable {
-  
-  public var url: URL? = nil
-  
-  // Basic Properties
-  public var label: String
-  public var disabled: Bool? = nil
-  public var enableGlobbing: Bool? = nil
-  public var program: String? = nil {
-    didSet {
-      if program != nil {
-        programArguments = nil
-      }
-    }
-  }
-  
-  public var programArguments: [String]? = nil {
-    didSet {
-      guard let args = programArguments else {
-        return
-      }
-      if args.count == 1 {
-        self.program = args.first
-        programArguments = nil
-      } else {
-        program = nil
-      }
-    }
-  }
-  
-  public var processType: ProcessType? = nil
-  
-  // Program
-  public var workingDirectory: String? = nil
-  public var standardOutPath: String? = nil
-  public var standardErrorPath: String? = nil
-  public var environmentVariables: [String: String]? = nil
-  
-  // Run Conditions
-  public var runAtLoad: Bool? = nil
-  public var startInterval: Int? = nil
-  public var onDemand: Bool? = nil
-  public var keepAlive: Bool? = nil
-  public var watchPaths: [String]? = nil
-  
-  // Security
-  public var umask: Int? = nil
-  // System Daemon Security
-  public var groupName: String? = nil
-  public var userName: String? = nil
-  public var rootDirectory: String? = nil
-  
-  
-  // Run Constriants
-  public var launchOnlyOnce: Bool? = nil
-  public var limitLoadToSessionType: [String]? = nil
-
-  public init(label: String, program: [String]) {
-    self.label = label
-    if program.count == 1 {
-      self.program = program.first
-    } else {
-      self.programArguments = program
-    }
-    
-  }
-  
-  public convenience init(label: String, program: String...) {
-    self.init(label: label, program: program)
-  }
-  
-  public enum CodingKeys: String, CodingKey {
-    case label = "Label"
-    case disabled = "Disabled"
-    case program = "Program"
-    case programArguments = "ProgramArguments"
-    
-    // Program
-    case workingDirectory = "WorkingDirectory"
-    case standardOutPath = "StandardOutPath"
-    case standardErrorPath = "StandardErrorPath"
-    case environmentVariables = "EnvironmentVariables"
-    
-    // Run Conditions
-    case runAtLoad = "RunAtLoad"
-    case startInterval = "StartInterval"
-    case onDemand = "OnDemand"
-    case keepAlive = "KeepAlive"
-    case watchPaths = "WatchPaths"
-    
-    // Security
-    case umask = "Umask"
-    case groupName = "GroupName"
-    case userName = "UserName"
-    case rootDirectory = "RootDirectory"
-    
-    // Run Constriants
-    case launchOnlyOnce = "LaunchOnlyOnce"
-    case limitLoadToSessionType = "LimitLoadToSessionType"
-    
-    // Process type
-    case processType = "ProcessType"
-    
-  }
-  
-  
-}
diff --git a/launchers/macosx/I2PLauncher/routermgmt/launchd/LaunchAgentManager.swift b/launchers/macosx/I2PLauncher/routermgmt/launchd/LaunchAgentManager.swift
deleted file mode 100644
index b9c26c78f891f99d580527cfdd491a372d353baa..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/routermgmt/launchd/LaunchAgentManager.swift
+++ /dev/null
@@ -1,203 +0,0 @@
-//
-//  LaunchAgentManager.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 07/10/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-
-public enum LaunchAgentManagerError: Swift.Error {
-  case urlNotSet(label: String)
-  
-  public var localizedDescription: String {
-    switch self {
-    case .urlNotSet(let label):
-      return "The URL is not set for agent \(label)"
-    }
-  }
-}
-
-public class LaunchAgentManager {
-  public static let shared = LaunchAgentManager()
-  
-  static let launchctl = "/bin/launchctl"
-  
-  var lastState: AgentStatus?
-  
-  let encoder = PropertyListEncoder()
-  let decoder = PropertyListDecoder()
-  
-  init() {
-    encoder.outputFormat = .xml
-  }
-  
-  func launchAgentsURL() throws -> URL {
-    let library = try FileManager.default.url(for: .libraryDirectory, in: .userDomainMask, appropriateFor: nil, create: false)
-    
-    return library.appendingPathComponent("LaunchAgents")
-  }
-  
-  public func read(agent called: String) throws -> LaunchAgent {
-    let url = try launchAgentsURL().appendingPathComponent(called)
-    
-    return try read(from: url)
-  }
-  
-  public func read(from url: URL) throws -> LaunchAgent {
-    return try decoder.decode(LaunchAgent.self, from: Data(contentsOf: url))
-  }
-  
-  public func write(_ agent: LaunchAgent, called: String) throws {
-    let url = try launchAgentsURL().appendingPathComponent(called)
-    
-    try write(agent, to: url)
-  }
-  
-  public func write(_ agent: LaunchAgent, to url: URL) throws {
-    try encoder.encode(agent).write(to: url)
-    
-    agent.url = url
-  }
-  
-  public func setURL(for agent: LaunchAgent) throws {
-    let contents = try FileManager.default.contentsOfDirectory(
-      at: try launchAgentsURL(),
-      includingPropertiesForKeys: nil,
-      options: [.skipsPackageDescendants, .skipsHiddenFiles, .skipsSubdirectoryDescendants]
-    )
-    
-    contents.forEach { url in
-      let testAgent = try? self.read(from: url)
-      
-      if agent.label == testAgent?.label {
-        agent.url = url
-        return
-      }
-    }
-    
-    
-  }
-  
-}
-
-extension LaunchAgentManager {
-  
-  /// Run `launchctl start` on the agent
-  ///
-  /// Check the status of the job with `.status(_: LaunchAgent)`
-  public func start(_ agent: LaunchAgent, _ termHandler: ((Process) -> Void)? = nil ) {
-    let arguments = ["start", agent.label]
-    let proc = Process.launchedProcess(launchPath: LaunchAgentManager.launchctl, arguments: arguments)
-    if ((termHandler) != nil) {
-      proc.terminationHandler = termHandler
-    }
-  }
-  
-  /// Run `launchctl stop` on the agent
-  ///
-  /// Check the status of the job with `.status(_: LaunchAgent)`
-  public func stop(_ agent: LaunchAgent, _ termHandler: ((Process) -> Void)? = nil ) {
-    let arguments = ["stop", agent.label]
-    let proc = Process.launchedProcess(launchPath: LaunchAgentManager.launchctl, arguments: arguments)
-    if ((termHandler) != nil) {
-      proc.terminationHandler = termHandler
-    }
-  }
-  
-  /// Run `launchctl load` on the agent
-  ///
-  /// Check the status of the job with `.status(_: LaunchAgent)`
-  public func load(_ agent: LaunchAgent, _ termHandler: ((Process) -> Void)? = nil ) throws {
-    guard let agentURL = agent.url else {
-      throw LaunchAgentManagerError.urlNotSet(label: agent.label)
-    }
-    
-    let arguments = ["load", agentURL.path]
-    let proc = Process.launchedProcess(launchPath: LaunchAgentManager.launchctl, arguments: arguments)
-    if ((termHandler) != nil) {
-      proc.terminationHandler = termHandler
-    }
-  }
-  
-  /// Run `launchctl unload` on the agent
-  ///
-  /// Check the status of the job with `.status(_: LaunchAgent)`
-  public func unload(_ agent: LaunchAgent, _ termHandler: ((Process) -> Void)? = nil ) throws {
-    guard let agentURL = agent.url else {
-      throw LaunchAgentManagerError.urlNotSet(label: agent.label)
-    }
-    
-    let arguments = ["unload", agentURL.path]
-    let proc = Process.launchedProcess(launchPath: LaunchAgentManager.launchctl, arguments: arguments)
-    if ((termHandler) != nil) {
-      proc.terminationHandler = termHandler
-    }
-  }
-  
-  /// Retreives the status of the LaunchAgent from `launchctl`
-  ///
-  /// - Returns: the agent's status
-  public func status(_ agent: LaunchAgent) -> AgentStatus {
-    
-    let launchctlTask = Process()
-    let grepTask = Process()
-    let cutTask = Process()
-    
-    launchctlTask.launchPath = "/bin/launchctl"
-    launchctlTask.arguments = ["list"]
-    
-    grepTask.launchPath = "/usr/bin/grep"
-    grepTask.arguments = [agent.label]
-    
-    cutTask.launchPath = "/usr/bin/cut"
-    cutTask.arguments = ["-f1"]
-    
-    let pipeLaunchCtlToGrep = Pipe()
-    launchctlTask.standardOutput = pipeLaunchCtlToGrep
-    grepTask.standardInput = pipeLaunchCtlToGrep
-    
-    let pipeGrepToCut = Pipe()
-    grepTask.standardOutput = pipeGrepToCut
-    cutTask.standardInput = pipeGrepToCut
-    
-    let pipeCutToFile = Pipe()
-    cutTask.standardOutput = pipeCutToFile
-    
-    let fileHandle: FileHandle = pipeCutToFile.fileHandleForReading as FileHandle
-    
-    launchctlTask.launch()
-    grepTask.launch()
-    cutTask.launch()
-    
-    
-    let data = fileHandle.readDataToEndOfFile()
-    let stringResult = String(data: data, encoding: .utf8)?.trimmingCharacters(in: .newlines) ?? ""
-    
-    let em = RouterManager.shared().eventManager
-    
-    switch stringResult {
-    case "-":
-      if (self.lastState != AgentStatus.loaded) {
-        self.lastState = AgentStatus.loaded
-        em.trigger(eventName: "launch_agent_loaded")
-      }
-
-      return .loaded
-    case "":
-      if (self.lastState != AgentStatus.unloaded) {
-        self.lastState = AgentStatus.unloaded
-        em.trigger(eventName: "launch_agent_unloaded")
-      }
-      return .unloaded
-    default:
-      if (self.lastState != AgentStatus.running(pid: Int(stringResult)!)) {
-        self.lastState = AgentStatus.running(pid: Int(stringResult)!)
-        em.trigger(eventName: "launch_agent_running")
-      }
-      return .running(pid: Int(stringResult)!)
-    }
-  }
-}
diff --git a/launchers/macosx/I2PLauncher/subprocesses/AppleStuffExceptionHandler.h b/launchers/macosx/I2PLauncher/subprocesses/AppleStuffExceptionHandler.h
deleted file mode 100644
index fc9fd98770aa028be36ec211d70bc957cef74e4a..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/subprocesses/AppleStuffExceptionHandler.h
+++ /dev/null
@@ -1,12 +0,0 @@
-//
-//  AppleStuffExceptionHandler.h
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 17/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-#import <Foundation/Foundation.h>
-
-extern NSException* __nullable AppleStuffExecuteWithPossibleExceptionInBlock(dispatch_block_t _Nonnull block);
-
diff --git a/launchers/macosx/I2PLauncher/subprocesses/AppleStuffExceptionHandler.m b/launchers/macosx/I2PLauncher/subprocesses/AppleStuffExceptionHandler.m
deleted file mode 100644
index 951a38355b1518c72df840fcd109761c26b5311f..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/subprocesses/AppleStuffExceptionHandler.m
+++ /dev/null
@@ -1,22 +0,0 @@
-//
-//  AppleStuffExceptionHandler.m
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 17/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-#import "AppleStuffExceptionHandler.h"
-
-NSException* __nullable AppleStuffExecuteWithPossibleExceptionInBlock(dispatch_block_t _Nonnull block) {
-  
-  @try {
-    if (block != nil) {
-      block();
-    }
-  }
-  @catch (NSException *exception) {
-    return exception;
-  }
-  return nil;
-}
diff --git a/launchers/macosx/I2PLauncher/subprocesses/Error.swift b/launchers/macosx/I2PLauncher/subprocesses/Error.swift
deleted file mode 100644
index cc3cfe02a0cfa3c5b72b9724457f2920432c2ff1..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/subprocesses/Error.swift
+++ /dev/null
@@ -1,22 +0,0 @@
-//
-//  Error.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 17/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-public class Error {
-  
-  /// Prints to console the arguments and exits with status 1
-  static func die(arguments: Any...) -> Never  {
-    let output = "ERROR: " + arguments.reduce("") { $0 + "\($1) " }
-    let trimOutput = output.trimmingCharacters(in: CharacterSet.whitespaces) + "\n"
-    let stderr = FileHandle.standardError
-    stderr.write(trimOutput.data(using: String.Encoding.utf8)!)
-    exit(1)
-  }
-}
-
diff --git a/launchers/macosx/I2PLauncher/subprocesses/ExecutionResult.swift b/launchers/macosx/I2PLauncher/subprocesses/ExecutionResult.swift
deleted file mode 100644
index f482bfd206a3fd36dcea2de3bd2288b8a55d96c1..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/subprocesses/ExecutionResult.swift
+++ /dev/null
@@ -1,63 +0,0 @@
-//
-//  ExecutionResult.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 17/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-public struct ExecutionResult {
-  
-  /// Whether the output was captured
-  public let didCaptureOutput : Bool
-  
-  /// The return status of the last subprocess
-  public var status: Int32 {
-    return pipelineStatuses.last!
-  }
-  
-  /// Return status of all subprocesses in the pipeline
-  public let pipelineStatuses : [Int32]
-  
-  /// The output of the subprocess. Empty string if no output was produced or not captured
-  public let output: String
-  
-  /// The error output of the last subprocess. Empty string if no error output was produced or not captured
-  public var errors : String {
-    return pipelineErrors?.last ?? ""
-  }
-  
-  /// The error output of all subprocesses in the pipeline. Empty string if no error output was produced or not captured
-  public let pipelineErrors : [String]?
-  
-  /// The output, split by newline
-  /// - SeeAlso: `output`
-  public var outputLines : [String] {
-    return self.output.splitByNewline()
-  }
-  
-  /// The error output, split by newline
-  /// - SeeAlso: `output`
-  public var errorsLines : [String] {
-    return self.errors.splitByNewline()
-  }
-  
-  /// An execution result where no output was captured
-  init(pipelineStatuses: [Int32]) {
-    self.pipelineStatuses = pipelineStatuses
-    self.didCaptureOutput = false
-    self.pipelineErrors = nil
-    self.output = ""
-  }
-  
-  /// An execution result where output was captured
-  init(pipelineStatuses: [Int32], pipelineErrors : [String], output : String) {
-    self.pipelineStatuses = pipelineStatuses
-    self.pipelineErrors = pipelineErrors
-    self.output = output
-    self.didCaptureOutput = true
-  }
-}
-
diff --git a/launchers/macosx/I2PLauncher/subprocesses/Subprocess+CompactAPI.swift b/launchers/macosx/I2PLauncher/subprocesses/Subprocess+CompactAPI.swift
deleted file mode 100644
index cb472e0c3050178c637f8552e762329557515705..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/subprocesses/Subprocess+CompactAPI.swift
+++ /dev/null
@@ -1,118 +0,0 @@
-//
-//  Subprocess+CompactAPI.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 17/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-
-// MARK: - Compact API
-extension Subprocess {
-  
-  /**
-   Executes a subprocess and wait for completion, returning the output. If there is an error in creating the task,
-   it immediately exits the process with status 1
-   - returns: the output as a String
-   - note: in case there is any error in executing the process or creating the task, it will halt execution. Use
-   the constructor and `output` instance method for a more graceful error handling
-   */
-  public static func output(
-    executablePath: String,
-    _ arguments: String...,
-    workingDirectory: String = ".") -> String {
-    
-    let process = Subprocess.init(executablePath: executablePath, arguments: arguments, workingDirectory: workingDirectory)
-    guard let result = process.execute(captureOutput: true) else {
-      Error.die(arguments: "Can't execute \"\(process)\"")
-    }
-    if result.status != 0 {
-      let errorLines = result.errors == "" ? "" : "\n" + result.errors
-      Error.die(arguments: "Process \"\(process)\" returned status \(result.status)", errorLines)
-    }
-    return result.output
-  }
-  
-  /**
-   Executes a subprocess and wait for completion, returning the execution result. If there is an error in creating the task,
-   it immediately exits the process with status 1
-   - returns: the execution result
-   - note: in case there is any error in executing the process or creating the task, it will halt execution. Use
-   the constructor and `execute` instance method for a more graceful error handling
-   */
-  public static func execute(
-    executablePath: String,
-    _ arguments: String...,
-    workingDirectory: String = ".") -> ExecutionResult {
-    
-    let process = Subprocess.init(executablePath: executablePath, arguments: arguments, workingDirectory: workingDirectory)
-    guard let result = process.execute(captureOutput: true) else {
-      Error.die(arguments: "Can't execute \"\(process)\"")
-    }
-    return result
-  }
-  
-  /**
-   Executes a subprocess and wait for completion, returning the output as an array of lines. If there is an error
-   in creating or executing the task, it immediately exits the process with status 1
-   - returns: the output as a String
-   - note: in case there is any error in executing the process or creating the task, it will halt execution. Use
-   the constructor and `output` instance method for a more graceful error handling
-   */
-  public static func outputLines(
-    executablePath: String,
-    _ arguments: String...,
-    workingDirectory: String = ".") -> [String] {
-    
-    let process = Subprocess.init(executablePath: executablePath, arguments: arguments, workingDirectory: workingDirectory)
-    guard let result = process.execute(captureOutput: true) else {
-      Error.die(arguments: "Can't execute \"\(process)\"")
-    }
-    if result.status != 0 {
-      let errorLines = result.errors == "" ? "" : "\n" + result.errors
-      Error.die(arguments: "Process \"\(process)\" returned status \(result.status)", errorLines)
-    }
-    return result.outputLines
-  }
-  
-  /**
-   Executes a subprocess and wait for completion, returning the exit status. If there is an error in creating the task,
-   it immediately exits the process with status 1
-   - returns: the output as a String
-   - note: in case there is any error in launching the process or creating the task, it will halt execution. Use
-   the constructor and the `run` instance method for a more graceful error handling
-   */
-  public static func run(
-    executablePath: String,
-    _ arguments: String...,
-    workingDirectory: String = ".") -> Int32 {
-    
-    let process = Subprocess.init(executablePath: executablePath, arguments: arguments, workingDirectory: workingDirectory)
-    guard let result = process.run() else {
-      Error.die(arguments: "Can't execute \"\(process)\"")
-    }
-    return result
-  }
-  
-  /**
-   Executes a subprocess and wait for completion. If there is an error in creating the task, or if the tasks
-   returns an exit status other than 0, it immediately exits the process with status 1
-   - note: in case there is any error in launching the process or creating the task, or if the task exists with a exit status other than 0, it will halt execution. Use
-   the constructor and `run` instance method for a more graceful error handling
-   */
-  public static func runOrDie(
-    executablePath: String,
-    _ arguments: String...,
-    workingDirectory: String = ".") {
-    
-    let process =  Subprocess.init(executablePath: executablePath, arguments: arguments, workingDirectory: workingDirectory)
-    guard let result = process.run() else {
-      Error.die(arguments: "Can't execute \"\(process)\"")
-    }
-    if result != 0 {
-      Error.die(arguments: "Process \"\(process)\" returned status \(result)")
-    }
-  }
-}
diff --git a/launchers/macosx/I2PLauncher/subprocesses/Subprocess.swift b/launchers/macosx/I2PLauncher/subprocesses/Subprocess.swift
deleted file mode 100644
index 2b83e747a2d30cd13d4bbb16b542c7580bd8fa24..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/subprocesses/Subprocess.swift
+++ /dev/null
@@ -1,159 +0,0 @@
-//
-//  Subprocess.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 17/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-
-public class Subprocess {
-  /// The path to the executable
-  let executablePath : String
-
-  /// Arguments to pass to the executable
-  let arguments : [String]
-
-  /// Working directory for the executable
-  let workingDirectory : String
-
-  /// Process to pipe to, if any
-  let pipeDestination : Subprocess?
-  
-  public convenience init(
-    executablePath: String,
-    arguments: [String] = [],
-    workingDirectory: String = "."
-    ) {
-    self.init(executablePath: executablePath,
-              arguments: arguments,
-              workingDirectory: workingDirectory,
-              pipeTo: nil)
-  }
-  
-  public init(
-    executablePath: String,
-    arguments: [String] = [],
-    workingDirectory: String = ".",
-    pipeTo: Subprocess?
-    ) {
-    self.executablePath = executablePath
-    self.arguments = arguments
-    self.workingDirectory = workingDirectory
-    self.pipeDestination = pipeTo
-  }
-  
-  /**
-   Returns a subprocess ready to be executed
-   - SeeAlso: init(executablePath:arguments:workingDirectory)
-   */
-  public convenience init(
-    _ executablePath: String,
-    _ arguments: String...,
-    workingDirectory: String = ".") {
-    self.init(executablePath: executablePath, arguments: arguments, workingDirectory: workingDirectory, pipeTo: nil)
-  }
-}
-
-// Public API
-extension Subprocess {
-  
-  /**
-   Executes the subprocess and wait for completition, returning the exit status
-   - returns: the termination status, or nil if it was not possible to execute the process
-   */
-  public func run() -> Int32? {
-    return self.execute(captureOutput: false)?.status
-  }
-  
-  /**
-   Executes the subprocess and wait for completion, returning the output
-   - returns: the output of the process, or nil if it was not possible to execute the process
-   - warning: the entire output will be stored in a String in memory
-   */
-  public func output() -> String? {
-    return self.execute(captureOutput: true)?.output
-  }
-  
-  /**
-   Executes the subprocess and wait for completition, returning the exit status
-   - returns: the execution result, or nil if it was not possible to execute the process
-   */
-  public func execute(captureOutput: Bool = false) -> ExecutionResult? {
-    return buildPipeline(captureOutput: captureOutput).run()
-  }
-}
-
-// Piping of STDIN, STDERR and STDOUT
-extension Subprocess {
-  
-  /// Pipes the output to this process to another process.
-  /// Will return a new subprocess, you should execute that subprocess to
-  /// run the entire pipe
-  public func pipe(to destination: Subprocess) -> Subprocess {
-    let downstreamProcess : Subprocess
-    if let existingPipe = self.pipeDestination {
-      downstreamProcess = existingPipe.pipe(to: destination)
-    } else {
-      downstreamProcess = destination
-    }
-    return Subprocess(executablePath: self.executablePath, arguments: self.arguments, workingDirectory: self.workingDirectory, pipeTo: downstreamProcess)
-  }
-}
-
-public func | (lhs: Subprocess, rhs: Subprocess) -> Subprocess {
-  return lhs.pipe(to: rhs)
-}
-
-public func | (lhs: String, rhs: String) -> String {
-  return "(\(lhs)\(rhs))"
-}
-
-// MARK: - Process execution
-public enum SubprocessError : LocalizedError {
-  case Error(status: Int, message: String)
-}
-
-extension Subprocess {
-  
-  /// Returns the task to execute
-  private func task() -> Process {
-    let task = Process()
-    task.launchPath = self.executablePath
-    task.arguments = self.arguments
-    task.currentDirectoryPath = self.workingDirectory
-    return task
-  }
-  
-  /// Returns the task pipeline for all the downstream processes
-  public func buildPipeline(captureOutput: Bool, input: AnyObject? = nil) -> TaskPipeline {
-    let task = self.task()
-    
-    if let inPipe = input {
-      task.standardInput = inPipe
-    }
-    
-    if let downstreamProcess = self.pipeDestination {
-      let downstreamPipeline = downstreamProcess.buildPipeline(captureOutput: captureOutput, input: task.standardOutput as AnyObject)
-      return downstreamPipeline.addToHead(task: task)
-    }
-    return TaskPipeline(task: task, captureOutput: captureOutput)
-  }
-}
-
-// Description for pretty print etc.
-extension Subprocess  : CustomStringConvertible {
-  
-  public var description : String {
-    return self.executablePath
-      + (self.arguments.count > 0
-        ? " " + self.arguments
-          .map { $0.replace(target: "\\ ", withString: " ") }
-          .joined(separator: " ")
-        : ""
-      )
-      + (self.pipeDestination != nil ? " | " + self.pipeDestination!.description : "" )
-  }
-}
diff --git a/launchers/macosx/I2PLauncher/subprocesses/TaskPipeline.swift b/launchers/macosx/I2PLauncher/subprocesses/TaskPipeline.swift
deleted file mode 100644
index 2021692069dae4125506389619d10d19167237e2..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/subprocesses/TaskPipeline.swift
+++ /dev/null
@@ -1,113 +0,0 @@
-//
-//  TaskPipeline.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 17/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-
-// Extend the stdlib with the extension bellow
-extension Process {
-  /// Launches a task, captures any objective-c exception and relaunches it as Swift error
-  public func launchCapturingExceptions() throws {
-    if let exception = AppleStuffExecuteWithPossibleExceptionInBlock({
-      self.launch()
-    }) {
-      let reason = exception.reason ?? "unknown error"
-      throw SubprocessError.Error(status: -1, message: reason)
-    }
-  }
-}
-
-/// A pipeline of tasks, connected in a cascade pattern with pipes
-public struct TaskPipeline {
-  
-  /// List of tasks in the pipeline
-  let tasks: [Process]
-  
-  /// Output pipe
-  let outputPipe: Pipe?
-  
-  /// Whether the pipeline should capture output to stdErr and stdOut
-  let captureOutput : Bool
-  
-  /// Adds a task to the head of the pipeline, that is, the task will provide the input
-  /// for the first task currently on the head of the pipeline
-  func addToHead(task: Process) -> TaskPipeline {
-    guard let firstTask = tasks.first else {
-      fatalError("Expecting at least one task")
-    }
-    let inoutPipe = Pipe()
-    firstTask.standardInput = inoutPipe
-    task.standardOutput = inoutPipe
-    
-    var errorPipe : Pipe?
-    if self.captureOutput {
-      errorPipe = Pipe()
-      task.standardError = errorPipe
-    }
-    return TaskPipeline(tasks: [task] + self.tasks, outputPipe: self.outputPipe, captureOutput: self.captureOutput)
-  }
-  
-  /// Start all tasks in the pipeline, then wait for them to complete
-  /// - returns: the return status of the last process in the pipe, or nil if there was an error
-  func run() -> ExecutionResult? {
-    
-    let runTasks = launchAndReturnNotFailedTasks()
-    if runTasks.count != self.tasks.count {
-      // dropped a task? it's because it failed to start, so error
-      return nil
-    }
-    runTasks.forEach { $0.waitUntilExit() }
-    
-    // exit status
-    let exitStatuses = runTasks.map { $0.terminationStatus }
-    guard captureOutput else {
-      return ExecutionResult(pipelineStatuses: exitStatuses)
-    }
-    
-    // output
-    let errorOutput = runTasks.map { task -> String in
-      guard let errorPipe = task.standardError as? Pipe else { return "" }
-      let readData = errorPipe.fileHandleForReading.readDataToEndOfFile()
-      return String(data: readData, encoding: String.Encoding.utf8)!
-    }
-    let output = String(data: self.outputPipe!.fileHandleForReading.readDataToEndOfFile(), encoding: String.Encoding.utf8)!
-    return ExecutionResult(pipelineStatuses: exitStatuses, pipelineErrors: errorOutput, output: output)
-  }
-  
-  /// Run all tasks and return the tasks that did not fail to launch
-  private func launchAndReturnNotFailedTasks() -> [Process] {
-    return self.tasks.compactMap { task -> Process? in
-      do {
-        try task.launchCapturingExceptions()
-        return task
-      } catch {
-        return nil
-      }
-    }
-  }
-  
-  init(task: Process, captureOutput: Bool) {
-    self.tasks = [task]
-    self.captureOutput = captureOutput
-    if captureOutput {
-      self.outputPipe = Pipe()
-      task.standardOutput = self.outputPipe
-      let errorPipe = Pipe()
-      task.standardError = errorPipe
-    } else {
-      self.outputPipe = nil
-    }
-  }
-  
-  private init(tasks: [Process], outputPipe: Pipe?, captureOutput: Bool) {
-    self.tasks = tasks
-    self.outputPipe = outputPipe
-    self.captureOutput = captureOutput
-  }
-}
-
diff --git a/launchers/macosx/I2PLauncher/userinterface/DownloadJavaViewController.swift b/launchers/macosx/I2PLauncher/userinterface/DownloadJavaViewController.swift
deleted file mode 100644
index 43e6c8a673623af82fcdddbb663cf1da116e088f..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/DownloadJavaViewController.swift
+++ /dev/null
@@ -1,34 +0,0 @@
-//
-//  DownloadJavaViewController.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 30/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import AppKit
-
-class DownloadJavaViewController: NSViewController {
-  
-  func urlSession(_ session: URLSession, downloadTask: URLSessionDownloadTask,
-                  didFinishDownloadingTo location: URL) {
-    guard let httpResponse = downloadTask.response as? HTTPURLResponse,
-      (200...299).contains(httpResponse.statusCode) else {
-        print ("server error")
-        return
-    }
-    do {
-      let documentsURL = try
-        FileManager.default.url(for: .documentDirectory,
-                                in: .userDomainMask,
-                                appropriateFor: nil,
-                                create: false)
-      let savedURL = documentsURL.appendingPathComponent(
-        location.lastPathComponent)
-      try FileManager.default.moveItem(at: location, to: savedURL)
-    } catch {
-      print ("file error: \(error)")
-    }
-  }
-  
-}
diff --git a/launchers/macosx/I2PLauncher/userinterface/LogViewController.swift b/launchers/macosx/I2PLauncher/userinterface/LogViewController.swift
deleted file mode 100644
index 0b62b2f04edda3b80d2a778de83f63ad39d2b73b..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/LogViewController.swift
+++ /dev/null
@@ -1,62 +0,0 @@
-//
-//  LogViewController.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 18/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Foundation
-import AppKit
-
-class LogViewerViewController : NSTabViewItem {
-  
-  @IBOutlet var scrollView: NSScrollView?
-  @IBOutlet var textFieldView: NSTextView?
-  
-  private var outputPipe : Pipe?
-  
-  override init(identifier: Any?) {
-    super.init(identifier: identifier)
-    self.captureStandardOutputAndRouteToTextView()
-  }
-  
-  required init?(coder aDecoder: NSCoder) {
-    super.init(coder: aDecoder)
-    self.captureStandardOutputAndRouteToTextView()
-  }
-  
-  
-  func captureStandardOutputAndRouteToTextView() {
-    outputPipe = RouterManager.shared().getRouterTask()?.processPipe
-    outputPipe?.fileHandleForReading.waitForDataInBackgroundAndNotify()
-    
-    NotificationCenter.default.addObserver(forName: NSNotification.Name.NSFileHandleDataAvailable, object: outputPipe?.fileHandleForReading , queue: nil) {
-      notification in
-
-      let output = self.outputPipe?.fileHandleForReading.availableData
-      let outputString = String(data: output!, encoding: String.Encoding.utf8) ?? ""
-      let workTask = DispatchWorkItem {
-        let previousOutput = self.textFieldView?.string ?? ""
-        let nextOutput = previousOutput + "\n" + outputString
-        self.textFieldView?.string = nextOutput
-        
-        let range = NSRange(location:nextOutput.count,length:0)
-        self.textFieldView?.scrollRangeToVisible(range)
-      }
-      DispatchQueue.main.async(execute: workTask)
-      
-      // When router stop, stop the stream as well. If not it will go wild and create high cpu load
-      RouterManager.shared().eventManager.listenTo(eventName: "router_stop", action: {
-        NSLog("Time to cancel stream!")
-        workTask.cancel()
-      })
-      
-      
-      self.outputPipe?.fileHandleForReading.waitForDataInBackgroundAndNotify()
-    }
-    
-  }
-}
-
-
diff --git a/launchers/macosx/I2PLauncher/userinterface/PopoverViewController.swift b/launchers/macosx/I2PLauncher/userinterface/PopoverViewController.swift
deleted file mode 100644
index fa79938e1f18cb9e972243df46280759cfb07cf1..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/PopoverViewController.swift
+++ /dev/null
@@ -1,47 +0,0 @@
-//
-//  PopoverViewController.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 18/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-
-class PopoverViewController: NSViewController {
-  
-  @IBOutlet var routerStatusViewOutlet: RouterStatusView?
-  
-  func getRouterStatusView() -> RouterStatusView? {
-    return self.routerStatusViewOutlet
-  }
-  
-  required init?(coder: NSCoder) {
-    super.init(coder: coder)
-  }
-  
-  @IBAction func onPreferencesClick(_ sender: Any) {
-    StatusBarController.launchPreferences(sender)
-  }
-  
-  override func viewDidLoad() {
-    super.viewDidLoad()
-    // Do view setup here.
-  }
-}
-
-
-extension PopoverViewController {
-  static func freshController() -> PopoverViewController {
-    let storyboard = NSStoryboard(name: "Storyboard", bundle: Bundle.main)
-    //2.
-    let identifier = NSStoryboard.SceneIdentifier(stringLiteral: "PopoverView")
-    //3.
-    guard let viewcontroller = storyboard.instantiateController(withIdentifier: identifier as String) as? PopoverViewController else {
-      fatalError("Why cant i find PopoverViewController? - Check PopoverViewController.storyboard")
-    }
-    //let viewcontroller = PopoverViewController()
-    return viewcontroller
-  }
-}
-
diff --git a/launchers/macosx/I2PLauncher/userinterface/RouterStatusView.swift b/launchers/macosx/I2PLauncher/userinterface/RouterStatusView.swift
deleted file mode 100644
index 67cd2847e203e62932534617d72f47e30788563e..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/RouterStatusView.swift
+++ /dev/null
@@ -1,236 +0,0 @@
-//
-//  RouterStatusView.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 22/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-
-@objc class RouterStatusView : NSView {
-  static var instance: RouterStatusView?
-  
-  static func getInstance() -> RouterStatusView? {
-    if (self.instance != Optional.none) {
-      return RouterStatusView.instance
-    }
-    return Optional.none
-  }
-  
-  var isFirefoxEnabled = false
-  
-  @IBOutlet var routerStatusLabel: NSTextField?
-  @IBOutlet var routerVersionLabel: NSTextField?
-  @IBOutlet var routerStartedByLabel: NSTextField?
-  @IBOutlet var routerUptimeLabel: NSTextField?
-  @IBOutlet var routerPIDLabel: NSTextField?
-  
-  
-  @IBOutlet var quickControlView: NSView?
-  @IBOutlet var routerStartStopButton: NSButton?
-  @IBOutlet var openConsoleButton: NSButton?
-  @IBOutlet var launchFirefoxButton: NSButton?
-  
-  
-  @objc func actionBtnOpenConsole(_ sender: Any?) {
-    SwiftApplicationDelegate.openLink(url: "http://localhost:7657")
-  }
-  
-  @objc func actionBtnStartRouter(_ sender: Any?) {
-    NSLog("Router start clicked")
-    (sender as! NSButton).isTransparent = true
-    let routerStatus = RouterRunner.launchAgent?.status()
-    DispatchQueue(label: "background_start").async {
-      switch routerStatus {
-      case .loaded?:
-        RouterManager.shared().routerRunner.StartAgent(RouterRunner.launchAgent)
-      case .unloaded?:
-        do {
-          try LaunchAgentManager.shared.load(RouterRunner.launchAgent!)
-          RouterManager.shared().routerRunner.StartAgent(RouterRunner.launchAgent)
-        } catch {
-          RouterManager.shared().eventManager.trigger(eventName: "router_exception", information: error)
-        }
-        break
-      default:
-        break
-      }
-      DispatchQueue.main.async {
-        self.reEnableButton()
-      }
-    }
-  }
-  
-  @objc func actionBtnStopRouter(_ sender: Any?) {
-    NSLog("Router stop clicked")
-    DispatchQueue(label: "background_shutdown").async {
-      RouterManager.shared().routerRunner.StopAgent({
-        RouterProcessStatus.isRouterRunning = false
-        RouterProcessStatus.isRouterChildProcess = false
-        NSLog("Router should be stopped by now.")
-      })
-      // Wait for it to die.
-      
-    }
-    RouterManager.shared().eventManager.trigger(eventName: "toggle_popover")
-    self.reEnableButton()
-  }
-  
-  @objc func actionBtnLaunchFirefox(_ sender: Any?) {
-    DispatchQueue.global(qos: .background).async {
-      Swift.print("Starting firefox")
-      let _ = FirefoxManager.shared().executeFirefox()
-    }
-  }
-  
-  func restartFn() {
-    RouterManager.shared().routerRunner.StopAgent({
-      sleep(30)
-      RouterManager.shared().routerRunner.StartAgent()
-    })
-  }
-  
-  func handlerRouterStart(information:Any?) {
-    NSLog("Triggered handlerRouterStart")
-    NSLog("PID2! %@", information as! String)
-    routerPIDLabel?.cell?.stringValue = "Router PID: "+(information as! String)
-    routerPIDLabel?.needsDisplay = true
-    routerStatusLabel?.cell?.stringValue = "Router status: Running"
-    RouterManager.shared().lastRouterPid = (information as? String)
-    self.toggleSetButtonStop()
-    self.reEnableButton()
-  }
-  
-  func reEnableButton() {
-    let currentStatus : AgentStatus = RouterRunner.launchAgent?.status() ?? AgentStatus.unloaded
-    if currentStatus != AgentStatus.loaded && currentStatus != AgentStatus.unloaded  {
-      self.toggleSetButtonStop()
-    } else {
-      self.toggleSetButtonStart()
-    }
-    routerStartStopButton?.isTransparent = false
-    routerStartStopButton?.needsDisplay = true
-    self.setRouterStatusLabelText()
-  }
-  
-  func setupObservers() {
-    RouterManager.shared().eventManager.listenTo(eventName: "router_start", action: handlerRouterStart)
-    RouterManager.shared().eventManager.listenTo(eventName: "router_stop", action: handleRouterStop)
-    RouterManager.shared().eventManager.listenTo(eventName: "router_pid", action: handlerRouterStart)
-    RouterManager.shared().eventManager.listenTo(eventName: "launch_agent_running", action: reEnableButton)
-    RouterManager.shared().eventManager.listenTo(eventName: "launch_agent_unloaded", action: reEnableButton)
-    RouterManager.shared().eventManager.listenTo(eventName: "launch_agent_loaded", action: reEnableButton)
-  }
-  
-  func setupFirefoxBtn() {
-    DispatchQueue.global(qos: .background).async {
-      if (FirefoxManager.shared().IsFirefoxFound() && !self.isFirefoxEnabled) {
-        Swift.print("Enabling Firefox Launch Button")
-        DispatchQueue.main.async {
-          self.isFirefoxEnabled = true
-          self.launchFirefoxButton?.isEnabled = true
-          self.launchFirefoxButton?.isTransparent = false
-          self.launchFirefoxButton?.needsDisplay = true
-          self.launchFirefoxButton?.action = #selector(self.actionBtnLaunchFirefox(_:))
-          self.launchFirefoxButton?.target = self
-        }
-      }
-    }
-  }
-  
-  override func viewWillDraw() {
-    super.viewWillDraw()
-    if (RouterStatusView.instance != nil) {
-      RouterStatusView.instance = self
-    }
-    self.reEnableButton()
-    openConsoleButton?.cell?.action = #selector(self.actionBtnOpenConsole(_:))
-    openConsoleButton?.cell?.target = self
-    
-  }
-  
-  func handleRouterStop() {
-    routerPIDLabel?.cell?.stringValue = "Router PID: Not running"
-    RouterManager.shared().lastRouterPid = nil
-    self.toggleSetButtonStart()
-    reEnableButton()
-  }
-  
-  private func toggleSetButtonStart() {
-    routerStatusLabel?.cell?.stringValue = "Router status: Not running"
-    routerStartStopButton?.title = "Start Router"
-    routerStartStopButton?.action = #selector(self.actionBtnStartRouter(_:))
-  }
-  
-  private func toggleSetButtonStop() {
-    routerStatusLabel?.cell?.stringValue = "Router status: Running"
-    routerStartStopButton?.title = "Stop Router"
-    routerStartStopButton?.action = #selector(self.actionBtnStopRouter(_:))
-  }
-  
-  func setRouterStatusLabelText() {
-    routerStartStopButton?.target = self
-    let staticStartedByLabelText = "Router started by launcher? "
-    let staticIsRunningLabelText = "Router status: "
-    let staticRouterVersionLabelText = "Router version: "
-    let staticRouterPidLabelText = "Router PID: "
-    
-    // Use default here to avoid any potential crashes with force unwrapping
-    let currentStatus : AgentStatus = RouterRunner.launchAgent?.status() ?? AgentStatus.unloaded
-    if currentStatus == AgentStatus.loaded || currentStatus == AgentStatus.unloaded  {
-      routerStatusLabel?.cell?.stringValue = staticIsRunningLabelText+"Not running"
-    } else {
-      routerStatusLabel?.cell?.stringValue = staticIsRunningLabelText+"Running"
-    }
-    
-    if RouterProcessStatus.isRouterChildProcess {
-      routerStartedByLabel?.cell?.stringValue = staticStartedByLabelText+"Yes"
-    } else {
-      routerStartedByLabel?.cell?.stringValue = staticStartedByLabelText+"No"
-    }
-    
-    // Try to display PID - if not, the string behind ?? is used as "default"
-    let tmpPidText = RouterManager.shared().lastRouterPid ?? "Not running"
-    routerPIDLabel?.cell?.stringValue = staticRouterPidLabelText+tmpPidText
-    
-    if let version = RouterProcessStatus.routerVersion {
-      routerVersionLabel?.cell?.stringValue = staticRouterVersionLabelText + version
-    } else {
-      routerVersionLabel?.cell?.stringValue = staticRouterVersionLabelText + "Still unknown"
-    }
-    
-    if let routerStartTime = RouterProcessStatus.routerStartedAt {
-      routerUptimeLabel?.cell?.stringValue = "Uptime: Router started " + DateTimeUtils.timeAgoSinceDate(date: NSDate(date: routerStartTime), numericDates: false)
-    } else {
-      routerUptimeLabel?.cell?.stringValue = "Uptime: Router isn't running"
-    }
-    
-    // Needs display function alerts the rendrerer that the UI parts need to be re-drawed.
-    routerStartStopButton?.needsDisplay = true
-    quickControlView?.needsDisplay = true
-    routerUptimeLabel?.needsDisplay = true
-    routerVersionLabel?.needsDisplay = true
-    routerStartedByLabel?.needsDisplay = true
-    routerPIDLabel?.needsDisplay = true
-  }
-  
-  
-  init() {
-    let c = NSCoder()
-    super.init(coder: c)!
-    self.setupObservers()
-    self.setupFirefoxBtn()
-    self.toggleSetButtonStart()
-    self.reEnableButton()
-  }
-  
-  required init?(coder decoder: NSCoder) {
-    super.init(coder: decoder)
-    self.setupObservers()
-    self.setupFirefoxBtn()
-    self.toggleSetButtonStart()
-    self.reEnableButton()
-  }
-  
-}
diff --git a/launchers/macosx/I2PLauncher/userinterface/StatusBarController.swift b/launchers/macosx/I2PLauncher/userinterface/StatusBarController.swift
deleted file mode 100644
index e2c19f3176701c130d8cc150f3aa1c8d2821e59c..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/StatusBarController.swift
+++ /dev/null
@@ -1,206 +0,0 @@
-//
-//  StatusBarController.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 13/03/2018.
-//  Copyright © 2018 I2P. All rights reserved.
-//
-
-import Foundation
-import Cocoa
-import Sparkle
-
-@objc class StatusBarController: NSObject, NSMenuDelegate {
-  
-  let popover = NSPopover()
-  let statusItem = NSStatusBar.system.statusItem(withLength: NSStatusItem.variableLength)
-  let storyboard = NSStoryboard(name: "Storyboard", bundle: Bundle.main)
-  
-  let updaterObject: SUUpdater = SUUpdater()
-  
-  var ctrl : PopoverViewController?
-  private static var preferencesController: NSWindowController?
-  private static var experimentalConsoleViewController: NSWindowController?
-
-  @IBOutlet var routerStatusTabView: RouterStatusView?
-  
-  @IBAction func handleNativePrefMenuClicked(_ sender: Any) {
-    StatusBarController.launchPreferences(sender)
-  }
-  
-  //var updateObjectRef : SUUpdater?
-  
-  @objc func handleOpenConsole(_ sender: Any?) {
-    SwiftApplicationDelegate.openLink(url: "http://localhost:7657")
-  }
-  
-  static func onExperimentalConsoleViewClick(_ sender: NSButton) {
-    if #available(OSX 10.12, *) {
-      print("Clicked for Experimental Console WebView")
-      if !(experimentalConsoleViewController != nil) {
-        let storyboard = NSStoryboard(name: "ConsoleWebView", bundle: Bundle.main)
-        experimentalConsoleViewController = storyboard.instantiateInitialController() as? NSWindowController
-        print("created experimental console webview controller")
-      }
-      if (experimentalConsoleViewController != nil) {
-        experimentalConsoleViewController!.showWindow(sender)
-        print("trying to view: Console WebView")
-      }
-    } else {
-      // Sorry, only OSX >= 10.12
-    }
-  }
-  
-  @objc static func launchPreferences(_ sender: Any) {
-    print("Preferences clicked")
-    if !(preferencesController != nil) {
-      let storyboard = NSStoryboard(name: "Preferences", bundle: Bundle.main)
-      preferencesController = storyboard.instantiateInitialController() as? NSWindowController
-      print("created preferences controller")
-    }
-    if (preferencesController != nil) {
-      NSApp.activate(ignoringOtherApps: true)
-      preferencesController!.showWindow(sender)
-      print("trying to view: Preferences")
-    }
-  }
-  
-  @objc func launchPreferencesStaticProxy(_ sender: Any) {
-    StatusBarController.launchPreferences(sender)
-  }
-  
-  static func launchRouterConsole(_ sender: Any) {
-    if (!Preferences.shared().featureToggleExperimental) {
-      // The normal...
-      NSWorkspace.shared.open(URL(string: "http://127.0.0.1:7657")!)
-    } else {
-      // Experimental
-    }
-  }
-  
-  func pidReaction(information:Any?){
-    let pidStr = information as! String
-    NSLog("Router PID is %@", pidStr)
-    showPopover(sender: nil)
-    RouterManager.shared().lastRouterPid = pidStr
-    self.ctrl?.getRouterStatusView()?.needsDisplay = true
-  }
-  
-  func event_toggle(information:Any?) {
-    self.togglePopover(sender: self)
-  }
-
-  
-  override init() {
-    super.init()
-    self.ctrl = PopoverViewController.freshController()
-    popover.contentViewController = self.ctrl
-    RouterManager.shared().eventManager.listenTo(eventName: "router_pid", action: pidReaction)
-    
-    RouterManager.shared().eventManager.listenTo(eventName: "toggle_popover", action: event_toggle)
-    
-    let _ = FirefoxManager.shared().tryAutoDetect()
-    
-    print("Is Firefox found? \(FirefoxManager.shared().IsFirefoxFound())")
-    print("Is Firefox profile extracted at \(Preferences.shared()["I2Pref_firefoxProfilePath"] as! String)? \(FirefoxManager.shared().IsProfileExtracted())")
-    if (!FirefoxManager.shared().IsProfileExtracted()) {
-      let _ = FirefoxManager.shared().unzipProfile()
-    }
-    
-    if let button = statusItem.button {
-      button.image = NSImage(named:"StatusBarButtonImage")
-      button.toolTip = "I2P Launch Manager"
-      button.target = self
-      button.action = #selector(self.statusBarButtonClicked(sender:))
-      button.sendAction(on: [.leftMouseUp, .rightMouseUp])
-    }
-  }
-  
-  @IBAction func openConsoleClicked(_ sender: Any) {
-    NSLog("openConsoleClicked got clicked")
-    let realSender = sender as! NSMenuItem
-    NSLog("Sender: @%", realSender)
-  }
-  
-  @IBAction func quitClicked(_ sender: NSMenuItem) {
-    NSApplication.shared.terminate(self)
-  }
-  
-  @objc func checkUpdateClicked(_ sender: NSMenuItem) {
-    //DispatchQueue(label: "updaterqueue").async {}
-    self.updaterObject.checkForUpdates(sender)
-  }
-  
-}
-
-/**
- *
- * Here you find menu & popover trigger related code.
- *
- */
-
-extension StatusBarController {
-  
-  // This is the construction of the context (right-click) menu spawned at the system tray icon.
-  @objc func constructMenu() -> NSMenu {
-    let menu = NSMenu()
-    
-    let updateMenuItem = NSMenuItem(title: "Check for updates", action: #selector(self.checkUpdateClicked(_:)), keyEquivalent: "U")
-    updateMenuItem.isEnabled = true
-    updateMenuItem.target = self
-    
-    
-    let preferencesMenuItem = NSMenuItem(title: "Preferences", action: #selector(self.launchPreferencesStaticProxy(_:)), keyEquivalent: "P")
-    preferencesMenuItem.isEnabled = true
-    preferencesMenuItem.target = self
-    
-    menu.addItem(NSMenuItem(title: "Open I2P Console", action: #selector(self.handleOpenConsole(_:)), keyEquivalent: "O"))
-    menu.addItem(NSMenuItem.separator())
-    menu.addItem(updateMenuItem)
-    menu.addItem(preferencesMenuItem)
-    menu.addItem(NSMenuItem.separator())
-    menu.addItem(NSMenuItem(title: "Quit I2P Launcher", action: #selector(SwiftApplicationDelegate.terminate(_:)), keyEquivalent: "q"))
-    
-    return menu
-  }
-  
-  @objc func statusBarButtonClicked(sender: NSStatusBarButton) {
-    let event = NSApp.currentEvent!
-    
-    if event.type == NSEvent.EventType.rightMouseUp {
-      closePopover(sender: nil)
-      
-      let ctxMenu = constructMenu()
-      
-      statusItem.menu = ctxMenu
-      statusItem.popUpMenu(ctxMenu)
-      
-      // This is critical, otherwise clicks won't be processed again
-      statusItem.menu = nil
-    } else {
-      togglePopover(sender: nil)
-    }
-  }
-  
-  func togglePopover(sender: AnyObject?) {
-    if popover.isShown {
-      closePopover(sender: sender)
-    } else {
-      showPopover(sender: sender)
-    }
-  }
-  
-  func showPopover(sender: AnyObject?) {
-    if let button = statusItem.button {
-      let inst = RouterStatusView.getInstance()
-      if (inst != nil) {
-        if (inst != Optional.none) { RouterStatusView.getInstance()?.setRouterStatusLabelText() }
-      }
-      popover.show(relativeTo: button.bounds, of: button, preferredEdge: NSRectEdge.minY)
-    }
-  }
-  
-  func closePopover(sender: AnyObject?) {
-    popover.performClose(sender)
-  }
-}
diff --git a/launchers/macosx/I2PLauncher/userinterface/Style2019/AppearanceObserver.swift b/launchers/macosx/I2PLauncher/userinterface/Style2019/AppearanceObserver.swift
deleted file mode 100644
index bdc1e380bc13877963f39ec98ffbc941bcd89a98..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/Style2019/AppearanceObserver.swift
+++ /dev/null
@@ -1,83 +0,0 @@
-//
-//  AppearanceObserver.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 15/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-
-protocol AppearanceObserver: AnyObject {
-  func changeAppearance(to newAppearance: NSAppearance)
-}
-
-@available(OSX 10.14, *)
-class Appearance {
-  class Weak {
-    fileprivate weak var object: AnyObject?
-    
-    init(_ object: AnyObject) {
-      self.object = object
-    }
-  }
-  
-  private static var effectiveAppearanceObserver: Any? = {
-    return NSApplication.shared.observe(
-      \NSApplication.effectiveAppearance,
-      options: [.new, .initial]
-    ) { _, change in
-      guard let newValue = change.newValue else { return }
-      
-      Appearance.fire(newAppearance: newValue)
-    }
-  }()
-  
-  private static var observers = [Weak]()
-  
-  private static func fire(newAppearance: NSAppearance) {
-    observers = observers.filter {
-      guard let object = $0.object else { return false }
-      
-      (object as? AppearanceObserver)?.changeAppearance(to: newAppearance)
-      return true
-    }
-  }
-  
-  static func addObserver(_ observer: AppearanceObserver) {
-    observers = observers.filter { $0.object != nil }
-    observers.append(Weak(observer))
-    
-    if effectiveAppearanceObserver == nil {
-      fatalError("Did not setup appearance observer.")
-    }
-  }
-  
-  static func removeObserver(_ observer: AppearanceObserver) {
-    observers = observers.filter { $0.object != nil && $0.object !== observer }
-  }
-}
-
-enum InterfaceStyle : String {
-  case Dark, Light
-  
-  init() {
-    let type = UserDefaults.standard.string(forKey: "AppleInterfaceStyle") ?? "Light"
-    self = InterfaceStyle(rawValue: type)!
-  }
-}
-
-
-extension NSAppearance {
-  var isDarkMode: Bool {
-    let currentStyle = InterfaceStyle()
-    if #available(OSX 10.14, *) {
-      return currentStyle == .Dark
-    } else {
-      return false
-    }
-  }
-}
-
-
-
diff --git a/launchers/macosx/I2PLauncher/userinterface/Style2019/BottomBar.swift b/launchers/macosx/I2PLauncher/userinterface/Style2019/BottomBar.swift
deleted file mode 100644
index 06f55dac4279df5372ef7b34f390df4bee4506d0..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/Style2019/BottomBar.swift
+++ /dev/null
@@ -1,237 +0,0 @@
-//
-//  BottomBar.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 17/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-import SnapKit
-import SwiftDate
-
-enum BottomBarStatus {
-  case undetermined
-  case updating
-  case updated(Date)
-}
-
-class BottomBar: NSView {
-  let settingsButton = NSButton()
-  let reloadButton = NSButton()
-  let doneButton = NSButton()
-  let aboutButton = NSButton()
-  let quitButton = NSButton()
-  let statusField = NSTextField()
-  let separator = ServiceTableRowView()
-  
-  var status: BottomBarStatus = .undetermined {
-    didSet {
-      updateStatusText()
-    }
-  }
-  
-  var reloadServicesCallback: () -> Void = {}
-  var openSettingsCallback: () -> Void = {}
-  var closeSettingsCallback: () -> Void = {}
-  
-  override init(frame frameRect: NSRect) {
-    super.init(frame: frameRect)
-    commonInit()
-  }
-  
-  required init?(coder: NSCoder) {
-    super.init(coder: coder)
-    commonInit()
-  }
-  
-  private func commonInit() {
-    addSubview(separator)
-    addSubview(settingsButton)
-    addSubview(reloadButton)
-    addSubview(statusField)
-    addSubview(doneButton)
-    addSubview(aboutButton)
-    addSubview(quitButton)
-    
-    let gearIcon = GearIcon()
-    settingsButton.addSubview(gearIcon)
-    
-    let refreshIcon = RefreshIcon()
-    reloadButton.addSubview(refreshIcon)
-    
-    separator.snp.makeConstraints { make in
-      make.height.equalTo(1)
-      make.left.top.right.equalTo(0)
-    }
-    
-    settingsButton.snp.makeConstraints { make in
-      make.height.width.equalTo(30)
-      make.bottom.left.equalTo(0)
-    }
-    
-    gearIcon.snp.makeConstraints { make in
-      make.centerX.centerY.equalToSuperview()
-      make.width.height.equalTo(22)
-    }
-    
-    reloadButton.snp.makeConstraints { make in
-      make.height.width.equalTo(30)
-      make.bottom.right.equalTo(0)
-    }
-    
-    refreshIcon.snp.makeConstraints { make in
-      make.centerX.centerY.equalToSuperview()
-      make.width.height.equalTo(18)
-    }
-    
-    statusField.snp.makeConstraints { make in
-      make.left.equalTo(settingsButton.snp.right)
-      make.right.equalTo(reloadButton.snp.left)
-      make.centerY.equalToSuperview()
-    }
-    
-    doneButton.snp.makeConstraints { make in
-      make.width.equalTo(60)
-      make.centerY.equalToSuperview()
-      make.right.equalTo(-3)
-    }
-    
-    aboutButton.snp.makeConstraints { make in
-      make.width.equalTo(56)
-      make.centerY.equalToSuperview()
-      make.left.equalTo(quitButton.snp.right).offset(6)
-    }
-    
-    quitButton.snp.makeConstraints { make in
-      make.width.equalTo(46)
-      make.centerY.equalToSuperview()
-      make.left.equalTo(3)
-    }
-    
-    settingsButton.isBordered = false
-    settingsButton.bezelStyle = .regularSquare
-    settingsButton.title = ""
-    settingsButton.target = self
-    settingsButton.action = #selector(BottomBar.openSettings)
-    gearIcon.scaleUnitSquare(to: NSSize(width: 0.46, height: 0.46))
-    
-    reloadButton.isBordered = false
-    reloadButton.bezelStyle = .regularSquare
-    reloadButton.title = ""
-    reloadButton.target = self
-    reloadButton.action = #selector(BottomBar.reloadServices)
-    refreshIcon.scaleUnitSquare(to: NSSize(width: 0.38, height: 0.38))
-    
-    statusField.isEditable = false
-    statusField.isBordered = false
-    statusField.isSelectable = false
-    let font = NSFont.systemFont(ofSize: 12)
-    let italicFont = NSFontManager.shared.font(
-      withFamily: font.fontName,
-      traits: NSFontTraitMask.italicFontMask,
-      weight: 5,
-      size: 10
-    )
-    
-    statusField.font = italicFont
-    statusField.textColor = NSColor.secondaryLabelColor
-    statusField.maximumNumberOfLines = 1
-    statusField.backgroundColor = NSColor.clear
-    statusField.alignment = .center
-    statusField.cell?.truncatesLastVisibleLine = true
-    
-    doneButton.title = "Done"
-    doneButton.bezelStyle = .regularSquare
-    doneButton.controlSize = .regular
-    doneButton.isHidden = true
-    doneButton.target = self
-    doneButton.action = #selector(BottomBar.closeSettings)
-    
-    aboutButton.title = "About"
-    aboutButton.bezelStyle = .regularSquare
-    aboutButton.controlSize = .regular
-    aboutButton.isHidden = true
-    aboutButton.target = self
-    aboutButton.action = #selector(BottomBar.openAbout)
-    
-    quitButton.title = "Quit"
-    quitButton.bezelStyle = .regularSquare
-    quitButton.controlSize = .regular
-    quitButton.isHidden = true
-    quitButton.target = NSApp
-    quitButton.action = #selector(NSApplication.terminate(_:))
-  }
-  
-  func updateStatusText() {
-    switch status {
-    case .undetermined: statusField.stringValue = ""
-    case .updating: statusField.stringValue = "Updating…"
-    case .updated(let date):
-      let colloquial = date.toRelative(style: RelativeFormatter.defaultStyle())
-      statusField.stringValue = "Updated \(colloquial)"
-    }
-  }
-  
-  @objc func reloadServices() {
-    reloadServicesCallback()
-  }
-  
-  @objc func openSettings() {
-    settingsButton.isHidden = true
-    statusField.isHidden = true
-    reloadButton.isHidden = true
-    
-    doneButton.isHidden = false
-    aboutButton.isHidden = false
-    quitButton.isHidden = false
-    
-    openSettingsCallback()
-  }
-  
-  @objc func closeSettings() {
-    settingsButton.isHidden = false
-    statusField.isHidden = false
-    reloadButton.isHidden = false
-    
-    doneButton.isHidden = true
-    aboutButton.isHidden = true
-    quitButton.isHidden = true
-    
-    closeSettingsCallback()
-  }
-  
-  @objc func openAbout() {
-    let githubLink = ""
-    let contributorsLink = ""
-    
-    let openSourceNotice = "I2PLauncher is an open-source project\n\(githubLink)"
-    let iconGlyphCredit = "Activity glyph (app icon)\nCreated by Gregor Črešnar from the Noun Project"
-    let contributors = "Contributors\n\(contributorsLink)"
-    let credits = NSMutableAttributedString(string: "\n\(openSourceNotice)\n\n\(iconGlyphCredit)\n\n\(contributors)\n\n")
-    
-    let normalFont = NSFont.systemFont(ofSize: 11)
-    let boldFont = NSFont.boldSystemFont(ofSize: 11)
-    
-    credits.addAttribute(.font, value: normalFont, range: NSRange(location: 0, length: credits.length))
-    for word in ["stts", "Activity", "Contributors"] {
-      credits.addAttribute(.font, value: boldFont, range: (credits.string as NSString).range(of: word))
-    }
-    
-    credits.addAttribute(
-      .link,
-      value: "https://\(githubLink)",
-      range: (credits.string as NSString).range(of: githubLink)
-    )
-    credits.addAttribute(
-      .link,
-      value: "https://\(contributorsLink)",
-      range: (credits.string as NSString).range(of: contributorsLink)
-    )
-    
-    NSApp.orderFrontStandardAboutPanel(options: [NSApplication.AboutPanelOptionKey(rawValue: "Credits"): credits])
-    NSApp.activate(ignoringOtherApps: true)
- 
-  }
-}
-
diff --git a/launchers/macosx/I2PLauncher/userinterface/Style2019/CustomScrollView.swift b/launchers/macosx/I2PLauncher/userinterface/Style2019/CustomScrollView.swift
deleted file mode 100644
index 258ce4ba285135f6f1cdcca048de1c8e194c1976..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/Style2019/CustomScrollView.swift
+++ /dev/null
@@ -1,18 +0,0 @@
-//
-//  CustomScrollView.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 07/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-import SnapKit
-
-class CustomScrollView: NSScrollView {
-  var topConstraint: Constraint?
-  
-  override var isOpaque: Bool {
-    return false
-  }
-}
diff --git a/launchers/macosx/I2PLauncher/userinterface/Style2019/EditorTableView/EditorTableCell.swift b/launchers/macosx/I2PLauncher/userinterface/Style2019/EditorTableView/EditorTableCell.swift
deleted file mode 100644
index 23580555d0e06a2dbedbc0b2fc60dc8ac2368921..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/Style2019/EditorTableView/EditorTableCell.swift
+++ /dev/null
@@ -1,99 +0,0 @@
-//
-//  EditorTableCell.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 08/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-import SnapKit
-
-class EditorTableCell: NSTableCellView {
-  let toggleButton = NSButton()
-  var selected: Bool = false {
-    didSet {
-      setNeedsDisplay(frame)
-    }
-  }
-  
-  var toggleCallback: () -> Void = {}
-  
-  override init(frame frameRect: NSRect) {
-    super.init(frame: frameRect)
-    commonInit()
-  }
-  
-  required init?(coder: NSCoder) {
-    super.init(coder: coder)
-    commonInit()
-  }
-  
-  private func commonInit() {
-    let textField = NSTextField()
-    textField.isEditable = false
-    textField.isBordered = false
-    textField.isSelectable = false
-    self.textField = textField
-    let font = NSFont.systemFont(ofSize: 11)
-    textField.font = font
-    textField.textColor = NSColor.textColor
-    textField.backgroundColor = NSColor.clear
-    addSubview(textField)
-    
-    textField.snp.makeConstraints { make in
-      make.left.equalTo(10)
-      make.centerY.equalToSuperview()
-    }
-    
-    addSubview(toggleButton)
-    toggleButton.title = ""
-    toggleButton.isBordered = false
-    toggleButton.bezelStyle = .texturedSquare
-    toggleButton.controlSize = .small
-    toggleButton.target = self
-    toggleButton.action = #selector(EditorTableCell.toggle)
-    toggleButton.wantsLayer = true
-    toggleButton.layer?.borderWidth = 1
-    toggleButton.layer?.cornerRadius = 4
-    toggleButton.snp.makeConstraints { make in
-      make.left.equalTo(textField.snp.right).offset(-4)
-      make.width.equalTo(36)
-      make.right.equalTo(-10)
-      make.height.equalTo(20)
-      make.centerY.equalToSuperview()
-    }
-  }
-  
-  @objc func toggle() {
-    self.selected = !selected
-    toggleCallback()
-  }
-  
-  override func draw(_ dirtyRect: NSRect) {
-    super.draw(dirtyRect)
-    
-    let color = selected ? StatusColor.green : NSColor.tertiaryLabelColor
-    let title = selected ? "ON" : "OFF"
-    
-    if #available(OSX 10.14, *) {
-      toggleButton.title = title
-      toggleButton.font = NSFont.systemFont(ofSize: 11)
-      toggleButton.contentTintColor = color
-    } else {
-      let paragraphStyle = NSMutableParagraphStyle()
-      paragraphStyle.alignment = .center
-      
-      let attributes: [NSAttributedString.Key: Any] = [
-        .font: NSFont.systemFont(ofSize: 11),
-        .foregroundColor: color,
-        .paragraphStyle: paragraphStyle
-      ]
-      
-      toggleButton.attributedTitle = NSAttributedString(string: title, attributes: attributes)
-    }
-    
-    toggleButton.layer?.borderColor = color.cgColor
-  }
-}
-
diff --git a/launchers/macosx/I2PLauncher/userinterface/Style2019/EditorTableView/EditorTableViewController.swift b/launchers/macosx/I2PLauncher/userinterface/Style2019/EditorTableView/EditorTableViewController.swift
deleted file mode 100644
index afe24af55de32f8621aec2fd8763f7d321828914..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/Style2019/EditorTableView/EditorTableViewController.swift
+++ /dev/null
@@ -1,171 +0,0 @@
-//
-//  EditorTableViewController.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 08/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-import SnapKit
-
-class EditorTableViewController: NSObject, SwitchableTableViewController {
-  let contentView: NSStackView
-  let scrollView: CustomScrollView
-  let tableView = NSTableView()
-  
-  let allServices: [BaseService] = BaseService.all().sorted()
-  var filteredServices: [BaseService]
-  var selectedServices: [BaseService] = []//Preferences.shared().selectedServices
-  
-  var selectionChanged = false
-  
-  let settingsView = SettingsView()
-  
-  var hidden: Bool = true
-  
-  init(contentView: NSStackView, scrollView: CustomScrollView) {
-    self.contentView = contentView
-    self.scrollView = scrollView
-    self.filteredServices = allServices
-    
-    print(allServices)
-    
-    super.init()
-    setup()
-  }
-  
-  func setup() {
-    tableView.frame = scrollView.bounds
-    let column = NSTableColumn(identifier: NSUserInterfaceItemIdentifier(rawValue: "editorColumnIdentifier"))
-    column.width = 200
-    tableView.addTableColumn(column)
-    tableView.autoresizesSubviews = true
-    tableView.wantsLayer = true
-    tableView.layer?.cornerRadius = 6
-    tableView.headerView = nil
-    tableView.rowHeight = 30
-    tableView.gridStyleMask = NSTableView.GridLineStyle.init(rawValue: 0)
-    tableView.dataSource = self
-    tableView.delegate = self
-    tableView.selectionHighlightStyle = .none
-    tableView.backgroundColor = NSColor.clear
-    
-    settingsView.isHidden = true
-    settingsView.searchCallback = { [weak self] searchString in
-      guard
-        let strongSelf = self,
-        let allServices = strongSelf.allServices as? [Service]
-        else { return }
-      
-      if searchString.trimmingCharacters(in: .whitespacesAndNewlines) == "" {
-        strongSelf.filteredServices = allServices
-      } else {
-        // Can't filter array with NSPredicate without making Service inherit KVO from NSObject, therefore we create
-        // an array of service names that we can run the predicate on
-        let allServiceNames = allServices.compactMap { $0.name } as NSArray
-        let predicate = NSPredicate(format: "SELF LIKE[cd] %@", argumentArray: ["*\(searchString)*"])
-        guard let filteredServiceNames = allServiceNames.filtered(using: predicate) as? [String] else { return }
-        
-        strongSelf.filteredServices = allServices.filter { filteredServiceNames.contains($0.name) }
-      }
-      
-      strongSelf.tableView.reloadData()
-    }
-    
-    contentView.addSubview(settingsView)
-    settingsView.snp.makeConstraints { make in
-      make.top.left.right.equalTo(0)
-      make.height.equalTo(130)
-    }
-  }
-  
-  func willShow() {
-    self.selectionChanged = false
-    
-    scrollView.topConstraint?.update(offset: settingsView.frame.size.height)
-    scrollView.documentView = tableView
-    
-    settingsView.isHidden = false
-    
-    // We should be using NSWindow's makeFirstResponder: instead of the search field's selectText:, but in this case, makeFirstResponder
-    // is causing a bug where the search field "gets focused" twice (focus ring animation) the first time it's drawn.
-    settingsView.searchField.selectText(nil)
-    
-    resizeViews()
-  }
-  
-  func resizeViews() {
-    tableView.frame = scrollView.bounds
-    tableView.tableColumns.first?.width = tableView.frame.size.width
-    
-    scrollView.frame.size.height = 400
-    
-    /*(NSApp.delegate as? SwiftApplicationDelegate)?.popupController.resizePopup(
-      height: scrollView.frame.size.height + 30 // bottomBar.frame.size.height
-    )*/
-  }
-  
-  func willOpenPopup() {
-    resizeViews()
-  }
-  
-  func didOpenPopup() {
-    settingsView.searchField.window?.makeFirstResponder(settingsView.searchField)
-  }
-  
-  func willHide() {
-    settingsView.isHidden = true
-  }
-}
-
-extension EditorTableViewController: NSTableViewDataSource {
-  func numberOfRows(in tableView: NSTableView) -> Int {
-    return filteredServices.count
-  }
-  
-  func tableView(_ tableView: NSTableView, objectValueFor tableColumn: NSTableColumn?, row: Int) -> Any? {
-    return nil
-  }
-}
-
-extension EditorTableViewController: NSTableViewDelegate {
-  func tableView(_ tableView: NSTableView, viewFor tableColumn: NSTableColumn?, row: Int) -> NSView? {
-    let identifier = tableColumn?.identifier ?? NSUserInterfaceItemIdentifier(rawValue: "identifier")
-    let cell = tableView.makeView(withIdentifier: identifier, owner: self) ?? EditorTableCell()
-    
-    guard let view = cell as? EditorTableCell else { return nil }
-    guard let service = filteredServices[row] as? Service else { return nil }
-    
-    view.textField?.stringValue = service.name
-    view.selected = selectedServices.contains(service)
-    view.toggleCallback = { [weak self] in
-      guard let strongSelf = self else { return }
-      
-      strongSelf.selectionChanged = true
-      
-      if view.selected {
-        self?.selectedServices.append(service)
-      } else {
-        if let index = self?.selectedServices.index(of: service) {
-          self?.selectedServices.remove(at: index)
-        }
-      }
-      
-      //Preferences.shared().selectedServices = strongSelf.selectedServices
-    }
-    
-    return view
-  }
-  
-  func tableView(_ tableView: NSTableView, rowViewForRow row: Int) -> NSTableRowView? {
-    let cellIdentifier = NSUserInterfaceItemIdentifier(rawValue: "rowView")
-    let cell = tableView.makeView(withIdentifier: cellIdentifier, owner: self) ?? ServiceTableRowView()
-    
-    guard let view = cell as? ServiceTableRowView else { return nil }
-    
-    view.showSeparator = row + 1 < filteredServices.count
-    
-    return view
-  }
-}
diff --git a/launchers/macosx/I2PLauncher/userinterface/Style2019/EditorTableView/SectionHeaderView.swift b/launchers/macosx/I2PLauncher/userinterface/Style2019/EditorTableView/SectionHeaderView.swift
deleted file mode 100644
index 1ef117c71e872f592577604fa4f7361812a42016..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/Style2019/EditorTableView/SectionHeaderView.swift
+++ /dev/null
@@ -1,39 +0,0 @@
-//
-//  SectionHeaderView.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 09/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-
-class SectionHeaderView: NSTextField {
-  init(name: String) {
-    super.init(frame: .zero)
-    
-    setup()
-    self.stringValue = name
-  }
-  
-  required init?(coder: NSCoder) {
-    super.init(frame: .zero)
-    setup()
-  }
-  
-  private func setup() {
-    self.isEditable = false
-    self.isBordered = false
-    self.isSelectable = false
-    let italicFont = NSFontManager.shared.font(withFamily: NSFont.systemFont(ofSize: 10).fontName,
-                                               traits: NSFontTraitMask.italicFontMask,
-                                               weight: 5,
-                                               size: 10)
-    self.font = italicFont
-    self.textColor = NSColor.secondaryLabelColor
-    self.maximumNumberOfLines = 1
-    self.cell!.truncatesLastVisibleLine = true
-    self.backgroundColor = NSColor.clear
-  }
-}
-
diff --git a/launchers/macosx/I2PLauncher/userinterface/Style2019/EditorTableView/SettingsView.swift b/launchers/macosx/I2PLauncher/userinterface/Style2019/EditorTableView/SettingsView.swift
deleted file mode 100644
index 98d2f2b4bdf9ead95af7c804cef433c3e0582c14..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/Style2019/EditorTableView/SettingsView.swift
+++ /dev/null
@@ -1,96 +0,0 @@
-//
-//  SettingsView.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 08/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-import SnapKit
-
-class SettingsView: NSView {
-  let settingsHeader = SectionHeaderView(name: "Hmm")
-  let notifyCheckbox = NSButton()
-  
-  let servicesHeader = SectionHeaderView(name: "Services")
-  let searchField = NSSearchField()
-  
-  var searchCallback: ((String) -> Void)?
-  
-  init() {
-    super.init(frame: .zero)
-    setup()
-  }
-  
-  required init?(coder: NSCoder) {
-    super.init(frame: .zero)
-    setup()
-  }
-  
-  func setup() {
-    addSubview(settingsHeader)
-    addSubview(notifyCheckbox)
-    addSubview(servicesHeader)
-    addSubview(searchField)
-    
-    let smallFont = NSFont.systemFont(ofSize: NSFont.systemFontSize(for: .small))
-    
-    
-    notifyCheckbox.setButtonType(.switch)
-    notifyCheckbox.title = "Notify when a status changes"
-    notifyCheckbox.font = smallFont
-    notifyCheckbox.state = Preferences.shared().notifyOnStatusChange ? .on : .off
-    notifyCheckbox.action = #selector(SettingsView.updateNotifyOnStatusChange)
-    notifyCheckbox.target = self
-    
-    searchField.sendsSearchStringImmediately = true
-    searchField.sendsWholeSearchString = false
-    searchField.action = #selector(SettingsView.filterServices)
-    searchField.target = self
-    
-    settingsHeader.snp.makeConstraints { make in
-      make.top.left.equalTo(6)
-      make.right.equalTo(-6)
-      make.height.equalTo(16)
-    }
-    
-    /*startAtLoginCheckbox.snp.makeConstraints { make in
-      make.top.equalTo(settingsHeader.snp.bottom).offset(6)
-      make.left.equalTo(14)
-      make.right.equalTo(-14)
-      make.height.equalTo(18)
-    }*/
-    
-    notifyCheckbox.snp.makeConstraints { make in
-      make.top.equalTo(settingsHeader.snp.bottom).offset(6)
-      make.left.equalTo(14)
-      make.right.equalTo(-14).priority(200)
-      make.height.equalTo(18)
-    }
-    
-    servicesHeader.snp.makeConstraints { make in
-      make.top.equalTo(notifyCheckbox.snp.bottom).offset(10)
-      make.left.equalTo(6)
-      make.right.equalTo(-6)
-      make.height.equalTo(16)
-    }
-    
-    searchField.snp.makeConstraints { make in
-      make.top.equalTo(servicesHeader.snp.bottom).offset(6)
-      make.left.equalTo(12)
-      make.right.equalTo(-12)
-      make.height.equalTo(22)
-    }
-  }
-  
-  
-  @objc private func updateNotifyOnStatusChange() {
-    Preferences.shared().notifyOnStatusChange = (notifyCheckbox.state == .on)
-  }
-  
-  @objc private func filterServices() {
-    searchCallback?(searchField.stringValue)
-  }
-}
-
diff --git a/launchers/macosx/I2PLauncher/userinterface/Style2019/Icons.swift b/launchers/macosx/I2PLauncher/userinterface/Style2019/Icons.swift
deleted file mode 100644
index 7847af87a5f66785bb9a1c191d5a8f99b10e978c..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/Style2019/Icons.swift
+++ /dev/null
@@ -1,375 +0,0 @@
-//
-//  Icons.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 11/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-
-class CheckmarkIcon: NSView {
-  var color: NSColor = NSColor(calibratedRed: 0.46, green: 0.78, blue: 0.56, alpha: 1) {
-    didSet {
-      self.needsDisplay = true
-    }
-  }
-  
-  override func draw(_ dirtyRect: NSRect) {
-    super.draw(dirtyRect)
-    
-    color.setStroke()
-    
-    let checkmarkPath = NSBezierPath()
-    checkmarkPath.lineWidth = 3
-    checkmarkPath.move(to: NSPoint(x: 17.01, y: 9.15))
-    checkmarkPath.curve(to: NSPoint(x: 16.3, y: 9.45),
-                        controlPoint1: NSPoint(x: 16.75, y: 9.15),
-                        controlPoint2: NSPoint(x: 16.5, y: 9.25))
-    checkmarkPath.line(to: NSPoint(x: 2.3, y: 23.45))
-    checkmarkPath.line(to: NSPoint(x: 3.71, y: 24.86))
-    checkmarkPath.line(to: NSPoint(x: 17.01, y: 11.57))
-    checkmarkPath.line(to: NSPoint(x: 42.3, y: 36.86))
-    checkmarkPath.line(to: NSPoint(x: 43.71, y: 35.45))
-    checkmarkPath.line(to: NSPoint(x: 17.71, y: 9.45))
-    checkmarkPath.curve(to: NSPoint(x: 17.01, y: 9.15),
-                        controlPoint1: NSPoint(x: 17.52, y: 9.25),
-                        controlPoint2: NSPoint(x: 17.26, y: 9.15))
-    checkmarkPath.close()
-    checkmarkPath.stroke()
-  }
-}
-
-class CrossIcon: NSView {
-  var color: NSColor = NSColor(calibratedRed: 0.9, green: 0.78, blue: 0.56, alpha: 1) {
-    didSet {
-      self.needsDisplay = true
-    }
-  }
-  
-  override func draw(_ dirtyRect: NSRect) {
-    super.draw(dirtyRect)
-    
-    color.setFill()
-    
-    let context = NSGraphicsContext.current!.cgContext
-    
-    NSGraphicsContext.saveGraphicsState()
-    context.translateBy(x: 23, y: 23)
-    context.rotate(by: -45 * CGFloat.pi / 180)
-    NSBezierPath(rect: NSRect(x: -26.88, y: -1, width: 53.75, height: 4)).fill()
-    NSGraphicsContext.restoreGraphicsState()
-    
-    NSGraphicsContext.saveGraphicsState()
-    context.translateBy(x: 23, y: 23)
-    context.rotate(by: -45 * CGFloat.pi / 180)
-    NSBezierPath(rect: NSRect(x: -1, y: -26.88, width: 4, height: 53.75)).fill()
-    NSGraphicsContext.restoreGraphicsState()
-  }
-}
-
-class RefreshIcon: NSView {
-  var color = NSColor.secondaryLabelColor {
-    didSet {
-      self.needsDisplay = true
-    }
-  }
-  
-  override func draw(_ dirtyRect: NSRect) {
-    super.draw(dirtyRect)
-    
-    color.setFill()
-    
-    let circle = NSBezierPath()
-    circle.move(to: NSPoint(x: 23, y: 3))
-    circle.line(to: NSPoint(x: 23, y: 5))
-    circle.curve(to: NSPoint(x: 41, y: 23),
-                 controlPoint1: NSPoint(x: 32.93, y: 5),
-                 controlPoint2: NSPoint(x: 41, y: 13.07))
-    circle.curve(to: NSPoint(x: 23, y: 41),
-                 controlPoint1: NSPoint(x: 41, y: 32.93),
-                 controlPoint2: NSPoint(x: 32.93, y: 41))
-    circle.curve(to: NSPoint(x: 5, y: 23),
-                 controlPoint1: NSPoint(x: 13.07, y: 41),
-                 controlPoint2: NSPoint(x: 5, y: 32.93))
-    circle.curve(to: NSPoint(x: 14.47, y: 7.14),
-                 controlPoint1: NSPoint(x: 5, y: 16.37),
-                 controlPoint2: NSPoint(x: 8.63, y: 10.29))
-    circle.line(to: NSPoint(x: 13.53, y: 5.38))
-    circle.curve(to: NSPoint(x: 3, y: 23),
-                 controlPoint1: NSPoint(x: 7.03, y: 8.88),
-                 controlPoint2: NSPoint(x: 3, y: 15.63))
-    circle.curve(to: NSPoint(x: 23, y: 43),
-                 controlPoint1: NSPoint(x: 3, y: 34.03),
-                 controlPoint2: NSPoint(x: 11.97, y: 43))
-    circle.curve(to: NSPoint(x: 43, y: 23),
-                 controlPoint1: NSPoint(x: 34.03, y: 43),
-                 controlPoint2: NSPoint(x: 43, y: 34.03))
-    circle.curve(to: NSPoint(x: 23, y: 3),
-                 controlPoint1: NSPoint(x: 43, y: 11.97),
-                 controlPoint2: NSPoint(x: 34.03, y: 3))
-    circle.close()
-    circle.fill()
-    
-    let arrowHead = NSBezierPath()
-    arrowHead.move(to: NSPoint(x: 4.2, y: 3.02))
-    arrowHead.line(to: NSPoint(x: 3.8, y: 4.98))
-    arrowHead.line(to: NSPoint(x: 13, y: 6.82))
-    arrowHead.line(to: NSPoint(x: 13, y: 16))
-    arrowHead.line(to: NSPoint(x: 15, y: 16))
-    arrowHead.line(to: NSPoint(x: 15, y: 6))
-    arrowHead.curve(to: NSPoint(x: 14.2, y: 5.02),
-                    controlPoint1: NSPoint(x: 15, y: 5.52),
-                    controlPoint2: NSPoint(x: 14.66, y: 5.11))
-    arrowHead.line(to: NSPoint(x: 4.2, y: 3.02))
-    arrowHead.close()
-    arrowHead.fill()
-  }
-}
-
-class GearIcon: NSView {
-  var color = NSColor.secondaryLabelColor {
-    didSet {
-      self.needsDisplay = true
-    }
-  }
-  
-  override func draw(_ dirtyRect: NSRect) {
-    super.draw(dirtyRect)
-    
-    color.setFill()
-    
-    let outerCog = NSBezierPath()
-    outerCog.move(to: NSPoint(x: 26.76, y: 9.49))
-    outerCog.curve(to: NSPoint(x: 27.62, y: 8.99),
-                   controlPoint1: NSPoint(x: 27.11, y: 9.49),
-                   controlPoint2: NSPoint(x: 27.44, y: 9.3))
-    outerCog.line(to: NSPoint(x: 28.4, y: 7.64))
-    outerCog.curve(to: NSPoint(x: 31.13, y: 6.9),
-                   controlPoint1: NSPoint(x: 28.93, y: 6.72),
-                   controlPoint2: NSPoint(x: 30.21, y: 6.37))
-    outerCog.line(to: NSPoint(x: 32.87, y: 7.9))
-    outerCog.curve(to: NSPoint(x: 33.6, y: 10.64),
-                   controlPoint1: NSPoint(x: 33.82, y: 8.46),
-                   controlPoint2: NSPoint(x: 34.15, y: 9.68))
-    outerCog.line(to: NSPoint(x: 32.82, y: 11.98))
-    outerCog.curve(to: NSPoint(x: 32.98, y: 13.18),
-                   controlPoint1: NSPoint(x: 32.6, y: 12.37),
-                   controlPoint2: NSPoint(x: 32.66, y: 12.86))
-    outerCog.curve(to: NSPoint(x: 36.48, y: 19.26),
-                   controlPoint1: NSPoint(x: 34.63, y: 14.87),
-                   controlPoint2: NSPoint(x: 35.85, y: 16.97))
-    outerCog.curve(to: NSPoint(x: 37.44, y: 19.99),
-                   controlPoint1: NSPoint(x: 36.6, y: 19.69),
-                   controlPoint2: NSPoint(x: 36.99, y: 19.99))
-    outerCog.line(to: NSPoint(x: 39, y: 19.99))
-    outerCog.curve(to: NSPoint(x: 41, y: 21.99),
-                   controlPoint1: NSPoint(x: 40.1, y: 19.99),
-                   controlPoint2: NSPoint(x: 41, y: 20.89))
-    outerCog.line(to: NSPoint(x: 41, y: 23.99))
-    outerCog.curve(to: NSPoint(x: 39, y: 25.99),
-                   controlPoint1: NSPoint(x: 41, y: 25.1),
-                   controlPoint2: NSPoint(x: 40.1, y: 25.99))
-    outerCog.line(to: NSPoint(x: 37.44, y: 25.99))
-    outerCog.curve(to: NSPoint(x: 36.48, y: 26.73),
-                   controlPoint1: NSPoint(x: 36.99, y: 25.99),
-                   controlPoint2: NSPoint(x: 36.6, y: 26.29))
-    outerCog.curve(to: NSPoint(x: 32.98, y: 32.81),
-                   controlPoint1: NSPoint(x: 35.85, y: 29.02),
-                   controlPoint2: NSPoint(x: 34.63, y: 31.12))
-    outerCog.curve(to: NSPoint(x: 32.82, y: 34.01),
-                   controlPoint1: NSPoint(x: 32.66, y: 33.13),
-                   controlPoint2: NSPoint(x: 32.6, y: 33.62))
-    outerCog.line(to: NSPoint(x: 33.6, y: 35.35))
-    outerCog.curve(to: NSPoint(x: 32.87, y: 38.08),
-                   controlPoint1: NSPoint(x: 34.15, y: 36.3),
-                   controlPoint2: NSPoint(x: 33.82, y: 37.53))
-    outerCog.line(to: NSPoint(x: 31.13, y: 39.08))
-    outerCog.curve(to: NSPoint(x: 28.4, y: 38.35),
-                   controlPoint1: NSPoint(x: 30.21, y: 39.62),
-                   controlPoint2: NSPoint(x: 28.93, y: 39.26))
-    outerCog.line(to: NSPoint(x: 27.62, y: 37))
-    outerCog.curve(to: NSPoint(x: 26.51, y: 36.53),
-                   controlPoint1: NSPoint(x: 27.4, y: 36.61),
-                   controlPoint2: NSPoint(x: 26.94, y: 36.42))
-    outerCog.curve(to: NSPoint(x: 19.49, y: 36.53),
-                   controlPoint1: NSPoint(x: 24.14, y: 37.14),
-                   controlPoint2: NSPoint(x: 21.86, y: 37.14))
-    outerCog.curve(to: NSPoint(x: 18.38, y: 37),
-                   controlPoint1: NSPoint(x: 19.06, y: 36.42),
-                   controlPoint2: NSPoint(x: 18.6, y: 36.61))
-    outerCog.line(to: NSPoint(x: 17.6, y: 38.35))
-    outerCog.curve(to: NSPoint(x: 14.87, y: 39.08),
-                   controlPoint1: NSPoint(x: 17.07, y: 39.26),
-                   controlPoint2: NSPoint(x: 15.79, y: 39.62))
-    outerCog.line(to: NSPoint(x: 13.13, y: 38.08))
-    outerCog.curve(to: NSPoint(x: 12.4, y: 35.35),
-                   controlPoint1: NSPoint(x: 12.18, y: 37.53),
-                   controlPoint2: NSPoint(x: 11.85, y: 36.3))
-    outerCog.line(to: NSPoint(x: 13.18, y: 34.01))
-    outerCog.curve(to: NSPoint(x: 13.02, y: 32.81),
-                   controlPoint1: NSPoint(x: 13.4, y: 33.62),
-                   controlPoint2: NSPoint(x: 13.34, y: 33.13))
-    outerCog.curve(to: NSPoint(x: 9.52, y: 26.73),
-                   controlPoint1: NSPoint(x: 11.36, y: 31.12),
-                   controlPoint2: NSPoint(x: 10.15, y: 29.02))
-    outerCog.curve(to: NSPoint(x: 8.56, y: 25.99),
-                   controlPoint1: NSPoint(x: 9.4, y: 26.29),
-                   controlPoint2: NSPoint(x: 9.01, y: 25.99))
-    outerCog.line(to: NSPoint(x: 7, y: 25.99))
-    outerCog.curve(to: NSPoint(x: 5, y: 23.99),
-                   controlPoint1: NSPoint(x: 5.9, y: 25.99),
-                   controlPoint2: NSPoint(x: 5, y: 25.1))
-    outerCog.line(to: NSPoint(x: 5, y: 21.99))
-    outerCog.curve(to: NSPoint(x: 7, y: 19.99),
-                   controlPoint1: NSPoint(x: 5, y: 20.89),
-                   controlPoint2: NSPoint(x: 5.9, y: 19.99))
-    outerCog.line(to: NSPoint(x: 8.56, y: 19.99))
-    outerCog.curve(to: NSPoint(x: 9.52, y: 19.26),
-                   controlPoint1: NSPoint(x: 9.01, y: 19.99),
-                   controlPoint2: NSPoint(x: 9.4, y: 19.69))
-    outerCog.curve(to: NSPoint(x: 13.02, y: 13.18),
-                   controlPoint1: NSPoint(x: 10.15, y: 16.97),
-                   controlPoint2: NSPoint(x: 11.36, y: 14.87))
-    outerCog.curve(to: NSPoint(x: 13.18, y: 11.98),
-                   controlPoint1: NSPoint(x: 13.34, y: 12.86),
-                   controlPoint2: NSPoint(x: 13.4, y: 12.37))
-    outerCog.line(to: NSPoint(x: 12.4, y: 10.64))
-    outerCog.curve(to: NSPoint(x: 13.13, y: 7.9),
-                   controlPoint1: NSPoint(x: 11.85, y: 9.68),
-                   controlPoint2: NSPoint(x: 12.18, y: 8.46))
-    outerCog.line(to: NSPoint(x: 14.87, y: 6.9))
-    outerCog.curve(to: NSPoint(x: 17.6, y: 7.64),
-                   controlPoint1: NSPoint(x: 15.79, y: 6.37),
-                   controlPoint2: NSPoint(x: 17.07, y: 6.73))
-    outerCog.line(to: NSPoint(x: 18.38, y: 8.99))
-    outerCog.curve(to: NSPoint(x: 19.49, y: 9.46),
-                   controlPoint1: NSPoint(x: 18.6, y: 9.38),
-                   controlPoint2: NSPoint(x: 19.06, y: 9.57))
-    outerCog.curve(to: NSPoint(x: 26.51, y: 9.45),
-                   controlPoint1: NSPoint(x: 21.86, y: 8.84),
-                   controlPoint2: NSPoint(x: 24.14, y: 8.84))
-    outerCog.curve(to: NSPoint(x: 26.76, y: 9.49),
-                   controlPoint1: NSPoint(x: 26.59, y: 9.48),
-                   controlPoint2: NSPoint(x: 26.67, y: 9.49))
-    outerCog.close()
-    outerCog.move(to: NSPoint(x: 30.14, y: 4.64))
-    outerCog.curve(to: NSPoint(x: 26.67, y: 6.64),
-                   controlPoint1: NSPoint(x: 28.71, y: 4.64),
-                   controlPoint2: NSPoint(x: 27.38, y: 5.4))
-    outerCog.line(to: NSPoint(x: 26.26, y: 7.34))
-    outerCog.curve(to: NSPoint(x: 19.74, y: 7.34),
-                   controlPoint1: NSPoint(x: 24.06, y: 6.88),
-                   controlPoint2: NSPoint(x: 21.94, y: 6.88))
-    outerCog.line(to: NSPoint(x: 19.33, y: 6.64))
-    outerCog.curve(to: NSPoint(x: 15.86, y: 4.64),
-                   controlPoint1: NSPoint(x: 18.62, y: 5.4),
-                   controlPoint2: NSPoint(x: 17.29, y: 4.64))
-    outerCog.curve(to: NSPoint(x: 13.87, y: 5.17),
-                   controlPoint1: NSPoint(x: 15.16, y: 4.64),
-                   controlPoint2: NSPoint(x: 14.47, y: 4.82))
-    outerCog.line(to: NSPoint(x: 12.13, y: 6.17))
-    outerCog.curve(to: NSPoint(x: 10.67, y: 11.64),
-                   controlPoint1: NSPoint(x: 10.22, y: 7.28),
-                   controlPoint2: NSPoint(x: 9.57, y: 9.73))
-    outerCog.line(to: NSPoint(x: 11.07, y: 12.34))
-    outerCog.curve(to: NSPoint(x: 7.81, y: 17.99),
-                   controlPoint1: NSPoint(x: 9.61, y: 13.97),
-                   controlPoint2: NSPoint(x: 8.5, y: 15.9))
-    outerCog.line(to: NSPoint(x: 7, y: 17.99))
-    outerCog.curve(to: NSPoint(x: 3, y: 21.99),
-                   controlPoint1: NSPoint(x: 4.79, y: 17.99),
-                   controlPoint2: NSPoint(x: 3, y: 19.79))
-    outerCog.line(to: NSPoint(x: 3, y: 23.99))
-    outerCog.curve(to: NSPoint(x: 7, y: 27.99),
-                   controlPoint1: NSPoint(x: 3, y: 26.2),
-                   controlPoint2: NSPoint(x: 4.79, y: 27.99))
-    outerCog.line(to: NSPoint(x: 7.81, y: 27.99))
-    outerCog.curve(to: NSPoint(x: 11.07, y: 33.65),
-                   controlPoint1: NSPoint(x: 8.5, y: 30.08),
-                   controlPoint2: NSPoint(x: 9.61, y: 32.02))
-    outerCog.line(to: NSPoint(x: 10.67, y: 34.35))
-    outerCog.curve(to: NSPoint(x: 12.13, y: 39.81),
-                   controlPoint1: NSPoint(x: 9.57, y: 36.26),
-                   controlPoint2: NSPoint(x: 10.22, y: 38.71))
-    outerCog.line(to: NSPoint(x: 13.87, y: 40.81))
-    outerCog.curve(to: NSPoint(x: 15.86, y: 41.35),
-                   controlPoint1: NSPoint(x: 14.47, y: 41.16),
-                   controlPoint2: NSPoint(x: 15.16, y: 41.35))
-    outerCog.curve(to: NSPoint(x: 19.33, y: 39.35),
-                   controlPoint1: NSPoint(x: 17.29, y: 41.35),
-                   controlPoint2: NSPoint(x: 18.62, y: 40.58))
-    outerCog.line(to: NSPoint(x: 19.74, y: 38.64))
-    outerCog.curve(to: NSPoint(x: 26.26, y: 38.64),
-                   controlPoint1: NSPoint(x: 21.94, y: 39.11),
-                   controlPoint2: NSPoint(x: 24.06, y: 39.11))
-    outerCog.line(to: NSPoint(x: 26.67, y: 39.35))
-    outerCog.curve(to: NSPoint(x: 30.14, y: 41.35),
-                   controlPoint1: NSPoint(x: 27.38, y: 40.58),
-                   controlPoint2: NSPoint(x: 28.71, y: 41.35))
-    outerCog.curve(to: NSPoint(x: 32.13, y: 40.81),
-                   controlPoint1: NSPoint(x: 30.84, y: 41.35),
-                   controlPoint2: NSPoint(x: 31.53, y: 41.16))
-    outerCog.line(to: NSPoint(x: 33.87, y: 39.81))
-    outerCog.curve(to: NSPoint(x: 35.33, y: 34.35),
-                   controlPoint1: NSPoint(x: 35.78, y: 38.71),
-                   controlPoint2: NSPoint(x: 36.43, y: 36.26))
-    outerCog.line(to: NSPoint(x: 34.93, y: 33.65))
-    outerCog.curve(to: NSPoint(x: 38.19, y: 27.99),
-                   controlPoint1: NSPoint(x: 36.39, y: 32.02),
-                   controlPoint2: NSPoint(x: 37.5, y: 30.08))
-    outerCog.line(to: NSPoint(x: 39, y: 27.99))
-    outerCog.curve(to: NSPoint(x: 43, y: 23.99),
-                   controlPoint1: NSPoint(x: 41.21, y: 27.99),
-                   controlPoint2: NSPoint(x: 43, y: 26.2))
-    outerCog.line(to: NSPoint(x: 43, y: 21.99))
-    outerCog.curve(to: NSPoint(x: 39, y: 17.99),
-                   controlPoint1: NSPoint(x: 43, y: 19.79),
-                   controlPoint2: NSPoint(x: 41.21, y: 17.99))
-    outerCog.line(to: NSPoint(x: 38.19, y: 17.99))
-    outerCog.curve(to: NSPoint(x: 34.93, y: 12.34),
-                   controlPoint1: NSPoint(x: 37.5, y: 15.9),
-                   controlPoint2: NSPoint(x: 36.39, y: 13.97))
-    outerCog.line(to: NSPoint(x: 35.33, y: 11.64))
-    outerCog.curve(to: NSPoint(x: 33.87, y: 6.17),
-                   controlPoint1: NSPoint(x: 36.43, y: 9.73),
-                   controlPoint2: NSPoint(x: 35.78, y: 7.28))
-    outerCog.line(to: NSPoint(x: 32.13, y: 5.17))
-    outerCog.curve(to: NSPoint(x: 30.14, y: 4.64),
-                   controlPoint1: NSPoint(x: 31.53, y: 4.82),
-                   controlPoint2: NSPoint(x: 30.84, y: 4.64))
-    outerCog.close()
-    outerCog.fill()
-    
-    let innerCircle = NSBezierPath()
-    innerCircle.move(to: NSPoint(x: 23, y: 29.99))
-    innerCircle.curve(to: NSPoint(x: 16, y: 22.99),
-                      controlPoint1: NSPoint(x: 19.14, y: 29.99),
-                      controlPoint2: NSPoint(x: 16, y: 26.85))
-    innerCircle.curve(to: NSPoint(x: 23, y: 15.99),
-                      controlPoint1: NSPoint(x: 16, y: 19.13),
-                      controlPoint2: NSPoint(x: 19.14, y: 15.99))
-    innerCircle.curve(to: NSPoint(x: 30, y: 22.99),
-                      controlPoint1: NSPoint(x: 26.86, y: 15.99),
-                      controlPoint2: NSPoint(x: 30, y: 19.13))
-    innerCircle.curve(to: NSPoint(x: 23, y: 29.99),
-                      controlPoint1: NSPoint(x: 30, y: 26.85),
-                      controlPoint2: NSPoint(x: 26.86, y: 29.99))
-    innerCircle.close()
-    innerCircle.move(to: NSPoint(x: 23, y: 13.99))
-    innerCircle.curve(to: NSPoint(x: 14, y: 22.99),
-                      controlPoint1: NSPoint(x: 18.04, y: 13.99),
-                      controlPoint2: NSPoint(x: 14, y: 18.03))
-    innerCircle.curve(to: NSPoint(x: 23, y: 31.99),
-                      controlPoint1: NSPoint(x: 14, y: 27.96),
-                      controlPoint2: NSPoint(x: 18.04, y: 31.99))
-    innerCircle.curve(to: NSPoint(x: 32, y: 22.99),
-                      controlPoint1: NSPoint(x: 27.96, y: 31.99),
-                      controlPoint2: NSPoint(x: 32, y: 27.96))
-    innerCircle.curve(to: NSPoint(x: 23, y: 13.99),
-                      controlPoint1: NSPoint(x: 32, y: 18.03),
-                      controlPoint2: NSPoint(x: 27.96, y: 13.99))
-    innerCircle.close()
-    innerCircle.fill()
-  }
-}
diff --git a/launchers/macosx/I2PLauncher/userinterface/Style2019/ServiceTableRowView.swift b/launchers/macosx/I2PLauncher/userinterface/Style2019/ServiceTableRowView.swift
deleted file mode 100644
index 1c982ca2f978978dbcea474822378089aa276ccd..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/Style2019/ServiceTableRowView.swift
+++ /dev/null
@@ -1,37 +0,0 @@
-//
-//  ServiceTableRowView.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 19/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-
-class ServiceTableRowView: NSTableRowView {
-  var showSeparator = true
-  var gradient: CAGradientLayer?
-  
-  override func layout() {
-    super.layout()
-    
-    let width = frame.size.width
-    let height = frame.size.height
-    
-    let gradient = self.gradient ?? CAGradientLayer()
-    
-    gradient.isHidden = !showSeparator
-    
-    self.wantsLayer = true
-    self.layer?.insertSublayer(gradient, at: 0)
-    self.gradient = gradient
-    
-    let separatorColor = NSColor.quaternaryLabelColor.cgColor
-    gradient.colors = [NSColor.clear.cgColor, separatorColor, separatorColor, separatorColor, NSColor.clear.cgColor]
-    gradient.locations = [0, 0.3, 0.5, 0.70, 1]
-    gradient.startPoint = CGPoint(x: 0, y: 0.5)
-    gradient.endPoint = CGPoint(x: 1, y: 0.5)
-    gradient.frame = CGRect(x: 0, y: height - 1, width: width, height: 1)
-  }
-}
-
diff --git a/launchers/macosx/I2PLauncher/userinterface/Style2019/ServiceTableViewController.swift b/launchers/macosx/I2PLauncher/userinterface/Style2019/ServiceTableViewController.swift
deleted file mode 100644
index ad9acb7a099cb872488bc0f5aadd737ca2dd4df8..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/Style2019/ServiceTableViewController.swift
+++ /dev/null
@@ -1,266 +0,0 @@
-//
-//  ServiceTableViewController.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 20/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-import SnapKit
-import MBPopup
-
-class ServiceTableViewController: NSObject, SwitchableTableViewController {
-  let contentView = NSStackView(frame: CGRect(x: 0, y: 0, width: 220, height: 400))
-  let scrollView = CustomScrollView()
-  let tableView = NSTableView()
-  let bottomBar = BottomBar()
-  let addServicesNoticeField = NSTextField()
-  
-  var editorTableViewController: EditorTableViewController
-  
-  var services: [BaseService] = [I2PRouterService(),HttpTunnelService(),IrcTunnelService()] {
-    didSet {
-      addServicesNoticeField.isHidden = services.count > 0
-    }
-  }
-  
-  var servicesBeingUpdated = [BaseService]()
-  var generalStatus: ServiceStatus {
-    let hasBadServices = services.first { $0.status > .stopped } != nil
-    
-    return hasBadServices ? .killed : .started
-  }
-  
-  var hidden: Bool = false
-  
-  var updateCallback: (() -> Void)?
-  
-  override init() {
-    self.editorTableViewController = EditorTableViewController(contentView: contentView, scrollView: scrollView)
-    super.init()
-  }
-  
-  func setup() {
-    //bottomBar.reloadServicesCallback = (NSApp.delegate as? SwiftApplicationDelegate)!.updateServices
-    
-    bottomBar.openSettingsCallback = { [weak self] in
-      self?.hide()
-      self?.editorTableViewController.show()
-    }
-    
-    bottomBar.closeSettingsCallback = { [weak self] in
-      self?.editorTableViewController.hide()
-      self?.show()
-    }
-    
-    contentView.snp.makeConstraints { make in
-      make.left.right.bottom.equalTo(0)
-      make.width.greaterThanOrEqualTo(220)
-      make.height.greaterThanOrEqualTo(40 + 30 + 2) // tableView.rowHeight + bottomBar.frame.size.height + 2
-    }
-    
-    contentView.addSubview(scrollView)
-    contentView.addSubview(bottomBar)
-    
-    scrollView.snp.makeConstraints { make in
-      scrollView.topConstraint = make.top.equalToSuperview().constraint
-      make.left.right.equalTo(0)
-    }
-    
-    bottomBar.snp.makeConstraints { make in
-      make.width.equalToSuperview()
-      make.top.equalTo(scrollView.snp.bottom)
-      make.height.equalTo(30)
-      make.left.right.equalTo(0)
-      make.bottom.equalTo(0)
-    }
-    
-    contentView.addSubview(addServicesNoticeField)
-    addServicesNoticeField.snp.makeConstraints { make in
-      make.height.equalTo(22)
-      make.left.right.equalTo(0)
-      make.centerY.equalToSuperview().offset(-14)
-    }
-    
-    scrollView.borderType = .noBorder
-    scrollView.hasVerticalScroller = true
-    scrollView.hasHorizontalScroller = false
-    scrollView.autoresizesSubviews = true
-    scrollView.documentView = tableView
-    scrollView.drawsBackground = false
-    scrollView.wantsLayer = true
-    scrollView.layer?.cornerRadius = 6
-    
-    tableView.frame = scrollView.bounds
-    let column = NSTableColumn(identifier: NSUserInterfaceItemIdentifier(rawValue: "serviceColumnIdentifier"))
-    column.width = tableView.frame.size.width
-    tableView.addTableColumn(column)
-    tableView.autoresizesSubviews = true
-    tableView.wantsLayer = true
-    tableView.layer?.cornerRadius = 6
-    tableView.headerView = nil
-    tableView.rowHeight = 40
-    tableView.gridStyleMask = NSTableView.GridLineStyle.init(rawValue: 0)
-    tableView.dataSource = self
-    tableView.delegate = self
-    tableView.selectionHighlightStyle = .none
-    tableView.backgroundColor = NSColor.clear
-    
-    addServicesNoticeField.isEditable = false
-    addServicesNoticeField.isBordered = false
-    addServicesNoticeField.isSelectable = false
-    
-    let italicFont = NSFontManager.shared.font(
-      withFamily: NSFont.systemFont(ofSize: 13).fontName,
-      traits: NSFontTraitMask.italicFontMask,
-      weight: 5,
-      size: 13
-    )
-    
-    addServicesNoticeField.font = italicFont
-    addServicesNoticeField.textColor = NSColor.textColor
-    addServicesNoticeField.maximumNumberOfLines = 1
-    addServicesNoticeField.cell!.truncatesLastVisibleLine = true
-    addServicesNoticeField.alignment = .center
-    addServicesNoticeField.stringValue = "Oh, maybe too empty? :)"
-    addServicesNoticeField.backgroundColor = .clear
-  }
-  
-  func willOpenPopup() {
-    resizeViews()
-    reloadData()
-    
-    if case let .updated(date) = bottomBar.status {
-      if Date().timeIntervalSince1970 - date.timeIntervalSince1970 > 60 {
-        //(NSApp.delegate as? SwiftApplicationDelegate)?.updateServices()
-      }
-    }
-  }
-  
-  func willShow() {
-    scrollView.topConstraint?.update(offset: 0)
-    scrollView.documentView = tableView
-    
-    if editorTableViewController.selectionChanged {
-      //self.services = ["I2PRouter","HttpTunnel"]//Preferences.shared.selectedServices
-      reloadData()
-      
-      //(NSApp.delegate as? SwiftApplicationDelegate)?.updateServices()
-    } else {
-      addServicesNoticeField.isHidden = services.count > 0
-    }
-    
-    resizeViews()
-  }
-  
-  func willHide() {
-    addServicesNoticeField.isHidden = true
-  }
-  
-  func resizeViews() {
-    var frame = scrollView.frame
-    frame.size.height = min(tableView.intrinsicContentSize.height, 490)
-    scrollView.frame = frame
-    
-    //(NSApp.delegate as? SwiftApplicationDelegate)?.popupController.resizePopup(height: scrollView.frame.size.height + bottomBar.frame.size.height)
-  }
-  
-  func reloadData(at index: Int? = nil) {
-    services.sort()
-    
-    bottomBar.updateStatusText()
-    
-    guard index != nil else {
-      tableView.reloadData()
-      return
-    }
-    
-    tableView.reloadData(forRowIndexes: IndexSet(integer: index!), columnIndexes: IndexSet(integer: 0))
-  }
-  
-  func updateServices(updateCallback: @escaping () -> Void) {
-    self.servicesBeingUpdated = [Service]()
-    
-    guard services.count > 0 else {
-      reloadData()
-      bottomBar.status = .updated(Date())
-      
-      self.updateCallback?()
-      self.updateCallback = nil
-      
-      return
-    }
-    
-    self.updateCallback = updateCallback
-    let serviceCallback: ((BaseService) -> Void) = { [weak self] service in self?.updatedStatus(for: service) }
-    
-    bottomBar.status = .updating
-    
-    services.forEach {
-      servicesBeingUpdated.append($0)
-      $0.updateStatus(callback: serviceCallback)
-    }
-  }
-  
-  func updatedStatus(for service: BaseService) {
-    if let index = servicesBeingUpdated.index(of: service) {
-      servicesBeingUpdated.remove(at: index)
-    }
-    
-    DispatchQueue.main.async { [weak self] in
-      self?.reloadData()
-      
-      if self?.servicesBeingUpdated.count == 0 {
-        self?.bottomBar.status = .updated(Date())
-        
-        self?.updateCallback?()
-        self?.updateCallback = nil
-      }
-    }
-  }
-}
-
-extension ServiceTableViewController: NSTableViewDataSource {
-  func numberOfRows(in tableView: NSTableView) -> Int {
-    return services.count
-  }
-  
-  func tableView(_ tableView: NSTableView, objectValueFor tableColumn: NSTableColumn?, row: Int) -> Any? {
-    return nil
-  }
-}
-
-extension ServiceTableViewController: NSTableViewDelegate {
-  func tableView(_ tableView: NSTableView, viewFor tableColumn: NSTableColumn?, row: Int) -> NSView? {
-    let identifier = tableColumn?.identifier ?? NSUserInterfaceItemIdentifier(rawValue: "identifier")
-    let cell = tableView.makeView(withIdentifier: identifier, owner: self) ?? StatusTableCell()
-    
-    guard let view = cell as? StatusTableCell else { return nil }
-    guard let service = services[row] as? Service else { return nil }
-    
-    view.textField?.stringValue = service.name
-    view.statusField.stringValue = service.message
-    view.statusIndicator.status = service.status
-    
-    return view
-  }
-  
-  func tableView(_ tableView: NSTableView, rowViewForRow row: Int) -> NSTableRowView? {
-    let cellIdentifier = NSUserInterfaceItemIdentifier(rawValue: "rowView")
-    let cell = tableView.makeView(withIdentifier: cellIdentifier, owner: self) ?? ServiceTableRowView()
-    
-    guard let view = cell as? ServiceTableRowView else { return nil }
-    
-    view.showSeparator = row + 1 < services.count
-    
-    return view
-  }
-  
-  func tableView(_ tableView: NSTableView, shouldSelectRow row: Int) -> Bool {
-    guard let _ = services[row] as? Service else { return false }
-    
-    //NSWorkspace.shared.open(service.url)
-    return false
-  }
-}
diff --git a/launchers/macosx/I2PLauncher/userinterface/Style2019/StatusIndicator.swift b/launchers/macosx/I2PLauncher/userinterface/Style2019/StatusIndicator.swift
deleted file mode 100644
index 2e8cb1ceb967c866691fb085fbcdca9d6b3e1f96..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/Style2019/StatusIndicator.swift
+++ /dev/null
@@ -1,62 +0,0 @@
-//
-//  StatusIndicator.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 09/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-
-class StatusIndicator: NSView {
-  var checkmarkIcon = CheckmarkIcon()
-  var crossIcon = CrossIcon()
-  
-  var status: ServiceStatus = .started {
-    didSet {
-      checkmarkIcon.isHidden = status > .stopped
-      crossIcon.isHidden = status <= .stopped
-      
-      switch status {
-      case .undetermined: crossIcon.color = StatusColor.gray
-      case .waiting: checkmarkIcon.color = StatusColor.gray
-      case .started: checkmarkIcon.color = StatusColor.green
-      case .notice: checkmarkIcon.color = StatusColor.green
-      case .killed: checkmarkIcon.color = StatusColor.red
-      case .crashed: checkmarkIcon.color = StatusColor.red
-      case .stopped: crossIcon.color = StatusColor.blue
-      case .restarting: crossIcon.color = StatusColor.orange
-      }
-    }
-  }
-  
-  init() {
-    super.init(frame: NSRect.zero)
-    commonInit()
-  }
-  
-  required init?(coder: NSCoder) {
-    super.init(coder: coder)
-    commonInit()
-  }
-  
-  private func commonInit() {
-    addSubview(checkmarkIcon)
-    addSubview(crossIcon)
-  }
-  
-  override func setFrameSize(_ newSize: NSSize) {
-    super.setFrameSize(newSize)
-    
-    checkmarkIcon.frame = bounds
-    crossIcon.frame = bounds
-  }
-}
-
-class StatusColor {
-  static var green = NSColor(calibratedRed: 0.36, green: 0.68, blue: 0.46, alpha: 1)
-  static var blue = NSColor(calibratedRed: 0.24, green: 0.54, blue: 1, alpha: 0.8)
-  static var orange = NSColor.orange
-  static var red = NSColor(calibratedRed: 0.9, green: 0.4, blue: 0.23, alpha: 1)
-  static var gray = NSColor.tertiaryLabelColor
-}
diff --git a/launchers/macosx/I2PLauncher/userinterface/Style2019/StatusTableCell.swift b/launchers/macosx/I2PLauncher/userinterface/Style2019/StatusTableCell.swift
deleted file mode 100644
index d050e31e6de69f6e508d52f5f58f0ed0752b62f6..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/Style2019/StatusTableCell.swift
+++ /dev/null
@@ -1,78 +0,0 @@
-//
-//  StatusTableCell.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 18/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-import SnapKit
-
-class StatusTableCell: NSTableCellView {
-  let statusIndicator = StatusIndicator()
-  let statusField = NSTextField()
-  
-  override init(frame frameRect: NSRect) {
-    super.init(frame: frameRect)
-    commonInit()
-  }
-  
-  required init?(coder: NSCoder) {
-    super.init(coder: coder)
-    commonInit()
-  }
-  
-  private func commonInit() {
-    statusIndicator.scaleUnitSquare(to: NSSize(width: 0.3, height: 0.3))
-    addSubview(statusIndicator)
-    
-    statusIndicator.snp.makeConstraints { make in
-      make.height.width.equalTo(14)
-      make.left.equalTo(8)
-      make.centerY.equalToSuperview()
-    }
-    
-    let textField = NSTextField()
-    textField.isEditable = false
-    textField.isBordered = false
-    textField.isSelectable = false
-    self.textField = textField
-    let font = NSFont.systemFont(ofSize: 12)
-    textField.font = font
-    textField.textColor = NSColor.labelColor
-    textField.backgroundColor = NSColor.clear
-    addSubview(textField)
-    
-    textField.snp.makeConstraints { make in
-      make.height.equalTo(18)
-      make.leading.equalTo(statusIndicator.snp.trailing).offset(4)
-      make.trailing.equalTo(8)
-      make.centerY.equalToSuperview().offset(-8)
-    }
-    
-    statusField.isEditable = false
-    statusField.isBordered = false
-    statusField.isSelectable = false
-    
-    let italicFont = NSFontManager.shared.font(
-      withFamily: font.fontName,
-      traits: NSFontTraitMask.italicFontMask,
-      weight: 5,
-      size: 10
-    )
-    statusField.font = italicFont
-    statusField.textColor = NSColor.secondaryLabelColor
-    statusField.maximumNumberOfLines = 1
-    statusField.cell!.truncatesLastVisibleLine = true
-    statusField.backgroundColor = NSColor.clear
-    addSubview(statusField)
-    
-    statusField.snp.makeConstraints { make in
-      make.height.equalTo(18)
-      make.leading.equalTo(statusIndicator.snp.trailing).offset(4)
-      make.trailing.equalToSuperview().offset(-8)
-      make.centerY.equalToSuperview().offset(10)
-    }
-  }
-}
diff --git a/launchers/macosx/I2PLauncher/userinterface/Style2019/SwitchableTableViewController.swift b/launchers/macosx/I2PLauncher/userinterface/Style2019/SwitchableTableViewController.swift
deleted file mode 100644
index 4999bfb5e9cd8d22aca1cd0ecd065cba0f87296f..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/Style2019/SwitchableTableViewController.swift
+++ /dev/null
@@ -1,31 +0,0 @@
-//
-//  SwitchableTableViewController.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 30/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-
-protocol SwitchableTableViewController {
-  var hidden: Bool { get set }
-  
-  mutating func show()
-  mutating func hide()
-  func willShow()
-  func willHide()
-}
-
-extension SwitchableTableViewController {
-  mutating func show() {
-    self.hidden = false
-    self.willShow()
-  }
-  
-  mutating func hide() {
-    self.hidden = true
-    self.willHide()
-  }
-}
-
diff --git a/launchers/macosx/I2PLauncher/userinterface/preferences/AdvancedTableView.swift b/launchers/macosx/I2PLauncher/userinterface/preferences/AdvancedTableView.swift
deleted file mode 100644
index 76a4bb3d1716971c191ed3f323892ee603c21c38..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/preferences/AdvancedTableView.swift
+++ /dev/null
@@ -1,17 +0,0 @@
-//
-//  AdvancedTableView.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 08/12/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-
-
-class AdvancedTableView: NSTableView {
-  override func viewWillDraw() {
-    super.viewWillDraw()
-  }
-}
-
diff --git a/launchers/macosx/I2PLauncher/userinterface/preferences/PreferencesViewController+TableView.swift b/launchers/macosx/I2PLauncher/userinterface/preferences/PreferencesViewController+TableView.swift
deleted file mode 100644
index b9bf125e568faa9408ac2659a36c751ddc8dee5c..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/preferences/PreferencesViewController+TableView.swift
+++ /dev/null
@@ -1,96 +0,0 @@
-//
-//  PreferencesViewController+TableView.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 08/12/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-
-extension PreferencesViewController: NSTableViewDataSource {
-  
-  func numberOfRows(in tableView: NSTableView) -> Int {
-    return Preferences.shared().count
-  }
-  
-}
-
-extension PreferencesViewController: NSTableViewDelegate {
-  
-  fileprivate enum CellIdentifiers {
-    static let NameCell = "KeyColumnID"
-    static let DefaultCell = "DefaultColumnID"
-    static let ValueCell = "ValueColumnID"
-  }
-  
-  @objc func tableViewDoubleClick(_ sender:AnyObject) {
-    print("Double click")
-    // 1
-    print(self.advPrefTableView.selectedRow)
-    guard self.advPrefTableView.selectedRow >= 0,
-      let item = Preferences.shared()[self.advPrefTableView.selectedRow] else {
-        return
-    }
-    print(item.name as Any)
-     /*
-     if item.isFolder {
-     // 2
-     self.representedObject = item.url as Any
-     }
-     else {
-     // 3
-     NSWorkspace.shared().open(item.url as URL)
-     }
-     */
-  }
-  
-  func tableView(_ tableView: NSTableView, sortDescriptorsDidChange oldDescriptors: [NSSortDescriptor]) {
-    // 1
-    guard let /*sortDescriptor*/ _ = self.advPrefTableView.sortDescriptors.first else {
-      return
-    }
-    /*if let order = Directory.FileOrder(rawValue: sortDescriptor.key!) {
-     // 2
-     sortOrder = order
-     sortAscending = sortDescriptor.ascending
-     reloadFileList()
-     }*/
-  }
-  
-  
-  func tableView(_ tableView: NSTableView, viewFor tableColumn: NSTableColumn?, row: Int) -> NSView? {
-    
-    //var image: NSImage?
-    var text: String = ""
-    var cellIdentifier: String = ""
-    
-    
-    // 1
-    guard let item = Preferences.shared()[row] else {
-      return nil
-    }
-    
-    // 2
-    if tableColumn == tableView.tableColumns[0] {
-      text = item.name!
-      cellIdentifier = CellIdentifiers.NameCell
-    } else if tableColumn == tableView.tableColumns[1] {
-      text = "\(item.defaultValue ?? "")"
-      cellIdentifier = CellIdentifiers.DefaultCell
-    } else if tableColumn == tableView.tableColumns[2] {
-      let thing = (item.selectedValue ?? "none")
-      text = "\(thing)"
-      cellIdentifier = CellIdentifiers.ValueCell
-    }
-    
-    // 3
-    if let cell = tableView.makeView(withIdentifier: NSUserInterfaceItemIdentifier(rawValue: cellIdentifier), owner: nil) as? NSTableCellView {
-      cell.textField?.stringValue = text
-      //cell.imageView?.image = image ?? nil
-      return cell
-    }
-    return nil
-  }
-  
-}
diff --git a/launchers/macosx/I2PLauncher/userinterface/preferences/PreferencesViewController.swift b/launchers/macosx/I2PLauncher/userinterface/preferences/PreferencesViewController.swift
deleted file mode 100644
index 1ce3b78cf5b331227cab067618fa04a34285a592..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/preferences/PreferencesViewController.swift
+++ /dev/null
@@ -1,290 +0,0 @@
-//
-//  PreferencesViewController.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 07/11/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-// Table view programming guide from Apple:
-// https://developer.apple.com/library/archive/documentation/Cocoa/Conceptual/TableView/Introduction/Introduction.html
-//
-
-import Cocoa
-import ServiceManagement
-
-
-@objc class PreferencesViewController: NSViewController {
-  
-  
-  var changeDockMenubarIconTimer: Timer?
-  
-  // MARK: - Advanced settings objects
-  @IBOutlet weak var advPrefTableView: NSTableView!
-  
-  // MARK: - Launcher settings objects
-  @IBOutlet var radioDockIcon: NSButton?
-  @IBOutlet var radioMenubarIcon: NSButton?
-  @IBOutlet var radioBothIcon: NSButton?
-  @IBOutlet var checkboxStartWithOSX: NSButton?
-  @IBOutlet var checkboxStartFirefoxAlso: NSButton?
-  
-  // MARK: - Router objects
-  @IBOutlet var checkboxStartWithLauncher: NSButton?
-  @IBOutlet var checkboxStopWithLauncher: NSButton?
-  @IBOutlet var buttonResetRouterConfig: NSButton?
-  
-  @IBAction func onEnterInTextField(_ sender: NSTextField) {
-    let selectedRowNumber = advPrefTableView.selectedRow
-    print("Trying to store preferences")
-    let currentItem = Preferences.shared()[selectedRowNumber]
-    currentItem?.selectedValue = sender.stringValue
-    Preferences.shared()[selectedRowNumber] = currentItem
-    UserDefaults.standard.set(sender.stringValue, forKey: (currentItem?.name)!)
-    Preferences.shared().syncPref()
-  }
-  
-  override func viewDidLoad() {
-    super.viewDidLoad()
-    
-    self.preferredContentSize = NSMakeSize(self.view.frame.size.width, self.view.frame.size.height)
-    
-    if (advPrefTableView != nil) {
-      // For data feeding and view
-      advPrefTableView.delegate = self
-      advPrefTableView.dataSource = self
-      
-      // Responding to Double-Click
-      advPrefTableView.target = self
-      advPrefTableView.doubleAction = #selector(tableViewDoubleClick(_:))
-      
-      // Always redraw preference items which might have changed state since last draw.
-      Preferences.shared().redrawPrefTableItems()
-      
-      // For sorting
-      advPrefTableView.tableColumns[0].sortDescriptorPrototype = NSSortDescriptor(key: "name", ascending: true)
-      advPrefTableView.tableColumns[1].sortDescriptorPrototype = NSSortDescriptor(key: "defaultValue", ascending: true)
-      advPrefTableView.tableColumns[2].sortDescriptorPrototype = NSSortDescriptor(key: "selectedValue", ascending: true)
-      
-      self.advPrefTableView.isEnabled = Preferences.shared().allowAdvancedPreferenceEdit
-    }
-    
-    // Update radio buttons to reflect runtime/stored preferences
-    self.updateRadioButtonEffect(mode: Preferences.shared().showAsIconMode, withSideEffect: false)
-    
-    if (Preferences.shared().stopRouterOnLauncherShutdown) {
-      self.checkboxStopWithLauncher?.state = NSControl.StateValue.on;
-    } else {
-      self.checkboxStopWithLauncher?.state = NSControl.StateValue.off;
-    }
-    if (Preferences.shared().startRouterOnLauncherStart) {
-      self.checkboxStartWithLauncher?.state = NSControl.StateValue.on;
-    } else {
-      self.checkboxStartWithLauncher?.state = NSControl.StateValue.off;
-    }
-    
-    
-  }
-  
-  override func viewDidAppear() {
-    super.viewDidAppear()
-    
-    // Update window title
-    self.parent?.view.window?.title = self.title!
-  }
-  
-  // MARK: - Router settings functions
-  
-  @IBAction func checkboxStartRouterWithLauncherClicked(_ sender: NSButton) {
-    switch sender.state {
-    case NSControl.StateValue.on:
-      print("on")
-      Preferences.shared().startRouterOnLauncherStart = true
-    case NSControl.StateValue.off:
-      print("off")
-      Preferences.shared().startRouterOnLauncherStart = false
-    default: break
-    }
-  }
-  
-  @IBAction func checkboxStopRouterWithLauncherClicked(_ sender: NSButton) {
-    switch sender.state {
-    case NSControl.StateValue.on:
-      print("on")
-      Preferences.shared().stopRouterOnLauncherShutdown = true
-    case NSControl.StateValue.off:
-      print("off")
-      Preferences.shared().stopRouterOnLauncherShutdown = false
-    default: break
-    }
-  }
-  
-  @IBAction func buttonResetRouterConfigClicked(_ sender: Any) {
-    // TODO: Add a modal dialog asking user if they are **really** sure
-  }
-  
-  // MARK: - Launcher settings functions
-  
-  @IBAction func checkboxStartLauncherOnOSXStartupClicked(_ sender: NSButton) {
-    let launcherAppId = "net.i2p.bootstrap.macosx.StartupItemApp"
-    let startupMgr = Startup()
-    switch sender.state {
-    case NSControl.StateValue.on:
-      print("on")
-      Preferences.shared()["I2Pref_startLauncherAtLogin"] = true
-      if (Preferences.shared()["I2Pref_useServiceManagementAsStartupTool"] as! Bool)
-      {
-        let success = SMLoginItemSetEnabled(launcherAppId as CFString, true)
-        print("SMLoginItemSetEnabled returned \(success)....")
-      } else {
-        let _ = startupMgr.addLoginItem(Startup.appPath())
-        print("Shared file for auto-startup added. (viewable via OSX Preferences -> Users -> Login Items)")
-      }
-    case NSControl.StateValue.off:
-      print("off")
-      Preferences.shared()["I2Pref_startLauncherAtLogin"] = false
-      if (Preferences.shared()["I2Pref_useServiceManagementAsStartupTool"] as! Bool)
-      {
-        let success = SMLoginItemSetEnabled(launcherAppId as CFString, false)
-        print("SMLoginItemSetEnabled returned \(success)....")
-      } else {
-        let _ = startupMgr.removeLoginItem(Startup.appPath())
-        print("Shared file for auto-startup removed (if any). (viewable via OSX Preferences -> Users -> Login Items)")
-      }
-    default: break
-    }
-  }
-  @IBAction func checkboxStartFirefoxAlsoAtLaunchClicked(_ sender: NSButton) {
-    switch sender.state {
-    case NSControl.StateValue.on:
-      print("launch firefox: on")
-      Preferences.shared().alsoStartFirefoxOnLaunch = true
-    case NSControl.StateValue.off:
-      print("launch firefox: off")
-      Preferences.shared().alsoStartFirefoxOnLaunch = false
-    default: break
-    }
-  }
-  
-  // MARK: - Radio buttons functions
-  
-  func updateDockMenubarIcons(_ mode: Preferences.ShowAsMode) -> Bool {
-    // Update preferences with latest choise
-    Preferences.shared().showAsIconMode = mode
-    // Update runtime
-    switch mode {
-    case .bothIcon, .dockIcon:
-      // Show dock icon
-      print("Preferences: Update Dock Icon -> Show")
-      if (!getDockIconStateIsShowing()) {
-        return triggerDockIconShowHide(showIcon: true)
-      }
-    case .menubarIcon:
-      // Hide dock icon
-      print("Preferences: Update Dock Icon -> Hide")
-      if (getDockIconStateIsShowing()) {
-        return triggerDockIconShowHide(showIcon: false)
-      }
-    }
-    // Note: In reality, this won't ever happen.
-    // The switch statement above would return before this.
-    return false
-  }
-  
-  func updateRadioButtonEffect(mode: Preferences.ShowAsMode, withSideEffect: Bool = true) {
-    changeDockMenubarIconTimer?.invalidate()
-    
-    radioDockIcon?.state = NSControl.StateValue.off
-    radioMenubarIcon?.state = NSControl.StateValue.off
-    radioBothIcon?.state = NSControl.StateValue.off
-    
-    switch mode {
-    case .bothIcon:
-      radioBothIcon?.state = NSControl.StateValue.on
-    case .dockIcon:
-      radioDockIcon?.state = NSControl.StateValue.on
-    case .menubarIcon:
-      radioMenubarIcon?.state = NSControl.StateValue.on
-    }
-    
-    if (withSideEffect) {
-      if #available(OSX 10.12, *) {
-        changeDockMenubarIconTimer = Timer.scheduledTimer(withTimeInterval: 0.3, repeats: false, block: { _ in
-          // If we're on 10.12 or later
-          let _ = self.updateDockMenubarIcons(mode)
-        })
-      } else {
-        // Fallback on earlier versions
-        let _ = self.updateDockMenubarIcons(mode)
-      }
-    }
-  }
-  
-  @IBAction func radioBothIconSelected(_ sender: Any) {
-    updateRadioButtonEffect(mode: Preferences.ShowAsMode.bothIcon)
-  }
-  
-  @IBAction func radioDockIconOnlySelected(_ sender: Any) {
-    updateRadioButtonEffect(mode: Preferences.ShowAsMode.dockIcon)
-  }
-  
-  @IBAction func radioMenubarOnlySelected(_ sender: Any) {
-    updateRadioButtonEffect(mode: Preferences.ShowAsMode.menubarIcon)
-  }
-  
-  // MARK: - Triggers
-  
-  func triggerDockIconHideShow(showIcon state: Bool) -> Bool {
-    // Get transform state.
-    var transformState: ProcessApplicationTransformState
-    if state {
-      transformState = ProcessApplicationTransformState(kProcessTransformToForegroundApplication)
-    } else {
-      transformState = ProcessApplicationTransformState(kProcessTransformToUIElementApplication)
-    }
-    
-    // Show / hide dock icon.
-    var psn = ProcessSerialNumber(highLongOfPSN: 0, lowLongOfPSN: UInt32(kCurrentProcess))
-    let transformStatus: OSStatus = TransformProcessType(&psn, transformState)
-    return transformStatus == 0
-  }
-  
-  func triggerDockIconShowHide(showIcon state: Bool) -> Bool {
-    var result: Bool
-    if state {
-      result = NSApp.setActivationPolicy(NSApplication.ActivationPolicy.regular)
-    } else {
-      result = NSApp.setActivationPolicy(NSApplication.ActivationPolicy.accessory)
-    }
-    return result
-  }
-  
-  func getDockIconStateIsShowing() -> Bool {
-    if NSApp.activationPolicy() == NSApplication.ActivationPolicy.regular {
-      return true
-    } else {
-      return false
-    }
-  }
-  
-  
-  // MARK: - Advanced
-  
-  @IBAction func checkboxEnableAdvancedPreferencesClicked(_ sender: NSButton) {
-    switch sender.state {
-    case NSControl.StateValue.on:
-      print("on")
-      Preferences.shared().allowAdvancedPreferenceEdit = true
-      self.advPrefTableView.isEnabled = true
-    case NSControl.StateValue.off:
-      print("off")
-      Preferences.shared().allowAdvancedPreferenceEdit = false
-      self.advPrefTableView.isEnabled = false
-    default: break
-    }
-  }
-
-  
-  // End of Class
-}
-
-
diff --git a/launchers/macosx/I2PLauncher/userinterface/preferences/PreferencesWindowController.swift b/launchers/macosx/I2PLauncher/userinterface/preferences/PreferencesWindowController.swift
deleted file mode 100644
index 1bed6b3d2b700b624020220ca1c99e4d655cf6ad..0000000000000000000000000000000000000000
--- a/launchers/macosx/I2PLauncher/userinterface/preferences/PreferencesWindowController.swift
+++ /dev/null
@@ -1,32 +0,0 @@
-//
-//  PreferencesWindowController.swift
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 07/11/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-
-class PreferencesWindowController: NSWindowController, NSWindowDelegate {
-
-  override func windowDidLoad() {
-    super.windowDidLoad()
-  
-    let visualEffect = NSVisualEffectView()
-    visualEffect.blendingMode = .behindWindow
-    visualEffect.state = .active
-    visualEffect.material = .dark
-    //self.window?.contentView = visualEffect
-    
-    //self.window?.titlebarAppearsTransparent = true
-    //self.window?.styleMask.insert(.fullSizeContentView)
-    window?.titlebarAppearsTransparent = true
-  }
-  
-  func windowShouldClose(_ sender: NSWindow) -> Bool {
-    self.window?.orderOut(sender)
-    return false
-  }
-
-}
diff --git a/launchers/macosx/ItoopieTransparent.png b/launchers/macosx/ItoopieTransparent.png
deleted file mode 100644
index 5edecdc1a19c9f8d7da9f6e646018c408f2efdf6..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/ItoopieTransparent.png and /dev/null differ
diff --git a/launchers/macosx/Licenses/Kanna.License b/launchers/macosx/Licenses/Kanna.License
deleted file mode 100644
index 30070bedd5f9f937683aa0a35f8b79e689511e5a..0000000000000000000000000000000000000000
--- a/launchers/macosx/Licenses/Kanna.License
+++ /dev/null
@@ -1,21 +0,0 @@
-The MIT License (MIT)
-
-Copyright (c) 2014 - 2015 Atsushi Kiwaki (@_tid_)
-
-Permission is hereby granted, free of charge, to any person obtaining a copy
-of this software and associated documentation files (the "Software"), to deal
-in the Software without restriction, including without limitation the rights
-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-copies of the Software, and to permit persons to whom the Software is
-furnished to do so, subject to the following conditions:
-
-The above copyright notice and this permission notice shall be included in all
-copies or substantial portions of the Software.
-
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
-SOFTWARE.
\ No newline at end of file
diff --git a/launchers/macosx/Licenses/MBPopup.License b/launchers/macosx/Licenses/MBPopup.License
deleted file mode 100644
index 41c13540e184e7a2d796fcc3b5cf751ee80d8d27..0000000000000000000000000000000000000000
--- a/launchers/macosx/Licenses/MBPopup.License
+++ /dev/null
@@ -1,21 +0,0 @@
-The MIT License (MIT)
-
-Copyright (c) Mahdi Bchetnia 2016
-
-Permission is hereby granted, free of charge, to any person obtaining a copy
-of this software and associated documentation files (the "Software"), to deal
-in the Software without restriction, including without limitation the rights
-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-copies of the Software, and to permit persons to whom the Software is
-furnished to do so, subject to the following conditions:
-
-The above copyright notice and this permission notice shall be included in all
-copies or substantial portions of the Software.
-
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
-SOFTWARE.
diff --git a/launchers/macosx/Licenses/SnapKit.License b/launchers/macosx/Licenses/SnapKit.License
deleted file mode 100644
index a18ccfbd9563176bddb26c686bc01902b634b43c..0000000000000000000000000000000000000000
--- a/launchers/macosx/Licenses/SnapKit.License
+++ /dev/null
@@ -1,19 +0,0 @@
-Copyright (c) 2011-Present SnapKit Team - https://github.com/SnapKit
-
-Permission is hereby granted, free of charge, to any person obtaining a copy
-of this software and associated documentation files (the "Software"), to deal
-in the Software without restriction, including without limitation the rights
-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-copies of the Software, and to permit persons to whom the Software is
-furnished to do so, subject to the following conditions:
-
-The above copyright notice and this permission notice shall be included in
-all copies or substantial portions of the Software.
-
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
-THE SOFTWARE.
diff --git a/launchers/macosx/Licenses/Sparkle.License b/launchers/macosx/Licenses/Sparkle.License
deleted file mode 100644
index 1e9b1c6e6f2619dae7877d32b3af3520bfa02dbc..0000000000000000000000000000000000000000
--- a/launchers/macosx/Licenses/Sparkle.License
+++ /dev/null
@@ -1,61 +0,0 @@
-Copyright (c) 2006-2013 Andy Matuschak.
-Copyright (c) 2009-2013 Elgato Systems GmbH.
-Copyright (c) 2011-2014 Kornel Lesiński.
-Copyright (c) 2015-2017 Mayur Pawashe.
-Copyright (c) 2014 C.W. Betts.
-Copyright (c) 2014 Petroules Corporation.
-Copyright (c) 2014 Big Nerd Ranch.
-All rights reserved.
-
-Permission is hereby granted, free of charge, to any person obtaining a copy of
-this software and associated documentation files (the "Software"), to deal in
-the Software without restriction, including without limitation the rights to
-use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
-the Software, and to permit persons to whom the Software is furnished to do so,
-subject to the following conditions:
-
-The above copyright notice and this permission notice shall be included in all
-copies or substantial portions of the Software.
-
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
-FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
-COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
-IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
-CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-
-=================
-EXTERNAL LICENSES
-=================
-
-bspatch.c and bsdiff.c, from bsdiff 4.3 <http://www.daemonology.net/bsdiff/>:
-    Copyright (c) 2003-2005 Colin Percival.
-
-sais.c and sais.c, from sais-lite (2010/08/07) <https://sites.google.com/site/yuta256/sais>:
-    Copyright (c) 2008-2010 Yuta Mori.
-
-SUDSAVerifier.m:
-    Copyright (c) 2011 Mark Hamlin.
-
-All rights reserved.
-
-Redistribution and use in source and binary forms, with or without
-modification, are permitted providing that the following conditions
-are met:
-1. Redistributions of source code must retain the above copyright
-   notice, this list of conditions and the following disclaimer.
-2. Redistributions in binary form must reproduce the above copyright
-   notice, this list of conditions and the following disclaimer in the
-   documentation and/or other materials provided with the distribution.
-
-THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
-IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
-WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
-ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
-DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
-DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
-OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
-HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
-STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
-IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
-POSSIBILITY OF SUCH DAMAGE.
diff --git a/launchers/macosx/Licenses/SwiftDate.License b/launchers/macosx/Licenses/SwiftDate.License
deleted file mode 100644
index 807f30103b22b7d7893d7c151cbc32d4f6c7d0cf..0000000000000000000000000000000000000000
--- a/launchers/macosx/Licenses/SwiftDate.License
+++ /dev/null
@@ -1,22 +0,0 @@
-The MIT License (MIT)
-
-Copyright (c) 2018 Daniele Margutti
-
-Permission is hereby granted, free of charge, to any person obtaining a copy
-of this software and associated documentation files (the "Software"), to deal
-in the Software without restriction, including without limitation the rights
-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-copies of the Software, and to permit persons to whom the Software is
-furnished to do so, subject to the following conditions:
-
-The above copyright notice and this permission notice shall be included in all
-copies or substantial portions of the Software.
-
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
-SOFTWARE.
-
diff --git a/launchers/macosx/Podfile b/launchers/macosx/Podfile
deleted file mode 100644
index da54edc9dbfd6fb7a8bcbcf127b1f8b6d2d9e233..0000000000000000000000000000000000000000
--- a/launchers/macosx/Podfile
+++ /dev/null
@@ -1,14 +0,0 @@
-# Uncomment the next line to define a global platform for your project
-# platform :ios, '9.0'
-platform :osx, '10.12'
-
-target 'I2PLauncher' do
-  # Comment the next line if you're not using Swift and don't want to use dynamic frameworks
-  use_frameworks!
-
-  # Pods for I2PLauncher
-  pod 'MBPopup'
-  pod 'SnapKit'
-  pod 'SwiftDate'
-  pod 'Kanna'
-end
diff --git a/launchers/macosx/README.md b/launchers/macosx/README.md
deleted file mode 100644
index 92713a51bb2320dfb6aeb5b9f66f8ab9826082bd..0000000000000000000000000000000000000000
--- a/launchers/macosx/README.md
+++ /dev/null
@@ -1,55 +0,0 @@
-# The Mac OS X Launcher
-
-## The Event Manager
-
-This is some Swift code which makes the application use events to signal the different compoents of the application. This seems to be the cleanest way since we're doing java subprocesses and so on. This can also be named a publish-subscribe system as well. If you're familiar with Javascript it would be a handy skill.
-
-### Event Overview
-
-| Event name | Details sent as arguments | Description |
-| ------------- | ------------- | ------------- |
-| router_start | nothing | This event get triggered when the router starts |
-| router_exception | exception message | This will be triggered in case something within the functions that start the java (router) subprocess throws an exception |
-| java_found | the location | This will be triggered once the DetectJava swift class has found java |
-| router_must_upgrade | nothing | This will be triggered if no I2P is found, or if it's failing to get the version from the jar file |
-| extract_completed | nothing | This is triggered when the deployment process is done extracting I2P to it's directory |
-| router_can_start | nothing | This event will be triggered when I2P is found and a version number has been found, router won't start before this event |
-| router_stop | error if any | Triggered when the router subprocess exits |
-| router_pid | the pid number as string | Triggered when we know the pid of the router subprocess |
-| router_version | the version string | Triggered when we have successfully extracted current I2P version |
-| extract_errored | the error message | Triggered if the process didn't exit correctly |
-| router_already_running | an error message | Triggered if any processes containing i2p.jar in name/arguments already exists upon router launch |
-
-## Misc
-
-**Note** this project is WIP, cause Meeh has yet to merge in Obj-C/Swift code for GUI stuff in OSX.
-
-However, this is a thin wrapper launching both Mac OS X trayicon and the I2P router - and make them talk together.
-
-More code will be merged in, it's just a f* mess which Meeh needs to clean up and move into repo.
-
-### Java Auto Downloader
-
-We got a quite reliable source regarding the download url,
-https://github.com/Homebrew/homebrew-cask/raw/master/Casks/java.rb
-
-Homebrew is quite well maintained on OSX and any updates at Oracle should quickly reflect to brew, which again will be noticed upon builds.
-
-## Howto build
-
-You can both build the project from the Xcode UI or you can build it from command line.
-
-An example build command:
-`REPACK_I2P=1 xcodebuild -target I2PLauncher -sdk /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk`
-
-**Note** you don't need REPACK_I2P except for the first build, and each time you wish to repack the zip file containing i2p.
-
-## Objective-C / Swift Links
-
-* https://nshipster.com/at-compiler-directives/
-* https://developer.apple.com/documentation/swift/cocoa_design_patterns/handling_cocoa_errors_in_swift
-* https://content.pivotal.io/blog/rails-to-ios-what-the-are-these-symbols-in-my-code
-* https://mackuba.eu/2008/10/05/learn-objective-c-in-30-minutes/
-* https://en.wikipedia.org/wiki/Objective-C
-* http://cocoadevcentral.com/d/learn_objectivec/
-
diff --git a/launchers/macosx/RouterWrapper/main.swift b/launchers/macosx/RouterWrapper/main.swift
deleted file mode 100644
index e240b221fd7e5e1eaa84ae33fca2c00bd87fd7a2..0000000000000000000000000000000000000000
--- a/launchers/macosx/RouterWrapper/main.swift
+++ /dev/null
@@ -1,54 +0,0 @@
-//
-//  main.swift
-//  RouterWrapper
-//
-//  Created by Mikal Villa on 24/04/2019.
-//  Copyright © 2019 The I2P Project. All rights reserved.
-//
-
-import Foundation
-
-let applicationsSupportPath: URL = FileManager.default.urls(for: .applicationSupportDirectory, in: .userDomainMask).first!
-
-let defaultStartupFlags:[String] = [
-  "-Djava.awt.headless=true",
-  "".appendingFormat("-Di2p.base.dir=%@", Preferences.shared().i2pBaseDirectory),
-  "".appendingFormat("-Dwrapper.logfile=%@/i2p/router.log", applicationsSupportPath.absoluteString),
-  "".appendingFormat("-Dwrapper.java.pidfile=%@/i2p/router.pid", applicationsSupportPath.absoluteString),
-  "-Dwrapper.logfile.loglevel=DEBUG", // TODO: Allow loglevel to be set from Preferences?
-  "-Dwrapper.console.loglevel=DEBUG",
-  "net.i2p.router.Router"
-]
-
-let javaCliArgs = Preferences.shared().javaCommandPath.splitByWhitespace()
-
-let daemonPath = javaCliArgs[0]
-let arguments = defaultStartupFlags.joined(separator: " ")
-
-let basePath = Preferences.shared().i2pBaseDirectory
-
-let jars = try! FileManager.default.contentsOfDirectory(atPath: basePath+"/lib")
-var classpath:String = "."
-for jar in jars {
-  if (jar.hasSuffix(".jar")) {
-    classpath += ":"+basePath+"/lib/"+jar
-  }
-}
-
-var cliArgs:[String] = []
-cliArgs.append(contentsOf: javaCliArgs.dropFirst())
-cliArgs.append(contentsOf: [
-  "-cp",
-  classpath,
-  ])
-// This allow java arguments to be passed from the settings
-cliArgs.append(contentsOf: Preferences.shared().javaCommandOptions.splitByWhitespace())
-cliArgs.append(contentsOf: defaultStartupFlags)
-
-print(cliArgs)
-
-let javaProc = Subprocess.init(executablePath: daemonPath, arguments: cliArgs, workingDirectory: basePath)
-
-let exitCode = javaProc.run()
-
-print("Exited with code \(exitCode)")
diff --git a/launchers/macosx/StartupItemApp/AppDelegate.swift b/launchers/macosx/StartupItemApp/AppDelegate.swift
deleted file mode 100644
index eed91414ce658f77d0a4e87c49ad7aba0a0d59c6..0000000000000000000000000000000000000000
--- a/launchers/macosx/StartupItemApp/AppDelegate.swift
+++ /dev/null
@@ -1,53 +0,0 @@
-//
-//  AppDelegate.swift
-//  StartupItemApp
-//
-//  Created by Mikal Villa on 21/12/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-import Cocoa
-
-extension Notification.Name {
-  static let killLauncher = Notification.Name("killStartupLauncher")
-}
-
-@NSApplicationMain
-class AppDelegate: NSObject {
-  
-  @objc func terminate() {
-    NSApp.terminate(nil)
-  }
-}
-
-extension AppDelegate: NSApplicationDelegate {
-  
-  func applicationDidFinishLaunching(_ aNotification: Notification) {
-    
-    let runningApps = NSWorkspace.shared.runningApplications
-    let isRunning = !runningApps.filter { $0.bundleIdentifier == Identifiers.mainApplicationBundleId }.isEmpty
-    
-    if !isRunning {
-      DistributedNotificationCenter.default().addObserver(self,
-                                                          selector: #selector(self.terminate),
-                                                          name: .killLauncher,
-                                                          object: Identifiers.mainApplicationBundleId)
-      
-      let path = Bundle.main.bundlePath as NSString
-      var components = path.pathComponents
-      components.removeLast()
-      components.removeLast()
-      components.removeLast()
-      components.append("MacOS")
-      components.append("I2PLauncher") //main app name
-      
-      let newPath = NSString.path(withComponents: components)
-      
-      NSWorkspace.shared.launchApplication(newPath)
-    }
-    else {
-      self.terminate()
-    }
-  }
-}
-
diff --git a/launchers/macosx/StartupItemApp/Assets.xcassets/AppIcon.appiconset/Contents.json b/launchers/macosx/StartupItemApp/Assets.xcassets/AppIcon.appiconset/Contents.json
deleted file mode 100644
index 2db2b1c7c6c316500a7a34807648434289494ba1..0000000000000000000000000000000000000000
--- a/launchers/macosx/StartupItemApp/Assets.xcassets/AppIcon.appiconset/Contents.json
+++ /dev/null
@@ -1,58 +0,0 @@
-{
-  "images" : [
-    {
-      "idiom" : "mac",
-      "size" : "16x16",
-      "scale" : "1x"
-    },
-    {
-      "idiom" : "mac",
-      "size" : "16x16",
-      "scale" : "2x"
-    },
-    {
-      "idiom" : "mac",
-      "size" : "32x32",
-      "scale" : "1x"
-    },
-    {
-      "idiom" : "mac",
-      "size" : "32x32",
-      "scale" : "2x"
-    },
-    {
-      "idiom" : "mac",
-      "size" : "128x128",
-      "scale" : "1x"
-    },
-    {
-      "idiom" : "mac",
-      "size" : "128x128",
-      "scale" : "2x"
-    },
-    {
-      "idiom" : "mac",
-      "size" : "256x256",
-      "scale" : "1x"
-    },
-    {
-      "idiom" : "mac",
-      "size" : "256x256",
-      "scale" : "2x"
-    },
-    {
-      "idiom" : "mac",
-      "size" : "512x512",
-      "scale" : "1x"
-    },
-    {
-      "idiom" : "mac",
-      "size" : "512x512",
-      "scale" : "2x"
-    }
-  ],
-  "info" : {
-    "version" : 1,
-    "author" : "xcode"
-  }
-}
\ No newline at end of file
diff --git a/launchers/macosx/StartupItemApp/Assets.xcassets/Contents.json b/launchers/macosx/StartupItemApp/Assets.xcassets/Contents.json
deleted file mode 100644
index da4a164c918651cdd1e11dca5cc62c333f097601..0000000000000000000000000000000000000000
--- a/launchers/macosx/StartupItemApp/Assets.xcassets/Contents.json
+++ /dev/null
@@ -1,6 +0,0 @@
-{
-  "info" : {
-    "version" : 1,
-    "author" : "xcode"
-  }
-}
\ No newline at end of file
diff --git a/launchers/macosx/StartupItemApp/Info.plist b/launchers/macosx/StartupItemApp/Info.plist
deleted file mode 100644
index 1838b63020776e990c5af292d81377ca24d5de45..0000000000000000000000000000000000000000
--- a/launchers/macosx/StartupItemApp/Info.plist
+++ /dev/null
@@ -1,34 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
-<plist version="1.0">
-<dict>
-	<key>CFBundleDevelopmentRegion</key>
-	<string>$(DEVELOPMENT_LANGUAGE)</string>
-	<key>CFBundleExecutable</key>
-	<string>$(EXECUTABLE_NAME)</string>
-	<key>CFBundleIconFile</key>
-	<string></string>
-	<key>CFBundleIdentifier</key>
-	<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
-	<key>CFBundleInfoDictionaryVersion</key>
-	<string>6.0</string>
-	<key>CFBundleName</key>
-	<string>$(PRODUCT_NAME)</string>
-	<key>CFBundlePackageType</key>
-	<string>APPL</string>
-	<key>CFBundleShortVersionString</key>
-	<string>1.0</string>
-	<key>CFBundleVersion</key>
-	<string>1</string>
-	<key>LSBackgroundOnly</key>
-	<true/>
-	<key>LSMinimumSystemVersion</key>
-	<string>$(MACOSX_DEPLOYMENT_TARGET)</string>
-	<key>NSHumanReadableCopyright</key>
-	<string>Copyright © 2018 The I2P Project. All rights reserved.</string>
-	<key>NSMainNibFile</key>
-	<string>MainMenu</string>
-	<key>NSPrincipalClass</key>
-	<string>NSApplication</string>
-</dict>
-</plist>
diff --git a/launchers/macosx/StartupItemApp/StartupItemApp.entitlements b/launchers/macosx/StartupItemApp/StartupItemApp.entitlements
deleted file mode 100644
index 35dbb596f83d4976969064ed998895808e1f7ce1..0000000000000000000000000000000000000000
--- a/launchers/macosx/StartupItemApp/StartupItemApp.entitlements
+++ /dev/null
@@ -1,14 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
-<plist version="1.0">
-<dict>
-	<key>com.apple.security.app-sandbox</key>
-	<true/>
-	<key>com.apple.security.application-groups</key>
-	<array>
-		<string>$(TeamIdentifierPrefix).i2p</string>
-	</array>
-	<key>com.apple.security.files.user-selected.read-only</key>
-	<true/>
-</dict>
-</plist>
diff --git a/launchers/macosx/build.sbt b/launchers/macosx/build.sbt
deleted file mode 100644
index 5ac371620c096cb201b93460deadb34f4a748c71..0000000000000000000000000000000000000000
--- a/launchers/macosx/build.sbt
+++ /dev/null
@@ -1,35 +0,0 @@
-import java.io.{File, FileNotFoundException, FileOutputStream}
-import java.util.zip._
-
-lazy val i2pVersion = "0.9.35"
-
-lazy val cleanAllTask = taskKey[Unit]("Clean up and remove the OSX bundle")
-lazy val buildAppBundleTask = taskKey[Unit](s"Build an Mac OS X bundle for I2P ${i2pVersion}.")
-lazy val buildDeployZipTask = taskKey[String](s"Build an zipfile with base directory for I2P ${i2pVersion}.")
-lazy val bundleBuildPath = new File("./output")
-
-
-lazy val resDir = new File("./../installer/resources")
-lazy val i2pBuildDir = new File("./../pkg-temp")
-lazy val warsForCopy = new File(i2pBuildDir, "webapps").list.filter { f => f.endsWith(".war") }
-lazy val jarsForCopy = new File(i2pBuildDir, "lib").list.filter { f => f.endsWith(".jar") }
-
-
-// Unmanaged classpath will be available at compile time
-unmanagedClasspath in Compile ++= Seq(
-    baseDirectory.value / ".." / ".." / "pkg-temp" / "lib" / "router.jar",
-    baseDirectory.value / ".." / ".." / "pkg-temp" / "lib" / "i2p.jar"
-)
-
-unmanagedBase in Compile := baseDirectory.value / ".." / ".." / "pkg-temp" / "lib"
-
-assemblyOption in assembly := (assemblyOption in assembly).value.copy(includeScala = false, includeDependency = false)
-
-assemblyExcludedJars in assembly := {
-    val cp = (fullClasspath in assembly).value
-    cp filter { c => jarsForCopy.toList.contains(c.data.getName) }
-}
-
-javacOptions ++= Seq("-source", "1.7", "-target", "1.7")
-scalacOptions in Compile := Seq("-deprecated","-target:jvm-1.7")
-
diff --git a/launchers/macosx/bumpInfoPlist.sh b/launchers/macosx/bumpInfoPlist.sh
deleted file mode 100644
index 28728b4a38e67b68b86c2efc6d46b02a68cb87e9..0000000000000000000000000000000000000000
--- a/launchers/macosx/bumpInfoPlist.sh
+++ /dev/null
@@ -1,6 +0,0 @@
-#!/usr/bin/env ruby
-git = `sh /etc/profile; which git`.chomp
-app_build = `#{git} rev-list HEAD --count`.chomp.to_i
-`/usr/libexec/PlistBuddy -c "Set :CFBundleVersion #{app_build}" "${TARGET_BUILD_DIR}/${INFOPLIST_PATH}"`
-puts "Updated #{ENV['TARGET_BUILD_DIR']}/#{ENV['INFOPLIST_PATH']}"
-
diff --git a/launchers/macosx/check_latest_java.sh b/launchers/macosx/check_latest_java.sh
deleted file mode 100755
index 2f953b2b92ee1d8de7526c00c5a726480614d7d2..0000000000000000000000000000000000000000
--- a/launchers/macosx/check_latest_java.sh
+++ /dev/null
@@ -1,41 +0,0 @@
-#!/usr/bin/env bash
-DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
-SRCROOT=${SRCROOT:-"$DIR"}
-
-echo "SRCROOT == $SRCROOT"
-
-java_version=11
-jsubv=28
-randhash="55eed80b163941c8885ad9298e6d786a"
-cookie_header="Cookie: oraclelicense=accept-securebackup-cookie"
-url="http://download.oracle.com/otn-pub/java/jdk/${java_version}+${jsubv}/${randhash}/jdk-${java_version}_osx-x64_bin.dmg"
-
-expected_etag="81ee08846975d4b8d46acf3b6eddf103:1531792451.574613"
-
-
-curl -I -H '${cookie_header}' -v -L $url 2> .tmp-java-check.log
-up_to_date="$(grep '${expected_etag}' .tmp-java-check.log | perl -pe 'chomp')"
-
-if [ ! -z "${up_to_date}"]; then
-    echo "NEW JAVA VERSION!"
-    cat .tmp-java-check.log
-    exit 1;
-fi
-
-echo "Java version check: Up to date!";
-
-rm -f .tmp-java-check.log
-
-header_content=$(cat <<EOF
-#ifndef __META_DL_JAVA_H__
-#define __META_DL_JAVA_H__
-
-#define JAVA_DOWNLOAD_URL "$url"
-
-#endif // __META_DL_JAVA_H__
-EOF
-)
-
-echo $header_content > $SRCROOT/meta_dl_java.h && echo "Wrote url to file $SRCROOT/meta_dl_java.h"
-
-
diff --git a/launchers/macosx/download_and_build_sparkle.sh b/launchers/macosx/download_and_build_sparkle.sh
deleted file mode 100755
index e4e667151c2edc735c4cf01a0bd1088e2b7a3ba4..0000000000000000000000000000000000000000
--- a/launchers/macosx/download_and_build_sparkle.sh
+++ /dev/null
@@ -1,8 +0,0 @@
-#!/usr/bin/env bash
-git clone --recursive https://github.com/sparkle-project/Sparkle.git
-cd Sparkle
-git checkout 1.21.3
-xcodebuild -project Sparkle.xcodeproj -configuration Release -target All ARCHS=x86_64 ONLY_ACTIVE_ARCH=YES CONFIGURATION_BUILD_DIR=build clean
-xcodebuild -project Sparkle.xcodeproj -configuration Release -target All ARCHS=x86_64 ONLY_ACTIVE_ARCH=YES CONFIGURATION_BUILD_DIR=build
-
-
diff --git a/launchers/macosx/images/128x128-Itoopie Transparent.png b/launchers/macosx/images/128x128-Itoopie Transparent.png
deleted file mode 100644
index 6484936a817e5804aa0f73718ca1d454d2864e3f..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/images/128x128-Itoopie Transparent.png and /dev/null differ
diff --git a/launchers/macosx/images/128x128-Itoopie Transparent@2x.png b/launchers/macosx/images/128x128-Itoopie Transparent@2x.png
deleted file mode 100644
index ede3adf3c93eb1110e0df7d84c5045f0a04dfee2..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/images/128x128-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/images/16x16-Itoopie Transparent@2x.png b/launchers/macosx/images/16x16-Itoopie Transparent@2x.png
deleted file mode 100644
index d31fa068d83e48debcb7e987450ea2d837efcf1c..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/images/16x16-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/images/256x256-Itoopie Transparent.png b/launchers/macosx/images/256x256-Itoopie Transparent.png
deleted file mode 100644
index ede3adf3c93eb1110e0df7d84c5045f0a04dfee2..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/images/256x256-Itoopie Transparent.png and /dev/null differ
diff --git a/launchers/macosx/images/256x256-Itoopie Transparent@2x.png b/launchers/macosx/images/256x256-Itoopie Transparent@2x.png
deleted file mode 100644
index 3fd1aa390f23aa8b376a15b46f87112c76a0eaea..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/images/256x256-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/images/32x32-Itoopie Transparent.png b/launchers/macosx/images/32x32-Itoopie Transparent.png
deleted file mode 100644
index d31fa068d83e48debcb7e987450ea2d837efcf1c..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/images/32x32-Itoopie Transparent.png and /dev/null differ
diff --git a/launchers/macosx/images/32x32-Itoopie Transparent@2x.png b/launchers/macosx/images/32x32-Itoopie Transparent@2x.png
deleted file mode 100644
index 9eac5605c18ad4e7c7c5f70f20349266743e412c..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/images/32x32-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/images/512x512-Itoopie Transparent.png b/launchers/macosx/images/512x512-Itoopie Transparent.png
deleted file mode 100644
index 3fd1aa390f23aa8b376a15b46f87112c76a0eaea..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/images/512x512-Itoopie Transparent.png and /dev/null differ
diff --git a/launchers/macosx/images/512x512-Itoopie Transparent@2x.png b/launchers/macosx/images/512x512-Itoopie Transparent@2x.png
deleted file mode 100644
index 61780fc9e3f821a1395b5182ea5c386eb233f015..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/images/512x512-Itoopie Transparent@2x.png and /dev/null differ
diff --git a/launchers/macosx/images/AppIcon.icns b/launchers/macosx/images/AppIcon.icns
deleted file mode 100644
index 73faa6a532bed8ba1baf719d0c9679d4ad679d85..0000000000000000000000000000000000000000
Binary files a/launchers/macosx/images/AppIcon.icns and /dev/null differ
diff --git a/launchers/macosx/include/PidWatcher.h b/launchers/macosx/include/PidWatcher.h
deleted file mode 100644
index ed738686d077a1e86f8896c72924255b67d64e20..0000000000000000000000000000000000000000
--- a/launchers/macosx/include/PidWatcher.h
+++ /dev/null
@@ -1,40 +0,0 @@
-#pragma once
-
-#include <CoreFoundation/CoreFoundation.h>
-#include <unistd.h>
-#include <sys/event.h>
-
-
-using callbackType = void (CFFileDescriptorRef, CFOptionFlags, void *);
-using HandleFunction = std::function<void(int)>;
-
-static inline void noteProcDeath(CFFileDescriptorRef fdref, CFOptionFlags callBackTypes, void *info) {
-    struct kevent kev;
-    int fd = CFFileDescriptorGetNativeDescriptor(fdref);
-    kevent(fd, NULL, 0, &kev, 1, NULL);
-    // take action on death of process here
-    NSLog(@"process with pid '%u' died\n", (unsigned int)kev.ident);
-    //sendUserNotification(APP_IDSTR, @"The I2P router has stopped.");
-    CFFileDescriptorInvalidate(fdref);
-    CFRelease(fdref); // the CFFileDescriptorRef is no longer of any use in this example
-}
-// one argument, an integer pid to watch, required
-int watchPid(int pid, callbackType callback = noteProcDeath) {
-    int fd = kqueue();
-    struct kevent kev;
-    EV_SET(&kev, pid, EVFILT_PROC, EV_ADD|EV_ENABLE, NOTE_EXIT, 0, NULL);
-    kevent(fd, &kev, 1, NULL, 0, NULL);
-    CFFileDescriptorRef fdref = CFFileDescriptorCreate(kCFAllocatorDefault, fd, true, callback, NULL);
-    CFFileDescriptorEnableCallBacks(fdref, kCFFileDescriptorReadCallBack);
-    CFRunLoopSourceRef source = CFFileDescriptorCreateRunLoopSource(kCFAllocatorDefault, fdref, 0);
-    CFRunLoopAddSource(CFRunLoopGetMain(), source, kCFRunLoopDefaultMode);
-    CFRelease(source);
-    /*
-    seconds
-    The length of time to run the run loop. If 0, only one pass is made through the run loop before returning;
-    if multiple sources or timers are ready to fire immediately, only one (possibly two if one is a version
-    0 source) will be fired, regardless of the value of returnAfterSourceHandled.
-    */
-    CFRunLoopRunInMode(kCFRunLoopDefaultMode, 0, false);
-    return 0;
-}
diff --git a/launchers/macosx/include/any.hpp b/launchers/macosx/include/any.hpp
deleted file mode 100644
index c588a0ec4737a50180b0eb4ea6d89c33cd893940..0000000000000000000000000000000000000000
--- a/launchers/macosx/include/any.hpp
+++ /dev/null
@@ -1,461 +0,0 @@
-//
-// Implementation of N4562 std::experimental::any (merged into C++17) for C++11 compilers.
-//
-// See also:
-//   + http://en.cppreference.com/w/cpp/any
-//   + http://en.cppreference.com/w/cpp/experimental/any
-//   + http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2015/n4562.html#any
-//   + https://cplusplus.github.io/LWG/lwg-active.html#2509
-//
-//
-// Copyright (c) 2016 Denilson das Merc�s Amorim
-//
-// Distributed under the Boost Software License, Version 1.0. (See accompanying
-// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
-//
-#ifndef LINB_ANY_HPP
-#define LINB_ANY_HPP
-#pragma once
-#include <typeinfo>
-#include <type_traits>
-#include <stdexcept>
-
-namespace linb
-{
-
-class bad_any_cast : public std::bad_cast
-{
-public:
-    const char* what() const noexcept override
-    {
-        return "bad any cast";
-    }
-};
-
-class any final
-{
-public:
-    /// Constructs an object of type any with an empty state.
-    any() :
-        vtable(nullptr)
-    {
-    }
-
-    /// Constructs an object of type any with an equivalent state as other.
-    any(const any& rhs) :
-        vtable(rhs.vtable)
-    {
-        if(!rhs.empty())
-        {
-            rhs.vtable->copy(rhs.storage, this->storage);
-        }
-    }
-
-    /// Constructs an object of type any with a state equivalent to the original state of other.
-    /// rhs is left in a valid but otherwise unspecified state.
-    any(any&& rhs) noexcept :
-        vtable(rhs.vtable)
-    {
-        if(!rhs.empty())
-        {
-            rhs.vtable->move(rhs.storage, this->storage);
-            rhs.vtable = nullptr;
-        }
-    }
-
-    /// Same effect as this->clear().
-    ~any()
-    {
-        this->clear();
-    }
-
-    /// Constructs an object of type any that contains an object of type T direct-initialized with std::forward<ValueType>(value).
-    ///
-    /// T shall satisfy the CopyConstructible requirements, otherwise the program is ill-formed.
-    /// This is because an `any` may be copy constructed into another `any` at any time, so a copy should always be allowed.
-    template<typename ValueType, typename = typename std::enable_if<!std::is_same<typename std::decay<ValueType>::type, any>::value>::type>
-    any(ValueType&& value)
-    {
-        static_assert(std::is_copy_constructible<typename std::decay<ValueType>::type>::value,
-            "T shall satisfy the CopyConstructible requirements.");
-        this->construct(std::forward<ValueType>(value));
-    }
-
-    /// Has the same effect as any(rhs).swap(*this). No effects if an exception is thrown.
-    any& operator=(const any& rhs)
-    {
-        any(rhs).swap(*this);
-        return *this;
-    }
-
-    /// Has the same effect as any(std::move(rhs)).swap(*this).
-    ///
-    /// The state of *this is equivalent to the original state of rhs and rhs is left in a valid
-    /// but otherwise unspecified state.
-    any& operator=(any&& rhs) noexcept
-    {
-        any(std::move(rhs)).swap(*this);
-        return *this;
-    }
-
-    /// Has the same effect as any(std::forward<ValueType>(value)).swap(*this). No effect if a exception is thrown.
-    ///
-    /// T shall satisfy the CopyConstructible requirements, otherwise the program is ill-formed.
-    /// This is because an `any` may be copy constructed into another `any` at any time, so a copy should always be allowed.
-    template<typename ValueType, typename = typename std::enable_if<!std::is_same<typename std::decay<ValueType>::type, any>::value>::type>
-    any& operator=(ValueType&& value)
-    {
-        static_assert(std::is_copy_constructible<typename std::decay<ValueType>::type>::value,
-            "T shall satisfy the CopyConstructible requirements.");
-        any(std::forward<ValueType>(value)).swap(*this);
-        return *this;
-    }
-
-    /// If not empty, destroys the contained object.
-    void clear() noexcept
-    {
-        if(!empty())
-        {
-            this->vtable->destroy(storage);
-            this->vtable = nullptr;
-        }
-    }
-
-    /// Returns true if *this has no contained object, otherwise false.
-    bool empty() const noexcept
-    {
-        return this->vtable == nullptr;
-    }
-
-    /// If *this has a contained object of type T, typeid(T); otherwise typeid(void).
-    const std::type_info& type() const noexcept
-    {
-        return empty()? typeid(void) : this->vtable->type();
-    }
-
-    /// Exchange the states of *this and rhs.
-    void swap(any& rhs) noexcept
-    {
-        if(this->vtable != rhs.vtable)
-        {
-            any tmp(std::move(rhs));
-
-            // move from *this to rhs.
-            rhs.vtable = this->vtable;
-            if(this->vtable != nullptr)
-            {
-                this->vtable->move(this->storage, rhs.storage);
-                //this->vtable = nullptr; -- uneeded, see below
-            }
-
-            // move from tmp (previously rhs) to *this.
-            this->vtable = tmp.vtable;
-            if(tmp.vtable != nullptr)
-            {
-                tmp.vtable->move(tmp.storage, this->storage);
-                tmp.vtable = nullptr;
-            }
-        }
-        else // same types
-        {
-            if(this->vtable != nullptr)
-                this->vtable->swap(this->storage, rhs.storage);
-        }
-    }
-
-private: // Storage and Virtual Method Table
-
-    union storage_union
-    {
-        using stack_storage_t = typename std::aligned_storage<2 * sizeof(void*), std::alignment_of<void*>::value>::type;
-
-        void*               dynamic;
-        stack_storage_t     stack;      // 2 words for e.g. shared_ptr
-    };
-
-    /// Base VTable specification.
-    struct vtable_type
-    {
-        // Note: The caller is responssible for doing .vtable = nullptr after destructful operations
-        // such as destroy() and/or move().
-
-        /// The type of the object this vtable is for.
-        const std::type_info& (*type)() noexcept;
-
-        /// Destroys the object in the union.
-        /// The state of the union after this call is unspecified, caller must ensure not to use src anymore.
-        void(*destroy)(storage_union&) noexcept;
-
-        /// Copies the **inner** content of the src union into the yet unitialized dest union.
-        /// As such, both inner objects will have the same state, but on separate memory locations.
-        void(*copy)(const storage_union& src, storage_union& dest);
-
-        /// Moves the storage from src to the yet unitialized dest union.
-        /// The state of src after this call is unspecified, caller must ensure not to use src anymore.
-        void(*move)(storage_union& src, storage_union& dest) noexcept;
-
-        /// Exchanges the storage between lhs and rhs.
-        void(*swap)(storage_union& lhs, storage_union& rhs) noexcept;
-    };
-
-    /// VTable for dynamically allocated storage.
-    template<typename T>
-    struct vtable_dynamic
-    {
-        static const std::type_info& type() noexcept
-        {
-            return typeid(T);
-        }
-
-        static void destroy(storage_union& storage) noexcept
-        {
-            //assert(reinterpret_cast<T*>(storage.dynamic));
-            delete reinterpret_cast<T*>(storage.dynamic);
-        }
-
-        static void copy(const storage_union& src, storage_union& dest)
-        {
-            dest.dynamic = new T(*reinterpret_cast<const T*>(src.dynamic));
-        }
-
-        static void move(storage_union& src, storage_union& dest) noexcept
-        {
-            dest.dynamic = src.dynamic;
-            src.dynamic = nullptr;
-        }
-
-        static void swap(storage_union& lhs, storage_union& rhs) noexcept
-        {
-            // just exchage the storage pointers.
-            std::swap(lhs.dynamic, rhs.dynamic);
-        }
-    };
-
-    /// VTable for stack allocated storage.
-    template<typename T>
-    struct vtable_stack
-    {
-        static const std::type_info& type() noexcept
-        {
-            return typeid(T);
-        }
-
-        static void destroy(storage_union& storage) noexcept
-        {
-            reinterpret_cast<T*>(&storage.stack)->~T();
-        }
-
-        static void copy(const storage_union& src, storage_union& dest)
-        {
-            new (&dest.stack) T(reinterpret_cast<const T&>(src.stack));
-        }
-
-        static void move(storage_union& src, storage_union& dest) noexcept
-        {
-            // one of the conditions for using vtable_stack is a nothrow move constructor,
-            // so this move constructor will never throw a exception.
-            new (&dest.stack) T(std::move(reinterpret_cast<T&>(src.stack)));
-            destroy(src);
-        }
-
-        static void swap(storage_union& lhs, storage_union& rhs) noexcept
-        {
-            storage_union tmp_storage;
-            move(rhs, tmp_storage);
-            move(lhs, rhs);
-            move(tmp_storage, lhs);
-        }
-    };
-
-    /// Whether the type T must be dynamically allocated or can be stored on the stack.
-    template<typename T>
-    struct requires_allocation :
-        std::integral_constant<bool,
-                !(std::is_nothrow_move_constructible<T>::value      // N4562 �6.3/3 [any.class]
-                  && sizeof(T) <= sizeof(storage_union::stack)
-                  && std::alignment_of<T>::value <= std::alignment_of<storage_union::stack_storage_t>::value)>
-    {};
-
-    /// Returns the pointer to the vtable of the type T.
-    template<typename T>
-    static vtable_type* vtable_for_type()
-    {
-        using VTableType = typename std::conditional<requires_allocation<T>::value, vtable_dynamic<T>, vtable_stack<T>>::type;
-        static vtable_type table = {
-            VTableType::type, VTableType::destroy,
-            VTableType::copy, VTableType::move,
-            VTableType::swap,
-        };
-        return &table;
-    }
-
-protected:
-    template<typename T>
-    friend const T* any_cast(const any* operand) noexcept;
-    template<typename T>
-    friend T* any_cast(any* operand) noexcept;
-
-    /// Same effect as is_same(this->type(), t);
-    bool is_typed(const std::type_info& t) const
-    {
-        return is_same(this->type(), t);
-    }
-
-    /// Checks if two type infos are the same.
-    ///
-    /// If ANY_IMPL_FAST_TYPE_INFO_COMPARE is defined, checks only the address of the
-    /// type infos, otherwise does an actual comparision. Checking addresses is
-    /// only a valid approach when there's no interaction with outside sources
-    /// (other shared libraries and such).
-    static bool is_same(const std::type_info& a, const std::type_info& b)
-    {
-#ifdef ANY_IMPL_FAST_TYPE_INFO_COMPARE
-        return &a == &b;
-#else
-        return a == b;
-#endif
-    }
-
-    /// Casts (with no type_info checks) the storage pointer as const T*.
-    template<typename T>
-    const T* cast() const noexcept
-    {
-        return requires_allocation<typename std::decay<T>::type>::value?
-            reinterpret_cast<const T*>(storage.dynamic) :
-            reinterpret_cast<const T*>(&storage.stack);
-    }
-
-    /// Casts (with no type_info checks) the storage pointer as T*.
-    template<typename T>
-    T* cast() noexcept
-    {
-        return requires_allocation<typename std::decay<T>::type>::value?
-            reinterpret_cast<T*>(storage.dynamic) :
-            reinterpret_cast<T*>(&storage.stack);
-    }
-
-private:
-    storage_union storage; // on offset(0) so no padding for align
-    vtable_type*  vtable;
-
-    template<typename ValueType, typename T>
-    typename std::enable_if<requires_allocation<T>::value>::type
-    do_construct(ValueType&& value)
-    {
-        storage.dynamic = new T(std::forward<ValueType>(value));
-    }
-
-    template<typename ValueType, typename T>
-    typename std::enable_if<!requires_allocation<T>::value>::type
-    do_construct(ValueType&& value)
-    {
-        new (&storage.stack) T(std::forward<ValueType>(value));
-    }
-
-    /// Chooses between stack and dynamic allocation for the type decay_t<ValueType>,
-    /// assigns the correct vtable, and constructs the object on our storage.
-    template<typename ValueType>
-    void construct(ValueType&& value)
-    {
-        using T = typename std::decay<ValueType>::type;
-
-        this->vtable = vtable_for_type<T>();
-
-        do_construct<ValueType,T>(std::forward<ValueType>(value));
-    }
-};
-
-
-
-namespace detail
-{
-    template<typename ValueType>
-    inline ValueType any_cast_move_if_true(typename std::remove_reference<ValueType>::type* p, std::true_type)
-    {
-        return std::move(*p);
-    }
-
-    template<typename ValueType>
-    inline ValueType any_cast_move_if_true(typename std::remove_reference<ValueType>::type* p, std::false_type)
-    {
-        return *p;
-    }
-}
-
-/// Performs *any_cast<add_const_t<remove_reference_t<ValueType>>>(&operand), or throws bad_any_cast on failure.
-template<typename ValueType>
-inline ValueType any_cast(const any& operand)
-{
-    auto p = any_cast<typename std::add_const<typename std::remove_reference<ValueType>::type>::type>(&operand);
-    if(p == nullptr) throw bad_any_cast();
-    return *p;
-}
-
-/// Performs *any_cast<remove_reference_t<ValueType>>(&operand), or throws bad_any_cast on failure.
-template<typename ValueType>
-inline ValueType any_cast(any& operand)
-{
-    auto p = any_cast<typename std::remove_reference<ValueType>::type>(&operand);
-    if(p == nullptr) throw bad_any_cast();
-    return *p;
-}
-
-///
-/// If ANY_IMPL_ANYCAST_MOVEABLE is not defined, does as N4562 specifies:
-///     Performs *any_cast<remove_reference_t<ValueType>>(&operand), or throws bad_any_cast on failure.
-///
-/// If ANY_IMPL_ANYCAST_MOVEABLE is defined, does as LWG Defect 2509 specifies:
-///     If ValueType is MoveConstructible and isn't a lvalue reference, performs
-///     std::move(*any_cast<remove_reference_t<ValueType>>(&operand)), otherwise
-///     *any_cast<remove_reference_t<ValueType>>(&operand). Throws bad_any_cast on failure.
-///
-template<typename ValueType>
-inline ValueType any_cast(any&& operand)
-{
-#ifdef ANY_IMPL_ANY_CAST_MOVEABLE
-    // https://cplusplus.github.io/LWG/lwg-active.html#2509
-    using can_move = std::integral_constant<bool,
-        std::is_move_constructible<ValueType>::value
-        && !std::is_lvalue_reference<ValueType>::value>;
-#else
-    using can_move = std::false_type;
-#endif
-
-    auto p = any_cast<typename std::remove_reference<ValueType>::type>(&operand);
-    if(p == nullptr) throw bad_any_cast();
-    return detail::any_cast_move_if_true<ValueType>(p, can_move());
-}
-
-/// If operand != nullptr && operand->type() == typeid(ValueType), a pointer to the object
-/// contained by operand, otherwise nullptr.
-template<typename T>
-inline const T* any_cast(const any* operand) noexcept
-{
-    if(operand == nullptr || !operand->is_typed(typeid(T)))
-        return nullptr;
-    else
-        return operand->cast<T>();
-}
-
-/// If operand != nullptr && operand->type() == typeid(ValueType), a pointer to the object
-/// contained by operand, otherwise nullptr.
-template<typename T>
-inline T* any_cast(any* operand) noexcept
-{
-    if(operand == nullptr || !operand->is_typed(typeid(T)))
-        return nullptr;
-    else
-        return operand->cast<T>();
-}
-
-}
-
-namespace std
-{
-    inline void swap(linb::any& lhs, linb::any& rhs) noexcept
-    {
-        lhs.swap(rhs);
-    }
-}
-
-#endif
diff --git a/launchers/macosx/include/fn.h b/launchers/macosx/include/fn.h
deleted file mode 100644
index ffd9ed033c6bfd0db04fbf604d3df11a94238ce2..0000000000000000000000000000000000000000
--- a/launchers/macosx/include/fn.h
+++ /dev/null
@@ -1,168 +0,0 @@
-#ifndef FN_H
-#define FN_H
-
-#include <functional>
-#include <algorithm>
-
-/*
- * higher-order functions
- *
- * Read
- * http://blog.madhukaraphatak.com/functional-programming-in-c++/
- *
- *
- * Lamda fingerprint:
-namespace {
-  struct f {
-    void operator()(int) {
-      // do something
-    }
-  };
-}
- *
- *
- *
-template <typename Collection,typename unop>
-void for_each(Collection col, unop op){
-  std::for_each(col.begin(),col.end(),op);
-}
-
-Usage:
-
-auto lambda_echo = [](int i ) { std::cout << i << std::endl; };
- std::vector<int> col{20,24,37,42,23,45,37};
- for_each(col,lambda_echo);
-
-*/
-template <typename Collection,typename unop>
-void for_each(Collection col, unop op){
-  std::for_each(col.begin(),col.end(),op);
-}
-
-/**
- * map
- *
- * Usage example:
- auto addOne = [](int i) { return i+1;};
- auto returnCol = map(col,addOne);
- for_each(returnCol,lambda_echo);
- *
- *
- *
- */
-template <typename Collection,typename unop>
-Collection map(Collection col,unop op) {
-  std::transform(col.begin(),col.end(),col.begin(),op);
-  return col;
-}
-
-
-
-/*
-Filter usage:
-
-auto filteredCol = filter(col,[](int value){ return value > 30;});
- for_each(filteredCol,lambda_echo);
-*/
-
-template <typename Collection,typename Predicate>
-Collection filterNot(Collection col,Predicate predicate ) {
-  auto returnIterator = std::remove_if(col.begin(),col.end(),predicate);
-  col.erase(returnIterator,std::end(col));
-  return col;
-}
-
-template <typename Collection,typename Predicate>
-Collection filter(Collection col,Predicate predicate) {
- //capture the predicate in order to be used inside function
- auto fnCol = filterNot(col,[predicate](typename Collection::value_type i) { return !predicate(i);});
- return fnCol;
-}
-
-/**
-  *
-  * Alternative map implementations
-  *
-  **/
-template<class F, class T, class U=decltype(std::declval<F>()(std::declval<T>()))>
-std::vector<U> fmap(F f, const std::vector<T>& vec)
-{
-    std::vector<U> result;
-    std::transform(vec.begin(), vec.end(), std::back_inserter(result), f);
-    return result;
-}
-
-template<class F, class T, class U=decltype(std::declval<F>()(std::declval<T>()))>
-std::shared_ptr<U> fmap(F f, const std::shared_ptr<T>& p)
-{
-    if (p == nullptr) return nullptr;
-    else return std::shared_ptr<U>(new U(f(*p)));
-}
-
-
-/**
- * Experimental code - should not be in production
- */
-
-namespace Experimental {
-    template <typename T>
-    T min3(const T& a, const T& b, const T& c)
-    {
-       return std::min(std::min(a, b), c);
-    }
-
-    class LevenshteinDistance
-    {
-        mutable std::vector<std::vector<unsigned int> > matrix_;
-
-    public:
-        explicit LevenshteinDistance(size_t initial_size = 8)
-            : matrix_(initial_size, std::vector<unsigned int>(initial_size))
-        {
-        }
-
-        unsigned int operator()(const std::string& s, const std::string& t) const
-        {
-            const size_t m = s.size();
-            const size_t n = t.size();
-            // The distance between a string and the empty string is the string's length
-            if (m == 0) {
-                return (unsigned int)n;
-            }
-            if (n == 0) {
-                return (unsigned int)m;
-            }
-            // Size the matrix as necessary
-            if (matrix_.size() < m + 1) {
-                matrix_.resize(m + 1, matrix_[0]);
-            }
-            if (matrix_[0].size() < n + 1) {
-                for (auto& mat : matrix_) {
-                    mat.resize(n + 1);
-                }
-            }
-            // The top row and left column are prefixes that can be reached by
-            // insertions and deletions alone
-            unsigned int i, j;
-            for (i = 1;  i <= m; ++i) {
-                matrix_[i][0] = i;
-            }
-            for (j = 1; j <= n; ++j) {
-                matrix_[0][j] = j;
-            }
-            // Fill in the rest of the matrix
-            for (j = 1; j <= n; ++j) {
-                for (i = 1; i <= m; ++i) {
-                    unsigned int substitution_cost = s[i - 1] == t[j - 1] ? 0 : 1;
-                    matrix_[i][j] =
-                        min3(matrix_[i - 1][j] + 1,                 // Deletion
-                        matrix_[i][j - 1] + 1,                      // Insertion
-                        matrix_[i - 1][j - 1] + substitution_cost); // Substitution
-                }
-            }
-            return matrix_[m][n];
-        }
-    };
-}
-
-#endif // FN_H
diff --git a/launchers/macosx/include/optional.h b/launchers/macosx/include/optional.h
deleted file mode 100644
index cd6f025ac67208c71abf58ccc2240b3102f671ba..0000000000000000000000000000000000000000
--- a/launchers/macosx/include/optional.h
+++ /dev/null
@@ -1,1066 +0,0 @@
-// Copyright (C) 2011 - 2012 Andrzej Krzemienski.
-//
-// Use, modification, and distribution is subject to the Boost Software
-// License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
-// http://www.boost.org/LICENSE_1_0.txt)
-//
-// The idea and interface is based on Boost.Optional library
-// authored by Fernando Luis Cacciola Carballal
-
-# ifndef ___OPTIONAL_HPP___
-# define ___OPTIONAL_HPP___
-
-# include <utility>
-# include <type_traits>
-# include <initializer_list>
-# include <cassert>
-# include <functional>
-# include <string>
-# include <stdexcept>
-
-# define TR2_OPTIONAL_REQUIRES(...) typename enable_if<__VA_ARGS__::value, bool>::type = false
-
-# if defined __GNUC__ // NOTE: GNUC is also defined for Clang
-#   if (__GNUC__ == 4) && (__GNUC_MINOR__ >= 8)
-#     define TR2_OPTIONAL_GCC_4_8_AND_HIGHER___
-#   elif (__GNUC__ > 4)
-#     define TR2_OPTIONAL_GCC_4_8_AND_HIGHER___
-#   endif
-#
-#   if (__GNUC__ == 4) && (__GNUC_MINOR__ >= 7)
-#     define TR2_OPTIONAL_GCC_4_7_AND_HIGHER___
-#   elif (__GNUC__ > 4)
-#     define TR2_OPTIONAL_GCC_4_7_AND_HIGHER___
-#   endif
-#
-#   if (__GNUC__ == 4) && (__GNUC_MINOR__ == 8) && (__GNUC_PATCHLEVEL__ >= 1)
-#     define TR2_OPTIONAL_GCC_4_8_1_AND_HIGHER___
-#   elif (__GNUC__ == 4) && (__GNUC_MINOR__ >= 9)
-#     define TR2_OPTIONAL_GCC_4_8_1_AND_HIGHER___
-#   elif (__GNUC__ > 4)
-#     define TR2_OPTIONAL_GCC_4_8_1_AND_HIGHER___
-#   endif
-# endif
-#
-# if defined __clang_major__
-#   if (__clang_major__ == 3 && __clang_minor__ >= 5)
-#     define TR2_OPTIONAL_CLANG_3_5_AND_HIGHTER_
-#   elif (__clang_major__ > 3)
-#     define TR2_OPTIONAL_CLANG_3_5_AND_HIGHTER_
-#   endif
-#   if defined TR2_OPTIONAL_CLANG_3_5_AND_HIGHTER_
-#     define TR2_OPTIONAL_CLANG_3_4_2_AND_HIGHER_
-#   elif (__clang_major__ == 3 && __clang_minor__ == 4 && __clang_patchlevel__ >= 2)
-#     define TR2_OPTIONAL_CLANG_3_4_2_AND_HIGHER_
-#   endif
-# endif
-#
-# if defined _MSC_VER
-#   if (_MSC_VER >= 1900)
-#     define TR2_OPTIONAL_MSVC_2015_AND_HIGHER___
-#   endif
-# endif
-
-# if defined __clang__
-#   if (__clang_major__ > 2) || (__clang_major__ == 2) && (__clang_minor__ >= 9)
-#     define OPTIONAL_HAS_THIS_RVALUE_REFS 1
-#   else
-#     define OPTIONAL_HAS_THIS_RVALUE_REFS 0
-#   endif
-# elif defined TR2_OPTIONAL_GCC_4_8_1_AND_HIGHER___
-#   define OPTIONAL_HAS_THIS_RVALUE_REFS 1
-# elif defined TR2_OPTIONAL_MSVC_2015_AND_HIGHER___
-#   define OPTIONAL_HAS_THIS_RVALUE_REFS 1
-# else
-#   define OPTIONAL_HAS_THIS_RVALUE_REFS 0
-# endif
-
-
-# if defined TR2_OPTIONAL_GCC_4_8_1_AND_HIGHER___
-#   define OPTIONAL_HAS_CONSTEXPR_INIT_LIST 1
-#   define OPTIONAL_CONSTEXPR_INIT_LIST constexpr
-# else
-#   define OPTIONAL_HAS_CONSTEXPR_INIT_LIST 0
-#   define OPTIONAL_CONSTEXPR_INIT_LIST
-# endif
-
-# if defined TR2_OPTIONAL_CLANG_3_5_AND_HIGHTER_ && (defined __cplusplus) && (__cplusplus != 201103L)
-#   define OPTIONAL_HAS_MOVE_ACCESSORS 1
-# else
-#   define OPTIONAL_HAS_MOVE_ACCESSORS 0
-# endif
-
-# // In C++11 constexpr implies const, so we need to make non-const members also non-constexpr
-# if (defined __cplusplus) && (__cplusplus == 201103L)
-#   define OPTIONAL_MUTABLE_CONSTEXPR
-# else
-#   define OPTIONAL_MUTABLE_CONSTEXPR constexpr
-# endif
-
-namespace std{
-
-namespace experimental{
-
-// BEGIN workaround for missing is_trivially_destructible
-# if defined TR2_OPTIONAL_GCC_4_8_AND_HIGHER___
-    // leave it: it is already there
-# elif defined TR2_OPTIONAL_CLANG_3_4_2_AND_HIGHER_
-    // leave it: it is already there
-# elif defined TR2_OPTIONAL_MSVC_2015_AND_HIGHER___
-    // leave it: it is already there
-# elif defined TR2_OPTIONAL_DISABLE_EMULATION_OF_TYPE_TRAITS
-    // leave it: the user doesn't want it
-# else
-	template <typename T>
-	using is_trivially_destructible = std::has_trivial_destructor<T>;
-# endif
-// END workaround for missing is_trivially_destructible
-
-# if (defined TR2_OPTIONAL_GCC_4_7_AND_HIGHER___)
-    // leave it; our metafunctions are already defined.
-# elif defined TR2_OPTIONAL_CLANG_3_4_2_AND_HIGHER_
-    // leave it; our metafunctions are already defined.
-# elif defined TR2_OPTIONAL_MSVC_2015_AND_HIGHER___
-    // leave it: it is already there
-# elif defined TR2_OPTIONAL_DISABLE_EMULATION_OF_TYPE_TRAITS
-    // leave it: the user doesn't want it
-# else
-
-
-// workaround for missing traits in GCC and CLANG
-template <class T>
-struct is_nothrow_move_constructible
-{
-  constexpr static bool value = std::is_nothrow_constructible<T, T&&>::value;
-};
-
-
-template <class T, class U>
-struct is_assignable
-{
-  template <class X, class Y>
-  constexpr static bool has_assign(...) { return false; }
-
-  template <class X, class Y, size_t S = sizeof((std::declval<X>() = std::declval<Y>(), true)) >
-  // the comma operator is necessary for the cases where operator= returns void
-  constexpr static bool has_assign(bool) { return true; }
-
-  constexpr static bool value = has_assign<T, U>(true);
-};
-
-
-template <class T>
-struct is_nothrow_move_assignable
-{
-  template <class X, bool has_any_move_assign>
-  struct has_nothrow_move_assign {
-    constexpr static bool value = false;
-  };
-
-  template <class X>
-  struct has_nothrow_move_assign<X, true> {
-    constexpr static bool value = noexcept( std::declval<X&>() = std::declval<X&&>() );
-  };
-
-  constexpr static bool value = has_nothrow_move_assign<T, is_assignable<T&, T&&>::value>::value;
-};
-// end workaround
-
-
-# endif
-
-
-
-// 20.5.4, optional for object types
-template <class T> class optional;
-
-// 20.5.5, optional for lvalue reference types
-template <class T> class optional<T&>;
-
-
-// workaround: std utility functions aren't constexpr yet
-template <class T> inline constexpr T&& constexpr_forward(typename std::remove_reference<T>::type& t) noexcept
-{
-  return static_cast<T&&>(t);
-}
-
-template <class T> inline constexpr T&& constexpr_forward(typename std::remove_reference<T>::type&& t) noexcept
-{
-    static_assert(!std::is_lvalue_reference<T>::value, "!!");
-    return static_cast<T&&>(t);
-}
-
-template <class T> inline constexpr typename std::remove_reference<T>::type&& constexpr_move(T&& t) noexcept
-{
-    return static_cast<typename std::remove_reference<T>::type&&>(t);
-}
-
-
-#if defined NDEBUG
-# define TR2_OPTIONAL_ASSERTED_EXPRESSION(CHECK, EXPR) (EXPR)
-#else
-# define TR2_OPTIONAL_ASSERTED_EXPRESSION(CHECK, EXPR) ((CHECK) ? (EXPR) : ([]{assert(!#CHECK);}(), (EXPR)))
-#endif
-
-
-namespace detail_
-{
-
-// static_addressof: a constexpr version of addressof
-template <typename T>
-struct has_overloaded_addressof
-{
-  template <class X>
-  constexpr static bool has_overload(...) { return false; }
-
-  template <class X, size_t S = sizeof(std::declval<X&>().operator&()) >
-  constexpr static bool has_overload(bool) { return true; }
-
-  constexpr static bool value = has_overload<T>(true);
-};
-
-template <typename T, TR2_OPTIONAL_REQUIRES(!has_overloaded_addressof<T>)>
-constexpr T* static_addressof(T& ref)
-{
-  return &ref;
-}
-
-template <typename T, TR2_OPTIONAL_REQUIRES(has_overloaded_addressof<T>)>
-T* static_addressof(T& ref)
-{
-  return std::addressof(ref);
-}
-
-
-// the call to convert<A>(b) has return type A and converts b to type A iff b decltype(b) is implicitly convertible to A
-template <class U>
-constexpr U convert(U v) { return v; }
-
-
-namespace swap_ns
-{
-  using std::swap;
-
-  template <class T>
-  void adl_swap(T& t, T& u) noexcept(noexcept(swap(t, u)))
-  {
-    swap(t, u);
-  }
-
-} // namespace swap_ns
-
-} // namespace detail
-
-
-constexpr struct trivial_init_t{} trivial_init{};
-
-
-// 20.5.6, In-place construction
-constexpr struct in_place_t{} in_place{};
-
-
-// 20.5.7, Disengaged state indicator
-struct nullopt_t
-{
-  struct init{};
-  constexpr explicit nullopt_t(init){}
-};
-constexpr nullopt_t nullopt{nullopt_t::init()};
-
-
-// 20.5.8, class bad_optional_access
-class bad_optional_access : public logic_error {
-public:
-  explicit bad_optional_access(const string& what_arg) : logic_error{what_arg} {}
-  explicit bad_optional_access(const char* what_arg) : logic_error{what_arg} {}
-};
-
-
-template <class T>
-union storage_t
-{
-  unsigned char dummy_;
-  T value_;
-
-  constexpr storage_t( trivial_init_t ) noexcept : dummy_() {};
-
-  template <class... Args>
-  constexpr storage_t( Args&&... args ) : value_(constexpr_forward<Args>(args)...) {}
-
-  ~storage_t(){}
-};
-
-
-template <class T>
-union constexpr_storage_t
-{
-    unsigned char dummy_;
-    T value_;
-
-    constexpr constexpr_storage_t( trivial_init_t ) noexcept : dummy_() {};
-
-    template <class... Args>
-    constexpr constexpr_storage_t( Args&&... args ) : value_(constexpr_forward<Args>(args)...) {}
-
-    ~constexpr_storage_t() = default;
-};
-
-
-template <class T>
-struct optional_base
-{
-    bool init_;
-    storage_t<T> storage_;
-
-    constexpr optional_base() noexcept : init_(false), storage_(trivial_init) {};
-
-    explicit constexpr optional_base(const T& v) : init_(true), storage_(v) {}
-
-    explicit constexpr optional_base(T&& v) : init_(true), storage_(constexpr_move(v)) {}
-
-    template <class... Args> explicit optional_base(in_place_t, Args&&... args)
-        : init_(true), storage_(constexpr_forward<Args>(args)...) {}
-
-    template <class U, class... Args, TR2_OPTIONAL_REQUIRES(is_constructible<T, std::initializer_list<U>>)>
-    explicit optional_base(in_place_t, std::initializer_list<U> il, Args&&... args)
-        : init_(true), storage_(il, std::forward<Args>(args)...) {}
-
-    ~optional_base() { if (init_) storage_.value_.T::~T(); }
-};
-
-
-template <class T>
-struct constexpr_optional_base
-{
-    bool init_;
-    constexpr_storage_t<T> storage_;
-
-    constexpr constexpr_optional_base() noexcept : init_(false), storage_(trivial_init) {};
-
-    explicit constexpr constexpr_optional_base(const T& v) : init_(true), storage_(v) {}
-
-    explicit constexpr constexpr_optional_base(T&& v) : init_(true), storage_(constexpr_move(v)) {}
-
-    template <class... Args> explicit constexpr constexpr_optional_base(in_place_t, Args&&... args)
-      : init_(true), storage_(constexpr_forward<Args>(args)...) {}
-
-    template <class U, class... Args, TR2_OPTIONAL_REQUIRES(is_constructible<T, std::initializer_list<U>>)>
-    OPTIONAL_CONSTEXPR_INIT_LIST explicit constexpr_optional_base(in_place_t, std::initializer_list<U> il, Args&&... args)
-      : init_(true), storage_(il, std::forward<Args>(args)...) {}
-
-    ~constexpr_optional_base() = default;
-};
-
-template <class T>
-using OptionalBase = typename std::conditional<
-    is_trivially_destructible<T>::value,                          // if possible
-    constexpr_optional_base<typename std::remove_const<T>::type>, // use base with trivial destructor
-    optional_base<typename std::remove_const<T>::type>
->::type;
-
-
-
-template <class T>
-class optional : private OptionalBase<T>
-{
-  static_assert( !std::is_same<typename std::decay<T>::type, nullopt_t>::value, "bad T" );
-  static_assert( !std::is_same<typename std::decay<T>::type, in_place_t>::value, "bad T" );
-
-
-  constexpr bool initialized() const noexcept { return OptionalBase<T>::init_; }
-  typename std::remove_const<T>::type* dataptr() {  return std::addressof(OptionalBase<T>::storage_.value_); }
-  constexpr const T* dataptr() const { return detail_::static_addressof(OptionalBase<T>::storage_.value_); }
-
-# if OPTIONAL_HAS_THIS_RVALUE_REFS == 1
-  constexpr const T& contained_val() const& { return OptionalBase<T>::storage_.value_; }
-#   if OPTIONAL_HAS_MOVE_ACCESSORS == 1
-  OPTIONAL_MUTABLE_CONSTEXPR T&& contained_val() && { return std::move(OptionalBase<T>::storage_.value_); }
-  OPTIONAL_MUTABLE_CONSTEXPR T& contained_val() & { return OptionalBase<T>::storage_.value_; }
-#   else
-  T& contained_val() & { return OptionalBase<T>::storage_.value_; }
-  T&& contained_val() && { return std::move(OptionalBase<T>::storage_.value_); }
-#   endif
-# else
-  constexpr const T& contained_val() const { return OptionalBase<T>::storage_.value_; }
-  T& contained_val() { return OptionalBase<T>::storage_.value_; }
-# endif
-
-  void clear() noexcept {
-    if (initialized()) dataptr()->T::~T();
-    OptionalBase<T>::init_ = false;
-  }
-
-  template <class... Args>
-  void initialize(Args&&... args) noexcept(noexcept(T(std::forward<Args>(args)...)))
-  {
-    assert(!OptionalBase<T>::init_);
-    ::new (static_cast<void*>(dataptr())) T(std::forward<Args>(args)...);
-    OptionalBase<T>::init_ = true;
-  }
-
-  template <class U, class... Args>
-  void initialize(std::initializer_list<U> il, Args&&... args) noexcept(noexcept(T(il, std::forward<Args>(args)...)))
-  {
-    assert(!OptionalBase<T>::init_);
-    ::new (static_cast<void*>(dataptr())) T(il, std::forward<Args>(args)...);
-    OptionalBase<T>::init_ = true;
-  }
-
-public:
-  typedef T value_type;
-
-  // 20.5.5.1, constructors
-  constexpr optional() noexcept : OptionalBase<T>()  {};
-  constexpr optional(nullopt_t) noexcept : OptionalBase<T>() {};
-
-  optional(const optional& rhs)
-  : OptionalBase<T>()
-  {
-    if (rhs.initialized()) {
-        ::new (static_cast<void*>(dataptr())) T(*rhs);
-        OptionalBase<T>::init_ = true;
-    }
-  }
-
-  optional(optional&& rhs) noexcept(is_nothrow_move_constructible<T>::value)
-  : OptionalBase<T>()
-  {
-    if (rhs.initialized()) {
-        ::new (static_cast<void*>(dataptr())) T(std::move(*rhs));
-        OptionalBase<T>::init_ = true;
-    }
-  }
-
-  constexpr optional(const T& v) : OptionalBase<T>(v) {}
-
-  constexpr optional(T&& v) : OptionalBase<T>(constexpr_move(v)) {}
-
-  template <class... Args>
-  explicit constexpr optional(in_place_t, Args&&... args)
-  : OptionalBase<T>(in_place_t{}, constexpr_forward<Args>(args)...) {}
-
-  template <class U, class... Args, TR2_OPTIONAL_REQUIRES(is_constructible<T, std::initializer_list<U>>)>
-  OPTIONAL_CONSTEXPR_INIT_LIST explicit optional(in_place_t, std::initializer_list<U> il, Args&&... args)
-  : OptionalBase<T>(in_place_t{}, il, constexpr_forward<Args>(args)...) {}
-
-  // 20.5.4.2, Destructor
-  ~optional() = default;
-
-  // 20.5.4.3, assignment
-  optional& operator=(nullopt_t) noexcept
-  {
-    clear();
-    return *this;
-  }
-
-  optional& operator=(const optional& rhs)
-  {
-    if      (initialized() == true  && rhs.initialized() == false) clear();
-    else if (initialized() == false && rhs.initialized() == true)  initialize(*rhs);
-    else if (initialized() == true  && rhs.initialized() == true)  contained_val() = *rhs;
-    return *this;
-  }
-
-  optional& operator=(optional&& rhs)
-  noexcept(is_nothrow_move_assignable<T>::value && is_nothrow_move_constructible<T>::value)
-  {
-    if      (initialized() == true  && rhs.initialized() == false) clear();
-    else if (initialized() == false && rhs.initialized() == true)  initialize(std::move(*rhs));
-    else if (initialized() == true  && rhs.initialized() == true)  contained_val() = std::move(*rhs);
-    return *this;
-  }
-
-  template <class U>
-  auto operator=(U&& v)
-  -> typename enable_if
-  <
-    is_same<typename decay<U>::type, T>::value,
-    optional&
-  >::type
-  {
-    if (initialized()) { contained_val() = std::forward<U>(v); }
-    else               { initialize(std::forward<U>(v));  }
-    return *this;
-  }
-
-
-  template <class... Args>
-  void emplace(Args&&... args)
-  {
-    clear();
-    initialize(std::forward<Args>(args)...);
-  }
-
-  template <class U, class... Args>
-  void emplace(initializer_list<U> il, Args&&... args)
-  {
-    clear();
-    initialize<U, Args...>(il, std::forward<Args>(args)...);
-  }
-
-  // 20.5.4.4, Swap
-  void swap(optional<T>& rhs) noexcept(is_nothrow_move_constructible<T>::value
-                                       && noexcept(detail_::swap_ns::adl_swap(declval<T&>(), declval<T&>())))
-  {
-    if      (initialized() == true  && rhs.initialized() == false) { rhs.initialize(std::move(**this)); clear(); }
-    else if (initialized() == false && rhs.initialized() == true)  { initialize(std::move(*rhs)); rhs.clear(); }
-    else if (initialized() == true  && rhs.initialized() == true)  { using std::swap; swap(**this, *rhs); }
-  }
-
-  // 20.5.4.5, Observers
-
-  explicit constexpr operator bool() const noexcept { return initialized(); }
-  constexpr bool has_value() const noexcept { return initialized(); }
-
-  constexpr T const* operator ->() const {
-    return TR2_OPTIONAL_ASSERTED_EXPRESSION(initialized(), dataptr());
-  }
-
-# if OPTIONAL_HAS_MOVE_ACCESSORS == 1
-
-  OPTIONAL_MUTABLE_CONSTEXPR T* operator ->() {
-    assert (initialized());
-    return dataptr();
-  }
-
-  constexpr T const& operator *() const& {
-    return TR2_OPTIONAL_ASSERTED_EXPRESSION(initialized(), contained_val());
-  }
-
-  OPTIONAL_MUTABLE_CONSTEXPR T& operator *() & {
-    assert (initialized());
-    return contained_val();
-  }
-
-  OPTIONAL_MUTABLE_CONSTEXPR T&& operator *() && {
-    assert (initialized());
-    return constexpr_move(contained_val());
-  }
-
-  constexpr T const& value() const& {
-    return initialized() ? contained_val() : (throw bad_optional_access("bad optional access"), contained_val());
-  }
-
-  OPTIONAL_MUTABLE_CONSTEXPR T& value() & {
-    return initialized() ? contained_val() : (throw bad_optional_access("bad optional access"), contained_val());
-  }
-
-  OPTIONAL_MUTABLE_CONSTEXPR T&& value() && {
-    if (!initialized()) throw bad_optional_access("bad optional access");
-	return std::move(contained_val());
-  }
-
-# else
-
-  T* operator ->() {
-    assert (initialized());
-    return dataptr();
-  }
-
-  constexpr T const& operator *() const {
-    return TR2_OPTIONAL_ASSERTED_EXPRESSION(initialized(), contained_val());
-  }
-
-  T& operator *() {
-    assert (initialized());
-    return contained_val();
-  }
-
-  constexpr T const& value() const {
-    return initialized() ? contained_val() : (throw bad_optional_access("bad optional access"), contained_val());
-  }
-
-  T& value() {
-    return initialized() ? contained_val() : (throw bad_optional_access("bad optional access"), contained_val());
-  }
-
-# endif
-
-# if OPTIONAL_HAS_THIS_RVALUE_REFS == 1
-
-  template <class V>
-  constexpr T value_or(V&& v) const&
-  {
-    return *this ? **this : detail_::convert<T>(constexpr_forward<V>(v));
-  }
-
-#   if OPTIONAL_HAS_MOVE_ACCESSORS == 1
-
-  template <class V>
-  OPTIONAL_MUTABLE_CONSTEXPR T value_or(V&& v) &&
-  {
-    return *this ? constexpr_move(const_cast<optional<T>&>(*this).contained_val()) : detail_::convert<T>(constexpr_forward<V>(v));
-  }
-
-#   else
-
-  template <class V>
-  T value_or(V&& v) &&
-  {
-    return *this ? constexpr_move(const_cast<optional<T>&>(*this).contained_val()) : detail_::convert<T>(constexpr_forward<V>(v));
-  }
-
-#   endif
-
-# else
-
-  template <class V>
-  constexpr T value_or(V&& v) const
-  {
-    return *this ? **this : detail_::convert<T>(constexpr_forward<V>(v));
-  }
-
-# endif
-
-  // 20.6.3.6, modifiers
-  void reset() noexcept { clear(); }
-};
-
-
-template <class T>
-class optional<T&>
-{
-  static_assert( !std::is_same<T, nullopt_t>::value, "bad T" );
-  static_assert( !std::is_same<T, in_place_t>::value, "bad T" );
-  T* ref;
-
-public:
-
-  // 20.5.5.1, construction/destruction
-  constexpr optional() noexcept : ref(nullptr) {}
-
-  constexpr optional(nullopt_t) noexcept : ref(nullptr) {}
-
-  constexpr optional(T& v) noexcept : ref(detail_::static_addressof(v)) {}
-
-  optional(T&&) = delete;
-
-  constexpr optional(const optional& rhs) noexcept : ref(rhs.ref) {}
-
-  explicit constexpr optional(in_place_t, T& v) noexcept : ref(detail_::static_addressof(v)) {}
-
-  explicit optional(in_place_t, T&&) = delete;
-
-  ~optional() = default;
-
-  // 20.5.5.2, mutation
-  optional& operator=(nullopt_t) noexcept {
-    ref = nullptr;
-    return *this;
-  }
-
-  // optional& operator=(const optional& rhs) noexcept {
-    // ref = rhs.ref;
-    // return *this;
-  // }
-
-  // optional& operator=(optional&& rhs) noexcept {
-    // ref = rhs.ref;
-    // return *this;
-  // }
-
-  template <typename U>
-  auto operator=(U&& rhs) noexcept
-  -> typename enable_if
-  <
-    is_same<typename decay<U>::type, optional<T&>>::value,
-    optional&
-  >::type
-  {
-    ref = rhs.ref;
-    return *this;
-  }
-
-  template <typename U>
-  auto operator=(U&& rhs) noexcept
-  -> typename enable_if
-  <
-    !is_same<typename decay<U>::type, optional<T&>>::value,
-    optional&
-  >::type
-  = delete;
-
-  void emplace(T& v) noexcept {
-    ref = detail_::static_addressof(v);
-  }
-
-  void emplace(T&&) = delete;
-
-
-  void swap(optional<T&>& rhs) noexcept
-  {
-    std::swap(ref, rhs.ref);
-  }
-
-  // 20.5.5.3, observers
-  constexpr T* operator->() const {
-    return TR2_OPTIONAL_ASSERTED_EXPRESSION(ref, ref);
-  }
-
-  constexpr T& operator*() const {
-    return TR2_OPTIONAL_ASSERTED_EXPRESSION(ref, *ref);
-  }
-
-  constexpr T& value() const {
-    return ref ? *ref : (throw bad_optional_access("bad optional access"), *ref);
-  }
-
-  explicit constexpr operator bool() const noexcept {
-    return ref != nullptr;
-  }
-
-  constexpr bool has_value() const noexcept {
-    return ref != nullptr;
-  }
-
-  template <class V>
-  constexpr typename decay<T>::type value_or(V&& v) const
-  {
-    return *this ? **this : detail_::convert<typename decay<T>::type>(constexpr_forward<V>(v));
-  }
-
-  // x.x.x.x, modifiers
-  void reset() noexcept { ref = nullptr; }
-};
-
-
-template <class T>
-class optional<T&&>
-{
-  static_assert( sizeof(T) == 0, "optional rvalue references disallowed" );
-};
-
-
-// 20.5.8, Relational operators
-template <class T> constexpr bool operator==(const optional<T>& x, const optional<T>& y)
-{
-  return bool(x) != bool(y) ? false : bool(x) == false ? true : *x == *y;
-}
-
-template <class T> constexpr bool operator!=(const optional<T>& x, const optional<T>& y)
-{
-  return !(x == y);
-}
-
-template <class T> constexpr bool operator<(const optional<T>& x, const optional<T>& y)
-{
-  return (!y) ? false : (!x) ? true : *x < *y;
-}
-
-template <class T> constexpr bool operator>(const optional<T>& x, const optional<T>& y)
-{
-  return (y < x);
-}
-
-template <class T> constexpr bool operator<=(const optional<T>& x, const optional<T>& y)
-{
-  return !(y < x);
-}
-
-template <class T> constexpr bool operator>=(const optional<T>& x, const optional<T>& y)
-{
-  return !(x < y);
-}
-
-
-// 20.5.9, Comparison with nullopt
-template <class T> constexpr bool operator==(const optional<T>& x, nullopt_t) noexcept
-{
-  return (!x);
-}
-
-template <class T> constexpr bool operator==(nullopt_t, const optional<T>& x) noexcept
-{
-  return (!x);
-}
-
-template <class T> constexpr bool operator!=(const optional<T>& x, nullopt_t) noexcept
-{
-  return bool(x);
-}
-
-template <class T> constexpr bool operator!=(nullopt_t, const optional<T>& x) noexcept
-{
-  return bool(x);
-}
-
-template <class T> constexpr bool operator<(const optional<T>&, nullopt_t) noexcept
-{
-  return false;
-}
-
-template <class T> constexpr bool operator<(nullopt_t, const optional<T>& x) noexcept
-{
-  return bool(x);
-}
-
-template <class T> constexpr bool operator<=(const optional<T>& x, nullopt_t) noexcept
-{
-  return (!x);
-}
-
-template <class T> constexpr bool operator<=(nullopt_t, const optional<T>&) noexcept
-{
-  return true;
-}
-
-template <class T> constexpr bool operator>(const optional<T>& x, nullopt_t) noexcept
-{
-  return bool(x);
-}
-
-template <class T> constexpr bool operator>(nullopt_t, const optional<T>&) noexcept
-{
-  return false;
-}
-
-template <class T> constexpr bool operator>=(const optional<T>&, nullopt_t) noexcept
-{
-  return true;
-}
-
-template <class T> constexpr bool operator>=(nullopt_t, const optional<T>& x) noexcept
-{
-  return (!x);
-}
-
-
-
-// 20.5.10, Comparison with T
-template <class T> constexpr bool operator==(const optional<T>& x, const T& v)
-{
-  return bool(x) ? *x == v : false;
-}
-
-template <class T> constexpr bool operator==(const T& v, const optional<T>& x)
-{
-  return bool(x) ? v == *x : false;
-}
-
-template <class T> constexpr bool operator!=(const optional<T>& x, const T& v)
-{
-  return bool(x) ? *x != v : true;
-}
-
-template <class T> constexpr bool operator!=(const T& v, const optional<T>& x)
-{
-  return bool(x) ? v != *x : true;
-}
-
-template <class T> constexpr bool operator<(const optional<T>& x, const T& v)
-{
-  return bool(x) ? *x < v : true;
-}
-
-template <class T> constexpr bool operator>(const T& v, const optional<T>& x)
-{
-  return bool(x) ? v > *x : true;
-}
-
-template <class T> constexpr bool operator>(const optional<T>& x, const T& v)
-{
-  return bool(x) ? *x > v : false;
-}
-
-template <class T> constexpr bool operator<(const T& v, const optional<T>& x)
-{
-  return bool(x) ? v < *x : false;
-}
-
-template <class T> constexpr bool operator>=(const optional<T>& x, const T& v)
-{
-  return bool(x) ? *x >= v : false;
-}
-
-template <class T> constexpr bool operator<=(const T& v, const optional<T>& x)
-{
-  return bool(x) ? v <= *x : false;
-}
-
-template <class T> constexpr bool operator<=(const optional<T>& x, const T& v)
-{
-  return bool(x) ? *x <= v : true;
-}
-
-template <class T> constexpr bool operator>=(const T& v, const optional<T>& x)
-{
-  return bool(x) ? v >= *x : true;
-}
-
-
-// Comparison of optional<T&> with T
-template <class T> constexpr bool operator==(const optional<T&>& x, const T& v)
-{
-  return bool(x) ? *x == v : false;
-}
-
-template <class T> constexpr bool operator==(const T& v, const optional<T&>& x)
-{
-  return bool(x) ? v == *x : false;
-}
-
-template <class T> constexpr bool operator!=(const optional<T&>& x, const T& v)
-{
-  return bool(x) ? *x != v : true;
-}
-
-template <class T> constexpr bool operator!=(const T& v, const optional<T&>& x)
-{
-  return bool(x) ? v != *x : true;
-}
-
-template <class T> constexpr bool operator<(const optional<T&>& x, const T& v)
-{
-  return bool(x) ? *x < v : true;
-}
-
-template <class T> constexpr bool operator>(const T& v, const optional<T&>& x)
-{
-  return bool(x) ? v > *x : true;
-}
-
-template <class T> constexpr bool operator>(const optional<T&>& x, const T& v)
-{
-  return bool(x) ? *x > v : false;
-}
-
-template <class T> constexpr bool operator<(const T& v, const optional<T&>& x)
-{
-  return bool(x) ? v < *x : false;
-}
-
-template <class T> constexpr bool operator>=(const optional<T&>& x, const T& v)
-{
-  return bool(x) ? *x >= v : false;
-}
-
-template <class T> constexpr bool operator<=(const T& v, const optional<T&>& x)
-{
-  return bool(x) ? v <= *x : false;
-}
-
-template <class T> constexpr bool operator<=(const optional<T&>& x, const T& v)
-{
-  return bool(x) ? *x <= v : true;
-}
-
-template <class T> constexpr bool operator>=(const T& v, const optional<T&>& x)
-{
-  return bool(x) ? v >= *x : true;
-}
-
-// Comparison of optional<T const&> with T
-template <class T> constexpr bool operator==(const optional<const T&>& x, const T& v)
-{
-  return bool(x) ? *x == v : false;
-}
-
-template <class T> constexpr bool operator==(const T& v, const optional<const T&>& x)
-{
-  return bool(x) ? v == *x : false;
-}
-
-template <class T> constexpr bool operator!=(const optional<const T&>& x, const T& v)
-{
-  return bool(x) ? *x != v : true;
-}
-
-template <class T> constexpr bool operator!=(const T& v, const optional<const T&>& x)
-{
-  return bool(x) ? v != *x : true;
-}
-
-template <class T> constexpr bool operator<(const optional<const T&>& x, const T& v)
-{
-  return bool(x) ? *x < v : true;
-}
-
-template <class T> constexpr bool operator>(const T& v, const optional<const T&>& x)
-{
-  return bool(x) ? v > *x : true;
-}
-
-template <class T> constexpr bool operator>(const optional<const T&>& x, const T& v)
-{
-  return bool(x) ? *x > v : false;
-}
-
-template <class T> constexpr bool operator<(const T& v, const optional<const T&>& x)
-{
-  return bool(x) ? v < *x : false;
-}
-
-template <class T> constexpr bool operator>=(const optional<const T&>& x, const T& v)
-{
-  return bool(x) ? *x >= v : false;
-}
-
-template <class T> constexpr bool operator<=(const T& v, const optional<const T&>& x)
-{
-  return bool(x) ? v <= *x : false;
-}
-
-template <class T> constexpr bool operator<=(const optional<const T&>& x, const T& v)
-{
-  return bool(x) ? *x <= v : true;
-}
-
-template <class T> constexpr bool operator>=(const T& v, const optional<const T&>& x)
-{
-  return bool(x) ? v >= *x : true;
-}
-
-
-// 20.5.12, Specialized algorithms
-template <class T>
-void swap(optional<T>& x, optional<T>& y) noexcept(noexcept(x.swap(y)))
-{
-  x.swap(y);
-}
-
-
-template <class T>
-constexpr optional<typename decay<T>::type> make_optional(T&& v)
-{
-  return optional<typename decay<T>::type>(constexpr_forward<T>(v));
-}
-
-template <class X>
-constexpr optional<X&> make_optional(reference_wrapper<X> v)
-{
-  return optional<X&>(v.get());
-}
-
-
-} // namespace experimental
-} // namespace std
-
-namespace std
-{
-  template <typename T>
-  struct hash<std::experimental::optional<T>>
-  {
-    typedef typename hash<T>::result_type result_type;
-    typedef std::experimental::optional<T> argument_type;
-
-    constexpr result_type operator()(argument_type const& arg) const {
-      return arg ? std::hash<T>{}(*arg) : result_type{};
-    }
-  };
-
-  template <typename T>
-  struct hash<std::experimental::optional<T&>>
-  {
-    typedef typename hash<T>::result_type result_type;
-    typedef std::experimental::optional<T&> argument_type;
-
-    constexpr result_type operator()(argument_type const& arg) const {
-      return arg ? std::hash<T>{}(*arg) : result_type{};
-    }
-  };
-}
-
-# undef TR2_OPTIONAL_REQUIRES
-# undef TR2_OPTIONAL_ASSERTED_EXPRESSION
-
-# endif //___OPTIONAL_HPP___
diff --git a/launchers/macosx/include/portcheck.h b/launchers/macosx/include/portcheck.h
deleted file mode 100644
index 39487369cb3724f9fe176343397202a2f359faaa..0000000000000000000000000000000000000000
--- a/launchers/macosx/include/portcheck.h
+++ /dev/null
@@ -1,60 +0,0 @@
-#pragma once
-
-#include <stdio.h>
-#include <unistd.h>
-#include <sys/types.h>
-#include <sys/socket.h>
-#include <arpa/inet.h>
-#include <errno.h>
-
-typedef struct sockaddr *sad; /* A necesary dummy typedef */
-
-int port_check(int portNum)
-{
-  int sock; /* Socket that will be bind */
-  struct sockaddr_in sin; /* Address Structure */
-  
-  /* Create the socket */
-  /* PF_INET is the option for make a TCP socket.
-   You can try "man socket" for more info */
-  sock = socket( PF_INET, SOCK_STREAM, 0 );
-  
-  /* The socket creation failed */
-  if ( 0 > sock ) {
-    perror( "socket" );
-    return ( -1 );
-  }
-  
-  /* Address */
-  sin.sin_family = AF_INET;
-  sin.sin_port = htons( portNum ); /* htons() convert the number
-                                    to big endian */
-  sin.sin_addr.s_addr = INADDR_ANY;
-  
-  /* We bind the socket to the port PORT to check if
-   the port is in use */
-  if ( 0 > bind( sock, (sad)&sin, sizeof( sin ) ) ) {
-    /* Bind failed, now we can check if the address is
-     in use */
-    
-    if ( EADDRINUSE == errno ) {
-      /* We put the code necesary to manage this case */
-      printf( "The TCP port %d is in use.\n", portNum );
-    }
-    
-    else
-    /* If the error were other than EADDRINUSE, we print it */
-      perror( "bind" );
-    
-    return 1;
-  }
-  
-  /* If we arrive to this point, the port weren't in use and
-   we have it attached to our program. We can close
-   the socket or use it */
-  close( sock ); /* Close the socket */
-  
-  return 0;
-}
-
-
diff --git a/launchers/macosx/include/sharedqueue.h b/launchers/macosx/include/sharedqueue.h
deleted file mode 100644
index 319b8542342a78680382d64cf702e41997a305da..0000000000000000000000000000000000000000
--- a/launchers/macosx/include/sharedqueue.h
+++ /dev/null
@@ -1,66 +0,0 @@
-#ifndef SHAREDQUEUE_H__
-#define SHAREDQUEUE_H__
-// Public domain
-
-#include <queue>
-#include <mutex>
-#include <exception>
-#include <condition_variable>
-
-/** Multiple producer, multiple consumer thread safe queue
- * Since 'return by reference' is used this queue won't throw */
-template<typename T>
-class shared_queue
-{
-  std::queue<T> queue_;
-  mutable std::mutex m_;
-  std::condition_variable data_cond_;
-  
-  shared_queue& operator=(const shared_queue&);
-  shared_queue(const shared_queue& other);
-  
-public:
-  shared_queue(){}
-  
-  void push(T item){
-    {
-      std::lock_guard<std::mutex> lock(m_);
-      queue_.push(item);
-    }
-    data_cond_.notify_one();
-  }
-  
-  /// \return immediately, with true if successful retrieval
-  bool try_and_pop(T& popped_item){
-    std::lock_guard<std::mutex> lock(m_);
-    if(queue_.empty()){
-      return false;
-    }
-    popped_item=std::move(queue_.front());
-    queue_.pop();
-    return true;
-  }
-  
-  /// Try to retrieve, if no items, wait till an item is available and try again
-  void wait_and_pop(T& popped_item){
-    std::unique_lock<std::mutex> lock(m_); // note: unique_lock is needed for std::condition_variable::wait
-    while(queue_.empty())
-    { //                       The 'while' loop below is equal to
-      data_cond_.wait(lock);  //data_cond_.wait(lock, [](bool result){return !queue_.empty();});
-    }
-    popped_item=std::move(queue_.front());
-    queue_.pop();
-  }
-  
-  bool empty() const{
-    std::lock_guard<std::mutex> lock(m_);
-    return queue_.empty();
-  }
-  
-  unsigned size() const{
-    std::lock_guard<std::mutex> lock(m_);
-    return queue_.size();
-  }
-};
-
-#endif // SHAREDQUEUE_H__
diff --git a/launchers/macosx/include/strutil.hpp b/launchers/macosx/include/strutil.hpp
deleted file mode 100644
index ca52442a2f2a2c1bd990e7d1ac38e4f1deb8fe48..0000000000000000000000000000000000000000
--- a/launchers/macosx/include/strutil.hpp
+++ /dev/null
@@ -1,130 +0,0 @@
-#ifndef __STRUTIL_HPP__
-#define __STRUTIL_HPP__
-
-#include <algorithm>
-#include <functional>
-#include <string>
-#include <memory>
-#include <iostream>
-#include <cctype>
-#include <locale>
-#include "optional.h"
-
-#import <Foundation/NSString.h>
-
-#include <CoreFoundation/CoreFoundation.h>
-#include <CoreFoundation/CFArray.h>
-#include <CoreFoundation/CFString.h>
-
-inline std::string strprintf(const char *fromat, ...)
-{
-	std::string s;
-	s.resize(128); // best guess
-	char *buff = const_cast<char *>(s.data());
-
-	va_list arglist;
-	va_start(arglist, fromat);
-	auto len = vsnprintf(buff, 128, fromat, arglist);
-	va_end(arglist);
-
-	if (len > 127)
-	{
-		va_start(arglist, fromat);
-		s.resize(len + 1); // leave room for null terminator
-		buff = const_cast<char *>(s.data());
-		len = vsnprintf(buff, len+1, fromat, arglist);
-		va_end(arglist);
-	}
-	s.resize(len);
-	return s; // move semantics FTW
-}
-
-inline std::string extractString(CFStringRef value)
-{
-  const char * data = CFStringGetCStringPtr(value, kCFStringEncodingUTF8);
-  if (data != NULL)
-  {
-    return std::string(data, strlen(data));
-  } else {
-    CFIndex strSize = CFStringGetLength(value)+1;
-    char * retry = (char *)malloc((int)strSize);
-    if (CFStringGetCString(value, retry, strSize, kCFStringEncodingUTF8)) {
-      return std::string(retry, strlen(retry));
-    }
-    return std::string("[null]");
-  }
-}
-
-inline bool replace(std::string& str, const std::string& from, const std::string& to) {
-  size_t start_pos = str.find(from);
-  if(start_pos == std::string::npos)
-    return false;
-  str.replace(start_pos, from.length(), to);
-  return true;
-}
-
-
-// trim from start (in place)
-static inline void ltrim(std::string &s) {
-    s.erase(s.begin(), std::find_if(s.begin(), s.end(),
-            std::not1(std::ptr_fun<int, int>(std::isspace))));
-}
-
-// trim from end (in place)
-static inline void rtrim(std::string &s) {
-    s.erase(std::find_if(s.rbegin(), s.rend(),
-            std::not1(std::ptr_fun<int, int>(std::isspace))).base(), s.end());
-}
-
-// trim from both ends (in place)
-static inline void trim(std::string &s) {
-    ltrim(s);
-    rtrim(s);
-}
-
-// trim from start (copying)
-static inline std::string ltrim_copy(std::string s) {
-    ltrim(s);
-    return s;
-}
-
-// trim from end (copying)
-static inline std::string rtrim_copy(std::string s) {
-    rtrim(s);
-    return s;
-}
-
-// trim from both ends (copying)
-static inline std::string trim_copy(std::string s) {
-    trim(s);
-    return s;
-}
-
-inline NSString* stdStringToNSString(std::string &stdstr) {
-  return [NSString stringWithUTF8String:stdstr.c_str()];
-}
-
-inline std::string nsStringToStd(NSString* nsStr) {
-  const char *charlist = [nsStr UTF8String];
-  return std::string(charlist);
-}
-
-#if __cplusplus > 201402L
-
-
-using std::optional;
-
-// Use CFStringRef instead of NSString*, otherwise disable ARC
-inline optional<CFStringRef> optionalString(bool val) {
-  optional<CFStringRef> myOptString;
-  if(val) {
-    // Cast to corresponding CoreFoundation object
-    myOptString = (CFStringRef)@"String";
-  }
-  return myOptString;
-}
-
-#endif
-
-
-#endif
diff --git a/launchers/macosx/include/subprocess.hpp b/launchers/macosx/include/subprocess.hpp
deleted file mode 100644
index fd3b1629d882b35379037dacce911fbf533f3d32..0000000000000000000000000000000000000000
--- a/launchers/macosx/include/subprocess.hpp
+++ /dev/null
@@ -1,1634 +0,0 @@
-/*!
-
-Documentation for C++ subprocessing libraray.
-
-@copyright The code is licensed under the [MIT
-  License](http://opensource.org/licenses/MIT):
-  <br>
-  Copyright &copy; 2016-2018 Arun Muralidharan.
-  <br>
-  Permission is hereby granted, free of charge, to any person obtaining a copy
-  of this software and associated documentation files (the "Software"), to deal
-  in the Software without restriction, including without limitation the rights
-  to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-  copies of the Software, and to permit persons to whom the Software is
-  furnished to do so, subject to the following conditions:
-  <br>
-  The above copyright notice and this permission notice shall be included in
-  all copies or substantial portions of the Software.
-  <br>
-  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-  AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-  OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
-  SOFTWARE.
-
-@author [Arun Muralidharan]
-@see https://github.com/arun11299/cpp-subprocess to download the source code
-
-@version 1.0.0
-*/
-
-#ifndef SUBPROCESS_HPP
-#define SUBPROCESS_HPP
-
-#ifdef __cplusplus
-
-#include <map>
-#include <algorithm>
-#include <iostream>
-#include <string>
-#include <cstdlib>
-#include <cassert>
-#include <cstring>
-#include <cstdio>
-#include <csignal>
-#include <future>
-#include <vector>
-#include <sstream>
-#include <memory>
-#include <initializer_list>
-#include <exception>
-
-extern "C" {
-  #include <unistd.h>
-  #include <fcntl.h>
-  #include <sys/types.h>
-  #include <sys/wait.h>
-  #include <signal.h>
-}
-
-/*!
- * Getting started with reading this source code.
- * The source is mainly divided into four parts:
- * 1. Exception Classes:
- *    These are very basic exception classes derived from
- *    runtime_error exception.
- *    There are two types of exception thrown from subprocess
- *    library: OSError and CalledProcessError
- *
- * 2. Popen Class
- *    This is the main class the users will deal with. It
- *    provides with all the API's to deal with processes.
- *
- * 3. Util namespace
- *    It includes some helper functions to split/join a string,
- *    reading from file descriptors, waiting on a process, fcntl
- *    options on file descriptors etc.
- *
- * 4. Detail namespace
- *    This includes some metaprogramming and helper classes.
- */
-
-
-namespace subprocess {
-
-// Max buffer size allocated on stack for read error
-// from pipe
-static const size_t SP_MAX_ERR_BUF_SIZ = 1024;
-
-// Default buffer capcity for OutBuffer and ErrBuffer.
-// If the data exceeds this capacity, the buffer size is grown
-// by 1.5 times its previous capacity
-static const size_t DEFAULT_BUF_CAP_BYTES = 8192;
-
-
-/*-----------------------------------------------
- *    EXCEPTION CLASSES
- *-----------------------------------------------
- */
-
-/*!
- * class: CalledProcessError
- * Thrown when there was error executing the command.
- * Check Popen class API's to know when this exception
- * can be thrown.
- *
- */
-class CalledProcessError: public std::runtime_error
-{
-public:
-  CalledProcessError(const std::string& error_msg):
-    std::runtime_error(error_msg)
-  {}
-};
-
-
-/*!
- * class: OSError
- * Thrown when some system call fails to execute or give result.
- * The exception message contains the name of the failed system call
- * with the stringisized errno code.
- * Check Popen class API's to know when this exception would be
- * thrown.
- * Its usual that the API exception specification would have
- * this exception together with CalledProcessError.
- */
-class OSError: public std::runtime_error
-{
-public:
-  OSError(const std::string& err_msg, int err_code):
-    std::runtime_error( err_msg + " : " + std::strerror(err_code) )
-  {}
-};
-
-//--------------------------------------------------------------------
-
-namespace util
-{
-
-  /*!
-   * Function: split
-   * Parameters:
-   * [in] str : Input string which needs to be split based upon the
-   *            delimiters provided.
-   * [in] deleims : Delimiter characters based upon which the string needs
-   *                to be split. Default constructed to ' '(space) and '\t'(tab)
-   * [out] vector<string> : Vector of strings split at deleimiter.
-   */
-  static inline std::vector<std::string>
-  split(const std::string& str, const std::string& delims=" \t")
-  {
-    std::vector<std::string> res;
-    size_t init = 0;
-
-    while (true) {
-      auto pos = str.find_first_of(delims, init);
-      if (pos == std::string::npos) {
-        res.emplace_back(str.substr(init, str.length()));
-        break;
-      }
-      res.emplace_back(str.substr(init, pos - init));
-      pos++;
-      init = pos;
-    }
-
-    return res;
-  }
-
-
-  /*!
-   * Function: join
-   * Parameters:
-   * [in] vec : Vector of strings which needs to be joined to form
-   *            a single string with words seperated by a seperator char.
-   *  [in] sep : String used to seperate 2 words in the joined string.
-   *             Default constructed to ' ' (space).
-   *  [out] string: Joined string.
-   */
-  static inline
-  std::string join(const std::vector<std::string>& vec,
-                   const std::string& sep = " ")
-  {
-    std::string res;
-    for (auto& elem : vec) res.append(elem + sep);
-    res.erase(--res.end());
-    return res;
-  }
-
-
-  /*!
-   * Function: set_clo_on_exec
-   * Sets/Resets the FD_CLOEXEC flag on the provided file descriptor
-   * based upon the `set` parameter.
-   * Parameters:
-   * [in] fd : The descriptor on which FD_CLOEXEC needs to be set/reset.
-   * [in] set : If 'true', set FD_CLOEXEC.
-   *            If 'false' unset FD_CLOEXEC.
-   */
-  static inline
-  void set_clo_on_exec(int fd, bool set = true)
-  {
-    int flags = fcntl(fd, F_GETFD, 0);
-    if (set) flags |= FD_CLOEXEC;
-    else flags &= ~FD_CLOEXEC;
-    //TODO: should check for errors
-    fcntl(fd, F_SETFD, flags);
-  }
-
-
-  /*!
-   * Function: pipe_cloexec
-   * Creates a pipe and sets FD_CLOEXEC flag on both
-   * read and write descriptors of the pipe.
-   * Parameters:
-   * [out] : A pair of file descriptors.
-   *         First element of pair is the read descriptor of pipe.
-   *         Second element is the write descriptor of pipe.
-   */
-  static inline
-  std::pair<int, int> pipe_cloexec() throw (OSError)
-  {
-    int pipe_fds[2];
-    int res = pipe(pipe_fds);
-    if (res) {
-      throw OSError("pipe failure", errno);
-    }
-
-    set_clo_on_exec(pipe_fds[0]);
-    set_clo_on_exec(pipe_fds[1]);
-
-    return std::make_pair(pipe_fds[0], pipe_fds[1]);
-  }
-
-
-  /*!
-   * Function: write_n
-   * Writes `length` bytes to the file descriptor `fd`
-   * from the buffer `buf`.
-   * Parameters:
-   * [in] fd : The file descriptotr to write to.
-   * [in] buf: Buffer from which data needs to be written to fd.
-   * [in] length: The number of bytes that needs to be written from
-   *              `buf` to `fd`.
-   * [out] int : Number of bytes written or -1 in case of failure.
-   */
-  static inline
-  int write_n(int fd, const char* buf, size_t length)
-  {
-    size_t nwritten = 0;
-    while (nwritten < length) {
-      int written = write(fd, buf + nwritten, (int)length - nwritten);
-      if (written == -1) return -1;
-      nwritten += written;
-    }
-    return (int)nwritten;
-  }
-
-
-  /*!
-   * Function: read_atmost_n
-   * Reads at the most `read_upto` bytes from the
-   * file descriptor `fd` before returning.
-   * Parameters:
-   * [in] fd : The file descriptor from which it needs to read.
-   * [in] buf : The buffer into which it needs to write the data.
-   * [in] read_upto: Max number of bytes which must be read from `fd`.
-   * [out] int : Number of bytes written to `buf` or read from `fd`
-   *             OR -1 in case of error.
-   *  NOTE: In case of EINTR while reading from socket, this API
-   *  will retry to read from `fd`, but only till the EINTR counter
-   *  reaches 50 after which it will return with whatever data it read.
-   */
-  static inline
-  int read_atmost_n(int fd, char* buf, size_t read_upto)
-  {
-    int rbytes = 0;
-    int eintr_cnter = 0;
-
-    while (1) {
-      int read_bytes = read(fd, buf + rbytes, (int)read_upto - rbytes);
-      if (read_bytes == -1) {
-        if (errno == EINTR) {
-          if (eintr_cnter >= 50) return -1;
-          eintr_cnter++;
-          continue;
-        }
-        return -1;
-      }
-      if (read_bytes == 0) return rbytes;
-
-      rbytes += read_bytes;
-    }
-    return rbytes;
-  }
-
-
-  /*!
-   * Function: read_all
-   * Reads all the available data from `fd` into
-   * `buf`. Internally calls read_atmost_n.
-   * Parameters:
-   * [in] fd : The file descriptor from which to read from.
-   * [in] buf : The buffer of type `class Buffer` into which
-   *            the read data is written to.
-   * [out] int: Number of bytes read OR -1 in case of failure.
-   *
-   * NOTE: `class Buffer` is a exposed public class. See below.
-   */
-  template <typename Buffer>
-  // Requires Buffer to be of type class Buffer
-  static inline int read_all(int fd, Buffer& buf)
-  {
-    size_t orig_size = buf.size();
-    int increment = (int)orig_size;
-    auto buffer = buf.data();
-    int total_bytes_read = 0;
-
-    while (1) {
-      int rd_bytes = read_atmost_n(fd, buffer, buf.size());
-      if (rd_bytes == increment) {
-        // Resize the buffer to accomodate more
-        orig_size = orig_size * 1.5;
-        increment = (int)orig_size - (int)buf.size();
-        buf.resize(orig_size);
-        //update the buffer pointer
-        buffer = buf.data();
-        buffer += rd_bytes;
-        total_bytes_read += rd_bytes;
-
-      } else if (rd_bytes != -1) {
-        total_bytes_read += rd_bytes;
-        break;
-
-      } else {
-        if (total_bytes_read == 0) return -1;
-        break;
-      }
-    }
-    return total_bytes_read;
-  }
-
-
-  /*!
-   * Function: wait_for_child_exit
-   * Waits for the process with pid `pid` to exit
-   * and returns its status.
-   * Parameters:
-   * [in] pid : The pid of the process.
-   * [out] pair<int, int>:
-   *    pair.first : Return code of the waitpid call.
-   *    pair.second : Exit status of the process.
-   *
-   *  NOTE: This is a blocking call as in, it will loop
-   *  till the child is exited.
-   */
-  static inline
-  std::pair<int, int> wait_for_child_exit(int pid)
-  {
-    int status = 0;
-    int ret = -1;
-    while (1) {
-      ret = waitpid(pid, &status, WNOHANG);
-      if (ret == -1) break;
-      if (ret == 0) continue;
-      return std::make_pair(ret, status);
-    }
-
-    return std::make_pair(ret, status);
-  }
-
-
-}; // end namespace util
-
-
-
-/* -------------------------------
- *     Popen Arguments
- * -------------------------------
- */
-
-/*!
- * The buffer size of the stdin/stdout/stderr
- * streams of the child process.
- * Default value is 0.
- */
-struct bufsize {
-  bufsize(int siz): bufsiz(siz) {}
-  int  bufsiz = 0;
-};
-
-/*!
- * Option to defer spawning of the child process
- * till `Popen::start_process` API is called.
- * Default value is false.
- */
-struct defer_spawn {
-  defer_spawn(bool d): defer(d) {}
-  bool defer  = false;
-};
-
-/*!
- * Option to close all file descriptors
- * when the child process is spawned.
- * The close fd list does not include
- * input/output/error if they are explicitly
- * set as part of the Popen arguments.
- *
- * Default value is false.
- */
-struct close_fds {
-  close_fds(bool c): close_all(c) {}
-  bool close_all = false;
-};
-
-/*!
- * Option to make the child process as the
- * session leader and thus the process
- * group leader.
- * Default value is false.
- */
-struct session_leader {
-  session_leader(bool sl): leader_(sl) {}
-  bool leader_ = false;
-};
-
-struct shell {
-  shell(bool s): shell_(s) {}
-  bool shell_ = false;
-};
-
-/*!
- * Base class for all arguments involving string value.
- */
-struct string_arg
-{
-  string_arg(const char* arg): arg_value(arg) {}
-  string_arg(std::string&& arg): arg_value(std::move(arg)) {}
-  string_arg(std::string arg): arg_value(std::move(arg)) {}
-  std::string arg_value;
-};
-
-/*!
- * Option to specify the executable name seperately
- * from the args sequence.
- * In this case the cmd args must only contain the
- * options required for this executable.
- *
- * Eg: executable{"ls"}
- */
-struct executable: string_arg
-{
-  template <typename T>
-  executable(T&& arg): string_arg(std::forward<T>(arg)) {}
-};
-
-/*!
- * Option to set the current working directory
- * of the spawned process.
- *
- * Eg: cwd{"/som/path/x"}
- */
-struct cwd: string_arg
-{
-  template <typename T>
-  cwd(T&& arg): string_arg(std::forward<T>(arg)) {}
-};
-
-/*!
- * Option to specify environment variables required by
- * the spawned process.
- *
- * Eg: environment{{ {"K1", "V1"}, {"K2", "V2"},... }}
- */
-struct environment
-{
-  environment(std::map<std::string, std::string>&& env):
-    env_(std::move(env)) {}
-  environment(const std::map<std::string, std::string>& env):
-    env_(env) {}
-  std::map<std::string, std::string> env_;
-};
-
-
-/*!
- * Used for redirecting input/output/error
- */
-enum IOTYPE {
-  STDOUT = 1,
-  STDERR,
-  PIPE,
-};
-
-//TODO: A common base/interface for below stream structures ??
-
-/*!
- * Option to specify the input channel for the child
- * process. It can be:
- * 1. An already open file descriptor.
- * 2. A file name.
- * 3. IOTYPE. Usuall a PIPE
- *
- * Eg: input{PIPE}
- * OR in case of redirection, output of another Popen
- * input{popen.output()}
- */
-struct input
-{
-  // For an already existing file descriptor.
-  input(int fd): rd_ch_(fd) {}
-
-  // FILE pointer.
-  input (FILE* fp):input(fileno(fp)) { assert(fp); }
-
-  input(const char* filename) {
-    int fd = open(filename, O_RDONLY);
-    if (fd == -1) throw OSError("File not found: ", errno);
-    rd_ch_ = fd;
-  }
-  input(IOTYPE typ) {
-    assert (typ == PIPE && "STDOUT/STDERR not allowed");
-    std::tie(rd_ch_, wr_ch_) = util::pipe_cloexec();
-  }
-
-  int rd_ch_ = -1;
-  int wr_ch_ = -1;
-};
-
-
-/*!
- * Option to specify the output channel for the child
- * process. It can be:
- * 1. An already open file descriptor.
- * 2. A file name.
- * 3. IOTYPE. Usually a PIPE.
- *
- * Eg: output{PIPE}
- * OR output{"output.txt"}
- */
-struct output
-{
-  output(int fd): wr_ch_(fd) {}
-
-  output (FILE* fp):output(fileno(fp)) { assert(fp); }
-
-  output(const char* filename) {
-    int fd = open(filename, O_APPEND | O_CREAT | O_RDWR, 0640);
-    if (fd == -1) throw OSError("File not found: ", errno);
-    wr_ch_ = fd;
-  }
-  output(IOTYPE typ) {
-    assert (typ == PIPE && "STDOUT/STDERR not allowed");
-    std::tie(rd_ch_, wr_ch_) = util::pipe_cloexec();
-  }
-
-  int rd_ch_ = -1;
-  int wr_ch_ = -1;
-};
-
-
-/*!
- * Option to specify the error channel for the child
- * process. It can be:
- * 1. An already open file descriptor.
- * 2. A file name.
- * 3. IOTYPE. Usually a PIPE or STDOUT
- *
- */
-struct error
-{
-  error(int fd): wr_ch_(fd) {}
-
-  error(FILE* fp):error(fileno(fp)) { assert(fp); }
-
-  error(const char* filename) {
-    int fd = open(filename, O_APPEND | O_CREAT | O_RDWR, 0640);
-    if (fd == -1) throw OSError("File not found: ", errno);
-    wr_ch_ = fd;
-  }
-  error(IOTYPE typ) {
-    assert ((typ == PIPE || typ == STDOUT) && "STDERR not aloowed");
-    if (typ == PIPE) {
-      std::tie(rd_ch_, wr_ch_) = util::pipe_cloexec();
-    } else {
-      // Need to defer it till we have checked all arguments
-      deferred_ = true;
-    }
-  }
-
-  bool deferred_ = false;
-  int rd_ch_ = -1;
-  int wr_ch_ = -1;
-};
-
-// Impoverished, meager, needy, truly needy
-// version of type erasure to store function pointers
-// needed to provide the functionality of preexec_func
-// ATTN: Can be used only to execute functions with no
-// arguments and returning void.
-// Could have used more efficient methods, ofcourse, but
-// that wont yield me the consistent syntax which I am
-// aiming for. If you know, then please do let me know.
-
-class preexec_func
-{
-public:
-  preexec_func() {}
-
-  template <typename Func>
-  preexec_func(Func f): holder_(new FuncHolder<Func>(f))
-  {}
-
-  void operator()() {
-    (*holder_)();
-  }
-
-private:
-  struct HolderBase {
-    virtual void operator()() const = 0;
-  };
-  template <typename T>
-  struct FuncHolder: HolderBase {
-    FuncHolder(T func): func_(func) {}
-    void operator()() const override {}
-    // The function pointer/reference
-    T func_;
-  };
-
-  std::unique_ptr<HolderBase> holder_ = nullptr;
-};
-
-// ~~~~ End Popen Args ~~~~
-
-
-/*!
- * class: Buffer
- * This class is a very thin wrapper around std::vector<char>
- * This is basically used to determine the length of the actual
- * data stored inside the dynamically resized vector.
- *
- * This is what is returned as the output to communicate and check_output
- * functions, so, users must know about this class.
- *
- * OutBuffer and ErrBuffer are just different typedefs to this class.
- */
-class Buffer
-{
-public:
-  Buffer() {}
-  Buffer(size_t cap) { buf.resize(cap); }
-  void add_cap(size_t cap) { buf.resize(cap); }
-
-#if 0
-  Buffer(const Buffer& other):
-    buf(other.buf),
-    length(other.length)
-  {
-    std::cout << "COPY" << std::endl;
-  }
-
-  Buffer(Buffer&& other):
-    buf(std::move(other.buf)),
-    length(other.length)
-  {
-    std::cout << "MOVE" << std::endl;
-  }
-#endif
-
-public:
-  std::vector<char> buf;
-  size_t length = 0;
-};
-
-// Buffer for storing output written to output fd
-using OutBuffer = Buffer;
-// Buffer for storing output written to error fd
-using ErrBuffer = Buffer;
-
-
-// Fwd Decl.
-class Popen;
-
-/*---------------------------------------------------
- *      DETAIL NAMESPACE
- *---------------------------------------------------
- */
-
-namespace detail {
-
-// Metaprogram for searching a type within
-// a variadic parameter pack
-// This is particularly required to do a compile time
-// checking of the arguments provided to 'check_ouput' function
-// wherein the user is not expected to provide an 'ouput' option.
-
-template <typename... T> struct param_pack{};
-
-template <typename F, typename T> struct has_type;
-
-template <typename F>
-struct has_type<F, param_pack<> > {
-  static constexpr bool value = false;
-};
-
-template <typename F, typename... T>
-struct has_type<F, param_pack<F, T...> > {
-  static constexpr bool value = true;
-};
-
-template <typename F, typename H, typename... T>
-struct has_type<F, param_pack<H,T...> > {
-  static constexpr bool value =
-    std::is_same<F, typename std::decay<H>::type>::value ? true : has_type<F, param_pack<T...> >::value;
-};
-
-//----
-
-/*!
- * A helper class to Popen class for setting
- * options as provided in the Popen constructor
- * or in check_ouput arguments.
- * This design allows us to _not_ have any fixed position
- * to any arguments and specify them in a way similar to what
- * can be done in python.
- */
-struct ArgumentDeducer
-{
-  ArgumentDeducer(Popen* p): popen_(p) {}
-
-  void set_option(executable&& exe);
-  void set_option(cwd&& cwdir);
-  void set_option(bufsize&& bsiz);
-  void set_option(environment&& env);
-  void set_option(defer_spawn&& defer);
-  void set_option(shell&& sh);
-  void set_option(input&& inp);
-  void set_option(output&& out);
-  void set_option(error&& err);
-  void set_option(close_fds&& cfds);
-  void set_option(preexec_func&& prefunc);
-  void set_option(session_leader&& sleader);
-
-private:
-  Popen* popen_ = nullptr;
-};
-
-/*!
- * A helper class to Popen.
- * This takes care of all the fork-exec logic
- * in the execute_child API.
- */
-class Child
-{
-public:
-  Child(Popen* p, int err_wr_pipe):
-    parent_(p),
-    err_wr_pipe_(err_wr_pipe)
-  {}
-
-  void execute_child();
-
-private:
-  // Lets call it parent even though
-  // technically a bit incorrect
-  Popen* parent_ = nullptr;
-  int err_wr_pipe_ = -1;
-};
-
-// Fwd Decl.
-class Streams;
-
-/*!
- * A helper class to Streams.
- * This takes care of management of communicating
- * with the child process with the means of the correct
- * file descriptor.
- */
-class Communication
-{
-public:
-  Communication(Streams* stream): stream_(stream)
-  {}
-  void operator=(const Communication&) = delete;
-public:
-  int send(const char* msg, size_t length);
-  int send(const std::vector<char>& msg);
-
-  std::pair<OutBuffer, ErrBuffer> communicate(const char* msg, size_t length);
-  std::pair<OutBuffer, ErrBuffer> communicate(const std::vector<char>& msg)
-  { return communicate(msg.data(), msg.size()); }
-
-  void set_out_buf_cap(size_t cap) { out_buf_cap_ = cap; }
-  void set_err_buf_cap(size_t cap) { err_buf_cap_ = cap; }
-
-private:
-  std::pair<OutBuffer, ErrBuffer> communicate_threaded(
-      const char* msg, size_t length);
-
-private:
-  Streams* stream_;
-  size_t out_buf_cap_ = DEFAULT_BUF_CAP_BYTES;
-  size_t err_buf_cap_ = DEFAULT_BUF_CAP_BYTES;
-};
-
-
-
-/*!
- * This is a helper class to Popen.
- * It takes care of management of all the file descriptors
- * and file pointers.
- * It dispatches of the communication aspects to the
- * Communication class.
- * Read through the data members to understand about the
- * various file descriptors used.
- */
-class Streams
-{
-public:
-  Streams():comm_(this) {}
-  void operator=(const Streams&) = delete;
-
-public:
-  void setup_comm_channels();
-
-  void cleanup_fds()
-  {
-    if (write_to_child_ != -1 && read_from_parent_ != -1) {
-      close(write_to_child_);
-    }
-    if (write_to_parent_ != -1 && read_from_child_ != -1) {
-      close(read_from_child_);
-    }
-    if (err_write_ != -1 && err_read_ != -1) {
-      close(err_read_);
-    }
-  }
-
-  void close_parent_fds()
-  {
-    if (write_to_child_ != -1)  close(write_to_child_);
-    if (read_from_child_ != -1) close(read_from_child_);
-    if (err_read_ != -1)        close(err_read_);
-  }
-
-  void close_child_fds()
-  {
-    if (write_to_parent_ != -1)  close(write_to_parent_);
-    if (read_from_parent_ != -1) close(read_from_parent_);
-    if (err_write_ != -1)        close(err_write_);
-  }
-
-  FILE* input()  { return input_.get(); }
-  FILE* output() { return output_.get(); }
-  FILE* error()  { return error_.get(); }
-
-  void input(FILE* fp)  { input_.reset(fp, fclose); }
-  void output(FILE* fp) { output_.reset(fp, fclose); }
-  void error(FILE* fp)  { error_.reset(fp, fclose); }
-
-  void set_out_buf_cap(size_t cap) { comm_.set_out_buf_cap(cap); }
-  void set_err_buf_cap(size_t cap) { comm_.set_err_buf_cap(cap); }
-
-public: /* Communication forwarding API's */
-  int send(const char* msg, size_t length)
-  { return comm_.send(msg, length); }
-
-  int send(const std::vector<char>& msg)
-  { return comm_.send(msg); }
-
-  std::pair<OutBuffer, ErrBuffer> communicate(const char* msg, size_t length)
-  { return comm_.communicate(msg, length); }
-
-  std::pair<OutBuffer, ErrBuffer> communicate(const std::vector<char>& msg)
-  { return comm_.communicate(msg); }
-
-
-public:// Yes they are public
-
-  std::shared_ptr<FILE> input_  = nullptr;
-  std::shared_ptr<FILE> output_ = nullptr;
-  std::shared_ptr<FILE> error_  = nullptr;
-
-  // Buffer size for the IO streams
-  int bufsiz_ = 0;
-
-  // Pipes for communicating with child
-
-  // Emulates stdin
-  int write_to_child_   = -1; // Parent owned descriptor
-  int read_from_parent_ = -1; // Child owned descriptor
-
-  // Emulates stdout
-  int write_to_parent_ = -1; // Child owned descriptor
-  int read_from_child_ = -1; // Parent owned descriptor
-
-  // Emulates stderr
-  int err_write_ = -1; // Write error to parent (Child owned)
-  int err_read_  = -1; // Read error from child (Parent owned)
-
-private:
-  Communication comm_;
-};
-
-}; // end namespace detail
-
-
-
-/*!
- * class: Popen
- * This is the single most important class in the whole library
- * and glues together all the helper classes to provide a common
- * interface to the client.
- *
- * API's provided by the class:
- * 1. Popen({"cmd"}, output{..}, error{..}, cwd{..}, ....)
- *    Command provided as a sequence.
- * 2. Popen("cmd arg1"m output{..}, error{..}, cwd{..}, ....)
- *    Command provided in a single string.
- * 3. wait()             - Wait for the child to exit.
- * 4. retcode()          - The return code of the exited child.
- * 5. pid()              - PID of the spawned child.
- * 6. poll()             - Check the status of the running child.
- * 7. kill(sig_num)      - Kill the child. SIGTERM used by default.
- * 8. send(...)          - Send input to the input channel of the child.
- * 9. communicate(...)   - Get the output/error from the child and close the channels
- *                         from the parent side.
- *10. input()            - Get the input channel/File pointer. Can be used for
- *                         cutomizing the way of sending input to child.
- *11. output()           - Get the output channel/File pointer. Usually used
-                           in case of redirection. See piping examples.
- *12. error()            - Get the error channel/File poiner. Usually used
-                           in case of redirection.
- *13. start_process()    - Start the child process. Only to be used when
- *                         `defer_spawn` option was provided in Popen constructor.
- */
-class Popen
-{
-public:
-  friend struct detail::ArgumentDeducer;
-  friend class detail::Child;
-
-  template <typename... Args>
-  Popen(const std::string& cmd_args, Args&& ...args):
-    args_(cmd_args)
-  {
-    vargs_ = util::split(cmd_args);
-    init_args(std::forward<Args>(args)...);
-
-    // Setup the communication channels of the Popen class
-    stream_.setup_comm_channels();
-
-    if (!defer_process_start_) execute_process();
-  }
-
-  template <typename... Args>
-  Popen(std::initializer_list<const char*> cmd_args, Args&& ...args)
-  {
-    vargs_.insert(vargs_.end(), cmd_args.begin(), cmd_args.end());
-    init_args(std::forward<Args>(args)...);
-
-    // Setup the communication channels of the Popen class
-    stream_.setup_comm_channels();
-
-    if (!defer_process_start_) execute_process();
-  }
-
-  void start_process() throw (CalledProcessError, OSError);
-
-  int pid() const noexcept { return child_pid_; }
-
-  int retcode() const noexcept { return retcode_; }
-
-  int wait() throw(OSError);
-
-  int poll() throw(OSError);
-
-  // Does not fail, Caller is expected to recheck the
-  // status with a call to poll()
-  void kill(int sig_num = 9);
-
-  void set_out_buf_cap(size_t cap) { stream_.set_out_buf_cap(cap); }
-
-  void set_err_buf_cap(size_t cap) { stream_.set_err_buf_cap(cap); }
-
-  int send(const char* msg, size_t length)
-  { return stream_.send(msg, length); }
-
-  int send(const std::vector<char>& msg)
-  { return stream_.send(msg); }
-
-  std::pair<OutBuffer, ErrBuffer> communicate(const char* msg, size_t length)
-  {
-    auto res = stream_.communicate(msg, length);
-    retcode_ = wait();
-    return res;
-  }
-
-  std::pair<OutBuffer, ErrBuffer> communicate(const std::vector<char>& msg)
-  {
-    auto res = stream_.communicate(msg);
-    retcode_ = wait();
-    return res;
-  }
-
-  std::pair<OutBuffer, ErrBuffer> communicate()
-  {
-    return communicate(nullptr, 0);
-  }
-
-  FILE* input()  { return stream_.input(); }
-  FILE* output() { return stream_.output();}
-  FILE* error()  { return stream_.error(); }
-
-private:
-  template <typename F, typename... Args>
-  void init_args(F&& farg, Args&&... args);
-  void init_args();
-  void populate_c_argv();
-  void execute_process() throw (CalledProcessError, OSError);
-
-private:
-  detail::Streams stream_;
-
-  bool defer_process_start_ = false;
-  bool close_fds_ = false;
-  bool has_preexec_fn_ = false;
-  bool shell_ = false;
-  bool session_leader_ = false;
-
-  std::string exe_name_;
-  std::string cwd_;
-  std::map<std::string, std::string> env_;
-  preexec_func preexec_fn_;
-
-  // Command in string format
-  std::string args_;
-  // Comamnd provided as sequence
-  std::vector<std::string> vargs_;
-  std::vector<char*> cargv_;
-
-  bool child_created_ = false;
-  // Pid of the child process
-  int child_pid_ = -1;
-
-  int retcode_ = -1;
-};
-
-inline void Popen::init_args() {
-  populate_c_argv();
-}
-
-template <typename F, typename... Args>
-inline void Popen::init_args(F&& farg, Args&&... args)
-{
-  detail::ArgumentDeducer argd(this);
-  argd.set_option(std::forward<F>(farg));
-  init_args(std::forward<Args>(args)...);
-}
-
-inline void Popen::populate_c_argv()
-{
-  cargv_.clear();
-  cargv_.reserve(vargs_.size() + 1);
-  for (auto& arg : vargs_) cargv_.push_back(&arg[0]);
-  cargv_.push_back(nullptr);
-}
-
-inline void Popen::start_process() throw (CalledProcessError, OSError)
-{
-  // The process was started/tried to be started
-  // in the constructor itself.
-  // For explicitly calling this API to start the
-  // process, 'defer_spawn' argument must be set to
-  // true in the constructor.
-  if (!defer_process_start_) {
-    assert (0);
-    return;
-  }
-  execute_process();
-}
-
-inline int Popen::wait() throw (OSError)
-{
-  int ret, status;
-  std::tie(ret, status) = util::wait_for_child_exit(pid());
-  if (ret == -1) {
-    if (errno != ECHILD) throw OSError("waitpid failed", errno);
-    return 0;
-  }
-  if (WIFEXITED(status)) return WEXITSTATUS(status);
-  if (WIFSIGNALED(status)) return WTERMSIG(status);
-  else return 255;
-
-  return 0;
-}
-
-inline int Popen::poll() throw (OSError)
-{
-  int status;
-  if (!child_created_) return -1; // TODO: ??
-
-  // Returns zero if child is still running
-  int ret = waitpid(child_pid_, &status, WNOHANG);
-  if (ret == 0) return -1;
-
-  if (ret == child_pid_) {
-    if (WIFSIGNALED(status)) {
-      retcode_ = WTERMSIG(status);
-    } else if (WIFEXITED(status)) {
-      retcode_ = WEXITSTATUS(status);
-    } else {
-      retcode_ = 255;
-    }
-    return retcode_;
-  }
-
-  if (ret == -1) {
-    // From subprocess.py
-    // This happens if SIGCHLD is set to be ignored
-    // or waiting for child process has otherwise been disabled
-    // for our process. This child is dead, we cannot get the
-    // status.
-    if (errno == ECHILD) retcode_ = 0;
-    else throw OSError("waitpid failed", errno);
-  } else {
-    retcode_ = ret;
-  }
-
-  return retcode_;
-}
-
-inline void Popen::kill(int sig_num)
-{
-  if (session_leader_) killpg(child_pid_, sig_num);
-  else ::kill(child_pid_, sig_num);
-}
-
-
-inline void Popen::execute_process() throw (CalledProcessError, OSError)
-{
-  int err_rd_pipe, err_wr_pipe;
-  std::tie(err_rd_pipe, err_wr_pipe) = util::pipe_cloexec();
-
-  if (shell_) {
-    auto new_cmd = util::join(vargs_);
-    vargs_.clear();
-    vargs_.insert(vargs_.begin(), {"/bin/sh", "-c"});
-    vargs_.push_back(new_cmd);
-    populate_c_argv();
-  }
-
-  if (exe_name_.length()) {
-    vargs_.insert(vargs_.begin(), exe_name_);
-    populate_c_argv();
-  }
-  exe_name_ = vargs_[0];
-
-  child_pid_ = fork();
-
-  if (child_pid_ < 0) {
-    close(err_rd_pipe);
-    close(err_wr_pipe);
-    throw OSError("fork failed", errno);
-  }
-
-  child_created_ = true;
-
-  if (child_pid_ == 0)
-  {
-    // Close descriptors belonging to parent
-    stream_.close_parent_fds();
-
-    //Close the read end of the error pipe
-    close(err_rd_pipe);
-
-    detail::Child chld(this, err_wr_pipe);
-    chld.execute_child();
-  }
-  else
-  {
-    close (err_wr_pipe);// close child side of pipe, else get stuck in read below
-
-    stream_.close_child_fds();
-
-    try {
-      char err_buf[SP_MAX_ERR_BUF_SIZ] = {0,};
-
-      int read_bytes = util::read_atmost_n(
-                                  err_rd_pipe,
-                                  err_buf,
-                                  SP_MAX_ERR_BUF_SIZ);
-      close(err_rd_pipe);
-
-      if (read_bytes || strlen(err_buf)) {
-        // Call waitpid to reap the child process
-        // waitpid suspends the calling process until the
-        // child terminates.
-        wait();
-
-        // Throw whatever information we have about child failure
-        throw CalledProcessError(err_buf);
-      }
-    } catch (std::exception& exp) {
-      stream_.cleanup_fds();
-      throw exp;
-    }
-
-  }
-}
-
-namespace detail {
-
-  inline void ArgumentDeducer::set_option(executable&& exe) {
-    popen_->exe_name_ = std::move(exe.arg_value);
-  }
-
-  inline void ArgumentDeducer::set_option(cwd&& cwdir) {
-    popen_->cwd_ = std::move(cwdir.arg_value);
-  }
-
-  inline void ArgumentDeducer::set_option(bufsize&& bsiz) {
-    popen_->stream_.bufsiz_ = bsiz.bufsiz;
-  }
-
-  inline void ArgumentDeducer::set_option(environment&& env) {
-    popen_->env_ = std::move(env.env_);
-  }
-
-  inline void ArgumentDeducer::set_option(defer_spawn&& defer) {
-    popen_->defer_process_start_ = defer.defer;
-  }
-
-  inline void ArgumentDeducer::set_option(shell&& sh) {
-    popen_->shell_ = sh.shell_;
-  }
-
-  inline void ArgumentDeducer::set_option(session_leader&& sleader) {
-    popen_->session_leader_ = sleader.leader_;
-  }
-
-  inline void ArgumentDeducer::set_option(input&& inp) {
-    if (inp.rd_ch_ != -1) popen_->stream_.read_from_parent_ = inp.rd_ch_;
-    if (inp.wr_ch_ != -1) popen_->stream_.write_to_child_ = inp.wr_ch_;
-  }
-
-  inline void ArgumentDeducer::set_option(output&& out) {
-    if (out.wr_ch_ != -1) popen_->stream_.write_to_parent_ = out.wr_ch_;
-    if (out.rd_ch_ != -1) popen_->stream_.read_from_child_ = out.rd_ch_;
-  }
-
-  inline void ArgumentDeducer::set_option(error&& err) {
-    if (err.deferred_) {
-      if (popen_->stream_.write_to_parent_) {
-        popen_->stream_.err_write_ = popen_->stream_.write_to_parent_;
-      } else {
-        throw std::runtime_error("Set output before redirecting error to output");
-      }
-    }
-    if (err.wr_ch_ != -1) popen_->stream_.err_write_ = err.wr_ch_;
-    if (err.rd_ch_ != -1) popen_->stream_.err_read_ = err.rd_ch_;
-  }
-
-  inline void ArgumentDeducer::set_option(close_fds&& cfds) {
-    popen_->close_fds_ = cfds.close_all;
-  }
-
-  inline void ArgumentDeducer::set_option(preexec_func&& prefunc) {
-    popen_->preexec_fn_ = std::move(prefunc);
-    popen_->has_preexec_fn_ = true;
-  }
-
-
-  inline void Child::execute_child() {
-    int sys_ret = -1;
-    auto& stream = parent_->stream_;
-
-    try {
-      if (stream.write_to_parent_ == 0)
-        stream.write_to_parent_ = dup(stream.write_to_parent_);
-
-      if (stream.err_write_ == 0 || stream.err_write_ == 1)
-        stream.err_write_ = dup(stream.err_write_);
-
-      // Make the child owned descriptors as the
-      // stdin, stdout and stderr for the child process
-      auto _dup2_ = [](int fd, int to_fd) {
-        if (fd == to_fd) {
-          // dup2 syscall does not reset the
-          // CLOEXEC flag if the descriptors
-          // provided to it are same.
-          // But, we need to reset the CLOEXEC
-          // flag as the provided descriptors
-          // are now going to be the standard
-          // input, output and error
-          util::set_clo_on_exec(fd, false);
-        } else if(fd != -1) {
-          int res = dup2(fd, to_fd);
-          if (res == -1) throw OSError("dup2 failed", errno);
-        }
-      };
-
-      // Create the standard streams
-      _dup2_(stream.read_from_parent_, 0); // Input stream
-      _dup2_(stream.write_to_parent_,  1); // Output stream
-      _dup2_(stream.err_write_,        2); // Error stream
-
-      // Close the duped descriptors
-      if (stream.read_from_parent_ != -1 && stream.read_from_parent_ > 2)
-        close(stream.read_from_parent_);
-
-      if (stream.write_to_parent_ != -1 && stream.write_to_parent_ > 2)
-        close(stream.write_to_parent_);
-
-      if (stream.err_write_ != -1 && stream.err_write_ > 2)
-        close(stream.err_write_);
-
-      // Close all the inherited fd's except the error write pipe
-      if (parent_->close_fds_) {
-        long max_fd = sysconf(_SC_OPEN_MAX);
-        if (max_fd == -1) throw OSError("sysconf failed", errno);
-
-        for (int i = 3; i < max_fd; i++) {
-          if (i == err_wr_pipe_) continue;
-          close(i);
-        }
-      }
-
-      // Change the working directory if provided
-      if (parent_->cwd_.length()) {
-        sys_ret = chdir(parent_->cwd_.c_str());
-        if (sys_ret == -1) throw OSError("chdir failed", errno);
-      }
-
-      if (parent_->has_preexec_fn_) {
-        parent_->preexec_fn_();
-      }
-
-      if (parent_->session_leader_) {
-        sys_ret = setsid();
-        if (sys_ret == -1) throw OSError("setsid failed", errno);
-      }
-
-      // Replace the current image with the executable
-      if (parent_->env_.size()) {
-        for (auto& kv : parent_->env_) {
-          setenv(kv.first.c_str(), kv.second.c_str(), 1);
-        }
-        sys_ret = execvp(parent_->exe_name_.c_str(), parent_->cargv_.data());
-      } else {
-        sys_ret = execvp(parent_->exe_name_.c_str(), parent_->cargv_.data());
-      }
-
-      if (sys_ret == -1) throw OSError("execve failed", errno);
-
-    } catch (const OSError& exp) {
-      // Just write the exception message
-      // TODO: Give back stack trace ?
-      std::string err_msg(exp.what());
-      //ATTN: Can we do something on error here ?
-      util::write_n(err_wr_pipe_, err_msg.c_str(), err_msg.length());
-      throw exp;
-    }
-
-    // Calling application would not get this
-    // exit failure
-    exit (EXIT_FAILURE);
-  }
-
-
-  inline void Streams::setup_comm_channels()
-  {
-    if (write_to_child_ != -1)  input(fdopen(write_to_child_, "wb"));
-    if (read_from_child_ != -1) output(fdopen(read_from_child_, "rb"));
-    if (err_read_ != -1)        error(fdopen(err_read_, "rb"));
-
-    auto handles = {input(), output(), error()};
-
-    for (auto& h : handles) {
-      if (h == nullptr) continue;
-      switch (bufsiz_) {
-      case 0:
-        setvbuf(h, nullptr, _IONBF, BUFSIZ);
-        break;
-      case 1:
-        setvbuf(h, nullptr, _IONBF, BUFSIZ);
-        break;
-      default:
-        setvbuf(h, nullptr, _IOFBF, bufsiz_);
-      };
-    }
-  }
-
-  inline int Communication::send(const char* msg, size_t length)
-  {
-    if (stream_->input() == nullptr) return -1;
-    return std::fwrite(msg, sizeof(char), (int)length, stream_->input());
-  }
-
-  inline int Communication::send(const std::vector<char>& msg)
-  {
-    return send(msg.data(), msg.size());
-  }
-
-  inline std::pair<OutBuffer, ErrBuffer>
-  Communication::communicate(const char* msg, size_t length)
-  {
-    // Optimization from subprocess.py
-    // If we are using one pipe, or no pipe
-    // at all, using select() or threads is unnecessary.
-    auto hndls = {stream_->input(), stream_->output(), stream_->error()};
-    int count = std::count(std::begin(hndls), std::end(hndls), nullptr);
-    const int len_conv = (int)length;
-
-    if (count >= 2) {
-      OutBuffer obuf;
-      ErrBuffer ebuf;
-      if (stream_->input()) {
-        if (msg) {
-          int wbytes = std::fwrite(msg, sizeof(char), (int)length, stream_->input());
-          if (wbytes < len_conv) {
-            if (errno != EPIPE && errno != EINVAL) {
-              throw OSError("fwrite error", errno);
-            }
-          }
-        }
-        // Close the input stream
-        stream_->input_.reset();
-      } else if (stream_->output()) {
-        // Read till EOF
-        // ATTN: This could be blocking, if the process
-        // at the other end screws up, we get screwed as well
-        obuf.add_cap(out_buf_cap_);
-
-        int rbytes = util::read_all(
-                            fileno(stream_->output()),
-                            obuf.buf);
-
-        if (rbytes == -1) {
-          throw OSError("read to obuf failed", errno);
-        }
-
-        obuf.length = rbytes;
-        // Close the output stream
-        stream_->output_.reset();
-
-      } else if (stream_->error()) {
-        // Same screwness applies here as well
-        ebuf.add_cap(err_buf_cap_);
-
-        int rbytes = util::read_atmost_n(
-                                  fileno(stream_->error()),
-                                  ebuf.buf.data(),
-                                  ebuf.buf.size());
-
-        if (rbytes == -1) {
-          throw OSError("read to ebuf failed", errno);
-        }
-
-        ebuf.length = rbytes;
-        // Close the error stream
-        stream_->error_.reset();
-      }
-      return std::make_pair(std::move(obuf), std::move(ebuf));
-    }
-
-    return communicate_threaded(msg, length);
-  }
-
-
-  inline std::pair<OutBuffer, ErrBuffer>
-  Communication::communicate_threaded(const char* msg, size_t length)
-  {
-    OutBuffer obuf;
-    ErrBuffer ebuf;
-    std::future<int> out_fut, err_fut;
-    const int length_conv = (int)length;
-
-    if (stream_->output()) {
-      obuf.add_cap(out_buf_cap_);
-
-      out_fut = std::async(std::launch::async,
-                          [&obuf, this] {
-                            return util::read_all(fileno(this->stream_->output()), obuf.buf);
-                          });
-    }
-    if (stream_->error()) {
-      ebuf.add_cap(err_buf_cap_);
-
-      err_fut = std::async(std::launch::async,
-                          [&ebuf, this] {
-                            return util::read_all(fileno(this->stream_->error()), ebuf.buf);
-                          });
-    }
-    if (stream_->input()) {
-      if (msg) {
-        int wbytes = std::fwrite(msg, sizeof(char), (int)length, stream_->input());
-        if (wbytes < length_conv) {
-          if (errno != EPIPE && errno != EINVAL) {
-            throw OSError("fwrite error", errno);
-          }
-        }
-      }
-      stream_->input_.reset();
-    }
-
-    if (out_fut.valid()) {
-      int res = out_fut.get();
-      if (res != -1) obuf.length = res;
-      else obuf.length = 0;
-    }
-    if (err_fut.valid()) {
-      int res = err_fut.get();
-      if (res != -1) ebuf.length = res;
-      else ebuf.length = 0;
-    }
-
-    return std::make_pair(std::move(obuf), std::move(ebuf));
-  }
-
-}; // end namespace detail
-
-
-
-// Convenience Functions
-//
-//
-namespace detail
-{
-  template<typename F, typename... Args>
-  OutBuffer check_output_impl(F& farg, Args&&... args)
-  {
-    static_assert(!detail::has_type<output, detail::param_pack<Args...> >::value, "output not allowed in args");
-    auto p = Popen(std::forward<F>(farg), std::forward<Args>(args)..., output{PIPE});
-    auto res = p.communicate();
-    auto retcode = p.poll();
-    if (retcode > 0) {
-      throw CalledProcessError("Command failed : Non zero retcode");
-    }
-    return std::move(res.first);
-  }
-
-  template<typename F, typename... Args>
-  int call_impl(F& farg, Args&&... args)
-  {
-    return Popen(std::forward<F>(farg), std::forward<Args>(args)...).wait();
-  }
-
-  static inline void pipeline_impl(std::vector<Popen>& cmds)
-  {
-    /* EMPTY IMPL */
-  }
-
-  template<typename... Args>
-  static inline void pipeline_impl(std::vector<Popen>& cmds,
-                                   const std::string& cmd,
-                                   Args&&... args)
-  {
-    if (cmds.size() == 0) {
-      cmds.emplace_back(cmd, output{PIPE}, defer_spawn{true});
-    } else {
-      cmds.emplace_back(cmd, input{cmds.back().output()}, output{PIPE}, defer_spawn{true});
-    }
-
-    pipeline_impl(cmds, std::forward<Args>(args)...);
-  }
-
-}
-
-/*-----------------------------------------------------------
- *        CONVIENIENCE FUNCTIONS
- *-----------------------------------------------------------
- */
-
-
-/*!
- * Run the command with arguments and wait for it to complete.
- * The parameters passed to the argument are exactly the same
- * one would use for Popen constructors.
- */
-template<typename... Args>
-int call(std::initializer_list<const char*> plist, Args&&... args)
-{
-  return (detail::call_impl(plist, std::forward<Args>(args)...));
-}
-
-template<typename... Args>
-int call(const std::string& arg, Args&&... args)
-{
-  return (detail::call_impl(arg, std::forward<Args>(args)...));
-}
-
-
-/*!
- * Run the command with arguments and wait for it to complete.
- * If the exit code was non-zero it raises a CalledProcessError.
- * The arguments are the same as for the Popen constructor.
- */
-template <typename... Args>
-OutBuffer check_output(std::initializer_list<const char*> plist, Args&&... args)
-{
-  return (detail::check_output_impl(plist, std::forward<Args>(args)...));
-}
-
-template <typename... Args>
-OutBuffer check_output(const std::string& arg, Args&&... args)
-{
-  return (detail::check_output_impl(arg, std::forward<Args>(args)...));
-}
-
-
-/*!
- * An easy way to pipeline easy commands.
- * Provide the commands that needs to be pipelined in the order they
- * would appear in a regular command.
- * It would wait for the last command provided in the pipeline
- * to finish and then return the OutBuffer.
- */
-template<typename... Args>
-// Args expected to be flat commands using string instead of initializer_list
-OutBuffer pipeline(Args&&... args)
-{
-  std::vector<Popen> pcmds;
-  detail::pipeline_impl(pcmds, std::forward<Args>(args)...);
-
-  for (auto& p : pcmds) p.start_process();
-  return (pcmds.back().communicate().first);
-}
-
-};
-
-#endif // __cplusplus
-
-#endif // SUBPROCESS_HPP
diff --git a/launchers/macosx/main.mm b/launchers/macosx/main.mm
deleted file mode 100644
index 54e0b5ee8ce89f7675410ffdb6e9635605cd2670..0000000000000000000000000000000000000000
--- a/launchers/macosx/main.mm
+++ /dev/null
@@ -1,245 +0,0 @@
-#include <functional>
-#include <memory>
-#include <iostream>
-#include <algorithm>
-#include <string>
-#include <list>
-#include <sys/stat.h>
-#include <stdlib.h>
-#include <future>
-#include <vector>
-
-#import <Foundation/Foundation.h>
-#import <Foundation/NSFileManager.h>
-#include <CoreFoundation/CFPreferences.h>
-
-#import <objc/Object.h>
-#import <Cocoa/Cocoa.h>
-#import <AppKit/AppKit.h>
-#import <AppKit/NSApplication.h>
-
-#import "I2PLauncher-Swift.h"
-
-#include "AppDelegate.h"
-#include "RouterTask.h"
-#include "include/fn.h"
-#include "include/portcheck.h"
-#import "SBridge.h"
-#import "Deployer.h"
-#include "logger_c.h"
-
-#ifdef __cplusplus
-#include <string>
-
-#include "include/subprocess.hpp"
-#include "include/strutil.hpp"
-
-#include "Logger.h"
-#include "LoggerWorker.hpp"
-
-using namespace subprocess;
-#endif
-
-#define debug(format, ...) CFShow([NSString stringWithFormat:format, ## __VA_ARGS__]);
-
-
-
-@interface AppDelegate () <NSUserNotificationCenterDelegate, NSApplicationDelegate>
-@end
-
-
-@implementation ExtractMetaInfo : NSObject
-@end
-
-
-@implementation AppDelegate
-
-- (void) awakeFromNib {
-}
-
-
-- (BOOL)userNotificationCenter:(NSUserNotificationCenter *)center
-     shouldPresentNotification:(NSUserNotification *)notification {
-  return YES;
-}
-
-- (void)extractI2PBaseDir:(void(^)(BOOL success, NSError *error))completion
-{
-  self.deployer = [[I2PDeployer alloc] initWithMetaInfo:self.metaInfo];
-  [self.deployer extractI2PBaseDir:completion];
-}
-
-- (void)applicationDidFinishLaunching:(NSNotification *)aNotification {
-  // Init application here
-  
-  // Here we initialize the swift code which would do most of the job from now on.
-  self.swiftRuntime = [[SwiftApplicationDelegate alloc] init];
-  
-  // This setup allows the application to send notifications
-  [[NSUserNotificationCenter defaultUserNotificationCenter] setDelegate:self];
-  
-  
-  // Start with user preferences
-  self.userPreferences = [NSUserDefaults standardUserDefaults];
-  // In case we are unbundled, make us a proper UI application
-  [NSApp setActivationPolicy:NSApplicationActivationPolicyAccessory];
-  [NSApp activateIgnoringOtherApps:YES];
-
-
-#ifdef __cplusplus
-
-  RouterProcessStatus* routerStatus = [[RouterProcessStatus alloc] init];
-  std::string i2pBaseDir(getDefaultBaseDir());
-  MLOG(INFO) << "i2pBaseDir = " << i2pBaseDir.c_str();
-  bool shouldAutoStartRouter = false;
-  
-  // Initialize the Swift environment (the UI components)
-  [self.swiftRuntime applicationDidFinishLaunching];
-  
-  NSInteger portNum = [self.userPreferences integerForKey:@"consolePortCheckNum"];
-  if (port_check((int)portNum) != 0)
-  {
-    NSLog(@"Seems i2p is already running - I will not start the router (port %d is in use..)", (int)portNum);
-    sendUserNotification(@"Found already running router", @"TCP port 7657 seem to be used by another i2p instance.");
-    
-    [routerStatus setRouterStatus: true];
-    [routerStatus setRouterRanByUs: false];
-    shouldAutoStartRouter = false;
-  } else {
-    shouldAutoStartRouter = true;
-  }
-  if (![self.userPreferences boolForKey:@"startRouterAtLogin"] && ![self.userPreferences boolForKey:@"startRouterAtStartup"])
-  {
-    // In this case we don't want to find a running service
-    std::string launchdFile(RealHomeDirectory());
-    launchdFile += "/Library/LaunchAgents/net.i2p.macosx.I2PRouter.plist";
-    
-  }
-
-  NSBundle *launcherBundle = [NSBundle mainBundle];
-  
-  
-  // Helper object to hold statefull path information
-  self.metaInfo = [[ExtractMetaInfo alloc] init];
-  self.metaInfo.i2pBase = [NSString stringWithUTF8String:i2pBaseDir.c_str()];
-  self.metaInfo.javaBinary = [routerStatus getJavaHome];
-  self.metaInfo.jarFile = [launcherBundle pathForResource:@"launcher" ofType:@"jar"];
-  self.metaInfo.zipFile = [launcherBundle pathForResource:@"base" ofType:@"zip"];
-
-  std::string basearg("-Di2p.dir.base=");
-  basearg += i2pBaseDir;
-
-  std::string jarfile("-cp ");
-  jarfile += [self.metaInfo.zipFile UTF8String];
-  
-  // This will trigger the router start after an upgrade.
-  [routerStatus listenForEventWithEventName:@"router_must_upgrade" callbackActionFn:^(NSString* information) {
-    NSLog(@"Got signal, router must be deployed from base.zip");
-    [self extractI2PBaseDir:^(BOOL success, NSError *error) {
-      if (success) {
-        sendUserNotification(@"I2P is done extracting", @"I2P is now installed and ready to run!");
-        NSLog(@"Done extracting I2P");
-        [routerStatus triggerEventWithEn:@"extract_completed" details:@"upgrade complete"];
-      } else {
-        NSLog(@"Error while extracting I2P");
-        [routerStatus triggerEventWithEn:@"extract_errored" details:[NSString stringWithFormat:@"%@", error]];
-      }
-    }];
-  }];
-  
-  NSString *nsI2PBaseStr = [NSString stringWithUTF8String:i2pBaseDir.c_str()];
-
-  [routerStatus listenForEventWithEventName:@"extract_completed" callbackActionFn:^(NSString* information) {
-    NSLog(@"Time to detect I2P version in install directory");
-    [self.swiftRuntime findInstalledI2PVersion];
-  }];
-  
-  //struct stat sb;
-  //if ( !(stat(i2pBaseDir.c_str(), &sb) == 0 && S_ISDIR(sb.st_mode)) )
-  BOOL shouldBeTrueOnReturnDir = YES;
-  if (! [NSFileManager.defaultManager fileExistsAtPath: nsI2PBaseStr isDirectory: &shouldBeTrueOnReturnDir])
-  {
-    // I2P is not extracted.
-    if (shouldBeTrueOnReturnDir) {
-      if (self.enableVerboseLogging) NSLog(@"I2P Directory don't exists!");
-      [routerStatus triggerEventWithEn:@"router_must_upgrade" details:@"deploy needed"];
-    } else {
-      // TODO: handle if i2p path exists but it's not a dir.
-    }
-  } else {
-    // I2P was already found extracted
-    NSString *nsI2pJar = [NSString stringWithFormat:@"%@/lib/i2p.jar", nsI2PBaseStr];
-    
-    // But does I2PBASE/lib/i2p.jar exists?
-    if ([NSFileManager.defaultManager fileExistsAtPath:nsI2pJar]) {
-      NSLog(@"Time to detect I2P version in install directory");
-      [self.swiftRuntime findInstalledI2PVersion];
-    } else {
-      // The directory exists, but not i2p.jar - most likely we're in mid-extraction state.
-      [routerStatus triggerEventWithEn:@"router_must_upgrade" details:@"deploy needed"];
-    }
-  }
-  
-#endif
-}
-
-/**
- *
- * Exit sequence
- *
- **/
-- (void)applicationWillTerminate:(NSNotification *)aNotification {
-  // Tear down here
-  [self.swiftRuntime applicationWillTerminate];
-  NSString *string = @"applicationWillTerminate executed";
-  NSLog(@"%@", string);
-  [[NSUserNotificationCenter defaultUserNotificationCenter] setDelegate:nil];
-}
-
-
-/* wrapper for main */
-- (AppDelegate *)initWithArgc:(int)argc argv:(const char **)argv {
-  return self;
-}
-@end
-
-#ifdef __cplusplus
-namespace {
-  const std::string logDirectory = getDefaultLogDir();
-}
-#endif
-
-int main(int argc, const char **argv)
-{
-  NSApplication *app = [NSApplication sharedApplication];
-
-#ifdef __cplusplus
-  mkdir(logDirectory.c_str(), S_IRUSR | S_IWUSR | S_IXUSR);
-  
-  SharedLogWorker logger("I2PLauncher", logDirectory);
-  MeehLog::initializeLogging(&logger);
-  
-  MLOG(INFO) << "Application is starting up";
-#endif
-  
-  AppDelegate *appDelegate = [[AppDelegate alloc] initWithArgc:argc argv:argv];
-  app.delegate = appDelegate;
-  auto mainBundle = [NSBundle mainBundle];
-  NSString* stringNameBundle = [mainBundle objectForInfoDictionaryKey:(NSString *)kCFBundleNameKey];
-  if ([[NSRunningApplication runningApplicationsWithBundleIdentifier:[mainBundle bundleIdentifier]] count] > 1) {
-    [[NSAlert alertWithMessageText:[NSString stringWithFormat:@"Another copy of %@ is already running.",stringNameBundle]
-                     defaultButton:nil alternateButton:nil otherButton:nil informativeTextWithFormat:@"This copy will now quit."] runModal];
-    
-    [NSApp terminate:nil];
-  }
-#pragma GCC diagnostic push
-#pragma GCC diagnostic ignored "-Wdeprecated-declarations"
-  [NSBundle loadNibNamed:@"I2Launcher" owner:NSApp];
-#pragma GCC diagnostic pop
-  
-  [NSApp run];
-  return 0;
-}
-
-
-
diff --git a/launchers/macosx/osx_create_dmg.sh b/launchers/macosx/osx_create_dmg.sh
deleted file mode 100755
index 501ad7239abb4ee46d5a46e6725f29872540923c..0000000000000000000000000000000000000000
--- a/launchers/macosx/osx_create_dmg.sh
+++ /dev/null
@@ -1,114 +0,0 @@
-#!/usr/bin/env bash
-DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
-
-source $DIR/.sign-secrets
-
-APP_NAME="I2PLauncher"
-VERSION="`/usr/libexec/PlistBuddy -c 'Print I2PRouterVersion' Info.plist`"
-DMG_BACKGROUND_IMG=${BACKGROUND_IMG:-"Background.png"}
-
-APP_EXE="${APP_NAME}.app/Contents/MacOS/${APP_NAME}"
-VOL_NAME="${APP_NAME}-${VERSION}"
-DMG_TMP="${VOL_NAME}-temp.dmg"
-DMG_FINAL="${DMG_NAME:-"I2PMacLauncher-fallback"}.dmg"
-STAGING_DIR="/tmp/mkdmg$$"
-
-# Check the background image DPI and convert it if it isn't 72x72
-_BACKGROUND_IMAGE_DPI_H=`sips -g dpiHeight ${DMG_BACKGROUND_IMG} | grep -Eo '[0-9]+\.[0-9]+'`
-_BACKGROUND_IMAGE_DPI_W=`sips -g dpiWidth ${DMG_BACKGROUND_IMG} | grep -Eo '[0-9]+\.[0-9]+'`
-
-if [ $(echo " $_BACKGROUND_IMAGE_DPI_H != 72.0 " | bc) -eq 1 -o $(echo " $_BACKGROUND_IMAGE_DPI_W != 72.0 " | bc) -eq 1 ]; then
-   echo "WARNING: The background image's DPI is not 72.  This will result in distorted backgrounds on Mac OS X 10.7+."
-   echo "         I will convert it to 72 DPI for you."
-
-   _DMG_BACKGROUND_TMP="${DMG_BACKGROUND_IMG%.*}"_dpifix."${DMG_BACKGROUND_IMG##*.}"
-
-   sips -s dpiWidth 72 -s dpiHeight 72 $DIR/${DMG_BACKGROUND_IMG} --out $DIR/${_DMG_BACKGROUND_TMP}
-
-
-  DMG_BACKGROUND_IMG="${_DMG_BACKGROUND_TMP}"
-fi
-
-# copy over the stuff we want in the final disk image to our staging dir
-mkdir -p "${STAGING_DIR}"
-cp -Rpf "${APP_NAME}.app" "${STAGING_DIR}"
-# ... cp anything else you want in the DMG - documentation, etc.
-
-# figure out how big our DMG needs to be
-#  assumes our contents are at least 1M!
-SIZE=`du -sh "${STAGING_DIR}" | sed 's/\([0-9\.]*\)M\(.*\)/\1/'`
-SIZE=`echo "${SIZE} + 23.0" | bc | awk '{print int($1+0.5)}'`
-
-if [ $? -ne 0 ]; then
-   echo "Error: Cannot compute size of staging dir"
-   exit
-fi
-
-# create the temp DMG file
-hdiutil create -srcfolder "${STAGING_DIR}" -volname "${VOL_NAME}" -fs HFS+ \
-      -fsargs "-c c=64,a=16,e=16" -format UDRW -size ${SIZE}M "$RELEASE_DIR/${DMG_TMP}"
-
-echo "Created DMG: ${DMG_TMP}"
-
-# mount it and save the device
-DEVICE=$(hdiutil attach -readwrite -noverify "$RELEASE_DIR/${DMG_TMP}" | \
-         egrep '^/dev/' | sed 1q | awk '{print $1}')
-
-sleep 2
-
-
-
-# add a link to the Applications dir
-echo "Add link to /Applications"
-cd /Volumes/"${VOL_NAME}"
-ln -sf /Applications Applications
-
-# add a background image
-mkdir -p /Volumes/"${VOL_NAME}"/.background
-cp "$DIR/`basename ${DMG_BACKGROUND_IMG}`" /Volumes/"${VOL_NAME}"/.background/`basename ${DMG_BACKGROUND_IMG}`
-
-cd $RELEASE_DIR
-
-# tell the Finder to resize the window, set the background,
-#  change the icon size, place the icons in the right position, etc.
-echo '
-   tell application "Finder"
-     tell disk "'${VOL_NAME}'"
-           open
-           set current view of container window to icon view
-           set toolbar visible of container window to false
-           set statusbar visible of container window to false
-           set the bounds of container window to {400, 100, 920, 440}
-           set viewOptions to the icon view options of container window
-           set arrangement of viewOptions to not arranged
-           set icon size of viewOptions to 72
-           set background picture of viewOptions to file ".background:'${DMG_BACKGROUND_IMG}'"
-           set position of item "'${APP_NAME}'.app" of container window to {160, 205}
-           set position of item "Applications" of container window to {360, 205}
-           close
-           open
-           update without registering applications
-           delay 2
-     end tell
-   end tell
-' | osascript
-
-sync
-
-# unmount it
-hdiutil detach "${DEVICE}"
-
-# now make the final image a compressed disk image
-echo "Creating compressed image"
-hdiutil convert "$RELEASE_DIR/${DMG_TMP}" -format UDZO -imagekey zlib-level=9 -o "$RELEASE_DIR/${DMG_FINAL}"
-
-codesign --force --deep --sign "${APPLE_CODE_SIGNER_ID}" "$RELEASE_DIR/${DMG_FINAL}"
-
-# clean up
-rm -rf "$RELEASE_DIR/${DMG_TMP}"
-rm -rf "${STAGING_DIR}"
-
-
-echo 'Done.'
-
-exit
diff --git a/launchers/macosx/project/plugins.sbt b/launchers/macosx/project/plugins.sbt
deleted file mode 100644
index 36cfe76603621674a16a8da508fe0c4b3d6476f3..0000000000000000000000000000000000000000
--- a/launchers/macosx/project/plugins.sbt
+++ /dev/null
@@ -1,2 +0,0 @@
-addSbtPlugin("com.eed3si9n" % "sbt-assembly" % "0.14.6")
-addSbtPlugin("com.typesafe.sbt" % "sbt-native-packager" % "1.3.4")
diff --git a/launchers/macosx/requirements.txt b/launchers/macosx/requirements.txt
deleted file mode 100644
index 58c95be88f09e6856ed48ff671a6b327279ac5ae..0000000000000000000000000000000000000000
--- a/launchers/macosx/requirements.txt
+++ /dev/null
@@ -1 +0,0 @@
-builddmg
diff --git a/launchers/macosx/src/main/java/net/i2p/launchers/BaseExtractor.java b/launchers/macosx/src/main/java/net/i2p/launchers/BaseExtractor.java
deleted file mode 100644
index c7009cf1720f1419d16cf55e46f027bd2e7ffd77..0000000000000000000000000000000000000000
--- a/launchers/macosx/src/main/java/net/i2p/launchers/BaseExtractor.java
+++ /dev/null
@@ -1,85 +0,0 @@
-package net.i2p.launchers;
-
-
-import java.io.BufferedInputStream;
-import java.io.BufferedOutputStream;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.nio.file.FileSystem;
-import java.nio.file.FileSystems;
-import java.nio.file.Files;
-import java.nio.file.Path;
-import java.util.Enumeration;
-import java.util.zip.ZipEntry;
-import java.util.zip.ZipFile;
-import java.nio.file.*;
-import java.nio.file.attribute.BasicFileAttributes;
-
-import static java.nio.file.Files.*;
-
-/**
- * As the name suggest, it extracts the base path.
- *
- * @author Meeh
- * @since 0.9.35
- */
-public class BaseExtractor extends EnvCheck {
-
-    public boolean printDebug = false;
-
-    public void unzip(final Path zipFile) {
-        try {
-            String destinationPath = this.baseDirPath;
-            final Path destDir = Files.createDirectories(FileSystems.getDefault().getPath(destinationPath));
-            if (notExists(destDir)) {
-                createDirectories(destDir);
-            }
-
-            try (FileSystem zipFileSystem = FileSystems.newFileSystem(zipFile, null)) {
-                final Path root = zipFileSystem.getRootDirectories().iterator().next();
-
-                walkFileTree(root, new SimpleFileVisitor<Path>() {
-                    @Override
-                    public FileVisitResult visitFile(Path file,
-                                                     BasicFileAttributes attrs) throws IOException {
-                        final Path destFile = Paths.get(destDir.toString(), file.toString());
-                        try {
-                            copy(file, destFile, StandardCopyOption.REPLACE_EXISTING);
-                        } catch (DirectoryNotEmptyException ignore) {
-                        }
-                        return FileVisitResult.CONTINUE;
-                    }
-
-                    @Override
-                    public FileVisitResult preVisitDirectory(Path dir,
-                                                             BasicFileAttributes attrs) throws IOException {
-                        final Path dirToCreate = Paths.get(destDir.toString(), dir.toString());
-                        if (notExists(dirToCreate)) {
-                            createDirectory(dirToCreate);
-                        }
-                        return FileVisitResult.CONTINUE;
-                    }
-                });
-            }
-        } catch (IOException e) {
-            //
-            System.err.println("Exception in extractor!");
-            System.err.println(e.toString());
-        }
-    }
-
-    public BaseExtractor(String[] args) {
-        super(args);
-    }
-
-    public static void main(String[] args) {
-        System.out.println("Starting extraction");
-        BaseExtractor be = new BaseExtractor(args);
-        String debug = System.getProperty("print.debug");
-        if (debug != null) {
-            be.printDebug = true;
-        }
-        be.unzip( FileSystems.getDefault().getPath(System.getProperty("i2p.base.zip")) );
-    }
-}
diff --git a/launchers/macosx/src/main/java/net/i2p/launchers/EnvCheck.java b/launchers/macosx/src/main/java/net/i2p/launchers/EnvCheck.java
deleted file mode 100644
index 3fa214b6f798b636ddcf44f398b1c399fbcc5c8b..0000000000000000000000000000000000000000
--- a/launchers/macosx/src/main/java/net/i2p/launchers/EnvCheck.java
+++ /dev/null
@@ -1,27 +0,0 @@
-package net.i2p.launchers;
-
-/**
- * Both the extractor class and the launcher class needs to be able to verify
- * the environment (variables) to work. This is a base class implementing it.
- *
- * @author Meeh
- * @since 0.9.35
- */
-public class EnvCheck {
-
-    protected String baseDirPath = null;
-
-    protected boolean isBaseDirectorySet() {
-        baseDirPath = System.getProperty("i2p.base.dir");
-        if (baseDirPath == null) {
-            baseDirPath = System.getenv("I2PBASE");
-        }
-        return (baseDirPath != null);
-    }
-
-    public EnvCheck(String[] args) {
-        if (!isBaseDirectorySet()) {
-            throw new RuntimeException("Can't detect I2P's base directory!");
-        }
-    }
-}
diff --git a/launchers/macosx/src/main/java/net/i2p/launchers/SimpleOSXLauncher.java b/launchers/macosx/src/main/java/net/i2p/launchers/SimpleOSXLauncher.java
deleted file mode 100644
index 3897a32f0e7c79a48d3987d607e136553dff6b4e..0000000000000000000000000000000000000000
--- a/launchers/macosx/src/main/java/net/i2p/launchers/SimpleOSXLauncher.java
+++ /dev/null
@@ -1,25 +0,0 @@
-package net.i2p.launchers;
-
-import net.i2p.router.Router;
-
-public class SimpleOSXLauncher extends EnvCheck {
-
-    protected Router i2pRouter;
-
-    /**
-     *
-     * This is bairly a abstraction layer for the Router.
-     * Why? I suspect we will add some spesific osx launcher code at startup
-     * in the jvm somewhere, and this seem like a nice place to not make a mess everywhere.
-     *
-     * @author Meeh
-     * @since 0.9.35
-     */
-    public SimpleOSXLauncher(String[] args) {
-        super(args);
-        i2pRouter = new Router();
-    }
-    public static void main(String[] args) {
-        new SimpleOSXLauncher(args);
-    }
-}
diff --git a/launchers/macosx/version.h.tpl b/launchers/macosx/version.h.tpl
deleted file mode 100644
index 282589a72a6ee1101df6c04f61aa370363fc361f..0000000000000000000000000000000000000000
--- a/launchers/macosx/version.h.tpl
+++ /dev/null
@@ -1,22 +0,0 @@
-//
-//  version.h
-//  I2PLauncher
-//
-//  Created by Mikal Villa on 28/09/2018.
-//  Copyright © 2018 The I2P Project. All rights reserved.
-//
-
-#ifndef version_h
-#define version_h
-
-
-#define DEF_I2P_VERSION "VERSION_REPLACED_BY_XCODE_BUILD_SCRIPT"
-#define NSDEF_I2P_VERSION @"VERSION_REPLACED_BY_XCODE_BUILD_SCRIPT"
-#define DEF_BUILD_INFO "BUILD_INFO_REPLACED_BY_XCODE_BUILD_SCRIPT"
-#define APPDOMAIN "net.i2p.bootstrap-macosx"
-#define NSAPPDOMAIN @APPDOMAIN
-#define CFAPPDOMAIN CFSTR(APPDOMAIN)
-#define APP_IDSTR @"I2P Launcher"
-
-
-#endif /* version_h */
diff --git a/launchers/project/IconHelper.scala b/launchers/project/IconHelper.scala
deleted file mode 100644
index 2cc82bba72bf738e9ae091d6cb1b052ae960e5d0..0000000000000000000000000000000000000000
--- a/launchers/project/IconHelper.scala
+++ /dev/null
@@ -1,52 +0,0 @@
-package root
-
-import sbt._, Keys._
-import java.io.File
-
-/**
-  *
-  * This is an autoplugin for sbt which makes it possible to
-  * create an correctly made icns file for usage as app icon.
-  *
-  * The task "convertToICNSTask" should become available for us to define
-  * because of this class.
-  *
-  * sips is only a command on Mac OS X afaik so this would probably need to be
-  * built on a mac.
-  *
-  * @since 0.9.35
-  */
-object IconHelper extends AutoPlugin {
-
-  def convertToICNS(inF: File, outF: File) {
-    if (inF.ext == "icns") {
-      IO.copyFile(inF, outF, preserveLastModified = true)
-    } else {
-      import sys.process._
-      val lines       = Seq("sips", "-g", "pixelHeight", "-g", "pixelWidth", inF.getPath).lines
-      val PixelWidth  = "\\s+pixelWidth: (\\d+)".r
-      val PixelHeight = "\\s+pixelHeight: (\\d+)".r
-      val srcWidth    = lines.collect { case PixelWidth (s) => s.toInt } .head
-      val srcHeight   = lines.collect { case PixelHeight(s) => s.toInt } .head
-      val supported   = IndexedSeq(16, 32, 48, 128, 256, 512)
-      val srcSize     = math.min(512, math.max(srcWidth, srcHeight))
-      val tgtSize     = supported(supported.indexWhere(_ >= srcSize))
-      val args0       = Seq(inF.getPath, "--out", outF.getPath)
-      val args1       = if (tgtSize != srcWidth || tgtSize != srcHeight) {
-        Seq("-z", tgtSize.toString, tgtSize.toString)
-      } else {
-        Seq.empty
-      }
-      val args        = Seq("sips", "-s", "format", "icns") ++ args1 ++ args0
-      args.!!
-    }
-  }
-
-  object autoImport {
-    val convertToICNSTask = taskKey[Unit]("Converts an image to Mac OS X's ICNS icon format")
-  }
-
-  import autoImport._
-
-}
-
diff --git a/launchers/project/build.properties b/launchers/project/build.properties
deleted file mode 100644
index 05313438a19deabea36f9de855cdfa6032a7c3f3..0000000000000000000000000000000000000000
--- a/launchers/project/build.properties
+++ /dev/null
@@ -1 +0,0 @@
-sbt.version=1.1.2
diff --git a/launchers/project/plugins.sbt b/launchers/project/plugins.sbt
deleted file mode 100644
index 42c612c7abe96e7b218f6db0d5872165e284fe4e..0000000000000000000000000000000000000000
--- a/launchers/project/plugins.sbt
+++ /dev/null
@@ -1,4 +0,0 @@
-addSbtPlugin("com.jsuereth" % "sbt-pgp" % "1.1.1")
-addSbtPlugin("com.oradian.sbt" % "sbt-sh" % "0.3.0")
-addSbtPlugin("com.eed3si9n" % "sbt-assembly" % "0.14.6")
-addSbtPlugin("com.typesafe.sbt" % "sbt-native-packager" % "1.3.4")
diff --git a/launchers/sbt b/launchers/sbt
deleted file mode 100755
index 94496df8de50950ea4071a3905900a93cc696881..0000000000000000000000000000000000000000
--- a/launchers/sbt
+++ /dev/null
@@ -1,579 +0,0 @@
-#!/usr/bin/env bash
-#
-# A more capable sbt runner, coincidentally also called sbt.
-# Author: Paul Phillips <paulp@improving.org>
-# https://github.com/paulp/sbt-extras
-
-set -o pipefail
-
-declare -r sbt_release_version="0.13.16"
-declare -r sbt_unreleased_version="0.13.16"
-
-declare -r latest_213="2.13.0-M2"
-declare -r latest_212="2.12.4"
-declare -r latest_211="2.11.12"
-declare -r latest_210="2.10.7"
-declare -r latest_29="2.9.3"
-declare -r latest_28="2.8.2"
-
-declare -r buildProps="project/build.properties"
-
-declare -r sbt_launch_ivy_release_repo="http://repo.typesafe.com/typesafe/ivy-releases"
-declare -r sbt_launch_ivy_snapshot_repo="https://repo.scala-sbt.org/scalasbt/ivy-snapshots"
-declare -r sbt_launch_mvn_release_repo="http://repo.scala-sbt.org/scalasbt/maven-releases"
-declare -r sbt_launch_mvn_snapshot_repo="http://repo.scala-sbt.org/scalasbt/maven-snapshots"
-
-declare -r default_jvm_opts_common="-Xms512m -Xmx1536m -Xss2m"
-declare -r noshare_opts="-Dsbt.global.base=project/.sbtboot -Dsbt.boot.directory=project/.boot -Dsbt.ivy.home=project/.ivy"
-
-declare sbt_jar sbt_dir sbt_create sbt_version sbt_script sbt_new
-declare sbt_explicit_version
-declare verbose noshare batch trace_level
-declare debugUs
-
-declare java_cmd="java"
-declare sbt_launch_dir="$HOME/.sbt/launchers"
-declare sbt_launch_repo
-
-# pull -J and -D options to give to java.
-declare -a java_args scalac_args sbt_commands residual_args
-
-# args to jvm/sbt via files or environment variables
-declare -a extra_jvm_opts extra_sbt_opts
-
-echoerr () { echo >&2 "$@"; }
-vlog ()    { [[ -n "$verbose" ]] && echoerr "$@"; }
-die ()     { echo "Aborting: $@" ; exit 1; }
-
-setTrapExit () {
-  # save stty and trap exit, to ensure echo is re-enabled if we are interrupted.
-  export SBT_STTY="$(stty -g 2>/dev/null)"
-
-  # restore stty settings (echo in particular)
-  onSbtRunnerExit() {
-    [ -t 0 ] || return
-    vlog ""
-    vlog "restoring stty: $SBT_STTY"
-    stty "$SBT_STTY"
-  }
-
-  vlog "saving stty: $SBT_STTY"
-  trap onSbtRunnerExit EXIT
-}
-
-# this seems to cover the bases on OSX, and someone will
-# have to tell me about the others.
-get_script_path () {
-  local path="$1"
-  [[ -L "$path" ]] || { echo "$path" ; return; }
-
-  local target="$(readlink "$path")"
-  if [[ "${target:0:1}" == "/" ]]; then
-    echo "$target"
-  else
-    echo "${path%/*}/$target"
-  fi
-}
-
-declare -r script_path="$(get_script_path "$BASH_SOURCE")"
-declare -r script_name="${script_path##*/}"
-
-init_default_option_file () {
-  local overriding_var="${!1}"
-  local default_file="$2"
-  if [[ ! -r "$default_file" && "$overriding_var" =~ ^@(.*)$ ]]; then
-    local envvar_file="${BASH_REMATCH[1]}"
-    if [[ -r "$envvar_file" ]]; then
-      default_file="$envvar_file"
-    fi
-  fi
-  echo "$default_file"
-}
-
-declare sbt_opts_file="$(init_default_option_file SBT_OPTS .sbtopts)"
-declare jvm_opts_file="$(init_default_option_file JVM_OPTS .jvmopts)"
-
-build_props_sbt () {
-  [[ -r "$buildProps" ]] && \
-    grep '^sbt\.version' "$buildProps" | tr '=\r' ' ' | awk '{ print $2; }'
-}
-
-update_build_props_sbt () {
-  local ver="$1"
-  local old="$(build_props_sbt)"
-
-  [[ -r "$buildProps" ]] && [[ "$ver" != "$old" ]] && {
-    perl -pi -e "s/^sbt\.version\b.*\$/sbt.version=${ver}/" "$buildProps"
-    grep -q '^sbt.version[ =]' "$buildProps" || printf "\nsbt.version=%s\n" "$ver" >> "$buildProps"
-
-    vlog "!!!"
-    vlog "!!! Updated file $buildProps setting sbt.version to: $ver"
-    vlog "!!! Previous value was: $old"
-    vlog "!!!"
-  }
-}
-
-set_sbt_version () {
-  sbt_version="${sbt_explicit_version:-$(build_props_sbt)}"
-  [[ -n "$sbt_version" ]] || sbt_version=$sbt_release_version
-  export sbt_version
-}
-
-url_base () {
-  local version="$1"
-
-  case "$version" in
-        0.7.*) echo "http://simple-build-tool.googlecode.com" ;;
-      0.10.* ) echo "$sbt_launch_ivy_release_repo" ;;
-    0.11.[12]) echo "$sbt_launch_ivy_release_repo" ;;
-    0.*-[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]-[0-9][0-9][0-9][0-9][0-9][0-9]) # ie "*-yyyymmdd-hhMMss"
-               echo "$sbt_launch_ivy_snapshot_repo" ;;
-          0.*) echo "$sbt_launch_ivy_release_repo" ;;
-    *-[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]-[0-9][0-9][0-9][0-9][0-9][0-9]) # ie "*-yyyymmdd-hhMMss"
-               echo "$sbt_launch_mvn_snapshot_repo" ;;
-            *) echo "$sbt_launch_mvn_release_repo" ;;
-  esac
-}
-
-make_url () {
-  local version="$1"
-
-  local base="${sbt_launch_repo:-$(url_base "$version")}"
-
-  case "$version" in
-        0.7.*) echo "$base/files/sbt-launch-0.7.7.jar" ;;
-      0.10.* ) echo "$base/org.scala-tools.sbt/sbt-launch/$version/sbt-launch.jar" ;;
-    0.11.[12]) echo "$base/org.scala-tools.sbt/sbt-launch/$version/sbt-launch.jar" ;;
-          0.*) echo "$base/org.scala-sbt/sbt-launch/$version/sbt-launch.jar" ;;
-            *) echo "$base/org/scala-sbt/sbt-launch/$version/sbt-launch.jar" ;;
-  esac
-}
-
-addJava ()     { vlog "[addJava] arg = '$1'"   ;     java_args+=("$1"); }
-addSbt ()      { vlog "[addSbt] arg = '$1'"    ;  sbt_commands+=("$1"); }
-addScalac ()   { vlog "[addScalac] arg = '$1'" ;   scalac_args+=("$1"); }
-addResidual () { vlog "[residual] arg = '$1'"  ; residual_args+=("$1"); }
-
-addResolver () { addSbt "set resolvers += $1"; }
-addDebugger () { addJava "-Xdebug" ; addJava "-Xrunjdwp:transport=dt_socket,server=y,suspend=n,address=$1"; }
-setThisBuild () {
-  vlog "[addBuild] args = '$@'"
-  local key="$1" && shift
-  addSbt "set $key in ThisBuild := $@"
-}
-setScalaVersion () {
-  [[ "$1" == *"-SNAPSHOT" ]] && addResolver 'Resolver.sonatypeRepo("snapshots")'
-  addSbt "++ $1"
-}
-setJavaHome () {
-  java_cmd="$1/bin/java"
-  setThisBuild javaHome "_root_.scala.Some(file(\"$1\"))"
-  export JAVA_HOME="$1"
-  export JDK_HOME="$1"
-  export PATH="$JAVA_HOME/bin:$PATH"
-}
-
-getJavaVersion() { "$1" -version 2>&1 | grep -E -e '(java|openjdk) version' | awk '{ print $3 }' | tr -d \"; }
-
-checkJava() {
-  # Warn if there is a Java version mismatch between PATH and JAVA_HOME/JDK_HOME
-
-  [[ -n "$JAVA_HOME" && -e "$JAVA_HOME/bin/java"     ]] && java="$JAVA_HOME/bin/java"
-  [[ -n "$JDK_HOME"  && -e "$JDK_HOME/lib/tools.jar" ]] && java="$JDK_HOME/bin/java"
-
-  if [[ -n "$java" ]]; then
-    pathJavaVersion=$(getJavaVersion java)
-    homeJavaVersion=$(getJavaVersion "$java")
-    if [[ "$pathJavaVersion" != "$homeJavaVersion" ]]; then
-      echoerr "Warning: Java version mismatch between PATH and JAVA_HOME/JDK_HOME, sbt will use the one in PATH"
-      echoerr "  Either: fix your PATH, remove JAVA_HOME/JDK_HOME or use -java-home"
-      echoerr "  java version from PATH:               $pathJavaVersion"
-      echoerr "  java version from JAVA_HOME/JDK_HOME: $homeJavaVersion"
-    fi
-  fi
-}
-
-java_version () {
-  local version=$(getJavaVersion "$java_cmd")
-  vlog "Detected Java version: $version"
-  echo "${version:2:1}"
-}
-
-# MaxPermSize critical on pre-8 JVMs but incurs noisy warning on 8+
-default_jvm_opts () {
-  local v="$(java_version)"
-  if [[ $v -ge 8 ]]; then
-    echo "$default_jvm_opts_common"
-  else
-    echo "-XX:MaxPermSize=384m $default_jvm_opts_common"
-  fi
-}
-
-build_props_scala () {
-  if [[ -r "$buildProps" ]]; then
-    versionLine="$(grep '^build.scala.versions' "$buildProps")"
-    versionString="${versionLine##build.scala.versions=}"
-    echo "${versionString%% .*}"
-  fi
-}
-
-execRunner () {
-  # print the arguments one to a line, quoting any containing spaces
-  vlog "# Executing command line:" && {
-    for arg; do
-      if [[ -n "$arg" ]]; then
-        if printf "%s\n" "$arg" | grep -q ' '; then
-          printf >&2 "\"%s\"\n" "$arg"
-        else
-          printf >&2 "%s\n" "$arg"
-        fi
-      fi
-    done
-    vlog ""
-  }
-
-  setTrapExit
-
-  if [[ -n "$batch" ]]; then
-    "$@" < /dev/null
-  else
-    "$@"
-  fi
-}
-
-jar_url ()  { make_url "$1"; }
-
-is_cygwin () [[ "$(uname -a)" == "CYGWIN"* ]]
-
-jar_file () {
-  is_cygwin \
-  && echo "$(cygpath -w $sbt_launch_dir/"$1"/sbt-launch.jar)" \
-  || echo "$sbt_launch_dir/$1/sbt-launch.jar"
-}
-
-download_url () {
-  local url="$1"
-  local jar="$2"
-
-  echoerr "Downloading sbt launcher for $sbt_version:"
-  echoerr "  From  $url"
-  echoerr "    To  $jar"
-
-  mkdir -p "${jar%/*}" && {
-    if command -v curl > /dev/null 2>&1; then
-      curl --fail --silent --location "$url" --output "$jar"
-    elif command -v wget > /dev/null 2>&1; then
-      wget -q -O "$jar" "$url"
-    fi
-  } && [[ -r "$jar" ]]
-}
-
-acquire_sbt_jar () {
-  {
-    sbt_jar="$(jar_file "$sbt_version")"
-    [[ -r "$sbt_jar" ]]
-  } || {
-    sbt_jar="$HOME/.ivy2/local/org.scala-sbt/sbt-launch/$sbt_version/jars/sbt-launch.jar"
-    [[ -r "$sbt_jar" ]]
-  } || {
-    sbt_jar="$(jar_file "$sbt_version")"
-    download_url "$(make_url "$sbt_version")" "$sbt_jar"
-  }
-}
-
-usage () {
-  set_sbt_version
-  cat <<EOM
-Usage: $script_name [options]
-
-Note that options which are passed along to sbt begin with -- whereas
-options to this runner use a single dash. Any sbt command can be scheduled
-to run first by prefixing the command with --, so --warn, --error and so on
-are not special.
-
-Output filtering: if there is a file in the home directory called .sbtignore
-and this is not an interactive sbt session, the file is treated as a list of
-bash regular expressions. Output lines which match any regex are not echoed.
-One can see exactly which lines would have been suppressed by starting this
-runner with the -x option.
-
-  -h | -help         print this message
-  -v                 verbose operation (this runner is chattier)
-  -d, -w, -q         aliases for --debug, --warn, --error (q means quiet)
-  -x                 debug this script
-  -trace <level>     display stack traces with a max of <level> frames (default: -1, traces suppressed)
-  -debug-inc         enable debugging log for the incremental compiler
-  -no-colors         disable ANSI color codes
-  -sbt-create        start sbt even if current directory contains no sbt project
-  -sbt-dir   <path>  path to global settings/plugins directory (default: ~/.sbt/<version>)
-  -sbt-boot  <path>  path to shared boot directory (default: ~/.sbt/boot in 0.11+)
-  -ivy       <path>  path to local Ivy repository (default: ~/.ivy2)
-  -no-share          use all local caches; no sharing
-  -offline           put sbt in offline mode
-  -jvm-debug <port>  Turn on JVM debugging, open at the given port.
-  -batch             Disable interactive mode
-  -prompt <expr>     Set the sbt prompt; in expr, 's' is the State and 'e' is Extracted
-  -script <file>     Run the specified file as a scala script
-
-  # sbt version (default: sbt.version from $buildProps if present, otherwise $sbt_release_version)
-  -sbt-force-latest         force the use of the latest release of sbt: $sbt_release_version
-  -sbt-version  <version>   use the specified version of sbt (default: $sbt_release_version)
-  -sbt-dev                  use the latest pre-release version of sbt: $sbt_unreleased_version
-  -sbt-jar      <path>      use the specified jar as the sbt launcher
-  -sbt-launch-dir <path>    directory to hold sbt launchers (default: $sbt_launch_dir)
-  -sbt-launch-repo <url>    repo url for downloading sbt launcher jar (default: $(url_base "$sbt_version"))
-
-  # scala version (default: as chosen by sbt)
-  -28                       use $latest_28
-  -29                       use $latest_29
-  -210                      use $latest_210
-  -211                      use $latest_211
-  -212                      use $latest_212
-  -213                      use $latest_213
-  -scala-home <path>        use the scala build at the specified directory
-  -scala-version <version>  use the specified version of scala
-  -binary-version <version> use the specified scala version when searching for dependencies
-
-  # java version (default: java from PATH, currently $(java -version 2>&1 | grep version))
-  -java-home <path>         alternate JAVA_HOME
-
-  # passing options to the jvm - note it does NOT use JAVA_OPTS due to pollution
-  # The default set is used if JVM_OPTS is unset and no -jvm-opts file is found
-  <default>        $(default_jvm_opts)
-  JVM_OPTS         environment variable holding either the jvm args directly, or
-                   the reference to a file containing jvm args if given path is prepended by '@' (e.g. '@/etc/jvmopts')
-                   Note: "@"-file is overridden by local '.jvmopts' or '-jvm-opts' argument.
-  -jvm-opts <path> file containing jvm args (if not given, .jvmopts in project root is used if present)
-  -Dkey=val        pass -Dkey=val directly to the jvm
-  -J-X             pass option -X directly to the jvm (-J is stripped)
-
-  # passing options to sbt, OR to this runner
-  SBT_OPTS         environment variable holding either the sbt args directly, or
-                   the reference to a file containing sbt args if given path is prepended by '@' (e.g. '@/etc/sbtopts')
-                   Note: "@"-file is overridden by local '.sbtopts' or '-sbt-opts' argument.
-  -sbt-opts <path> file containing sbt args (if not given, .sbtopts in project root is used if present)
-  -S-X             add -X to sbt's scalacOptions (-S is stripped)
-EOM
-}
-
-process_args () {
-  require_arg () {
-    local type="$1"
-    local opt="$2"
-    local arg="$3"
-
-    if [[ -z "$arg" ]] || [[ "${arg:0:1}" == "-" ]]; then
-      die "$opt requires <$type> argument"
-    fi
-  }
-  while [[ $# -gt 0 ]]; do
-    case "$1" in
-          -h|-help) usage; exit 0 ;;
-                -v) verbose=true && shift ;;
-                -d) addSbt "--debug" && shift ;;
-                -w) addSbt "--warn"  && shift ;;
-                -q) addSbt "--error" && shift ;;
-                -x) debugUs=true && shift ;;
-            -trace) require_arg integer "$1" "$2" && trace_level="$2" && shift 2 ;;
-              -ivy) require_arg path "$1" "$2" && addJava "-Dsbt.ivy.home=$2" && shift 2 ;;
-        -no-colors) addJava "-Dsbt.log.noformat=true" && shift ;;
-         -no-share) noshare=true && shift ;;
-         -sbt-boot) require_arg path "$1" "$2" && addJava "-Dsbt.boot.directory=$2" && shift 2 ;;
-          -sbt-dir) require_arg path "$1" "$2" && sbt_dir="$2" && shift 2 ;;
-        -debug-inc) addJava "-Dxsbt.inc.debug=true" && shift ;;
-          -offline) addSbt "set offline in Global := true" && shift ;;
-        -jvm-debug) require_arg port "$1" "$2" && addDebugger "$2" && shift 2 ;;
-            -batch) batch=true && shift ;;
-           -prompt) require_arg "expr" "$1" "$2" && setThisBuild shellPrompt "(s => { val e = Project.extract(s) ; $2 })" && shift 2 ;;
-           -script) require_arg file "$1" "$2" && sbt_script="$2" && addJava "-Dsbt.main.class=sbt.ScriptMain" && shift 2 ;;
-
-       -sbt-create) sbt_create=true && shift ;;
-          -sbt-jar) require_arg path "$1" "$2" && sbt_jar="$2" && shift 2 ;;
-      -sbt-version) require_arg version "$1" "$2" && sbt_explicit_version="$2" && shift 2 ;;
- -sbt-force-latest) sbt_explicit_version="$sbt_release_version" && shift ;;
-          -sbt-dev) sbt_explicit_version="$sbt_unreleased_version" && shift ;;
-   -sbt-launch-dir) require_arg path "$1" "$2" && sbt_launch_dir="$2" && shift 2 ;;
-  -sbt-launch-repo) require_arg path "$1" "$2" && sbt_launch_repo="$2" && shift 2 ;;
-    -scala-version) require_arg version "$1" "$2" && setScalaVersion "$2" && shift 2 ;;
-   -binary-version) require_arg version "$1" "$2" && setThisBuild scalaBinaryVersion "\"$2\"" && shift 2 ;;
-       -scala-home) require_arg path "$1" "$2" && setThisBuild scalaHome "_root_.scala.Some(file(\"$2\"))" && shift 2 ;;
-        -java-home) require_arg path "$1" "$2" && setJavaHome "$2" && shift 2 ;;
-         -sbt-opts) require_arg path "$1" "$2" && sbt_opts_file="$2" && shift 2 ;;
-         -jvm-opts) require_arg path "$1" "$2" && jvm_opts_file="$2" && shift 2 ;;
-
-               -D*) addJava "$1" && shift ;;
-               -J*) addJava "${1:2}" && shift ;;
-               -S*) addScalac "${1:2}" && shift ;;
-               -28) setScalaVersion "$latest_28" && shift ;;
-               -29) setScalaVersion "$latest_29" && shift ;;
-              -210) setScalaVersion "$latest_210" && shift ;;
-              -211) setScalaVersion "$latest_211" && shift ;;
-              -212) setScalaVersion "$latest_212" && shift ;;
-              -213) setScalaVersion "$latest_213" && shift ;;
-               new) sbt_new=true && : ${sbt_explicit_version:=$sbt_release_version} && addResidual "$1" && shift ;;
-                 *) addResidual "$1" && shift ;;
-    esac
-  done
-}
-
-# process the direct command line arguments
-process_args "$@"
-
-# skip #-styled comments and blank lines
-readConfigFile() {
-  local end=false
-  until $end; do
-    read || end=true
-    [[ $REPLY =~ ^# ]] || [[ -z $REPLY ]] || echo "$REPLY"
-  done < "$1"
-}
-
-# if there are file/environment sbt_opts, process again so we
-# can supply args to this runner
-if [[ -r "$sbt_opts_file" ]]; then
-  vlog "Using sbt options defined in file $sbt_opts_file"
-  while read opt; do extra_sbt_opts+=("$opt"); done < <(readConfigFile "$sbt_opts_file")
-elif [[ -n "$SBT_OPTS" && ! ("$SBT_OPTS" =~ ^@.*) ]]; then
-  vlog "Using sbt options defined in variable \$SBT_OPTS"
-  extra_sbt_opts=( $SBT_OPTS )
-else
-  vlog "No extra sbt options have been defined"
-fi
-
-[[ -n "${extra_sbt_opts[*]}" ]] && process_args "${extra_sbt_opts[@]}"
-
-# reset "$@" to the residual args
-set -- "${residual_args[@]}"
-argumentCount=$#
-
-# set sbt version
-set_sbt_version
-
-checkJava
-
-# only exists in 0.12+
-setTraceLevel() {
-  case "$sbt_version" in
-    "0.7."* | "0.10."* | "0.11."* ) echoerr "Cannot set trace level in sbt version $sbt_version" ;;
-                                 *) setThisBuild traceLevel $trace_level ;;
-  esac
-}
-
-# set scalacOptions if we were given any -S opts
-[[ ${#scalac_args[@]} -eq 0 ]] || addSbt "set scalacOptions in ThisBuild += \"${scalac_args[@]}\""
-
-# Update build.properties on disk to set explicit version - sbt gives us no choice
-[[ -n "$sbt_explicit_version" && -z "$sbt_new" ]] && update_build_props_sbt "$sbt_explicit_version"
-vlog "Detected sbt version $sbt_version"
-
-if [[ -n "$sbt_script" ]]; then
-  residual_args=( $sbt_script ${residual_args[@]} )
-else
-  # no args - alert them there's stuff in here
-  (( argumentCount > 0 )) || {
-    vlog "Starting $script_name: invoke with -help for other options"
-    residual_args=( shell )
-  }
-fi
-
-# verify this is an sbt dir, -create was given or user attempts to run a scala script
-[[ -r ./build.sbt || -d ./project || -n "$sbt_create" || -n "$sbt_script" || -n "$sbt_new" ]] || {
-  cat <<EOM
-$(pwd) doesn't appear to be an sbt project.
-If you want to start sbt anyway, run:
-  $0 -sbt-create
-
-EOM
-  exit 1
-}
-
-# pick up completion if present; todo
-[[ -r .sbt_completion.sh ]] && source .sbt_completion.sh
-
-# directory to store sbt launchers
-[[ -d "$sbt_launch_dir" ]] || mkdir -p "$sbt_launch_dir"
-[[ -w "$sbt_launch_dir" ]] || sbt_launch_dir="$(mktemp -d -t sbt_extras_launchers.XXXXXX)"
-
-# no jar? download it.
-[[ -r "$sbt_jar" ]] || acquire_sbt_jar || {
-  # still no jar? uh-oh.
-  echo "Download failed. Obtain the jar manually and place it at $sbt_jar"
-  exit 1
-}
-
-if [[ -n "$noshare" ]]; then
-  for opt in ${noshare_opts}; do
-    addJava "$opt"
-  done
-else
-  case "$sbt_version" in
-    "0.7."* | "0.10."* | "0.11."* | "0.12."* )
-      [[ -n "$sbt_dir" ]] || {
-        sbt_dir="$HOME/.sbt/$sbt_version"
-        vlog "Using $sbt_dir as sbt dir, -sbt-dir to override."
-      }
-    ;;
-  esac
-
-  if [[ -n "$sbt_dir" ]]; then
-    addJava "-Dsbt.global.base=$sbt_dir"
-  fi
-fi
-
-if [[ -r "$jvm_opts_file" ]]; then
-  vlog "Using jvm options defined in file $jvm_opts_file"
-  while read opt; do extra_jvm_opts+=("$opt"); done < <(readConfigFile "$jvm_opts_file")
-elif [[ -n "$JVM_OPTS" && ! ("$JVM_OPTS" =~ ^@.*) ]]; then
-  vlog "Using jvm options defined in \$JVM_OPTS variable"
-  extra_jvm_opts=( $JVM_OPTS )
-else
-  vlog "Using default jvm options"
-  extra_jvm_opts=( $(default_jvm_opts) )
-fi
-
-# traceLevel is 0.12+
-[[ -n "$trace_level" ]] && setTraceLevel
-
-main () {
-  execRunner "$java_cmd" \
-    "${extra_jvm_opts[@]}" \
-    "${java_args[@]}" \
-    -jar "$sbt_jar" \
-    "${sbt_commands[@]}" \
-    "${residual_args[@]}"
-}
-
-# sbt inserts this string on certain lines when formatting is enabled:
-#   val OverwriteLine = "\r\u001BM\u001B[2K"
-# ...in order not to spam the console with a million "Resolving" lines.
-# Unfortunately that makes it that much harder to work with when
-# we're not going to print those lines anyway. We strip that bit of
-# line noise, but leave the other codes to preserve color.
-mainFiltered () {
-  local ansiOverwrite='\r\x1BM\x1B[2K'
-  local excludeRegex=$(egrep -v '^#|^$' ~/.sbtignore | paste -sd'|' -)
-
-  echoLine () {
-    local line="$1"
-    local line1="$(echo "$line" | sed 's/\r\x1BM\x1B\[2K//g')"       # This strips the OverwriteLine code.
-    local line2="$(echo "$line1" | sed 's/\x1B\[[0-9;]*[JKmsu]//g')" # This strips all codes - we test regexes against this.
-
-    if [[ $line2 =~ $excludeRegex ]]; then
-      [[ -n $debugUs ]] && echo "[X] $line1"
-    else
-      [[ -n $debugUs ]] && echo "    $line1" || echo "$line1"
-    fi
-  }
-
-  echoLine "Starting sbt with output filtering enabled."
-  main | while read -r line; do echoLine "$line"; done
-}
-
-# Only filter if there's a filter file and we don't see a known interactive command.
-# Obviously this is super ad hoc but I don't know how to improve on it. Testing whether
-# stdin is a terminal is useless because most of my use cases for this filtering are
-# exactly when I'm at a terminal, running sbt non-interactively.
-shouldFilter () { [[ -f ~/.sbtignore ]] && ! egrep -q '\b(shell|console|consoleProject)\b' <<<"${residual_args[@]}"; }
-
-# run sbt
-if shouldFilter; then mainFiltered; else main; fi