SMART.pm 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158
  1. package Disk::SMART;
  2. use warnings;
  3. use strict;
  4. use Carp;
  5. use Math::Round;
  6. =head1 NAME
  7. Disk::SMART - Provides an interface to smartctl
  8. =head1 VERSION
  9. Version 0.01
  10. =cut
  11. our $VERSION = '0.01';
  12. =head1 SYNOPSIS
  13. Disk::SMART is an object ooriented module that provides an interface to get SMART disk info from a device as well as initiate testing.
  14. use Disk::SMART;
  15. my $smart = Disk::SMART->new('/dev/sda');
  16. =cut
  17. =head1 METHODS
  18. =head2 B<new (DEVICE)>
  19. Instantiates the Disk::SMART object
  20. C<DEVICE> - Device identifier of SSD / Hard Drive
  21. my $smart = Disk::SMART->new( 'dev/sda', '/dev/sdb' );
  22. =cut
  23. sub new {
  24. my ( $class, @devices ) = @_;
  25. confess "Valid device identifier not supplied to constructor.\n" if ( !@devices );
  26. my $smartctl = '/usr/sbin/smartctl';
  27. if ( !-f $smartctl ) {
  28. confess "smartctl binary was not found on your system, are you running as root?\n";
  29. }
  30. my $self = bless {}, $class;
  31. foreach my $device (@devices) {
  32. $self->{'devices'}->{$device}->{'SMART_OUTPUT'} = qx($smartctl -a $device);
  33. }
  34. return $self;
  35. }
  36. =head1 Getting information from smartctl
  37. =cut
  38. =head2 B<get_disk_temp (DEVICE)>
  39. Returns an array with the temperature of the device in Celsius and Farenheit, or N/A.
  40. C<DEVICE> - Device identifier of SSD / Hard Drive
  41. my ($temp_c, $temp_f) = $smart->get_disk_temp('/dev/sda');
  42. =cut
  43. sub get_disk_temp {
  44. my ( $self, $device ) = @_;
  45. my $smart_output = $self->{'devices'}->{$device}->{'SMART_OUTPUT'};
  46. my ($temp_c) = $smart_output =~ /(Temperature_Celsius.*\n)/;
  47. if ( defined $temp_c ) {
  48. chomp $temp_c;
  49. $temp_c =~ s/ //g;
  50. $temp_c =~ s/.*-//;
  51. $temp_c =~ s/\(.*\)//;
  52. }
  53. if ( !$temp_c || $smart_output =~ qr/S.M.A.R.T. not available/x ) {
  54. return 'N/A';
  55. }
  56. else {
  57. my $temp_f = round( ( $temp_c * 9 ) / 5 + 32 );
  58. return ( $temp_c, $temp_f );
  59. }
  60. return undef;
  61. }
  62. =head2 B<get_disk_health (DEVICE)>
  63. Returns the health of the disk. Output is "PASSED", "FAILED", or "N/A".
  64. C<DEVICE> - Device identifier of SSD / Hard Drive
  65. my $disk_health = $smart->get_disk_health('/dev/sda');
  66. =cut
  67. sub get_disk_health {
  68. my ( $self, $device ) = @_;
  69. my $smart_output = $self->{'devices'}->{$device}->{'SMART_OUTPUT'};
  70. my ($health) = $smart_output =~ /(SMART overall-health self-assessment.*\n)/;
  71. if ( defined $health and $health =~ /PASSED|FAILED/x ) {
  72. $health =~ s/.*: //;
  73. chomp $health;
  74. return $health;
  75. }
  76. else {
  77. return 'N/A';
  78. }
  79. }
  80. =head2 B<get_disk_model (DEVICE)>
  81. Returns the model of the device. Output is "<device>: <model>" or "N/A". eg. "/dev/sda: ST3250410AS"
  82. C<DEVICE> - Device identifier of SSD / Hard Drive
  83. my $disk_model = $smart->get_disk_model('/dev/sda');
  84. =cut
  85. sub get_disk_model {
  86. my ( $self, $device ) = @_;
  87. my $smart_output = $self->{'devices'}->{$device}->{'SMART_OUTPUT'};
  88. my ($model) = $smart_output =~ /(Device\ Model.*\n)/;
  89. if ( defined $model ) {
  90. $model =~ s/.*:\ //;
  91. $model =~ s/^\s+|\s+$//g; #trim beginning and ending whitepace
  92. }
  93. return ($model) ? "$device: $model" : "$device: N/A";
  94. }
  95. 1;
  96. __END__
  97. =head1 AUTHOR
  98. Paul Trost <paul.trost@trostfamily.org>
  99. =head1 LICENSE AND COPYRIGHT
  100. Copyright 2014.
  101. This script is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License v2, or at your option any later version.
  102. <http://gnu.org/licenses/gpl.html>
  103. =cut