* gdbtypes.c (check_stub_method): Make sure we get back a function
[deliverable/binutils-gdb.git] / ld / ldexp.c
CommitLineData
c611e285 1/* This module handles expression trees.
1abb243d 2Copyright (C) 1991, 1993, 1994, 1995 Free Software Foundation, Inc.
c611e285 3Written by Steve Chamberlain of Cygnus Support (sac@cygnus.com).
2fa0b342
DHW
4
5This file is part of GLD, the Gnu Linker.
6
7GLD is free software; you can redistribute it and/or modify
8it under the terms of the GNU General Public License as published by
c611e285 9the Free Software Foundation; either version 2, or (at your option)
2fa0b342
DHW
10any later version.
11
12GLD is distributed in the hope that it will be useful,
13but WITHOUT ANY WARRANTY; without even the implied warranty of
14MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15GNU General Public License for more details.
16
17You should have received a copy of the GNU General Public License
18along with GLD; see the file COPYING. If not, write to
19the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
20
21/*
c611e285 22This module is in charge of working out the contents of expressions.
2fa0b342 23
c611e285
SC
24It has to keep track of the relative/absness of a symbol etc. This is
25done by keeping all values in a struct (an etree_value_type) which
26contains a value, a section to which it is relative and a valid bit.
27
28*/
2fa0b342
DHW
29
30
2fa0b342 31#include "bfd.h"
c611e285 32#include "sysdep.h"
31ddb156 33#include "bfdlink.h"
2fa0b342
DHW
34
35#include "ld.h"
36#include "ldmain.h"
37#include "ldmisc.h"
38#include "ldexp.h"
c611e285 39#include "ldgram.h"
2fa0b342
DHW
40#include "ldlang.h"
41
31ddb156
ILT
42static void exp_print_token PARAMS ((token_code_type code));
43static void make_abs PARAMS ((etree_value_type *ptr));
44static etree_value_type new_abs PARAMS ((bfd_vma value));
45static void check PARAMS ((lang_output_section_statement_type *os,
46 const char *name, const char *op));
47static etree_value_type new_rel
48 PARAMS ((bfd_vma value, lang_output_section_statement_type *section));
49static etree_value_type new_rel_from_section
50 PARAMS ((bfd_vma value, lang_output_section_statement_type *section));
51static etree_value_type fold_binary
52 PARAMS ((etree_type *tree,
53 lang_output_section_statement_type *current_section,
54 lang_phase_type allocation_done,
55 bfd_vma dot, bfd_vma *dotp));
56static etree_value_type fold_name
57 PARAMS ((etree_type *tree,
58 lang_output_section_statement_type *current_section,
59 lang_phase_type allocation_done,
60 bfd_vma dot));
61static etree_value_type exp_fold_tree_no_dot
62 PARAMS ((etree_type *tree,
63 lang_output_section_statement_type *current_section,
64 lang_phase_type allocation_done));
65
2fa0b342 66static void
8bf66be8
DM
67exp_print_token (code)
68 token_code_type code;
2fa0b342 69{
31ddb156
ILT
70 static CONST struct
71 {
72 token_code_type code;
73 char *name;
74 } table[] =
c611e285 75 {
31ddb156
ILT
76 { INT, "int" },
77 { REL, "relocateable" },
78 { NAME,"NAME" },
79 { PLUSEQ,"+=" },
80 { MINUSEQ,"-=" },
81 { MULTEQ,"*=" },
82 { DIVEQ,"/=" },
83 { LSHIFTEQ,"<<=" },
84 { RSHIFTEQ,">>=" },
85 { ANDEQ,"&=" },
86 { OREQ,"|=" },
87 { OROR,"||" },
88 { ANDAND,"&&" },
89 { EQ,"==" },
90 { NE,"!=" },
91 { LE,"<=" },
92 { GE,">=" },
93 { LSHIFT,"<<" },
94 { RSHIFT,">>=" },
95 { ALIGN_K,"ALIGN" },
96 { BLOCK,"BLOCK" },
97 { SECTIONS,"SECTIONS" },
98 { SIZEOF_HEADERS,"SIZEOF_HEADERS" },
99 { NEXT,"NEXT" },
100 { SIZEOF,"SIZEOF" },
101 { ADDR,"ADDR" },
102 { MEMORY,"MEMORY" },
103 { DEFINED,"DEFINED" },
104 { TARGET_K,"TARGET" },
105 { SEARCH_DIR,"SEARCH_DIR" },
106 { MAP,"MAP" },
107 { QUAD,"QUAD" },
108 { LONG,"LONG" },
109 { SHORT,"SHORT" },
110 { BYTE,"BYTE" },
111 { ENTRY,"ENTRY" },
112 { 0,(char *)NULL }
113 };
2fa0b342 114 unsigned int idx;
31ddb156 115
2fa0b342
DHW
116 for (idx = 0; table[idx].name != (char*)NULL; idx++) {
117 if (table[idx].code == code) {
2e2bf962 118 fprintf(config.map_file, "%s", table[idx].name);
2fa0b342
DHW
119 return;
120 }
121 }
122 /* Not in table, just print it alone */
2e2bf962 123 fprintf(config.map_file, "%c",code);
2fa0b342
DHW
124}
125
126static void
8bf66be8
DM
127make_abs (ptr)
128 etree_value_type *ptr;
2fa0b342 129{
2fa0b342
DHW
130 asection *s = ptr->section->bfd_section;
131 ptr->value += s->vma;
76971f0d 132 ptr->section = abs_output_section;
2fa0b342 133}
c611e285 134
8bf66be8
DM
135static etree_value_type
136new_abs (value)
137 bfd_vma value;
2fa0b342
DHW
138{
139 etree_value_type new;
140 new.valid = true;
76971f0d 141 new.section = abs_output_section;
2fa0b342
DHW
142 new.value = value;
143 return new;
144}
145
3a399523 146static void
8bf66be8
DM
147check (os, name, op)
148 lang_output_section_statement_type *os;
149 CONST char *name;
150 CONST char *op;
2fa0b342
DHW
151{
152 if (os == (lang_output_section_statement_type *)NULL) {
fcf276c4 153 einfo("%F%P: %s uses undefined section %s\n", op, name);
2fa0b342
DHW
154 }
155 if (os->processed == false) {
fcf276c4 156 einfo("%F%P: %s forward reference of section %s\n",op, name);
2fa0b342
DHW
157 }
158}
159
c611e285 160etree_type *
8bf66be8
DM
161exp_intop (value)
162 bfd_vma value;
2fa0b342 163{
bfbdc80f 164 etree_type *new = (etree_type *)stat_alloc((bfd_size_type)(sizeof(new->value)));
2fa0b342
DHW
165 new->type.node_code = INT;
166 new->value.value = value;
167 new->type.node_class = etree_value;
168 return new;
169
170}
171
31ddb156
ILT
172/* Build an expression representing an unnamed relocateable value. */
173
174etree_type *
175exp_relop (section, value)
176 asection *section;
177 bfd_vma value;
178{
179 etree_type *new = (etree_type *) stat_alloc (sizeof (new->rel));
180 new->type.node_code = REL;
181 new->type.node_class = etree_rel;
182 new->rel.section = section;
183 new->rel.value = value;
184 return new;
185}
2fa0b342 186
8bf66be8
DM
187static etree_value_type
188new_rel (value, section)
189 bfd_vma value;
190 lang_output_section_statement_type *section;
2fa0b342
DHW
191{
192 etree_value_type new;
193 new.valid = true;
194 new.value = value;
195 new.section = section;
196 return new;
197}
198
8bf66be8
DM
199static etree_value_type
200new_rel_from_section (value, section)
201 bfd_vma value;
202 lang_output_section_statement_type *section;
2fa0b342
DHW
203{
204 etree_value_type new;
205 new.valid = true;
206 new.value = value;
207 new.section = section;
76971f0d 208
2fa0b342 209 new.value -= section->bfd_section->vma;
76971f0d 210
2fa0b342
DHW
211 return new;
212}
213
214static etree_value_type
8bf66be8
DM
215fold_binary (tree, current_section, allocation_done, dot, dotp)
216 etree_type *tree;
217 lang_output_section_statement_type *current_section;
1abb243d 218 lang_phase_type allocation_done;
8bf66be8
DM
219 bfd_vma dot;
220 bfd_vma *dotp;
2fa0b342
DHW
221{
222 etree_value_type result;
223
1abb243d 224 result = exp_fold_tree (tree->binary.lhs, current_section,
2fa0b342 225 allocation_done, dot, dotp);
1abb243d
ILT
226 if (result.valid)
227 {
228 etree_value_type other;
229
230 other = exp_fold_tree (tree->binary.rhs,
231 current_section,
232 allocation_done, dot,dotp) ;
233 if (other.valid)
2fa0b342 234 {
1abb243d
ILT
235 /* If the values are from different sections, or this is an
236 absolute expression, make both the source arguments
237 absolute. However, adding or subtracting an absolute
238 value from a relative value is meaningful, and is an
239 exception. */
240 if (current_section != abs_output_section
241 && (result.section == abs_output_section
242 || other.section == abs_output_section)
243 && (tree->type.node_code == '+'
244 || tree->type.node_code == '-'))
245 {
246 etree_value_type hold;
2fa0b342 247
1abb243d
ILT
248 /* If there is only one absolute term, make sure it is the
249 second one. */
250 if (result.section == abs_output_section)
251 {
252 hold = result;
253 result = other;
254 other = hold;
255 }
256 }
257 else if (result.section != other.section
258 || current_section == abs_output_section)
259 {
260 make_abs(&result);
261 make_abs(&other);
262 }
263
264 switch (tree->type.node_code)
265 {
266 case '%':
267 if (other.value == 0)
268 einfo ("%F%S %% by zero\n");
269 result.value = ((bfd_signed_vma) result.value
270 % (bfd_signed_vma) other.value);
271 break;
272
273 case '/':
274 if (other.value == 0)
275 einfo ("%F%S / by zero\n");
276 result.value = ((bfd_signed_vma) result.value
277 / (bfd_signed_vma) other.value);
278 break;
279
280#define BOP(x,y) case x : result.value = result.value y other.value; break;
281 BOP('+',+);
282 BOP('*',*);
283 BOP('-',-);
284 BOP(LSHIFT,<<);
285 BOP(RSHIFT,>>);
286 BOP(EQ,==);
287 BOP(NE,!=);
288 BOP('<',<);
289 BOP('>',>);
290 BOP(LE,<=);
291 BOP(GE,>=);
292 BOP('&',&);
293 BOP('^',^);
294 BOP('|',|);
295 BOP(ANDAND,&&);
296 BOP(OROR,||);
297
298 default:
299 FAIL();
300 }
301 }
302 else
303 {
304 result.valid = false;
2fa0b342
DHW
305 }
306 }
1abb243d 307
2fa0b342
DHW
308 return result;
309}
1abb243d 310
c611e285 311etree_value_type
8bf66be8 312invalid ()
2fa0b342
DHW
313{
314 etree_value_type new;
315 new.valid = false;
316 return new;
317}
318
31ddb156 319static etree_value_type
8bf66be8
DM
320fold_name (tree, current_section, allocation_done, dot)
321 etree_type *tree;
322 lang_output_section_statement_type *current_section;
323 lang_phase_type allocation_done;
324 bfd_vma dot;
2fa0b342
DHW
325{
326 etree_value_type result;
327 switch (tree->type.node_code)
ac004870 328 {
65c552e3
SC
329 case SIZEOF_HEADERS:
330 if (allocation_done != lang_first_phase_enum)
31ddb156
ILT
331 {
332 result = new_abs ((bfd_vma)
333 bfd_sizeof_headers (output_bfd,
334 link_info.relocateable));
335 }
336 else
337 {
338 result.valid = false;
339 }
65c552e3 340 break;
ac004870 341 case DEFINED:
1abb243d
ILT
342 if (allocation_done == lang_first_phase_enum)
343 result.valid = false;
344 else
345 {
346 struct bfd_link_hash_entry *h;
347
348 h = bfd_link_hash_lookup (link_info.hash, tree->name.name,
349 false, false, true);
350 result.value = (h != (struct bfd_link_hash_entry *) NULL
351 && (h->type == bfd_link_hash_defined
352 || h->type == bfd_link_hash_common));
353 result.section = 0;
354 result.valid = true;
355 }
ac004870
SC
356 break;
357 case NAME:
358 result.valid = false;
31ddb156
ILT
359 if (tree->name.name[0] == '.' && tree->name.name[1] == 0)
360 {
361 if (allocation_done != lang_first_phase_enum)
362 result = new_rel_from_section(dot, current_section);
363 else
364 result = invalid();
ac004870 365 }
1abb243d 366 else if (allocation_done != lang_first_phase_enum)
31ddb156
ILT
367 {
368 struct bfd_link_hash_entry *h;
369
370 h = bfd_link_hash_lookup (link_info.hash, tree->name.name,
371 false, false, true);
1abb243d 372 if (h != NULL && h->type == bfd_link_hash_defined)
31ddb156 373 {
1abb243d
ILT
374 if (bfd_is_abs_section (h->u.def.section))
375 result = new_abs (h->u.def.value);
376 else if (allocation_done == lang_final_phase_enum)
377 {
378 lang_output_section_statement_type *os;
31ddb156 379
1abb243d
ILT
380 os = (lang_output_section_statement_lookup
381 (h->u.def.section->output_section->name));
382
383 /* FIXME: Is this correct if this section is being
384 linked with -R? */
385 result = new_rel ((h->u.def.value
386 + h->u.def.section->output_offset),
387 os);
388 }
2fa0b342 389 }
1abb243d
ILT
390 else if (allocation_done == lang_final_phase_enum)
391 einfo ("%F%S: undefined symbol `%s' referenced in expression\n",
392 tree->name.name);
ac004870 393 }
ac004870 394 break;
2fa0b342 395
ac004870 396 case ADDR:
2fa0b342 397
ac004870
SC
398 if (allocation_done != lang_first_phase_enum) {
399 lang_output_section_statement_type *os =
400 lang_output_section_find(tree->name.name);
401 check(os,tree->name.name,"ADDR");
402 result = new_rel((bfd_vma)0, os);
403 }
404 else {
405 result = invalid();
406 }
407 break;
408 case SIZEOF:
409 if(allocation_done != lang_first_phase_enum) {
410 lang_output_section_statement_type *os =
411 lang_output_section_find(tree->name.name);
412 check(os,tree->name.name,"SIZEOF");
c611e285 413 result = new_abs((bfd_vma)(os->bfd_section->_raw_size));
ac004870
SC
414 }
415 else {
416 result = invalid();
417 }
418 break;
2fa0b342 419
ac004870
SC
420 default:
421 FAIL();
422 break;
423 }
2fa0b342
DHW
424
425 return result;
426}
c611e285 427etree_value_type
8bf66be8
DM
428exp_fold_tree (tree, current_section, allocation_done, dot, dotp)
429 etree_type *tree;
430 lang_output_section_statement_type *current_section;
431 lang_phase_type allocation_done;
432 bfd_vma dot;
433 bfd_vma *dotp;
2fa0b342
DHW
434{
435 etree_value_type result;
436
437 if (tree == (etree_type *)NULL) {
8bf66be8
DM
438 result.valid = false;
439 }
2fa0b342 440 else {
8bf66be8
DM
441 switch (tree->type.node_class)
442 {
443 case etree_value:
444 result = new_rel(tree->value.value, current_section);
445 break;
31ddb156
ILT
446 case etree_rel:
447 if (allocation_done != lang_final_phase_enum)
448 result.valid = false;
449 else
450 result = new_rel ((tree->rel.value
451 + tree->rel.section->output_section->vma
452 + tree->rel.section->output_offset),
453 current_section);
454 break;
8bf66be8
DM
455 case etree_unary:
456 result = exp_fold_tree(tree->unary.child,
457 current_section,
458 allocation_done, dot, dotp);
459 if (result.valid == true)
c611e285 460 {
8bf66be8 461 switch(tree->type.node_code)
d4c02e29 462 {
8bf66be8
DM
463 case ALIGN_K:
464 if (allocation_done != lang_first_phase_enum) {
465 result = new_rel_from_section(ALIGN_N(dot,
466 result.value) ,
467 current_section);
468
469 }
470 else {
471 result.valid = false;
472 }
473 break;
474 case ABSOLUTE:
475 if (allocation_done != lang_first_phase_enum)
c611e285 476 {
8bf66be8
DM
477 if (current_section
478 == (lang_output_section_statement_type*)NULL)
479 {
480 /* Outside a section, so it's all ok */
d4c02e29 481
8bf66be8 482 }
c611e285 483 else {
8bf66be8
DM
484 /* Inside a section, subtract the base of the section,
485 so when it's added again (in an assignment), everything comes out fine
486 */
487 result.section = abs_output_section;
488 result.value -= current_section->bfd_section->vma;
489 result.valid = true;
490 }
491 }
492 else
493 {
494 result.valid = false;
495 }
496
497 break;
498 case '~':
499 make_abs(&result);
500 result.value = ~result.value;
501 break;
502 case '!':
503 make_abs(&result);
504 result.value = !result.value;
505 break;
506 case '-':
507 make_abs(&result);
508 result.value = -result.value;
509 break;
510 case NEXT:
511 if (allocation_done ==lang_allocating_phase_enum) {
c611e285 512 make_abs(&result);
8bf66be8 513 result.value = ALIGN_N(dot, result.value);
c611e285 514 }
8bf66be8
DM
515 else {
516 /* Return next place aligned to value */
517 result.valid = false;
518 }
519 break;
520 default:
521 FAIL();
c611e285 522 }
8bf66be8 523 }
2fa0b342 524
8bf66be8
DM
525 break;
526 case etree_trinary:
2fa0b342 527
8bf66be8
DM
528 result = exp_fold_tree(tree->trinary.cond,
529 current_section,
530 allocation_done, dot, dotp);
531 if (result.valid) {
532 result = exp_fold_tree(result.value ?
533 tree->trinary.lhs:tree->trinary.rhs,
c611e285
SC
534 current_section,
535 allocation_done, dot, dotp);
8bf66be8 536 }
d4c02e29 537
8bf66be8
DM
538 break;
539 case etree_binary:
540 result = fold_binary(tree, current_section, allocation_done,
541 dot, dotp);
542 break;
543 case etree_assign:
31ddb156 544 case etree_provide:
8bf66be8
DM
545 if (tree->assign.dst[0] == '.' && tree->assign.dst[1] == 0) {
546 /* Assignment to dot can only be done during allocation */
31ddb156
ILT
547 if (tree->type.node_class == etree_provide)
548 einfo ("%F%S can not PROVIDE assignment to location counter\n");
8bf66be8
DM
549 if (allocation_done == lang_allocating_phase_enum) {
550 result = exp_fold_tree(tree->assign.src,
551 current_section,
552 lang_allocating_phase_enum, dot, dotp);
553 if (result.valid == false) {
554 einfo("%F%S invalid assignment to location counter\n");
555 }
556 else {
557 if (current_section ==
558 (lang_output_section_statement_type *)NULL) {
559 einfo("%F%S assignment to location counter invalid outside of SECTION\n");
560 }
561 else {
562 bfd_vma nextdot =result.value +
563 current_section->bfd_section->vma;
564 if (nextdot < dot) {
565 einfo("%F%S cannot move location counter backwards (from %V to %V)\n", dot, nextdot);
566 }
567 else {
568 *dotp = nextdot;
2fa0b342 569 }
8bf66be8 570 }
2fa0b342 571 }
8bf66be8
DM
572 }
573 }
31ddb156 574 else
8bf66be8 575 {
31ddb156
ILT
576 result = exp_fold_tree (tree->assign.src,
577 current_section, allocation_done,
578 dot, dotp);
579 if (result.valid)
580 {
581 struct bfd_link_hash_entry *h;
582
583 h = bfd_link_hash_lookup (link_info.hash, tree->assign.dst,
584 (tree->type.node_class == etree_assign
585 ? true : false),
586 false, false);
587 if (h == (struct bfd_link_hash_entry *) NULL)
588 {
589 if (tree->type.node_class == etree_assign)
590 einfo ("%P%F:%s: hash creation failed\n",
591 tree->assign.dst);
592 }
593 else if (tree->type.node_class == etree_provide
594 && h->type != bfd_link_hash_undefined
595 && h->type != bfd_link_hash_common)
596 {
597 /* Do nothing. The symbol was defined by some
598 object. */
599 }
600 else
601 {
602 /* FIXME: Should we worry if the symbol is already
603 defined? */
604 h->type = bfd_link_hash_defined;
605 h->u.def.value = result.value;
606 h->u.def.section = result.section->bfd_section;
607 }
608 }
609 }
8bf66be8
DM
610 break;
611 case etree_name:
612 result = fold_name(tree, current_section, allocation_done, dot);
613 break;
614 default:
fcf276c4 615 einfo("%F%S need more of these %d\n",tree->type.node_class );
2fa0b342 616
c611e285 617 }
8bf66be8 618 }
2fa0b342
DHW
619
620 return result;
621}
622
623
31ddb156 624static etree_value_type
8bf66be8
DM
625exp_fold_tree_no_dot (tree, current_section, allocation_done)
626 etree_type *tree;
627 lang_output_section_statement_type *current_section;
628 lang_phase_type allocation_done;
2fa0b342
DHW
629{
630return exp_fold_tree(tree, current_section, allocation_done, (bfd_vma)
631 0, (bfd_vma *)NULL);
632}
633
634etree_type *
8bf66be8
DM
635exp_binop (code, lhs, rhs)
636 int code;
637 etree_type *lhs;
638 etree_type *rhs;
2fa0b342
DHW
639{
640 etree_type value, *new;
641 etree_value_type r;
642
643 value.type.node_code = code;
644 value.binary.lhs = lhs;
645 value.binary.rhs = rhs;
646 value.type.node_class = etree_binary;
76971f0d
SC
647 r = exp_fold_tree_no_dot(&value,
648 abs_output_section,
2fa0b342
DHW
649 lang_first_phase_enum );
650 if (r.valid)
651 {
652 return exp_intop(r.value);
653 }
bfbdc80f 654 new = (etree_type *)stat_alloc((bfd_size_type)(sizeof(new->binary)));
2fa0b342
DHW
655 memcpy((char *)new, (char *)&value, sizeof(new->binary));
656 return new;
657}
658
659etree_type *
8bf66be8
DM
660exp_trinop (code, cond, lhs, rhs)
661 int code;
662 etree_type *cond;
663 etree_type *lhs;
664 etree_type *rhs;
2fa0b342
DHW
665{
666 etree_type value, *new;
667 etree_value_type r;
668 value.type.node_code = code;
669 value.trinary.lhs = lhs;
670 value.trinary.cond = cond;
671 value.trinary.rhs = rhs;
672 value.type.node_class = etree_trinary;
673 r= exp_fold_tree_no_dot(&value, (lang_output_section_statement_type
674 *)NULL,lang_first_phase_enum);
675 if (r.valid) {
676 return exp_intop(r.value);
677 }
bfbdc80f 678 new = (etree_type *)stat_alloc((bfd_size_type)(sizeof(new->trinary)));
2fa0b342
DHW
679 memcpy((char *)new,(char *) &value, sizeof(new->trinary));
680 return new;
681}
682
683
684etree_type *
8bf66be8
DM
685exp_unop (code, child)
686 int code;
687 etree_type *child;
2fa0b342
DHW
688{
689 etree_type value, *new;
690
691 etree_value_type r;
692 value.unary.type.node_code = code;
693 value.unary.child = child;
694 value.unary.type.node_class = etree_unary;
8bf66be8 695 r = exp_fold_tree_no_dot(&value,abs_output_section,
c611e285
SC
696 lang_first_phase_enum);
697 if (r.valid) {
2fa0b342
DHW
698 return exp_intop(r.value);
699 }
bfbdc80f 700 new = (etree_type *)stat_alloc((bfd_size_type)(sizeof(new->unary)));
2fa0b342
DHW
701 memcpy((char *)new, (char *)&value, sizeof(new->unary));
702 return new;
703}
704
705
706etree_type *
8bf66be8
DM
707exp_nameop (code, name)
708 int code;
709 CONST char *name;
2fa0b342 710{
2fa0b342 711 etree_type value, *new;
2fa0b342
DHW
712 etree_value_type r;
713 value.name.type.node_code = code;
714 value.name.name = name;
715 value.name.type.node_class = etree_name;
716
717
76971f0d
SC
718 r = exp_fold_tree_no_dot(&value,
719 (lang_output_section_statement_type *)NULL,
720 lang_first_phase_enum);
2fa0b342
DHW
721 if (r.valid) {
722 return exp_intop(r.value);
723 }
bfbdc80f 724 new = (etree_type *)stat_alloc((bfd_size_type)(sizeof(new->name)));
2fa0b342
DHW
725 memcpy((char *)new, (char *)&value, sizeof(new->name));
726 return new;
727
728}
729
730
731
732
733etree_type *
8bf66be8
DM
734exp_assop (code, dst, src)
735 int code;
736 CONST char *dst;
737 etree_type *src;
2fa0b342
DHW
738{
739 etree_type value, *new;
740
741 value.assign.type.node_code = code;
742
743
744 value.assign.src = src;
745 value.assign.dst = dst;
746 value.assign.type.node_class = etree_assign;
747
748#if 0
749 if (exp_fold_tree_no_dot(&value, &result)) {
750 return exp_intop(result);
751 }
752#endif
bfbdc80f 753 new = (etree_type*)stat_alloc((bfd_size_type)(sizeof(new->assign)));
2fa0b342
DHW
754 memcpy((char *)new, (char *)&value, sizeof(new->assign));
755 return new;
756}
757
31ddb156
ILT
758/* Handle PROVIDE. */
759
760etree_type *
761exp_provide (dst, src)
762 const char *dst;
763 etree_type *src;
764{
765 etree_type *n;
766
767 n = (etree_type *) stat_alloc (sizeof (n->assign));
768 n->assign.type.node_code = '=';
769 n->assign.type.node_class = etree_provide;
770 n->assign.src = src;
771 n->assign.dst = dst;
772 return n;
773}
774
2fa0b342 775void
8bf66be8
DM
776exp_print_tree (tree)
777 etree_type *tree;
2fa0b342
DHW
778{
779 switch (tree->type.node_class) {
780 case etree_value:
c611e285 781 print_address(tree->value.value);
2fa0b342 782 return;
31ddb156
ILT
783 case etree_rel:
784 if (tree->rel.section->owner != NULL)
785 fprintf (config.map_file, "%s:",
786 bfd_get_filename (tree->rel.section->owner));
787 fprintf (config.map_file, "%s+", tree->rel.section->name);
788 print_address (tree->rel.value);
789 return;
2fa0b342
DHW
790 case etree_assign:
791#if 0
792 if (tree->assign.dst->sdefs != (asymbol *)NULL){
2e2bf962 793 fprintf(config.map_file,"%s (%x) ",tree->assign.dst->name,
2fa0b342
DHW
794 tree->assign.dst->sdefs->value);
795 }
796 else {
2e2bf962 797 fprintf(config.map_file,"%s (UNDEFINED)",tree->assign.dst->name);
2fa0b342
DHW
798 }
799#endif
2e2bf962
SC
800 fprintf(config.map_file,"%s ",tree->assign.dst);
801 exp_print_token(tree->type.node_code);
802 exp_print_tree(tree->assign.src);
2fa0b342 803 break;
31ddb156
ILT
804 case etree_provide:
805 fprintf (config.map_file, "PROVIDE (%s, ", tree->assign.dst);
806 exp_print_tree (tree->assign.src);
807 fprintf (config.map_file, ")");
808 break;
2fa0b342 809 case etree_binary:
bfbdc80f 810 fprintf(config.map_file,"(");
2e2bf962
SC
811 exp_print_tree(tree->binary.lhs);
812 exp_print_token(tree->type.node_code);
813 exp_print_tree(tree->binary.rhs);
bfbdc80f 814 fprintf(config.map_file,")");
2fa0b342
DHW
815 break;
816 case etree_trinary:
2e2bf962
SC
817 exp_print_tree(tree->trinary.cond);
818 fprintf(config.map_file,"?");
819 exp_print_tree(tree->trinary.lhs);
820 fprintf(config.map_file,":");
821 exp_print_tree(tree->trinary.rhs);
2fa0b342
DHW
822 break;
823 case etree_unary:
2e2bf962 824 exp_print_token(tree->unary.type.node_code);
bfbdc80f
SC
825 if (tree->unary.child)
826 {
827
2e2bf962
SC
828 fprintf(config.map_file,"(");
829 exp_print_tree(tree->unary.child);
830 fprintf(config.map_file,")");
bfbdc80f
SC
831 }
832
2fa0b342
DHW
833 break;
834 case etree_undef:
2e2bf962 835 fprintf(config.map_file,"????????");
2fa0b342
DHW
836 break;
837 case etree_name:
838 if (tree->type.node_code == NAME) {
2e2bf962 839 fprintf(config.map_file,"%s", tree->name.name);
2fa0b342
DHW
840 }
841 else {
2e2bf962 842 exp_print_token(tree->type.node_code);
bfbdc80f 843 if (tree->name.name)
2e2bf962 844 fprintf(config.map_file,"(%s)", tree->name.name);
2fa0b342
DHW
845 }
846 break;
847 default:
848 FAIL();
849 break;
850 }
851}
852
853
854
855
856bfd_vma
8bf66be8
DM
857exp_get_vma (tree, def, name, allocation_done)
858 etree_type *tree;
859 bfd_vma def;
860 char *name;
861 lang_phase_type allocation_done;
2fa0b342
DHW
862{
863 etree_value_type r;
864
865 if (tree != (etree_type *)NULL) {
866 r = exp_fold_tree_no_dot(tree,
bfbdc80f 867 abs_output_section,
2fa0b342
DHW
868 allocation_done);
869 if (r.valid == false && name) {
fcf276c4 870 einfo("%F%S nonconstant expression for %s\n",name);
2fa0b342
DHW
871 }
872 return r.value;
873 }
874 else {
875 return def;
876 }
877}
878
879int
8bf66be8
DM
880exp_get_value_int (tree,def,name, allocation_done)
881 etree_type *tree;
882 int def;
883 char *name;
884 lang_phase_type allocation_done;
2fa0b342
DHW
885{
886 return (int)exp_get_vma(tree,(bfd_vma)def,name, allocation_done);
887}
65c552e3 888
1abb243d
ILT
889
890int
891exp_get_abs_int (tree, def, name, allocation_done)
892 etree_type *tree;
893 int def;
894 char *name;
895 lang_phase_type allocation_done;
896{
897 etree_value_type res;
898 res = exp_fold_tree_no_dot (tree, abs_output_section, allocation_done);
899
900 if (res.valid)
901 {
902 res.value += res.section->bfd_section->vma;
903 }
904 else {
905 einfo ("%F%S non constant expression for %s\n",name);
906 }
907 return res.value;
908}
This page took 0.287792 seconds and 4 git commands to generate.