Loading drivers/media/platform/msm/vidc/msm_v4l2_vidc.c +1 −0 Original line number Diff line number Diff line Loading @@ -335,6 +335,7 @@ static int msm_vidc_initialize_core(struct platform_device *pdev, init_completion(&core->completions[i]); } INIT_DELAYED_WORK(&core->fw_unload_work, msm_vidc_fw_unload_handler); return rc; } Loading drivers/media/platform/msm/vidc/msm_vidc_common.c +56 −25 Original line number Diff line number Diff line Loading @@ -15,7 +15,6 @@ #include <linux/sched.h> #include <linux/slab.h> #include <linux/kernel.h> #include <linux/workqueue.h> #include <soc/qcom/subsystem_restart.h> #include <asm/div64.h> #include "msm_vidc_common.h" Loading Loading @@ -2244,6 +2243,7 @@ static int msm_comm_init_core(struct msm_vidc_inst *inst) goto fail_load_fw; } core->state = VIDC_CORE_LOADED; dprintk(VIDC_DBG, "Firmware downloaded\n"); } mutex_unlock(&core->lock); Loading Loading @@ -2281,7 +2281,6 @@ fail_vote_bus: static int msm_vidc_deinit_core(struct msm_vidc_inst *inst) { int rc = 0; struct msm_vidc_core *core; struct hfi_device *hdev; Loading @@ -2305,35 +2304,22 @@ static int msm_vidc_deinit_core(struct msm_vidc_inst *inst) mutex_lock(&core->lock); if (list_empty(&core->instances)) { if (core->state > VIDC_CORE_INIT) { if (core->resources.ocmem_size) { if (inst->state != MSM_VIDC_CORE_INVALID) msm_comm_unset_ocmem(core); call_hfi_op(hdev, free_ocmem, hdev->hfi_device_data); } dprintk(VIDC_DBG, "Calling vidc_hal_core_release\n"); rc = call_hfi_op(hdev, core_release, hdev->hfi_device_data); if (rc) { dprintk(VIDC_ERR, "Failed to release core, id = %d\n", core->id); goto exit; } } cancel_delayed_work(&core->fw_unload_work); core->state = VIDC_CORE_UNINIT; call_hfi_op(hdev, unload_fw, hdev->hfi_device_data); msm_comm_unvote_buses(core); /* * Delay unloading of firmware for 10 sec. This is useful * in avoiding firmware download delays in cases where we * will have a burst of back to back video playback sessions * e.g. thumbnail generation. */ schedule_delayed_work(&core->fw_unload_work, msecs_to_jiffies(10000)); } core_already_uninited: change_inst_state(inst, MSM_VIDC_CORE_UNINIT); exit: mutex_unlock(&core->lock); return rc; return 0; } int msm_comm_force_cleanup(struct msm_vidc_inst *inst) Loading Loading @@ -4541,3 +4527,48 @@ int msm_comm_smem_get_domain_partition(struct msm_vidc_inst *inst, return msm_smem_get_domain_partition(inst->mem_client, flags, buffer_type, domain_num, partition_num); } void msm_vidc_fw_unload_handler(struct work_struct *work) { struct msm_vidc_core *core = NULL; struct hfi_device *hdev = NULL; int rc = 0; core = container_of(work, struct msm_vidc_core, fw_unload_work.work); if (!core || !core->device) { dprintk(VIDC_ERR, "%s - invalid work or core handle\n", __func__); return; } hdev = core->device; mutex_lock(&core->lock); if (list_empty(&core->instances) && core->state != VIDC_CORE_UNINIT) { if (core->state > VIDC_CORE_INIT) { if (core->resources.ocmem_size) { if (core->state != VIDC_CORE_INVALID) msm_comm_unset_ocmem(core); call_hfi_op(hdev, free_ocmem, hdev->hfi_device_data); } dprintk(VIDC_DBG, "Calling vidc_hal_core_release\n"); rc = call_hfi_op(hdev, core_release, hdev->hfi_device_data); if (rc) { dprintk(VIDC_ERR, "Failed to release core, id = %d\n", core->id); return; } } core->state = VIDC_CORE_UNINIT; call_hfi_op(hdev, unload_fw, hdev->hfi_device_data); dprintk(VIDC_DBG, "Firmware unloaded\n"); msm_comm_unvote_buses(core); } mutex_unlock(&core->lock); } drivers/media/platform/msm/vidc/msm_vidc_internal.h +3 −0 Original line number Diff line number Diff line Loading @@ -20,6 +20,7 @@ #include <linux/types.h> #include <linux/completion.h> #include <linux/wait.h> #include <linux/workqueue.h> #include <linux/msm-bus.h> #include <linux/msm-bus-board.h> #include <soc/qcom/ocmem.h> Loading Loading @@ -275,6 +276,7 @@ struct msm_vidc_core { u32 enc_codec_supported; u32 dec_codec_supported; struct msm_vidc_idle_stats idle_stats; struct delayed_work fw_unload_work; }; struct msm_vidc_inst { Loading Loading @@ -391,4 +393,5 @@ struct msm_smem *msm_smem_user_to_kernel(void *clt, int fd, u32 offset, enum hal_buffer buffer_type); int msm_smem_get_domain_partition(void *clt, u32 flags, enum hal_buffer buffer_type, int *domain_num, int *partition_num); void msm_vidc_fw_unload_handler(struct work_struct *work); #endif Loading
drivers/media/platform/msm/vidc/msm_v4l2_vidc.c +1 −0 Original line number Diff line number Diff line Loading @@ -335,6 +335,7 @@ static int msm_vidc_initialize_core(struct platform_device *pdev, init_completion(&core->completions[i]); } INIT_DELAYED_WORK(&core->fw_unload_work, msm_vidc_fw_unload_handler); return rc; } Loading
drivers/media/platform/msm/vidc/msm_vidc_common.c +56 −25 Original line number Diff line number Diff line Loading @@ -15,7 +15,6 @@ #include <linux/sched.h> #include <linux/slab.h> #include <linux/kernel.h> #include <linux/workqueue.h> #include <soc/qcom/subsystem_restart.h> #include <asm/div64.h> #include "msm_vidc_common.h" Loading Loading @@ -2244,6 +2243,7 @@ static int msm_comm_init_core(struct msm_vidc_inst *inst) goto fail_load_fw; } core->state = VIDC_CORE_LOADED; dprintk(VIDC_DBG, "Firmware downloaded\n"); } mutex_unlock(&core->lock); Loading Loading @@ -2281,7 +2281,6 @@ fail_vote_bus: static int msm_vidc_deinit_core(struct msm_vidc_inst *inst) { int rc = 0; struct msm_vidc_core *core; struct hfi_device *hdev; Loading @@ -2305,35 +2304,22 @@ static int msm_vidc_deinit_core(struct msm_vidc_inst *inst) mutex_lock(&core->lock); if (list_empty(&core->instances)) { if (core->state > VIDC_CORE_INIT) { if (core->resources.ocmem_size) { if (inst->state != MSM_VIDC_CORE_INVALID) msm_comm_unset_ocmem(core); call_hfi_op(hdev, free_ocmem, hdev->hfi_device_data); } dprintk(VIDC_DBG, "Calling vidc_hal_core_release\n"); rc = call_hfi_op(hdev, core_release, hdev->hfi_device_data); if (rc) { dprintk(VIDC_ERR, "Failed to release core, id = %d\n", core->id); goto exit; } } cancel_delayed_work(&core->fw_unload_work); core->state = VIDC_CORE_UNINIT; call_hfi_op(hdev, unload_fw, hdev->hfi_device_data); msm_comm_unvote_buses(core); /* * Delay unloading of firmware for 10 sec. This is useful * in avoiding firmware download delays in cases where we * will have a burst of back to back video playback sessions * e.g. thumbnail generation. */ schedule_delayed_work(&core->fw_unload_work, msecs_to_jiffies(10000)); } core_already_uninited: change_inst_state(inst, MSM_VIDC_CORE_UNINIT); exit: mutex_unlock(&core->lock); return rc; return 0; } int msm_comm_force_cleanup(struct msm_vidc_inst *inst) Loading Loading @@ -4541,3 +4527,48 @@ int msm_comm_smem_get_domain_partition(struct msm_vidc_inst *inst, return msm_smem_get_domain_partition(inst->mem_client, flags, buffer_type, domain_num, partition_num); } void msm_vidc_fw_unload_handler(struct work_struct *work) { struct msm_vidc_core *core = NULL; struct hfi_device *hdev = NULL; int rc = 0; core = container_of(work, struct msm_vidc_core, fw_unload_work.work); if (!core || !core->device) { dprintk(VIDC_ERR, "%s - invalid work or core handle\n", __func__); return; } hdev = core->device; mutex_lock(&core->lock); if (list_empty(&core->instances) && core->state != VIDC_CORE_UNINIT) { if (core->state > VIDC_CORE_INIT) { if (core->resources.ocmem_size) { if (core->state != VIDC_CORE_INVALID) msm_comm_unset_ocmem(core); call_hfi_op(hdev, free_ocmem, hdev->hfi_device_data); } dprintk(VIDC_DBG, "Calling vidc_hal_core_release\n"); rc = call_hfi_op(hdev, core_release, hdev->hfi_device_data); if (rc) { dprintk(VIDC_ERR, "Failed to release core, id = %d\n", core->id); return; } } core->state = VIDC_CORE_UNINIT; call_hfi_op(hdev, unload_fw, hdev->hfi_device_data); dprintk(VIDC_DBG, "Firmware unloaded\n"); msm_comm_unvote_buses(core); } mutex_unlock(&core->lock); }
drivers/media/platform/msm/vidc/msm_vidc_internal.h +3 −0 Original line number Diff line number Diff line Loading @@ -20,6 +20,7 @@ #include <linux/types.h> #include <linux/completion.h> #include <linux/wait.h> #include <linux/workqueue.h> #include <linux/msm-bus.h> #include <linux/msm-bus-board.h> #include <soc/qcom/ocmem.h> Loading Loading @@ -275,6 +276,7 @@ struct msm_vidc_core { u32 enc_codec_supported; u32 dec_codec_supported; struct msm_vidc_idle_stats idle_stats; struct delayed_work fw_unload_work; }; struct msm_vidc_inst { Loading Loading @@ -391,4 +393,5 @@ struct msm_smem *msm_smem_user_to_kernel(void *clt, int fd, u32 offset, enum hal_buffer buffer_type); int msm_smem_get_domain_partition(void *clt, u32 flags, enum hal_buffer buffer_type, int *domain_num, int *partition_num); void msm_vidc_fw_unload_handler(struct work_struct *work); #endif