Linux PipeWire深度解析之pw_stream_return_buffer调用流程与实战(五十一)
简介CSDN博客专家、《Android系统多媒体进阶实战》作者博主新书推荐《Android系统多媒体进阶实战》Android Audio工程师专栏地址Audio工程师进阶系列【原创干货持续更新中……】Android多媒体专栏地址多媒体系统工程师系列【原创干货持续更新中……】专题一 二AAOS车载系统AOSP14系统攻城狮入门视频实战课专题三Android14 Binder之HIDL与AIDL通信实战课专题四Android15快速自定义与集成音效实战课专题五Android15音频策略实战课专题六Android15音频性能实战课(无声/杂音/断音/爆音实战案例)人生格言人生从来没有捷径只有行动才是治疗恐惧和懒惰的唯一良药.更多原创,欢迎关注Android系统攻城狮文章目录1.前言要点概括2.应用场景与用法函数原型参数说明返回值应用场景3.调用流程剖析3.1核心步骤3.2调用流程图3.3生命周期图4.实战应用案例5.一句话总结1.前言本篇目的Linux PipeWire深度解析之pw_stream_return_buffer调用流程与实战。要点概括核心功能把已经dequeue但不准备作为有效媒体数据提交的pw_buffer退回给PipeWireStream。工作机制应用从Stream中取出Buffer后如果发现当前Buffer不适合继续处理或者本周期决定放弃提交就调用pw_stream_return_buffer把Buffer还回Stream内部队列。典型用途Buffer检查失败、数据源不足、业务决定丢弃本周期输出、采集数据不再处理、异常路径下避免Buffer泄漏。pw_stream_return_buffer的本质不是“提交媒体数据”而是“退回Buffer使用权”。它解决的问题是应用已经通过pw_stream_dequeue_buffer拿到了Buffer但后续判断发现不应该把它作为正常数据送入PipeWire图调度此时需要把Buffer还回去。它和pw_stream_queue_buffer的区别非常关键。queue_buffer表示Buffer已经完成正常处理可以进入后续媒体链路return_buffer表示放弃本次使用只是把Buffer归还给Stream不表达有效媒体数据提交语义。它也不是内存释放函数。Buffer内存仍然由PipeWireStream管理应用不能手动释放pw_buffer也不能在return之后继续访问该Buffer。return之后Buffer所有权重新回到PipeWire后续可能被再次dequeue复用。2.应用场景与用法pw_stream_return_buffer是PipeWireStream API中用于退回已取出Buffer的接口。它位于PipeWireStream数据路径的异常分支或放弃分支中。正常媒体数据处理路径通常是dequeue、处理、queue而return_buffer处理的是dequeue之后不想提交有效数据的场景。pw_stream_return_buffer用于把已经dequeue但不准备提交的Buffer退回给PipeWireStream。函数原型intpw_stream_return_buffer(structpw_stream*stream,structpw_buffer*buffer);参数说明structpw_stream*stream;stream表示当前Buffer所属的PipeWireStream对象。该Stream必须是有效Stream并且必须和buffer来源一致。不能从一个Stream中dequeue出Buffer再通过另一个Stream调用return_buffer。structpw_buffer*buffer;buffer表示需要退回的pw_buffer对象。该Buffer通常来自同一个Stream的pw_stream_dequeue_buffer。调用return_buffer之后应用不应继续读取、写入或修改该Buffer中的spa_buffer、spa_data、spa_chunk等字段。返回值成功时通常返回0。失败时返回负值错误码。工程代码中应按“小于0为失败”的方式处理。return_buffer失败通常说明调用关系不正确例如Stream无效、Buffer无效、Buffer不属于当前Stream或者Buffer当前状态不允许被退回。应用场景第一类场景是Buffer检查失败。应用dequeue到Buffer后发现data-data为空、data-chunk为空、maxsize不足、格式状态不符合预期此时不应把该Buffer当作有效数据queue出去可以直接return_buffer退回。第二类场景是播放流数据不足。例如播放器、网络音频、解码器或环形缓冲区当前没有足够PCM数据。如果业务策略不是补静音而是放弃本周期提交就可以return_buffer退回Buffer。第三类场景是采集数据丢弃。采集流中如果当前输入数据不再需要处理例如录音暂停、上层丢弃、算法模块临时不可用可以在读取前或读取后退回Buffer避免应用侧长期占用Buffer。第四类场景是异常路径清理。实时音视频处理代码中dequeue之后可能出现业务判断失败、格式变化、状态切换、对象销毁前保护等情况。return_buffer可以保证Buffer及时回到Stream避免Buffer池被应用侧耗尽。3.调用流程剖析3.1核心步骤1.应用创建pw_stream对象并注册process事件回调。2.应用调用pw_stream_connect连接Stream完成格式协商和Buffer协商。3.PipeWire通过add_buffer事件把Buffer加入Stream内部管理。4.PipeWire图调度触发process回调。5.应用调用pw_stream_dequeue_buffer取出一个pw_buffer。6.应用检查Buffer状态、业务状态、数据源状态或格式状态。7.如果Buffer可以正常处理则进入常规数据路径处理完成后调用pw_stream_queue_buffer。8.如果Buffer不适合提交有效数据则进入退回路径。9.应用调用pw_stream_return_buffer把Buffer退回Stream。10.Buffer重新回到Stream内部可用队列等待后续调度周期再次使用。3.2调用流程图3.3生命周期图4.实战应用案例下面以“播放流中数据不足时退回Buffer”为例说明pw_stream_return_buffer的典型用法。播放流正常情况下应该取出Buffer、填充PCM、设置chunk、queue提交。但如果当前业务侧没有可用PCM数据并且不希望填充静音就可以把Buffer退回给Stream。structapp_data{structpw_stream*stream;uint32_tframe_size;};staticuint32_tread_pcm_from_ringbuffer(void*dst,uint32_tmax_bytes){/* * 实际项目中这里通常从解码器、网络流、 * 环形缓冲区或算法输出队列中读取PCM数据。 */return0;}staticvoidon_process(void*userdata){structapp_data*appuserdata;structpw_buffer*b;structspa_buffer*buf;structspa_data*data;uint32_tn_bytes;intret;bpw_stream_dequeue_buffer(app-stream);if(bNULL)return;bufb-buffer;databuf-datas[0];if(data-dataNULL||data-chunkNULL){retpw_stream_return_buffer(app-stream,b);(void)ret;return;}n_bytesread_pcm_from_ringbuffer(data-data,data-maxsize);if(n_bytes0){retpw_stream_return_buffer(app-stream,b);(void)ret;return;}data-chunk-offset0;data-chunk-sizen_bytes;data-chunk-strideapp-frame_size;pw_stream_queue_buffer(app-stream,b);}这个案例中return_buffer只出现在放弃路径。当Buffer不可写或者没有有效PCM数据时应用不把Buffer提交给正常播放链路而是退回Stream。这样可以避免把无效数据、脏数据或未初始化数据送入PipeWire图。采集流中也可以使用return_buffer。例如应用取到采集Buffer后发现当前录音已经暂停或者上层算法暂时不需要数据就可以退回Buffer。structcapture_data{structpw_stream*stream;bool capture_enabled;};staticvoidon_capture_process(void*userdata){structcapture_data*appuserdata;structpw_buffer*b;structspa_buffer*buf;structspa_data*data;constuint8_t*src;uint32_tsize;bpw_stream_dequeue_buffer(app-stream);if(bNULL)return;if(!app-capture_enabled){pw_stream_return_buffer(app-stream,b);return;}bufb-buffer;databuf-datas[0];if(data-dataNULL||data-chunkNULL){pw_stream_return_buffer(app-stream,b);return;}srcSPA_PTROFF(data-data,data-chunk-offset,uint8_t);sizedata-chunk-size;/* * 正常采集处理 * 可以送入录音文件、编码器、语音前处理、 * 回声消除模块或网络发送模块。 */(void)src;(void)size;pw_stream_queue_buffer(app-stream,b);}工程开发中使用pw_stream_return_buffer要注意四点。第一return_buffer只能用于已经dequeue出来的Buffer。没有dequeue就return或者重复return同一个Buffer都会破坏Stream内部Buffer状态。第二return_buffer不是正常提交路径。如果Buffer已经填充了有效音频或视频数据并且希望PipeWire继续处理应使用pw_stream_queue_buffer而不是return_buffer。第三return之后不要继续访问Buffer。return之后Buffer所有权已经回到PipeWire应用继续读写会造成数据竞争、状态错乱或难以复现的实时问题。第四异常路径也必须归还Buffer。只要dequeue成功无论后续成功、失败、丢弃还是暂停都必须通过queue_buffer或return_buffer结束本次Buffer持有周期。5.一句话总结pw_stream_return_buffer是PipeWireStream数据路径中的Buffer退回接口当应用已经dequeue到Buffer但不准备提交有效媒体数据时用它把Buffer使用权还给Stream避免Buffer长期占用并保持图调度链路稳定。

