Regression bug since 2.037. For example in such code:
import std.stdio;
int mul100(int n)
out(result)
{
writeln("result == ", result);
}
body
{
return n * 100;
}
int main()
{
mul100(5);
return 0;
}
compiled with -debug output is always
result == 0 and should be result == 500
Comment #1 by lat7h — 2010-01-12T13:09:11Z
More details: for any primitive type (all integer, character, and floating point types, including unsigned, complex, and typedef'd varieties thereof) the out contract's result will always be type.init. For example, the following code works (and shouldn't, the out contract is incorrect):
-------
typedef cdouble sometype = 4.0 + 2.0i;
sometype buggy()
out(result) { assert( result == 4.0 + 2.0i ); } // should fail but doesn't
body { return cast(sometype)0; }
unittest { assert(buggy() == 0); }
-------
This does not happen for structs, classes, static or dynamic arrays (all seem to function correctly).
Comment #2 by andrei — 2010-02-21T17:01:52Z
An example involving a nested function:
void fun() {
int gun()
out(result)
{
assert(result == 42);
} body
{
return 42;
}
gun();
}
void main() {
fun();
}
Comment #3 by witold.baryluk+d — 2010-03-09T17:08:03Z
It is probably related to bug3634
Comment #4 by clugdbug — 2010-03-15T00:55:50Z
*** Issue 3963 has been marked as a duplicate of this issue. ***
Comment #5 by lat7h — 2010-03-15T20:43:30Z
Not sure if it helps, but the compiler knows this problem will arise at compile time; the following compiles just fine, though it clearly should not:
-----
int buggy(int y)
out(result) { static assert(result==0); }
body { return y; }
void main() { buggy(3); }
----
I don't know why. Debugging shows that statement.c:3490 still creates the "result = y" assignment I'd expect... I don't know where else to look.
Comment #6 by rsinfu — 2010-05-07T11:30:35Z
Created attachment 624
Patch for DMD 2.045
The attached patch should fix the problem.
Since DMD 2.028, result variables are marked as const. The cause of this bug is that DMD mistakenly tries to const-fold a result variable into its default initializer. Unfortunately, it succeeds when return type is a basic value type (int, bool, etc.).
The attached patch adds a STCresult storage class to declaration.h, and applies it to the vresult. The STCresult is similar to the STCparameter; it disables default-value initialization of result variables.
Comment #7 by bugzilla — 2010-05-15T16:17:46Z
changelog 490
Comment #8 by clugdbug — 2010-06-07T00:11:57Z
*** Issue 3634 has been marked as a duplicate of this issue. ***