VRP and signed <-> unsigned conversion

Steven Schveighoffer schveiguy at gmail.com
Wed Dec 15 14:39:09 UTC 2021


Here's an interesting situation that I hadn't considered before:

```d
ubyte foo(ubyte a, ubyte b)
{
    return (a & 0xf) - (b & 0xf);
}
```

This fails to compile because the VRP of both integer operands is 0 - 
15. This gives a VRP of the result of -15 to 15, which does not fit into 
a `ubyte`.

However, -15 to 15 *does* fit into a `byte`. And a `byte` implicitly 
casts to a `ubyte`, so you can rewrite the function:

```d
ubyte foo(ubyte a, ubyte b)
{
    byte result = (a & 0xf) - (b & 0xf);
    return result;
}
```

I'm wondering:

1. Does it make sense for this to be valid? Should we reexamine unsigned 
<-> signed implicit casting?
2. If the above rewrite is possible, shouldn't VRP just allow this 
conversion? i.e. a type that has an unsigned/signed counterpart should 
be assignable if the signed/unsigned can accept the range.

-Steve


More information about the Digitalmars-d mailing list