Thread overview
BitArray contracts
Aug 24, 2010
bearophile
Aug 24, 2010
bearophile
August 24, 2010
This a part of std.bitmanip.BitArray:


    void init(void[] v, size_t numbits)
    in
    {
        assert(numbits <= v.length * 8);
        assert((v.length & 3) == 0);
    }
    body
    {
        ptr = cast(uint*)v.ptr;
        len = numbits;
    }


But it seems this program works with no errors:

import std.bitmanip: BitArray;
void main() {
    ubyte[4] data;
    BitArray bits;
    bits.init(data, 100);
}


Do you kno why is this assert present?
assert((v.length & 3) == 0);

Isn't this enough?
assert((v.length & 2) == 0);

Bye,
bearophile
August 24, 2010
On Mon, 23 Aug 2010 22:49:14 -0400, bearophile <bearophileHUGS@lycos.com> wrote:

> This a part of std.bitmanip.BitArray:
>
>
>     void init(void[] v, size_t numbits)
>     in
>     {
>         assert(numbits <= v.length * 8);
>         assert((v.length & 3) == 0);
>     }
>     body
>     {
>         ptr = cast(uint*)v.ptr;
>         len = numbits;
>     }
>
>
> But it seems this program works with no errors:
>
> import std.bitmanip: BitArray;
> void main() {
>     ubyte[4] data;
>     BitArray bits;
>     bits.init(data, 100);
> }

If bitarray is not a template, then it's compiled in release mode inside phobos.  The in contract is probably not compiled in.

> Do you kno why is this assert present?
> assert((v.length & 3) == 0);
>
> Isn't this enough?
> assert((v.length & 2) == 0);

The first is asserting that v.length is a multiple of 4, I think the point is to be able to manipulate all the data using words.  Yours is asserting, well, it's asserting that the second bit is not set.  That yields the following sequence:

0,1,4,5,8,9,12,13...

I'm not sure why you want that sequence.

-Steve
August 24, 2010
Steven Schveighoffer:
> If bitarray is not a template, then it's compiled in release mode inside phobos.  The in contract is probably not compiled in.

I see, it's the problem discussed recently, with the proposal of the two phobos libs, one compiled with -release and one without, that the compiler chooses according to the type of your compilation.


> The first is asserting that v.length is a multiple of 4, I think the point is to be able to manipulate all the data using words.  Yours is asserting, well, it's asserting that the second bit is not set.  That yields the following sequence:
> 
> 0,1,4,5,8,9,12,13...
> 
> I'm not sure why you want that sequence.

You are right, I was very wrong (to avoid such errors I use the modulus % for that purpose, the compiler optimizes it away).
But CPU words may be 8 bytes long too, so in that code I prefer:
assert(v.length % size_t.sizeof == 0);

Bye and thank you,
bearophile