#include <stdio.h>
#include <inttypes.h>
int main(void)
{
int8_t int8;
int16_t int16;
int32_t int32;
int64_t int64;
uint8_t uint8;
uint16_t uint16;
uint32_t uint32;
uint64_t uint64;
scanf("%"SCNd8"%"SCNd16"%"SCNd32"%"SCNd64"%"SCNu8"%"SCNu16"%"SCNu32"%"SCNu64,
&int8, &int16, &int32, &int64, &uint8, &uint16, &uint32, &uint64);
printf("%"PRId8"\n%"PRId16"\n%"PRId32"\n%"PRId64"\n%"PRIu8"\n%"PRIu16"\n%"PRIu32"\n%"PRIu64"\n",
int8, int16, int32, int64, uint8, uint16, uint32, uint64);
return 0;
}
I can't compile this code using latest gcc + MinGW + Netbeans + Windows. Netbeans says "unable to resolve identifier SCNd8 and SCNu8". I can't find any reference for SCNd8 and SCNu8 on gcc man page although http://linux.die.net/include/inttypes.h defines them. I don't receive syntax error for using PRId8 or PRIu8.
MinGW inttypes.h (lacks SCNd8 and SCNu8 ) (sample code)
#define PRIXFAST64 "I64X"
#define PRIXMAX "I64X"
#define PRIXPTR "X"
/*
* fscanf macros for signed int types
* NOTE: if 32-bit int is used for int_fast8_t and int_fast16_t
* (see stdint.h, 7.18.1.3), FAST8 and FAST16 should have
* no length identifiers
*/
#define SCNd16 "hd"
#define SCNd32 "d"
#define SCNd64 "I64d"
#define SCNdLEAST16 "hd"
#define SCNdLEAST32 "d"
#define SCNdLEAST64 "I64d"
#define SCNdFAST16 "hd"
Interesting - I have MinGW with GCC Version 4.5.1 installed.
The format specifier macros in inttypes.h
work for the most part, except for the the ones for inputting 8-bit ints (SCNd8
and SCNu8
). Those macros are defined in inttypes.h
, but trying to use them doesn't work so well. With the following code:
#include <stdio.h>
#include <inttypes.h>
int main(void)
{
int8_t int8 = 0;
uint8_t uint8 = 0;
scanf("%"SCNd8, &int8);
scanf("%"SCNu8, &uint8);
return 0;
}
I get the following warnings:
C:\temp\test.c: In function 'main':
C:\temp\test.c:9:5: warning: unknown conversion type character 'h' in format
C:\temp\test.c:9:5: warning: too many arguments for format
C:\temp\test.c:10:5: warning: unknown conversion type character 'h' in format
C:\temp\test.c:10:5: warning: too many arguments for format
So it seems that GCC 4.5.1 and/or glibc don't support the "%hhd" and "%hhu" C99 format specifiers. If I run this program under a debugger, more than just the byte variables do end up being modified by the scanf()
calls.
Just for reference, I'm using the following command to compile:
"C:\MinGW\bin\gcc" -std=c99 -Wall -g -Ic:\MinGW\include -D_WIN32_WINNT=0x0500 "C:\temp\test.c" -lkernel32 -luser32 -lgdi32 -ladvapi32 -lshlwapi -loleaut32 -o "test".exe
Note that the various character-sized int input formats (that use "hh") in inttypes.h
only get compiled in if the C99 standard is specified - they're protected by:
#if defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L
The other format specifiers are compiled in even for C90 compiles.
So you won't get the "hh" formats unless you use the -std=c99
or -std=gnu99
options (but remember that they don't seem to work anyway).
Update:
Of course! The reason the "hhd" and "hhu' specifiers aren't supported is because the MinGW runtime uses the scanf()
from Microsoft's msvcrt.dll
which doesn't know anything about the new stuff in C99's input formats. If you want to use these input formats, you'll need to use some other scanf()
implementation.
As mentioned in MinGW's inttypes.h
:
MS runtime scanf appears to treat "hh" as "h"
You could add the following after #include <inttypes.h>
:
#ifndef SCNd8
#define SCNd8 "hhd"
#endif
#ifndef SCNu8
#define SCNu8 "hhu"
#endif
Which should be appropriate for most platforms.
Clarification:
Where "most platforms" refers to platforms with a C99-compliant fscanf
/scanf
that can handle the hh
prefix for char
, not just the h
prefix for short
.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With