Marechal va_list em delegado C #
Eu estou tentando fazer isso funcionar a partir de c #:
Cabeçalho C:
typedef void (LogFunc) (const char *format, va_list args);
bool Init(uint32 version, LogFunc *log)
Implementação C #:
static class NativeMethods
{
[DllImport("My.dll", SetLastError = true)]
internal static extern bool Init(uint version, LogFunc log);
[UnmanagedFunctionPointer(CallingConvention.Cdecl, SetLastError = true)]
internal delegate void LogFunc(string format, string[] args);
}
class Program
{
public static void Main(string[] args)
{
NativeMethods.Init(5, LogMessage);
Console.ReadLine();
}
private static void LogMessage(string format, string[] args)
{
Console.WriteLine("Format: {0}, args: {1}", format, DisplayArgs(args));
}
}
O que acontece aqui é que a chamada paraNativeMethods.Init
chama de voltaLogMessage
e passa dados de código não gerenciado como parâmetros. Isso funciona para a maioria dos casos em que os argumentos são seqüências de caracteres. No entanto, há uma chamada em que o formato é:
Plugin carregado% s para a versão% d.
e o args contém apenas uma string (o nome do plugin). Eles não contêm o valor da versão, o que faz sentido desde que eu useistring[]
na declaração do delegado. A pergunta é: como devo escrever o delegado para obter a string e o int?
Eu tentei usarobject[] args
e tenho essa exceção:Uma VARIANT inválida foi detectada durante uma conversão de uma VARIANT não gerenciada para um objeto gerenciado. Passar VARIANTs inválidos para o CLR pode causar exceções inesperadas, corrupção ou perda de dados.
EDIT: eu poderia alterar a assinatura de delegado para isso:
internal delegate void LogFunc(string format, IntPtr args);
Eu poderia analisar o formato e descobrir quantos argumentos esperar e de que tipo. Por exemplo. paraPlugin carregado% s para a versão% d. Eu esperaria uma string e um int. Existe uma maneira de obter esses 2 fora desse IntPtr?