aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--ChangeLog9
-rw-r--r--common.mk1
-rw-r--r--hash.c3
-rw-r--r--symbol.c6
-rw-r--r--symbol.h1
5 files changed, 19 insertions, 1 deletions
diff --git a/ChangeLog b/ChangeLog
index df444e9830..c98761b1ac 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,12 @@
+Tue Jul 28 07:23:03 2015 Eric Wong <e@80x24.org>
+
+ * symbol.h (struct RSymbol): add hashval field
+ * symbol.c (dsymbol_alloc): setup hashval field once
+ * hash.c (rb_any_hash): return RSymbol->hashval directly
+ * common.mk: hash.o depends on symbol.h
+ Thanks to Bruno Escherl <bruno@escherl.net> for the bug report
+ [ruby-core:70129] [Bug #11396]
+
Tue Jul 28 03:26:15 2015 Aaron Patterson <tenderlove@ruby-lang.org>
* ext/openssl/lib/openssl/ssl.rb (module OpenSSL): raise a more
diff --git a/common.mk b/common.mk
index b0a4a96499..1a3e463ef0 100644
--- a/common.mk
+++ b/common.mk
@@ -1532,6 +1532,7 @@ hash.$(OBJEXT): {$(VPATH)}oniguruma.h
hash.$(OBJEXT): {$(VPATH)}probes.h
hash.$(OBJEXT): {$(VPATH)}st.h
hash.$(OBJEXT): {$(VPATH)}subst.h
+hash.$(OBJEXT): {$(VPATH)}symbol.h
hash.$(OBJEXT): {$(VPATH)}util.h
hash.$(OBJEXT): {$(VPATH)}vm_opts.h
inits.$(OBJEXT): $(hdrdir)/ruby/ruby.h
diff --git a/hash.c b/hash.c
index 7b8733f41c..5b13d98ea3 100644
--- a/hash.c
+++ b/hash.c
@@ -17,6 +17,7 @@
#include <errno.h>
#include "probes.h"
#include "id.h"
+#include "symbol.h"
#ifdef __APPLE__
# ifdef HAVE_CRT_EXTERNS_H
@@ -149,7 +150,7 @@ rb_any_hash(VALUE a)
hnum = rb_str_hash(a);
}
else if (BUILTIN_TYPE(a) == T_SYMBOL) {
- hnum = rb_objid_hash((st_index_t)a);
+ return RSYMBOL(a)->hashval;
}
else if (BUILTIN_TYPE(a) == T_FLOAT) {
return rb_dbl_hash(rb_float_value(a));
diff --git a/symbol.c b/symbol.c
index 9fbe3dda74..9e2fccd689 100644
--- a/symbol.c
+++ b/symbol.c
@@ -505,12 +505,18 @@ static VALUE
dsymbol_alloc(const VALUE klass, const VALUE str, rb_encoding * const enc, const ID type)
{
const VALUE dsym = rb_newobj_of(klass, T_SYMBOL | FL_WB_PROTECTED);
+ st_index_t hashval;
rb_enc_associate(dsym, enc);
OBJ_FREEZE(dsym);
RB_OBJ_WRITE(dsym, &RSYMBOL(dsym)->fstr, str);
RSYMBOL(dsym)->id = type;
+ /* we want hashval to be in Fixnum range [ruby-core:15713] r15672 */
+ hashval = rb_str_hash(str);
+ hashval <<= 1;
+ RSYMBOL(dsym)->hashval = (st_index_t)RSHIFT(hashval, 1);
+
register_sym(str, dsym);
rb_hash_aset(global_symbols.dsymbol_fstr_hash, str, Qtrue);
diff --git a/symbol.h b/symbol.h
index 549eabdf61..5c52b9742b 100644
--- a/symbol.h
+++ b/symbol.h
@@ -25,6 +25,7 @@
struct RSymbol {
struct RBasic basic;
+ st_index_t hashval;
VALUE fstr;
ID id;
};