changeset 9233:f5b68edd82c4

Fix canonicalize loop-detection corner case. Do not attempt to stat the symlink values stored via seen_triple. Without this, coreutils' tests/misc/readlink-fp-loop test would fail on linux-2.6.18, (but not 2.6.22). * lib/canonicalize.c (seen_triple): Use triple_compare_ino_str, not triple_compare. The former compares dev,ino,filename, while the latter would actually stat dirname(filename) when dev and ino were equal. * lib/hash-triple.c: Install <string.h>. (STREQ): Define. (triple_compare_ino_str): New function. * lib/hash-triple.h (triple_compare_ino_str): Declare it.
author Jim Meyering <jim@meyering.net>
date Fri, 28 Sep 2007 23:26:49 +0200
parents 01d4e199e19f
children 67dac9500a0e
files ChangeLog lib/canonicalize.c lib/hash-triple.c lib/hash-triple.h
diffstat 4 files changed, 27 insertions(+), 1 deletions(-) [+]
line wrap: on
line diff
--- a/ChangeLog	Tue Sep 25 07:11:35 2007 -0600
+++ b/ChangeLog	Fri Sep 28 23:26:49 2007 +0200
@@ -1,3 +1,17 @@
+2007-09-28  Jim Meyering  <jim@meyering.net>
+
+	Fix canonicalize loop-detection corner case.
+	Do not attempt to stat the symlink values stored via seen_triple.
+	Without this, coreutils' tests/misc/readlink-fp-loop test would fail
+	on linux-2.6.18, (but not 2.6.22).
+	* lib/canonicalize.c (seen_triple): Use triple_compare_ino_str, not
+	triple_compare.  The former compares dev,ino,filename, while the latter
+	would actually stat dirname(filename) when dev and ino were equal.
+	* lib/hash-triple.c: Install <string.h>.
+	(STREQ): Define.
+	(triple_compare_ino_str): New function.
+	* lib/hash-triple.h (triple_compare_ino_str): Declare it.
+
 2007-09-28  Eric Blake  <ebb9@byu.net>
 
 	Enforce that AC_REPLACE_FUNCS files exist.
--- a/lib/canonicalize.c	Tue Sep 25 07:11:35 2007 -0600
+++ b/lib/canonicalize.c	Fri Sep 28 23:26:49 2007 +0200
@@ -135,7 +135,7 @@
       *ht = hash_initialize (initial_capacity,
 			    NULL,
 			    triple_hash,
-			    triple_compare,
+			    triple_compare_ino_str,
 			    triple_free);
       if (*ht == NULL)
 	xalloc_die ();
--- a/lib/hash-triple.c	Tue Sep 25 07:11:35 2007 -0600
+++ b/lib/hash-triple.c	Fri Sep 28 23:26:49 2007 +0200
@@ -22,11 +22,14 @@
 #include "hash-triple.h"
 
 #include <stdlib.h>
+#include <string.h>
 
 #include "hash-pjw.h"
 #include "same.h"
 #include "same-inode.h"
 
+#define STREQ(a, b) (strcmp ((a), (b)) == 0)
+
 /* Hash an F_triple, and *do* consider the file name.  */
 size_t
 triple_hash (void const *x, size_t table_size)
@@ -57,6 +60,14 @@
   return (SAME_INODE (*a, *b) && same_name (a->name, b->name)) ? true : false;
 }
 
+bool
+triple_compare_ino_str (void const *x, void const *y)
+{
+  struct F_triple const *a = x;
+  struct F_triple const *b = y;
+  return (SAME_INODE (*a, *b) && STREQ (a->name, b->name)) ? true : false;
+}
+
 /* Free an F_triple.  */
 void
 triple_free (void *x)
--- a/lib/hash-triple.h	Tue Sep 25 07:11:35 2007 -0600
+++ b/lib/hash-triple.h	Fri Sep 28 23:26:49 2007 +0200
@@ -16,6 +16,7 @@
 extern size_t triple_hash (void const *x, size_t table_size);
 extern size_t triple_hash_no_name (void const *x, size_t table_size);
 extern bool triple_compare (void const *x, void const *y);
+extern bool triple_compare_ino_str (void const *x, void const *y);
 extern void triple_free (void *x);
 
 #endif