* support/regression/ports/hc08spec.mk: REENTRANT must be reentrant
[fw/sdcc] / src / SDCCsymt.c
1 /*-------------------------------------------------------------------------
2   SDCCsymt.c - Code file for Symbols table related structures and MACRO's.
3         Written By -  Sandeep Dutta . sandeep.dutta@usa.net (1998)
4
5    This program is free software; you can redistribute it and/or modify it
6    under the terms of the GNU General Public License as published by the
7    Free Software Foundation; either version 2, or (at your option) any
8    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
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 this program; if not, write to the Free Software
17    Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
18
19    In other words, you are welcome to use, share and improve this program.
20    You are forbidden to forbid anyone else to use, share and improve
21    what you give them.   Help stamp out software-hoarding!
22 -------------------------------------------------------------------------*/
23
24 #include "common.h"
25 #include "newalloc.h"
26
27 #include "SDCCsymt.h"
28
29 value *aggregateToPointer (value *val);
30 void printTypeChainRaw (sym_link * start, FILE * of);
31
32 void printFromToType(sym_link *from, sym_link *to) {
33   fprintf (stderr, "from type '");
34   printTypeChain (from, stderr);
35   fprintf (stderr, "'\nto type '");
36   printTypeChain (to, stderr);
37   fprintf (stderr, "'\n");
38 }
39
40 /* noun strings */
41 char *nounName(sym_link *sl) {
42   switch (SPEC_NOUN(sl)) 
43     {
44     case V_INT: {
45       if (SPEC_LONG(sl)) return "long";
46       if (sl->select.s._short) return "short";
47       return "int";
48     }
49     case V_FLOAT: return "float";
50     case V_CHAR: return "char";
51     case V_VOID: return "void";
52     case V_STRUCT: return "struct";
53     case V_LABEL: return "label";
54     case V_BITFIELD: return "bitfield";
55     case V_BIT: return "bit";
56     case V_SBIT: return "sbit";
57     case V_DOUBLE: return "double";
58     }
59   return "unknown";
60 };
61
62 bucket *SymbolTab[256];         /* the symbol    table  */
63 bucket *StructTab[256];         /* the structure table  */
64 bucket *TypedefTab[256];        /* the typedef   table  */
65 bucket *LabelTab[256];          /* the Label     table  */
66 bucket *enumTab[256];           /* enumerated    table  */
67
68 /*------------------------------------------------------------------*/
69 /* initSymt () - initialises symbol table related stuff             */
70 /*------------------------------------------------------------------*/
71 void 
72 initSymt ()
73 {
74   int i = 0;
75
76   for (i = 0; i < 256; i++)
77     SymbolTab[i] = StructTab[i] = (void *) NULL;
78
79
80 }
81 /*-----------------------------------------------------------------*/
82 /* newBucket - allocates & returns a new bucket        */
83 /*-----------------------------------------------------------------*/
84 bucket *
85 newBucket ()
86 {
87   bucket *bp;
88
89   bp = Safe_alloc ( sizeof (bucket));
90
91   return bp;
92 }
93
94 /*-----------------------------------------------------------------*/
95 /* hashKey - computes the hashkey given a symbol name              */
96 /*-----------------------------------------------------------------*/
97 int 
98 hashKey (const char *s)
99 {
100   unsigned long key = 0;
101
102   while (*s)
103     key += *s++;
104   return key % 256;
105 }
106
107 /*-----------------------------------------------------------------*/
108 /* addSym - adds a symbol to the hash Table                        */
109 /*-----------------------------------------------------------------*/
110 void 
111 addSym (bucket ** stab,
112         void *sym,
113         char *sname,
114         int level,
115         int block,
116         int checkType)
117 {
118   int i;                        /* index into the hash Table */
119   bucket *bp;                   /* temp bucket    *         */
120
121   if (checkType) {
122     symbol *csym = (symbol *)sym;
123
124     if (getenv("DEBUG_SANITY")) {
125       fprintf (stderr, "addSym: %s ", sname);
126     }
127     /* make sure the type is complete and sane */
128     checkTypeSanity(csym->etype, csym->name);
129   }
130
131   /* prevent overflow of the (r)name buffers */
132   if (strlen(sname)>SDCC_SYMNAME_MAX) {
133     werror (W_SYMBOL_NAME_TOO_LONG, SDCC_SYMNAME_MAX);
134     sname[SDCC_SYMNAME_MAX]='\0';
135   }
136
137   /* the symbols are always added at the head of the list  */
138   i = hashKey (sname);
139   /* get a free entry */
140   bp = Safe_alloc ( sizeof (bucket));
141
142   bp->sym = sym;                /* update the symbol pointer  */
143   bp->level = level;            /* update the nest level      */
144   bp->block = block;
145   strncpyz (bp->name, sname, sizeof(bp->name)); /* copy the name into place */
146
147   /* if this is the first entry */
148   if (stab[i] == NULL)
149     {
150       bp->prev = bp->next = (void *) NULL;      /* point to nothing */
151       stab[i] = bp;
152     }
153   /* not first entry then add @ head of list */
154   else
155     {
156       bp->prev = NULL;
157       stab[i]->prev = bp;
158       bp->next = stab[i];
159       stab[i] = bp;
160     }
161 }
162
163 /*-----------------------------------------------------------------*/
164 /* deleteSym - deletes a symbol from the hash Table  entry     */
165 /*-----------------------------------------------------------------*/
166 void 
167 deleteSym (bucket ** stab, void *sym, char *sname)
168 {
169   int i = 0;
170   bucket *bp;
171
172   i = hashKey (sname);
173
174   bp = stab[i];
175   /* find the symbol */
176   while (bp)
177     {
178       if (bp->sym == sym)       /* found it then break out */
179         break;                  /* of the loop       */
180       bp = bp->next;
181     }
182
183   if (!bp)                      /* did not find it */
184     return;
185   /* if this is the first one in the chain */
186   if (!bp->prev)
187     {
188       stab[i] = bp->next;
189       if (stab[i])              /* if chain ! empty */
190         stab[i]->prev = (void *) NULL;
191     }
192   /* middle || end of chain */
193   else
194     {
195       if (bp->next)             /* if not end of chain */
196         bp->next->prev = bp->prev;
197
198       bp->prev->next = bp->next;
199     }
200
201 }
202
203 /*-----------------------------------------------------------------*/
204 /* findSym - finds a symbol in a table           */
205 /*-----------------------------------------------------------------*/
206 void *
207 findSym (bucket ** stab, void *sym, const char *sname)
208 {
209   bucket *bp;
210
211   bp = stab[hashKey (sname)];
212   while (bp)
213     {
214       if (bp->sym == sym || strcmp (bp->name, sname) == 0)
215         break;
216       bp = bp->next;
217     }
218
219   return (bp ? bp->sym : (void *) NULL);
220 }
221
222 /*-----------------------------------------------------------------*/
223 /* findSymWithLevel - finds a symbol with a name & level           */
224 /*-----------------------------------------------------------------*/
225 void *
226 findSymWithLevel (bucket ** stab, symbol * sym)
227 {
228   bucket *bp;
229
230   bp = stab[hashKey (sym->name)];
231
232   /**
233    **  do the search from the head of the list since the
234    **  elements are added at the head it is ensured that
235    ** we will find the deeper definitions before we find
236    ** the global ones. we need to check for symbols with
237    ** level <= to the level given, if levels match then block
238    ** numbers need to match as well
239    **/
240   while (bp)
241     {
242       if (strcmp (bp->name, sym->name) == 0 && bp->level <= sym->level)
243         {
244           /* if this is parameter then nothing else need to be checked */
245           if (((symbol *) (bp->sym))->_isparm)
246             return (bp->sym);
247           /* if levels match then block numbers should also match */
248           if (bp->level && bp->level == sym->level && bp->block == sym->block)
249             return (bp->sym);
250           /* if levels don't match then we are okay */
251           if (bp->level && bp->level != sym->level && bp->block <= sym->block)
252             return (bp->sym);
253           /* if this is a global variable then we are ok too */
254           if (bp->level == 0)
255             return (bp->sym);
256         }
257
258       bp = bp->next;
259     }
260
261   return (void *) NULL;
262 }
263
264 /*-----------------------------------------------------------------*/
265 /* findSymWithBlock - finds a symbol with name in with a block     */
266 /*-----------------------------------------------------------------*/
267 void *
268 findSymWithBlock (bucket ** stab, symbol * sym, int block)
269 {
270   bucket *bp;
271
272   bp = stab[hashKey (sym->name)];
273   while (bp)
274     {
275       if (strcmp (bp->name, sym->name) == 0 &&
276           bp->block <= block)
277         break;
278       bp = bp->next;
279     }
280
281   return (bp ? bp->sym : (void *) NULL);
282 }
283
284 /*------------------------------------------------------------------*/
285 /* newSymbol () - returns a new pointer to a symbol                 */
286 /*------------------------------------------------------------------*/
287 symbol *
288 newSymbol (char *name, int scope)
289 {
290   symbol *sym;
291
292   sym = Safe_alloc ( sizeof (symbol));
293
294   strncpyz (sym->name, name, sizeof(sym->name));        /* copy the name */
295   sym->level = scope;           /* set the level    */
296   sym->block = currBlockno;
297   sym->lineDef = mylineno;      /* set the line number */
298   sym->fileDef = currFname;
299   return sym;
300 }
301
302 /*------------------------------------------------------------------*/
303 /* newLink - creates a new link (declarator,specifier)              */
304 /*------------------------------------------------------------------*/
305 sym_link *
306 newLink (SYM_LINK_CLASS select)
307 {
308   sym_link *p;
309
310   p = Safe_alloc ( sizeof (sym_link));
311   p->class=select;
312
313   return p;
314 }
315
316 /*------------------------------------------------------------------*/
317 /* newStruct - creats a new structdef from the free list            */
318 /*------------------------------------------------------------------*/
319 structdef *
320 newStruct (char *tag)
321 {
322   structdef *s;
323
324   s = Safe_alloc ( sizeof (structdef));
325
326   strncpyz (s->tag, tag, sizeof(s->tag));               /* copy the tag */
327   return s;
328 }
329   
330 /*------------------------------------------------------------------*/
331 /* sclsFromPtr - Return the storage class a pointer points into.    */
332 /*               S_FIXED is returned for generic pointers or other  */
333 /*               unexpected cases                                   */
334 /*------------------------------------------------------------------*/
335 STORAGE_CLASS
336 sclsFromPtr(sym_link *ptr)
337 {
338   switch (DCL_TYPE (ptr))
339     {
340     case POINTER:
341       return S_DATA;
342     case GPOINTER:
343       return S_FIXED;
344     case FPOINTER:
345       return S_XDATA;
346     case CPOINTER:
347       return S_CODE;
348     case IPOINTER:
349       return S_IDATA;
350     case PPOINTER:
351       return S_PDATA;
352     case EEPPOINTER:
353       return S_EEPROM;
354     case FUNCTION:
355       return S_CODE;
356     default:
357       return S_FIXED;
358     }
359 }
360
361 /*------------------------------------------------------------------*/
362 /* pointerTypes - do the computation for the pointer types          */
363 /*------------------------------------------------------------------*/
364 void 
365 pointerTypes (sym_link * ptr, sym_link * type)
366 {
367   if (IS_SPEC (ptr))
368     return;
369
370   /* find the first pointer type */
371   while (ptr && !IS_PTR (ptr))
372     ptr = ptr->next;
373
374   /* could not find it */
375   if (!ptr || IS_SPEC (ptr))
376     return;
377   
378   if (IS_PTR(ptr) && DCL_TYPE(ptr)!=UPOINTER) {
379     pointerTypes (ptr->next, type);
380     return;
381   }
382
383   /* change the pointer type depending on the
384      storage class of the type */
385   if (IS_SPEC (type))
386     {
387       switch (SPEC_SCLS (type))
388         {
389         case S_XDATA:
390           DCL_TYPE (ptr) = FPOINTER;
391           break;
392         case S_IDATA:
393           DCL_TYPE (ptr) = IPOINTER;
394           break;
395         case S_PDATA:
396           DCL_TYPE (ptr) = PPOINTER;
397           break;
398         case S_DATA:
399           DCL_TYPE (ptr) = POINTER;
400           break;
401         case S_CODE:
402           DCL_TYPE (ptr) = CPOINTER;
403           break;
404         case S_EEPROM:
405           DCL_TYPE (ptr) = EEPPOINTER;
406           break;
407         default:
408           DCL_TYPE (ptr) = port->unqualified_pointer;
409           break;
410         }
411       /* the storage class of type ends here */
412       SPEC_SCLS (type) = 0;
413     }
414
415   /* now change all the remaining unknown pointers
416      to generic pointers */
417   while (ptr)
418     {
419       if (!IS_SPEC (ptr) && DCL_TYPE (ptr) == UPOINTER)
420         DCL_TYPE (ptr) = port->unqualified_pointer;
421       ptr = ptr->next;
422     }
423
424   /* same for the type although it is highly unlikely that
425      type will have a pointer */
426   while (type)
427     {
428       if (!IS_SPEC (type) && DCL_TYPE (type) == UPOINTER)
429         DCL_TYPE (type) = port->unqualified_pointer;
430       type = type->next;
431     }
432 }
433
434 /*------------------------------------------------------------------*/
435 /* addDecl - adds a declarator @ the end of a chain                 */
436 /*------------------------------------------------------------------*/
437 void 
438 addDecl (symbol * sym, int type, sym_link * p)
439 {
440   sym_link *head;
441   sym_link *tail;
442   sym_link *t;
443
444   if (getenv("SDCC_DEBUG_FUNCTION_POINTERS"))
445     fprintf (stderr, "SDCCsymt.c:addDecl(%s,%d,%p)\n", sym->name, type, p);
446
447   /* if we are passed a link then set head & tail */
448   if (p)
449     {
450       tail = head = p;
451       while (tail->next)
452         tail = tail->next;
453     }
454   else
455     {
456       head = tail = newLink (DECLARATOR);
457       DCL_TYPE (head) = type;
458     }
459
460   /* if this is the first entry   */
461   if (!sym->type)
462     {
463       sym->type = head;
464       sym->etype = tail;
465     }
466   else
467     {
468       if (IS_SPEC (sym->etype) && IS_SPEC (head) && head == tail)
469         {
470           sym->etype = mergeSpec (sym->etype, head, sym->name);
471         }
472       else
473         {
474           if (IS_SPEC (sym->etype) && !IS_SPEC (head) && head == tail)
475             {
476               t = sym->type;
477               while (t->next != sym->etype)
478                 t = t->next;
479               t->next = head;
480               tail->next = sym->etype;
481             }
482           else
483             {
484               sym->etype->next = head;
485               sym->etype = tail;
486             }
487         }
488     }
489
490   /* if the type is an unknown pointer and has
491      a tspec then take the storage class const & volatile
492      attribute from the tspec & make it those of this
493      symbol */
494   if (p &&
495       !IS_SPEC (p) &&
496       //DCL_TYPE (p) == UPOINTER &&
497       DCL_TSPEC (p))
498     {
499       if (!IS_SPEC (sym->etype))
500         {
501           sym->etype = sym->etype->next = newLink (SPECIFIER);
502         }
503       SPEC_SCLS (sym->etype) = SPEC_SCLS (DCL_TSPEC (p));
504       DCL_TSPEC (p) = NULL;
505     }
506
507   // if there is a function in this type chain
508   if (p && funcInChain(sym->type)) {
509     processFuncArgs (sym);
510   }
511
512   return;
513 }
514
515 /*------------------------------------------------------------------
516   checkTypeSanity: prevent the user from doing e.g.:
517   unsigned float uf;
518   ------------------------------------------------------------------*/
519 void checkTypeSanity(sym_link *etype, char *name) {
520   char *noun;
521
522   if (!etype) {
523     if (getenv("DEBUG_SANITY")) {
524       fprintf (stderr, "sanity check skipped for %s (etype==0)\n", name);
525     }
526     return;
527   }
528
529   if (!IS_SPEC(etype)) {
530     if (getenv("DEBUG_SANITY")) {
531       fprintf (stderr, "sanity check skipped for %s (!IS_SPEC)\n", name);
532     }
533     return;
534   }
535
536   noun=nounName(etype);
537
538   if (getenv("DEBUG_SANITY")) {
539     fprintf (stderr, "checking sanity for %s %p\n", name, etype);
540   }
541
542   if ((SPEC_NOUN(etype)==V_CHAR || 
543        SPEC_NOUN(etype)==V_FLOAT || 
544        SPEC_NOUN(etype)==V_DOUBLE || 
545        SPEC_NOUN(etype)==V_VOID) &&
546       (etype->select.s._short || SPEC_LONG(etype))) {
547     // long or short for char float double or void
548     werror (E_LONG_OR_SHORT_INVALID, noun, name);
549   }
550   if ((SPEC_NOUN(etype)==V_FLOAT || 
551        SPEC_NOUN(etype)==V_DOUBLE || 
552        SPEC_NOUN(etype)==V_VOID) && 
553       (etype->select.s._signed || SPEC_USIGN(etype))) {
554     // signed or unsigned for float double or void
555     werror (E_SIGNED_OR_UNSIGNED_INVALID, noun, name);
556   }
557
558   // special case for "short"
559   if (etype->select.s._short) {
560     SPEC_NOUN(etype) = options.shortis8bits ? V_CHAR : V_INT;
561     etype->select.s._short = 0;
562   }
563
564   /* if no noun e.g. 
565      "const a;" or "data b;" or "signed s" or "long l"
566      assume an int */
567   if (!SPEC_NOUN(etype)) {
568     SPEC_NOUN(etype)=V_INT;
569   }
570
571   /* ISO/IEC 9899 J.3.9 implementation defined behaviour: */
572   /* a "plain" int bitfield is unsigned */
573   if (SPEC_NOUN(etype)==V_BIT ||
574       SPEC_NOUN(etype)==V_SBIT) {
575     if (!etype->select.s._signed)
576       SPEC_USIGN(etype) = 1;
577   }
578
579   if (etype->select.s._signed && SPEC_USIGN(etype)) {
580     // signed AND unsigned 
581     werror (E_SIGNED_AND_UNSIGNED_INVALID, noun, name);
582   }
583   if (etype->select.s._short && SPEC_LONG(etype)) {
584     // short AND long
585     werror (E_LONG_AND_SHORT_INVALID, noun, name);
586   }
587
588 }
589
590 /*------------------------------------------------------------------*/
591 /* mergeSpec - merges two specifiers and returns the new one        */
592 /*------------------------------------------------------------------*/
593 sym_link *
594 mergeSpec (sym_link * dest, sym_link * src, char *name)
595 {
596   if (!IS_SPEC(dest) || !IS_SPEC(src)) {
597 #if 0
598     werror (E_INTERNAL_ERROR, __FILE__, __LINE__, "cannot merge declarator");
599     exit (1);
600 #else
601     werror (E_SYNTAX_ERROR, yytext);
602     // the show must go on
603     return newIntLink();
604 #endif
605   }
606
607   if (SPEC_NOUN(src)) {
608     if (!SPEC_NOUN(dest)) {
609       SPEC_NOUN(dest)=SPEC_NOUN(src);
610     } else {
611       /* we shouldn't redeclare the type */
612       if (getenv("DEBUG_SANITY")) {
613         fprintf (stderr, "mergeSpec: ");
614       }
615       werror(E_TWO_OR_MORE_DATA_TYPES, name);
616     }
617   }
618   
619   if (SPEC_SCLS(src)) {
620     /* if destination has no storage class */
621     if (!SPEC_SCLS (dest) || SPEC_SCLS(dest)==S_REGISTER) {
622       SPEC_SCLS (dest) = SPEC_SCLS (src);
623     } else {
624       if (getenv("DEBUG_SANITY")) {
625         fprintf (stderr, "mergeSpec: ");
626       }
627       werror(E_TWO_OR_MORE_STORAGE_CLASSES, name);
628     }
629   }
630
631   /* copy all the specifications  */
632
633   // we really should do: 
634 #if 0
635   if (SPEC_what(src)) {
636     if (SPEC_what(dest)) {
637       werror(W_DUPLICATE_SPEC, "what");
638     }
639     SPEC_what(dst)|=SPEC_what(src);
640   }
641 #endif
642   // but there are more important thing right now
643
644   SPEC_LONG (dest) |= SPEC_LONG (src);
645   dest->select.s._short|=src->select.s._short;
646   SPEC_USIGN (dest) |= SPEC_USIGN (src);
647   dest->select.s._signed|=src->select.s._signed;
648   SPEC_STAT (dest) |= SPEC_STAT (src);
649   SPEC_EXTR (dest) |= SPEC_EXTR (src);
650   SPEC_CONST(dest) |= SPEC_CONST (src);
651   SPEC_ABSA (dest) |= SPEC_ABSA (src);
652   SPEC_VOLATILE (dest) |= SPEC_VOLATILE (src);
653   SPEC_ADDR (dest) |= SPEC_ADDR (src);
654   SPEC_OCLS (dest) = SPEC_OCLS (src);
655   SPEC_BLEN (dest) |= SPEC_BLEN (src);
656   SPEC_BSTR (dest) |= SPEC_BSTR (src);
657   SPEC_TYPEDEF (dest) |= SPEC_TYPEDEF (src);
658   SPEC_ENUM (dest) |= SPEC_ENUM (src);
659   if (SPEC_ARGREG(src) && !SPEC_ARGREG(dest))
660       SPEC_ARGREG(dest) = SPEC_ARGREG(src);
661   
662   if (IS_STRUCT (dest) && SPEC_STRUCT (dest) == NULL)
663     SPEC_STRUCT (dest) = SPEC_STRUCT (src);
664
665   /* these are the only function attributes that will be set 
666      in a specifier while parsing */
667   FUNC_NONBANKED(dest) |= FUNC_NONBANKED(src);
668   FUNC_BANKED(dest) |= FUNC_BANKED(src);
669   FUNC_ISCRITICAL(dest) |= FUNC_ISCRITICAL(src);
670   FUNC_ISREENT(dest) |= FUNC_ISREENT(src);
671   FUNC_ISNAKED(dest) |= FUNC_ISNAKED(src);
672   FUNC_ISISR(dest) |= FUNC_ISISR(src);
673   FUNC_ISJAVANATIVE(dest) |= FUNC_ISJAVANATIVE(src);
674   FUNC_ISBUILTIN(dest) |= FUNC_ISBUILTIN(src);
675   FUNC_ISOVERLAY(dest) |= FUNC_ISOVERLAY(src);
676   FUNC_INTNO(dest) |= FUNC_INTNO(src);
677   FUNC_REGBANK(dest) |= FUNC_REGBANK(src);
678
679   return dest;
680 }
681
682 /*------------------------------------------------------------------*/
683 /* genSymName - generates and returns a name used for anonymous vars */
684 /*------------------------------------------------------------------*/
685 char *
686 genSymName (int level)
687 {
688   static int gCount = 0;
689   static char gname[SDCC_NAME_MAX + 1];
690
691   SNPRINTF (gname, sizeof(gname), "__%04d%04d", level, gCount++);
692   return gname;
693 }
694
695 /*------------------------------------------------------------------*/
696 /* getSpec - returns the specifier part from a declaration chain    */
697 /*------------------------------------------------------------------*/
698 sym_link *
699 getSpec (sym_link * p)
700 {
701   sym_link *loop;
702
703   loop = p;
704   while (p && !(IS_SPEC (p)))
705     p = p->next;
706
707   return p;
708 }
709
710 /*------------------------------------------------------------------*/
711 /* newCharLink() - creates an char type                             */
712 /*------------------------------------------------------------------*/
713 sym_link *
714 newCharLink ()
715 {
716   sym_link *p;
717
718   p = newLink (SPECIFIER);
719   SPEC_NOUN (p) = V_CHAR;
720
721   return p;
722 }
723
724 /*------------------------------------------------------------------*/
725 /* newFloatLink - a new Float type                                  */
726 /*------------------------------------------------------------------*/
727 sym_link *
728 newFloatLink ()
729 {
730   sym_link *p;
731
732   p = newLink (SPECIFIER);
733   SPEC_NOUN (p) = V_FLOAT;
734
735   return p;
736 }
737
738 /*------------------------------------------------------------------*/
739 /* newLongLink() - new long type                                    */
740 /*------------------------------------------------------------------*/
741 sym_link *
742 newLongLink ()
743 {
744   sym_link *p;
745
746   p = newLink (SPECIFIER);
747   SPEC_NOUN (p) = V_INT;
748   SPEC_LONG (p) = 1;
749
750   return p;
751 }
752
753 /*------------------------------------------------------------------*/
754 /* newIntLink() - creates an int type                               */
755 /*------------------------------------------------------------------*/
756 sym_link *
757 newIntLink ()
758 {
759   sym_link *p;
760
761   p = newLink (SPECIFIER);
762   SPEC_NOUN (p) = V_INT;
763
764   return p;
765 }
766
767 /*------------------------------------------------------------------*/
768 /* getSize - returns size of a type chain in bits                   */
769 /*------------------------------------------------------------------*/
770 unsigned int 
771 getSize (sym_link * p)
772 {
773   /* if nothing return 0 */
774   if (!p)
775     return 0;
776   if (IS_SPEC (p))
777     {                           /* if this is the specifier then */
778       switch (SPEC_NOUN (p))
779         {                       /* depending on the specifier type */
780         case V_INT:
781           return (IS_LONG (p) ? LONGSIZE : INTSIZE);
782         case V_FLOAT:
783           return FLOATSIZE;
784         case V_CHAR:
785           return CHARSIZE;
786         case V_VOID:
787           return 0;
788         case V_STRUCT:
789           return SPEC_STRUCT (p)->size;
790         case V_LABEL:
791           return 0;
792         case V_SBIT:
793         case V_BIT:
794           return BITSIZE;
795         case V_BITFIELD:
796           return ((SPEC_BLEN (p) / 8) + (SPEC_BLEN (p) % 8 ? 1 : 0));
797         default:
798           return 0;
799         }
800     }
801
802   /* this is a declarator */
803   switch (DCL_TYPE (p))
804     {
805     case ARRAY:
806       if (DCL_ELEM(p)) {
807         return DCL_ELEM (p) * getSize (p->next);
808       } else {
809           //    werror (E_INTERNAL_ERROR, __FILE__, __LINE__, 
810           //    "can not tell the size of an array[]");
811         return 0;
812       }
813     case IPOINTER:
814     case PPOINTER:
815     case POINTER:
816       return (PTRSIZE);
817     case EEPPOINTER:
818     case FPOINTER:
819     case CPOINTER:
820     case FUNCTION:
821       return (FPTRSIZE);
822     case GPOINTER:
823       return (GPTRSIZE);
824
825     default:
826       return 0;
827     }
828 }
829
830 /*---------------------------------------------------------------------*/
831 /* getAllocSize - returns size of a type chain in bytes for allocation */
832 /*---------------------------------------------------------------------*/
833 unsigned int
834 getAllocSize (sym_link *p)
835 {
836   if (IS_STRUCT (p) && SPEC_STRUCT (p)->type == STRUCT)
837     {
838       /* if this is a struct specifier then  */
839       /* calculate the size as it could end  */
840       /* with an array of unspecified length */
841       symbol *sflds = SPEC_STRUCT (p)->fields;
842
843       while (sflds && sflds->next)
844         sflds = sflds->next;
845
846       if (sflds && !IS_BITFIELD (sflds->type))
847         return sflds->offset + getAllocSize (sflds->type);
848       else
849         return SPEC_STRUCT (p)->size;
850     }
851   else
852     return getSize (p);
853 }
854
855 /*------------------------------------------------------------------*/
856 /* bitsForType - returns # of bits required to store this type      */
857 /*------------------------------------------------------------------*/
858 unsigned int 
859 bitsForType (sym_link * p)
860 {
861   /* if nothing return 0 */
862   if (!p)
863     return 0;
864
865   if (IS_SPEC (p))
866     {                           /* if this is the specifier then */
867
868       switch (SPEC_NOUN (p))
869         {                       /* depending on the specifier type */
870         case V_INT:
871           return (IS_LONG (p) ? LONGSIZE * 8 : INTSIZE * 8);
872         case V_FLOAT:
873           return FLOATSIZE * 8;
874         case V_CHAR:
875           return CHARSIZE * 8;
876         case V_VOID:
877           return 0;
878         case V_STRUCT:
879           return SPEC_STRUCT (p)->size * 8;
880         case V_LABEL:
881           return 0;
882         case V_SBIT:
883         case V_BIT:
884           return 1;
885         case V_BITFIELD:
886           return SPEC_BLEN (p);
887         default:
888           return 0;
889         }
890     }
891
892   /* this is a specifier  */
893   switch (DCL_TYPE (p))
894     {
895     case ARRAY:
896       return DCL_ELEM (p) * getSize (p->next) * 8;
897     case IPOINTER:
898     case PPOINTER:
899     case POINTER:
900       return (PTRSIZE * 8);
901     case EEPPOINTER:
902     case FPOINTER:
903     case CPOINTER:
904     case FUNCTION:
905       return (FPTRSIZE * 8);
906     case GPOINTER:
907       return (GPTRSIZE * 8);
908
909     default:
910       return 0;
911     }
912 }
913
914 /*------------------------------------------------------------------*/
915 /* copySymbolChain - copies a symbol chain                          */
916 /*------------------------------------------------------------------*/
917 symbol *
918 copySymbolChain (symbol * src)
919 {
920   symbol *dest;
921
922   if (!src)
923     return NULL;
924
925   dest = copySymbol (src);
926   dest->next = copySymbolChain (src->next);
927   return dest;
928 }
929
930 /*------------------------------------------------------------------*/
931 /* copySymbol - makes a copy of a symbol                            */
932 /*------------------------------------------------------------------*/
933 symbol *
934 copySymbol (symbol * src)
935 {
936   symbol *dest;
937
938   if (!src)
939     return NULL;
940
941   dest = newSymbol (src->name, src->level);
942   memcpy (dest, src, sizeof (symbol));
943   dest->level = src->level;
944   dest->block = src->block;
945   dest->ival = copyIlist (src->ival);
946   dest->type = copyLinkChain (src->type);
947   dest->etype = getSpec (dest->type);
948   dest->next = NULL;
949   dest->key = src->key;
950   dest->allocreq = src->allocreq;
951   return dest;
952 }
953
954 /*------------------------------------------------------------------*/
955 /* reverseSyms - reverses the links for a symbol chain      */
956 /*------------------------------------------------------------------*/
957 symbol *
958 reverseSyms (symbol * sym)
959 {
960   symbol *prev, *curr, *next;
961
962   if (!sym)
963     return NULL;
964
965   prev = sym;
966   curr = sym->next;
967
968   while (curr)
969     {
970       next = curr->next;
971       curr->next = prev;
972       prev = curr;
973       curr = next;
974     }
975   sym->next = (void *) NULL;
976   return prev;
977 }
978
979 /*------------------------------------------------------------------*/
980 /* reverseLink - reverses the links for a type chain        */
981 /*------------------------------------------------------------------*/
982 sym_link *
983 reverseLink (sym_link * type)
984 {
985   sym_link *prev, *curr, *next;
986
987   if (!type)
988     return NULL;
989
990   prev = type;
991   curr = type->next;
992
993   while (curr)
994     {
995       next = curr->next;
996       curr->next = prev;
997       prev = curr;
998       curr = next;
999     }
1000   type->next = (void *) NULL;
1001   return prev;
1002 }
1003
1004 /*------------------------------------------------------------------*/
1005 /* addSymChain - adds a symbol chain to the symboltable             */
1006 /*------------------------------------------------------------------*/
1007 void 
1008 addSymChain (symbol * symHead)
1009 {
1010   symbol *sym = symHead;
1011   symbol *csym = NULL;
1012   int error = 0;
1013
1014   for (; sym != NULL; sym = sym->next)
1015     {
1016       changePointer(sym->type);
1017       checkTypeSanity(sym->etype, sym->name);
1018
1019       if (!sym->level && !(IS_SPEC(sym->etype) && IS_TYPEDEF(sym->etype)))
1020         checkDecl (sym, 0);
1021       
1022       /* if already exists in the symbol table then check if
1023          one of them is an extern definition if yes then
1024          then check if the type match, if the types match then
1025          delete the current entry and add the new entry      */
1026       if ((csym = findSymWithLevel (SymbolTab, sym)) &&
1027           csym->level == sym->level) {
1028
1029         /* If the previous definition was for an array with incomplete */
1030         /* type, and the new definition has completed the type, update */
1031         /* the original type to match */
1032         if (IS_DECL(csym->type) && DCL_TYPE(csym->type)==ARRAY
1033             && IS_DECL(sym->type) && DCL_TYPE(sym->type)==ARRAY)
1034           {
1035             if (!DCL_ELEM(csym->type) && DCL_ELEM(sym->type))
1036               DCL_ELEM(csym->type) = DCL_ELEM(sym->type);
1037           }
1038
1039         #if 0
1040         /* If only one of the definitions used the "at" keyword, copy */
1041         /* the address to the other. */
1042         if (IS_SPEC(csym->etype) && SPEC_ABSA(csym->etype)
1043             && IS_SPEC(sym->etype) && !SPEC_ABSA(sym->etype))
1044           {
1045             SPEC_ABSA (sym->etype) = 1;
1046             SPEC_ADDR (sym->etype) = SPEC_ADDR (csym->etype);
1047           }
1048         if (IS_SPEC(csym->etype) && !SPEC_ABSA(csym->etype)
1049             && IS_SPEC(sym->etype) && SPEC_ABSA(sym->etype))
1050           {
1051             SPEC_ABSA (csym->etype) = 1;
1052             SPEC_ADDR (csym->etype) = SPEC_ADDR (sym->etype);
1053           }
1054         #endif
1055   
1056         error = 0;        
1057         if (csym->ival && sym->ival)
1058           error = 1;
1059         if (compareTypeExact (csym->type, sym->type, sym->level) != 1)
1060           error = 1;
1061         
1062         if (error) {
1063           /* one definition extern ? */
1064           if (IS_EXTERN (csym->etype) || IS_EXTERN (sym->etype))
1065             werror (E_EXTERN_MISMATCH, sym->name);
1066           else
1067             werror (E_DUPLICATE, sym->name);
1068           werrorfl (csym->fileDef, csym->lineDef, E_PREVIOUS_DEF);
1069           #if 0
1070           fprintf (stderr, "from type '");
1071           printTypeChain (csym->type, stderr);
1072           if (IS_SPEC (csym->etype) && SPEC_ABSA (csym->etype))
1073             fprintf(stderr, " at 0x%x", SPEC_ADDR (csym->etype));
1074           fprintf (stderr, "'\nto type '");
1075           printTypeChain (sym->type, stderr);
1076           if (IS_SPEC (sym->etype) && SPEC_ABSA (sym->etype))
1077             fprintf(stderr, " at 0x%x", SPEC_ADDR (sym->etype));
1078           fprintf (stderr, "'\n");
1079           #endif
1080           continue;
1081         }
1082
1083         if (csym->ival && !sym->ival)
1084           sym->ival = csym->ival;
1085
1086         /* delete current entry */
1087         deleteSym (SymbolTab, csym, csym->name);
1088         deleteFromSeg(csym);
1089       }
1090       
1091       /* add new entry */
1092       addSym (SymbolTab, sym, sym->name, sym->level, sym->block, 1);
1093     }
1094 }
1095
1096
1097 /*------------------------------------------------------------------*/
1098 /* funcInChain - DCL Type 'FUNCTION' found in type chain            */
1099 /*------------------------------------------------------------------*/
1100 int 
1101 funcInChain (sym_link * lnk)
1102 {
1103   while (lnk)
1104     {
1105       if (IS_FUNC (lnk))
1106         return 1;
1107       lnk = lnk->next;
1108     }
1109   return 0;
1110 }
1111
1112 /*------------------------------------------------------------------*/
1113 /* structElemType - returns the type info of a struct member        */
1114 /*------------------------------------------------------------------*/
1115 sym_link *
1116 structElemType (sym_link * stype, value * id)
1117 {
1118   symbol *fields = (SPEC_STRUCT (stype) ? SPEC_STRUCT (stype)->fields : NULL);
1119   sym_link *type, *etype;
1120   sym_link *petype = getSpec (stype);
1121
1122   if (fields && id) {
1123     
1124     /* look for the id */
1125     while (fields)
1126       {
1127         if (strcmp (fields->rname, id->name) == 0)
1128           {
1129             type = copyLinkChain (fields->type);
1130             etype = getSpec (type);
1131             SPEC_SCLS (etype) = (SPEC_SCLS (petype) == S_REGISTER ?
1132                                  SPEC_SCLS (etype) : SPEC_SCLS (petype));
1133             if (IS_SPEC (type))
1134               SPEC_CONST (type) |= SPEC_CONST (stype);
1135             else
1136               DCL_PTR_CONST (type) |= SPEC_CONST (stype);
1137             return type;
1138           }
1139         fields = fields->next;
1140       }
1141   }
1142
1143   werror (E_NOT_MEMBER, id->name);
1144     
1145   // the show must go on
1146   return newIntLink();
1147 }
1148
1149 /*------------------------------------------------------------------*/
1150 /* getStructElement - returns element of a tructure definition      */
1151 /*------------------------------------------------------------------*/
1152 symbol *
1153 getStructElement (structdef * sdef, symbol * sym)
1154 {
1155   symbol *field;
1156
1157   for (field = sdef->fields; field; field = field->next)
1158     if (strcmp (field->name, sym->name) == 0)
1159       return field;
1160
1161   werror (E_NOT_MEMBER, sym->name);
1162
1163   return sdef->fields;
1164 }
1165
1166 /*------------------------------------------------------------------*/
1167 /* compStructSize - computes the size of a structure                */
1168 /*------------------------------------------------------------------*/
1169 int 
1170 compStructSize (int su, structdef * sdef)
1171 {
1172     int sum = 0, usum = 0;
1173     int bitOffset = 0;
1174     symbol *loop;
1175
1176     /* for the identifiers  */
1177     loop = sdef->fields;
1178     while (loop) {
1179
1180         /* create the internal name for this variable */
1181         SNPRINTF (loop->rname, sizeof(loop->rname), "_%s", loop->name);
1182         if (su == UNION) {
1183             sum = 0;
1184             bitOffset = 0;
1185         }
1186         SPEC_VOLATILE (loop->etype) |= (su == UNION ? 1 : 0);
1187
1188         /* if this is a bit field  */
1189         if (loop->bitVar) {
1190
1191             /* change it to a unsigned bit */
1192             SPEC_NOUN (loop->etype) = V_BITFIELD;
1193             SPEC_USIGN (loop->etype) = 1;
1194             SPEC_BLEN (loop->etype) = loop->bitVar;
1195
1196             if (loop->bitVar == BITVAR_PAD) {
1197                 /* A zero length bitfield forces padding */
1198                 SPEC_BSTR (loop->etype) = bitOffset;
1199                 SPEC_BLEN (loop->etype) = 0;
1200                 bitOffset = 8;
1201                 loop->offset = sum;
1202             }
1203             else {
1204                 if (bitOffset == 8) {
1205                     bitOffset = 0;
1206                     sum++;
1207                 }
1208                 /* check if this fit into the remaining   */
1209                 /* bits of this byte else align it to the */
1210                 /* next byte boundary                     */
1211                 if (loop->bitVar <= (8 - bitOffset)) {
1212                     /* fits into current byte */
1213                     loop->offset = sum;
1214                     SPEC_BSTR (loop->etype) = bitOffset;
1215                     bitOffset += loop->bitVar;
1216                 }
1217                 else if (!bitOffset) {
1218                     /* does not fit, but is already byte aligned */
1219                     loop->offset = sum;
1220                     SPEC_BSTR (loop->etype) = bitOffset;
1221                     bitOffset += loop->bitVar;
1222                 } 
1223                 else {
1224                     /* does not fit; need to realign first */
1225                     sum++;
1226                     loop->offset = (su == UNION ? sum = 0 : sum);
1227                     bitOffset = 0;
1228                     SPEC_BSTR (loop->etype) = bitOffset;
1229                     bitOffset += loop->bitVar;
1230                 }
1231                 while (bitOffset>8) {
1232                     bitOffset -= 8;
1233                     sum++;
1234                 } 
1235             }
1236         }
1237         else {
1238             /* This is a non-bit field. Make sure we are */
1239             /* byte aligned first */
1240             if (bitOffset) {
1241                 sum++;
1242                 loop->offset = (su == UNION ? sum = 0 : sum);
1243                 bitOffset = 0;
1244             }
1245             loop->offset = sum;
1246             checkDecl (loop, 1);
1247             sum += getSize (loop->type);
1248         }
1249
1250         loop = loop->next;
1251
1252         /* if union then size = sizeof largest field */
1253         if (su == UNION) {
1254             /* For UNION, round up after each field */
1255             sum += ((bitOffset+7)/8);
1256             usum = max (usum, sum);
1257         }
1258
1259     }
1260     
1261     /* For STRUCT, round up after all fields processed */
1262     if (su != UNION)
1263         sum += ((bitOffset+7)/8);
1264
1265     return (su == UNION ? usum : sum);
1266 }
1267
1268 /*-------------------------------------------------------------------*/
1269 /* promoteAnonStructs - promote anonymous struct/union's fields into */
1270 /*                      an enclosing struct/union                    */
1271 /*-------------------------------------------------------------------*/
1272 void
1273 promoteAnonStructs (int su, structdef * sdef)
1274 {
1275   symbol *field;
1276   symbol *subfield;
1277   symbol **tofield;
1278   symbol *nextfield;
1279   symbol *dupfield;
1280   int base;
1281
1282   tofield = &sdef->fields;
1283   field = sdef->fields;
1284   while (field)
1285     {
1286       nextfield = field->next;
1287       if (!*field->name && IS_STRUCT (field->type))
1288         {
1289           /* Found an anonymous struct/union. Replace it */
1290           /* with the fields it contains and adjust all  */
1291           /* the offsets */
1292           
1293           base = field->offset;
1294           subfield = copySymbolChain (SPEC_STRUCT (field->type)->fields);
1295           if (!subfield)
1296             continue;           /* just in case it's empty */
1297           
1298           *tofield = subfield;
1299           for (;;)
1300             {
1301               /* check for field name conflicts resulting from promotion */
1302               dupfield = sdef->fields;
1303               while (dupfield && dupfield != subfield)
1304                 {
1305                   if (*subfield->name && !strcmp (dupfield->name, subfield->name))
1306                     {
1307                       werrorfl (subfield->fileDef, subfield->lineDef,
1308                                 E_DUPLICATE_MEMBER,
1309                                 su==STRUCT ? "struct" : "union",
1310                                 subfield->name);
1311                       werrorfl (dupfield->fileDef, dupfield->lineDef,
1312                                 E_PREVIOUS_DEF);
1313                     }
1314                   dupfield = dupfield->next;
1315                 }
1316               
1317               subfield->offset += base;
1318               if (subfield->next)
1319                 subfield = subfield->next;
1320               else
1321                 break;
1322             }
1323           subfield->next = nextfield;
1324           tofield = &subfield->next;
1325         }
1326       else
1327         tofield = &field->next;
1328       field = nextfield;
1329     }
1330 }
1331
1332
1333 /*------------------------------------------------------------------*/
1334 /* checkSClass - check the storage class specification              */
1335 /*------------------------------------------------------------------*/
1336 static void 
1337 checkSClass (symbol * sym, int isProto)
1338 {
1339   sym_link *t;
1340   
1341   if (getenv("DEBUG_SANITY")) {
1342     fprintf (stderr, "checkSClass: %s \n", sym->name);
1343   }
1344   
1345   /* type is literal can happen for enums change
1346      to auto */
1347   if (SPEC_SCLS (sym->etype) == S_LITERAL && !SPEC_ENUM (sym->etype))
1348     SPEC_SCLS (sym->etype) = S_AUTO;
1349   
1350   /* if sfr or sbit then must also be volatile */
1351   if (SPEC_SCLS (sym->etype) == S_SBIT ||
1352       SPEC_SCLS (sym->etype) == S_SFR)
1353     {
1354       SPEC_VOLATILE (sym->etype) = 1;
1355     }
1356   
1357   /* if absolute address given then it mark it as
1358      volatile -- except in the PIC port */
1359
1360 #if !OPT_DISABLE_PIC || !OPT_DISABLE_PIC16
1361   /* The PIC port uses a different peep hole optimizer based on "pCode" */
1362   if (!TARGET_IS_PIC && !TARGET_IS_PIC16)
1363 #endif
1364
1365     if (IS_ABSOLUTE (sym->etype))
1366       SPEC_VOLATILE (sym->etype) = 1;
1367   
1368   /* If code memory is read only, then pointers to code memory */
1369   /* implicitly point to constants -- make this explicit       */
1370   t = sym->type;
1371   while (t && t->next) {
1372     if (IS_CODEPTR(t) && port->mem.code_ro) {
1373       if (IS_SPEC(t->next)) {
1374         SPEC_CONST (t->next) = 1;
1375       } else {
1376         DCL_PTR_CONST (t->next) = 1;
1377       }
1378     }
1379     t = t->next;
1380   }
1381
1382   /* global variables declared const put into code */
1383   /* if no other storage class specified */
1384   if (sym->level == 0 &&
1385       SPEC_SCLS(sym->etype) == S_FIXED &&
1386       !IS_FUNC(sym->type)) {
1387     /* find the first non-array link */
1388     t = sym->type;
1389     while (IS_ARRAY(t))
1390       t = t->next;
1391     if (IS_CONSTANT (t)) {
1392       SPEC_SCLS (sym->etype) = S_CODE;
1393     }
1394   }
1395
1396   /* global variable in code space is a constant */
1397   if (sym->level == 0 &&
1398       SPEC_SCLS (sym->etype) == S_CODE &&
1399       port->mem.code_ro) {
1400     /* find the first non-array link */
1401     t = sym->type;
1402     while (IS_ARRAY(t))
1403       t = t->next;
1404     if (IS_SPEC(t)) {
1405       SPEC_CONST (t) = 1;
1406     } else {
1407       DCL_PTR_CONST (t) = 1;
1408     }
1409   }
1410
1411   /* if bit variable then no storage class can be */
1412   /* specified since bit is already a storage */
1413   if (IS_BITVAR (sym->etype) &&
1414       (SPEC_SCLS (sym->etype) != S_FIXED &&
1415        SPEC_SCLS (sym->etype) != S_SBIT &&
1416        SPEC_SCLS (sym->etype) != S_BIT)
1417     )
1418     {
1419       werror (E_BITVAR_STORAGE, sym->name);
1420       SPEC_SCLS (sym->etype) = S_FIXED;
1421     }
1422
1423   /* extern variables cannot be initialized */
1424   if (IS_EXTERN (sym->etype) && sym->ival)
1425     {
1426       werror (E_EXTERN_INIT, sym->name);
1427       sym->ival = NULL;
1428     }
1429
1430   /* if this is an automatic symbol */
1431   if (sym->level && (options.stackAuto || reentrant)) {
1432     if ((SPEC_SCLS (sym->etype) == S_AUTO ||
1433          SPEC_SCLS (sym->etype) == S_FIXED ||
1434          SPEC_SCLS (sym->etype) == S_REGISTER ||
1435          SPEC_SCLS (sym->etype) == S_STACK ||
1436          SPEC_SCLS (sym->etype) == S_XSTACK)) {
1437       SPEC_SCLS (sym->etype) = S_AUTO;
1438     } else {
1439       /* storage class may only be specified for statics */
1440       if (!IS_STATIC(sym->etype)) {
1441         werror (E_AUTO_ASSUMED, sym->name);
1442       }
1443     }
1444   }
1445
1446   /* automatic symbols cannot be given   */
1447   /* an absolute address ignore it      */
1448   if (sym->level &&
1449       SPEC_ABSA (sym->etype) &&
1450       (options.stackAuto || reentrant))
1451     {
1452       werror (E_AUTO_ABSA, sym->name);
1453       SPEC_ABSA (sym->etype) = 0;
1454     }
1455
1456   /* arrays & pointers cannot be defined for bits   */
1457   /* SBITS or SFRs or BIT                           */
1458   if ((IS_ARRAY (sym->type) || IS_PTR (sym->type)) &&
1459       (SPEC_NOUN (sym->etype) == V_BIT ||
1460        SPEC_NOUN (sym->etype) == V_SBIT ||
1461        SPEC_NOUN (sym->etype) == V_BITFIELD ||
1462        SPEC_SCLS (sym->etype) == S_SFR))
1463     werror (E_BIT_ARRAY, sym->name);
1464
1465   /* if this is a bit|sbit then set length & start  */
1466   if (SPEC_NOUN (sym->etype) == V_BIT ||
1467       SPEC_NOUN (sym->etype) == V_SBIT)
1468     {
1469       SPEC_BLEN (sym->etype) = 1;
1470       SPEC_BSTR (sym->etype) = 0;
1471     }
1472
1473   if (!isProto) {
1474     /* variables declared in CODE space must have */
1475     /* initializers if not an extern */
1476     if (SPEC_SCLS (sym->etype) == S_CODE &&
1477         sym->ival == NULL &&
1478         !sym->_isparm &&
1479         //!sym->level &&
1480         port->mem.code_ro &&
1481         !IS_EXTERN (sym->etype) &&
1482         !funcInChain (sym->type))
1483       werror (E_CODE_NO_INIT, sym->name);
1484   }
1485
1486   /* if parameter or local variable then change */
1487   /* the storage class to reflect where the var will go */
1488   if (sym->level && SPEC_SCLS (sym->etype) == S_FIXED &&
1489       !IS_STATIC(sym->etype))
1490     {
1491       if (options.stackAuto || (currFunc && IFFUNC_ISREENT (currFunc->type)))
1492         {
1493           SPEC_SCLS (sym->etype) = (options.useXstack ?
1494                                     S_XSTACK : S_STACK);
1495         }
1496       else
1497         {
1498           /* hack-o-matic! I see no reason why the useXstack option should ever
1499            * control this allcoation, but the code was originally that way, and
1500            * changing it for non-390 ports breaks the compiler badly.
1501            */
1502           bool useXdata = (TARGET_IS_DS390 || TARGET_IS_DS400) ? 
1503                 1 : options.useXstack;
1504           SPEC_SCLS (sym->etype) = (useXdata ?
1505                                     S_XDATA : S_FIXED);
1506         }
1507     }
1508 }
1509
1510 /*------------------------------------------------------------------*/
1511 /* changePointer - change pointer to functions                      */
1512 /*------------------------------------------------------------------*/
1513 void 
1514 changePointer (sym_link * p)
1515 {
1516
1517   /* go thru the chain of declarations   */
1518   /* if we find a pointer to a function  */
1519   /* unconditionally change it to a ptr  */
1520   /* to code area                        */
1521   for (; p; p = p->next)
1522     {
1523       if (!IS_SPEC (p) && DCL_TYPE (p) == UPOINTER)
1524         DCL_TYPE (p) = port->unqualified_pointer;
1525       if (IS_PTR (p) && IS_FUNC (p->next))
1526         DCL_TYPE (p) = CPOINTER;
1527     }
1528 }
1529
1530 /*------------------------------------------------------------------*/
1531 /* checkDecl - does semantic validation of a declaration                   */
1532 /*------------------------------------------------------------------*/
1533 int 
1534 checkDecl (symbol * sym, int isProto)
1535 {
1536
1537   checkSClass (sym, isProto);           /* check the storage class      */
1538   changePointer (sym->type);          /* change pointers if required */
1539
1540   /* if this is an array without any dimension
1541      then update the dimension from the initial value */
1542   if (IS_ARRAY (sym->type) && !DCL_ELEM (sym->type))
1543     DCL_ELEM (sym->type) = getNelements (sym->type, sym->ival);
1544
1545   return 0;
1546 }
1547
1548 /*-------------------------------------------------------------------*/
1549 /* copyStruct - makes a copy of the struct chain & rets ptr 2 struct */
1550 /*-------------------------------------------------------------------*/
1551 structdef *
1552 copyStruct (structdef * src)
1553 {
1554   structdef *dst = (void *) NULL;
1555
1556   if (src)
1557     {
1558       dst = newStruct(src->tag);
1559       memcpy(dst, src, sizeof(structdef));      /* copy it */
1560       dst->fields = copySymbolChain(src->fields);
1561     }
1562   return dst;
1563 }
1564
1565 /*------------------------------------------------------------------*/
1566 /* copyLinkChain - makes a copy of the link chain & rets ptr 2 head */
1567 /*------------------------------------------------------------------*/
1568 sym_link *
1569 copyLinkChain (sym_link * p)
1570 {
1571   sym_link *head, *curr, *loop;
1572
1573   curr = p;
1574   head = loop = (curr ? newLink (p->class) : (void *) NULL);
1575   while (curr)
1576     {
1577       memcpy (loop, curr, sizeof (sym_link));   /* copy it */
1578       if ((curr == p) && IS_STRUCT(curr) && SPEC_STRUCT(curr)->type == STRUCT)
1579         {
1580           /* if this is a struct specifier which ends */
1581           /* with an array of unspecified length then */
1582           /* copy the struct and it's fields */
1583           struct symbol *field = SPEC_STRUCT(curr)->fields;
1584           while (field && field->next)
1585             field = field->next; /* find last one */
1586           if (field && IS_ARRAY(field->type) && !DCL_ELEM(field->type))
1587             SPEC_STRUCT(loop) = copyStruct(SPEC_STRUCT(curr));
1588         }
1589       loop->next = (curr->next ? newLink (curr->next->class) : (void *) NULL);
1590       loop = loop->next;
1591       curr = curr->next;
1592     }
1593
1594   return head;
1595 }
1596
1597 /*------------------------------------------------------------------*/
1598 /* cleanUpBlock - cleansup the symbol table specified for all the   */
1599 /*                symbols in the given block                        */
1600 /*------------------------------------------------------------------*/
1601 void 
1602 cleanUpBlock (bucket ** table, int block)
1603 {
1604   int i;
1605   bucket *chain;
1606
1607   /* go thru the entire  table  */
1608   for (i = 0; i < 256; i++)
1609     {
1610       for (chain = table[i]; chain; chain = chain->next)
1611         {
1612           if (chain->block >= block)
1613             {
1614               deleteSym (table, chain->sym, chain->name);
1615             }
1616         }
1617     }
1618 }
1619
1620 /*------------------------------------------------------------------*/
1621 /* cleanUpLevel - cleansup the symbol table specified for all the   */
1622 /*                symbols in the given level                        */
1623 /*------------------------------------------------------------------*/
1624 void 
1625 cleanUpLevel (bucket ** table, int level)
1626 {
1627   int i;
1628   bucket *chain;
1629
1630   /* go thru the entire  table  */
1631   for (i = 0; i < 256; i++)
1632     {
1633       for (chain = table[i]; chain; chain = chain->next)
1634         {
1635           if (chain->level >= level)
1636             {
1637               deleteSym (table, chain->sym, chain->name);
1638             }
1639         }
1640     }
1641 }
1642
1643 /*------------------------------------------------------------------*/
1644 /* computeTypeOr - computes the resultant type from two types       */
1645 /*------------------------------------------------------------------*/
1646 static sym_link *
1647 computeTypeOr (sym_link * etype1, sym_link * etype2, sym_link * reType)
1648 {
1649   /* sanity check */
1650   assert (   (IS_CHAR (etype1) || IS_BIT (etype1))
1651           && (IS_CHAR (etype2) || IS_BIT (etype2)));
1652
1653   if (SPEC_USIGN (etype1) == SPEC_USIGN (etype2))
1654     {
1655       SPEC_USIGN (reType) = SPEC_USIGN (etype1);
1656       return reType;
1657     }
1658   
1659   if (SPEC_USIGN (etype1))
1660     {
1661       if (   IS_LITERAL (etype2)
1662           && floatFromVal (valFromType (etype2)) >= 0)
1663         SPEC_USIGN (reType) = 1;
1664       else
1665         {
1666           /* promote to int */
1667           SPEC_USIGN (reType) = 0;
1668           SPEC_NOUN (reType) = V_INT;
1669         }
1670     }
1671   else /* etype1 signed */
1672     {
1673       if (   IS_LITERAL (etype2)
1674           && floatFromVal (valFromType (etype2)) <= 127)
1675         SPEC_USIGN (reType) = 0;
1676       else
1677         {
1678           /* promote to int */
1679           SPEC_USIGN (reType) = 0;
1680           SPEC_NOUN (reType) = V_INT;
1681         }
1682     }
1683
1684   if (SPEC_USIGN (etype2))
1685     {
1686       if (   IS_LITERAL (etype1)
1687           && floatFromVal (valFromType (etype1)) >= 0)
1688         SPEC_USIGN (reType) = 1;
1689       else
1690         {
1691           /* promote to int */
1692           SPEC_USIGN (reType) = 0;
1693           SPEC_NOUN (reType) = V_INT;
1694         }
1695     }
1696   else /* etype2 signed */
1697     {
1698       if (   IS_LITERAL (etype1)
1699           && floatFromVal (valFromType (etype1)) <= 127)
1700         SPEC_USIGN (reType) = 0;
1701       else
1702         {
1703           /* promote to int */
1704           SPEC_USIGN (reType) = 0;
1705           SPEC_NOUN (reType) = V_INT;
1706         }
1707     }
1708   return reType;
1709 }
1710
1711 /*------------------------------------------------------------------*/
1712 /* computeType - computes the resultant type from two types         */
1713 /*------------------------------------------------------------------*/
1714 sym_link *
1715 computeType (sym_link * type1, sym_link * type2,
1716              RESULT_TYPE resultType, int op)
1717 {
1718   sym_link *rType;
1719   sym_link *reType;
1720   sym_link *etype1 = getSpec (type1);
1721   sym_link *etype2;
1722
1723   etype2 = type2 ? getSpec (type2) : type1;
1724
1725   /* if one of them is a float then result is a float */
1726   /* here we assume that the types passed are okay */
1727   /* and can be cast to one another                */
1728   /* which ever is greater in size */
1729   if (IS_FLOAT (etype1) || IS_FLOAT (etype2))
1730     rType = newFloatLink ();
1731   else
1732     /* if both are bitvars choose the larger one */
1733   if (IS_BITVAR (etype1) && IS_BITVAR (etype2))
1734     {
1735       rType = SPEC_BLEN (etype1) >= SPEC_BLEN (etype2) ?
1736                 copyLinkChain (type1) : copyLinkChain (type1);
1737     }
1738     /* if only one of them is a bit variable
1739        then the other one prevails */
1740   else if (IS_BITVAR (etype1) && !IS_BITVAR (etype2))
1741     {
1742       rType = copyLinkChain (type2);
1743       /* bitfield can have up to 16 bits */
1744       if (getSize (etype1) > 1)
1745         SPEC_NOUN (getSpec (rType)) = V_INT;
1746     }
1747   else if (IS_BITVAR (etype2) && !IS_BITVAR (etype1))
1748     {
1749       rType = copyLinkChain (type1);
1750       /* bitfield can have up to 16 bits */
1751       if (getSize (etype2) > 1)
1752         SPEC_NOUN (getSpec (rType)) = V_INT;
1753     }
1754   else
1755     /* if one of them is a pointer or array then that
1756        prevails */
1757   if (IS_PTR (type1) || IS_ARRAY (type1))
1758     rType = copyLinkChain (type1);
1759   else if (IS_PTR (type2) || IS_ARRAY (type2))
1760     rType = copyLinkChain (type2);
1761   else if (getSize (type1) > getSize (type2))
1762     rType = copyLinkChain (type1);
1763   else
1764     rType = copyLinkChain (type2);
1765
1766   reType = getSpec (rType);
1767
1768   /* avoid conflicting types */
1769   reType->select.s._signed = 0;
1770
1771   /* if result is a literal then make not so */
1772   if (IS_LITERAL (reType))
1773     SPEC_SCLS (reType) = S_REGISTER;
1774
1775   switch (resultType)
1776     {
1777       case RESULT_TYPE_CHAR:
1778         if (IS_BITVAR (reType))
1779           {
1780             SPEC_NOUN (reType) = V_CHAR;
1781             SPEC_SCLS (reType) = 0;
1782             SPEC_USIGN (reType) = 0;
1783             return rType;
1784           }
1785         break;
1786       case RESULT_TYPE_INT:
1787       case RESULT_TYPE_NONE:
1788       case RESULT_TYPE_OTHER:
1789         if (IS_BIT (reType))
1790           {
1791             SPEC_NOUN (reType) = V_CHAR;
1792             SPEC_SCLS (reType) = 0;
1793             SPEC_USIGN (reType) = 0;
1794             return rType;
1795           }
1796         else if (IS_BITFIELD (reType))
1797           {
1798             /* could be smarter, but it depends on the op */
1799             /* this is for the worst case: a multiplication of 4 * 4 bit */
1800             SPEC_NOUN (reType) = SPEC_BLEN (reType) <= 4 ? V_CHAR : V_INT;
1801             SPEC_SCLS (reType) = 0;
1802             SPEC_USIGN (reType) = 0;
1803             return rType;
1804           }
1805         else if (IS_CHAR (reType))
1806           {
1807             if (op == '|' || op == '^')
1808               return computeTypeOr (etype1, etype2, reType);
1809             else if (   op == '&'
1810                      && SPEC_USIGN (etype1) != SPEC_USIGN (etype2))
1811               {
1812                 SPEC_USIGN (reType) = 1;
1813                 return rType;
1814               }
1815             else if (op == '*')
1816               {
1817                 SPEC_NOUN (reType) = V_INT;
1818                 SPEC_USIGN (reType) = 0;
1819                 return rType;
1820               }
1821             /* TODO: should be in SDCCast.c */
1822             else if (   op == '/'
1823                      && (   !SPEC_USIGN (etype1)
1824                          || !SPEC_USIGN (etype2)))
1825               {
1826                 SPEC_NOUN (reType) = V_INT;
1827                 SPEC_USIGN (reType) = 0;
1828                 return rType;
1829               }
1830           }
1831         break;
1832       default:
1833         break;
1834     }
1835
1836   /* SDCC's sign promotion:
1837      - if one or both operands are unsigned, the resultant type will be unsigned
1838        (except char, see below)
1839      - if an operand is promoted to a larger type (char -> int, int -> long),
1840        the larger type will be signed
1841
1842      SDCC tries hard to avoid promotion to int and does 8 bit calculation as
1843      much as possible. We're leaving ISO IEC 9899 here and have to extrapolate
1844      the standard. The standard demands, that the result has to be the same
1845      "as if" the promotion would have been performed:
1846
1847      - if the result of an operation with two char's is promoted to a
1848        larger type, the result will be signed.
1849
1850      More sophisticated are these:
1851      - if the result of an operation with two char's is a char again,
1852        the result will only then be unsigned, if both operands are
1853        unsigned. In all other cases the result will be signed.
1854
1855        This seems to be contradictionary to the first two rules, but it makes
1856        real sense (all types are char's):
1857
1858         A signed char can be negative; this must be preserved in the result
1859                 -1 * 100 = -100;
1860
1861         Only if both operands are unsigned it's safe to make the result
1862         unsigned; this helps to avoid overflow:
1863                 2 * 100 =  200;
1864
1865      - ToDo: document '|', '^' and '&'
1866      
1867      Homework: - why is (200 * 200 < 0) true?
1868                - why is { char l = 200, r = 200; (r * l > 0) } true?
1869   */
1870
1871   if (!IS_FLOAT (reType)
1872       && (   (SPEC_USIGN (etype1)
1873               /* if this operand is promoted to a larger type,
1874                  then it will be promoted to a signed type */
1875               && !(getSize (etype1) < getSize (reType))
1876               /* char require special handling */
1877               && !IS_CHAR (etype1))
1878           || /* same for 2nd operand */  
1879              (SPEC_USIGN (etype2)
1880               && !(getSize (etype2) < getSize (reType))
1881               && !IS_CHAR (etype2))
1882           || /* if both are 'unsigned char' and not promoted
1883                 let the result be unsigned too */
1884              (   SPEC_USIGN (etype1)
1885               && SPEC_USIGN (etype2)
1886               && IS_CHAR (etype1)
1887               && IS_CHAR (etype2)
1888               && IS_CHAR (reType))))
1889     SPEC_USIGN (reType) = 1;
1890   else
1891     SPEC_USIGN (reType) = 0;
1892
1893   return rType;
1894 }
1895
1896 /*--------------------------------------------------------------------*/
1897 /* compareType - will do type check return 1 if match, -1 if castable */
1898 /*--------------------------------------------------------------------*/
1899 int
1900 compareType (sym_link * dest, sym_link * src)
1901 {
1902   if (!dest && !src)
1903     return 1;
1904
1905   if (dest && !src)
1906     return 0;
1907
1908   if (src && !dest)
1909     return 0;
1910
1911   /* if dest is a declarator then */
1912   if (IS_DECL (dest))
1913     {
1914       if (IS_DECL (src))
1915         {
1916           if (DCL_TYPE (src) == DCL_TYPE (dest)) {
1917             if (IS_FUNC(src)) {
1918               //checkFunction(src,dest);
1919             }
1920             return compareType (dest->next, src->next);
1921           }
1922           if (IS_PTR (dest) && IS_GENPTR (src) && IS_VOID(src->next)) {
1923             return -1;
1924           }
1925           if (IS_PTR (src) && IS_GENPTR (dest))
1926             return -1;
1927           if (IS_PTR (dest) && IS_ARRAY (src)) {
1928             value *val=aggregateToPointer (valFromType(src));
1929             int res=compareType (dest, val->type);
1930             Safe_free(val->type);
1931             Safe_free(val);
1932             return res;
1933           }
1934           if (IS_PTR (dest) && IS_FUNC (dest->next) && IS_FUNC (src))
1935             return compareType (dest->next, src);
1936           return 0;
1937         }
1938       else if (IS_PTR (dest) && IS_INTEGRAL (src))
1939         return -1;
1940       else
1941         return 0;
1942     }
1943
1944   /* if one is a specifier and the other is not */
1945   if ((IS_SPEC (src) && !IS_SPEC (dest)) ||
1946       (IS_SPEC (dest) && !IS_SPEC (src)))
1947     return 0;
1948
1949   /* if one of them is a void then ok */
1950   if (SPEC_NOUN (dest) == V_VOID &&
1951       SPEC_NOUN (src) != V_VOID)
1952     return -1;
1953
1954   if (SPEC_NOUN (dest) != V_VOID &&
1955       SPEC_NOUN (src) == V_VOID)
1956     return -1;
1957
1958   /* if they are both bitfields then if the lengths
1959      and starts don't match */
1960   if (IS_BITFIELD (dest) && IS_BITFIELD (src) &&
1961       (SPEC_BLEN (dest) != SPEC_BLEN (src) ||
1962        SPEC_BSTR (dest) != SPEC_BSTR (src)))
1963     return -1;
1964
1965   /* it is a specifier */
1966   if (SPEC_NOUN (dest) != SPEC_NOUN (src))
1967     {
1968       if (SPEC_USIGN (dest) == SPEC_USIGN (src) &&
1969           IS_INTEGRAL (dest) && IS_INTEGRAL (src) &&
1970           /* I would prefer
1971           bitsForType (dest) == bitsForType (src))
1972              instead of the next two lines, but the regression tests fail with
1973              them; I guess it's a problem with replaceCheaperOp  */
1974           getSize (dest) == getSize (src) &&
1975           !(!IS_BIT (dest) && IS_BIT (src)))
1976         return 1;
1977       else if (IS_ARITHMETIC (dest) && IS_ARITHMETIC (src))
1978         return -1;
1979       else
1980         return 0;
1981     }
1982   else if (IS_STRUCT (dest))
1983     {
1984       if (SPEC_STRUCT (dest) != SPEC_STRUCT (src))
1985         return 0;
1986       else
1987         return 1;
1988     }
1989   if (SPEC_LONG (dest) != SPEC_LONG (src))
1990     return -1;
1991
1992   if (SPEC_USIGN (dest) != SPEC_USIGN (src))
1993     return -1;
1994
1995   return 1;
1996 }
1997
1998 /*--------------------------------------------------------------------*/
1999 /* compareTypeExact - will do type check return 1 if match exactly    */
2000 /*--------------------------------------------------------------------*/
2001 int
2002 compareTypeExact (sym_link * dest, sym_link * src, int level)
2003 {
2004   STORAGE_CLASS srcScls, destScls;
2005   
2006   if (!dest && !src)
2007     return 1;
2008
2009   if (dest && !src)
2010     return 0;
2011
2012   if (src && !dest)
2013     return 0;
2014
2015   /* if dest is a declarator then */
2016   if (IS_DECL (dest))
2017     {
2018       if (IS_DECL (src))
2019         {
2020           if (DCL_TYPE (src) == DCL_TYPE (dest)) {
2021             if ((DCL_TYPE (src) == ARRAY) && (DCL_ELEM (src) != DCL_ELEM (dest)))
2022               return 0;
2023             if (DCL_PTR_CONST (src) != DCL_PTR_CONST (dest))
2024               return 0;
2025             if (DCL_PTR_VOLATILE (src) != DCL_PTR_VOLATILE (dest))
2026               return 0;
2027             if (IS_FUNC(src))
2028               {
2029                 value *exargs, *acargs, *checkValue;
2030
2031                 /* verify function return type */
2032                 if (!compareTypeExact (dest->next, src->next, -1))
2033                   return 0;
2034                 if (FUNC_ISISR (dest) != FUNC_ISISR (src))
2035                   return 0;
2036                 if (FUNC_REGBANK (dest) != FUNC_REGBANK (src))
2037                   return 0;
2038                 if (IFFUNC_ISNAKED (dest) != IFFUNC_ISNAKED (src))
2039                   return 0;
2040                 #if 0
2041                 if (IFFUNC_ISREENT (dest) != IFFUNC_ISREENT (src) && argCnt>1)
2042                   return 0;
2043                 #endif
2044
2045                 /* compare expected args with actual args */
2046                 exargs = FUNC_ARGS(dest);
2047                 acargs = FUNC_ARGS(src);
2048
2049                 /* for all the expected args do */
2050                 for (; exargs && acargs; exargs = exargs->next, acargs = acargs->next)
2051                   {
2052                     //checkTypeSanity(acargs->etype, acargs->name);
2053
2054                     if (IS_AGGREGATE (acargs->type))
2055                       {
2056                         checkValue = copyValue (acargs);
2057                         aggregateToPointer (checkValue);
2058                       }
2059                     else
2060                       checkValue = acargs;
2061
2062                     #if 0
2063                     if (!compareTypeExact (exargs->type, checkValue->type, -1))
2064                       return 0;
2065                     #endif
2066                   }
2067
2068                   /* if one them ended we have a problem */
2069                   if ((exargs && !acargs && !IS_VOID (exargs->type)) ||
2070                       (!exargs && acargs && !IS_VOID (acargs->type)))
2071                     return 0;                  
2072                   return 1;
2073               }
2074             return compareTypeExact (dest->next, src->next, level);
2075           }
2076           return 0;
2077         }
2078       return 0;
2079     }
2080
2081   /* if one is a specifier and the other is not */
2082   if ((IS_SPEC (src) && !IS_SPEC (dest)) ||
2083       (IS_SPEC (dest) && !IS_SPEC (src)))
2084     return 0;
2085
2086   /* if one of them is a void then ok */
2087   if (SPEC_NOUN (dest) != SPEC_NOUN (src))
2088     return 0;
2089
2090   /* if they are both bitfields then if the lengths
2091      and starts don't match */
2092   if (IS_BITFIELD (dest) && IS_BITFIELD (src) &&
2093       (SPEC_BLEN (dest) != SPEC_BLEN (src) ||
2094        SPEC_BSTR (dest) != SPEC_BSTR (src)))
2095     return 0;
2096
2097   if (IS_INTEGRAL (dest))
2098     {
2099       /* signedness must match */
2100       if (SPEC_USIGN (dest) != SPEC_USIGN (src))
2101         return 0;
2102       /* size must match */
2103       if (SPEC_LONG (dest) != SPEC_LONG (src))
2104         return 0;
2105       if (SPEC_SHORT (dest) != SPEC_SHORT (src))
2106         return 0;
2107     }
2108   
2109   if (IS_STRUCT (dest))
2110     {
2111       if (SPEC_STRUCT (dest) != SPEC_STRUCT (src))
2112         return 0;
2113     }
2114
2115   if (SPEC_CONST (dest) != SPEC_CONST (src))
2116     return 0;
2117   if (SPEC_VOLATILE (dest) != SPEC_VOLATILE (src))
2118     return 0;
2119   if (SPEC_STAT (dest) != SPEC_STAT (src))
2120     return 0;
2121   if (SPEC_ABSA (dest) != SPEC_ABSA (src))
2122     return 0;
2123   if (SPEC_ABSA (dest) && SPEC_ADDR (dest) != SPEC_ADDR (src))
2124     return 0;
2125       
2126   destScls = SPEC_SCLS (dest);
2127   srcScls = SPEC_SCLS (src);
2128   
2129   /* Compensate for const to const code change in checkSClass() */
2130   if (!level & port->mem.code_ro && SPEC_CONST (dest))
2131     {
2132       if (srcScls == S_CODE && destScls == S_FIXED)
2133         destScls = S_CODE;
2134       if (destScls == S_CODE && srcScls == S_FIXED)
2135         srcScls = S_CODE;
2136     }
2137
2138   /* compensate for allocGlobal() */  
2139   if ((srcScls == S_FIXED || srcScls == S_AUTO)
2140       && port->mem.default_globl_map == xdata
2141       && !level)
2142     srcScls = S_XDATA;
2143   
2144   if (level>0 && !SPEC_STAT (dest))
2145     {
2146       /* Compensate for hack-o-matic in checkSClass() */
2147       if (options.stackAuto || (currFunc && IFFUNC_ISREENT (currFunc->type)))
2148         {
2149           if (destScls == S_FIXED)
2150             destScls = (options.useXstack ? S_XSTACK : S_STACK);
2151           if (srcScls == S_FIXED)
2152             srcScls = (options.useXstack ? S_XSTACK : S_STACK);
2153         }
2154       else if (TARGET_IS_DS390 || TARGET_IS_DS400 || options.useXstack)
2155         {
2156           if (destScls == S_FIXED)
2157             destScls = S_XDATA;
2158           if (srcScls == S_FIXED)
2159             srcScls = S_XDATA;
2160         }
2161     }
2162
2163   if (srcScls != destScls)
2164     {
2165       #if 0
2166       printf ("level = %d\n", level);
2167       printf ("SPEC_SCLS (src) = %d, SPEC_SCLS (dest) = %d\n",
2168                 SPEC_SCLS (src), SPEC_SCLS (dest));
2169       printf ("srcScls = %d, destScls = %d\n",srcScls, destScls);
2170       #endif
2171       return 0;
2172     }
2173   
2174   return 1;
2175 }
2176
2177 /*------------------------------------------------------------------*/
2178 /* inCalleeSaveList - return 1 if found in callee save list          */
2179 /*------------------------------------------------------------------*/
2180 static int
2181 calleeCmp(void *p1, void *p2)
2182 {
2183   return (strcmp((char *)p1, (char *)(p2)) == 0);
2184 }
2185
2186 bool
2187 inCalleeSaveList(char *s)
2188 {
2189   if (options.all_callee_saves)
2190     return 1;
2191   return isinSetWith(options.calleeSavesSet, s, calleeCmp);
2192 }
2193
2194 /*-----------------------------------------------------------------*/
2195 /* aggregateToPointer:  change an agggregate type function      */
2196 /*         argument to a pointer to that type.     */
2197 /*-----------------------------------------------------------------*/
2198 value *
2199 aggregateToPointer (value * val)
2200 {
2201   if (IS_AGGREGATE (val->type))
2202     {
2203       /* if this is a structure */
2204       /* then we need to add a new link */
2205       if (IS_STRUCT (val->type))
2206         {
2207           /* first lets add DECLARATOR type */
2208           sym_link *p = val->type;
2209
2210           werror (W_STRUCT_AS_ARG, val->name);
2211           val->type = newLink (DECLARATOR);
2212           val->type->next = p;
2213         }
2214
2215       /* change to a pointer depending on the */
2216       /* storage class specified        */
2217       switch (SPEC_SCLS (val->etype))
2218         {
2219         case S_IDATA:
2220           DCL_TYPE (val->type) = IPOINTER;
2221           break;
2222         case S_PDATA:
2223           DCL_TYPE (val->type) = PPOINTER;
2224           break;
2225         case S_FIXED:
2226           if (SPEC_OCLS(val->etype)) {
2227             DCL_TYPE(val->type)=PTR_TYPE(SPEC_OCLS(val->etype));
2228           } else {
2229             // this happens for (external) function parameters
2230             DCL_TYPE (val->type) = port->unqualified_pointer;
2231           }
2232           break;
2233         case S_AUTO:
2234         case S_DATA:
2235         case S_REGISTER:
2236           DCL_TYPE (val->type) = POINTER;
2237           break;
2238         case S_CODE:
2239           DCL_TYPE (val->type) = CPOINTER;
2240           break;
2241         case S_XDATA:
2242           DCL_TYPE (val->type) = FPOINTER;
2243           break;
2244         case S_EEPROM:
2245           DCL_TYPE (val->type) = EEPPOINTER;
2246           break;
2247         default:
2248           DCL_TYPE (val->type) = port->unqualified_pointer;
2249         }
2250       
2251       /* is there is a symbol associated then */
2252       /* change the type of the symbol as well */
2253       if (val->sym)
2254         {
2255           val->sym->type = copyLinkChain (val->type);
2256           val->sym->etype = getSpec (val->sym->type);
2257         }
2258     }
2259   return val;
2260 }
2261 /*------------------------------------------------------------------*/
2262 /* checkFunction - does all kinds of check on a function            */
2263 /*------------------------------------------------------------------*/
2264 int 
2265 checkFunction (symbol * sym, symbol *csym)
2266 {
2267   value *exargs, *acargs;
2268   value *checkValue;
2269   int argCnt = 0;
2270
2271   if (getenv("DEBUG_SANITY")) {
2272     fprintf (stderr, "checkFunction: %s ", sym->name);
2273   }
2274
2275   if (!IS_DECL(sym->type) || DCL_TYPE(sym->type)!=FUNCTION)
2276     {
2277       werror(E_SYNTAX_ERROR, sym->name);
2278       return 0;
2279     }
2280     
2281   /* make sure the type is complete and sane */
2282   checkTypeSanity(((symbol *)sym)->etype, ((symbol *)sym)->name);
2283
2284   /* if not type then some kind of error */
2285   if (!sym->type)
2286     return 0;
2287
2288   /* if the function has no type then make it return int */
2289   if (!sym->type->next)
2290     sym->type->next = sym->etype = newIntLink ();
2291
2292   /* function cannot return aggregate */
2293   if (IS_AGGREGATE (sym->type->next))
2294     {
2295       werror (E_FUNC_AGGR, sym->name);
2296       return 0;
2297     }
2298
2299   /* function cannot return bit */
2300   if (IS_BITVAR (sym->type->next))
2301     {
2302       werror (E_FUNC_BIT, sym->name);
2303       return 0;
2304     }
2305
2306   /* check if this function is defined as calleeSaves
2307      then mark it as such */
2308   FUNC_CALLEESAVES(sym->type) = inCalleeSaveList (sym->name);
2309
2310   /* if interrupt service routine  */
2311   /* then it cannot have arguments */
2312   if (IFFUNC_ARGS(sym->type) && FUNC_ISISR (sym->type))
2313     {
2314       if (!IS_VOID(FUNC_ARGS(sym->type)->type)) {
2315         werror (E_INT_ARGS, sym->name);
2316         FUNC_ARGS(sym->type)=NULL;
2317       }
2318     }
2319
2320   for (argCnt=1, acargs = FUNC_ARGS(sym->type); 
2321        acargs; 
2322        acargs=acargs->next, argCnt++) {
2323     if (!acargs->sym) { 
2324       // this can happen for reentrant functions
2325       werror(E_PARAM_NAME_OMITTED, sym->name, argCnt);
2326       // the show must go on: synthesize a name and symbol
2327       SNPRINTF (acargs->name, sizeof(acargs->name), "_%s_PARM_%d", sym->name, argCnt);
2328       acargs->sym = newSymbol (acargs->name, 1);
2329       SPEC_OCLS (acargs->etype) = istack;
2330       acargs->sym->type = copyLinkChain (acargs->type);
2331       acargs->sym->etype = getSpec (acargs->sym->type);
2332       acargs->sym->_isparm = 1;
2333       strncpyz (acargs->sym->rname, acargs->name, sizeof(acargs->sym->rname));
2334     } else if (strcmp(acargs->sym->name, acargs->sym->rname)==0) { 
2335       // synthesized name
2336       werror(E_PARAM_NAME_OMITTED, sym->name, argCnt);
2337     }
2338   }
2339   argCnt--;
2340
2341   if (!csym && !(csym = findSym (SymbolTab, sym, sym->name)))
2342     return 1;                   /* not defined nothing more to check  */
2343
2344   /* check if body already present */
2345   if (csym && IFFUNC_HASBODY(csym->type))
2346     {
2347       werror (E_FUNC_BODY, sym->name);
2348       return 0;
2349     }
2350
2351   /* check the return value type   */
2352   if (compareType (csym->type, sym->type) <= 0)
2353     {
2354       werror (E_PREV_DEF_CONFLICT, csym->name, "type");
2355       printFromToType(csym->type, sym->type);
2356       return 0;
2357     }
2358
2359   if (FUNC_ISISR (csym->type) != FUNC_ISISR (sym->type))
2360     {
2361       werror (E_PREV_DEF_CONFLICT, csym->name, "interrupt");
2362     }
2363
2364   if (FUNC_REGBANK (csym->type) != FUNC_REGBANK (sym->type))
2365     {
2366       werror (E_PREV_DEF_CONFLICT, csym->name, "using");
2367     }
2368
2369   if (IFFUNC_ISNAKED (csym->type) != IFFUNC_ISNAKED (sym->type))
2370     {
2371       werror (E_PREV_DEF_CONFLICT, csym->name, "_naked");
2372     }
2373   
2374   /* Really, reentrant should match regardless of argCnt, but     */
2375   /* this breaks some existing code (the fp lib functions). If    */
2376   /* the first argument is always passed the same way, this       */
2377   /* lax checking is ok (but may not be true for in future ports) */
2378   if (IFFUNC_ISREENT (csym->type) != IFFUNC_ISREENT (sym->type)
2379       && argCnt>1)
2380     {
2381       //printf("argCnt = %d\n",argCnt);
2382       werror (E_PREV_DEF_CONFLICT, csym->name, "reentrant");
2383     }
2384
2385   /* compare expected args with actual args */
2386   exargs = FUNC_ARGS(csym->type);
2387   acargs = FUNC_ARGS(sym->type);
2388
2389   /* for all the expected args do */
2390   for (argCnt = 1;
2391        exargs && acargs;
2392        exargs = exargs->next, acargs = acargs->next, argCnt++)
2393     {
2394       if (getenv("DEBUG_SANITY")) {
2395         fprintf (stderr, "checkFunction: %s ", exargs->name);
2396       }
2397       /* make sure the type is complete and sane */
2398       checkTypeSanity(exargs->etype, exargs->name);
2399
2400       /* If the actual argument is an array, any prototype
2401        * will have modified it to a pointer. Duplicate that
2402        * change here.
2403        */
2404       if (IS_AGGREGATE (acargs->type))
2405         {
2406           checkValue = copyValue (acargs);
2407           aggregateToPointer (checkValue);
2408         }
2409       else
2410         {
2411           checkValue = acargs;
2412         }
2413
2414       if (compareType (exargs->type, checkValue->type) <= 0)
2415         {
2416           werror (E_ARG_TYPE, argCnt);
2417           printFromToType(exargs->type, checkValue->type);
2418           return 0;
2419         }
2420     }
2421
2422   /* if one them ended we have a problem */
2423   if ((exargs && !acargs && !IS_VOID (exargs->type)) ||
2424       (!exargs && acargs && !IS_VOID (acargs->type)))
2425     werror (E_ARG_COUNT);
2426
2427   /* replace with this defition */
2428   sym->cdef = csym->cdef;
2429   deleteSym (SymbolTab, csym, csym->name);
2430   deleteFromSeg(csym);
2431   addSym (SymbolTab, sym, sym->name, sym->level, sym->block, 1);
2432   if (IS_EXTERN (csym->etype) && !
2433       IS_EXTERN (sym->etype))
2434     {
2435       addSet (&publics, sym);
2436     }
2437   return 1;
2438 }
2439
2440 /*------------------------------------------------------------------*/
2441 /* cdbStructBlock - calls struct printing for a blcks               */
2442 /*------------------------------------------------------------------*/
2443 void cdbStructBlock (int block)
2444 {
2445   int i;
2446   bucket **table = StructTab;
2447   bucket *chain;
2448
2449   /* go thru the entire  table  */
2450   for (i = 0; i < 256; i++)
2451     {
2452       for (chain = table[i]; chain; chain = chain->next)
2453         {
2454           if (chain->block >= block)
2455             {
2456               if(debugFile)
2457                 debugFile->writeType((structdef *)chain->sym, chain->block, 0, NULL);
2458             }
2459         }
2460     }
2461 }
2462
2463 /*-----------------------------------------------------------------*/
2464 /* processFuncArgs - does some processing with function args       */
2465 /*-----------------------------------------------------------------*/
2466 void 
2467 processFuncArgs (symbol * func)
2468 {
2469   value *val;
2470   int pNum = 1;
2471   sym_link *funcType=func->type;
2472
2473   if (getenv("SDCC_DEBUG_FUNCTION_POINTERS"))
2474     fprintf (stderr, "SDCCsymt.c:processFuncArgs(%s)\n", func->name);
2475
2476   /* find the function declaration within the type */
2477   while (funcType && !IS_FUNC(funcType))
2478     funcType=funcType->next;
2479
2480   /* if this function has variable argument list */
2481   /* then make the function a reentrant one    */
2482   if (IFFUNC_HASVARARGS(funcType) || (options.stackAuto && !func->cdef))
2483     FUNC_ISREENT(funcType)=1;
2484
2485   /* check if this function is defined as calleeSaves
2486      then mark it as such */
2487   FUNC_CALLEESAVES(funcType) = inCalleeSaveList (func->name);
2488
2489   /* loop thru all the arguments   */
2490   val = FUNC_ARGS(funcType);
2491
2492   /* if it is void then remove parameters */
2493   if (val && IS_VOID (val->type))
2494     {
2495       FUNC_ARGS(funcType) = NULL;
2496       return;
2497     }
2498
2499   /* reset regparm for the port */
2500   (*port->reset_regparms) ();
2501   /* if any of the arguments is an aggregate */
2502   /* change it to pointer to the same type */
2503   while (val)
2504     {
2505         int argreg = 0;
2506       /* mark it as a register parameter if
2507          the function does not have VA_ARG
2508          and as port dictates */
2509       if (!IFFUNC_HASVARARGS(funcType) &&
2510           (argreg = (*port->reg_parm) (val->type)))
2511         {
2512           SPEC_REGPARM (val->etype) = 1;
2513           SPEC_ARGREG(val->etype) = argreg;
2514         } else if (IFFUNC_ISREENT(funcType)) {
2515             FUNC_HASSTACKPARM(funcType) = 1;
2516         }
2517
2518       if (IS_AGGREGATE (val->type))
2519         {
2520           aggregateToPointer (val);
2521         }
2522
2523       val = val->next;
2524       pNum++;
2525     }
2526
2527   /* if this is an internal generated function call */
2528   if (func->cdef) {
2529     /* ignore --stack-auto for this one, we don't know how it is compiled */
2530     /* simply trust on --int-long-reent or --float-reent */
2531     if (IFFUNC_ISREENT(funcType)) {
2532       return;
2533     }
2534   } else {
2535     /* if this function is reentrant or */
2536     /* automatics r 2b stacked then nothing */
2537     if (IFFUNC_ISREENT (funcType) || options.stackAuto)
2538       return;
2539   }
2540
2541   val = FUNC_ARGS(funcType);
2542   pNum = 1;
2543   while (val)
2544     {
2545
2546       /* if a symbolname is not given  */
2547       /* synthesize a variable name */
2548       if (!val->sym)
2549         {
2550           SNPRINTF (val->name, sizeof(val->name), 
2551                     "_%s_PARM_%d", func->name, pNum++);
2552           val->sym = newSymbol (val->name, 1);
2553           SPEC_OCLS (val->etype) = port->mem.default_local_map;
2554           val->sym->type = copyLinkChain (val->type);
2555           val->sym->etype = getSpec (val->sym->type);
2556           val->sym->_isparm = 1;
2557           strncpyz (val->sym->rname, val->name, sizeof(val->sym->rname));
2558           #if 0
2559           /* ?? static functions shouldn't imply static parameters - EEP */
2560           if (IS_SPEC(func->etype)) {
2561             SPEC_STAT (val->etype) = SPEC_STAT (val->sym->etype) =
2562               SPEC_STAT (func->etype);
2563           }
2564           #endif
2565           addSymChain (val->sym);
2566
2567         }
2568       else                      /* symbol name given create synth name */
2569         {
2570
2571           SNPRINTF (val->name, sizeof(val->name), "_%s_PARM_%d", func->name, pNum++);
2572           strncpyz (val->sym->rname, val->name, sizeof(val->sym->rname));
2573           val->sym->_isparm = 1;
2574           SPEC_OCLS (val->etype) = SPEC_OCLS (val->sym->etype) =
2575             (options.model != MODEL_SMALL ? xdata : data);
2576           
2577           #if 0
2578           /* ?? static functions shouldn't imply static parameters - EEP */
2579           if (IS_SPEC(func->etype)) {
2580             SPEC_STAT (val->etype) = SPEC_STAT (val->sym->etype) =
2581               SPEC_STAT (func->etype);
2582           }
2583           #endif
2584         }
2585       if (!isinSet(operKeyReset, val->sym)) {
2586         addSet (&operKeyReset, val->sym);
2587         applyToSet (operKeyReset, resetParmKey);
2588       }
2589       val = val->next;
2590     }
2591 }
2592
2593 /*-----------------------------------------------------------------*/
2594 /* isSymbolEqual - compares two symbols return 1 if they match     */
2595 /*-----------------------------------------------------------------*/
2596 int 
2597 isSymbolEqual (symbol * dest, symbol * src)
2598 {
2599   /* if pointers match then equal */
2600   if (dest == src)
2601     return 1;
2602
2603   /* if one of them is null then don't match */
2604   if (!dest || !src)
2605     return 0;
2606
2607   /* if both of them have rname match on rname */
2608   if (dest->rname[0] && src->rname[0])
2609     return (!strcmp (dest->rname, src->rname));
2610
2611   /* otherwise match on name */
2612   return (!strcmp (dest->name, src->name));
2613 }
2614
2615 void PT(sym_link *type)
2616 {
2617         printTypeChain(type,0);
2618 }
2619 /*-----------------------------------------------------------------*/
2620 /* printTypeChain - prints the type chain in human readable form   */
2621 /*-----------------------------------------------------------------*/
2622 void
2623 printTypeChain (sym_link * start, FILE * of)
2624 {
2625   int nlr = 0;
2626   value *args;
2627   sym_link * type, * search;
2628   STORAGE_CLASS scls;
2629
2630   if (!of)
2631     {
2632       of = stdout;
2633       nlr = 1;
2634     }
2635
2636   if (start==NULL) {
2637     fprintf (of, "void");
2638     return;
2639   }
2640
2641   /* Print the chain as it is written in the source: */
2642   /* start with the last entry.                      */
2643   /* However, the storage class at the end of the    */
2644   /* chain reall applies to the first in the chain!  */
2645
2646   for (type = start; type && type->next; type = type->next)
2647     ;
2648   if (IS_SPEC (type))
2649     scls=SPEC_SCLS(type);
2650   else
2651     scls=0;
2652   while (type)
2653     {
2654       if (type==start) {
2655         switch (scls) 
2656           {
2657           case S_DATA: fprintf (of, "data-"); break;
2658           case S_XDATA: fprintf (of, "xdata-"); break;
2659           case S_SFR: fprintf (of, "sfr-"); break;
2660           case S_SBIT: fprintf (of, "sbit-"); break;
2661           case S_CODE: fprintf (of, "code-"); break;
2662           case S_IDATA: fprintf (of, "idata-"); break;
2663           case S_PDATA: fprintf (of, "pdata-"); break;
2664           case S_LITERAL: fprintf (of, "literal-"); break;
2665           case S_STACK: fprintf (of, "stack-"); break;
2666           case S_XSTACK: fprintf (of, "xstack-"); break;
2667           case S_BIT: fprintf (of, "bit-"); break;
2668           case S_EEPROM: fprintf (of, "eeprom-"); break;
2669           default: break;
2670           }
2671       }
2672
2673       if (IS_DECL (type))
2674         {
2675           if (!IS_FUNC(type)) {
2676             if (DCL_PTR_VOLATILE (type)) {
2677               fprintf (of, "volatile-");
2678             }
2679             if (DCL_PTR_CONST (type)) {
2680               fprintf (of, "const-");
2681             }
2682           }
2683           switch (DCL_TYPE (type))
2684             {
2685             case FUNCTION:
2686               fprintf (of, "function %s %s", 
2687                        (IFFUNC_ISBUILTIN(type) ? "__builtin__" : " "),
2688                        (IFFUNC_ISJAVANATIVE(type) ? "_JavaNative" : " "));
2689               fprintf (of, "( ");
2690               for (args = FUNC_ARGS(type); 
2691                    args; 
2692                    args=args->next) {
2693                 printTypeChain(args->type, of);
2694                 if (args->next)
2695                   fprintf(of, ", ");
2696               }
2697               fprintf (of, ") ");
2698               break;
2699             case GPOINTER:
2700               fprintf (of, "generic* ");
2701               break;
2702             case CPOINTER:
2703               fprintf (of, "code* ");
2704               break;
2705             case FPOINTER:
2706               fprintf (of, "xdata* ");
2707               break;
2708             case EEPPOINTER:
2709               fprintf (of, "eeprom* ");
2710               break;
2711             case POINTER:
2712               fprintf (of, "near* ");
2713               break;
2714             case IPOINTER:
2715               fprintf (of, "idata* ");
2716               break;
2717             case PPOINTER:
2718               fprintf (of, "pdata* ");
2719               break;
2720             case UPOINTER:
2721               fprintf (of, "unknown* ");
2722               break;
2723             case ARRAY:
2724               if (DCL_ELEM(type)) {
2725                 fprintf (of, "[%d] ", DCL_ELEM(type));
2726               } else {
2727                 fprintf (of, "[] ");
2728               }
2729               break;
2730             }
2731         }
2732       else
2733         {
2734           if (SPEC_VOLATILE (type))
2735             fprintf (of, "volatile-");
2736           if (SPEC_CONST (type))
2737             fprintf (of, "const-");
2738           if (SPEC_USIGN (type))
2739             fprintf (of, "unsigned-");
2740           switch (SPEC_NOUN (type))
2741             {
2742             case V_INT:
2743               if (IS_LONG (type))
2744                 fprintf (of, "long-");
2745               fprintf (of, "int");
2746               break;
2747
2748             case V_CHAR:
2749               fprintf (of, "char");
2750               break;
2751
2752             case V_VOID:
2753               fprintf (of, "void");
2754               break;
2755
2756             case V_FLOAT:
2757               fprintf (of, "float");
2758               break;
2759
2760             case V_STRUCT:
2761               fprintf (of, "struct %s", SPEC_STRUCT (type)->tag);
2762               break;
2763
2764             case V_SBIT:
2765               fprintf (of, "sbit");
2766               break;
2767
2768             case V_BIT:
2769               fprintf (of, "bit");
2770               break;
2771
2772             case V_BITFIELD:
2773               fprintf (of, "bitfield {%d,%d}", SPEC_BSTR (type), SPEC_BLEN (type));
2774               break;
2775
2776             case V_DOUBLE:
2777               fprintf (of, "double");
2778               break;
2779
2780             default:
2781               fprintf (of, "unknown type");
2782               break;
2783             }
2784         }
2785       /* search entry in list before "type" */
2786       for (search = start; search && search->next != type;)
2787         search = search->next;
2788       type = search;
2789       if (type)
2790         fputc (' ', of);
2791     }
2792   if (nlr)
2793     fprintf (of, "\n");
2794 }
2795
2796 /*--------------------------------------------------------------------*/
2797 /* printTypeChainRaw - prints the type chain in human readable form   */
2798 /*                     in the raw data structure ordering             */
2799 /*--------------------------------------------------------------------*/
2800 void
2801 printTypeChainRaw (sym_link * start, FILE * of)
2802 {
2803   int nlr = 0;
2804   value *args;
2805   sym_link * type;
2806
2807   if (!of)
2808     {
2809       of = stdout;
2810       nlr = 1;
2811     }
2812
2813   if (start==NULL) {
2814     fprintf (of, "void");
2815     return;
2816   }
2817
2818   type = start;
2819   
2820   while (type)
2821     {
2822       if (IS_DECL (type))
2823         {
2824           if (!IS_FUNC(type)) {
2825             if (DCL_PTR_VOLATILE (type)) {
2826               fprintf (of, "volatile-");
2827             }
2828             if (DCL_PTR_CONST (type)) {
2829               fprintf (of, "const-");
2830             }
2831           }
2832           switch (DCL_TYPE (type))
2833             {
2834             case FUNCTION:
2835               fprintf (of, "function %s %s", 
2836                        (IFFUNC_ISBUILTIN(type) ? "__builtin__" : " "),
2837                        (IFFUNC_ISJAVANATIVE(type) ? "_JavaNative" : " "));
2838               fprintf (of, "( ");
2839               for (args = FUNC_ARGS(type); 
2840                    args; 
2841                    args=args->next) {
2842                 printTypeChain(args->type, of);
2843                 if (args->next)
2844                   fprintf(of, ", ");
2845               }
2846               fprintf (of, ") ");
2847               break;
2848             case GPOINTER:
2849               fprintf (of, "generic* ");
2850               break;
2851             case CPOINTER:
2852               fprintf (of, "code* ");
2853               break;
2854             case FPOINTER:
2855               fprintf (of, "xdata* ");
2856               break;
2857             case EEPPOINTER:
2858               fprintf (of, "eeprom* ");
2859               break;
2860             case POINTER:
2861               fprintf (of, "near* ");
2862               break;
2863             case IPOINTER:
2864               fprintf (of, "idata* ");
2865               break;
2866             case PPOINTER:
2867               fprintf (of, "pdata* ");
2868               break;
2869             case UPOINTER:
2870               fprintf (of, "unknown* ");
2871               break;
2872             case ARRAY:
2873               if (DCL_ELEM(type)) {
2874                 fprintf (of, "[%d] ", DCL_ELEM(type));
2875               } else {
2876                 fprintf (of, "[] ");
2877               }
2878               break;
2879             }
2880           if (DCL_TSPEC(type))
2881             {
2882               fprintf (of, "{");
2883               printTypeChainRaw(DCL_TSPEC(type), of);
2884               fprintf (of, "}");
2885             }
2886         }
2887       else if (IS_SPEC (type))
2888         {
2889         switch (SPEC_SCLS (type)) 
2890           {
2891           case S_DATA: fprintf (of, "data-"); break;
2892           case S_XDATA: fprintf (of, "xdata-"); break;
2893           case S_SFR: fprintf (of, "sfr-"); break;
2894           case S_SBIT: fprintf (of, "sbit-"); break;
2895           case S_CODE: fprintf (of, "code-"); break;
2896           case S_IDATA: fprintf (of, "idata-"); break;
2897           case S_PDATA: fprintf (of, "pdata-"); break;
2898           case S_LITERAL: fprintf (of, "literal-"); break;
2899           case S_STACK: fprintf (of, "stack-"); break;
2900           case S_XSTACK: fprintf (of, "xstack-"); break;
2901           case S_BIT: fprintf (of, "bit-"); break;
2902           case S_EEPROM: fprintf (of, "eeprom-"); break;
2903           default: break;
2904           }
2905           if (SPEC_VOLATILE (type))
2906             fprintf (of, "volatile-");
2907           if (SPEC_CONST (type))
2908             fprintf (of, "const-");
2909           if (SPEC_USIGN (type))
2910             fprintf (of, "unsigned-");
2911           switch (SPEC_NOUN (type))
2912             {
2913             case V_INT:
2914               if (IS_LONG (type))
2915                 fprintf (of, "long-");
2916               fprintf (of, "int");
2917               break;
2918
2919             case V_CHAR:
2920               fprintf (of, "char");
2921               break;
2922
2923             case V_VOID:
2924               fprintf (of, "void");
2925               break;
2926
2927             case V_FLOAT:
2928               fprintf (of, "float");
2929               break;
2930
2931             case V_STRUCT:
2932               fprintf (of, "struct %s", SPEC_STRUCT (type)->tag);
2933               break;
2934
2935             case V_SBIT:
2936               fprintf (of, "sbit");
2937               break;
2938
2939             case V_BIT:
2940               fprintf (of, "bit");
2941               break;
2942
2943             case V_BITFIELD:
2944               fprintf (of, "bitfield {%d,%d}", SPEC_BSTR (type), SPEC_BLEN (type));
2945               break;
2946
2947             case V_DOUBLE:
2948               fprintf (of, "double");
2949               break;
2950
2951             default:
2952               fprintf (of, "unknown type");
2953               break;
2954             }
2955         }
2956       else
2957         fprintf (of, "NOT_SPEC_OR_DECL");
2958       type = type->next;
2959       if (type)
2960         fputc (' ', of);
2961     }
2962   if (nlr)
2963     fprintf (of, "\n");
2964 }
2965
2966
2967 /*-----------------------------------------------------------------*/
2968 /* powof2 - returns power of two for the number if number is pow 2 */
2969 /*-----------------------------------------------------------------*/
2970 int
2971 powof2 (TYPE_UDWORD num)
2972 {
2973   int nshifts = 0;
2974   int n1s = 0;
2975
2976   while (num)
2977     {
2978       if (num & 1)
2979         n1s++;
2980       num >>= 1;
2981       nshifts++;
2982     }
2983
2984   if (n1s > 1 || nshifts == 0)
2985     return 0;
2986   return nshifts - 1;
2987 }
2988
2989 symbol *__fsadd;
2990 symbol *__fssub;
2991 symbol *__fsmul;
2992 symbol *__fsdiv;
2993 symbol *__fseq;
2994 symbol *__fsneq;
2995 symbol *__fslt;
2996 symbol *__fslteq;
2997 symbol *__fsgt;
2998 symbol *__fsgteq;
2999
3000 /* Dims: mul/div/mod, BYTE/WORD/DWORD, SIGNED/UNSIGNED */
3001 symbol *__muldiv[3][3][2];
3002 /* Dims: BYTE/WORD/DWORD SIGNED/UNSIGNED */
3003 sym_link *__multypes[3][2];
3004 /* Dims: to/from float, BYTE/WORD/DWORD, SIGNED/USIGNED */
3005 symbol *__conv[2][3][2];
3006 /* Dims: shift left/shift right, BYTE/WORD/DWORD, SIGNED/UNSIGNED */
3007 symbol *__rlrr[2][3][2];
3008
3009 sym_link *floatType;
3010
3011 static char *
3012 _mangleFunctionName(char *in)
3013 {
3014   if (port->getMangledFunctionName)
3015     {
3016       return port->getMangledFunctionName(in);
3017     }
3018   else
3019     {
3020       return in;
3021     }
3022 }
3023
3024 /*-----------------------------------------------------------------*/
3025 /* typeFromStr - create a typechain from an encoded string         */
3026 /* basic types -        'c' - char                                 */
3027 /*                      's' - short                                */
3028 /*                      'i' - int                                  */
3029 /*                      'l' - long                                 */
3030 /*                      'f' - float                                */
3031 /*                      'v' - void                                 */
3032 /*                      '*' - pointer - default (GPOINTER)         */
3033 /* modifiers -          'u' - unsigned                             */
3034 /* pointer modifiers -  'g' - generic                              */
3035 /*                      'x' - xdata                                */
3036 /*                      'p' - code                                 */
3037 /*                      'd' - data                                 */                     
3038 /*                      'F' - function                             */                     
3039 /* examples : "ig*" - generic int *                                */
3040 /*            "cx*" - char xdata *                                 */
3041 /*            "ui" -  unsigned int                                 */
3042 /*-----------------------------------------------------------------*/
3043 sym_link *typeFromStr (char *s)
3044 {
3045     sym_link *r = newLink(DECLARATOR);
3046     int usign = 0;
3047
3048     do {
3049         sym_link *nr;
3050         switch (*s) {
3051         case 'u' : 
3052             usign = 1;
3053             s++;
3054             continue ;
3055             break ;
3056         case 'c':
3057             r->class = SPECIFIER;
3058             SPEC_NOUN(r) = V_CHAR;
3059             break;
3060         case 's':
3061         case 'i':
3062             r->class = SPECIFIER;
3063             SPEC_NOUN(r) = V_INT;
3064             break;
3065         case 'l':
3066             r->class = SPECIFIER;
3067             SPEC_NOUN(r) = V_INT;
3068             SPEC_LONG(r) = 1;
3069             break;
3070         case 'f':
3071             r->class = SPECIFIER;
3072             SPEC_NOUN(r) = V_FLOAT;
3073             break;
3074         case 'v':
3075             r->class = SPECIFIER;
3076             SPEC_NOUN(r) = V_VOID;
3077             break;
3078         case '*':
3079             DCL_TYPE(r) = port->unqualified_pointer;
3080             break;
3081         case 'g':
3082         case 'x':
3083         case 'p':
3084         case 'd':
3085         case 'F':
3086             assert(*(s+1)=='*');
3087             nr = newLink(DECLARATOR);
3088             nr->next = r;
3089             r = nr;
3090             switch (*s) {
3091             case 'g':
3092                 DCL_TYPE(r) = GPOINTER;
3093                 break;
3094             case 'x':
3095                 DCL_TYPE(r) = FPOINTER;
3096                 break;
3097             case 'p':
3098                 DCL_TYPE(r) = CPOINTER;
3099                 break;
3100             case 'd':
3101                 DCL_TYPE(r) = POINTER;
3102                 break;
3103             case 'F':
3104                 DCL_TYPE(r) = FUNCTION;
3105                 nr = newLink(DECLARATOR);
3106                 nr->next = r;
3107                 r = nr;
3108                 DCL_TYPE(r) = CPOINTER;
3109                 break;
3110             }
3111             s++;
3112             break;
3113         default:
3114             werror(E_INTERNAL_ERROR, __FILE__, __LINE__, 
3115                    "typeFromStr: unknown type");
3116             break;
3117         }
3118         if (IS_SPEC(r) && usign) {
3119             SPEC_USIGN(r) = 1;
3120             usign = 0;
3121         }
3122         s++;
3123     } while (*s);
3124     return r;
3125 }
3126
3127 /*-----------------------------------------------------------------*/
3128 /* initCSupport - create functions for C support routines          */
3129 /*-----------------------------------------------------------------*/
3130 void 
3131 initCSupport ()
3132 {
3133   const char *smuldivmod[] =
3134   {
3135     "mul", "div", "mod"
3136   };
3137   const char *sbwd[] =
3138   {
3139     "char", "int", "long"
3140   };
3141   const char *ssu[] =
3142   {
3143     "s", "u"
3144   };
3145   const char *srlrr[] =
3146   {
3147     "rl", "rr"
3148   };
3149
3150   int bwd, su, muldivmod, tofrom, rlrr;
3151
3152   if (getenv("SDCC_NO_C_SUPPORT")) {
3153     /* for debugging only */
3154     return;
3155   }
3156
3157   floatType = newFloatLink ();
3158
3159   for (bwd = 0; bwd < 3; bwd++)
3160     {
3161       sym_link *l = NULL;
3162       switch (bwd)
3163         {
3164         case 0:
3165           l = newCharLink ();
3166           break;
3167         case 1:
3168           l = newIntLink ();
3169           break;
3170         case 2:
3171           l = newLongLink ();
3172           break;
3173         default:
3174           assert (0);
3175         }
3176       __multypes[bwd][0] = l;
3177       __multypes[bwd][1] = copyLinkChain (l);
3178       SPEC_USIGN (__multypes[bwd][1]) = 1;
3179     }
3180
3181   __fsadd = funcOfType ("__fsadd", floatType, floatType, 2, options.float_rent);
3182   __fssub = funcOfType ("__fssub", floatType, floatType, 2, options.float_rent);
3183   __fsmul = funcOfType ("__fsmul", floatType, floatType, 2, options.float_rent);
3184   __fsdiv = funcOfType ("__fsdiv", floatType, floatType, 2, options.float_rent);
3185   __fseq = funcOfType ("__fseq", CHARTYPE, floatType, 2, options.float_rent);
3186   __fsneq = funcOfType ("__fsneq", CHARTYPE, floatType, 2, options.float_rent);
3187   __fslt = funcOfType ("__fslt", CHARTYPE, floatType, 2, options.float_rent);
3188   __fslteq = funcOfType ("__fslteq", CHARTYPE, floatType, 2, options.float_rent);
3189   __fsgt = funcOfType ("__fsgt", CHARTYPE, floatType, 2, options.float_rent);
3190   __fsgteq = funcOfType ("__fsgteq", CHARTYPE, floatType, 2, options.float_rent);
3191
3192   for (tofrom = 0; tofrom < 2; tofrom++)
3193     {
3194       for (bwd = 0; bwd < 3; bwd++)
3195         {
3196           for (su = 0; su < 2; su++)
3197             {
3198               if (tofrom)
3199                 {
3200                   SNPRINTF (buffer, sizeof(buffer), "__fs2%s%s", ssu[su], sbwd[bwd]);
3201                   __conv[tofrom][bwd][su] = funcOfType (buffer, __multypes[bwd][su], floatType, 1, options.float_rent);
3202                 }
3203               else
3204                 {
3205                   SNPRINTF (buffer, sizeof(buffer), "__%s%s2fs", ssu[su], sbwd[bwd]);
3206                   __conv[tofrom][bwd][su] = funcOfType (buffer, floatType, __multypes[bwd][su], 1, options.float_rent);
3207                 }
3208             }
3209         }
3210     }
3211
3212 /*
3213   for (muldivmod = 0; muldivmod < 3; muldivmod++)
3214     {
3215       for (bwd = 0; bwd < 3; bwd++)
3216         {
3217           for (su = 0; su < 2; su++)
3218             {
3219               SNPRINTF (buffer, sizeof(buffer),
3220                         "_%s%s%s",
3221                        smuldivmod[muldivmod],
3222                        ssu[su],
3223                        sbwd[bwd]);
3224               __muldiv[muldivmod][bwd][su] = funcOfType (_mangleFunctionName(buffer), __multypes[bwd][su], __multypes[bwd][su], 2, options.intlong_rent);
3225               FUNC_NONBANKED (__muldiv[muldivmod][bwd][su]->type) = 1;
3226             }
3227         }
3228     }
3229
3230   muluint() and mulsint() resp. mululong() and mulslong() return the same result.
3231   Therefore they've been merged into mulint() and mullong().
3232 */
3233
3234   for (bwd = 0; bwd < 3; bwd++)
3235     {
3236       for (su = 0; su < 2; su++)
3237         {
3238           for (muldivmod = 1; muldivmod < 3; muldivmod++)
3239             {
3240               /* div and mod */
3241               SNPRINTF (buffer, sizeof(buffer),
3242                         "_%s%s%s",
3243                        smuldivmod[muldivmod],
3244                        ssu[su],
3245                        sbwd[bwd]);
3246               __muldiv[muldivmod][bwd][su] = funcOfType (_mangleFunctionName(buffer), __multypes[bwd][su], __multypes[bwd][su], 2, options.intlong_rent);
3247               FUNC_NONBANKED (__muldiv[muldivmod][bwd][su]->type) = 1;
3248             }
3249         }
3250     }
3251   /* mul only */
3252   muldivmod = 0;
3253   /* byte */
3254   bwd = 0;
3255   for (su = 0; su < 2; su++)
3256     {
3257       /* muluchar and mulschar are still separate functions, because e.g. the z80
3258          port is sign/zero-extending to int before calling mulint() */
3259       SNPRINTF (buffer, sizeof(buffer),
3260                 "_%s%s%s",
3261                 smuldivmod[muldivmod],
3262                 ssu[su],
3263                 sbwd[bwd]);
3264       __muldiv[muldivmod][bwd][su] = funcOfType (_mangleFunctionName(buffer), __multypes[bwd][su], __multypes[bwd][su], 2, options.intlong_rent);
3265       FUNC_NONBANKED (__muldiv[muldivmod][bwd][su]->type) = 1;
3266     }
3267   /* signed only */
3268   su = 0;
3269   /* word and doubleword */
3270   for (bwd = 1; bwd < 3; bwd++)
3271     {
3272       /* mul, int/long */
3273       SNPRINTF (buffer, sizeof(buffer),
3274                 "_%s%s",
3275                 smuldivmod[muldivmod],
3276                 sbwd[bwd]);
3277       __muldiv[muldivmod][bwd][0] = funcOfType (_mangleFunctionName(buffer), __multypes[bwd][su], __multypes[bwd][su], 2, options.intlong_rent);
3278       FUNC_NONBANKED (__muldiv[muldivmod][bwd][0]->type) = 1;
3279       /* signed = unsigned */
3280       __muldiv[muldivmod][bwd][1] = __muldiv[muldivmod][bwd][0];
3281     }
3282
3283   for (rlrr = 0; rlrr < 2; rlrr++)
3284     {
3285       for (bwd = 0; bwd < 3; bwd++)
3286         {
3287           for (su = 0; su < 2; su++)
3288             {
3289               SNPRINTF (buffer, sizeof(buffer),
3290                         "_%s%s%s",
3291                        srlrr[rlrr],
3292                        ssu[su],
3293                        sbwd[bwd]);
3294               __rlrr[rlrr][bwd][su] = funcOfType (_mangleFunctionName(buffer), __multypes[bwd][su], __multypes[0][0], 2, options.intlong_rent);
3295               FUNC_NONBANKED (__rlrr[rlrr][bwd][su]->type) = 1;
3296             }
3297         }
3298     }
3299 }
3300
3301 /*-----------------------------------------------------------------*/
3302 /* initBuiltIns - create prototypes for builtin functions          */
3303 /*-----------------------------------------------------------------*/
3304 void initBuiltIns()
3305 {
3306     int i;
3307     symbol *sym;
3308
3309     if (!port->builtintable) return ;
3310
3311     for (i = 0 ; port->builtintable[i].name ; i++) {
3312         sym = funcOfTypeVarg(port->builtintable[i].name,port->builtintable[i].rtype,
3313                              port->builtintable[i].nParms,port->builtintable[i].parm_types);
3314         FUNC_ISBUILTIN(sym->type) = 1;
3315         FUNC_ISREENT(sym->type) = 0;    /* can never be reentrant */
3316     }
3317 }
3318
3319 sym_link *validateLink(sym_link         *l, 
3320                         const char      *macro,
3321                         const char      *args,
3322                         const char      select,
3323                         const char      *file, 
3324                         unsigned        line)
3325 {    
3326   if (l && l->class==select)
3327     {
3328         return l;
3329     }
3330     fprintf(stderr, 
3331             "Internal error: validateLink failed in %s(%s) @ %s:%u:"
3332             " expected %s, got %s\n",
3333             macro, args, file, line, 
3334             DECLSPEC2TXT(select), l ? DECLSPEC2TXT(l->class) : "null-link");
3335     exit(-1);
3336     return l; // never reached, makes compiler happy.
3337 }
3338
3339 /*--------------------------------------------------------------------*/
3340 /* newEnumType - create an integer type compatible with enumerations  */
3341 /*--------------------------------------------------------------------*/
3342 sym_link *
3343 newEnumType (symbol *enumlist)
3344 {
3345   int min, max, v;
3346   symbol *sym;
3347   sym_link *type;
3348
3349   if (!enumlist)
3350     {
3351       type = newLink (SPECIFIER);
3352       SPEC_NOUN (type) = V_INT;
3353       return type;
3354     }
3355       
3356   /* Determine the range of the enumerated values */
3357   sym = enumlist;
3358   min = max = (int) floatFromVal (valFromType (sym->type));
3359   for (sym = sym->next; sym; sym = sym->next)
3360     {
3361       v = (int) floatFromVal (valFromType (sym->type));
3362       if (v<min)
3363         min = v;
3364       if (v>max)
3365         max = v;
3366     }
3367
3368   /* Determine the smallest integer type that is compatible with this range */
3369   type = newLink (SPECIFIER);
3370   if (min>=0 && max<=255)
3371     {
3372       SPEC_NOUN (type) = V_CHAR;
3373       SPEC_USIGN (type) = 1;
3374     }
3375   else if (min>=-128 && max<=127)
3376     {
3377       SPEC_NOUN (type) = V_CHAR;
3378     }
3379   else if (min>=0 && max<=65535)
3380     {
3381       SPEC_NOUN (type) = V_INT;
3382       SPEC_USIGN (type) = 1;
3383     }
3384   else if (min>=-32768 && max<=32767)
3385     {
3386       SPEC_NOUN (type) = V_INT;
3387     }
3388   else
3389     {
3390       SPEC_NOUN (type) = V_INT;
3391       SPEC_LONG (type) = 1;
3392       if (min>=0)
3393         SPEC_USIGN (type) = 1;
3394     }
3395   
3396   return type;    
3397 }