Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/338.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 河豚示例,其中自动按大小填充和取消填充键_Java_Encryption_Cryptography_Blowfish - Fatal编程技术网

Java 河豚示例,其中自动按大小填充和取消填充键

Java 河豚示例,其中自动按大小填充和取消填充键,java,encryption,cryptography,blowfish,Java,Encryption,Cryptography,Blowfish,Blowfish具有强大的加密能力,可以使用多达56字节的密钥(448位密钥)。 密钥必须是8字节的倍数(最多56字节) 我想写的例子将自动填充和取消填充键的大小。因为Blowfish创建了8字节加密输出的块,所以输出也被填充并添加到8字节的倍数 实际上想编写java代码来模拟- 我正在使用工具的信息- ALGORITM = "Blowfish"; HEX KEY = "92514c2df6e22f079acabedce08f8ac3"; PLAIN_TEXT = "sangasong@son

Blowfish具有强大的加密能力,可以使用多达56字节的密钥(448位密钥)。 密钥必须是8字节的倍数(最多56字节)

我想写的例子将自动填充和取消填充键的大小。因为Blowfish创建了8字节加密输出的块,所以输出也被填充并添加到8字节的倍数

实际上想编写java代码来模拟-

我正在使用工具的信息-

ALGORITM = "Blowfish";
HEX KEY = "92514c2df6e22f079acabedce08f8ac3";
PLAIN_TEXT = "sangasong@song.com"
工具返回-

CD3A08381467823D4013960E75E465F0B00C5E3BAEFBECBB 
请建议

尝试了java代码:

public class TestBlowfish
{
    final String KEY = "92514c2df6e22f079acabedce08f8ac3";
    final String PLAIN_TEXT = "sangasong@song.com";
    byte[] keyBytes = DatatypeConverter.parseHexBinary(KEY); 
}

public static void main(String[] args) throws Exception 
{
    try 
    {
        byte[] encrypted = encrypt(keyBytes, PLAIN_TEXT);
        System.out.println( "Encrypted hex: " + Hex.encodeHexString(encrypted));

    }catch (GeneralSecurityException e) 
    {
        e.printStackTrace();
    }
}

private static byte[] encrypt(byte[] key, String plainText) throws GeneralSecurityException
{
    SecretKey secret_key = new SecretKeySpec(key, "Blowfish");
    Cipher cipher = Cipher.getInstance("Blowfish");
    cipher.init(Cipher.ENCRYPT_MODE, secret_key);

    return cipher.doFinal(plainText.getBytes());
} 
结果-

Encrypted hex: 525bd4bd786a545fe7786b0076b3bbc2127425f0ea58c29d

我不确定这个问题的相关性:我认为没有必要获得与此脚本相同的输出:您无法保证它的安全性/效率。。。 引起我注意的是填充部分:有几种填充块的解决方案,其中一些很简单,但非常不安全,可能这个脚本使用了其中一种“糟糕”的解决方案

您是否检查了您的程序是否能够检索到正确的纯文本?(您需要对匹配的
解密
函数进行编码)。
如果是这样的话,这意味着它工作正常,可以用于任何您最初的目的,无论此脚本的输出是什么…

因此,脚本使用了错误版本的PKCS#7填充,当输入大小已经可以除以块大小时,它不会填充-键和明文都是如此。此外,它使用ECB模式加密。这两种方法都不应该在现实生活中使用

以下代码要求将Bouncy Castle提供程序添加到JCE(
Service.addProvider(new BouncyCastleProvider())
),并且Bouncy Castle库的十六进制类位于类路径中

警告:仅在有限输入下测试,如果钥匙尺寸大于最大值,则不会切割钥匙尺寸

警告:以下代码在加密方面不可靠

import org.bouncycastle.util.encoders.Hex;

