[PATCH] powerpc/xive: discard ESB load value when interrupt is invalid

Cédric Le Goater clg at kaod.org
Tue Jan 14 00:31:04 AEDT 2020


On 1/13/20 2:01 PM, Cédric Le Goater wrote:
> From: Frederic Barrat <fbarrat at linux.ibm.com>
> 
> A load on an ESB page returning all 1's means that the underlying
> device has invalidated the access to the PQ state of the interrupt
> through mmio. It may happen, for example when querying a PHB interrupt
> while the PHB is in an error state.
> 
> In that case, we should consider the interrupt to be invalid when
> checking its state in the irq_get_irqchip_state() handler.


and we need also these tags :

Fixes: da15c03b047d ("powerpc/xive: Implement get_irqchip_state method for XIVE to fix shutdown race")
Cc: stable at vger.kernel.org # v5.3+



> Cc: Paul Mackerras <paulus at ozlabs.org>
> Signed-off-by: Frederic Barrat <fbarrat at linux.ibm.com>
> [ clg: - wrote a commit log
>        - introduced XIVE_ESB_INVALID ]
> Signed-off-by: Cédric Le Goater <clg at kaod.org>
> ---
>  arch/powerpc/include/asm/xive-regs.h |  1 +
>  arch/powerpc/sysdev/xive/common.c    | 15 ++++++++++++---
>  2 files changed, 13 insertions(+), 3 deletions(-)
> 
> diff --git a/arch/powerpc/include/asm/xive-regs.h b/arch/powerpc/include/asm/xive-regs.h
> index f2dfcd50a2d3..33aee7490cbb 100644
> --- a/arch/powerpc/include/asm/xive-regs.h
> +++ b/arch/powerpc/include/asm/xive-regs.h
> @@ -39,6 +39,7 @@
>  
>  #define XIVE_ESB_VAL_P		0x2
>  #define XIVE_ESB_VAL_Q		0x1
> +#define XIVE_ESB_INVALID	0xFF
>  
>  /*
>   * Thread Management (aka "TM") registers
> diff --git a/arch/powerpc/sysdev/xive/common.c b/arch/powerpc/sysdev/xive/common.c
> index f5fadbd2533a..9651ca061828 100644
> --- a/arch/powerpc/sysdev/xive/common.c
> +++ b/arch/powerpc/sysdev/xive/common.c
> @@ -972,12 +972,21 @@ static int xive_get_irqchip_state(struct irq_data *data,
>  				  enum irqchip_irq_state which, bool *state)
>  {
>  	struct xive_irq_data *xd = irq_data_get_irq_handler_data(data);
> +	u8 pq;
>  
>  	switch (which) {
>  	case IRQCHIP_STATE_ACTIVE:
> -		*state = !xd->stale_p &&
> -			 (xd->saved_p ||
> -			  !!(xive_esb_read(xd, XIVE_ESB_GET) & XIVE_ESB_VAL_P));
> +		pq = xive_esb_read(xd, XIVE_ESB_GET);
> +
> +		/*
> +		 * The esb value being all 1's means we couldn't get
> +		 * the PQ state of the interrupt through mmio. It may
> +		 * happen, for example when querying a PHB interrupt
> +		 * while the PHB is in an error state. We consider the
> +		 * interrupt to be inactive in that case.
> +		 */
> +		*state = (pq != XIVE_ESB_INVALID) && !xd->stale_p &&
> +			(xd->saved_p || !!(pq & XIVE_ESB_VAL_P));
>  		return 0;
>  	default:
>  		return -EINVAL;
> 



More information about the Linuxppc-dev mailing list