Reading Audio with Advanced Audio File Services (ExtAudioFileRead)

I'm working on understanding Core Audio, more specifically: Advanced Audio File Services

Here I want to use ExtAudioFileRead() to read some audio data from a file.
This works great while I use one huge buffer to store my audio data (i.e. one AudioBuffer ). As soon as I use more than one AudioBuffer , ExtAudioFileRead() returns an error code of -50 ("error in parameter list"). As far as I can tell, this means that one of the ExtAudioFileRead() arguments is incorrect. Probably audioBufferList .

I cannot use one huge buffer, because then dataByteSize would fill its UInt32 integer range with huge files.

Here is the code to create an audioBufferList :

 AudioBufferList *audioBufferList; audioBufferList = malloc(sizeof(AudioBufferList) + (numBuffers-1)*sizeof(AudioBuffer)); audioBufferList->mNumberBuffers = numBuffers; for (int bufferIdx = 0; bufferIdx<numBuffers; bufferIdx++ ) { audioBufferList->mBuffers[bufferIdx].mNumberChannels = numChannels; audioBufferList->mBuffers[bufferIdx].mDataByteSize = dataByteSize; audioBufferList->mBuffers[bufferIdx].mData = malloc(dataByteSize); } 

And here is a working but overflowing code:

 UInt32 dataByteSize = fileLengthInFrames * bytesPerFrame; // this will overflow AudioBufferList *audioBufferList = malloc(sizeof(audioBufferList)); audioBufferList->mNumberBuffers = 1; audioBufferList->mBuffers[0].mNumberChannels = numChannels; audioBufferList->mBuffers[0].mDataByteSize = dataByteSize; audioBufferList->mBuffers[0].mData = malloc(dataByteSize); 

And finally, calling ExtAudioFileRead() (should work with both versions):

 UInt32 numFrames = fileLengthInFrames; error = ExtAudioFileRead(extAudioFileRef, &numFrames, audioBufferList); 

Do you know what I'm doing wrong here?

+4
source share
4 answers

I think you misunderstand the purpose of the mNumberBuffers field. This is usually 1 for mono and interlaced stereo data. The only reason you should set it to something else is the data with multiple tracks, where each channel is in a separate data buffer.

If you want to read part of a file, you must set dataByteSize from the buffer to a reasonable size, and when you read the file, tell the API only to give you many bytes and iterate over it.

+5
source

I also had the same problem with mNumberBuffers> 1, ... My work involved creating my own internal buffer:

sort of:

char buffer1 [byteSize]; char buffer2 [byteSize]; ......

you can also use pointers to make things easier, for example:

buffer [index] [byteSize];

then you will have to scroll them manually and fill them in the main stream to avoid glitches in the sound.

ExtAudioFileRead will only fill the buffer [0] in the AudioBufferList, then you can specify that this points to different manually buffered buffers when playing audio.

hope this helps.

+1
source

mNumberBuffers == 2 when you are dealing with unmoved stereo. This is the number of audio channels when they are not interleaved.

0
source

Cocoa just doesn't seem to accept mNumberBuffers> 1. What a shame, as it makes the whole structure useless. (Hope this is correct ...)

-3
source

Source: https://habr.com/ru/post/1304197/


All Articles