Skip to content

Instantly share code, notes, and snippets.

@rhowe
Created December 7, 2019 07:38
Show Gist options
  • Save rhowe/2da6b302ffa9496a467442cd40f623e0 to your computer and use it in GitHub Desktop.
Save rhowe/2da6b302ffa9496a467442cd40f623e0 to your computer and use it in GitHub Desktop.
AOC2019day7part1
#!/bin/bash
set -eu
getval() {
case $1 in
0) echo "${ram[$2]}" ;;
1) echo "$2" ;;
esac
}
jmpt() {
local addrmode=$1
local arg=$(getval "${addrmode:0:1}" "$2")
local dest=$(getval "${addrmode:1:1}" "$3")
if [ "$arg" -ne 0 ]; then
pc=$dest
else
pc=$((pc+2))
fi
}
jmpf() {
local addrmode=$1
local arg=$(getval "${addrmode:0:1}" "$2")
local dest=$(getval "${addrmode:1:1}" "$3")
if [ "$arg" -eq 0 ]; then
pc=$dest
else
pc=$((pc+2))
fi
}
add() {
local addrmode=$1
local src1=$(getval "${addrmode:0:1}" "$2")
local src2=$(getval "${addrmode:1:1}" "$3")
local dest=$4
ram[$dest]=$((src1 + src2))
pc=$((pc+3))
}
mul() {
local addrmode=$1
local src1=$(getval "${addrmode:0:1}" "$2")
local src2=$(getval "${addrmode:1:1}" "$3")
local dest=$4
ram[$dest]=$((src1 * src2))
pc=$((pc+3))
}
cmpl() {
local addrmode=$1
local src1=$(getval "${addrmode:0:1}" "$2")
local src2=$(getval "${addrmode:1:1}" "$3")
local dest=$4
if [ "$src1" -lt "$src2" ]; then
ans=1
else
ans=0
fi
ram[$dest]=$ans
pc=$((pc+3))
}
cmpe() {
local addrmode=$1
local src1=$(getval "${addrmode:0:1}" "$2")
local src2=$(getval "${addrmode:1:1}" "$3")
local dest=$4
if [ "$src1" -eq "$src2" ]; then
local ans=1
else
local ans=0
fi
ram[$dest]=$ans
pc=$((pc+3))
}
inb() {
local addrmode=$1
local dest=$2
ram[$dest]=${inputs[0]}
inputs="${inputs[@]:1}"
pc=$((pc+1))
}
outb() {
local addrmode=$1
local src=$(getval "${addrmode:0:1}" "$2")
echo "$src"
pc=$((pc+1))
}
gdb() {
echo -ne "$pc"\\t >&2
seq 0 15 | xargs | tr \ \\t >&2
for addr in $(seq 0 16 "${#ram[@]}"); do
echo "$addr: ${ram[@]:$addr:16}" | tr \ \\t >&2
done
}
run() {
inputs=("$@")
[ -z "${DEBUG:-}" ] || echo "program start: ${inputs[@]}" >&2
pc=0
ram=("${program[@]}")
while true; do
local opcode=$(printf %04d "${ram[$pc]}")
local addrmode=${opcode: -3:1}${opcode: -4:1}
[ -z "${DEBUG:-}" ] || gdb
pc=$((pc+1))
case "${opcode: -2}" in
01) add "$addrmode" "${ram[@]:$pc:3}" ;;
02) mul "$addrmode" "${ram[@]:$pc:3}" ;;
03) inb "$addrmode" "${ram[@]:$pc:1}" ;;
04) outb "$addrmode" "${ram[@]:$pc:1}" ;;
05) jmpt "$addrmode" "${ram[@]:$pc:2}" ;;
06) jmpf "$addrmode" "${ram[@]:$pc:2}" ;;
07) cmpl "$addrmode" "${ram[@]:$pc:3}" ;;
08) cmpe "$addrmode" "${ram[@]:$pc:3}" ;;
99) break ;;
*)
echo "Unknown opcode $opcode at $pc" >&2
return 1
;;
esac
done
}
IFS=, read -r -a program < "$1"
highestoutput=0
for phases in {0,1,2,3,4},{0,1,2,3,4},{0,1,2,3,4},{0,1,2,3,4},{0,1,2,3,4}; do
IFS=, read -r -a phasearray <<<"$phases"
if [ "$(xargs -n1 echo <<<"${phasearray[@]}" | sort -u)" != "$(xargs -n1 echo <<<"${phasearray[@]}" | sort)" ]; then
continue
fi
acc=0
for phase in "${phasearray[@]}"; do
acc=$(run "$phase" "$acc")
done
if [ "$acc" -gt "$highestoutput" ]; then
highestoutput=$acc
fi
done
echo "$highestoutput"
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment