我在C文件中有一个结构,如下所示
struct Parameter{
char param1[20];
char param2[20];
}
以及C文件中的一个函数,它将此结构作为参数以及char *作为另一个参数,如下所示
extern "C" __declspec(dllexport) void GetValue(char* opt,struct Parameter param);
void GetValue(char* opt, struct Parameter params)
{
printf("%s", params->param1);
}
我想使用编组从我的C#应用程序中调用它。我在C#中创建了一个类似的结构
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)]
public class Parameters
{
public string Param1 { get; set; }
public string Param1 { get; set; }
}
并使用以下方法在C#中调用它
[DllImport(@"C:\Test\CTestDll.dll",CallingConvention = CallingConvention.Cdecl,CharSet=CharSet.Ansi)]
public static extern void GetValue([MarshalAs(UnmanagedType.LPStr)]StringBuilder sbOut, [MarshalAs(UnmanagedType.LPStruct)]Parameters sbIn);
但是作为print语句的结果是打印null。我在C编程方面不是很好。请帮我解决一下。我错了,是C函数还是C#编组
答案 0 :(得分:2)
不同之处在于,在C ++中,您的结构包含原始字符,而在C#中,您的类包含对字符串的引用。 MarshalAs属性将使用char数组而不是对string的引用:
unsafe static class Program
{
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)]
public struct Parameters
{
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 20)]
public String Param1;
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 20)]
public String Param2;
}
[DllImport(@"CTestDll2.dll", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Ansi)]
public static extern void GetValue(StringBuilder sbOut, Parameters sbIn);
static void Main(string[] args)
{
var p = new Parameters
{
Param1 = "abc",
Param2 = "dfc"
};
var s = new StringBuilder("some text");
GetValue(s, p);
}
}
C ++:
// CTestDll.h
#pragma once
#include <stdio.h>
extern "C" __declspec(dllexport) void GetValue(char* opt, struct Parameter param);
struct Parameter{
char param1[20];
char param2[20];
};
void GetValue(char* opt, struct Parameter params)
{
printf("param1: %s, param2: %s, string: %s", params.param1, params.param2, opt);
}