diff --git a/Cargo.lock b/Cargo.lock index 5e4f78c..e16a0af 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -90,6 +90,12 @@ dependencies = [ [[package]] name = "p12" version = "0.1.0" +dependencies = [ + "anyhow", + "base64", + "common", + "rand", +] [[package]] name = "p13" @@ -214,9 +220,9 @@ checksum = "69cdb34c158ceb288df11e18b4bd39de994f6657d83847bdffdbd7f346754b0f" [[package]] name = "rand" -version = "0.9.1" +version = "0.9.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9fbfd9d094a40bf3ae768db9361049ace4c0e04a4fd6b359518bd7b73a73dd97" +checksum = "6db2770f06117d490610c7488547d543617b21bfa07796d7a12f6f1bd53850d1" dependencies = [ "rand_chacha", "rand_core", diff --git a/Cargo.toml b/Cargo.toml index 5343f5a..bf4fef7 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -5,3 +5,9 @@ edition = "2024" [workspace] members = ["problems/*", "common"] + +[workspace.dependencies] +hex = "0.4.3" +base64 = "0.22.1" +anyhow = "1.0.98" +rand = "0.9.2" diff --git a/cryptopal_book/.gitignore b/cryptopal_book/.gitignore new file mode 100644 index 0000000..7585238 --- /dev/null +++ b/cryptopal_book/.gitignore @@ -0,0 +1 @@ +book diff --git a/problems/p1/Cargo.toml b/problems/p1/Cargo.toml index 36de262..d5055a0 100644 --- a/problems/p1/Cargo.toml +++ b/problems/p1/Cargo.toml @@ -4,5 +4,5 @@ version = "0.1.0" edition = "2024" [dependencies] -hex = "0.4.3" -base64 = "0.22.1" +hex = { workspace = true } +base64 = { workspace = true } diff --git a/problems/p10/Cargo.toml b/problems/p10/Cargo.toml index 06ef0c3..99d1931 100644 --- a/problems/p10/Cargo.toml +++ b/problems/p10/Cargo.toml @@ -4,7 +4,7 @@ version = "0.1.0" edition = "2024" [dependencies] -anyhow = "1.0" -hex = "0.4" -base64 = "0.22" +anyhow = { workspace = true } +hex = { workspace = true } +base64 = { workspace = true } common = { path = "../../common" } diff --git a/problems/p11/Cargo.toml b/problems/p11/Cargo.toml index 7111df7..6182a9a 100644 --- a/problems/p11/Cargo.toml +++ b/problems/p11/Cargo.toml @@ -5,4 +5,4 @@ edition = "2024" [dependencies] common = { path = "../../common" } -rand = "0.9.1" +rand = { workspace = true } diff --git a/problems/p12/Cargo.toml b/problems/p12/Cargo.toml index eb7d2e7..3690b2a 100644 --- a/problems/p12/Cargo.toml +++ b/problems/p12/Cargo.toml @@ -4,3 +4,7 @@ version = "0.1.0" edition = "2024" [dependencies] +common = { path = "../../common" } +rand = { workspace = true } +base64 = { workspace = true } +anyhow = { workspace = true } diff --git a/problems/p12/src/main.rs b/problems/p12/src/main.rs index e7a11a9..bde7810 100644 --- a/problems/p12/src/main.rs +++ b/problems/p12/src/main.rs @@ -1,3 +1,82 @@ -fn main() { - println!("Hello, world!"); +use std::process::exit; + +use anyhow::Result; +use base64::{Engine, engine::general_purpose::STANDARD}; +use common::{aes_ecb_enc, pkcs7_padding}; +use rand::{prelude::*, rand_core::block}; + +fn gen_random_key() -> [u8; 16] { + let mut rng = rand::rng(); + let mut key = [0u8; 16]; + rng.fill(&mut key); + key +} + +fn oracle(controlled_input: &[u8], key: &[u8; 16], unknown_string: &[u8]) -> Vec { + let mut data = Vec::new(); + data.extend_from_slice(controlled_input); + data.extend_from_slice(unknown_string); + + pkcs7_padding(&mut data, 16); + + aes_ecb_enc(&data, key).unwrap() +} + +fn main() -> Result<()> { + let b64_unknown_string = "Um9sbGluJyBpbiBteSA1LjAKV2l0aCBteSByYWctdG9wIGRvd24gc28gbXkgaGFpciBjYW4gYmxvdwpUaGUgZ2lybGllcyBvbiBzdGFuZGJ5IHdhdmluZyBqdXN0IHRvIHNheSBoaQpEaWQgeW91IHN0b3A/IE5vLCBJIGp1c3QgZHJvdmUgYnkK"; + let unknown_string = STANDARD.decode(b64_unknown_string)?; + let key = gen_random_key(); + + // let plaintext = Vec::new(); + + // step1. find padding length and unknown_string length. + let mut padding_len = 0; + + let prev_cipher = oracle(&vec![0; padding_len], &key, &unknown_string); + while prev_cipher.len() + 16 != oracle(&vec![0; padding_len], &key, &unknown_string).len() { + padding_len += 1; + } + println!("padding_len: {padding_len}"); // 6 + let unknown_str_len = prev_cipher.len() - padding_len; + println!("unknown_str_len: {unknown_str_len}"); + + assert_eq!(unknown_str_len, unknown_string.len()); // debug use + + let mut cracked: Vec = Vec::new(); + + let mut flag = false; + + while cracked.len() != unknown_str_len { + padding_len += 1; + for i in 0..=255u8 { + let mut block = Vec::new(); + block.push(i); + block.extend_from_slice(&cracked[..cracked.len().min(15)]); + + pkcs7_padding(&mut block, 16); + block.extend(b"1".repeat(padding_len)); + let cipher = oracle(&block, &key, &unknown_string); + + let chunks: Vec<&[u8]> = cipher.chunks(16).collect(); + let first_16 = chunks[0]; + let need_crack_16 = chunks[chunks.len() - 1 - ((cracked.len() + 1) / 16)]; + if first_16 == need_crack_16 { + cracked.insert(0, i); + flag = true; + break; + } + } + if flag { + flag = false; + } else { + println!("Error. Some byte not found."); + println!("Cerrent length: {}", cracked.len()); + exit(0) + } + } + println!("{}", String::from_utf8_lossy(&cracked)); + // println!("{}", String::from_utf8_lossy(&plaintext)); + assert_eq!(cracked, unknown_string); + + Ok(()) } diff --git a/problems/p15/Cargo.toml b/problems/p15/Cargo.toml index 9ad3a39..88bd750 100644 --- a/problems/p15/Cargo.toml +++ b/problems/p15/Cargo.toml @@ -4,4 +4,4 @@ version = "0.1.0" edition = "2024" [dependencies] -anyhow = "1.0.98" +anyhow = { workspace = true } diff --git a/problems/p2/Cargo.toml b/problems/p2/Cargo.toml index dc22998..a384a03 100644 --- a/problems/p2/Cargo.toml +++ b/problems/p2/Cargo.toml @@ -4,4 +4,4 @@ version = "0.1.0" edition = "2024" [dependencies] -hex = "0.4.3" +hex = { workspace = true } diff --git a/problems/p3/Cargo.toml b/problems/p3/Cargo.toml index 8fe35a6..cd5a38c 100644 --- a/problems/p3/Cargo.toml +++ b/problems/p3/Cargo.toml @@ -5,4 +5,4 @@ edition = "2024" [dependencies] common = { path = "../../common/" } -hex = "0.4.3" +hex = { workspace = true } diff --git a/problems/p4/Cargo.toml b/problems/p4/Cargo.toml index f6b82cf..f84ac06 100644 --- a/problems/p4/Cargo.toml +++ b/problems/p4/Cargo.toml @@ -4,5 +4,5 @@ version = "0.1.0" edition = "2024" [dependencies] -hex = "0.4.3" +hex = { workspace = true } common = { path = "../../common/" } diff --git a/problems/p5/Cargo.toml b/problems/p5/Cargo.toml index 75dbd0f..0a77a7b 100644 --- a/problems/p5/Cargo.toml +++ b/problems/p5/Cargo.toml @@ -5,5 +5,5 @@ edition = "2024" [dependencies] common = { path = "../../common/" } -hex = "0.4.3" -anyhow = "1.0.98" +hex = { workspace = true } +anyhow = { workspace = true } diff --git a/problems/p6/Cargo.toml b/problems/p6/Cargo.toml index 1a64dfe..90eeab4 100644 --- a/problems/p6/Cargo.toml +++ b/problems/p6/Cargo.toml @@ -4,6 +4,6 @@ version = "0.1.0" edition = "2024" [dependencies] -base64 = "0.22.1" -anyhow = "1.0.98" +base64 = { workspace = true } +anyhow = { workspace = true } common = { path = "../../common/" } diff --git a/problems/p7/Cargo.toml b/problems/p7/Cargo.toml index 62de4f3..6392ba6 100644 --- a/problems/p7/Cargo.toml +++ b/problems/p7/Cargo.toml @@ -4,6 +4,6 @@ version = "0.1.0" edition = "2024" [dependencies] -anyhow = "1.0.98" -hex = "0.4.3" -base64 = "0.22.1" +anyhow = { workspace = true } +hex = { workspace = true } +base64 = { workspace = true } diff --git a/problems/p8/Cargo.toml b/problems/p8/Cargo.toml index 24397e3..5f82952 100644 --- a/problems/p8/Cargo.toml +++ b/problems/p8/Cargo.toml @@ -4,4 +4,4 @@ version = "0.1.0" edition = "2024" [dependencies] -hex = "0.4.3" +hex = { workspace = true }