相关新闻

如何用3个步骤让小爱音箱播放你的本地音乐库?

如何用3个步骤让小爱音箱播放你的本地音乐库?

如何用3个步骤让小爱音箱播放你的本地音乐库? 【免费下载链接】xiaomusic 使用小爱音箱播放音乐,音乐使用 yt-dlp 下载。 项目地址: https://gitcode.com/GitHub_Trending/xia/xiaomusic 你是否厌倦了在线音乐平台的版权限制和广告干扰&#xff1…

2026/10/20 1:22:30 阅读更多 →
从0到1带你使用最新版Codex,我整理的全新保姆即教程来了

从0到1带你使用最新版Codex,我整理的全新保姆即教程来了

最近 Codex 的存在感,确实越来越强了。 但我发现一件很有意思的事:很多人已经装好了 Codex,却还是把它当成另一个 ChatGPT。 而最近openai开始不再更新Codex App,二十选择把codex app揉进Chat GPT 客户端里面。 很多人使用codex的…

2026/10/20 1:22:29 阅读更多 →
Linux进程创建:fork()与写时拷贝揭秘

Linux进程创建:fork()与写时拷贝揭秘

进程控制进程创建Linux创建进程通过fork()函数调用!在之前的学习已经提到了这个知识点!父进程在主函数中调用fork函数,此时os就在创建了一个子进程,此时父子进程就开始并发调度,分流运行! fork函数返回: 子…

