Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

SM2加密后是30开头的,但是后台需要04开头的 这个可以转换么 #78

Open
yushenNO1 opened this issue Apr 14, 2023 · 19 comments

Comments

@yushenNO1
Copy link

No description provided.

@muzipiao
Copy link
Owner

将密文 ASN1 解码即可,查看 Readme 文档或 Demo 示例。

// ASN1 解码
NSString *c1c3c2Result1 = [GMSm2Utils asn1DecodeToC1C3C2:enResult1]; // 解码为 c1c3c2字符串
NSArray<NSString *> *c1c3c2Result2 = [GMSm2Utils asn1DecodeToC1C3C2Array:enResult2]; // 解码为 @[c1,c3,c2]
NSData *c1c3c2Result3 = [GMSm2Utils asn1DecodeToC1C3C2Data:enResult3]; // 解码为 c1c3c2拼接的Data

@muzipiao
Copy link
Owner

04 代表非压缩格式,解码出来默认不带 04,后端需要,手动拼接加上 04 即可。

@yushenNO1
Copy link
Author

这个解出来和后台的的对不上
麻烦可以帮我看下是哪有有问题么
初始公钥:
04653b7ea84362e5d01386d60cd2976226df3ede1d10d5efd583e2e671cd78bb5c39298c38d611f058451331de8b52d3befffa9ede3734e54d696903a84033cdcf
初始私钥:
2cac75851ed2e9ac993a3210eb770435a85d32f1b9047fb738bdfdaaf4efd2e6
加密后公钥:04d69318ad20b99cdd9e823c220bd3cc06652060abb3e99638aba4e1c97d9a409c21de35cd72a8a41ff009419734c943515abcaba81358a734b3f55842f19755b1f36dd67d293263df9fc3d96a35653853bb36e36521d8c1f8102fa6ef5944cf91a37bdd1552a5e309b14bf13bf8565eee7c37c4dd9b7468656de363a7b109a71a3de9d179f004f71aa37532913ea0375529e91e7f3674662fee864dfa625b96fff619d17cf179e01d65376e4373c7c65bf8e86b17dd887ea3c290d16ce60a0dc5e9df522b77bd8f0914eb283277b0faecb4373f8a3c4ade3b68e510602e5c65c637ce
加密后私钥:04b397e89cccdc8a70aae1044c13d9d0d8d721e05441e547b1e9d5ef6c2ded3738bc397d8e8fcd279e3c5bf43d57d6b6decdc504311c44e92f8182869fc15d2d9ade1e508e29ff7f9104351da2d1e34e5cf3e86c8623d55dc45a8b38224873ce9a8801be0de182182019eaabdfa7ffd6c63aeb9380d698d7505eb2982c9668e620cfa30d59af3c66ceaf7e26f6aad4622c82db5e73a7c8cd9de840d77c316299a4
解密后公钥: 0420982890d70746c92c7d4b5216f7b54816c1cd8b7f1653d5d790eb472edb70b506760dfa10009d4068479dc0d05d75e8ce74f1741c93c645755ae361a93221de
解密后私钥:
203fce2a3a29e36dad7eda93d2ea9930888343c970a04f599ec764b8d5fbe53b

@muzipiao
Copy link
Owner

加密后公钥:
加密后私钥:
这俩是什么意思,密钥还需要加密吗?那加密密钥用的是什么

@yushenNO1
Copy link
Author

初始公钥: ==> 公钥
初始私钥: ==> 私钥

加密后公钥:==> 加密密文
加密后私钥:==> 加密密文

解密后公钥: ==> 结果
解密后私钥: ==> 结果

@yushenNO1
Copy link
Author

解密后公钥: ==> 结果
解密后私钥: ==> 结果

这两个是密文解密后预期结果

@muzipiao
Copy link
Owner

  1. 没有私钥加密这个说法:公钥加密,私钥解密;私钥签名,公钥验签;
  2. 公钥加密结果 04d693.......5c637ce 明显是没有经过 ASN1 编码的,而 OpenSSL 加解密都是 ASN1 编码格式的密文;
  3. 所以,无非是没有进行 ASN1 编码问题,把 04d693.......5c637ce 前面的 04 标志去掉,进行 ASN1 编码,送入解密即可。
  4. 签名类似,注意 ASN1 编码和 04 标志即可。
NSString *priKey = @"2cac75851ed2e.....8bdfdaaf4efd2e6";
NSString *cipertext = @"d69318ad20b99......e5c65c637ce";
NSString *ciperAsn1 = [GMSm2Utils asn1EncodeWithC1C3C2:cipertext];
NSString *plaintext = [GMSm2Utils decryptToText:ciperAsn1 privateKey:priKey];
NSLog(@"解密结果==%@", plaintext);

