static u32 res_trk_sel_clk_rate(unsigned long hclk_rate) { mutex_lock(&resource_context.lock); if (clk_set_rate(resource_context.hclk, hclk_rate)) { VCDRES_MSG_ERROR("vidc hclk set rate failed\n"); mutex_unlock(&resource_context.lock); return false; } resource_context.hclk_rate = hclk_rate; mutex_unlock(&resource_context.lock); return true; }
static u32 res_trk_sel_clk_rate(unsigned long hclk_rate) { u32 status = true; mutex_lock(&resource_context.lock); if (clk_set_rate(resource_context.vcodec_clk, hclk_rate)) { VCDRES_MSG_ERROR("vidc hclk set rate failed\n"); status = false; } else resource_context.vcodec_clk_rate = hclk_rate; mutex_unlock(&resource_context.lock); return status; }
u32 res_trk_get_curr_perf_level(u32 *pn_perf_lvl) { unsigned long freq; if (!pn_perf_lvl) { VCDRES_MSG_ERROR("%s(): pn_perf_lvl is NULL\n", __func__); return false; } VCDRES_MSG_LOW("clk_regime_msm_get_clk_freq_hz"); if (!res_trk_get_clk_rate(&freq)) { VCDRES_MSG_ERROR("%s(): res_trk_get_clk_rate FAILED\n", __func__); *pn_perf_lvl = 0; return false; } *pn_perf_lvl = res_trk_convert_freq_to_perf_lvl((u64) freq); VCDRES_MSG_MED("%s(): freq = %lu, *pn_perf_lvl = %u", __func__, freq, *pn_perf_lvl); return true; }
static u32 res_trk_get_clk() { if (resource_context.vcodec_clk || resource_context.vcodec_pclk) { VCDRES_MSG_ERROR("%s() Clock reference exists\n", __func__); goto bail_out; } resource_context.vcodec_clk = clk_get(resource_context.device, "core_clk"); if (IS_ERR(resource_context.vcodec_clk)) { VCDRES_MSG_ERROR("%s(): core_clk get failed\n", __func__); goto bail_out; } resource_context.vcodec_pclk = clk_get(resource_context.device, "iface_clk"); if (IS_ERR(resource_context.vcodec_pclk)) { VCDRES_MSG_ERROR("%s(): iface_clk get failed\n", __func__); goto release_vcodec_clk; } if (clk_set_rate(resource_context.vcodec_clk, vidc_clk_table[0])) { VCDRES_MSG_ERROR("%s(): set rate failed in power up\n", __func__); goto release_vcodec_pclk; } return true; release_vcodec_pclk: clk_put(resource_context.vcodec_pclk); resource_context.vcodec_pclk = NULL; release_vcodec_clk: clk_put(resource_context.vcodec_clk); resource_context.vcodec_clk = NULL; bail_out: return false; }
void res_trk_init(struct device *device, u32 irq) { if (resource_context.device || resource_context.irq_num || !device) { VCDRES_MSG_ERROR("%s() Resource Tracker Init error\n", __func__); } else { memset(&resource_context, 0, sizeof(resource_context)); mutex_init(&resource_context.lock); resource_context.device = device; resource_context.irq_num = irq; resource_context.core_type = VCD_CORE_1080P; } }
int res_trk_update_bus_perf_level(struct vcd_dev_ctxt *dev_ctxt, u32 perf_level) { struct vcd_clnt_ctxt *cctxt_itr = NULL; u32 enc_perf_level = 0, dec_perf_level = 0; u32 bus_clk_index, client_type = 0; int rc = 0; if (dev_ctxt->turbo_mode_set) return rc; cctxt_itr = dev_ctxt->cctxt_list_head; while (cctxt_itr) { if (cctxt_itr->decoding) dec_perf_level += cctxt_itr->reqd_perf_lvl; else enc_perf_level += cctxt_itr->reqd_perf_lvl; cctxt_itr = cctxt_itr->next; } if (!enc_perf_level) client_type = 1; if (perf_level <= RESTRK_1080P_VGA_PERF_LEVEL) bus_clk_index = 0; else if (perf_level <= RESTRK_1080P_720P_PERF_LEVEL) bus_clk_index = 1; else if (perf_level <= RESTRK_1080P_MAX_PERF_LEVEL) bus_clk_index = 2; else bus_clk_index = 3; if (dev_ctxt->reqd_perf_lvl + dev_ctxt->curr_perf_lvl == 0) bus_clk_index = 2; else if (resource_context.vidc_platform_data->disable_turbo && bus_clk_index == 3) { VCDRES_MSG_ERROR("Warning: Turbo mode not supported " " falling back to 1080p bus\n"); bus_clk_index = 2; } if (bus_clk_index == 3) dev_ctxt->turbo_mode_set = 1; bus_clk_index = (bus_clk_index << 1) + (client_type + 1); VCDRES_MSG_LOW("%s(), bus_clk_index = %d", __func__, bus_clk_index); VCDRES_MSG_LOW("%s(),context.pcl = %x", __func__, resource_context.pcl); VCDRES_MSG_LOW("%s(), bus_perf_level = %x", __func__, perf_level); rc = msm_bus_scale_client_update_request(resource_context.pcl, bus_clk_index); return rc; }
int res_trk_enable_footswitch(void) { int rc = 0; mutex_lock(&resource_context.lock); resource_context.footswitch = regulator_get(NULL, "fs_ved"); if (IS_ERR(resource_context.footswitch)) { VCDRES_MSG_ERROR("foot switch get failed\n"); resource_context.footswitch = NULL; rc = -EINVAL; } else rc = regulator_enable(resource_context.footswitch); mutex_unlock(&resource_context.lock); return rc; }
u32 res_trk_get_clk_rate(unsigned long *phclk_rate) { u32 status = true; mutex_lock(&resource_context.lock); if (phclk_rate) { *phclk_rate = clk_get_rate(resource_context.vcodec_clk); if (!(*phclk_rate)) { VCDRES_MSG_ERROR("vidc hclk get rate failed\n"); status = false; } } else status = false; mutex_unlock(&resource_context.lock); return status; }
u32 res_trk_get_max_perf_level(u32 *pn_max_perf_lvl) { bool turbo_supported = !resource_context.vidc_platform_data->disable_turbo; if (!pn_max_perf_lvl) { VCDRES_MSG_ERROR("%s(): pn_max_perf_lvl is NULL\n", __func__); return false; } if (turbo_supported) *pn_max_perf_lvl = RESTRK_1080P_TURBO_PERF_LEVEL; else *pn_max_perf_lvl = RESTRK_1080P_MAX_PERF_LEVEL; VCDRES_MSG_MED("%s: %u", __func__, (u32)*pn_max_perf_lvl); return true; }
u32 res_trk_download_firmware(void) { const struct firmware *fw_video = NULL; int rc = 0; VCDRES_MSG_HIGH("%s(): Request firmware download\n", __func__); mutex_lock(&resource_context.lock); rc = request_firmware(&fw_video, VIDC_FW, resource_context.device); if (rc) { VCDRES_MSG_ERROR("request_firmware for %s error %d\n", VIDC_FW, rc); mutex_unlock(&resource_context.lock); return false; } vidc_video_codec_fw = (unsigned char *)fw_video->data; vidc_video_codec_fw_size = (u32) fw_video->size; mutex_unlock(&resource_context.lock); return true; }
u32 res_trk_power_up(void) { VCDRES_MSG_LOW("clk_regime_rail_enable"); VCDRES_MSG_LOW("clk_regime_sel_rail_control"); #ifdef AXI_CLK_SCALING { VCDRES_MSG_MED("\n res_trk_power_up():: " "Calling AXI add requirement\n"); ebi1_clk = clk_get(resource_context.device, "mem_clk"); if (IS_ERR(ebi1_clk)) { VCDRES_MSG_ERROR("Request AXI bus QOS fails."); return false; } clk_prepare_enable(ebi1_clk); } #endif VCDRES_MSG_MED("\n res_trk_power_up():: Calling " "vidc_enable_pwr_rail()\n"); return res_trk_enable_videocore(); }
void res_trk_init(struct device *device, u32 irq) { if (resource_context.device || resource_context.irq_num || !device) { VCDRES_MSG_ERROR("%s() Resource Tracker Init error\n", __func__); return; } memset(&resource_context, 0, sizeof(resource_context)); mutex_init(&resource_context.lock); resource_context.device = device; resource_context.irq_num = irq; resource_context.core_type = VCD_CORE_720P; resource_context.regulator = regulator_get(NULL, "fs_mfc"); resource_context.vidc_platform_data = (struct msm_vidc_platform_data *) device->platform_data; if (resource_context.vidc_platform_data) { resource_context.memtype = resource_context.vidc_platform_data->memtype; } else { resource_context.memtype = -1; } }
void res_trk_init(struct device *device, u32 irq) { u32 memorytype = PMEM_MEMTYPE; if (resource_context.device || resource_context.irq_num || !device) { VCDRES_MSG_ERROR("%s() Resource Tracker Init error\n", __func__); } else { memset(&resource_context, 0, sizeof(resource_context)); mutex_init(&resource_context.lock); resource_context.device = device; resource_context.irq_num = irq; #ifdef CONFIG_MSM_BUS_SCALING resource_context.vidc_bus_client_pdata = (struct msm_bus_scale_pdata *)device->platform_data; #endif resource_context.core_type = VCD_CORE_1080P; if (memorytype == PMEM_MEMTYPE_EBI1) { resource_context.device_addr = (phys_addr_t) allocate_contiguous_memory_nomap(VIDC_FW_SIZE, resource_context.memtype, SZ_4K); if (resource_context.device_addr) { resource_context.base_addr = (u8 *) ioremap((unsigned long) resource_context.device_addr, VIDC_FW_SIZE); if (!resource_context.base_addr) { free_contiguous_memory_by_paddr( (unsigned long) resource_context.device_addr); resource_context.device_addr = (phys_addr_t)NULL; } } } } }
static u32 res_trk_enable_videocore(void) { mutex_lock(&resource_context.lock); if (!resource_context.rail_enabled) { int rc = -1; rc = regulator_enable(resource_context.regulator); if (rc) { VCDRES_MSG_ERROR("%s(): regulator_enable failed %d\n", __func__, rc); goto bail_out; } VCDRES_MSG_LOW("%s(): regulator enable Success %d\n", __func__, rc); resource_context.pclk = clk_get(resource_context.device, "iface_clk"); if (IS_ERR(resource_context.pclk)) { VCDRES_MSG_ERROR("%s(): iface_clk get failed\n" , __func__); goto disable_regulator; } resource_context.hclk = clk_get(resource_context.device, "core_clk"); if (IS_ERR(resource_context.hclk)) { VCDRES_MSG_ERROR("%s(): core_clk get failed\n" , __func__); goto release_pclk; } resource_context.hclk_div2 = clk_get(resource_context.device, "core_div2_clk"); if (IS_ERR(resource_context.hclk_div2)) { VCDRES_MSG_ERROR("%s(): core_div2_clk get failed\n" , __func__); goto release_hclk_pclk; } if (clk_set_rate(resource_context.hclk, mfc_clk_freq_table[0])) { VCDRES_MSG_ERROR("\n pwr_rail_enable:" " set clk rate failed\n"); goto release_all_clks; } if (clk_prepare_enable(resource_context.pclk)) { VCDRES_MSG_ERROR("vidc pclk Enable failed\n"); goto release_all_clks; } if (clk_prepare_enable(resource_context.hclk)) { VCDRES_MSG_ERROR("vidc hclk Enable failed\n"); goto disable_pclk; } if (clk_prepare_enable(resource_context.hclk_div2)) { VCDRES_MSG_ERROR("vidc hclk_div2 Enable failed\n"); goto disable_hclk_pclk; } rc = clk_reset(resource_context.pclk, CLK_RESET_DEASSERT); if (rc) { VCDRES_MSG_ERROR("\n clk_reset failed %d\n", rc); goto disable_and_release_all_clks; } msleep(20); clk_disable_unprepare(resource_context.pclk); clk_disable_unprepare(resource_context.hclk); clk_disable_unprepare(resource_context.hclk_div2); } resource_context.rail_enabled = 1; mutex_unlock(&resource_context.lock); return true; disable_and_release_all_clks: clk_disable_unprepare(resource_context.hclk_div2); disable_hclk_pclk: clk_disable_unprepare(resource_context.hclk); disable_pclk: clk_disable_unprepare(resource_context.pclk); release_all_clks: clk_put(resource_context.hclk_div2); resource_context.hclk_div2 = NULL; release_hclk_pclk: clk_put(resource_context.hclk); resource_context.hclk = NULL; release_pclk: clk_put(resource_context.pclk); resource_context.pclk = NULL; disable_regulator: regulator_disable(resource_context.regulator); bail_out: mutex_unlock(&resource_context.lock); return false; }
u32 res_trk_set_perf_level(u32 req_perf_lvl, u32 *pn_set_perf_lvl, struct vcd_dev_ctxt *dev_ctxt) { u32 vidc_freq = 0; if (!pn_set_perf_lvl || !dev_ctxt) { VCDRES_MSG_ERROR("%s(): NULL pointer! dev_ctxt(%p)\n", __func__, dev_ctxt); return false; } if (dev_ctxt->turbo_mode_set && (req_perf_lvl < RESTRK_1080P_TURBO_PERF_LEVEL)) { VCDRES_MSG_MED("%s(): TURBO MODE!!\n", __func__); return true; } VCDRES_MSG_LOW("%s(), req_perf_lvl = %d", __func__, req_perf_lvl); if (resource_context.vidc_platform_data->disable_turbo && req_perf_lvl > RESTRK_1080P_MAX_PERF_LEVEL) { VCDRES_MSG_ERROR("%s(): Turbo not supported! dev_ctxt(%p)\n", __func__, dev_ctxt); } #ifdef CONFIG_MSM_BUS_SCALING if (!res_trk_update_bus_perf_level(dev_ctxt, req_perf_lvl) < 0) { VCDRES_MSG_ERROR("%s(): update buf perf level failed\n", __func__); return false; } #endif if (dev_ctxt->reqd_perf_lvl + dev_ctxt->curr_perf_lvl == 0) req_perf_lvl = RESTRK_1080P_MAX_PERF_LEVEL; if (req_perf_lvl <= RESTRK_1080P_VGA_PERF_LEVEL) { vidc_freq = vidc_clk_table[0]; *pn_set_perf_lvl = RESTRK_1080P_VGA_PERF_LEVEL; } else if (req_perf_lvl <= RESTRK_1080P_720P_PERF_LEVEL) { vidc_freq = vidc_clk_table[1]; *pn_set_perf_lvl = RESTRK_1080P_720P_PERF_LEVEL; } else if (req_perf_lvl <= RESTRK_1080P_MAX_PERF_LEVEL) { vidc_freq = vidc_clk_table[2]; *pn_set_perf_lvl = RESTRK_1080P_MAX_PERF_LEVEL; } else { vidc_freq = vidc_clk_table[4]; *pn_set_perf_lvl = RESTRK_1080P_TURBO_PERF_LEVEL; } if (resource_context.vidc_platform_data->disable_turbo && *pn_set_perf_lvl == RESTRK_1080P_TURBO_PERF_LEVEL) { VCDRES_MSG_ERROR("Warning: Turbo mode not supported " " falling back to 1080p clocks\n"); vidc_freq = vidc_clk_table[2]; *pn_set_perf_lvl = RESTRK_1080P_MAX_PERF_LEVEL; } resource_context.perf_level = *pn_set_perf_lvl; VCDRES_MSG_MED("VIDC: vidc_freq = %u, req_perf_lvl = %u\n", vidc_freq, req_perf_lvl); #ifdef USE_RES_TRACKER if (req_perf_lvl != RESTRK_1080P_MIN_PERF_LEVEL) { VCDRES_MSG_MED("%s(): Setting vidc freq to %u\n", __func__, vidc_freq); if (!res_trk_sel_clk_rate(vidc_freq)) { if (vidc_freq == vidc_clk_table[4]) { if (res_trk_sel_clk_rate(vidc_clk_table[3])) goto ret; } VCDRES_MSG_ERROR("%s(): res_trk_sel_clk_rate FAILED\n", __func__); *pn_set_perf_lvl = 0; return false; } } #endif ret: VCDRES_MSG_MED("%s() set perl level : %d", __func__, *pn_set_perf_lvl); return true; }
//static u32 res_trk_disable_pwr_rail(void) static u32 res_trk_disable_videocore(void) /* 20110511 Y.Yagami -S vidc: vdec: Generate output done in reconfig. */ { int rc = -1; mutex_lock(&resource_context.lock); #ifdef PATCH0330 #else if (resource_context.clock_enabled) { mutex_unlock(&resource_context.lock); VCDRES_MSG_LOW("\n Calling CLK disable in Power Down\n"); res_trk_disable_clocks(); mutex_lock(&resource_context.lock); } #endif /* PATCH0330 */ if (!resource_context.rail_enabled) { mutex_unlock(&resource_context.lock); return false; } #ifdef PATCH0330 if (!resource_context.clock_enabled && resource_context.pclk && resource_context.hclk && resource_context.hclk_div2) { VCDRES_MSG_LOW("\nEnabling clk before disabling pwr rail\n"); /* 20110511 Y.Yagami CHG-S msm: vidc: Fix video core clock power up/down sequence */ // clk_set_rate(resource_context.hclk, // mfc_clk_freq_table[0]); if (clk_set_rate(resource_context.hclk, mfc_clk_freq_table[0])) { VCDRES_MSG_ERROR("\n pwr_rail_disable:" " set clk rate failed\n"); goto bail_out; } /* 20110511 Y.Yagami CHG-E msm: vidc: Fix video core clock power up/down sequence */ if (clk_enable(resource_context.pclk)) { VCDRES_MSG_ERROR("vidc pclk Enable failed\n"); goto bail_out; } if (clk_enable(resource_context.hclk)) { VCDRES_MSG_ERROR("vidc hclk Enable failed\n"); goto disable_pclk; } if (clk_enable(resource_context.hclk_div2)) { VCDRES_MSG_ERROR("vidc hclk_div2 Enable failed\n"); goto disable_hclk; } } else { VCDRES_MSG_ERROR("\ndisabling pwr rail: Enabling clk failed\n"); goto bail_out; } #endif /* PATCH0330 */ resource_context.rail_enabled = 0; rc = clk_reset(resource_context.pclk, CLK_RESET_ASSERT); if (rc) { VCDRES_MSG_ERROR("\n clk_reset failed %d\n", rc); mutex_unlock(&resource_context.lock); return false; } msleep(20); rc = internal_pwr_rail_ctl(PWR_RAIL_MFC_CLK, 0); if (rc) { VCDRES_MSG_ERROR("\n clk_reset failed %d\n", rc); mutex_unlock(&resource_context.lock); return false; } #ifdef PATCH0330 clk_disable(resource_context.pclk); clk_disable(resource_context.hclk); clk_disable(resource_context.hclk_div2); #endif /* PATCH0330 */ clk_put(resource_context.hclk_div2); clk_put(resource_context.hclk); clk_put(resource_context.pclk); #ifdef PATCH0330 resource_context.hclk_div2 = NULL; resource_context.hclk = NULL; resource_context.pclk = NULL; #endif /* PATCH0330 */ mutex_unlock(&resource_context.lock); return true; #ifdef PATCH0330 disable_hclk: clk_disable(resource_context.hclk); disable_pclk: clk_disable(resource_context.pclk); bail_out: if (resource_context.pclk) { clk_put(resource_context.pclk); resource_context.pclk = NULL; } if (resource_context.hclk) { clk_put(resource_context.hclk); resource_context.hclk = NULL; } if (resource_context.hclk_div2) { clk_put(resource_context.hclk_div2); resource_context.hclk_div2 = NULL; } mutex_unlock(&resource_context.lock); return false; #endif /* PATCH0330 */ }
u32 res_trk_set_perf_level(u32 req_perf_lvl, u32 *pn_set_perf_lvl, struct vcd_dev_ctxt *dev_ctxt) { struct vcd_clnt_ctxt *cctxt_itr = NULL; u32 axi_freq = 0, mfc_freq = 0, calc_mfc_freq = 0; u8 enc_clnt_present = false; if (!pn_set_perf_lvl || !dev_ctxt) { VCDRES_MSG_ERROR("%s(): NULL pointer! dev_ctxt(%p)\n", __func__, dev_ctxt); return false; } VCDRES_MSG_LOW("%s(), req_perf_lvl = %d", __func__, req_perf_lvl); calc_mfc_freq = res_trk_convert_perf_lvl_to_freq( (u64)req_perf_lvl); if (calc_mfc_freq < VCD_RESTRK_MIN_FREQ_POINT) calc_mfc_freq = VCD_RESTRK_MIN_FREQ_POINT; else if (calc_mfc_freq > VCD_RESTRK_MAX_FREQ_POINT) calc_mfc_freq = VCD_RESTRK_MAX_FREQ_POINT; cctxt_itr = dev_ctxt->cctxt_list_head; while (cctxt_itr) { VCDRES_MSG_LOW("\n cctxt_itr = %p", cctxt_itr); if (!cctxt_itr->decoding) { VCDRES_MSG_LOW("\n Encoder client"); enc_clnt_present = true; break; } else { VCDRES_MSG_LOW("\n Decoder client"); } cctxt_itr = cctxt_itr->next; } if (enc_clnt_present) { if (req_perf_lvl >= VGA_PERF_LEVEL) { mfc_freq = mfc_clk_freq_table[2]; axi_freq = axi_clk_freq_table_enc[1]; } else { mfc_freq = mfc_clk_freq_table[0]; axi_freq = axi_clk_freq_table_enc[0]; } VCDRES_MSG_MED("\n ENCODER: axi_freq = %u" ", mfc_freq = %u, calc_mfc_freq = %u," " req_perf_lvl = %u", axi_freq, mfc_freq, calc_mfc_freq, req_perf_lvl); } else { if (req_perf_lvl <= QVGA_PERF_LEVEL) { mfc_freq = mfc_clk_freq_table[0]; axi_freq = axi_clk_freq_table_dec[0]; } else { axi_freq = axi_clk_freq_table_dec[0]; if (req_perf_lvl <= VGA_PERF_LEVEL) mfc_freq = mfc_clk_freq_table[0]; else if (req_perf_lvl <= WVGA_PERF_LEVEL) mfc_freq = mfc_clk_freq_table[1]; else { mfc_freq = mfc_clk_freq_table[2]; axi_freq = axi_clk_freq_table_dec[1]; } } VCDRES_MSG_MED("\n DECODER: axi_freq = %u" ", mfc_freq = %u, calc_mfc_freq = %u," " req_perf_lvl = %u", axi_freq, mfc_freq, calc_mfc_freq, req_perf_lvl); } #ifdef AXI_CLK_SCALING if (req_perf_lvl != VCD_RESTRK_MIN_PERF_LEVEL) { VCDRES_MSG_MED("\n %s(): Setting AXI freq to %u", __func__, axi_freq); clk_set_rate(ebi1_clk, axi_freq * 1000); } #endif #ifdef USE_RES_TRACKER if (req_perf_lvl != VCD_RESTRK_MIN_PERF_LEVEL) { VCDRES_MSG_MED("\n %s(): Setting MFC freq to %u", __func__, mfc_freq); if (!res_trk_sel_clk_rate(mfc_freq)) { VCDRES_MSG_ERROR("%s(): res_trk_sel_clk_rate FAILED\n", __func__); *pn_set_perf_lvl = 0; return false; } } #endif *pn_set_perf_lvl = res_trk_convert_freq_to_perf_lvl((u64) mfc_freq); return true; }
//static u32 res_trk_enable_pwr_rail(void) static u32 res_trk_enable_videocore(void) /* 20110511 Y.Yagami CHG-E msm: vidc: Fix video core clock power up/down sequence */ { mutex_lock(&resource_context.lock); if (!resource_context.rail_enabled) { int rc = -1; rc = internal_pwr_rail_mode(PWR_RAIL_MFC_CLK, PWR_RAIL_CTL_MANUAL); if (rc) { VCDRES_MSG_ERROR("%s(): internal_pwr_rail_mode \ failed %d\n", __func__, rc); mutex_unlock(&resource_context.lock); return false; } VCDRES_MSG_LOW("%s(): internal_pwr_rail_mode Success %d\n", __func__, rc); resource_context.pclk = clk_get(resource_context.device, "mfc_pclk"); if (IS_ERR(resource_context.pclk)) { VCDRES_MSG_ERROR("%s(): mfc_pclk get failed\n" , __func__); /* 20110511 Y.Yagami CHG-S msm: vidc: Fix video core clock power up/down sequence */ // mutex_unlock(&resource_context.lock); // return false; goto bail_out; /* 20110511 Y.Yagami CHG-E msm: vidc: Fix video core clock power up/down sequence */ } resource_context.hclk = clk_get(resource_context.device, "mfc_clk"); if (IS_ERR(resource_context.hclk)) { VCDRES_MSG_ERROR("%s(): mfc_clk get failed\n" , __func__); /* 20110511 Y.Yagami CHG-S msm: vidc: Fix video core clock power up/down sequence */ // clk_put(resource_context.pclk); // mutex_unlock(&resource_context.lock); // return false; goto release_pclk; /* 20110511 Y.Yagami CHG-E msm: vidc: Fix video core clock power up/down sequence */ } resource_context.hclk_div2 = clk_get(resource_context.device, "mfc_div2_clk"); /* 20110511 Y.Yagami CHG-S msm: vidc: Fix video core clock power up/down sequence */ // if (IS_ERR(resource_context.pclk)) { if (IS_ERR(resource_context.hclk_div2)) { /* 20110511 Y.Yagami CHG-E msm: vidc: Fix video core clock power up/down sequence */ VCDRES_MSG_ERROR("%s(): mfc_div2_clk get failed\n" , __func__); /* 20110511 Y.Yagami CHG-S msm: vidc: Fix video core clock power up/down sequence */ // clk_put(resource_context.pclk); // clk_put(resource_context.hclk); // mutex_unlock(&resource_context.lock); // return false; goto release_hclk_pclk; /* 20110511 Y.Yagami CHG-E msm: vidc: Fix video core clock power up/down sequence */ } #ifdef PATCH0330 /* 20110511 Y.Yagami CHG-S msm: vidc: Fix video core clock power up/down sequence */ // clk_set_rate(resource_context.hclk, // mfc_clk_freq_table[0]); // // clk_enable(resource_context.pclk); // clk_enable(resource_context.hclk); // clk_enable(resource_context.hclk_div2); if (clk_set_rate(resource_context.hclk, mfc_clk_freq_table[0])) { VCDRES_MSG_ERROR("\n pwr_rail_enable:" " set clk rate failed\n"); goto release_all_clks; } if (clk_enable(resource_context.pclk)) { VCDRES_MSG_ERROR("vidc pclk Enable failed\n"); goto release_all_clks; } if (clk_enable(resource_context.hclk)) { VCDRES_MSG_ERROR("vidc hclk Enable failed\n"); goto disable_pclk; } if (clk_enable(resource_context.hclk_div2)) { VCDRES_MSG_ERROR("vidc hclk_div2 Enable failed\n"); goto disable_hclk_pclk; } /* 20110511 Y.Yagami CHG-E msm: vidc: Fix video core clock power up/down sequence */ #endif /* PATCH0330 */ rc = internal_pwr_rail_ctl(PWR_RAIL_MFC_CLK, 1); if (rc) { VCDRES_MSG_ERROR("\n internal_pwr_rail_ctl failed %d\n" , rc); /* 20110511 Y.Yagami CHG-S msm: vidc: Fix video core clock power up/down sequence */ // mutex_unlock(&resource_context.lock); // return false; goto disable_and_release_all_clks; /* 20110511 Y.Yagami CHG-E msm: vidc: Fix video core clock power up/down sequence */ } VCDRES_MSG_LOW("%s(): internal_pwr_rail_ctl Success %d\n" , __func__, rc); msleep(20); rc = clk_reset(resource_context.pclk, CLK_RESET_DEASSERT); if (rc) { VCDRES_MSG_ERROR("\n clk_reset failed %d\n", rc); /* 20110511 Y.Yagami CHG-S msm: vidc: Fix video core clock power up/down sequence */ // mutex_unlock(&resource_context.lock); // return false; goto disable_and_release_all_clks; /* 20110511 Y.Yagami CHG-E msm: vidc: Fix video core clock power up/down sequence */ } msleep(20); #ifdef PATCH0330 clk_disable(resource_context.pclk); clk_disable(resource_context.hclk); clk_disable(resource_context.hclk_div2); #endif /* PATCH0330 */ }
u32 res_trk_download_firmware(void) { const struct firmware *fw_boot = NULL; const struct firmware *fw_mpg4_dec = NULL; const struct firmware *fw_h263_dec = NULL; const struct firmware *fw_h264_dec = NULL; const struct firmware *fw_mpg4_enc = NULL; const struct firmware *fw_h264_enc = NULL; const struct firmware *fw_vc1_dec = NULL; int rc = 0; u32 status = true; VCDRES_MSG_HIGH("%s(): Request firmware download\n", __func__); mutex_lock(&resource_context.lock); rc = request_firmware(&fw_boot, VIDC_BOOT_FW, resource_context.device); if (rc) { VCDRES_MSG_ERROR("request_firmware for %s error %d\n", VIDC_BOOT_FW, rc); mutex_unlock(&resource_context.lock); return false; } vidc_command_control_fw = (unsigned char *)fw_boot->data; vidc_command_control_fw_size = (u32) fw_boot->size; rc = request_firmware(&fw_mpg4_dec, VIDC_MPG4_DEC_FW, resource_context.device); if (rc) { VCDRES_MSG_ERROR("request_firmware for %s error %d\n", VIDC_MPG4_DEC_FW, rc); status = false; goto boot_fw_free; } vidc_mpg4_dec_fw = (unsigned char *)fw_mpg4_dec->data; vidc_mpg4_dec_fw_size = (u32) fw_mpg4_dec->size; rc = request_firmware(&fw_h263_dec, VIDC_H263_DEC_FW, resource_context.device); if (rc) { VCDRES_MSG_ERROR("request_firmware for %s error %d\n", VIDC_H263_DEC_FW, rc); status = false; goto mp4dec_fw_free; } vidc_h263_dec_fw = (unsigned char *)fw_h263_dec->data; vidc_h263_dec_fw_size = (u32) fw_h263_dec->size; rc = request_firmware(&fw_h264_dec, VIDC_H264_DEC_FW, resource_context.device); if (rc) { VCDRES_MSG_ERROR("request_firmware for %s error %d\n", VIDC_H264_DEC_FW, rc); status = false; goto h263dec_fw_free; } vidc_h264_dec_fw = (unsigned char *)fw_h264_dec->data; vidc_h264_dec_fw_size = (u32) fw_h264_dec->size; rc = request_firmware(&fw_mpg4_enc, VIDC_MPG4_ENC_FW, resource_context.device); if (rc) { VCDRES_MSG_ERROR("request_firmware for %s error %d\n", VIDC_MPG4_ENC_FW, rc); status = false; goto h264dec_fw_free; } vidc_mpg4_enc_fw = (unsigned char *)fw_mpg4_enc->data; vidc_mpg4_enc_fw_size = (u32) fw_mpg4_enc->size; rc = request_firmware(&fw_h264_enc, VIDC_H264_ENC_FW, resource_context.device); if (rc) { VCDRES_MSG_ERROR("request_firmware for %s error %d\n", VIDC_H264_ENC_FW, rc); status = false; goto mp4enc_fw_free; } vidc_h264_enc_fw = (unsigned char *)fw_h264_enc->data; vidc_h264_enc_fw_size = (u32) fw_h264_enc->size; rc = request_firmware(&fw_vc1_dec, VIDC_VC1_DEC_FW, resource_context.device); if (rc) { VCDRES_MSG_ERROR("request_firmware for %s error %d\n", VIDC_VC1_DEC_FW, rc); status = false; goto h264enc_fw_free; } vidc_vc1_dec_fw = (unsigned char *)fw_vc1_dec->data; vidc_vc1_dec_fw_size = (u32) fw_vc1_dec->size; mutex_unlock(&resource_context.lock); return status; h264enc_fw_free: release_firmware(fw_h264_enc); mp4enc_fw_free: release_firmware(fw_mpg4_enc); h264dec_fw_free: release_firmware(fw_h264_dec); h263dec_fw_free: release_firmware(fw_h263_dec); mp4dec_fw_free: release_firmware(fw_mpg4_dec); boot_fw_free: release_firmware(fw_boot); mutex_unlock(&resource_context.lock); return false; }
static u32 res_trk_enable_pwr_rail(void) { mutex_lock(&resource_context.lock); if (!resource_context.rail_enabled) { int rc = -1; rc = internal_pwr_rail_mode(PWR_RAIL_MFC_CLK, PWR_RAIL_CTL_MANUAL); if (rc) { VCDRES_MSG_ERROR("%s(): internal_pwr_rail_mode \ failed %d\n", __func__, rc); mutex_unlock(&resource_context.lock); return false; } VCDRES_MSG_LOW("%s(): internal_pwr_rail_mode Success %d\n", __func__, rc); resource_context.pclk = clk_get(resource_context.device, "mfc_pclk"); if (IS_ERR(resource_context.pclk)) { VCDRES_MSG_ERROR("%s(): mfc_pclk get failed\n" , __func__); mutex_unlock(&resource_context.lock); return false; } resource_context.hclk = clk_get(resource_context.device, "mfc_clk"); if (IS_ERR(resource_context.hclk)) { VCDRES_MSG_ERROR("%s(): mfc_clk get failed\n" , __func__); clk_put(resource_context.pclk); mutex_unlock(&resource_context.lock); return false; } resource_context.hclk_div2 = clk_get(resource_context.device, "mfc_div2_clk"); if (IS_ERR(resource_context.pclk)) { VCDRES_MSG_ERROR("%s(): mfc_div2_clk get failed\n" , __func__); clk_put(resource_context.pclk); clk_put(resource_context.hclk); mutex_unlock(&resource_context.lock); return false; } rc = internal_pwr_rail_ctl(PWR_RAIL_MFC_CLK, 1); if (rc) { VCDRES_MSG_ERROR("\n internal_pwr_rail_ctl failed %d\n" , rc); mutex_unlock(&resource_context.lock); return false; } VCDRES_MSG_LOW("%s(): internal_pwr_rail_ctl Success %d\n" , __func__, rc); msleep(20); rc = clk_reset(resource_context.pclk, CLK_RESET_DEASSERT); if (rc) { VCDRES_MSG_ERROR("\n clk_reset failed %d\n", rc); mutex_unlock(&resource_context.lock); return false; } msleep(20); }
static u32 res_trk_disable_videocore(void) { int rc = -1; mutex_lock(&resource_context.lock); if (!resource_context.rail_enabled) { mutex_unlock(&resource_context.lock); return false; } if (!resource_context.clock_enabled && resource_context.pclk && resource_context.hclk && resource_context.hclk_div2) { VCDRES_MSG_LOW("\nEnabling clk before disabling pwr rail\n"); if (clk_set_rate(resource_context.hclk, mfc_clk_freq_table[0])) { VCDRES_MSG_ERROR("\n pwr_rail_disable:" " set clk rate failed\n"); goto bail_out; } if (clk_prepare_enable(resource_context.pclk)) { VCDRES_MSG_ERROR("vidc pclk Enable failed\n"); goto bail_out; } if (clk_prepare_enable(resource_context.hclk)) { VCDRES_MSG_ERROR("vidc hclk Enable failed\n"); goto disable_pclk; } if (clk_prepare_enable(resource_context.hclk_div2)) { VCDRES_MSG_ERROR("vidc hclk_div2 Enable failed\n"); goto disable_hclk; } } else { VCDRES_MSG_ERROR("\ndisabling pwr rail: Enabling clk failed\n"); goto bail_out; } resource_context.rail_enabled = 0; rc = clk_reset(resource_context.pclk, CLK_RESET_ASSERT); if (rc) { VCDRES_MSG_ERROR("\n clk_reset failed %d\n", rc); mutex_unlock(&resource_context.lock); return false; } msleep(20); clk_disable_unprepare(resource_context.pclk); clk_disable_unprepare(resource_context.hclk); clk_disable_unprepare(resource_context.hclk_div2); clk_put(resource_context.hclk_div2); clk_put(resource_context.hclk); clk_put(resource_context.pclk); rc = regulator_disable(resource_context.regulator); if (rc) { VCDRES_MSG_ERROR("\n regulator disable failed %d\n", rc); mutex_unlock(&resource_context.lock); return false; } resource_context.hclk_div2 = NULL; resource_context.hclk = NULL; resource_context.pclk = NULL; mutex_unlock(&resource_context.lock); return true; disable_hclk: clk_disable_unprepare(resource_context.hclk); disable_pclk: clk_disable_unprepare(resource_context.pclk); bail_out: if (resource_context.pclk) { clk_put(resource_context.pclk); resource_context.pclk = NULL; } if (resource_context.hclk) { clk_put(resource_context.hclk); resource_context.hclk = NULL; } if (resource_context.hclk_div2) { clk_put(resource_context.hclk_div2); resource_context.hclk_div2 = NULL; } mutex_unlock(&resource_context.lock); return false; }
u32 res_trk_set_perf_level(u32 n_req_perf_lvl, u32 *pn_set_perf_lvl, struct vcd_clnt_ctxt_type_t *p_cctxt) { u32 axi_freq = 0, mfc_freq = 0, calc_mfc_freq = 0; int rc = -1; if (!pn_set_perf_lvl) { VCDRES_MSG_ERROR("%s(): pn_perf_lvl is NULL\n", __func__); return FALSE; } VCDRES_MSG_LOW("%s(), n_req_perf_lvl = %d", __func__, n_req_perf_lvl); if (p_cctxt) { calc_mfc_freq = res_trk_convert_perf_lvl_to_freq( (u64)n_req_perf_lvl); if (calc_mfc_freq < VCD_RESTRK_MIN_FREQ_POINT) calc_mfc_freq = VCD_RESTRK_MIN_FREQ_POINT; else if (calc_mfc_freq > VCD_RESTRK_MAX_FREQ_POINT) calc_mfc_freq = VCD_RESTRK_MAX_FREQ_POINT; if (!p_cctxt->b_decoding) { if (n_req_perf_lvl >= VGA_PERF_LEVEL) { mfc_freq = mfc_clk_freq_table[2]; axi_freq = axi_clk_freq_table_enc[1]; } else { mfc_freq = mfc_clk_freq_table[0]; axi_freq = axi_clk_freq_table_enc[0]; } VCDRES_MSG_HIGH("\n ENCODER: axi_freq = %u" ", mfc_freq = %u, calc_mfc_freq = %u," " n_req_perf_lvl = %u", axi_freq, mfc_freq, calc_mfc_freq, n_req_perf_lvl); } else { if (n_req_perf_lvl <= QVGA_PERF_LEVEL) { mfc_freq = mfc_clk_freq_table[0]; axi_freq = axi_clk_freq_table_dec[0]; } else { axi_freq = axi_clk_freq_table_dec[0]; if (n_req_perf_lvl <= VGA_PERF_LEVEL) mfc_freq = mfc_clk_freq_table[0]; else if (n_req_perf_lvl <= WVGA_PERF_LEVEL) mfc_freq = mfc_clk_freq_table[1]; else { mfc_freq = mfc_clk_freq_table[2]; axi_freq = axi_clk_freq_table_dec[1]; } } VCDRES_MSG_HIGH("\n DECODER: axi_freq = %u" ", mfc_freq = %u, calc_mfc_freq = %u," " n_req_perf_lvl = %u", axi_freq, mfc_freq, calc_mfc_freq, n_req_perf_lvl); } } else { VCDRES_MSG_HIGH("%s() WARNING:: p_cctxt is NULL", __func__); return TRUE; } #ifdef AXI_CLK_SCALING if (n_req_perf_lvl != VCD_RESTRK_MIN_PERF_LEVEL) { VCDRES_MSG_HIGH("\n %s(): Setting AXI freq to %u", __func__, axi_freq); rc = pm_qos_update_requirement(PM_QOS_SYSTEM_BUS_FREQ, MSM_AXI_QOS_NAME, axi_freq); if (rc < 0) { VCDRES_MSG_ERROR("\n Update AXI bus QOS fails," "rc = %d\n", rc); return FALSE; } } #endif #ifdef USE_RES_TRACKER if (n_req_perf_lvl != VCD_RESTRK_MIN_PERF_LEVEL) { VCDRES_MSG_HIGH("\n %s(): Setting MFC freq to %u", __func__, mfc_freq); if (!vid_c_sel_clk_rate(mfc_freq)) { VCDRES_MSG_ERROR("%s(): vid_c_sel_clk_rate FAILED\n", __func__); *pn_set_perf_lvl = 0; return FALSE; } } #endif *pn_set_perf_lvl = res_trk_convert_freq_to_perf_lvl((u64) mfc_freq); return TRUE; }