使用 PortAudio 写入 fifo 并使用 ffmpeg 在 OSX 上读取
write with PortAudio into fifo and read with ffmpeg on OSX
我想做什么:
- 在 PortAudio 中打开我的麦克风作为音频源(有效)
- 将流写入 fifo(有效)
- 使用 ffmpeg 读取 fifo(不起作用)
在 PortAudio 中,我使用 Blocking I/O,如下所示:
http://portaudio.com/docs/v19-doxydocs/blocking_read_write.html
在循环中,我这样写入 fifo:
int data = write('/tmp/aaa', sampleBlock, bufferSize);
当我将它读取到 PortAudio 写入缓冲区时,它起作用了。
bytes_read = read('/tmp/aaa', readSampleBlock, bufferSize);
err = Pa_WriteStream(stream, readSampleBlock, bufferSize)
当我在控制台上用 ffmpeg 阅读它时:
ffmpeg -y -i /tmp/aaa -f s16le -acodec copy -f nut -ar 48000 -ac 2 -v debug -report -acodec copy out.wav
它只是阻塞循环而已。
谁能帮我弄清楚我需要做什么?
我的代码:
#define SAMPLE_SIZE (1)
#define FRAMES_PER_BUFFER (480)
#define AUDIOFIFO "/tmp/aaa"
char *sampleBlock = NULL;
int status, captured_bytes, fifo, bytes_read;
err = Pa_OpenStream(&stream,
&inputParameters,
NULL,
48000,
FRAMES_PER_BUFFER,
paClipOff,
NULL, /* no callback, use blocking API */
NULL ); /* no callback, so no callback userData */
if( err != paNoError ) goto error;
numBytes = FRAMES_PER_BUFFER * numChannels * SAMPLE_SIZE ;
sampleBlock = (char *) malloc( numBytes );
memset( sampleBlock, SAMPLE_SILENCE, numBytes );
if (status = mkfifo(AUDIOFIFO, 0666) < 0)
{
printf("Error making AUDIOFIFO: %s \n", strerror(errno));
}
err = Pa_StartStream( stream );
if( err != paNoError )
{
goto error;
}
fifo = open(AUDIOFIFO, O_RDWR, O_NONBLOCK);
if (fifo < 0) printf("Error opening AUDIOFIFO: %s \n", strerror(errno));
for( i=0; i<(60*48000)/FRAMES_PER_BUFFER; ++i )
{
if ((err = Pa_ReadStream(stream, sampleBlock, FRAMES_PER_BUFFER)) != paNoError)
{
goto xrun;
}
captured_bytes = write(fifo, sampleBlock, FRAMES_PER_BUFFER);
if (captured_bytes < 0)
{
printf("Error writing to AUDIOFIFO: %s \n", strerror(errno));
}
framesProcessed += bufferSize;
}
AFAIK,ffmpeg 命令行的一般格式是:
ffmpeg <GLOBAL OPTIONS> <INPUT OPTIONS> -i INPUT <OUTPUT OPTIONS> OUTPUT
即您必须在 ffmpeg 打开它之前 描述您的输入流。
所以我认为 -f s16le
(至少)必须在 ffmpeg 命令行上的 -i /tmp/aaa
之前:
ffmpeg -y -f s16le -i /tmp/aaa ....
我想做什么:
- 在 PortAudio 中打开我的麦克风作为音频源(有效)
- 将流写入 fifo(有效)
- 使用 ffmpeg 读取 fifo(不起作用)
在 PortAudio 中,我使用 Blocking I/O,如下所示: http://portaudio.com/docs/v19-doxydocs/blocking_read_write.html
在循环中,我这样写入 fifo:
int data = write('/tmp/aaa', sampleBlock, bufferSize);
当我将它读取到 PortAudio 写入缓冲区时,它起作用了。
bytes_read = read('/tmp/aaa', readSampleBlock, bufferSize);
err = Pa_WriteStream(stream, readSampleBlock, bufferSize)
当我在控制台上用 ffmpeg 阅读它时:
ffmpeg -y -i /tmp/aaa -f s16le -acodec copy -f nut -ar 48000 -ac 2 -v debug -report -acodec copy out.wav
它只是阻塞循环而已。
谁能帮我弄清楚我需要做什么?
我的代码:
#define SAMPLE_SIZE (1)
#define FRAMES_PER_BUFFER (480)
#define AUDIOFIFO "/tmp/aaa"
char *sampleBlock = NULL;
int status, captured_bytes, fifo, bytes_read;
err = Pa_OpenStream(&stream,
&inputParameters,
NULL,
48000,
FRAMES_PER_BUFFER,
paClipOff,
NULL, /* no callback, use blocking API */
NULL ); /* no callback, so no callback userData */
if( err != paNoError ) goto error;
numBytes = FRAMES_PER_BUFFER * numChannels * SAMPLE_SIZE ;
sampleBlock = (char *) malloc( numBytes );
memset( sampleBlock, SAMPLE_SILENCE, numBytes );
if (status = mkfifo(AUDIOFIFO, 0666) < 0)
{
printf("Error making AUDIOFIFO: %s \n", strerror(errno));
}
err = Pa_StartStream( stream );
if( err != paNoError )
{
goto error;
}
fifo = open(AUDIOFIFO, O_RDWR, O_NONBLOCK);
if (fifo < 0) printf("Error opening AUDIOFIFO: %s \n", strerror(errno));
for( i=0; i<(60*48000)/FRAMES_PER_BUFFER; ++i )
{
if ((err = Pa_ReadStream(stream, sampleBlock, FRAMES_PER_BUFFER)) != paNoError)
{
goto xrun;
}
captured_bytes = write(fifo, sampleBlock, FRAMES_PER_BUFFER);
if (captured_bytes < 0)
{
printf("Error writing to AUDIOFIFO: %s \n", strerror(errno));
}
framesProcessed += bufferSize;
}
AFAIK,ffmpeg 命令行的一般格式是:
ffmpeg <GLOBAL OPTIONS> <INPUT OPTIONS> -i INPUT <OUTPUT OPTIONS> OUTPUT
即您必须在 ffmpeg 打开它之前 描述您的输入流。
所以我认为 -f s16le
(至少)必须在 ffmpeg 命令行上的 -i /tmp/aaa
之前:
ffmpeg -y -f s16le -i /tmp/aaa ....