gallois cli tool

This commit is contained in:
Christoph J. Scherr 2023-05-19 13:56:29 +02:00
parent b372e4e659
commit 34385e8a6d
Signed by: PlexSheep
GPG Key ID: 25B4ACF7D88186CC
4 changed files with 79 additions and 22 deletions

View File

@ -64,9 +64,14 @@ pub struct AlgoCommand {
#[derive(Subcommand, Clone, Debug, PartialEq, Eq)] #[derive(Subcommand, Clone, Debug, PartialEq, Eq)]
pub enum MathActions { pub enum MathActions {
#[command(name="modexp")] #[command(name="modexp")]
/// perform exponentiation with a constant modulo applied
Modexp(ModexpArgs), Modexp(ModexpArgs),
/// perform modular reduction
Modred(ModredArgs), Modred(ModredArgs),
/// p minus 1 prime test
Pm1(PM1Args), Pm1(PM1Args),
//// calculate in a gallois field
Gallois(GalloisAction),
} }
#[derive(Args, Clone, Debug, PartialEq, Eq)] #[derive(Args, Clone, Debug, PartialEq, Eq)]
@ -92,6 +97,41 @@ pub struct PM1Args {
pub max_prime: u128, pub max_prime: u128,
} }
#[derive(Args, Clone, Debug, PartialEq, Eq)]
pub struct GalloisAction {
#[clap(value_parser=maybe_hex::<u128>)]
pub field: u128,
#[command(subcommand)]
pub action: GalloisActions
}
#[derive(Subcommand, Clone, Debug, PartialEq, Eq)]
pub enum GalloisActions {
/// draw the root of n
Sqrt(GalloisSqrtArgs),
/// reduce n to the range of the field
Reduce(GalloisReduceArgs),
/// calculate the (multiplicative) inverse of n
Invert(GalloisInvertArgs),
}
#[derive(Args, Clone, Debug, PartialEq, Eq)]
pub struct GalloisSqrtArgs {
#[clap(value_parser=maybe_hex::<u128>)]
pub n: u128,
}
#[derive(Args, Clone, Debug, PartialEq, Eq)]
pub struct GalloisReduceArgs {
pub n: i128,
}
#[derive(Args, Clone, Debug, PartialEq, Eq)]
pub struct GalloisInvertArgs {
#[clap(value_parser=maybe_hex::<u128>)]
pub n: u128,
}
#[derive(Subcommand, Clone, Debug, PartialEq, Eq)] #[derive(Subcommand, Clone, Debug, PartialEq, Eq)]
pub enum BinaryActions { pub enum BinaryActions {
/// bit rotation/circular shifting (only 32bit) /// bit rotation/circular shifting (only 32bit)

View File

@ -10,7 +10,7 @@
use crate::cplex::cli::Cli; use crate::cplex::cli::Cli;
use std::fmt::{Debug, LowerHex}; use std::fmt::{Debug, LowerHex, Display};
use pyo3::prelude::*; use pyo3::prelude::*;
@ -48,11 +48,13 @@ pub fn seperator() {
/////////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////////////
/// process a result with some int /// process a result with some int
pub fn proc_result<T>(result: Result<T, String>, args: Cli) pub fn proc_result<T, K>(result: Result<T, K>, args: Cli)
where where
T: Debug, T: Debug,
T: Integer, T: Integer,
T: LowerHex T: LowerHex,
T: Display,
K: Debug
{ {
if args.verbose { if args.verbose {
seperator(); seperator();
@ -60,11 +62,11 @@ pub fn proc_result<T>(result: Result<T, String>, args: Cli)
match result { match result {
Ok(res) => { Ok(res) => {
if args.machine { if args.machine {
println!("{:#x}", res); println!("{} ({:#x})", res, res);
} }
else { else {
seperator(); seperator();
println!("result is {:#x}", res); println!("result is {} ({:#x})", res, res);
} }
} }
Err(e) => { Err(e) => {
@ -84,17 +86,18 @@ pub fn proc_num<T>(num: T, args: Cli)
where where
T: Debug, T: Debug,
T: Integer, T: Integer,
T: LowerHex T: LowerHex,
T: Display,
{ {
if args.verbose { if args.verbose {
seperator(); seperator();
} }
if args.machine { if args.machine {
println!("{:#x}", num); println!("{} ({:#x})", num, num);
} }
else { else {
seperator(); seperator();
println!("result is {:#x}", num); println!("result is {} ({:#x})", num, num);
} }
} }
@ -116,9 +119,10 @@ pub fn proc_vec<T>(vec: Vec<T>, args: Cli)
} }
/// process a result with some vec /// process a result with some vec
pub fn proc_result_vec<T>(res: Result<Vec<T>, String>, args: Cli) pub fn proc_result_vec<T, K>(res: Result<Vec<T>, K>, args: Cli)
where where
T: Debug, T: Debug,
K: Debug
{ {
if args.verbose { if args.verbose {
seperator(); seperator();

View File

@ -60,6 +60,23 @@ pub fn main() {
); );
cplex::printing::proc_result_vec(vec, args); cplex::printing::proc_result_vec(vec, args);
} }
MathActions::Gallois(gal_args) => {
let field = math::gallois::GalloisFiled::new(gal_args.field, args.verbose);
match gal_args.action {
GalloisActions::Sqrt(gal_sqrt_args) => {
let result = field.sqrt(gal_sqrt_args.n);
cplex::printing::proc_result(result, args);
}
GalloisActions::Reduce(gal_red_args) => {
let result = field.reduce_neg(gal_red_args.n);
cplex::printing::proc_num(result, args);
}
GalloisActions::Invert(gal_inv_args) => {
let result = field.inverse(gal_inv_args.n);
cplex::printing::proc_result(result, args);
}
}
}
} }
} }
Commands::Binary(action) => { Commands::Binary(action) => {

View File

@ -56,7 +56,7 @@ pub struct GalloisFiled {
impl GalloisFiled { impl GalloisFiled {
/// make a new gallois field /// make a new gallois field
pub fn new(base: u128, verbose: bool) -> Self { pub fn new(base: u128, verbose: bool) -> Self {
let mut field = GalloisFiled{ let field = GalloisFiled{
base, base,
// TODO: calculate the characteristic // TODO: calculate the characteristic
cha: 0, cha: 0,
@ -70,14 +70,7 @@ impl GalloisFiled {
/// reduce a number to fit into the gallois field /// reduce a number to fit into the gallois field
pub fn reduce(self, n: u128) -> u128 { pub fn reduce(self, n: u128) -> u128 {
let mut n = n; return n % self.base;
if n < 0 {
while n < 0 {
n += self.base;
}
}
n %= self.base;
return n;
} }
/// reduce a negative number to fit into the gallois field /// reduce a negative number to fit into the gallois field
@ -135,6 +128,7 @@ impl GalloisFiled {
/////////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////////////
#[test] #[test]
fn test_gallois_sqrt() { fn test_gallois_sqrt() {
let field = GalloisFiled::new(67, true);
panic!("TODO") panic!("TODO")
} }
@ -149,4 +143,6 @@ fn test_gallois_inverse() {
assert_eq!(field.inverse(6).unwrap(), 14); assert_eq!(field.inverse(6).unwrap(), 14);
assert_eq!(field.inverse(54).unwrap(), 20); assert_eq!(field.inverse(54).unwrap(), 20);
assert!(field.inverse(0).is_err()); assert!(field.inverse(0).is_err());
// TODO add a test for a field that has a non prime base
} }