Re: [PATCH 07/23] drm/vmwgfx: stop using dma_resv_excl_fence

2022-03-22 Thread Christian König

Am 21.03.22 um 16:11 schrieb Zack Rusin:

On Mon, 2022-03-21 at 15:12 +0100, Christian König wrote:

Am 21.03.22 um 15:02 schrieb Zack Rusin:

On Mon, 2022-03-21 at 14:58 +0100, Christian König wrote:

⚠ External Email: This email originated from outside of the
organization. Do not click links or open attachments unless you
recognize the sender.

Instead use the new dma_resv_get_singleton function.

Signed-off-by: Christian König 
Reviewed-by: Daniel Vetter 
Cc: VMware Graphics 
Cc: Zack Rusin 
---
   drivers/gpu/drm/vmwgfx/vmwgfx_resource.c | 6 --
   1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_resource.c
b/drivers/gpu/drm/vmwgfx/vmwgfx_resource.c
index 708899ba2102..36c3b5db7e69 100644
--- a/drivers/gpu/drm/vmwgfx/vmwgfx_resource.c
+++ b/drivers/gpu/drm/vmwgfx/vmwgfx_resource.c
@@ -1165,8 +1165,10 @@ int vmw_resources_clean(struct
vmw_buffer_object *vbo, pgoff_t start,
  vmw_bo_fence_single(bo, NULL);
  if (bo->moving)
  dma_fence_put(bo->moving);
-   bo->moving = dma_fence_get
-   (dma_resv_excl_fence(bo->base.resv));
+
+   /* TODO: This is actually a memory management
dependency */
+   return dma_resv_get_singleton(bo->base.resv,
false,
+ &bo->moving);
  }

  return 0;
--
2.25.1


Sorry, I haven't had the time to go over the entire series, the
patch
looks good, but what's the memory management dependency the todo
mentions?

Previously the function installed only the exclusive fence as moving
fence into the BO.
Now it grabs all fences and installs them as moving fence into the
BO.

But what we really need is tracking if a fence in the reservation
object
is a kernel memory management dependency or not.

Patch #19 adds that and patch #23 then finally gets rid of the whole
bo->moving handling here because it becomes completely unnecessary.

I can drop the comment if you want or just note that it is only
temporary until the follow up patches are merged.

Ah, yes, if you could remove it that'd be great. The patch will never
be backported anywhere without the rest of the series, so it shouldn't
be a problem.


Sure, can I then have your rb for this one?

Thanks,
Christian.



z




Re: [PATCH] drm/ttm: fix potential null ptr deref in when mem space alloc fails

2022-03-22 Thread Christian König

Am 21.03.22 um 16:44 schrieb Robert Beckett:



On 21/03/2022 09:51, Christian König wrote:

Am 18.03.22 um 20:50 schrieb Robert Beckett:

when allocating a resource in place it is common to free the buffer's
resource, then allocate a new resource in a different placement.

e.g. amdgpu_bo_create_kernel_at calls ttm_resource_free, then calls
ttm_bo_mem_space.


Well yes I'm working the drivers towards this, but NAK at the moment. 
Currently bo->resource is never expected to be NULL.


And yes I'm searching for this bug in amdgpu for quite a while. Where 
exactly does that happen?


in my case, I am writing new code for i915 that does this. I will 
switch it to allocate the new resource first, then free the old one if 
successful.


For the existing amd case, see 
https://nam11.safelinks.protection.outlook.com/?url=https%3A%2F%2Fgit.kernel.org%2Fpub%2Fscm%2Flinux%2Fkernel%2Fgit%2Ftorvalds%2Flinux.git%2Ftree%2Fdrivers%2Fgpu%2Fdrm%2Famd%2Famdgpu%2Famdgpu_object.c%3Fh%3Dv5.17%23n384&data=04%7C01%7Cchristian.koenig%40amd.com%7C81f91d39683e4991181008da0b51a8d0%7C3dd8961fe4884e608e11a82d994e183d%7C0%7C0%7C637834742606744919%7CUnknown%7CTWFpbGZsb3d8eyJWIjoiMC4wLjAwMDAiLCJQIjoiV2luMzIiLCJBTiI6Ik1haWwiLCJXVCI6Mn0%3D%7C3000&sdata=mjHPvBStFM7tsYf%2BL9fYCWqddZuIaeza6BsRF3fAmao%3D&reserved=0



amdgpu_bo_create_kernel_at calls ttm_resource_free, then calls 
ttm_bo_mem_space. If the ttm_bo_mem_space call fails (e.g. due to 
memory pressure), then the error path will try to deref bo->resource, 
which will be null at that point.


Yeah, but that's a special handling only used during driver startup. We 
somehow have this on systems with DMA-buf sharing as well.




to fix this, I honestly don't see a reason to not also have the safety 
check for null there. It could check early and return an error if it 
is null. I think that defensive programming here makes sense, better 
than a null deref if someone programs it wrong.


Having it here is fine, the problem is you need to have that at tons of 
other places as well.


Maybe I should send you my WIP patch set for this? If you handle all the 
other cases as well I'm perfectly fine with this.


Regards,
Christian.







Amdgpu is supposed to allocate a new resource first, then do a swap 
and the free the old one.


Thanks,
Christian.



In this situation, bo->resource will be null as it is cleared during
the initial freeing of the previous resource.
This leads to a null deref.

Fixes: d3116756a710 (drm/ttm: rename bo->mem and make it a pointer)

Signed-off-by: Robert Beckett 
---
  drivers/gpu/drm/ttm/ttm_bo.c | 2 +-
  1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/ttm/ttm_bo.c 
b/drivers/gpu/drm/ttm/ttm_bo.c

index db3dc7ef5382..62b29ee7d040 100644
--- a/drivers/gpu/drm/ttm/ttm_bo.c
+++ b/drivers/gpu/drm/ttm/ttm_bo.c
@@ -875,7 +875,7 @@ int ttm_bo_mem_space(struct ttm_buffer_object *bo,
  }
  error:
-    if (bo->resource->mem_type == TTM_PL_SYSTEM && !bo->pin_count)
+    if (bo->resource && bo->resource->mem_type == TTM_PL_SYSTEM && 
!bo->pin_count)

  ttm_bo_move_to_lru_tail_unlocked(bo);
  return ret;






Re: drm/bridge: anx7625: Set downstream sink into normal status

2022-03-22 Thread Pin-yen Lin
Hi Xin,

Can we use dev_dbg instead of dev_info for the logging?

The log here is more like a debugging message, and using dev_dbg makes
it consistent with anx7625_dp_stop.

Sorry for not catching this earlier.

Best regards,
Pin-yen

On Thu, Mar 3, 2022 at 3:52 PM Pin-yen Lin  wrote:
>
> Reviewed-by: Pin-Yen Lin 
>
>
> On Wed, Mar 2, 2022 at 8:09 PM Xin Ji  wrote:
> >
> > As downstream sink was set into standby mode while bridge disabled,
> > this patch used for setting downstream sink into normal status
> > while enable bridge.
> >
> > Signed-off-by: Xin Ji 
> > ---
> >  drivers/gpu/drm/bridge/analogix/anx7625.c | 8 
> >  1 file changed, 8 insertions(+)
> >
> > diff --git a/drivers/gpu/drm/bridge/analogix/anx7625.c 
> > b/drivers/gpu/drm/bridge/analogix/anx7625.c
> > index 9aab879a8851..963eaf73ecab 100644
> > --- a/drivers/gpu/drm/bridge/analogix/anx7625.c
> > +++ b/drivers/gpu/drm/bridge/analogix/anx7625.c
> > @@ -919,12 +919,20 @@ static void anx7625_dp_start(struct anx7625_data *ctx)
> >  {
> > int ret;
> > struct device *dev = &ctx->client->dev;
> > +   u8 data;
> >
> > if (!ctx->display_timing_valid) {
> > DRM_DEV_ERROR(dev, "mipi not set display timing yet.\n");
> > return;
> > }
> >
> > +   dev_info(dev, "set downstream sink into normal\n");
> > +   /* Downstream sink enter into normal mode */
> > +   data = 1;
> > +   ret = anx7625_aux_trans(ctx, DP_AUX_NATIVE_WRITE, 0x000600, 1, 
> > &data);
> > +   if (ret < 0)
> > +   dev_err(dev, "IO error : set sink into normal mode fail\n");
> > +
> > /* Disable HDCP */
> > anx7625_write_and(ctx, ctx->i2c.rx_p1_client, 0xee, 0x9f);
> >


Re: drm/bridge: anx7625: Set downstream sink into normal status

2022-03-22 Thread Xin Ji
On Tue, Mar 22, 2022 at 03:33:17PM +0800, Pin-yen Lin wrote:
> Hi Xin,
> 
> Can we use dev_dbg instead of dev_info for the logging?
> 
> The log here is more like a debugging message, and using dev_dbg makes
> it consistent with anx7625_dp_stop.
> 
> Sorry for not catching this earlier.
> 
> Best regards,
> Pin-yen
Hi Pin-yen, OK, I'll change it in next version.
Thanks,
Xin
> 
> On Thu, Mar 3, 2022 at 3:52 PM Pin-yen Lin  wrote:
> >
> > Reviewed-by: Pin-Yen Lin 
> >
> >
> > On Wed, Mar 2, 2022 at 8:09 PM Xin Ji  wrote:
> > >
> > > As downstream sink was set into standby mode while bridge disabled,
> > > this patch used for setting downstream sink into normal status
> > > while enable bridge.
> > >
> > > Signed-off-by: Xin Ji 
> > > ---
> > >  drivers/gpu/drm/bridge/analogix/anx7625.c | 8 
> > >  1 file changed, 8 insertions(+)
> > >
> > > diff --git a/drivers/gpu/drm/bridge/analogix/anx7625.c 
> > > b/drivers/gpu/drm/bridge/analogix/anx7625.c
> > > index 9aab879a8851..963eaf73ecab 100644
> > > --- a/drivers/gpu/drm/bridge/analogix/anx7625.c
> > > +++ b/drivers/gpu/drm/bridge/analogix/anx7625.c
> > > @@ -919,12 +919,20 @@ static void anx7625_dp_start(struct anx7625_data 
> > > *ctx)
> > >  {
> > > int ret;
> > > struct device *dev = &ctx->client->dev;
> > > +   u8 data;
> > >
> > > if (!ctx->display_timing_valid) {
> > > DRM_DEV_ERROR(dev, "mipi not set display timing yet.\n");
> > > return;
> > > }
> > >
> > > +   dev_info(dev, "set downstream sink into normal\n");
> > > +   /* Downstream sink enter into normal mode */
> > > +   data = 1;
> > > +   ret = anx7625_aux_trans(ctx, DP_AUX_NATIVE_WRITE, 0x000600, 1, 
> > > &data);
> > > +   if (ret < 0)
> > > +   dev_err(dev, "IO error : set sink into normal mode 
> > > fail\n");
> > > +
> > > /* Disable HDCP */
> > > anx7625_write_and(ctx, ctx->i2c.rx_p1_client, 0xee, 0x9f);
> > >


[PATCH v2] drm/bridge: anx7625: Set downstream sink into normal status

2022-03-22 Thread Xin Ji
As downstream sink was set into standby mode while bridge disabled,
this patch used for setting downstream sink into normal status
while enable bridge.

Signed-off-by: Xin Ji 
Reviewed-by: Pin-Yen Lin 

---
V1 -> V2: use dev_dbg replace of dev_info
---
 drivers/gpu/drm/bridge/analogix/anx7625.c | 8 
 1 file changed, 8 insertions(+)

diff --git a/drivers/gpu/drm/bridge/analogix/anx7625.c 
b/drivers/gpu/drm/bridge/analogix/anx7625.c
index 9a2a19ad4202..dcf3275a00fe 100644
--- a/drivers/gpu/drm/bridge/analogix/anx7625.c
+++ b/drivers/gpu/drm/bridge/analogix/anx7625.c
@@ -924,12 +924,20 @@ static void anx7625_dp_start(struct anx7625_data *ctx)
 {
int ret;
struct device *dev = &ctx->client->dev;
+   u8 data;
 
if (!ctx->display_timing_valid) {
DRM_DEV_ERROR(dev, "mipi not set display timing yet.\n");
return;
}
 
+   dev_dbg(dev, "set downstream sink into normal\n");
+   /* Downstream sink enter into normal mode */
+   data = 1;
+   ret = anx7625_aux_trans(ctx, DP_AUX_NATIVE_WRITE, 0x000600, 1, &data);
+   if (ret < 0)
+   dev_err(dev, "IO error : set sink into normal mode fail\n");
+
/* Disable HDCP */
anx7625_write_and(ctx, ctx->i2c.rx_p1_client, 0xee, 0x9f);
 
-- 
2.25.1



Re: [PATCH v2] drm/bridge: anx7625: Set downstream sink into normal status

2022-03-22 Thread Hsin-Yi Wang
On Tue, Mar 22, 2022 at 4:02 PM Xin Ji  wrote:
>
> As downstream sink was set into standby mode while bridge disabled,
> this patch used for setting downstream sink into normal status
> while enable bridge.
>
> Signed-off-by: Xin Ji 
> Reviewed-by: Pin-Yen Lin 
>
> ---
> V1 -> V2: use dev_dbg replace of dev_info
> ---
>  drivers/gpu/drm/bridge/analogix/anx7625.c | 8 
>  1 file changed, 8 insertions(+)
>
> diff --git a/drivers/gpu/drm/bridge/analogix/anx7625.c 
> b/drivers/gpu/drm/bridge/analogix/anx7625.c
> index 9a2a19ad4202..dcf3275a00fe 100644
> --- a/drivers/gpu/drm/bridge/analogix/anx7625.c
> +++ b/drivers/gpu/drm/bridge/analogix/anx7625.c
> @@ -924,12 +924,20 @@ static void anx7625_dp_start(struct anx7625_data *ctx)
>  {
> int ret;
> struct device *dev = &ctx->client->dev;
> +   u8 data;
>
> if (!ctx->display_timing_valid) {
> DRM_DEV_ERROR(dev, "mipi not set display timing yet.\n");
> return;
> }
>
> +   dev_dbg(dev, "set downstream sink into normal\n");
> +   /* Downstream sink enter into normal mode */
> +   data = 1;
> +   ret = anx7625_aux_trans(ctx, DP_AUX_NATIVE_WRITE, 0x000600, 1, &data);
> +   if (ret < 0)
> +   dev_err(dev, "IO error : set sink into normal mode fail\n");
> +

The driver uses DRM_DEV_* for logs. Can we use this?

> /* Disable HDCP */
> anx7625_write_and(ctx, ctx->i2c.rx_p1_client, 0xee, 0x9f);
>
> --
> 2.25.1
>


Re: [PATCH v2 4/7] drm/i915/guc: use the memcpy_from_wc call from the drm

2022-03-22 Thread Michal Wajdeczko



On 21.03.2022 22:14, Lucas De Marchi wrote:
> On Thu, Mar 03, 2022 at 11:30:10PM +0530, Balasubramani Vivekanandan wrote:
>> memcpy_from_wc functions in i915_memcpy.c will be removed and replaced
>> by the implementation in drm_cache.c.
>> Updated to use the functions provided by drm_cache.c.
>>
>> v2: Check if the log object allocated from local memory or system memory
>>    and according setup the iosys_map (Lucas)
>>
>> Cc: Lucas De Marchi 
>>
>> Signed-off-by: Balasubramani Vivekanandan
>> 
>> ---
>> drivers/gpu/drm/i915/gt/uc/intel_guc_log.c | 15 ---
>> 1 file changed, 12 insertions(+), 3 deletions(-)
>>
>> diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c
>> b/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c
>> index a24dc6441872..b9db765627ea 100644
>> --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c
>> +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c
>> @@ -3,6 +3,7 @@
>>  * Copyright © 2014-2019 Intel Corporation
>>  */
>>
>> +#include 
>> #include 
>> #include 
>>
>> @@ -206,6 +207,7 @@ static void guc_read_update_log_buffer(struct
>> intel_guc_log *log)
>> enum guc_log_buffer_type type;
>> void *src_data, *dst_data;
>> bool new_overflow;
>> +    struct iosys_map src_map;
>>
>> mutex_lock(&log->relay.lock);
>>
>> @@ -282,14 +284,21 @@ static void guc_read_update_log_buffer(struct
>> intel_guc_log *log)
>>     }
>>
>>     /* Just copy the newly written data */
>> +    if (i915_gem_object_is_lmem(log->vma->obj))
>> +    iosys_map_set_vaddr_iomem(&src_map, (void __iomem
>> *)src_data);
>> +    else
>> +    iosys_map_set_vaddr(&src_map, src_data);
> 
> It would be better to keep this outside of the loop. So inside the loop
> we can use only iosys_map_incr(&src_map, buffer_size). However you'd
> also have to handle the read_offset. The iosys_map_ API has both a
> src_offset and dst_offset due to situations like that. Maybe this is
> missing in the new drm_memcpy_* function you're adding?
> 
> This function was not correct wrt to IO memory access with the other
> 2 places in this function doing plain memcpy(). Since we are starting to
> use iosys_map here, we probably should handle this commit as "migrate to
> iosys_map", and convert those. In your current final state
> we have 3 variables aliasing the same memory location. IMO it will be
> error prone to keep it like that
> 
> +Michal, some questions:

@Lucas, better to ask Alan who is making some changes around GuC log

@Alan, can you help answer below questions?

thanks,
Michal

> 
> - I'm not very familiar with the relayfs API. Is the `dst_data +=
> PAGE_SIZE;`
> really correct?
> 
> - Could you double check this patch and ack if ok?
> 
> Heads up that since the log buffer is potentially in lmem, we will need
> to convert this function to take that into account. All those accesses
> to log_buf_state need to use the proper kernel abstraction for system vs
> I/O memory.
> 
> thanks
> Lucas De Marchi
> 
>> +
>>     if (read_offset > write_offset) {
>> -    i915_memcpy_from_wc(dst_data, src_data, write_offset);
>> +    drm_memcpy_from_wc_vaddr(dst_data, &src_map,
>> + write_offset);
>>     bytes_to_copy = buffer_size - read_offset;
>>     } else {
>>     bytes_to_copy = write_offset - read_offset;
>>     }
>> -    i915_memcpy_from_wc(dst_data + read_offset,
>> -    src_data + read_offset, bytes_to_copy);
>> +    iosys_map_incr(&src_map, read_offset);
>> +    drm_memcpy_from_wc_vaddr(dst_data + read_offset, &src_map,
>> + bytes_to_copy);
>>
>>     src_data += buffer_size;
>>     dst_data += buffer_size;
>> -- 
>> 2.25.1
>>


Re: [PATCH v2] drm/bridge: anx7625: Set downstream sink into normal status

2022-03-22 Thread Xin Ji
On Tue, Mar 22, 2022 at 04:43:20PM +0800, Hsin-Yi Wang wrote:
> On Tue, Mar 22, 2022 at 4:02 PM Xin Ji  wrote:
> >
> > As downstream sink was set into standby mode while bridge disabled,
> > this patch used for setting downstream sink into normal status
> > while enable bridge.
> >
> > Signed-off-by: Xin Ji 
> > Reviewed-by: Pin-Yen Lin 
> >
> > ---
> > V1 -> V2: use dev_dbg replace of dev_info
> > ---
> >  drivers/gpu/drm/bridge/analogix/anx7625.c | 8 
> >  1 file changed, 8 insertions(+)
> >
> > diff --git a/drivers/gpu/drm/bridge/analogix/anx7625.c 
> > b/drivers/gpu/drm/bridge/analogix/anx7625.c
> > index 9a2a19ad4202..dcf3275a00fe 100644
> > --- a/drivers/gpu/drm/bridge/analogix/anx7625.c
> > +++ b/drivers/gpu/drm/bridge/analogix/anx7625.c
> > @@ -924,12 +924,20 @@ static void anx7625_dp_start(struct anx7625_data *ctx)
> >  {
> > int ret;
> > struct device *dev = &ctx->client->dev;
> > +   u8 data;
> >
> > if (!ctx->display_timing_valid) {
> > DRM_DEV_ERROR(dev, "mipi not set display timing yet.\n");
> > return;
> > }
> >
> > +   dev_dbg(dev, "set downstream sink into normal\n");
> > +   /* Downstream sink enter into normal mode */
> > +   data = 1;
> > +   ret = anx7625_aux_trans(ctx, DP_AUX_NATIVE_WRITE, 0x000600, 1, 
> > &data);
> > +   if (ret < 0)
> > +   dev_err(dev, "IO error : set sink into normal mode fail\n");
> > +
> 
> The driver uses DRM_DEV_* for logs. Can we use this?
Hi Hsin-Yi, as comment in drm/drm_print.h:
"NOTE: this is deprecated in favor of drm_dbg". DRM bridge driver not
use DRM_DEV_* any more. I'll send a patch to replace all of DRM_DEV_*
later.

Thanks,
Xin
> 
> > /* Disable HDCP */
> > anx7625_write_and(ctx, ctx->i2c.rx_p1_client, 0xee, 0x9f);
> >
> > --
> > 2.25.1
> >


Re: [PATCH v2] drm/bridge: anx7625: Set downstream sink into normal status

2022-03-22 Thread Pin-yen Lin
The DRM_DEV_* macros have been deprecated:
https://www.kernel.org/doc/html/latest/gpu/drm-internals.html#c.DRM_DEV_DEBUG_DRIVER

On Tue, Mar 22, 2022 at 4:43 PM Hsin-Yi Wang  wrote:
>
> On Tue, Mar 22, 2022 at 4:02 PM Xin Ji  wrote:
> >
> > As downstream sink was set into standby mode while bridge disabled,
> > this patch used for setting downstream sink into normal status
> > while enable bridge.
> >
> > Signed-off-by: Xin Ji 
> > Reviewed-by: Pin-Yen Lin 
> >
> > ---
> > V1 -> V2: use dev_dbg replace of dev_info
> > ---
> >  drivers/gpu/drm/bridge/analogix/anx7625.c | 8 
> >  1 file changed, 8 insertions(+)
> >
> > diff --git a/drivers/gpu/drm/bridge/analogix/anx7625.c 
> > b/drivers/gpu/drm/bridge/analogix/anx7625.c
> > index 9a2a19ad4202..dcf3275a00fe 100644
> > --- a/drivers/gpu/drm/bridge/analogix/anx7625.c
> > +++ b/drivers/gpu/drm/bridge/analogix/anx7625.c
> > @@ -924,12 +924,20 @@ static void anx7625_dp_start(struct anx7625_data *ctx)
> >  {
> > int ret;
> > struct device *dev = &ctx->client->dev;
> > +   u8 data;
> >
> > if (!ctx->display_timing_valid) {
> > DRM_DEV_ERROR(dev, "mipi not set display timing yet.\n");
> > return;
> > }
> >
> > +   dev_dbg(dev, "set downstream sink into normal\n");
> > +   /* Downstream sink enter into normal mode */
> > +   data = 1;
> > +   ret = anx7625_aux_trans(ctx, DP_AUX_NATIVE_WRITE, 0x000600, 1, 
> > &data);
> > +   if (ret < 0)
> > +   dev_err(dev, "IO error : set sink into normal mode fail\n");
> > +
>
> The driver uses DRM_DEV_* for logs. Can we use this?
>
> > /* Disable HDCP */
> > anx7625_write_and(ctx, ctx->i2c.rx_p1_client, 0xee, 0x9f);
> >
> > --
> > 2.25.1
> >


Re: [PATCH v2] drm/bridge: anx7625: Set downstream sink into normal status

2022-03-22 Thread Chen-Yu Tsai
On Tue, Mar 22, 2022 at 4:52 PM Xin Ji  wrote:
>
> On Tue, Mar 22, 2022 at 04:43:20PM +0800, Hsin-Yi Wang wrote:
> > On Tue, Mar 22, 2022 at 4:02 PM Xin Ji  wrote:
> > >
> > > As downstream sink was set into standby mode while bridge disabled,
> > > this patch used for setting downstream sink into normal status
> > > while enable bridge.
> > >
> > > Signed-off-by: Xin Ji 
> > > Reviewed-by: Pin-Yen Lin 
> > >
> > > ---
> > > V1 -> V2: use dev_dbg replace of dev_info
> > > ---
> > >  drivers/gpu/drm/bridge/analogix/anx7625.c | 8 
> > >  1 file changed, 8 insertions(+)
> > >
> > > diff --git a/drivers/gpu/drm/bridge/analogix/anx7625.c 
> > > b/drivers/gpu/drm/bridge/analogix/anx7625.c
> > > index 9a2a19ad4202..dcf3275a00fe 100644
> > > --- a/drivers/gpu/drm/bridge/analogix/anx7625.c
> > > +++ b/drivers/gpu/drm/bridge/analogix/anx7625.c
> > > @@ -924,12 +924,20 @@ static void anx7625_dp_start(struct anx7625_data 
> > > *ctx)
> > >  {
> > > int ret;
> > > struct device *dev = &ctx->client->dev;
> > > +   u8 data;
> > >
> > > if (!ctx->display_timing_valid) {
> > > DRM_DEV_ERROR(dev, "mipi not set display timing yet.\n");
> > > return;
> > > }
> > >
> > > +   dev_dbg(dev, "set downstream sink into normal\n");
> > > +   /* Downstream sink enter into normal mode */
> > > +   data = 1;
> > > +   ret = anx7625_aux_trans(ctx, DP_AUX_NATIVE_WRITE, 0x000600, 1, 
> > > &data);
> > > +   if (ret < 0)
> > > +   dev_err(dev, "IO error : set sink into normal mode 
> > > fail\n");
> > > +
> >
> > The driver uses DRM_DEV_* for logs. Can we use this?
> Hi Hsin-Yi, as comment in drm/drm_print.h:
> "NOTE: this is deprecated in favor of drm_dbg". DRM bridge driver not
> use DRM_DEV_* any more. I'll send a patch to replace all of DRM_DEV_*
> later.

drm_dbg is better than dev_dbg though. With the former, you still get the
option to control it with the drm.debug module parameter, unlike the latter
which normally gets compiled out.

Please use drm_dbg*.

ChenYu

> Thanks,
> Xin
> >
> > > /* Disable HDCP */
> > > anx7625_write_and(ctx, ctx->i2c.rx_p1_client, 0xee, 0x9f);
> > >
> > > --
> > > 2.25.1
> > >


Re: [PATCH v5 1/9] drm/i915/gt: Use XY_FAST_COLOR_BLT to clear obj on graphics ver 12+

2022-03-22 Thread Thomas Hellström
On Tue, 2022-03-22 at 04:14 +0530, Ramalingam C wrote:
> Use faster XY_FAST_COLOR_BLT cmd on graphics version of 12 and more,
> for clearing (Zero out) the pages of the newly allocated object.
> 
> XY_FAST_COLOR_BLT is faster than the older XY_COLOR_BLT.
> 
> v2:
>   Typo fix at title [Thomas]
> 
> Signed-off-by: Ramalingam C 
> Signed-off-by: Chris Wilson 
> Reviewed-by: Thomas Hellstrom 
> ---
>  drivers/gpu/drm/i915/gt/intel_gpu_commands.h |  5 +++
>  drivers/gpu/drm/i915/gt/intel_migrate.c  | 43 +-
> --
>  2 files changed, 43 insertions(+), 5 deletions(-)
> 
> diff --git a/drivers/gpu/drm/i915/gt/intel_gpu_commands.h
> b/drivers/gpu/drm/i915/gt/intel_gpu_commands.h
> index d112ffd56418..925e55b6a94f 100644
> --- a/drivers/gpu/drm/i915/gt/intel_gpu_commands.h
> +++ b/drivers/gpu/drm/i915/gt/intel_gpu_commands.h
> @@ -205,6 +205,11 @@
>  
>  #define COLOR_BLT_CMD  (2 << 29 | 0x40 << 22 | (5 -
> 2))
>  #define XY_COLOR_BLT_CMD   (2 << 29 | 0x50 << 22)
> +#define XY_FAST_COLOR_BLT_CMD  (2 << 29 | 0x44 << 22)
> +#define   XY_FAST_COLOR_BLT_DEPTH_32   (2 << 19)
> +#define   XY_FAST_COLOR_BLT_DW 16
> +#define   XY_FAST_COLOR_BLT_MOCS_MASK  GENMASK(27, 21)
> +#define   XY_FAST_COLOR_BLT_MEM_TYPE_SHIFT 31
>  #define SRC_COPY_BLT_CMD   (2 << 29 | 0x43 << 22)
>  #define GEN9_XY_FAST_COPY_BLT_CMD  (2 << 29 | 0x42 << 22)
>  #define XY_SRC_COPY_BLT_CMD(2 << 29 | 0x53 << 22)
> diff --git a/drivers/gpu/drm/i915/gt/intel_migrate.c
> b/drivers/gpu/drm/i915/gt/intel_migrate.c
> index 20444d6ceb3c..73199ebf0671 100644
> --- a/drivers/gpu/drm/i915/gt/intel_migrate.c
> +++ b/drivers/gpu/drm/i915/gt/intel_migrate.c
> @@ -614,20 +614,53 @@ intel_context_migrate_copy(struct intel_context
> *ce,
> return err;
>  }
>  
> -static int emit_clear(struct i915_request *rq, u64 offset, int size,
> u32 value)
> +static int emit_clear(struct i915_request *rq, u64 offset, int size,
> + u32 value, bool is_lmem)
>  {
> -   const int ver = GRAPHICS_VER(rq->engine->i915);
> +   struct drm_i915_private *i915 = rq->engine->i915;
> +   int mocs = rq->engine->gt->mocs.uc_index << 1;
> +   const int ver = GRAPHICS_VER(i915);
> +   int ring_sz;
> u32 *cs;
>  
> GEM_BUG_ON(size >> PAGE_SHIFT > S16_MAX);
>  
> offset += (u64)rq->engine->instance << 32;
>  
> -   cs = intel_ring_begin(rq, ver >= 8 ? 8 : 6);
> +   if (ver >= 12)
> +   ring_sz = 16;

XY_FAST_COLOR_BLT_DW

With that fixed, 
Reviewed-by: Thomas Hellström 


> +   else if (ver >= 8)
> +   ring_sz = 8;
> +   else
> +   ring_sz = 6;
> +
> +   cs = intel_ring_begin(rq, ring_sz);
> if (IS_ERR(cs))
> return PTR_ERR(cs);
>  
> -   if (ver >= 8) {
> +   if (ver >= 12) {
> +   *cs++ = XY_FAST_COLOR_BLT_CMD |
> XY_FAST_COLOR_BLT_DEPTH_32 |
> +   (XY_FAST_COLOR_BLT_DW - 2);
> +   *cs++ = FIELD_PREP(XY_FAST_COLOR_BLT_MOCS_MASK, mocs)
> |
> +   (PAGE_SIZE - 1);
> +   *cs++ = 0;
> +   *cs++ = size >> PAGE_SHIFT << 16 | PAGE_SIZE / 4;
> +   *cs++ = lower_32_bits(offset);
> +   *cs++ = upper_32_bits(offset);
> +   *cs++ = !is_lmem << XY_FAST_COLOR_BLT_MEM_TYPE_SHIFT;
> +   /* BG7 */
> +   *cs++ = value;
> +   *cs++ = 0;
> +   *cs++ = 0;
> +   *cs++ = 0;
> +   /* BG11 */
> +   *cs++ = 0;
> +   *cs++ = 0;
> +   /* BG13 */
> +   *cs++ = 0;
> +   *cs++ = 0;
> +   *cs++ = 0;
> +   } else if (ver >= 8) {
> *cs++ = XY_COLOR_BLT_CMD | BLT_WRITE_RGBA | (7 - 2);
> *cs++ = BLT_DEPTH_32 | BLT_ROP_COLOR_COPY |
> PAGE_SIZE;
> *cs++ = 0;
> @@ -711,7 +744,7 @@ intel_context_migrate_clear(struct intel_context
> *ce,
> if (err)
> goto out_rq;
>  
> -   err = emit_clear(rq, offset, len, value);
> +   err = emit_clear(rq, offset, len, value, is_lmem);
>  
> /* Arbitration is re-enabled between requests. */
>  out_rq:




Re: [PATCH 0/4] Drop wbinvd_on_all_cpus usage

2022-03-22 Thread Tvrtko Ursulin



On 21/03/2022 15:15, Thomas Hellström wrote:

On Mon, 2022-03-21 at 14:43 +, Tvrtko Ursulin wrote:


On 21/03/2022 13:40, Thomas Hellström wrote:

Hi,

On Mon, 2022-03-21 at 13:12 +, Tvrtko Ursulin wrote:


On 21/03/2022 12:33, Thomas Hellström wrote:

On Mon, 2022-03-21 at 12:22 +, Tvrtko Ursulin wrote:


On 21/03/2022 11:03, Thomas Hellström wrote:

Hi, Tvrtko.

On 3/21/22 11:27, Tvrtko Ursulin wrote:


On 19/03/2022 19:42, Michael Cheng wrote:

To align with the discussion in [1][2], this patch
series
drops
all
usage of
wbvind_on_all_cpus within i915 by either replacing the
call
with certain
drm clflush helpers, or reverting to a previous logic.


AFAIU, complaint from [1] was that it is wrong to provide
non
x86
implementations under the wbinvd_on_all_cpus name.
Instead an
arch
agnostic helper which achieves the same effect could be
created.
Does
Arm have such concept?


I also understand Linus' email like we shouldn't leak
incoherent
IO
to
other architectures, meaning any remaining wbinvd()s should
be
X86
only.


The last part is completely obvious since it is a x86
instruction
name.


Yeah, I meant the function implementing wbinvd() semantics.



But I think we can't pick a solution until we know how the
concept
maps
to Arm and that will also include seeing how the
drm_clflush_sg for
Arm
would look. Is there a range based solution, or just a big
hammer
there.
If the latter, then it is no good to churn all these reverts
but
instead
an arch agnostic wrapper, with a generic name, would be the
way to
go.


But my impression was that ARM would not need the range-based
interface
either, because ARM is only for discrete and with discrete
we're
always
coherent.


Not sure what you mean here - what about flushing system memory
objects
on discrete? Those still need flushing on paths like suspend
which this
series touches. Am I missing something?


System bos on discrete should always have

I915_BO_CACHE_COHERENT_FOR_READ | I915_BO_CACHE_COHERENT_FOR_WRITE

either by the gpu being fully cache coherent (or us mapping system
write-combined). Hence no need for cache clflushes or wbinvd() for
incoherent IO.


Hmm so you are talking about the shmem ttm backend. It ends up
depending on the result of i915_ttm_cache_level, yes? It cannot end
up with I915_CACHE_NONE from that function?


If the object is allocated with allowable placement in either LMEM or
SYSTEM, and it ends in system, it gets allocated with I915_CACHE_NONE,
but then the shmem ttm backend isn't used but TTM's wc pools, and the
object should *always* be mapped wc. Even in system.


I am not familiar with neither TTM backend or wc pools so maybe a missed 
question - if obj->cache_level can be set to none, and 
obj->cache_coherency to zero, then during object lifetime helpers which 
consult those fields (like i915_gem_cpu_write_needs_clflush, 
__start_cpu_write, etc) are giving out incorrect answers? That is, it is 
irrelevant that they would say flushes are required, since in actuality 
those objects can never ever and from anywhere be mapped other than WC 
so flushes aren't actually required?



I also found in i915_drm.h:

  * As caching mode when specifying `I915_MMAP_OFFSET_FIXED`,
WC or WB will
  * be used, depending on the object placement on creation. WB
will be used
  * when the object can only exist in system memory, WC
otherwise.

If what you say is true, that on discrete it is _always_ WC, then
that needs updating as well.


If an object is allocated as system only, then it is mapped WB, and
we're relying on the gpu being cache coherent to avoid clflushes. Same
is actually currently true if the object happens to be accessed by the
cpu while evicted. Might need an update for that.


Hmm okay, I think I actually misunderstood something here. I think the 
reason for difference bbtween smem+lmem object which happens to be in 
smem and smem only object is eluding me.




That's adhering to Linus'

"And I sincerely hope to the gods that no cache-incoherent i915
mess
ever makes it out of the x86 world. Incoherent IO was always a
historical mistake and should never ever happen again, so we should
not spread that horrific pattern around."


Sure, but I was not talking about IO - just the CPU side access to
CPU side objects.


OK, I was under the impression that clflushes() and wbinvd()s in i915
was only ever used to make data visible to non-snooping GPUs.

Do you mean that there are other uses as well? Agreed the wb cache
flush on on suspend only if gpu is !I915_BO_CACHE_COHERENT_FOR_READ?
looks to not fit this pattern completely.


Don't know, I was first trying to understand handling of the 
obj->cache_coherent as discussed in the first quote block. Are the flags 
consistently set and how the Arm low level code will look.



Otherwise, for architectures where memory isn't always fully coherent
with the cpu cache, I'd expect them to use the apis in
asm/cacheflush.h, like flush_cache_range() and similar, which are 

Re: [PATCH v2] drm/bridge: anx7625: Set downstream sink into normal status

2022-03-22 Thread Xin Ji
On Tue, Mar 22, 2022 at 05:16:43PM +0800, Chen-Yu Tsai wrote:
> On Tue, Mar 22, 2022 at 4:52 PM Xin Ji  wrote:
> >
> > On Tue, Mar 22, 2022 at 04:43:20PM +0800, Hsin-Yi Wang wrote:
> > > On Tue, Mar 22, 2022 at 4:02 PM Xin Ji  wrote:
> > > >
> > > > As downstream sink was set into standby mode while bridge disabled,
> > > > this patch used for setting downstream sink into normal status
> > > > while enable bridge.
> > > >
> > > > Signed-off-by: Xin Ji 
> > > > Reviewed-by: Pin-Yen Lin 
> > > >
> > > > ---
> > > > V1 -> V2: use dev_dbg replace of dev_info
> > > > ---
> > > >  drivers/gpu/drm/bridge/analogix/anx7625.c | 8 
> > > >  1 file changed, 8 insertions(+)
> > > >
> > > > diff --git a/drivers/gpu/drm/bridge/analogix/anx7625.c 
> > > > b/drivers/gpu/drm/bridge/analogix/anx7625.c
> > > > index 9a2a19ad4202..dcf3275a00fe 100644
> > > > --- a/drivers/gpu/drm/bridge/analogix/anx7625.c
> > > > +++ b/drivers/gpu/drm/bridge/analogix/anx7625.c
> > > > @@ -924,12 +924,20 @@ static void anx7625_dp_start(struct anx7625_data 
> > > > *ctx)
> > > >  {
> > > > int ret;
> > > > struct device *dev = &ctx->client->dev;
> > > > +   u8 data;
> > > >
> > > > if (!ctx->display_timing_valid) {
> > > > DRM_DEV_ERROR(dev, "mipi not set display timing 
> > > > yet.\n");
> > > > return;
> > > > }
> > > >
> > > > +   dev_dbg(dev, "set downstream sink into normal\n");
> > > > +   /* Downstream sink enter into normal mode */
> > > > +   data = 1;
> > > > +   ret = anx7625_aux_trans(ctx, DP_AUX_NATIVE_WRITE, 0x000600, 1, 
> > > > &data);
> > > > +   if (ret < 0)
> > > > +   dev_err(dev, "IO error : set sink into normal mode 
> > > > fail\n");
> > > > +
> > >
> > > The driver uses DRM_DEV_* for logs. Can we use this?
> > Hi Hsin-Yi, as comment in drm/drm_print.h:
> > "NOTE: this is deprecated in favor of drm_dbg". DRM bridge driver not
> > use DRM_DEV_* any more. I'll send a patch to replace all of DRM_DEV_*
> > later.
> 
> drm_dbg is better than dev_dbg though. With the former, you still get the
> option to control it with the drm.debug module parameter, unlike the latter
> which normally gets compiled out.
> 
> Please use drm_dbg*.
> 
> ChenYu

Hi ChenYu, the parameter of drm_dbg is "drm", if use drm_dbg, it will
change more code, I'll consider to upstream new patch to replace all of
them later.

Thanks,
Xin
> 
> > Thanks,
> > Xin
> > >
> > > > /* Disable HDCP */
> > > > anx7625_write_and(ctx, ctx->i2c.rx_p1_client, 0xee, 0x9f);
> > > >
> > > > --
> > > > 2.25.1
> > > >


Re: [PATCH 0/4] Drop wbinvd_on_all_cpus usage

2022-03-22 Thread Thomas Hellström
On Tue, 2022-03-22 at 10:13 +, Tvrtko Ursulin wrote:
> 
> On 21/03/2022 15:15, Thomas Hellström wrote:
> > On Mon, 2022-03-21 at 14:43 +, Tvrtko Ursulin wrote:
> > > 
> > > On 21/03/2022 13:40, Thomas Hellström wrote:
> > > > Hi,
> > > > 
> > > > On Mon, 2022-03-21 at 13:12 +, Tvrtko Ursulin wrote:
> > > > > 
> > > > > On 21/03/2022 12:33, Thomas Hellström wrote:
> > > > > > On Mon, 2022-03-21 at 12:22 +, Tvrtko Ursulin wrote:
> > > > > > > 
> > > > > > > On 21/03/2022 11:03, Thomas Hellström wrote:
> > > > > > > > Hi, Tvrtko.
> > > > > > > > 
> > > > > > > > On 3/21/22 11:27, Tvrtko Ursulin wrote:
> > > > > > > > > 
> > > > > > > > > On 19/03/2022 19:42, Michael Cheng wrote:
> > > > > > > > > > To align with the discussion in [1][2], this patch
> > > > > > > > > > series
> > > > > > > > > > drops
> > > > > > > > > > all
> > > > > > > > > > usage of
> > > > > > > > > > wbvind_on_all_cpus within i915 by either replacing
> > > > > > > > > > the
> > > > > > > > > > call
> > > > > > > > > > with certain
> > > > > > > > > > drm clflush helpers, or reverting to a previous
> > > > > > > > > > logic.
> > > > > > > > > 
> > > > > > > > > AFAIU, complaint from [1] was that it is wrong to
> > > > > > > > > provide
> > > > > > > > > non
> > > > > > > > > x86
> > > > > > > > > implementations under the wbinvd_on_all_cpus name.
> > > > > > > > > Instead an
> > > > > > > > > arch
> > > > > > > > > agnostic helper which achieves the same effect could
> > > > > > > > > be
> > > > > > > > > created.
> > > > > > > > > Does
> > > > > > > > > Arm have such concept?
> > > > > > > > 
> > > > > > > > I also understand Linus' email like we shouldn't leak
> > > > > > > > incoherent
> > > > > > > > IO
> > > > > > > > to
> > > > > > > > other architectures, meaning any remaining wbinvd()s
> > > > > > > > should
> > > > > > > > be
> > > > > > > > X86
> > > > > > > > only.
> > > > > > > 
> > > > > > > The last part is completely obvious since it is a x86
> > > > > > > instruction
> > > > > > > name.
> > > > > > 
> > > > > > Yeah, I meant the function implementing wbinvd() semantics.
> > > > > > 
> > > > > > > 
> > > > > > > But I think we can't pick a solution until we know how
> > > > > > > the
> > > > > > > concept
> > > > > > > maps
> > > > > > > to Arm and that will also include seeing how the
> > > > > > > drm_clflush_sg for
> > > > > > > Arm
> > > > > > > would look. Is there a range based solution, or just a
> > > > > > > big
> > > > > > > hammer
> > > > > > > there.
> > > > > > > If the latter, then it is no good to churn all these
> > > > > > > reverts
> > > > > > > but
> > > > > > > instead
> > > > > > > an arch agnostic wrapper, with a generic name, would be
> > > > > > > the
> > > > > > > way to
> > > > > > > go.
> > > > > > 
> > > > > > But my impression was that ARM would not need the range-
> > > > > > based
> > > > > > interface
> > > > > > either, because ARM is only for discrete and with discrete
> > > > > > we're
> > > > > > always
> > > > > > coherent.
> > > > > 
> > > > > Not sure what you mean here - what about flushing system
> > > > > memory
> > > > > objects
> > > > > on discrete? Those still need flushing on paths like suspend
> > > > > which this
> > > > > series touches. Am I missing something?
> > > > 
> > > > System bos on discrete should always have
> > > > 
> > > > I915_BO_CACHE_COHERENT_FOR_READ |
> > > > I915_BO_CACHE_COHERENT_FOR_WRITE
> > > > 
> > > > either by the gpu being fully cache coherent (or us mapping
> > > > system
> > > > write-combined). Hence no need for cache clflushes or wbinvd()
> > > > for
> > > > incoherent IO.
> > > 
> > > Hmm so you are talking about the shmem ttm backend. It ends up
> > > depending on the result of i915_ttm_cache_level, yes? It cannot
> > > end
> > > up with I915_CACHE_NONE from that function?
> > 
> > If the object is allocated with allowable placement in either LMEM
> > or
> > SYSTEM, and it ends in system, it gets allocated with
> > I915_CACHE_NONE,
> > but then the shmem ttm backend isn't used but TTM's wc pools, and
> > the
> > object should *always* be mapped wc. Even in system.
> 
> I am not familiar with neither TTM backend or wc pools so maybe a
> missed 
> question - if obj->cache_level can be set to none, and 
> obj->cache_coherency to zero, then during object lifetime helpers
> which 
> consult those fields (like i915_gem_cpu_write_needs_clflush, 
> __start_cpu_write, etc) are giving out incorrect answers? That is, it
> is 
> irrelevant that they would say flushes are required, since in
> actuality 
> those objects can never ever and from anywhere be mapped other than
> WC 
> so flushes aren't actually required?

If we map other than WC somewhere in these situations, that should be a
bug needing a fix. It might be that some of these helpers that you
mention might still flag that a clflush is needed, and in that case
that's an oversight that also needs fixing.

> 
> > > I also found in i915_drm.h:
> > > 
> > >   * As caching mod

Re: [PATCH 0/4] Drop wbinvd_on_all_cpus usage

2022-03-22 Thread Thomas Hellström
On Tue, 2022-03-22 at 11:26 +0100, Thomas Hellström wrote:
> On Tue, 2022-03-22 at 10:13 +, Tvrtko Ursulin wrote:
> > 
> > On 21/03/2022 15:15, Thomas Hellström wrote:
> > > On Mon, 2022-03-21 at 14:43 +, Tvrtko Ursulin wrote:
> > > > 
> > > > On 21/03/2022 13:40, Thomas Hellström wrote:
> > > > > Hi,
> > > > > 
> > > > > On Mon, 2022-03-21 at 13:12 +, Tvrtko Ursulin wrote:
> > > > > > 
> > > > > > On 21/03/2022 12:33, Thomas Hellström wrote:
> > > > > > > On Mon, 2022-03-21 at 12:22 +, Tvrtko Ursulin wrote:
> > > > > > > > 
> > > > > > > > On 21/03/2022 11:03, Thomas Hellström wrote:
> > > > > > > > > Hi, Tvrtko.
> > > > > > > > > 
> > > > > > > > > On 3/21/22 11:27, Tvrtko Ursulin wrote:
> > > > > > > > > > 
> > > > > > > > > > On 19/03/2022 19:42, Michael Cheng wrote:
> > > > > > > > > > > To align with the discussion in [1][2], this
> > > > > > > > > > > patch
> > > > > > > > > > > series
> > > > > > > > > > > drops
> > > > > > > > > > > all
> > > > > > > > > > > usage of
> > > > > > > > > > > wbvind_on_all_cpus within i915 by either
> > > > > > > > > > > replacing
> > > > > > > > > > > the
> > > > > > > > > > > call
> > > > > > > > > > > with certain
> > > > > > > > > > > drm clflush helpers, or reverting to a previous
> > > > > > > > > > > logic.
> > > > > > > > > > 
> > > > > > > > > > AFAIU, complaint from [1] was that it is wrong to
> > > > > > > > > > provide
> > > > > > > > > > non
> > > > > > > > > > x86
> > > > > > > > > > implementations under the wbinvd_on_all_cpus name.
> > > > > > > > > > Instead an
> > > > > > > > > > arch
> > > > > > > > > > agnostic helper which achieves the same effect
> > > > > > > > > > could
> > > > > > > > > > be
> > > > > > > > > > created.
> > > > > > > > > > Does
> > > > > > > > > > Arm have such concept?
> > > > > > > > > 
> > > > > > > > > I also understand Linus' email like we shouldn't leak
> > > > > > > > > incoherent
> > > > > > > > > IO
> > > > > > > > > to
> > > > > > > > > other architectures, meaning any remaining wbinvd()s
> > > > > > > > > should
> > > > > > > > > be
> > > > > > > > > X86
> > > > > > > > > only.
> > > > > > > > 
> > > > > > > > The last part is completely obvious since it is a x86
> > > > > > > > instruction
> > > > > > > > name.
> > > > > > > 
> > > > > > > Yeah, I meant the function implementing wbinvd()
> > > > > > > semantics.
> > > > > > > 
> > > > > > > > 
> > > > > > > > But I think we can't pick a solution until we know how
> > > > > > > > the
> > > > > > > > concept
> > > > > > > > maps
> > > > > > > > to Arm and that will also include seeing how the
> > > > > > > > drm_clflush_sg for
> > > > > > > > Arm
> > > > > > > > would look. Is there a range based solution, or just a
> > > > > > > > big
> > > > > > > > hammer
> > > > > > > > there.
> > > > > > > > If the latter, then it is no good to churn all these
> > > > > > > > reverts
> > > > > > > > but
> > > > > > > > instead
> > > > > > > > an arch agnostic wrapper, with a generic name, would be
> > > > > > > > the
> > > > > > > > way to
> > > > > > > > go.
> > > > > > > 
> > > > > > > But my impression was that ARM would not need the range-
> > > > > > > based
> > > > > > > interface
> > > > > > > either, because ARM is only for discrete and with
> > > > > > > discrete
> > > > > > > we're
> > > > > > > always
> > > > > > > coherent.
> > > > > > 
> > > > > > Not sure what you mean here - what about flushing system
> > > > > > memory
> > > > > > objects
> > > > > > on discrete? Those still need flushing on paths like
> > > > > > suspend
> > > > > > which this
> > > > > > series touches. Am I missing something?
> > > > > 
> > > > > System bos on discrete should always have
> > > > > 
> > > > > I915_BO_CACHE_COHERENT_FOR_READ |
> > > > > I915_BO_CACHE_COHERENT_FOR_WRITE
> > > > > 
> > > > > either by the gpu being fully cache coherent (or us mapping
> > > > > system
> > > > > write-combined). Hence no need for cache clflushes or
> > > > > wbinvd()
> > > > > for
> > > > > incoherent IO.
> > > > 
> > > > Hmm so you are talking about the shmem ttm backend. It ends up
> > > > depending on the result of i915_ttm_cache_level, yes? It cannot
> > > > end
> > > > up with I915_CACHE_NONE from that function?
> > > 
> > > If the object is allocated with allowable placement in either
> > > LMEM
> > > or
> > > SYSTEM, and it ends in system, it gets allocated with
> > > I915_CACHE_NONE,
> > > but then the shmem ttm backend isn't used but TTM's wc pools, and
> > > the
> > > object should *always* be mapped wc. Even in system.
> > 
> > I am not familiar with neither TTM backend or wc pools so maybe a
> > missed 
> > question - if obj->cache_level can be set to none, and 
> > obj->cache_coherency to zero, then during object lifetime helpers
> > which 
> > consult those fields (like i915_gem_cpu_write_needs_clflush, 
> > __start_cpu_write, etc) are giving out incorrect answers? That is,
> > it
> > is 
> > irrelevant that they would say flushes are required, since in
> > actuality 
>

Re: [PATCH 21/22] drm: Use drm_mode_init() for on-stack modes

2022-03-22 Thread Andrzej Hajda

On 18.02.2022 11:04, Ville Syrjala wrote:

From: Ville Syrjälä 

Initialize on-stack modes with drm_mode_init() to guarantee
no stack garbage in the list head, or that we aren't copying
over another mode's list head.

Based on the following cocci script, with manual fixups:
@decl@
identifier M;
expression E;
@@
- struct drm_display_mode M = E;
+ struct drm_display_mode M;

@@
identifier decl.M;
expression decl.E;
statement S, S1;
@@
struct drm_display_mode M;
... when != S
+ drm_mode_init(&M, &E);
+
S1

@@
expression decl.E;
@@
- &*E
+ E

Signed-off-by: Ville Syrjälä 
---



Reviewed-by: Andrzej Hajda 

Regards
Andrzej


Re: [PATCH 22/22] drm: Use drm_mode_copy()

2022-03-22 Thread Andrzej Hajda

On 18.02.2022 11:04, Ville Syrjala wrote:

From: Ville Syrjälä 

struct drm_display_mode embeds a list head, so overwriting
the full struct with another one will corrupt the list
(if the destination mode is on a list). Use drm_mode_copy()
instead which explicitly preserves the list head of
the destination mode.

Even if we know the destination mode is not on any list
using drm_mode_copy() seems decent as it sets a good
example. Bad examples of not using it might eventually
get copied into code where preserving the list head
actually matters.

Obviously one case not covered here is when the mode
itself is embedded in a larger structure and the whole
structure is copied. But if we are careful when copying
into modes embedded in structures I think we can be a
little more reassured that bogus list heads haven't been
propagated in.

@is_mode_copy@
@@
drm_mode_copy(...)
{
...
}

@depends on !is_mode_copy@
struct drm_display_mode *mode;
expression E, S;
@@
(
- *mode = E
+ drm_mode_copy(mode, &E)
|
- memcpy(mode, E, S)
+ drm_mode_copy(mode, E)
)

@depends on !is_mode_copy@
struct drm_display_mode mode;
expression E;
@@
(
- mode = E
+ drm_mode_copy(&mode, &E)
|
- memcpy(&mode, E, S)
+ drm_mode_copy(&mode, E)
)

@@
struct drm_display_mode *mode;
@@
- &*mode
+ mode

Signed-off-by: Ville Syrjälä 
---


Reviewed-by: Andrzej Hajda 

Regards
Andrzej


[PATCH v6 9/9] drm/i915/migrate: Evict and restore the flatccs capable lmem obj

2022-03-22 Thread Ramalingam C
When we are swapping out the local memory obj on flat-ccs capable platform,
we need to capture the ccs data too along with main meory and we need to
restore it when we are swapping in the content.

When lmem object is swapped into a smem obj, smem obj will
have the extra pages required to hold the ccs data corresponding to the
lmem main memory. So main memory of lmem will be copied into the initial
pages of the smem and then ccs data corresponding to the main memory
will be copied to the subsequent pages of smem. ccs data is 1/256 of
lmem size.

Swapin happens exactly in reverse order. First main memory of lmem is
restored from the smem's initial pages and the ccs data will be restored
from the subsequent pages of smem.

Extracting and restoring the CCS data is done through a special cmd called
XY_CTRL_SURF_COPY_BLT

v2: Fixing the ccs handling
v3: Handle the ccs data at same loop as main memory [Thomas]
v4: changes for emit_copy_ccs
v5: handle non-flat-ccs scenario

Signed-off-by: Ramalingam C 
---
 drivers/gpu/drm/i915/gt/intel_migrate.c | 164 +++-
 1 file changed, 160 insertions(+), 4 deletions(-)

diff --git a/drivers/gpu/drm/i915/gt/intel_migrate.c 
b/drivers/gpu/drm/i915/gt/intel_migrate.c
index 5f6341f91622..84877ca95ce2 100644
--- a/drivers/gpu/drm/i915/gt/intel_migrate.c
+++ b/drivers/gpu/drm/i915/gt/intel_migrate.c
@@ -657,6 +657,65 @@ static int emit_copy(struct i915_request *rq,
return 0;
 }
 
+static int scatter_list_length(struct scatterlist *sg)
+{
+   int len = 0;
+
+   while (sg && sg_dma_len(sg)) {
+   len += sg_dma_len(sg);
+   sg = sg_next(sg);
+   };
+
+   return len;
+}
+
+static void
+calculate_chunk_sz(struct drm_i915_private *i915, bool src_is_lmem,
+  int *src_sz, int *ccs_sz, u32 bytes_to_cpy,
+  u32 ccs_bytes_to_cpy)
+{
+   if (ccs_bytes_to_cpy) {
+   /*
+* We can only copy the ccs data corresponding to
+* the CHUNK_SZ of lmem which is
+* GET_CCS_BYTES(i915, CHUNK_SZ))
+*/
+   *ccs_sz = min_t(int, ccs_bytes_to_cpy, GET_CCS_BYTES(i915, 
CHUNK_SZ));
+
+   if (!src_is_lmem)
+   /*
+* When CHUNK_SZ is passed all the pages upto CHUNK_SZ
+* will be taken for the blt. in Flat-ccs supported
+* platform Smem obj will have more pages than required
+* for main meory hence limit it to the required size
+* for main memory
+*/
+   *src_sz = min_t(int, bytes_to_cpy, CHUNK_SZ);
+   } else { /* ccs handling is not required */
+   *src_sz = CHUNK_SZ;
+   }
+}
+
+static void get_ccs_sg_sgt(struct sgt_dma *it, u32 bytes_to_cpy)
+{
+   u32 len;
+
+   do {
+   GEM_BUG_ON(!it->sg || !sg_dma_len(it->sg));
+   len = it->max - it->dma;
+   if (len > bytes_to_cpy) {
+   it->dma += bytes_to_cpy;
+   break;
+   }
+
+   bytes_to_cpy -= len;
+
+   it->sg = __sg_next(it->sg);
+   it->dma = sg_dma_address(it->sg);
+   it->max = it->dma + sg_dma_len(it->sg);
+   } while (bytes_to_cpy);
+}
+
 int
 intel_context_migrate_copy(struct intel_context *ce,
   const struct i915_deps *deps,
@@ -668,9 +727,15 @@ intel_context_migrate_copy(struct intel_context *ce,
   bool dst_is_lmem,
   struct i915_request **out)
 {
-   struct sgt_dma it_src = sg_sgt(src), it_dst = sg_sgt(dst);
+   struct sgt_dma it_src = sg_sgt(src), it_dst = sg_sgt(dst), it_ccs;
+   struct drm_i915_private *i915 = ce->engine->i915;
+   u32 ccs_bytes_to_cpy = 0, bytes_to_cpy;
+   enum i915_cache_level ccs_cache_level;
+   int src_sz, dst_sz, ccs_sz;
u32 src_offset, dst_offset;
+   u8 src_access, dst_access;
struct i915_request *rq;
+   bool ccs_is_src;
int err;
 
GEM_BUG_ON(ce->vm != ce->engine->gt->migrate.context->vm);
@@ -678,6 +743,38 @@ intel_context_migrate_copy(struct intel_context *ce,
 
GEM_BUG_ON(ce->ring->size < SZ_64K);
 
+   src_sz = scatter_list_length(src);
+   bytes_to_cpy = src_sz;
+
+   if (HAS_FLAT_CCS(i915) && src_is_lmem ^ dst_is_lmem) {
+   src_access = !src_is_lmem && dst_is_lmem;
+   dst_access = !src_access;
+
+   dst_sz = scatter_list_length(dst);
+   if (src_is_lmem) {
+   it_ccs = it_dst;
+   ccs_cache_level = dst_cache_level;
+   ccs_is_src = false;
+   } else if (dst_is_lmem) {
+   bytes_to_cpy = dst_sz;
+   it_ccs = it_src;
+   ccs_cache_level = src

Re: [PATCH 0/4] Drop wbinvd_on_all_cpus usage

2022-03-22 Thread Tvrtko Ursulin



On 22/03/2022 10:26, Thomas Hellström wrote:

On Tue, 2022-03-22 at 10:13 +, Tvrtko Ursulin wrote:


On 21/03/2022 15:15, Thomas Hellström wrote:

On Mon, 2022-03-21 at 14:43 +, Tvrtko Ursulin wrote:


On 21/03/2022 13:40, Thomas Hellström wrote:

Hi,

On Mon, 2022-03-21 at 13:12 +, Tvrtko Ursulin wrote:


On 21/03/2022 12:33, Thomas Hellström wrote:

On Mon, 2022-03-21 at 12:22 +, Tvrtko Ursulin wrote:


On 21/03/2022 11:03, Thomas Hellström wrote:

Hi, Tvrtko.

On 3/21/22 11:27, Tvrtko Ursulin wrote:


On 19/03/2022 19:42, Michael Cheng wrote:

To align with the discussion in [1][2], this patch
series
drops
all
usage of
wbvind_on_all_cpus within i915 by either replacing
the
call
with certain
drm clflush helpers, or reverting to a previous
logic.


AFAIU, complaint from [1] was that it is wrong to
provide
non
x86
implementations under the wbinvd_on_all_cpus name.
Instead an
arch
agnostic helper which achieves the same effect could
be
created.
Does
Arm have such concept?


I also understand Linus' email like we shouldn't leak
incoherent
IO
to
other architectures, meaning any remaining wbinvd()s
should
be
X86
only.


The last part is completely obvious since it is a x86
instruction
name.


Yeah, I meant the function implementing wbinvd() semantics.



But I think we can't pick a solution until we know how
the
concept
maps
to Arm and that will also include seeing how the
drm_clflush_sg for
Arm
would look. Is there a range based solution, or just a
big
hammer
there.
If the latter, then it is no good to churn all these
reverts
but
instead
an arch agnostic wrapper, with a generic name, would be
the
way to
go.


But my impression was that ARM would not need the range-
based
interface
either, because ARM is only for discrete and with discrete
we're
always
coherent.


Not sure what you mean here - what about flushing system
memory
objects
on discrete? Those still need flushing on paths like suspend
which this
series touches. Am I missing something?


System bos on discrete should always have

I915_BO_CACHE_COHERENT_FOR_READ |
I915_BO_CACHE_COHERENT_FOR_WRITE

either by the gpu being fully cache coherent (or us mapping
system
write-combined). Hence no need for cache clflushes or wbinvd()
for
incoherent IO.


Hmm so you are talking about the shmem ttm backend. It ends up
depending on the result of i915_ttm_cache_level, yes? It cannot
end
up with I915_CACHE_NONE from that function?


If the object is allocated with allowable placement in either LMEM
or
SYSTEM, and it ends in system, it gets allocated with
I915_CACHE_NONE,
but then the shmem ttm backend isn't used but TTM's wc pools, and
the
object should *always* be mapped wc. Even in system.


I am not familiar with neither TTM backend or wc pools so maybe a
missed
question - if obj->cache_level can be set to none, and
obj->cache_coherency to zero, then during object lifetime helpers
which
consult those fields (like i915_gem_cpu_write_needs_clflush,
__start_cpu_write, etc) are giving out incorrect answers? That is, it
is
irrelevant that they would say flushes are required, since in
actuality
those objects can never ever and from anywhere be mapped other than
WC
so flushes aren't actually required?


If we map other than WC somewhere in these situations, that should be a
bug needing a fix. It might be that some of these helpers that you
mention might still flag that a clflush is needed, and in that case
that's an oversight that also needs fixing.




I also found in i915_drm.h:

   * As caching mode when specifying
`I915_MMAP_OFFSET_FIXED`,
WC or WB will
   * be used, depending on the object placement on
creation. WB
will be used
   * when the object can only exist in system memory, WC
otherwise.

If what you say is true, that on discrete it is _always_ WC, then
that needs updating as well.


If an object is allocated as system only, then it is mapped WB, and
we're relying on the gpu being cache coherent to avoid clflushes.
Same
is actually currently true if the object happens to be accessed by
the
cpu while evicted. Might need an update for that.


Hmm okay, I think I actually misunderstood something here. I think
the
reason for difference bbtween smem+lmem object which happens to be in
smem and smem only object is eluding me.



That's adhering to Linus'

"And I sincerely hope to the gods that no cache-incoherent i915
mess
ever makes it out of the x86 world. Incoherent IO was always a
historical mistake and should never ever happen again, so we
should
not spread that horrific pattern around."


Sure, but I was not talking about IO - just the CPU side access
to
CPU side objects.


OK, I was under the impression that clflushes() and wbinvd()s in
i915
was only ever used to make data visible to non-snooping GPUs.

Do you mean that there are other uses as well? Agreed the wb cache
flush on on suspend only if gpu is
!I915_BO_CACHE_COHERENT_FOR_READ?
looks to not fit this pattern completely.


Don't know, I was first trying to un

Re: [PATCH 0/4] Drop wbinvd_on_all_cpus usage

2022-03-22 Thread Thomas Hellström
On Tue, 2022-03-22 at 11:20 +, Tvrtko Ursulin wrote:
> 
> On 22/03/2022 10:26, Thomas Hellström wrote:
> > On Tue, 2022-03-22 at 10:13 +, Tvrtko Ursulin wrote:
> > > 
> > > On 21/03/2022 15:15, Thomas Hellström wrote:
> > > > On Mon, 2022-03-21 at 14:43 +, Tvrtko Ursulin wrote:
> > > > > 
> > > > > On 21/03/2022 13:40, Thomas Hellström wrote:
> > > > > > Hi,
> > > > > > 
> > > > > > On Mon, 2022-03-21 at 13:12 +, Tvrtko Ursulin wrote:
> > > > > > > 
> > > > > > > On 21/03/2022 12:33, Thomas Hellström wrote:
> > > > > > > > On Mon, 2022-03-21 at 12:22 +, Tvrtko Ursulin
> > > > > > > > wrote:
> > > > > > > > > 
> > > > > > > > > On 21/03/2022 11:03, Thomas Hellström wrote:
> > > > > > > > > > Hi, Tvrtko.
> > > > > > > > > > 
> > > > > > > > > > On 3/21/22 11:27, Tvrtko Ursulin wrote:
> > > > > > > > > > > 
> > > > > > > > > > > On 19/03/2022 19:42, Michael Cheng wrote:
> > > > > > > > > > > > To align with the discussion in [1][2], this
> > > > > > > > > > > > patch
> > > > > > > > > > > > series
> > > > > > > > > > > > drops
> > > > > > > > > > > > all
> > > > > > > > > > > > usage of
> > > > > > > > > > > > wbvind_on_all_cpus within i915 by either
> > > > > > > > > > > > replacing
> > > > > > > > > > > > the
> > > > > > > > > > > > call
> > > > > > > > > > > > with certain
> > > > > > > > > > > > drm clflush helpers, or reverting to a previous
> > > > > > > > > > > > logic.
> > > > > > > > > > > 
> > > > > > > > > > > AFAIU, complaint from [1] was that it is wrong to
> > > > > > > > > > > provide
> > > > > > > > > > > non
> > > > > > > > > > > x86
> > > > > > > > > > > implementations under the wbinvd_on_all_cpus
> > > > > > > > > > > name.
> > > > > > > > > > > Instead an
> > > > > > > > > > > arch
> > > > > > > > > > > agnostic helper which achieves the same effect
> > > > > > > > > > > could
> > > > > > > > > > > be
> > > > > > > > > > > created.
> > > > > > > > > > > Does
> > > > > > > > > > > Arm have such concept?
> > > > > > > > > > 
> > > > > > > > > > I also understand Linus' email like we shouldn't
> > > > > > > > > > leak
> > > > > > > > > > incoherent
> > > > > > > > > > IO
> > > > > > > > > > to
> > > > > > > > > > other architectures, meaning any remaining
> > > > > > > > > > wbinvd()s
> > > > > > > > > > should
> > > > > > > > > > be
> > > > > > > > > > X86
> > > > > > > > > > only.
> > > > > > > > > 
> > > > > > > > > The last part is completely obvious since it is a x86
> > > > > > > > > instruction
> > > > > > > > > name.
> > > > > > > > 
> > > > > > > > Yeah, I meant the function implementing wbinvd()
> > > > > > > > semantics.
> > > > > > > > 
> > > > > > > > > 
> > > > > > > > > But I think we can't pick a solution until we know
> > > > > > > > > how
> > > > > > > > > the
> > > > > > > > > concept
> > > > > > > > > maps
> > > > > > > > > to Arm and that will also include seeing how the
> > > > > > > > > drm_clflush_sg for
> > > > > > > > > Arm
> > > > > > > > > would look. Is there a range based solution, or just
> > > > > > > > > a
> > > > > > > > > big
> > > > > > > > > hammer
> > > > > > > > > there.
> > > > > > > > > If the latter, then it is no good to churn all these
> > > > > > > > > reverts
> > > > > > > > > but
> > > > > > > > > instead
> > > > > > > > > an arch agnostic wrapper, with a generic name, would
> > > > > > > > > be
> > > > > > > > > the
> > > > > > > > > way to
> > > > > > > > > go.
> > > > > > > > 
> > > > > > > > But my impression was that ARM would not need the
> > > > > > > > range-
> > > > > > > > based
> > > > > > > > interface
> > > > > > > > either, because ARM is only for discrete and with
> > > > > > > > discrete
> > > > > > > > we're
> > > > > > > > always
> > > > > > > > coherent.
> > > > > > > 
> > > > > > > Not sure what you mean here - what about flushing system
> > > > > > > memory
> > > > > > > objects
> > > > > > > on discrete? Those still need flushing on paths like
> > > > > > > suspend
> > > > > > > which this
> > > > > > > series touches. Am I missing something?
> > > > > > 
> > > > > > System bos on discrete should always have
> > > > > > 
> > > > > > I915_BO_CACHE_COHERENT_FOR_READ |
> > > > > > I915_BO_CACHE_COHERENT_FOR_WRITE
> > > > > > 
> > > > > > either by the gpu being fully cache coherent (or us mapping
> > > > > > system
> > > > > > write-combined). Hence no need for cache clflushes or
> > > > > > wbinvd()
> > > > > > for
> > > > > > incoherent IO.
> > > > > 
> > > > > Hmm so you are talking about the shmem ttm backend. It ends
> > > > > up
> > > > > depending on the result of i915_ttm_cache_level, yes? It
> > > > > cannot
> > > > > end
> > > > > up with I915_CACHE_NONE from that function?
> > > > 
> > > > If the object is allocated with allowable placement in either
> > > > LMEM
> > > > or
> > > > SYSTEM, and it ends in system, it gets allocated with
> > > > I915_CACHE_NONE,
> > > > but then the shmem ttm backend isn't used but TTM's wc pools,
> > > > and
> > > > the
> > > > object should *always* be mapped wc. 

Re: [PATCH 07/23] drm/vmwgfx: stop using dma_resv_excl_fence

2022-03-22 Thread Zack Rusin
On Tue, 2022-03-22 at 08:13 +0100, Christian König wrote:
> Am 21.03.22 um 16:11 schrieb Zack Rusin:
> > On Mon, 2022-03-21 at 15:12 +0100, Christian König wrote:
> > > Am 21.03.22 um 15:02 schrieb Zack Rusin:
> > > > On Mon, 2022-03-21 at 14:58 +0100, Christian König wrote:
> > > > > ⚠ External Email: This email originated from outside of the
> > > > > organization. Do not click links or open attachments unless
> > > > > you
> > > > > recognize the sender.
> > > > > 
> > > > > Instead use the new dma_resv_get_singleton function.
> > > > > 
> > > > > Signed-off-by: Christian König 
> > > > > Reviewed-by: Daniel Vetter 
> > > > > Cc: VMware Graphics 
> > > > > Cc: Zack Rusin 
> > > > > ---
> > > > >    drivers/gpu/drm/vmwgfx/vmwgfx_resource.c | 6 --
> > > > >    1 file changed, 4 insertions(+), 2 deletions(-)
> > > > > 
> > > > > diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_resource.c
> > > > > b/drivers/gpu/drm/vmwgfx/vmwgfx_resource.c
> > > > > index 708899ba2102..36c3b5db7e69 100644
> > > > > --- a/drivers/gpu/drm/vmwgfx/vmwgfx_resource.c
> > > > > +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_resource.c
> > > > > @@ -1165,8 +1165,10 @@ int vmw_resources_clean(struct
> > > > > vmw_buffer_object *vbo, pgoff_t start,
> > > > >   vmw_bo_fence_single(bo, NULL);
> > > > >   if (bo->moving)
> > > > >   dma_fence_put(bo->moving);
> > > > > -   bo->moving = dma_fence_get
> > > > > -   (dma_resv_excl_fence(bo->base.resv));
> > > > > +
> > > > > +   /* TODO: This is actually a memory management
> > > > > dependency */
> > > > > +   return dma_resv_get_singleton(bo->base.resv,
> > > > > false,
> > > > > + &bo->moving);
> > > > >   }
> > > > > 
> > > > >   return 0;
> > > > > --
> > > > > 2.25.1
> > > > > 
> > > > Sorry, I haven't had the time to go over the entire series, the
> > > > patch
> > > > looks good, but what's the memory management dependency the
> > > > todo
> > > > mentions?
> > > Previously the function installed only the exclusive fence as
> > > moving
> > > fence into the BO.
> > > Now it grabs all fences and installs them as moving fence into
> > > the
> > > BO.
> > > 
> > > But what we really need is tracking if a fence in the reservation
> > > object
> > > is a kernel memory management dependency or not.
> > > 
> > > Patch #19 adds that and patch #23 then finally gets rid of the
> > > whole
> > > bo->moving handling here because it becomes completely
> > > unnecessary.
> > > 
> > > I can drop the comment if you want or just note that it is only
> > > temporary until the follow up patches are merged.
> > Ah, yes, if you could remove it that'd be great. The patch will
> > never
> > be backported anywhere without the rest of the series, so it
> > shouldn't
> > be a problem.
> 
> Sure, can I then have your rb for this one?

Yes, of course. Thanks!
Reviewed-by: Zack Rusin 


[PATCH] drm/nouveau/pmu: Add missing callbacks for Tegra devices

2022-03-22 Thread Karol Herbst
Fixes a crash booting on those platforms with nouveau.

Fixes: 4cdd2450bf73 ("drm/nouveau/pmu/gm200-: use alternate falcon reset 
sequence")
Cc: Ben Skeggs 
Cc: Karol Herbst 
Cc: dri-devel@lists.freedesktop.org
Cc: nouv...@lists.freedesktop.org
Cc:  # v5.17+
Signed-off-by: Karol Herbst 
---
 drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gm20b.c | 1 +
 drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gp102.c | 2 +-
 drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gp10b.c | 1 +
 drivers/gpu/drm/nouveau/nvkm/subdev/pmu/priv.h  | 1 +
 4 files changed, 4 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gm20b.c 
b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gm20b.c
index e1772211b0a4..612310d5d481 100644
--- a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gm20b.c
+++ b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gm20b.c
@@ -216,6 +216,7 @@ gm20b_pmu = {
.intr = gt215_pmu_intr,
.recv = gm20b_pmu_recv,
.initmsg = gm20b_pmu_initmsg,
+   .reset = gf100_pmu_reset,
 };
 
 #if IS_ENABLED(CONFIG_ARCH_TEGRA_210_SOC)
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gp102.c 
b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gp102.c
index 6bf7fc1bd1e3..1a6f9c3af5ec 100644
--- a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gp102.c
+++ b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gp102.c
@@ -23,7 +23,7 @@
  */
 #include "priv.h"
 
-static void
+void
 gp102_pmu_reset(struct nvkm_pmu *pmu)
 {
struct nvkm_device *device = pmu->subdev.device;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gp10b.c 
b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gp10b.c
index ba1583bb618b..94cfb1791af6 100644
--- a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gp10b.c
+++ b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gp10b.c
@@ -83,6 +83,7 @@ gp10b_pmu = {
.intr = gt215_pmu_intr,
.recv = gm20b_pmu_recv,
.initmsg = gm20b_pmu_initmsg,
+   .reset = gp102_pmu_reset,
 };
 
 #if IS_ENABLED(CONFIG_ARCH_TEGRA_210_SOC)
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/priv.h 
b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/priv.h
index bcaade758ff7..21abf31f4442 100644
--- a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/priv.h
+++ b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/priv.h
@@ -41,6 +41,7 @@ int gt215_pmu_send(struct nvkm_pmu *, u32[2], u32, u32, u32, 
u32);
 
 bool gf100_pmu_enabled(struct nvkm_pmu *);
 void gf100_pmu_reset(struct nvkm_pmu *);
+void gp102_pmu_reset(struct nvkm_pmu *pmu);
 
 void gk110_pmu_pgob(struct nvkm_pmu *, bool);
 
-- 
2.35.1



Re: [PATCH 0/4] Drop wbinvd_on_all_cpus usage

2022-03-22 Thread Tvrtko Ursulin



On 22/03/2022 11:37, Thomas Hellström wrote:

On Tue, 2022-03-22 at 11:20 +, Tvrtko Ursulin wrote:


On 22/03/2022 10:26, Thomas Hellström wrote:

On Tue, 2022-03-22 at 10:13 +, Tvrtko Ursulin wrote:


On 21/03/2022 15:15, Thomas Hellström wrote:

On Mon, 2022-03-21 at 14:43 +, Tvrtko Ursulin wrote:


On 21/03/2022 13:40, Thomas Hellström wrote:

Hi,

On Mon, 2022-03-21 at 13:12 +, Tvrtko Ursulin wrote:


On 21/03/2022 12:33, Thomas Hellström wrote:

On Mon, 2022-03-21 at 12:22 +, Tvrtko Ursulin
wrote:


On 21/03/2022 11:03, Thomas Hellström wrote:

Hi, Tvrtko.

On 3/21/22 11:27, Tvrtko Ursulin wrote:


On 19/03/2022 19:42, Michael Cheng wrote:

To align with the discussion in [1][2], this
patch
series
drops
all
usage of
wbvind_on_all_cpus within i915 by either
replacing
the
call
with certain
drm clflush helpers, or reverting to a previous
logic.


AFAIU, complaint from [1] was that it is wrong to
provide
non
x86
implementations under the wbinvd_on_all_cpus
name.
Instead an
arch
agnostic helper which achieves the same effect
could
be
created.
Does
Arm have such concept?


I also understand Linus' email like we shouldn't
leak
incoherent
IO
to
other architectures, meaning any remaining
wbinvd()s
should
be
X86
only.


The last part is completely obvious since it is a x86
instruction
name.


Yeah, I meant the function implementing wbinvd()
semantics.



But I think we can't pick a solution until we know
how
the
concept
maps
to Arm and that will also include seeing how the
drm_clflush_sg for
Arm
would look. Is there a range based solution, or just
a
big
hammer
there.
If the latter, then it is no good to churn all these
reverts
but
instead
an arch agnostic wrapper, with a generic name, would
be
the
way to
go.


But my impression was that ARM would not need the
range-
based
interface
either, because ARM is only for discrete and with
discrete
we're
always
coherent.


Not sure what you mean here - what about flushing system
memory
objects
on discrete? Those still need flushing on paths like
suspend
which this
series touches. Am I missing something?


System bos on discrete should always have

I915_BO_CACHE_COHERENT_FOR_READ |
I915_BO_CACHE_COHERENT_FOR_WRITE

either by the gpu being fully cache coherent (or us mapping
system
write-combined). Hence no need for cache clflushes or
wbinvd()
for
incoherent IO.


Hmm so you are talking about the shmem ttm backend. It ends
up
depending on the result of i915_ttm_cache_level, yes? It
cannot
end
up with I915_CACHE_NONE from that function?


If the object is allocated with allowable placement in either
LMEM
or
SYSTEM, and it ends in system, it gets allocated with
I915_CACHE_NONE,
but then the shmem ttm backend isn't used but TTM's wc pools,
and
the
object should *always* be mapped wc. Even in system.


I am not familiar with neither TTM backend or wc pools so maybe a
missed
question - if obj->cache_level can be set to none, and
obj->cache_coherency to zero, then during object lifetime helpers
which
consult those fields (like i915_gem_cpu_write_needs_clflush,
__start_cpu_write, etc) are giving out incorrect answers? That
is, it
is
irrelevant that they would say flushes are required, since in
actuality
those objects can never ever and from anywhere be mapped other
than
WC
so flushes aren't actually required?


If we map other than WC somewhere in these situations, that should
be a
bug needing a fix. It might be that some of these helpers that you
mention might still flag that a clflush is needed, and in that case
that's an oversight that also needs fixing.




I also found in i915_drm.h:

    * As caching mode when specifying
`I915_MMAP_OFFSET_FIXED`,
WC or WB will
    * be used, depending on the object placement on
creation. WB
will be used
    * when the object can only exist in system memory,
WC
otherwise.

If what you say is true, that on discrete it is _always_ WC,
then
that needs updating as well.


If an object is allocated as system only, then it is mapped WB,
and
we're relying on the gpu being cache coherent to avoid
clflushes.
Same
is actually currently true if the object happens to be accessed
by
the
cpu while evicted. Might need an update for that.


Hmm okay, I think I actually misunderstood something here. I
think
the
reason for difference bbtween smem+lmem object which happens to
be in
smem and smem only object is eluding me.



That's adhering to Linus'

"And I sincerely hope to the gods that no cache-incoherent
i915
mess
ever makes it out of the x86 world. Incoherent IO was
always a
historical mistake and should never ever happen again, so
we
should
not spread that horrific pattern around."


Sure, but I was not talking about IO - just the CPU side
access
to
CPU side objects.


OK, I was under the impression that clflushes() and wbinvd()s
in
i915
was only ever used to make data visible to non-snooping GPUs.

Do you mean that there are other uses as well? Agreed the wb
cache
flush on on suspend only if gpu is
!I915_

Re: [PATCH v11 5/7] dt-bindings: display: Add Loongson display controller

2022-03-22 Thread Jiaxun Yang




在 2022/3/22 2:33, Sui Jingfeng 写道:


On 2022/3/22 07:20, Rob Herring wrote:

On Tue, Mar 22, 2022 at 12:29:14AM +0800, Sui Jingfeng wrote:

From: suijingfeng 


Needs a commit message.


Signed-off-by: suijingfeng 
Signed-off-by: Sui Jingfeng <15330273...@189.cn>

Same person? Don't need both emails.


Yes,  suijingf...@loongson.cn is my company's email. But it can not be 
used to send patches to dri-devel,


when send patches with this email, the patch will not be shown on 
patch works.


Emails  are either blocked or got  rejected  by loongson's mail 
server.  It can only receive emails


from you and other people, but not dri-devel. so have to use my 
personal email(15330273...@189.cn) to send patches.

In this case you can just use your company's email to sign-off
code and sending with your personal email. It's common practice.

If you don't want to receiving kernel email in your company mailbox,
you can add a entry in .mailmap .

Thanks.
- Jiaxun


Re: [PATCH v11 2/7] MIPS: Loongson64: dts: introduce ls3A4000 evaluation board

2022-03-22 Thread Jiaxun Yang




在 2022/3/21 16:29, Sui Jingfeng 写道:

From: suijingfeng 

The board name is LS3A4000_7A1000_EVB_BOARD_V1.4, it consist of 1.8Ghz
mips64r5 4-core CPU and LS7A1000 bridge chip. It has PCIe GEN2 x8 slot,
therefore can play with discrete graphics card.


Hi Jingfeng,

As we've discussed before if you are going to introduce new dts then you 
*MUST*

include it in makefile and wire it up in code.

A dts file doing nothing lying in the tree is just suspicious.

Thanks.
- Jiaxun



While the integrated display copntroller is equipped with a VGA output
and a DVI output, the VGA is connect to the DVO0 output port of the
display controller, the DVI is connected to DVO1 output port of the
display controller.

 +--++---+
 | DDR4 ||  +---+|
 +--+|  | PCIe Root complex |   LS7A1000 |
|| MC0   |  +--++-+++|
   +--+  HT 3.0  | || || |
   | LS3A4000 |<>| +---++---+  +--++--++-+   +--+
   |   CPU|<>| | GC1000 |  | LSDC |<-->| DDR3 MC |<->| VRAM |
   +--+  | ++  +-+--+-++-+   +--+
|| MC1   +---|--|+
 +--+|  |
 | DDR4 |  +---+   DVO0  |  |  DVO1   +--+
 +--+   VGA <--|ADV7125|<+  +>|TFP410|--> DVI/HDMI
   +---+  +--+

Signed-off-by: suijingfeng 
Signed-off-by: Sui Jingfeng <15330273...@189.cn>
---
  .../boot/dts/loongson/ls3a4000_7a1000_evb.dts | 136 ++
  1 file changed, 136 insertions(+)
  create mode 100644 arch/mips/boot/dts/loongson/ls3a4000_7a1000_evb.dts

diff --git a/arch/mips/boot/dts/loongson/ls3a4000_7a1000_evb.dts 
b/arch/mips/boot/dts/loongson/ls3a4000_7a1000_evb.dts
new file mode 100644
index ..f467eddccdac
--- /dev/null
+++ b/arch/mips/boot/dts/loongson/ls3a4000_7a1000_evb.dts
@@ -0,0 +1,136 @@
+// SPDX-License-Identifier: GPL-2.0
+
+/dts-v1/;
+
+#include "loongson64g-package.dtsi"
+#include "ls7a-pch.dtsi"
+
+/ {
+   compatible = "loongson,loongson64g-4core-ls7a";
+   model = "LS3A4000_7A1000_EVB_BOARD_V1.4";
+
+   vga-encoder {
+   compatible = "adi,adv7123", "dumb-vga-dac";
+
+   ports {
+   #address-cells = <1>;
+   #size-cells = <0>;
+
+   port@0 {
+   reg = <0>;
+   adv7123_in: endpoint {
+   remote-endpoint = <&dc_out_rgb0>;
+   };
+   };
+
+   port@1 {
+   reg = <1>;
+   adv7123_out: endpoint {
+   remote-endpoint = <&vga_connector_in>;
+   };
+   };
+   };
+   };
+
+   vga-connector {
+   compatible = "vga-connector";
+   label = "vga";
+
+   ddc-i2c-bus = <&i2c6>;
+
+   port {
+   vga_connector_in: endpoint {
+   remote-endpoint = <&adv7123_out>;
+   };
+   };
+   };
+
+   tfp410: dvi-encoder {
+   compatible = "ti,tfp410";
+
+   ports {
+   #address-cells = <1>;
+   #size-cells = <0>;
+
+   port@0 {
+   reg = <0>;
+   tfp410_in: endpoint {
+   pclk-sample = <1>;
+   bus-width = <24>;
+   remote-endpoint = <&dc_out_rgb1>;
+   };
+   };
+
+   port@1 {
+   reg = <1>;
+   tfp410_out: endpoint {
+   remote-endpoint = <&dvi_connector_in>;
+   };
+   };
+   };
+   };
+
+   dvi-connector {
+   compatible = "dvi-connector";
+   label = "dvi";
+   digital;
+
+   ddc-i2c-bus = <&i2c7>;
+
+   port {
+   dvi_connector_in: endpoint {
+   remote-endpoint = <&tfp410_out>;
+   };
+   };
+   };
+};
+
+&package0 {
+   htvec: interrupt-controller@efdfb80 {
+   compatible = "loongson,htvec-1.0";
+   reg = <0xefd 0xfb80 0x40>;
+   interrupt-controller;
+   #interrupt-cells = <1>;
+
+   interrupt-parent = <&liointc>;
+   interrupts

[PATCH 1/7] drm/gma500: Use managed drmm_mode_config_init()

2022-03-22 Thread Patrik Jakobsson
Signed-off-by: Patrik Jakobsson 
---
 drivers/gpu/drm/gma500/framebuffer.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/gma500/framebuffer.c 
b/drivers/gpu/drm/gma500/framebuffer.c
index 45df9de22007..2b99c996fdc2 100644
--- a/drivers/gpu/drm/gma500/framebuffer.c
+++ b/drivers/gpu/drm/gma500/framebuffer.c
@@ -514,7 +514,8 @@ void psb_modeset_init(struct drm_device *dev)
struct pci_dev *pdev = to_pci_dev(dev->dev);
int i;
 
-   drm_mode_config_init(dev);
+   if (drmm_mode_config_init(dev))
+   return;
 
dev->mode_config.min_width = 0;
dev->mode_config.min_height = 0;
@@ -546,6 +547,5 @@ void psb_modeset_cleanup(struct drm_device *dev)
if (dev_priv->modeset) {
drm_kms_helper_poll_fini(dev);
psb_fbdev_fini(dev);
-   drm_mode_config_cleanup(dev);
}
 }
-- 
2.35.1



[PATCH 3/7] drm/gma500: Make use of the drm connector iterator

2022-03-22 Thread Patrik Jakobsson
This makes sure we're using proper locking when iterating the list of
connectors.

Signed-off-by: Patrik Jakobsson 
---
 drivers/gpu/drm/gma500/cdv_device.c| 10 ++--
 drivers/gpu/drm/gma500/cdv_intel_display.c |  9 +--
 drivers/gpu/drm/gma500/framebuffer.c   |  6 +++--
 drivers/gpu/drm/gma500/gma_display.c   | 16 -
 drivers/gpu/drm/gma500/oaktrail_crtc.c | 17 -
 drivers/gpu/drm/gma500/oaktrail_lvds.c | 15 ++--
 drivers/gpu/drm/gma500/psb_device.c| 28 +++---
 drivers/gpu/drm/gma500/psb_drv.c   | 10 
 drivers/gpu/drm/gma500/psb_intel_display.c | 15 
 9 files changed, 84 insertions(+), 42 deletions(-)

diff --git a/drivers/gpu/drm/gma500/cdv_device.c 
b/drivers/gpu/drm/gma500/cdv_device.c
index f854f58bcbb3..dd32b484dd82 100644
--- a/drivers/gpu/drm/gma500/cdv_device.c
+++ b/drivers/gpu/drm/gma500/cdv_device.c
@@ -262,6 +262,7 @@ static int cdv_save_display_registers(struct drm_device 
*dev)
struct drm_psb_private *dev_priv = to_drm_psb_private(dev);
struct pci_dev *pdev = to_pci_dev(dev->dev);
struct psb_save_area *regs = &dev_priv->regs;
+   struct drm_connector_list_iter conn_iter;
struct drm_connector *connector;
 
dev_dbg(dev->dev, "Saving GPU registers.\n");
@@ -298,8 +299,10 @@ static int cdv_save_display_registers(struct drm_device 
*dev)
regs->cdv.saveIER = REG_READ(PSB_INT_ENABLE_R);
regs->cdv.saveIMR = REG_READ(PSB_INT_MASK_R);
 
-   list_for_each_entry(connector, &dev->mode_config.connector_list, head)
+   drm_connector_list_iter_begin(dev, &conn_iter);
+   drm_for_each_connector_iter(connector, &conn_iter)
connector->funcs->dpms(connector, DRM_MODE_DPMS_OFF);
+   drm_connector_list_iter_end(&conn_iter);
 
return 0;
 }
@@ -317,6 +320,7 @@ static int cdv_restore_display_registers(struct drm_device 
*dev)
struct drm_psb_private *dev_priv = to_drm_psb_private(dev);
struct pci_dev *pdev = to_pci_dev(dev->dev);
struct psb_save_area *regs = &dev_priv->regs;
+   struct drm_connector_list_iter conn_iter;
struct drm_connector *connector;
u32 temp;
 
@@ -373,8 +377,10 @@ static int cdv_restore_display_registers(struct drm_device 
*dev)
 
drm_mode_config_reset(dev);
 
-   list_for_each_entry(connector, &dev->mode_config.connector_list, head)
+   drm_connector_list_iter_begin(dev, &conn_iter);
+   drm_for_each_connector_iter(connector, &conn_iter)
connector->funcs->dpms(connector, DRM_MODE_DPMS_ON);
+   drm_connector_list_iter_end(&conn_iter);
 
/* Resume the modeset for every activated CRTC */
drm_helper_resume_force_mode(dev);
diff --git a/drivers/gpu/drm/gma500/cdv_intel_display.c 
b/drivers/gpu/drm/gma500/cdv_intel_display.c
index 94ebc48a4349..0c3ddcdc29dc 100644
--- a/drivers/gpu/drm/gma500/cdv_intel_display.c
+++ b/drivers/gpu/drm/gma500/cdv_intel_display.c
@@ -584,13 +584,14 @@ static int cdv_intel_crtc_mode_set(struct drm_crtc *crtc,
bool ok;
bool is_lvds = false;
bool is_dp = false;
-   struct drm_mode_config *mode_config = &dev->mode_config;
+   struct drm_connector_list_iter conn_iter;
struct drm_connector *connector;
const struct gma_limit_t *limit;
u32 ddi_select = 0;
bool is_edp = false;
 
-   list_for_each_entry(connector, &mode_config->connector_list, head) {
+   drm_connector_list_iter_begin(dev, &conn_iter);
+   drm_for_each_connector_iter(connector, &conn_iter) {
struct gma_encoder *gma_encoder =
gma_attached_encoder(connector);
 
@@ -613,10 +614,14 @@ static int cdv_intel_crtc_mode_set(struct drm_crtc *crtc,
is_edp = true;
break;
default:
+   drm_connector_list_iter_end(&conn_iter);
DRM_ERROR("invalid output type.\n");
return 0;
}
+
+   break;
}
+   drm_connector_list_iter_end(&conn_iter);
 
if (dev_priv->dplla_96mhz)
/* low-end sku, 96/100 mhz */
diff --git a/drivers/gpu/drm/gma500/framebuffer.c 
b/drivers/gpu/drm/gma500/framebuffer.c
index 2b99c996fdc2..0ac6ea5fd3a1 100644
--- a/drivers/gpu/drm/gma500/framebuffer.c
+++ b/drivers/gpu/drm/gma500/framebuffer.c
@@ -451,6 +451,7 @@ static const struct drm_mode_config_funcs psb_mode_funcs = {
 static void psb_setup_outputs(struct drm_device *dev)
 {
struct drm_psb_private *dev_priv = to_drm_psb_private(dev);
+   struct drm_connector_list_iter conn_iter;
struct drm_connector *connector;
 
drm_mode_create_scaling_mode_property(dev);
@@ -461,8 +462,8 @@ static void psb_setup_outputs(struct drm_device *dev)
"backlight", 0, 100);
   

[PATCH 4/7] drm/gma500: gma500 don't register non-hotpluggable connectors

2022-03-22 Thread Patrik Jakobsson
According to docs we should only register connectors that are
hotpluggable. No connectors in gma500 are hotpluggable.

Signed-off-by: Patrik Jakobsson 
---
 drivers/gpu/drm/gma500/cdv_intel_crt.c  | 3 ---
 drivers/gpu/drm/gma500/cdv_intel_dp.c   | 3 ---
 drivers/gpu/drm/gma500/cdv_intel_hdmi.c | 2 --
 drivers/gpu/drm/gma500/cdv_intel_lvds.c | 2 --
 drivers/gpu/drm/gma500/oaktrail_hdmi.c  | 1 -
 drivers/gpu/drm/gma500/oaktrail_lvds.c  | 1 -
 drivers/gpu/drm/gma500/psb_intel_lvds.c | 2 --
 drivers/gpu/drm/gma500/psb_intel_sdvo.c | 2 --
 8 files changed, 16 deletions(-)

diff --git a/drivers/gpu/drm/gma500/cdv_intel_crt.c 
b/drivers/gpu/drm/gma500/cdv_intel_crt.c
index 4a9bb4994a26..1ae0fbbda0eb 100644
--- a/drivers/gpu/drm/gma500/cdv_intel_crt.c
+++ b/drivers/gpu/drm/gma500/cdv_intel_crt.c
@@ -194,7 +194,6 @@ static void cdv_intel_crt_destroy(struct drm_connector 
*connector)
struct gma_encoder *gma_encoder = gma_attached_encoder(connector);
 
psb_intel_i2c_destroy(gma_encoder->ddc_bus);
-   drm_connector_unregister(connector);
drm_connector_cleanup(connector);
kfree(connector);
 }
@@ -281,8 +280,6 @@ void cdv_intel_crt_init(struct drm_device *dev,
drm_connector_helper_add(connector,
&cdv_intel_crt_connector_helper_funcs);
 
-   drm_connector_register(connector);
-
return;
 failed_ddc:
drm_encoder_cleanup(&gma_encoder->base);
diff --git a/drivers/gpu/drm/gma500/cdv_intel_dp.c 
b/drivers/gpu/drm/gma500/cdv_intel_dp.c
index f562e91337c7..3fba9d4e785d 100644
--- a/drivers/gpu/drm/gma500/cdv_intel_dp.c
+++ b/drivers/gpu/drm/gma500/cdv_intel_dp.c
@@ -1866,7 +1866,6 @@ cdv_intel_dp_destroy(struct drm_connector *connector)
intel_dp->panel_fixed_mode = NULL;
}
i2c_del_adapter(&intel_dp->adapter);
-   drm_connector_unregister(connector);
drm_connector_cleanup(connector);
kfree(connector);
 }
@@ -1990,8 +1989,6 @@ cdv_intel_dp_init(struct drm_device *dev, struct 
psb_intel_mode_device *mode_dev
connector->interlace_allowed = false;
connector->doublescan_allowed = false;
 
-   drm_connector_register(connector);
-
/* Set up the DDC bus. */
switch (output_reg) {
case DP_B:
diff --git a/drivers/gpu/drm/gma500/cdv_intel_hdmi.c 
b/drivers/gpu/drm/gma500/cdv_intel_hdmi.c
index e525689f84f0..e0d4c49b3c92 100644
--- a/drivers/gpu/drm/gma500/cdv_intel_hdmi.c
+++ b/drivers/gpu/drm/gma500/cdv_intel_hdmi.c
@@ -245,7 +245,6 @@ static void cdv_hdmi_destroy(struct drm_connector 
*connector)
struct gma_encoder *gma_encoder = gma_attached_encoder(connector);
 
psb_intel_i2c_destroy(gma_encoder->i2c_bus);
-   drm_connector_unregister(connector);
drm_connector_cleanup(connector);
kfree(connector);
 }
@@ -352,7 +351,6 @@ void cdv_hdmi_init(struct drm_device *dev,
 
hdmi_priv->hdmi_i2c_adapter = &(gma_encoder->i2c_bus->adapter);
hdmi_priv->dev = dev;
-   drm_connector_register(connector);
return;
 
 failed_ddc:
diff --git a/drivers/gpu/drm/gma500/cdv_intel_lvds.c 
b/drivers/gpu/drm/gma500/cdv_intel_lvds.c
index 9e1cdb11023c..851a3cc4653e 100644
--- a/drivers/gpu/drm/gma500/cdv_intel_lvds.c
+++ b/drivers/gpu/drm/gma500/cdv_intel_lvds.c
@@ -329,7 +329,6 @@ static void cdv_intel_lvds_destroy(struct drm_connector 
*connector)
struct gma_encoder *gma_encoder = gma_attached_encoder(connector);
 
psb_intel_i2c_destroy(gma_encoder->i2c_bus);
-   drm_connector_unregister(connector);
drm_connector_cleanup(connector);
kfree(connector);
 }
@@ -647,7 +646,6 @@ void cdv_intel_lvds_init(struct drm_device *dev,
 
 out:
mutex_unlock(&dev->mode_config.mutex);
-   drm_connector_register(connector);
return;
 
 failed_find:
diff --git a/drivers/gpu/drm/gma500/oaktrail_hdmi.c 
b/drivers/gpu/drm/gma500/oaktrail_hdmi.c
index 6eef60a5ac27..b5946a1cdcd5 100644
--- a/drivers/gpu/drm/gma500/oaktrail_hdmi.c
+++ b/drivers/gpu/drm/gma500/oaktrail_hdmi.c
@@ -654,7 +654,6 @@ void oaktrail_hdmi_init(struct drm_device *dev,
connector->display_info.subpixel_order = SubPixelHorizontalRGB;
connector->interlace_allowed = false;
connector->doublescan_allowed = false;
-   drm_connector_register(connector);
dev_info(dev->dev, "HDMI initialised.\n");
 
return;
diff --git a/drivers/gpu/drm/gma500/oaktrail_lvds.c 
b/drivers/gpu/drm/gma500/oaktrail_lvds.c
index 04852dbc7fb3..aed5de8f8245 100644
--- a/drivers/gpu/drm/gma500/oaktrail_lvds.c
+++ b/drivers/gpu/drm/gma500/oaktrail_lvds.c
@@ -401,7 +401,6 @@ void oaktrail_lvds_init(struct drm_device *dev,
 out:
mutex_unlock(&dev->mode_config.mutex);
 
-   drm_connector_register(connector);
return;
 
 failed_find:
diff --git a/drivers/gpu/drm/gma500/psb_intel_lvds.c 
b/drivers/gpu/drm/gma500/psb_intel_lvds.c
index ac97e0d3c7dd..ec8f0b504ccc 100644
--- a/dri

[PATCH 2/7] drm/gma500: Uninstall interrupts on driver removal

2022-03-22 Thread Patrik Jakobsson
Reloading the driver revealed that the interrupt handler never got
uninstalled.

Signed-off-by: Patrik Jakobsson 
---
 drivers/gpu/drm/gma500/psb_drv.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/gpu/drm/gma500/psb_drv.c b/drivers/gpu/drm/gma500/psb_drv.c
index 82d51e9821ad..b231fddb8817 100644
--- a/drivers/gpu/drm/gma500/psb_drv.c
+++ b/drivers/gpu/drm/gma500/psb_drv.c
@@ -173,6 +173,8 @@ static void psb_driver_unload(struct drm_device *dev)
gma_backlight_exit(dev);
psb_modeset_cleanup(dev);
 
+   gma_irq_uninstall(dev);
+
if (dev_priv->ops->chip_teardown)
dev_priv->ops->chip_teardown(dev);
 
-- 
2.35.1



[PATCH 5/7] drm/gma500: Free the correct connector allocation

2022-03-22 Thread Patrik Jakobsson
The allocation is made for the gma_connector object so we must use the
same address when free()ing the object.

Signed-off-by: Patrik Jakobsson 
---
 drivers/gpu/drm/gma500/cdv_intel_crt.c  | 3 ++-
 drivers/gpu/drm/gma500/cdv_intel_dp.c   | 3 ++-
 drivers/gpu/drm/gma500/cdv_intel_hdmi.c | 3 ++-
 drivers/gpu/drm/gma500/cdv_intel_lvds.c | 3 ++-
 drivers/gpu/drm/gma500/psb_intel_lvds.c | 3 ++-
 drivers/gpu/drm/gma500/psb_intel_sdvo.c | 4 +++-
 6 files changed, 13 insertions(+), 6 deletions(-)

diff --git a/drivers/gpu/drm/gma500/cdv_intel_crt.c 
b/drivers/gpu/drm/gma500/cdv_intel_crt.c
index 1ae0fbbda0eb..6bcd18c63c31 100644
--- a/drivers/gpu/drm/gma500/cdv_intel_crt.c
+++ b/drivers/gpu/drm/gma500/cdv_intel_crt.c
@@ -191,11 +191,12 @@ static enum drm_connector_status cdv_intel_crt_detect(
 
 static void cdv_intel_crt_destroy(struct drm_connector *connector)
 {
+   struct gma_connector *gma_connector = to_gma_connector(connector);
struct gma_encoder *gma_encoder = gma_attached_encoder(connector);
 
psb_intel_i2c_destroy(gma_encoder->ddc_bus);
drm_connector_cleanup(connector);
-   kfree(connector);
+   kfree(gma_connector);
 }
 
 static int cdv_intel_crt_get_modes(struct drm_connector *connector)
diff --git a/drivers/gpu/drm/gma500/cdv_intel_dp.c 
b/drivers/gpu/drm/gma500/cdv_intel_dp.c
index 3fba9d4e785d..72b1b2fc3c27 100644
--- a/drivers/gpu/drm/gma500/cdv_intel_dp.c
+++ b/drivers/gpu/drm/gma500/cdv_intel_dp.c
@@ -1857,6 +1857,7 @@ cdv_intel_dp_set_property(struct drm_connector *connector,
 static void
 cdv_intel_dp_destroy(struct drm_connector *connector)
 {
+   struct gma_connector *gma_connector = to_gma_connector(connector);
struct gma_encoder *gma_encoder = gma_attached_encoder(connector);
struct cdv_intel_dp *intel_dp = gma_encoder->dev_priv;
 
@@ -1867,7 +1868,7 @@ cdv_intel_dp_destroy(struct drm_connector *connector)
}
i2c_del_adapter(&intel_dp->adapter);
drm_connector_cleanup(connector);
-   kfree(connector);
+   kfree(gma_connector);
 }
 
 static const struct drm_encoder_helper_funcs cdv_intel_dp_helper_funcs = {
diff --git a/drivers/gpu/drm/gma500/cdv_intel_hdmi.c 
b/drivers/gpu/drm/gma500/cdv_intel_hdmi.c
index e0d4c49b3c92..8987e555e113 100644
--- a/drivers/gpu/drm/gma500/cdv_intel_hdmi.c
+++ b/drivers/gpu/drm/gma500/cdv_intel_hdmi.c
@@ -242,11 +242,12 @@ static enum drm_mode_status cdv_hdmi_mode_valid(struct 
drm_connector *connector,
 
 static void cdv_hdmi_destroy(struct drm_connector *connector)
 {
+   struct gma_connector *gma_connector = to_gma_connector(connector);
struct gma_encoder *gma_encoder = gma_attached_encoder(connector);
 
psb_intel_i2c_destroy(gma_encoder->i2c_bus);
drm_connector_cleanup(connector);
-   kfree(connector);
+   kfree(gma_connector);
 }
 
 static const struct drm_encoder_helper_funcs cdv_hdmi_helper_funcs = {
diff --git a/drivers/gpu/drm/gma500/cdv_intel_lvds.c 
b/drivers/gpu/drm/gma500/cdv_intel_lvds.c
index 851a3cc4653e..98d9f5483a7c 100644
--- a/drivers/gpu/drm/gma500/cdv_intel_lvds.c
+++ b/drivers/gpu/drm/gma500/cdv_intel_lvds.c
@@ -326,11 +326,12 @@ static int cdv_intel_lvds_get_modes(struct drm_connector 
*connector)
  */
 static void cdv_intel_lvds_destroy(struct drm_connector *connector)
 {
+   struct gma_connector *gma_connector = to_gma_connector(connector);
struct gma_encoder *gma_encoder = gma_attached_encoder(connector);
 
psb_intel_i2c_destroy(gma_encoder->i2c_bus);
drm_connector_cleanup(connector);
-   kfree(connector);
+   kfree(gma_connector);
 }
 
 static int cdv_intel_lvds_set_property(struct drm_connector *connector,
diff --git a/drivers/gpu/drm/gma500/psb_intel_lvds.c 
b/drivers/gpu/drm/gma500/psb_intel_lvds.c
index ec8f0b504ccc..cad00380b386 100644
--- a/drivers/gpu/drm/gma500/psb_intel_lvds.c
+++ b/drivers/gpu/drm/gma500/psb_intel_lvds.c
@@ -521,12 +521,13 @@ static int psb_intel_lvds_get_modes(struct drm_connector 
*connector)
  */
 void psb_intel_lvds_destroy(struct drm_connector *connector)
 {
+   struct gma_connector *gma_connector = to_gma_connector(connector);
struct gma_encoder *gma_encoder = gma_attached_encoder(connector);
struct psb_intel_lvds_priv *lvds_priv = gma_encoder->dev_priv;
 
psb_intel_i2c_destroy(lvds_priv->ddc_bus);
drm_connector_cleanup(connector);
-   kfree(connector);
+   kfree(gma_connector);
 }
 
 int psb_intel_lvds_set_property(struct drm_connector *connector,
diff --git a/drivers/gpu/drm/gma500/psb_intel_sdvo.c 
b/drivers/gpu/drm/gma500/psb_intel_sdvo.c
index 5b72a759a182..a85aace25548 100644
--- a/drivers/gpu/drm/gma500/psb_intel_sdvo.c
+++ b/drivers/gpu/drm/gma500/psb_intel_sdvo.c
@@ -1542,8 +1542,10 @@ static int psb_intel_sdvo_get_modes(struct drm_connector 
*connector)
 
 static void psb_intel_sdvo_destroy(struct drm_connector *connector)
 {
+   struct gma_connector *gma_connector = to_gma_connector(connec

[PATCH 6/7] drm/gma500: Declare a few functions static

2022-03-22 Thread Patrik Jakobsson
These functions are not used outside of their file scope so can be
declared as static.

Signed-off-by: Patrik Jakobsson 
---
 drivers/gpu/drm/gma500/gma_display.c | 15 +++
 drivers/gpu/drm/gma500/psb_drv.c |  2 +-
 2 files changed, 8 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/gma500/gma_display.c 
b/drivers/gpu/drm/gma500/gma_display.c
index e8157464d9eb..369bc1f751cb 100644
--- a/drivers/gpu/drm/gma500/gma_display.c
+++ b/drivers/gpu/drm/gma500/gma_display.c
@@ -176,9 +176,9 @@ void gma_crtc_load_lut(struct drm_crtc *crtc)
}
 }
 
-int gma_crtc_gamma_set(struct drm_crtc *crtc, u16 *red, u16 *green, u16 *blue,
-  u32 size,
-  struct drm_modeset_acquire_ctx *ctx)
+static int gma_crtc_gamma_set(struct drm_crtc *crtc, u16 *red, u16 *green,
+ u16 *blue, u32 size,
+ struct drm_modeset_acquire_ctx *ctx)
 {
gma_crtc_load_lut(crtc);
 
@@ -323,10 +323,9 @@ void gma_crtc_dpms(struct drm_crtc *crtc, int mode)
REG_WRITE(DSPARB, 0x3F3E);
 }
 
-int gma_crtc_cursor_set(struct drm_crtc *crtc,
-   struct drm_file *file_priv,
-   uint32_t handle,
-   uint32_t width, uint32_t height)
+static int gma_crtc_cursor_set(struct drm_crtc *crtc,
+  struct drm_file *file_priv, uint32_t handle,
+  uint32_t width, uint32_t height)
 {
struct drm_device *dev = crtc->dev;
struct drm_psb_private *dev_priv = to_drm_psb_private(dev);
@@ -439,7 +438,7 @@ int gma_crtc_cursor_set(struct drm_crtc *crtc,
return ret;
 }
 
-int gma_crtc_cursor_move(struct drm_crtc *crtc, int x, int y)
+static int gma_crtc_cursor_move(struct drm_crtc *crtc, int x, int y)
 {
struct drm_device *dev = crtc->dev;
struct gma_crtc *gma_crtc = to_gma_crtc(crtc);
diff --git a/drivers/gpu/drm/gma500/psb_drv.c b/drivers/gpu/drm/gma500/psb_drv.c
index bb0e3288e35b..2aff54d505e2 100644
--- a/drivers/gpu/drm/gma500/psb_drv.c
+++ b/drivers/gpu/drm/gma500/psb_drv.c
@@ -100,7 +100,7 @@ static const struct drm_ioctl_desc psb_ioctls[] = {
  *
  * Soft reset the graphics engine and then reload the necessary registers.
  */
-void psb_spank(struct drm_psb_private *dev_priv)
+static void psb_spank(struct drm_psb_private *dev_priv)
 {
PSB_WSGX32(_PSB_CS_RESET_BIF_RESET | _PSB_CS_RESET_DPM_RESET |
_PSB_CS_RESET_TA_RESET | _PSB_CS_RESET_USE_RESET |
-- 
2.35.1



[PATCH 7/7] drm/gma500: Add crtc prefix to vblank functions

2022-03-22 Thread Patrik Jakobsson
These functions operate on a crtc and should be prefixed properly.

Suggested-by: Thomas Zimmermann 
Signed-off-by: Patrik Jakobsson 
---
 drivers/gpu/drm/gma500/gma_display.c | 6 +++---
 drivers/gpu/drm/gma500/psb_irq.c | 6 +++---
 drivers/gpu/drm/gma500/psb_irq.h | 6 +++---
 3 files changed, 9 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/gma500/gma_display.c 
b/drivers/gpu/drm/gma500/gma_display.c
index 369bc1f751cb..34ec3fca09ba 100644
--- a/drivers/gpu/drm/gma500/gma_display.c
+++ b/drivers/gpu/drm/gma500/gma_display.c
@@ -575,9 +575,9 @@ const struct drm_crtc_funcs gma_crtc_funcs = {
.set_config = gma_crtc_set_config,
.destroy = gma_crtc_destroy,
.page_flip = gma_crtc_page_flip,
-   .enable_vblank = gma_enable_vblank,
-   .disable_vblank = gma_disable_vblank,
-   .get_vblank_counter = gma_get_vblank_counter,
+   .enable_vblank = gma_crtc_enable_vblank,
+   .disable_vblank = gma_crtc_disable_vblank,
+   .get_vblank_counter = gma_crtc_get_vblank_counter,
 };
 
 /*
diff --git a/drivers/gpu/drm/gma500/psb_irq.c b/drivers/gpu/drm/gma500/psb_irq.c
index 2e8ded532930..e6e6d61bbeab 100644
--- a/drivers/gpu/drm/gma500/psb_irq.c
+++ b/drivers/gpu/drm/gma500/psb_irq.c
@@ -371,7 +371,7 @@ void gma_irq_uninstall(struct drm_device *dev)
free_irq(pdev->irq, dev);
 }
 
-int gma_enable_vblank(struct drm_crtc *crtc)
+int gma_crtc_enable_vblank(struct drm_crtc *crtc)
 {
struct drm_device *dev = crtc->dev;
unsigned int pipe = crtc->index;
@@ -404,7 +404,7 @@ int gma_enable_vblank(struct drm_crtc *crtc)
return 0;
 }
 
-void gma_disable_vblank(struct drm_crtc *crtc)
+void gma_crtc_disable_vblank(struct drm_crtc *crtc)
 {
struct drm_device *dev = crtc->dev;
unsigned int pipe = crtc->index;
@@ -428,7 +428,7 @@ void gma_disable_vblank(struct drm_crtc *crtc)
 /* Called from drm generic code, passed a 'crtc', which
  * we use as a pipe index
  */
-u32 gma_get_vblank_counter(struct drm_crtc *crtc)
+u32 gma_crtc_get_vblank_counter(struct drm_crtc *crtc)
 {
struct drm_device *dev = crtc->dev;
unsigned int pipe = crtc->index;
diff --git a/drivers/gpu/drm/gma500/psb_irq.h b/drivers/gpu/drm/gma500/psb_irq.h
index c22878914f5b..b51e395194ff 100644
--- a/drivers/gpu/drm/gma500/psb_irq.h
+++ b/drivers/gpu/drm/gma500/psb_irq.h
@@ -20,9 +20,9 @@ void gma_irq_postinstall(struct drm_device *dev);
 int  gma_irq_install(struct drm_device *dev, unsigned int irq);
 void gma_irq_uninstall(struct drm_device *dev);
 
-int  gma_enable_vblank(struct drm_crtc *crtc);
-void gma_disable_vblank(struct drm_crtc *crtc);
-u32  gma_get_vblank_counter(struct drm_crtc *crtc);
+int  gma_crtc_enable_vblank(struct drm_crtc *crtc);
+void gma_crtc_disable_vblank(struct drm_crtc *crtc);
+u32  gma_crtc_get_vblank_counter(struct drm_crtc *crtc);
 void gma_enable_pipestat(struct drm_psb_private *dev_priv, int pipe, u32 mask);
 void gma_disable_pipestat(struct drm_psb_private *dev_priv, int pipe, u32 
mask);
 
-- 
2.35.1



Re: [PATCH v11 2/7] MIPS: Loongson64: dts: introduce ls3A4000 evaluation board

2022-03-22 Thread Sui Jingfeng



On 2022/3/22 21:05, Jiaxun Yang wrote:



在 2022/3/21 16:29, Sui Jingfeng 写道:

From: suijingfeng 

The board name is LS3A4000_7A1000_EVB_BOARD_V1.4, it consist of 1.8Ghz
mips64r5 4-core CPU and LS7A1000 bridge chip. It has PCIe GEN2 x8 slot,
therefore can play with discrete graphics card.


Hi Jingfeng,

As we've discussed before if you are going to introduce new dts then 
you *MUST*

include it in makefile and wire it up in code.

A dts file doing nothing lying in the tree is just suspicious.

Thanks.
- Jiaxun


Hi, Jiaxun,

I know what you means, but it is the kernel side developer's job.
I am just a naive graphic driver developer,I can not care so much.
Below is my private patch which can be used to built specific dts
into the linux kernel, therefore make the verification easier.


diff --git a/arch/mips/boot/dts/loongson/Makefile 
b/arch/mips/boot/dts/loongson/Makefile
index 5c6433e441ee..99b66675c4a1 100644
--- a/arch/mips/boot/dts/loongson/Makefile
+++ b/arch/mips/boot/dts/loongson/Makefile
@@ -1,9 +1,22 @@
 # SPDX-License-Identifier: GPL-2.0
-dtb-$(CONFIG_MACH_LOONGSON64)  += loongson64_2core_2k1000.dtb
-dtb-$(CONFIG_MACH_LOONGSON64)  += loongson64c_4core_ls7a.dtb
-dtb-$(CONFIG_MACH_LOONGSON64)  += loongson64c_4core_rs780e.dtb
-dtb-$(CONFIG_MACH_LOONGSON64)  += loongson64c_8core_rs780e.dtb
-dtb-$(CONFIG_MACH_LOONGSON64)  += loongson64g_4core_ls7a.dtb
-dtb-$(CONFIG_MACH_LOONGSON64)  += loongson64v_4core_virtio.dtb
+
+dtb-$(CONFIG_LOONGSON64_LS2K1000_PAI_V1_5) += ls2k1000_pai.dtb
+dtb-$(CONFIG_LOONGSON64_LS2K1000_EVB_V1_2) += ls2k1000_evb.dtb
+dtb-$(CONFIG_LOONGSON64_LS2K1000_GENERIC)  += loongson64_2core_2k1000.dtb
+
+dtb-$(CONFIG_LOONGSON64_LS3A3000_LS7A1000) += loongson64c_4core_ls7a.dtb
+dtb-$(CONFIG_LOONGSON64_LS3A3000_RS780E)   += loongson64c_4core_rs780e.dtb
+dtb-$(CONFIG_LOONGSON64_LS3B3000_RS780E)   += loongson64c_8core_rs780e.dtb
+
+dtb-$(CONFIG_LOONGSON64_LS3A4000_7A1000_LEMOTE_A1901) += lemote_a1901.dtb
+dtb-$(CONFIG_LOONGSON64_LS3A4000_7A1000_EVB_V1_4) += ls3a4000_7a1000_evb.dtb
+dtb-$(CONFIG_LOONGSON64_LS3A4000_7A1000_GENERIC)  += loongson64g_4core_ls7a.dtb
+
+dtb-$(CONFIG_LOONGSON64_BOARD_DEFAULT) += loongson64_2core_2k1000.dtb
+dtb-$(CONFIG_LOONGSON64_BOARD_DEFAULT) += loongson64c_4core_ls7a.dtb
+dtb-$(CONFIG_LOONGSON64_BOARD_DEFAULT) += loongson64c_4core_rs780e.dtb
+dtb-$(CONFIG_LOONGSON64_BOARD_DEFAULT) += loongson64c_8core_rs780e.dtb
+dtb-$(CONFIG_LOONGSON64_BOARD_DEFAULT) += loongson64g_4core_ls7a.dtb
+dtb-$(CONFIG_LOONGSON64_BOARD_DEFAULT) += loongson64v_4core_virtio.dtb
 
 obj-$(CONFIG_BUILTIN_DTB)	+= $(addsuffix .o, $(dtb-y))

diff --git a/arch/mips/include/asm/mach-loongson64/builtin_dtbs.h 
b/arch/mips/include/asm/mach-loongson64/builtin_dtbs.h
index 8be710557bdb..605bfa47b4b9 100644
--- a/arch/mips/include/asm/mach-loongson64/builtin_dtbs.h
+++ b/arch/mips/include/asm/mach-loongson64/builtin_dtbs.h
@@ -8,10 +8,10 @@
 #ifndef __ASM_MACH_LOONGSON64_BUILTIN_DTBS_H_
 #define __ASM_MACH_LOONGSON64_BUILTIN_DTBS_H_
 
-extern u32 __dtb_loongson64_2core_2k1000_begin[];

-extern u32 __dtb_loongson64c_4core_ls7a_begin[];
-extern u32 __dtb_loongson64c_4core_rs780e_begin[];
-extern u32 __dtb_loongson64c_8core_rs780e_begin[];
-extern u32 __dtb_loongson64g_4core_ls7a_begin[];
-extern u32 __dtb_loongson64v_4core_virtio_begin[];
+extern u32 __weak __dtb_loongson64_2core_2k1000_begin[];
+extern u32 __weak __dtb_loongson64c_4core_ls7a_begin[];
+extern u32 __weak __dtb_loongson64c_4core_rs780e_begin[];
+extern u32 __weak __dtb_loongson64c_8core_rs780e_begin[];
+extern u32 __weak __dtb_loongson64g_4core_ls7a_begin[];
+extern u32 __weak __dtb_loongson64v_4core_virtio_begin[];
 #endif
diff --git a/arch/mips/loongson64/Kconfig b/arch/mips/loongson64/Kconfig
index 517f1f8e81fb..7030185ed0c6 100644
--- a/arch/mips/loongson64/Kconfig
+++ b/arch/mips/loongson64/Kconfig
@@ -12,4 +12,43 @@ config RS780_HPET
  Note: This driver is doing some dangerous hack. Please only enable
  it on RS780E systems.
 
+choice

+   prompt "Board type"
+   depends on MACH_LOONGSON64
+   depends on BUILTIN_DTB
+   help
+pick a device tree that matches the target board.
+
+config LOONGSON64_BOARD_DEFAULT
+   bool "Default"
+
+config LOONGSON64_LS3A4000_7A1000_LEMOTE_A1901
+   bool "LEMOTE A1901 LS3A4000 board"
+
+config LOONGSON64_LS3A4000_7A1000_EVB_V1_4
+   bool "LS3A4000 LS7A1000 evaluation board v1.4"
+
+config LOONGSON64_LS3A4000_7A1000_GENERIC
+   bool "LS3A4000 LS7A1000 generic board"
+
+config LOONGSON64_LS3A3000_LS7A1000
+   bool "LS3A3000 LS7A1000 generic board"
+
+config LOONGSON64_LS3A3000_RS780E
+   bool "LS3A3000 RS780E generic board"
+
+config LOONGSON64_LS3B3000_RS780E
+   bool "LS3B3000 RS780E generic board"
+
+config LOONGSON64_LS2K1000_PAI_V1_5
+   bool "LS2K1000 PAI board V1.5"
+
+config LOONGSON64_LS2K1000_EVB_V1_2
+   bool "LS2K1000 evaluation board V1.2"
+
+config LOONGSON64_LS2K1000_GENERIC
+   boo

Re: [PATCH v2 4/7] drm/i915/guc: use the memcpy_from_wc call from the drm

2022-03-22 Thread Balasubramani Vivekanandan
On 21.03.2022 14:14, Lucas De Marchi wrote:
> On Thu, Mar 03, 2022 at 11:30:10PM +0530, Balasubramani Vivekanandan wrote:
> > memcpy_from_wc functions in i915_memcpy.c will be removed and replaced
> > by the implementation in drm_cache.c.
> > Updated to use the functions provided by drm_cache.c.
> > 
> > v2: Check if the log object allocated from local memory or system memory
> >and according setup the iosys_map (Lucas)
> > 
> > Cc: Lucas De Marchi 
> > 
> > Signed-off-by: Balasubramani Vivekanandan 
> > 
> > ---
> > drivers/gpu/drm/i915/gt/uc/intel_guc_log.c | 15 ---
> > 1 file changed, 12 insertions(+), 3 deletions(-)
> > 
> > diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c 
> > b/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c
> > index a24dc6441872..b9db765627ea 100644
> > --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c
> > +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c
> > @@ -3,6 +3,7 @@
> >  * Copyright © 2014-2019 Intel Corporation
> >  */
> > 
> > +#include 
> > #include 
> > #include 
> > 
> > @@ -206,6 +207,7 @@ static void guc_read_update_log_buffer(struct 
> > intel_guc_log *log)
> > enum guc_log_buffer_type type;
> > void *src_data, *dst_data;
> > bool new_overflow;
> > +   struct iosys_map src_map;
> > 
> > mutex_lock(&log->relay.lock);
> > 
> > @@ -282,14 +284,21 @@ static void guc_read_update_log_buffer(struct 
> > intel_guc_log *log)
> > }
> > 
> > /* Just copy the newly written data */
> > +   if (i915_gem_object_is_lmem(log->vma->obj))
> > +   iosys_map_set_vaddr_iomem(&src_map, (void __iomem 
> > *)src_data);
> > +   else
> > +   iosys_map_set_vaddr(&src_map, src_data);
> 
> It would be better to keep this outside of the loop. So inside the loop
> we can use only iosys_map_incr(&src_map, buffer_size). However you'd
> also have to handle the read_offset. The iosys_map_ API has both a
> src_offset and dst_offset due to situations like that. Maybe this is
> missing in the new drm_memcpy_* function you're adding?
> 
> This function was not correct wrt to IO memory access with the other
> 2 places in this function doing plain memcpy(). Since we are starting to
> use iosys_map here, we probably should handle this commit as "migrate to
> iosys_map", and convert those. In your current final state
> we have 3 variables aliasing the same memory location. IMO it will be
> error prone to keep it like that
yes, it is a good suggestion to completely change the reading of the GuC
log for the relay to use the iosys_map interfaces.
Though it was planned eventually, doing it now with this series will
avoid mixing of memcpy() and drm_memcpy_*(which needs iosys_map
parameters) functions.
I will do the changes.
> 
> +Michal, some questions:
> 
> - I'm not very familiar with the relayfs API. Is the `dst_data += PAGE_SIZE;`
> really correct?
> 
> - Could you double check this patch and ack if ok?
> 
> Heads up that since the log buffer is potentially in lmem, we will need
> to convert this function to take that into account. All those accesses
> to log_buf_state need to use the proper kernel abstraction for system vs
> I/O memory.
> 
> thanks
> Lucas De Marchi
> 
> > +
> > if (read_offset > write_offset) {
> > -   i915_memcpy_from_wc(dst_data, src_data, write_offset);
> > +   drm_memcpy_from_wc_vaddr(dst_data, &src_map,
> > +write_offset);
> > bytes_to_copy = buffer_size - read_offset;
> > } else {
> > bytes_to_copy = write_offset - read_offset;
> > }
> > -   i915_memcpy_from_wc(dst_data + read_offset,
> > -   src_data + read_offset, bytes_to_copy);
> > +   iosys_map_incr(&src_map, read_offset);
> > +   drm_memcpy_from_wc_vaddr(dst_data + read_offset, &src_map,
> > +bytes_to_copy);
> > 
> > src_data += buffer_size;
> > dst_data += buffer_size;
> > -- 
> > 2.25.1
> > 


Re: [PATCH v11 5/7] dt-bindings: display: Add Loongson display controller

2022-03-22 Thread Sui Jingfeng



On 2022/3/22 21:08, Jiaxun Yang wrote:



在 2022/3/22 2:33, Sui Jingfeng 写道:


On 2022/3/22 07:20, Rob Herring wrote:

On Tue, Mar 22, 2022 at 12:29:14AM +0800, Sui Jingfeng wrote:

From: suijingfeng 


Needs a commit message.


Signed-off-by: suijingfeng 
Signed-off-by: Sui Jingfeng <15330273...@189.cn>

Same person? Don't need both emails.


Yes,  suijingf...@loongson.cn is my company's email. But it can not 
be used to send patches to dri-devel,


when send patches with this email, the patch will not be shown on 
patch works.


Emails  are either blocked or got  rejected  by loongson's mail 
server.  It can only receive emails


from you and other people, but not dri-devel. so have to use my 
personal email(15330273...@189.cn) to send patches.

In this case you can just use your company's email to sign-off
code and sending with your personal email. It's common practice.

If you don't want to receiving kernel email in your company mailbox,
you can add a entry in .mailmap .

|I'm using `git send-email -7 --cover-letter --annotate -v11` command to 
send patches, it will automatically sign off patches with the my private 
emails. |



Thanks.
- Jiaxun


Re: [PATCH] drm: drm_bufs: Error out if 'dev->agp' is a null pointer

2022-03-22 Thread Daniel Vetter
On Mon, Mar 21, 2022 at 09:02:47PM +0800, Zheyu Ma wrote:
> On Thu, Mar 17, 2022 at 6:49 PM Daniel Vetter  wrote:
> >
> > On Fri, Mar 11, 2022 at 07:23:02AM +, Zheyu Ma wrote:
> > > The user program can control the 'drm_buf_desc::flags' via ioctl system
> > > call and enter the function drm_legacy_addbufs_agp(). If the driver
> > > doesn't initialize the agp resources, the driver will cause a null
> > > pointer dereference.
> > >
> > > The following log reveals it:
> > > general protection fault, probably for non-canonical address
> > > 0xdc0f:  [#1] PREEMPT SMP KASAN PTI
> > > KASAN: null-ptr-deref in range [0x0078-0x007f]
> > > Call Trace:
> > >  
> > >  drm_ioctl_kernel+0x342/0x450 drivers/gpu/drm/drm_ioctl.c:785
> > >  drm_ioctl+0x592/0x940 drivers/gpu/drm/drm_ioctl.c:885
> > >  vfs_ioctl fs/ioctl.c:51 [inline]
> > >  __do_sys_ioctl fs/ioctl.c:874 [inline]
> > >  __se_sys_ioctl+0xaa/0xf0 fs/ioctl.c:860
> > >  do_syscall_x64 arch/x86/entry/common.c:50 [inline]
> > >  do_syscall_64+0x43/0x90 arch/x86/entry/common.c:80
> > >  entry_SYSCALL_64_after_hwframe+0x44/0xae
> > >
> > > Fix this bug by adding a check.
> > >
> > > Signed-off-by: Zheyu Ma 
> >
> > You can only hit this if you enabled a DRIVER_LEGACY drm driver, which
> > opens you up to tons of other CVEs and issues. What's your .config?
> 
> Yes, I enable the DRM_LEGACY option in the config.
> I think you mean this is not a normal configuration file? Do you have
> a recommended configuration option for when I want to test the GPU
> driver?

Yeah DRM_LEGACY gives you all kinds of horrible and known-broken
interfaces. Don't enable that :-)

You have a bunch of other drivers enable which require DRM_LEGACY, so
those will disable too. Anything else I think would be an upstream bug and
we'd need to adjust Kconfig (or fix the code).

Cheers, Daniel
> 
> Actually, I use the following configs related to GPU:
> 
> CONFIG_AGP=y
> CONFIG_AGP_AMD64=y
> CONFIG_AGP_INTEL=y
> CONFIG_AGP_SIS=y
> CONFIG_AGP_VIA=y
> CONFIG_INTEL_GTT=y
> CONFIG_VGA_ARB=y
> CONFIG_VGA_ARB_MAX_GPUS=16
> CONFIG_DRM=y
> CONFIG_DRM_MIPI_DSI=y
> CONFIG_DRM_KMS_HELPER=y
> CONFIG_DRM_DEBUG_MODESET_LOCK=y
> CONFIG_DRM_FBDEV_EMULATION=y
> CONFIG_DRM_FBDEV_OVERALLOC=100
> CONFIG_DRM_TTM=y
> CONFIG_DRM_VRAM_HELPER=y
> CONFIG_DRM_TTM_HELPER=y
> CONFIG_DRM_GEM_SHMEM_HELPER=y
> CONFIG_DRM_SCHED=y
> CONFIG_DRM_RADEON=y
> CONFIG_DRM_AMDGPU=y
> CONFIG_DRM_AMD_DC=y
> CONFIG_DRM_AMD_DC_DCN=y
> CONFIG_DRM_I915=y
> CONFIG_DRM_I915_FORCE_PROBE=""
> CONFIG_DRM_I915_CAPTURE_ERROR=y
> CONFIG_DRM_I915_COMPRESS_ERROR=y
> CONFIG_DRM_I915_USERPTR=y
> CONFIG_DRM_I915_REQUEST_TIMEOUT=2
> CONFIG_DRM_I915_FENCE_TIMEOUT=1
> CONFIG_DRM_I915_USERFAULT_AUTOSUSPEND=250
> CONFIG_DRM_I915_HEARTBEAT_INTERVAL=2500
> CONFIG_DRM_I915_PREEMPT_TIMEOUT=640
> CONFIG_DRM_I915_MAX_REQUEST_BUSYWAIT=8000
> CONFIG_DRM_I915_STOP_TIMEOUT=100
> CONFIG_DRM_I915_TIMESLICE_DURATION=1
> CONFIG_DRM_VMWGFX=y
> CONFIG_DRM_GMA500=y
> CONFIG_DRM_UDL=y
> CONFIG_DRM_AST=y
> CONFIG_DRM_MGAG200=y
> CONFIG_DRM_QXL=y
> CONFIG_DRM_VIRTIO_GPU=y
> CONFIG_DRM_PANEL=y
> CONFIG_DRM_BRIDGE=y
> CONFIG_DRM_PANEL_BRIDGE=y
> CONFIG_DRM_BOCHS=y
> CONFIG_DRM_CIRRUS_QEMU=y
> CONFIG_DRM_GM12U320=y
> CONFIG_DRM_VBOXVIDEO=y
> CONFIG_DRM_GUD=y
> CONFIG_DRM_HYPERV=y
> CONFIG_DRM_LEGACY=y
> CONFIG_DRM_TDFX=y
> CONFIG_DRM_R128=y
> CONFIG_DRM_MGA=y
> CONFIG_DRM_SIS=y
> CONFIG_DRM_VIA=y
> CONFIG_DRM_SAVAGE=y
> CONFIG_DRM_PANEL_ORIENTATION_QUIRKS=y
> 
> Thanks,
> Zheyu Ma

-- 
Daniel Vetter
Software Engineer, Intel Corporation
http://blog.ffwll.ch


[PATCH 1/2] dt-bindings: lcdif: Add compatible for i.MX8MP

2022-03-22 Thread Marek Vasut
Add compatible string for i.MX8MP LCDIF variant. This is called LCDIFv3
and is completely different from the LCDIFv3 found in i.MX23 in that it
has a completely scrambled register layout compared to all previous LCDIF
variants. The new LCDIFv3 also supports 36bit address space. However,
except for the complete bit reshuffling, this is still LCDIF and it still
works like one.

Signed-off-by: Marek Vasut 
Cc: Alexander Stein 
Cc: Laurent Pinchart 
Cc: Lucas Stach 
Cc: Peng Fan 
Cc: Rob Herring 
Cc: Robby Cai 
Cc: Sam Ravnborg 
Cc: Stefan Agner 
Cc: devicet...@vger.kernel.org
---
 Documentation/devicetree/bindings/display/fsl,lcdif.yaml | 1 +
 1 file changed, 1 insertion(+)

diff --git a/Documentation/devicetree/bindings/display/fsl,lcdif.yaml 
b/Documentation/devicetree/bindings/display/fsl,lcdif.yaml
index 900a56cae80e6..876015a44a1e6 100644
--- a/Documentation/devicetree/bindings/display/fsl,lcdif.yaml
+++ b/Documentation/devicetree/bindings/display/fsl,lcdif.yaml
@@ -20,6 +20,7 @@ properties:
   - fsl,imx23-lcdif
   - fsl,imx28-lcdif
   - fsl,imx6sx-lcdif
+  - fsl,imx8mp-lcdif
   - items:
   - enum:
   - fsl,imx6sl-lcdif
-- 
2.35.1



[PATCH 2/2] drm: lcdif: Add support for i.MX8MP LCDIF variant

2022-03-22 Thread Marek Vasut
ot;);
+
+   lcdif->bridge = bridge;
+
+   /*
+* Get hold of the connector. This is a bit of a hack, until the bridge
+* API gives us bus flags and formats.
+*/
+   drm_connector_list_iter_begin(drm, &iter);
+   lcdif->connector = drm_connector_list_iter_next(&iter);
+   drm_connector_list_iter_end(&iter);
+
+   return 0;
+}
+
+static irqreturn_t lcdif_irq_handler(int irq, void *data)
+{
+   struct drm_device *drm = data;
+   struct lcdif_drm_private *lcdif = drm->dev_private;
+   u32 reg;
+
+   reg = readl(lcdif->base + LCDC_V8_INT_STATUS_D0);
+
+   if (reg & INT_STATUS_D0_VS_BLANK)
+   drm_crtc_handle_vblank(&lcdif->crtc);
+
+   writel(INT_STATUS_D0_VS_BLANK, lcdif->base + LCDC_V8_INT_STATUS_D0);
+
+   return IRQ_HANDLED;
+}
+
+static int lcdif_load(struct drm_device *drm)
+{
+   struct platform_device *pdev = to_platform_device(drm->dev);
+   struct lcdif_drm_private *lcdif;
+   struct resource *res;
+   int ret;
+
+   lcdif = devm_kzalloc(&pdev->dev, sizeof(*lcdif), GFP_KERNEL);
+   if (!lcdif)
+   return -ENOMEM;
+
+   lcdif->drm = drm;
+   drm->dev_private = lcdif;
+
+   res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+   lcdif->base = devm_ioremap_resource(drm->dev, res);
+   if (IS_ERR(lcdif->base))
+   return PTR_ERR(lcdif->base);
+
+   lcdif->clk = devm_clk_get(drm->dev, NULL);
+   if (IS_ERR(lcdif->clk))
+   return PTR_ERR(lcdif->clk);
+
+   lcdif->clk_axi = devm_clk_get_optional(drm->dev, "axi");
+   if (IS_ERR(lcdif->clk_axi))
+   return PTR_ERR(lcdif->clk_axi);
+
+   lcdif->clk_disp_axi = devm_clk_get_optional(drm->dev, "disp_axi");
+   if (IS_ERR(lcdif->clk_disp_axi))
+   return PTR_ERR(lcdif->clk_disp_axi);
+
+   platform_set_drvdata(pdev, drm);
+
+   ret = dma_set_mask_and_coherent(drm->dev, DMA_BIT_MASK(36));
+   if (ret)
+   return ret;
+
+   /* Modeset init */
+   drm_mode_config_init(drm);
+
+   ret = lcdif_kms_init(lcdif);
+   if (ret < 0) {
+   dev_err(drm->dev, "Failed to initialize KMS pipeline\n");
+   return ret;
+   }
+
+   ret = drm_vblank_init(drm, drm->mode_config.num_crtc);
+   if (ret < 0) {
+   dev_err(drm->dev, "Failed to initialise vblank\n");
+   return ret;
+   }
+
+   /* Start with vertical blanking interrupt reporting disabled. */
+   drm_crtc_vblank_off(&lcdif->crtc);
+
+   ret = lcdif_attach_bridge(lcdif);
+   if (ret)
+   return dev_err_probe(drm->dev, ret, "Cannot connect bridge\n");
+
+   drm->mode_config.min_width  = LCDIF_MIN_XRES;
+   drm->mode_config.min_height = LCDIF_MIN_YRES;
+   drm->mode_config.max_width  = LCDIF_MAX_XRES;
+   drm->mode_config.max_height = LCDIF_MAX_YRES;
+   drm->mode_config.funcs  = &lcdif_mode_config_funcs;
+   drm->mode_config.helper_private = &lcdif_mode_config_helpers;
+
+   drm_mode_config_reset(drm);
+
+   ret = platform_get_irq(pdev, 0);
+   if (ret < 0)
+   return ret;
+   lcdif->irq = ret;
+
+   ret = request_irq(lcdif->irq, lcdif_irq_handler, 0,
+ drm->driver->name, drm);
+   if (ret < 0) {
+   dev_err(drm->dev, "Failed to install IRQ handler\n");
+   return ret;
+   }
+
+   drm_kms_helper_poll_init(drm);
+
+   drm_helper_hpd_irq_event(drm);
+
+   pm_runtime_enable(drm->dev);
+
+   return 0;
+}
+
+static void lcdif_unload(struct drm_device *drm)
+{
+   struct lcdif_drm_private *lcdif = drm->dev_private;
+
+   pm_runtime_get_sync(drm->dev);
+
+   drm_crtc_vblank_off(&lcdif->crtc);
+
+   drm_kms_helper_poll_fini(drm);
+   drm_mode_config_cleanup(drm);
+
+   pm_runtime_put_sync(drm->dev);
+   pm_runtime_disable(drm->dev);
+
+   free_irq(lcdif->irq, drm->dev);
+
+   drm->dev_private = NULL;
+}
+
+DEFINE_DRM_GEM_CMA_FOPS(fops);
+
+static const struct drm_driver lcdif_driver = {
+   .driver_features= DRIVER_GEM | DRIVER_MODESET | DRIVER_ATOMIC,
+   DRM_GEM_CMA_DRIVER_OPS,
+   .fops   = &fops,
+   .name   = "lcdif",
+   .desc   = "LCDIF Controller DRM",
+   .date   = "20220322",
+   .major  = 1,
+   .minor  = 0,
+};
+
+static const struct of_device_id lcdif_dt_ids[] = {
+   { .compatible = "fsl,imx8mp-lcdif" },
+   { /* sentinel */ }
+};
+MODULE_DEVICE_TABLE(of, lcdif_dt_ids);
+
+static int lcdif_probe(struct platform_device *pde

Re: [Intel-gfx] [PATCH 1/4] i915/gem: drop wbinvd_on_all_cpus usage

2022-03-22 Thread Daniel Vetter
On Mon, Mar 21, 2022 at 10:42:03AM -0700, Michael Cheng wrote:
> 
> On 2022-03-21 10:28 a.m., Tvrtko Ursulin wrote:
> > 
> > On 21/03/2022 16:31, Michael Cheng wrote:
> > > On 2022-03-21 3:30 a.m., Tvrtko Ursulin wrote:
> > > 
> > > > 
> > > > On 19/03/2022 19:42, Michael Cheng wrote:
> > > > > Previous concern with using drm_clflush_sg was that we don't
> > > > > know what the
> > > > > sg_table is pointing to, thus the usage of wbinvd_on_all_cpus to flush
> > > > > everything at once to avoid paranoia.
> > > > 
> > > > And now we know, or we know it is not a concern?
> > > > 
> > > > > To make i915 more architecture-neutral and be less paranoid,
> > > > > lets attempt to
> > > > 
> > > > "Lets attempt" as we don't know if this will work and/or what
> > > > can/will break?
> > > 
> > > Yes, but it seems like there's no regression with IGT .
> > > 
> > > If there's a big hit in performance, or if this solution gets
> > > accepted and the bug reports come flying in, we can explore other
> > > solutions. But speaking to Dan Vetter, ideal solution would be to
> > > avoid any calls directly to wbinvd, and use drm helpers in place.
> > > 
> > > +Daniel for any extra input.
> > > 
> > > > > use drm_clflush_sg to flush the pages for when the GPU wants to read
> > > > > from main memory.
> > > > > 
> > > > > Signed-off-by: Michael Cheng 
> > > > > ---
> > > > >   drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c | 9 ++---
> > > > >   1 file changed, 2 insertions(+), 7 deletions(-)
> > > > > 
> > > > > diff --git a/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c
> > > > > b/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c
> > > > > index f5062d0c6333..b0a5baaebc43 100644
> > > > > --- a/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c
> > > > > +++ b/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c
> > > > > @@ -8,6 +8,7 @@
> > > > >   #include 
> > > > >   #include 
> > > > >   #include 
> > > > > +#include 
> > > > >     #include 
> > > > >   @@ -250,16 +251,10 @@ static int
> > > > > i915_gem_object_get_pages_dmabuf(struct drm_i915_gem_object
> > > > > *obj)
> > > > >    * DG1 is special here since it still snoops
> > > > > transactions even with
> > > > >    * CACHE_NONE. This is not the case with other
> > > > > HAS_SNOOP platforms. We
> > > > >    * might need to revisit this as we add new discrete platforms.
> > > > > - *
> > > > > - * XXX: Consider doing a vmap flush or something, where possible.
> > > > > - * Currently we just do a heavy handed
> > > > > wbinvd_on_all_cpus() here since
> > > > > - * the underlying sg_table might not even point to
> > > > > struct pages, so we
> > > > > - * can't just call drm_clflush_sg or similar, like we
> > > > > do elsewhere in
> > > > > - * the driver.
> > > > >    */
> > > > >   if (i915_gem_object_can_bypass_llc(obj) ||
> > > > >   (!HAS_LLC(i915) && !IS_DG1(i915)))
> > > > > -    wbinvd_on_all_cpus();
> > > > > +    drm_clflush_sg(pages);
> > > > 
> > > > And as noticed before, drm_clfush_sg still can call
> > > > wbinvd_on_all_cpus so are you just punting the issue somewhere
> > > > else? How will it be solved there?
> > > > 
> > > Instead of calling an x86 asm directly, we are using what's
> > > available to use to make the driver more architecture neutral.
> > > Agreeing with Thomas, this solution falls within the "prefer
> > > range-aware clflush apis", and since some other generation platform
> > > doesn't support clflushopt, it will fall back to using wbinvd.
> > 
> > Right, I was trying to get the information on what will drm_clflush_sg
> > do on Arm. Is it range based or global there, or if the latter exists.
> > 
> I am not too sure about the ARM side. We are currently working that out with
> the ARM folks in a different thread.

It won't do anything useful on arm. The _only_ way to get special memory
on arm is by specifying what you want at allocation time. Anything else is
busted, more or less. Which is why none of these code paths should run on
anything else than x86.

And even on x86 they're at best questionable, but some of these are
mistakes encoded into uapi and we're stuck.

We should still try to use drm_clflush_sg() imo to make the entire ordeal
less horrible, and if that turns out to be problematic, we need to bite
the bullet and fix the uapi architecture instead of trying to
retroshoehorn performance fixes into uapi that just can't do it properly.

In this case here this would mean fixing allocation flags with
GEM_CREATE_EXT and fixing userspace to use that when needed (it should
know already since pretty much all drivers have this issue in some form or
another).

Cheers, Daniel


> > Regards,
> > 
> > Tvrtko

-- 
Daniel Vetter
Software Engineer, Intel Corporation
http://blog.ffwll.ch


[PATCH v2] drm/i915: Add a DP1.2 compatible way to read LTTPR capabilities

2022-03-22 Thread Imre Deak
At least some DELL monitors (P2715Q) with DPCD_REV 1.2 return corrupted
DPCD register values when reading from the 0xF- LTTPR range with an
AUX transaction block size bigger than 1. The DP standard requires 0 to
be returned - as for any other reserved/invalid addresses - but these
monitors return the DPCD_REV register value repeated in each byte of the
read buffer. This will in turn corrupt the values returned by the LTTPRs
between the source and the monitor: LTTPRs must adjust the values they
read from the downstream DPRX, for instance left-shift/init the
downstream DP_PHY_REPEATER_CNT value. Since the value returned by the
monitor's DPRX is non-zero the adjusted values will be corrupt.

Reading the LTTPR registers one-by-one instead of reading all of them
with a single AUX transfer works around the issue.

According to the DP standard's 0xF register description:
"LTTPR-related registers at DPCD Addresses Fh through F02FFh are
valid only for DPCD r1.4 (or higher)." While it's unclear if DPCD r1.4
refers to the DPCD_REV or to the
LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV register (tickets filed
at the VESA site to clarify this haven't been addressed), one
possibility is that it's a restriction due to non-compliant monitors
described above. Disabling the non-transparent LTTPR mode for all such
monitors is not a viable solution: the transparent LTTPR mode has its
own issue causing link training failures and this would affect a lot of
monitors in use with DPCD_REV < 1.4. Instead this patch works around
the problem by reading the LTTPR common and PHY cap registers one-by-one
for any monitor with a DPCD_REV < 1.4.

The standard requires the DPCD capabilites to be read after the LTTPR
common capabilities are read, so re-read the DPCD capabilities after
the LTTPR common and PHY caps were read out.

v2:
- Use for instead of a while loop. (Ville)
- Add to code comment the monitor model with the problem.

Closes: https://gitlab.freedesktop.org/drm/intel/-/issues/4531
Cc: Ville Syrjälä 
Signed-off-by: Imre Deak 
---
 drivers/gpu/drm/dp/drm_dp.c   | 57 ---
 .../drm/i915/display/intel_dp_link_training.c | 30 +++---
 include/drm/dp/drm_dp_helper.h|  2 +
 3 files changed, 58 insertions(+), 31 deletions(-)

diff --git a/drivers/gpu/drm/dp/drm_dp.c b/drivers/gpu/drm/dp/drm_dp.c
index 703972ae14c64..58744f83931af 100644
--- a/drivers/gpu/drm/dp/drm_dp.c
+++ b/drivers/gpu/drm/dp/drm_dp.c
@@ -2390,9 +2390,35 @@ int drm_dp_dsc_sink_supported_input_bpcs(const u8 
dsc_dpcd[DP_DSC_RECEIVER_CAP_S
 }
 EXPORT_SYMBOL(drm_dp_dsc_sink_supported_input_bpcs);
 
+static int drm_dp_read_lttpr_regs(struct drm_dp_aux *aux, const u8 
dpcd[DP_RECEIVER_CAP_SIZE], int address,
+ u8 *buf, int buf_size)
+{
+   /*
+* At least the DELL P2715Q monitor with a DPCD_REV < 0x14 returns
+* corrupted values when reading from the 0xF- range with a block
+* size bigger than 1.
+*/
+   int block_size = dpcd[DP_DPCD_REV] < 0x14 ? 1 : buf_size;
+   int offset;
+   int ret;
+
+   for (offset = 0; offset < buf_size; offset += block_size) {
+   ret = drm_dp_dpcd_read(aux,
+  address + offset,
+  &buf[offset], block_size);
+   if (ret < 0)
+   return ret;
+
+   WARN_ON(ret != block_size);
+   }
+
+   return 0;
+}
+
 /**
  * drm_dp_read_lttpr_common_caps - read the LTTPR common capabilities
  * @aux: DisplayPort AUX channel
+ * @dpcd: DisplayPort configuration data
  * @caps: buffer to return the capability info in
  *
  * Read capabilities common to all LTTPRs.
@@ -2400,25 +2426,19 @@ EXPORT_SYMBOL(drm_dp_dsc_sink_supported_input_bpcs);
  * Returns 0 on success or a negative error code on failure.
  */
 int drm_dp_read_lttpr_common_caps(struct drm_dp_aux *aux,
+ const u8 dpcd[DP_RECEIVER_CAP_SIZE],
  u8 caps[DP_LTTPR_COMMON_CAP_SIZE])
 {
-   int ret;
-
-   ret = drm_dp_dpcd_read(aux,
-  
DP_LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV,
-  caps, DP_LTTPR_COMMON_CAP_SIZE);
-   if (ret < 0)
-   return ret;
-
-   WARN_ON(ret != DP_LTTPR_COMMON_CAP_SIZE);
-
-   return 0;
+   return drm_dp_read_lttpr_regs(aux, dpcd,
+ 
DP_LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV,
+ caps, DP_LTTPR_COMMON_CAP_SIZE);
 }
 EXPORT_SYMBOL(drm_dp_read_lttpr_common_caps);
 
 /**
  * drm_dp_read_lttpr_phy_caps - read the capabilities for a given LTTPR PHY
  * @aux: DisplayPort AUX channel
+ * @dpcd: DisplayPort configuration data
  * @dp_phy: LTTPR PHY to read the capabilities for
  * @caps: buffer to return the capability info in
  *
@@ -2427,20 +2447,13 @@ EXPORT_SYMBOL(

Re: [PATCH 3/7] drm/gma500: Make use of the drm connector iterator

2022-03-22 Thread Daniel Vetter
On Tue, Mar 22, 2022 at 02:17:38PM +0100, Patrik Jakobsson wrote:
> This makes sure we're using proper locking when iterating the list of
> connectors.
> 
> Signed-off-by: Patrik Jakobsson 

Note that this is only needed if your driver deals with hotpluggable
connectors. Since gma500 doesn't, not really a need to convert this over,
but it also doesn't hurt.

If the kerneldoc doesn't explain this, maybe we should add it? Care for a
patch.

Either way on the entire series:

Acked-by: Daniel Vetter 

I'll leave it up to you whether you want to push this one too or not.
-Daniel

> ---
>  drivers/gpu/drm/gma500/cdv_device.c| 10 ++--
>  drivers/gpu/drm/gma500/cdv_intel_display.c |  9 +--
>  drivers/gpu/drm/gma500/framebuffer.c   |  6 +++--
>  drivers/gpu/drm/gma500/gma_display.c   | 16 -
>  drivers/gpu/drm/gma500/oaktrail_crtc.c | 17 -
>  drivers/gpu/drm/gma500/oaktrail_lvds.c | 15 ++--
>  drivers/gpu/drm/gma500/psb_device.c| 28 +++---
>  drivers/gpu/drm/gma500/psb_drv.c   | 10 
>  drivers/gpu/drm/gma500/psb_intel_display.c | 15 
>  9 files changed, 84 insertions(+), 42 deletions(-)
> 
> diff --git a/drivers/gpu/drm/gma500/cdv_device.c 
> b/drivers/gpu/drm/gma500/cdv_device.c
> index f854f58bcbb3..dd32b484dd82 100644
> --- a/drivers/gpu/drm/gma500/cdv_device.c
> +++ b/drivers/gpu/drm/gma500/cdv_device.c
> @@ -262,6 +262,7 @@ static int cdv_save_display_registers(struct drm_device 
> *dev)
>   struct drm_psb_private *dev_priv = to_drm_psb_private(dev);
>   struct pci_dev *pdev = to_pci_dev(dev->dev);
>   struct psb_save_area *regs = &dev_priv->regs;
> + struct drm_connector_list_iter conn_iter;
>   struct drm_connector *connector;
>  
>   dev_dbg(dev->dev, "Saving GPU registers.\n");
> @@ -298,8 +299,10 @@ static int cdv_save_display_registers(struct drm_device 
> *dev)
>   regs->cdv.saveIER = REG_READ(PSB_INT_ENABLE_R);
>   regs->cdv.saveIMR = REG_READ(PSB_INT_MASK_R);
>  
> - list_for_each_entry(connector, &dev->mode_config.connector_list, head)
> + drm_connector_list_iter_begin(dev, &conn_iter);
> + drm_for_each_connector_iter(connector, &conn_iter)
>   connector->funcs->dpms(connector, DRM_MODE_DPMS_OFF);
> + drm_connector_list_iter_end(&conn_iter);
>  
>   return 0;
>  }
> @@ -317,6 +320,7 @@ static int cdv_restore_display_registers(struct 
> drm_device *dev)
>   struct drm_psb_private *dev_priv = to_drm_psb_private(dev);
>   struct pci_dev *pdev = to_pci_dev(dev->dev);
>   struct psb_save_area *regs = &dev_priv->regs;
> + struct drm_connector_list_iter conn_iter;
>   struct drm_connector *connector;
>   u32 temp;
>  
> @@ -373,8 +377,10 @@ static int cdv_restore_display_registers(struct 
> drm_device *dev)
>  
>   drm_mode_config_reset(dev);
>  
> - list_for_each_entry(connector, &dev->mode_config.connector_list, head)
> + drm_connector_list_iter_begin(dev, &conn_iter);
> + drm_for_each_connector_iter(connector, &conn_iter)
>   connector->funcs->dpms(connector, DRM_MODE_DPMS_ON);
> + drm_connector_list_iter_end(&conn_iter);
>  
>   /* Resume the modeset for every activated CRTC */
>   drm_helper_resume_force_mode(dev);
> diff --git a/drivers/gpu/drm/gma500/cdv_intel_display.c 
> b/drivers/gpu/drm/gma500/cdv_intel_display.c
> index 94ebc48a4349..0c3ddcdc29dc 100644
> --- a/drivers/gpu/drm/gma500/cdv_intel_display.c
> +++ b/drivers/gpu/drm/gma500/cdv_intel_display.c
> @@ -584,13 +584,14 @@ static int cdv_intel_crtc_mode_set(struct drm_crtc 
> *crtc,
>   bool ok;
>   bool is_lvds = false;
>   bool is_dp = false;
> - struct drm_mode_config *mode_config = &dev->mode_config;
> + struct drm_connector_list_iter conn_iter;
>   struct drm_connector *connector;
>   const struct gma_limit_t *limit;
>   u32 ddi_select = 0;
>   bool is_edp = false;
>  
> - list_for_each_entry(connector, &mode_config->connector_list, head) {
> + drm_connector_list_iter_begin(dev, &conn_iter);
> + drm_for_each_connector_iter(connector, &conn_iter) {
>   struct gma_encoder *gma_encoder =
>   gma_attached_encoder(connector);
>  
> @@ -613,10 +614,14 @@ static int cdv_intel_crtc_mode_set(struct drm_crtc 
> *crtc,
>   is_edp = true;
>   break;
>   default:
> + drm_connector_list_iter_end(&conn_iter);
>   DRM_ERROR("invalid output type.\n");
>   return 0;
>   }
> +
> + break;
>   }
> + drm_connector_list_iter_end(&conn_iter);
>  
>   if (dev_priv->dplla_96mhz)
>   /* low-end sku, 96/100 mhz */
> diff --git a/drivers/gpu/drm/gma500/framebuffer.c 
> b/drivers/gpu/drm/gma500/framebuffer.c
> index 2b99c996fdc2..0ac6ea5fd3a1 100644
> --- a/drivers/gpu/drm/gma

Re: [PATCH 0/4] Drop wbinvd_on_all_cpus usage

2022-03-22 Thread Thomas Hellström



On 3/22/22 13:53, Tvrtko Ursulin wrote:


On 22/03/2022 11:37, Thomas Hellström wrote:

On Tue, 2022-03-22 at 11:20 +, Tvrtko Ursulin wrote:


On 22/03/2022 10:26, Thomas Hellström wrote:

On Tue, 2022-03-22 at 10:13 +, Tvrtko Ursulin wrote:


On 21/03/2022 15:15, Thomas Hellström wrote:

On Mon, 2022-03-21 at 14:43 +, Tvrtko Ursulin wrote:


On 21/03/2022 13:40, Thomas Hellström wrote:

Hi,

On Mon, 2022-03-21 at 13:12 +, Tvrtko Ursulin wrote:


On 21/03/2022 12:33, Thomas Hellström wrote:

On Mon, 2022-03-21 at 12:22 +, Tvrtko Ursulin
wrote:


On 21/03/2022 11:03, Thomas Hellström wrote:

Hi, Tvrtko.

On 3/21/22 11:27, Tvrtko Ursulin wrote:


On 19/03/2022 19:42, Michael Cheng wrote:

To align with the discussion in [1][2], this
patch
series
drops
all
usage of
wbvind_on_all_cpus within i915 by either
replacing
the
call
with certain
drm clflush helpers, or reverting to a previous
logic.


AFAIU, complaint from [1] was that it is wrong to
provide
non
x86
implementations under the wbinvd_on_all_cpus
name.
Instead an
arch
agnostic helper which achieves the same effect
could
be
created.
Does
Arm have such concept?


I also understand Linus' email like we shouldn't
leak
incoherent
IO
to
other architectures, meaning any remaining
wbinvd()s
should
be
X86
only.


The last part is completely obvious since it is a x86
instruction
name.


Yeah, I meant the function implementing wbinvd()
semantics.



But I think we can't pick a solution until we know
how
the
concept
maps
to Arm and that will also include seeing how the
drm_clflush_sg for
Arm
would look. Is there a range based solution, or just
a
big
hammer
there.
If the latter, then it is no good to churn all these
reverts
but
instead
an arch agnostic wrapper, with a generic name, would
be
the
way to
go.


But my impression was that ARM would not need the
range-
based
interface
either, because ARM is only for discrete and with
discrete
we're
always
coherent.


Not sure what you mean here - what about flushing system
memory
objects
on discrete? Those still need flushing on paths like
suspend
which this
series touches. Am I missing something?


System bos on discrete should always have

I915_BO_CACHE_COHERENT_FOR_READ |
I915_BO_CACHE_COHERENT_FOR_WRITE

either by the gpu being fully cache coherent (or us mapping
system
write-combined). Hence no need for cache clflushes or
wbinvd()
for
incoherent IO.


Hmm so you are talking about the shmem ttm backend. It ends
up
depending on the result of i915_ttm_cache_level, yes? It
cannot
end
up with I915_CACHE_NONE from that function?


If the object is allocated with allowable placement in either
LMEM
or
SYSTEM, and it ends in system, it gets allocated with
I915_CACHE_NONE,
but then the shmem ttm backend isn't used but TTM's wc pools,
and
the
object should *always* be mapped wc. Even in system.


I am not familiar with neither TTM backend or wc pools so maybe a
missed
question - if obj->cache_level can be set to none, and
obj->cache_coherency to zero, then during object lifetime helpers
which
consult those fields (like i915_gem_cpu_write_needs_clflush,
__start_cpu_write, etc) are giving out incorrect answers? That
is, it
is
irrelevant that they would say flushes are required, since in
actuality
those objects can never ever and from anywhere be mapped other
than
WC
so flushes aren't actually required?


If we map other than WC somewhere in these situations, that should
be a
bug needing a fix. It might be that some of these helpers that you
mention might still flag that a clflush is needed, and in that case
that's an oversight that also needs fixing.




I also found in i915_drm.h:

    * As caching mode when specifying
`I915_MMAP_OFFSET_FIXED`,
WC or WB will
    * be used, depending on the object placement on
creation. WB
will be used
    * when the object can only exist in system memory,
WC
otherwise.

If what you say is true, that on discrete it is _always_ WC,
then
that needs updating as well.


If an object is allocated as system only, then it is mapped WB,
and
we're relying on the gpu being cache coherent to avoid
clflushes.
Same
is actually currently true if the object happens to be accessed
by
the
cpu while evicted. Might need an update for that.


Hmm okay, I think I actually misunderstood something here. I
think
the
reason for difference bbtween smem+lmem object which happens to
be in
smem and smem only object is eluding me.



That's adhering to Linus'

"And I sincerely hope to the gods that no cache-incoherent
i915
mess
ever makes it out of the x86 world. Incoherent IO was
always a
historical mistake and should never ever happen again, so
we
should
not spread that horrific pattern around."


Sure, but I was not talking about IO - just the CPU side
access
to
CPU side objects.


OK, I was under the impression that clflushes() and wbinvd()s
in
i915
was only ever used to make data visible to non-snooping GPUs.

Do you mean that there are other uses as well? Agreed the wb
cache

Re: [PATCH 3/7] drm/gma500: Make use of the drm connector iterator

2022-03-22 Thread Patrik Jakobsson
On Tue, Mar 22, 2022 at 3:39 PM Daniel Vetter  wrote:
>
> On Tue, Mar 22, 2022 at 02:17:38PM +0100, Patrik Jakobsson wrote:
> > This makes sure we're using proper locking when iterating the list of
> > connectors.
> >
> > Signed-off-by: Patrik Jakobsson 
>
> Note that this is only needed if your driver deals with hotpluggable
> connectors. Since gma500 doesn't, not really a need to convert this over,
> but it also doesn't hurt.

Good point. Not sure but I think there is a slight possibility that
Cedarview can support DP MST. If someone adds support for DP MST then
this code would make sense. I was never able to exercise the DP code
because I couldn't find an eDP cable that fits the Intel DN2800MT (my
only device with DP). Do you happen to know what the 40-pin connector
is called? Perhaps Intel has some standard for eDP connectors?

>
> If the kerneldoc doesn't explain this, maybe we should add it? Care for a
> patch.

I didn't see it being mentioned anywhere. I'll send a patch.

>
> Either way on the entire series:
>
> Acked-by: Daniel Vetter 

Thanks for having a look.

>
> I'll leave it up to you whether you want to push this one too or not.
> -Daniel
>
> > ---
> >  drivers/gpu/drm/gma500/cdv_device.c| 10 ++--
> >  drivers/gpu/drm/gma500/cdv_intel_display.c |  9 +--
> >  drivers/gpu/drm/gma500/framebuffer.c   |  6 +++--
> >  drivers/gpu/drm/gma500/gma_display.c   | 16 -
> >  drivers/gpu/drm/gma500/oaktrail_crtc.c | 17 -
> >  drivers/gpu/drm/gma500/oaktrail_lvds.c | 15 ++--
> >  drivers/gpu/drm/gma500/psb_device.c| 28 +++---
> >  drivers/gpu/drm/gma500/psb_drv.c   | 10 
> >  drivers/gpu/drm/gma500/psb_intel_display.c | 15 
> >  9 files changed, 84 insertions(+), 42 deletions(-)
> >
> > diff --git a/drivers/gpu/drm/gma500/cdv_device.c 
> > b/drivers/gpu/drm/gma500/cdv_device.c
> > index f854f58bcbb3..dd32b484dd82 100644
> > --- a/drivers/gpu/drm/gma500/cdv_device.c
> > +++ b/drivers/gpu/drm/gma500/cdv_device.c
> > @@ -262,6 +262,7 @@ static int cdv_save_display_registers(struct drm_device 
> > *dev)
> >   struct drm_psb_private *dev_priv = to_drm_psb_private(dev);
> >   struct pci_dev *pdev = to_pci_dev(dev->dev);
> >   struct psb_save_area *regs = &dev_priv->regs;
> > + struct drm_connector_list_iter conn_iter;
> >   struct drm_connector *connector;
> >
> >   dev_dbg(dev->dev, "Saving GPU registers.\n");
> > @@ -298,8 +299,10 @@ static int cdv_save_display_registers(struct 
> > drm_device *dev)
> >   regs->cdv.saveIER = REG_READ(PSB_INT_ENABLE_R);
> >   regs->cdv.saveIMR = REG_READ(PSB_INT_MASK_R);
> >
> > - list_for_each_entry(connector, &dev->mode_config.connector_list, head)
> > + drm_connector_list_iter_begin(dev, &conn_iter);
> > + drm_for_each_connector_iter(connector, &conn_iter)
> >   connector->funcs->dpms(connector, DRM_MODE_DPMS_OFF);
> > + drm_connector_list_iter_end(&conn_iter);
> >
> >   return 0;
> >  }
> > @@ -317,6 +320,7 @@ static int cdv_restore_display_registers(struct 
> > drm_device *dev)
> >   struct drm_psb_private *dev_priv = to_drm_psb_private(dev);
> >   struct pci_dev *pdev = to_pci_dev(dev->dev);
> >   struct psb_save_area *regs = &dev_priv->regs;
> > + struct drm_connector_list_iter conn_iter;
> >   struct drm_connector *connector;
> >   u32 temp;
> >
> > @@ -373,8 +377,10 @@ static int cdv_restore_display_registers(struct 
> > drm_device *dev)
> >
> >   drm_mode_config_reset(dev);
> >
> > - list_for_each_entry(connector, &dev->mode_config.connector_list, head)
> > + drm_connector_list_iter_begin(dev, &conn_iter);
> > + drm_for_each_connector_iter(connector, &conn_iter)
> >   connector->funcs->dpms(connector, DRM_MODE_DPMS_ON);
> > + drm_connector_list_iter_end(&conn_iter);
> >
> >   /* Resume the modeset for every activated CRTC */
> >   drm_helper_resume_force_mode(dev);
> > diff --git a/drivers/gpu/drm/gma500/cdv_intel_display.c 
> > b/drivers/gpu/drm/gma500/cdv_intel_display.c
> > index 94ebc48a4349..0c3ddcdc29dc 100644
> > --- a/drivers/gpu/drm/gma500/cdv_intel_display.c
> > +++ b/drivers/gpu/drm/gma500/cdv_intel_display.c
> > @@ -584,13 +584,14 @@ static int cdv_intel_crtc_mode_set(struct drm_crtc 
> > *crtc,
> >   bool ok;
> >   bool is_lvds = false;
> >   bool is_dp = false;
> > - struct drm_mode_config *mode_config = &dev->mode_config;
> > + struct drm_connector_list_iter conn_iter;
> >   struct drm_connector *connector;
> >   const struct gma_limit_t *limit;
> >   u32 ddi_select = 0;
> >   bool is_edp = false;
> >
> > - list_for_each_entry(connector, &mode_config->connector_list, head) {
> > + drm_connector_list_iter_begin(dev, &conn_iter);
> > + drm_for_each_connector_iter(connector, &conn_iter) {
> >   struct gma_encoder *gma_encoder =
> >   

Re: [PATCH v11 2/7] MIPS: Loongson64: dts: introduce ls3A4000 evaluation board

2022-03-22 Thread Jiaxun Yang




在 2022/3/22 13:38, Sui Jingfeng 写道:


On 2022/3/22 21:05, Jiaxun Yang wrote:



在 2022/3/21 16:29, Sui Jingfeng 写道:

From: suijingfeng 

The board name is LS3A4000_7A1000_EVB_BOARD_V1.4, it consist of 1.8Ghz
mips64r5 4-core CPU and LS7A1000 bridge chip. It has PCIe GEN2 x8 slot,
therefore can play with discrete graphics card.


Hi Jingfeng,

As we've discussed before if you are going to introduce new dts then 
you *MUST*

include it in makefile and wire it up in code.

A dts file doing nothing lying in the tree is just suspicious.

Thanks.
- Jiaxun


Hi, Jiaxun,

I know what you means, but it is the kernel side developer's job.
I am just a naive graphic driver developer,I can not care so much.
Below is my private patch which can be used to built specific dts
into the linux kernel, therefore make the verification easier.

Hi Jingfeng,

In kernel world we take care all the stuff we touched ourself :-)

If you are not confident with them please drop those DTS from the patchset
besides the generic one. I can do the rest for you after getting this 
set merged.


Thanks.
- Jiaxun



Re: [RFC v3 8/8] selftests: Add binder cgroup gpu memory transfer test

2022-03-22 Thread Christian Brauner
On Mon, Mar 14, 2022 at 05:43:40PM -0700, Todd Kjos wrote:
> On Wed, Mar 9, 2022 at 8:53 AM T.J. Mercier  wrote:
> >
> > This test verifies that the cgroup GPU memory charge is transferred
> > correctly when a dmabuf is passed between processes in two different
> > cgroups and the sender specifies BINDER_BUFFER_FLAG_SENDER_NO_NEED in the
> > binder transaction data containing the dmabuf file descriptor.
> >
> > Signed-off-by: T.J. Mercier 
> 
> Reviewed-by: Todd Kjos 
> for the binder driver interactions. Need Christian to take a look at
> the binderfs interactions.

Sorry, just saw this now. I'll take a look tomorrow!


Re: [PATCH v11 5/7] dt-bindings: display: Add Loongson display controller

2022-03-22 Thread Jiaxun Yang




在 2022/3/22 13:54, Sui Jingfeng 写道:


On 2022/3/22 21:08, Jiaxun Yang wrote:



在 2022/3/22 2:33, Sui Jingfeng 写道:


On 2022/3/22 07:20, Rob Herring wrote:

On Tue, Mar 22, 2022 at 12:29:14AM +0800, Sui Jingfeng wrote:

From: suijingfeng 


Needs a commit message.


Signed-off-by: suijingfeng 
Signed-off-by: Sui Jingfeng <15330273...@189.cn>

Same person? Don't need both emails.


Yes,  suijingf...@loongson.cn is my company's email. But it can not 
be used to send patches to dri-devel,


when send patches with this email, the patch will not be shown on 
patch works.


Emails  are either blocked or got  rejected  by loongson's mail 
server.  It can only receive emails


from you and other people, but not dri-devel. so have to use my 
personal email(15330273...@189.cn) to send patches.

In this case you can just use your company's email to sign-off
code and sending with your personal email. It's common practice.

If you don't want to receiving kernel email in your company mailbox,
you can add a entry in .mailmap .

|I'm using `git send-email -7 --cover-letter --annotate -v11` command 
to send patches, it will automatically sign off patches with the my 
private emails. |

The alternative solution is:

git format-patch -7 -v11 --cover-letter
git send-email ./*.patch

Thanks.
- Jiaxun




Thanks.
- Jiaxun




[RFC] drm/i915: Split out intel_vtd_active and run_as_guest to own header

2022-03-22 Thread Tvrtko Ursulin
From: Tvrtko Ursulin 

...

Signed-off-by: Tvrtko Ursulin 
Cc: Jani Nikula 
Cc: Lucas De Marchi 
---
Typed up how I see it - bash away.
---
 drivers/gpu/drm/i915/display/intel_bw.c  |  3 +-
 drivers/gpu/drm/i915/display/intel_display.c |  9 -
 drivers/gpu/drm/i915/display/intel_display.h |  2 ++
 drivers/gpu/drm/i915/display/intel_fbc.c |  3 +-
 drivers/gpu/drm/i915/gem/i915_gem_stolen.c   |  3 +-
 drivers/gpu/drm/i915/gem/i915_gemfs.c|  3 +-
 drivers/gpu/drm/i915/gt/intel_ggtt.c |  5 +--
 drivers/gpu/drm/i915/gt/intel_gtt.c  | 12 +++
 drivers/gpu/drm/i915/gt/intel_gtt.h  |  2 ++
 drivers/gpu/drm/i915/i915_debugfs.c  |  1 +
 drivers/gpu/drm/i915/i915_driver.c   |  3 +-
 drivers/gpu/drm/i915/i915_driver.h   |  4 +++
 drivers/gpu/drm/i915/i915_drv.h  | 37 
 drivers/gpu/drm/i915/i915_gpu_error.c|  3 +-
 drivers/gpu/drm/i915/intel_device_info.c |  4 ++-
 drivers/gpu/drm/i915/intel_pch.c |  3 +-
 drivers/gpu/drm/i915/intel_vtd.h | 27 ++
 17 files changed, 76 insertions(+), 48 deletions(-)
 create mode 100644 drivers/gpu/drm/i915/intel_vtd.h

diff --git a/drivers/gpu/drm/i915/display/intel_bw.c 
b/drivers/gpu/drm/i915/display/intel_bw.c
index ac11ff19e47d..6c9cb4f97218 100644
--- a/drivers/gpu/drm/i915/display/intel_bw.c
+++ b/drivers/gpu/drm/i915/display/intel_bw.c
@@ -13,6 +13,7 @@
 #include "intel_mchbar_regs.h"
 #include "intel_pcode.h"
 #include "intel_pm.h"
+#include "intel_vtd.h"
 
 /* Parameters for Qclk Geyserville (QGV) */
 struct intel_qgv_point {
@@ -649,7 +650,7 @@ static unsigned int intel_bw_data_rate(struct 
drm_i915_private *dev_priv,
for_each_pipe(dev_priv, pipe)
data_rate += bw_state->data_rate[pipe];
 
-   if (DISPLAY_VER(dev_priv) >= 13 && intel_vtd_active(dev_priv))
+   if (DISPLAY_VER(dev_priv) >= 13 && intel_vtd_active(dev_priv->drm.dev))
data_rate = DIV_ROUND_UP(data_rate * 105, 100);
 
return data_rate;
diff --git a/drivers/gpu/drm/i915/display/intel_display.c 
b/drivers/gpu/drm/i915/display/intel_display.c
index dc6e21e4ef0b..e80f3ca3ee4e 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -110,6 +110,7 @@
 #include "intel_quirks.h"
 #include "intel_sprite.h"
 #include "intel_tc.h"
+#include "intel_vtd.h"
 #include "intel_vga.h"
 #include "i9xx_plane.h"
 #include "skl_scaler.h"
@@ -1197,7 +1198,7 @@ static bool needs_async_flip_vtd_wa(const struct 
intel_crtc_state *crtc_state)
 {
struct drm_i915_private *i915 = to_i915(crtc_state->uapi.crtc->dev);
 
-   return crtc_state->uapi.async_flip && intel_vtd_active(i915) &&
+   return crtc_state->uapi.async_flip && intel_vtd_active(i915->drm.dev) &&
(DISPLAY_VER(i915) == 9 || IS_BROADWELL(i915) || 
IS_HASWELL(i915));
 }
 
@@ -10699,3 +10700,9 @@ void intel_display_driver_unregister(struct 
drm_i915_private *i915)
acpi_video_unregister();
intel_opregion_unregister(i915);
 }
+
+bool intel_scanout_needs_vtd_wa(struct drm_i915_private *dev_priv)
+{
+   return DISPLAY_VER(dev_priv) >= 6 &&
+  intel_vtd_active(dev_priv->drm.dev);
+}
diff --git a/drivers/gpu/drm/i915/display/intel_display.h 
b/drivers/gpu/drm/i915/display/intel_display.h
index 8513703086b7..d69587c76e71 100644
--- a/drivers/gpu/drm/i915/display/intel_display.h
+++ b/drivers/gpu/drm/i915/display/intel_display.h
@@ -694,4 +694,6 @@ void assert_transcoder(struct drm_i915_private *dev_priv,
 #define I915_STATE_WARN_ON(x)  \
I915_STATE_WARN((x), "%s", "WARN_ON(" __stringify(x) ")")
 
+bool intel_scanout_needs_vtd_wa(struct drm_i915_private *dev_priv);
+
 #endif
diff --git a/drivers/gpu/drm/i915/display/intel_fbc.c 
b/drivers/gpu/drm/i915/display/intel_fbc.c
index 142280b6ce6d..00a3e30587a5 100644
--- a/drivers/gpu/drm/i915/display/intel_fbc.c
+++ b/drivers/gpu/drm/i915/display/intel_fbc.c
@@ -50,6 +50,7 @@
 #include "intel_display_types.h"
 #include "intel_fbc.h"
 #include "intel_frontbuffer.h"
+#include "intel_vtd.h"
 
 #define for_each_fbc_id(__dev_priv, __fbc_id) \
for ((__fbc_id) = INTEL_FBC_A; (__fbc_id) < I915_MAX_FBCS; 
(__fbc_id)++) \
@@ -1643,7 +1644,7 @@ static int intel_sanitize_fbc_option(struct 
drm_i915_private *i915)
 static bool need_fbc_vtd_wa(struct drm_i915_private *i915)
 {
/* WaFbcTurnOffFbcWhenHyperVisorIsUsed:skl,bxt */
-   if (intel_vtd_active(i915) &&
+   if (intel_vtd_active(i915->drm.dev) &&
(IS_SKYLAKE(i915) || IS_BROXTON(i915))) {
drm_info(&i915->drm,
 "Disabling framebuffer compression (FBC) to prevent 
screen flicker with VT-d enabled\n");
diff --git a/drivers/gpu/drm/i915/gem/i915_gem_stolen.c 
b/drivers/gpu/drm/i915/gem/i915_gem_stolen.c
index 143f61aaa867..9b986b1b0b60 100644
--- a/drivers/gpu/drm/i915/gem/

Re: [Intel-gfx] [PATCH v13 09/13] drm/i915/guc: Check sizing of guc_capture output

2022-03-22 Thread Lucas De Marchi

On Mon, Mar 21, 2022 at 09:45:23AM -0700, Alan Previn wrote:

Add intel_guc_capture_output_min_size_est function to
provide a reasonable minimum size for error-capture
region before allocating the shared buffer.

Signed-off-by: Alan Previn 
Reviewed-by: Matthew Brost 
---
.../gpu/drm/i915/gt/uc/intel_guc_capture.c| 48 +++
.../gpu/drm/i915/gt/uc/intel_guc_capture.h|  1 +
drivers/gpu/drm/i915/gt/uc/intel_guc_log.c|  7 ++-
3 files changed, 55 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_capture.c 
b/drivers/gpu/drm/i915/gt/uc/intel_guc_capture.c
index 63ef407a2fd0..f87fee216430 100644
--- a/drivers/gpu/drm/i915/gt/uc/intel_guc_capture.c
+++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_capture.c
@@ -663,6 +663,54 @@ intel_guc_capture_getnullheader(struct intel_guc *guc,
return 0;
}

+#define GUC_CAPTURE_OVERBUFFER_MULTIPLIER 3


missing blank line here


+int
+intel_guc_capture_output_min_size_est(struct intel_guc *guc)
+{
+   struct intel_gt *gt = guc_to_gt(guc);
+   struct intel_engine_cs *engine;
+   enum intel_engine_id id;
+   int worst_min_size = 0, num_regs = 0;
+   size_t tmp = 0;
+
+   /*
+* If every single engine-instance suffered a failure in quick 
succession but
+* were all unrelated, then a burst of multiple error-capture events 
would dump
+* registers for every one engine instance, one at a time. In this 
case, GuC
+* would even dump the global-registers repeatedly.
+*
+* For each engine instance, there would be 1 x 
guc_state_capture_group_t output
+* followed by 3 x guc_state_capture_t lists. The latter is how the 
register
+* dumps are split across different register types (where the '3' are 
global vs class
+* vs instance). Finally, let's multiply the whole thing by 3x (just so 
we are
+* not limited to just 1 round of data in a worst case full register 
dump log)
+*
+* NOTE: intel_guc_log that allocates the log buffer would round this 
size up to
+* a power of two.
+*/
+
+   for_each_engine(engine, gt, id) {
+   worst_min_size += sizeof(struct 
guc_state_capture_group_header_t) +
+ (3 * sizeof(struct 
guc_state_capture_header_t));
+
+   if (!intel_guc_capture_getlistsize(guc, 0, 
GUC_CAPTURE_LIST_TYPE_GLOBAL, 0, &tmp))
+   num_regs += tmp;
+
+   if (!intel_guc_capture_getlistsize(guc, 0, 
GUC_CAPTURE_LIST_TYPE_ENGINE_CLASS,
+  engine->class, &tmp)) {
+   num_regs += tmp;
+   }
+   if (!intel_guc_capture_getlistsize(guc, 0, 
GUC_CAPTURE_LIST_TYPE_ENGINE_INSTANCE,
+  engine->class, &tmp)) {
+   num_regs += tmp;
+   }
+   }
+
+   worst_min_size += (num_regs * sizeof(struct guc_mmio_reg));
+
+   return (worst_min_size * GUC_CAPTURE_OVERBUFFER_MULTIPLIER);
+}
+
static void
guc_capture_free_ads_cache(struct intel_guc_state_capture *gc)
{
diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_capture.h 
b/drivers/gpu/drm/i915/gt/uc/intel_guc_capture.h
index 8de7704e12eb..540d72079462 100644
--- a/drivers/gpu/drm/i915/gt/uc/intel_guc_capture.h
+++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_capture.h
@@ -11,6 +11,7 @@
struct guc_gt_system_info;
struct intel_guc;

+int intel_guc_capture_output_min_size_est(struct intel_guc *guc);
int intel_guc_capture_getlist(struct intel_guc *guc, u32 owner, u32 type, u32 
classid,
  void **outptr);
int intel_guc_capture_getlistsize(struct intel_guc *guc, u32 owner, u32 type, 
u32 classid,
diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c 
b/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c
index fe4b2d3f305d..ed05b1a04f9c 100644
--- a/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c
+++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_log.c
@@ -7,10 +7,11 @@
#include 

#include "gt/intel_gt.h"
+#include "intel_guc_capture.h"
+#include "intel_guc_log.h"
#include "i915_drv.h"
#include "i915_irq.h"
#include "i915_memcpy.h"
-#include "intel_guc_log.h"


This seems to be an artifact of rebasing or you tried to sort the
includes... when sorting make sure you use LANG=C to avoid locale
differences wrt sorting

The previous placement of intel_guc_log.h was actually the correct one.
I'm squashing this and the previous blank line I mentioned as a fixup.

thanks
Lucas De Marchi



static void guc_log_copy_debuglogs_for_relay(struct intel_guc_log *log);

@@ -466,6 +467,10 @@ int intel_guc_log_create(struct intel_guc_log *log)
 *  | Capture logs  |
 *  +===+ + CAPTURE_SIZE
 */
+   if (intel_guc_capture_output_min_size_est(guc) > CAPTURE_BUFFER_SIZE)
+   DRM_WARN("GuC log buffer for state_capture maybe too small. %d < 
%d\n"

Re: [Freedreno] [PATCH v3 12/13] drm/msm/dsi: Add support for DSC configuration

2022-03-22 Thread Vinod Koul
On 17-02-22, 16:11, Marijn Suijten wrote:
> Hi Vinod,
> 
> Thanks for taking time to go through this review, please find some
> clarifications below.
> 
> On 2022-02-17 16:44:04, Vinod Koul wrote:
> > Hi Marijn,
> > 
> > On 11-12-21, 01:03, Marijn Suijten wrote:
> > 
> > > > +static int dsi_dsc_update_pic_dim(struct msm_display_dsc_config *dsc,
> > > > + int pic_width, int pic_height)
> > > 
> > > This function - adopted from downstream - does not seem to perform a
> > > whole lot, especially without the modulo checks against the slice size.
> > > Perhaps it can be inlined?
> > 
> > Most of the code here is :)
> > 
> > This was split from downstream code to check and update dimension. We
> > can inline this, or should we leave that to compiler. I am not a very
> > big fan of inlining...
> 
> It doesn't seem beneficial to code readability to have this function,
> which is only called just once and also has the same struct members read
> in a `DBG()` directly, abstracted away to a function.  Not really
> concerned about generated code/performance FWIW.
> 
> Also note that the caller isn't checking the `-EINVAL` result...

I have made this void inline.

> > > 
> > > > +{
> > > > +   if (!dsc || !pic_width || !pic_height) {
> > > > +   pr_err("DSI: invalid input: pic_width: %d pic_height: 
> > > > %d\n", pic_width, pic_height);
> > > > +   return -EINVAL;
> > > > +   }
> > > > +
> > > > +   dsc->drm->pic_width = pic_width;
> > > > +   dsc->drm->pic_height = pic_height;
> > > > +
> > > > +   return 0;
> > > > +}
> > > > +
> > > >  static void dsi_timing_setup(struct msm_dsi_host *msm_host, bool 
> > > > is_bonded_dsi)
> > > >  {
> > > > struct drm_display_mode *mode = msm_host->mode;
> > > > @@ -940,7 +954,68 @@ static void dsi_timing_setup(struct msm_dsi_host 
> > > > *msm_host, bool is_bonded_dsi)
> > > > hdisplay /= 2;
> > > > }
> > > >  
> > > > +   if (msm_host->dsc) {
> > > > +   struct msm_display_dsc_config *dsc = msm_host->dsc;
> > > > +
> > > > +   /* update dsc params with timing params */
> > > > +   dsi_dsc_update_pic_dim(dsc, mode->hdisplay, 
> > > > mode->vdisplay);
> 
> That is, the result code here should be checked (or function inlined).

This function return void, so no point in checking

> > > > +
> > > > +   /* we do the calculations for dsc parameters here so 
> > > > that
> > > > +* panel can use these parameters
> > > > +*/
> > > > +   dsi_populate_dsc_params(dsc);
> > > > +
> > > > +   /* Divide the display by 3 but keep back/font porch and
> > > > +* pulse width same
> > > > +*/
> > > 
> > > A more general nit on the comments in this patch series: it is
> > > appreciated if comments explain the rationale rather than - or in
> > > addition to - merely paraphrasing the code that follows.
> > 
> > Yes it might be the case here, but in this case I wanted to explicitly
> > point out hat we need to divide display by 3...
> 
> The main point here is justifying _why_ there's a division by 3 for the
> active portion of the signal, I presume that's the compression ratio
> (having not read into the DSC compression standard yet at all)?

I have updated this comment

> > > > +   if (msm_host->dsc) {
> > > > +   struct msm_display_dsc_config *dsc = 
> > > > msm_host->dsc;
> > > > +   u32 reg, reg_ctrl, reg_ctrl2;
> > > > +   u32 slice_per_intf, bytes_in_slice, 
> > > > total_bytes_per_intf;
> > > > +
> > > > +   reg_ctrl = dsi_read(msm_host, 
> > > > REG_DSI_COMMAND_COMPRESSION_MODE_CTRL);
> > > > +   reg_ctrl2 = dsi_read(msm_host, 
> > > > REG_DSI_COMMAND_COMPRESSION_MODE_CTRL2);
> > > 
> > > Shouldn't old values be masked out first, before writing new bits or
> > > values below?  The video-mode variant doesn't read back old register
> > > values.
> > 
> > This follows downstream where the registers are read, modified and
> > written back
> 
> Are you sure about this?  The register values are never cleared, meaning
> that only bits get added through the `|=` below but never unset - unless
> downstream clears these registers elsewhere before ending up in (their
> equivalent of) dsi_timing_setup.

I have modified video mode to write and not read now. For command mode
all bits are set to some value so no need to mask old values for that

> Thanks.  I forgot to mention: there seem to be a lot of similarities
> between the video and commandmode computations, can those possibly be
> factored out of the if-else to save on duplication and accidental
> mismatches like these?

Thanks, this was a good suggestion and am happy to report that I have
incorporated this and indeed code looks better

-- 
~Vinod


Re: [PATCH v2] drm/i915: Add a DP1.2 compatible way to read LTTPR capabilities

2022-03-22 Thread Ville Syrjälä
On Tue, Mar 22, 2022 at 04:38:44PM +0200, Imre Deak wrote:
> At least some DELL monitors (P2715Q) with DPCD_REV 1.2 return corrupted
> DPCD register values when reading from the 0xF- LTTPR range with an
> AUX transaction block size bigger than 1. The DP standard requires 0 to
> be returned - as for any other reserved/invalid addresses - but these
> monitors return the DPCD_REV register value repeated in each byte of the
> read buffer. This will in turn corrupt the values returned by the LTTPRs
> between the source and the monitor: LTTPRs must adjust the values they
> read from the downstream DPRX, for instance left-shift/init the
> downstream DP_PHY_REPEATER_CNT value. Since the value returned by the
> monitor's DPRX is non-zero the adjusted values will be corrupt.
> 
> Reading the LTTPR registers one-by-one instead of reading all of them
> with a single AUX transfer works around the issue.
> 
> According to the DP standard's 0xF register description:
> "LTTPR-related registers at DPCD Addresses Fh through F02FFh are
> valid only for DPCD r1.4 (or higher)." While it's unclear if DPCD r1.4
> refers to the DPCD_REV or to the
> LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV register (tickets filed
> at the VESA site to clarify this haven't been addressed), one
> possibility is that it's a restriction due to non-compliant monitors
> described above. Disabling the non-transparent LTTPR mode for all such
> monitors is not a viable solution: the transparent LTTPR mode has its
> own issue causing link training failures and this would affect a lot of
> monitors in use with DPCD_REV < 1.4. Instead this patch works around
> the problem by reading the LTTPR common and PHY cap registers one-by-one
> for any monitor with a DPCD_REV < 1.4.
> 
> The standard requires the DPCD capabilites to be read after the LTTPR
> common capabilities are read, so re-read the DPCD capabilities after
> the LTTPR common and PHY caps were read out.
> 
> v2:
> - Use for instead of a while loop. (Ville)
> - Add to code comment the monitor model with the problem.
> 
> Closes: https://gitlab.freedesktop.org/drm/intel/-/issues/4531
> Cc: Ville Syrjälä 
> Signed-off-by: Imre Deak 

Reviewed-by: Ville Syrjälä 

> ---
>  drivers/gpu/drm/dp/drm_dp.c   | 57 ---
>  .../drm/i915/display/intel_dp_link_training.c | 30 +++---
>  include/drm/dp/drm_dp_helper.h|  2 +
>  3 files changed, 58 insertions(+), 31 deletions(-)
> 
> diff --git a/drivers/gpu/drm/dp/drm_dp.c b/drivers/gpu/drm/dp/drm_dp.c
> index 703972ae14c64..58744f83931af 100644
> --- a/drivers/gpu/drm/dp/drm_dp.c
> +++ b/drivers/gpu/drm/dp/drm_dp.c
> @@ -2390,9 +2390,35 @@ int drm_dp_dsc_sink_supported_input_bpcs(const u8 
> dsc_dpcd[DP_DSC_RECEIVER_CAP_S
>  }
>  EXPORT_SYMBOL(drm_dp_dsc_sink_supported_input_bpcs);
>  
> +static int drm_dp_read_lttpr_regs(struct drm_dp_aux *aux, const u8 
> dpcd[DP_RECEIVER_CAP_SIZE], int address,
> +   u8 *buf, int buf_size)
> +{
> + /*
> +  * At least the DELL P2715Q monitor with a DPCD_REV < 0x14 returns
> +  * corrupted values when reading from the 0xF- range with a block
> +  * size bigger than 1.
> +  */
> + int block_size = dpcd[DP_DPCD_REV] < 0x14 ? 1 : buf_size;
> + int offset;
> + int ret;
> +
> + for (offset = 0; offset < buf_size; offset += block_size) {
> + ret = drm_dp_dpcd_read(aux,
> +address + offset,
> +&buf[offset], block_size);
> + if (ret < 0)
> + return ret;
> +
> + WARN_ON(ret != block_size);
> + }
> +
> + return 0;
> +}
> +
>  /**
>   * drm_dp_read_lttpr_common_caps - read the LTTPR common capabilities
>   * @aux: DisplayPort AUX channel
> + * @dpcd: DisplayPort configuration data
>   * @caps: buffer to return the capability info in
>   *
>   * Read capabilities common to all LTTPRs.
> @@ -2400,25 +2426,19 @@ EXPORT_SYMBOL(drm_dp_dsc_sink_supported_input_bpcs);
>   * Returns 0 on success or a negative error code on failure.
>   */
>  int drm_dp_read_lttpr_common_caps(struct drm_dp_aux *aux,
> +   const u8 dpcd[DP_RECEIVER_CAP_SIZE],
> u8 caps[DP_LTTPR_COMMON_CAP_SIZE])
>  {
> - int ret;
> -
> - ret = drm_dp_dpcd_read(aux,
> -
> DP_LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV,
> -caps, DP_LTTPR_COMMON_CAP_SIZE);
> - if (ret < 0)
> - return ret;
> -
> - WARN_ON(ret != DP_LTTPR_COMMON_CAP_SIZE);
> -
> - return 0;
> + return drm_dp_read_lttpr_regs(aux, dpcd,
> +   
> DP_LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV,
> +   caps, DP_LTTPR_COMMON_CAP_SIZE);
>  }
>  EXPORT_SYMBOL(drm_dp_read_lttpr_common_caps);
>  
>  /**
>   * drm_dp_read_lttpr_phy_caps - read the

Re: [PATCH 1/2] dt-bindings: display: imx: Add fsl,imx21-lcdc docs

2022-03-22 Thread Uwe Kleine-König
Hi Rob,

On Mon, Feb 21, 2022 at 02:55:36PM +0100, Uwe Kleine-König wrote:
> On Thu, Feb 10, 2022 at 06:54:13PM +0100, Lucas Stach wrote:
> > Am Dienstag, dem 01.02.2022 um 11:35 -0600 schrieb Rob Herring:
> > > On Fri, Jan 28, 2022 at 06:58:29PM +0100, Uwe Kleine-König wrote:
> > > > On Fri, Jan 28, 2022 at 07:04:10AM -0600, Rob Herring wrote:
> > > > > On Fri, Jan 28, 2022 at 4:59 AM Uwe Kleine-König
> > > > >  wrote:
> > > > > > 
> > > > > > From: Marian Cichy 
> > > > > > 
> > > > > > This files documents the device tree for the new imx21-lcdc DRM 
> > > > > > driver.
> > > > > 
> > > > > No, bindings document h/w and the h/w has not changed. We already have
> > > > > a binding for the LCDC.
> > > > 
> > > > Just to be sure we're talking about the same thing: You're refering to
> > > > Documentation/devicetree/bindings/display/imx/fsl,imx-fb.txt, right?
> > > 
> > > Looks right...
> > > 
> > > > I'm unsure what to do now. Should the two different bindings just be
> > > > described in the same file? Should I stick to fsl,imx21-fb even for the
> > > > new binding? (The hardware unit is named LCDC, so the name chosen here
> > > > is the better one.) Please advise.
> > > 
> > > Yes, the name is unfortunate, but it should be 1 binding, 1 file, and 
> > > unchanged (unless you want to add new optional properties). 
> >
> > The old FB driver binding is pretty insane. Except the reg and
> > interrupt properties it is very confused about things. It exposes
> > internal implementation details (like specifying verbatim register
> > settings in the DT) and other properties are just misplaced, like the
> > lcd-supply property that controls the panel power supply.
> > 
> > I really don't think that trying to stay backwards compatible here is a
> > win for anyone. Anyone willing to switch their systems running on a 15
> > year old SoC to the new DRM driver probably doesn't mind if they have
> > to modify the DTS to make it work. Can we please let the FB driver die
> > in peace and have a clean slate driver/binding for the DRM driver?
> 
> Does this feedback change anything on your side? My expectation is that
> the graphics people will be happy about every fb driver being replaced
> by a DRM driver and there will be hardly any incentive to add a layer
> over the DRM driver to make it honor the old fb binding.
> 
> Assume I convert the old binding to yaml and then add the newly
> supported binding to that using a big oneOf, would that be an acceptable
> compromise?

I'd like to get forward with this driver. What would be a good way to
continue here? 

Best regards
Uwe

-- 
Pengutronix e.K.   | Uwe Kleine-König|
Industrial Linux Solutions | https://www.pengutronix.de/ |


signature.asc
Description: PGP signature


[PATCH v6] drm/msm/disp/dpu1: add inline rotation support for sc7280 target

2022-03-22 Thread Vinod Polimera
- Some DPU versions support inline rot90. It is supported only for
limited amount of UBWC formats.
- There are two versions of inline rotators, v1 (present on sm8250 and
sm7250) and v2 (sc7280). These versions differ in the list of supported
formats and in the scaler possibilities.

Changes in RFC:
- Rebase changes to the latest code base.
- Append rotation config variables with v2 and
remove unused variables.(Dmitry)
- Move pixel_ext setup separately from scaler3 config.(Dmitry)
- Add 270 degree rotation to supported rotation list.(Dmitry)

Changes in V2:
- Remove unused macros and fix indentation.
- Add check if 90 rotation is supported and
add supported rotations to rot_cfg.

Changes in V3:
- Fix indentation.
- Move rot_supported to sspp capabilities. (Dmitry)
- Config pixel_ext based on src_h/src_w directly. (Dmitry)
- Misc changes.

Changes in V4:
- Pass boolean value to sspp blk based on supported rotations for each hw.

Changes in V5:
- Update boolean value to true/false and add it for qcm2290.

Changes in V6:
- Add changes that are missed as part of v5.
- Add dpu_find_format inline function to find valid format. (Dmitry)

Co-developed-by: Kalyan Thota 
Signed-off-by: Kalyan Thota 
Signed-off-by: Vinod Polimera 
---
 drivers/gpu/drm/msm/disp/dpu1/dpu_formats.h|  21 +++
 drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c | 185 ++---
 drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.h |  18 +++
 drivers/gpu/drm/msm/disp/dpu1/dpu_plane.c  | 109 ---
 drivers/gpu/drm/msm/disp/dpu1/dpu_plane.h  |   2 +
 5 files changed, 230 insertions(+), 105 deletions(-)

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_formats.h 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_formats.h
index 418f5ae..8e26ea5 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_formats.h
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_formats.h
@@ -31,6 +31,27 @@ const struct msm_format *dpu_get_msm_format(
struct msm_kms *kms,
const uint32_t format,
const uint64_t modifiers);
+/**
+ * dpu_find_format - validate if the pixel format is supported
+ * @fmt:   pointer to the dpu format
+ * @supported_formats: supported formats by dpu HW
+ * @num_formatss:  total number of formats
+ *
+ * Return: false if not valid format, true on success
+ */
+static inline bool dpu_find_format(const struct dpu_format *fmt, const u32 
*supported_formats,
+   size_t num_formats)
+{
+   int i;
+
+   for (i = 0; i < num_formats; i++) {
+   /* check for valid formats supported by inline rotation */
+   if (fmt->base.pixel_format == supported_formats[i])
+   return true;
+   }
+
+   return false;
+}
 
 /**
  * dpu_format_check_modified_format - validate format and buffers for
diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c
index a4fe77c..ced7fb3 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c
@@ -35,6 +35,9 @@
BIT(DPU_SSPP_TS_PREFILL) | BIT(DPU_SSPP_TS_PREFILL_REC1) |\
BIT(DPU_SSPP_CDP) | BIT(DPU_SSPP_EXCL_RECT))
 
+#define VIG_SC7280_MASK \
+   (VIG_SC7180_MASK | BIT(DPU_SSPP_INLINE_ROTATION))
+
 #define DMA_SDM845_MASK \
(BIT(DPU_SSPP_SRC) | BIT(DPU_SSPP_QOS) | BIT(DPU_SSPP_QOS_8LVL) |\
BIT(DPU_SSPP_TS_PREFILL) | BIT(DPU_SSPP_TS_PREFILL_REC1) |\
@@ -203,6 +206,11 @@ static const uint32_t plane_formats_yuv[] = {
DRM_FORMAT_YVU420,
 };
 
+static const u32 rotation_v2_formats[] = {
+   DRM_FORMAT_NV12,
+   /* TODO add formats after validation */
+};
+
 /*
  * DPU sub blocks config
  */
@@ -642,8 +650,7 @@ static const struct dpu_ctl_cfg qcm2290_ctl[] = {
  */
 
 /* SSPP common configuration */
-
-#define _VIG_SBLK(num, sdma_pri, qseed_ver) \
+#define _VIG_SBLK(num, sdma_pri, qseed_ver, rot_cfg) \
{ \
.maxdwnscale = MAX_DOWNSCALE_RATIO, \
.maxupscale = MAX_UPSCALE_RATIO, \
@@ -660,6 +667,7 @@ static const struct dpu_ctl_cfg qcm2290_ctl[] = {
.num_formats = ARRAY_SIZE(plane_formats_yuv), \
.virt_format_list = plane_formats, \
.virt_num_formats = ARRAY_SIZE(plane_formats), \
+   .rotation_cfg = rot_cfg, \
}
 
 #define _DMA_SBLK(num, sdma_pri) \
@@ -676,22 +684,28 @@ static const struct dpu_ctl_cfg qcm2290_ctl[] = {
}
 
 static const struct dpu_sspp_sub_blks msm8998_vig_sblk_0 =
-   _VIG_SBLK("0", 0, DPU_SSPP_SCALER_QSEED3);
+   _VIG_SBLK("0", 0, DPU_SSPP_SCALER_QSEED3, NULL);
 static const struct dpu_sspp_sub_blks msm8998_vig_sblk_1 =
-   _VIG_SBLK("1", 0, DPU_SSPP_SCALER_QSEED3);
+  

Re: [PATCH v13 00/13] Add GuC Error Capture Support

2022-03-22 Thread Lucas De Marchi

On Mon, Mar 21, 2022 at 09:45:14AM -0700, Alan Previn wrote:

This series:
 1. Enables support of GuC to report error-state-capture
using a list of MMIO registers the driver registers
and GuC will dump, log and notify right before a GuC
triggered engine-reset event.
 2. Updates the ADS blob creation to register said lists
of global, engine class and engine instance registers
with GuC.
 3. Defines tables of register lists that are global or
engine class or engine instance in scope.
 4. Updates usage and buffer-state data for the regions
of the shared GuC log-buffer to accomdate both
the existing relay logging of general debug logs
along with the new error state capture usage.
 5. Using a pool of preallocated memory, provide ability
to extract and format the GuC reported register-capture
data into chunks consistent with existing i915 error-
state collection flows and structures.
 6. Connects the i915_gpu_coredump reporting function
to the GuC error capture module to print all GuC
error state capture dumps that is reported.

This is the 13th rev of this series where the first 3 revs
are RFC

Prior receipts of rvb's:
 - Patch #2, #3, #4, #5, #10, #11, #12, #13 have received
   R-v-b's from Umesh Nerlige Ramappa 
 - Patch #1, #6, #7, #8, #9 has received an R-v-b from Matthew Brost
   . NOTE: some of these came in on the
   trybot series. https://patchwork.freedesktop.org/series/100831/

Changes from prior revs:
 v13:- Fixing register list definition styling as per Jani's request.


As in v12, the CI failure in display is unrelated to these changes.

Applied to drm-intel-gt-next.

Thanks
Lucas De Marchi


Re: [PATCH v2] drm/nouveau/bios: Rename prom_init() and friends functions

2022-03-22 Thread Lyude Paul
Reviewed-by: Lyude Paul 

Will push to drm-misc-next

On Sat, 2022-03-19 at 11:27 +0100, Christophe Leroy wrote:
> While working at fixing powerpc headers, I ended up with the
> following error.
> 
> drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowrom.c:48:1: error:
> conflicting types for 'prom_init'; have 'void *(struct nvkm_bios *, const
> char *)'
> make[5]: *** [scripts/Makefile.build:288:
> drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowrom.o] Error 1
> 
> powerpc and a few other architectures have a prom_init() global function.
> One day or another it will conflict with the one in shadowrom.c
> 
> Those being static, they can easily be renamed. Do it.
> 
> While at it, also rename the ops structure as 'nvbios_prom' instead of
> 'nvbios_rom' in order to make it clear that it refers to the
> NV_PROM device.
> 
> Signed-off-by: Christophe Leroy 
> ---
> v2: using nvbios_prom prefix instead of nvbios_rom. Changed structure name
> to keep things consistant.
> 
>  drivers/gpu/drm/nouveau/nvkm/subdev/bios/priv.h    |  2 +-
>  drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadow.c  |  2 +-
>  .../gpu/drm/nouveau/nvkm/subdev/bios/shadowrom.c   | 14 +++---
>  3 files changed, 9 insertions(+), 9 deletions(-)
> 
> diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/priv.h
> b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/priv.h
> index fac1bff1311b..cfa8a0c356dd 100644
> --- a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/priv.h
> +++ b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/priv.h
> @@ -19,7 +19,7 @@ struct nvbios_source {
>  int nvbios_extend(struct nvkm_bios *, u32 length);
>  int nvbios_shadow(struct nvkm_bios *);
>  
> -extern const struct nvbios_source nvbios_rom;
> +extern const struct nvbios_source nvbios_prom;
>  extern const struct nvbios_source nvbios_ramin;
>  extern const struct nvbios_source nvbios_acpi_fast;
>  extern const struct nvbios_source nvbios_acpi_slow;
> diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadow.c
> b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadow.c
> index 4b571cc6bc70..19188683c8fc 100644
> --- a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadow.c
> +++ b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadow.c
> @@ -171,7 +171,7 @@ nvbios_shadow(struct nvkm_bios *bios)
> struct shadow mthds[] = {
> { 0, &nvbios_of },
> { 0, &nvbios_ramin },
> -   { 0, &nvbios_rom },
> +   { 0, &nvbios_prom },
> { 0, &nvbios_acpi_fast },
> { 4, &nvbios_acpi_slow },
> { 1, &nvbios_pcirom },
> diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowrom.c
> b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowrom.c
> index ffa4b395220a..39144ceb117b 100644
> --- a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowrom.c
> +++ b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowrom.c
> @@ -25,7 +25,7 @@
>  #include 
>  
>  static u32
> -prom_read(void *data, u32 offset, u32 length, struct nvkm_bios *bios)
> +nvbios_prom_read(void *data, u32 offset, u32 length, struct nvkm_bios
> *bios)
>  {
> struct nvkm_device *device = data;
> u32 i;
> @@ -38,14 +38,14 @@ prom_read(void *data, u32 offset, u32 length, struct
> nvkm_bios *bios)
>  }
>  
>  static void
> -prom_fini(void *data)
> +nvbios_prom_fini(void *data)
>  {
> struct nvkm_device *device = data;
> nvkm_pci_rom_shadow(device->pci, true);
>  }
>  
>  static void *
> -prom_init(struct nvkm_bios *bios, const char *name)
> +nvbios_prom_init(struct nvkm_bios *bios, const char *name)
>  {
> struct nvkm_device *device = bios->subdev.device;
> if (device->card_type == NV_40 && device->chipset >= 0x4c)
> @@ -55,10 +55,10 @@ prom_init(struct nvkm_bios *bios, const char *name)
>  }
>  
>  const struct nvbios_source
> -nvbios_rom = {
> +nvbios_prom = {
> .name = "PROM",
> -   .init = prom_init,
> -   .fini = prom_fini,
> -   .read = prom_read,
> +   .init = nvbios_prom_init,
> +   .fini = nvbios_prom_fini,
> +   .read = nvbios_prom_read,
> .rw = false,
>  };

-- 
Cheers,
 Lyude Paul (she/her)
 Software Engineer at Red Hat



Re: [PATCH 1/2] dt-bindings: display: imx: Add fsl,imx21-lcdc docs

2022-03-22 Thread Rob Herring
On Thu, Feb 10, 2022 at 11:54 AM Lucas Stach  wrote:
>
> Hi Rob,
>
> Am Dienstag, dem 01.02.2022 um 11:35 -0600 schrieb Rob Herring:
> > On Fri, Jan 28, 2022 at 06:58:29PM +0100, Uwe Kleine-König wrote:
> > > Hello Rob,
> > >
> > > On Fri, Jan 28, 2022 at 07:04:10AM -0600, Rob Herring wrote:
> > > > On Fri, Jan 28, 2022 at 4:59 AM Uwe Kleine-König
> > > >  wrote:
> > > > >
> > > > > From: Marian Cichy 
> > > > >
> > > > > This files documents the device tree for the new imx21-lcdc DRM 
> > > > > driver.
> > > >
> > > > No, bindings document h/w and the h/w has not changed. We already have
> > > > a binding for the LCDC.
> > >
> > > Just to be sure we're talking about the same thing: You're refering to
> > > Documentation/devicetree/bindings/display/imx/fsl,imx-fb.txt, right?
> >
> > Looks right...
> >
> > > I'm unsure what to do now. Should the two different bindings just be
> > > described in the same file? Should I stick to fsl,imx21-fb even for the
> > > new binding? (The hardware unit is named LCDC, so the name chosen here
> > > is the better one.) Please advise.
> >
> > Yes, the name is unfortunate, but it should be 1 binding, 1 file, and
> > unchanged (unless you want to add new optional properties).
> >
> The old FB driver binding is pretty insane. Except the reg and
> interrupt properties it is very confused about things. It exposes
> internal implementation details (like specifying verbatim register
> settings in the DT) and other properties are just misplaced, like the
> lcd-supply property that controls the panel power supply.

I agree on 'lcd-supply', but that can simply be marked as deprecated
as can anything else. From what I remember working on these chips, I'm
not sure you can really avoid some of these register properties. For
example, the Sharp config is pretty much a use some value with some
specific Sharp panel. I guess we can have 'if panel A, then register
value is X' type code in the driver. Maybe the DMA settings can be
heuristics based on the pixel data rate, but I recall avoiding
underruns was challenging on some parts.

> I really don't think that trying to stay backwards compatible here is a
> win for anyone. Anyone willing to switch their systems running on a 15
> year old SoC to the new DRM driver probably doesn't mind if they have
> to modify the DTS to make it work. Can we please let the FB driver die
> in peace and have a clean slate driver/binding for the DRM driver?

The existing binding will still need a schema if it appears in dts files.

There's nothing really conflicting between the 2 bindings. Your
choices are to merge it all into 1 node and it's up to kernel
configuration (or module load) to select which driver. Or you have 2
nodes in the DT with one enabled at a time (because 2 enabled nodes at
the same address is not allowed). Then you need a DT change to switch.
Either way is fine and the schema should match which one you pick, but
I would do 1 node.

If you do a new binding, then justify it for the reasons above, not
the old one is for the FB driver and the new one is for the DRM
driver.

Rob


Re: [Freedreno] [PATCH v3 12/13] drm/msm/dsi: Add support for DSC configuration

2022-03-22 Thread Marijn Suijten
On 2022-03-22 22:46:50, Vinod Koul wrote:
> On 17-02-22, 16:11, Marijn Suijten wrote:
> > Hi Vinod,
> > 
> > Thanks for taking time to go through this review, please find some
> > clarifications below.
> > 
> > On 2022-02-17 16:44:04, Vinod Koul wrote:
> > > Hi Marijn,
> > > 
> > > On 11-12-21, 01:03, Marijn Suijten wrote:
> > > 
> > > > > +static int dsi_dsc_update_pic_dim(struct msm_display_dsc_config *dsc,
> > > > > +   int pic_width, int pic_height)
> > > > 
> > > > This function - adopted from downstream - does not seem to perform a
> > > > whole lot, especially without the modulo checks against the slice size.
> > > > Perhaps it can be inlined?
> > > 
> > > Most of the code here is :)
> > > 
> > > This was split from downstream code to check and update dimension. We
> > > can inline this, or should we leave that to compiler. I am not a very
> > > big fan of inlining...
> > 
> > It doesn't seem beneficial to code readability to have this function,
> > which is only called just once and also has the same struct members read
> > in a `DBG()` directly, abstracted away to a function.  Not really
> > concerned about generated code/performance FWIW.
> > 
> > Also note that the caller isn't checking the `-EINVAL` result...
> 
> I have made this void inline.

Perhaps there is a misunderstanding here: with inlining I am referring
to the process of transplanting the _function body_ to the only
call-site, not adding the `inline` keyword nor changing this to `void`.

The checks that make this function return `-EINVAL` seem valid, so the
caller should check it instead of removing the return?

> > > > 
> > > > > +{
> > > > > + if (!dsc || !pic_width || !pic_height) {
> > > > > + pr_err("DSI: invalid input: pic_width: %d pic_height: 
> > > > > %d\n", pic_width, pic_height);
> > > > > + return -EINVAL;
> > > > > + }
> > > > > +
> > > > > + dsc->drm->pic_width = pic_width;
> > > > > + dsc->drm->pic_height = pic_height;
> > > > > +
> > > > > + return 0;
> > > > > +}
> > > > > +
> > > > >  static void dsi_timing_setup(struct msm_dsi_host *msm_host, bool 
> > > > > is_bonded_dsi)
> > > > >  {
> > > > >   struct drm_display_mode *mode = msm_host->mode;
> > > > > @@ -940,7 +954,68 @@ static void dsi_timing_setup(struct msm_dsi_host 
> > > > > *msm_host, bool is_bonded_dsi)
> > > > >   hdisplay /= 2;
> > > > >   }
> > > > >  
> > > > > + if (msm_host->dsc) {
> > > > > + struct msm_display_dsc_config *dsc = msm_host->dsc;
> > > > > +
> > > > > + /* update dsc params with timing params */
> > > > > + dsi_dsc_update_pic_dim(dsc, mode->hdisplay, 
> > > > > mode->vdisplay);
> > 
> > That is, the result code here should be checked (or function inlined).
> 
> This function return void, so no point in checking

It isn't returning `void` in the current patch series that my email is
reviewing, hence explicitly mentioning here that it may have been
overlooked.

Please only convert this to `void` if you are sure that the clause that
originally made `dsi_dsc_update_pic_dim()` return `-EINVAL` on invalid
input is unreachable (if, for example, you moved this check to another
location, say here in `dsi_timing_setup`).

Alas, it's pretty tricky to reason and pose assumptions about code that
I cannot see; we should probably continue this discussion in the next
patch revision depending on how it looks :)

> > [..]
> > Thanks.  I forgot to mention: there seem to be a lot of similarities
> > between the video and commandmode computations, can those possibly be
> > factored out of the if-else to save on duplication and accidental
> > mismatches like these?
> 
> Thanks, this was a good suggestion and am happy to report that I have
> incorporated this and indeed code looks better

Thank you for applying this and the other comments, glad to hear the
code is shaping up and looking forward to the next revision!

- Marijn


Re: [PATCH v7 06/12] clk: Always set the rate on clk_set_range_rate

2022-03-22 Thread Dmitry Osipenko
On 2/25/22 17:35, Maxime Ripard wrote:
> When we change a clock minimum or maximum using clk_set_rate_range(),
> clk_set_min_rate() or clk_set_max_rate(), the current code will only
> trigger a new rate change if the rate is outside of the new boundaries.
> 
> However, a clock driver might want to always keep the clock rate to
> one of its boundary, for example the minimum to keep the power
> consumption as low as possible.
> 
> Since they don't always get called though, clock providers don't have the
> opportunity to implement this behaviour.
> 
> Let's trigger a clk_set_rate() on the previous requested rate every time
> clk_set_rate_range() is called. That way, providers that care about the
> new boundaries have a chance to adjust the rate, while providers that
> don't care about those new boundaries will return the same rate than
> before, which will be ignored by clk_set_rate() and won't result in a
> new rate change.
> 
> Suggested-by: Stephen Boyd 
> Signed-off-by: Maxime Ripard 
> ---
>  drivers/clk/clk.c  | 45 
>  drivers/clk/clk_test.c | 58 +++---
>  2 files changed, 49 insertions(+), 54 deletions(-)
> 
> diff --git a/drivers/clk/clk.c b/drivers/clk/clk.c
> index c15ee5070f52..9bc8bf434b94 100644
> --- a/drivers/clk/clk.c
> +++ b/drivers/clk/clk.c
> @@ -2373,28 +2373,29 @@ int clk_set_rate_range(struct clk *clk, unsigned long 
> min, unsigned long max)
>   goto out;
>   }
>  
> - rate = clk_core_get_rate_nolock(clk->core);
> - if (rate < min || rate > max) {
> - /*
> -  * FIXME:
> -  * We are in bit of trouble here, current rate is outside the
> -  * the requested range. We are going try to request appropriate
> -  * range boundary but there is a catch. It may fail for the
> -  * usual reason (clock broken, clock protected, etc) but also
> -  * because:
> -  * - round_rate() was not favorable and fell on the wrong
> -  *   side of the boundary
> -  * - the determine_rate() callback does not really check for
> -  *   this corner case when determining the rate
> -  */
> -
> - rate = clamp(clk->core->req_rate, min, max);
> - ret = clk_core_set_rate_nolock(clk->core, rate);
> - if (ret) {
> - /* rollback the changes */
> - clk->min_rate = old_min;
> - clk->max_rate = old_max;
> - }
> + /*
> +  * Since the boundaries have been changed, let's give the
> +  * opportunity to the provider to adjust the clock rate based on
> +  * the new boundaries.
> +  *
> +  * We also need to handle the case where the clock is currently
> +  * outside of the boundaries. Clamping the last requested rate
> +  * to the current minimum and maximum will also handle this.
> +  *
> +  * FIXME:
> +  * There is a catch. It may fail for the usual reason (clock
> +  * broken, clock protected, etc) but also because:
> +  * - round_rate() was not favorable and fell on the wrong
> +  *   side of the boundary
> +  * - the determine_rate() callback does not really check for
> +  *   this corner case when determining the rate
> +  */
> + rate = clamp(clk->core->req_rate, min, max);
> + ret = clk_core_set_rate_nolock(clk->core, rate);
> + if (ret) {
> + /* rollback the changes */
> + clk->min_rate = old_min;
> + clk->max_rate = old_max;
>   }
>  
>  out:

Hi,

NVIDIA Tegra30 no longer boots with this change.

You can't assume that rate was requested by clk_set_rate() before
clk_set_rate_range() is called, see what [1] does. T30 memory rate now
drops to min on boot when clk debug range is inited innocuously and CPU
no longer can make any progress because display controller takes out
whole memory bandwidth.

[1]
https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git/tree/drivers/memory/tegra/tegra30-emc.c#n1437

If clk_set_rate() wasn't ever invoked and req_rate=0, then you must not
change the clk rate if it's within the new range. Please revert this
patch, thanks.


[PATCH 1/8] drm: Put related statements next to each other in Makefile

2022-03-22 Thread Thomas Zimmermann
Give the Makefile a bit more structure by putting rules for core,
helpers, drivers, etc next to each other.

Signed-off-by: Thomas Zimmermann 
---
 drivers/gpu/drm/Makefile | 23 +--
 1 file changed, 17 insertions(+), 6 deletions(-)

diff --git a/drivers/gpu/drm/Makefile b/drivers/gpu/drm/Makefile
index c2ef5f9fce54..e5929437e13c 100644
--- a/drivers/gpu/drm/Makefile
+++ b/drivers/gpu/drm/Makefile
@@ -18,7 +18,6 @@ drm-y   :=drm_aperture.o drm_auth.o drm_cache.o \
drm_syncobj.o drm_lease.o drm_writeback.o drm_client.o \
drm_client_modeset.o drm_atomic_uapi.o \
drm_managed.o drm_vblank_work.o
-
 drm-$(CONFIG_DRM_LEGACY) += drm_agpsupport.o drm_bufs.o drm_context.o 
drm_dma.o \
drm_hashtab.o drm_irq.o drm_legacy_misc.o 
drm_lock.o \
drm_memory.o drm_scatter.o drm_vm.o
@@ -30,8 +29,16 @@ drm-$(CONFIG_PCI) += drm_pci.o
 drm-$(CONFIG_DEBUG_FS) += drm_debugfs.o drm_debugfs_crc.o
 drm-$(CONFIG_DRM_LOAD_EDID_FIRMWARE) += drm_edid_load.o
 drm-$(CONFIG_DRM_PRIVACY_SCREEN) += drm_privacy_screen.o 
drm_privacy_screen_x86.o
+obj-$(CONFIG_DRM)  += drm.o
 
 obj-$(CONFIG_DRM_NOMODESET) += drm_nomodeset.o
+obj-$(CONFIG_DRM_PANEL_ORIENTATION_QUIRKS) += drm_panel_orientation_quirks.o
+
+#
+# Memory-management helpers
+#
+
+obj-$(CONFIG_DRM_BUDDY) += drm_buddy.o
 
 drm_cma_helper-y := drm_gem_cma_helper.o
 drm_cma_helper-$(CONFIG_DRM_KMS_HELPER) += drm_fb_cma_helper.o
@@ -40,14 +47,16 @@ obj-$(CONFIG_DRM_GEM_CMA_HELPER) += drm_cma_helper.o
 drm_shmem_helper-y := drm_gem_shmem_helper.o
 obj-$(CONFIG_DRM_GEM_SHMEM_HELPER) += drm_shmem_helper.o
 
-obj-$(CONFIG_DRM_BUDDY) += drm_buddy.o
-
 drm_vram_helper-y := drm_gem_vram_helper.o
 obj-$(CONFIG_DRM_VRAM_HELPER) += drm_vram_helper.o
 
 drm_ttm_helper-y := drm_gem_ttm_helper.o
 obj-$(CONFIG_DRM_TTM_HELPER) += drm_ttm_helper.o
 
+#
+# Modesetting helpers
+#
+
 drm_kms_helper-y := drm_bridge_connector.o drm_crtc_helper.o \
drm_dsc.o drm_encoder_slave.o drm_flip_work.o drm_hdcp.o \
drm_probe_helper.o \
@@ -60,14 +69,16 @@ drm_kms_helper-y := drm_bridge_connector.o 
drm_crtc_helper.o \
drm_format_helper.o drm_self_refresh_helper.o drm_rect.o
 drm_kms_helper-$(CONFIG_DRM_PANEL_BRIDGE) += bridge/panel.o
 drm_kms_helper-$(CONFIG_DRM_FBDEV_EMULATION) += drm_fb_helper.o
-
 obj-$(CONFIG_DRM_KMS_HELPER) += drm_kms_helper.o
+
+#
+# Drivers and the rest
+#
+
 obj-$(CONFIG_DRM_DEBUG_SELFTEST) += selftests/
 
-obj-$(CONFIG_DRM)  += drm.o
 obj-$(CONFIG_DRM_MIPI_DBI) += drm_mipi_dbi.o
 obj-$(CONFIG_DRM_MIPI_DSI) += drm_mipi_dsi.o
-obj-$(CONFIG_DRM_PANEL_ORIENTATION_QUIRKS) += drm_panel_orientation_quirks.o
 obj-y  += arm/
 obj-y  += dp/
 obj-$(CONFIG_DRM_TTM)  += ttm/
-- 
2.35.1



[PATCH 0/8] drm: Introduce display-helper library

2022-03-22 Thread Thomas Zimmermann
Move DisplayPort, HDMI and various other display helpers from KMS
helpers into a new module. Adapt all drivers.

This patch is part of an on-going effort to reduce the minimum size
of DRM when linked into the kernel binary. The helpers for various
display and video-output standards are not required for minimal
graphics output and can be moved into a separate module.

The DisplayPort code was already part of the DP module, which now
forms the base of the display-helper module. Moving other helpers
into the new module reduces KMS helpers by ~14 KiB (from 243 KiB to
229 KiB). More importantly, restructuring the code allows for a more
fine-grained selection of helpers and dependencies.

Built on x64-64, i586, aarch64, and arm.

Thomas Zimmermann (8):
  drm: Put related statements next to each other in Makefile
  drm: Rename dp/ to display/
  drm/display: Introduce a DRM display-helper module
  drm/display: Split DisplayPort header into core and helper
  drm/display: Move DSC header and helpers into display-helper module
  drm/display: Move HDCP helpers into display-helper module
  drm/display: Move HDMI helpers into display-helper module
  drm/display: Move SCDC helpers into display-helper library

 Documentation/gpu/drm-kms-helpers.rst |  43 +-
 drivers/gpu/drm/Kconfig   |  23 +
 drivers/gpu/drm/Makefile  |  29 +-
 .../gpu/drm/amd/amdgpu/amdgpu_connectors.c|   2 +-
 drivers/gpu/drm/amd/amdgpu/amdgpu_mode.h  |   4 +-
 drivers/gpu/drm/amd/amdgpu/atombios_dp.c  |   3 +-
 drivers/gpu/drm/amd/amdgpu/dce_v10_0.c|   1 +
 drivers/gpu/drm/amd/amdgpu/dce_v11_0.c|   1 +
 drivers/gpu/drm/amd/amdgpu/dce_v6_0.c |   1 +
 drivers/gpu/drm/amd/amdgpu/dce_v8_0.c |   1 +
 drivers/gpu/drm/amd/display/Kconfig   |   1 +
 .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c |   5 +-
 .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h |   2 +-
 .../amd/display/amdgpu_dm/amdgpu_dm_hdcp.c|   2 +-
 .../display/amdgpu_dm/amdgpu_dm_mst_types.c   |   4 +-
 .../drm/amd/display/dc/core/dc_link_dpcd.c|   2 +-
 .../gpu/drm/amd/display/dc/dcn20/dcn20_dsc.c  |   2 +
 .../gpu/drm/amd/display/dc/dcn20/dcn20_dsc.h  |   2 +-
 .../drm/amd/display/dc/dml/dsc/rc_calc_fpu.h  |   2 +-
 drivers/gpu/drm/amd/display/dc/dsc/dc_dsc.c   |   4 +-
 .../gpu/drm/amd/display/dc/dsc/dscc_types.h   |   2 +-
 .../gpu/drm/amd/display/dc/dsc/rc_calc_dpi.c  |   2 +-
 drivers/gpu/drm/amd/display/dc/os_types.h |   2 +-
 .../gpu/drm/amd/display/include/dpcd_defs.h   |   2 +-
 .../gpu/drm/amd/display/modules/hdcp/hdcp.h   |   4 +-
 drivers/gpu/drm/bridge/Kconfig|   5 +
 drivers/gpu/drm/bridge/analogix/Kconfig   |   2 +
 .../drm/bridge/analogix/analogix-anx6345.c|   2 +-
 .../drm/bridge/analogix/analogix-anx78xx.c|   4 +-
 .../drm/bridge/analogix/analogix-i2c-dptx.c   |   2 +-
 .../drm/bridge/analogix/analogix_dp_core.h|   2 +-
 drivers/gpu/drm/bridge/analogix/anx7625.c |   6 +-
 drivers/gpu/drm/bridge/cadence/Kconfig|   1 +
 .../drm/bridge/cadence/cdns-mhdp8546-core.c   |   4 +-
 .../drm/bridge/cadence/cdns-mhdp8546-core.h   |   2 +-
 .../drm/bridge/cadence/cdns-mhdp8546-hdcp.c   |   2 +-
 drivers/gpu/drm/bridge/ite-it6505.c   |   4 +-
 drivers/gpu/drm/bridge/parade-ps8640.c|   4 +-
 drivers/gpu/drm/bridge/sii902x.c  |   2 +-
 drivers/gpu/drm/bridge/sil-sii8620.c  |   2 +-
 drivers/gpu/drm/bridge/synopsys/Kconfig   |   1 +
 drivers/gpu/drm/bridge/synopsys/dw-hdmi.c |   4 +-
 drivers/gpu/drm/bridge/tc358767.c |   2 +-
 drivers/gpu/drm/bridge/tc358775.c |   2 +-
 drivers/gpu/drm/bridge/ti-sn65dsi86.c |   4 +-
 drivers/gpu/drm/display/Makefile  |  13 +
 .../drm_display_helper_mod.c} |  10 +-
 .../gpu/drm/{dp => display}/drm_dp_aux_bus.c  |   4 +-
 .../gpu/drm/{dp => display}/drm_dp_aux_dev.c  |   4 +-
 drivers/gpu/drm/{dp => display}/drm_dp_cec.c  |   2 +-
 .../{dp => display}/drm_dp_dual_mode_helper.c |   2 +-
 .../{dp/drm_dp.c => display/drm_dp_helper.c}  |   4 +-
 .../{dp => display}/drm_dp_helper_internal.h  |   0
 .../drm/{dp => display}/drm_dp_mst_topology.c |   2 +-
 .../drm_dp_mst_topology_internal.h|   2 +-
 .../{drm_dsc.c => display/drm_dsc_helper.c}   |   5 +-
 .../{drm_hdcp.c => display/drm_hdcp_helper.c} |   4 +-
 drivers/gpu/drm/display/drm_hdmi_helper.c | 463 +++
 .../gpu/drm/{ => display}/drm_scdc_helper.c   |   3 +-
 drivers/gpu/drm/dp/Makefile   |   9 -
 drivers/gpu/drm/drm_connector.c   |  34 -
 drivers/gpu/drm/drm_edid.c| 439 +--
 drivers/gpu/drm/drm_mipi_dsi.c|   6 +-
 drivers/gpu/drm/exynos/Kconfig|   1 +
 drivers/gpu/drm/exynos/exynos_hdmi.c  |   2 +-
 drivers/gpu/drm/gma500/cdv_intel_dp.c |   2 +-
 drivers/gpu/drm/gma500/intel_bios.c   |   3 +-
 drivers/gpu/drm/hdmi/Makefile   

[PATCH 7/8] drm/display: Move HDMI helpers into display-helper module

2022-03-22 Thread Thomas Zimmermann
Move DRM's HMDI helpers into the display/ subdirectoy and add it
to DRM's display helpers. Update all affected drivers. No functional
changes.

The HDMI helpers were implemented in the EDID and connector code, but
are actually unrelated. With the move to the display-helper library, we
can remove the dependency on drm_edid.{c,h} in many driver's HDMI source
files.

Signed-off-by: Thomas Zimmermann 
---
 drivers/gpu/drm/Kconfig   |   9 +
 drivers/gpu/drm/amd/amdgpu/dce_v10_0.c|   1 +
 drivers/gpu/drm/amd/amdgpu/dce_v11_0.c|   1 +
 drivers/gpu/drm/amd/amdgpu/dce_v6_0.c |   1 +
 drivers/gpu/drm/amd/amdgpu/dce_v8_0.c |   1 +
 .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c |   1 +
 drivers/gpu/drm/bridge/Kconfig|   4 +
 drivers/gpu/drm/bridge/analogix/Kconfig   |   1 +
 .../drm/bridge/analogix/analogix-anx78xx.c|   2 +-
 drivers/gpu/drm/bridge/sii902x.c  |   2 +-
 drivers/gpu/drm/bridge/sil-sii8620.c  |   2 +-
 drivers/gpu/drm/bridge/synopsys/Kconfig   |   1 +
 drivers/gpu/drm/bridge/synopsys/dw-hdmi.c |   2 +-
 drivers/gpu/drm/display/Makefile  |   1 +
 drivers/gpu/drm/display/drm_hdmi_helper.c | 463 ++
 drivers/gpu/drm/drm_connector.c   |  34 --
 drivers/gpu/drm/drm_edid.c| 438 +
 drivers/gpu/drm/exynos/Kconfig|   1 +
 drivers/gpu/drm/exynos/exynos_hdmi.c  |   2 +-
 drivers/gpu/drm/hdmi/Makefile |   4 +
 drivers/gpu/drm/i2c/Kconfig   |   1 +
 drivers/gpu/drm/i2c/tda998x_drv.c |   2 +-
 drivers/gpu/drm/i915/Kconfig  |   1 +
 drivers/gpu/drm/i915/display/intel_dp.c   |   2 +-
 drivers/gpu/drm/i915/display/intel_hdmi.c |   1 +
 drivers/gpu/drm/i915/display/intel_lspcon.c   |   2 +-
 drivers/gpu/drm/i915/display/intel_sdvo.c |   1 +
 drivers/gpu/drm/mediatek/Kconfig  |   1 +
 drivers/gpu/drm/mediatek/mtk_hdmi.c   |   2 +-
 drivers/gpu/drm/msm/Kconfig   |   1 +
 drivers/gpu/drm/msm/hdmi/hdmi_bridge.c|   2 +
 drivers/gpu/drm/nouveau/Kconfig   |   1 +
 drivers/gpu/drm/nouveau/dispnv50/disp.c   |   1 +
 drivers/gpu/drm/omapdrm/Kconfig   |   2 +
 drivers/gpu/drm/omapdrm/dss/hdmi4.c   |   1 +
 drivers/gpu/drm/radeon/radeon_audio.c |   1 +
 drivers/gpu/drm/rockchip/Kconfig  |   2 +
 drivers/gpu/drm/rockchip/inno_hdmi.c  |   2 +-
 drivers/gpu/drm/rockchip/rk3066_hdmi.c|   1 +
 drivers/gpu/drm/sti/Kconfig   |   1 +
 drivers/gpu/drm/sti/sti_hdmi.c|   2 +-
 drivers/gpu/drm/sun4i/Kconfig |   1 +
 drivers/gpu/drm/sun4i/sun4i_hdmi_enc.c|   2 +-
 drivers/gpu/drm/tegra/Kconfig |   1 +
 drivers/gpu/drm/tegra/hdmi.c  |   1 +
 drivers/gpu/drm/tegra/sor.c   |   1 +
 drivers/gpu/drm/vc4/Kconfig   |   1 +
 drivers/gpu/drm/vc4/vc4_hdmi.c|   2 +-
 include/drm/display/drm_hdmi_helper.h |  36 ++
 include/drm/drm_connector.h   |   2 -
 include/drm/drm_edid.h|  31 +-
 51 files changed, 572 insertions(+), 507 deletions(-)
 create mode 100644 drivers/gpu/drm/display/drm_hdmi_helper.c
 create mode 100644 drivers/gpu/drm/hdmi/Makefile
 create mode 100644 include/drm/display/drm_hdmi_helper.h

diff --git a/drivers/gpu/drm/Kconfig b/drivers/gpu/drm/Kconfig
index 5cc5fc0d386d..c306a09aed81 100644
--- a/drivers/gpu/drm/Kconfig
+++ b/drivers/gpu/drm/Kconfig
@@ -102,6 +102,13 @@ config DRM_HDCP_HELPER
help
  DRM helpers for HDCP.
 
+config DRM_HDMI_HELPER
+   tristate
+   depends on DRM
+   select DRM_DISPLAY_HELPER
+   help
+ DRM helpers for HDMI.
+
 config DRM_KMS_HELPER
tristate
depends on DRM
@@ -265,6 +272,7 @@ config DRM_RADEON
depends on AGP || !AGP
select FW_LOADER
select DRM_DP_HELPER
+   select DRM_HDMI_HELPER
 select DRM_KMS_HELPER
 select DRM_TTM
select DRM_TTM_HELPER
@@ -285,6 +293,7 @@ config DRM_AMDGPU
tristate "AMD GPU"
depends on DRM && PCI && MMU
select FW_LOADER
+   select DRM_HDMI_HELPER
select DRM_DP_HELPER
select DRM_KMS_HELPER
select DRM_SCHED
diff --git a/drivers/gpu/drm/amd/amdgpu/dce_v10_0.c 
b/drivers/gpu/drm/amd/amdgpu/dce_v10_0.c
index 288fce7dc0ed..a7fe477a0aef 100644
--- a/drivers/gpu/drm/amd/amdgpu/dce_v10_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/dce_v10_0.c
@@ -21,6 +21,7 @@
  *
  */
 
+#include 
 #include 
 #include 
 
diff --git a/drivers/gpu/drm/amd/amdgpu/dce_v11_0.c 
b/drivers/gpu/drm/amd/amdgpu/dce_v11_0.c
index cbe5250b31cb..67c28464 100644
--- a/drivers/gpu/drm/amd/amdgpu/dce_v11_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/dce_v11_0.c
@@ -21,6 +21,7 @@
  *
  */
 
+#include 
 #include 
 #includ

[PATCH 4/8] drm/display: Split DisplayPort header into core and helper

2022-03-22 Thread Thomas Zimmermann
Move DisplayPort protocol constants and structures into the new
header drm_dp.h, which can be used by DRM core components. The
existing header drm_dp_helper.h now only contains helper code for
graphics drivers. No functional changes.

Signed-off-by: Thomas Zimmermann 
---
 Documentation/gpu/drm-kms-helpers.rst |3 +
 include/drm/display/drm_dp.h  | 1688 +
 include/drm/display/drm_dp_helper.h   | 1662 +---
 3 files changed, 1693 insertions(+), 1660 deletions(-)
 create mode 100644 include/drm/display/drm_dp.h

diff --git a/Documentation/gpu/drm-kms-helpers.rst 
b/Documentation/gpu/drm-kms-helpers.rst
index 2584f5bff66f..09463ee99730 100644
--- a/Documentation/gpu/drm-kms-helpers.rst
+++ b/Documentation/gpu/drm-kms-helpers.rst
@@ -235,6 +235,9 @@ Display Port Helper Functions Reference
 .. kernel-doc:: drivers/gpu/drm/display/drm_dp_helper.c
:doc: dp helpers
 
+.. kernel-doc:: include/drm/display/drm_dp.h
+   :internal:
+
 .. kernel-doc:: include/drm/display/drm_dp_helper.h
:internal:
 
diff --git a/include/drm/display/drm_dp.h b/include/drm/display/drm_dp.h
new file mode 100644
index ..3c937f8bdb42
--- /dev/null
+++ b/include/drm/display/drm_dp.h
@@ -0,0 +1,1688 @@
+/*
+ * Copyright © 2008 Keith Packard
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that copyright
+ * notice and this permission notice appear in supporting documentation, and
+ * that the name of the copyright holders not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission.  The copyright holders make no representations
+ * about the suitability of this software for any purpose.  It is provided "as
+ * is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
+ * OF THIS SOFTWARE.
+ */
+
+#ifndef _DRM_DP_H_
+#define _DRM_DP_H_
+
+#include 
+
+/*
+ * Unless otherwise noted, all values are from the DP 1.1a spec.  Note that
+ * DP and DPCD versions are independent.  Differences from 1.0 are not noted,
+ * 1.0 devices basically don't exist in the wild.
+ *
+ * Abbreviations, in chronological order:
+ *
+ * eDP: Embedded DisplayPort version 1
+ * DPI: DisplayPort Interoperability Guideline v1.1a
+ * 1.2: DisplayPort 1.2
+ * MST: Multistream Transport - part of DP 1.2a
+ *
+ * 1.2 formally includes both eDP and DPI definitions.
+ */
+
+/* MSA (Main Stream Attribute) MISC bits (as MISC1<<8|MISC0) */
+#define DP_MSA_MISC_SYNC_CLOCK (1 << 0)
+#define DP_MSA_MISC_INTERLACE_VTOTAL_EVEN  (1 << 8)
+#define DP_MSA_MISC_STEREO_NO_3D   (0 << 9)
+#define DP_MSA_MISC_STEREO_PROG_RIGHT_EYE  (1 << 9)
+#define DP_MSA_MISC_STEREO_PROG_LEFT_EYE   (3 << 9)
+/* bits per component for non-RAW */
+#define DP_MSA_MISC_6_BPC  (0 << 5)
+#define DP_MSA_MISC_8_BPC  (1 << 5)
+#define DP_MSA_MISC_10_BPC (2 << 5)
+#define DP_MSA_MISC_12_BPC (3 << 5)
+#define DP_MSA_MISC_16_BPC (4 << 5)
+/* bits per component for RAW */
+#define DP_MSA_MISC_RAW_6_BPC  (1 << 5)
+#define DP_MSA_MISC_RAW_7_BPC  (2 << 5)
+#define DP_MSA_MISC_RAW_8_BPC  (3 << 5)
+#define DP_MSA_MISC_RAW_10_BPC (4 << 5)
+#define DP_MSA_MISC_RAW_12_BPC (5 << 5)
+#define DP_MSA_MISC_RAW_14_BPC (6 << 5)
+#define DP_MSA_MISC_RAW_16_BPC (7 << 5)
+/* pixel encoding/colorimetry format */
+#define _DP_MSA_MISC_COLOR(misc1_7, misc0_21, misc0_3, misc0_4) \
+   ((misc1_7) << 15 | (misc0_4) << 4 | (misc0_3) << 3 | ((misc0_21) << 1))
+#define DP_MSA_MISC_COLOR_RGB  _DP_MSA_MISC_COLOR(0, 0, 0, 0)
+#define DP_MSA_MISC_COLOR_CEA_RGB  _DP_MSA_MISC_COLOR(0, 0, 1, 0)
+#define DP_MSA_MISC_COLOR_RGB_WIDE_FIXED   _DP_MSA_MISC_COLOR(0, 3, 0, 0)
+#define DP_MSA_MISC_COLOR_RGB_WIDE_FLOAT   _DP_MSA_MISC_COLOR(0, 3, 0, 1)
+#define DP_MSA_MISC_COLOR_Y_ONLY   _DP_MSA_MISC_COLOR(1, 0, 0, 0)
+#define DP_MSA_MISC_COLOR_RAW  _DP_MSA_MISC_COLOR(1, 1, 0, 0)
+#define DP_MSA_MISC_COLOR_YCBCR_422_BT601  _DP_MSA_MISC_COLOR(0, 1, 1, 0)
+#define DP_MSA_MISC_COLOR_YCBCR_422_BT709  _DP_MSA_MISC_COLOR(0, 1, 1, 1)
+#define DP_MSA_MISC_COLOR_YCBCR_444_BT601  _DP

[PATCH 5/8] drm/display: Move DSC header and helpers into display-helper module

2022-03-22 Thread Thomas Zimmermann
DSC is the Display Stream Compression standard for DisplayPort. Move
the DSC code into display/ and split the header into files for protocol
core and DRM helpers. Adapt all users of the code. No functional
changes.

To avoid the proliferation of Kconfig options, DSC is part of DRM's
support for DisplayPort. If necessary, a new option could make DSC an
independent feature.

Signed-off-by: Thomas Zimmermann 
---
 Documentation/gpu/drm-kms-helpers.rst |  6 +++---
 drivers/gpu/drm/Makefile  |  2 +-
 .../gpu/drm/amd/display/dc/dcn20/dcn20_dsc.c  |  2 ++
 .../gpu/drm/amd/display/dc/dcn20/dcn20_dsc.h  |  2 +-
 .../drm/amd/display/dc/dml/dsc/rc_calc_fpu.h  |  2 +-
 drivers/gpu/drm/amd/display/dc/dsc/dc_dsc.c   |  4 ++--
 .../gpu/drm/amd/display/dc/dsc/dscc_types.h   |  2 +-
 .../gpu/drm/amd/display/dc/dsc/rc_calc_dpi.c  |  2 +-
 drivers/gpu/drm/display/Makefile  |  3 ++-
 .../{drm_dsc.c => display/drm_dsc_helper.c}   |  2 +-
 drivers/gpu/drm/drm_mipi_dsi.c|  6 +++---
 drivers/gpu/drm/i915/display/icl_dsi.c|  1 +
 drivers/gpu/drm/i915/display/intel_bios.c |  1 +
 .../drm/i915/display/intel_display_types.h|  2 +-
 drivers/gpu/drm/i915/display/intel_dp.c   |  1 +
 .../gpu/drm/i915/display/intel_qp_tables.c|  2 +-
 drivers/gpu/drm/i915/display/intel_vdsc.c |  2 ++
 include/drm/{ => display}/drm_dsc.h   |  8 +---
 include/drm/display/drm_dsc_helper.h  | 20 +++
 19 files changed, 46 insertions(+), 24 deletions(-)
 rename drivers/gpu/drm/{drm_dsc.c => display/drm_dsc_helper.c} (99%)
 rename include/drm/{ => display}/drm_dsc.h (97%)
 create mode 100644 include/drm/display/drm_dsc_helper.h

diff --git a/Documentation/gpu/drm-kms-helpers.rst 
b/Documentation/gpu/drm-kms-helpers.rst
index 09463ee99730..7af55fb4072c 100644
--- a/Documentation/gpu/drm-kms-helpers.rst
+++ b/Documentation/gpu/drm-kms-helpers.rst
@@ -326,13 +326,13 @@ MIPI DSI Helper Functions Reference
 Display Stream Compression Helper Functions Reference
 =
 
-.. kernel-doc:: drivers/gpu/drm/drm_dsc.c
+.. kernel-doc:: drivers/gpu/drm/display/drm_dsc_helper.c
:doc: dsc helpers
 
-.. kernel-doc:: include/drm/drm_dsc.h
+.. kernel-doc:: include/drm/display/drm_dsc.h
:internal:
 
-.. kernel-doc:: drivers/gpu/drm/drm_dsc.c
+.. kernel-doc:: drivers/gpu/drm/display/drm_dsc_helper.c
:export:
 
 Output Probing Helper Functions Reference
diff --git a/drivers/gpu/drm/Makefile b/drivers/gpu/drm/Makefile
index 07f7a70a78ea..b8353af70152 100644
--- a/drivers/gpu/drm/Makefile
+++ b/drivers/gpu/drm/Makefile
@@ -58,7 +58,7 @@ obj-$(CONFIG_DRM_TTM_HELPER) += drm_ttm_helper.o
 #
 
 drm_kms_helper-y := drm_bridge_connector.o drm_crtc_helper.o \
-   drm_dsc.o drm_encoder_slave.o drm_flip_work.o drm_hdcp.o \
+   drm_encoder_slave.o drm_flip_work.o drm_hdcp.o \
drm_probe_helper.o \
drm_plane_helper.o drm_atomic_helper.o \
drm_kms_helper_common.o \
diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dsc.c 
b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dsc.c
index ef5c4c0f4d6c..6f24ceab97ad 100644
--- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dsc.c
+++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dsc.c
@@ -23,6 +23,8 @@
  *
  */
 
+#include 
+
 #include "reg_helper.h"
 #include "dcn20_dsc.h"
 #include "dsc/dscc_types.h"
diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dsc.h 
b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dsc.h
index 1118e33aaa2c..c21ecedc4692 100644
--- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dsc.h
+++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dsc.h
@@ -26,7 +26,7 @@
 
 #include "dsc.h"
 #include "dsc/dscc_types.h"
-#include 
+#include 
 
 #define TO_DCN20_DSC(dsc)\
container_of(dsc, struct dcn20_dsc, base)
diff --git a/drivers/gpu/drm/amd/display/dc/dml/dsc/rc_calc_fpu.h 
b/drivers/gpu/drm/amd/display/dc/dml/dsc/rc_calc_fpu.h
index cad244c023cd..d7cd8cc24758 100644
--- a/drivers/gpu/drm/amd/display/dc/dml/dsc/rc_calc_fpu.h
+++ b/drivers/gpu/drm/amd/display/dc/dml/dsc/rc_calc_fpu.h
@@ -27,7 +27,7 @@
 #define __RC_CALC_FPU_H__
 
 #include "os_types.h"
-#include 
+#include 
 
 #define QP_SET_SIZE 15
 
diff --git a/drivers/gpu/drm/amd/display/dc/dsc/dc_dsc.c 
b/drivers/gpu/drm/amd/display/dc/dsc/dc_dsc.c
index 411b79979e2e..8da28bcfac7e 100644
--- a/drivers/gpu/drm/amd/display/dc/dsc/dc_dsc.c
+++ b/drivers/gpu/drm/amd/display/dc/dsc/dc_dsc.c
@@ -22,10 +22,10 @@
  * Author: AMD
  */
 
-#include 
+#include 
+#include 
 #include "dc_hw_types.h"
 #include "dsc.h"
-#include 
 #include "dc.h"
 #include "rc_calc.h"
 #include "fixed31_32.h"
diff --git a/drivers/gpu/drm/amd/display/dc/dsc/dscc_types.h 
b/drivers/gpu/drm/amd/display/dc/dsc/dscc_types.h
index 9f70e87b3ecb..ad80bde9bc0f 100644
--- a/drivers/gpu/drm/amd/display/dc/dsc/dscc_types.h
+++ b/drivers/gpu/drm/amd/display/dc/dsc/dscc_types.h
@@ -26

[PATCH 8/8] drm/display: Move SCDC helpers into display-helper library

2022-03-22 Thread Thomas Zimmermann
SCDC is the Status and Control Data Channel for HDMI. Move the SCDC
helpers into display/ and split the header into files for core and
helpers. Update all affected drivers. No functional changes.

To avoid the proliferation of Kconfig options, SCDC is part of DRM's
support for HDMI. If necessary, a new option could make SCDC an
independent feature.

Signed-off-by: Thomas Zimmermann 
---
 Documentation/gpu/drm-kms-helpers.rst |  6 +-
 drivers/gpu/drm/Makefile  |  2 +-
 drivers/gpu/drm/bridge/synopsys/dw-hdmi.c |  2 +-
 drivers/gpu/drm/display/Makefile  |  2 +-
 .../gpu/drm/{ => display}/drm_scdc_helper.c   |  3 +-
 drivers/gpu/drm/drm_edid.c|  1 -
 drivers/gpu/drm/i915/display/intel_ddi.c  |  2 +-
 drivers/gpu/drm/i915/display/intel_hdmi.c |  2 +-
 drivers/gpu/drm/nouveau/dispnv50/disp.c   |  2 +-
 drivers/gpu/drm/tegra/sor.c   |  2 +-
 drivers/gpu/drm/vc4/vc4_hdmi.c|  2 +-
 .../{drm_scdc_helper.h => display/drm_scdc.h} | 52 +---
 include/drm/display/drm_scdc_helper.h | 79 +++
 13 files changed, 94 insertions(+), 63 deletions(-)
 rename drivers/gpu/drm/{ => display}/drm_scdc_helper.c (99%)
 rename include/drm/{drm_scdc_helper.h => display/drm_scdc.h} (65%)
 create mode 100644 include/drm/display/drm_scdc_helper.h

diff --git a/Documentation/gpu/drm-kms-helpers.rst 
b/Documentation/gpu/drm-kms-helpers.rst
index cfda5a092a48..2d473bc64c9f 100644
--- a/Documentation/gpu/drm-kms-helpers.rst
+++ b/Documentation/gpu/drm-kms-helpers.rst
@@ -356,13 +356,13 @@ EDID Helper Functions Reference
 SCDC Helper Functions Reference
 ===
 
-.. kernel-doc:: drivers/gpu/drm/drm_scdc_helper.c
+.. kernel-doc:: drivers/gpu/drm/display/drm_scdc_helper.c
:doc: scdc helpers
 
-.. kernel-doc:: include/drm/drm_scdc_helper.h
+.. kernel-doc:: include/drm/display/drm_scdc_helper.h
:internal:
 
-.. kernel-doc:: drivers/gpu/drm/drm_scdc_helper.c
+.. kernel-doc:: drivers/gpu/drm/display/drm_scdc_helper.c
:export:
 
 HDMI Infoframes Helper Reference
diff --git a/drivers/gpu/drm/Makefile b/drivers/gpu/drm/Makefile
index 746a3a4953f3..15fe3163f822 100644
--- a/drivers/gpu/drm/Makefile
+++ b/drivers/gpu/drm/Makefile
@@ -63,7 +63,7 @@ drm_kms_helper-y := drm_bridge_connector.o drm_crtc_helper.o \
drm_plane_helper.o drm_atomic_helper.o \
drm_kms_helper_common.o \
drm_simple_kms_helper.o drm_modeset_helper.o \
-   drm_scdc_helper.o drm_gem_atomic_helper.o \
+   drm_gem_atomic_helper.o \
drm_gem_framebuffer_helper.o \
drm_atomic_state_helper.o drm_damage_helper.o \
drm_format_helper.o drm_self_refresh_helper.o drm_rect.o
diff --git a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c 
b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c
index a06a2d51e77f..268d1f47d58c 100644
--- a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c
+++ b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c
@@ -26,13 +26,13 @@
 
 #include 
 #include 
+#include 
 #include 
 #include 
 #include 
 #include 
 #include 
 #include 
-#include 
 
 #include "dw-hdmi-audio.h"
 #include "dw-hdmi-cec.h"
diff --git a/drivers/gpu/drm/display/Makefile b/drivers/gpu/drm/display/Makefile
index dfe21583afa0..4a36847b4aaf 100644
--- a/drivers/gpu/drm/display/Makefile
+++ b/drivers/gpu/drm/display/Makefile
@@ -8,6 +8,6 @@ drm_display_helper-$(CONFIG_DRM_DP_HELPER) := drm_dp_helper.o 
drm_dp_dual_mode_h
 drm_display_helper-$(CONFIG_DRM_DP_AUX_CHARDEV) += drm_dp_aux_dev.o
 drm_display_helper-$(CONFIG_DRM_DP_CEC) += drm_dp_cec.o
 drm_display_helper-$(CONFIG_DRM_HDCP_HELPER) += drm_hdcp_helper.o
-drm_display_helper-$(CONFIG_DRM_HDMI_HELPER) += drm_hdmi_helper.o
+drm_display_helper-$(CONFIG_DRM_HDMI_HELPER) += drm_hdmi_helper.o 
drm_scdc_helper.o
 
 obj-$(CONFIG_DRM_DISPLAY_HELPER) += drm_display_helper.o
diff --git a/drivers/gpu/drm/drm_scdc_helper.c 
b/drivers/gpu/drm/display/drm_scdc_helper.c
similarity index 99%
rename from drivers/gpu/drm/drm_scdc_helper.c
rename to drivers/gpu/drm/display/drm_scdc_helper.c
index 48a382464d54..81881e81ceae 100644
--- a/drivers/gpu/drm/drm_scdc_helper.c
+++ b/drivers/gpu/drm/display/drm_scdc_helper.c
@@ -21,11 +21,12 @@
  * DEALINGS IN THE SOFTWARE.
  */
 
+#include 
 #include 
 #include 
 
+#include 
 #include 
-#include 
 
 /**
  * DOC: scdc helpers
diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index 4d865ebcd623..cf15690d4a83 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -42,7 +42,6 @@
 #include 
 #include 
 #include 
-#include 
 
 #include "drm_crtc_internal.h"
 
diff --git a/drivers/gpu/drm/i915/display/intel_ddi.c 
b/drivers/gpu/drm/i915/display/intel_ddi.c
index dc208df829f1..563c3f1c49a1 100644
--- a/drivers/gpu/drm/i915/display/intel_ddi.c
+++ b/drivers/gpu/drm/i915/display/intel_ddi.c
@@ -27,8 +27,8 @@
 
 #include 
 
+#include 
 #incl

[PATCH 6/8] drm/display: Move HDCP helpers into display-helper module

2022-03-22 Thread Thomas Zimmermann
Move DRM's HDCP helper library into the display/ subdirectory and add
it to DRM's display helpers. Split the header file into core and helpers.
Update all affected drivers. No functional changes.

Signed-off-by: Thomas Zimmermann 
---
 Documentation/gpu/drm-kms-helpers.rst |  2 +-
 drivers/gpu/drm/Kconfig   |  7 ++
 drivers/gpu/drm/Makefile  |  2 +-
 drivers/gpu/drm/amd/display/Kconfig   |  1 +
 .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c |  2 +-
 .../amd/display/amdgpu_dm/amdgpu_dm_hdcp.c|  2 +-
 .../gpu/drm/amd/display/modules/hdcp/hdcp.h   |  2 +-
 drivers/gpu/drm/bridge/Kconfig|  1 +
 drivers/gpu/drm/bridge/analogix/Kconfig   |  1 +
 drivers/gpu/drm/bridge/analogix/anx7625.c |  2 +-
 drivers/gpu/drm/bridge/cadence/Kconfig|  1 +
 .../drm/bridge/cadence/cdns-mhdp8546-core.c   |  2 +-
 .../drm/bridge/cadence/cdns-mhdp8546-hdcp.c   |  2 +-
 drivers/gpu/drm/bridge/ite-it6505.c   |  2 +-
 drivers/gpu/drm/display/Makefile  |  1 +
 .../{drm_hdcp.c => display/drm_hdcp_helper.c} |  4 ++--
 drivers/gpu/drm/i915/Kconfig  |  1 +
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c  |  2 +-
 drivers/gpu/drm/i915/display/intel_gmbus.c|  2 +-
 drivers/gpu/drm/i915/display/intel_hdcp.c |  2 +-
 drivers/gpu/drm/i915/display/intel_hdmi.c |  2 +-
 drivers/misc/mei/hdcp/mei_hdcp.h  |  2 +-
 include/drm/{ => display}/drm_hdcp.h  | 14 ++--
 include/drm/display/drm_hdcp_helper.h | 22 +++
 include/drm/i915_mei_hdcp_interface.h |  2 +-
 25 files changed, 54 insertions(+), 29 deletions(-)
 rename drivers/gpu/drm/{drm_hdcp.c => display/drm_hdcp_helper.c} (99%)
 rename include/drm/{ => display}/drm_hdcp.h (95%)
 create mode 100644 include/drm/display/drm_hdcp_helper.h

diff --git a/Documentation/gpu/drm-kms-helpers.rst 
b/Documentation/gpu/drm-kms-helpers.rst
index 7af55fb4072c..cfda5a092a48 100644
--- a/Documentation/gpu/drm-kms-helpers.rst
+++ b/Documentation/gpu/drm-kms-helpers.rst
@@ -226,7 +226,7 @@ Panel Self Refresh Helper Reference
 HDCP Helper Functions Reference
 ===
 
-.. kernel-doc:: drivers/gpu/drm/drm_hdcp.c
+.. kernel-doc:: drivers/gpu/drm/display/drm_hdcp_helper.c
:export:
 
 Display Port Helper Functions Reference
diff --git a/drivers/gpu/drm/Kconfig b/drivers/gpu/drm/Kconfig
index bffcd4d2314b..5cc5fc0d386d 100644
--- a/drivers/gpu/drm/Kconfig
+++ b/drivers/gpu/drm/Kconfig
@@ -95,6 +95,13 @@ config DRM_DP_HELPER
help
  DRM helpers for DisplayPort.
 
+config DRM_HDCP_HELPER
+   tristate
+   depends on DRM
+   select DRM_DISPLAY_HELPER
+   help
+ DRM helpers for HDCP.
+
 config DRM_KMS_HELPER
tristate
depends on DRM
diff --git a/drivers/gpu/drm/Makefile b/drivers/gpu/drm/Makefile
index b8353af70152..746a3a4953f3 100644
--- a/drivers/gpu/drm/Makefile
+++ b/drivers/gpu/drm/Makefile
@@ -58,7 +58,7 @@ obj-$(CONFIG_DRM_TTM_HELPER) += drm_ttm_helper.o
 #
 
 drm_kms_helper-y := drm_bridge_connector.o drm_crtc_helper.o \
-   drm_encoder_slave.o drm_flip_work.o drm_hdcp.o \
+   drm_encoder_slave.o drm_flip_work.o \
drm_probe_helper.o \
drm_plane_helper.o drm_atomic_helper.o \
drm_kms_helper_common.o \
diff --git a/drivers/gpu/drm/amd/display/Kconfig 
b/drivers/gpu/drm/amd/display/Kconfig
index 127667e549c1..2264245c42de 100644
--- a/drivers/gpu/drm/amd/display/Kconfig
+++ b/drivers/gpu/drm/amd/display/Kconfig
@@ -20,6 +20,7 @@ config DRM_AMD_DC_DCN
 config DRM_AMD_DC_HDCP
bool "Enable HDCP support in DC"
depends on DRM_AMD_DC
+   select DRM_HDCP_HELPER
help
  Choose this option if you want to support HDCP authentication.
 
diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c 
b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
index 4473ac43e5f5..ca42b7274372 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
@@ -48,7 +48,7 @@
 #include "amdgpu_dm.h"
 #ifdef CONFIG_DRM_AMD_DC_HDCP
 #include "amdgpu_dm_hdcp.h"
-#include 
+#include 
 #endif
 #include "amdgpu_pm.h"
 #include "amdgpu_atombios.h"
diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_hdcp.c 
b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_hdcp.c
index bf0d50277f8f..15c0e3f2a9c3 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_hdcp.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_hdcp.c
@@ -27,7 +27,7 @@
 #include "amdgpu.h"
 #include "amdgpu_dm.h"
 #include "dm_helpers.h"
-#include 
+#include 
 #include "hdcp_psp.h"
 
 /*
diff --git a/drivers/gpu/drm/amd/display/modules/hdcp/hdcp.h 
b/drivers/gpu/drm/amd/display/modules/hdcp/hdcp.h
index 6e88705e22f7..392c0c03365a 100644
--- a/drivers/gpu/drm/amd/display/modules/hdcp/hdcp.h
+++ b/drivers/gpu/drm/amd/display/modules/hdcp/h

[PATCH 2/8] drm: Rename dp/ to display/

2022-03-22 Thread Thomas Zimmermann
Rename dp/ to display/ to account for additional display-related
helpers, such as HDMI. Update all related include statements. No
functional changes.

Various drivers, such as i915 and amdgpu, use similar naming scheme
by putting code for video-output standards into a local display/
directory. The new directory's name is aligned with that policy.

Signed-off-by: Thomas Zimmermann 
---
 Documentation/gpu/drm-kms-helpers.rst | 26 +--
 drivers/gpu/drm/Makefile  |  2 +-
 .../gpu/drm/amd/amdgpu/amdgpu_connectors.c|  2 +-
 drivers/gpu/drm/amd/amdgpu/amdgpu_mode.h  |  4 +--
 drivers/gpu/drm/amd/amdgpu/atombios_dp.c  |  3 ++-
 .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c |  2 +-
 .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h |  2 +-
 .../display/amdgpu_dm/amdgpu_dm_mst_types.c   |  4 +--
 .../drm/amd/display/dc/core/dc_link_dpcd.c|  2 +-
 drivers/gpu/drm/amd/display/dc/dsc/dc_dsc.c   |  2 +-
 drivers/gpu/drm/amd/display/dc/os_types.h |  2 +-
 .../gpu/drm/amd/display/include/dpcd_defs.h   |  2 +-
 .../gpu/drm/amd/display/modules/hdcp/hdcp.h   |  2 +-
 .../drm/bridge/analogix/analogix-anx6345.c|  2 +-
 .../drm/bridge/analogix/analogix-anx78xx.c|  2 +-
 .../drm/bridge/analogix/analogix-i2c-dptx.c   |  2 +-
 .../drm/bridge/analogix/analogix_dp_core.h|  2 +-
 drivers/gpu/drm/bridge/analogix/anx7625.c |  4 +--
 .../drm/bridge/cadence/cdns-mhdp8546-core.c   |  2 +-
 .../drm/bridge/cadence/cdns-mhdp8546-core.h   |  2 +-
 drivers/gpu/drm/bridge/ite-it6505.c   |  2 +-
 drivers/gpu/drm/bridge/parade-ps8640.c|  4 +--
 drivers/gpu/drm/bridge/tc358767.c |  2 +-
 drivers/gpu/drm/bridge/tc358775.c |  2 +-
 drivers/gpu/drm/bridge/ti-sn65dsi86.c |  4 +--
 drivers/gpu/drm/{dp => display}/Makefile  |  0
 drivers/gpu/drm/{dp => display}/drm_dp.c  |  4 +--
 .../gpu/drm/{dp => display}/drm_dp_aux_bus.c  |  4 +--
 .../gpu/drm/{dp => display}/drm_dp_aux_dev.c  |  4 +--
 drivers/gpu/drm/{dp => display}/drm_dp_cec.c  |  2 +-
 .../{dp => display}/drm_dp_dual_mode_helper.c |  2 +-
 .../{dp => display}/drm_dp_helper_internal.h  |  0
 .../drm/{dp => display}/drm_dp_helper_mod.c   |  0
 .../drm/{dp => display}/drm_dp_mst_topology.c |  2 +-
 .../drm_dp_mst_topology_internal.h|  2 +-
 drivers/gpu/drm/drm_dsc.c |  3 ++-
 drivers/gpu/drm/gma500/cdv_intel_dp.c |  2 +-
 drivers/gpu/drm/gma500/intel_bios.c   |  3 ++-
 drivers/gpu/drm/i915/display/intel_bios.c |  2 +-
 drivers/gpu/drm/i915/display/intel_display.c  |  2 +-
 .../drm/i915/display/intel_display_types.h|  4 +--
 drivers/gpu/drm/i915/display/intel_dp.c   |  2 +-
 drivers/gpu/drm/i915/display/intel_dp_hdcp.c  |  4 +--
 .../drm/i915/display/intel_dp_link_training.h |  2 +-
 drivers/gpu/drm/i915/display/intel_lspcon.c   |  2 +-
 drivers/gpu/drm/msm/dp/dp_audio.c |  2 +-
 drivers/gpu/drm/msm/dp/dp_aux.h   |  2 +-
 drivers/gpu/drm/msm/dp/dp_catalog.c   |  2 +-
 drivers/gpu/drm/msm/dp/dp_ctrl.c  |  3 ++-
 drivers/gpu/drm/msm/edp/edp.h |  3 ++-
 drivers/gpu/drm/msm/edp/edp_ctrl.c|  3 ++-
 drivers/gpu/drm/nouveau/dispnv50/disp.c   |  2 +-
 drivers/gpu/drm/nouveau/nouveau_connector.h   |  2 +-
 drivers/gpu/drm/nouveau/nouveau_dp.c  |  2 +-
 drivers/gpu/drm/nouveau/nouveau_encoder.h |  6 +++--
 drivers/gpu/drm/panel/panel-edp.c |  4 +--
 .../gpu/drm/panel/panel-samsung-atna33xc20.c  |  4 +--
 drivers/gpu/drm/radeon/atombios_dp.c  |  2 +-
 drivers/gpu/drm/radeon/radeon_connectors.c|  2 +-
 drivers/gpu/drm/radeon/radeon_dp_mst.c|  2 +-
 drivers/gpu/drm/radeon/radeon_mode.h  |  4 +--
 .../gpu/drm/rockchip/analogix_dp-rockchip.c   |  2 +-
 drivers/gpu/drm/rockchip/cdn-dp-core.c|  2 +-
 drivers/gpu/drm/rockchip/cdn-dp-core.h|  2 +-
 drivers/gpu/drm/rockchip/rockchip_lvds.c  |  2 +-
 drivers/gpu/drm/rockchip/rockchip_rgb.c   |  2 +-
 .../drm/selftests/test-drm_dp_mst_helper.c|  4 +--
 drivers/gpu/drm/tegra/dp.c|  2 +-
 drivers/gpu/drm/tegra/dpaux.c |  4 +--
 drivers/gpu/drm/tegra/sor.c   |  2 +-
 drivers/gpu/drm/xlnx/zynqmp_dp.c  |  2 +-
 include/drm/{dp => display}/drm_dp_aux_bus.h  |  0
 .../{dp => display}/drm_dp_dual_mode_helper.h |  0
 include/drm/{dp => display}/drm_dp_helper.h   |  0
 .../drm/{dp => display}/drm_dp_mst_helper.h   |  2 +-
 include/drm/drm_dsc.h |  2 +-
 76 files changed, 106 insertions(+), 98 deletions(-)
 rename drivers/gpu/drm/{dp => display}/Makefile (100%)
 rename drivers/gpu/drm/{dp => display}/drm_dp.c (99%)
 rename drivers/gpu/drm/{dp => display}/drm_dp_aux_bus.c (99%)
 rename drivers/gpu/drm/{dp => display}/drm_dp_aux_dev.c (99%)
 rename drivers/gpu/drm/{dp => display}/drm_dp_cec.c (99%)
 rename drivers/gpu/drm/{dp => display}/drm_dp_dual_mode_h

[PATCH 3/8] drm/display: Introduce a DRM display-helper module

2022-03-22 Thread Thomas Zimmermann
Replace the DP-helper module with a display-helper module. Update
all related Kconfig and Makefile rules.

Besides the existing code for DisplayPort, the new module will
contain helpers for other video-output standards, such as HDMI.
Drivers will still be able to select the required video-output
helpers. Linking all such code into a single module avoids the
proliferation of small kernel modules.

Signed-off-by: Thomas Zimmermann 
---
 drivers/gpu/drm/Kconfig|  7 +++
 drivers/gpu/drm/display/Makefile   |  9 +
 .../{drm_dp_helper_mod.c => drm_display_helper_mod.c}  | 10 +-
 drivers/gpu/drm/display/{drm_dp.c => drm_dp_helper.c}  |  0
 4 files changed, 17 insertions(+), 9 deletions(-)
 rename drivers/gpu/drm/display/{drm_dp_helper_mod.c => 
drm_display_helper_mod.c} (51%)
 rename drivers/gpu/drm/display/{drm_dp.c => drm_dp_helper.c} (100%)

diff --git a/drivers/gpu/drm/Kconfig b/drivers/gpu/drm/Kconfig
index f1422bee3dcc..bffcd4d2314b 100644
--- a/drivers/gpu/drm/Kconfig
+++ b/drivers/gpu/drm/Kconfig
@@ -82,9 +82,16 @@ config DRM_DEBUG_SELFTEST
 
  If in doubt, say "N".
 
+config DRM_DISPLAY_HELPER
+   tristate
+   depends on DRM
+   help
+ DRM helpers for display adapters.
+
 config DRM_DP_HELPER
tristate
depends on DRM
+   select DRM_DISPLAY_HELPER
help
  DRM helpers for DisplayPort.
 
diff --git a/drivers/gpu/drm/display/Makefile b/drivers/gpu/drm/display/Makefile
index 75faffc706b1..90f12e9b4735 100644
--- a/drivers/gpu/drm/display/Makefile
+++ b/drivers/gpu/drm/display/Makefile
@@ -2,8 +2,9 @@
 
 obj-$(CONFIG_DRM_DP_AUX_BUS) += drm_dp_aux_bus.o
 
-drm_dp_helper-y := drm_dp.o drm_dp_dual_mode_helper.o drm_dp_helper_mod.o 
drm_dp_mst_topology.o
-drm_dp_helper-$(CONFIG_DRM_DP_AUX_CHARDEV) += drm_dp_aux_dev.o
-drm_dp_helper-$(CONFIG_DRM_DP_CEC) += drm_dp_cec.o
+drm_display_helper-y := drm_display_helper_mod.o
+drm_display_helper-$(CONFIG_DRM_DP_HELPER) := drm_dp_helper.o 
drm_dp_dual_mode_helper.o drm_dp_mst_topology.o
+drm_display_helper-$(CONFIG_DRM_DP_AUX_CHARDEV) += drm_dp_aux_dev.o
+drm_display_helper-$(CONFIG_DRM_DP_CEC) += drm_dp_cec.o
 
-obj-$(CONFIG_DRM_DP_HELPER) += drm_dp_helper.o
+obj-$(CONFIG_DRM_DISPLAY_HELPER) += drm_display_helper.o
diff --git a/drivers/gpu/drm/display/drm_dp_helper_mod.c 
b/drivers/gpu/drm/display/drm_display_helper_mod.c
similarity index 51%
rename from drivers/gpu/drm/display/drm_dp_helper_mod.c
rename to drivers/gpu/drm/display/drm_display_helper_mod.c
index db753de24000..d8a6e6228773 100644
--- a/drivers/gpu/drm/display/drm_dp_helper_mod.c
+++ b/drivers/gpu/drm/display/drm_display_helper_mod.c
@@ -4,19 +4,19 @@
 
 #include "drm_dp_helper_internal.h"
 
-MODULE_DESCRIPTION("DRM DisplayPort helper");
+MODULE_DESCRIPTION("DRM display adapter helper");
 MODULE_LICENSE("GPL and additional rights");
 
-static int __init drm_dp_helper_module_init(void)
+static int __init drm_display_helper_module_init(void)
 {
return drm_dp_aux_dev_init();
 }
 
-static void __exit drm_dp_helper_module_exit(void)
+static void __exit drm_display_helper_module_exit(void)
 {
/* Call exit functions from specific dp helpers here */
drm_dp_aux_dev_exit();
 }
 
-module_init(drm_dp_helper_module_init);
-module_exit(drm_dp_helper_module_exit);
+module_init(drm_display_helper_module_init);
+module_exit(drm_display_helper_module_exit);
diff --git a/drivers/gpu/drm/display/drm_dp.c 
b/drivers/gpu/drm/display/drm_dp_helper.c
similarity index 100%
rename from drivers/gpu/drm/display/drm_dp.c
rename to drivers/gpu/drm/display/drm_dp_helper.c
-- 
2.35.1



Re: [PATCH 1/7] drm/gma500: Use managed drmm_mode_config_init()

2022-03-22 Thread Thomas Zimmermann

Hi Patrik

Am 22.03.22 um 14:17 schrieb Patrik Jakobsson:

Signed-off-by: Patrik Jakobsson 
---
  drivers/gpu/drm/gma500/framebuffer.c | 4 ++--
  1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/gma500/framebuffer.c 
b/drivers/gpu/drm/gma500/framebuffer.c
index 45df9de22007..2b99c996fdc2 100644
--- a/drivers/gpu/drm/gma500/framebuffer.c
+++ b/drivers/gpu/drm/gma500/framebuffer.c
@@ -514,7 +514,8 @@ void psb_modeset_init(struct drm_device *dev)
struct pci_dev *pdev = to_pci_dev(dev->dev);
int i;
  
-	drm_mode_config_init(dev);

+   if (drmm_mode_config_init(dev))
+   return;


This will fail without any notice. I suggest to return an error here or 
at let psb_driver_load() fail.


Best regards
Thomas

  
  	dev->mode_config.min_width = 0;

dev->mode_config.min_height = 0;
@@ -546,6 +547,5 @@ void psb_modeset_cleanup(struct drm_device *dev)
if (dev_priv->modeset) {
drm_kms_helper_poll_fini(dev);
psb_fbdev_fini(dev);
-   drm_mode_config_cleanup(dev);
}
  }


--
Thomas Zimmermann
Graphics Driver Developer
SUSE Software Solutions Germany GmbH
Maxfeldstr. 5, 90409 Nürnberg, Germany
(HRB 36809, AG Nürnberg)
Geschäftsführer: Ivo Totev


OpenPGP_signature
Description: OpenPGP digital signature


[GIT PULL] fbdev updates & fixes for v5.18-rc1

2022-03-22 Thread Helge Deller
Hello Linus,

please pull the latest fbdev updates and fixes for kernel 5.18-rc1.

This patchset has been in linux-next without any reported problems and
includes a lot of small fixes and code cleanups across many traditional
fbdev drivers.

Thanks!
Helge



The following changes since commit e783362eb54cd99b2cac8b3a9aeac942e6f6ac07:

  Linux 5.17-rc1 (2022-01-23 10:12:53 +0200)

are available in the Git repository at:

  http://git.kernel.org/pub/scm/linux/kernel/git/deller/linux-fbdev.git 
tags/for-5.18/fbdev-1

for you to fetch changes up to e445c8b2aa2df0e49f6037886c32d54a5e3960b1:

  video: fbdev: kyro: make read-only array ODValues static const (2022-03-11 
08:27:37 +0100)


fbdev fixes and updates for kernel v5.18-rc1

Lots of small fixes and code cleanups across most of the fbdev drivers.

This includes conversions to use helper functions, const conversions, spelling
fixes, help text updates, adding return value checks, small build fixes, and
much more.


Arnd Bergmann (1):
  agp: define proper stubs for empty helpers

Cai Huoqing (11):
  video: fbdev: au1200fb: Make use of dma_mmap_coherent()
  video: fbdev: omapfb: panel-lgphilips-lb035q02: Make use of the helper 
function dev_err_probe()
  video: fbdev: omapfb: lcd_ams_delta: Make use of the helper function 
dev_err_probe()
  video: fbdev: omapfb: panel-sharp-ls037v7dw01: Make use of the helper 
function dev_err_probe()
  video: fbdev: omapfb: panel-tpo-td043mtea1: Make use of the helper 
function dev_err_probe()
  video: fbdev: da8xx-fb: Make use of the helper function dev_err_probe()
  video: fbdev: pxa168fb: Make use of the helper function dev_err_probe()
  video: fbdev: pxa3xx-gcu: Make use of the helper function dev_err_probe()
  video: fbdev: ssd1307fb: Make use of the helper function dev_err_probe()
  video: fbdev: s3c-fb: Make use of the helper function dev_err_probe()
  video: fbdev: mmp: Make use of the helper function dev_err_probe()

Changcheng Deng (1):
  video: fbmem: use swap() to make code cleaner in fb_rotate_logo()

Chunyang Zhong (1):
  video: fbdev: ocfb: add const to of_device_id

Colin Ian King (7):
  video: fbdev: aty128fb: make some arrays static const
  video: fbdev: mb862xx: remove redundant assignment to pointer ptr
  video: fbdev: via: Fix spelling mistake "bellow" -> "below"
  video: fbdev: atyfb: Remove assigned but never used variable statements
  video: fbdev: asiliantfb: remove redundant assignment to variable Ftarget
  video: fbdev: pxa168fb: Initialize pointers with NULL and not plain 
integer 0
  video: fbdev: kyro: make read-only array ODValues static const

Dan Carpenter (3):
  video: fbdev: savagefb: make a variable local
  video: fbdev: atmel_lcdfb: fix an error code in atmel_lcdfb_probe()
  video: fbdev: fbcvt.c: fix printing in fb_cvt_print_name()

Evgeny Novikov (1):
  video: fbdev: w100fb: Reset global state

Geert Uytterhoeven (4):
  video: fbdev: atari: Fix TT High video mode
  video: fbdev: atari: Convert to standard round_up() helper
  video: fbdev: atari: Remove unused atafb_setcolreg()
  video: fbdev: au1100fb: Spelling s/palette/palette/

George Kennedy (1):
  video: fbdev: cirrusfb: check pixclock to avoid divide by zero

Greg Kroah-Hartman (1):
  video: fbdev: omapfb: use default_groups in kobj_type

Guo Zhengkui (1):
  video: fbdev: omapfb: Use sysfs_emit() instead of snprintf()

Haowen Bai (1):
  video: fbdev: offb: fix warning comparing pointer to 0

Helge Deller (1):
  video: fbdev: sm712fb: Fix crash in smtcfb_read()

Jiasheng Jiang (1):
  video: fbdev: imxfb: Check for null res pointer

Jing Yao (3):
  video: fbdev: omapfb: panel-dsi-cm: Use sysfs_emit() instead of snprintf()
  video: fbdev: omapfb: panel-tpo-td043mtea1: Use sysfs_emit() instead of 
snprintf()
  video: fbdev: udlfb: replace snprintf in show functions with sysfs_emit

Krzysztof Kozlowski (1):
  video: fbdev: s3c-fb: drop unneeded MODULE_ALIAS

Luca Weiss (2):
  backlight: qcom-wled: Add PM6150L compatible
  dt-bindings: simple-framebuffer: allow standalone compatible

Miaoqian Lin (1):
  video: fbdev: omapfb: Add missing of_node_put() in dvic_probe_of

Michael Schmitz (1):
  video: fbdev: atari: Atari 2 bpp (STe) palette bugfix

Minghao Chi (1):
  video: fbdev: mach64_ct: remove redundant res variable

Tim Gardner (1):
  video: fbdev: nvidiafb: Use strscpy() to prevent buffer overflow

Wang Hai (1):
  video: fbdev: smscufx: Fix null-ptr-deref in ufx_usb_probe()

Wei Ming Chen (1):
  video: fbdev: Fix wrong file path for pvr2fb.c in Kconfig help text

Xiaoke Wang (1):
  video: fbdev: via: check the return value of kstrdup()

Xu Wang (2):
  ba

Re: [PATCH 1/7] drm/gma500: Use managed drmm_mode_config_init()

2022-03-22 Thread Thomas Zimmermann



Am 22.03.22 um 20:30 schrieb Thomas Zimmermann:

Hi Patrik

Am 22.03.22 um 14:17 schrieb Patrik Jakobsson:

Signed-off-by: Patrik Jakobsson 
---
  drivers/gpu/drm/gma500/framebuffer.c | 4 ++--
  1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/gma500/framebuffer.c 
b/drivers/gpu/drm/gma500/framebuffer.c

index 45df9de22007..2b99c996fdc2 100644
--- a/drivers/gpu/drm/gma500/framebuffer.c
+++ b/drivers/gpu/drm/gma500/framebuffer.c
@@ -514,7 +514,8 @@ void psb_modeset_init(struct drm_device *dev)
  struct pci_dev *pdev = to_pci_dev(dev->dev);
  int i;
-    drm_mode_config_init(dev);
+    if (drmm_mode_config_init(dev))
+    return;


This will fail without any notice. I suggest to return an error here or 
at let psb_driver_load() fail.


'and let psb_driver_load() fail'



Best regards
Thomas


  dev->mode_config.min_width = 0;
  dev->mode_config.min_height = 0;
@@ -546,6 +547,5 @@ void psb_modeset_cleanup(struct drm_device *dev)
  if (dev_priv->modeset) {
  drm_kms_helper_poll_fini(dev);
  psb_fbdev_fini(dev);
-    drm_mode_config_cleanup(dev);
  }
  }




--
Thomas Zimmermann
Graphics Driver Developer
SUSE Software Solutions Germany GmbH
Maxfeldstr. 5, 90409 Nürnberg, Germany
(HRB 36809, AG Nürnberg)
Geschäftsführer: Ivo Totev


OpenPGP_signature
Description: OpenPGP digital signature


Re: [PATCH 3/7] drm/gma500: Make use of the drm connector iterator

2022-03-22 Thread Thomas Zimmermann

Hi

Am 22.03.22 um 16:46 schrieb Patrik Jakobsson:

On Tue, Mar 22, 2022 at 3:39 PM Daniel Vetter  wrote:


On Tue, Mar 22, 2022 at 02:17:38PM +0100, Patrik Jakobsson wrote:

This makes sure we're using proper locking when iterating the list of
connectors.

Signed-off-by: Patrik Jakobsson 


Note that this is only needed if your driver deals with hotpluggable
connectors. Since gma500 doesn't, not really a need to convert this over,
but it also doesn't hurt.


I'd fix this if only for copy-pasters to not copy incorrect code. :)



Good point. Not sure but I think there is a slight possibility that
Cedarview can support DP MST. If someone adds support for DP MST then
this code would make sense. I was never able to exercise the DP code
because I couldn't find an eDP cable that fits the Intel DN2800MT (my
only device with DP). Do you happen to know what the 40-pin connector
is called? Perhaps Intel has some standard for eDP connectors?



If the kerneldoc doesn't explain this, maybe we should add it? Care for a
patch.


I didn't see it being mentioned anywhere. I'll send a patch.



Either way on the entire series:

Acked-by: Daniel Vetter 


Thanks for having a look.



I'll leave it up to you whether you want to push this one too or not.
-Daniel


---
  drivers/gpu/drm/gma500/cdv_device.c| 10 ++--
  drivers/gpu/drm/gma500/cdv_intel_display.c |  9 +--
  drivers/gpu/drm/gma500/framebuffer.c   |  6 +++--
  drivers/gpu/drm/gma500/gma_display.c   | 16 -
  drivers/gpu/drm/gma500/oaktrail_crtc.c | 17 -
  drivers/gpu/drm/gma500/oaktrail_lvds.c | 15 ++--
  drivers/gpu/drm/gma500/psb_device.c| 28 +++---
  drivers/gpu/drm/gma500/psb_drv.c   | 10 
  drivers/gpu/drm/gma500/psb_intel_display.c | 15 
  9 files changed, 84 insertions(+), 42 deletions(-)

diff --git a/drivers/gpu/drm/gma500/cdv_device.c 
b/drivers/gpu/drm/gma500/cdv_device.c
index f854f58bcbb3..dd32b484dd82 100644
--- a/drivers/gpu/drm/gma500/cdv_device.c
+++ b/drivers/gpu/drm/gma500/cdv_device.c
@@ -262,6 +262,7 @@ static int cdv_save_display_registers(struct drm_device 
*dev)
   struct drm_psb_private *dev_priv = to_drm_psb_private(dev);
   struct pci_dev *pdev = to_pci_dev(dev->dev);
   struct psb_save_area *regs = &dev_priv->regs;
+ struct drm_connector_list_iter conn_iter;
   struct drm_connector *connector;

   dev_dbg(dev->dev, "Saving GPU registers.\n");
@@ -298,8 +299,10 @@ static int cdv_save_display_registers(struct drm_device 
*dev)
   regs->cdv.saveIER = REG_READ(PSB_INT_ENABLE_R);
   regs->cdv.saveIMR = REG_READ(PSB_INT_MASK_R);

- list_for_each_entry(connector, &dev->mode_config.connector_list, head)
+ drm_connector_list_iter_begin(dev, &conn_iter);
+ drm_for_each_connector_iter(connector, &conn_iter)
   connector->funcs->dpms(connector, DRM_MODE_DPMS_OFF);
+ drm_connector_list_iter_end(&conn_iter);

   return 0;
  }
@@ -317,6 +320,7 @@ static int cdv_restore_display_registers(struct drm_device 
*dev)
   struct drm_psb_private *dev_priv = to_drm_psb_private(dev);
   struct pci_dev *pdev = to_pci_dev(dev->dev);
   struct psb_save_area *regs = &dev_priv->regs;
+ struct drm_connector_list_iter conn_iter;
   struct drm_connector *connector;
   u32 temp;

@@ -373,8 +377,10 @@ static int cdv_restore_display_registers(struct drm_device 
*dev)

   drm_mode_config_reset(dev);

- list_for_each_entry(connector, &dev->mode_config.connector_list, head)
+ drm_connector_list_iter_begin(dev, &conn_iter);
+ drm_for_each_connector_iter(connector, &conn_iter)
   connector->funcs->dpms(connector, DRM_MODE_DPMS_ON);
+ drm_connector_list_iter_end(&conn_iter);

   /* Resume the modeset for every activated CRTC */
   drm_helper_resume_force_mode(dev);
diff --git a/drivers/gpu/drm/gma500/cdv_intel_display.c 
b/drivers/gpu/drm/gma500/cdv_intel_display.c
index 94ebc48a4349..0c3ddcdc29dc 100644
--- a/drivers/gpu/drm/gma500/cdv_intel_display.c
+++ b/drivers/gpu/drm/gma500/cdv_intel_display.c
@@ -584,13 +584,14 @@ static int cdv_intel_crtc_mode_set(struct drm_crtc *crtc,
   bool ok;
   bool is_lvds = false;
   bool is_dp = false;
- struct drm_mode_config *mode_config = &dev->mode_config;
+ struct drm_connector_list_iter conn_iter;
   struct drm_connector *connector;
   const struct gma_limit_t *limit;
   u32 ddi_select = 0;
   bool is_edp = false;

- list_for_each_entry(connector, &mode_config->connector_list, head) {
+ drm_connector_list_iter_begin(dev, &conn_iter);
+ drm_for_each_connector_iter(connector, &conn_iter) {
   struct gma_encoder *gma_encoder =
   gma_attached_encoder(connector);

@@ -613,10 +614,14 @@ static int cdv_intel_crtc_mode_set(struct drm_crtc *crtc,
   is_edp = true;
   break;

Re: [PATCH 7/7] drm/gma500: Add crtc prefix to vblank functions

2022-03-22 Thread Thomas Zimmermann

Hi

Am 22.03.22 um 14:17 schrieb Patrik Jakobsson:

These functions operate on a crtc and should be prefixed properly.

Suggested-by: Thomas Zimmermann 
Signed-off-by: Patrik Jakobsson 


For the whole patchset:

Reviewed-by: Thomas Zimmermann 

If you like, please consider the few comments I had.

Best regards
Thomas



---
  drivers/gpu/drm/gma500/gma_display.c | 6 +++---
  drivers/gpu/drm/gma500/psb_irq.c | 6 +++---
  drivers/gpu/drm/gma500/psb_irq.h | 6 +++---
  3 files changed, 9 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/gma500/gma_display.c 
b/drivers/gpu/drm/gma500/gma_display.c
index 369bc1f751cb..34ec3fca09ba 100644
--- a/drivers/gpu/drm/gma500/gma_display.c
+++ b/drivers/gpu/drm/gma500/gma_display.c
@@ -575,9 +575,9 @@ const struct drm_crtc_funcs gma_crtc_funcs = {
.set_config = gma_crtc_set_config,
.destroy = gma_crtc_destroy,
.page_flip = gma_crtc_page_flip,
-   .enable_vblank = gma_enable_vblank,
-   .disable_vblank = gma_disable_vblank,
-   .get_vblank_counter = gma_get_vblank_counter,
+   .enable_vblank = gma_crtc_enable_vblank,
+   .disable_vblank = gma_crtc_disable_vblank,
+   .get_vblank_counter = gma_crtc_get_vblank_counter,
  };
  
  /*

diff --git a/drivers/gpu/drm/gma500/psb_irq.c b/drivers/gpu/drm/gma500/psb_irq.c
index 2e8ded532930..e6e6d61bbeab 100644
--- a/drivers/gpu/drm/gma500/psb_irq.c
+++ b/drivers/gpu/drm/gma500/psb_irq.c
@@ -371,7 +371,7 @@ void gma_irq_uninstall(struct drm_device *dev)
free_irq(pdev->irq, dev);
  }
  
-int gma_enable_vblank(struct drm_crtc *crtc)

+int gma_crtc_enable_vblank(struct drm_crtc *crtc)
  {
struct drm_device *dev = crtc->dev;
unsigned int pipe = crtc->index;
@@ -404,7 +404,7 @@ int gma_enable_vblank(struct drm_crtc *crtc)
return 0;
  }
  
-void gma_disable_vblank(struct drm_crtc *crtc)

+void gma_crtc_disable_vblank(struct drm_crtc *crtc)
  {
struct drm_device *dev = crtc->dev;
unsigned int pipe = crtc->index;
@@ -428,7 +428,7 @@ void gma_disable_vblank(struct drm_crtc *crtc)
  /* Called from drm generic code, passed a 'crtc', which
   * we use as a pipe index
   */
-u32 gma_get_vblank_counter(struct drm_crtc *crtc)
+u32 gma_crtc_get_vblank_counter(struct drm_crtc *crtc)
  {
struct drm_device *dev = crtc->dev;
unsigned int pipe = crtc->index;
diff --git a/drivers/gpu/drm/gma500/psb_irq.h b/drivers/gpu/drm/gma500/psb_irq.h
index c22878914f5b..b51e395194ff 100644
--- a/drivers/gpu/drm/gma500/psb_irq.h
+++ b/drivers/gpu/drm/gma500/psb_irq.h
@@ -20,9 +20,9 @@ void gma_irq_postinstall(struct drm_device *dev);
  int  gma_irq_install(struct drm_device *dev, unsigned int irq);
  void gma_irq_uninstall(struct drm_device *dev);
  
-int  gma_enable_vblank(struct drm_crtc *crtc);

-void gma_disable_vblank(struct drm_crtc *crtc);
-u32  gma_get_vblank_counter(struct drm_crtc *crtc);
+int  gma_crtc_enable_vblank(struct drm_crtc *crtc);
+void gma_crtc_disable_vblank(struct drm_crtc *crtc);
+u32  gma_crtc_get_vblank_counter(struct drm_crtc *crtc);
  void gma_enable_pipestat(struct drm_psb_private *dev_priv, int pipe, u32 
mask);
  void gma_disable_pipestat(struct drm_psb_private *dev_priv, int pipe, u32 
mask);
  


--
Thomas Zimmermann
Graphics Driver Developer
SUSE Software Solutions Germany GmbH
Maxfeldstr. 5, 90409 Nürnberg, Germany
(HRB 36809, AG Nürnberg)
Geschäftsführer: Ivo Totev


OpenPGP_signature
Description: OpenPGP digital signature


Re: [PATCH v11 5/7] dt-bindings: display: Add Loongson display controller

2022-03-22 Thread Rob Herring
On Tue, Mar 22, 2022 at 09:54:08PM +0800, Sui Jingfeng wrote:
> 
> On 2022/3/22 21:08, Jiaxun Yang wrote:
> > 
> > 
> > 在 2022/3/22 2:33, Sui Jingfeng 写道:
> > > 
> > > On 2022/3/22 07:20, Rob Herring wrote:
> > > > On Tue, Mar 22, 2022 at 12:29:14AM +0800, Sui Jingfeng wrote:
> > > > > From: suijingfeng 
> > > > > 
> > > > Needs a commit message.
> > > > 
> > > > > Signed-off-by: suijingfeng 
> > > > > Signed-off-by: Sui Jingfeng <15330273...@189.cn>
> > > > Same person? Don't need both emails.
> > > 
> > > Yes,  suijingf...@loongson.cn is my company's email. But it can not
> > > be used to send patches to dri-devel,
> > > 
> > > when send patches with this email, the patch will not be shown on
> > > patch works.
> > > 
> > > Emails  are either blocked or got  rejected  by loongson's mail
> > > server.  It can only receive emails
> > > 
> > > from you and other people, but not dri-devel. so have to use my
> > > personal email(15330273...@189.cn) to send patches.
> > In this case you can just use your company's email to sign-off
> > code and sending with your personal email. It's common practice.
> > 
> > If you don't want to receiving kernel email in your company mailbox,
> > you can add a entry in .mailmap .
> > 
> |I'm using `git send-email -7 --cover-letter --annotate -v11` command to
> send patches, it will automatically sign off patches with the my private
> emails. |

I think that is only if you set your git config author to your private 
email. Pretty much anything git might automatically do can be turned 
off.

Rob



[PATCH] fbdev: udlfb: properly check endpoint type

2022-03-22 Thread Pavel Skripkin
syzbot reported warning in usb_submit_urb, which is caused by wrong
endpoint type.

This driver uses out bulk endpoint for communication, so
let's check if this endpoint is present and bail out early if not.

Fail log:

usb 1-1: BOGUS urb xfer, pipe 3 != type 1
WARNING: CPU: 0 PID: 4822 at drivers/usb/core/urb.c:493 
usb_submit_urb+0xd27/0x1540 drivers/usb/core/urb.c:493
Modules linked in:
CPU: 0 PID: 4822 Comm: kworker/0:3 Tainted: GW 5.13.0-syzkaller 
#0
...
Workqueue: usb_hub_wq hub_event
RIP: 0010:usb_submit_urb+0xd27/0x1540 drivers/usb/core/urb.c:493
...
Call Trace:
 dlfb_submit_urb+0x89/0x160 drivers/video/fbdev/udlfb.c:1969
 dlfb_set_video_mode+0x21f0/0x2950 drivers/video/fbdev/udlfb.c:315
 dlfb_ops_set_par+0x2a3/0x840 drivers/video/fbdev/udlfb.c:1110
 dlfb_usb_probe.cold+0x113e/0x1f4a drivers/video/fbdev/udlfb.c:1732
 usb_probe_interface+0x315/0x7f0 drivers/usb/core/driver.c:396

Fixes: 88e58b1a42f8 ("Staging: add udlfb driver")
Reported-and-tested-by: syzbot+53ce4a4246d0fe0fe...@syzkaller.appspotmail.com
Signed-off-by: Pavel Skripkin 
---
 drivers/video/fbdev/udlfb.c | 14 --
 1 file changed, 12 insertions(+), 2 deletions(-)

diff --git a/drivers/video/fbdev/udlfb.c b/drivers/video/fbdev/udlfb.c
index b9cdd02c1000..2343c7955747 100644
--- a/drivers/video/fbdev/udlfb.c
+++ b/drivers/video/fbdev/udlfb.c
@@ -1649,8 +1649,9 @@ static int dlfb_usb_probe(struct usb_interface *intf,
const struct device_attribute *attr;
struct dlfb_data *dlfb;
struct fb_info *info;
-   int retval = -ENOMEM;
+   int retval;
struct usb_device *usbdev = interface_to_usbdev(intf);
+   struct usb_endpoint_descriptor *out;
 
/* usb initialization */
dlfb = kzalloc(sizeof(*dlfb), GFP_KERNEL);
@@ -1664,6 +1665,12 @@ static int dlfb_usb_probe(struct usb_interface *intf,
dlfb->udev = usb_get_dev(usbdev);
usb_set_intfdata(intf, dlfb);
 
+   retval = usb_find_common_endpoints(intf->cur_altsetting, NULL, &out, 
NULL, NULL);
+   if (retval) {
+   dev_err(&intf->dev, "Device should have at lease 1 bulk 
endpoint!\n");
+   goto error;
+   }
+
dev_dbg(&intf->dev, "console enable=%d\n", console);
dev_dbg(&intf->dev, "fb_defio enable=%d\n", fb_defio);
dev_dbg(&intf->dev, "shadow enable=%d\n", shadow);
@@ -1673,6 +1680,7 @@ static int dlfb_usb_probe(struct usb_interface *intf,
if (!dlfb_parse_vendor_descriptor(dlfb, intf)) {
dev_err(&intf->dev,
"firmware not recognized, incompatible device?\n");
+   retval = -ENODEV;
goto error;
}
 
@@ -1686,8 +1694,10 @@ static int dlfb_usb_probe(struct usb_interface *intf,
 
/* allocates framebuffer driver structure, not framebuffer memory */
info = framebuffer_alloc(0, &dlfb->udev->dev);
-   if (!info)
+   if (!info) {
+   retval = -ENOMEM;
goto error;
+   }
 
dlfb->info = info;
info->par = dlfb;
-- 
2.35.1



[Bug 215727] New: drm:amdgpu_job_timedout [amdgpu]] *ERROR* ring gfx_0.0.0 timeout when using firefox, chrome or icaclient

2022-03-22 Thread bugzilla-daemon
https://bugzilla.kernel.org/show_bug.cgi?id=215727

Bug ID: 215727
   Summary: drm:amdgpu_job_timedout [amdgpu]] *ERROR* ring
gfx_0.0.0 timeout when using firefox, chrome or
icaclient
   Product: Drivers
   Version: 2.5
Kernel Version: 5.16.15-arch1-1
  Hardware: Intel
OS: Linux
  Tree: Mainline
Status: NEW
  Severity: high
  Priority: P1
 Component: Video(DRI - non Intel)
  Assignee: drivers_video-...@kernel-bugs.osdl.org
  Reporter: scal...@poczta.fm
Regression: No

Created attachment 300599
  --> https://bugzilla.kernel.org/attachment.cgi?id=300599&action=edit
Dmesg

Hi,

Symptoms:
I have installed an AMD Radeon RX 6700-XT card and started having following
random crashes when using a browser or icaclient (Citrix client):
[   85.861734] [drm:amdgpu_job_timedout [amdgpu]] *ERROR* ring gfx_0.0.0
timeout, signaled seq=13365, emitted seq=13367
[   85.862162] [drm:amdgpu_job_timedout [amdgpu]] *ERROR* Process information:
process kwin_x11 pid 819 thread kwin_x11:cs0 pid 838
Display hangs/ becomes glitched.

Steps to reproduce:
Happens randomly when using a browser (tested firefox and chrome-based) or
icaclient.
I get this error several times every day.
Happens in Xorg, also in Wayland.
Process mentioned in the error is not always window manager (kwin_x11).
Sometimes it's Xorg (or Xwayland), sometimes app (i.e. firefox).
System: Archlinux (linux-firmware 20220309.cd01f85-1)
DE: KDE 5.24.3 / mesa 21.3.7

Logs:
In this case of attached dmesg I was using kwin on Xorg and just started
firefox (hardware acceleration was on). Same thing happens when using icaclient
(very frequent crashes, but hard to reproduce on demand).
Afterwards, i have also tried collecting gfx_0.0.0 data with umr:
umr -R gfx_0.0.0

This also resulted with crash:
[  171.047397] BUG: unable to handle page fault for address: b34e820c

(full log at the end of attached dmesg).

If you need additional data I can reproduce this error.

-- 
You may reply to this email to add a comment.

You are receiving this mail because:
You are watching the assignee of the bug.

[Bug 215727] drm:amdgpu_job_timedout [amdgpu]] *ERROR* ring gfx_0.0.0 timeout when using firefox, chrome or icaclient

2022-03-22 Thread bugzilla-daemon
https://bugzilla.kernel.org/show_bug.cgi?id=215727

--- Comment #1 from Wojciech Krol (scal...@poczta.fm) ---
Created attachment 300600
  --> https://bugzilla.kernel.org/attachment.cgi?id=300600&action=edit
Partial umr -R gfx_0.0.0

-- 
You may reply to this email to add a comment.

You are receiving this mail because:
You are watching the assignee of the bug.

[PATCH] video: of: display_timing: Remove a redundant zeroing of memory

2022-03-22 Thread Christophe JAILLET
of_parse_display_timing() already call memset(0) on its 2nd argument, so
there is no need to clear it explicitly before calling this function.

Use kmalloc() instead of kzalloc() to save a few cycles.

Signed-off-by: Christophe JAILLET 
---
 drivers/video/of_display_timing.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/video/of_display_timing.c 
b/drivers/video/of_display_timing.c
index f93b6abbe258..bebd371c6b93 100644
--- a/drivers/video/of_display_timing.c
+++ b/drivers/video/of_display_timing.c
@@ -199,7 +199,7 @@ struct display_timings *of_get_display_timings(const struct 
device_node *np)
struct display_timing *dt;
int r;
 
-   dt = kzalloc(sizeof(*dt), GFP_KERNEL);
+   dt = kmalloc(sizeof(*dt), GFP_KERNEL);
if (!dt) {
pr_err("%pOF: could not allocate display_timing 
struct\n",
np);
-- 
2.32.0



Re: [PATCH v11 7/7] drm/lsdc: add drm driver for loongson display controller

2022-03-22 Thread Rob Herring
On Tue, Mar 22, 2022 at 12:29:16AM +0800, Sui Jingfeng wrote:
> From: suijingfeng 
> 
> There is a display controller in loongson's LS2K1000 SoC and LS7A1000
> bridge chip, the display controller is a PCI device in those chips. It
> has two display pipes but with only one hardware cursor. Each way has
> a DVO interface which provide RGB888 signals, vertical & horizontal
> synchronisations, data enable and the pixel clock. Each CRTC is able to
> scanout from 1920x1080 resolution at 60Hz, the maxmium resolution is
> 2048x2048 according to the hardware spec. Loongson display controllers
> are simple which require scanout buffers to be physically contiguous.
> 
> For LS7A1000 bridge chip, the DC is equipped with a dedicated video RAM
> which is typically 64MB or more. In this case, VRAM helper based driver
> is intend to be used. While LS2K1000 is a SoC, only system memory is
> available. Therefore CMA helper based driver is intend to be used. It is
> possible to use VRAM helper based solution by carving out part of system
> memory as VRAM though.
> 
> For LS7A1000, there are 4 dedicated GPIOs whose control register is
> located at the DC register space, They are used to emulate two way i2c.
> One for DVO0, another for DVO1. LS2K1000 and LS2K0500 SoC don't have such
> GPIO hardwared, they grab i2c adapter from other module, either general
> purpose GPIO emulated i2c or hardware i2c adapter.
> 
> +--++---+
> | DDR4 ||  +---+|
> +--+|  | PCIe Root complex |   LS7A1000 |
>|| MC0   |  +--++-+++|
>   +--+  HT 3.0  | || || |
>   | LS3A4000 |<>| +---++---+  +--++--++-+   +--+
>   |   CPU|<>| | GC1000 |  | LSDC |<-->| DDR3 MC |<->| VRAM |
>   +--+  | ++  +-+--+-++-+   +--+
>|| MC1   +---|--|+
> +--+|  |
> | DDR4 |  +---+   DVO0  |  |  DVO1   +--+
> +--+   VGA <--|ADV7125|<+  +>|TFP410|--> DVI/HDMI
>   +---+  +--+
> 
> The above picture give a simple usage of LS7A1000, note that the encoder
> is not necessary adv7125 or tfp410, other candicates can be ch7034b,
> sil9022, ite66121 and lt8618 etc.
> 
> v2: Fixup warnings reported by kernel test robot
> 
> v3: Fix more grammar mistakes in Kconfig reported by Randy Dunlap and give
> more details about lsdc.
> 
> v4:
>1) Add dts required and explain why device tree is required.
>2) Give more description about lsdc and VRAM helper based driver.
>3) Fix warnings reported by kernel test robot.
>4) Introduce stride_alignment member into struct lsdc_chip_desc, the
>   stride alignment is 256 bytes for ls7a1000, ls2k1000 and ls2k0500.
> 
> v5:
>1) Using writel and readl replace writeq and readq, to fix kernel test
>   robot report build error on other archtecture.
>2) Set default fb format to XRGB at crtc reset time.
> 
> v6:
>1) Explain why we are not switch to drm dridge subsystem on ls2k1000.
>2) Explain why tiny drm driver is not suitable for us.
>3) Give a short description of the trival dirty uppdate implement based
>   on CMA helper.
> 
> v7:
>1) Remove select I2C_GPIO and I2C_LS2X in Kconfig, it is not ready now
>2) Licensing issues are fixed suggested by Krzysztof Kozlowski.
>3) Remove lsdc_pixpll_print(), part of it move to debugfs.
>4) Set prefer_shadow to true if vram based driver is in using.
>5) Replace double blank lines with single line in all files.
>6) Verbose cmd line parameter is replaced with drm_dbg()
>7) All warnnings reported by ./scripts/checkpatch.pl --strict are fixed
>8) Get edid from dtb support is removed as suggested by Maxime Ripard
>9) Fix typos and various improvement
> 
> v8:
>1) Drop damage update implement and its command line.
>2) Drop DRM_LSDC_VRAM_DRIVER config option as suggested by Maxime.
>3) Deduce DC's identification from its compatible property.
>4) Drop the board specific dts patch.
>5) Add documention about the display controller device node.
> 
> v9:
>1) Fix the warnings reported by checkpatch script and fix typos
> 
> v10:
>1) Pass `make dt_binding_check` validation
>2) Fix warnings reported by kernel test robot
> 
> v11:
>1) Convert the driver to use drm bridge and of graph framework.
>2) Dump register value support through debugfs.
> 
> Reported-by: kernel test robot 
> Signed-off-by: suijingfeng 
> Signed-off-by: Sui Jingfeng <15330273...@189.cn>
> Signed-off-by: suijingfeng 
> ---
>  drivers/gpu/drm/Kconfig |   2 +
>  drivers/gpu/drm/Makefile|   1 +
>  drivers/gpu/drm/lsdc/Kconfig|  23 ++
>  drivers/gpu/drm/lsdc/Makefile   |  13 +

Re: [PATCH v11 5/7] dt-bindings: display: Add Loongson display controller

2022-03-22 Thread Rob Herring
On Tue, Mar 22, 2022 at 10:33:45AM +0800, Sui Jingfeng wrote:
> 
> On 2022/3/22 07:20, Rob Herring wrote:
> > On Tue, Mar 22, 2022 at 12:29:14AM +0800, Sui Jingfeng wrote:
> > > From: suijingfeng 
> > > 
> > Needs a commit message.
> > 
> > > Signed-off-by: suijingfeng 
> > > Signed-off-by: Sui Jingfeng <15330273...@189.cn>
> > Same person? Don't need both emails.
> 
> Yes,  suijingf...@loongson.cn is my company's email. But it can not be used
> to send patches to dri-devel,
> 
> when send patches with this email, the patch will not be shown on patch
> works.
> 
> Emails  are either blocked or got  rejected  by loongson's mail server.  It
> can only receive emails
> 
> from you and other people, but not dri-devel. so have to use my personal
> email(15330273...@189.cn) to send patches.
> 
> > > ---
> > >   .../loongson/loongson,display-controller.yaml | 230 ++
> > >   1 file changed, 230 insertions(+)
> > >   create mode 100644 
> > > Documentation/devicetree/bindings/display/loongson/loongson,display-controller.yaml
> > > 
> > > diff --git 
> > > a/Documentation/devicetree/bindings/display/loongson/loongson,display-controller.yaml
> > >  
> > > b/Documentation/devicetree/bindings/display/loongson/loongson,display-controller.yaml
> > > new file mode 100644
> > > index ..7be63346289e
> > > --- /dev/null
> > > +++ 
> > > b/Documentation/devicetree/bindings/display/loongson/loongson,display-controller.yaml
> > > @@ -0,0 +1,230 @@
> > > +# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
> > > +%YAML 1.2
> > > +---
> > > +$id: 
> > > http://devicetree.org/schemas/display/loongson/loongson,display-controller.yaml#
> > > +$schema: http://devicetree.org/meta-schemas/core.yaml#
> > > +
> > > +title: Loongson LS7A1000/LS2K1000/LS2K0500 Display Controller Device 
> > > Tree Bindings
> > > +
> > > +maintainers:
> > > +  - Sui Jingfeng 
> > > +
> > > +description: |+
> > > +
> > > +  Loongson display controllers are simple which require scanout buffers
> > > +  to be physically contiguous. LS2K1000/LS2K0500 is a SOC, only system
> > > +  memory is available. LS7A1000/LS7A2000 is bridge chip which is equipped
> > > +  with a dedicated video RAM which is 64MB or more, precise size can be
> > > +  read from the PCI BAR 2 of the GPU device(0x0014:0x7A15) in the bridge
> > > +  chip.
> > > +
> > > +  LSDC has two display pipes, each way has a DVO interface which provide
> > > +  RGB888 signals, vertical & horizontal synchronisations, data enable and
> > > +  the pixel clock. LSDC has two CRTC, each CRTC is able to scanout from
> > > +  1920x1080 resolution at 60Hz. Each CRTC has two FB address registers.
> > > +
> > > +  For LS7A1000, there are 4 dedicated GPIOs whose control register is
> > > +  located at the DC register space. They are used to emulate two way i2c,
> > > +  One for DVO0, another for DVO1.
> > > +
> > > +  LS2K1000 and LS2K0500 SoC grab i2c adapter from other module, either
> > > +  general purpose GPIO emulated i2c or hardware i2c in the SoC.
> > > +
> > > +  LSDC's display pipeline have several components as below description,
> > > +
> > > +  The display controller in LS7A1000:
> > > + ___ _
> > > +|---|   | |
> > > +|  CRTC0 --> | DVO0 > Encoder0 ---> Connector0 ---> | Monitor |
> > > +|  _   _ ---|^ ^|_|
> > > +| | | | |---|| |
> > > +| |_| |_|| i2c0 <+-+
> > > +|---|
> > > +|   DC IN LS7A1000  |
> > > +|  _   _ ---|
> > > +| | | | || i2c1 <+-+
> > > +| |_| |_|---|| | _
> > > +|---|| || |
> > > +|  CRTC1 --> | DVO1 > Encoder1 ---> Connector1 ---> |  Panel  |
> > > +|---|   |_|
> > > +|___|
> > > +
> > > +  Simple usage of LS7A1000 with LS3A4000 CPU:
> > > +
> > > ++--++---+
> > > +| DDR4 ||  +---+|
> > > ++--+|  | PCIe Root complex |   LS7A1000 |
> > > +   || MC0   |  +--++-+++|
> > > +  +--+  HT 3.0  | || || |
> > > +  | LS3A4000 |<>| +---++---+  +--++--++-+   +--+
> > > +  |   CPU|<>| | GC1000 |  | LSDC |<-->| DDR3 MC |<->| VRAM |
> > > +  +--+  | ++  +-+--+-++-+   +--+
> > > +   || MC1   +---|--|+
> > > ++--+|  |
> > > +| DDR4 |  +---+   DVO0  |  |  DVO1   +--+
> > > ++--+   VGA <--|ADV7125|<+  +-

Re: Parallel modesets and private state objects broken, where to go with MST?

2022-03-22 Thread Lyude Paul
OK so - this has become a bit of a larger rabbit hole. I've been putting quite
a bit of work into this and I think I'm starting to make some progress -
although on a different aspect of this issue. After talking with danvet they
realized that we're also potentially not handling encoder stealing with MST
correctly - which we need to do in order to know that we're correctly pulling
in every related crtc/connector into the state - along with avoiding encoder
conflicts if something tries to use a GPU's DP encoder in SST mode while it's
driving other displays in MST mode.

So - it seems this will likely need to be solved first before we can deal with
ensuring that we perform the correct CRTC waits in atomic commits with the MST
helpers. This has been pretty painful to figure out, but I think I'm starting
to make some progress - but I'd really appreciate getting some feedback on
this approach I've came up with so I maybe can skip having to rewrite it
later.

So: to clarify the problem, it boils down to something like this:

State 1:
  * DP-1 (hosts MST topology, so is disconnected + no encoder)
* MST topology
  * DP-2 (has display)
  * DP-3 (has display)
  (In hardware)
  * drm_encoder A drives:
* DP-2
* DP-3
  (In software)
  * drm_encoder A unused
  * Fake MST drm_encoder B -> DP-2
  * Fake MST drm_encoder C -> DP-3

Problems:
  * DP-1 gets disconnected, MST topology disappears
  * We disable maybe 1 display
  * DP-1 is disconnected, suddenly replaced with SST display
  * Driver tries to assign drm_encoder A to new DP-1 display
  *** Error! drm_encoder A is still driving fake encoders B and C ***


I'm not sure if the exact above example would actually happen - you
might need to do some tricks to get it into such a state. But you get
the general idea - there's missing coverage with how we handle encoder
conflicts when it comes to encoders that aren't directly handling CRTCs.
If we can fix this, I think we should be able to reliably figure out
every CRTC involved in modesets like this - and ensure that nonblocking
modesets come up with the right CRTC dependencies.

My current idea for handling this is as follows:
  * Add the following fields to drm_connector_state:
* reserved_encoder → an encoder that is "reserved" by the connector,
  but is not directly attached to a monitor. Note reserved
  connectors cannot have CRTCs attached to them. When a connector
  has no more CRTCs reserved, it should lose it's reserved encoder.
* dependent_crtcs → a bitmask of CRTCs that depend on this
  connector's state, but are not directly attached to it.
  * Add the following fields to drm_crtc_state:
* connector_dependency → a connector whose state this CRTC relies
  on, but is not directly attached to. This connector must be pulled
  into the atomic state whenever this CRTC requires a modeset.

The reason for adding all of these fields to drm_connector_state and
drm_crtc_state is because I don't think it's possible for us to rely on
a particular private object being in all atomic states - so we need a
way for the DRM core to be able to understand these object relationships
on it's own and reference them from any type of atomic state change so
that we can pull in dependent CRTCs as needed.

>From there, we'd just:
  * Add some functions to handle these new fields, something like:
* drm_atomic_reserve_crtc_for_connector(crtc, encoder, conn_state)
* drm_atomic_release_crtc_from_connector(crtc, conn_state)
  * Teach the various DRM core functions how to handle these new fields

Does this seem like I'm on the right track so far? JFYI - I've been busy
trying to write up some patches for this, but there's definitely a lot
of code to go through and change.

On Wed, 2022-03-16 at 16:28 -0400, Lyude Paul wrote:
> On Wed, 2022-03-16 at 13:01 +0200, Ville Syrjälä wrote:
> > On Mon, Mar 14, 2022 at 06:16:36PM -0400, Lyude Paul wrote:
> > > Hi! First a little bit of background: I've recently been trying to get
> > > rid
> > > of
> > > all of the non-atomic payload bandwidth management code in the MST
> > > helpers
> > > in
> > > order to make it easier to implement DSC and fallback link rate
> > > retraining
> > > support down the line. Currently bandwidth information is stored in two
> > > places, partially in the MST atomic state and partially in the mst
> > > manager's
> > > payload table (which exists outside of the atomic state and has its own
> > > locking). The portions in the atomic state are used to try to determine
> > > if
> > > a
> > > given display configuration can fit within the given bandwidth
> > > limitations
> > > during the atomic check phase, and are implemented through the use of
> > > private
> > > state objects.
> > > 
> > > My current goal has been to move as much of this as possible over to the
> > > atomic state and entirely get rid of the payload table along with it's
> > > locks.
> > > My main reason for doing this is that it both decomplicates thin

[RFC 00/19] drm/edid: overhaul CEA data block iteration

2022-03-22 Thread Jani Nikula
Add iterators for EDID blocks and CEA data blocks, to iterate through
all data blocks across all CEA extensions and CTA blocks in DisplayID
data blocks. Fix all code assuming only one CEA extension. Fix code
assuming CTA blocks contain everything that CEA extensions do. Sprinkle
a bunch of cleanups on top.

This is completely UNTESTED, didn't even smoke test it. It builds. ;)

This superseeds parts of [1] and [2].

BR,
Jani.

[1] https://patchwork.freedesktop.org/series/101241/
[2] 
https://patchwork.freedesktop.org/patch/msgid/20220321044330.27723-1-cooper.ch...@intel.com


Cc: Shawn C Lee 
Cc: Cooper Chiou 
Cc: william.ts...@intel.com
Cc: ankit.k.nauti...@intel.com
Cc: ville.syrj...@linux.intel.com
Cc: Drew Davenport 

Jani Nikula (19):
  drm/edid: add drm_edid_extension_block_count() and drm_edid_size()
  drm: use drm_edid_extension_block_count() and drm_edid_size()
  drm/edid: clean up CEA data block tag definitions
  drm/edid: add iterator for EDID base and extension blocks
  drm/edid: add iterator for CEA data blocks
  drm/edid: clean up cea_db_is_*() functions
  drm/edid: convert add_cea_modes() to use cea db iter
  drm/edid: convert drm_edid_to_speaker_allocation() to use cea db iter
  drm/edid: convert drm_edid_to_sad() to use cea db iter
  drm/edid: convert drm_detect_hdmi_monitor() to use cea db iter
  drm/edid: convert drm_detect_monitor_audio() to use cea db iter
  drm/edid: convert drm_parse_cea_ext() to use cea db iter
  drm/edid: convert drm_edid_to_eld() to use cea db iter
  drm/edid: sunset the old unused cea data block iterators
  drm/edid: restore some type safety to cea_db_*() functions
  drm/edid: detect basic audio only on CEA extension
  drm/edid: detect color formats and CEA revision only on CEA extension
  drm/edid: skip CEA extension scan in drm_edid_to_eld() just for CEA
rev
  drm/edid: sunset drm_find_cea_extension()

 drivers/gpu/drm/drm_connector.c |   2 +-
 drivers/gpu/drm/drm_debugfs.c   |   3 +-
 drivers/gpu/drm/drm_edid.c  | 781 ++--
 include/drm/drm_edid.h  |   2 +
 4 files changed, 455 insertions(+), 333 deletions(-)

-- 
2.30.2



[RFC 02/19] drm: use drm_edid_extension_block_count() and drm_edid_size()

2022-03-22 Thread Jani Nikula
Use the block count and size helpers in all drm core code.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_connector.c |  2 +-
 drivers/gpu/drm/drm_debugfs.c   |  3 +--
 drivers/gpu/drm/drm_edid.c  | 14 +++---
 3 files changed, 9 insertions(+), 10 deletions(-)

diff --git a/drivers/gpu/drm/drm_connector.c b/drivers/gpu/drm/drm_connector.c
index 76a8c707c34b..cfed43e61380 100644
--- a/drivers/gpu/drm/drm_connector.c
+++ b/drivers/gpu/drm/drm_connector.c
@@ -2138,7 +2138,7 @@ int drm_connector_update_edid_property(struct 
drm_connector *connector,
return 0;
 
if (edid)
-   size = EDID_LENGTH * (1 + edid->extensions);
+   size = drm_edid_size(edid);
 
/* Set the display info, using edid if available, otherwise
 * resetting the values to defaults. This duplicates the work
diff --git a/drivers/gpu/drm/drm_debugfs.c b/drivers/gpu/drm/drm_debugfs.c
index 7f1b82dbaebb..a832ef6b33fe 100644
--- a/drivers/gpu/drm/drm_debugfs.c
+++ b/drivers/gpu/drm/drm_debugfs.c
@@ -362,8 +362,7 @@ static ssize_t edid_write(struct file *file, const char 
__user *ubuf,
if (len == 5 && !strncmp(buf, "reset", 5)) {
connector->override_edid = false;
ret = drm_connector_update_edid_property(connector, NULL);
-   } else if (len < EDID_LENGTH ||
-  EDID_LENGTH * (1 + edid->extensions) > len)
+   } else if (len < EDID_LENGTH || drm_edid_size(edid) > len)
ret = -EINVAL;
else {
connector->override_edid = false;
diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index f4b49693e666..b96906774433 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -1643,8 +1643,8 @@ bool drm_edid_are_equal(const struct edid *edid1, const 
struct edid *edid2)
return false;
 
if (edid1) {
-   edid1_len = EDID_LENGTH * (1 + edid1->extensions);
-   edid2_len = EDID_LENGTH * (1 + edid2->extensions);
+   edid1_len = drm_edid_size(edid1);
+   edid2_len = drm_edid_size(edid2);
 
if (edid1_len != edid2_len)
return false;
@@ -1770,7 +1770,7 @@ bool drm_edid_is_valid(struct edid *edid)
if (!edid)
return false;
 
-   for (i = 0; i <= edid->extensions; i++)
+   for (i = 0; i <= drm_edid_extension_block_count(edid); i++)
if (!drm_edid_block_valid(raw + i * EDID_LENGTH, i, true, NULL))
return false;
 
@@ -2224,7 +2224,7 @@ EXPORT_SYMBOL(drm_edid_size);
  */
 struct edid *drm_edid_duplicate(const struct edid *edid)
 {
-   return kmemdup(edid, (edid->extensions + 1) * EDID_LENGTH, GFP_KERNEL);
+   return kmemdup(edid, drm_edid_size(edid), GFP_KERNEL);
 }
 EXPORT_SYMBOL(drm_edid_duplicate);
 
@@ -3353,17 +3353,17 @@ const u8 *drm_find_edid_extension(const struct edid 
*edid,
int i;
 
/* No EDID or EDID extensions */
-   if (edid == NULL || edid->extensions == 0)
+   if (edid == NULL || drm_edid_extension_block_count(edid) == 0)
return NULL;
 
/* Find CEA extension */
-   for (i = *ext_index; i < edid->extensions; i++) {
+   for (i = *ext_index; i < drm_edid_extension_block_count(edid); i++) {
edid_ext = (const u8 *)edid + EDID_LENGTH * (i + 1);
if (edid_ext[0] == ext_id)
break;
}
 
-   if (i >= edid->extensions)
+   if (i >= drm_edid_extension_block_count(edid))
return NULL;
 
*ext_index = i + 1;
-- 
2.30.2



[RFC 01/19] drm/edid: add drm_edid_extension_block_count() and drm_edid_size()

2022-03-22 Thread Jani Nikula
Add abstractions for getting the number of EDID extension blocks and the
total EDID size in bytes.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 18 ++
 include/drm/drm_edid.h |  2 ++
 2 files changed, 20 insertions(+)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index 561f53831e29..f4b49693e666 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -2198,6 +2198,24 @@ struct edid *drm_get_edid_switcheroo(struct 
drm_connector *connector,
 }
 EXPORT_SYMBOL(drm_get_edid_switcheroo);
 
+/**
+ * drm_edid_extension_block_count - get the number of EDID extension blocks
+ */
+u8 drm_edid_extension_block_count(const struct edid *edid)
+{
+   return edid->extensions;
+}
+EXPORT_SYMBOL(drm_edid_extension_block_count);
+
+/**
+ * drm_edid_size - get the EDID size in bytes
+ */
+size_t drm_edid_size(const struct edid *edid)
+{
+   return (drm_edid_extension_block_count(edid) + 1) * EDID_LENGTH;
+}
+EXPORT_SYMBOL(drm_edid_size);
+
 /**
  * drm_edid_duplicate - duplicate an EDID and the extensions
  * @edid: EDID to duplicate
diff --git a/include/drm/drm_edid.h b/include/drm/drm_edid.h
index 144c495b99c4..7a19daa00c0c 100644
--- a/include/drm/drm_edid.h
+++ b/include/drm/drm_edid.h
@@ -564,6 +564,8 @@ struct edid *drm_get_edid(struct drm_connector *connector,
 u32 drm_edid_get_panel_id(struct i2c_adapter *adapter);
 struct edid *drm_get_edid_switcheroo(struct drm_connector *connector,
 struct i2c_adapter *adapter);
+u8 drm_edid_extension_block_count(const struct edid *edid);
+size_t drm_edid_size(const struct edid *edid);
 struct edid *drm_edid_duplicate(const struct edid *edid);
 int drm_add_edid_modes(struct drm_connector *connector, struct edid *edid);
 int drm_add_override_edid_modes(struct drm_connector *connector);
-- 
2.30.2



[RFC 03/19] drm/edid: clean up CEA data block tag definitions

2022-03-22 Thread Jani Nikula
Add prefixed names, group, sort, add references.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 59 +-
 1 file changed, 32 insertions(+), 27 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index b96906774433..6c188539493e 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -3329,15 +3329,20 @@ add_detailed_modes(struct drm_connector *connector, 
struct edid *edid,
return closure.modes;
 }
 
-#define AUDIO_BLOCK0x01
-#define VIDEO_BLOCK 0x02
-#define VENDOR_BLOCK0x03
-#define SPEAKER_BLOCK  0x04
-#define HDR_STATIC_METADATA_BLOCK  0x6
-#define USE_EXTENDED_TAG 0x07
-#define EXT_VIDEO_CAPABILITY_BLOCK 0x00
-#define EXT_VIDEO_DATA_BLOCK_420   0x0E
-#define EXT_VIDEO_CAP_BLOCK_Y420CMDB 0x0F
+/* CEA-861-F Table 44 CEA Data Block Tag Codes */
+#define CEA_DB_AUDIO   1
+#define CEA_DB_VIDEO   2
+#define CEA_DB_VENDOR  3
+#define CEA_DB_SPEAKER 4
+#define CEA_DB_EXTENDED_TAG7
+
+/* CEA-861-F Table 46 CEA Data Block Tag Codes */
+#define CEA_EXT_DB_VIDEO_CAP   0
+#define CEA_EXT_DB_VENDOR  1
+#define CEA_EXT_DB_HDR_STATIC_METADATA 6 /* CEA-861.3 2005 */
+#define CEA_EXT_DB_420_VIDEO_DATA  14
+#define CEA_EXT_DB_420_VIDEO_CAP_MAP   15
+
 #define EDID_BASIC_AUDIO   (1 << 6)
 #define EDID_CEA_YCRCB444  (1 << 5)
 #define EDID_CEA_YCRCB422  (1 << 4)
@@ -4220,7 +4225,7 @@ cea_db_offsets(const u8 *cea, int *start, int *end)
 
 static bool cea_db_is_hdmi_vsdb(const u8 *db)
 {
-   if (cea_db_tag(db) != VENDOR_BLOCK)
+   if (cea_db_tag(db) != CEA_DB_VENDOR)
return false;
 
if (cea_db_payload_len(db) < 5)
@@ -4231,7 +4236,7 @@ static bool cea_db_is_hdmi_vsdb(const u8 *db)
 
 static bool cea_db_is_hdmi_forum_vsdb(const u8 *db)
 {
-   if (cea_db_tag(db) != VENDOR_BLOCK)
+   if (cea_db_tag(db) != CEA_DB_VENDOR)
return false;
 
if (cea_db_payload_len(db) < 7)
@@ -4242,7 +4247,7 @@ static bool cea_db_is_hdmi_forum_vsdb(const u8 *db)
 
 static bool cea_db_is_microsoft_vsdb(const u8 *db)
 {
-   if (cea_db_tag(db) != VENDOR_BLOCK)
+   if (cea_db_tag(db) != CEA_DB_VENDOR)
return false;
 
if (cea_db_payload_len(db) != 21)
@@ -4253,13 +4258,13 @@ static bool cea_db_is_microsoft_vsdb(const u8 *db)
 
 static bool cea_db_is_vcdb(const u8 *db)
 {
-   if (cea_db_tag(db) != USE_EXTENDED_TAG)
+   if (cea_db_tag(db) != CEA_DB_EXTENDED_TAG)
return false;
 
if (cea_db_payload_len(db) != 2)
return false;
 
-   if (cea_db_extended_tag(db) != EXT_VIDEO_CAPABILITY_BLOCK)
+   if (cea_db_extended_tag(db) != CEA_EXT_DB_VIDEO_CAP)
return false;
 
return true;
@@ -4267,13 +4272,13 @@ static bool cea_db_is_vcdb(const u8 *db)
 
 static bool cea_db_is_y420cmdb(const u8 *db)
 {
-   if (cea_db_tag(db) != USE_EXTENDED_TAG)
+   if (cea_db_tag(db) != CEA_DB_EXTENDED_TAG)
return false;
 
if (!cea_db_payload_len(db))
return false;
 
-   if (cea_db_extended_tag(db) != EXT_VIDEO_CAP_BLOCK_Y420CMDB)
+   if (cea_db_extended_tag(db) != CEA_EXT_DB_420_VIDEO_CAP_MAP)
return false;
 
return true;
@@ -4281,13 +4286,13 @@ static bool cea_db_is_y420cmdb(const u8 *db)
 
 static bool cea_db_is_y420vdb(const u8 *db)
 {
-   if (cea_db_tag(db) != USE_EXTENDED_TAG)
+   if (cea_db_tag(db) != CEA_DB_EXTENDED_TAG)
return false;
 
if (!cea_db_payload_len(db))
return false;
 
-   if (cea_db_extended_tag(db) != EXT_VIDEO_DATA_BLOCK_420)
+   if (cea_db_extended_tag(db) != CEA_EXT_DB_420_VIDEO_DATA)
return false;
 
return true;
@@ -4354,7 +4359,7 @@ add_cea_modes(struct drm_connector *connector, struct 
edid *edid)
db = &cea[i];
dbl = cea_db_payload_len(db);
 
-   if (cea_db_tag(db) == VIDEO_BLOCK) {
+   if (cea_db_tag(db) == CEA_DB_VIDEO) {
video = db + 1;
video_len = dbl;
modes += do_cea_modes(connector, video, dbl);
@@ -4428,10 +4433,10 @@ static void fixup_detailed_cea_mode_clock(struct 
drm_display_mode *mode)
 
 static bool cea_db_is_hdmi_hdr_metadata_block(const u8 *db)
 {
-   if (cea_db_tag(db) != USE_EXTENDED_TAG)
+   if (cea_db_tag(db) != CEA_DB_EXTENDED_TAG)
return false;
 
-   if (db[1] != HDR_STATIC_METADATA_BLOCK)
+   if (db[1] != CEA_EXT_DB_HDR_STATIC_METADATA)
return false;
 
if (cea_db_payload_len(db) < 3)
@@ -4622,7 +4627,7 @@ static void drm_edid_to_eld(struct drm_connector 
*connector, struct edid *edid)
dbl = cea_db_payload_len(db);
 

[RFC 04/19] drm/edid: add iterator for EDID base and extension blocks

2022-03-22 Thread Jani Nikula
Add an iterator abstraction for going through all the EDID blocks.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 46 ++
 1 file changed, 46 insertions(+)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index 6c188539493e..31d132fcd0ca 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -3348,6 +3348,52 @@ add_detailed_modes(struct drm_connector *connector, 
struct edid *edid,
 #define EDID_CEA_YCRCB422  (1 << 4)
 #define EDID_CEA_VCDB_QS   (1 << 6)
 
+/*
+ * EDID base and extension block iterator.
+ *
+ * struct drm_edid_iter iter;
+ * const u8 *block;
+ *
+ * drm_edid_iter_begin(edid, &iter);
+ * drm_edid_iter_for_each(block, &iter) {
+ * // do stuff with block
+ * }
+ * drm_edid_iter_end(&iter);
+ */
+struct drm_edid_iter {
+   const struct edid *edid;
+
+   /* Current block index. */
+   int index;
+};
+
+static void drm_edid_iter_begin(const struct edid *edid,
+   struct drm_edid_iter *iter)
+{
+   memset(iter, 0, sizeof(*iter));
+
+   iter->edid = edid;
+}
+
+static const void *__drm_edid_iter_next(struct drm_edid_iter *iter)
+{
+   if (!iter->edid)
+   return NULL;
+
+   if (iter->index > drm_edid_extension_block_count(iter->edid))
+   return NULL;
+
+   return (const u8 *)iter->edid + EDID_LENGTH * iter->index++;
+}
+
+#define drm_edid_iter_for_each(__block, __iter)\
+   while (((__block) = __drm_edid_iter_next(__iter)))
+
+static void drm_edid_iter_end(struct drm_edid_iter *iter)
+{
+   memset(iter, 0, sizeof(*iter));
+}
+
 /*
  * Search EDID for CEA extension block.
  */
-- 
2.30.2



[RFC 05/19] drm/edid: add iterator for CEA data blocks

2022-03-22 Thread Jani Nikula
Add an iterator for CEA Data Blocks across CEA extensions and CTA
DisplayID Data Blocks.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 198 ++---
 1 file changed, 186 insertions(+), 12 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index 31d132fcd0ca..c12c3cbab274 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -4196,24 +4196,12 @@ do_hdmi_vsdb_modes(struct drm_connector *connector, 
const u8 *db, u8 len,
return modes;
 }
 
-static int
-cea_db_payload_len(const u8 *db)
-{
-   return db[0] & 0x1f;
-}
-
 static int
 cea_db_extended_tag(const u8 *db)
 {
return db[1];
 }
 
-static int
-cea_db_tag(const u8 *db)
-{
-   return db[0] >> 5;
-}
-
 static int
 cea_revision(const u8 *cea)
 {
@@ -4269,6 +4257,192 @@ cea_db_offsets(const u8 *cea, int *start, int *end)
return 0;
 }
 
+/*
+ * CEA Data Block iterator.
+ *
+ * Iterate through all CEA Data Blocks in both EDID CEA extensions and CTA Data
+ * Blocks in DisplayID extension blocks.
+ *
+ * struct cea_db *db:
+ * struct cea_db_iter iter;
+ *
+ * cea_db_iter_edid_begin(edid, &iter);
+ * cea_db_iter_for_each(db, &iter) {
+ * // do stuff with db
+ * }
+ * cea_db_iter_end(&iter);
+ */
+struct cea_db_iter {
+   struct drm_edid_iter edid_iter;
+   struct displayid_iter displayid_iter;
+
+   /* Current Data Block Collection. */
+   const u8 *collection;
+
+   /* Current Data Block index in current collection. */
+   int index;
+
+   /* End index in current collection. */
+   int end;
+};
+
+/* CEA-861-F section 7.5 CEA Extension Version 3 and Table 43 */
+struct cea_db {
+   u8 tag_length;
+   u8 data[];
+} __packed;
+
+static int cea_db_tag(const void *_db)
+{
+   /* FIXME: Transition to passing struct cea_db * everywhere. */
+   const struct cea_db *db = _db;
+
+   return db->tag_length >> 5;
+}
+
+static int cea_db_payload_len(const void *_db)
+{
+   /* FIXME: Transition to passing struct cea_db * everywhere. */
+   const struct cea_db *db = _db;
+
+   return db->tag_length & 0x1f;
+}
+
+static const void *cea_db_data(const struct cea_db *db)
+{
+   return db->data;
+}
+
+static void cea_db_iter_edid_begin(const struct edid *edid, struct cea_db_iter 
*iter)
+{
+   memset(iter, 0, sizeof(*iter));
+
+   drm_edid_iter_begin(edid, &iter->edid_iter);
+   displayid_iter_edid_begin(edid, &iter->displayid_iter);
+}
+
+static const struct cea_db *
+__cea_db_iter_current_block(const struct cea_db_iter *iter)
+{
+   const struct cea_db *db;
+
+   if (!iter->collection)
+   return NULL;
+
+   db = (const struct cea_db *)&iter->collection[iter->index];
+
+   if (iter->index + sizeof(*db) <= iter->end &&
+   iter->index + sizeof(*db) + cea_db_payload_len(db) <= iter->end)
+   return db;
+
+   return NULL;
+}
+
+/*
+ * References:
+ * - VESA E-EDID v1.4
+ * - CEA-861-F section 7.5 CEA Extension Version 3
+ */
+static const void *__cea_db_iter_edid_next(struct cea_db_iter *iter)
+{
+   const u8 *ext;
+
+   drm_edid_iter_for_each(ext, &iter->edid_iter) {
+   /* Only support CEA extension revision 3+ */
+   if (ext[0] != CEA_EXT || cea_revision(ext) < 3)
+   continue;
+
+   iter->index = 4;
+   iter->end = ext[2];
+   if (iter->end == 0)
+   iter->end = 127;
+   if (iter->end < 4 || iter->end > 127)
+   continue;
+
+   return ext;
+   }
+
+   return NULL;
+}
+
+/*
+ * References:
+ * - DisplayID v1.3 Appendix C: CEA Data Block within a DisplayID Data Block
+ * - DisplayID v2.0 section 4.10 CTA DisplayID Data Block
+ *
+ * Note that the above do not specify any connection between DisplayID Data
+ * Block revision and CEA Extension versions.
+ */
+static const void *__cea_db_iter_displayid_next(struct cea_db_iter *iter)
+{
+   const struct displayid_block *block;
+
+   displayid_iter_for_each(block, &iter->displayid_iter) {
+   if (block->tag != DATA_BLOCK_CTA)
+   continue;
+
+   iter->index = sizeof(*block);
+   iter->end = iter->index + block->num_bytes;
+
+   return block;
+   }
+
+   return NULL;
+}
+
+static const struct cea_db *__cea_db_iter_next(struct cea_db_iter *iter)
+{
+   const struct cea_db *db;
+
+   if (iter->collection) {
+   /* Current collection should always be valid. */
+   db = __cea_db_iter_current_block(iter);
+   if (WARN_ON(!db)) {
+   iter->collection = NULL;
+   return NULL;
+   }
+
+   /* Next block in CEA Data Block Collection */
+   iter->index += sizeof(*db) + cea_db_payload_len(db);
+
+   db = __cea_db_ite

[RFC 06/19] drm/edid: clean up cea_db_is_*() functions

2022-03-22 Thread Jani Nikula
Abstract helpers for matching vendor data blocks and extended tags, and
use them to simplify all the cea_db_is_*() functions.

Take void pointer as parameter to allow transitional use for both u8 *
and struct cea_db *.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 113 -
 1 file changed, 37 insertions(+), 76 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index c12c3cbab274..a0a5a7271658 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -4196,12 +4196,6 @@ do_hdmi_vsdb_modes(struct drm_connector *connector, 
const u8 *db, u8 len,
return modes;
 }
 
-static int
-cea_db_extended_tag(const u8 *db)
-{
-   return db[1];
-}
-
 static int
 cea_revision(const u8 *cea)
 {
@@ -4313,6 +4307,22 @@ static const void *cea_db_data(const struct cea_db *db)
return db->data;
 }
 
+static bool cea_db_is_extended_tag(const struct cea_db *db, int tag)
+{
+   return (cea_db_tag(db) == CEA_DB_EXTENDED_TAG &&
+   cea_db_payload_len(db) >= 1 &&
+   db->data[0] == tag);
+}
+
+static bool cea_db_is_vendor(const struct cea_db *db, int vendor_oui)
+{
+   const u8 *data = cea_db_data(db);
+
+   return (cea_db_tag(db) == CEA_DB_VENDOR &&
+   cea_db_payload_len(db) >= 3 &&
+   oui(data[2], data[1], data[0]) == vendor_oui);
+}
+
 static void cea_db_iter_edid_begin(const struct edid *edid, struct cea_db_iter 
*iter)
 {
memset(iter, 0, sizeof(*iter));
@@ -4443,79 +4453,44 @@ static void cea_db_iter_end(struct cea_db_iter *iter)
memset(iter, 0, sizeof(*iter));
 }
 
-static bool cea_db_is_hdmi_vsdb(const u8 *db)
+static bool cea_db_is_hdmi_vsdb(const void *db)
 {
-   if (cea_db_tag(db) != CEA_DB_VENDOR)
-   return false;
-
-   if (cea_db_payload_len(db) < 5)
-   return false;
-
-   return oui(db[3], db[2], db[1]) == HDMI_IEEE_OUI;
+   return (cea_db_is_vendor(db, HDMI_IEEE_OUI) &&
+   cea_db_payload_len(db) >= 5);
 }
 
-static bool cea_db_is_hdmi_forum_vsdb(const u8 *db)
+static bool cea_db_is_hdmi_forum_vsdb(const void *db)
 {
-   if (cea_db_tag(db) != CEA_DB_VENDOR)
-   return false;
-
-   if (cea_db_payload_len(db) < 7)
-   return false;
-
-   return oui(db[3], db[2], db[1]) == HDMI_FORUM_IEEE_OUI;
+   return (cea_db_is_vendor(db, HDMI_FORUM_IEEE_OUI) &&
+   cea_db_payload_len(db) >= 7);
 }
 
-static bool cea_db_is_microsoft_vsdb(const u8 *db)
+static bool cea_db_is_microsoft_vsdb(const void *db)
 {
-   if (cea_db_tag(db) != CEA_DB_VENDOR)
-   return false;
-
-   if (cea_db_payload_len(db) != 21)
-   return false;
-
-   return oui(db[3], db[2], db[1]) == MICROSOFT_IEEE_OUI;
+   return (cea_db_is_vendor(db, MICROSOFT_IEEE_OUI) &&
+   cea_db_payload_len(db) == 21);
 }
 
-static bool cea_db_is_vcdb(const u8 *db)
+static bool cea_db_is_vcdb(const void *db)
 {
-   if (cea_db_tag(db) != CEA_DB_EXTENDED_TAG)
-   return false;
-
-   if (cea_db_payload_len(db) != 2)
-   return false;
-
-   if (cea_db_extended_tag(db) != CEA_EXT_DB_VIDEO_CAP)
-   return false;
-
-   return true;
+   return (cea_db_is_extended_tag(db, CEA_EXT_DB_VIDEO_CAP) &&
+   cea_db_payload_len(db) == 2);
 }
 
-static bool cea_db_is_y420cmdb(const u8 *db)
+static bool cea_db_is_y420cmdb(const void *db)
 {
-   if (cea_db_tag(db) != CEA_DB_EXTENDED_TAG)
-   return false;
-
-   if (!cea_db_payload_len(db))
-   return false;
-
-   if (cea_db_extended_tag(db) != CEA_EXT_DB_420_VIDEO_CAP_MAP)
-   return false;
-
-   return true;
+   return cea_db_is_extended_tag(db, CEA_EXT_DB_420_VIDEO_CAP_MAP);
 }
 
-static bool cea_db_is_y420vdb(const u8 *db)
+static bool cea_db_is_y420vdb(const void *db)
 {
-   if (cea_db_tag(db) != CEA_DB_EXTENDED_TAG)
-   return false;
-
-   if (!cea_db_payload_len(db))
-   return false;
-
-   if (cea_db_extended_tag(db) != CEA_EXT_DB_420_VIDEO_DATA)
-   return false;
+   return cea_db_is_extended_tag(db, CEA_EXT_DB_420_VIDEO_DATA);
+}
 
-   return true;
+static bool cea_db_is_hdmi_hdr_metadata_block(const void *db)
+{
+   return (cea_db_is_extended_tag(db, CEA_EXT_DB_HDR_STATIC_METADATA) &&
+   cea_db_payload_len(db) >= 3);
 }
 
 #define for_each_cea_db(cea, i, start, end) \
@@ -4651,20 +4626,6 @@ static void fixup_detailed_cea_mode_clock(struct 
drm_display_mode *mode)
mode->clock = clock;
 }
 
-static bool cea_db_is_hdmi_hdr_metadata_block(const u8 *db)
-{
-   if (cea_db_tag(db) != CEA_DB_EXTENDED_TAG)
-   return false;
-
-   if (db[1] != CEA_EXT_DB_HDR_STATIC_METADATA)
-   return false;
-
-   if (cea_db_payload_len(db) < 3)
-   return false;
-
-   re

[RFC 07/19] drm/edid: convert add_cea_modes() to use cea db iter

2022-03-22 Thread Jani Nikula
Iterate through all CEA EDID extension blocks and DisplayID CTA data
blocks to add CEA modes.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 67 ++
 1 file changed, 31 insertions(+), 36 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index a0a5a7271658..d92ce5d540c3 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -4539,46 +4539,41 @@ static void drm_parse_y420cmdb_bitmap(struct 
drm_connector *connector,
 static int
 add_cea_modes(struct drm_connector *connector, struct edid *edid)
 {
-   const u8 *cea = drm_find_cea_extension(edid);
-   const u8 *db, *hdmi = NULL, *video = NULL;
-   u8 dbl, hdmi_len, video_len = 0;
+   const struct cea_db *db;
+   struct cea_db_iter iter;
int modes = 0;
 
-   if (cea && cea_revision(cea) >= 3) {
-   int i, start, end;
-
-   if (cea_db_offsets(cea, &start, &end))
-   return 0;
-
-   for_each_cea_db(cea, i, start, end) {
-   db = &cea[i];
-   dbl = cea_db_payload_len(db);
-
-   if (cea_db_tag(db) == CEA_DB_VIDEO) {
-   video = db + 1;
-   video_len = dbl;
-   modes += do_cea_modes(connector, video, dbl);
-   } else if (cea_db_is_hdmi_vsdb(db)) {
-   hdmi = db;
-   hdmi_len = dbl;
-   } else if (cea_db_is_y420vdb(db)) {
-   const u8 *vdb420 = &db[2];
-
-   /* Add 4:2:0(only) modes present in EDID */
-   modes += do_y420vdb_modes(connector,
- vdb420,
- dbl - 1);
-   }
+   cea_db_iter_edid_begin(edid, &iter);
+   cea_db_iter_for_each(db, &iter) {
+   const u8 *hdmi = NULL, *video = NULL;
+   u8 hdmi_len = 0, video_len = 0;
+
+   if (cea_db_tag(db) == CEA_DB_VIDEO) {
+   video = cea_db_data(db);
+   video_len = cea_db_payload_len(db);
+   modes += do_cea_modes(connector, video, video_len);
+   } else if (cea_db_is_hdmi_vsdb(db)) {
+   /* FIXME: Switch to use cea_db_data() */
+   hdmi = (const u8 *)db;
+   hdmi_len = cea_db_payload_len(db);
+   } else if (cea_db_is_y420vdb(db)) {
+   const u8 *vdb420 = cea_db_data(db) + 1;
+
+   /* Add 4:2:0(only) modes present in EDID */
+   modes += do_y420vdb_modes(connector, vdb420,
+ cea_db_payload_len(db) - 1);
}
-   }
 
-   /*
-* We parse the HDMI VSDB after having added the cea modes as we will
-* be patching their flags when the sink supports stereo 3D.
-*/
-   if (hdmi)
-   modes += do_hdmi_vsdb_modes(connector, hdmi, hdmi_len, video,
-   video_len);
+   /*
+* We parse the HDMI VSDB after having added the cea modes as we
+* will be patching their flags when the sink supports stereo
+* 3D.
+*/
+   if (hdmi)
+   modes += do_hdmi_vsdb_modes(connector, hdmi, hdmi_len,
+   video, video_len);
+   }
+   cea_db_iter_end(&iter);
 
return modes;
 }
-- 
2.30.2



[RFC 09/19] drm/edid: convert drm_edid_to_sad() to use cea db iter

2022-03-22 Thread Jani Nikula
Use the cea db iterator for short audio descriptors. We'll still stop at
the first audio data block, but not at the first CEA extension if that
doesn't have the info.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 34 +-
 1 file changed, 9 insertions(+), 25 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index 992b3578a73f..e341790521d6 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -4854,40 +4854,21 @@ static void drm_edid_to_eld(struct drm_connector 
*connector, struct edid *edid)
  */
 int drm_edid_to_sad(struct edid *edid, struct cea_sad **sads)
 {
+   const struct cea_db *db;
+   struct cea_db_iter iter;
int count = 0;
-   int i, start, end, dbl;
-   const u8 *cea;
-
-   cea = drm_find_cea_extension(edid);
-   if (!cea) {
-   DRM_DEBUG_KMS("SAD: no CEA Extension found\n");
-   return 0;
-   }
-
-   if (cea_revision(cea) < 3) {
-   DRM_DEBUG_KMS("SAD: wrong CEA revision\n");
-   return 0;
-   }
-
-   if (cea_db_offsets(cea, &start, &end)) {
-   DRM_DEBUG_KMS("SAD: invalid data block offsets\n");
-   return -EPROTO;
-   }
-
-   for_each_cea_db(cea, i, start, end) {
-   const u8 *db = &cea[i];
 
+   cea_db_iter_edid_begin(edid, &iter);
+   cea_db_iter_for_each(db, &iter) {
if (cea_db_tag(db) == CEA_DB_AUDIO) {
int j;
 
-   dbl = cea_db_payload_len(db);
-
-   count = dbl / 3; /* SAD is 3B */
+   count = cea_db_payload_len(db) / 3; /* SAD is 3B */
*sads = kcalloc(count, sizeof(**sads), GFP_KERNEL);
if (!*sads)
return -ENOMEM;
for (j = 0; j < count; j++) {
-   const u8 *sad = &db[1 + j * 3];
+   const u8 *sad = &db->data[j * 3];
 
(*sads)[j].format = (sad[0] & 0x78) >> 3;
(*sads)[j].channels = sad[0] & 0x7;
@@ -4897,6 +4878,9 @@ int drm_edid_to_sad(struct edid *edid, struct cea_sad 
**sads)
break;
}
}
+   cea_db_iter_end(&iter);
+
+   DRM_DEBUG_KMS("Found %d Short Audio Descriptors\n", count);
 
return count;
 }
-- 
2.30.2



[RFC 08/19] drm/edid: convert drm_edid_to_speaker_allocation() to use cea db iter

2022-03-22 Thread Jani Nikula
Use the cea db iterator for speaker allocation. We'll still stop at the
first speaker data block, but not at the first CEA extension if that
doesn't have the info.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 47 --
 1 file changed, 15 insertions(+), 32 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index d92ce5d540c3..992b3578a73f 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -4916,42 +4916,25 @@ EXPORT_SYMBOL(drm_edid_to_sad);
  */
 int drm_edid_to_speaker_allocation(struct edid *edid, u8 **sadb)
 {
+   const struct cea_db *db;
+   struct cea_db_iter iter;
int count = 0;
-   int i, start, end, dbl;
-   const u8 *cea;
 
-   cea = drm_find_cea_extension(edid);
-   if (!cea) {
-   DRM_DEBUG_KMS("SAD: no CEA Extension found\n");
-   return 0;
-   }
-
-   if (cea_revision(cea) < 3) {
-   DRM_DEBUG_KMS("SAD: wrong CEA revision\n");
-   return 0;
-   }
-
-   if (cea_db_offsets(cea, &start, &end)) {
-   DRM_DEBUG_KMS("SAD: invalid data block offsets\n");
-   return -EPROTO;
-   }
-
-   for_each_cea_db(cea, i, start, end) {
-   const u8 *db = &cea[i];
-
-   if (cea_db_tag(db) == CEA_DB_SPEAKER) {
-   dbl = cea_db_payload_len(db);
-
-   /* Speaker Allocation Data Block */
-   if (dbl == 3) {
-   *sadb = kmemdup(&db[1], dbl, GFP_KERNEL);
-   if (!*sadb)
-   return -ENOMEM;
-   count = dbl;
-   break;
-   }
+   cea_db_iter_edid_begin(edid, &iter);
+   cea_db_iter_for_each(db, &iter) {
+   if (cea_db_tag(db) == CEA_DB_SPEAKER &&
+   cea_db_payload_len(db) == 3) {
+   *sadb = kmemdup(db->data, cea_db_payload_len(db),
+   GFP_KERNEL);
+   if (!*sadb)
+   return -ENOMEM;
+   count = cea_db_payload_len(db);
+   break;
}
}
+   cea_db_iter_end(&iter);
+
+   DRM_DEBUG_KMS("Found %d Speaker Allocation Data Blocks\n", count);
 
return count;
 }
-- 
2.30.2



[RFC 10/19] drm/edid: convert drm_detect_hdmi_monitor() to use cea db iter

2022-03-22 Thread Jani Nikula
Iterate through all CEA data blocks, not just the first CEA extension.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 25 +++--
 1 file changed, 11 insertions(+), 14 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index e341790521d6..399e69dc1aed 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -4978,27 +4978,24 @@ EXPORT_SYMBOL(drm_av_sync_delay);
  */
 bool drm_detect_hdmi_monitor(struct edid *edid)
 {
-   const u8 *edid_ext;
-   int i;
-   int start_offset, end_offset;
-
-   edid_ext = drm_find_cea_extension(edid);
-   if (!edid_ext)
-   return false;
-
-   if (cea_db_offsets(edid_ext, &start_offset, &end_offset))
-   return false;
+   const struct cea_db *db;
+   struct cea_db_iter iter;
+   bool hdmi = false;
 
/*
 * Because HDMI identifier is in Vendor Specific Block,
 * search it from all data blocks of CEA extension.
 */
-   for_each_cea_db(edid_ext, i, start_offset, end_offset) {
-   if (cea_db_is_hdmi_vsdb(&edid_ext[i]))
-   return true;
+   cea_db_iter_edid_begin(edid, &iter);
+   cea_db_iter_for_each(db, &iter) {
+   if (cea_db_is_hdmi_vsdb(db)) {
+   hdmi = true;
+   break;
+   }
}
+   cea_db_iter_end(&iter);
 
-   return false;
+   return hdmi;
 }
 EXPORT_SYMBOL(drm_detect_hdmi_monitor);
 
-- 
2.30.2



[RFC 11/19] drm/edid: convert drm_detect_monitor_audio() to use cea db iter

2022-03-22 Thread Jani Nikula
Iterate through all CEA data blocks.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 23 +--
 1 file changed, 13 insertions(+), 10 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index 399e69dc1aed..77763d94dd93 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -5013,10 +5013,10 @@ EXPORT_SYMBOL(drm_detect_hdmi_monitor);
  */
 bool drm_detect_monitor_audio(struct edid *edid)
 {
+   const struct cea_db *db;
+   struct cea_db_iter iter;
const u8 *edid_ext;
-   int i, j;
bool has_audio = false;
-   int start_offset, end_offset;
 
edid_ext = drm_find_cea_extension(edid);
if (!edid_ext)
@@ -5029,18 +5029,21 @@ bool drm_detect_monitor_audio(struct edid *edid)
goto end;
}
 
-   if (cea_db_offsets(edid_ext, &start_offset, &end_offset))
-   goto end;
+   cea_db_iter_edid_begin(edid, &iter);
+   cea_db_iter_for_each(db, &iter) {
+   if (cea_db_tag(db) == CEA_DB_AUDIO) {
+   const u8 *data = cea_db_data(db);
+   int i;
 
-   for_each_cea_db(edid_ext, i, start_offset, end_offset) {
-   if (cea_db_tag(&edid_ext[i]) == CEA_DB_AUDIO) {
-   has_audio = true;
-   for (j = 1; j < cea_db_payload_len(&edid_ext[i]) + 1; j 
+= 3)
+   for (i = 0; i < cea_db_payload_len(db); i += 3)
DRM_DEBUG_KMS("CEA audio format %d\n",
- (edid_ext[i + j] >> 3) & 0xf);
-   goto end;
+ (data[i] >> 3) & 0xf);
+   has_audio = true;
+   break;
}
}
+   cea_db_iter_end(&iter);
+
 end:
return has_audio;
 }
-- 
2.30.2



[RFC 13/19] drm/edid: convert drm_edid_to_eld() to use cea db iter

2022-03-22 Thread Jani Nikula
Iterate through all CEA data blocks across all CEA extensions and
DisplayID data blocks. This may gather more data than before, and if
there's duplicated data, some is overwritten by whichever comes last.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 64 +-
 1 file changed, 29 insertions(+), 35 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index d4bf9ef09c3c..ccbaa91b171d 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -4758,12 +4758,12 @@ static void clear_eld(struct drm_connector *connector)
  */
 static void drm_edid_to_eld(struct drm_connector *connector, struct edid *edid)
 {
+   const struct cea_db *db;
+   struct cea_db_iter iter;
uint8_t *eld = connector->eld;
const u8 *cea;
-   const u8 *db;
int total_sad_count = 0;
int mnl;
-   int dbl;
 
clear_eld(connector);
 
@@ -4789,43 +4789,37 @@ static void drm_edid_to_eld(struct drm_connector 
*connector, struct edid *edid)
eld[DRM_ELD_PRODUCT_CODE0] = edid->prod_code[0];
eld[DRM_ELD_PRODUCT_CODE1] = edid->prod_code[1];
 
-   if (cea_revision(cea) >= 3) {
-   int i, start, end;
+   cea_db_iter_edid_begin(edid, &iter);
+   cea_db_iter_for_each(db, &iter) {
+   const u8 *data = cea_db_data(db);
+   int len = cea_db_payload_len(db);
int sad_count;
 
-   if (cea_db_offsets(cea, &start, &end)) {
-   start = 0;
-   end = 0;
-   }
-
-   for_each_cea_db(cea, i, start, end) {
-   db = &cea[i];
-   dbl = cea_db_payload_len(db);
-
-   switch (cea_db_tag(db)) {
-   case CEA_DB_AUDIO:
-   /* Audio Data Block, contains SADs */
-   sad_count = min(dbl / 3, 15 - total_sad_count);
-   if (sad_count >= 1)
-   memcpy(&eld[DRM_ELD_CEA_SAD(mnl, 
total_sad_count)],
-  &db[1], sad_count * 3);
-   total_sad_count += sad_count;
-   break;
-   case CEA_DB_SPEAKER:
-   /* Speaker Allocation Data Block */
-   if (dbl >= 1)
-   eld[DRM_ELD_SPEAKER] = db[1];
-   break;
-   case CEA_DB_VENDOR:
-   /* HDMI Vendor-Specific Data Block */
-   if (cea_db_is_hdmi_vsdb(db))
-   drm_parse_hdmi_vsdb_audio(connector, 
db);
-   break;
-   default:
-   break;
-   }
+   switch (cea_db_tag(db)) {
+   case CEA_DB_AUDIO:
+   /* Audio Data Block, contains SADs */
+   sad_count = min(len / 3, 15 - total_sad_count);
+   if (sad_count >= 1)
+   memcpy(&eld[DRM_ELD_CEA_SAD(mnl, 
total_sad_count)],
+  data, sad_count * 3);
+   total_sad_count += sad_count;
+   break;
+   case CEA_DB_SPEAKER:
+   /* Speaker Allocation Data Block */
+   if (len >= 1)
+   eld[DRM_ELD_SPEAKER] = data[0];
+   break;
+   case CEA_DB_VENDOR:
+   /* HDMI Vendor-Specific Data Block */
+   if (cea_db_is_hdmi_vsdb(db))
+   drm_parse_hdmi_vsdb_audio(connector, (const u8 
*)db);
+   break;
+   default:
+   break;
}
}
+   cea_db_iter_end(&iter);
+
eld[DRM_ELD_SAD_COUNT_CONN_TYPE] |= total_sad_count << 
DRM_ELD_SAD_COUNT_SHIFT;
 
if (connector->connector_type == DRM_MODE_CONNECTOR_DisplayPort ||
-- 
2.30.2



[RFC 12/19] drm/edid: convert drm_parse_cea_ext() to use cea db iter

2022-03-22 Thread Jani Nikula
Iterate through all CEA data blocks across all CEA extensions and
DisplayID data blocks.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 25 +
 1 file changed, 13 insertions(+), 12 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index 77763d94dd93..d4bf9ef09c3c 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -5342,8 +5342,9 @@ static void drm_parse_cea_ext(struct drm_connector 
*connector,
  const struct edid *edid)
 {
struct drm_display_info *info = &connector->display_info;
+   const struct cea_db *db;
+   struct cea_db_iter iter;
const u8 *edid_ext;
-   int i, start, end;
 
edid_ext = drm_find_cea_extension(edid);
if (!edid_ext)
@@ -5358,25 +5359,25 @@ static void drm_parse_cea_ext(struct drm_connector 
*connector,
if (edid_ext[3] & EDID_CEA_YCRCB422)
info->color_formats |= DRM_COLOR_FORMAT_YCBCR422;
 
-   if (cea_db_offsets(edid_ext, &start, &end))
-   return;
-
-   for_each_cea_db(edid_ext, i, start, end) {
-   const u8 *db = &edid_ext[i];
+   cea_db_iter_edid_begin(edid, &iter);
+   cea_db_iter_for_each(db, &iter) {
+   /* FIXME: convert parsers to use struct cea_db */
+   const u8 *data = (const u8 *)db;
 
if (cea_db_is_hdmi_vsdb(db))
-   drm_parse_hdmi_vsdb_video(connector, db);
+   drm_parse_hdmi_vsdb_video(connector, data);
if (cea_db_is_hdmi_forum_vsdb(db))
-   drm_parse_hdmi_forum_vsdb(connector, db);
+   drm_parse_hdmi_forum_vsdb(connector, data);
if (cea_db_is_microsoft_vsdb(db))
-   drm_parse_microsoft_vsdb(connector, db);
+   drm_parse_microsoft_vsdb(connector, data);
if (cea_db_is_y420cmdb(db))
-   drm_parse_y420cmdb_bitmap(connector, db);
+   drm_parse_y420cmdb_bitmap(connector, data);
if (cea_db_is_vcdb(db))
-   drm_parse_vcdb(connector, db);
+   drm_parse_vcdb(connector, data);
if (cea_db_is_hdmi_hdr_metadata_block(db))
-   drm_parse_hdr_metadata_block(connector, db);
+   drm_parse_hdr_metadata_block(connector, data);
}
+   cea_db_iter_end(&iter);
 }
 
 static
-- 
2.30.2



[RFC 15/19] drm/edid: restore some type safety to cea_db_*() functions

2022-03-22 Thread Jani Nikula
During the transition, we accepted a void pointer for a poor C
programmer's version of polymorphism. Switch the functions to use struct
cea_db * to regain some more type safety.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 19 ---
 1 file changed, 8 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index 0400c4024de7..b3aedeefed82 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -4244,11 +4244,8 @@ struct cea_db {
u8 data[];
 } __packed;
 
-static int cea_db_tag(const void *_db)
+static int cea_db_tag(const struct cea_db *db)
 {
-   /* FIXME: Transition to passing struct cea_db * everywhere. */
-   const struct cea_db *db = _db;
-
return db->tag_length >> 5;
 }
 
@@ -4411,41 +4408,41 @@ static void cea_db_iter_end(struct cea_db_iter *iter)
memset(iter, 0, sizeof(*iter));
 }
 
-static bool cea_db_is_hdmi_vsdb(const void *db)
+static bool cea_db_is_hdmi_vsdb(const struct cea_db *db)
 {
return (cea_db_is_vendor(db, HDMI_IEEE_OUI) &&
cea_db_payload_len(db) >= 5);
 }
 
-static bool cea_db_is_hdmi_forum_vsdb(const void *db)
+static bool cea_db_is_hdmi_forum_vsdb(const struct cea_db *db)
 {
return (cea_db_is_vendor(db, HDMI_FORUM_IEEE_OUI) &&
cea_db_payload_len(db) >= 7);
 }
 
-static bool cea_db_is_microsoft_vsdb(const void *db)
+static bool cea_db_is_microsoft_vsdb(const struct cea_db *db)
 {
return (cea_db_is_vendor(db, MICROSOFT_IEEE_OUI) &&
cea_db_payload_len(db) == 21);
 }
 
-static bool cea_db_is_vcdb(const void *db)
+static bool cea_db_is_vcdb(const struct cea_db *db)
 {
return (cea_db_is_extended_tag(db, CEA_EXT_DB_VIDEO_CAP) &&
cea_db_payload_len(db) == 2);
 }
 
-static bool cea_db_is_y420cmdb(const void *db)
+static bool cea_db_is_y420cmdb(const struct cea_db *db)
 {
return cea_db_is_extended_tag(db, CEA_EXT_DB_420_VIDEO_CAP_MAP);
 }
 
-static bool cea_db_is_y420vdb(const void *db)
+static bool cea_db_is_y420vdb(const struct cea_db *db)
 {
return cea_db_is_extended_tag(db, CEA_EXT_DB_420_VIDEO_DATA);
 }
 
-static bool cea_db_is_hdmi_hdr_metadata_block(const void *db)
+static bool cea_db_is_hdmi_hdr_metadata_block(const struct cea_db *db)
 {
return (cea_db_is_extended_tag(db, CEA_EXT_DB_HDR_STATIC_METADATA) &&
cea_db_payload_len(db) >= 3);
-- 
2.30.2



[RFC 14/19] drm/edid: sunset the old unused cea data block iterators

2022-03-22 Thread Jani Nikula
All CEA data block iteration has now been converted to the new cea db
iterators.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 45 --
 1 file changed, 45 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index ccbaa91b171d..0400c4024de7 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -4209,48 +4209,6 @@ cea_revision(const u8 *cea)
return cea[1];
 }
 
-static int
-cea_db_offsets(const u8 *cea, int *start, int *end)
-{
-   /* DisplayID CTA extension blocks and top-level CEA EDID
-* block header definitions differ in the following bytes:
-*   1) Byte 2 of the header specifies length differently,
-*   2) Byte 3 is only present in the CEA top level block.
-*
-* The different definitions for byte 2 follow.
-*
-* DisplayID CTA extension block defines byte 2 as:
-*   Number of payload bytes
-*
-* CEA EDID block defines byte 2 as:
-*   Byte number (decimal) within this block where the 18-byte
-*   DTDs begin. If no non-DTD data is present in this extension
-*   block, the value should be set to 04h (the byte after next).
-*   If set to 00h, there are no DTDs present in this block and
-*   no non-DTD data.
-*/
-   if (cea[0] == DATA_BLOCK_CTA) {
-   /*
-* for_each_displayid_db() has already verified
-* that these stay within expected bounds.
-*/
-   *start = 3;
-   *end = *start + cea[2];
-   } else if (cea[0] == CEA_EXT) {
-   /* Data block offset in CEA extension block */
-   *start = 4;
-   *end = cea[2];
-   if (*end == 0)
-   *end = 127;
-   if (*end < 4 || *end > 127)
-   return -ERANGE;
-   } else {
-   return -EOPNOTSUPP;
-   }
-
-   return 0;
-}
-
 /*
  * CEA Data Block iterator.
  *
@@ -4493,9 +4451,6 @@ static bool cea_db_is_hdmi_hdr_metadata_block(const void 
*db)
cea_db_payload_len(db) >= 3);
 }
 
-#define for_each_cea_db(cea, i, start, end) \
-   for ((i) = (start); (i) < (end) && (i) + 
cea_db_payload_len(&(cea)[(i)]) < (end); (i) += cea_db_payload_len(&(cea)[(i)]) 
+ 1)
-
 static void drm_parse_y420cmdb_bitmap(struct drm_connector *connector,
  const u8 *db)
 {
-- 
2.30.2



[RFC 18/19] drm/edid: skip CEA extension scan in drm_edid_to_eld() just for CEA rev

2022-03-22 Thread Jani Nikula
The DisplayID CTA data block version does not necessarily match the CEA
revision. Simplify by postponing drm_edid_to_eld() slightly, and reusing
the CEA revision extracted by drm_parse_cea_ext().

By not bailing out early in drm_edid_to_eld() we may end up filling
meaningless data to the ELD. However, the main decision for audio is not
the ELD, but rather drm_detect_monitor_audio() called by drivers.

(Arguably a future cleanup could do that in drm_add_edid_modes() and
cache the result in the connector.)

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 15 +--
 1 file changed, 5 insertions(+), 10 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index f40427dc5236..dfaa21f00941 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -4710,10 +4710,10 @@ static void clear_eld(struct drm_connector *connector)
  */
 static void drm_edid_to_eld(struct drm_connector *connector, struct edid *edid)
 {
+   struct drm_display_info *info = &connector->display_info;
const struct cea_db *db;
struct cea_db_iter iter;
uint8_t *eld = connector->eld;
-   const u8 *cea;
int total_sad_count = 0;
int mnl;
 
@@ -4722,16 +4722,10 @@ static void drm_edid_to_eld(struct drm_connector 
*connector, struct edid *edid)
if (!edid)
return;
 
-   cea = drm_find_cea_extension(edid);
-   if (!cea) {
-   DRM_DEBUG_KMS("ELD: no CEA Extension found\n");
-   return;
-   }
-
mnl = get_monitor_name(edid, &eld[DRM_ELD_MONITOR_NAME_STRING]);
DRM_DEBUG_KMS("ELD monitor %s\n", &eld[DRM_ELD_MONITOR_NAME_STRING]);
 
-   eld[DRM_ELD_CEA_EDID_VER_MNL] = cea[1] << DRM_ELD_CEA_EDID_VER_SHIFT;
+   eld[DRM_ELD_CEA_EDID_VER_MNL] = info->cea_rev << 
DRM_ELD_CEA_EDID_VER_SHIFT;
eld[DRM_ELD_CEA_EDID_VER_MNL] |= mnl;
 
eld[DRM_ELD_VER] = DRM_ELD_VER_CEA861D;
@@ -5681,8 +5675,6 @@ int drm_add_edid_modes(struct drm_connector *connector, 
struct edid *edid)
return 0;
}
 
-   drm_edid_to_eld(connector, edid);
-
/*
 * CEA-861-F adds ycbcr capability map block, for HDMI 2.0 sinks.
 * To avoid multiple parsing of same block, lets parse that map
@@ -5690,6 +5682,9 @@ int drm_add_edid_modes(struct drm_connector *connector, 
struct edid *edid)
 */
quirks = drm_add_display_info(connector, edid);
 
+   /* Depends on info->cea_rev set by drm_add_display_info() above */
+   drm_edid_to_eld(connector, edid);
+
/*
 * EDID spec says modes should be preferred in this order:
 * - preferred detailed mode
-- 
2.30.2



[RFC 17/19] drm/edid: detect color formats and CEA revision only on CEA extension

2022-03-22 Thread Jani Nikula
The CTA data block in DisplayID does not have the bits from byte 3 that
a CEA extension has. Only look for them in CEA extensions, but also look
for them in all CEA extensions.

The DisplayID CTA data block version does not seem to match the CEA
revision either. Ignore it for the purpose of CEA revision.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 31 ---
 1 file changed, 20 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index b6675f8638bb..f40427dc5236 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -5293,22 +5293,31 @@ static void drm_parse_cea_ext(struct drm_connector 
*connector,
  const struct edid *edid)
 {
struct drm_display_info *info = &connector->display_info;
+   struct drm_edid_iter edid_iter;
const struct cea_db *db;
struct cea_db_iter iter;
-   const u8 *edid_ext;
+   const u8 *cea;
 
-   edid_ext = drm_find_cea_extension(edid);
-   if (!edid_ext)
-   return;
+   drm_edid_iter_begin(edid, &edid_iter);
+   drm_edid_iter_for_each(cea, &edid_iter) {
+   if (cea[0] != CEA_EXT)
+   continue;
 
-   info->cea_rev = edid_ext[1];
+   if (!info->cea_rev)
+   info->cea_rev = cea[1];
 
-   /* The existence of a CEA block should imply RGB support */
-   info->color_formats = DRM_COLOR_FORMAT_RGB444;
-   if (edid_ext[3] & EDID_CEA_YCRCB444)
-   info->color_formats |= DRM_COLOR_FORMAT_YCBCR444;
-   if (edid_ext[3] & EDID_CEA_YCRCB422)
-   info->color_formats |= DRM_COLOR_FORMAT_YCBCR422;
+   if (info->cea_rev != cea[1])
+   DRM_DEBUG_KMS("CEA extension version mismatch %u != 
%u\n",
+ info->cea_rev, cea[1]);
+
+   /* The existence of a CEA block should imply RGB support */
+   info->color_formats = DRM_COLOR_FORMAT_RGB444;
+   if (cea[3] & EDID_CEA_YCRCB444)
+   info->color_formats |= DRM_COLOR_FORMAT_YCBCR444;
+   if (cea[3] & EDID_CEA_YCRCB422)
+   info->color_formats |= DRM_COLOR_FORMAT_YCBCR422;
+   }
+   drm_edid_iter_end(&edid_iter);
 
cea_db_iter_edid_begin(edid, &iter);
cea_db_iter_for_each(db, &iter) {
-- 
2.30.2



[RFC 19/19] drm/edid: sunset drm_find_cea_extension()

2022-03-22 Thread Jani Nikula
Convert drm_find_cea_extension() to a predicate function to check if the
EDID has a CEA extension or a DisplayID CTA data block. This is mainly
to avoid adding new users that only find the first CEA extension.

Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 17 -
 1 file changed, 8 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index dfaa21f00941..84314b65b75b 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -3422,30 +3422,29 @@ const u8 *drm_find_edid_extension(const struct edid 
*edid,
return edid_ext;
 }
 
-static const u8 *drm_find_cea_extension(const struct edid *edid)
+/* Return true if the EDID has a CEA extension or a DisplayID CTA data block */
+static bool drm_edid_has_cea_extension(const struct edid *edid)
 {
const struct displayid_block *block;
struct displayid_iter iter;
-   const u8 *cea;
int ext_index = 0;
+   bool found = false;
 
/* Look for a top level CEA extension block */
-   /* FIXME: make callers iterate through multiple CEA ext blocks? */
-   cea = drm_find_edid_extension(edid, CEA_EXT, &ext_index);
-   if (cea)
-   return cea;
+   if (drm_find_edid_extension(edid, CEA_EXT, &ext_index))
+   return true;
 
/* CEA blocks can also be found embedded in a DisplayID block */
displayid_iter_edid_begin(edid, &iter);
displayid_iter_for_each(block, &iter) {
if (block->tag == DATA_BLOCK_CTA) {
-   cea = (const u8 *)block;
+   found = true;
break;
}
}
displayid_iter_end(&iter);
 
-   return cea;
+   return found;
 }
 
 static __always_inline const struct drm_display_mode *cea_mode_for_vic(u8 vic)
@@ -3715,7 +3714,7 @@ add_alternate_cea_modes(struct drm_connector *connector, 
struct edid *edid)
int modes = 0;
 
/* Don't add CEA modes if the CEA extension block is missing */
-   if (!drm_find_cea_extension(edid))
+   if (!drm_edid_has_cea_extension(edid))
return 0;
 
/*
-- 
2.30.2



[RFC 16/19] drm/edid: detect basic audio only on CEA extension

2022-03-22 Thread Jani Nikula
The CTA data block in DisplayID does not have the bits from byte 3 that
a CEA extension has. Only look for them in CEA extensions, but also look
for them in all CEA extensions.

References: 
https://patchwork.freedesktop.org/patch/msgid/20220321044330.27723-1-cooper.ch...@intel.com
Signed-off-by: Jani Nikula 
---
 drivers/gpu/drm/drm_edid.c | 17 +++--
 1 file changed, 11 insertions(+), 6 deletions(-)

diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c
index b3aedeefed82..b6675f8638bb 100644
--- a/drivers/gpu/drm/drm_edid.c
+++ b/drivers/gpu/drm/drm_edid.c
@@ -4959,16 +4959,21 @@ EXPORT_SYMBOL(drm_detect_hdmi_monitor);
  */
 bool drm_detect_monitor_audio(struct edid *edid)
 {
+   struct drm_edid_iter edid_iter;
const struct cea_db *db;
struct cea_db_iter iter;
-   const u8 *edid_ext;
+   const u8 *cea;
bool has_audio = false;
 
-   edid_ext = drm_find_cea_extension(edid);
-   if (!edid_ext)
-   goto end;
-
-   has_audio = ((edid_ext[3] & EDID_BASIC_AUDIO) != 0);
+   drm_edid_iter_begin(edid, &edid_iter);
+   drm_edid_iter_for_each(cea, &edid_iter) {
+   if (cea[0] == CEA_EXT) {
+   has_audio = cea[3] & EDID_BASIC_AUDIO;
+   if (has_audio)
+   break;
+   }
+   }
+   drm_edid_iter_end(&edid_iter);
 
if (has_audio) {
DRM_DEBUG_KMS("Monitor has basic audio support\n");
-- 
2.30.2



Re: [PATCH 1/7] drm/gma500: Use managed drmm_mode_config_init()

2022-03-22 Thread Patrik Jakobsson
On Tue, Mar 22, 2022 at 8:32 PM Thomas Zimmermann  wrote:
>
>
>
> Am 22.03.22 um 20:30 schrieb Thomas Zimmermann:
> > Hi Patrik
> >
> > Am 22.03.22 um 14:17 schrieb Patrik Jakobsson:
> >> Signed-off-by: Patrik Jakobsson 
> >> ---
> >>   drivers/gpu/drm/gma500/framebuffer.c | 4 ++--
> >>   1 file changed, 2 insertions(+), 2 deletions(-)
> >>
> >> diff --git a/drivers/gpu/drm/gma500/framebuffer.c
> >> b/drivers/gpu/drm/gma500/framebuffer.c
> >> index 45df9de22007..2b99c996fdc2 100644
> >> --- a/drivers/gpu/drm/gma500/framebuffer.c
> >> +++ b/drivers/gpu/drm/gma500/framebuffer.c
> >> @@ -514,7 +514,8 @@ void psb_modeset_init(struct drm_device *dev)
> >>   struct pci_dev *pdev = to_pci_dev(dev->dev);
> >>   int i;
> >> -drm_mode_config_init(dev);
> >> +if (drmm_mode_config_init(dev))
> >> +return;
> >
> > This will fail without any notice. I suggest to return an error here or
> > at let psb_driver_load() fail.
>
> 'and let psb_driver_load() fail'

Hi Thomas,
I did consider it but there are more places where psb_driver_load()
can fail so I think it deserves its own patch.

I'll send a follow-up.

-Patrik

>
> >
> > Best regards
> > Thomas
> >
> >>   dev->mode_config.min_width = 0;
> >>   dev->mode_config.min_height = 0;
> >> @@ -546,6 +547,5 @@ void psb_modeset_cleanup(struct drm_device *dev)
> >>   if (dev_priv->modeset) {
> >>   drm_kms_helper_poll_fini(dev);
> >>   psb_fbdev_fini(dev);
> >> -drm_mode_config_cleanup(dev);
> >>   }
> >>   }
> >
>
> --
> Thomas Zimmermann
> Graphics Driver Developer
> SUSE Software Solutions Germany GmbH
> Maxfeldstr. 5, 90409 Nürnberg, Germany
> (HRB 36809, AG Nürnberg)
> Geschäftsführer: Ivo Totev


  1   2   >