summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKevin Huang <kevinh@nvidia.com>2014-05-09 14:41:26 -0400
committerDan Willemsen <dwillemsen@nvidia.com>2015-03-18 15:11:06 -0400
commit1d9eba07c58b0a30f479b233371c939180a0e419 (patch)
tree1b4081a723834d8b295a147e85f6d7b7b205a88c
parent5cd313e20221c93008f1d56ac223d6e08966505e (diff)
gpu: nvgpu: add HAL for regops
Bug 1500195 Change-Id: I5545d1a95a58e7daa5a74cc20f3fc6828774fc42 Signed-off-by: Kevin Huang <kevinh@nvidia.com> Reviewed-on: http://git-master/r/488507 Reviewed-by: Automatic_Commit_Validation_User GVS: Gerrit_Virtual_Submit Reviewed-by: Terje Bergstrom <tbergstrom@nvidia.com>
-rw-r--r--drivers/gpu/nvgpu/gk20a/gk20a.h18
-rw-r--r--drivers/gpu/nvgpu/gk20a/gr_gk20a.c2
-rw-r--r--drivers/gpu/nvgpu/gk20a/hal_gk20a.c2
-rw-r--r--drivers/gpu/nvgpu/gk20a/regops_gk20a.c146
-rw-r--r--drivers/gpu/nvgpu/gk20a/regops_gk20a.h11
5 files changed, 147 insertions, 32 deletions
diff --git a/drivers/gpu/nvgpu/gk20a/gk20a.h b/drivers/gpu/nvgpu/gk20a/gk20a.h
index de234972..fc97fcb9 100644
--- a/drivers/gpu/nvgpu/gk20a/gk20a.h
+++ b/drivers/gpu/nvgpu/gk20a/gk20a.h
@@ -298,6 +298,24 @@ struct gpu_ops {
298 int (*suspend_clk_support)(struct gk20a *g); 298 int (*suspend_clk_support)(struct gk20a *g);
299 } clk; 299 } clk;
300 bool privsecurity; 300 bool privsecurity;
301 struct {
302 const struct regop_offset_range* (
303 *get_global_whitelist_ranges)(void);
304 int (*get_global_whitelist_ranges_count)(void);
305 const struct regop_offset_range* (
306 *get_context_whitelist_ranges)(void);
307 int (*get_context_whitelist_ranges_count)(void);
308 const u32* (*get_runcontrol_whitelist)(void);
309 int (*get_runcontrol_whitelist_count)(void);
310 const struct regop_offset_range* (
311 *get_runcontrol_whitelist_ranges)(void);
312 int (*get_runcontrol_whitelist_ranges_count)(void);
313 const u32* (*get_qctl_whitelist)(void);
314 int (*get_qctl_whitelist_count)(void);
315 const struct regop_offset_range* (
316 *get_qctl_whitelist_ranges)(void);
317 int (*get_qctl_whitelist_ranges_count)(void);
318 } regops;
301}; 319};
302 320
303struct gk20a { 321struct gk20a {
diff --git a/drivers/gpu/nvgpu/gk20a/gr_gk20a.c b/drivers/gpu/nvgpu/gk20a/gr_gk20a.c
index c1789427..cbad1292 100644
--- a/drivers/gpu/nvgpu/gk20a/gr_gk20a.c
+++ b/drivers/gpu/nvgpu/gk20a/gr_gk20a.c
@@ -5080,7 +5080,7 @@ static inline bool is_valid_cyclestats_bar0_offset_gk20a(struct gk20a *g,
5080 5080
5081 /* whitelist check */ 5081 /* whitelist check */
5082 valid = valid && 5082 valid = valid &&
5083 is_bar0_global_offset_whitelisted_gk20a(offset); 5083 is_bar0_global_offset_whitelisted_gk20a(g, offset);
5084 /* resource size check in case there was a problem 5084 /* resource size check in case there was a problem
5085 * with allocating the assumed size of bar0 */ 5085 * with allocating the assumed size of bar0 */
5086 valid = valid && 5086 valid = valid &&
diff --git a/drivers/gpu/nvgpu/gk20a/hal_gk20a.c b/drivers/gpu/nvgpu/gk20a/hal_gk20a.c
index 1b8157f1..218491ea 100644
--- a/drivers/gpu/nvgpu/gk20a/hal_gk20a.c
+++ b/drivers/gpu/nvgpu/gk20a/hal_gk20a.c
@@ -25,6 +25,7 @@
25#include "mm_gk20a.h" 25#include "mm_gk20a.h"
26#include "pmu_gk20a.h" 26#include "pmu_gk20a.h"
27#include "clk_gk20a.h" 27#include "clk_gk20a.h"
28#include "regops_gk20a.h"
28 29
29struct gpu_ops gk20a_ops = { 30struct gpu_ops gk20a_ops = {
30 .clock_gating = { 31 .clock_gating = {
@@ -53,6 +54,7 @@ int gk20a_init_hal(struct gpu_ops *gops)
53 gk20a_init_mm(gops); 54 gk20a_init_mm(gops);
54 gk20a_init_pmu_ops(gops); 55 gk20a_init_pmu_ops(gops);
55 gk20a_init_clk_ops(gops); 56 gk20a_init_clk_ops(gops);
57 gk20a_init_regops(gops);
56 gops->name = "gk20a"; 58 gops->name = "gk20a";
57 59
58 return 0; 60 return 0;
diff --git a/drivers/gpu/nvgpu/gk20a/regops_gk20a.c b/drivers/gpu/nvgpu/gk20a/regops_gk20a.c
index 4a115fb1..87a95afe 100644
--- a/drivers/gpu/nvgpu/gk20a/regops_gk20a.c
+++ b/drivers/gpu/nvgpu/gk20a/regops_gk20a.c
@@ -29,11 +29,6 @@
29 29
30 30
31 31
32struct regop_offset_range {
33 u32 base:24;
34 u32 count:8;
35};
36
37static int regop_bsearch_range_cmp(const void *pkey, const void *pelem) 32static int regop_bsearch_range_cmp(const void *pkey, const void *pelem)
38{ 33{
39 u32 key = *(u32 *)pkey; 34 u32 key = *(u32 *)pkey;
@@ -551,31 +546,32 @@ static int validate_reg_op_info(struct dbg_session_gk20a *dbg_s,
551static bool check_whitelists(struct dbg_session_gk20a *dbg_s, 546static bool check_whitelists(struct dbg_session_gk20a *dbg_s,
552 struct nvhost_dbg_gpu_reg_op *op, u32 offset) 547 struct nvhost_dbg_gpu_reg_op *op, u32 offset)
553{ 548{
549 struct gk20a *g = dbg_s->g;
554 bool valid = false; 550 bool valid = false;
555 551
556 if (op->type == REGOP(TYPE_GLOBAL)) { 552 if (op->type == REGOP(TYPE_GLOBAL)) {
557 /* search global list */ 553 /* search global list */
558 valid = !!bsearch(&offset, 554 valid = !!bsearch(&offset,
559 gk20a_global_whitelist_ranges, 555 g->ops.regops.get_global_whitelist_ranges(),
560 gk20a_global_whitelist_ranges_count, 556 g->ops.regops.get_global_whitelist_ranges_count(),
561 sizeof(*gk20a_global_whitelist_ranges), 557 sizeof(*g->ops.regops.get_global_whitelist_ranges()),
562 regop_bsearch_range_cmp); 558 regop_bsearch_range_cmp);
563 559
564 /* if debug session and channel is bound search context list */ 560 /* if debug session and channel is bound search context list */
565 if ((!valid) && (!dbg_s->is_profiler && dbg_s->ch)) { 561 if ((!valid) && (!dbg_s->is_profiler && dbg_s->ch)) {
566 /* binary search context list */ 562 /* binary search context list */
567 valid = !!bsearch(&offset, 563 valid = !!bsearch(&offset,
568 gk20a_context_whitelist_ranges, 564 g->ops.regops.get_context_whitelist_ranges(),
569 gk20a_context_whitelist_ranges_count, 565 g->ops.regops.get_context_whitelist_ranges_count(),
570 sizeof(*gk20a_context_whitelist_ranges), 566 sizeof(*g->ops.regops.get_context_whitelist_ranges()),
571 regop_bsearch_range_cmp); 567 regop_bsearch_range_cmp);
572 } 568 }
573 569
574 /* if debug session and channel is bound search runcontrol list */ 570 /* if debug session and channel is bound search runcontrol list */
575 if ((!valid) && (!dbg_s->is_profiler && dbg_s->ch)) { 571 if ((!valid) && (!dbg_s->is_profiler && dbg_s->ch)) {
576 valid = linear_search(offset, 572 valid = linear_search(offset,
577 gk20a_runcontrol_whitelist, 573 g->ops.regops.get_runcontrol_whitelist(),
578 gk20a_runcontrol_whitelist_count); 574 g->ops.regops.get_runcontrol_whitelist_count());
579 } 575 }
580 } else if (op->type == REGOP(TYPE_GR_CTX)) { 576 } else if (op->type == REGOP(TYPE_GR_CTX)) {
581 /* it's a context-relative op */ 577 /* it's a context-relative op */
@@ -587,22 +583,22 @@ static bool check_whitelists(struct dbg_session_gk20a *dbg_s,
587 583
588 /* binary search context list */ 584 /* binary search context list */
589 valid = !!bsearch(&offset, 585 valid = !!bsearch(&offset,
590 gk20a_context_whitelist_ranges, 586 g->ops.regops.get_context_whitelist_ranges(),
591 gk20a_context_whitelist_ranges_count, 587 g->ops.regops.get_context_whitelist_ranges_count(),
592 sizeof(*gk20a_context_whitelist_ranges), 588 sizeof(*g->ops.regops.get_context_whitelist_ranges()),
593 regop_bsearch_range_cmp); 589 regop_bsearch_range_cmp);
594 590
595 /* if debug session and channel is bound search runcontrol list */ 591 /* if debug session and channel is bound search runcontrol list */
596 if ((!valid) && (!dbg_s->is_profiler && dbg_s->ch)) { 592 if ((!valid) && (!dbg_s->is_profiler && dbg_s->ch)) {
597 valid = linear_search(offset, 593 valid = linear_search(offset,
598 gk20a_runcontrol_whitelist, 594 g->ops.regops.get_runcontrol_whitelist(),
599 gk20a_runcontrol_whitelist_count); 595 g->ops.regops.get_runcontrol_whitelist_count());
600 } 596 }
601 597
602 } else if (op->type == REGOP(TYPE_GR_CTX_QUAD)) { 598 } else if (op->type == REGOP(TYPE_GR_CTX_QUAD)) {
603 valid = linear_search(offset, 599 valid = linear_search(offset,
604 gk20a_qctl_whitelist, 600 g->ops.regops.get_qctl_whitelist(),
605 gk20a_qctl_whitelist_count); 601 g->ops.regops.get_qctl_whitelist_count());
606 } 602 }
607 603
608 return valid; 604 return valid;
@@ -692,13 +688,105 @@ static bool validate_reg_ops(struct dbg_session_gk20a *dbg_s,
692} 688}
693 689
694/* exported for tools like cyclestats, etc */ 690/* exported for tools like cyclestats, etc */
695bool is_bar0_global_offset_whitelisted_gk20a(u32 offset) 691bool is_bar0_global_offset_whitelisted_gk20a(struct gk20a *g, u32 offset)
696{ 692{
697
698 bool valid = !!bsearch(&offset, 693 bool valid = !!bsearch(&offset,
699 gk20a_global_whitelist_ranges, 694 g->ops.regops.get_global_whitelist_ranges(),
700 gk20a_global_whitelist_ranges_count, 695 g->ops.regops.get_global_whitelist_ranges_count(),
701 sizeof(*gk20a_global_whitelist_ranges), 696 sizeof(*g->ops.regops.get_global_whitelist_ranges()),
702 regop_bsearch_range_cmp); 697 regop_bsearch_range_cmp);
703 return valid; 698 return valid;
704} 699}
700
701const struct regop_offset_range *gk20a_get_global_whitelist_ranges(void)
702{
703 return gk20a_global_whitelist_ranges;
704}
705
706int gk20a_get_global_whitelist_ranges_count(void)
707{
708 return gk20a_global_whitelist_ranges_count;
709}
710
711const struct regop_offset_range *gk20a_get_context_whitelist_ranges(void)
712{
713 return gk20a_context_whitelist_ranges;
714}
715
716int gk20a_get_context_whitelist_ranges_count(void)
717{
718 return gk20a_context_whitelist_ranges_count;
719}
720
721const u32 *gk20a_get_runcontrol_whitelist(void)
722{
723 return gk20a_runcontrol_whitelist;
724}
725
726int gk20a_get_runcontrol_whitelist_count(void)
727{
728 return gk20a_runcontrol_whitelist_count;
729}
730
731const struct regop_offset_range *gk20a_get_runcontrol_whitelist_ranges(void)
732{
733 return gk20a_runcontrol_whitelist_ranges;
734}
735
736int gk20a_get_runcontrol_whitelist_ranges_count(void)
737{
738 return gk20a_runcontrol_whitelist_ranges_count;
739}
740
741const u32 *gk20a_get_qctl_whitelist(void)
742{
743 return gk20a_qctl_whitelist;
744}
745
746int gk20a_get_qctl_whitelist_count(void)
747{
748 return gk20a_qctl_whitelist_count;
749}
750
751const struct regop_offset_range *gk20a_get_qctl_whitelist_ranges(void)
752{
753 return gk20a_qctl_whitelist_ranges;
754}
755
756int gk20a_get_qctl_whitelist_ranges_count(void)
757{
758 return gk20a_qctl_whitelist_ranges_count;
759}
760
761void gk20a_init_regops(struct gpu_ops *gops)
762{
763 gops->regops.get_global_whitelist_ranges =
764 gk20a_get_global_whitelist_ranges;
765 gops->regops.get_global_whitelist_ranges_count =
766 gk20a_get_global_whitelist_ranges_count;
767
768 gops->regops.get_context_whitelist_ranges =
769 gk20a_get_context_whitelist_ranges;
770 gops->regops.get_context_whitelist_ranges_count =
771 gk20a_get_context_whitelist_ranges_count;
772
773 gops->regops.get_runcontrol_whitelist =
774 gk20a_get_runcontrol_whitelist;
775 gops->regops.get_runcontrol_whitelist_count =
776 gk20a_get_runcontrol_whitelist_count;
777
778 gops->regops.get_runcontrol_whitelist_ranges =
779 gk20a_get_runcontrol_whitelist_ranges;
780 gops->regops.get_runcontrol_whitelist_ranges_count =
781 gk20a_get_runcontrol_whitelist_ranges_count;
782
783 gops->regops.get_qctl_whitelist =
784 gk20a_get_qctl_whitelist;
785 gops->regops.get_qctl_whitelist_count =
786 gk20a_get_qctl_whitelist_count;
787
788 gops->regops.get_qctl_whitelist_ranges =
789 gk20a_get_qctl_whitelist_ranges;
790 gops->regops.get_qctl_whitelist_ranges_count =
791 gk20a_get_qctl_whitelist_ranges_count;
792}
diff --git a/drivers/gpu/nvgpu/gk20a/regops_gk20a.h b/drivers/gpu/nvgpu/gk20a/regops_gk20a.h
index 23b4865b..808e8bbe 100644
--- a/drivers/gpu/nvgpu/gk20a/regops_gk20a.h
+++ b/drivers/gpu/nvgpu/gk20a/regops_gk20a.h
@@ -19,6 +19,13 @@
19#ifndef __REGOPS_GK20A_H_ 19#ifndef __REGOPS_GK20A_H_
20#define __REGOPS_GK20A_H_ 20#define __REGOPS_GK20A_H_
21 21
22#include <linux/nvhost_dbg_gpu_ioctl.h>
23
24struct regop_offset_range {
25 u32 base:24;
26 u32 count:8;
27};
28
22int exec_regops_gk20a(struct dbg_session_gk20a *dbg_s, 29int exec_regops_gk20a(struct dbg_session_gk20a *dbg_s,
23 struct nvhost_dbg_gpu_reg_op *ops, 30 struct nvhost_dbg_gpu_reg_op *ops,
24 u64 num_ops); 31 u64 num_ops);
@@ -26,7 +33,6 @@ int exec_regops_gk20a(struct dbg_session_gk20a *dbg_s,
26/* turn seriously unwieldy names -> something shorter */ 33/* turn seriously unwieldy names -> something shorter */
27#define REGOP(x) NVHOST_DBG_GPU_REG_OP_##x 34#define REGOP(x) NVHOST_DBG_GPU_REG_OP_##x
28 35
29
30static inline bool reg_op_is_gr_ctx(u8 type) 36static inline bool reg_op_is_gr_ctx(u8 type)
31{ 37{
32 return type == REGOP(TYPE_GR_CTX) || 38 return type == REGOP(TYPE_GR_CTX) ||
@@ -42,6 +48,7 @@ static inline bool reg_op_is_read(u8 op)
42 op == REGOP(READ_64) ; 48 op == REGOP(READ_64) ;
43} 49}
44 50
45bool is_bar0_global_offset_whitelisted_gk20a(u32 offset); 51bool is_bar0_global_offset_whitelisted_gk20a(struct gk20a *g, u32 offset);
46 52
53void gk20a_init_regops(struct gpu_ops *gops);
47#endif /* __REGOPS_GK20A_H_ */ 54#endif /* __REGOPS_GK20A_H_ */