Loading drivers/platform/msm/ipa/ipa_v2/ipa.c +41 −1 Original line number Original line Diff line number Diff line Loading @@ -2802,6 +2802,45 @@ void ipa_dec_client_disable_clks(void) ipa_active_clients_unlock(); ipa_active_clients_unlock(); } } /** * ipa_inc_acquire_wakelock() - Increase active clients counter, and * acquire wakelock if necessary * * Return codes: * None */ void ipa_inc_acquire_wakelock(void) { unsigned long flags; spin_lock_irqsave(&ipa_ctx->wakelock_ref_cnt.spinlock, flags); ipa_ctx->wakelock_ref_cnt.cnt++; if (ipa_ctx->wakelock_ref_cnt.cnt == 1) __pm_stay_awake(&ipa_ctx->w_lock); IPADBG("active wakelock ref cnt = %d\n", ipa_ctx->wakelock_ref_cnt.cnt); spin_unlock_irqrestore(&ipa_ctx->wakelock_ref_cnt.spinlock, flags); } /** * ipa_dec_release_wakelock() - Decrease active clients counter * * In case if the ref count is 0, release the wakelock. * * Return codes: * None */ void ipa_dec_release_wakelock(void) { unsigned long flags; spin_lock_irqsave(&ipa_ctx->wakelock_ref_cnt.spinlock, flags); ipa_ctx->wakelock_ref_cnt.cnt--; IPADBG("active wakelock ref cnt = %d\n", ipa_ctx->wakelock_ref_cnt.cnt); if (ipa_ctx->wakelock_ref_cnt.cnt == 0) __pm_relax(&ipa_ctx->w_lock); spin_unlock_irqrestore(&ipa_ctx->wakelock_ref_cnt.spinlock, flags); } static int ipa_setup_bam_cfg(const struct ipa_plat_drv_res *res) static int ipa_setup_bam_cfg(const struct ipa_plat_drv_res *res) { { void *ipa_bam_mmio; void *ipa_bam_mmio; Loading Loading @@ -3552,7 +3591,8 @@ static int ipa_init(const struct ipa_plat_drv_res *resource_p, /* Create a wakeup source. */ /* Create a wakeup source. */ ipa_ctx->pdev->power.wakeup = wakeup_source_register("IPA_WS"); wakeup_source_init(&ipa_ctx->w_lock, "IPA_WS"); spin_lock_init(&ipa_ctx->wakelock_ref_cnt.spinlock); /* Initialize IPA RM (resource manager) */ /* Initialize IPA RM (resource manager) */ result = ipa_rm_initialize(); result = ipa_rm_initialize(); Loading drivers/platform/msm/ipa/ipa_v2/ipa_dp.c +4 −4 Original line number Original line Diff line number Diff line Loading @@ -233,6 +233,7 @@ static void ipa_tx_switch_to_intr_mode(struct ipa_sys_context *sys) } } atomic_set(&sys->curr_polling_state, 0); atomic_set(&sys->curr_polling_state, 0); ipa_handle_tx_core(sys, true, false); ipa_handle_tx_core(sys, true, false); ipa_dec_release_wakelock(); return; return; fail: fail: Loading @@ -246,7 +247,6 @@ static void ipa_handle_tx(struct ipa_sys_context *sys) int cnt; int cnt; ipa_inc_client_enable_clks(); ipa_inc_client_enable_clks(); pm_stay_awake(ipa_ctx->pdev); do { do { cnt = ipa_handle_tx_core(sys, true, true); cnt = ipa_handle_tx_core(sys, true, true); if (cnt == 0) { if (cnt == 0) { Loading @@ -259,7 +259,6 @@ static void ipa_handle_tx(struct ipa_sys_context *sys) } while (inactive_cycles <= POLLING_INACTIVITY_TX); } while (inactive_cycles <= POLLING_INACTIVITY_TX); ipa_tx_switch_to_intr_mode(sys); ipa_tx_switch_to_intr_mode(sys); pm_relax(ipa_ctx->pdev); ipa_dec_client_disable_clks(); ipa_dec_client_disable_clks(); } } Loading Loading @@ -670,6 +669,7 @@ static void ipa_sps_irq_tx_notify(struct sps_event_notify *notify) IPAERR("sps_set_config() failed %d\n", ret); IPAERR("sps_set_config() failed %d\n", ret); break; break; } } ipa_inc_acquire_wakelock(); atomic_set(&sys->curr_polling_state, 1); atomic_set(&sys->curr_polling_state, 1); queue_work(sys->wq, &sys->work); queue_work(sys->wq, &sys->work); } } Loading Loading @@ -785,6 +785,7 @@ static void ipa_rx_switch_to_intr_mode(struct ipa_sys_context *sys) } } atomic_set(&sys->curr_polling_state, 0); atomic_set(&sys->curr_polling_state, 0); ipa_handle_rx_core(sys, true, false); ipa_handle_rx_core(sys, true, false); ipa_dec_release_wakelock(); return; return; fail: fail: Loading Loading @@ -902,6 +903,7 @@ static void ipa_sps_irq_rx_notify(struct sps_event_notify *notify) IPAERR("sps_set_config() failed %d\n", ret); IPAERR("sps_set_config() failed %d\n", ret); break; break; } } ipa_inc_acquire_wakelock(); atomic_set(&sys->curr_polling_state, 1); atomic_set(&sys->curr_polling_state, 1); queue_work(sys->wq, &sys->work); queue_work(sys->wq, &sys->work); } } Loading Loading @@ -935,7 +937,6 @@ static void ipa_handle_rx(struct ipa_sys_context *sys) int cnt; int cnt; ipa_inc_client_enable_clks(); ipa_inc_client_enable_clks(); pm_stay_awake(ipa_ctx->pdev); do { do { cnt = ipa_handle_rx_core(sys, true, true); cnt = ipa_handle_rx_core(sys, true, true); if (cnt == 0) { if (cnt == 0) { Loading @@ -956,7 +957,6 @@ static void ipa_handle_rx(struct ipa_sys_context *sys) } while (inactive_cycles <= POLLING_INACTIVITY_RX); } while (inactive_cycles <= POLLING_INACTIVITY_RX); ipa_rx_switch_to_intr_mode(sys); ipa_rx_switch_to_intr_mode(sys); pm_relax(ipa_ctx->pdev); ipa_dec_client_disable_clks(); ipa_dec_client_disable_clks(); } } Loading drivers/platform/msm/ipa/ipa_v2/ipa_i.h +12 −0 Original line number Original line Diff line number Diff line Loading @@ -788,6 +788,11 @@ struct ipa_active_clients { int cnt; int cnt; }; }; struct ipa_wakelock_ref_cnt { spinlock_t spinlock; int cnt; }; struct ipa_tag_completion { struct ipa_tag_completion { struct completion comp; struct completion comp; atomic_t cnt; atomic_t cnt; Loading Loading @@ -1160,6 +1165,8 @@ struct ipacm_client_info { * @ipa_num_pipes: The number of pipes used by IPA HW * @ipa_num_pipes: The number of pipes used by IPA HW * @skip_uc_pipe_reset: Indicates whether pipe reset via uC needs to be avoided * @skip_uc_pipe_reset: Indicates whether pipe reset via uC needs to be avoided * @ipa_client_apps_wan_cons_agg_gro: RMNET_IOCTL_INGRESS_FORMAT_AGG_DATA * @ipa_client_apps_wan_cons_agg_gro: RMNET_IOCTL_INGRESS_FORMAT_AGG_DATA * @w_lock: Indicates the wakeup source. * @wakelock_ref_cnt: Indicates the number of times wakelock is acquired * IPA context - holds all relevant info about IPA driver and its state * IPA context - holds all relevant info about IPA driver and its state */ */ Loading Loading @@ -1261,6 +1268,9 @@ struct ipa_context { u32 peer_bam_map_cnt; u32 peer_bam_map_cnt; u32 wdi_map_cnt; u32 wdi_map_cnt; bool use_dma_zone; bool use_dma_zone; struct wakeup_source w_lock; struct ipa_wakelock_ref_cnt wakelock_ref_cnt; /* RMNET_IOCTL_INGRESS_FORMAT_AGG_DATA */ /* RMNET_IOCTL_INGRESS_FORMAT_AGG_DATA */ bool ipa_client_apps_wan_cons_agg_gro; bool ipa_client_apps_wan_cons_agg_gro; /* M-release support to know client pipes */ /* M-release support to know client pipes */ Loading Loading @@ -1988,4 +1998,6 @@ void ipa_flow_control(enum ipa_client_type ipa_client, bool enable, uint32_t qmap_id); uint32_t qmap_id); int ipa2_restore_suspend_handler(void); int ipa2_restore_suspend_handler(void); void ipa_sps_irq_control_all(bool enable); void ipa_sps_irq_control_all(bool enable); void ipa_inc_acquire_wakelock(void); void ipa_dec_release_wakelock(void); #endif /* _IPA_I_H_ */ #endif /* _IPA_I_H_ */ drivers/platform/msm/ipa/ipa_v3/ipa.c +45 −0 Original line number Original line Diff line number Diff line Loading @@ -2881,6 +2881,47 @@ void ipa3_dec_client_disable_clks(void) ipa3_active_clients_unlock(); ipa3_active_clients_unlock(); } } /** * ipa3_inc_acquire_wakelock() - Increase active clients counter, and * acquire wakelock if necessary * * Return codes: * None */ void ipa3_inc_acquire_wakelock(void) { unsigned long flags; spin_lock_irqsave(&ipa3_ctx->wakelock_ref_cnt.spinlock, flags); ipa3_ctx->wakelock_ref_cnt.cnt++; if (ipa3_ctx->wakelock_ref_cnt.cnt == 1) __pm_stay_awake(&ipa3_ctx->w_lock); IPADBG("active wakelock ref cnt = %d\n", ipa3_ctx->wakelock_ref_cnt.cnt); spin_unlock_irqrestore(&ipa3_ctx->wakelock_ref_cnt.spinlock, flags); } /** * ipa3_dec_release_wakelock() - Decrease active clients counter * * In case if the ref count is 0, release the wakelock. * * Return codes: * None */ void ipa3_dec_release_wakelock(void) { unsigned long flags; spin_lock_irqsave(&ipa3_ctx->wakelock_ref_cnt.spinlock, flags); ipa3_ctx->wakelock_ref_cnt.cnt--; IPADBG("active wakelock ref cnt = %d\n", ipa3_ctx->wakelock_ref_cnt.cnt); if (ipa3_ctx->wakelock_ref_cnt.cnt == 0) __pm_relax(&ipa3_ctx->w_lock); spin_unlock_irqrestore(&ipa3_ctx->wakelock_ref_cnt.spinlock, flags); } int ipa3_set_required_perf_profile(enum ipa_voltage_level floor_voltage, int ipa3_set_required_perf_profile(enum ipa_voltage_level floor_voltage, u32 bandwidth_mbps) u32 bandwidth_mbps) { { Loading Loading @@ -3625,6 +3666,10 @@ static int ipa3_init(const struct ipa3_plat_drv_res *resource_p, goto fail_nat_dev_add; goto fail_nat_dev_add; } } /* Create a wakeup source. */ wakeup_source_init(&ipa3_ctx->w_lock, "IPA_WS"); spin_lock_init(&ipa3_ctx->wakelock_ref_cnt.spinlock); /* Initialize IPA RM (resource manager) */ /* Initialize IPA RM (resource manager) */ result = ipa3_rm_initialize(); result = ipa3_rm_initialize(); if (result) { if (result) { Loading drivers/platform/msm/ipa/ipa_v3/ipa_dp.c +8 −2 Original line number Original line Diff line number Diff line Loading @@ -212,6 +212,7 @@ static void ipa3_tx_switch_to_intr_mode(struct ipa3_sys_context *sys) if (ipa3_ctx->transport_prototype == IPA_TRANSPORT_TYPE_GSI) { if (ipa3_ctx->transport_prototype == IPA_TRANSPORT_TYPE_GSI) { atomic_set(&sys->curr_polling_state, 0); atomic_set(&sys->curr_polling_state, 0); ipa3_dec_release_wakelock(); ret = gsi_config_channel_mode(sys->ep->gsi_chan_hdl, ret = gsi_config_channel_mode(sys->ep->gsi_chan_hdl, GSI_CHAN_MODE_CALLBACK); GSI_CHAN_MODE_CALLBACK); if (ret != GSI_STATUS_SUCCESS) { if (ret != GSI_STATUS_SUCCESS) { Loading Loading @@ -239,8 +240,8 @@ static void ipa3_tx_switch_to_intr_mode(struct ipa3_sys_context *sys) } } atomic_set(&sys->curr_polling_state, 0); atomic_set(&sys->curr_polling_state, 0); ipa3_handle_tx_core(sys, true, false); ipa3_handle_tx_core(sys, true, false); ipa3_dec_release_wakelock(); } } return; return; fail: fail: Loading Loading @@ -775,6 +776,7 @@ static void ipa3_sps_irq_tx_notify(struct sps_event_notify *notify) IPAERR("sps_set_config() failed %d\n", ret); IPAERR("sps_set_config() failed %d\n", ret); break; break; } } ipa3_inc_acquire_wakelock(); atomic_set(&sys->curr_polling_state, 1); atomic_set(&sys->curr_polling_state, 1); queue_work(sys->wq, &sys->work); queue_work(sys->wq, &sys->work); } } Loading Loading @@ -852,6 +854,7 @@ static void ipa3_rx_switch_to_intr_mode(struct ipa3_sys_context *sys) if (ipa3_ctx->transport_prototype == IPA_TRANSPORT_TYPE_GSI) { if (ipa3_ctx->transport_prototype == IPA_TRANSPORT_TYPE_GSI) { atomic_set(&sys->curr_polling_state, 0); atomic_set(&sys->curr_polling_state, 0); ipa3_dec_release_wakelock(); ret = gsi_config_channel_mode(sys->ep->gsi_chan_hdl, ret = gsi_config_channel_mode(sys->ep->gsi_chan_hdl, GSI_CHAN_MODE_CALLBACK); GSI_CHAN_MODE_CALLBACK); if (ret != GSI_STATUS_SUCCESS) { if (ret != GSI_STATUS_SUCCESS) { Loading Loading @@ -879,8 +882,8 @@ static void ipa3_rx_switch_to_intr_mode(struct ipa3_sys_context *sys) } } atomic_set(&sys->curr_polling_state, 0); atomic_set(&sys->curr_polling_state, 0); ipa3_handle_rx_core(sys, true, false); ipa3_handle_rx_core(sys, true, false); ipa3_dec_release_wakelock(); } } return; return; fail: fail: Loading Loading @@ -927,6 +930,7 @@ static void ipa3_sps_irq_rx_notify(struct sps_event_notify *notify) IPAERR("sps_set_config() failed %d\n", ret); IPAERR("sps_set_config() failed %d\n", ret); break; break; } } ipa3_inc_acquire_wakelock(); atomic_set(&sys->curr_polling_state, 1); atomic_set(&sys->curr_polling_state, 1); queue_work(sys->wq, &sys->work); queue_work(sys->wq, &sys->work); } } Loading Loading @@ -3296,6 +3300,7 @@ static void ipa_gsi_irq_rx_notify_cb(struct gsi_chan_xfer_notify *notify) /* put the gsi channel into polling mode */ /* put the gsi channel into polling mode */ gsi_config_channel_mode(sys->ep->gsi_chan_hdl, gsi_config_channel_mode(sys->ep->gsi_chan_hdl, GSI_CHAN_MODE_POLL); GSI_CHAN_MODE_POLL); ipa3_inc_acquire_wakelock(); atomic_set(&sys->curr_polling_state, 1); atomic_set(&sys->curr_polling_state, 1); queue_work(sys->wq, &sys->work); queue_work(sys->wq, &sys->work); } } Loading Loading @@ -3341,6 +3346,7 @@ static void ipa_dma_gsi_irq_rx_notify_cb(struct gsi_chan_xfer_notify *notify) /* put the gsi channel into polling mode */ /* put the gsi channel into polling mode */ gsi_config_channel_mode(sys->ep->gsi_chan_hdl, gsi_config_channel_mode(sys->ep->gsi_chan_hdl, GSI_CHAN_MODE_POLL); GSI_CHAN_MODE_POLL); ipa3_inc_acquire_wakelock(); atomic_set(&sys->curr_polling_state, 1); atomic_set(&sys->curr_polling_state, 1); queue_work(sys->wq, &sys->work); queue_work(sys->wq, &sys->work); } } Loading Loading
drivers/platform/msm/ipa/ipa_v2/ipa.c +41 −1 Original line number Original line Diff line number Diff line Loading @@ -2802,6 +2802,45 @@ void ipa_dec_client_disable_clks(void) ipa_active_clients_unlock(); ipa_active_clients_unlock(); } } /** * ipa_inc_acquire_wakelock() - Increase active clients counter, and * acquire wakelock if necessary * * Return codes: * None */ void ipa_inc_acquire_wakelock(void) { unsigned long flags; spin_lock_irqsave(&ipa_ctx->wakelock_ref_cnt.spinlock, flags); ipa_ctx->wakelock_ref_cnt.cnt++; if (ipa_ctx->wakelock_ref_cnt.cnt == 1) __pm_stay_awake(&ipa_ctx->w_lock); IPADBG("active wakelock ref cnt = %d\n", ipa_ctx->wakelock_ref_cnt.cnt); spin_unlock_irqrestore(&ipa_ctx->wakelock_ref_cnt.spinlock, flags); } /** * ipa_dec_release_wakelock() - Decrease active clients counter * * In case if the ref count is 0, release the wakelock. * * Return codes: * None */ void ipa_dec_release_wakelock(void) { unsigned long flags; spin_lock_irqsave(&ipa_ctx->wakelock_ref_cnt.spinlock, flags); ipa_ctx->wakelock_ref_cnt.cnt--; IPADBG("active wakelock ref cnt = %d\n", ipa_ctx->wakelock_ref_cnt.cnt); if (ipa_ctx->wakelock_ref_cnt.cnt == 0) __pm_relax(&ipa_ctx->w_lock); spin_unlock_irqrestore(&ipa_ctx->wakelock_ref_cnt.spinlock, flags); } static int ipa_setup_bam_cfg(const struct ipa_plat_drv_res *res) static int ipa_setup_bam_cfg(const struct ipa_plat_drv_res *res) { { void *ipa_bam_mmio; void *ipa_bam_mmio; Loading Loading @@ -3552,7 +3591,8 @@ static int ipa_init(const struct ipa_plat_drv_res *resource_p, /* Create a wakeup source. */ /* Create a wakeup source. */ ipa_ctx->pdev->power.wakeup = wakeup_source_register("IPA_WS"); wakeup_source_init(&ipa_ctx->w_lock, "IPA_WS"); spin_lock_init(&ipa_ctx->wakelock_ref_cnt.spinlock); /* Initialize IPA RM (resource manager) */ /* Initialize IPA RM (resource manager) */ result = ipa_rm_initialize(); result = ipa_rm_initialize(); Loading
drivers/platform/msm/ipa/ipa_v2/ipa_dp.c +4 −4 Original line number Original line Diff line number Diff line Loading @@ -233,6 +233,7 @@ static void ipa_tx_switch_to_intr_mode(struct ipa_sys_context *sys) } } atomic_set(&sys->curr_polling_state, 0); atomic_set(&sys->curr_polling_state, 0); ipa_handle_tx_core(sys, true, false); ipa_handle_tx_core(sys, true, false); ipa_dec_release_wakelock(); return; return; fail: fail: Loading @@ -246,7 +247,6 @@ static void ipa_handle_tx(struct ipa_sys_context *sys) int cnt; int cnt; ipa_inc_client_enable_clks(); ipa_inc_client_enable_clks(); pm_stay_awake(ipa_ctx->pdev); do { do { cnt = ipa_handle_tx_core(sys, true, true); cnt = ipa_handle_tx_core(sys, true, true); if (cnt == 0) { if (cnt == 0) { Loading @@ -259,7 +259,6 @@ static void ipa_handle_tx(struct ipa_sys_context *sys) } while (inactive_cycles <= POLLING_INACTIVITY_TX); } while (inactive_cycles <= POLLING_INACTIVITY_TX); ipa_tx_switch_to_intr_mode(sys); ipa_tx_switch_to_intr_mode(sys); pm_relax(ipa_ctx->pdev); ipa_dec_client_disable_clks(); ipa_dec_client_disable_clks(); } } Loading Loading @@ -670,6 +669,7 @@ static void ipa_sps_irq_tx_notify(struct sps_event_notify *notify) IPAERR("sps_set_config() failed %d\n", ret); IPAERR("sps_set_config() failed %d\n", ret); break; break; } } ipa_inc_acquire_wakelock(); atomic_set(&sys->curr_polling_state, 1); atomic_set(&sys->curr_polling_state, 1); queue_work(sys->wq, &sys->work); queue_work(sys->wq, &sys->work); } } Loading Loading @@ -785,6 +785,7 @@ static void ipa_rx_switch_to_intr_mode(struct ipa_sys_context *sys) } } atomic_set(&sys->curr_polling_state, 0); atomic_set(&sys->curr_polling_state, 0); ipa_handle_rx_core(sys, true, false); ipa_handle_rx_core(sys, true, false); ipa_dec_release_wakelock(); return; return; fail: fail: Loading Loading @@ -902,6 +903,7 @@ static void ipa_sps_irq_rx_notify(struct sps_event_notify *notify) IPAERR("sps_set_config() failed %d\n", ret); IPAERR("sps_set_config() failed %d\n", ret); break; break; } } ipa_inc_acquire_wakelock(); atomic_set(&sys->curr_polling_state, 1); atomic_set(&sys->curr_polling_state, 1); queue_work(sys->wq, &sys->work); queue_work(sys->wq, &sys->work); } } Loading Loading @@ -935,7 +937,6 @@ static void ipa_handle_rx(struct ipa_sys_context *sys) int cnt; int cnt; ipa_inc_client_enable_clks(); ipa_inc_client_enable_clks(); pm_stay_awake(ipa_ctx->pdev); do { do { cnt = ipa_handle_rx_core(sys, true, true); cnt = ipa_handle_rx_core(sys, true, true); if (cnt == 0) { if (cnt == 0) { Loading @@ -956,7 +957,6 @@ static void ipa_handle_rx(struct ipa_sys_context *sys) } while (inactive_cycles <= POLLING_INACTIVITY_RX); } while (inactive_cycles <= POLLING_INACTIVITY_RX); ipa_rx_switch_to_intr_mode(sys); ipa_rx_switch_to_intr_mode(sys); pm_relax(ipa_ctx->pdev); ipa_dec_client_disable_clks(); ipa_dec_client_disable_clks(); } } Loading
drivers/platform/msm/ipa/ipa_v2/ipa_i.h +12 −0 Original line number Original line Diff line number Diff line Loading @@ -788,6 +788,11 @@ struct ipa_active_clients { int cnt; int cnt; }; }; struct ipa_wakelock_ref_cnt { spinlock_t spinlock; int cnt; }; struct ipa_tag_completion { struct ipa_tag_completion { struct completion comp; struct completion comp; atomic_t cnt; atomic_t cnt; Loading Loading @@ -1160,6 +1165,8 @@ struct ipacm_client_info { * @ipa_num_pipes: The number of pipes used by IPA HW * @ipa_num_pipes: The number of pipes used by IPA HW * @skip_uc_pipe_reset: Indicates whether pipe reset via uC needs to be avoided * @skip_uc_pipe_reset: Indicates whether pipe reset via uC needs to be avoided * @ipa_client_apps_wan_cons_agg_gro: RMNET_IOCTL_INGRESS_FORMAT_AGG_DATA * @ipa_client_apps_wan_cons_agg_gro: RMNET_IOCTL_INGRESS_FORMAT_AGG_DATA * @w_lock: Indicates the wakeup source. * @wakelock_ref_cnt: Indicates the number of times wakelock is acquired * IPA context - holds all relevant info about IPA driver and its state * IPA context - holds all relevant info about IPA driver and its state */ */ Loading Loading @@ -1261,6 +1268,9 @@ struct ipa_context { u32 peer_bam_map_cnt; u32 peer_bam_map_cnt; u32 wdi_map_cnt; u32 wdi_map_cnt; bool use_dma_zone; bool use_dma_zone; struct wakeup_source w_lock; struct ipa_wakelock_ref_cnt wakelock_ref_cnt; /* RMNET_IOCTL_INGRESS_FORMAT_AGG_DATA */ /* RMNET_IOCTL_INGRESS_FORMAT_AGG_DATA */ bool ipa_client_apps_wan_cons_agg_gro; bool ipa_client_apps_wan_cons_agg_gro; /* M-release support to know client pipes */ /* M-release support to know client pipes */ Loading Loading @@ -1988,4 +1998,6 @@ void ipa_flow_control(enum ipa_client_type ipa_client, bool enable, uint32_t qmap_id); uint32_t qmap_id); int ipa2_restore_suspend_handler(void); int ipa2_restore_suspend_handler(void); void ipa_sps_irq_control_all(bool enable); void ipa_sps_irq_control_all(bool enable); void ipa_inc_acquire_wakelock(void); void ipa_dec_release_wakelock(void); #endif /* _IPA_I_H_ */ #endif /* _IPA_I_H_ */
drivers/platform/msm/ipa/ipa_v3/ipa.c +45 −0 Original line number Original line Diff line number Diff line Loading @@ -2881,6 +2881,47 @@ void ipa3_dec_client_disable_clks(void) ipa3_active_clients_unlock(); ipa3_active_clients_unlock(); } } /** * ipa3_inc_acquire_wakelock() - Increase active clients counter, and * acquire wakelock if necessary * * Return codes: * None */ void ipa3_inc_acquire_wakelock(void) { unsigned long flags; spin_lock_irqsave(&ipa3_ctx->wakelock_ref_cnt.spinlock, flags); ipa3_ctx->wakelock_ref_cnt.cnt++; if (ipa3_ctx->wakelock_ref_cnt.cnt == 1) __pm_stay_awake(&ipa3_ctx->w_lock); IPADBG("active wakelock ref cnt = %d\n", ipa3_ctx->wakelock_ref_cnt.cnt); spin_unlock_irqrestore(&ipa3_ctx->wakelock_ref_cnt.spinlock, flags); } /** * ipa3_dec_release_wakelock() - Decrease active clients counter * * In case if the ref count is 0, release the wakelock. * * Return codes: * None */ void ipa3_dec_release_wakelock(void) { unsigned long flags; spin_lock_irqsave(&ipa3_ctx->wakelock_ref_cnt.spinlock, flags); ipa3_ctx->wakelock_ref_cnt.cnt--; IPADBG("active wakelock ref cnt = %d\n", ipa3_ctx->wakelock_ref_cnt.cnt); if (ipa3_ctx->wakelock_ref_cnt.cnt == 0) __pm_relax(&ipa3_ctx->w_lock); spin_unlock_irqrestore(&ipa3_ctx->wakelock_ref_cnt.spinlock, flags); } int ipa3_set_required_perf_profile(enum ipa_voltage_level floor_voltage, int ipa3_set_required_perf_profile(enum ipa_voltage_level floor_voltage, u32 bandwidth_mbps) u32 bandwidth_mbps) { { Loading Loading @@ -3625,6 +3666,10 @@ static int ipa3_init(const struct ipa3_plat_drv_res *resource_p, goto fail_nat_dev_add; goto fail_nat_dev_add; } } /* Create a wakeup source. */ wakeup_source_init(&ipa3_ctx->w_lock, "IPA_WS"); spin_lock_init(&ipa3_ctx->wakelock_ref_cnt.spinlock); /* Initialize IPA RM (resource manager) */ /* Initialize IPA RM (resource manager) */ result = ipa3_rm_initialize(); result = ipa3_rm_initialize(); if (result) { if (result) { Loading
drivers/platform/msm/ipa/ipa_v3/ipa_dp.c +8 −2 Original line number Original line Diff line number Diff line Loading @@ -212,6 +212,7 @@ static void ipa3_tx_switch_to_intr_mode(struct ipa3_sys_context *sys) if (ipa3_ctx->transport_prototype == IPA_TRANSPORT_TYPE_GSI) { if (ipa3_ctx->transport_prototype == IPA_TRANSPORT_TYPE_GSI) { atomic_set(&sys->curr_polling_state, 0); atomic_set(&sys->curr_polling_state, 0); ipa3_dec_release_wakelock(); ret = gsi_config_channel_mode(sys->ep->gsi_chan_hdl, ret = gsi_config_channel_mode(sys->ep->gsi_chan_hdl, GSI_CHAN_MODE_CALLBACK); GSI_CHAN_MODE_CALLBACK); if (ret != GSI_STATUS_SUCCESS) { if (ret != GSI_STATUS_SUCCESS) { Loading Loading @@ -239,8 +240,8 @@ static void ipa3_tx_switch_to_intr_mode(struct ipa3_sys_context *sys) } } atomic_set(&sys->curr_polling_state, 0); atomic_set(&sys->curr_polling_state, 0); ipa3_handle_tx_core(sys, true, false); ipa3_handle_tx_core(sys, true, false); ipa3_dec_release_wakelock(); } } return; return; fail: fail: Loading Loading @@ -775,6 +776,7 @@ static void ipa3_sps_irq_tx_notify(struct sps_event_notify *notify) IPAERR("sps_set_config() failed %d\n", ret); IPAERR("sps_set_config() failed %d\n", ret); break; break; } } ipa3_inc_acquire_wakelock(); atomic_set(&sys->curr_polling_state, 1); atomic_set(&sys->curr_polling_state, 1); queue_work(sys->wq, &sys->work); queue_work(sys->wq, &sys->work); } } Loading Loading @@ -852,6 +854,7 @@ static void ipa3_rx_switch_to_intr_mode(struct ipa3_sys_context *sys) if (ipa3_ctx->transport_prototype == IPA_TRANSPORT_TYPE_GSI) { if (ipa3_ctx->transport_prototype == IPA_TRANSPORT_TYPE_GSI) { atomic_set(&sys->curr_polling_state, 0); atomic_set(&sys->curr_polling_state, 0); ipa3_dec_release_wakelock(); ret = gsi_config_channel_mode(sys->ep->gsi_chan_hdl, ret = gsi_config_channel_mode(sys->ep->gsi_chan_hdl, GSI_CHAN_MODE_CALLBACK); GSI_CHAN_MODE_CALLBACK); if (ret != GSI_STATUS_SUCCESS) { if (ret != GSI_STATUS_SUCCESS) { Loading Loading @@ -879,8 +882,8 @@ static void ipa3_rx_switch_to_intr_mode(struct ipa3_sys_context *sys) } } atomic_set(&sys->curr_polling_state, 0); atomic_set(&sys->curr_polling_state, 0); ipa3_handle_rx_core(sys, true, false); ipa3_handle_rx_core(sys, true, false); ipa3_dec_release_wakelock(); } } return; return; fail: fail: Loading Loading @@ -927,6 +930,7 @@ static void ipa3_sps_irq_rx_notify(struct sps_event_notify *notify) IPAERR("sps_set_config() failed %d\n", ret); IPAERR("sps_set_config() failed %d\n", ret); break; break; } } ipa3_inc_acquire_wakelock(); atomic_set(&sys->curr_polling_state, 1); atomic_set(&sys->curr_polling_state, 1); queue_work(sys->wq, &sys->work); queue_work(sys->wq, &sys->work); } } Loading Loading @@ -3296,6 +3300,7 @@ static void ipa_gsi_irq_rx_notify_cb(struct gsi_chan_xfer_notify *notify) /* put the gsi channel into polling mode */ /* put the gsi channel into polling mode */ gsi_config_channel_mode(sys->ep->gsi_chan_hdl, gsi_config_channel_mode(sys->ep->gsi_chan_hdl, GSI_CHAN_MODE_POLL); GSI_CHAN_MODE_POLL); ipa3_inc_acquire_wakelock(); atomic_set(&sys->curr_polling_state, 1); atomic_set(&sys->curr_polling_state, 1); queue_work(sys->wq, &sys->work); queue_work(sys->wq, &sys->work); } } Loading Loading @@ -3341,6 +3346,7 @@ static void ipa_dma_gsi_irq_rx_notify_cb(struct gsi_chan_xfer_notify *notify) /* put the gsi channel into polling mode */ /* put the gsi channel into polling mode */ gsi_config_channel_mode(sys->ep->gsi_chan_hdl, gsi_config_channel_mode(sys->ep->gsi_chan_hdl, GSI_CHAN_MODE_POLL); GSI_CHAN_MODE_POLL); ipa3_inc_acquire_wakelock(); atomic_set(&sys->curr_polling_state, 1); atomic_set(&sys->curr_polling_state, 1); queue_work(sys->wq, &sys->work); queue_work(sys->wq, &sys->work); } } Loading