"The instruction at "0x30cb05e4" referenced memory at "0x00000000". The
memory could not be "written".
I narrowed down why this is happening, but haven't yet found a
workaround to my liking. If anyone has any insight, I would be greatly
appreciative.
Here is what I have been able to learn: The bug is occurring because of
the SharePoint Presence information. On SharePoint pages that display
user presence icons, the HTML calls client side javascript with the
following line:
onload="IMNRC('us...@address.com')"
This function (found in ows.js) then creates a client side ActiveX
object:
IMNControlObj = new ActiveXObject("Name.NameCtrl.1")
Something about the creation of this object causes axWebBrowser to die
a miserable death when you close the form containting the axWebBrowser
control.
So - I have pursued the following options:
1. Disable presence information on the server side:
http://www.microsoft.com/resources/documentation/wss/2/all/adminguide/en-us/stse14.mspx
This works, but it is not a very nice option because I want my app to
be able to connect to sites I don't have admin control over.
2. Disable scripts on the axWebBrowser control, using a bit of
trickery:
http://thecodeproject.com/books/0764549146_8.asp
http://groups-beta.google.com/group/microsoft.public.inetsdk.programming.webbrowser_ctl/messages/09dab8164cc55c67?thread_id=8f14b6135cdb8686&mode=thread&noheader=1&q=axWebBrowser%20DLCTL_NO_DLACTIVEXCTLS&
I built a solution that does this, but unfortunately, it works only for
WSS sites. For SharePoint Portal sites, you need javascript enabled, or
else it won't display the pages. I also tried disabling ActiveX
controls - but for some reason they still get loaded.
3. Spoof the UserAgent, so that the javascript doesn't load the
presence information. This won't work, because no matter what you do to
change the UserAgent, the navigator object in client-side javascript
will always reference the global IE setting:
http://support.microsoft.com/kb/q183412/
4. Download the page ahead of time, and search and replace out the
offending code. A very ugly option indeed. Haven't tried it yet, but I
am guessing I will run into problems with relative paths.
5. Find a way to hook into the events of the IMG tag at load time, and
disable the onload event... Haven't found a way to do this yet.
6. Find a way to clean up whatever evil the Name.NameCtrl ActiveX
object is doing before the form closes...
If anyone has any other insight, I would be greatly appreciative.
private void ConfigureUserAgent()
{
try
{
// Get the regisitry key for the IE user agent
Microsoft.Win32.RegistryKey rk =
Microsoft.Win32.Registry.LocalMachine.OpenSubKey(@"SOFTWARE\Microsoft\Windows\CurrentVersion\Internet
Settings\5.0\User Agent",true);
// Set the browser string to be an unknown browser, running on a mac
os
// This prevents the Presence ActiveX control from loading, which
will crash
// axWebBrowser, when the application closes.
rk.SetValue(null,"Unknown Browser");
rk.SetValue("Compatible","compatible");
rk.SetValue("Version","MSIE 6.0");
rk.SetValue("Platform","mac");
// Navigate to a blank page - wait for it to load
this.Navigate("about:blank");
while(this.w_axWebBrowser.Document == null)
{
Application.DoEvents();
}
// Run a script that causes the browser control to access the user
agent setting out
// of the registry. The browser then stores the setting for the
remainder of the session.
mshtml.IHTMLDocument2 doc = (mshtml.IHTMLDocument2)
this.w_axWebBrowser.Document;
mshtml.IHTMLWindow2 parentWindow = doc.parentWindow;
parentWindow.execScript("var ua = navigator.userAgent;",
"javascript");
// Restore the User Agent keys to their default state
rk.SetValue(null,"");
rk.DeleteValue("Compatible");
rk.DeleteValue("Version");
rk.DeleteValue("Platform");
}
catch (Exception ex)
{
System.Diagnostics.Debug.WriteLine("Exception thrown: " + ex.Message
+ "\n" + ex.StackTrace);
}
}
If anyone finds a cleaner solution - I would be very interested to
know.