elastic / elastic-agent-system-metrics

Apache License 2.0
0 stars 22 forks source link

The process `GetSelf` method can produce incorrect results when used with an alternate hostfs #147

Closed fearful-symmetry closed 2 months ago

fearful-symmetry commented 2 months ago

Right now, process.GetSelf() fetches the pid of the process with os.Getpid() and then uses the alternate hostfs to fetch the metrics from /proc/GETPID/ There's a problem with this, which you can demonstrate with a small test:

func TestContainerPids(t *testing.T) {
    t.Logf("os.getpid: %d", os.Getpid())

    raw, err := os.ReadFile("/proc/self/stat")
    require.NoError(t, err)
    pid := strings.Split(string(raw), " ")[0]
    t.Logf("statfile: %s", pid)

    raw, err = os.ReadFile("/hostfs/proc/self/stat")
    require.NoError(t, err)
    pid = strings.Split(string(raw), " ")[0]
    t.Logf("statfile hostfs: %s", pid)
}

This returns:

    process_container_test.go:42: os.getpid: 16
    process_container_test.go:47: statfile: 16
    process_container_test.go:52: statfile hostfs: 3929281

The namespacing is actually smart enough to handle something like /hostfs/proc/self/, but if you do os.Getpid() and then pass that to /hostfs/proc, you'll get an invalid result.

On linux, when we're using hostfs, GetSelf() should use /hostfs/proc/self instead.