@yushenNO1
Copy link
Author

好的,谢谢

Repository owner deleted a comment from yannvr Feb 23, 2024
@xiaohuiLoveming
Copy link

为什么,我用自己生成的公钥(代码里那个生成公私钥的方法)去加密,然后自己生成的私钥解密,然后会崩溃啊

@xiaohuiLoveming
Copy link

NSString *pubKey = @"0408E3FFF9505BCFAF9307E665E9229F4E1B3936437A870407EA3D97886BAFBC9"
"C624537215DE9507BC0E2DD276CF74695C99DF42424F28E9004CDE4678F63D698";
// 私钥
NSString *prikey = @"90F3A42B9FE24AB196305FD92EC82E647616C3A3694441FB3422E7838E24DEAE";
NSString *plaintext = @"123456";
NSString *enResult1 = [GMSm2Utils encryptText:plaintext publicKey:pubKey];
NSString *deResult1 = [GMSm2Utils decryptToText:enResult1 privateKey:priKey];
demo代码里面的,到解密时候,会崩溃,在if(!sm2_plaintext_size(cipher_bytes,ctext_len,&ptext_len))
在这一行崩溃掉

@muzipiao
Copy link
Owner

muzipiao commented Nov 5, 2024

你在 Demo 中测试一下你的代码,如果无错误,大概率是项目中的 OpenSSL 版本低导致,低于OpenSSL 1.1.1l 的版本。

  1. 方法1:你项目可能有多个 OpenSSL,升级项目 OpenSSL 版本为 OpenSSL 1.1.1l 以上版本,版本可参考 GMOpenSSL;
  2. 方法2:集成 GMObjC 源码,参考Git记录的这一次提交update 3.2.1 cb8e788 2021年10月8日 15:31还原这一行代码;
-        if (!sm2_plaintext_size(key, digest, ctext_len, &ptext_len)) {
+        if (!sm2_plaintext_size(cipher_bytes, ctext_len, &ptext_len)) {

注意:OpenSSL 1.1.1l 前后此 API 方法sm2_plaintext_size有较大变化,需要对应。

@xiaohuiLoveming
Copy link

我是昨天直接使用pod GMObjC的,我看到pods里面有GMObjC和GMOpenSSL这两个文件包的。我刚才使用openssl version 这个代码在终端中看到LibreSSL 3.3.6 这个版本咋这么高啊,是不是不对啊

@muzipiao
Copy link
Owner

muzipiao commented Nov 5, 2024

  1. 你是在 Mac 电脑终端里执行的openssl version吧?电脑的的 OpenSSL 版本和项目没有一毛钱关系,Mac电脑自带的一般是LibreSSL 3.3.6
  2. OpenSSL 版本低,我指的项目里面可能存在多个 OpenSSL,执行代码时调用的是低版本的 OpenSSL;
  3. 你把 GMObjC 项目下载下来,或者新建一个干净的 Demo,你上面的代码运行应该算没问题的。

@xiaohuiLoveming
Copy link

是的,你得demo没问题,我刚运行了,是可以的,我排查下项目中的openSSL,刚看到一个-framework "OpenSSL"的,这个我改成-Objc-l"GMObjC" -framework "OpenSSL"就可以了吧

@xiaohuiLoveming
Copy link

还是报错,我执行了pod GMObjC 和 pod GMOpenSSL(是3.0.5)版本的(OpenSSL)这次应该是高于1.1.1l了吧,不是3.0.8,这个版本应该没问题的吧,为啥还是解密报错,还是那个错误,

@xiaohuiLoveming
Copy link

xiaohuiLoveming commented Nov 5, 2024 via email

@xiaohuiLoveming
Copy link

xiaohuiLoveming commented Nov 6, 2024 via email

@muzipiao
Copy link
Owner

muzipiao commented Nov 6, 2024

  1. 版本排序abcdefghijklmnopqrstuvwxyz,g 的版本比 l 低;
  2. GMObjC 仅仅是对 OpenSSL 中的国密加密封装,GMObjC 文件中的源码可自行修改;
  3. 最简单的方法是共用项目的 1.1.1g,将 GMObjC 文件夹拖入项目集成源码,还原sm2_plaintext_size方法即可;
  4. 另外一种方法是使用 Carthage 编译 GMObjC 为动态库,项目保留2套OpenSSL库,可参考 Readme 文档。

@xiaohuiLoveming
Copy link

xiaohuiLoveming commented Nov 6, 2024 via email

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants