调整加密逻辑
This commit is contained in:
@@ -59,12 +59,7 @@ impl AesCbcCipher {
|
|||||||
return Err(anyhow!("aes_cbc data err"));
|
return Err(anyhow!("aes_cbc data err"));
|
||||||
}
|
}
|
||||||
let mut iv = [0; 16];
|
let mut iv = [0; 16];
|
||||||
iv[0..4].copy_from_slice(&net_packet.source().octets());
|
iv[0..12].copy_from_slice(&net_packet.head_tag());
|
||||||
iv[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
iv[8] = net_packet.protocol().into();
|
|
||||||
iv[9] = net_packet.transport_protocol();
|
|
||||||
iv[10] = net_packet.is_gateway() as u8;
|
|
||||||
iv[11] = net_packet.source_ttl();
|
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
iv[12..16].copy_from_slice(&finger.hash[0..4]);
|
iv[12..16].copy_from_slice(&finger.hash[0..4]);
|
||||||
}
|
}
|
||||||
@@ -102,12 +97,7 @@ impl AesCbcCipher {
|
|||||||
) -> anyhow::Result<()> {
|
) -> anyhow::Result<()> {
|
||||||
let data_len = net_packet.data_len();
|
let data_len = net_packet.data_len();
|
||||||
let mut iv = [0; 16];
|
let mut iv = [0; 16];
|
||||||
iv[0..4].copy_from_slice(&net_packet.source().octets());
|
iv[0..12].copy_from_slice(&net_packet.head_tag());
|
||||||
iv[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
iv[8] = net_packet.protocol().into();
|
|
||||||
iv[9] = net_packet.transport_protocol();
|
|
||||||
iv[10] = net_packet.is_gateway() as u8;
|
|
||||||
iv[11] = net_packet.source_ttl();
|
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
iv[12..16].copy_from_slice(&finger.hash[0..4]);
|
iv[12..16].copy_from_slice(&finger.hash[0..4]);
|
||||||
net_packet.set_data_len(data_len + 16)?;
|
net_packet.set_data_len(data_len + 16)?;
|
||||||
@@ -146,3 +136,18 @@ impl AesCbcCipher {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
#[test]
|
||||||
|
fn test_aes_cbc() {
|
||||||
|
let d = AesCbcCipher::new_128([0; 16], Some(Finger::new("123")));
|
||||||
|
let mut p = NetPacket::new_encrypt([0; 100]).unwrap();
|
||||||
|
let src = p.buffer().to_vec();
|
||||||
|
d.encrypt_ipv4(&mut p).unwrap();
|
||||||
|
d.decrypt_ipv4(&mut p).unwrap();
|
||||||
|
assert_eq!(p.buffer(), &src);
|
||||||
|
let d = AesCbcCipher::new_128([0; 16], None);
|
||||||
|
let mut p = NetPacket::new_encrypt([0; 100]).unwrap();
|
||||||
|
let src = p.buffer().to_vec();
|
||||||
|
d.encrypt_ipv4(&mut p).unwrap();
|
||||||
|
d.decrypt_ipv4(&mut p).unwrap();
|
||||||
|
assert_eq!(p.buffer(), &src);
|
||||||
|
}
|
||||||
|
|||||||
@@ -110,13 +110,7 @@ impl AesEcbCipher {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
let mut nonce_raw = [0; 12];
|
let nonce_raw = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
|
||||||
let len = net_packet.payload().len();
|
let len = net_packet.payload().len();
|
||||||
if len < 12 {
|
if len < 12 {
|
||||||
return Err(anyhow!("data len err"));
|
return Err(anyhow!("data len err"));
|
||||||
@@ -202,13 +196,7 @@ impl AesEcbCipher {
|
|||||||
net_packet.payload_mut().copy_from_slice(ciphertext);
|
net_packet.payload_mut().copy_from_slice(ciphertext);
|
||||||
net_packet.set_encrypt_flag(true);
|
net_packet.set_encrypt_flag(true);
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
let mut nonce_raw = [0; 12];
|
let nonce_raw = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
|
||||||
let finger = finger.calculate_finger(&nonce_raw, ciphertext);
|
let finger = finger.calculate_finger(&nonce_raw, ciphertext);
|
||||||
let src_data_len = net_packet.data_len();
|
let src_data_len = net_packet.data_len();
|
||||||
//设置实际长度
|
//设置实际长度
|
||||||
@@ -224,6 +212,8 @@ impl AesEcbCipher {
|
|||||||
fn test_openssl_aes_ecb() {
|
fn test_openssl_aes_ecb() {
|
||||||
let d = AesEcbCipher::new_128([0; 16], Some(Finger::new("123")));
|
let d = AesEcbCipher::new_128([0; 16], Some(Finger::new("123")));
|
||||||
let mut p = NetPacket::new_encrypt([0; 100]).unwrap();
|
let mut p = NetPacket::new_encrypt([0; 100]).unwrap();
|
||||||
|
let src = p.buffer().to_vec();
|
||||||
d.encrypt_ipv4(&mut p).unwrap();
|
d.encrypt_ipv4(&mut p).unwrap();
|
||||||
d.decrypt_ipv4(&mut p).unwrap();
|
d.decrypt_ipv4(&mut p).unwrap();
|
||||||
|
assert_eq!(p.buffer(), &src);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -54,13 +54,7 @@ impl AesEcbCipher {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
let mut nonce_raw = [0; 12];
|
let nonce_raw = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
|
||||||
let len = net_packet.payload().len();
|
let len = net_packet.payload().len();
|
||||||
if len < 12 {
|
if len < 12 {
|
||||||
return Err(anyhow!("payload len <12"));
|
return Err(anyhow!("payload len <12"));
|
||||||
@@ -134,13 +128,7 @@ impl AesEcbCipher {
|
|||||||
net_packet.set_encrypt_flag(true);
|
net_packet.set_encrypt_flag(true);
|
||||||
|
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
let mut nonce_raw = [0; 12];
|
let nonce_raw = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
|
||||||
let finger = finger.calculate_finger(&nonce_raw, buf);
|
let finger = finger.calculate_finger(&nonce_raw, buf);
|
||||||
let src_data_len = net_packet.data_len();
|
let src_data_len = net_packet.data_len();
|
||||||
//设置实际长度
|
//设置实际长度
|
||||||
|
|||||||
@@ -47,13 +47,7 @@ impl AesGcmCipher {
|
|||||||
log::error!("数据异常,长度小于{}", AES_GCM_ENCRYPTION_RESERVED);
|
log::error!("数据异常,长度小于{}", AES_GCM_ENCRYPTION_RESERVED);
|
||||||
return Err(anyhow!("data err"));
|
return Err(anyhow!("data err"));
|
||||||
}
|
}
|
||||||
let mut nonce_raw = [0; 12];
|
let nonce_raw = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
|
||||||
let nonce: &GenericArray<u8, U12> = Nonce::from_slice(&nonce_raw);
|
let nonce: &GenericArray<u8, U12> = Nonce::from_slice(&nonce_raw);
|
||||||
|
|
||||||
let mut secret_body = SecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
let mut secret_body = SecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
||||||
@@ -89,13 +83,7 @@ impl AesGcmCipher {
|
|||||||
if net_packet.reserve() < AES_GCM_ENCRYPTION_RESERVED {
|
if net_packet.reserve() < AES_GCM_ENCRYPTION_RESERVED {
|
||||||
return Err(anyhow!("too short"));
|
return Err(anyhow!("too short"));
|
||||||
}
|
}
|
||||||
let mut nonce_raw = [0; 12];
|
let nonce_raw = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
|
||||||
let nonce: &GenericArray<u8, U12> = Nonce::from_slice(&nonce_raw);
|
let nonce: &GenericArray<u8, U12> = Nonce::from_slice(&nonce_raw);
|
||||||
let data_len = net_packet.data_len() + AES_GCM_ENCRYPTION_RESERVED;
|
let data_len = net_packet.data_len() + AES_GCM_ENCRYPTION_RESERVED;
|
||||||
net_packet.set_data_len(data_len)?;
|
net_packet.set_data_len(data_len)?;
|
||||||
@@ -123,3 +111,22 @@ impl AesGcmCipher {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_aes_gcm() {
|
||||||
|
let d = AesGcmCipher::new_256([0; 32], Some(Finger::new("123")));
|
||||||
|
let mut p =
|
||||||
|
NetPacket::new_encrypt([1; 13 + crate::protocol::body::ENCRYPTION_RESERVED]).unwrap();
|
||||||
|
let src = p.buffer().to_vec();
|
||||||
|
d.encrypt_ipv4(&mut p).unwrap();
|
||||||
|
d.decrypt_ipv4(&mut p).unwrap();
|
||||||
|
assert_eq!(p.buffer(), &src);
|
||||||
|
|
||||||
|
let d = AesGcmCipher::new_256([0; 32], None);
|
||||||
|
let mut p =
|
||||||
|
NetPacket::new_encrypt([0; 13 + crate::protocol::body::ENCRYPTION_RESERVED]).unwrap();
|
||||||
|
let src = p.buffer().to_vec();
|
||||||
|
d.encrypt_ipv4(&mut p).unwrap();
|
||||||
|
d.decrypt_ipv4(&mut p).unwrap();
|
||||||
|
assert_eq!(p.buffer(), &src);
|
||||||
|
}
|
||||||
|
|||||||
@@ -62,13 +62,7 @@ impl AesGcmCipher {
|
|||||||
log::error!("数据异常,长度小于{}", AES_GCM_ENCRYPTION_RESERVED);
|
log::error!("数据异常,长度小于{}", AES_GCM_ENCRYPTION_RESERVED);
|
||||||
return Err(anyhow!("data err"));
|
return Err(anyhow!("data err"));
|
||||||
}
|
}
|
||||||
let mut nonce_raw = [0; 12];
|
let nonce_raw = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
|
||||||
let nonce = aead::Nonce::assume_unique_for_key(nonce_raw);
|
let nonce = aead::Nonce::assume_unique_for_key(nonce_raw);
|
||||||
let mut secret_body = SecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
let mut secret_body = SecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
@@ -100,13 +94,7 @@ impl AesGcmCipher {
|
|||||||
&self,
|
&self,
|
||||||
net_packet: &mut NetPacket<B>,
|
net_packet: &mut NetPacket<B>,
|
||||||
) -> anyhow::Result<()> {
|
) -> anyhow::Result<()> {
|
||||||
let mut nonce_raw = [0; 12];
|
let nonce_raw = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
|
||||||
let nonce = aead::Nonce::assume_unique_for_key(nonce_raw);
|
let nonce = aead::Nonce::assume_unique_for_key(nonce_raw);
|
||||||
let data_len = net_packet.data_len() + AES_GCM_ENCRYPTION_RESERVED;
|
let data_len = net_packet.data_len() + AES_GCM_ENCRYPTION_RESERVED;
|
||||||
net_packet.set_data_len(data_len)?;
|
net_packet.set_data_len(data_len)?;
|
||||||
@@ -139,3 +127,22 @@ impl AesGcmCipher {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_aes_gcm() {
|
||||||
|
let d = AesGcmCipher::new_256([0; 32], Some(Finger::new("123")));
|
||||||
|
let mut p =
|
||||||
|
NetPacket::new_encrypt([0; 13 + crate::protocol::body::ENCRYPTION_RESERVED]).unwrap();
|
||||||
|
let src = p.buffer().to_vec();
|
||||||
|
d.encrypt_ipv4(&mut p).unwrap();
|
||||||
|
d.decrypt_ipv4(&mut p).unwrap();
|
||||||
|
assert_eq!(p.buffer(), &src);
|
||||||
|
|
||||||
|
let d = AesGcmCipher::new_256([0; 32], None);
|
||||||
|
let mut p =
|
||||||
|
NetPacket::new_encrypt([0; 13 + crate::protocol::body::ENCRYPTION_RESERVED]).unwrap();
|
||||||
|
let src = p.buffer().to_vec();
|
||||||
|
d.encrypt_ipv4(&mut p).unwrap();
|
||||||
|
d.decrypt_ipv4(&mut p).unwrap();
|
||||||
|
assert_eq!(p.buffer(), &src);
|
||||||
|
}
|
||||||
|
|||||||
@@ -3,8 +3,11 @@ use anyhow::anyhow;
|
|||||||
use chacha20::cipher::{Key, KeyIvInit, StreamCipher};
|
use chacha20::cipher::{Key, KeyIvInit, StreamCipher};
|
||||||
use chacha20::ChaCha20;
|
use chacha20::ChaCha20;
|
||||||
|
|
||||||
|
use crate::cipher::finger::{gen_nonce, gen_random_nonce};
|
||||||
use crate::cipher::Finger;
|
use crate::cipher::Finger;
|
||||||
use crate::protocol::body::ChaCah20SecretBody;
|
use crate::protocol::body::{
|
||||||
|
IVSecretBody, SecretTail, SecretTailMut, FINGER_RESERVED, RANDOM_RESERVED,
|
||||||
|
};
|
||||||
use crate::protocol::NetPacket;
|
use crate::protocol::NetPacket;
|
||||||
|
|
||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
@@ -34,29 +37,22 @@ impl ChaCha20Cipher {
|
|||||||
//未加密的数据直接丢弃
|
//未加密的数据直接丢弃
|
||||||
return Err(anyhow!("not encrypt"));
|
return Err(anyhow!("not encrypt"));
|
||||||
}
|
}
|
||||||
let mut iv = [0; 12];
|
let mut head_tag = net_packet.head_tag();
|
||||||
iv[0..4].copy_from_slice(&net_packet.source().octets());
|
|
||||||
iv[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
iv[8] = net_packet.protocol().into();
|
|
||||||
iv[9] = net_packet.transport_protocol();
|
|
||||||
iv[10] = net_packet.is_gateway() as u8;
|
|
||||||
iv[11] = net_packet.source_ttl();
|
|
||||||
|
|
||||||
let mut secret_body =
|
let mut secret_body = IVSecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
||||||
ChaCah20SecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
let finger = finger.calculate_finger(&iv[..12], secret_body.en_body());
|
let finger = finger.calculate_finger(&head_tag, secret_body.data());
|
||||||
if &finger != secret_body.finger() {
|
if &finger != secret_body.finger() {
|
||||||
return Err(anyhow!("ChaCha20 finger err"));
|
return Err(anyhow!("ChaCha20 finger err"));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
gen_nonce(&mut head_tag, secret_body.random_buf());
|
||||||
ChaCha20::new(
|
ChaCha20::new(
|
||||||
Key::<ChaCha20>::from_slice(&self.key),
|
Key::<ChaCha20>::from_slice(&self.key),
|
||||||
Iv::<ChaCha20>::from_slice(&iv),
|
Iv::<ChaCha20>::from_slice(&head_tag),
|
||||||
)
|
)
|
||||||
.apply_keystream(secret_body.en_body_mut());
|
.apply_keystream(secret_body.data_mut());
|
||||||
let len = secret_body.en_body().len();
|
let len = secret_body.data().len();
|
||||||
net_packet.set_encrypt_flag(false);
|
net_packet.set_encrypt_flag(false);
|
||||||
net_packet.set_payload_len(len)?;
|
net_packet.set_payload_len(len)?;
|
||||||
Ok(())
|
Ok(())
|
||||||
@@ -66,29 +62,26 @@ impl ChaCha20Cipher {
|
|||||||
net_packet: &mut NetPacket<B>,
|
net_packet: &mut NetPacket<B>,
|
||||||
) -> anyhow::Result<()> {
|
) -> anyhow::Result<()> {
|
||||||
let data_len = net_packet.data_len();
|
let data_len = net_packet.data_len();
|
||||||
let mut iv = [0; 12];
|
let head_tag = net_packet.head_tag();
|
||||||
iv[0..4].copy_from_slice(&net_packet.source().octets());
|
|
||||||
iv[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
iv[8] = net_packet.protocol().into();
|
|
||||||
iv[9] = net_packet.transport_protocol();
|
|
||||||
iv[10] = net_packet.is_gateway() as u8;
|
|
||||||
iv[11] = net_packet.source_ttl();
|
|
||||||
if let Some(_) = &self.finger {
|
if let Some(_) = &self.finger {
|
||||||
net_packet.set_data_len(data_len + 12)?;
|
net_packet.set_data_len(data_len + RANDOM_RESERVED + FINGER_RESERVED)?;
|
||||||
|
} else {
|
||||||
|
net_packet.set_data_len(data_len + RANDOM_RESERVED)?;
|
||||||
}
|
}
|
||||||
let mut secret_body =
|
let mut secret_body = IVSecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
||||||
ChaCah20SecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
let mut nonce = head_tag;
|
||||||
|
secret_body.set_random(&gen_random_nonce(&mut nonce));
|
||||||
|
|
||||||
ChaCha20::new(
|
ChaCha20::new(
|
||||||
Key::<ChaCha20>::from_slice(&self.key),
|
Key::<ChaCha20>::from_slice(&self.key),
|
||||||
Iv::<ChaCha20>::from_slice(&iv),
|
Iv::<ChaCha20>::from_slice(&nonce),
|
||||||
)
|
)
|
||||||
.apply_keystream(secret_body.en_body_mut());
|
.apply_keystream(secret_body.data_mut());
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
let finger = finger.calculate_finger(&iv[..12], secret_body.en_body_mut());
|
let finger = finger.calculate_finger(&head_tag, secret_body.data());
|
||||||
let mut secret_body = ChaCah20SecretBody::new(net_packet.payload_mut(), true)?;
|
let mut secret_body = IVSecretBody::new(net_packet.payload_mut(), true)?;
|
||||||
secret_body.set_finger(&finger)?;
|
secret_body.set_finger(&finger)?;
|
||||||
}
|
}
|
||||||
|
|
||||||
net_packet.set_encrypt_flag(true);
|
net_packet.set_encrypt_flag(true);
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
@@ -98,7 +91,7 @@ impl ChaCha20Cipher {
|
|||||||
fn test_chacha20() {
|
fn test_chacha20() {
|
||||||
let d = ChaCha20Cipher::new_256([0; 32], Some(Finger::new("123")));
|
let d = ChaCha20Cipher::new_256([0; 32], Some(Finger::new("123")));
|
||||||
let mut p =
|
let mut p =
|
||||||
NetPacket::new_encrypt([0; 13 + crate::protocol::body::ENCRYPTION_RESERVED]).unwrap();
|
NetPacket::new_encrypt([1; 13 + crate::protocol::body::ENCRYPTION_RESERVED]).unwrap();
|
||||||
let src = p.buffer().to_vec();
|
let src = p.buffer().to_vec();
|
||||||
d.encrypt_ipv4(&mut p).unwrap();
|
d.encrypt_ipv4(&mut p).unwrap();
|
||||||
d.decrypt_ipv4(&mut p).unwrap();
|
d.decrypt_ipv4(&mut p).unwrap();
|
||||||
@@ -106,7 +99,7 @@ fn test_chacha20() {
|
|||||||
|
|
||||||
let d = ChaCha20Cipher::new_256([0; 32], None);
|
let d = ChaCha20Cipher::new_256([0; 32], None);
|
||||||
let mut p =
|
let mut p =
|
||||||
NetPacket::new_encrypt([0; 13 + crate::protocol::body::ENCRYPTION_RESERVED]).unwrap();
|
NetPacket::new_encrypt([2; 13 + crate::protocol::body::ENCRYPTION_RESERVED]).unwrap();
|
||||||
let src = p.buffer().to_vec();
|
let src = p.buffer().to_vec();
|
||||||
d.encrypt_ipv4(&mut p).unwrap();
|
d.encrypt_ipv4(&mut p).unwrap();
|
||||||
d.decrypt_ipv4(&mut p).unwrap();
|
d.decrypt_ipv4(&mut p).unwrap();
|
||||||
|
|||||||
@@ -3,8 +3,11 @@ use anyhow::anyhow;
|
|||||||
use ring::aead;
|
use ring::aead;
|
||||||
use ring::aead::{LessSafeKey, UnboundKey};
|
use ring::aead::{LessSafeKey, UnboundKey};
|
||||||
|
|
||||||
|
use crate::cipher::finger::{gen_nonce, gen_random_nonce};
|
||||||
use crate::cipher::Finger;
|
use crate::cipher::Finger;
|
||||||
use crate::protocol::body::{SecretBody, AES_GCM_ENCRYPTION_RESERVED};
|
use crate::protocol::body::{
|
||||||
|
AEADSecretBody, SecretTail, SecretTailMut, FINGER_RESERVED, RANDOM_RESERVED, TAG_RESERVED,
|
||||||
|
};
|
||||||
use crate::protocol::NetPacket;
|
use crate::protocol::NetPacket;
|
||||||
|
|
||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
@@ -40,34 +43,29 @@ impl ChaCha20Poly1305Cipher {
|
|||||||
//未加密的数据直接丢弃
|
//未加密的数据直接丢弃
|
||||||
return Err(anyhow!("not encrypt"));
|
return Err(anyhow!("not encrypt"));
|
||||||
}
|
}
|
||||||
if net_packet.payload().len() < AES_GCM_ENCRYPTION_RESERVED {
|
if net_packet.payload().len() < TAG_RESERVED {
|
||||||
log::error!("数据异常,长度小于{}", AES_GCM_ENCRYPTION_RESERVED);
|
log::error!("数据异常,长度小于{}", TAG_RESERVED);
|
||||||
return Err(anyhow!("data err"));
|
return Err(anyhow!("data err"));
|
||||||
}
|
}
|
||||||
let mut nonce_raw = [0; 12];
|
let mut head_tag = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
let mut secret_body = AEADSecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
|
||||||
let nonce = aead::Nonce::assume_unique_for_key(nonce_raw);
|
|
||||||
let mut secret_body = SecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
let finger = finger.calculate_finger(&nonce_raw, secret_body.en_body());
|
let finger = finger.calculate_finger(&head_tag, secret_body.data_tag_mut());
|
||||||
if &finger != secret_body.finger() {
|
if &finger != secret_body.finger() {
|
||||||
return Err(anyhow!("ring CHACHA20_POLY1305 finger err"));
|
return Err(anyhow!("ring CHACHA20_POLY1305 finger err"));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
gen_nonce(&mut head_tag, secret_body.random_buf());
|
||||||
|
let nonce = aead::Nonce::assume_unique_for_key(head_tag);
|
||||||
let rs = self
|
let rs = self
|
||||||
.cipher
|
.cipher
|
||||||
.open_in_place(nonce, aead::Aad::empty(), secret_body.en_body_mut());
|
.open_in_place(nonce, aead::Aad::empty(), secret_body.data_tag_mut());
|
||||||
if let Err(e) = rs {
|
if let Err(e) = rs {
|
||||||
return Err(anyhow!("ring CHACHA20_POLY1305 解密失败:{}", e));
|
return Err(anyhow!("ring CHACHA20_POLY1305 解密失败:{}", e));
|
||||||
}
|
}
|
||||||
|
let len = secret_body.data().len();
|
||||||
net_packet.set_encrypt_flag(false);
|
net_packet.set_encrypt_flag(false);
|
||||||
net_packet.set_data_len(net_packet.data_len() - AES_GCM_ENCRYPTION_RESERVED)?;
|
net_packet.set_payload_len(len)?;
|
||||||
return Ok(());
|
return Ok(());
|
||||||
}
|
}
|
||||||
/// net_packet 必须预留足够长度
|
/// net_packet 必须预留足够长度
|
||||||
@@ -77,23 +75,23 @@ impl ChaCha20Poly1305Cipher {
|
|||||||
&self,
|
&self,
|
||||||
net_packet: &mut NetPacket<B>,
|
net_packet: &mut NetPacket<B>,
|
||||||
) -> anyhow::Result<()> {
|
) -> anyhow::Result<()> {
|
||||||
let mut nonce_raw = [0; 12];
|
let head_tag = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
let data_len = net_packet.data_len();
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
if self.finger.is_some() {
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
net_packet.set_data_len(data_len + TAG_RESERVED + RANDOM_RESERVED + FINGER_RESERVED)?;
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
} else {
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
net_packet.set_data_len(data_len + TAG_RESERVED + RANDOM_RESERVED)?;
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
}
|
||||||
let nonce = aead::Nonce::assume_unique_for_key(nonce_raw);
|
let mut secret_body = AEADSecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
||||||
let data_len = net_packet.data_len() + AES_GCM_ENCRYPTION_RESERVED;
|
let mut nonce = head_tag;
|
||||||
net_packet.set_data_len(data_len)?;
|
secret_body.set_random(&gen_random_nonce(&mut nonce));
|
||||||
let mut secret_body = SecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
let nonce = aead::Nonce::assume_unique_for_key(nonce);
|
||||||
let rs = self.cipher.seal_in_place_separate_tag(
|
let rs = self.cipher.seal_in_place_separate_tag(
|
||||||
nonce,
|
nonce,
|
||||||
aead::Aad::empty(),
|
aead::Aad::empty(),
|
||||||
secret_body.body_mut(),
|
secret_body.data_mut(),
|
||||||
);
|
);
|
||||||
return match rs {
|
match rs {
|
||||||
Ok(tag) => {
|
Ok(tag) => {
|
||||||
let tag = tag.as_ref();
|
let tag = tag.as_ref();
|
||||||
if tag.len() != 16 {
|
if tag.len() != 16 {
|
||||||
@@ -101,14 +99,14 @@ impl ChaCha20Poly1305Cipher {
|
|||||||
}
|
}
|
||||||
secret_body.set_tag(tag)?;
|
secret_body.set_tag(tag)?;
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
let finger = finger.calculate_finger(&nonce_raw, secret_body.en_body());
|
let finger = finger.calculate_finger(&head_tag, secret_body.data_tag_mut());
|
||||||
secret_body.set_finger(&finger)?;
|
secret_body.set_finger(&finger)?;
|
||||||
}
|
}
|
||||||
net_packet.set_encrypt_flag(true);
|
net_packet.set_encrypt_flag(true);
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
Err(e) => Err(anyhow!("ring CHACHA20_POLY1305 加密失败:{}", e)),
|
Err(e) => Err(anyhow!("ring CHACHA20_POLY1305 加密失败:{}", e)),
|
||||||
};
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,11 +1,13 @@
|
|||||||
|
use crate::cipher::finger::{gen_nonce, gen_random_nonce};
|
||||||
|
use crate::cipher::Finger;
|
||||||
|
use crate::protocol::body::{
|
||||||
|
AEADSecretBody, SecretTail, SecretTailMut, FINGER_RESERVED, RANDOM_RESERVED, TAG_RESERVED,
|
||||||
|
};
|
||||||
|
use crate::protocol::NetPacket;
|
||||||
use anyhow::anyhow;
|
use anyhow::anyhow;
|
||||||
use chacha20poly1305::aead::{Nonce, Tag};
|
use chacha20poly1305::aead::{Nonce, Tag};
|
||||||
use chacha20poly1305::{AeadInPlace, ChaCha20Poly1305, Key, KeyInit};
|
use chacha20poly1305::{AeadInPlace, ChaCha20Poly1305, Key, KeyInit};
|
||||||
|
|
||||||
use crate::cipher::Finger;
|
|
||||||
use crate::protocol::body::{SecretBody, AES_GCM_ENCRYPTION_RESERVED};
|
|
||||||
use crate::protocol::NetPacket;
|
|
||||||
|
|
||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
pub struct ChaCha20Poly1305Cipher {
|
pub struct ChaCha20Poly1305Cipher {
|
||||||
key: Vec<u8>,
|
key: Vec<u8>,
|
||||||
@@ -24,6 +26,7 @@ impl ChaCha20Poly1305Cipher {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl ChaCha20Poly1305Cipher {
|
impl ChaCha20Poly1305Cipher {
|
||||||
pub fn key(&self) -> &[u8] {
|
pub fn key(&self) -> &[u8] {
|
||||||
&self.key
|
&self.key
|
||||||
@@ -39,35 +42,31 @@ impl ChaCha20Poly1305Cipher {
|
|||||||
//未加密的数据直接丢弃
|
//未加密的数据直接丢弃
|
||||||
return Err(anyhow!("not encrypt"));
|
return Err(anyhow!("not encrypt"));
|
||||||
}
|
}
|
||||||
if net_packet.payload().len() < AES_GCM_ENCRYPTION_RESERVED {
|
if net_packet.payload().len() < TAG_RESERVED {
|
||||||
log::error!("数据异常,长度小于{}", AES_GCM_ENCRYPTION_RESERVED);
|
log::error!("数据异常,长度小于{}", TAG_RESERVED);
|
||||||
return Err(anyhow!("data err"));
|
return Err(anyhow!("data err"));
|
||||||
}
|
}
|
||||||
let mut nonce_raw = [0; 12];
|
let mut head_tag = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
let mut secret_body = AEADSecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
|
||||||
let mut secret_body = SecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
let finger = finger.calculate_finger(&nonce_raw, secret_body.en_body());
|
let finger = finger.calculate_finger(&head_tag, secret_body.data_tag_mut());
|
||||||
if &finger != secret_body.finger() {
|
if &finger != secret_body.finger() {
|
||||||
return Err(anyhow!("rs CHACHA20_POLY1305 finger err"));
|
return Err(anyhow!("rs CHACHA20_POLY1305 finger err"));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
let nonce: Nonce<ChaCha20Poly1305> = nonce_raw.into();
|
gen_nonce(&mut head_tag, secret_body.random_buf());
|
||||||
|
let nonce: Nonce<ChaCha20Poly1305> = head_tag.into();
|
||||||
let tag: Tag<ChaCha20Poly1305> =
|
let tag: Tag<ChaCha20Poly1305> =
|
||||||
Tag::<ChaCha20Poly1305>::from_slice(secret_body.tag()).clone();
|
Tag::<ChaCha20Poly1305>::from_slice(secret_body.tag()).clone();
|
||||||
if let Err(e) =
|
if let Err(e) =
|
||||||
self.cipher
|
self.cipher
|
||||||
.decrypt_in_place_detached(&nonce, &[], secret_body.body_mut(), &tag)
|
.decrypt_in_place_detached(&nonce, &[], secret_body.data_mut(), &tag)
|
||||||
{
|
{
|
||||||
return Err(anyhow!("rs CHACHA20_POLY1305 decrypt_ipv4 {:?}", e));
|
return Err(anyhow!("rs CHACHA20_POLY1305 decrypt_ipv4 {:?}", e));
|
||||||
}
|
}
|
||||||
|
let len = secret_body.data().len();
|
||||||
net_packet.set_encrypt_flag(false);
|
net_packet.set_encrypt_flag(false);
|
||||||
net_packet.set_data_len(net_packet.data_len() - AES_GCM_ENCRYPTION_RESERVED)?;
|
net_packet.set_payload_len(len)?;
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
/// net_packet 必须预留足够长度
|
/// net_packet 必须预留足够长度
|
||||||
@@ -77,21 +76,21 @@ impl ChaCha20Poly1305Cipher {
|
|||||||
&self,
|
&self,
|
||||||
net_packet: &mut NetPacket<B>,
|
net_packet: &mut NetPacket<B>,
|
||||||
) -> anyhow::Result<()> {
|
) -> anyhow::Result<()> {
|
||||||
let mut nonce_raw = [0; 12];
|
let head_tag = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
let data_len = net_packet.data_len();
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
if self.finger.is_some() {
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
net_packet.set_data_len(data_len + TAG_RESERVED + RANDOM_RESERVED + FINGER_RESERVED)?;
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
} else {
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
net_packet.set_data_len(data_len + TAG_RESERVED + RANDOM_RESERVED)?;
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
}
|
||||||
let nonce = nonce_raw.into();
|
let mut secret_body = AEADSecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
||||||
let data_len = net_packet.data_len() + AES_GCM_ENCRYPTION_RESERVED;
|
let mut nonce = head_tag;
|
||||||
net_packet.set_data_len(data_len)?;
|
secret_body.set_random(&gen_random_nonce(&mut nonce));
|
||||||
let mut secret_body = SecretBody::new(net_packet.payload_mut(), self.finger.is_some())?;
|
let nonce = nonce.into();
|
||||||
let rs = self
|
let rs = self
|
||||||
.cipher
|
.cipher
|
||||||
.encrypt_in_place_detached(&nonce, &[], secret_body.body_mut());
|
.encrypt_in_place_detached(&nonce, &[], secret_body.data_mut());
|
||||||
return match rs {
|
match rs {
|
||||||
Ok(tag) => {
|
Ok(tag) => {
|
||||||
let tag: &[u8] = tag.as_ref();
|
let tag: &[u8] = tag.as_ref();
|
||||||
if tag.len() != 16 {
|
if tag.len() != 16 {
|
||||||
@@ -99,14 +98,14 @@ impl ChaCha20Poly1305Cipher {
|
|||||||
}
|
}
|
||||||
secret_body.set_tag(tag)?;
|
secret_body.set_tag(tag)?;
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
let finger = finger.calculate_finger(&nonce_raw, secret_body.en_body());
|
let finger = finger.calculate_finger(&head_tag, secret_body.data_tag_mut());
|
||||||
secret_body.set_finger(&finger)?;
|
secret_body.set_finger(&finger)?;
|
||||||
}
|
}
|
||||||
net_packet.set_encrypt_flag(true);
|
net_packet.set_encrypt_flag(true);
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
Err(e) => Err(anyhow!("rs CHACHA20_POLY1305 加密失败:{}", e)),
|
Err(e) => Err(anyhow!("rs CHACHA20_POLY1305 加密失败:{}", e)),
|
||||||
};
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -118,4 +117,10 @@ fn test_rs_chacha20_poly1305() {
|
|||||||
d.encrypt_ipv4(&mut p).unwrap();
|
d.encrypt_ipv4(&mut p).unwrap();
|
||||||
d.decrypt_ipv4(&mut p).unwrap();
|
d.decrypt_ipv4(&mut p).unwrap();
|
||||||
assert_eq!(p.buffer(), &src);
|
assert_eq!(p.buffer(), &src);
|
||||||
|
let d = ChaCha20Poly1305Cipher::new_256([0; 32], None);
|
||||||
|
let mut p = NetPacket::new_encrypt([0; 73]).unwrap();
|
||||||
|
let src = p.buffer().to_vec();
|
||||||
|
d.encrypt_ipv4(&mut p).unwrap();
|
||||||
|
d.decrypt_ipv4(&mut p).unwrap();
|
||||||
|
assert_eq!(p.buffer(), &src);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,4 +1,5 @@
|
|||||||
use anyhow::anyhow;
|
use anyhow::anyhow;
|
||||||
|
use rand::RngCore;
|
||||||
|
|
||||||
use sha2::Digest;
|
use sha2::Digest;
|
||||||
|
|
||||||
@@ -49,3 +50,27 @@ impl Finger {
|
|||||||
return key[20..].try_into().unwrap();
|
return key[20..].try_into().unwrap();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
impl<B: AsRef<[u8]>> NetPacket<B> {
|
||||||
|
pub fn head_tag(&self) -> [u8; 12] {
|
||||||
|
let mut tag = [0; 12];
|
||||||
|
tag[0..4].copy_from_slice(&self.buffer()[4..8]);
|
||||||
|
tag[4..8].copy_from_slice(&self.buffer()[8..12]);
|
||||||
|
tag[8] = self.protocol().into();
|
||||||
|
tag[9] = self.transport_protocol();
|
||||||
|
tag[10] = self.is_gateway() as u8;
|
||||||
|
tag[11] = self.source_ttl();
|
||||||
|
tag
|
||||||
|
}
|
||||||
|
}
|
||||||
|
pub fn gen_nonce(tag: &mut [u8], random: &[u8]) {
|
||||||
|
tag[8] = random[0] ^ tag[8];
|
||||||
|
tag[9] = random[1] ^ tag[9];
|
||||||
|
tag[10] = random[2] ^ tag[10];
|
||||||
|
tag[11] = random[3] ^ tag[11];
|
||||||
|
}
|
||||||
|
pub fn gen_random_nonce(tag: &mut [u8; 12]) -> [u8; 4] {
|
||||||
|
let mut random = [0; 4];
|
||||||
|
rand::thread_rng().fill_bytes(&mut random);
|
||||||
|
gen_nonce(tag, &random);
|
||||||
|
random
|
||||||
|
}
|
||||||
|
|||||||
@@ -48,13 +48,7 @@ impl Sm4CbcCipher {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
let mut nonce_raw = [0; 12];
|
let nonce_raw = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
|
||||||
let len = net_packet.payload().len();
|
let len = net_packet.payload().len();
|
||||||
if len < 12 {
|
if len < 12 {
|
||||||
return Err(anyhow!("payload len <12"));
|
return Err(anyhow!("payload len <12"));
|
||||||
@@ -126,13 +120,7 @@ impl Sm4CbcCipher {
|
|||||||
net_packet.payload_mut()[..len].copy_from_slice(&out[..len]);
|
net_packet.payload_mut()[..len].copy_from_slice(&out[..len]);
|
||||||
net_packet.payload_mut()[len..].copy_from_slice(&iv);
|
net_packet.payload_mut()[len..].copy_from_slice(&iv);
|
||||||
if let Some(finger) = &self.finger {
|
if let Some(finger) = &self.finger {
|
||||||
let mut nonce_raw = [0; 12];
|
let nonce_raw = net_packet.head_tag();
|
||||||
nonce_raw[0..4].copy_from_slice(&net_packet.source().octets());
|
|
||||||
nonce_raw[4..8].copy_from_slice(&net_packet.destination().octets());
|
|
||||||
nonce_raw[8] = net_packet.protocol().into();
|
|
||||||
nonce_raw[9] = net_packet.transport_protocol();
|
|
||||||
nonce_raw[10] = net_packet.is_gateway() as u8;
|
|
||||||
nonce_raw[11] = net_packet.source_ttl();
|
|
||||||
let finger = finger.calculate_finger(&nonce_raw, net_packet.payload());
|
let finger = finger.calculate_finger(&nonce_raw, net_packet.payload());
|
||||||
let src_data_len = net_packet.data_len();
|
let src_data_len = net_packet.data_len();
|
||||||
//设置实际长度
|
//设置实际长度
|
||||||
|
|||||||
+255
-79
@@ -4,6 +4,261 @@ pub const ENCRYPTION_RESERVED: usize = 16 + 32 + 12;
|
|||||||
pub const AES_GCM_ENCRYPTION_RESERVED: usize = 32;
|
pub const AES_GCM_ENCRYPTION_RESERVED: usize = 32;
|
||||||
pub const RSA_ENCRYPTION_RESERVED: usize = 32;
|
pub const RSA_ENCRYPTION_RESERVED: usize = 32;
|
||||||
|
|
||||||
|
pub const RANDOM_RESERVED: usize = 4;
|
||||||
|
pub const FINGER_RESERVED: usize = 12;
|
||||||
|
pub const TAG_RESERVED: usize = 16;
|
||||||
|
|
||||||
|
/*
|
||||||
|
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||||
|
| random(32) |
|
||||||
|
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||||
|
| finger(32) |
|
||||||
|
| finger(32) |
|
||||||
|
| finger(32) |
|
||||||
|
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||||
|
*/
|
||||||
|
pub trait SecretTail {
|
||||||
|
fn buffer(&self) -> &[u8];
|
||||||
|
fn exist_finger(&self) -> bool;
|
||||||
|
fn random_buf(&self) -> &[u8] {
|
||||||
|
let buf = self.buffer();
|
||||||
|
let mut end = buf.len();
|
||||||
|
if self.exist_finger() {
|
||||||
|
end -= FINGER_RESERVED;
|
||||||
|
}
|
||||||
|
&buf[end - RANDOM_RESERVED..end]
|
||||||
|
}
|
||||||
|
fn finger(&self) -> &[u8] {
|
||||||
|
if self.exist_finger() {
|
||||||
|
let buf = self.buffer();
|
||||||
|
let end = buf.len();
|
||||||
|
&buf[end - FINGER_RESERVED..end]
|
||||||
|
} else {
|
||||||
|
&[]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub trait SecretTailMut: SecretTail {
|
||||||
|
fn buffer_mut(&mut self) -> &mut [u8];
|
||||||
|
fn set_random(&mut self, random: &[u8]) {
|
||||||
|
let f = self.exist_finger();
|
||||||
|
let buf = self.buffer_mut();
|
||||||
|
let mut end = buf.len();
|
||||||
|
if f {
|
||||||
|
end -= FINGER_RESERVED;
|
||||||
|
}
|
||||||
|
buf[end - RANDOM_RESERVED..end].copy_from_slice(random);
|
||||||
|
}
|
||||||
|
fn set_finger(&mut self, finger: &[u8]) -> io::Result<()> {
|
||||||
|
if self.exist_finger() {
|
||||||
|
if finger.len() != FINGER_RESERVED {
|
||||||
|
return Err(io::Error::new(
|
||||||
|
io::ErrorKind::InvalidData,
|
||||||
|
"finger.len != 12",
|
||||||
|
));
|
||||||
|
}
|
||||||
|
let buf = self.buffer_mut();
|
||||||
|
let end = buf.len();
|
||||||
|
buf[end - FINGER_RESERVED..end].copy_from_slice(finger);
|
||||||
|
Ok(())
|
||||||
|
} else {
|
||||||
|
Err(io::Error::new(
|
||||||
|
io::ErrorKind::InvalidData,
|
||||||
|
"not exist finger",
|
||||||
|
))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* aead加密数据体
|
||||||
|
0 15 31
|
||||||
|
0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
|
||||||
|
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||||
|
| 数据体 |
|
||||||
|
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||||
|
| tag(32) |
|
||||||
|
| tag(32) |
|
||||||
|
| tag(32) |
|
||||||
|
| tag(32) |
|
||||||
|
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||||
|
| random(32) |
|
||||||
|
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||||
|
| finger(32) |
|
||||||
|
| finger(32) |
|
||||||
|
| finger(32) |
|
||||||
|
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||||
|
|
||||||
|
注:finger用于快速校验数据是否被修改,上层可使用token、协议头参与计算finger,
|
||||||
|
确保服务端和客户端都能感知修改(服务端不能解密也能校验指纹)
|
||||||
|
*/
|
||||||
|
pub struct AEADSecretBody<B> {
|
||||||
|
buffer: B,
|
||||||
|
exist_finger: bool,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<B: AsRef<[u8]>> AEADSecretBody<B> {
|
||||||
|
pub fn new(buffer: B, exist_finger: bool) -> io::Result<AEADSecretBody<B>> {
|
||||||
|
let len = buffer.as_ref().len();
|
||||||
|
let min_len = if exist_finger {
|
||||||
|
TAG_RESERVED + RANDOM_RESERVED + FINGER_RESERVED
|
||||||
|
} else {
|
||||||
|
TAG_RESERVED + RANDOM_RESERVED
|
||||||
|
};
|
||||||
|
// 不能大于udp最大载荷长度
|
||||||
|
if len < min_len || len > 65535 - 20 - 8 - 12 {
|
||||||
|
return Err(io::Error::new(
|
||||||
|
io::ErrorKind::InvalidData,
|
||||||
|
format!("AEADSecretBody length overflow {}", len),
|
||||||
|
));
|
||||||
|
}
|
||||||
|
Ok(AEADSecretBody {
|
||||||
|
buffer,
|
||||||
|
exist_finger,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
pub fn data(&self) -> &[u8] {
|
||||||
|
let mut end = self.buffer.as_ref().len() - TAG_RESERVED - RANDOM_RESERVED;
|
||||||
|
if self.exist_finger {
|
||||||
|
end -= FINGER_RESERVED;
|
||||||
|
}
|
||||||
|
&self.buffer.as_ref()[..end]
|
||||||
|
}
|
||||||
|
pub fn tag(&self) -> &[u8] {
|
||||||
|
let mut end = self.buffer.as_ref().len() - RANDOM_RESERVED;
|
||||||
|
if self.exist_finger {
|
||||||
|
end -= FINGER_RESERVED;
|
||||||
|
}
|
||||||
|
&self.buffer.as_ref()[end - TAG_RESERVED..end]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<B: AsRef<[u8]>> SecretTail for AEADSecretBody<B> {
|
||||||
|
#[inline]
|
||||||
|
fn buffer(&self) -> &[u8] {
|
||||||
|
self.buffer.as_ref()
|
||||||
|
}
|
||||||
|
#[inline]
|
||||||
|
fn exist_finger(&self) -> bool {
|
||||||
|
self.exist_finger
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<B: AsRef<[u8]> + AsMut<[u8]>> SecretTailMut for AEADSecretBody<B> {
|
||||||
|
#[inline]
|
||||||
|
fn buffer_mut(&mut self) -> &mut [u8] {
|
||||||
|
self.buffer.as_mut()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<B: AsRef<[u8]> + AsMut<[u8]>> AEADSecretBody<B> {
|
||||||
|
/// 数据部分
|
||||||
|
pub fn data_mut(&mut self) -> &mut [u8] {
|
||||||
|
let mut end = self.buffer.as_ref().len() - RANDOM_RESERVED - TAG_RESERVED;
|
||||||
|
if self.exist_finger {
|
||||||
|
end -= FINGER_RESERVED;
|
||||||
|
}
|
||||||
|
&mut self.buffer.as_mut()[..end]
|
||||||
|
}
|
||||||
|
/// 数据和tag部分
|
||||||
|
pub fn data_tag_mut(&mut self) -> &mut [u8] {
|
||||||
|
let mut end = self.buffer.as_ref().len() - RANDOM_RESERVED;
|
||||||
|
if self.exist_finger {
|
||||||
|
end -= FINGER_RESERVED;
|
||||||
|
}
|
||||||
|
&mut self.buffer.as_mut()[..end]
|
||||||
|
}
|
||||||
|
pub fn set_tag(&mut self, tag: &[u8]) -> io::Result<()> {
|
||||||
|
if tag.len() != 16 {
|
||||||
|
return Err(io::Error::new(io::ErrorKind::InvalidData, "tag.len != 16"));
|
||||||
|
}
|
||||||
|
let mut end = self.buffer.as_ref().len() - RANDOM_RESERVED;
|
||||||
|
if self.exist_finger {
|
||||||
|
end -= FINGER_RESERVED;
|
||||||
|
}
|
||||||
|
self.buffer.as_mut()[end - TAG_RESERVED..end].copy_from_slice(tag);
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 带随机数的加密数据体
|
||||||
|
0 15 31
|
||||||
|
0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
|
||||||
|
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||||
|
| 数据体 |
|
||||||
|
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||||
|
| random(32) |
|
||||||
|
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||||
|
| finger(32) |
|
||||||
|
| finger(32) |
|
||||||
|
| finger(32) |
|
||||||
|
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||||
|
|
||||||
|
注:finger用于快速校验数据是否被修改,上层可使用token、协议头参与计算finger,
|
||||||
|
确保服务端和客户端都能感知修改(服务端不能解密也能校验指纹)
|
||||||
|
*/
|
||||||
|
pub struct IVSecretBody<B> {
|
||||||
|
buffer: B,
|
||||||
|
exist_finger: bool,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<B: AsRef<[u8]>> IVSecretBody<B> {
|
||||||
|
pub fn new(buffer: B, exist_finger: bool) -> io::Result<IVSecretBody<B>> {
|
||||||
|
let len = buffer.as_ref().len();
|
||||||
|
let min_len = if exist_finger {
|
||||||
|
FINGER_RESERVED + RANDOM_RESERVED
|
||||||
|
} else {
|
||||||
|
RANDOM_RESERVED
|
||||||
|
};
|
||||||
|
// 不能大于udp最大载荷长度
|
||||||
|
if len < min_len || len > 65535 - 20 - 8 - 12 {
|
||||||
|
return Err(io::Error::new(
|
||||||
|
io::ErrorKind::InvalidData,
|
||||||
|
format!("IVSecretBody length overflow {}", len),
|
||||||
|
));
|
||||||
|
}
|
||||||
|
Ok(IVSecretBody {
|
||||||
|
buffer,
|
||||||
|
exist_finger,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
pub fn data(&self) -> &[u8] {
|
||||||
|
let mut end = self.buffer.as_ref().len() - RANDOM_RESERVED;
|
||||||
|
if self.exist_finger {
|
||||||
|
end -= FINGER_RESERVED;
|
||||||
|
}
|
||||||
|
&self.buffer.as_ref()[..end]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<B: AsRef<[u8]> + AsMut<[u8]>> IVSecretBody<B> {
|
||||||
|
pub fn data_mut(&mut self) -> &mut [u8] {
|
||||||
|
let mut end = self.buffer.as_ref().len() - RANDOM_RESERVED;
|
||||||
|
if self.exist_finger {
|
||||||
|
end -= FINGER_RESERVED;
|
||||||
|
}
|
||||||
|
&mut self.buffer.as_mut()[..end]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<B: AsRef<[u8]>> SecretTail for IVSecretBody<B> {
|
||||||
|
#[inline]
|
||||||
|
fn buffer(&self) -> &[u8] {
|
||||||
|
self.buffer.as_ref()
|
||||||
|
}
|
||||||
|
#[inline]
|
||||||
|
fn exist_finger(&self) -> bool {
|
||||||
|
self.exist_finger
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<B: AsRef<[u8]> + AsMut<[u8]>> SecretTailMut for IVSecretBody<B> {
|
||||||
|
#[inline]
|
||||||
|
fn buffer_mut(&mut self) -> &mut [u8] {
|
||||||
|
self.buffer.as_mut()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/* aes_gcm加密数据体
|
/* aes_gcm加密数据体
|
||||||
0 15 31
|
0 15 31
|
||||||
0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
|
0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
|
||||||
@@ -253,85 +508,6 @@ impl<B: AsRef<[u8]> + AsMut<[u8]>> AesCbcSecretBody<B> {
|
|||||||
&mut self.buffer.as_mut()[..end]
|
&mut self.buffer.as_mut()[..end]
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/* ChaCah20加密数据体
|
|
||||||
0 15 31
|
|
||||||
0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
|
|
||||||
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
||||||
| 数据体 |
|
|
||||||
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
||||||
| finger(32) |
|
|
||||||
| finger(32) |
|
|
||||||
| finger(32) |
|
|
||||||
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
||||||
|
|
||||||
注:finger用于快速校验数据是否被修改,上层可使用token、协议头参与计算finger,
|
|
||||||
确保服务端和客户端都能感知修改(服务端不能解密也能校验指纹)
|
|
||||||
*/
|
|
||||||
pub struct ChaCah20SecretBody<B> {
|
|
||||||
buffer: B,
|
|
||||||
exist_finger: bool,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<B: AsRef<[u8]>> ChaCah20SecretBody<B> {
|
|
||||||
pub fn new(buffer: B, exist_finger: bool) -> io::Result<ChaCah20SecretBody<B>> {
|
|
||||||
let len = buffer.as_ref().len();
|
|
||||||
let min_len = if exist_finger { 12 } else { 0 };
|
|
||||||
// 不能大于udp最大载荷长度
|
|
||||||
if len < min_len || len > 65535 - 20 - 8 - 12 {
|
|
||||||
return Err(io::Error::new(
|
|
||||||
io::ErrorKind::InvalidData,
|
|
||||||
"ChaCah20SecretBody length overflow",
|
|
||||||
));
|
|
||||||
}
|
|
||||||
Ok(ChaCah20SecretBody {
|
|
||||||
buffer,
|
|
||||||
exist_finger,
|
|
||||||
})
|
|
||||||
}
|
|
||||||
pub fn en_body(&self) -> &[u8] {
|
|
||||||
let mut end = self.buffer.as_ref().len();
|
|
||||||
if self.exist_finger {
|
|
||||||
end -= 12;
|
|
||||||
}
|
|
||||||
&self.buffer.as_ref()[..end]
|
|
||||||
}
|
|
||||||
pub fn finger(&self) -> &[u8] {
|
|
||||||
if self.exist_finger {
|
|
||||||
let end = self.buffer.as_ref().len();
|
|
||||||
&self.buffer.as_ref()[end - 12..end]
|
|
||||||
} else {
|
|
||||||
&[]
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<B: AsRef<[u8]> + AsMut<[u8]>> ChaCah20SecretBody<B> {
|
|
||||||
pub fn set_finger(&mut self, finger: &[u8]) -> io::Result<()> {
|
|
||||||
if self.exist_finger {
|
|
||||||
if finger.len() != 12 {
|
|
||||||
return Err(io::Error::new(
|
|
||||||
io::ErrorKind::InvalidData,
|
|
||||||
"finger.len != 12",
|
|
||||||
));
|
|
||||||
}
|
|
||||||
let end = self.buffer.as_ref().len();
|
|
||||||
self.buffer.as_mut()[end - 12..end].copy_from_slice(finger);
|
|
||||||
Ok(())
|
|
||||||
} else {
|
|
||||||
Err(io::Error::new(
|
|
||||||
io::ErrorKind::InvalidData,
|
|
||||||
"cbc not exist finger",
|
|
||||||
))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
pub fn en_body_mut(&mut self) -> &mut [u8] {
|
|
||||||
let mut end = self.buffer.as_ref().len();
|
|
||||||
if self.exist_finger {
|
|
||||||
end -= 12;
|
|
||||||
}
|
|
||||||
&mut self.buffer.as_mut()[..end]
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* rsa加密数据体
|
/* rsa加密数据体
|
||||||
0 15 31
|
0 15 31
|
||||||
|
|||||||
Reference in New Issue
Block a user