D issues are now tracked on GitHub. This Bugzilla instance remains as a read-only archive.
Issue 7801 - Nested function returning garbage instead of closed-over parameter
Summary: Nested function returning garbage instead of closed-over parameter
Status: RESOLVED DUPLICATE of issue 1841
Alias: None
Product: D
Classification: Unclassified
Component: dmd (show other issues)
Version: D2
Hardware: All All
: P2 normal
Assignee: No Owner
URL:
Keywords: wrong-code
Depends on:
Blocks:
 
Reported: 2012-03-30 14:53 UTC by edmccard
Modified: 2013-02-01 00:51 UTC (History)
1 user (show)

See Also:


Attachments

Note You need to log in before you can comment on or make changes to this issue.
Description edmccard 2012-03-30 14:53:02 UTC
I ran into a strange and hard-to-describe problem with nested functions closing over the argument to their enclosing function.

When a nested function (A) returns the value of another nested function (B) that returns a parameter of the enclosing function (C), and when (A) is returned from (C), then calling (A) returns an incorrect value if either run from a 32-bit program, or run from 64-bit and (A) has a parameter of class type (it works when (A) has no class parameters).

The following code demonstrates the issue:


auto foo(T)(int val)
{
    int nested()
    {
        return val;
    }

    int escaping(T ignored)
    {
        return nested();
    }

    return &escaping;
}

struct Bar {}

class Baz {}

void main()
{
    auto func1 = foo!int(55);
    auto val1 = func1(12);
    // 64-bit ok, 32-bit fail (varying)
    assert(val1 == 55);

    auto func2 = foo!Bar(55);
    Bar bar;
    auto val2 = func2(bar);
    // 64-bit ok, 32-bit fail (equal to incorrect val1)
    assert(val2 == 55);

    auto func3 = foo!Baz(55);
    auto baz = new Baz();
    auto val3 = func3(baz);
    // 64- and 32-bit fail (varying, different from val1/val2)
    assert(val3 == 55);
}
Comment 1 Don 2013-02-01 00:51:02 UTC

*** This issue has been marked as a duplicate of issue 1841 ***