blob: 8ed58e81fe8807e1efe222f531f2186537d03213 [file] [log] [blame]
David Gibsonfc14dad2005-06-08 17:18:34 +10001/*
2 * (C) Copyright David Gibson <dwg@au1.ibm.com>, IBM Corporation. 2005.
3 *
David Gibson63dc9c72007-09-18 11:44:04 +10004 *
David Gibsonfc14dad2005-06-08 17:18:34 +10005 * This program is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU General Public License as
7 * published by the Free Software Foundation; either version 2 of the
8 * License, or (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * General Public License for more details.
David Gibson63dc9c72007-09-18 11:44:04 +100014 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
18 * USA
David Gibsonfc14dad2005-06-08 17:18:34 +100019 */
20
David Gibson86dbcbd2005-10-19 16:00:31 +100021%locations
22
David Gibsonfc14dad2005-06-08 17:18:34 +100023%{
24#include "dtc.h"
Jon Loeligere45e6fd2007-03-23 15:18:41 -050025#include "srcpos.h"
David Gibsonfc14dad2005-06-08 17:18:34 +100026
Jon Loeliger39488492007-02-16 09:33:54 -060027int yylex(void);
David Gibson9ed27a22007-11-07 11:16:19 +110028unsigned long long eval_literal(const char *s, int base, int bits);
David Gibsonfc14dad2005-06-08 17:18:34 +100029
David Gibsonf0517db2005-07-15 17:14:24 +100030extern struct boot_info *the_boot_info;
David Gibsonfc14dad2005-06-08 17:18:34 +100031
32%}
33
34%union {
David Gibson9ed27a22007-11-07 11:16:19 +110035 char *propnodename;
36 char *literal;
37 char *labelref;
Jon Loeligeraf0278a2007-02-15 10:59:27 -060038 unsigned int cbase;
David Gibson03a9b9d2005-07-11 16:49:52 +100039 u8 byte;
David Gibsonfc14dad2005-06-08 17:18:34 +100040 struct data data;
David Gibson9ed27a22007-11-07 11:16:19 +110041
42 u64 addr;
43 cell_t cell;
David Gibsonfc14dad2005-06-08 17:18:34 +100044 struct property *prop;
45 struct property *proplist;
46 struct node *node;
47 struct node *nodelist;
David Gibsonf040d952005-10-24 18:18:38 +100048 struct reserve_info *re;
David Gibsonfc14dad2005-06-08 17:18:34 +100049}
50
David Gibson9138db52007-11-07 11:17:17 +110051%token DT_V1
David Gibsonf0517db2005-07-15 17:14:24 +100052%token DT_MEMRESERVE
David Gibson9ed27a22007-11-07 11:16:19 +110053%token <propnodename> DT_PROPNODENAME
54%token <literal> DT_LITERAL
David Gibson9138db52007-11-07 11:17:17 +110055%token <literal> DT_LEGACYLITERAL
Jon Loeligeraf0278a2007-02-15 10:59:27 -060056%token <cbase> DT_BASE
David Gibsonfc14dad2005-06-08 17:18:34 +100057%token <byte> DT_BYTE
58%token <data> DT_STRING
David Gibson9ed27a22007-11-07 11:16:19 +110059%token <labelref> DT_LABEL
60%token <labelref> DT_REF
David Gibsonfc14dad2005-06-08 17:18:34 +100061
62%type <data> propdata
David Gibson32da4752007-02-07 16:37:50 +110063%type <data> propdataprefix
David Gibsonf0517db2005-07-15 17:14:24 +100064%type <re> memreserve
David Gibsonf040d952005-10-24 18:18:38 +100065%type <re> memreserves
David Gibson9138db52007-11-07 11:17:17 +110066%type <re> v0_memreserve
67%type <re> v0_memreserves
David Gibson9ed27a22007-11-07 11:16:19 +110068%type <addr> addr
David Gibsonfc14dad2005-06-08 17:18:34 +100069%type <data> celllist
David Gibson9ed27a22007-11-07 11:16:19 +110070%type <cbase> cellbase
71%type <cell> cellval
David Gibsonfc14dad2005-06-08 17:18:34 +100072%type <data> bytestring
73%type <prop> propdef
74%type <proplist> proplist
75
David Gibsonf0517db2005-07-15 17:14:24 +100076%type <node> devicetree
David Gibsonfc14dad2005-06-08 17:18:34 +100077%type <node> nodedef
78%type <node> subnode
79%type <nodelist> subnodes
David Gibson9ed27a22007-11-07 11:16:19 +110080%type <labelref> label
David Gibson4102d842005-06-16 14:36:37 +100081
David Gibsonfc14dad2005-06-08 17:18:34 +100082%%
83
Jon Loeliger30807ca2007-10-18 09:42:16 -050084sourcefile:
David Gibson9138db52007-11-07 11:17:17 +110085 DT_V1 ';' memreserves devicetree
86 {
87 the_boot_info = build_boot_info($3, $4);
88 }
89 | v0_memreserves devicetree
Jon Loeliger30807ca2007-10-18 09:42:16 -050090 {
David Gibsonf0517db2005-07-15 17:14:24 +100091 the_boot_info = build_boot_info($1, $2);
92 }
93 ;
94
Jon Loeliger30807ca2007-10-18 09:42:16 -050095memreserves:
Jon Loeliger56412892007-10-23 09:28:54 -050096 /* empty */
Jon Loeliger30807ca2007-10-18 09:42:16 -050097 {
David Gibsonf040d952005-10-24 18:18:38 +100098 $$ = NULL;
David Gibsonf0517db2005-07-15 17:14:24 +100099 }
Jon Loeliger56412892007-10-23 09:28:54 -0500100 | memreserve memreserves
101 {
102 $$ = chain_reserve_entry($1, $2);
103 }
David Gibsonf0517db2005-07-15 17:14:24 +1000104 ;
105
Jon Loeliger30807ca2007-10-18 09:42:16 -0500106memreserve:
David Gibson9ed27a22007-11-07 11:16:19 +1100107 label DT_MEMRESERVE addr addr ';'
Jon Loeliger30807ca2007-10-18 09:42:16 -0500108 {
Milton Millerd4290332007-07-07 01:18:49 -0500109 $$ = build_reserve_entry($3, $4, $1);
David Gibsonf0517db2005-07-15 17:14:24 +1000110 }
David Gibson9138db52007-11-07 11:17:17 +1100111 ;
112
113v0_memreserves:
114 /* empty */
115 {
116 $$ = NULL;
117 }
118 | v0_memreserve v0_memreserves
119 {
120 $$ = chain_reserve_entry($1, $2);
121 };
122 ;
123
124v0_memreserve:
125 memreserve
126 {
127 $$ = $1;
128 }
David Gibson9ed27a22007-11-07 11:16:19 +1100129 | label DT_MEMRESERVE addr '-' addr ';'
Jon Loeliger30807ca2007-10-18 09:42:16 -0500130 {
Milton Millerd4290332007-07-07 01:18:49 -0500131 $$ = build_reserve_entry($3, $5 - $3 + 1, $1);
David Gibsonf0517db2005-07-15 17:14:24 +1000132 }
133 ;
134
David Gibson9ed27a22007-11-07 11:16:19 +1100135addr:
136 DT_LITERAL
137 {
David Gibson9138db52007-11-07 11:17:17 +1100138 $$ = eval_literal($1, 0, 64);
139 }
140 | DT_LEGACYLITERAL
141 {
David Gibson9ed27a22007-11-07 11:16:19 +1100142 $$ = eval_literal($1, 16, 64);
143 }
144 ;
145
Jon Loeliger30807ca2007-10-18 09:42:16 -0500146devicetree:
147 '/' nodedef
148 {
David Gibsonf0517db2005-07-15 17:14:24 +1000149 $$ = name_node($2, "", NULL);
150 }
David Gibsonfc14dad2005-06-08 17:18:34 +1000151 ;
152
Jon Loeliger30807ca2007-10-18 09:42:16 -0500153nodedef:
154 '{' proplist subnodes '}' ';'
155 {
David Gibsonfc14dad2005-06-08 17:18:34 +1000156 $$ = build_node($2, $3);
157 }
158 ;
159
Jon Loeliger30807ca2007-10-18 09:42:16 -0500160proplist:
Jon Loeliger56412892007-10-23 09:28:54 -0500161 /* empty */
Jon Loeliger30807ca2007-10-18 09:42:16 -0500162 {
David Gibsonfc14dad2005-06-08 17:18:34 +1000163 $$ = NULL;
164 }
Jon Loeliger7b3fb782007-10-22 16:09:56 -0500165 | proplist propdef
Jon Loeliger56412892007-10-23 09:28:54 -0500166 {
Jon Loeliger7b3fb782007-10-22 16:09:56 -0500167 $$ = chain_property($2, $1);
Jon Loeliger56412892007-10-23 09:28:54 -0500168 }
David Gibsonfc14dad2005-06-08 17:18:34 +1000169 ;
170
Jon Loeliger30807ca2007-10-18 09:42:16 -0500171propdef:
David Gibson9ed27a22007-11-07 11:16:19 +1100172 label DT_PROPNODENAME '=' propdata ';'
Jon Loeliger30807ca2007-10-18 09:42:16 -0500173 {
David Gibson4102d842005-06-16 14:36:37 +1000174 $$ = build_property($2, $4, $1);
David Gibsonfc14dad2005-06-08 17:18:34 +1000175 }
David Gibson9ed27a22007-11-07 11:16:19 +1100176 | label DT_PROPNODENAME ';'
Jon Loeliger30807ca2007-10-18 09:42:16 -0500177 {
David Gibson9ad45872005-06-17 14:32:32 +1000178 $$ = build_property($2, empty_data, $1);
David Gibsonfc14dad2005-06-08 17:18:34 +1000179 }
180 ;
181
Jon Loeliger30807ca2007-10-18 09:42:16 -0500182propdata:
183 propdataprefix DT_STRING
184 {
185 $$ = data_merge($1, $2);
David Gibson32da4752007-02-07 16:37:50 +1100186 }
Jon Loeliger30807ca2007-10-18 09:42:16 -0500187 | propdataprefix '<' celllist '>'
188 {
David Gibsonf7497dc2007-11-02 16:54:26 +1100189 $$ = data_merge($1, $3);
Jon Loeliger30807ca2007-10-18 09:42:16 -0500190 }
191 | propdataprefix '[' bytestring ']'
192 {
193 $$ = data_merge($1, $3);
194 }
David Gibsonefbbef82007-12-05 10:43:50 +1100195 | propdataprefix DT_REF
196 {
197 $$ = data_add_marker($1, REF_PATH, $2);
198 }
Jon Loeliger30807ca2007-10-18 09:42:16 -0500199 | propdata DT_LABEL
200 {
David Gibsondc941772007-11-22 14:39:23 +1100201 $$ = data_add_marker($1, LABEL, $2);
Jon Loeliger30807ca2007-10-18 09:42:16 -0500202 }
David Gibson32da4752007-02-07 16:37:50 +1100203 ;
204
Jon Loeliger30807ca2007-10-18 09:42:16 -0500205propdataprefix:
Jon Loeliger56412892007-10-23 09:28:54 -0500206 /* empty */
207 {
208 $$ = empty_data;
209 }
210 | propdata ','
Jon Loeliger30807ca2007-10-18 09:42:16 -0500211 {
212 $$ = $1;
213 }
214 | propdataprefix DT_LABEL
215 {
David Gibsondc941772007-11-22 14:39:23 +1100216 $$ = data_add_marker($1, LABEL, $2);
Jon Loeliger30807ca2007-10-18 09:42:16 -0500217 }
David Gibsonfc14dad2005-06-08 17:18:34 +1000218 ;
219
Jon Loeliger30807ca2007-10-18 09:42:16 -0500220celllist:
Jon Loeliger56412892007-10-23 09:28:54 -0500221 /* empty */
222 {
223 $$ = empty_data;
224 }
David Gibson9ed27a22007-11-07 11:16:19 +1100225 | celllist cellval
Jon Loeliger30807ca2007-10-18 09:42:16 -0500226 {
David Gibson9ed27a22007-11-07 11:16:19 +1100227 $$ = data_append_cell($1, $2);
Jon Loeligeraf0278a2007-02-15 10:59:27 -0600228 }
Jon Loeliger30807ca2007-10-18 09:42:16 -0500229 | celllist DT_REF
230 {
David Gibsondc941772007-11-22 14:39:23 +1100231 $$ = data_append_cell(data_add_marker($1, REF_PHANDLE,
232 $2), -1);
David Gibson81f2e892005-06-16 17:04:00 +1000233 }
Jon Loeliger30807ca2007-10-18 09:42:16 -0500234 | celllist DT_LABEL
235 {
David Gibsondc941772007-11-22 14:39:23 +1100236 $$ = data_add_marker($1, LABEL, $2);
Jon Loeliger30807ca2007-10-18 09:42:16 -0500237 }
David Gibsonfc14dad2005-06-08 17:18:34 +1000238 ;
239
David Gibson9ed27a22007-11-07 11:16:19 +1100240cellbase:
241 /* empty */
242 {
243 $$ = 16;
244 }
245 | DT_BASE
246 ;
247
248cellval:
David Gibson9138db52007-11-07 11:17:17 +1100249 DT_LITERAL
250 {
251 $$ = eval_literal($1, 0, 32);
252 }
253 | cellbase DT_LEGACYLITERAL
David Gibson9ed27a22007-11-07 11:16:19 +1100254 {
255 $$ = eval_literal($2, $1, 32);
256 }
257 ;
258
Jon Loeliger30807ca2007-10-18 09:42:16 -0500259bytestring:
Jon Loeliger56412892007-10-23 09:28:54 -0500260 /* empty */
261 {
262 $$ = empty_data;
263 }
264 | bytestring DT_BYTE
Jon Loeliger30807ca2007-10-18 09:42:16 -0500265 {
266 $$ = data_append_byte($1, $2);
267 }
268 | bytestring DT_LABEL
269 {
David Gibsondc941772007-11-22 14:39:23 +1100270 $$ = data_add_marker($1, LABEL, $2);
Jon Loeliger30807ca2007-10-18 09:42:16 -0500271 }
David Gibsonfc14dad2005-06-08 17:18:34 +1000272 ;
273
Jon Loeliger30807ca2007-10-18 09:42:16 -0500274subnodes:
Jon Loeliger56412892007-10-23 09:28:54 -0500275 /* empty */
Jon Loeliger30807ca2007-10-18 09:42:16 -0500276 {
277 $$ = NULL;
278 }
Jon Loeliger56412892007-10-23 09:28:54 -0500279 | subnode subnodes
280 {
281 $$ = chain_node($1, $2);
282 }
David Gibsonc0481022007-12-05 10:27:04 +1100283 | subnode propdef
284 {
285 yyerror("syntax error: properties must precede subnodes\n");
286 YYERROR;
287 }
David Gibsonfc14dad2005-06-08 17:18:34 +1000288 ;
289
Jon Loeliger30807ca2007-10-18 09:42:16 -0500290subnode:
David Gibson9ed27a22007-11-07 11:16:19 +1100291 label DT_PROPNODENAME nodedef
Jon Loeliger30807ca2007-10-18 09:42:16 -0500292 {
293 $$ = name_node($3, $2, $1);
294 }
David Gibson4102d842005-06-16 14:36:37 +1000295 ;
296
Jon Loeliger30807ca2007-10-18 09:42:16 -0500297label:
Jon Loeliger56412892007-10-23 09:28:54 -0500298 /* empty */
Jon Loeliger30807ca2007-10-18 09:42:16 -0500299 {
300 $$ = NULL;
301 }
Jon Loeliger56412892007-10-23 09:28:54 -0500302 | DT_LABEL
303 {
304 $$ = $1;
305 }
David Gibsonfc14dad2005-06-08 17:18:34 +1000306 ;
307
308%%
309
Scott Woodf77fe6a2008-01-03 17:43:29 -0600310void yyerrorf(char const *s, ...)
David Gibsonfc14dad2005-06-08 17:18:34 +1000311{
Scott Wood910efac2008-01-03 17:43:31 -0600312 const char *fname = srcpos_file ? srcpos_file->name : "<no-file>";
Scott Woodf77fe6a2008-01-03 17:43:29 -0600313 va_list va;
314 va_start(va, s);
Jon Loeligere45e6fd2007-03-23 15:18:41 -0500315
316 if (strcmp(fname, "-") == 0)
317 fname = "stdin";
318
Scott Woodf77fe6a2008-01-03 17:43:29 -0600319 fprintf(stderr, "%s:%d ", fname, yylloc.first_line);
320 vfprintf(stderr, s, va);
321 fprintf(stderr, "\n");
322
323 va_end(va);
324}
325
326void yyerror (char const *s)
327{
328 yyerrorf("%s", s);
David Gibsonfc14dad2005-06-08 17:18:34 +1000329}
Jon Loeliger39488492007-02-16 09:33:54 -0600330
David Gibson9ed27a22007-11-07 11:16:19 +1100331unsigned long long eval_literal(const char *s, int base, int bits)
Jon Loeliger39488492007-02-16 09:33:54 -0600332{
David Gibson9ed27a22007-11-07 11:16:19 +1100333 unsigned long long val;
Milton Miller85ab5cc2007-07-07 01:18:48 -0500334 char *e;
Jon Loeliger39488492007-02-16 09:33:54 -0600335
David Gibson9ed27a22007-11-07 11:16:19 +1100336 errno = 0;
337 val = strtoull(s, &e, base);
338 if (*e)
339 yyerror("bad characters in literal");
340 else if ((errno == ERANGE)
341 || ((bits < 64) && (val >= (1ULL << bits))))
342 yyerror("literal out of range");
343 else if (errno != 0)
344 yyerror("bad literal");
345 return val;
Jon Loeliger39488492007-02-16 09:33:54 -0600346}