一、前言
为什么要学习这个buffer,因为是最近在有涉及到一些媒体的业务。
- 1.Android窗口系统通过C-S架构和一套Buffer循环机制实现,在保证安全稳定的前提下基本上做到了极致性能(无大块内存拷贝,IPC通信内容最少)。
- 2.SurfaceFlinger创建Layer,将其中的BufferQueueProducer作为IGraphicBufferProducer传给应用侧的Surface,因而构成窗口。
- 3.Surface是皮,BufferQueue是肉,通过这样的皮肉关系构建了Buffer循环机制。Buffer循环机制不仅用于窗口系统,也用于视频播放解码流,相机拍照数据流等(Camera2.0架构)。
二、循环buffer的实现
- 1、先进先出
- 2、当空闲缓冲区用完,且又有新的数据需要存储时,覆盖历史数据,保存新的数据
- 3、环形缓冲区在实现时采用的是线型的存储结构
- 4、线型存储中需要四个指针,分别为缓冲区首地址指针(pHead)、尾地址指针(pTail)、有效数据起始指针(pValid)、有效数据尾指针(pValidTail)。其中pValid<pValidTail或者pValid>=pValidTtail,如下图所示:
三、媒体的Buffer循环机制
对于按一定帧率刷新的窗口系统,每一次渲染只有很有限的时间,频繁地申请/释放图形内存是不可接受的。Android的做法是维护一个Buffer队列,按生产者——消费者模式循环利用。
这个Buffer就是上一章所述的GraphicBuffer。
1-Buffer的状态
Buffer队列池中持有固定数量的Buffer(由setBufferCount函数决定,一般是3块),每个Buffer有四种状态,决定其是否可以被生产者/消费者访问。
在WINCE开发中很多时候需要用到循环队列来缓存数据,比如在串口通信中,可以将接收到的数据流先缓存到循环队列中,然后再从循环队列中取出数据做下一步的处理。这样可以有效的避免解析数据帧时繁琐的拼接处理。
四、小结
核心点
- 消费者生产者模式
- 环形缓冲区在实现时采用的是线型的存储结构