将字符串从 C# 传递到 c++ .dll会打乱数据

本文关键字:dll 数据 c++ 字符串 | 更新日期: 2023-09-27 18:34:39

我有一个 c++ dll,带有以下代码:

extern "C"
{
    const char *SaveDate;
    __declspec(dllexport) void SetDate(const char *date)
    {
        SaveDate = date;
        std::cout << "date: " << SaveDate  << std::endl;
    }
}

当我打印该函数中的值时,它会打印

'date: 20160215' 

但是当我从另一个函数中获取"SaveDate"变量并打印它时,它会打印

'104'

我的 C# 是:

[DllImport("XmlRecord.dll", CallingConvention = CallingConvention.Cdecl)]
public static extern void SetSlate(string date);

public bool SetupRec()
{
    string Date = DateTime.Now.ToString("yyyyMMdd");
    SetSlate(Date);
}

为什么在 c++ dll 中打乱此值?

谢谢。

将字符串从 C# 传递到 c++ .dll会打乱数据

如果使用 P/Invoke,则传递给 C 函数的任何参数在调用期间都有效。

如果要重用输入字符串,则需要复制它。您作为参数获得的那个将在通话后释放(您甚至不知道何时(。只需将其保存到std::string而不是持有const char *即可。

如果绝对希望避免复制数据,可以利用一些机制,但必须在 C# 端采取适当的预防措施,因为允许 GC 随时移动内存中的对象。
这涉及长期对象固定(使用 GCHandle 类(,这会阻碍 GC,因此最好避免使用。如果可以将数据有效性限制为单个堆栈帧,则短期固定(使用 fixed 语句(是可行的。然后,必须将数据作为IntPtr传递给 C 函数,以绕过 .NET 封送处理。