Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • World
  • Users
  • Groups
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Code Project
CODE PROJECT For Those Who Code
  • Home
  • Articles
  • FAQ
Community
  1. Home
  2. General Programming
  3. C#
  4. Interop - Marshaling nested structs

Interop - Marshaling nested structs

Scheduled Pinned Locked Moved C#
csharpcomhelpquestion
4 Posts 2 Posters 7 Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • N Offline
    N Offline
    Nathan Tran
    wrote on last edited by
    #1

    Hi, I'm getting a System.ArgumentException trying to call the following IActiveDesktop method: STDMETHOD (AddDesktopItem)(THIS_ LPCCOMPONENT pcomp, DWORD dwReserved) PURE; This is how I'm marshaling the call. void AddDesktopItem( [In, MarshalAs( UnmanagedType.LPStruct )] COMPONENT pcomp, [In] int dwReserved ); I believe the problem is with marshaling the COMPONENT structure. Could some one point out to me if I'm marshaling the nested structures correctly. Here is the original typedef for the struct and my c# attempt at marshaling it. typedef struct _tagCOMPONENT { DWORD dwSize; //Size of this structure DWORD dwID; //Reserved: Set it always to zero. int iComponentType; //One of COMP_TYPE_* BOOL fChecked; // Is this component enabled? BOOL fDirty; // Had the component been modified and not BOOL fNoScroll; // Is the component scrollable? COMPPOS cpPos; // Width, height etc., WCHAR wszFriendlyName[MAX_PATH]; WCHAR wszSource[INTERNET_MAX_URL_LENGTH]; //URL of the component. WCHAR wszSubscribedURL[INTERNET_MAX_URL_LENGTH]; //Subscrined URL DWORD dwCurItemState; // Current state of the Component. COMPSTATEINFO csiOriginal; COMPSTATEINFO csiRestored; // Restored state of the component. } COMPONENT; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode )] public class COMPONENT { public int dwSize; // Size of the structure. public int dwID; // Reserved. Set to zero. public COMP_TYPE iComponentType; [MarshalAs( UnmanagedType.Bool )] public bool fChecked; [MarshalAs( UnmanagedType.Bool )] public bool fDirty; [MarshalAs( UnmanagedType.Bool )] public bool fNoScroll; [MarshalAs( UnmanagedType.Struct )] public COMPPOS cpPos; [MarshalAs( UnmanagedType.ByValTStr, SizeConst = 260 )] public string wszFriendlyName; [MarshalAs( UnmanagedType.ByValTStr, SizeConst = 2083 )] public string wszSource; [MarshalAs( UnmanagedType.ByValTStr, SizeConst = 2083 )] public string wszSubscribedURL; public ITEM_STATE dwCurItemState; [MarshalAs( UnmanagedType.Struct )] public COMPSTATEINFO csiOriginal; [MarshalAs( UnmanagedType.Struct )] public COMPSTATEINFO csiRestored; } StructLayout( LayoutKind.Sequential )] public class COMPSTATEINFO { public int dwSize; public int iLeft; public int iTop; public int dwWidth; public int dwH

    L 1 Reply Last reply
    0
    • N Nathan Tran

      Hi, I'm getting a System.ArgumentException trying to call the following IActiveDesktop method: STDMETHOD (AddDesktopItem)(THIS_ LPCCOMPONENT pcomp, DWORD dwReserved) PURE; This is how I'm marshaling the call. void AddDesktopItem( [In, MarshalAs( UnmanagedType.LPStruct )] COMPONENT pcomp, [In] int dwReserved ); I believe the problem is with marshaling the COMPONENT structure. Could some one point out to me if I'm marshaling the nested structures correctly. Here is the original typedef for the struct and my c# attempt at marshaling it. typedef struct _tagCOMPONENT { DWORD dwSize; //Size of this structure DWORD dwID; //Reserved: Set it always to zero. int iComponentType; //One of COMP_TYPE_* BOOL fChecked; // Is this component enabled? BOOL fDirty; // Had the component been modified and not BOOL fNoScroll; // Is the component scrollable? COMPPOS cpPos; // Width, height etc., WCHAR wszFriendlyName[MAX_PATH]; WCHAR wszSource[INTERNET_MAX_URL_LENGTH]; //URL of the component. WCHAR wszSubscribedURL[INTERNET_MAX_URL_LENGTH]; //Subscrined URL DWORD dwCurItemState; // Current state of the Component. COMPSTATEINFO csiOriginal; COMPSTATEINFO csiRestored; // Restored state of the component. } COMPONENT; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode )] public class COMPONENT { public int dwSize; // Size of the structure. public int dwID; // Reserved. Set to zero. public COMP_TYPE iComponentType; [MarshalAs( UnmanagedType.Bool )] public bool fChecked; [MarshalAs( UnmanagedType.Bool )] public bool fDirty; [MarshalAs( UnmanagedType.Bool )] public bool fNoScroll; [MarshalAs( UnmanagedType.Struct )] public COMPPOS cpPos; [MarshalAs( UnmanagedType.ByValTStr, SizeConst = 260 )] public string wszFriendlyName; [MarshalAs( UnmanagedType.ByValTStr, SizeConst = 2083 )] public string wszSource; [MarshalAs( UnmanagedType.ByValTStr, SizeConst = 2083 )] public string wszSubscribedURL; public ITEM_STATE dwCurItemState; [MarshalAs( UnmanagedType.Struct )] public COMPSTATEINFO csiOriginal; [MarshalAs( UnmanagedType.Struct )] public COMPSTATEINFO csiRestored; } StructLayout( LayoutKind.Sequential )] public class COMPSTATEINFO { public int dwSize; public int iLeft; public int iTop; public int dwWidth; public int dwH

      L Offline
      L Offline
      leppie
      wrote on last edited by
      #2

      Nathan Tran wrote: I'm getting a System.ArgumentException trying to call the following IActiveDesktop method: STDMETHOD (AddDesktopItem)(THIS_ LPCCOMPONENT pcomp, DWORD dwReserved) PURE; This is how I'm marshaling the call. void AddDesktopItem( [In, MarshalAs( UnmanagedType.LPStruct )] COMPONENT pcomp, [In] int dwReserved ); I believe the problem is with marshaling the COMPONENT structure. STOP! :) Its exactly what it says. Dont use LPStruct. Just add ref to it, or Marshall the structure to unmanaged memory 1st, then pass an IntPtr into the function (obviously you will need to change the function definition). Once (and only then), you can lok at the HRESULT you are getting to see if the struct size is infact correct (which probably wont be the case, never is with these nested structs). Good luck :) NOT lol, where is the functions DllImportAttribute? Thats the problem. Not sure how it compiled... I rated this article 2 by mistake. It deserves more. I wanted to get to the second page... - vjedlicka 3:33 25 Nov '02

      N 1 Reply Last reply
      0
      • L leppie

        Nathan Tran wrote: I'm getting a System.ArgumentException trying to call the following IActiveDesktop method: STDMETHOD (AddDesktopItem)(THIS_ LPCCOMPONENT pcomp, DWORD dwReserved) PURE; This is how I'm marshaling the call. void AddDesktopItem( [In, MarshalAs( UnmanagedType.LPStruct )] COMPONENT pcomp, [In] int dwReserved ); I believe the problem is with marshaling the COMPONENT structure. STOP! :) Its exactly what it says. Dont use LPStruct. Just add ref to it, or Marshall the structure to unmanaged memory 1st, then pass an IntPtr into the function (obviously you will need to change the function definition). Once (and only then), you can lok at the HRESULT you are getting to see if the struct size is infact correct (which probably wont be the case, never is with these nested structs). Good luck :) NOT lol, where is the functions DllImportAttribute? Thats the problem. Not sure how it compiled... I rated this article 2 by mistake. It deserves more. I wanted to get to the second page... - vjedlicka 3:33 25 Nov '02

        N Offline
        N Offline
        Nathan Tran
        wrote on last edited by
        #3

        leppie, I don't need the DllImportAttribute since this COM method is being called through a c# mapped interface. Based on your suggestion to use IntPtr I have made the following changes to the code but I'm still getting System.ArgumentException. void AddDesktopItem( [In] IntPtr component, [In] int dwReserved ); [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode )] public class COMPONENT { public int dwSize; // Size of the structure. public int dwID; // Reserved. Set to zero. public COMP_TYPE iComponentType; public int fChecked; public int fDirty; public int fNoScroll; public COMPPOS cpPos; [MarshalAs( UnmanagedType.ByValTStr, SizeConst = 260 )] public string wszFriendlyName; [MarshalAs( UnmanagedType.ByValTStr, SizeConst = 2083 )] public string wszSource; [MarshalAs( UnmanagedType.ByValTStr, SizeConst = 2083 )] public string wszSubscribedURL; public ITEM_STATE dwCurItemState; public COMPSTATEINFO csiOriginal; public COMPSTATEINFO csiRestored; } and the help method to copy the struct to unmanaged mem is as follows. public static IntPtr CreateByteBuffer( COMPONENT comp ) { IntPtr bufferPtr = Marshal.AllocCoTaskMem( Marshal.SizeOf( comp ) ); Marshal.StructureToPtr( comp, bufferPtr, true ); return bufferPtr; } Note: I have verified that the size of the struct to be correct. It is 8972 bytes to be exact. I have even checked the memory location of the IntPtr and all the relevant data is there. Any other suggestion? Nathan.

        L 1 Reply Last reply
        0
        • N Nathan Tran

          leppie, I don't need the DllImportAttribute since this COM method is being called through a c# mapped interface. Based on your suggestion to use IntPtr I have made the following changes to the code but I'm still getting System.ArgumentException. void AddDesktopItem( [In] IntPtr component, [In] int dwReserved ); [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode )] public class COMPONENT { public int dwSize; // Size of the structure. public int dwID; // Reserved. Set to zero. public COMP_TYPE iComponentType; public int fChecked; public int fDirty; public int fNoScroll; public COMPPOS cpPos; [MarshalAs( UnmanagedType.ByValTStr, SizeConst = 260 )] public string wszFriendlyName; [MarshalAs( UnmanagedType.ByValTStr, SizeConst = 2083 )] public string wszSource; [MarshalAs( UnmanagedType.ByValTStr, SizeConst = 2083 )] public string wszSubscribedURL; public ITEM_STATE dwCurItemState; public COMPSTATEINFO csiOriginal; public COMPSTATEINFO csiRestored; } and the help method to copy the struct to unmanaged mem is as follows. public static IntPtr CreateByteBuffer( COMPONENT comp ) { IntPtr bufferPtr = Marshal.AllocCoTaskMem( Marshal.SizeOf( comp ) ); Marshal.StructureToPtr( comp, bufferPtr, true ); return bufferPtr; } Note: I have verified that the size of the struct to be correct. It is 8972 bytes to be exact. I have even checked the memory location of the IntPtr and all the relevant data is there. Any other suggestion? Nathan.

          L Offline
          L Offline
          leppie
          wrote on last edited by
          #4

          Nathan Tran wrote: Any other suggestion? Maybe the C# mapping is wrong? I dont really know the COM stuff too well. Normal interop I do know well. You have thus checked that stuff and it checks out ok. That leads me back to that function, what happens from there? Sorry couldnt help more :| I rated this article 2 by mistake. It deserves more. I wanted to get to the second page... - vjedlicka 3:33 25 Nov '02

          1 Reply Last reply
          0
          Reply
          • Reply as topic
          Log in to reply
          • Oldest to Newest
          • Newest to Oldest
          • Most Votes


          • Login

          • Don't have an account? Register

          • Login or register to search.
          • First post
            Last post
          0
          • Categories
          • Recent
          • Tags
          • Popular
          • World
          • Users
          • Groups