Message ID | 20240729123225.63285-1-arjun@redhat.com |
---|---|
State | New |
Headers | show |
Series | [v2] manual/stdio: Clarify putc and putwc | expand |
* Arjun Shankar: > The manual entry for `putc' described what "most systems" do instead of > describing the glibc implementation and its guarantees. This commit > fixes that by warning that putc may be implemented as a macro that > double-evaluates `stream', and removing the performance claim. > > Even though the current `putc' implementation does not double-evaluate > `stream', offering this obscure guarantee as an extension to what > POSIX allows does not seem very useful. > > The entry for `putwc' is also edited to bring it in line with `putc'. > --- > v1: https://sourceware.org/pipermail/libc-alpha/2024-July/158676.html > Changes since v1: Dropped the performance claim. > --- > manual/stdio.texi | 12 ++++++------ > 1 file changed, 6 insertions(+), 6 deletions(-) > > diff --git a/manual/stdio.texi b/manual/stdio.texi > index f5e289d58a..f9529a098d 100644 > --- a/manual/stdio.texi > +++ b/manual/stdio.texi > @@ -903,21 +903,21 @@ This function is a GNU extension. > @deftypefun int putc (int @var{c}, FILE *@var{stream}) > @standards{ISO, stdio.h} > @safety{@prelim{}@mtsafe{}@asunsafe{@asucorrupt{}}@acunsafe{@acucorrupt{} @aculock{}}} > -This is just like @code{fputc}, except that most systems implement it as > +This is just like @code{fputc}, except that it may be implemented as > a macro, making it faster. One consequence is that it may evaluate the > @var{stream} argument more than once, which is an exception to the > -general rule for macros. @code{putc} is usually the best function to > -use for writing a single character. > +general rule for macros. Therefore, @var{stream} should never be an > +expression with side-effects. > @end deftypefun > > @deftypefun wint_t putwc (wchar_t @var{wc}, FILE *@var{stream}) > @standards{ISO, wchar.h} > @safety{@prelim{}@mtsafe{}@asunsafe{@asucorrupt{}}@acunsafe{@acucorrupt{} @aculock{}}} > -This is just like @code{fputwc}, except that it can be implement as > +This is just like @code{fputwc}, except that it may be implemented as > a macro, making it faster. One consequence is that it may evaluate the > @var{stream} argument more than once, which is an exception to the > -general rule for macros. @code{putwc} is usually the best function to > -use for writing a single wide character. > +general rule for macros. Therefore, @var{stream} should never be an > +expression with side-effects. > @end deftypefun > > @deftypefun int putc_unlocked (int @var{c}, FILE *@var{stream}) Looks okay to me. Reviewed-by: Florian Weimer <fweimer@redhat.com> Thanks, Florian
On 2024-07-29 14:30:59 +0200, Arjun Shankar wrote: > diff --git a/manual/stdio.texi b/manual/stdio.texi > index f5e289d58a..f9529a098d 100644 > --- a/manual/stdio.texi > +++ b/manual/stdio.texi > @@ -903,21 +903,21 @@ This function is a GNU extension. > @deftypefun int putc (int @var{c}, FILE *@var{stream}) > @standards{ISO, stdio.h} > @safety{@prelim{}@mtsafe{}@asunsafe{@asucorrupt{}}@acunsafe{@acucorrupt{} @aculock{}}} > -This is just like @code{fputc}, except that most systems implement it as > +This is just like @code{fputc}, except that it may be implemented as > a macro, making it faster. One consequence is that it may evaluate the > @var{stream} argument more than once, which is an exception to the > -general rule for macros. @code{putc} is usually the best function to > -use for writing a single character. > +general rule for macros. Therefore, @var{stream} should never be an > +expression with side-effects. I think that the word "consequence" is misleading. This is not just a consequence (any function may be implemented as a macro, BTW). This is also because the C standard explicitly allows "stream" to be evaluated more than once (this is an exception to the general rule). On the opposite, it is guaranteed that the argument "c" will be evaluated exactly once. > @end deftypefun > > @deftypefun wint_t putwc (wchar_t @var{wc}, FILE *@var{stream}) > @standards{ISO, wchar.h} > @safety{@prelim{}@mtsafe{}@asunsafe{@asucorrupt{}}@acunsafe{@acucorrupt{} @aculock{}}} > -This is just like @code{fputwc}, except that it can be implement as > +This is just like @code{fputwc}, except that it may be implemented as > a macro, making it faster. One consequence is that it may evaluate the > @var{stream} argument more than once, which is an exception to the > -general rule for macros. @code{putwc} is usually the best function to > -use for writing a single wide character. > +general rule for macros. Therefore, @var{stream} should never be an > +expression with side-effects. Ditto.
On Jul 29 2024, Vincent Lefevre wrote: > On 2024-07-29 14:30:59 +0200, Arjun Shankar wrote: >> diff --git a/manual/stdio.texi b/manual/stdio.texi >> index f5e289d58a..f9529a098d 100644 >> --- a/manual/stdio.texi >> +++ b/manual/stdio.texi >> @@ -903,21 +903,21 @@ This function is a GNU extension. >> @deftypefun int putc (int @var{c}, FILE *@var{stream}) >> @standards{ISO, stdio.h} >> @safety{@prelim{}@mtsafe{}@asunsafe{@asucorrupt{}}@acunsafe{@acucorrupt{} @aculock{}}} >> -This is just like @code{fputc}, except that most systems implement it as >> +This is just like @code{fputc}, except that it may be implemented as >> a macro, making it faster. One consequence is that it may evaluate the >> @var{stream} argument more than once, which is an exception to the >> -general rule for macros. @code{putc} is usually the best function to >> -use for writing a single character. >> +general rule for macros. Therefore, @var{stream} should never be an >> +expression with side-effects. > > I think that the word "consequence" is misleading. This is not just a > consequence (any function may be implemented as a macro, BTW). This is > also because the C standard explicitly allows "stream" to be evaluated > more than once (this is an exception to the general rule). The same is true for the getc and getwc functions.
> >> -This is just like @code{fputc}, except that most systems implement it as > >> +This is just like @code{fputc}, except that it may be implemented as > >> a macro, making it faster. One consequence is that it may evaluate the > >> @var{stream} argument more than once, which is an exception to the > >> -general rule for macros. @code{putc} is usually the best function to > >> -use for writing a single character. > >> +general rule for macros. Therefore, @var{stream} should never be an > >> +expression with side-effects. > > > > I think that the word "consequence" is misleading. This is not just a > > consequence (any function may be implemented as a macro, BTW). This is > > also because the C standard explicitly allows "stream" to be evaluated > > more than once (this is an exception to the general rule). Thanks Vincent. Looks like I should have waited a bit before pushing this. My plan now is to change: > This is just like @code{fputc}, except that it may be implemented as > a macro, making it faster. One consequence is that it may evaluate the > @var{stream} argument more than once, which is an exception to the > general rule for macros. To: "This is just like @code{fputc}, except that it may be implemented as a macro and may evaluate the @var{stream} argument more than once, which is an exception to the general rule for macros." > The same is true for the getc and getwc functions. Thanks Andreas. I'll look at them as well. Cheers!
* Arjun Shankar: >> >> -This is just like @code{fputc}, except that most systems implement it as >> >> +This is just like @code{fputc}, except that it may be implemented as >> >> a macro, making it faster. One consequence is that it may evaluate the >> >> @var{stream} argument more than once, which is an exception to the >> >> -general rule for macros. @code{putc} is usually the best function to >> >> -use for writing a single character. >> >> +general rule for macros. Therefore, @var{stream} should never be an >> >> +expression with side-effects. >> > >> > I think that the word "consequence" is misleading. This is not just a >> > consequence (any function may be implemented as a macro, BTW). This is >> > also because the C standard explicitly allows "stream" to be evaluated >> > more than once (this is an exception to the general rule). > > Thanks Vincent. Looks like I should have waited a bit before pushing this. > > My plan now is to change: > >> This is just like @code{fputc}, except that it may be implemented as >> a macro, making it faster. One consequence is that it may evaluate the >> @var{stream} argument more than once, which is an exception to the >> general rule for macros. > > To: > > "This is just like @code{fputc}, except that it may be implemented as > a macro and may evaluate the @var{stream} argument more than once, > which is an exception to the general rule for macros." It's still confusing. The general rule for macros is that they still need to behave like function calls and evaluate each argument only once. What about this? | This is just like @code{fputc}, except that it may be implemented as a | macro which evaluates the @var{stream} argument more than once. Thanks, Florian
diff --git a/manual/stdio.texi b/manual/stdio.texi index f5e289d58a..f9529a098d 100644 --- a/manual/stdio.texi +++ b/manual/stdio.texi @@ -903,21 +903,21 @@ This function is a GNU extension. @deftypefun int putc (int @var{c}, FILE *@var{stream}) @standards{ISO, stdio.h} @safety{@prelim{}@mtsafe{}@asunsafe{@asucorrupt{}}@acunsafe{@acucorrupt{} @aculock{}}} -This is just like @code{fputc}, except that most systems implement it as +This is just like @code{fputc}, except that it may be implemented as a macro, making it faster. One consequence is that it may evaluate the @var{stream} argument more than once, which is an exception to the -general rule for macros. @code{putc} is usually the best function to -use for writing a single character. +general rule for macros. Therefore, @var{stream} should never be an +expression with side-effects. @end deftypefun @deftypefun wint_t putwc (wchar_t @var{wc}, FILE *@var{stream}) @standards{ISO, wchar.h} @safety{@prelim{}@mtsafe{}@asunsafe{@asucorrupt{}}@acunsafe{@acucorrupt{} @aculock{}}} -This is just like @code{fputwc}, except that it can be implement as +This is just like @code{fputwc}, except that it may be implemented as a macro, making it faster. One consequence is that it may evaluate the @var{stream} argument more than once, which is an exception to the -general rule for macros. @code{putwc} is usually the best function to -use for writing a single wide character. +general rule for macros. Therefore, @var{stream} should never be an +expression with side-effects. @end deftypefun @deftypefun int putc_unlocked (int @var{c}, FILE *@var{stream})