.TH MPU_SCANF 3 "September 2026" "libmpuio" "LIBMPUIO Programmer's Manual" .SH NAME mpu_scanf, mpu_fscanf, mpu_sscanf, mpu_vscanf, mpu_vfscanf, mpu_vsscanf, mpu_scanf_unlocked, mpu_fscanf_unlocked, mpu_vscanf_unlocked, mpu_vfscanf_unlocked \- formatted UCS-2 input including libmpu numbers .SH SYNOPSIS .nf #include int mpu_scanf( const __mpu_char16_t *format, ... ); int mpu_fscanf( mpu_FILE *stream, const __mpu_char16_t *format, ... ); int mpu_sscanf( const __mpu_char16_t *string, const __mpu_char16_t *format, ... ); int mpu_vscanf( const __mpu_char16_t *format, va_list args ); int mpu_vfscanf( mpu_FILE *stream, const __mpu_char16_t *format, va_list args ); int mpu_vsscanf( const __mpu_char16_t *string, const __mpu_char16_t *format, va_list args ); int mpu_scanf_unlocked( const __mpu_char16_t *format, ... ); int mpu_fscanf_unlocked( mpu_FILE *stream, const __mpu_char16_t *format, ... ); int mpu_vscanf_unlocked( const __mpu_char16_t *format, va_list args ); int mpu_vfscanf_unlocked( mpu_FILE *stream, const __mpu_char16_t *format, va_list args ); .fi .SH DESCRIPTION The .BR mpu_scanf () family reads formatted text using 16-bit .B __mpu_char16_t (UCS-2) format strings and destinations. .PP For a real file stream, external UTF-8 is decoded to UCS-2 before formatted input is interpreted. For string input, the source string is already UCS-2. Raw byte input through .BR mpu_fread (3) is not involved in this conversion. .PP The functions correspond to the usual stdio scanf family: .BR mpu_scanf () reads from .BR mpu_stdin , .BR mpu_fscanf () from a specified stream, and .BR mpu_sscanf () from a NUL-terminated UCS-2 string. The v-functions take a .B va_list instead of variadic arguments. .PP The unlocked forms do not acquire the stream mutex. They are intended for use while the caller owns the stream lock with .BR mpu_flockfile (3), or where external synchronization is otherwise guaranteed. .SH FORMAT A format string contains ordinary UCS-2 characters, white-space characters, and conversion specifications. .PP An ordinary non-white-space character must match the next input character exactly. A white-space character in the format consumes zero or more input white-space characters. .PP A conversion begins with .B % and has the general form .PP .nf %[*][width][length]conversion .fi .PP For libmpu objects the historical size modifier .B z or .B Z replaces the ordinary length modifier. The two forms are equivalent: .PP .nf %[*][width]zconversion %[*][width]Zconversion .fi .PP A literal percent sign is written as .BR %% . .SH ASSIGNMENT SUPPRESSION An asterisk immediately following .B % suppresses assignment. The input is consumed normally but no pointer argument is taken and the conversion does not increase the return value. .PP For example, .PP .nf %*d %d .fi .PP skips the first decimal integer and stores the second. .SH FIELD WIDTH A decimal field width limits the maximum number of input characters consumed by that conversion. It is a maximum, not a minimum. .PP For example, .PP .nf %3d .fi .PP reads at most three characters belonging to the decimal integer. .PP The implementation checks field-width accumulation for integer overflow. An overflowing width sets .B errno to .B EOVERFLOW and is not allowed to wrap internally. .SH ORDINARY INTEGER RANGE SEMANTICS Ordinary integer tokens are converted through .BR strtoimax (3) or .BR strtoumax (3) before the selected scanf destination type is stored. The entire token accepted by the LIBMPUIO scanner must also be consumed by the native conversion routine; a scanner/parser disagreement is rejected rather than silently accepting a trailing suffix. .PP For compatibility with glibc-style scanf behavior, conversion to a destination narrower than .B intmax_t or .B uintmax_t uses the native C narrowing conversion. Thus, on the supported two's-complement GNU/Linux targets, values such as 128 read by .B %hhd and 256 read by .B %hhu have the same wrapped result as glibc scanf and do not by themselves force .BR errno . .PP If the source token itself exceeds the range accepted by .B strtoimax or .BR strtoumax , the native parser sets .B errno to .B ERANGE and its saturated result is then stored using the selected length modifier. LIBMPUIO preserves this behavior. Programs that need portable arbitrary-range integer input should use the .B z/Z MPU integer conversions instead of depending on native narrowing outside the C destination range. .SH LENGTH MODIFIERS For ordinary integer conversions and .B %n the supported length modifiers are: .TP .B hh Pointer to .B signed char or .B unsigned char as appropriate. .TP .B h Pointer to .B short or .B unsigned short . .TP .B l Pointer to .B long or .B unsigned long . For floating conversions, .B %lf stores into .BR double * . .TP .B ll Pointer to .B long long or .B unsigned long long . .TP .B j Pointer to .B intmax_t or .B uintmax_t . .TP .B t Pointer to .B ptrdiff_t or the corresponding unsigned integer type. .TP .B L For an ordinary floating conversion, store into .BR long double * . .PP The standard C .B z length modifier is intentionally not implemented. In LIBMPUIO both .B z and .B Z introduce the LibMPU size modifier described below. .SH CHARACTER CONVERSION .TP .B %c Reads one UCS-2 character into .BR __mpu_char16_t * . Unlike most conversions, .B %c does not skip leading white space. A field width greater than one reads exactly that many UCS-2 characters. No terminating NUL is appended. .SH STRING CONVERSION .TP .B %s Reads a sequence of non-white-space UCS-2 characters into .BR __mpu_char16_t * . Leading input white space is skipped. A terminating UCS-2 NUL is appended. The caller must provide enough storage for the selected field width plus the terminator, or for the complete input token when no width is supplied. .TP .B %a LIBMPUIO extension: matches a sequence of non-white-space input characters and stores them through .BR __mpu_char8_t * as a NUL-terminated multibyte string encoded according to the active .B LC_CTYPE locale. For file and console streams, external multibyte input is decoded by LIBMPUIO before the scanf conversion is applied. The field width limits the number of input characters, not the number of bytes in the resulting multibyte string. The destination must therefore provide enough room for the converted string and its terminating NUL. A character that cannot be represented in the active locale causes the conversion to fail with .BR EILSEQ . Length modifiers and the MPU .B z/Z modifier do not apply to this conversion. .SH SCANSET CONVERSION .TP .B %[ Reads a nonempty sequence of UCS-2 characters selected by a scanset and appends a terminating NUL. .PP The supported forms include: .PP .nf %[abc] %[a-z] %[^0-9] %[]a-z] .fi .PP A leading .B ^ negates the set. Ranges are recognized. A closing bracket .B ] can be included by placing it first in the set. As with .BR %c , leading white space is not skipped automatically. .SH SIGNED INTEGER CONVERSIONS .TP .B %d Reads a signed decimal integer. .TP .B %i Reads a signed integer with base determined from the input, corresponding to the usual C integer notation. .PP The destination type is selected by the length modifier. With no length modifier the destination is .BR int * . .SH UNSIGNED INTEGER CONVERSIONS .TP .B %u Reads an unsigned decimal integer. .TP .B %o Reads an unsigned octal integer. .TP .B %x, %X Read an unsigned hexadecimal integer. Hexadecimal alphabetic digits may occur immediately after an optional .B 0x or .B 0X prefix. .TP .B %b, %B libmpuio extension: read an unsigned binary integer. An optional .B 0b or .B 0B prefix is accepted. .PP The compatibility conversions .BR %D , .BR %O , and .B %U are also recognized by the current scanner. .PP The destination type is selected by the length modifier. With no modifier it is .BR unsigned int * . .SH POINTER CONVERSION .TP .B %p Reads a hexadecimal pointer representation and stores the result through a .BR void ** . .SH ORDINARY FLOATING CONVERSIONS .TP .B %e, %E, %f, %F, %g, %G Read an ordinary floating-point value. The lexical input is converted through .BR strtold (3) after the UCS-2 token has been converted to the active locale multibyte encoding. .PP With no length modifier the destination is .BR float * . With .B l it is .BR double * , and with .B L it is .BR long double * . .PP For .B %e/%E/%f/%F/%g/%G the scanner accepts signed decimal values, decimal exponent forms, and supported special values such as infinity and NaN. Ordinary floating input also accepts the C-style NaN forms .BR nan() and .BR nan(payload) , where the payload contains ASCII letters, digits, or underscore characters. The spelling is case-insensitive and an optional leading sign is accepted. .PP Ordinary floating input follows the active .B LC_NUMERIC radix character. The scanner obtains the locale decimal-point string from .BR localeconv (3), converts it to strict UCS-2 for token recognition, and converts the completed numeric token back to the active locale multibyte encoding before calling .BR strtold (3). This applies to .B %e/%E/%f/%F/%g/%G input. .PP Consequently ordinary formatted output and ordinary formatted input use the same locale radix convention. In the C locale the radix character remains .BR . ; in a locale whose decimal point is a comma, for example, ordinary input accepts forms such as .BR 12,5 . .PP This locale rule applies only to ordinary C floating conversions. The .B z and .B Z MPU real/complex conversions continue to use the LIBMPU numeric grammar and are not reinterpreted by the ordinary libc locale tokenizer. .SH COUNT CONVERSION .TP .B %n Stores the number of UCS-2 input characters consumed so far. It consumes no input and does not increment the successful-assignment count returned by the function. .PP The ordinary length modifiers .BR hh , h , l , ll , j , and .B t select the destination integer type for .BR %n . .SH LIBMPU SIZE MODIFIER The LibMPU arbitrary-precision size modifier is .PP .nf z Z .fi .PP The lower-case and upper-case forms are equivalent. LIBMPUIO intentionally does not implement the standard C .B z length modifier for .BR size_t . Thus, for example, .B %zu means a default-size LibMPU unsigned-integer conversion, not a .B size_t conversion. .PP If no decimal digits follow .B z or .BR Z , 128 bits are assumed. The decimal .I bits field must be one of the supported MPU sizes: .PP .nf 8, 16, 32, 64, 128, 256, 512, 1024, 2048, 4096, 8192, 16384, 32768, 65536 .fi .PP The actual grammar is compiled from .B MPU_REAL_IO_LIMIT in .BR . Only sizes not greater than that value exist. If LibMPU was configured with .B MPU_REAL_IO_LIMIT=16384, then .B z32768/Z32768 and .B z65536/Z65536 are invalid format modifiers; they are rejected before a conversion is performed. .PP The accepted size is independent of the following conversion class. After the modifier has been parsed, integer conversions operate on libmpu integer objects, real conversions operate on libmpu real objects, and .B j/J operate on libmpu complex objects. Integer conversions may use sizes from 8 bits; real and complex conversions require at least 32 bits. .PP .B MPU_MATH_FN_LIMIT limits transcendental/math operations only and does not define the formatted input grammar. .SH DESTINATION TYPE MODEL Ordinary and MPU input conversions also have separate destination contracts. For ordinary conversions the conversion and standard length modifier select a pointer to the corresponding C destination type, such as .B int * for .B %d or .B double * for .BR %lf . .PP For an MPU conversion, .B z or .B Z selects both the MPU interpretation and its exact storage size. The destination argument points to an MPU object of that size. With libmpu's array typedefs, passing the array object name naturally supplies a pointer to its first storage byte: .PP .nf mpu_int128_t x; mpu_real128_t r; mpu_sscanf( text, MPU_UCS2("%z128u"), x ); mpu_sscanf( text, MPU_UCS2("%z128g"), r ); .fi .PP The destination pointer contains no run-time size metadata, so the scanner cannot infer the MPU bit size from the pointer. The explicit size modifier is therefore required to describe how the pointed-to storage is to be interpreted. Ordinary C destinations should use ordinary C conversions rather than using an MPU conversion merely as a way to reinterpret their object representation. .SH LIBMPU INTEGER CONVERSIONS The following conversions take a pointer to a libmpu integer object whose storage size matches the requested .BR z/Z : .TP .B %zd, %Zd, %zi, %Zi Read a signed arbitrary-precision integer. .TP .B %zu, %Zu Read an unsigned arbitrary-precision decimal integer. .TP .B %zo, %Zo Read an unsigned arbitrary-precision octal integer. .TP .B %zx, %Zx, %zX, %ZX Read an unsigned arbitrary-precision hexadecimal integer. .TP .B %zb, %Zb, %zB, %ZB Read an unsigned arbitrary-precision binary integer. .PP Radix prefixes are normalized before conversion by libmpu. Thus the scanner can feed the canonical representation expected by .BR iatoi () and .BR iatoui () without requiring the caller to manipulate prefixes. .PP Examples: .PP .nf mpu_int128_t x; mpu_sscanf( text, fmt_Z128x, x ); .fi .SH LIBMPU REAL CONVERSIONS The historical real conversions are: .TP .B %zr, %Zr, %zR, %ZR Read a libmpu arbitrary-precision real value. .TP .B %ze/%Ze, %zE/%ZE, %zf/%Zf, %zF/%ZF, %zg/%Zg, %zG/%ZG Read a libmpu arbitrary-precision real value using the corresponding formatted input conversion name. .PP All of these conversions store into a libmpu real object of the selected size. In particular, both .B %Z128R and .B %Z128E expect an .B mpu_real128_t destination. They use the same real-number conversion path and both accept the longhand real representation emitted by real output formats. Conversion is performed through .BR ascii_to_real () from libmpu. .PP For compatibility with the historical CODE.LIB format language, real output with .B %r/%R uses an .B e/E exponent delimiter. Therefore a value printed with .B %Z128R can be read back with either .B %Z128R or .BR %Z128E . .PP The corresponding destination type mapping is: .PP .nf %Z128R -> mpu_real128_t %Z128E -> mpu_real128_t %Z128J -> mpu_complex128_t .fi .SH LIBMPU COMPLEX CONVERSIONS .TP .B %zj, %Zj, %zJ, %ZJ Read a libmpu complex value using the historical real/imaginary notation. The destination is a libmpu complex object of the selected size; for example, .B %Z128J expects .BR mpu_complex128_t . .PP For example, the following is the native form emitted by an upper-case complex format: .PP .nf 1.250000R+0000-2.500000J+0000 .fi .PP The scanner separates the real and imaginary components, converts each through .BR ascii_to_real () and combines them with .BR c_gen_complex () . The return class from .BR ascii_to_real () is authoritative: r/R denotes the real component and j/J the imaginary component. Either component may be absent and is then initialized to exact zero. White space is permitted between the two components and after a leading sign. If a possible second component is not imaginary, the probe and any intervening white space are pushed back so the following input remains available to the next conversion. .PP The LIBMPU special forms inf, NaN and ind are accepted together with their _e/_r/_j suffix forms. The scanner determines only the lexical boundary; LIBMPU performs numeric interpretation. .PP A token containing no decimal digit is numeric only when it contains an explicit decimal point. Thus `.`, `+.e`, `-.r` and `.j` are accepted, while bare `e`, `r` and `j` (including signed or exponent-suffixed variants) are not numeric tokens. This lexical restriction prevents ordinary alphabetic input from being confused with numeric constants even though .BR ascii_to_real () accepts the historical bare-letter forms directly. .PP For the accepted digitless point forms, the scanner supplies an explicit zero significand and passes the canonical token to .BR ascii_to_real () . That LibMPU routine remains authoritative for the numeric value and for the e/r/j component class. Ordinary finite values and special-value syntax are passed unchanged and are not interpreted by this compatibility normalization. .PP The lower-case .B j name conflicts with the standard .B j integer length modifier. When followed by an ordinary integer conversion, .B j is interpreted as the standard .B intmax_t/uintmax_t length modifier. In an MPU conversion, especially after .BR z/Z , it is the complex conversion character. .SH LIBMPU COUNT CONVERSION .TP .B %zn, %Zn Stores the number of UCS-2 characters consumed so far in a libmpu integer object of the selected size. It does not consume input and does not increment the assignment count. .SH NUMERIC TOKEN ROLLBACK For decimal floating input, an exponent marker and optional sign are rolled back if no exponent digit follows. Thus input such as .B 12e+X can match 12 while leaving e+X for subsequent input. The same rule is honored when a field width ends in the middle of an exponent. .PP An unterminated NaN payload is a matching failure; the token is rolled back rather than silently accepting a partial payload. .PP libmpuio preserves characters that are not part of a successfully accepted numeric token. This includes suffix characters after an integer and incomplete radix or exponent constructs. .PP For example, when scanning an integer from input conceptually equivalent to .PP .nf 123abc .fi .PP the letters remain available to the next conversion. Similarly, incomplete .B 0x or .B 0b prefixes and incomplete floating exponents are rolled back rather than silently lost. .SH UTF-8 AND UCS-2 All formatted text inside libmpuio is UCS-2. Real files and console streams use UTF-8 externally. Valid UTF-8 scalar values above U+FFFF cannot be represented by strict UCS-2 and therefore produce .BR EILSEQ . UTF-16 surrogate pairs are not synthesized. .PP The .B %c, .B %s, and .B %[ destinations therefore use .B __mpu_char16_t storage, not the platform .B wchar_t type. The LIBMPUIO .B %a conversion is the explicit current-locale multibyte-string interface and stores through .BR __mpu_char8_t * . .SH RETURN VALUE On success these functions return the number of input items assigned. A conversion suppressed with .B * does not count. The .B %n conversion also does not count. .PP If an input failure occurs before the first successful assignment, .B mpu_EOF is returned. A matching failure before any assignment returns zero. If a later conversion fails after one or more assignments, the number of completed assignments is returned. .SH ERRORS Errors from the underlying stream and UTF-8 decoder are reflected in the stream error state and .BR errno . Malformed or unrepresentable UTF-8 may set .BR EILSEQ . A format width or MPU bit-size whose decimal accumulation overflows its internal integer representation may set .BR EOVERFLOW . .PP Invalid streams or invalid internal arguments may set .BR EINVAL . .SH THREAD SAFETY The ordinary stream-based functions lock the .B mpu_FILE object while scanning. The .B *_unlocked forms do not acquire the mutex. .PP A typical explicit-locking sequence is: .PP .nf mpu_flockfile( fp ); r = mpu_fscanf_unlocked( fp, format, &value ); mpu_funlockfile( fp ); .fi .SH EXAMPLES Read an ordinary decimal integer and UCS-2 word: .PP .nf __mpu_char16_t format[] = MPU_UCS2("%d %s"); __mpu_char16_t word[64]; int value; if( mpu_sscanf(text, format, &value, word) == 2 ) { /* value and word are available here. */ } .fi .PP Read a current-locale multibyte word: .PP .nf __mpu_char8_t word8[64]; if( mpu_sscanf(text, MPU_UCS2("%a"), word8) == 1 ) { /* word8 contains a current-locale multibyte string. */ } .fi .PP Read a 128-bit libmpu integer: .PP .nf mpu_int128_t value; __mpu_char16_t format[] = MPU_UCS2("%Z128x"); if( mpu_fscanf(fp, format, value) == 1 ) { /* value contains the hexadecimal integer. */ } .fi .PP Read the same 128-bit real value with either the R or E conversion: .PP .nf mpu_real128_t r1, r2; mpu_sscanf( MPU_UCS2( "1.23456789E+10" ), MPU_UCS2( "%Z128R" ), r1 ); mpu_sscanf( MPU_UCS2( "1.23456789E+10" ), MPU_UCS2( "%Z128E" ), r2 ); mpu_printf( MPU_UCS2( "R: %Z128R\n" ), r1 ); mpu_printf( MPU_UCS2( "E: %Z128R\n" ), r2 ); .fi .PP Both assignments above write to .B mpu_real128_t objects. A complex destination is used only with the native complex conversion .BR j/J . .PP Read a 128-bit real and complex value: .PP .nf mpu_real128_t r; mpu_complex128_t c; __mpu_char16_t format[] = MPU_UCS2( "%Z128E %Z128J" ); if( mpu_fscanf( fp, format, r, c ) == 2 ) { /* r and c were converted by libmpu. */ } .fi .SH NOTES The LIBMPUIO format language intentionally preserves the historical LibMPU numeric-size syntax. Lower-case .B z is therefore reserved for LibMPU together with upper-case .BR Z ; it is not the C .B size_t length modifier. .SH SEE ALSO .BR libmpuio (3), .BR mpu_printf (3), .BR mpu_fopen (3), .BR mpu_fread (3), .BR mpu_flockfile (3), .BR strtold (3) .SH LOCKED VERSUS UNLOCKED FORMATTED INPUT .BR mpu_fscanf_unlocked (), .BR mpu_vfscanf_unlocked (), .BR mpu_scanf_unlocked (), and .BR mpu_vscanf_unlocked () use the exact same scanner as the ordinary stream forms but omit implicit stream locking. Tokenization, rollback, assignment counts, native range semantics, MPU z/Z conversions, EOF/matching failure, and errors are unchanged. .PP The sscanf family scans caller-owned UCS-2 memory rather than an mpu_FILE stream and therefore has no stream-unlocked variant.