1#![allow(non_camel_case_types)]
2#![allow(non_snake_case)]
3#![allow(non_upper_case_globals)]
4#![allow(unused_variables)]
5#![allow(dead_code)]
6
7use aes::{self,Aes128,Aes256, Block};
8use sm4::Sm4;
9use crate::common::{self,errcode};
10use super::*;
11use rand::random;
12use aes::cipher::{
13 BlockEncrypt, BlockDecrypt, KeyInit,
14 generic_array::GenericArray,
15};
16const MAX_ENCRYPT_BLOCK_SIZE:usize=2048;
17const CIPHER_BLOCK_SIZE_128:usize=16;
18const CIPHER_BLOCK_SIZE_256:usize=32;
19const MAX_PASSWD_SIZE:usize=32;
20
21#[derive(PartialEq,Eq,Copy,Clone)]
22pub enum E_ENCRYPT_ALG {
23 enc_alg_null = 0,
24 enc_alg_aes_cbc_128=1,
25 enc_alg_aes_cbc_256=2,
26 enc_alg_aes_gcm_128=3,
27 enc_alg_aes_gcm_256=4,
28 enc_alg_sm4=5,
29}
30
31#[derive(Clone)]
32pub struct crypto_alg_t {
33 alg:E_ENCRYPT_ALG,
34 passwd_len:usize,
35 passwd:[u8;MAX_PASSWD_SIZE],
36 cryptor_aes_128:Option<Aes128>,
37 cryptor_sm4:Option<Sm4>,
38
39}
40
41impl crypto_alg_t {
42 pub fn new(alg:E_ENCRYPT_ALG,passwd:&[u8])->Result<Self,errcode::RESULT> {
43 let mut enc_alg = Self {
44 alg,
45 passwd_len:std::cmp::min(passwd.len(),MAX_PASSWD_SIZE),
46 passwd:[0;MAX_PASSWD_SIZE],
47 cryptor_aes_128:None,
48 cryptor_sm4:None,
49
50 };
51 unsafe {
52 std::ptr::copy_nonoverlapping(passwd.as_ptr(), enc_alg.passwd.as_mut_ptr(),enc_alg.passwd_len);
53 }
54 match alg {
55 E_ENCRYPT_ALG::enc_alg_aes_cbc_128=> {
56 enc_alg.cryptor_aes_128=match Aes128::new_from_slice(&enc_alg.passwd[0..16]) {
57 Ok(e)=>Some(e),
58 Err(_)=>None,
59 };
60 },
61 E_ENCRYPT_ALG::enc_alg_sm4=>{
62 enc_alg.cryptor_sm4=match Sm4::new_from_slice(&enc_alg.passwd[0..16]) {
63 Ok(e)=>Some(e),
64 Err(_)=>None,
65 };
66 },
67 _=>(),
68 }
69 return Ok(enc_alg)
70 }
71
72 #[inline(always)]
73 fn encrypt_bock(&self,input:&Block,output:&mut Block) {
74 match self.alg {
75 E_ENCRYPT_ALG::enc_alg_aes_cbc_128=> {
76 if let Some(e)=&self.cryptor_aes_128 {
77 e.encrypt_block_b2b(input, output);
78 }
79 },
80 E_ENCRYPT_ALG::enc_alg_sm4=> {
81 if let Some(e)=&self.cryptor_sm4 {
82 e.encrypt_block_b2b(input, output);
83 }
84 },
85 _=>(),
86 }
87 }
88 pub fn encrypt_aes128_sm4(&self,src:&[u8],dst:&mut [u8])->Result<usize,errcode::RESULT> {
90 let src_len = src.len();
91 if dst.len()<src_len+18 {
92 return Err(errcode::ERROR_BUFFER_TOO_SMALL)
93 }
94
95 let iv=random::<u128>().to_be_bytes();
96 let len_bytes = (src_len as u16).to_be_bytes();
97 dst[0]=len_bytes[0];
99 dst[1]=len_bytes[1];
100 let pad_len = common::ceiling(src_len as u64,CIPHER_BLOCK_SIZE_128 as u64) as usize * CIPHER_BLOCK_SIZE_128;
101 let mut pad_buf = Vec::with_capacity(pad_len);
102
103 pad_buf.extend_from_slice(src);
104 pad_buf.resize(pad_len,0);
105
106 let mut input = GenericArray::from_slice(&iv[0..CIPHER_BLOCK_SIZE_128]);
107 let mut output = GenericArray::from_mut_slice(&mut dst[2..2+CIPHER_BLOCK_SIZE_128]);
108
109 self.encrypt_bock(&input,&mut output);
110 let mut dst_start=2+CIPHER_BLOCK_SIZE_128;
111 let mut src_start = 0;
112 while src_start<src_len {
113 slice_xor_simple(&iv,&mut pad_buf[src_start..src_start+CIPHER_BLOCK_SIZE_128]);
114 input = GenericArray::from_slice(&pad_buf[src_start..src_start+CIPHER_BLOCK_SIZE_128]);
115 output = GenericArray::from_mut_slice(&mut dst[dst_start..dst_start+CIPHER_BLOCK_SIZE_128]);
116 self.encrypt_bock(&input,&mut output);
117 dst_start+=CIPHER_BLOCK_SIZE_128;
118 src_start+=CIPHER_BLOCK_SIZE_128;
119 }
120
121 return Ok(pad_len+18)
122
123 }
124
125
126
127 pub fn encrypt_aes_256(&self,src:&[u8],dst:&mut [u8])->Result<usize,errcode::RESULT> {
128 Err(errcode::ERROR_NOT_SUPPORT)
129 }
130 pub fn encrypt(&self,src:&[u8],dst:&mut [u8])->Result<usize,errcode::RESULT> {
131
132 match self.alg {
133 E_ENCRYPT_ALG::enc_alg_aes_cbc_128=>return self.encrypt_aes128_sm4(src, dst),
134 E_ENCRYPT_ALG::enc_alg_aes_cbc_256=>return self.encrypt_aes_256(src, dst),
135 E_ENCRYPT_ALG::enc_alg_sm4=>return self.encrypt_aes128_sm4(src, dst),
136 _=>return Err(errcode::ERROR_NOT_SUPPORT),
137 }
138
139 }
140
141 pub fn get_alg(&self)->E_ENCRYPT_ALG {
142 return self.alg
143 }
144
145 #[inline(always)]
146 fn decrypt_bock(&self,input:&Block,output:&mut Block) {
147 match self.alg {
148 E_ENCRYPT_ALG::enc_alg_aes_cbc_128=> {
149 if let Some(e)=&self.cryptor_aes_128 {
150 e.decrypt_block_b2b(input, output);
151 }
152 },
153 E_ENCRYPT_ALG::enc_alg_sm4=> {
154 if let Some(e)=&self.cryptor_sm4 {
155 e.decrypt_block_b2b(input, output);
156 }
157 },
158 _=>(),
159 }
160 }
161
162 pub fn decrypt_aes128_sm4(&self,src:&[u8],dst:&mut [u8])->Result<usize,errcode::RESULT> {
163 let src_len = src.len();
164 if dst.len()+18<src_len {
165 return Err(errcode::ERROR_BUFFER_TOO_SMALL)
166 }
167
168 let mut iv=[0u8;16];
169
170 let data_len:u16 = ((src[0] as u16) << 8) +src[1] as u16;
172 if src_len<data_len as usize+2 || ((src_len-2) % CIPHER_BLOCK_SIZE_128!=0) {
173 return Err(errcode::ERROR_INVALID_MSG)
175 }
176 let mut input = GenericArray::from_slice(&src[2..2+CIPHER_BLOCK_SIZE_128]);
177 let mut output = GenericArray::from_mut_slice(&mut iv);
178 self.decrypt_bock(&input,&mut output);
179 let mut dst_start=0;
180 let mut src_start = 2+CIPHER_BLOCK_SIZE_128;
181 while src_start<src_len {
182 input = GenericArray::from_slice(&src[src_start..src_start+CIPHER_BLOCK_SIZE_128]);
184 output = GenericArray::from_mut_slice(&mut dst[dst_start..dst_start+CIPHER_BLOCK_SIZE_128]);
185 self.decrypt_bock(&input,&mut output);
186
187 slice_xor_simple(&iv,&mut dst[dst_start..dst_start+CIPHER_BLOCK_SIZE_128]);
188 dst_start+=CIPHER_BLOCK_SIZE_128;
189 src_start+=CIPHER_BLOCK_SIZE_128;
190 }
191
192 return Ok(data_len as usize)
193
194 }
195
196 pub fn decrypt_aes_256(&self,src:&[u8],dst:&mut [u8])->Result<usize,errcode::RESULT> {
197 Err(errcode::ERROR_NOT_SUPPORT)
198 }
199
200
201 pub fn decrypt(&self,src:&[u8],dst:&mut [u8])->Result<usize,errcode::RESULT> {
202
203 match self.alg {
204 E_ENCRYPT_ALG::enc_alg_aes_cbc_128=>return self.decrypt_aes128_sm4(src, dst),
205 E_ENCRYPT_ALG::enc_alg_aes_cbc_256=>return self.decrypt_aes_256(src, dst),
206 E_ENCRYPT_ALG::enc_alg_sm4=>return self.decrypt_aes128_sm4(src, dst),
207 _=>return Err(errcode::ERROR_NOT_SUPPORT),
208 }
209
210 }
211}