02 September 2008
Using Themes in ASP.NET loads System.Drawing namespace
Using the System.Drawing namespace is strongly discouraged in ASP.NET as it leads to a lot of performance/runtime problems.
Recently one of our customers reported an issue where we were getting GDI+ errors in a normal ASP.NET application.
Exception type: System.Runtime.InteropServices.ExternalException
Message: GDI+ is not properly initialized (internal GDI+ error).
InnerException: <none>
StackTrace (generated):
SP IP Function
048CE1A0 7AE65963 System.Drawing.Bitmap..ctor(System.IO.Stream)
048CE1C8 7AE31EAE System.Drawing.ToolboxBitmapAttribute..cctor()
StackTraceString: <none>
HResult: 80004005
The GDI+ calls were not something intentional, none of the application code contained any reference to the System.Drawing namespace. But the namespace was getting loaded in the process as a result of applying a Theme to the page.
System.Reflection.CustomAttribute._CreateCaObject(Void*, Void*, Byte**, Byte*, Int32*)
System.Reflection.CustomAttribute.CreateCaObject(System.Reflection.Module, System.RuntimeMethodHandle, IntPtr ByRef, IntPtr, Int32 ByRef)
System.Reflection.CustomAttribute.GetCustomAttributes(System.Reflection.Module, Int32, Int32, System.RuntimeType, Boolean, System.Collections.IList)
System.Reflection.CustomAttribute.GetCustomAttributes(System.RuntimeType, System.RuntimeType, Boolean)
System.RuntimeType.GetCustomAttributes(System.Type, Boolean)
System.ComponentModel.ReflectTypeDescriptionProvider.ReflectGetAttributes(System.Type)
System.ComponentModel.ReflectTypeDescriptionProvider+ReflectedTypeData.GetAttributes()
System.ComponentModel.TypeDescriptor+TypeDescriptionNode+DefaultTypeDescriptor.System.ComponentModel.ICustomTypeDescriptor.GetAttributes()
System.ComponentModel.TypeDescriptor.GetAttributes(System.Type)
System.Web.UI.ThemeableAttribute.IsTypeThemeable(System.Type)
System.Web.UI.Control.ApplySkin(System.Web.UI.Page)
System.Web.UI.Control.InitRecursive(System.Web.UI.Control)
System.Web.UI.Control.InitRecursive(System.Web.UI.Control)
System.Web.UI.Control.InitRecursive(System.Web.UI.Control)
System.Web.UI.Control.InitRecursive(System.Web.UI.Control)
System.Web.UI.Page.ProcessRequestMain(Boolean, Boolean)
When an ASPX page has to load a Theme we loop through all Controls/Types on the page and check if we can apply the theme to it(IsTypeThemeable). This involves generating a list of attributes for the Control/Type. Its a simple call to TypeDescriptor.GetAttributes method which results in each attribute being instantiated. And this is where the trouble starts.
Controls have a ToolboxBitmap attribute which is a picture representation of the control. Its a bitmap and this results in the unintentional loading of the System.Drawing namespace in the worker process.
Currently a fix is being worked on and should be released soon.
Comment Notification
If you would like to receive an email when updates are made to this post, please register here
Subscribe to this post's comments using
Comment Policy: No HTML allowed. URIs and line breaks are converted automatically. Your e–mail address will not show up on any public page.