1# 使用SM2密文格式转换(C/C++) 2 3<!--Kit: Crypto Architecture Kit--> 4<!--Subsystem: Security--> 5<!--Owner: @zxz--3--> 6<!--Designer: @lanming--> 7<!--Tester: @PAFT--> 8<!--Adviser: @zengyawen--> 9 10当前支持的SM2密文格式为国密标准的ASN.1格式,其中各参数组合顺序为C1C3C2,具体参数含义请参考[转换SM2密文格式](crypto-asym-encrypt-decrypt-spec.md#转换sm2密文格式)。 11 12开发者可指定SM2密文的参数,将其转换成符合国密标准的ASN.1格式密文。反之,也可以从国密标准的ASN.1格式密文中取出具体的SM2密文参数,便于开发者自行组合成其他格式的SM2密文。 13 14**指定密文参数,生成标准ASN.1密文** 15 161. 调用[OH_CryptoSm2CiphertextSpec_Create](../../reference/apis-crypto-architecture-kit/capi-crypto-asym-cipher-h.md#oh_cryptosm2ciphertextspec_create),创建空的SM2密文规格对象。 17 182. 调用[OH_CryptoSm2CiphertextSpec_SetItem](../../reference/apis-crypto-architecture-kit/capi-crypto-asym-cipher-h.md#oh_cryptosm2ciphertextspec_setitem),设置密文的各个参数(C1.x、C1.y、C2、C3)。 19 203. 调用[OH_CryptoSm2CiphertextSpec_Encode](../../reference/apis-crypto-architecture-kit/capi-crypto-asym-cipher-h.md#oh_cryptosm2ciphertextspec_encode),生成ASN.1格式的密文(当前密文转换仅支持SM3,实现中只校验hash长度是否为32字节)。 21 224. 使用完毕后,调用[OH_CryptoSm2CiphertextSpec_Destroy](../../reference/apis-crypto-architecture-kit/capi-crypto-asym-cipher-h.md#oh_cryptosm2ciphertextspec_destroy)销毁SM2密文规格对象。 23 24```C++ 25#include "CryptoArchitectureKit/crypto_architecture_kit.h" 26 27static OH_Crypto_ErrCode doTestGenCipherTextBySpec() 28{ 29 // 准备SM2密文参数。 30 uint8_t c1x[] = {45, 153, 88, 82, 104, 221, 226, 43, 174, 21, 122, 248, 5, 232, 105, 41, 92, 95, 102, 224, 31 216, 149, 85, 236, 110, 6, 64, 188, 149, 70, 70, 183}; 32 uint8_t c1y[] = {107, 93, 198, 247, 119, 18, 40, 110, 90, 156, 193, 158, 205, 113, 170, 128, 146, 109, 75, 33 17, 181, 109, 110, 91, 149, 5, 110, 233, 209, 78, 229, 96}; 34 uint8_t c2[] = {100, 227, 78, 195, 249, 179, 43, 70, 242, 69, 169, 10, 65, 123}; 35 uint8_t c3[] = {87, 167, 167, 247, 88, 146, 203, 234, 83, 126, 117, 129, 52, 142, 82, 54, 152, 226, 201, 111, 36 143, 115, 169, 125, 128, 42, 157, 31, 114, 198, 109, 244}; 37 38 // 创建空的SM2密文规格对象。 39 OH_CryptoSm2CiphertextSpec *sm2CipherSpec = nullptr; 40 OH_Crypto_ErrCode ret = OH_CryptoSm2CiphertextSpec_Create(nullptr, &sm2CipherSpec); 41 if (ret != CRYPTO_SUCCESS) { 42 return ret; 43 } 44 45 // 设置各个参数。 46 Crypto_DataBlob c1xBlob = {c1x, sizeof(c1x)}; 47 Crypto_DataBlob c1yBlob = {c1y, sizeof(c1y)}; 48 Crypto_DataBlob c2Blob = {c2, sizeof(c2)}; 49 Crypto_DataBlob c3Blob = {c3, sizeof(c3)}; 50 51 ret = OH_CryptoSm2CiphertextSpec_SetItem(sm2CipherSpec, CRYPTO_SM2_CIPHERTEXT_C1_X, &c1xBlob); 52 if (ret != CRYPTO_SUCCESS) { 53 OH_CryptoSm2CiphertextSpec_Destroy(sm2CipherSpec); 54 return ret; 55 } 56 ret = OH_CryptoSm2CiphertextSpec_SetItem(sm2CipherSpec, CRYPTO_SM2_CIPHERTEXT_C1_Y, &c1yBlob); 57 if (ret != CRYPTO_SUCCESS) { 58 OH_CryptoSm2CiphertextSpec_Destroy(sm2CipherSpec); 59 return ret; 60 } 61 ret = OH_CryptoSm2CiphertextSpec_SetItem(sm2CipherSpec, CRYPTO_SM2_CIPHERTEXT_C2, &c2Blob); 62 if (ret != CRYPTO_SUCCESS) { 63 OH_CryptoSm2CiphertextSpec_Destroy(sm2CipherSpec); 64 return ret; 65 } 66 ret = OH_CryptoSm2CiphertextSpec_SetItem(sm2CipherSpec, CRYPTO_SM2_CIPHERTEXT_C3, &c3Blob); 67 if (ret != CRYPTO_SUCCESS) { 68 OH_CryptoSm2CiphertextSpec_Destroy(sm2CipherSpec); 69 return ret; 70 } 71 72 // 编码为ASN.1格式。 73 Crypto_DataBlob encoded = { 0 }; 74 ret = OH_CryptoSm2CiphertextSpec_Encode(sm2CipherSpec, &encoded); 75 if (ret != CRYPTO_SUCCESS) { 76 OH_CryptoSm2CiphertextSpec_Destroy(sm2CipherSpec); 77 return ret; 78 } 79 80 // 清理资源。 81 OH_Crypto_FreeDataBlob(&encoded); 82 OH_CryptoSm2CiphertextSpec_Destroy(sm2CipherSpec); 83 return ret; 84} 85``` 86 87**从标准ASN.1密文中获取密文参数** 88 891. 调用[OH_CryptoSm2CiphertextSpec_Create](../../reference/apis-crypto-architecture-kit/capi-crypto-asym-cipher-h.md#oh_cryptosm2ciphertextspec_create),从ASN.1格式密文创建SM2密文规格对象。 90 912. 调用[OH_CryptoSm2CiphertextSpec_GetItem](../../reference/apis-crypto-architecture-kit/capi-crypto-asym-cipher-h.md#oh_cryptosm2ciphertextspec_getitem),获取密文中的各个参数(C1.x、C1.y、C2、C3)。 92 933. 使用完毕后,调用[OH_CryptoSm2CiphertextSpec_Destroy](../../reference/apis-crypto-architecture-kit/capi-crypto-asym-cipher-h.md#oh_cryptosm2ciphertextspec_destroy)销毁SM2密文规格对象。 94 95```C++ 96include "CryptoArchitectureKit/crypto_architecture_kit.h" 97 98static OH_Crypto_ErrCode doTestGetCipherTextSpec() 99{ 100 // 准备标准ASN.1格式密文。 101 uint8_t cipherTextArray[] = {48, 118, 2, 32, 45, 153, 88, 82, 104, 221, 226, 43, 174, 21, 122, 248, 5, 232, 105, 102 41, 92, 95, 102, 224, 216, 149, 85, 236, 110, 6, 64, 188, 149, 70, 70, 183, 2, 32, 107, 103 93, 198, 247, 119, 18, 40, 110, 90, 156, 193, 158, 205, 113, 170, 128, 146, 109, 75, 17, 104 181, 109, 110, 91, 149, 5, 110, 233, 209, 78, 229, 96, 4, 32, 87, 167, 167, 247, 88, 146, 105 203, 234, 83, 126, 117, 129, 52, 142, 82, 54, 152, 226, 201, 111, 143, 115, 169, 125, 128, 106 42, 157, 31, 114, 198, 109, 244, 4, 14, 100, 227, 78, 195, 249, 179, 43, 70, 242, 69, 169, 107 10, 65, 123}; 108 Crypto_DataBlob cipherText = {cipherTextArray, sizeof(cipherTextArray)}; 109 110 // 从ASN.1格式密文创建SM2密文规格对象。 111 OH_CryptoSm2CiphertextSpec *sm2CipherSpec = nullptr; 112 OH_Crypto_ErrCode ret = OH_CryptoSm2CiphertextSpec_Create(&cipherText, &sm2CipherSpec); 113 if (ret != CRYPTO_SUCCESS) { 114 return ret; 115 } 116 117 // 获取各个参数。 118 Crypto_DataBlob c1x = { 0 }; 119 Crypto_DataBlob c1y = { 0 }; 120 Crypto_DataBlob c2 = { 0 }; 121 Crypto_DataBlob c3 = { 0 }; 122 123 ret = OH_CryptoSm2CiphertextSpec_GetItem(sm2CipherSpec, CRYPTO_SM2_CIPHERTEXT_C1_X, &c1x); 124 if (ret != CRYPTO_SUCCESS) { 125 goto EXIT; 126 } 127 ret = OH_CryptoSm2CiphertextSpec_GetItem(sm2CipherSpec, CRYPTO_SM2_CIPHERTEXT_C1_Y, &c1y); 128 if (ret != CRYPTO_SUCCESS) { 129 goto EXIT; 130 } 131 ret = OH_CryptoSm2CiphertextSpec_GetItem(sm2CipherSpec, CRYPTO_SM2_CIPHERTEXT_C2, &c2); 132 if (ret != CRYPTO_SUCCESS) { 133 goto EXIT; 134 } 135 ret = OH_CryptoSm2CiphertextSpec_GetItem(sm2CipherSpec, CRYPTO_SM2_CIPHERTEXT_C3, &c3); 136 if (ret != CRYPTO_SUCCESS) { 137 goto EXIT; 138 } 139 140EXIT: 141 OH_Crypto_FreeDataBlob(&c1x); 142 OH_Crypto_FreeDataBlob(&c1y); 143 OH_Crypto_FreeDataBlob(&c2); 144 OH_Crypto_FreeDataBlob(&c3); 145 OH_CryptoSm2CiphertextSpec_Destroy(sm2CipherSpec); 146 return ret; 147} 148``` 149