
com.lambdaworks.codec.Base64 Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of scrypt Show documentation
Show all versions of scrypt Show documentation
Java implementation of scrypt
The newest version!
// Copyright (C) 2011 - Will Glozer. All rights reserved.
package com.lambdaworks.codec;
import java.util.Arrays;
/**
* High-performance base64 codec based on the algorithm used in Mikael Grev's MiG Base64.
* This implementation is designed to handle base64 without line splitting and with
* optional padding. Alternative character tables may be supplied to the {@code encode}
* and {@code decode} methods to implement modified base64 schemes.
*
* Decoding assumes correct input, the caller is responsible for ensuring that the input
* contains no invalid characters.
*
* @author Will Glozer
*/
public class Base64 {
private static final char[] encode = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/".toCharArray();
private static final int[] decode = new int[128];
private static final char pad = '=';
static {
Arrays.fill(decode, -1);
for (int i = 0; i < encode.length; i++) {
decode[encode[i]] = i;
}
decode[pad] = 0;
}
/**
* Decode base64 chars to bytes.
*
* @param chars Chars to encode.
*
* @return Decoded bytes.
*/
public static byte[] decode(char[] chars) {
return decode(chars, decode, pad);
}
/**
* Encode bytes to base64 chars, with padding.
*
* @param bytes Bytes to encode.
*
* @return Encoded chars.
*/
public static char[] encode(byte[] bytes) {
return encode(bytes, encode, pad);
}
/**
* Encode bytes to base64 chars, with optional padding.
*
* @param bytes Bytes to encode.
* @param padded Add padding to output.
*
* @return Encoded chars.
*/
public static char[] encode(byte[] bytes, boolean padded) {
return encode(bytes, encode, padded ? pad : 0);
}
/**
* Decode base64 chars to bytes using the supplied decode table and padding
* character.
*
* @param src Base64 encoded data.
* @param table Decode table.
* @param pad Padding character.
*
* @return Decoded bytes.
*/
public static byte[] decode(char[] src, int[] table, char pad) {
int len = src.length;
if (len == 0) return new byte[0];
int padCount = (src[len - 1] == pad ? (src[len - 2] == pad ? 2 : 1) : 0);
int bytes = (len * 6 >> 3) - padCount;
int blocks = (bytes / 3) * 3;
byte[] dst = new byte[bytes];
int si = 0, di = 0;
while (di < blocks) {
int n = table[src[si++]] << 18 | table[src[si++]] << 12 | table[src[si++]] << 6 | table[src[si++]];
dst[di++] = (byte) (n >> 16);
dst[di++] = (byte) (n >> 8);
dst[di++] = (byte) n;
}
if (di < bytes) {
int n = 0;
switch (len - si) {
case 4: n |= table[src[si+3]];
case 3: n |= table[src[si+2]] << 6;
case 2: n |= table[src[si+1]] << 12;
case 1: n |= table[src[si]] << 18;
}
for (int r = 16; di < bytes; r -= 8) {
dst[di++] = (byte) (n >> r);
}
}
return dst;
}
/**
* Encode bytes to base64 chars using the supplied encode table and with
* optional padding.
*
* @param src Bytes to encode.
* @param table Encoding table.
* @param pad Padding character, or 0 for no padding.
*
* @return Encoded chars.
*/
public static char[] encode(byte[] src, char[] table, char pad) {
int len = src.length;
if (len == 0) return new char[0];
int blocks = (len / 3) * 3;
int chars = ((len - 1) / 3 + 1) << 2;
int tail = len - blocks;
if (pad == 0 && tail > 0) chars -= 3 - tail;
char[] dst = new char[chars];
int si = 0, di = 0;
while (si < blocks) {
int n = (src[si++] & 0xff) << 16 | (src[si++] & 0xff) << 8 | (src[si++] & 0xff);
dst[di++] = table[(n >>> 18) & 0x3f];
dst[di++] = table[(n >>> 12) & 0x3f];
dst[di++] = table[(n >>> 6) & 0x3f];
dst[di++] = table[n & 0x3f];
}
if (tail > 0) {
int n = (src[si] & 0xff) << 10;
if (tail == 2) n |= (src[++si] & 0xff) << 2;
dst[di++] = table[(n >>> 12) & 0x3f];
dst[di++] = table[(n >>> 6) & 0x3f];
if (tail == 2) dst[di++] = table[n & 0x3f];
if (pad != 0) {
if (tail == 1) dst[di++] = pad;
dst[di] = pad;
}
}
return dst;
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy