summaryrefslogtreecommitdiffstats
path: root/drivers/gpu
diff options
context:
space:
mode:
authorArto Merilainen <amerilainen@nvidia.com>2014-04-09 07:50:43 -0400
committerDan Willemsen <dwillemsen@nvidia.com>2015-03-18 15:09:05 -0400
commitd4586cc3ab132fd03dce731e1e053bd70d9122cf (patch)
tree47e340280b4d89a6e833661e01491d5721cbbc3e /drivers/gpu
parent3eedb0256d0fd1f2a26a9609d2c2e7baf8240306 (diff)
gpu: nvgpu: Alloc physical mem for CBC in sim
CBC frontdoor access works incorrectly in the simulator if CBC is allocated from IOVA. This patch makes CBC allocation to happen from physical memory if are running in simulator. Bug 1409151 Change-Id: Ia1d1ca35b5a0375f4707824df3ef06ad1b9117d4 Signed-off-by: Arto Merilainen <amerilainen@nvidia.com>
Diffstat (limited to 'drivers/gpu')
-rw-r--r--drivers/gpu/nvgpu/gk20a/ltc_common.c94
-rw-r--r--drivers/gpu/nvgpu/gk20a/ltc_gk20a.c24
-rw-r--r--drivers/gpu/nvgpu/gk20a/mm_gk20a.h2
3 files changed, 100 insertions, 20 deletions
diff --git a/drivers/gpu/nvgpu/gk20a/ltc_common.c b/drivers/gpu/nvgpu/gk20a/ltc_common.c
index 8af8c687..2d2516d9 100644
--- a/drivers/gpu/nvgpu/gk20a/ltc_common.c
+++ b/drivers/gpu/nvgpu/gk20a/ltc_common.c
@@ -180,6 +180,85 @@ static int gk20a_ltc_init_zbc(struct gk20a *g, struct gr_gk20a *gr)
180 return 0; 180 return 0;
181} 181}
182 182
183static int gk20a_ltc_alloc_phys_cbc(struct gk20a *g,
184 size_t compbit_backing_size)
185{
186 struct gr_gk20a *gr = &g->gr;
187 int order = ffs(compbit_backing_size >> PAGE_SHIFT);
188 struct page *pages;
189 struct sg_table *sgt;
190 int err = 0;
191
192 /* allocate few pages */
193 pages = alloc_pages(GFP_KERNEL, order);
194 if (!pages) {
195 gk20a_dbg(gpu_dbg_pte, "alloc_pages failed\n");
196 err = -ENOMEM;
197 goto err_alloc_pages;
198 }
199
200 /* clean up the pages */
201 memset(page_address(pages), 0, compbit_backing_size);
202
203 /* allocate room for placing the pages pointer.. */
204 gr->compbit_store.pages =
205 kzalloc(sizeof(*gr->compbit_store.pages), GFP_KERNEL);
206 if (!gr->compbit_store.pages) {
207 gk20a_dbg(gpu_dbg_pte, "failed to allocate pages struct");
208 err = -ENOMEM;
209 goto err_alloc_compbit_store;
210 }
211
212 err = gk20a_get_sgtable_from_pages(&g->dev->dev, &sgt, &pages, 0,
213 compbit_backing_size);
214 if (err) {
215 gk20a_dbg(gpu_dbg_pte, "could not get sg table for pages\n");
216 goto err_alloc_sg_table;
217 }
218
219 /* store the parameters to gr structure */
220 *gr->compbit_store.pages = pages;
221 gr->compbit_store.base_iova = sg_phys(sgt->sgl);
222 gr->compbit_store.size = compbit_backing_size;
223
224 kfree(sgt);
225
226 return 0;
227
228err_alloc_sg_table:
229 kfree(gr->compbit_store.pages);
230 gr->compbit_store.pages = NULL;
231err_alloc_compbit_store:
232 __free_pages(pages, order);
233err_alloc_pages:
234 return err;
235}
236
237static int gk20a_ltc_alloc_virt_cbc(struct gk20a *g,
238 size_t compbit_backing_size)
239{
240 struct device *d = dev_from_gk20a(g);
241 struct gr_gk20a *gr = &g->gr;
242 DEFINE_DMA_ATTRS(attrs);
243 dma_addr_t iova;
244
245 dma_set_attr(DMA_ATTR_NO_KERNEL_MAPPING, &attrs);
246
247 gr->compbit_store.pages =
248 dma_alloc_attrs(d, compbit_backing_size, &iova,
249 GFP_KERNEL, &attrs);
250 if (!gr->compbit_store.pages) {
251 gk20a_err(dev_from_gk20a(g), "failed to allocate backing store for compbit : size %zu",
252 compbit_backing_size);
253 return -ENOMEM;
254 }
255
256 gr->compbit_store.base_iova = iova;
257 gr->compbit_store.size = compbit_backing_size;
258
259 return 0;
260}
261
183static void gk20a_ltc_init_cbc(struct gk20a *g, struct gr_gk20a *gr) 262static void gk20a_ltc_init_cbc(struct gk20a *g, struct gr_gk20a *gr)
184{ 263{
185 u32 max_size = gr->max_comptag_mem; 264 u32 max_size = gr->max_comptag_mem;
@@ -187,10 +266,17 @@ static void gk20a_ltc_init_cbc(struct gk20a *g, struct gr_gk20a *gr)
187 266
188 u32 compbit_base_post_divide; 267 u32 compbit_base_post_divide;
189 u64 compbit_base_post_multiply64; 268 u64 compbit_base_post_multiply64;
190 u64 compbit_store_base_iova = 269 u64 compbit_store_base_iova;
191 NV_MC_SMMU_VADDR_TRANSLATE(gr->compbit_store.base_iova); 270 u64 compbit_base_post_divide64;
192 u64 compbit_base_post_divide64 = (compbit_store_base_iova >> 271
193 ltc_ltcs_ltss_cbc_base_alignment_shift_v()); 272 if (IS_ENABLED(CONFIG_GK20A_PHYS_PAGE_TABLES))
273 compbit_store_base_iova = gr->compbit_store.base_iova;
274 else
275 compbit_store_base_iova = NV_MC_SMMU_VADDR_TRANSLATE(
276 gr->compbit_store.base_iova);
277
278 compbit_base_post_divide64 = compbit_store_base_iova >>
279 ltc_ltcs_ltss_cbc_base_alignment_shift_v();
194 280
195 do_div(compbit_base_post_divide64, gr->num_fbps); 281 do_div(compbit_base_post_divide64, gr->num_fbps);
196 compbit_base_post_divide = u64_lo32(compbit_base_post_divide64); 282 compbit_base_post_divide = u64_lo32(compbit_base_post_divide64);
diff --git a/drivers/gpu/nvgpu/gk20a/ltc_gk20a.c b/drivers/gpu/nvgpu/gk20a/ltc_gk20a.c
index 74475d7a..f5c6d7e7 100644
--- a/drivers/gpu/nvgpu/gk20a/ltc_gk20a.c
+++ b/drivers/gpu/nvgpu/gk20a/ltc_gk20a.c
@@ -27,10 +27,6 @@
27 27
28static int gk20a_ltc_init_comptags(struct gk20a *g, struct gr_gk20a *gr) 28static int gk20a_ltc_init_comptags(struct gk20a *g, struct gr_gk20a *gr)
29{ 29{
30 struct device *d = dev_from_gk20a(g);
31 DEFINE_DMA_ATTRS(attrs);
32 dma_addr_t iova;
33
34 /* max memory size (MB) to cover */ 30 /* max memory size (MB) to cover */
35 u32 max_size = gr->max_comptag_mem; 31 u32 max_size = gr->max_comptag_mem;
36 /* one tag line covers 128KB */ 32 /* one tag line covers 128KB */
@@ -50,6 +46,8 @@ static int gk20a_ltc_init_comptags(struct gk20a *g, struct gr_gk20a *gr)
50 46
51 u32 compbit_backing_size; 47 u32 compbit_backing_size;
52 48
49 int err;
50
53 gk20a_dbg_fn(""); 51 gk20a_dbg_fn("");
54 52
55 if (max_comptag_lines == 0) { 53 if (max_comptag_lines == 0) {
@@ -84,17 +82,13 @@ static int gk20a_ltc_init_comptags(struct gk20a *g, struct gr_gk20a *gr)
84 gk20a_dbg_info("max comptag lines : %d", 82 gk20a_dbg_info("max comptag lines : %d",
85 max_comptag_lines); 83 max_comptag_lines);
86 84
87 dma_set_attr(DMA_ATTR_NO_KERNEL_MAPPING, &attrs); 85 if (IS_ENABLED(CONFIG_GK20A_PHYS_PAGE_TABLES))
88 gr->compbit_store.size = compbit_backing_size; 86 err = gk20a_ltc_alloc_phys_cbc(g, compbit_backing_size);
89 gr->compbit_store.pages = dma_alloc_attrs(d, gr->compbit_store.size, 87 else
90 &iova, GFP_KERNEL, &attrs); 88 err = gk20a_ltc_alloc_virt_cbc(g, compbit_backing_size);
91 if (!gr->compbit_store.pages) { 89
92 gk20a_err(dev_from_gk20a(g), "failed to allocate" 90 if (err)
93 "backing store for compbit : size %d", 91 return err;
94 compbit_backing_size);
95 return -ENOMEM;
96 }
97 gr->compbit_store.base_iova = iova;
98 92
99 gk20a_allocator_init(&gr->comp_tags, "comptag", 93 gk20a_allocator_init(&gr->comp_tags, "comptag",
100 1, /* start */ 94 1, /* start */
diff --git a/drivers/gpu/nvgpu/gk20a/mm_gk20a.h b/drivers/gpu/nvgpu/gk20a/mm_gk20a.h
index cdbab138..d583849d 100644
--- a/drivers/gpu/nvgpu/gk20a/mm_gk20a.h
+++ b/drivers/gpu/nvgpu/gk20a/mm_gk20a.h
@@ -156,7 +156,7 @@ struct gr_ctx_desc {
156}; 156};
157 157
158struct compbit_store_desc { 158struct compbit_store_desc {
159 struct pages **pages; 159 struct page **pages;
160 size_t size; 160 size_t size;
161 u64 base_iova; 161 u64 base_iova;
162}; 162};