相关疑难解决方法(0)

GraphViz C#interop偶尔会导致AccessViolationException

在ImplicitOperator中使用David Brown的可下载示例我将一个经常工作的DOT文件的GraphViz渲染器组合到一个内存中的图像中.

不幸的是,我的版本因为我已经使用IIS 7 ASP.NET Web应用程序的8次执行中的1次失败率而失败.我知道DOT文件数据是一致的,因为我将失败的实例与工作实例,它们是相同的.

由于大卫的网站似乎暗示博客的未来不确定,我将在这里重新打印互联网文章.希望他不介意.失败是在示例的末尾,在第三个语句集的RenderImage中.我已经注意到// TODO的失败行:......失败总是发生在那里(如果它发生的话).通过这一行,g和gvc指针不为零,并且正确填充了布局字符串.

我真的不希望任何人在运行时调试它.相反,我希望对互操作代码的一些静态分析可能会揭示问题.我想不出任何先进的编组技术 - 两个IntPtrs和一个字符串不需要很多帮助,对吧?

谢谢!

旁注:我看了一下MSAGL的试用版,我没有留下深刻的印象 - 微软99美元,我希望节点布局和/或文档的更多功能可以解释我所缺少的内容.也许我从QuickGraph到AGL的快速端口不公平地偏向于我的经验,因为这些方法存在一些根本的差异(例如,以边缘为中心与以节点为中心).

public static class Graphviz
{
  public const string LIB_GVC = "gvc.dll";
  public const string LIB_GRAPH = "graph.dll";
  public const int SUCCESS = 0;

  /// <summary> 
  /// Creates a new Graphviz context. 
  /// </summary> 
  [DllImport(LIB_GVC)]
  public static extern IntPtr gvContext();

  /// <summary> 
  /// Releases a context's resources. 
  /// </summary> 
  [DllImport(LIB_GVC)]
  public static extern int gvFreeContext(IntPtr gvc);

  /// <summary> 
  /// Reads a …
Run Code Online (Sandbox Code Playgroud)

c# graphviz access-violation

8
推荐指数
1
解决办法
2372
查看次数

为什么.NET程序能够在损坏的堆栈中存活?(当使用错误的调用约定时)

在VS2010中,如果使用错误的调用约定调用函数,则托管调试助手将为您提供pInvokeStackImbalance异常(pInvokeStackImbalance MDA),这通常是因为在调用C库时未指定CallingConvention = Cdecl.比如你写的

[DllImport("some_c_lib.dll")]
static extern void my_c_function(int arg1, int arg2);
Run Code Online (Sandbox Code Playgroud)

代替

[DllImport("some_c_lib.dll", CallingConvention=CallingConvention.Cdecl)]
static extern void my_c_function(int arg1, int arg2);
Run Code Online (Sandbox Code Playgroud)

因此获得了StdCall调用约定而不是Cdelc.

如果你回答这个问题,你已经知道了这个差异,但是对于这个线程的其他访问者:StdCall意味着被调用者清除堆栈中的参数,而Cdecl意味着调用者清理堆栈.

因此,如果您的C代码中的调用约定错误,则您的堆栈不会被清理并且程序崩溃.

但是,即使.NET程序使用StdCall进行Cdecl功能,.NET程序似乎也不会崩溃.默认情况下,VS2008上没有启用堆栈不平衡检查,因此一些VS2008项目使用了他们的作者不知道的错误调用约定.我刚尝试过GnuMpDotNet,即使缺少Cdelc声明,样本运行也很好.X-MPIR也是如此.

它们都在调试模式下抛出pInvokeStackImbalance MDA异常,但在发布模式下不会崩溃.为什么是这样?.NET VM是否将所有对本机代码的调用包装起来并在之后恢复堆栈本身?如果是这样,为什么还要使用CallingConvention属性呢?

.net pinvoke dllimport

8
推荐指数
1
解决办法
1133
查看次数

标签 统计

.net ×1

access-violation ×1

c# ×1

dllimport ×1

graphviz ×1

pinvoke ×1