From 9ab183e388057e53a84234a9f82d797b314b0419 Mon Sep 17 00:00:00 2001
From: sayle <sayle@138bc75d-0d04-0410-961f-82ee72b054a4>
Date: Tue, 12 Sep 2006 16:02:31 +0000
Subject: [PATCH] 	PR middle-end/4520 	PR bootstrap/28784 	*
 cselib.c (cselib_hash_rtx): Avoid hashing on the address of labels 	and
 symbols.  Instead use the implementation from cse.c's hash_rtx.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@116891 138bc75d-0d04-0410-961f-82ee72b054a4
---
 gcc/ChangeLog |  7 +++++++
 gcc/cselib.c  | 24 +++++++++++++++++++-----
 2 files changed, 26 insertions(+), 5 deletions(-)

diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 5d66902f67fb..0a0d31b8cf27 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,10 @@
+2006-09-12  Roger Sayle  <roger@eyesopen.com>
+
+	PR middle-end/4520
+	PR bootstrap/28784
+	* cselib.c (cselib_hash_rtx): Avoid hashing on the address of labels
+	and symbols.  Instead use the implementation from cse.c's hash_rtx.
+
 2006-09-12  Jan Hubicka  <jh@suse.cz>
 
 	PR rtl-optimization/28071
diff --git a/gcc/cselib.c b/gcc/cselib.c
index edfc328c0d84..4070da7c01f0 100644
--- a/gcc/cselib.c
+++ b/gcc/cselib.c
@@ -630,14 +630,28 @@ cselib_hash_rtx (rtx x, int create)
 
       /* Assume there is only one rtx object for any given label.  */
     case LABEL_REF:
-      hash
-	+= ((unsigned) LABEL_REF << 7) + (unsigned long) XEXP (x, 0);
+      /* We don't hash on the address of the CODE_LABEL to avoid bootstrap
+	 differences and differences between each stage's debugging dumps.  */
+      hash += (((unsigned int) LABEL_REF << 7)
+	       + CODE_LABEL_NUMBER (XEXP (x, 0)));
       return hash ? hash : (unsigned int) LABEL_REF;
 
     case SYMBOL_REF:
-      hash
-	+= ((unsigned) SYMBOL_REF << 7) + (unsigned long) XSTR (x, 0);
-      return hash ? hash : (unsigned int) SYMBOL_REF;
+      {
+	/* Don't hash on the symbol's address to avoid bootstrap differences.
+	   Different hash values may cause expressions to be recorded in
+	   different orders and thus different registers to be used in the
+	   final assembler.  This also avoids differences in the dump files
+	   between various stages.  */
+	unsigned int h = 0;
+	const unsigned char *p = (const unsigned char *) XSTR (x, 0);
+
+	while (*p)
+	  h += (h << 7) + *p++; /* ??? revisit */
+
+	hash += ((unsigned int) SYMBOL_REF << 7) + h;
+	return hash ? hash : (unsigned int) SYMBOL_REF;
+      }
 
     case PRE_DEC:
     case PRE_INC:
-- 
GitLab