C++ Logo

std-proposals

Advanced search

Re: [std-proposals] Type-safe printf and auto

From: Alejandro Colomar <alx.manpages_at_[hidden]>
Date: Mon, 13 Mar 2023 01:15:16 +0100
Hi Robin

On 3/13/23 01:05, Robin Rowe via Std-Proposals wrote:
> > to get printf() to do what you're suggesting. I have
> > serious doubts it can even be made to do what you want in C
>
> Interesting, Thiago. Why not?
>
> > What makes you think that it's a small change to printf?
>
> Am basing my thinking on the fact that modern C compilers warn on type
> mismatch in printf, even say what the type is and what the right flag
> would be.
>
> > If they are using that in C++, at the next refactoring opportunity,
> > they should update to std::format and std::print, dispensing of the
> > printf() code in the first place.
>
> No, often best to not replace working legacy C code with fresh C++ code
> to do the same thing. Too expensive.
>
> I've been refactoring legacy code for decades, yet can't recall a
> "refactoring opportunity". I'm just fixing new warnings in old code
> generated by improved compilers. Yes, I can cast to (int) to silence
> such warnings. But if being cavalier, it would be quicker to silence the
> warning systemwide using a compiler flag. To respect the warning,
> correct it without a cast, is the goal.

No, that's not silencing a warning. That's fixing the bug. That's one
of the few places where a cast is the right thing. The cast converts
the value to the correct type, and not doing the cast is a bug, and it
could be disastrous if the type is not of the same width that printf(3)
expects. The right way to print something that doesn't have a
printf(3) specifier is to transform it to [u]intmax_t via a cast (in
C++ you can use some less-aggressive cast) and print it with the "j"
modifier. It's not a workaround, but rather the only correct way to do
it.

Here's a small part of the system_data_types(7) manual page:
<https://mirrors.edge.kernel.org/pub/linux/docs/man-pages/book/man-pages-6.03.pdf#system_data_types_7>

       Most of the integer types described in this page don’t have a
       corresponding length modifier for the printf(3) and the
       scanf(3) families of functions. To print a value of an integer
       type that doesn’t have a length modifier, it should be con‐
       verted to intmax_t or uintmax_t by an explicit cast.

And you could also have a look at the example program at the bottom of
that page.

Regards,

Alex.

Received on 2023-03-13 00:15:19