*** empty log message ***
[deliverable/binutils-gdb.git] / ld / ldexp.c
1 /* Copyright (C) 1991 Free Software Foundation, Inc.
2
3 This file is part of GLD, the Gnu Linker.
4
5 GLD is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 1, or (at your option)
8 any later version.
9
10 GLD 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
13 GNU General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with GLD; see the file COPYING. If not, write to
17 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
18
19 /*
20 $Id$
21
22 $Log$
23 Revision 1.1 1991/03/21 21:28:34 gumby
24 Initial revision
25
26 * Revision 1.1 1991/03/13 00:48:16 chrisb
27 * Initial revision
28 *
29 * Revision 1.6 1991/03/10 09:31:22 rich
30 * Modified Files:
31 * Makefile config.h ld-emul.c ld-emul.h ld-gld.c ld-gld960.c
32 * ld-lnk960.c ld.h lddigest.c ldexp.c ldexp.h ldfile.c ldfile.h
33 * ldgram.y ldinfo.h ldlang.c ldlang.h ldlex.h ldlex.l ldmain.c
34 * ldmain.h ldmisc.c ldmisc.h ldsym.c ldsym.h ldversion.c
35 * ldversion.h ldwarn.h ldwrite.c ldwrite.h y.tab.h
36 *
37 * As of this round of changes, ld now builds on all hosts of (Intel960)
38 * interest and copy passes my copy test on big endian hosts again.
39 *
40 * Revision 1.5 1991/03/09 03:25:04 sac
41 * Added support for LONG, SHORT and BYTE keywords in scripts
42 *
43 * Revision 1.4 1991/03/06 02:27:15 sac
44 * Added LONG, SHORT and BYTE keywords
45 *
46 * Revision 1.3 1991/02/22 17:14:59 sac
47 * Added RCS keywords and copyrights
48 *
49 */
50
51 /*
52 * Written by Steve Chamberlain
53 * steve@cygnus.com
54 *
55 * This module handles expression trees.
56 */
57
58
59 #include "sysdep.h"
60 #include "bfd.h"
61
62 #include "ld.h"
63 #include "ldmain.h"
64 #include "ldmisc.h"
65 #include "ldexp.h"
66 #include "ldgram.tab.h"
67 #include "ldsym.h"
68 #include "ldlang.h"
69
70 extern char *output_filename;
71 extern unsigned int undefined_global_sym_count;
72 extern unsigned int defined_global_sym_count;
73 extern bfd *output_bfd;
74 extern size_t largest_section;
75 extern lang_statement_list_type file_chain;
76 extern args_type command_line;
77 extern ld_config_type config;
78
79 extern lang_input_statement_type *script_file;
80 extern unsigned int defined_global_sym_count;
81
82 extern bfd_vma print_dot;
83
84
85 static void
86 exp_print_token(outfile, code)
87 FILE *outfile;
88 token_code_type code;
89 {
90 static struct {
91 token_code_type code;
92 char *name;
93 } table[] =
94 {
95 INT, "int",
96 CHAR,"char",
97 NAME,"NAME",
98 PLUSEQ,"+=",
99 MINUSEQ,"-=",
100 MULTEQ,"*=",
101 DIVEQ,"/=",
102 LSHIFTEQ,"<<=",
103 RSHIFTEQ,">>=",
104 ANDEQ,"&=",
105 OREQ,"|=",
106 OROR,"||",
107 ANDAND,"&&",
108 EQ,"==",
109 NE,"!=",
110 LE,"<=",
111 GE,">=",
112 LSHIFT,"<<",
113 RSHIFT,">>=",
114 ALIGN_K,"ALIGN",
115 BLOCK,"BLOCK",
116 SECTIONS,"SECTIONS",
117 ALIGNMENT,"ALIGNMENT",
118 SIZEOF_HEADERS,"SIZEOF_HEADERS",
119 NEXT,"NEXT",
120 SIZEOF,"SIZEOF",
121 ADDR,"ADDR",
122 MEMORY,"MEMORY",
123 DSECT,"DSECT",
124 NOLOAD,"NOLOAD",
125 COPY,"COPY",
126 INFO,"INFO",
127 OVERLAY,"OVERLAY",
128 DEFINED,"DEFINED",
129 TARGET_K,"TARGET",
130 SEARCH_DIR,"SEARCH_DIR",
131 MAP,"MAP",
132 LONG,"LONG",
133 SHORT,"SHORT",
134 BYTE,"BYTE",
135 ENTRY,"ENTRY",
136 0,(char *)NULL} ;
137
138
139
140 unsigned int idx;
141 for (idx = 0; table[idx].name != (char*)NULL; idx++) {
142 if (table[idx].code == code) {
143 fprintf(outfile, "%s", table[idx].name);
144 return;
145 }
146 }
147 /* Not in table, just print it alone */
148 fprintf(outfile, "%c",code);
149 }
150
151 static void
152 make_abs(ptr)
153 etree_value_type *ptr;
154 {
155 if (ptr->section != (lang_output_section_statement_type *)NULL) {
156 asection *s = ptr->section->bfd_section;
157 ptr->value += s->vma;
158 ptr->section = (lang_output_section_statement_type *)NULL;
159 }
160
161 }
162 static
163 etree_value_type new_abs(value)
164 bfd_vma value;
165 {
166 etree_value_type new;
167 new.valid = true;
168 new.section = (lang_output_section_statement_type *)NULL;
169 new.value = value;
170 return new;
171 }
172
173 static void check(os)
174 lang_output_section_statement_type *os;
175 {
176 if (os == (lang_output_section_statement_type *)NULL) {
177 info("%F%P undefined section");
178 }
179 if (os->processed == false) {
180 info("%F%P forward reference of section");
181 }
182 }
183
184 etree_type *exp_intop(value)
185 bfd_vma value;
186 {
187 etree_type *new = (etree_type *)ldmalloc(sizeof(new->value));
188 new->type.node_code = INT;
189 new->value.value = value;
190 new->type.node_class = etree_value;
191 return new;
192
193 }
194
195
196 static
197 etree_value_type new_rel(value, section)
198 bfd_vma value;
199 lang_output_section_statement_type *section;
200 {
201 etree_value_type new;
202 new.valid = true;
203 new.value = value;
204 new.section = section;
205 return new;
206 }
207
208 static
209 etree_value_type new_rel_from_section(value, section)
210 bfd_vma value;
211 lang_output_section_statement_type *section;
212 {
213 etree_value_type new;
214 new.valid = true;
215 new.value = value;
216 new.section = section;
217 if (new.section != (lang_output_section_statement_type *)NULL) {
218 new.value -= section->bfd_section->vma;
219 }
220 return new;
221 }
222
223 static etree_value_type
224 fold_binary(tree, current_section, allocation_done, dot, dotp)
225 etree_type *tree;
226 lang_output_section_statement_type *current_section;
227 lang_phase_type allocation_done;
228 bfd_vma dot;
229 bfd_vma *dotp;
230 {
231 etree_value_type result;
232
233 result = exp_fold_tree(tree->binary.lhs, current_section,
234 allocation_done, dot, dotp);
235 if (result.valid) {
236 etree_value_type other;
237 other = exp_fold_tree(tree->binary.rhs,
238 current_section,
239 allocation_done, dot,dotp) ;
240 if (other.valid) {
241 /* If values are from different sections, or this is an */
242 /* absolute expression, make both source args absolute */
243 if (result.section != other.section ||
244 current_section == (lang_output_section_statement_type *)NULL) {
245
246 make_abs(&result);
247 make_abs(&other);
248 }
249
250 switch (tree->type.node_code)
251 {
252 case '%':
253 /* Mod, both absolule*/
254
255 if (other.value == 0) {
256 info("%F%S % by zero\n");
257 }
258 result.value %= other.value;
259 break;
260 case '/':
261 if (other.value == 0) {
262 info("%F%S / by zero\n");
263 }
264 result.value /= other.value;
265 break;
266 #define BOP(x,y) case x : result.value = result.value y other.value;break;
267 BOP('+',+);
268 BOP('*',*);
269 BOP('-',-);
270 BOP(LSHIFT,<<);
271 BOP(RSHIFT,>>);
272 BOP(EQ,==);
273 BOP(NE,!=);
274 BOP('<',<);
275 BOP('>',>);
276 BOP(LE,<=);
277 BOP(GE,>=);
278 BOP('&',&);
279 BOP('^',^);
280 BOP('|',|);
281 BOP(ANDAND,&&);
282 BOP(OROR,||);
283 default:
284 FAIL();
285 }
286 }
287 }
288 return result;
289 }
290 etree_value_type invalid()
291 {
292 etree_value_type new;
293 new.valid = false;
294 return new;
295 }
296
297 etree_value_type fold_name(tree, current_section, allocation_done, dot)
298 etree_type *tree;
299 lang_output_section_statement_type *current_section;
300 lang_phase_type allocation_done;
301 bfd_vma dot;
302
303 {
304 etree_value_type result;
305 switch (tree->type.node_code)
306 {
307 case DEFINED:
308 result.value =
309 ldsym_get_soft(tree->name.name) != (ldsym_type *)NULL;
310 result.section = 0;
311 result.valid = true;
312 break;
313 case NAME:
314 result.valid = false;
315 if (tree->name.name[0] == '.' && tree->name.name[1] == 0) {
316
317 if (allocation_done != lang_first_phase_enum) {
318 result = new_rel_from_section(dot, current_section);
319 }
320 else {
321 result = invalid();
322 }
323 }
324 else {
325 if (allocation_done == lang_final_phase_enum) {
326 ldsym_type *sy = ldsym_get_soft(tree->name.name);
327
328 if (sy) {
329 asymbol **sdefp = sy->sdefs_chain;
330
331 if (sdefp) {
332 asymbol *sdef = *sdefp;
333 if (sdef->section == (asection *)NULL) {
334 /* This is an absolute symbol */
335 result = new_abs(sdef->value);
336 }
337 else {
338 lang_output_section_statement_type *os =
339 lang_output_section_statement_lookup( sdef->section->output_section->name);
340 result = new_rel(sdef->value, os);
341 }
342 }
343 }
344 if (result.valid == false) {
345 info("%F%S: undefined symbol `%s' referenced in expression.\n",
346 tree->name.name);
347 }
348
349 }
350 }
351
352 break;
353
354 case ADDR:
355
356 if (allocation_done != lang_first_phase_enum) {
357 lang_output_section_statement_type *os =
358 lang_output_section_find(tree->name.name);
359 check(os);
360 result = new_rel((bfd_vma)0, os);
361 }
362 else {
363 result = invalid();
364 }
365 break;
366 case SIZEOF:
367 if(allocation_done != lang_first_phase_enum) {
368 lang_output_section_statement_type *os =
369 lang_output_section_find(tree->name.name);
370 check(os);
371 result = new_abs((bfd_vma)(os->bfd_section->size));
372 }
373 else {
374 result = invalid();
375 }
376 break;
377
378 default:
379 FAIL();
380 break;
381 }
382
383 return result;
384 }
385 etree_value_type exp_fold_tree(tree, current_section, allocation_done,
386 dot, dotp)
387 etree_type *tree;
388 lang_output_section_statement_type *current_section;
389 lang_phase_type allocation_done;
390 bfd_vma dot;
391 bfd_vma *dotp;
392 {
393 etree_value_type result;
394
395 if (tree == (etree_type *)NULL) {
396 result.valid = false;
397 }
398 else {
399 switch (tree->type.node_class)
400 {
401 case etree_value:
402 result = new_rel(tree->value.value, current_section);
403 break;
404 case etree_unary:
405 result = exp_fold_tree(tree->unary.child,
406 current_section,
407 allocation_done, dot, dotp);
408 if (result.valid == true)
409 {
410 switch(tree->type.node_code)
411 {
412 case ALIGN_K:
413 if (allocation_done != lang_first_phase_enum) {
414 result = new_rel_from_section(ALIGN(dot,
415 result.value) ,
416 current_section);
417
418 }
419 else {
420 result.valid = false;
421 }
422 break;
423 case '-':
424 result.value = -result.value;
425 break;
426 case NEXT:
427 result.valid = false;
428 break;
429 default:
430 FAIL();
431 }
432 }
433
434 break;
435 case etree_trinary:
436
437 result = exp_fold_tree(tree->trinary.cond,
438 current_section,
439 allocation_done, dot, dotp);
440 if (result.valid) {
441 result = exp_fold_tree(result.value ?
442 tree->trinary.lhs:tree->trinary.rhs,
443 current_section,
444 allocation_done, dot, dotp);
445 }
446
447 break;
448 case etree_binary:
449 result = fold_binary(tree, current_section, allocation_done,
450 dot, dotp);
451 break;
452 case etree_assign:
453 if (tree->assign.dst[0] == '.' && tree->assign.dst[1] == 0) {
454 /* Assignment to dot can only be done during allocation */
455 if (allocation_done == lang_allocating_phase_enum) {
456 result = exp_fold_tree(tree->assign.src,
457 current_section,
458 lang_allocating_phase_enum, dot, dotp);
459 if (result.valid == false) {
460 info("%F%S invalid assignment to location counter\n");
461 }
462 else {
463 if (current_section ==
464 (lang_output_section_statement_type *)NULL) {
465 info("%F%S assignment to location counter invalid outside of SECTION\n");
466 }
467 else {
468 unsigned long nextdot =result.value +
469 current_section->bfd_section->vma;
470 if (nextdot < dot) {
471 info("%F%S cannot move location counter backwards");
472 }
473 else {
474 *dotp = nextdot;
475 }
476 }
477 }
478 }
479 }
480 else {
481 ldsym_type *sy = ldsym_get(tree->assign.dst);
482
483 /* If this symbol has just been created then we'll place it into
484 * a section of our choice
485 */
486 result = exp_fold_tree(tree->assign.src,
487 current_section, allocation_done,
488 dot, dotp);
489 if (result.valid)
490 {
491 asymbol *def;
492 asymbol **def_ptr = (asymbol **)ldmalloc(sizeof(asymbol **));
493 /* Add this definition to script file */
494 def = (asymbol *)bfd_make_empty_symbol(script_file->the_bfd);
495 *def_ptr = def;
496
497
498 def->value = result.value;
499 if (result.section !=
500 (lang_output_section_statement_type *)NULL) {
501 if (current_section !=
502 (lang_output_section_statement_type *)NULL) {
503
504 def->section = result.section->bfd_section;
505 def->flags = BSF_GLOBAL | BSF_EXPORT;
506 }
507 else {
508 /* Force to absolute */
509 def->value += result.section->bfd_section->vma;
510 def->section = (asection *)NULL;
511 def->flags = BSF_GLOBAL | BSF_EXPORT | BSF_ABSOLUTE;
512 }
513
514
515 }
516 else {
517 def->section = (asection *)NULL;
518 def->flags = BSF_GLOBAL | BSF_EXPORT | BSF_ABSOLUTE;
519 }
520
521
522 def->udata = (void *)NULL;
523 def->name = sy->name;
524 Q_enter_global_ref(def_ptr);
525 }
526
527 }
528
529
530 break;
531 case etree_name:
532 result = fold_name(tree, current_section, allocation_done, dot);
533 break;
534 default:
535 info("%F%S Need more of these %d",tree->type.node_class );
536
537 }
538 }
539
540 return result;
541 }
542
543
544 etree_value_type exp_fold_tree_no_dot(tree, current_section, allocation_done)
545 etree_type *tree;
546 lang_output_section_statement_type *current_section;
547 lang_phase_type allocation_done;
548 {
549 return exp_fold_tree(tree, current_section, allocation_done, (bfd_vma)
550 0, (bfd_vma *)NULL);
551 }
552
553 etree_type *
554 exp_binop(code, lhs, rhs)
555 int code;
556 etree_type *lhs;
557 etree_type *rhs;
558 {
559 etree_type value, *new;
560 etree_value_type r;
561
562 value.type.node_code = code;
563 value.binary.lhs = lhs;
564 value.binary.rhs = rhs;
565 value.type.node_class = etree_binary;
566 r = exp_fold_tree_no_dot(&value, (lang_output_section_statement_type *)NULL,
567 lang_first_phase_enum );
568 if (r.valid)
569 {
570 return exp_intop(r.value);
571 }
572 new = (etree_type *)ldmalloc(sizeof(new->binary));
573 memcpy((char *)new, (char *)&value, sizeof(new->binary));
574 return new;
575 }
576
577 etree_type *
578 exp_trinop(code, cond, lhs, rhs)
579 int code;
580 etree_type *cond;
581 etree_type *lhs;
582 etree_type *rhs;
583 {
584 etree_type value, *new;
585 etree_value_type r;
586 value.type.node_code = code;
587 value.trinary.lhs = lhs;
588 value.trinary.cond = cond;
589 value.trinary.rhs = rhs;
590 value.type.node_class = etree_trinary;
591 r= exp_fold_tree_no_dot(&value, (lang_output_section_statement_type
592 *)NULL,lang_first_phase_enum);
593 if (r.valid) {
594 return exp_intop(r.value);
595 }
596 new = (etree_type *)ldmalloc(sizeof(new->trinary));
597 memcpy((char *)new,(char *) &value, sizeof(new->trinary));
598 return new;
599 }
600
601
602 etree_type *
603 exp_unop(code, child)
604 int code;
605 etree_type *child;
606 {
607 etree_type value, *new;
608
609 etree_value_type r;
610 value.unary.type.node_code = code;
611 value.unary.child = child;
612 value.unary.type.node_class = etree_unary;
613 r = exp_fold_tree_no_dot(&value,(lang_output_section_statement_type *)NULL,
614 lang_first_phase_enum);
615 if (r.valid) {
616 return exp_intop(r.value);
617 }
618 new = (etree_type *)ldmalloc(sizeof(new->unary));
619 memcpy((char *)new, (char *)&value, sizeof(new->unary));
620 return new;
621 }
622
623
624 etree_type *
625 exp_nameop(code, name)
626 int code;
627 char *name;
628 {
629
630 etree_type value, *new;
631
632 etree_value_type r;
633 value.name.type.node_code = code;
634 value.name.name = name;
635 value.name.type.node_class = etree_name;
636
637
638 r = exp_fold_tree_no_dot(&value,(lang_output_section_statement_type *)NULL,
639 lang_first_phase_enum);
640 if (r.valid) {
641 return exp_intop(r.value);
642 }
643 new = (etree_type *)ldmalloc(sizeof(new->name));
644 memcpy((char *)new, (char *)&value, sizeof(new->name));
645 return new;
646
647 }
648
649
650
651
652 etree_type *
653 exp_assop(code, dst, src)
654 int code;
655 char *dst;
656 etree_type *src;
657 {
658 etree_type value, *new;
659
660 value.assign.type.node_code = code;
661
662
663 value.assign.src = src;
664 value.assign.dst = dst;
665 value.assign.type.node_class = etree_assign;
666
667 #if 0
668 if (exp_fold_tree_no_dot(&value, &result)) {
669 return exp_intop(result);
670 }
671 #endif
672 new = (etree_type*)ldmalloc(sizeof(new->assign));
673 memcpy((char *)new, (char *)&value, sizeof(new->assign));
674 return new;
675 }
676
677 void
678 exp_print_tree(outfile, tree)
679 FILE *outfile;
680 etree_type *tree;
681 {
682 switch (tree->type.node_class) {
683 case etree_value:
684 fprintf(outfile,"0x%08lx",(bfd_vma)(tree->value.value));
685 return;
686 case etree_assign:
687 #if 0
688 if (tree->assign.dst->sdefs != (asymbol *)NULL){
689 fprintf(outfile,"%s (%x) ",tree->assign.dst->name,
690 tree->assign.dst->sdefs->value);
691 }
692 else {
693 fprintf(outfile,"%s (UNDEFINED)",tree->assign.dst->name);
694 }
695 #endif
696 fprintf(outfile,"%s ",tree->assign.dst);
697 exp_print_token(outfile,tree->type.node_code);
698 exp_print_tree(outfile,tree->assign.src);
699 break;
700 case etree_binary:
701 exp_print_tree(outfile,tree->binary.lhs);
702 exp_print_token(outfile,tree->type.node_code);
703 exp_print_tree(outfile,tree->binary.rhs);
704 break;
705 case etree_trinary:
706 exp_print_tree(outfile,tree->trinary.cond);
707 fprintf(outfile,"?");
708 exp_print_tree(outfile,tree->trinary.lhs);
709 fprintf(outfile,":");
710 exp_print_tree(outfile,tree->trinary.rhs);
711 break;
712 case etree_unary:
713 exp_print_token(outfile,tree->unary.type.node_code);
714 fprintf(outfile,"(");
715 exp_print_tree(outfile,tree->unary.child);
716 fprintf(outfile,")");
717 break;
718 case etree_undef:
719 fprintf(outfile,"????????");
720 break;
721 case etree_name:
722 if (tree->type.node_code == NAME) {
723 fprintf(outfile,"%s", tree->name.name);
724 }
725 else {
726 exp_print_token(outfile,tree->type.node_code);
727 fprintf(outfile,"(%s)", tree->name.name);
728 }
729 break;
730 default:
731 FAIL();
732 break;
733 }
734 }
735
736
737
738
739 bfd_vma
740 exp_get_vma(tree, def, name, allocation_done)
741 etree_type *tree;
742 bfd_vma def;
743 char *name;
744 lang_phase_type allocation_done;
745 {
746 etree_value_type r;
747
748 if (tree != (etree_type *)NULL) {
749 r = exp_fold_tree_no_dot(tree,
750 (lang_output_section_statement_type *)NULL,
751 allocation_done);
752 if (r.valid == false && name) {
753 info("%F%S Nonconstant expression for %s\n",name);
754 }
755 return r.value;
756 }
757 else {
758 return def;
759 }
760 }
761
762 int
763 exp_get_value_int(tree,def,name, allocation_done)
764 etree_type *tree;
765 int def;
766 char *name;
767 lang_phase_type allocation_done;
768 {
769 return (int)exp_get_vma(tree,(bfd_vma)def,name, allocation_done);
770 }
This page took 0.044089 seconds and 4 git commands to generate.