D issues are now tracked on GitHub. This Bugzilla instance remains as a read-only archive.
Issue 17766 - Wrong choice of generic mutable/const/immutable methods
Summary: Wrong choice of generic mutable/const/immutable methods
Status: NEW
Alias: None
Product: D
Classification: Unclassified
Component: dmd (show other issues)
Version: D2
Hardware: All All
: P2 major
Assignee: No Owner
URL:
Keywords: wrong-code
Depends on:
Blocks:
 
Reported: 2017-08-20 05:19 UTC by Илья Ярошенко
Modified: 2024-12-13 18:54 UTC (History)
3 users (show)

See Also:


Attachments

Note You need to log in before you can comment on or make changes to this issue.
Description Илья Ярошенко 2017-08-20 05:19:27 UTC
static struct Foo()
    {
        char opIndex(Indexes...)(Indexes indexes) immutable
        {
            return 'i';
        }

        char opIndex()() const
        {
            return 'c';
        }

        char opIndex(Indexes...)(Indexes indexes)
        {
            return 'm';
        }
    }
    pragma(msg, Foo!()()[]);
    pragma(msg, (cast(const) Foo!()())[]);
    pragma(msg, (cast(immutable) Foo!()())[]);

Prints
'c'
'c'
'c'

But shuold be

'm'
'c'
'i'

Type qualifier should have priority.
Comment 1 alexandru.ermicioi 2018-10-22 19:11:27 UTC
This is not the only case, here is another case of wrong selection:

----------------------
class Mquartz(T, Z) {
    Z pass(T component) const {
        "Mutable pass".writeln;
        return component.z;
    }
    const(Z) pass(const T component) const {
        "Const pass".writeln;
        return component.z;
    }
    const(Z) pass(immutable T component) const {
        "Immutable pass".writeln;
        return component.z;
    }
    const(Z) pass(inout T component) const {
        "Inout pass".writeln;
        return component.z;
    }
}

struct V {
    int z;
}

void main() {

    auto m = new Mquartz!(V, typeof(V.z));

    // V v = V(21);
    // writeln(m.pass(v));
    writeln(m.pass(V(20)));
    writeln(m.pass(const(V)(20)));
    writeln(m.pass(immutable(V)(20)));
    writeln(m.pass(inout(V)(20)));
}
-------------------------
Current logic will select only const version with const argument instead of selecting right ones:
-------------------------
Const pass
20
Const pass
20
Const pass
20
Const pass
20
-------------------------
The overload selection logic works as expected only if m is const, then response will as expected:
-------------------------
Mutable pass
20
Const pass
20
Immutable pass
20
Inout pass
20
-------------------------
Comment 2 dlangBugzillaToGithub 2024-12-13 18:54:09 UTC
THIS ISSUE HAS BEEN MOVED TO GITHUB

https://github.com/dlang/dmd/issues/19304

DO NOT COMMENT HERE ANYMORE, NOBODY WILL SEE IT, THIS ISSUE HAS BEEN MOVED TO GITHUB