forked from influxdata/telegraf
-
Notifications
You must be signed in to change notification settings - Fork 0
/
linux_sysctl_fs.go
119 lines (100 loc) · 2.45 KB
/
linux_sysctl_fs.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
package linux_sysctl_fs
import (
"bytes"
"errors"
"io/ioutil"
"os"
"strconv"
"path"
"github.com/influxdata/telegraf"
"github.com/influxdata/telegraf/plugins/inputs"
)
// https://www.kernel.org/doc/Documentation/sysctl/fs.txt
type SysctlFS struct {
path string
}
var sysctlFSDescription = `Provides Linux sysctl fs metrics`
var sysctlFSSampleConfig = ``
func (sfs SysctlFS) Description() string {
return sysctlFSDescription
}
func (sfs SysctlFS) SampleConfig() string {
return sysctlFSSampleConfig
}
func (sfs *SysctlFS) gatherList(file string, fields map[string]interface{}, fieldNames ...string) error {
bs, err := ioutil.ReadFile(sfs.path + "/" + file)
if err != nil {
// Ignore non-existing entries
if errors.Is(err, os.ErrNotExist) {
return nil
}
return err
}
bsplit := bytes.Split(bytes.TrimRight(bs, "\n"), []byte{'\t'})
for i, name := range fieldNames {
if i >= len(bsplit) {
break
}
if name == "" {
continue
}
v, err := strconv.ParseUint(string(bsplit[i]), 10, 64)
if err != nil {
return err
}
fields[name] = v
}
return nil
}
func (sfs *SysctlFS) gatherOne(name string, fields map[string]interface{}) error {
bs, err := ioutil.ReadFile(sfs.path + "/" + name)
if err != nil {
// Ignore non-existing entries
if errors.Is(err, os.ErrNotExist) {
return nil
}
return err
}
v, err := strconv.ParseUint(string(bytes.TrimRight(bs, "\n")), 10, 64)
if err != nil {
return err
}
fields[name] = v
return nil
}
func (sfs *SysctlFS) Gather(acc telegraf.Accumulator) error {
fields := map[string]interface{}{}
for _, n := range []string{"aio-nr", "aio-max-nr", "dquot-nr", "dquot-max", "super-nr", "super-max"} {
if err := sfs.gatherOne(n, fields); err != nil {
return err
}
}
err := sfs.gatherList("inode-state", fields, "inode-nr", "inode-free-nr", "inode-preshrink-nr")
if err != nil {
return err
}
err = sfs.gatherList("dentry-state", fields, "dentry-nr", "dentry-unused-nr", "dentry-age-limit", "dentry-want-pages")
if err != nil {
return err
}
err = sfs.gatherList("file-nr", fields, "file-nr", "", "file-max")
if err != nil {
return err
}
acc.AddFields("linux_sysctl_fs", fields, nil)
return nil
}
func GetHostProc() string {
procPath := "/proc"
if os.Getenv("HOST_PROC") != "" {
procPath = os.Getenv("HOST_PROC")
}
return procPath
}
func init() {
inputs.Add("linux_sysctl_fs", func() telegraf.Input {
return &SysctlFS{
path: path.Join(GetHostProc(), "/sys/fs"),
}
})
}