github.com/hinshun/containerd@v0.2.7/osutils/reaper.go (about) 1 // +build !windows 2 3 package osutils 4 5 import "syscall" 6 7 // Exit is the wait4 information from an exited process 8 type Exit struct { 9 Pid int 10 Status int 11 } 12 13 // Reap reaps all child processes for the calling process and returns their 14 // exit information 15 func Reap(wait bool) (exits []Exit, err error) { 16 var ( 17 ws syscall.WaitStatus 18 rus syscall.Rusage 19 ) 20 flag := syscall.WNOHANG 21 if wait { 22 flag = 0 23 } 24 for { 25 pid, err := syscall.Wait4(-1, &ws, flag, &rus) 26 if err != nil { 27 if err == syscall.ECHILD { 28 return exits, nil 29 } 30 return exits, err 31 } 32 if pid <= 0 { 33 return exits, nil 34 } 35 exits = append(exits, Exit{ 36 Pid: pid, 37 Status: exitStatus(ws), 38 }) 39 } 40 } 41 42 const exitSignalOffset = 128 43 44 // exitStatus returns the correct exit status for a process based on if it 45 // was signaled or exited cleanly 46 func exitStatus(status syscall.WaitStatus) int { 47 if status.Signaled() { 48 return exitSignalOffset + int(status.Signal()) 49 } 50 return status.ExitStatus() 51 }