From 2e9a1f6b05e79f1b7de15d5ae64f3222d989e7e5 Mon Sep 17 00:00:00 2001 From: Paolo Carlini Date: Thu, 12 Feb 2004 18:24:07 +0000 Subject: [PATCH] PR libstdc++/13731 (final part: writev) 2004-02-12 Paolo Carlini PR libstdc++/13731 (final part: writev) * config/io/basic_file_stdio.cc (__gnu_internal::xwrite): New, a wrapper around writev() handling partial writes. (__basic_file::xwrite): Move to __gnu_internal and make static. (__basic_file::xsputn): Update call. (__basic_file::xsputn_2): Likewise. * config/io/basic_file_stdio.h (__basic_file::write): Don't declare, now static. From-SVN: r77717 --- libstdc++-v3/ChangeLog | 12 +++ libstdc++-v3/config/io/basic_file_stdio.cc | 88 ++++++++++++++-------- libstdc++-v3/config/io/basic_file_stdio.h | 3 - 3 files changed, 70 insertions(+), 33 deletions(-) diff --git a/libstdc++-v3/ChangeLog b/libstdc++-v3/ChangeLog index b74af678a17..b4a808445ae 100644 --- a/libstdc++-v3/ChangeLog +++ b/libstdc++-v3/ChangeLog @@ -1,3 +1,15 @@ +2004-02-12 Paolo Carlini + + PR libstdc++/13731 (final part: writev) + * config/io/basic_file_stdio.cc (__gnu_internal::xwrite): + New, a wrapper around writev() handling partial writes. + (__basic_file::xwrite): Move to __gnu_internal and make + static. + (__basic_file::xsputn): Update call. + (__basic_file::xsputn_2): Likewise. + * config/io/basic_file_stdio.h (__basic_file::write): + Don't declare, now static. + 2004-02-11 Stefan Olsson * docs/html/ext/mt_allocator.html: New. diff --git a/libstdc++-v3/config/io/basic_file_stdio.cc b/libstdc++-v3/config/io/basic_file_stdio.cc index 1419fdedf4b..f83b7a25f88 100644 --- a/libstdc++-v3/config/io/basic_file_stdio.cc +++ b/libstdc++-v3/config/io/basic_file_stdio.cc @@ -105,6 +105,60 @@ namespace __gnu_internal default: return 0; // invalid } } + + // Wrapper handling partial write. + static std::streamsize + xwrite(int __fd, const char* __s, std::streamsize __n) + { + std::streamsize __nleft = __n; + while (__nleft > 0) + { + const std::streamsize __ret = write(__fd, __s, __nleft); + if (__ret == -1L && errno == EINTR) + continue; + else if (__ret == -1L) + break; + __nleft -= __ret; + __s += __ret; + } + return __n - __nleft; + } + +#ifdef _GLIBCXX_HAVE_WRITEV + // Wrapper handling partial writev. + static std::streamsize + xwritev(int __fd, const char* __s1, std::streamsize __n1, + const char* __s2, std::streamsize __n2) + { + std::streamsize __ret; + + struct iovec __iov[2]; + __iov[0].iov_base = const_cast(__s1); + __iov[0].iov_len = __n1; + __iov[1].iov_base = const_cast(__s2); + __iov[1].iov_len = __n2; + + do + __ret = writev(__fd, __iov, 2); + while (__ret == -1L && errno == EINTR); + + if (__ret == -1L) + __ret = 0; + else if (__ret < __n1 + __n2) + { + if (__ret >= __n1) + { + const std::streamsize __off = __ret - __n1; + __ret += xwrite(__fd, __s2 + __off, __n2 - __off); + } + else + __ret += xwritev(__fd, __s1 + __ret, __n1 - __ret, + __s2, __n2); + } + + return __ret; + } +#endif } // namespace __gnu_internal namespace std @@ -201,27 +255,9 @@ namespace std return __ret; } - // Wrapper handling partial write. - streamsize - __basic_file::xwrite(const char* __s, streamsize __n) - { - streamsize __nleft = __n; - while (__nleft > 0) - { - const streamsize __ret = write(this->fd(), __s, __nleft); - if (__ret == -1L && errno == EINTR) - continue; - else if (__ret == -1L) - break; - __nleft -= __ret; - __s += __ret; - } - return __n - __nleft; - } - streamsize __basic_file::xsputn(const char* __s, streamsize __n) - { return __basic_file::xwrite(__s, __n); } + { return __gnu_internal::xwrite(this->fd(), __s, __n); } streamsize __basic_file::xsputn_2(const char* __s1, streamsize __n1, @@ -229,21 +265,13 @@ namespace std { streamsize __ret = 0; #ifdef _GLIBCXX_HAVE_WRITEV - struct iovec __iov[2]; - __iov[0].iov_base = const_cast(__s1); - __iov[0].iov_len = __n1; - __iov[1].iov_base = const_cast(__s2); - __iov[1].iov_len = __n2; - - do - __ret = writev(this->fd(), __iov, 2); - while (__ret == -1L && errno == EINTR); + __ret = __gnu_internal::xwritev(this->fd(), __s1, __n1, __s2, __n2); #else if (__n1) - __ret = __basic_file::xwrite(__s1, __n1); + __ret = __gnu_internal::xwrite(this->fd(), __s1, __n1); if (__ret == __n1) - __ret += __basic_file::xwrite(__s2, __n2); + __ret += __gnu_internal::xwrite(this->fd(), __s2, __n2); #endif return __ret; } diff --git a/libstdc++-v3/config/io/basic_file_stdio.h b/libstdc++-v3/config/io/basic_file_stdio.h index 9c0ccfd1bad..57ff4326e6b 100644 --- a/libstdc++-v3/config/io/basic_file_stdio.h +++ b/libstdc++-v3/config/io/basic_file_stdio.h @@ -83,9 +83,6 @@ namespace std ~__basic_file(); - streamsize - xwrite(const char* __s, streamsize __n); - streamsize xsputn(const char* __s, streamsize __n);