Help ...When to Call ::CoInitialize and ::CoUninitialize();- 
Author Message
 Help ...When to Call ::CoInitialize and ::CoUninitialize();-

Hi every one
I had a confusion with where and when to using CoInitialize,CoInitializeEx
and CoUninitialize();

I have a Atl based com ServerA(outprocess exe.) I build another atl ServerB
(a dll) which uses COM objects of ServerA. Finally VB uses ServerB objects.
ServerA has one function which is running in second thread too. Server B
aslo has second thread too. So there is a situation where three threads can
run pararelly.

My questionS are
1. Do I have to add  CoInitialize(NULL) and CoUninitialize() to each every
function which uses COM object.
    eg FunctionX()
    {
        CoInitialize(NULL)

        //Call the COM object

        CoUninitialize()
    }
2.only Add CoInitializeEX(....) and CoUninitialize() only in the thread
creation ??
eg: DWORD WINAPI CTestMacroInterface::ThreadProcInitiateTest(void *p)
    {

     ::CoInitializeEx(NULL,COINIT_APARTMENTTHREADED);
     CTestMacroInterface* pObject =( CTestMacroInterface*)p;

     pObject->ExecuteTest();

     ::CoUninitialize();
       return 0;

Quote:
}

3. Do I have to CoInitialize(NULL) only for Dll server and
CoInitializeEX(...) for EXE server ??

4.All the dispatch functions need to add   CoInitialize(NULL) and
CoUninitialize()  internally
eg
    STDMETHODIMP CMTSDriverDisp::ClearChannelAssignments()
    {
     ::CoInitialize(NULL);
     if (m_pCurrentdrv!=NULL)
     {
      m_pCurrentdrv->ClearChannelAssignments();
     }
     ::CoUninitialize();
     return S_OK;
    }
5. If there is any harm if I add all function in my class with
::CoInitialize(NULL); and ::CoUninitialize();
 in pairs
6. Can I share static variable in two thread. eg Class A has a static
variable. object A which is created in main thread access in the static
variable.and object B aslo acess the static variable in a second thread.

I got and access violation error in my program. Please Help me out the rules
how to I use these initialisation.



Wed, 08 Sep 2004 00:07:42 GMT  
 Help ...When to Call ::CoInitialize and ::CoUninitialize();-
Every thread that plans to use COM has to call CoInitialize(Ex) as the
first COM call, and CoUninitialize as the last COM call. Nested
initializations to the same apartment model are allowed but not needed
and are generally discouraged (each successful CoInitialize(Ex) must be
matched by CoUninitialize on the same thread). Typically CoInitialize is
called at the top of WinMain or ThreadProc, and CoUninitialize at the
bottom.

Out-of-proc server needs to initialize COM on all its threads, including
its primary thread (the one on which WinMain or main is called) and any
threads it explicitly creates. In-proc server needs to initialize COM on
threads that it explicitly creates.

CoInitialize(0) is equivalent to CoInitializeEx(0,
COINIT_APARTMENTTHREADED). The thread calls CoInitializeEx(0,
COINIT_APARTMENTTHREADED) (or CoInitialize(0) ) or CoInitializeEx(0,
COINIT_MULTITHREADED) depending on which apartment it wants to enter -
STA or MTA. Choice of STA vs MTA is independent of whether the server is
in-proc or out-of-proc.

You can access a variable from multiple threads, but you need to ensure
proper access synchronization. Imagine one thread writing to a variable
and another reading from it at the same time. The reader may end up with
an inconsistent value - half old and half new.

Special rules apply to COM interface pointers - you cannot use them from
the threads belonging to different apartments. For more details, see
"INFO: Descriptions and Workings of OLE Threading Models (Q150777)" at

http://support.microsoft.com/default.aspx?scid=kb;EN-US;q150777

--
With best wishes,
    Igor Tandetnik

"For every complex problem, there is a solution that is simple, neat,
and wrong." H.L. Mencken


Quote:
> Hi every one
> I had a confusion with where and when to using

