Sign in to follow this  
Followers 0
Naveed

List Running Tasks on Remote Machine

8 posts in this topic

Hi guys, i am stuck with this piece of code and its driving me nuts....aaaargh..

I am trying to list the tasks running on a remote machine into a gui and i need to figure out how to display the results on the gui and separate the tasks so i can end them individually, i have got half way there and have hit a brick wall.

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <array.au3>
#include <File.au3>
#include <Constants.au3>

GLobal $in

Func guiexample()
    Local $msg
    Opt("GUIOnEventMode", 1)
    GUICreate("My GUI")
    GUISetState(@SW_SHOW)
    $test = GUICtrlCreateButton("List Tasks",20,20,100,100)
    GUICtrlSetOnEvent($test,"listtasks")
    $test2 = GUICtrlCreateButton("Kill Tasks",120,20,100,100)
    GUICtrlSetOnEvent($test2,"Killtask")
    GUISetOnEvent($GUI_EVENT_CLOSE,"exit1")
    $in = GUICtrlCreateInput("",20,130,200,200)


    While 1
        $msg = GUIGetMsg()

        If $msg = $GUI_EVENT_CLOSE Then ExitLoop
    WEnd
    GUIDelete()
EndFunc

guiexample()

Func listtasks()
$foo = Run("cmd.exe /c" & "tasklist", @SystemDir, @SW_HIDE, $STDERR_CHILD + $stdout_child)
        Local $line
        While 1
            $line = StdoutRead($foo)
            If @error Then ExitLoop
            $txt = FileOpen("test.txt",2)
            FileWrite($txt,$line)
            Sleep(2000)
        WEnd
            Dim $tx1
            $file = _FileReadToArray("test.txt",$tx1)
            _ArrayDisplay($tx1,"listview")
            For $i = $tx1[5] To $tx1[0] Step 1
            GUICtrlSetData($in, $i)
            Next
            FileClose($txt)
EndFunc

Func Killtask()
    Run("cmd.exe /c" & "taskkill /s  /IM $task", "")
EndFunc

Func exit1()
    Exit
EndFunc

Can somebody point me in the right direction, thanks in advance.

Nav

Share this post


Link to post
Share on other sites



Ok Guys i am one step closer, but i need some help with the last hurdle......

I have managed to get the tasks through the WMI but i need some help with adding them to a listview box.

I can get the results to display in a message box but need to add them to listview box

#include <GUIConstantsEx.au3>

    Opt("GUIOnEventMode", 1)
    GUICreate("My GUI",600,600)
    GUISetState(@SW_SHOW)
    $test = GUICtrlCreateButton("List Tasks",20,20,100,100)
    GUICtrlSetOnEvent($test,"gettasks")
    $test2 = GUICtrlCreateButton("Kill Tasks",120,20,100,100)
    GUICtrlSetOnEvent($test2,"")
    GUISetOnEvent($GUI_EVENT_CLOSE,"exit1")
    $in = GUICtrlCreateInput("",20,130,200,200)
    $in1 = GUICtrlCreateListView("",230,130,200,200)

Func gettasks()
$wbemFlagReturnImmediately = 0x10
$wbemFlagForwardOnly = 0x20
$strComputer = "localhost"
$objWMIService = ObjGet("winmgmts:\\" & $strComputer & "\root\CIMV2")
$colItems = $objWMIService.ExecQuery("SELECT * FROM Win32_Process", "WQL", _
                                          $wbemFlagReturnImmediately + $wbemFlagForwardOnly)

If IsObj($colItems) then
   Local $Object_Flag = 0
   For $objItem In $colItems
      $Object_Flag = 1
      $Caption = $objItem.Caption
      MsgBox(1,"",$objItem.Caption)

  ;if Msgbox(1,"WMI Output",$Output) = 2 then ExitLoop
   Next
  ;If $Object_Flag = 0 Then Msgbox(1,"WMI Output",$OutputTitle)
Else
   Msgbox(0,"WMI Output","No WMI Objects Found for class: " & "Win32_Process" )
Endif

EndFunc

While 1
        $msg = GUIGetMsg()

        If $msg = $GUI_EVENT_CLOSE Then ExitLoop
    WEnd

Func exit1()
    Exit
EndFunc

Any help will be much appreciated...

Share this post


Link to post
Share on other sites

Hi,

try this:

#include <GUIConstantsEx.au3>
#include <array.au3>

