提交 30ec910e 编写于 作者: R Roland Dreier 提交者: Wim Van Sebroeck

[WATCHDOG] hpwdt: Use dmi_walk() instead of own copy

We can simplify the code by deleting all of the duplicated DMI table
walking code and using the kernel's existing dmi_walk() interface to
find the DMI entry the driver is looking for.
Signed-off-by: NRoland Dreier <rolandd@cisco.com>
Acked-by: NThomas Mingarelli <Thomas.Mingarelli@hp.com>
Signed-off-by: NWim Van Sebroeck <wim@iguana.be>
Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
上级 ef82710a
...@@ -58,41 +58,6 @@ struct bios32_service_dir { ...@@ -58,41 +58,6 @@ struct bios32_service_dir {
u8 reserved[5]; u8 reserved[5];
}; };
/*
* smbios_entry_point - defines SMBIOS entry point structure
*
* anchor[4] - anchor string (_SM_)
* checksum - checksum of the entry point structure
* length - length of the entry point structure
* major_ver - major version (02h for revision 2.1)
* minor_ver - minor version (01h for revision 2.1)
* max_struct_size - size of the largest SMBIOS structure
* revision - entry point structure revision implemented
* formatted_area[5] - reserved
* intermediate_anchor[5] - intermediate anchor string (_DMI_)
* intermediate_checksum - intermediate checksum
* table_length - structure table length
* table_address - structure table address
* table_num_structs - number of SMBIOS structures present
* bcd_revision - BCD revision
*/
struct smbios_entry_point {
u8 anchor[4];
u8 checksum;
u8 length;
u8 major_ver;
u8 minor_ver;
u16 max_struct_size;
u8 revision;
u8 formatted_area[5];
u8 intermediate_anchor[5];
u8 intermediate_checksum;
u16 table_length;
u32 table_address;
u16 table_num_structs;
u8 bcd_revision;
};
/* type 212 */ /* type 212 */
struct smbios_cru64_info { struct smbios_cru64_info {
u8 type; u8 type;
...@@ -175,24 +140,6 @@ static struct pci_device_id hpwdt_devices[] = { ...@@ -175,24 +140,6 @@ static struct pci_device_id hpwdt_devices[] = {
}; };
MODULE_DEVICE_TABLE(pci, hpwdt_devices); MODULE_DEVICE_TABLE(pci, hpwdt_devices);
/*
* bios_checksum
*/
static int __devinit bios_checksum(const char __iomem *ptr, int len)
{
char sum = 0;
int i;
/*
* calculate checksum of size bytes. This should add up
* to zero if we have a valid header.
*/
for (i = 0; i < len; i++)
sum += ptr[i];
return ((sum == 0) && (len > 0));
}
#ifndef CONFIG_X86_64 #ifndef CONFIG_X86_64
/* --32 Bit Bios------------------------------------------------------------ */ /* --32 Bit Bios------------------------------------------------------------ */
...@@ -302,6 +249,24 @@ static int __devinit cru_detect(unsigned long map_entry, ...@@ -302,6 +249,24 @@ static int __devinit cru_detect(unsigned long map_entry,
return retval; return retval;
} }
/*
* bios_checksum
*/
static int __devinit bios_checksum(const char __iomem *ptr, int len)
{
char sum = 0;
int i;
/*
* calculate checksum of size bytes. This should add up
* to zero if we have a valid header.
*/
for (i = 0; i < len; i++)
sum += ptr[i];
return ((sum == 0) && (len > 0));
}
/* /*
* bios32_present * bios32_present
* *
...@@ -410,12 +375,8 @@ asmlinkage void asminline_call(struct cmn_registers *pi86Regs, ...@@ -410,12 +375,8 @@ asmlinkage void asminline_call(struct cmn_registers *pi86Regs,
* dmi_find_cru * dmi_find_cru
* *
* Routine Description: * Routine Description:
* This function checks wether or not a SMBIOS/DMI record is * This function checks whether or not a SMBIOS/DMI record is
* the 64bit CRU info or not * the 64bit CRU info or not
*
* Return Value:
* 0 : SUCCESS - if record found
* <0 : FAILURE - if record not found
*/ */
static void __devinit dmi_find_cru(const struct dmi_header *dm) static void __devinit dmi_find_cru(const struct dmi_header *dm)
{ {
...@@ -434,135 +395,11 @@ static void __devinit dmi_find_cru(const struct dmi_header *dm) ...@@ -434,135 +395,11 @@ static void __devinit dmi_find_cru(const struct dmi_header *dm)
} }
} }
/*
* dmi_table
*
* Routine Description:
* Decode the SMBIOS/DMI table and check if we have a 64bit CRU record
* or not.
*
* We have to be cautious here. We have seen BIOSes with DMI pointers
* pointing to completely the wrong place for example
*/
static void __devinit dmi_table(u8 *buf, int len, int num,
void (*decode)(const struct dmi_header *))
{
u8 *data = buf;
int i = 0;
/*
* Stop when we see all the items the table claimed to have
* OR we run off the end of the table (also happens)
*/
while ((i < num) && (data - buf + sizeof(struct dmi_header)) <= len) {
const struct dmi_header *dm = (const struct dmi_header *)data;
/*
* We want to know the total length (formated area and strings)
* before decoding to make sure we won't run off the table in
* dmi_decode or dmi_string
*/
data += dm->length;
while ((data - buf < len - 1) && (data[0] || data[1]))
data++;
if (data - buf < len - 1)
decode(dm);
data += 2;
i++;
}
}
/*
* smbios_present
*
* Routine Description:
* This function parses the SMBIOS entry point table to retrieve
* the 64 bit CRU Service.
*
* Return Value:
* 0 : SUCCESS
* <0 : FAILURE
*/
static int __devinit smbios_present(const char __iomem *p)
{
struct smbios_entry_point *eps =
(struct smbios_entry_point *) p;
int length;
u8 *buf;
/* check if we have indeed the SMBIOS table entry point */
if ((strncmp((char *)eps->anchor, "_SM_",
sizeof(eps->anchor))) == 0) {
length = eps->length;
/* SMBIOS v2.1 implementation might use 0x1e */
if ((length == 0x1e) &&
(eps->major_ver == 2) &&
(eps->minor_ver == 1))
length = 0x1f;
/*
* Now we will check:
* - SMBIOS checksum must be 0
* - intermediate anchor should be _DMI_
* - intermediate checksum should be 0
*/
if ((bios_checksum(p, length)) &&
(strncmp((char *)eps->intermediate_anchor, "_DMI_",
sizeof(eps->intermediate_anchor)) == 0) &&
(bios_checksum(p+0x10, 15))) {
buf = ioremap(eps->table_address, eps->table_length);
if (buf == NULL)
return -ENODEV;
/* Scan the DMI table for the 64 bit CRU service */
dmi_table(buf, eps->table_length,
eps->table_num_structs, dmi_find_cru);
iounmap(buf);
return 0;
}
}
return -ENODEV;
}
static void __devinit smbios_scan_machine(void)
{
char __iomem *p, *q;
if (efi_enabled) {
if (efi.smbios == EFI_INVALID_TABLE_ADDR)
return;
p = ioremap(efi.smbios, 32);
if (p == NULL)
return;
smbios_present(p);
iounmap(p);
} else {
/*
* Search from 0x0f0000 through 0x0fffff, inclusive.
*/
p = ioremap(PCI_ROM_BASE1, ROM_SIZE);
if (p == NULL)
return;
for (q = p; q < p + ROM_SIZE; q += 16)
if (!smbios_present(q))
break;
iounmap(p);
}
}
static int __devinit detect_cru_service(void) static int __devinit detect_cru_service(void)
{ {
cru_rom_addr = NULL; cru_rom_addr = NULL;
smbios_scan_machine(); /* will become dmi_walk(dmi_find_cru); */ dmi_walk(dmi_find_cru);
/* if cru_rom_addr has been set then we found a CRU service */ /* if cru_rom_addr has been set then we found a CRU service */
return ((cru_rom_addr != NULL)? 0: -ENODEV); return ((cru_rom_addr != NULL)? 0: -ENODEV);
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册