xref: /OK3568_Linux_fs/u-boot/cmd/crypto.c (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun // SPDX-License-Identifier: GPL-2.0
2*4882a593Smuzhiyun /*
3*4882a593Smuzhiyun  * Copyright (c) 2019 Fuzhou Rockchip Electronics Co., Ltd
4*4882a593Smuzhiyun  */
5*4882a593Smuzhiyun 
6*4882a593Smuzhiyun #include <common.h>
7*4882a593Smuzhiyun #include <command.h>
8*4882a593Smuzhiyun #include <crypto.h>
9*4882a593Smuzhiyun #include <dm.h>
10*4882a593Smuzhiyun #include <u-boot/md5.h>
11*4882a593Smuzhiyun #include <u-boot/sha1.h>
12*4882a593Smuzhiyun #include <u-boot/sha256.h>
13*4882a593Smuzhiyun #include <u-boot/sha512.h>
14*4882a593Smuzhiyun #include <rockchip/crypto_fix_test_data.h>
15*4882a593Smuzhiyun 
16*4882a593Smuzhiyun #define PERF_TOTAL_SIZE			(128 * 1024 * 1024)
17*4882a593Smuzhiyun #define PERF_BUFF_SIZE			(4 * 1024 * 1024)
18*4882a593Smuzhiyun 
19*4882a593Smuzhiyun #define CALC_RATE_MPBS(bytes, ms)	(((bytes) / 1024) / (ms))
20*4882a593Smuzhiyun 
21*4882a593Smuzhiyun struct hash_test_data {
22*4882a593Smuzhiyun 	const char	*algo_name;
23*4882a593Smuzhiyun 	const char	*mode_name;
24*4882a593Smuzhiyun 	u32		algo;
25*4882a593Smuzhiyun 	const u8	*data;
26*4882a593Smuzhiyun 	u32		data_len;
27*4882a593Smuzhiyun 	const u8	*hash;
28*4882a593Smuzhiyun 	u32		hash_len;
29*4882a593Smuzhiyun 	const u8	*key;
30*4882a593Smuzhiyun 	u32		key_len;
31*4882a593Smuzhiyun };
32*4882a593Smuzhiyun 
33*4882a593Smuzhiyun struct cipher_test_data {
34*4882a593Smuzhiyun 	const char	*algo_name;
35*4882a593Smuzhiyun 	const char	*mode_name;
36*4882a593Smuzhiyun 	u32		algo;
37*4882a593Smuzhiyun 	u32		mode;
38*4882a593Smuzhiyun 	const u8	*key;
39*4882a593Smuzhiyun 	const u8	*twk_key;
40*4882a593Smuzhiyun 	u32		key_len;
41*4882a593Smuzhiyun 	const u8	*iv;
42*4882a593Smuzhiyun 	u32		iv_len;
43*4882a593Smuzhiyun 	const u8	*plain;
44*4882a593Smuzhiyun 	u32		plain_len;
45*4882a593Smuzhiyun 	const u8	*cipher;
46*4882a593Smuzhiyun 	u32		cipher_len;
47*4882a593Smuzhiyun 	const u8	*aad;
48*4882a593Smuzhiyun 	u32		aad_len;
49*4882a593Smuzhiyun 	const u8	*tag;
50*4882a593Smuzhiyun 	u32		tag_len;
51*4882a593Smuzhiyun };
52*4882a593Smuzhiyun 
53*4882a593Smuzhiyun struct rsa_test_data {
54*4882a593Smuzhiyun 	const char	*algo_name;
55*4882a593Smuzhiyun 	const char	*mode_name;
56*4882a593Smuzhiyun 	u32		algo;
57*4882a593Smuzhiyun 	const u8	*n;
58*4882a593Smuzhiyun 	u32		n_len;
59*4882a593Smuzhiyun 	const u8	*e;
60*4882a593Smuzhiyun 	u32		e_len;
61*4882a593Smuzhiyun 	const u8	*d;
62*4882a593Smuzhiyun 	u32		d_len;
63*4882a593Smuzhiyun 	const u8	*c;
64*4882a593Smuzhiyun 	u32		c_len;
65*4882a593Smuzhiyun 	const u8	*sign_in;
66*4882a593Smuzhiyun 	u32		sign_in_len;
67*4882a593Smuzhiyun 	const u8	*sign_out;
68*4882a593Smuzhiyun 	u32		sign_out_len;
69*4882a593Smuzhiyun };
70*4882a593Smuzhiyun 
71*4882a593Smuzhiyun #define IS_MAC_MODE(mode)	((mode) == RK_MODE_CBC_MAC || \
72*4882a593Smuzhiyun 				 (mode) == RK_MODE_CMAC)
73*4882a593Smuzhiyun 
74*4882a593Smuzhiyun #define IS_AE_MODE(mode)	((mode) == RK_MODE_CCM || \
75*4882a593Smuzhiyun 				 (mode) == RK_MODE_GCM)
76*4882a593Smuzhiyun #define HASH_TEST(algo_type, data_in, hash_val) {\
77*4882a593Smuzhiyun 	.algo_name = "HASH", \
78*4882a593Smuzhiyun 	.mode_name = #algo_type, \
79*4882a593Smuzhiyun 	.algo      = CRYPTO_##algo_type, \
80*4882a593Smuzhiyun 	.data      = (data_in),\
81*4882a593Smuzhiyun 	.data_len  = sizeof(data_in), \
82*4882a593Smuzhiyun 	.hash      = (hash_val), \
83*4882a593Smuzhiyun 	.hash_len  = sizeof(hash_val) \
84*4882a593Smuzhiyun }
85*4882a593Smuzhiyun 
86*4882a593Smuzhiyun #define HMAC_TEST(algo_type, data_in, hash_val, hmac_key) {\
87*4882a593Smuzhiyun 	.algo_name = "HMAC", \
88*4882a593Smuzhiyun 	.mode_name = #algo_type, \
89*4882a593Smuzhiyun 	.algo      = CRYPTO_HMAC_##algo_type, \
90*4882a593Smuzhiyun 	.data      = (data_in),\
91*4882a593Smuzhiyun 	.data_len  = sizeof(data_in), \
92*4882a593Smuzhiyun 	.hash      = (hash_val), \
93*4882a593Smuzhiyun 	.hash_len  = sizeof(hash_val), \
94*4882a593Smuzhiyun 	.key       = (hmac_key), \
95*4882a593Smuzhiyun 	.key_len   = sizeof(hmac_key)\
96*4882a593Smuzhiyun }
97*4882a593Smuzhiyun 
98*4882a593Smuzhiyun #define CIPHER_XTS_TEST(algo_type, mode_type, key1, key2, iv_val, in, out) { \
99*4882a593Smuzhiyun 	.algo_name  = #algo_type, \
100*4882a593Smuzhiyun 	.mode_name  = #mode_type, \
101*4882a593Smuzhiyun 	.algo       = CRYPTO_##algo_type,\
102*4882a593Smuzhiyun 	.mode       = RK_MODE_##mode_type, \
103*4882a593Smuzhiyun 	.key        = (key1), \
104*4882a593Smuzhiyun 	.twk_key    = (key2), \
105*4882a593Smuzhiyun 	.key_len    = sizeof(key1), \
106*4882a593Smuzhiyun 	.iv         = (iv_val), \
107*4882a593Smuzhiyun 	.iv_len     = sizeof(iv_val), \
108*4882a593Smuzhiyun 	.plain      = (in), \
109*4882a593Smuzhiyun 	.plain_len  = sizeof(in), \
110*4882a593Smuzhiyun 	.cipher     = (out), \
111*4882a593Smuzhiyun 	.cipher_len = sizeof(out) \
112*4882a593Smuzhiyun }
113*4882a593Smuzhiyun 
114*4882a593Smuzhiyun #define CIPHER_TEST(algo, mode, key, iv, plain, cipher) \
115*4882a593Smuzhiyun 		CIPHER_XTS_TEST(algo, mode, key, NULL, iv, plain, cipher)
116*4882a593Smuzhiyun 
117*4882a593Smuzhiyun #define CIPHER_AE_TEST(algo_type, mode_type, key_val, iv_val, \
118*4882a593Smuzhiyun 		       in, out, aad_val, tag_val) { \
119*4882a593Smuzhiyun 	.algo_name  = #algo_type, \
120*4882a593Smuzhiyun 	.mode_name  = #mode_type, \
121*4882a593Smuzhiyun 	.algo       = CRYPTO_##algo_type,\
122*4882a593Smuzhiyun 	.mode       = RK_MODE_##mode_type, \
123*4882a593Smuzhiyun 	.key        = (key_val), \
124*4882a593Smuzhiyun 	.key_len    = sizeof(key_val), \
125*4882a593Smuzhiyun 	.iv         = (iv_val), \
126*4882a593Smuzhiyun 	.iv_len     = sizeof(iv_val), \
127*4882a593Smuzhiyun 	.plain      = (in), \
128*4882a593Smuzhiyun 	.plain_len  = sizeof(in), \
129*4882a593Smuzhiyun 	.cipher     = (out), \
130*4882a593Smuzhiyun 	.cipher_len = sizeof(out), \
131*4882a593Smuzhiyun 	.aad        = (aad_val), \
132*4882a593Smuzhiyun 	.aad_len    = sizeof(aad_val), \
133*4882a593Smuzhiyun 	.tag        = (tag_val), \
134*4882a593Smuzhiyun 	.tag_len    = sizeof(tag_val), \
135*4882a593Smuzhiyun }
136*4882a593Smuzhiyun 
137*4882a593Smuzhiyun #define RSA_TEST(nbits, bn, be, bc, bd, in, out) { \
138*4882a593Smuzhiyun 	.algo_name    = "RSA", \
139*4882a593Smuzhiyun 	.mode_name    = #nbits, \
140*4882a593Smuzhiyun 	.algo         = CRYPTO_RSA##nbits, \
141*4882a593Smuzhiyun 	.n            = (bn), \
142*4882a593Smuzhiyun 	.n_len        = sizeof(bn), \
143*4882a593Smuzhiyun 	.e            = (be), \
144*4882a593Smuzhiyun 	.e_len        = sizeof(be), \
145*4882a593Smuzhiyun 	.d            = (bd), \
146*4882a593Smuzhiyun 	.d_len        = sizeof(bd), \
147*4882a593Smuzhiyun 	.c            = (bc), \
148*4882a593Smuzhiyun 	.c_len        = sizeof(bc), \
149*4882a593Smuzhiyun 	.sign_in      = (in), \
150*4882a593Smuzhiyun 	.sign_in_len  = sizeof(in), \
151*4882a593Smuzhiyun 	.sign_out     = (out), \
152*4882a593Smuzhiyun 	.sign_out_len = sizeof(out) \
153*4882a593Smuzhiyun }
154*4882a593Smuzhiyun 
155*4882a593Smuzhiyun #define EMPTY_TEST() {}
156*4882a593Smuzhiyun 
157*4882a593Smuzhiyun const struct hash_test_data hash_data_set[] = {
158*4882a593Smuzhiyun 	HASH_TEST(MD5,    foo_data, hash_md5),
159*4882a593Smuzhiyun 	HASH_TEST(SHA1,   foo_data, hash_sha1),
160*4882a593Smuzhiyun 	HASH_TEST(SHA256, foo_data, hash_sha256),
161*4882a593Smuzhiyun 	HASH_TEST(SHA512, foo_data, hash_sha512),
162*4882a593Smuzhiyun 	HASH_TEST(SM3,    foo_data, hash_sm3),
163*4882a593Smuzhiyun 
164*4882a593Smuzhiyun #if CONFIG_IS_ENABLED(ROCKCHIP_HMAC)
165*4882a593Smuzhiyun 	EMPTY_TEST(),
166*4882a593Smuzhiyun 	HMAC_TEST(MD5,    foo_data, hmac_md5,    hmac_key),
167*4882a593Smuzhiyun 	HMAC_TEST(SHA1,   foo_data, hmac_sha1,   hmac_key),
168*4882a593Smuzhiyun 	HMAC_TEST(SHA256, foo_data, hmac_sha256, hmac_key),
169*4882a593Smuzhiyun 	HMAC_TEST(SHA512, foo_data, hmac_sha512, hmac_key),
170*4882a593Smuzhiyun 	HMAC_TEST(SM3,    foo_data, hmac_sm3,    hmac_key),
171*4882a593Smuzhiyun #endif
172*4882a593Smuzhiyun };
173*4882a593Smuzhiyun 
174*4882a593Smuzhiyun const struct cipher_test_data cipher_data_set[] = {
175*4882a593Smuzhiyun #if CONFIG_IS_ENABLED(ROCKCHIP_CIPHER)
176*4882a593Smuzhiyun 	CIPHER_TEST(DES, ECB, des_key, des_iv, foo_data, des_ecb_cipher),
177*4882a593Smuzhiyun 	CIPHER_TEST(DES, CBC, des_key, des_iv, foo_data, des_cbc_cipher),
178*4882a593Smuzhiyun 	CIPHER_TEST(DES, CFB, des_key, des_iv, foo_data, des_cfb_cipher),
179*4882a593Smuzhiyun 	CIPHER_TEST(DES, OFB, des_key, des_iv, foo_data, des_ofb_cipher),
180*4882a593Smuzhiyun 
181*4882a593Smuzhiyun 	EMPTY_TEST(),
182*4882a593Smuzhiyun 	CIPHER_TEST(DES, ECB, tdes_key, tdes_iv, foo_data, tdes_ecb_cipher),
183*4882a593Smuzhiyun 	CIPHER_TEST(DES, CBC, tdes_key, tdes_iv, foo_data, tdes_cbc_cipher),
184*4882a593Smuzhiyun 	CIPHER_TEST(DES, CFB, tdes_key, tdes_iv, foo_data, tdes_cfb_cipher),
185*4882a593Smuzhiyun 	CIPHER_TEST(DES, OFB, tdes_key, tdes_iv, foo_data, tdes_ofb_cipher),
186*4882a593Smuzhiyun 
187*4882a593Smuzhiyun 	EMPTY_TEST(),
188*4882a593Smuzhiyun 	CIPHER_TEST(AES, ECB, aes_key, aes_iv, foo_data, aes_ecb_cipher),
189*4882a593Smuzhiyun 	CIPHER_TEST(AES, CBC, aes_key, aes_iv, foo_data, aes_cbc_cipher),
190*4882a593Smuzhiyun 	CIPHER_TEST(AES, CFB, aes_key, aes_iv, foo_data, aes_cfb_cipher),
191*4882a593Smuzhiyun 	CIPHER_TEST(AES, OFB, aes_key, aes_iv, foo_data, aes_ofb_cipher),
192*4882a593Smuzhiyun 	CIPHER_TEST(AES, CTS, aes_key, aes_iv, foo_data, aes_cts_cipher),
193*4882a593Smuzhiyun 	CIPHER_TEST(AES, CTR, aes_key, aes_iv, foo_data, aes_ctr_cipher),
194*4882a593Smuzhiyun 	CIPHER_XTS_TEST(AES, XTS, aes_key, aes_twk_key,
195*4882a593Smuzhiyun 			aes_iv, foo_data, aes_xts_cipher),
196*4882a593Smuzhiyun 	CIPHER_TEST(AES, CBC_MAC, aes_key, aes_iv, foo_data, aes_cbc_mac),
197*4882a593Smuzhiyun 	CIPHER_TEST(AES, CMAC, aes_key, aes_iv, foo_data, aes_cmac),
198*4882a593Smuzhiyun 	CIPHER_AE_TEST(AES, CCM, aes_key, aes_ccm_iv, foo_data, aes_ccm_cipher,
199*4882a593Smuzhiyun 		       ad_data, aes_ccm_tag),
200*4882a593Smuzhiyun 	CIPHER_AE_TEST(AES, GCM, aes_key, aes_iv, foo_data, aes_gcm_cipher,
201*4882a593Smuzhiyun 		       ad_data, aes_gcm_tag),
202*4882a593Smuzhiyun 
203*4882a593Smuzhiyun 	EMPTY_TEST(),
204*4882a593Smuzhiyun 	CIPHER_TEST(SM4, ECB, sm4_key, sm4_iv, foo_data, sm4_ecb_cipher),
205*4882a593Smuzhiyun 	CIPHER_TEST(SM4, CBC, sm4_key, sm4_iv, foo_data, sm4_cbc_cipher),
206*4882a593Smuzhiyun 	CIPHER_TEST(SM4, CFB, sm4_key, sm4_iv, foo_data, sm4_cfb_cipher),
207*4882a593Smuzhiyun 	CIPHER_TEST(SM4, OFB, sm4_key, sm4_iv, foo_data, sm4_ofb_cipher),
208*4882a593Smuzhiyun 	CIPHER_TEST(SM4, CTS, sm4_key, sm4_iv, foo_data, sm4_cts_cipher),
209*4882a593Smuzhiyun 	CIPHER_TEST(SM4, CTR, sm4_key, sm4_iv, foo_data, sm4_ctr_cipher),
210*4882a593Smuzhiyun 	CIPHER_XTS_TEST(SM4, XTS, sm4_key, sm4_twk_key,
211*4882a593Smuzhiyun 			sm4_iv, foo_data, sm4_xts_cipher),
212*4882a593Smuzhiyun 	CIPHER_TEST(SM4, CBC_MAC, sm4_key, sm4_iv, foo_data, sm4_cbc_mac),
213*4882a593Smuzhiyun 	CIPHER_TEST(SM4, CMAC, sm4_key, sm4_iv, foo_data, sm4_cmac),
214*4882a593Smuzhiyun 	CIPHER_AE_TEST(SM4, CCM, sm4_key, sm4_ccm_iv, foo_data, sm4_ccm_cipher,
215*4882a593Smuzhiyun 		       ad_data, sm4_ccm_tag),
216*4882a593Smuzhiyun 	CIPHER_AE_TEST(SM4, GCM, sm4_key, sm4_iv, foo_data, sm4_gcm_cipher,
217*4882a593Smuzhiyun 		       ad_data, sm4_gcm_tag),
218*4882a593Smuzhiyun #else
219*4882a593Smuzhiyun 	EMPTY_TEST(),
220*4882a593Smuzhiyun #endif
221*4882a593Smuzhiyun };
222*4882a593Smuzhiyun 
223*4882a593Smuzhiyun const struct rsa_test_data rsa_data_set[] = {
224*4882a593Smuzhiyun #if CONFIG_IS_ENABLED(ROCKCHIP_RSA)
225*4882a593Smuzhiyun 
226*4882a593Smuzhiyun #ifdef CONFIG_ROCKCHIP_CRYPTO_V1
227*4882a593Smuzhiyun 	RSA_TEST(2048, rsa2048_n, rsa2048_e, rsa2048_c, rsa2048_d,
228*4882a593Smuzhiyun 		 rsa2048_sign_in, rsa2048_sign_out),
229*4882a593Smuzhiyun #else
230*4882a593Smuzhiyun 	RSA_TEST(4096, rsa4096_n, rsa4096_e, NULL, rsa4096_d,
231*4882a593Smuzhiyun 		 rsa4096_sign_in, rsa4096_sign_out),
232*4882a593Smuzhiyun #endif
233*4882a593Smuzhiyun 
234*4882a593Smuzhiyun #else
235*4882a593Smuzhiyun 	EMPTY_TEST(),
236*4882a593Smuzhiyun #endif
237*4882a593Smuzhiyun };
238*4882a593Smuzhiyun 
dump_hex(const char * name,const u8 * array,u32 len)239*4882a593Smuzhiyun static void dump_hex(const char *name, const u8 *array, u32 len)
240*4882a593Smuzhiyun {
241*4882a593Smuzhiyun 	int i;
242*4882a593Smuzhiyun 
243*4882a593Smuzhiyun 	printf("[%s]: %uByte", name, len);
244*4882a593Smuzhiyun 	for (i = 0; i < len; i++) {
245*4882a593Smuzhiyun 		if (i % 32 == 0)
246*4882a593Smuzhiyun 			printf("\n");
247*4882a593Smuzhiyun 		printf("%02x ", array[i]);
248*4882a593Smuzhiyun 	}
249*4882a593Smuzhiyun 	printf("\n");
250*4882a593Smuzhiyun }
251*4882a593Smuzhiyun 
print_result_MBps(const char * algo_name,const char * mode_name,const char * crypt,ulong MBps,const u8 * expect,const u8 * actual,u32 len)252*4882a593Smuzhiyun static inline void print_result_MBps(const char *algo_name,
253*4882a593Smuzhiyun 				     const char *mode_name,
254*4882a593Smuzhiyun 				     const char *crypt, ulong MBps,
255*4882a593Smuzhiyun 				     const u8 *expect, const u8 *actual,
256*4882a593Smuzhiyun 				     u32 len)
257*4882a593Smuzhiyun {
258*4882a593Smuzhiyun 	if (memcmp(expect, actual, len) == 0) {
259*4882a593Smuzhiyun 		printf("[%s] %-8s%-8s PASS    (%luMBps)\n",
260*4882a593Smuzhiyun 		       algo_name, mode_name, crypt, MBps);
261*4882a593Smuzhiyun 	} else {
262*4882a593Smuzhiyun 		printf("[%s] %-8s%-8s FAIL\n",
263*4882a593Smuzhiyun 		       algo_name, mode_name, crypt);
264*4882a593Smuzhiyun 		dump_hex("expect", expect, len);
265*4882a593Smuzhiyun 		dump_hex("actual", actual, len);
266*4882a593Smuzhiyun 	}
267*4882a593Smuzhiyun }
268*4882a593Smuzhiyun 
print_result_ms(const char * algo_name,const char * mode_name,const char * crypt,ulong time_cost,const u8 * expect,const u8 * actual,u32 len)269*4882a593Smuzhiyun static inline void print_result_ms(const char *algo_name, const char *mode_name,
270*4882a593Smuzhiyun 				   const char *crypt, ulong time_cost,
271*4882a593Smuzhiyun 				   const u8 *expect, const u8 *actual, u32 len)
272*4882a593Smuzhiyun {
273*4882a593Smuzhiyun 	if (memcmp(expect, actual, len) == 0) {
274*4882a593Smuzhiyun 		printf("[%s] %-8s%-8s PASS    (%lums)\n",
275*4882a593Smuzhiyun 		       algo_name, mode_name, crypt, time_cost);
276*4882a593Smuzhiyun 	} else {
277*4882a593Smuzhiyun 		printf("[%s] %-8s%-8s FAIL\n",
278*4882a593Smuzhiyun 		       algo_name, mode_name, crypt);
279*4882a593Smuzhiyun 		dump_hex("expect", expect, len);
280*4882a593Smuzhiyun 		dump_hex("actual", actual, len);
281*4882a593Smuzhiyun 	}
282*4882a593Smuzhiyun }
283*4882a593Smuzhiyun 
test_hash_perf(struct udevice * dev,u32 algo,const u8 * key,u32 key_len,ulong * MBps)284*4882a593Smuzhiyun int test_hash_perf(struct udevice *dev, u32 algo,
285*4882a593Smuzhiyun 		   const u8 *key, u32 key_len, ulong *MBps)
286*4882a593Smuzhiyun {
287*4882a593Smuzhiyun 	u32 total_size = PERF_TOTAL_SIZE;
288*4882a593Smuzhiyun 	u32 data_size = PERF_BUFF_SIZE;
289*4882a593Smuzhiyun 	sha_context ctx;
290*4882a593Smuzhiyun 	u8 *data = NULL;
291*4882a593Smuzhiyun 	u8 hash_out[64];
292*4882a593Smuzhiyun 	int ret, i;
293*4882a593Smuzhiyun 
294*4882a593Smuzhiyun 	*MBps = 0;
295*4882a593Smuzhiyun 
296*4882a593Smuzhiyun 	ctx.algo = algo;
297*4882a593Smuzhiyun 	ctx.length = total_size;
298*4882a593Smuzhiyun 
299*4882a593Smuzhiyun 	data = (u8 *)memalign(CONFIG_SYS_CACHELINE_SIZE, data_size);
300*4882a593Smuzhiyun 	if (!data) {
301*4882a593Smuzhiyun 		printf("%s, %d: memalign %u error!\n",
302*4882a593Smuzhiyun 		       __func__, __LINE__, data_size);
303*4882a593Smuzhiyun 		return -EINVAL;
304*4882a593Smuzhiyun 	}
305*4882a593Smuzhiyun 
306*4882a593Smuzhiyun 	memset(data, 0xab, data_size);
307*4882a593Smuzhiyun 
308*4882a593Smuzhiyun 	ulong start = get_timer(0);
309*4882a593Smuzhiyun 
310*4882a593Smuzhiyun 	if (key)
311*4882a593Smuzhiyun 		ret = crypto_hmac_init(dev, &ctx, (u8 *)key, key_len);
312*4882a593Smuzhiyun 	else
313*4882a593Smuzhiyun 		ret = crypto_sha_init(dev, &ctx);
314*4882a593Smuzhiyun 
315*4882a593Smuzhiyun 	if (ret) {
316*4882a593Smuzhiyun 		printf("crypto_sha_init error ret = %d!\n", ret);
317*4882a593Smuzhiyun 		goto exit;
318*4882a593Smuzhiyun 	}
319*4882a593Smuzhiyun 
320*4882a593Smuzhiyun 	for (i = 0; i < total_size / data_size; i++) {
321*4882a593Smuzhiyun 		ret = crypto_sha_update(dev, (u32 *)data, data_size);
322*4882a593Smuzhiyun 		if (ret) {
323*4882a593Smuzhiyun 			printf("crypto_sha_update error!\n");
324*4882a593Smuzhiyun 			goto exit;
325*4882a593Smuzhiyun 		}
326*4882a593Smuzhiyun 	}
327*4882a593Smuzhiyun 
328*4882a593Smuzhiyun 	ret = crypto_sha_final(dev, &ctx, hash_out);
329*4882a593Smuzhiyun 	if (ret) {
330*4882a593Smuzhiyun 		printf("crypto_sha_final error ret = %d!\n", ret);
331*4882a593Smuzhiyun 		goto exit;
332*4882a593Smuzhiyun 	}
333*4882a593Smuzhiyun 
334*4882a593Smuzhiyun 	ulong time_cost = get_timer(start);
335*4882a593Smuzhiyun 
336*4882a593Smuzhiyun 	*MBps = CALC_RATE_MPBS(total_size, time_cost);
337*4882a593Smuzhiyun 
338*4882a593Smuzhiyun exit:
339*4882a593Smuzhiyun 	free(data);
340*4882a593Smuzhiyun 
341*4882a593Smuzhiyun 	return ret;
342*4882a593Smuzhiyun }
343*4882a593Smuzhiyun 
test_cipher_perf(struct udevice * dev,cipher_context * ctx,ulong * MBps,bool enc)344*4882a593Smuzhiyun int test_cipher_perf(struct udevice *dev, cipher_context *ctx,
345*4882a593Smuzhiyun 		     ulong *MBps, bool enc)
346*4882a593Smuzhiyun {
347*4882a593Smuzhiyun 	u32 total_size = PERF_TOTAL_SIZE;
348*4882a593Smuzhiyun 	u32 data_size = PERF_BUFF_SIZE;
349*4882a593Smuzhiyun 	u8 *plain = NULL, *cipher = NULL;
350*4882a593Smuzhiyun 	u8 aad[128], tag[16];
351*4882a593Smuzhiyun 	int ret = 0, i;
352*4882a593Smuzhiyun 
353*4882a593Smuzhiyun 	*MBps = 0;
354*4882a593Smuzhiyun 
355*4882a593Smuzhiyun 	plain = (u8 *)memalign(CONFIG_SYS_CACHELINE_SIZE, data_size);
356*4882a593Smuzhiyun 	if (!plain) {
357*4882a593Smuzhiyun 		printf("%s, %d: memalign %u error!\n",
358*4882a593Smuzhiyun 		       __func__, __LINE__, data_size);
359*4882a593Smuzhiyun 		return -EINVAL;
360*4882a593Smuzhiyun 	}
361*4882a593Smuzhiyun 
362*4882a593Smuzhiyun 	cipher = (u8 *)memalign(CONFIG_SYS_CACHELINE_SIZE, data_size);
363*4882a593Smuzhiyun 	if (!cipher) {
364*4882a593Smuzhiyun 		printf("%s, %d: memalign %u error!\n",
365*4882a593Smuzhiyun 		       __func__, __LINE__, data_size);
366*4882a593Smuzhiyun 		free(plain);
367*4882a593Smuzhiyun 		return -EINVAL;
368*4882a593Smuzhiyun 	}
369*4882a593Smuzhiyun 
370*4882a593Smuzhiyun 	memset(plain, 0xab, data_size);
371*4882a593Smuzhiyun 	memset(aad, 0xcb, sizeof(aad));
372*4882a593Smuzhiyun 
373*4882a593Smuzhiyun 	ulong start = get_timer(0);
374*4882a593Smuzhiyun 
375*4882a593Smuzhiyun 	for (i = 0; i < total_size / data_size; i++) {
376*4882a593Smuzhiyun 		if (IS_MAC_MODE(ctx->mode))
377*4882a593Smuzhiyun 			ret = crypto_mac(dev, ctx, plain, data_size, cipher);
378*4882a593Smuzhiyun 		else if (IS_AE_MODE(ctx->mode))
379*4882a593Smuzhiyun 			ret = crypto_ae(dev, ctx, plain, data_size,
380*4882a593Smuzhiyun 					aad, sizeof(aad), cipher, tag);
381*4882a593Smuzhiyun 		else
382*4882a593Smuzhiyun 			ret = crypto_cipher(dev, ctx, plain, cipher,
383*4882a593Smuzhiyun 					    data_size, enc);
384*4882a593Smuzhiyun 		if (ret) {
385*4882a593Smuzhiyun 			printf("%s, %d:crypto calc error! ret = %d\n",
386*4882a593Smuzhiyun 			       __func__, __LINE__, ret);
387*4882a593Smuzhiyun 			goto exit;
388*4882a593Smuzhiyun 		}
389*4882a593Smuzhiyun 	}
390*4882a593Smuzhiyun 
391*4882a593Smuzhiyun 	ulong time_cost = get_timer(start);
392*4882a593Smuzhiyun 
393*4882a593Smuzhiyun 	*MBps = CALC_RATE_MPBS(total_size, time_cost);
394*4882a593Smuzhiyun exit:
395*4882a593Smuzhiyun 	free(plain);
396*4882a593Smuzhiyun 	free(cipher);
397*4882a593Smuzhiyun 
398*4882a593Smuzhiyun 	return ret;
399*4882a593Smuzhiyun }
400*4882a593Smuzhiyun 
test_hash_result(void)401*4882a593Smuzhiyun int test_hash_result(void)
402*4882a593Smuzhiyun {
403*4882a593Smuzhiyun 	const struct hash_test_data *test_data = NULL;
404*4882a593Smuzhiyun 	sha_context csha_ctx;
405*4882a593Smuzhiyun 	struct udevice *dev;
406*4882a593Smuzhiyun 	unsigned int i;
407*4882a593Smuzhiyun 	u8 out[64];
408*4882a593Smuzhiyun 	int ret;
409*4882a593Smuzhiyun 
410*4882a593Smuzhiyun 	printf("\n=================== hash & hmac test ===================\n");
411*4882a593Smuzhiyun 
412*4882a593Smuzhiyun 	for (i = 0; i < ARRAY_SIZE(hash_data_set); i++) {
413*4882a593Smuzhiyun 		test_data = &hash_data_set[i];
414*4882a593Smuzhiyun 		if (test_data->algo == 0) {
415*4882a593Smuzhiyun 			printf("\n");
416*4882a593Smuzhiyun 			continue;
417*4882a593Smuzhiyun 		}
418*4882a593Smuzhiyun 
419*4882a593Smuzhiyun 		dev = crypto_get_device(test_data->algo);
420*4882a593Smuzhiyun 		if (!dev) {
421*4882a593Smuzhiyun 			printf("[%s] %-16s unsupported!!!\n",
422*4882a593Smuzhiyun 			       test_data->algo_name,
423*4882a593Smuzhiyun 			       test_data->mode_name);
424*4882a593Smuzhiyun 			continue;
425*4882a593Smuzhiyun 		}
426*4882a593Smuzhiyun 
427*4882a593Smuzhiyun 		csha_ctx.algo   = test_data->algo;
428*4882a593Smuzhiyun 		csha_ctx.length = test_data->data_len;
429*4882a593Smuzhiyun 
430*4882a593Smuzhiyun 		memset(out, 0x00, sizeof(out));
431*4882a593Smuzhiyun 		if (test_data->key) {
432*4882a593Smuzhiyun 			ret = crypto_hmac_init(dev, &csha_ctx,
433*4882a593Smuzhiyun 					       (u8 *)test_data->key,
434*4882a593Smuzhiyun 					       test_data->key_len);
435*4882a593Smuzhiyun 			ret |= crypto_hmac_update(dev, (void *)test_data->data,
436*4882a593Smuzhiyun 						  test_data->data_len);
437*4882a593Smuzhiyun 			ret |= crypto_hmac_final(dev, &csha_ctx, out);
438*4882a593Smuzhiyun 			if (ret) {
439*4882a593Smuzhiyun 				printf("hmac calc error ret = %d\n", ret);
440*4882a593Smuzhiyun 				goto error;
441*4882a593Smuzhiyun 			}
442*4882a593Smuzhiyun 		} else {
443*4882a593Smuzhiyun 			ret = crypto_sha_init(dev, &csha_ctx);
444*4882a593Smuzhiyun 			ret |= crypto_sha_update(dev, (void *)test_data->data,
445*4882a593Smuzhiyun 						 test_data->data_len);
446*4882a593Smuzhiyun 			ret |= crypto_sha_final(dev, &csha_ctx, out);
447*4882a593Smuzhiyun 			if (ret) {
448*4882a593Smuzhiyun 				printf("hash calc error ret = %d\n", ret);
449*4882a593Smuzhiyun 				goto error;
450*4882a593Smuzhiyun 			}
451*4882a593Smuzhiyun 		}
452*4882a593Smuzhiyun 
453*4882a593Smuzhiyun 		ulong MBps = 0;
454*4882a593Smuzhiyun 
455*4882a593Smuzhiyun 		test_hash_perf(dev, test_data->algo,
456*4882a593Smuzhiyun 			       test_data->key, test_data->key_len, &MBps);
457*4882a593Smuzhiyun 		print_result_MBps(test_data->algo_name, test_data->mode_name,
458*4882a593Smuzhiyun 				  "", MBps, test_data->hash, out,
459*4882a593Smuzhiyun 				  test_data->hash_len);
460*4882a593Smuzhiyun 		printf("+++++++++++++++++++++++++++++++++++++++++++++++++++\n");
461*4882a593Smuzhiyun 	}
462*4882a593Smuzhiyun 
463*4882a593Smuzhiyun 	return 0;
464*4882a593Smuzhiyun error:
465*4882a593Smuzhiyun 	printf("%s %s test error!\n",
466*4882a593Smuzhiyun 	       test_data->algo_name, test_data->mode_name);
467*4882a593Smuzhiyun 	return ret;
468*4882a593Smuzhiyun }
469*4882a593Smuzhiyun 
test_cipher_result(void)470*4882a593Smuzhiyun int test_cipher_result(void)
471*4882a593Smuzhiyun {
472*4882a593Smuzhiyun 	const struct cipher_test_data *test_data = NULL;
473*4882a593Smuzhiyun 	struct udevice *dev;
474*4882a593Smuzhiyun 	cipher_context ctx;
475*4882a593Smuzhiyun 	u8 out[256], tag[16];
476*4882a593Smuzhiyun 	int ret;
477*4882a593Smuzhiyun 	u32 i;
478*4882a593Smuzhiyun 
479*4882a593Smuzhiyun 	printf("\n===================== cipher test ======================\n");
480*4882a593Smuzhiyun 
481*4882a593Smuzhiyun 	for (i = 0; i < ARRAY_SIZE(cipher_data_set); i++) {
482*4882a593Smuzhiyun 		test_data = &cipher_data_set[i];
483*4882a593Smuzhiyun 		if (test_data->algo == 0) {
484*4882a593Smuzhiyun 			printf("\n");
485*4882a593Smuzhiyun 			continue;
486*4882a593Smuzhiyun 		}
487*4882a593Smuzhiyun 
488*4882a593Smuzhiyun 		dev = crypto_get_device(test_data->algo);
489*4882a593Smuzhiyun 		if (!dev) {
490*4882a593Smuzhiyun 			printf("[%s] %-16s unsupported!!!\n",
491*4882a593Smuzhiyun 			       test_data->algo_name, test_data->mode_name);
492*4882a593Smuzhiyun 			continue;
493*4882a593Smuzhiyun 		}
494*4882a593Smuzhiyun 
495*4882a593Smuzhiyun 		memset(&ctx, 0x00, sizeof(ctx));
496*4882a593Smuzhiyun 
497*4882a593Smuzhiyun 		ctx.algo    = test_data->algo;
498*4882a593Smuzhiyun 		ctx.mode    = test_data->mode;
499*4882a593Smuzhiyun 		ctx.key     = test_data->key;
500*4882a593Smuzhiyun 		ctx.twk_key = test_data->twk_key;
501*4882a593Smuzhiyun 		ctx.key_len = test_data->key_len;
502*4882a593Smuzhiyun 		ctx.iv      = test_data->iv;
503*4882a593Smuzhiyun 		ctx.iv_len  = test_data->iv_len;
504*4882a593Smuzhiyun 
505*4882a593Smuzhiyun 		ulong MBps = 0;
506*4882a593Smuzhiyun 
507*4882a593Smuzhiyun 		test_cipher_perf(dev, &ctx, &MBps, true);
508*4882a593Smuzhiyun 
509*4882a593Smuzhiyun 		/* AES/SM4 mac */
510*4882a593Smuzhiyun 		if (IS_MAC_MODE(ctx.mode))
511*4882a593Smuzhiyun 			ret = crypto_mac(dev, &ctx, test_data->plain,
512*4882a593Smuzhiyun 					 test_data->plain_len, out);
513*4882a593Smuzhiyun 		else if (IS_AE_MODE(ctx.mode))
514*4882a593Smuzhiyun 			ret = crypto_ae(dev, &ctx,
515*4882a593Smuzhiyun 					test_data->plain, test_data->plain_len,
516*4882a593Smuzhiyun 					test_data->aad, test_data->aad_len,
517*4882a593Smuzhiyun 					out, tag);
518*4882a593Smuzhiyun 		else
519*4882a593Smuzhiyun 			ret = crypto_cipher(dev, &ctx, test_data->plain,
520*4882a593Smuzhiyun 					    out, test_data->plain_len, true);
521*4882a593Smuzhiyun 		if (ret)
522*4882a593Smuzhiyun 			goto error;
523*4882a593Smuzhiyun 
524*4882a593Smuzhiyun 		if (test_data->tag &&
525*4882a593Smuzhiyun 		    memcmp(test_data->tag, tag, test_data->tag_len) != 0) {
526*4882a593Smuzhiyun 			printf("tag mismatch!!!\n");
527*4882a593Smuzhiyun 			dump_hex("expect", test_data->tag, test_data->tag_len);
528*4882a593Smuzhiyun 			dump_hex("actual", tag, test_data->tag_len);
529*4882a593Smuzhiyun 			goto error;
530*4882a593Smuzhiyun 		}
531*4882a593Smuzhiyun 
532*4882a593Smuzhiyun 		print_result_MBps(test_data->algo_name, test_data->mode_name,
533*4882a593Smuzhiyun 				  "encrypt", MBps, test_data->cipher, out,
534*4882a593Smuzhiyun 				  test_data->cipher_len);
535*4882a593Smuzhiyun 
536*4882a593Smuzhiyun 		if (!IS_MAC_MODE(ctx.mode) && !IS_AE_MODE(ctx.mode)) {
537*4882a593Smuzhiyun 			test_cipher_perf(dev, &ctx, &MBps, false);
538*4882a593Smuzhiyun 			ret = crypto_cipher(dev, &ctx, test_data->cipher,
539*4882a593Smuzhiyun 					    out, test_data->cipher_len, false);
540*4882a593Smuzhiyun 			if (ret)
541*4882a593Smuzhiyun 				goto error;
542*4882a593Smuzhiyun 
543*4882a593Smuzhiyun 			print_result_MBps(test_data->algo_name,
544*4882a593Smuzhiyun 					  test_data->mode_name,
545*4882a593Smuzhiyun 					  "decrypt", MBps,
546*4882a593Smuzhiyun 					  test_data->plain, out,
547*4882a593Smuzhiyun 					  test_data->plain_len);
548*4882a593Smuzhiyun 		}
549*4882a593Smuzhiyun 		printf("+++++++++++++++++++++++++++++++++++++++++++++++++++\n");
550*4882a593Smuzhiyun 	}
551*4882a593Smuzhiyun 	return 0;
552*4882a593Smuzhiyun error:
553*4882a593Smuzhiyun 	printf("%s %s test error, ret = %d!\n",
554*4882a593Smuzhiyun 	       test_data->algo_name, test_data->mode_name, ret);
555*4882a593Smuzhiyun 	return ret;
556*4882a593Smuzhiyun }
557*4882a593Smuzhiyun 
test_rsa_result(void)558*4882a593Smuzhiyun int test_rsa_result(void)
559*4882a593Smuzhiyun {
560*4882a593Smuzhiyun 	const struct rsa_test_data *test_data = NULL;
561*4882a593Smuzhiyun 	u8 *hard_out = NULL, *e_tmp;
562*4882a593Smuzhiyun 	u32 data_size = 4096 / 8;
563*4882a593Smuzhiyun 	ulong start, time_cost;
564*4882a593Smuzhiyun 	struct udevice *dev;
565*4882a593Smuzhiyun 	rsa_key rsa_key;
566*4882a593Smuzhiyun 	int ret, i;
567*4882a593Smuzhiyun 
568*4882a593Smuzhiyun 	hard_out = (u8 *)memalign(CONFIG_SYS_CACHELINE_SIZE, data_size);
569*4882a593Smuzhiyun 	if (!hard_out) {
570*4882a593Smuzhiyun 		printf("%s, %d: memalign %u error!\n",
571*4882a593Smuzhiyun 		       __func__, __LINE__, data_size);
572*4882a593Smuzhiyun 		return -EINVAL;
573*4882a593Smuzhiyun 	}
574*4882a593Smuzhiyun 
575*4882a593Smuzhiyun 	e_tmp = (u8 *)memalign(CONFIG_SYS_CACHELINE_SIZE, data_size);
576*4882a593Smuzhiyun 	if (!e_tmp) {
577*4882a593Smuzhiyun 		printf("%s, %d: memalign %u error!\n",
578*4882a593Smuzhiyun 		       __func__, __LINE__, data_size);
579*4882a593Smuzhiyun 		return -EINVAL;
580*4882a593Smuzhiyun 	}
581*4882a593Smuzhiyun 
582*4882a593Smuzhiyun 	printf("\n====================== rsa test ========================\n");
583*4882a593Smuzhiyun 	for (i = 0; i < ARRAY_SIZE(rsa_data_set); i++) {
584*4882a593Smuzhiyun 		test_data = &rsa_data_set[i];
585*4882a593Smuzhiyun 		if (test_data->algo == 0) {
586*4882a593Smuzhiyun 			printf("\n");
587*4882a593Smuzhiyun 			continue;
588*4882a593Smuzhiyun 		}
589*4882a593Smuzhiyun 
590*4882a593Smuzhiyun 		dev = crypto_get_device(test_data->algo);
591*4882a593Smuzhiyun 		if (!dev) {
592*4882a593Smuzhiyun 			printf("[%s] %-16s unsupported!!!\n",
593*4882a593Smuzhiyun 			       test_data->algo_name, test_data->mode_name);
594*4882a593Smuzhiyun 			continue;
595*4882a593Smuzhiyun 		}
596*4882a593Smuzhiyun 
597*4882a593Smuzhiyun 		/* sign test */
598*4882a593Smuzhiyun 		memset(&rsa_key, 0x00, sizeof(rsa_key));
599*4882a593Smuzhiyun 		rsa_key.algo = test_data->algo;
600*4882a593Smuzhiyun 		rsa_key.n = (u32 *)test_data->n;
601*4882a593Smuzhiyun 		rsa_key.e = (u32 *)test_data->d;
602*4882a593Smuzhiyun #ifdef CONFIG_ROCKCHIP_CRYPTO_V1
603*4882a593Smuzhiyun 		rsa_key.c = (u32 *)test_data->c;
604*4882a593Smuzhiyun #endif
605*4882a593Smuzhiyun 
606*4882a593Smuzhiyun 		start = get_timer(0);
607*4882a593Smuzhiyun 		ret = crypto_rsa_verify(dev, &rsa_key,
608*4882a593Smuzhiyun 					(u8 *)test_data->sign_in, hard_out);
609*4882a593Smuzhiyun 		if (ret) {
610*4882a593Smuzhiyun 			printf("sign test error, ret = %d\n", ret);
611*4882a593Smuzhiyun 			goto error;
612*4882a593Smuzhiyun 		}
613*4882a593Smuzhiyun 		time_cost = get_timer(start);
614*4882a593Smuzhiyun 		print_result_ms(test_data->algo_name, test_data->mode_name,
615*4882a593Smuzhiyun 				"sign", time_cost, test_data->sign_out,
616*4882a593Smuzhiyun 				hard_out, test_data->n_len);
617*4882a593Smuzhiyun 
618*4882a593Smuzhiyun 		/* verify test */
619*4882a593Smuzhiyun 		memset(&rsa_key, 0x00, sizeof(rsa_key));
620*4882a593Smuzhiyun 		memset(e_tmp, 0x00, data_size);
621*4882a593Smuzhiyun 		memcpy(e_tmp, test_data->e, test_data->e_len);
622*4882a593Smuzhiyun 		rsa_key.algo = test_data->algo;
623*4882a593Smuzhiyun 		rsa_key.n = (u32 *)test_data->n;
624*4882a593Smuzhiyun 		rsa_key.e = (u32 *)e_tmp;
625*4882a593Smuzhiyun #ifdef CONFIG_ROCKCHIP_CRYPTO_V1
626*4882a593Smuzhiyun 		rsa_key.c = (u32 *)test_data->c;
627*4882a593Smuzhiyun #endif
628*4882a593Smuzhiyun 
629*4882a593Smuzhiyun 		start = get_timer(0);
630*4882a593Smuzhiyun 		ret = crypto_rsa_verify(dev, &rsa_key,
631*4882a593Smuzhiyun 					(u8 *)test_data->sign_out, hard_out);
632*4882a593Smuzhiyun 		if (ret) {
633*4882a593Smuzhiyun 			printf("verify test error, ret = %d\n", ret);
634*4882a593Smuzhiyun 			goto error;
635*4882a593Smuzhiyun 		}
636*4882a593Smuzhiyun 		time_cost = get_timer(start);
637*4882a593Smuzhiyun 
638*4882a593Smuzhiyun 		print_result_ms(test_data->algo_name, test_data->mode_name,
639*4882a593Smuzhiyun 				"verify", time_cost, test_data->sign_in,
640*4882a593Smuzhiyun 				hard_out, test_data->n_len);
641*4882a593Smuzhiyun 
642*4882a593Smuzhiyun 		printf("+++++++++++++++++++++++++++++++++++++++++++++++++++\n");
643*4882a593Smuzhiyun 	}
644*4882a593Smuzhiyun 
645*4882a593Smuzhiyun 	free(hard_out);
646*4882a593Smuzhiyun 	free(e_tmp);
647*4882a593Smuzhiyun 
648*4882a593Smuzhiyun 	return 0;
649*4882a593Smuzhiyun error:
650*4882a593Smuzhiyun 	free(hard_out);
651*4882a593Smuzhiyun 	free(e_tmp);
652*4882a593Smuzhiyun 	printf("%s %s test error!\n",
653*4882a593Smuzhiyun 	       test_data->algo_name, test_data->mode_name);
654*4882a593Smuzhiyun 	return ret;
655*4882a593Smuzhiyun }
656*4882a593Smuzhiyun 
test_all_result(void)657*4882a593Smuzhiyun static int test_all_result(void)
658*4882a593Smuzhiyun {
659*4882a593Smuzhiyun 	int ret = 0;
660*4882a593Smuzhiyun 
661*4882a593Smuzhiyun 	ret = test_hash_result();
662*4882a593Smuzhiyun 	if (ret)
663*4882a593Smuzhiyun 		goto exit;
664*4882a593Smuzhiyun 
665*4882a593Smuzhiyun 	ret = test_cipher_result();
666*4882a593Smuzhiyun 	if (ret)
667*4882a593Smuzhiyun 		goto exit;
668*4882a593Smuzhiyun 
669*4882a593Smuzhiyun 	ret = test_rsa_result();
670*4882a593Smuzhiyun 	if (ret)
671*4882a593Smuzhiyun 		goto exit;
672*4882a593Smuzhiyun 
673*4882a593Smuzhiyun exit:
674*4882a593Smuzhiyun 	return 0;
675*4882a593Smuzhiyun }
676*4882a593Smuzhiyun 
do_crypto(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])677*4882a593Smuzhiyun static int do_crypto(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
678*4882a593Smuzhiyun {
679*4882a593Smuzhiyun 	return test_all_result();
680*4882a593Smuzhiyun }
681*4882a593Smuzhiyun 
682*4882a593Smuzhiyun U_BOOT_CMD(
683*4882a593Smuzhiyun 	crypto, 1, 1, do_crypto,
684*4882a593Smuzhiyun 	"crypto test",
685*4882a593Smuzhiyun 	""
686*4882a593Smuzhiyun );
687