* wcwidth.m4 (gl_FUNC_WCWIDTH): Simplify by using AC_CHECK_DECLS.
[gnulib.git] / m4 / readdir.m4
1 #serial 9
2
3 # Copyright (C) 1997, 1999, 2000, 2001, 2002, 2003, 2006 Free Software
4 # Foundation, Inc.
5 #
6 # This file is free software; the Free Software Foundation
7 # gives unlimited permission to copy and/or distribute it,
8 # with or without modifications, as long as this notice is preserved.
9
10 dnl SunOS's readdir is broken in such a way that rm.c has to add extra code
11 dnl to test whether a NULL return value really means there are no more files
12 dnl in the directory.
13 dnl
14 dnl And the rm from coreutils-5.0 exposes a similar problem when there
15 dnl are 338 or more files in a directory on a Darwin-6.5 system
16 dnl
17 dnl Detect the problem by creating a directory containing 500 files (254 not
18 dnl counting . and .. is the minimum for SunOS, 338 for Darwin) and see
19 dnl if a loop doing `readdir; unlink' removes all of them.
20 dnl
21 dnl Define HAVE_WORKING_READDIR if readdir does *not* have this problem.
22
23 dnl Written by Jim Meyering.
24
25 AC_DEFUN([GL_FUNC_READDIR],
26 [dnl
27 AC_REQUIRE([AC_HEADER_DIRENT])
28 AC_CACHE_CHECK([for working readdir], gl_cv_func_working_readdir,
29   [dnl
30   # Arrange for deletion of the temporary directory this test creates, in
31   # case the test itself fails to delete everything -- as happens on Sunos.
32   ac_clean_files="$ac_clean_files conf-dir"
33
34   AC_TRY_RUN(
35 [#   include <stdio.h>
36 #   include <stdlib.h>
37 #   include <sys/types.h>
38 #   include <string.h>
39
40 #   ifdef HAVE_DIRENT_H
41 #    include <dirent.h>
42 #    define NLENGTH(direct) (strlen((direct)->d_name))
43 #   else /* not HAVE_DIRENT_H */
44 #    define dirent direct
45 #    define NLENGTH(direct) ((direct)->d_namlen)
46 #    ifdef HAVE_SYS_NDIR_H
47 #     include <sys/ndir.h>
48 #    endif /* HAVE_SYS_NDIR_H */
49 #    ifdef HAVE_SYS_DIR_H
50 #     include <sys/dir.h>
51 #    endif /* HAVE_SYS_DIR_H */
52 #    ifdef HAVE_NDIR_H
53 #     include <ndir.h>
54 #    endif /* HAVE_NDIR_H */
55 #   endif /* HAVE_DIRENT_H */
56
57 #   define DOT_OR_DOTDOT(Basename) \
58      (Basename[0] == '.' && (Basename[1] == '\0' \
59                              || (Basename[1] == '.' && Basename[2] == '\0')))
60
61 /* Don't try to use replacement mkdir; it wouldn't resolve at link time.  */
62 #   undef mkdir
63
64     static void
65     create_N_file_dir (const char *dir, size_t n_files)
66     {
67       unsigned int i;
68
69       if (mkdir (dir, 0700))
70         abort ();
71       if (chdir (dir))
72         abort ();
73
74       for (i = 0; i < n_files; i++)
75         {
76           char file_name[4];
77           FILE *out;
78
79           sprintf (file_name, "%03d", i);
80           out = fopen (file_name, "w");
81           if (!out)
82             abort ();
83           if (fclose (out) == EOF)
84             abort ();
85         }
86
87       if (chdir (".."))
88         abort ();
89     }
90
91     static void
92     remove_dir (const char *dir)
93     {
94       DIR *dirp;
95
96       if (chdir (dir))
97         abort ();
98
99       dirp = opendir (".");
100       if (dirp == NULL)
101         abort ();
102
103       while (1)
104         {
105           struct dirent *dp = readdir (dirp);
106           if (dp == NULL)
107             break;
108
109           if (DOT_OR_DOTDOT (dp->d_name))
110             continue;
111
112           if (unlink (dp->d_name))
113             abort ();
114         }
115       closedir (dirp);
116
117       if (chdir (".."))
118         abort ();
119
120       if (rmdir (dir))
121         exit (1);
122     }
123
124     int
125     main ()
126     {
127       const char *dir = "conf-dir";
128       create_N_file_dir (dir, 500);
129       remove_dir (dir);
130       exit (0);
131     }],
132   gl_cv_func_working_readdir=yes,
133   gl_cv_func_working_readdir=no,
134   gl_cv_func_working_readdir=no)])
135
136   if test $gl_cv_func_working_readdir = yes; then
137     AC_DEFINE(HAVE_WORKING_READDIR, 1,
138       [Define if readdir is found to work properly in some unusual cases. ])
139   fi
140 ])