;Opt("GUIOnEventMode", 1)
GUICreate("My GUI",600,600)
GUISetState(@SW_SHOW)
$test = GUICtrlCreateButton("List Tasks",20,20,100,100)
;GUICtrlSetOnEvent($test,"gettasks")
$test2 = GUICtrlCreateButton("Kill Tasks",120,20,100,100)
;GUICtrlSetOnEvent($test2,"")
;GUISetOnEvent($GUI_EVENT_CLOSE,"exit1")
$in = GUICtrlCreateInput("",20,130,200,200)
Global $in1 = GUICtrlCreateListView("Tasks                               ",230,130,200,200)

While 1
    $msg = GUIGetMsg()
        Select
            Case $msg = $GUI_EVENT_CLOSE
                Exit
            Case $msg = $test
                gettasks ()
            Case $msg = $test2
                exit1 ()
        EndSelect
WEnd

Func exit1()
    Exit
EndFunc

;use gettask ("Hostname") to get processes from other computer
Func gettasks($strComputer = "localhost")
    $count = 1
    Local $arTasks [1]
    $wbemFlagReturnImmediately = 0x10
    $wbemFlagForwardOnly = 0x20
    $objWMIService = ObjGet("winmgmts:\\" & $strComputer & "\root\CIMV2")
    $colItems = $objWMIService.ExecQuery("SELECT * FROM Win32_Process", "WQL", _
                                          $wbemFlagReturnImmediately + $wbemFlagForwardOnly)

    If IsObj($colItems) then
        Local $Object_Flag = 0
        For $objItem In $colItems
            $Object_Flag = 1
            ReDim $arTasks [$count]
            $arTasks [$count - 1] = $objItem.Caption
            $count += 1
            ;GUICtrlCreateListViewItem ($objitem.Caption, $in1)
            ;if Msgbox(1,"WMI Output",$Output) = 2 then ExitLoop
        Next
        _ArraySort ($artasks)
        For $i = 0 To UBound ($artasks) - 1
            GUICtrlCreateListViewItem ($artasks [$i], $in1)
        Next
        ;If $Object_Flag = 0 Then Msgbox(1,"WMI Output",$OutputTitle)
    Else
        Msgbox(0,"WMI Output","No WMI Objects Found for class: " & "Win32_Process" )
    Endif
EndFunc

;-))

Stefan

Share this post


Link to post
Share on other sites

Thanks Stefan, i went with something similair in the end here is what i got, however now when i try to read the listview item and its text when selected it fails, any ideas??

#include <GUIConstantsEx.au3>
#Include <GuiListView.au3>

Opt("GUIOnEventMode", 1)
Global $in1

GUICreate("My GUI",220,700)
GUISetState(@SW_SHOW)
$list = GUICtrlCreateButton("List Tasks",10,10,100,30)
GUICtrlSetOnEvent($list,"gettasks")
$kill = GUICtrlCreateButton("Kill Tasks",110,10,100,30)
GUICtrlSetOnEvent($kill,"kill")
GUISetOnEvent($GUI_EVENT_CLOSE,"exit1")
$in1 = GUICtrlCreateListView("",10,45,200,600)
_GUICtrlListView_InsertColumn($in1, 0, "Tasks", 200)
GUICtrlSetFont($in1,10,"","","cambria")

Func kill()
    MsgBox(1,"",_GUICtrlListView_GetItemSelected($in1, 1),10)
EndFunc

Func gettasks()
$wbemFlagReturnImmediately = 0x10
$wbemFlagForwardOnly = 0x20
$strComputer = "localhost"
$objWMIService = ObjGet("winmgmts:\\" & $strComputer & "\root\CIMV2")
$colItems = $objWMIService.ExecQuery("SELECT * FROM Win32_Process", "WQL", _
                                          $wbemFlagReturnImmediately + $wbemFlagForwardOnly)

If IsObj($colItems) then
   Local $Object_Flag = 0
   For $objItem In $colItems
      $Object_Flag = 1
      $Caption = $objItem.Caption
      _GUICtrlListView_AddItem($in1, $objItem.caption)
   Next
Else
   Msgbox(0,"WMI Output","No WMI Objects Found for class: " & "Win32_Process" )
Endif

EndFunc

While 1
        $msg = GUIGetMsg()

        If $msg = $GUI_EVENT_CLOSE Then ExitLoop
    WEnd

Func exit1()
    Exit
EndFunc

I need to be able to read the text of the selected item as i will be passing that to a taskkill command for the remote machine. any ideas???

Thanks in advance....

Share this post


Link to post
Share on other sites

#5 ·  Posted (edited)

Hi,

you try to check, if item 1 is selected. Therefore you only get True or False (i guess mostly false :mellow: ) in your msgbox.

See helpfile function _GUICtrlListView_GetItemSelected ().

Try this:

