一、概述

ECC算法(Elliptic curve cryptography,椭圆曲线密码学)

椭圆加密算法(ECC)是一种公钥加密体制,最初由Koblitz和Miller两人于1985年提出,其数学基础是利用椭圆曲线上的有理点构成Abel加法群上椭圆离散对数的计算困难性。

是目前已知的公钥体制中,对每比特所提供加密强度最高的一种体制。在软件注册保护方面起到很大的作用,一般的序列号通常由该算法产生。

ECDSA is a digital signature algorithm是一种数字签名算法

ECIES is an Integrated Encryption scheme 是一种集成加密方案

ECDH is a key secure key exchange algorithm是密钥安全密钥交换算法

1.1、jdk实现

ECC算法在jdk1.5后加入支持,目前仅仅只能完成密钥的生成与解析。

JDK1.7开始内置了ECC公私钥生成、签名验签,但没有实现加密解密。

jdk支持ecdsa、不支持ecdh、ecies

bc支持ecdsa、ecdh、ecies

1.2、bc实现【提供实现】

在Java中使用ECC算法有以下几点需要注意:

JDK1.7开始内置了ECC公私钥生成、签名验签,但没有实现加密解密,因此需要使用BouncyCastle来做Security Provider;

在Java中使用高级别的加解密算法,比如AES使用256bit密钥、ECC使用Secp256r1等需要更新JRE的security policy文件,否则会报类似“Illegal key size or default parameters”这样的错误。具体怎样更换policy文件,可以参考这里

实际项目开发过程中,可能发现有传递给Java的公钥不是完整的X.509 SubjectPublicKeyInfo,比如只传递了一个65字节的ECPoint过来,这种情况可以跟对方沟通清楚所使用的Algorithm以及NamedCurve,补全DER数据后,再使用Java Security库解析。

public classBcEcc {public static KeyPair initKeyPair(String algorithm, Integer keySize) throwsException {

Security.addProvider(neworg.bouncycastle.jce.provider.BouncyCastleProvider());

KeyPairGenerator keyPairGenerator= KeyPairGenerator.getInstance("EC","BC");

keyPairGenerator.initialize(keySize,newSecureRandom());

KeyPair keyPair=keyPairGenerator.generateKeyPair();returnkeyPair;

}public static byte[] encrypt(byte[] content, PublicKey publicKey) throwsException {

Security.addProvider(neworg.bouncycastle.jce.provider.BouncyCastleProvider());

Cipher cipher= Cipher.getInstance("ECIES","BC");//写不写 BC都可以,都是会选择BC实现来做

cipher.init(Cipher.ENCRYPT_MODE, publicKey);returncipher.doFinal(content);

}public static byte[] decrypt(byte[] content, PrivateKey privateKey) throwsException {

Security.addProvider(neworg.bouncycastle.jce.provider.BouncyCastleProvider());

Cipher cipher= Cipher.getInstance("ECIES","BC");

cipher.init(Cipher.DECRYPT_MODE, privateKey);returncipher.doFinal(content);

}

}

二、ECDSA签名

基于ECC与DSA签名算法分类信息,ECDSA(elliptic curve digital signature algorithm) 椭圆曲线数字签名算法:速度快,强度高,签名短

算法

密钥长度

默认长度

签名长度

实现的方

NONEwithECDSA

112-571

256

128

JDK/BC

RIPEMD160withECDSA

同上

256

160

BC

SHA1withECDSA

...

256

160

JDK/BC

SHA224withECDSA

...

256

224

JDK/BC

SHA256withECDSA

...

256

256

JDK/BC

SHA384withECDSA

...

256

384

JDK/BC

SHA512withECDSA

...

256

512

JDK/BC

签名示例

/algorithm-sign/algorithm-sign-impl/src/main/java/com/github/bjlhx15/security/sign003ecc

http://baike.baidu.com/item/%E6%A4%AD%E5%9C%86%E5%8A%A0%E5%AF%86%E7%AE%97%E6%B3%95/10305582?sefr=cr

