Skip to content

Commit

Permalink
Merge git://git.kernel.org/pub/scm/linux/kernel/git/wim/linux-2.6-wat…
Browse files Browse the repository at this point in the history
…chdog

* git://git.kernel.org/pub/scm/linux/kernel/git/wim/linux-2.6-watchdog:
  [WATCHDOG] make watchdog/hpwdt.c:asminline_call() static
  [WATCHDOG] Remove volatiles from watchdog device structures
  [WATCHDOG] replace remaining __FUNCTION__ occurrences
  [WATCHDOG] hpwdt: Use dmi_walk() instead of own copy
  [WATCHDOG] Fix return value warning in hpwdt
  [WATCHDOG] Fix declaration of struct smbios_entry_point in hpwdt
  [WATCHDOG] it8712f_wdt support for 16-bit timeout values, WDIOC_GETSTATUS
  • Loading branch information
Linus Torvalds committed Mar 11, 2008
2 parents 99eeed4 + 8b1266f commit dae311b
Show file tree
Hide file tree
Showing 8 changed files with 100 additions and 216 deletions.
4 changes: 2 additions & 2 deletions drivers/watchdog/cpu5wdt.c
Original file line number Diff line number Diff line change
Expand Up @@ -59,9 +59,9 @@ static int ticks = 10000;

static struct {
struct completion stop;
volatile int running;
int running;
struct timer_list timer;
volatile int queue;
int queue;
int default_ticks;
unsigned long inuse;
} cpu5wdt_device;
Expand Down
214 changes: 24 additions & 190 deletions drivers/watchdog/hpwdt.c
Original file line number Diff line number Diff line change
Expand Up @@ -58,41 +58,6 @@ struct bios32_service_dir {
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;
u64 table_address;
u16 table_num_structs;
u8 bcd_revision;
};

/* type 212 */
struct smbios_cru64_info {
u8 type;
Expand Down Expand Up @@ -175,31 +140,13 @@ static struct pci_device_id 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
/* --32 Bit Bios------------------------------------------------------------ */

#define HPWDT_ARCH 32

asmlinkage void asminline_call(struct cmn_registers *pi86Regs,
unsigned long *pRomEntry)
static void asminline_call(struct cmn_registers *pi86Regs,
unsigned long *pRomEntry)
{
asm("pushl %ebp \n\t"
"movl %esp, %ebp \n\t"
Expand Down Expand Up @@ -302,6 +249,24 @@ static int __devinit cru_detect(unsigned long map_entry,
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
*
Expand Down Expand Up @@ -368,8 +333,8 @@ static int __devinit detect_cru_service(void)

#define HPWDT_ARCH 64

asmlinkage void asminline_call(struct cmn_registers *pi86Regs,
unsigned long *pRomEntry)
static void asminline_call(struct cmn_registers *pi86Regs,
unsigned long *pRomEntry)
{
asm("pushq %rbp \n\t"
"movq %rsp, %rbp \n\t"
Expand Down Expand Up @@ -410,12 +375,8 @@ asmlinkage void asminline_call(struct cmn_registers *pi86Regs,
* dmi_find_cru
*
* 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
*
* Return Value:
* 0 : SUCCESS - if record found
* <0 : FAILURE - if record not found
*/
static void __devinit dmi_find_cru(const struct dmi_header *dm)
{
Expand All @@ -434,138 +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 int __devinit smbios_scan_machine(void)
{
char __iomem *p, *q;
int rc;

if (efi_enabled) {
if (efi.smbios == EFI_INVALID_TABLE_ADDR)
return -ENODEV;

p = ioremap(efi.smbios, 32);
if (p == NULL)
return -ENOMEM;

rc = smbios_present(p);
iounmap(p);
} else {
/*
* Search from 0x0f0000 through 0x0fffff, inclusive.
*/
p = ioremap(PCI_ROM_BASE1, ROM_SIZE);
if (p == NULL)
return -ENOMEM;

for (q = p; q < p + ROM_SIZE; q += 16) {
rc = smbios_present(q);
if (!rc) {
break;
}
}
iounmap(p);
}
}

static int __devinit detect_cru_service(void)
{
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 */
return ((cru_rom_addr != NULL)? 0: -ENODEV);
Expand Down
Loading

0 comments on commit dae311b

Please sign in to comment.