473,782 Members | 2,664 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

multiple threads writing to WebBrowser, getting deadlocked

I have multiple threads writing to WebBrowser (using a function that
checks InvokedRequired , and if so, invokes itself on the WebBrowser
thread) and they are getting deadlocked.

They only deadlock when I use lock { } around the call to
WebBrowser.Writ e to ensure thread safety!

Does any one have experience with such a thing?

Zytan

Apr 2 '07 #1
18 6866
Zytan <zy**********@g mail.comwrote:
I have multiple threads writing to WebBrowser (using a function that
checks InvokedRequired , and if so, invokes itself on the WebBrowser
thread) and they are getting deadlocked.

They only deadlock when I use lock { } around the call to
WebBrowser.Writ e to ensure thread safety!

Does any one have experience with such a thing?
Hang on - do you mean you've already got a lock when you call Invoke?

Could you post a short but complete program which demonstrates the
problem?

See http://www.pobox.com/~skeet/csharp/complete.html for details of
what I mean by that.

--
Jon Skeet - <sk***@pobox.co m>
http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
If replying to the group, please do not mail me too
Apr 2 '07 #2
Zytan wrote:
I have multiple threads writing to WebBrowser (using a function that
checks InvokedRequired , and if so, invokes itself on the WebBrowser
thread) and they are getting deadlocked.

They only deadlock when I use lock { } around the call to
WebBrowser.Writ e to ensure thread safety!
Using 'lock' doesn't make sense.

WebBrowser is a WinForms control, and should only be accessed from its
UI thread. So, if you use Control.InvokeR equired, and properly use
Control.Invoke or Control.BeginIn voke to marshal your call over to the
UI control, you don't need to use 'lock', because all code that touches
the WebBrowser control is serialized on its UI thread.

Access to Control.InvokeR equired is not required to be synchronized - in
fact, it would be easy to deadlock if it and its ilk did require
synchronization . Similarly, Control.Invoke, Control.BeginIn voke etc.
don't require synchronization - check docs for Control.InvokeR equired.

-- Barry

--
http://barrkel.blogspot.com/
Apr 2 '07 #3
Zytan wrote:
I have multiple threads writing to WebBrowser (using a function that
checks InvokedRequired , and if so, invokes itself on the WebBrowser
thread) and they are getting deadlocked.

They only deadlock when I use lock { } around the call to
WebBrowser.Writ e to ensure thread safety!

Does any one have experience with such a thing?
Well if you do:

class Foo
{
//Some stuff to setup a WebBrowser control called WebBrowser

public void SomeMethod()
{
lock(WebBrowser )
{
if(InvokeRequir ed)
{
Invoke(new SomeDelegate(So meMethod));
} else {
//Do something
}
}
}
}

This will result in a deadlock when called from a thread other than the
UI thread. Instead, you should do:

class Foo
{
//Some stuff to setup a WebBrowser control called WebBrowser

public void SomeMethod()
{
if(InvokeRequir ed)
{
Invoke(new SomeDelegate(So meMethod));
} else {
lock(WebBrowser )
{
//Do something
}
}
}
}
}

If you want more than that, post some code :-)

Alun Harford
Apr 2 '07 #4
Hang on - do you mean you've already got a lock when you call Invoke?

Yes.
Could you post a short but complete program which demonstrates the
problem?
Ok, I made a small program that does nothing but start a timer that
ticks every second. It calls MyWriteLine. This calls (using
InvokeRequired + Invoke, if needed) WebBrowser.Docu ment.Write. (Well,
it makes sure the WebBrowser has a Document to write to, and if not,
navgiates to "about:blan k" first).

Then, I made a thread that I can start/stop with two buttons, this
thread does the same thing as the timer. The stop button calls
myThread.Join() ; to wait for the thread to complete.

Starting the thread is fine, they both update te WebBrowser. Stopping
the thread hangs on myThread.Join() ;

I thought this is a problem with synchronization , so I made a wrapper
to MyWriteLine, and placed a critical section lock into. Thus,
MyWriteLine is only called within a critical section. Now, the
program hangs at the lock statement when I stop the thread.

I'd post the code, but I don't have it with me at the moment. I'll
code it again, and do some more testing. I have a feeling that
replacing WebBrowser with another control solves the problem.

Zytan

Apr 3 '07 #5
WebBrowser is a WinForms control, and should only be accessed from its
UI thread. So, if you use Control.InvokeR equired, and properly use
Control.Invoke or Control.BeginIn voke to marshal your call over to the
UI control, you don't need to use 'lock', because all code that touches
the WebBrowser control is serialized on its UI thread.
Ok, I knew that Control.Invoke made the call on the same thread as
Control, but, I am unaware of what it's doing internally. I don't
know what 'marshal' actually means. So, it basically means it is
serialized on the Control's thread, meaning that all calls to
Control.Invoke are called in order, one after the other, and thus
multiple threads all calling Control.Invoke to update a single control
will be safe.
Access to Control.InvokeR equired is not required to be synchronized - in
fact, it would be easy to deadlock if it and its ilk did require
synchronization . Similarly, Control.Invoke, Control.BeginIn voke etc.
don't require synchronization - check docs for Control.InvokeR equired.
Ok, thanks, Barry

