【问题标题】:Performance between CoreAudio and AVFoundationCoreAudio 和 AVFoundation 之间的性能
【发布时间】:2017-08-11 21:32:37
【问题描述】:

我有一个关于 CoreAudio 和 AVFoundation 的问题。

我使用带有 AUGraph 和 AudioUnit 的 CoreAudio 构建了一个专业音频应用程序。

我想切换到看起来非常棒的 AVFoundation 框架。但由于我担心性能,我想了解更多。

在我的核心音频渲染回调中,我可以以 44100kHz 的采样率处理 512 个样本,因此我的回调每 10 毫秒调用一次,我认为它可以轻松更快(对吗?)。

现在在 AVFoundation 中,渲染回调是 AVAudioNode 的 Tap。而且我在评论中看到 bufferSize 参数是the requested size of the incoming buffers in sample frames. Supported range is [100, 400] ms. 那么这是否意味着我每次调用都不能处理少于 4410 个样本?

限制是否来自 Objective-C 的约束(消息调用、锁定等)?

它不会对实时 DSP 流程产生影响吗?

【问题讨论】:

    标签: avfoundation core-audio


    【解决方案1】:

    在我使用 iOS AVAudioEngine API (iOS 10.3.3) 的实验中,我确实发现在 AVAudioNode 总线上安装分接头不会在我的 iPhone 7 上提供短于 4410 个样本的缓冲区。这可能是因为 AVAudioEngine 分接头提供与 CoreAudio 音频单元回调相比,缓冲到优先级较低的线程,因此无法经常可靠地调用,从而导致更高的延迟。

    但是,可以创建一个 V3 AUAudioUnit 子类,接收的缓冲区(由实例的 internalRenderBlock 用于输出)配置为在 iPhone 7 上从 512 到短至 64 个样本。在音频会话上调用 setPreferredIOBufferDuration 似乎可以设置首选 AUAudioUnit 渲染块缓冲区大小。我发布了一些测试代码(混合了 Swift 3 和 Objective C),用于创建我认为可以工作的低延迟 V3 AUAudioUnit 音频发生器子类here。确实需要了解并遵循渲染块内的实时编码限制(没有方法调用、锁、内存分配等),因此块内的音频上下文代码的纯 C 似乎是最好的(甚至可能是强制性的)。

    对于具有同样短缓冲区的低延迟麦克风输入,您可以尝试将您的音频单元子类连接到 audioEngine 的 inputNode,然后在您的单元渲染块内调用输入的 AURenderPullInputBlock。

    【讨论】:

    • 非常感谢@hotpaw2!我一直很欣赏你在这里的高质量答案。这就是我一直在寻找的,它似乎是一个很好的解决方案。我没有关于继承 AUAudioUnit。顺便说一句,我们无法从 AVAudioPlayer 获取音频单元真是太遗憾了......所以如果我理解得很好,以高速率获取/更改 AVAudioPlayerNode 样本的正确方法是:AVAudioPlayerNode -> MyCustomAU(使用渲染回调)-> 其他AVAudioUnit。确实,目前似乎只能使用 macOS 10.13 及更高版本从中获取 AudioUnit...
    • 我之前评论的来源Apple Documentation
    • 一个 AUAudioUnit 子类似乎适用于在 macOS 10.12 下运行的 iOS 模拟器中运行的代码。猜猜这可能意味着什么……
    • @hotpaw2 我也感谢您提供的所有优质答案,谢谢!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-29
    • 2019-01-31
    • 2010-11-21
    • 2012-05-26
    • 2013-09-02
    • 2014-03-15
    相关资源
    最近更新 更多