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