diff options
author | Eric Blake <eblake@redhat.com> | 2011-06-14 03:56:05 +0000 |
---|---|---|
committer | Eric Blake <eblake@redhat.com> | 2011-06-14 03:56:05 +0000 |
commit | 4226571d7af401f07fea4797b93c2c888f5e9880 (patch) | |
tree | 27ea4ca682438a63d1cbbe4a7656ad083e99a9a8 /newlib/libc/stdio/wsetup.c | |
parent | 0fdbb2d0cdf86dddcd7c915ab3ef1172c704ecc2 (diff) | |
download | newlib-4226571d7af401f07fea4797b93c2c888f5e9880.zip newlib-4226571d7af401f07fea4797b93c2c888f5e9880.tar.gz newlib-4226571d7af401f07fea4797b93c2c888f5e9880.tar.bz2 |
printf: set errno for read-only stream
* libc/stdio/wsetup.c (__swsetup_r): Set errno on failure.
* libc/stdio/fvwrite.c (__sfvwrite_r): Simplify.
* libc/stdio/wbuf.c (__swbuf_r): Likewise.
* libc/stdio/local.h (cantwrite): Adjust comment.
Diffstat (limited to 'newlib/libc/stdio/wsetup.c')
-rw-r--r-- | newlib/libc/stdio/wsetup.c | 19 |
1 files changed, 15 insertions, 4 deletions
diff --git a/newlib/libc/stdio/wsetup.c b/newlib/libc/stdio/wsetup.c index dcbda0a..08ae70f 100644 --- a/newlib/libc/stdio/wsetup.c +++ b/newlib/libc/stdio/wsetup.c @@ -20,12 +20,13 @@ #include <_ansi.h> #include <stdio.h> #include <stdlib.h> +#include <errno.h> #include "local.h" /* * Various output routines call wsetup to be sure it is safe to write, * because either _flags does not include __SWR, or _buf is NULL. - * _wsetup returns 0 if OK to write, nonzero otherwise. + * _wsetup returns 0 if OK to write, nonzero and set errno otherwise. */ int @@ -44,7 +45,11 @@ _DEFUN(__swsetup_r, (ptr, fp), if ((fp->_flags & __SWR) == 0) { if ((fp->_flags & __SRW) == 0) - return EOF; + { + ptr->_errno = EBADF; + fp->_flags |= __SERR; + return EOF; + } if (fp->_flags & __SRD) { /* clobber any ungetc data */ @@ -62,7 +67,7 @@ _DEFUN(__swsetup_r, (ptr, fp), * A string I/O file should not explicitly allocate a buffer * unless asprintf is being used. */ - if (fp->_bf._base == NULL + if (fp->_bf._base == NULL && (!(fp->_flags & __SSTR) || (fp->_flags & __SMBF))) __smakebuf_r (ptr, fp); @@ -79,5 +84,11 @@ _DEFUN(__swsetup_r, (ptr, fp), else fp->_w = fp->_flags & __SNBF ? 0 : fp->_bf._size; - return (!fp->_bf._base && (fp->_flags & __SMBF)) ? EOF : 0; + if (!fp->_bf._base && (fp->_flags & __SMBF)) + { + /* __smakebuf_r set errno, but not flag */ + fp->_flags |= __SERR; + return EOF; + } + return 0; } |