(no commit message)
[geda-pcb/pcjc2.git] / src / res_parse.y
bloba72fee77e78ff5109693ece4c97edba9fc62bf30
1 %{
3 #ifdef HAVE_CONFIG_H
4 #include "config.h"
5 #endif
7 #include <stdio.h>
8 #include <stdlib.h>
10 #ifdef HAVE_STRING_H
11 #include <string.h>
12 #endif
14 #define YYDEBUG 0
15 #define YYERROR_VERBOSE 1
17 /* #define YYSTYPE void * */
19 #include "global.h"
20 #include "resource.h"
21 #include "res_parse.h"
23 #ifdef HAVE_LIBDMALLOC
24 #include <dmalloc.h>
25 #endif
27 static Resource *parsed_res;
28 static Resource *current_res;
30 int reserror(const char *);
31 int reslex();
33 #define f(x) current_res->flags |= x
37 %name-prefix="res"
38 %start top_res
40 %union {
41 int ival;
42 char *sval;
43 Resource *rval;
46 %token <sval> STRING INCLUDE
47 %type <rval> res
51 top_res
52 : { current_res = parsed_res = resource_create(NULL); }
53 res_item_zm
56 res
57 : { current_res = resource_create(current_res); }
58 '{' res_item_zm '}'
59 { $$ = current_res; current_res = current_res->parent; }
62 res_item_zm : res_item res_item_zm | ;
63 res_item
64 : STRING { resource_add_val(current_res, 0, $1, 0); f(FLAG_V); }
65 | STRING '=' STRING { resource_add_val(current_res, $1, $3, 0); f(FLAG_NV); }
66 | INCLUDE { resource_add_val(current_res, 0, $1, 0); f(FLAG_S); }
67 | res { resource_add_val(current_res, 0, 0, $1); f(FLAG_S); }
68 | STRING '=' res { resource_add_val(current_res, $1, 0, $3); f(FLAG_NS); }
69 | error
74 static const char *res_filename = NULL;
75 static FILE *res_file = NULL;
76 static const char **res_strings = NULL;
77 static int res_string_idx = 0;
78 int res_lineno;
80 int
81 res_parse_getchars(char *buf, int max_size)
83 if (res_file)
85 int i = fgetc(res_file);
86 buf[0] = i;
87 if (i == EOF)
88 return 0;
90 else
92 if (res_strings[0] == 0)
93 return 0;
94 buf[0] = res_strings[0][res_string_idx];
95 res_string_idx ++;
96 if (buf[0] == 0)
98 res_strings ++;
99 res_string_idx = 0;
100 buf[0] = '\n';
101 return 1;
104 return 1;
107 Resource *
108 resource_parse(const char *filename, const char **strings)
110 res_lineno = 1;
111 if (filename)
113 res_file = fopen (filename, "r");
114 if (res_file == NULL)
116 perror(filename);
117 return NULL;
119 res_filename = filename;
121 else if (strings)
123 res_strings = strings;
124 res_string_idx = 0;
126 else
127 return NULL;
128 #if YYDEBUG
129 yydebug = 1;
130 #endif
131 if (resparse())
132 parsed_res = NULL;
133 if (filename)
135 fclose (res_file);
136 res_filename = NULL;
137 res_file = NULL;
139 else
140 res_strings = NULL;
141 return parsed_res;
144 Resource *
145 resource_create(Resource *parent)
147 Resource *rv = (Resource *)malloc(sizeof(Resource));
148 rv->parent = parent;
149 rv->flags = 0;
150 rv->c = 0;
151 rv->v = (ResourceVal *)malloc(sizeof(ResourceVal));
152 return rv;
155 void
156 resource_add_val(Resource *n, char *name, char *value, Resource *subres)
158 n->v = (ResourceVal *)realloc(n->v, sizeof(ResourceVal)*(n->c+1));
159 n->v[n->c].name = name;
160 n->v[n->c].value = value;
161 n->v[n->c].subres = subres;
162 n->c++;
165 char *
166 resource_value(const Resource *res, char *name)
168 int i;
169 if (res == 0 || name == 0)
170 return 0;
171 for (i=0; i<res->c; i++)
172 if (res->v[i].name && res->v[i].value
173 && NSTRCMP(res->v[i].name, name) == 0)
174 return res->v[i].value;
175 return 0;
178 Resource *
179 resource_subres(const Resource *res, const char *name)
181 int i;
182 if (res == 0 || name == 0)
183 return 0;
184 for (i=0; i<res->c; i++)
185 if (res->v[i].name && res->v[i].subres
186 && NSTRCMP(res->v[i].name, name) == 0)
187 return res->v[i].subres;
188 return 0;
192 reserror(const char *str)
194 fprintf(stderr, "Error: %s around line %d: %s\n",
195 res_file ? res_filename : "internal strings",
196 res_lineno, str);
197 return 0;
200 static void
201 dump_res(Resource *n, int l)
203 int i;
204 for (i=0; i<n->c; i++)
206 if (n->v[i].subres)
208 printf("%*cn[%s] = {\n", l, ' ', n->v[i].name? n->v[i].name :"");
209 dump_res(n->v[i].subres, l+3);
210 printf("%*c}\n", l, ' ');
212 else
213 printf("%*cn[%s] = v[%s]\n", l, ' ', n->v[i].name? n->v[i].name :"", n->v[i].value? n->v[i].value :"");
217 void
218 resource_dump (Resource *r)
220 dump_res (r, 0);