Bug 17258 – Pass by name doesn't work reliably and can sometimes lead to memory corruption

Status
RESOLVED
Resolution
FIXED
Severity
critical
Priority
P1
Component
dmd
Product
D
Version
D2
Platform
All
OS
All
Creation time
2017-03-15T17:22:31Z
Last change time
2019-05-25T08:57:01Z
Keywords
wrong-code
Assigned to
Suleyman Sahmi (سليمان السهمي)
Creator
ZombineDev

Comments

Comment #0 by petar.p.kirov — 2017-03-15T17:22:31Z
struct ByName1(alias Var) { alias var = Var; } struct ByName2(alias Var) { alias var = Var; void inc() { var++; } } void byName2(alias var)() { var++; } void test1() { int x; ByName1!x v; v.var++; assert(v.var == 1); // v.var is 1 => passes - OK assert(x == v.var); // x is 0 => fails - NG } void test2() { int x; ByName2!x v; v.inc(); // import std.stdio; // writeln(v.var); // Prints garbage !!! assert(v.var == 1); // v.var is ??? => fails - NG assert(x == v.var); // x is 0, v.var is ??? => fails - NG } void test3() { int x; byName2!x(); assert (x == 1); // x is 1 => passes - OK } void main() { test1(); // fails because &x != &v.var test2(); // fails because of bad code gen / memory corruption test3(); // passes }
Comment #1 by ag0aep6g — 2017-03-15T19:40:27Z
Looks like the compiler thinks `var` is a field. Writing to `v.var` then stomps over anything that's actually there. ---- struct ByName3(alias Var) { alias var = Var; ubyte value = 1; } void main() { ushort x; ByName3!x v; ubyte w = 2; v.var = 0xAA_BB; /* stomps over v.value and w */ import std.stdio; writefln("%X", v.value); /* prints "BB", should be 1 */ writefln("%X", w); /* prints "AA", should be 2 */ } ----
Comment #2 by dlang-bot — 2019-05-25T08:57:01Z
dlang/dmd pull request #9884 "Fix issue 17258 - Alias parameter wrongly accessed as a field" was merged into stable: - a21e8dfd606ae94b104b4a1a81b2c31476cf13ca by سليمان السهمي (Suleyman Sahmi): Fix issue 17258 - Alias parameter wrongly accessed as a field https://github.com/dlang/dmd/pull/9884