2 # Check whether getcwd has the bug that it succeeds for a working directory
3 # longer than PATH_MAX, yet returns a truncated directory name.
4 # If so, arrange to compile the wrapper function.
6 # This is necessary for at least GNU libc on linux-2.4.19 and 2.4.20.
7 # I've heard that this is due to a Linux kernel bug, and that it has
8 # been fixed between 2.4.21-pre3 and 2.4.21-pre4. */
10 # Copyright (C) 2003, 2004 Free Software Foundation, Inc.
12 # This program is free software; you can redistribute it and/or modify
13 # it under the terms of the GNU General Public License as published by
14 # the Free Software Foundation; either version 2, or (at your option)
17 # This program is distributed in the hope that it will be useful,
18 # but WITHOUT ANY WARRANTY; without even the implied warranty of
19 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 # GNU General Public License for more details.
22 # You should have received a copy of the GNU General Public License
23 # along with this program; if not, write to the Free Software Foundation,
24 # Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
28 AC_DEFUN([GL_FUNC_GETCWD_PATH_MAX],
30 AC_CHECK_DECLS([getcwd])
31 AC_CACHE_CHECK([whether getcwd properly handles paths longer than PATH_MAX],
32 gl_cv_func_getcwd_vs_path_max,
34 # Arrange for deletion of the temporary directory this test creates.
35 ac_clean_files="$ac_clean_files confdir3"
36 AC_RUN_IFELSE([AC_LANG_SOURCE([[
42 #include <sys/types.h>
44 /* Don't get link errors because mkdir is redefined to rpl_mkdir. */
51 /* The extra casts work around common compiler bugs. */
52 #define TYPE_SIGNED(t) (! ((t) 0 < (t) -1))
53 /* The outer cast is needed to work around a bug in Cray C 5.0.3.0.
54 It is necessary at least when t == time_t. */
55 #define TYPE_MINIMUM(t) ((t) (TYPE_SIGNED (t) \
56 ? ~ (t) 0 << (sizeof (t) * CHAR_BIT - 1) : (t) 0))
57 #define TYPE_MAXIMUM(t) ((t) (~ (t) 0 - TYPE_MINIMUM (t)))
60 # define INT_MAX TYPE_MAXIMUM (int)
63 /* The length of this name must be 8. */
64 #define DIR_NAME "confdir3"
70 /* The Hurd doesn't define this, so getcwd can't exhibit the bug --
71 at least not on a local file system. And if we were to start worrying
72 about remote file systems, we'd have to enable the wrapper function
73 all of the time, just to be safe. That's not worth the cost. */
75 #elif INT_MAX - 9 <= PATH_MAX
76 /* The '9', above, comes from strlen (DIR_NAME) + 1. */
77 /* FIXME: Assuming there's a system for which this is true,
78 this should be done in a compile test. */
81 char buf[PATH_MAX + 20];
82 char *cwd = getcwd (buf, PATH_MAX);
90 cwd_len = strlen (cwd);
97 cwd_len += 1 + strlen (DIR_NAME);
98 /* If mkdir or chdir fails, be pessimistic and consider that
100 if (mkdir (DIR_NAME, 0700) < 0 || chdir (DIR_NAME) < 0)
105 if ((c = getcwd (buf, PATH_MAX)) == NULL)
107 /* This allows any failure to indicate there is no bug.
108 FIXME: check errno? */
111 if ((len = strlen (c)) != cwd_len)
121 /* Leaving behind such a deep directory is not polite.
122 So clean up here, right away, even though the driving
123 shell script would also clean up. */
127 /* Unlink first, in case the chdir failed. */
129 for (i = 0; i <= n_chdirs; i++)
131 if (chdir ("..") < 0)
141 [gl_cv_func_getcwd_vs_path_max=yes],
142 [gl_cv_func_getcwd_vs_path_max=no],
143 [gl_cv_func_getcwd_vs_path_max=no])])
145 if test $gl_cv_func_getcwd_vs_path_max = no; then
147 AC_DEFINE(getcwd, rpl_getcwd,
148 [Define to rpl_getcwd if the wrapper function should be used.])