为什么我似乎无法生成相同的基于密码的加密密钥?

发布于 2024-12-15 02:14:12 字数 3281 浏览 0 评论 0原文

我正在开发一些 Java 软件,该软件需要使用两个单独的软件对网络连接两端的信息进行加密和解密。为了缓解这个问题,我有一个类 Cryptoographer 来处理数据加密。截至目前,控制器(连接的一侧)和代理(另一侧)都使用此类根据两个程序之间共享的密码生成 SecretKey。

密钥是在 Cryptoographer 类的此函数中生成的:

public SecretKey generateKey(String key) {
    this._paramSpec = new PBEParameterSpec(this.SALT, this.ITERATION_COUNT);
    PBEKeySpec spec = new PBEKeySpec(key.toCharArray());
    SecretKeyFactory fac = null;
    try {
        fac = SecretKeyFactory.getInstance("PBEWithMD5AndDES");
    } catch (NoSuchAlgorithmException ex) {
        ex.printStackTrace();
        System.err.println("[ERR] Cryptographer could not create a SecretKeyFactory due to an unsupported algorithm.");
    }
    try {
        if (fac == null)
            return null;
        return fac.generateSecret(spec);
    } catch (InvalidKeySpecException ex) {
        System.err.println("[ERR] Cryptographer could not generate a SecretKey due to an invalid Key Specification.");
        ex.printStackTrace();
        return null;
    }
}

加密本身发生在加密函数中:

public byte[] encrypt(byte[] message) {
    try {
        this._cipher.init(Cipher.ENCRYPT_MODE, this._key, this._paramSpec);
    } catch (InvalidKeyException ex) {
        System.err.println("[ERR] Cryptographer could not encrypt a message because the provided key is invalid.");
        ex.printStackTrace();
        return new byte[0];
    } catch (InvalidAlgorithmParameterException ex) {
        System.err.println("[ERR] Cryptographer could not encrypt a message because the parameters are invalid.");
        ex.printStackTrace();
        return new byte[0];
    }
    try {
        return this._cipher.doFinal(message);
    } catch (IllegalBlockSizeException ex) {
        System.err.println("[ERR] Cryptographer could not encrypt a message due to an illegal block size.");
        ex.printStackTrace();
        return new byte[0];
    } catch (BadPaddingException ex) {
        System.err.println("[ERR] Cryptographer could not encrypt a message due to bad padding.");
        ex.printStackTrace();
        return new byte[0];
    }
}

并且由解密函数解密:

public byte[] decrypt(byte[] message) {
    try {
        this._cipher.init(Cipher.DECRYPT_MODE, this._key, this._paramSpec);
    } catch (InvalidKeyException ex) {
        System.err.println("[ERR] Cryptographer could not decrypt a message because the provided key is invalid.");
        return new byte[0];
    } catch (InvalidAlgorithmParameterException ex) {
        System.err.println("[ERR] Cryptographer could not decrypt a message because the parameters are invalid.");
    }
    try {
        return this._cipher.doFinal(message);
    } catch (IllegalBlockSizeException ex) {
        System.err.println("[ERR] Cryptographer could not decrypt a message due to an illegal block size.");
        return new byte[0];
    } catch (BadPaddingException ex) {
        System.err.println("[ERR] Cryptographer could not decrypt a message due to bad padding.");
        return new byte[0];
    }
}

加密似乎工作正常,但是当我尝试在接收端解密序列化对象时,抛出 InvalidKeyException。比较控制器和代理上独立生成的密钥表明,尽管它们源自相同的密码,但它们生成的密钥并不相同。

现在,我对 Java 加密还不熟悉,所以我完全有可能在这里做错了什么。似乎我缺少了一个随机元素。目标是让连接的每一端都从相同的密码生成相同的密钥。那么我正在做的事情有什么明显错误的吗?如果您需要查看更多代码,请告诉我。我很乐意发布它。

