Jump to content

How to Get the Command Line that a Running Process was Ran With?


Zohar
 Share

Recommended Posts

Hi

 

If you run ProcessExplorer, and add a column called "Command Line",

(can be found via RightClicking the Column Headers, and going to the Process Image tab)

you can see the command that the process was started with.

 

How can I get it programmatically inside AutoIt, for a process which I have its PID?

 

Thank you

Link to comment
Share on other sites

I would think you could just use ProcessList

https://www.autoitscript.com/autoit3/docs/functions/ProcessList.htm

If you already know the pid then you can compare it to the array created by processList (remember to use a loop so if a new process starts then it will include it in the array).

Share what you have for getting the PID (code)

Edited by computergroove

Get Scite to add a popup when you use a 3rd party UDF -> http://www.autoitscript.com/autoit3/scite/docs/SciTE4AutoIt3/user-calltip-manager.html

Link to comment
Share on other sites

You could use WMI to retrieve the CommandLine.  Change the value of $PID in the example below for a demo.

; Generated by AutoIt Scriptomatic
$wbemFlagReturnImmediately = 0x10
$wbemFlagForwardOnly = 0x20
$colItems = ""
$strComputer = "localhost"
$PID = "0"
$Output=""
$Output = $Output & "Computer: " & $strComputer  & @CRLF
$Output = $Output & "==========================================" & @CRLF
$objWMIService = ObjGet("winmgmts:\\" & $strComputer & "\root\CIMV2")
$colItems = $objWMIService.ExecQuery("SELECT * FROM Win32_Process WHERE ProcessID=" & $PID, "WQL", _
                                          $wbemFlagReturnImmediately + $wbemFlagForwardOnly)
If IsObj($colItems) then
   For $objItem In $colItems
      $Output = $Output & "Caption: " & $objItem.Caption & @CRLF
      $Output = $Output & "CommandLine: " & $objItem.CommandLine & @CRLF
      $Output = $Output & "ProcessId: " & $objItem.ProcessId & @CRLF
      if Msgbox(1,"WMI Output",$Output) = 2 then ExitLoop
      $Output=""
   Next
Else
   Msgbox(0,"WMI Output","No WMI Objects Found for class: " & "Win32_Process" )
Endif
Link to comment
Share on other sites

$PID = @AutoItPID ; just to pick a PID

$oWMI = ObjGet("winmgmts:\\" & @ComputerName & "\root\CIMV2")
If @error Then
    RunWait(@ComSpec & ' /c net start winmgmt  ', '', @SW_HIDE)
    RunWait(@ComSpec & ' /c net continue winmgmt  ', '', @SW_HIDE)
    $oWMI = ObjGet("winmgmts:\\" & @ComputerName & "\root\CIMV2")
EndIf
$oProcesses = $oWMI.ExecQuery("SELECT * FROM Win32_Process", "WQL", 0x30)
For $oProcess In $oProcesses
    If $oProcess.ProcessId = $PID Then ExitLoop
Next
MsgBox(262144, Default, $oProcess.CommandLine, 0)

Edit: spudw2k was quicker :x

Edited by Exit

App: Au3toCmd              UDF: _SingleScript()                             

Link to comment
Share on other sites

Or just check out

_WinAPI_GetProcessCommandLine 

function in the help file.

Br,

UEZ

Edited by UEZ

Please don't send me any personal message and ask for support! I will not reply!

Selection of finest graphical examples at Codepen.io

The own fart smells best!
Her 'sikim hıyar' diyene bir avuç tuz alıp koşma!
¯\_(ツ)_/¯  ٩(●̮̮̃•̃)۶ ٩(-̮̮̃-̃)۶ૐ

Link to comment
Share on other sites

Thank you all

 

Or just check out

_WinAPI_GetProcessCommandLine 

function in the help file.

Br,

UEZ

 

I cannot find this function in the help file.

I assume it's because I am not using the latest version..

I use v3.3.6.1..
 

Link to comment
Share on other sites

Thank you all

 

 

I cannot find this function in the help file.

I assume it's because I am not using the latest version..

I use v3.3.6.1..

 

Yes, it's because you're using a very old version, so that function isn't in there. _WinAPIEx was added to the UDFs back in December 2013 to version 3.3.10.0.

If I posted any code, assume that code was written using the latest release version unless stated otherwise. Also, if it doesn't work on XP I can't help with that because I don't have access to XP, and I'm not going to.
Give a programmer the correct code and he can do his work for a day. Teach a programmer to debug and he can do his work for a lifetime - by Chirag Gude
How to ask questions the smart way!

I hereby grant any person the right to use any code I post, that I am the original author of, on the autoitscript.com forums, unless I've specifically stated otherwise in the code or the thread post. If you do use my code all I ask, as a courtesy, is to make note of where you got it from.

Back up and restore Windows user files _Array.au3 - Modified array functions that include support for 2D arrays.  -  ColorChooser - An add-on for SciTE that pops up a color dialog so you can select and paste a color code into a script.  -  Customizable Splashscreen GUI w/Progress Bar - Create a custom "splash screen" GUI with a progress bar and custom label.  -  _FileGetProperty - Retrieve the properties of a file  -  SciTE Toolbar - A toolbar demo for use with the SciTE editor  -  GUIRegisterMsg demo - Demo script to show how to use the Windows messages to interact with controls and your GUI.  -   Latin Square password generator

Link to comment
Share on other sites

OK I understand.

BTW, maybe I should tell you what is the bigger picture.

I am writing a small function that will prevent more than 1 instance of a script running.

the code to do it is quite simple:

Func    CheckIfAnotherInstanceLikeMeExists()
Local   $Array_ProcessList  =ProcessList(@ScriptName)
Return ($Array_ProcessList[0][0]>1)
EndFunc

This code resides in a Common UDF that I created, and use among my scripts.

 

The problem:

It works for compiled scripts, but not for not-yet-compiled(au3) scripts.

Why?

Because compiled scripts have their process name like the name of the script, for example "SomeScript.exe".

When scripts that are still in source are ran, their process name is "AutoIt3.exe".

So I want my function to work also if the script is not compiled yet.

I found via ProcessExplorer that the CommandLine data holds the name of the script.

But is there another way to do it?

Edited by Zohar
Link to comment
Share on other sites

Something like this ?

#include <WinAPIProc.au3>

$iPID = @AutoItPID
$sFullExe = @AutoItExe
$sExe = StringRegExpReplace($sFullExe, ".*\\", "")

$aProcessList = ProcessList($sExe)
For $i = 1 To $aProcessList[0][0]
    If $aProcessList[$i][1] = $iPID Then ContinueLoop
    $sFileName = _WinAPI_GetProcessFileName($aProcessList[$i][1])
    If $sFileName = $sFullExe Then
        ConsoleWrite("Launched two times !")
        Exit
    EndIf
Next
Link to comment
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
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...