Date: Tue, 2 Mar 2004 12:33:57 -0800 From: "Jordan K. Hubbard" <jkh@queasyweasel.com> To: David Schultz <das@FreeBSD.ORG> Cc: standards@FreeBSD.ORG Subject: Re: Another conformance question... This time fputs(). Message-ID: <EE5F13CE-6C88-11D8-9000-000393BB9222@queasyweasel.com> In-Reply-To: <20040302165323.GA17665@VARK.homeunix.com> References: <F648D56F-6C28-11D8-9000-000393BB9222@queasyweasel.com> <20040302165323.GA17665@VARK.homeunix.com>
next in thread | previous in thread | raw e-mail | index | archive | help
--Apple-Mail-6--979293609 Content-Transfer-Encoding: 7bit Content-Type: text/plain; charset=US-ASCII; format=flowed On Mar 2, 2004, at 8:53 AM, David Schultz wrote: > Nice catch. I think the wording of POSIX suggests that the error > code is supposed to be EBADF, which is returned if ``the file > descriptor [...] is not a valid file descriptor for writing.'' > Although you could argue that the standard is wrong, Linux and > Solaris return EBADF, so we probably should, too. Yeah, that's the approach I just took. Thanks. > (By the way, there are a few other cantwrite() calls in libc that > probably have the same bug.) I've been looking at those... The ones used by the vfprintf() internals look like a no-brainer since the man page says: In addition to the errors documented for the write(2) system call, the printf() family of functions may fail if: [ ... ] Since we've cleverly short-circuited the write(2) calls with the cantwrite() checks, one assumes we're on the hook to emulate what would have happened if we actually had called write(2). I was sort of on the fence about the call in __swbuf(), which is used in the include/stdio.h macros to implement the putc()/putc_unlocked() internals, but I guess there's really no question about it either since http://www.opengroup.org/onlinepubs/007904975/functions/fputc.html is pretty clear that EBADF is expected in the same case. With the full understanding that tabs are going to get smashed in this paste but don't represent what I'd actually commit, does anyone have any objection to the following diff? Index: stdio/vfprintf.c =================================================================== RCS file: /home/ncvs/src/lib/libc/stdio/vfprintf.c,v retrieving revision 1.62 diff -u -r1.62 vfprintf.c --- stdio/vfprintf.c 18 Jan 2004 10:32:49 -0000 1.62 +++ stdio/vfprintf.c 2 Mar 2004 20:31:15 -0000 @@ -50,6 +50,7 @@ #include <sys/types.h> #include <ctype.h> +#include <errno.h> #include <limits.h> #include <locale.h> #include <stddef.h> @@ -641,8 +642,10 @@ decimal_point = localeconv()->decimal_point; #endif /* sorry, fprintf(read_only_file, "") returns EOF, not 0 */ - if (cantwrite(fp)) + if (cantwrite(fp)) { + errno = EBADF; return (EOF); + } /* optimise fprintf(stderr) (and other unbuffered Unix files) */ if ((fp->_flags & (__SNBF|__SWR|__SRW)) == (__SNBF|__SWR) && Index: stdio/vfwprintf.c =================================================================== RCS file: /home/ncvs/src/lib/libc/stdio/vfwprintf.c,v retrieving revision 1.16 diff -u -r1.16 vfwprintf.c --- stdio/vfwprintf.c 23 Jan 2004 22:48:16 -0000 1.16 +++ stdio/vfwprintf.c 2 Mar 2004 20:31:16 -0000 @@ -54,6 +54,7 @@ #include <sys/types.h> #include <ctype.h> +#include <errno.h> #include <limits.h> #include <locale.h> #include <stdarg.h> @@ -646,8 +647,10 @@ #endif convbuf = NULL; /* sorry, fwprintf(read_only_file, L"") returns WEOF, not 0 */ - if (cantwrite(fp)) + if (cantwrite(fp)) { + errno = EBADF; return (EOF); + } /* optimise fprintf(stderr) (and other unbuffered Unix files) */ if ((fp->_flags & (__SNBF|__SWR|__SRW)) == (__SNBF|__SWR) && Index: stdio/wbuf.c =================================================================== RCS file: /home/ncvs/src/lib/libc/stdio/wbuf.c,v retrieving revision 1.10 diff -u -r1.10 wbuf.c --- stdio/wbuf.c 13 Aug 2002 09:30:41 -0000 1.10 +++ stdio/wbuf.c 2 Mar 2004 20:31:16 -0000 @@ -40,6 +40,7 @@ #include <sys/cdefs.h> __FBSDID("$FreeBSD: src/lib/libc/stdio/wbuf.c,v 1.10 2002/08/13 09:30:41 tjr Exp $"); +#include <errno.h> #include <stdio.h> #include "local.h" @@ -65,8 +66,10 @@ * calls might wrap _w from negative to positive. */ fp->_w = fp->_lbfsize; - if (cantwrite(fp)) + if (cantwrite(fp)) { + errno = EBADF; return (EOF); + } c = (unsigned char)c; ORIENT(fp, -1); > I'll bet the isatty() call in __smakebuf() is setting errno > because /dev/null doesn't support the relevant ioctl. Note that > rc=0 so libc is ignoring the error and completing the write, even > though it spuriously sets errno. In any case, you're right that > this is an unrelated bug. No, I don't think that's it (see reply to bde on -arch). I've looked at isatty() and it's fine, it just calls tcgetattr() which sets errno to ENOTTY correctly (I checked). > ASCII stupid question, get a stupid ANSI. UGH!! :-) -- Jordan K. Hubbard Engineering Manager, BSD technology group Apple Computer --Apple-Mail-6--979293609--
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?EE5F13CE-6C88-11D8-9000-000393BB9222>