首页 > 解决方案 > 无法创建 SinkInputInfo 数组

问题描述

我无法创建一个 SinkInputInfo 对象数组。我已将此发布到相应的仓库,但没有收到任何回复。

最小复制:

using PulseAudio;

public void main () {
    SinkInputInfo[] sink_inputs;
}

输出

/tmp/test.vala.PFQW80.c: In function ‘_vala_pa_sink_input_info_array_free’:
/tmp/test.vala.PFQW80.c:18:4: warning: implicit declaration of function ‘pulse_audio_sink_input_info_destroy’ [-Wimplicit-function-declaration]
   18 |    pulse_audio_sink_input_info_destroy (&array[i]);
      |    ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/usr/bin/ld: /tmp/ccZQGm6J.o: in function `_vala_pa_sink_input_info_array_free':
test.vala.PFQW80.c:(.text+0x3f): undefined reference to `pulse_audio_sink_input_info_destroy'
collect2: error: ld returned 1 exit status
error: cc exited with status 256

标签: valapulseaudiomeson-build

解决方案


您不能创建SinkInputInfo. 您也不能在任何地方存储它的实例。

原因是它只在回调中有效:

https://www.freedesktop.org/software/pulseaudio/doxygen/introspect.html#query_sec

信息结构中的数据成员仅在回调期间有效。如果在回调完成后需要它们,则必须执行信息结构的深拷贝。

libpulse 不提供任何方法来复制或释放SinkInputInfo指针类型。

但是,您可以在结构中使用任何内容:

Gee.ArrayList<string> sink_inputs;

public void cb(PulseAudio.Context c, PulseAudio.SinkInputInfo? i, int eol) {
        sink_inputs.add(i.name);
}

public void main () {
    var loop = new PulseAudio.MainLoop();
    var context = new PulseAudio.Context(loop.get_api(), null);
    sink_inputs = new Gee.ArrayList<string>();
    context.get_sink_input_info_list(cb);
}

这里我只存储name属性。您可以通过在 vala 中创建自己的数据类型并复制您感兴趣的任何内容来扩展它。

此外 vapi 文件不完整,有办法告诉 Vala 编译器复制和内存管理不可用。请参阅https://wiki.gnome.org/Projects/Vala/ManualBindings#Structs

我有一段时间没有编写任何 Vala 代码,但我认为 vapi 文件应该将 destroy_function 设置为空字符串。

总结:不要尝试将SinkInputInfo回调的参数存储在任何地方,只需复制您感兴趣的结构的字段即可。


推荐阅读