CoInitialize,CoInitializeEx
Quote:
> and CoUninitialize();

> I have a Atl based com ServerA(outprocess exe.) I build another atl
ServerB
> (a dll) which uses COM objects of ServerA. Finally VB uses ServerB
objects.
> ServerA has one function which is running in second thread too. Server
B
> aslo has second thread too. So there is a situation where three
threads can
> run pararelly.

> My questionS are
> 1. Do I have to add  CoInitialize(NULL) and CoUninitialize() to each
every
> function which uses COM object.
>     eg FunctionX()
>     {
>         CoInitialize(NULL)

>         //Call the COM object

>         CoUninitialize()
>     }
> 2.only Add CoInitializeEX(....) and CoUninitialize() only in the
thread
> creation ??
> eg: DWORD WINAPI CTestMacroInterface::ThreadProcInitiateTest(void *p)
>     {

>      ::CoInitializeEx(NULL,COINIT_APARTMENTTHREADED);
>      CTestMacroInterface* pObject =( CTestMacroInterface*)p;

>      pObject->ExecuteTest();

>      ::CoUninitialize();
>        return 0;
> }
> 3. Do I have to CoInitialize(NULL) only for Dll server and
> CoInitializeEX(...) for EXE server ??

> 4.All the dispatch functions need to add   CoInitialize(NULL) and
> CoUninitialize()  internally
> eg
>     STDMETHODIMP CMTSDriverDisp::ClearChannelAssignments()
>     {
>      ::CoInitialize(NULL);
>      if (m_pCurrentdrv!=NULL)
>      {
>       m_pCurrentdrv->ClearChannelAssignments();
>      }
>      ::CoUninitialize();
>      return S_OK;
>     }
> 5. If there is any harm if I add all function in my class with
> ::CoInitialize(NULL); and ::CoUninitialize();
>  in pairs
> 6. Can I share static variable in two thread. eg Class A has a static
> variable. object A which is created in main thread access in the
static
> variable.and object B aslo acess the static variable in a second
thread.

> I got and access violation error in my program. Please Help me out the
rules
> how to I use these initialisation.



Wed, 08 Sep 2004 00:49:06 GMT  
 Help ...When to Call ::CoInitialize and ::CoUninitialize();-
Thanks Igor
Based on your comments
1.Every thread that plans to ...
 In my atll dll  I am having a ThreadProc for a worker thread where I call
CoInitializeEx(0,COINIT_APARTMENTTHREADED)
and CoUninitialize  at the end of the thread. At the end of the thread Do I
have to call CoInitializeEx( ...) in the Primary thread again ??
When I call  ThreadProc It's works ok. But Call second time I get ole32.dll
access violation Error.
What if I add CoInitialize(0) CoUninitialize to all function which uses com
object regardless of thread.
Note :I am using GIT method to share com interface pointer between threads.

2...Out-of-proc server needs to initialize COM
Once we develop com object we don't know how the user going to use (multiple
threads..)
You mean add CoInitializeEx(COINIT_MULTITHREADED) and CoUninitialize to each
interface with in the server so that some function they can call same thread
other can call in worker thread.
eg sample interface for an out process EXE
 STDMETHODIMP CMTSDriverDisp::ClearChannelAssignments()
    {     ::CoInitialize(0,COINIT_MULTITHREADED);
      if (m_pCurrentdrv!=NULL)
    {
      m_pCurrentdrv->ClearChannelAssignments();
     }
     ::CoUninitialize();
    return S_OK;
    }

Note: My out process exe not use any COM objects internally if it so  Do I
have to add CoInitialize(0,COINIT_MULTITHREADED)  ::CoUninitialize();in the
each interface ??

3. For in process (dll)  STA should I use
CoInitializeEx(0,COINIT_APARTMENTTHREADED) always ?? in all interface
functions or the calling function
4.For outprocess(exe)MTA  should I useCoInitializeEx(0,COINIT_MULTITHREADED)
always?? in all interface functions or the calling function

Thanks in advance


