CI20 HDMI and LCD controller pixel clock calculations

12 views
Skip to first unread message

Paul Boddie

unread,
Oct 6, 2022, 3:53:30 PM10/6/22
to MIPS Creator CI20 Development, Ezequiel Garcia, H. Nikolaus Schaller, Paul Cercueil, zhouy...@wanyeetech.com, Riccardo Mottola
Hello,

Having been a party to the prolonged process of getting the CI20's HDMI
support mainlined in the new 6.0.0 kernel, but unlike everybody else who
seemingly found this support to work for them, I was left with a CI20 that
wasn't able to produce a picture on my monitor, this being a DVI-capable
monitor that had been used successfully via a suitable HDMI adapter with the
legacy 3.18 kernel.

I have now managed to investigate the HDMI and LCD controller peripheral
configurations, concluding that they are largely correct. However, the
obstacle for my own configuration is actually a misconfigured pixel clock in
the LCD controller peripheral.

Consider a mode of 1280x1024 @ 60Hz, supported and reported by my monitor.
This should employ a pixel clock of around 108MHz, as indicated by the
modeline generated by the modetest utility:

1280x1024 60.02 1280 1328 1440 1688 1024 1025 1028 1066 108000

Upon trying to configure the pixel clock in the JZ4780, what appears to have
been happening is that the parent clock of 888MHz is divided by 108MHz, but
the result is rounded up. From ingenic_clk_calc_div (in drivers/clk/ingenic/
cgu.c):

div = DIV_ROUND_UP(parent_rate, req_rate);

Since 888MHz / 108MHz is around 8.2, the divisor becomes 9 in the above
calculation. The resulting frequency then becomes 888MHz / 9 or around
98.7MHz.

Now, I can imagine that there are situations where rounding up the divisor,
and thus rounding down any generated frequency is desirable. The required or
desired rate may be an upper bound dictated by the peripheral or its
activities.

In this case, however, if the pixel clock is not high enough, the HDMI
controller fails to provide the data to the monitor correctly, yielding the
unhelpful "Input Not Supported" message on my monitor.

So, for clocks where the indicated frequency is a lower bound on any generated
frequency, there needs to be an alternative to the above where the divisor is
rounded down, not up:

div = parent_rate / req_rate;

I have briefly tested two kinds of modifications to the behaviour of the code:
one where all dividers are effectively rounded down (by employing "floor" or
"integer" division semantics); one where only the LCD pixel clock dividers are
rounded down. In both cases, the CI20 does boot and produce a picture.

In the former case where the behaviour of all dividers have been changed, the
only apparently significant consequence appears to be with the HDMI peripheral
clock itself, this normally using a generated frequency of 26909090Hz but
being given a frequency of 27750000Hz instead. (The SSI peripheral clocks do
not seem to be set up, but these have reported frequencies equal to their
parent clock instead of dividing it by 23.)

Personally, I would imagine a less invasive change to be more desirable. The
more selective case in my testing just adds an extra member to the
ingenic_cgu_div_info structure, and where this member has a true value, the
conventional "floor" division operation is used instead of DIV_ROUND_UP.

To summarise, the clock frequency handling is apparently incorrect or
incomplete for the Ingenic SoCs and would benefit from some revision. I would
welcome sensible feedback on how this might be done and whether augmenting the
divider structure and calculating the divisor differently is the right
solution. A patch implementing the selective change to the LCD pixel clock
dividers is attached.

Thanks for any guidance that might be offered!

Paul
jz4780-cgu-divider-rounding.diff

Paul Cercueil

unread,
Oct 6, 2022, 4:20:51 PM10/6/22
to Paul Boddie, MIPS Creator CI20 Development, Ezequiel Garcia, H. Nikolaus Schaller, zhouy...@wanyeetech.com, Riccardo Mottola
Hi Paul,

You can parent the HDMI clock to the VPLL which is not used right now
(AFAIK).

You can set the VPLL to 108 MHz or any multiple. The best value might
be 1944 MHz (max. is 2 GHz) as a higher value means less difference
when using a higher-than-perfect divider. Probably sips more power
though.

If you know what frequencies your monitor asks for 720p and 1080p,
there's maybe a particular frequency that works fine for all of them.

Cheers,
-Paul


Le jeu., oct. 6 2022 at 21:53:23 +0200, Paul Boddie
<pa...@boddie.org.uk> a écrit :

Paul Boddie

unread,
Oct 6, 2022, 5:32:20 PM10/6/22
to Paul Cercueil, MIPS Creator CI20 Development, Ezequiel Garcia, H. Nikolaus Schaller, zhouy...@wanyeetech.com, Riccardo Mottola
On Thursday, 6 October 2022 22:20:39 CEST Paul Cercueil wrote:
> Hi Paul,
>
> You can parent the HDMI clock to the VPLL which is not used right now
> (AFAIK).

The VPLL currently is the parent clock. Here is an abridged and condensed
extract from clk_summary showing a working configuration:

vpll 2 2 0 888000000 0 0 50000 Y
hdmi 1 1 0 26909090 0 0 50000 Y
lcd1pixclk 0 0 0 888000000 0 0 50000 Y
lcd0pixclk 1 1 0 111000000 0 0 50000 Y

> You can set the VPLL to 108 MHz or any multiple. The best value might
> be 1944 MHz (max. is 2 GHz) as a higher value means less difference
> when using a higher-than-perfect divider. Probably sips more power
> though.

I think 888MHz divided by eight is just fine in this situation, and this is
precisely what the legacy 3.18 kernel did for the CI20. But I suppose that
since the VPLL is only used for the HDMI and LCD frequencies, we could try and
choose a better value.

