如何使Visual Studio宏将调试器附加到w3wp.exe的所有实例?

时间:2009-05-05 01:48:39

标签: .net visual-studio visual-studio-2005 debugging visual-studio-macros

我正在开发网络应用程序,花费大量的工作时间用于“Ctrl + Alt + P”,按进程名称排序,并选择w3wp.exe来附加我的调试器。

更糟糕的是,我正在开发一个跨越多个应用程序池的应用程序,因此我通常有2或3个w3wp.exe实例,并且无法知道要连接哪个,所以我通常会结束附加到所有这些,这是过度的,但有效。

总而言之,这非常烦人......

我的同事找到了一种方法让VS宏自动附加到w3wp.exe(他基本上记录了这个):

Sub AttachMacro()    
  Try    
    Dim dbg2 As EnvDTE80.Debugger2 = DTE.Debugger    
    Dim trans As EnvDTE80.Transport = dbg2.Transports.Item("Default")    
    Dim dbgeng(3) As EnvDTE80.Engine    
    dbgeng(0) = trans.Engines.Item("T-SQL")    
    dbgeng(1) = trans.Engines.Item("T-SQL")    
    dbgeng(2) = trans.Engines.Item("Managed")    
    Dim proc2 As EnvDTE80.Process2 = dbg2.GetProcesses(trans, "ENIAC").Item("w3wp.exe")    
    proc2.Attach2(dbgeng)    
  Catch ex As System.Exception    
    MsgBox(ex.Message)    
  End Try    
End Sub

我不确定是否所有这些都是必要的,或者其他什么,我从来没有为VS做过一个宏,我真的不知道从哪里开始。

是否有办法修改此宏,以便不将自身附加到w3wp.exe的 实例,而是将其自身附加到w3wp的所有实例。 exe文件?

4 个答案:

答案 0 :(得分:8)

Sub MacroAttachToAllProcesses()

    Try

        Dim dbg2 As EnvDTE80.Debugger2 = DTE.Debugger
        Dim trans As EnvDTE80.Transport = dbg2.Transports.Item("Default")
        Dim dbgeng(3) As EnvDTE80.Engine

        dbgeng(0) = trans.Engines.Item("T-SQL")
        dbgeng(1) = trans.Engines.Item("T-SQL")
        dbgeng(2) = trans.Engines.Item("Managed")

        For Each theProcess As EnvDTE80.Process2 In dbg2.GetProcesses(trans, "COMPUTERNAME")
            If theProcess.Name.Contains("w3wp.exe") Then
                theProcess.Attach2(dbgeng)
            End If

        Next

    Catch ex As System.Exception
        MsgBox(ex.Message)
    End Try

End Sub

答案 1 :(得分:1)

我知道您正在为此任务寻找宏,并且我有类似的宏。但是,我想解释一种在开始调试时将调试器附加到解决方案中的项目的方法。

这是一个鲜为人知的功能 - 如果您在解决方案浏览器中右键单击解决方案文件,选择属性,则可以定义多个启动项目及其操作。运行时,调试器将附加到列出的项目中。

注意:如果您有一个Web服务,它将打开一个浏览器窗口,但您可以通过告诉它不要打开一个窗口来禁用该项目的属性。

答案 2 :(得分:1)

这是我附加到远程w3wp进程的方式。它比DanC的解决方案运行得更快,并且有一些额外的错误处理。

Private Sub AttachToW3wp(ByVal machineName As String)
    ' In order for this to work, you have to be running the Visual Studio 2010 Remote Debugging Monitor
    ' as your (domain) user.  
    ' It won't work if the remote debugger is running as a service.  I've tried every permutation of 
    ' domain and username in the the transport qualifier, tried the obvious local system username,
    ' even tried looking at the network traffic 
    ' in WireShark, I can't figure it out how to make it work if you are running as a service.  
    ' If you are running the debugger as a service, even running the macro that gets created by VS's 
    ' macro recorder when you attach to a process doesn't work.
    Dim transportQualifier = machineName
    Try
        Dim processToAttachTo As String = "w3wp.exe"
        Dim dbg2 As EnvDTE80.Debugger2 = DTE.Debugger
        Dim trans As EnvDTE80.Transport = dbg2.Transports.Item("Default")
        Dim dbgeng(2) As EnvDTE80.Engine
        dbgeng(0) = trans.Engines.Item("T-SQL")
        dbgeng(1) = trans.Engines.Item("Managed (v2.0, v1.1, v1.0)")
        Dim processesRemote = dbg2.GetProcesses(trans, transportQualifier)
        Dim attached As Boolean = False
        Dim processRemote As EnvDTE80.Process2
        For Each processRemote In processesRemote
            ' For some reason it takes a much longer time to get the remote process names then it 
            ' does the user name, so let's skip over all the processes that have the wrong UserName.
            If processRemote.UserName = "NETWORK SERVICE" AndAlso _
               (Right(processRemote.Name, Len(processToAttachTo)) = processToAttachTo) Then
                If processRemote.IsBeingDebugged Then
                    MsgBox(processToAttachTo & " on " & machineName & " is already being debugged")
                Else
                    processRemote.Attach2(dbgeng)
                End If
                attached = True
            End If
        Next
        If Not attached Then
            MsgBox(processToAttachTo & " is not running on " & machineName & ".")
        End If
    Catch ex As System.Exception
        MsgBox("Exception attempting to attach to " & transportQualifier & ": " & ex.Message)
    End Try
End Sub

答案 3 :(得分:0)

您可能需要查看gflags.exe。它的一个选项是运行的调试器,附加到特定可执行文件的每次调用。