February 03, 2022
On Thursday, 3 February 2022 at 03:25:39 UTC, H. S. Teoh wrote:
> On Thu, Feb 03, 2022 at 02:01:34AM +0000, forkit via Digitalmars-d-learn wrote: [...]
>> would be nice if the compiler told me something though :-(
>> 
>> i.e. "hey, dude, you really wanna to that?"
>
> Mark your function @safe, and the compiler will stop you from unsafe casts of this nature. That's part of the reason we have @safe. ;-)
>
>
> T

so i mark all my modules as @safe, by default.

I commented it out though, so I could do the cast.

Then realised I didn't need the cast at all, just the .dup

now it's @safe again.

But @safe or not, nothing good can come from casting an immutable string to a mutable string, and the compiler really should know that ;-)

February 03, 2022
I know we are talking about something else but just to make sure, there is no need for the cast, copy, or .reverse:

     const palindrome = "able was I ere I saw elba";
     writeln(palindrome);
     writeln(palindrome.retro);

Ali

February 03, 2022

On 2/3/22 12:53 AM, forkit wrote:

>

But @safe or not, nothing good can come from casting an immutable string to a mutable string, and the compiler really should know that ;-)

If you have a function that accepts mutable data, but you know for that call it won't mutate the data (or maybe it's a C function that never mutates the data, but isn't attributed with const/immutable), then it is not UB.

It's only UB to cast away immutable/const and mutate it.

Reference: https://dlang.org/spec/const3.html#removing_with_cast

-Steve

February 03, 2022

On 2/2/22 10:07 PM, Tejas wrote:

>

On Wednesday, 2 February 2022 at 23:21:52 UTC, forkit wrote:

>

Any reason why compiling this with ldc would cause the exe to crash?

Compiling with DMD (using either declaration of palindrome works just fine though)

// ----

module test;

import std;

void main()
{
    char[] palindrome = cast(char[])"able was I ere I saw elba";

   //char[] palindrome = ['a','b','l','e','w','a','s','I','e','r','e','I','s','a','w','e','l','b','a'];

    writeln(palindrome);

    // note: The line below causes the exe to crash when compiled with ldc
    // but only if using the first version of palindrome.

    writeln(palindrome.reverse);
}

// ---

This segfaults even on dmd 2.098.0 for me.
Clearly implementation defined behavior.

Note that on Windows DMD, string literals are not marked as Read only. This is legacy from the D1 days when strings were actually typed as char[]. In fact, if you mutate the data, then it mutated the literal, so if you used the literal later, then you got the mutated version!

e.g.:

auto str = "foo";
str[0] = 'b';
writeln("foo"); // outputs "boo"

On Linux, the literals were marked as ROM, and so you get a runtime fault. If you search back to the D1 days you can find posts about this difference between Windows and Linux.

I'm assuming LDC and GDC follow the same practice as Linux DMD.

-Steve

February 04, 2022
On Thursday, 3 February 2022 at 02:01:34 UTC, forkit wrote:
> On Thursday, 3 February 2022 at 01:57:12 UTC, H. S. Teoh wrote:
>>
>
> would be nice if the compiler told me something though :-(
>
> i.e. "hey, dude, you really wanna to that?"

would be nice if programmers (C or D) learnt that a typecast means "shut up compiler I know what I do". You explicitly instructed the compiler to not complain.

Remove the typecast and the compiler will bring an error.

That's the reason why typecasts are to be avoided as much as possible.It is often a code smell.
February 04, 2022
On Friday, 4 February 2022 at 10:09:22 UTC, Patrick Schluter wrote:
> On Thursday, 3 February 2022 at 02:01:34 UTC, forkit wrote:
>> On Thursday, 3 February 2022 at 01:57:12 UTC, H. S. Teoh wrote:
>>>
>>
>> would be nice if the compiler told me something though :-(
>>
>> i.e. "hey, dude, you really wanna to that?"
>
> would be nice if programmers (C or D) learnt that a typecast means "shut up compiler I know what I do". You explicitly instructed the compiler to not complain.
>
> Remove the typecast and the compiler will bring an error.
>
> That's the reason why typecasts are to be avoided as much as possible.It is often a code smell.

In C, I would have no such expectation.

The cast will occur whether I typed it in or not. My problem was, that I forgot the .dup

For the compiler to allow me to cast from immutable to mutable (without the .dup), makes about as much sense as the compiler allowing this:

int i;
i = "Hello";

February 04, 2022
On Friday, 4 February 2022 at 10:09:22 UTC, Patrick Schluter wrote:
> On Thursday, 3 February 2022 at 02:01:34 UTC, forkit wrote:
>> On Thursday, 3 February 2022 at 01:57:12 UTC, H. S. Teoh wrote:
>>>
>>
>> would be nice if the compiler told me something though :-(
>>
>> i.e. "hey, dude, you really wanna to that?"
>
> would be nice if programmers (C or D) learnt that a typecast means "shut up compiler I know what I do". You explicitly instructed the compiler to not complain.
>
> Remove the typecast and the compiler will bring an error.
>
> That's the reason why typecasts are to be avoided as much as possible.It is often a code smell.

If I had wrote the code below, then I should not expect anything, whatsoever, from the compiler.

() @trustMe_I_am_a_complete_idiot { char[] palindrome = cast(char[])"able was I ere I saw elba";  } ();

February 04, 2022
On Friday, 4 February 2022 at 11:26:42 UTC, forkit wrote:

> If I had wrote the code below, then I should not expect anything, whatsoever, from the compiler.
>
> () @trustMe_I_am_a_complete_idiot { char[] palindrome = cast(char[])"able was I ere I saw elba";  } ();

This is almost exactly what you have to do today, assuming you're using @safe. You'll **have** to write this then:

`() @trusted { auto palindrome = cast(char[])"able was I ere I saw elba"; } ();`

Instead, you opted to comment out `@safe`. Unfortunately, "@safe by default" idea was brutally eviscerated.

As others have already stated, casting immutability away is something that has to be supported, e.g. to interface with const-agnostic APIs. `@safe` requires such casts to be more verbose, with good reason.
February 04, 2022
On Fri, Feb 04, 2022 at 03:58:19PM +0000, Stanislav Blinov via Digitalmars-d-learn wrote: [...]
> As others have already stated, casting immutability away is something that has to be supported, e.g. to interface with const-agnostic APIs. `@safe` requires such casts to be more verbose, with good reason.

Not to mention, casting to/from immutable is necessary in order to be able to implement D's GC in D.

Basically, a cast is equivalent to telling the compiler "I know what I'm doing, don't complain".  Generally casts should be avoided except under special circumstances.


T

-- 
Fact is stranger than fiction.
February 05, 2022
On Friday, 4 February 2022 at 15:58:19 UTC, Stanislav Blinov wrote:
>
> ..
> ...
> As others have already stated, casting immutability away is something that has to be supported, e.g. to interface with const-agnostic APIs. `@safe` requires such casts to be more verbose, with good reason.

I concede ;-)

That the compiler knows this is @safe:
cast(char[])iStr.dup;

and this is not @safe:
cast(char[])iStr;

is sufficent.