有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

加密Java密码。doFinal()写入额外字节

我正在使用Java密码和AES实现加密/解密。除了对doFinal()的调用中额外写入了5个字节之外,一切都正常。最后,我得到了一个正确解码的字符串,并附加了5个额外字节

我认为原因是整个16字节的块正在被写入。我看到写了3个16字节的块,包括最后一个。输入的加密文件是64字节。未加密文本应为43字节

doFinal的文档表明,它可以返回写入输出缓冲区的字节数。然而,它是0,16,16,16。我尝试了各种形式的doFinal和update,但行为没有改变

写一个完整的块是有道理的,因为大多数算法都是这样操作的。然而,如果它不告诉我输出数据的大小,我该如何防止多余的数据

也许我应该使用另一种算法吗?AES256是一个要求,但我想知道不同的块类型或填充类型是否允许它写入正确的字节数

有什么指导吗

为了(一些)简洁而剪短:

decryptCipher = Cipher.getInstance("AES");
decryptCipher.init(Cipher.DECRYPT_MODE, aesKey);

商业是解密程序的一部分

    long bytesToRead = inputFile.length();

    while ((inLen = in.read(buffer)) > 0) {
        int bytesOut = 0;
        byte[] cryptBytes = null;
        int outLen = cipher.getOutputSize(inLen);
        cryptBytes = new byte[outLen];

        if (bytesToRead <= buffer.length) {
            try {
                bytesOut = cipher.doFinal(buffer, 0, inLen, cryptBytes, 0);
            } catch (ShortBufferException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        } else
            try {
                bytesOut = cipher.update(buffer, 0, inLen, cryptBytes, 0);
            } catch (ShortBufferException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }

        out.write(cryptBytes, 0, bytesOut);
        bytesToRead -= inLen;

    }
    try {
        out.flush();
        in.close();
        out.close();
    } catch (IOException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }

共 (2) 个答案

  1. # 1 楼答案

    调用Cipher时必须指定填充机制。getInstance()-显然,它在加密和解密时必须相同。例如:

    decryptCipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
    

    如果没有填充机制,解密端就没有关于明文结尾位置的信息(在最后一个块内)

  2. # 2 楼答案

    AES是一种分组密码,它自然会给你整个分组,就像所有的分组密码一样

    有关更多信息,请参见Wikipedia article on AES

    你说你想让它输出“正确的字节数”。你是如何决定正确的字节数的