三、nodejs版

crypto支持ecdsa、ecdh,不支持ecies加密解密

ecccrypto支持ecies加密解密

jsrsasign 使用

3.1、使用原生crypto 操作ecdsa、ecdh

无需安装类库模块

//原生crypto 支持 签名 验签 密钥交换//签名

functionecc_ecdsa_sign(signAlgorithmName, privateKey, srcData) {

const crypto= require('crypto');

const sign=crypto.createSign(signAlgorithmName);

sign.update(srcData);//注意这里是pkcs1, java后端默认是pkcs8

const private_key = '-----BEGIN EC PRIVATE KEY-----\n' +privateKey+

'-----END EC PRIVATE KEY-----\n';return sign.sign(private_key).toString('base64');

}//验签

functionecc_ecdsa_verify(signAlgorithmName, publicKey,sign, srcData) {//校验这里直接使用公钥,直接后端java生成的即可

const crypto = require('crypto');

const verify=crypto.createVerify(signAlgorithmName);

verify.update(srcData);//verify.update(new Buffer(srcData, 'utf-8'));

var public_key='-----BEGIN PUBLIC KEY-----\n' +publicKey+'-----END PUBLIC KEY-----\n';

console.log(verify.verify(public_key, sign,"base64"));

}//密钥交换

functionecc_ecdh(srcData) {

const crypto= require('crypto');

const assert= require('assert');//Generate Alice's keys...

const alice = crypto.createECDH('secp521r1');

const alice_key=alice.generateKeys();//Generate Bob's keys...

const bob = crypto.createECDH('secp521r1');

const bob_key=bob.generateKeys();//Exchange and generate the secret...

const alice_secret =alice.computeSecret(bob_key);

const bob_secret=bob.computeSecret(alice_key);

console.log("alice_secret:" + alice_secret.toString("base64"))

console.log("bob_secret:" + bob_secret.toString("base64"))

assert(alice_secret, bob_secret);

}//算法

var algorithmName ={

sha1:"sha1",

sha224:"sha224",

sha256:"sha256",

sha384:"sha384",

sha512:"sha512"}

module.exports={

algorithmName, ecc_ecdsa_sign, ecc_ecdsa_verify, ecc_ecdh

}

测试:

functionmain() {var algorithm = require("../main/ecc001crypto")//pkcs1

var priKey =

"MHQCAQEEID7ytsiAhdlS+hisEkdox7E2pTDP/nKmFdyKWyrqaFh/oAcGBSuBBAAKoUQDQgAEE0eb7o1ibninvBQlX8+sjigHaB4612Nn620p20zPxbKAjLa5w5M2jJwtD3v2bRDjmIeAV3AHhzxzPNt56t7B6A==\n";//普通的后端key

var pubKey =

"MFYwEAYHKoZIzj0CAQYFK4EEAAoDQgAEE0eb7o1ibninvBQlX8+sjigHaB4612Nn620p20zPxbKAjLa5w5M2jJwtD3v2bRDjmIeAV3AHhzxzPNt56t7B6A==\n";

console.log("-----签名-验签-------")var value = algorithm.ecc_ecdsa_sign(algorithm.algorithmName.sha1, priKey, "hello world")

console.log(value)

algorithm.ecc_ecdsa_verify(algorithm.algorithmName.sha1, pubKey, value,"hello world")var value = algorithm.ecc_ecdsa_sign(algorithm.algorithmName.sha224, priKey, "hello world")

console.log(value)

algorithm.ecc_ecdsa_verify(algorithm.algorithmName.sha224, pubKey, value,"hello world")var value = algorithm.ecc_ecdsa_sign(algorithm.algorithmName.sha256, priKey, "hello world")

console.log(value)

algorithm.ecc_ecdsa_verify(algorithm.algorithmName.sha256, pubKey, value,"hello world")var value = algorithm.ecc_ecdsa_sign(algorithm.algorithmName.sha384, priKey, "hello world")

console.log(value)

algorithm.ecc_ecdsa_verify(algorithm.algorithmName.sha384, pubKey, value,"hello world")var value = algorithm.ecc_ecdsa_sign(algorithm.algorithmName.sha512, priKey, "hello world")

console.log(value)

algorithm.ecc_ecdsa_verify(algorithm.algorithmName.sha512, pubKey, value,"hello world")

console.log("-----java的签名-验签-------")var javaSign='MEYCIQDFtnUYxR0jPw8/16iZxYlEkW+AJkcPIxpXSWNnU9DoGwIhAJ1A8XlSoeqRvGC9ZzOthvGvQoOXZ+saiy7iryHINJa0';

algorithm.ecc_ecdsa_verify(algorithm.algorithmName.sha256, pubKey, javaSign,"我是测试数据对的纷纷")

console.log("-----密钥交换-------")

algorithm.ecc_ecdh("")

}

