将ArgIterator编组到va_list

时间:2015-04-16 12:40:32

标签: c# interop variadic-functions

所以,我有一个想法尝试p /调用带va_list的C函数。我知道如何调用经典的varargs函数(使用__arglist),并且在我看来va_list就像ArgIterator一样,我认为可能只是通过它的方法:

[DllImport("msvcrt.dll", CharSet = CharSet.Unicode, CallingConvention = CallingConvention.Cdecl)]
public static extern int vswprintf(StringBuilder str, int length, string format, ArgIterator args);

public static int vswprintf(StringBuilder str, int length, string format, __arglist)
{
    return vswprintf(str, length, format, new ArgIterator(__arglist));
}

int len = 100;
StringBuilder sb = new StringBuilder(len);
vswprintf(sb, len, "%s, %d", __arglist("test", 2));

事实证明,.NET实际上认识到了这一点,因为引发了以下异常:

System.NotSupportedException
   in System.StubHelpers.StubHelpers.MarshalToUnmanagedVaListInternal(IntPtr va_list, UInt32 vaListSize, IntPtr pArgIterator)
   in Program.vswprintf(StringBuilder str, Int32 length, String format, ArgIterator args)
   in Program.vswprintf(StringBuilder str, Int32 length, String format)

所以,显然,.NET知道我想做什么,并且有一些应该做的事情:

[MethodImpl(MethodImplOptions.InternalCall), ForceTokenStabilization]
internal static extern void MarshalToUnmanagedVaListInternal(IntPtr va_list, uint vaListSize, IntPtr pArgIterator); //Reflector

参数的名称暗示了目的,但异常让我感到困惑。我是否对p / invoke做错了,或者这个.NET编组方法没有完成?

编辑:
经过一番研究后,我发现了这种方法的implementation,似乎无法传递正常的字符串。所以我修改了代码:

vswprintf(sb, len, "%d, %d", __arglist(1, 2));

但这会引发AccessViolationException(我最喜欢的)!现在怎么了?

0 个答案:

没有答案