将C++ strncpy函数从dll编码为c#
问题描述:
下面是一个玩具示例,用于更好地理解c#和C++/dll之间字符串类型的编组。将C++ strncpy函数从dll编码为c#
将下面的“MyStrCopy”函数编组到C#中的最佳方式是什么? (优选地不使用不安全的关键字和通过编组类型流入和流出的C#为字符串类型。)
文件:MyStrCopy.cs
using System.Runtime.InteropServices;
namespace MySpace {
class MyDll {
[DllImport (@"MyStrCopy")]
public static extern void MyStrCopy(
string dest????, string source????, int dest_length????);
}
}
FILE:MyStrCopy.h:
extern "C" {
void __declspec(dllexport) MyStrCopy(
char* dest, const char* source, int dest_length);
}
FILE:MyStrCopy.cpp
#include <cstring>
#include "MyStrCopy.h"
void MyStrCopy(char* dest, const char* source, int dest_len) {
strncpy(dest, source, dest_len);
dest[dest_len-1] = 0; // zero terminated when source > dest
}
我编译上面的文件“MyStrCopy.cp p“放入一个名为:MyStrCopy.dll
我也有点好奇,如果你返回char *以及在不使用不安全和编组类型的字符串的相同首选项时它会是什么样子。例如,如果DLL导出函数看起来像这个:
char* MyStrCopy(char* dest, const char* source, int dest_len) {
return strncpy(dest, source, dest_len);
}
答
using System.Text;
using System.Runtime.InteropServices;
namespace MySpace
{
class MyDll {
[DllImport("MyStrCopy.dll", CharSet = CharSet.Ansi)]
public static extern void MyStrCopy(
StringBuilder dst_str,
string src_str,
int dst_len);
static void ExampleUsage() {
int dest_len = 100;
StringBuilder dest_str = new StringBuilder(dest_len);
string source = "this is a string";
MyStrCopy(dest_str, source, dest_len);
return;
}
} //class
} //namespace
使用C函数,是由设计打破是非常不明智的,函数strncpy()有致命的缺陷,因为它并不能保证它会零终止字符串。这将导致C#程序崩溃,导致无法访问AccessViolationException。这个玩具将成为另一个程序员的头痛,投票结束。 –
这是一个很好的观点,在strncpy()之后添加以下内容,它适用于所有情况:dest [dest_len-1] = 0;无论如何,重点仅仅是看到C#中的[DllImport]语法示例,它允许您将字符串传递给像strncpy()这样的函数,无论它们是什么......在我的例子中,我真的试图将一些值从使用DLL互操作从C++端将列表转换为c#端。 –