diff --git a/LICENSE.md b/LICENSE.GPL2.md
similarity index 100%
rename from LICENSE.md
rename to LICENSE.GPL2.md
diff --git a/LICENSE.GPL3.md b/LICENSE.GPL3.md
new file mode 100644
index 0000000000000000000000000000000000000000..44c0c9c2a6ed93eb0c089d0ddfde37e1b56e3fde
--- /dev/null
+++ b/LICENSE.GPL3.md
@@ -0,0 +1,294 @@
+### GNU GENERAL PUBLIC LICENSE
+
+Version 2, June 1991
+
+    Copyright (C) 1989, 1991 Free Software Foundation, Inc.  
+    51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA
+
+    Everyone is permitted to copy and distribute verbatim copies
+    of this license document, but changing it is not allowed.
+
+### Preamble
+
+The licenses for most software are designed to take away your freedom
+to share and change it. By contrast, the GNU General Public License is
+intended to guarantee your freedom to share and change free
+software--to make sure the software is free for all its users. This
+General Public License applies to most of the Free Software
+Foundation's software and to any other program whose authors commit to
+using it. (Some other Free Software Foundation software is covered by
+the GNU Lesser General Public License instead.) You can apply it to
+your programs, too.
+
+When we speak of free software, we are referring to freedom, not
+price. Our General Public Licenses are designed to make sure that you
+have the freedom to distribute copies of free software (and charge for
+this service if you wish), that you receive source code or can get it
+if you want it, that you can change the software or use pieces of it
+in new free programs; and that you know you can do these things.
+
+To protect your rights, we need to make restrictions that forbid
+anyone to deny you these rights or to ask you to surrender the rights.
+These restrictions translate to certain responsibilities for you if
+you distribute copies of the software, or if you modify it.
+
+For example, if you distribute copies of such a program, whether
+gratis or for a fee, you must give the recipients all the rights that
+you have. You must make sure that they, too, receive or can get the
+source code. And you must show them these terms so they know their
+rights.
+
+We protect your rights with two steps: (1) copyright the software, and
+(2) offer you this license which gives you legal permission to copy,
+distribute and/or modify the software.
+
+Also, for each author's protection and ours, we want to make certain
+that everyone understands that there is no warranty for this free
+software. If the software is modified by someone else and passed on,
+we want its recipients to know that what they have is not the
+original, so that any problems introduced by others will not reflect
+on the original authors' reputations.
+
+Finally, any free program is threatened constantly by software
+patents. We wish to avoid the danger that redistributors of a free
+program will individually obtain patent licenses, in effect making the
+program proprietary. To prevent this, we have made it clear that any
+patent must be licensed for everyone's free use or not licensed at
+all.
+
+The precise terms and conditions for copying, distribution and
+modification follow.
+
+### TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
+
+**0.** This License applies to any program or other work which
+contains a notice placed by the copyright holder saying it may be
+distributed under the terms of this General Public License. The
+"Program", below, refers to any such program or work, and a "work
+based on the Program" means either the Program or any derivative work
+under copyright law: that is to say, a work containing the Program or
+a portion of it, either verbatim or with modifications and/or
+translated into another language. (Hereinafter, translation is
+included without limitation in the term "modification".) Each licensee
+is addressed as "you".
+
+Activities other than copying, distribution and modification are not
+covered by this License; they are outside its scope. The act of
+running the Program is not restricted, and the output from the Program
+is covered only if its contents constitute a work based on the Program
+(independent of having been made by running the Program). Whether that
+is true depends on what the Program does.
+
+**1.** You may copy and distribute verbatim copies of the Program's
+source code as you receive it, in any medium, provided that you
+conspicuously and appropriately publish on each copy an appropriate
+copyright notice and disclaimer of warranty; keep intact all the
+notices that refer to this License and to the absence of any warranty;
+and give any other recipients of the Program a copy of this License
+along with the Program.
+
+You may charge a fee for the physical act of transferring a copy, and
+you may at your option offer warranty protection in exchange for a
+fee.
+
+**2.** You may modify your copy or copies of the Program or any
+portion of it, thus forming a work based on the Program, and copy and
+distribute such modifications or work under the terms of Section 1
+above, provided that you also meet all of these conditions:
+
+  
+**a)** You must cause the modified files to carry prominent notices
+stating that you changed the files and the date of any change.
+
+  
+**b)** You must cause any work that you distribute or publish, that in
+whole or in part contains or is derived from the Program or any part
+thereof, to be licensed as a whole at no charge to all third parties
+under the terms of this License.
+
+  
+**c)** If the modified program normally reads commands interactively
+when run, you must cause it, when started running for such interactive
+use in the most ordinary way, to print or display an announcement
+including an appropriate copyright notice and a notice that there is
+no warranty (or else, saying that you provide a warranty) and that
+users may redistribute the program under these conditions, and telling
+the user how to view a copy of this License. (Exception: if the
+Program itself is interactive but does not normally print such an
+announcement, your work based on the Program is not required to print
+an announcement.)
+
+These requirements apply to the modified work as a whole. If
+identifiable sections of that work are not derived from the Program,
+and can be reasonably considered independent and separate works in
+themselves, then this License, and its terms, do not apply to those
+sections when you distribute them as separate works. But when you
+distribute the same sections as part of a whole which is a work based
+on the Program, the distribution of the whole must be on the terms of
+this License, whose permissions for other licensees extend to the
+entire whole, and thus to each and every part regardless of who wrote
+it.
+
+Thus, it is not the intent of this section to claim rights or contest
+your rights to work written entirely by you; rather, the intent is to
+exercise the right to control the distribution of derivative or
+collective works based on the Program.
+
+In addition, mere aggregation of another work not based on the Program
+with the Program (or with a work based on the Program) on a volume of
+a storage or distribution medium does not bring the other work under
+the scope of this License.
+
+**3.** You may copy and distribute the Program (or a work based on it,
+under Section 2) in object code or executable form under the terms of
+Sections 1 and 2 above provided that you also do one of the following:
+
+  
+**a)** Accompany it with the complete corresponding machine-readable
+source code, which must be distributed under the terms of Sections 1
+and 2 above on a medium customarily used for software interchange; or,
+
+  
+**b)** Accompany it with a written offer, valid for at least three
+years, to give any third party, for a charge no more than your cost of
+physically performing source distribution, a complete machine-readable
+copy of the corresponding source code, to be distributed under the
+terms of Sections 1 and 2 above on a medium customarily used for
+software interchange; or,
+
+  
+**c)** Accompany it with the information you received as to the offer
+to distribute corresponding source code. (This alternative is allowed
+only for noncommercial distribution and only if you received the
+program in object code or executable form with such an offer, in
+accord with Subsection b above.)
+
+The source code for a work means the preferred form of the work for
+making modifications to it. For an executable work, complete source
+code means all the source code for all modules it contains, plus any
+associated interface definition files, plus the scripts used to
+control compilation and installation of the executable. However, as a
+special exception, the source code distributed need not include
+anything that is normally distributed (in either source or binary
+form) with the major components (compiler, kernel, and so on) of the
+operating system on which the executable runs, unless that component
+itself accompanies the executable.
+
+If distribution of executable or object code is made by offering
+access to copy from a designated place, then offering equivalent
+access to copy the source code from the same place counts as
+distribution of the source code, even though third parties are not
+compelled to copy the source along with the object code.
+
+**4.** You may not copy, modify, sublicense, or distribute the Program
+except as expressly provided under this License. Any attempt otherwise
+to copy, modify, sublicense or distribute the Program is void, and
+will automatically terminate your rights under this License. However,
+parties who have received copies, or rights, from you under this
+License will not have their licenses terminated so long as such
+parties remain in full compliance.
+
+**5.** You are not required to accept this License, since you have not
+signed it. However, nothing else grants you permission to modify or
+distribute the Program or its derivative works. These actions are
+prohibited by law if you do not accept this License. Therefore, by
+modifying or distributing the Program (or any work based on the
+Program), you indicate your acceptance of this License to do so, and
+all its terms and conditions for copying, distributing or modifying
+the Program or works based on it.
+
+**6.** Each time you redistribute the Program (or any work based on
+the Program), the recipient automatically receives a license from the
+original licensor to copy, distribute or modify the Program subject to
+these terms and conditions. You may not impose any further
+restrictions on the recipients' exercise of the rights granted herein.
+You are not responsible for enforcing compliance by third parties to
+this License.
+
+**7.** If, as a consequence of a court judgment or allegation of
+patent infringement or for any other reason (not limited to patent
+issues), conditions are imposed on you (whether by court order,
+agreement or otherwise) that contradict the conditions of this
+License, they do not excuse you from the conditions of this License.
+If you cannot distribute so as to satisfy simultaneously your
+obligations under this License and any other pertinent obligations,
+then as a consequence you may not distribute the Program at all. For
+example, if a patent license would not permit royalty-free
+redistribution of the Program by all those who receive copies directly
+or indirectly through you, then the only way you could satisfy both it
+and this License would be to refrain entirely from distribution of the
+Program.
+
+If any portion of this section is held invalid or unenforceable under
+any particular circumstance, the balance of the section is intended to
+apply and the section as a whole is intended to apply in other
+circumstances.
+
+It is not the purpose of this section to induce you to infringe any
+patents or other property right claims or to contest validity of any
+such claims; this section has the sole purpose of protecting the
+integrity of the free software distribution system, which is
+implemented by public license practices. Many people have made
+generous contributions to the wide range of software distributed
+through that system in reliance on consistent application of that
+system; it is up to the author/donor to decide if he or she is willing
+to distribute software through any other system and a licensee cannot
+impose that choice.
+
+This section is intended to make thoroughly clear what is believed to
+be a consequence of the rest of this License.
+
+**8.** If the distribution and/or use of the Program is restricted in
+certain countries either by patents or by copyrighted interfaces, the
+original copyright holder who places the Program under this License
+may add an explicit geographical distribution limitation excluding
+those countries, so that distribution is permitted only in or among
+countries not thus excluded. In such case, this License incorporates
+the limitation as if written in the body of this License.
+
+**9.** The Free Software Foundation may publish revised and/or new
+versions of the General Public License from time to time. Such new
+versions will be similar in spirit to the present version, but may
+differ in detail to address new problems or concerns.
+
+Each version is given a distinguishing version number. If the Program
+specifies a version number of this License which applies to it and
+"any later version", you have the option of following the terms and
+conditions either of that version or of any later version published by
+the Free Software Foundation. If the Program does not specify a
+version number of this License, you may choose any version ever
+published by the Free Software Foundation.
+
+**10.** If you wish to incorporate parts of the Program into other
+free programs whose distribution conditions are different, write to
+the author to ask for permission. For software which is copyrighted by
+the Free Software Foundation, write to the Free Software Foundation;
+we sometimes make exceptions for this. Our decision will be guided by
+the two goals of preserving the free status of all derivatives of our
+free software and of promoting the sharing and reuse of software
+generally.
+
+**NO WARRANTY**
+
+**11.** BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO
+WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW.
+EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR
+OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY
+KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE
+PROGRAM IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME
+THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
+
+**12.** IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN
+WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY
+AND/OR REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU
+FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR
+CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE
+PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING
+RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A
+FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), EVEN IF
+SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
+DAMAGES.
+
+### END OF TERMS AND CONDITIONS
diff --git a/README.md b/README.md
index 3626ed5eba4b1adaeb2f3d5883f91ada9390ade2..42934703538be92048013faf45a156dfc0a5a9ff 100644
--- a/README.md
+++ b/README.md
@@ -92,7 +92,7 @@ The older implementation is still available at <https://github.com/sandsmark/Qua
 
 > This program is free software: you can redistribute it and/or modify it
 > under the terms of the GNU General Public License as published by the Free