main();

3.2、使用类库ecccrypto操作ecdsa、ecdh、ecies加密解密

安装:npm i eccrypto

//使用 eccrypto 库 支持 签名 验签 密钥交换 加密解密//签名 验签

functionecc_ecdsa(signAlgorithmName, pubKey, priKey, str) {var crypto = require("crypto");var eccrypto = require("eccrypto");//A new random 32-byte private key.

var privateKey =eccrypto.generatePrivate();

console.log(privateKey.toString("base64"))//Corresponding uncompressed (65-byte) public key.

var publicKey =eccrypto.getPublic(privateKey);

console.log(publicKey.toString("base64"))//var str = "message to sign";

//Always hash you message to sign!

var msg =crypto.createHash(signAlgorithmName).update(str).digest();

eccrypto.sign(privateKey, msg).then(function(sig) {

console.log("Signature in DER format:", sig.toString("base64"));

eccrypto.verify(publicKey, msg, sig).then(function() {

console.log("Signature is OK");

}).catch(function() {

console.log("Signature is BAD");

});

});

}//密钥交换

functionecc_ecdh() {var eccrypto = require("eccrypto");var privateKeyA =eccrypto.generatePrivate();var publicKeyA =eccrypto.getPublic(privateKeyA);var privateKeyB =eccrypto.generatePrivate();var publicKeyB =eccrypto.getPublic(privateKeyB);

eccrypto.derive(privateKeyA, publicKeyB).then(function(sharedKey1) {

eccrypto.derive(privateKeyB, publicKeyA).then(function(sharedKey2) {

console.log("Both shared keys are equal:", sharedKey1.toString("base64"), sharedKey2.toString("base64"));

});

});

}//ecc加密解密

functionecc_ecies() {var eccrypto = require("eccrypto");var privateKeyA =eccrypto.generatePrivate();var publicKeyA =eccrypto.getPublic(privateKeyA);var privateKeyB =eccrypto.generatePrivate();var publicKeyB =eccrypto.getPublic(privateKeyB);//Encrypting the message for B.

eccrypto.encrypt(publicKeyB, Buffer.from("msg to b")).then(function(encrypted) {//B decrypting the message.

console.log("Message to part B[encrypted]:", encrypted.ciphertext.toString("base64"));

eccrypto.decrypt(privateKeyB, encrypted).then(function(plaintext) {

console.log("Message to part B:", plaintext.toString());

});

});//Encrypting the message for A.

eccrypto.encrypt(publicKeyA, Buffer.from("msg to a")).then(function(encrypted) {//A decrypting the message.

console.log("Message to part A[encrypted]:", encrypted.ciphertext.toString("base64"));

eccrypto.decrypt(privateKeyA, encrypted).then(function(plaintext) {

console.log("Message to part A:", plaintext.toString());

});

});

}//算法

var algorithmName ={

sha1:"sha1",

sha224:"sha224",

sha256:"sha256",//sha384: "sha384", //Error: Message is too long

//sha512: "sha512"

}