public class BadBlowfish {
        private static SecretKey createKey(String theKey) {
        final byte[] keyData = theKey.getBytes(StandardCharsets.US_ASCII);
        final byte[] paddedKeyData = halfPadPKCS7(keyData, 8);
        SecretKey secret = new SecretKeySpec(paddedKeyData, "Blowfish");
        return secret;
    }

    private static byte[] halfUnpadPKCS7(final byte[] paddedPlaintext, int blocksize) {
        int b = paddedPlaintext[paddedPlaintext.length - 1] & 0xFF;
        if (b > 0x07) {
            return paddedPlaintext.clone();
        }
        return Arrays.copyOf(paddedPlaintext, paddedPlaintext.length - b);
    }

    private static byte[] halfPadPKCS7(final byte[] plaintext, int blocksize) {
        if (plaintext.length % blocksize == 0) {
            return plaintext.clone();
        }

        int newLength = (plaintext.length / blocksize + 1) * blocksize;
        int paddingLength = newLength - plaintext.length;

        final byte[] paddedPlaintext = Arrays.copyOf(plaintext, newLength);
        for (int offset = plaintext.length; offset < newLength; offset++) {
            paddedPlaintext[offset] = (byte) paddingLength;
        }
        return paddedPlaintext;
    }

    public static void main(String[] args) throws Exception {
        Cipher cipher = Cipher.getInstance("Blowfish/ECB/NoPadding");
        SecretKey key = createKey("123456781234567");
        cipher.init(Cipher.DECRYPT_MODE, key);
        byte[] plaintextData = cipher.doFinal(Hex.decode("085585C60B3D23257763E6D8BB0A0891"));
        byte[] unpaddedPlaintextData = halfUnpadPKCS7(plaintextData, cipher.getBlockSize());

        String plaintextHex = Hex.toHexString(unpaddedPlaintextData);
        System.out.println(plaintextHex);
        String plaintext = new String(unpaddedPlaintextData, StandardCharsets.UTF_8);
        System.out.println(plaintext);
    }
}
import org.bounchycastle.util.encoders.Hex;
公共级河豚{
私有静态SecretKey createKey(字符串theKey){
最终字节[]keyData=key.getBytes(标准字符集.US\u ASCII);
最后一个字节[]paddedKeyData=halfPadPKCS7(keyData,8);
SecretKey secret=新的SecretKeySpec(paddedKeyData,“河豚”);
归还秘密;
}
专用静态字节[]半UNPADPKCS7(最终字节[]填充明文,int blocksize){
int b=paddedPlaintext[paddedPlaintext.length-1]&0xFF;
如果(b>0x07){
返回paddedPlaintext.clone();
}
返回Arrays.copyOf(paddedPlaintext,paddedPlaintext.length-b);
}
专用静态字节[]halfPadPKCS7(最终字节[]明文,int blocksize){
if(明文.length%blocksize==0){
返回明文.clone();
}
int newLength=(plaintext.length/blocksize+1)*blocksize;
int paddingLength=newLength-plaintext.length;
最后一个字节[]paddedPlaintext=Arrays.copyOf(纯文本,newLength);
对于(int offset=plaintext.length;offset
建议。。。什么?到目前为止你试过什么吗?你为什么要按键?它应该以正确的大小生成。“那你为什么要解开它呢?”科科努普,我已经编辑了我的问题。请看看到目前为止我都试了些什么。很好!现在您是否运行它并遇到任何错误?没有错误。但输出和工具不同。我们的客户使用webnet77工具进行加密,并将加密代码发送给我们。在原始帖子中添加输出。@Coconop实际上尝试了各种方式和顺序进行加密,但从未得到与该工具相同的结果。非常感谢@owlstead。我对你的代码做了一些小的修改,得到了我想要的确切的解决方案。帮了大忙!!你认为当我从URL发送加密代码时,它不会工作吗??由于独立java程序工作得很好…但我遇到了一个异常-获取javax.crypto.IllegalBlockSizeException:使用填充密码解密时,输入长度必须是8的倍数?始终URL编码密文。确保发送和接收密文时密文是相同的。