Bug 5835 – `TypeInfo_Array.getHash` creates raw data hash instead using array element hash function

Status
RESOLVED
Resolution
FIXED
Severity
normal
Priority
P2
Component
dmd
Product
D
Version
D2
Platform
All
OS
All
Creation time
2011-04-11T05:52:00Z
Last change time
2014-03-08T07:47:40Z
Keywords
patch, wrong-code
Assigned to
verylonglogin.reg
Creator
k.hara.pg

Comments

Comment #0 by k.hara.pg — 2011-04-11T05:52:31Z
Sample code: ---- import std.stdio; class Foo{ hash_t toHash(){ writeln("Foo.toHash"); return 0; } } void main(){ Foo[] arr = [new Foo(), new Foo()]; typeid(arr).getHash(&arr); // doesn't call Foo.toHash() } ---- The typeid(arr) returns instance of TypeInfo_Array, but its getHash is not call Object.toHash of each element. The internal TypeInfo class rt.typeinfo.ti_AC.TypeInfo_AC supports it, but this is only used in array/associative-array operations.
Comment #1 by k.hara.pg — 2011-04-11T05:56:44Z
Patches: https://github.com/9rnsr/dmd/compare/master...aa_hash_fix https://github.com/9rnsr/druntime/compare/master...aa_hash_fix Changes: - TypeInfo_AC is derived from TypeInfo_Array. - Class array's TypeInfo is instance of TypeInfo_AC.
Comment #2 by k.hara.pg — 2011-04-11T19:34:45Z
Sorry, this patch has disabling optimizing problem. I'll fix it.
Comment #3 by k.hara.pg — 2011-04-11T22:55:45Z
Changed. - Removing getInternalTypeInfo is too strict. - Changed internal TypeInfo of class array -> typeid(Object[]) - TypeInfo_AC is only used for TypeInfo class of typeid(user class array).
Comment #4 by yebblies — 2012-02-04T20:50:53Z
Are these patches still valid? Maybe worth turning them into pull requests.
Comment #5 by verylonglogin.reg — 2014-03-06T01:57:36Z
Simplified original testcase: --- class S { int i; this(in int i) { this.i = i; } override hash_t toHash() { return 0; } } void main() { S[] a1 = [new S(11)], a2 = [new S(12)]; assert(typeid(S[]).getHash(&a1) == typeid(S[]).getHash(&a2)); // fails } --- With structs: --- struct S { int i; hash_t toHash() const @safe nothrow { return 0; } } void main() { S[] a1 = [S(11)], a2 = [S(12)]; assert(typeid(S[]).getHash(&a1) != typeid(S[]).getHash(&a2)); // fails } --- Associative arrays are affected too because of this: --- struct S { int i; hash_t toHash() const @safe nothrow { return 0; } bool opEquals(ref const S el) const { return true; } int opCmp(ref const S el) const { return 0; } } void main() { int[S[]] aa = [[S(11)] : 13]; assert([S(12)] in aa); // fails } ---
Comment #6 by verylonglogin.reg — 2014-03-06T02:09:12Z
Will fix soon.
Comment #7 by verylonglogin.reg — 2014-03-06T03:28:11Z
(In reply to comment #5) > ... > With structs: > ... > assert(typeid(S[]).getHash(&a1) != typeid(S[]).getHash(&a2)); // fails > ... Of course `==` was meant. A fixing pull: https://github.com/D-Programming-Language/druntime/pull/735
Comment #8 by github-bugzilla — 2014-03-08T04:32:32Z
Commits pushed to master at https://github.com/D-Programming-Language/druntime https://github.com/D-Programming-Language/druntime/commit/1a3f6796270752ba0d770539392f2815f57e8181 Fix Issue 5835 - `TypeInfo_Array.getHash` creates raw data hash instead using array element hash function Issue URL: https://d.puremagic.com/issues/show_bug.cgi?id=5835 https://github.com/D-Programming-Language/druntime/commit/dc3e69a24622331722978158cfef3df10204dcf9 Merge pull request #735 from denis-sh/fix-Issue-5835 Fix Issue 5835