Enclose definitions in #if for POSIX-draft like API.
[gnulib.git] / lib / utime.c
index f7107ab..9ddb8b8 100644 (file)
@@ -1,8 +1,9 @@
-/* Copyright (C) 1998, 2001, 2002, 2003 Free Software Foundation, Inc.
+/* Copyright (C) 1998, 2001, 2002, 2003, 2004, 2006 Free Software
+   Foundation, Inc.
 
 
-   This program is free software; you can redistribute it and/or modify it
+   This program is free software: you can redistribute it and/or modify it
    under the terms of the GNU General Public License as published by the
    under the terms of the GNU General Public License as published by the
-   Free Software Foundation; either version 2, or (at your option) any
+   Free Software Foundation; either version 3 of the License, or any
    later version.
 
    This program is distributed in the hope that it will be useful,
    later version.
 
    This program is distributed in the hope that it will be useful,
    GNU General Public License for more details.
 
    You should have received a copy of the GNU General Public License
    GNU General Public License for more details.
 
    You should have received a copy of the GNU General Public License
-   along with this program; if not, write to the Free Software Foundation,
-   Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
+   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
 
 /* derived from a function in touch.c */
 
 
 /* derived from a function in touch.c */
 
-#ifdef HAVE_CONFIG_H
-# include <config.h>
-#endif
+#include <config.h>
 #undef utime
 
 #include <sys/types.h>
 #undef utime
 
 #include <sys/types.h>
 # include <utime.h>
 #endif
 
 # include <utime.h>
 #endif
 
+#if !HAVE_UTIMES_NULL
+# include <sys/stat.h>
+# include <fcntl.h>
+#endif
+
+#include <unistd.h>
+#include <errno.h>
+
 #include "full-write.h"
 #include "safe-read.h"
 
 #include "full-write.h"
 #include "safe-read.h"
 
@@ -40,6 +46,11 @@ struct utimbuf
 };
 #endif
 
 };
 #endif
 
+/* The results of open() in this file are not used with fchdir,
+   therefore save some unnecessary work in fchdir.c.  */
+#undef open
+#undef close
+
 /* Emulate utime (file, NULL) for systems (like 4.3BSD) that do not
    interpret it to set the access and modification times of FILE to
    the current time.  Return 0 if successful, -1 if not. */
 /* Emulate utime (file, NULL) for systems (like 4.3BSD) that do not
    interpret it to set the access and modification times of FILE to
    the current time.  Return 0 if successful, -1 if not. */
@@ -53,11 +64,12 @@ utime_null (const char *file)
   int fd;
   char c;
   int status = 0;
   int fd;
   char c;
   int status = 0;
-  struct stat sb;
+  struct stat st;
+  int saved_errno = 0;
 
   fd = open (file, O_RDWR);
   if (fd < 0
 
   fd = open (file, O_RDWR);
   if (fd < 0
-      || fstat (fd, &sb) < 0
+      || fstat (fd, &st) < 0
       || safe_read (fd, &c, sizeof c) == SAFE_READ_ERROR
       || lseek (fd, (off_t) 0, SEEK_SET) < 0
       || full_write (fd, &c, sizeof c) != sizeof c
       || safe_read (fd, &c, sizeof c) == SAFE_READ_ERROR
       || lseek (fd, (off_t) 0, SEEK_SET) < 0
       || full_write (fd, &c, sizeof c) != sizeof c
@@ -65,9 +77,23 @@ utime_null (const char *file)
         of patches, but that system doesn't use this code: it has utimes.
         || fsync (fd) < 0
       */
         of patches, but that system doesn't use this code: it has utimes.
         || fsync (fd) < 0
       */
-      || (st.st_size == 0 && ftruncate (fd, st.st_size) < 0)
-      || close (fd) < 0)
-    status = -1;
+      || (st.st_size == 0 && ftruncate (fd, st.st_size) < 0))
+    {
+      saved_errno = errno;
+      status = -1;
+    }
+
+  if (0 <= fd)
+    {
+      if (close (fd) < 0)
+       status = -1;
+
+      /* If there was a prior failure, use the saved errno value.
+        But if the only failure was in the close, don't change errno.  */
+      if (saved_errno)
+       errno = saved_errno;
+    }
+
   return status;
 #endif
 }
   return status;
 #endif
 }