From 68e4e93e72e0047d5bd01af5072363c2797721dc Mon Sep 17 00:00:00 2001 From: Sebastian Tobie Date: Tue, 17 Dec 2024 13:38:02 +0100 Subject: [PATCH] incomplete solution for day 17 --- days/2024/17.rs | 159 ++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 159 insertions(+) create mode 100644 days/2024/17.rs diff --git a/days/2024/17.rs b/days/2024/17.rs new file mode 100644 index 0000000..7260127 --- /dev/null +++ b/days/2024/17.rs @@ -0,0 +1,159 @@ +use advent_of_code::strings::{convert_to_array, parsenumber}; +#[allow(unused_imports)] +use advent_of_code_macros::{include_data, include_example}; +use log::debug; +use thousands::Separable; + +include_data!(DATA 2024 17); + +const ADV: u64 = 0; +const BXL: u64 = 1; +const BST: u64 = 2; +const JNZ: u64 = 3; +const BXC: u64 = 4; +const OUT: u64 = 5; +const BDV: u64 = 6; +const CDV: u64 = 7; + +const BASE: u64 = 2; + +#[derive(Debug, Clone)] +struct GenericCPU { + a: u64, + b: u64, + c: u64, + pos: usize, + ops: Vec, + output: Vec, +} + +impl GenericCPU { + fn generic_process(&mut self) { + let mut opcode; + let mut operand; + loop { + opcode = match self.ops.get(self.pos) { + None => break, + Some(x) => *x, + }; + operand = *self.ops.get(self.pos + 1).unwrap(); + match opcode { + ADV => { + debug!("truncating A({}) >> {} = {}", self.a, self.comboop(operand), self.a >> self.comboop(operand)); + self.a >>= self.comboop(operand); + }, + BXL => { + debug!("XOR B({}) with {} = {}", self.b, operand, self.b ^ operand); + self.b ^= operand; + }, + BST => { + self.b = self.comboop(operand) % 8; + debug!("Setting B to comboop({}) = ({})", operand, self.b) + }, + JNZ => { + if self.a != 0 { + debug!("Jumping to {}", operand); + self.pos = operand as usize; + continue; + } + debug!("Do nothing"); + }, + BXC => { + debug!("XORing B and C"); + self.b ^= self.c; + }, + OUT => { + debug!("printing {} % 8 = {}", self.comboop(operand), self.comboop(operand) % 8); + self.output.push(self.comboop(operand) % 8); + }, + BDV => { + debug!("truncating A({}) >> {} = B({})", self.a, self.comboop(operand), self.a >> self.comboop(operand)); + self.b = self.a >> self.comboop(operand); + }, + CDV => { + debug!("truncating A({}) >> {} = C({})", self.a, self.comboop(operand), self.a >> self.comboop(operand)); + self.c = self.a >> self.comboop(operand); + }, + x => { + debug!("opcode {x} unimplemented"); + break; + }, + } + self.pos += 2; + } + } + fn comboop(&self, op: u64) -> u64 { + match op { + 0..=3 => op, + 4 => self.a, + 5 => self.b, + 6 => self.c, + 7 => unimplemented!(), + _ => unreachable!(), + } + } +} + +fn get_content(i: &str) -> String { + if i == "" { + i.to_string() + } else { + i.split_once(':').unwrap().1.trim().to_string() + } +} + +fn round(n: u64) -> u64 { + let mut b = n % 8; + b ^= 6; + b ^= n >> b; + b ^= 7; + b % 8 +} + +fn main() { + let data = convert_to_array::<_, _, '\n'>(DATA, get_content); + let mut mem = GenericCPU { + a: parsenumber(&data[0]), + b: parsenumber(&data[1]), + c: parsenumber(&data[2]), + pos: 0, + ops: data[4].split(',').map(|op| parsenumber(op)).collect(), + output: Vec::new(), + }; + let mut n = mem.a; + while n > 0 { + println!("Round: {}", round(n)); + n >>= 3; + } + mem.generic_process(); + let output = mem.output.iter().map(|x| x.to_string()).collect::>().join(","); + println!("output: {}", output); + let mut n: u64 = 0; + 'numloop: for (pos, num) in mem.ops.iter().cloned().enumerate().map(|(x, y)| (x * 3, y)) { + for i in 0..8 { + if round(i) == num { + println!("Adding {:>18}, the source of {}", i, num); + n += i << pos; + continue 'numloop; + } + } + println!("Not Possible to find equivalent of {}", num); + } + println!("Testing {}", n); + mem.a = n; + mem.b = 0; + mem.c = 0; + mem.pos = 0; + mem.output.clear(); + mem.generic_process(); + if mem.output == mem.ops { + println!("A: {n}") + } else { + println!("{:?}\n{:?}", mem.ops, mem.output); + } +} + +#[cfg(test)] +mod test { + use super::*; +}