Lines Matching +full:timing +full:- +full:0

1 // SPDX-License-Identifier: GPL-2.0-only
35 #define DSI_START 0x00
37 #define DSI_INTEN 0x08
39 #define DSI_INTSTA 0x0c
40 #define LPRX_RD_RDY_INT_FLAG BIT(0)
47 #define DSI_CON_CTRL 0x10
48 #define DSI_RESET BIT(0)
52 #define DSI_MODE_CTRL 0x14
54 #define CMD_MODE 0
61 #define DSI_TXRX_CTRL 0x18
72 #define DSI_PSCTRL 0x1c
73 #define DSI_PS_WC GENMASK(13, 0)
75 #define PACKED_PS_16BIT_RGB565 0
80 #define DSI_VSA_NL 0x20
81 #define DSI_VBP_NL 0x24
82 #define DSI_VFP_NL 0x28
83 #define DSI_VACT_NL 0x2C
84 #define VACT_NL GENMASK(14, 0)
85 #define DSI_SIZE_CON 0x38
87 #define DSI_WIDTH GENMASK(14, 0)
88 #define DSI_HSA_WC 0x50
89 #define DSI_HBP_WC 0x54
90 #define DSI_HFP_WC 0x58
94 #define DSI_CMDQ_SIZE 0x60
95 #define CMDQ_SIZE 0x3f
98 #define DSI_HSTX_CKL_WC 0x64
101 #define DSI_RX_DATA0 0x74
102 #define DSI_RX_DATA1 0x78
103 #define DSI_RX_DATA2 0x7c
104 #define DSI_RX_DATA3 0x80
106 #define DSI_RACK 0x84
107 #define RACK BIT(0)
109 #define DSI_PHY_LCCON 0x104
110 #define LC_HS_TX_EN BIT(0)
114 #define DSI_PHY_LD0CON 0x108
115 #define LD0_HS_TX_EN BIT(0)
119 #define DSI_PHY_TIMECON0 0x110
120 #define LPX GENMASK(7, 0)
125 #define DSI_PHY_TIMECON1 0x114
126 #define TA_GO GENMASK(7, 0)
131 #define DSI_PHY_TIMECON2 0x118
132 #define CONT_DET GENMASK(7, 0)
137 #define DSI_PHY_TIMECON3 0x11c
138 #define CLK_HS_PREP GENMASK(7, 0)
143 #define VM_CMD_EN BIT(0)
147 #define FORCE_COMMIT BIT(0)
151 #define CONFIG GENMASK(7, 0)
152 #define SHORT_PACKET 0
159 #define NS_TO_CYCLE(n, c) ((n) / (c) + (((n) % (c)) ? 1 : 0))
240 u32 temp = readl(dsi->regs + offset); in mtk_dsi_mask()
242 writel((temp & ~mask) | (data & mask), dsi->regs + offset); in mtk_dsi_mask()
248 u32 data_rate_mhz = DIV_ROUND_UP(dsi->data_rate, HZ_PER_MHZ); in mtk_dsi_phy_timconfig()
249 struct mtk_phy_timing *timing = &dsi->phy_timing; in mtk_dsi_phy_timconfig() local
251 timing->lpx = (60 * data_rate_mhz / (8 * 1000)) + 1; in mtk_dsi_phy_timconfig()
252 timing->da_hs_prepare = (80 * data_rate_mhz + 4 * 1000) / 8000; in mtk_dsi_phy_timconfig()
253 timing->da_hs_zero = (170 * data_rate_mhz + 10 * 1000) / 8000 + 1 - in mtk_dsi_phy_timconfig()
254 timing->da_hs_prepare; in mtk_dsi_phy_timconfig()
255 timing->da_hs_trail = timing->da_hs_prepare + 1; in mtk_dsi_phy_timconfig()
257 timing->ta_go = 4 * timing->lpx - 2; in mtk_dsi_phy_timconfig()
258 timing->ta_sure = timing->lpx + 2; in mtk_dsi_phy_timconfig()
259 timing->ta_get = 4 * timing->lpx; in mtk_dsi_phy_timconfig()
260 timing->da_hs_exit = 2 * timing->lpx + 1; in mtk_dsi_phy_timconfig()
262 timing->clk_hs_prepare = 70 * data_rate_mhz / (8 * 1000); in mtk_dsi_phy_timconfig()
263 timing->clk_hs_post = timing->clk_hs_prepare + 8; in mtk_dsi_phy_timconfig()
264 timing->clk_hs_trail = timing->clk_hs_prepare; in mtk_dsi_phy_timconfig()
265 timing->clk_hs_zero = timing->clk_hs_trail * 4; in mtk_dsi_phy_timconfig()
266 timing->clk_hs_exit = 2 * timing->clk_hs_trail; in mtk_dsi_phy_timconfig()
268 timcon0 = FIELD_PREP(LPX, timing->lpx) | in mtk_dsi_phy_timconfig()
269 FIELD_PREP(HS_PREP, timing->da_hs_prepare) | in mtk_dsi_phy_timconfig()
270 FIELD_PREP(HS_ZERO, timing->da_hs_zero) | in mtk_dsi_phy_timconfig()
271 FIELD_PREP(HS_TRAIL, timing->da_hs_trail); in mtk_dsi_phy_timconfig()
273 timcon1 = FIELD_PREP(TA_GO, timing->ta_go) | in mtk_dsi_phy_timconfig()
274 FIELD_PREP(TA_SURE, timing->ta_sure) | in mtk_dsi_phy_timconfig()
275 FIELD_PREP(TA_GET, timing->ta_get) | in mtk_dsi_phy_timconfig()
276 FIELD_PREP(DA_HS_EXIT, timing->da_hs_exit); in mtk_dsi_phy_timconfig()
279 FIELD_PREP(CLK_ZERO, timing->clk_hs_zero) | in mtk_dsi_phy_timconfig()
280 FIELD_PREP(CLK_TRAIL, timing->clk_hs_trail); in mtk_dsi_phy_timconfig()
282 timcon3 = FIELD_PREP(CLK_HS_PREP, timing->clk_hs_prepare) | in mtk_dsi_phy_timconfig()
283 FIELD_PREP(CLK_HS_POST, timing->clk_hs_post) | in mtk_dsi_phy_timconfig()
284 FIELD_PREP(CLK_HS_EXIT, timing->clk_hs_exit); in mtk_dsi_phy_timconfig()
286 writel(timcon0, dsi->regs + DSI_PHY_TIMECON0); in mtk_dsi_phy_timconfig()
287 writel(timcon1, dsi->regs + DSI_PHY_TIMECON1); in mtk_dsi_phy_timconfig()
288 writel(timcon2, dsi->regs + DSI_PHY_TIMECON2); in mtk_dsi_phy_timconfig()
289 writel(timcon3, dsi->regs + DSI_PHY_TIMECON3); in mtk_dsi_phy_timconfig()
299 mtk_dsi_mask(dsi, DSI_CON_CTRL, DSI_EN, 0); in mtk_dsi_disable()
305 mtk_dsi_mask(dsi, DSI_CON_CTRL, DSI_RESET, 0); in mtk_dsi_reset_engine()
311 mtk_dsi_mask(dsi, DSI_CON_CTRL, DPHY_RESET, 0); in mtk_dsi_reset_dphy()
316 mtk_dsi_mask(dsi, DSI_PHY_LCCON, LC_HS_TX_EN, 0); in mtk_dsi_clk_ulp_mode_enter()
317 mtk_dsi_mask(dsi, DSI_PHY_LCCON, LC_ULPM_EN, 0); in mtk_dsi_clk_ulp_mode_enter()
322 mtk_dsi_mask(dsi, DSI_PHY_LCCON, LC_ULPM_EN, 0); in mtk_dsi_clk_ulp_mode_leave()
324 mtk_dsi_mask(dsi, DSI_PHY_LCCON, LC_WAKEUP_EN, 0); in mtk_dsi_clk_ulp_mode_leave()
329 mtk_dsi_mask(dsi, DSI_PHY_LD0CON, LD0_HS_TX_EN, 0); in mtk_dsi_lane0_ulp_mode_enter()
330 mtk_dsi_mask(dsi, DSI_PHY_LD0CON, LD0_ULPM_EN, 0); in mtk_dsi_lane0_ulp_mode_enter()
335 mtk_dsi_mask(dsi, DSI_PHY_LD0CON, LD0_ULPM_EN, 0); in mtk_dsi_lane0_ulp_mode_leave()
337 mtk_dsi_mask(dsi, DSI_PHY_LD0CON, LD0_WAKEUP_EN, 0); in mtk_dsi_lane0_ulp_mode_leave()
342 return readl(dsi->regs + DSI_PHY_LCCON) & LC_HS_TX_EN; in mtk_dsi_clk_hs_state()
350 mtk_dsi_mask(dsi, DSI_PHY_LCCON, LC_HS_TX_EN, 0); in mtk_dsi_clk_hs_mode()
357 if (dsi->mode_flags & MIPI_DSI_MODE_VIDEO) { in mtk_dsi_set_mode()
358 if (dsi->mode_flags & MIPI_DSI_MODE_VIDEO_BURST) in mtk_dsi_set_mode()
360 else if (dsi->mode_flags & MIPI_DSI_MODE_VIDEO_SYNC_PULSE) in mtk_dsi_set_mode()
366 writel(vid_mode, dsi->regs + DSI_MODE_CTRL); in mtk_dsi_set_mode()
371 mtk_dsi_mask(dsi, dsi->driver_data->reg_vm_cmd_off, VM_CMD_EN, VM_CMD_EN); in mtk_dsi_set_vm_cmd()
372 mtk_dsi_mask(dsi, dsi->driver_data->reg_vm_cmd_off, TS_VFP_EN, TS_VFP_EN); in mtk_dsi_set_vm_cmd()
377 u32 regval, tmp_reg = 0; in mtk_dsi_rxtx_control()
381 for (i = 0; i < dsi->lanes; i++) in mtk_dsi_rxtx_control()
386 if (dsi->mode_flags & MIPI_DSI_CLOCK_NON_CONTINUOUS) in mtk_dsi_rxtx_control()
389 if (dsi->mode_flags & MIPI_DSI_MODE_NO_EOT_PACKET) in mtk_dsi_rxtx_control()
392 writel(regval, dsi->regs + DSI_TXRX_CTRL); in mtk_dsi_rxtx_control()
399 if (dsi->format == MIPI_DSI_FMT_RGB565) in mtk_dsi_ps_control()
405 ps_wc = FIELD_PREP(DSI_PS_WC, dsi->vm.hactive * dsi_buf_bpp); in mtk_dsi_ps_control()
409 switch (dsi->format) { in mtk_dsi_ps_control()
427 vact_nl = FIELD_PREP(VACT_NL, dsi->vm.vactive); in mtk_dsi_ps_control()
428 writel(vact_nl, dsi->regs + DSI_VACT_NL); in mtk_dsi_ps_control()
429 writel(ps_wc, dsi->regs + DSI_HSTX_CKL_WC); in mtk_dsi_ps_control()
431 writel(ps_val, dsi->regs + DSI_PSCTRL); in mtk_dsi_ps_control()
446 struct videomode *vm = &dsi->vm; in mtk_dsi_config_vdo_timing_per_frame_lp()
448 if (dsi->format == MIPI_DSI_FMT_RGB565) in mtk_dsi_config_vdo_timing_per_frame_lp()
453 da_hs_trail = dsi->phy_timing.da_hs_trail; in mtk_dsi_config_vdo_timing_per_frame_lp()
454 ps_wc = vm->hactive * dsi_tmp_buf_bpp; in mtk_dsi_config_vdo_timing_per_frame_lp()
456 if (dsi->mode_flags & MIPI_DSI_MODE_VIDEO_SYNC_PULSE) { in mtk_dsi_config_vdo_timing_per_frame_lp()
458 vm->hsync_len * dsi_tmp_buf_bpp - 10; in mtk_dsi_config_vdo_timing_per_frame_lp()
460 vm->hback_porch * dsi_tmp_buf_bpp - 10; in mtk_dsi_config_vdo_timing_per_frame_lp()
466 horizontal_sync_active_byte = vm->hsync_len * dsi_tmp_buf_bpp - 4; in mtk_dsi_config_vdo_timing_per_frame_lp()
467 horizontal_backporch_byte = (vm->hback_porch + vm->hsync_len) * in mtk_dsi_config_vdo_timing_per_frame_lp()
468 dsi_tmp_buf_bpp - 10; in mtk_dsi_config_vdo_timing_per_frame_lp()
471 if (dsi->mode_flags & MIPI_DSI_MODE_VIDEO_BURST) { in mtk_dsi_config_vdo_timing_per_frame_lp()
479 horizontal_frontporch_byte = vm->hfront_porch * dsi_tmp_buf_bpp - hfp_byte_adjust; in mtk_dsi_config_vdo_timing_per_frame_lp()
481 horizontal_frontporch_byte) % dsi->lanes; in mtk_dsi_config_vdo_timing_per_frame_lp()
483 horizontal_backporch_byte += dsi->lanes - v_active_roundup; in mtk_dsi_config_vdo_timing_per_frame_lp()
484 hstx_cklp_wc_min = (DIV_ROUND_UP(cklp_wc_min_adjust, dsi->lanes) + da_hs_trail + 1) in mtk_dsi_config_vdo_timing_per_frame_lp()
485 * dsi->lanes / 6 - 1; in mtk_dsi_config_vdo_timing_per_frame_lp()
487 ps_wc), dsi->lanes) + da_hs_trail + 1) * dsi->lanes / 6 - 1; in mtk_dsi_config_vdo_timing_per_frame_lp()
490 writel(hstx_cklp_wc, dsi->regs + DSI_HSTX_CKL_WC); in mtk_dsi_config_vdo_timing_per_frame_lp()
492 hs_vb_ps_wc = ps_wc - (dsi->phy_timing.lpx + dsi->phy_timing.da_hs_exit + in mtk_dsi_config_vdo_timing_per_frame_lp()
493 dsi->phy_timing.da_hs_prepare + dsi->phy_timing.da_hs_zero + 2) * dsi->lanes; in mtk_dsi_config_vdo_timing_per_frame_lp()
497 writel(horizontal_sync_active_byte, dsi->regs + DSI_HSA_WC); in mtk_dsi_config_vdo_timing_per_frame_lp()
498 writel(horizontal_backporch_byte, dsi->regs + DSI_HBP_WC); in mtk_dsi_config_vdo_timing_per_frame_lp()
499 writel(horizontal_frontporch_byte, dsi->regs + DSI_HFP_WC); in mtk_dsi_config_vdo_timing_per_frame_lp()
511 struct mtk_phy_timing *timing = &dsi->phy_timing; in mtk_dsi_config_vdo_timing_per_line_lp() local
512 struct videomode *vm = &dsi->vm; in mtk_dsi_config_vdo_timing_per_line_lp()
514 if (dsi->format == MIPI_DSI_FMT_RGB565) in mtk_dsi_config_vdo_timing_per_line_lp()
519 horizontal_sync_active_byte = (vm->hsync_len * dsi_tmp_buf_bpp - 10); in mtk_dsi_config_vdo_timing_per_line_lp()
521 if (dsi->mode_flags & MIPI_DSI_MODE_VIDEO_SYNC_PULSE) in mtk_dsi_config_vdo_timing_per_line_lp()
522 horizontal_backporch_byte = vm->hback_porch * dsi_tmp_buf_bpp - 10; in mtk_dsi_config_vdo_timing_per_line_lp()
524 horizontal_backporch_byte = (vm->hback_porch + vm->hsync_len) * in mtk_dsi_config_vdo_timing_per_line_lp()
525 dsi_tmp_buf_bpp - 10; in mtk_dsi_config_vdo_timing_per_line_lp()
527 data_phy_cycles = timing->lpx + timing->da_hs_prepare + in mtk_dsi_config_vdo_timing_per_line_lp()
528 timing->da_hs_zero + timing->da_hs_exit + 3; in mtk_dsi_config_vdo_timing_per_line_lp()
530 delta = dsi->mode_flags & MIPI_DSI_MODE_VIDEO_BURST ? 18 : 12; in mtk_dsi_config_vdo_timing_per_line_lp()
531 delta += dsi->mode_flags & MIPI_DSI_MODE_NO_EOT_PACKET ? 0 : 2; in mtk_dsi_config_vdo_timing_per_line_lp()
533 horizontal_frontporch_byte = vm->hfront_porch * dsi_tmp_buf_bpp; in mtk_dsi_config_vdo_timing_per_line_lp()
535 data_phy_cycles_byte = data_phy_cycles * dsi->lanes + delta; in mtk_dsi_config_vdo_timing_per_line_lp()
538 horizontal_frontporch_byte -= data_phy_cycles_byte * in mtk_dsi_config_vdo_timing_per_line_lp()
542 horizontal_backporch_byte -= data_phy_cycles_byte * in mtk_dsi_config_vdo_timing_per_line_lp()
546 DRM_WARN("HFP + HBP less than d-phy, FPS will under 60Hz\n"); in mtk_dsi_config_vdo_timing_per_line_lp()
549 if ((dsi->mode_flags & MIPI_DSI_HS_PKT_END_ALIGNED) && in mtk_dsi_config_vdo_timing_per_line_lp()
550 (dsi->lanes == 4)) { in mtk_dsi_config_vdo_timing_per_line_lp()
552 roundup(horizontal_sync_active_byte, dsi->lanes) - 2; in mtk_dsi_config_vdo_timing_per_line_lp()
554 roundup(horizontal_frontporch_byte, dsi->lanes) - 2; in mtk_dsi_config_vdo_timing_per_line_lp()
556 roundup(horizontal_backporch_byte, dsi->lanes) - 2; in mtk_dsi_config_vdo_timing_per_line_lp()
557 horizontal_backporch_byte -= in mtk_dsi_config_vdo_timing_per_line_lp()
558 (vm->hactive * dsi_tmp_buf_bpp + 2) % dsi->lanes; in mtk_dsi_config_vdo_timing_per_line_lp()
561 writel(horizontal_sync_active_byte, dsi->regs + DSI_HSA_WC); in mtk_dsi_config_vdo_timing_per_line_lp()
562 writel(horizontal_backporch_byte, dsi->regs + DSI_HBP_WC); in mtk_dsi_config_vdo_timing_per_line_lp()
563 writel(horizontal_frontporch_byte, dsi->regs + DSI_HFP_WC); in mtk_dsi_config_vdo_timing_per_line_lp()
568 struct videomode *vm = &dsi->vm; in mtk_dsi_config_vdo_timing()
570 writel(vm->vsync_len, dsi->regs + DSI_VSA_NL); in mtk_dsi_config_vdo_timing()
571 writel(vm->vback_porch, dsi->regs + DSI_VBP_NL); in mtk_dsi_config_vdo_timing()
572 writel(vm->vfront_porch, dsi->regs + DSI_VFP_NL); in mtk_dsi_config_vdo_timing()
573 writel(vm->vactive, dsi->regs + DSI_VACT_NL); in mtk_dsi_config_vdo_timing()
575 if (dsi->driver_data->has_size_ctl) in mtk_dsi_config_vdo_timing()
576 writel(FIELD_PREP(DSI_HEIGHT, vm->vactive) | in mtk_dsi_config_vdo_timing()
577 FIELD_PREP(DSI_WIDTH, vm->hactive), in mtk_dsi_config_vdo_timing()
578 dsi->regs + DSI_SIZE_CON); in mtk_dsi_config_vdo_timing()
580 if (dsi->driver_data->support_per_frame_lp) in mtk_dsi_config_vdo_timing()
590 writel(0, dsi->regs + DSI_START); in mtk_dsi_start()
591 writel(1, dsi->regs + DSI_START); in mtk_dsi_start()
596 writel(0, dsi->regs + DSI_START); in mtk_dsi_stop()
601 writel(CMD_MODE, dsi->regs + DSI_MODE_CTRL); in mtk_dsi_set_cmd_mode()
608 writel(inten, dsi->regs + DSI_INTEN); in mtk_dsi_set_interrupt_enable()
613 dsi->irq_data |= irq_bit; in mtk_dsi_irq_data_set()
618 dsi->irq_data &= ~irq_bit; in mtk_dsi_irq_data_clear()
624 s32 ret = 0; in mtk_dsi_wait_for_irq_done()
627 ret = wait_event_interruptible_timeout(dsi->irq_wait_queue, in mtk_dsi_wait_for_irq_done()
628 dsi->irq_data & irq_flag, in mtk_dsi_wait_for_irq_done()
630 if (ret == 0) { in mtk_dsi_wait_for_irq_done()
631 DRM_WARN("Wait DSI IRQ(0x%08x) Timeout\n", irq_flag); in mtk_dsi_wait_for_irq_done()
646 status = readl(dsi->regs + DSI_INTSTA) & flag; in mtk_dsi_irq()
651 tmp = readl(dsi->regs + DSI_INTSTA); in mtk_dsi_irq()
654 mtk_dsi_mask(dsi, DSI_INTSTA, status, 0); in mtk_dsi_irq()
656 wake_up_interruptible(&dsi->irq_wait_queue); in mtk_dsi_irq()
669 return -ETIME; in mtk_dsi_switch_to_cmd_mode()
671 return 0; in mtk_dsi_switch_to_cmd_mode()
677 struct device *dev = dsi->host.dev; in mtk_dsi_poweron()
681 if (++dsi->refcount != 1) in mtk_dsi_poweron()
682 return 0; in mtk_dsi_poweron()
684 ret = mipi_dsi_pixel_format_to_bpp(dsi->format); in mtk_dsi_poweron()
685 if (ret < 0) { in mtk_dsi_poweron()
686 dev_err(dev, "Unknown MIPI DSI format %d\n", dsi->format); in mtk_dsi_poweron()
691 dsi->data_rate = DIV_ROUND_UP_ULL(dsi->vm.pixelclock * bit_per_pixel, in mtk_dsi_poweron()
692 dsi->lanes); in mtk_dsi_poweron()
694 ret = clk_set_rate(dsi->hs_clk, dsi->data_rate); in mtk_dsi_poweron()
695 if (ret < 0) { in mtk_dsi_poweron()
700 phy_power_on(dsi->phy); in mtk_dsi_poweron()
702 ret = clk_prepare_enable(dsi->engine_clk); in mtk_dsi_poweron()
703 if (ret < 0) { in mtk_dsi_poweron()
708 ret = clk_prepare_enable(dsi->digital_clk); in mtk_dsi_poweron()
709 if (ret < 0) { in mtk_dsi_poweron()
716 if (dsi->driver_data->has_shadow_ctl) in mtk_dsi_poweron()
718 dsi->regs + dsi->driver_data->reg_shadow_dbg_off); in mtk_dsi_poweron()
728 return 0; in mtk_dsi_poweron()
730 clk_disable_unprepare(dsi->engine_clk); in mtk_dsi_poweron()
732 phy_power_off(dsi->phy); in mtk_dsi_poweron()
734 dsi->refcount--; in mtk_dsi_poweron()
740 if (WARN_ON(dsi->refcount == 0)) in mtk_dsi_poweroff()
743 if (--dsi->refcount != 0) in mtk_dsi_poweroff()
759 /* set the lane number as 0 to pull down mipi */ in mtk_dsi_poweroff()
760 writel(0, dsi->regs + DSI_TXRX_CTRL); in mtk_dsi_poweroff()
764 clk_disable_unprepare(dsi->engine_clk); in mtk_dsi_poweroff()
765 clk_disable_unprepare(dsi->digital_clk); in mtk_dsi_poweroff()
767 phy_power_off(dsi->phy); in mtk_dsi_poweroff()
769 dsi->lanes_ready = false; in mtk_dsi_poweroff()
774 if (!dsi->lanes_ready) { in mtk_dsi_lane_ready()
775 dsi->lanes_ready = true; in mtk_dsi_lane_ready()
781 mtk_dsi_clk_hs_mode(dsi, 0); in mtk_dsi_lane_ready()
789 if (dsi->enabled) in mtk_output_dsi_enable()
798 dsi->enabled = true; in mtk_output_dsi_enable()
803 if (!dsi->enabled) in mtk_output_dsi_disable()
806 dsi->enabled = false; in mtk_output_dsi_disable()
816 return drm_bridge_attach(encoder, dsi->next_bridge, in mtk_dsi_bridge_attach()
817 &dsi->bridge, flags); in mtk_dsi_bridge_attach()
826 drm_display_mode_to_videomode(adjusted, &dsi->vm); in mtk_dsi_bridge_mode_set()
842 if (dsi->refcount == 0) in mtk_dsi_bridge_atomic_enable()
855 if (ret < 0) in mtk_dsi_bridge_atomic_pre_enable()
875 bpp = mipi_dsi_pixel_format_to_bpp(dsi->format); in mtk_dsi_bridge_mode_valid()
876 if (bpp < 0) in mtk_dsi_bridge_mode_valid()
879 if (mode->clock * bpp / dsi->lanes > 1500000) in mtk_dsi_bridge_mode_valid()
916 ret = drm_simple_encoder_init(drm, &dsi->encoder, in mtk_dsi_encoder_init()
923 ret = mtk_find_possible_crtcs(drm, dsi->host.dev); in mtk_dsi_encoder_init()
924 if (ret < 0) in mtk_dsi_encoder_init()
926 dsi->encoder.possible_crtcs = ret; in mtk_dsi_encoder_init()
928 ret = drm_bridge_attach(&dsi->encoder, &dsi->bridge, NULL, in mtk_dsi_encoder_init()
933 dsi->connector = drm_bridge_connector_init(drm, &dsi->encoder); in mtk_dsi_encoder_init()
934 if (IS_ERR(dsi->connector)) { in mtk_dsi_encoder_init()
936 ret = PTR_ERR(dsi->connector); in mtk_dsi_encoder_init()
939 drm_connector_attach_encoder(dsi->connector, &dsi->encoder); in mtk_dsi_encoder_init()
941 return 0; in mtk_dsi_encoder_init()
944 drm_encoder_cleanup(&dsi->encoder); in mtk_dsi_encoder_init()
951 unsigned int encoder_index = drm_encoder_index(&dsi->encoder); in mtk_dsi_encoder_index()
975 drm_encoder_cleanup(&dsi->encoder); in mtk_dsi_unbind()
987 struct device *dev = host->dev; in mtk_dsi_host_attach()
990 dsi->lanes = device->lanes; in mtk_dsi_host_attach()
991 dsi->format = device->format; in mtk_dsi_host_attach()
992 dsi->mode_flags = device->mode_flags; in mtk_dsi_host_attach()
993 dsi->next_bridge = devm_drm_of_get_bridge(dev, dev->of_node, 1, 0); in mtk_dsi_host_attach()
994 if (IS_ERR(dsi->next_bridge)) { in mtk_dsi_host_attach()
995 ret = PTR_ERR(dsi->next_bridge); in mtk_dsi_host_attach()
996 if (ret == -EPROBE_DEFER) in mtk_dsi_host_attach()
1000 dsi->next_bridge = devm_drm_of_get_bridge(dev, dev->of_node, 0, 0); in mtk_dsi_host_attach()
1001 if (IS_ERR(dsi->next_bridge)) in mtk_dsi_host_attach()
1002 return PTR_ERR(dsi->next_bridge); in mtk_dsi_host_attach()
1006 * set flag to request the DSI host bridge be pre-enabled before device bridge in mtk_dsi_host_attach()
1007 * in the chain, so the DSI host is ready when the device bridge is pre-enabled in mtk_dsi_host_attach()
1009 dsi->next_bridge->pre_enable_prev_first = true; in mtk_dsi_host_attach()
1011 drm_bridge_add(&dsi->bridge); in mtk_dsi_host_attach()
1013 ret = component_add(host->dev, &mtk_dsi_component_ops); in mtk_dsi_host_attach()
1016 drm_bridge_remove(&dsi->bridge); in mtk_dsi_host_attach()
1020 return 0; in mtk_dsi_host_attach()
1028 component_del(host->dev, &mtk_dsi_component_ops); in mtk_dsi_host_detach()
1029 drm_bridge_remove(&dsi->bridge); in mtk_dsi_host_detach()
1030 return 0; in mtk_dsi_host_detach()
1038 ret = readl_poll_timeout(dsi->regs + DSI_INTSTA, val, !(val & DSI_BUSY), in mtk_dsi_wait_for_idle()
1061 DRM_INFO("type is 0x02, try again\n"); in mtk_dsi_recv_cnt()
1064 DRM_INFO("type(0x%x) not recognized\n", type); in mtk_dsi_recv_cnt()
1068 return 0; in mtk_dsi_recv_cnt()
1073 const char *tx_buf = msg->tx_buf; in mtk_dsi_cmdq()
1074 u8 config, cmdq_size, cmdq_off, type = msg->type; in mtk_dsi_cmdq()
1076 u32 reg_cmdq_off = dsi->driver_data->reg_cmdq_off; in mtk_dsi_cmdq()
1081 config = (msg->tx_len > 2) ? LONG_PACKET : SHORT_PACKET; in mtk_dsi_cmdq()
1083 if (msg->tx_len > 2) { in mtk_dsi_cmdq()
1084 cmdq_size = 1 + (msg->tx_len + 3) / 4; in mtk_dsi_cmdq()
1087 reg_val = (msg->tx_len << 16) | (type << 8) | config; in mtk_dsi_cmdq()
1095 for (i = 0; i < msg->tx_len; i++) in mtk_dsi_cmdq()
1096 mtk_dsi_mask(dsi, (reg_cmdq_off + cmdq_off + i) & (~0x3U), in mtk_dsi_cmdq()
1097 (0xffUL << (((i + cmdq_off) & 3U) * 8U)), in mtk_dsi_cmdq()
1102 if (dsi->driver_data->cmdq_long_packet_ctl) { in mtk_dsi_cmdq()
1117 return -ETIME; in mtk_dsi_host_send_cmd()
1119 return 0; in mtk_dsi_host_send_cmd()
1133 dsi_mode = readl(dsi->regs + DSI_MODE_CTRL); in mtk_dsi_host_transfer()
1141 if (MTK_DSI_HOST_IS_READ(msg->type)) in mtk_dsi_host_transfer()
1150 if (!MTK_DSI_HOST_IS_READ(msg->type)) { in mtk_dsi_host_transfer()
1151 recv_cnt = 0; in mtk_dsi_host_transfer()
1155 if (!msg->rx_buf) { in mtk_dsi_host_transfer()
1157 ret = -EINVAL; in mtk_dsi_host_transfer()
1161 for (i = 0; i < 16; i++) in mtk_dsi_host_transfer()
1162 *(read_data + i) = readb(dsi->regs + DSI_RX_DATA0 + i); in mtk_dsi_host_transfer()
1164 recv_cnt = mtk_dsi_recv_cnt(read_data[0], read_data); in mtk_dsi_host_transfer()
1174 if (recv_cnt > msg->rx_len) in mtk_dsi_host_transfer()
1175 recv_cnt = msg->rx_len; in mtk_dsi_host_transfer()
1178 memcpy(msg->rx_buf, src_addr, recv_cnt); in mtk_dsi_host_transfer()
1180 DRM_INFO("dsi get %zd byte data from the panel address(0x%x)\n", in mtk_dsi_host_transfer()
1181 recv_cnt, *((u8 *)(msg->tx_buf))); in mtk_dsi_host_transfer()
1189 return ret < 0 ? ret : recv_cnt; in mtk_dsi_host_transfer()
1201 struct device *dev = &pdev->dev; in mtk_dsi_probe()
1210 dsi->driver_data = of_device_get_match_data(dev); in mtk_dsi_probe()
1212 dsi->engine_clk = devm_clk_get(dev, "engine"); in mtk_dsi_probe()
1213 if (IS_ERR(dsi->engine_clk)) in mtk_dsi_probe()
1214 return dev_err_probe(dev, PTR_ERR(dsi->engine_clk), in mtk_dsi_probe()
1218 dsi->digital_clk = devm_clk_get(dev, "digital"); in mtk_dsi_probe()
1219 if (IS_ERR(dsi->digital_clk)) in mtk_dsi_probe()
1220 return dev_err_probe(dev, PTR_ERR(dsi->digital_clk), in mtk_dsi_probe()
1223 dsi->hs_clk = devm_clk_get(dev, "hs"); in mtk_dsi_probe()
1224 if (IS_ERR(dsi->hs_clk)) in mtk_dsi_probe()
1225 return dev_err_probe(dev, PTR_ERR(dsi->hs_clk), "Failed to get hs clock\n"); in mtk_dsi_probe()
1227 dsi->regs = devm_platform_ioremap_resource(pdev, 0); in mtk_dsi_probe()
1228 if (IS_ERR(dsi->regs)) in mtk_dsi_probe()
1229 return dev_err_probe(dev, PTR_ERR(dsi->regs), "Failed to ioremap memory\n"); in mtk_dsi_probe()
1231 dsi->phy = devm_phy_get(dev, "dphy"); in mtk_dsi_probe()
1232 if (IS_ERR(dsi->phy)) in mtk_dsi_probe()
1233 return dev_err_probe(dev, PTR_ERR(dsi->phy), "Failed to get MIPI-DPHY\n"); in mtk_dsi_probe()
1235 irq_num = platform_get_irq(pdev, 0); in mtk_dsi_probe()
1236 if (irq_num < 0) in mtk_dsi_probe()
1239 dsi->host.ops = &mtk_dsi_ops; in mtk_dsi_probe()
1240 dsi->host.dev = dev; in mtk_dsi_probe()
1241 ret = mipi_dsi_host_register(&dsi->host); in mtk_dsi_probe()
1242 if (ret < 0) in mtk_dsi_probe()
1245 ret = devm_request_irq(&pdev->dev, irq_num, mtk_dsi_irq, in mtk_dsi_probe()
1246 IRQF_TRIGGER_NONE, dev_name(&pdev->dev), dsi); in mtk_dsi_probe()
1248 mipi_dsi_host_unregister(&dsi->host); in mtk_dsi_probe()
1249 return dev_err_probe(&pdev->dev, ret, "Failed to request DSI irq\n"); in mtk_dsi_probe()
1252 init_waitqueue_head(&dsi->irq_wait_queue); in mtk_dsi_probe()
1256 dsi->bridge.of_node = dev->of_node; in mtk_dsi_probe()
1257 dsi->bridge.type = DRM_MODE_CONNECTOR_DSI; in mtk_dsi_probe()
1259 return 0; in mtk_dsi_probe()
1267 mipi_dsi_host_unregister(&dsi->host); in mtk_dsi_remove()
1271 .reg_cmdq_off = 0x200,
1272 .reg_vm_cmd_off = 0x130,
1273 .reg_shadow_dbg_off = 0x190
1277 .reg_cmdq_off = 0x180,
1278 .reg_vm_cmd_off = 0x130,
1279 .reg_shadow_dbg_off = 0x190
1283 .reg_cmdq_off = 0x200,
1284 .reg_vm_cmd_off = 0x130,
1285 .reg_shadow_dbg_off = 0x190,
1291 .reg_cmdq_off = 0xd00,
1292 .reg_vm_cmd_off = 0x200,
1293 .reg_shadow_dbg_off = 0xc00,
1299 .reg_cmdq_off = 0xd00,
1300 .reg_vm_cmd_off = 0x200,
1301 .reg_shadow_dbg_off = 0xc00,
1309 { .compatible = "mediatek,mt2701-dsi", .data = &mt2701_dsi_driver_data },
1310 { .compatible = "mediatek,mt8173-dsi", .data = &mt8173_dsi_driver_data },
1311 { .compatible = "mediatek,mt8183-dsi", .data = &mt8183_dsi_driver_data },
1312 { .compatible = "mediatek,mt8186-dsi", .data = &mt8186_dsi_driver_data },
1313 { .compatible = "mediatek,mt8188-dsi", .data = &mt8188_dsi_driver_data },
1322 .name = "mtk-dsi",