c++commarshallingstaapartments

Will COM marshalling be (ever) neccessary for an object with ThreadingModel Both?


This is triggered by another question.

Specifically, I have a in process COM class, that is defined in the CLSID registry as having a ThreadingModel of Both.

Our process activates this object through CoCreateInstance (not CoCreateInstanceEx, if that even matters for an in-proc dll server)

Given a threading model of Bothand given th rules listed in the docs:

Threading model of server | Apartment server is run in
------------------------------------------------------
Both                      | Same apartment as client

and given what Hans writes in the other answer:

... Marshaling occurs when the client call needs to be made on a different thread. ... can happen when the ThreadingModel specified in the comClass element demands it. In other words, when the COM object was created on one thread but is called on another and the server is not thread-safe.

my tentative conclusion would be that such an object will never need implicit marshalling of calls to its interfaces, since the object will always live in the same apartment as its client.

Is that correct, even if the client process is running as STA?


Solution

  • Yes, there may be marshaling.

    If the client of your COM class is running in an STA and you attempt to invoke your class from another apartment, it will have to marshal to the apartment that it was created in.

    The COM terminology can be really confusing. When you refer to a 'client' in this case, you're really referring to a thread, not the entire application (as it would imply).

    Both just means that the threading model of the server conforms to the client that instantiates it. That is, when you instantiate your class, it takes on the threading model of the thread it was created on. Since you're instantiating the server in an STA, your server will use STA, meaning it can only be invoked on the thread that created it; if another thread tries to invoke it, it will marshal to the thread it was created on.