-> Software Foundation, either version 3 of the License, or (at your option)
+> Software Foundation, either version 2 of the License, or (at your option)
 > any later version.
 
 > This program is distributed in the hope that it will be useful,
diff --git a/app/src/main/java/de/kuschku/quasseldroid_ng/QuasseldroidNG.kt b/app/src/main/java/de/kuschku/quasseldroid_ng/QuasseldroidNG.kt
index 9ff456e538cabffe217696060b4d955557f6ac5c..4eff8cf83ac90b9ea333546de1cef8e2c01da9ec 100644
--- a/app/src/main/java/de/kuschku/quasseldroid_ng/QuasseldroidNG.kt
+++ b/app/src/main/java/de/kuschku/quasseldroid_ng/QuasseldroidNG.kt
@@ -10,6 +10,7 @@ import android.os.Build
 import de.kuschku.quasseldroid_ng.service.QuasselService
 import de.kuschku.quasseldroid_ng.util.AndroidCompatibilityUtils
 import de.kuschku.quasseldroid_ng.util.AndroidLoggingHandler
+import de.kuschku.quasseldroid_ng.util.AndroidStreamChannelFactory
 import de.kuschku.quasseldroid_ng.util.helper.systemService
 import org.acra.ACRA
 import org.acra.ReportingInteractionMode
