gpt4 book ai didi

c - 连续录制音频的内存问题

转载 作者:太空狗 更新时间:2023-10-29 16:48:58 25 4
gpt4 key购买 nike

在这里,我正在尝试为连续录制的音频系统编写一些代码。然后,当某个振幅阈值被打破时,我会尝试在一定时间内录制音频。

#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <string.h>
#include <time.h>
#include <portaudio.h>
#include <sndfile.h>

#define FRAMES_PER_BUFFER (1024)
#define SAMPLE_SIZE (4)

typedef struct
{
uint16_t formatType;
uint16_t numberOfChannels;
uint32_t sampleRate;
float* recordedSamples;
} AudioData;

AudioData initAudioData(uint32_t sampleRate, uint16_t channels, int type)
{
AudioData data;
data.formatType = type;
data.numberOfChannels = channels;
data.sampleRate = sampleRate;
return data;
}

float avg(float *data)
{
int elems = sizeof(data) / sizeof(data[0]);
float sum = 0;
for (int i = 0; i < elems; i++)
{
sum += fabs(*(data + i));
}
return (float) sum / elems;
}

int main(void)
{
AudioData data = initAudioData(44100, 2, paFloat32);
PaStream *stream = NULL;
PaError err = paNoError;
int size = FRAMES_PER_BUFFER * data.numberOfChannels * SAMPLE_SIZE;
float *sampleBlock = malloc(size);
float *recordedSamples = NULL;
time_t talking = 0;
time_t silence = 0;

if((err = Pa_Initialize())) goto done;
PaStreamParameters inputParameters =
{
.device = Pa_GetDefaultInputDevice(),
.channelCount = data.numberOfChannels,
.sampleFormat = data.formatType,
.suggestedLatency = Pa_GetDeviceInfo(Pa_GetDefaultInputDevice())->defaultHighInputLatency,
.hostApiSpecificStreamInfo = NULL
};
if((err = Pa_OpenStream(&stream, &inputParameters, NULL, data.sampleRate, FRAMES_PER_BUFFER, paClipOff, NULL, NULL))) goto done;
if((err = Pa_StartStream(stream))) goto done;
for(int i = 0;;)
{
err = Pa_ReadStream(stream, sampleBlock, FRAMES_PER_BUFFER);
if(avg(sampleBlock) > 0.000550) // talking
{
printf("You're talking! %d\n", i);
i++;
time(&talking);
recordedSamples = realloc(recordedSamples, size * i);
if (recordedSamples) memcpy(recordedSamples + ((i - 1) * size), sampleBlock, size); // problem here writing to memory at i = 16?
else free(recordedSamples);
}
else //silence
{
double test = difftime(time(&silence), talking);
printf("Time diff: %g\n", test);
if (test >= 1.5)
{
// TODO: finish code processing audio snippet
talking = 0;
free(recordedSamples); // problem freeing memory?
}
}
}

done:
free(sampleBlock);
Pa_Terminate();
return err;
}

但是,代码有些挑剔。有时当我在 Xcode 中运行我的程序时,我会得到以下输出:

Time diff: 1.4218e+09
You're talking! 0
You're talking! 1
You're talking! 2
You're talking! 3
You're talking! 4
You're talking! 5
You're talking! 6
You're talking! 7
You're talking! 8
You're talking! 9
You're talking! 10
You're talking! 11
You're talking! 12
You're talking! 13
You're talking! 14
You're talking! 15
(lldb)

Xcode 指向这一行就是问题所在:

if (recordedSamples) memcpy(recordedSamples + ((i - 1) * size), sampleBlock, size); // problem here writing to memory at i = 16?

其他时候我运行代码,我得到这个错误:

Time diff: 1.4218e+09
You're talking! 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 0
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 1
Time diff: 2
Time diff: 1.4218e+09
CTestEnvironment(55085,0x7fff7938e300) malloc: *** error for object 0x10081ea00: pointer being freed was not allocated
*** set a breakpoint in malloc_error_break to debug

这两个错误都让我有些困惑……有什么建议吗?

最佳答案

您正在超出分配缓冲区的范围:

recordedSamples = realloc(recordedSamples, size * i);
memcpy(recordedSamples + ((i - 1) * size), sampleBlock, size);

realloc() 分配一定数量的字节,这里是size * i。生成的指针存储在 recordedSamples 中,其类型为 float*

memcpy() 然后尝试将数据写入recordedSamples + ((i - 1) * size。指针算法用于确定应写入的位置到。因为 recordedSamplesfloat* 类型,recordedSample + X 指向 X 浮点值(不是 X 字节)的偏移量。

也就是说,recordedSamples + ((i - 1) * size指向内存位置((i - 1) * size * sizeof(float)字节在 recordedSamples 之后。这通常不在分配的缓冲区内,因为 float 大于单个字节。

要解决这个问题,最大的问题是 size 应该是字节数还是 float 。这取决于您使用的 API 函数,我没有详细研究过。

如果它是一些floats,那么你必须调整对基本内存管理函数的调用,比如mallocreallocmemcpy,因为都是按字节操作的。要代替 malloc(size),您可以调用 malloc(size * sizeof(float))

如果 size 确实是字节数,那么将 recordedSamples 设为 char* 或至少强制转换会更符合逻辑它在使用字节偏移量进行指针运算之前,例如 memcpy((char*)recordedSamples + ...)

关于c - 连续录制音频的内存问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28058234/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com