⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 base64.java

📁 The Staged Event-Driven Architecture (SEDA) is a new design for building scalable Internet services.
💻 JAVA
字号:
/*
 * Copyright (c) 1999, 2000
 * Lehrstuhl fuer Prozessleittechnik (PLT), RWTH Aachen
 * D-52064 Aachen, Germany.
 * All rights reserved.
 *
 * This library is free software; you can redistribute it and/or modify
 * it under the terms of the GNU Library General Public License as
 * published by the Free Software Foundation; either version 2 of the
 * License, or (at your option) any later version.
 *
 * This library 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 Library General Public License for more details.
 *
 * You should have received a copy of the GNU Library General Public
 * License along with this program (see the file COPYING.LIB for more
 * details); if not, write to the Free Software Foundation, Inc.,
 * 675 Mass Ave, Cambridge, MA 02139, USA.
 */

package seda.sandStorm.lib.util;

import seda.sandStorm.api.*;
import seda.sandStorm.core.*;
import java.util.*;

/**
 * Encode and decode Base64 data. 
 */
public abstract class Base64 {

  private static final boolean DEBUG = false;

  /**
   * Converts data into base64 encoded data.
   *
   * @param data Data to be encoded.
   * @return A BufferElement with the data encoded in Base64.
   */
  public static BufferElement encode(BufferElement data) {

    byte input[] = data.getBytes();
    int offset = data.getOffset();
    int length = data.getSize();

    // Calculate length of encoded data including optional padding.
    int encodedLength = ((length + 2) / 3) * 4;
    byte output[] = new byte[encodedLength];
    int outoffset = 0;

    // Now do the encoding, thus inflating every three bytes of binary
    // data to four ASCII characters.
    int b1, b2, b3;
    int endPos = offset + length - 1 - 2;
    while (offset <= endPos) {
      b1 = input[offset++];
      b2 = input[offset++];
      b3 = input[offset++];

      output[outoffset++] = encodingBase64Alphabet[(b1 >>> 2) & 0x3F];
      output[outoffset++] = encodingBase64Alphabet[((b1 << 4) & 0x30) | ((b2 >>> 4) & 0xF)];
      output[outoffset++] = encodingBase64Alphabet[((b2 << 2) & 0x3C) | ((b3 >>> 6) & 0x03)];
      output[outoffset++] = encodingBase64Alphabet[b3 & 0x3F];
    }

    // If one or two bytes are left (because we work on blocks of three
    // bytes), convert them too and apply padding.

    endPos += 2; // now points to the last encodable byte
    if (offset <= endPos) {
      b1 = input[offset++];
      output[outoffset++] = encodingBase64Alphabet[(b1 >>> 2) & 0x3F];
      if (offset <= endPos) {
	b2 = input[offset++]; 
	output[outoffset++] = encodingBase64Alphabet[((b1 << 4) & 0x30) | ((b2 >>> 4) & 0xF)];
	output[outoffset++] = encodingBase64Alphabet[(b2 << 2) & 0x3C];
	output[outoffset] = '=';
      } else {
	output[outoffset++] = encodingBase64Alphabet[(b1 << 4) & 0x30];
	output[outoffset++] = '=';
	output[outoffset] = '=';
      }
    }
    return new BufferElement(output);
  }

