Just what the heck is an ActiveX EXE? How do I use it and more importantly, why?
An ActiveX EXE is a special type of COM component that is used in specific circumstances. Yes, it is an EXE file, meaning it is loaded into its own address space and given its own process and threads, but it is designed to be an OLE automation server, just like an ActiveX DLL. In other words, it has no forms, has no “starting” point like a sub Main() and exposes interfaces (classes) to be used by a client application, just like an ActiveX DLL.
OK, if an ActiveX EXE is so similar, why would I choose to use an ActiveX EXE over an ActiveX DLL you may ask? Good question but let me explain how an ActiveX DLL works first, before I tell you about an ActiveX EXE.
An ActiveX DLL is mapped into the address space of the client application and becomes part of client’s process; the ActiveX DLL does not spawn its own thread. This means, in versions prior to VB.Net any way, the thread of the client application must yield processing and give that thread to the ActiveX DLL to use. This gives you synchronous processing; the calling application can not continue until the ActiveX DLL returns from the method call. This is a form of Apartment Threading; the DLL is not single threaded, that would mean all of the classes given out to clients would share the same thread, in Apartment Threading, each class is dependant on the thread given to it by the client application and all of those threads work independently.
An ActiveX EXE on the other hand creates a new thread for each new class that it creates! Each thread is independent of the client application. Hold on their Guru, are you talking about Multi-threading in a VB application??? Your damn straight, you can create a fully multi-threaded application by just creating classes from an ActiveX EXE. So, you can create an asynchronous call, meaning that the client application can continue processing while the ActiveX EXE is processing too. Just be sure to notify the client application that processing has either finished or has an error. The best way to do this is to create an event in the ActiveX EXE, then when creating the ActiveX EXE class, declare it with the “With Events” keyword.
Ok, sounds great, but when am I ever going to use it? As Scotty on Star Trek would say, “The right tool for the right job”, an ActiveX EXE is a tool and there is specific reasons when and why you would use it. The number one reason not to use it is when you will be transferring large amounts of data between the client and COM component. Remember, and ActiveX EXE is running out side of the clients processes, meaning, they can not pass data directly between the two, the operating system must “Marshall” the data back and forth, this creates a tremendous amount of over head and can significantly slow down the processing time; not a good idea.
There is also a “Gotcha” involved in an ActiveX EXE, they do not always work as stated, yes, the class does have its own thread and yes that thread is independent from the client application, but in VB anyway, the VB main thread does have a tendency to yield, just like a DLL. The work around that I have used in the past is to include the “timer Lite” DLL that you will find in our code section. I have the client call the main method, that method starts a timer for less then one second and returns to the client application. When the timer fires, I then call an internal (private) method that will execute the code the client thought was going to process. I know this sounds confusing, but it will all come together when we do the sample.
So, if passing data back and forth is very light and you need to process something independently of the client application, or you what something to run strictly firing it’s own events with minimal interaction with the client application, an ActiveX EXE could be your savior.
Let me give you an example of when I have used an ActiveX EXE in the past.
I needed to create an IVR (Interactive Voice Response, you know, press 1 for this, press 2 for that) system. It was to have 96 lines coming in and each line must run independently, it must have a “Master Control” application that controls the whole thing, for example, start and stop the system and monitor what is going on in the system, detect “dead” lines, clear them and re-start that line again.
OK, I need 96 instances of something that work independently of each other and independently of the client application. The thing I need to create will have minimal communications with the client except for sending up a few messages to let it know what is going on. Hmmmmm…..Sounds like a job for an ActiveX EXE to me, what do you think?
The final product worked like this. A VB based application would start, it would check the IVR board to see how many lines are available. It would then create that many instances of a class in an ActiveX EXE (in this case, 96), it would then pass a line to the class to monitor; the VB app then just sat back and waited.
The EXE class would handle it’s own events, for example “Line Ring”, and would process the call, it would send up a message to the VB app via an event to let the VB app know the line was being used and when it was finished with a call.
Sounds kind of nifty eh? And it worked like a charm.