module.exports={

algorithmName, ecc_ecdsa, ecc_ecdh, ecc_ecies

}

测试:

functionmain() {var algorithm = require("../main/ecc002eccrypto")//pkcs1

var priKey =

"MHQCAQEEID7ytsiAhdlS+hisEkdox7E2pTDP/nKmFdyKWyrqaFh/oAcGBSuBBAAKoUQDQgAEE0eb7o1ibninvBQlX8+sjigHaB4612Nn620p20zPxbKAjLa5w5M2jJwtD3v2bRDjmIeAV3AHhzxzPNt56t7B6A==";//普通的后端key

var pubKey =

"MFYwEAYHKoZIzj0CAQYFK4EEAAoDQgAEE0eb7o1ibninvBQlX8+sjigHaB4612Nn620p20zPxbKAjLa5w5M2jJwtD3v2bRDjmIeAV3AHhzxzPNt56t7B6A==";

console.log("-----签名-验签-------")var value = algorithm.ecc_ecdsa(algorithm.algorithmName.sha1, pubKey,priKey, "hello world")var value = algorithm.ecc_ecdsa(algorithm.algorithmName.sha224, pubKey,priKey, "hello world")var value = algorithm.ecc_ecdsa(algorithm.algorithmName.sha256, pubKey,priKey, "hello world")//var value = algorithm.ecc_ecdsa(algorithm.algorithmName.sha384, pubKey,priKey, "hello world")

console.log("-----密钥交换-------")

algorithm.ecc_ecdh("")

console.log("-----加密 解密-------")

algorithm.ecc_ecies("")

}

main();

3.3、使用类库jsrsasign操作

//使用 eccrypto 库 支持 签名 验签 密钥交换 加密解密//签名 验签

functionecc_ecdsa_sign(signAlgorithmName, priKey, str) {var Jsrsasign = require('jsrsasign');//导入的Jsrsasign模块里面有很多实用的对象,对应不同的方法

console.log(Jsrsasign)

const privateKeyString= '-----BEGIN PRIVATE KEY-----\n' +priKey+ '\n-----END PRIVATE KEY-----\n';//传入私钥

//默认传入的私钥是PKCS#1的格式,所以采用readPrivateKeyFromPEMString(keyPEM)这个方法

//rsa.readPrivateKeyFromPEMString(PrivateKey);

//如果后台生产出来的私钥是PKCS#8的格式,就不能用readPrivateKeyFromPEMString(keyPEM)这个方法

const key =Jsrsasign.KEYUTIL.getKey(privateKeyString);//创建 Signature 对象,设置签名编码算法

const signature = newJsrsasign.KJUR.crypto.Signature({ alg: signAlgorithmName });//初始化

signature.init(key);//上面3行相当于这句

//const signature = new Jsrsasign.KJUR.crypto.Signature({ alg: signAlgorithmName,prvkeypem:privateKeyString });//!这里指定 私钥 pem!

//传入待加密字符串

signature.updateString(str);//生成密文

const originSign =signature.sign();

const sign64=Jsrsasign.hextob64(originSign);

console.log('sign base64 =======', sign64);//const sign64u = Jsrsasign.hextob64u(originSign);

//console.log('sign base64u=======', sign64u);

returnsign64;

}functionecc_ecdsa_verify(signAlgorithmName, pubKey, sign, str) {var Jsrsasign = require('jsrsasign');//导入的Jsrsasign模块里面有很多实用的对象,对应不同的方法

console.log(Jsrsasign)

const pKeyString= '-----BEGIN PUBLIC KEY-----\n' +pubKey+ '\n-----END PUBLIC KEY-----\n';//1.传入私钥

//默认传入的私钥是PKCS#1的格式,所以采用readPrivateKeyFromPEMString(keyPEM)这个方法

//rsa.readPrivateKeyFromPEMString(PrivateKey);

//如果后台生产出来的私钥是PKCS#8的格式,就不能用readPrivateKeyFromPEMString(keyPEM)这个方法

//const key = Jsrsasign.KEYUTIL.getKey(pKeyString);

//2. 创建 Signature 对象,设置签名编码算法

//const signature = new Jsrsasign.KJUR.crypto.Signature({ alg: signAlgorithmName});

//3.初始化

//signature.init(key)

//上面3行另一种写法

const signature = newJsrsasign.KJUR.crypto.Signature({ alg: signAlgorithmName, prvkeypem: pKeyString });//传入待加密字符串

signature.updateString(str);var b =signature.verify(Jsrsasign.b64tohex(sign))//生成密文

console.log('sign verify =======', b);returnb;

}//ecc加密解密

