]> andersk Git - splint.git/blob - src/ctype.c
Dave's Updates
[splint.git] / src / ctype.c
1 /*
2 ** LCLint - annotation-assisted static program checker
3 ** Copyright (C) 1994-2001 University of Virginia,
4 **         Massachusetts Institute of Technology
5 **
6 ** This program is free software; you can redistribute it and/or modify it
7 ** under the terms of the GNU General Public License as published by the
8 ** Free Software Foundation; either version 2 of the License, or (at your
9 ** option) any later version.
10 ** 
11 ** This program is distributed in the hope that it will be useful, but
12 ** WITHOUT ANY WARRANTY; without even the implied warranty of
13 ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14 ** General Public License for more details.
15 ** 
16 ** The GNU General Public License is available from http://www.gnu.org/ or
17 ** the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
18 ** MA 02111-1307, USA.
19 **
20 ** For information on lclint: lclint-request@cs.virginia.edu
21 ** To report a bug: lclint-bug@cs.virginia.edu
22 ** For more information: http://lclint.cs.virginia.edu
23 */
24 /*
25 ** ctype.c
26 **
27 ** This files implements three types: ctentry, cttable and ctype.
28 ** They should probably be separated soon.
29 */
30
31 # include "lclintMacros.nf"
32 # include "basic.h"
33 # include "structNames.h"
34
35 static void ctype_recordConj (ctype p_c);
36
37
38 /*
39 ** ctbase file
40 */
41
42 # include "ctbase.i"
43
44 /*
45 ** ctype table
46 */
47
48 # include "cttable.i"
49
50 static ctype ctype_getConjA (ctype p_c) /*@*/ ;
51 static ctype ctype_getConjB (ctype p_c) /*@*/ ;
52
53 static bool ctype_isComplex (ctype c)
54 {
55   return (ctentry_isComplex (ctype_getCtentry(c)));
56 }
57
58 static bool ctype_isPlain (ctype c)
59 {
60   return (ctentry_isPlain (ctype_getCtentry(c)));
61 }
62
63 static bool ctype_isBroken (ctype c)
64 {
65   /*@+enumint@*/
66   if (c == CTK_DNE || c == CTK_INVALID || c == CTK_UNKNOWN)
67     {
68       /*@-enumint@*/
69       return TRUE;
70     }
71   else
72     {
73       ctentry cte = ctype_getCtentry (c);
74
75       return (ctentry_isBogus (cte));
76     }
77 }
78
79 ctkind
80 ctkind_fromInt (int i)
81 {
82   /*@+enumint@*/
83   if (i < CTK_UNKNOWN || i > CTK_COMPLEX)
84     {
85       llcontbug (message ("ctkind_fromInt: out of range: %d", i));
86       return CTK_INVALID;
87     }
88   return (ctkind) i;
89   /*@=enumint@*/
90 }
91
92 /*
93 ** ctype functions
94 */
95
96 void
97 ctype_initTable ()
98 {
99   cttable_init ();
100 }
101
102 void
103 ctype_destroyMod ()
104 {
105   cttable_reset ();
106 }
107
108 void
109 ctype_loadTable (FILE *f)
110 {
111   DPRINTF (("Loading cttable!"));
112   cttable_load (f);
113 }
114
115 void
116 ctype_dumpTable (FILE *f)
117 {
118   DPRINTF (("Dumping cttable!"));
119   cttable_dump (f);
120 }
121
122 cstring
123 ctype_unparseTable ()
124 {
125   return (cttable_unparse ());
126 }
127
128 void
129 ctype_printTable ()
130 {
131   cttable_print ();
132 }
133
134 bool
135 ctype_isUserBool (ctype ct)
136 {
137   if (ctype_isUA (ct))
138     {
139       return (usymtab_isBoolType (ctype_typeId (ct)));
140     }
141   
142   return (FALSE);
143 }
144
145 ctype
146 ctype_createUser (typeId u)
147 {
148   /* requires: ctype_createUser (u) is never called more than once for any u. */
149
150   ctbase ct = ctbase_createUser (u);
151   return (cttable_addFullSafe (ctentry_makeNew (CTK_PLAIN, ct)));
152 }
153
154 ctype
155 ctype_createAbstract (typeId u)
156 {
157  /* requires: ctype_createAbstract (u) is never called more than once for any u. */
158  /*           [ tested by cttable_addFullSafe, not really required ]            */
159   return (cttable_addFullSafe (ctentry_makeNew (CTK_PLAIN, ctbase_createAbstract (u))));
160 }
161
162 int
163 ctype_count (void)
164 {
165   return (cttab.size);
166 }
167
168 ctype
169 ctype_realType (ctype c)
170 {
171   ctype r = c;
172
173   if (ctype_isElips (c) || ctype_isMissingParamsMarker (c))
174     {
175       return c;
176     }
177
178   if (ctype_isUA (c))
179     {
180       r = uentry_getRealType (usymtab_getTypeEntry (ctype_typeId (c)));
181     }
182   
183   if (ctype_isManifestBool (r))
184     {
185       if (context_canAccessBool ())      
186         {
187           r = context_boolImplementationType ();
188         }
189     }
190   
191   return r;
192 }
193
194 bool
195 ctype_isSimple (ctype c)
196 {
197   return (!(ctype_isPointer (c) 
198             || ctype_isArray (c)
199             || ctype_isFunction (c)));
200 }
201
202 ctype
203 ctype_forceRealType (ctype c)
204 {
205   ctype r = c;
206
207   if (ctype_isUA (c))
208     {
209       r = uentry_getForceRealType (usymtab_getTypeEntry (ctype_typeId (c)));
210     }
211   
212   return r;
213 }
214
215 ctype
216 ctype_realishType (ctype c)
217 {
218   if (ctype_isUA (c))
219     {
220       if (ctype_isManifestBool (c))
221         {
222           return ctype_bool;
223         }
224       else
225         {
226           ctype r = uentry_getRealType (usymtab_getTypeEntry 
227                                         (ctype_typeId (c)));
228           return (r);
229         }
230     }
231
232   return c;
233 }
234
235 bool
236 ctype_isUA (ctype c)
237 {
238   return (!ctype_isUnknown (c) && ctbase_isUA (ctype_getCtbase (c)));
239 }
240
241 bool
242 ctype_isUser (ctype c)
243 {
244   return (!ctype_isUnknown (c) && ctbase_isUser (ctype_getCtbase (c)));
245 }
246
247 bool
248 ctype_isAbstract (ctype c)
249 {
250   return (!ctype_isUnknown (c) 
251           && ((ctype_isPlain (c) && ctbase_isAbstract (ctype_getCtbaseSafe (c))) ||
252               (ctype_isConj (c) &&
253                (ctype_isAbstract (ctype_getConjA (c)) 
254                 || ctype_isAbstract (ctype_getConjB (c))))));
255 }
256
257 bool
258 ctype_isImmutableAbstract (ctype t)
259 {
260   return (ctype_isAbstract (t) && !ctype_isMutable (t));
261 }
262
263 bool
264 ctype_isRealAbstract (ctype c)
265 {
266   return (ctype_isAbstract (ctype_realType (c)) ||
267           (ctype_isConj (c) && 
268            (ctype_isRealAbstract (ctype_getConjA (c)) || 
269             ctype_isRealAbstract (ctype_getConjB (c)))));
270 }
271
272 /*
273 ** primitive creators
274 */
275
276 /*
277 ** createPrim not necessary --- subsumed by ctype_int, etc.
278 */
279
280 /*
281 ** ctbase_unknown --- removed argument
282 */
283
284 /*
285 ** derived types:
286 **    requires:  if DerivedType (T) exists in cttable, then T->derivedType is it.
287 */
288
289 ctype
290 ctype_makePointer (ctype c)
291 {
292   if (c == ctype_char)
293     {
294       return ctype_string;
295     }
296   else if (c == ctype_void)
297     {
298       return ctype_voidPointer;
299     }
300   else
301     {
302       ctentry cte = ctype_getCtentry (c);
303       ctype clp = ctentry_getPtr (cte);
304       
305       if /*@+enumint@*/ (clp == CTK_DNE) /*@=enumint@*/
306         {
307           ctype cnew = cttable_addDerived (CTK_PTR, ctbase_makePointer (c), c);
308           ctentry_setPtr (cte, cnew);
309           return (cnew);
310         }
311       else
312         {
313           return clp;
314         }
315     }
316 }
317
318 ctype ctype_makeFixedArray (ctype c, long size)
319 {
320   return (cttable_addDerived (CTK_ARRAY, ctbase_makeFixedArray (c, size), c));
321 }
322
323 ctype
324 ctype_makeArray (ctype c)
325 {
326   ctentry cte = ctype_getCtentry (c);
327   ctype clp = ctentry_getArray (cte);
328
329   if /*@+enumint@*/ (clp == CTK_DNE) /*@=enumint@*/
330     {
331       ctype cnew = cttable_addDerived (CTK_ARRAY, ctbase_makeArray (c), c);
332       ctentry_setArray (cte, cnew);
333       return (cnew);
334     }
335   else
336     return clp;
337 }
338
339 /*
340 ** requires c is a pointer of array
341 */
342
343 ctype
344 ctype_baseArrayPtr (ctype c)
345 {
346   ctentry cte = ctype_getCtentry (ctype_realType (c));
347
348   if (ctype_isConj (c))
349     {
350       if (ctype_isAP (ctype_getConjA (c)))
351         {
352           if (ctype_isAP (ctype_getConjB (c)))
353             {
354               return (ctype_makeConj (ctype_baseArrayPtr (ctype_getConjA (c)),
355                                       ctype_baseArrayPtr (ctype_getConjB (c))));
356             }
357           else
358             {
359               return (ctype_baseArrayPtr (ctype_getConjA (c)));
360             }
361         }
362       else
363         {
364           return (ctype_baseArrayPtr (ctype_getConjB (c)));
365         }
366     }
367   else if (ctype_isInt (c)) /* could be NULL */
368     {
369       return ctype_unknown;
370     }
371   else
372     {
373       ctype clp = ctentry_getBase (cte);
374
375       if (ctype_isBroken (clp))
376         {
377           llbuglit ("ctype_baseArrayPtr: bogus ctype");
378         }
379
380       return clp;
381     }
382 }
383
384 ctype
385 ctype_getReturnType (ctype c)
386 {
387   if (ctype_isUnknown (c))
388     {
389       return ctype_unknown;
390     }
391
392   return (ctbase_baseFunction (ctype_getCtbaseSafe (c)));
393 }
394
395 /*
396 ** must be a shared pointer
397 */
398
399 /*@observer@*/ uentryList
400 ctype_argsFunction (ctype c)
401 {
402   if (ctype_isUnknown (c))
403     {
404       return uentryList_undefined;
405     }
406
407   return (ctbase_argsFunction (ctype_getCtbaseSafe (c)));
408 }
409
410 /*
411 ** Returns type with base type p and compound types from c.
412 **
413 ** i.e.,  c = char *[]; p = int
414 **     => int *[]
415 */
416
417 ctype
418 ctype_newBase (ctype c, ctype p)
419 {
420   return (ctbase_newBase (c, p));
421 }
422
423 bool
424 ctype_sameAltTypes (ctype c1, ctype c2)
425 {
426   ctype c1a, c2a;
427   ctype c1b, c2b;
428
429   llassert (ctype_isConj (c1) && ctype_isConj (c2));
430
431   c1a = ctype_getConjA (c1);
432   c2a = ctype_getConjA (c2);
433
434   c1b = ctype_getConjB (c1);
435   c2b = ctype_getConjB (c2);
436
437   if (ctype_compare (c1a, c2a) == 0)
438     {
439       if (ctype_compare (c1b, c2b) == 0)
440         {
441           return TRUE;
442         }
443       else
444         {
445           if (ctype_isConj (c1b) && ctype_isConj (c2b))
446             {
447               return ctype_sameAltTypes (c1b, c2b);
448             }
449           else
450             {
451               return FALSE;
452             }
453         }
454     }
455   else
456     {
457       if (ctype_compare (c1a, c2b) == 0)
458         {
459           if (ctype_compare (c1b, c2a) == 0)
460             {
461               return TRUE;
462             }
463           else
464             {
465               if (ctype_isConj (c1b) && ctype_isConj (c2a))
466                 {
467                   return ctype_sameAltTypes (c1b, c2a);
468                 }
469               else
470                 {
471                   return FALSE;
472                 }
473             }
474         }
475       else
476         {
477           return FALSE;
478         }
479     }
480 }
481
482 int
483 ctype_compare (ctype c1, ctype c2)
484 {
485   ctentry ce1;
486   ctentry ce2;
487
488   if (ctype_isUnknown (c1))
489     {
490       if (ctype_isUnknown (c2))
491         {
492           return 0;
493         }
494       else
495         {
496           return  1;
497         }
498     }
499   
500   if (ctype_isUnknown (c2))
501     {
502       return -1;
503     }
504
505   /* Can't get entries for special ctypes (elips marker) */
506
507   if (ctype_isElips (c1) || ctype_isElips (c2)
508       || ctype_isMissingParamsMarker (c1) || ctype_isMissingParamsMarker (c2)) {
509     return int_compare (c1, c2);
510   }
511
512   ce1 = ctype_getCtentry (c1);
513   ce2 = ctype_getCtentry (c2);
514
515   if (ctentry_isComplex (ce1))
516     {
517       if (ctentry_isComplex (ce2))
518         {
519           return (ctbase_compare (ctype_getCtbase (c1),
520                                   ctype_getCtbase (c2), FALSE));
521         }
522       else
523         {
524           return 1;
525         }
526     }
527   else if (ctentry_isComplex (ce2))
528     {
529       return -1;
530     }
531   else
532     {
533       return (int_compare (c1, c2));
534     }
535 }
536
537 /*
538 ** complex types
539 */
540
541 /*
542 ** makeFunction:  pointer to function returning base
543 */
544
545 ctype
546 ctype_makeParamsFunction (ctype base, /*@only@*/ uentryList p)
547 {
548   uentryList_fixImpParams (p);
549   return (ctype_makeFunction (base, p));
550 }
551
552 ctype
553 ctype_makeNFParamsFunction (ctype base, /*@only@*/ uentryList p)
554 {
555   uentryList_fixImpParams (p);
556   return (ctbase_makeNFFunction (base, p));
557 }
558
559 ctype
560 ctype_makeFunction (ctype base, /*@only@*/ uentryList p)
561 {
562   ctype ret;
563   ret = ctbase_makeFunction (base, p);
564   return (ret);
565 }
566
567 ctype ctype_expectFunction (ctype c)
568 {
569   /* handle parenthesized declarations */
570
571   if (!ctype_isAP (c))
572     {
573       c = ctype_makePointer (c);
574     }
575
576   return (cttable_addComplex (ctbase_expectFunction (c)));
577 }
578
579 /*
580 ** makeRealFunction: function returning base
581 */
582
583 ctype ctype_makeRawFunction (ctype base, uentryList p)
584 {
585   return (cttable_addComplex (ctbase_makeLiveFunction (base, p)));
586 }
587
588 /*
589 ** plain predicates
590 */
591
592 /***
593 **** this is very poorly defined
594 ****
595 **** need to unify function/function pointer meaning
596 ***/
597
598 bool
599 ctype_isFunction (ctype c)
600 {
601   if (ctype_isKnown (c) && ctype_isDefined (c))
602     {
603       return (ctbase_isFunction (ctype_getCtbase (c)));
604     }
605   else
606     {
607       return FALSE;
608     }
609 }
610
611 bool
612 ctype_isExpFcn (ctype c)
613 {
614   return (ctype_isKnown (c) && ctbase_isExpFcn (ctype_getCtbase (c))); 
615 }
616
617 bool
618 ctype_isVoid (ctype c)
619 {
620   return (c == CTX_VOID);
621 }
622
623 bool
624 ctype_isArbitraryIntegral (ctype c)
625 {
626   ctype cr = ctype_realType (c);
627
628   return (cr == ctype_anyintegral || cr == ctype_unsignedintegral 
629           || cr == ctype_signedintegral);
630 }
631
632 bool
633 ctype_isUnsignedIntegral (ctype c)
634 {
635   ctype cr = ctype_realType (c);
636
637   return (cr == ctype_unsignedintegral);
638 }
639
640 bool
641 ctype_isSignedIntegral (ctype c)
642 {
643   ctype cr = ctype_realType (c);
644
645   return (cr == ctype_signedintegral);
646 }
647
648 bool
649 ctype_isInt (ctype c)
650 {
651   cprim cp = ctype_toCprim (c);
652
653   return (c == ctype_unknown || cprim_isAnyInt (cp)
654           || (cprim_isAnyChar (cp) && context_msgCharInt ())
655           || (c == ctype_bool && context_msgBoolInt ()) 
656           || (ctype_isEnum (c) && context_msgEnumInt ()));
657 }
658
659 bool
660 ctype_isRegularInt (ctype c)
661 {
662   cprim cp = ctype_toCprim (c);
663
664   return (c == ctype_unknown
665           || cprim_closeEnough (cprim_int, cp)
666           || (cprim_isAnyChar (cp) && context_msgCharInt ())
667           || (c == ctype_bool && context_msgBoolInt ()) 
668           || (ctype_isEnum (c) && context_msgEnumInt ()));
669 }
670
671 bool
672 ctype_isString (ctype c)
673 {
674   return (c == ctype_string 
675           || (ctype_isPointer (c)
676               && ctype_isChar (ctype_baseArrayPtr (c))));
677 }
678
679 bool
680 ctype_isChar (ctype c)
681 {
682    return ((c == ctype_unknown) || (cprim_isAnyChar (ctype_toCprim (c)))
683           || (context_getFlag (FLG_CHARINT) && ctype_isInt (c))); 
684 }
685
686 bool
687 ctype_isUnsignedChar (ctype c)
688 {
689   return ((c == ctype_unknown) || (cprim_isUnsignedChar (ctype_toCprim (c))));
690 }
691
692 bool
693 ctype_isSignedChar (ctype c)
694 {
695   return ((c == ctype_unknown) || (cprim_isSignedChar (ctype_toCprim (c))));
696 }
697
698 /*
699 ** Returns true if c matches the name -booltype <bool>
700 */
701
702 bool
703 ctype_isManifestBool (ctype c)
704 {
705   /*
706   ** Changed the meaning of ctype_isBool - evs 2000-07-24
707   ** The old meaning was very convoluted!
708   **
709   ** c is a bool if:
710   **       c == CTX_BOOL - its a direct bool
711   **       c is a user/abstract type matching the bool name
712   **            (should never occur?)
713   */
714
715   if (ctype_isDirectBool (c)) {
716     return TRUE;
717   } else if (ctype_isUA (c)) {
718     return ctype_isUserBool (c);
719   } else {
720     return FALSE;
721   }
722 }
723
724 bool
725 ctype_isBool (ctype c)
726 {
727   /*
728   ** Changed the meaning of ctype_isBool - evs 2000-07-24
729   ** The old meaning was very convoluted!
730   **
731   ** c is a bool if:
732   **       its a manifest bool
733   **       +boolint and ctype_isInt (c)
734   */
735
736   if (ctype_isManifestBool (c)) {
737     return TRUE;
738   } else if (context_msgBoolInt ()) {
739     return ctype_isInt (c);
740   } else {
741     return FALSE;
742   }
743
744 # if 0
745   if (context_getFlag (FLG_ABSTRACTBOOL))
746     {
747       if (typeId_isInvalid (boolType))
748         { 
749           boolType = usymtab_getTypeId (context_getBoolName ());
750         } 
751       
752       if (context_hasAccess (boolType))
753         {
754           return (((c == CTX_UNKNOWN) || (c == CTX_BOOL) 
755                    || (context_msgBoolInt () 
756                        && (c == CTX_INT 
757                            || (c == CTX_CHAR && context_msgCharInt ()))))
758                   || ctype_isInt (c));
759         }
760     }
761   
762   return ((c == CTX_UNKNOWN) || (c == CTX_BOOL)
763           || (context_msgBoolInt ()
764               && (c == CTX_INT || (c == CTX_CHAR && context_msgCharInt ()))));
765 # endif
766 }
767
768 bool
769 ctype_isDirectBool (ctype c)
770 {
771   return (c == CTX_BOOL);
772 }
773
774 bool
775 ctype_isReal (ctype c)
776 {
777   return (cprim_isAnyReal (ctype_toCprim (c)));
778 }
779
780 bool
781 ctype_isFloat (ctype c)
782 {
783   return (c == ctype_float);
784 }
785
786 bool
787 ctype_isDouble (ctype c)
788 {
789   return (c == ctype_double || c == ctype_ldouble);
790 }
791
792 bool
793 ctype_isSigned (ctype c)
794 {
795   return (!ctype_isUnsigned (c));
796 }
797
798 bool
799 ctype_isNumeric (ctype c)
800 {
801   return (ctype_isInt (c) || ctype_isReal (c) || ctype_isEnum (c));
802 }
803
804
805 /*
806 ** real predicates
807 **
808 ** work on actual type in current context
809 */
810
811 bool
812 ctype_isRealNumeric (ctype c)
813 {
814   if (ctype_isPlain (c))
815     return (ctype_isNumeric (ctype_realType (c)));
816   if (ctype_isConj (c))
817     return (ctype_isRealNumeric (ctype_getConjA (c)) ||
818             ctype_isRealNumeric (ctype_getConjB (c)));
819   else
820     return FALSE;
821 }
822
823 bool
824 ctype_isRealInt (ctype c)
825 {
826   if (ctype_isPlain (c))
827     return (ctype_isInt (ctype_realType (c)));
828   else if (ctype_isConj (c))
829     return (ctype_isRealInt (ctype_getConjA (c)) ||
830             ctype_isRealInt (ctype_getConjB (c)));
831   else
832     {
833       if (ctype_isEnum (c) && context_msgEnumInt ()) return TRUE;
834       return FALSE;
835     }
836 }
837
838 bool
839 ctype_isRealVoid (ctype c)
840 {
841   if (ctype_isPlain (c))
842     {
843       return (ctype_isVoid (ctype_realType (c)));
844     }
845   else if (ctype_isConj (c))
846     {
847       return (ctype_isRealVoid (ctype_getConjA (c)) ||
848               ctype_isRealVoid (ctype_getConjB (c)));
849     }
850   else
851     {
852       return FALSE;
853     }
854 }
855
856 bool
857 ctype_isRealBool (ctype c)
858 {
859   if (ctype_isPlain (c))
860     {
861       return (ctype_isBool (ctype_realishType (c)));
862     }
863   else if (ctype_isConj (c))
864     {
865       return (ctype_isRealBool (ctype_getConjA (c)) ||
866               ctype_isRealBool (ctype_getConjB (c)));
867     }
868   else
869     {
870       return FALSE;
871     }
872 }
873
874 bool
875 ctype_isRealPointer (ctype c)
876 {
877   if (ctype_isConj (c))
878     return (ctype_isRealPointer (ctype_getConjA (c)) ||
879             ctype_isRealPointer (ctype_getConjB (c)));
880   return (ctype_isPointer (ctype_realType (c)));
881 }
882
883 bool
884 ctype_isRealSU (ctype c)
885 {
886   if (ctype_isConj (c))
887     {
888       return (ctype_isRealSU (ctype_getConjA (c)) ||
889               ctype_isRealSU (ctype_getConjB (c)));
890     }
891
892   DPRINTF (("Real su: %s / %s", ctype_unparse (c), ctype_unparse (ctype_realType (c))));
893   return (ctype_isStructorUnion (ctype_realType (c)));
894 }
895   
896 bool
897 ctype_isRealArray (ctype c)
898 {
899   if (ctype_isConj (c))
900     return (ctype_isRealArray (ctype_getConjA (c)) ||
901             ctype_isRealArray (ctype_getConjB (c)));
902   return (ctype_isArray (ctype_realType (c)));
903 }
904
905 bool
906 ctype_isRealAP (ctype c)
907 {
908   if (ctype_isConj (c))
909     return (ctype_isRealAP (ctype_getConjA (c)) ||
910             ctype_isRealAP (ctype_getConjB (c)));
911   return (ctype_isAP (ctype_realType (c)));
912 }
913
914 bool
915 ctype_isRealFunction (ctype c)
916 {
917   if (ctype_isConj (c))
918     return (ctype_isRealFunction (ctype_getConjA (c)) ||
919             ctype_isRealFunction (ctype_getConjB (c)));
920   return (ctype_isFunction (ctype_realType (c)));
921 }
922
923 bool
924 ctype_isDirectInt (ctype c)
925 {
926   return (c == CTX_INT || c == CTX_UINT || c == CTX_SINT || c == CTX_ULINT || c == CTX_USINT);
927 }
928
929 /*
930 ** forceful predicates
931 **
932 ** take *ctype; if its a conjunct, and there is a match replace with match only.
933 **                                 if both match, still conjunct
934 */
935
936 static bool
937   ctype_isForcePred (ctype * c, bool (pred) (ctype))
938 {
939   if (ctype_isConj (*c))
940     {
941       ctype cbr = ctype_getConjA (*c);
942
943       if ((*pred) (cbr))
944         {
945           if ((*pred) (ctype_getConjB (*c)))
946             {
947               ;
948             }
949           else
950             {
951               *c = cbr;
952             }
953
954           return TRUE;
955         }
956       else 
957         {
958           if ((*pred) (cbr = ctype_getConjB (*c)))
959             {
960               *c = cbr;
961               return TRUE;
962             }
963         }
964     }
965
966   return ((*pred) (*c));
967 }
968
969 bool
970 ctype_isForceRealNumeric (ctype * c)
971 {
972   return (ctype_isForcePred (c, ctype_isRealNumeric));
973 }
974
975 bool
976 ctype_isForceRealInt (ctype * c)
977 {
978   return (ctype_isForcePred (c, ctype_isRealInt));
979 }
980
981 bool
982 ctype_isForceRealBool (ctype * c)
983 {
984   return (ctype_isForcePred (c, ctype_isRealBool));
985 }
986
987 /*
988 ** conjuncts
989 **
990 ** save int/char, int/bool, other random conjuncts
991 */
992
993 static ctype
994 ctype_makeConjAux (ctype c1, ctype c2, bool isExplicit)
995 {
996   if (ctype_isBogus (c1) || ctype_isUndefined (c1))
997     {
998       return c2;
999     }
1000   else if (ctype_isBogus (c2) || ctype_isUndefined (c2))
1001     {
1002       return c1;
1003     }
1004   else
1005     {
1006       if (isExplicit)
1007         {
1008           return (ctype_makeExplicitConj (c1, c2));
1009         }
1010       else
1011         {
1012           return (ctype_makeConj (c1, c2));
1013         }
1014     }
1015 }
1016
1017 ctype
1018 ctype_makeExplicitConj (ctype c1, ctype c2)
1019 {
1020   if (ctype_isFunction (c1) && !ctype_isFunction (c2))
1021     {
1022       ctype ret = ctype_makeExplicitConj (ctype_getReturnType (c1), c2);
1023
1024       return ctype_makeFunction (ret, uentryList_copy (ctype_getParams (c1)));
1025     }
1026   else if (ctype_isFunction (c2) && !ctype_isFunction (c1))
1027     {
1028       ctype ret = ctype_makeExplicitConj (c1, ctype_getReturnType (c2));
1029
1030       return ctype_makeFunction (ret, uentryList_copy (ctype_getParams (c2)));
1031     }
1032   else
1033     {
1034       return (cttable_addComplex (ctbase_makeConj (c1, c2, TRUE)));
1035     }
1036 }
1037
1038 static ctype ic = ctype_unknown;   /* int | char */
1039 static ctype ib = ctype_unknown;   /* int | bool */
1040 static ctype ifl = ctype_unknown;  /* int | float */
1041 static ctype ibf = ctype_unknown;  /* int | bool | float */
1042 static ctype ibc = ctype_unknown;  /* int | bool | char */
1043 static ctype iv = ctype_unknown;   /* int | void * */
1044 static ctype ivf = ctype_unknown;  /* int | void * | float */
1045 static ctype ivb = ctype_unknown;  /* int | void * | bool */
1046 static ctype ivbf = ctype_unknown; /* int | void * | bool | float */
1047 static ctype cuc = ctype_unknown;  /* char | unsigned char */
1048
1049 static void
1050 ctype_recordConj (ctype c)
1051 {
1052   ctype c1, c2;
1053   
1054   llassert (ctype_isConj (c));
1055
1056   c1 = ctype_getConjA (c);
1057   c2 = ctype_getConjB (c);
1058
1059   /* No, can't swap!
1060   if (c2 == ctype_int && c1 != ctype_int) 
1061     {
1062       ctype tmp;
1063
1064       tmp = c1;
1065       c1 = c2;
1066       c2 = tmp;
1067     }
1068     */
1069
1070   if (c1 == ctype_int)
1071     {
1072       if (c2 == ctype_char)
1073         {
1074           llassert (ic == ctype_unknown);
1075           ic = c;
1076         }
1077       else if (c2 == ctype_bool)
1078         {
1079           llassert (ib == ctype_unknown);
1080           ib = c;
1081         }
1082       else if (c2 == ctype_float)
1083         {
1084           llassert (ifl == ctype_unknown);
1085           ifl = c;
1086         }
1087       else if (c2 == CTP_VOID)
1088         {
1089           llassert (iv == ctype_unknown); 
1090           iv = c;
1091         }
1092       else
1093         {
1094           /* not special */
1095         }
1096     }
1097   else if (c1 == ib && ib != ctype_unknown)
1098     {
1099       if (c2 == ctype_float)
1100         {
1101           llassert (ibf == ctype_unknown);
1102           ibf = c;
1103         }        
1104       else if (c2 == ctype_char)
1105         {
1106           llassert (ibc == ctype_unknown);
1107           ibc = c;
1108         }       
1109       else
1110         {
1111           /* not special */
1112         }
1113     }
1114   else if (c1 == iv)
1115     {
1116       if (c2 == ctype_bool)
1117         {
1118           llassert (ivb == ctype_unknown);
1119           ivb = c;
1120         }
1121       else if (c2 == ctype_float)
1122         {
1123           llassert (ivf == ctype_unknown);
1124           ivf = c;
1125         }
1126       else
1127         {
1128           /* not special */
1129         }
1130     }
1131   else if (c1 == ivf)
1132     {
1133       if (c2 == ctype_bool)
1134         {
1135           llassert (ivbf == ctype_unknown);
1136           ivbf = c;
1137         }
1138     }
1139   else if (c1 == ivb)
1140     {
1141       if (c2 == ctype_float)
1142         {
1143           llassert (ivbf == ctype_unknown);
1144           ivbf  = c;
1145         }
1146     }
1147   else if (c1 == ctype_char)
1148     {
1149       if (c2 == ctype_uchar)
1150         {
1151           llassert (cuc == ctype_unknown);
1152
1153           cuc = c;
1154         }
1155     }
1156   else
1157     {
1158       /* not special */
1159     }
1160 }
1161
1162 ctype
1163 ctype_makeConj (ctype c1, ctype c2)
1164 {
1165   /* no: can have unsigned long @alt long@: llassert (c1 != c2); */
1166
1167   DPRINTF (("Make conj: %s / %s", ctype_unparse (c1), ctype_unparse (c2)));
1168
1169   if (ctype_isUnknown (c1)) 
1170     {
1171       return c2;
1172     }
1173   else if (ctype_isUnknown (c2))
1174     {
1175       return c1;
1176     }
1177   else if (ctype_isFunction (c1) && !ctype_isFunction (c2))
1178     {
1179       ctype ret = ctype_makeConj (ctype_getReturnType (c1), c2);
1180       return ctype_makeFunction (ret, uentryList_copy (ctype_getParams (c1)));
1181     }
1182   else if (ctype_isFunction (c2) && !ctype_isFunction (c1))
1183     {
1184       ctype ret = ctype_makeConj (c1, ctype_getReturnType (c2));
1185       return ctype_makeFunction (ret, uentryList_copy (ctype_getParams (c2)));
1186     }
1187   else
1188     {
1189       if (ctype_isManifestBool (c1))
1190         {
1191           c1 = ctype_bool;
1192         }
1193       
1194       if (ctype_isManifestBool (c2))
1195         {
1196           c2 = ctype_bool;
1197         }
1198       
1199       if (ctbase_isVoidPointer (ctype_getCtbaseSafe (c1)))
1200         {
1201           c1 = ctype_voidPointer;
1202         }
1203       
1204       if (ctbase_isVoidPointer (ctype_getCtbaseSafe (c2)))
1205         {
1206           c2 = ctype_voidPointer;
1207         }
1208
1209       /*
1210       ** Ouch, can't do this.  unsigned, etc. modifiers might
1211       ** apply to wrong type!
1212       **
1213       ** if (c2 == ctype_int && c1 != ctype_int) 
1214       ** {
1215       **  ctype tmp;
1216       **
1217       **  tmp = c1;
1218       **  c1 = c2;
1219       **  c2 = tmp;
1220       ** }
1221       **
1222       */
1223
1224       if (c1 == ctype_int)
1225         {
1226           if (c2 == ctype_char)
1227             {
1228               if (ic == ctype_unknown)
1229                 {
1230                   ic = cttable_addComplex (ctbase_makeConj (ctype_int, ctype_char, FALSE));
1231                 }
1232               
1233               return ic;
1234             }
1235           else if (c2 == ctype_bool)
1236             {
1237               if (ib == ctype_unknown)
1238                 {
1239                   ib = cttable_addComplex 
1240                     (ctbase_makeConj (ctype_int, ctype_bool, FALSE));
1241                 }
1242               
1243               return ib;
1244             }
1245           else if (c2 == ctype_float)
1246             {
1247               if (ifl == ctype_unknown)
1248                 {
1249                   ifl = cttable_addComplex (ctbase_makeConj (ctype_int, ctype_float, FALSE));
1250                 }
1251               
1252               return ifl;
1253             }
1254           else 
1255             {
1256               if (c2 == ctype_voidPointer)
1257                 {
1258                   if (iv == ctype_unknown)
1259                     {
1260                       iv = cttable_addComplex
1261                         (ctbase_makeConj (ctype_int, 
1262                                           ctype_voidPointer,
1263                                           FALSE));
1264                     }
1265                   
1266                   return iv;
1267                 }
1268             }
1269         }
1270       else if (c1 == ib && ib != ctype_unknown)
1271         {
1272           if (c2 == ctype_float)
1273             {
1274               if (ibf == ctype_unknown)
1275                 {
1276                   ibf = cttable_addComplex (ctbase_makeConj (ib, ctype_float, FALSE));
1277                 }
1278               
1279               return ibf;
1280             }    
1281           else if (c2 == ctype_char)
1282             {
1283               if (ibc == ctype_unknown)
1284                 {
1285                   ibc = cttable_addComplex (ctbase_makeConj (ib, ctype_char, FALSE));
1286                 }
1287               
1288               return ibc;
1289             }    
1290           else
1291             {
1292               ;
1293             }
1294         }
1295       else if (c1 == iv)
1296         {
1297           if (c2 == ctype_bool)
1298             {
1299               if (ivb == ctype_unknown)
1300                 {
1301                   ivb = cttable_addComplex (ctbase_makeConj (c1, c2, FALSE));
1302                 }
1303               
1304               return ivb;
1305             }
1306           else if (c2 == ctype_float)
1307             {
1308               if (ivf == ctype_unknown)
1309                 {
1310                   ivf = cttable_addComplex (ctbase_makeConj (c1, c2, FALSE));
1311                 }
1312               
1313               return ivf;
1314             }
1315           else
1316             {
1317               ;
1318             }
1319         }
1320       else if (c1 == ivf)
1321         {
1322           if (c2 == ctype_bool)
1323             {
1324               if (ivbf == ctype_unknown)
1325                 {
1326                   ivbf = cttable_addComplex (ctbase_makeConj (c1, c2, FALSE));
1327                 }
1328               
1329               return ivbf;
1330             }
1331         }
1332       else if (c1 == ivb)
1333         {
1334           if (c2 == ctype_float)
1335             {
1336               if (ivbf == ctype_unknown)
1337                 {
1338                   ivbf = cttable_addComplex (ctbase_makeConj (c1, c2, FALSE));
1339                 }
1340               
1341                       return ivbf;
1342             }
1343         }
1344       else if (c1 == ctype_char)
1345         {
1346           if (c2 == ctype_uchar)
1347             {
1348               if (cuc == ctype_unknown)
1349                 {
1350                   cuc = cttable_addComplex (ctbase_makeConj (c1, c2, FALSE));
1351                 }
1352               
1353                       return cuc;
1354             }
1355         }
1356       else
1357         {
1358           ;
1359         }
1360
1361       
1362       return (cttable_addComplex (ctbase_makeConj (c1, c2, FALSE)));
1363     }
1364 }
1365
1366
1367 bool
1368 ctype_isConj (ctype c)
1369 {
1370   return (ctype_isComplex (c) && ctbase_isConj (ctype_getCtbase (c)));
1371 }
1372
1373 static ctype
1374 ctype_getConjA (ctype c)
1375 {
1376   if (!ctype_isConj (c))
1377     llbuglit ("ctype_getConjA: not a conj");
1378   return (ctbase_getConjA (ctype_getCtbaseSafe (c)));
1379 }
1380
1381 static ctype
1382 ctype_getConjB (ctype c)
1383 {
1384   if (!ctype_isConj (c))
1385     llbuglit ("ctype_getConjB: not a conj");
1386   return (ctbase_getConjB (ctype_getCtbaseSafe (c)));
1387 }
1388
1389 static bool
1390 ctype_isExplicitConj (ctype c)
1391 {
1392   return (ctype_isConj (c) && ctbase_isExplicitConj (ctype_getCtbaseSafe (c)));
1393 }
1394
1395 /** << need to fix resolveConj >> **/
1396
1397 /*
1398 ** structs and unions
1399 */
1400
1401 ctype
1402 ctype_createStruct (/*@only@*/ cstring n, /*@only@*/ uentryList f)
1403 {
1404   ctype ct;
1405
1406   DPRINTF (("Creating a struct: %s / %s",
1407             n, uentryList_unparse (f)));
1408
1409   ct = cttable_addComplex (ctbase_createStruct (n, f));
1410   DPRINTF (("ct: %s", ctype_unparse (ct)));
1411   return (ct);
1412 }
1413
1414 uentryList
1415 ctype_getFields (ctype c)
1416 {
1417   return (ctbase_getuentryList (ctype_getCtbaseSafe (c)));
1418 }
1419
1420 ctype
1421 ctype_createUnion (/*@only@*/ cstring n, /*@only@*/ uentryList f)
1422 {
1423   ctype ret;
1424
1425   ret = cttable_addComplex (ctbase_createUnion (n, f));
1426   return ret;
1427 }
1428
1429 /*
1430 ** matching
1431 **
1432 ** if ctype's are same, definite match.
1433 ** else, need to call ctbase_match.
1434 **
1435 ** if necessary context can memoize matches
1436 */
1437
1438 static bool
1439   quickMatch (ctype c1, ctype c2)
1440 {
1441   if (c1 == c2)
1442     return TRUE;
1443
1444   return FALSE;
1445 }
1446
1447 bool
1448 ctype_genMatch (ctype c1, ctype c2, bool force, bool arg, bool def, bool deep)
1449 {
1450   bool match;
1451
1452   DPRINTF (("Gen match: %s / %s arg: %s", ctype_unparse (c1), ctype_unparse (c2), bool_unparse (arg)));
1453
1454   if (quickMatch (c1, c2))
1455     {
1456       return TRUE;
1457     }
1458
1459   if (ctype_isElips (c1) || ctype_isElips (c2))
1460     {
1461       return FALSE;
1462     }
1463   else
1464     {
1465       match = ctbase_genMatch (ctype_getCtbase (c1), ctype_getCtbase (c2), force, arg, def, deep);
1466       return (match);
1467     }
1468 }
1469
1470 bool
1471 ctype_sameName (ctype c1, ctype c2)
1472 {
1473   if (quickMatch (c1, c2))
1474     return TRUE;
1475   else
1476     return (cstring_equal (ctype_unparse (c1), ctype_unparse (c2)));
1477 }
1478
1479 bool 
1480 ctype_almostEqual (ctype c1, ctype c2)
1481 {
1482   if (ctype_equal (c1, c2))
1483     {
1484       return TRUE;
1485     }
1486   else
1487     {
1488       if (ctype_isUnknown (c1))
1489         {
1490           return ctype_isUnknown (c2);
1491         }
1492       else if (ctype_isUnknown (c2))
1493         {
1494           return FALSE;
1495         }
1496       else
1497         {
1498           return (ctbase_almostEqual (ctype_getCtbase (c1), ctype_getCtbase (c2)));
1499         }
1500     }
1501 }
1502  
1503 bool
1504 ctype_matchDef (ctype c1, ctype c2)
1505 {
1506   DPRINTF (("Match def: %s / %s", ctype_unparse (c1), ctype_unparse (c2)));
1507
1508   if (quickMatch (c1, c2))
1509     return TRUE;
1510
1511   if (ctype_isElips (c1))
1512     return (ctype_isElips (c2) || ctype_isUnknown (c2));
1513
1514   if (ctype_isElips (c2))
1515     {
1516       return (ctype_isUnknown (c2));
1517     }
1518   else
1519     {
1520       bool oldrelax = context_getFlag (FLG_RELAXQUALS);
1521       bool res;
1522
1523       context_setFlagTemp (FLG_RELAXQUALS, FALSE);
1524       res = ctbase_matchDef (ctype_getCtbase (c1), ctype_getCtbase (c2));
1525       context_setFlagTemp (FLG_RELAXQUALS, oldrelax);
1526       return res;
1527     }
1528 }
1529
1530 bool ctype_match (ctype c1, ctype c2)
1531 {
1532   if (quickMatch (c1, c2))
1533     return TRUE;
1534
1535   if (ctype_isElips (c1))
1536     return (ctype_isElips (c2) || ctype_isUnknown (c2));
1537
1538   if (ctype_isElips (c2))
1539     return (ctype_isUnknown (c2));
1540  
1541   return (ctbase_match (ctype_getCtbase (c1), ctype_getCtbase (c2)));
1542 }
1543
1544 bool
1545 ctype_forceMatch (ctype c1, ctype c2)
1546 {
1547   if (quickMatch (c1, c2))
1548     return TRUE;
1549
1550   if (ctype_isElips (c1))
1551     return (ctype_isElips (c2));
1552
1553   if (ctype_isElips (c2))
1554     return FALSE;
1555
1556   /*@-modobserver@*/
1557   /* The call forceMatch may modify the observer params, but, we don't care. */
1558   return (ctbase_forceMatch (ctype_getCtbase (c1), ctype_getCtbase (c2)));
1559   /*@=modobserver@*/
1560 }
1561
1562 bool
1563 ctype_matchArg (ctype c1, ctype c2)
1564 {
1565   if (quickMatch (c1, c2))
1566     {
1567       return TRUE;
1568     }
1569   else
1570     {
1571       return (ctbase_matchArg (ctype_getCtbase (c1), ctype_getCtbase (c2)));
1572     }
1573 }
1574
1575 /*
1576 ** simple ctype_is operations.
1577 ** DO NOT use real type of c, only direct type.
1578 */
1579
1580 /*
1581 ** ctype_isVoidPointer
1582 **
1583 ** void *
1584 */
1585
1586 bool
1587 ctype_isVoidPointer (ctype c)
1588 {
1589   if (ctype_isComplex (c))
1590     {
1591       return ctbase_isVoidPointer (ctype_getCtbaseSafe (c));
1592     }
1593   if (ctype_isConj (c))
1594     {
1595       return (ctype_isVoidPointer (ctype_getConjA (c)) ||
1596               ctype_isVoidPointer (ctype_getConjB (c)));
1597     }
1598   else
1599     {
1600       return (c == ctype_voidPointer
1601               || (ctype_isRealPointer (c) 
1602                   && ctype_isVoid (ctype_baseArrayPtr (c))));
1603     }
1604 }
1605
1606 /*
1607 ** ctype_isPointer
1608 **
1609 ** true for C and LCL pointers
1610 */
1611
1612 bool
1613 ctype_isPointer (ctype c)
1614 {
1615   if (ctype_isElips (c)) return FALSE;
1616
1617   if (ctype_isComplex (c))
1618     {
1619       ctbase ctb = ctype_getCtbaseSafe (c);
1620       bool res = ctbase_isPointer (ctb);
1621
1622       return res;
1623     }
1624   else
1625     {
1626       bool res = ctentry_isPointer (ctype_getCtentry (c));
1627
1628       return res;
1629     }
1630 }
1631
1632 /*
1633 ** ctype_isArray
1634 **
1635 ** true for C and LCL array's
1636 */
1637
1638 bool
1639 ctype_isArray (ctype c)
1640 {
1641   if (ctype_isElips (c)) return FALSE;
1642
1643   if (ctype_isComplex (c))
1644     return (ctbase_isEitherArray (ctype_getCtbaseSafe (c)));
1645   else
1646     return (ctentry_isArray (ctype_getCtentry (c)));
1647 }
1648
1649 bool ctype_isIncompleteArray (ctype c)
1650 {
1651   return (ctype_isArray (c) && !ctype_isFixedArray (c));
1652 }
1653
1654 bool ctype_isFixedArray (ctype c)
1655 {
1656   if (ctype_isElips (c)) return FALSE;
1657
1658   return (ctbase_isFixedArray (ctype_getCtbaseSafe (c)));
1659 }
1660
1661 bool
1662 ctype_isArrayPtr (ctype c)
1663 {
1664   return ((ctype_isArray (c)) || (ctype_isPointer (c)));
1665 }
1666
1667 typeId
1668 ctype_typeId (ctype c)
1669 {
1670   return (ctbase_typeId (ctype_getCtbase (c)));
1671 }
1672
1673 cstring
1674 ctype_unparseDeclaration (ctype c, /*@only@*/ cstring name)
1675 {
1676   llassert (!(ctype_isElips (c) || ctype_isMissingParamsMarker (c)));
1677
1678   if (ctype_isUnknown (c))
1679     {
1680       return message ("? %q", name);
1681     }
1682   else
1683     {
1684       return (ctbase_unparseDeclaration (ctype_getCtbase (c), name));
1685     }
1686 }
1687
1688 cstring
1689 ctype_unparse (ctype c)
1690 {
1691   if (ctype_isElips (c))
1692     {
1693       return cstring_makeLiteralTemp ("...");
1694     }
1695   else if (ctype_isMissingParamsMarker (c))
1696     {
1697       return cstring_makeLiteralTemp ("-");
1698     }
1699   else if (ctype_isUnknown (c))
1700     {
1701       return cstring_makeLiteralTemp ("?");
1702     }
1703   else
1704     {
1705       /*@-modobserver@*/
1706       return (ctentry_doUnparse (ctype_getCtentry (c)));
1707       /*@=modobserver@*/
1708     }
1709 }
1710  
1711 cstring
1712 ctype_unparseSafe (ctype c)
1713 {
1714   if (ctype_isElips (c))
1715     {
1716       return cstring_makeLiteralTemp ("...");
1717     }
1718   else if (ctype_isMissingParamsMarker (c))
1719     {
1720       return cstring_makeLiteralTemp ("-");
1721     }
1722   else
1723     {
1724       cstring ret;
1725
1726       if /*@+enumint@*/ (c >= CTK_PLAIN && c < cttab.size) /*@=enumint@*/
1727         {
1728           ctentry cte = ctype_getCtentry (c);
1729           
1730           if (cstring_isDefined (cte->unparse))
1731             {
1732               return (cte->unparse);
1733             }
1734         }
1735       
1736       ret = message ("[%d]", (int) c);
1737       cstring_markOwned (ret);
1738       return ret;
1739     }
1740 }
1741
1742 cstring
1743 ctype_unparseDeep (ctype c)
1744 {
1745   if (ctype_isElips (c))
1746     {
1747       return cstring_makeLiteralTemp ("...");
1748     }
1749   if (ctype_isMissingParamsMarker (c))
1750     {
1751       return cstring_makeLiteralTemp ("-");
1752     }
1753       
1754   return (ctentry_doUnparseDeep (ctype_getCtentry (c)));
1755 }
1756
1757 ctype
1758 ctype_undump (char **c)
1759 {
1760   return ((ctype) reader_getInt (c));   /* check its valid? */
1761 }
1762
1763 cstring
1764 ctype_dump (ctype c)
1765 {
1766   DPRINTF (("Ctype dump: %s", ctype_unparse (c)));
1767
1768   if (c < 0)
1769     {
1770       /* Handle invalid types in a kludgey way. */
1771       return (message ("0"));
1772     }
1773   
1774   if (ctype_isUA (c))
1775     {
1776       cstring tname = usymtab_getTypeEntryName 
1777         (usymtab_convertId (ctype_typeId (c)));
1778       
1779       if (cstring_equal (tname, context_getBoolName ()))
1780         {
1781           cstring_free (tname);
1782           return (message ("%d", ctype_bool));
1783         }
1784       
1785       cstring_free (tname);
1786     }
1787
1788   DPRINTF (("Returning: %d", c));
1789   return (message ("%d", c));
1790 }
1791
1792 ctype
1793 ctype_getBaseType (ctype c)
1794 {
1795   ctentry cte = ctype_getCtentry (c);
1796
1797   switch (ctentry_getKind (cte))
1798     {
1799     case CTK_UNKNOWN:
1800     case CTK_INVALID:
1801     case CTK_PLAIN:
1802       return c;
1803     case CTK_PTR:
1804     case CTK_ARRAY:
1805       return (ctype_getBaseType (ctype_baseArrayPtr (c)));
1806     case CTK_COMPLEX:
1807       {
1808         ctbase ctb = cte->ctbase;
1809
1810         if (ctbase_isDefined (ctb))
1811           {
1812             /*@access ctbase@*/
1813             switch (ctb->type)
1814               {
1815               case CT_UNKNOWN:
1816               case CT_PRIM:
1817               case CT_USER:
1818               case CT_ENUM:
1819               case CT_ENUMLIST:
1820               case CT_BOOL:
1821               case CT_ABST:
1822               case CT_FCN:
1823               case CT_STRUCT:
1824               case CT_UNION:
1825               case CT_EXPFCN:
1826                 return c;
1827               case CT_PTR:
1828               case CT_ARRAY:
1829                 return (ctype_getBaseType (ctb->contents.base));
1830               case CT_FIXEDARRAY:
1831                 return (ctype_getBaseType (ctb->contents.farray->base));
1832               case CT_CONJ:             /* base type of A conj branch? */
1833                 return (ctype_getBaseType (ctb->contents.conj->a));
1834               }
1835             /*@noaccess ctbase@*/
1836           }
1837         else
1838           {
1839             return c;
1840           }
1841       }
1842     default:
1843       llbuglit ("ctype_newBase: bad case");
1844     }
1845   llcontbuglit ("ctype_getBaseType: unreachable code");
1846   return ((ctype)NULL);
1847 }
1848
1849 ctype
1850 ctype_adjustPointers (int np, ctype c)
1851 {
1852   
1853   if (ctype_isFunction (c))
1854     {
1855       c = ctype_makeParamsFunction
1856         (ctype_adjustPointers (np, ctype_getReturnType (c)),
1857          uentryList_copy (ctype_argsFunction (c)));
1858     }
1859   else
1860     {
1861       /* fix this should not use getBaseType ??? */
1862       ctype cb = ctype_getBaseType (c);
1863
1864       while (np > 0)
1865         {
1866           cb = ctype_makePointer (cb);
1867           np--;
1868         }
1869       c = ctype_newBase (c, cb);
1870     }
1871
1872   return (c);
1873 }
1874
1875
1876 enumNameList
1877 ctype_elist (ctype c)
1878 {
1879   return (ctbase_elist (ctype_getCtbase (c)));
1880 }
1881
1882 bool
1883 ctype_isFirstVoid (ctype c)
1884 {
1885   return (c == CTX_VOID || (ctype_isConj (c) && ctype_isFirstVoid (ctype_getConjA (c))));
1886 }
1887
1888 ctype
1889 ctype_createEnum (/*@keep@*/ cstring tag, /*@keep@*/ enumNameList el)
1890 {
1891   return (cttable_addComplex (ctbase_createEnum (tag, el)));
1892 }
1893
1894 bool
1895 ctype_isEnum (ctype c)
1896 {
1897   return (ctype_isComplex (c) && ctbase_isEnum (ctype_getCtbase (c)));
1898 }
1899
1900 cstring
1901 ctype_enumTag (ctype c)
1902 {
1903   llassert (ctype_isEnum (c));
1904
1905   return (ctbase_enumTag (ctype_getCtbaseSafe (c)));
1906 }
1907
1908 bool
1909 ctype_isStruct (ctype c)
1910 {
1911   return (ctype_isComplex (c) && ctbase_isStruct (ctype_getCtbaseSafe (c)));
1912 }
1913
1914 bool
1915 ctype_isUnion (ctype c)
1916 {
1917   return (ctype_isComplex (c) && ctbase_isUnion (ctype_getCtbaseSafe (c)));
1918 }
1919
1920 ctype
1921 ctype_resolveNumerics (ctype c1, ctype c2)
1922 {
1923   /*
1924   ** returns longest type of c1 and c2
1925   */
1926
1927   if (c1 == c2) return c1;
1928
1929   c1 = ctype_realType (c1);
1930   c2 = ctype_realType (c2);
1931
1932   if (ctype_isEnum (c1)) c1 = ctype_unknown;
1933   if (ctype_isEnum (c2)) c2 = ctype_int;
1934
1935   if (c1 == ctype_ldouble || c2 == ctype_ldouble) return ctype_ldouble;
1936
1937   /* 2001-06-08: This fix provided by Jim Zelenka. */
1938   if (c1 == ctype_llint || c2 == ctype_llint) return ctype_llint;
1939   if (c1 == ctype_ullint || c2 == ctype_ullint) return ctype_ullint;
1940
1941   if (c1 == ctype_ulint || c2 == ctype_ulint) return ctype_ulint;
1942   if (c1 == ctype_lint || c2 == ctype_lint) return ctype_lint;
1943   if (c1 == ctype_uint || c2 == ctype_uint) return ctype_uint;
1944   if (c1 == ctype_int || c2 == ctype_int) return ctype_int;
1945
1946   /* 2001-06-08: This fix provided by Jim Zelenka. */
1947   if (c1 == ctype_usint || c2 == ctype_usint) return ctype_usint;
1948
1949   if (c1 == ctype_sint || c2 == ctype_sint) return ctype_sint;
1950
1951   if (c1 == ctype_uchar || c2 == ctype_uchar) return ctype_uchar;
1952   if (c1 == ctype_char || c2 == ctype_char) return ctype_char;
1953
1954   if (ctype_isKnown (c1)) return c1;
1955   else return c2;
1956 }
1957
1958 bool
1959 ctype_isStructorUnion (ctype c)
1960 {
1961   return (ctype_isStruct (c) || ctype_isUnion (c));
1962 }
1963
1964 ctype
1965 ctype_fixArrayPtr (ctype c)
1966 {
1967   if (ctype_isArray (c))
1968     {
1969       return (ctype_makePointer (ctype_baseArrayPtr (c)));
1970     }
1971   else
1972     return c;
1973 }
1974
1975 /*
1976 ** createUnnamedStruct/Union
1977 **
1978 ** check if it corresponds to an existing LCL-specified unnamed struct
1979 ** otherwise, give it a new tag
1980 */
1981
1982 ctype
1983 ctype_createUnnamedStruct (/*@only@*/ uentryList f)
1984 {
1985   ctype ret = usymtab_structFieldsType (f);
1986
1987   DPRINTF (("unnamed struct: %s", ctype_unparse (ret)));
1988
1989   if (ctype_isDefined (ret))
1990     {
1991       uentryList_free (f);
1992       return ret;
1993     }
1994   else
1995     {
1996       cstring ft = fakeTag ();
1997       ctype ct = ctype_createStruct (cstring_copy (ft), f);
1998       uentry ue = uentry_makeStructTagLoc (ft, ct);
1999
2000       DPRINTF (("Unnamed struct: %s", uentry_unparseFull (ue)));
2001       ue = usymtab_supGlobalEntryReturn (ue);
2002       DPRINTF (("After Unnamed struct: %s", uentry_unparseFull (ue)));
2003
2004       cstring_free (ft);
2005       return (ct);
2006     }
2007 }
2008
2009 ctype
2010 ctype_createUnnamedUnion (/*@only@*/ uentryList f)
2011 {
2012   ctype ret = usymtab_unionFieldsType (f);
2013   
2014   if (ctype_isDefined (ret))
2015     {
2016       uentryList_free (f);
2017       return ret;
2018     }
2019   else
2020     {
2021       cstring ft = fakeTag ();
2022       ctype ct = ctype_createUnion (cstring_copy (ft), f);
2023       uentry ue = uentry_makeUnionTagLoc (ft, ct);
2024
2025       usymtab_supGlobalEntry (ue);
2026       cstring_free (ft);
2027       return (ct);
2028     }
2029 }
2030
2031 bool
2032 ctype_isUnnamedSU (ctype c)
2033 {
2034   if (ctype_isSU (c))
2035     {
2036       return ctbase_isUnnamedSU (ctype_getCtbase (c));
2037     }
2038   else
2039     {
2040       return FALSE;
2041     }
2042 }
2043
2044 ctype
2045 ctype_createForwardStruct (cstring n)
2046 {
2047   uentry ue  = uentry_makeStructTag (n, ctype_unknown, fileloc_undefined);
2048   ctype ct = usymtab_supForwardTypeEntry (ue);
2049
2050   cstring_free (n);
2051   return (ct);
2052 }
2053
2054 ctype
2055 ctype_createForwardUnion (cstring n)
2056 {
2057   uentry ue  = uentry_makeUnionTag (n, ctype_unknown, fileloc_undefined);
2058   ctype ct = usymtab_supForwardTypeEntry (ue);
2059
2060   cstring_free (n);
2061   return (ct);
2062 }
2063
2064 ctype
2065 ctype_removePointers (ctype c)
2066 {
2067   ctype oldc;
2068
2069   while (ctype_isKnown (c) && ctype_isArrayPtr (c))
2070     {
2071       oldc = c;
2072       c = ctype_baseArrayPtr (c);
2073       llassert (c != oldc);
2074     }
2075   
2076   return (c);
2077 }
2078
2079 bool ctype_isMutable (ctype t)
2080 {
2081   if (ctype_isUA (t))
2082     {
2083       return (uentry_isMutableDatatype 
2084               (usymtab_getTypeEntry (ctype_typeId (t))));
2085     }
2086   else 
2087     {
2088       return (ctype_isPointer (ctype_realType (t)));
2089       /*!! || ctype_isStructorUnion (ctype_realType (t))); */
2090     }
2091 }
2092
2093 bool ctype_isRefCounted (ctype t)
2094 {
2095   if (ctype_isUA (t))
2096     {
2097       return (uentry_isRefCountedDatatype 
2098               (usymtab_getTypeEntry (ctype_typeId (t))));
2099     }
2100
2101   return FALSE;
2102 }
2103
2104 bool ctype_isVisiblySharable (ctype t)
2105 {
2106   if (ctype_isUnknown (t)) return TRUE;
2107
2108   if (ctype_isConj (t))
2109     {
2110       return (ctype_isVisiblySharable (ctype_getConjA (t))
2111               || ctype_isVisiblySharable (ctype_getConjB (t)));
2112     }
2113
2114   if (ctype_isMutable (t))
2115     {
2116       if (ctype_isUA (t))
2117         {
2118           ctype rt = ctype_realType (t);
2119
2120           if (rt == t)
2121             {
2122               return TRUE;
2123             }
2124           else
2125             {
2126               return ctype_isVisiblySharable (rt);
2127
2128             }
2129         }
2130       else
2131         {
2132           return TRUE;
2133         }
2134     }
2135   
2136   return FALSE;
2137 }
2138
2139 # if 0
2140 /* Replaced by ctype_isMutable (more sensible) */
2141 bool ctype_canAlias (ctype ct)
2142 {
2143   /* can ct refer to memory locations?
2144   **       ==> a pointer or a mutable abstract type
2145   **           arrays?  
2146   */
2147
2148   ctype tr = ctype_realType (ct);
2149
2150   return (ctype_isPointer (tr) || ctype_isMutable (ct) || ctype_isStructorUnion (tr));
2151 }
2152 # endif
2153
2154 /*
2155 ** c1 is the dominant type; c2 is the modifier type
2156 **
2157 ** eg. double + long int => long double
2158 */
2159
2160 ctype ctype_combine (ctype dominant, ctype modifier)
2161 {
2162   DPRINTF (("Combine: %s + %s", 
2163             ctype_unparse (dominant),
2164             ctype_unparse (modifier)));
2165
2166   if (ctype_isConj (dominant)) 
2167     {      
2168       ctype res;
2169
2170       if (ctype_isExplicitConj (dominant))
2171         {
2172           res = ctype_makeExplicitConj (ctype_combine (ctype_getConjA (dominant), 
2173                                                        modifier),
2174                                         ctype_getConjB (dominant));
2175         }
2176       else
2177         {
2178           res = ctype_makeConj (ctype_combine (ctype_getConjA (dominant),
2179                                                modifier),
2180                                 ctype_getConjB (dominant));
2181         }
2182
2183       return res;
2184     }
2185
2186   if (ctype_isUnknown (modifier)) 
2187     {
2188       return dominant;
2189     }
2190   else if (ctype_isUnknown (dominant))
2191     {
2192       return modifier; 
2193     }
2194   else
2195     {
2196       if (ctype_isEnum (dominant)) dominant = ctype_int;
2197       if (ctype_isEnum (modifier)) modifier = ctype_int;
2198       
2199       if (modifier == ctype_uint)
2200         {
2201           if (dominant == ctype_int) return ctype_uint;
2202           if (dominant == ctype_lint) return ctype_ulint;
2203           if (dominant == ctype_sint) return ctype_usint;
2204           if (dominant == ctype_char) return ctype_uchar;
2205
2206           /* evs 2000-07-28: added this line */
2207           if (dominant == ctype_llint) return ctype_ullint;
2208
2209           if ((dominant == ctype_uint) || dominant == ctype_uchar)
2210             {
2211               voptgenerror (FLG_DUPLICATEQUALS, 
2212                             message ("Duplicate unsigned qualifier"),
2213                             g_currentloc);
2214
2215               return ctype_uint;
2216             }
2217           else
2218             {
2219               voptgenerror (FLG_DUPLICATEQUALS, 
2220                             message ("Type qualifier unsigned used with %s", 
2221                                      ctype_unparse (dominant)),
2222                             g_currentloc);
2223           
2224               return dominant;
2225             }
2226         }
2227       else if (modifier == ctype_llint)
2228         {
2229           if (dominant == ctype_int)
2230             {
2231               return ctype_llint;
2232             }
2233           
2234           voptgenerror (FLG_DUPLICATEQUALS, 
2235                         message ("Duplicate long qualifier on non-int"),
2236                         g_currentloc);
2237         }
2238       else if (modifier == ctype_lint)
2239         {
2240           if (dominant == ctype_int) return ctype_lint;
2241           if (dominant == ctype_uint) return ctype_ulint;
2242           if (dominant == ctype_double) return ctype_ldouble;
2243           
2244           if (dominant == ctype_lint || dominant == ctype_ulint 
2245               || dominant == ctype_sint || dominant == ctype_usint
2246               || dominant == ctype_ldouble)
2247             {
2248               if (dominant == ctype_lint)
2249                 {
2250                   /* long long not supported by ANSI */
2251                   return ctype_llint;
2252                 }
2253               
2254               /* ++jimz */
2255               if (dominant == ctype_ulint)
2256                 {
2257                   /* unsigned long long not supported by ANSI */
2258                   return ctype_ullint;
2259                 }
2260               /* ==jimz */
2261
2262               if (dominant == ctype_sint || dominant == ctype_usint)
2263                 {
2264                   if (!context_getFlag (FLG_IGNOREQUALS))
2265                     {
2266                       llerrorlit (FLG_SYNTAX, 
2267                                   "Contradictory long and short type qualifiers");
2268                     }
2269                 }
2270               else
2271                 {
2272                   voptgenerror (FLG_DUPLICATEQUALS, 
2273                                 message ("Duplicate long qualifier"),
2274                                 g_currentloc);
2275                 }
2276               
2277               return ctype_lint;
2278             }
2279         }
2280       else if (modifier == ctype_sint)
2281         {
2282           if (dominant == ctype_int) return ctype_sint;
2283           if (dominant == ctype_uint) return ctype_usint;
2284           
2285           if (dominant == ctype_sint || dominant == ctype_usint)
2286             {
2287               voptgenerror (FLG_DUPLICATEQUALS, 
2288                             message ("Duplicate short qualifier"),
2289                             g_currentloc);
2290               return ctype_uint;
2291             }
2292           else if (dominant == ctype_lint)
2293             {
2294               if (!context_getFlag (FLG_IGNOREQUALS))
2295                 {
2296                   llerrorlit (FLG_SYNTAX, 
2297                               "Contradictory long and short type qualifiers");
2298                 }
2299               
2300               return dominant;
2301             }
2302 /* ++jimz */
2303           else if (dominant == ctype_llint)
2304             {
2305               if (!context_getFlag (FLG_IGNOREQUALS))
2306                 {
2307                   llerrorlit (FLG_SYNTAX, 
2308                               "Contradictory long long and short type qualifiers");
2309                 }
2310               
2311               return dominant;
2312             }
2313 /* ==jimz */
2314           else
2315             {
2316               if (!context_getFlag (FLG_IGNOREQUALS))
2317                 {
2318                   llerror (FLG_SYNTAX, 
2319                            message ("Type qualifier short used with %s", 
2320                                     ctype_unparse (dominant)));
2321                 }
2322
2323               return dominant;
2324             }
2325         }
2326       else if (modifier == ctype_ulint)
2327         {
2328           if (dominant == ctype_int) return modifier;
2329           
2330           if (dominant == ctype_lint || dominant == ctype_ulint)
2331             {
2332               voptgenerror (FLG_DUPLICATEQUALS, 
2333                             message ("Duplicate long qualifier"),
2334                             g_currentloc);
2335
2336               return modifier;
2337             }
2338           
2339           if (dominant == ctype_uint || dominant == ctype_usint)
2340             {
2341               voptgenerror (FLG_DUPLICATEQUALS, 
2342                             message ("Duplicate unsigned qualifier"),
2343                             g_currentloc);
2344
2345               return modifier;
2346             }
2347           
2348           if (dominant == ctype_sint || dominant == ctype_usint)
2349             {
2350               if (!context_getFlag (FLG_IGNOREQUALS))
2351                 {
2352                   llerrorlit (FLG_SYNTAX,
2353                               "Contradictory long and short type qualifiers");
2354                 }
2355
2356               return dominant;
2357             }
2358           
2359           if (!context_getFlag (FLG_IGNOREQUALS))
2360             {
2361               llerror (FLG_SYNTAX,
2362                        message ("Type qualifiers unsigned long used with %s", 
2363                                 ctype_unparse (dominant)));
2364             }
2365
2366           return dominant;
2367         }
2368       else if (modifier == ctype_usint)
2369         {
2370           if (dominant == ctype_int) return modifier;
2371           
2372           if (dominant == ctype_sint || dominant == ctype_usint)
2373             {
2374               voptgenerror (FLG_DUPLICATEQUALS, 
2375                             message ("Duplicate short qualifier"),
2376                             g_currentloc);
2377               return modifier;
2378             }
2379           
2380           if (dominant == ctype_uint)
2381             {
2382               voptgenerror (FLG_DUPLICATEQUALS, 
2383                             message ("Duplicate unsigned qualifier"),
2384                             g_currentloc);
2385
2386               return modifier;
2387             }
2388           
2389           if (dominant == ctype_lint || dominant == ctype_ulint
2390               || dominant == ctype_llint)
2391             {
2392               if (!context_getFlag (FLG_IGNOREQUALS))
2393                 {
2394                   llerrorlit (FLG_SYNTAX, 
2395                               "Contradictory long and short type qualifiers");
2396                 }
2397
2398               return dominant;
2399             }
2400           
2401           if (!context_getFlag (FLG_IGNOREQUALS))
2402             {
2403               llerror (FLG_SYNTAX, 
2404                        message ("Type qualifiers unsigned short used with %s",
2405                                 ctype_unparse (dominant)));
2406             }
2407
2408           return dominant;
2409         }
2410       else
2411         {
2412           ;
2413         }
2414
2415       return dominant;
2416     }
2417 }
2418   
2419 ctype ctype_resolve (ctype c)
2420 {
2421   if (ctype_isUnknown (c)) return ctype_int;
2422   return c;
2423 }
2424
2425 ctype ctype_fromQual (qual q)
2426 {
2427   if (qual_isSigned (q)) return ctype_int;
2428   if (qual_isUnsigned (q)) return ctype_uint;
2429   if (qual_isLong (q)) return ctype_lint;
2430   if (qual_isShort (q)) return ctype_sint;
2431   
2432   llcontbug (message ("ctype_fromQual: invalid qualifier: %s", qual_unparse (q)));
2433   return ctype_unknown;
2434 }
2435
2436 bool 
2437 ctype_isAnyFloat (ctype c)
2438 {
2439   return (cprim_isAnyReal (ctype_toCprim (c)));
2440 }
2441
2442 bool
2443 ctype_isUnsigned (ctype c)
2444 {
2445   if (ctype_isConj (c))
2446     return (ctype_isUnsigned (ctype_getConjA (c)) ||
2447             ctype_isUnsigned (ctype_getConjB (c)));
2448
2449   return (c == ctype_uint || c == ctype_uchar
2450           || c == ctype_usint || c == ctype_ulint
2451           || c == ctype_ullint
2452           || c == ctype_unsignedintegral);
2453 }
2454
2455 /* ++jimz */
2456 static bool
2457 ctype_isLongLong (ctype c)
2458 {
2459   if (ctype_isConj (c))
2460     return (ctype_isLongLong (ctype_getConjA (c)) ||
2461             ctype_isLongLong (ctype_getConjB (c)));
2462
2463   return (c == ctype_llint || c == ctype_ullint);
2464 }
2465 /* ==jimz */
2466
2467 static bool
2468 ctype_isLong (ctype c)
2469 {
2470   if (ctype_isConj (c))
2471     return (ctype_isLong (ctype_getConjA (c)) ||
2472             ctype_isLong (ctype_getConjB (c)));
2473
2474   return (c == ctype_lint || c == ctype_ulint);
2475 }
2476
2477 static bool
2478 ctype_isShort (ctype c)
2479 {
2480   if (ctype_isConj (c))
2481     return (ctype_isShort (ctype_getConjA (c)) ||
2482             ctype_isShort (ctype_getConjB (c)));
2483
2484   return (c == ctype_sint || c == ctype_usint);
2485 }
2486
2487 bool
2488 ctype_isStackAllocated (ctype c)
2489 {
2490   ctype ct = ctype_realType (c);
2491
2492   if (ctype_isConj (ct))
2493     return (ctype_isStackAllocated (ctype_getConjA (ct)) ||
2494             ctype_isStackAllocated (ctype_getConjB (ct)));
2495   
2496   return (ctype_isArray (c) || ctype_isSU (c));
2497 }
2498
2499 static bool ctype_isMoreUnsigned (ctype c1, ctype c2)
2500 {
2501   return (ctype_isUnsigned (c1) && !ctype_isUnsigned (c2));
2502 }
2503
2504 static bool ctype_isLonger (ctype c1, ctype c2)
2505 {
2506   /* 2001-06-10: Fix for long long's provided by Jim Zelenka */
2507   return ((ctype_isDouble (c1) && !ctype_isDouble (c2))
2508           || (ctype_isLongLong (c1) && !ctype_isLongLong (c2))
2509           || (ctype_isLong (c1) 
2510               && (!ctype_isLong (c2)) && (!ctype_isLongLong (c2)))
2511           || (ctype_isShort (c2) && !ctype_isShort (c1)));
2512 }
2513
2514 ctype
2515 ctype_widest (ctype c1, ctype c2)
2516 {
2517   if (ctype_isMoreUnsigned (c2, c1) || ctype_isLonger (c2, c1))
2518     {
2519       return c2;
2520     }
2521   else
2522     {
2523       return c1;
2524     }
2525 }
2526
2527 static /*@observer@*/ ctbase ctype_getCtbase (ctype c)
2528 {
2529   /*@+enumint@*/
2530   if (c >= 0 && c < cttab.size)
2531     {
2532       return (cttab.entries[c]->ctbase);
2533     }
2534   else 
2535     {
2536       if (c == ctype_unknown)
2537         llbuglit ("ctype_getCtbase: ctype unknown");
2538       if (c == ctype_undefined)
2539         llbuglit ("ctype_getCtbase: ctype undefined");
2540       if (c == ctype_dne)
2541         llbuglit ("ctype_getCtbase: ctype dne");
2542       if (c == ctype_elipsMarker)
2543         llbuglit ("ctype_getCtbase: elips marker");
2544       
2545       llfatalbug (message ("ctype_getCtbase: ctype out of range: %d", c));
2546       BADEXIT;
2547     }
2548
2549   /*@=enumint@*/
2550 }
2551
2552 static /*@notnull@*/ /*@observer@*/ ctbase
2553 ctype_getCtbaseSafe (ctype c)
2554 {
2555   ctbase res = ctype_getCtbase (c);
2556
2557   llassert (ctbase_isDefined (res));
2558   return res;
2559 }
2560
2561 /*
2562 ** ctentry
2563 */
2564
2565 static ctentry
2566 ctype_getCtentry (ctype c)
2567 {
2568   static /*@only@*/ ctentry errorEntry = NULL;
2569
2570   if (cttab.size == 0)
2571     {
2572       if (errorEntry == NULL)
2573         {
2574           errorEntry = ctentry_makeNew (CTK_UNKNOWN, ctbase_undefined);
2575         }
2576
2577       return errorEntry;
2578     }
2579
2580   /*@+enumint@*/
2581   if (c >= CTK_PLAIN && c < cttab.size)
2582     {
2583       return (cttab.entries[c]);
2584     }
2585   else if (c == CTK_UNKNOWN) 
2586     llcontbuglit ("ctype_getCtentry: ctype unknown");
2587   else if (c == CTK_INVALID)
2588     llcontbuglit ("ctype_getCtentry: ctype invalid (ctype_undefined)");
2589   else if (c == CTK_DNE)
2590     llcontbuglit ("ctype_getCtentry: ctype dne");
2591   else if (c == CTK_ELIPS) 
2592     llcontbuglit ("ctype_getCtentry: ctype elipsis");
2593   else if (c == CTK_MISSINGPARAMS) 
2594     llcontbuglit ("ctype_getCtentry: ctype missing params");
2595   else
2596     llbug (message ("ctype_getCtentry: ctype out of range: %d", c));
2597
2598   return (cttab.entries[ctype_unknown]);
2599   /*@=enumint@*/
2600 }
2601
2602 /*drl 11/28/2000 */
2603 /* requires that the type is an fixed array */
2604 /* return the size of the array */
2605
2606 long int ctype_getArraySize (ctype c)
2607 {
2608   long int size;
2609   ctentry cte = ctype_getCtentry (c);
2610   ctbase ctb;
2611   llassert ( (ctentry_getKind (cte) ==  CTK_COMPLEX) || (ctentry_getKind(cte) == CTK_ARRAY) );
2612
2613   ctb = cte->ctbase;
2614
2615   size = ctbase_getArraySize (ctb);
2616
2617   DPRINTF(( message("ctype_getArraySize: got fixed array size of %d ", (int)size) ));
2618   return size;
2619 }
2620
This page took 0.234107 seconds and 5 git commands to generate.