Printing size_t using printf in GNU systems

266 Views Asked by At

While I was reading this article, I came across this paragraph:

Similarly, don’t make any effort to cater to the possibility that long will be smaller than predefined types like size_t. For example, the following code is ok:

printf ("size = %lu\n", (unsigned long) sizeof array);
printf ("diff = %ld\n", (long) (pointer2 - pointer1));

1989 Standard C requires this to work, and we know of only one counterexample: 64-bit programs on Microsoft Windows. We will leave it to those who want to port GNU programs to that environment to figure out how to do it.

Does really the 1989 Standard C allow that code?

1

There are 1 best solutions below

3
On BEST ANSWER

The question as asked:

Does really the 1989 Standard C allow that code?

Yes, if by "allow" we mean "this will compile and run, doing something reasonable and not triggering undefined behavior" (and not "this will do what I want"). The two cases are slightly different.

For size_t, the result will be truncated if it is too large. For ptrdiff_t, the result will be implementation-defined if it is too large.

However, recent versions of Visual Studio (_MSC_VER >= 1800) support the z and t conversions (necessary for C++11 support anyway), so you can use:

size_t size;
printf("size = %zu\n", size);
ptrdiff_t diff;
printf("diff = %td\n", diff);

This will also work on other systems (GNU, BSD, Darwin). For older versions of Visual Studio there are alternatives, but it would require using a different format string on different platforms.

A note on GNU coding standards

The GNU coding standards are for the GNU organization, which has some very specific goals and does not care much about supporting Windows. I would take their coding standards with a grain of salt, unless you have a specific reason to follow them (for example, you want your project to become a GNU project in the future).