functionecc_ecies() {var Jsrsasign = require('jsrsasign');var keypair = Jsrsasign.KEYUTIL.generateKeypair("EC","secp256k1");

console.log(keypair)var pubKey=keypair.pubKeyObj.pubKeyHexvar priKey=keypair.prvKeyObj.prvKeyHex

console.log(Jsrsasign.hextob64(pubKey))

console.log(Jsrsasign.hextob64(priKey))

}//算法

var algorithmName ={

SHA1withECDSA:"SHA1withECDSA",

SHA224withECDSA:"SHA224withECDSA",

SHA256withECDSA:"SHA256withECDSA",

SHA384withECDSA:"SHA384withECDSA", //Error: Message is too long

SHA512withECDSA: "SHA512withECDSA"}

module.exports={

algorithmName, ecc_ecdsa_sign, ecc_ecdsa_verify, ecc_ecies

}

测试

functionmain() {var algorithm = require("../main/ecc003jsrsasign")//pkcs1

var priKeyPkcs1 =

"MHQCAQEEID7ytsiAhdlS+hisEkdox7E2pTDP/nKmFdyKWyrqaFh/oAcGBSuBBAAKoUQDQgAEE0eb7o1ibninvBQlX8+sjigHaB4612Nn620p20zPxbKAjLa5w5M2jJwtD3v2bRDjmIeAV3AHhzxzPNt56t7B6A==";var priKeyPkcs8 =

"MIGNAgEAMBAGByqGSM49AgEGBSuBBAAKBHYwdAIBAQQgPvK2yICF2VL6GKwSR2jHsTalMM/+cqYV3IpbKupoWH+gBwYFK4EEAAqhRANCAAQTR5vujWJueKe8FCVfz6yOKAdoHjrXY2frbSnbTM/FsoCMtrnDkzaMnC0Pe/ZtEOOYh4BXcAeHPHM823nq3sHo";//普通的后端key

var pubKey =

"MFYwEAYHKoZIzj0CAQYFK4EEAAoDQgAEE0eb7o1ibninvBQlX8+sjigHaB4612Nn620p20zPxbKAjLa5w5M2jJwtD3v2bRDjmIeAV3AHhzxzPNt56t7B6A==";

console.log("-----签名-验签-------")var value = algorithm.ecc_ecdsa_sign(algorithm.algorithmName.SHA1withECDSA, priKeyPkcs8, "hello world")

algorithm.ecc_ecdsa_verify(algorithm.algorithmName.SHA1withECDSA, pubKey, value,"hello world")var value = algorithm.ecc_ecdsa_sign(algorithm.algorithmName.SHA224withECDSA, priKeyPkcs8, "hello world")

algorithm.ecc_ecdsa_verify(algorithm.algorithmName.SHA224withECDSA, pubKey, value,"hello world")var value = algorithm.ecc_ecdsa_sign(algorithm.algorithmName.SHA256withECDSA, priKeyPkcs8, "hello world")

algorithm.ecc_ecdsa_verify(algorithm.algorithmName.SHA256withECDSA, pubKey, value,"hello world")var value = algorithm.ecc_ecdsa_sign(algorithm.algorithmName.SHA384withECDSA, priKeyPkcs8, "hello world")

algorithm.ecc_ecdsa_verify(algorithm.algorithmName.SHA384withECDSA, pubKey, value,"hello world")var value = algorithm.ecc_ecdsa_sign(algorithm.algorithmName.SHA512withECDSA, priKeyPkcs8, "hello world")

algorithm.ecc_ecdsa_verify(algorithm.algorithmName.SHA512withECDSA, pubKey, value,"hello world")//console.log("-----密钥交换-------")

//algorithm.ecc_ecdh("")

console.log("-----加密 解密-------")

algorithm.ecc_ecies("")

}