  /**
   * Converts Base64 encoded data into binary data.
   *
   * @param data Base64 encoded data.
   * @return A BufferElement containing the decoded data.
   */
  public static BufferElement decode(BufferElement data) {

    byte input[] = data.getBytes();
    int offset = data.getOffset();
    int length = data.getSize();

    // Check if we need to squash the data
    if ((offset != 0) || (length != input.length)) {
      byte input2[] = new byte[length];
      System.arraycopy(input, offset, input2, 0, length);
      input = input2;
    }

    // Strip out whitespace 
    StringTokenizer st = new StringTokenizer(new String(input), " \t\r\n", false);
    String newinput = new String();
    while (st.hasMoreTokens()) {
      newinput += st.nextToken();
    }
    input = newinput.getBytes();
    offset = 0;
    length = input.length;

    // Calculate length of decoded data including optional padding.
    int endPos = offset + length - 1;
    // Determine the length of data to be decoded. Optional padding has
    // to be removed first.
    if (DEBUG) System.err.println("endPos: "+endPos);
    while ((endPos >= 0) && 
	((input[endPos] == '=') ||
 	 (input[endPos] == '\r') ||
	 (input[endPos] == '\n'))) {
      endPos--;
    }
    if (DEBUG) System.err.println("endPos fixed to: "+endPos);

    int decodedLength = endPos - offset - length / 4 + 1;
    byte output[] = new byte[decodedLength];
    int outoffset = 0;

    // Now do the four-to-three entities/letters/bytes/whatever
    // conversion. We chew on as many four-letter groups as we can,
    // converting them into three byte groups.

    byte b1, b2, b3, b4;
    // This points to the last letter in the last four-letter group
    int stopPos = endPos - 3; 
    while (offset <= stopPos) {
      if (DEBUG) System.err.print("b1: "+input[offset]+" -> ");
      b1 = decodingBase64Alphabet[input[offset++]];
      if (DEBUG) System.err.print(b1+"\nb2: "+input[offset]+" -> ");
      b2 = decodingBase64Alphabet[input[offset++]];
      if (DEBUG) System.err.print(b2+"\nb3: "+input[offset]+" -> ");
      b3 = decodingBase64Alphabet[input[offset++]];
      if (DEBUG) System.err.print(b3+"\nb4: "+input[offset]+" -> ");
      b4 = decodingBase64Alphabet[input[offset++]];
      if (DEBUG) System.err.println(b4);
      output[outoffset++] = (byte)(((b1 << 2) & 0xFF) | ((b2 >>> 4) & 0x03));
      output[outoffset++] = (byte)(((b2 << 4) & 0xFF) | ((b3 >>> 2) & 0x0F));
      output[outoffset++] = (byte)(((b3 << 6) & 0xFF) | (b4 & 0x3F));
    }

    // If one, two or three letters from the base64 encoded data are
    // left, convert them too.
    // Hack Note(tm): if the length of encoded data is not a multiple
    // of four, then padding must occur ('='). As the decoding alphabet
    // contains zeros everywhere with the exception of valid letters,
    // indexing into the mapping is just fine and reliefs us of the
    // pain to check everything and make thus makes the code better.

    if (DEBUG) System.err.println("offset "+offset+", endPos "+endPos+", length "+length);

    if (offset <= endPos) {
      if (DEBUG) System.err.print("END b1: "+input[offset]+" -> ");
      b1 = decodingBase64Alphabet[input[offset++]];
      if (DEBUG) System.err.print(b1+"\nEND b2: "+input[offset]+" -> ");
      b2 = decodingBase64Alphabet[input[offset++]];
      if (DEBUG) System.err.println(b2);
      output[outoffset++] = (byte)(((b1 << 2) & 0xFF) | ((b2 >>> 4) & 0x03));
      if (offset <= endPos) { 
	b3 = decodingBase64Alphabet[input[offset]];
	output[outoffset++] = (byte)(((b2 << 4) & 0xFF) | ((b3 >>> 2) & 0x0F));
      }
    }
    return new BufferElement(output);
  }

  /**
   * Mapping from binary 0-63 to base64 alphabet according to RFC 2045.
   */
  private static final byte [] encodingBase64Alphabet = {
    'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M',
    'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z',
    'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm',
    'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z',
    '0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
    '+', '/'
  };

  /**
   * Mapping from base64 alphabet to binary 0-63.
   */
  private static final byte [] decodingBase64Alphabet;

  /**
   * The class initializer is responsible to set up the mapping from the
   * base64 alphabet (ASCII-based) to binary 0-63.
   */
  static {
    decodingBase64Alphabet = new byte[256];
    for ( int i = 0; i < 64; ++i ) {
      decodingBase64Alphabet[encodingBase64Alphabet[i]] = (byte)(i & 0xff);
    }
  }

}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -