Unhandled exception of type 'System.ApplicationException' occurred in System.Drawing.dll
Asked Answered
T

4

20

I have a winforms app. In development mode, when debugging from Visual Studio .NET 2003 (Yes, I know it's old, but this is a legacy project), I get this error when I try to open a new form. In order to open a new form I get an instance of the form and then I call ShowDialog() method, for example:

frmTest test = new frmTest(here my parameters);
test.ShowDialog();

If I press F11 (step into) when debugging it is not crashing, but If in the line where I instantiate the form I press F10 to go into next line, that is, test.ShowDialog(), then it crashes showing this error.

The complete message error is:

"An unhandled exception of type 'System.ApplicationException' occurred in System.drawing.dll. Additional Information: An attempt was made to free a mutual exclusion that does not belong to the process"

I have translated last part: Additional information ... since it was appearing in spanish.

The form that I am instantiating with parameters, its constructor, consists on initialize some variables for example:

public frmTest(string param1, string param2)
{
   InitializeComponent();

   this.param1 = param1;
   this.param2 = param2;
}

private void frmTest_Load(object sender, EventArgs e)
{
    // here I call a remote webservice asynchronously.
}

Also my form "frmTest" has four pictureboxes, a label, and a button. Three of the pictureboxes contain a png image (it is assigned on design time through Image property), the last picturebox contains a animated gif, also loaded in design time through Image property. Maybe the error occurs due to these images?

Tuberculosis answered 5/7, 2017 at 21:19 Comment(19)
You can try removing image properties of all the pictureboxes and run the program. If it runs good then start setting property of one picturebox at a time and run the program to determine which picturebox is the cause of the issue.Platen
I think the best option would be to port it to the latest framework. If project is big, it could take a while but if it's important to you then why not?Trample
The old version might contain some bugs that were addressed in newer versions.Trample
I used to port project from 1999, it was C++ project though. It was a huge project with ~~20 000 lines or more.Trample
Also may be worth tracing it further via obtaining the full stack trace and using a decompiling tool like the free dotPeek by JetBrains to look inside the source code of the .net 1.1 dll if you can't port as @III advised.Felicitation
That is a pretty wonky exception. But who knows, ApplicationException was one of the .NET 1.0 design mistakes. This question needs a better, non-translated exception message and a stack trace. But it is probably a thread bug, .NET 1.x made it very easy to get that wrong without a decent diagnostic. Use the debugger's Debug > Windows > Threads window to have a look at what is going on.Illbehaved
@DimitarNikovski you have a guide for that? A link or anything? I'm interested tooYonina
I think you should show us what's happening in the form constructor, maybe we can help you moreYonina
I think this problem is not form your contractor. It can be happen form your page load. Place a debug point in page load in frmTest and press F10 . carefully debug and find out where your application .Vole
Maybe the images are loaded asynchronously and the form is not yet ready to be called (ShowDialog method). Can't you create an event / delegate on your form that could be fired after Load / Render. The event would call the "test.ShowDialog(); code. Hope this helpsSorehead
I cant see how this can be properly answered without the details of // here I call a remote webservice asynchronously. And the stack traceGowrie
I agree with @HansPassant... this sounds like a threading issue. See this article: How to: Make Thread-Safe Calls to Windows Forms ControlsRussian
Here's a snippet from Programming Microsoft Visual Basic .NET Version 2003 (Part IV, Chapter 19, page 652) that is specific to .NET 1.1.Russian
Do you static Main method have the [STAThread] attribute. Seems like a threading issue.Starvation
Try stack trace to determine the method which is causing this issue. I think this issue is related to SizeChanged event. Are you trying to resize picture box or something programmatically at the time of form load?Geanine
Looks like a thread safe issue. Your async calls are trying to add the pictures to the place holder. The place holder is running under the main thread. Better use delegates to add the picturesInterpolation
The code samples are the basic setup. Best to show the interesting code where the bug might be. And indeed, good to comment out and stp by step turn on parts.Circumstance
Download .NET Reflector and debug System.drawing.dllSahaptin
Agreed, you should port the project to a more modern framework. Just because the project hasn't been properly maintained doesn't mean you shouldn't start now.Blowzed
D
1

TL;DR: Your web request handler will execute on a different thread. Ensure you don't do anything that isn't thread-safe in that handler. You can use Invoke to dispatch your callback handler's code to the main thread.

Diagnosis

The problem here is almost certainly hiding in the missing details of your asynchronous call.

// here I call a remote webservice asynchronously.

Asynchronously is a little bit too vague to be sure what exactly is happening, but there's a very good chance that the asynchronous mechanism that you are using has executed its callback on a different thread from the main UI thread.

Overview

This is common in the .NET model. Asynchronous I/O in the .NET model makes use of threads in a thread pool to handle I/O via I/O Completion Ports (IOCP). It means that when a call like Socket.BeginReceive or WebRequest.BeginGetResponse (or any .NET asynchronous web request that uses similar technology internally) completes, the callback will execute on a thread in the thread pool, not the main thread. This may be surprising to you, since you didn't actively create another thread; you just participated in making asynchronous calls.

You must be very careful about what you do in the callback from your web request as many user-interface / Windows Forms operations are not permitted on any thread other than the main UI thread. Similarly, it may not be the UI itself that is causing you problems, you may have just accessed some resource or object that is not thread safe. Many seemingly innocuous things can cause a crash or exception if you're not careful with multithreading.

To resolve the issue:

If in doubt, in your callback, as early as you can, dispatch (a.k.a. Invoke) the code in your handler so that it runs on the main thread.

A common pattern for doing this would be something like what follows below.

Suppose you have made a call like this:

IAsyncResult result = (IAsyncResult myHttpWebRequest.BeginGetResponse(
    new AsyncCallback(RespoCallback), myRequestState);

The handler might be set up like this:

private static void RespCallback(IAsyncResult asynchronousResult)
{  
    // THIS IS NOT GOING TO WORK BECAUSE WE ARE ON THE WRONG THREAD.  e.g.:
    this.label1.Text = "OK";  // BOOM!  :(
}

Instead, dispatch any necessary processing back to the main thread.

private static void RespCallback(IAsyncResult asynchronousResult)
{  
    this.Invoke((MethodInvoker) delegate { 
       // This block of code will run on the main thread.
       // It is safe to do UI things now.  e.g.:
       this.label1.Text = "OK";  // HOORAY!  :)
    });
}

I'm not advising this as a general best practice. I'm not saying to just immediately dispatch all your handlers back to the main thread. One size does not fit all. You should really look at the specific details of what you do in your handler and ensure you aren't doing thread-specific things. But I am saying that in the absence of any kind of explanation from you about what your asynchronous handlers are doing, the problem would likely be solved by invoking the handler code on the main thread.

Note: Of course, to fix your problem with this technique, it requires that your main thread is running. If you blocked your main thread with a (bad) technique like the one in this example then you'll have to redesign part of your app. Here's an example of something that would require a bigger rework:

// Start the asynchronous request.
IAsyncResult result=
  (IAsyncResult) myHttpWebRequest.BeginGetResponse(new AsyncCallback(RespCallback),myRequestState);

// this line implements the timeout, if there is a timeout, the callback fires and the request becomes aborted
ThreadPool.RegisterWaitForSingleObject (result.AsyncWaitHandle, new WaitOrTimerCallback(TimeoutCallback), myHttpWebRequest, DefaultTimeout, true);

// The response came in the allowed time. The work processing will happen in the 
// callback function.
allDone.WaitOne(); // *** DANGER:  This blocks the main thread, the IO thread
                   // won't be able to dispatch any work to it via `invoke`

Notice the WaitOne call? That blocks execution of the executing thread. If this code executes on the main thread, then the main thread will be blocked until the WebRequest completes. You'll have to redesign so that either you don't block the main thread (my recommendation) or that you more closely examine your callback handler to see why what it's doing is conflicting with other threads.

Doubletalk answered 7/2, 2020 at 17:1 Comment(0)
N
0

Application exceptions are not thrown by the framework itself: what-is-applicationexception-for-in-net; Problem should be in the code you have not the framework. Also be sure to check "InvokeRequired" property before taking the action and if it is, run the method using "Invoke" method. Can check c-sharp-cross-thread-call-problem for that.

Nigeria answered 13/5, 2018 at 17:8 Comment(0)
L
0

May be the async call is trying to access UI thread.

Make sure you are not using control properties like TextBox.Text. If so, you just have to pass its value to the async call, or store it in a class variable before the call.

Also, inside an async call you can't assign values to that properties. Use Invoke() instead.

Lacteous answered 17/12, 2018 at 13:43 Comment(0)
A
0

Try to add an exception breakpoint and VS will stop at the instruction causing the exception. The actual stacktrace may help.

Have You tried to close VS's local variable watch window? Maybe it is evaluating something for You on UI components where the accessing thread should be equal to owner thread of UI component!

Adigun answered 1/3, 2019 at 14:38 Comment(1)
Why -1? Both are valid debug steps! Many doesnt know about exception breakpoints. Many dont take care about how the actual values become visible in local variable watch window. During VS actually executes parts of our code to show values may cause unpredictable missfunction; especially in winforms controls, where the hwnd creator thread really important.Adigun

© 2022 - 2024 — McMap. All rights reserved.