mirror of
https://github.com/munin-monitoring/contrib.git
synced 2018-11-08 00:59:34 +01:00
177 lines
5.7 KiB
Perl
Executable File
177 lines
5.7 KiB
Perl
Executable File
#!/usr/bin/perl -w
|
||
#
|
||
# Plugin to monitor harddrive temperatures through SMART.
|
||
#
|
||
# client-conf.d/-options:
|
||
#
|
||
# smartctl -- path to smartctl executable
|
||
# drives -- List drives to monitor. E.g. "env.drives hda hdc".
|
||
# type_$dev -- device type for one drive, e.g. "env.type_sda 3ware,0"
|
||
# args_$dev -- additional arguments to smartctl for one drive,
|
||
# e.g. "env.args_hda -v 194,10xCelsius"
|
||
# Use this to make the plugin use the --all or -a option
|
||
# if your disk will not return it's temperature when
|
||
# only the -A option is used.
|
||
#
|
||
# Note for users of RAID controllers (smartmontools currently only
|
||
# supports 3ware): you can specify the drives attached to your RAID
|
||
# controller(s) as raiddev_num (e.g. sda_0). Then you must specify the
|
||
# type like this: type_sda_0 3ware,0.
|
||
#
|
||
# $Log$
|
||
# Revision 1.1.2.5 2005/03/03 10:22:25 lupe
|
||
# Add feature to specify additional arguments to smartctl
|
||
#
|
||
# Revision 1.1.2.4 2005/02/17 10:59:33 lupe
|
||
# Support more than one drive on RAID controllers. Explain how to configure
|
||
# them.
|
||
#
|
||
# Revision 1.1.2.3 2005/01/29 22:14:36 jimmyo
|
||
# Make the plugin check all rdsks.
|
||
#
|
||
# Revision 1.1.2.2 2005/01/26 09:34:37 jimmyo
|
||
# Added license note.
|
||
#
|
||
# Revision 1.1.2.1 2005/01/25 21:00:05 jimmyo
|
||
# Added plugin generic/hddtemp_smartctl, made by Lupe Christoph. Made it the default hddtemp plugin.
|
||
#
|
||
# Revision 1.1 2004/11/10 16:11:27 jimmyo
|
||
# Added new plugin linux/hddtemp_smartctl, made by Peter Gervai (SF#1032727).
|
||
#
|
||
# Revision 1.0 2004/09/22
|
||
# New plugin: Peter Gervai <grin(*)grin.hu>
|
||
#
|
||
#
|
||
#%# family=auto
|
||
#%# capabilities=autoconf
|
||
#
|
||
# Copyright (c) 2005, Lutz Peter Christoph
|
||
# All rights reserved.
|
||
#
|
||
# Redistribution and use in source and binary forms, with or without
|
||
# modification, are permitted provided that the following conditions
|
||
# are met:
|
||
#
|
||
# * Redistributions of source code must retain the above copyright
|
||
# notice, this list of conditions and the following disclaimer.
|
||
#
|
||
# * Redistributions in binary form must reproduce the above copyright
|
||
# notice, this list of conditions and the following disclaimer in
|
||
# the documentation and/or other materials provided with the
|
||
# distribution.
|
||
#
|
||
# * The name and aliases of Lutz Peter Christoph ("Lupe Christoph",
|
||
# "Lutz Christoph") may not be used to endorse or promote products
|
||
# derived from this software without specific prior written
|
||
# permission.
|
||
#
|
||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||
# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||
# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||
# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||
# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||
# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||
# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||
# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||
# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||
|
||
|
||
use strict;
|
||
|
||
my $smartctl = exists $ENV{smartctl} ? $ENV{smartctl} : undef;
|
||
|
||
# If the envvar is not set, look for smartctl
|
||
# first, try $PATH
|
||
$smartctl = `which smartctl` unless $smartctl;
|
||
chomp $smartctl;
|
||
$smartctl = undef unless -x $smartctl;
|
||
|
||
# Still not found? Check obvious places
|
||
my @dirs = qw(/usr/bin /usr/sbin /usr/local/bin /usr/local/sbin);
|
||
until ($smartctl or @dirs == 0) {
|
||
my $dir = shift @dirs;
|
||
my $path = $dir.'/smartctl';
|
||
$smartctl = $path if -x $path;
|
||
}
|
||
|
||
$ENV{LANG} = 'C';
|
||
$ENV{LC_ALL} = 'C';
|
||
my @drives;
|
||
|
||
# Try to get a default set of drives
|
||
if ($^O eq 'darwin') {
|
||
opendir(DEV, '/dev');
|
||
@drives = grep /^disk[0-9]+$/, readdir DEV;
|
||
closedir(DEV);
|
||
} elsif ($^O eq 'freebsd') {
|
||
opendir(DEV, '/dev');
|
||
@drives = grep /^ad|da[0-9]+$/, readdir DEV;
|
||
closedir(DEV);
|
||
} elsif ($^O eq 'linux') {
|
||
# On Linux, we know how to enumerate ide drives.
|
||
# SCSI is not as easy
|
||
if (-d '/dev') {
|
||
opendir(IDE, '/dev');
|
||
@drives = grep /^sd[a-z]$/, readdir IDE;
|
||
closedir(IDE);
|
||
}
|
||
} elsif (($^O eq 'netbsd') or ($^O eq 'openbsd')) {
|
||
opendir(DEV, '/dev');
|
||
@drives = grep /^wd|sd[0-9]+c$/, readdir DEV;
|
||
closedir(DEV);
|
||
} elsif ($^O eq 'solaris') {
|
||
@drives = map { s@.*/@@ ; $_ } glob '/dev/rdsk/c*t*d*s2';
|
||
}
|
||
|
||
@drives = split ' ', $ENV{drives} if exists $ENV{drives};
|
||
|
||
# Sort list of drives
|
||
@drives = sort @drives;
|
||
|
||
if (defined $ARGV[0]) {
|
||
if ($ARGV[0] eq 'autoconf') {
|
||
if ($smartctl and -x $smartctl) {
|
||
if (@drives) {
|
||
print "yes\n";
|
||
exit 0;
|
||
} else {
|
||
print "no (no drives known)\n";
|
||
exit 1;
|
||
}
|
||
} else {
|
||
print "no (smartctl not found)\n";
|
||
exit 1;
|
||
}
|
||
} elsif ($ARGV[0] eq 'config') {
|
||
print "graph_title HDD temperature\n";
|
||
print "graph_args --base 1000 -l 0\n";
|
||
print "graph_vlabel temp in <20>C\n";
|
||
print "graph_category sensors\n";
|
||
print "graph_info This graph shows the temperature in degrees Celsius of the hard drives in the machine.\n";
|
||
print "$_.label $_\n" foreach @drives;
|
||
exit 0;
|
||
}
|
||
}
|
||
|
||
foreach (@drives) {
|
||
my $dev;
|
||
$dev = $_ =~ /(.*)(?:_\d+)/ ? $1 : $_;
|
||
my $cmd = $smartctl.' -A ';
|
||
$cmd .= $ENV{'args_'.$_}.' ' if exists $ENV{'args_'.$_};
|
||
$cmd .= '-d '.$ENV{'type_'.$_}.' ' if exists $ENV{'type_'.$_};
|
||
if ($^O eq 'solaris') {
|
||
$cmd .= "/dev/rdsk/$dev";
|
||
} else {
|
||
$cmd .= "/dev/$dev";
|
||
}
|
||
my $output = `$cmd`;
|
||
if ($output =~ /Current Drive Temperature:\s*(\d+)/) {
|
||
print "$_.value $1\n";
|
||
} elsif ($output =~ /^(194 Temperature_Celsius.*)/m) {
|
||
my @F = split ' ', $1;
|
||
print "$_.value $F[9]\n";
|
||
}
|
||
}
|