fn run_hash (mut input: Vec<u8>) -> String {
pad (&mut input);
let datablocks = compress(input);
return format_hash(datablocks);
}
fn pad(data: &mut Vec<u8>) {
data.extend(data.len().to_be_bytes());
while data.len() % 6 > 0 {
data.push(255);
}
}
fn compress(mut data: Vec<u8>) -> Vec<u8> {
let mut mainblock: Vec<u8> = data[data.len() - 6..].to_vec();
data.truncate(data.len() - 6);
while data.len() >= 6 {
mainblock = mainblock
.iter()
.zip(data[data.len() - 6..].iter())
.map(|(&x1, &x2)| ((x1.rotate_right(x2.into())) ^ (x2.rotate_right(x1.into()))))
.collect();
data.truncate(data.len() - 6);
}
return mainblock;
}
fn format_hash(data: Vec<u8>) -> String {
let mut outstr = String::new();
for i in data.iter().enumerate() {
match i.0 + 1 == 2 || i.0 + 1 == 4 {
true => outstr = format!("{outstr}{:02X}-",i.1),
false => outstr = format!("{outstr}{:02X}",i.1),
}
}
return outstr;
}
pub fn hash (input: Vec<u8>) -> String {
let hashinput = Vec::<u8>::from(input);
return run_hash(hashinput);
}
pub fn generate_salted_input (input: Vec<u8>) -> Vec<u8> {
let mut input = Vec::<u8>::from(input);
let salt: Vec<u8> = input.iter().zip(input.iter().rev()).map(|(x1, x2)| (x1 | x2) ^ (x1 & x2)).collect();
input.append(&mut salt.clone());
input
}
pub fn salt_then_hash(input: Vec<u8>) -> String {
let saltydata = generate_salted_input(input);
hash(saltydata)
}