Quote:
> Every thread that plans to use COM has to call CoInitialize(Ex) as the
> first COM call, and CoUninitialize as the last COM call. Nested
> initializations to the same apartment model are allowed but not needed
> and are generally discouraged (each successful CoInitialize(Ex) must be
> matched by CoUninitialize on the same thread). Typically CoInitialize is
> called at the top of WinMain or ThreadProc, and CoUninitialize at the
> bottom.

> Out-of-proc server needs to initialize COM on all its threads, including
> its primary thread (the one on which WinMain or main is called) and any
> threads it explicitly creates. In-proc server needs to initialize COM on
> threads that it explicitly creates.

> CoInitialize(0) is equivalent to CoInitializeEx(0,
> COINIT_APARTMENTTHREADED). The thread calls CoInitializeEx(0,
> COINIT_APARTMENTTHREADED) (or CoInitialize(0) ) or CoInitializeEx(0,
> COINIT_MULTITHREADED) depending on which apartment it wants to enter -
> STA or MTA. Choice of STA vs MTA is independent of whether the server is
> in-proc or out-of-proc.

> You can access a variable from multiple threads, but you need to ensure
> proper access synchronization. Imagine one thread writing to a variable
> and another reading from it at the same time. The reader may end up with
> an inconsistent value - half old and half new.

> Special rules apply to COM interface pointers - you cannot use them from
> the threads belonging to different apartments. For more details, see
> "INFO: Descriptions and Workings of OLE Threading Models (Q150777)" at

> http://support.microsoft.com/default.aspx?scid=kb;EN-US;q150777

> --
> With best wishes,
>     Igor Tandetnik

> "For every complex problem, there is a solution that is simple, neat,
> and wrong." H.L. Mencken



> > Hi every one
> > I had a confusion with where and when to using
> CoInitialize,CoInitializeEx
> > and CoUninitialize();

> > I have a Atl based com ServerA(outprocess exe.) I build another atl
> ServerB
> > (a dll) which uses COM objects of ServerA. Finally VB uses ServerB
> objects.
> > ServerA has one function which is running in second thread too. Server
> B
> > aslo has second thread too. So there is a situation where three
> threads can
> > run pararelly.

> > My questionS are
> > 1. Do I have to add  CoInitialize(NULL) and CoUninitialize() to each
> every
> > function which uses COM object.
> >     eg FunctionX()
> >     {
> >         CoInitialize(NULL)

> >         //Call the COM object

> >         CoUninitialize()
> >     }
> > 2.only Add CoInitializeEX(....) and CoUninitialize() only in the
> thread
> > creation ??
> > eg: DWORD WINAPI CTestMacroInterface::ThreadProcInitiateTest(void *p)
> >     {

> >      ::CoInitializeEx(NULL,COINIT_APARTMENTTHREADED);
> >      CTestMacroInterface* pObject =( CTestMacroInterface*)p;

> >      pObject->ExecuteTest();

> >      ::CoUninitialize();
> >        return 0;
> > }
> > 3. Do I have to CoInitialize(NULL) only for Dll server and
> > CoInitializeEX(...) for EXE server ??

> > 4.All the dispatch functions need to add   CoInitialize(NULL) and
> > CoUninitialize()  internally
> > eg
> >     STDMETHODIMP CMTSDriverDisp::ClearChannelAssignments()
> >     {
> >      ::CoInitialize(NULL);
> >      if (m_pCurrentdrv!=NULL)
> >      {
> >       m_pCurrentdrv->ClearChannelAssignments();
> >      }
> >      ::CoUninitialize();
> >      return S_OK;
> >     }
> > 5. If there is any harm if I add all function in my class with
> > ::CoInitialize(NULL); and ::CoUninitialize();
> >  in pairs
> > 6. Can I share static variable in two thread. eg Class A has a static
> > variable. object A which is created in main thread access in the
> static
> > variable.and object B aslo acess the static variable in a second
> thread.

> > I got and access violation error in my program. Please Help me out the
> rules
> > how to I use these initialisation.



