1
#ifndef _avcall_h /*-*- C -*-*/
4
Copyright 1993 Bill Triggs, <Bill.Triggs@inrialpes.fr>
6
Copyright 1995-2006 Bruno Haible, <bruno@clisp.org>
8
This is free software distributed under the GNU General Public
9
Licence described in the file COPYING. Contact the author if
10
you don't have this or can't live with it. There is ABSOLUTELY
11
NO WARRANTY, explicit or implied, on this software.
13
/*----------------------------------------------------------------------
14
av_call() foreign function interface.
16
Varargs-style macros to build a C argument list incrementally
17
and call a function on it.
18
----------------------------------------------------------------------*/
21
/* These definitions are adjusted by `configure' automatically. */
76
/* Calling convention */
77
/* Define if using pcc non-reentrant struct return convention */
78
#undef __PCC_STRUCT_RETURN__
79
/* Define if small structs are returned in registers */
80
#undef __SMALL_STRUCT_RETURN__
81
/* Define if floating-point results are returned in the integer registers */
82
#undef __IREG_FLOAT_RETURN__
84
/* gl_AC_TYPE_LONG_LONG */
85
/* Define if your compiler supports the 'long long' type. */
88
/* End of definitions adjusted by `configure'. */
91
/* Max # words in argument-list and temporary structure storage.
93
#ifndef __AV_ALIST_WORDS
94
#define __AV_ALIST_WORDS 256
97
/* Determine the alignment of a type at compile time.
100
#define __AV_alignof __alignof__
102
#if defined(__mips__) || defined(__mipsn32__) || defined(__mips64__) /* SGI compiler */
103
#define __AV_alignof __builtin_alignof
105
#define __AV_offsetof(type,ident) ((unsigned long)&(((type*)0)->ident))
106
#define __AV_alignof(type) __AV_offsetof(struct { char __slot1; type __slot2; }, __slot2)
112
#if defined(__mipsn32__)
113
typedef long long __avword;
115
typedef long __avword;
139
enum __AV_alist_flags
142
/* how to return structs */
143
/* There are basically 3 ways to return structs:
144
* a. The called function returns a pointer to static data. Not reentrant.
145
* b. The caller passes the return structure address in a dedicated register
146
* or as a first (or last), invisible argument. The called function stores
148
* c. Like b, and the called function also returns the return structure
149
* address in the return value register. (This is not very distinguishable
151
* Independently of this,
152
* r. small structures (<= 4 or <= 8 bytes) may be returned in the return
153
* value register(s), or
154
* m. even small structures are passed in memory.
156
/* gcc-2.6.3 employs the following strategy:
157
* - If PCC_STATIC_STRUCT_RETURN is defined in the machine description
158
* it uses method a, else method c.
159
* - If flag_pcc_struct_return is set (either by -fpcc-struct-return or if
160
* DEFAULT_PCC_STRUCT_RETURN is defined to 1 in the machine description)
161
* it uses method m, else (either by -freg-struct-return or if
162
* DEFAULT_PCC_STRUCT_RETURN is defined to 0 in the machine description)
165
__AV_PCC_STRUCT_RETURN = 1<<0, /* a: need to copy the struct */
166
__AV_SMALL_STRUCT_RETURN = 1<<1, /* r: special case for small structs */
167
__AV_GCC_STRUCT_RETURN = 1<<2, /* consider 8 byte structs as small */
168
#if defined(__sparc__) && !defined(__sparc64__)
169
__AV_SUNCC_STRUCT_RETURN = 1<<3,
170
__AV_SUNPROCC_STRUCT_RETURN = 1<<4,
172
#if defined(__i386__)
173
__AV_NEXTGCC_STRUCT_RETURN = 1<<3,
174
__AV_MSVC_STRUCT_RETURN = 1<<4,
176
#if defined(__hppa__)
177
__AV_OLDGCC_STRUCT_RETURN = 1<<3,
179
/* the default way to return structs */
180
/* This choice here is based on the assumption that the function you are
181
* going to call has been compiled with the same compiler you are using to
183
* If you want to call functions with another struct returning convention,
184
* just #define __AV_STRUCT_RETURN ...
185
* before or after #including <avcall.h>.
187
#ifndef __AV_STRUCT_RETURN
189
#if defined(__sparc__) && !defined(__sparc64__) && defined(sun) && defined(__SUNPRO_C) /* SUNWspro cc */
190
__AV_SUNPROCC_STRUCT_RETURN,
192
#if defined(__PCC_STRUCT_RETURN__) /* defined through configure, see above */
193
__AV_PCC_STRUCT_RETURN,
195
#if defined(__SMALL_STRUCT_RETURN__) || defined(__mipsn32__) || defined(__mips64__) /* defined through configure, see above */
196
__AV_SMALL_STRUCT_RETURN |
198
#if defined(__GNUC__)
199
__AV_GCC_STRUCT_RETURN |
201
#if defined(__i386__) && defined(NeXT) && defined(__GNUC__) /* NeXT gcc-2.5.8 */
202
__AV_NEXTGCC_STRUCT_RETURN |
204
#if defined(__i386__) && defined(_MSC_VER) /* MSVC 4.0 */
205
__AV_MSVC_STRUCT_RETURN |
207
#if defined(__hppa__) && defined(__GNUC__) && (__GNUC__ < 3) && (__GNUC_MINOR__ < 7)
208
__AV_OLDGCC_STRUCT_RETURN |
215
/* how to return floats */
216
#if defined(__m68k__) || (defined(__sparc__) && !defined(__sparc64__))
217
__AV_SUNCC_FLOAT_RETURN = 1<<5,
219
#if defined(__m68k__)
220
__AV_FREG_FLOAT_RETURN = 1<<6,
222
/* the default way to return floats */
223
/* This choice here is based on the assumption that the function you are
224
* going to call has been compiled with the same compiler you are using to
226
* If you want to call functions with another float returning convention,
227
* just #define __AV_FLOAT_RETURN ...
228
* before or after #including <avcall.h>.
230
#ifndef __AV_FLOAT_RETURN
231
#if (defined(__m68k__) || (defined(__sparc__) && !defined(__sparc64__))) && !defined(__GNUC__) && defined(sun) && !defined(__SUNPRO_C) /* sun cc */
232
__AV_FLOAT_RETURN = __AV_SUNCC_FLOAT_RETURN,
233
#elif (defined(__m68k__) && !defined(__IREG_FLOAT_RETURN__))
234
__AV_FLOAT_RETURN = __AV_FREG_FLOAT_RETURN,
236
__AV_FLOAT_RETURN = 0,
240
/* how to pass structs */
241
#if defined(__mips__) || defined(__mipsn32__) || defined(__mips64__)
242
__AV_SGICC_STRUCT_ARGS = 1<<7,
244
#if defined(__powerpc__) && !defined(__powerpc64__)
245
__AV_AIXCC_STRUCT_ARGS = 1<<7,
247
/* the default way to pass floats */
248
/* This choice here is based on the assumption that the function you are
249
* going to call has been compiled with the same compiler you are using to
251
* If you want to call functions with another float passing convention,
252
* just #define __AV_STRUCT_ARGS ...
253
* before or after #including <avcall.h>.
255
#ifndef __AV_STRUCT_ARGS
256
#if (defined(__mips__) || defined(__mipsn32__) || defined(__mips64__)) && !defined(__GNUC__) /* SGI mips cc */
257
__AV_STRUCT_ARGS = __AV_SGICC_STRUCT_ARGS,
259
#if defined(__powerpc__) && !defined(__powerpc64__) && defined(_AIX) && !defined(__GNUC__) /* AIX cc, xlc */
260
__AV_STRUCT_ARGS = __AV_AIXCC_STRUCT_ARGS,
262
__AV_STRUCT_ARGS = 0,
267
/* how to pass floats */
268
/* ANSI C compilers and GNU gcc pass floats as floats.
269
* K&R C compilers pass floats as doubles. We don't support them any more.
272
/* how to pass and return small integer arguments */
273
__AV_ANSI_INTEGERS = 0, /* no promotions */
274
__AV_TRADITIONAL_INTEGERS = 0, /* promote [u]char, [u]short to [u]int */
275
/* Fortunately these two methods are compatible. Our macros work with both. */
277
/* stack cleanup policy */
278
__AV_CDECL_CLEANUP = 0, /* caller pops args after return */
279
__AV_STDCALL_CLEANUP = 0, /* callee pops args before return */
280
/* currently only supported on __i386__ */
282
__AV_CLEANUP = __AV_CDECL_CLEANUP,
285
/* These are for internal use only */
286
#if defined(__i386__) || defined(__m68k__) || defined(__mipsn32__) || defined(__mips64__) || defined(__sparc64__) || defined(__alpha__) || defined(__arm__) || (defined(__powerpc__) && !defined(__powerpc64__)) || defined(__convex__) || defined(__ia64__) || defined(__x86_64__) || defined(__s390__)
287
__AV_REGISTER_STRUCT_RETURN = 1<<9,
289
#if defined(__mips__) && !defined(__mipsn32__) && !defined(__mips64__)
290
__AV_FLOAT_1 = 1<<10,
291
__AV_FLOAT_2 = 1<<11,
292
__AV_DOUBLE_1 = 1<<12,
293
__AV_DOUBLE_2 = 1<<13,
296
__AV_flag_for_broken_compilers_that_dont_like_trailing_commas
301
/* function to be called */
303
/* some av_... macros need these flags */
305
/* return type, address for the result */
309
/* current pointer into the args[] array */
311
#if defined(__sparc__) || defined(__sparc64__) || defined(__hppa__) || (defined(__powerpc__) && !defined(__powerpc64__) && !defined(_AIX) && !(defined(__MACH__) && defined(__APPLE__))) || defined(__s390__)
312
/* limit pointer into the args[] array */
315
#if defined(__i386__) && 0
316
/* Filler word, needed if the numbers of words up to now in this structure */
317
/* is odd (because on MSVC, alignof(double) = 8, normally = 4). */
320
#if defined(__i386__) || defined(__m68k__) || (defined(__sparc__) && !defined(__sparc64__)) || defined(__hppa__) || defined(__arm__) || (defined(__powerpc__) && !defined(__powerpc64__)) || defined(__convex__) || defined(__s390__)
321
/* temporary storage, used to split doubles into two words */
324
#if defined(__sparc__) && !defined(__sparc64__) && defined(HAVE_LONG_LONG)
330
#if defined(__x86_64__)
331
/* store the integer arguments in an extra array */
335
#if defined(__mips__) && !defined(__mipsn32__) && !defined(__mips64__)
336
/* store the floating-point arguments in an extra array */
341
#if defined(__mipsn32__) || defined(__mips64__)
342
/* store the floating-point arguments in an extra array */
343
int anum; /* redundant: (LIST).aptr = &(LIST).args[(LIST).anum] */
344
unsigned int farg_mask; /* bitmask of those entries in farg[] which have a value */
345
unsigned int darg_mask; /* bitmask of those entries in args[] which have a double value */
348
#if defined(__sparc64__)
349
/* store the floating-point arguments in an extra array */
350
int anum; /* redundant: (LIST).aptr = &(LIST).args[(LIST).anum] */
351
unsigned int farg_mask; /* bitmask of those entries in farg[] which have a value */
352
unsigned int darg_mask; /* bitmask of those entries in args[] which have a double value */
354
#if defined(__ia64__) || defined(__x86_64__)
355
/* store the floating-point arguments in an extra array */
359
__avword args[__AV_ALIST_WORDS]; /* sizeof(double)-aligned */
360
#if defined(__powerpc__) || defined(__powerpc64__)
361
/* store the floating-point arguments in an extra array */
365
#if defined(__s390__)
366
/* store the floating-point arguments in an extra array */
378
/* store the arguments passed in registers in an extra array */
379
__avword regargs[8+7];
383
/* The limit for the pointer into the args[] array. */
384
#if defined(__sparc__) || defined(__sparc64__) || defined(__hppa__) || (defined(__powerpc__) && !defined(__powerpc64__) && !defined(_AIX) && !(defined(__MACH__) && defined(__APPLE__))) || defined(__s390)
385
#define __av_eptr(LIST) ((LIST).eptr)
387
#define __av_eptr(LIST) (&(LIST).args[__AV_ALIST_WORDS])
390
/* Delayed overflow detection */
391
#if defined(__hppa__)
392
#define av_overflown(LIST) ((LIST).aptr < __av_eptr(LIST))
394
#define av_overflown(LIST) ((LIST).aptr > __av_eptr(LIST))
399
* av_start_<type> macros which specify the return type
402
#define __AV_START_FLAGS \
403
__AV_STRUCT_RETURN | __AV_FLOAT_RETURN | __AV_STRUCT_ARGS | __AV_CLEANUP
405
#define __av_start(LIST,FUNC,RADDR,RETTYPE) \
406
((LIST).func = (__avword(*)())(FUNC), \
407
(LIST).raddr = (void*)(RADDR), \
408
(LIST).rtype = (RETTYPE), \
410
(LIST).flags = __AV_START_FLAGS)
412
#if defined(__i386__) || defined(__m68k__) || defined(__alpha__) || defined(__arm__) || defined(__m88k__) || defined(__convex__)
413
#define __av_start1(LIST) \
414
(LIST).aptr = &(LIST).args[0],
416
#if defined(__mips__) && !defined(__mipsn32__) && !defined(__mips64__)
417
#define __av_start1(LIST) \
419
(LIST).aptr = &(LIST).args[0],
421
#if defined(__mipsn32__) || defined(__mips64__)
422
#define __av_start1(LIST) \
424
(LIST).farg_mask = 0, \
425
(LIST).darg_mask = 0, \
426
(LIST).aptr = &(LIST).args[0],
428
#if defined(__sparc__) && !defined(__sparc64__)
429
#define __av_start1(LIST) \
430
(LIST).aptr = &(LIST).args[0], \
431
(LIST).eptr = &(LIST).args[__AV_ALIST_WORDS],
433
#if defined(__sparc64__)
434
#define __av_start1(LIST) \
436
(LIST).farg_mask = 0, \
437
(LIST).darg_mask = 0, \
438
(LIST).aptr = &(LIST).args[0], \
439
(LIST).eptr = &(LIST).args[__AV_ALIST_WORDS],
441
#if defined(__hppa__)
442
#define __av_start1(LIST) \
443
(LIST).aptr = &(LIST).args[__AV_ALIST_WORDS], \
444
(LIST).eptr = &(LIST).args[0],
446
#if defined(__powerpc__) || defined(__powerpc64__)
447
#if defined(__powerpc64__) || defined(_AIX) || (defined(__MACH__) && defined(__APPLE__))
448
#define __av_start1(LIST) \
449
(LIST).aptr = &(LIST).args[0], \
450
(LIST).faptr = &(LIST).fargs[0],
452
#define __av_start1(LIST) \
453
(LIST).aptr = &(LIST).args[0], \
454
(LIST).faptr = &(LIST).fargs[0], \
455
(LIST).eptr = &(LIST).args[__AV_ALIST_WORDS],
458
#if defined(__s390__)
459
#define __av_start1(LIST) \
460
(LIST).aptr = &(LIST).args[0], \
461
(LIST).fargwords = 0, \
462
(LIST).faptr = &(LIST).fargs[0], \
463
(LIST).daptr = &(LIST).dargs[0], \
464
(LIST).fargsusedptr = &(LIST).fargsused[0], \
465
(LIST).dargsusedptr = &(LIST).dargsused[0], \
466
(LIST).eptr = &(LIST).args[__AV_ALIST_WORDS],
468
#if defined(__ia64__)
469
#define __av_start1(LIST) \
470
(LIST).aptr = &(LIST).args[0], \
471
(LIST).faptr = &(LIST).fargs[0],
473
#if defined(__x86_64__)
474
#define __av_start1(LIST) \
475
(LIST).aptr = &(LIST).args[0], \
476
(LIST).iaptr = &(LIST).iargs[0], \
477
(LIST).faptr = &(LIST).fargs[0],
480
#define av_start_void(LIST,FUNC) __av_start(LIST,FUNC,0, __AVvoid)
481
#define av_start_char(LIST,FUNC,RADDR) __av_start(LIST,FUNC,RADDR,__AVchar)
482
#define av_start_schar(LIST,FUNC,RADDR) __av_start(LIST,FUNC,RADDR,__AVschar)
483
#define av_start_uchar(LIST,FUNC,RADDR) __av_start(LIST,FUNC,RADDR,__AVuchar)
484
#define av_start_short(LIST,FUNC,RADDR) __av_start(LIST,FUNC,RADDR,__AVshort)
485
#define av_start_ushort(LIST,FUNC,RADDR) __av_start(LIST,FUNC,RADDR,__AVushort)
486
#define av_start_int(LIST,FUNC,RADDR) __av_start(LIST,FUNC,RADDR,__AVint)
487
#define av_start_uint(LIST,FUNC,RADDR) __av_start(LIST,FUNC,RADDR,__AVuint)
488
#define av_start_long(LIST,FUNC,RADDR) __av_start(LIST,FUNC,RADDR,__AVlong)
489
#define av_start_ulong(LIST,FUNC,RADDR) __av_start(LIST,FUNC,RADDR,__AVulong)
490
#define av_start_longlong(LIST,FUNC,RADDR) __av_start(LIST,FUNC,RADDR,__AVlonglong)
491
#define av_start_ulonglong(LIST,FUNC,RADDR) __av_start(LIST,FUNC,RADDR,__AVulonglong)
492
#define av_start_float(LIST,FUNC,RADDR) __av_start(LIST,FUNC,RADDR,__AVfloat)
493
#define av_start_double(LIST,FUNC,RADDR) __av_start(LIST,FUNC,RADDR,__AVdouble)
494
#define av_start_ptr(LIST,FUNC,TYPE,RADDR) __av_start(LIST,FUNC,RADDR,__AVvoidp)
496
#define av_start_struct(LIST,FUNC,TYPE,TYPE_SPLITTABLE,RADDR) \
497
_av_start_struct(LIST,FUNC,sizeof(TYPE),TYPE_SPLITTABLE,RADDR)
498
#define _av_start_struct(LIST,FUNC,TYPE_SIZE,TYPE_SPLITTABLE,RADDR) \
499
(__av_start(LIST,FUNC,RADDR,__AVstruct), \
500
(LIST).rsize = TYPE_SIZE, \
501
__av_start_struct1(LIST,TYPE_SIZE,TYPE_SPLITTABLE), \
504
#define __av_start_struct1(LIST,TYPE_SIZE,TYPE_SPLITTABLE) \
505
((LIST).flags & __AV_PCC_STRUCT_RETURN \
506
? /* pcc struct return convention: \
507
* called function returns pointer to value, we'll copy its contents afterwards. \
510
: __av_start_struct2(LIST,TYPE_SIZE,TYPE_SPLITTABLE) \
512
#if (defined(__sparc__) && !defined(__sparc64__)) || defined(__m88k__)
513
/* Return structure pointer is passed in a special register.
515
#define __av_start_struct2(LIST,TYPE_SIZE,TYPE_SPLITTABLE) 0
517
#define __av_start_struct2(LIST,TYPE_SIZE,TYPE_SPLITTABLE) \
518
(((LIST).flags & __AV_SMALL_STRUCT_RETURN) \
519
&& __av_reg_struct_return(LIST,TYPE_SIZE,TYPE_SPLITTABLE) \
520
? /* <= Word-sized structures are returned in a register. */ \
521
__av_start_struct3(LIST) \
522
: __av_start_struct4(LIST,TYPE_SIZE) \
524
/* Determines whether a structure is returned in registers,
525
* depending on its size and its word-splittable flag.
527
#if (defined(__i386__) && defined(_WIN32))
528
#define __av_reg_struct_return(LIST,TYPE_SIZE,TYPE_SPLITTABLE) \
529
((TYPE_SIZE) == 1 || (TYPE_SIZE) == 2 || (TYPE_SIZE) == 4 \
530
|| ((TYPE_SIZE) == 8 \
531
&& (((LIST).flags & __AV_MSVC_STRUCT_RETURN) \
532
|| ((TYPE_SPLITTABLE) \
533
&& ((LIST).flags & __AV_GCC_STRUCT_RETURN) \
535
/* Turn on __AV_REGISTER_STRUCT_RETURN if __AV_SMALL_STRUCT_RETURN was set
536
* and the struct will actually be returned in registers.
538
#define __av_start_struct3(LIST) \
539
((LIST).flags |= __AV_REGISTER_STRUCT_RETURN, 0)
541
#if (defined(__i386__) && !defined(_WIN32)) || defined(__m68k__) || defined(__arm__) || (defined(__powerpc__) && !defined(__powerpc64__)) || defined(__convex__) || defined(__s390__)
542
#define __av_reg_struct_return(LIST,TYPE_SIZE,TYPE_SPLITTABLE) \
543
((TYPE_SIZE) == 1 || (TYPE_SIZE) == 2 || (TYPE_SIZE) == 4 \
544
|| ((TYPE_SIZE) == 8 && (TYPE_SPLITTABLE) \
545
&& ((LIST).flags & __AV_GCC_STRUCT_RETURN) \
547
/* Turn on __AV_REGISTER_STRUCT_RETURN if __AV_SMALL_STRUCT_RETURN was set
548
* and the struct will actually be returned in registers.
550
#define __av_start_struct3(LIST) \
551
((LIST).flags |= __AV_REGISTER_STRUCT_RETURN, 0)
553
#if defined(__alpha__)
554
#define __av_reg_struct_return(LIST,TYPE_SIZE,TYPE_SPLITTABLE) \
555
((TYPE_SIZE) == 1 || (TYPE_SIZE) == 2 || (TYPE_SIZE) == 4 || (TYPE_SIZE) == 8 \
556
|| ((TYPE_SIZE) == 16 && (TYPE_SPLITTABLE) \
557
&& ((LIST).flags & __AV_GCC_STRUCT_RETURN) \
559
/* Turn on __AV_REGISTER_STRUCT_RETURN if __AV_SMALL_STRUCT_RETURN was set
560
* and the struct will actually be returned in registers.
562
#define __av_start_struct3(LIST) \
563
((LIST).flags |= __AV_REGISTER_STRUCT_RETURN, 0)
565
#if defined(__hppa__)
566
#define __av_reg_struct_return(LIST,TYPE_SIZE,TYPE_SPLITTABLE) \
567
((LIST).flags & __AV_OLDGCC_STRUCT_RETURN \
568
? ((TYPE_SIZE) == 1 || (TYPE_SIZE) == 2 || (TYPE_SIZE) == 4) \
569
: ((TYPE_SIZE) <= 8) \
571
/* Test both __AV_OLDGCC_STRUCT_RETURN and __AV_SMALL_STRUCT_RETURN at run time. */
572
#define __av_start_struct3(LIST) \
575
#if defined(__mips__) && !defined(__mipsn32__) && !defined(__mips64__)
576
#define __av_reg_struct_return(LIST,TYPE_SIZE,TYPE_SPLITTABLE) \
577
((TYPE_SIZE) == 1 || (TYPE_SIZE) == 2 || (TYPE_SIZE) == 4)
578
/* Test __AV_SMALL_STRUCT_RETURN instead of __AV_REGISTER_STRUCT_RETURN. */
579
#define __av_start_struct3(LIST) \
582
#if defined(__mipsn32__) || defined(__mips64__)
583
#define __av_reg_struct_return(LIST,TYPE_SIZE,TYPE_SPLITTABLE) \
584
((LIST).flags & __AV_GCC_STRUCT_RETURN \
585
? ((TYPE_SIZE) == 1 || (TYPE_SIZE) == 2 || (TYPE_SIZE) == 4 || (TYPE_SIZE) == 8) \
586
: ((TYPE_SIZE) <= 16) \
588
/* Turn on __AV_REGISTER_STRUCT_RETURN if __AV_SMALL_STRUCT_RETURN was set
589
* and the struct will actually be returned in registers.
591
#define __av_start_struct3(LIST) \
592
((LIST).flags |= __AV_REGISTER_STRUCT_RETURN, 0)
594
#if defined(__powerpc64__)
595
#define __av_reg_struct_return(LIST,TYPE_SIZE,TYPE_SPLITTABLE) \
597
#define __av_start_struct3(LIST) \
600
#if defined(__sparc64__) || defined(__ia64__)
601
#define __av_reg_struct_return(LIST,TYPE_SIZE,TYPE_SPLITTABLE) \
603
/* Turn on __AV_REGISTER_STRUCT_RETURN if __AV_SMALL_STRUCT_RETURN was set
604
* and the struct will actually be returned in registers.
606
#define __av_start_struct3(LIST) \
607
((LIST).flags |= __AV_REGISTER_STRUCT_RETURN, 0)
609
#if defined(__x86_64__)
610
#define __av_reg_struct_return(LIST,TYPE_SIZE,TYPE_SPLITTABLE) \
612
/* Turn on __AV_REGISTER_STRUCT_RETURN if __AV_SMALL_STRUCT_RETURN was set
613
* and the struct will actually be returned in registers.
615
#define __av_start_struct3(LIST) \
616
((LIST).flags |= __AV_REGISTER_STRUCT_RETURN, 0)
618
#if defined(__i386__)
619
/* Return structure pointer is passed in a special register or as first arg. */
620
#define __av_start_struct4(LIST,TYPE_SIZE) \
621
((LIST).flags & __AV_NEXTGCC_STRUCT_RETURN \
622
? 0 /* special register */ \
623
: (*(LIST).aptr++ = (__avword)((LIST).raddr), 0) /* first arg */ \
626
#if defined(__m68k__) || defined(__hppa__) || defined(__ia64__)
627
/* Return structure pointer is passed in a special register.
629
#define __av_start_struct4(LIST,TYPE_SIZE) 0
631
/* Return structure pointer is passed as first arg.
633
#if defined(__alpha__) || defined(__arm__) || defined(__powerpc__) || defined(__powerpc64__) || defined(__convex__) || defined(__s390__)
634
#define __av_start_struct4(LIST,TYPE_SIZE) \
635
(*(LIST).aptr++ = (__avword)((LIST).raddr), 0)
637
#if defined(__mips__) || defined(__mipsn32__) || defined(__mips64__) || defined(__sparc64__)
638
#define __av_start_struct4(LIST,TYPE_SIZE) \
639
(*(LIST).aptr++ = (__avword)((LIST).raddr), \
644
#if defined(__x86_64__)
645
#define __av_start_struct4(LIST,TYPE_SIZE) \
646
(*(LIST).iaptr++ = (__avword)((LIST).raddr), 0)
652
* av_<type> macros which specify the argument and its type
656
* scalar argument types
659
#if defined(__i386__) || defined(__m68k__) || (defined(__sparc__) && !defined(__sparc64__)) || defined(__alpha__) || defined(__arm__) || defined(__powerpc__) || defined(__powerpc64__) || defined(__m88k__) || defined(__convex__) || defined(__ia64__) || defined(__x86_64__) || defined(__s390__)
660
/* Floats and all integer types are passed as words,
661
* doubles as two words.
663
#define __av_word(LIST,VAL) \
664
(++(LIST).aptr > __av_eptr(LIST) \
665
? -1 : ((LIST).aptr[-1] = (__avword)(VAL), 0))
667
#if defined(__mips__) || defined(__mipsn32__) || defined(__mips64__) || defined(__sparc64__)
668
/* Most things are passed as integers:
670
#define __av_word(LIST,VAL) \
671
(++(LIST).aptr > __av_eptr(LIST) \
672
? -1 : ((LIST).anum++, (LIST).aptr[-1] = (__avword)(VAL), 0))
674
#if defined(__hppa__)
675
/* Floats and all integer types are passed as words,
676
* doubles as two words.
678
#define __av_word(LIST,VAL) \
679
(--(LIST).aptr < __av_eptr(LIST) \
680
? -1 : (*(LIST).aptr = (__avword)(VAL), 0))
683
/* Some arguments are passed in registers. Query the macro AV_ARG_REGNUM.
684
* This should really be an argument to __av_word.
686
#undef __av_word /**/
687
#define __av_word(LIST,VAL) \
688
((AV_ARG_REGNUM) >= 0 \
689
? ((AV_ARG_REGNUM) < 8+7 \
690
? -1 : ((LIST).regargs[(AV_ARG_REGNUM)] = (__avword)(VAL), 0)) \
691
: (++(LIST).aptr > __av_eptr(LIST) \
692
? -1 : ((LIST).aptr[-1] = (__avword)(VAL), 0)))
695
/* integer argument types */
697
#if defined(__x86_64__)
698
/* The first 6 integer arguments are passed in registers. */
699
#define av_long(LIST,VAL) \
700
((LIST).iaptr < &(LIST).iargs[6] \
701
? (*(LIST).iaptr++ = (long)(VAL), 0) \
702
: __av_word(LIST,(long)(VAL)))
704
#define av_long(LIST,VAL) __av_word(LIST,(long)(VAL))
707
#if defined(__x86_64__)
708
/* The first 6 integer arguments are passed in registers. */
709
#define av_ulong(LIST,VAL) \
710
((LIST).iaptr < &(LIST).iargs[6] \
711
? (*(LIST).iaptr++ = (unsigned long)(VAL), 0) \
712
: __av_word(LIST,(unsigned long)(VAL)))
714
#define av_ulong(LIST,VAL) __av_word(LIST,(unsigned long)(VAL))
717
#if defined(__x86_64__)
718
/* The first 6 integer arguments are passed in registers. */
719
#define av_ptr(LIST,TYPE,VAL) \
720
((LIST).iaptr < &(LIST).iargs[6] \
721
? (*(LIST).iaptr++ = (__avword)(TYPE)(VAL), 0) \
722
: __av_word(LIST,(TYPE)(VAL)))
724
#define av_ptr(LIST,TYPE,VAL) __av_word(LIST,(TYPE)(VAL))
727
#define av_char av_long
728
#define av_schar av_long
729
#define av_short av_long
730
#define av_int av_long
731
#define av_uchar av_ulong
732
#define av_ushort av_ulong
733
#define av_uint av_ulong
735
#if defined(__mips64__) || defined(__sparc64__) || defined(__alpha__) || defined(__powerpc64__) || defined(__ia64__) || defined(__x86_64__)
736
/* `long long' and `long' are identical. */
737
#define av_longlong av_long
738
#define av_ulonglong av_ulong
739
#elif defined(__mipsn32__)
740
/* `long long' fits in __avword. */
741
#define av_longlong __av_word
742
#define av_ulonglong(LIST,VAL) __av_word(LIST,(unsigned long long)(VAL))
743
#elif defined(__i386__) || defined(__m68k__) || (defined(__mips__) && !defined(__mipsn32__) && !defined(__mips64__)) || (defined(__sparc__) && !defined(__sparc64__)) || defined(__hppa__) || defined(__arm__) || defined(__powerpc__) || defined(__m88k__) || defined(__convex__) || defined(__s390__)
744
/* `long long's are passed embedded on the arg stack. */
745
#define av_longlong(LIST,VAL) __av_longlong(LIST,long long,VAL)
746
#define av_ulonglong(LIST,VAL) __av_longlong(LIST,unsigned long long,VAL)
747
#if defined(__i386__) || defined(__m68k__) || defined(__arm__) || (defined(__powerpc__) && (defined(_AIX) || (defined(__MACH__) && defined(__APPLE__)))) || defined(__convex__)
748
/* `long long's are (at most) word-aligned. */
749
#define __av_longlong(LIST,TYPE,VAL) \
750
(((LIST).aptr += sizeof(TYPE)/sizeof(__avword)) > __av_eptr(LIST) \
751
? -1 : (((TYPE*)(LIST).aptr)[-1] = (TYPE)(VAL), 0))
753
#if defined(__mips__) || (defined(__sparc__) && !defined(__sparc64__)) || defined(__hppa__) || (defined(__powerpc__) && !(defined(_AIX) || (defined(__MACH__) && defined(__APPLE__)))) || defined(__m88k__) || defined(__s390__)
754
/* `long long's have alignment 8. */
755
#if defined(__mips__)
756
#define __av_longlong(LIST,TYPE,VAL) \
757
(((LIST).aptr = (__avword*)(((__avword)(LIST).aptr+sizeof(TYPE)+__AV_alignof(TYPE)-1) & -(long)__AV_alignof(TYPE))) > __av_eptr(LIST) \
758
? -1 : ((LIST).anum++, ((TYPE*)(LIST).aptr)[-1] = (TYPE)(VAL), 0))
760
#if defined(__sparc__) && !defined(__sparc64__)
761
/* Within the arg stack, the alignment is only 4, not 8. */
762
/* This assumes sizeof(long long) == 2*sizeof(__avword). */
763
#define __av_longlong(LIST,TYPE,VAL) \
764
(((LIST).aptr += sizeof(TYPE)/sizeof(__avword)) > __av_eptr(LIST) \
766
((LIST).tmp._longlong = (TYPE)(VAL), \
767
(LIST).aptr[-2] = (LIST).tmp.words[0], \
768
(LIST).aptr[-1] = (LIST).tmp.words[1], \
771
#if defined(__hppa__)
772
#define __av_longlong(LIST,TYPE,VAL) \
773
(((LIST).aptr = (__avword*)(((__avword)(LIST).aptr & -(long)__AV_alignof(TYPE)) - sizeof(TYPE))) < __av_eptr(LIST) \
774
? -1 : (*(TYPE*)(LIST).aptr = (TYPE)(VAL), 0))
776
#if (defined(__powerpc__) && !defined(__powerpc64__) && !(defined(_AIX) || (defined(__MACH__) && defined(__APPLE__)))) || defined(__m88k__)
777
#define __av_longlong(LIST,TYPE,VAL) \
778
(((LIST).aptr = (__avword*)(((__avword)(LIST).aptr+sizeof(TYPE)+__AV_alignof(TYPE)-1) & -(long)__AV_alignof(TYPE))) > __av_eptr(LIST) \
779
? -1 : (((TYPE*)(LIST).aptr)[-1] = (TYPE)(VAL), 0))
781
#if defined(__s390__)
782
#define __av_longlong(LIST,TYPE,VAL) \
783
(((LIST).aptr = (__avword*)(((__avword)(LIST).aptr+sizeof(TYPE)+__AV_alignof(TYPE)-1) & -(long)__AV_alignof(TYPE))) > __av_eptr(LIST) \
785
(((LIST).aptr - (LIST).args - (LIST).fargwords == 4 ? ++(LIST).aptr,0 : 0), \
786
(((TYPE*)(LIST).aptr)[-1] = (TYPE)(VAL), 0)))
791
/* floating-point argument types */
793
#if defined(__i386__) || defined(__m68k__) || (defined(__sparc__) && !defined(__sparc64__)) || defined(__arm__) || defined(__convex__)
795
#define av_float(LIST,VAL) \
796
(++(LIST).aptr > __av_eptr(LIST) \
797
? -1 : (((float*)(LIST).aptr)[-1] = (float)(VAL), 0))
799
/* This assumes sizeof(double) == 2*sizeof(__avword). */
800
#define av_double(LIST,VAL) \
801
(((LIST).aptr += 2) > __av_eptr(LIST) \
803
((LIST).tmp._double = (double)(VAL), \
804
(LIST).aptr[-2] = (LIST).tmp.words[0], \
805
(LIST).aptr[-1] = (LIST).tmp.words[1], \
810
#if defined(__mips__) && !defined(__mipsn32__) && !defined(__mips64__)
812
/* Up to 2 leading float or double non-varargs args can be passed in
813
* float registers, but we also push them into the corresponding int
814
* registers in case of varargs. For doubles we need to align the aptr
815
* to an even boundary.
817
#define av_float(LIST,VAL) \
818
(++(LIST).aptr > __av_eptr(LIST) \
819
? -1 : ((++(LIST).anum == 1 \
820
? ((LIST).flags |= __AV_FLOAT_1, \
821
(LIST).floatarg[0] = ((float*)(LIST).aptr)[-1] = (float)(VAL))\
822
: (LIST).anum == 2 && (((LIST).flags & __AV_FLOAT_1) || ((LIST).flags & __AV_DOUBLE_1))\
823
? ((LIST).flags |= __AV_FLOAT_2, \
824
(LIST).floatarg[1] = ((float*)(LIST).aptr)[-1] = (float)(VAL))\
825
: (((float*)(LIST).aptr)[-1] = (float)(VAL))), \
828
#define av_double(LIST,VAL) \
829
(((LIST).aptr = (__avword*)(((__avword)(LIST).aptr+15)&-8)) \
831
? -1 : ((++(LIST).anum == 1 \
832
? ((LIST).flags |= __AV_DOUBLE_1, \
833
(LIST).doublearg[0] = ((double*)(LIST).aptr)[-1] = (double)(VAL))\
834
: (LIST).anum == 2 && (((LIST).flags & __AV_FLOAT_1) || ((LIST).flags & __AV_DOUBLE_1))\
835
? ((LIST).flags |= __AV_DOUBLE_2, \
836
(LIST).doublearg[1] = ((double*)(LIST).aptr)[-1] = (double)(VAL))\
837
: (((double*)(LIST).aptr)[-1] = (double)(VAL))), \
842
#if defined(__mipsn32__) || defined(__mips64__)
844
/* Up to 8 leading float or double non-varargs args can be passed in
845
* float registers, but we also push them into the corresponding int
846
* registers in case of varargs.
848
#define av_float(LIST,VAL) \
849
((LIST).aptr >= __av_eptr(LIST) \
850
? -1 : (((LIST).anum < 8 \
851
? ((LIST).farg_mask |= (1 << (LIST).anum), \
852
(LIST).farg[(LIST).anum] = *(float*)(LIST).aptr = (float)(VAL)) \
853
: (*(float*)(LIST).aptr = (float)(VAL))), \
858
#define av_double(LIST,VAL) \
859
((LIST).aptr >= __av_eptr(LIST) \
860
? -1 : (((LIST).anum < 8 && ((LIST).darg_mask |= (1 << (LIST).anum))), \
861
*(double*)(LIST).aptr = (double)(VAL), \
868
#if defined(__sparc64__)
870
/* Up to 16 leading float or double non-varargs args can be passed in
871
* float registers, but we also push them into the corresponding int
872
* registers in case of varargs.
874
#define av_float(LIST,VAL) \
875
((LIST).aptr >= __av_eptr(LIST) \
876
? -1 : (((LIST).anum < 16 && ((LIST).farg_mask |= (1 << (LIST).anum))), \
877
(*(float*)(LIST).aptr = (float)(VAL)), \
882
#define av_double(LIST,VAL) \
883
((LIST).aptr >= __av_eptr(LIST) \
884
? -1 : (((LIST).anum < 16 && ((LIST).darg_mask |= (1 << (LIST).anum))), \
885
*(double*)(LIST).aptr = (double)(VAL), \
892
#if defined(__alpha__)
894
#define av_double(LIST,VAL) \
895
(++(LIST).aptr > __av_eptr(LIST) \
896
? -1 : (((double*)(LIST).aptr)[-1] = (double)(VAL), 0))
898
#define av_float(LIST,VAL) \
899
(++(LIST).aptr > __av_eptr(LIST) \
901
: (((LIST).aptr > &(LIST).args[6] \
902
? /* These args will be fetched from memory using "lds" instructions */ \
903
/* therefore store them as floats */ \
904
(*(float*)((LIST).aptr-1) = (float)(VAL)) \
905
: /* The first 6 args will be put into registers by "ldt" instructions */ \
906
/* (see avcall-alpha.c!). Therefore store them as doubles. */ \
907
/* When viewed as floats, the value will be the correct one. */\
908
(*(double*)((LIST).aptr-1) = (double)(float)(VAL)) \
913
#if defined(__hppa__)
915
#define av_float(LIST,VAL) \
916
(--(LIST).aptr < __av_eptr(LIST) \
917
? -1 : (*(float*)(LIST).aptr = (float)(VAL), 0))
919
#define av_double(LIST,VAL) \
920
(((LIST).aptr = (__avword*)(((long)(LIST).aptr-sizeof(double)) & -(long)sizeof(double))) \
922
? -1 : (*(double*)(LIST).aptr = (double)(VAL), 0))
926
#if defined(__powerpc__) && !defined(__powerpc64__) && (defined(_AIX) || (defined(__MACH__) && defined(__APPLE__)))
928
/* Up to 13 float or double non-varargs args can be passed in
929
* float registers, but we also push them into the corresponding int
930
* registers in case of varargs.
933
#define av_float(LIST,VAL) \
934
(++(LIST).aptr > __av_eptr(LIST) \
935
? -1 : (((float*)(LIST).aptr)[-1] = (float)(VAL), \
936
(LIST).faptr < &(LIST).fargs[13] && \
937
(*(LIST).faptr++ = (double)(float)(VAL)), \
940
#define av_double(LIST,VAL) \
941
(((LIST).aptr += 2) > __av_eptr(LIST) \
943
((LIST).tmp._double = (double)(VAL), \
944
(LIST).aptr[-2] = (LIST).tmp.words[0], \
945
(LIST).aptr[-1] = (LIST).tmp.words[1], \
946
(LIST).faptr < &(LIST).fargs[13] && \
947
(*(LIST).faptr++ = (LIST).tmp._double), \
952
#if defined(__powerpc__) && !defined(__powerpc64__) && !(defined(_AIX) || (defined(__MACH__) && defined(__APPLE__)))
954
/* Up to 8 float or double non-varargs args can be passed in
955
* float registers, without occupying space in the general registers.
958
#define av_float(LIST,VAL) \
959
((LIST).faptr < &(LIST).fargs[8] \
960
? ((*(LIST).faptr++ = (double)(float)(VAL)), 0) \
961
: (++(LIST).aptr > __av_eptr(LIST) \
962
? -1 : (((float*)(LIST).aptr)[-1] = (float)(VAL), 0)))
964
#define av_double(LIST,VAL) \
965
((LIST).faptr < &(LIST).fargs[8] \
966
? ((*(LIST).faptr++ = (double)(VAL)), 0) \
967
: (((LIST).aptr += 2) > __av_eptr(LIST) \
969
((LIST).tmp._double = (double)(VAL), \
970
(LIST).aptr[-2] = (LIST).tmp.words[0], \
971
(LIST).aptr[-1] = (LIST).tmp.words[1], \
976
#if defined(__powerpc64__)
978
/* Up to 13 float or double non-varargs args can be passed in
979
* float registers, but we also push them into the corresponding int
980
* registers in case of varargs.
983
#define av_float(LIST,VAL) \
984
(++(LIST).aptr > __av_eptr(LIST) \
985
? -1 : (((float*)(LIST).aptr)[-1] = (float)(VAL), \
986
(LIST).faptr < &(LIST).fargs[13] && \
987
(*(LIST).faptr++ = (double)(float)(VAL)), \
990
#define av_double(LIST,VAL) \
991
(++(LIST).aptr > __av_eptr(LIST) \
992
? -1 : (((double*)(LIST).aptr)[-1] = (double)(VAL), \
993
(LIST).faptr < &(LIST).fargs[13] && \
994
(*(LIST).faptr++ = (double)(VAL)), \
999
#if defined(__s390__)
1001
/* Up to 2 float or double non-varargs args can be passed in
1002
* float registers, without occupying space in the general registers.
1005
#define av_float(LIST,VAL) \
1006
((LIST).faptr < &(LIST).fargs[2] \
1007
? (LIST).daptr++, *(LIST).fargsusedptr++ = 1, *(LIST).dargsusedptr++ = 0, ((*(LIST).faptr++ = (float)(VAL)), 0) \
1008
: (++(LIST).aptr > __av_eptr(LIST) \
1009
? -1 : ((LIST).fargwords++, ((float*)(LIST).aptr)[-1] = (float)(VAL), 0)))
1011
#define av_double(LIST,VAL) \
1012
((LIST).daptr < &(LIST).dargs[2] \
1013
? (LIST).faptr++, *(LIST).dargsusedptr++ = 1, *(LIST).fargsusedptr++ = 0, ((*(LIST).daptr++ = (double)(VAL)), 0) \
1014
: (((LIST).aptr += 2) > __av_eptr(LIST) \
1016
((LIST).fargwords+=2, (LIST).tmp._double = (double)(VAL), \
1017
(LIST).aptr[-2] = (LIST).tmp.words[0], \
1018
(LIST).aptr[-1] = (LIST).tmp.words[1], \
1023
#if defined(__m88k__)
1025
#define av_float(LIST,VAL) \
1026
(++(LIST).aptr > __av_eptr(LIST) \
1027
? -1 : (((float*)(LIST).aptr)[-1] = (float)(VAL), 0))
1029
#define av_double(LIST,VAL) \
1030
(((LIST).aptr = (__avword*)(((long)(LIST).aptr+sizeof(double)+sizeof(double)-1) & -(long)sizeof(double))) \
1032
? -1 : (((double*)(LIST).aptr)[-1] = (double)(VAL), 0))
1036
#if defined(__ia64__)
1038
/* Up to 8 leading float or double non-varargs args can be passed in
1039
* float registers, but we also push them into the corresponding int
1040
* registers in case of varargs.
1042
#define av_float(LIST,VAL) \
1043
((LIST).aptr >= __av_eptr(LIST) \
1044
? -1 : ((*(float*)(LIST).aptr = (float)(VAL)), \
1045
((LIST).faptr < &(LIST).fargs[8] && (*(LIST).faptr = *(float*)(LIST).aptr, (LIST).faptr++)), \
1049
#define av_double(LIST,VAL) \
1050
((LIST).aptr >= __av_eptr(LIST) \
1051
? -1 : (*(double*)(LIST).aptr = (double)(VAL), \
1052
((LIST).faptr < &(LIST).fargs[8] && (*(LIST).faptr = *(double*)(LIST).aptr, (LIST).faptr++)), \
1058
#if defined(__x86_64__)
1060
/* Up to 8 leading float or double args can be passed in float registers.
1062
#define av_float(LIST,VAL) \
1063
((LIST).faptr < &(LIST).fargs[8] \
1064
? (*(LIST).faptr = 0.0, *(float*)(LIST).faptr = (float)(VAL), \
1067
: ((LIST).aptr >= __av_eptr(LIST) \
1068
? -1 : ((*(float*)(LIST).aptr = (float)(VAL)), \
1072
#define av_double(LIST,VAL) \
1073
((LIST).faptr < &(LIST).fargs[8] \
1074
? (*(LIST).faptr = (double)(VAL), \
1077
: ((LIST).aptr >= __av_eptr(LIST) \
1078
? -1 : ((*(double*)(LIST).aptr = (double)(VAL)), \
1085
* structure argument types
1088
#define av_struct(LIST,TYPE,VAL) \
1089
__av_struct(LIST,TYPE,sizeof(TYPE),__AV_alignof(TYPE),__av_struct_assign,VAL)
1090
#define __av_struct_assign(TYPE,TYPE_SIZE,TYPE_ALIGN,PLACE,VAL) \
1091
*(TYPE*)(PLACE) = (VAL)
1092
/* _av_struct() is like av_struct(), except that you pass the type's size and alignment
1093
* and the value's address instead of the type and the value themselves.
1095
#define _av_struct(LIST,TYPE_SIZE,TYPE_ALIGN,VAL_ADDR) \
1096
__av_struct(LIST,unknown,TYPE_SIZE,TYPE_ALIGN,__av_struct_copy,VAL_ADDR)
1097
#define __av_struct_copy(TYPE,TYPE_SIZE,TYPE_ALIGN,PLACE,VAL_ADDR) \
1098
__structcpy(PLACE,VAL_ADDR,TYPE_SIZE,TYPE_ALIGN)
1099
/* Structure argument alignment. */
1100
#if defined(__i386__) && defined(_MSC_VER)
1101
/* In MSVC, doubles inside structures have alignment 8, i.e.
1102
* __AV_alignof(double) = 8, but doubles (and also structures containing
1103
* doubles) are passed on the stack with alignment 4. Looks really weird.
1105
#define __av_struct_alignment(TYPE_ALIGN) \
1106
((TYPE_ALIGN) <= 4 ? (TYPE_ALIGN) : 4)
1108
#define __av_struct_alignment(TYPE_ALIGN) \
1111
#if defined(__i386__) || defined(__mips__) || defined(__mipsn32__) || defined(__mips64__) || defined(__alpha__) || (defined(__powerpc__) && !defined(__powerpc64__) && (defined(_AIX) || (defined(__MACH__) && defined(__APPLE__)))) || defined(__powerpc64__) || defined(__m88k__) || defined(__ia64__) || defined(__s390__)
1112
/* Structures are passed as fully aligned structures on the arg stack.
1113
* We align the aptr, store the structure, then fill to word alignment.
1114
* Single-small-integer structures are NOT promoted to integers and have
1115
* different alignment.
1117
/* little endian -> small structures < 1 word are adjusted to the left */
1118
#if defined(__i386__) || defined(__alpha__) || defined(__x86_64__)
1119
#define __av_struct(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1121
(__avword*)(((__avword)(LIST).aptr+(TYPE_SIZE)+__av_struct_alignment(TYPE_ALIGN)-1) & -(long)__av_struct_alignment(TYPE_ALIGN)))\
1123
? -1 : (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((__avword)(LIST).aptr-(TYPE_SIZE)),VAL),\
1124
(LIST).aptr = (__avword*)(((__avword)(LIST).aptr+sizeof(__avword)-1) & -(long)sizeof(__avword)),\
1127
#if defined(__ia64__)
1128
/* Types larger than a word have 2-word alignment. */
1129
#define __av_struct(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1130
((LIST).aptr = (__avword*)(((__avword)(LIST).aptr+(TYPE_SIZE)+__av_struct_alignment(TYPE_ALIGN)-1) & -(long)__av_struct_alignment(TYPE_ALIGN)), \
1131
((TYPE_SIZE) > sizeof(__avword) && (((LIST).aptr - &(LIST).args[0]) & 1) ? ++(LIST).aptr : 0), \
1132
((LIST).aptr > __av_eptr(LIST) \
1133
? -1 : (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((__avword)(LIST).aptr-(TYPE_SIZE)),VAL),\
1134
(LIST).aptr = (__avword*)(((__avword)(LIST).aptr+sizeof(__avword)-1) & -(long)sizeof(__avword)),\
1137
/* small structures < 1 word are adjusted depending on compiler */
1138
#if defined(__mips__) && !defined(__mipsn32__) && !defined(__mips64__)
1139
#define __av_struct_leftadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1141
(__avword*)(((__avword)(LIST).aptr+(TYPE_SIZE)+(TYPE_ALIGN)-1) & -(long)(TYPE_ALIGN)))\
1143
? -1 : (++(LIST).anum, \
1144
ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((__avword)(LIST).aptr-(TYPE_SIZE)),VAL),\
1145
(LIST).aptr = (__avword*)(((__avword)(LIST).aptr+sizeof(__avword)-1) & -(long)sizeof(__avword)),\
1147
#define __av_struct_rightadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1149
(__avword*)(((((__avword)(LIST).aptr+(TYPE_SIZE)+(TYPE_ALIGN)-1) & -(long)(TYPE_ALIGN))\
1150
+sizeof(__avword)-1) & -(long)sizeof(__avword))) \
1152
? -1 : (++(LIST).anum, \
1153
ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((__avword)(LIST).aptr-(TYPE_SIZE)),VAL),\
1155
#define __av_struct(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1156
((LIST).flags & __AV_SGICC_STRUCT_ARGS \
1157
? /* SGI MIPS cc passes small structures left-adjusted, although big-endian! */\
1158
__av_struct_leftadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1159
: /* SGI MIPS gcc passes small structures within the first four words left- \
1160
* adjusted, for compatibility with cc. But structures in memory are passed \
1161
* right-adjusted!! See gcc-2.6.3/config/mips/mips.c:function_arg(). \
1163
((LIST).aptr < &(LIST).args[4] \
1164
? __av_struct_leftadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1165
: __av_struct_rightadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL)))
1167
#if defined(__mipsn32__) || defined(__mips64__)
1168
/* When a structure is passed (partially) in registers, it is passed in the
1169
* integer registers, except that doubles within the structure are passed in
1170
* the floating point registers. Instead of distinguishing these cases, we
1171
* always pass the structure in both the integer and the floating point
1174
#define __av_struct_leftadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1176
(__avword*)(((__avword)(LIST).aptr+(TYPE_SIZE)+(TYPE_ALIGN)-1) & -(long)(TYPE_ALIGN)))\
1178
? -1 : (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((__avword)(LIST).aptr-(TYPE_SIZE)),VAL),\
1179
(LIST).aptr = (__avword*)(((__avword)(LIST).aptr+sizeof(__avword)-1) & -(long)sizeof(__avword)),\
1180
((LIST).anum < 8 && ((LIST).darg_mask |= (-1 << (LIST).anum))), \
1181
(LIST).anum += (((((TYPE_SIZE)+(TYPE_ALIGN)-1) & -(long)(TYPE_ALIGN)) + sizeof(__avword)-1) & -(long)sizeof(__avword))/sizeof(__avword),\
1182
(LIST).darg_mask &= (1 << ((LIST).anum < 8 ? (LIST).anum : 8)) - 1, \
1184
#define __av_struct_rightadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1186
(__avword*)(((((__avword)(LIST).aptr+(TYPE_SIZE)+(TYPE_ALIGN)-1) & -(long)(TYPE_ALIGN))\
1187
+sizeof(__avword)-1) & -(long)sizeof(__avword))) \
1189
? -1 : (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((__avword)(LIST).aptr-(TYPE_SIZE)),VAL),\
1190
((LIST).anum < 8 && ((LIST).darg_mask |= (-1 << (LIST).anum))), \
1191
(LIST).anum += (((((TYPE_SIZE)+(TYPE_ALIGN)-1) & -(long)(TYPE_ALIGN)) + sizeof(__avword)-1) & -(long)sizeof(__avword))/sizeof(__avword),\
1192
(LIST).darg_mask &= (1 << ((LIST).anum < 8 ? (LIST).anum : 8)) - 1, \
1194
#define __av_struct(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1195
((LIST).flags & __AV_SGICC_STRUCT_ARGS \
1196
? /* SGI MIPS cc passes small structures left-adjusted, although big-endian! */\
1197
__av_struct_leftadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1198
: /* SGI MIPS gcc passes small structures right-adjusted. */ \
1199
__av_struct_rightadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL))
1201
#if defined(__powerpc__) || defined(__powerpc64__)
1202
#define __av_struct_leftadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL)\
1204
(__avword*)(((__avword)(LIST).aptr+(TYPE_SIZE)+(TYPE_ALIGN)-1) & -(long)(TYPE_ALIGN)))\
1206
? -1 : (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((__avword)(LIST).aptr-(TYPE_SIZE)),VAL),\
1207
(LIST).aptr = (__avword*)(((__avword)(LIST).aptr+sizeof(__avword)-1) & -(long)sizeof(__avword)),\
1209
#define __av_struct_rightadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL)\
1211
(__avword*)(((((__avword)(LIST).aptr+(TYPE_SIZE)+(TYPE_ALIGN)-1) & -(long)(TYPE_ALIGN))\
1212
+sizeof(__avword)-1) & -(long)sizeof(__avword))) \
1214
? -1 : (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((__avword)(LIST).aptr-(TYPE_SIZE)),VAL),\
1216
#if !defined(__powerpc64__)
1217
#define __av_struct(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1218
((LIST).flags & __AV_AIXCC_STRUCT_ARGS \
1219
? /* AIX cc and xlc pass small structures left-adjusted, although big-endian! */\
1220
__av_struct_leftadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1221
: /* gcc passes small structures right-adjusted. */ \
1222
__av_struct_rightadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL))
1224
#if defined(__powerpc64__)
1225
#define __av_struct(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1226
__av_struct_rightadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL)
1229
#if defined(__s390__)
1230
#define __av_struct_rightadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL)\
1232
(__avword*)(((((__avword)(LIST).aptr+(TYPE_SIZE)+(TYPE_ALIGN)-1) & -(long)(TYPE_ALIGN))\
1233
+sizeof(__avword)-1) & -(long)sizeof(__avword))) \
1235
? -1 : (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((__avword)(LIST).aptr-(TYPE_SIZE)),VAL),\
1237
#define __av_struct(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1238
((TYPE_SIZE) != 1 && (TYPE_SIZE) != 2 && (TYPE_SIZE) != 4 && (TYPE_SIZE) != 8 \
1240
> ((LIST).eptr = (__avword*)((long)(LIST).eptr - (((TYPE_SIZE)+7)&-8)))\
1242
(ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)(LIST).eptr,VAL), \
1243
(LIST).aptr[-1] = (__avword)(LIST).eptr, \
1245
: (((TYPE_SIZE) == 8 && (LIST).aptr - (LIST).args - (LIST).fargwords == 4 ? ++(LIST).aptr,0 : 0), \
1246
__av_struct_rightadjusted(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL)))
1248
/* big endian -> small structures < 1 word are adjusted to the right */
1249
#if defined(__m88k__)
1250
#define __av_struct(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1252
(__avword*)(((((__avword)(LIST).aptr+(TYPE_SIZE)+(TYPE_ALIGN)-1) & -(long)(TYPE_ALIGN))\
1253
+sizeof(__avword)-1) & -(long)sizeof(__avword))) \
1255
? -1 : (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((__avword)(LIST).aptr-(TYPE_SIZE)),VAL),\
1259
#if defined(__m68k__) || defined(__arm__) || defined(__convex__)
1260
/* Structures are passed as embedded copies on the arg stack.
1262
#define __av_struct(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1263
(((LIST).aptr = (__avword*)(((long)(LIST).aptr+(TYPE_SIZE)+sizeof(__avword)-1) & -(long)sizeof(__avword))) \
1265
? -1 : (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((__avword)(LIST).aptr-(TYPE_SIZE)),VAL),\
1268
#if (defined(__sparc__) && !defined(__sparc64__)) || (defined(__powerpc__) && !defined(__powerpc64__) && !(defined(_AIX) || (defined(__MACH__) && defined(__APPLE__))))
1269
/* Structures are passed as pointers to caller-made local copies. We
1270
* grab space for the copies from the end of the argument list space
1271
* and always use maximal (double) alignment.
1273
#define __av_struct(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1275
> ((LIST).eptr = (__avword*)((long)(LIST).eptr - (((TYPE_SIZE)+7)&-8)))\
1277
(ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)(LIST).eptr,VAL), \
1278
(LIST).aptr[-1] = (__avword)(LIST).eptr, \
1281
#if defined(__sparc64__)
1282
/* Structures <= 16 bytes are passed as embedded copies on the arg stack,
1283
* left-adjusted (although big-endian!).
1284
* When a structure is passed (partially) in registers, it is passed in the
1285
* integer registers, except that floats and doubles within the structure
1286
* are passed in the floating point registers. Instead of distinguishing
1287
* these cases, we always pass the structure in both the integer and the
1288
* floating point registers.
1289
* Big structures are passed as pointers to caller-made local copies.
1290
* FIXME: Shouldn't (LIST).anum be incremented in sync with (LIST).aptr ?
1292
#define __av_struct(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1295
> ((LIST).eptr = (__avword*)((long)(LIST).eptr - (((TYPE_SIZE)+7)&-8)))\
1297
(ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)(LIST).eptr,VAL), \
1298
(LIST).aptr[-1] = (__avword)(LIST).eptr, \
1301
(__avword*)(((__avword)(LIST).aptr+(TYPE_SIZE)+(TYPE_ALIGN)-1) & -(long)(TYPE_ALIGN)))\
1303
? -1 : (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((__avword)(LIST).aptr-(TYPE_SIZE)),VAL),\
1304
(LIST).aptr = (__avword*)(((__avword)(LIST).aptr+sizeof(__avword)-1) & -(long)sizeof(__avword)),\
1306
&& ((LIST).farg_mask |= (-1 << (LIST).anum), \
1307
(LIST).darg_mask |= (-1 << (LIST).anum))), \
1308
(LIST).anum += (((((TYPE_SIZE)+(TYPE_ALIGN)-1) & -(long)(TYPE_ALIGN)) + sizeof(__avword)-1) & -(long)sizeof(__avword))/sizeof(__avword),\
1309
(LIST).farg_mask &= (1 << ((LIST).anum < 16 ? (LIST).anum : 16)) - 1, \
1310
(LIST).darg_mask &= (1 << ((LIST).anum < 16 ? (LIST).anum : 16)) - 1, \
1313
#if defined(__hppa__)
1314
/* Structures <= 8 bytes are passed as embedded copies on the arg stack.
1315
* Big structures are passed as pointers to caller-made local copies.
1317
#define __av_struct(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1320
< ((LIST).eptr = (__avword*)((long)(LIST).eptr + (((TYPE_SIZE) + 7) & -8))) \
1322
: (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((long)(LIST).eptr - (((TYPE_SIZE) + 7) & -8)), VAL), \
1323
*(LIST).aptr = (__avword)((long)(LIST).eptr - (((TYPE_SIZE) + 7) & -8)), \
1325
: ((TYPE_SIZE) > 4 \
1326
? (((LIST).aptr = (__avword*)((((long)(LIST).aptr & -8) - (long)(TYPE_SIZE)) & -8)) \
1328
? -1 : (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)(LIST).aptr,VAL), 0)) \
1329
: /* FIXME: gcc-2.6.3 passes structures <= 4 bytes in memory left-adjusted! ?? */\
1330
(((LIST).aptr = (__avword*)(((long)(LIST).aptr & -4) - (long)(TYPE_SIZE))) \
1332
? -1 : (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)(LIST).aptr,VAL), \
1333
(LIST).aptr = (__avword*)((long)(LIST).aptr & -4), \
1336
#if defined(__x86_64__)
1337
/* Structures <= 16 bytes can be passed in integer or floating-point registers
1338
if there is enough room for the whole number of words needed by the structure
1339
in the corresponding iargs/fargs block. We can't distinguish the two cases
1340
and support only passing in integer registers. Other structures are passed
1341
on the arg stack. */
1342
#define __av_struct(LIST,TYPE,TYPE_SIZE,TYPE_ALIGN,ASSIGN,VAL) \
1343
((LIST).iaptr + ((TYPE_SIZE) + sizeof(__avword)-1) / sizeof(__avword) <= &(LIST).iargs[6] \
1344
? (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)(LIST).iaptr,VAL), \
1345
(LIST).iaptr += ((TYPE_SIZE) + sizeof(__avword)-1) / sizeof(__avword), \
1347
: ((LIST).aptr = (__avword*)((__avword)(LIST).aptr + (((TYPE_SIZE)+__av_struct_alignment(TYPE_ALIGN)-1) & -(long)__av_struct_alignment(TYPE_ALIGN))), \
1348
((LIST).aptr > __av_eptr(LIST) \
1349
? -1 : (ASSIGN(TYPE,TYPE_SIZE,TYPE_ALIGN,(void*)((__avword)(LIST).aptr - (((TYPE_SIZE)+__av_struct_alignment(TYPE_ALIGN)-1) & -(long)__av_struct_alignment(TYPE_ALIGN))),VAL),\
1354
* calling the function
1357
#define av_call(LIST) __builtin_avcall(&(LIST))
1359
/* Determine whether a struct type is word-splittable, i.e. whether each of
1360
* its components fit into a register.
1361
* The entire computation is done at compile time.
1363
#define av_word_splittable_1(slot1) \
1364
(__av_offset1(slot1)/sizeof(__avword) == (__av_offset1(slot1)+sizeof(slot1)-1)/sizeof(__avword))
1365
#define av_word_splittable_2(slot1,slot2) \
1366
((__av_offset1(slot1)/sizeof(__avword) == (__av_offset1(slot1)+sizeof(slot1)-1)/sizeof(__avword)) \
1367
&& (__av_offset2(slot1,slot2)/sizeof(__avword) == (__av_offset2(slot1,slot2)+sizeof(slot2)-1)/sizeof(__avword)) \
1369
#define av_word_splittable_3(slot1,slot2,slot3) \
1370
((__av_offset1(slot1)/sizeof(__avword) == (__av_offset1(slot1)+sizeof(slot1)-1)/sizeof(__avword)) \
1371
&& (__av_offset2(slot1,slot2)/sizeof(__avword) == (__av_offset2(slot1,slot2)+sizeof(slot2)-1)/sizeof(__avword)) \
1372
&& (__av_offset3(slot1,slot2,slot3)/sizeof(__avword) == (__av_offset3(slot1,slot2,slot3)+sizeof(slot3)-1)/sizeof(__avword)) \
1374
#define av_word_splittable_4(slot1,slot2,slot3,slot4) \
1375
((__av_offset1(slot1)/sizeof(__avword) == (__av_offset1(slot1)+sizeof(slot1)-1)/sizeof(__avword)) \
1376
&& (__av_offset2(slot1,slot2)/sizeof(__avword) == (__av_offset2(slot1,slot2)+sizeof(slot2)-1)/sizeof(__avword)) \
1377
&& (__av_offset3(slot1,slot2,slot3)/sizeof(__avword) == (__av_offset3(slot1,slot2,slot3)+sizeof(slot3)-1)/sizeof(__avword)) \
1378
&& (__av_offset4(slot1,slot2,slot3,slot4)/sizeof(__avword) == (__av_offset4(slot1,slot2,slot3,slot4)+sizeof(slot4)-1)/sizeof(__avword)) \
1380
#define __av_offset1(slot1) \
1382
#define __av_offset2(slot1,slot2) \
1383
((__av_offset1(slot1)+sizeof(slot1)+__AV_alignof(slot2)-1) & -(long)__AV_alignof(slot2))
1384
#define __av_offset3(slot1,slot2,slot3) \
1385
((__av_offset2(slot1,slot2)+sizeof(slot2)+__AV_alignof(slot3)-1) & -(long)__AV_alignof(slot3))
1386
#define __av_offset4(slot1,slot2,slot3,slot4) \
1387
((__av_offset3(slot1,slot2,slot3)+sizeof(slot3)+__AV_alignof(slot4)-1) & -(long)__AV_alignof(slot4))
1390
* Miscellaneous declarations.
1393
extern int __builtin_avcall (av_alist* l);
1394
extern void __structcpy (void* dest, const void* src, unsigned long size, unsigned long alignment);
1396
#endif /*_avcall_h */