aboutsummaryrefslogtreecommitdiffstats
path: root/contrib/restricted/libffi/testsuite/libffi.closures/cls_longdouble.c
blob: 2bb92cd8830ef1390ff0bef1e83f4824f10bf188 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
/* Area:		ffi_call, closure_call 
   Purpose:		Check long double arguments. 
   Limitations:	none. 
   PR:			none. 
   Originator:	Blake Chaffin	*/ 
 
/* This test is known to PASS on armv7l-unknown-linux-gnueabihf, so I have 
   remove the xfail for arm*-*-* below, until we know more.  */ 
/* { dg-do run { xfail strongarm*-*-* xscale*-*-* } } */ 
/* { dg-options -mlong-double-128 { target powerpc64*-*-linux* } } */ 
 
#include "ffitest.h" 
 
long double cls_ldouble_fn( 
	long double	a1, 
	long double	a2, 
	long double	a3, 
	long double	a4, 
	long double	a5, 
	long double	a6, 
	long double	a7, 
	long double	a8) 
{ 
	long double	r = a1 + a2 + a3 + a4 + a5 + a6 + a7 + a8; 
 
	printf("%Lg %Lg %Lg %Lg %Lg %Lg %Lg %Lg: %Lg\n", 
		a1, a2, a3, a4, a5, a6, a7, a8, r); 
 
	return r; 
} 
 
static void 
cls_ldouble_gn(ffi_cif* cif __UNUSED__, void* resp,  
	       void** args, void* userdata __UNUSED__) 
{ 
	long double	a1	= *(long double*)args[0]; 
	long double	a2	= *(long double*)args[1]; 
	long double	a3	= *(long double*)args[2]; 
	long double	a4	= *(long double*)args[3]; 
	long double	a5	= *(long double*)args[4]; 
	long double	a6	= *(long double*)args[5]; 
	long double	a7	= *(long double*)args[6]; 
	long double	a8	= *(long double*)args[7]; 
 
	*(long double*)resp = cls_ldouble_fn( 
		a1, a2, a3, a4, a5, a6, a7, a8); 
} 
 
int main(void) 
{ 
	ffi_cif	cif; 
        void* code; 
	ffi_closure*	pcl = ffi_closure_alloc(sizeof(ffi_closure), &code); 
	void*			args[9]; 
	ffi_type*		arg_types[9]; 
	long double		res	= 0; 
 
	long double	arg1	= 1; 
	long double	arg2	= 2; 
	long double	arg3	= 3; 
	long double	arg4	= 4; 
	long double	arg5	= 5; 
	long double	arg6	= 6; 
	long double	arg7	= 7; 
	long double	arg8	= 8; 
 
	arg_types[0] = &ffi_type_longdouble; 
	arg_types[1] = &ffi_type_longdouble; 
	arg_types[2] = &ffi_type_longdouble; 
	arg_types[3] = &ffi_type_longdouble; 
	arg_types[4] = &ffi_type_longdouble; 
	arg_types[5] = &ffi_type_longdouble; 
	arg_types[6] = &ffi_type_longdouble; 
	arg_types[7] = &ffi_type_longdouble; 
	arg_types[8] = NULL; 
 
	CHECK(ffi_prep_cif(&cif, FFI_DEFAULT_ABI, 8, &ffi_type_longdouble, 
		arg_types) == FFI_OK); 
 
	args[0] = &arg1; 
	args[1] = &arg2; 
	args[2] = &arg3; 
	args[3] = &arg4; 
	args[4] = &arg5; 
	args[5] = &arg6; 
	args[6] = &arg7; 
	args[7] = &arg8; 
	args[8] = NULL; 
 
	ffi_call(&cif, FFI_FN(cls_ldouble_fn), &res, args); 
	/* { dg-output "1 2 3 4 5 6 7 8: 36" } */ 
	printf("res: %Lg\n", res); 
	/* { dg-output "\nres: 36" } */ 
 
	CHECK(ffi_prep_closure_loc(pcl, &cif, cls_ldouble_gn, NULL, code) == FFI_OK); 
 
	res = ((long double(*)(long double, long double, long double, long double, 
		long double, long double, long double, long double))(code))(arg1, arg2, 
		arg3, arg4, arg5, arg6, arg7, arg8); 
	/* { dg-output "\n1 2 3 4 5 6 7 8: 36" } */ 
	printf("res: %Lg\n", res); 
	/* { dg-output "\nres: 36" } */ 
 
	return 0; 
}