main();

更多:https://github.com/kjur/jsrsasign.git

3.5、nodejs结合java使用签名验签

Java 语言,就使用「PKCS8」密钥格式,也叫 「PKCS#8」,如果非 Java 语言可以考虑「PKCS1」。

Java 使用private key 和 public key时,要把首尾「-----BEGIN PRIVATE KEY-----」之类的删除,但在 JavaScript 里使用时,一定要加上。

nodejs与java的ecc加密签名通讯。

3.5.1、使用java操作生成双方公私钥

java端ecc:https://github.com/bjlhx15/algorithm-sign.git

使用测代码生成:com.github.bjlhx15.security.encryptSign001BcEcc.BcEccAlgorithmUtilTest 生成  initKeyPairBase64  ,后续操作方便使用 process 测试

A pubKey:MFYwEAYHKoZIzj0CAQYFK4EEAAoDQgAEYfNJOtj1Xkfp9bVqoXlB4ixVhNtN7Zl+mPPiyeDrPbKNX7XhmN8EcyOhjfpbXYmJY8JItue9rajOqouS45wYpQ==A priKey:MIGNAgEAMBAGByqGSM49AgEGBSuBBAAKBHYwdAIBAQQg1xRtgNwZ3oo+509hN+EkoH+hGRDhHiq0zfZy0zQxAOegBwYFK4EEAAqhRANCAARh80k62PVeR+n1tWqheUHiLFWE203tmX6Y8+LJ4Os9so1fteGY3wRzI6GN+ltdiYljwki2572tqM6qi5LjnBil

A priKey[pkcs1]:MHQCAQEEINcUbYDcGd6KPudPYTfhJKB/oRkQ4R4qtM32ctM0MQDnoAcGBSuBBAAKoUQDQgAEYfNJOtj1Xkfp9bVqoXlB4ixVhNtN7Zl+mPPiyeDrPbKNX7XhmN8EcyOhjfpbXYmJY8JItue9rajOqouS45wYpQ==

B pubKey:MFYwEAYHKoZIzj0CAQYFK4EEAAoDQgAEJN5FVWR90XaFSMjVEbCGgAqrMbvHCIM0i84kVLuKpESDNgGSnz0AZt4HKElRR8MkZbzsnJdMq5gmDxTrYMyg8Q==B priKey:MIGNAgEAMBAGByqGSM49AgEGBSuBBAAKBHYwdAIBAQQgUHzI83yRMCfl395xdpx/CB2eZPIsEORBN3OPQyN0RT6gBwYFK4EEAAqhRANCAAQk3kVVZH3RdoVIyNURsIaACqsxu8cIgzSLziRUu4qkRIM2AZKfPQBm3gcoSVFHwyRlvOycl0yrmCYPFOtgzKDx

A 向 B 发送数据【密文、签名】

A 需要用B的 公钥加密数据

密文:BNmsoiMfajCwsqvNGwx198QliMzFVFySnsGkJuBWGNHxbe/lKxcsDnh3qTyD8DNd+m0se2l3mmJudy+2+msDwCde2lVGLDCRjHh8htCFaFJUGSPP/f7IrzWUMJB1zF8nr1VB7GIGgMeGyGaynE31viTg3Q==A 需要用自己的 私钥签名

