feat(crypt):完成DES便捷加密函数。
This commit is contained in:
parent
8cbb7f5269
commit
56fef4c3de
|
@ -8,11 +8,14 @@ Rust 中可以使用的常用辅助功能工具箱。主要配备以下功能:
|
||||||
- [x] No Padding
|
- [x] No Padding
|
||||||
- [x] ZerosPadding
|
- [x] ZerosPadding
|
||||||
- [x] Pkcs7Padding
|
- [x] Pkcs7Padding
|
||||||
- [ ] DES-CBC 便捷加解密算法
|
- [x] DES-CBC 便捷加解密算法
|
||||||
|
- [x] No Padding
|
||||||
|
- [x] ZerosPadding
|
||||||
|
- [x] Pkcs7Padding
|
||||||
|
- [ ] 3DES-CBC 便捷加解密算法
|
||||||
- [ ] No Padding
|
- [ ] No Padding
|
||||||
- [ ] ZerosPadding
|
- [ ] ZerosPadding
|
||||||
- [ ] Pkcs7Padding
|
- [ ] Pkcs7Padding
|
||||||
- [ ] 3DES 便捷加解密算法
|
|
||||||
- [ ] RSA 加解密算法
|
- [ ] RSA 加解密算法
|
||||||
- [ ] 1024 位长
|
- [ ] 1024 位长
|
||||||
- [ ] 2048 位长
|
- [ ] 2048 位长
|
||||||
|
|
128
src/encryption/des.rs
Normal file
128
src/encryption/des.rs
Normal file
|
@ -0,0 +1,128 @@
|
||||||
|
use cipher::{BlockDecryptMut, BlockEncryptMut, KeyIvInit};
|
||||||
|
use des::Des;
|
||||||
|
|
||||||
|
type DesEncryptor = cbc::Encryptor<Des>;
|
||||||
|
type DesDecryptor = cbc::Decryptor<Des>;
|
||||||
|
|
||||||
|
/// 利用Sha512生成24字节的密钥
|
||||||
|
///
|
||||||
|
/// - `key` 原始密钥
|
||||||
|
fn generate_key<T: AsRef<[u8]>>(key: T) -> [u8; 8] {
|
||||||
|
let mut hasher = hmac_sha256::Hash::new();
|
||||||
|
hasher.update(key);
|
||||||
|
let result = hasher.finalize();
|
||||||
|
let mut compressed_key = [0u8; 8];
|
||||||
|
for i in 0..8 {
|
||||||
|
compressed_key[i] = result[i];
|
||||||
|
for j in 1..4 {
|
||||||
|
compressed_key[i] ^= result[i + j * 8];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
compressed_key
|
||||||
|
}
|
||||||
|
|
||||||
|
/// 使用指定的密钥和填充方式对数据进行加密。
|
||||||
|
/// 如果需要字符串形式的密文,可以配合使用`hex`或者`base64`等函数。
|
||||||
|
///
|
||||||
|
/// - `key` 密钥
|
||||||
|
/// - `padding` 填充方式
|
||||||
|
/// - `plain_data` 明文数据
|
||||||
|
fn encrypt<T: AsRef<[u8]>, D: AsRef<[u8]>>(
|
||||||
|
key: T,
|
||||||
|
padding: super::Padding,
|
||||||
|
plain_data: D,
|
||||||
|
) -> Vec<u8> {
|
||||||
|
let key = generate_key(key);
|
||||||
|
let encryptor = DesEncryptor::new(key.as_slice().into(), &key.into());
|
||||||
|
let result = match padding {
|
||||||
|
super::Padding::NoPadding => encryptor
|
||||||
|
.encrypt_padded_vec_mut::<cipher::block_padding::NoPadding>(plain_data.as_ref()),
|
||||||
|
super::Padding::ZeroPadding => encryptor
|
||||||
|
.encrypt_padded_vec_mut::<cipher::block_padding::ZeroPadding>(plain_data.as_ref()),
|
||||||
|
super::Padding::Pkcs7Padding => {
|
||||||
|
encryptor.encrypt_padded_vec_mut::<cipher::block_padding::Pkcs7>(plain_data.as_ref())
|
||||||
|
}
|
||||||
|
};
|
||||||
|
result
|
||||||
|
}
|
||||||
|
|
||||||
|
/// 使用指定的密钥和填充方式对数据进行解密。
|
||||||
|
///
|
||||||
|
/// - `key` 密钥
|
||||||
|
/// - `padding` 填充方式
|
||||||
|
/// - `cipher_data` 密文数据
|
||||||
|
fn decrypt<T: AsRef<[u8]>, D: AsRef<[u8]>>(
|
||||||
|
key: T,
|
||||||
|
padding: super::Padding,
|
||||||
|
cipher_data: D,
|
||||||
|
) -> Result<Vec<u8>, super::DecryptFailedError> {
|
||||||
|
let key = generate_key(key);
|
||||||
|
let decryptor = DesDecryptor::new(key.as_slice().into(), &key.into());
|
||||||
|
let result = match padding {
|
||||||
|
super::Padding::NoPadding => decryptor
|
||||||
|
.decrypt_padded_vec_mut::<cipher::block_padding::NoPadding>(cipher_data.as_ref()),
|
||||||
|
super::Padding::ZeroPadding => decryptor
|
||||||
|
.decrypt_padded_vec_mut::<cipher::block_padding::ZeroPadding>(cipher_data.as_ref()),
|
||||||
|
super::Padding::Pkcs7Padding => {
|
||||||
|
decryptor.decrypt_padded_vec_mut::<cipher::block_padding::Pkcs7>(cipher_data.as_ref())
|
||||||
|
}
|
||||||
|
};
|
||||||
|
result.map_err(|_| super::DecryptFailedError {})
|
||||||
|
}
|
||||||
|
|
||||||
|
/// 快捷无填充加密函数
|
||||||
|
///
|
||||||
|
/// - `key` 密钥
|
||||||
|
/// - `plain_data` 明文数据
|
||||||
|
pub fn encrypt_no_padding<T: AsRef<[u8]>, D: AsRef<[u8]>>(key: T, plain_data: D) -> Vec<u8> {
|
||||||
|
encrypt(key, super::Padding::NoPadding, plain_data)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// 快捷无填充解密函数
|
||||||
|
///
|
||||||
|
/// - `key` 密钥
|
||||||
|
/// - `cipher_data` 密文数据
|
||||||
|
pub fn decrypt_no_padding<T: AsRef<[u8]>, D: AsRef<[u8]>>(
|
||||||
|
key: T,
|
||||||
|
cipher_data: D,
|
||||||
|
) -> Result<Vec<u8>, super::DecryptFailedError> {
|
||||||
|
decrypt(key, super::Padding::NoPadding, cipher_data)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// 快捷零填充加密函数
|
||||||
|
///
|
||||||
|
/// - `key` 密钥
|
||||||
|
/// - `plain_data` 明文数据
|
||||||
|
pub fn encrypt_zero_padding<T: AsRef<[u8]>, D: AsRef<[u8]>>(key: T, plain_data: D) -> Vec<u8> {
|
||||||
|
encrypt(key, super::Padding::ZeroPadding, plain_data)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// 快捷零填充解密函数
|
||||||
|
///
|
||||||
|
/// - `key` 密钥
|
||||||
|
/// - `cipher_data` 密文数据
|
||||||
|
pub fn decrypt_zero_padding<T: AsRef<[u8]>, D: AsRef<[u8]>>(
|
||||||
|
key: T,
|
||||||
|
cipher_data: D,
|
||||||
|
) -> Result<Vec<u8>, super::DecryptFailedError> {
|
||||||
|
decrypt(key, super::Padding::ZeroPadding, cipher_data)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// 快捷Pkcs7填充加密函数
|
||||||
|
///
|
||||||
|
/// - `key` 密钥
|
||||||
|
/// - `plain_data` 明文数据
|
||||||
|
pub fn encrypt_pkcs7_padding<T: AsRef<[u8]>, D: AsRef<[u8]>>(key: T, plain_data: D) -> Vec<u8> {
|
||||||
|
encrypt(key, super::Padding::Pkcs7Padding, plain_data)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// 快捷Pkcs7填充解密函数
|
||||||
|
///
|
||||||
|
/// - `key` 密钥
|
||||||
|
/// - `cipher_data` 密文数据
|
||||||
|
pub fn decrypt_pkcs7_padding<T: AsRef<[u8]>, D: AsRef<[u8]>>(
|
||||||
|
key: T,
|
||||||
|
cipher_data: D,
|
||||||
|
) -> Result<Vec<u8>, super::DecryptFailedError> {
|
||||||
|
decrypt(key, super::Padding::Pkcs7Padding, cipher_data)
|
||||||
|
}
|
|
@ -1,6 +1,7 @@
|
||||||
use thiserror::Error;
|
use thiserror::Error;
|
||||||
|
|
||||||
pub mod aes;
|
pub mod aes;
|
||||||
|
pub mod des;
|
||||||
|
|
||||||
pub enum Padding {
|
pub enum Padding {
|
||||||
NoPadding,
|
NoPadding,
|
||||||
|
|
25
tests/des_cryption.rs
Normal file
25
tests/des_cryption.rs
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
#[cfg(test)]
|
||||||
|
mod des_test {
|
||||||
|
#[test]
|
||||||
|
fn encrypt_zero_padding() {
|
||||||
|
let cipher_data =
|
||||||
|
rs_toolbox::encryption::des::encrypt_zero_padding("123456", "Hello world.");
|
||||||
|
let cipher_hex = rs_toolbox::serialize::to_hex(cipher_data);
|
||||||
|
assert_eq!(cipher_hex, "34115b8448d11e6d284576573a28629b");
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn decrypt_zero_padding() {
|
||||||
|
let plain_data = rs_toolbox::encryption::des::decrypt_zero_padding(
|
||||||
|
"123456",
|
||||||
|
rs_toolbox::serialize::from_hex("34115b8448d11e6d284576573a28629b").unwrap(),
|
||||||
|
);
|
||||||
|
if plain_data.is_err() {
|
||||||
|
panic!("Decrypt failed");
|
||||||
|
}
|
||||||
|
assert_eq!(
|
||||||
|
String::from_utf8(plain_data.unwrap()).unwrap(),
|
||||||
|
"Hello world."
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user