Python BinField的二进制数据处理实现
项目描述
binfield
Python binfield实现,用于二进制数据处理。
为什么?Python支持通过二进制运算进行二进制数据操作,速度很快,但阅读起来很困难,尤其是在原型设计时,尤其是对于复杂(嵌套)结构。
这个库旨在解决这个问题:它允许像字典一样使用常量索引操作二进制数据:只需定义结构类并创建一个具有起始数据的实例。现在您可以使用索引来读取和写入数据
优点:
免费软件:Apache许可协议
自文档化代码:注释中的docstrings和类型
已测试:请参阅顶部的徽章
支持多个Python版本
Python 2.7 Python 3.4 Python 3.5 Python 3.6 Python 3.7 PyPy PyPy3 Jyton 2.7
用法
可以简单地从BinField类创建未映射的对象
bf = BinField(42)
应将具有固定大小的数据创建为新的类(类型):示例基于实际数据(ZigBee帧控制字段)
# Describe
class ZBFrameControl(binfield.BinField):
_size_ = 16 # Optional, used as source for mask, if mask is not defined
_mask_ = 0xFF7F # Optional, used as source for size, if size is not defined
FrameType = [0, 3] # Enum
Security = 3
FramePending = 4
AckRequest = 5
PAN_ID_Compression = 6
SecurityNumberSuppress = 8
InformationPresent = 9
DstAddrMode = [10, 12]
FrameVersion = [12, 14]
SrcAddrMode = [14, 16]
# Construct from frame
# (limitation: endian conversion is not supported, make it using another tools)
frame = frame = ZBFrameControl(0x0803) # Beacon request
>>> print(frame)
<2051 == 0x0803 == (0b0000100000000011 & 0b1111111111111111)
FrameType = <3 == 0x03 == (0b011 & 0b111)>
Security = <0 == 0x00 == (0b0 & 0b1)>
FramePending = <0 == 0x00 == (0b0 & 0b1)>
AckRequest = <0 == 0x00 == (0b0 & 0b1)>
PAN_ID_Compression = <0 == 0x00 == (0b0 & 0b1)>
SecurityNumberSuppress = <0 == 0x00 == (0b0 & 0b1)>
InformationPresent = <0 == 0x00 == (0b0 & 0b1)>
DstAddrMode = <2 == 0x02 == (0b10 & 0b11)>
FrameVersion = <0 == 0x00 == (0b00 & 0b11)>
SrcAddrMode = <0 == 0x00 == (0b00 & 0b11)>
>>> repr(frame)
'ZBFrameControl(x=0x0803, base=16)'
>>> print(frame.FrameType)
<3 == 0x03 == (0b011 & 0b111)> # Get nested structure: current is flat, so we have single value
# We can use slice to get bits from value: result type is always subclass of BinField
>>> repr(frame.FrameType[: 2])
'<FrameType_slice_0_2(x=0x03, base=16) at 0x7FD0ACA57408>'
>>> frame.FrameType == 3 # Transparent comparision with integers
True
>>> int(frame.FrameType) # Painless conversion to int
3
>>> bool(frame.AckRequest) # And bool
False
>>> print(frame[1: 5]) # Ignore indexes and just get few bits using slice
<1 == 0x01 == (0b0001 & 0b1111)>
>>> print(ZBFrameControl.AckRequest) # Request indexes from created data type
5
>>> print(ZBFrameControl.DstAddrMode) # Multiple bits too
slice(10, 12, None)
# Modification of nested data (if no type conversion was used) changes original object:
>>> frame.AckRequest = 1
>>> print(frame)
<2083 == 0x0823 == (0b0000100000100011 & 0b1111111101111111)
FrameType = <3 == 0x03 == (0b011 & 0b111)>
Security = <0 == 0x00 == (0b0 & 0b1)>
FramePending = <0 == 0x00 == (0b0 & 0b1)>
AckRequest = <1 == 0x01 == (0b1 & 0b1)>
PAN_ID_Compression = <0 == 0x00 == (0b0 & 0b1)>
SecurityNumberSuppress = <0 == 0x00 == (0b0 & 0b1)>
InformationPresent = <0 == 0x00 == (0b0 & 0b1)>
DstAddrMode = <2 == 0x02 == (0b10 & 0b11)>
FrameVersion = <0 == 0x00 == (0b00 & 0b11)>
SrcAddrMode = <0 == 0x00 == (0b00 & 0b11)>
>
# But remember, that nested blocks has it's own classes
>>> repr(frame.DstAddrMode)
'<DstAddrMode(x=0x02, base=16) at 0x7FD0AD139548>'
>>> fr2 = ZBFrameControl(0xFFFF)
>>> repr(fr2)
'ZBFrameControl(x=0xFF7F, base=16)' # Mask if applied, if defined
# Fields can be set only from integers
>>> frame.SrcAddrMode = fr2.SrcAddrMode
Traceback (most recent call last):
...
TypeError: BinField value could be set only as int
>>> repr(frame['FramePending']) # __getitem__ and __setitem__ is supported
'<FramePending(x=0x00, base=16) at 0x7FD0ACAD3188>'
支持嵌套结构,如果需要的话。定义示例(不与任何实际数据对齐)
class NestedMappedBinField(BinField):
test_index = 0
nested_block = {
'_index_': (1, 6),
'single_bit': 0,
'multiple': (1, 3)
}
>>> bf = NestedMappedBinField(0xFF)
# No _size_ and no _mask_ -> size is not limited,
# but indexes can not be changed after class creation
>>> print(bf)
<255 == 0xFF == (0b11111111)
test_index = <1 == 0x01 == (0b1 & 0b1)>
nested_block =
<31 == 0x1F == (0b11111 & 0b11111)
single_bit = <1 == 0x01 == (0b1 & 0b1)>
multiple = <3 == 0x03 == (0b11 & 0b11)>
>
>
# Get nested block: nested block is structured.
>>> print(bf.nested_block)
<31 == 0x1F == (0b11111 & 0b11111)
single_bit = <1 == 0x01 == (0b1 & 0b1)>
multiple = <3 == 0x03 == (0b11 & 0b11)>
>
注意: 负索引按设计不支持!
测试
该软件包 binfield 的主要测试机制使用 tox。可用的测试环境:
pep8 py27 py34 py35 py36 pypy pypy3 pylint docs
持续集成(CI)系统
为了代码检查,同时使用多个CI系统。
Travis CI:用于检查:PEP8、pylint、bandit、安装可能性以及单元测试。同时,它在coveralls上发布覆盖率。
coveralls:用于显示覆盖率。
持续部署(CD)系统
Travis CI:用于在PyPI上发布软件包。
项目详情
下载文件
下载适用于您平台的文件。如果您不确定选择哪个,请了解更多关于 安装包 的信息。
源代码分发
BinField-0.9.3.tar.gz (27.1 kB 查看哈希值)
构建分发
BinField-0.9.3-py3-none-any.whl (17.9 kB 查看哈希值)
关闭
BinField-0.9.3.tar.gz的哈希值
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 655e06476769ec45694453d67cc0d7c17668a4d4873dc1bb4b9d86f360f75f99 |
|
MD5 | add875d49bd4d5889a7bcad9daaf948d |
|
BLAKE2b-256 | cf8e1090f5117025c24dedbb0eb3f1f59bba8e3bc493a7e19105daa10f30bc99 |
关闭
BinField-0.9.3-py3-none-any.whl的哈希值
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 58731833ffcbb5bd71668c5bad44327ce367ba01f7b64fd3da8455b9844fd1f5 |
|
MD5 | 578648bdff6fd58f72d7aba683edec74 |
|
BLAKE2b-256 | eb0285c7269c7b71af42a5d8273c456b8c16d6ead5be279707c8c57d4cfa79ce |