Skip to content

Commit

Permalink
feat: YAML serializer (#53)
Browse files Browse the repository at this point in the history
* feat: draft an implementation of a YAML serializer for protobufs.

This introduces the `yara-x-proto-yaml` crate, which has a minimalistic API that takes a protobuf message and produces a YAML representation of it.

* fix: make the order of map entries stable

The `map` type in a protobuf is internally represented by a `HashMap`, which doesn't guarantee that items are always iterated in the the same order. The order may vary between executions, even if the map's content is the same. This means that we are forced to sort the items in the map before serializing them to YAML.

* feat: protobuf to yaml serialization

* fix: errors that occured while merging

* fix: clippy warnings

* chore: update comments

* feat: add support for PE module output in dumper

---------

Co-authored-by: Victor M. Alvarez <[email protected]>
  • Loading branch information
TommYDeeee and plusvic authored Nov 23, 2023
1 parent 3823821 commit f1f68a6
Show file tree
Hide file tree
Showing 23 changed files with 893 additions and 44 deletions.
122 changes: 122 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 2 additions & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ members = [
"yara-x-macros",
"yara-x-parser",
"yara-x-proto",
"yara-x-proto-yaml",
"yara-x-py",
]
resolver = "2"
Expand Down Expand Up @@ -83,6 +84,7 @@ yara-x-fmt = { path = "yara-x-fmt" }
yara-x-macros = { path = "yara-x-macros" }
yara-x-parser = { path = "yara-x-parser" }
yara-x-proto = { path = "yara-x-proto" }
yara-x-proto-yaml = { path = "yara-x-proto-yaml" }


[profile.release]
Expand Down
21 changes: 21 additions & 0 deletions docs/Module Developer's Guide.md
Original file line number Diff line number Diff line change
Expand Up @@ -146,6 +146,27 @@ actually field tags (i.e: a unique number identifying each field in a message).
This may be confusing if you are not familiar with protobuf's syntax, so again:
explore the protobuf's [documentation](https://developers.google.com/protocol-buffers).

One thing that can be done with integer fields is to represent them in some other way.
This optional representation is shown in `yr dump` crate output. This crate provides
two output formats: JSON and YAML. Both can be shown in colored output via `-c|--color` option.
The last mentioned also provides custom representation for integer numbers. Let's say
for some fields it makes sense to show them as hexadecimal numbers. This can be done by
adding `[(yara.field_options).yaml_fmt = "<format>"];` descriptor to the field.
Currently supported formats are: hexadecimal number and human-readable timestamp.
For example:

```
message Macho {
optional uint32 magic = 1 [(yara.field_options).yml_fmt= "x"];
}
```

This will mark magic field as a hexadecimal number and it will be shown as
`magic: 0xfeedfacf` instead of `4277009103`. Other format that is supported right now is
for timestamps. If you want to show some integer field as a timestamp you can do it by
setting `[(yara.field_options).yml_fmt = "t"];` descriptor to the field and
human readable timestamps will be shown in YAML comment after its integer value.

Also notice that we are defining our fields as `optional`. In `proto2` fields
must be either `optional` or `required`, while in `proto3` they are always
optional and can't be forced to be required. We are going to discuss this topic
Expand Down
8 changes: 6 additions & 2 deletions yara-x-cli/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -36,21 +36,25 @@ logging = ["dep:log", "dep:env_logger"]
[dependencies]
ascii_tree = { workspace = true }
anyhow = { workspace = true }
clap = { workspace = true, features=["cargo"] }
clap = { workspace = true, features=["cargo", "derive"] }
globwalk = { workspace = true }
enable-ansi-support = { workspace = true }
env_logger = { workspace = true , optional = true }
log = { workspace = true, optional = true }
protobuf = { workspace = true }
serde_json = { workspace = true }
protobuf-json-mapping = "3.3.0"
serde_json = { workspace = true, features = ["preserve_order"] }
yansi = { workspace = true }
yara-x = { workspace = true }
yara-x-parser = { workspace = true, features = ["ascii-tree"] }
yara-x-proto-yaml = { workspace = true }
yara-x-fmt = { workspace = true }

colored_json = "4.0.0"
crossbeam = "0.8.2"
crossterm = "0.27.0"
indent = "0.1.1"
pprof = { version = "0.13.0", features = ["flamegraph"], optional=true }
strum_macros = "0.25"
superconsole = "0.2.0"
wild = "2.1.0"
Loading

0 comments on commit f1f68a6

Please sign in to comment.