Bit Fields

Bit-level parsing for protocols that pack data at the bit level.

Available Types

  • BitStruct - Container for bit-level fields

  • Bit - Single bit (boolean)

  • Bits - Multiple bits (integer)

  • EmbeddedBitStruct - Embed BitStruct in a Struct

BitStruct

Define a bit-level structure:

from pystructs import BitStruct, Bit, Bits

class TCPFlags(BitStruct):
    class Meta:
        size = 1  # 1 byte = 8 bits

    fin = Bit()
    syn = Bit()
    rst = Bit()
    psh = Bit()
    ack = Bit()
    urg = Bit()
    reserved = Bits(2)

flags = TCPFlags.parse(b"\x12")
print(flags.syn)  # True
print(flags.ack)  # True

Bit

Single bit field (boolean value):

class Flags(BitStruct):
    class Meta:
        size = 1

    enabled = Bit()
    active = Bit()
    ready = Bit()
    # ...

Bits

Multiple bits field (integer value):

class ControlByte(BitStruct):
    class Meta:
        size = 1

    mode = Bits(3)      # 3 bits: 0-7
    priority = Bits(2)  # 2 bits: 0-3
    reserved = Bits(3)

ctrl = ControlByte.parse(b"\x4a")
print(ctrl.mode)      # 2
print(ctrl.priority)  # 1

EmbeddedBitStruct

Embed a BitStruct within a regular Struct:

from pystructs import Struct, UInt16, EmbeddedBitStruct

class TCPHeader(Struct):
    class Meta:
        endian = "big"

    src_port = UInt16()
    dst_port = UInt16()
    flags = EmbeddedBitStruct(TCPFlags)

header = TCPHeader.parse(b"\x00\x50\x1f\x90\x12")
print(header.src_port)   # 80
print(header.flags.syn)  # True

Multi-Byte BitStruct

For bit fields spanning multiple bytes:

class StatusRegister(BitStruct):
    class Meta:
        size = 2  # 16 bits

    error_code = Bits(4)
    warning_level = Bits(4)
    state = Bits(4)
    version = Bits(4)

API Reference

class pystructs.fields.bitfields.BitStruct(**kwargs: Any)[source]

Base class for bit-level structures.

BitStruct allows defining fields at the bit level within a fixed-size byte container. Fields are packed in declaration order.

Example:
>>> class StatusByte(BitStruct):
...     class Meta:
...         size = 1  # 1 byte = 8 bits
...     enabled = Bit()
...     mode = Bits(3)
...     reserved = Bits(4)
...
>>> status = StatusByte.parse(b'\x15')
>>> status.enabled
True
>>> status.mode
2
classmethod parse(data: bytes) T[source]

Parse binary data into a BitStruct instance.

Args:

data: Binary data to parse

Returns:

Parsed BitStruct instance

Raises:

UnexpectedEOF: If not enough bytes available

to_bytes() bytes[source]

Serialize the BitStruct to bytes.

Returns:

Serialized bytes

to_dict() Dict[str, Any][source]

Convert to a dictionary.

Returns:

Dictionary with field names as keys

class pystructs.fields.bitfields.Bit(default: Any = None)[source]

Single bit field (boolean).

Examples:
>>> class StatusBits(BitStruct):
...     class Meta:
...         size = 1
...     enabled = Bit()
...     ready = Bit()
...     error = Bit()
property bits: int

Number of bits this field occupies.

extract(value: int, offset: int) bool[source]

Extract a single bit as boolean.

Args:

value: The integer value containing all bits offset: Bit offset within the integer

Returns:

True if bit is set, False otherwise

insert(current: int, value: Any, offset: int) int[source]

Insert a boolean as a single bit.

Args:

current: The current integer value value: Boolean value to insert offset: Bit offset within the integer

Returns:

Updated integer with the bit set or cleared

class pystructs.fields.bitfields.Bits(num_bits: int, default: int = 0)[source]

Multi-bit field (unsigned integer).

Examples:
>>> class PackedData(BitStruct):
...     class Meta:
...         size = 1
...     type_id = Bits(3)   # 3 bits for type (0-7)
...     value = Bits(5)     # 5 bits for value (0-31)
property bits: int

Number of bits this field occupies.

extract(value: int, offset: int) int[source]

Extract multiple bits as unsigned integer.

Args:

value: The integer value containing all bits offset: Bit offset within the integer

Returns:

Extracted unsigned integer value

insert(current: int, value: Any, offset: int) int[source]

Insert an unsigned integer into multiple bits.

Args:

current: The current integer value value: Integer value to insert (will be masked) offset: Bit offset within the integer

Returns:

Updated integer with the value inserted

class pystructs.fields.bitfields.EmbeddedBitStruct(bitstruct_class: Type[BitStruct], default: BitStruct | None = None, required: bool = True, validators: List[Callable] | None = None)[source]

Embedded BitStruct field for use in regular Struct.

Examples:
>>> class StatusByte(BitStruct):
...     class Meta:
...         size = 1
...     enabled = Bit()
...     mode = Bits(7)
...
>>> class Packet(Struct):
...     status = EmbeddedBitStruct(StatusByte)
...     data = UInt16()
parse(buffer: BinaryIO, instance: Any) BitStruct[source]

Parse BitStruct from buffer.

Args:

buffer: Binary stream to read from instance: The parent struct instance

Returns:

Parsed BitStruct instance

serialize(value: BitStruct, instance: Any) bytes[source]

Serialize BitStruct to bytes.

Args:

value: The BitStruct to serialize instance: The parent struct instance

Returns:

Serialized bytes