aboutsummaryrefslogtreecommitdiffhomepage
path: root/internal/pipewire/pod.go
diff options
context:
space:
mode:
Diffstat (limited to 'internal/pipewire/pod.go')
-rw-r--r--internal/pipewire/pod.go46
1 files changed, 46 insertions, 0 deletions
diff --git a/internal/pipewire/pod.go b/internal/pipewire/pod.go
index 523322f7..15ff25c3 100644
--- a/internal/pipewire/pod.go
+++ b/internal/pipewire/pod.go
@@ -5,6 +5,7 @@ import (
"io"
"math"
"reflect"
+ "slices"
"strconv"
)
@@ -573,3 +574,48 @@ func (d *SPADict) UnmarshalPOD(data []byte) (Word, error) {
}
return wireSize, nil
}
+
+// A Message is a value that can be transmitted as a message over PipeWire protocol native.
+type Message interface {
+ // Opcode returns the opcode of this message.
+ Opcode() byte
+ // FileCount returns the number of files associated with this message.
+ FileCount() Int
+
+ KnownSize
+}
+
+// A MessageEncoder provides methods for encoding a [Message].
+type MessageEncoder struct{ Message }
+
+// SizeMessage returns the size of Message transmitted over protocol native.
+func (m MessageEncoder) SizeMessage(footer KnownSize) (size Word) {
+ size = SizeHeader + m.Message.Size()
+ if footer != nil {
+ size += footer.Size()
+ }
+ return
+}
+
+// AppendMessage appends the protocol native encoding of Message to dst and returns the appended slice.
+func (m MessageEncoder) AppendMessage(dst []byte, Id, sequence Int, footer KnownSize) (data []byte, err error) {
+ size := m.SizeMessage(footer)
+ if size&^SizeMax != 0 {
+ return dst, ErrSizeRange
+ }
+
+ data = slices.Grow(dst, int(size))
+ data = (&Header{
+ ID: Id,
+ Opcode: m.Message.Opcode(),
+ Size: size - SizeHeader,
+ Sequence: sequence,
+ FileCount: m.Message.FileCount(),
+ }).append(data)
+ data, err = MarshalAppend(data, m.Message)
+ if err == nil && footer != nil {
+ data, err = MarshalAppend(data, footer)
+ }
+
+ return
+}