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