Hi Alex, On 9/20/20 11:40 PM, Alejandro Colomar wrote: > Reported-by: Michael Kerrisk <mtk.manpages@xxxxxxxxx> > Signed-off-by: Alejandro Colomar <colomar.6.4.3@xxxxxxxxx> > --- > Hi Michael, > > On 9/20/20 10:20 PM, Michael Kerrisk (man-pages) wrote: >> PS It occurs to me that this manual page is a suitable place >> to explain the general technique of casting integral system >> data types to [u]intmax_t for the purpose of printf(). Would >> you like to add this, Alex? > > Sure. Good idea! > > Hope you like the patch :) Good in principle, but some tweaks required. > man7/system_data_types.7 | 52 ++++++++++++++++++++++++++++++++++++++++ > 1 file changed, 52 insertions(+) > > diff --git a/man7/system_data_types.7 b/man7/system_data_types.7 > index 5128e1f01..1fcc09dae 100644 > --- a/man7/system_data_types.7 > +++ b/man7/system_data_types.7 > @@ -626,6 +626,58 @@ See also: > .SH NOTES > The structures described in this manual page shall contain, > at least, the members shown in their definition, in no particular order. > +.PP > +Most of the types described in this page don't have a corresponding s/types/integer types/ > +length modifier for the > +.BR printf (3) > +and the > +.BR scanf (3) > +families of functions. > +To print a value of a type that doesn't have a length modifier, > +it should be converted to > +.I intmax_t > +or > +.I uintmax_t > +by an explicit cast. > +To scan into a variable of a type that doesn't have a length modifier, s/a type/an integer/ > +an intermediate temporary variable of type > +.I intmax_t > +or > +.I uintmax_t > +should be used. Hmmm -- I wonder if we need to say something about range checking. I mean, what if time_t is narrower than intmax_t in the example below? (It's not, on my x86-64 system.) The problem of course is how to construct such a range check in the absence of any appropriate POSIX constants (e.g., there is no TIME_T_MAX). > +The example below shows how these conversions should be done. > +.SH EXAMPLES > +The program shown below scans from a string and prints a value stored in > +a variable of a type that doesn't have a length modifier. > +The appropriate conversions from and to > +.I intmax_t > +are used as explained in the notes section above: > +.PP > +.EX > +#include <stdint.h> > +#include <stdio.h> > +#include <stdlib.h> > +#include <time.h> > + > +int > +main (void) > +{ > + static const char *const str = "There are 60 s in an hour"; Either "60" needs to be 3600 or "hour" needs to be "minute". > + time_t secs; > + intmax_t tmp; > + > + /* Scan the number from the string into the temporary variable */ > + sscanf(str, "There are %jd", &tmp); > + > + /* Copy the value to the time_t variable secs */ > + secs = tmp; > + > + /* Print the value */ > + printf("There are %jd seconds in an hour!\en", (intmax_t) secs); See my previous comment. A change may be required in the line above. > + > + exit(EXIT_SUCCESS); > +} > +.EE > .SH SEE ALSO > .BR feature_test_macros (7), > .BR standards (7) Thanks, Michael -- Michael Kerrisk Linux man-pages maintainer; http://www.kernel.org/doc/man-pages/ Linux/UNIX System Programming Training: http://man7.org/training/