2009-10-29 73 views

回答

2

从旧的代码:

public void testSymCypher(SecretKey k, String str) 
     throws BadPaddingException, IllegalBlockSizeException, 
     InvalidAlgorithmParameterException, InvalidKeyException, 
     NoSuchAlgorithmException, NoSuchPaddingException 
{ 
    Cipher cip = Cipher.getInstance("DESede/CBC/PKCS5Padding"); 
    cip.init(Cipher.ENCRYPT_MODE,k); 
    byte[] ciphered = cip.doFinal(str.getBytes()); 
    byte iv[] = cip.getIV(); 

    // printing the ciphered string 
    printHexadecimal(ciphered); 

    IvParameterSpec dps = new IvParameterSpec(iv); 
    cip.init(Cipher.DECRYPT_MODE,k,dps); 
    byte[] deciphered = cip.doFinal(ciphered); 

    // printing the deciphered string 
    printHexadecimal(deciphered); 
} 

比DESede的其他使用通知中的Java JDK可用6:

  • DESede/CBC/NoPadding(168)
  • DESede/CBC/PKCS5Padding(168)

还有ECB模式下可用(但要carreful不使用它的两倍!),你不需要在这种情况下,使用第四部分:

  • DESede/ECB/NoPadding(168)
  • DESede/ECB/PKCS5Padding(168)

要生成DESede键:

KeyGenerator generatorDes = KeyGenerator.getInstance("DESede"); 
    SecretKey skaes = generatorDes.generateKey(); 

最后,我从推荐阅读SUN如果this document你需要对Java和加密工作

+0

此代码给了我一个java.security.InvalidKeyException:无效密钥长度:8个字节\t在com.sun.crypto.provider.DESedeCipher.engineGetKeySize(DashoA13 * ..) – ScArcher2 2009-10-29 19:20:45

+0

我想这是因为我犯了一个错误用的KeyGenerator :它是DESede而不是DES。 如果您使用自己的密钥,请检查您的密钥大小(它似乎与您使用的3DES密钥的种类有关,因为我不太了解它,请参阅3DES的维基百科页面)。 – Kartoch 2009-10-29 21:16:03

1

我们使用基于密码的DES加密这个小帮手类从字符串到十六进制字符串和背部 - 不知道如何得到这个使用3DES工作虽然:

import java.security.spec.KeySpec; 

import javax.crypto.Cipher; 
import javax.crypto.SecretKey; 
import javax.crypto.SecretKeyFactory; 
import javax.crypto.spec.PBEKeySpec; 
import javax.crypto.spec.PBEParameterSpec; 

public class DesHelper { 
    private static org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(DesHelper.class); 

    static final byte[] SALT = { (byte) 0x09, /* snip - randomly chosen but static salt*/ }; 
    static final int ITERATIONS = 11; 

    private Cipher _ecipher; 
    private Cipher _dcipher; 

    public DesHelper(final String passphrase) { 
     try { 
      final PBEParameterSpec params = new PBEParameterSpec(SALT, ITERATIONS); 

      final KeySpec keySpec = new PBEKeySpec(passphrase.toCharArray()); 
      final SecretKey key = SecretKeyFactory.getInstance("PBEWithMD5AndDES") 
        .generateSecret(keySpec); 

      _ecipher = Cipher.getInstance(key.getAlgorithm()); 
      _dcipher = Cipher.getInstance(key.getAlgorithm()); 
      _ecipher.init(Cipher.ENCRYPT_MODE, key, params); 
      _dcipher.init(Cipher.DECRYPT_MODE, key, params); 

     } catch (final Exception e) { 
      throw new RuntimeException(e); 
     } 
    } 

    public String encrypt(final String string) { 
     try { 
      // Encode the string into bytes using utf-8 
      final byte[] bytes = string.getBytes("UTF-8"); 

      // Encrypt 
      final byte[] enc = _ecipher.doFinal(bytes); 

      // Encode bytes to base64 to get a string 
      return bytesToHex(enc); 
     } catch (final Exception e) { 
      throw new RuntimeException(e); 
     } 
    } 

    public String decrypt(final String str) { 
     try { 
      // Decode base64 to get bytes 
      final byte[] dec = hexToBytes(str); 

      // Decrypt 
      final byte[] utf8 = _dcipher.doFinal(dec); 

      // Decode using utf-8 
      return new String(utf8, "UTF8"); 
     } catch (final Exception e) { 
      log.info("decrypting string failed: " + str + " (" + e.getMessage() + ")"); 
      return null; 
     } 
    } 

    private static String bytesToHex(final byte[] bytes) { 
     final StringBuilder buf = new StringBuilder(bytes.length * 2); 
     for (final byte b : bytes) { 
      final String hex = Integer.toHexString(0xff & b); 
      if (hex.length() == 1) { 
       buf.append("0"); 
      } 
      buf.append(hex); 
     } 
     return buf.toString(); 
    } 

    private static byte[] hexToBytes(final String hex) { 
     final byte[] bytes = new byte[hex.length()/2]; 
     for (int i = 0; i < bytes.length; i++) { 
      bytes[i] = (byte) Integer.parseInt(hex.substring(i * 2, i * 2 + 2), 16); 
     } 
     return bytes; 
    } 
} 

你会使用这个类是这样的:

public static void main(final String[] args) { 
    final DesHelper h = new DesHelper("blabla"); 
    System.out.println(h.decrypt(h.encrypt("foobar"))); 
} 
0

您也可以考虑使用流密码(例如,3DES块加密顶部的OFB或CTR模式),以便您不必处理将字符串填充到密码块大小的倍数。