Thread overview
[Issue 18672] Error in @safe transitive propagation with associative arrays
Mar 27, 2018
Seb
Mar 27, 2018
ag0aep6g
Mar 28, 2018
Carsten Blüggel
Mar 29, 2018
RazvanN
Apr 02, 2018
Seb
Aug 23, 2018
RazvanN
Dec 17, 2022
Iain Buclaw
March 27, 2018
https://issues.dlang.org/show_bug.cgi?id=18672

Seb <greensunny12@gmail.com> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
            Summary|@safe should be             |Error in @safe transitive
                   |transitively propagated     |propagation with
                   |                            |associative arrays
           Severity|enhancement                 |normal

--- Comment #1 from Seb <greensunny12@gmail.com> ---
Argh I accidentally hit submit.

The reason for the resubmission is that the following code compiles fine already:

cat > main.d << EOF
void main() @safe
{
    struct Foo
    {
        int i;
        ~this() // <- no need to annotate with @safe explicitly here
        {
            assert(1);
        }
        void m(){}  // <- no need to annotate with @safe explicitly here
    }

    Foo foo;
    foo.m();
}
EOF

So DMD already does transitively apply @safe, but apparently if it generated for associative arrays this generation doesn't work in all cases.

--
March 27, 2018
https://issues.dlang.org/show_bug.cgi?id=18672

hsteoh@quickfur.ath.cx changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |hsteoh@quickfur.ath.cx

--
March 27, 2018
https://issues.dlang.org/show_bug.cgi?id=18672

ag0aep6g <ag0aep6g@gmail.com> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |ag0aep6g@gmail.com

--- Comment #2 from ag0aep6g <ag0aep6g@gmail.com> ---
(In reply to Seb from comment #1)
> So DMD already does transitively apply @safe, but apparently if it generated for associative arrays this generation doesn't work in all cases.

It's not the associative array. It's just that the generated opAssign isn't
@safe (for no reason):

----
void main() @safe
{
    struct ThrowingElement
    {
        ~this() {}
    }

    ThrowingElement aa;
        /* Accepted. The destructor is apparently inferred as @safe. */
    aa = aa;
        /* Error: @safe function D main cannot call @system generated
        function onlineapp.main.ThrowingElement.opAssign */
}
----

--
March 28, 2018
https://issues.dlang.org/show_bug.cgi?id=18672

Carsten Blüggel <chilli@posteo.net> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |chilli@posteo.net

--
March 29, 2018
https://issues.dlang.org/show_bug.cgi?id=18672

RazvanN <razvan.nitu1305@gmail.com> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |razvan.nitu1305@gmail.com

--- Comment #3 from RazvanN <razvan.nitu1305@gmail.com> ---
(In reply to ag0aep6g from comment #2)
> (In reply to Seb from comment #1)
> > So DMD already does transitively apply @safe, but apparently if it generated for associative arrays this generation doesn't work in all cases.
> 
> It's not the associative array. It's just that the generated opAssign isn't
> @safe (for no reason):
> 
> ----
> void main() @safe
> {
>     struct ThrowingElement
>     {
>         ~this() {}
>     }
> 
>     ThrowingElement aa;
>         /* Accepted. The destructor is apparently inferred as @safe. */
>     aa = aa;
>         /* Error: @safe function D main cannot call @system generated
>         function onlineapp.main.ThrowingElement.opAssign */
> }
> ----

That's because the generated opAssign is not @safe. Look at [1] : it injects a pointer which is void initialized, after that the function is inferred to be @system. I tried replacing the void initializer with null, or with a new ExpInitializer(loc, new ThisExp(loc)). That solves the current test case, but ends up failing other tests (for reasons unknown)

[1] https://github.com/dlang/dmd/blob/master/src/dmd/clone.d#L273

--
April 02, 2018
https://issues.dlang.org/show_bug.cgi?id=18672

--- Comment #4 from Seb <greensunny12@gmail.com> ---
@RazvanN how about setting the opAssign to @trusted instead when we now that
the dtor is @safe?
The problem is that sd.dtor.isSafe() returns 0 :/
Maybe we need to go through semantic first before looking at this?
Also there seems to be an existing check for this already - it just doesn't get
triggered

```
stc = mergeFuncAttrs(stc, sd.dtor);
if (stc & STC.safe)
```

Well at least the high-level isSafe traits infers the safety correctly:

https://run.dlang.io/is/6ePqDY

--
August 23, 2018
https://issues.dlang.org/show_bug.cgi?id=18672

--- Comment #5 from RazvanN <razvan.nitu1305@gmail.com> ---
PR : https://github.com/dlang/dmd/pull/8607

--
December 17, 2022
https://issues.dlang.org/show_bug.cgi?id=18672

Iain Buclaw <ibuclaw@gdcproject.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
           Priority|P1                          |P3

--
December 13
https://issues.dlang.org/show_bug.cgi?id=18672

--- Comment #6 from dlangBugzillaToGithub <robert.schadek@posteo.de> ---
THIS ISSUE HAS BEEN MOVED TO GITHUB

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

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

--