Implement set 1 challenge 3.

This commit is contained in:
2022-03-25 20:23:48 -04:00
parent c33686220d
commit 495f305c11

View File

@@ -8,36 +8,12 @@ pub struct Base64Bytes(Vec<u8>);
impl std::fmt::Display for Base64Bytes {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
let Base64Bytes(digits) = self;
let mut r: Vec<u8> = digits
.iter()
.map(|d| match d {
0..=25 => *d + ('A' as u8),
26..=51 => *d - 26 + ('a' as u8),
52..=61 => *d - 52 + ('0' as u8),
62 => '+' as u8,
63 => '/' as u8,
_ => panic!("Unexpected base64 digit '{}'", d),
})
.collect();
// Handle padding
let pad = '=' as u8;
match r.len() % 4 {
0 => (),
2 => {
r.push(pad);
r.push(pad);
}
3 => r.push(pad),
_ => (),
}
write!(f, "Base64({})", str::from_utf8(r.as_slice()).unwrap())
write!(f, "Base64({})", self.to_base64_string())
}
}
impl Base64Bytes {
pub fn to_string(&self) -> String {
pub fn to_base64_string(&self) -> String {
let Base64Bytes(digits) = self;
let mut r: Vec<u8> = digits
.iter()
@@ -106,6 +82,7 @@ impl HexBytes {
}
}
#[allow(dead_code)]
pub fn to_utf8_string(&self) -> String {
let HexBytes(v) = self;
String::from(str::from_utf8(&v).unwrap())
@@ -120,6 +97,33 @@ impl HexBytes {
r
}
fn is_ascii(&self) -> bool {
let HexBytes(v) = self;
for &c in v.iter() {
if c < 32 || c > 127 {
return false;
}
}
true
}
fn ascii_score(&self) -> u32 {
let HexBytes(v) = self;
let mut r = 0;
for &c in v.iter() {
match c {
32 => r += 2,
33..=64 => r += 1,
65..=90 => r += 3,
91..=96 => r += 1,
97..=122 => r += 3,
123..=127 => r += 1,
_ => (),
}
}
r
}
fn xor(HexBytes(a): &HexBytes, HexBytes(b): &HexBytes) -> HexBytes {
HexBytes(
Iterator::zip(a.iter(), b.iter())
@@ -127,14 +131,18 @@ impl HexBytes {
.collect(),
)
}
fn xor_byte(HexBytes(a): &HexBytes, byte: u8) -> HexBytes {
HexBytes(a.iter().map(|e| e ^ byte).collect())
}
}
pub fn challenge1() {
let input = HexBytes::from_str("49276d206b696c6c696e6720796f757220627261696e206c696b65206120706f69736f6e6f7573206d757368726f6f6d");
let expected = String::from("SSdtIGtpbGxpbmcgeW91ciBicmFpbiBsaWtlIGEgcG9pc29ub3VzIG11c2hyb29t");
let result = input.to_base64();
if result.to_string() == expected {
println!("[okay] Challenge 1: {}", result);
let a = HexBytes::from_str("49276d206b696c6c696e6720796f757220627261696e206c696b65206120706f69736f6e6f7573206d757368726f6f6d");
let e = String::from("SSdtIGtpbGxpbmcgeW91ciBicmFpbiBsaWtlIGEgcG9pc29ub3VzIG11c2hyb29t");
let r = a.to_base64();
if r.to_base64_string() == e {
println!("[okay] Challenge 1: {}", r);
} else {
println!("[fail] Challenge 1")
}
@@ -152,4 +160,19 @@ pub fn challenge2() {
}
}
pub fn challenge3() {}
pub fn challenge3() {
let a =
HexBytes::from_str("1b37373331363f78151b7f2b783431333d78397828372d363c78373e783a393b3736");
let mut h: Vec<HexBytes> = (0..=255).map(|i| HexBytes::xor_byte(&a, i)).collect();
h.sort_by(|a, b| a.ascii_score().partial_cmp(&b.ascii_score()).unwrap());
let h: Vec<HexBytes> = h.into_iter().filter(|b| b.is_ascii()).collect();
let r = h[h.len() - 1].to_utf8_string();
let e = String::from("Cooking MC's like a pound of bacon");
if r == e {
println!("[okay] Challenge 3: {}", r);
} else {
println!("[fail] Challenge 3: {}", r);
}
}