Loading drivers/video/msm/mdss/mdp3_ctrl.c +17 −0 Original line number Diff line number Diff line Loading @@ -506,6 +506,7 @@ static int mdp3_ctrl_dma_init(struct msm_fb_data_type *mfd, int vbp, vfp, vspw; int vtotal, vporch; struct mdp3_notification dma_done_callback; struct mdp3_tear_check te; vbp = panel_info->lcdc.v_back_porch; vfp = panel_info->lcdc.v_front_porch; Loading Loading @@ -537,12 +538,28 @@ static int mdp3_ctrl_dma_init(struct msm_fb_data_type *mfd, (MDP3_DMA_OUTPUT_COMP_BITS_8 << 2)| MDP3_DMA_OUTPUT_COMP_BITS_8; te.frame_rate = panel_info->mipi.frame_rate; te.hw_vsync_mode = panel_info->mipi.hw_vsync_mode; te.tear_check_en = panel_info->te.tear_check_en; te.sync_cfg_height = panel_info->te.sync_cfg_height; te.vsync_init_val = panel_info->te.vsync_init_val; te.sync_threshold_start = panel_info->te.sync_threshold_start; te.sync_threshold_continue = panel_info->te.sync_threshold_continue; te.start_pos = panel_info->te.start_pos; te.rd_ptr_irq = panel_info->te.rd_ptr_irq; te.refx100 = panel_info->te.refx100; if (dma->dma_config) rc = dma->dma_config(dma, &sourceConfig, &outputConfig); else rc = -EINVAL; if (outputConfig.out_sel == MDP3_DMA_OUTPUT_SEL_DSI_CMD) { if (dma->dma_sync_config) rc = dma->dma_sync_config(dma, &sourceConfig, &te); else rc = -EINVAL; dma_done_callback.handler = dma_done_notify_handler; dma_done_callback.arg = mfd->mdp.private1; dma->dma_done_notifier(dma, &dma_done_callback); Loading drivers/video/msm/mdss/mdp3_dma.c +44 −24 Original line number Diff line number Diff line Loading @@ -24,6 +24,11 @@ #define DMA_CCS_CONFIG_MASK 0xfffffc17 #define HIST_WAIT_TIMEOUT(frame) ((75 * HZ * (frame)) / 1000) #define VSYNC_SELECT 0x024 #define VSYNC_TOTAL_LINES_SHIFT 21 #define VSYNC_COUNT_MASK 0x7ffff #define VSYNC_THRESH_CONT_SHIFT 16 static void mdp3_vsync_intr_handler(int type, void *arg) { struct mdp3_dma *dma = (struct mdp3_dma *)arg; Loading Loading @@ -266,32 +271,48 @@ static void mdp3_dma_clk_auto_gating(struct mdp3_dma *dma, int enable) } } static int mdp3_dma_sync_config(struct mdp3_dma *dma, struct mdp3_dma_source *source_config) int mdp3_dma_sync_config(struct mdp3_dma *dma, struct mdp3_dma_source *source_config, struct mdp3_tear_check *te) { u32 sync_config; u32 vsync_clk_speed_hz, vclks_line, cfg; int porch = source_config->vporch; int height = source_config->height; int total_lines = height + porch; int dma_sel = dma->dma_sel; pr_debug("mdp3_dma_sync_config\n"); vsync_clk_speed_hz = MDP_VSYNC_CLK_RATE; if (dma->output_config.out_sel == MDP3_DMA_OUTPUT_SEL_DSI_CMD) { int porch = source_config->vporch; int height = source_config->height; int vtotal = height + porch; sync_config = vtotal << 21; sync_config |= source_config->vsync_count; sync_config |= BIT(19); sync_config |= BIT(20); MDP3_REG_WRITE(MDP3_REG_SYNC_CONFIG_0 + dma_sel, sync_config); MDP3_REG_WRITE(MDP3_REG_VSYNC_SEL, 0x024); MDP3_REG_WRITE(MDP3_REG_PRIMARY_VSYNC_INIT_VAL + dma_sel, height); MDP3_REG_WRITE(MDP3_REG_PRIMARY_RD_PTR_IRQ, 0x5); MDP3_REG_WRITE(MDP3_REG_SYNC_THRESH_0 + dma_sel, (4 << 16 | 2)); MDP3_REG_WRITE(MDP3_REG_PRIMARY_START_P0S + dma_sel, porch); MDP3_REG_WRITE(MDP3_REG_TEAR_CHECK_EN, 0x1); cfg = total_lines << VSYNC_TOTAL_LINES_SHIFT; total_lines *= te->frame_rate; vclks_line = (total_lines) ? vsync_clk_speed_hz / total_lines : 0; cfg |= BIT(19); if (te->hw_vsync_mode) cfg |= BIT(20); if (te->refx100) { vclks_line = vclks_line * te->frame_rate * 100 / te->refx100; } else { pr_warn("refx100 cannot be zero! Use 6000 as default\n"); vclks_line = vclks_line * te->frame_rate * 100 / 6000; } cfg |= (vclks_line & VSYNC_COUNT_MASK); MDP3_REG_WRITE(MDP3_REG_SYNC_CONFIG_0 + dma_sel, cfg); MDP3_REG_WRITE(MDP3_REG_VSYNC_SEL, VSYNC_SELECT); MDP3_REG_WRITE(MDP3_REG_PRIMARY_VSYNC_INIT_VAL + dma_sel, te->vsync_init_val); MDP3_REG_WRITE(MDP3_REG_PRIMARY_RD_PTR_IRQ, te->rd_ptr_irq); MDP3_REG_WRITE(MDP3_REG_SYNC_THRESH_0 + dma_sel, ((te->sync_threshold_continue << VSYNC_THRESH_CONT_SHIFT) | te->sync_threshold_start)); MDP3_REG_WRITE(MDP3_REG_PRIMARY_START_P0S + dma_sel, te->start_pos); MDP3_REG_WRITE(MDP3_REG_TEAR_CHECK_EN, te->tear_check_en); return 0; } Loading Loading @@ -324,8 +345,6 @@ static int mdp3_dmap_config(struct mdp3_dma *dma, dma->source_config = *source_config; dma->output_config = *output_config; mdp3_dma_sync_config(dma, source_config); mdp3_irq_enable(MDP3_INTR_LCDC_UNDERFLOW); mdp3_dma_callback_setup(dma); return 0; Loading Loading @@ -378,7 +397,6 @@ static int mdp3_dmas_config(struct mdp3_dma *dma, dma->source_config = *source_config; dma->output_config = *output_config; mdp3_dma_sync_config(dma, source_config); mdp3_dma_callback_setup(dma); return 0; Loading Loading @@ -925,6 +943,7 @@ int mdp3_dma_init(struct mdp3_dma *dma) switch (dma->dma_sel) { case MDP3_DMA_P: dma->dma_config = mdp3_dmap_config; dma->dma_sync_config = mdp3_dma_sync_config; dma->dma_config_source = mdp3_dmap_config_source; dma->config_cursor = mdp3_dmap_cursor_config; dma->config_ccs = mdp3_dmap_ccs_config; Loading @@ -941,6 +960,7 @@ int mdp3_dma_init(struct mdp3_dma *dma) break; case MDP3_DMA_S: dma->dma_config = mdp3_dmas_config; dma->dma_sync_config = mdp3_dma_sync_config; dma->dma_config_source = mdp3_dmas_config_source; dma->config_cursor = NULL; dma->config_ccs = NULL; Loading drivers/video/msm/mdss/mdp3_dma.h +16 −0 Original line number Diff line number Diff line Loading @@ -233,6 +233,19 @@ struct mdp3_notification { void *arg; }; struct mdp3_tear_check { int frame_rate; bool hw_vsync_mode; u32 tear_check_en; u32 sync_cfg_height; u32 vsync_init_val; u32 sync_threshold_start; u32 sync_threshold_continue; u32 start_pos; u32 rd_ptr_irq; u32 refx100; }; struct mdp3_intf; struct mdp3_dma { Loading Loading @@ -265,6 +278,9 @@ struct mdp3_dma { struct mdp3_dma_source *source_config, struct mdp3_dma_output_config *output_config); int (*dma_sync_config)(struct mdp3_dma *dma, struct mdp3_dma_source *source_config, struct mdp3_tear_check *te); void (*dma_config_source)(struct mdp3_dma *dma); int (*start)(struct mdp3_dma *dma, struct mdp3_intf *intf); Loading Loading
drivers/video/msm/mdss/mdp3_ctrl.c +17 −0 Original line number Diff line number Diff line Loading @@ -506,6 +506,7 @@ static int mdp3_ctrl_dma_init(struct msm_fb_data_type *mfd, int vbp, vfp, vspw; int vtotal, vporch; struct mdp3_notification dma_done_callback; struct mdp3_tear_check te; vbp = panel_info->lcdc.v_back_porch; vfp = panel_info->lcdc.v_front_porch; Loading Loading @@ -537,12 +538,28 @@ static int mdp3_ctrl_dma_init(struct msm_fb_data_type *mfd, (MDP3_DMA_OUTPUT_COMP_BITS_8 << 2)| MDP3_DMA_OUTPUT_COMP_BITS_8; te.frame_rate = panel_info->mipi.frame_rate; te.hw_vsync_mode = panel_info->mipi.hw_vsync_mode; te.tear_check_en = panel_info->te.tear_check_en; te.sync_cfg_height = panel_info->te.sync_cfg_height; te.vsync_init_val = panel_info->te.vsync_init_val; te.sync_threshold_start = panel_info->te.sync_threshold_start; te.sync_threshold_continue = panel_info->te.sync_threshold_continue; te.start_pos = panel_info->te.start_pos; te.rd_ptr_irq = panel_info->te.rd_ptr_irq; te.refx100 = panel_info->te.refx100; if (dma->dma_config) rc = dma->dma_config(dma, &sourceConfig, &outputConfig); else rc = -EINVAL; if (outputConfig.out_sel == MDP3_DMA_OUTPUT_SEL_DSI_CMD) { if (dma->dma_sync_config) rc = dma->dma_sync_config(dma, &sourceConfig, &te); else rc = -EINVAL; dma_done_callback.handler = dma_done_notify_handler; dma_done_callback.arg = mfd->mdp.private1; dma->dma_done_notifier(dma, &dma_done_callback); Loading
drivers/video/msm/mdss/mdp3_dma.c +44 −24 Original line number Diff line number Diff line Loading @@ -24,6 +24,11 @@ #define DMA_CCS_CONFIG_MASK 0xfffffc17 #define HIST_WAIT_TIMEOUT(frame) ((75 * HZ * (frame)) / 1000) #define VSYNC_SELECT 0x024 #define VSYNC_TOTAL_LINES_SHIFT 21 #define VSYNC_COUNT_MASK 0x7ffff #define VSYNC_THRESH_CONT_SHIFT 16 static void mdp3_vsync_intr_handler(int type, void *arg) { struct mdp3_dma *dma = (struct mdp3_dma *)arg; Loading Loading @@ -266,32 +271,48 @@ static void mdp3_dma_clk_auto_gating(struct mdp3_dma *dma, int enable) } } static int mdp3_dma_sync_config(struct mdp3_dma *dma, struct mdp3_dma_source *source_config) int mdp3_dma_sync_config(struct mdp3_dma *dma, struct mdp3_dma_source *source_config, struct mdp3_tear_check *te) { u32 sync_config; u32 vsync_clk_speed_hz, vclks_line, cfg; int porch = source_config->vporch; int height = source_config->height; int total_lines = height + porch; int dma_sel = dma->dma_sel; pr_debug("mdp3_dma_sync_config\n"); vsync_clk_speed_hz = MDP_VSYNC_CLK_RATE; if (dma->output_config.out_sel == MDP3_DMA_OUTPUT_SEL_DSI_CMD) { int porch = source_config->vporch; int height = source_config->height; int vtotal = height + porch; sync_config = vtotal << 21; sync_config |= source_config->vsync_count; sync_config |= BIT(19); sync_config |= BIT(20); MDP3_REG_WRITE(MDP3_REG_SYNC_CONFIG_0 + dma_sel, sync_config); MDP3_REG_WRITE(MDP3_REG_VSYNC_SEL, 0x024); MDP3_REG_WRITE(MDP3_REG_PRIMARY_VSYNC_INIT_VAL + dma_sel, height); MDP3_REG_WRITE(MDP3_REG_PRIMARY_RD_PTR_IRQ, 0x5); MDP3_REG_WRITE(MDP3_REG_SYNC_THRESH_0 + dma_sel, (4 << 16 | 2)); MDP3_REG_WRITE(MDP3_REG_PRIMARY_START_P0S + dma_sel, porch); MDP3_REG_WRITE(MDP3_REG_TEAR_CHECK_EN, 0x1); cfg = total_lines << VSYNC_TOTAL_LINES_SHIFT; total_lines *= te->frame_rate; vclks_line = (total_lines) ? vsync_clk_speed_hz / total_lines : 0; cfg |= BIT(19); if (te->hw_vsync_mode) cfg |= BIT(20); if (te->refx100) { vclks_line = vclks_line * te->frame_rate * 100 / te->refx100; } else { pr_warn("refx100 cannot be zero! Use 6000 as default\n"); vclks_line = vclks_line * te->frame_rate * 100 / 6000; } cfg |= (vclks_line & VSYNC_COUNT_MASK); MDP3_REG_WRITE(MDP3_REG_SYNC_CONFIG_0 + dma_sel, cfg); MDP3_REG_WRITE(MDP3_REG_VSYNC_SEL, VSYNC_SELECT); MDP3_REG_WRITE(MDP3_REG_PRIMARY_VSYNC_INIT_VAL + dma_sel, te->vsync_init_val); MDP3_REG_WRITE(MDP3_REG_PRIMARY_RD_PTR_IRQ, te->rd_ptr_irq); MDP3_REG_WRITE(MDP3_REG_SYNC_THRESH_0 + dma_sel, ((te->sync_threshold_continue << VSYNC_THRESH_CONT_SHIFT) | te->sync_threshold_start)); MDP3_REG_WRITE(MDP3_REG_PRIMARY_START_P0S + dma_sel, te->start_pos); MDP3_REG_WRITE(MDP3_REG_TEAR_CHECK_EN, te->tear_check_en); return 0; } Loading Loading @@ -324,8 +345,6 @@ static int mdp3_dmap_config(struct mdp3_dma *dma, dma->source_config = *source_config; dma->output_config = *output_config; mdp3_dma_sync_config(dma, source_config); mdp3_irq_enable(MDP3_INTR_LCDC_UNDERFLOW); mdp3_dma_callback_setup(dma); return 0; Loading Loading @@ -378,7 +397,6 @@ static int mdp3_dmas_config(struct mdp3_dma *dma, dma->source_config = *source_config; dma->output_config = *output_config; mdp3_dma_sync_config(dma, source_config); mdp3_dma_callback_setup(dma); return 0; Loading Loading @@ -925,6 +943,7 @@ int mdp3_dma_init(struct mdp3_dma *dma) switch (dma->dma_sel) { case MDP3_DMA_P: dma->dma_config = mdp3_dmap_config; dma->dma_sync_config = mdp3_dma_sync_config; dma->dma_config_source = mdp3_dmap_config_source; dma->config_cursor = mdp3_dmap_cursor_config; dma->config_ccs = mdp3_dmap_ccs_config; Loading @@ -941,6 +960,7 @@ int mdp3_dma_init(struct mdp3_dma *dma) break; case MDP3_DMA_S: dma->dma_config = mdp3_dmas_config; dma->dma_sync_config = mdp3_dma_sync_config; dma->dma_config_source = mdp3_dmas_config_source; dma->config_cursor = NULL; dma->config_ccs = NULL; Loading
drivers/video/msm/mdss/mdp3_dma.h +16 −0 Original line number Diff line number Diff line Loading @@ -233,6 +233,19 @@ struct mdp3_notification { void *arg; }; struct mdp3_tear_check { int frame_rate; bool hw_vsync_mode; u32 tear_check_en; u32 sync_cfg_height; u32 vsync_init_val; u32 sync_threshold_start; u32 sync_threshold_continue; u32 start_pos; u32 rd_ptr_irq; u32 refx100; }; struct mdp3_intf; struct mdp3_dma { Loading Loading @@ -265,6 +278,9 @@ struct mdp3_dma { struct mdp3_dma_source *source_config, struct mdp3_dma_output_config *output_config); int (*dma_sync_config)(struct mdp3_dma *dma, struct mdp3_dma_source *source_config, struct mdp3_tear_check *te); void (*dma_config_source)(struct mdp3_dma *dma); int (*start)(struct mdp3_dma *dma, struct mdp3_intf *intf); Loading