blob: 100ca658fa7f4a86a5f5ed474b59cb58bcdda572 [file] [log] [blame]
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001/* Parser-tokenizer link implementation */
2
3#include <stdio.h>
4
5#include "PROTO.h"
6#include "malloc.h"
7#include "tokenizer.h"
8#include "node.h"
9#include "grammar.h"
10#include "parser.h"
11#include "errcode.h"
12
13extern int debugging;
14
15
16/* Parse input coming from the given tokenizer structure.
17 Return error code. */
18
19static int
20parsetok(tok, g, start, n_ret)
21 struct tok_state *tok;
22 grammar *g;
23 int start;
24 node **n_ret;
25{
26 parser_state *ps;
27 int ret;
28
29 if ((ps = newparser(g, start)) == NULL) {
30 fprintf(stderr, "no mem for new parser\n");
31 return E_NOMEM;
32 }
33
34 for (;;) {
35 char *a, *b;
36 int type;
37 int len;
38 char *str;
39
40 type = tok_get(tok, &a, &b);
41 if (type == ERRORTOKEN) {
42 ret = tok->done;
43 break;
44 }
45 len = b - a;
46 str = NEW(char, len + 1);
47 if (str == NULL) {
48 fprintf(stderr, "no mem for next token\n");
49 ret = E_NOMEM;
50 break;
51 }
52 strncpy(str, a, len);
53 str[len] = '\0';
54 ret = addtoken(ps, (int)type, str);
55 if (ret != E_OK) {
Guido van Rossum840bcf11990-11-18 17:39:41 +000056 if (ret == E_DONE) {
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000057 *n_ret = ps->p_tree;
Guido van Rossum840bcf11990-11-18 17:39:41 +000058 ps->p_tree = NULL;
59 }
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000060 else if (tok->lineno <= 1 && tok->done == E_EOF)
61 ret = E_EOF;
62 break;
63 }
64 }
65
66 delparser(ps);
67 return ret;
68}
69
70
71/* Parse input coming from a string. Return error code. */
72
73int
74parsestring(s, g, start, n_ret)
75 char *s;
76 grammar *g;
77 int start;
78 node **n_ret;
79{
80 struct tok_state *tok = tok_setups(s);
81 int ret;
82
83 if (tok == NULL) {
84 fprintf(stderr, "no mem for tok_setups\n");
85 return E_NOMEM;
86 }
87 ret = parsetok(tok, g, start, n_ret);
88 if (ret == E_TOKEN || ret == E_SYNTAX) {
89 fprintf(stderr, "String parsing error at line %d\n",
90 tok->lineno);
91 }
92 tok_free(tok);
93 return ret;
94}
95
96
97/* Parse input coming from a file. Return error code. */
98
99int
100parsefile(fp, g, start, ps1, ps2, n_ret)
101 FILE *fp;
102 grammar *g;
103 int start;
104 char *ps1, *ps2;
105 node **n_ret;
106{
107 struct tok_state *tok = tok_setupf(fp, ps1, ps2);
108 int ret;
109
110 if (tok == NULL) {
111 fprintf(stderr, "no mem for tok_setupf\n");
112 return E_NOMEM;
113 }
114 ret = parsetok(tok, g, start, n_ret);
115 if (ret == E_TOKEN || ret == E_SYNTAX) {
116 char *p;
Guido van Rossum840bcf11990-11-18 17:39:41 +0000117 fprintf(stderr, "Parsing error at line %d:\n", tok->lineno);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000118 *tok->inp = '\0';
119 if (tok->inp > tok->buf && tok->inp[-1] == '\n')
120 tok->inp[-1] = '\0';
121 fprintf(stderr, "%s\n", tok->buf);
122 for (p = tok->buf; p < tok->cur; p++) {
123 if (*p == '\t')
124 putc('\t', stderr);
125 else
126 putc(' ', stderr);
127 }
128 fprintf(stderr, "^\n");
129 }
130 tok_free(tok);
131 return ret;
132}