]> arthur.barton.de Git - netdata.git/blob - charts.d/sensors.chart.sh
added documentation; minor adjustments to charts.d collectors
[netdata.git] / charts.d / sensors.chart.sh
1 #!/bin/sh
2
3 # sensors docs
4 # https://www.kernel.org/doc/Documentation/hwmon/sysfs-interface
5
6 # if this chart is called X.chart.sh, then all functions and global variables
7 # must start with X_
8
9 # the directory the kernel keeps sensor data
10 sensors_sys_dir="${NETDATA_HOST_PREFIX}/sys/devices"
11
12 # how deep in the tree to check for sensor data
13 sensors_sys_depth=10
14
15 # if set to 1, the script will overwrite internal
16 # script functions with code generated ones
17 # leave to 1, is faster
18 sensors_source_update=1
19
20 # how frequently to collect sensor data
21 # the default is to collect it at every iteration of charts.d
22 sensors_update_every=
23
24 sensors_find_all_files() {
25         find $1 -maxdepth $sensors_sys_depth -name \*_input -o -name temp 2>/dev/null
26 }
27
28 sensors_find_all_dirs() {
29         sensors_find_all_files $1 | while read
30         do
31                 dirname $REPLY
32         done | sort -u
33 }
34
35 # _check is called once, to find out if this chart should be enabled or not
36 sensors_check() {
37
38         # this should return:
39         #  - 0 to enable the chart
40         #  - 1 to disable the chart
41
42         [ ! -z "$( sensors_find_all_files $sensors_sys_dir )" ] && return 0
43         return 1
44 }
45
46 sensors_check_files() {
47         # we only need sensors that report a non-zero value
48
49         local f= v=
50         for f in $*
51         do
52                 [ ! -f "$f" ] && continue
53
54                 v="$( cat $f )"
55                 v=$(( v + 1 - 1 ))
56                 [ $v -ne 0 ] && echo "$f" && continue
57                 
58                 echo >&2 "charts.d: sensors: $f gives zero values"
59         done
60 }
61
62 sensors_check_temp_type() {
63         # valid temp types are 1 to 6
64         # disabled sensors have the value 0
65
66         local f= t= v=
67         for f in $*
68         do
69                 t=$( echo $f | sed "s|_input$|_type|g" )
70                 [ "$f" = "$t" ] && echo "$f" && continue
71                 [ ! -f "$t" ] && echo "$f" && continue
72
73                 v="$( cat $t )"
74                 v=$(( v + 1 - 1 ))
75                 [ $v -ne 0 ] && echo "$f" && continue
76
77                 echo >&2 "charts.d: sensors: $f is disabled"
78         done
79 }
80
81 # _create is called once, to create the charts
82 sensors_create() {
83         local path= dir= name= x= file= lfile= labelname= labelid= device= subsystem= id= type= mode= files= multiplier= divisor=
84
85         # we create a script with the source of the
86         # sensors_update() function
87         # - the highest speed we can achieve -
88         [ $sensors_source_update -eq 1 ] && echo >$TMP_DIR/sensors.sh "sensors_update() {"
89
90         for path in $( sensors_find_all_dirs $sensors_sys_dir | sort -u )
91         do
92                 dir=$( basename $path )
93                 device=
94                 subsystem=
95                 id=
96                 type=
97                 name=
98
99                 [ -h $path/device ] && device=$( readlink -f $path/device )
100                 [ ! -z "$device" ] && device=$( basename $device )
101                 [ -z "$device" ] && device="$dir"
102
103                 [ -h $path/subsystem ] && subsystem=$( readlink -f $path/subsystem )
104                 [ ! -z "$subsystem" ] && subsystem=$( basename $subsystem )
105                 [ -z "$subsystem" ] && subsystem="$dir"
106
107                 [ -f $path/name ] && name=$( cat $path/name )
108                 [ -z "$name" ] && name="$dir"
109
110                 [ -f $path/type ] && type=$( cat $path/type )
111                 [ -z "$type" ] && type="$dir"
112
113                 id="$( fixid "$device.$subsystem.$dir" )"
114
115                 echo >&2 "charts.d: sensors: on path='$path', dir='$dir', device='$device', subsystem='$subsystem', id='$id', name='$name'"
116
117                 for mode in temperature voltage fans power current energy humidity
118                 do
119                         files=
120                         multiplier=1
121                         divisor=1
122                         algorithm="absolute"
123
124                         case $mode in
125                                 temperature)
126                                         files="$( ls $path/temp*_input 2>/dev/null; ls $path/temp 2>/dev/null )"
127                                         files="$( sensors_check_files $files )"
128                                         files="$( sensors_check_temp_type $files )"
129                                         [ -z "$files" ] && continue
130                                         echo "CHART sensors.temp_$id '' '$name Temperature' 'Celcius' '$device' '' line 6000 $sensors_update_every"
131                                         echo >>$TMP_DIR/sensors.sh "echo \"BEGIN sensors.temp_$id \$1\""
132                                         divisor=1000
133                                         ;;
134
135                                 voltage)
136                                         files="$( ls $path/in*_input 2>/dev/null )"
137                                         files="$( sensors_check_files $files )"
138                                         [ -z "$files" ] && continue
139                                         echo "CHART sensors.volt_$id '' '$name Voltage' 'Volts' '$device' '' line 6001 $sensors_update_every"
140                                         echo >>$TMP_DIR/sensors.sh "echo \"BEGIN sensors.volt_$id \$1\""
141                                         divisor=1000
142                                         ;;
143
144                                 current)
145                                         files="$( ls $path/curr*_input 2>/dev/null )"
146                                         files="$( sensors_check_files $files )"
147                                         [ -z "$files" ] && continue
148                                         echo "CHART sensors.curr_$id '' '$name Current' 'Ampere' '$device' '' line 6002 $sensors_update_every"
149                                         echo >>$TMP_DIR/sensors.sh "echo \"BEGIN sensors.curr_$id \$1\""
150                                         divisor=1000
151                                         ;;
152
153                                 power)
154                                         files="$( ls $path/power*_input 2>/dev/null )"
155                                         files="$( sensors_check_files $files )"
156                                         [ -z "$files" ] && continue
157                                         echo "CHART sensors.power_$id '' '$name Power' 'Watt' '$device' '' line 6003 $sensors_update_every"
158                                         echo >>$TMP_DIR/sensors.sh "echo \"BEGIN sensors.power_$id \$1\""
159                                         divisor=1000000
160                                         ;;
161
162                                 fans)
163                                         files="$( ls $path/fan*_input 2>/dev/null )"
164                                         files="$( sensors_check_files $files )"
165                                         [ -z "$files" ] && continue
166                                         echo "CHART sensors.fan_$id '' '$name Fans Speed' 'Rotations / Minute' '$device' '' line 6004 $sensors_update_every"
167                                         echo >>$TMP_DIR/sensors.sh "echo \"BEGIN sensors.fan_$id \$1\""
168                                         ;;
169
170                                 energy)
171                                         files="$( ls $path/energy*_input 2>/dev/null )"
172                                         files="$( sensors_check_files $files )"
173                                         [ -z "$files" ] && continue
174                                         echo "CHART sensors.energy_$id '' '$name Energy' 'Joule' '$device' '' areastack 6005 $sensors_update_every"
175                                         echo >>$TMP_DIR/sensors.sh "echo \"BEGIN sensors.energy_$id \$1\""
176                                         algorithm="incremental"
177                                         divisor=1000000
178                                         ;;
179
180                                 humidity)
181                                         files="$( ls $path/humidity*_input 2>/dev/null )"
182                                         files="$( sensors_check_files $files )"
183                                         [ -z "$files" ] && continue
184                                         echo "CHART sensors.humidity_$id '' '$name Humidity' 'Percent' '$device' '' line 6006 $sensors_update_every"
185                                         echo >>$TMP_DIR/sensors.sh "echo \"BEGIN sensors.humidity_$id \$1\""
186                                         divisor=1000
187                                         ;;
188
189                                 *)
190                                         continue
191                                         ;;
192                         esac
193
194                         for x in $files
195                         do
196                                 file="$x"
197                                 fid="$( fixid "$file" )"
198                                 lfile="$( basename $file | sed "s|_input$|_label|g" )"
199                                 labelname="$( basename $file | sed "s|_input$||g" )"
200
201                                 if [ ! "$path/$lfile" = "$file" -a -f "$path/$lfile" ]
202                                         then
203                                         labelname="$( cat "$path/$lfile" )"
204                                 fi
205
206                                 echo "DIMENSION $fid '$labelname' $algorithm $multiplier $divisor"
207                                 echo >>$TMP_DIR/sensors.sh "printf \"SET $fid = \"; cat $file "
208                         done
209
210                         echo >>$TMP_DIR/sensors.sh "echo END"
211                 done
212         done
213
214         [ $sensors_source_update -eq 1 ] && echo >>$TMP_DIR/sensors.sh "}"
215         # cat >&2 $TMP_DIR/sensors.sh
216
217         # ok, load the function sensors_update() we created
218         [ $sensors_source_update -eq 1 ] && . $TMP_DIR/sensors.sh
219
220         return 0
221 }
222
223 # _update is called continiously, to collect the values
224 sensors_update() {
225         # the first argument to this function is the microseconds since last update
226         # pass this parameter to the BEGIN statement (see bellow).
227
228         # do all the work to collect / calculate the values
229         # for each dimension
230         # remember: KEEP IT SIMPLE AND SHORT
231
232         [ $sensors_source_update -eq 0 ] && . $TMP_DIR/sensors.sh $1
233
234         return 0
235 }
236