2017-10-12 42 views
1

我有一个函数在一个DLL中具有以下标识符。C#编组一个const char *从DLL的返回值

const char* function(void) 

DLL在堆上分配字符串,并期望它只被读取。我曾尝试以下导入功能,但我得到一个访问冲突

[DllImport("great.dll", CharSet = CharSet.Ansi, 
         CallingConvention = CallingConvention.Cdecl) 
] 
public static extern string function(); 

如何处理这个正确

错误消息:

System.AccessViolationException:“试图读取或写保护的内存。这往往表明其他内存已经损坏。“

+0

封送拆分器假定DLL在COM堆上分配了字符串,因此在返回的指针上调用CoTaskMemFree。显然,DLL没有这样做。问题是,该字符串是如何分配的?在继续之前,您需要了解这一点。 –

+0

我不这么认为。但是,如果它足够适合你。 –

+1

另请参阅https://docs.microsoft.com/zh-cn/dotnet/framework/interop/default-marshaling-for-strings –

回答

2

就问题 “”与相同参数类型等功能的文字,我已经能够使用[的MarshalAs(UnmanagedType.LPStr)来处理它,但是这不会对返回值工作”

https://docs.microsoft.com/en-us/dotnet/api/system.runtime.interopservices.marshalasattribute?view=netframework-4.7

//Applied to a return value. 
[return: MarshalAs(UnmanagedType.LPWStr)] 
    public String GetMessage() 
    { 
     return "Hello World"; 
    } 

更新引用这一点:保持这种情况下,它是为别人寻找有关有帮助‘的MarshalAs’和返回值,因为这个问题笔者已经解决了他们的问题,因为他们 以上评论

+0

顺便说一句,你知道http://www.pinvoke.net/网站? –

+0

这是惊人的。三个完全废话的upvote。你已经在你用C#实现的函数上应用了MarshalAs?做体面的事情,并删除这个来保存你的脸红。 –

+0

你有没有想过,有人可能会从本机代码端与这个C#方法交谈? (说回调或直接调用它?)。更有趣的是你没有注意到这是微软的示例代码,而不是我的,原来问题的答案实际上是关于“[return:...]”的,因为问题是提到能够使用MarshalAs,但不与返回值。在批评之前请仔细阅读 –