📄 fiolib.c
字号:
cp = buf; /* where to fill in result */ *cp = EOS; /* EOS terminate just in case */#if ((CPU_FAMILY != I960) && (CPU_FAMILY != PPC)) size = (*fioFltFormatRtn) (&vaList,prec,doAlt,ch, &doSign,cp,buf+sizeof(buf));#else size = (*fioFltFormatRtn) (vaList, prec, doAlt, ch, &doSign,cp,buf+sizeof(buf));#endif if ((int)size < 0) /* strange value (Nan,Inf,..) */ { size = -size; /* get string length */ prec = oldprec; /* old precision (not default)*/ doZeroPad = FALSE; /* don't pad with zeroes */ if (doSign) /* is strange value signed? */ sign = '-'; } else { if (doSign) sign = '-'; if (*cp == EOS) cp++; } break; } /* FALLTHROUGH if no floating point format routine */ default: /* "%?" prints ?, unless ? is NULL */ if (ch == EOS) return (ret); /* pretend it was %c with argument ch */ cp = buf; *cp = ch; size = 1; sign = EOS; break; } /* All reasonable formats wind up here. At this point, * `cp' points to a string which (if not doLAdjust) * should be padded out to `width' places. If * doZeroPad, it should first be prefixed by any * sign or other prefix; otherwise, it should be blank * padded before the prefix is emitted. After any * left-hand padding and prefixing, emit zeroes * required by a decimal [diouxX] precision, then print * the string proper, then emit zeroes required by any * leftover floating precision; finally, if doLAdjust, * pad with blanks. */ /* * compute actual size, so we know how much to pad. * fieldsz excludes decimal prec; realsz includes it */ fieldsz = size + fpprec; if (sign) { fieldsz++; if (fieldSzIncludeSign) dprec++; } else if (doHexPrefix) fieldsz += 2; realsz = (dprec > fieldsz) ? dprec : fieldsz; /* right-adjusting blank padding */ if (!doLAdjust && !doZeroPad) PAD(width - realsz, blanks); /* prefix */ if (sign) { if ((*outRoutine) (&sign, 1, outarg) != OK) return (ERROR); } else if (doHexPrefix) { ox[0] = '0'; ox[1] = ch; if ((*outRoutine) (ox, 2, outarg) != OK) return (ERROR); } /* right-adjusting zero padding */ if (!doLAdjust && doZeroPad) PAD(width - realsz, zeroes); /* leading zeroes from decimal precision */ PAD(dprec - fieldsz, zeroes); /* the string or number proper */ if ((*outRoutine) (cp, size, outarg) != OK) return (ERROR); /* trailing floating point zeroes */ PAD(fpprec, zeroes); /* left-adjusting padding (always blank) */ if (doLAdjust) PAD(width - realsz, blanks); /* finally, adjust ret */ ret += (width > realsz) ? width : realsz; } }/********************************************************************************* putbuf - put characters in a buffer** This routine is a support routine for sprintf().* This routine copies length bytes from source to destination, leaving the* destination buffer pointer pointing at byte following block copied.*/LOCAL STATUS putbuf ( char *inbuf, /* pointer to source buffer */ int length, /* number of bytes to copy */ char **outptr /* pointer to destination buffer */ ) { bcopy (inbuf, *outptr, length); *outptr += length; return (OK); }/********************************************************************************* printbuf - printf() support routine: print characters in a buffer*/LOCAL STATUS printbuf ( char *buf, int nbytes, int fd ) { return (write (fd, buf, nbytes) == nbytes ? OK : ERROR); }/********************************************************************************* fioRead - read a buffer** This routine repeatedly calls the routine read() until <maxbytes> have* been read into <buffer>. If EOF is reached, the number of bytes read* will be less than <maxbytes>.** RETURNS:* The number of bytes read, or ERROR if there is an error during the read* operation.** SEE ALSO: read()*/int fioRead ( int fd, /* file descriptor of file to read */ char * buffer, /* buffer to receive input */ int maxbytes /* maximum number of bytes to read */ ) { int original_maxbytes = maxbytes; int nbytes; while (maxbytes > 0) { nbytes = read (fd, buffer, maxbytes); if (nbytes < 0) return (ERROR); if (nbytes == 0) return (original_maxbytes - maxbytes); maxbytes -= nbytes; buffer += nbytes; } return (original_maxbytes); }/********************************************************************************* fioRdString - read a string from a file** This routine puts a line of input into <string>. The specified input* file descriptor is read until <maxbytes>, an EOF, an EOS, or a newline* character is reached. A newline character or EOF is replaced with EOS,* unless <maxbytes> characters have been read.** RETURNS:* The length of the string read, including the terminating EOS;* or EOF if a read error occurred or end-of-file occurred without* reading any other character.*/int fioRdString ( int fd, /* fd of device to read */ FAST char string[], /* buffer to receive input */ int maxbytes /* max no. of chars to read */ ) { char c; FAST int nchars = 0; FAST int i = 0; /* read characters until * 1) specified line limit is reached, * 2) end-of-file is reached, * 3) EOS character is read, * 4) newline character is read, * or 5) read error occurs. */ while (i < maxbytes) { nchars = read (fd, &c, 1); if (nchars == ERROR) /* if can't read file */ break; /* check for newline terminator */ if ((nchars != 1) || (c == '\n') || (c == EOS)) { string [i++] = EOS; break; } string [i++] = c; } if (nchars == ERROR || ((nchars == 0) && (i == 1))) i = EOF; return (i); }/********************************************************************************* sscanf - read and convert characters from an ASCII string (ANSI)** This routine reads characters from the string <str>, interprets them* according to format specifications in the string <fmt>, which specifies* the admissible input sequences and how they are to be converted for* assignment, using subsequent arguments as pointers to the objects to* receive the converted input.** If there are insufficient arguments for the format, the behavior is* undefined. If the format is exhausted while arguments remain, the excess* arguments are evaluated but are otherwise ignored.** The format is a multibyte character sequence, beginning and ending in* its initial shift state. The format is composed of zero or more directives:* one or more white-space characters; an ordinary multibyte character (neither* `%' nor a white-space character); or a conversion specification. Each* conversion specification is introduced by the `%' character. After the `%',* the following appear in sequence:** .iP "" 4* An optional assignment-suppressing character `*'.* .iP* An optional non-zero decimal integer that specifies the maximum field * width.* .iP* An optional `h' or `l' (el) indicating the size of the receiving* object. The conversion specifiers `d', `i', and `n' should be* preceded by `h' if the corresponding argument is a pointer to `short* int' rather than a pointer to `int', or by `l' if it is a pointer to* `long int'. Similarly, the conversion specifiers `o', `u', and `x'* shall be preceded by `h' if the corresponding argument is a pointer* to `unsigned short int' rather than a pointer to `unsigned int', or* by `l' if it is a pointer to `unsigned long int'. Finally, the* conversion specifiers `e', `f', and `g' shall be preceded by `l' if* the corresponding argument is a pointer to `double' rather than a* pointer to `float'. If an `h' or `l' appears with any other* conversion specifier, the behavior is undefined.* .iP* \&WARNING: ANSI C also specifies an optional `L' in some of the same* contexts as `l' above, corresponding to a `long double *' argument.* However, the current release of the VxWorks libraries does not support * `long double' data; using the optional `L' gives unpredictable results.* .iP* A character that specifies the type of conversion to be applied. The* valid conversion specifiers are described below.* .LP** The sscanf() routine executes each directive of the format in turn. If a * directive fails, as detailed below, sscanf() returns. Failures* are described as input failures (due to the unavailability of input* characters), or matching failures (due to inappropriate input).* * A directive composed of white-space character(s) is executed by reading* input up to the first non-white-space character (which remains unread),* or until no more characters can be read.** A directive that is an ordinary multibyte character is executed by reading* the next characters of the stream. If one of the characters differs from* one comprising the directive, the directive fails, and the differing and* subsequent characters remain unread.** A directive that is a conversion specification defines a set of matching* input sequences, as described below for each specifier. A conversion* specification is executed in the following steps:** Input white-space characters (as specified by the isspace() function) are * skipped, unless the specification includes a `[', `c', or `n' specifier.** An input item is read from the stream, unless the specification includes* an `n' specifier. An input item is defined as the longest matching* sequence of input characters, unless that exceeds a specified field width,* in which case it is the initial subsequence of that length in the* sequence. The first character, if any, after the input item remains* unread. If the length of the input item is zero, the execution of the* directive fails: this condition is a matching failure, unless an error* prevented input from the stream, in which case it is an input failure.** Except in the case of a `%' specifier, the input item is converted to a* type appropriate to the conversion specifier. If the input item is not a* matching sequence, the execution of the directive fails: this condition* is a matching failure. Unless assignment suppression was indicated by a* `*', the result of the conversion is placed in the object pointed to by* the first argument following the <fmt> argument that has not already* received a conversion result. If this object does not have an appropriate* type, or if the result of the conversion cannot be represented in the* space provided, the behavior is undefined.** The following conversion specifiers are valid:** .iP `d'* Matches an optionally signed decimal integer whose format is* the same as expected for the subject sequence of the strtol()* function with the value 10 for the <base> argument. The * corresponding argument should be a pointer to `int'.* .iP `i'* Matches an optionally signed integer, whose format is the* same as expected for the subject sequence of the strtol()* function with the value 0 for the <base> argument. The * corresponding argument should be a pointer to `int'.* .iP `o'* Matches an optionally signed octal integer, whose format is the* same as expected for the subject sequence of the strtoul()* function with the value 8 for the <base> argument. The* corresponding argument should be a pointer to `unsigned int'.* .iP `u'* Matches an optionally signed decimal integer, whose format is * the same as expected for the subject sequence of the strtoul()* function with the value 10 for the <base> argument. The* corresponding argument should be a pointer to `unsigned int'.* .iP `x'* Matches an optionally signed hexadecimal integer, whose format is* the same as expected for the subject sequence of the strtoul()* function with the value 16 for the <base> argument. The* corresponding argument should be a pointer to `unsigned int'.* .iP "`e', `f', `g'"* Match an optionally signed floating-point number, whose format* is the same as expected for the subject string of the strtod()* function. The corresponding argument should be a pointer to `float'.* .iP `s'* Matches a sequence of non-white-space characters. The * corresponding argument should be a pointer to the initial* character of an array large enough to accept the sequence* and a terminating null character, which will be added
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -