mirror of
https://github.com/gbdev/rgbds.git
synced 2025-11-20 18:22:07 +00:00
Allow underscores in numeric literals
Fixes #539 Changes \@'s output to start with "_u", not "_", so it will be valid within labels but not numerics
This commit is contained in:
@@ -999,16 +999,16 @@ static void readNumber(int radix, int32_t baseValue)
|
|||||||
{
|
{
|
||||||
uint32_t value = baseValue;
|
uint32_t value = baseValue;
|
||||||
|
|
||||||
for (;;) {
|
for (;; shiftChars(1)) {
|
||||||
int c = peek(0);
|
int c = peek(0);
|
||||||
|
|
||||||
if (c < '0' || c > '0' + radix - 1)
|
if (c == '_')
|
||||||
|
continue;
|
||||||
|
else if (c < '0' || c > '0' + radix - 1)
|
||||||
break;
|
break;
|
||||||
if (value > (UINT32_MAX - (c - '0')) / radix)
|
if (value > (UINT32_MAX - (c - '0')) / radix)
|
||||||
warning(WARNING_LARGE_CONSTANT, "Integer constant is too large\n");
|
warning(WARNING_LARGE_CONSTANT, "Integer constant is too large\n");
|
||||||
value = value * radix + (c - '0');
|
value = value * radix + (c - '0');
|
||||||
|
|
||||||
shiftChars(1);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
yylval.nConstValue = value;
|
yylval.nConstValue = value;
|
||||||
@@ -1019,17 +1019,19 @@ static void readFractionalPart(void)
|
|||||||
uint32_t value = 0, divisor = 1;
|
uint32_t value = 0, divisor = 1;
|
||||||
|
|
||||||
dbgPrint("Reading fractional part\n");
|
dbgPrint("Reading fractional part\n");
|
||||||
for (;;) {
|
for (;; shiftChars(1)) {
|
||||||
int c = peek(0);
|
int c = peek(0);
|
||||||
|
|
||||||
if (c < '0' || c > '9')
|
if (c == '_')
|
||||||
|
continue;
|
||||||
|
else if (c < '0' || c > '9')
|
||||||
break;
|
break;
|
||||||
shiftChars(1);
|
|
||||||
if (divisor > (UINT32_MAX - (c - '0')) / 10) {
|
if (divisor > (UINT32_MAX - (c - '0')) / 10) {
|
||||||
warning(WARNING_LARGE_CONSTANT,
|
warning(WARNING_LARGE_CONSTANT,
|
||||||
"Precision of fixed-point constant is too large\n");
|
"Precision of fixed-point constant is too large\n");
|
||||||
/* Discard any additional digits */
|
/* Discard any additional digits */
|
||||||
while (c = peek(0), c >= '0' && c <= '9')
|
shiftChars(1);
|
||||||
|
while (c = peek(0), (c >= '0' && c <= '9') || c == '_')
|
||||||
shiftChars(1);
|
shiftChars(1);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -1055,7 +1057,7 @@ static void readBinaryNumber(void)
|
|||||||
uint32_t value = 0;
|
uint32_t value = 0;
|
||||||
|
|
||||||
dbgPrint("Reading binary number with digits [%c,%c]\n", binDigits[0], binDigits[1]);
|
dbgPrint("Reading binary number with digits [%c,%c]\n", binDigits[0], binDigits[1]);
|
||||||
for (;;) {
|
for (;; shiftChars(1)) {
|
||||||
int c = peek(0);
|
int c = peek(0);
|
||||||
int bit;
|
int bit;
|
||||||
|
|
||||||
@@ -1063,13 +1065,13 @@ static void readBinaryNumber(void)
|
|||||||
bit = 0;
|
bit = 0;
|
||||||
else if (c == binDigits[1])
|
else if (c == binDigits[1])
|
||||||
bit = 1;
|
bit = 1;
|
||||||
|
else if (c == '_')
|
||||||
|
continue;
|
||||||
else
|
else
|
||||||
break;
|
break;
|
||||||
if (value > (UINT32_MAX - bit) / 2)
|
if (value > (UINT32_MAX - bit) / 2)
|
||||||
warning(WARNING_LARGE_CONSTANT, "Integer constant is too large\n");
|
warning(WARNING_LARGE_CONSTANT, "Integer constant is too large\n");
|
||||||
value = value * 2 + bit;
|
value = value * 2 + bit;
|
||||||
|
|
||||||
shiftChars(1);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
yylval.nConstValue = value;
|
yylval.nConstValue = value;
|
||||||
@@ -1081,7 +1083,7 @@ static void readHexNumber(void)
|
|||||||
bool empty = true;
|
bool empty = true;
|
||||||
|
|
||||||
dbgPrint("Reading hex number\n");
|
dbgPrint("Reading hex number\n");
|
||||||
for (;;) {
|
for (;; shiftChars(1)) {
|
||||||
int c = peek(0);
|
int c = peek(0);
|
||||||
|
|
||||||
if (c >= 'a' && c <= 'f') /* Convert letters to right after digits */
|
if (c >= 'a' && c <= 'f') /* Convert letters to right after digits */
|
||||||
@@ -1090,6 +1092,8 @@ static void readHexNumber(void)
|
|||||||
c = c - 'A' + 10;
|
c = c - 'A' + 10;
|
||||||
else if (c >= '0' && c <= '9')
|
else if (c >= '0' && c <= '9')
|
||||||
c = c - '0';
|
c = c - '0';
|
||||||
|
else if (c == '_' && !empty)
|
||||||
|
continue;
|
||||||
else
|
else
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@@ -1097,7 +1101,6 @@ static void readHexNumber(void)
|
|||||||
warning(WARNING_LARGE_CONSTANT, "Integer constant is too large\n");
|
warning(WARNING_LARGE_CONSTANT, "Integer constant is too large\n");
|
||||||
value = value * 16 + c;
|
value = value * 16 + c;
|
||||||
|
|
||||||
shiftChars(1);
|
|
||||||
empty = false;
|
empty = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -117,7 +117,8 @@ void macro_SetUniqueID(uint32_t id)
|
|||||||
if (uniqueID > maxUniqueID)
|
if (uniqueID > maxUniqueID)
|
||||||
maxUniqueID = uniqueID;
|
maxUniqueID = uniqueID;
|
||||||
/* The buffer is guaranteed to be the correct size */
|
/* The buffer is guaranteed to be the correct size */
|
||||||
sprintf(uniqueIDBuf, "_%" PRIu32, id);
|
/* This is a valid label fragment, but not a valid numeric */
|
||||||
|
sprintf(uniqueIDBuf, "_u%" PRIu32, id);
|
||||||
uniqueIDPtr = uniqueIDBuf;
|
uniqueIDPtr = uniqueIDBuf;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
21
test/asm/underscore-in-numeric-literal.asm
Normal file
21
test/asm/underscore-in-numeric-literal.asm
Normal file
@@ -0,0 +1,21 @@
|
|||||||
|
SECTION "Test", ROM0
|
||||||
|
|
||||||
|
_1234::
|
||||||
|
|
||||||
|
; without underscores
|
||||||
|
dw _1234 ; label
|
||||||
|
db 123, 123, 123 ; decimal
|
||||||
|
dw 12345 ; decimal
|
||||||
|
dw $abcd ; hex
|
||||||
|
db &200 ; octal
|
||||||
|
db %11110000, %10 ; binary
|
||||||
|
dl 6.283185 ; fixed point
|
||||||
|
|
||||||
|
; with underscores
|
||||||
|
dw _1234 ; label
|
||||||
|
db 123, 1_23, 1__23 ; decimal
|
||||||
|
dw 12_345 ; decimal
|
||||||
|
dw $ab_cd ; hex
|
||||||
|
db &2_0_0_ ; octal
|
||||||
|
db %1111_0000, %1_0 ; binary
|
||||||
|
dl 6_._283_185 ; fixed point
|
||||||
0
test/asm/underscore-in-numeric-literal.err
Normal file
0
test/asm/underscore-in-numeric-literal.err
Normal file
0
test/asm/underscore-in-numeric-literal.out
Normal file
0
test/asm/underscore-in-numeric-literal.out
Normal file
BIN
test/asm/underscore-in-numeric-literal.out.bin
Normal file
BIN
test/asm/underscore-in-numeric-literal.out.bin
Normal file
Binary file not shown.
@@ -1,19 +1,19 @@
|
|||||||
warning: unique-id.asm(12) -> unique-id.asm::m(4): [-Wuser]
|
warning: unique-id.asm(12) -> unique-id.asm::m(4): [-Wuser]
|
||||||
_1
|
_u1
|
||||||
warning: unique-id.asm(12) -> unique-id.asm::m(5) -> unique-id.asm::m::REPT~1(6): [-Wuser]
|
warning: unique-id.asm(12) -> unique-id.asm::m(5) -> unique-id.asm::m::REPT~1(6): [-Wuser]
|
||||||
_2
|
_u2
|
||||||
warning: unique-id.asm(12) -> unique-id.asm::m(5) -> unique-id.asm::m::REPT~2(6): [-Wuser]
|
warning: unique-id.asm(12) -> unique-id.asm::m(5) -> unique-id.asm::m::REPT~2(6): [-Wuser]
|
||||||
_3
|
_u3
|
||||||
warning: unique-id.asm(12) -> unique-id.asm::m(8): [-Wuser]
|
warning: unique-id.asm(12) -> unique-id.asm::m(8): [-Wuser]
|
||||||
_1
|
_u1
|
||||||
warning: unique-id.asm(14) -> unique-id.asm::m(4): [-Wuser]
|
warning: unique-id.asm(14) -> unique-id.asm::m(4): [-Wuser]
|
||||||
_4
|
_u4
|
||||||
warning: unique-id.asm(14) -> unique-id.asm::m(5) -> unique-id.asm::m::REPT~1(6): [-Wuser]
|
warning: unique-id.asm(14) -> unique-id.asm::m(5) -> unique-id.asm::m::REPT~1(6): [-Wuser]
|
||||||
_5
|
_u5
|
||||||
warning: unique-id.asm(14) -> unique-id.asm::m(5) -> unique-id.asm::m::REPT~2(6): [-Wuser]
|
warning: unique-id.asm(14) -> unique-id.asm::m(5) -> unique-id.asm::m::REPT~2(6): [-Wuser]
|
||||||
_6
|
_u6
|
||||||
warning: unique-id.asm(14) -> unique-id.asm::m(8): [-Wuser]
|
warning: unique-id.asm(14) -> unique-id.asm::m(8): [-Wuser]
|
||||||
_4
|
_u4
|
||||||
FATAL: unique-id.asm(15):
|
FATAL: unique-id.asm(15):
|
||||||
Macro argument '\@' not defined
|
Macro argument '\@' not defined
|
||||||
while expanding symbol "print"
|
while expanding symbol "print"
|
||||||
|
|||||||
Reference in New Issue
Block a user