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