Subject: bug#12958: closed (Re: bug#12958: Assume POSIX 1003.1-1988 or later for dirent.h.)

From: [email-masked] (GNU bug Tracking System)
Date: Fri, 23 Nov 2012 09:12:03 +0000

Your bug report

#12958: Assume POSIX 1003.1-1988 or later for dirent.h.

which was filed against the emacs package, has been closed.

The explanation is attached below, along with your original report.
If you require more details, please reply to [email-masked].

-- 
12958: http://debbugs.gnu.org/cgi/bugreport.cgi?bug=12958
GNU Bug Tracking System
Contact [email-masked] with problems

Subject: Re: bug#12958: Assume POSIX 1003.1-1988 or later for dirent.h.
From: Paul Eggert <[email-masked]>
To: Eli Zaretskii <[email-masked]>
Cc: [email-masked]
Date: Fri, 23 Nov 2012 01:09:44 -0800
List-Id: <debbugs-submit.debbugs.gnu.org>

Thanks, Eli and Juanma.  I made both sets of changes and
installed it as trunk bzr 110986.

Subject: Assume POSIX 1003.1-1988 or later for dirent.h.
From: Paul Eggert <[email-masked]>
To: [email-masked]
Date: Wed, 21 Nov 2012 20:16:23 -0800
List-Id: <debbugs-submit.debbugs.gnu.org>

Here's a patch that I'd like to install to simplify Emacs based
on assuming that the underyling system supports POSIX 1003.1-1988
or later with respect to dirent.h.  This is universal these days
on GNUish hosts.  I'm CC'ing this to Eli, as this affects the
Microsoft port, by updating it a bit to use the POSIXish
"struct dirent" rather than the pre-POSIX "struct direct".
I have tested this on GNU/Linux but not on Microsoft.

