diff options
| author | Ophestra <cat@gensokyo.uk> | 2025-11-25 04:16:11 +0900 |
|---|---|---|
| committer | Ophestra <cat@gensokyo.uk> | 2025-11-25 04:16:11 +0900 |
| commit | 88d3e464136db5192e311e4be077aa3db218e5f2 (patch) | |
| tree | d7e6f5155dd66a7b752456d213f92036a486eb3e /internal/pipewire | |
| parent | e51e81bb22a85f0324a80a32bb2b10f3a8616e17 (diff) | |
internal/pipewire: implement Client::UpdateProperties
This is the second message on the captured sample.
Signed-off-by: Ophestra <cat@gensokyo.uk>
Diffstat (limited to 'internal/pipewire')
| -rw-r--r-- | internal/pipewire/client.go | 51 | ||||
| -rw-r--r-- | internal/pipewire/client_test.go | 442 | ||||
| -rw-r--r-- | internal/pipewire/header_test.go | 14 | ||||
| -rw-r--r-- | internal/pipewire/pipewire.go | 35 |
4 files changed, 507 insertions, 35 deletions
diff --git a/internal/pipewire/client.go b/internal/pipewire/client.go new file mode 100644 index 00000000..4480dc8e --- /dev/null +++ b/internal/pipewire/client.go @@ -0,0 +1,51 @@ +package pipewire + +/* pipewire/client.h */ + +const ( + PW_TYPE_INTERFACE_Client = PW_TYPE_INFO_INTERFACE_BASE + "Client" + PW_CLIENT_PERM_MASK = PW_PERM_RWXM + PW_VERSION_CLIENT = 3 + + PW_ID_CLIENT = 1 +) + +const ( + PW_CLIENT_CHANGE_MASK_PROPS = 1 << iota + + PW_CLIENT_CHANGE_MASK_ALL = 1<<iota - 1 +) + +const ( + PW_CLIENT_EVENT_INFO = iota + PW_CLIENT_EVENT_PERMISSIONS + PW_CLIENT_EVENT_NUM + + PW_VERSION_CLIENT_EVENTS = 0 +) + +const ( + PW_CLIENT_METHOD_ADD_LISTENER = iota + PW_CLIENT_METHOD_ERROR + PW_CLIENT_METHOD_UPDATE_PROPERTIES + PW_CLIENT_METHOD_GET_PERMISSIONS + PW_CLIENT_METHOD_UPDATE_PERMISSIONS + PW_CLIENT_METHOD_NUM + + PW_VERSION_CLIENT_METHODS = 0 +) + +// ClientUpdateProperties is used to update the properties of a client. +type ClientUpdateProperties struct { + // Props are properties to update on the client. + Props *SPADict +} + +// MarshalBinary satisfies [encoding.BinaryMarshaler] via [Marshal]. +func (c *ClientUpdateProperties) MarshalBinary() ([]byte, error) { return Marshal(c) } + +// UnmarshalBinary satisfies [encoding.BinaryUnmarshaler] via [Unmarshal]. +func (c *ClientUpdateProperties) UnmarshalBinary(data []byte) error { + _, err := Unmarshal(data, c) + return err +} diff --git a/internal/pipewire/client_test.go b/internal/pipewire/client_test.go new file mode 100644 index 00000000..744c5187 --- /dev/null +++ b/internal/pipewire/client_test.go @@ -0,0 +1,442 @@ +package pipewire_test + +import ( + "testing" + + "hakurei.app/internal/pipewire" +) + +func TestClientUpdateProperties(t *testing.T) { + encodingTestCases[pipewire.ClientUpdateProperties, *pipewire.ClientUpdateProperties]{ + {"sample", []byte{ + // ClientUpdateProperties: size + 0xf8, 5, 0, 0, + // ClientUpdateProperties: struct + 0xe, 0, 0, 0, + + // ClientUpdateProperties.Props: size + 0xf0, 5, 0, 0, + // ClientUpdateProperties.Props: struct + 0xe, 0, 0, 0, + + // ClientUpdateProperties.Props.NItems: size + 4, 0, 0, 0, + // ClientUpdateProperties.Props.NItems: int + 4, 0, 0, 0, + 0x1e, 0, 0, 0, + 0, 0, 0, 0, + + // ClientUpdateProperties.Props.Items + + 0x11, 0, 0, 0, + 8, 0, 0, 0, + 0x72, 0x65, 0x6d, 0x6f, + 0x74, 0x65, 0x2e, 0x69, + 0x6e, 0x74, 0x65, 0x6e, + 0x74, 0x69, 0x6f, 0x6e, + 0, 0, 0, 0, + 0, 0, 0, 0, + + 8, 0, 0, 0, + 8, 0, 0, 0, + 0x6d, 0x61, 0x6e, 0x61, + 0x67, 0x65, 0x72, 0, + + 0x11, 0, 0, 0, + 8, 0, 0, 0, + 0x61, 0x70, 0x70, 0x6c, + 0x69, 0x63, 0x61, 0x74, + 0x69, 0x6f, 0x6e, 0x2e, + 0x6e, 0x61, 0x6d, 0x65, + 0, 0, 0, 0, + 0, 0, 0, 0, + 0xd, 0, 0, 0, + 8, 0, 0, 0, + 0x70, 0x77, 0x2d, 0x63, + 0x6f, 0x6e, 0x74, 0x61, + 0x69, 0x6e, 0x65, 0x72, + 0, 0, 0, 0, + 0x1b, 0, 0, 0, + 8, 0, 0, 0, + 0x61, 0x70, 0x70, 0x6c, + 0x69, 0x63, 0x61, 0x74, + 0x69, 0x6f, 0x6e, 0x2e, + 0x70, 0x72, 0x6f, 0x63, + 0x65, 0x73, 0x73, 0x2e, + 0x62, 0x69, 0x6e, 0x61, + 0x72, 0x79, 0, 0, + 0, 0, 0, 0, + 0xd, 0, 0, 0, + 8, 0, 0, 0, + 0x70, 0x77, 0x2d, 0x63, + 0x6f, 0x6e, 0x74, 0x61, + 0x69, 0x6e, 0x65, 0x72, + 0, 0, 0, 0, + 0x15, 0, 0, 0, + 8, 0, 0, 0, + 0x61, 0x70, 0x70, 0x6c, + 0x69, 0x63, 0x61, 0x74, + 0x69, 0x6f, 0x6e, 0x2e, + 0x6c, 0x61, 0x6e, 0x67, + 0x75, 0x61, 0x67, 0x65, + 0, 0, 0, 0, + 0xc, 0, 0, 0, + 8, 0, 0, 0, + 0x65, 0x6e, 0x5f, 0x55, + 0x53, 0x2e, 0x55, 0x54, + 0x46, 0x2d, 0x38, 0, + 0, 0, 0, 0, + 0x17, 0, 0, 0, + 8, 0, 0, 0, + 0x61, 0x70, 0x70, 0x6c, + 0x69, 0x63, 0x61, 0x74, + 0x69, 0x6f, 0x6e, 0x2e, + 0x70, 0x72, 0x6f, 0x63, + 0x65, 0x73, 0x73, 0x2e, + 0x69, 0x64, 0, 0, + 5, 0, 0, 0, + 8, 0, 0, 0, + 0x31, 0x34, 0x34, 0x33, + 0, 0, 0, 0, + 0x19, 0, 0, 0, + 8, 0, 0, 0, + 0x61, 0x70, 0x70, 0x6c, + 0x69, 0x63, 0x61, 0x74, + 0x69, 0x6f, 0x6e, 0x2e, + 0x70, 0x72, 0x6f, 0x63, + 0x65, 0x73, 0x73, 0x2e, + 0x75, 0x73, 0x65, 0x72, + 0, 0, 0, 0, + 0, 0, 0, 0, + 6, 0, 0, 0, + 8, 0, 0, 0, + 0x61, 0x6c, 0x69, 0x63, + 0x65, 0, 0, 0, + 0x19, 0, 0, 0, + 8, 0, 0, 0, + 0x61, 0x70, 0x70, 0x6c, + 0x69, 0x63, 0x61, 0x74, + 0x69, 0x6f, 0x6e, 0x2e, + 0x70, 0x72, 0x6f, 0x63, + 0x65, 0x73, 0x73, 0x2e, + 0x68, 0x6f, 0x73, 0x74, + 0, 0, 0, 0, + 0, 0, 0, 0, + 6, 0, 0, 0, + 8, 0, 0, 0, + 0x6e, 0x69, 0x78, 0x6f, + 0x73, 0, 0, 0, + 0x1f, 0, 0, 0, + 8, 0, 0, 0, + 0x61, 0x70, 0x70, 0x6c, + 0x69, 0x63, 0x61, 0x74, + 0x69, 0x6f, 0x6e, 0x2e, + 0x70, 0x72, 0x6f, 0x63, + 0x65, 0x73, 0x73, 0x2e, + 0x73, 0x65, 0x73, 0x73, + 0x69, 0x6f, 0x6e, 0x2d, + 0x69, 0x64, 0, 0, + 2, 0, 0, 0, + 8, 0, 0, 0, + 0x31, 0, 0, 0, + 0, 0, 0, 0, + 0x13, 0, 0, 0, + 8, 0, 0, 0, + 0x77, 0x69, 0x6e, 0x64, + 0x6f, 0x77, 0x2e, 0x78, + 0x31, 0x31, 0x2e, 0x64, + 0x69, 0x73, 0x70, 0x6c, + 0x61, 0x79, 0, 0, + 0, 0, 0, 0, + 3, 0, 0, 0, + 8, 0, 0, 0, + 0x3a, 0x30, 0, 0, + 0, 0, 0, 0, + 0xc, 0, 0, 0, + 8, 0, 0, 0, + 0x63, 0x70, 0x75, 0x2e, + 0x76, 0x6d, 0x2e, 0x6e, + 0x61, 0x6d, 0x65, 0, + 0, 0, 0, 0, + 5, 0, 0, 0, + 8, 0, 0, 0, + 0x71, 0x65, 0x6d, 0x75, + 0, 0, 0, 0, + 0xa, 0, 0, 0, + 8, 0, 0, 0, + 0x6c, 0x6f, 0x67, 0x2e, + 0x6c, 0x65, 0x76, 0x65, + 0x6c, 0, 0, 0, + 0, 0, 0, 0, + 2, 0, 0, 0, + 8, 0, 0, 0, + 0x30, 0, 0, 0, + 0, 0, 0, 0, + 0xe, 0, 0, 0, + 8, 0, 0, 0, + 0x63, 0x70, 0x75, 0x2e, + 0x6d, 0x61, 0x78, 0x2d, + 0x61, 0x6c, 0x69, 0x67, + 0x6e, 0, 0, 0, + 3, 0, 0, 0, + 8, 0, 0, 0, + 0x33, 0x32, 0, 0, + 0, 0, 0, 0, + 0x13, 0, 0, 0, + 8, 0, 0, 0, + 0x64, 0x65, 0x66, 0x61, + 0x75, 0x6c, 0x74, 0x2e, + 0x63, 0x6c, 0x6f, 0x63, + 0x6b, 0x2e, 0x72, 0x61, + 0x74, 0x65, 0, 0, + 0, 0, 0, 0, + 6, 0, 0, 0, + 8, 0, 0, 0, + 0x34, 0x38, 0x30, 0x30, + 0x30, 0, 0, 0, + 0x16, 0, 0, 0, + 8, 0, 0, 0, + 0x64, 0x65, 0x66, 0x61, + 0x75, 0x6c, 0x74, 0x2e, + 0x63, 0x6c, 0x6f, 0x63, + 0x6b, 0x2e, 0x71, 0x75, + 0x61, 0x6e, 0x74, 0x75, + 0x6d, 0, 0, 0, + 5, 0, 0, 0, + 8, 0, 0, 0, + 0x31, 0x30, 0x32, 0x34, + 0, 0, 0, 0, + 0x1a, 0, 0, 0, + 8, 0, 0, 0, + 0x64, 0x65, 0x66, 0x61, + 0x75, 0x6c, 0x74, 0x2e, + 0x63, 0x6c, 0x6f, 0x63, + 0x6b, 0x2e, 0x6d, 0x69, + 0x6e, 0x2d, 0x71, 0x75, + 0x61, 0x6e, 0x74, 0x75, + 0x6d, 0, 0, 0, + 0, 0, 0, 0, + 3, 0, 0, 0, + 8, 0, 0, 0, + 0x33, 0x32, 0, 0, + 0, 0, 0, 0, + 0x1a, 0, 0, 0, + 8, 0, 0, 0, + 0x64, 0x65, 0x66, 0x61, + 0x75, 0x6c, 0x74, 0x2e, + 0x63, 0x6c, 0x6f, 0x63, + 0x6b, 0x2e, 0x6d, 0x61, + 0x78, 0x2d, 0x71, 0x75, + 0x61, 0x6e, 0x74, 0x75, + 0x6d, 0, 0, 0, + 0, 0, 0, 0, + 5, 0, 0, 0, + 8, 0, 0, 0, + 0x32, 0x30, 0x34, 0x38, + 0, 0, 0, 0, + 0x1c, 0, 0, 0, + 8, 0, 0, 0, + 0x64, 0x65, 0x66, 0x61, + 0x75, 0x6c, 0x74, 0x2e, + 0x63, 0x6c, 0x6f, 0x63, + 0x6b, 0x2e, 0x71, 0x75, + 0x61, 0x6e, 0x74, 0x75, + 0x6d, 0x2d, 0x6c, 0x69, + 0x6d, 0x69, 0x74, 0, + 0, 0, 0, 0, + 5, 0, 0, 0, + 8, 0, 0, 0, + 0x38, 0x31, 0x39, 0x32, + 0, 0, 0, 0, + 0x1c, 0, 0, 0, + 8, 0, 0, 0, + 0x64, 0x65, 0x66, 0x61, + 0x75, 0x6c, 0x74, 0x2e, + 0x63, 0x6c, 0x6f, 0x63, + 0x6b, 0x2e, 0x71, 0x75, + 0x61, 0x6e, 0x74, 0x75, + 0x6d, 0x2d, 0x66, 0x6c, + 0x6f, 0x6f, 0x72, 0, + 0, 0, 0, 0, + 2, 0, 0, 0, + 8, 0, 0, 0, + 0x34, 0, 0, 0, + 0, 0, 0, 0, + 0x14, 0, 0, 0, + 8, 0, 0, 0, + 0x64, 0x65, 0x66, 0x61, + 0x75, 0x6c, 0x74, 0x2e, + 0x76, 0x69, 0x64, 0x65, + 0x6f, 0x2e, 0x77, 0x69, + 0x64, 0x74, 0x68, 0, + 0, 0, 0, 0, + 4, 0, 0, 0, + 8, 0, 0, 0, + 0x36, 0x34, 0x30, 0, + 0, 0, 0, 0, + 0x15, 0, 0, 0, + 8, 0, 0, 0, + 0x64, 0x65, 0x66, 0x61, + 0x75, 0x6c, 0x74, 0x2e, + 0x76, 0x69, 0x64, 0x65, + 0x6f, 0x2e, 0x68, 0x65, + 0x69, 0x67, 0x68, 0x74, + 0, 0, 0, 0, + 4, 0, 0, 0, + 8, 0, 0, 0, + 0x34, 0x38, 0x30, 0, + 0, 0, 0, 0, + 0x17, 0, 0, 0, + 8, 0, 0, 0, + 0x64, 0x65, 0x66, 0x61, + 0x75, 0x6c, 0x74, 0x2e, + 0x76, 0x69, 0x64, 0x65, + 0x6f, 0x2e, 0x72, 0x61, + 0x74, 0x65, 0x2e, 0x6e, + 0x75, 0x6d, 0, 0, + 3, 0, 0, 0, + 8, 0, 0, 0, + 0x32, 0x35, 0, 0, + 0, 0, 0, 0, + 0x19, 0, 0, 0, + 8, 0, 0, 0, + 0x64, 0x65, 0x66, 0x61, + 0x75, 0x6c, 0x74, 0x2e, + 0x76, 0x69, 0x64, 0x65, + 0x6f, 0x2e, 0x72, 0x61, + 0x74, 0x65, 0x2e, 0x64, + 0x65, 0x6e, 0x6f, 0x6d, + 0, 0, 0, 0, + 0, 0, 0, 0, + 2, 0, 0, 0, + 8, 0, 0, 0, + 0x31, 0, 0, 0, + 0, 0, 0, 0, + 0x1b, 0, 0, 0, + 8, 0, 0, 0, + 0x63, 0x6c, 0x6f, 0x63, + 0x6b, 0x2e, 0x70, 0x6f, + 0x77, 0x65, 0x72, 0x2d, + 0x6f, 0x66, 0x2d, 0x74, + 0x77, 0x6f, 0x2d, 0x71, + 0x75, 0x61, 0x6e, 0x74, + 0x75, 0x6d, 0, 0, + 0, 0, 0, 0, + 5, 0, 0, 0, + 8, 0, 0, 0, + 0x74, 0x72, 0x75, 0x65, + 0, 0, 0, 0, + 0x11, 0, 0, 0, + 8, 0, 0, 0, + 0x6c, 0x69, 0x6e, 0x6b, + 0x2e, 0x6d, 0x61, 0x78, + 0x2d, 0x62, 0x75, 0x66, + 0x66, 0x65, 0x72, 0x73, + 0, 0, 0, 0, + 0, 0, 0, 0, + 3, 0, 0, 0, + 8, 0, 0, 0, + 0x36, 0x34, 0, 0, + 0, 0, 0, 0, + 0xf, 0, 0, 0, + 8, 0, 0, 0, + 0x6d, 0x65, 0x6d, 0x2e, + 0x77, 0x61, 0x72, 0x6e, + 0x2d, 0x6d, 0x6c, 0x6f, + 0x63, 0x6b, 0, 0, + 6, 0, 0, 0, + 8, 0, 0, 0, + 0x66, 0x61, 0x6c, 0x73, + 0x65, 0, 0, 0, + 0x10, 0, 0, 0, + 8, 0, 0, 0, + 0x6d, 0x65, 0x6d, 0x2e, + 0x61, 0x6c, 0x6c, 0x6f, + 0x77, 0x2d, 0x6d, 0x6c, + 0x6f, 0x63, 0x6b, 0, + 5, 0, 0, 0, + 8, 0, 0, 0, + 0x74, 0x72, 0x75, 0x65, + 0, 0, 0, 0, + 0x17, 0, 0, 0, + 8, 0, 0, 0, + 0x73, 0x65, 0x74, 0x74, + 0x69, 0x6e, 0x67, 0x73, + 0x2e, 0x63, 0x68, 0x65, + 0x63, 0x6b, 0x2d, 0x71, + 0x75, 0x61, 0x6e, 0x74, + 0x75, 0x6d, 0, 0, + 6, 0, 0, 0, + 8, 0, 0, 0, + 0x66, 0x61, 0x6c, 0x73, + 0x65, 0, 0, 0, + 0x14, 0, 0, 0, + 8, 0, 0, 0, + 0x73, 0x65, 0x74, 0x74, + 0x69, 0x6e, 0x67, 0x73, + 0x2e, 0x63, 0x68, 0x65, + 0x63, 0x6b, 0x2d, 0x72, + 0x61, 0x74, 0x65, 0, + 0, 0, 0, 0, + 6, 0, 0, 0, + 8, 0, 0, 0, + 0x66, 0x61, 0x6c, 0x73, + 0x65, 0, 0, 0, + 0xd, 0, 0, 0, + 8, 0, 0, 0, + 0x63, 0x6f, 0x72, 0x65, + 0x2e, 0x76, 0x65, 0x72, + 0x73, 0x69, 0x6f, 0x6e, + 0, 0, 0, 0, + 6, 0, 0, 0, + 8, 0, 0, 0, + 0x31, 0x2e, 0x34, 0x2e, + 0x37, 0, 0, 0, + 0xa, 0, 0, 0, + 8, 0, 0, 0, + 0x63, 0x6f, 0x72, 0x65, + 0x2e, 0x6e, 0x61, 0x6d, + 0x65, 0, 0, 0, + 0, 0, 0, 0, + 0x14, 0, 0, 0, + 8, 0, 0, 0, + 0x70, 0x69, 0x70, 0x65, + 0x77, 0x69, 0x72, 0x65, + 0x2d, 0x61, 0x6c, 0x69, + 0x63, 0x65, 0x2d, 0x31, + 0x34, 0x34, 0x33, 0, + 0, 0, 0, 0, + }, pipewire.ClientUpdateProperties{Props: &pipewire.SPADict{NItems: 0x1e, Items: []pipewire.SPADictItem{ + {Key: "remote.intention", Value: "manager"}, + {Key: "application.name", Value: "pw-container"}, + {Key: "application.process.binary", Value: "pw-container"}, + {Key: "application.language", Value: "en_US.UTF-8"}, + {Key: "application.process.id", Value: "1443"}, + {Key: "application.process.user", Value: "alice"}, + {Key: "application.process.host", Value: "nixos"}, + {Key: "application.process.session-id", Value: "1"}, + {Key: "window.x11.display", Value: ":0"}, + {Key: "cpu.vm.name", Value: "qemu"}, + {Key: "log.level", Value: "0"}, + {Key: "cpu.max-align", Value: "32"}, + {Key: "default.clock.rate", Value: "48000"}, + {Key: "default.clock.quantum", Value: "1024"}, + {Key: "default.clock.min-quantum", Value: "32"}, + {Key: "default.clock.max-quantum", Value: "2048"}, + {Key: "default.clock.quantum-limit", Value: "8192"}, + {Key: "default.clock.quantum-floor", Value: "4"}, + {Key: "default.video.width", Value: "640"}, + {Key: "default.video.height", Value: "480"}, + {Key: "default.video.rate.num", Value: "25"}, + {Key: "default.video.rate.denom", Value: "1"}, + {Key: "clock.power-of-two-quantum", Value: "true"}, + {Key: "link.max-buffers", Value: "64"}, + {Key: "mem.warn-mlock", Value: "false"}, + {Key: "mem.allow-mlock", Value: "true"}, + {Key: "settings.check-quantum", Value: "false"}, + {Key: "settings.check-rate", Value: "false"}, + {Key: "core.version", Value: "1.4.7"}, + {Key: "core.name", Value: "pipewire-alice-1443"}, + }}}, nil}, + }.run(t) +} diff --git a/internal/pipewire/header_test.go b/internal/pipewire/header_test.go index 8501dc19..efcea71f 100644 --- a/internal/pipewire/header_test.go +++ b/internal/pipewire/header_test.go @@ -25,6 +25,20 @@ func TestHeader(t *testing.T) { }, pipewire.Header{ID: pipewire.PW_ID_CORE, Opcode: pipewire.PW_CORE_METHOD_HELLO, Size: 0x18, Sequence: 0, FileCount: 0}, nil}, + {"PW_CLIENT_METHOD_UPDATE_PROPERTIES", []byte{ + // Id + 1, 0, 0, 0, + // size + 0, 6, 0, + // opcode + 2, + // seq + 1, 0, 0, 0, + // n_fds + 0, 0, 0, 0, + }, pipewire.Header{ID: pipewire.PW_ID_CLIENT, Opcode: pipewire.PW_CLIENT_METHOD_UPDATE_PROPERTIES, + Size: 0x600, Sequence: 1, FileCount: 0}, nil}, + {"PW_SECURITY_CONTEXT_METHOD_CREATE", []byte{ // Id 3, 0, 0, 0, diff --git a/internal/pipewire/pipewire.go b/internal/pipewire/pipewire.go index 4b03a543..8f38bce3 100644 --- a/internal/pipewire/pipewire.go +++ b/internal/pipewire/pipewire.go @@ -14,41 +14,6 @@ // for any other uses of the protocol. package pipewire -/* pipewire/client.h */ - -const ( - PW_TYPE_INTERFACE_Client = PW_TYPE_INFO_INTERFACE_BASE + "Client" - PW_CLIENT_PERM_MASK = PW_PERM_RWXM - PW_VERSION_CLIENT = 3 - - PW_ID_CLIENT = 1 -) - -const ( - PW_CLIENT_CHANGE_MASK_PROPS = 1 << iota - - PW_CLIENT_CHANGE_MASK_ALL = 1<<iota - 1 -) - -const ( - PW_CLIENT_EVENT_INFO = iota - PW_CLIENT_EVENT_PERMISSIONS - PW_CLIENT_EVENT_NUM - - PW_VERSION_CLIENT_EVENTS = 0 -) - -const ( - PW_CLIENT_METHOD_ADD_LISTENER = iota - PW_CLIENT_METHOD_ERROR - PW_CLIENT_METHOD_UPDATE_PROPERTIES - PW_CLIENT_METHOD_GET_PERMISSIONS - PW_CLIENT_METHOD_UPDATE_PERMISSIONS - PW_CLIENT_METHOD_NUM - - PW_VERSION_CLIENT_METHODS = 0 -) - /* pipewire/device.h */ const ( |
