What's the bug in the following code:
```d
import std.digest.md;
import std.stdio;
pragma(inline, false) // just in case
string getHash()
{
ubyte[16] hash = [1,2,3,4,5,6,6,78,8,8,7,7,6,3,2,3];
string a = toHexString(hash);
return a;
}
pragma(inline, false) // just in case
void destroystack()
{
writeln("asd","asd","asd","asd","asd","asd");
}
void main()
{
string a = getHash();
destroystack();
writeln(a);
}
```
It prints garbage after the "asdasdasdasdasdasd" line.
Hint: when changing
```
string a = toHexString(hash);
return a;
```
to
```
return toHexString(hash);
```
the compiler errors with:
`Error: escaping reference to stack allocated value returned by toHexString(hash)`.
So:
- the documentation of toHexString says that the overloads returning a string return a GC allocated string
- the _implementation_ of `string toHexString(...)` does a `new char[16]`, so GC allocates.
- `string a = toHexString(hash);` calls `char[num*2] toHexString(...)` instead of `string toHexString(...)`. OOPS.
I don't know whether this is a compiler bug (choosing the wrong overload) or a Phobos bug (overloads don't work like that).
The underlying issue is the allowance to slice a static array RValue, which can never be valid. This is issue 12625.
Now, we may fix this, and then what happens is that your code that compiled before now doesn't compile with the same message as the "bad" version. But that's not good either. toHexString should work on a static array without creating another static array.
So I'll leave this bug open.
Comment #3 by greensunny12 — 2018-02-27T22:13:47Z
FWIW -dip1000 warns about this problem:
foo.d(8): Deprecation: slice of static array temporary returned by toHexString(hash) assigned to longer lived variable a
but I still think we should do something about the API.
Comment #4 by dfj1esp02 — 2018-03-20T15:40:45Z
(In reply to Seb from comment #3)
> foo.d(8): Deprecation: slice of static array temporary returned by
> toHexString(hash) assigned to longer lived variable a
>
> but I still think we should do something about the API.
Slicing a temporary and storing it anywhere should be deprecated in unsafe code too. It should be valid to only pass it as a function argument.
Comment #5 by bugzilla — 2019-12-30T15:01:32Z
(In reply to Steven Schveighoffer from comment #2)
> toHexString should work on a static array without
> creating another static array.
>
> So I'll leave this bug open.
What's wrong with this?
(In reply to Seb from comment #3)
> FWIW -dip1000 warns about this problem:
>
> foo.d(8): Deprecation: slice of static array temporary returned by
> toHexString(hash) assigned to longer lived variable a
Can't find any information on when this deprecation cycle will end. Do you know?
Comment #6 by robert.schadek — 2024-12-01T16:27:53Z