diff options
author | Mahantesh Kumbar <mkumbar@nvidia.com> | 2016-06-02 08:08:37 -0400 |
---|---|---|
committer | Terje Bergstrom <tbergstrom@nvidia.com> | 2016-06-04 18:21:35 -0400 |
commit | f99de40936236b4e8b00fa847f502c7b94af85c3 (patch) | |
tree | 0be307642c99a03e1807fbe5549e5c47fb6ded1e /drivers/gpu | |
parent | 608101dbfa1c99069ca2abe9d70a204419f8e719 (diff) |
gpu: nvgpu: WPR & PMU interface update
Update WPR interface & PMU interface
to support latest ACR/PMU ucode versions
Change-Id: I4d1bd7a5c43751e96c1db58832cd316006d56954
Signed-off-by: Mahantesh Kumbar <mkumbar@nvidia.com>
Reviewed-on: http://git-master/r/1158070
Reviewed-by: Automatic_Commit_Validation_User
GVS: Gerrit_Virtual_Submit
Reviewed-by: Terje Bergstrom <tbergstrom@nvidia.com>
Tested-by: Terje Bergstrom <tbergstrom@nvidia.com>
Diffstat (limited to 'drivers/gpu')
-rw-r--r-- | drivers/gpu/nvgpu/gk20a/gk20a.h | 4 | ||||
-rw-r--r-- | drivers/gpu/nvgpu/gk20a/pmu_gk20a.c | 4 | ||||
-rw-r--r-- | drivers/gpu/nvgpu/gk20a/pmu_gk20a.h | 32 | ||||
-rw-r--r-- | drivers/gpu/nvgpu/gm20b/acr_gm20b.c | 40 | ||||
-rw-r--r-- | drivers/gpu/nvgpu/gm20b/acr_gm20b.h | 6 |
5 files changed, 62 insertions, 24 deletions
diff --git a/drivers/gpu/nvgpu/gk20a/gk20a.h b/drivers/gpu/nvgpu/gk20a/gk20a.h index 85289087..3da19cc8 100644 --- a/drivers/gpu/nvgpu/gk20a/gk20a.h +++ b/drivers/gpu/nvgpu/gk20a/gk20a.h | |||
@@ -549,10 +549,10 @@ struct gpu_ops { | |||
549 | int (*falcon_clear_halt_interrupt_status)(struct gk20a *g, | 549 | int (*falcon_clear_halt_interrupt_status)(struct gk20a *g, |
550 | unsigned int timeout); | 550 | unsigned int timeout); |
551 | int (*init_falcon_setup_hw)(struct gk20a *g, | 551 | int (*init_falcon_setup_hw)(struct gk20a *g, |
552 | struct flcn_bl_dmem_desc *desc, u32 bl_sz); | 552 | void *desc, u32 bl_sz); |
553 | bool (*is_lazy_bootstrap)(u32 falcon_id); | 553 | bool (*is_lazy_bootstrap)(u32 falcon_id); |
554 | bool (*is_priv_load)(u32 falcon_id); | 554 | bool (*is_priv_load)(u32 falcon_id); |
555 | void (*get_wpr)(struct gk20a *g, u64 *base, u64 *size); | 555 | void (*get_wpr)(struct gk20a *g, struct wpr_carveout_info *inf); |
556 | int (*alloc_blob_space)(struct gk20a *g, | 556 | int (*alloc_blob_space)(struct gk20a *g, |
557 | size_t size, struct mem_desc *mem); | 557 | size_t size, struct mem_desc *mem); |
558 | int (*pmu_populate_loader_cfg)(struct gk20a *g, | 558 | int (*pmu_populate_loader_cfg)(struct gk20a *g, |
diff --git a/drivers/gpu/nvgpu/gk20a/pmu_gk20a.c b/drivers/gpu/nvgpu/gk20a/pmu_gk20a.c index 51ffc552..d12c5987 100644 --- a/drivers/gpu/nvgpu/gk20a/pmu_gk20a.c +++ b/drivers/gpu/nvgpu/gk20a/pmu_gk20a.c | |||
@@ -1623,7 +1623,7 @@ void pmu_copy_to_dmem(struct pmu_gk20a *pmu, | |||
1623 | return; | 1623 | return; |
1624 | } | 1624 | } |
1625 | 1625 | ||
1626 | static int pmu_idle(struct pmu_gk20a *pmu) | 1626 | int pmu_idle(struct pmu_gk20a *pmu) |
1627 | { | 1627 | { |
1628 | struct gk20a *g = gk20a_from_pmu(pmu); | 1628 | struct gk20a *g = gk20a_from_pmu(pmu); |
1629 | unsigned long end_jiffies = jiffies + | 1629 | unsigned long end_jiffies = jiffies + |
@@ -1714,7 +1714,7 @@ void pmu_enable_irq(struct pmu_gk20a *pmu, bool enable) | |||
1714 | gk20a_dbg_fn("done"); | 1714 | gk20a_dbg_fn("done"); |
1715 | } | 1715 | } |
1716 | 1716 | ||
1717 | static int pmu_enable_hw(struct pmu_gk20a *pmu, bool enable) | 1717 | int pmu_enable_hw(struct pmu_gk20a *pmu, bool enable) |
1718 | { | 1718 | { |
1719 | struct gk20a *g = gk20a_from_pmu(pmu); | 1719 | struct gk20a *g = gk20a_from_pmu(pmu); |
1720 | 1720 | ||
diff --git a/drivers/gpu/nvgpu/gk20a/pmu_gk20a.h b/drivers/gpu/nvgpu/gk20a/pmu_gk20a.h index b8bb18a2..7d91b111 100644 --- a/drivers/gpu/nvgpu/gk20a/pmu_gk20a.h +++ b/drivers/gpu/nvgpu/gk20a/pmu_gk20a.h | |||
@@ -450,6 +450,31 @@ struct pmu_ucode_desc { | |||
450 | u32 compressed; | 450 | u32 compressed; |
451 | }; | 451 | }; |
452 | 452 | ||
453 | struct pmu_ucode_desc_v1 { | ||
454 | u32 descriptor_size; | ||
455 | u32 image_size; | ||
456 | u32 tools_version; | ||
457 | u32 app_version; | ||
458 | char date[GK20A_PMU_UCODE_NB_MAX_DATE_LENGTH]; | ||
459 | u32 bootloader_start_offset; | ||
460 | u32 bootloader_size; | ||
461 | u32 bootloader_imem_offset; | ||
462 | u32 bootloader_entry_point; | ||
463 | u32 app_start_offset; | ||
464 | u32 app_size; | ||
465 | u32 app_imem_offset; | ||
466 | u32 app_imem_entry; | ||
467 | u32 app_dmem_offset; | ||
468 | u32 app_resident_code_offset; | ||
469 | u32 app_resident_code_size; | ||
470 | u32 app_resident_data_offset; | ||
471 | u32 app_resident_data_size; | ||
472 | u32 nb_imem_overlays; | ||
473 | u32 nb_dmem_overlays; | ||
474 | struct {u32 start; u32 size; } load_ovl[64]; | ||
475 | u32 compressed; | ||
476 | }; | ||
477 | |||
453 | #define PMU_UNIT_REWIND (0x00) | 478 | #define PMU_UNIT_REWIND (0x00) |
454 | #define PMU_UNIT_PG (0x03) | 479 | #define PMU_UNIT_PG (0x03) |
455 | #define PMU_UNIT_INIT (0x07) | 480 | #define PMU_UNIT_INIT (0x07) |
@@ -1295,7 +1320,10 @@ struct pmu_pg_stats { | |||
1295 | 1320 | ||
1296 | struct pmu_gk20a { | 1321 | struct pmu_gk20a { |
1297 | 1322 | ||
1298 | struct pmu_ucode_desc *desc; | 1323 | union { |
1324 | struct pmu_ucode_desc *desc; | ||
1325 | struct pmu_ucode_desc_v1 *desc_v1; | ||
1326 | }; | ||
1299 | struct mem_desc ucode; | 1327 | struct mem_desc ucode; |
1300 | 1328 | ||
1301 | struct mem_desc pg_buf; | 1329 | struct mem_desc pg_buf; |
@@ -1427,5 +1455,7 @@ void pmu_handle_fecs_boot_acr_msg(struct gk20a *g, struct pmu_msg *msg, | |||
1427 | void gk20a_pmu_elpg_statistics(struct gk20a *g, | 1455 | void gk20a_pmu_elpg_statistics(struct gk20a *g, |
1428 | u32 *ingating_time, u32 *ungating_time, u32 *gating_cnt); | 1456 | u32 *ingating_time, u32 *ungating_time, u32 *gating_cnt); |
1429 | int gk20a_pmu_reset(struct gk20a *g); | 1457 | int gk20a_pmu_reset(struct gk20a *g); |
1458 | int pmu_idle(struct pmu_gk20a *pmu); | ||
1459 | int pmu_enable_hw(struct pmu_gk20a *pmu, bool enable); | ||
1430 | 1460 | ||
1431 | #endif /*__PMU_GK20A_H__*/ | 1461 | #endif /*__PMU_GK20A_H__*/ |
diff --git a/drivers/gpu/nvgpu/gm20b/acr_gm20b.c b/drivers/gpu/nvgpu/gm20b/acr_gm20b.c index 1b8e7b5f..7ef6be09 100644 --- a/drivers/gpu/nvgpu/gm20b/acr_gm20b.c +++ b/drivers/gpu/nvgpu/gm20b/acr_gm20b.c | |||
@@ -43,7 +43,7 @@ static int gm20b_bootstrap_hs_flcn(struct gk20a *g); | |||
43 | static int pmu_wait_for_halt(struct gk20a *g, unsigned int timeout); | 43 | static int pmu_wait_for_halt(struct gk20a *g, unsigned int timeout); |
44 | static int clear_halt_interrupt_status(struct gk20a *g, unsigned int timeout); | 44 | static int clear_halt_interrupt_status(struct gk20a *g, unsigned int timeout); |
45 | static int gm20b_init_pmu_setup_hw1(struct gk20a *g, | 45 | static int gm20b_init_pmu_setup_hw1(struct gk20a *g, |
46 | struct flcn_bl_dmem_desc *desc, u32 bl_sz); | 46 | void *desc, u32 bl_sz); |
47 | static int lsfm_discover_ucode_images(struct gk20a *g, | 47 | static int lsfm_discover_ucode_images(struct gk20a *g, |
48 | struct ls_flcn_mgr *plsfm); | 48 | struct ls_flcn_mgr *plsfm); |
49 | static int lsfm_add_ucode_img(struct gk20a *g, struct ls_flcn_mgr *plsfm, | 49 | static int lsfm_add_ucode_img(struct gk20a *g, struct ls_flcn_mgr *plsfm, |
@@ -62,7 +62,7 @@ static int gm20b_alloc_blob_space(struct gk20a *g, | |||
62 | size_t size, struct mem_desc *mem); | 62 | size_t size, struct mem_desc *mem); |
63 | static bool gm20b_is_priv_load(u32 falcon_id); | 63 | static bool gm20b_is_priv_load(u32 falcon_id); |
64 | static bool gm20b_is_lazy_bootstrap(u32 falcon_id); | 64 | static bool gm20b_is_lazy_bootstrap(u32 falcon_id); |
65 | static void gm20b_wpr_info(struct gk20a *g, u64 *base, u64 *size); | 65 | static void gm20b_wpr_info(struct gk20a *g, struct wpr_carveout_info *inf); |
66 | 66 | ||
67 | /*Globals*/ | 67 | /*Globals*/ |
68 | static get_ucode_details pmu_acr_supp_ucode_list[] = { | 68 | static get_ucode_details pmu_acr_supp_ucode_list[] = { |
@@ -83,13 +83,15 @@ static void start_gm20b_pmu(struct gk20a *g) | |||
83 | pwr_falcon_cpuctl_startcpu_f(1)); | 83 | pwr_falcon_cpuctl_startcpu_f(1)); |
84 | } | 84 | } |
85 | 85 | ||
86 | static void gm20b_wpr_info(struct gk20a *g, u64 *base, u64 *size) | 86 | static void gm20b_wpr_info(struct gk20a *g, struct wpr_carveout_info *inf) |
87 | { | 87 | { |
88 | struct mc_carveout_info inf; | 88 | struct mc_carveout_info mem_inf; |
89 | 89 | ||
90 | mc_get_carveout_info(&inf, NULL, MC_SECURITY_CARVEOUT2); | 90 | mc_get_carveout_info(&mem_inf, NULL, MC_SECURITY_CARVEOUT2); |
91 | *base = inf.base; | 91 | |
92 | *size = inf.size; | 92 | inf->wpr_base = mem_inf.base; |
93 | inf->nonwpr_base = 0; | ||
94 | inf->size = mem_inf.size; | ||
93 | } | 95 | } |
94 | 96 | ||
95 | void gm20b_init_secure_pmu(struct gpu_ops *gops) | 97 | void gm20b_init_secure_pmu(struct gpu_ops *gops) |
@@ -368,7 +370,7 @@ int prepare_ucode_blob(struct gk20a *g) | |||
368 | u32 wprsize; | 370 | u32 wprsize; |
369 | struct mm_gk20a *mm = &g->mm; | 371 | struct mm_gk20a *mm = &g->mm; |
370 | struct vm_gk20a *vm = &mm->pmu.vm; | 372 | struct vm_gk20a *vm = &mm->pmu.vm; |
371 | struct mc_carveout_info inf; | 373 | struct wpr_carveout_info wpr_inf; |
372 | struct sg_table *sgt; | 374 | struct sg_table *sgt; |
373 | struct page *page; | 375 | struct page *page; |
374 | 376 | ||
@@ -388,10 +390,10 @@ int prepare_ucode_blob(struct gk20a *g) | |||
388 | gm20b_mm_mmu_vpr_info_fetch(g); | 390 | gm20b_mm_mmu_vpr_info_fetch(g); |
389 | gr_gk20a_init_ctxsw_ucode(g); | 391 | gr_gk20a_init_ctxsw_ucode(g); |
390 | 392 | ||
391 | g->ops.pmu.get_wpr(g, &inf.base, &inf.size); | 393 | g->ops.pmu.get_wpr(g, &wpr_inf); |
392 | wpr_addr = (phys_addr_t)inf.base; | 394 | wpr_addr = (phys_addr_t)wpr_inf.wpr_base; |
393 | wprsize = (u32)inf.size; | 395 | wprsize = (u32)wpr_inf.size; |
394 | gm20b_dbg_pmu("wpr carveout base:%llx\n", inf.base); | 396 | gm20b_dbg_pmu("wpr carveout base:%llx\n", wpr_inf.wpr_base); |
395 | gm20b_dbg_pmu("wpr carveout size :%x\n", wprsize); | 397 | gm20b_dbg_pmu("wpr carveout size :%x\n", wprsize); |
396 | 398 | ||
397 | sgt = kzalloc(sizeof(*sgt), GFP_KERNEL); | 399 | sgt = kzalloc(sizeof(*sgt), GFP_KERNEL); |
@@ -539,7 +541,7 @@ static int lsfm_discover_ucode_images(struct gk20a *g, | |||
539 | static int gm20b_pmu_populate_loader_cfg(struct gk20a *g, | 541 | static int gm20b_pmu_populate_loader_cfg(struct gk20a *g, |
540 | void *lsfm, u32 *p_bl_gen_desc_size) | 542 | void *lsfm, u32 *p_bl_gen_desc_size) |
541 | { | 543 | { |
542 | struct mc_carveout_info inf; | 544 | struct wpr_carveout_info wpr_inf; |
543 | struct pmu_gk20a *pmu = &g->pmu; | 545 | struct pmu_gk20a *pmu = &g->pmu; |
544 | struct lsfm_managed_ucode_img *p_lsfm = | 546 | struct lsfm_managed_ucode_img *p_lsfm = |
545 | (struct lsfm_managed_ucode_img *)lsfm; | 547 | (struct lsfm_managed_ucode_img *)lsfm; |
@@ -563,8 +565,8 @@ static int gm20b_pmu_populate_loader_cfg(struct gk20a *g, | |||
563 | physical addresses of each respective segment. | 565 | physical addresses of each respective segment. |
564 | */ | 566 | */ |
565 | addr_base = p_lsfm->lsb_header.ucode_off; | 567 | addr_base = p_lsfm->lsb_header.ucode_off; |
566 | g->ops.pmu.get_wpr(g, &inf.base, &inf.size); | 568 | g->ops.pmu.get_wpr(g, &wpr_inf); |
567 | addr_base += inf.base; | 569 | addr_base += wpr_inf.wpr_base; |
568 | gm20b_dbg_pmu("pmu loader cfg u32 addrbase %x\n", (u32)addr_base); | 570 | gm20b_dbg_pmu("pmu loader cfg u32 addrbase %x\n", (u32)addr_base); |
569 | /*From linux*/ | 571 | /*From linux*/ |
570 | addr_code = u64_lo32((addr_base + | 572 | addr_code = u64_lo32((addr_base + |
@@ -611,7 +613,7 @@ static int gm20b_pmu_populate_loader_cfg(struct gk20a *g, | |||
611 | static int gm20b_flcn_populate_bl_dmem_desc(struct gk20a *g, | 613 | static int gm20b_flcn_populate_bl_dmem_desc(struct gk20a *g, |
612 | void *lsfm, u32 *p_bl_gen_desc_size, u32 falconid) | 614 | void *lsfm, u32 *p_bl_gen_desc_size, u32 falconid) |
613 | { | 615 | { |
614 | struct mc_carveout_info inf; | 616 | struct wpr_carveout_info wpr_inf; |
615 | struct lsfm_managed_ucode_img *p_lsfm = | 617 | struct lsfm_managed_ucode_img *p_lsfm = |
616 | (struct lsfm_managed_ucode_img *)lsfm; | 618 | (struct lsfm_managed_ucode_img *)lsfm; |
617 | struct flcn_ucode_img *p_img = &(p_lsfm->ucode_img); | 619 | struct flcn_ucode_img *p_img = &(p_lsfm->ucode_img); |
@@ -635,11 +637,11 @@ static int gm20b_flcn_populate_bl_dmem_desc(struct gk20a *g, | |||
635 | physical addresses of each respective segment. | 637 | physical addresses of each respective segment. |
636 | */ | 638 | */ |
637 | addr_base = p_lsfm->lsb_header.ucode_off; | 639 | addr_base = p_lsfm->lsb_header.ucode_off; |
638 | g->ops.pmu.get_wpr(g, &inf.base, &inf.size); | 640 | g->ops.pmu.get_wpr(g, &wpr_inf); |
639 | if (falconid == LSF_FALCON_ID_GPCCS) | 641 | if (falconid == LSF_FALCON_ID_GPCCS) |
640 | addr_base += g->pmu.wpr_buf.gpu_va; | 642 | addr_base += g->pmu.wpr_buf.gpu_va; |
641 | else | 643 | else |
642 | addr_base += inf.base; | 644 | addr_base += wpr_inf.wpr_base; |
643 | gm20b_dbg_pmu("gen loader cfg %x u32 addrbase %x ID\n", (u32)addr_base, | 645 | gm20b_dbg_pmu("gen loader cfg %x u32 addrbase %x ID\n", (u32)addr_base, |
644 | p_lsfm->wpr_header.falcon_id); | 646 | p_lsfm->wpr_header.falcon_id); |
645 | addr_code = u64_lo32((addr_base + | 647 | addr_code = u64_lo32((addr_base + |
@@ -1299,7 +1301,7 @@ int gm20b_init_nspmu_setup_hw1(struct gk20a *g) | |||
1299 | } | 1301 | } |
1300 | 1302 | ||
1301 | static int gm20b_init_pmu_setup_hw1(struct gk20a *g, | 1303 | static int gm20b_init_pmu_setup_hw1(struct gk20a *g, |
1302 | struct flcn_bl_dmem_desc *desc, u32 bl_sz) | 1304 | void *desc, u32 bl_sz) |
1303 | { | 1305 | { |
1304 | 1306 | ||
1305 | struct pmu_gk20a *pmu = &g->pmu; | 1307 | struct pmu_gk20a *pmu = &g->pmu; |
diff --git a/drivers/gpu/nvgpu/gm20b/acr_gm20b.h b/drivers/gpu/nvgpu/gm20b/acr_gm20b.h index a1dceae9..51492827 100644 --- a/drivers/gpu/nvgpu/gm20b/acr_gm20b.h +++ b/drivers/gpu/nvgpu/gm20b/acr_gm20b.h | |||
@@ -386,6 +386,12 @@ struct acr_fw_header { | |||
386 | u32 hdr_size; /*size of above header*/ | 386 | u32 hdr_size; /*size of above header*/ |
387 | }; | 387 | }; |
388 | 388 | ||
389 | struct wpr_carveout_info { | ||
390 | u64 wpr_base; | ||
391 | u64 nonwpr_base; | ||
392 | u64 size; | ||
393 | }; | ||
394 | |||
389 | void gm20b_init_secure_pmu(struct gpu_ops *gops); | 395 | void gm20b_init_secure_pmu(struct gpu_ops *gops); |
390 | int prepare_ucode_blob(struct gk20a *g); | 396 | int prepare_ucode_blob(struct gk20a *g); |
391 | int gm20b_pmu_setup_sw(struct gk20a *g); | 397 | int gm20b_pmu_setup_sw(struct gk20a *g); |