Skip to content

Commit a5998fc

Browse files
kvaneeshmpe
authored andcommitted
powerpc/mm/radix: Optimise tlbiel flush all case
_tlbiel_pid() is called with a ric (Radix Invalidation Control) argument of either RIC_FLUSH_TLB or RIC_FLUSH_ALL. RIC_FLUSH_ALL says to invalidate the entire TLB and the Page Walk Cache (PWC). To flush the whole TLB, we have to iterate over each set (congruence class) of the TLB. Currently we do that and pass RIC_FLUSH_ALL each time. That is not incorrect but it means we flush the PWC 128 times, when once would suffice. Fix it by doing the first flush with the ric value we're passed, and then if it was RIC_FLUSH_ALL, we downgrade it to RIC_FLUSH_TLB, because we know we have just flushed the PWC and don't need to do it again. Signed-off-by: Aneesh Kumar K.V <[email protected]> [mpe: Split out of combined patch, tweak logic, rewrite change log] Signed-off-by: Michael Ellerman <[email protected]>
1 parent cf4f08b commit a5998fc

File tree

1 file changed

+13
-2
lines changed

1 file changed

+13
-2
lines changed

arch/powerpc/mm/tlb-radix.c

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -46,9 +46,20 @@ static inline void _tlbiel_pid(unsigned long pid, unsigned long ric)
4646
int set;
4747

4848
asm volatile("ptesync": : :"memory");
49-
for (set = 0; set < POWER9_TLB_SETS_RADIX ; set++) {
49+
50+
/*
51+
* Flush the first set of the TLB, and if we're doing a RIC_FLUSH_ALL,
52+
* also flush the entire Page Walk Cache.
53+
*/
54+
__tlbiel_pid(pid, 0, ric);
55+
56+
if (ric == RIC_FLUSH_ALL)
57+
/* For the remaining sets, just flush the TLB */
58+
ric = RIC_FLUSH_TLB;
59+
60+
for (set = 1; set < POWER9_TLB_SETS_RADIX ; set++)
5061
__tlbiel_pid(pid, set, ric);
51-
}
62+
5263
asm volatile("ptesync": : :"memory");
5364
asm volatile(PPC_INVALIDATE_ERAT "; isync" : : :"memory");
5465
}

0 commit comments

Comments
 (0)