Click here to Skip to main content
15,888,351 members
Please Sign up or sign in to vote.
1.00/5 (1 vote)
See more:
Hello,

I have one C# Window Services based application in which using ActiveX which required to be run on Single thread apartment [STA]. That ActiveX doing TCP communication.

If I run it as MTA then it gives exception "ActiveX control cannot be instantiated because the current thread is not in a single-threaded apartment."

Now I found two ways to run it in STA.

1) Write [STAThread] in entry level method of application. Like below:
C#
[STAThread]
static void Main()



2) Start New thread and set apartment state to STA like below

C#
Thread t = new Thread(() => StartTCPCommunication());
t.SetApartmentState(ApartmentState.STA);
t.Start();


Now my question is what is the difference between above 2 ways.

Because my application structure is like that I can't use Way#1 becuase my appication running as Windows Service. so even if I use way#1 it give me ActiveX exception mentioned above.

If I convert windows services to Windows Desktop application then same code working fine with Way#1

But I need windows service so I need to use Way#2, but when I used that I can not do TCP communication and even not get any exception.

So can any one help me to figure out the issue ? or some alternate way ?

Thanks in advance
Posted
Updated 14-Apr-15 0:32am
v2
Comments
Sergey Alexandrovich Kryukov 14-Apr-15 10:24am    
First of all, why do you think you need STA for your service? Yes, it's possible that you need it; I just want to know why.
—SA

1 solution

First of all, here is the simplest advice: don't use any stupid and obsolete ActiveX controls for TCP communications. Just listen how it sounds: ActiveX? In .NET? Seriously?

Instead, you can use the sockets, or, even better and simpler, the class System.Net.Sockets.TcpListener. which is also the part of sockets API, wrapped for your convenience:
https://msdn.microsoft.com/en-us/library/system.net.sockets.tcplistener%28v=vs.110%29.aspx,
https://msdn.microsoft.com/en-us/library/system.net.sockets.tcplistener%28v=vs.110%29.aspx.

Also, I don't know why you decided that Way#1 cannot be used for a service. A service application also has the entry point method, so you can apply the attribute [System.STAThread] to it.

And of course you always could use Way#2. You did not provide any information on why it did not work, but you could face different problems by different reasons. For example, you could create this STAThread but still do something problematic not in this thread, but in some other thread. :-)

—SA
 
Share this answer
 
Comments
npdev13 15-Apr-15 1:48am    
Hi SA,

Thanks for looking into the issue.

Actually my requirement little complex and difficult to explain why I am using ActiveX

but anyway I found the solution of the problem. Actually my issue was how to use Activex without Windows application. And by writing below line it works for me
System.Windows.Forms.Application.Run();

in Way#2 I have modified code like below and it works fine

Thread t = new Thread((ThreadStart)
delegate
{
StartTCPCommunication();
System.Windows.Forms.Application.Run();
});
t.SetApartmentState(ApartmentState.STA);
t.Start();


Thanks again for looking into this.
Sergey Alexandrovich Kryukov 15-Apr-15 1:59am    
If you don't want to explain, don't. But I gave you tree options for the solution. How a service is related to Application.Run? It all looks like a big abuse. No, you hardly solved the problem; even if you managed to shut up one exception...
—SA

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900