Groups | Blog | Home
all groups > dotnet interop > august 2005 >

dotnet interop : [Structured Storage] IEnumSTATSTG.Next(..) fails to return STATSTG


luke
8/29/2005 6:19:37 AM
Hi,
I'm developing a .NET wrapper to access COM compound files. I've
imported all needed COM interfaces including IStorage and IEnumSTATSG
and I can successfully open a storage file using StgOpenStorage. The
problem is, when I try to enumerate the streams ans substorages
inside: IEnumSTATSTG.Next() is never giving me any STATSTG object,
althoug the HRESULT is S_OK.
Here's the interfaces:

[ComImport]
[GuidAttribute("0000000B-0000-0000-C000-000000000046")]
[InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown)]
public interface IStorage
{
........

[PreserveSig]
int EnumElements(int reserved1, IntPtr reserved2, int reserved3,
[MarshalAs(UnmanagedType.Interface)] out IEnumSTATSTG ppenum);

........
}

[ComImport]
[GuidAttribute("0000000D-0000-0000-C000-000000000046")]
[InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown)]
[System.Security.SuppressUnmanagedCodeSecurity]
public interface IEnumSTATSTG
{
.......
[PreserveSig]
int Next(uint celt, out STATSTG rgelt, out uint pceltFetched);
........
}

I'm importing StgOpenStorage as :

[DllImportAttribute("Ole32.dll")]
public static extern int
StgOpenStorage([MarshalAs(UnmanagedType.LPWStr)] string wcsName, IntPtr
pstgPriority, int grfMode, IntPtr snbExclude, int reserved, out
IStorage storage);

and the code where I'm trying to use it together:

IStorage storage;
IEnumSTATSTG ie;
System.Runtime.InteropServices.STATSTG statstg = new
System.Runtime.InteropServices.STATSTG();
int res0 = Ole32.StgOpenStorage("testfile.xls", IntPtr.Zero, 0x00000000
| 0x00000010 | 0x00000000, IntPtr.Zero, 0, out storage);
uint k;
int res1 = storage.EnumElements(0, IntPtr.Zero, 0, out ie);
int res2 = ie.Next(1, out statstg, out k);

As a result: res0, res1, and res2 are 0, which means the HRESULTS are
S_OK,
but the statstg is still empty, the same way k is 0 (should be 1, as
res2=0 means that ie.Next succeeded).

Is there a problem with marshalling interfaces somewhere? Please, help
me, I'm really out of any idea what could be the cause.

Luke
luke
8/29/2005 10:21:04 AM
Hi Mattias,
Thanks for your reply. All interface methods are in Vtable Order, just
like it's given on MSDN. I don't have to declare IUnknown standard
interface methods, as I applied the
InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown) attribute,
right?

Luke
luke
8/29/2005 1:27:32 PM
It works:) Thank you very mych, Mattias.

Luke
Mattias Sjögren
8/29/2005 6:51:00 PM
[quoted text, click to view]


Are you sure all interface methods are declared in the correct order?


Mattias

--
Mattias Sjögren [MVP] mattias @ mvps.org
http://www.msjogren.net/dotnet/ | http://www.dotnetinterop.com
Mattias Sjögren
8/29/2005 8:48:29 PM
[quoted text, click to view]

It seems the MSDN docs have them in the wrong order. The correct order
(just like all other IEnum* interfaces) is Next, Skip, Reset, Close.


[quoted text, click to view]

Right.


Mattias

--
Mattias Sjögren [MVP] mattias @ mvps.org
http://www.msjogren.net/dotnet/ | http://www.dotnetinterop.com
AddThis Social Bookmark Button