Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Check if a process exists in go way

Tags:

process

go

If I have the PID of a process, is os.FindProcess enough to test for the existing of the process? I mean if it returns err can I assume that it's terminated (or killed)?

Edit:

I've just wrote a wrapper function around kill -s 0 (old-style bash process testing). This works without any problem, but I'm still happy if there is other solutions (done with go libraries) to this problem.:

func checkPid(pid int) bool {
    out, err := exec.Command("kill", "-s", "0", strconv.Itoa(pid)).CombinedOutput()
    if err != nil {
        log.Println(err)
    }

    if string(out) == "" {
        return true // pid exist
    }
    return false
}
like image 823
Fatih Arslan Avatar asked Mar 04 '13 14:03

Fatih Arslan


People also ask

How do I check if a PID exists?

The easiest way to find out if process is running is run ps aux command and grep process name. If you got output along with process name/pid, your process is running.

How get PID process details?

In this quick article, we've explored how to get the name and the command line of a given PID in the Linux command line. The ps -p <PID> command is pretty straightforward to get the process information of a PID. Alternatively, we can also access the special /proc/PID directory to retrieve process information.

What is the PID in ps?

The ps command shows the process identification number (listed under PID ) for each process you own, which is created after you type a command. This command also shows you the terminal from which it was started ( TTY ), the cpu time it has used so far ( TIME ), and the command it is performing ( COMMAND ).


2 Answers

Here is the traditional unix way to see if a process is alive - send it a signal of 0 (like you did with your bash example).

From kill(2):

   If  sig  is 0, then no signal is sent, but error checking is still per‐
   formed; this can be used to check for the existence of a process ID  or
   process group ID.

And translated into Go

package main

import (
    "fmt"
    "log"
    "os"
    "strconv"
    "syscall"
)

func main() {
    for _, p := range os.Args[1:] {
        pid, err := strconv.ParseInt(p, 10, 64)
        if err != nil {
            log.Fatal(err)
        }
        process, err := os.FindProcess(int(pid))
        if err != nil {
            fmt.Printf("Failed to find process: %s\n", err)
        } else {
            err := process.Signal(syscall.Signal(0))
            fmt.Printf("process.Signal on pid %d returned: %v\n", pid, err)
        }

    }
}

When you run it you get this, showing that process 123 is dead, process 1 is alive but not owned by you and process 12606 is alive and owned by you.

$ ./kill 1 $$ 123
process.Signal on pid 1 returned: operation not permitted
process.Signal on pid 12606 returned: <nil>
process.Signal on pid 123 returned: no such process
like image 134
Nick Craig-Wood Avatar answered Oct 09 '22 10:10

Nick Craig-Wood


On unix like systems (linux, freebsd, etc) os.FindProcess will never return an error. I don't know what happens on Windows. This means you won't know if the PID is correct until you try to use the *os.Process for something.

You can look at the code here.

like image 20
Stephen Weinberg Avatar answered Oct 09 '22 10:10

Stephen Weinberg