diff options
| author | Matthew Hall <hallmatthew314@gmail.com> | 2022-09-07 00:05:23 +1200 |
|---|---|---|
| committer | Matthew Hall <hallmatthew314@gmail.com> | 2022-09-07 00:05:23 +1200 |
| commit | 97e3b4a9d7e995848341e53b2c002930c85d5c47 (patch) | |
| tree | 45299ac50115bc3cc87f546cbbc8ba7519813a61 | |
| parent | b5aecfbd9d32bf894ab82d7b594f91a5f59acb2a (diff) | |
Parser + boilerplate for Among Us
| -rw-r--r-- | src/among_us/among_us.cr | 29 | ||||
| -rw-r--r-- | src/among_us/parser.cr | 48 | ||||
| -rw-r--r-- | src/among_us/program.cr | 34 | ||||
| -rw-r--r-- | src/flint.cr | 11 | ||||
| -rw-r--r-- | test_programs/among_us/cat.sus | 6 | ||||
| -rw-r--r-- | test_programs/among_us/hello_world.sus | 66 | ||||
| -rw-r--r-- | test_programs/among_us/no_color_no_sus.sus | 1 | ||||
| -rw-r--r-- | test_programs/among_us/no_color_with_sus.sus | 1 | ||||
| -rw-r--r-- | test_programs/among_us/truth_machine.sus | 23 |
9 files changed, 215 insertions, 4 deletions
diff --git a/src/among_us/among_us.cr b/src/among_us/among_us.cr new file mode 100644 index 0000000..4b4f3b8 --- /dev/null +++ b/src/among_us/among_us.cr @@ -0,0 +1,29 @@ +module AmongUs + + enum Command + SUS + VENTED + SUSSY + ELECTRICAL + WHO + WHERE + end + + enum Color + RED + BLUE + PURPLE + GREEN + YELLOW + CYAN + BLACK + WHITE + BROWN + LIME + PINK + ORANGE + end + + alias Instruction = Command | Color +end + diff --git a/src/among_us/parser.cr b/src/among_us/parser.cr new file mode 100644 index 0000000..84894bd --- /dev/null +++ b/src/among_us/parser.cr @@ -0,0 +1,48 @@ +require "../util.cr" +require "./among_us.cr" + +struct AmongUs::Parser + def initialize(code_io : IO) + @raw_code = code_io.gets_to_end + code_io.close + end + + def parse : Array(Instruction) + tokens = @raw_code.split + instructions = [] of Instruction + color_seen = false + sus_safe = false + + tokens.each do |token| + case token.upcase + when "WHO?" + instructions << Command::WHO + when "WHERE?" + instructions << Command::WHERE + else + i = parse_instruction(token) + if i.nil? + raise Util::ParserError.new("Failed to parse command/color '#{token}'") + end + instructions << i + end + + color_seen = true if instructions[-1].is_a?(Color) + if instructions[-1] == Command::SUS && !sus_safe + unless color_seen + raise Util::ParserError.new("Provided program uses SUS command, but no colors are provided before first SUS") + end + sus_safe = true + end + end + + return instructions + end + + private def parse_instruction(str : String) : Instruction? + i = Command.parse?(str) + return i unless i.nil? + Color.parse?(str) + end +end + diff --git a/src/among_us/program.cr b/src/among_us/program.cr new file mode 100644 index 0000000..a54f24b --- /dev/null +++ b/src/among_us/program.cr @@ -0,0 +1,34 @@ +require "big" + +struct AmongUs::Program < Flint::Program + def interpret : Nil + code = Parser.new(@source_io).parse + jumps = find_jumps(code) + + stack = [] of BigInt + acc1 = BigInt.new + acc2 = BigInt.new + color = code.find &.is_a?(Color) + + puts code + puts jumps + end + + private def find_jumps(code : Array(Instruction)) : Hash(Int32, Int32) + jumps = {} of Int32 => Int32 + stack = [] of Int32 + + code.each_index do |i| + case code[i] + when Command::WHO + stack << i + when Command::WHERE + jumps[i] = stack.pop + jumps[jumps[i]] = i + end + end + + return jumps + end +end + diff --git a/src/flint.cr b/src/flint.cr index 6d68305..02fdd85 100644 --- a/src/flint.cr +++ b/src/flint.cr @@ -4,6 +4,7 @@ require "option_parser" require "./util.cr" require "./program.cr" +require "./among_us/*" require "./brainfuck/*" require "./thue/*" @@ -11,6 +12,7 @@ module Flint VERSION = "0.1.1" enum Language + AmongUs Brainfuck Thue end @@ -71,10 +73,9 @@ module Flint crash("ERROR: No language chosen", parser) if _args.size == 0 crash("ERROR: No source file chosen", parser) if _args.size == 1 && !read_stdin source_file = _args[1] unless read_stdin - language = case _args[0].downcase - when "brainfuck" then Language::Brainfuck - when "thue" then Language::Thue - else crash("ERROR: Unknown language specified: '#{_args[0]}'\nUser the '--supported-languages' flag to see whatlanguages are valid.", parser) + language = Language.parse?(_args[0]) + if language.nil? + crash("ERROR: Unknown language specified: '#{_args[0]}'\nUser the '--supported-languages' flag to see whatlanguages are valid.", parser) end end end @@ -90,6 +91,8 @@ module Flint end program = case language.not_nil! + in Language::AmongUs + AmongUs::Program.new(source_io) in Language::Brainfuck begin m_str = language_options[:memory_size]? diff --git a/test_programs/among_us/cat.sus b/test_programs/among_us/cat.sus new file mode 100644 index 0000000..45f3406 --- /dev/null +++ b/test_programs/among_us/cat.sus @@ -0,0 +1,6 @@ +RED SUS +BLUE SUS +WHO? +YELLOW SUS +GREEN SUS +WHERE? diff --git a/test_programs/among_us/hello_world.sus b/test_programs/among_us/hello_world.sus new file mode 100644 index 0000000..1bbc3aa --- /dev/null +++ b/test_programs/among_us/hello_world.sus @@ -0,0 +1,66 @@ +ORANGE SUS +BLUE SUS + +ORANGE SUS ORANGE SUS +RED SUS RED SUS RED SUS +BLUE SUS + +WHITE SUS WHITE SUS WHITE SUS +ORANGE SUS ORANGE SUS ORANGE SUS +ORANGE SUS ORANGE SUS ORANGE SUS ORANGE SUS +BLUE SUS + +ORANGE SUS +WHITE SUS WHITE SUS +BLUE SUS + +RED SUS RED SUS RED SUS +RED SUS RED SUS RED SUS +BLUE SUS + +WHITE SUS WHITE SUS WHITE SUS +BLUE SUS + +ORANGE SUS +WHITE SUS WHITE SUS +BLUE SUS + +PINK SUS +ORANGE SUS ORANGE SUS ORANGE SUS +RED SUS RED SUS +BLUE SUS + +ORANGE SUS +RED SUS RED SUS +BLUE SUS + +ORANGE SUS ORANGE SUS ORANGE SUS +ORANGE SUS ORANGE SUS ORANGE SUS ORANGE SUS +WHITE SUS WHITE SUS WHITE SUS +BLUE SUS + +WHITE SUS WHITE SUS WHITE SUS +BLUE SUS +BLUE SUS + +WHITE SUS WHITE SUS WHITE SUS +WHITE SUS WHITE SUS WHITE SUS WHITE SUS +BLUE SUS + +PINK SUS +ORANGE SUS ORANGE SUS ORANGE SUS +ORANGE SUS ORANGE SUS ORANGE SUS ORANGE SUS +RED SUS RED SUS +BLUE SUS + +PINK SUS +VENTED VENTED +SUSSY SUSSY SUSSY +SUSSY SUSSY SUSSY +BLUE SUS +WHO? +PURPLE SUS +GREEN SUS +PURPLE SUS +SUSSY BLUE SUS +WHERE? diff --git a/test_programs/among_us/no_color_no_sus.sus b/test_programs/among_us/no_color_no_sus.sus new file mode 100644 index 0000000..c64a84e --- /dev/null +++ b/test_programs/among_us/no_color_no_sus.sus @@ -0,0 +1 @@ +VENTED VENTED SUSSY ELECTRICAL diff --git a/test_programs/among_us/no_color_with_sus.sus b/test_programs/among_us/no_color_with_sus.sus new file mode 100644 index 0000000..aa221e3 --- /dev/null +++ b/test_programs/among_us/no_color_with_sus.sus @@ -0,0 +1 @@ +VENTED VENTED SUS ELECTRICAL diff --git a/test_programs/among_us/truth_machine.sus b/test_programs/among_us/truth_machine.sus new file mode 100644 index 0000000..c4371a0 --- /dev/null +++ b/test_programs/among_us/truth_machine.sus @@ -0,0 +1,23 @@ +YELLOW SUS +GREEN SUS +BROWN SUS +PURPLE SUS +WHITE SUS +SUS SUS SUS SUS SUS SUS SUS SUS +SUS SUS SUS SUS SUS SUS SUS SUS +SUS SUS SUS SUS SUS SUS SUS SUS +SUS SUS SUS SUS SUS SUS SUS SUS +SUS SUS SUS SUS SUS SUS SUS SUS SUS +SUS SUS SUS SUS SUS SUS +BLUE SUS +WHO? +ORANGE SUS SUS SUS SUS +RED SUS SUS SUS SUS SUS SUS SUS SUS +BLUE SUS +PINK SUS +BLUE SUS +WHERE? +PURPLE SUS +WHO? +GREEN SUS +WHERE? |
