none
.ShowDialog() Crashes. RRS feed

  • Question

  • Hi,

    I found some issues with the code i have written.

    When i use the function SHGetFileInfo() from Shell32 i am getting ReportAVOnCOMRelease exception.

    Here is the code :

                Shell32.SHFILEINFO shfi = new Shell32.SHFILEINFO();
                uint flags = Shell32.SHGFI_ICON | Shell32.SHGFI_USEFILEATTRIBUTES;

                flags += Shell32.SHGFI_SMALLICON;

                Shell32.SHGetFileInfo(FileName,
                    Shell32.FILE_ATTRIBUTE_NORMAL,
                    ref shfi,
                    (uint)System.Runtime.InteropServices.Marshal.SizeOf(shfi),
                    flags);

    Same exception i am getting in this.ShowDialog();

     

    I think this exception is results to crash.

     Can you please suggest why this exception coming and how to fix it.

    I searched on the net and found that this exception is because of release of COM objects.

    Regards

    PraveenM

     

    Wednesday, June 8, 2011 6:16 AM

Answers

  • I'm still not following all of your example. You said that the icon is being created on the fly, but what you showed in your code was just creating a file, not actually an icon. What happens if you browse out to the file you are creating on-the-fly? Can you see the icon in Windows Explorer? More importantly, can you see the icon at different sizes (change the folder view to Details, Small, Medium, Large, Extra Large, etc). Does the icon show up for all of the different sizes?

    Here's the other real source of confusion...the error message you're getting sounds completely unrelated to the code we're looking at. The error message is related to COM objects - basically, the COM object reference count is corrupt. The code you're showing so far just relates to Windows API calls through P/Invoke. P/Invoke does keep a file handle reference count, but to my knowledge it could only get screwed up if you explicitly call FreeLibrary or something similar.

    • Marked as answer by Paul Zhou Monday, June 20, 2011 3:33 AM
    Wednesday, June 15, 2011 9:51 PM
  •  

     
    int nRefCount = -1;
    do
    {
                if (Submit != null && Submit.Target != null)
              {
                  nRefCount = System.Runtime.InteropServices.Marshal.ReleaseComObject(Submit.Target);
              }
    }
    while (nRefCount>0);

    Hi All ,

    I have found fix for random crashes when your application is working on C++,C#,COM 3 technology platform.

    When C++ or C# starts communicating with each other using COM, COM creates some RCW,CW objects for that.

    The deletion/life sycle of these objects is very sensitive hence we need to take care of that.

    So we have added above written code in C# at every close window call.

    this helps to clean the RCW objects immediately after closing the window.

    Try this whenever you face ReportAVOnCOMRelease() exception.

     

     

    • Marked as answer by Praveen_More Thursday, October 13, 2011 6:24 AM
    Thursday, October 13, 2011 6:23 AM

