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