重新分配std :: simel_ptr< qaudiobuffer>成员导致堆腐败

发布于 2025-02-13 07:14:15 字数 2645 浏览 0 评论 0原文

我在尝试将智能指针成员构造为std :: simolor_ptr< qaudiobuffer>时遇到了问题。

在按钮中分配了这一点,请单击QT插槽,如下所示:

void
MainWindow::on_start_clicked() {
    // second time this occurs HEAP corruption inside createAudioBuffer function
    mpAudioBuffer = createAudioBuffer(*mpAudioConfig);
    ...
}

Qaudiobuffer智能指针第一次分配时可以正常工作,但是当重新分配时(通过成员fn creat> createAudioBuffer < /code>)由于audioconfig参数的更改,该参数会导致sizeinbytes更改,因此std :: make_unique&lt; qaudiobuffer&gt;(...)在Visual Studio中导致heap_corruption_detected弹出对话框崩溃。

此崩溃在数组eleter中与分配的const auto data = std :: make_unique&lt; char []&gt;(sizeinbytes)此堆分配的智能指针阵列与长度参数一起传递给该堆分配的智能指针阵列 QByTearray应该在哪里进行深入复制,但是崩溃似乎指向某个地方的一些双重删除。

std::unique_ptr<QAudioBuffer>
MainWindow::createAudioBuffer(const AudioConfig& rConfig) const
{
    const auto bytesPerSample =
        (rConfig.sampleFormat == SampleFormat::Uint8) ? 1 :
        (rConfig.sampleFormat == SampleFormat::Int32) ? 4 :
        (rConfig.sampleFormat == SampleFormat::Int16) ? 2 : -1;
    const auto sizeInBytes = bytesPerSample * rConfig.channelCount * rConfig.frameCount;
    // allocate raw data for the QByteArray which is passed into the QAudioBuffer ctor.
    const auto data = std::make_unique<char[]>(sizeInBytes);
    // TODO initialize data here
    return std::make_unique<QAudioBuffer>(QByteArray(
        data.get(), sizeInBytes), [&rConfig]()-> QAudioFormat {
            // use lambda to initialize member - no need for separate
            // QAudioFormat object as embedded into test QAudioBuffer
            QAudioFormat format;
            format.setSampleRate(static_cast<int>(rConfig.sampleRate));
            format.setChannelCount(static_cast<int>(rConfig.channelCount));
            format.setSampleFormat(QAudioFormat::Int32);
            return format;
        }());
}

相应的堆栈跟踪如下:

ucrtbased.dll!free_dbg_nolock(void * const block, const int block_use) Line 952 C++
ucrtbased.dll!_free_dbg(void * block, int block_use) Line 1030  C++
afdx.exe!operator delete(void * block) Line 38  C++
afdx.exe!operator delete[](void * block) Line 32    C++
afdx.exe!std::default_delete<char [0]>::operator()<char,0>(char * _Ptr) Line 3156   C++
afdx.exe!std::unique_ptr<char [0],std::default_delete<char [0]>>::~unique_ptr<char [0],std::default_delete<char [0]>>() Line 3390   C++
afdx.exe!MainWindow::createAudioBuffer(const AudioConfig & rConfig) Line 544    C++

I am having problems trying to construct a smart pointer member to a std::unique_ptr<QAudioBuffer>.

This is assigned in a button click QT slot as follows:

void
MainWindow::on_start_clicked() {
    // second time this occurs HEAP corruption inside createAudioBuffer function
    mpAudioBuffer = createAudioBuffer(*mpAudioConfig);
    ...
}

The construction of the QAudioBuffer smart pointer works fine the first time it is assigned, however when this is reassigned (via a member fn createAudioBuffer) due to a change in the AudioConfig parameter that causes a sizeInBytes change, then the std::make_unique<QAudioBuffer>(...) crashes resulting in a HEAP_CORRUPTION_DETECTED popup dialog in visual studio.

This crash is in the array deleter corresponding to the heap allocated const auto data = std::make_unique<char[]>(sizeInBytes) This heap allocated smart pointer array is passed along with a length parameter to QByteArray where is should be deep copied, however the crash would appear to point to some double delete somewhere.

std::unique_ptr<QAudioBuffer>
MainWindow::createAudioBuffer(const AudioConfig& rConfig) const
{
    const auto bytesPerSample =
        (rConfig.sampleFormat == SampleFormat::Uint8) ? 1 :
        (rConfig.sampleFormat == SampleFormat::Int32) ? 4 :
        (rConfig.sampleFormat == SampleFormat::Int16) ? 2 : -1;
    const auto sizeInBytes = bytesPerSample * rConfig.channelCount * rConfig.frameCount;
    // allocate raw data for the QByteArray which is passed into the QAudioBuffer ctor.
    const auto data = std::make_unique<char[]>(sizeInBytes);
    // TODO initialize data here
    return std::make_unique<QAudioBuffer>(QByteArray(
        data.get(), sizeInBytes), [&rConfig]()-> QAudioFormat {
            // use lambda to initialize member - no need for separate
            // QAudioFormat object as embedded into test QAudioBuffer
            QAudioFormat format;
            format.setSampleRate(static_cast<int>(rConfig.sampleRate));
            format.setChannelCount(static_cast<int>(rConfig.channelCount));
            format.setSampleFormat(QAudioFormat::Int32);
            return format;
        }());
}

The corresponding stack trace is as follows:

ucrtbased.dll!free_dbg_nolock(void * const block, const int block_use) Line 952 C++
ucrtbased.dll!_free_dbg(void * block, int block_use) Line 1030  C++
afdx.exe!operator delete(void * block) Line 38  C++
afdx.exe!operator delete[](void * block) Line 32    C++
afdx.exe!std::default_delete<char [0]>::operator()<char,0>(char * _Ptr) Line 3156   C++
afdx.exe!std::unique_ptr<char [0],std::default_delete<char [0]>>::~unique_ptr<char [0],std::default_delete<char [0]>>() Line 3390   C++
afdx.exe!MainWindow::createAudioBuffer(const AudioConfig & rConfig) Line 544    C++

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文