Thread overview | ||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
March 28, 2020 Spec on casting to integer with smaller range than value | ||||
---|---|---|---|---|
| ||||
Hi all, Where can I read in the spec what the outcomes of the following are? ``` uint a = 260; auto b = cast(ubyte) a; float f = 1.203125f * 255.0f; auto zz = cast(ubyte) f; // https://github.com/ldc-developers/ldc/issues/3237 ``` Thanks, Johan |
March 28, 2020 Re: Spec on casting to integer with smaller range than value | ||||
---|---|---|---|---|
| ||||
Posted in reply to Johan | On Saturday, 28 March 2020 at 12:09:49 UTC, Johan wrote:
> Hi all,
> Where can I read in the spec what the outcomes of the following are?
>
> ```
> uint a = 260;
> auto b = cast(ubyte) a;
>
> float f = 1.203125f * 255.0f;
> auto zz = cast(ubyte) f;
> // https://github.com/ldc-developers/ldc/issues/3237
> ```
>
> Thanks,
> Johan
cast (ubyte)x is the same as = ((cast(uint)x) & 0xff)
|
March 28, 2020 Re: Spec on casting to integer with smaller range than value | ||||
---|---|---|---|---|
| ||||
Posted in reply to Johan | On Saturday, 28 March 2020 at 12:09:49 UTC, Johan wrote: > float f = 1.203125f * 255.0f; > auto zz = cast(ubyte) f; > // https://github.com/ldc-developers/ldc/issues/3237 The 2nd cast, float to int, should be https://dlang.org/spec/expression.html#cast_expressions, §7: 'Casting a floating point value to an integral type is the equivalent of converting to an integer using truncation.' It doesn't specify the behavior if that integer doesn't fit; that should probably be explicitly mentioned as undefined behavior, to account for the observed LLVM/gcc behavior. |
March 28, 2020 Re: Spec on casting to integer with smaller range than value | ||||
---|---|---|---|---|
| ||||
Posted in reply to kinke | On Saturday, 28 March 2020 at 15:33:35 UTC, kinke wrote:
> that should probably be explicitly mentioned as undefined behavior, to account for the observed LLVM/gcc behavior.
Which would make `cast(int) someFloat` not allowed in @safe code.
Is there any chance LLVM could be instructed to treat it as implementation-defined behavior?
|
March 28, 2020 Re: Spec on casting to integer with smaller range than value | ||||
---|---|---|---|---|
| ||||
Posted in reply to Dennis | On Saturday, 28 March 2020 at 15:47:04 UTC, Dennis wrote:
> On Saturday, 28 March 2020 at 15:33:35 UTC, kinke wrote:
>> that should probably be explicitly mentioned as undefined behavior, to account for the observed LLVM/gcc behavior.
>
> Which would make `cast(int) someFloat` not allowed in @safe code.
@safe is about memory corruption, not about disallowing any undefined behavior.
|
March 28, 2020 Re: Spec on casting to integer with smaller range than value | ||||
---|---|---|---|---|
| ||||
Posted in reply to kinke | On Saturday, 28 March 2020 at 16:06:39 UTC, kinke wrote: > @safe is about memory corruption, not about disallowing any undefined behavior. The spec provides two definitions: > Safe functions are functions that are statically checked to exhibit no possibility of undefined behavior. Undefined behavior is often used as a vector for malicious attacks. https://dlang.org/spec/function.html#function-safety > Memory Safety for a program is defined as it being impossible for the program to corrupt memory. Therefore, the safe subset of D consists only of programming language features that are guaranteed to never result in memory corruption. https://dlang.org/spec/memory-safe-d.html Presence of undefined behavior is sufficient to cause memory corruption, and memory corruption itself is undefined behavior, so the definitions are equivalent and both describe the same thing. |
March 28, 2020 Re: Spec on casting to integer with smaller range than value | ||||
---|---|---|---|---|
| ||||
Posted in reply to Dennis | On Saturday, 28 March 2020 at 16:15:08 UTC, Dennis wrote: > Presence of undefined behavior is sufficient to cause memory corruption, and memory corruption itself is undefined behavior, so the definitions are equivalent and both describe the same thing. This came up before in different discussions: https://github.com/dlang/dlang.org/pull/2578#discussion_r257200332 https://forum.dlang.org/post/qu53go$r6v$1@digitalmars.com |
March 28, 2020 Re: Spec on casting to integer with smaller range than value | ||||
---|---|---|---|---|
| ||||
Posted in reply to Dennis | On Saturday, 28 March 2020 at 15:47:04 UTC, Dennis wrote: > Which would make `cast(int) someFloat` not allowed in @safe code. In LLVM lingo, the out-of-bounds cast wouldn't be undefined behavior per se, but yield a 'poison' value, whose later usage might eventually trigger undefined behavior, depending on what exactly you're doing with it. > Safe functions are functions that are statically checked to exhibit no possibility of undefined behavior. If that's really the ultimate goal, then these casts would probably need a prefixed bounds check in @safe code, just like an array bounds check (incl. omitting it if it can be statically determined to fit). |
March 28, 2020 Re: Spec on casting to integer with smaller range than value | ||||
---|---|---|---|---|
| ||||
Posted in reply to Stefan Koch | On Saturday, 28 March 2020 at 15:23:19 UTC, Stefan Koch wrote:
>
> cast (ubyte)x is the same as = ((cast(uint)x) & 0xff)
Where does the spec say that?
-Johan
|
March 29, 2020 Re: Spec on casting to integer with smaller range than value | ||||
---|---|---|---|---|
| ||||
Posted in reply to Johan | On Saturday, 28 March 2020 at 19:11:04 UTC, Johan wrote: > On Saturday, 28 March 2020 at 15:23:19 UTC, Stefan Koch wrote: >> >> cast (ubyte)x is the same as = ((cast(uint)x) & 0xff) > > Where does the spec say that? > > -Johan > cast(uint)x is the trunc() that happens when casting a FP to integral type. https://dlang.org/spec/expression.html#cast_expressions §7. > & 0xFF is not specified but is the normal part of the cast uint -> ubyte. |
Copyright © 1999-2021 by the D Language Foundation