@Override
        public byte[] decode(final byte[] in) {
            // Ignore trailing '=' padding and whitespace from the input.
            int limit = in.length;
            for (; limit > 0; limit--) {
                final byte c = in[limit - 1];
                if (c != '=' && c != '\n' && c != '\r' && c != ' ' && c != '\t') {
                    break;
                }
            }

            // If the input includes whitespace, this output array will be longer than necessary.
            final byte[] out = new byte[(int) (limit * 6L / 8L)];
            int outCount = 0;
            int inCount = 0;

            int word = 0;
            for (int pos = 0; pos < limit; pos++) {
                final byte c = in[pos];

                final int bits;
                if (c == '.' || c == '/' || (c >= 'A' && c <= 'z') || (c >= '0' && c <= '9')) {
                    bits = DECODE_TABLE[c];
                } else if (c == '\n' || c == '\r' || c == ' ' || c == '\t') {
                    continue;
                } else {
                    throw new IllegalArgumentException("invalid character to decode: " + c);
                }

                // Append this char's 6 bits to the word.
                word = (word << 6) | (byte) bits;

                // For every 4 chars of input, we accumulate 24 bits of output. Emit 3 bytes.
                inCount++;
                if (inCount % 4 == 0) {
                    out[outCount++] = (byte) (word >> 16);
                    out[outCount++] = (byte) (word >> 8);
                    out[outCount++] = (byte) word;
                }
            }

            final int lastWordChars = inCount % 4;
            if (lastWordChars == 1) {
                // We read 1 char followed by "===". But 6 bits is a truncated byte! Fail.
                return new byte[0];
            } else if (lastWordChars == 2) {
                // We read 2 chars followed by "==". Emit 1 byte with 8 of those 12 bits.
                word = word << 12;
                out[outCount++] = (byte) (word >> 16);
            } else if (lastWordChars == 3) {
                // We read 3 chars, followed by "=". Emit 2 bytes for 16 of those 18 bits.
                word = word << 6;
                out[outCount++] = (byte) (word >> 16);
                out[outCount++] = (byte) (word >> 8);
            }

            // If we sized our out array perfectly, we're done.
            if (outCount == out.length) {
                return out;
            }

            // Copy the decoded bytes to a new, right-sized array.
            final byte[] prefix = new byte[outCount];
            System.arraycopy(out, 0, prefix, 0, outCount);
            return prefix;
        }
A mod of Square's Okio Base64 encoder
<p>
Original author: Alexander Y. Kleymenov

@see <a href="https://github.com/square/okio/blob/okio-parent-1.15.0/okio/src/main/java/okio/Base64.java">Okio</a>
crypto/support/hashes/bcrypt/src/main/java/org/apache/shiro/crypto/support/hashes/bcrypt/OpenBSDBase64.java