0

This is somewhat of a follow up to a previous question I had asked, although I am now able to provide a lot more code to improve my question and further show my trouble with this area.

I have three routines here. Two of these routines work together - and if successful, will load an assembly into memory using System.Reflection. I would like for these routines to return an error if the file did not load properly into memory, but for some reason these try-catch statements simply will not work the way I would like.

Note: For this routine to work the file must be a .net assembly. If, for example, the file was programmed in VB6 an error will be thrown. This is the error I am trying to have returned to me.

private void ExecuteDataIntoMemory(string filePath)
{

    byte[] bytes = File.ReadAllBytes(filePath);

    try
    {
        ExecFile(bytes);
        MessageBox.Show("successfully loaded this file into memory");
    }

    catch
    {
        MessageBox.Show("Could not load this file into memory");
    }

}

private static void ExecFile(byte[] data)
{
    try
    {
        //Work around for "SetCompatibleTextRenderingDefault"  
        System.Threading.Thread T = new System.Threading.Thread(ExecFile);
        //Set STA to support drag/drop and dialogs?
        T.SetApartmentState(System.Threading.ApartmentState.STA);
        T.Start(data);
    }

    catch
    {
        MessageBox.Show("caught some error ...");
    }

}
private static void ExecFile(object o)
{

        System.Reflection.MethodInfo T = System.Reflection.Assembly.Load((byte[])o).EntryPoint;
        if (T.GetParameters().Length == 1)
            T.Invoke(null, new object[] { new string[] { } });
        else
            T.Invoke(null, null);


}

I can clarify more if necessary but I'm not sure what other information to include at this point.

4

5 に答える 5

1

Use the "throw" statement within the catch statement of ExecFile to raise the same "exception" (or error) caught in ExecFile. For example:

 catch {
      throw;
 }

I think I figured out the problem though. ExecFile(byte[]) starts the thread and returns immediately without waiting for the thread to exit. To allow that method to wait for the thread to exit, add:

 T.Join();

right after starting the thread. (To avoid possible ambiguity, however, you should rename ExecFile(object). I'm also not sure whether ExecFile(byte[]) will catch the exception from ExecFile(object).)

于 2011-07-10T14:38:39.390 に答える
0

If you catch the Exception in ExecFile(byte[] data) it won't be propagated in your parent method (ExecuteDataIntoMemory(string filePath)), and then won't be catched again

If you really need to catch your exception twice, rewrite your child method this way

private static void ExecFile(byte[] data)
{
    try
    {
        //Work around for "SetCompatibleTextRenderingDefault"  
        System.Threading.Thread T = new System.Threading.Thread(ExecFile);
        //Set STA to support drag/drop and dialogs?
        T.SetApartmentState(System.Threading.ApartmentState.STA);
        T.Start(data);
    }

    catch (Exception ex)
    {
        MessageBox.Show("caught some error ...");
        throw ex;
    }
}

If not, simply not try..catch errors in this method, and the Exception will be propagated..

于 2011-07-10T14:48:32.333 に答える
0

If I understand you well, You want the ExecuteDataIntoMemory to be evaluated only if the ExecFile succeed.

1- You are running a new thread to execute the ExecFile method which will be executed in a different thread. So first at the try block in ExecFile(byte[] data) run the ExecFile(data) without a new Thread because you want to wait for it any way:

try
{
    ExecFile(data);
}

2- Notice that you have two method with the same name 'ExecFile(byte[] data)' and ExecFile(object o) the data you are passing is from type byte[] so it will be infinite recursive or till stack over flow exception is raised. So you should cast data to object and then pass it to the method i.e:

try
{
    ExecFile((object)data);
}

3- At the catch block of the ExecFile(byte[] data) method rethrow the exception so it can be handled from the caller method two i.e:

try
{
    ExecFile((object)data);
}
catch
{
    MessageBox.Show("caught some error ...");
    throw;
}
于 2011-07-10T15:00:42.313 に答える
0

Just look in the callstack which method call the ExecuteDataIntoMemory method again?

if you are using Visual studio IDE put a breakpoint at the messagebox:

   MessageBox.Show("successfully loaded this file into memory");

then simple go to the view menu, from there find the callstack window to display and look at the callstack (show external code to the callstack)

maybe this could help.

于 2011-07-10T15:03:22.633 に答える
0
  1. The rough way (I think), but should work in your case, is subscribe to

    AppDomain.CurrentDomain.UnhandledException

event riased, which will get the exception raised directly from the function ExecFile(object o);

  1. Or create a state machine which is set to NEGATIVE state in case of any exception in ExecFile(object o); method.

  2. Or just do not do it in multithreading :)

于 2011-07-10T15:08:41.963 に答える