Wed, 08 Sep 2004 02:44:17 GMT  
 Help ...When to Call ::CoInitialize and ::CoUninitialize();-

Quote:
> Thanks Igor
> Based on your comments
> 1.Every thread that plans to ...
>  In my atll dll  I am having a ThreadProc for a worker thread where I
call
> CoInitializeEx(0,COINIT_APARTMENTTHREADED)
> and CoUninitialize  at the end of the thread. At the end of the thread
Do I
> have to call CoInitializeEx( ...) in the Primary thread again ??

Of course not. COM initialization is on a per-thread basis. Initializing
and unintializing it in one thread does not affect other threads.

Quote:
> When I call  ThreadProc It's works ok. But Call second time I get
ole32.dll
> access violation Error.
> What if I add CoInitialize(0) CoUninitialize to all function which
uses com
> object regardless of thread.
> Note :I am using GIT method to share com interface pointer between

threads.

What do you mean, call it again? You don't call ThreadProc, you pass its
address as a parameter to CreateThread or similar function. It does not
make sense to initialize/uninitialize in every member function. If a
method of COM object is called at all, the COM must be initialized
already, right?

Quote:
> 2...Out-of-proc server needs to initialize COM
> Once we develop com object we don't know how the user going to use
(multiple
> threads..)

It does not matter. The clients are necessarily in a different process,
so they will be in a different apartment anyway. Out-of-proc COM server
can me STA or MTA no matter what threading model its clients are
expected to use.

Quote:
> You mean add CoInitializeEx(COINIT_MULTITHREADED) and CoUninitialize
to each
> interface with in the server so that some function they can call same
thread
> other can call in worker thread.

Not each interface - each thread. Again - COM initialization is
performed on a per-thread basis.

Quote:
> eg sample interface for an out process EXE
>  STDMETHODIMP CMTSDriverDisp::ClearChannelAssignments()
>     {     ::CoInitialize(0,COINIT_MULTITHREADED);
>       if (m_pCurrentdrv!=NULL)
>     {
>       m_pCurrentdrv->ClearChannelAssignments();
>      }
>      ::CoUninitialize();
>     return S_OK;
>     }

> Note: My out process exe not use any COM objects internally if it so
Do I
> have to add CoInitialize(0,COINIT_MULTITHREADED)

::CoUninitialize();in the

Quote:
> each interface ??

Don't do that. Initialize once in WinMain, and once in any ThreadProc
you might have.

Quote:
> 3. For in process (dll)  STA should I use
> CoInitializeEx(0,COINIT_APARTMENTTHREADED) always ?? in all interface
> functions or the calling function

Again, only in ThreadProc of any new thread your DLL may create.

Quote:
> 4.For outprocess(exe)MTA  should I

useCoInitializeEx(0,COINIT_MULTITHREADED)

Quote:
> always?? in all interface functions or the calling function

Only once in WinMain and ThreadProc.

BTW, you don't have to initalize all threads in the same way. An STA
object (in-proc or out-of-proc) can internally create MTA worker
threads, and vice versa. STA object/MTA workers combination often makes
a lot of sense.
--
With best wishes,
    Igor Tandetnik

"For every complex problem, there is a solution that is simple, neat,
and wrong." H.L. Mencken



Wed, 08 Sep 2004 03:24:18 GMT  
 
 [ 4 post ] 

 Relevant Pages 

1. Help on CoInitialize,CoInitializeEx and CoUninitialize();

2. Problem with multiple CoInitialize/CoUninitialize

3. Reg. CoInitialize and CoUninitialize from DLLs

4. ExitThread hangs due to CoInitialize / CoUninitialize

5. CoInitialize has not been called

6. Is there an apartment before I call CoInitialize?

7. Do I need CoInitialize if I make no calls to Co*()

8. Calling CoInitialize from a new dll thread

9. calling CoInitialize() multiple times on the same thread?

10. where to call: CoInitialize or CoInitializeSecurity or AfxOleInit?

11. where to call: CoInitialize or CoInitializeSecurity or AfxOleInit?

 

 
Powered by phpBB® Forum Software