Please take a look
bearophile
bearophileHUGS at lycos.com
Sat Dec 22 06:14:56 PST 2007
Lukas Pinkowski:
>Taking a look at it, I see, you've done the following:
>
> uint opCast() {
> //return (up << 16) | low; // worse?
> return *(cast(uint*)(cast(void*)this));
> }
>
> You really should uncomment the first line and remove the second, since
> uint* is a pointer to a 4-byte type, while your struct holds 3 bytes.
> Thus dereferencing the uint* will lead to a 4th byte with an arbitrary
> value and finally to errors.
I belive you; code similar to that ( (up << 16) | low ) was the first thing I have written.
The funny thing is that (before posting the code on this newsgroup) I have written almost 200 lines of testing code along the code for those 24 bit unsigned integers, and they have failed catching the bug you talk about :-]
This other piece of testing code too fails spotting the problem:
import std.random, u24;
int randInt(int max) {
int k, n;
n = max + 1;
k = cast(int)(n * (rand / (uint.max + 1.0)));
return (k == n) ? k - 1 : k;
}
void main() {
Uint24[200_000] arr;
assert(arr.sizeof == 200_000*3);
rand_seed(10, 0);
foreach(ref u; arr)
u = randInt(Uint24.max);
rand_seed(10, 0);
foreach(i, u; arr)
assert(u == randInt(Uint24.max));
}
Eventually I'll probably put back code like that ( (up << 16) | low ) because I must write safe code (despite being slower) but so far I have failed finding testcases that make that double casting fail :-) Can you show me an example where if shows the bug?
Bye and thank you,
bearophile
More information about the Digitalmars-d-learn
mailing list