hare

[hare] The Hare programming language
git clone https://git.torresjrjr.com/hare.git
Log | Files | Refs | README | LICENSE

commit 0193a81d039770c7909c274d75471ac815cb8007
parent 73b846f9d8ba7eba10ae719afd1e2a68f00a7123
Author: Stacy Harper <contact@stacyharper.net>
Date:   Fri, 23 Dec 2022 15:50:08 +0100

Add @packed to lexers/parsers

Signed-off-by: Stacy Harper <contact@stacyharper.net>

Diffstat:
Mhare/ast/type.ha | 1+
Mhare/lex/token.ha | 2++
Mhare/parse/type.ha | 8+++++++-
Mhare/unparse/type.ha | 6+++++-
4 files changed, 15 insertions(+), 2 deletions(-)

diff --git a/hare/ast/type.ha b/hare/ast/type.ha @@ -108,6 +108,7 @@ export type struct_member = struct { // struct { ... } export type struct_type = struct { + packed: bool, members: []struct_member, }; diff --git a/hare/lex/token.ha b/hare/lex/token.ha @@ -14,6 +14,7 @@ export type ltok = enum uint { ATTR_INIT, ATTR_NORETURN, ATTR_OFFSET, + ATTR_PACKED, ATTR_SYMBOL, ATTR_TEST, ATTR_THREADLOCAL, @@ -163,6 +164,7 @@ const bmap: [_]str = [ "@init", "@noreturn", "@offset", + "@packed", "@symbol", "@test", "@threadlocal", diff --git a/hare/parse/type.ha b/hare/parse/type.ha @@ -236,6 +236,12 @@ fn fn_type(lexer: *lex::lexer) (ast::_type | error) = { fn struct_union_type(lexer: *lex::lexer) (ast::_type | error) = { let membs: []ast::struct_member = []; let kind = want(lexer, ltok::STRUCT, ltok::UNION)?; + let packed = false; + + if (kind.0 == ltok::STRUCT && try(lexer, ltok::ATTR_PACKED)? is lex::token) { + packed = true; + }; + want(lexer, ltok::LBRACE)?; for (true) { @@ -291,7 +297,7 @@ fn struct_union_type(lexer: *lex::lexer) (ast::_type | error) = { flags = ast::type_flags::NONE, repr = switch (kind.0) { case ltok::STRUCT => - yield ast::struct_type { members = membs, ...}; + yield ast::struct_type { members = membs, packed = packed, ...}; case ltok::UNION => yield membs: ast::union_type; case => abort(); diff --git a/hare/unparse/type.ha b/hare/unparse/type.ha @@ -161,7 +161,11 @@ fn struct_union_type( let z = 0z; let membs = match (t.repr) { case let st: ast::struct_type => - z += fmt::fprint(out, "struct {")?; + z += fmt::fprint(out, "struct ")?; + if (st.packed) { + z += fmt::fprint(out, "@packed ")?; + }; + z += fmt::fprint(out, "{")?; yield st.members: []ast::struct_member; case let ut: ast::union_type => z += fmt::fprint(out, "union {")?;