Question

I have a windows form app that normally runs without a problem, but every so often (<1% of the time) I see an error like this:

Visual Styles-related operation resulted in an error because no visual style is currently active. at System.Windows.Forms.VisualStyles.VisualStyleRenderer.get_Handle() at System.Windows.Forms.VisualStyles.VisualStyleRenderer.DrawBackground(IDeviceContext dc, Rectangle bounds, Rectangle clipRectangle) at System.Windows.Forms.GroupBoxRenderer.DrawThemedGroupBoxWithText(Graphics g, Rectangle bounds, String groupBoxText, Font font, Color textColor, TextFormatFlags flags, GroupBoxState state) at System.Windows.Forms.GroupBoxRenderer.DrawGroupBox(Graphics g, Rectangle bounds, String groupBoxText, Font font, TextFormatFlags flags, GroupBoxState state) at System.Windows.Forms.GroupBox.OnPaint(PaintEventArgs e) at System.Windows.Forms.Control.PaintWithErrorHandling(PaintEventArgs e, Int16 layer) at System.Windows.Forms.Control.WmPaint(Message& m) at System.Windows.Forms.Control.WndProc(Message& m) at System.Windows.Forms.GroupBox.WndProc(Message& m) at System.Windows.Forms.Control.ControlNativeWindow.OnMessage(Message& m) at System.Windows.Forms.Control.ControlNativeWindow.WndProc(Message& m) at System.Windows.Forms.NativeWindow.Callback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)

I've dealt with Visual Styles errors before, so have ensured that the machines using the app have compatible desktop themes. What's strange with this error is that the program starts and runs happily for some time (eg. 30 mins) before this exception is thrown. I don't understand how the state of the Visual Style could change during execution.

The application is made up of a Console app that launches a Windows Form, which uses Awesomium to load web pages and respond to javascript callbacks.

I'm catching the error with a ThreadExceptionEventHandler listening to Application.ThreadException on the Console app. It occurred to me that perhaps the windows form had been disposed when the error occurs, but I don't think this is the case because when I log the error I can access instance members of the Form eg. myForm.ToString()

Since none of my code is featured in the stack trace, I'm not sure what else would help describing this error. Has anyone seen anything like this before?

Was it helpful?

Solution

Hans Passant was correct, this was a GDI handle leak. I couldn't reproduce it on my development environment, so needed to add some logging to my server. In case it helps anyone else, here is how I got the information I needed by invoking the GetGuiResources function.

    [DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]
    static extern int GetGuiResources(IntPtr hProcess, int uiFlags);

and using it to obtain handle counts:

    var p = Process.GetCurrentProcess();
    kernel = p.HandleCount;

    gdiObjects = GetGuiResources(p.Handle, 0);
    userObjects = GetGuiResources(p.Handle, 1);

    gdiObjectsPeak = GetGuiResources(p.Handle, 2);
    userObjectsPeak = GetGuiResources(p.Handle, 4);

Once that was in place, I saw that GDI objects were at the 10,000 ceiling when the crash occurred.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top