summaryrefslogtreecommitdiff
path: root/pc/chdirsaf.c
diff options
context:
space:
mode:
Diffstat (limited to 'pc/chdirsaf.c')
-rw-r--r--pc/chdirsaf.c34
1 files changed, 34 insertions, 0 deletions
diff --git a/pc/chdirsaf.c b/pc/chdirsaf.c
new file mode 100644
index 0000000..0598f78
--- /dev/null
+++ b/pc/chdirsaf.c
@@ -0,0 +1,34 @@
+/* A safer version of chdir, which returns back to the
+ initial working directory when the program exits. */
+
+#include <errno.h>
+#include <stdlib.h>
+#include <unistd.h>
+
+static char *initial_wd;
+
+static void
+restore_wd (void)
+{
+ chdir (initial_wd);
+}
+
+int
+chdir_safer (char const *dir)
+{
+ if (! initial_wd)
+ {
+ size_t s;
+ for (s = 256; ! (initial_wd = getcwd (0, s)); s *= 2)
+ if (errno != ERANGE)
+ return -1;
+ if (atexit (restore_wd) != 0)
+ {
+ free (initial_wd);
+ initial_wd = 0;
+ return -1;
+ }
+ }
+
+ return chdir (dir);
+}