diff --git a/src/tasks/mod.rs b/src/tasks/mod.rs index f7475be..b024471 100644 --- a/src/tasks/mod.rs +++ b/src/tasks/mod.rs @@ -11,7 +11,7 @@ use tasks01::{ gcm::{gcm_decrypt, gcm_encrypt}, gfmul::gfmul_task, pad_oracle::padding_oracle, - pfmath::gfpoly_add, + pfmath::{gfdiv, gfpoly_add, gfpoly_divmod, gfpoly_mul, gfpoly_pow, gfpoly_powmod}, poly2block::poly2block, sea128::sea128, xex::{self, fde_xex}, @@ -86,10 +86,42 @@ pub fn task_deploy(testcase: &Testcase) -> Result { } "gfpoly_add" => { let result = gfpoly_add(args)?; - let json = json!({"plaintext" : result.to_c_array()}); + let json = json!({"S" : result.to_c_array()}); Ok(json) } + "gfpoly_mul" => { + let result = gfpoly_mul(args)?; + let json = json!({"P" : result.to_c_array()}); + + Ok(json) + } + "gfpoly_pow" => { + let result = gfpoly_pow(args)?; + let json = json!({"Z" : result.to_c_array()}); + + Ok(json) + } + "gfdiv" => { + let result = gfdiv(args)?; + let out = BASE64_STANDARD.encode(result); + let json = json!({"q" : out}); + + Ok(json) + } + "gfpoly_divmod" => { + let result = gfpoly_divmod(args)?; + let json = json!({"Q" : result.0.to_c_array(), "R" : result.1.to_c_array()}); + + Ok(json) + } + "gfpoly_powmod" => { + let result = gfpoly_powmod(args)?; + let json = json!({"Z" : result.to_c_array()}); + + Ok(json) + } + _ => Err(anyhow!( "Fatal. No compatible action found. Json data was {:?}. Arguments were; {:?}", testcase, @@ -279,4 +311,22 @@ mod tests { Ok(()) } + + #[test] + fn test_task_gcm_gfpoly_add() -> Result<()> { + let json = fs::read_to_string("test_json/gcm_decrypt_sea.json").unwrap(); + let parsed = parse_json(json).unwrap(); + + let expected = json!({ "responses" : { "b856d760-023d-4b00-bad2-15d2b6da22fe" : { + "plaintext": "RGFzIGlzdCBlaW4gVGVzdA==", + "authentic": true, + }}}); + + assert_eq!( + serde_json::to_value(task_distrubute(&parsed)?).unwrap(), + serde_json::to_value(expected).unwrap() + ); + + Ok(()) + } } diff --git a/src/tasks/tasks01/pfmath.rs b/src/tasks/tasks01/pfmath.rs index b0c978e..4ad3ac7 100644 --- a/src/tasks/tasks01/pfmath.rs +++ b/src/tasks/tasks01/pfmath.rs @@ -2,7 +2,7 @@ use anyhow::Result; use base64::{prelude::BASE64_STANDARD, Engine}; use serde_json::Value; -use crate::utils::field::Polynomial; +use crate::utils::field::{FieldElement, Polynomial}; pub fn gfpoly_add(args: &Value) -> Result { let poly_a = Polynomial::from_c_array(&args["A"].clone()); @@ -13,3 +13,57 @@ pub fn gfpoly_add(args: &Value) -> Result { Ok(result) } + +pub fn gfpoly_mul(args: &Value) -> Result { + let poly_a = Polynomial::from_c_array(&args["A"].clone()); + + let poly_b = Polynomial::from_c_array(&args["B"].clone()); + + let result = poly_a * poly_b; + + Ok(result) +} + +pub fn gfpoly_pow(args: &Value) -> Result { + let poly_a = Polynomial::from_c_array(&args["A"].clone()); + + let k: u128 = serde_json::from_value(args["k"].clone())?; + + let result = poly_a.pow(k); + + Ok(result) +} + +pub fn gfdiv(args: &Value) -> Result { + let f1_text: String = serde_json::from_value(args["a"].clone())?; + let f_a = FieldElement::new(BASE64_STANDARD.decode(f1_text)?); + + let f2_text: String = serde_json::from_value(args["b"].clone())?; + let f_b = FieldElement::new(BASE64_STANDARD.decode(f2_text)?); + + let result = f_a / f_b; + + Ok(result) +} + +pub fn gfpoly_divmod(args: &Value) -> Result<(Polynomial, Polynomial)> { + let poly_a = Polynomial::from_c_array(&args["A"].clone()); + + let poly_b = Polynomial::from_c_array(&args["B"].clone()); + + let result = poly_a.div(&poly_b); + + Ok(result) +} + +pub fn gfpoly_powmod(args: &Value) -> Result { + let poly_a = Polynomial::from_c_array(&args["A"].clone()); + + let poly_m = Polynomial::from_c_array(&args["M"].clone()); + + let k: u128 = serde_json::from_value(args["k"].clone())?; + + let result = poly_a.pow_mod(k, poly_m); + + Ok(result) +} diff --git a/src/utils/field.rs b/src/utils/field.rs index 59ffc18..fac51f2 100644 --- a/src/utils/field.rs +++ b/src/utils/field.rs @@ -77,19 +77,19 @@ impl Polynomial { polynomial_2_block(vec![0], "gcm").unwrap(), )]); - eprintln!("Initial result: {:?}", result); + //eprintln!("Initial result: {:?}", result); while exponent > 0 { - eprintln!("Current exponent: {:02X}", exponent); + //eprintln!("Current exponent: {:02X}", exponent); if exponent & 1 == 1 { let temp = &self * &result; - eprintln!("After multiplication: {:?}", temp); + //eprintln!("After multiplication: {:?}", temp); result = temp.div(&modulus).1; - eprintln!("After mod: {:?}", result); + //eprintln!("After mod: {:?}", result); } let temp_square = &self * &self; - eprintln!("After squaring: {:?}", temp_square); + //eprintln!("After squaring: {:?}", temp_square); self = temp_square.div(&modulus).1; - eprintln!("After mod: {:?}", self); + //eprintln!("After mod: {:?}", self); exponent >>= 1; } result @@ -286,7 +286,7 @@ impl FieldElement { pub fn inv(mut self) -> Self { let mut inverser: u128 = 0xfffffffffffffffffffffffffffffffe; let mut inverse: Vec = polynomial_2_block(vec![0], "gcm").unwrap(); - eprintln!("Inverse start {:02X?}", inverse); + //eprintln!("Inverse start {:02X?}", inverse); while inverser > 0 { //eprintln!("{:02X}", inverser); @@ -297,7 +297,7 @@ impl FieldElement { self.field_element = gfmul(&self.field_element, &self.field_element, "gcm") .expect("Error in sqrmul sqr"); } - eprintln!("Inverse rhs {:?}", inverse); + //eprintln!("Inverse rhs {:?}", inverse); FieldElement::new(inverse) } } diff --git a/test_json/pfmath_tests.json b/test_json/pfmath_tests.json new file mode 100644 index 0000000..b9cc6e0 --- /dev/null +++ b/test_json/pfmath_tests.json @@ -0,0 +1,98 @@ +{ + "testcases": { + "gfpoly_add": { + "action": "gfpoly_add", + "arguments": { + "A": [ + "NeverGonnaGiveYouUpAAA==", + "NeverGonnaLetYouDownAA==", + "NeverGonnaRunAroundAAA==", + "AndDesertYouAAAAAAAAAA==" + ], + "B": [ + "KryptoanalyseAAAAAAAAA==", + "DHBWMannheimAAAAAAAAAA==" + ] + } + }, + "gfpoly_mul": { + "action": "gfpoly_mul", + "arguments": { + "A": [ + "JAAAAAAAAAAAAAAAAAAAAA==", + "wAAAAAAAAAAAAAAAAAAAAA==", + "ACAAAAAAAAAAAAAAAAAAAA==" + ], + "B": [ + "0AAAAAAAAAAAAAAAAAAAAA==", + "IQAAAAAAAAAAAAAAAAAAAA==" + ] + } + }, + "gfpoly_mul_10": { + "action": "gfpoly_mul", + "arguments": { + "A": [ + "JAAAAAAAAAAAAAAAAAAAAA==", + "wAAAAAAAAAAAAAAAAAAAAA==", + "ACAAAAAAAAAAAAAAAAAAAA==" + ], + "B": [ + "AAAAAAAAAAAAAAAAAAAAAA==" + ] + } + }, + "gfpoly_mul_01": { + "action": "gfpoly_mul", + "arguments": { + "A": [ + "AAAAAAAAAAAAAAAAAAAAAA==" + ], + "B": [ + "0AAAAAAAAAAAAAAAAAAAAA==", + "IQAAAAAAAAAAAAAAAAAAAA==" + ] + } + }, + "gfpoly_pow": { + "action": "gfpoly_pow", + "arguments": { + "A": [ + "JAAAAAAAAAAAAAAAAAAAAA==", + "wAAAAAAAAAAAAAAAAAAAAA==", + "ACAAAAAAAAAAAAAAAAAAAA==" + ], + "k": 3 + } + }, + "gfpoly_pow_k0": { + "action": "gfpoly_pow", + "arguments": { + "A": [ + "JAAAAAAAAAAAAAAAAAAAAA==", + "wAAAAAAAAAAAAAAAAAAAAA==", + "ACAAAAAAAAAAAAAAAAAAAA==" + ], + "k": 0 + } + }, + "gfpoly_pow_k1": { + "action": "gfpoly_pow", + "arguments": { + "A": [ + "JAAAAAAAAAAAAAAAAAAAAA==", + "wAAAAAAAAAAAAAAAAAAAAA==", + "ACAAAAAAAAAAAAAAAAAAAA==" + ], + "k": 1 + } + }, + "gfdiv": { + "action": "gfdiv", + "arguments": { + "a": "JAAAAAAAAAAAAAAAAAAAAA==", + "b": "wAAAAAAAAAAAAAAAAAAAAA==" + } + } + } +}