Implement __SCOPE__ (#1845)

This commit is contained in:
Rangi
2025-10-04 16:41:21 -04:00
committed by GitHub
parent 13e85b5151
commit 7733ccdeb6
3 changed files with 51 additions and 0 deletions

View File

@@ -1729,6 +1729,7 @@ The following symbols are defined by the assembler:
.It Dv @ Ta Ic EQU Ta PC value (essentially, the current memory address)
.It Dv . Ta Ic EQUS Ta The current global label scope
.It Dv .. Ta Ic EQUS Ta The current local label scope
.It Dv __SCOPE__ Ta Ic EQUS Ta The innermost current label scope level (empty, ".", or "..")
.It Dv _RS Ta Ic = Ta _RS Counter
.It Dv _NARG Ta Ic EQU Ta Number of arguments passed to macro, updated by Ic SHIFT
.It Dv __ISO_8601_LOCAL__ Ta Ic EQUS Ta ISO 8601 timestamp (local)

View File

@@ -39,6 +39,7 @@ static Symbol const *localScope = nullptr; // Current section's local label sco
static Symbol *PCSymbol;
static Symbol *NARGSymbol;
static Symbol *SCOPESymbol;
static Symbol *globalScopeSymbol;
static Symbol *localScopeSymbol;
static Symbol *RSSymbol;
@@ -67,6 +68,19 @@ static int32_t NARGCallback() {
}
}
static std::shared_ptr<std::string> SCOPECallback() {
if (localScope) {
return std::make_shared<std::string>("..");
} else if (globalScope) {
return std::make_shared<std::string>(".");
} else {
if (!sect_GetSymbolSection()) {
error("`__SCOPE__` has no value outside of a section");
}
return std::make_shared<std::string>("");
}
}
static std::shared_ptr<std::string> globalScopeCallback() {
if (!globalScope) {
error("`.` has no value outside of a label scope");
@@ -296,6 +310,10 @@ Symbol *sym_FindScopedValidSymbol(std::string const &symName) {
if (sym == localScopeSymbol && !localScope) {
return nullptr;
}
// `__SCOPE__` has no value outside of a section
if (sym == SCOPESymbol && !sect_GetSymbolSection()) {
return nullptr;
}
return sym;
}
@@ -683,6 +701,11 @@ void sym_Init(time_t now) {
localScopeSymbol->data = localScopeCallback;
localScopeSymbol->isBuiltin = true;
SCOPESymbol = &createSymbol("__SCOPE__"s);
SCOPESymbol->type = SYM_EQUS;
SCOPESymbol->data = SCOPECallback;
SCOPESymbol->isBuiltin = true;
RSSymbol = sym_AddVar("_RS"s, 0);
RSSymbol->isBuiltin = true;

27
test/asm/scope-level.asm Normal file
View File

@@ -0,0 +1,27 @@
assert !def(__SCOPE__)
section "test", rom0
assert !def(.)
assert !def(..)
assert #__SCOPE__ === ""
Alpha.local1:
assert !def(.)
assert #.. === "Alpha.local1"
assert #__SCOPE__ === ".."
Beta:
assert #. === "Beta"
assert !def(..)
assert #__SCOPE__ === "."
Alpha.local2:
assert #. === "Beta"
assert #.. === "Alpha.local2"
assert #__SCOPE__ === ".."
.newLocal:
assert #. === "Beta"
assert #.. === "Beta.newLocal"
assert #__SCOPE__ === ".."