Implement EXPORT DEF to define and export symbols (#1422)

This commit is contained in:
Sylvie
2024-07-25 17:40:58 -04:00
committed by GitHub
parent 13a8895fca
commit 92abe24894
5 changed files with 103 additions and 20 deletions

View File

@@ -1107,6 +1107,17 @@ DEF y *= 2 ; y == 20
DEF y >>= 1 ; y == 10
DEF x ^= y ; x == 1
.Ed
.Pp
Declaring a variable with
.Ic EXPORT DEF
or
.Ic EXPORT REDEF
will define and
.Ic EXPORT
it at the same time.
(See
.Sx Exporting and importing symbols
below).
.Ss Numeric constants
.Ic EQU
is used to define immutable numeric symbols.
@@ -1143,6 +1154,17 @@ ENDM
assert NUM_ITEMS == 4
assert ITEM_04 == 16
.Ed
.Pp
Declaring a numeric constant with
.Ic EXPORT DEF
or
.Ic EXPORT REDEF
will define and
.Ic EXPORT
it at the same time.
(See
.Sx Exporting and importing symbols
below).
.Ss Offset constants
The RS group of commands is a handy way of defining structure offsets:
.Bd -literal -offset indent
@@ -1180,6 +1202,15 @@ is omitted, it's assumed to be 1.
Note that colons
.Ql \&:
following the name are not allowed.
.Pp
Declaring an offset constant with
.Ic EXPORT DEF
will define and
.Ic EXPORT
it at the same time.
(See
.Sx Exporting and importing symbols
below).
.Ss String constants
.Ic EQUS
is used to define string constant symbols.
@@ -1218,8 +1249,6 @@ Note that colons
.Ql \&:
following the name are not allowed.
.Pp
String constants can't be exported or imported.
.Pp
String constants, like numeric constants, cannot be redefined.
However, the
.Ic REDEF
@@ -1232,6 +1261,8 @@ REDEF s EQUS "{s}world!"
PRINTLN "{s}\en"
.Ed
.Pp
String constants can't be exported or imported.
.Pp
.Sy Important note :
When a string constant is expanded, its expansion may contain another string constant, which will be expanded as well.
If this creates an infinite loop,

View File

@@ -196,6 +196,15 @@
%token <std::string> ANON "anonymous label"
%type <std::string> def_id
%type <std::string> redef_id
%type <std::string> def_numeric
%type <std::string> def_equ
%type <std::string> redef_equ
%type <std::string> def_set
%type <std::string> def_rb
%type <std::string> def_rw
%type <std::string> def_rl
%type <std::string> def_equs
%type <std::string> redef_equs
%type <std::string> scoped_id
%type <std::string> scoped_anon_id
%token POP_EQU "EQU"
@@ -529,6 +538,7 @@ directive:
| print
| println
| export
| export_def
| db
| dw
| dl
@@ -551,12 +561,7 @@ directive:
| fail
| warn
| assert
| def_equ
| redef_equ
| def_set
| def_rb
| def_rw
| def_rl
| def_numeric
| def_equs
| redef_equs
| purge
@@ -570,6 +575,15 @@ directive:
| align
;
def_numeric:
def_equ
| redef_equ
| def_set
| def_rb
| def_rw
| def_rl
;
trailing_comma: %empty | COMMA;
compound_eq:
@@ -931,64 +945,75 @@ dl:
def_equ:
def_id POP_EQU const {
sym_AddEqu($1, $3);
$$ = std::move($1);
sym_AddEqu($$, $3);
}
;
redef_equ:
redef_id POP_EQU const {
sym_RedefEqu($1, $3);
$$ = std::move($1);
sym_RedefEqu($$, $3);
}
;
def_set:
def_id POP_EQUAL const {
sym_AddVar($1, $3);
$$ = std::move($1);
sym_AddVar($$, $3);
}
| redef_id POP_EQUAL const {
sym_AddVar($1, $3);
$$ = std::move($1);
sym_AddVar($$, $3);
}
| def_id compound_eq const {
compoundAssignment($1, $2, $3);
$$ = std::move($1);
compoundAssignment($$, $2, $3);
}
| redef_id compound_eq const {
compoundAssignment($1, $2, $3);
$$ = std::move($1);
compoundAssignment($$, $2, $3);
}
;
def_rb:
def_id POP_RB rs_uconst {
$$ = std::move($1);
uint32_t rs = sym_GetRSValue();
sym_AddEqu($1, rs);
sym_AddEqu($$, rs);
sym_SetRSValue(rs + $3);
}
;
def_rw:
def_id POP_RW rs_uconst {
$$ = std::move($1);
uint32_t rs = sym_GetRSValue();
sym_AddEqu($1, rs);
sym_AddEqu($$, rs);
sym_SetRSValue(rs + 2 * $3);
}
;
def_rl:
def_id Z80_RL rs_uconst {
$$ = std::move($1);
uint32_t rs = sym_GetRSValue();
sym_AddEqu($1, rs);
sym_AddEqu($$, rs);
sym_SetRSValue(rs + 4 * $3);
}
;
def_equs:
def_id POP_EQUS string {
sym_AddString($1, std::make_shared<std::string>($3));
$$ = std::move($1);
sym_AddString($$, std::make_shared<std::string>($3));
}
;
redef_equs:
redef_id POP_EQUS string {
sym_RedefString($1, std::make_shared<std::string>($3));
$$ = std::move($1);
sym_RedefString($$, std::make_shared<std::string>($3));
}
;
@@ -1025,6 +1050,12 @@ export_list_entry:
}
;
export_def:
POP_EXPORT def_numeric {
sym_Export($2);
}
;
include:
label POP_INCLUDE string endofline {
fstk_RunInclude($3, false);

View File

@@ -3,7 +3,7 @@ error: anon-label-bad.asm(2):
error: anon-label-bad.asm(6):
Reference to anonymous label 2 before, when only 1 has been created so far
error: anon-label-bad.asm(9):
syntax error, unexpected anonymous label, expecting label or identifier or local identifier
syntax error, unexpected anonymous label
error: anon-label-bad.asm(10):
syntax error, unexpected anonymous label, expecting label or identifier or local identifier
error: anon-label-bad.asm(22):

18
test/asm/export.asm Normal file
View File

@@ -0,0 +1,18 @@
EXPORT undefined
DEF equ_sym EQU 1
DEF var_sym = 2
EXPORT equ_sym, var_sym
EXPORT DEF constant EQU 42
EXPORT DEF variable = 1337
EXPORT DEF byte RB
EXPORT DEF word RW
EXPORT DEF long RL
EXPORT REDEF constant EQU 69
EXPORT REDEF variable = 1234
; String constants can't be exported or imported.
DEF equs_sym EQUS "hello"
EXPORT equs_sym ; exports undefined symbol `hello` due to EQUS expansion
EXPORT DEF string EQUS "goodbye" ; invalid syntax

3
test/asm/export.err Normal file
View File

@@ -0,0 +1,3 @@
error: export.asm(18):
syntax error, unexpected EQUS
error: Assembly aborted (1 error)!