Working with Processes



FOR-PROCS: "proc_pattern" <...> ;FOR-PROCS

This is a special cycle which can be used to perform operations not just on single processes, but entire groups of processes matching a specified mask; commands included in the body of FOR-PROCS loop will be applied to each of these processes.

It works in this way: if there are, for example, five processes matching a certain mask, then FOR-PROCS: loop will be automatically executed five times and each time values of the variables %FOUND-PROC% and %FOUND-PID% will be renewed; these variables contains a name of last found process and its Process ID (PID) respectively.

Example:

#( test_for_processes
\ printing to console names of all running processes
NoActive
Action:
    FOR-PROCS: "*.exe"
        FOUND-PROC TYPE CR
    ;FOR-PROCS
)#

That means that on each iteration of the loop you get access to the name and PID of the next process matching a specified mask, and now it only remains to perform the required action with this process (e.g. stop it or assign a desired priority etc.) or to perform another check in order to decide what to do with this process.

Example:

#( test_for_processes1
\ displaying a query and ending, one by one,  
\ all found processes of Internet Explorer
NoActive
Action:
    FOR-PROCS: "iexplore.exe"
        QUERY: "End process %FOUND-PROC%?"
        IF
            KILL: "%FOUND-PID%"
        THEN
    ;FOR-PROCS
)#

KILL: "proc_pattern"

This word terminates a specified process. It can take as its argument a mask of a process name (which is normally the same as the name of the executable file which is used to start this process) or a string containing numerical process identifier (PID), which is stored in predefined variable PROC-ID immediately after a program has been started.

By using a process identifier as an argument, you can terminate a particular process even if there are several instances of the same program running, i. e. there are several processes with the same name. Please note that variable PROC-ID is filled each time a when a program is successfully started by words START-APP, START-APPW or QSTART-APP, but if the process we want to stop was started by word START-APPW, you shouldn't use the value stored in PROC-ID, for in this case this variable would contain PID of the process which was already stopped.

KILL: can also be used with predefined variable %WATCH-PROC-ID%, in which words WatchProc:/WatchProcStop: store the PID of the process they have found.

Examples:

\ using process name
KILL: "opera.exe"
KILL: "notepad.exe"
KILL: "*pad.exe"
\ using process identifier (PID)
KILL: "2121"
KILL: "%PROC-ID%"
   
#( test_proc_id
NoActive
VARIABLE my_notepad_id
Action:
    START-APP: notepad.exe
    PAUSE: 1000
    START-APP: notepad.exe
    PROC-ID my_notepad_id !
    PAUSE: 1000
    START-APP: notepad.exe
    \ ... something useful here
    \ terminating the second instance of Notepad
    KILL: "%my_notepad_id @%"
)#

There also exists a postfix version of this word:

S" opera.exe" KILL
S" 2121" KILL

kill ( pid -- )

This postfix word terminates a process accepting its PID as an argument. Since word kill takes a number as its argument, you won't have to convert a number returned by PROC-ID or WATCH-PROC-ID into a string:

386 kill
PROC-ID kill
my_proc_id @ kill

PROC-TIME: "proc_pattern"

Puts on stack the time (number of seconds) during which a specified process has been working.

Works only in WinNT/2000/XP.


ProcActiveTime ( pid -- ms)

Puts on stack the time (double number - number of milliseconds) during which the specified process has been working. Takes a PID as its argument.

Example:

#( test_proctime
NoActive
Action:
    S" notepad.exe" PROC-EXIST? ?DUP
    IF
        \ printing the time of work to console
        ProcActiveTime D>S . CR
    ELSE
        MSG: "Notepad is not started!"
    THEN
)#

PROC-EXIST: "proc_pattern"

Returns TRUE (-1) if there exists a process matching a specified pattern. As an argument for PROC-EXIST: one should normally use the name of the executable file that starts a process.

Example:

Rule: PROC-EXIST: "winword.exe"

A process can be identified not only by the file name, but also by full path to the application file. In order to do that, use option PROC-FULLPATH. If the process name contains at least one backslash ('\'), nnCron will automatically try to identify it by the full path to its executable file.

Example:

Rule: PROC-FULLPATH PROC-EXIST: "C:\PROGRAM FILES\OPERA\opera.exe"
Rule: PROC-EXIST: "C:\PROGRAM FILES\OPERA\opera.exe"

If you want to find out PID of a process, use postfix word PROC-EXIST?

Example:

\ puts on stack PID of 'winword.exe'
S" winword.exe" PROC-EXIST?

PROC-FULLNAME ( pid - a u)
PROC-NAME ( pid - a u)

These postfix words get Process ID (PID) as their arguments and return a string with full/short process name. PROC-NAME returns a short process name (usually a name of the executable file, like notepad.exe), and PROC-FULLNAME returns the name of the executable file together with the full path to this file (c:\windows\system32\notepad.exe).

Example:

#( test_procname
WatchProc: "notepad.exe"
Action:
\ printing process short name to the console
WATCH-PROC-ID PROC-NAME TYPE CR
\ displaying a message with process full name
MSG: "%WATCH-PROC-ID PROC-FULLNAME%" 
)#

PROC-WAIT-IDLE ( pid -- )

This postfix word pauses the task until the specified process becomes idle. For example, you can use PROC-WAIT-IDLE when launching an application (START-APP:) if you want to make sure the application is fully loaded into computer memory before the task resumes it's work.

Example:

#( test_start_app
NoActive
Action:
    START-APP: your_prog.exe
    \ pausing the task until your_prog.exe is 
    \ fully loaded into computer memory
    PROC-ID PROC-WAIT-IDLE
    \ resuming the task
    \ ...
)#

proc_pattern is a process's name or name mask. Normally, a process name is the same as the name of executable file which is used to start this process. However, one can also use a full path to the executable file as a process name. In masks of process names or paths to executable files, you can use wildcard characters '*' and '?', or regular expressions between slashes: /<regexp>/.
If a mask contains at least one backslash ('\'), it will be compared with the full path of executable file.
Process identifiers also can be used as values for proc_pattern. (See PROC-ID, %WATCH-PROC-ID%).

Examples:

\ process name
PROC-EXIST: "notepad.exe"
\ mask of  process name
PROC-EXIST: "notepad*"
PROC-EXIST: "*pad.exe" \ masks of process names taking in account the full path PROC-EXIST: "*\notepad*" PROC-EXIST: "c:\*\notepad.exe" \ regular expression PROC-EXIST: "/(note)|(word)pad.exe/i" \ process identifier PROC-EXIST: "1116"
PROC-EXIST: "%WATCH-PROC-ID%"
PROC-EXIST: "%my_proc_id @%"

See also: