The Go Programming Language

Text file src/lib9/fmt/charstod.c

     1	/*
     2	 * The authors of this software are Rob Pike and Ken Thompson,
     3	 * with contributions from Mike Burrows and Sean Dorward.
     4	 *
     5	 *     Copyright (c) 2002-2006 by Lucent Technologies.
     6	 *     Portions Copyright (c) 2004 Google Inc.
     7	 * 
     8	 * Permission to use, copy, modify, and distribute this software for any
     9	 * purpose without fee is hereby granted, provided that this entire notice
    10	 * is included in all copies of any software which is or includes a copy
    11	 * or modification of this software and in all copies of the supporting
    12	 * documentation for such software.
    13	 * THIS SOFTWARE IS BEING PROVIDED "AS IS", WITHOUT ANY EXPRESS OR IMPLIED
    14	 * WARRANTY.  IN PARTICULAR, NEITHER THE AUTHORS NOR LUCENT TECHNOLOGIES 
    15	 * NOR GOOGLE INC MAKE ANY REPRESENTATION OR WARRANTY OF ANY KIND CONCERNING 
    16	 * THE MERCHANTABILITY OF THIS SOFTWARE OR ITS FITNESS FOR ANY PARTICULAR PURPOSE.
    17	 */
    18	
    19	#include <u.h>
    20	#include <libc.h>
    21	#include "fmtdef.h"
    22	
    23	/*
    24	 * Reads a floating-point number by interpreting successive characters
    25	 * returned by (*f)(vp).  The last call it makes to f terminates the
    26	 * scan, so is not a character in the number.  It may therefore be
    27	 * necessary to back up the input stream up one byte after calling charstod.
    28	 */
    29	
    30	double
    31	fmtcharstod(int(*f)(void*), void *vp)
    32	{
    33		double num, dem;
    34		int neg, eneg, dig, exp, c;
    35	
    36		num = 0;
    37		neg = 0;
    38		dig = 0;
    39		exp = 0;
    40		eneg = 0;
    41	
    42		c = (*f)(vp);
    43		while(c == ' ' || c == '\t')
    44			c = (*f)(vp);
    45		if(c == '-' || c == '+'){
    46			if(c == '-')
    47				neg = 1;
    48			c = (*f)(vp);
    49		}
    50		while(c >= '0' && c <= '9'){
    51			num = num*10 + c-'0';
    52			c = (*f)(vp);
    53		}
    54		if(c == '.')
    55			c = (*f)(vp);
    56		while(c >= '0' && c <= '9'){
    57			num = num*10 + c-'0';
    58			dig++;
    59			c = (*f)(vp);
    60		}
    61		if(c == 'e' || c == 'E'){
    62			c = (*f)(vp);
    63			if(c == '-' || c == '+'){
    64				if(c == '-'){
    65					dig = -dig;
    66					eneg = 1;
    67				}
    68				c = (*f)(vp);
    69			}
    70			while(c >= '0' && c <= '9'){
    71				exp = exp*10 + c-'0';
    72				c = (*f)(vp);
    73			}
    74		}
    75		exp -= dig;
    76		if(exp < 0){
    77			exp = -exp;
    78			eneg = !eneg;
    79		}
    80		dem = __fmtpow10(exp);
    81		if(eneg)
    82			num /= dem;
    83		else
    84			num *= dem;
    85		if(neg)
    86			return -num;
    87		return num;
    88	}

release.r60.3. Except as noted, this content is licensed under a Creative Commons Attribution 3.0 License.