summaryrefslogtreecommitdiff
path: root/scripts/kconfig/expr1.c
Unidiff
Diffstat (limited to 'scripts/kconfig/expr1.c') (more/less context) (ignore whitespace changes)
-rw-r--r--scripts/kconfig/expr1.c333
1 files changed, 333 insertions, 0 deletions
diff --git a/scripts/kconfig/expr1.c b/scripts/kconfig/expr1.c
new file mode 100644
index 0000000..8b45801
--- a/dev/null
+++ b/scripts/kconfig/expr1.c
@@ -0,0 +1,333 @@
1/*
2 * Copyright (C) 2002 Roman Zippel <zippel@linux-m68k.org>
3 * Released under the terms of the GNU GPL v2.0.
4 */
5
6#include <ctype.h>
7#include <stdio.h>
8#include <stdlib.h>
9#include <string.h>
10#include "cml1.h"
11
12struct file *file_list;
13struct file *current_file;
14
15struct symbol symbol_yes = {
16 name: "y",
17 curr: { "y", yes },
18 flags: SYMBOL_YES|SYMBOL_VALID,
19}, symbol_mod = {
20 name: "m",
21 curr: { "m", mod },
22 flags: SYMBOL_MOD|SYMBOL_VALID,
23}, symbol_no = {
24 name: "n",
25 curr: { "n", no },
26 flags: SYMBOL_NO|SYMBOL_VALID,
27}, symbol_empty = {
28 name: "",
29 curr: { "", no },
30 flags: SYMBOL_VALID,
31};
32
33struct expr *expr_alloc_symbol(struct symbol *sym)
34{
35 struct expr *e = malloc(sizeof(*e));
36 memset(e, 0, sizeof(*e));
37 e->token = T_WORD;
38 e->left.sym = sym;
39 return e;
40}
41
42struct expr *expr_alloc_one(int token, struct expr *ce)
43{
44 struct expr *e = malloc(sizeof(*e));
45 memset(e, 0, sizeof(*e));
46 e->token = token;
47 e->left.expr = ce;
48 return e;
49}
50
51struct expr *expr_alloc_two(int token, struct expr *e1, struct expr *e2)
52{
53 struct expr *e = malloc(sizeof(*e));
54 memset(e, 0, sizeof(*e));
55 e->token = token;
56 e->left.expr = e1;
57 e->right.expr = e2;
58 return e;
59}
60
61struct expr *expr_alloc_comp(int token, struct symbol *s1, struct symbol *s2)
62{
63 struct expr *e = malloc(sizeof(*e));
64 memset(e, 0, sizeof(*e));
65 e->token = token;
66 e->left.sym = s1;
67 e->right.sym = s2;
68 return e;
69}
70
71struct expr *expr_alloc_and(struct expr *e1, struct expr *e2)
72{
73 if (!e1)
74 return e2;
75 return e2 ? expr_alloc_two(T_AND, e1, e2) : e1;
76}
77
78struct expr *expr_copy(struct expr *org)
79{
80 struct expr *e;
81
82 if (!org)
83 return NULL;
84
85 e = malloc(sizeof(*org));
86 memcpy(e, org, sizeof(*org));
87 switch (org->token) {
88 case T_WORD:
89 e->left = org->left;
90 break;
91 case '!':
92 e->left.expr = expr_copy(org->left.expr);
93 break;
94 case '=':
95 case T_UNEQUAL:
96 e->left.sym = org->left.sym;
97 e->right.sym = org->right.sym;
98 break;
99 case T_OR:
100 case T_AND:
101 case '&':
102 case '|':
103 case '^':
104 case T_IF:
105 case T_ELSE:
106 e->left.expr = expr_copy(org->left.expr);
107 e->right.expr = expr_copy(org->right.expr);
108 break;
109 default:
110 printf("can't copy token %d\n", e->token);
111 free(e);
112 e = NULL;
113 break;
114 }
115
116 return e;
117}
118
119void expr_free(struct expr *e)
120{
121 if (!e)
122 return;
123
124 switch (e->token) {
125 case T_WORD:
126 break;
127 case '!':
128 expr_free(e->left.expr);
129 return;
130 case '=':
131 case T_UNEQUAL:
132 break;
133 case '|':
134 case T_OR:
135 case T_AND:
136 case '&':
137 case T_IF:
138 case T_ELSE:
139 expr_free(e->left.expr);
140 expr_free(e->right.expr);
141 break;
142 default:
143 printf("how to free token %d?\n", e->token);
144 break;
145 }
146 free(e);
147}
148
149static inline int token_gt(int t1, int t2)
150{
151#if 0
152 return 1;
153#else
154 switch (t1) {
155 case '=':
156 case T_UNEQUAL:
157 if (t2 == '!')
158 return 1;
159 case '!':
160 if (t2 == T_AND || t2 == T_IF || t2 == T_ELSE || t2 == '&')
161 return 1;
162 case '&':
163 case T_IF:
164 case T_ELSE:
165 case T_AND:
166 if (t2 == T_OR || t2 == '|')
167 return 1;
168 case '|':
169 case T_OR:
170 if (t2 == '^')
171 return 1;
172 case '^':
173 if (t2 == 0)
174 return 1;
175 case 0:
176 return 0;
177 }
178 printf("[%dgt%d?]", t1, t2);
179 return 0;
180#endif
181}
182
183int print_type = 1;
184
185static void print_sym(FILE *out, struct symbol *sym)
186{
187 fprintf(out, "%s", sym->name);
188 if (print_type)
189 fprintf(out, "%s",
190 sym->type == SYMBOL_BOOLEAN ? "?" :
191 sym->type == SYMBOL_TRISTATE ? "??" :
192 sym->type == SYMBOL_HEX ? "h" :
193 sym->type == SYMBOL_INT ? "i" :
194 sym->type == SYMBOL_STRING ? "s" :
195 "");
196}
197
198void fprint_expr(FILE *out, struct expr *e, int prevtoken)
199{
200 if (!e) {
201 fprintf(out, "<none>");
202 return;
203 }
204
205 switch (e->token) {
206 case T_WORD:
207 print_sym(out, e->left.sym);
208 break;
209 case '!':
210 if (token_gt(prevtoken, '!'))
211 fprintf(out, "(");
212 fprintf(out, "!");
213 fprint_expr(out, e->left.expr, '!');
214 if (token_gt(prevtoken, '!'))
215 fprintf(out, ")");
216 break;
217 case '=':
218 if (token_gt(prevtoken, '='))
219 fprintf(out, "(");
220 print_sym(out, e->left.sym);
221 fprintf(out, "=");
222 print_sym(out, e->right.sym);
223 if (token_gt(prevtoken, '='))
224 fprintf(out, ")");
225 break;
226 case T_UNEQUAL:
227 if (token_gt(prevtoken, T_UNEQUAL))
228 fprintf(out, "(");
229 print_sym(out, e->left.sym);
230 fprintf(out, "!=");
231 print_sym(out, e->right.sym);
232 if (token_gt(prevtoken, T_UNEQUAL))
233 fprintf(out, ")");
234 break;
235 case T_OR:
236 if (token_gt(prevtoken, T_OR))
237 fprintf(out, "(");
238 fprint_expr(out, e->left.expr, T_OR);
239 fprintf(out, " || ");
240 fprint_expr(out, e->right.expr, T_OR);
241 if (token_gt(prevtoken, T_OR))
242 fprintf(out, ")");
243 break;
244 case T_AND:
245 if (token_gt(prevtoken, T_AND))
246 fprintf(out, "(");
247 fprint_expr(out, e->left.expr, T_AND);
248 fprintf(out, " && ");
249 fprint_expr(out, e->right.expr, T_AND);
250 if (token_gt(prevtoken, T_AND))
251 fprintf(out, ")");
252 break;
253 case '|':
254 if (token_gt(prevtoken, '|'))
255 fprintf(out, "(");
256 fprint_expr(out, e->left.expr, '|');
257 fprintf(out, " || ");
258 fprint_expr(out, e->right.expr, '|');
259 if (token_gt(prevtoken, '|'))
260 fprintf(out, ")");
261 break;
262 case '&':
263 if (token_gt(prevtoken, '&'))
264 fprintf(out, "(");
265 fprint_expr(out, e->left.expr, '&');
266 if (print_type)
267 fprintf(out, " & ");
268 else
269 fprintf(out, " && ");
270 fprint_expr(out, e->right.expr, '&');
271 if (token_gt(prevtoken, '&'))
272 fprintf(out, ")");
273 break;
274 case '^':
275 if (e->left.expr) {
276 fprint_expr(out, e->left.expr, '^');
277 fprintf(out, " ^ ");
278 }
279 fprintf(out, "%s", e->right.sym->name);
280 break;
281 case T_IF:
282 if (token_gt(prevtoken, T_IF))
283 fprintf(out, "[");
284 if (e->right.expr) {
285 fprint_expr(out, e->right.expr, T_IF);
286 fprintf(out, " && ");
287 }
288 fprint_expr(out, e->left.expr, T_IF);
289 if (token_gt(prevtoken, T_IF))
290 fprintf(out, "]");
291 break;
292 case T_ELSE:
293 if (token_gt(prevtoken, T_ELSE))
294 fprintf(out, "[");
295 //fprintf(out, "[");
296 if (e->right.expr) {
297 fprint_expr(out, e->right.expr, T_ELSE);
298 fprintf(out, " && ");
299 }
300 fprintf(out, "!");
301 fprint_expr(out, e->left.expr, '!');
302 if (token_gt(prevtoken, T_ELSE))
303 fprintf(out, "]");
304 break;
305 default:
306 fprintf(out, "<unknown token %d>", e->token);
307 break;
308 }
309}
310
311void print_expr(int mask, struct expr *e, int prevtoken)
312{
313 if (!(cdebug & mask))
314 return;
315 fprint_expr(stdout, e, prevtoken);
316}
317
318struct file *lookup_file(const char *name)
319{
320 struct file *file;
321
322 for (file = file_list; file; file = file->next) {
323 if (!strcmp(name, file->name))
324 return file;
325 }
326
327 file = malloc(sizeof(*file));
328 memset(file, 0, sizeof(*file));
329 file->name = strdup(name);
330 file->next = file_list;
331 file_list = file;
332 return file;
333}