Zytan

Apr 3 '07 #6
Well if you do:
>
class Foo
{
//Some stuff to setup a WebBrowser control called WebBrowser

public void SomeMethod()
{
lock(WebBrowser )
{
if(InvokeRequir ed)
{
Invoke(new SomeDelegate(So meMethod));
} else {
//Do something
}
}
}
}
Ha ha, yes, I wasn't stupid enough to recusively attempt to enter the
same lock. The lock I have is in a wrapper around SomeMethod().
If you want more than that, post some code :-)
I will once I make my small source example again.

Zytan

Apr 3 '07 #7
Code example: Make two Buttons (btnStart, btnStop), and one
WebBroswer (webLog), and paste this into the main Form:

Thread myThread;
private volatile bool m_ThreadProcess ing = false;
private int m_count = 0;

private void ThreadFunc()
{
while (m_ThreadProces sing)
{
Thread.Sleep(40 0);
m_count++;
MyWrite(webLog, m_count + "<br>" +
Environment.New Line);
}
}

private void btnStart_Click( object sender, EventArgs e)
{
if (myThread == null)
{
myThread = new Thread(ThreadFu nc);
m_ThreadProcess ing = true;
myThread.Start( );
}
}

private void btnStop_Click(o bject sender, EventArgs e)
{
if (myThread != null)
{
m_ThreadProcess ing = false;
myThread.Join() ; // <------------- HANGS HERE!
myThread = null;
}
}

delegate void MyWrite_Delegat e(WebBrowser web, string str);
public static void MyWrite(WebBrow ser web, string str)
{
if (web.InvokeRequ ired)
{
MyWrite_Delegat e funcptr = MyWrite;
object[] args = { web, str };
web.Invoke(func ptr, args);
}
else
{
if (web.Document == null) web.Navigate("a bout:blank");
web.Document.Wr ite(str);
web.Document.Wi ndow.ScrollTo(0 , int.MaxValue); //
scroll to bottom
}
}

