From: Bruno Haible Date: Sat, 24 Sep 2011 02:07:12 +0000 (+0200) Subject: read: Support for MSVC 9. X-Git-Tag: v0.1~1763 X-Git-Url: http://erislabs.org.uk/gitweb/?a=commitdiff_plain;h=7bad64eadf0456e71707c843b2c83a44951683f2;p=gnulib.git read: Support for MSVC 9. * lib/unistd.in.h (read): Replace also when GNULIB_UNISTD_H_NONBLOCKING is not 1. * lib/read.c (read_nothrow): New function. (rpl_read): Define also when GNULIB_NONBLOCKING is not 1. Use read_nothrow. * m4/read.m4 (gl_FUNC_READ): Replace read if the platform has an invalid parameter handler. (gl_PREREQ_READ): New macro. * modules/read (Depends-on): Add msvc-inval. (configure.ac): Invoke gl_PREREQ_READ. * doc/posix-functions/read.texi: Mention the problem on MSVC. --- diff --git a/ChangeLog b/ChangeLog index cfe80269a..3c8a7a0a4 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,20 @@ 2011-09-23 Bruno Haible + read: Support for MSVC 9. + * lib/unistd.in.h (read): Replace also when GNULIB_UNISTD_H_NONBLOCKING + is not 1. + * lib/read.c (read_nothrow): New function. + (rpl_read): Define also when GNULIB_NONBLOCKING is not 1. Use + read_nothrow. + * m4/read.m4 (gl_FUNC_READ): Replace read if the platform has an + invalid parameter handler. + (gl_PREREQ_READ): New macro. + * modules/read (Depends-on): Add msvc-inval. + (configure.ac): Invoke gl_PREREQ_READ. + * doc/posix-functions/read.texi: Mention the problem on MSVC. + +2011-09-23 Bruno Haible + close: Support for MSVC 9. * lib/close.c: Include , msvc-inval.h. (close_nothrow): New function. diff --git a/doc/posix-functions/read.texi b/doc/posix-functions/read.texi index 34a20d735..ab625f5cd 100644 --- a/doc/posix-functions/read.texi +++ b/doc/posix-functions/read.texi @@ -9,6 +9,9 @@ Gnulib module: stdio, nonblocking Portability problems fixed by Gnulib module @code{stdio}, together with module @code{nonblocking}: @itemize @item +This function crashes when invoked with invalid arguments on some platforms: +MSVC 9. +@item When reading from a non-blocking pipe whose buffer is empty, this function fails with @code{errno} being set to @code{EINVAL} instead of @code{EAGAIN} on some platforms: diff --git a/lib/read.c b/lib/read.c index 61675af0d..98b78012d 100644 --- a/lib/read.c +++ b/lib/read.c @@ -20,25 +20,48 @@ /* Specification. */ #include -/* Replace this function only if module 'nonblocking' is requested. */ -#if GNULIB_NONBLOCKING +#if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__ -# if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__ +# include +# include -# include -# include +# define WIN32_LEAN_AND_MEAN /* avoid including junk */ +# include -# define WIN32_LEAN_AND_MEAN /* avoid including junk */ -# include +# include "msvc-inval.h" +# include "msvc-nothrow.h" -# include "msvc-nothrow.h" +# undef read + +# if HAVE_MSVC_INVALID_PARAMETER_HANDLER +static inline int +read_nothrow (int fd, void *buf, size_t count) +{ + int result; + + TRY_MSVC_INVAL + { + result = read (fd, buf, count); + } + CATCH_MSVC_INVAL + { + result = -1; + errno = EBADF; + } + DONE_MSVC_INVAL; + + return result; +} +# else +# define read_nothrow read +# endif ssize_t rpl_read (int fd, void *buf, size_t count) -#undef read { - ssize_t ret = read (fd, buf, count); + ssize_t ret = read_nothrow (fd, buf, count); +# if GNULIB_NONBLOCKING if (ret < 0 && GetLastError () == ERROR_NO_DATA) { @@ -54,8 +77,9 @@ rpl_read (int fd, void *buf, size_t count) errno = EAGAIN; } } +# endif + return ret; } -# endif #endif diff --git a/lib/unistd.in.h b/lib/unistd.in.h index 60a7530b4..79b86cb0f 100644 --- a/lib/unistd.in.h +++ b/lib/unistd.in.h @@ -1177,7 +1177,7 @@ _GL_WARN_ON_USE (pwrite, "pwrite is unportable - " /* Read up to COUNT bytes from file descriptor FD into the buffer starting at BUF. See the POSIX:2008 specification . */ -# if @REPLACE_READ@ && @GNULIB_UNISTD_H_NONBLOCKING@ +# if @REPLACE_READ@ # if !(defined __cplusplus && defined GNULIB_NAMESPACE) # undef read # define read rpl_read diff --git a/m4/read.m4 b/m4/read.m4 index 310e5ebcf..5d484b6f0 100644 --- a/m4/read.m4 +++ b/m4/read.m4 @@ -1,4 +1,4 @@ -# read.m4 serial 2 +# read.m4 serial 3 dnl Copyright (C) 2011 Free Software Foundation, Inc. dnl This file is free software; the Free Software Foundation dnl gives unlimited permission to copy and/or distribute it, @@ -7,6 +7,10 @@ dnl with or without modifications, as long as this notice is preserved. AC_DEFUN([gl_FUNC_READ], [ AC_REQUIRE([gl_UNISTD_H_DEFAULTS]) + AC_REQUIRE([gl_MSVC_INVAL]) + if test $HAVE_MSVC_INVALID_PARAMETER_HANDLER = 1; then + REPLACE_READ=1 + fi dnl This ifdef is just an optimization, to avoid performing a configure dnl check whose result is not used. It does not make the test of dnl GNULIB_UNISTD_H_NONBLOCKING or GNULIB_NONBLOCKING redundant. @@ -17,3 +21,9 @@ AC_DEFUN([gl_FUNC_READ], fi ]) ]) + +# Prerequisites of lib/read.c. +AC_DEFUN([gl_PREREQ_READ], +[ + AC_REQUIRE([AC_C_INLINE]) +]) diff --git a/modules/read b/modules/read index d72595583..baa758b2d 100644 --- a/modules/read +++ b/modules/read @@ -7,12 +7,14 @@ m4/read.m4 Depends-on: unistd +msvc-inval [test $REPLACE_READ = 1] msvc-nothrow [test $REPLACE_READ = 1] configure.ac: gl_FUNC_READ if test $REPLACE_READ = 1; then AC_LIBOBJ([read]) + gl_PREREQ_READ fi gl_UNISTD_MODULE_INDICATOR([read])