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

📄 vfprintf.c

📁 Axis 221 camera embedded programing interface
💻 C
📖 第 1 页 / 共 4 页
字号:
			}			maxposarg = 0;		/* Possible redundant store, but cuts size. */			if ((fmt > p) && (*p != '0')) {				goto PREC_WIDTH;			}			fmt = p;			/* Back up for possible '0's flag. */			/* Now fall through to check flags. */		}#else  /* NL_ARGMAX */		if (*fmt == '$') {		/* Positional spec. */			return -1;		}		if ((fmt > p) && (*p != '0')) {			goto PREC_WIDTH;		}		fmt = p;			/* Back up for possible '0's flag. */		/* Now fall through to check flags. */#endif /* NL_ARGMAX */	restart_flags:		/* Process flags. */		i = 1;		p = spec_flags;			do {			if (*fmt == *p++) {				++fmt;				flags |= i;				goto restart_flags;			}			i += i;				/* Better than i <<= 1 for bcc */		} while (*p);		i = 0;		/* If '+' then ignore ' ', and if '-' then ignore '0'. */		/* Note: Need to ignore '0' when prec is an arg with val < 0, */		/*       but that test needs to wait until the arg is retrieved. */		flags &= ~((flags & (FLAG_PLUS|FLAG_MINUS)) >> 1);		/* Note: Ignore '0' when prec is specified < 0 too (in printf). */		if (fmt[-1] != '%') {	/* If we've done anything, loop for width. */			goto width_precision;		}	} PREC_WIDTH:	if (*p == '*') {			/* Prec or width takes an arg. */#ifdef NL_ARGMAX		if (maxposarg) {			if ((*fmt++ != '$') || (i <= 0)) {				/* Using pos args and no $ or invalid arg number. */				return -1;			}			argnumber[-dpoint] = i;		} else#endif /* NL_ARGMAX */		if (++p != fmt) {			 /* Not using pos args but digits followed *. */			return -1;		}		i = INT_MIN;	}	if (!dpoint) {		width = i;		if (*fmt == '.') {			++fmt;			dpoint = -1;		/* To use as default precison. */			goto width_precision;		}	} else {		preci = i;	}	/* Process qualifier. */	p = qual_chars;	do {		if (*fmt == *p) {			++fmt;			break;		}	} while (*++p);	if ((p - qual_chars < 2) && (*fmt == *p)) {		p += ((sizeof(qual_chars)-2) / 2);		++fmt;	}	dataargtype = ((int)(p[(sizeof(qual_chars)-2) / 2])) << 8;	/* Process conversion specifier. */	if (!*fmt) {		return -1;	}	p = spec_chars;	do {		if (*fmt == *p) {			p_m_spec_chars = p - spec_chars;			if ((p_m_spec_chars >= CONV_c)				&& (dataargtype & PA_FLAG_LONG)) {				p_m_spec_chars -= 2; /* lc -> C and ls -> S */			}			ppfs->conv_num = p_m_spec_chars;			p = spec_ranges-1;			while (p_m_spec_chars > *++p) {}			i = p - spec_ranges;			argtype[2] = (dataargtype | spec_or_mask[i]) & spec_and_mask[i];			p = spec_chars;			break;		}	} while(*++p);	ppfs->info.spec = *fmt;	ppfs->info.prec = preci;	ppfs->info.width = width;	ppfs->info.pad = ((flags & FLAG_ZERO) ? '0' : ' ');	ppfs->info._flags = (flags & ~FLAG_ZERO) | (dataargtype & __PA_INTMASK);	ppfs->num_data_args = 1;	if (!*p) {#ifdef __UCLIBC_HAS_PRINTF_M_SPEC__		if (*fmt == 'm') {			ppfs->conv_num = CONV_m;			ppfs->num_data_args = 0;			goto DONE;		}#endif#ifdef __UCLIBC_HAS_GLIBC_CUSTOM_PRINTF__		/* Handle custom arg -- WARNING -- overwrites p!!! */		ppfs->conv_num = CONV_custom0;		p = _custom_printf_spec;		do {			if (*p == *fmt) {				if ((ppfs->num_data_args					 = ((*_custom_printf_arginfo[(int)(p-_custom_printf_spec)])						(&(ppfs->info), MAX_ARGS_PER_SPEC, argtype+2)))					> MAX_ARGS_PER_SPEC) {					break;		/* Error -- too many args! */				}				goto DONE;			}		} while (++p < (_custom_printf_spec + MAX_USER_SPEC));#endif /* __UCLIBC_HAS_GLIBC_CUSTOM_PRINTF__ */		/* Otherwise error. */		return -1;	}		#if defined(__UCLIBC_HAS_GLIBC_CUSTOM_PRINTF__) || defined(__UCLIBC_HAS_PRINTF_M_SPEC__) DONE:#endif#ifdef NL_ARGMAX	if (maxposarg > 0) {		i = 0;		do {			/* Update maxposarg and check that NL_ARGMAX is not exceeded. */			n = ((i <= 2)				 ? (ppfs->argnumber[i] = argnumber[i])				 : argnumber[2] + (i-2));			if (n > maxposarg) {				if ((maxposarg = n) > NL_ARGMAX) {					return -1;				}			}			--n;			/* Record argtype with largest size (current, new). */			if (_is_equal_or_bigger_arg(ppfs->argtype[n], argtype[i])) {				ppfs->argtype[n] = argtype[i];			}		} while (++i < ppfs->num_data_args + 2);	} else {#endif /* NL_ARGMAX */		ppfs->argnumber[2] = 1;		memcpy(ppfs->argtype, argtype + 2, ppfs->num_data_args * sizeof(int));#ifdef NL_ARGMAX	}	ppfs->maxposarg = maxposarg;#endif /* NL_ARGMAX */#ifdef __UCLIBC_HAS_WCHAR__	if ((flags = ppfs->info._flags & FLAG_WIDESTREAM) == 0) {		ppfs->fmtpos = ++fmt;	} else {		ppfs->fmtpos = (const char *) (((const wchar_t *)(ppfs->fmtpos))									   + (fmt - buf) );	}#else  /* __UCLIBC_HAS_WCHAR__ */	ppfs->fmtpos = ++fmt;#endif /* __UCLIBC_HAS_WCHAR__ */ 	return ppfs->num_data_args + 2;}#endif/**********************************************************************/#ifdef L_register_printf_function#ifdef __UCLIBC_HAS_GLIBC_CUSTOM_PRINTF__int register_printf_function(int spec, printf_function handler,							 printf_arginfo_function arginfo){	register char *r;	register char *p;	if (spec && (arginfo != NULL)) { /* TODO -- check if spec is valid char */		r = NULL;		p = _custom_printf_spec + MAX_USER_SPEC;		do {			--p;			if (!*p) {				r = p;			}#ifdef __BCC__			else				/* bcc generates less code with fall-through */#endif			if (*p == spec) {				r = p;				p = _custom_printf_spec;			}		} while (p > _custom_printf_spec);		if (r) {			if (handler) {				*r = spec;				_custom_printf_handler[(int)(r - p)] = handler;				_custom_printf_arginfo[(int)(r - p)] = arginfo;			} else {				*r = 0;			}			return 0;		}		/* TODO -- if asked to unregister a non-existent spec, return what? */	}	return -1;}#endif#endif/**********************************************************************/#if defined(L_vfprintf) || defined(L_vfwprintf)/* We only support ascii digits (or their USC equivalent codes) in * precision and width settings in *printf (wide) format strings. * In other words, we don't currently support glibc's 'I' flag. * We do accept it, but it is currently ignored. */static void _charpad(FILE * __restrict stream, int padchar, size_t numpad);#ifdef L_vfprintf#define VFPRINTF vfprintf#define FMT_TYPE char#define OUTNSTR _outnstr#define STRLEN  strlen#define _PPFS_init _ppfs_init#define OUTPUT(F,S)			__fputs_unlocked(S,F)/* #define _outnstr(stream, string, len)	__stdio_fwrite(string, len, stream) */#define _outnstr(stream, string, len)	((len > 0) ? __stdio_fwrite(string, len, stream) : 0)#define FP_OUT _fp_out_narrow#ifdef __STDIO_PRINTF_FLOATstatic void _fp_out_narrow(FILE *fp, intptr_t type, intptr_t len, intptr_t buf){	if (type & 0x80) {			/* Some type of padding needed. */		int buflen = strlen((const char *) buf);		if ((len -= buflen) > 0) {			_charpad(fp, (type & 0x7f), len);		}		len = buflen;	}	OUTNSTR(fp, (const char *) buf, len);}#endif /* __STDIO_PRINTF_FLOAT */#else  /* L_vfprintf */#define VFPRINTF vfwprintf#define FMT_TYPE wchar_t#define OUTNSTR _outnwcs#define STRLEN  wcslen#define _PPFS_init _ppwfs_init#define OUTPUT(F,S)			fputws(S,F)#define _outnwcs(stream, wstring, len)	_wstdio_fwrite(wstring, len, stream)#define FP_OUT _fp_out_widestatic void _outnstr(FILE *stream, const char *s, size_t wclen){	/* NOTE!!! len here is the number of wchars we want to generate!!! */	wchar_t wbuf[64];	mbstate_t mbstate;	size_t todo, r;	mbstate.__mask = 0;	todo = wclen;		while (todo) {		r = mbsrtowcs(wbuf, &s,					  ((todo <= sizeof(wbuf)/sizeof(wbuf[0]))					   ? todo					   : sizeof(wbuf)/sizeof(wbuf[0])),					  &mbstate);		assert(((ssize_t)r) > 0);		_outnwcs(stream, wbuf, r);		todo -= r;	}}#ifdef __STDIO_PRINTF_FLOAT#ifdef __UCLIBC_MJN3_ONLY__#warning TODO: Move defines from _fpmaxtostr.  Put them in a common header.#endif/* The following defines are from _fpmaxtostr.*/#define DIGITS_PER_BLOCK     9#define NUM_DIGIT_BLOCKS   ((DECIMAL_DIG+DIGITS_PER_BLOCK-1)/DIGITS_PER_BLOCK)#define BUF_SIZE  ( 3 + NUM_DIGIT_BLOCKS * DIGITS_PER_BLOCK )static void _fp_out_wide(FILE *fp, intptr_t type, intptr_t len, intptr_t buf){	wchar_t wbuf[BUF_SIZE];	const char *s = (const char *) buf;	int i;	if (type & 0x80) {			/* Some type of padding needed */		int buflen = strlen(s);		if ((len -= buflen) > 0) {			_charpad(fp, (type & 0x7f), len);		}		len = buflen;	}	if (len > 0) {		i = 0;		do {#ifdef __LOCALE_C_ONLY			wbuf[i] = s[i];#else  /* __LOCALE_C_ONLY */#ifdef __UCLIBC_HAS_GLIBC_DIGIT_GROUPING__			if (s[i] == ',') {				wbuf[i] = __UCLIBC_CURLOCALE_DATA.thousands_sep_wc;			} else#endif /* __UCLIBC_HAS_GLIBC_DIGIT_GROUPING__ */			if (s[i] == '.') {				wbuf[i] = __UCLIBC_CURLOCALE_DATA.decimal_point_wc;			} else {				wbuf[i] = s[i];			}#endif /* __LOCALE_C_ONLY */		} while (++i < len);		OUTNSTR(fp, wbuf, len);	}}#endif /* __STDIO_PRINTF_FLOAT */static int _ppwfs_init(register ppfs_t *ppfs, const wchar_t *fmt0){	static const wchar_t invalid_wcs[] = L"Invalid wide format string.";	int r;	/* First, zero out everything... argnumber[], argtype[], argptr[] */	memset(ppfs, 0, sizeof(ppfs_t)); /* TODO: nonportable???? */#ifdef NL_ARGMAX	--ppfs->maxposarg;			/* set to -1 */#endif /* NL_ARGMAX */	ppfs->fmtpos = (const char *) fmt0;	ppfs->info._flags = FLAG_WIDESTREAM;	{		mbstate_t mbstate;		const wchar_t *p;		mbstate.__mask = 0;	/* Initialize the mbstate. */		p = fmt0;		if (wcsrtombs(NULL, &p, SIZE_MAX, &mbstate) == ((size_t)(-1))) {			ppfs->fmtpos = (const char *) invalid_wcs;			return -1;		}	}	/* now set all argtypes to no-arg */	{#if 1		/* TODO - use memset here since already "paid for"? */		register int *p = ppfs->argtype;				r = MAX_ARGS;		do {			*p++ = __PA_NOARG;		} while (--r);#else		/* TODO -- get rid of this?? */		register char *p = (char *) ((MAX_ARGS-1) * sizeof(int));		do {			*((int *)(((char *)ppfs) + ((int)p) + offsetof(ppfs_t,argtype))) = __PA_NOARG;			p -= sizeof(int);		} while (p);#endif	}	/*	 * Run through the entire format string to validate it and initialize	 * the positional arg numbers (if any).	 */	{		register const wchar_t *fmt = fmt0;		while (*fmt) {			if ((*fmt == '%') && (*++fmt != '%')) {				ppfs->fmtpos = (const char *) fmt; /* back up to the '%' */				if ((r = _ppfs_parsespec(ppfs)) < 0) {					return -1;				}				fmt = (const wchar_t *) ppfs->fmtpos; /* update to one past end of spec */			} else {				++fmt;			}		}		ppfs->fmtpos = (const char *) fmt0; /* rewind */	}#ifdef NL_ARGMAX	/* If we have positional args, make sure we know all the types. */	{		register int *p = ppfs->argtype;		r = ppfs->maxposarg;		while (--r >= 0) {			if ( *p == __PA_NOARG ) { /* missing arg type!!! */				return -1;			}			++p;		}	}#endif /* NL_ARGMAX */	return 0;}#endif /* L_vfprintf */static void _charpad(FILE * __restrict stream, int padchar, size_t numpad){	/* TODO -- Use a buffer to cut down on function calls... */	FMT_TYPE pad[1];	*pad = padchar;	while (numpad) {		OUTNSTR(stream, pad, 1);		--numpad;	}}/* TODO -- Dynamically allocate work space to accomodate stack-poor archs? */static int _do_one_spec(FILE * __restrict stream,						 register ppfs_t *ppfs, int *count){	static const char spec_base[] = SPEC_BASE;#ifdef L_vfprintf	static const char prefix[] = "+\0-\0 \0000x\0000X";	/*                            0  2  4  6   9 11*/#else  /* L_vfprintf */

⌨️ 快捷键说明

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