1 | /*****************************************************************************/ |
2 | /* */ |
3 | /* datatype.h */ |
4 | /* */ |
5 | /* Type string handling for the cc65 C compiler */ |
6 | /* */ |
7 | /* */ |
8 | /* */ |
9 | /* (C) 1998-2015, Ullrich von Bassewitz */ |
10 | /* Roemerstrasse 52 */ |
11 | /* D-70794 Filderstadt */ |
12 | /* EMail: uz@cc65.org */ |
13 | /* */ |
14 | /* */ |
15 | /* This software is provided 'as-is', without any expressed or implied */ |
16 | /* warranty. In no event will the authors be held liable for any damages */ |
17 | /* arising from the use of this software. */ |
18 | /* */ |
19 | /* Permission is granted to anyone to use this software for any purpose, */ |
20 | /* including commercial applications, and to alter it and redistribute it */ |
21 | /* freely, subject to the following restrictions: */ |
22 | /* */ |
23 | /* 1. The origin of this software must not be misrepresented; you must not */ |
24 | /* claim that you wrote the original software. If you use this software */ |
25 | /* in a product, an acknowledgment in the product documentation would be */ |
26 | /* appreciated but is not required. */ |
27 | /* 2. Altered source versions must be plainly marked as such, and must not */ |
28 | /* be misrepresented as being the original software. */ |
29 | /* 3. This notice may not be removed or altered from any source */ |
30 | /* distribution. */ |
31 | /* */ |
32 | /*****************************************************************************/ |
33 | |
34 | |
35 | |
36 | #ifndef DATATYPE_H |
37 | #define DATATYPE_H |
38 | |
39 | |
40 | |
41 | #include <stdio.h> |
42 | |
43 | /* common */ |
44 | #include "attrib.h" |
45 | #include "inline.h" |
46 | #include "mmodel.h" |
47 | |
48 | /* cc65 */ |
49 | #include "funcdesc.h" |
50 | |
51 | |
52 | |
53 | /*****************************************************************************/ |
54 | /* Data */ |
55 | /*****************************************************************************/ |
56 | |
57 | |
58 | |
59 | |
60 | /* Basic data types */ |
61 | enum { |
62 | T_END = 0x000000, |
63 | |
64 | /* Basic types */ |
65 | T_TYPE_NONE = 0x000000, |
66 | T_TYPE_CHAR = 0x000001, |
67 | T_TYPE_SHORT = 0x000002, |
68 | T_TYPE_INT = 0x000003, |
69 | T_TYPE_LONG = 0x000004, |
70 | T_TYPE_LONGLONG = 0x000005, |
71 | T_TYPE_ENUM = 0x000006, |
72 | T_TYPE_FLOAT = 0x000007, |
73 | T_TYPE_DOUBLE = 0x000008, |
74 | T_TYPE_VOID = 0x000009, |
75 | T_TYPE_STRUCT = 0x00000A, |
76 | T_TYPE_UNION = 0x00000B, |
77 | T_TYPE_ARRAY = 0x00000C, |
78 | T_TYPE_PTR = 0x00000D, |
79 | T_TYPE_FUNC = 0x00000E, |
80 | T_MASK_TYPE = 0x00000F, |
81 | |
82 | /* Type classes */ |
83 | T_CLASS_NONE = 0x000000, |
84 | T_CLASS_INT = 0x000010, |
85 | T_CLASS_FLOAT = 0x000020, |
86 | T_CLASS_PTR = 0x000030, |
87 | T_CLASS_STRUCT = 0x000040, |
88 | T_CLASS_FUNC = 0x000050, |
89 | T_MASK_CLASS = 0x000070, |
90 | |
91 | /* Type signedness */ |
92 | T_SIGN_NONE = 0x000000, |
93 | T_SIGN_UNSIGNED = 0x000080, |
94 | T_SIGN_SIGNED = 0x000100, |
95 | T_MASK_SIGN = 0x000180, |
96 | |
97 | /* Type size modifiers */ |
98 | T_SIZE_NONE = 0x000000, |
99 | T_SIZE_SHORT = 0x000200, |
100 | T_SIZE_LONG = 0x000400, |
101 | T_SIZE_LONGLONG = 0x000600, |
102 | T_MASK_SIZE = 0x000600, |
103 | |
104 | /* Type qualifiers */ |
105 | T_QUAL_NONE = 0x000000, |
106 | T_QUAL_CONST = 0x000800, |
107 | T_QUAL_VOLATILE = 0x001000, |
108 | T_QUAL_RESTRICT = 0x002000, |
109 | T_QUAL_NEAR = 0x004000, |
110 | T_QUAL_FAR = 0x008000, |
111 | T_QUAL_ADDRSIZE = T_QUAL_NEAR | T_QUAL_FAR, |
112 | T_QUAL_FASTCALL = 0x010000, |
113 | T_QUAL_CDECL = 0x020000, |
114 | T_QUAL_CCONV = T_QUAL_FASTCALL | T_QUAL_CDECL, |
115 | T_MASK_QUAL = 0x03F800, |
116 | |
117 | /* Types */ |
118 | T_CHAR = T_TYPE_CHAR | T_CLASS_INT | T_SIGN_UNSIGNED | T_SIZE_NONE, |
119 | T_SCHAR = T_TYPE_CHAR | T_CLASS_INT | T_SIGN_SIGNED | T_SIZE_NONE, |
120 | T_UCHAR = T_TYPE_CHAR | T_CLASS_INT | T_SIGN_UNSIGNED | T_SIZE_NONE, |
121 | T_SHORT = T_TYPE_SHORT | T_CLASS_INT | T_SIGN_SIGNED | T_SIZE_SHORT, |
122 | T_USHORT = T_TYPE_SHORT | T_CLASS_INT | T_SIGN_UNSIGNED | T_SIZE_SHORT, |
123 | T_INT = T_TYPE_INT | T_CLASS_INT | T_SIGN_SIGNED | T_SIZE_NONE, |
124 | T_UINT = T_TYPE_INT | T_CLASS_INT | T_SIGN_UNSIGNED | T_SIZE_NONE, |
125 | T_LONG = T_TYPE_LONG | T_CLASS_INT | T_SIGN_SIGNED | T_SIZE_LONG, |
126 | T_ULONG = T_TYPE_LONG | T_CLASS_INT | T_SIGN_UNSIGNED | T_SIZE_LONG, |
127 | T_LONGLONG = T_TYPE_LONGLONG | T_CLASS_INT | T_SIGN_SIGNED | T_SIZE_LONGLONG, |
128 | T_ULONGLONG = T_TYPE_LONGLONG | T_CLASS_INT | T_SIGN_UNSIGNED | T_SIZE_LONGLONG, |
129 | T_ENUM = T_TYPE_ENUM | T_CLASS_INT | T_SIGN_SIGNED | T_SIZE_NONE, |
130 | T_FLOAT = T_TYPE_FLOAT | T_CLASS_FLOAT | T_SIGN_NONE | T_SIZE_NONE, |
131 | T_DOUBLE = T_TYPE_DOUBLE | T_CLASS_FLOAT | T_SIGN_NONE | T_SIZE_NONE, |
132 | T_VOID = T_TYPE_VOID | T_CLASS_NONE | T_SIGN_NONE | T_SIZE_NONE, |
133 | T_STRUCT = T_TYPE_STRUCT | T_CLASS_STRUCT | T_SIGN_NONE | T_SIZE_NONE, |
134 | T_UNION = T_TYPE_UNION | T_CLASS_STRUCT | T_SIGN_NONE | T_SIZE_NONE, |
135 | T_ARRAY = T_TYPE_ARRAY | T_CLASS_PTR | T_SIGN_NONE | T_SIZE_NONE, |
136 | T_PTR = T_TYPE_PTR | T_CLASS_PTR | T_SIGN_NONE | T_SIZE_NONE, |
137 | T_FUNC = T_TYPE_FUNC | T_CLASS_FUNC | T_SIGN_NONE | T_SIZE_NONE, |
138 | |
139 | /* Aliases */ |
140 | T_SIZE_T = T_UINT, |
141 | }; |
142 | |
143 | |
144 | |
145 | /* Type code entry */ |
146 | typedef unsigned long TypeCode; |
147 | |
148 | /* Type entry */ |
149 | typedef struct Type Type; |
150 | struct Type { |
151 | TypeCode C; /* Code for this entry */ |
152 | union { |
153 | void* P; /* Arbitrary attribute pointer */ |
154 | long L; /* Numeric attribute value */ |
155 | unsigned long U; /* Dito, unsigned */ |
156 | } A; /* Type attribute if necessary */ |
157 | }; |
158 | |
159 | /* A macro that expands to a full initializer for struct Type */ |
160 | #define TYPE(T) { (T), { 0 } } |
161 | |
162 | /* Maximum length of a type string */ |
163 | #define MAXTYPELEN 30 |
164 | |
165 | /* Special encodings for element counts of an array */ |
166 | #define UNSPECIFIED -1L /* Element count was not specified */ |
167 | #define FLEXIBLE 0L /* Flexible array struct member */ |
168 | |
169 | /* Sizes. Floating point sizes come from fp.h */ |
170 | #define SIZEOF_CHAR 1U |
171 | #define SIZEOF_SHORT 2U |
172 | #define SIZEOF_INT 2U |
173 | #define SIZEOF_LONG 4U |
174 | #define SIZEOF_LONGLONG 8U |
175 | #define SIZEOF_FLOAT (FP_F_Size()) |
176 | #define SIZEOF_DOUBLE (FP_D_Size()) |
177 | #define SIZEOF_PTR SIZEOF_INT |
178 | |
179 | /* Bit sizes */ |
180 | #define CHAR_BITS (8 * SIZEOF_CHAR) |
181 | #define SHORT_BITS (8 * SIZEOF_SHORT) |
182 | #define INT_BITS (8 * SIZEOF_INT) |
183 | #define LONG_BITS (8 * SIZEOF_LONG) |
184 | #define LONGLONG_BITS (8 * SIZEOF_LONGLONG) |
185 | #define FLOAT_BITS (8 * SIZEOF_FLOAT) |
186 | #define DOUBLE_BITS (8 * SIZEOF_DOUBLE) |
187 | #define PTR_BITS (8 * SIZEOF_PTR) |
188 | |
189 | /* Predefined type strings */ |
190 | extern Type type_schar[]; |
191 | extern Type type_uchar[]; |
192 | extern Type type_int[]; |
193 | extern Type type_uint[]; |
194 | extern Type type_long[]; |
195 | extern Type type_ulong[]; |
196 | extern Type type_void[]; |
197 | extern Type type_size_t[]; |
198 | extern Type type_float[]; |
199 | extern Type type_double[]; |
200 | |
201 | /* Forward for the SymEntry struct */ |
202 | struct SymEntry; |
203 | |
204 | |
205 | |
206 | /*****************************************************************************/ |
207 | /* Code */ |
208 | /*****************************************************************************/ |
209 | |
210 | |
211 | |
212 | unsigned TypeLen (const Type* T); |
213 | /* Return the length of the type string */ |
214 | |
215 | Type* TypeCopy (Type* Dest, const Type* Src); |
216 | /* Copy a type string */ |
217 | |
218 | Type* TypeDup (const Type* T); |
219 | /* Create a copy of the given type on the heap */ |
220 | |
221 | Type* TypeAlloc (unsigned Len); |
222 | /* Allocate memory for a type string of length Len. Len *must* include the |
223 | ** trailing T_END. |
224 | */ |
225 | |
226 | void TypeFree (Type* T); |
227 | /* Free a type string */ |
228 | |
229 | int SignExtendChar (int C); |
230 | /* Do correct sign extension of a character */ |
231 | |
232 | TypeCode GetDefaultChar (void); |
233 | /* Return the default char type (signed/unsigned) depending on the settings */ |
234 | |
235 | Type* GetCharArrayType (unsigned Len); |
236 | /* Return the type for a char array of the given length */ |
237 | |
238 | Type* GetImplicitFuncType (void); |
239 | /* Return a type string for an inplicitly declared function */ |
240 | |
241 | Type* PointerTo (const Type* T); |
242 | /* Return a type string that is "pointer to T". The type string is allocated |
243 | ** on the heap and may be freed after use. |
244 | */ |
245 | |
246 | void PrintType (FILE* F, const Type* T); |
247 | /* Output translation of type array. */ |
248 | |
249 | void PrintRawType (FILE* F, const Type* T); |
250 | /* Print a type string in raw format (for debugging) */ |
251 | |
252 | void PrintFuncSig (FILE* F, const char* Name, Type* T); |
253 | /* Print a function signature. */ |
254 | |
255 | int TypeHasAttr (const Type* T); |
256 | /* Return true if the given type has attribute data */ |
257 | |
258 | #if defined(HAVE_INLINE) |
259 | INLINE void CopyTypeAttr (const Type* Src, Type* Dest) |
260 | /* Copy attribute data from Src to Dest */ |
261 | { |
262 | Dest->A = Src->A; |
263 | } |
264 | #else |
265 | # define CopyTypeAttr(Src, Dest) ((Dest)->A = (Src)->A) |
266 | #endif |
267 | |
268 | #if defined(HAVE_INLINE) |
269 | INLINE TypeCode UnqualifiedType (TypeCode T) |
270 | /* Return the unqalified type code */ |
271 | { |
272 | return (T & ~T_MASK_QUAL); |
273 | } |
274 | #else |
275 | # define UnqualifiedType(T) ((T) & ~T_MASK_QUAL) |
276 | #endif |
277 | |
278 | unsigned SizeOf (const Type* T); |
279 | /* Compute size of object represented by type array. */ |
280 | |
281 | unsigned PSizeOf (const Type* T); |
282 | /* Compute size of pointer object. */ |
283 | |
284 | unsigned CheckedSizeOf (const Type* T); |
285 | /* Return the size of a data type. If the size is zero, emit an error and |
286 | ** return some valid size instead (so the rest of the compiler doesn't have |
287 | ** to work with invalid sizes). |
288 | */ |
289 | unsigned CheckedPSizeOf (const Type* T); |
290 | /* Return the size of a data type that is pointed to by a pointer. If the |
291 | ** size is zero, emit an error and return some valid size instead (so the |
292 | ** rest of the compiler doesn't have to work with invalid sizes). |
293 | */ |
294 | |
295 | unsigned TypeOf (const Type* T); |
296 | /* Get the code generator base type of the object */ |
297 | |
298 | Type* Indirect (Type* T); |
299 | /* Do one indirection for the given type, that is, return the type where the |
300 | ** given type points to. |
301 | */ |
302 | |
303 | Type* ArrayToPtr (Type* T); |
304 | /* Convert an array to a pointer to it's first element */ |
305 | |
306 | #if defined(HAVE_INLINE) |
307 | INLINE TypeCode GetType (const Type* T) |
308 | /* Get the raw type */ |
309 | { |
310 | return (T->C & T_MASK_TYPE); |
311 | } |
312 | #else |
313 | # define GetType(T) ((T)->C & T_MASK_TYPE) |
314 | #endif |
315 | |
316 | #if defined(HAVE_INLINE) |
317 | INLINE int IsTypeChar (const Type* T) |
318 | /* Return true if this is a character type */ |
319 | { |
320 | return (GetType (T) == T_TYPE_CHAR); |
321 | } |
322 | #else |
323 | # define IsTypeChar(T) (GetType (T) == T_TYPE_CHAR) |
324 | #endif |
325 | |
326 | #if defined(HAVE_INLINE) |
327 | INLINE int IsTypeInt (const Type* T) |
328 | /* Return true if this is an int type (signed or unsigned) */ |
329 | { |
330 | return (GetType (T) == T_TYPE_INT); |
331 | } |
332 | #else |
333 | # define IsTypeInt(T) (GetType (T) == T_TYPE_INT) |
334 | #endif |
335 | |
336 | #if defined(HAVE_INLINE) |
337 | INLINE int IsTypeLong (const Type* T) |
338 | /* Return true if this is a long type (signed or unsigned) */ |
339 | { |
340 | return (GetType (T) == T_TYPE_LONG); |
341 | } |
342 | #else |
343 | # define IsTypeLong(T) (GetType (T) == T_TYPE_LONG) |
344 | #endif |
345 | |
346 | #if defined(HAVE_INLINE) |
347 | INLINE int IsTypeFloat (const Type* T) |
348 | /* Return true if this is a float type */ |
349 | { |
350 | return (GetType (T) == T_TYPE_FLOAT); |
351 | } |
352 | #else |
353 | # define IsTypeFloat(T) (GetType (T) == T_TYPE_FLOAT) |
354 | #endif |
355 | |
356 | #if defined(HAVE_INLINE) |
357 | INLINE int IsTypeDouble (const Type* T) |
358 | /* Return true if this is a double type */ |
359 | { |
360 | return (GetType (T) == T_TYPE_DOUBLE); |
361 | } |
362 | #else |
363 | # define IsTypeDouble(T) (GetType (T) == T_TYPE_DOUBLE) |
364 | #endif |
365 | |
366 | #if defined(HAVE_INLINE) |
367 | INLINE int IsTypePtr (const Type* T) |
368 | /* Return true if this is a pointer type */ |
369 | { |
370 | return (GetType (T) == T_TYPE_PTR); |
371 | } |
372 | #else |
373 | # define IsTypePtr(T) (GetType (T) == T_TYPE_PTR) |
374 | #endif |
375 | |
376 | #if defined(HAVE_INLINE) |
377 | INLINE int IsTypeStruct (const Type* T) |
378 | /* Return true if this is a struct type */ |
379 | { |
380 | return (GetType (T) == T_TYPE_STRUCT); |
381 | } |
382 | #else |
383 | # define IsTypeStruct(T) (GetType (T) == T_TYPE_STRUCT) |
384 | #endif |
385 | |
386 | #if defined(HAVE_INLINE) |
387 | INLINE int IsTypeUnion (const Type* T) |
388 | /* Return true if this is a union type */ |
389 | { |
390 | return (GetType (T) == T_TYPE_UNION); |
391 | } |
392 | #else |
393 | # define IsTypeUnion(T) (GetType (T) == T_TYPE_UNION) |
394 | #endif |
395 | |
396 | #if defined(HAVE_INLINE) |
397 | INLINE int IsTypeArray (const Type* T) |
398 | /* Return true if this is an array type */ |
399 | { |
400 | return (GetType (T) == T_TYPE_ARRAY); |
401 | } |
402 | #else |
403 | # define IsTypeArray(T) (GetType (T) == T_TYPE_ARRAY) |
404 | #endif |
405 | |
406 | #if defined(HAVE_INLINE) |
407 | INLINE int IsTypeVoid (const Type* T) |
408 | /* Return true if this is a void type */ |
409 | { |
410 | return (GetType (T) == T_TYPE_VOID); |
411 | } |
412 | #else |
413 | # define IsTypeVoid(T) (GetType (T) == T_TYPE_VOID) |
414 | #endif |
415 | |
416 | #if defined(HAVE_INLINE) |
417 | INLINE int IsTypeFunc (const Type* T) |
418 | /* Return true if this is a function class */ |
419 | { |
420 | return (GetType (T) == T_TYPE_FUNC); |
421 | } |
422 | #else |
423 | # define IsTypeFunc(T) (GetType (T) == T_TYPE_FUNC) |
424 | #endif |
425 | |
426 | #if defined(HAVE_INLINE) |
427 | INLINE int IsTypeFuncPtr (const Type* T) |
428 | /* Return true if this is a function pointer */ |
429 | { |
430 | return (IsTypePtr (T) && IsTypeFunc (T+1)); |
431 | } |
432 | #else |
433 | # define IsTypeFuncPtr(T) (IsTypePtr (T) && IsTypeFunc (T+1)) |
434 | #endif |
435 | |
436 | #if defined(HAVE_INLINE) |
437 | INLINE TypeCode GetClass (const Type* T) |
438 | /* Get the class of a type string */ |
439 | { |
440 | return (T->C & T_MASK_CLASS); |
441 | } |
442 | #else |
443 | # define GetClass(T) ((T)->C & T_MASK_CLASS) |
444 | #endif |
445 | |
446 | #if defined(HAVE_INLINE) |
447 | INLINE int IsClassInt (const Type* T) |
448 | /* Return true if this is an integer type */ |
449 | { |
450 | return (GetClass (T) == T_CLASS_INT); |
451 | } |
452 | #else |
453 | # define IsClassInt(T) (GetClass (T) == T_CLASS_INT) |
454 | #endif |
455 | |
456 | #if defined(HAVE_INLINE) |
457 | INLINE int IsClassFloat (const Type* T) |
458 | /* Return true if this is a float type */ |
459 | { |
460 | return (GetClass (T) == T_CLASS_FLOAT); |
461 | } |
462 | #else |
463 | # define IsClassFloat(T) (GetClass (T) == T_CLASS_FLOAT) |
464 | #endif |
465 | |
466 | #if defined(HAVE_INLINE) |
467 | INLINE int IsClassPtr (const Type* T) |
468 | /* Return true if this is a pointer type */ |
469 | { |
470 | return (GetClass (T) == T_CLASS_PTR); |
471 | } |
472 | #else |
473 | # define IsClassPtr(T) (GetClass (T) == T_CLASS_PTR) |
474 | #endif |
475 | |
476 | #if defined(HAVE_INLINE) |
477 | INLINE int IsClassStruct (const Type* T) |
478 | /* Return true if this is a struct type */ |
479 | { |
480 | return (GetClass (T) == T_CLASS_STRUCT); |
481 | } |
482 | #else |
483 | # define IsClassStruct(T) (GetClass (T) == T_CLASS_STRUCT) |
484 | #endif |
485 | |
486 | #if defined(HAVE_INLINE) |
487 | INLINE int IsClassFunc (const Type* T) |
488 | /* Return true if this is a function type */ |
489 | { |
490 | return (GetClass (T) == T_CLASS_FUNC); |
491 | } |
492 | #else |
493 | # define IsClassFunc(T) (GetClass (T) == T_CLASS_FUNC) |
494 | #endif |
495 | |
496 | #if defined(HAVE_INLINE) |
497 | INLINE TypeCode GetSignedness (const Type* T) |
498 | /* Get the sign of a type */ |
499 | { |
500 | return (T->C & T_MASK_SIGN); |
501 | } |
502 | #else |
503 | # define GetSignedness(T) ((T)->C & T_MASK_SIGN) |
504 | #endif |
505 | |
506 | #if defined(HAVE_INLINE) |
507 | INLINE int IsSignUnsigned (const Type* T) |
508 | /* Return true if this is an unsigned type */ |
509 | { |
510 | return (GetSignedness (T) == T_SIGN_UNSIGNED); |
511 | } |
512 | #else |
513 | # define IsSignUnsigned(T) (GetSignedness (T) == T_SIGN_UNSIGNED) |
514 | #endif |
515 | |
516 | #if defined(HAVE_INLINE) |
517 | INLINE int IsSignSigned (const Type* T) |
518 | /* Return true if this is a signed type */ |
519 | { |
520 | return (GetSignedness (T) == T_SIGN_SIGNED); |
521 | } |
522 | #else |
523 | # define IsSignSigned(T) (GetSignedness (T) == T_SIGN_SIGNED) |
524 | #endif |
525 | |
526 | #if defined(HAVE_INLINE) |
527 | INLINE TypeCode GetQualifier (const Type* T) |
528 | /* Get the qualifier from the given type string */ |
529 | { |
530 | return (T->C & T_MASK_QUAL); |
531 | } |
532 | #else |
533 | # define GetQualifier(T) ((T)->C & T_MASK_QUAL) |
534 | #endif |
535 | |
536 | #if defined(HAVE_INLINE) |
537 | INLINE int IsQualConst (const Type* T) |
538 | /* Return true if the given type has a const memory image */ |
539 | { |
540 | return (T->C & T_QUAL_CONST) != 0; |
541 | } |
542 | #else |
543 | # define IsQualConst(T) (((T)->C & T_QUAL_CONST) != 0) |
544 | #endif |
545 | |
546 | #if defined(HAVE_INLINE) |
547 | INLINE int IsQualVolatile (const Type* T) |
548 | /* Return true if the given type has a volatile type qualifier */ |
549 | { |
550 | return (T->C & T_QUAL_VOLATILE) != 0; |
551 | } |
552 | #else |
553 | # define IsQualVolatile(T) (((T)->C & T_QUAL_VOLATILE) != 0) |
554 | #endif |
555 | |
556 | #if defined(HAVE_INLINE) |
557 | INLINE int IsQualRestrict (const Type* T) |
558 | /* Return true if the given type has a restrict qualifier */ |
559 | { |
560 | return (T->C & T_QUAL_RESTRICT) != 0; |
561 | } |
562 | #else |
563 | # define IsQualRestrict(T) (((T)->C & T_QUAL_RESTRICT) != 0) |
564 | #endif |
565 | |
566 | #if defined(HAVE_INLINE) |
567 | INLINE int IsQualNear (const Type* T) |
568 | /* Return true if the given type has a near qualifier */ |
569 | { |
570 | return (T->C & T_QUAL_NEAR) != 0; |
571 | } |
572 | #else |
573 | # define IsQualNear(T) (((T)->C & T_QUAL_NEAR) != 0) |
574 | #endif |
575 | |
576 | #if defined(HAVE_INLINE) |
577 | INLINE int IsQualFar (const Type* T) |
578 | /* Return true if the given type has a far qualifier */ |
579 | { |
580 | return (T->C & T_QUAL_FAR) != 0; |
581 | } |
582 | #else |
583 | # define IsQualFar(T) (((T)->C & T_QUAL_FAR) != 0) |
584 | #endif |
585 | |
586 | #if defined(HAVE_INLINE) |
587 | INLINE int IsQualFastcall (const Type* T) |
588 | /* Return true if the given type has a fastcall qualifier */ |
589 | { |
590 | return (T->C & T_QUAL_FASTCALL) != 0; |
591 | } |
592 | #else |
593 | # define IsQualFastcall(T) (((T)->C & T_QUAL_FASTCALL) != 0) |
594 | #endif |
595 | |
596 | #if defined(HAVE_INLINE) |
597 | INLINE int IsQualCDecl (const Type* T) |
598 | /* Return true if the given type has a cdecl qualifier */ |
599 | { |
600 | return (T->C & T_QUAL_CDECL) != 0; |
601 | } |
602 | #else |
603 | # define IsQualCDecl(T) (((T)->C & T_QUAL_CDECL) != 0) |
604 | #endif |
605 | |
606 | #if defined(HAVE_INLINE) |
607 | INLINE int IsQualCConv (const Type* T) |
608 | /* Return true if the given type has a calling convention qualifier */ |
609 | { |
610 | return (T->C & T_QUAL_CCONV) != 0; |
611 | } |
612 | #else |
613 | # define IsQualCConv(T) (((T)->C & T_QUAL_CCONV) != 0) |
614 | #endif |
615 | |
616 | int IsVariadicFunc (const Type* T) attribute ((const)); |
617 | /* Return true if this is a function type or pointer to function type with |
618 | ** variable parameter list |
619 | */ |
620 | |
621 | #if defined(HAVE_INLINE) |
622 | INLINE TypeCode GetSizeModifier (const Type* T) |
623 | /* Get the size modifier of a type */ |
624 | { |
625 | return (T->C & T_MASK_SIZE); |
626 | } |
627 | #else |
628 | # define GetSizeModifier(T) ((T)->C & T_MASK_SIZE) |
629 | #endif |
630 | |
631 | FuncDesc* GetFuncDesc (const Type* T) attribute ((const)); |
632 | /* Get the FuncDesc pointer from a function or pointer-to-function type */ |
633 | |
634 | void SetFuncDesc (Type* T, FuncDesc* F); |
635 | /* Set the FuncDesc pointer in a function or pointer-to-function type */ |
636 | |
637 | Type* GetFuncReturn (Type* T) attribute ((const)); |
638 | /* Return a pointer to the return type of a function or pointer-to-function type */ |
639 | |
640 | long GetElementCount (const Type* T); |
641 | /* Get the element count of the array specified in T (which must be of |
642 | ** array type). |
643 | */ |
644 | |
645 | void SetElementCount (Type* T, long Count); |
646 | /* Set the element count of the array specified in T (which must be of |
647 | ** array type). |
648 | */ |
649 | |
650 | Type* GetElementType (Type* T); |
651 | /* Return the element type of the given array type. */ |
652 | |
653 | Type* GetBaseElementType (Type* T); |
654 | /* Return the base element type of a given type. If T is not an array, this |
655 | ** will return. Otherwise it will return the base element type, which means |
656 | ** the element type that is not an array. |
657 | */ |
658 | |
659 | struct SymEntry* GetSymEntry (const Type* T) attribute ((const)); |
660 | /* Return a SymEntry pointer from a type */ |
661 | |
662 | void SetSymEntry (Type* T, struct SymEntry* S); |
663 | /* Set the SymEntry pointer for a type */ |
664 | |
665 | Type* IntPromotion (Type* T); |
666 | /* Apply the integer promotions to T and return the result. The returned type |
667 | ** string may be T if there is no need to change it. |
668 | */ |
669 | |
670 | Type* PtrConversion (Type* T); |
671 | /* If the type is a function, convert it to pointer to function. If the |
672 | ** expression is an array, convert it to pointer to first element. Otherwise |
673 | ** return T. |
674 | */ |
675 | |
676 | TypeCode AddrSizeQualifier (unsigned AddrSize); |
677 | /* Return T_QUAL_NEAR or T_QUAL_FAR depending on the address size */ |
678 | |
679 | #if defined(HAVE_INLINE) |
680 | INLINE TypeCode CodeAddrSizeQualifier (void) |
681 | /* Return T_QUAL_NEAR or T_QUAL_FAR depending on the code address size */ |
682 | { |
683 | return AddrSizeQualifier (CodeAddrSize); |
684 | } |
685 | #else |
686 | # define CodeAddrSizeQualifier() (AddrSizeQualifier (CodeAddrSize)) |
687 | #endif |
688 | |
689 | #if defined(HAVE_INLINE) |
690 | INLINE TypeCode DataAddrSizeQualifier (void) |
691 | /* Return T_QUAL_NEAR or T_QUAL_FAR depending on the data address size */ |
692 | { |
693 | return AddrSizeQualifier (DataAddrSize); |
694 | } |
695 | #else |
696 | # define DataAddrSizeQualifier() (AddrSizeQualifier (DataAddrSize)) |
697 | #endif |
698 | |
699 | |
700 | |
701 | /* End of datatype.h */ |
702 | |
703 | #endif |
704 | |