Note that this hangs only with this single thread accessing the
WebBrowser. Not even the main thread accesses it! (I'm preparing for
you guys to show me the obvious error I've been missing all day.)

Zytan

Apr 3 '07 #8
On Apr 3, 4:49 pm, "Zytan" <zytanlith...@g mail.comwrote:
Code example: Make two Buttons (btnStart, btnStop), and one
WebBroswer (webLog), and paste this into the main Form:
<snip>

Yes, that would hang. You're using "Invoke" from myThread - that will
block until the delegate you've passed it has been executed on the UI
thread.

Now, from the UI thread, you're calling myThread.Join - that will
block until myThread has completed.

So, how can either of them get anywhere?

Jon

Apr 3 '07 #9
Yes, that would hang. You're using "Invoke" from myThread - that will
block until the delegate you've passed it has been executed on the UI
thread.

Now, from the UI thread, you're calling myThread.Join - that will
block until myThread has completed.
Ok, it's a deadlock.

I was uncertain as what happened as a result of Invoke. Thanks to
your reply, I have a better idea. The message queue in the main
thread is processing the 'stop button clicked' message, which is
running Thread.Join, which is waiting for myThread to terminate. The
message queue is stalled (never a good idea).

myThread is upset that it doesn't own the control (as it shouldn't,
since it doesn't have a message queue to maintain it), so it tells the
GUI thread to deal with it, via Invoke. Now, my understanding is that
Invoke is *not a function pointer call* (perhaps this is why they call
them delegates, instead of function pointers?), it is a message placed
in the GUI thread. (This is why an earlier post mentioned that
Control.Invoke is serialized, meaning they are handled one at a time,
because the message queue processes one message at a time. So, if
multiple threads posted multiple messages into the queue, it still
does one at a time, and my WebBrowser doesn't need a critical
section.) But, the GUI thread has its message queue stalled.

Solution #1: Use BeginInvoke, which is a 'non blocking' call (it must
call Win32's PostMessage instead of SendMessage).

Solution #2: Don't use Thread.Join(). The examples show it, so I
used it. Often, it is unneeded.

Solution #3: Don't make the worker threads access the GUI.

Solution #4: Use BackgroundWorke r, which I presume doesn't have this
issue (I think it calls a function of yours when it is done, so you
never have to call something like BackgroundWorke r.Join, which likely
doesn't exist).

Does that all make sense?

Zytan

Apr 3 '07 #10

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

2
1802
by: Lad | last post by:
I would like to use httplib/urllib to download webpages from 3 different websites.From my script I want to open 3 webbrowser windows( 3 threads) and open in each thread( window) pages from a particular website. Is it possible to do that in Python? Thanks for help Lad
7
11217
by: Guyon Morée | last post by:
If I have multiple threads reading from the same file, would that be a problem? if yes, how would I solve it? Let's say I want to take it a step further and start writing to 1 file form multiple threads, how would I solve that? thanx,
4
5299
by: Tony Liu | last post by:
Hi, how can I create multiple new file handles of a file without having to share to file to the other processes? I have a file that will be accessed by multiple threads in my application, each time a thread try to do something with the file, the thread will create a new file handle. However, if I specify FileShare.ReadWrite, other process can also open that file. I tried FileShare.Inheritable but it doesn't work. The reason I needs to...
32
14898
by: tshad | last post by:
Can you do a search for more that one string in another string? Something like: someString.IndexOf("something1","something2","something3",0) or would you have to do something like: if ((someString.IndexOf("something1",0) >= 0) || ((someString.IndexOf("something2",0) >= 0) ||
6
2527
by: RahimAsif | last post by:
Hi guys, I would like some advice on thread programming using C#. I am writing an application that communicates with a panel over ethernet, collects data and writes it to a file. The way the data is collected is that we have different schedules (so one set of data is collected say every second, another set of data might be collected every 30 seconds, and so on).
6
5108
by: cj | last post by:
As many of you know I'm writing a TCP/IP server with multiple threads handling multiple short conversations (submit a short string, send back a sort string). Threads are created as needed to handle a new connection request and terminate after the exchange is complete. I got a new request for the program. I've been asked the the program write all the strings it receives and sends to a log file. I'm concerned about all these threads...
11
4346
by: Olie | last post by:
This post is realy to get some opinions on the best way of getting fast comunication between multiple applications. I have scowered the web for imformation on this subject and have just found conflicting views and far from ideal solutions. My application has to send small amounts of data about 50bytes to multiple client applications. The catch is that this has to happen about 1000 times a second. My first attempt was .net remotting...
2
3152
by: PAzevedo | last post by:
I have this Hashtable of Hashtables, and I'm accessing this object from multiple threads, now the Hashtable object is thread safe for reading, but not for writing, so I lock the object every time I need to write to it, but now it occurred to me that maybe I could just lock one of the Hashtables inside without locking the entire object, but then I thought maybe some thread could instruct the outside Hashtable to remove an inside Hashtable...
2
4087
by: scriptlearner | last post by:
OS: Solaris 9 Python Version: 2.4.4 I need to log certain data in a worker thread; however, I am getting an error now when I use two worker threads. I think the problem comes from the line logging.info('Thread Object (%d):(%d), Time:%s in seconds %d'% (self.no,self.duration,time.ctime(),time.time())) when multiple worker thread is trying to update the log files. What did I do wrong? Should I lock the log file before writing to
0
9639
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However, people are often confused as to whether an ONU can Work As a Router. In this blog post, we’ll explore What is ONU, What Is Router, ONU & Router’s main usage, and What is the difference between ONU and Router. Let’s take a closer look ! Part I. Meaning of...
0
9474
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can effortlessly switch the default language on Windows 10 without reinstalling. I'll walk you through it. First, let's disable language synchronization. With a Microsoft account, language settings sync across devices. To prevent any complications,...
0
10308
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers, it seems that the internal comparison operator "<=>" tries to promote arguments from unsigned to signed. This is as boiled down as I can make it. Here is my compilation command: g++-12 -std=c++20 -Wnarrowing bit_field.cpp Here is the code in...
0
10143
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven tapestry of website design and digital marketing. It's not merely about having a website; it's about crafting an immersive digital experience that captivates audiences and drives business growth. The Art of Business Website Design Your website is...
0
8964
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing, and deployment—without human intervention. Imagine an AI that can take a project description, break it down, write the code, debug it, and then launch it, all on its own.... Now, this would greatly impact the work of software developers. The idea...
1
7486
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome a new presenter, Adolph Dupré who will be discussing some powerful techniques for using class modules. He will explain when you may want to use classes instead of User Defined Types (UDT). For example, to manage the data in unbound forms. Adolph will...
0
5375
by: TSSRALBI | last post by:
Hello I'm a network technician in training and I need your help. I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs. The last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols. I succeeded, with both firewalls in the same network. But I'm wondering if it's possible to do the same thing, with 2 Pfsense firewalls...
2
3633
muto222
by: muto222 | last post by:
How can i add a mobile payment intergratation into php mysql website.
3
2870
bsmnconsultancy
by: bsmnconsultancy | last post by:
In today's digital era, a well-designed website is crucial for businesses looking to succeed. Whether you're a small business owner or a large corporation in Toronto, having a strong online presence can significantly impact your brand's success. BSMN Consultancy, a leader in Website Development in Toronto offers valuable insights into creating effective websites that not only look great but also perform exceptionally well. In this comprehensive...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.