sign:MEUCIQCEF3hAZed32ZLwxuhuGozogPstm2YPSYNp+jMqGTnK7wIge3L+RMWegt9eBm6u5j7oWi06boKTWspOBSWJRY33Fj8=A 向 B 发送数据:ok

B用 需要用自己 的私钥解密

解密后:我是测试数据对的纷纷

B需要用A 的公钥验签

check:true

3.5.2、nodejs交互操作

方案一、使用nodejs自带模块crypto签名

将A的公私钥,分发给nodejs使用

java使用的是pkcs8,nodejs的crypto使用的是pkcs1,所以这里使用的是 priKey[pkcs1]

参看3.1示例,注意使用的是sha256的算法

方案二、使用工具类-jsrsasign

安装: npm i jsrsasign

参看3.2

3.5.3、java验签

此时nodejs端会将签名发送至,java端

java端验签:使用客户的公钥,以及签名

@org.junit.Test

publicvoidpkcs8checkSign() throws Exception {

String msg= "我是测试数据对的 http://blog.bjlhx.top/";

System.out.println("B需要用A 的公钥验签");boolean check = BcEccAlgorithmUtil.verify("MFYwEAYHKoZIzj0CAQYFK4EEAAoDQgAEYfNJOtj1Xkfp9bVqoXlB4ixVhNtN7Zl+mPPiyeDrPbKNX7XhmN8EcyOhjfpbXYmJY8JItue9rajOqouS45wYpQ==",

msg,"MEUCIEuuqtMhHw/JvZgyBrs5djPD0VIZjxdeHYUWeEJsqcdlAiEAyVowkbpvQJuZWrUG2FXhq6+BFDpq9wFSl2CcjcSjGRM=");

System.out.println("check:" +check);

}

输出

B需要用A 的公钥验签

check:true

https://github.com/bjlhx15/algorithm-sign.git的encryptSign001BcEcc 的pkcs8checkSign

3.5.4、java端回发数据签名

参看:com.github.bjlhx15.security.encryptSign001BcEcc.BcEccAlgorithmUtilTest#process

签名值:MEQCIEQbw0cfSMncVG/3OT+/HnNQamNAZFPLYt5uYpjCsvoZAiAI9l4hdDDJqXlfKBxovkBUtqjl8r+5BQHZfkS4QRH0/A==

3.5.5、node验签

参看3.1

console.log("-----java的签名-验签-------")var javaSign = 'MEQCIEQbw0cfSMncVG/3OT+/HnNQamNAZFPLYt5uYpjCsvoZAiAI9l4hdDDJqXlfKBxovkBUtqjl8r+5BQHZfkS4QRH0/A==';

algorithm.ecc_ecdsa_verify(algorithm.algorithmName.sha256, pubKeyRemote, javaSign, msg+":B")

pubKeyRemote:是B的公钥;

java端代码:https://github.com/bjlhx15/algorithm-sign.git的com.github.bjlhx15.security.encryptSign001BcEcc.BcEccAlgorithmUtilTest

nodejs端代码:https://github.com/bjlhx15/algorithm-sign-nodejs.git 的ecc00X代码 主要看:testEcc001crypto