Func kill()
    $arselect = _GUICtrlListView_GetSelectedIndices ($in1, "True")
    If $select [0] = "" Then 
        MsgBox (0,"Error", "No Selection")
    Else
        MsgBox(1,"",_GUICtrlListView_GetItemText($in1, $arselect [1]),5)
    EndIf
EndFunc

If you want to allow multi selection in your listview, you have to loop over array $arselect:

For $i = 1 To $arselect [0]
    MsgBox(1,"",_GUICtrlListView_GetItemText($in1, $arselect [$i]),5)
Next

in the else tree.

;-))

Stefan

Edited by 99ojo

Share this post


Link to post
Share on other sites

With 99ojo's suggestions, the below works for me. Prompts the user for the asset number right off the bat. Only thing that I would add would be some sort of loop, so if the user clicks List Tasks again, they get prompted for a new asset:

#include <GUIConstantsEx.au3>
#include <GUIListView.au3>
#include <array.au3>

$strComputer = InputBox("Which asset", "Please enter asset tag")
GUICreate("My GUI",600,600)
GUISetState(@SW_SHOW)
$test = GUICtrlCreateButton("List Tasks",20,20,100,100)
$test2 = GUICtrlCreateButton("Kill Tasks",120,20,100,100)
$test3 = GUICtrlCreateButton("Exit",220,20,100,100)
$in = GUICtrlCreateInput("",20,130,200,200)
Global $in1 = GUICtrlCreateListView("Tasks                              ",230,130,200,200)

While 1
    $msg = GUIGetMsg()
        Select
            Case $msg = $GUI_EVENT_CLOSE
                Exit
            Case $msg = $test
                gettasks ()
            Case $msg = $test2
                exit1 ()
   Case $msg = $test3
    Exit
        EndSelect
WEnd

Func exit1($strComputer = $strComputer)
    $arselect = _GUICtrlListView_GetSelectedIndices ($in1, "True")
    If $arselect [0] = "" Then 
        MsgBox (0,"Error", "No Selection")
    Else
        $process = _GUICtrlListView_GetItemText($in1, $arselect [1])
  RunWait( "taskkill /s " & $strComputer & " /IM " & $process )
    EndIf
EndFunc

Func gettasks($strComputer = $strComputer)
    $count = 1
    Local $arTasks [1]
    $wbemFlagReturnImmediately = 0x10
    $wbemFlagForwardOnly = 0x20
    $objWMIService = ObjGet("winmgmts:\\" & $strComputer & "\root\CIMV2")
    $colItems = $objWMIService.ExecQuery("SELECT * FROM Win32_Process", "WQL", _
                                        $wbemFlagReturnImmediately + $wbemFlagForwardOnly)

    If IsObj($colItems) then
        Local $Object_Flag = 0
        For $objItem In $colItems
            $Object_Flag = 1
            ReDim $arTasks [$count]
            $arTasks [$count - 1] = $objItem.Caption
            $count += 1
        Next
        _ArraySort ($artasks)
        For $i = 0 To UBound ($artasks) - 1
            GUICtrlCreateListViewItem ($artasks [$i], $in1)
        Next
    Else
        Msgbox(0,"WMI Output","No WMI Objects Found for class: " & "Win32_Process" )
    Endif
EndFunc

√-1 2^3 ∑ π, and it was delicious!

Share this post


Link to post
Share on other sites

Thanks for all your help Guys :mellow:

Got it working, here is the finished product.

#include <GUIConstantsEx.au3>
#include <GuiListView.au3>

Opt("GUIOnEventMode", 1)
Global $in1

GUICreate("Remote Task Manager", 220, 720)
GUISetState(@SW_SHOW)
$assetfield = GUICtrlCreateInput("", 10, 10, 200, 20)
$list = GUICtrlCreateButton("List Tasks", 10, 40, 100, 30)
GUICtrlSetOnEvent($list, "gettasks")
$kill = GUICtrlCreateButton("End Task", 110, 40, 100, 30)
GUICtrlSetOnEvent($kill, "kill")
GUISetOnEvent($GUI_EVENT_CLOSE, "exit1")
$in1 = GUICtrlCreateListView("", 10, 75, 200, 600)
$col = _GUICtrlListView_InsertColumn($in1, 0, "Tasks", 200)
GUICtrlSetFont($in1, 10, "", "", "cambria")

Func kill()
    $arselect = _GUICtrlListView_GetSelectedIndices($in1, "True")
    If $arselect[0] = "" Then
        MsgBox(0, "Error", "No Selection")
    Else
        $process = _GUICtrlListView_GetItemText($in1, $arselect[1])
        RunWait("taskkill /s " & GUICtrlRead($assetfield) & " /IM " & $process)
    EndIf
    Sleep(1000)
    gettasks()
