当前位置: 首页 > 知识库问答 >
问题:

节点。js加密密钥和iv匹配java SecretKeySpec/IvParameterSpec

伯建安
2023-03-14

我正在尝试将Java(简单)加密算法移植到Node JS。我需要能够解密/加密从Java端加密/解密的东西。

我被困在一开始,密码的初始化。

在Java中,我用SecretKeySpec获取密钥,用IvParameterSpec获取初始化向量:

public CryptStuff(String password) throws zillion_exceptions {
    if (password==null) throw new InvalidKeyException("No encryption password is set!");
    key = new SecretKeySpec(password.getBytes("UTF-8"), "AES");
    cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
    ivSpec=new IvParameterSpec(new byte[cipher.getBlockSize()]);
    cipher.init(Cipher.ENCRYPT_MODE, key, ivSpec);
}

NodeJS需要一个密钥缓冲区和一个IV缓冲区,但是,我不知道如何从头开始计算它们:

var mCrypto = require('crypto'),
    key=[0,0,0,0,0,0,.......],
    iv=[0,0,0,0,0,.........];

function init (password) {

    // generate key from password
    // generate IV from blocksize?

    var aesCipher = mCrypto.createCipheriv("aes-????????", (new Buffer(key)), (new Buffer(iv)));
    .
    .
    .
}

另外,AES/CBC/PKCS5P的匹配算法字符串是什么?

共有1个答案

姬奇思
2023-03-14

假设您的密码字符串与Java代码中的密码字符串相同,您可以在node中创建如下密钥缓冲区:

var key = new Buffer(password, "utf8");

因为你使用的是零填充静脉注射(糟糕!)在Java中,这是节点中的等效代码:

var iv = new Buffer(16); // 16 byte buffer with random data
iv.fill(0); // fill with zeros

因为在Java中使用CBC模式,所以在node中也必须这样做。请注意,根据“密码”长度选择密码字符串时,必须选择正确的密钥大小:

var aesCipher = mCrypto.createCipheriv("aes-128-cbc", key, iv);
// or
var aesCipher = mCrypto.createCipheriv("aes-192-cbc", key, iv);
// or
var aesCipher = mCrypto.createCipheriv("aes-256-cbc", key, iv);

节点将自动应用PKCS#7填充,这与AES的PKCS#5填充相同。

密码通常不具有用作密钥的适当长度(AES的有效长度为16字节、24字节和32字节),并且密码仅由可打印字符组成,这可能会使攻击者更容易强行使用密钥。

从密码创建密钥需要的是密钥派生函数。流行的是PBKDF2、bcrypt和scrypt(成本不断增加)。

你真的应该为你产生的每一个密文生成一个新的随机IV。如果你使用静态IV,观察你的密文的攻击者可以确定你发送了相同甚至相似的信息。如果你使用随机IV,那么密文差异如此之大,以至于攻击者无法确定两个不同的密文是否是由相同的明文创建的。这被称为语义安全

random IV本身不必是秘密的,所以你可以很容易地将其预编到密文中,并在解密之前将其切掉。

您甚至可以将其与密钥派生函数(KDF)结合起来。只需为KDF生成一个随机盐。KDF通常能够派生可变数量的输出字节,所以只需让它派生密钥||IV(级联),然后拆分它们。现在,您只需要将盐预置到密文中。

根据您的系统,您可能容易受到诸如填充预言攻击之类的攻击。对此的最佳防御是对密文进行身份验证。因此,您可以使用具有强大MAC(如HMAC-SHA256)的加密然后MAC方案,或者使用经过身份验证的操作模式(如GCM或EAX)。Java和节点都支持GCM,但涉及的工作有点多。

 类似资料:
  • 我试图在节点之间建立加密通信。js和NodeMCU。经过一些努力,我能够使用node加密。js并在NodeMCU上解密。反之亦然。mscdex的答复有效。因此,我修改了节点。为了他人的利益而编写js代码。谢谢 NodeMCU代码: 节点。js工作代码: 现在再次进行NodeMCU侧测试: 什么在起作用? 节点。js加密在NodeMCU上被解密,尽管加密的字符串有点不同。 什么不起作用? NodeM

  • 我写这个问题的答案是因为我挣扎了很多(可能是因为缺乏经验),迷失在许多不同的加密/解密节点或Python的方法中。 我想也许我的案子能在将来帮助人们。 我需要做的是: 从表单中获取数据,使用加密(node js)对其进行加密。 我选择使用AES加密。 我是这样开始的(我不会经历我尝试过的一切): > 我遵循了本页末尾的例子 在我的案例中给出: 这可能是javascript和coffeescript

  • 使用EVP_BytesToKey()返回错误的key和iv可能出了什么问题? 我试过用iter计数值做实验,但似乎没有一个能产生工作键和IV。我假设命令行默认的iter计数是1。 同样确认的是,如果我用命令行显示的工作键和iv覆盖从EVP_BytesToKey()返回的内容和硬代码无符号char数组,我的其余代码工作正常,解密正确。 有人能帮忙吗?

  • 我已经看过了AES-Encryption with Crypto(node js)/decryption with Pycrypto(python)的文章,因为我正试图做完全相反的事情,但我似乎做得不对。这是我到目前为止试过的。。。 Python加密 节点。js解密 每次我尝试运行节点时。js解密,我最终得到错误消息:

  • 问题内容: 我在下面的(E.1)中使用它来进行我的应用程序,显然我认识并理解了其中的一个巨大的安全漏洞。我对加密越来越感兴趣,并且想更好地理解它,我需要随IV一起生成一个随机密钥,但是不确定如何正确地执行此操作。有人可以向我解释一下熟悉AES加密的工作原理(IV和KEY)吗? )因此,我将来能够更好地理解并可以运用我的知识,本质上,我只是想使代码更安全,谢谢。 (E.1) 问题答案: AES密钥仅