Fixed bug in 'main.c'
phimvt@lurac.latrobe.edu.au — 2000-11-24 05:35:31
Fixed bug in main.c
The Joy prototype implementation had a serious bug that could cause
a crash:
LIBRA
dup == 2 * . (* legal attempt to re-define built-in "dup" *)
Joy accepts this (as it is supposed to, even if it is not often
a good idea to re-define a built-in). But now the call
11 dup.
produces a CRASH.
The error occurred in the prototype as follows: The new definition
will overwrite a pointer to the internal function dup_() by
with a pointer to the code [2 *]. Then when the new dup is called
it attempts to execute an internal function by that mangled
pointer. But the mangled pointer does not point to any function,
so the system crashes.
To fix the problem, if in a definition a name is encountered
that is in fact a built-in, a new symbol table node has to be
created as if the new name had not been seen before. This
new node creation already occurs when a name is being looked up.
That same new node creation has to be used in definitions
when an inbuilt is being redefined.
The new node creation can now occur for two quite different
reasons, so it was best to define a new function "enterglobal()".
This new function is now called in two different places.
1) Before function "lookup()", insert the new function "enterglobals()",
whose body is essentially something that occurred already inside function
"lookup()".
2) In function "lookup()" replace those lines by a call to the
new function "enterglobals()".
3) In function "definition()" insert a conditional
if (location < firstlibra) /* if it is a builtin */
enterglobals(); /* treat as if new */
The VMS "DIFF-file gives the details:
************
File DSK8B:[PHIMVT.JOY.C]MAIN.C-OLD;1
25 PUBLIC void lookup()
******
File DSK8B:[PHIMVT.JOY.C]MAIN.C;90
25 PUBLIC void enterglobal()
26 {
27 location = symtabindex++;
28 D( printf("getsym, new: '%s'\n",id); )
29 location->name = (char *) malloc(strlen(id) + 1);
30 strcpy(location->name,id);
31 location->u.body = NULL; /* may be assigned in definition */
32 location->next = hashentry[hashvalue];
33 D( printf("entered %s at %d\n",id,LOC2INT(location)); )
34 hashentry[hashvalue] = location;
35 }
36 PUBLIC void lookup()
************
************
File DSK8B:[PHIMVT.JOY.C]MAIN.C-OLD;1
41 { location = symtabindex++;
42 D( printf("getsym, new: '%s'\n",id); )
43 location->name = (char *) malloc(strlen(id) + 1);
44 strcpy(location->name,id);
45 location->u.body = NULL; /* may be assigned in definition */
46 location->next = hashentry[hashvalue];
47 D( printf("entered %s at %d\n",id,LOC2INT(location)); )
48 hashentry[hashvalue] = location; }
49 }
******
File DSK8B:[PHIMVT.JOY.C]MAIN.C;90
52 enterglobal();
53 }
************
************
File DSK8B:[PHIMVT.JOY.C]MAIN.C-OLD;1
80 here = location; getsym();
******
File DSK8B:[PHIMVT.JOY.C]MAIN.C;90
84 if (location < firstlibra)
85 { printf("warning: overwriting inbuilt '%s'\n",location->name);
86 enterglobal(); }
87 here = location; getsym();
************
Number of difference sections found: 3
Number of difference records found: 22
DIFFERENCES /IGNORE=()/MERGED=1/OUTPUT=DSK8B:[PHIMVT.JOY.C]MAIN.DIFFS;2-
DSK8B:[PHIMVT.JOY.C]MAIN.C-OLD;1-
DSK8B:[PHIMVT.JOY.C]MAIN.C;90