2026/10/17 5:12:16 阅读更多 →

最新新闻

一站式云原生DevOps平台:打通研发交付全链路

一站式云原生DevOps平台:打通研发交付全链路

简介:软件研发管理平台一站式云原生DevOps解决方案是一份面向企业研发团队、产品经理及DevOps转型人员的系统化演示文稿,重点阐释如何借助敏捷迭代、小步快跑的方式完成产品规划、项目管理、质量跟踪与持续交付,适合用于方案汇报、团队内训和…

2026/10/20 1:21:57 阅读更多 →
Anki 间隔重复完全指南:让每张卡片的复习时间自动排好

Anki 间隔重复完全指南:让每张卡片的复习时间自动排好

Anki 间隔重复完全指南:让每张卡片的复习时间自动排好 【免费下载链接】anki Anki is a smart spaced repetition flashcard program 项目地址: https://gitcode.com/GitHub_Trending/an/anki 每晚背完单词,第二天就忘掉大半,问题不在…

2026/10/20 1:21:57 阅读更多 →
基于ROS的轮式机器人建模与路径规划仿真实践指南

基于ROS的轮式机器人建模与路径规划仿真实践指南

简介:基于ROS的轮式机器人建模与路径规划仿真是哈尔滨师范大学自然科学学报2020年刊发的一篇学术论文(PDF格式),聚焦移动机器人路径规划、自主导航与避障技术。文章以ROS作为机器人开发平台,通过Rviz建立双轮差速机器人…

