novice2 wrote: > does anyone know: is D2 std.bitmanip compatible with C bitfields? > can i use it, if i need translate .h file with something like this: > > typedef struct { > unsigned int can_compress : 1; > unsigned int can_uncompress : 1; > unsigned int can_get_info : 1; > unsigned int : 7; > unsigned int : 16; > unsigned int : 16; > unsigned int : 16; > unsigned int : 16; > unsigned int : 16; > } capabilities; > > Thanks.
Here's a way to do it. Enjoy! :) Usage example: struct Test { ushort bits; mixin GroupPackedAccess!(bits, ubyte, "stuff", 3, bool, "otherstuff" ); } module packed; template PackedAccessTools(string NAME, int from, int to) { const max = 1 << (to-from); static if (to >= 32) static assert(false, "Too large"); else static if (to >= 16) alias uint type; else static if (to >= 8) alias ushort type; else alias ubyte type; // 0 .. 4 -> ((1 << 4):16 - 1):15 & ~0 -> 7 == 1111 // 4 .. 8 -> ((1 << 8):256 - 1):255 & ~((1 << 4): 16 - 1):15 -> 11110000 const type mask = ((1 << to) - 1) - ((1 << from) - 1); const ID = NAME~"_"~from.stringof~"_"~to.stringof; } template PackedAccess(alias VAR, T, string NAME, int from, int to) { mixin(ctReplace(` T NAME() { static if (is(T == bool)) return (VAR & (°.mask)) != 0; else return cast(T) ((VAR & (°.mask)) >> from); } T NAME(T nv) { Assert(nv < °.max, "Value too big"); VAR &= (~°.mask); VAR |= (nv << from); return nv; } `, "NAME", NAME, "°", "PackedAccessTools!(NAME, from, to)", "·", PackedAccessTools!(NAME, from, to).ID )); } template NaturalTypeSize(T) { static if (is(T==bool)) const NaturalTypeSize = 1; else static assert(false, "No known default size for "~T.stringof~"!"); } template GroupPackedAccess(alias VAR, T...) { static if (T.length > 2) { static if (is(typeof(T[0])==void)) { static if (is(typeof(T[4]): int) && !is(T[4]: int)) { mixin PackedAccess!(VAR, T[2], T[3], T[1], T[1]+T[4]); mixin GroupPackedAccess!(VAR, void, T[1]+T[4], T[5 ..$]); } else { mixin PackedAccess!(VAR, T[2], T[3], T[1], T[1]+NaturalTypeSize!(T[2])); mixin GroupPackedAccess!(VAR, void, T[1]+NaturalTypeSize!(T[2]), T[4 ..$]); } } else { mixin GroupPackedAccess!(VAR, void, 0, T); } } }