Dynamic Invokes and Marshaling a "ref SByte*"

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts
  • Stephen Gennard

    Dynamic Invokes and Marshaling a "ref SByte*"

    Hello,

    I having a problem dynamically invoking a static method that takes a
    reference to a SByte*. If I do it directly it works just fine.

    Anyone any ideas why?

    I have include a example below...

    --
    Stephen Gennard
    email: Stephen.Gennard @microfocus.com

    D:\development> csc /unsafe /target:library /out:sb.dll sb.cs

    Microsoft (R) Visual C# .NET Compiler version 7.10.3052.4
    for Microsoft (R) .NET Framework version 1.1.4322
    Copyright (C) Microsoft Corporation 2001-2002. All rights reserved.


    D:\development\ netx45\ilrts\Te sts>csc /unsafe /define:DYNAMIC sbinvoke.cs
    Microsoft (R) Visual C# .NET Compiler version 7.10.3052.4
    for Microsoft (R) .NET Framework version 1.1.4322
    Copyright (C) Microsoft Corporation 2001-2002. All rights reserved.


    D:\development> sbinvoke
    DYNAMIC invoke of GetMemory()

    Unhandled Exception: System.Argument Exception: Object type cannot be
    converted t
    o target type.
    at System.Reflecti on.RuntimeMetho dInfo.InternalI nvoke(Object obj,
    BindingFlag
    s invokeAttr, Binder binder, Object[] parameters, CultureInfo culture,
    Boolean i
    sBinderDefault, Assembly caller, Boolean verifyAccess)
    at System.Reflecti on.RuntimeMetho dInfo.InternalI nvoke(Object obj,
    BindingFlag
    s invokeAttr, Binder binder, Object[] parameters, CultureInfo culture,
    Boolean v
    erifyAccess)
    at System.Reflecti on.RuntimeMetho dInfo.Invoke(Ob ject obj,
    BindingFlags invoke
    Attr, Binder binder, Object[] parameters, CultureInfo culture)
    at SBInvoke.test()
    at SBInvoke.Main(S tring[] args)


    Now for the one that works...

    D:\development> csc /unsafe sbinvoke.cs /r:sb.dll
    Microsoft (R) Visual C# .NET Compiler version 7.10.3052.4
    for Microsoft (R) .NET Framework version 1.1.4322
    Copyright (C) Microsoft Corporation 2001-2002. All rights reserved.


    D:\development> sbinvoke
    ILREF invoke of GetMemory()

    abcdefghijklmno pqrstuvwxyz

    --file: SBInvoke.cs
    using System;
    using System.Runtime. InteropServices ;
    using System.Reflecti on;

    public class SBInvoke
    {
    public unsafe static void test()
    {
    SByte *memory = null;
    #if DYNAMIC
    Console.WriteLi ne("DYNAMIC invoke of GetMemory()");

    Assembly assembly = Assembly.LoadFr om("sb.dll");
    Type type = assembly.GetTyp e("SB");

    /* find GetMemory() method */
    MethodInfo method2invoke = null;
    foreach (MethodInfo method in type.GetMethods ())
    {
    if (method.Name.Co mpareTo("GetMem ory") == 0)
    method2invoke = method;
    }

    object[] parms = { (IntPtr)memory };

    int size = (int)method2inv oke.Invoke(meth od2invoke,parms );

    byte *countPtr = (byte*)(IntPtr) parms[0];
    #else
    Console.WriteLi ne("ILREF invoke of GetMemory()");

    int size = SB.GetMemory(re f memory);
    byte *countPtr = (byte*)memory;
    #endif

    Console.WriteLi ne();

    for(int c=0; c<size; c++)
    {
    Console.Write(( char)*countPtr) ;
    countPtr++;
    }

    Console.WriteLi ne();
    }

    public static int Main(string[] args)
    {
    test();
    return 0;
    }
    }

    --file: sb.cs
    using System.Runtime. InteropServices ;
    using System;

    public class SB
    {
    public unsafe static int GetMemory(
    #if DOES_AN_ATTRIBU TE_OR_TWO_HELP
    [MarshalAs(Unman agedType.LPArra y)]
    #endif
    ref SByte *ptr)
    {
    ptr = (SByte*)Marshal .AllocHGlobal(2 6);

    byte *initPtr = (byte*)ptr;
    for(int c=0; c<26; c++)
    *initPtr++=(byt e)('a'+(byte)c) ;

    return 26;
    }
    }



    using System.Runtime. InteropServices ;
    using System;

    public class SB
    {
    public unsafe static int GetMemory(
    #if DOES_AN_ATTRIBU TE_OR_TWO_HELP
    [MarshalAs(Unman agedType.LPArra y)]
    #endif
    ref SByte *ptr)
    {
    ptr = (SByte*)Marshal .AllocHGlobal(2 6);

    byte *initPtr = (byte*)ptr;
    for(int c=0; c<26; c++)
    *initPtr++=(byt e)('a'+(byte)c) ;

    return 26;
    }
    }


    using System;
    using System.Runtime. InteropServices ;
    using System.Reflecti on;

    public class SBInvoke
    {
    public unsafe static void test()
    {
    SByte *memory = null;
    #if DYNAMIC
    Console.WriteLi ne("DYNAMIC invoke of GetMemory()");

    Assembly assembly = Assembly.LoadFr om("sb.dll");
    Type type = assembly.GetTyp e("SB");

    /* find GetMemory() method */
    MethodInfo method2invoke = null;
    foreach (MethodInfo method in type.GetMethods ())
    {
    if (method.Name.Co mpareTo("GetMem ory") == 0)
    method2invoke = method;
    }

    object[] parms = { (IntPtr)memory };

    int size = (int)method2inv oke.Invoke(meth od2invoke,parms );

    byte *countPtr = (byte*)(IntPtr) parms[0];
    #else
    Console.WriteLi ne("ILREF invoke of GetMemory()");

    int size = SB.GetMemory(re f memory);
    byte *countPtr = (byte*)memory;
    #endif

    Console.WriteLi ne();

    for(int c=0; c<size; c++)
    {
    Console.Write(( char)*countPtr) ;
    countPtr++;
    }

    Console.WriteLi ne();
    }

    public static int Main(string[] args)
    {
    test();
    return 0;
    }
    }


Working...