xref: /csrg-svn/lib/libm/common_source/atanh.c (revision 42657)
134124Sbostic /*
224590Szliu  * Copyright (c) 1985 Regents of the University of California.
334124Sbostic  * All rights reserved.
434124Sbostic  *
5*42657Sbostic  * %sccs.include.redist.c%
634124Sbostic  *
734124Sbostic  * All recipients should regard themselves as participants in an ongoing
834124Sbostic  * research project and hence should feel obligated to report their
934124Sbostic  * experiences (good or bad) with these elementary function codes, using
1034124Sbostic  * the sendbug(8) program, to the authors.
1124590Szliu  */
1224590Szliu 
1324590Szliu #ifndef lint
14*42657Sbostic static char sccsid[] = "@(#)atanh.c	5.5 (Berkeley) 06/01/90";
1534124Sbostic #endif /* not lint */
1624590Szliu 
1724590Szliu /* ATANH(X)
1824590Szliu  * RETURN THE HYPERBOLIC ARC TANGENT OF X
1924590Szliu  * DOUBLE PRECISION (VAX D format 56 bits, IEEE DOUBLE 53 BITS)
2024590Szliu  * CODED IN C BY K.C. NG, 1/8/85;
2124590Szliu  * REVISED BY K.C. NG on 2/7/85, 3/7/85, 8/18/85.
2224590Szliu  *
2324590Szliu  * Required kernel function:
2424590Szliu  *	log1p(x) 	...return log(1+x)
2524590Szliu  *
2624590Szliu  * Method :
2724590Szliu  *	Return
2824590Szliu  *                          1              2x                          x
2924590Szliu  *		atanh(x) = --- * log(1 + -------) = 0.5 * log1p(2 * --------)
3024590Szliu  *                          2             1 - x                      1 - x
3124590Szliu  *
3224590Szliu  * Special cases:
3324590Szliu  *	atanh(x) is NaN if |x| > 1 with signal;
3424590Szliu  *	atanh(NaN) is that NaN with no signal;
3524590Szliu  *	atanh(+-1) is +-INF with signal.
3624590Szliu  *
3724590Szliu  * Accuracy:
3824590Szliu  *	atanh(x) returns the exact hyperbolic arc tangent of x nearly rounded.
3924590Szliu  *	In a test run with 512,000 random arguments on a VAX, the maximum
4024590Szliu  *	observed error was 1.87 ulps (units in the last place) at
4124590Szliu  *	x= -3.8962076028810414000e-03.
4224590Szliu  */
4335679Sbostic #include "mathimpl.h"
4435679Sbostic 
4531853Szliu #if defined(vax)||defined(tahoe)
4624590Szliu #include <errno.h>
4731853Szliu #endif	/* defined(vax)||defined(tahoe) */
4824590Szliu 
4924590Szliu double atanh(x)
5024590Szliu double x;
5124590Szliu {
5235679Sbostic 	double z;
5324590Szliu 	z = copysign(0.5,x);
5424590Szliu 	x = copysign(x,1.0);
5531853Szliu #if defined(vax)||defined(tahoe)
5624590Szliu 	if (x == 1.0) {
5724590Szliu 	    return(copysign(1.0,z)*infnan(ERANGE));	/* sign(x)*INF */
5824590Szliu 	}
5931853Szliu #endif	/* defined(vax)||defined(tahoe) */
6024590Szliu 	x = x/(1.0-x);
6124590Szliu 	return( z*log1p(x+x) );
6224590Szliu }
63