2026/10/20 1:21:57 阅读更多 →
OpenRocket 实战指南:一枚火箭从建模到弹道落地的完整仿真流程

OpenRocket 实战指南:一枚火箭从建模到弹道落地的完整仿真流程

OpenRocket 实战指南:一枚火箭从建模到弹道落地的完整仿真流程 【免费下载链接】openrocket Model-rocketry aerodynamics and trajectory simulation software 项目地址: https://gitcode.com/GitHub_Trending/op/openrocket OpenRocket 是一款开源火箭仿真…

2026/10/20 1:21:57 阅读更多 →
用调茶构建成长记录系统:具身化行为驱动的神经可塑实践

用调茶构建成长记录系统:具身化行为驱动的神经可塑实践

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/20 1:21:57 阅读更多 →
把 REA 逆向分析的 token 消耗压下来:给 Agent 的搜索与追踪上三道闸门

把 REA 逆向分析的 token 消耗压下来:给 Agent 的搜索与追踪上三道闸门

把 REA 逆向分析的 token 消耗压下来:给 Agent 的搜索与追踪上三道闸门 【免费下载链接】rea Reverse engineer anything with agents, from app behavior down to native binaries. 项目地址: https://gitcode.com/GitHub_Trending/rea2/rea 让 REA 这类 Ag…

2026/10/20 1:20:54 阅读更多 →

日新闻

CLRC663芯片Pin-to-Pin替代实战:从评估到量产全记录

CLRC663芯片Pin-to-Pin替代实战:从评估到量产全记录

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/20 1:01:30 阅读更多 →
ESP32舵机控制指南:原理、多路驱动与避坑实战

ESP32舵机控制指南:原理、多路驱动与避坑实战

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/20 1:01:30 阅读更多 →
位移法实现一阶低通滤波:单片机ADC采样降噪实战

位移法实现一阶低通滤波:单片机ADC采样降噪实战

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/20 1:01:30 阅读更多 →

周新闻

基于GMM的语音识别系统原理与MATLAB实现详解

基于GMM的语音识别系统原理与MATLAB实现详解

说到基于高斯混合模型(GMM)的语音识别系统,很多人第一反应就是一堆数学公式,觉得门槛很高。但如果你真的在MATLAB里把它落地跑通,会发现核心其实就是三件事:把声音变成特征向量,用GMM给每个类别…

2026/10/19 10:02:04 阅读更多 →
数字图像处理入门:反白、灰度化、调色板修改与导出txt实践

数字图像处理入门:反白、灰度化、调色板修改与导出txt实践

数字图像处理这四个字听起来挺唬人,但落到具体操作上,无非就是让计算机按你的想法“摆弄”像素。我在一个模拟项目X里用了一套特别经典的基础处理流程:对图像做反白、改调色板、彩色转灰度,最后把像素数据导出成txt文件。单看每一…

2026/10/19 17:32:41 阅读更多 →
机器人大脑技术盘点:具身智能的感知、决策与数据闭环

机器人大脑技术盘点:具身智能的感知、决策与数据闭环

如果你的信息流最近也天天刷到“机器人大脑”这个词,你会发现一个很有意思的现象:每个人说的“大脑”根本不是同一个东西。有人指的是大语言模型,有人指的是运动控制系统,还有人指的是能理解物理世界的端到端模型。在2026年这个时…

2026/10/19 1:30:52 阅读更多 →

月新闻

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/19 2:54:50 阅读更多 →
Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/19 9:10:22 阅读更多 →
黑夜航拍船只数据集训练YOLOV5模型全流程解析

黑夜航拍船只数据集训练YOLOV5模型全流程解析

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/18 12:16:16 阅读更多 →