=== modified file 'ChangeLog'
--- ChangeLog	2012-11-21 21:06:52 +0000
+++ ChangeLog	2012-11-22 04:03:01 +0000
@@ -1,3 +1,8 @@
+2012-11-22  Paul Eggert  <[email-masked]>
+
+	Assume POSIX 1003.1-1988 or later for dirent.h.
+	* configure.ac: Do not check for dirent.h or closdir.
+
 2012-11-21  Paul Eggert  <[email-masked]>
 
 	Assume POSIX 1003.1-1988 or later for unistd.h (Bug#12945).

=== modified file 'admin/CPP-DEFINES'
--- admin/CPP-DEFINES	2012-11-21 21:06:52 +0000
+++ admin/CPP-DEFINES	2012-11-22 04:03:01 +0000
@@ -118,7 +118,6 @@
 HAVE_CFSETSPEED
 HAVE_CLOCK_GETTIME
 HAVE_CLOCK_SETTIME
-HAVE_CLOSEDIR
 HAVE_COFF_H
 HAVE_COM_ERR_H
 HAVE_COPYSIGN
@@ -143,7 +142,6 @@
 HAVE_DEV_PTMX
 HAVE_DIALOGS
 HAVE_DIFFTIME
-HAVE_DIRENT_H
 HAVE_DUP2
 HAVE_ENDGRENT
 HAVE_ENDPWENT

=== modified file 'admin/ChangeLog'
--- admin/ChangeLog	2012-11-21 21:06:52 +0000
+++ admin/ChangeLog	2012-11-22 04:03:01 +0000
@@ -1,3 +1,9 @@
+2012-11-22  Paul Eggert  <[email-masked]>
+
+	Assume POSIX 1003.1-1988 or later for dirent.h.
+	* CPP-DEFINES (HAVE_CLOSEDIR, HAVE_DIRENT_H): Remove.
+	* notes/copyright: Adjust to src/ndir.h -> nt/inc/dirent.h renaming.
+
 2012-11-21  Paul Eggert  <[email-masked]>
 
 	Assume POSIX 1003.1-1988 or later for unistd.h (Bug#12945).

=== modified file 'admin/notes/copyright'
--- admin/notes/copyright	2012-01-19 07:21:25 +0000
+++ admin/notes/copyright	2012-11-22 04:03:01 +0000
@@ -380,7 +380,7 @@
 src/gmalloc.c
   - contains numerous copyrights from the GNU C library. Leave them alone.
 
-src/ndir.h
+nt/inc/dirent.h
   - see comments below. This file is OK to be released with Emacs
   22, but we may want to revisit it afterwards.
 
@@ -429,7 +429,7 @@
   File says it's in the public domain, but that might not make it so.
 
 etc/e/eterm-color.ti
-src/ndir.h
+nt/inc/dirent.h
   On legal advice from Matt Norwood, the following comment was added
   to these files in Feb/Mar 2007:

=== modified file 'configure.ac'
--- configure.ac	2012-11-21 21:06:52 +0000
+++ configure.ac	2012-11-22 04:03:01 +0000
@@ -1289,7 +1289,7 @@
   linux/version.h sys/systeminfo.h
   coff.h pty.h
   sys/vlimit.h sys/resource.h
-  sys/utsname.h pwd.h utmp.h dirent.h util.h)
+  sys/utsname.h pwd.h utmp.h util.h)
 
 AC_MSG_CHECKING(if personality LINUX32 can be set)
 AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[#include <sys/personality.h>]], [[personality (PER_LINUX32)]])],
@@ -2891,7 +2891,7 @@

 AC_CHECK_FUNCS(gethostname \
-closedir getrusage get_current_dir_name \
+getrusage get_current_dir_name \
 lrand48 \
 select getpagesize setlocale \
 utimes getrlimit setrlimit shutdown getaddrinfo \

=== modified file 'nt/ChangeLog'
--- nt/ChangeLog	2012-11-21 21:06:52 +0000
+++ nt/ChangeLog	2012-11-22 04:03:01 +0000
@@ -1,3 +1,10 @@
+2012-11-22  Paul Eggert  <[email-masked]>
+
+	Assume POSIX 1003.1-1988 or later for dirent.h.
+	* inc/dirent.h: Rename from ../src/ndir.h, with these changes:
+	(struct dirent): Rename from struct direct.  All uses changed.
+	* inc/sys/dir.h: Remove.
+
 2012-11-21  Paul Eggert  <[email-masked]>
 
 	Assume POSIX 1003.1-1988 or later for unistd.h (Bug#12945).

=== renamed file 'src/ndir.h' => 'nt/inc/dirent.h'
--- src/ndir.h	2011-01-15 23:16:57 +0000
+++ nt/inc/dirent.h	2012-11-22 04:03:01 +0000
@@ -1,7 +1,5 @@
 /*
-	<dir.h> -- definitions for 4.2BSD-compatible directory access
-
-	last edit:	09-Jul-1983	D A Gwyn
+	<dirent.h> -- definitions for POSIX-compatible directory access
 
  * The code here is forced by the interface, and is not subject to
  * copyright, constituting the only possible expression of the
@@ -16,7 +14,7 @@
 #endif /* not WINDOWSNT */
 	/* NOTE:  MAXNAMLEN must be one less than a multiple of 4 */
 
-struct direct				/* data from readdir() */
+struct dirent				/* data from readdir() */
 	{
 	long		d_ino;		/* inode number of entry */
 	unsigned short	d_reclen;	/* length of this record */
@@ -33,9 +31,8 @@
 	}	DIR;			/* stream data from opendir() */
 
 extern DIR		*opendir (char *);
-extern struct direct	*readdir (DIR *);
+extern struct dirent	*readdir (DIR *);
 extern void		seekdir (DIR *, long);
 extern void		closedir (DIR *);
 
 #define rewinddir( dirp )	seekdir( dirp, 0L )
-

=== removed file 'nt/inc/sys/dir.h'
--- nt/inc/sys/dir.h	2011-01-15 23:16:57 +0000
+++ nt/inc/sys/dir.h	1970-01-01 00:00:00 +0000
@@ -1,6 +0,0 @@
-/*
- * map sys\dir.h to ..\..\..\src\ndir.h
- */
-
-#include "..\..\..\src\ndir.h"
-

=== modified file 'src/ChangeLog'
--- src/ChangeLog	2012-11-22 03:56:38 +0000
+++ src/ChangeLog	2012-11-22 04:06:38 +0000
@@ -1,3 +1,20 @@
+2012-11-22  Paul Eggert  <[email-masked]>
+
+	Assume POSIX 1003.1-1988 or later for dirent.h.
+	* dired.c: Assume HAVE_DIRENT_H.
+	(NAMLEN): Remove, replacing with ...
+	(dirent_namelen): New function.  All uses changed.  Use the GNU macro
+	_D_EXACT_NAMELEN if available, as it's faster than strlen.
+	(DIRENTRY): Remove, replacing all uses with 'struct dirent'.
+	(DIRENTRY_NONEMPTY): Remove, replacing with ...
+	(dirent_nonempty): New function.  All uses changed.
+	* makefile.w32-in (DIR_H): Now just dirent.h, not sys/dir.h and ndir.h.
+	($(BLD)/w32.$(O)): Depend on $(DIR_H), not $(SRC)/ndir.h.
+	* ndir.h: Rename to ../nt/inc/dirent.h.
+	* sysdep.h (closedir) [!HAVE_CLOSEDIR]: Remove.
+	Do not include <dirent.h>; no longer needed.
+	* w32.c: Include <dirent.h> rather than "ndir.h".
+
 2012-11-22  Eli Zaretskii  <[email-masked]>
 
 	* w32.c (getcwd): Fix the 2nd argument type, to prevent conflicts

=== modified file 'src/dired.c'
--- src/dired.c	2012-10-01 02:07:14 +0000
+++ src/dired.c	2012-11-22 04:03:01 +0000
@@ -31,44 +31,10 @@
 #include <errno.h>
 #include <unistd.h>
 
-/* The d_nameln member of a struct dirent includes the '\0' character
-   on some systems, but not on others.  What's worse, you can't tell
-   at compile-time which one it will be, since it really depends on
-   the sort of system providing the filesystem you're reading from,
-   not the system you are running on.  Paul Eggert
-   <[email-masked]> says this occurs when Emacs is running on a
-   SunOS 4.1.2 host, reading a directory that is remote-mounted from a
-   Solaris 2.1 host and is in a native Solaris 2.1 filesystem.
-
-   Since applying strlen to the name always works, we'll just do that.  */
-#define NAMLEN(p) strlen (p->d_name)
-
-#ifdef HAVE_DIRENT_H
-
 #include <dirent.h>
-#define DIRENTRY struct dirent
-
-#else /* not HAVE_DIRENT_H */
-
-#include <sys/dir.h>
-#include <sys/stat.h>
-
-#define DIRENTRY struct direct
-
-extern DIR *opendir (char *);
-extern struct direct *readdir (DIR *);
-
-#endif /* HAVE_DIRENT_H */
-
 #include <filemode.h>
 #include <stat-time.h>
 
-#ifdef MSDOS
-#define DIRENTRY_NONEMPTY(p) ((p)->d_name[0] != 0)
-#else
-#define DIRENTRY_NONEMPTY(p) ((p)->d_ino)
-#endif
-
 #include "lisp.h"
 #include "systime.h"
 #include "character.h"
@@ -88,6 +54,28 @@
 
 static ptrdiff_t scmp (const char *, const char *, ptrdiff_t);
 
+/* Return the number of bytes in DP's name.  */
+static ptrdiff_t
+dirent_namelen (struct dirent *dp)
+{
+#ifdef _D_EXACT_NAMLEN
+  return _D_EXACT_NAMLEN (dp);
+#else
+  return strlen (dp->d_name);
+#endif
+}
+
+/* Return true if DP represents a real directory entry.  */
+static bool
+dirent_nonempty (struct dirent *dp)
+{
+#ifdef MSDOS
+  return dp->d_name[0] != 0;
+#else
+  return 1;
+#endif
+}
+
 #ifdef WINDOWSNT
 Lisp_Object
 directory_files_internal_w32_unwind (Lisp_Object arg)
@@ -124,7 +112,7 @@
   bool needsep = 0;
   ptrdiff_t count = SPECPDL_INDEX ();
   struct gcpro gcpro1, gcpro2, gcpro3, gcpro4, gcpro5;
-  DIRENTRY *dp;
+  struct dirent *dp;
 #ifdef WINDOWSNT
   Lisp_Object w32_save = Qnil;
 #endif
@@ -225,14 +213,14 @@
       if (dp == NULL)
 	break;
 
-      if (DIRENTRY_NONEMPTY (dp))
+      if (dirent_nonempty (dp))
 	{
 	  ptrdiff_t len;
 	  bool wanted = 0;
 	  Lisp_Object name, finalname;
 	  struct gcpro gcpro1, gcpro2;
 
-	  len = NAMLEN (dp);
+	  len = dirent_namelen (dp);
 	  name = finalname = make_unibyte_string (dp->d_name, len);
 	  GCPRO2 (finalname, name);
 
@@ -442,7 +430,8 @@
   return file_name_completion (file, directory, 1, Qnil);
 }
 
-static int file_name_completion_stat (Lisp_Object dirname, DIRENTRY *dp, struct stat *st_addr);
+static int file_name_completion_stat (Lisp_Object dirname, struct dirent *dp,
+				      struct stat *st_addr);
 static Lisp_Object Qdefault_directory;
 
 static Lisp_Object
@@ -499,7 +488,7 @@
   /* (att3b compiler bug requires do a null comparison this way) */
   while (1)
     {
-      DIRENTRY *dp;
+      struct dirent *dp;
       ptrdiff_t len;
       bool canexclude = 0;
 
@@ -517,10 +506,10 @@
 
       if (!dp) break;
 
-      len = NAMLEN (dp);
+      len = dirent_namelen (dp);
 
       QUIT;
-      if (! DIRENTRY_NONEMPTY (dp)
+      if (! dirent_nonempty (dp)
 	  || len < SCHARS (encoded_file)
 	  || 0 <= scmp (dp->d_name, SSDATA (encoded_file),
 			SCHARS (encoded_file)))
@@ -806,9 +795,10 @@
 }
 
 static int
-file_name_completion_stat (Lisp_Object dirname, DIRENTRY *dp, struct stat *st_addr)
+file_name_completion_stat (Lisp_Object dirname, struct dirent *dp,
+			   struct stat *st_addr)
 {
-  ptrdiff_t len = NAMLEN (dp);
+  ptrdiff_t len = dirent_namelen (dp);
   ptrdiff_t pos = SCHARS (dirname);
   int value;
   USE_SAFE_ALLOCA;

=== modified file 'src/makefile.w32-in'
--- src/makefile.w32-in	2012-11-17 23:16:24 +0000
+++ src/makefile.w32-in	2012-11-22 04:03:01 +0000
@@ -413,8 +413,7 @@
 		 $(MS_W32_H)
 CONFIG_H       = $(SRC)/config.h \
 		 $(CONF_POST_H)
-DIR_H          = $(NT_INC)/sys/dir.h \
-		 $(SRC)/ndir.h
+DIR_H          = $(NT_INC)/dirent.h
 W32GUI_H       = $(SRC)/w32gui.h \
 		 $(SYSTIME_H)
 DISPEXTERN_H   = $(SRC)/dispextern.h \
@@ -1175,7 +1174,6 @@
 
 $(BLD)/w32.$(O) : \
 	$(SRC)/w32.c \
-	$(SRC)/ndir.h \
 	$(SRC)/w32.h \
 	$(SRC)/w32common.h \
 	$(SRC)/w32heap.h \
@@ -1187,6 +1185,7 @@
 	$(CAREADLINKAT_H) \
 	$(CODING_H) \
 	$(CONFIG_H) \
+	$(DIR_H) \
 	$(DISPEXTERN_H) \
 	$(GRP_H) \
 	$(LISP_H) \

=== modified file 'src/sysdep.c'
--- src/sysdep.c	2012-11-21 21:06:52 +0000
+++ src/sysdep.c	2012-11-22 04:03:01 +0000
@@ -2220,28 +2220,6 @@
 		       &emacs_norealloc_allocator, careadlinkatcwd);
 }
 
-/* Directory routines for systems that don't have them. */
-
-#ifdef HAVE_DIRENT_H
-
-#include <dirent.h>
-
-#if !defined (HAVE_CLOSEDIR)
-
-int
-closedir (DIR *dirp /* stream from opendir */)
-{
-  int rtnval;
-
-  rtnval = emacs_close (dirp->dd_fd);
-  xfree (dirp);
-
-  return rtnval;
-}
-#endif /* not HAVE_CLOSEDIR */
-#endif /* HAVE_DIRENT_H */
-
-
 /* Return a struct timeval that is roughly equivalent to T.
    Use the least timeval not less than T.
    Return an extremal value if the result would overflow.  */

=== modified file 'src/w32.c'
--- src/w32.c	2012-11-22 03:56:38 +0000
+++ src/w32.c	2012-11-22 04:06:38 +0000
@@ -179,7 +179,7 @@
 #undef sendto
 
 #include "w32.h"
-#include "ndir.h"
+#include <dirent.h>
 #include "w32common.h"
 #include "w32heap.h"
 #include "w32select.h"
@@ -2448,7 +2448,7 @@
    and readdir.  We can't use the procedures supplied in sysdep.c,
    so we provide them here.  */
 
-struct direct dir_static;       /* simulated directory contents */
+struct dirent dir_static;       /* simulated directory contents */
 static HANDLE dir_find_handle = INVALID_HANDLE_VALUE;
 static int    dir_is_fat;
 static char   dir_pathname[MAXPATHLEN+1];
@@ -2518,7 +2518,7 @@
   xfree ((char *) dirp);
 }
 
-struct direct *
+struct dirent *
 readdir (DIR *dirp)
 {
   int downcase = !NILP (Vw32_downcase_file_names);
@@ -2572,7 +2572,7 @@
       downcase = 1;	/* 8+3 aliases are returned in all caps */
     }
   dir_static.d_namlen = strlen (dir_static.d_name);
-  dir_static.d_reclen = sizeof (struct direct) - MAXNAMLEN + 3 +
+  dir_static.d_reclen = sizeof (struct dirent) - MAXNAMLEN + 3 +
     dir_static.d_namlen - dir_static.d_namlen % 4;
 
   /* If the file name in cFileName[] includes `?' characters, it means