// getDetails fills in CPU, memory, FD usage, and command line details for the process. func (proc *Process) getDetails(cmdline string) error { proc.Mem = sigar.ProcMem{} if err := proc.Mem.Get(proc.Pid); err != nil { return fmt.Errorf("error getting process mem for pid=%d: %v", proc.Pid, err) } proc.Cpu = sigar.ProcTime{} if err := proc.Cpu.Get(proc.Pid); err != nil { return fmt.Errorf("error getting process cpu time for pid=%d: %v", proc.Pid, err) } if cmdline == "" { args := sigar.ProcArgs{} if err := args.Get(proc.Pid); err != nil && !sigar.IsNotImplemented(err) { return fmt.Errorf("error getting process arguments for pid=%d: %v", proc.Pid, err) } proc.CmdLine = strings.Join(args.List, " ") } else { proc.CmdLine = cmdline } if fd, err := getProcFDUsage(proc.Pid); err != nil { return fmt.Errorf("error getting process file descriptor usage for pid=%d: %v", proc.Pid, err) } else if fd != nil { proc.FD = *fd } return nil }
// getProcFDUsage returns file descriptor usage information for the process // identified by the given PID. If the feature is not implemented then nil // is returned with no error. If there is a permission error while reading the // data then nil is returned with no error (/proc/[pid]/fd requires root // permissions). Any other errors that occur are returned. func getProcFDUsage(pid int) (*sigar.ProcFDUsage, error) { fd := sigar.ProcFDUsage{} if err := fd.Get(pid); err != nil { switch { case sigar.IsNotImplemented(err): return nil, nil case os.IsPermission(err): return nil, nil default: return nil, err } } return &fd, nil }
// getProcFDUsage returns file descriptor usage information for the process // identified by the given PID. If the feature is not implemented then nil // is returned with no error. If there is a permission error while reading the // data then nil is returned with no error (/proc/[pid]/fd requires root // permissions). Any other errors that occur are returned. func getProcFDUsage(pid int) (*sigar.ProcFDUsage, error) { // It's not possible to collect FD usage from other processes on FreeBSD // due to linprocfs not exposing the information. if runtime.GOOS == "freebsd" && pid != os.Getpid() { return nil, nil } fd := sigar.ProcFDUsage{} if err := fd.Get(pid); err != nil { switch { case sigar.IsNotImplemented(err): return nil, nil case os.IsPermission(err): return nil, nil default: return nil, err } } return &fd, nil }