-
VS2010&OLE32.dll access violation problem with COM
My program using COM and some DLLs and this program invokes access violation exception when I close the application. I've grabbing information below
- dli {cb=36 pidd=0x5caf5a1c ppfn=0x5cb175e4 ...} DelayLoadInfo
cb 36 unsigned long
+ pidd 0x5caf5a1c __DELAY_IMPORT_DESCRIPTOR_ole32_dll {grAttrs=1 rvaDLLName=429088 rvaHmod=5561600 ...} const ImgDelayDescr *
+ ppfn 0x5cb175e4 __imp__CoUninitialize@0 int (void)* *
+ szDll 0x5c638c20 "ole32.dll" const char *
+ dlp {fImportByName=1 szProcName=0x5caf627a "CoUninitialize" dwOrdinal=1554997882 } DelayLoadProc
+ hmodCur 0x74df0000 {unused=9460301 } HINSTANCE__ *
pfnCur 0x00000000 int (void)*
dwLastError 0 unsigned long
- dli.dlp {fImportByName=1 szProcName=0x5caf627a "CoUninitialize" dwOrdinal=1554997882 } DelayLoadProc
fImportByName 1 int
- szProcName 0x5caf627a "CoUninitialize" const char *
67 'C' const char
dwOrdinal 1554997882 unsigned long
- dli.dlp.szProcName 0x5caf627a "CoUninitialize" const char *
67 'C' const char
it seems CoUninitialize method involves some bad memory manipulations.
This problem does not occurs on the VS2008.
Why does this occurs ?
-
Re: VS2010&OLE32.dll access violation problem with COM
If you are using COM smart pointers and calling CoUninitialize before the smart pointer goes out of scope, you can see a similar issue.
-
Re: VS2010&OLE32.dll access violation problem with COM
But, I hadn't saw this problem on VS2008.
-
Re: VS2010&OLE32.dll access violation problem with COM
Well, it doesn't matter, had you or had not. What matters is to call CoUnintialize only after all smartpointers left their scopes, or were nullified to the moment otherwise. You make sure this is done and see if the problem has gone.
-
Re: VS2010&OLE32.dll access violation problem with COM
Do you mean the 'smart pointer' as COM's smart pointers ?
How is the boost::shared_ptr ?
-
Re: VS2010&OLE32.dll access violation problem with COM
Okay. The problem mentioned by Arjay relates to having non released COM interfaces while CoInitialize gets called. Now it's up to you to get what kind of smart pointers it's about. ;)
-
Re: VS2010&OLE32.dll access violation problem with COM
Thanks.
I'm using many CComQIPtr(s) and released all of them before CoUninitialize and checked timing of release, therefor I couldn't resolve this issue. Why?
-
Re: VS2010&OLE32.dll access violation problem with COM
So you are sure about interfaces being timely released. Then another suspect (pretty obvious, I'd say) is delayed load. :) Did you try to remove it?
-
Re: VS2010&OLE32.dll access violation problem with COM
I've known the delay load of DLL but have not known the delay load around COM and CComPtr(or CComQIPtr). What is that ?
I haven't using delay loaded DLL(s).
Additionally, I've using Skype4COM.dll by '#import' pragma to communicate with the SkypeAPI and running the initialization process like below on the beginning of a worker thread
CoInitialize(NULL);
// Create object
ISkypePtr pSkype(__uuidof(Skype));
// Create sink
scoped_ptr<CSkypeEvents> pSink( new CSkypeEvents(man) );
HRESULT hr(S_OK);
// Connect events
hr = pSink->DispEventAdvise(pSkype);
if( NULL == pSkype ){
}
// Attach to API
hr = pSkype->Attach(5, VARIANT_TRUE);
if( FAILED(hr) ){
}
But, ntdll.dll issue will occurs if I will not run this procedure.
-
Re: VS2010&OLE32.dll access violation problem with COM
Quote:
Originally Posted by
lightshield
I've known the delay load of DLL but have not known the delay load around COM and CComPtr(or CComQIPtr). What is that ?
I haven't using delay loaded DLL(s).
Additionally, I've using Skype4COM.dll by '#import' pragma to communicate with the SkypeAPI and running the initialization process like below on the beginning of a worker thread
CoInitialize(NULL);
// Create object
ISkypePtr pSkype(__uuidof(Skype));
// Create sink
scoped_ptr<CSkypeEvents> pSink( new CSkypeEvents(man) );
HRESULT hr(S_OK);
// Connect events
hr = pSink->DispEventAdvise(pSkype);
if( NULL == pSkype ){
}
// Attach to API
hr = pSkype->Attach(5, VARIANT_TRUE);
if( FAILED(hr) ){
}
But, ntdll.dll issue will occurs if I will not run this procedure.
In the code above, where does CoUninitialize get called?
-
Re: VS2010&OLE32.dll access violation problem with COM
The above code is just the initializing part. CoUninitialize is used in my program.
-
Re: VS2010&OLE32.dll access violation problem with COM
Quote:
Originally Posted by
lightshield
The above code is just the initializing part. CoUninitialize is used in my program.
Look, you've got a problem that we suspect is due to the scoping of the COM smart pointers getting released after your call to CoUninitialize. Of course, we don't know for sure until we see your code.
So can we just save time here and have you post the complete code from CoInitialize to CoUninitialize?
-
Re: VS2010&OLE32.dll access violation problem with COM
My worker thread routine is as below.
Code:
class Worker{
Worker(){}
void operator()(void)
{
CoInitialize(NULL);
// init skype api dll
while(true){
// skype api procedures using Skype4COM.dll
}
CoUninitialize();
}
};
This is a worker thread and this thread will only uses skype-api's produced by Skype's DLL.
BUT I've unloading Skype-DLL on the main thread. This procedure maybe the cause of this problem. I'll try to remove this procedure to detect an affected part of my sources.
Sorry Igor, I might have using delayed load.
-
Re: VS2010&OLE32.dll access violation problem with COM
Please use [Code][/Code] tags.
What does the following mean?
Code:
// skype api procedures using Skype4COM.dll
Are using COM to access this dll? Or do you call LoadLibrary?
If Skype4Com.dll is a COM dll, then you don't need to call LoadLibrary ANYWHERE (because the COM subsystem handles that for you).
-
Re: VS2010&OLE32.dll access violation problem with COM
skype4COM is a COM library.
I didn't use LoadLibrary so I didn't use delayed load.
I've using '#import' pragma to import Skype's class information like below in the cpp file that implementing Skype client functionalities.
Code:
#import ".\\Skype4COM.dll" named_guids
-
Re: VS2010&OLE32.dll access violation problem with COM
So we're back to my original question of how you are releasing the smart pointer.
[Note to self]Why does it take so long to pry info out of some posters?[/Note to self]
The code that you posted doesn't tell me anything on where you are releasing the com pointers because you don't show that part of the code.
Code:
class Worker{
Worker(){}
void operator()(void)
{
CoInitialize(NULL);
// init skype api dll
while(true){
// skype api procedures using Skype4COM.dll
}
CoUninitialize();
}
};
If you create the COM smart pointer where you have "// init skype api dll", then CoUnitialize is called before the smart pointer goes out of scope.
But rather than me guessing, can you just post the entire code?
-
Re: VS2010&OLE32.dll access violation problem with COM
I've created COM smart pointers only in the main thread explicitly and above worker thread just using the skype's COM interface.
Code:
void operator()(void)
{
error_message.clear();
run = true;
pause = false;
theApp.LoadSkype4COMDLL();
CoInitialize(NULL);
// Create object
ISkypePtr pSkype(__uuidof(Skype));
// Create sink
scoped_ptr<CSkypeEvents> pSink( new CSkypeEvents(man) );
HRESULT hr(S_OK);
// Connect events
hr = pSink->DispEventAdvise(pSkype);
if( NULL == pSkype ){
error_message += L"DispEventAdvise failed\n";
//goto finalize;
}
// Attach to API
hr = pSkype->Attach(5, VARIANT_TRUE);
if( FAILED(hr) ){
error_message += L"Attach failed\n";
goto finalize;
}
xtime xt;
MSG msg;
while( run )
{
while(
run
&& PeekMessage( &msg, NULL, 0, 0, PM_REMOVE )
){
TranslateMessage(&msg);
DispatchMessage(&msg);
}
ThreadWait( xt, 50, 10 ); // wait
}
finalize:
// Disconnect events
pSink->DispEventUnadvise(pSkype);
// Cleanup
pSkype = NULL;
CoUninitialize();
theApp.UnloadSkype4COMDLL();
pause = true;
run = false;
}
And I've checked that COM pointers nullified correctly like below
Code:
class CMyView : public CView{
...
public:
void CleanUPCOMPtr( void );
private:
CComQIPtr<ISomeInterface> p; // declared as a class member variable
};
// called when closing this app
void CMyView::CleanUpCOMPtr( void )
{
if( !(!p) ){
p.Release();
}
ASSERT(!p);
}
On the above code, CleanUpCOMPtr called before CoUninitialize function and assertion didn't occur when I closing this application. These two things has exactly confirmed.
CoUninitialize function has been called in the CMyApp::ExitInstance function. CMyApp inherits CWinAppEx.
My entire code is very long and can't open to public.
I may create a solution to repro this bug as I possible.
-
Re: VS2010&OLE32.dll access violation problem with COM
You need to read up on COM and understand what smart pointers do for you.
I say this because with COM, you don't need to explicitly load a COM dll.
So remove these two lines.
Code:
theApp.LoadSkype4COMDLL();
theApp.UnloadSkype4COMDLL();
Also, I finally get you to post the code because I needed to see what you are actually doing. And guess what? You are calling CoUninitialize before your smart pointers are going out of scope.
Code:
void operator()(void)
{
theApp.LoadSkype4COMDLL(); // What's this?
CoInitialize(NULL);
// Create object
ISkypePtr pSkype(__uuidof(Skype));
// Create sink
scoped_ptr<CSkypeEvents> pSink( new CSkypeEvents(man) );
CoUninitialize(); // Whoops. pSkype and pSink haven't gone out of scope yet.
theApp.UnloadSkype4COMDLL(); // What's this?
}
Read up about COM smart pointers (or step through the smart pointer code). You'll see that smart pointers automatically call Release - that's why they're smart.
So, you don't need to do this.
// called when closing this app
Code:
void CMyView::CleanUpCOMPtr( void )
{
if( !(!p) ){
p.Release();
}
ASSERT(!p);
}
To fix this, just scope the COM pointers
Code:
CoInitialize(NULL);
{ // Scoping block
ISkypePtr pSkype(__uuidof(Skype));
scoped_ptr<CSkypeEvents> pSink( new CSkypeEvents(man) );
HRESULT hr(S_OK);
// Connect events
hr = pSink->DispEventAdvise(pSkype);
if( NULL == pSkype )
{
error_message += L"DispEventAdvise failed\n";
//goto finalize;
}
// Attach to API
hr = pSkype->Attach(5, VARIANT_TRUE);
if( FAILED(hr) )
{
error_message += L"Attach failed\n";
goto finalize;
}
xtime xt;
MSG msg;
while( run )
{
while( run && PeekMessage( &msg, NULL, 0, 0, PM_REMOVE ) )
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
ThreadWait( xt, 50, 10 ); // wait
}
finalize:
// Disconnect events
pSink->DispEventUnadvise(pSkype);
} // End of scoping block (causes smart pointer to release their interfaces)
CoUninitialize();
-
Re: VS2010&OLE32.dll access violation problem with COM
Thanks Arjay
But if I didn't run this code at least once this issue will occurs.
Code:
CoInitialize(NULL);
{
ISkype *pSkype(NULL);
// do something
}
CoUninitialize();
Is the above code ok ?
theApp.LoadSkype4COMDLL and theApp.UnloadSkype4COMDLL will do that 'regsvr32 /s skype4COM.dll' and 'regsvr32 /s /u skype4COM.dll'.
These processes may be needed on my sense if we want complete nullification.
CComPtr holder are CView and CDocument inherited class on myprogram , and I've checked that these destructors will be called before CoUninitialize.
So all of CComPtr's destructors will be proceeded.
Then, how can we suspect about an access violation in the ntdll.dll ?
-
Re: VS2010&OLE32.dll access violation problem with COM
Quote:
Originally Posted by
lightshield
theApp.LoadSkype4COMDLL and theApp.UnloadSkype4COMDLL will do that 'regsvr32 /s skype4COM.dll' and 'regsvr32 /s /u skype4COM.dll'.
These processes may be needed on my sense if we want complete nullification.
Then, how can we suspect about an access violation in the ntdll.dll ?
instead of calling those methods Loadxxx, you should call them Registerxxx. Actually you should let a setup program handle the COM registration. With your program, what happens if the skype dll is already registered? Your program will break the next guy.
I have no idea what nullification is.
The problem with your program is in your code, not in ntdll.dll.
-
Re: VS2010&OLE32.dll access violation problem with COM
Yes, the problem is in my code exactly, but access violation exception message pumped up in the ntdll.dll.
-
Re: VS2010&OLE32.dll access violation problem with COM
Quote:
These processes may be needed on my sense if we want complete nullification.
Okay, this is where you're wrong. Sorry, but your COM knowledge seems rather poor. I'd recommend to start learning COM from very basics.
Regarding nullification, it was said exclusively about smart pointers, as this is a common practice for releasing interface before the moment the smart pointer leaves its scope:
Code:
ISomePtr p = NULL;
HRESULT hr = p.CreateInstance(__uuidof(Some));
. . .
p = NULL;
. . .
-
Re: VS2010&OLE32.dll access violation problem with COM
I mean the nullification as the uninstallation of software modules.
I've known about the nullification of pointers of COM interfaces in terms of 'SafeRelease'.
By the way, therefor I've deleted sources that use CComQIPtr(s) completely, an exception in the ntdll.dll occurs.
It seems a problem that should be solved by myself.
Thanks all.
-
Re: VS2010&OLE32.dll access violation problem with COM
:thumb:
Quote:
Originally Posted by
lightshield
I mean the nullification as the uninstallation of software modules.
I've known about the nullification of pointers of COM interfaces in terms of 'SafeRelease'.
By the way, therefor I've deleted sources that use CComQIPtr(s) completely, an exception in the ntdll.dll occurs.
It seems a problem that should be solved by myself.
Thanks all.
You're going the wrong direction. All your COM interfaces should use a COM smart pointer like CComQIPtr.
-
Re: VS2010&OLE32.dll access violation problem with COM
Quote:
Originally Posted by
lightshield
I mean the nullification as the uninstallation of software modules.
And what's the idea behind? Why do you need that? :confused:
Quote:
By the way, therefor I've deleted sources that use CComQIPtr(s) completely, an exception in the ntdll.dll occurs.
Therefore? Afraid, I don't follow you. What's wrong with CComQIPtr? :confused: In terms of 'safe release' CComQIPtr has no difference compared with other COM smart pointers.
-
Re: VS2010&OLE32.dll access violation problem with COM
There are users who think like that some software are not uninstalled after uninstallation if some COM components don't unregistered. So I do these things in my program.
And sorry for my poor English skill.
But I really wonder that this issue doesn't occurs in VS2008.
-
Re: VS2010&OLE32.dll access violation problem with COM
Quote:
Originally Posted by
Arjay
:thumb:You're going the wrong direction. All your COM interfaces should use a COM smart pointer like CComQIPtr.
No, it's a special case. I'll use COM smart pointers mainly. it's just a test case.
I found the problem in implementations in basic MDI-frameworks( CMainframe, CChildFrame, CMyApp, CMyDoc, CMyView).
Maybe I can find the affected part soon.
-
Re: VS2010&OLE32.dll access violation problem with COM
Quote:
Originally Posted by
lightshield
There are users who think like that some software are not uninstalled after uninstallation if some COM components don't unregistered. So I do these things in my program.
And sorry for my poor English skill.
But I really wonder that this issue doesn't occurs in VS2008.
Those users would be wrong with that assumption and you would be wrong for coding it that way. Look there is a defined system for software installations/uninstallations that involved reference counting of components? Why not learn how to follow the recommended way to install apps instead of your hacked way?
In terms of your program appearing to run on 2008 - by the looks of code you posted and your understanding of COM, I'd say you got lucky.
-
Re: VS2010&OLE32.dll access violation problem with COM
Quote:
Originally Posted by
Arjay
Those users would be wrong with that assumption and you would be wrong for coding it that way. Look there is a defined system for software installations/uninstallations that involved reference counting of components? Why not learn how to follow the recommended way to install apps instead of your hacked way?
In terms of your program appearing to run on 2008 - by the looks of code you posted and your understanding of COM, I'd say you got lucky.
I have to unregister my COM component for the special reason that related to the running state of my application( running or shutting down. e.g. DirectShow filters). So I handling the registration of my COM components in my program. I think that it is necessary to fulfill the software requirement and it's not suitable for the installation system. Skype-API will not be involved in this requirement, so this may not be unregistered.
As I wrote in previous posts, this issue occurs after I deleted sources that use COM smart pointers.
I've screwing up now. COM related libraries that I using are below..
-Direct2D
-DirectShow(MicrosoftSDK v7.1)
But I found some lights to solve this issue. I'll try to resolve by myself. thanks all
-
Re: VS2010&OLE32.dll access violation problem with COM
Try to use SetErrorInfo(0,NULL) before CoUninitialize() if you sure that there are no active smart-pointers. It may help.
-
Re: VS2010&OLE32.dll access violation problem with COM
Quote:
Originally Posted by
Vi2
Try to use SetErrorInfo(0,NULL) before CoUninitialize() if you sure that there are no active smart-pointers. It may help.
It won't make any difference.
-
Re: VS2010&OLE32.dll access violation problem with COM
Quote:
Originally Posted by
Vi2
Try to use SetErrorInfo(0,NULL) before CoUninitialize() if you sure that there are no active smart-pointers. It may help.
I've saw no difference by this method.
-
Re: VS2010&OLE32.dll access violation problem with COM
I've fixed this problem !
Seems this error had not came from CComQIPtr and COM。 MFC's some points might be causes... fmmmm