diff options
| author | Guo Ren <guoren@linux.alibaba.com> | 2023-01-26 22:53:06 -0500 |
|---|---|---|
| committer | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2023-02-15 17:22:26 +0100 |
| commit | 8eee3521bca7104de4859b853d4358373291f681 (patch) | |
| tree | 29614530b6441cb50b520e9e6d8ee209207e77f5 /arch | |
| parent | 6ff8b48253926147e441b9d0c833ca6494707d0b (diff) | |
| download | linux-8eee3521bca7104de4859b853d4358373291f681.tar.gz linux-8eee3521bca7104de4859b853d4358373291f681.tar.bz2 linux-8eee3521bca7104de4859b853d4358373291f681.zip | |
riscv: Fixup race condition on PG_dcache_clean in flush_icache_pte
commit 950b879b7f0251317d26bae0687e72592d607532 upstream.
In commit 588a513d3425 ("arm64: Fix race condition on PG_dcache_clean
in __sync_icache_dcache()"), we found RISC-V has the same issue as the
previous arm64. The previous implementation didn't guarantee the correct
sequence of operations, which means flush_icache_all() hasn't been
called when the PG_dcache_clean was set. That would cause a risk of page
synchronization.
Fixes: 08f051eda33b ("RISC-V: Flush I$ when making a dirty page executable")
Signed-off-by: Guo Ren <guoren@linux.alibaba.com>
Signed-off-by: Guo Ren <guoren@kernel.org>
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
Reviewed-by: Conor Dooley <conor.dooley@microchip.com>
Link: https://lore.kernel.org/r/20230127035306.1819561-1-guoren@kernel.org
Cc: stable@vger.kernel.org
Signed-off-by: Palmer Dabbelt <palmer@rivosinc.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Diffstat (limited to 'arch')
| -rw-r--r-- | arch/riscv/mm/cacheflush.c | 4 |
1 files changed, 3 insertions, 1 deletions
diff --git a/arch/riscv/mm/cacheflush.c b/arch/riscv/mm/cacheflush.c index 89f81067e09e..2ae1201cff88 100644 --- a/arch/riscv/mm/cacheflush.c +++ b/arch/riscv/mm/cacheflush.c @@ -85,7 +85,9 @@ void flush_icache_pte(pte_t pte) { struct page *page = pte_page(pte); - if (!test_and_set_bit(PG_dcache_clean, &page->flags)) + if (!test_bit(PG_dcache_clean, &page->flags)) { flush_icache_all(); + set_bit(PG_dcache_clean, &page->flags); + } } #endif /* CONFIG_MMU */ |
