Search code examples
iosavfoundationavaudiosessionaudiounitremoteio

AudioUnitRender Error -50 meaning


I get an Error -50 in AudioUnitRender call. My Audio Unit is simply a RemoteIO unit getting samples from the mic. What is the meaning of error -50?

  let status = AudioUnitRender(controller.audioUnit!, ioActionFlags, inTimeStamp, inBusNumber, inNumberFrames, listPtr)

if noErr != status {
    print("Error \(status)");
    fatalError("Render status \(status)")
  // return status;
}

Solution

  • -50 (kAudio_ParamError) means one of the parameters you passed is wrong.

    A common error with AudioUnitRender is to pass an AudioBufferList with the wrong number of mNumberBuffers (you may be recording non-interleaved stereo) or the AudioBuffers themselves may be the wrong size or have the wrong number of channels.

    I encounter this problem whenever I forget that the simulator and device remote audio units have different default stream formats and don't explicitly set them via

    AudioUnitSetProperty(audioUnit, kAudioUnitProperty_StreamFormat, kAudioUnitScope_Output, 1, &streamFormatIActuallyWant, UInt32(MemoryLayout<AudioStreamBasicDescription>.size))
    

    I think the simulator defaults to interleaved integer and the device defaults to non interleaved float, although maybe that's just my configuration.

    From the AudioUnitRender header file:

    The caller must provide a valid ioData AudioBufferList that matches the expected topology for the current audio format for the given bus. The buffer list can be of two variants:
    (1) If the mData pointers are non-null then the audio unit will render its output into those buffers. These buffers should be aligned to 16 byte boundaries (which is normally what malloc will return).
    (2) If the mData pointers are null, then the audio unit can provide pointers to its own buffers. In this case the audio unit is required to keep those buffers valid for the duration of the calling thread's I/O cycle

    By passing null mData (point (2)) can save you an unnecessary copy, but you still need to know the format "topology", which is just mNumberBuffers (probably 1 or 2).