diff mbox series

drm/mgag200: Fix PLL setup for G200_SE_A rev >=4

Message ID 20221013082901.471417-1-jfalempe@redhat.com (mailing list archive)
State New, archived
Headers show
Series drm/mgag200: Fix PLL setup for G200_SE_A rev >=4 | expand

Commit Message

Jocelyn Falempe Oct. 13, 2022, 8:29 a.m. UTC
For G200_SE_A, PLL M setting is wrong, which leads to blank screen,
or "signal out of range" on VGA display.
previous code had "m |= 0x80" which was changed to
m |= ((pixpllcn & BIT(8)) >> 1);

Tested on G200_SE_A rev 42

This line of code was moved to another file with
commit 85397f6bc4ff ("drm/mgag200: Initialize each model in separate
function") but can be easily backported before this commit.

Fixes: 2dd040946ecf ("drm/mgag200: Store values (not bits) in struct mgag200_pll_values")
Cc: stable@vger.kernel.org
Signed-off-by: Jocelyn Falempe <jfalempe@redhat.com>
---
 drivers/gpu/drm/mgag200/mgag200_g200se.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

Comments

Thomas Zimmermann Oct. 13, 2022, 9:05 a.m. UTC | #1
Hi

Am 13.10.22 um 10:29 schrieb Jocelyn Falempe:
> For G200_SE_A, PLL M setting is wrong, which leads to blank screen,
> or "signal out of range" on VGA display.
> previous code had "m |= 0x80" which was changed to
> m |= ((pixpllcn & BIT(8)) >> 1);
> 
> Tested on G200_SE_A rev 42
> 
> This line of code was moved to another file with
> commit 85397f6bc4ff ("drm/mgag200: Initialize each model in separate
> function") but can be easily backported before this commit.
> 
> Fixes: 2dd040946ecf ("drm/mgag200: Store values (not bits) in struct mgag200_pll_values")
> Cc: stable@vger.kernel.org
> Signed-off-by: Jocelyn Falempe <jfalempe@redhat.com>
> ---
>   drivers/gpu/drm/mgag200/mgag200_g200se.c | 2 +-
>   1 file changed, 1 insertion(+), 1 deletion(-)
> 
> diff --git a/drivers/gpu/drm/mgag200/mgag200_g200se.c b/drivers/gpu/drm/mgag200/mgag200_g200se.c
> index be389ed91cbd..4ec035029b8b 100644
> --- a/drivers/gpu/drm/mgag200/mgag200_g200se.c
> +++ b/drivers/gpu/drm/mgag200/mgag200_g200se.c
> @@ -284,7 +284,7 @@ static void mgag200_g200se_04_pixpllc_atomic_update(struct drm_crtc *crtc,
>   	pixpllcp = pixpllc->p - 1;
>   	pixpllcs = pixpllc->s;
>   
> -	xpixpllcm = pixpllcm | ((pixpllcn & BIT(8)) >> 1);
> +	xpixpllcm = pixpllcm | BIT(7);

Thanks for figuring this out. G200SE apparently is special compared to 
the other models. The old MGA docs only list this bit as <reserved>. 
Really makes me wonder why this is different.

Please write it as

   BIT(7) | pixpllcm

so that bit settings are ordered MSB-to-LSB and include a one-line 
comment that says that G200SE needs to set this bit unconditionally.

Best regards
Thomas



>   	xpixpllcn = pixpllcn;
>   	xpixpllcp = (pixpllcs << 3) | pixpllcp;
>
Jocelyn Falempe Oct. 13, 2022, 9:37 a.m. UTC | #2
On 13/10/2022 11:05, Thomas Zimmermann wrote:
> Hi
> 
> Am 13.10.22 um 10:29 schrieb Jocelyn Falempe:
>> For G200_SE_A, PLL M setting is wrong, which leads to blank screen,
>> or "signal out of range" on VGA display.
>> previous code had "m |= 0x80" which was changed to
>> m |= ((pixpllcn & BIT(8)) >> 1);
>>
>> Tested on G200_SE_A rev 42
>>
>> This line of code was moved to another file with
>> commit 85397f6bc4ff ("drm/mgag200: Initialize each model in separate
>> function") but can be easily backported before this commit.
>>
>> Fixes: 2dd040946ecf ("drm/mgag200: Store values (not bits) in struct 
>> mgag200_pll_values")
>> Cc: stable@vger.kernel.org
>> Signed-off-by: Jocelyn Falempe <jfalempe@redhat.com>
>> ---
>>   drivers/gpu/drm/mgag200/mgag200_g200se.c | 2 +-
>>   1 file changed, 1 insertion(+), 1 deletion(-)
>>
>> diff --git a/drivers/gpu/drm/mgag200/mgag200_g200se.c 
>> b/drivers/gpu/drm/mgag200/mgag200_g200se.c
>> index be389ed91cbd..4ec035029b8b 100644
>> --- a/drivers/gpu/drm/mgag200/mgag200_g200se.c
>> +++ b/drivers/gpu/drm/mgag200/mgag200_g200se.c
>> @@ -284,7 +284,7 @@ static void 
>> mgag200_g200se_04_pixpllc_atomic_update(struct drm_crtc *crtc,
>>       pixpllcp = pixpllc->p - 1;
>>       pixpllcs = pixpllc->s;
>> -    xpixpllcm = pixpllcm | ((pixpllcn & BIT(8)) >> 1);
>> +    xpixpllcm = pixpllcm | BIT(7);
> 
> Thanks for figuring this out. G200SE apparently is special compared to 
> the other models. The old MGA docs only list this bit as <reserved>. 
> Really makes me wonder why this is different.

I think it might be because of the "clock * 2" trick for this model.
(so N parameter is half of what it should be, and doesn't have BIT(8) 
set). But I don't have the G200SE A specific hardware spec either.


> 
> Please write it as
> 
>    BIT(7) | pixpllcm
> 
> so that bit settings are ordered MSB-to-LSB and include a one-line 
> comment that says that G200SE needs to set this bit unconditionally.

Thanks, I will send a v2 shortly.

> 
> Best regards
> Thomas
> 
> 
> 
>>       xpixpllcn = pixpllcn;
>>       xpixpllcp = (pixpllcs << 3) | pixpllcp;
>
Ville Syrjälä Oct. 13, 2022, 10:36 a.m. UTC | #3
On Thu, Oct 13, 2022 at 11:05:19AM +0200, Thomas Zimmermann wrote:
> Hi
> 
> Am 13.10.22 um 10:29 schrieb Jocelyn Falempe:
> > For G200_SE_A, PLL M setting is wrong, which leads to blank screen,
> > or "signal out of range" on VGA display.
> > previous code had "m |= 0x80" which was changed to
> > m |= ((pixpllcn & BIT(8)) >> 1);
> > 
> > Tested on G200_SE_A rev 42
> > 
> > This line of code was moved to another file with
> > commit 85397f6bc4ff ("drm/mgag200: Initialize each model in separate
> > function") but can be easily backported before this commit.
> > 
> > Fixes: 2dd040946ecf ("drm/mgag200: Store values (not bits) in struct mgag200_pll_values")
> > Cc: stable@vger.kernel.org
> > Signed-off-by: Jocelyn Falempe <jfalempe@redhat.com>
> > ---
> >   drivers/gpu/drm/mgag200/mgag200_g200se.c | 2 +-
> >   1 file changed, 1 insertion(+), 1 deletion(-)
> > 
> > diff --git a/drivers/gpu/drm/mgag200/mgag200_g200se.c b/drivers/gpu/drm/mgag200/mgag200_g200se.c
> > index be389ed91cbd..4ec035029b8b 100644
> > --- a/drivers/gpu/drm/mgag200/mgag200_g200se.c
> > +++ b/drivers/gpu/drm/mgag200/mgag200_g200se.c
> > @@ -284,7 +284,7 @@ static void mgag200_g200se_04_pixpllc_atomic_update(struct drm_crtc *crtc,
> >   	pixpllcp = pixpllc->p - 1;
> >   	pixpllcs = pixpllc->s;
> >   
> > -	xpixpllcm = pixpllcm | ((pixpllcn & BIT(8)) >> 1);
> > +	xpixpllcm = pixpllcm | BIT(7);
> 
> Thanks for figuring this out. G200SE apparently is special compared to 
> the other models. The old MGA docs only list this bit as <reserved>. 
> Really makes me wonder why this is different.

Could measure eg. the vblank interval with and without that bit set
and see what effect it has. Assuming the PLL locks without the bit
of course.
Jocelyn Falempe Oct. 13, 2022, 1:18 p.m. UTC | #4
On 13/10/2022 12:36, Ville Syrjälä wrote:
> On Thu, Oct 13, 2022 at 11:05:19AM +0200, Thomas Zimmermann wrote:
>> Hi
>>
>> Am 13.10.22 um 10:29 schrieb Jocelyn Falempe:
>>> For G200_SE_A, PLL M setting is wrong, which leads to blank screen,
>>> or "signal out of range" on VGA display.
>>> previous code had "m |= 0x80" which was changed to
>>> m |= ((pixpllcn & BIT(8)) >> 1);
>>>
>>> Tested on G200_SE_A rev 42
>>>
>>> This line of code was moved to another file with
>>> commit 85397f6bc4ff ("drm/mgag200: Initialize each model in separate
>>> function") but can be easily backported before this commit.
>>>
>>> Fixes: 2dd040946ecf ("drm/mgag200: Store values (not bits) in struct mgag200_pll_values")
>>> Cc: stable@vger.kernel.org
>>> Signed-off-by: Jocelyn Falempe <jfalempe@redhat.com>
>>> ---
>>>    drivers/gpu/drm/mgag200/mgag200_g200se.c | 2 +-
>>>    1 file changed, 1 insertion(+), 1 deletion(-)
>>>
>>> diff --git a/drivers/gpu/drm/mgag200/mgag200_g200se.c b/drivers/gpu/drm/mgag200/mgag200_g200se.c
>>> index be389ed91cbd..4ec035029b8b 100644
>>> --- a/drivers/gpu/drm/mgag200/mgag200_g200se.c
>>> +++ b/drivers/gpu/drm/mgag200/mgag200_g200se.c
>>> @@ -284,7 +284,7 @@ static void mgag200_g200se_04_pixpllc_atomic_update(struct drm_crtc *crtc,
>>>    	pixpllcp = pixpllc->p - 1;
>>>    	pixpllcs = pixpllc->s;
>>>    
>>> -	xpixpllcm = pixpllcm | ((pixpllcn & BIT(8)) >> 1);
>>> +	xpixpllcm = pixpllcm | BIT(7);
>>
>> Thanks for figuring this out. G200SE apparently is special compared to
>> the other models. The old MGA docs only list this bit as <reserved>.
>> Really makes me wonder why this is different.
> 
> Could measure eg. the vblank interval with and without that bit set
> and see what effect it has. Assuming the PLL locks without the bit
> of course.
> 

Thanks for the pointer, but I don't have physical access to the system, 
so I'm not able to check that.
I think reverting to the previous setting that used to work is the safer 
approach here.
diff mbox series

Patch

diff --git a/drivers/gpu/drm/mgag200/mgag200_g200se.c b/drivers/gpu/drm/mgag200/mgag200_g200se.c
index be389ed91cbd..4ec035029b8b 100644
--- a/drivers/gpu/drm/mgag200/mgag200_g200se.c
+++ b/drivers/gpu/drm/mgag200/mgag200_g200se.c
@@ -284,7 +284,7 @@  static void mgag200_g200se_04_pixpllc_atomic_update(struct drm_crtc *crtc,
 	pixpllcp = pixpllc->p - 1;
 	pixpllcs = pixpllc->s;
 
-	xpixpllcm = pixpllcm | ((pixpllcn & BIT(8)) >> 1);
+	xpixpllcm = pixpllcm | BIT(7);
 	xpixpllcn = pixpllcn;
 	xpixpllcp = (pixpllcs << 3) | pixpllcp;