diff options
Diffstat (limited to 'drivers/gpu/nvgpu/gv11b/fb_gv11b.c')
-rw-r--r-- | drivers/gpu/nvgpu/gv11b/fb_gv11b.c | 27 |
1 files changed, 22 insertions, 5 deletions
diff --git a/drivers/gpu/nvgpu/gv11b/fb_gv11b.c b/drivers/gpu/nvgpu/gv11b/fb_gv11b.c index 75045800..d89018e5 100644 --- a/drivers/gpu/nvgpu/gv11b/fb_gv11b.c +++ b/drivers/gpu/nvgpu/gv11b/fb_gv11b.c | |||
@@ -1434,13 +1434,19 @@ static void gv11b_fb_handle_mmu_fault_common(struct gk20a *g, | |||
1434 | g->ops.fifo.teardown_ch_tsg(g, act_eng_bitmask, | 1434 | g->ops.fifo.teardown_ch_tsg(g, act_eng_bitmask, |
1435 | id, id_type, RC_TYPE_MMU_FAULT, mmfault); | 1435 | id, id_type, RC_TYPE_MMU_FAULT, mmfault); |
1436 | } else { | 1436 | } else { |
1437 | err = gv11b_fb_fix_page_fault(g, mmfault); | 1437 | if (mmfault->fault_type == gmmu_fault_type_pte_v()) { |
1438 | if (err) { | 1438 | nvgpu_log(g, gpu_dbg_intr, "invalid pte! try to fix"); |
1439 | *invalidate_replay_val |= | 1439 | err = gv11b_fb_fix_page_fault(g, mmfault); |
1440 | fb_mmu_invalidate_replay_cancel_global_f(); | 1440 | if (err) |
1441 | *invalidate_replay_val |= | ||
1442 | fb_mmu_invalidate_replay_cancel_global_f(); | ||
1443 | else | ||
1444 | *invalidate_replay_val |= | ||
1445 | fb_mmu_invalidate_replay_start_ack_all_f(); | ||
1441 | } else { | 1446 | } else { |
1447 | /* cancel faults other than invalid pte */ | ||
1442 | *invalidate_replay_val |= | 1448 | *invalidate_replay_val |= |
1443 | fb_mmu_invalidate_replay_start_ack_all_f(); | 1449 | fb_mmu_invalidate_replay_cancel_global_f(); |
1444 | } | 1450 | } |
1445 | /* refch in mmfault is assigned at the time of copying | 1451 | /* refch in mmfault is assigned at the time of copying |
1446 | * fault info from snap reg or bar2 fault buf | 1452 | * fault info from snap reg or bar2 fault buf |
@@ -1960,6 +1966,17 @@ static int gv11b_fb_fix_page_fault(struct gk20a *g, | |||
1960 | nvgpu_log(g, gpu_dbg_intr | gpu_dbg_pte, | 1966 | nvgpu_log(g, gpu_dbg_intr | gpu_dbg_pte, |
1961 | "pte: %#08x %#08x", pte[1], pte[0]); | 1967 | "pte: %#08x %#08x", pte[1], pte[0]); |
1962 | 1968 | ||
1969 | if (pte[0] == 0x0 && pte[1] == 0x0) { | ||
1970 | nvgpu_log(g, gpu_dbg_intr | gpu_dbg_pte, | ||
1971 | "pte all zeros, do not set valid"); | ||
1972 | return -1; | ||
1973 | } | ||
1974 | if (pte[0] & gmmu_new_pte_valid_true_f()) { | ||
1975 | nvgpu_log(g, gpu_dbg_intr | gpu_dbg_pte, | ||
1976 | "pte valid already set"); | ||
1977 | return -1; | ||
1978 | } | ||
1979 | |||
1963 | pte[0] |= gmmu_new_pte_valid_true_f(); | 1980 | pte[0] |= gmmu_new_pte_valid_true_f(); |
1964 | if (pte[0] & gmmu_new_pte_read_only_true_f()) | 1981 | if (pte[0] & gmmu_new_pte_read_only_true_f()) |
1965 | pte[0] &= ~(gmmu_new_pte_read_only_true_f()); | 1982 | pte[0] &= ~(gmmu_new_pte_read_only_true_f()); |