summaryrefslogtreecommitdiffstats
path: root/drivers/gpu
diff options
context:
space:
mode:
authorMahantesh Kumbar <mkumbar@nvidia.com>2017-10-04 10:11:04 -0400
committermobile promotions <svcmobile_promotions@nvidia.com>2017-10-21 20:34:34 -0400
commit2904e3ac0081d4e898378f6ba667658c85547368 (patch)
tree856be258a7c213c8f03179218e2111bf8bc6e6bf /drivers/gpu
parent324cf7b49e83f9641fde7ba97958b085da615d78 (diff)
gpu: nvgpu: gv100 memory unlock support
- Added method to load mem unlock binary into nvdec falcon & execute to perform mem unlock if VPR enabled. - Updated .mem_unlock gv100 HAL to point method gv100_fb_memory_unlock(). - Updated .mem_unlock gv11b HAL to NULL. - Added vpr info hw registers - Added nvdec enable hw register Change-Id: Ia4bf820ae103baede679d300d1d390fd748c919a Signed-off-by: Mahantesh Kumbar <mkumbar@nvidia.com> (cherry picked from commit 2e176ad9d47316bf4d001692a2ae07e6c1fb1ccb) Reviewed-on: https://git-master.nvidia.com/r/1573101 Reviewed-by: mobile promotions <svcmobile_promotions@nvidia.com> Tested-by: mobile promotions <svcmobile_promotions@nvidia.com>
Diffstat (limited to 'drivers/gpu')
-rw-r--r--drivers/gpu/nvgpu/gv100/fb_gv100.c124
-rw-r--r--drivers/gpu/nvgpu/gv100/fb_gv100.h1
-rw-r--r--drivers/gpu/nvgpu/gv100/hal_gv100.c1
-rw-r--r--drivers/gpu/nvgpu/gv11b/hal_gv11b.c1
-rw-r--r--drivers/gpu/nvgpu/include/nvgpu/hw/gv100/hw_fb_gv100.h36
-rw-r--r--drivers/gpu/nvgpu/include/nvgpu/hw/gv100/hw_mc_gv100.h8
6 files changed, 171 insertions, 0 deletions
diff --git a/drivers/gpu/nvgpu/gv100/fb_gv100.c b/drivers/gpu/nvgpu/gv100/fb_gv100.c
index bcb6d740..0a2939bf 100644
--- a/drivers/gpu/nvgpu/gv100/fb_gv100.c
+++ b/drivers/gpu/nvgpu/gv100/fb_gv100.c
@@ -28,14 +28,25 @@
28#include <nvgpu/log.h> 28#include <nvgpu/log.h>
29#include <nvgpu/enabled.h> 29#include <nvgpu/enabled.h>
30#include <nvgpu/gmmu.h> 30#include <nvgpu/gmmu.h>
31#include <nvgpu/nvgpu_common.h>
32#include <nvgpu/kmem.h>
33#include <nvgpu/nvgpu_mem.h>
34#include <nvgpu/acr/nvgpu_acr.h>
35#include <nvgpu/firmware.h>
36#include <nvgpu/pmu.h>
37#include <nvgpu/falcon.h>
31 38
32#include "gk20a/gk20a.h" 39#include "gk20a/gk20a.h"
33#include "gv100/fb_gv100.h" 40#include "gv100/fb_gv100.h"
41#include "gm20b/acr_gm20b.h"
34 42
35#include <nvgpu/hw/gv100/hw_fb_gv100.h> 43#include <nvgpu/hw/gv100/hw_fb_gv100.h>
44#include <nvgpu/hw/gv100/hw_falcon_gv100.h>
45#include <nvgpu/hw/gv100/hw_mc_gv100.h>
36 46
37#define HW_SCRUB_TIMEOUT_DEFAULT 100 /* usec */ 47#define HW_SCRUB_TIMEOUT_DEFAULT 100 /* usec */
38#define HW_SCRUB_TIMEOUT_MAX 2000000 /* usec */ 48#define HW_SCRUB_TIMEOUT_MAX 2000000 /* usec */
49#define MEM_UNLOCK_TIMEOUT 3500 /* msec */
39 50
40void gv100_fb_reset(struct gk20a *g) 51void gv100_fb_reset(struct gk20a *g)
41{ 52{
@@ -58,3 +69,116 @@ void gv100_fb_reset(struct gk20a *g)
58 val &= ~fb_mmu_priv_level_mask_write_violation_m(); 69 val &= ~fb_mmu_priv_level_mask_write_violation_m();
59 gk20a_writel(g, fb_mmu_priv_level_mask_r(), val); 70 gk20a_writel(g, fb_mmu_priv_level_mask_r(), val);
60} 71}
72
73int gv100_fb_memory_unlock(struct gk20a *g)
74{
75 struct nvgpu_firmware *mem_unlock_fw = NULL;
76 struct bin_hdr *hsbin_hdr = NULL;
77 struct acr_fw_header *fw_hdr = NULL;
78 u32 *mem_unlock_ucode = NULL;
79 u32 *mem_unlock_ucode_header = NULL;
80 u32 sec_imem_dest = 0;
81 u32 val = 0;
82 int err = 0;
83
84 nvgpu_log_fn(g, " ");
85
86 /* Check vpr enable status */
87 val = gk20a_readl(g, fb_mmu_vpr_info_r());
88 val &= ~fb_mmu_vpr_info_index_m();
89 val |= fb_mmu_vpr_info_index_cya_lo_v();
90 gk20a_writel(g, fb_mmu_vpr_info_r(), val);
91 val = gk20a_readl(g, fb_mmu_vpr_info_r());
92 if (!(val & fb_mmu_vpr_info_cya_lo_in_use_m())) {
93 nvgpu_log_info(g, "mem unlock not required on this SKU, skipping");
94 goto exit;
95 }
96
97 /* get mem unlock ucode binary */
98 mem_unlock_fw = nvgpu_request_firmware(g, "mem_unlock.bin", 0);
99 if (!mem_unlock_fw) {
100 nvgpu_err(g, "mem unlock ucode get fail");
101 err = -ENOENT;
102 goto exit;
103 }
104
105 /* Enable nvdec */
106 g->ops.mc.enable(g, mc_enable_nvdec_enabled_f());
107
108 /* nvdec falcon reset */
109 nvgpu_flcn_reset(&g->nvdec_flcn);
110
111 hsbin_hdr = (struct bin_hdr *)mem_unlock_fw->data;
112 fw_hdr = (struct acr_fw_header *)(mem_unlock_fw->data +
113 hsbin_hdr->header_offset);
114
115 mem_unlock_ucode_header = (u32 *)(mem_unlock_fw->data +
116 fw_hdr->hdr_offset);
117 mem_unlock_ucode = (u32 *)(mem_unlock_fw->data +
118 hsbin_hdr->data_offset);
119
120 /* Patch Ucode singnatures */
121 if (acr_ucode_patch_sig(g, mem_unlock_ucode,
122 (u32 *)(mem_unlock_fw->data + fw_hdr->sig_prod_offset),
123 (u32 *)(mem_unlock_fw->data + fw_hdr->sig_dbg_offset),
124 (u32 *)(mem_unlock_fw->data + fw_hdr->patch_loc),
125 (u32 *)(mem_unlock_fw->data + fw_hdr->patch_sig)) < 0) {
126 nvgpu_err(g, "mem unlock patch signatures fail");
127 err = -EPERM;
128 goto exit;
129 }
130
131 /* Clear interrupts */
132 nvgpu_flcn_set_irq(&g->nvdec_flcn, false, 0x0, 0x0);
133
134 /* Copy Non Secure IMEM code */
135 nvgpu_flcn_copy_to_imem(&g->nvdec_flcn, 0,
136 (u8 *)&mem_unlock_ucode[
137 mem_unlock_ucode_header[OS_CODE_OFFSET] >> 2],
138 mem_unlock_ucode_header[OS_CODE_SIZE], 0, false,
139 GET_IMEM_TAG(mem_unlock_ucode_header[OS_CODE_OFFSET]));
140
141 /* Put secure code after non-secure block */
142 sec_imem_dest = GET_NEXT_BLOCK(mem_unlock_ucode_header[OS_CODE_SIZE]);
143
144 nvgpu_flcn_copy_to_imem(&g->nvdec_flcn, sec_imem_dest,
145 (u8 *)&mem_unlock_ucode[
146 mem_unlock_ucode_header[APP_0_CODE_OFFSET] >> 2],
147 mem_unlock_ucode_header[APP_0_CODE_SIZE], 0, true,
148 GET_IMEM_TAG(mem_unlock_ucode_header[APP_0_CODE_OFFSET]));
149
150 /* load DMEM: ensure that signatures are patched */
151 nvgpu_flcn_copy_to_dmem(&g->nvdec_flcn, 0, (u8 *)&mem_unlock_ucode[
152 mem_unlock_ucode_header[OS_DATA_OFFSET] >> 2],
153 mem_unlock_ucode_header[OS_DATA_SIZE], 0);
154
155 nvgpu_log_info(g, "nvdec sctl reg %x\n",
156 gk20a_readl(g, g->nvdec_flcn.flcn_base +
157 falcon_falcon_sctl_r()));
158
159 /* set BOOTVEC to start of non-secure code */
160 nvgpu_flcn_bootstrap(&g->nvdec_flcn, 0);
161
162 /* wait for complete & halt */
163 nvgpu_flcn_wait_for_halt(&g->nvdec_flcn, MEM_UNLOCK_TIMEOUT);
164
165 /* check mem unlock status */
166 val = nvgpu_flcn_mailbox_read(&g->nvdec_flcn, 0);
167 if (val) {
168 nvgpu_err(g, "memory unlock failed, err %x", val);
169 err = -1;
170 goto exit;
171 }
172
173 nvgpu_log_info(g, "nvdec sctl reg %x\n",
174 gk20a_readl(g, g->nvdec_flcn.flcn_base +
175 falcon_falcon_sctl_r()));
176
177exit:
178 if (mem_unlock_fw)
179 nvgpu_release_firmware(g, mem_unlock_fw);
180
181 nvgpu_log_fn(g, "done, status - %d", err);
182
183 return err;
184}
diff --git a/drivers/gpu/nvgpu/gv100/fb_gv100.h b/drivers/gpu/nvgpu/gv100/fb_gv100.h
index d5a36661..b6db262a 100644
--- a/drivers/gpu/nvgpu/gv100/fb_gv100.h
+++ b/drivers/gpu/nvgpu/gv100/fb_gv100.h
@@ -28,4 +28,5 @@
28struct gk20a; 28struct gk20a;
29 29
30void gv100_fb_reset(struct gk20a *g); 30void gv100_fb_reset(struct gk20a *g);
31int gv100_fb_memory_unlock(struct gk20a *g);
31#endif 32#endif
diff --git a/drivers/gpu/nvgpu/gv100/hal_gv100.c b/drivers/gpu/nvgpu/gv100/hal_gv100.c
index 2007eee0..4e05f22b 100644
--- a/drivers/gpu/nvgpu/gv100/hal_gv100.c
+++ b/drivers/gpu/nvgpu/gv100/hal_gv100.c
@@ -421,6 +421,7 @@ static const struct gpu_ops gv100_ops = {
421 .set_debug_mode = gm20b_fb_set_debug_mode, 421 .set_debug_mode = gm20b_fb_set_debug_mode,
422 .tlb_invalidate = gk20a_fb_tlb_invalidate, 422 .tlb_invalidate = gk20a_fb_tlb_invalidate,
423 .hub_isr = gv11b_fb_hub_isr, 423 .hub_isr = gv11b_fb_hub_isr,
424 .mem_unlock = gv100_fb_memory_unlock,
424 }, 425 },
425 .fifo = { 426 .fifo = {
426 .init_fifo_setup_hw = gv11b_init_fifo_setup_hw, 427 .init_fifo_setup_hw = gv11b_init_fifo_setup_hw,
diff --git a/drivers/gpu/nvgpu/gv11b/hal_gv11b.c b/drivers/gpu/nvgpu/gv11b/hal_gv11b.c
index 22beabf7..729727c9 100644
--- a/drivers/gpu/nvgpu/gv11b/hal_gv11b.c
+++ b/drivers/gpu/nvgpu/gv11b/hal_gv11b.c
@@ -385,6 +385,7 @@ static const struct gpu_ops gv11b_ops = {
385 .set_debug_mode = gm20b_fb_set_debug_mode, 385 .set_debug_mode = gm20b_fb_set_debug_mode,
386 .tlb_invalidate = gk20a_fb_tlb_invalidate, 386 .tlb_invalidate = gk20a_fb_tlb_invalidate,
387 .hub_isr = gv11b_fb_hub_isr, 387 .hub_isr = gv11b_fb_hub_isr,
388 .mem_unlock = NULL,
388 }, 389 },
389 .clock_gating = { 390 .clock_gating = {
390 .slcg_bus_load_gating_prod = 391 .slcg_bus_load_gating_prod =
diff --git a/drivers/gpu/nvgpu/include/nvgpu/hw/gv100/hw_fb_gv100.h b/drivers/gpu/nvgpu/include/nvgpu/hw/gv100/hw_fb_gv100.h
index 3bba3fb8..a4fcd1e6 100644
--- a/drivers/gpu/nvgpu/include/nvgpu/hw/gv100/hw_fb_gv100.h
+++ b/drivers/gpu/nvgpu/include/nvgpu/hw/gv100/hw_fb_gv100.h
@@ -460,6 +460,42 @@ static inline u32 fb_mmu_vpr_info_r(void)
460{ 460{
461 return 0x00100cd0U; 461 return 0x00100cd0U;
462} 462}
463static inline u32 fb_mmu_vpr_info_index_f(u32 v)
464{
465 return (v & 0x3U) << 0U;
466}
467static inline u32 fb_mmu_vpr_info_index_v(u32 r)
468{
469 return (r >> 0U) & 0x3U;
470}
471static inline u32 fb_mmu_vpr_info_index_m(void)
472{
473 return 0x3U << 0U;
474}
475static inline u32 fb_mmu_vpr_info_index_addr_lo_v(void)
476{
477 return 0x00000000U;
478}
479static inline u32 fb_mmu_vpr_info_index_addr_hi_v(void)
480{
481 return 0x00000001U;
482}
483static inline u32 fb_mmu_vpr_info_index_cya_lo_v(void)
484{
485 return 0x00000002U;
486}
487static inline u32 fb_mmu_vpr_info_index_cya_hi_v(void)
488{
489 return 0x00000003U;
490}
491static inline u32 fb_mmu_vpr_info_cya_lo_in_use_m(void)
492{
493 return 0x1U << 4U;
494}
495static inline u32 fb_mmu_vpr_info_fetch_f(u32 v)
496{
497 return (v & 0x1U) << 2U;
498}
463static inline u32 fb_mmu_vpr_info_fetch_v(u32 r) 499static inline u32 fb_mmu_vpr_info_fetch_v(u32 r)
464{ 500{
465 return (r >> 2U) & 0x1U; 501 return (r >> 2U) & 0x1U;
diff --git a/drivers/gpu/nvgpu/include/nvgpu/hw/gv100/hw_mc_gv100.h b/drivers/gpu/nvgpu/include/nvgpu/hw/gv100/hw_mc_gv100.h
index 2efeac79..f367991e 100644
--- a/drivers/gpu/nvgpu/include/nvgpu/hw/gv100/hw_mc_gv100.h
+++ b/drivers/gpu/nvgpu/include/nvgpu/hw/gv100/hw_mc_gv100.h
@@ -196,6 +196,14 @@ static inline u32 mc_enable_hub_enabled_f(void)
196{ 196{
197 return 0x20000000U; 197 return 0x20000000U;
198} 198}
199static inline u32 mc_enable_nvdec_disabled_v(void)
200{
201 return 0x00000000U;
202}
203static inline u32 mc_enable_nvdec_enabled_f(void)
204{
205 return 0x8000U;
206}
199static inline u32 mc_intr_ltc_r(void) 207static inline u32 mc_intr_ltc_r(void)
200{ 208{
201 return 0x000001c0U; 209 return 0x000001c0U;