Detect assignments to undeclared variables.
Previously we only detected reading from undefined variables.
diff --git a/libacc/acc.cpp b/libacc/acc.cpp
index 7da744a..7ba30a9 100644
--- a/libacc/acc.cpp
+++ b/libacc/acc.cpp
@@ -3832,11 +3832,28 @@
return false;
}
+ void linkGlobal(tokenid_t t, bool isFunction) {
+ VariableInfo* pVI = VI(t);
+ void* n = NULL;
+ if (mpSymbolLookupFn) {
+ n = mpSymbolLookupFn(mpSymbolLookupContext, nameof(t));
+ }
+ if (pVI->pType == NULL) {
+ if (isFunction) {
+ pVI->pType = mkpIntFn;
+ } else {
+ pVI->pType = mkpInt;
+ }
+ }
+ pVI->pAddress = n;
+ }
+
/* Parse and evaluate a unary expression.
* allowAssignment is true if '=' parsing wanted (quick hack)
*/
void unary(bool allowAssignment) {
- intptr_t n, t, a;
+ tokenid_t t;
+ intptr_t n, a;
t = 0;
n = 1; /* type of expression 0 = forward, 1 = value, other = lvalue */
if (acceptStringLiteral()) {
@@ -3924,18 +3941,11 @@
n = (intptr_t) pVI->pAddress;
/* forward reference: try our lookup function */
if (!n) {
- if (mpSymbolLookupFn) {
- n = (intptr_t) mpSymbolLookupFn(
- mpSymbolLookupContext, nameof(t));
+ linkGlobal(t, tok == '(');
+ n = (intptr_t) pVI->pAddress;
+ if (!n && tok != '(') {
+ error("Undeclared variable %s\n", nameof(t));
}
- if (pVI->pType == NULL) {
- if (tok == '(') {
- pVI->pType = mkpIntFn;
- } else {
- pVI->pType = mkpInt;
- }
- }
- pVI->pAddress = (void*) n;
}
if ((tok == '=') & allowAssignment) {
/* assignment */
@@ -3945,7 +3955,11 @@
} else if (tok != '(') {
/* variable */
if (!n) {
- error("Undefined variable %s", nameof(t));
+ linkGlobal(t, false);
+ n = (intptr_t) pVI->pAddress;
+ if (!n) {
+ error("Undeclared variable %s\n", nameof(t));
+ }
}
pGen->loadR0(n, tokl == 11, tokc, pVI->pType);
if (tokl == 11) {