[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[bug-gnulib] problems with standards.texi's "error" function
From: |
Paul Eggert |
Subject: |
[bug-gnulib] problems with standards.texi's "error" function |
Date: |
Fri, 03 Dec 2004 12:56:38 -0800 |
User-agent: |
Gnus/5.1006 (Gnus v5.10.6) Emacs/21.3 (gnu/linux) |
standards.texi says "you should declare functions to return @code{int}
rather than omitting the @code{int}" but it contains an example (the
"error" function) whose declaration does not specify the returned value.
Also, the advice about passing integer and pointer arguments
indiscriminately is obsolete. For example, this program:
#include <stdio.h>
void
error (s, a1, a2, a3)
char *s;
char *a1, *a2, *a3;
{
fprintf (stderr, "error: ");
fprintf (stderr, s, a1, a2, a3);
}
int
main (void)
{
long double i = 10;
error ("This should be 10: %Lg\n", i);
return 0;
}
outputs "error: This should be 10: 5.13142e-4937" on 64-bit SPARC
hosts (and I presume similar results obtain on many other modern
hosts).
I suggest rewording this example to advise using Standard C if you
want to have a reliable error function, and to point programmers at
the Gnulib error module to save them from having to reinvent the wheel
here.
Here is a proposed patch.
2004-12-03 Paul Eggert <address@hidden>
* standards.texi (CPU Portability): Declare a return type for "error".
Recommend using <stdarg.h> for programs that need "error", and suggest
the Gnulib error module.
*** standards.texi.~1.3.~ Mon Nov 29 16:42:46 2004
--- standards.texi Fri Dec 3 12:42:41 2004
***************
*** 2694,2705 ****
use prototypes (perhaps conditionalized to be active only in Standard C)
to make the code work on those systems.
! In certain cases, it is ok to pass integer and pointer arguments
indiscriminately to the same function, and use no prototype on any
! system. For example, many GNU programs have error-reporting functions
that pass their arguments along to @code{printf} and friends:
@example
error (s, a1, a2, a3)
char *s;
char *a1, *a2, *a3;
--- 2694,2707 ----
use prototypes (perhaps conditionalized to be active only in Standard C)
to make the code work on those systems.
! It used to be ok to pass integer and pointer arguments
indiscriminately to the same function, and use no prototype on any
! system. For example, many older versions of GNU programs
! have error-reporting functions
that pass their arguments along to @code{printf} and friends:
@example
+ void
error (s, a1, a2, a3)
char *s;
char *a1, *a2, *a3;
***************
*** 2710,2723 ****
@end example
@noindent
! In practice, this works on all machines, since a pointer is generally
! the widest possible kind of argument; it is much simpler than any
! ``correct'' alternative. Be sure @emph{not} to use a prototype for such
! functions.
!
! If you have decided to use Standard C, then you can instead define
@code{error} using @file{stdarg.h}, and pass the arguments along to
! @code{vfprintf}.
@cindex casting pointers to integers
Avoid casting pointers to integers if you can. Such casts greatly
--- 2712,2722 ----
@end example
@noindent
! This no longer works as well as it used to, since many modern machines
! have wider arguments than pointers. Nowadays it's better to define
@code{error} using @file{stdarg.h}, and pass the arguments along to
! @code{vfprintf}. For an example of this, please see the error module
! of @uref{http://www.gnu.org/software/gnulib/, Gnulib}.
@cindex casting pointers to integers
Avoid casting pointers to integers if you can. Such casts greatly
- [bug-gnulib] problems with standards.texi's "error" function,
Paul Eggert <=