In libobjc/: 2011-06-07 Nicola Pero <nicola.pero@meta-innovation.com>
[gcc.git] / libobjc / encoding.c
1 /* Encoding of types for Objective C.
2 Copyright (C) 1993, 1995, 1996, 1997, 1998, 2000, 2002, 2004, 2009, 2010
3 Free Software Foundation, Inc.
4 Contributed by Kresten Krab Thorup
5 Bitfield support by Ovidiu Predescu
6
7 This file is part of GCC.
8
9 GCC is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 3, or (at your option)
12 any later version.
13
14 GCC is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
18
19 Under Section 7 of GPL version 3, you are granted additional
20 permissions described in the GCC Runtime Library Exception, version
21 3.1, as published by the Free Software Foundation.
22
23 You should have received a copy of the GNU General Public License and
24 a copy of the GCC Runtime Library Exception along with this program;
25 see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
26 <http://www.gnu.org/licenses/>. */
27
28 /* FIXME: This file has no business including tm.h. */
29
30 /* FIXME: This file contains functions that will abort the entire
31 program if they fail. Is that really needed ? */
32
33 #include "objc-private/common.h"
34 #include "objc-private/error.h"
35 #include "tconfig.h"
36 #include "coretypes.h"
37 #include "tm.h"
38 #include "objc/runtime.h"
39 #include "objc-private/module-abi-8.h" /* For struct objc_method */
40 #include <stdlib.h>
41 #include <ctype.h>
42 #include <string.h> /* For memcpy. */
43
44 #undef MAX
45 #define MAX(X, Y) \
46 ({ typeof (X) __x = (X), __y = (Y); \
47 (__x > __y ? __x : __y); })
48
49 #undef MIN
50 #define MIN(X, Y) \
51 ({ typeof (X) __x = (X), __y = (Y); \
52 (__x < __y ? __x : __y); })
53
54 #undef ROUND
55 #define ROUND(V, A) \
56 ({ typeof (V) __v = (V); typeof (A) __a = (A); \
57 __a * ((__v+__a - 1)/__a); })
58
59
60 /* Various hacks for objc_layout_record. These are used by the target
61 macros. */
62
63 #define TREE_CODE(TYPE) *(TYPE)
64 #define TREE_TYPE(TREE) (TREE)
65
66 #define RECORD_TYPE _C_STRUCT_B
67 #define UNION_TYPE _C_UNION_B
68 #define QUAL_UNION_TYPE _C_UNION_B
69 #define ARRAY_TYPE _C_ARY_B
70
71 #define REAL_TYPE _C_DBL
72
73 #define VECTOR_TYPE _C_VECTOR
74
75 #define TYPE_FIELDS(TYPE) ({const char *_field = (TYPE)+1; \
76 while (*_field != _C_STRUCT_E && *_field != _C_STRUCT_B \
77 && *_field != _C_UNION_B && *_field++ != '=') \
78 /* do nothing */; \
79 _field;})
80
81 #define DECL_MODE(TYPE) *(TYPE)
82 #define TYPE_MODE(TYPE) *(TYPE)
83
84 #define DFmode _C_DBL
85
86 #define strip_array_types(TYPE) ({const char *_field = (TYPE); \
87 while (*_field == _C_ARY_B)\
88 {\
89 while (isdigit ((unsigned char)*++_field))\
90 ;\
91 }\
92 _field;})
93
94 /* Some ports (eg ARM) allow the structure size boundary to be
95 selected at compile-time. We override the normal definition with
96 one that has a constant value for this compilation. */
97 #ifndef BITS_PER_UNIT
98 #define BITS_PER_UNIT 8
99 #endif
100 #undef STRUCTURE_SIZE_BOUNDARY
101 #define STRUCTURE_SIZE_BOUNDARY (BITS_PER_UNIT * sizeof (struct{char a;}))
102
103 /* Some ROUND_TYPE_ALIGN macros use TARGET_foo, and consequently
104 target_flags. Define a dummy entry here to so we don't die.
105 We have to rename it because target_flags may already have been
106 declared extern. */
107 #define target_flags not_target_flags
108 static int __attribute__ ((__unused__)) not_target_flags = 0;
109
110 /* Some ROUND_TYPE_ALIGN use ALTIVEC_VECTOR_MODE (rs6000 darwin).
111 Define a dummy ALTIVEC_VECTOR_MODE so it will not die. */
112 #undef ALTIVEC_VECTOR_MODE
113 #define ALTIVEC_VECTOR_MODE(MODE) (0)
114
115 /* Furthermore, some (powerpc) targets also use TARGET_ALIGN_NATURAL
116 in their alignment macros. Currently[4.5/6], rs6000.h points this
117 to a static variable, initialized by target overrides. This is reset
118 in linux64.h but not in darwin64.h. The macro is not used by *86*. */
119
120 #if __MACH__
121 # if __LP64__
122 # undef TARGET_ALIGN_NATURAL
123 # define TARGET_ALIGN_NATURAL 1
124 # endif
125
126 /* On Darwin32, we need to recurse until we find the starting stuct type. */
127 static int
128 _darwin_rs6000_special_round_type_align (const char *struc, int comp, int spec)
129 {
130 const char *_stp , *_fields = TYPE_FIELDS (struc);
131 if (!_fields)
132 return MAX (comp, spec);
133 _stp = strip_array_types (_fields);
134 if (TYPE_MODE(_stp) == _C_COMPLEX)
135 _stp++;
136 switch (TYPE_MODE(_stp))
137 {
138 case RECORD_TYPE:
139 case UNION_TYPE:
140 return MAX (MAX (comp, spec), objc_alignof_type (_stp) * BITS_PER_UNIT);
141 break;
142 case DFmode:
143 case _C_LNG_LNG:
144 case _C_ULNG_LNG:
145 return MAX (MAX (comp, spec), 64);
146 break;
147
148 default:
149 return MAX (comp, spec);
150 break;
151 }
152 }
153
154 /* See comment below. */
155 #define darwin_rs6000_special_round_type_align(S,C,S2) \
156 (_darwin_rs6000_special_round_type_align ((char*)(S), (int)(C), (int)(S2)))
157 #endif
158
159 /* FIXME: while this file has no business including tm.h, this
160 definitely has no business defining this macro but it
161 is only way around without really rewritting this file,
162 should look after the branch of 3.4 to fix this. */
163 #define rs6000_special_round_type_align(STRUCT, COMPUTED, SPECIFIED) \
164 ({ const char *_fields = TYPE_FIELDS (STRUCT); \
165 ((_fields != 0 \
166 && TYPE_MODE (strip_array_types (TREE_TYPE (_fields))) == DFmode) \
167 ? MAX (MAX (COMPUTED, SPECIFIED), 64) \
168 : MAX (COMPUTED, SPECIFIED));})
169
170
171 /* Skip a variable name, enclosed in quotes ("). */
172 static inline
173 const char *
174 objc_skip_variable_name (const char *type)
175 {
176 /* Skip the variable name if any. */
177 if (*type == '"')
178 {
179 /* FIXME: How do we know we won't read beyond the end of the
180 string. Here and in the rest of the file! */
181 /* Skip '"'. */
182 type++;
183 /* Skip to the next '"'. */
184 while (*type != '"')
185 type++;
186 /* Skip '"'. */
187 type++;
188 }
189
190 return type;
191 }
192
193 int
194 objc_sizeof_type (const char *type)
195 {
196 type = objc_skip_variable_name (type);
197
198 switch (*type) {
199 case _C_BOOL:
200 return sizeof (_Bool);
201 break;
202
203 case _C_ID:
204 return sizeof (id);
205 break;
206
207 case _C_CLASS:
208 return sizeof (Class);
209 break;
210
211 case _C_SEL:
212 return sizeof (SEL);
213 break;
214
215 case _C_CHR:
216 return sizeof (char);
217 break;
218
219 case _C_UCHR:
220 return sizeof (unsigned char);
221 break;
222
223 case _C_SHT:
224 return sizeof (short);
225 break;
226
227 case _C_USHT:
228 return sizeof (unsigned short);
229 break;
230
231 case _C_INT:
232 return sizeof (int);
233 break;
234
235 case _C_UINT:
236 return sizeof (unsigned int);
237 break;
238
239 case _C_LNG:
240 return sizeof (long);
241 break;
242
243 case _C_ULNG:
244 return sizeof (unsigned long);
245 break;
246
247 case _C_LNG_LNG:
248 return sizeof (long long);
249 break;
250
251 case _C_ULNG_LNG:
252 return sizeof (unsigned long long);
253 break;
254
255 case _C_FLT:
256 return sizeof (float);
257 break;
258
259 case _C_DBL:
260 return sizeof (double);
261 break;
262
263 case _C_LNG_DBL:
264 return sizeof (long double);
265 break;
266
267 case _C_VOID:
268 return sizeof (void);
269 break;
270
271 case _C_PTR:
272 case _C_ATOM:
273 case _C_CHARPTR:
274 return sizeof (char *);
275 break;
276
277 case _C_ARY_B:
278 {
279 int len = atoi (type + 1);
280 while (isdigit ((unsigned char)*++type))
281 ;
282 return len * objc_aligned_size (type);
283 }
284 break;
285
286 case _C_VECTOR:
287 {
288 /* Skip the '!'. */
289 type++;
290 /* Skip the '['. */
291 type++;
292
293 /* The size in bytes is the following number. */
294 int size = atoi (type);
295 return size;
296 }
297 break;
298
299 case _C_BFLD:
300 {
301 /* The GNU encoding of bitfields is: b 'position' 'type'
302 'size'. */
303 int position, size;
304 int startByte, endByte;
305
306 position = atoi (type + 1);
307 while (isdigit ((unsigned char)*++type))
308 ;
309 size = atoi (type + 1);
310
311 startByte = position / BITS_PER_UNIT;
312 endByte = (position + size) / BITS_PER_UNIT;
313 return endByte - startByte;
314 }
315
316 case _C_UNION_B:
317 case _C_STRUCT_B:
318 {
319 struct objc_struct_layout layout;
320 unsigned int size;
321
322 objc_layout_structure (type, &layout);
323 while (objc_layout_structure_next_member (&layout))
324 /* do nothing */ ;
325 objc_layout_finish_structure (&layout, &size, NULL);
326
327 return size;
328 }
329
330 case _C_COMPLEX:
331 {
332 type++; /* Skip after the 'j'. */
333 switch (*type)
334 {
335 case _C_CHR:
336 return sizeof (_Complex char);
337 break;
338
339 case _C_UCHR:
340 return sizeof (_Complex unsigned char);
341 break;
342
343 case _C_SHT:
344 return sizeof (_Complex short);
345 break;
346
347 case _C_USHT:
348 return sizeof (_Complex unsigned short);
349 break;
350
351 case _C_INT:
352 return sizeof (_Complex int);
353 break;
354
355 case _C_UINT:
356 return sizeof (_Complex unsigned int);
357 break;
358
359 case _C_LNG:
360 return sizeof (_Complex long);
361 break;
362
363 case _C_ULNG:
364 return sizeof (_Complex unsigned long);
365 break;
366
367 case _C_LNG_LNG:
368 return sizeof (_Complex long long);
369 break;
370
371 case _C_ULNG_LNG:
372 return sizeof (_Complex unsigned long long);
373 break;
374
375 case _C_FLT:
376 return sizeof (_Complex float);
377 break;
378
379 case _C_DBL:
380 return sizeof (_Complex double);
381 break;
382
383 case _C_LNG_DBL:
384 return sizeof (_Complex long double);
385 break;
386
387 default:
388 {
389 /* FIXME: Is this so bad that we have to abort the
390 entire program ? (it applies to all the other
391 _objc_abort calls in this file).
392 */
393 _objc_abort ("unknown complex type %s\n", type);
394 return 0;
395 }
396 }
397 }
398
399 default:
400 {
401 _objc_abort ("unknown type %s\n", type);
402 return 0;
403 }
404 }
405 }
406
407 int
408 objc_alignof_type (const char *type)
409 {
410 type = objc_skip_variable_name (type);
411
412 switch (*type) {
413 case _C_BOOL:
414 return __alignof__ (_Bool);
415 break;
416
417 case _C_ID:
418 return __alignof__ (id);
419 break;
420
421 case _C_CLASS:
422 return __alignof__ (Class);
423 break;
424
425 case _C_SEL:
426 return __alignof__ (SEL);
427 break;
428
429 case _C_CHR:
430 return __alignof__ (char);
431 break;
432
433 case _C_UCHR:
434 return __alignof__ (unsigned char);
435 break;
436
437 case _C_SHT:
438 return __alignof__ (short);
439 break;
440
441 case _C_USHT:
442 return __alignof__ (unsigned short);
443 break;
444
445 case _C_INT:
446 return __alignof__ (int);
447 break;
448
449 case _C_UINT:
450 return __alignof__ (unsigned int);
451 break;
452
453 case _C_LNG:
454 return __alignof__ (long);
455 break;
456
457 case _C_ULNG:
458 return __alignof__ (unsigned long);
459 break;
460
461 case _C_LNG_LNG:
462 return __alignof__ (long long);
463 break;
464
465 case _C_ULNG_LNG:
466 return __alignof__ (unsigned long long);
467 break;
468
469 case _C_FLT:
470 return __alignof__ (float);
471 break;
472
473 case _C_DBL:
474 return __alignof__ (double);
475 break;
476
477 case _C_LNG_DBL:
478 return __alignof__ (long double);
479 break;
480
481 case _C_PTR:
482 case _C_ATOM:
483 case _C_CHARPTR:
484 return __alignof__ (char *);
485 break;
486
487 case _C_ARY_B:
488 while (isdigit ((unsigned char)*++type))
489 /* do nothing */;
490 return objc_alignof_type (type);
491
492 case _C_VECTOR:
493 {
494 /* Skip the '!'. */
495 type++;
496 /* Skip the '['. */
497 type++;
498
499 /* Skip the size. */
500 while (isdigit ((unsigned char)*type))
501 type++;
502
503 /* Skip the ','. */
504 type++;
505
506 /* The alignment in bytes is the following number. */
507 return atoi (type);
508 }
509 case _C_STRUCT_B:
510 case _C_UNION_B:
511 {
512 struct objc_struct_layout layout;
513 unsigned int align;
514
515 objc_layout_structure (type, &layout);
516 while (objc_layout_structure_next_member (&layout))
517 /* do nothing */;
518 objc_layout_finish_structure (&layout, NULL, &align);
519
520 return align;
521 }
522
523
524 case _C_COMPLEX:
525 {
526 type++; /* Skip after the 'j'. */
527 switch (*type)
528 {
529 case _C_CHR:
530 return __alignof__ (_Complex char);
531 break;
532
533 case _C_UCHR:
534 return __alignof__ (_Complex unsigned char);
535 break;
536
537 case _C_SHT:
538 return __alignof__ (_Complex short);
539 break;
540
541 case _C_USHT:
542 return __alignof__ (_Complex unsigned short);
543 break;
544
545 case _C_INT:
546 return __alignof__ (_Complex int);
547 break;
548
549 case _C_UINT:
550 return __alignof__ (_Complex unsigned int);
551 break;
552
553 case _C_LNG:
554 return __alignof__ (_Complex long);
555 break;
556
557 case _C_ULNG:
558 return __alignof__ (_Complex unsigned long);
559 break;
560
561 case _C_LNG_LNG:
562 return __alignof__ (_Complex long long);
563 break;
564
565 case _C_ULNG_LNG:
566 return __alignof__ (_Complex unsigned long long);
567 break;
568
569 case _C_FLT:
570 return __alignof__ (_Complex float);
571 break;
572
573 case _C_DBL:
574 return __alignof__ (_Complex double);
575 break;
576
577 case _C_LNG_DBL:
578 return __alignof__ (_Complex long double);
579 break;
580
581 default:
582 {
583 _objc_abort ("unknown complex type %s\n", type);
584 return 0;
585 }
586 }
587 }
588
589 default:
590 {
591 _objc_abort ("unknown type %s\n", type);
592 return 0;
593 }
594 }
595 }
596
597 int
598 objc_aligned_size (const char *type)
599 {
600 int size, align;
601
602 type = objc_skip_variable_name (type);
603 size = objc_sizeof_type (type);
604 align = objc_alignof_type (type);
605
606 return ROUND (size, align);
607 }
608
609 int
610 objc_promoted_size (const char *type)
611 {
612 int size, wordsize;
613
614 type = objc_skip_variable_name (type);
615 size = objc_sizeof_type (type);
616 wordsize = sizeof (void *);
617
618 return ROUND (size, wordsize);
619 }
620
621 inline
622 const char *
623 objc_skip_type_qualifiers (const char *type)
624 {
625 while (*type == _C_CONST
626 || *type == _C_IN
627 || *type == _C_INOUT
628 || *type == _C_OUT
629 || *type == _C_BYCOPY
630 || *type == _C_BYREF
631 || *type == _C_ONEWAY
632 || *type == _C_GCINVISIBLE)
633 {
634 type += 1;
635 }
636 return type;
637 }
638
639 inline
640 const char *
641 objc_skip_typespec (const char *type)
642 {
643 type = objc_skip_variable_name (type);
644 type = objc_skip_type_qualifiers (type);
645
646 switch (*type) {
647
648 case _C_ID:
649 /* An id may be annotated by the actual type if it is known
650 with the @"ClassName" syntax */
651
652 if (*++type != '"')
653 return type;
654 else
655 {
656 while (*++type != '"')
657 /* do nothing */;
658 return type + 1;
659 }
660
661 /* The following are one character type codes */
662 case _C_CLASS:
663 case _C_SEL:
664 case _C_CHR:
665 case _C_UCHR:
666 case _C_CHARPTR:
667 case _C_ATOM:
668 case _C_SHT:
669 case _C_USHT:
670 case _C_INT:
671 case _C_UINT:
672 case _C_LNG:
673 case _C_BOOL:
674 case _C_ULNG:
675 case _C_LNG_LNG:
676 case _C_ULNG_LNG:
677 case _C_FLT:
678 case _C_DBL:
679 case _C_LNG_DBL:
680 case _C_VOID:
681 case _C_UNDEF:
682 return ++type;
683 break;
684
685 case _C_COMPLEX:
686 return type + 2;
687 break;
688
689 case _C_ARY_B:
690 /* skip digits, typespec and closing ']' */
691 while (isdigit ((unsigned char)*++type))
692 ;
693 type = objc_skip_typespec (type);
694 if (*type == _C_ARY_E)
695 return ++type;
696 else
697 {
698 _objc_abort ("bad array type %s\n", type);
699 return 0;
700 }
701
702 case _C_VECTOR:
703 /* Skip '!' */
704 type++;
705 /* Skip '[' */
706 type++;
707 /* Skip digits (size) */
708 while (isdigit ((unsigned char)*type))
709 type++;
710 /* Skip ',' */
711 type++;
712 /* Skip digits (alignment) */
713 while (isdigit ((unsigned char)*type))
714 type++;
715 /* Skip typespec. */
716 type = objc_skip_typespec (type);
717 /* Skip closing ']'. */
718 if (*type == _C_ARY_E)
719 return ++type;
720 else
721 {
722 _objc_abort ("bad vector type %s\n", type);
723 return 0;
724 }
725
726 case _C_BFLD:
727 /* The GNU encoding of bitfields is: b 'position' 'type'
728 'size'. */
729 while (isdigit ((unsigned char)*++type))
730 ; /* skip position */
731 while (isdigit ((unsigned char)*++type))
732 ; /* skip type and size */
733 return type;
734
735 case _C_STRUCT_B:
736 /* skip name, and elements until closing '}' */
737
738 while (*type != _C_STRUCT_E && *type++ != '=')
739 ;
740 while (*type != _C_STRUCT_E)
741 {
742 type = objc_skip_typespec (type);
743 }
744 return ++type;
745
746 case _C_UNION_B:
747 /* skip name, and elements until closing ')' */
748
749 while (*type != _C_UNION_E && *type++ != '=')
750 ;
751 while (*type != _C_UNION_E)
752 {
753 type = objc_skip_typespec (type);
754 }
755 return ++type;
756
757 case _C_PTR:
758 /* Just skip the following typespec */
759
760 return objc_skip_typespec (++type);
761
762 default:
763 {
764 _objc_abort ("unknown type %s\n", type);
765 return 0;
766 }
767 }
768 }
769
770 inline
771 const char *
772 objc_skip_offset (const char *type)
773 {
774 /* The offset is prepended by a '+' if the argument is passed in
775 registers. PS: The compiler stopped generating this '+' in
776 version 3.4. */
777 if (*type == '+')
778 type++;
779
780 /* Some people claim that on some platforms, where the stack grows
781 backwards, the compiler generates negative offsets (??). Skip a
782 '-' for such a negative offset. */
783 if (*type == '-')
784 type++;
785
786 /* Skip the digits that represent the offset. */
787 while (isdigit ((unsigned char) *type))
788 type++;
789
790 return type;
791 }
792
793 const char *
794 objc_skip_argspec (const char *type)
795 {
796 type = objc_skip_typespec (type);
797 type = objc_skip_offset (type);
798 return type;
799 }
800
801 char *
802 method_copyReturnType (struct objc_method *method)
803 {
804 if (method == NULL)
805 return 0;
806 else
807 {
808 char *returnValue;
809 size_t returnValueSize;
810
811 /* Determine returnValueSize. */
812 {
813 /* Find the end of the first argument. We want to return the
814 first argument spec, plus 1 byte for the \0 at the end. */
815 const char *type = method->method_types;
816 if (*type == '\0')
817 return NULL;
818 type = objc_skip_argspec (type);
819 returnValueSize = type - method->method_types + 1;
820 }
821
822 /* Copy the first argument into returnValue. */
823 returnValue = malloc (sizeof (char) * returnValueSize);
824 memcpy (returnValue, method->method_types, returnValueSize);
825 returnValue[returnValueSize - 1] = '\0';
826
827 return returnValue;
828 }
829 }
830
831 char *
832 method_copyArgumentType (struct objc_method * method, unsigned int argumentNumber)
833 {
834 if (method == NULL)
835 return 0;
836 else
837 {
838 char *returnValue;
839 const char *returnValueStart;
840 size_t returnValueSize;
841
842 /* Determine returnValueStart and returnValueSize. */
843 {
844 const char *type = method->method_types;
845
846 /* Skip the first argument (return type). */
847 type = objc_skip_argspec (type);
848
849 /* Now keep skipping arguments until we get to
850 argumentNumber. */
851 while (argumentNumber > 0)
852 {
853 /* We are supposed to skip an argument, but the string is
854 finished. This means we were asked for a non-existing
855 argument. */
856 if (*type == '\0')
857 return NULL;
858
859 type = objc_skip_argspec (type);
860 argumentNumber--;
861 }
862
863 /* If the argument does not exist, return NULL. */
864 if (*type == '\0')
865 return NULL;
866
867 returnValueStart = type;
868 type = objc_skip_argspec (type);
869 returnValueSize = type - returnValueStart + 1;
870 }
871
872 /* Copy the argument into returnValue. */
873 returnValue = malloc (sizeof (char) * returnValueSize);
874 memcpy (returnValue, returnValueStart, returnValueSize);
875 returnValue[returnValueSize - 1] = '\0';
876
877 return returnValue;
878 }
879 }
880
881 void method_getReturnType (struct objc_method * method, char *returnValue,
882 size_t returnValueSize)
883 {
884 if (returnValue == NULL || returnValueSize == 0)
885 return;
886
887 /* Zero the string; we'll then write the argument type at the
888 beginning of it, if needed. */
889 memset (returnValue, 0, returnValueSize);
890
891 if (method == NULL)
892 return;
893 else
894 {
895 size_t argumentTypeSize;
896
897 /* Determine argumentTypeSize. */
898 {
899 /* Find the end of the first argument. We want to return the
900 first argument spec. */
901 const char *type = method->method_types;
902 if (*type == '\0')
903 return;
904 type = objc_skip_argspec (type);
905 argumentTypeSize = type - method->method_types;
906 if (argumentTypeSize > returnValueSize)
907 argumentTypeSize = returnValueSize;
908 }
909 /* Copy the argument at the beginning of the string. */
910 memcpy (returnValue, method->method_types, argumentTypeSize);
911 }
912 }
913
914 void method_getArgumentType (struct objc_method * method, unsigned int argumentNumber,
915 char *returnValue, size_t returnValueSize)
916 {
917 if (returnValue == NULL || returnValueSize == 0)
918 return;
919
920 /* Zero the string; we'll then write the argument type at the
921 beginning of it, if needed. */
922 memset (returnValue, 0, returnValueSize);
923
924 if (method == NULL)
925 return;
926 else
927 {
928 const char *returnValueStart;
929 size_t argumentTypeSize;
930
931 /* Determine returnValueStart and argumentTypeSize. */
932 {
933 const char *type = method->method_types;
934
935 /* Skip the first argument (return type). */
936 type = objc_skip_argspec (type);
937
938 /* Now keep skipping arguments until we get to
939 argumentNumber. */
940 while (argumentNumber > 0)
941 {
942 /* We are supposed to skip an argument, but the string is
943 finished. This means we were asked for a non-existing
944 argument. */
945 if (*type == '\0')
946 return;
947
948 type = objc_skip_argspec (type);
949 argumentNumber--;
950 }
951
952 /* If the argument does not exist, it's game over. */
953 if (*type == '\0')
954 return;
955
956 returnValueStart = type;
957 type = objc_skip_argspec (type);
958 argumentTypeSize = type - returnValueStart;
959 if (argumentTypeSize > returnValueSize)
960 argumentTypeSize = returnValueSize;
961 }
962 /* Copy the argument at the beginning of the string. */
963 memcpy (returnValue, returnValueStart, argumentTypeSize);
964 }
965 }
966
967 unsigned int
968 method_getNumberOfArguments (struct objc_method *method)
969 {
970 if (method == NULL)
971 return 0;
972 else
973 {
974 unsigned int i = 0;
975 const char *type = method->method_types;
976 while (*type)
977 {
978 type = objc_skip_argspec (type);
979 i += 1;
980 }
981
982 if (i == 0)
983 {
984 /* This could only happen if method_types is invalid; in
985 that case, return 0. */
986 return 0;
987 }
988 else
989 {
990 /* Remove the return type. */
991 return (i - 1);
992 }
993 }
994 }
995
996 unsigned
997 objc_get_type_qualifiers (const char *type)
998 {
999 unsigned res = 0;
1000 BOOL flag = YES;
1001
1002 while (flag)
1003 switch (*type++)
1004 {
1005 case _C_CONST: res |= _F_CONST; break;
1006 case _C_IN: res |= _F_IN; break;
1007 case _C_INOUT: res |= _F_INOUT; break;
1008 case _C_OUT: res |= _F_OUT; break;
1009 case _C_BYCOPY: res |= _F_BYCOPY; break;
1010 case _C_BYREF: res |= _F_BYREF; break;
1011 case _C_ONEWAY: res |= _F_ONEWAY; break;
1012 case _C_GCINVISIBLE: res |= _F_GCINVISIBLE; break;
1013 default: flag = NO;
1014 }
1015
1016 return res;
1017 }
1018
1019 /* The following three functions can be used to determine how a
1020 structure is laid out by the compiler. For example:
1021
1022 struct objc_struct_layout layout;
1023 int i;
1024
1025 objc_layout_structure (type, &layout);
1026 while (objc_layout_structure_next_member (&layout))
1027 {
1028 int position, align;
1029 const char *type;
1030
1031 objc_layout_structure_get_info (&layout, &position, &align, &type);
1032 printf ("element %d has offset %d, alignment %d\n",
1033 i++, position, align);
1034 }
1035
1036 These functions are used by objc_sizeof_type and objc_alignof_type
1037 functions to compute the size and alignment of structures. The
1038 previous method of computing the size and alignment of a structure
1039 was not working on some architectures, particulary on AIX, and in
1040 the presence of bitfields inside the structure. */
1041 void
1042 objc_layout_structure (const char *type,
1043 struct objc_struct_layout *layout)
1044 {
1045 const char *ntype;
1046
1047 if (*type != _C_UNION_B && *type != _C_STRUCT_B)
1048 {
1049 _objc_abort ("record (or union) type expected in objc_layout_structure, got %s\n",
1050 type);
1051 }
1052
1053 type ++;
1054 layout->original_type = type;
1055
1056 /* Skip "<name>=" if any. Avoid embedded structures and unions. */
1057 ntype = type;
1058 while (*ntype != _C_STRUCT_E && *ntype != _C_STRUCT_B && *ntype != _C_UNION_B
1059 && *ntype++ != '=')
1060 /* do nothing */;
1061
1062 /* If there's a "<name>=", ntype - 1 points to '='; skip the the name */
1063 if (*(ntype - 1) == '=')
1064 type = ntype;
1065
1066 layout->type = type;
1067 layout->prev_type = NULL;
1068 layout->record_size = 0;
1069 layout->record_align = BITS_PER_UNIT;
1070
1071 layout->record_align = MAX (layout->record_align, STRUCTURE_SIZE_BOUNDARY);
1072 }
1073
1074 BOOL
1075 objc_layout_structure_next_member (struct objc_struct_layout *layout)
1076 {
1077 register int desired_align = 0;
1078
1079 /* The following are used only if the field is a bitfield */
1080 register const char *bfld_type = 0;
1081 register int bfld_type_align = 0, bfld_field_size = 0;
1082
1083 /* The current type without the type qualifiers */
1084 const char *type;
1085 BOOL unionp = layout->original_type[-1] == _C_UNION_B;
1086
1087 /* Add the size of the previous field to the size of the record. */
1088 if (layout->prev_type)
1089 {
1090 type = objc_skip_type_qualifiers (layout->prev_type);
1091 if (unionp)
1092 layout->record_size = MAX (layout->record_size,
1093 objc_sizeof_type (type) * BITS_PER_UNIT);
1094
1095 else if (*type != _C_BFLD)
1096 layout->record_size += objc_sizeof_type (type) * BITS_PER_UNIT;
1097 else {
1098 /* Get the bitfield's type */
1099 for (bfld_type = type + 1;
1100 isdigit ((unsigned char)*bfld_type);
1101 bfld_type++)
1102 /* do nothing */;
1103
1104 bfld_type_align = objc_alignof_type (bfld_type) * BITS_PER_UNIT;
1105 bfld_field_size = atoi (objc_skip_typespec (bfld_type));
1106 layout->record_size += bfld_field_size;
1107 }
1108 }
1109
1110 if ((unionp && *layout->type == _C_UNION_E)
1111 || (!unionp && *layout->type == _C_STRUCT_E))
1112 return NO;
1113
1114 /* Skip the variable name if any */
1115 layout->type = objc_skip_variable_name (layout->type);
1116 type = objc_skip_type_qualifiers (layout->type);
1117
1118 if (*type != _C_BFLD)
1119 desired_align = objc_alignof_type (type) * BITS_PER_UNIT;
1120 else
1121 {
1122 desired_align = 1;
1123 /* Skip the bitfield's offset */
1124 for (bfld_type = type + 1;
1125 isdigit ((unsigned char) *bfld_type);
1126 bfld_type++)
1127 /* do nothing */;
1128
1129 bfld_type_align = objc_alignof_type (bfld_type) * BITS_PER_UNIT;
1130 bfld_field_size = atoi (objc_skip_typespec (bfld_type));
1131 }
1132
1133 /* The following won't work for vectors. */
1134 #ifdef BIGGEST_FIELD_ALIGNMENT
1135 desired_align = MIN (desired_align, BIGGEST_FIELD_ALIGNMENT);
1136 #endif
1137 #ifdef ADJUST_FIELD_ALIGN
1138 desired_align = ADJUST_FIELD_ALIGN (type, desired_align);
1139 #endif
1140
1141 /* Record must have at least as much alignment as any field.
1142 Otherwise, the alignment of the field within the record
1143 is meaningless. */
1144 #ifndef PCC_BITFIELD_TYPE_MATTERS
1145 layout->record_align = MAX (layout->record_align, desired_align);
1146 #else /* PCC_BITFIELD_TYPE_MATTERS */
1147 if (*type == _C_BFLD)
1148 {
1149 /* For these machines, a zero-length field does not
1150 affect the alignment of the structure as a whole.
1151 It does, however, affect the alignment of the next field
1152 within the structure. */
1153 if (bfld_field_size)
1154 layout->record_align = MAX (layout->record_align, desired_align);
1155 else
1156 desired_align = objc_alignof_type (bfld_type) * BITS_PER_UNIT;
1157
1158 /* A named bit field of declared type `int'
1159 forces the entire structure to have `int' alignment.
1160 Q1: How is encoded this thing and how to check for it?
1161 Q2: How to determine maximum_field_alignment at runtime? */
1162
1163 /* if (DECL_NAME (field) != 0) */
1164 {
1165 int type_align = bfld_type_align;
1166 #if 0
1167 if (maximum_field_alignment != 0)
1168 type_align = MIN (type_align, maximum_field_alignment);
1169 else if (DECL_PACKED (field))
1170 type_align = MIN (type_align, BITS_PER_UNIT);
1171 #endif
1172
1173 layout->record_align = MAX (layout->record_align, type_align);
1174 }
1175 }
1176 else
1177 layout->record_align = MAX (layout->record_align, desired_align);
1178 #endif /* PCC_BITFIELD_TYPE_MATTERS */
1179
1180 /* Does this field automatically have alignment it needs
1181 by virtue of the fields that precede it and the record's
1182 own alignment? */
1183
1184 if (*type == _C_BFLD)
1185 layout->record_size = atoi (type + 1);
1186 else if (layout->record_size % desired_align != 0)
1187 {
1188 /* No, we need to skip space before this field.
1189 Bump the cumulative size to multiple of field alignment. */
1190 layout->record_size = ROUND (layout->record_size, desired_align);
1191 }
1192
1193 /* Jump to the next field in record. */
1194
1195 layout->prev_type = layout->type;
1196 layout->type = objc_skip_typespec (layout->type); /* skip component */
1197
1198 return YES;
1199 }
1200
1201 void objc_layout_finish_structure (struct objc_struct_layout *layout,
1202 unsigned int *size,
1203 unsigned int *align)
1204 {
1205 BOOL unionp = layout->original_type[-1] == _C_UNION_B;
1206 if (layout->type
1207 && ((!unionp && *layout->type == _C_STRUCT_E)
1208 || (unionp && *layout->type == _C_UNION_E)))
1209 {
1210 /* Work out the alignment of the record as one expression and store
1211 in the record type. Round it up to a multiple of the record's
1212 alignment. */
1213 #if defined (ROUND_TYPE_ALIGN) && ! defined (__sparc__)
1214 layout->record_align = ROUND_TYPE_ALIGN (layout->original_type-1,
1215 1,
1216 layout->record_align);
1217 #else
1218 layout->record_align = MAX (1, layout->record_align);
1219 #endif
1220
1221 #ifdef ROUND_TYPE_SIZE
1222 layout->record_size = ROUND_TYPE_SIZE (layout->original_type,
1223 layout->record_size,
1224 layout->record_align);
1225 #else
1226 /* Round the size up to be a multiple of the required alignment */
1227 layout->record_size = ROUND (layout->record_size, layout->record_align);
1228 #endif
1229
1230 layout->type = NULL;
1231 }
1232 if (size)
1233 *size = layout->record_size / BITS_PER_UNIT;
1234 if (align)
1235 *align = layout->record_align / BITS_PER_UNIT;
1236 }
1237
1238 void objc_layout_structure_get_info (struct objc_struct_layout *layout,
1239 unsigned int *offset,
1240 unsigned int *align,
1241 const char **type)
1242 {
1243 if (offset)
1244 *offset = layout->record_size / BITS_PER_UNIT;
1245 if (align)
1246 *align = layout->record_align / BITS_PER_UNIT;
1247 if (type)
1248 *type = layout->prev_type;
1249 }