Message ID | 20190124195900.22620-12-jagan@amarulasolutions.com (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
Series | drm/sun4i: Allwinner A64 MIPI-DSI support | expand |
On Fri, Jan 25, 2019 at 01:28:49AM +0530, Jagan Teki wrote: > Minimum PLL used for MIPI is 500MHz, as per manual, but > lowering the min rate by 300MHz can result proper working > nkms divider with the help of desired dclock rate from > panel driver. > > Signed-off-by: Jagan Teki <jagan@amarulasolutions.com> > Acked-by: Stephen Boyd <sboyd@kernel.org> Going 200MHz below the minimum doesn't seem really reasonable. What is the issue that you are trying to fix here? It looks like it's picking bad dividers, but if that's the case, this isn't the proper fix. Maxime
On Sat, Jan 26, 2019 at 2:54 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Fri, Jan 25, 2019 at 01:28:49AM +0530, Jagan Teki wrote: > > Minimum PLL used for MIPI is 500MHz, as per manual, but > > lowering the min rate by 300MHz can result proper working > > nkms divider with the help of desired dclock rate from > > panel driver. > > > > Signed-off-by: Jagan Teki <jagan@amarulasolutions.com> > > Acked-by: Stephen Boyd <sboyd@kernel.org> > > Going 200MHz below the minimum doesn't seem really reasonable. What > is the issue that you are trying to fix here? > > It looks like it's picking bad dividers, but if that's the case, this > isn't the proper fix. As I stated in earlier patches, the whole idea is pick the desired dclk divider based dclk rate. So the dotclock, sun4i_dclk_round_rate is unable to get the proper dclk divider at the end, so it eventually picking up wrong divider value and fired vblank timeout. So, we come-up with optimal and working min_rate 300MHz in pll-mipi to get the desired clock something like below. [ 2.415773] [drm] No driver support for vblank timestamp query. [ 2.424116] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 [ 2.424172] ideal = 220000000, rounded = 0 [ 2.424176] ideal = 275000000, rounded = 0 [ 2.424194] ccu_nkm_round_rate: rate = 330000000 [ 2.424197] ideal = 330000000, rounded = 330000000 [ 2.424201] sun4i_dclk_round_rate: div = 6 rate = 55000000 [ 2.424205] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 [ 2.424209] ideal = 220000000, rounded = 0 [ 2.424213] ideal = 275000000, rounded = 0 [ 2.424230] ccu_nkm_round_rate: rate = 330000000 [ 2.424233] ideal = 330000000, rounded = 330000000 [ 2.424236] sun4i_dclk_round_rate: div = 6 rate = 55000000 [ 2.424253] ccu_nkm_round_rate: rate = 330000000 [ 2.424270] ccu_nkm_round_rate: rate = 330000000 [ 2.424278] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 [ 2.424281] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 [ 2.424306] ccu_nkm_set_rate: rate = 330000000, parent_rate = 297000000 [ 2.424309] ccu_nkm_set_rate: _nkm.n = 5 [ 2.424311] ccu_nkm_set_rate: _nkm.k = 2 [ 2.424313] ccu_nkm_set_rate: _nkm.m = 9 [ 2.424661] sun4i_dclk_set_rate div 6 [ 2.424668] sun4i_dclk_recalc_rate: val = 6, rate = 55000000 But look like this wouldn't valid for all other dclock rates, say BPI panel has 30MHz clock that would failed with this logic. On the other side Allwinner BSP calculating dclk divider based on the SoC's. for A33 [1] it is fixed dclk divider of 4 and for A64 is is calculated based on the bpp/lanes. Since the above min_rate is not desired for possible panels clock, I think we can rely on BSP to make a move here. I'm planning to do these changes in next version. Let me know if you have any comments here? [1] https://patchwork.kernel.org/patch/10777519/
On Mon, Jan 28, 2019 at 03:06:10PM +0530, Jagan Teki wrote: > On Sat, Jan 26, 2019 at 2:54 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > On Fri, Jan 25, 2019 at 01:28:49AM +0530, Jagan Teki wrote: > > > Minimum PLL used for MIPI is 500MHz, as per manual, but > > > lowering the min rate by 300MHz can result proper working > > > nkms divider with the help of desired dclock rate from > > > panel driver. > > > > > > Signed-off-by: Jagan Teki <jagan@amarulasolutions.com> > > > Acked-by: Stephen Boyd <sboyd@kernel.org> > > > > Going 200MHz below the minimum doesn't seem really reasonable. What > > is the issue that you are trying to fix here? > > > > It looks like it's picking bad dividers, but if that's the case, this > > isn't the proper fix. > > As I stated in earlier patches, the whole idea is pick the desired > dclk divider based dclk rate. So the dotclock, sun4i_dclk_round_rate > is unable to get the proper dclk divider at the end, so it eventually > picking up wrong divider value and fired vblank timeout. > > So, we come-up with optimal and working min_rate 300MHz in pll-mipi to > get the desired clock something like below. > [ 2.415773] [drm] No driver support for vblank timestamp query. > [ 2.424116] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > [ 2.424172] ideal = 220000000, rounded = 0 > [ 2.424176] ideal = 275000000, rounded = 0 > [ 2.424194] ccu_nkm_round_rate: rate = 330000000 > [ 2.424197] ideal = 330000000, rounded = 330000000 > [ 2.424201] sun4i_dclk_round_rate: div = 6 rate = 55000000 > [ 2.424205] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > [ 2.424209] ideal = 220000000, rounded = 0 > [ 2.424213] ideal = 275000000, rounded = 0 > [ 2.424230] ccu_nkm_round_rate: rate = 330000000 > [ 2.424233] ideal = 330000000, rounded = 330000000 > [ 2.424236] sun4i_dclk_round_rate: div = 6 rate = 55000000 > [ 2.424253] ccu_nkm_round_rate: rate = 330000000 > [ 2.424270] ccu_nkm_round_rate: rate = 330000000 > [ 2.424278] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > [ 2.424281] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > [ 2.424306] ccu_nkm_set_rate: rate = 330000000, parent_rate = 297000000 > [ 2.424309] ccu_nkm_set_rate: _nkm.n = 5 > [ 2.424311] ccu_nkm_set_rate: _nkm.k = 2 > [ 2.424313] ccu_nkm_set_rate: _nkm.m = 9 > [ 2.424661] sun4i_dclk_set_rate div 6 > [ 2.424668] sun4i_dclk_recalc_rate: val = 6, rate = 55000000 > > But look like this wouldn't valid for all other dclock rates, say BPI > panel has 30MHz clock that would failed with this logic. > > On the other side Allwinner BSP calculating dclk divider based on the > SoC's. for A33 [1] it is fixed dclk divider of 4 and for A64 is is > calculated based on the bpp/lanes. It looks like the A64 has the same divider of 4: https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 I think you're confusing it with the ratio between the pixel clock and the dotclock, called dsi_div: https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L198 Maxime
On Tue, Jan 29, 2019 at 8:43 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Mon, Jan 28, 2019 at 03:06:10PM +0530, Jagan Teki wrote: > > On Sat, Jan 26, 2019 at 2:54 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > On Fri, Jan 25, 2019 at 01:28:49AM +0530, Jagan Teki wrote: > > > > Minimum PLL used for MIPI is 500MHz, as per manual, but > > > > lowering the min rate by 300MHz can result proper working > > > > nkms divider with the help of desired dclock rate from > > > > panel driver. > > > > > > > > Signed-off-by: Jagan Teki <jagan@amarulasolutions.com> > > > > Acked-by: Stephen Boyd <sboyd@kernel.org> > > > > > > Going 200MHz below the minimum doesn't seem really reasonable. What > > > is the issue that you are trying to fix here? > > > > > > It looks like it's picking bad dividers, but if that's the case, this > > > isn't the proper fix. > > > > As I stated in earlier patches, the whole idea is pick the desired > > dclk divider based dclk rate. So the dotclock, sun4i_dclk_round_rate > > is unable to get the proper dclk divider at the end, so it eventually > > picking up wrong divider value and fired vblank timeout. > > > > So, we come-up with optimal and working min_rate 300MHz in pll-mipi to > > get the desired clock something like below. > > [ 2.415773] [drm] No driver support for vblank timestamp query. > > [ 2.424116] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > [ 2.424172] ideal = 220000000, rounded = 0 > > [ 2.424176] ideal = 275000000, rounded = 0 > > [ 2.424194] ccu_nkm_round_rate: rate = 330000000 > > [ 2.424197] ideal = 330000000, rounded = 330000000 > > [ 2.424201] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > [ 2.424205] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > [ 2.424209] ideal = 220000000, rounded = 0 > > [ 2.424213] ideal = 275000000, rounded = 0 > > [ 2.424230] ccu_nkm_round_rate: rate = 330000000 > > [ 2.424233] ideal = 330000000, rounded = 330000000 > > [ 2.424236] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > [ 2.424253] ccu_nkm_round_rate: rate = 330000000 > > [ 2.424270] ccu_nkm_round_rate: rate = 330000000 > > [ 2.424278] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > [ 2.424281] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > [ 2.424306] ccu_nkm_set_rate: rate = 330000000, parent_rate = 297000000 > > [ 2.424309] ccu_nkm_set_rate: _nkm.n = 5 > > [ 2.424311] ccu_nkm_set_rate: _nkm.k = 2 > > [ 2.424313] ccu_nkm_set_rate: _nkm.m = 9 > > [ 2.424661] sun4i_dclk_set_rate div 6 > > [ 2.424668] sun4i_dclk_recalc_rate: val = 6, rate = 55000000 > > > > But look like this wouldn't valid for all other dclock rates, say BPI > > panel has 30MHz clock that would failed with this logic. > > > > On the other side Allwinner BSP calculating dclk divider based on the > > SoC's. for A33 [1] it is fixed dclk divider of 4 and for A64 is is > > calculated based on the bpp/lanes. > > It looks like the A64 has the same divider of 4: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > I think you're confusing it with the ratio between the pixel clock and > the dotclock, called dsi_div: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L198 Ahh.. I thought this initially but as far as DSI clock computation is concern, the L12 tcon_div is local variable which is used for edge0 computation in burst mode and not for the dsi clock computation. Since the BSP is unable to get the tcon_div during edge0 computation, they defined it locally I think. You can see the lcd_clk_config() code [2], where we can see DSI clock computation using dsi_div value. Here is dump after the in Line 792 which is after computation[3] [ 10.800737] lcd_clk_config: dsi_div = 6, tcon_div = 4, lcd_div = 1 [ 10.800743] lcd_clk_config: lcd_dclk_freq = 55, dclk_rate = 55000000 [ 10.800749] lcd_clk_config: lcd_rate = 330000000, pll_rate = 330000000 The above dump the lcd_rate 330MHz is computed with panel clock, 55MHz into dsi_div 6. So this can be our actual divider values dclk_min_div, dclk_max_div in sun4i_dclk_round_rate (from drivers/gpu/drm/sun4i/sun4i_dotclock.c) We can even confirm this from Mainline code: [ 1.866128] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 55000000 [ 1.873112] round_rate, parent = 330000000 [ 1.877351] round_rate, rate = 330000000 [ 1.881338] ideal = 330000000, rounded = 330000000, div = 6 [ 1.887232] sun4i_dclk_round_rate: div = 6 rate = 55000000 [ 1.887239] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 55000000 [ 1.887243] round_rate, parent = 330000000 [ 1.887259] round_rate, rate = 330000000 [ 1.887264] ideal = 330000000, rounded = 330000000, div = 6 [ 1.887267] sun4i_dclk_round_rate: div = 6 rate = 55000000 [ 1.887270] round_rate, parent = 330000000 [ 1.887286] round_rate, rate = 330000000 [ 1.887292] round_rate, parent = 330000000 [ 1.887307] round_rate, rate = 330000000 [ 1.887320] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 [ 1.887324] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 [ 1.887350] rate = 330000000 [ 1.887353] parent_rate = 297000000 [ 1.887355] reg = 0x80c00000 [ 1.887359] _nkm.n = 5, nkm->n.offset = 0x1, nkm->n.shift = 8 [ 1.887362] _nkm.k = 2, nkm->k.offset = 0x1, nkm->k.shift = 4 [ 1.887365] _nkm.m = 9, nkm->m.offset = 0x1, nkm->m.shift = 0 [ 1.887712] sun4i_dclk_set_rate div 6 [ 1.887720] sun4i_dclk_recalc_rate: val = 6, rate = 55000000 So, the dsi_div from AW BSP is our dclk_mini_div(and dclk_max_div) and that can be computed as format/lanes in A64. Hope this explaining clears the diff, let me know if I miss anything. [2] https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L781 [3] https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L792
On Tue, Jan 29, 2019 at 11:01:31PM +0530, Jagan Teki wrote: > On Tue, Jan 29, 2019 at 8:43 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > On Mon, Jan 28, 2019 at 03:06:10PM +0530, Jagan Teki wrote: > > > On Sat, Jan 26, 2019 at 2:54 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > On Fri, Jan 25, 2019 at 01:28:49AM +0530, Jagan Teki wrote: > > > > > Minimum PLL used for MIPI is 500MHz, as per manual, but > > > > > lowering the min rate by 300MHz can result proper working > > > > > nkms divider with the help of desired dclock rate from > > > > > panel driver. > > > > > > > > > > Signed-off-by: Jagan Teki <jagan@amarulasolutions.com> > > > > > Acked-by: Stephen Boyd <sboyd@kernel.org> > > > > > > > > Going 200MHz below the minimum doesn't seem really reasonable. What > > > > is the issue that you are trying to fix here? > > > > > > > > It looks like it's picking bad dividers, but if that's the case, this > > > > isn't the proper fix. > > > > > > As I stated in earlier patches, the whole idea is pick the desired > > > dclk divider based dclk rate. So the dotclock, sun4i_dclk_round_rate > > > is unable to get the proper dclk divider at the end, so it eventually > > > picking up wrong divider value and fired vblank timeout. > > > > > > So, we come-up with optimal and working min_rate 300MHz in pll-mipi to > > > get the desired clock something like below. > > > [ 2.415773] [drm] No driver support for vblank timestamp query. > > > [ 2.424116] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > > [ 2.424172] ideal = 220000000, rounded = 0 > > > [ 2.424176] ideal = 275000000, rounded = 0 > > > [ 2.424194] ccu_nkm_round_rate: rate = 330000000 > > > [ 2.424197] ideal = 330000000, rounded = 330000000 > > > [ 2.424201] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > > [ 2.424205] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > > [ 2.424209] ideal = 220000000, rounded = 0 > > > [ 2.424213] ideal = 275000000, rounded = 0 > > > [ 2.424230] ccu_nkm_round_rate: rate = 330000000 > > > [ 2.424233] ideal = 330000000, rounded = 330000000 > > > [ 2.424236] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > > [ 2.424253] ccu_nkm_round_rate: rate = 330000000 > > > [ 2.424270] ccu_nkm_round_rate: rate = 330000000 > > > [ 2.424278] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > > [ 2.424281] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > > [ 2.424306] ccu_nkm_set_rate: rate = 330000000, parent_rate = 297000000 > > > [ 2.424309] ccu_nkm_set_rate: _nkm.n = 5 > > > [ 2.424311] ccu_nkm_set_rate: _nkm.k = 2 > > > [ 2.424313] ccu_nkm_set_rate: _nkm.m = 9 > > > [ 2.424661] sun4i_dclk_set_rate div 6 > > > [ 2.424668] sun4i_dclk_recalc_rate: val = 6, rate = 55000000 > > > > > > But look like this wouldn't valid for all other dclock rates, say BPI > > > panel has 30MHz clock that would failed with this logic. > > > > > > On the other side Allwinner BSP calculating dclk divider based on the > > > SoC's. for A33 [1] it is fixed dclk divider of 4 and for A64 is is > > > calculated based on the bpp/lanes. > > > > It looks like the A64 has the same divider of 4: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > I think you're confusing it with the ratio between the pixel clock and > > the dotclock, called dsi_div: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L198 > > Ahh.. I thought this initially but as far as DSI clock computation is > concern, the L12 tcon_div is local variable which is used for edge0 > computation in burst mode and not for the dsi clock computation. Since > the BSP is unable to get the tcon_div during edge0 computation, they > defined it locally I think. > > You can see the lcd_clk_config() code [2], where we can see DSI clock > computation using dsi_div value. > > Here is dump after the in Line 792 which is after computation[3] > [ 10.800737] lcd_clk_config: dsi_div = 6, tcon_div = 4, lcd_div = 1 > [ 10.800743] lcd_clk_config: lcd_dclk_freq = 55, dclk_rate = 55000000 > [ 10.800749] lcd_clk_config: lcd_rate = 330000000, pll_rate = 330000000 > > The above dump the lcd_rate 330MHz is computed with panel clock, 55MHz > into dsi_div 6. So this can be our actual divider values dclk_min_div, > dclk_max_div in sun4i_dclk_round_rate (from > drivers/gpu/drm/sun4i/sun4i_dotclock.c) I wish it was in your commit log in the first place, instead of having to exchange multiple mails over this. However, I don't think that's quite true, and it might be a bug in Allwinner's implementation (or rather something quite confusing). You're right that the lcd_rate and pll_rate seem to be generated from the pixel clock, and it indeed looks like the ratio between the pixel clock and the TCON dotclock is defined through the number of bits per lanes. However, in this case, dsi_rate is actually the same than lcd_rate, since pll_rate is going to be divided by dsi_div: https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 Since lcd_div is 1, it also means that in this case, dsi_rate == dclk_rate. The DSI module clock however, is always set to 148.5 MHz. Indeed, if we look at: https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 We can see that the rate in clk_info is used if it's different than 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a DSI panel, will hardcode it to 148.5 MHz: https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 So, the DSI clock is set to this here: https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 The TCON *module* clock (the one in the clock controller) has been set to lcd_rate (so the pixel clock times the number of bits per lane) here: https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 And the PLL has been set to the same rate here: https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 Let's take a step back now: that function we were looking at, lcd_clk_config, is called by lcd_clk_enable, which is in turn called by disp_lcd_enable here: https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 The next function being called is disp_al_lcd_cfg, and that function will hardcode the TCON dotclock divider to 4, here: https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 So, in the end, the dotclock divider is always 4, the DSI module clock is set to 148.5 MHz, and the TCON module clock is set to 330MHz. Since the TCON module clock doesn't have a divider, the PLL is set at that same value but this is redundant. I'll experiment with this and try to see how it works on the A33. Maxime
On Fri, Feb 1, 2019 at 8:01 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Tue, Jan 29, 2019 at 11:01:31PM +0530, Jagan Teki wrote: > > On Tue, Jan 29, 2019 at 8:43 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > On Mon, Jan 28, 2019 at 03:06:10PM +0530, Jagan Teki wrote: > > > > On Sat, Jan 26, 2019 at 2:54 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > On Fri, Jan 25, 2019 at 01:28:49AM +0530, Jagan Teki wrote: > > > > > > Minimum PLL used for MIPI is 500MHz, as per manual, but > > > > > > lowering the min rate by 300MHz can result proper working > > > > > > nkms divider with the help of desired dclock rate from > > > > > > panel driver. > > > > > > > > > > > > Signed-off-by: Jagan Teki <jagan@amarulasolutions.com> > > > > > > Acked-by: Stephen Boyd <sboyd@kernel.org> > > > > > > > > > > Going 200MHz below the minimum doesn't seem really reasonable. What > > > > > is the issue that you are trying to fix here? > > > > > > > > > > It looks like it's picking bad dividers, but if that's the case, this > > > > > isn't the proper fix. > > > > > > > > As I stated in earlier patches, the whole idea is pick the desired > > > > dclk divider based dclk rate. So the dotclock, sun4i_dclk_round_rate > > > > is unable to get the proper dclk divider at the end, so it eventually > > > > picking up wrong divider value and fired vblank timeout. > > > > > > > > So, we come-up with optimal and working min_rate 300MHz in pll-mipi to > > > > get the desired clock something like below. > > > > [ 2.415773] [drm] No driver support for vblank timestamp query. > > > > [ 2.424116] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > > > [ 2.424172] ideal = 220000000, rounded = 0 > > > > [ 2.424176] ideal = 275000000, rounded = 0 > > > > [ 2.424194] ccu_nkm_round_rate: rate = 330000000 > > > > [ 2.424197] ideal = 330000000, rounded = 330000000 > > > > [ 2.424201] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > > > [ 2.424205] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > > > [ 2.424209] ideal = 220000000, rounded = 0 > > > > [ 2.424213] ideal = 275000000, rounded = 0 > > > > [ 2.424230] ccu_nkm_round_rate: rate = 330000000 > > > > [ 2.424233] ideal = 330000000, rounded = 330000000 > > > > [ 2.424236] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > > > [ 2.424253] ccu_nkm_round_rate: rate = 330000000 > > > > [ 2.424270] ccu_nkm_round_rate: rate = 330000000 > > > > [ 2.424278] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > > > [ 2.424281] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > > > [ 2.424306] ccu_nkm_set_rate: rate = 330000000, parent_rate = 297000000 > > > > [ 2.424309] ccu_nkm_set_rate: _nkm.n = 5 > > > > [ 2.424311] ccu_nkm_set_rate: _nkm.k = 2 > > > > [ 2.424313] ccu_nkm_set_rate: _nkm.m = 9 > > > > [ 2.424661] sun4i_dclk_set_rate div 6 > > > > [ 2.424668] sun4i_dclk_recalc_rate: val = 6, rate = 55000000 > > > > > > > > But look like this wouldn't valid for all other dclock rates, say BPI > > > > panel has 30MHz clock that would failed with this logic. > > > > > > > > On the other side Allwinner BSP calculating dclk divider based on the > > > > SoC's. for A33 [1] it is fixed dclk divider of 4 and for A64 is is > > > > calculated based on the bpp/lanes. > > > > > > It looks like the A64 has the same divider of 4: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > I think you're confusing it with the ratio between the pixel clock and > > > the dotclock, called dsi_div: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L198 > > > > Ahh.. I thought this initially but as far as DSI clock computation is > > concern, the L12 tcon_div is local variable which is used for edge0 > > computation in burst mode and not for the dsi clock computation. Since > > the BSP is unable to get the tcon_div during edge0 computation, they > > defined it locally I think. > > > > You can see the lcd_clk_config() code [2], where we can see DSI clock > > computation using dsi_div value. > > > > Here is dump after the in Line 792 which is after computation[3] > > [ 10.800737] lcd_clk_config: dsi_div = 6, tcon_div = 4, lcd_div = 1 > > [ 10.800743] lcd_clk_config: lcd_dclk_freq = 55, dclk_rate = 55000000 > > [ 10.800749] lcd_clk_config: lcd_rate = 330000000, pll_rate = 330000000 > > > > The above dump the lcd_rate 330MHz is computed with panel clock, 55MHz > > into dsi_div 6. So this can be our actual divider values dclk_min_div, > > dclk_max_div in sun4i_dclk_round_rate (from > > drivers/gpu/drm/sun4i/sun4i_dotclock.c) > > I wish it was in your commit log in the first place, instead of having > to exchange multiple mails over this. > > However, I don't think that's quite true, and it might be a bug in > Allwinner's implementation (or rather something quite confusing). > > You're right that the lcd_rate and pll_rate seem to be generated from > the pixel clock, and it indeed looks like the ratio between the pixel > clock and the TCON dotclock is defined through the number of bits per > lanes. > > However, in this case, dsi_rate is actually the same than lcd_rate, > since pll_rate is going to be divided by dsi_div: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > Since lcd_div is 1, it also means that in this case, dsi_rate == > dclk_rate. Yes, but the lcd_rate and dsi_rate are not same, since dsi_rate is again computed as dsi_div with pll_rate. lcd_rate = dclk_rate * 6; pll_rate = lcd_rate * 1; dsi_rate = pll_rate / 6; [ 14.719981] tcon_div = 4, lcd_div = 1, dsi_div = 6, dsi_rate = 148500000 [ 14.722666] dsi_div = 6, lcd_div = 1 [ 14.722695] [DISP]disp_module_init finish [ 14.727699] lcd_rate = 180000000, pll_rate = 180000000 [ 14.730269] dsi_rate = 30000000 > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > we look at: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > We can see that the rate in clk_info is used if it's different than > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > DSI panel, will hardcode it to 148.5 MHz: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > So, the DSI clock is set to this here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > The TCON *module* clock (the one in the clock controller) has been set > to lcd_rate (so the pixel clock times the number of bits per lane) here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > And the PLL has been set to the same rate here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > Let's take a step back now: that function we were looking at, > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > by disp_lcd_enable here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > The next function being called is disp_al_lcd_cfg, and that function > will hardcode the TCON dotclock divider to 4, here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 Haa.. this is reason I have TCON_DCLK register value is 4 in BSP # devmem 0x01c0c044 0xF0000004 > So, in the end, the dotclock divider is always 4, the DSI module clock > is set to 148.5 MHz, and the TCON module clock is set to 330MHz. Since > the TCON module clock doesn't have a divider, the PLL is set at that > same value but this is redundant. 330 or 180MHz. if we have pixel clock 30MHz with 6 div value it's 180MHz. > > I'll experiment with this and try to see how it works on the A33. OK, thanks. will try digging further on this from my side as well.
Hi Maxime, On Fri, Feb 1, 2019 at 8:01 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Tue, Jan 29, 2019 at 11:01:31PM +0530, Jagan Teki wrote: > > On Tue, Jan 29, 2019 at 8:43 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > On Mon, Jan 28, 2019 at 03:06:10PM +0530, Jagan Teki wrote: > > > > On Sat, Jan 26, 2019 at 2:54 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > On Fri, Jan 25, 2019 at 01:28:49AM +0530, Jagan Teki wrote: > > > > > > Minimum PLL used for MIPI is 500MHz, as per manual, but > > > > > > lowering the min rate by 300MHz can result proper working > > > > > > nkms divider with the help of desired dclock rate from > > > > > > panel driver. > > > > > > > > > > > > Signed-off-by: Jagan Teki <jagan@amarulasolutions.com> > > > > > > Acked-by: Stephen Boyd <sboyd@kernel.org> > > > > > > > > > > Going 200MHz below the minimum doesn't seem really reasonable. What > > > > > is the issue that you are trying to fix here? > > > > > > > > > > It looks like it's picking bad dividers, but if that's the case, this > > > > > isn't the proper fix. > > > > > > > > As I stated in earlier patches, the whole idea is pick the desired > > > > dclk divider based dclk rate. So the dotclock, sun4i_dclk_round_rate > > > > is unable to get the proper dclk divider at the end, so it eventually > > > > picking up wrong divider value and fired vblank timeout. > > > > > > > > So, we come-up with optimal and working min_rate 300MHz in pll-mipi to > > > > get the desired clock something like below. > > > > [ 2.415773] [drm] No driver support for vblank timestamp query. > > > > [ 2.424116] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > > > [ 2.424172] ideal = 220000000, rounded = 0 > > > > [ 2.424176] ideal = 275000000, rounded = 0 > > > > [ 2.424194] ccu_nkm_round_rate: rate = 330000000 > > > > [ 2.424197] ideal = 330000000, rounded = 330000000 > > > > [ 2.424201] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > > > [ 2.424205] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > > > [ 2.424209] ideal = 220000000, rounded = 0 > > > > [ 2.424213] ideal = 275000000, rounded = 0 > > > > [ 2.424230] ccu_nkm_round_rate: rate = 330000000 > > > > [ 2.424233] ideal = 330000000, rounded = 330000000 > > > > [ 2.424236] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > > > [ 2.424253] ccu_nkm_round_rate: rate = 330000000 > > > > [ 2.424270] ccu_nkm_round_rate: rate = 330000000 > > > > [ 2.424278] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > > > [ 2.424281] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > > > [ 2.424306] ccu_nkm_set_rate: rate = 330000000, parent_rate = 297000000 > > > > [ 2.424309] ccu_nkm_set_rate: _nkm.n = 5 > > > > [ 2.424311] ccu_nkm_set_rate: _nkm.k = 2 > > > > [ 2.424313] ccu_nkm_set_rate: _nkm.m = 9 > > > > [ 2.424661] sun4i_dclk_set_rate div 6 > > > > [ 2.424668] sun4i_dclk_recalc_rate: val = 6, rate = 55000000 > > > > > > > > But look like this wouldn't valid for all other dclock rates, say BPI > > > > panel has 30MHz clock that would failed with this logic. > > > > > > > > On the other side Allwinner BSP calculating dclk divider based on the > > > > SoC's. for A33 [1] it is fixed dclk divider of 4 and for A64 is is > > > > calculated based on the bpp/lanes. > > > > > > It looks like the A64 has the same divider of 4: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > I think you're confusing it with the ratio between the pixel clock and > > > the dotclock, called dsi_div: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L198 > > > > Ahh.. I thought this initially but as far as DSI clock computation is > > concern, the L12 tcon_div is local variable which is used for edge0 > > computation in burst mode and not for the dsi clock computation. Since > > the BSP is unable to get the tcon_div during edge0 computation, they > > defined it locally I think. > > > > You can see the lcd_clk_config() code [2], where we can see DSI clock > > computation using dsi_div value. > > > > Here is dump after the in Line 792 which is after computation[3] > > [ 10.800737] lcd_clk_config: dsi_div = 6, tcon_div = 4, lcd_div = 1 > > [ 10.800743] lcd_clk_config: lcd_dclk_freq = 55, dclk_rate = 55000000 > > [ 10.800749] lcd_clk_config: lcd_rate = 330000000, pll_rate = 330000000 > > > > The above dump the lcd_rate 330MHz is computed with panel clock, 55MHz > > into dsi_div 6. So this can be our actual divider values dclk_min_div, > > dclk_max_div in sun4i_dclk_round_rate (from > > drivers/gpu/drm/sun4i/sun4i_dotclock.c) > > I wish it was in your commit log in the first place, instead of having > to exchange multiple mails over this. > > However, I don't think that's quite true, and it might be a bug in > Allwinner's implementation (or rather something quite confusing). > > You're right that the lcd_rate and pll_rate seem to be generated from > the pixel clock, and it indeed looks like the ratio between the pixel > clock and the TCON dotclock is defined through the number of bits per > lanes. > > However, in this case, dsi_rate is actually the same than lcd_rate, > since pll_rate is going to be divided by dsi_div: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > Since lcd_div is 1, it also means that in this case, dsi_rate == > dclk_rate. > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > we look at: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > We can see that the rate in clk_info is used if it's different than > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > DSI panel, will hardcode it to 148.5 MHz: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > So, the DSI clock is set to this here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > The TCON *module* clock (the one in the clock controller) has been set > to lcd_rate (so the pixel clock times the number of bits per lane) here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > And the PLL has been set to the same rate here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > Let's take a step back now: that function we were looking at, > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > by disp_lcd_enable here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > The next function being called is disp_al_lcd_cfg, and that function > will hardcode the TCON dotclock divider to 4, here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > So, in the end, the dotclock divider is always 4, the DSI module clock > is set to 148.5 MHz, and the TCON module clock is set to 330MHz. Since > the TCON module clock doesn't have a divider, the PLL is set at that > same value but this is redundant. > > I'll experiment with this and try to see how it works on the A33. How is it with A33?
On Mon, Feb 11, 2019 at 07:37:57PM +0530, Jagan Teki wrote: > Hi Maxime, > > On Fri, Feb 1, 2019 at 8:01 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > On Tue, Jan 29, 2019 at 11:01:31PM +0530, Jagan Teki wrote: > > > On Tue, Jan 29, 2019 at 8:43 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > On Mon, Jan 28, 2019 at 03:06:10PM +0530, Jagan Teki wrote: > > > > > On Sat, Jan 26, 2019 at 2:54 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > On Fri, Jan 25, 2019 at 01:28:49AM +0530, Jagan Teki wrote: > > > > > > > Minimum PLL used for MIPI is 500MHz, as per manual, but > > > > > > > lowering the min rate by 300MHz can result proper working > > > > > > > nkms divider with the help of desired dclock rate from > > > > > > > panel driver. > > > > > > > > > > > > > > Signed-off-by: Jagan Teki <jagan@amarulasolutions.com> > > > > > > > Acked-by: Stephen Boyd <sboyd@kernel.org> > > > > > > > > > > > > Going 200MHz below the minimum doesn't seem really reasonable. What > > > > > > is the issue that you are trying to fix here? > > > > > > > > > > > > It looks like it's picking bad dividers, but if that's the case, this > > > > > > isn't the proper fix. > > > > > > > > > > As I stated in earlier patches, the whole idea is pick the desired > > > > > dclk divider based dclk rate. So the dotclock, sun4i_dclk_round_rate > > > > > is unable to get the proper dclk divider at the end, so it eventually > > > > > picking up wrong divider value and fired vblank timeout. > > > > > > > > > > So, we come-up with optimal and working min_rate 300MHz in pll-mipi to > > > > > get the desired clock something like below. > > > > > [ 2.415773] [drm] No driver support for vblank timestamp query. > > > > > [ 2.424116] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > > > > [ 2.424172] ideal = 220000000, rounded = 0 > > > > > [ 2.424176] ideal = 275000000, rounded = 0 > > > > > [ 2.424194] ccu_nkm_round_rate: rate = 330000000 > > > > > [ 2.424197] ideal = 330000000, rounded = 330000000 > > > > > [ 2.424201] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > > > > [ 2.424205] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > > > > [ 2.424209] ideal = 220000000, rounded = 0 > > > > > [ 2.424213] ideal = 275000000, rounded = 0 > > > > > [ 2.424230] ccu_nkm_round_rate: rate = 330000000 > > > > > [ 2.424233] ideal = 330000000, rounded = 330000000 > > > > > [ 2.424236] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > > > > [ 2.424253] ccu_nkm_round_rate: rate = 330000000 > > > > > [ 2.424270] ccu_nkm_round_rate: rate = 330000000 > > > > > [ 2.424278] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > > > > [ 2.424281] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > > > > [ 2.424306] ccu_nkm_set_rate: rate = 330000000, parent_rate = 297000000 > > > > > [ 2.424309] ccu_nkm_set_rate: _nkm.n = 5 > > > > > [ 2.424311] ccu_nkm_set_rate: _nkm.k = 2 > > > > > [ 2.424313] ccu_nkm_set_rate: _nkm.m = 9 > > > > > [ 2.424661] sun4i_dclk_set_rate div 6 > > > > > [ 2.424668] sun4i_dclk_recalc_rate: val = 6, rate = 55000000 > > > > > > > > > > But look like this wouldn't valid for all other dclock rates, say BPI > > > > > panel has 30MHz clock that would failed with this logic. > > > > > > > > > > On the other side Allwinner BSP calculating dclk divider based on the > > > > > SoC's. for A33 [1] it is fixed dclk divider of 4 and for A64 is is > > > > > calculated based on the bpp/lanes. > > > > > > > > It looks like the A64 has the same divider of 4: > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > > > I think you're confusing it with the ratio between the pixel clock and > > > > the dotclock, called dsi_div: > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L198 > > > > > > Ahh.. I thought this initially but as far as DSI clock computation is > > > concern, the L12 tcon_div is local variable which is used for edge0 > > > computation in burst mode and not for the dsi clock computation. Since > > > the BSP is unable to get the tcon_div during edge0 computation, they > > > defined it locally I think. > > > > > > You can see the lcd_clk_config() code [2], where we can see DSI clock > > > computation using dsi_div value. > > > > > > Here is dump after the in Line 792 which is after computation[3] > > > [ 10.800737] lcd_clk_config: dsi_div = 6, tcon_div = 4, lcd_div = 1 > > > [ 10.800743] lcd_clk_config: lcd_dclk_freq = 55, dclk_rate = 55000000 > > > [ 10.800749] lcd_clk_config: lcd_rate = 330000000, pll_rate = 330000000 > > > > > > The above dump the lcd_rate 330MHz is computed with panel clock, 55MHz > > > into dsi_div 6. So this can be our actual divider values dclk_min_div, > > > dclk_max_div in sun4i_dclk_round_rate (from > > > drivers/gpu/drm/sun4i/sun4i_dotclock.c) > > > > I wish it was in your commit log in the first place, instead of having > > to exchange multiple mails over this. > > > > However, I don't think that's quite true, and it might be a bug in > > Allwinner's implementation (or rather something quite confusing). > > > > You're right that the lcd_rate and pll_rate seem to be generated from > > the pixel clock, and it indeed looks like the ratio between the pixel > > clock and the TCON dotclock is defined through the number of bits per > > lanes. > > > > However, in this case, dsi_rate is actually the same than lcd_rate, > > since pll_rate is going to be divided by dsi_div: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > > > Since lcd_div is 1, it also means that in this case, dsi_rate == > > dclk_rate. > > > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > > we look at: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > > > We can see that the rate in clk_info is used if it's different than > > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > > DSI panel, will hardcode it to 148.5 MHz: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > > > So, the DSI clock is set to this here: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > > > The TCON *module* clock (the one in the clock controller) has been set > > to lcd_rate (so the pixel clock times the number of bits per lane) here: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > > > And the PLL has been set to the same rate here: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > > > Let's take a step back now: that function we were looking at, > > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > > by disp_lcd_enable here: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > > > The next function being called is disp_al_lcd_cfg, and that function > > will hardcode the TCON dotclock divider to 4, here: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > > > So, in the end, the dotclock divider is always 4, the DSI module clock > > is set to 148.5 MHz, and the TCON module clock is set to 330MHz. Since > > the TCON module clock doesn't have a divider, the PLL is set at that > > same value but this is redundant. > > > > I'll experiment with this and try to see how it works on the A33. > > How is it with A33? The conclusions are the one I sent in my last series Maxime
On Tue, Feb 12, 2019 at 3:00 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Mon, Feb 11, 2019 at 07:37:57PM +0530, Jagan Teki wrote: > > Hi Maxime, > > > > On Fri, Feb 1, 2019 at 8:01 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > On Tue, Jan 29, 2019 at 11:01:31PM +0530, Jagan Teki wrote: > > > > On Tue, Jan 29, 2019 at 8:43 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > On Mon, Jan 28, 2019 at 03:06:10PM +0530, Jagan Teki wrote: > > > > > > On Sat, Jan 26, 2019 at 2:54 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > > > On Fri, Jan 25, 2019 at 01:28:49AM +0530, Jagan Teki wrote: > > > > > > > > Minimum PLL used for MIPI is 500MHz, as per manual, but > > > > > > > > lowering the min rate by 300MHz can result proper working > > > > > > > > nkms divider with the help of desired dclock rate from > > > > > > > > panel driver. > > > > > > > > > > > > > > > > Signed-off-by: Jagan Teki <jagan@amarulasolutions.com> > > > > > > > > Acked-by: Stephen Boyd <sboyd@kernel.org> > > > > > > > > > > > > > > Going 200MHz below the minimum doesn't seem really reasonable. What > > > > > > > is the issue that you are trying to fix here? > > > > > > > > > > > > > > It looks like it's picking bad dividers, but if that's the case, this > > > > > > > isn't the proper fix. > > > > > > > > > > > > As I stated in earlier patches, the whole idea is pick the desired > > > > > > dclk divider based dclk rate. So the dotclock, sun4i_dclk_round_rate > > > > > > is unable to get the proper dclk divider at the end, so it eventually > > > > > > picking up wrong divider value and fired vblank timeout. > > > > > > > > > > > > So, we come-up with optimal and working min_rate 300MHz in pll-mipi to > > > > > > get the desired clock something like below. > > > > > > [ 2.415773] [drm] No driver support for vblank timestamp query. > > > > > > [ 2.424116] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > > > > > [ 2.424172] ideal = 220000000, rounded = 0 > > > > > > [ 2.424176] ideal = 275000000, rounded = 0 > > > > > > [ 2.424194] ccu_nkm_round_rate: rate = 330000000 > > > > > > [ 2.424197] ideal = 330000000, rounded = 330000000 > > > > > > [ 2.424201] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > > > > > [ 2.424205] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > > > > > [ 2.424209] ideal = 220000000, rounded = 0 > > > > > > [ 2.424213] ideal = 275000000, rounded = 0 > > > > > > [ 2.424230] ccu_nkm_round_rate: rate = 330000000 > > > > > > [ 2.424233] ideal = 330000000, rounded = 330000000 > > > > > > [ 2.424236] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > > > > > [ 2.424253] ccu_nkm_round_rate: rate = 330000000 > > > > > > [ 2.424270] ccu_nkm_round_rate: rate = 330000000 > > > > > > [ 2.424278] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > > > > > [ 2.424281] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > > > > > [ 2.424306] ccu_nkm_set_rate: rate = 330000000, parent_rate = 297000000 > > > > > > [ 2.424309] ccu_nkm_set_rate: _nkm.n = 5 > > > > > > [ 2.424311] ccu_nkm_set_rate: _nkm.k = 2 > > > > > > [ 2.424313] ccu_nkm_set_rate: _nkm.m = 9 > > > > > > [ 2.424661] sun4i_dclk_set_rate div 6 > > > > > > [ 2.424668] sun4i_dclk_recalc_rate: val = 6, rate = 55000000 > > > > > > > > > > > > But look like this wouldn't valid for all other dclock rates, say BPI > > > > > > panel has 30MHz clock that would failed with this logic. > > > > > > > > > > > > On the other side Allwinner BSP calculating dclk divider based on the > > > > > > SoC's. for A33 [1] it is fixed dclk divider of 4 and for A64 is is > > > > > > calculated based on the bpp/lanes. > > > > > > > > > > It looks like the A64 has the same divider of 4: > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > > > > > I think you're confusing it with the ratio between the pixel clock and > > > > > the dotclock, called dsi_div: > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L198 > > > > > > > > Ahh.. I thought this initially but as far as DSI clock computation is > > > > concern, the L12 tcon_div is local variable which is used for edge0 > > > > computation in burst mode and not for the dsi clock computation. Since > > > > the BSP is unable to get the tcon_div during edge0 computation, they > > > > defined it locally I think. > > > > > > > > You can see the lcd_clk_config() code [2], where we can see DSI clock > > > > computation using dsi_div value. > > > > > > > > Here is dump after the in Line 792 which is after computation[3] > > > > [ 10.800737] lcd_clk_config: dsi_div = 6, tcon_div = 4, lcd_div = 1 > > > > [ 10.800743] lcd_clk_config: lcd_dclk_freq = 55, dclk_rate = 55000000 > > > > [ 10.800749] lcd_clk_config: lcd_rate = 330000000, pll_rate = 330000000 > > > > > > > > The above dump the lcd_rate 330MHz is computed with panel clock, 55MHz > > > > into dsi_div 6. So this can be our actual divider values dclk_min_div, > > > > dclk_max_div in sun4i_dclk_round_rate (from > > > > drivers/gpu/drm/sun4i/sun4i_dotclock.c) > > > > > > I wish it was in your commit log in the first place, instead of having > > > to exchange multiple mails over this. > > > > > > However, I don't think that's quite true, and it might be a bug in > > > Allwinner's implementation (or rather something quite confusing). > > > > > > You're right that the lcd_rate and pll_rate seem to be generated from > > > the pixel clock, and it indeed looks like the ratio between the pixel > > > clock and the TCON dotclock is defined through the number of bits per > > > lanes. > > > > > > However, in this case, dsi_rate is actually the same than lcd_rate, > > > since pll_rate is going to be divided by dsi_div: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > > > > > Since lcd_div is 1, it also means that in this case, dsi_rate == > > > dclk_rate. > > > > > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > > > we look at: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > > > > > We can see that the rate in clk_info is used if it's different than > > > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > > > DSI panel, will hardcode it to 148.5 MHz: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > > > > > So, the DSI clock is set to this here: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > > > > > The TCON *module* clock (the one in the clock controller) has been set > > > to lcd_rate (so the pixel clock times the number of bits per lane) here: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > > > > > And the PLL has been set to the same rate here: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > > > > > Let's take a step back now: that function we were looking at, > > > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > > > by disp_lcd_enable here: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > > > > > The next function being called is disp_al_lcd_cfg, and that function > > > will hardcode the TCON dotclock divider to 4, here: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > > > > > So, in the end, the dotclock divider is always 4, the DSI module clock > > > is set to 148.5 MHz, and the TCON module clock is set to 330MHz. Since > > > the TCON module clock doesn't have a divider, the PLL is set at that > > > same value but this is redundant. > > > > > > I'll experiment with this and try to see how it works on the A33. > > > > How is it with A33? > > The conclusions are the one I sent in my last series In this series? [PATCH v3 0/8] drm/sun4i: dsi: Add burst mode support
On Fri, Feb 1, 2019 at 8:01 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Tue, Jan 29, 2019 at 11:01:31PM +0530, Jagan Teki wrote: > > On Tue, Jan 29, 2019 at 8:43 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > On Mon, Jan 28, 2019 at 03:06:10PM +0530, Jagan Teki wrote: > > > > On Sat, Jan 26, 2019 at 2:54 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > On Fri, Jan 25, 2019 at 01:28:49AM +0530, Jagan Teki wrote: > > > > > > Minimum PLL used for MIPI is 500MHz, as per manual, but > > > > > > lowering the min rate by 300MHz can result proper working > > > > > > nkms divider with the help of desired dclock rate from > > > > > > panel driver. > > > > > > > > > > > > Signed-off-by: Jagan Teki <jagan@amarulasolutions.com> > > > > > > Acked-by: Stephen Boyd <sboyd@kernel.org> > > > > > > > > > > Going 200MHz below the minimum doesn't seem really reasonable. What > > > > > is the issue that you are trying to fix here? > > > > > > > > > > It looks like it's picking bad dividers, but if that's the case, this > > > > > isn't the proper fix. > > > > > > > > As I stated in earlier patches, the whole idea is pick the desired > > > > dclk divider based dclk rate. So the dotclock, sun4i_dclk_round_rate > > > > is unable to get the proper dclk divider at the end, so it eventually > > > > picking up wrong divider value and fired vblank timeout. > > > > > > > > So, we come-up with optimal and working min_rate 300MHz in pll-mipi to > > > > get the desired clock something like below. > > > > [ 2.415773] [drm] No driver support for vblank timestamp query. > > > > [ 2.424116] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > > > [ 2.424172] ideal = 220000000, rounded = 0 > > > > [ 2.424176] ideal = 275000000, rounded = 0 > > > > [ 2.424194] ccu_nkm_round_rate: rate = 330000000 > > > > [ 2.424197] ideal = 330000000, rounded = 330000000 > > > > [ 2.424201] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > > > [ 2.424205] sun4i_dclk_round_rate: min_div = 4 max_div = 127, rate = 55000000 > > > > [ 2.424209] ideal = 220000000, rounded = 0 > > > > [ 2.424213] ideal = 275000000, rounded = 0 > > > > [ 2.424230] ccu_nkm_round_rate: rate = 330000000 > > > > [ 2.424233] ideal = 330000000, rounded = 330000000 > > > > [ 2.424236] sun4i_dclk_round_rate: div = 6 rate = 55000000 > > > > [ 2.424253] ccu_nkm_round_rate: rate = 330000000 > > > > [ 2.424270] ccu_nkm_round_rate: rate = 330000000 > > > > [ 2.424278] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > > > [ 2.424281] sun4i_dclk_recalc_rate: val = 1, rate = 330000000 > > > > [ 2.424306] ccu_nkm_set_rate: rate = 330000000, parent_rate = 297000000 > > > > [ 2.424309] ccu_nkm_set_rate: _nkm.n = 5 > > > > [ 2.424311] ccu_nkm_set_rate: _nkm.k = 2 > > > > [ 2.424313] ccu_nkm_set_rate: _nkm.m = 9 > > > > [ 2.424661] sun4i_dclk_set_rate div 6 > > > > [ 2.424668] sun4i_dclk_recalc_rate: val = 6, rate = 55000000 > > > > > > > > But look like this wouldn't valid for all other dclock rates, say BPI > > > > panel has 30MHz clock that would failed with this logic. > > > > > > > > On the other side Allwinner BSP calculating dclk divider based on the > > > > SoC's. for A33 [1] it is fixed dclk divider of 4 and for A64 is is > > > > calculated based on the bpp/lanes. > > > > > > It looks like the A64 has the same divider of 4: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > I think you're confusing it with the ratio between the pixel clock and > > > the dotclock, called dsi_div: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L198 > > > > Ahh.. I thought this initially but as far as DSI clock computation is > > concern, the L12 tcon_div is local variable which is used for edge0 > > computation in burst mode and not for the dsi clock computation. Since > > the BSP is unable to get the tcon_div during edge0 computation, they > > defined it locally I think. > > > > You can see the lcd_clk_config() code [2], where we can see DSI clock > > computation using dsi_div value. > > > > Here is dump after the in Line 792 which is after computation[3] > > [ 10.800737] lcd_clk_config: dsi_div = 6, tcon_div = 4, lcd_div = 1 > > [ 10.800743] lcd_clk_config: lcd_dclk_freq = 55, dclk_rate = 55000000 > > [ 10.800749] lcd_clk_config: lcd_rate = 330000000, pll_rate = 330000000 > > > > The above dump the lcd_rate 330MHz is computed with panel clock, 55MHz > > into dsi_div 6. So this can be our actual divider values dclk_min_div, > > dclk_max_div in sun4i_dclk_round_rate (from > > drivers/gpu/drm/sun4i/sun4i_dotclock.c) > > I wish it was in your commit log in the first place, instead of having > to exchange multiple mails over this. > > However, I don't think that's quite true, and it might be a bug in > Allwinner's implementation (or rather something quite confusing). > > You're right that the lcd_rate and pll_rate seem to be generated from > the pixel clock, and it indeed looks like the ratio between the pixel > clock and the TCON dotclock is defined through the number of bits per > lanes. > > However, in this case, dsi_rate is actually the same than lcd_rate, > since pll_rate is going to be divided by dsi_div: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > Since lcd_div is 1, it also means that in this case, dsi_rate == > dclk_rate. > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > we look at: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > We can see that the rate in clk_info is used if it's different than > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > DSI panel, will hardcode it to 148.5 MHz: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > So, the DSI clock is set to this here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > The TCON *module* clock (the one in the clock controller) has been set > to lcd_rate (so the pixel clock times the number of bits per lane) here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > And the PLL has been set to the same rate here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 Let me explain, something more. According to bsp there are clk_info.tcon_div which I will explain below. clk_info.dsi_div which is dynamic and it depends on bpp/lanes, so it is 6 for 24bpp and 4 lanes devices. PLL rate here depends on dsi_div (not tcon_div) Code here https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L784 is computing the actual set rate, which depends on dsi_rate. lcd_rate = dclk_rate * clk_info.dsi_div; dsi_rate = pll_rate / clk_info.dsi_div; Say if the dclk_rate 148MHz then the dsi_rate is 888MHz which set rate for above link you mentioned. Here are the evidence with some prints. https://gist.github.com/openedev/9bae2d87d2fcc06b999fe48c998b7043 https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > Let's take a step back now: that function we were looking at, > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > by disp_lcd_enable here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > The next function being called is disp_al_lcd_cfg, and that function > will hardcode the TCON dotclock divider to 4, here: > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 tcon_div from BSP point-of-view of there are two variants 00) clk_info.tcon_div which is 4 and same is set the divider position in SUN4I_TCON0_DCLK_REG (like above link refer) 01) tcon_div which is 4 and used for edge timings computation https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 The real reason for 01) is again 4 is they set the divider to 4 in 00) which is technically wrong because the dividers which used during dotclock in above (dsi_div) should be used here as well. Since there is no dynamic way of doing this BSP hard-coding these values. Patches 5,6,7 on this series doing this https://patchwork.freedesktop.org/series/60847/ Hope this explanation helps?
Hi, I've reordered the mail a bit to work on chunks On Fri, May 24, 2019 at 03:37:42PM +0530, Jagan Teki wrote: > > I wish it was in your commit log in the first place, instead of having > > to exchange multiple mails over this. > > > > However, I don't think that's quite true, and it might be a bug in > > Allwinner's implementation (or rather something quite confusing). > > > > You're right that the lcd_rate and pll_rate seem to be generated from > > the pixel clock, and it indeed looks like the ratio between the pixel > > clock and the TCON dotclock is defined through the number of bits per > > lanes. > > > > However, in this case, dsi_rate is actually the same than lcd_rate, > > since pll_rate is going to be divided by dsi_div: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > > > Since lcd_div is 1, it also means that in this case, dsi_rate == > > dclk_rate. > > > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > > we look at: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > > > We can see that the rate in clk_info is used if it's different than > > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > > DSI panel, will hardcode it to 148.5 MHz: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > Let me explain, something more. > > According to bsp there are clk_info.tcon_div which I will explain below. > clk_info.dsi_div which is dynamic and it depends on bpp/lanes, so it > is 6 for 24bpp and 4 lanes devices. > > PLL rate here depends on dsi_div (not tcon_div) > > Code here > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L784 > > is computing the actual set rate, which depends on dsi_rate. > > lcd_rate = dclk_rate * clk_info.dsi_div; > dsi_rate = pll_rate / clk_info.dsi_div; > > Say if the dclk_rate 148MHz then the dsi_rate is 888MHz which set rate > for above link you mentioned. > > Here are the evidence with some prints. > > https://gist.github.com/openedev/9bae2d87d2fcc06b999fe48c998b7043 > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a Ok, so we agree up to this point, and the prints confirm that the analysis above is the right one. > > So, the DSI clock is set to this here: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 Your patch doesn't address that, so let's leave that one alone. > > The TCON *module* clock (the one in the clock controller) has been set > > to lcd_rate (so the pixel clock times the number of bits per lane) here: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > > > And the PLL has been set to the same rate here: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > > > Let's take a step back now: that function we were looking at, > > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > > by disp_lcd_enable here: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > > > The next function being called is disp_al_lcd_cfg, and that function > > will hardcode the TCON dotclock divider to 4, here: > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > tcon_div from BSP point-of-view of there are two variants > 00) clk_info.tcon_div which is 4 and same is set the divider position > in SUN4I_TCON0_DCLK_REG (like above link refer) > 01) tcon_div which is 4 and used for edge timings computation > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > The real reason for 01) is again 4 is they set the divider to 4 in 00) > which is technically wrong because the dividers which used during > dotclock in above (dsi_div) should be used here as well. Since there > is no dynamic way of doing this BSP hard-coding these values. > > Patches 5,6,7 on this series doing this > https://patchwork.freedesktop.org/series/60847/ > > Hope this explanation helps? It doesn't. The clock tree is this one: PLL(s) -> TCON module clock -> TCON dotclock. The links I mentioned above show that the clock set to lcd_rate is the TCON module clocks (and it should be the one taking the bpp and lanes into account), while the TCON dotclock uses a fixed divider of 4. In your patches, you're using the bpp / lanes divider on the TCON dotclock, ie, the wrong clock. Again, I'm not saying that my analysis of the source code is correct here. But you haven't said anything to prove it's wrong either. Maxime -- Maxime Ripard, Bootlin Embedded Linux and Kernel engineering https://bootlin.com
On Wed, Jun 5, 2019 at 12:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > Hi, > > I've reordered the mail a bit to work on chunks > > On Fri, May 24, 2019 at 03:37:42PM +0530, Jagan Teki wrote: > > > I wish it was in your commit log in the first place, instead of having > > > to exchange multiple mails over this. > > > > > > However, I don't think that's quite true, and it might be a bug in > > > Allwinner's implementation (or rather something quite confusing). > > > > > > You're right that the lcd_rate and pll_rate seem to be generated from > > > the pixel clock, and it indeed looks like the ratio between the pixel > > > clock and the TCON dotclock is defined through the number of bits per > > > lanes. > > > > > > However, in this case, dsi_rate is actually the same than lcd_rate, > > > since pll_rate is going to be divided by dsi_div: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > > > > > Since lcd_div is 1, it also means that in this case, dsi_rate == > > > dclk_rate. > > > > > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > > > we look at: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > > > > > We can see that the rate in clk_info is used if it's different than > > > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > > > DSI panel, will hardcode it to 148.5 MHz: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > > > Let me explain, something more. > > > > According to bsp there are clk_info.tcon_div which I will explain below. > > clk_info.dsi_div which is dynamic and it depends on bpp/lanes, so it > > is 6 for 24bpp and 4 lanes devices. > > > > PLL rate here depends on dsi_div (not tcon_div) > > > > Code here > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L784 > > > > is computing the actual set rate, which depends on dsi_rate. > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > dsi_rate = pll_rate / clk_info.dsi_div; > > > > Say if the dclk_rate 148MHz then the dsi_rate is 888MHz which set rate > > for above link you mentioned. > > > > Here are the evidence with some prints. > > > > https://gist.github.com/openedev/9bae2d87d2fcc06b999fe48c998b7043 > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > Ok, so we agree up to this point, and the prints confirm that the > analysis above is the right one. > > > > So, the DSI clock is set to this here: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > Your patch doesn't address that, so let's leave that one alone. Basically this is final pll set rate when sun4i_dotclock.c called the desired rate with ccu_nkm.c so it ended the final rate with parent as Line 8 of https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > The TCON *module* clock (the one in the clock controller) has been set > > > to lcd_rate (so the pixel clock times the number of bits per lane) here: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > > > > > And the PLL has been set to the same rate here: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > > > > > Let's take a step back now: that function we were looking at, > > > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > > > by disp_lcd_enable here: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > > > > > The next function being called is disp_al_lcd_cfg, and that function > > > will hardcode the TCON dotclock divider to 4, here: > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > > > tcon_div from BSP point-of-view of there are two variants > > 00) clk_info.tcon_div which is 4 and same is set the divider position > > in SUN4I_TCON0_DCLK_REG (like above link refer) > > 01) tcon_div which is 4 and used for edge timings computation > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > The real reason for 01) is again 4 is they set the divider to 4 in 00) > > which is technically wrong because the dividers which used during > > dotclock in above (dsi_div) should be used here as well. Since there > > is no dynamic way of doing this BSP hard-coding these values. > > > > Patches 5,6,7 on this series doing this > > https://patchwork.freedesktop.org/series/60847/ > > > > Hope this explanation helps? > > It doesn't. > > The clock tree is this one: > > PLL(s) -> TCON module clock -> TCON dotclock. > > The links I mentioned above show that the clock set to lcd_rate is the > TCON module clocks (and it should be the one taking the bpp and lanes > into account), while the TCON dotclock uses a fixed divider of 4. Sorry, I can argue much other-than giving some code snips, according to [1] 00) Line 785, 786 with dclk_rate 148000000 lcd_rate = dclk_rate * clk_info.dsi_div; pll_rate = lcd_rate * clk_info.lcd_div; Since dsi_div is 6 (bpp/lanes), lcd_div 1 lcd_rate = 888000000, pll_rate = 888000000 01) Line 801, 804 are final rates computed as per clock driver (say ccu_nkm in mainline) lcd_rate_set=891000000 As per your comments if it would be 4 then the desired numbers are would be 592000000 not 888000000. This is what I'm trying to say in all mails, and same as verified with 2-lanes devices as well where the dsi_div is 12 so the final rate is 290MHz * 12 > > In your patches, you're using the bpp / lanes divider on the TCON > dotclock, ie, the wrong clock. > > Again, I'm not saying that my analysis of the source code is correct > here. But you haven't said anything to prove it's wrong either. Don't understand what proves are remaining, I have explained each line from BSP and saying pll rate is depends on dsi_div which is bpp/lanes not wrt tcon_div on BSP (which is set to default 4) and which indeed verified in A33, R40. all the code using bpp/lanes. Please let me know if you need any more information to look? [1] https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805
On Wed, Jun 05, 2019 at 01:03:16PM +0530, Jagan Teki wrote: > On Wed, Jun 5, 2019 at 12:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > Hi, > > > > I've reordered the mail a bit to work on chunks > > > > On Fri, May 24, 2019 at 03:37:42PM +0530, Jagan Teki wrote: > > > > I wish it was in your commit log in the first place, instead of having > > > > to exchange multiple mails over this. > > > > > > > > However, I don't think that's quite true, and it might be a bug in > > > > Allwinner's implementation (or rather something quite confusing). > > > > > > > > You're right that the lcd_rate and pll_rate seem to be generated from > > > > the pixel clock, and it indeed looks like the ratio between the pixel > > > > clock and the TCON dotclock is defined through the number of bits per > > > > lanes. > > > > > > > > However, in this case, dsi_rate is actually the same than lcd_rate, > > > > since pll_rate is going to be divided by dsi_div: > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > > > > > > > Since lcd_div is 1, it also means that in this case, dsi_rate == > > > > dclk_rate. > > > > > > > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > > > > we look at: > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > > > > > > > We can see that the rate in clk_info is used if it's different than > > > > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > > > > DSI panel, will hardcode it to 148.5 MHz: > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > > > > > Let me explain, something more. > > > > > > According to bsp there are clk_info.tcon_div which I will explain below. > > > clk_info.dsi_div which is dynamic and it depends on bpp/lanes, so it > > > is 6 for 24bpp and 4 lanes devices. > > > > > > PLL rate here depends on dsi_div (not tcon_div) > > > > > > Code here > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L784 > > > > > > is computing the actual set rate, which depends on dsi_rate. > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > dsi_rate = pll_rate / clk_info.dsi_div; > > > > > > Say if the dclk_rate 148MHz then the dsi_rate is 888MHz which set rate > > > for above link you mentioned. > > > > > > Here are the evidence with some prints. > > > > > > https://gist.github.com/openedev/9bae2d87d2fcc06b999fe48c998b7043 > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > Ok, so we agree up to this point, and the prints confirm that the > > analysis above is the right one. > > > > > > So, the DSI clock is set to this here: > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > > > Your patch doesn't address that, so let's leave that one alone. > > Basically this is final pll set rate when sun4i_dotclock.c called the > desired rate with ccu_nkm.c so it ended the final rate with parent as > Line 8 of > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a If that's important to the driver, it should be set explicitly then, and not work by accident. > > > > The TCON *module* clock (the one in the clock controller) has been set > > > > to lcd_rate (so the pixel clock times the number of bits per lane) here: > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > > > > > > > And the PLL has been set to the same rate here: > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > > > > > > > Let's take a step back now: that function we were looking at, > > > > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > > > > by disp_lcd_enable here: > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > > > > > > > The next function being called is disp_al_lcd_cfg, and that function > > > > will hardcode the TCON dotclock divider to 4, here: > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > > > > > tcon_div from BSP point-of-view of there are two variants > > > 00) clk_info.tcon_div which is 4 and same is set the divider position > > > in SUN4I_TCON0_DCLK_REG (like above link refer) > > > 01) tcon_div which is 4 and used for edge timings computation > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > The real reason for 01) is again 4 is they set the divider to 4 in 00) > > > which is technically wrong because the dividers which used during > > > dotclock in above (dsi_div) should be used here as well. Since there > > > is no dynamic way of doing this BSP hard-coding these values. > > > > > > Patches 5,6,7 on this series doing this > > > https://patchwork.freedesktop.org/series/60847/ > > > > > > Hope this explanation helps? > > > > It doesn't. > > > > The clock tree is this one: > > > > PLL(s) -> TCON module clock -> TCON dotclock. > > > > The links I mentioned above show that the clock set to lcd_rate is the > > TCON module clocks (and it should be the one taking the bpp and lanes > > into account), while the TCON dotclock uses a fixed divider of 4. > > Sorry, I can argue much other-than giving some code snips, according to [1] > > 00) Line 785, 786 with dclk_rate 148000000 > > lcd_rate = dclk_rate * clk_info.dsi_div; > pll_rate = lcd_rate * clk_info.lcd_div; > > Since dsi_div is 6 (bpp/lanes), lcd_div 1 > > lcd_rate = 888000000, pll_rate = 888000000 > > 01) Line 801, 804 are final rates computed as per clock driver (say > ccu_nkm in mainline) > > lcd_rate_set=891000000 > > As per your comments if it would be 4 then the desired numbers are > would be 592000000 not 888000000. > > This is what I'm trying to say in all mails, and same as verified with > 2-lanes devices as well where the dsi_div is 12 so the final rate is > 290MHz * 12 In the code you sent, you're forcing a divider on the internal TCON clock, while that one is fixed in the BSP. There's indeed the bpp / lanes divider, but it's used in the *parent* clock of the one you're changing. And the dsi0_clk clock you pointed out in the code snippet is yet another clock, the MIPI DSI module clock. The analysis you have is probably correct, you're just not implementing it properly in your patch. Maxime -- Maxime Ripard, Bootlin Embedded Linux and Kernel engineering https://bootlin.com
On Fri, Jun 14, 2019 at 7:54 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Wed, Jun 05, 2019 at 01:03:16PM +0530, Jagan Teki wrote: > > On Wed, Jun 5, 2019 at 12:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > Hi, > > > > > > I've reordered the mail a bit to work on chunks > > > > > > On Fri, May 24, 2019 at 03:37:42PM +0530, Jagan Teki wrote: > > > > > I wish it was in your commit log in the first place, instead of having > > > > > to exchange multiple mails over this. > > > > > > > > > > However, I don't think that's quite true, and it might be a bug in > > > > > Allwinner's implementation (or rather something quite confusing). > > > > > > > > > > You're right that the lcd_rate and pll_rate seem to be generated from > > > > > the pixel clock, and it indeed looks like the ratio between the pixel > > > > > clock and the TCON dotclock is defined through the number of bits per > > > > > lanes. > > > > > > > > > > However, in this case, dsi_rate is actually the same than lcd_rate, > > > > > since pll_rate is going to be divided by dsi_div: > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > > > > > > > > > Since lcd_div is 1, it also means that in this case, dsi_rate == > > > > > dclk_rate. > > > > > > > > > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > > > > > we look at: > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > > > > > > > > > We can see that the rate in clk_info is used if it's different than > > > > > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > > > > > DSI panel, will hardcode it to 148.5 MHz: > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > > > > > > > Let me explain, something more. > > > > > > > > According to bsp there are clk_info.tcon_div which I will explain below. > > > > clk_info.dsi_div which is dynamic and it depends on bpp/lanes, so it > > > > is 6 for 24bpp and 4 lanes devices. > > > > > > > > PLL rate here depends on dsi_div (not tcon_div) > > > > > > > > Code here > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L784 > > > > > > > > is computing the actual set rate, which depends on dsi_rate. > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > dsi_rate = pll_rate / clk_info.dsi_div; > > > > > > > > Say if the dclk_rate 148MHz then the dsi_rate is 888MHz which set rate > > > > for above link you mentioned. > > > > > > > > Here are the evidence with some prints. > > > > > > > > https://gist.github.com/openedev/9bae2d87d2fcc06b999fe48c998b7043 > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > Ok, so we agree up to this point, and the prints confirm that the > > > analysis above is the right one. > > > > > > > > So, the DSI clock is set to this here: > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > > > > > Your patch doesn't address that, so let's leave that one alone. > > > > Basically this is final pll set rate when sun4i_dotclock.c called the > > desired rate with ccu_nkm.c so it ended the final rate with parent as > > Line 8 of > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > If that's important to the driver, it should be set explicitly then, > and not work by accident. > > > > > > The TCON *module* clock (the one in the clock controller) has been set > > > > > to lcd_rate (so the pixel clock times the number of bits per lane) here: > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > > > > > > > > > And the PLL has been set to the same rate here: > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > > > > > > > > > Let's take a step back now: that function we were looking at, > > > > > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > > > > > by disp_lcd_enable here: > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > > > > > > > > > The next function being called is disp_al_lcd_cfg, and that function > > > > > will hardcode the TCON dotclock divider to 4, here: > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > > > > > > > tcon_div from BSP point-of-view of there are two variants > > > > 00) clk_info.tcon_div which is 4 and same is set the divider position > > > > in SUN4I_TCON0_DCLK_REG (like above link refer) > > > > 01) tcon_div which is 4 and used for edge timings computation > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > > > The real reason for 01) is again 4 is they set the divider to 4 in 00) > > > > which is technically wrong because the dividers which used during > > > > dotclock in above (dsi_div) should be used here as well. Since there > > > > is no dynamic way of doing this BSP hard-coding these values. > > > > > > > > Patches 5,6,7 on this series doing this > > > > https://patchwork.freedesktop.org/series/60847/ > > > > > > > > Hope this explanation helps? > > > > > > It doesn't. > > > > > > The clock tree is this one: > > > > > > PLL(s) -> TCON module clock -> TCON dotclock. > > > > > > The links I mentioned above show that the clock set to lcd_rate is the > > > TCON module clocks (and it should be the one taking the bpp and lanes > > > into account), while the TCON dotclock uses a fixed divider of 4. > > > > Sorry, I can argue much other-than giving some code snips, according to [1] > > > > 00) Line 785, 786 with dclk_rate 148000000 > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > Since dsi_div is 6 (bpp/lanes), lcd_div 1 > > > > lcd_rate = 888000000, pll_rate = 888000000 > > > > 01) Line 801, 804 are final rates computed as per clock driver (say > > ccu_nkm in mainline) > > > > lcd_rate_set=891000000 > > > > As per your comments if it would be 4 then the desired numbers are > > would be 592000000 not 888000000. > > > > This is what I'm trying to say in all mails, and same as verified with > > 2-lanes devices as well where the dsi_div is 12 so the final rate is > > 290MHz * 12 > > In the code you sent, you're forcing a divider on the internal TCON > clock, while that one is fixed in the BSP. > > There's indeed the bpp / lanes divider, but it's used in the *parent* > clock of the one you're changing. > > And the dsi0_clk clock you pointed out in the code snippet is yet > another clock, the MIPI DSI module clock. Correct, look like I refereed wrong reference in the above mail. sorry for the noise. Actually I'm trying to explain about pll_rate here which indeed depends on dsi.div https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L786 lcd_rate = dclk_rate * clk_info.dsi_div; pll_rate = lcd_rate * clk_info.lcd_div; Say 1) For 148MHz dclk_rate with dsi_div is 6 (24/4) lcd_div is 1 which resulting pll_rate is 888MHz. 2) For 30MHz dclk_rate with 4 lane and 24 RGB the resulting pll_rate is 180MHz 3) For 27.5MHz dclk_rate with 2 lane and 24 RGB the resulting pll_rate is 330MHz Here is the few more logs in code, for case 2) [ 1.920441] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 [ 1.920505] ideal = 180000000, rounded = 178200000 [ 1.920509] sun4i_dclk_round_rate: div = 6 rate = 29700000 [ 1.920514] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 [ 1.920532] ideal = 180000000, rounded = 178200000 [ 1.920535] sun4i_dclk_round_rate: div = 6 rate = 29700000 [ 1.920572] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 [ 1.920576] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 [ 1.920597] rate = 178200000 [ 1.920599] parent_rate = 297000000 [ 1.920602] reg = 0x90c00000 [ 1.920605] _nkm.n = 3, nkm->n.offset = 0x1, nkm->n.shift = 8 [ 1.920609] _nkm.k = 2, nkm->k.offset = 0x1, nkm->k.shift = 4 [ 1.920612] _nkm.m = 10, nkm->m.offset = 0x1, nkm->m.shift = 0 [ 1.920958] sun4i_dclk_set_rate div 6 [ 1.920966] sun4i_dclk_recalc_rate: val = 6, rate = 29700000 and clk_summary: pll-video0 1 1 1 297000000 0 0 50000 hdmi 0 0 0 297000000 0 0 50000 tcon1 0 0 0 297000000 0 0 50000 pll-mipi 1 1 1 178200000 0 0 50000 tcon0 2 2 1 178200000 0 0 50000 tcon-pixel-clock 1 1 1 29700000 0 0 50000 pll-video0-2x 0 0 0 594000000 0 0 50000
On Thu, Jun 20, 2019 at 11:57:44PM +0530, Jagan Teki wrote: > On Fri, Jun 14, 2019 at 7:54 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > On Wed, Jun 05, 2019 at 01:03:16PM +0530, Jagan Teki wrote: > > > On Wed, Jun 5, 2019 at 12:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > Hi, > > > > > > > > I've reordered the mail a bit to work on chunks > > > > > > > > On Fri, May 24, 2019 at 03:37:42PM +0530, Jagan Teki wrote: > > > > > > I wish it was in your commit log in the first place, instead of having > > > > > > to exchange multiple mails over this. > > > > > > > > > > > > However, I don't think that's quite true, and it might be a bug in > > > > > > Allwinner's implementation (or rather something quite confusing). > > > > > > > > > > > > You're right that the lcd_rate and pll_rate seem to be generated from > > > > > > the pixel clock, and it indeed looks like the ratio between the pixel > > > > > > clock and the TCON dotclock is defined through the number of bits per > > > > > > lanes. > > > > > > > > > > > > However, in this case, dsi_rate is actually the same than lcd_rate, > > > > > > since pll_rate is going to be divided by dsi_div: > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > > > > > > > > > > > Since lcd_div is 1, it also means that in this case, dsi_rate == > > > > > > dclk_rate. > > > > > > > > > > > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > > > > > > we look at: > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > > > > > > > > > > > We can see that the rate in clk_info is used if it's different than > > > > > > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > > > > > > DSI panel, will hardcode it to 148.5 MHz: > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > > > > > > > > > Let me explain, something more. > > > > > > > > > > According to bsp there are clk_info.tcon_div which I will explain below. > > > > > clk_info.dsi_div which is dynamic and it depends on bpp/lanes, so it > > > > > is 6 for 24bpp and 4 lanes devices. > > > > > > > > > > PLL rate here depends on dsi_div (not tcon_div) > > > > > > > > > > Code here > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L784 > > > > > > > > > > is computing the actual set rate, which depends on dsi_rate. > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > dsi_rate = pll_rate / clk_info.dsi_div; > > > > > > > > > > Say if the dclk_rate 148MHz then the dsi_rate is 888MHz which set rate > > > > > for above link you mentioned. > > > > > > > > > > Here are the evidence with some prints. > > > > > > > > > > https://gist.github.com/openedev/9bae2d87d2fcc06b999fe48c998b7043 > > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > > > Ok, so we agree up to this point, and the prints confirm that the > > > > analysis above is the right one. > > > > > > > > > > So, the DSI clock is set to this here: > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > > > > > > > Your patch doesn't address that, so let's leave that one alone. > > > > > > Basically this is final pll set rate when sun4i_dotclock.c called the > > > desired rate with ccu_nkm.c so it ended the final rate with parent as > > > Line 8 of > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > If that's important to the driver, it should be set explicitly then, > > and not work by accident. > > > > > > > > The TCON *module* clock (the one in the clock controller) has been set > > > > > > to lcd_rate (so the pixel clock times the number of bits per lane) here: > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > > > > > > > > > > > And the PLL has been set to the same rate here: > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > > > > > > > > > > > Let's take a step back now: that function we were looking at, > > > > > > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > > > > > > by disp_lcd_enable here: > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > > > > > > > > > > > The next function being called is disp_al_lcd_cfg, and that function > > > > > > will hardcode the TCON dotclock divider to 4, here: > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > > > > > > > > > tcon_div from BSP point-of-view of there are two variants > > > > > 00) clk_info.tcon_div which is 4 and same is set the divider position > > > > > in SUN4I_TCON0_DCLK_REG (like above link refer) > > > > > 01) tcon_div which is 4 and used for edge timings computation > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > > > > > The real reason for 01) is again 4 is they set the divider to 4 in 00) > > > > > which is technically wrong because the dividers which used during > > > > > dotclock in above (dsi_div) should be used here as well. Since there > > > > > is no dynamic way of doing this BSP hard-coding these values. > > > > > > > > > > Patches 5,6,7 on this series doing this > > > > > https://patchwork.freedesktop.org/series/60847/ > > > > > > > > > > Hope this explanation helps? > > > > > > > > It doesn't. > > > > > > > > The clock tree is this one: > > > > > > > > PLL(s) -> TCON module clock -> TCON dotclock. > > > > > > > > The links I mentioned above show that the clock set to lcd_rate is the > > > > TCON module clocks (and it should be the one taking the bpp and lanes > > > > into account), while the TCON dotclock uses a fixed divider of 4. > > > > > > Sorry, I can argue much other-than giving some code snips, according to [1] > > > > > > 00) Line 785, 786 with dclk_rate 148000000 > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > > > Since dsi_div is 6 (bpp/lanes), lcd_div 1 > > > > > > lcd_rate = 888000000, pll_rate = 888000000 > > > > > > 01) Line 801, 804 are final rates computed as per clock driver (say > > > ccu_nkm in mainline) > > > > > > lcd_rate_set=891000000 > > > > > > As per your comments if it would be 4 then the desired numbers are > > > would be 592000000 not 888000000. > > > > > > This is what I'm trying to say in all mails, and same as verified with > > > 2-lanes devices as well where the dsi_div is 12 so the final rate is > > > 290MHz * 12 > > > > In the code you sent, you're forcing a divider on the internal TCON > > clock, while that one is fixed in the BSP. > > > > There's indeed the bpp / lanes divider, but it's used in the *parent* > > clock of the one you're changing. > > > > And the dsi0_clk clock you pointed out in the code snippet is yet > > another clock, the MIPI DSI module clock. > > Correct, look like I refereed wrong reference in the above mail. sorry > for the noise. > > Actually I'm trying to explain about pll_rate here which indeed > depends on dsi.div > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L786 > > lcd_rate = dclk_rate * clk_info.dsi_div; > pll_rate = lcd_rate * clk_info.lcd_div; > > Say > > 1) For 148MHz dclk_rate with dsi_div is 6 (24/4) lcd_div is 1 which > resulting pll_rate is 888MHz. > > 2) For 30MHz dclk_rate with 4 lane and 24 RGB the resulting pll_rate is 180MHz > > 3) For 27.5MHz dclk_rate with 2 lane and 24 RGB the resulting pll_rate is 330MHz > > Here is the few more logs in code, for case 2) > > [ 1.920441] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > [ 1.920505] ideal = 180000000, rounded = 178200000 > [ 1.920509] sun4i_dclk_round_rate: div = 6 rate = 29700000 > [ 1.920514] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > [ 1.920532] ideal = 180000000, rounded = 178200000 > [ 1.920535] sun4i_dclk_round_rate: div = 6 rate = 29700000 > [ 1.920572] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > [ 1.920576] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > [ 1.920597] rate = 178200000 > [ 1.920599] parent_rate = 297000000 > [ 1.920602] reg = 0x90c00000 > [ 1.920605] _nkm.n = 3, nkm->n.offset = 0x1, nkm->n.shift = 8 > [ 1.920609] _nkm.k = 2, nkm->k.offset = 0x1, nkm->k.shift = 4 > [ 1.920612] _nkm.m = 10, nkm->m.offset = 0x1, nkm->m.shift = 0 > [ 1.920958] sun4i_dclk_set_rate div 6 > [ 1.920966] sun4i_dclk_recalc_rate: val = 6, rate = 29700000 > > and clk_summary: > > pll-video0 1 1 1 297000000 > 0 0 50000 > hdmi 0 0 0 297000000 > 0 0 50000 > tcon1 0 0 0 297000000 > 0 0 50000 > pll-mipi 1 1 1 178200000 > 0 0 50000 > tcon0 2 2 1 178200000 > 0 0 50000 > tcon-pixel-clock 1 1 1 29700000 > 0 0 50000 > pll-video0-2x 0 0 0 594000000 > 0 0 50000 This discussion is going nowhere. I'm telling you that your patch doesn't apply the divider you want on the proper clock, and you're replying that indeed, you're applying it on the wrong clock. It might work by accident in your case, but the board I have here clearly indicates otherwise, so there's two possible way out here: - Either you apply that divider to the TCON *module* clock, and not the dclk - Or you point to somewhere in the allwinner code where the bpp / lanes divider is used for the dclk divider. Maxim -- Maxime Ripard, Bootlin Embedded Linux and Kernel engineering https://bootlin.com
On Tue, Jun 25, 2019 at 8:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Thu, Jun 20, 2019 at 11:57:44PM +0530, Jagan Teki wrote: > > On Fri, Jun 14, 2019 at 7:54 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > On Wed, Jun 05, 2019 at 01:03:16PM +0530, Jagan Teki wrote: > > > > On Wed, Jun 5, 2019 at 12:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > Hi, > > > > > > > > > > I've reordered the mail a bit to work on chunks > > > > > > > > > > On Fri, May 24, 2019 at 03:37:42PM +0530, Jagan Teki wrote: > > > > > > > I wish it was in your commit log in the first place, instead of having > > > > > > > to exchange multiple mails over this. > > > > > > > > > > > > > > However, I don't think that's quite true, and it might be a bug in > > > > > > > Allwinner's implementation (or rather something quite confusing). > > > > > > > > > > > > > > You're right that the lcd_rate and pll_rate seem to be generated from > > > > > > > the pixel clock, and it indeed looks like the ratio between the pixel > > > > > > > clock and the TCON dotclock is defined through the number of bits per > > > > > > > lanes. > > > > > > > > > > > > > > However, in this case, dsi_rate is actually the same than lcd_rate, > > > > > > > since pll_rate is going to be divided by dsi_div: > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > > > > > > > > > > > > > Since lcd_div is 1, it also means that in this case, dsi_rate == > > > > > > > dclk_rate. > > > > > > > > > > > > > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > > > > > > > we look at: > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > > > > > > > > > > > > > We can see that the rate in clk_info is used if it's different than > > > > > > > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > > > > > > > DSI panel, will hardcode it to 148.5 MHz: > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > > > > > > > > > > > Let me explain, something more. > > > > > > > > > > > > According to bsp there are clk_info.tcon_div which I will explain below. > > > > > > clk_info.dsi_div which is dynamic and it depends on bpp/lanes, so it > > > > > > is 6 for 24bpp and 4 lanes devices. > > > > > > > > > > > > PLL rate here depends on dsi_div (not tcon_div) > > > > > > > > > > > > Code here > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L784 > > > > > > > > > > > > is computing the actual set rate, which depends on dsi_rate. > > > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > > dsi_rate = pll_rate / clk_info.dsi_div; > > > > > > > > > > > > Say if the dclk_rate 148MHz then the dsi_rate is 888MHz which set rate > > > > > > for above link you mentioned. > > > > > > > > > > > > Here are the evidence with some prints. > > > > > > > > > > > > https://gist.github.com/openedev/9bae2d87d2fcc06b999fe48c998b7043 > > > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > > > > > Ok, so we agree up to this point, and the prints confirm that the > > > > > analysis above is the right one. > > > > > > > > > > > > So, the DSI clock is set to this here: > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > > > > > > > > > Your patch doesn't address that, so let's leave that one alone. > > > > > > > > Basically this is final pll set rate when sun4i_dotclock.c called the > > > > desired rate with ccu_nkm.c so it ended the final rate with parent as > > > > Line 8 of > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > If that's important to the driver, it should be set explicitly then, > > > and not work by accident. > > > > > > > > > > The TCON *module* clock (the one in the clock controller) has been set > > > > > > > to lcd_rate (so the pixel clock times the number of bits per lane) here: > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > > > > > > > > > > > > > And the PLL has been set to the same rate here: > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > > > > > > > > > > > > > Let's take a step back now: that function we were looking at, > > > > > > > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > > > > > > > by disp_lcd_enable here: > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > > > > > > > > > > > > > The next function being called is disp_al_lcd_cfg, and that function > > > > > > > will hardcode the TCON dotclock divider to 4, here: > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > > > > > > > > > > > tcon_div from BSP point-of-view of there are two variants > > > > > > 00) clk_info.tcon_div which is 4 and same is set the divider position > > > > > > in SUN4I_TCON0_DCLK_REG (like above link refer) > > > > > > 01) tcon_div which is 4 and used for edge timings computation > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > > > > > > > The real reason for 01) is again 4 is they set the divider to 4 in 00) > > > > > > which is technically wrong because the dividers which used during > > > > > > dotclock in above (dsi_div) should be used here as well. Since there > > > > > > is no dynamic way of doing this BSP hard-coding these values. > > > > > > > > > > > > Patches 5,6,7 on this series doing this > > > > > > https://patchwork.freedesktop.org/series/60847/ > > > > > > > > > > > > Hope this explanation helps? > > > > > > > > > > It doesn't. > > > > > > > > > > The clock tree is this one: > > > > > > > > > > PLL(s) -> TCON module clock -> TCON dotclock. > > > > > > > > > > The links I mentioned above show that the clock set to lcd_rate is the > > > > > TCON module clocks (and it should be the one taking the bpp and lanes > > > > > into account), while the TCON dotclock uses a fixed divider of 4. > > > > > > > > Sorry, I can argue much other-than giving some code snips, according to [1] > > > > > > > > 00) Line 785, 786 with dclk_rate 148000000 > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > > > > > Since dsi_div is 6 (bpp/lanes), lcd_div 1 > > > > > > > > lcd_rate = 888000000, pll_rate = 888000000 > > > > > > > > 01) Line 801, 804 are final rates computed as per clock driver (say > > > > ccu_nkm in mainline) > > > > > > > > lcd_rate_set=891000000 > > > > > > > > As per your comments if it would be 4 then the desired numbers are > > > > would be 592000000 not 888000000. > > > > > > > > This is what I'm trying to say in all mails, and same as verified with > > > > 2-lanes devices as well where the dsi_div is 12 so the final rate is > > > > 290MHz * 12 > > > > > > In the code you sent, you're forcing a divider on the internal TCON > > > clock, while that one is fixed in the BSP. > > > > > > There's indeed the bpp / lanes divider, but it's used in the *parent* > > > clock of the one you're changing. > > > > > > And the dsi0_clk clock you pointed out in the code snippet is yet > > > another clock, the MIPI DSI module clock. > > > > Correct, look like I refereed wrong reference in the above mail. sorry > > for the noise. > > > > Actually I'm trying to explain about pll_rate here which indeed > > depends on dsi.div > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L786 > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > Say > > > > 1) For 148MHz dclk_rate with dsi_div is 6 (24/4) lcd_div is 1 which > > resulting pll_rate is 888MHz. > > > > 2) For 30MHz dclk_rate with 4 lane and 24 RGB the resulting pll_rate is 180MHz > > > > 3) For 27.5MHz dclk_rate with 2 lane and 24 RGB the resulting pll_rate is 330MHz > > > > Here is the few more logs in code, for case 2) > > > > [ 1.920441] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > > [ 1.920505] ideal = 180000000, rounded = 178200000 > > [ 1.920509] sun4i_dclk_round_rate: div = 6 rate = 29700000 > > [ 1.920514] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > > [ 1.920532] ideal = 180000000, rounded = 178200000 > > [ 1.920535] sun4i_dclk_round_rate: div = 6 rate = 29700000 > > [ 1.920572] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > > [ 1.920576] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > > [ 1.920597] rate = 178200000 > > [ 1.920599] parent_rate = 297000000 > > [ 1.920602] reg = 0x90c00000 > > [ 1.920605] _nkm.n = 3, nkm->n.offset = 0x1, nkm->n.shift = 8 > > [ 1.920609] _nkm.k = 2, nkm->k.offset = 0x1, nkm->k.shift = 4 > > [ 1.920612] _nkm.m = 10, nkm->m.offset = 0x1, nkm->m.shift = 0 > > [ 1.920958] sun4i_dclk_set_rate div 6 > > [ 1.920966] sun4i_dclk_recalc_rate: val = 6, rate = 29700000 > > > > and clk_summary: > > > > pll-video0 1 1 1 297000000 > > 0 0 50000 > > hdmi 0 0 0 297000000 > > 0 0 50000 > > tcon1 0 0 0 297000000 > > 0 0 50000 > > pll-mipi 1 1 1 178200000 > > 0 0 50000 > > tcon0 2 2 1 178200000 > > 0 0 50000 > > tcon-pixel-clock 1 1 1 29700000 > > 0 0 50000 > > pll-video0-2x 0 0 0 594000000 > > 0 0 50000 > > This discussion is going nowhere. I'm telling you that your patch > doesn't apply the divider you want on the proper clock, and you're > replying that indeed, you're applying it on the wrong clock. > > It might work by accident in your case, but the board I have here > clearly indicates otherwise, so there's two possible way out here: > > - Either you apply that divider to the TCON *module* clock, and not > the dclk > > - Or you point to somewhere in the allwinner code where the bpp / > lanes divider is used for the dclk divider. I don't know how to proceed further on this, as you say it might work in accident but I have tested this in A33, A64 and R40 with 4 different DSI panels and one DSI-RGB bridge. All of them do use PLL_MIPI (pll_rate) and it indeed depends on bpp/lanes 4-lane, 24-bit: Novatek NT35596 panel 4-lane, 24-bit: Feiyang, FY07024di26a30d panel 4-lane, 24-bit: Bananapi-s070wv20 panel 2-lane, 24-bit: Techstar,ts8550b panel and 4-lane, 24-bit, ICN6211 DSI-to-RGB bridge panel All above listed panels and bridges are working as per BSP and do follow bpp/lanes and for DIVIDER 4 no panel is working. The panels/bridges I have has tested in BSP and as you mentioned in another mail, your panel is not tested in BSP - this is the only difference. I did much reverse-engineering on PLL_MIPI clocking in BSP so I'm afraid what can I do next on this, If you want to look further on BSP I would suggest to verify on pll_rate side. If you feel anything I'm missing please let me know. Jagan.
On Tue, Jun 25, 2019 at 09:00:36PM +0530, Jagan Teki wrote: > On Tue, Jun 25, 2019 at 8:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > On Thu, Jun 20, 2019 at 11:57:44PM +0530, Jagan Teki wrote: > > > On Fri, Jun 14, 2019 at 7:54 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > On Wed, Jun 05, 2019 at 01:03:16PM +0530, Jagan Teki wrote: > > > > > On Wed, Jun 5, 2019 at 12:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > Hi, > > > > > > > > > > > > I've reordered the mail a bit to work on chunks > > > > > > > > > > > > On Fri, May 24, 2019 at 03:37:42PM +0530, Jagan Teki wrote: > > > > > > > > I wish it was in your commit log in the first place, instead of having > > > > > > > > to exchange multiple mails over this. > > > > > > > > > > > > > > > > However, I don't think that's quite true, and it might be a bug in > > > > > > > > Allwinner's implementation (or rather something quite confusing). > > > > > > > > > > > > > > > > You're right that the lcd_rate and pll_rate seem to be generated from > > > > > > > > the pixel clock, and it indeed looks like the ratio between the pixel > > > > > > > > clock and the TCON dotclock is defined through the number of bits per > > > > > > > > lanes. > > > > > > > > > > > > > > > > However, in this case, dsi_rate is actually the same than lcd_rate, > > > > > > > > since pll_rate is going to be divided by dsi_div: > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > > > > > > > > > > > > > > > Since lcd_div is 1, it also means that in this case, dsi_rate == > > > > > > > > dclk_rate. > > > > > > > > > > > > > > > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > > > > > > > > we look at: > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > > > > > > > > > > > > > > > We can see that the rate in clk_info is used if it's different than > > > > > > > > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > > > > > > > > DSI panel, will hardcode it to 148.5 MHz: > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > > > > > > > > > > > > > Let me explain, something more. > > > > > > > > > > > > > > According to bsp there are clk_info.tcon_div which I will explain below. > > > > > > > clk_info.dsi_div which is dynamic and it depends on bpp/lanes, so it > > > > > > > is 6 for 24bpp and 4 lanes devices. > > > > > > > > > > > > > > PLL rate here depends on dsi_div (not tcon_div) > > > > > > > > > > > > > > Code here > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L784 > > > > > > > > > > > > > > is computing the actual set rate, which depends on dsi_rate. > > > > > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > > > dsi_rate = pll_rate / clk_info.dsi_div; > > > > > > > > > > > > > > Say if the dclk_rate 148MHz then the dsi_rate is 888MHz which set rate > > > > > > > for above link you mentioned. > > > > > > > > > > > > > > Here are the evidence with some prints. > > > > > > > > > > > > > > https://gist.github.com/openedev/9bae2d87d2fcc06b999fe48c998b7043 > > > > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > > > > > > > Ok, so we agree up to this point, and the prints confirm that the > > > > > > analysis above is the right one. > > > > > > > > > > > > > > So, the DSI clock is set to this here: > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > > > > > > > > > > > Your patch doesn't address that, so let's leave that one alone. > > > > > > > > > > Basically this is final pll set rate when sun4i_dotclock.c called the > > > > > desired rate with ccu_nkm.c so it ended the final rate with parent as > > > > > Line 8 of > > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > > > If that's important to the driver, it should be set explicitly then, > > > > and not work by accident. > > > > > > > > > > > > The TCON *module* clock (the one in the clock controller) has been set > > > > > > > > to lcd_rate (so the pixel clock times the number of bits per lane) here: > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > > > > > > > > > > > > > > > And the PLL has been set to the same rate here: > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > > > > > > > > > > > > > > > Let's take a step back now: that function we were looking at, > > > > > > > > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > > > > > > > > by disp_lcd_enable here: > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > > > > > > > > > > > > > > > The next function being called is disp_al_lcd_cfg, and that function > > > > > > > > will hardcode the TCON dotclock divider to 4, here: > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > > > > > > > > > > > > > tcon_div from BSP point-of-view of there are two variants > > > > > > > 00) clk_info.tcon_div which is 4 and same is set the divider position > > > > > > > in SUN4I_TCON0_DCLK_REG (like above link refer) > > > > > > > 01) tcon_div which is 4 and used for edge timings computation > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > > > > > > > > > The real reason for 01) is again 4 is they set the divider to 4 in 00) > > > > > > > which is technically wrong because the dividers which used during > > > > > > > dotclock in above (dsi_div) should be used here as well. Since there > > > > > > > is no dynamic way of doing this BSP hard-coding these values. > > > > > > > > > > > > > > Patches 5,6,7 on this series doing this > > > > > > > https://patchwork.freedesktop.org/series/60847/ > > > > > > > > > > > > > > Hope this explanation helps? > > > > > > > > > > > > It doesn't. > > > > > > > > > > > > The clock tree is this one: > > > > > > > > > > > > PLL(s) -> TCON module clock -> TCON dotclock. > > > > > > > > > > > > The links I mentioned above show that the clock set to lcd_rate is the > > > > > > TCON module clocks (and it should be the one taking the bpp and lanes > > > > > > into account), while the TCON dotclock uses a fixed divider of 4. > > > > > > > > > > Sorry, I can argue much other-than giving some code snips, according to [1] > > > > > > > > > > 00) Line 785, 786 with dclk_rate 148000000 > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > > > > > > > Since dsi_div is 6 (bpp/lanes), lcd_div 1 > > > > > > > > > > lcd_rate = 888000000, pll_rate = 888000000 > > > > > > > > > > 01) Line 801, 804 are final rates computed as per clock driver (say > > > > > ccu_nkm in mainline) > > > > > > > > > > lcd_rate_set=891000000 > > > > > > > > > > As per your comments if it would be 4 then the desired numbers are > > > > > would be 592000000 not 888000000. > > > > > > > > > > This is what I'm trying to say in all mails, and same as verified with > > > > > 2-lanes devices as well where the dsi_div is 12 so the final rate is > > > > > 290MHz * 12 > > > > > > > > In the code you sent, you're forcing a divider on the internal TCON > > > > clock, while that one is fixed in the BSP. > > > > > > > > There's indeed the bpp / lanes divider, but it's used in the *parent* > > > > clock of the one you're changing. > > > > > > > > And the dsi0_clk clock you pointed out in the code snippet is yet > > > > another clock, the MIPI DSI module clock. > > > > > > Correct, look like I refereed wrong reference in the above mail. sorry > > > for the noise. > > > > > > Actually I'm trying to explain about pll_rate here which indeed > > > depends on dsi.div > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L786 > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > > > Say > > > > > > 1) For 148MHz dclk_rate with dsi_div is 6 (24/4) lcd_div is 1 which > > > resulting pll_rate is 888MHz. > > > > > > 2) For 30MHz dclk_rate with 4 lane and 24 RGB the resulting pll_rate is 180MHz > > > > > > 3) For 27.5MHz dclk_rate with 2 lane and 24 RGB the resulting pll_rate is 330MHz > > > > > > Here is the few more logs in code, for case 2) > > > > > > [ 1.920441] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > > > [ 1.920505] ideal = 180000000, rounded = 178200000 > > > [ 1.920509] sun4i_dclk_round_rate: div = 6 rate = 29700000 > > > [ 1.920514] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > > > [ 1.920532] ideal = 180000000, rounded = 178200000 > > > [ 1.920535] sun4i_dclk_round_rate: div = 6 rate = 29700000 > > > [ 1.920572] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > > > [ 1.920576] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > > > [ 1.920597] rate = 178200000 > > > [ 1.920599] parent_rate = 297000000 > > > [ 1.920602] reg = 0x90c00000 > > > [ 1.920605] _nkm.n = 3, nkm->n.offset = 0x1, nkm->n.shift = 8 > > > [ 1.920609] _nkm.k = 2, nkm->k.offset = 0x1, nkm->k.shift = 4 > > > [ 1.920612] _nkm.m = 10, nkm->m.offset = 0x1, nkm->m.shift = 0 > > > [ 1.920958] sun4i_dclk_set_rate div 6 > > > [ 1.920966] sun4i_dclk_recalc_rate: val = 6, rate = 29700000 > > > > > > and clk_summary: > > > > > > pll-video0 1 1 1 297000000 > > > 0 0 50000 > > > hdmi 0 0 0 297000000 > > > 0 0 50000 > > > tcon1 0 0 0 297000000 > > > 0 0 50000 > > > pll-mipi 1 1 1 178200000 > > > 0 0 50000 > > > tcon0 2 2 1 178200000 > > > 0 0 50000 > > > tcon-pixel-clock 1 1 1 29700000 > > > 0 0 50000 > > > pll-video0-2x 0 0 0 594000000 > > > 0 0 50000 > > > > This discussion is going nowhere. I'm telling you that your patch > > doesn't apply the divider you want on the proper clock, and you're > > replying that indeed, you're applying it on the wrong clock. > > > > It might work by accident in your case, but the board I have here > > clearly indicates otherwise, so there's two possible way out here: > > > > - Either you apply that divider to the TCON *module* clock, and not > > the dclk > > > > - Or you point to somewhere in the allwinner code where the bpp / > > lanes divider is used for the dclk divider. > > I don't know how to proceed further on this, as you say it might work > in accident but I have tested this in A33, A64 and R40 with 4 > different DSI panels and one DSI-RGB bridge. All of them do use > PLL_MIPI (pll_rate) and it indeed depends on bpp/lanes > > 4-lane, 24-bit: Novatek NT35596 panel > 4-lane, 24-bit: Feiyang, FY07024di26a30d panel > 4-lane, 24-bit: Bananapi-s070wv20 panel > 2-lane, 24-bit: Techstar,ts8550b panel > > and > > 4-lane, 24-bit, ICN6211 DSI-to-RGB bridge panel > > All above listed panels and bridges are working as per BSP and do > follow bpp/lanes and for DIVIDER 4 no panel is working. Look. I'm not saying that there's no issue, I'm saying that your patch, applied to the clock you're applying it to, doesn't make sense and isn't what the BSP does. You can keep on arguing that your patch is perfect as is, but the fact that there's regressions proves otherwise. > The panels/bridges I have has tested in BSP and as you mentioned in > another mail, your panel is not tested in BSP - this is the only > difference. I did much reverse-engineering on PLL_MIPI clocking in BSP > so I'm afraid what can I do next on this, If you want to look further > on BSP I would suggest to verify on pll_rate side. If you feel > anything I'm missing please let me know. I already told you how we can make some progress in the mail you quoted, but you chose to ignore that. Until there's been some progress on either points mentionned above, I'm just going to stop answering on this topic. Maxime -- Maxime Ripard, Bootlin Embedded Linux and Kernel engineering https://bootlin.com
Hi Maxime On Wed, Jul 3, 2019 at 1:49 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Tue, Jun 25, 2019 at 09:00:36PM +0530, Jagan Teki wrote: > > On Tue, Jun 25, 2019 at 8:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > On Thu, Jun 20, 2019 at 11:57:44PM +0530, Jagan Teki wrote: > > > > On Fri, Jun 14, 2019 at 7:54 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > On Wed, Jun 05, 2019 at 01:03:16PM +0530, Jagan Teki wrote: > > > > > > On Wed, Jun 5, 2019 at 12:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > > > Hi, > > > > > > > > > > > > > > I've reordered the mail a bit to work on chunks > > > > > > > > > > > > > > On Fri, May 24, 2019 at 03:37:42PM +0530, Jagan Teki wrote: > > > > > > > > > I wish it was in your commit log in the first place, instead of having > > > > > > > > > to exchange multiple mails over this. > > > > > > > > > > > > > > > > > > However, I don't think that's quite true, and it might be a bug in > > > > > > > > > Allwinner's implementation (or rather something quite confusing). > > > > > > > > > > > > > > > > > > You're right that the lcd_rate and pll_rate seem to be generated from > > > > > > > > > the pixel clock, and it indeed looks like the ratio between the pixel > > > > > > > > > clock and the TCON dotclock is defined through the number of bits per > > > > > > > > > lanes. > > > > > > > > > > > > > > > > > > However, in this case, dsi_rate is actually the same than lcd_rate, > > > > > > > > > since pll_rate is going to be divided by dsi_div: > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > > > > > > > > > > > > > > > > > Since lcd_div is 1, it also means that in this case, dsi_rate == > > > > > > > > > dclk_rate. > > > > > > > > > > > > > > > > > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > > > > > > > > > we look at: > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > > > > > > > > > > > > > > > > > We can see that the rate in clk_info is used if it's different than > > > > > > > > > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > > > > > > > > > DSI panel, will hardcode it to 148.5 MHz: > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > > > > > > > > > > > > > > > Let me explain, something more. > > > > > > > > > > > > > > > > According to bsp there are clk_info.tcon_div which I will explain below. > > > > > > > > clk_info.dsi_div which is dynamic and it depends on bpp/lanes, so it > > > > > > > > is 6 for 24bpp and 4 lanes devices. > > > > > > > > > > > > > > > > PLL rate here depends on dsi_div (not tcon_div) > > > > > > > > > > > > > > > > Code here > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L784 > > > > > > > > > > > > > > > > is computing the actual set rate, which depends on dsi_rate. > > > > > > > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > > > > dsi_rate = pll_rate / clk_info.dsi_div; > > > > > > > > > > > > > > > > Say if the dclk_rate 148MHz then the dsi_rate is 888MHz which set rate > > > > > > > > for above link you mentioned. > > > > > > > > > > > > > > > > Here are the evidence with some prints. > > > > > > > > > > > > > > > > https://gist.github.com/openedev/9bae2d87d2fcc06b999fe48c998b7043 > > > > > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > > > > > > > > > Ok, so we agree up to this point, and the prints confirm that the > > > > > > > analysis above is the right one. > > > > > > > > > > > > > > > > So, the DSI clock is set to this here: > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > > > > > > > > > > > > > Your patch doesn't address that, so let's leave that one alone. > > > > > > > > > > > > Basically this is final pll set rate when sun4i_dotclock.c called the > > > > > > desired rate with ccu_nkm.c so it ended the final rate with parent as > > > > > > Line 8 of > > > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > > > > > If that's important to the driver, it should be set explicitly then, > > > > > and not work by accident. > > > > > > > > > > > > > > The TCON *module* clock (the one in the clock controller) has been set > > > > > > > > > to lcd_rate (so the pixel clock times the number of bits per lane) here: > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > > > > > > > > > > > > > > > > > And the PLL has been set to the same rate here: > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > > > > > > > > > > > > > > > > > Let's take a step back now: that function we were looking at, > > > > > > > > > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > > > > > > > > > by disp_lcd_enable here: > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > > > > > > > > > > > > > > > > > The next function being called is disp_al_lcd_cfg, and that function > > > > > > > > > will hardcode the TCON dotclock divider to 4, here: > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > > > > > > > > > > > > > > > tcon_div from BSP point-of-view of there are two variants > > > > > > > > 00) clk_info.tcon_div which is 4 and same is set the divider position > > > > > > > > in SUN4I_TCON0_DCLK_REG (like above link refer) > > > > > > > > 01) tcon_div which is 4 and used for edge timings computation > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > > > > > > > > > > > The real reason for 01) is again 4 is they set the divider to 4 in 00) > > > > > > > > which is technically wrong because the dividers which used during > > > > > > > > dotclock in above (dsi_div) should be used here as well. Since there > > > > > > > > is no dynamic way of doing this BSP hard-coding these values. > > > > > > > > > > > > > > > > Patches 5,6,7 on this series doing this > > > > > > > > https://patchwork.freedesktop.org/series/60847/ > > > > > > > > > > > > > > > > Hope this explanation helps? > > > > > > > > > > > > > > It doesn't. > > > > > > > > > > > > > > The clock tree is this one: > > > > > > > > > > > > > > PLL(s) -> TCON module clock -> TCON dotclock. > > > > > > > > > > > > > > The links I mentioned above show that the clock set to lcd_rate is the > > > > > > > TCON module clocks (and it should be the one taking the bpp and lanes > > > > > > > into account), while the TCON dotclock uses a fixed divider of 4. > > > > > > > > > > > > Sorry, I can argue much other-than giving some code snips, according to [1] > > > > > > > > > > > > 00) Line 785, 786 with dclk_rate 148000000 > > > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > > > > > > > > > Since dsi_div is 6 (bpp/lanes), lcd_div 1 > > > > > > > > > > > > lcd_rate = 888000000, pll_rate = 888000000 > > > > > > > > > > > > 01) Line 801, 804 are final rates computed as per clock driver (say > > > > > > ccu_nkm in mainline) > > > > > > > > > > > > lcd_rate_set=891000000 > > > > > > > > > > > > As per your comments if it would be 4 then the desired numbers are > > > > > > would be 592000000 not 888000000. > > > > > > > > > > > > This is what I'm trying to say in all mails, and same as verified with > > > > > > 2-lanes devices as well where the dsi_div is 12 so the final rate is > > > > > > 290MHz * 12 > > > > > > > > > > In the code you sent, you're forcing a divider on the internal TCON > > > > > clock, while that one is fixed in the BSP. > > > > > > > > > > There's indeed the bpp / lanes divider, but it's used in the *parent* > > > > > clock of the one you're changing. > > > > > > > > > > And the dsi0_clk clock you pointed out in the code snippet is yet > > > > > another clock, the MIPI DSI module clock. > > > > > > > > Correct, look like I refereed wrong reference in the above mail. sorry > > > > for the noise. > > > > > > > > Actually I'm trying to explain about pll_rate here which indeed > > > > depends on dsi.div > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L786 > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > > > > > Say > > > > > > > > 1) For 148MHz dclk_rate with dsi_div is 6 (24/4) lcd_div is 1 which > > > > resulting pll_rate is 888MHz. > > > > > > > > 2) For 30MHz dclk_rate with 4 lane and 24 RGB the resulting pll_rate is 180MHz > > > > > > > > 3) For 27.5MHz dclk_rate with 2 lane and 24 RGB the resulting pll_rate is 330MHz > > > > > > > > Here is the few more logs in code, for case 2) > > > > > > > > [ 1.920441] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > > > > [ 1.920505] ideal = 180000000, rounded = 178200000 > > > > [ 1.920509] sun4i_dclk_round_rate: div = 6 rate = 29700000 > > > > [ 1.920514] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > > > > [ 1.920532] ideal = 1800ls and one DSI-RGB bridge. All of them do use > > PLL_MIPI (pll_rate) and it indeed depends on bpp/lanes > >00000, rounded = 178200000 > > > > [ 1.920535] sun4i_dclk_round_rate: div = 6 rate = 29700000 > > > > [ 1.920572] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > > > > [ 1.920576] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > > > > [ 1.920597] rate = 178200000 > > > > [ 1.920599] parent_rate = 297000000 > > > > [ 1.920602] reg = 0x90c00000 > > > > [ 1.920605] _nkm.n = 3, nkm->n.offset = 0x1, nkm->n.shift = 8 > > > > [ 1.920609] _nkm.k = 2, nkm->k.offset = 0x1, nkm->k.shift = 4 > > > > [ 1.920612] _nkm.m = 10, nkm->m.offset = 0x1, nkm->m.shift = 0 > > > > [ 1.920958] sun4i_dclk_set_rate div 6 > > > > [ 1.920966] sun4i_dclk_recalc_rate: val = 6, rate = 29700000 > > > > > > > > and clk_summary: > > > > > > > > pll-video0 1 1 1 297000000 > > > > 0 0 50000 > > > > hdmi 0 0 0 297000000 > > > > 0 0 50000 > > > > tcon1 0 0 0 297000000 > > > > 0 0 50000 > > > > pll-mipi 1 1 1 178200000 > > > > 0 0 50000 > > > > tcon0 2 2 1 178200000 > > > > 0 0 50000 > > > > tcon-pixel-clock 1 1 1 29700000 > > > > 0 0 50000 > > > > pll-video0-2x 0 0 0 594000000 > > > > 0 0 50000 > > > > > > This discussion is going nowhere. I'm telling you that your patch > > > doesn't apply the divider you want on the proper clock, and you're > > > replying that indeed, you're applying it on the wrong clock. > > > > > > It might work by accident in your case, but the board I have here > > > clearly indicates otherwise, so there's two possible way out here: > > > > > > - Either you apply that divider to the TCON *module* clock, and not > > > the dclk > > > > > > - Or you point to somewhere in the allwinner code where the bpp / > > > lanes divider is used for the dclk divider. > > > > I don't know how to proceed further on this, as you say it might work > > in accident but I have tested this in A33, A64 and R40 with 4 > > different DSI panels and one DSI-RGB bridge. All of them do use > > PLL_MIPI (pll_rate) and it indeed depends on bpp/lanes > > > > 4-lane, 24-bit: Novatek NT35596 panel > > 4-lane, 24-bit: Feiyang, FY07024di26a30d panel > > 4-lane, 24-bit: Bananapi-s070wv20 panel > > 2-lane, 24-bit: Techstar,ts8550b panel > > > > and > > > > 4-lane, 24-bit, ICN6211 DSI-to-RGB bridge panel > > > > All above listed panels and bridges are working as per BSP and do > > follow bpp/lanes and for DIVIDER 4 no panel is working. > > Look. I'm not saying that there's no issue, I'm saying that your > patch, applied to the clock you're applying it to, doesn't make sense > and isn't what the BSP does. tcon-pixel clock is the rate that you want to achive on display side and if you have 4 lanes 32bit or lanes and different bit number that you need to have a clock that is able to put outside bits and speed equal to pixel-clock * bits / lanes. so If you want a pixel-clock of 40 mhz and you have 32bits and 4 lanes you need to have a clock of 40 * 32 / 4 in no-burst mode. I think that this is done but most of the display. Now in burst mode I don't know how should work the calculation of the clock for the require bandwidth and even I understand your comment I would like to have your clock tree after you boot on the display side and if it is possible I want to assemble a kit like you have. > > You can keep on arguing that your patch is perfect as is, but the fact > that there's regressions proves otherwise. > Well when you push your code you said that you have tested on more then one display. Can I know where are the others? > > The panels/bridges I have has tested in BSP and as you mentioned in > > another mail, your panel is not tested in BSP - this is the only > > difference. I did much reverse-engineering on PLL_MIPI clocking in BSP > > so I'm afraid what can I do next on this, If you want to look further > > on BSP I would suggest to verify on pll_rate side. If you feel > > anything I'm missing please let me know. > > I already told you how we can make some progress in the mail you > quoted, but you chose to ignore that. > Yes, the idea is to make progress. Thank you about your helping Michael > Until there's been some progress on either points mentionned above, > I'm just going to stop answering on this topic. > > Maxime > > -- > Maxime Ripard, Bootlin > Embedded Linux and Kernel engineering > https://bootlin.com
On Fri, Jul 05, 2019 at 07:52:27PM +0200, Michael Nazzareno Trimarchi wrote: > On Wed, Jul 3, 2019 at 1:49 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > On Tue, Jun 25, 2019 at 09:00:36PM +0530, Jagan Teki wrote: > > > On Tue, Jun 25, 2019 at 8:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > On Thu, Jun 20, 2019 at 11:57:44PM +0530, Jagan Teki wrote: > > > > > On Fri, Jun 14, 2019 at 7:54 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > On Wed, Jun 05, 2019 at 01:03:16PM +0530, Jagan Teki wrote: > > > > > > > On Wed, Jun 5, 2019 at 12:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > > > > > Hi, > > > > > > > > > > > > > > > > I've reordered the mail a bit to work on chunks > > > > > > > > > > > > > > > > On Fri, May 24, 2019 at 03:37:42PM +0530, Jagan Teki wrote: > > > > > > > > > > I wish it was in your commit log in the first place, instead of having > > > > > > > > > > to exchange multiple mails over this. > > > > > > > > > > > > > > > > > > > > However, I don't think that's quite true, and it might be a bug in > > > > > > > > > > Allwinner's implementation (or rather something quite confusing). > > > > > > > > > > > > > > > > > > > > You're right that the lcd_rate and pll_rate seem to be generated from > > > > > > > > > > the pixel clock, and it indeed looks like the ratio between the pixel > > > > > > > > > > clock and the TCON dotclock is defined through the number of bits per > > > > > > > > > > lanes. > > > > > > > > > > > > > > > > > > > > However, in this case, dsi_rate is actually the same than lcd_rate, > > > > > > > > > > since pll_rate is going to be divided by dsi_div: > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > > > > > > > > > > > > > > > > > > > Since lcd_div is 1, it also means that in this case, dsi_rate == > > > > > > > > > > dclk_rate. > > > > > > > > > > > > > > > > > > > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > > > > > > > > > > we look at: > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > > > > > > > > > > > > > > > > > > > We can see that the rate in clk_info is used if it's different than > > > > > > > > > > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > > > > > > > > > > DSI panel, will hardcode it to 148.5 MHz: > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > > > > > > > > > > > > > > > > > Let me explain, something more. > > > > > > > > > > > > > > > > > > According to bsp there are clk_info.tcon_div which I will explain below. > > > > > > > > > clk_info.dsi_div which is dynamic and it depends on bpp/lanes, so it > > > > > > > > > is 6 for 24bpp and 4 lanes devices. > > > > > > > > > > > > > > > > > > PLL rate here depends on dsi_div (not tcon_div) > > > > > > > > > > > > > > > > > > Code here > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L784 > > > > > > > > > > > > > > > > > > is computing the actual set rate, which depends on dsi_rate. > > > > > > > > > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > > > > > dsi_rate = pll_rate / clk_info.dsi_div; > > > > > > > > > > > > > > > > > > Say if the dclk_rate 148MHz then the dsi_rate is 888MHz which set rate > > > > > > > > > for above link you mentioned. > > > > > > > > > > > > > > > > > > Here are the evidence with some prints. > > > > > > > > > > > > > > > > > > https://gist.github.com/openedev/9bae2d87d2fcc06b999fe48c998b7043 > > > > > > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > > > > > > > > > > > Ok, so we agree up to this point, and the prints confirm that the > > > > > > > > analysis above is the right one. > > > > > > > > > > > > > > > > > > So, the DSI clock is set to this here: > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > > > > > > > > > > > > > > > Your patch doesn't address that, so let's leave that one alone. > > > > > > > > > > > > > > Basically this is final pll set rate when sun4i_dotclock.c called the > > > > > > > desired rate with ccu_nkm.c so it ended the final rate with parent as > > > > > > > Line 8 of > > > > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > > > > > > > If that's important to the driver, it should be set explicitly then, > > > > > > and not work by accident. > > > > > > > > > > > > > > > > The TCON *module* clock (the one in the clock controller) has been set > > > > > > > > > > to lcd_rate (so the pixel clock times the number of bits per lane) here: > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > > > > > > > > > > > > > > > > > > > And the PLL has been set to the same rate here: > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > > > > > > > > > > > > > > > > > > > Let's take a step back now: that function we were looking at, > > > > > > > > > > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > > > > > > > > > > by disp_lcd_enable here: > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > > > > > > > > > > > > > > > > > > > The next function being called is disp_al_lcd_cfg, and that function > > > > > > > > > > will hardcode the TCON dotclock divider to 4, here: > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > > > > > > > > > > > > > > > > > tcon_div from BSP point-of-view of there are two variants > > > > > > > > > 00) clk_info.tcon_div which is 4 and same is set the divider position > > > > > > > > > in SUN4I_TCON0_DCLK_REG (like above link refer) > > > > > > > > > 01) tcon_div which is 4 and used for edge timings computation > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > > > > > > > > > > > > > The real reason for 01) is again 4 is they set the divider to 4 in 00) > > > > > > > > > which is technically wrong because the dividers which used during > > > > > > > > > dotclock in above (dsi_div) should be used here as well. Since there > > > > > > > > > is no dynamic way of doing this BSP hard-coding these values. > > > > > > > > > > > > > > > > > > Patches 5,6,7 on this series doing this > > > > > > > > > https://patchwork.freedesktop.org/series/60847/ > > > > > > > > > > > > > > > > > > Hope this explanation helps? > > > > > > > > > > > > > > > > It doesn't. > > > > > > > > > > > > > > > > The clock tree is this one: > > > > > > > > > > > > > > > > PLL(s) -> TCON module clock -> TCON dotclock. > > > > > > > > > > > > > > > > The links I mentioned above show that the clock set to lcd_rate is the > > > > > > > > TCON module clocks (and it should be the one taking the bpp and lanes > > > > > > > > into account), while the TCON dotclock uses a fixed divider of 4. > > > > > > > > > > > > > > Sorry, I can argue much other-than giving some code snips, according to [1] > > > > > > > > > > > > > > 00) Line 785, 786 with dclk_rate 148000000 > > > > > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > > > > > > > > > > > Since dsi_div is 6 (bpp/lanes), lcd_div 1 > > > > > > > > > > > > > > lcd_rate = 888000000, pll_rate = 888000000 > > > > > > > > > > > > > > 01) Line 801, 804 are final rates computed as per clock driver (say > > > > > > > ccu_nkm in mainline) > > > > > > > > > > > > > > lcd_rate_set=891000000 > > > > > > > > > > > > > > As per your comments if it would be 4 then the desired numbers are > > > > > > > would be 592000000 not 888000000. > > > > > > > > > > > > > > This is what I'm trying to say in all mails, and same as verified with > > > > > > > 2-lanes devices as well where the dsi_div is 12 so the final rate is > > > > > > > 290MHz * 12 > > > > > > > > > > > > In the code you sent, you're forcing a divider on the internal TCON > > > > > > clock, while that one is fixed in the BSP. > > > > > > > > > > > > There's indeed the bpp / lanes divider, but it's used in the *parent* > > > > > > clock of the one you're changing. > > > > > > > > > > > > And the dsi0_clk clock you pointed out in the code snippet is yet > > > > > > another clock, the MIPI DSI module clock. > > > > > > > > > > Correct, look like I refereed wrong reference in the above mail. sorry > > > > > for the noise. > > > > > > > > > > Actually I'm trying to explain about pll_rate here which indeed > > > > > depends on dsi.div > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L786 > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > > > > > > > Say > > > > > > > > > > 1) For 148MHz dclk_rate with dsi_div is 6 (24/4) lcd_div is 1 which > > > > > resulting pll_rate is 888MHz. > > > > > > > > > > 2) For 30MHz dclk_rate with 4 lane and 24 RGB the resulting pll_rate is 180MHz > > > > > > > > > > 3) For 27.5MHz dclk_rate with 2 lane and 24 RGB the resulting pll_rate is 330MHz > > > > > > > > > > Here is the few more logs in code, for case 2) > > > > > > > > > > [ 1.920441] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > > > > > [ 1.920505] ideal = 180000000, rounded = 178200000 > > > > > [ 1.920509] sun4i_dclk_round_rate: div = 6 rate = 29700000 > > > > > [ 1.920514] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > > > > > [ 1.920532] ideal = 1800ls and one DSI-RGB bridge. All of them do use > > > PLL_MIPI (pll_rate) and it indeed depends on bpp/lanes > > >00000, rounded = 178200000 > > > > > [ 1.920535] sun4i_dclk_round_rate: div = 6 rate = 29700000 > > > > > [ 1.920572] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > > > > > [ 1.920576] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > > > > > [ 1.920597] rate = 178200000 > > > > > [ 1.920599] parent_rate = 297000000 > > > > > [ 1.920602] reg = 0x90c00000 > > > > > [ 1.920605] _nkm.n = 3, nkm->n.offset = 0x1, nkm->n.shift = 8 > > > > > [ 1.920609] _nkm.k = 2, nkm->k.offset = 0x1, nkm->k.shift = 4 > > > > > [ 1.920612] _nkm.m = 10, nkm->m.offset = 0x1, nkm->m.shift = 0 > > > > > [ 1.920958] sun4i_dclk_set_rate div 6 > > > > > [ 1.920966] sun4i_dclk_recalc_rate: val = 6, rate = 29700000 > > > > > > > > > > and clk_summary: > > > > > > > > > > pll-video0 1 1 1 297000000 > > > > > 0 0 50000 > > > > > hdmi 0 0 0 297000000 > > > > > 0 0 50000 > > > > > tcon1 0 0 0 297000000 > > > > > 0 0 50000 > > > > > pll-mipi 1 1 1 178200000 > > > > > 0 0 50000 > > > > > tcon0 2 2 1 178200000 > > > > > 0 0 50000 > > > > > tcon-pixel-clock 1 1 1 29700000 > > > > > 0 0 50000 > > > > > pll-video0-2x 0 0 0 594000000 > > > > > 0 0 50000 > > > > > > > > This discussion is going nowhere. I'm telling you that your patch > > > > doesn't apply the divider you want on the proper clock, and you're > > > > replying that indeed, you're applying it on the wrong clock. > > > > > > > > It might work by accident in your case, but the board I have here > > > > clearly indicates otherwise, so there's two possible way out here: > > > > > > > > - Either you apply that divider to the TCON *module* clock, and not > > > > the dclk > > > > > > > > - Or you point to somewhere in the allwinner code where the bpp / > > > > lanes divider is used for the dclk divider. > > > > > > I don't know how to proceed further on this, as you say it might work > > > in accident but I have tested this in A33, A64 and R40 with 4 > > > different DSI panels and one DSI-RGB bridge. All of them do use > > > PLL_MIPI (pll_rate) and it indeed depends on bpp/lanes > > > > > > 4-lane, 24-bit: Novatek NT35596 panel > > > 4-lane, 24-bit: Feiyang, FY07024di26a30d panel > > > 4-lane, 24-bit: Bananapi-s070wv20 panel > > > 2-lane, 24-bit: Techstar,ts8550b panel > > > > > > and > > > > > > 4-lane, 24-bit, ICN6211 DSI-to-RGB bridge panel > > > > > > All above listed panels and bridges are working as per BSP and do > > > follow bpp/lanes and for DIVIDER 4 no panel is working. > > > > Look. I'm not saying that there's no issue, I'm saying that your > > patch, applied to the clock you're applying it to, doesn't make sense > > and isn't what the BSP does. > > tcon-pixel clock is the rate that you want to achive on display side > and if you have 4 lanes 32bit or lanes and different bit number that > you need to have a clock that is able to put outside bits and speed > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > the display. So this is what the issue is then? This one does make sense, and you should just change the rate in the call to clk_set_rate in sun4i_tcon0_mode_set_cpu. I'm still wondering why that hasn't been brought up in either the discussion or the commit log before though. > Now in burst mode I don't know how should work the calculation of > the clock for the require bandwidth and even I understand your > comment I would like to have your clock tree after you boot on the > display side and if it is possible I want to assemble a kit like you > have. The setup is probably going to be a bit difficult to reproduce, it's a prototype that I have that can't really be found anywhere. Jagan asked me on IRC for the reference, and he found the part, but it's unclear to me if it can be easily adapted to a common board. However, I'm not even sure we need this. I'll test the next version and let you know if it works. Maxime -- Maxime Ripard, Bootlin Embedded Linux and Kernel engineering https://bootlin.com
Hi Maxime On Thu, Jul 11, 2019 at 2:23 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Fri, Jul 05, 2019 at 07:52:27PM +0200, Michael Nazzareno Trimarchi wrote: > > On Wed, Jul 3, 2019 at 1:49 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > On Tue, Jun 25, 2019 at 09:00:36PM +0530, Jagan Teki wrote: > > > > On Tue, Jun 25, 2019 at 8:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > On Thu, Jun 20, 2019 at 11:57:44PM +0530, Jagan Teki wrote: > > > > > > On Fri, Jun 14, 2019 at 7:54 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > > > On Wed, Jun 05, 2019 at 01:03:16PM +0530, Jagan Teki wrote: > > > > > > > > On Wed, Jun 5, 2019 at 12:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > > > > > > > Hi, > > > > > > > > > > > > > > > > > > I've reordered the mail a bit to work on chunks > > > > > > > > > > > > > > > > > > On Fri, May 24, 2019 at 03:37:42PM +0530, Jagan Teki wrote: > > > > > > > > > > > I wish it was in your commit log in the first place, instead of having > > > > > > > > > > > to exchange multiple mails over this. > > > > > > > > > > > > > > > > > > > > > > However, I don't think that's quite true, and it might be a bug in > > > > > > > > > > > Allwinner's implementation (or rather something quite confusing). > > > > > > > > > > > > > > > > > > > > > > You're right that the lcd_rate and pll_rate seem to be generated from > > > > > > > > > > > the pixel clock, and it indeed looks like the ratio between the pixel > > > > > > > > > > > clock and the TCON dotclock is defined through the number of bits per > > > > > > > > > > > lanes. > > > > > > > > > > > > > > > > > > > > > > However, in this case, dsi_rate is actually the same than lcd_rate, > > > > > > > > > > > since pll_rate is going to be divided by dsi_div: > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > > > > > > > > > > > > > > > > > > > > > Since lcd_div is 1, it also means that in this case, dsi_rate == > > > > > > > > > > > dclk_rate. > > > > > > > > > > > > > > > > > > > > > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > > > > > > > > > > > we look at: > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > > > > > > > > > > > > > > > > > > > > > We can see that the rate in clk_info is used if it's different than > > > > > > > > > > > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > > > > > > > > > > > DSI panel, will hardcode it to 148.5 MHz: > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > > > > > > > > > > > > > > > > > > > Let me explain, something more. > > > > > > > > > > > > > > > > > > > > According to bsp there are clk_info.tcon_div which I will explain below. > > > > > > > > > > clk_info.dsi_div which is dynamic and it depends on bpp/lanes, so it > > > > > > > > > > is 6 for 24bpp and 4 lanes devices. > > > > > > > > > > > > > > > > > > > > PLL rate here depends on dsi_div (not tcon_div) > > > > > > > > > > > > > > > > > > > > Code here > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L784 > > > > > > > > > > > > > > > > > > > > is computing the actual set rate, which depends on dsi_rate. > > > > > > > > > > > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > > > > > > dsi_rate = pll_rate / clk_info.dsi_div; > > > > > > > > > > > > > > > > > > > > Say if the dclk_rate 148MHz then the dsi_rate is 888MHz which set rate > > > > > > > > > > for above link you mentioned. > > > > > > > > > > > > > > > > > > > > Here are the evidence with some prints. > > > > > > > > > > > > > > > > > > > > https://gist.github.com/openedev/9bae2d87d2fcc06b999fe48c998b7043 > > > > > > > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > > > > > > > > > > > > > Ok, so we agree up to this point, and the prints confirm that the > > > > > > > > > analysis above is the right one. > > > > > > > > > > > > > > > > > > > > So, the DSI clock is set to this here: > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > > > > > > > > > > > > > > > > > Your patch doesn't address that, so let's leave that one alone. > > > > > > > > > > > > > > > > Basically this is final pll set rate when sun4i_dotclock.c called the > > > > > > > > desired rate with ccu_nkm.c so it ended the final rate with parent as > > > > > > > > Line 8 of > > > > > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > > > > > > > > > If that's important to the driver, it should be set explicitly then, > > > > > > > and not work by accident. > > > > > > > > > > > > > > > > > > The TCON *module* clock (the one in the clock controller) has been set > > > > > > > > > > > to lcd_rate (so the pixel clock times the number of bits per lane) here: > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > > > > > > > > > > > > > > > > > > > > > And the PLL has been set to the same rate here: > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > > > > > > > > > > > > > > > > > > > > > Let's take a step back now: that function we were looking at, > > > > > > > > > > > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > > > > > > > > > > > by disp_lcd_enable here: > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > > > > > > > > > > > > > > > > > > > > > The next function being called is disp_al_lcd_cfg, and that function > > > > > > > > > > > will hardcode the TCON dotclock divider to 4, here: > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > > > > > > > > > > > > > > > > > > > tcon_div from BSP point-of-view of there are two variants > > > > > > > > > > 00) clk_info.tcon_div which is 4 and same is set the divider position > > > > > > > > > > in SUN4I_TCON0_DCLK_REG (like above link refer) > > > > > > > > > > 01) tcon_div which is 4 and used for edge timings computation > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > > > > > > > > > > > > > > > The real reason for 01) is again 4 is they set the divider to 4 in 00) > > > > > > > > > > which is technically wrong because the dividers which used during > > > > > > > > > > dotclock in above (dsi_div) should be used here as well. Since there > > > > > > > > > > is no dynamic way of doing this BSP hard-coding these values. > > > > > > > > > > > > > > > > > > > > Patches 5,6,7 on this series doing this > > > > > > > > > > https://patchwork.freedesktop.org/series/60847/ > > > > > > > > > > > > > > > > > > > > Hope this explanation helps? > > > > > > > > > > > > > > > > > > It doesn't. > > > > > > > > > > > > > > > > > > The clock tree is this one: > > > > > > > > > > > > > > > > > > PLL(s) -> TCON module clock -> TCON dotclock. > > > > > > > > > > > > > > > > > > The links I mentioned above show that the clock set to lcd_rate is the > > > > > > > > > TCON module clocks (and it should be the one taking the bpp and lanes > > > > > > > > > into account), while the TCON dotclock uses a fixed divider of 4. > > > > > > > > > > > > > > > > Sorry, I can argue much other-than giving some code snips, according to [1] > > > > > > > > > > > > > > > > 00) Line 785, 786 with dclk_rate 148000000 > > > > > > > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > > > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > > > > > > > > > > > > > Since dsi_div is 6 (bpp/lanes), lcd_div 1 > > > > > > > > > > > > > > > > lcd_rate = 888000000, pll_rate = 888000000 > > > > > > > > > > > > > > > > 01) Line 801, 804 are final rates computed as per clock driver (say > > > > > > > > ccu_nkm in mainline) > > > > > > > > > > > > > > > > lcd_rate_set=891000000 > > > > > > > > > > > > > > > > As per your comments if it would be 4 then the desired numbers are > > > > > > > > would be 592000000 not 888000000. > > > > > > > > > > > > > > > > This is what I'm trying to say in all mails, and same as verified with > > > > > > > > 2-lanes devices as well where the dsi_div is 12 so the final rate is > > > > > > > > 290MHz * 12 > > > > > > > > > > > > > > In the code you sent, you're forcing a divider on the internal TCON > > > > > > > clock, while that one is fixed in the BSP. > > > > > > > > > > > > > > There's indeed the bpp / lanes divider, but it's used in the *parent* > > > > > > > clock of the one you're changing. > > > > > > > > > > > > > > And the dsi0_clk clock you pointed out in the code snippet is yet > > > > > > > another clock, the MIPI DSI module clock. > > > > > > > > > > > > Correct, look like I refereed wrong reference in the above mail. sorry > > > > > > for the noise. > > > > > > > > > > > > Actually I'm trying to explain about pll_rate here which indeed > > > > > > depends on dsi.div > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L786 > > > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > > > > > > > > > Say > > > > > > > > > > > > 1) For 148MHz dclk_rate with dsi_div is 6 (24/4) lcd_div is 1 which > > > > > > resulting pll_rate is 888MHz. > > > > > > > > > > > > 2) For 30MHz dclk_rate with 4 lane and 24 RGB the resulting pll_rate is 180MHz > > > > > > > > > > > > 3) For 27.5MHz dclk_rate with 2 lane and 24 RGB the resulting pll_rate is 330MHz > > > > > > > > > > > > Here is the few more logs in code, for case 2) > > > > > > > > > > > > [ 1.920441] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > > > > > > [ 1.920505] ideal = 180000000, rounded = 178200000 > > > > > > [ 1.920509] sun4i_dclk_round_rate: div = 6 rate = 29700000 > > > > > > [ 1.920514] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > > > > > > [ 1.920532] ideal = 1800ls and one DSI-RGB bridge. All of them do use > > > > PLL_MIPI (pll_rate) and it indeed depends on bpp/lanes > > > >00000, rounded = 178200000 > > > > > > [ 1.920535] sun4i_dclk_round_rate: div = 6 rate = 29700000 > > > > > > [ 1.920572] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > > > > > > [ 1.920576] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > > > > > > [ 1.920597] rate = 178200000 > > > > > > [ 1.920599] parent_rate = 297000000 > > > > > > [ 1.920602] reg = 0x90c00000 > > > > > > [ 1.920605] _nkm.n = 3, nkm->n.offset = 0x1, nkm->n.shift = 8 > > > > > > [ 1.920609] _nkm.k = 2, nkm->k.offset = 0x1, nkm->k.shift = 4 > > > > > > [ 1.920612] _nkm.m = 10, nkm->m.offset = 0x1, nkm->m.shift = 0 > > > > > > [ 1.920958] sun4i_dclk_set_rate div 6 > > > > > > [ 1.920966] sun4i_dclk_recalc_rate: val = 6, rate = 29700000 > > > > > > > > > > > > and clk_summary: > > > > > > > > > > > > pll-video0 1 1 1 297000000 > > > > > > 0 0 50000 > > > > > > hdmi 0 0 0 297000000 > > > > > > 0 0 50000 > > > > > > tcon1 0 0 0 297000000 > > > > > > 0 0 50000 > > > > > > pll-mipi 1 1 1 178200000 > > > > > > 0 0 50000 > > > > > > tcon0 2 2 1 178200000 > > > > > > 0 0 50000 > > > > > > tcon-pixel-clock 1 1 1 29700000 > > > > > > 0 0 50000 > > > > > > pll-video0-2x 0 0 0 594000000 > > > > > > 0 0 50000 > > > > > > > > > > This discussion is going nowhere. I'm telling you that your patch > > > > > doesn't apply the divider you want on the proper clock, and you're > > > > > replying that indeed, you're applying it on the wrong clock. > > > > > > > > > > It might work by accident in your case, but the board I have here > > > > > clearly indicates otherwise, so there's two possible way out here: > > > > > > > > > > - Either you apply that divider to the TCON *module* clock, and not > > > > > the dclk > > > > > > > > > > - Or you point to somewhere in the allwinner code where the bpp / > > > > > lanes divider is used for the dclk divider. > > > > > > > > I don't know how to proceed further on this, as you say it might work > > > > in accident but I have tested this in A33, A64 and R40 with 4 > > > > different DSI panels and one DSI-RGB bridge. All of them do use > > > > PLL_MIPI (pll_rate) and it indeed depends on bpp/lanes > > > > > > > > 4-lane, 24-bit: Novatek NT35596 panel > > > > 4-lane, 24-bit: Feiyang, FY07024di26a30d panel > > > > 4-lane, 24-bit: Bananapi-s070wv20 panel > > > > 2-lane, 24-bit: Techstar,ts8550b panel > > > > > > > > and > > > > > > > > 4-lane, 24-bit, ICN6211 DSI-to-RGB bridge panel > > > > > > > > All above listed panels and bridges are working as per BSP and do > > > > follow bpp/lanes and for DIVIDER 4 no panel is working. > > > > > > Look. I'm not saying that there's no issue, I'm saying that your > > > patch, applied to the clock you're applying it to, doesn't make sense > > > and isn't what the BSP does. > > > > tcon-pixel clock is the rate that you want to achive on display side > > and if you have 4 lanes 32bit or lanes and different bit number that > > you need to have a clock that is able to put outside bits and speed > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > the display. > > So this is what the issue is then? > > This one does make sense, and you should just change the rate in the > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > I'm still wondering why that hasn't been brought up in either the > discussion or the commit log before though. > Something like this? drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- 2 files changed, 11 insertions(+), 11 deletions(-) diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c b/drivers/gpu/drm/sun4i/sun4i_tcon.c index 64c43ee6bd92..42560d5c327c 100644 --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct drm_display_mode *mode, } static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, - const struct drm_display_mode *mode) + const struct drm_display_mode *mode, + u32 tcon_mul) { /* Configure the dot clock */ - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); /* Set the resolution */ regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct sun4i_tcon *tcon, u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); u8 lanes = device->lanes; u32 block_space, start_delay; - u32 tcon_div; + u32 tcon_div, tcon_mul; - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; + tcon->dclk_min_div = 4; + tcon->dclk_max_div = 127; - sun4i_tcon0_mode_set_common(tcon, mode); + tcon_mul = bpp / lanes; + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); /* Set dithering if needed */ sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct sun4i_tcon *tcon, */ regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); tcon_div &= GENMASK(6, 0); - block_space = mode->htotal * bpp / (tcon_div * lanes); + block_space = mode->htotal * tcon_div * tcon_mul; block_space -= mode->hdisplay + 40; regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct sun4i_tcon *tcon, tcon->dclk_min_div = 7; tcon->dclk_max_div = 7; - sun4i_tcon0_mode_set_common(tcon, mode); + sun4i_tcon0_mode_set_common(tcon, mode, 1); /* Set dithering if needed */ sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct sun4i_tcon *tcon, tcon->dclk_min_div = 6; tcon->dclk_max_div = 127; - sun4i_tcon0_mode_set_common(tcon, mode); + sun4i_tcon0_mode_set_common(tcon, mode, 1); /* Set dithering if needed */ sun4i_tcon0_mode_set_dithering(tcon, connector); diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h index 5c3ad5be0690..a07090579f84 100644 --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h @@ -13,8 +13,6 @@ #include <drm/drm_encoder.h> #include <drm/drm_mipi_dsi.h> -#define SUN6I_DSI_TCON_DIV 4 - struct sun6i_dsi { struct drm_connector connector; struct drm_encoder encoder; > > Now in burst mode I don't know how should work the calculation of > > the clock for the require bandwidth and even I understand your > > comment I would like to have your clock tree after you boot on the > > display side and if it is possible I want to assemble a kit like you > > have. > > The setup is probably going to be a bit difficult to reproduce, it's a > prototype that I have that can't really be found anywhere. Jagan asked > me on IRC for the reference, and he found the part, but it's unclear > to me if it can be easily adapted to a common board. > > However, I'm not even sure we need this. I'll test the next version > and let you know if it works. > > Maxime > > -- > Maxime Ripard, Bootlin > Embedded Linux and Kernel engineering > https://bootlin.com
Hi On Thu, Jul 11, 2019 at 7:43 PM Michael Nazzareno Trimarchi <michael@amarulasolutions.com> wrote: > > Hi Maxime > > On Thu, Jul 11, 2019 at 2:23 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > On Fri, Jul 05, 2019 at 07:52:27PM +0200, Michael Nazzareno Trimarchi wrote: > > > On Wed, Jul 3, 2019 at 1:49 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > On Tue, Jun 25, 2019 at 09:00:36PM +0530, Jagan Teki wrote: > > > > > On Tue, Jun 25, 2019 at 8:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > On Thu, Jun 20, 2019 at 11:57:44PM +0530, Jagan Teki wrote: > > > > > > > On Fri, Jun 14, 2019 at 7:54 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > > > > > On Wed, Jun 05, 2019 at 01:03:16PM +0530, Jagan Teki wrote: > > > > > > > > > On Wed, Jun 5, 2019 at 12:19 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > > > > > > > > > Hi, > > > > > > > > > > > > > > > > > > > > I've reordered the mail a bit to work on chunks > > > > > > > > > > > > > > > > > > > > On Fri, May 24, 2019 at 03:37:42PM +0530, Jagan Teki wrote: > > > > > > > > > > > > I wish it was in your commit log in the first place, instead of having > > > > > > > > > > > > to exchange multiple mails over this. > > > > > > > > > > > > > > > > > > > > > > > > However, I don't think that's quite true, and it might be a bug in > > > > > > > > > > > > Allwinner's implementation (or rather something quite confusing). > > > > > > > > > > > > > > > > > > > > > > > > You're right that the lcd_rate and pll_rate seem to be generated from > > > > > > > > > > > > the pixel clock, and it indeed looks like the ratio between the pixel > > > > > > > > > > > > clock and the TCON dotclock is defined through the number of bits per > > > > > > > > > > > > lanes. > > > > > > > > > > > > > > > > > > > > > > > > However, in this case, dsi_rate is actually the same than lcd_rate, > > > > > > > > > > > > since pll_rate is going to be divided by dsi_div: > > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L791 > > > > > > > > > > > > > > > > > > > > > > > > Since lcd_div is 1, it also means that in this case, dsi_rate == > > > > > > > > > > > > dclk_rate. > > > > > > > > > > > > > > > > > > > > > > > > The DSI module clock however, is always set to 148.5 MHz. Indeed, if > > > > > > > > > > > > we look at: > > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L804 > > > > > > > > > > > > > > > > > > > > > > > > We can see that the rate in clk_info is used if it's different than > > > > > > > > > > > > 0. This is filled by disp_al_lcd_get_clk_info, which, in the case of a > > > > > > > > > > > > DSI panel, will hardcode it to 148.5 MHz: > > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L164 > > > > > > > > > > > > > > > > > > > > > > Let me explain, something more. > > > > > > > > > > > > > > > > > > > > > > According to bsp there are clk_info.tcon_div which I will explain below. > > > > > > > > > > > clk_info.dsi_div which is dynamic and it depends on bpp/lanes, so it > > > > > > > > > > > is 6 for 24bpp and 4 lanes devices. > > > > > > > > > > > > > > > > > > > > > > PLL rate here depends on dsi_div (not tcon_div) > > > > > > > > > > > > > > > > > > > > > > Code here > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L784 > > > > > > > > > > > > > > > > > > > > > > is computing the actual set rate, which depends on dsi_rate. > > > > > > > > > > > > > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > > > > > > > dsi_rate = pll_rate / clk_info.dsi_div; > > > > > > > > > > > > > > > > > > > > > > Say if the dclk_rate 148MHz then the dsi_rate is 888MHz which set rate > > > > > > > > > > > for above link you mentioned. > > > > > > > > > > > > > > > > > > > > > > Here are the evidence with some prints. > > > > > > > > > > > > > > > > > > > > > > https://gist.github.com/openedev/9bae2d87d2fcc06b999fe48c998b7043 > > > > > > > > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > > > > > > > > > > > > > > > Ok, so we agree up to this point, and the prints confirm that the > > > > > > > > > > analysis above is the right one. > > > > > > > > > > > > > > > > > > > > > > So, the DSI clock is set to this here: > > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L805 > > > > > > > > > > > > > > > > > > > > Your patch doesn't address that, so let's leave that one alone. > > > > > > > > > > > > > > > > > > Basically this is final pll set rate when sun4i_dotclock.c called the > > > > > > > > > desired rate with ccu_nkm.c so it ended the final rate with parent as > > > > > > > > > Line 8 of > > > > > > > > > https://gist.github.com/openedev/700de2e3701b2bf3ad1aa0f0fa862c9a > > > > > > > > > > > > > > > > If that's important to the driver, it should be set explicitly then, > > > > > > > > and not work by accident. > > > > > > > > > > > > > > > > > > > > The TCON *module* clock (the one in the clock controller) has been set > > > > > > > > > > > > to lcd_rate (so the pixel clock times the number of bits per lane) here: > > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L800 > > > > > > > > > > > > > > > > > > > > > > > > And the PLL has been set to the same rate here: > > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L794 > > > > > > > > > > > > > > > > > > > > > > > > Let's take a step back now: that function we were looking at, > > > > > > > > > > > > lcd_clk_config, is called by lcd_clk_enable, which is in turn called > > > > > > > > > > > > by disp_lcd_enable here: > > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L1328 > > > > > > > > > > > > > > > > > > > > > > > > The next function being called is disp_al_lcd_cfg, and that function > > > > > > > > > > > > will hardcode the TCON dotclock divider to 4, here: > > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/disp_al.c#L240 > > > > > > > > > > > > > > > > > > > > > > tcon_div from BSP point-of-view of there are two variants > > > > > > > > > > > 00) clk_info.tcon_div which is 4 and same is set the divider position > > > > > > > > > > > in SUN4I_TCON0_DCLK_REG (like above link refer) > > > > > > > > > > > 01) tcon_div which is 4 and used for edge timings computation > > > > > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/lowlevel_sun50iw1/de_dsi.c#L12 > > > > > > > > > > > > > > > > > > > > > > The real reason for 01) is again 4 is they set the divider to 4 in 00) > > > > > > > > > > > which is technically wrong because the dividers which used during > > > > > > > > > > > dotclock in above (dsi_div) should be used here as well. Since there > > > > > > > > > > > is no dynamic way of doing this BSP hard-coding these values. > > > > > > > > > > > > > > > > > > > > > > Patches 5,6,7 on this series doing this > > > > > > > > > > > https://patchwork.freedesktop.org/series/60847/ > > > > > > > > > > > > > > > > > > > > > > Hope this explanation helps? > > > > > > > > > > > > > > > > > > > > It doesn't. > > > > > > > > > > > > > > > > > > > > The clock tree is this one: > > > > > > > > > > > > > > > > > > > > PLL(s) -> TCON module clock -> TCON dotclock. > > > > > > > > > > > > > > > > > > > > The links I mentioned above show that the clock set to lcd_rate is the > > > > > > > > > > TCON module clocks (and it should be the one taking the bpp and lanes > > > > > > > > > > into account), while the TCON dotclock uses a fixed divider of 4. > > > > > > > > > > > > > > > > > > Sorry, I can argue much other-than giving some code snips, according to [1] > > > > > > > > > > > > > > > > > > 00) Line 785, 786 with dclk_rate 148000000 > > > > > > > > > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > > > > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > > > > > > > > > > > > > > > Since dsi_div is 6 (bpp/lanes), lcd_div 1 > > > > > > > > > > > > > > > > > > lcd_rate = 888000000, pll_rate = 888000000 > > > > > > > > > > > > > > > > > > 01) Line 801, 804 are final rates computed as per clock driver (say > > > > > > > > > ccu_nkm in mainline) > > > > > > > > > > > > > > > > > > lcd_rate_set=891000000 > > > > > > > > > > > > > > > > > > As per your comments if it would be 4 then the desired numbers are > > > > > > > > > would be 592000000 not 888000000. > > > > > > > > > > > > > > > > > > This is what I'm trying to say in all mails, and same as verified with > > > > > > > > > 2-lanes devices as well where the dsi_div is 12 so the final rate is > > > > > > > > > 290MHz * 12 > > > > > > > > > > > > > > > > In the code you sent, you're forcing a divider on the internal TCON > > > > > > > > clock, while that one is fixed in the BSP. > > > > > > > > > > > > > > > > There's indeed the bpp / lanes divider, but it's used in the *parent* > > > > > > > > clock of the one you're changing. > > > > > > > > > > > > > > > > And the dsi0_clk clock you pointed out in the code snippet is yet > > > > > > > > another clock, the MIPI DSI module clock. > > > > > > > > > > > > > > Correct, look like I refereed wrong reference in the above mail. sorry > > > > > > > for the noise. > > > > > > > > > > > > > > Actually I'm trying to explain about pll_rate here which indeed > > > > > > > depends on dsi.div > > > > > > > https://github.com/BPI-SINOVOIP/BPI-M64-bsp/blob/master/linux-sunxi/drivers/video/sunxi/disp2/disp/de/disp_lcd.c#L786 > > > > > > > > > > > > > > lcd_rate = dclk_rate * clk_info.dsi_div; > > > > > > > pll_rate = lcd_rate * clk_info.lcd_div; > > > > > > > > > > > > > > Say > > > > > > > > > > > > > > 1) For 148MHz dclk_rate with dsi_div is 6 (24/4) lcd_div is 1 which > > > > > > > resulting pll_rate is 888MHz. > > > > > > > > > > > > > > 2) For 30MHz dclk_rate with 4 lane and 24 RGB the resulting pll_rate is 180MHz > > > > > > > > > > > > > > 3) For 27.5MHz dclk_rate with 2 lane and 24 RGB the resulting pll_rate is 330MHz > > > > > > > > > > > > > > Here is the few more logs in code, for case 2) > > > > > > > > > > > > > > [ 1.920441] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > > > > > > > [ 1.920505] ideal = 180000000, rounded = 178200000 > > > > > > > [ 1.920509] sun4i_dclk_round_rate: div = 6 rate = 29700000 > > > > > > > [ 1.920514] sun4i_dclk_round_rate: min_div = 6 max_div = 6, rate = 30000000 > > > > > > > [ 1.920532] ideal = 1800ls and one DSI-RGB bridge. All of them do use > > > > > PLL_MIPI (pll_rate) and it indeed depends on bpp/lanes > > > > >00000, rounded = 178200000 > > > > > > > [ 1.920535] sun4i_dclk_round_rate: div = 6 rate = 29700000 > > > > > > > [ 1.920572] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > > > > > > > [ 1.920576] sun4i_dclk_recalc_rate: val = 1, rate = 178200000 > > > > > > > [ 1.920597] rate = 178200000 > > > > > > > [ 1.920599] parent_rate = 297000000 > > > > > > > [ 1.920602] reg = 0x90c00000 > > > > > > > [ 1.920605] _nkm.n = 3, nkm->n.offset = 0x1, nkm->n.shift = 8 > > > > > > > [ 1.920609] _nkm.k = 2, nkm->k.offset = 0x1, nkm->k.shift = 4 > > > > > > > [ 1.920612] _nkm.m = 10, nkm->m.offset = 0x1, nkm->m.shift = 0 > > > > > > > [ 1.920958] sun4i_dclk_set_rate div 6 > > > > > > > [ 1.920966] sun4i_dclk_recalc_rate: val = 6, rate = 29700000 > > > > > > > > > > > > > > and clk_summary: > > > > > > > > > > > > > > pll-video0 1 1 1 297000000 > > > > > > > 0 0 50000 > > > > > > > hdmi 0 0 0 297000000 > > > > > > > 0 0 50000 > > > > > > > tcon1 0 0 0 297000000 > > > > > > > 0 0 50000 > > > > > > > pll-mipi 1 1 1 178200000 > > > > > > > 0 0 50000 > > > > > > > tcon0 2 2 1 178200000 > > > > > > > 0 0 50000 > > > > > > > tcon-pixel-clock 1 1 1 29700000 > > > > > > > 0 0 50000 > > > > > > > pll-video0-2x 0 0 0 594000000 > > > > > > > 0 0 50000 > > > > > > > > > > > > This discussion is going nowhere. I'm telling you that your patch > > > > > > doesn't apply the divider you want on the proper clock, and you're > > > > > > replying that indeed, you're applying it on the wrong clock. > > > > > > > > > > > > It might work by accident in your case, but the board I have here > > > > > > clearly indicates otherwise, so there's two possible way out here: > > > > > > > > > > > > - Either you apply that divider to the TCON *module* clock, and not > > > > > > the dclk > > > > > > > > > > > > - Or you point to somewhere in the allwinner code where the bpp / > > > > > > lanes divider is used for the dclk divider. > > > > > > > > > > I don't know how to proceed further on this, as you say it might work > > > > > in accident but I have tested this in A33, A64 and R40 with 4 > > > > > different DSI panels and one DSI-RGB bridge. All of them do use > > > > > PLL_MIPI (pll_rate) and it indeed depends on bpp/lanes > > > > > > > > > > 4-lane, 24-bit: Novatek NT35596 panel > > > > > 4-lane, 24-bit: Feiyang, FY07024di26a30d panel > > > > > 4-lane, 24-bit: Bananapi-s070wv20 panel > > > > > 2-lane, 24-bit: Techstar,ts8550b panel > > > > > > > > > > and > > > > > > > > > > 4-lane, 24-bit, ICN6211 DSI-to-RGB bridge panel > > > > > > > > > > All above listed panels and bridges are working as per BSP and do > > > > > follow bpp/lanes and for DIVIDER 4 no panel is working. > > > > > > > > Look. I'm not saying that there's no issue, I'm saying that your > > > > patch, applied to the clock you're applying it to, doesn't make sense > > > > and isn't what the BSP does. > > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > you need to have a clock that is able to put outside bits and speed > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > the display. > > > > So this is what the issue is then? > > > > This one does make sense, and you should just change the rate in the > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > I'm still wondering why that hasn't been brought up in either the > > discussion or the commit log before though. > > > Something like this? > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > 2 files changed, 11 insertions(+), 11 deletions(-) > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > index 64c43ee6bd92..42560d5c327c 100644 > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > drm_display_mode *mode, > } > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > - const struct drm_display_mode *mode) > + const struct drm_display_mode *mode, > + u32 tcon_mul) > { > /* Configure the dot clock */ > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > /* Set the resolution */ > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > sun4i_tcon *tcon, > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > u8 lanes = device->lanes; > u32 block_space, start_delay; > - u32 tcon_div; > + u32 tcon_div, tcon_mul; > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > + tcon->dclk_min_div = 4; > + tcon->dclk_max_div = 127; > > - sun4i_tcon0_mode_set_common(tcon, mode); > + tcon_mul = bpp / lanes; > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > Maybe wrong clock ;) but is this your idea? Michael > /* Set dithering if needed */ > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > sun4i_tcon *tcon, > */ > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > tcon_div &= GENMASK(6, 0); > - block_space = mode->htotal * bpp / (tcon_div * lanes); > + block_space = mode->htotal * tcon_div * tcon_mul; > block_space -= mode->hdisplay + 40; > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > sun4i_tcon *tcon, > > tcon->dclk_min_div = 7; > tcon->dclk_max_div = 7; > - sun4i_tcon0_mode_set_common(tcon, mode); > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > /* Set dithering if needed */ > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > sun4i_tcon *tcon, > > tcon->dclk_min_div = 6; > tcon->dclk_max_div = 127; > - sun4i_tcon0_mode_set_common(tcon, mode); > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > /* Set dithering if needed */ > sun4i_tcon0_mode_set_dithering(tcon, connector); > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > index 5c3ad5be0690..a07090579f84 100644 > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > @@ -13,8 +13,6 @@ > #include <drm/drm_encoder.h> > #include <drm/drm_mipi_dsi.h> > > -#define SUN6I_DSI_TCON_DIV 4 > - > struct sun6i_dsi { > struct drm_connector connector; > struct drm_encoder encoder; > > > > > Now in burst mode I don't know how should work the calculation of > > > the clock for the require bandwidth and even I understand your > > > comment I would like to have your clock tree after you boot on the > > > display side and if it is possible I want to assemble a kit like you > > > have. > > > > The setup is probably going to be a bit difficult to reproduce, it's a > > prototype that I have that can't really be found anywhere. Jagan asked > > me on IRC for the reference, and he found the part, but it's unclear > > to me if it can be easily adapted to a common board. > > > > However, I'm not even sure we need this. I'll test the next version > > and let you know if it works. > > > > Maxime > > > > -- > > Maxime Ripard, Bootlin > > Embedded Linux and Kernel engineering > > https://bootlin.com > > > > -- > | Michael Nazzareno Trimarchi Amarula Solutions BV | > | COO - Founder Cruquiuskade 47 | > | +31(0)851119172 Amsterdam 1018 AM NL | > | [`as] http://www.amarulasolutions.com |
On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > tcon-pixel clock is the rate that you want to achive on display side > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > you need to have a clock that is able to put outside bits and speed > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > the display. > > > > So this is what the issue is then? > > > > This one does make sense, and you should just change the rate in the > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > I'm still wondering why that hasn't been brought up in either the > > discussion or the commit log before though. > > > Something like this? > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > 2 files changed, 11 insertions(+), 11 deletions(-) > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > index 64c43ee6bd92..42560d5c327c 100644 > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > drm_display_mode *mode, > } > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > - const struct drm_display_mode *mode) > + const struct drm_display_mode *mode, > + u32 tcon_mul) > { > /* Configure the dot clock */ > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > /* Set the resolution */ > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > sun4i_tcon *tcon, > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > u8 lanes = device->lanes; > u32 block_space, start_delay; > - u32 tcon_div; > + u32 tcon_div, tcon_mul; > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > + tcon->dclk_min_div = 4; > + tcon->dclk_max_div = 127; > > - sun4i_tcon0_mode_set_common(tcon, mode); > + tcon_mul = bpp / lanes; > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > /* Set dithering if needed */ > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > sun4i_tcon *tcon, > */ > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > tcon_div &= GENMASK(6, 0); > - block_space = mode->htotal * bpp / (tcon_div * lanes); > + block_space = mode->htotal * tcon_div * tcon_mul; > block_space -= mode->hdisplay + 40; > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > sun4i_tcon *tcon, > > tcon->dclk_min_div = 7; > tcon->dclk_max_div = 7; > - sun4i_tcon0_mode_set_common(tcon, mode); > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > /* Set dithering if needed */ > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > sun4i_tcon *tcon, > > tcon->dclk_min_div = 6; > tcon->dclk_max_div = 127; > - sun4i_tcon0_mode_set_common(tcon, mode); > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > /* Set dithering if needed */ > sun4i_tcon0_mode_set_dithering(tcon, connector); > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > index 5c3ad5be0690..a07090579f84 100644 > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > @@ -13,8 +13,6 @@ > #include <drm/drm_encoder.h> > #include <drm/drm_mipi_dsi.h> > > -#define SUN6I_DSI_TCON_DIV 4 > - > struct sun6i_dsi { > struct drm_connector connector; > struct drm_encoder encoder; I had more something like this in mind: http://code.bulix.org/nlp5a4-803511 You really don't need to change the divider range (or this is another issue that the one you mentionned). Maxime -- Maxime Ripard, Bootlin Embedded Linux and Kernel engineering https://bootlin.com
On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > you need to have a clock that is able to put outside bits and speed > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > the display. > > > > > > So this is what the issue is then? > > > > > > This one does make sense, and you should just change the rate in the > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > I'm still wondering why that hasn't been brought up in either the > > > discussion or the commit log before though. > > > > > Something like this? > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > index 64c43ee6bd92..42560d5c327c 100644 > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > drm_display_mode *mode, > > } > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > - const struct drm_display_mode *mode) > > + const struct drm_display_mode *mode, > > + u32 tcon_mul) > > { > > /* Configure the dot clock */ > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > /* Set the resolution */ > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > sun4i_tcon *tcon, > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > u8 lanes = device->lanes; > > u32 block_space, start_delay; > > - u32 tcon_div; > > + u32 tcon_div, tcon_mul; > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > + tcon->dclk_min_div = 4; > > + tcon->dclk_max_div = 127; > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > + tcon_mul = bpp / lanes; > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > /* Set dithering if needed */ > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > sun4i_tcon *tcon, > > */ > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > tcon_div &= GENMASK(6, 0); > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > + block_space = mode->htotal * tcon_div * tcon_mul; > > block_space -= mode->hdisplay + 40; > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > sun4i_tcon *tcon, > > > > tcon->dclk_min_div = 7; > > tcon->dclk_max_div = 7; > > - sun4i_tcon0_mode_set_common(tcon, mode); > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > /* Set dithering if needed */ > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > sun4i_tcon *tcon, > > > > tcon->dclk_min_div = 6; > > tcon->dclk_max_div = 127; > > - sun4i_tcon0_mode_set_common(tcon, mode); > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > /* Set dithering if needed */ > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > index 5c3ad5be0690..a07090579f84 100644 > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > @@ -13,8 +13,6 @@ > > #include <drm/drm_encoder.h> > > #include <drm/drm_mipi_dsi.h> > > > > -#define SUN6I_DSI_TCON_DIV 4 > > - > > struct sun6i_dsi { > > struct drm_connector connector; > > struct drm_encoder encoder; > > I had more something like this in mind: > http://code.bulix.org/nlp5a4-803511 Worth to look at it. was it working on your panel? meanwhile I will check it. We have updated with below change [1], seems working on but is actually checking the each divider as before start with 4... till 127. This new approach, is start looking the best divider from 4.. based on the idea vs rounded it will ended up best divider like [2] https://gist.github.com/openedev/7e2c33248b372d29be9979e06d483673 https://gist.github.com/openedev/c72dfffc0ca59e7ec1edcd7ad360cdd1 Jagan.
Hi On Sat., 20 Jul. 2019, 8:58 am Maxime Ripard, <maxime.ripard@bootlin.com> wrote: > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi > wrote: > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > you need to have a clock that is able to put outside bits and speed > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > the display. > > > > > > So this is what the issue is then? > > > > > > This one does make sense, and you should just change the rate in the > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > I'm still wondering why that hasn't been brought up in either the > > > discussion or the commit log before though. > > > > > Something like this? > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > index 64c43ee6bd92..42560d5c327c 100644 > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > drm_display_mode *mode, > > } > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > - const struct drm_display_mode > *mode) > > + const struct drm_display_mode > *mode, > > + u32 tcon_mul) > > { > > /* Configure the dot clock */ > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > /* Set the resolution */ > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > sun4i_tcon *tcon, > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > u8 lanes = device->lanes; > > u32 block_space, start_delay; > > - u32 tcon_div; > > + u32 tcon_div, tcon_mul; > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > + tcon->dclk_min_div = 4; > > + tcon->dclk_max_div = 127; > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > + tcon_mul = bpp / lanes; > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > /* Set dithering if needed */ > > sun4i_tcon0_mode_set_dithering(tcon, > sun4i_tcon_get_connector(encoder)); > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > sun4i_tcon *tcon, > > */ > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > tcon_div &= GENMASK(6, 0); > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > + block_space = mode->htotal * tcon_div * tcon_mul; > > block_space -= mode->hdisplay + 40; > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > sun4i_tcon *tcon, > > > > tcon->dclk_min_div = 7; > > tcon->dclk_max_div = 7; > > - sun4i_tcon0_mode_set_common(tcon, mode); > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > /* Set dithering if needed */ > > sun4i_tcon0_mode_set_dithering(tcon, > sun4i_tcon_get_connector(encoder)); > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > sun4i_tcon *tcon, > > > > tcon->dclk_min_div = 6; > > tcon->dclk_max_div = 127; > > - sun4i_tcon0_mode_set_common(tcon, mode); > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > /* Set dithering if needed */ > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > index 5c3ad5be0690..a07090579f84 100644 > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > @@ -13,8 +13,6 @@ > > #include <drm/drm_encoder.h> > > #include <drm/drm_mipi_dsi.h> > > > > -#define SUN6I_DSI_TCON_DIV 4 > > - > > struct sun6i_dsi { > > struct drm_connector connector; > > struct drm_encoder encoder; > > I had more something like this in mind: > http://code.bulix.org/nlp5a4-803511 I sent another patch to jagan and I'm fully agree that the proper change need to show the reason and not change constraints as we discuss We are on same line Thank you > > > > > > You really don't need to change the divider range (or this is another > issue that the one you mentionned). > > Maxime > > -- > Maxime Ripard, Bootlin > Embedded Linux and Kernel engineering > https://bootlin.com >
On Sat, Jul 20, 2019 at 12:46 PM Jagan Teki <jagan@amarulasolutions.com> wrote: > > On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard > <maxime.ripard@bootlin.com> wrote: > > > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > > you need to have a clock that is able to put outside bits and speed > > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > > the display. > > > > > > > > So this is what the issue is then? > > > > > > > > This one does make sense, and you should just change the rate in the > > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > > > I'm still wondering why that hasn't been brought up in either the > > > > discussion or the commit log before though. > > > > > > > Something like this? > > > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > index 64c43ee6bd92..42560d5c327c 100644 > > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > > drm_display_mode *mode, > > > } > > > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > > - const struct drm_display_mode *mode) > > > + const struct drm_display_mode *mode, > > > + u32 tcon_mul) > > > { > > > /* Configure the dot clock */ > > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > > > /* Set the resolution */ > > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > sun4i_tcon *tcon, > > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > > u8 lanes = device->lanes; > > > u32 block_space, start_delay; > > > - u32 tcon_div; > > > + u32 tcon_div, tcon_mul; > > > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > > + tcon->dclk_min_div = 4; > > > + tcon->dclk_max_div = 127; > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > + tcon_mul = bpp / lanes; > > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > > > /* Set dithering if needed */ > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > sun4i_tcon *tcon, > > > */ > > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > > tcon_div &= GENMASK(6, 0); > > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > > + block_space = mode->htotal * tcon_div * tcon_mul; > > > block_space -= mode->hdisplay + 40; > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > > sun4i_tcon *tcon, > > > > > > tcon->dclk_min_div = 7; > > > tcon->dclk_max_div = 7; > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > /* Set dithering if needed */ > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > > sun4i_tcon *tcon, > > > > > > tcon->dclk_min_div = 6; > > > tcon->dclk_max_div = 127; > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > /* Set dithering if needed */ > > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > index 5c3ad5be0690..a07090579f84 100644 > > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > @@ -13,8 +13,6 @@ > > > #include <drm/drm_encoder.h> > > > #include <drm/drm_mipi_dsi.h> > > > > > > -#define SUN6I_DSI_TCON_DIV 4 > > > - > > > struct sun6i_dsi { > > > struct drm_connector connector; > > > struct drm_encoder encoder; > > > > I had more something like this in mind: > > http://code.bulix.org/nlp5a4-803511 > > Worth to look at it. was it working on your panel? meanwhile I will check it. > > We have updated with below change [1], seems working on but is > actually checking the each divider as before start with 4... till 127. > > This new approach, is start looking the best divider from 4.. based on > the idea vs rounded it will ended up best divider like [2] > > https://gist.github.com/openedev/7e2c33248b372d29be9979e06d483673 > https://gist.github.com/openedev/c72dfffc0ca59e7ec1edcd7ad360cdd1 I made quick check on two possibilities. 1) with Maxime change https://gist.github.com/openedev/3b0b3d35ced6d89f5be0831f1cc9d840 https://gist.github.com/openedev/dd6a9e528cde80ef0508cb54723f505d 2) with Maxime change along with min 4, max 127 divider values. The outcome similar like 1) This look it will depends on divider, need to check further on this page. Jagan.
On Sat, Jul 20, 2019 at 12:46:27PM +0530, Jagan Teki wrote: > On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard > <maxime.ripard@bootlin.com> wrote: > > > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > > you need to have a clock that is able to put outside bits and speed > > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > > the display. > > > > > > > > So this is what the issue is then? > > > > > > > > This one does make sense, and you should just change the rate in the > > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > > > I'm still wondering why that hasn't been brought up in either the > > > > discussion or the commit log before though. > > > > > > > Something like this? > > > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > index 64c43ee6bd92..42560d5c327c 100644 > > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > > drm_display_mode *mode, > > > } > > > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > > - const struct drm_display_mode *mode) > > > + const struct drm_display_mode *mode, > > > + u32 tcon_mul) > > > { > > > /* Configure the dot clock */ > > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > > > /* Set the resolution */ > > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > sun4i_tcon *tcon, > > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > > u8 lanes = device->lanes; > > > u32 block_space, start_delay; > > > - u32 tcon_div; > > > + u32 tcon_div, tcon_mul; > > > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > > + tcon->dclk_min_div = 4; > > > + tcon->dclk_max_div = 127; > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > + tcon_mul = bpp / lanes; > > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > > > /* Set dithering if needed */ > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > sun4i_tcon *tcon, > > > */ > > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > > tcon_div &= GENMASK(6, 0); > > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > > + block_space = mode->htotal * tcon_div * tcon_mul; > > > block_space -= mode->hdisplay + 40; > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > > sun4i_tcon *tcon, > > > > > > tcon->dclk_min_div = 7; > > > tcon->dclk_max_div = 7; > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > /* Set dithering if needed */ > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > > sun4i_tcon *tcon, > > > > > > tcon->dclk_min_div = 6; > > > tcon->dclk_max_div = 127; > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > /* Set dithering if needed */ > > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > index 5c3ad5be0690..a07090579f84 100644 > > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > @@ -13,8 +13,6 @@ > > > #include <drm/drm_encoder.h> > > > #include <drm/drm_mipi_dsi.h> > > > > > > -#define SUN6I_DSI_TCON_DIV 4 > > > - > > > struct sun6i_dsi { > > > struct drm_connector connector; > > > struct drm_encoder encoder; > > > > I had more something like this in mind: > > http://code.bulix.org/nlp5a4-803511 > > Worth to look at it. was it working on your panel? meanwhile I will check it. I haven't tested it. > We have updated with below change [1], seems working on but is > actually checking the each divider as before start with 4... till 127. > > This new approach, is start looking the best divider from 4.. based on > the idea vs rounded it will ended up best divider like [2] But why? I mean, it's not like it's the first time I'm asking this... If the issue is what Micheal described, then the divider has nothing to do with it. We've had that discussion over and over again. So you need to come with some argument and proof that the divider of that clock need to change. Otherwise, stop trying to make that happen: it won't. Maxime -- Maxime Ripard, Bootlin Embedded Linux and Kernel engineering https://bootlin.com
Hi On Sat, Jul 20, 2019 at 11:32 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Sat, Jul 20, 2019 at 12:46:27PM +0530, Jagan Teki wrote: > > On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard > > <maxime.ripard@bootlin.com> wrote: > > > > > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > > > you need to have a clock that is able to put outside bits and speed > > > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > > > the display. > > > > > > > > > > So this is what the issue is then? > > > > > > > > > > This one does make sense, and you should just change the rate in the > > > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > > > > > I'm still wondering why that hasn't been brought up in either the > > > > > discussion or the commit log before though. > > > > > > > > > Something like this? > > > > > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > index 64c43ee6bd92..42560d5c327c 100644 > > > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > > > drm_display_mode *mode, > > > > } > > > > > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > > > - const struct drm_display_mode *mode) > > > > + const struct drm_display_mode *mode, > > > > + u32 tcon_mul) > > > > { > > > > /* Configure the dot clock */ > > > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > > > > > /* Set the resolution */ > > > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > sun4i_tcon *tcon, > > > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > > > u8 lanes = device->lanes; > > > > u32 block_space, start_delay; > > > > - u32 tcon_div; > > > > + u32 tcon_div, tcon_mul; > > > > > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > > > + tcon->dclk_min_div = 4; > > > > + tcon->dclk_max_div = 127; > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > + tcon_mul = bpp / lanes; > > > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > > > > > /* Set dithering if needed */ > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > sun4i_tcon *tcon, > > > > */ > > > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > > > tcon_div &= GENMASK(6, 0); > > > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > > > + block_space = mode->htotal * tcon_div * tcon_mul; > > > > block_space -= mode->hdisplay + 40; > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > > > sun4i_tcon *tcon, > > > > > > > > tcon->dclk_min_div = 7; > > > > tcon->dclk_max_div = 7; > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > /* Set dithering if needed */ > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > > > sun4i_tcon *tcon, > > > > > > > > tcon->dclk_min_div = 6; > > > > tcon->dclk_max_div = 127; > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > /* Set dithering if needed */ > > > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > index 5c3ad5be0690..a07090579f84 100644 > > > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > @@ -13,8 +13,6 @@ > > > > #include <drm/drm_encoder.h> > > > > #include <drm/drm_mipi_dsi.h> > > > > > > > > -#define SUN6I_DSI_TCON_DIV 4 > > > > - > > > > struct sun6i_dsi { > > > > struct drm_connector connector; > > > > struct drm_encoder encoder; > > > > > > I had more something like this in mind: > > > http://code.bulix.org/nlp5a4-803511 > > > > Worth to look at it. was it working on your panel? meanwhile I will check it. > > I haven't tested it. > > > We have updated with below change [1], seems working on but is > > actually checking the each divider as before start with 4... till 127. > > > > This new approach, is start looking the best divider from 4.. based on > > the idea vs rounded it will ended up best divider like [2] > > But why? > > I mean, it's not like it's the first time I'm asking this... > > If the issue is what Micheal described, then the divider has nothing > to do with it. We've had that discussion over and over again. > Sorry to quick copy and paste but my idea is somenthing like: --- drivers/gpu/drm/sun4i/sun4i_dotclock.c | 5 ++++- drivers/gpu/drm/sun4i/sun4i_tcon.c | 9 ++++++--- drivers/gpu/drm/sun4i/sun4i_tcon.h | 1 + drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- 4 files changed, 11 insertions(+), 6 deletions(-) diff --git a/drivers/gpu/drm/sun4i/sun4i_dotclock.c b/drivers/gpu/drm/sun4i/sun4i_dotclock.c index 417ade3d2565..b8be67cbb037 100644 --- a/drivers/gpu/drm/sun4i/sun4i_dotclock.c +++ b/drivers/gpu/drm/sun4i/sun4i_dotclock.c @@ -74,12 +74,15 @@ static long sun4i_dclk_round_rate(struct clk_hw *hw, unsigned long rate, struct sun4i_tcon *tcon = dclk->tcon; unsigned long best_parent = 0; u8 best_div = 1; + u64 ideal = (u64)rate * tcon->dclk_mul; int i; for (i = tcon->dclk_min_div; i <= tcon->dclk_max_div; i++) { - u64 ideal = (u64)rate * i; unsigned long rounded; + if (!tcon->dclk_mul) + ideal = (u64)rate * i; + /* * ideal has overflowed the max value that can be stored in an * unsigned long, and every clk operation we might do on a diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c b/drivers/gpu/drm/sun4i/sun4i_tcon.c index 64c43ee6bd92..3301952bcf32 100644 --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c @@ -337,8 +337,9 @@ static void sun4i_tcon0_mode_set_cpu(struct sun4i_tcon *tcon, u32 block_space, start_delay; u32 tcon_div; - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; + tcon->dclk_min_div = 4; + tcon->dclk_max_div = 127; + tcon->dclk_mul = bpp / lanes; sun4i_tcon0_mode_set_common(tcon, mode); @@ -366,7 +367,7 @@ static void sun4i_tcon0_mode_set_cpu(struct sun4i_tcon *tcon, */ regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); tcon_div &= GENMASK(6, 0); - block_space = mode->htotal * bpp / (tcon_div * lanes); + block_space = mode->htotal * tcon_div * tcon->dclk_mul; block_space -= mode->hdisplay + 40; regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, @@ -408,6 +409,7 @@ static void sun4i_tcon0_mode_set_lvds(struct sun4i_tcon *tcon, tcon->dclk_min_div = 7; tcon->dclk_max_div = 7; + tcon->dclk_mul = 0; sun4i_tcon0_mode_set_common(tcon, mode); /* Set dithering if needed */ @@ -487,6 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct sun4i_tcon *tcon, tcon->dclk_min_div = 6; tcon->dclk_max_div = 127; + tcon->dclk_mul = 0; sun4i_tcon0_mode_set_common(tcon, mode); /* Set dithering if needed */ diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.h b/drivers/gpu/drm/sun4i/sun4i_tcon.h index f9f1fe80b206..44b69533778e 100644 --- a/drivers/gpu/drm/sun4i/sun4i_tcon.h +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.h @@ -248,6 +248,7 @@ struct sun4i_tcon { struct clk *dclk; u8 dclk_max_div; u8 dclk_min_div; + u8 dclk_mul; /* Reset control */ struct reset_control *lcd_rst; diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h index 5c3ad5be0690..a07090579f84 100644 --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h @@ -13,8 +13,6 @@ #include <drm/drm_encoder.h> #include <drm/drm_mipi_dsi.h> -#define SUN6I_DSI_TCON_DIV 4 - struct sun6i_dsi { struct drm_connector connector; struct drm_encoder encoder;
Hi Maxime, On Sat, Jul 20, 2019 at 3:02 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Sat, Jul 20, 2019 at 12:46:27PM +0530, Jagan Teki wrote: > > On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard > > <maxime.ripard@bootlin.com> wrote: > > > > > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > > > you need to have a clock that is able to put outside bits and speed > > > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > > > the display. > > > > > > > > > > So this is what the issue is then? > > > > > > > > > > This one does make sense, and you should just change the rate in the > > > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > > > > > I'm still wondering why that hasn't been brought up in either the > > > > > discussion or the commit log before though. > > > > > > > > > Something like this? > > > > > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > index 64c43ee6bd92..42560d5c327c 100644 > > > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > > > drm_display_mode *mode, > > > > } > > > > > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > > > - const struct drm_display_mode *mode) > > > > + const struct drm_display_mode *mode, > > > > + u32 tcon_mul) > > > > { > > > > /* Configure the dot clock */ > > > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > > > > > /* Set the resolution */ > > > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > sun4i_tcon *tcon, > > > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > > > u8 lanes = device->lanes; > > > > u32 block_space, start_delay; > > > > - u32 tcon_div; > > > > + u32 tcon_div, tcon_mul; > > > > > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > > > + tcon->dclk_min_div = 4; > > > > + tcon->dclk_max_div = 127; > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > + tcon_mul = bpp / lanes; > > > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > > > > > /* Set dithering if needed */ > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > sun4i_tcon *tcon, > > > > */ > > > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > > > tcon_div &= GENMASK(6, 0); > > > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > > > + block_space = mode->htotal * tcon_div * tcon_mul; > > > > block_space -= mode->hdisplay + 40; > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > > > sun4i_tcon *tcon, > > > > > > > > tcon->dclk_min_div = 7; > > > > tcon->dclk_max_div = 7; > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > /* Set dithering if needed */ > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > > > sun4i_tcon *tcon, > > > > > > > > tcon->dclk_min_div = 6; > > > > tcon->dclk_max_div = 127; > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > /* Set dithering if needed */ > > > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > index 5c3ad5be0690..a07090579f84 100644 > > > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > @@ -13,8 +13,6 @@ > > > > #include <drm/drm_encoder.h> > > > > #include <drm/drm_mipi_dsi.h> > > > > > > > > -#define SUN6I_DSI_TCON_DIV 4 > > > > - > > > > struct sun6i_dsi { > > > > struct drm_connector connector; > > > > struct drm_encoder encoder; > > > > > > I had more something like this in mind: > > > http://code.bulix.org/nlp5a4-803511 > > > > Worth to look at it. was it working on your panel? meanwhile I will check it. > > I haven't tested it. > > > We have updated with below change [1], seems working on but is > > actually checking the each divider as before start with 4... till 127. > > > > This new approach, is start looking the best divider from 4.. based on > > the idea vs rounded it will ended up best divider like [2] > > But why? > > I mean, it's not like it's the first time I'm asking this... > > If the issue is what Micheal described, then the divider has nothing > to do with it. We've had that discussion over and over again. This is what Michael is mentioned in above mail "tcon-pixel clock is the rate that you want to achive on display side and if you have 4 lanes 32bit or lanes and different bit number that you need to have a clock that is able to put outside bits and speed equal to pixel-clock * bits / lanes. so If you want a pixel-clock of 40 mhz and you have 32bits and 4 lanes you need to have a clock of 40 * 32 / 4 in no-burst mode. " He is trying to manage the bpp/lanes into dclk_mul (in last mail) and it can multiply with pixel clock which is rate argument in sun4i_dclk_round_rate. The solution I have mentioned in dclk_min, max is bpp/lanes also multiple rate in dotclock sun4i_dclk_round_rate. In both cases the overall pll_rate depends on dividers, the one that I have on this patch is based on BSP and the Michael one is more generic way so-that it can not to touch other functionalities and looping dividers to find the best one. If dclk_min/max is bpp/lanes then dotclock directly using divider 6 (assuming 24-bit and 4 lanes) and return the pll_rate and divider 6 associated. if dclk_mul is bpp/lanes, on Michael new change, the dividers start with 4 and end with 127 but the constant ideal rate which rate * bpp/lanes but the loop from sun4i_dclk_round_rate computed the divider as 6 only, ie what I'm mentioned on the above mail. Jagan.
Hi Jagan On Mon, Jul 22, 2019 at 12:21 PM Jagan Teki <jagan@amarulasolutions.com> wrote: > > Hi Maxime, > > On Sat, Jul 20, 2019 at 3:02 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > On Sat, Jul 20, 2019 at 12:46:27PM +0530, Jagan Teki wrote: > > > On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard > > > <maxime.ripard@bootlin.com> wrote: > > > > > > > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > > > > you need to have a clock that is able to put outside bits and speed > > > > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > > > > the display. > > > > > > > > > > > > So this is what the issue is then? > > > > > > > > > > > > This one does make sense, and you should just change the rate in the > > > > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > > > > > > > I'm still wondering why that hasn't been brought up in either the > > > > > > discussion or the commit log before though. > > > > > > > > > > > Something like this? > > > > > > > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > > > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > > > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > index 64c43ee6bd92..42560d5c327c 100644 > > > > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > > > > drm_display_mode *mode, > > > > > } > > > > > > > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > > > > - const struct drm_display_mode *mode) > > > > > + const struct drm_display_mode *mode, > > > > > + u32 tcon_mul) > > > > > { > > > > > /* Configure the dot clock */ > > > > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > > > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > > > > > > > /* Set the resolution */ > > > > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > > > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > sun4i_tcon *tcon, > > > > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > > > > u8 lanes = device->lanes; > > > > > u32 block_space, start_delay; > > > > > - u32 tcon_div; > > > > > + u32 tcon_div, tcon_mul; > > > > > > > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > > > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > > > > + tcon->dclk_min_div = 4; > > > > > + tcon->dclk_max_div = 127; > > > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > + tcon_mul = bpp / lanes; > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > > > > > > > /* Set dithering if needed */ > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > sun4i_tcon *tcon, > > > > > */ > > > > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > > > > tcon_div &= GENMASK(6, 0); > > > > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > > > > + block_space = mode->htotal * tcon_div * tcon_mul; > > > > > block_space -= mode->hdisplay + 40; > > > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > > > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > > > > sun4i_tcon *tcon, > > > > > > > > > > tcon->dclk_min_div = 7; > > > > > tcon->dclk_max_div = 7; > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > /* Set dithering if needed */ > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > > > > sun4i_tcon *tcon, > > > > > > > > > > tcon->dclk_min_div = 6; > > > > > tcon->dclk_max_div = 127; > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > /* Set dithering if needed */ > > > > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > > > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > index 5c3ad5be0690..a07090579f84 100644 > > > > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > @@ -13,8 +13,6 @@ > > > > > #include <drm/drm_encoder.h> > > > > > #include <drm/drm_mipi_dsi.h> > > > > > > > > > > -#define SUN6I_DSI_TCON_DIV 4 > > > > > - > > > > > struct sun6i_dsi { > > > > > struct drm_connector connector; > > > > > struct drm_encoder encoder; > > > > > > > > I had more something like this in mind: > > > > http://code.bulix.org/nlp5a4-803511 > > > > > > Worth to look at it. was it working on your panel? meanwhile I will check it. > > > > I haven't tested it. > > > > > We have updated with below change [1], seems working on but is > > > actually checking the each divider as before start with 4... till 127. > > > > > > This new approach, is start looking the best divider from 4.. based on > > > the idea vs rounded it will ended up best divider like [2] > > > > But why? > > > > I mean, it's not like it's the first time I'm asking this... > > > > If the issue is what Micheal described, then the divider has nothing > > to do with it. We've had that discussion over and over again. > > This is what Michael is mentioned in above mail > "tcon-pixel clock is the rate that you want to achive on display side and > if you have 4 lanes 32bit or lanes and different bit number that you need > to have a clock that is able to put outside bits and speed equal to > pixel-clock * bits / lanes. so If you want a pixel-clock of 40 mhz > and you have 32bits and 4 lanes you need to have a clock of > 40 * 32 / 4 in no-burst mode. " > > He is trying to manage the bpp/lanes into dclk_mul (in last mail) and > it can multiply with pixel clock which is rate argument in > sun4i_dclk_round_rate. > > The solution I have mentioned in dclk_min, max is bpp/lanes also > multiple rate in dotclock sun4i_dclk_round_rate. > > In both cases the overall pll_rate depends on dividers, the one that I > have on this patch is based on BSP and the Michael one is more generic > way so-that it can not to touch other functionalities and looping > dividers to find the best one. > > If dclk_min/max is bpp/lanes then dotclock directly using divider 6 > (assuming 24-bit and 4 lanes) and return the pll_rate and divider 6 > associated. > > if dclk_mul is bpp/lanes, on Michael new change, the dividers start > with 4 and end with 127 but the constant ideal rate which rate * > bpp/lanes but the loop from sun4i_dclk_round_rate computed the divider > as 6 only, ie what I'm mentioned on the above mail. > tcon-pixel clock and tcon are mutual connected. The code is done in a way that optimal clock need to be search. Now the patch that I propose is more connected to the description I gave. I need some comment from Maxime, what he prefers or we need to search for a different one. I don't had time to check Maxime proposal because I'm working on other projects. Michael > Jagan.
On Mon, Jul 22, 2019 at 3:55 PM Michael Nazzareno Trimarchi <michael@amarulasolutions.com> wrote: > > Hi Jagan > > On Mon, Jul 22, 2019 at 12:21 PM Jagan Teki <jagan@amarulasolutions.com> wrote: > > > > Hi Maxime, > > > > On Sat, Jul 20, 2019 at 3:02 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > On Sat, Jul 20, 2019 at 12:46:27PM +0530, Jagan Teki wrote: > > > > On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard > > > > <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > > > > > you need to have a clock that is able to put outside bits and speed > > > > > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > > > > > the display. > > > > > > > > > > > > > > So this is what the issue is then? > > > > > > > > > > > > > > This one does make sense, and you should just change the rate in the > > > > > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > > > > > > > > > I'm still wondering why that hasn't been brought up in either the > > > > > > > discussion or the commit log before though. > > > > > > > > > > > > > Something like this? > > > > > > > > > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > > > > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > > > > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > index 64c43ee6bd92..42560d5c327c 100644 > > > > > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > > > > > drm_display_mode *mode, > > > > > > } > > > > > > > > > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > > > > > - const struct drm_display_mode *mode) > > > > > > + const struct drm_display_mode *mode, > > > > > > + u32 tcon_mul) > > > > > > { > > > > > > /* Configure the dot clock */ > > > > > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > > > > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > > > > > > > > > /* Set the resolution */ > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > > > > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > sun4i_tcon *tcon, > > > > > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > > > > > u8 lanes = device->lanes; > > > > > > u32 block_space, start_delay; > > > > > > - u32 tcon_div; > > > > > > + u32 tcon_div, tcon_mul; > > > > > > > > > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > > > > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > > > > > + tcon->dclk_min_div = 4; > > > > > > + tcon->dclk_max_div = 127; > > > > > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > + tcon_mul = bpp / lanes; > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > sun4i_tcon *tcon, > > > > > > */ > > > > > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > > > > > tcon_div &= GENMASK(6, 0); > > > > > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > > > > > + block_space = mode->htotal * tcon_div * tcon_mul; > > > > > > block_space -= mode->hdisplay + 40; > > > > > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > > > > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > tcon->dclk_min_div = 7; > > > > > > tcon->dclk_max_div = 7; > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > tcon->dclk_min_div = 6; > > > > > > tcon->dclk_max_div = 127; > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > index 5c3ad5be0690..a07090579f84 100644 > > > > > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > @@ -13,8 +13,6 @@ > > > > > > #include <drm/drm_encoder.h> > > > > > > #include <drm/drm_mipi_dsi.h> > > > > > > > > > > > > -#define SUN6I_DSI_TCON_DIV 4 > > > > > > - > > > > > > struct sun6i_dsi { > > > > > > struct drm_connector connector; > > > > > > struct drm_encoder encoder; > > > > > > > > > > I had more something like this in mind: > > > > > http://code.bulix.org/nlp5a4-803511 > > > > > > > > Worth to look at it. was it working on your panel? meanwhile I will check it. > > > > > > I haven't tested it. > > > > > > > We have updated with below change [1], seems working on but is > > > > actually checking the each divider as before start with 4... till 127. > > > > > > > > This new approach, is start looking the best divider from 4.. based on > > > > the idea vs rounded it will ended up best divider like [2] > > > > > > But why? > > > > > > I mean, it's not like it's the first time I'm asking this... > > > > > > If the issue is what Micheal described, then the divider has nothing > > > to do with it. We've had that discussion over and over again. > > > > This is what Michael is mentioned in above mail > > "tcon-pixel clock is the rate that you want to achive on display side and > > if you have 4 lanes 32bit or lanes and different bit number that you need > > to have a clock that is able to put outside bits and speed equal to > > pixel-clock * bits / lanes. so If you want a pixel-clock of 40 mhz > > and you have 32bits and 4 lanes you need to have a clock of > > 40 * 32 / 4 in no-burst mode. " > > > > He is trying to manage the bpp/lanes into dclk_mul (in last mail) and > > it can multiply with pixel clock which is rate argument in > > sun4i_dclk_round_rate. > > > > The solution I have mentioned in dclk_min, max is bpp/lanes also > > multiple rate in dotclock sun4i_dclk_round_rate. > > > > In both cases the overall pll_rate depends on dividers, the one that I > > have on this patch is based on BSP and the Michael one is more generic > > way so-that it can not to touch other functionalities and looping > > dividers to find the best one. > > > > If dclk_min/max is bpp/lanes then dotclock directly using divider 6 > > (assuming 24-bit and 4 lanes) and return the pll_rate and divider 6 > > associated. > > > > if dclk_mul is bpp/lanes, on Michael new change, the dividers start > > with 4 and end with 127 but the constant ideal rate which rate * > > bpp/lanes but the loop from sun4i_dclk_round_rate computed the divider > > as 6 only, ie what I'm mentioned on the above mail. > > > > tcon-pixel clock and tcon are mutual connected. The code is done in a way > that optimal clock need to be search. Now the patch that I propose is more > connected to the description I gave. True, ie what I'm trying to say in above mail. My idea on the above mail is to give more information on the both the solutions (one on the this patch and another you mentioned on above mail) are depends on divider value for computing desired pll_rate. > > I need some comment from Maxime, what he prefers or we need to search for > a different one. I don't had time to check Maxime proposal because I'm working > on other projects. I already provide my logs on Maxime change.if you want you can have a look.
On Mon, Jul 22, 2019 at 03:51:04PM +0530, Jagan Teki wrote: > Hi Maxime, > > On Sat, Jul 20, 2019 at 3:02 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > On Sat, Jul 20, 2019 at 12:46:27PM +0530, Jagan Teki wrote: > > > On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard > > > <maxime.ripard@bootlin.com> wrote: > > > > > > > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > > > > you need to have a clock that is able to put outside bits and speed > > > > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > > > > the display. > > > > > > > > > > > > So this is what the issue is then? > > > > > > > > > > > > This one does make sense, and you should just change the rate in the > > > > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > > > > > > > I'm still wondering why that hasn't been brought up in either the > > > > > > discussion or the commit log before though. > > > > > > > > > > > Something like this? > > > > > > > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > > > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > > > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > index 64c43ee6bd92..42560d5c327c 100644 > > > > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > > > > drm_display_mode *mode, > > > > > } > > > > > > > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > > > > - const struct drm_display_mode *mode) > > > > > + const struct drm_display_mode *mode, > > > > > + u32 tcon_mul) > > > > > { > > > > > /* Configure the dot clock */ > > > > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > > > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > > > > > > > /* Set the resolution */ > > > > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > > > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > sun4i_tcon *tcon, > > > > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > > > > u8 lanes = device->lanes; > > > > > u32 block_space, start_delay; > > > > > - u32 tcon_div; > > > > > + u32 tcon_div, tcon_mul; > > > > > > > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > > > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > > > > + tcon->dclk_min_div = 4; > > > > > + tcon->dclk_max_div = 127; > > > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > + tcon_mul = bpp / lanes; > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > > > > > > > /* Set dithering if needed */ > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > sun4i_tcon *tcon, > > > > > */ > > > > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > > > > tcon_div &= GENMASK(6, 0); > > > > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > > > > + block_space = mode->htotal * tcon_div * tcon_mul; > > > > > block_space -= mode->hdisplay + 40; > > > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > > > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > > > > sun4i_tcon *tcon, > > > > > > > > > > tcon->dclk_min_div = 7; > > > > > tcon->dclk_max_div = 7; > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > /* Set dithering if needed */ > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > > > > sun4i_tcon *tcon, > > > > > > > > > > tcon->dclk_min_div = 6; > > > > > tcon->dclk_max_div = 127; > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > /* Set dithering if needed */ > > > > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > > > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > index 5c3ad5be0690..a07090579f84 100644 > > > > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > @@ -13,8 +13,6 @@ > > > > > #include <drm/drm_encoder.h> > > > > > #include <drm/drm_mipi_dsi.h> > > > > > > > > > > -#define SUN6I_DSI_TCON_DIV 4 > > > > > - > > > > > struct sun6i_dsi { > > > > > struct drm_connector connector; > > > > > struct drm_encoder encoder; > > > > > > > > I had more something like this in mind: > > > > http://code.bulix.org/nlp5a4-803511 > > > > > > Worth to look at it. was it working on your panel? meanwhile I will check it. > > > > I haven't tested it. > > > > > We have updated with below change [1], seems working on but is > > > actually checking the each divider as before start with 4... till 127. > > > > > > This new approach, is start looking the best divider from 4.. based on > > > the idea vs rounded it will ended up best divider like [2] > > > > But why? > > > > I mean, it's not like it's the first time I'm asking this... > > > > If the issue is what Micheal described, then the divider has nothing > > to do with it. We've had that discussion over and over again. > > This is what Michael is mentioned in above mail "tcon-pixel clock is > the rate that you want to achive on display side and if you have 4 > lanes 32bit or lanes and different bit number that you need to have > a clock that is able to put outside bits and speed equal to > pixel-clock * bits / lanes. so If you want a pixel-clock of 40 mhz > and you have 32bits and 4 lanes you need to have a clock of 40 * 32 > / 4 in no-burst mode. " Yeah, so we need to change the clock rate. > He is trying to manage the bpp/lanes into dclk_mul (in last mail) > and it can multiply with pixel clock which is rate argument in > sun4i_dclk_round_rate. > > The solution I have mentioned in dclk_min, max is bpp/lanes also > multiple rate in dotclock sun4i_dclk_round_rate. > > In both cases the overall pll_rate depends on dividers, the one that I > have on this patch is based on BSP and the Michael one is more generic > way so-that it can not to touch other functionalities and looping > dividers to find the best one. > > If dclk_min/max is bpp/lanes then dotclock directly using divider 6 > (assuming 24-bit and 4 lanes) and return the pll_rate and divider 6 > associated. > > if dclk_mul is bpp/lanes, on Michael new change, the dividers start > with 4 and end with 127 but the constant ideal rate which rate * > bpp/lanes but the loop from sun4i_dclk_round_rate computed the divider > as 6 only, ie what I'm mentioned on the above mail. We've been over this a couple of times already. The clock is generated like this: PLL -> TCON Module Clock -> TCON DCLK You want the TCON DCLK to be at the pixel clock rate * bpp / lanes. Fine, that makes sense. Except that the patch you've sent, instead of changing the rate itself, changes the ratio between the module clock and DCLK. And this is where the issue lies. First, from a logical viewpoint, it doesn't make sense. If you want to change the clock rate, then just do it. Don't hack around the multipliers trying to fall back to something that works for you. Then, the ratio itself needs to be set to 4. This is the part that we've discussed way too many times already, but in the Allwinner BSP, that ratio is hardcoded to 4, and we've had panels that need it at that value. So, what you want to do is to have: TCON DCLK = pixel clock * bpp / lanes TCON Module Clock = DCLK * 4 PLL = Module Clock * Module Clock Divider (which I believe is 1 in most cases) So you want to increase the PLL. Fortunately for use, this is exactly what a call to clk_set_rate will end up doing. Maxime -- Maxime Ripard, Bootlin Embedded Linux and Kernel engineering https://bootlin.com
Hi On Wed, Jul 24, 2019 at 11:05 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Mon, Jul 22, 2019 at 03:51:04PM +0530, Jagan Teki wrote: > > Hi Maxime, > > > > On Sat, Jul 20, 2019 at 3:02 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > On Sat, Jul 20, 2019 at 12:46:27PM +0530, Jagan Teki wrote: > > > > On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard > > > > <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > > > > > you need to have a clock that is able to put outside bits and speed > > > > > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > > > > > the display. > > > > > > > > > > > > > > So this is what the issue is then? > > > > > > > > > > > > > > This one does make sense, and you should just change the rate in the > > > > > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > > > > > > > > > I'm still wondering why that hasn't been brought up in either the > > > > > > > discussion or the commit log before though. > > > > > > > > > > > > > Something like this? > > > > > > > > > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > > > > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > > > > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > index 64c43ee6bd92..42560d5c327c 100644 > > > > > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > > > > > drm_display_mode *mode, > > > > > > } > > > > > > > > > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > > > > > - const struct drm_display_mode *mode) > > > > > > + const struct drm_display_mode *mode, > > > > > > + u32 tcon_mul) > > > > > > { > > > > > > /* Configure the dot clock */ > > > > > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > > > > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > > > > > > > > > /* Set the resolution */ > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > > > > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > sun4i_tcon *tcon, > > > > > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > > > > > u8 lanes = device->lanes; > > > > > > u32 block_space, start_delay; > > > > > > - u32 tcon_div; > > > > > > + u32 tcon_div, tcon_mul; > > > > > > > > > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > > > > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > > > > > + tcon->dclk_min_div = 4; > > > > > > + tcon->dclk_max_div = 127; > > > > > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > + tcon_mul = bpp / lanes; > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > sun4i_tcon *tcon, > > > > > > */ > > > > > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > > > > > tcon_div &= GENMASK(6, 0); > > > > > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > > > > > + block_space = mode->htotal * tcon_div * tcon_mul; > > > > > > block_space -= mode->hdisplay + 40; > > > > > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > > > > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > tcon->dclk_min_div = 7; > > > > > > tcon->dclk_max_div = 7; > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > tcon->dclk_min_div = 6; > > > > > > tcon->dclk_max_div = 127; > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > index 5c3ad5be0690..a07090579f84 100644 > > > > > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > @@ -13,8 +13,6 @@ > > > > > > #include <drm/drm_encoder.h> > > > > > > #include <drm/drm_mipi_dsi.h> > > > > > > > > > > > > -#define SUN6I_DSI_TCON_DIV 4 > > > > > > - > > > > > > struct sun6i_dsi { > > > > > > struct drm_connector connector; > > > > > > struct drm_encoder encoder; > > > > > > > > > > I had more something like this in mind: > > > > > http://code.bulix.org/nlp5a4-803511 > > > > > > > > Worth to look at it. was it working on your panel? meanwhile I will check it. > > > > > > I haven't tested it. > > > > > > > We have updated with below change [1], seems working on but is > > > > actually checking the each divider as before start with 4... till 127. > > > > > > > > This new approach, is start looking the best divider from 4.. based on > > > > the idea vs rounded it will ended up best divider like [2] > > > > > > But why? > > > > > > I mean, it's not like it's the first time I'm asking this... > > > > > > If the issue is what Micheal described, then the divider has nothing > > > to do with it. We've had that discussion over and over again. > > > > This is what Michael is mentioned in above mail "tcon-pixel clock is > > the rate that you want to achive on display side and if you have 4 > > lanes 32bit or lanes and different bit number that you need to have > > a clock that is able to put outside bits and speed equal to > > pixel-clock * bits / lanes. so If you want a pixel-clock of 40 mhz > > and you have 32bits and 4 lanes you need to have a clock of 40 * 32 > > / 4 in no-burst mode. " > > Yeah, so we need to change the clock rate. > > > He is trying to manage the bpp/lanes into dclk_mul (in last mail) > > and it can multiply with pixel clock which is rate argument in > > sun4i_dclk_round_rate. > > > > The solution I have mentioned in dclk_min, max is bpp/lanes also > > multiple rate in dotclock sun4i_dclk_round_rate. > > > > In both cases the overall pll_rate depends on dividers, the one that I > > have on this patch is based on BSP and the Michael one is more generic > > way so-that it can not to touch other functionalities and looping > > dividers to find the best one. > > > > If dclk_min/max is bpp/lanes then dotclock directly using divider 6 > > (assuming 24-bit and 4 lanes) and return the pll_rate and divider 6 > > associated. > > > > if dclk_mul is bpp/lanes, on Michael new change, the dividers start > > with 4 and end with 127 but the constant ideal rate which rate * > > bpp/lanes but the loop from sun4i_dclk_round_rate computed the divider > > as 6 only, ie what I'm mentioned on the above mail. > > We've been over this a couple of times already. > > The clock is generated like this: > > PLL -> TCON Module Clock -> TCON DCLK > > You want the TCON DCLK to be at the pixel clock rate * bpp / > lanes. Fine, that makes sense. > > Except that the patch you've sent, instead of changing the rate > itself, changes the ratio between the module clock and DCLK. > > And this is where the issue lies. First, from a logical viewpoint, it > doesn't make sense. If you want to change the clock rate, then just do > it. Don't hack around the multipliers trying to fall back to something > that works for you. > > Then, the ratio itself needs to be set to 4. This is the part that > we've discussed way too many times already, but in the Allwinner BSP, > that ratio is hardcoded to 4, and we've had panels that need it at > that value. > > So, what you want to do is to have: > > TCON DCLK = pixel clock * bpp / lanes > TCON Module Clock = DCLK * 4 > PLL = Module Clock * Module Clock Divider (which I believe is 1 in most cases) pll-mipi 1 1 1 178200000 0 0 50000 tcon0 2 2 1 178200000 0 0 50000 tcon-pixel-clock 1 1 1 29700000 0 0 50000 This is an english problem from my side: tcon-pixel-clock is DCLK tcon0 must be tcon-pixel-clock * bpp / lanes because the logic need to put a bit every cycle. One solution can be: - set_rate_exclusive to tcon0 and calculate as display pixel clock * bpp / lanes - calculate the tcon-pixel-clock using all divider Problem is that the function that calculate tcon-pixel-clock does not have any constrain on the ideal value. What you are suggesting is not correct in my opinion or I'm not following your suggesstion. What I know is that if we have a pixel-clock of dvi display of 50Mhz and we have 4 lanes 32bit we need a clock in the logic of 400Mhz (this is the ideal throughtput). So tcon-pixel-clock is 50mhz and tcon0 is 400Mhz. Michael > > So you want to increase the PLL. Fortunately for use, this is exactly > what a call to clk_set_rate will end up doing. > > Maxime > > -- > Maxime Ripard, Bootlin > Embedded Linux and Kernel engineering > https://bootlin.com
Hi Maxime On Mon, Jul 29, 2019 at 8:59 AM Michael Nazzareno Trimarchi <michael@amarulasolutions.com> wrote: > > Hi > > On Wed, Jul 24, 2019 at 11:05 AM Maxime Ripard > <maxime.ripard@bootlin.com> wrote: > > > > On Mon, Jul 22, 2019 at 03:51:04PM +0530, Jagan Teki wrote: > > > Hi Maxime, > > > > > > On Sat, Jul 20, 2019 at 3:02 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > On Sat, Jul 20, 2019 at 12:46:27PM +0530, Jagan Teki wrote: > > > > > On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard > > > > > <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > > > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > > > > > > you need to have a clock that is able to put outside bits and speed > > > > > > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > > > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > > > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > > > > > > the display. > > > > > > > > > > > > > > > > So this is what the issue is then? > > > > > > > > > > > > > > > > This one does make sense, and you should just change the rate in the > > > > > > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > > > > > > > > > > > I'm still wondering why that hasn't been brought up in either the > > > > > > > > discussion or the commit log before though. > > > > > > > > > > > > > > > Something like this? > > > > > > > > > > > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > > > > > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > > > > > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > > > > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > index 64c43ee6bd92..42560d5c327c 100644 > > > > > > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > > > > > > drm_display_mode *mode, > > > > > > > } > > > > > > > > > > > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > > > > > > - const struct drm_display_mode *mode) > > > > > > > + const struct drm_display_mode *mode, > > > > > > > + u32 tcon_mul) > > > > > > > { > > > > > > > /* Configure the dot clock */ > > > > > > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > > > > > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > > > > > > > > > > > /* Set the resolution */ > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > > > > > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > > sun4i_tcon *tcon, > > > > > > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > > > > > > u8 lanes = device->lanes; > > > > > > > u32 block_space, start_delay; > > > > > > > - u32 tcon_div; > > > > > > > + u32 tcon_div, tcon_mul; > > > > > > > > > > > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > > > > > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > > > > > > + tcon->dclk_min_div = 4; > > > > > > > + tcon->dclk_max_div = 127; > > > > > > > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > + tcon_mul = bpp / lanes; > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > > sun4i_tcon *tcon, > > > > > > > */ > > > > > > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > > > > > > tcon_div &= GENMASK(6, 0); > > > > > > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > > > > > > + block_space = mode->htotal * tcon_div * tcon_mul; > > > > > > > block_space -= mode->hdisplay + 40; > > > > > > > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > > > > > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > > > tcon->dclk_min_div = 7; > > > > > > > tcon->dclk_max_div = 7; > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > > > tcon->dclk_min_div = 6; > > > > > > > tcon->dclk_max_div = 127; > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > index 5c3ad5be0690..a07090579f84 100644 > > > > > > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > @@ -13,8 +13,6 @@ > > > > > > > #include <drm/drm_encoder.h> > > > > > > > #include <drm/drm_mipi_dsi.h> > > > > > > > > > > > > > > -#define SUN6I_DSI_TCON_DIV 4 > > > > > > > - > > > > > > > struct sun6i_dsi { > > > > > > > struct drm_connector connector; > > > > > > > struct drm_encoder encoder; > > > > > > > > > > > > I had more something like this in mind: > > > > > > http://code.bulix.org/nlp5a4-803511 > > > > > > > > > > Worth to look at it. was it working on your panel? meanwhile I will check it. > > > > > > > > I haven't tested it. > > > > > > > > > We have updated with below change [1], seems working on but is > > > > > actually checking the each divider as before start with 4... till 127. > > > > > > > > > > This new approach, is start looking the best divider from 4.. based on > > > > > the idea vs rounded it will ended up best divider like [2] > > > > > > > > But why? > > > > > > > > I mean, it's not like it's the first time I'm asking this... > > > > > > > > If the issue is what Micheal described, then the divider has nothing > > > > to do with it. We've had that discussion over and over again. > > > > > > This is what Michael is mentioned in above mail "tcon-pixel clock is > > > the rate that you want to achive on display side and if you have 4 > > > lanes 32bit or lanes and different bit number that you need to have > > > a clock that is able to put outside bits and speed equal to > > > pixel-clock * bits / lanes. so If you want a pixel-clock of 40 mhz > > > and you have 32bits and 4 lanes you need to have a clock of 40 * 32 > > > / 4 in no-burst mode. " > > > > Yeah, so we need to change the clock rate. > > > > > He is trying to manage the bpp/lanes into dclk_mul (in last mail) > > > and it can multiply with pixel clock which is rate argument in > > > sun4i_dclk_round_rate. > > > > > > The solution I have mentioned in dclk_min, max is bpp/lanes also > > > multiple rate in dotclock sun4i_dclk_round_rate. > > > > > > In both cases the overall pll_rate depends on dividers, the one that I > > > have on this patch is based on BSP and the Michael one is more generic > > > way so-that it can not to touch other functionalities and looping > > > dividers to find the best one. > > > > > > If dclk_min/max is bpp/lanes then dotclock directly using divider 6 > > > (assuming 24-bit and 4 lanes) and return the pll_rate and divider 6 > > > associated. > > > > > > if dclk_mul is bpp/lanes, on Michael new change, the dividers start > > > with 4 and end with 127 but the constant ideal rate which rate * > > > bpp/lanes but the loop from sun4i_dclk_round_rate computed the divider > > > as 6 only, ie what I'm mentioned on the above mail. > > > > We've been over this a couple of times already. > > > > The clock is generated like this: > > > > PLL -> TCON Module Clock -> TCON DCLK > > > > You want the TCON DCLK to be at the pixel clock rate * bpp / > > lanes. Fine, that makes sense. > > > > Except that the patch you've sent, instead of changing the rate > > itself, changes the ratio between the module clock and DCLK. > > > > And this is where the issue lies. First, from a logical viewpoint, it > > doesn't make sense. If you want to change the clock rate, then just do > > it. Don't hack around the multipliers trying to fall back to something > > that works for you. > > > > Then, the ratio itself needs to be set to 4. This is the part that > > we've discussed way too many times already, but in the Allwinner BSP, > > that ratio is hardcoded to 4, and we've had panels that need it at > > that value. > > > > So, what you want to do is to have: > > > > TCON DCLK = pixel clock * bpp / lanes > > TCON Module Clock = DCLK * 4 > > PLL = Module Clock * Module Clock Divider (which I believe is 1 in most cases) > > pll-mipi 1 1 1 178200000 > 0 0 50000 > tcon0 2 2 1 178200000 > 0 0 50000 > tcon-pixel-clock 1 1 1 29700000 > 0 0 50000 > > This is an english problem from my side: > tcon-pixel-clock is DCLK > tcon0 must be tcon-pixel-clock * bpp / lanes because the logic need to > put a bit every cycle. > > One solution can be: > - set_rate_exclusive to tcon0 and calculate as display pixel clock * > bpp / lanes > - calculate the tcon-pixel-clock using all divider > > Problem is that the function that calculate tcon-pixel-clock does not > have any constrain on the ideal value. What you are > suggesting is not correct in my opinion or I'm not following your > suggesstion. What I know is that if we have a pixel-clock > of dvi display of 50Mhz and we have 4 lanes 32bit we need a clock in > the logic of 400Mhz (this is the ideal throughtput). > So tcon-pixel-clock is 50mhz and tcon0 is 400Mhz. > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c b/drivers/gpu/drm/sun4i/sun4i_tcon.c index 94f24c5e2dc5..ffb7906054e5 100644 --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c @@ -338,8 +338,9 @@ static void sun4i_tcon0_mode_set_cpu(struct sun4i_tcon *tcon, u32 block_space, start_delay; u32 tcon_div; - tcon->dclk_min_div = bpp/lanes; - tcon->dclk_max_div = bpp/lanes; + tcon->dclk_min_div = 4; + tcon->dclk_max_div = 127; + clk_set_rate_exclusive(tcon->sclk0, mode->crtc_clock * 1000 * bpp / lanes); sun4i_tcon0_mode_set_common(tcon, mode); Something like this on top of jagan proposal Michael > Michael > > > > > > So you want to increase the PLL. Fortunately for use, this is exactly > > what a call to clk_set_rate will end up doing. > > > > Maxime > > > > -- > > Maxime Ripard, Bootlin > > Embedded Linux and Kernel engineering > > https://bootlin.com > > > > -- > | Michael Nazzareno Trimarchi Amarula Solutions BV | > | COO - Founder Cruquiuskade 47 | > | +31(0)851119172 Amsterdam 1018 AM NL | > | [`as] http://www.amarulasolutions.com |
On Mon, Jul 29, 2019 at 08:59:04AM +0200, Michael Nazzareno Trimarchi wrote: > Hi > > On Wed, Jul 24, 2019 at 11:05 AM Maxime Ripard > <maxime.ripard@bootlin.com> wrote: > > > > On Mon, Jul 22, 2019 at 03:51:04PM +0530, Jagan Teki wrote: > > > Hi Maxime, > > > > > > On Sat, Jul 20, 2019 at 3:02 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > On Sat, Jul 20, 2019 at 12:46:27PM +0530, Jagan Teki wrote: > > > > > On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard > > > > > <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > > > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > > > > > > you need to have a clock that is able to put outside bits and speed > > > > > > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > > > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > > > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > > > > > > the display. > > > > > > > > > > > > > > > > So this is what the issue is then? > > > > > > > > > > > > > > > > This one does make sense, and you should just change the rate in the > > > > > > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > > > > > > > > > > > I'm still wondering why that hasn't been brought up in either the > > > > > > > > discussion or the commit log before though. > > > > > > > > > > > > > > > Something like this? > > > > > > > > > > > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > > > > > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > > > > > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > > > > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > index 64c43ee6bd92..42560d5c327c 100644 > > > > > > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > > > > > > drm_display_mode *mode, > > > > > > > } > > > > > > > > > > > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > > > > > > - const struct drm_display_mode *mode) > > > > > > > + const struct drm_display_mode *mode, > > > > > > > + u32 tcon_mul) > > > > > > > { > > > > > > > /* Configure the dot clock */ > > > > > > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > > > > > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > > > > > > > > > > > /* Set the resolution */ > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > > > > > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > > sun4i_tcon *tcon, > > > > > > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > > > > > > u8 lanes = device->lanes; > > > > > > > u32 block_space, start_delay; > > > > > > > - u32 tcon_div; > > > > > > > + u32 tcon_div, tcon_mul; > > > > > > > > > > > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > > > > > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > > > > > > + tcon->dclk_min_div = 4; > > > > > > > + tcon->dclk_max_div = 127; > > > > > > > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > + tcon_mul = bpp / lanes; > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > > sun4i_tcon *tcon, > > > > > > > */ > > > > > > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > > > > > > tcon_div &= GENMASK(6, 0); > > > > > > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > > > > > > + block_space = mode->htotal * tcon_div * tcon_mul; > > > > > > > block_space -= mode->hdisplay + 40; > > > > > > > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > > > > > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > > > tcon->dclk_min_div = 7; > > > > > > > tcon->dclk_max_div = 7; > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > > > tcon->dclk_min_div = 6; > > > > > > > tcon->dclk_max_div = 127; > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > index 5c3ad5be0690..a07090579f84 100644 > > > > > > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > @@ -13,8 +13,6 @@ > > > > > > > #include <drm/drm_encoder.h> > > > > > > > #include <drm/drm_mipi_dsi.h> > > > > > > > > > > > > > > -#define SUN6I_DSI_TCON_DIV 4 > > > > > > > - > > > > > > > struct sun6i_dsi { > > > > > > > struct drm_connector connector; > > > > > > > struct drm_encoder encoder; > > > > > > > > > > > > I had more something like this in mind: > > > > > > http://code.bulix.org/nlp5a4-803511 > > > > > > > > > > Worth to look at it. was it working on your panel? meanwhile I will check it. > > > > > > > > I haven't tested it. > > > > > > > > > We have updated with below change [1], seems working on but is > > > > > actually checking the each divider as before start with 4... till 127. > > > > > > > > > > This new approach, is start looking the best divider from 4.. based on > > > > > the idea vs rounded it will ended up best divider like [2] > > > > > > > > But why? > > > > > > > > I mean, it's not like it's the first time I'm asking this... > > > > > > > > If the issue is what Micheal described, then the divider has nothing > > > > to do with it. We've had that discussion over and over again. > > > > > > This is what Michael is mentioned in above mail "tcon-pixel clock is > > > the rate that you want to achive on display side and if you have 4 > > > lanes 32bit or lanes and different bit number that you need to have > > > a clock that is able to put outside bits and speed equal to > > > pixel-clock * bits / lanes. so If you want a pixel-clock of 40 mhz > > > and you have 32bits and 4 lanes you need to have a clock of 40 * 32 > > > / 4 in no-burst mode. " > > > > Yeah, so we need to change the clock rate. > > > > > He is trying to manage the bpp/lanes into dclk_mul (in last mail) > > > and it can multiply with pixel clock which is rate argument in > > > sun4i_dclk_round_rate. > > > > > > The solution I have mentioned in dclk_min, max is bpp/lanes also > > > multiple rate in dotclock sun4i_dclk_round_rate. > > > > > > In both cases the overall pll_rate depends on dividers, the one that I > > > have on this patch is based on BSP and the Michael one is more generic > > > way so-that it can not to touch other functionalities and looping > > > dividers to find the best one. > > > > > > If dclk_min/max is bpp/lanes then dotclock directly using divider 6 > > > (assuming 24-bit and 4 lanes) and return the pll_rate and divider 6 > > > associated. > > > > > > if dclk_mul is bpp/lanes, on Michael new change, the dividers start > > > with 4 and end with 127 but the constant ideal rate which rate * > > > bpp/lanes but the loop from sun4i_dclk_round_rate computed the divider > > > as 6 only, ie what I'm mentioned on the above mail. > > > > We've been over this a couple of times already. > > > > The clock is generated like this: > > > > PLL -> TCON Module Clock -> TCON DCLK > > > > You want the TCON DCLK to be at the pixel clock rate * bpp / > > lanes. Fine, that makes sense. > > > > Except that the patch you've sent, instead of changing the rate > > itself, changes the ratio between the module clock and DCLK. > > > > And this is where the issue lies. First, from a logical viewpoint, it > > doesn't make sense. If you want to change the clock rate, then just do > > it. Don't hack around the multipliers trying to fall back to something > > that works for you. > > > > Then, the ratio itself needs to be set to 4. This is the part that > > we've discussed way too many times already, but in the Allwinner BSP, > > that ratio is hardcoded to 4, and we've had panels that need it at > > that value. > > > > So, what you want to do is to have: > > > > TCON DCLK = pixel clock * bpp / lanes > > TCON Module Clock = DCLK * 4 > > PLL = Module Clock * Module Clock Divider (which I believe is 1 in most cases) > > pll-mipi 1 1 1 178200000 > 0 0 50000 > tcon0 2 2 1 178200000 > 0 0 50000 > tcon-pixel-clock 1 1 1 29700000 > 0 0 50000 Is this before or after your patches? > This is an english problem from my side: > tcon-pixel-clock is DCLK > tcon0 must be tcon-pixel-clock * bpp / lanes, because the logic need to > put a bit every cycle. Again, I'm not saying this is wrong, but each time I've looked at it the BSP was using a 4 divider between the tcon module clock and the dotclock. So, please prove me wrong here. > One solution can be: > - set_rate_exclusive to tcon0 and calculate as display pixel clock * > bpp / lanes I'm not sure what set_rate_exclusive has to do with it. I mean, it's a good idea to use it, but it shouldn't really change anything to the discussion. > - calculate the tcon-pixel-clock using all divider I'm not sure what you mean by that. > Problem is that the function that calculate tcon-pixel-clock does not > have any constrain on the ideal value. It does have constraints, but you're right that it will not try to find an exact match and bail out if it can't do it, but will find the closest match. > What you are suggesting is not correct in my opinion or I'm not > following your suggesstion. Then prove me wrong. > What I know is that if we have a pixel-clock of dvi display of 50Mhz > and we have 4 lanes 32bit we need a clock in the logic of 400Mhz > (this is the ideal throughtput). > So tcon-pixel-clock is 50mhz and tcon0 is 400Mhz. There's one thing to keep in mind though. The TCON dotclock in the MIPI-DSI case isn't directly tied to the Bit Clock, it's simply an internal clock in the pipeline to feed the FIFO of the MIPI-DSI controller. The MIPI-DSI controller itself will generate that clock, and only that one will have those constraints. Maxime -- Maxime Ripard, Bootlin Embedded Linux and Kernel engineering https://bootlin.com
Hi Maxime On Tue, Aug 13, 2019 at 8:05 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Mon, Jul 29, 2019 at 08:59:04AM +0200, Michael Nazzareno Trimarchi wrote: > > Hi > > > > On Wed, Jul 24, 2019 at 11:05 AM Maxime Ripard > > <maxime.ripard@bootlin.com> wrote: > > > > > > On Mon, Jul 22, 2019 at 03:51:04PM +0530, Jagan Teki wrote: > > > > Hi Maxime, > > > > > > > > On Sat, Jul 20, 2019 at 3:02 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > On Sat, Jul 20, 2019 at 12:46:27PM +0530, Jagan Teki wrote: > > > > > > On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard > > > > > > <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > > > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > > > > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > > > > > > > you need to have a clock that is able to put outside bits and speed > > > > > > > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > > > > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > > > > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > > > > > > > the display. > > > > > > > > > > > > > > > > > > So this is what the issue is then? > > > > > > > > > > > > > > > > > > This one does make sense, and you should just change the rate in the > > > > > > > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > > > > > > > > > > > > > I'm still wondering why that hasn't been brought up in either the > > > > > > > > > discussion or the commit log before though. > > > > > > > > > > > > > > > > > Something like this? > > > > > > > > > > > > > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > > > > > > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > > > > > > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > > > > > > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > > index 64c43ee6bd92..42560d5c327c 100644 > > > > > > > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > > > > > > > drm_display_mode *mode, > > > > > > > > } > > > > > > > > > > > > > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > > > > > > > - const struct drm_display_mode *mode) > > > > > > > > + const struct drm_display_mode *mode, > > > > > > > > + u32 tcon_mul) > > > > > > > > { > > > > > > > > /* Configure the dot clock */ > > > > > > > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > > > > > > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > > > > > > > > > > > > > /* Set the resolution */ > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > > > > > > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > > > sun4i_tcon *tcon, > > > > > > > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > > > > > > > u8 lanes = device->lanes; > > > > > > > > u32 block_space, start_delay; > > > > > > > > - u32 tcon_div; > > > > > > > > + u32 tcon_div, tcon_mul; > > > > > > > > > > > > > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > > > > > > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > > > > > > > + tcon->dclk_min_div = 4; > > > > > > > > + tcon->dclk_max_div = 127; > > > > > > > > > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > > + tcon_mul = bpp / lanes; > > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > > > sun4i_tcon *tcon, > > > > > > > > */ > > > > > > > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > > > > > > > tcon_div &= GENMASK(6, 0); > > > > > > > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > > > > > > > + block_space = mode->htotal * tcon_div * tcon_mul; > > > > > > > > block_space -= mode->hdisplay + 40; > > > > > > > > > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > > > > > > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > > > > > tcon->dclk_min_div = 7; > > > > > > > > tcon->dclk_max_div = 7; > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > > > > > tcon->dclk_min_div = 6; > > > > > > > > tcon->dclk_max_div = 127; > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > > index 5c3ad5be0690..a07090579f84 100644 > > > > > > > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > > @@ -13,8 +13,6 @@ > > > > > > > > #include <drm/drm_encoder.h> > > > > > > > > #include <drm/drm_mipi_dsi.h> > > > > > > > > > > > > > > > > -#define SUN6I_DSI_TCON_DIV 4 > > > > > > > > - > > > > > > > > struct sun6i_dsi { > > > > > > > > struct drm_connector connector; > > > > > > > > struct drm_encoder encoder; > > > > > > > > > > > > > > I had more something like this in mind: > > > > > > > http://code.bulix.org/nlp5a4-803511 > > > > > > > > > > > > Worth to look at it. was it working on your panel? meanwhile I will check it. > > > > > > > > > > I haven't tested it. > > > > > > > > > > > We have updated with below change [1], seems working on but is > > > > > > actually checking the each divider as before start with 4... till 127. > > > > > > > > > > > > This new approach, is start looking the best divider from 4.. based on > > > > > > the idea vs rounded it will ended up best divider like [2] > > > > > > > > > > But why? > > > > > > > > > > I mean, it's not like it's the first time I'm asking this... > > > > > > > > > > If the issue is what Micheal described, then the divider has nothing > > > > > to do with it. We've had that discussion over and over again. > > > > > > > > This is what Michael is mentioned in above mail "tcon-pixel clock is > > > > the rate that you want to achive on display side and if you have 4 > > > > lanes 32bit or lanes and different bit number that you need to have > > > > a clock that is able to put outside bits and speed equal to > > > > pixel-clock * bits / lanes. so If you want a pixel-clock of 40 mhz > > > > and you have 32bits and 4 lanes you need to have a clock of 40 * 32 > > > > / 4 in no-burst mode. " > > > > > > Yeah, so we need to change the clock rate. > > > > > > > He is trying to manage the bpp/lanes into dclk_mul (in last mail) > > > > and it can multiply with pixel clock which is rate argument in > > > > sun4i_dclk_round_rate. > > > > > > > > The solution I have mentioned in dclk_min, max is bpp/lanes also > > > > multiple rate in dotclock sun4i_dclk_round_rate. > > > > > > > > In both cases the overall pll_rate depends on dividers, the one that I > > > > have on this patch is based on BSP and the Michael one is more generic > > > > way so-that it can not to touch other functionalities and looping > > > > dividers to find the best one. > > > > > > > > If dclk_min/max is bpp/lanes then dotclock directly using divider 6 > > > > (assuming 24-bit and 4 lanes) and return the pll_rate and divider 6 > > > > associated. > > > > > > > > if dclk_mul is bpp/lanes, on Michael new change, the dividers start > > > > with 4 and end with 127 but the constant ideal rate which rate * > > > > bpp/lanes but the loop from sun4i_dclk_round_rate computed the divider > > > > as 6 only, ie what I'm mentioned on the above mail. > > > > > > We've been over this a couple of times already. > > > > > > The clock is generated like this: > > > > > > PLL -> TCON Module Clock -> TCON DCLK > > > > > > You want the TCON DCLK to be at the pixel clock rate * bpp / > > > lanes. Fine, that makes sense. > > > > > > Except that the patch you've sent, instead of changing the rate > > > itself, changes the ratio between the module clock and DCLK. > > > > > > And this is where the issue lies. First, from a logical viewpoint, it > > > doesn't make sense. If you want to change the clock rate, then just do > > > it. Don't hack around the multipliers trying to fall back to something > > > that works for you. > > > > > > Then, the ratio itself needs to be set to 4. This is the part that > > > we've discussed way too many times already, but in the Allwinner BSP, > > > that ratio is hardcoded to 4, and we've had panels that need it at > > > that value. > > > > > > So, what you want to do is to have: > > > > > > TCON DCLK = pixel clock * bpp / lanes > > > TCON Module Clock = DCLK * 4 > > > PLL = Module Clock * Module Clock Divider (which I believe is 1 in most cases) > > > > pll-mipi 1 1 1 178200000 > > 0 0 50000 > > tcon0 2 2 1 178200000 > > 0 0 50000 > > tcon-pixel-clock 1 1 1 29700000 > > 0 0 50000 > > Is this before or after your patches? > This is just an example of clock tree to be clear to everyone how they are connected > > This is an english problem from my side: > > tcon-pixel-clock is DCLK > > tcon0 must be tcon-pixel-clock * bpp / lanes, because the logic need to > > put a bit every cycle. > > Again, I'm not saying this is wrong, but each time I've looked at it > the BSP was using a 4 divider between the tcon module clock and the > dotclock. > We have tested on 4-5 displays. Well I don't care on bsp but I care about if it works and if other SoC has similar approach on clock calculation. > So, please prove me wrong here. > Having only 10 pages of documentation is a bit difficult. > > One solution can be: > > - set_rate_exclusive to tcon0 and calculate as display pixel clock * > > bpp / lanes > > I'm not sure what set_rate_exclusive has to do with it. I mean, it's a > good idea to use it, but it shouldn't really change anything to the > discussion. Well, this will just do a minimal change on source code and put the constrains to the tcon0 > > > - calculate the tcon-pixel-clock using all divider > > I'm not sure what you mean by that. > > > Problem is that the function that calculate tcon-pixel-clock does not > > have any constrain on the ideal value. > > It does have constraints, but you're right that it will not try to > find an exact match and bail out if it can't do it, but will find the > closest match. > We need to find the closest divider that match the pixel clock and be close to the ideal tcon0 rate. > > What you are suggesting is not correct in my opinion or I'm not > > following your suggesstion. > > Then prove me wrong. > > > What I know is that if we have a pixel-clock of dvi display of 50Mhz > > and we have 4 lanes 32bit we need a clock in the logic of 400Mhz > > (this is the ideal throughtput). > > So tcon-pixel-clock is 50mhz and tcon0 is 400Mhz. > > There's one thing to keep in mind though. The TCON dotclock in the > MIPI-DSI case isn't directly tied to the Bit Clock, it's simply an > internal clock in the pipeline to feed the FIFO of the MIPI-DSI > controller. The MIPI-DSI controller itself will generate that clock, > and only that one will have those constraints. > I have done the same thinking but because it works for us seems that somehow is used to internal logic too Michael > Maxime > > -- > Maxime Ripard, Bootlin > Embedded Linux and Kernel engineering > https://bootlin.com
Hi, On Thu, Aug 15, 2019 at 02:25:57PM +0200, Michael Nazzareno Trimarchi wrote: > On Tue, Aug 13, 2019 at 8:05 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > On Mon, Jul 29, 2019 at 08:59:04AM +0200, Michael Nazzareno Trimarchi wrote: > > > Hi > > > > > > On Wed, Jul 24, 2019 at 11:05 AM Maxime Ripard > > > <maxime.ripard@bootlin.com> wrote: > > > > > > > > On Mon, Jul 22, 2019 at 03:51:04PM +0530, Jagan Teki wrote: > > > > > Hi Maxime, > > > > > > > > > > On Sat, Jul 20, 2019 at 3:02 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > On Sat, Jul 20, 2019 at 12:46:27PM +0530, Jagan Teki wrote: > > > > > > > On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard > > > > > > > <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > > > > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > > > > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > > > > > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > > > > > > > > you need to have a clock that is able to put outside bits and speed > > > > > > > > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > > > > > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > > > > > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > > > > > > > > the display. > > > > > > > > > > > > > > > > > > > > So this is what the issue is then? > > > > > > > > > > > > > > > > > > > > This one does make sense, and you should just change the rate in the > > > > > > > > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > > > > > > > > > > > > > > > I'm still wondering why that hasn't been brought up in either the > > > > > > > > > > discussion or the commit log before though. > > > > > > > > > > > > > > > > > > > Something like this? > > > > > > > > > > > > > > > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > > > > > > > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > > > > > > > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > > > > > > > > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > > > index 64c43ee6bd92..42560d5c327c 100644 > > > > > > > > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > > > > > > > > drm_display_mode *mode, > > > > > > > > > } > > > > > > > > > > > > > > > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > > > > > > > > - const struct drm_display_mode *mode) > > > > > > > > > + const struct drm_display_mode *mode, > > > > > > > > > + u32 tcon_mul) > > > > > > > > > { > > > > > > > > > /* Configure the dot clock */ > > > > > > > > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > > > > > > > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > > > > > > > > > > > > > > > /* Set the resolution */ > > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > > > > > > > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > > > > sun4i_tcon *tcon, > > > > > > > > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > > > > > > > > u8 lanes = device->lanes; > > > > > > > > > u32 block_space, start_delay; > > > > > > > > > - u32 tcon_div; > > > > > > > > > + u32 tcon_div, tcon_mul; > > > > > > > > > > > > > > > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > > > > > > > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > > > > > > > > + tcon->dclk_min_div = 4; > > > > > > > > > + tcon->dclk_max_div = 127; > > > > > > > > > > > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > > > + tcon_mul = bpp / lanes; > > > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > > > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > > > > sun4i_tcon *tcon, > > > > > > > > > */ > > > > > > > > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > > > > > > > > tcon_div &= GENMASK(6, 0); > > > > > > > > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > > > > > > > > + block_space = mode->htotal * tcon_div * tcon_mul; > > > > > > > > > block_space -= mode->hdisplay + 40; > > > > > > > > > > > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > > > > > > > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > > > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > > > > > > > tcon->dclk_min_div = 7; > > > > > > > > > tcon->dclk_max_div = 7; > > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > > > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > > > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > > > > > > > tcon->dclk_min_div = 6; > > > > > > > > > tcon->dclk_max_div = 127; > > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > > > index 5c3ad5be0690..a07090579f84 100644 > > > > > > > > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > > > @@ -13,8 +13,6 @@ > > > > > > > > > #include <drm/drm_encoder.h> > > > > > > > > > #include <drm/drm_mipi_dsi.h> > > > > > > > > > > > > > > > > > > -#define SUN6I_DSI_TCON_DIV 4 > > > > > > > > > - > > > > > > > > > struct sun6i_dsi { > > > > > > > > > struct drm_connector connector; > > > > > > > > > struct drm_encoder encoder; > > > > > > > > > > > > > > > > I had more something like this in mind: > > > > > > > > http://code.bulix.org/nlp5a4-803511 > > > > > > > > > > > > > > Worth to look at it. was it working on your panel? meanwhile I will check it. > > > > > > > > > > > > I haven't tested it. > > > > > > > > > > > > > We have updated with below change [1], seems working on but is > > > > > > > actually checking the each divider as before start with 4... till 127. > > > > > > > > > > > > > > This new approach, is start looking the best divider from 4.. based on > > > > > > > the idea vs rounded it will ended up best divider like [2] > > > > > > > > > > > > But why? > > > > > > > > > > > > I mean, it's not like it's the first time I'm asking this... > > > > > > > > > > > > If the issue is what Micheal described, then the divider has nothing > > > > > > to do with it. We've had that discussion over and over again. > > > > > > > > > > This is what Michael is mentioned in above mail "tcon-pixel clock is > > > > > the rate that you want to achive on display side and if you have 4 > > > > > lanes 32bit or lanes and different bit number that you need to have > > > > > a clock that is able to put outside bits and speed equal to > > > > > pixel-clock * bits / lanes. so If you want a pixel-clock of 40 mhz > > > > > and you have 32bits and 4 lanes you need to have a clock of 40 * 32 > > > > > / 4 in no-burst mode. " > > > > > > > > Yeah, so we need to change the clock rate. > > > > > > > > > He is trying to manage the bpp/lanes into dclk_mul (in last mail) > > > > > and it can multiply with pixel clock which is rate argument in > > > > > sun4i_dclk_round_rate. > > > > > > > > > > The solution I have mentioned in dclk_min, max is bpp/lanes also > > > > > multiple rate in dotclock sun4i_dclk_round_rate. > > > > > > > > > > In both cases the overall pll_rate depends on dividers, the one that I > > > > > have on this patch is based on BSP and the Michael one is more generic > > > > > way so-that it can not to touch other functionalities and looping > > > > > dividers to find the best one. > > > > > > > > > > If dclk_min/max is bpp/lanes then dotclock directly using divider 6 > > > > > (assuming 24-bit and 4 lanes) and return the pll_rate and divider 6 > > > > > associated. > > > > > > > > > > if dclk_mul is bpp/lanes, on Michael new change, the dividers start > > > > > with 4 and end with 127 but the constant ideal rate which rate * > > > > > bpp/lanes but the loop from sun4i_dclk_round_rate computed the divider > > > > > as 6 only, ie what I'm mentioned on the above mail. > > > > > > > > We've been over this a couple of times already. > > > > > > > > The clock is generated like this: > > > > > > > > PLL -> TCON Module Clock -> TCON DCLK > > > > > > > > You want the TCON DCLK to be at the pixel clock rate * bpp / > > > > lanes. Fine, that makes sense. > > > > > > > > Except that the patch you've sent, instead of changing the rate > > > > itself, changes the ratio between the module clock and DCLK. > > > > > > > > And this is where the issue lies. First, from a logical viewpoint, it > > > > doesn't make sense. If you want to change the clock rate, then just do > > > > it. Don't hack around the multipliers trying to fall back to something > > > > that works for you. > > > > > > > > Then, the ratio itself needs to be set to 4. This is the part that > > > > we've discussed way too many times already, but in the Allwinner BSP, > > > > that ratio is hardcoded to 4, and we've had panels that need it at > > > > that value. > > > > > > > > So, what you want to do is to have: > > > > > > > > TCON DCLK = pixel clock * bpp / lanes > > > > TCON Module Clock = DCLK * 4 > > > > PLL = Module Clock * Module Clock Divider (which I believe is 1 in most cases) > > > > > > pll-mipi 1 1 1 178200000 > > > 0 0 50000 > > > tcon0 2 2 1 178200000 > > > 0 0 50000 > > > tcon-pixel-clock 1 1 1 29700000 > > > 0 0 50000 > > > > Is this before or after your patches? > > > > This is just an example of clock tree to be clear to everyone how they > are connected > > > > This is an english problem from my side: > > > tcon-pixel-clock is DCLK > > > tcon0 must be tcon-pixel-clock * bpp / lanes, because the logic need to > > > put a bit every cycle. > > > > Again, I'm not saying this is wrong, but each time I've looked at it > > the BSP was using a 4 divider between the tcon module clock and the > > dotclock. > > We have tested on 4-5 displays. Well I don't care on bsp but I care > about if it works and if other SoC has similar approach on clock > calculation. Well, it's also breaking another panel. > > So, please prove me wrong here. > > Having only 10 pages of documentation is a bit difficult. The BSP source code will be a fine example too. > > > One solution can be: > > > - set_rate_exclusive to tcon0 and calculate as display pixel clock * > > > bpp / lanes > > > > I'm not sure what set_rate_exclusive has to do with it. I mean, it's a > > good idea to use it, but it shouldn't really change anything to the > > discussion. > > Well, this will just do a minimal change on source code and put the constrains > to the tcon0 I agree, but again, this has nothing to do with the current discussion. Maxime -- Maxime Ripard, Bootlin Embedded Linux and Kernel engineering https://bootlin.com
Hi Maxime On Wed, Aug 28, 2019 at 3:03 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > Hi, > > On Thu, Aug 15, 2019 at 02:25:57PM +0200, Michael Nazzareno Trimarchi wrote: > > On Tue, Aug 13, 2019 at 8:05 AM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > On Mon, Jul 29, 2019 at 08:59:04AM +0200, Michael Nazzareno Trimarchi wrote: > > > > Hi > > > > > > > > On Wed, Jul 24, 2019 at 11:05 AM Maxime Ripard > > > > <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > On Mon, Jul 22, 2019 at 03:51:04PM +0530, Jagan Teki wrote: > > > > > > Hi Maxime, > > > > > > > > > > > > On Sat, Jul 20, 2019 at 3:02 PM Maxime Ripard <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > > > On Sat, Jul 20, 2019 at 12:46:27PM +0530, Jagan Teki wrote: > > > > > > > > On Sat, Jul 20, 2019 at 12:28 PM Maxime Ripard > > > > > > > > <maxime.ripard@bootlin.com> wrote: > > > > > > > > > > > > > > > > > > On Thu, Jul 11, 2019 at 07:43:16PM +0200, Michael Nazzareno Trimarchi wrote: > > > > > > > > > > > > tcon-pixel clock is the rate that you want to achive on display side > > > > > > > > > > > > and if you have 4 lanes 32bit or lanes and different bit number that > > > > > > > > > > > > you need to have a clock that is able to put outside bits and speed > > > > > > > > > > > > equal to pixel-clock * bits / lanes. so If you want a pixel-clock of > > > > > > > > > > > > 40 mhz and you have 32bits and 4 lanes you need to have a clock of > > > > > > > > > > > > 40 * 32 / 4 in no-burst mode. I think that this is done but most of > > > > > > > > > > > > the display. > > > > > > > > > > > > > > > > > > > > > > So this is what the issue is then? > > > > > > > > > > > > > > > > > > > > > > This one does make sense, and you should just change the rate in the > > > > > > > > > > > call to clk_set_rate in sun4i_tcon0_mode_set_cpu. > > > > > > > > > > > > > > > > > > > > > > I'm still wondering why that hasn't been brought up in either the > > > > > > > > > > > discussion or the commit log before though. > > > > > > > > > > > > > > > > > > > > > Something like this? > > > > > > > > > > > > > > > > > > > > drivers/gpu/drm/sun4i/sun4i_tcon.c | 20 +++++++++++--------- > > > > > > > > > > drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h | 2 -- > > > > > > > > > > 2 files changed, 11 insertions(+), 11 deletions(-) > > > > > > > > > > > > > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > > > > b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > > > > index 64c43ee6bd92..42560d5c327c 100644 > > > > > > > > > > --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > > > > +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c > > > > > > > > > > @@ -263,10 +263,11 @@ static int sun4i_tcon_get_clk_delay(const struct > > > > > > > > > > drm_display_mode *mode, > > > > > > > > > > } > > > > > > > > > > > > > > > > > > > > static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, > > > > > > > > > > - const struct drm_display_mode *mode) > > > > > > > > > > + const struct drm_display_mode *mode, > > > > > > > > > > + u32 tcon_mul) > > > > > > > > > > { > > > > > > > > > > /* Configure the dot clock */ > > > > > > > > > > - clk_set_rate(tcon->dclk, mode->crtc_clock * 1000); > > > > > > > > > > + clk_set_rate(tcon->dclk, mode->crtc_clock * tcon_mul * 1000); > > > > > > > > > > > > > > > > > > > > /* Set the resolution */ > > > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_BASIC0_REG, > > > > > > > > > > @@ -335,12 +336,13 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > > > > > sun4i_tcon *tcon, > > > > > > > > > > u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); > > > > > > > > > > u8 lanes = device->lanes; > > > > > > > > > > u32 block_space, start_delay; > > > > > > > > > > - u32 tcon_div; > > > > > > > > > > + u32 tcon_div, tcon_mul; > > > > > > > > > > > > > > > > > > > > - tcon->dclk_min_div = SUN6I_DSI_TCON_DIV; > > > > > > > > > > - tcon->dclk_max_div = SUN6I_DSI_TCON_DIV; > > > > > > > > > > + tcon->dclk_min_div = 4; > > > > > > > > > > + tcon->dclk_max_div = 127; > > > > > > > > > > > > > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > > > > + tcon_mul = bpp / lanes; > > > > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, tcon_mul); > > > > > > > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > > > > > @@ -366,7 +368,7 @@ static void sun4i_tcon0_mode_set_cpu(struct > > > > > > > > > > sun4i_tcon *tcon, > > > > > > > > > > */ > > > > > > > > > > regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); > > > > > > > > > > tcon_div &= GENMASK(6, 0); > > > > > > > > > > - block_space = mode->htotal * bpp / (tcon_div * lanes); > > > > > > > > > > + block_space = mode->htotal * tcon_div * tcon_mul; > > > > > > > > > > block_space -= mode->hdisplay + 40; > > > > > > > > > > > > > > > > > > > > regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, > > > > > > > > > > @@ -408,7 +410,7 @@ static void sun4i_tcon0_mode_set_lvds(struct > > > > > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > > > > > > > > > tcon->dclk_min_div = 7; > > > > > > > > > > tcon->dclk_max_div = 7; > > > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, sun4i_tcon_get_connector(encoder)); > > > > > > > > > > @@ -487,7 +489,7 @@ static void sun4i_tcon0_mode_set_rgb(struct > > > > > > > > > > sun4i_tcon *tcon, > > > > > > > > > > > > > > > > > > > > tcon->dclk_min_div = 6; > > > > > > > > > > tcon->dclk_max_div = 127; > > > > > > > > > > - sun4i_tcon0_mode_set_common(tcon, mode); > > > > > > > > > > + sun4i_tcon0_mode_set_common(tcon, mode, 1); > > > > > > > > > > > > > > > > > > > > /* Set dithering if needed */ > > > > > > > > > > sun4i_tcon0_mode_set_dithering(tcon, connector); > > > > > > > > > > diff --git a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > > > > b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > > > > index 5c3ad5be0690..a07090579f84 100644 > > > > > > > > > > --- a/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > > > > +++ b/drivers/gpu/drm/sun4i/sun6i_mipi_dsi.h > > > > > > > > > > @@ -13,8 +13,6 @@ > > > > > > > > > > #include <drm/drm_encoder.h> > > > > > > > > > > #include <drm/drm_mipi_dsi.h> > > > > > > > > > > > > > > > > > > > > -#define SUN6I_DSI_TCON_DIV 4 > > > > > > > > > > - > > > > > > > > > > struct sun6i_dsi { > > > > > > > > > > struct drm_connector connector; > > > > > > > > > > struct drm_encoder encoder; > > > > > > > > > > > > > > > > > > I had more something like this in mind: > > > > > > > > > http://code.bulix.org/nlp5a4-803511 > > > > > > > > > > > > > > > > Worth to look at it. was it working on your panel? meanwhile I will check it. > > > > > > > > > > > > > > I haven't tested it. > > > > > > > > > > > > > > > We have updated with below change [1], seems working on but is > > > > > > > > actually checking the each divider as before start with 4... till 127. > > > > > > > > > > > > > > > > This new approach, is start looking the best divider from 4.. based on > > > > > > > > the idea vs rounded it will ended up best divider like [2] > > > > > > > > > > > > > > But why? > > > > > > > > > > > > > > I mean, it's not like it's the first time I'm asking this... > > > > > > > > > > > > > > If the issue is what Micheal described, then the divider has nothing > > > > > > > to do with it. We've had that discussion over and over again. > > > > > > > > > > > > This is what Michael is mentioned in above mail "tcon-pixel clock is > > > > > > the rate that you want to achive on display side and if you have 4 > > > > > > lanes 32bit or lanes and different bit number that you need to have > > > > > > a clock that is able to put outside bits and speed equal to > > > > > > pixel-clock * bits / lanes. so If you want a pixel-clock of 40 mhz > > > > > > and you have 32bits and 4 lanes you need to have a clock of 40 * 32 > > > > > > / 4 in no-burst mode. " > > > > > > > > > > Yeah, so we need to change the clock rate. > > > > > > > > > > > He is trying to manage the bpp/lanes into dclk_mul (in last mail) > > > > > > and it can multiply with pixel clock which is rate argument in > > > > > > sun4i_dclk_round_rate. > > > > > > > > > > > > The solution I have mentioned in dclk_min, max is bpp/lanes also > > > > > > multiple rate in dotclock sun4i_dclk_round_rate. > > > > > > > > > > > > In both cases the overall pll_rate depends on dividers, the one that I > > > > > > have on this patch is based on BSP and the Michael one is more generic > > > > > > way so-that it can not to touch other functionalities and looping > > > > > > dividers to find the best one. > > > > > > > > > > > > If dclk_min/max is bpp/lanes then dotclock directly using divider 6 > > > > > > (assuming 24-bit and 4 lanes) and return the pll_rate and divider 6 > > > > > > associated. > > > > > > > > > > > > if dclk_mul is bpp/lanes, on Michael new change, the dividers start > > > > > > with 4 and end with 127 but the constant ideal rate which rate * > > > > > > bpp/lanes but the loop from sun4i_dclk_round_rate computed the divider > > > > > > as 6 only, ie what I'm mentioned on the above mail. > > > > > > > > > > We've been over this a couple of times already. > > > > > > > > > > The clock is generated like this: > > > > > > > > > > PLL -> TCON Module Clock -> TCON DCLK > > > > > > > > > > You want the TCON DCLK to be at the pixel clock rate * bpp / > > > > > lanes. Fine, that makes sense. > > > > > > > > > > Except that the patch you've sent, instead of changing the rate > > > > > itself, changes the ratio between the module clock and DCLK. > > > > > > > > > > And this is where the issue lies. First, from a logical viewpoint, it > > > > > doesn't make sense. If you want to change the clock rate, then just do > > > > > it. Don't hack around the multipliers trying to fall back to something > > > > > that works for you. > > > > > > > > > > Then, the ratio itself needs to be set to 4. This is the part that > > > > > we've discussed way too many times already, but in the Allwinner BSP, > > > > > that ratio is hardcoded to 4, and we've had panels that need it at > > > > > that value. > > > > > > > > > > So, what you want to do is to have: > > > > > > > > > > TCON DCLK = pixel clock * bpp / lanes > > > > > TCON Module Clock = DCLK * 4 > > > > > PLL = Module Clock * Module Clock Divider (which I believe is 1 in most cases) > > > > > > > > pll-mipi 1 1 1 178200000 > > > > 0 0 50000 > > > > tcon0 2 2 1 178200000 > > > > 0 0 50000 > > > > tcon-pixel-clock 1 1 1 29700000 > > > > 0 0 50000 > > > > > > Is this before or after your patches? > > > > > > > This is just an example of clock tree to be clear to everyone how they > > are connected > > > > > > This is an english problem from my side: > > > > tcon-pixel-clock is DCLK > > > > tcon0 must be tcon-pixel-clock * bpp / lanes, because the logic need to > > > > put a bit every cycle. > > > > > > Again, I'm not saying this is wrong, but each time I've looked at it > > > the BSP was using a 4 divider between the tcon module clock and the > > > dotclock. > > > > We have tested on 4-5 displays. Well I don't care on bsp but I care > > about if it works and if other SoC has similar approach on clock > > calculation. > > Well, it's also breaking another panel. > Agree but I need to have the panel. Do you know if we have users of this panel? I don't want to break the users off course. Can I have your clk_tree dbg of your devices the panel datasheet? > > > So, please prove me wrong here. > > > > Having only 10 pages of documentation is a bit difficult. > > The BSP source code will be a fine example too. > Do you have any contact in allwinner? Let's be this last email, I don't want to bother the people more. After I get the panel info and datasheet I will come back if I found a solution that does not break it Michael > > > > One solution can be: > > > > - set_rate_exclusive to tcon0 and calculate as display pixel clock * > > > > bpp / lanes > > > > > > I'm not sure what set_rate_exclusive has to do with it. I mean, it's a > > > good idea to use it, but it shouldn't really change anything to the > > > discussion. > > > > Well, this will just do a minimal change on source code and put the constrains > > to the tcon0 > > I agree, but again, this has nothing to do with the current discussion. > > Maxime > > -- > Maxime Ripard, Bootlin > Embedded Linux and Kernel engineering > https://bootlin.com
diff --git a/drivers/clk/sunxi-ng/ccu-sun50i-a64.c b/drivers/clk/sunxi-ng/ccu-sun50i-a64.c index 932836d26e2b..296d489aad6e 100644 --- a/drivers/clk/sunxi-ng/ccu-sun50i-a64.c +++ b/drivers/clk/sunxi-ng/ccu-sun50i-a64.c @@ -183,6 +183,7 @@ static struct ccu_nkm pll_mipi_clk = { .n = _SUNXI_CCU_MULT(8, 4), .k = _SUNXI_CCU_MULT_MIN(4, 2, 2), .m = _SUNXI_CCU_DIV(0, 4), + .min_rate = 300000000, .common = { .reg = 0x040, .hw.init = CLK_HW_INIT("pll-mipi", "pll-video0",