summaryrefslogtreecommitdiffstats
path: root/Parser
diff options
context:
space:
mode:
authorJeremy Hylton <jeremy@alum.mit.edu>2000-06-20 19:10:44 (GMT)
committerJeremy Hylton <jeremy@alum.mit.edu>2000-06-20 19:10:44 (GMT)
commit94988067b96c6187fd940eaff99c2c5a68daac68 (patch)
tree681d7a64160eeab1ece2685bb234971d404ef0a6 /Parser
parent56c807d318954222bb67167477d98eafb6b85d81 (diff)
downloadcpython-94988067b96c6187fd940eaff99c2c5a68daac68.zip
cpython-94988067b96c6187fd940eaff99c2c5a68daac68.tar.gz
cpython-94988067b96c6187fd940eaff99c2c5a68daac68.tar.bz2
Add new parser error code, E_OVERFLOW. This error is returned when
the number of children of a node exceeds the max possible value for the short that is used to count them. The Python runtime converts this parser error into the SyntaxError "expression too long."
Diffstat (limited to 'Parser')
-rw-r--r--Parser/node.c11
-rw-r--r--Parser/parser.c29
2 files changed, 23 insertions, 17 deletions
diff --git a/Parser/node.c b/Parser/node.c
index c2308fd..3f593c8 100644
--- a/Parser/node.c
+++ b/Parser/node.c
@@ -29,10 +29,13 @@ PERFORMANCE OF THIS SOFTWARE.
******************************************************************/
+#include <limits.h>
+
/* Parse tree node implementation */
#include "pgenheaders.h"
#include "node.h"
+#include "errcode.h"
node *
PyNode_New(type)
@@ -52,7 +55,7 @@ PyNode_New(type)
#define XXX 3 /* Node alignment factor to speed up realloc */
#define XXXROUNDUP(n) ((n) == 1 ? 1 : ((n) + XXX - 1) / XXX * XXX)
-node *
+int
PyNode_AddChild(n1, type, str, lineno)
register node *n1;
int type;
@@ -62,12 +65,14 @@ PyNode_AddChild(n1, type, str, lineno)
register int nch = n1->n_nchildren;
register int nch1 = nch+1;
register node *n;
+ if (nch == SHRT_MAX || nch < 0)
+ return E_OVERFLOW;
if (XXXROUNDUP(nch) < nch1) {
n = n1->n_child;
nch1 = XXXROUNDUP(nch1);
PyMem_RESIZE(n, node, nch1);
if (n == NULL)
- return NULL;
+ return E_NOMEM;
n1->n_child = n;
}
n = &n1->n_child[n1->n_nchildren++];
@@ -76,7 +81,7 @@ PyNode_AddChild(n1, type, str, lineno)
n->n_lineno = lineno;
n->n_nchildren = 0;
n->n_child = NULL;
- return n;
+ return 0;
}
/* Forward */
diff --git a/Parser/parser.c b/Parser/parser.c
index 3b75dbc..00299af 100644
--- a/Parser/parser.c
+++ b/Parser/parser.c
@@ -153,11 +153,11 @@ shift(s, type, str, newstate, lineno)
int newstate;
int lineno;
{
+ int err;
assert(!s_empty(s));
- if (PyNode_AddChild(s->s_top->s_parent, type, str, lineno) == NULL) {
- fprintf(stderr, "shift: no mem in addchild\n");
- return -1;
- }
+ err = PyNode_AddChild(s->s_top->s_parent, type, str, lineno);
+ if (err)
+ return err;
s->s_top->s_state = newstate;
return 0;
}
@@ -172,13 +172,13 @@ push(s, type, d, newstate, lineno)
int newstate;
int lineno;
{
+ int err;
register node *n;
n = s->s_top->s_parent;
assert(!s_empty(s));
- if (PyNode_AddChild(n, type, (char *)NULL, lineno) == NULL) {
- fprintf(stderr, "push: no mem in addchild\n");
- return -1;
- }
+ err = PyNode_AddChild(n, type, (char *)NULL, lineno);
+ if (err)
+ return err;
s->s_top->s_state = newstate;
return s_push(s, d, CHILD(n, NCH(n)-1));
}
@@ -233,6 +233,7 @@ PyParser_AddToken(ps, type, str, lineno)
int lineno;
{
register int ilabel;
+ int err;
D(printf("Token %s/'%s' ... ", _PyParser_TokenNames[type], str));
@@ -260,20 +261,20 @@ PyParser_AddToken(ps, type, str, lineno)
int arrow = x & ((1<<7)-1);
dfa *d1 = PyGrammar_FindDFA(
ps->p_grammar, nt);
- if (push(&ps->p_stack, nt, d1,
- arrow, lineno) < 0) {
+ if ((err = push(&ps->p_stack, nt, d1,
+ arrow, lineno)) > 0) {
D(printf(" MemError: push\n"));
- return E_NOMEM;
+ return err;
}
D(printf(" Push ...\n"));
continue;
}
/* Shift the token */
- if (shift(&ps->p_stack, type, str,
- x, lineno) < 0) {
+ if ((err = shift(&ps->p_stack, type, str,
+ x, lineno)) > 0) {
D(printf(" MemError: shift.\n"));
- return E_NOMEM;
+ return err;
}
D(printf(" Shift.\n"));
/* Pop while we are in an accept-only state */