List Info

Thread: Threading




Threading
user name
2006-11-15 15:58:31
> > There's a whole lot of ways to write code that
'could deadlock'
> > because someone else does something stupid or
malicious 
>
> I fail to see how someone using an interface you've
made
> public "stupid or
> malicious".

* In response to me firing an event defined on my public
interface, to which
my client has subscribed, said client's callback displays a
modal dialog box
requesting user input.  Said user is getting coffee at the
time.

* They queue up more than 24 requests to the thread pool
that call methods
which hang out waiting for stuff to get done.  This doesn't
even involve
touching my interface, but if my component relies on threads
from the thread
pool, I'm now in trouble.

* The client opens a named mutex my component uses
internally for
cross-process synchronization, and fiddles with it.

* The client starts a thread that proceeds to use inordinate
amounts of CPU
time.  At best, this slows down the ability/willingness of
the thread pool
manager to dispatch pooled threads to handle pending
requests.  At worst,
the CPU is pegged to the degree that the thread pool manager
refuses to
dispatch further work requests until the cpu settles down. 
Again, the
client isn't doing anything to my interface directly, but if
my component
relies on the TP to get my job done, I'm in trouble.

* Even though I implement IDispose, the client didn't
leverage the using
construct, nor did they use try/finally on their own to
ensure that they
called my Dispose method.  And they kept a reference to my
public interface
stored in a static field (directly or indirectly), so my
finalizer (if I
even have one) can't kick in an clean up the mess.  They've
only used my
public interfaces, but their use of my public interfaces
isn't playing very
nicely.

My point was only that I frequently talk to people who think
that (1) code
that uses lock(this) is intrinsically prone to deadlock for
some magical
reason and (2) that as long as they avoid lock(this), their
apps are somehow
magically free from
deadlock/race/starvation/indefinite-postponement/whatever
worries.  While
switching from lock(this) to
lock(somePrivateObjectReference) may be well
advised, that's only the tip of the iceberg when it comes to
program
correctness in the face of multithreaded execution.

> Mind
> you, the following isn't all that much work:
>
>     if(!Monitor.TryEnter(obj, lockTimeout))
>     {
>         throw new MyEnterTimeoutException("Timout
waiting for
> Enter.");
>     }
>     try
>     {
>         // TODO: something
>     }
>     finally
>     {
>         Monitor.Exit(obj);
>     }
>

Neither is

DisposableWidget dw = new DisposableWidget();
try
{
  // do something
}
finally
{
  ((IDisposable)dw).Dispose();
}

But they gave us 'using' nonetheless 

Neither the 'using' nor the 'lock' construct is required to
get the job
done.  They're both just conveniences.  The difference is
that the 'using'
construct (as a convenience) makes a very common programming
pattern doable
w/less typing.  But the 'lock' construct only goes half way
(IMO) towards
providing the convenience it targets.

> Given the current state of
> Visual C# I think that's (and should be) very low on
their list.

No argument there.  I never said it was something that kept
me up at night
  Just
an annoyance.

-Mike
Bear Canyon Consulting LLC
http://www.bearcanyon.com
http://www.pluralsigh
t.com/mike

===================================
This list is hosted by DevelopMentorŪ  http://www.develop.com

View archives and manage your subscription(s) at http://discuss.develop.com

[1]

about | contact  Other archives ( Real Estate discussion Medical topics )