Skip to content

Instantly share code, notes, and snippets.

@mingodad
Created December 27, 2018 09:48
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save mingodad/47f61a4997f5be63c9e0a9394a1f68b6 to your computer and use it in GitHub Desktop.
Save mingodad/47f61a4997f5be63c9e0a9394a1f68b6 to your computer and use it in GitHub Desktop.
Add compiler warning/error for duplicate variable declaration in Lua 5.1.5
--- lparser.c 2018-11-30 11:47:05.053864317 +0100
+++ lparser.c 2018-12-27 09:28:55.536952662 +0100
@@ -6,6 +6,7 @@
#include <string.h>
+#include <stdio.h>
#define lparser_c
#define LUA_CORE
@@ -61,6 +62,14 @@
}
}
+#define MAXSRC 80
+static void parser_warning (LexState *ls, const char *msg) {
+ char buff[MAXSRC];
+ luaO_chunkid(buff, getstr(ls->source), MAXSRC);
+ msg = luaO_pushfstring(ls->L, "%s:%d: warning %s", buff, ls->linenumber, msg);
+ fprintf(stderr, "%s\n", msg);
+ fflush(stderr);
+}
static void error_expected (LexState *ls, int token) {
luaX_syntaxerror(ls,
@@ -159,8 +168,30 @@
static void new_localvar (LexState *ls, TString *name, int n) {
FuncState *fs = ls->fs;
- luaY_checklimit(fs, fs->nactvar+n+1, LUAI_MAXVARS, "local variables");
- fs->actvar[fs->nactvar+n] = cast(unsigned short, registerlocalvar(ls, name));
+ int nactvar_n = fs->nactvar+n;
+
+ /* allow '_' and '(for...' duplicates */
+ const char *str_name = getstr(name);
+ if(!(str_name[0] == '(' || (name->tsv.len == 1 && str_name[0] == '_'))) {
+ int vidx = 0;
+ for (; vidx < nactvar_n; ++vidx) {
+ if (name == getlocvar(fs, vidx).varname) {
+ if(fs->bl && vidx < fs->bl->nactvar) {
+ int saved_top = lua_gettop(ls->L);
+ parser_warning(ls, luaO_pushfstring(ls->L,
+ "Name [%s] already declared will be shadowed", str_name));
+ lua_settop(ls->L, saved_top);
+ }
+ else {
+ luaX_syntaxerror(ls, luaO_pushfstring(ls->L,
+ "Name [%s] already declared", str_name));
+ }
+ }
+ }
+ }
+
+ luaY_checklimit(fs, nactvar_n+1, LUAI_MAXVARS, "local variables");
+ fs->actvar[nactvar_n] = cast(unsigned short, registerlocalvar(ls, name));
}
@denisdemaisbr
Copy link

$ patch --merge --verbose -u -p0 < ../../compiler-warning-lua-5.1.5.patch
Hmm... Looks like a unified diff to me...
(Stripping trailing CRs from patch; use --binary to disable.)
The text leading up to this was:

|--- lparser.c 2018-11-30 11:47:05.053864317 +0100
|+++ lparser.c 2018-12-27 09:28:55.536952662 +0100

patching file lparser.c
Using Plan A...
Hunk #1 merged at 9.
Hunk #2 merged at 65-72.
patch unexpectedly ends in middle of line
Hunk #3 merged at 171-194.
done

min.lua:7: Name [a] already declared near 'local'

works very nice!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment