/test/builtins/Unit/divtc3_test.c

https://gitlab.com/drgroovestarr/external_compiler-rt · C · 374 lines · 329 code · 29 blank · 16 comment · 72 complexity · aaa2b0109ce9ff39d04da69897756015 MD5 · raw file

  1. //===-- divtc3_test.c - Test __divtc3 -------------------------------------===//
  2. //
  3. // The LLVM Compiler Infrastructure
  4. //
  5. // This file is dual licensed under the MIT and the University of Illinois Open
  6. // Source Licenses. See LICENSE.TXT for details.
  7. //
  8. //===----------------------------------------------------------------------===//
  9. //
  10. // This file tests __divtc3 for the compiler_rt library.
  11. //
  12. //===----------------------------------------------------------------------===//
  13. #include <stdio.h>
  14. #include "int_lib.h"
  15. #include <math.h>
  16. #include <complex.h>
  17. // Returns: the quotient of (a + ib) / (c + id)
  18. COMPILER_RT_ABI long double _Complex
  19. __divtc3(long double __a, long double __b, long double __c, long double __d);
  20. enum {zero, non_zero, inf, NaN, non_zero_nan};
  21. int
  22. classify(long double _Complex x)
  23. {
  24. if (x == 0)
  25. return zero;
  26. if (isinf(creall(x)) || isinf(cimagl(x)))
  27. return inf;
  28. if (isnan(creall(x)) && isnan(cimagl(x)))
  29. return NaN;
  30. if (isnan(creall(x)))
  31. {
  32. if (cimagl(x) == 0)
  33. return NaN;
  34. return non_zero_nan;
  35. }
  36. if (isnan(cimagl(x)))
  37. {
  38. if (creall(x) == 0)
  39. return NaN;
  40. return non_zero_nan;
  41. }
  42. return non_zero;
  43. }
  44. int test__divtc3(long double a, long double b, long double c, long double d)
  45. {
  46. long double _Complex r = __divtc3(a, b, c, d);
  47. // printf("test__divtc3(%Lf, %Lf, %Lf, %Lf) = %Lf + I%Lf\n",
  48. // a, b, c, d, creall(r), cimagl(r));
  49. long double _Complex dividend;
  50. long double _Complex divisor;
  51. __real__ dividend = a;
  52. __imag__ dividend = b;
  53. __real__ divisor = c;
  54. __imag__ divisor = d;
  55. switch (classify(dividend))
  56. {
  57. case zero:
  58. switch (classify(divisor))
  59. {
  60. case zero:
  61. if (classify(r) != NaN)
  62. return 1;
  63. break;
  64. case non_zero:
  65. if (classify(r) != zero)
  66. return 1;
  67. break;
  68. case inf:
  69. if (classify(r) != zero)
  70. return 1;
  71. break;
  72. case NaN:
  73. if (classify(r) != NaN)
  74. return 1;
  75. break;
  76. case non_zero_nan:
  77. if (classify(r) != NaN)
  78. return 1;
  79. break;
  80. }
  81. break;
  82. case non_zero:
  83. switch (classify(divisor))
  84. {
  85. case zero:
  86. if (classify(r) != inf)
  87. return 1;
  88. break;
  89. case non_zero:
  90. if (classify(r) != non_zero)
  91. return 1;
  92. {
  93. long double _Complex z = (a * c + b * d) / (c * c + d * d)
  94. + (b * c - a * d) / (c * c + d * d) * _Complex_I;
  95. if (cabsl((r - z)/r) > 1.e-6)
  96. return 1;
  97. }
  98. break;
  99. case inf:
  100. if (classify(r) != zero)
  101. return 1;
  102. break;
  103. case NaN:
  104. if (classify(r) != NaN)
  105. return 1;
  106. break;
  107. case non_zero_nan:
  108. if (classify(r) != NaN)
  109. return 1;
  110. break;
  111. }
  112. break;
  113. case inf:
  114. switch (classify(divisor))
  115. {
  116. case zero:
  117. if (classify(r) != inf)
  118. return 1;
  119. break;
  120. case non_zero:
  121. if (classify(r) != inf)
  122. return 1;
  123. break;
  124. case inf:
  125. if (classify(r) != NaN)
  126. return 1;
  127. break;
  128. case NaN:
  129. if (classify(r) != NaN)
  130. return 1;
  131. break;
  132. case non_zero_nan:
  133. if (classify(r) != NaN)
  134. return 1;
  135. break;
  136. }
  137. break;
  138. case NaN:
  139. switch (classify(divisor))
  140. {
  141. case zero:
  142. if (classify(r) != NaN)
  143. return 1;
  144. break;
  145. case non_zero:
  146. if (classify(r) != NaN)
  147. return 1;
  148. break;
  149. case inf:
  150. if (classify(r) != NaN)
  151. return 1;
  152. break;
  153. case NaN:
  154. if (classify(r) != NaN)
  155. return 1;
  156. break;
  157. case non_zero_nan:
  158. if (classify(r) != NaN)
  159. return 1;
  160. break;
  161. }
  162. break;
  163. case non_zero_nan:
  164. switch (classify(divisor))
  165. {
  166. case zero:
  167. if (classify(r) != inf)
  168. return 1;
  169. break;
  170. case non_zero:
  171. if (classify(r) != NaN)
  172. return 1;
  173. break;
  174. case inf:
  175. if (classify(r) != NaN)
  176. return 1;
  177. break;
  178. case NaN:
  179. if (classify(r) != NaN)
  180. return 1;
  181. break;
  182. case non_zero_nan:
  183. if (classify(r) != NaN)
  184. return 1;
  185. break;
  186. }
  187. break;
  188. }
  189. return 0;
  190. }
  191. long double x[][2] =
  192. {
  193. { 1.e-6, 1.e-6},
  194. {-1.e-6, 1.e-6},
  195. {-1.e-6, -1.e-6},
  196. { 1.e-6, -1.e-6},
  197. { 1.e+6, 1.e-6},
  198. {-1.e+6, 1.e-6},
  199. {-1.e+6, -1.e-6},
  200. { 1.e+6, -1.e-6},
  201. { 1.e-6, 1.e+6},
  202. {-1.e-6, 1.e+6},
  203. {-1.e-6, -1.e+6},
  204. { 1.e-6, -1.e+6},
  205. { 1.e+6, 1.e+6},
  206. {-1.e+6, 1.e+6},
  207. {-1.e+6, -1.e+6},
  208. { 1.e+6, -1.e+6},
  209. {NAN, NAN},
  210. {-INFINITY, NAN},
  211. {-2, NAN},
  212. {-1, NAN},
  213. {-0.5, NAN},
  214. {-0., NAN},
  215. {+0., NAN},
  216. {0.5, NAN},
  217. {1, NAN},
  218. {2, NAN},
  219. {INFINITY, NAN},
  220. {NAN, -INFINITY},
  221. {-INFINITY, -INFINITY},
  222. {-2, -INFINITY},
  223. {-1, -INFINITY},
  224. {-0.5, -INFINITY},
  225. {-0., -INFINITY},
  226. {+0., -INFINITY},
  227. {0.5, -INFINITY},
  228. {1, -INFINITY},
  229. {2, -INFINITY},
  230. {INFINITY, -INFINITY},
  231. {NAN, -2},
  232. {-INFINITY, -2},
  233. {-2, -2},
  234. {-1, -2},
  235. {-0.5, -2},
  236. {-0., -2},
  237. {+0., -2},
  238. {0.5, -2},
  239. {1, -2},
  240. {2, -2},
  241. {INFINITY, -2},
  242. {NAN, -1},
  243. {-INFINITY, -1},
  244. {-2, -1},
  245. {-1, -1},
  246. {-0.5, -1},
  247. {-0., -1},
  248. {+0., -1},
  249. {0.5, -1},
  250. {1, -1},
  251. {2, -1},
  252. {INFINITY, -1},
  253. {NAN, -0.5},
  254. {-INFINITY, -0.5},
  255. {-2, -0.5},
  256. {-1, -0.5},
  257. {-0.5, -0.5},
  258. {-0., -0.5},
  259. {+0., -0.5},
  260. {0.5, -0.5},
  261. {1, -0.5},
  262. {2, -0.5},
  263. {INFINITY, -0.5},
  264. {NAN, -0.},
  265. {-INFINITY, -0.},
  266. {-2, -0.},
  267. {-1, -0.},
  268. {-0.5, -0.},
  269. {-0., -0.},
  270. {+0., -0.},
  271. {0.5, -0.},
  272. {1, -0.},
  273. {2, -0.},
  274. {INFINITY, -0.},
  275. {NAN, 0.},
  276. {-INFINITY, 0.},
  277. {-2, 0.},
  278. {-1, 0.},
  279. {-0.5, 0.},
  280. {-0., 0.},
  281. {+0., 0.},
  282. {0.5, 0.},
  283. {1, 0.},
  284. {2, 0.},
  285. {INFINITY, 0.},
  286. {NAN, 0.5},
  287. {-INFINITY, 0.5},
  288. {-2, 0.5},
  289. {-1, 0.5},
  290. {-0.5, 0.5},
  291. {-0., 0.5},
  292. {+0., 0.5},
  293. {0.5, 0.5},
  294. {1, 0.5},
  295. {2, 0.5},
  296. {INFINITY, 0.5},
  297. {NAN, 1},
  298. {-INFINITY, 1},
  299. {-2, 1},
  300. {-1, 1},
  301. {-0.5, 1},
  302. {-0., 1},
  303. {+0., 1},
  304. {0.5, 1},
  305. {1, 1},
  306. {2, 1},
  307. {INFINITY, 1},
  308. {NAN, 2},
  309. {-INFINITY, 2},
  310. {-2, 2},
  311. {-1, 2},
  312. {-0.5, 2},
  313. {-0., 2},
  314. {+0., 2},
  315. {0.5, 2},
  316. {1, 2},
  317. {2, 2},
  318. {INFINITY, 2},
  319. {NAN, INFINITY},
  320. {-INFINITY, INFINITY},
  321. {-2, INFINITY},
  322. {-1, INFINITY},
  323. {-0.5, INFINITY},
  324. {-0., INFINITY},
  325. {+0., INFINITY},
  326. {0.5, INFINITY},
  327. {1, INFINITY},
  328. {2, INFINITY},
  329. {INFINITY, INFINITY}
  330. };
  331. int main()
  332. {
  333. const unsigned N = sizeof(x) / sizeof(x[0]);
  334. unsigned i, j;
  335. for (i = 0; i < N; ++i)
  336. {
  337. for (j = 0; j < N; ++j)
  338. {
  339. if (test__divtc3(x[i][0], x[i][1], x[j][0], x[j][1]))
  340. return 1;
  341. }
  342. }
  343. // printf("No errors found.\n");
  344. return 0;
  345. }