diff -ruN a/newlib/libc/stdio/fvwrite.c b/newlib/libc/stdio/fvwrite.c --- a/newlib/libc/stdio/fvwrite.c 2013-10-31 01:10:06.110679241 +0100 +++ b/newlib/libc/stdio/fvwrite.c 2013-10-31 19:58:15.828200705 +0100 @@ -21,6 +21,7 @@ #include #include #include +#include #include "local.h" #include "fvwrite.h" @@ -89,12 +90,14 @@ if (fp->_flags & __SNBF) { /* - * Unbuffered: write up to BUFSIZ bytes at a time. + * Unbuffered: split the buffer in the larger chunk that + * is less than INT_MAX, as some legacy code may expect + * int instead of size_t */ do { GETIOV (;); - w = fp->_write (ptr, fp->_cookie, p, MIN (len, BUFSIZ)); + w = fp->_write (ptr, fp->_cookie, p, MIN (len, INT_MAX)); if (w <= 0) goto err; p += w; @@ -177,30 +180,24 @@ fp->_p += w; w = len; /* but pretend copied all */ } - else if (fp->_p > fp->_bf._base && len > w) + else if (fp->_p > fp->_bf._base || len < fp->_bf._size) { - /* fill and flush */ + /* pass through the buffer */ + w = MIN (len, w); COPY (w); - /* fp->_w -= w; *//* unneeded */ + fp->_w -= w; fp->_p += w; - if (_fflush_r (ptr, fp)) + if (fp->_w == 0 && _fflush_r (ptr, fp)) goto err; } - else if (len >= (w = fp->_bf._size)) + else { /* write directly */ + w = ((int)MIN (len, INT_MAX)) / fp->_bf._size * fp->_bf._size; w = fp->_write (ptr, fp->_cookie, p, w); if (w <= 0) goto err; } - else - { - /* fill and done */ - w = len; - COPY (w); - fp->_w -= w; - fp->_p += w; - } p += w; len -= w; }