readIdentifier does not process characters that get truncated

Previously a '.' could be past the truncation limit but still
cause the identifier to be marked as local, violating an
assertion in `sym_AddLocalLabel`.

Fixes #832
This commit is contained in:
Rangi
2021-04-16 21:15:01 -04:00
parent e78a1d5bfd
commit c755fa3469
4 changed files with 36 additions and 18 deletions

View File

@@ -1210,6 +1210,11 @@ static bool startsIdentifier(int c)
return (c <= 'Z' && c >= 'A') || (c <= 'z' && c >= 'a') || c == '.' || c == '_';
}
static bool continuesIdentifier(int c)
{
return startsIdentifier(c) || (c <= '9' && c >= '0') || c == '#' || c == '@';
}
static int readIdentifier(char firstChar)
{
dbgPrint("Reading identifier or keyword\n");
@@ -1217,30 +1222,24 @@ static int readIdentifier(char firstChar)
yylval.tzSym[0] = firstChar;
uint16_t nodeID = keywordDict[0].children[dictIndex(firstChar)];
int tokenType = firstChar == '.' ? T_LOCAL_ID : T_ID;
size_t i;
size_t i = 1;
for (i = 1; ; i++) {
int c = peek();
/* If that char isn't in the symbol charset, end */
if ((c > '9' || c < '0')
&& (c > 'Z' || c < 'A')
&& (c > 'z' || c < 'a')
&& c != '#' && c != '.' && c != '@' && c != '_')
break;
/* Continue reading while the char is in the symbol charset */
for (int c = peek(); continuesIdentifier(c); i++, c = peek()) {
shiftChar();
/* Write the char to the identifier's name */
if (i < sizeof(yylval.tzSym) - 1)
if (i < sizeof(yylval.tzSym) - 1) {
/* Write the char to the identifier's name */
yylval.tzSym[i] = c;
/* If the char was a dot, mark the identifier as local */
if (c == '.')
tokenType = T_LOCAL_ID;
/* If the char was a dot, mark the identifier as local */
if (c == '.')
tokenType = T_LOCAL_ID;
/* Attempt to traverse the tree to check for a keyword */
if (nodeID) /* Do nothing if matching already failed */
nodeID = keywordDict[nodeID].children[dictIndex(c)];
/* Attempt to traverse the tree to check for a keyword */
if (nodeID) /* Do nothing if matching already failed */
nodeID = keywordDict[nodeID].children[dictIndex(c)];
}
}
if (i > sizeof(yylval.tzSym) - 1) {

View File

@@ -0,0 +1,11 @@
SECTION "Test", ROM0
MACRO a000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001
println "truncated :("
ENDM
a012:
a012.local
a0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000012:
a0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000012.local

View File

@@ -0,0 +1,7 @@
warning: local-truncated.asm(10): [-Wlong-string]
Symbol name too long, got truncated
ERROR: local-truncated.asm(10):
'a000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001' already defined at local-truncated.asm(3)
warning: local-truncated.asm(11): [-Wlong-string]
Symbol name too long, got truncated
error: Assembly aborted (1 error)!

View File

@@ -0,0 +1 @@
truncated :(