I'm working on some Java software which entails encrypting and decrypting information on both ends of a network connection using two separate pieces of software. To ease this, I have one class, Cryptographer, that handles the encryption of data. As of right now, the Controller (one side of the connection) and the Agent (the other side) both use this class to generate a SecretKey based on a password shared between the two programs.

The key is generated in this function of the Cryptographer class:

public SecretKey generateKey(String key) {
    this._paramSpec = new PBEParameterSpec(this.SALT, this.ITERATION_COUNT);
    PBEKeySpec spec = new PBEKeySpec(key.toCharArray());
    SecretKeyFactory fac = null;
    try {
        fac = SecretKeyFactory.getInstance("PBEWithMD5AndDES");
    } catch (NoSuchAlgorithmException ex) {
        ex.printStackTrace();
        System.err.println("[ERR] Cryptographer could not create a SecretKeyFactory due to an unsupported algorithm.");
    }
    try {
        if (fac == null)
            return null;
        return fac.generateSecret(spec);
    } catch (InvalidKeySpecException ex) {
        System.err.println("[ERR] Cryptographer could not generate a SecretKey due to an invalid Key Specification.");
        ex.printStackTrace();
        return null;
    }
}

The encryption itself takes place in the encrypt function:

public byte[] encrypt(byte[] message) {
    try {
        this._cipher.init(Cipher.ENCRYPT_MODE, this._key, this._paramSpec);
    } catch (InvalidKeyException ex) {
        System.err.println("[ERR] Cryptographer could not encrypt a message because the provided key is invalid.");
        ex.printStackTrace();
        return new byte[0];
    } catch (InvalidAlgorithmParameterException ex) {
        System.err.println("[ERR] Cryptographer could not encrypt a message because the parameters are invalid.");
        ex.printStackTrace();
        return new byte[0];
    }
    try {
        return this._cipher.doFinal(message);
    } catch (IllegalBlockSizeException ex) {
        System.err.println("[ERR] Cryptographer could not encrypt a message due to an illegal block size.");
        ex.printStackTrace();
        return new byte[0];
    } catch (BadPaddingException ex) {
        System.err.println("[ERR] Cryptographer could not encrypt a message due to bad padding.");
        ex.printStackTrace();
        return new byte[0];
    }
}

And it gets decrypted by the decrypt function:

public byte[] decrypt(byte[] message) {
    try {
        this._cipher.init(Cipher.DECRYPT_MODE, this._key, this._paramSpec);
    } catch (InvalidKeyException ex) {
        System.err.println("[ERR] Cryptographer could not decrypt a message because the provided key is invalid.");
        return new byte[0];
    } catch (InvalidAlgorithmParameterException ex) {
        System.err.println("[ERR] Cryptographer could not decrypt a message because the parameters are invalid.");
    }
    try {
        return this._cipher.doFinal(message);
    } catch (IllegalBlockSizeException ex) {
        System.err.println("[ERR] Cryptographer could not decrypt a message due to an illegal block size.");
        return new byte[0];
    } catch (BadPaddingException ex) {
        System.err.println("[ERR] Cryptographer could not decrypt a message due to bad padding.");
        return new byte[0];
    }
}

Encryption seems to work fine, but when I try to decrypt a serialized object on the receiving end, the InvalidKeyException gets thrown. Comparing the keys independently generated on the Controller and the Agent shows that, although they are sourced in the same password, they are not generating identical keys.

Now, I am new to encryption in Java, so it's entirely possible I'm doing something wrong here. It seems like there is a random element to this that I'm missing. The goal is to get each side of the connection to generate an identical key from identical passwords. So is there anything I'm doing that's obviously wrong? If you need to see more code, let me know. I'll be happy to post it.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

野生奥特曼 2024-12-22 02:14:12

抛出的 InvalidKeyException 向我表明我将查看接收端如何使用密钥。您将其存储在数据库还是文件中?您确定它与用于加密数据的编码相同吗?

The InvalidKeyException being thrown indicates to me that I would look at how the key is being used on the receiving end. Are you storing it in a database or file? Are you sure it is in the same encoding that was used to encrypt the data?

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文