@@ -33,8 +34,9 @@ class QuasseldroidNG : Application() {
 
     if (!ACRA.isACRASenderServiceProcess()) {
       // Init compatibility utils
-      AndroidCompatibilityUtils.init()
-      AndroidLoggingHandler.init()
+      AndroidCompatibilityUtils.inject()
+      AndroidLoggingHandler.inject()
+      AndroidStreamChannelFactory.inject()
 
       startService(Intent(this, QuasselService::class.java))
       if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
diff --git a/app/src/main/java/de/kuschku/quasseldroid_ng/ui/MainActivity.kt b/app/src/main/java/de/kuschku/quasseldroid_ng/ui/MainActivity.kt
index 5af0e5171ec6feb98044db2e19941cf1c93101e9..933598260cd76e795b2792206865b0e3d22a1d31 100644
--- a/app/src/main/java/de/kuschku/quasseldroid_ng/ui/MainActivity.kt
+++ b/app/src/main/java/de/kuschku/quasseldroid_ng/ui/MainActivity.kt
@@ -15,7 +15,7 @@ import butterknife.ButterKnife
 import de.kuschku.libquassel.session.Backend
 import de.kuschku.libquassel.session.ConnectionState
 import de.kuschku.libquassel.session.SocketAddress
-import de.kuschku.libquassel.util.LoggingHandler
+import de.kuschku.libquassel.util.compatibility.LoggingHandler
 import de.kuschku.quasseldroid_ng.R
 import de.kuschku.quasseldroid_ng.util.helper.stickyMapNotNull
 import de.kuschku.quasseldroid_ng.util.helper.stickySwitchMapNotNull
diff --git a/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidCompatibilityUtils.kt b/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidCompatibilityUtils.kt
index f3057a9720f05f088e74cd55d862c3839ca7a925..aee755bc8bfa2722a2988c681d883136b8a312d3 100644
--- a/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidCompatibilityUtils.kt
+++ b/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidCompatibilityUtils.kt
@@ -1,11 +1,11 @@
 package de.kuschku.quasseldroid_ng.util
 
 import android.os.Build
-import de.kuschku.libquassel.util.CompatibilityUtils
+import de.kuschku.libquassel.util.compatibility.CompatibilityUtils
 import java.util.*
 
 object AndroidCompatibilityUtils {
-  fun init() {
+  fun inject() {
     /**
      * This is used to check if the current device supports Sockets with the KeepAlive flag.
      * As that feature is only missing on Chromium devices, we just check for that
diff --git a/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidHandlerService.kt b/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidHandlerService.kt
index 8c575bc4691f509499178722f03292639e455944..c7278f3aa0b7ec588a471c9714280f645b7f349a 100644
--- a/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidHandlerService.kt
+++ b/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidHandlerService.kt
@@ -3,7 +3,7 @@ package de.kuschku.quasseldroid_ng.util
 import android.os.Handler
 import android.os.HandlerThread
 import android.os.Process
-import de.kuschku.libquassel.util.HandlerService
+import de.kuschku.libquassel.util.compatibility.HandlerService
 
 class AndroidHandlerService : HandlerService {
   override fun parse(f: () -> Unit) {
diff --git a/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidLoggingHandler.kt b/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidLoggingHandler.kt
index 0e69d331d4bf1a98a1e7c8d0fc936ba5625107c3..bd2ebaf1d968a758434f00a3cc151c54019faa6b 100644
--- a/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidLoggingHandler.kt
+++ b/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidLoggingHandler.kt
@@ -1,7 +1,7 @@
 package de.kuschku.quasseldroid_ng.util
 
 import android.util.Log
-import de.kuschku.libquassel.util.LoggingHandler
+import de.kuschku.libquassel.util.compatibility.LoggingHandler
 
 object AndroidLoggingHandler : LoggingHandler() {
   override fun isLoggable(logLevel: LogLevel, tag: String): Boolean {
@@ -25,7 +25,7 @@ object AndroidLoggingHandler : LoggingHandler() {
     LogLevel.ASSERT  -> Log.ASSERT
   }
 
-  fun init() {
+  fun inject() {
     LoggingHandler.loggingHandlers.clear()
     LoggingHandler.loggingHandlers.add(this)
   }
diff --git a/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidStreamChannelFactory.kt b/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidStreamChannelFactory.kt
new file mode 100644
index 0000000000000000000000000000000000000000..40ca744039284346a8bf9f291aa621cc16788ae7
--- /dev/null
+++ b/app/src/main/java/de/kuschku/quasseldroid_ng/util/AndroidStreamChannelFactory.kt
@@ -0,0 +1,18 @@
+package de.kuschku.quasseldroid_ng.util
+
+import de.kuschku.libquassel.util.compatibility.StreamChannelFactory
+import de.kuschku.quasseldroid_ng.util.backport.ReadableStreamChannel
+import de.kuschku.quasseldroid_ng.util.backport.WritableStreamChannel
+import java.io.InputStream
+import java.io.OutputStream
+import java.nio.channels.ReadableByteChannel
+import java.nio.channels.WritableByteChannel
+
+object AndroidStreamChannelFactory : StreamChannelFactory {
+  override fun create(stream: InputStream): ReadableByteChannel = ReadableStreamChannel(stream)
+  override fun create(stream: OutputStream): WritableByteChannel = WritableStreamChannel(stream)
+
+  fun inject() {
+    StreamChannelFactory.instance = this
+  }
+}
diff --git a/app/src/main/java/de/kuschku/quasseldroid_ng/util/backport/ReadableStreamChannel.kt b/app/src/main/java/de/kuschku/quasseldroid_ng/util/backport/ReadableStreamChannel.kt
new file mode 100644
index 0000000000000000000000000000000000000000..dc47a94bc4b176f18c9792e48ffc5351fbfc8527
--- /dev/null
+++ b/app/src/main/java/de/kuschku/quasseldroid_ng/util/backport/ReadableStreamChannel.kt
@@ -0,0 +1,83 @@
+/*
+ * Copyright (c) 2000, 2012, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package de.kuschku.quasseldroid_ng.util.backport
+
+import java.io.IOException
+import java.io.InputStream
+import java.nio.ByteBuffer
+import java.nio.channels.ReadableByteChannel
+import java.nio.channels.spi.AbstractInterruptibleChannel
+
+class ReadableStreamChannel(
+  private var stream: InputStream
+) : AbstractInterruptibleChannel(), ReadableByteChannel {
+  private var buffer = ByteArray(0)
+  private var open = true
+  private val readLock = Any()
+
+  @Throws(IOException::class)
+  override fun read(dst: ByteBuffer): Int {
+    val len = dst.remaining()
+    var totalRead = 0
+    var bytesRead = 0
+    synchronized(readLock) {
+      while (totalRead < len) {
+        val bytesToRead = Math.min(len - totalRead,
+                                   TRANSFER_SIZE)
+
+        if (buffer.size < bytesToRead)
+          buffer = ByteArray(bytesToRead)
+        if ((totalRead > 0) && !(stream.available() > 0))
+          break // block at most once
+        try {
+          begin()
+          bytesRead = stream.read(buffer, 0, bytesToRead)
+        } finally {
+          end(bytesRead > 0)
+        }
+        if (bytesRead < 0)
+          break
+        else
+          totalRead += bytesRead
+        dst.put(buffer, 0, bytesRead)
+      }
+      if (bytesRead < 0 && totalRead == 0)
+        return -1
+
+      return totalRead
+    }
+  }
+
+  @Throws(IOException::class)
+  override fun implCloseChannel() {
+    stream.close()
+    open = false
+  }
+
+  companion object {
+    private val TRANSFER_SIZE = 8192
+  }
+}
diff --git a/app/src/main/java/de/kuschku/quasseldroid_ng/util/backport/WritableStreamChannel.kt b/app/src/main/java/de/kuschku/quasseldroid_ng/util/backport/WritableStreamChannel.kt
new file mode 100644
index 0000000000000000000000000000000000000000..4f7542301adffbadbbc6f9f6e2f7b31cebb8d621
--- /dev/null
+++ b/app/src/main/java/de/kuschku/quasseldroid_ng/util/backport/WritableStreamChannel.kt
@@ -0,0 +1,76 @@
+/*
+ * Copyright (c) 2000, 2012, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package de.kuschku.quasseldroid_ng.util.backport
+
+import java.io.IOException
+import java.io.OutputStream
+import java.nio.ByteBuffer
+import java.nio.channels.WritableByteChannel
+import java.nio.channels.spi.AbstractInterruptibleChannel
+
+
+class WritableStreamChannel(
+  private var stream: OutputStream
+) : AbstractInterruptibleChannel(), WritableByteChannel {
+  private var buffer = ByteArray(0)
+  private var open = true
+  private val writeLock = Any()
+
+  @Throws(IOException::class)
+  override fun write(src: ByteBuffer): Int {
+    val len = src.remaining()
+    var totalWritten = 0
+    synchronized(writeLock) {
+      while (totalWritten < len) {
+        val bytesToWrite = Math.min(len - totalWritten,
+                                    TRANSFER_SIZE)
+
+        if (buffer.size < bytesToWrite)
+          buffer = ByteArray(bytesToWrite)
+        src.get(buffer, 0, bytesToWrite)
+
+        try {
+          begin()
+          stream.write(buffer, 0, bytesToWrite)
+        } finally {
+          end(bytesToWrite > 0)
+        }
+        totalWritten += bytesToWrite
+      }
+      return totalWritten
+    }
+  }
+
+  @Throws(IOException::class)
+  override fun implCloseChannel() {
+    stream.close()
+    open = false
+  }
+
+  companion object {
+    private val TRANSFER_SIZE = 8192
+  }
+}
diff --git a/lib/src/main/java/de/kuschku/libquassel/quassel/syncables/interfaces/invokers/Invokers.kt b/lib/src/main/java/de/kuschku/libquassel/quassel/syncables/interfaces/invokers/Invokers.kt
index cbfd8c2060441483e98a33f993d1a40ddde0c2a3..203884d8e37aa8f6166a048b8ac3c4667ec0fca7 100644
--- a/lib/src/main/java/de/kuschku/libquassel/quassel/syncables/interfaces/invokers/Invokers.kt
+++ b/lib/src/main/java/de/kuschku/libquassel/quassel/syncables/interfaces/invokers/Invokers.kt
@@ -2,9 +2,9 @@ package de.kuschku.libquassel.quassel.syncables.interfaces.invokers
 
 import de.kuschku.libquassel.annotations.Syncable
 import de.kuschku.libquassel.quassel.syncables.interfaces.*
-import de.kuschku.libquassel.util.LoggingHandler.LogLevel.DEBUG
-import de.kuschku.libquassel.util.LoggingHandler.LogLevel.WARN
-import de.kuschku.libquassel.util.log
+import de.kuschku.libquassel.util.compatibility.LoggingHandler.LogLevel.DEBUG
+import de.kuschku.libquassel.util.compatibility.LoggingHandler.LogLevel.WARN
+import de.kuschku.libquassel.util.compatibility.log
 
 object Invokers {
   private val registry = mutableMapOf<String, Invoker<*>>()
@@ -44,7 +44,8 @@ object Invokers {
   private fun <T> getInvoker(type: Class<T>): Invoker<T>? {
     val syncable: Syncable? = type.getAnnotation(Syncable::class.java)
     if (syncable == null) {
-      log(WARN, "Invokers", "Invoker not annotated: ${type.canonicalName}")
+      log(WARN, "Invokers",
+          "Invoker not annotated: ${type.canonicalName}")
       return null
     }
 
diff --git a/lib/src/main/java/de/kuschku/libquassel/session/ConnectionState.kt b/lib/src/main/java/de/kuschku/libquassel/session/ConnectionState.kt
index 1647d13cb33f093297bd6ff9a01895b0d846f345..51391c02a361636797182ef79e224200934d4599 100644
--- a/lib/src/main/java/de/kuschku/libquassel/session/ConnectionState.kt
+++ b/lib/src/main/java/de/kuschku/libquassel/session/ConnectionState.kt
@@ -5,5 +5,5 @@ enum class ConnectionState {
   CONNECTING,
   HANDSHAKE,
   INIT,
-  CONNECTED,
+  CONNECTED
 }
diff --git a/lib/src/main/java/de/kuschku/libquassel/session/CoreConnection.kt b/lib/src/main/java/de/kuschku/libquassel/session/CoreConnection.kt
index af42d2d4c76a471b4d47937b1f60b12215343f9a..9b26573ffa9f64f107b8c6460ab82722e62521c9 100644
--- a/lib/src/main/java/de/kuschku/libquassel/session/CoreConnection.kt
+++ b/lib/src/main/java/de/kuschku/libquassel/session/CoreConnection.kt
@@ -9,12 +9,12 @@ import de.kuschku.libquassel.protocol.primitive.serializer.IntSerializer
 import de.kuschku.libquassel.protocol.primitive.serializer.ProtocolSerializer
 import de.kuschku.libquassel.protocol.primitive.serializer.VariantListSerializer
 import de.kuschku.libquassel.quassel.ProtocolFeature
-import de.kuschku.libquassel.util.CompatibilityUtils
-import de.kuschku.libquassel.util.HandlerService
-import de.kuschku.libquassel.util.LoggingHandler.LogLevel.*
+import de.kuschku.libquassel.util.compatibility.CompatibilityUtils
+import de.kuschku.libquassel.util.compatibility.HandlerService
+import de.kuschku.libquassel.util.compatibility.LoggingHandler.LogLevel.*
+import de.kuschku.libquassel.util.compatibility.log
 import de.kuschku.libquassel.util.hasFlag
 import de.kuschku.libquassel.util.helpers.write
-import de.kuschku.libquassel.util.log
 import de.kuschku.libquassel.util.nio.ChainedByteBuffer
 import de.kuschku.libquassel.util.nio.WrappedChannel
 import io.reactivex.BackpressureStrategy
@@ -116,6 +116,7 @@ class CoreConnection(
       channel?.close()
       interrupt()
       handlerService.quit()
+      setState(ConnectionState.DISCONNECTED)
     } catch (e: Throwable) {
       log(WARN, TAG, "Error encountered while closing connection", e)
     }
@@ -155,24 +156,23 @@ class CoreConnection(
       readHandshake()
       while (!isInterrupted) {
         sizeBuffer.clear()
-        channel?.read(sizeBuffer)
+        if (channel?.read(sizeBuffer) == -1)
+          break
         sizeBuffer.flip()
 
         val size = IntSerializer.deserialize(sizeBuffer, session.coreFeatures)
         if (size > 64 * 1024 * 1024)
           throw SocketException("Too large frame received: $size")
         val dataBuffer = ByteBuffer.allocateDirect(size)
-        while (!isInterrupted && dataBuffer.position() < dataBuffer.limit() && channel?.read(
-          dataBuffer) ?: -1 > 0) {
+        while (dataBuffer.position() < dataBuffer.limit() && channel?.read(dataBuffer) ?: -1 > 0) {
         }
         dataBuffer.flip()
-        if (!isInterrupted)
-          handlerService.parse {
-            when (internalState.value) {
-              ConnectionState.HANDSHAKE -> processHandshake(dataBuffer)
-              else                      -> processSigProxy(dataBuffer)
-            }
+        handlerService.parse {
+          when (internalState.value) {
+            ConnectionState.HANDSHAKE -> processHandshake(dataBuffer)
+            else                      -> processSigProxy(dataBuffer)
           }
+        }
       }
     } catch (e: Throwable) {
       log(WARN, TAG, "Error encountered in connection", e)
diff --git a/lib/src/main/java/de/kuschku/libquassel/session/MessageRunnable.kt b/lib/src/main/java/de/kuschku/libquassel/session/MessageRunnable.kt
index e3f2b0eca8e68c3d5679619bd526e3202bf48e37..f48594eb67575206f02b6ae1d950923be6da152e 100644
--- a/lib/src/main/java/de/kuschku/libquassel/session/MessageRunnable.kt
+++ b/lib/src/main/java/de/kuschku/libquassel/session/MessageRunnable.kt
@@ -2,9 +2,9 @@ package de.kuschku.libquassel.session
 
 import de.kuschku.libquassel.protocol.Quassel_Features
 import de.kuschku.libquassel.protocol.primitive.serializer.Serializer
-import de.kuschku.libquassel.util.LoggingHandler.LogLevel.WARN
+import de.kuschku.libquassel.util.compatibility.LoggingHandler.LogLevel.WARN
+import de.kuschku.libquassel.util.compatibility.log
 import de.kuschku.libquassel.util.helpers.write
-import de.kuschku.libquassel.util.log
 import de.kuschku.libquassel.util.nio.ChainedByteBuffer
 import de.kuschku.libquassel.util.nio.WrappedChannel
 import java.nio.ByteBuffer
diff --git a/lib/src/main/java/de/kuschku/libquassel/session/ProtocolHandler.kt b/lib/src/main/java/de/kuschku/libquassel/session/ProtocolHandler.kt
index 84de4de6b0c51aec9e633a79561a200f9c9a9e03..5f364a5eee0ae91d496d6b659f6ffce23edfaba4 100644
--- a/lib/src/main/java/de/kuschku/libquassel/session/ProtocolHandler.kt
+++ b/lib/src/main/java/de/kuschku/libquassel/session/ProtocolHandler.kt
@@ -7,9 +7,9 @@ import de.kuschku.libquassel.quassel.exceptions.ObjectNotFoundException
 import de.kuschku.libquassel.quassel.syncables.RpcHandler
 import de.kuschku.libquassel.quassel.syncables.interfaces.ISyncableObject
 import de.kuschku.libquassel.quassel.syncables.interfaces.invokers.Invokers
-import de.kuschku.libquassel.util.LoggingHandler.LogLevel.DEBUG
-import de.kuschku.libquassel.util.LoggingHandler.LogLevel.WARN
-import de.kuschku.libquassel.util.log
+import de.kuschku.libquassel.util.compatibility.LoggingHandler.LogLevel.DEBUG
+import de.kuschku.libquassel.util.compatibility.LoggingHandler.LogLevel.WARN
+import de.kuschku.libquassel.util.compatibility.log
 import org.threeten.bp.Instant
 
 abstract class ProtocolHandler : SignalProxy, AuthHandler {
@@ -33,7 +33,8 @@ abstract class ProtocolHandler : SignalProxy, AuthHandler {
         log(DEBUG, "No receiver registered for $f")
       }
     } catch (e: Throwable) {
-      log(WARN, "ProtocolHandler", "Error Handling SignalProxyMessage", e)
+      log(WARN, "ProtocolHandler",
+          "Error Handling SignalProxyMessage", e)
     }
     return true
   }
@@ -44,7 +45,8 @@ abstract class ProtocolHandler : SignalProxy, AuthHandler {
         log(DEBUG, "No receiver registered for $f")
       }
     } catch (e: Throwable) {
-      log(WARN, "ProtocolHandler", "Error Handling HandshakeMessage", e)
+      log(WARN, "ProtocolHandler",
+          "Error Handling HandshakeMessage", e)
     }
     return true
   }
@@ -170,5 +172,6 @@ abstract class ProtocolHandler : SignalProxy, AuthHandler {
 
   open fun cleanUp() {
     objectStorage.clear()
+    toInit.clear()
   }
 }
diff --git a/lib/src/main/java/de/kuschku/libquassel/session/Session.kt b/lib/src/main/java/de/kuschku/libquassel/session/Session.kt
index 56dc9efdd5cf5516ae95256b296bd08a8758f3c3..e77a42c700f267b5c5d19809cd5c64cb038d3e6b 100644
--- a/lib/src/main/java/de/kuschku/libquassel/session/Session.kt
+++ b/lib/src/main/java/de/kuschku/libquassel/session/Session.kt
@@ -6,11 +6,11 @@ import de.kuschku.libquassel.protocol.message.SignalProxyMessage
 import de.kuschku.libquassel.quassel.QuasselFeature
 import de.kuschku.libquassel.quassel.syncables.*
 import de.kuschku.libquassel.quassel.syncables.interfaces.invokers.Invokers
-import de.kuschku.libquassel.util.HandlerService
-import de.kuschku.libquassel.util.LoggingHandler.LogLevel.DEBUG
-import de.kuschku.libquassel.util.LoggingHandler.LogLevel.INFO
+import de.kuschku.libquassel.util.compatibility.HandlerService
+import de.kuschku.libquassel.util.compatibility.LoggingHandler.LogLevel.DEBUG
+import de.kuschku.libquassel.util.compatibility.LoggingHandler.LogLevel.INFO
+import de.kuschku.libquassel.util.compatibility.log
 import de.kuschku.libquassel.util.hasFlag
-import de.kuschku.libquassel.util.log
 import io.reactivex.BackpressureStrategy
 import io.reactivex.Flowable
 import io.reactivex.subjects.BehaviorSubject
diff --git a/lib/src/main/java/de/kuschku/libquassel/util/CompatibilityUtils.kt b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/CompatibilityUtils.kt
similarity index 95%
rename from lib/src/main/java/de/kuschku/libquassel/util/CompatibilityUtils.kt
rename to lib/src/main/java/de/kuschku/libquassel/util/compatibility/CompatibilityUtils.kt
index a9161802a778311fd22cb83265d2c11a70d205c1..5a44ad0024579afe0ab9420f4d7e8b08f882118f 100644
--- a/lib/src/main/java/de/kuschku/libquassel/util/CompatibilityUtils.kt
+++ b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/CompatibilityUtils.kt
@@ -1,4 +1,4 @@
-package de.kuschku.libquassel.util
+package de.kuschku.libquassel.util.compatibility
 
 import java.io.OutputStream
 import java.util.zip.Deflater
diff --git a/lib/src/main/java/de/kuschku/libquassel/util/HandlerService.kt b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/HandlerService.kt
similarity index 78%
rename from lib/src/main/java/de/kuschku/libquassel/util/HandlerService.kt
rename to lib/src/main/java/de/kuschku/libquassel/util/compatibility/HandlerService.kt
index 7b1334453148b580f3d3266bfc3953be6db371be..0c81b5536d867c917a2ec0b69b38daa9e0b834c5 100644
--- a/lib/src/main/java/de/kuschku/libquassel/util/HandlerService.kt
+++ b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/HandlerService.kt
@@ -1,4 +1,4 @@
-package de.kuschku.libquassel.util
+package de.kuschku.libquassel.util.compatibility
 
 interface HandlerService {
   fun parse(f: () -> Unit)
diff --git a/lib/src/main/java/de/kuschku/libquassel/util/LoggingHandler.kt b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/LoggingHandler.kt
similarity index 96%
rename from lib/src/main/java/de/kuschku/libquassel/util/LoggingHandler.kt
rename to lib/src/main/java/de/kuschku/libquassel/util/compatibility/LoggingHandler.kt
index 43e5b29644b7262ab8e9644a51354d2360ce148b..4deee5821a49ea7f9a76881d246dd95ee0f1eb61 100644
--- a/lib/src/main/java/de/kuschku/libquassel/util/LoggingHandler.kt
+++ b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/LoggingHandler.kt
@@ -1,4 +1,4 @@
-package de.kuschku.libquassel.util
+package de.kuschku.libquassel.util.compatibility
 
 abstract class LoggingHandler {
   abstract fun log(logLevel: LogLevel, tag: String, message: String? = null,
diff --git a/lib/src/main/java/de/kuschku/libquassel/util/compatibility/StreamChannelFactory.kt b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/StreamChannelFactory.kt
new file mode 100644
index 0000000000000000000000000000000000000000..ee59bae56048ff21450068d43b3d5e8490f1d9dd
--- /dev/null
+++ b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/StreamChannelFactory.kt
@@ -0,0 +1,18 @@
+package de.kuschku.libquassel.util.compatibility
+
+import de.kuschku.libquassel.util.compatibility.reference.JavaStreamChannelFactory
+import java.io.InputStream
+import java.io.OutputStream
+import java.nio.channels.ReadableByteChannel
+import java.nio.channels.WritableByteChannel
+
+interface StreamChannelFactory {
+  fun create(stream: InputStream): ReadableByteChannel
+  fun create(stream: OutputStream): WritableByteChannel
+
+  companion object : StreamChannelFactory {
+    override fun create(stream: InputStream) = instance.create(stream)
+    override fun create(stream: OutputStream) = instance.create(stream)
+    var instance: StreamChannelFactory = JavaStreamChannelFactory
+  }
+}
diff --git a/lib/src/main/java/de/kuschku/libquassel/util/JavaHandlerService.kt b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/reference/JavaHandlerService.kt
similarity index 90%
rename from lib/src/main/java/de/kuschku/libquassel/util/JavaHandlerService.kt
rename to lib/src/main/java/de/kuschku/libquassel/util/compatibility/reference/JavaHandlerService.kt
index 4459302fd29da85e613c1fe30bf0b7c18cacb858..141780406f11fedb797c515b6a19cd727ac2a93f 100644
--- a/lib/src/main/java/de/kuschku/libquassel/util/JavaHandlerService.kt
+++ b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/reference/JavaHandlerService.kt
@@ -1,5 +1,6 @@
-package de.kuschku.libquassel.util
+package de.kuschku.libquassel.util.compatibility.reference
 
+import de.kuschku.libquassel.util.compatibility.HandlerService
 import java.util.concurrent.Executors
 
 class JavaHandlerService : HandlerService {
diff --git a/lib/src/main/java/de/kuschku/libquassel/util/JavaLoggingHandler.kt b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/reference/JavaLoggingHandler.kt
similarity index 70%
rename from lib/src/main/java/de/kuschku/libquassel/util/JavaLoggingHandler.kt
rename to lib/src/main/java/de/kuschku/libquassel/util/compatibility/reference/JavaLoggingHandler.kt
index e6e09148d7edbcd833d6a9a858c30e0747bc0310..668d869593894048be0fbb43c887c8dd268a2655 100644
--- a/lib/src/main/java/de/kuschku/libquassel/util/JavaLoggingHandler.kt
+++ b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/reference/JavaLoggingHandler.kt
@@ -1,15 +1,18 @@
-package de.kuschku.libquassel.util
+package de.kuschku.libquassel.util.compatibility.reference
 
+import de.kuschku.libquassel.util.compatibility.LoggingHandler
 import java.util.logging.Level
 import java.util.logging.Logger
 
 object JavaLoggingHandler : LoggingHandler() {
   override fun isLoggable(logLevel: LogLevel, tag: String): Boolean {
-    return Logger.getLogger(tag).isLoggable(priority(logLevel))
+    return Logger.getLogger(tag).isLoggable(
+      priority(logLevel))
   }
 
   override fun log(logLevel: LogLevel, tag: String, message: String?, throwable: Throwable?) {
-    val priority = priority(logLevel)
+    val priority = priority(
+      logLevel)
     val logger = Logger.getLogger(tag)
     if (message != null)
       logger.log(priority, message)
@@ -26,8 +29,8 @@ object JavaLoggingHandler : LoggingHandler() {
     LogLevel.ASSERT  -> Level.SEVERE
   }
 
-  fun init() {
-    LoggingHandler.loggingHandlers.clear()
-    LoggingHandler.loggingHandlers.add(this)
+  fun inject() {
+    loggingHandlers.clear()
+    loggingHandlers.add(this)
   }
 }
diff --git a/lib/src/main/java/de/kuschku/libquassel/util/compatibility/reference/JavaStreamChannelFactory.kt b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/reference/JavaStreamChannelFactory.kt
new file mode 100644
index 0000000000000000000000000000000000000000..57473e492863a2b8826e8a8b675786f77c3ef9fd
--- /dev/null
+++ b/lib/src/main/java/de/kuschku/libquassel/util/compatibility/reference/JavaStreamChannelFactory.kt
@@ -0,0 +1,17 @@
+package de.kuschku.libquassel.util.compatibility.reference
+
+import de.kuschku.libquassel.util.compatibility.StreamChannelFactory
+import java.io.InputStream
+import java.io.OutputStream
+import java.nio.channels.Channels
+import java.nio.channels.ReadableByteChannel
+import java.nio.channels.WritableByteChannel
+
+object JavaStreamChannelFactory : StreamChannelFactory {
+  override fun create(stream: InputStream): ReadableByteChannel = Channels.newChannel(stream)
+  override fun create(stream: OutputStream): WritableByteChannel = Channels.newChannel(stream)
+
+  fun inject() {
+    StreamChannelFactory.instance = this
+  }
+}
diff --git a/lib/src/main/java/de/kuschku/libquassel/util/helpers/StringHelper.kt b/lib/src/main/java/de/kuschku/libquassel/util/helpers/StringHelper.kt
index 59f2985a71fd47d88afc6bf191eb27aee0e6a43b..bd4f543fd88ce561a30268db3f05a5db3f8b29be 100644
--- a/lib/src/main/java/de/kuschku/libquassel/util/helpers/StringHelper.kt
+++ b/lib/src/main/java/de/kuschku/libquassel/util/helpers/StringHelper.kt
@@ -5,8 +5,4 @@ package de.kuschku.libquassel.util.helpers
  *
  * @return A list with all substrings of length 1, in order
  */
-fun String.split(): Array<String> {
-  val chars = arrayOfNulls<String>(length)
-  val charArray = toCharArray()
-  return chars.indices.map { String(charArray, it, 1) }.toTypedArray()
-}
+fun String.split() = Array(length) { this.substring(it, it + 1) }
diff --git a/lib/src/main/java/de/kuschku/libquassel/util/nio/WrappedChannel.kt b/lib/src/main/java/de/kuschku/libquassel/util/nio/WrappedChannel.kt
index 1896f5f90da3dbe9657394e5dcd92155a8109376..1170202b27c27cb0b2dd7b15878eaba14eb26401 100644
--- a/lib/src/main/java/de/kuschku/libquassel/util/nio/WrappedChannel.kt
+++ b/lib/src/main/java/de/kuschku/libquassel/util/nio/WrappedChannel.kt
@@ -1,7 +1,8 @@
 package de.kuschku.libquassel.util.nio
 
 import de.kuschku.libquassel.session.SocketAddress
-import de.kuschku.libquassel.util.CompatibilityUtils
+import de.kuschku.libquassel.util.compatibility.CompatibilityUtils
+import de.kuschku.libquassel.util.compatibility.StreamChannelFactory
 import java.io.Flushable
 import java.io.IOException
 import java.io.InputStream
@@ -9,7 +10,10 @@ import java.io.OutputStream
 import java.net.Socket
 import java.net.SocketException
 import java.nio.ByteBuffer
-import java.nio.channels.*
+import java.nio.channels.ByteChannel
+import java.nio.channels.InterruptibleChannel
+import java.nio.channels.ReadableByteChannel
+import java.nio.channels.WritableByteChannel
 import java.security.GeneralSecurityException
 import java.util.zip.InflaterInputStream
 import javax.net.ssl.SSLContext
@@ -19,16 +23,21 @@ import javax.net.ssl.X509TrustManager
 
 class WrappedChannel(
   private val socket: Socket,
-  private val rawInStream: InputStream? = null,
-  private val rawOutStream: OutputStream? = null,
+  private var rawInStream: InputStream? = null,
+  private var rawOutStream: OutputStream? = null,
   private var flusher: (() -> Unit)? = null
 ) : Flushable, ByteChannel, InterruptibleChannel {
   private var rawIn: ReadableByteChannel? = null
   private var rawOut: WritableByteChannel? = null
 
   init {
-    this.rawIn = Channels.newChannel(rawInStream)
-    this.rawOut = Channels.newChannel(rawOutStream)
+    val rawInStream = this.rawInStream
+    if (rawInStream != null)
+      this.rawIn = StreamChannelFactory.create(rawInStream)
+
+    val rawOutStream = this.rawOutStream
+    if (rawOutStream != null)
+      this.rawOut = StreamChannelFactory.create(rawOutStream)
   }
 
   companion object {
diff --git a/lib/src/test/java/de/kuschku/libquassel/ConnectionUnitTest.kt b/lib/src/test/java/de/kuschku/libquassel/ConnectionUnitTest.kt
index 6ea74866617dd22a6c1aafe5f75212b38f6c7a59..08de3201d0593736ff52d89e93ca469a50fe6d53 100644
--- a/lib/src/test/java/de/kuschku/libquassel/ConnectionUnitTest.kt
+++ b/lib/src/test/java/de/kuschku/libquassel/ConnectionUnitTest.kt
@@ -9,8 +9,8 @@ import de.kuschku.libquassel.quassel.QuasselFeature
 import de.kuschku.libquassel.session.CoreConnection
 import de.kuschku.libquassel.session.Session
 import de.kuschku.libquassel.session.SocketAddress
-import de.kuschku.libquassel.util.JavaHandlerService
-import de.kuschku.libquassel.util.JavaLoggingHandler
+import de.kuschku.libquassel.util.compatibility.reference.JavaHandlerService
+import de.kuschku.libquassel.util.compatibility.reference.JavaLoggingHandler
 import org.junit.BeforeClass
 import org.junit.Test
 import org.threeten.bp.Instant
@@ -53,7 +53,8 @@ class ConnectionUnitTest {
     session.userData = user to pass
 
     session.connection.onNext(
-      CoreConnection(session, SocketAddress(host, port), JavaHandlerService()))
+      CoreConnection(session, SocketAddress(host, port),
+                     JavaHandlerService()))
     session.connection.value.start()
     session.connection.value.join()
   }