>From c518eebf6a0d0b1f7edd66a01dac9b9d39fb81c3 Mon Sep 17 00:00:00 2001
From: Richard Jones
Date: Wed, 1 Oct 2008 13:54:44 +0100
Subject: [PATCH] fsync implementation.
---
MODULES.html.sh | 1 +
NEWS | 2 +
doc/posix-functions/fsync.texi | 8 ++--
lib/fsync.c | 62 ++++++++++++++++++++++++++++++++++++++++
lib/unistd.in.h | 17 +++++++++++
m4/fsync.m4 | 19 ++++++++++++
m4/unistd_h.m4 | 2 +
modules/fsync | 24 +++++++++++++++
modules/unistd | 2 +
9 files changed, 133 insertions(+), 4 deletions(-)
create mode 100644 lib/fsync.c
create mode 100644 m4/fsync.m4
create mode 100644 modules/fsync
diff --git a/MODULES.html.sh b/MODULES.html.sh
index afaf8ba..058125d 100755
--- a/MODULES.html.sh
+++ b/MODULES.html.sh
@@ -2110,6 +2110,7 @@ func_all_modules ()
func_module freopen
func_module fseek
func_module fseeko
+ func_module fsync
func_module ftell
func_module ftello
func_module ftruncate
diff --git a/NEWS b/NEWS
index ef04cf4..4c6edfe 100644
--- a/NEWS
+++ b/NEWS
@@ -6,6 +6,8 @@ User visible incompatible changes
Date Modules Changes
+2008-10-01 fsync This function has been implemented for Windows.
+
2008-09-28 sockets When using this module, you now need to link with
$(LIBSOCKET).
diff --git a/doc/posix-functions/fsync.texi b/doc/posix-functions/fsync.texi
index 405be40..fb88214 100644
--- a/doc/posix-functions/fsync.texi
+++ b/doc/posix-functions/fsync.texi
@@ -4,15 +4,15 @@
POSIX specification: @url{http://www.opengroup.org/susv3xsh/fsync.html}
-Gnulib module: ---
+Gnulib module: fsync
Portability problems fixed by Gnulib:
@itemize
address@hidden
+This function is missing on some platforms:
+mingw.
@end itemize
Portability problems not fixed by Gnulib:
@itemize
address@hidden
-This function is missing on some platforms:
-mingw.
@end itemize
diff --git a/lib/fsync.c b/lib/fsync.c
new file mode 100644
index 0000000..e353ebf
--- /dev/null
+++ b/lib/fsync.c
@@ -0,0 +1,62 @@
+/* Emulate fsync on platforms which lack it, primarily Windows and
+ cross-compilers like MinGW.
+
+ This is derived from sqlite3 sources and is in the public domain.
+
+ Written by Richard W.M. Jones
+*/
+
+#include
+#include
+
+#if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__
+
+/* _get_osfhandle */
+#include
+
+/* FlushFileBuffers */
+#define WIN32_LEAN_AND_MEAN
+#include
+
+#include
+
+int
+fsync (int fd)
+{
+ HANDLE h = (HANDLE) _get_osfhandle (fd);
+ DWORD err;
+
+ if (h == INVALID_HANDLE_VALUE)
+ {
+ errno = EBADF;
+ return -1;
+ }
+
+ if (!FlushFileBuffers (h))
+ {
+ /* Translate some Windows errors into rough approximations of Unix
+ * errors. MSDN is useless as usual - in this case it doesn't
+ * document the full range of errors.
+ */
+ err = GetLastError ();
+ switch (err)
+ {
+ /* eg. Trying to fsync a tty. */
+ case ERROR_INVALID_HANDLE:
+ errno = EINVAL;
+ break;
+
+ default:
+ errno = EIO;
+ }
+ return -1;
+ }
+
+ return 0;
+}
+
+#else /* Windows */
+
+#error "This platform lacks fsync function, and Gnulib doesn't provide a replacement. This is a bug in Gnulib."
+
+#endif /* !Windows */
diff --git a/lib/unistd.in.h b/lib/unistd.in.h
index e75b4cd..71eaa4d 100644
--- a/lib/unistd.in.h
+++ b/lib/unistd.in.h
@@ -140,6 +140,23 @@ extern int dup2 (int, int);
#endif
+#if @GNULIB_FSYNC@
+/* Synchronize changes to a file.
+ Return 0 if successful, otherwise -1 and errno set.
+ See POSIX:2001 specification
+ . */
+# if address@hidden@
+extern int fsync (int fd);
+# endif
+#elif defined GNULIB_POSIXCHECK
+# undef fsync
+# define fsync(fd) \
+ (GL_LINK_WARNING ("fsync is unportable - " \
+ "use gnulib module fsync for portability"), \
+ fsync (fd))
+#endif
+
+
#if @GNULIB_FTRUNCATE@
# if address@hidden@
/* Change the size of the file to which FD is opened to become equal to LENGTH.
diff --git a/m4/fsync.m4 b/m4/fsync.m4
new file mode 100644
index 0000000..eac7409
--- /dev/null
+++ b/m4/fsync.m4
@@ -0,0 +1,19 @@
+# fsync.m4 serial 1
+dnl Copyright (C) 2008 Free Software Foundation, Inc.
+dnl This file is free software; the Free Software Foundation
+dnl gives unlimited permission to copy and/or distribute it,
+dnl with or without modifications, as long as this notice is preserved.
+
+AC_DEFUN([gl_FUNC_FSYNC],
+[
+ AC_REQUIRE([gl_UNISTD_H_DEFAULTS])
+ AC_CHECK_FUNCS_ONCE([fsync])
+ if test $ac_cv_func_fsync = no; then
+ HAVE_FSYNC=0
+ AC_LIBOBJ([fsync])
+ gl_PREREQ_FSYNC
+ fi
+])
+
+# Prerequisites of lib/fsync.c.
+AC_DEFUN([gl_PREREQ_FSYNC], [:])
diff --git a/m4/unistd_h.m4 b/m4/unistd_h.m4
index 0e76a52..9e9a56b 100644
--- a/m4/unistd_h.m4
+++ b/m4/unistd_h.m4
@@ -36,6 +36,7 @@ AC_DEFUN([gl_UNISTD_H_DEFAULTS],
GNULIB_DUP2=0; AC_SUBST([GNULIB_DUP2])
GNULIB_ENVIRON=0; AC_SUBST([GNULIB_ENVIRON])
GNULIB_FCHDIR=0; AC_SUBST([GNULIB_FCHDIR])
+ GNULIB_FSYNC=0; AC_SUBST([GNULIB_FSYNC])
GNULIB_FTRUNCATE=0; AC_SUBST([GNULIB_FTRUNCATE])
GNULIB_GETCWD=0; AC_SUBST([GNULIB_GETCWD])
GNULIB_GETLOGIN_R=0; AC_SUBST([GNULIB_GETLOGIN_R])
@@ -48,6 +49,7 @@ AC_DEFUN([gl_UNISTD_H_DEFAULTS],
GNULIB_WRITE=0; AC_SUBST([GNULIB_WRITE])
dnl Assume proper GNU behavior unless another module says otherwise.
HAVE_DUP2=1; AC_SUBST([HAVE_DUP2])
+ HAVE_FSYNC=1; AC_SUBST([HAVE_FSYNC])
HAVE_FTRUNCATE=1; AC_SUBST([HAVE_FTRUNCATE])
HAVE_GETPAGESIZE=1; AC_SUBST([HAVE_GETPAGESIZE])
HAVE_READLINK=1; AC_SUBST([HAVE_READLINK])
diff --git a/modules/fsync b/modules/fsync
new file mode 100644
index 0000000..3de3ee3
--- /dev/null
+++ b/modules/fsync
@@ -0,0 +1,24 @@
+Description:
+fsync(2) function: synchronize writes to a file.
+
+Files:
+lib/fsync.c
+m4/fsync.m4
+
+Depends-on:
+unistd
+
+configure.ac:
+gl_FUNC_FSYNC
+gl_UNISTD_MODULE_INDICATOR([fsync])
+
+Makefile.am:
+
+Include:
+
+
+License:
+Public Domain
+
+Maintainer:
+Richard W.M. Jones, Jim Meyering
diff --git a/modules/unistd b/modules/unistd
index 9410778..efd97b5 100644
--- a/modules/unistd
+++ b/modules/unistd
@@ -28,6 +28,7 @@ unistd.h: unistd.in.h
-e 's|@''GNULIB_DUP2''@|$(GNULIB_DUP2)|g' \
-e 's|@''GNULIB_ENVIRON''@|$(GNULIB_ENVIRON)|g' \
-e 's|@''GNULIB_FCHDIR''@|$(GNULIB_FCHDIR)|g' \
+ -e 's|@''GNULIB_FSYNC''@|$(GNULIB_FSYNC)|g' \
-e 's|@''GNULIB_FTRUNCATE''@|$(GNULIB_FTRUNCATE)|g' \
-e 's|@''GNULIB_GETCWD''@|$(GNULIB_GETCWD)|g' \
-e 's|@''GNULIB_GETLOGIN_R''@|$(GNULIB_GETLOGIN_R)|g' \
@@ -39,6 +40,7 @@ unistd.h: unistd.in.h
-e 's|@''GNULIB_UNISTD_H_SIGPIPE''@|$(GNULIB_UNISTD_H_SIGPIPE)|g' \
-e 's|@''GNULIB_WRITE''@|$(GNULIB_WRITE)|g' \
-e 's|@''HAVE_DUP2''@|$(HAVE_DUP2)|g' \
+ -e 's|@''HAVE_FSYNC''@|$(HAVE_FSYNC)|g' \
-e 's|@''HAVE_FTRUNCATE''@|$(HAVE_FTRUNCATE)|g' \
-e 's|@''HAVE_GETPAGESIZE''@|$(HAVE_GETPAGESIZE)|g' \
-e 's|@''HAVE_READLINK''@|$(HAVE_READLINK)|g' \
--
1.6.0.1