From eb32be33c8e52c70f3fb4067a3035f7c52122594 Mon Sep 17 00:00:00 2001 From: jn Date: Wed, 1 Feb 2023 19:56:22 +0100 Subject: [PATCH] Add data.strz directive for zero-terminated strings A common pattern in fox32 software is this: data.str "Some string here" data.8 0 i.e. a zero- or NUL-terminated string. To make such strings easier to write, introduce a new directive data.strz, which adds the zero byte automatically: data.strz "Some string here" --- src/fox32.pest | 2 ++ src/main.rs | 10 ++++++++++ 2 files changed, 12 insertions(+) diff --git a/src/fox32.pest b/src/fox32.pest index bca7355..1d30191 100644 --- a/src/fox32.pest +++ b/src/fox32.pest @@ -19,12 +19,14 @@ data = { data_half | data_word | data_str | + data_strz | data_fill } data_byte = { "data.8" ~ operand_value } data_half = { "data.16" ~ operand_value } data_word = { "data.32" ~ operand_value } data_str = { "data.str" ~ immediate_str } +data_strz = { "data.strz" ~ immediate_str } data_fill = { "data.fill" ~ operand_value ~ "," ~ operand_value } constant = { "const" ~ constant_name ~ operand_value } diff --git a/src/main.rs b/src/main.rs index 990b3c7..7e0ced3 100644 --- a/src/main.rs +++ b/src/main.rs @@ -291,6 +291,7 @@ enum AstNode { DataHalf(u16), DataWord(u32), DataStr(String), + DataStrZero(String), DataFill { value: u8, size: u32, @@ -630,6 +631,10 @@ fn parse_data(pair: pest::iterators::Pair) -> AstNode { let string = pair.into_inner().next().unwrap().into_inner().next().unwrap().as_str(); AstNode::DataStr(string.to_string()) }, + Rule::data_strz => { + let string = pair.into_inner().next().unwrap().into_inner().next().unwrap().as_str(); + AstNode::DataStrZero(string.to_string()) + }, Rule::data_fill => { let value = { let ast = parse_operand(pair.clone().into_inner().next().unwrap(), false); @@ -982,6 +987,11 @@ fn assemble_node(node: AstNode) -> AssembledInstruction { AstNode::DataStr(string) => { return string.as_bytes().into(); }, + AstNode::DataStrZero(string) => { + let mut bytes: Vec = string.as_bytes().into(); + bytes.push(0); + return bytes.into(); + }, AstNode::LabelOperand {name, size, is_relative} => { // label is used on its own, not as an operand: // LabelOperand was previously only checked as part of operands