imx: fix GIP bits clear method

mx_mu_xsr_rmw() doesn't work correctly for w1c bits
because it reads the register and writes it back fully.
So, use imx_mu_write to clear pending interrupts from MU,
instead of imx_mu_xsr_rmw.

Using imx_mu_xsr_rmw might clear a pending interrupt that
was triggered while handling the current interrupt.

This fixes the case when fw boot confirmation and first
command are sent, from kernel, close to each other and
the command is missed.

Signed-off-by: Iuliana Prodan <iuliana.prodan@nxp.com>
Signed-off-by: Daniel Baluta <daniel.baluta@nxp.com>
This commit is contained in:
Iuliana Prodan 2023-03-02 15:52:41 +02:00 committed by Daniel Baluta
parent 388d69fb9a
commit e6845e69e5
1 changed files with 13 additions and 9 deletions

View File

@ -57,7 +57,8 @@ static void irq_handler(void *arg)
imx_mu_xcr_rmw(IMX_MU_VERSION, IMX_MU_GIER, 0, IMX_MU_xCR_GIEn(IMX_MU_VERSION, 1)); imx_mu_xcr_rmw(IMX_MU_VERSION, IMX_MU_GIER, 0, IMX_MU_xCR_GIEn(IMX_MU_VERSION, 1));
/* Clear GP pending interrupt #1 */ /* Clear GP pending interrupt #1 */
imx_mu_xsr_rmw(IMX_MU_VERSION, IMX_MU_GSR, IMX_MU_xSR_GIPn(IMX_MU_VERSION, 1), 0); imx_mu_write(IMX_MU_xSR_GIPn(IMX_MU_VERSION, 1),
IMX_MU_xSR(IMX_MU_VERSION, IMX_MU_GSR));
interrupt_clear(PLATFORM_IPC_INTERRUPT); interrupt_clear(PLATFORM_IPC_INTERRUPT);
@ -73,7 +74,8 @@ static void irq_handler(void *arg)
imx_mu_xcr_rmw(IMX_MU_VERSION, IMX_MU_GIER, 0, IMX_MU_xCR_GIEn(IMX_MU_VERSION, 0)); imx_mu_xcr_rmw(IMX_MU_VERSION, IMX_MU_GIER, 0, IMX_MU_xCR_GIEn(IMX_MU_VERSION, 0));
/* Clear GP pending interrupt #0 */ /* Clear GP pending interrupt #0 */
imx_mu_xsr_rmw(IMX_MU_VERSION, IMX_MU_GSR, IMX_MU_xSR_GIPn(IMX_MU_VERSION, 0), 0); imx_mu_write(IMX_MU_xSR_GIPn(IMX_MU_VERSION, 0),
IMX_MU_xSR(IMX_MU_VERSION, IMX_MU_GSR));
interrupt_clear(PLATFORM_IPC_INTERRUPT); interrupt_clear(PLATFORM_IPC_INTERRUPT);
@ -204,11 +206,11 @@ int platform_ipc_init(struct ipc *ipc)
IMX_MU_xCR_GIEn(IMX_MU_VERSION, 3)); IMX_MU_xCR_GIEn(IMX_MU_VERSION, 3));
/* Clear all pending interrupts from MU */ /* Clear all pending interrupts from MU */
imx_mu_xsr_rmw(IMX_MU_VERSION, IMX_MU_GSR, imx_mu_write(IMX_MU_xSR_GIPn(IMX_MU_VERSION, 0) |
IMX_MU_xSR_GIPn(IMX_MU_VERSION, 0) |
IMX_MU_xSR_GIPn(IMX_MU_VERSION, 1) | IMX_MU_xSR_GIPn(IMX_MU_VERSION, 1) |
IMX_MU_xSR_GIPn(IMX_MU_VERSION, 2) | IMX_MU_xSR_GIPn(IMX_MU_VERSION, 2) |
IMX_MU_xSR_GIPn(IMX_MU_VERSION, 3), 0); IMX_MU_xSR_GIPn(IMX_MU_VERSION, 3),
IMX_MU_xSR(IMX_MU_VERSION, IMX_MU_GSR));
/* Clear pending interrupt for DSP Core */ /* Clear pending interrupt for DSP Core */
interrupt_clear(PLATFORM_IPC_INTERRUPT); interrupt_clear(PLATFORM_IPC_INTERRUPT);
@ -260,7 +262,8 @@ int ipc_platform_poll_is_cmd_pending(void)
imx_mu_xcr_rmw(IMX_MU_VERSION, IMX_MU_GIER, 0, IMX_MU_xCR_GIEn(IMX_MU_VERSION, 0)); imx_mu_xcr_rmw(IMX_MU_VERSION, IMX_MU_GIER, 0, IMX_MU_xCR_GIEn(IMX_MU_VERSION, 0));
/* Clear GP pending interrupt #0 */ /* Clear GP pending interrupt #0 */
imx_mu_xsr_rmw(IMX_MU_VERSION, IMX_MU_GSR, IMX_MU_xSR_GIPn(IMX_MU_VERSION, 0), 0); imx_mu_write(IMX_MU_xSR_GIPn(IMX_MU_VERSION, 0),
IMX_MU_xSR(IMX_MU_VERSION, IMX_MU_GSR));
interrupt_clear(PLATFORM_IPC_INTERRUPT); interrupt_clear(PLATFORM_IPC_INTERRUPT);
@ -285,7 +288,8 @@ int ipc_platform_poll_is_host_ready(void)
imx_mu_xcr_rmw(IMX_MU_VERSION, IMX_MU_GIER, 0, IMX_MU_xCR_GIEn(IMX_MU_VERSION, 1)); imx_mu_xcr_rmw(IMX_MU_VERSION, IMX_MU_GIER, 0, IMX_MU_xCR_GIEn(IMX_MU_VERSION, 1));
/* Clear GP pending interrupt #1 */ /* Clear GP pending interrupt #1 */
imx_mu_xsr_rmw(IMX_MU_VERSION, IMX_MU_GSR, IMX_MU_xSR_GIPn(IMX_MU_VERSION, 1), 0); imx_mu_write(IMX_MU_xSR_GIPn(IMX_MU_VERSION, 1),
IMX_MU_xSR(IMX_MU_VERSION, IMX_MU_GSR));
interrupt_clear(PLATFORM_IPC_INTERRUPT); interrupt_clear(PLATFORM_IPC_INTERRUPT);