PRB: Blocking Occurs When Calling VB ActiveX EXE from ASP
ID: Q201014
|
The information in this article applies to:
-
Microsoft Internet Information Server version 4.0
-
Active Server Pages
-
Microsoft Visual Basic Learning, Professional, and Enterprise Editions for Windows, versions 5.0, 6.0
SYMPTOMS
When you create an ActiveX EXE component under Active Server Pages (ASP) in page scope only, all requests to the component are serialized to a single thread and blocking occurs.
CAUSE
When you use the apartment threading model to create your Visual Basic ActiveX EXE Component, all requests to the same Visual Basic ActiveX EXE Component are serialized.
If an object running in a single-threaded apartment (STA) is called concurrently by multiple clients (regardless of their threading model), COM synchronizes access to the object by posting window messages to the component's message queue. As a result, the object only receives one call each time it retrieves and dispatches a COM-related message.
While this interference implies some performance penalty, it allows applications that support different threading models to work together. Thus, all possible combinations of client and out-of-process component interoperability are supported.
RESOLUTION
By default, your Visual Basic EXE Instancing value is set to MultiUse. Therefore, only one object is created using the single-threaded apartment (STA) model. In Visual Basic, you are unable to mark your component's threading model to either Free or Both to allow multithreading.
However, you can achieve concurrent execution by marking your object as single use (singleton). This has scalability consequences. Every call to the object creates a new thread and a new object, which decreases performance and increases memory usage. At this point, you should consider rewriting your component.
STATUS
This behavior is by design.
MORE INFORMATION
Steps to Reproduce Behavior
- Use Performance Monitor (PerfMon) to monitor the following counters:
- Requests Queued
- Requests Executing
- Sessions Total
- Thread Count
- If you are using one computer as your client, make sure that you have the following options set in Internet Explorer (On the View menu, click Internet Options and then click the Advanced tab:
- Select the Browse in new process check box.
- Select the Disable all cookie use check box.
- Create a Visual Basic ActiveX EXE called ThreadWaitProject.ThreadTest, and implement the following function:
Private Declare Function GetCurrentThreadId Lib "kernel32" () As Long
Private Declare Sub Sleep Lib "kernel32" (ByVal dwMilliseconds As Long)
Function ThreadWait(nSeconds As Long) As Long
Sleep nSeconds * 1000
ThreadWait = GetCurrentThreadId
End Function
- Create an ASP page called threadwait_vb_exe.asp with the following script:
<%
Option Explicit
DIM NSec
Sub TestEXE
response.write "<H1>OOP VB EXE Threadwait</H1>"
Dim objTest
Set objTest = Server.CreateObject("ThreadWaitProjectEXE.ThreadSleep")
Response.Write "StartTime: " & Now & "<BR>"
Response.Write "ThreadID: " & objTest.ThreadWait(10) & "<BR>"
Response.Write "EndTime: " & Now & "<BR>"
Response.write "Session ID: " & Session.SessionId & "<BR>"
Set objTest = Nothing
End Sub
TestEXE
%>
- From two distinct (see the previous step 2) clients, request the Active Server Pages (ASP) page threadwait_vb_exe at the same time.
RESULT: Both requests share the same ThreadID, and the start and end times of both requests are serialized (the second request starts only when the first request has finished). Use PerfMon (step 1) to see that one request is queued while the other is being executed.
Additional query words:
Keywords : kbASP kbCOMt kbVBp500 kbVBp600 kbGrpASP
Version : WINDOWS:5.0,6.0; winnt:4.0
Platform : WINDOWS winnt
Issue type : kbprb