⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 strtod.c

📁 Axis 221 camera embedded programing interface
💻 C
📖 第 1 页 / 共 2 页
字号:
/*  Copyright (C) 2000, 2003     Manuel Novoa III * *  This library is free software; you can redistribute it and/or *  modify it under the terms of the GNU Library General Public *  License as published by the Free Software Foundation; either *  version 2 of the License, or (at your option) any later version. * *  This library is distributed in the hope that it will be useful, *  but WITHOUT ANY WARRANTY; without even the implied warranty of *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU *  Library General Public License for more details. * *  You should have received a copy of the GNU Library General Public *  License along with this library; if not, write to the Free *  Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. *//* Notes: * * The primary objective of this implementation was minimal size and * portablility, while providing robustness and resonable accuracy. * * This implementation depends on IEEE floating point behavior and expects * to be able to generate +/- infinity as a result. * * There are a number of compile-time options below. *//* July 27, 2003 * * General cleanup and some minor size optimizations. * Change implementation to support __strtofpmax() rather than strtod(). *   Now all the strto{floating pt}() funcs are implemented in terms of *   of the internal __strtofpmax() function. * Support "nan", "inf", and "infinity" strings (case-insensitive). * Support hexadecimal floating point notation. * Support wchar variants. * Support xlocale variants. * * TODO: * * Consider accumulating blocks of digits in longs to save floating pt mults. *   This would likely be much better on anything that only supported floats *   where DECIMAL_DIG == 9.  Actually, if floats have FLT_MAX_10_EXP == 38, *   we could calculate almost all the exponent multipliers (p_base) in *   long arithmetic as well. *//**********************************************************************//*							OPTIONS									  *//**********************************************************************//* Defined if we want to recognize "nan", "inf", and "infinity". (C99) */#define _STRTOD_NAN_INF_STRINGS  1/* Defined if we want support hexadecimal floating point notation. (C99) *//* Note!  Now controlled by uClibc configuration.  See below. */#define _STRTOD_HEXADECIMAL_FLOATS 1/* Defined if we want to scale with a O(log2(exp)) multiplications. * This is generally a good thing to do unless you are really tight * on space and do not expect to convert values of large magnitude. */#define _STRTOD_LOG_SCALING	  1/* WARNING!!!   WARNING!!!   WARNING!!!   WARNING!!!   WARNING!!! * * Clearing any of the options below this point is not advised (or tested). * * WARNING!!!   WARNING!!!   WARNING!!!   WARNING!!!   WARNING!!! *//* Defined if we want strtod to set errno appropriately. *//* NOTE: Implies all options below. */#define _STRTOD_ERRNO			1/* Defined if we want support for the endptr arg. *//* Implied by _STRTOD_ERRNO. */#define _STRTOD_ENDPTR		   1/* Defined if we want to prevent overflow in accumulating the exponent. *//* Implied by _STRTOD_ERRNO. */#define _STRTOD_RESTRICT_EXP	 1/* Defined if we want to process mantissa digits more intelligently. *//* Implied by _STRTOD_ERRNO. */#define _STRTOD_RESTRICT_DIGITS  1/* Defined if we want to skip scaling 0 for the exponent. *//* Implied by _STRTOD_ERRNO. */#define _STRTOD_ZERO_CHECK	   1/**********************************************************************//* Don't change anything that follows.									   *//**********************************************************************/#ifdef _STRTOD_ERRNO#undef _STRTOD_ENDPTR#undef _STRTOD_RESTRICT_EXP#undef _STRTOD_RESTRICT_DIGITS#undef _STRTOD_ZERO_CHECK#define _STRTOD_ENDPTR		   1#define _STRTOD_RESTRICT_EXP	 1#define _STRTOD_RESTRICT_DIGITS  1#define _STRTOD_ZERO_CHECK	   1#endif/**********************************************************************/#define _ISOC99_SOURCE 1#define _GNU_SOURCE#include <stdlib.h>#include <string.h>#include <ctype.h>#include <errno.h>#include <limits.h>#include <float.h>#include <bits/uClibc_fpmax.h>#include <locale.h>#ifdef __UCLIBC_HAS_WCHAR__#include <wchar.h>#include <wctype.h>#include <bits/uClibc_uwchar.h>#endif#ifdef __UCLIBC_HAS_XLOCALE__#include <xlocale.h>#endif /* __UCLIBC_HAS_XLOCALE__ *//* Handle _STRTOD_HEXADECIMAL_FLOATS via uClibc config now. */#undef _STRTOD_HEXADECIMAL_FLOATS#ifdef __UCLIBC_HAS_HEXADECIMAL_FLOATS__#define _STRTOD_HEXADECIMAL_FLOATS 1#endif /* __UCLIBC_HAS_HEXADECIMAL_FLOATS__ *//**********************************************************************/#undef _STRTOD_FPMAX#if FPMAX_TYPE == 3#define NEED_STRTOLD_WRAPPER#define NEED_STRTOD_WRAPPER#define NEED_STRTOF_WRAPPER#elif FPMAX_TYPE == 2#define NEED_STRTOD_WRAPPER#define NEED_STRTOF_WRAPPER#elif FPMAX_TYPE == 1#define NEED_STRTOF_WRAPPER#else#error unknown FPMAX_TYPE!#endifextern void __fp_range_check(__fpmax_t y, __fpmax_t x);/**********************************************************************/#ifdef _STRTOD_RESTRICT_DIGITS#define EXP_DENORM_ADJUST DECIMAL_DIG#define MAX_ALLOWED_EXP (DECIMAL_DIG  + EXP_DENORM_ADJUST - FPMAX_MIN_10_EXP)#if MAX_ALLOWED_EXP > INT_MAX#error size assumption violated for MAX_ALLOWED_EXP#endif#else/* We want some excess if we're not restricting mantissa digits. */#define MAX_ALLOWED_EXP ((20 - FPMAX_MIN_10_EXP) * 2)#endif#if defined(_STRTOD_RESTRICT_DIGITS) || defined(_STRTOD_ENDPTR) || defined(_STRTOD_HEXADECIMAL_FLOATS)#undef _STRTOD_NEED_NUM_DIGITS#define _STRTOD_NEED_NUM_DIGITS 1#endif/**********************************************************************/#if defined(L___strtofpmax) || defined(L___strtofpmax_l) || defined(L___wcstofpmax) || defined(L___wcstofpmax_l)#if defined(L___wcstofpmax) || defined(L___wcstofpmax_l)#define __strtofpmax    __wcstofpmax#define __strtofpmax_l  __wcstofpmax_l#define Wchar wchar_t#ifdef __UCLIBC_DO_XLOCALE#define ISSPACE(C) iswspace_l((C), locale_arg)#else#define ISSPACE(C) iswspace((C))#endif#else  /* defined(L___wcstofpmax) || defined(L___wcstofpmax) */#define Wchar char#ifdef __UCLIBC_DO_XLOCALE#define ISSPACE(C) isspace_l((C), locale_arg)#else#define ISSPACE(C) isspace((C))#endif#endif /* defined(L___wcstofpmax) || defined(L___wcstofpmax) */#if defined(__UCLIBC_HAS_XLOCALE__) && !defined(__UCLIBC_DO_XLOCALE)__fpmax_t __strtofpmax(const Wchar *str, Wchar **endptr, int exponent_power){	return __strtofpmax_l(str, endptr, exponent_power, __UCLIBC_CURLOCALE);}#else  /* defined(__UCLIBC_HAS_XLOCALE__) && !defined(__UCLIBC_DO_XLOCALE) */__fpmax_t __XL_NPP(__strtofpmax)(const Wchar *str, Wchar **endptr, int exponent_power								 __LOCALE_PARAM ){	__fpmax_t number;	__fpmax_t p_base = 10;			/* Adjusted to 16 in the hex case. */	Wchar *pos0;#ifdef _STRTOD_ENDPTR	Wchar *pos1;#endif	Wchar *pos = (Wchar *) str;	int exponent_temp;	int negative; /* A flag for the number, a multiplier for the exponent. */#ifdef _STRTOD_NEED_NUM_DIGITS	int num_digits;#endif#ifdef __UCLIBC_HAS_LOCALE__	const char *decpt = __LOCALE_PTR->decimal_point;#if defined(L___wcstofpmax) || defined(L___wcstofpmax)	wchar_t decpt_wc = __LOCALE_PTR->decimal_point;#else	int decpt_len = __LOCALE_PTR->decimal_point_len;#endif#endif#ifdef _STRTOD_HEXADECIMAL_FLOATS	Wchar expchar = 'e';	Wchar *poshex = NULL;	__uint16_t is_mask = _ISdigit;#define EXPCHAR		expchar#define IS_X_DIGIT(C) __isctype((C), is_mask)#else  /* _STRTOD_HEXADECIMAL_FLOATS */#define EXPCHAR		'e'#define IS_X_DIGIT(C) isdigit((C))#endif /* _STRTOD_HEXADECIMAL_FLOATS */	while (ISSPACE(*pos)) {		/* Skip leading whitespace. */		++pos;	}	negative = 0;	switch(*pos) {				/* Handle optional sign. */		case '-': negative = 1;	/* Fall through to increment position. */		case '+': ++pos;	}#ifdef _STRTOD_HEXADECIMAL_FLOATS	if ((*pos == '0') && (((pos[1])|0x20) == 'x')) {		poshex = ++pos;			/* Save position of 'x' in case no digits */		++pos;					/*   and advance past it.  */		is_mask = _ISxdigit;	/* Used by IS_X_DIGIT. */		expchar = 'p';			/* Adjust exponent char. */		p_base = 16;			/* Adjust base multiplier. */	}#endif	number = 0.;#ifdef _STRTOD_NEED_NUM_DIGITS	num_digits = -1;#endif/* 	exponent_power = 0; */	pos0 = NULL; LOOP:	while (IS_X_DIGIT(*pos)) {	/* Process string of (hex) digits. */#ifdef _STRTOD_RESTRICT_DIGITS		if (num_digits < 0) {	/* First time through? */			++num_digits;		/* We've now seen a digit. */		}		if (num_digits || (*pos != '0')) { /* Had/have nonzero. */			++num_digits;			if (num_digits <= DECIMAL_DIG) { /* Is digit significant? */#ifdef _STRTOD_HEXADECIMAL_FLOATS				number = number * p_base					+ (isdigit(*pos)					   ? (*pos - '0')					   : (((*pos)|0x20) - ('a' - 10)));#else  /* _STRTOD_HEXADECIMAL_FLOATS */				number = number * p_base + (*pos - '0');#endif /* _STRTOD_HEXADECIMAL_FLOATS */			}		}#else  /* _STRTOD_RESTRICT_DIGITS */#ifdef _STRTOD_NEED_NUM_DIGITS		++num_digits;#endif#ifdef _STRTOD_HEXADECIMAL_FLOATS		number = number * p_base			+ (isdigit(*pos)			   ? (*pos - '0')			   : (((*pos)|0x20) - ('a' - 10)));#else  /* _STRTOD_HEXADECIMAL_FLOATS */		number = number * p_base + (*pos - '0');

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -