/gcc/testsuite/gcc.target/x86_64/abi/test_passing_structs.c

https://bitbucket.org/pizzafactory/pf-gcc · C · 261 lines · 218 code · 36 blank · 7 comment · 6 complexity · 22f689997d822243ee42202328f4fb16 MD5 · raw file

  1. /* This tests passing of structs. */
  2. #include "defines.h"
  3. #include "args.h"
  4. #include <complex.h>
  5. struct IntegerRegisters iregs;
  6. struct FloatRegisters fregs;
  7. unsigned int num_iregs, num_fregs;
  8. struct int_struct
  9. {
  10. int i;
  11. };
  12. struct long_struct
  13. {
  14. long l;
  15. };
  16. struct long2_struct
  17. {
  18. long l1, l2;
  19. };
  20. struct long3_struct
  21. {
  22. long l1, l2, l3;
  23. };
  24. /* Check that the struct is passed as the individual members in iregs. */
  25. void
  26. check_struct_passing1 (struct int_struct is ATTRIBUTE_UNUSED)
  27. {
  28. check_int_arguments;
  29. }
  30. void
  31. check_struct_passing2 (struct long_struct ls ATTRIBUTE_UNUSED)
  32. {
  33. check_int_arguments;
  34. }
  35. void
  36. check_struct_passing3 (struct long2_struct ls ATTRIBUTE_UNUSED)
  37. {
  38. check_int_arguments;
  39. }
  40. void
  41. check_struct_passing4 (struct long3_struct ls ATTRIBUTE_UNUSED)
  42. {
  43. /* Check the passing on the stack by comparing the address of the
  44. stack elements to the expected place on the stack. */
  45. assert ((unsigned long)&ls.l1 == rsp+8);
  46. assert ((unsigned long)&ls.l2 == rsp+16);
  47. assert ((unsigned long)&ls.l3 == rsp+24);
  48. }
  49. #ifdef CHECK_M64_M128
  50. struct m128_struct
  51. {
  52. __m128 x;
  53. };
  54. struct m128_2_struct
  55. {
  56. __m128 x1, x2;
  57. };
  58. /* Check that the struct is passed as the individual members in fregs. */
  59. void
  60. check_struct_passing5 (struct m128_struct ms1 ATTRIBUTE_UNUSED,
  61. struct m128_struct ms2 ATTRIBUTE_UNUSED,
  62. struct m128_struct ms3 ATTRIBUTE_UNUSED,
  63. struct m128_struct ms4 ATTRIBUTE_UNUSED,
  64. struct m128_struct ms5 ATTRIBUTE_UNUSED,
  65. struct m128_struct ms6 ATTRIBUTE_UNUSED,
  66. struct m128_struct ms7 ATTRIBUTE_UNUSED,
  67. struct m128_struct ms8 ATTRIBUTE_UNUSED)
  68. {
  69. check_m128_arguments;
  70. }
  71. void
  72. check_struct_passing6 (struct m128_2_struct ms ATTRIBUTE_UNUSED)
  73. {
  74. /* Check the passing on the stack by comparing the address of the
  75. stack elements to the expected place on the stack. */
  76. assert ((unsigned long)&ms.x1 == rsp+8);
  77. assert ((unsigned long)&ms.x2 == rsp+24);
  78. }
  79. #endif
  80. struct flex1_struct
  81. {
  82. long i;
  83. long flex[];
  84. };
  85. struct flex2_struct
  86. {
  87. long i;
  88. long flex[0];
  89. };
  90. void
  91. check_struct_passing7 (struct flex1_struct is ATTRIBUTE_UNUSED)
  92. {
  93. check_int_arguments;
  94. }
  95. void
  96. check_struct_passing8 (struct flex2_struct is ATTRIBUTE_UNUSED)
  97. {
  98. check_int_arguments;
  99. }
  100. struct complex1_struct
  101. {
  102. int c;
  103. __complex__ float x;
  104. };
  105. struct complex1a_struct
  106. {
  107. long l;
  108. float f;
  109. };
  110. struct complex2_struct
  111. {
  112. int c;
  113. __complex__ float x;
  114. float y;
  115. };
  116. struct complex2a_struct
  117. {
  118. long l;
  119. double d;
  120. };
  121. void
  122. check_struct_passing9 (struct complex1_struct is ATTRIBUTE_UNUSED)
  123. {
  124. check_int_arguments;
  125. check_float_arguments;
  126. }
  127. void
  128. check_struct_passing10 (struct complex2_struct is ATTRIBUTE_UNUSED)
  129. {
  130. check_int_arguments;
  131. check_double_arguments;
  132. }
  133. static struct flex1_struct f1s = { 60, { } };
  134. static struct flex2_struct f2s = { 61, { } };
  135. int
  136. main (void)
  137. {
  138. struct int_struct is = { 48 };
  139. struct long_struct ls = { 49 };
  140. #ifdef CHECK_LARGER_STRUCTS
  141. struct long2_struct l2s = { 50, 51 };
  142. struct long3_struct l3s = { 52, 53, 54 };
  143. #endif
  144. #ifdef CHECK_M64_M128
  145. struct m128_struct m128s[8];
  146. struct m128_2_struct m128_2s = {
  147. { 48.394, 39.3, -397.9, 3484.9 },
  148. { -8.394, -93.3, 7.9, 84.94 }
  149. };
  150. int i;
  151. #endif
  152. struct complex1_struct c1s = { 4, ( -13.4 + 3.5*I ) };
  153. union
  154. {
  155. struct complex1_struct c;
  156. struct complex1a_struct u;
  157. } c1u;
  158. struct complex2_struct c2s = { 4, ( -13.4 + 3.5*I ), -34.5 };
  159. union
  160. {
  161. struct complex2_struct c;
  162. struct complex2a_struct u;
  163. } c2u;
  164. clear_struct_registers;
  165. iregs.I0 = is.i;
  166. num_iregs = 1;
  167. clear_int_hardware_registers;
  168. WRAP_CALL (check_struct_passing1)(is);
  169. clear_struct_registers;
  170. iregs.I0 = ls.l;
  171. num_iregs = 1;
  172. clear_int_hardware_registers;
  173. WRAP_CALL (check_struct_passing2)(ls);
  174. #ifdef CHECK_LARGER_STRUCTS
  175. clear_struct_registers;
  176. iregs.I0 = l2s.l1;
  177. iregs.I1 = l2s.l2;
  178. num_iregs = 2;
  179. clear_int_hardware_registers;
  180. WRAP_CALL (check_struct_passing3)(l2s);
  181. WRAP_CALL (check_struct_passing4)(l3s);
  182. #endif
  183. #ifdef CHECK_M64_M128
  184. clear_struct_registers;
  185. for (i = 0; i < 8; i++)
  186. {
  187. m128s[i].x = (__m128){32+i, 0, i, 0};
  188. fregs.xmm0._m128[i] = m128s[i].x;
  189. }
  190. num_fregs = 8;
  191. clear_float_hardware_registers;
  192. WRAP_CALL (check_struct_passing5)(m128s[0], m128s[1], m128s[2], m128s[3],
  193. m128s[4], m128s[5], m128s[6], m128s[7]);
  194. WRAP_CALL (check_struct_passing6)(m128_2s);
  195. #endif
  196. clear_struct_registers;
  197. iregs.I0 = f1s.i;
  198. num_iregs = 1;
  199. clear_int_hardware_registers;
  200. WRAP_CALL (check_struct_passing7)(f1s);
  201. clear_struct_registers;
  202. iregs.I0 = f2s.i;
  203. num_iregs = 1;
  204. clear_int_hardware_registers;
  205. WRAP_CALL (check_struct_passing8)(f2s);
  206. clear_struct_registers;
  207. c1u.c = c1s;
  208. iregs.I0 = c1u.u.l;
  209. num_iregs = 1;
  210. fregs.xmm0._float [0] = c1u.u.f;
  211. num_fregs = 1;
  212. clear_int_hardware_registers;
  213. clear_float_hardware_registers;
  214. WRAP_CALL (check_struct_passing9)(c1s);
  215. clear_struct_registers;
  216. c2u.c = c2s;
  217. iregs.I0 = c2u.u.l;
  218. num_iregs = 1;
  219. fregs.xmm0._double[0] = c2u.u.d;
  220. num_fregs = 1;
  221. clear_int_hardware_registers;
  222. clear_float_hardware_registers;
  223. WRAP_CALL (check_struct_passing10)(c2s);
  224. return 0;
  225. }