EndFunc   ;==>kill

$close = GUICtrlCreateButton("Close", 10, 680, 200, 30)
GUICtrlSetOnEvent($close, "exit1")

Func gettasks()
    If StringLen(GUICtrlRead($assetfield)) = 0 Then
        MsgBox(1, "Blank", "Asset Number Blank. Please provide the assett number")
    Else
        _GUICtrlListView_DeleteAllItems(GUICtrlGetHandle($in1))
        $wbemFlagReturnImmediately = 0x10
        $wbemFlagForwardOnly = 0x20
        $strComputer = GUICtrlRead($assetfield)
        $objWMIService = ObjGet("winmgmts:\\" & $strComputer & "\root\CIMV2")
        $colItems = $objWMIService.ExecQuery("SELECT * FROM Win32_Process", "WQL", _
                $wbemFlagReturnImmediately + $wbemFlagForwardOnly)

        If IsObj($colItems) Then
            Local $Object_Flag = 0
            For $objItem In $colItems
                $Object_Flag = 1
                $Caption = $objItem.Caption
                _GUICtrlListView_AddItem($in1, $objItem.caption)
            Next
        Else
            MsgBox(0, "WMI Output", "No WMI Objects Found for class: " & "Win32_Process")
        EndIf
    EndIf
EndFunc   ;==>gettasks

While 1
    $msg = GUIGetMsg()

    If $msg = $GUI_EVENT_CLOSE Then ExitLoop
WEnd
Func exit1()
    Exit
EndFunc   ;==>exit1

Thanks Once Again.

Nav

Share this post


Link to post
Share on other sites

#8 ·  Posted (edited)

Hello there...eventually this could be of some interest:

Your version only works perfect if locally logged on user account is existing on the remote machine and has permissions there. Here an example how to check for a certain service on a remote machine using an other than the locally logged in user:

Global $h_wbemFlagReturnImmediately = 0x10
Global $h_wbemFlagForwardOnly = 0x20
Global $h_wbemFlags = $h_wbemFlagReturnImmediately + $h_wbemFlagForwardOnly

Global $a_Hosts[3] = ["HOST-1", "HOST-2", "HOST-3"]         ; change here to match your environment
Global $a_Processes[4] = ["process-1.exe", "process-2.exe", "process-3.exe", "regedit.exe"]
Global $s_AdminUser = "Administrator"                       ; change here to match your environment
Global $s_AdminPW = "password"                              ; change here to match your environment


For $i=0 To UBound($a_Hosts) -1
    $s_ProcessRunning = _CheckRemoteProcesses($a_Hosts[$i], $a_Processes, $s_AdminUser, $s_AdminPW)
Next


Func _CheckRemoteProcesses($s_Host, $a_Processes, $s_AdminUser, $s_AdminPW)

    Local $o_RemoteWMIService, $o_Process, $o_colProcesses
    Local $s_ProcessExists = "NO"
    Local $i_Result = 0, $s_ProcessRunning

    ; Create an object for the remote host's WMI interface and authenticate against it
    $o_SWbemLocator = ObjCreate("WbemScripting.SWbemLocator")
    If IsObj($o_SWbemLocator) Then
        $o_RemoteWMIService = $o_SWbemLocator.ConnectServer($s_Host, "root\CIMV2", $s_AdminUser, $s_AdminPW)
        If IsObj($o_RemoteWMIService) Then
            $o_colProcesses = $o_RemoteWMIService.ExecQuery("Select * from Win32_Process", "WQL", $h_wbemFlags)
            If IsObj($o_colProcesses) Then
                For $o_elements In $o_colProcesses
                    For $i=0 To UBound($a_Processes) -1
                        If $o_elements.Name == $a_Processes[$i] Then
                            ConsoleWrite(@CRLF & $s_Host & ": Process " & $a_Processes[$i] & " exists." & @CRLF)
                            $s_ProcessExists = "YES"
                        EndIf
                    Next
                Next
            EndIf
            If $s_ProcessExists = "NO" Then ConsoleWrite(@CRLF & $s_Host & ": No process found." & @CRLF)
            Return $s_ProcessExists
        Else
            ConsoleWrite(@CRLF & $s_Host & ": Probably wrong password or account disabled/inactive.")
            Return $s_ProcessExists = "Error"
        EndIf
    Else
        ConsoleWrite(@CRLF & ": Can't setup SWbemLocator object.")
        Return $s_ProcessExists = "Error"
    EndIf

EndFunc   ;==>_CheckRemoteProcesses

Best Regards,

Chris

Edited by cherdeg

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now
Sign in to follow this  
Followers 0