From bb0a4050e8cab5c4494b15d349b385e49d83fe04 Mon Sep 17 00:00:00 2001 From: Oscar Blumberg Date: Mon, 3 Aug 2015 12:15:52 -0400 Subject: [PATCH] Fix object_id with padding Forgotten in the padding fix : immutables with haspadding fields. --- src/builtins.c | 17 +++++++++++++---- test/core.jl | 14 ++++++++++++++ 2 files changed, 27 insertions(+), 4 deletions(-) diff --git a/src/builtins.c b/src/builtins.c index 7a99461524e67..fd52430778d9c 100644 --- a/src/builtins.c +++ b/src/builtins.c @@ -1102,11 +1102,10 @@ static uptrint_t bits_hash(void *b, size_t sz) } } -DLLEXPORT uptrint_t jl_object_id(jl_value_t *v) +static uptrint_t jl_object_id_(jl_value_t *tv, jl_value_t *v) { - if (jl_is_symbol(v)) + if (tv == (jl_value_t*)jl_sym_type) return ((jl_sym_t*)v)->hash; - jl_value_t *tv = (jl_value_t*)jl_typeof(v); if (tv == (jl_value_t*)jl_simplevector_type) { uptrint_t h = 0; size_t l = jl_svec_len(v); @@ -1148,13 +1147,23 @@ DLLEXPORT uptrint_t jl_object_id(jl_value_t *v) u = f==NULL ? 0 : jl_object_id(f); } else { - u = bits_hash(vo, dt->fields[f].size); + jl_datatype_t *fieldtype = (jl_datatype_t*)jl_svecref(dt->types, f); + assert(jl_is_datatype(fieldtype) && !fieldtype->abstract && !fieldtype->mutabl); + if (fieldtype->haspadding) + u = jl_object_id_((jl_value_t*)fieldtype, (jl_value_t*)vo); + else + u = bits_hash(vo, dt->fields[f].size); } h = bitmix(h, u); } return h; } +DLLEXPORT uptrint_t jl_object_id(jl_value_t *v) +{ + return jl_object_id_(jl_typeof(v), v); +} + // init ----------------------------------------------------------------------- static void add_builtin(const char *name, jl_value_t *v) diff --git a/test/core.jl b/test/core.jl index 35e2745f51ef6..d678ae4c4f173 100644 --- a/test/core.jl +++ b/test/core.jl @@ -3173,3 +3173,17 @@ let x = Array(Empty12394,1), y = [Empty12394()] @test_throws UndefRefError x==y @test_throws UndefRefError y==x end + +# object_id of haspadding field +immutable HasPadding + x::Bool + y::Int +end +immutable HasHasPadding + x::HasPadding +end +hashaspadding = HasHasPadding(HasPadding(true,1)) +hashaspadding2 = HasHasPadding(HasPadding(true,1)) +unsafe_store!(convert(Ptr{UInt8},pointer_from_objref(hashaspadding)), 0x12, 2) +unsafe_store!(convert(Ptr{UInt8},pointer_from_objref(hashaspadding2)), 0x21, 2) +@test object_id(hashaspadding) == object_id(hashaspadding2)