mirror of https://gitee.com/openkylin/qemu.git
target/openrisc: Fix tlb flushing in mtspr
The previous code was confused, avoiding the flush of the old entry if the new entry is invalid. We need to flush the old page if the old entry is valid and the new page if the new entry is valid. This bug was masked by over-flushing elsewhere. Signed-off-by: Richard Henderson <richard.henderson@linaro.org> Signed-off-by: Stafford Horne <shorne@gmail.com>
This commit is contained in:
parent
2acaa2331b
commit
fffde6695f
|
@ -32,6 +32,7 @@ void HELPER(mtspr)(CPUOpenRISCState *env, target_ulong spr, target_ulong rb)
|
|||
#ifndef CONFIG_USER_ONLY
|
||||
OpenRISCCPU *cpu = openrisc_env_get_cpu(env);
|
||||
CPUState *cs = CPU(cpu);
|
||||
target_ulong mr;
|
||||
int idx;
|
||||
|
||||
switch (spr) {
|
||||
|
@ -85,12 +86,15 @@ void HELPER(mtspr)(CPUOpenRISCState *env, target_ulong spr, target_ulong rb)
|
|||
|
||||
case TO_SPR(1, 512) ... TO_SPR(1, 512+DTLB_SIZE-1): /* DTLBW0MR 0-127 */
|
||||
idx = spr - TO_SPR(1, 512);
|
||||
if (!(rb & 1)) {
|
||||
tlb_flush_page(cs, env->tlb.dtlb[idx].mr & TARGET_PAGE_MASK);
|
||||
mr = env->tlb.dtlb[idx].mr;
|
||||
if (mr & 1) {
|
||||
tlb_flush_page(cs, mr & TARGET_PAGE_MASK);
|
||||
}
|
||||
if (rb & 1) {
|
||||
tlb_flush_page(cs, rb & TARGET_PAGE_MASK);
|
||||
}
|
||||
env->tlb.dtlb[idx].mr = rb;
|
||||
break;
|
||||
|
||||
case TO_SPR(1, 640) ... TO_SPR(1, 640+DTLB_SIZE-1): /* DTLBW0TR 0-127 */
|
||||
idx = spr - TO_SPR(1, 640);
|
||||
env->tlb.dtlb[idx].tr = rb;
|
||||
|
@ -102,14 +106,18 @@ void HELPER(mtspr)(CPUOpenRISCState *env, target_ulong spr, target_ulong rb)
|
|||
case TO_SPR(1, 1280) ... TO_SPR(1, 1407): /* DTLBW3MR 0-127 */
|
||||
case TO_SPR(1, 1408) ... TO_SPR(1, 1535): /* DTLBW3TR 0-127 */
|
||||
break;
|
||||
|
||||
case TO_SPR(2, 512) ... TO_SPR(2, 512+ITLB_SIZE-1): /* ITLBW0MR 0-127 */
|
||||
idx = spr - TO_SPR(2, 512);
|
||||
if (!(rb & 1)) {
|
||||
tlb_flush_page(cs, env->tlb.itlb[idx].mr & TARGET_PAGE_MASK);
|
||||
mr = env->tlb.itlb[idx].mr;
|
||||
if (mr & 1) {
|
||||
tlb_flush_page(cs, mr & TARGET_PAGE_MASK);
|
||||
}
|
||||
if (rb & 1) {
|
||||
tlb_flush_page(cs, rb & TARGET_PAGE_MASK);
|
||||
}
|
||||
env->tlb.itlb[idx].mr = rb;
|
||||
break;
|
||||
|
||||
case TO_SPR(2, 640) ... TO_SPR(2, 640+ITLB_SIZE-1): /* ITLBW0TR 0-127 */
|
||||
idx = spr - TO_SPR(2, 640);
|
||||
env->tlb.itlb[idx].tr = rb;
|
||||
|
@ -121,6 +129,7 @@ void HELPER(mtspr)(CPUOpenRISCState *env, target_ulong spr, target_ulong rb)
|
|||
case TO_SPR(2, 1280) ... TO_SPR(2, 1407): /* ITLBW3MR 0-127 */
|
||||
case TO_SPR(2, 1408) ... TO_SPR(2, 1535): /* ITLBW3TR 0-127 */
|
||||
break;
|
||||
|
||||
case TO_SPR(5, 1): /* MACLO */
|
||||
env->mac = deposit64(env->mac, 0, 32, rb);
|
||||
break;
|
||||
|
|
Loading…
Reference in New Issue