blob: 7e5c5684dc5ac84b79411d3d14bf52bd104399fb [file] [log] [blame]
khenaidooa46458b2021-12-15 16:50:44 -05001package codec
2
3import (
4 "io"
5
6 "github.com/golang/protobuf/proto"
Abhay Kumara2ae5992025-11-10 14:02:24 +00007
khenaidooa46458b2021-12-15 16:50:44 -05008 "github.com/jhump/protoreflect/internal/codec"
9)
10
11// ErrOverflow is returned when an integer is too large to be represented.
12var ErrOverflow = codec.ErrOverflow
13
14// ErrBadWireType is returned when decoding a wire-type from a buffer that
15// is not valid.
16var ErrBadWireType = codec.ErrBadWireType
17
18// NB: much of the implementation is in an internal package, to avoid an import
19// cycle between this codec package and the desc package. We export it from
20// this package, but we can't use a type alias because we also need to add
21// methods to it, to broaden the exposed API.
22
23// Buffer is a reader and a writer that wraps a slice of bytes and also
24// provides API for decoding and encoding the protobuf binary format.
25//
26// Its operation is similar to that of a bytes.Buffer: writing pushes
27// data to the end of the buffer while reading pops data from the head
28// of the buffer. So the same buffer can be used to both read and write.
29type Buffer codec.Buffer
30
31// NewBuffer creates a new buffer with the given slice of bytes as the
32// buffer's initial contents.
33func NewBuffer(buf []byte) *Buffer {
34 return (*Buffer)(codec.NewBuffer(buf))
35}
36
37// SetDeterministic sets this buffer to encode messages deterministically. This
38// is useful for tests. But the overhead is non-zero, so it should not likely be
39// used outside of tests. When true, map fields in a message must have their
40// keys sorted before serialization to ensure deterministic output. Otherwise,
41// values in a map field will be serialized in map iteration order.
42func (cb *Buffer) SetDeterministic(deterministic bool) {
43 (*codec.Buffer)(cb).SetDeterministic(deterministic)
44}
45
46// IsDeterministic returns whether or not this buffer is configured to encode
47// messages deterministically.
48func (cb *Buffer) IsDeterministic() bool {
49 return (*codec.Buffer)(cb).IsDeterministic()
50}
51
52// Reset resets this buffer back to empty. Any subsequent writes/encodes
53// to the buffer will allocate a new backing slice of bytes.
54func (cb *Buffer) Reset() {
55 (*codec.Buffer)(cb).Reset()
56}
57
58// Bytes returns the slice of bytes remaining in the buffer. Note that
59// this does not perform a copy: if the contents of the returned slice
60// are modified, the modifications will be visible to subsequent reads
61// via the buffer.
62func (cb *Buffer) Bytes() []byte {
63 return (*codec.Buffer)(cb).Bytes()
64}
65
66// String returns the remaining bytes in the buffer as a string.
67func (cb *Buffer) String() string {
68 return (*codec.Buffer)(cb).String()
69}
70
71// EOF returns true if there are no more bytes remaining to read.
72func (cb *Buffer) EOF() bool {
73 return (*codec.Buffer)(cb).EOF()
74}
75
76// Skip attempts to skip the given number of bytes in the input. If
77// the input has fewer bytes than the given count, io.ErrUnexpectedEOF
78// is returned and the buffer is unchanged. Otherwise, the given number
79// of bytes are skipped and nil is returned.
80func (cb *Buffer) Skip(count int) error {
81 return (*codec.Buffer)(cb).Skip(count)
82
83}
84
85// Len returns the remaining number of bytes in the buffer.
86func (cb *Buffer) Len() int {
87 return (*codec.Buffer)(cb).Len()
88}
89
90// Read implements the io.Reader interface. If there are no bytes
91// remaining in the buffer, it will return 0, io.EOF. Otherwise,
92// it reads max(len(dest), cb.Len()) bytes from input and copies
93// them into dest. It returns the number of bytes copied and a nil
94// error in this case.
95func (cb *Buffer) Read(dest []byte) (int, error) {
96 return (*codec.Buffer)(cb).Read(dest)
97}
98
99var _ io.Reader = (*Buffer)(nil)
100
101// Write implements the io.Writer interface. It always returns
102// len(data), nil.
103func (cb *Buffer) Write(data []byte) (int, error) {
104 return (*codec.Buffer)(cb).Write(data)
105}
106
107var _ io.Writer = (*Buffer)(nil)
108
109// DecodeVarint reads a varint-encoded integer from the Buffer.
110// This is the format for the
111// int32, int64, uint32, uint64, bool, and enum
112// protocol buffer types.
113func (cb *Buffer) DecodeVarint() (uint64, error) {
114 return (*codec.Buffer)(cb).DecodeVarint()
115}
116
117// DecodeTagAndWireType decodes a field tag and wire type from input.
118// This reads a varint and then extracts the two fields from the varint
119// value read.
120func (cb *Buffer) DecodeTagAndWireType() (tag int32, wireType int8, err error) {
121 return (*codec.Buffer)(cb).DecodeTagAndWireType()
122}
123
124// DecodeFixed64 reads a 64-bit integer from the Buffer.
125// This is the format for the
126// fixed64, sfixed64, and double protocol buffer types.
127func (cb *Buffer) DecodeFixed64() (x uint64, err error) {
128 return (*codec.Buffer)(cb).DecodeFixed64()
129}
130
131// DecodeFixed32 reads a 32-bit integer from the Buffer.
132// This is the format for the
133// fixed32, sfixed32, and float protocol buffer types.
134func (cb *Buffer) DecodeFixed32() (x uint64, err error) {
135 return (*codec.Buffer)(cb).DecodeFixed32()
136}
137
138// DecodeRawBytes reads a count-delimited byte buffer from the Buffer.
139// This is the format used for the bytes protocol buffer
140// type and for embedded messages.
141func (cb *Buffer) DecodeRawBytes(alloc bool) (buf []byte, err error) {
142 return (*codec.Buffer)(cb).DecodeRawBytes(alloc)
143}
144
145// ReadGroup reads the input until a "group end" tag is found
146// and returns the data up to that point. Subsequent reads from
147// the buffer will read data after the group end tag. If alloc
148// is true, the data is copied to a new slice before being returned.
149// Otherwise, the returned slice is a view into the buffer's
150// underlying byte slice.
151//
152// This function correctly handles nested groups: if a "group start"
153// tag is found, then that group's end tag will be included in the
154// returned data.
155func (cb *Buffer) ReadGroup(alloc bool) ([]byte, error) {
156 return (*codec.Buffer)(cb).ReadGroup(alloc)
157}
158
159// SkipGroup is like ReadGroup, except that it discards the
160// data and just advances the buffer to point to the input
161// right *after* the "group end" tag.
162func (cb *Buffer) SkipGroup() error {
163 return (*codec.Buffer)(cb).SkipGroup()
164}
165
166// SkipField attempts to skip the value of a field with the given wire
167// type. When consuming a protobuf-encoded stream, it can be called immediately
168// after DecodeTagAndWireType to discard the subsequent data for the field.
169func (cb *Buffer) SkipField(wireType int8) error {
170 return (*codec.Buffer)(cb).SkipField(wireType)
171}
172
173// EncodeVarint writes a varint-encoded integer to the Buffer.
174// This is the format for the
175// int32, int64, uint32, uint64, bool, and enum
176// protocol buffer types.
177func (cb *Buffer) EncodeVarint(x uint64) error {
178 return (*codec.Buffer)(cb).EncodeVarint(x)
179}
180
181// EncodeTagAndWireType encodes the given field tag and wire type to the
182// buffer. This combines the two values and then writes them as a varint.
183func (cb *Buffer) EncodeTagAndWireType(tag int32, wireType int8) error {
184 return (*codec.Buffer)(cb).EncodeTagAndWireType(tag, wireType)
185}
186
187// EncodeFixed64 writes a 64-bit integer to the Buffer.
188// This is the format for the
189// fixed64, sfixed64, and double protocol buffer types.
190func (cb *Buffer) EncodeFixed64(x uint64) error {
191 return (*codec.Buffer)(cb).EncodeFixed64(x)
192
193}
194
195// EncodeFixed32 writes a 32-bit integer to the Buffer.
196// This is the format for the
197// fixed32, sfixed32, and float protocol buffer types.
198func (cb *Buffer) EncodeFixed32(x uint64) error {
199 return (*codec.Buffer)(cb).EncodeFixed32(x)
200}
201
202// EncodeRawBytes writes a count-delimited byte buffer to the Buffer.
203// This is the format used for the bytes protocol buffer
204// type and for embedded messages.
205func (cb *Buffer) EncodeRawBytes(b []byte) error {
206 return (*codec.Buffer)(cb).EncodeRawBytes(b)
207}
208
209// EncodeMessage writes the given message to the buffer.
210func (cb *Buffer) EncodeMessage(pm proto.Message) error {
211 return (*codec.Buffer)(cb).EncodeMessage(pm)
212}
213
214// EncodeDelimitedMessage writes the given message to the buffer with a
215// varint-encoded length prefix (the delimiter).
216func (cb *Buffer) EncodeDelimitedMessage(pm proto.Message) error {
217 return (*codec.Buffer)(cb).EncodeDelimitedMessage(pm)
218}