Lines Matching full:dsi
3 * R-Car MIPI DSI Encoder
45 struct clk *dsi; member
127 static void rcar_mipi_dsi_write(struct rcar_mipi_dsi *dsi, u32 reg, u32 data) in rcar_mipi_dsi_write() argument
129 iowrite32(data, dsi->mmio + reg); in rcar_mipi_dsi_write()
132 static u32 rcar_mipi_dsi_read(struct rcar_mipi_dsi *dsi, u32 reg) in rcar_mipi_dsi_read() argument
134 return ioread32(dsi->mmio + reg); in rcar_mipi_dsi_read()
137 static void rcar_mipi_dsi_clr(struct rcar_mipi_dsi *dsi, u32 reg, u32 clr) in rcar_mipi_dsi_clr() argument
139 rcar_mipi_dsi_write(dsi, reg, rcar_mipi_dsi_read(dsi, reg) & ~clr); in rcar_mipi_dsi_clr()
142 static void rcar_mipi_dsi_set(struct rcar_mipi_dsi *dsi, u32 reg, u32 set) in rcar_mipi_dsi_set() argument
144 rcar_mipi_dsi_write(dsi, reg, rcar_mipi_dsi_read(dsi, reg) | set); in rcar_mipi_dsi_set()
147 static int rcar_mipi_dsi_phtw_test(struct rcar_mipi_dsi *dsi, u32 phtw) in rcar_mipi_dsi_phtw_test() argument
152 rcar_mipi_dsi_write(dsi, PHTW, phtw); in rcar_mipi_dsi_phtw_test()
156 2000, 10000, false, dsi, PHTW); in rcar_mipi_dsi_phtw_test()
158 dev_err(dsi->dev, "PHY test interface write timeout (0x%08x)\n", in rcar_mipi_dsi_phtw_test()
180 static void rcar_mipi_dsi_parameters_calc(struct rcar_mipi_dsi *dsi, in rcar_mipi_dsi_parameters_calc() argument
199 fout_target = target * mipi_dsi_pixel_format_to_bpp(dsi->format) in rcar_mipi_dsi_parameters_calc()
200 / (2 * dsi->lanes); in rcar_mipi_dsi_parameters_calc()
258 dev_dbg(dsi->dev, in rcar_mipi_dsi_parameters_calc()
262 dev_dbg(dsi->dev, in rcar_mipi_dsi_parameters_calc()
268 static void rcar_mipi_dsi_set_display_timing(struct rcar_mipi_dsi *dsi, in rcar_mipi_dsi_set_display_timing() argument
279 if (mipi_dsi_pixel_format_to_bpp(dsi->format) == 24) in rcar_mipi_dsi_set_display_timing()
280 rcar_mipi_dsi_write(dsi, TXVMPSPHSETR, TXVMPSPHSETR_DT_RGB24); in rcar_mipi_dsi_set_display_timing()
281 else if (mipi_dsi_pixel_format_to_bpp(dsi->format) == 18) in rcar_mipi_dsi_set_display_timing()
282 rcar_mipi_dsi_write(dsi, TXVMPSPHSETR, TXVMPSPHSETR_DT_RGB18); in rcar_mipi_dsi_set_display_timing()
283 else if (mipi_dsi_pixel_format_to_bpp(dsi->format) == 16) in rcar_mipi_dsi_set_display_timing()
284 rcar_mipi_dsi_write(dsi, TXVMPSPHSETR, TXVMPSPHSETR_DT_RGB16); in rcar_mipi_dsi_set_display_timing()
286 dev_warn(dsi->dev, "unsupported format"); in rcar_mipi_dsi_set_display_timing()
294 rcar_mipi_dsi_write(dsi, TXVMSETR, setr); in rcar_mipi_dsi_set_display_timing()
315 rcar_mipi_dsi_write(dsi, TXVMVPRMSET0R, vprmset0r); in rcar_mipi_dsi_set_display_timing()
316 rcar_mipi_dsi_write(dsi, TXVMVPRMSET1R, vprmset1r); in rcar_mipi_dsi_set_display_timing()
317 rcar_mipi_dsi_write(dsi, TXVMVPRMSET2R, vprmset2r); in rcar_mipi_dsi_set_display_timing()
318 rcar_mipi_dsi_write(dsi, TXVMVPRMSET3R, vprmset3r); in rcar_mipi_dsi_set_display_timing()
319 rcar_mipi_dsi_write(dsi, TXVMVPRMSET4R, vprmset4r); in rcar_mipi_dsi_set_display_timing()
322 static int rcar_mipi_dsi_startup(struct rcar_mipi_dsi *dsi, in rcar_mipi_dsi_startup() argument
335 dsi_format = mipi_dsi_pixel_format_to_bpp(dsi->format); in rcar_mipi_dsi_startup()
337 dev_warn(dsi->dev, "invalid format"); in rcar_mipi_dsi_startup()
342 rcar_mipi_dsi_parameters_calc(dsi, dsi->clocks.pll, in rcar_mipi_dsi_startup()
346 rcar_mipi_dsi_set(dsi, LPCLKSET, LPCLKSET_CKEN); in rcar_mipi_dsi_startup()
349 rcar_mipi_dsi_set(dsi, CFGCLKSET, CFGCLKSET_CKEN); in rcar_mipi_dsi_startup()
351 rcar_mipi_dsi_clr(dsi, PHYSETUP, PHYSETUP_RSTZ); in rcar_mipi_dsi_startup()
352 rcar_mipi_dsi_clr(dsi, PHYSETUP, PHYSETUP_SHUTDOWNZ); in rcar_mipi_dsi_startup()
354 rcar_mipi_dsi_set(dsi, PHTC, PHTC_TESTCLR); in rcar_mipi_dsi_startup()
355 rcar_mipi_dsi_clr(dsi, PHTC, PHTC_TESTCLR); in rcar_mipi_dsi_startup()
358 phy_setup = rcar_mipi_dsi_read(dsi, PHYSETUP); in rcar_mipi_dsi_startup()
361 rcar_mipi_dsi_write(dsi, PHYSETUP, phy_setup); in rcar_mipi_dsi_startup()
364 ret = rcar_mipi_dsi_phtw_test(dsi, phtw[i]); in rcar_mipi_dsi_startup()
370 rcar_mipi_dsi_clr(dsi, CLOCKSET1, CLOCKSET1_SHADOW_CLEAR); in rcar_mipi_dsi_startup()
371 rcar_mipi_dsi_set(dsi, CLOCKSET1, CLOCKSET1_SHADOW_CLEAR); in rcar_mipi_dsi_startup()
372 rcar_mipi_dsi_clr(dsi, CLOCKSET1, CLOCKSET1_SHADOW_CLEAR); in rcar_mipi_dsi_startup()
380 rcar_mipi_dsi_write(dsi, CLOCKSET2, clockset2); in rcar_mipi_dsi_startup()
381 rcar_mipi_dsi_write(dsi, CLOCKSET3, clockset3); in rcar_mipi_dsi_startup()
383 rcar_mipi_dsi_clr(dsi, CLOCKSET1, CLOCKSET1_UPDATEPLL); in rcar_mipi_dsi_startup()
384 rcar_mipi_dsi_set(dsi, CLOCKSET1, CLOCKSET1_UPDATEPLL); in rcar_mipi_dsi_startup()
386 rcar_mipi_dsi_clr(dsi, CLOCKSET1, CLOCKSET1_UPDATEPLL); in rcar_mipi_dsi_startup()
389 rcar_mipi_dsi_write(dsi, PPISETR, ppisetr); in rcar_mipi_dsi_startup()
391 rcar_mipi_dsi_set(dsi, PHYSETUP, PHYSETUP_SHUTDOWNZ); in rcar_mipi_dsi_startup()
392 rcar_mipi_dsi_set(dsi, PHYSETUP, PHYSETUP_RSTZ); in rcar_mipi_dsi_startup()
397 if ((rcar_mipi_dsi_read(dsi, PPICLSR) & PPICLSR_STPST) && in rcar_mipi_dsi_startup()
398 (rcar_mipi_dsi_read(dsi, PPIDLSR) & PPIDLSR_STPST) && in rcar_mipi_dsi_startup()
399 (rcar_mipi_dsi_read(dsi, CLOCKSET1) & CLOCKSET1_LOCK)) in rcar_mipi_dsi_startup()
406 dev_err(dsi->dev, "failed to enable PPI clock\n"); in rcar_mipi_dsi_startup()
411 ret = rcar_mipi_dsi_phtw_test(dsi, phtw2[i]); in rcar_mipi_dsi_startup()
418 rcar_mipi_dsi_write(dsi, VCLKSET, vclkset); in rcar_mipi_dsi_startup()
427 dev_warn(dsi->dev, "unsupported format"); in rcar_mipi_dsi_startup()
431 | VCLKSET_LANE(dsi->lanes - 1); in rcar_mipi_dsi_startup()
433 rcar_mipi_dsi_write(dsi, VCLKSET, vclkset); in rcar_mipi_dsi_startup()
436 rcar_mipi_dsi_set(dsi, VCLKEN, VCLKEN_CKEN); in rcar_mipi_dsi_startup()
438 dev_dbg(dsi->dev, "DSI device is started\n"); in rcar_mipi_dsi_startup()
443 static void rcar_mipi_dsi_shutdown(struct rcar_mipi_dsi *dsi) in rcar_mipi_dsi_shutdown() argument
446 rcar_mipi_dsi_write(dsi, VCLKSET, 0); in rcar_mipi_dsi_shutdown()
449 rcar_mipi_dsi_write(dsi, VCLKSET, 0); in rcar_mipi_dsi_shutdown()
451 rcar_mipi_dsi_clr(dsi, PHYSETUP, PHYSETUP_RSTZ); in rcar_mipi_dsi_shutdown()
452 rcar_mipi_dsi_clr(dsi, PHYSETUP, PHYSETUP_SHUTDOWNZ); in rcar_mipi_dsi_shutdown()
455 rcar_mipi_dsi_clr(dsi, CFGCLKSET, CFGCLKSET_CKEN); in rcar_mipi_dsi_shutdown()
458 rcar_mipi_dsi_clr(dsi, LPCLKSET, LPCLKSET_CKEN); in rcar_mipi_dsi_shutdown()
460 dev_dbg(dsi->dev, "DSI device is shutdown\n"); in rcar_mipi_dsi_shutdown()
463 static int rcar_mipi_dsi_clk_enable(struct rcar_mipi_dsi *dsi) in rcar_mipi_dsi_clk_enable() argument
467 reset_control_deassert(dsi->rstc); in rcar_mipi_dsi_clk_enable()
469 ret = clk_prepare_enable(dsi->clocks.mod); in rcar_mipi_dsi_clk_enable()
473 ret = clk_prepare_enable(dsi->clocks.dsi); in rcar_mipi_dsi_clk_enable()
480 clk_disable_unprepare(dsi->clocks.mod); in rcar_mipi_dsi_clk_enable()
482 reset_control_assert(dsi->rstc); in rcar_mipi_dsi_clk_enable()
486 static void rcar_mipi_dsi_clk_disable(struct rcar_mipi_dsi *dsi) in rcar_mipi_dsi_clk_disable() argument
488 clk_disable_unprepare(dsi->clocks.dsi); in rcar_mipi_dsi_clk_disable()
489 clk_disable_unprepare(dsi->clocks.mod); in rcar_mipi_dsi_clk_disable()
491 reset_control_assert(dsi->rstc); in rcar_mipi_dsi_clk_disable()
494 static int rcar_mipi_dsi_start_hs_clock(struct rcar_mipi_dsi *dsi) in rcar_mipi_dsi_start_hs_clock() argument
504 rcar_mipi_dsi_set(dsi, PPICLCR, PPICLCR_TXREQHS); in rcar_mipi_dsi_start_hs_clock()
508 2000, 10000, false, dsi, PPICLSR); in rcar_mipi_dsi_start_hs_clock()
510 dev_err(dsi->dev, "failed to enable HS clock\n"); in rcar_mipi_dsi_start_hs_clock()
514 rcar_mipi_dsi_set(dsi, PPICLSCR, PPICLSCR_TOHS); in rcar_mipi_dsi_start_hs_clock()
519 static int rcar_mipi_dsi_start_video(struct rcar_mipi_dsi *dsi) in rcar_mipi_dsi_start_video() argument
527 2000, 10000, false, dsi, LINKSR); in rcar_mipi_dsi_start_video()
529 dev_err(dsi->dev, "Link failed to become ready\n"); in rcar_mipi_dsi_start_video()
534 rcar_mipi_dsi_clr(dsi, TXVMCR, TXVMCR_VFCLR); in rcar_mipi_dsi_start_video()
538 2000, 10000, false, dsi, TXVMSR); in rcar_mipi_dsi_start_video()
540 dev_err(dsi->dev, "Failed to de-assert video FIFO clear\n"); in rcar_mipi_dsi_start_video()
545 rcar_mipi_dsi_set(dsi, TXVMCR, TXVMCR_EN_VIDEO); in rcar_mipi_dsi_start_video()
549 2000, 10000, false, dsi, TXVMSR); in rcar_mipi_dsi_start_video()
551 dev_err(dsi->dev, "Failed to enable video transmission\n"); in rcar_mipi_dsi_start_video()
558 static void rcar_mipi_dsi_stop_video(struct rcar_mipi_dsi *dsi) in rcar_mipi_dsi_stop_video() argument
564 rcar_mipi_dsi_clr(dsi, TXVMCR, TXVMCR_EN_VIDEO); in rcar_mipi_dsi_stop_video()
568 2000, 100000, false, dsi, TXVMSR); in rcar_mipi_dsi_stop_video()
570 dev_err(dsi->dev, "Failed to disable video transmission\n"); in rcar_mipi_dsi_stop_video()
575 rcar_mipi_dsi_set(dsi, TXVMCR, TXVMCR_VFCLR); in rcar_mipi_dsi_stop_video()
579 2000, 100000, false, dsi, TXVMSR); in rcar_mipi_dsi_stop_video()
581 dev_err(dsi->dev, "Failed to assert video FIFO clear\n"); in rcar_mipi_dsi_stop_video()
593 struct rcar_mipi_dsi *dsi = bridge_to_rcar_mipi_dsi(bridge); in rcar_mipi_dsi_attach() local
595 return drm_bridge_attach(bridge->encoder, dsi->next_bridge, bridge, in rcar_mipi_dsi_attach()
602 struct rcar_mipi_dsi *dsi = bridge_to_rcar_mipi_dsi(bridge); in rcar_mipi_dsi_atomic_enable() local
604 rcar_mipi_dsi_start_video(dsi); in rcar_mipi_dsi_atomic_enable()
610 struct rcar_mipi_dsi *dsi = bridge_to_rcar_mipi_dsi(bridge); in rcar_mipi_dsi_atomic_disable() local
612 rcar_mipi_dsi_stop_video(dsi); in rcar_mipi_dsi_atomic_disable()
618 struct rcar_mipi_dsi *dsi = bridge_to_rcar_mipi_dsi(bridge); in rcar_mipi_dsi_pclk_enable() local
629 ret = rcar_mipi_dsi_clk_enable(dsi); in rcar_mipi_dsi_pclk_enable()
631 dev_err(dsi->dev, "failed to enable DSI clocks\n"); in rcar_mipi_dsi_pclk_enable()
635 ret = rcar_mipi_dsi_startup(dsi, mode); in rcar_mipi_dsi_pclk_enable()
639 rcar_mipi_dsi_set_display_timing(dsi, mode); in rcar_mipi_dsi_pclk_enable()
641 ret = rcar_mipi_dsi_start_hs_clock(dsi); in rcar_mipi_dsi_pclk_enable()
648 rcar_mipi_dsi_shutdown(dsi); in rcar_mipi_dsi_pclk_enable()
650 rcar_mipi_dsi_clk_disable(dsi); in rcar_mipi_dsi_pclk_enable()
656 struct rcar_mipi_dsi *dsi = bridge_to_rcar_mipi_dsi(bridge); in rcar_mipi_dsi_pclk_disable() local
658 rcar_mipi_dsi_shutdown(dsi); in rcar_mipi_dsi_pclk_disable()
659 rcar_mipi_dsi_clk_disable(dsi); in rcar_mipi_dsi_pclk_disable()
691 struct rcar_mipi_dsi *dsi = host_to_rcar_mipi_dsi(host); in rcar_mipi_dsi_host_attach() local
694 if (device->lanes > dsi->num_data_lanes) in rcar_mipi_dsi_host_attach()
697 dsi->lanes = device->lanes; in rcar_mipi_dsi_host_attach()
698 dsi->format = device->format; in rcar_mipi_dsi_host_attach()
700 dsi->next_bridge = devm_drm_of_get_bridge(dsi->dev, dsi->dev->of_node, in rcar_mipi_dsi_host_attach()
702 if (IS_ERR(dsi->next_bridge)) { in rcar_mipi_dsi_host_attach()
703 ret = PTR_ERR(dsi->next_bridge); in rcar_mipi_dsi_host_attach()
704 dev_err(dsi->dev, "failed to get next bridge: %d\n", ret); in rcar_mipi_dsi_host_attach()
709 dsi->bridge.funcs = &rcar_mipi_dsi_bridge_ops; in rcar_mipi_dsi_host_attach()
710 dsi->bridge.of_node = dsi->dev->of_node; in rcar_mipi_dsi_host_attach()
711 drm_bridge_add(&dsi->bridge); in rcar_mipi_dsi_host_attach()
719 struct rcar_mipi_dsi *dsi = host_to_rcar_mipi_dsi(host); in rcar_mipi_dsi_host_detach() local
721 drm_bridge_remove(&dsi->bridge); in rcar_mipi_dsi_host_detach()
735 static int rcar_mipi_dsi_parse_dt(struct rcar_mipi_dsi *dsi) in rcar_mipi_dsi_parse_dt() argument
739 ret = drm_of_get_data_lanes_count_ep(dsi->dev->of_node, 1, 0, 1, 4); in rcar_mipi_dsi_parse_dt()
741 dev_err(dsi->dev, "missing or invalid data-lanes property\n"); in rcar_mipi_dsi_parse_dt()
745 dsi->num_data_lanes = ret; in rcar_mipi_dsi_parse_dt()
749 static struct clk *rcar_mipi_dsi_get_clock(struct rcar_mipi_dsi *dsi, in rcar_mipi_dsi_get_clock() argument
755 clk = devm_clk_get(dsi->dev, name); in rcar_mipi_dsi_get_clock()
762 dev_err_probe(dsi->dev, PTR_ERR(clk), "failed to get %s clock\n", in rcar_mipi_dsi_get_clock()
768 static int rcar_mipi_dsi_get_clocks(struct rcar_mipi_dsi *dsi) in rcar_mipi_dsi_get_clocks() argument
770 dsi->clocks.mod = rcar_mipi_dsi_get_clock(dsi, NULL, false); in rcar_mipi_dsi_get_clocks()
771 if (IS_ERR(dsi->clocks.mod)) in rcar_mipi_dsi_get_clocks()
772 return PTR_ERR(dsi->clocks.mod); in rcar_mipi_dsi_get_clocks()
774 dsi->clocks.pll = rcar_mipi_dsi_get_clock(dsi, "pll", true); in rcar_mipi_dsi_get_clocks()
775 if (IS_ERR(dsi->clocks.pll)) in rcar_mipi_dsi_get_clocks()
776 return PTR_ERR(dsi->clocks.pll); in rcar_mipi_dsi_get_clocks()
778 dsi->clocks.dsi = rcar_mipi_dsi_get_clock(dsi, "dsi", true); in rcar_mipi_dsi_get_clocks()
779 if (IS_ERR(dsi->clocks.dsi)) in rcar_mipi_dsi_get_clocks()
780 return PTR_ERR(dsi->clocks.dsi); in rcar_mipi_dsi_get_clocks()
782 if (!dsi->clocks.pll && !dsi->clocks.dsi) { in rcar_mipi_dsi_get_clocks()
783 dev_err(dsi->dev, "no input clock (pll, dsi)\n"); in rcar_mipi_dsi_get_clocks()
792 struct rcar_mipi_dsi *dsi; in rcar_mipi_dsi_probe() local
796 dsi = devm_kzalloc(&pdev->dev, sizeof(*dsi), GFP_KERNEL); in rcar_mipi_dsi_probe()
797 if (dsi == NULL) in rcar_mipi_dsi_probe()
800 platform_set_drvdata(pdev, dsi); in rcar_mipi_dsi_probe()
802 dsi->dev = &pdev->dev; in rcar_mipi_dsi_probe()
803 dsi->info = of_device_get_match_data(&pdev->dev); in rcar_mipi_dsi_probe()
805 ret = rcar_mipi_dsi_parse_dt(dsi); in rcar_mipi_dsi_probe()
811 dsi->mmio = devm_ioremap_resource(dsi->dev, mem); in rcar_mipi_dsi_probe()
812 if (IS_ERR(dsi->mmio)) in rcar_mipi_dsi_probe()
813 return PTR_ERR(dsi->mmio); in rcar_mipi_dsi_probe()
815 ret = rcar_mipi_dsi_get_clocks(dsi); in rcar_mipi_dsi_probe()
819 dsi->rstc = devm_reset_control_get(dsi->dev, NULL); in rcar_mipi_dsi_probe()
820 if (IS_ERR(dsi->rstc)) { in rcar_mipi_dsi_probe()
821 dev_err(dsi->dev, "failed to get cpg reset\n"); in rcar_mipi_dsi_probe()
822 return PTR_ERR(dsi->rstc); in rcar_mipi_dsi_probe()
825 /* Initialize the DSI host. */ in rcar_mipi_dsi_probe()
826 dsi->host.dev = dsi->dev; in rcar_mipi_dsi_probe()
827 dsi->host.ops = &rcar_mipi_dsi_host_ops; in rcar_mipi_dsi_probe()
828 ret = mipi_dsi_host_register(&dsi->host); in rcar_mipi_dsi_probe()
837 struct rcar_mipi_dsi *dsi = platform_get_drvdata(pdev); in rcar_mipi_dsi_remove() local
839 mipi_dsi_host_unregister(&dsi->host); in rcar_mipi_dsi_remove()
845 { .compatible = "renesas,r8a779a0-dsi-csi2-tx" },
855 .name = "rcar-mipi-dsi",
862 MODULE_DESCRIPTION("Renesas R-Car MIPI DSI Encoder Driver");