YAML-like structured binary data representation language (partially based on Python).
Project description
libvstruct2
YAML-like structured binary data representation language (partially based on Python). Goals:
- brief
- expressive (capable to describe most contemporary file/data formats)
- human-readable
- fast (enough)
- easy to parse
- easy to translate into Python parsers
- WARNING: very alpha release, many things are still broken / can change.
Note: some automagical conversions happen when translating .vs2 sources to .py sources to simplify
writing the definitions (to-be-documented). See the included file formats for examples.
Vlad Topan (vtopan/gmail), Feb. 2020
Format
- YAML-like, mapping structures to
- field:typelists or detailed field descriptions.
- field:
- type
- key1: value1
- key2: value2
- example:
StructName:
- field1: I4 # 4-byte integer - this is ignored
- field2:
- a[100]
- desc: some 4-byte integer field
- offset: 1234
- shorthands exist (see
PFX_MAPinlibvstruct2/defparser.pyfor a full mapping), the [Fields][] section below for details:@ ...is equivalent to- offset: ...= ...is equivalent to- validator: ...(dynamic expression, exact value or collection)? ...is equivalent to- lookahead: ...(preview data, don't consume buffer)
VStruct objects
Each VStruct object (structure or field) has the obvious attributes (.offset, .size, .value, .parent, etc.) and
some less obvious attributes and methods:
.root: the top-level VStruct which initiated the parsing process.first_parent(type_or_typename): returns the first (grand)parent of the given type
Fields
- syntax:
<indent>- <fieldname>: <fieldtype>followed optionally by additional modifiers- most modifiers also have a short syntax, either as a modifier prefix or as a suffix to the
<fieldtype>- prefix example:
- dyn_offset: <offset>is the same as@ <offset> - suffix example:
- field1: R[<length>]is the same as- field1: Rfollowed by- length: <length>
- prefix example:
- modifiers (with prefixes/suffixes in parenthesis where available):
- prefixes:
validator(=): after evaluation, test the resulting value with this expression- can be a
list/tuple,dict, callable or exact (immediate) value
- can be a
should_be(?=): same asvalidator, but instead of stopping the parser, only a warning is issueddyn_offset(@): dynamic offset - evaluated at runtime (seeDynExpr)formatter(~): used to format the value for display - a callable or adict(if value is not in dict,?is returned)hidden(.): don't display when displaying the structure (flag used for internal / irrelevant fields)description("..."): field descriptionbit_map({...}): masks mapping bits to nameslookahead(?): parsing the field won't consume from the buffer (the current offset is not changed)out_of_struct(*): the field does not follow from the current offset (this is set automatically bydyn_offset)required(!): flag which marks a conditional field as required (raisesParseErrorif missing)post_parse(;): function to be called after parsing for additional processing (receives an object instance)post_parse_value(:): function to be called after parsing to further process the value (receives the object instance, must return the new value)- can also be a list of functions if the value is a sequence (only the values will be passed to the functions)
- suffixes:
length([...]): number of elements (field becomes an array, i.e.listof fields)- exception: for string and regex types, the
lengthmeans the number of characters! - if the value starts with
<, it is interpreted asmaxlen(maximum length), e.g. for NULL-terminated strings
- exception: for string and regex types, the
condition(<...>):DynExprwhich, if evaluates to False, the field is considered "not present"
- no shortcut syntax (yet):
update_offset: flag which causes an out-of-struct field to still update its parent's.offsetendianness: little ('<') or big ('>'), default: little- note: this is inherited from parent structures if not defined in fields
stop: alternative stop condition (DynExpr) for arrays (in this case,lengthmay be simplyTrue)second_pass: (only for out_of_struct nodes) parse only on a second pass
- prefixes:
- virtual fields can be created with the syntax:
- <fieldname> := <expression>(their.sizewill be 0, but the.offsetwill be correct)- these are instances of the
Evalbasic type
- these are instances of the
- most modifiers also have a short syntax, either as a modifier prefix or as a suffix to the
Expressions
DynExpr
- most values can be defined as dynamic expressions (to reference other fields which become available during parsing)
- automagically identified by trying to parse each expression as an immediate; on failure, a DynExpr is created
- syntax:
$<field>extracts the value of<field>in the current (VStruct) structure (equivalent toself.<field>.value)@<field>the offset of<field>(self.<field>.offset):<field>the size of<field>(self.<field>.size)&<attr>extracts the value of an attribute of the current VStruct (equivalent toself.<attr>)- parent objects can be referenced using
^, e.g.:&^^==self.parent.parent$^Field1==self.parent.Field1.value
- notes:
- depending on the context,
selfis usually the currentVStruct(e.g. when evaluatingconditions,lengths, etc.); an exception exist though -selfis the current field when validating (validatorexpressions)
- depending on the context,
Regex expressions
- the match is attempted from the current position
- format:
<op>/<regex>/<flags><op>: what result to return- default (no
<op>field): bool (Trueif matched) @: match offset or -1:: match length
- default (no
<flags>: sequence of classic regex flags (sdotall,mmultiline,icase insensitive) and custom flags:f: attempt match in full file (default: 8k from current offset)
Datatypes
- see
libvstruct2/basefields.pyfor the implementation of all the basic types
Numbers
Integers
I1/I2/I4/I8: signed 1/2/4/8-byte integer (default endianness, little if none set)PK1..8: packed integer (DWARF3 LEB128) - TBD- signedness prefix:
S/U(default: unsigned) - endianness suffix:
B: big endianL: little endianE: dynamic endianness (set by a conditional expression in the struct)- default: little endian
Real numbers
F2/F4: floating-point 2/4-byte real numbers (float/double)
Bit masks (flags)
BM#(#is the number of bytes, e.g.BM2): flags- accepts a
bit_map({ ... }) key which maps bits/bit groups to names
- accepts a
Text & binary blobs
a/u8/16/32/w/r: null-terminated ASCII / UTF 8/16/32 / widechar / raw (binary) string (C strings) - TBDAS[len]/WS[len]/R[len]: fixed/maximum-length ASCII / widechar / raw (binary) string (LPSTR/PWSTR)
RegEx-based fields
RX: basic (binary) regex field (the actual regex must be passed as the condition, e.g.- MyField: RX <^abc>).valuewill contain the groups tuple if more than one, a singlebytesotherwise.raw_matchwill contain the full (binary) match
T: string token (ignores whitespace) - multiple values separated by a comma (e.g.- MyField: T <a, b, cde>)SRX: string regex (UTF-8encoded)IS: integer string (textual integer);.valuewill be the actual number
Keys
- any type can be followed by any number of "keys" (indented
- name: valuefields) with supplemental rules / information
Feedback
Feedback is welcome via email or as issues on the gitlab project.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file libvstruct2-2.0.5.tar.gz.
File metadata
- Download URL: libvstruct2-2.0.5.tar.gz
- Upload date:
- Size: 58.0 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/5.1.0 CPython/3.12.2
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
e48fe04627951031e6573b5f06977c852d196e9fcd3275a0a5223110e051b4ad
|
|
| MD5 |
15e7c60b935b4309831188d356893165
|
|
| BLAKE2b-256 |
f38be50cf2b3459bcb60a45ead38aa729d957656694b33f55947b03ddebd8586
|
File details
Details for the file libvstruct2-2.0.5-py3-none-any.whl.
File metadata
- Download URL: libvstruct2-2.0.5-py3-none-any.whl
- Upload date:
- Size: 72.9 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/5.1.0 CPython/3.12.2
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
4966d98cd7d1035d255da9ab9ba7ec9b95a3f26dbb114ea837d934af6fe2662e
|
|
| MD5 |
07d12f2e366490b087114791d942cfb8
|
|
| BLAKE2b-256 |
e066e6ae4ed6b4aebe300e032c407c2c9afbc00265f2c2f2f6d5a2484ed9cf0b
|