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

📄 blockcipher.java

📁 一个非常好的ssh客户端实现
💻 JAVA
字号:
/****************************************************************************** * * Copyright (c) 1999-2003 AppGate Network Security AB. All Rights Reserved. *  * This file contains Original Code and/or Modifications of Original Code as * defined in and that are subject to the MindTerm Public Source License, * Version 2.0, (the 'License'). You may not use this file except in compliance * with the License. *  * You should have received a copy of the MindTerm Public Source License * along with this software; see the file LICENSE.  If not, write to * AppGate Network Security AB, Otterhallegatan 2, SE-41118 Goteborg, SWEDEN * *****************************************************************************/package com.mindbright.security.cipher;import com.mindbright.jca.security.SecureRandom;import com.mindbright.jca.security.Key;import com.mindbright.jca.security.InvalidKeyException;import com.mindbright.jca.security.spec.AlgorithmParameterSpec;import com.mindbright.jce.crypto.Cipher;import com.mindbright.jce.crypto.CipherSpi;import com.mindbright.jce.crypto.spec.IvParameterSpec;import com.mindbright.jce.crypto.spec.SecretKeySpec;public abstract class BlockCipher extends CipherSpi {    // Default is to ECB    //    final static int MODE_ECB = 0;    final static int MODE_CBC = 1;    final static int MODE_CFB = 2;    final static int MODE_OFB = 3;    final static int MODE_CTR = 4;    byte[] iv;    byte[] tmpBlk;    byte[] ctr;    int    opMode;    int    feedbackMode;    int    streamBits;    int    blockSize;    boolean pkcs5Padding;    boolean ctrInit = false;    protected int engineDoFinal(byte[] input, int inputOffset, int inputLen,				byte[] output, int outputOffset) {	int n = 0;	switch(feedbackMode) {	case MODE_ECB:	    n = internalDoFinalECB(input, inputOffset, inputLen,				   output, outputOffset);	    break;	case MODE_CBC:	    n = internalDoFinalCBC(input, inputOffset, inputLen,				   output, outputOffset);	    break;	case MODE_CFB:	    n = internalDoFinalCFB(input, inputOffset, inputLen,				   output, outputOffset);	    break;	case MODE_OFB:	    n = internalDoFinalOFB(input, inputOffset, inputLen,				   output, outputOffset);	case MODE_CTR: 	    n = internalDoFinalCTR(input, inputOffset, inputLen, 				   output, outputOffset);	    break;	}	return n;    }    private final int internalDoFinalECB(byte[] input, int inputOffset, int inputLen,					 byte[] output, int outputOffset) {	int nBlocks = inputLen / blockSize;	if(opMode == Cipher.ENCRYPT_MODE) {	    for(int bc = 0; bc < nBlocks; bc++) {		blockEncrypt(input, inputOffset, output, outputOffset);		inputOffset  += blockSize;		outputOffset += blockSize;	    }	} else {	    for(int bc = 0; bc < nBlocks; bc++) {		blockDecrypt(input, inputOffset, output, outputOffset);		inputOffset  += blockSize;		outputOffset += blockSize;	    }	}	return inputLen;    }    private final int internalDoFinalCBC(byte[] input, int inputOffset,					 int inputLen,					 byte[] output, int outputOffset) {	int nBlocks = inputLen / blockSize;	if(opMode == Cipher.ENCRYPT_MODE) {	    for(int bc = 0; bc < nBlocks; bc++) {		blockXor(input, inputOffset, blockSize, iv, 0);		blockEncrypt(iv, 0, output, outputOffset);		System.arraycopy(output, outputOffset, iv, 0, blockSize);		inputOffset  += blockSize;		outputOffset += blockSize;	    }	    // !!! TODO Move out to engineDoFinal	    if(pkcs5Padding) {		int rest = inputLen % blockSize;		int pad  = blockSize - rest;		for(int i = 0; i < blockSize; i++) {		    if(i < rest) {			iv[i] ^= input[inputOffset++];		    } else {			iv[i] ^= (byte)pad;		    }		}		blockEncrypt(iv, 0, output, outputOffset);		System.arraycopy(output, outputOffset, iv, 0, blockSize);		inputLen += (blockSize - rest);	    }	} else {	    for(int bc = 0; bc < nBlocks; bc++) {		blockDecrypt(input, inputOffset, tmpBlk, 0);		for(int i = 0; i < blockSize; i++) {		    tmpBlk[i] ^= iv[i];		    iv[i] = input[inputOffset + i];		    output[outputOffset + i] = tmpBlk[i];		}		inputOffset  += blockSize;		outputOffset += blockSize;	    }	}	return inputLen;    }    private final int internalDoFinalCFB(byte[] input, int inputOffset, int inputLen,					 byte[] output, int outputOffset) {	int endOffset = inputOffset + inputLen;	int bs        = blockSize;	if(opMode == Cipher.ENCRYPT_MODE) {	    for(; inputOffset < endOffset;) {		blockEncrypt(iv, 0, iv, 0);		if(inputOffset + bs > endOffset) {		    bs = endOffset - inputOffset;		} 		blockXor(input, inputOffset, bs, iv, 0);		System.arraycopy(iv, 0, output, outputOffset, bs);		inputOffset  += bs;		outputOffset += bs;	    }	} else {	    for(; inputOffset < endOffset;) {		blockEncrypt(iv, 0, tmpBlk, 0);		if(inputOffset + bs > endOffset) {		    bs = endOffset - inputOffset;		}		System.arraycopy(input, inputOffset, iv, 0, bs);		blockXor(iv, 0, bs, tmpBlk, 0);		System.arraycopy(tmpBlk, 0, output, outputOffset, bs);		inputOffset  += bs;		outputOffset += bs;	    }	}	return inputLen;    }    private final int internalDoFinalOFB(byte[] input, int inputOffset, int inputLen,					 byte[] output, int outputOffset) {	int endOffset = inputOffset + inputLen;	for(; inputOffset < endOffset;) {	    blockEncrypt(iv, 0, iv, 0);	    int srcLen = ((inputOffset + blockSize <= endOffset) ?			  blockSize : endOffset - inputOffset);	    for(int i = 0; i < srcLen; i++) {		output[outputOffset + i] = input[inputOffset + i];		output[outputOffset + i] ^= iv[i];	    }	    inputOffset  += blockSize;	    outputOffset += blockSize;	}	return inputLen;    }    private final int internalDoFinalCTR(byte[] input, int inputOffset,					 int inputLen,					 byte[] output, int outputOffset) {	if (!ctrInit) {	    ctr = new byte[blockSize]; // 'X' in draft	    System.arraycopy(iv, 0, ctr, 0, blockSize);	    ctrInit = true;	}	int nBlocks = inputLen / blockSize;	for(int bc = 0; bc < nBlocks; bc++) {	    	    blockEncrypt(ctr, 0, tmpBlk, 0);	    System.arraycopy(input, inputOffset, output, outputOffset,			     blockSize);	    blockXor(tmpBlk, 0, blockSize, output, outputOffset);	    inputOffset  += blockSize;	    outputOffset += blockSize;	    nboIncr(ctr);	}	return inputLen;    }    private static final void blockXor(byte[] src, int srcOffset, int srcLen,				       byte[] dest, int destOffset) {	for(; srcLen > 0; srcLen--) {	    dest[destOffset++] ^= src[srcOffset++];	}    }    protected static final int getIntMSBO(byte[] src, int srcOffset) {	return (((src[srcOffset    ] & 0xff) << 24) |		((src[srcOffset + 1] & 0xff) << 16) |		((src[srcOffset + 2] & 0xff) << 8)  |		( src[srcOffset + 3] & 0xff));    }    protected static final int getIntLSBO(byte[] src, int srcOffset) {	return (( src[srcOffset    ] & 0xff)        |		((src[srcOffset + 1] & 0xff) << 8)  |		((src[srcOffset + 2] & 0xff) << 16) |		((src[srcOffset + 3] & 0xff) << 24));    }    protected static final void putIntMSBO(int val, byte[] dest, int destOffset) {	dest[destOffset    ] = (byte)((val >>> 24) & 0xff);	dest[destOffset + 1] = (byte)((val >>> 16) & 0xff);	dest[destOffset + 2] = (byte)((val >>> 8 ) & 0xff);	dest[destOffset + 3] = (byte)( val         & 0xff);    }    protected static final void putIntLSBO(int val, byte[] dest, int destOffset) {	dest[destOffset    ] = (byte)( val         & 0xff);	dest[destOffset + 1] = (byte)((val >>> 8 ) & 0xff);	dest[destOffset + 2] = (byte)((val >>> 16) & 0xff);	dest[destOffset + 3] = (byte)((val >>> 24) & 0xff);    }    protected static final void nboIncr(byte[] b) {	for (int i = b.length-1; i >= 0 && 0 == ++b[i]; i--);    }    protected int engineGetBlockSize() {	return getBlockSize();    }    protected byte[] engineGetIV() {	return iv;    }    protected int engineGetOutputSize(int inputLen) {	// !!! TODO: fix this	int bs = getBlockSize();	if(((inputLen % bs) > 0) || pkcs5Padding) {	    inputLen += (bs - (inputLen % bs));	}	return inputLen;    }    /*    protected AlgorithmParameters engineGetParameters() {	return null;    }    */    /*    protected void engineInit(int opmode, Key key,			      AlgorithmParameters params,			      SecureRandom random) {	engineInit(opmode, key, (AlgorithmParameterSpec)null, random);    }    */    protected void engineInit(int opmode, Key key,			      AlgorithmParameterSpec params,			      SecureRandom random) throws InvalidKeyException {	initializeKey(((SecretKeySpec)key).getEncoded());	blockSize = getBlockSize();	if(params == null) {	    params = new IvParameterSpec(new byte[blockSize]);	}	this.opMode = opmode;	this.iv     = ((IvParameterSpec)params).getIV();	this.tmpBlk = new byte[blockSize];    }    protected void engineInit(int opmode, Key key,			      SecureRandom random) throws InvalidKeyException {	engineInit(opmode, key, (AlgorithmParameterSpec)null, random);    }    protected void engineSetMode(String mode) {	if("CBC".equalsIgnoreCase(mode)) {	    feedbackMode = MODE_CBC;	} else if("ECB".equalsIgnoreCase(mode)) {	    feedbackMode = MODE_ECB;	} else if("CFB".equalsIgnoreCase(mode)) {	    feedbackMode = MODE_CFB;	} else if("OFB".equalsIgnoreCase(mode)) {	    feedbackMode = MODE_OFB;	} else if("CTR".equalsIgnoreCase(mode)) {	    feedbackMode = MODE_CTR;	}    }    protected void engineSetPadding(String padding) {	if("PKCS5Padding".equalsIgnoreCase(padding)) {	    pkcs5Padding = true;	} else if("NoPadding".equalsIgnoreCase(padding)) {	} else if("SSL3Padding".equalsIgnoreCase(padding)) {	} else {	    // !!! TODO Throw NoSuchPaddingException	}    }    public abstract int getBlockSize();    public abstract void initializeKey(byte[] key) throws InvalidKeyException;    public abstract void blockEncrypt(byte[] in, int offset,				      byte[] out, int outOffset);    public abstract void blockDecrypt(byte[] in, int offset,				      byte[] out, int outOffset);}

⌨️ 快捷键说明

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