设置WA_DeleteOnClose的栈QDialog出现double free错误原因问询
问题结论先明确
你关于「错误是在第一次调用~QDialog()时触发」的判断是错误的。你看到的~MyDialog()打印确实是第一次析构执行时输出的,但崩溃实际触发在析构函数执行完成后的内存释放环节。
具体执行流程&报错原因
整个运行过程的执行顺序如下:
- 你在栈空间创建了
MyDialog实例d,栈对象的内存完全由编译器自动管理,离开作用域时会自动触发析构、回收栈空间,不需要也不能手动用delete释放。 - 你给栈对象设置了
WA_DeleteOnClose属性,Qt的QDialog关闭逻辑会检测该标记,在关闭事件处理的末尾主动执行delete this;操作。 - 关闭对话框时,首先触发
MyDialog的析构函数执行,所以控制台输出了~MyDialog()日志,析构函数本身的执行过程没有问题。 - 析构执行完成后,
delete运算符会尝试把栈对象的地址传给堆内存分配器进行释放,栈地址完全不属于堆内存的管理范围,内存分配器会直接识别到这是非法的内存释放操作,立刻抛出double free or corruption错误,程序直接终止,所以你看不到后续After exec的日志输出,也不会走到作用域结束的第二次自动析构步骤。
即使在部分内存检测逻辑较宽松的平台上,第一次delete栈地址没有立刻触发崩溃,等代码走到作用域结束时,编译器会自动再次析构已经被手动释放过的d对象,依然会触发二次析构的double free错误。
内容的提问来源于stack exchange,提问作者LRDPRDX
相关产品推荐
相关产品推荐

