diff --git a/router/java/src/net/i2p/data/i2np/DatabaseLookupMessage.java b/router/java/src/net/i2p/data/i2np/DatabaseLookupMessage.java
index b3a7b4339223647678d9bac91a54f7603146be55..4c0319f9bbf5cd3b78c7d536a3a7aeea0ec09d2e 100644
--- a/router/java/src/net/i2p/data/i2np/DatabaseLookupMessage.java
+++ b/router/java/src/net/i2p/data/i2np/DatabaseLookupMessage.java
@@ -304,8 +304,7 @@ public class DatabaseLookupMessage extends FastI2NPMessageImpl {
      *  Preliminary, not fully supported, see proposal 154.
      *
      *  @throws IllegalStateException if key or tag previously set, to protect saved checksum
-     *  @param encryptKey non-null
-     *  @param encryptTag non-null
+     *  @param pubKey non-null
      *  @since 0.9.46
      */
     public void setReplySession(PublicKey pubKey) {
diff --git a/router/java/src/net/i2p/router/crypto/ratchet/RatchetPayload.java b/router/java/src/net/i2p/router/crypto/ratchet/RatchetPayload.java
index d290238fdc005e77a8904bbd01a69f58b8c5ec25..59cabe29b5669772c5a14147a07385bca4afae11 100644
--- a/router/java/src/net/i2p/router/crypto/ratchet/RatchetPayload.java
+++ b/router/java/src/net/i2p/router/crypto/ratchet/RatchetPayload.java
@@ -67,7 +67,6 @@ class RatchetPayload {
         public void gotAck(int id, int n);
 
         /**
-         *  @param di may be null
          *  @since 0.9.46
          */
         public void gotAckRequest();
diff --git a/router/java/src/net/i2p/router/crypto/ratchet/RatchetSessionTag.java b/router/java/src/net/i2p/router/crypto/ratchet/RatchetSessionTag.java
index 948b80c2e598911bf45d3ede8d1799dc4ab53f88..a5dc55b6ee1148f5297b873f6b4f15ffa491c2a1 100644
--- a/router/java/src/net/i2p/router/crypto/ratchet/RatchetSessionTag.java
+++ b/router/java/src/net/i2p/router/crypto/ratchet/RatchetSessionTag.java
@@ -1,11 +1,9 @@
 package net.i2p.router.crypto.ratchet;
 
-import java.util.Arrays;
-
 import net.i2p.data.Base64;
 
 /**
- *  8 bytes, usually of random data.
+ *  8 bytes of random data.
  *  Does not extend SessionTag or DataStructure to save space
  *
  *  @since 0.9.44
@@ -25,18 +23,38 @@ public class RatchetSessionTag {
         _data = RatchetPayload.fromLong8(val, 0);
     }
     
+    /**
+     *  @return data as a byte array
+     */
     public byte[] getData() {
         byte[] rv = new byte[LENGTH];
         RatchetPayload.toLong8(rv, 0, _data);
         return rv;
     }
     
+    /**
+     *  @return data as a long value
+     *  @since 0.9.46
+     */
+    public long getLong() {
+        return _data;
+    }
+    
     public int length() {
         return LENGTH;
     }
 
+    /** 12 chars */
     public String toBase64() {
-        return Base64.encode(getData());
+        // for efficiency
+        //return Base64.encode(getData());
+        StringBuilder buf = new StringBuilder(12);
+        for (int i = 58; i > 0; i -= 6) {
+            buf.append(Base64.ALPHABET_I2P.charAt(((int) (_data >> i)) & 0x3f));
+        }
+        buf.append(Base64.ALPHABET_I2P.charAt(((int) (_data << 2)) & 0x3c));
+        buf.append('=');
+        return buf.toString();
     }
 
     /**
@@ -56,10 +74,20 @@ public class RatchetSessionTag {
 
     @Override
     public String toString() {
-        StringBuilder buf = new StringBuilder(64);
+        StringBuilder buf = new StringBuilder(33);
         buf.append("[RatchetSessionTag: ");
         buf.append(toBase64());
         buf.append(']');
         return buf.toString();
     }
+
+/****
+    public static void main(String[] args) {
+        // test toBase64()
+        long l = net.i2p.util.RandomSource.getInstance().nextLong();
+        RatchetSessionTag tag = new RatchetSessionTag(l);
+        System.out.println(tag.toBase64());
+        System.out.println(Base64.encode(tag.getData()));
+    }
+****/
 }
diff --git a/router/java/src/net/i2p/router/crypto/ratchet/RatchetTagSet.java b/router/java/src/net/i2p/router/crypto/ratchet/RatchetTagSet.java
index 2e1475daf399dbd5af3ed4e96f1b77e41256d9cd..06a06b049b0dad103ab8e5878aa8b3412c5e3878 100644
--- a/router/java/src/net/i2p/router/crypto/ratchet/RatchetTagSet.java
+++ b/router/java/src/net/i2p/router/crypto/ratchet/RatchetTagSet.java
@@ -227,7 +227,9 @@ class RatchetTagSet implements TagSetHandle {
     }
 
     /**
-     *  The identifier for the session.
+     *  The root key for the tag set.
+     *  Used to match the OB and IB ES tagset 0, where both
+     *  will have the same root key.
      *  Not used for cryptographic operations after setup.
      */
     public SessionKey getAssociatedKey() {
@@ -285,11 +287,6 @@ class RatchetTagSet implements TagSetHandle {
         return _created + Math.min(_timeout, RatchetSKM.SESSION_PENDING_DURATION_MS);
     }
 
-    /** for debugging */
-    public int getOriginalSize() {
-        return _originalSize;
-    }
-
     /**
      *  unused tags generated
      *  @return 0 for outbound
@@ -365,22 +362,6 @@ class RatchetTagSet implements TagSetHandle {
         return new SessionKey(_nextRootKey);
     }
 
-    /**
-     *  tags still available
-     *  inbound only
-     *  testing only
-     */
-    private List<RatchetSessionTag> getTags() {
-        if (_sessionTags == null)
-            return Collections.emptyList();
-        int sz = _sessionTags.size();
-        List<RatchetSessionTag> rv = new ArrayList<RatchetSessionTag>(sz);
-        for (int i = 0; i < sz; i++) {
-            rv.add(_sessionTags.valueAt(i));
-        }
-        return rv;
-    }
-
     /**
      *  first tag still available, or null
      *  inbound only
@@ -407,8 +388,8 @@ class RatchetTagSet implements TagSetHandle {
         if (idx < 0) {
             Log log = I2PAppContext.getGlobalContext().logManager().getLog(RatchetTagSet.class);
             if (log.shouldWarn())
-                log.warn("Tag not found " + Base64.encode(tag.getData()) +
-                         " Remaining tags: " + getTags(), new Exception());
+                log.warn("Tag not found " + tag.toBase64() +
+                         " in:\n" + toString(), new Exception());
             return null;
         }
         _acked = true;
@@ -443,7 +424,7 @@ class RatchetTagSet implements TagSetHandle {
             // dup or some other error
             Log log = I2PAppContext.getGlobalContext().logManager().getLog(RatchetTagSet.class);
             if (log.shouldWarn())
-                log.warn("No key found for tag " + Base64.encode(tag.getData()) + " at index " + idx +
+                log.warn("No key found for tag " + tag.toBase64() + " at index " + idx +
                          " tagnum = " + tagnum + " lastkey = " + _lastKey, new Exception());
             return null;
         }
@@ -540,14 +521,9 @@ class RatchetTagSet implements TagSetHandle {
         return new SessionKeyAndNonce(key, _id, _lastKey, _remoteKey);
     }
 
-    /**
-     *  For outbound only, call when we can use it.
-     */
-    public void setAcked() { _acked = true; }
-
     /**
      *  For inbound, returns true after first consume() call.
-     *  For outbound, returns true after set.
+     *  For outbound, returns true after first consumeNextKey() call.
      */
     public boolean getAcked() { return _acked; }
 
@@ -584,11 +560,11 @@ class RatchetTagSet implements TagSetHandle {
         PublicKey pk = getRemoteKey();
         if (pk != null)
             buf.append("\nRemote Public Key: ").append(pk.toBase64());
-        buf.append("\nRoot Key: ").append(_key.toBase64());
+        buf.append("\nRoot Key:   ").append(_key.toBase64());
         if (_tagsetKey != null)
             buf.append("\nTagset Key: ").append(_tagsetKey.toBase64());
         if (_nextKey != null)
-            buf.append("\nNext Key: ").append(_nextKey);
+            buf.append("\nNext Key:   ").append(_nextKey);
         int sz = size();
         buf.append("\nSize: ").append(sz)
            .append(" Orig: ").append(_originalSize)
@@ -601,36 +577,52 @@ class RatchetTagSet implements TagSetHandle {
                 RatchetSessionTag tag = _sessionTags.valueAt(i);
                 if (tag == null)
                     continue;
-                buf.append("\n  " + n + '\t' + Base64.encode(tag.getData()));
+                buf.append("\n  ").append(n).append('\t').append(tag.toBase64());
                 if (_sessionKeys != null) {
                     byte[] key = _sessionKeys.get(n);
                     if (key != null)
-                        buf.append('\t' + Base64.encode(key));
+                        buf.append('\t').append(Base64.encode(key));
                     else
-                        buf.append("\tdeferred");
+                        buf.append("\tTBD");
                 }
             }
         }
         return buf.toString();
     }
 
+     /**
+     *  tags still available
+     *  inbound only
+     *  testing only
+     */
 /****
+    private List<RatchetSessionTag> getTags() {
+        if (_sessionTags == null)
+            return Collections.emptyList();
+        int sz = _sessionTags.size();
+        List<RatchetSessionTag> rv = new ArrayList<RatchetSessionTag>(sz);
+        for (int i = 0; i < sz; i++) {
+            rv.add(_sessionTags.valueAt(i));
+        }
+        return rv;
+    }
+
     public static void main(String[] args) {
         SessionKey k1 = new SessionKey(new byte[32]);
         SessionKey k2 = new SessionKey(new byte[32]);
         System.out.println("Send test");
         HKDF hkdf = new HKDF(I2PAppContext.getGlobalContext());
-        RatchetTagSet rts = new RatchetTagSet(hkdf, k1, k2, 0, 0);
+        RatchetTagSet rts = new RatchetTagSet(hkdf, k1, k2, 0, 0, 0);
         System.out.println("TAGNUM\tTAG\t\tKEY");
         for (int i = 0; i < 20; i++) {
             RatchetSessionTag tag = rts.consumeNext();
             SessionKey key = rts.consumeNextKey();
-            System.out.println(i + "\t" + Base64.encode(tag.getData()) + '\t' + Base64.encode(key.getData()));
+            System.out.println(i + "\t" + tag.toBase64() + '\t' + key.toBase64());
         }
         System.out.println("Size now: " + rts.size());
         System.out.println("");
         System.out.println("Receive test in-order");
-        rts = new RatchetTagSet(hkdf, null, (PublicKey) null, k1, k2, 0, 0, 10, 50);
+        rts = new RatchetTagSet(hkdf, null, (PublicKey) null, k1, k2, 0, 0, 0, 10, 50);
         System.out.println("Size now: " + rts.size());
         List<RatchetSessionTag> tags = rts.getTags();
         int j = 0;
@@ -638,22 +630,22 @@ class RatchetTagSet implements TagSetHandle {
         for (RatchetSessionTag tag : tags) {
             SessionKey key = rts.consume(tag);
             if (key != null)
-                System.out.println(j++ + "\t" + Base64.encode(tag.getData()) + '\t' + Base64.encode(key.getData()));
+                System.out.println(j++ + "\t" + tag.toBase64() + '\t' + key.toBase64());
             else
-                System.out.println(j++ + "\t" + Base64.encode(tag.getData()) + "\t NOT FOUND");
+                System.out.println(j++ + "\t" + tag.toBase64() + "\t NOT FOUND");
         }
         for (int i = 11; i <= 20; i++) {
             RatchetSessionTag tag = rts.getFirstTag();
             SessionKey key = rts.consume(tag);
             if (key != null)
-                System.out.println(i + "\t" + Base64.encode(tag.getData()) + '\t' + Base64.encode(key.getData()));
+                System.out.println(i + "\t" + tag.toBase64() + '\t' + key.toBase64());
             else
-                System.out.println(i + "\t" + Base64.encode(tag.getData()) + "\t NOT FOUND");
+                System.out.println(i + "\t" + tag.toBase64() + "\t NOT FOUND");
         }
         System.out.println("Size now: " + rts.size());
         System.out.println("");
         System.out.println("Receive test out of order");
-        rts = new RatchetTagSet(hkdf, null, (PublicKey) null, k1, k2, 0, 0, 10, 50);
+        rts = new RatchetTagSet(hkdf, null, (PublicKey) null, k1, k2, 0, 0, 0, 10, 50);
         System.out.println("Size now: " + rts.size());
         tags = rts.getTags();
         List<RatchetSessionTag> origtags = new ArrayList<RatchetSessionTag>(tags);