[Mono-list] Threading + Exception Handling (2 Questions)

Jonathan Pryor jonpryor@vt.edu
20 Mar 2003 09:47:09 -0500


--=-z3WDgyELhBczgjoKeVBL
Content-Type: text/plain
Content-Transfer-Encoding: 7bit

Oops.  Forgot to attach the UnhandledException sample.

 - Jon

On Thu, 2003-03-20 at 09:45, Jonathan Pryor wrote:
> It sounds like you want to have an exception generated in one thread
> appear in another.  I don't think that's possible.  Exceptions are
> relative to the thread they're generated from, and deal exclusively with
> the thread of that stack.
> 
> However, there is a workaround, if I'm understanding you correctly.  You
> could hook up the AppDomain.UnhandledException event to your first
> thread, which would let you know if an exception was thrown from some
> thread in your application and not caught.
> 
> In theory, you could use the UnhandledExceptionEventArgs information to
> determine the type of the thrown exception, to ensure that you're
> trapping the right errors.  Alas, this information appears to be null
> for my build of mono (see attached sample program), but that might be
> fixed by now.  Anyone else know for sure?
> 
> Regardless, your UnhandledException handler can set a variable which the
> main thread checks.  If the variable is set, the main thread would throw
> an exception, simulating the appearance of the thread moving from one
> thread to another.
> 
> As for Thread.Abort, it should work as you expect.  Thread.Abort
> generates an exception in the specified thread, not the calling thread
> (unless they're the same), and that exception will have no effect on the
> calling thread.  So Thread.Abort followed by a throw should work.
> 
> There is one problem, though.  Thread.Abort isn't implemented for mono
> under Windows (it's a pthread under Windows problem; check the
> archives), so this may not be an acceptable solution for you.
> 
>  - Jon
> 
> On Thu, 2003-03-20 at 08:51, Timothy Parez wrote:
> > Hello,
> >  
> > I have class which creates another thread
> > now that other tread can throw a custom error, but
> > when this error is thrown I want the main thread of the class library
> > to receive this exception so that the client application which uses my
> > library get's this error and all execution of other code in my class
> > library is stopped.
> >  
> >  //Code executed by the main thread:
> >   protected byte[] Query(byte[] sendData)
> >   {
> >    //Set all values
> >    data = sendData;
> >  
> >    queryThread = new Thread(new ThreadStart(ExecuteQuery));
> >             
> >    //Start the query
> >    queryThread.Start();
> >    
> >    //Wait for the query to exit
> >    if (!queryThread.Join(timeout * 1000))
> >    {
> >     queryThread.Abort();
> >     throw new Exceptions.QueryTimeoutException("Query Timeout: " +
> > timeout.ToString() + " seconds");
> >    }
> >    
> >    //Return the response, which is now saved in the local variable
> >    return queryResponse;
> >   }
> >  
> > // Code executed by the queryThread
> >  private void ExecuteQuery()
> >   {
> >    UdpClient client = new UdpClient();
> >    //Connect to the server and send the query data
> >    try
> >    {
> >     client.Connect(ip,port);
> >     client.Send(data,data.Length);
> >    }
> >    catch (Exception e)
> >    {
> >     client.Close();
> >     throw new Exceptions.InvalidHostException("Unknown host: " +
> > ip,e);
> >    }
> >  
> >    //Listen for a response - This is the client side
> >    IPEndPoint serverIPEndPoint = new IPEndPoint(IPAddress.Any,0);
> >    
> >    //Receive the response
> >    try
> >    {
> >     queryResponse = client.Receive(ref serverIPEndPoint);
> >    }
> >    catch (Exception e)
> >    {
> >     throw new Exceptions.ConnectionRefusedException("The connection
> > was refused by the remote host: " + ip + ":" + port.ToString(),e);
> >    }
> >    finally
> >    {
> >     client.Close();
> >    }
> >   }
> >  
> > As you can see the ExecuteQuery() function can throw the
> > Exceptions.ConnectionRefusedException,
> > but my main thread never receives this error, so the execution of the
> > code in the main thread does not stop.
> > How can I fix this.
> >  
> > I also have a second question: 
> >     queryThread.Abort();
> >     throw new Exceptions.QueryTimeoutException("Query Timeout: " +
> > timeout.ToString() + " seconds");
> > I abort the second thread, will the QueryTimeoutException still be
> > thrown ? (I hope so), or will the .Abort() cause an error
> > which will prevent from the QueryTimeoutException ever happening, in
> > that case how do I abort the second query and still throw the
> > QueryTimeoutException ?
> >  
> >  
> > Thnx.
> > TP.
> 
> _______________________________________________
> Mono-list maillist  -  Mono-list@lists.ximian.com
> http://lists.ximian.com/mailman/listinfo/mono-list

--=-z3WDgyELhBczgjoKeVBL
Content-Disposition: attachment; filename=threading.cs
Content-Type: text/plain; name=threading.cs; charset=UTF-8
Content-Transfer-Encoding: 7bit

// What happens when a thread throws an uncaught exception?

using System;
using System.Threading;

class R {
  private static void Worker () {
    Console.WriteLine ("Worker Thread: Working...");
    Thread.Sleep (500);
    Console.WriteLine ("Worker Thread: Problem.");
    throw new Exception ("Worker Thread Problem");
  }

  public static void Main () {
    Thread t = new Thread (new ThreadStart (Worker));
    Console.WriteLine ("Main: Starting Worker");
    AppDomain.CurrentDomain.UnhandledException += 
      new UnhandledExceptionEventHandler (OnUnhandledException);
    t.Start ();
    t.Join ();
    Console.WriteLine ("Main: Finished");
  }

  private static void OnUnhandledException (object sender, UnhandledExceptionEventArgs e)
  {
    Console.WriteLine ("Unhandled Exception:");
    Console.WriteLine ("  sender=" + sender);
    Console.WriteLine ("  e=" + e);
    if (e != null) {
      Console.WriteLine ("  e: " + e);
      Console.WriteLine ("  Exception: " + e.ExceptionObject);
      Console.WriteLine ("  IsTerminating: " + e.IsTerminating);
    }
    else
      Console.WriteLine ("  ** UnhandledExceptionEventArgs is null?!");

    Console.WriteLine ("Generating New Exception");
    throw new Exception ("In the right thread?");
  }
}


--=-z3WDgyELhBczgjoKeVBL--