Boot firmware can leave a PAGE_FAULT_ACTIVE condition in an IOMMU bank
before the driver has configured paging.  Such a bank shows:

  PAGE_FAULT_ACTIVE=1  STALL_ACTIVE=0  IDLE=1

rk_iommu_is_stall_active() sees STALL_ACTIVE=0 and reports the whole
IOMMU as "not stalled", so any subsequent readx_poll_timeout() loop
waiting for the stall to complete never sees a passing result even
after the other banks have correctly entered stall mode.

Detect the orphaned-fault pattern (PAGE_FAULT_ACTIVE & !STALL_ACTIVE &
IDLE) and skip those banks in the stall check.  They have no in-flight
transaction, so they are already quiescent.

Signed-off-by: Jiaxing Hu <[email protected]>
---
 drivers/iommu/rockchip-iommu.c | 20 +++++++++++++++++---
 1 file changed, 17 insertions(+), 3 deletions(-)

diff --git a/drivers/iommu/rockchip-iommu.c b/drivers/iommu/rockchip-iommu.c
index 0013cf196..f42ffcafb 100644
--- a/drivers/iommu/rockchip-iommu.c
+++ b/drivers/iommu/rockchip-iommu.c
@@ -378,9 +378,23 @@ static bool rk_iommu_is_stall_active(struct rk_iommu 
*iommu)
        bool active = true;
        int i;
 
-       for (i = 0; i < iommu->num_mmu; i++)
-               active &= !!(rk_iommu_read(iommu->bases[i], RK_MMU_STATUS) &
-                                          RK_MMU_STATUS_STALL_ACTIVE);
+       for (i = 0; i < iommu->num_mmu; i++) {
+               u32 status = rk_iommu_read(iommu->bases[i], RK_MMU_STATUS);
+
+               /*
+                * A bank stuck with PAGE_FAULT_ACTIVE but without STALL_ACTIVE
+                * and with IDLE set has an orphaned fault left by firmware 
before
+                * paging was configured.  It cannot enter stall mode but has no
+                * transaction in flight, so it is already quiescent.  Skip it
+                * rather than treating it as "not stalled."
+                */
+               if ((status & RK_MMU_STATUS_PAGE_FAULT_ACTIVE) &&
+                   !(status & RK_MMU_STATUS_STALL_ACTIVE) &&
+                   (status & RK_MMU_STATUS_IDLE))
+                       continue;
+
+               active &= !!(status & RK_MMU_STATUS_STALL_ACTIVE);
+       }
 
        return active;
 }
-- 
2.43.0

Reply via email to