summaryrefslogtreecommitdiff
path: root/lib/save-cwd.c
diff options
context:
space:
mode:
authorPaul Eggert <eggert@cs.ucla.edu>2005-01-18 21:58:11 +0000
committerPaul Eggert <eggert@cs.ucla.edu>2005-01-18 21:58:11 +0000
commitd9203c96c70e64ae24a2f2d36e1ba80d79628dc5 (patch)
treee2234134cab629269d9b9d004cf167e40775f09b /lib/save-cwd.c
parent79fedf129cbfc69a04861c64e58ddff9f05d47e1 (diff)
downloadgnulib-d9203c96c70e64ae24a2f2d36e1ba80d79628dc5.tar.gz
* modules/chdir-long, modules/openat: New files.
* modules/save-cwd (Depends-on): Depend on chdir-long. (Makefile.am): Remove lib_SOURCES; now handled by AC_LIBSOURCES. * lib/save-cwd.c: Include "save-cwd.h" before other include files. (O_DIRECTORY): Remove; not needed here, since "." must be a directory. All uses removed. (save_cwd): Use __sgi || __sun, not sun || __sun. __sun is universal on Suns, and we also need to test for IRIX. Revamp code to use 'if' rather than '#if'. Avoid unnecessary comparison of cwd->desc to 0. Change the name of the robust chdir function from chdir to chdir_long. * lib/save-cwd.c: Include chdir-long.h rather than chdir.h. (restore_cwd): Use chdir_long, not chdir. * lib/chdir-long.c: Renamed from chdir.c. * lib/chdir-long.h: Renamed from chdir.h. [!defined PATH_MAX]: Define chdir_long to chdir on systems like the Hurd. * m4/chdir-long.m4, openat.m4: New files. * m4/save-cwd.m4 (gl_SAVE_CWD): Add AC_LIBSOURCES for save-cwd.c, save-cwd.h. Add AC_LIBOBJ for save-cwd.
Diffstat (limited to 'lib/save-cwd.c')
-rw-r--r--lib/save-cwd.c57
1 files changed, 28 insertions, 29 deletions
diff --git a/lib/save-cwd.c b/lib/save-cwd.c
index 93b1fe85ca..272f7421e9 100644
--- a/lib/save-cwd.c
+++ b/lib/save-cwd.c
@@ -21,6 +21,8 @@
# include "config.h"
#endif
+#include "save-cwd.h"
+
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
@@ -37,11 +39,7 @@
#include <errno.h>
-#ifndef O_DIRECTORY
-# define O_DIRECTORY 0
-#endif
-
-#include "save-cwd.h"
+#include "chdir-long.h"
#include "xgetcwd.h"
/* Record the location of the current working directory in CWD so that
@@ -64,48 +62,49 @@
int
save_cwd (struct saved_cwd *cwd)
{
+#if !HAVE_FCHDIR
+# undef fchdir
+# define fchdir(x) (abort (), 0)
+ bool have_working_fchdir = false;
+ bool fchdir_needs_testing = false;
+#elif (__sgi || __sun)
static bool have_working_fchdir = true;
+ bool fchdir_needs_testing = true;
+#else
+ bool have_working_fchdir = true;
+ bool fchdir_needs_testing = false;
+#endif
cwd->desc = -1;
cwd->name = NULL;
if (have_working_fchdir)
{
-#if HAVE_FCHDIR
- cwd->desc = open (".", O_RDONLY | O_DIRECTORY);
- if (cwd->desc < 0)
- cwd->desc = open (".", O_WRONLY | O_DIRECTORY);
+ cwd->desc = open (".", O_RDONLY);
if (cwd->desc < 0)
{
- cwd->name = xgetcwd ();
- return cwd->name ? 0 : -1;
+ cwd->desc = open (".", O_WRONLY);
+ if (cwd->desc < 0)
+ {
+ cwd->name = xgetcwd ();
+ return cwd->name ? 0 : -1;
+ }
}
-# if __sun__ || sun
/* On SunOS 4 and IRIX 5.3, fchdir returns EINVAL when auditing
is enabled, so we have to fall back to chdir. */
- if (fchdir (cwd->desc))
+ if (fchdir_needs_testing && fchdir (cwd->desc) != 0)
{
- if (errno == EINVAL)
- {
- close (cwd->desc);
- cwd->desc = -1;
- have_working_fchdir = false;
- }
- else
+ int saved_errno = errno;
+ close (cwd->desc);
+ cwd->desc = -1;
+ if (saved_errno != EINVAL)
{
- int saved_errno = errno;
- close (cwd->desc);
- cwd->desc = -1;
errno = saved_errno;
return -1;
}
+ have_working_fchdir = false;
}
-# endif /* __sun__ || sun */
-#else
-# define fchdir(x) (abort (), 0)
- have_working_fchdir = false;
-#endif
}
if (!have_working_fchdir)
@@ -127,7 +126,7 @@ restore_cwd (const struct saved_cwd *cwd)
if (0 <= cwd->desc)
return fchdir (cwd->desc);
else
- return chdir (cwd->name);
+ return chdir_long (cwd->name);
}
void