diff options
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/gpu/nvgpu/gk20a/ctrl_gk20a.c | 68 |
1 files changed, 68 insertions, 0 deletions
diff --git a/drivers/gpu/nvgpu/gk20a/ctrl_gk20a.c b/drivers/gpu/nvgpu/gk20a/ctrl_gk20a.c index 56b4d947..39581eb2 100644 --- a/drivers/gpu/nvgpu/gk20a/ctrl_gk20a.c +++ b/drivers/gpu/nvgpu/gk20a/ctrl_gk20a.c | |||
@@ -674,6 +674,69 @@ clean_up: | |||
674 | return err; | 674 | return err; |
675 | } | 675 | } |
676 | 676 | ||
677 | static int nvgpu_gpu_get_engine_info( | ||
678 | struct gk20a *g, | ||
679 | struct nvgpu_gpu_get_engine_info_args *args) | ||
680 | { | ||
681 | int err = 0; | ||
682 | u32 engine_enum = ENGINE_INVAL_GK20A; | ||
683 | u32 report_index = 0; | ||
684 | u32 engine_id_idx; | ||
685 | const u32 max_buffer_engines = args->engine_info_buf_size / | ||
686 | sizeof(struct nvgpu_gpu_get_engine_info_item); | ||
687 | struct nvgpu_gpu_get_engine_info_item __user *dst_item_list = | ||
688 | (void __user *)(uintptr_t)args->engine_info_buf_addr; | ||
689 | |||
690 | for (engine_id_idx = 0; engine_id_idx < g->fifo.num_engines; | ||
691 | ++engine_id_idx) { | ||
692 | u32 active_engine_id = g->fifo.active_engines_list[engine_id_idx]; | ||
693 | const struct fifo_engine_info_gk20a *src_info = | ||
694 | &g->fifo.engine_info[active_engine_id]; | ||
695 | struct nvgpu_gpu_get_engine_info_item dst_info; | ||
696 | |||
697 | memset(&dst_info, 0, sizeof(dst_info)); | ||
698 | |||
699 | engine_enum = src_info->engine_enum; | ||
700 | |||
701 | switch (engine_enum) { | ||
702 | case ENGINE_GR_GK20A: | ||
703 | dst_info.engine_id = NVGPU_GPU_ENGINE_ID_GR; | ||
704 | break; | ||
705 | |||
706 | case ENGINE_GRCE_GK20A: | ||
707 | dst_info.engine_id = NVGPU_GPU_ENGINE_ID_GR_COPY; | ||
708 | break; | ||
709 | |||
710 | case ENGINE_ASYNC_CE_GK20A: | ||
711 | dst_info.engine_id = NVGPU_GPU_ENGINE_ID_ASYNC_COPY; | ||
712 | break; | ||
713 | |||
714 | default: | ||
715 | gk20a_err(dev_from_gk20a(g), "Unmapped engine enum %u\n", | ||
716 | engine_enum); | ||
717 | continue; | ||
718 | } | ||
719 | |||
720 | dst_info.engine_instance = src_info->inst_id; | ||
721 | dst_info.runlist_id = src_info->runlist_id; | ||
722 | |||
723 | if (report_index < max_buffer_engines) { | ||
724 | err = copy_to_user(&dst_item_list[report_index], | ||
725 | &dst_info, sizeof(dst_info)); | ||
726 | if (err) | ||
727 | goto clean_up; | ||
728 | } | ||
729 | |||
730 | ++report_index; | ||
731 | } | ||
732 | |||
733 | args->engine_info_buf_size = | ||
734 | report_index * sizeof(struct nvgpu_gpu_get_engine_info_item); | ||
735 | |||
736 | clean_up: | ||
737 | return err; | ||
738 | } | ||
739 | |||
677 | long gk20a_ctrl_dev_ioctl(struct file *filp, unsigned int cmd, unsigned long arg) | 740 | long gk20a_ctrl_dev_ioctl(struct file *filp, unsigned int cmd, unsigned long arg) |
678 | { | 741 | { |
679 | struct device *dev = filp->private_data; | 742 | struct device *dev = filp->private_data; |
@@ -916,6 +979,11 @@ long gk20a_ctrl_dev_ioctl(struct file *filp, unsigned int cmd, unsigned long arg | |||
916 | (struct nvgpu_gpu_get_gpu_time_args *)buf); | 979 | (struct nvgpu_gpu_get_gpu_time_args *)buf); |
917 | break; | 980 | break; |
918 | 981 | ||
982 | case NVGPU_GPU_IOCTL_GET_ENGINE_INFO: | ||
983 | err = nvgpu_gpu_get_engine_info(g, | ||
984 | (struct nvgpu_gpu_get_engine_info_args *)buf); | ||
985 | break; | ||
986 | |||
919 | default: | 987 | default: |
920 | dev_dbg(dev_from_gk20a(g), "unrecognized gpu ioctl cmd: 0x%x", cmd); | 988 | dev_dbg(dev_from_gk20a(g), "unrecognized gpu ioctl cmd: 0x%x", cmd); |
921 | err = -ENOTTY; | 989 | err = -ENOTTY; |