func FillPidMetrics()

in metric/system/process/process_linux_common.go [110:165]


func FillPidMetrics(hostfs resolve.Resolver, pid int, state ProcState, filter func(string) bool) (ProcState, error) {
	// Memory Data
	var err error
	state.Memory, err = getMemData(hostfs, pid)
	if err != nil {
		return state, fmt.Errorf("error getting memory data for pid %d: %w", pid, err)
	}

	// CPU Data
	state.CPU, err = getCPUTime(hostfs, pid)
	if err != nil {
		return state, fmt.Errorf("error getting CPU data for pid %d: %w", pid, err)
	}

	// CLI args
	if len(state.Args) == 0 {
		state.Args, err = getArgs(hostfs, pid)
		if err != nil {
			return state, fmt.Errorf("error getting CLI args for pid %d: %w", pid, err)
		}

	}

	// FD metrics
	state.FD, err = getFDStats(hostfs, pid)
	if err != nil {
		return state, fmt.Errorf("error getting FD metrics for pid %d: %w", pid, err)
	}

	if state.Env == nil {
		// env vars
		state.Env, _ = getEnvData(hostfs, pid, filter)
	}

	state.Exe, state.Cwd, err = getProcStringData(hostfs, pid)
	// skip permission errors and file not found errors
	// see https://github.com/elastic/elastic-agent-system-metrics/issues/135 for a bit more context,
	// depending on the permissions/caps that this is running with, the /exe symlink may have different levels of permission restrictions.
	// A kernel proc will also return file not found.
	if err != nil && !errors.Is(err, os.ErrPermission) && !errors.Is(err, os.ErrNotExist) { // ignore permission errors
		return state, fmt.Errorf("error getting metadata for pid %d: %w", pid, err)
	}

	state.Username, err = getUser(hostfs, pid)
	if err != nil {
		return state, fmt.Errorf("error creating username for pid %d: %w", pid, err)
	}

	// the /proc/[pid]/io metrics require SYS_PTRACE when run from inside docker
	state.IO, err = getIOData(hostfs, pid)
	if err != nil {
		return state, NonFatalErr{Err: fmt.Errorf("/io unavailable; if running inside a container, use SYS_PTRACE: %w", err)}
	}

	return state, nil
}