summaryrefslogtreecommitdiffstats
path: root/src/dmioem.c
blob: 67cd517d8617dc152dfa93de587aca0de20fb33e (plain)
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
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134

/*
 * Decoding of OEM-specific entries
 * This file is part of the dmidecode project.
 *
 *   (C) 2007 Jean Delvare <khali@linux-fr.org>
 *
 *   This program is free software; you can redistribute it and/or modify
 *   it under the terms of the GNU General Public License as published by
 *   the Free Software Foundation; either version 2 of the License, or
 *   (at your option) any later version.
 *
 *   This program is distributed in the hope that it will be useful,
 *   but WITHOUT ANY WARRANTY; without even the implied warranty of
 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *   GNU General Public License for more details.
 *
 *   You should have received a copy of the GNU General Public License
 *   along with this program; if not, write to the Free Software
 *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
 */

#include <stdio.h>
#include <string.h>

#include "types.h"
#include "dmidecode.h"
#include "dmioem.h"

/*
 * Globals for vendor-specific decodes
 */

enum DMI_VENDORS { VENDOR_UNKNOWN, VENDOR_HP };

static enum DMI_VENDORS dmi_vendor = VENDOR_UNKNOWN;

/*
 * Remember the system vendor for later use. We only actually store the
 * value if we know how to decode at least one specific entry type for
 * that vendor.
 */
void dmi_set_vendor(const struct dmi_header *h)
{
        const char *vendor;

        if( !h || !h->data ) {
                return;
        }
        vendor = dmi_string(h, h->data[0x04]);
        if( !vendor ) {
                return;
        } else if(strcmp(vendor, "HP") == 0) {
                dmi_vendor = VENDOR_HP;
        }
}

/*
 * HP-specific data structures are decoded here.
 *
 * Code contributed by John Cagle.
 */

static int dmi_decode_hp(struct dmi_header *h)
{
        u8 *data = h->data;
        int nic, ptr;

        switch (h->type) {
        case 204:
                /*
                 * Vendor Specific: HP ProLiant System/Rack Locator
                 */
                printf("HP ProLiant System/Rack Locator\n");
                if(h->length < 0x0B)
                        break;
                printf("\tRack Name: %s\n", dmi_string(h, data[0x04]));
                printf("\tEnclosure Name: %s\n", dmi_string(h, data[0x05]));
                printf("\tEnclosure Model: %s\n", dmi_string(h, data[0x06]));
                printf("\tEnclosure Serial: %s\n", dmi_string(h, data[0x0A]));
                printf("\tEnclosure Bays: %d\n", data[0x08]);
                printf("\tServer Bay: %s\n", dmi_string(h, data[0x07]));
                printf("\tBays Filled: %d\n", data[0x09]);
                break;

        case 209:
        case 221:
                /*
                 * Vendor Specific: HP ProLiant NIC MAC Information
                 *
                 * This prints the BIOS NIC number,
                 * PCI bus/device/function, and MAC address
                 */
                printf(h->type == 221 ?
                       "HP BIOS iSCSI NIC PCI and MAC Information\n" :
                       "HP BIOS NIC PCI and MAC Information\n");
                nic = 1;
                ptr = 4;
                while(h->length >= ptr + 8) {
                        if(data[ptr] == 0x00 && data[ptr + 1] == 0x00)
                                printf("\tNIC %d: Disabled\n", nic);
                        else if(data[ptr] == 0xFF && data[ptr + 1] == 0xFF)
                                printf("\tNIC %d: Not Installed\n", nic);
                        else {
                                printf("\tNIC %d: PCI device %02x:%02x.%x, "
                                       "MAC address %02X:%02X:%02X:%02X:%02X:%02X\n",
                                       nic, data[ptr + 1], data[ptr] >> 3, data[ptr] & 7,
                                       data[ptr + 2], data[ptr + 3],
                                       data[ptr + 4], data[ptr + 5], data[ptr + 6], data[ptr + 7]);
                        }
                        nic++;
                        ptr += 8;
                }
                break;

        default:
                return 0;
        }
        return 1;
}

/*
 * Dispatch vendor-specific entries decoding
 * Return 1 if decoding was successful, 0 otherwise
 */
int dmi_decode_oem(struct dmi_header *h)
{
        switch (dmi_vendor) {
        case VENDOR_HP:
                return dmi_decode_hp(h);
        default:
                return 0;
        }
}