请教MS专家和各位高手:.NET RCW Thread Idle(GC?)
beck 2002-07-23 01:48:05 工作发现,如果使用一个全局的RCW对象(包装一个COM),开始的时候我在主线程和新生成的线程使用这个对象进行COM调用都没有问题。但是,如果程序idle 10几到20几分钟后,主线程中调用该对象没有问题,新生成的线程中则会抛出System.InvalidCastException,QI失败。
大家可以试一下,下面用的是MS Web浏览器控件,我们实际还用了其它的ActiveX控件,但问题是一样的。我想应该不是控件的问题,怀疑是.NET的BUG或者我们使用.NET有点不对的地方。问题的关键是开始都没有问题,就是idle了一段时间后问题就出来了。也曾想过是不是GC的问题?但我直接调用System.GC.Collect()也还是要等idle 10几分钟后才有问题。
用VB.NET建一个WindowsApplication,Form上添加Web浏览器控件,再添加两个Button(ButtonThreadNavigate、ButtonSelfNavigate_Click),输入代码:
Public Shared __M_Web As AxSHDocVw.AxWebBrowser '全局静态引用,以便线程使用
Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
Thread.CurrentThread.Name = "__Main__"
__M_Web = Me.AxWebBrowser1
End Sub
Private Sub ButtonSelfNavigate_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles ButtonSelfNavigate.Click
NavigateURL("http://www.csdn.net")
End Sub
Private Sub ButtonThreadNavigate_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles ButtonThreadNavigate.Click
Dim __Thread As System.Threading.Thread = New System.Threading.Thread(AddressOf ThreadNavigate)
__Thread.Start()
End Sub
Public Shared Sub NavigateURL(ByVal strURL As String)
Trace.WriteLine("Navigate Thread:" & Thread.CurrentThread.GetHashCode() & ":" & Thread.CurrentThread.Name)
Try
__M_Web.Navigate(strURL)
Catch exp As Exception
Trace.WriteLine(exp.ToString())
MsgBox(exp.ToString())
End Try
Trace.WriteLine("End NavigateURL")
End Sub
Public Shared Sub ThreadNavigate()
NavigateURL("http://www.yahoo.com")
End Sub
先点击SelfNavigate,然后点击ThreadNavigate,没有问题。好,不理他,把程序放在一边。10-20分钟后过来,点击SelfNavigate,没有问题;点击ThreadNavigate,异常发生:
System.InvalidCastException: 接口 SHDocVw.IWebBrowser2 的 QueryInterface 失败。
at SHDocVw.IWebBrowser2.Navigate(String URL, Object& Flags, Object& TargetFrameName, Object& PostData, Object& Headers)
at AxSHDocVw.AxWebBrowser.Navigate(String uRL, Object& flags, Object& targetFrameName, Object& postData, Object& headers)
at testcallscript.Form1.NavigateURL(String strURL) in D:\Documents and Settings\Administrator\My Documents\Visual Studio Projects\testcallscript\Form1.vb:line 218
(运行环境:中文/英文.NET SP1/中文Win2000 SP2;英文.NET SP1/英文Win2000 SP2)