java ecc 加密_java-信息安全(十一)-非对称加密算法002-ECC,签名003-ECDSA签名相关推荐

  1. android 对称加密和非对称加密,Android开发加密之对称与非对称加密算法使用案例.pdf...

    Android开发加密之对称与非对称加密算法使用案例 消息摘要 md5:登录注册, sha1 对称加密  1.des:Data Encryption Standard,数据加密标准  2.aes: ...

  2. java的rsa加密_java实现的RSA加密算法详解

    本文实例讲述了java实现的RSA加密算法.分享给大家供大家参考,具体如下: 一.什么是非对称加密 1.加密的密钥与加密的密钥不相同,这样的加密算法称之为非对称加密 2.密钥分为:公钥,私钥 公钥:可 ...

  3. java aes256 加密_java Aes256 加密算法的实现

    如果希望进行AES256位的加密解密,需要事先从java官网下载 local_policy.jar与US_export_policy.jar替换%JAVA_HOME%/jre/lib/security ...

  4. java 3des加密_Java使用3DES加密解密的流程 - 3des加密解密详细解释

    Java使用3DES加密解密的流程 ①传入共同约定的密钥(keyBytes)以及算法(Algorithm),来构建SecretKey密钥对象 SecretKey deskey = new Secret ...

  5. java如何加密_Java如何实现密码加密

    在查询时,我们如果要对用户的登录信息进行加密,通常会将其密码进行加密. 1) 可以借助spring框架工具类DigestUtils 2) 也可以使用shiro框架来实现 //保存用户自身信息 //1构 ...

  6. java string 加密_java字符串加密解密

    java字符串加密解密 try { String test = "123456789@fdj.com"; EncryptionDecryption des = new Encryp ...

  7. java des3加密_JAVA加密算法(3)- 对称加密算法(DES、3DES、AES)

    对称加密算法概念 加密密钥和解密密钥相同,大部分算法加密揭秘过程互逆. 特点:算法公开.(相比非对称加密)计算量小.加密速度快.效率高. 弱点:双方都使用同样的密钥,安全性得不到保证. 常用对称加密算 ...

  8. java类加密_Java中常用加密类型

    1.对称加密 image.png 密钥:加解密钥相同 缺点:无法确保密钥被安全传递 常用算法:DES.3DES(TripleDES).AES等 2.非对称加密 image.png image.png ...

  9. java 对象加密_java.security包实现对象加密

    Java原生支持常见的加密算法,例如DES.RSA.随便写点关于Java安全包的东西. Java.security.Provider对象官方的解释是:实现了 Java 安全性的一部分或者全部. pro ...

  10. java ase 加密_java实现ase加密解密

    展开全部 这个算法java SDK自带的额 参考代码如下: /**解密 * @param content  待解密内容 * @param password 解密密钥 * @return */ publ ...

最新文章

  1. android shortcut livefoulder
  2. 什么是BS结构、CS结构、RIA结构程序
  3. 三星手机续航测试软件,三星S21系列续航测试简报出炉
  4. jgit_JGit身份验证说明
  5. STM32----摸石头过河系列(三)
  6. lr分析器的设计与实现实验_GBDT+LR:Practical Lessons from Predicting Clicks on Ads
  7. STM32 DMA详解
  8. python pip更改源
  9. vivo Z1的USB调试模式在哪里,打开vivo Z1USB调试模式的经验
  10. 以图搜图-自动生成图模式匹配Cypher
  11. 计算机系表白祖国母亲,青春向祖国告白——“给祖国母亲的一封告白信”活动纪实...
  12. FusionCharts报表
  13. 枚举---枚举的其他应用
  14. 关于鼠标右键的快捷键
  15. JAVA下载文件的几_详解Java文件下载的几种实现方式
  16. 恶意代码分析-静态分析基础
  17. 母亲节不能陪在妈妈身边,我用css和js给妈妈做了一个爱心飘落
  18. ZYNQ lwip协议栈phy芯片自协商连接速度
  19. ctp linux 查询死循环,CTP行情接入常见的问题记录
  20. Docker命令汇总

热门文章

  1. C# 9 新特性 —— 增强的模式匹配
  2. WPF开源控件扩展库 - MaterialDesignExtensions
  3. 数据结构与算法专题——第九题 外排序
  4. Kubernetes:通过自动化节省IT预算的4种方法
  5. .NET分布式大规模计算利器-Orleans(一)
  6. 混沌工程详细介绍——Netflix持续交付实践探寻
  7. 在.Net Core中实现一个WebSocket路由
  8. 基于IdentityServer4 实现.NET Core的认证授权
  9. ASP.NET Core集成现有系统认证
  10. Entity Framework Core 2.0 使用代码进行自动迁移