summary refs log tree commit diff
path: root/src/parser.rs
diff options
context:
space:
mode:
authorSophie Forrest <git@sophieforrest.com>2024-08-30 23:35:45 +1200
committerSophie Forrest <git@sophieforrest.com>2024-08-30 23:35:45 +1200
commit3c163eabc78ddbd26bb250ef5ad6da28cd61adc6 (patch)
tree58e17534e1db18813554d4fb6e67020f898b655d /src/parser.rs
parent17b78f8cb127817b93f7e6ced7e55d8748806a80 (diff)
feat: split engine into crates
Diffstat (limited to '')
-rw-r--r--crates/brainf_rs/src/parser.rs (renamed from src/parser.rs)39
1 files changed, 19 insertions, 20 deletions
diff --git a/src/parser.rs b/crates/brainf_rs/src/parser.rs
index e639516..c9b3246 100644
--- a/src/parser.rs
+++ b/crates/brainf_rs/src/parser.rs
@@ -1,11 +1,10 @@
 //! Parser implementation for Brainfuck. Parses operator codes into instruction
 //! sets.
 
+use brainf_lexer::Token;
 use miette::{Diagnostic, SourceSpan};
 use thiserror::Error;
 
-use crate::lexer::OperatorCode;
-
 /// Parsed instructions for Brainfuck.
 #[derive(Clone, Debug)]
 pub enum Instruction {
@@ -102,49 +101,49 @@ pub enum Error {
 /// This function will return an error if a loop is encountered with no
 /// beginning, a loop is encountered with no ending, or if the parser attempts
 /// to slice out of bounds.
-pub fn parse(src: &str, operator_codes: &[OperatorCode]) -> Result<Vec<Instruction>, Error> {
+pub fn parse(src: &str, tokens: &[Token]) -> Result<Vec<Instruction>, Error> {
 	let mut program: Vec<Instruction> = Vec::new();
 	let mut loop_stack: i32 = 0;
 	let mut loop_start = 0;
-	let mut loop_source_offset: usize = 0;
+	let mut loop_span: (usize, usize) = (0, 0);
 
-	operator_codes
+	tokens
 		.iter()
 		.enumerate()
 		.try_for_each(|(i, operator_code)| -> Result<(), Error> {
 			match (loop_stack, *operator_code) {
-				(0i32, OperatorCode::StartLoop { offset }) => {
+				(0i32, Token::StartLoop(span)) => {
 					loop_start = i;
-					loop_source_offset = offset;
+					loop_span = span;
 					loop_stack += 1i32;
 				}
 				(0i32, _) => {
 					if let Some(instruction) = match *operator_code {
-						OperatorCode::IncrementPointer => Some(Instruction::IncrementPointer),
-						OperatorCode::DecrementPointer => Some(Instruction::DecrementPointer),
-						OperatorCode::IncrementByte => Some(Instruction::IncrementByte),
-						OperatorCode::DecrementByte => Some(Instruction::DecrementByte),
-						OperatorCode::OutputByte => Some(Instruction::OutputByte),
-						OperatorCode::InputByte => Some(Instruction::InputByte),
-						OperatorCode::EndLoop { offset } => {
+						Token::IncrementPointer => Some(Instruction::IncrementPointer),
+						Token::DecrementPointer => Some(Instruction::DecrementPointer),
+						Token::IncrementByte => Some(Instruction::IncrementByte),
+						Token::DecrementByte => Some(Instruction::DecrementByte),
+						Token::OutputByte => Some(Instruction::OutputByte),
+						Token::InputByte => Some(Instruction::InputByte),
+						Token::EndLoop(span) => {
 							return Err(Error::LoopWithNoBeginning {
 								input: src.to_owned(),
-								loop_src: (offset, 1).into(),
+								loop_src: span.into(),
 							})
 						}
 						// We don't care about this variant as it is handled in a subsequent arm
-						OperatorCode::StartLoop { .. } => None,
+						Token::StartLoop { .. } => None,
 					} {
 						program.push(instruction);
 					}
 				}
-				(_, OperatorCode::StartLoop { .. }) => loop_stack += 1i32,
-				(_, OperatorCode::EndLoop { .. }) => {
+				(_, Token::StartLoop { .. }) => loop_stack += 1i32,
+				(_, Token::EndLoop { .. }) => {
 					loop_stack -= 1i32;
 					if loop_stack == 0i32 {
 						let loop_program = parse(
 							src,
-							match operator_codes.get(loop_start + 1..i) {
+							match tokens.get(loop_start + 1..i) {
 								Some(value) => value,
 								None => return Err(Error::SliceOutOfBounds(loop_start + 1..i)),
 							},
@@ -164,7 +163,7 @@ pub fn parse(src: &str, operator_codes: &[OperatorCode]) -> Result<Vec<Instructi
 	} else {
 		Err(Error::LoopWithNoEnding {
 			input: src.to_owned(),
-			loop_src: (loop_source_offset, 1).into(),
+			loop_src: loop_span.into(),
 		})
 	}
 }