【发布时间】:2015-09-16 20:02:00
【问题描述】:
我编写了以下小型示例测试用例,它只是将单个键/值写入QSettings 对象(使用 Qt 5.5):
#include <QSettings>
int main()
{
QSettings settings("/tmp/settings.ini", QSettings::IniFormat);
std::string data = "world";
QByteArray arr(data.c_str(), data.size());
settings.setValue("hello", arr);
return 0;
}
我编译如下:
$ g++ main.cpp -I${QTDIR}/include -I${QTDIR}/include/QtCore -fpic \
-L${QTDIR}/lib -Wl,-R -Wl,"$QTDIR/lib" -lQt5Core -o test
按预期运行它不会产生stdout/stderr 输出
$ ./test
但是,通过查看它创建的 "settings.ini" 文件,我们可以看到它按预期工作:
$ cat /tmp/settings.ini
[General]
hello=@ByteArray(world)
但是,尽管valgrind 运行它会报告内存泄漏:
$ valgrind --quiet --leak-check=full ./test
==2148== 4 bytes in 1 blocks are definitely lost in loss record 1 of 4
==2148== at 0x4C2B0E0: operator new(unsigned long) (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==2148== by 0x4EC4CA1: qrand() (in ${QTDIR}/lib/libQt5Core.so.5.5.0)
==2148== by 0x5012CC3: ??? (in ${QTDIR}/lib/libQt5Core.so.5.5.0)
==2148== by 0x4FE6291: QFile::open(QFlags<QIODevice::OpenModeFlag>) (in ${QTDIR}/lib/libQt5Core.so.5.5.0)
==2148== by 0x5013350: QTemporaryFile::open(QFlags<QIODevice::OpenModeFlag>) (in ${QTDIR}/lib/libQt5Core.so.5.5.0)
==2148== by 0x505CA7D: ??? (in ${QTDIR}/lib/libQt5Core.so.5.5.0)
==2148== by 0x505DE8C: ??? (in ${QTDIR}/lib/libQt5Core.so.5.5.0)
==2148== by 0x4FF5A3B: QLockFile::tryLock(int) (in ${QTDIR}/lib/libQt5Core.so.5.5.0)
==2148== by 0x503DE80: ??? (in ${QTDIR}/lib/libQt5Core.so.5.5.0)
==2148== by 0x503F0C8: QSettings::~QSettings() (in ${QTDIR}/lib/libQt5Core.so.5.5.0)
==2148== by 0x400E72: main (in /home/steve/test)
==2148==
可以看出这是源自QSettings 析构函数。
QSettings::sync():
请注意,调用settings.sync() 对内存泄漏没有影响,它所做的只是将泄漏移动到源自sync() 内部,而不是析构函数。
这是意料之中的,因为documentation 声明sync() 是从析构函数中调用的。
问题:
如何正确清理以防止这种内存泄漏?
【问题讨论】:
-
我在 Qt Creator 3.5.0 中使用 Visual Leak 检测器 2.4RC2。它不会检测到任何内存泄漏。
-
这是否表明 QtCreator 正在抑制 Visual Leak 检测器报告内存泄漏?
-
我不确定,但无论如何我都在 Windows 上,还有 Qt 5.5。也许这是您构建的 qt 错误。
标签: c++ qt memory-leaks