All replies

  •  

    Hi PraveenM,

     

    Welcome to the MSDN forum.

     

    According to your description, it seems that you are not ensure that which code crash the application.

     

    I suggest you use SOS Debugging Extension to debug your code and find the root cause.

     

    Have a nice day!


    Paul Zhou [MSFT]
    MSDN Community Support | Feedback to us
    Get or Request Code Sample from Microsoft
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

    Friday, June 10, 2011 6:45 AM
  • Can you please explain in more detail.

    Friday, June 10, 2011 12:20 PM
  • There are a few possible issues that I see at a quick glance:

    First, why are you using FILE_ATTRIBUTE_NORMAL when you're trying to get the icon for a file? Does it really matter what the file attributes are if you're just getting the icons? What happens if you get rid of FILE_ATTRIBUTE_NORMAL and SHGFI_USE_FILE_ATTRIBUTES (from flags)?

    As a side note, though I seriously doubt it's the issue, as a general practice you should avoid confusing the '+' operator with the '|' operator. One is bitwise or, one is a mathematical addition. This line:

    flags += Shell32.SHGFI_SMALLICON;

    Should be:

    flags |= Shell32.SHGFI_SMALLICON;

     

    Also, is it possible that the icon file is just corrupted? Are you able to get the large icon, or any other icons?

    How is the ShowDialog error related? Does your dialog use the same icon, or do you execute some logic when the dialog is shown?

    Friday, June 10, 2011 3:05 PM
  • Hi,

    Icon file is created on temporarily basis.

    string dummyFileName = Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData) + "/CD1A4877-FC4C-4a32-8E4C-3BCF182DAD65" + sfileExtension; 
    FileInfo MyFile = new FileInfo(dummyFileName);
    if (!MyFile.Exists)
    {MyFile.Create();}

    For large icons i didnot tried.

    Yes the dialog uses the same icons.

     

    Monday, June 13, 2011 5:20 AM
  • Hi I tried with your suggestions.

    1. Removing SHGFI_USE_FILE_ATTRIBUTES:

    Result : Exception is still coming.SHGFI_USE_FILE_ATTRIBUTES  attribute used generally when dnt want to depend on file name.

    and if you dnt add this attribute then   FILE_ATTRIBUTE_NORMAL is neglected.

    2. adding flags |= Shell32.SHGFI_SMALLICON and find usefull.but exception is still coming.

    Here is the code:
            public class Shell32
            {
                public const int MAX_PATH = 256;

                public const uint FILE_ATTRIBUTE_NORMAL = 0x00000080;

                public const uint SHGFI_ICON = 0x000000100;
                public const uint SHGFI_USEFILEATTRIBUTES = 0x000000010;

                public const uint SHGFI_SMALLICON = 0x000000001;

                [StructLayout(LayoutKind.Sequential)]
                public struct SHFILEINFO
                {
                    public const int NAMESIZE = 80;
                    public IntPtr hIcon;
                    public int iIcon;
                    public uint dwAttributes;
                    [MarshalAs(UnmanagedType.ByValTStr, SizeConst = MAX_PATH)]
                    public string szDisplayName;
                    [MarshalAs(UnmanagedType.ByValTStr, SizeConst = NAMESIZE)]
                    public string szTypeName;               
                };

                [DllImport("Shell32.dll")]
                public static extern IntPtr SHGetFileInfo(
                    string pszPath,
                    uint dwFileAttributes,
                    ref SHFILEINFO psfi,
                    uint cbFileInfo,
                    uint uFlags
                    );
            }

            public static Icon IconFromFileExtension(string sfileExtension)
            {
                //TODO : Create it in user temp directory
                System.Drawing.Icon icon=null;
                try
                {
                string dummyFileName = Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData) + "\\CD1" + sfileExtension;

                FileInfo MyFile = new FileInfo(dummyFileName);

                if (!MyFile.Exists)
                {
                    MyFile.Create();
                }

                Shell32.SHFILEINFO shfi = new Shell32.SHFILEINFO();
                uint flags = Shell32.SHGFI_ICON /*| Shell32.SHGFI_USEFILEATTRIBUTES*/;

                flags |= Shell32.SHGFI_SMALLICON;              

                    Shell32.SHGetFileInfo(dummyFileName,
                    Shell32.FILE_ATTRIBUTE_NORMAL,
                    ref shfi,
                    (uint)Marshal.SizeOf(shfi),
                    flags);

                    icon = (System.Drawing.Icon)System.Drawing.Icon.FromHandle(shfi.hIcon).Clone();
               
                DestroyIcon(shfi.hIcon);  // Cleanup
                }
                catch (Exception ex)
                {
                }

                return icon;
            }

     

    Monday, June 13, 2011 7:43 AM
  • Hi,

    please update me something?

    Wednesday, June 15, 2011 10:50 AM
  • I'm still not following all of your example. You said that the icon is being created on the fly, but what you showed in your code was just creating a file, not actually an icon. What happens if you browse out to the file you are creating on-the-fly? Can you see the icon in Windows Explorer? More importantly, can you see the icon at different sizes (change the folder view to Details, Small, Medium, Large, Extra Large, etc). Does the icon show up for all of the different sizes?

    Here's the other real source of confusion...the error message you're getting sounds completely unrelated to the code we're looking at. The error message is related to COM objects - basically, the COM object reference count is corrupt. The code you're showing so far just relates to Windows API calls through P/Invoke. P/Invoke does keep a file handle reference count, but to my knowledge it could only get screwed up if you explicitly call FreeLibrary or something similar.

    • Marked as answer by Paul Zhou Monday, June 20, 2011 3:33 AM
    Wednesday, June 15, 2011 9:51 PM
  •  

     
    int nRefCount = -1;
    do
    {
                if (Submit != null && Submit.Target != null)
              {
                  nRefCount = System.Runtime.InteropServices.Marshal.ReleaseComObject(Submit.Target);
              }
    }
    while (nRefCount>0);

    Hi All ,

    I have found fix for random crashes when your application is working on C++,C#,COM 3 technology platform.

    When C++ or C# starts communicating with each other using COM, COM creates some RCW,CW objects for that.

    The deletion/life sycle of these objects is very sensitive hence we need to take care of that.

    So we have added above written code in C# at every close window call.

    this helps to clean the RCW objects immediately after closing the window.

    Try this whenever you face ReportAVOnCOMRelease() exception.

     

     

    • Marked as answer by Praveen_More Thursday, October 13, 2011 6:24 AM
    Thursday, October 13, 2011 6:23 AM