简体   繁体   English

如何从Visual Studio加载项中获取正在运行的进程的堆栈跟踪?

[英]How to get stack trace of a running process from within a Visual Studio add-in?

I am writing a Visual Studio add-in in C# which will run while I am debugging a process in the same Visual Studio window and I need access to that the process' stack trace from within my add-in. 我在C#中编写一个Visual Studio加载项,当我在同一个Visual Studio窗口中调试一个进程时,它将运行,我需要从我的加载项中访问该进程的堆栈跟踪。 I tried putting this code into my add-in but it returns the add-in's stack trace, not the process I am debugging. 我尝试将此代码放入我的加载项,但它返回加载项的堆栈跟踪,而不是我正在调试的进程。

System.Diagnostics.StackTrace stacktrace = new System.Diagnostics.StackTrace(true);
System.Diagnostics.StackFrame stackframe = stacktrace.GetFrame(0);

Any help would be appreciated. 任何帮助,将不胜感激。

The easiest way would be to ask the debugger for the stack frames through the DTE automation object. 最简单的方法是通过DTE自动化对象向调试器询问堆栈帧。 The DTE object should be available to you through your add-in. 您可以通过加载项使用DTE对象。 The property you want is Debugger.CurrentThread.StackFrames . 您需要的属性是Debugger.CurrentThread.StackFrames If you're using .NET 4, you can do: 如果您使用的是.NET 4,则可以执行以下操作:

    static string GetCurrentStackTrace(DTE dte)
    {
        bool canGetStackTrace =
            (dte != null) &&
            (dte.Debugger != null) &&
            (dte.Debugger.CurrentThread != null) &&
            (dte.Debugger.CurrentThread.StackFrames != null);

        if (!canGetStackTrace)
            return string.Empty;

        return string.Join(
            "\n",
            dte.Debugger.CurrentThread.StackFrames.Cast<StackFrame>().Select(f => f.FunctionName)
        );
    }

Otherwise, you can do: 否则,你可以这样做:

    static string GetCurrentStackTrace(DTE dte)
    {
        bool canGetStackTrace =
            (dte != null) &&
            (dte.Debugger != null) &&
            (dte.Debugger.CurrentThread != null) &&
            (dte.Debugger.CurrentThread.StackFrames != null);

        if (!canGetStackTrace)
            return string.Empty;

        StringBuilder stackTrace = new StringBuilder();

        foreach (StackFrame frame in dte.Debugger.CurrentThread.StackFrames)
        {
            stackTrace.AppendFormat("{0}\n", frame.FunctionName);
        }

        return stackTrace.ToString();
    }

The painful and involved way would be to use ICorDebug and StackWalk64 to get managed and native stacks separately and then stitch them together by hand. 痛苦和参与的方式是使用ICorDebugStackWalk64分别获取托管和本机堆栈,然后手动将它们拼接在一起。 Since you're a VS add-in, you might as well let the debugger do the heavy lifting for you! 既然你是一个VS加载项,你也可以让调试器为你做繁重的工作!

The code is working as expected since when you call the code, your add-in (under VS) is the "current process". 代码正在按预期工作,因为当您调用代码时,您的加载项(在VS下)是“当前进程”。

I am not sure what you mean by "currently running process" (do you mean the process being run/debugged under VS?), but I don't think its possible to get a stack-trace of another process. 我不确定“当前正在运行的进程”是什么意思(你的意思是在VS下运行/调试进程吗?),但我认为不可能获得另一个进程的堆栈跟踪。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM