-
-
Notifications
You must be signed in to change notification settings - Fork 2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Feature] Bitfield with inverse variable bit 'endianness' #2041
Comments
In terms of bitfield ordering the only feature implemented and described in the documentation is the ability to read the fields of a bitfield in either one of the two possible orders. There is no syntax provided that would allow reading the bits of a variable in the reverse order than the one expected. For variables the best you can do is choose endianness, but within each byte, bits are always read in the same order. fn reverse(auto b) {
b = (b & 0xF0) >> 4 | (b & 0x0F) << 4;
b = (b & 0xCC) >> 2 | (b & 0x33) << 2;
b = (b & 0xAA) >> 1 | (b & 0x55) << 1;
return b;
}; |
Ah, that actually works thanks. Given I'm still relatively very very new to ImHex, I didn't expect that you could apply a format function via attribute on the fields of a bitfield; some of the other modifiers I tried weren't available; so I didn't think you could apply regular attributes. For anyone else reading, here's an example: fn reverse3bits(u8 b) {
b = (b & 0xF8) | ((b & 0x04) >> 2) | (b & 0x02) | ((b & 0x01) << 2);
return b;
};
// Mode 2 structure (128 bits)
bitfield BC7BlockMode2 {
unsigned mode : 3 [[format("reverse3bits")]]; // Mode bits (001)
unsigned partition : 6; // Partition number
// rest of bitfield.
} That fixes the opening post's case. |
For reference and to give credit where's due hare's the place I got it from |
What feature would you like to see?
The ability to represent variables with inverse bit order, where the 'lowest' bit represents the 'highest' bit.
i.e. a bit sequence of
00001
(highest to lowest bit) should represent32
(last bit is highest), and not1
(last bit is lowest).How will this feature be useful to you and others?
Some formats have bitfields whose fields are read in the following order:
Most to least significant bit (within a given byte)
be
to a field declaration before a bitfield.Treating the 'lowest' bit as the 'highest' (i.e. reversing bit order) at variable level.
In my case, I encountered a format with both.
The idea here being that the format is read as a bit 'stream' which is 'endian-free'. You read a bit (Most Significant Bit -> Least Significant Bit), shift an existing variable by 1, and OR the new value in. Therefore, the order of the bits within a field is reversed.
Request Type
Additional context?
As an example, I've been trying to parse BC7 blocks docs 1 docs 2 in the DDS file format; after doing some things with BZip3 pattern; however, I'm unable to currently correctly represent the struct fields.
In this screenshot, the
mode
field should read4
rather than1
; because it appears as the last bit[001]00000
in the byte; however it's interpreted as1
instead. Same applies to other fields.I have tried all permutations of
[[bitfield_order]]
attribute andbe / le
specifier; including also nesting structs with mixed endianness etc. Nothing appears to work.In the case of the screenshot I used
be
on the field declaration with no attribute (it gets me the correct layout, just not ordering). I've also dug the wiki quite hard, but I cannot find the answer.The text was updated successfully, but these errors were encountered: