From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from e7.ny.us.ibm.com (e7.ny.us.ibm.com [32.97.182.137]) (using TLSv1 with cipher DHE-RSA-AES256-SHA (256/256 bits)) (Client CN "e7.ny.us.ibm.com", Issuer "GeoTrust SSL CA" (verified OK)) by ozlabs.org (Postfix) with ESMTPS id 6AA25B6F7C for ; Tue, 4 Oct 2011 18:54:43 +1100 (EST) Received: from d01relay01.pok.ibm.com (d01relay01.pok.ibm.com [9.56.227.233]) by e7.ny.us.ibm.com (8.14.4/8.13.1) with ESMTP id p946XI3v026808 for ; Tue, 4 Oct 2011 02:33:18 -0400 Received: from d01av03.pok.ibm.com (d01av03.pok.ibm.com [9.56.224.217]) by d01relay01.pok.ibm.com (8.13.8/8.13.8/NCO v10.0) with ESMTP id p947sWbD186518 for ; Tue, 4 Oct 2011 03:54:32 -0400 Received: from d01av03.pok.ibm.com (loopback [127.0.0.1]) by d01av03.pok.ibm.com (8.14.4/8.13.1/NCO v10.0 AVout) with ESMTP id p947sVqn016169 for ; Tue, 4 Oct 2011 04:54:32 -0300 Subject: Re: [PATCH] PSeries: Cancel RTAS event scan before firmware flash From: Subrata Modak To: Ravi K Nittala In-Reply-To: <20111004074932.27428.81900.stgit@localhost6.localdomain6> References: <20111004074932.27428.81900.stgit@localhost6.localdomain6> Content-Type: text/plain Date: Tue, 04 Oct 2011 13:24:21 +0530 Message-Id: <1317714863.4423.4.camel@subratamodak.linux.ibm.com> Mime-Version: 1.0 Cc: Anton Blanchard , naveedaus , Michael Neuling , Pavaman , suzuki@linux.vnet.ibm.com, ranittal@linux.vnet.ibm.com, Vishu , linuxppc-dev@lists.ozlabs.org, Divya Vikas Reply-To: subrata@linux.vnet.ibm.com List-Id: Linux on PowerPC Developers Mail List List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Also, On Tue, 2011-10-04 at 13:19 +0530, Ravi K Nittala wrote: > The RTAS firmware flash update is conducted using an RTAS call that is > serialized by lock_rtas() which uses spin_lock. While the flash is in > progress, rtasd performs scan for any RTAS events that are generated by > the system. rtasd keeps scanning for the RTAS events generated on the > machine. This is performed via workqueue mechanism. The rtas_event_scan() > also uses an RTAS call to scan the events, eventually trying to acquire > the spin_lock before issuing the request. > > The flash update takes a while to complete and during this time, any other > RTAS call has to wait. In this case, rtas_event_scan() waits for a long time > on the spin_lock resulting in a soft lockup. > > Fix: Just before the flash update is performed, the queued rtas_event_scan() > work item is cancelled from the work queue so that there is no other RTAS > call issued while the flash is in progress. After the flash completes, the > system reboots and the rtas_event_scan() is rescheduled. > > Signed-off-by: Suzuki Poulose > Signed-off-by: Ravi Nittala Reported-by: Divya Vikas Regards-- Subrata > > --- > arch/powerpc/include/asm/rtas.h | 6 ++++++ > arch/powerpc/kernel/rtas_flash.c | 6 ++++++ > arch/powerpc/kernel/rtasd.c | 7 +++++++ > 3 files changed, 19 insertions(+), 0 deletions(-) > > diff --git a/arch/powerpc/include/asm/rtas.h b/arch/powerpc/include/asm/rtas.h > index 58625d1..754723b 100644 > --- a/arch/powerpc/include/asm/rtas.h > +++ b/arch/powerpc/include/asm/rtas.h > @@ -245,6 +245,12 @@ extern int early_init_dt_scan_rtas(unsigned long node, > > extern void pSeries_log_error(char *buf, unsigned int err_type, int fatal); > > +#ifdef CONFIG_PPC_RTAS_DAEMON > +extern void rtas_cancel_event_scan(void); > +#else > +static inline void rtas_cancel_event_scan(void) { } > +#endif > + > /* Error types logged. */ > #define ERR_FLAG_ALREADY_LOGGED 0x0 > #define ERR_FLAG_BOOT 0x1 /* log was pulled from NVRAM on boot */ > diff --git a/arch/powerpc/kernel/rtas_flash.c b/arch/powerpc/kernel/rtas_flash.c > index e037c74..4174b4b 100644 > --- a/arch/powerpc/kernel/rtas_flash.c > +++ b/arch/powerpc/kernel/rtas_flash.c > @@ -568,6 +568,12 @@ static void rtas_flash_firmware(int reboot_type) > } > > /* > + * Just before starting the firmware flash, cancel the event scan work > + * to avoid any soft lockup issues. > + */ > + rtas_cancel_event_scan(); > + > + /* > * NOTE: the "first" block must be under 4GB, so we create > * an entry with no data blocks in the reserved buffer in > * the kernel data segment. > diff --git a/arch/powerpc/kernel/rtasd.c b/arch/powerpc/kernel/rtasd.c > index 481ef06..1045ff4 100644 > --- a/arch/powerpc/kernel/rtasd.c > +++ b/arch/powerpc/kernel/rtasd.c > @@ -472,6 +472,13 @@ static void start_event_scan(void) > &event_scan_work, event_scan_delay); > } > > +/* Cancel the rtas event scan work */ > +void rtas_cancel_event_scan(void) > +{ > + cancel_delayed_work_sync(&event_scan_work); > +} > +EXPORT_SYMBOL_GPL(rtas_cancel_event_scan); > + > static int __init rtas_init(void) > { > struct proc_dir_entry *entry; >