Changeset 5681

Show
Ignore:
Timestamp:
03/12/09 17:44:27 (4 years ago)
Author:
khali
Message:

Use dmidecode to find IPMI interfaces if available. This is required
if non-standard address or register width are used. And anyway it is
always better to avoid access to random I/O ports.

Location:
lm-sensors/trunk
Files:
2 modified

Legend:

Unmodified
Added
Removed
  • lm-sensors/trunk/CHANGES

    r5680 r5681  
    66                  Display Super-I/O address even if LD is disabled 
    77                  Differentiate between PC8374L and WPCD377I 
     8                  Use dmidecode to find IPMI interfaces if available 
    89 
    9103.1.0 "Happy Birthday Lina" (2009-02-28) 
  • lm-sensors/trunk/prog/detect/sensors-detect

    r5680 r5681  
    50025002 
    50035003        return 8; 
     5004} 
     5005 
     5006######## 
     5007# IPMI # 
     5008######## 
     5009 
     5010# Returns: number of IPMI interfaces found 
     5011sub ipmi_from_smbios 
     5012{ 
     5013        my ($version, $if, @ipmi_if); 
     5014 
     5015        if (open(local *DMIDECODE, "dmidecode --version 2>/dev/null |")) { 
     5016                $version = <DMIDECODE>; 
     5017                close(DMIDECODE); 
     5018                chomp $version if defined $version; 
     5019        } 
     5020 
     5021        if (!defined $version 
     5022         || !($version =~ m/^(\d+).(\d+)$/) 
     5023         || !(($1 == 2 && $2 >= 7) || $1 > 2)) { 
     5024                print "# DMI data unavailable, please consider installing dmidecode 2.7\n". 
     5025                      "# or later for better results.\n"; 
     5026                return; 
     5027        } 
     5028 
     5029        # Parse the output of dmidecode into an array of IPMI interfaces. 
     5030        # Each entry is a hash with the following keys: type and addr. 
     5031        $if = -1; 
     5032        open(local *DMIDECODE, "dmidecode -t 38 2>/dev/null |") or return 0; 
     5033        while (<DMIDECODE>) { 
     5034                if (m/^IPMI Device Information/) { 
     5035                        $if++; 
     5036                        next; 
     5037                } 
     5038                next unless $if >= 0; 
     5039 
     5040                if (m/^\tInterface Type: (.*)$/) { 
     5041                        $ipmi_if[$if]->{type} = "IPMI BMC $1"; 
     5042                        $ipmi_if[$if]->{type} =~ s/ \(.*//; 
     5043                        next; 
     5044                } 
     5045                if (m/^\tBase Address: (0x[0-9A-Fa-f]+) \(I\/O\)$/) { 
     5046                        $ipmi_if[$if]->{addr} = oct($1); 
     5047                        next; 
     5048                } 
     5049        } 
     5050        close(DMIDECODE); 
     5051 
     5052        foreach $if (@ipmi_if) { 
     5053                if (exists $if->{addr}) { 
     5054                        printf("\%-60s", sprintf("Found `\%s' at 0x\%x... ", 
     5055                                                 $if->{type}, $if->{addr})); 
     5056                } else { 
     5057                        printf("\%-60s", sprintf("Found `\%s'... ", 
     5058                                                 $if->{type})); 
     5059                } 
     5060                print "Success!\n". 
     5061                      "    (confidence 8, driver `ipmisensors')\n"; 
     5062                my $new_hash = { 
     5063                        conf => 8, 
     5064                        isa_addr => $if->{addr} || 0, 
     5065                        chipname => $if->{type}, 
     5066                }; 
     5067                add_isa_to_chips_detected("ipmisensors", $new_hash); 
     5068        } 
     5069 
     5070        return scalar @ipmi_if; 
    50045071} 
    50055072 
     
    54625529                        print "Some systems (mainly servers) implement IPMI, a set of common interfaces\n". 
    54635530                              "through which system health data may be retrieved, amongst other things.\n". 
    5464                               "We have to read from arbitrary I/O ports to probe for such interfaces.\n". 
    5465                               "This is normally safe. Do you want to scan for IPMI interfaces?\n". 
    5466                               "(YES/no): "; 
     5531                              "We first try to get the information from SMBIOS. If we don't find it\n". 
     5532                              "there, we have to read from arbitrary I/O ports to probe for such\n". 
     5533                              "interfaces. This is normally safe. Do you want to scan for IPMI\n". 
     5534                              "interfaces? (YES/no): "; 
    54675535                        unless (<STDIN> =~ /^\s*n/i) { 
    5468                                 initialize_ioports(); 
    5469                                 scan_isa_bus(\@ipmi_ifs); 
    5470                                 close_ioports(); 
     5536                                if (!ipmi_from_smbios()) { 
     5537                                        initialize_ioports(); 
     5538                                        scan_isa_bus(\@ipmi_ifs); 
     5539                                        close_ioports(); 
     5540                                } 
    54715541                        } 
    54725542                        print "\n";