aboutsummaryrefslogtreecommitdiffstats
path: root/arch/powerpc/platforms
diff options
context:
space:
mode:
authorBreno Leitao <leitao@linux.vnet.ibm.com>2010-02-03 00:56:41 -0500
committerBenjamin Herrenschmidt <benh@kernel.crashing.org>2010-02-16 22:02:47 -0500
commit8d3d50bf1913561ef3b1f5b53115c5a481ba9b1e (patch)
tree31da78f8750942c4ec16de24d63e9834b348fcbf /arch/powerpc/platforms
parente0508b1516ad4423499d4118a9037ae0aa4e9c2f (diff)
powerpc/eeh: Fix a bug when pci structure is null
During a EEH recover, the pci_dev structure can be null, mainly if an eeh event is detected during cpi config operation. In this case, the pci_dev will not be known (and will be null) the kernel will crash with the following message: Unable to handle kernel paging request for data at address 0x000000a0 Faulting instruction address: 0xc00000000006b8b4 Oops: Kernel access of bad area, sig: 11 [#1] NIP [c00000000006b8b4] .eeh_event_handler+0x10c/0x1a0 LR [c00000000006b8a8] .eeh_event_handler+0x100/0x1a0 Call Trace: [c0000003a80dff00] [c00000000006b8a8] .eeh_event_handler+0x100/0x1a0 [c0000003a80dff90] [c000000000031f1c] .kernel_thread+0x54/0x70 The bug occurs because pci_name() tries to access a null pointer. This patch just guarantee that pci_name() is not called on Null pointers. Signed-off-by: Breno Leitao <leitao@linux.vnet.ibm.com> Signed-off-by: Linas Vepstas <linasvepstas@gmail.com> Signed-off-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
Diffstat (limited to 'arch/powerpc/platforms')
-rw-r--r--arch/powerpc/platforms/pseries/eeh.c4
-rw-r--r--arch/powerpc/platforms/pseries/eeh_driver.c4
-rw-r--r--arch/powerpc/platforms/pseries/eeh_event.c2
3 files changed, 5 insertions, 5 deletions
diff --git a/arch/powerpc/platforms/pseries/eeh.c b/arch/powerpc/platforms/pseries/eeh.c
index ccd8dd03b8c9..3304f32fc7b8 100644
--- a/arch/powerpc/platforms/pseries/eeh.c
+++ b/arch/powerpc/platforms/pseries/eeh.c
@@ -491,7 +491,7 @@ int eeh_dn_check_failure(struct device_node *dn, struct pci_dev *dev)
491 pdn->eeh_mode & EEH_MODE_NOCHECK) { 491 pdn->eeh_mode & EEH_MODE_NOCHECK) {
492 ignored_check++; 492 ignored_check++;
493 pr_debug("EEH: Ignored check (%x) for %s %s\n", 493 pr_debug("EEH: Ignored check (%x) for %s %s\n",
494 pdn->eeh_mode, pci_name (dev), dn->full_name); 494 pdn->eeh_mode, eeh_pci_name(dev), dn->full_name);
495 return 0; 495 return 0;
496 } 496 }
497 497
@@ -515,7 +515,7 @@ int eeh_dn_check_failure(struct device_node *dn, struct pci_dev *dev)
515 printk (KERN_ERR "EEH: %d reads ignored for recovering device at " 515 printk (KERN_ERR "EEH: %d reads ignored for recovering device at "
516 "location=%s driver=%s pci addr=%s\n", 516 "location=%s driver=%s pci addr=%s\n",
517 pdn->eeh_check_count, location, 517 pdn->eeh_check_count, location,
518 dev->driver->name, pci_name(dev)); 518 dev->driver->name, eeh_pci_name(dev));
519 printk (KERN_ERR "EEH: Might be infinite loop in %s driver\n", 519 printk (KERN_ERR "EEH: Might be infinite loop in %s driver\n",
520 dev->driver->name); 520 dev->driver->name);
521 dump_stack(); 521 dump_stack();
diff --git a/arch/powerpc/platforms/pseries/eeh_driver.c b/arch/powerpc/platforms/pseries/eeh_driver.c
index 0c252c3a5f9f..b8d70f5d9aa9 100644
--- a/arch/powerpc/platforms/pseries/eeh_driver.c
+++ b/arch/powerpc/platforms/pseries/eeh_driver.c
@@ -337,7 +337,7 @@ struct pci_dn * handle_eeh_events (struct eeh_event *event)
337 location = location ? location : "unknown"; 337 location = location ? location : "unknown";
338 printk(KERN_ERR "EEH: Error: Cannot find partition endpoint " 338 printk(KERN_ERR "EEH: Error: Cannot find partition endpoint "
339 "for location=%s pci addr=%s\n", 339 "for location=%s pci addr=%s\n",
340 location, pci_name(event->dev)); 340 location, eeh_pci_name(event->dev));
341 return NULL; 341 return NULL;
342 } 342 }
343 343
@@ -368,7 +368,7 @@ struct pci_dn * handle_eeh_events (struct eeh_event *event)
368 pci_str = pci_name (frozen_pdn->pcidev); 368 pci_str = pci_name (frozen_pdn->pcidev);
369 drv_str = pcid_name (frozen_pdn->pcidev); 369 drv_str = pcid_name (frozen_pdn->pcidev);
370 } else { 370 } else {
371 pci_str = pci_name (event->dev); 371 pci_str = eeh_pci_name(event->dev);
372 drv_str = pcid_name (event->dev); 372 drv_str = pcid_name (event->dev);
373 } 373 }
374 374
diff --git a/arch/powerpc/platforms/pseries/eeh_event.c b/arch/powerpc/platforms/pseries/eeh_event.c
index ddb80f5d850b..ec5df8f519c7 100644
--- a/arch/powerpc/platforms/pseries/eeh_event.c
+++ b/arch/powerpc/platforms/pseries/eeh_event.c
@@ -80,7 +80,7 @@ static int eeh_event_handler(void * dummy)
80 eeh_mark_slot(event->dn, EEH_MODE_RECOVERING); 80 eeh_mark_slot(event->dn, EEH_MODE_RECOVERING);
81 81
82 printk(KERN_INFO "EEH: Detected PCI bus error on device %s\n", 82 printk(KERN_INFO "EEH: Detected PCI bus error on device %s\n",
83 pci_name(event->dev)); 83 eeh_pci_name(event->dev));
84 84
85 pdn = handle_eeh_events(event); 85 pdn = handle_eeh_events(event);
86 86