Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

COM Interop .NET STA

If I have an STA thread in .NET, and I create an STA COM object in that thread, and then the thread finishes -- does that kill that instance of the object?

Is my understanding correct that STA COM objects can be accessed by multiple threads and runtime will automatically marshal the calls to all happen in the apartment thread? Is that thread the thread that has created the instance? So if that thread finishes, the instance is orphaned and lost? Or is there a separate thread created for STA instances?
How does this play out in ASP.Net with ASPCompat=True? My understanding is that each request is handled by a random worker thread, and if my STA component is placed into the session, will it randomly die because the request processor thread that created it might have finished?

like image 674
MK. Avatar asked Dec 13 '10 16:12

MK.


1 Answers

If you create your STA COM object on a .NET STA Thread, all calls to your object are marshalled to that thread.

If you create your STA COM object on a .NET MTA Thread, the runtime will create a STA thread and marshall all calls to that thread.

So, when your (STA) thread exists, your COM objects are inaccessable.

A solution might be to create the objects on a new thread for which you can control the lifetime.

I have done a similar thing like that:

using (ManualResetEventSlim mre = new ManualResetEventSlim(false))
{  
    Thread _STAThread = new Thread(new ThreadStart(() =>
                {
                    globalComObject = new ComClass();
                    mre.Set();
                    try
                    {
                        Thread.CurrentThread.Join();
                    }
                    catch (ThreadAbortException)
                    {
                    }
                }));
                _STAThread.SetApartmentState(ApartmentState.STA);
                _STAThread.IsBackground = true;
                _STAThread.Start();
                mre.Wait();
}

The code starts a new thread, set the appartment to STA and waits for the creation of a COM object on that thread. The thread itself is running till your application exits (IsBackground = true) or you kill the thread explicitly with Thread.Abort().

But keep in mind, that all calls to your COM objects are marshalled and thus executed serialized one after another on that one thread. That might be a big bottleneck in your App.

ASPCompat=true signals the ASP.NET runtime, that you are using STA COM objects and thus running the page within an STA thread. otherwise you migth get an exception or all your COM objects will run in the automatically generated STA thread shared by all requests to your page (see MSDN here: http://msdn.microsoft.com/en-us/library/zwk9h2kb(VS.80).aspx)

like image 190
Jan Avatar answered Sep 30 '22 09:09

Jan