wmii

git clone git://oldgit.suckless.org/wmii/
Log | Files | Refs | README | LICENSE

charstod.c (1997B)


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