v2 / vlib / encoding / cbor / raw.v
41 lines · 38 sloc · 1.28 KB · 468855eef1db0ff73c62be2d1bf176ffa0e1478e
Raw
1module cbor
2
3// RawMessage holds the byte-exact encoding of one CBOR data item as it
4// appeared on the wire. Useful for caching/forwarding code that wants to
5// defer decoding of a nested field.
6//
7// struct Envelope {
8// id int
9// payload cbor.RawMessage // bytes preserved as-is
10// }
11//
12// raw := cbor.decode[cbor.RawMessage](bytes)!
13// back := cbor.encode(raw, cbor.EncodeOpts{})! // identical bytes
14pub struct RawMessage {
15pub mut:
16 data []u8
17}
18
19// pack_raw appends a RawMessage's bytes to the Packer without re-encoding.
20// An empty RawMessage is rejected: emitting zero bytes would silently
21// drop the slot when the value is a struct field or array element,
22// shifting every subsequent item by one — almost always a caller bug.
23@[inline]
24pub fn (mut p Packer) pack_raw(raw RawMessage) ! {
25 if raw.data.len == 0 {
26 return error('cbor: pack_raw called with empty RawMessage')
27 }
28 p.reserve(raw.data.len)
29 unsafe { p.buf.push_many(raw.data.data, raw.data.len) }
30}
31
32// unpack_raw captures the bytes of the next value without building a
33// Value tree. Returns an owned clone, safe to outlive the unpacker.
34@[direct_array_access]
35pub fn (mut u Unpacker) unpack_raw() !RawMessage {
36 start := u.pos
37 u.skip_value()!
38 return RawMessage{
39 data: u.data[start..u.pos].clone()
40 }
41}
42