У меня есть приложение, которое предоставляет исключение, когда приложение выходит. Callstack показывает, что исключение происходит из CComPtr :: release при вызове CoUnintialize.
> ieframe.dll!ATL::CComPtr<IWebBrowser2>::Release() + 0x5b bytes
ieframe.dll!CConnectionPoint::UnadviseAll() + 0x131d0 bytes
ieframe.dll!CConnectionPoint::~CConnectionPoint() + 0x18 bytes
ieframe.dll!CShellOcx::~CShellOcx() + 0xf7 bytes
ieframe.dll!CWebBrowserOC::'scalar deleting destructor'() + 0x14 bytes
ieframe.dll!CAggregatedUnknown::CUnkInner::Release() + 0x474a1 bytes
ole32.dll!CStdIdentity::ReleaseCtrlUnk() Line 1149 C++
ole32.dll!CStdMarshal::Disconnect(unsigned long dwType) Line 3454 C++
ole32.dll!CStdMarshal::DisconnectAndRelease(unsigned long dwType) Line 3161 + 0x11 bytes C++
ole32.dll!COIDTable::ThreadCleanup() + 0x31bed bytes C++
ole32.dll!FinishShutdown() Line 1035 C++
ole32.dll!ApartmentUninitialize(int fHostThread) Line 1291 C++
ole32.dll!wCoUninitialize(COleTls & Tls, int fHostThread) Line 2709 + 0x7 bytes C++
ole32.dll!CoUninitialize() Line 2632 C++
imm32.dll!000007feff3832f2()
[Frames below may be incorrect and/or missing, no symbols loaded for imm32.dll]
msctf.dll!000007fefeea7d59()
ntdll.dll!RtlProcessFlsData() + 0x84 bytes
ntdll.dll!LdrShutdownThread() + 0x4b bytes
ntdll.dll!RtlExitUserThread() + 0x38 bytes
IEShims.dll!NS_CreateThread::DesktopIE_ThreadProc() + 0xd6 bytes
kernel32.dll!BaseThreadInitThunk() + 0xd bytes
ntdll.dll!RtlUserThreadStart() + 0x21 bytes
Исключение - нарушение прав доступа
Вы, ребята, столкнулись с такой ситуацией? Что я могу применить, чтобы понять причину этого? до сих пор я сделал следующее
У меня есть эта проблема и после красных
http://mfctips.com/2012/10/29/cfiledialogdomodal-causes-access-violation/
Я подозреваю, что проблема заключалась в том, чтобы поставить QFileDialog в качестве локальной переменной моих методов Qmainwindow. Затем я решил, что мой Qfiledialog будет частным членом QMainwindow, например:
//в MainWindow.h
class MainWindow : public QMainWindow
{
Q_OBJECT
......
private:
......
QFileDialog *ptDialog;
.....
}
Поэтому я дал новый QfileDialog для ptDialog в конструкторе MainWindow и вызвал ptDialog-> exec() согласно моим потребностям в методах MainWindow, а именно:
//в MainWindow.cpp
//конструктор
MainWindow::MainWindow(QWidget *parent):
QMainWindow(parent),
ui(new Ui::MainWindow)
{
.....
ptDialog=new QFileDialog(this, tr("Abrir Imagem"),QCoreApplication::applicationDirPath(), "Imagens (*.png *.jpg *.jpeg *.bmp)");
......
}
//любой метод, который я хочу использовать QFileDialog
void MainWindow::LoadFile()
{
if(ptDialog->exec())
{
SetFile(ptDialog->selectedFiles().first());
}
}
Я думаю, таким образом, Qmainwindow будет выпущен только в конце приложения, избегая проблемы.
Это, скорее всего, происходит из-за неправильного порядка выпуска объектов. Рассмотрим следующий пример: COM-объект A предназначен для собственного COM-объекта B, поэтому ожидаемая последовательность заключается в том, что объект A явно называется Release()
и в нем destructor он вызовет Release()
для объекта B. Теперь, когда CoUnintialize()
называется COM, принудительно освобождает все COM-объекты в некоторой последовательности. Таким образом, существует вероятность, что объект B сначала называется Release()
а теперь объект A содержит обвисший указатель на то, что он считает объектом B, и поэтому, когда вызывается объект A Release()
он пытается использовать обвисший указатель и запускается неопределенное поведение.
Решение, поэтому эта проблема явно выделяет объекты в правильной последовательности до CoUnintialize()
.
CoUninitialize
все действия COM должны быть прекращены. У тебя этого не происходит.