detached 33fbbb4

fix: pass PipeWire connect params by pointer array

commit
33fbbb461f4e5b256579d1f7659af13599bcaf41
author
brice · · 2026-04-10 15:21 UTC
parent
330b110
signature
GPG VerifiedCD88F9E564E0102646FB6077A1A07C7C7C3E349D · arch-gpg Verified for the committer email
2 files · +15 -7
M internal/capi/stream_params.go +3 -3
@@ -131,13 +131,13 @@ type connectParams struct {
131131 params []unsafe.Pointer
132132 }
133133
134-// Pointer returns a pointer to the first param, suitable for passing as
135-// the params argument to pw_stream_connect.
134+// Pointer returns a pointer to the params array, suitable for passing as
135+// the params argument to pw_stream_connect (which expects spa_pod **).
136136 func (cp *connectParams) Pointer() unsafe.Pointer {
137137 if len(cp.params) == 0 {
138138 return nil
139139 }
140- return cp.params[0]
140+ return unsafe.Pointer(&cp.params[0])
141141 }
142142
143143 // Count returns the number of params in the params slice.
@@ -131,13 +131,13 @@ type connectParams struct {
131 params []unsafe.Pointer131 params []unsafe.Pointer
132 }132 }
133 133
134-// Pointer returns a pointer to the first param, suitable for passing as134+// Pointer returns a pointer to the params array, suitable for passing as
135-// the params argument to pw_stream_connect.135+// the params argument to pw_stream_connect (which expects spa_pod **).
136 func (cp *connectParams) Pointer() unsafe.Pointer {136 func (cp *connectParams) Pointer() unsafe.Pointer {
137 if len(cp.params) == 0 {137 if len(cp.params) == 0 {
138 return nil138 return nil
139 }139 }
140- return cp.params[0]140+ return unsafe.Pointer(&cp.params[0])
141 }141 }
142 142
143 // Count returns the number of params in the params slice.143 // Count returns the number of params in the params slice.
M internal/capi/stream_params_test.go +12 -4
@@ -174,10 +174,18 @@ func TestConnectParamsHelpers(t *testing.T) {
174174 t.Error("Pointer() returned nil")
175175 }
176176
177- // The pointer should point to the start of the storage buffer.
178- expected := unsafe.Pointer(&cp.storage[0])
179- if ptr != expected {
180- t.Errorf("Pointer() = %v, want %v", ptr, expected)
177+ // Pointer() must return the address of the params slice entry (spa_pod **),
178+ // NOT the raw spa_pod * that the entry points to.
179+ expectedParamsAddr := unsafe.Pointer(&cp.params[0])
180+ if ptr != expectedParamsAddr {
181+ t.Errorf("Pointer() = %v, want &params[0] = %v", ptr, expectedParamsAddr)
182+ }
183+
184+ // Pointer() must NOT equal the storage start (that would be spa_pod *,
185+ // which is the wrong indirection level for pw_stream_connect).
186+ storageAddr := unsafe.Pointer(&cp.storage[0])
187+ if ptr == storageAddr {
188+ t.Errorf("Pointer() must not equal &storage[0] (%v); it should be one indirection level above", storageAddr)
181189 }
182190 }
183191
@@ -174,10 +174,18 @@ func TestConnectParamsHelpers(t *testing.T) {
174 t.Error("Pointer() returned nil")174 t.Error("Pointer() returned nil")
175 }175 }
176 176
177- // The pointer should point to the start of the storage buffer.177+ // Pointer() must return the address of the params slice entry (spa_pod **),
178- expected := unsafe.Pointer(&cp.storage[0])178+ // NOT the raw spa_pod * that the entry points to.
179- if ptr != expected {179+ expectedParamsAddr := unsafe.Pointer(&cp.params[0])
180- t.Errorf("Pointer() = %v, want %v", ptr, expected)180+ if ptr != expectedParamsAddr {
181+ t.Errorf("Pointer() = %v, want &params[0] = %v", ptr, expectedParamsAddr)
182+ }
183+
184+ // Pointer() must NOT equal the storage start (that would be spa_pod *,
185+ // which is the wrong indirection level for pw_stream_connect).
186+ storageAddr := unsafe.Pointer(&cp.storage[0])
187+ if ptr == storageAddr {
188+ t.Errorf("Pointer() must not equal &storage[0] (%v); it should be one indirection level above", storageAddr)
181 }189 }
182 }190 }
183 191

Keyboard shortcuts

Single-key shortcuts are on. ctrl k and esc work whatever this says.

ctrl k :
go to a section, branch, tag, file or repository
?
this list
j k
move the row cursor down / up
enter
open the row under the cursor; on Files, a directory opens or closes in place
↑ ↓ ← → home end
in the file tree (focus on a row): previous / next row, close / open a directory or go to its parent / first entry, first / last row. They never open a file
l h
on Files: open a directory or a file / close a directory or go up to its parent, then to the parent page. Elsewhere: into the side panel (on a merge request, its files) / back to the content; there j k move between its controls
g g G
first / last row
/
filter the list; on Files, find a file anywhere in the repository (esc clears, enter opens the best match)
b
switch branch or tag
g s g f g c g b g m g i g r g a
tabs: summary, files, commits, branches & tags, merge requests, issues, releases, actions (when available)
g h
home
w
wide mode: use the whole width of the screen, or not (remembered)
y
copy a permalink pinned to the commit
d u x
diff: split / unified / collapse or expand all
e E
diff: the whole file in view / every file, with the lines the hunks hide
n
merge request: next note in the diff
esc
close a dialog, leave a field

Branches 1

Tags 8

↑↓ moveenter openesc close