From 9e7e2948e30921e60d40057c0693aafb79198b1a Mon Sep 17 00:00:00 2001
From: zzz <zzz@mail.i2p>
Date: Sat, 20 Sep 2014 12:20:08 +0000
Subject: [PATCH] dont return next IV to cache

---
 .../i2p/router/transport/ntcp/EstablishState.java   | 13 ++++++++-----
 .../i2p/router/transport/ntcp/NTCPConnection.java   | 10 ++++++++++
 2 files changed, 18 insertions(+), 5 deletions(-)

diff --git a/router/java/src/net/i2p/router/transport/ntcp/EstablishState.java b/router/java/src/net/i2p/router/transport/ntcp/EstablishState.java
index facf890f9e..4697e15f6d 100644
--- a/router/java/src/net/i2p/router/transport/ntcp/EstablishState.java
+++ b/router/java/src/net/i2p/router/transport/ntcp/EstablishState.java
@@ -640,9 +640,8 @@ class EstablishState {
                         prepareExtra(src);
                         byte nextWriteIV[] = _curEncrypted; // reuse buf
                         System.arraycopy(_prevEncrypted, _prevEncrypted.length-AES_SIZE, nextWriteIV, 0, AES_SIZE);
-                        byte nextReadIV[] = _curDecrypted;  // reuse buf
-                        System.arraycopy(_e_bobSig, _e_bobSig.length-AES_SIZE, nextReadIV, 0, nextReadIV.length);
-                        _con.finishOutboundEstablishment(_dh.getSessionKey(), (_tsA-_tsB), nextWriteIV, nextReadIV); // skew in seconds
+                        // this does not copy the nextWriteIV, do not release to cache
+                        _con.finishOutboundEstablishment(_dh.getSessionKey(), (_tsA-_tsB), nextWriteIV, _e_bobSig); // skew in seconds
                         releaseBufs();
                         // if socket gets closed this will be null - prevent NPE
                         InetAddress ia = _con.getChannel().socket().getInetAddress();
@@ -821,8 +820,9 @@ class EstablishState {
                 _con.setRemotePeer(_aliceIdent);
                 if (_log.shouldLog(Log.DEBUG))
                     _log.debug(prefix()+"e_bobSig is " + _e_bobSig.length + " bytes long");
-                byte iv[] = _curDecrypted;  // reuse buf
+                byte iv[] = _curEncrypted;  // reuse buf
                 System.arraycopy(_e_bobSig, _e_bobSig.length-AES_SIZE, iv, 0, AES_SIZE);
+                // this does not copy the IV, do not release to cache
                 _con.finishInboundEstablishment(_dh.getSessionKey(), (tsA-_tsB), iv, _prevEncrypted); // skew in seconds
                 releaseBufs();
                 if (_log.shouldLog(Log.INFO))
@@ -936,7 +936,10 @@ class EstablishState {
         // null or longer for OB
         if (_prevEncrypted != null && _prevEncrypted.length == AES_SIZE)
             SimpleByteCache.release(_prevEncrypted);
-        SimpleByteCache.release(_curEncrypted);
+        // Do not release _curEncrypted if verified, it is passed to
+        // NTCPConnection to use as the IV
+        if (_state != State.VERIFIED)
+            SimpleByteCache.release(_curEncrypted);
         SimpleByteCache.release(_curDecrypted);
         SimpleByteCache.release(_hX_xor_bobIdentHash);
         if (_dh.getPeerPublicValue() == null)
diff --git a/router/java/src/net/i2p/router/transport/ntcp/NTCPConnection.java b/router/java/src/net/i2p/router/transport/ntcp/NTCPConnection.java
index 0e6ad83234..a9752a2862 100644
--- a/router/java/src/net/i2p/router/transport/ntcp/NTCPConnection.java
+++ b/router/java/src/net/i2p/router/transport/ntcp/NTCPConnection.java
@@ -266,6 +266,8 @@ class NTCPConnection {
     /** 
      * @param clockSkew alice's clock minus bob's clock in seconds (may be negative, obviously, but |val| should
      *                  be under 1 minute)
+     * @param prevWriteEnd exactly 16 bytes, not copied, do not corrupt
+     * @param prevReadEnd 16 or more bytes, last 16 bytes copied
      */
     public void finishInboundEstablishment(SessionKey key, long clockSkew, byte prevWriteEnd[], byte prevReadEnd[]) {
         NTCPConnection toClose = locked_finishInboundEstablishment(key, clockSkew, prevWriteEnd, prevReadEnd);
@@ -278,6 +280,12 @@ class NTCPConnection {
         enqueueInfoMessage();
     }
     
+    /** 
+     * @param clockSkew alice's clock minus bob's clock in seconds (may be negative, obviously, but |val| should
+     *                  be under 1 minute)
+     * @param prevWriteEnd exactly 16 bytes, not copied, do not corrupt
+     * @param prevReadEnd 16 or more bytes, last 16 bytes copied
+     */
     private synchronized NTCPConnection locked_finishInboundEstablishment(
             SessionKey key, long clockSkew, byte prevWriteEnd[], byte prevReadEnd[]) {
         _sessionKey = key;
@@ -582,6 +590,8 @@ class NTCPConnection {
     /** 
      * @param clockSkew alice's clock minus bob's clock in seconds (may be negative, obviously, but |val| should
      *                  be under 1 minute)
+     * @param prevWriteEnd exactly 16 bytes, not copied, do not corrupt
+     * @param prevReadEnd 16 or more bytes, last 16 bytes copied
      */
     public synchronized void finishOutboundEstablishment(SessionKey key, long clockSkew, byte prevWriteEnd[], byte prevReadEnd[]) {
         if (_log.shouldLog(Log.DEBUG))
-- 
GitLab