As Richard said, STA's and MTA's are artifacts of COM.
In the early days of 16 bit Windows there was only one thread in all of
the operating system, so no one developing COM-objects then needed to
worry about if their code was called from multiple threads. No one
needed synchronization objects such as events and mutexes. Good times
all around :)
When Win32 came along you suddenly found yourself with all these threads
that could potentially call into your nice piece of code that was only
designed to be called from one and only one thread. What to do? There
had been a lot of COM-objects developed for 16-bit Windows that was used
in thousands of millions of applications (;)) and it was not feasible to
just throw them away because we now finally could do multitasking.
The solution was apartments. COM applications in 16-bit Windows already
had to perform some initialization prior to begin using COM, they had to
call the method CoInitialize(). So here was a way to identify
COM-applications that don't know anything about threading. If you call
CoInitialize you don't know what threads are and if you have created an
object on a thread, you assume that all calls to that object come in on
the same thread. Cool!
The requirement that you need to initialize COM before you could use any
of it was kept, but now you had to perform that initialization on every
thread that was about to use or create a COM object. Those applications
that was designed with threading in mind could state that by calling a
new method, CoInitializeEx, and state if they allowed calls coming in
from any thread or from just the one thread.
Any thread that calls CoInitialize() is said to enter the Single
Threaded Apartment (STA). In that apartment there can live only one
thread. If someone calls an object that is created on a thread in an STA
from another thread, the COM-runtime is said to marshal the code from
one thread to the other. This is accomplished by posting windows
messages to the STA thread. Windows messages will be put in the threads
message queue, which gives the thread a chance to handle them nice and
easy one by one. This is why a thread in an STA must contain a message pump.
A thread can call CoInitializeEx and state that the code here can handle
calls from multiple threads, that it has all the mutexes and critical
sections or whatever in check. These threads are said to enter the Multi
Threaded Apartment. An object created by a thread in the MTA can be
called directly by code on any other thread that is also in the MTA. No
marshalling and windows messaging voodoo necessary.
Pheew!
So when a .NET application is about to call a COM-object via interop, it
checks the current threads apartment state, which can either be MTA,
STA, or unknown. If the threads apartment state is STA, CoInitialize()
is called before interop is performed. If MTA or Unknown is set,
CoInitializeEx() is called with the multithreaded parameter. This
enables the COM-runtime to use marshalling where needed and skip it
where it is not needed.
The thread's apartment state can be set by using the
Threading.ApartmentState property for any thread or by applying the
STAThread or MTAThread to the application's Main method.
Jeeesh, what a long post! There are a lot more details to it, but I
think this covers the basics.
Regards,
Joakim
Richard Blewett [DevelopMentor] wrote:
Wow thousands of millions is alot of articles ;-)
The reason articles refer to COM interop when they talk about STAThread and MTAThread is because those attributes only have any relevance when you are performing COM interop. They have no impact whatsoever when no COM interop occurs.
So do you understand STAs and MTA in COM terms?
Regards
Richard Blewett - DevelopMentor
http://www.dotnetconsult.co.uk/weblog
http://www.dotnetconsult.co.uk
hi
i read thousands of millions of articles about STA and MTA :-). everything
very theoretical and i don't get it...
could anybody explain me the [STAThread] and [MTAThread] on a nice, small
and simple example where i really can see the difference between these two
methods...
they're all talking about 2 message loops and com interop... but what
benefit does i get when using either STA or MTA?
thanx, jazper