asin.c 1.3 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283
  1. /*
  2. * (c) copyright 1988 by the Vrije Universiteit, Amsterdam, The Netherlands.
  3. * See the copyright notice in the ACK home directory, in the file "Copyright".
  4. *
  5. * Author: Ceriel J.H. Jacobs
  6. */
  7. /* $Id$ */
  8. #include <math.h>
  9. #include <errno.h>
  10. extern int errno;
  11. static double
  12. asin_acos(x, cosfl)
  13. double x;
  14. {
  15. int negative = x < 0;
  16. int i;
  17. double g;
  18. extern double sqrt();
  19. static double p[] = {
  20. -0.27368494524164255994e+2,
  21. 0.57208227877891731407e+2,
  22. -0.39688862997540877339e+2,
  23. 0.10152522233806463645e+2,
  24. -0.69674573447350646411e+0
  25. };
  26. static double q[] = {
  27. -0.16421096714498560795e+3,
  28. 0.41714430248260412556e+3,
  29. -0.38186303361750149284e+3,
  30. 0.15095270841030604719e+3,
  31. -0.23823859153670238830e+2,
  32. 1.0
  33. };
  34. if (negative) {
  35. x = -x;
  36. }
  37. if (x > 0.5) {
  38. i = 1;
  39. if (x > 1) {
  40. errno = EDOM;
  41. return 0;
  42. }
  43. g = 0.5 - 0.5 * x;
  44. x = - sqrt(g);
  45. x += x;
  46. }
  47. else {
  48. /* ??? avoid underflow ??? */
  49. i = 0;
  50. g = x * x;
  51. }
  52. x += x * g * POLYNOM4(g, p) / POLYNOM5(g, q);
  53. if (cosfl) {
  54. if (! negative) x = -x;
  55. }
  56. if ((cosfl == 0) == (i == 1)) {
  57. x = (x + M_PI_4) + M_PI_4;
  58. }
  59. else if (cosfl && negative && i == 1) {
  60. x = (x + M_PI_2) + M_PI_2;
  61. }
  62. if (! cosfl && negative) x = -x;
  63. return x;
  64. }
  65. double
  66. asin(x)
  67. double x;
  68. {
  69. return asin_acos(x, 0);
  70. }
  71. double
  72. acos(x)
  73. double x;
  74. {
  75. return asin_acos(x, 1);
  76. }