The input to VPLL is the 12MHz oscillator and the HDMI frequency is supposed
to be between 18MHz and 27MHz, according to the manual, while the desired
pixel clock frequency is 108MHz in this case. So, taking the lowest common
multiple would actually be 108MHz.

However, I don't know what the mechanism is to set up VPLL, as in how any of
these things reach their eventual values. Clearly, something concludes that
888MHz is a good VPLL setting, and then the clocks are derived from that.

> If you know what frequencies your monitor asks for 720p and 1080p,
> there's maybe a particular frequency that works fine for all of them.

It can do up to 1280x1024 at 60Hz or 75Hz, 1024x768 at 60Hz, 70Hz or 75Hz, and
a bunch of other intermediate and lower resolutions. Since I bought it
seventeen years ago, it does more traditional resolutions rather than being
specified in terms of 720p and 1080p.

But as I noted, the problem isn't really about my configuration because the
3.18 kernel worked just fine. It is about selecting clock frequencies
appropriately, and since they aren't being selected appropriately in this
case, I start to wonder if there aren't other situations where
misconfigurations occur and prevent things from functioning as they should.

Paul


Paul Cercueil

unread,
Oct 6, 2022, 8:43:07 PM10/6/22
to Paul Boddie, MIPS Creator CI20 Development, Ezequiel Garcia, H. Nikolaus Schaller, zhouy...@wanyeetech.com, Riccardo Mottola


Le jeu., oct. 6 2022 at 23:32:14 +0200, Paul Boddie
<pa...@boddie.org.uk> a écrit :
Nice theory, but the oscillator is 48 MHz ;)

> However, I don't know what the mechanism is to set up VPLL, as in how
> any of
> these things reach their eventual values. Clearly, something
> concludes that
> 888MHz is a good VPLL setting, and then the clocks are derived from
> that.

The something in question is just u-boot. It doesn't mean it's the best
setting.

>> If you know what frequencies your monitor asks for 720p and 1080p,
>> there's maybe a particular frequency that works fine for all of
>> them.
>
> It can do up to 1280x1024 at 60Hz or 75Hz, 1024x768 at 60Hz, 70Hz or
> 75Hz, and
> a bunch of other intermediate and lower resolutions. Since I bought it
> seventeen years ago, it does more traditional resolutions rather than
> being
> specified in terms of 720p and 1080p.
>
> But as I noted, the problem isn't really about my configuration
> because the
> 3.18 kernel worked just fine. It is about selecting clock frequencies
> appropriately, and since they aren't being selected appropriately in
> this
> case, I start to wonder if there aren't other situations where
> misconfigurations occur and prevent things from functioning as they
> should.

Well, AFAIK the screen doesn't actually advertize the range of
acceptable frequencies. The driver will always give a frequency lower
or equal to the one requested, since giving a higher frequency might
mean overclocking.

If there is a mechanism in DRM which allows to get a range of
frequencies for a given screen resolution, I am not aware of it.

Cheers,
-Paul


Paul Boddie

unread,
Oct 7, 2022, 10:43:50 AM10/7/22
to mips-creat...@googlegroups.com, Paul Cercueil, Ezequiel Garcia, H. Nikolaus Schaller, zhouy...@wanyeetech.com, Riccardo Mottola
On Friday, 7 October 2022 02:42:54 CEST Paul Cercueil wrote:
> Le jeu., oct. 6 2022 at 23:32:14 +0200, Paul Boddie
> >
> > The input to VPLL is the 12MHz oscillator and the HDMI frequency is
> > supposed to be between 18MHz and 27MHz, according to the manual, while the
> > desired pixel clock frequency is 108MHz in this case. So, taking the
> > lowest common multiple would actually be 108MHz.
>
> Nice theory, but the oscillator is 48 MHz ;)

I was just going off what the manual says. But anyway, my point was that if
the framework is supposed to calculate a usable parent clock frequency to
divide for the HDMI and pixel clocks, then this is how it might do so.

> > However, I don't know what the mechanism is to set up VPLL, as in how
> > any of these things reach their eventual values. Clearly, something
> > concludes that 888MHz is a good VPLL setting, and then the clocks are
> > derived from that.
>
> The something in question is just u-boot. It doesn't mean it's the best
> setting.

It is probably just a reasonable guess. For a 48MHz input and the previously
mentioned frequencies, the lowest common multiple is 432MHz. Boosting it to
888MHz just provides a number that can be divided in different ways that aim
to be as close to the desired frequencies as possible.

> > But as I noted, the problem isn't really about my configuration
> > because the 3.18 kernel worked just fine. It is about selecting clock
> > frequencies appropriately, and since they aren't being selected
> > appropriately in this case, I start to wonder if there aren't other
> > situations where misconfigurations occur and prevent things from
> > functioning as they should.
>
> Well, AFAIK the screen doesn't actually advertize the range of
> acceptable frequencies. The driver will always give a frequency lower
> or equal to the one requested, since giving a higher frequency might
> mean overclocking.

The pixel clock frequency will follow from the supported frame rate and the
visible resolution, porch and sync properties, of course, but there is also
provision for the pixel clock to be explicitly indicated by the EDID payload.
I imagine that a modern screen would probably deal with any divergence above
the ideal frequency by buffering the signal, and various techniques are
probably used historically to moderate things like the line frequency.

> If there is a mechanism in DRM which allows to get a range of
> frequencies for a given screen resolution, I am not aware of it.

The DRM framework doesn't need to do anything more than indicate the desired
pixel clock frequency. The issue here appears to be that the LCD controller is
not driven fast enough to provide the data to the HDMI controller at an
acceptable rate. Given that, how would you ensure that frequency values are
reliably calculated for the LCD controller?

Paul


Reply all
Reply to author
Forward
0 new messages