Re: [RFC PATCH 3/5] drm/amdgpu: Allow explicit sync for VM ops.

2022-06-15 Thread Christian König

Am 06.06.22 um 13:00 schrieb Bas Nieuwenhuizen:

On Mon, Jun 6, 2022 at 12:35 PM Christian König
 wrote:

[SNIP]
That part won't work at all and would cause additional synchronization
problems.

First of all for implicit synced CS we should use READ, not BOOKKEEP.
Because BOOKKEEP would incorrectly be ignored by OpenGL importers. I've
fixed that this causes memory corruption, but it is still nice to avoid.

Yes, what I'm saying is that on implicit sync CS submission should add
READ fences to the dma resv and on explicit sync CS submission should
add BOOKKEEP fences.


No, exactly that is wrong.

Implicit CS submissions should add WRITE fences.

Explicit CS submissions should add READ fences.

Only VM updates should add BOOKKEEP fences.


BOOKKEEP can only be used by VM updates themselves. So that they don't
interfere with CS.

That is the point why we would go BOOKKEEP for explicit sync CS
submissions, no? Explicit submission shouldn't interfere with any
other CS submissions. That includes being totally ignored by GL
importers (if we want to have synchronization there between an
explicit submission and GL, userspace is expected to use Jason's
dmabuf fence import/export IOCTLs)


No, that would break existing DMA-buf rules.

Explicit CS submissions are still a dependency for implicit submissions.



Then the second problem is that the VM IOCTL has absolutely no idea what
the CS IOCTL would be doing. That's why we have added the EXPLICIT sync
flag on the BO.
It doesn't need to? We just use a different sync_mode for BOOKKEEP
fences vs others:
https://nam11.safelinks.protection.outlook.com/?url=https%3A%2F%2Fpatchwork.freedesktop.org%2Fpatch%2F487887%2F%3Fseries%3D104578%26rev%3D2&data=05%7C01%7Cchristian.koenig%40amd.com%7C81db0fea1c854076fc4408da47abafaa%7C3dd8961fe4884e608e11a82d994e183d%7C0%7C0%7C637901099957139870%7CUnknown%7CTWFpbGZsb3d8eyJWIjoiMC4wLjAwMDAiLCJQIjoiV2luMzIiLCJBTiI6Ik1haWwiLCJXVCI6Mn0%3D%7C3000%7C%7C%7C&sdata=F72Boaesx83MD2pjGuucA1buawi205XLSsQHg5EH39A%3D&reserved=0


No, exactly that's completely broken.

Regards,
Christian.



(the nice thing about doing it this way is that it is independent of
the IOCTL, i.e. also works for the delayed mapping changes we trigger
on CS submit)


Regards,
Christian.


That should be doable, but then you don't need any of the other changes.

Regards,
Christian.


#1 Is rather easy to fix, you just need to copy all dma_fences from the
page table dma_resv object over to the BOs dma_resv object in the gem
close handler. E.g. exactly what you suggested with the dma_resv_copy
function.

#2 is a nightmare.

We can't move the TLB flush at the end of the unmap operation because on
async TLB flushes are either a bit complicated (double flushes etc..) or
don't even work at all because of hw bugs. So to have a reliable TLB
flush we must make sure that nothing else is ongoing and that means
CS->VM->CS barrier.

We try very hard to circumvent that already on maps by (for example)
using a completely new VMID for CS after the VM map operation.

But for the unmap operation we would need some kind special dma_fence
implementation which would not only wait for all existing dma_fence but
also for the one added until the unmap operation is completed. Cause
otherwise our operation we do at #1 would simply not catch all
dma_fences which have access to the memory.

That's certainly doable, but I think just using the drm_exec stuff I
already came up with is easier.

When we can grab locks for all the BOs involved amdgpu_vm_clear_freed()
goes away and we can keep track of the unmap operations in the bo_va
structure.

With that done you can make the explicit sync you noted in the bo_va
structure and implicit sync when the bo_va structure goes away.

Then the only reason I can see why we would need a CS->VM dependency is
implicit synchronization, and that's what we are trying to avoid here in
the first place.

Regards,
Christian.


To get rid of this barrier you must first fix the part where CS
submissions wait for the VM operation to complete, e.g. the necessity of
the barrier.

I'm working on this for a couple of years now and I'm really running out
of idea how to explain this restriction.

Regards,
Christian.





Re: [RFC PATCH 3/5] drm/amdgpu: Allow explicit sync for VM ops.

2022-06-15 Thread Christian König

Hi Bas,

sorry I totally missed your reply. Just tried to answer your original 
questions.


Regards,
Christian.

Am 15.06.22 um 02:40 schrieb Bas Nieuwenhuizen:

Hi Christian,

Friendly ping on the comments here. Are you okay with me re-spinning
the series with a fixed patch 1 or do we need further discussion on
the approach here?

Thanks,
Bas

On Mon, Jun 6, 2022 at 1:00 PM Bas Nieuwenhuizen
 wrote:

On Mon, Jun 6, 2022 at 12:35 PM Christian König
 wrote:

Am 06.06.22 um 12:30 schrieb Bas Nieuwenhuizen:

On Mon, Jun 6, 2022 at 12:15 PM Christian König
 wrote:


Am 03.06.22 um 21:11 schrieb Bas Nieuwenhuizen:

On Fri, Jun 3, 2022 at 8:41 PM Christian König  wrote:

Am 03.06.22 um 19:50 schrieb Bas Nieuwenhuizen:

[SNIP]

Yeah, but that's exactly the bubble we try to avoid. Isn't it?

For this series, not really.  To clarify there are two sides for
getting GPU bubbles and no overlap:

(1) VM operations implicitly wait for earlier CS submissions
(2) CS submissions implicitly wait for earlier VM operations

Together, these combine to ensure that you get a (potentially small)
bubble any time VM work happens.

Your series (and further ideas) tackles (2), and is a worthwhile thing
to do. However, while writing the userspace for this I noticed this
isn't enough to get rid of all our GPU bubbles. In particular when
doing a non-sparse map of a new BO, that tends to need to be waited on
for the next CS anyway for API semantics. Due to VM operations
happening on a single timeline that means this high priority map can
end up being blocked by earlier sparse maps and hence the bubble in
that case still exists.

So in this series I try to tackle (1) instead. Since GPU work
typically lags behind CPU submissions and VM operations aren't that
slow, we can typically execute VM operations early enough that any
implicit syncs from (2) are less/no issue.

Ok, once more since you don't seem to understand what I want to say: It
isn't possible to fix #1 before you have fixed #2.

The VM unmap operation here is a barrier which divides the CS operations
in a before and after. This is intentional design.

Why is that barrier needed? The two barriers I got and understood and
I think we can deal with:

1) the VM unmap is a barrier between prior CS and later memory free.
2) The TLB flush need to happen between a VM unmap and later CS.

But why do we need the VM unmap to be a strict barrier between prior
CS and later CS?

Exactly because of the two reasons you mentioned.

This is the part I'm not seeing. I get that removing #2 is a
nightmare, which is why I did something that doesn't violate that
constraint.

Like if an explicit CS that was running before the VM operation  runs
till after the VM operation (and hence possibly till after the TLB
flush, or otherwise have the TLB flush not apply due to lack of async
TLB flush support), that is not an issue. It might see the state from
before the unmap, or after the unmap, or some intermediate state and
all of those would be okay.

We still get the constraint that the TLB flush happens between the VM
unmap and later CS and hence the unmap is certainly visible to them.

So you basically just want to set the sync mode in
amdgpu_vm_update_range() to AMDGPU_SYNC_EXPLICIT even when it is an unmap?

Yes, with the caveat that I want to do that only for
DMA_RESV_USAGE_BOOKKEEP or higher (i.e. if we submit a CS with
implicit sync we get the old implicit behavior, if we submit a CS with
explicit sync we get the new explicit behavior). The rest of the
series is basically just for enabling explicit sync submissions.

That part won't work at all and would cause additional synchronization
problems.

First of all for implicit synced CS we should use READ, not BOOKKEEP.
Because BOOKKEEP would incorrectly be ignored by OpenGL importers. I've
fixed that this causes memory corruption, but it is still nice to avoid.

Yes, what I'm saying is that on implicit sync CS submission should add
READ fences to the dma resv and on explicit sync CS submission should
add BOOKKEEP fences.


BOOKKEEP can only be used by VM updates themselves. So that they don't
interfere with CS.

That is the point why we would go BOOKKEEP for explicit sync CS
submissions, no? Explicit submission shouldn't interfere with any
other CS submissions. That includes being totally ignored by GL
importers (if we want to have synchronization there between an
explicit submission and GL, userspace is expected to use Jason's
dmabuf fence import/export IOCTLs)


Then the second problem is that the VM IOCTL has absolutely no idea what
the CS IOCTL would be doing. That's why we have added the EXPLICIT sync
flag on the BO.

It doesn't need to? We just use a different sync_mode for BOOKKEEP
fences vs others:
https://nam11.safelinks.protection.outlook.com/?url=https%3A%2F%2Fpatchwork.freedesktop.org%2Fpatch%2F487887%2F%3Fseries%3D104578%26rev%3D2&data=05%7C01%7Cchristian.koenig%40amd.com%7C0c76d5c34db846f2fff208da4e67ad7b%7C3dd8961fe4884e608e11a82d994e183d%7

Re: [Intel-gfx] [PATCH 3/3] drm/doc/rfc: VM_BIND uapi definition

2022-06-15 Thread Tvrtko Ursulin



On 14/06/2022 17:42, Niranjana Vishwanathapura wrote:

On Tue, Jun 14, 2022 at 05:07:37PM +0100, Tvrtko Ursulin wrote:


On 14/06/2022 17:02, Tvrtko Ursulin wrote:


On 14/06/2022 16:43, Niranjana Vishwanathapura wrote:

On Tue, Jun 14, 2022 at 08:16:41AM +0100, Tvrtko Ursulin wrote:


On 14/06/2022 00:39, Matthew Brost wrote:

On Mon, Jun 13, 2022 at 07:09:06PM +0100, Tvrtko Ursulin wrote:


On 13/06/2022 18:49, Niranjana Vishwanathapura wrote:

On Mon, Jun 13, 2022 at 05:22:02PM +0100, Tvrtko Ursulin wrote:


On 13/06/2022 16:05, Niranjana Vishwanathapura wrote:

On Mon, Jun 13, 2022 at 09:24:18AM +0100, Tvrtko Ursulin wrote:


On 10/06/2022 17:14, Niranjana Vishwanathapura wrote:
On Fri, Jun 10, 2022 at 05:48:39PM +0300, Lionel Landwerlin 
wrote:

On 10/06/2022 13:37, Tvrtko Ursulin wrote:


On 10/06/2022 08:07, Niranjana Vishwanathapura wrote:

VM_BIND and related uapi definitions

Signed-off-by: Niranjana Vishwanathapura

---
  Documentation/gpu/rfc/i915_vm_bind.h | 490
+++
  1 file changed, 490 insertions(+)
  create mode 100644 Documentation/gpu/rfc/i915_vm_bind.h

diff --git
a/Documentation/gpu/rfc/i915_vm_bind.h
b/Documentation/gpu/rfc/i915_vm_bind.h
new file mode 100644
index ..9fc854969cfb
--- /dev/null
+++ b/Documentation/gpu/rfc/i915_vm_bind.h
@@ -0,0 +1,490 @@
+/* SPDX-License-Identifier: MIT */
+/*
+ * Copyright © 2022 Intel Corporation
+ */
+
+/**
+ * DOC: I915_PARAM_HAS_VM_BIND
+ *
+ * VM_BIND feature availability.
+ * See typedef drm_i915_getparam_t param.
+ * bit[0]: If set, VM_BIND is supported, otherwise not.
+ * bits[8-15]: VM_BIND implementation version.
+ * version 0 will not have VM_BIND/UNBIND
timeline fence array support.
+ */
+#define I915_PARAM_HAS_VM_BIND    57
+
+/**
+ * DOC: I915_VM_CREATE_FLAGS_USE_VM_BIND
+ *
+ * Flag to opt-in for VM_BIND mode of binding during VM 
creation.

+ * See struct drm_i915_gem_vm_control flags.
+ *
+ * The older execbuf2 ioctl will not
support VM_BIND mode of operation.
+ * For VM_BIND mode, we have new execbuf3
ioctl which will not accept any
+ * execlist (See struct
drm_i915_gem_execbuffer3 for more details).
+ *
+ */
+#define I915_VM_CREATE_FLAGS_USE_VM_BIND    (1 << 0)
+
+/**
+ * DOC: I915_CONTEXT_CREATE_FLAGS_LONG_RUNNING
+ *
+ * Flag to declare context as long running.
+ * See struct drm_i915_gem_context_create_ext flags.
+ *
+ * Usage of dma-fence expects that they
complete in reasonable amount of time.
+ * Compute on the other hand can be long
running. Hence it is not appropriate
+ * for compute contexts to export request
completion dma-fence to user.
+ * The dma-fence usage will be limited to
in-kernel consumption only.
+ * Compute contexts need to use user/memory fence.
+ *
+ * So, long running contexts do not support output 
fences. Hence,

+ * I915_EXEC_FENCE_SIGNAL (See
&drm_i915_gem_exec_fence.flags) is expected
+ * to be not used. DRM_I915_GEM_WAIT ioctl
call is also not supported for
+ * objects mapped to long running contexts.
+ */
+#define I915_CONTEXT_CREATE_FLAGS_LONG_RUNNING   (1u << 2)
+
+/* VM_BIND related ioctls */
+#define DRM_I915_GEM_VM_BIND    0x3d
+#define DRM_I915_GEM_VM_UNBIND    0x3e
+#define DRM_I915_GEM_EXECBUFFER3    0x3f
+#define DRM_I915_GEM_WAIT_USER_FENCE    0x40
+
+#define DRM_IOCTL_I915_GEM_VM_BIND
DRM_IOWR(DRM_COMMAND_BASE +
DRM_I915_GEM_VM_BIND, struct
drm_i915_gem_vm_bind)
+#define DRM_IOCTL_I915_GEM_VM_UNBIND
DRM_IOWR(DRM_COMMAND_BASE +
DRM_I915_GEM_VM_UNBIND, struct
drm_i915_gem_vm_bind)
+#define DRM_IOCTL_I915_GEM_EXECBUFFER3
DRM_IOWR(DRM_COMMAND_BASE +
DRM_I915_GEM_EXECBUFFER3, struct
drm_i915_gem_execbuffer3)
+#define DRM_IOCTL_I915_GEM_WAIT_USER_FENCE
DRM_IOWR(DRM_COMMAND_BASE +
DRM_I915_GEM_WAIT_USER_FENCE, struct
drm_i915_gem_wait_user_fence)
+
+/**
+ * struct drm_i915_gem_vm_bind - VA to object mapping to 
bind.

+ *
+ * This structure is passed to VM_BIND
ioctl and specifies the mapping of GPU
+ * virtual address (VA) range to the
section of an object that should be bound
+ * in the device page table of the specified address 
space (VM).

+ * The VA range specified must be unique
(ie., not currently bound) and can
+ * be mapped to whole object or a section
of the object (partial binding).
+ * Multiple VA mappings can be created to
the same section of the object
+ * (aliasing).
+ *
+ * The @queue_idx specifies the queue to
use for binding. Same queue can be
+ * used for both VM_BIND and VM_UNBIND
calls. All submitted bind and unbind
+ * operations in a queue are performed in the order of 
submission.

+ *
+ * The @start, @offset and @length should
be 4K page aligned. However the DG2
+ * and XEHPSDV has 64K page size for device
local-memory and has compact page
+ * table. On those platforms, for binding
device local-memory objects, the
+ * @start should be 2M aligned, @offset and
@length should be 64K aligned.
+ * Also, on those platforms, it is not
allowed to bind an device local-memory
+ * object and a system memory object in a
single 2M sect

Re: [PATCH 02/64] drm/crtc: Introduce drmm_crtc_init_with_planes

2022-06-15 Thread Thomas Zimmermann

Hi

Am 14.06.22 um 14:09 schrieb Maxime Ripard:

On Tue, Jun 14, 2022 at 01:47:28PM +0200, Thomas Zimmermann wrote:

Am 14.06.22 um 11:04 schrieb Maxime Ripard:

On Tue, Jun 14, 2022 at 10:29:20AM +0200, Thomas Zimmermann wrote:

Am 14.06.22 um 09:37 schrieb Maxime Ripard:

Hi Thomas,

On Mon, Jun 13, 2022 at 01:23:54PM +0200, Thomas Zimmermann wrote:

Am 10.06.22 um 11:28 schrieb Maxime Ripard:

The DRM-managed function to register a CRTC is
drmm_crtc_alloc_with_planes(), which will allocate the underlying
structure and initialisation the CRTC.

However, we might want to separate the structure creation and the CRTC
initialisation, for example if the structure is shared across multiple
DRM entities, for example an encoder and a connector.

Let's create an helper to only initialise a CRTC that would be passed as
an argument.


Before I review all of thes patches, one question. it's yet not clear to me
why drm_crtc_init_with_planes() wouldn't work. (I know we discussed this on
IRC.)

If you're calling drmm_mode_config_init(), it will clean up all the CRTC,
encoder connector, etc. data structures for you. For CRTC instances in
kmalloced memory, wouldn't it be simpler to put the corresponding kfree into
vc4_crtc_destroy()?


My intent was to remove as much of the lifetime handling and
memory-management from drivers as possible.

My feeling is that while the solution you suggest would definitely work,
it relies on drivers authors to know about this, and make the effort to
convert the drivers themselves. And then we would have to review that,
which we will probably miss (collectively), because it's a bit obscure.

While with either the drmm_alloc_* functions, or the new functions I
introduce there, we can just deprecate the old ones, create a TODO entry
and a coccinelle script and trust that it works properly.


Thanks for explaining the motivation.

I would not want to deprecate any of the existing functions, as they work
for many drivers. The drmm_ functions add additional overhead that not
everyone is willing to pay.


I'm a bit confused. drm_crtc_init_with_planes() at the moment has:

* Note: consider using drmm_crtc_alloc_with_planes() instead of
* drm_crtc_init_with_planes() to let the DRM managed resource infrastructure
* take care of cleanup and deallocation.

Just like drm_encoder_init(), drm_simple_encoder_init() and
drm_universal_plane_init(), so all the functions we have a drmm_* helper
for.

And we have a TODO-list item that heavily hints at using them:
https://dri.freedesktop.org/docs/drm/gpu/todo.html#object-lifetime-fixes

So it looks like we're already well on the deprecation path?


AFAIU that TODO item is about replacing devm_kzalloc() with drmm_kzalloc().
It's not about the plain init functions, such as drm_crtc_init_with_planes()
or drm_universal_plane_init(). Many simple drivers allocate their
modesetting pipeline's components first and then build the pipeline with the
drm_ functions. I don't think we can take that away from them.


Sure, that's exactly what those first patches are about? It allows to
use a DRM managed initialization without disrupting the drivers
structure too much?


The concern I have is that we're adding lots of helpers for all kind of
scenarios and end up with a lot of duplication (and fragmentation among
drivers).


I can see two: whether you want to allocate / init, or just init?
We're not going to have more than that.


For example, drmm_crtc_alloc_with_planes() really isn't much used
by anything. [1]


Not that I disagree here, but it might be that it isn't the most helpful
helper?

In vc4 case, we just can't use it easily.

Our CRTC driver is shared between the "regular" CRTCs in the display
path, and another instance dedicated to the writeback connector.

The shared stuff is initialized through vc4_crtc_init():
https://elixir.bootlin.com/linux/latest/source/drivers/gpu/drm/vc4/vc4_crtc.c#L1120

It initializes the structure, set up the planes, etc. Basically
everything that our CRTC controller will be doing, and would be shared
by both cases.

However, since the writeback and regular CRTC structures are different,
we can't really make that function allocate the backing structure
either.


It appears to me that it's a problem with how vc4 organizes its 
pipeline. That's why I suggested to move some of vc4's init code around 
to make such allocations more flexible.




We could do some compiler magic to pass the total size and the offset to
that function, just like what drmm_crtc_alloc_with_planes is doing, but
then we would have the same issue with the writeback stuff that needs to
initialize the encoder and connector.


In vc4_crtc.c it should be possible to use 
drmm_crtc_alloc_with_planes(). In vc4_txp.c, the code apparently 
initializes struct vc4_txp, so it would be better to use a managed 
cleanup of struct vc4_txp.



See, helpers should be useful to many drivers. If we add them, we also 
add a resources and maintenance overhead to our libraries. And right 

Re: [PATCH] drm/arm/hdlcd: Take over EFI framebuffer properly

2022-06-15 Thread Thomas Zimmermann

Hi

Am 14.06.22 um 23:06 schrieb Robin Murphy:

On 2022-06-14 14:48, Thomas Zimmermann wrote:

Hi

Am 14.06.22 um 15:04 schrieb Robin Murphy:

The Arm Juno board EDK2 port has provided an EFI GOP display via HDLCD0
for some time now, which works nicely as an early framebuffer. However,
once the HDLCD driver probes and takes over the hardware, it should
take over the logical framebuffer as well, otherwise the now-defunct GOP
device hangs about and virtual console output inevitably disappears into
the wrong place most of the time.

Signed-off-by: Robin Murphy 
---
  drivers/gpu/drm/arm/hdlcd_drv.c | 2 ++
  1 file changed, 2 insertions(+)

diff --git a/drivers/gpu/drm/arm/hdlcd_drv.c 
b/drivers/gpu/drm/arm/hdlcd_drv.c

index af59077a5481..a5d04884658b 100644
--- a/drivers/gpu/drm/arm/hdlcd_drv.c
+++ b/drivers/gpu/drm/arm/hdlcd_drv.c
@@ -331,6 +331,8 @@ static int hdlcd_drm_bind(struct device *dev)
  goto err_vblank;
  }
+    drm_fb_helper_remove_conflicting_framebuffers(NULL, "hdlcd", 
false);

+


In addition to what Javier said, it appears to be too late to call 
this function. If anything her etouches hardware, you might 
accidentally interfere with the EFI-related driver. Rather call it at 
the top of ldlcd_drm_bind().


OK, thanks for the info. I mostly just copied the pattern from the 
simplest-looking other users (sun4i, tegra, vc4) who all seemed to call 
it fairly late, and indeed naively it seemed logical not to do it *too* 
early when there's more chance we might fail to bind and leave the user 
with no framebuffer at all. In particular, waiting until we've bound the 
HDMI encoder seems like a good idea in the case of the Juno board (which 
is the only real HDLCD user), as the I2C bus often gets stuck if the 
System Control Processor is having a bad day. I also don't believe 
there's anything here that would affect efifb more than the fact that 
once the DRM CRTC is alive we simply stop scanning out from the region 
of memory that efifb is managing, but if it's considered good practice 
to do this early then I can certainly make that change too.
We've been struggling with this a bit. If it works reliably, you're 
welcome to leave it where it is.


Historically, most drivers call this function very early. But for error 
recovery it would be better to do it as late as possible.  Ideally, 
drivers would first initialize their DRM software state, then kickout 
the generic driver, and finally take over hardware. But that would 
require a careful review of each driver. :/


Best regards
Thomas



Cheers,
Robin.


--
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] drm/arm/hdlcd: Take over EFI framebuffer properly

2022-06-15 Thread Javier Martinez Canillas
On 6/15/22 09:39, Thomas Zimmermann wrote:
> Hi
> 
> Am 14.06.22 um 23:06 schrieb Robin Murphy:
>> On 2022-06-14 14:48, Thomas Zimmermann wrote:
>>> Hi
>>>
>>> Am 14.06.22 um 15:04 schrieb Robin Murphy:
 The Arm Juno board EDK2 port has provided an EFI GOP display via HDLCD0
 for some time now, which works nicely as an early framebuffer. However,
 once the HDLCD driver probes and takes over the hardware, it should
 take over the logical framebuffer as well, otherwise the now-defunct GOP
 device hangs about and virtual console output inevitably disappears into
 the wrong place most of the time.

 Signed-off-by: Robin Murphy 
 ---
   drivers/gpu/drm/arm/hdlcd_drv.c | 2 ++
   1 file changed, 2 insertions(+)

 diff --git a/drivers/gpu/drm/arm/hdlcd_drv.c 
 b/drivers/gpu/drm/arm/hdlcd_drv.c
 index af59077a5481..a5d04884658b 100644
 --- a/drivers/gpu/drm/arm/hdlcd_drv.c
 +++ b/drivers/gpu/drm/arm/hdlcd_drv.c
 @@ -331,6 +331,8 @@ static int hdlcd_drm_bind(struct device *dev)
   goto err_vblank;
   }
 +    drm_fb_helper_remove_conflicting_framebuffers(NULL, "hdlcd", 
 false);
 +
>>>
>>> In addition to what Javier said, it appears to be too late to call 
>>> this function. If anything her etouches hardware, you might 
>>> accidentally interfere with the EFI-related driver. Rather call it at 
>>> the top of ldlcd_drm_bind().
>>
>> OK, thanks for the info. I mostly just copied the pattern from the 
>> simplest-looking other users (sun4i, tegra, vc4) who all seemed to call 
>> it fairly late, and indeed naively it seemed logical not to do it *too* 
>> early when there's more chance we might fail to bind and leave the user 
>> with no framebuffer at all. In particular, waiting until we've bound the 
>> HDMI encoder seems like a good idea in the case of the Juno board (which 
>> is the only real HDLCD user), as the I2C bus often gets stuck if the 
>> System Control Processor is having a bad day. I also don't believe 
>> there's anything here that would affect efifb more than the fact that 
>> once the DRM CRTC is alive we simply stop scanning out from the region 
>> of memory that efifb is managing, but if it's considered good practice 
>> to do this early then I can certainly make that change too.
> We've been struggling with this a bit. If it works reliably, you're 
> welcome to leave it where it is.
> 
> Historically, most drivers call this function very early. But for error 
> recovery it would be better to do it as late as possible.  Ideally, 
> drivers would first initialize their DRM software state, then kickout 
> the generic driver, and finally take over hardware. But that would 
> require a careful review of each driver. :/
>

We got bug reports on Fedora about regressions caused by the fact that some
programs made the (wrong) assumption that /dev/dri/card0 would be the "main"
display and just hard-coded that path.

But removing the conflicting framebuffers after calling devm_drm_dev_alloc()
breaks this assumption, since the registered device will be /dev/dri/card1.

All this is to say that doing it too late, even if nothing is touching the HW
yet, could still have unexpected consequences across your graphics stack.

-- 
Best regards,

Javier Martinez Canillas
Linux Engineering
Red Hat



Re: [PATCH] drm/arm/hdlcd: Take over EFI framebuffer properly

2022-06-15 Thread Thomas Zimmermann



Am 15.06.22 um 09:50 schrieb Javier Martinez Canillas:
[...]

Historically, most drivers call this function very early. But for error
recovery it would be better to do it as late as possible.  Ideally,
drivers would first initialize their DRM software state, then kickout
the generic driver, and finally take over hardware. But that would
require a careful review of each driver. :/



We got bug reports on Fedora about regressions caused by the fact that some
programs made the (wrong) assumption that /dev/dri/card0 would be the "main"
display and just hard-coded that path.


Shh! Don't tell anyone.



But removing the conflicting framebuffers after calling devm_drm_dev_alloc()
breaks this assumption, since the registered device will be /dev/dri/card1.

All this is to say that doing it too late, even if nothing is touching the HW
yet, could still have unexpected consequences across your graphics stack.



--
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] drm/arm/hdlcd: Take over EFI framebuffer properly

2022-06-15 Thread Javier Martinez Canillas
On 6/15/22 09:53, Thomas Zimmermann wrote:
> 
> 
> Am 15.06.22 um 09:50 schrieb Javier Martinez Canillas:
> [...]
>>> Historically, most drivers call this function very early. But for error
>>> recovery it would be better to do it as late as possible.  Ideally,
>>> drivers would first initialize their DRM software state, then kickout
>>> the generic driver, and finally take over hardware. But that would
>>> require a careful review of each driver. :/
>>>
>>
>> We got bug reports on Fedora about regressions caused by the fact that some
>> programs made the (wrong) assumption that /dev/dri/card0 would be the "main"
>> display and just hard-coded that path.
> 
> Shh! Don't tell anyone.
>

:)

What I tried to say is that deciding where to kick out the firmware-provided
framebuffer isn't trivial and would just land the patch as is. At some point
we should probably agree on the best place and audit all the drivers to make
sure that are doing it properly. 

-- 
Best regards,

Javier Martinez Canillas
Linux Engineering
Red Hat



Re: [PATCH 02/64] drm/crtc: Introduce drmm_crtc_init_with_planes

2022-06-15 Thread Maxime Ripard
On Wed, Jun 15, 2022 at 09:22:55AM +0200, Thomas Zimmermann wrote:
> Hi
> 
> Am 14.06.22 um 14:09 schrieb Maxime Ripard:
> > On Tue, Jun 14, 2022 at 01:47:28PM +0200, Thomas Zimmermann wrote:
> > > Am 14.06.22 um 11:04 schrieb Maxime Ripard:
> > > > On Tue, Jun 14, 2022 at 10:29:20AM +0200, Thomas Zimmermann wrote:
> > > > > Am 14.06.22 um 09:37 schrieb Maxime Ripard:
> > > > > > Hi Thomas,
> > > > > > 
> > > > > > On Mon, Jun 13, 2022 at 01:23:54PM +0200, Thomas Zimmermann wrote:
> > > > > > > Am 10.06.22 um 11:28 schrieb Maxime Ripard:
> > > > > > > > The DRM-managed function to register a CRTC is
> > > > > > > > drmm_crtc_alloc_with_planes(), which will allocate the 
> > > > > > > > underlying
> > > > > > > > structure and initialisation the CRTC.
> > > > > > > > 
> > > > > > > > However, we might want to separate the structure creation and 
> > > > > > > > the CRTC
> > > > > > > > initialisation, for example if the structure is shared across 
> > > > > > > > multiple
> > > > > > > > DRM entities, for example an encoder and a connector.
> > > > > > > > 
> > > > > > > > Let's create an helper to only initialise a CRTC that would be 
> > > > > > > > passed as
> > > > > > > > an argument.
> > > > > > > 
> > > > > > > Before I review all of thes patches, one question. it's yet not 
> > > > > > > clear to me
> > > > > > > why drm_crtc_init_with_planes() wouldn't work. (I know we 
> > > > > > > discussed this on
> > > > > > > IRC.)
> > > > > > > 
> > > > > > > If you're calling drmm_mode_config_init(), it will clean up all 
> > > > > > > the CRTC,
> > > > > > > encoder connector, etc. data structures for you. For CRTC 
> > > > > > > instances in
> > > > > > > kmalloced memory, wouldn't it be simpler to put the corresponding 
> > > > > > > kfree into
> > > > > > > vc4_crtc_destroy()?
> > > > > > 
> > > > > > My intent was to remove as much of the lifetime handling and
> > > > > > memory-management from drivers as possible.
> > > > > > 
> > > > > > My feeling is that while the solution you suggest would definitely 
> > > > > > work,
> > > > > > it relies on drivers authors to know about this, and make the 
> > > > > > effort to
> > > > > > convert the drivers themselves. And then we would have to review 
> > > > > > that,
> > > > > > which we will probably miss (collectively), because it's a bit 
> > > > > > obscure.
> > > > > > 
> > > > > > While with either the drmm_alloc_* functions, or the new functions I
> > > > > > introduce there, we can just deprecate the old ones, create a TODO 
> > > > > > entry
> > > > > > and a coccinelle script and trust that it works properly.
> > > > > 
> > > > > Thanks for explaining the motivation.
> > > > > 
> > > > > I would not want to deprecate any of the existing functions, as they 
> > > > > work
> > > > > for many drivers. The drmm_ functions add additional overhead that not
> > > > > everyone is willing to pay.
> > > > 
> > > > I'm a bit confused. drm_crtc_init_with_planes() at the moment has:
> > > > 
> > > > * Note: consider using drmm_crtc_alloc_with_planes() instead of
> > > > * drm_crtc_init_with_planes() to let the DRM managed resource 
> > > > infrastructure
> > > > * take care of cleanup and deallocation.
> > > > 
> > > > Just like drm_encoder_init(), drm_simple_encoder_init() and
> > > > drm_universal_plane_init(), so all the functions we have a drmm_* helper
> > > > for.
> > > > 
> > > > And we have a TODO-list item that heavily hints at using them:
> > > > https://dri.freedesktop.org/docs/drm/gpu/todo.html#object-lifetime-fixes
> > > > 
> > > > So it looks like we're already well on the deprecation path?
> > > 
> > > AFAIU that TODO item is about replacing devm_kzalloc() with 
> > > drmm_kzalloc().
> > > It's not about the plain init functions, such as 
> > > drm_crtc_init_with_planes()
> > > or drm_universal_plane_init(). Many simple drivers allocate their
> > > modesetting pipeline's components first and then build the pipeline with 
> > > the
> > > drm_ functions. I don't think we can take that away from them.
> > 
> > Sure, that's exactly what those first patches are about? It allows to
> > use a DRM managed initialization without disrupting the drivers
> > structure too much?
> > 
> > > The concern I have is that we're adding lots of helpers for all kind of
> > > scenarios and end up with a lot of duplication (and fragmentation among
> > > drivers).
> > 
> > I can see two: whether you want to allocate / init, or just init?
> > We're not going to have more than that.
> > 
> > > For example, drmm_crtc_alloc_with_planes() really isn't much used
> > > by anything. [1]
> > 
> > Not that I disagree here, but it might be that it isn't the most helpful
> > helper?
> > 
> > In vc4 case, we just can't use it easily.
> > 
> > Our CRTC driver is shared between the "regular" CRTCs in the display
> > path, and another instance dedicated to the writeback connector.
> > 
> > The shared stuff is initialized through vc4_crtc_init():
> > https://elixir.bootlin.com/linux/la

Re: [PATCH v2 6/7] drm/bridge: anx7625: Register Type-C mode switches

2022-06-15 Thread AngeloGioacchino Del Regno

Il 14/06/22 18:57, Prashant Malani ha scritto:

On Tue, Jun 14, 2022 at 1:18 AM AngeloGioacchino Del Regno
 wrote:


Il 09/06/22 20:09, Prashant Malani ha scritto:

When the DT node has "switches" available, register a Type-C mode-switch
for each listed "switch". This allows the driver to receive state
information about what operating mode a Type-C port and its connected
peripherals are in, as well as status information (like VDOs) related to
that state.

The callback function is currently a stub, but subsequent patches will
implement the required functionality.

Signed-off-by: Prashant Malani 
---

Changes since v2:
- No changes.

   drivers/gpu/drm/bridge/analogix/anx7625.c | 73 +++
   drivers/gpu/drm/bridge/analogix/anx7625.h |  6 ++
   2 files changed, 79 insertions(+)

diff --git a/drivers/gpu/drm/bridge/analogix/anx7625.c 
b/drivers/gpu/drm/bridge/analogix/anx7625.c
index 07ed44c6b839..d41a21103bd3 100644
--- a/drivers/gpu/drm/bridge/analogix/anx7625.c
+++ b/drivers/gpu/drm/bridge/analogix/anx7625.c
@@ -15,6 +15,7 @@
   #include 
   #include 
   #include 
+#include 
   #include 

   #include 
@@ -2581,9 +2582,59 @@ static void anx7625_runtime_disable(void *data)
   pm_runtime_disable(data);
   }

+static int anx7625_typec_mux_set(struct typec_mux_dev *mux,
+  struct typec_mux_state *state)
+{
+ return 0;
+}
+
+static int anx7625_register_mode_switch(struct device *dev, struct device_node 
*node,
+ struct anx7625_data *ctx)
+{
+ struct anx7625_port_data *port_data;
+ struct typec_mux_desc mux_desc = {};
+ char name[32];
+ u32 port_num;
+ int ret;
+
+ ret = of_property_read_u32(node, "reg", &port_num);
+ if (ret)
+ return ret;
+
+ if (port_num >= ctx->num_typec_switches) {
+ dev_err(dev, "Invalid port number specified: %d\n", port_num);
+ return -EINVAL;
+ }
+
+ port_data = &ctx->typec_ports[port_num];
+ port_data->ctx = ctx;
+ mux_desc.fwnode = &node->fwnode;
+ mux_desc.drvdata = port_data;
+ snprintf(name, sizeof(name), "%s-%u", node->name, port_num);
+ mux_desc.name = name;
+ mux_desc.set = anx7625_typec_mux_set;
+
+ port_data->typec_mux = typec_mux_register(dev, &mux_desc);
+ if (IS_ERR(port_data->typec_mux)) {
+ ret = PTR_ERR(port_data->typec_mux);
+ dev_err(dev, "Mode switch register for port %d failed: %d", 
port_num, ret);
+ }


Please return 0 at the end of this function.

 if (IS_ERR()) {
 ..code..
 return ret;
 }

 return 0;
}


May I ask why? We're not missing any return paths. I would rather we
keep it as is (which has the valid return value).



I know that you're not missing any return paths.

That's only because the proposed one is a common pattern in the kernel
and it's only for consistency.

Regards,
Angelo



Re: [PATCH v2 1/3] drm/msm/dpu: Move LM CRC code into separate method

2022-06-15 Thread Dmitry Baryshkov
On Wed, 15 Jun 2022 at 00:13, Jessica Zhang  wrote:
>
> Move layer mixer-specific section of dpu_crtc_get_crc() into a separate
> helper method. This way, we can make it easier to get CRCs from other HW
> blocks by adding other get_crc helper methods.
>
> Changes since V1:
> - Moved common bitmasks to dpu_hw_util.h
> - Moved common CRC methods to dpu_hw_util.c
> - Updated copyrights
> - Changed crcs array to a dynamically allocated array and added it as a
>   member of crtc_state
>
> Signed-off-by: Jessica Zhang 

Please split this into separate patches. One for hw_util, one for the rest

> ---
>  drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c| 88 +
>  drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.h|  4 +
>  drivers/gpu/drm/msm/disp/dpu1/dpu_hw_lm.c   | 42 +-
>  drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.c | 46 ++-
>  drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.h | 16 
>  5 files changed, 124 insertions(+), 72 deletions(-)
>
> diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c 
> b/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
> index b56f777dbd0e..16742a66878e 100644
> --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
> +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
> @@ -1,5 +1,6 @@
>  // SPDX-License-Identifier: GPL-2.0-only
>  /*
> + * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
>   * Copyright (c) 2014-2021 The Linux Foundation. All rights reserved.
>   * Copyright (C) 2013 Red Hat
>   * Author: Rob Clark 
> @@ -88,6 +89,11 @@ static int dpu_crtc_verify_crc_source(struct drm_crtc 
> *crtc,
> enum dpu_crtc_crc_source source = dpu_crtc_parse_crc_source(src_name);
> struct dpu_crtc_state *crtc_state = to_dpu_crtc_state(crtc->state);
>
> +   if (crtc_state->crcs) {
> +   kfree(crtc_state->crcs);
> +   crtc_state->crcs = NULL;
> +   }
> +
> if (source < 0) {
> DRM_DEBUG_DRIVER("Invalid source %s for CRTC%d\n", src_name, 
> crtc->index);
> return -EINVAL;
> @@ -96,20 +102,37 @@ static int dpu_crtc_verify_crc_source(struct drm_crtc 
> *crtc,
> if (source == DPU_CRTC_CRC_SOURCE_LAYER_MIXER)
> *values_cnt = crtc_state->num_mixers;
>
> +   crtc_state->crcs = kcalloc(*values_cnt, sizeof(crtc_state->crcs), 
> GFP_KERNEL);
> +

I do not quite like the idea of constantly allocating and freeing the
crcs array. I'd suggest defining sensible MAX_CRC_VALUES, using a
static array and verifying that no one over commits the
MAX_CRC_VALUES.
If at some point we decide that we really need the dynamic array, we
can implement it later. We already had dynamic arrays and Rob had to
fix it. See 00326bfa4e63 ("drm/msm/dpu: Remove dynamic allocation from
atomic context").

> return 0;
>  }
>
> +static void dpu_crtc_setup_lm_misr(struct dpu_crtc_state *crtc_state)
> +{
> +   struct dpu_crtc_mixer *m;
> +   int i;
> +
> +   for (i = 0; i < crtc_state->num_mixers; ++i) {
> +   m = &crtc_state->mixers[i];
> +
> +   if (!m->hw_lm || !m->hw_lm->ops.setup_misr)
> +   continue;
> +
> +   /* Calculate MISR over 1 frame */
> +   m->hw_lm->ops.setup_misr(m->hw_lm, true, 1);
> +   }
> +}
> +
>  static int dpu_crtc_set_crc_source(struct drm_crtc *crtc, const char 
> *src_name)
>  {
> enum dpu_crtc_crc_source source = dpu_crtc_parse_crc_source(src_name);
> enum dpu_crtc_crc_source current_source;
> struct dpu_crtc_state *crtc_state;
> struct drm_device *drm_dev = crtc->dev;
> -   struct dpu_crtc_mixer *m;
>
> bool was_enabled;
> bool enable = false;
> -   int i, ret = 0;
> +   int ret = 0;
>
> if (source < 0) {
> DRM_DEBUG_DRIVER("Invalid CRC source %s for CRTC%d\n", 
> src_name, crtc->index);
> @@ -137,6 +160,10 @@ static int dpu_crtc_set_crc_source(struct drm_crtc 
> *crtc, const char *src_name)
> goto cleanup;
>
> } else if (was_enabled && !enable) {
> +   if (crtc_state->crcs) {
> +   kfree(crtc_state->crcs);
> +   crtc_state->crcs = NULL;
> +   }
> drm_crtc_vblank_put(crtc);
> }
>
> @@ -146,16 +173,8 @@ static int dpu_crtc_set_crc_source(struct drm_crtc 
> *crtc, const char *src_name)
>
> crtc_state->crc_frame_skip_count = 0;
>
> -   for (i = 0; i < crtc_state->num_mixers; ++i) {
> -   m = &crtc_state->mixers[i];
> -
> -   if (!m->hw_lm || !m->hw_lm->ops.setup_misr)
> -   continue;
> -
> -   /* Calculate MISR over 1 frame */
> -   m->hw_lm->ops.setup_misr(m->hw_lm, true, 1);
> -   }
> -
> +   if (source == DPU_CRTC_CRC_SOURCE_LAYER_MIXER)
> +   dpu_crtc_setup_lm_misr(crtc_state);

else ?

>
>  cleanup:
> drm_modeset_unlock(&crtc->mutex);
> @@ -174,34 +193,21 @@ static u32 dpu

Re: [PATCH v2 2/3] drm/msm/dpu: Add MISR register support for interface

2022-06-15 Thread Dmitry Baryshkov
On Wed, 15 Jun 2022 at 00:13, Jessica Zhang  wrote:
>
> Add support for setting MISR registers within the interface
>
> Changes since V1:
> - Replaced dpu_hw_intf collect_misr and setup_misr implementations with
>   calls to dpu_hw_utils helper methods
>
> Signed-off-by: Jessica Zhang 

Reviewed-by: Dmitry Baryshkov 

> ---
>  drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.c | 19 ++-
>  drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.h |  8 +++-
>  2 files changed, 25 insertions(+), 2 deletions(-)
>
> diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.c 
> b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.c
> index 3f4d2c6e1b45..0157613224fd 100644
> --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.c
> +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.c
> @@ -1,5 +1,7 @@
>  // SPDX-License-Identifier: GPL-2.0-only
> -/* Copyright (c) 2015-2018, The Linux Foundation. All rights reserved.
> +/*
> + * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
> + * Copyright (c) 2015-2018, The Linux Foundation. All rights reserved.
>   */
>
>  #include "dpu_hwio.h"
> @@ -67,6 +69,9 @@
>  #define INTF_CFG2_DATABUS_WIDENBIT(0)
>  #define INTF_CFG2_DATA_HCTL_EN BIT(4)
>
> +#define INTF_MISR_CTRL 0x180
> +#define INTF_MISR_SIGNATURE0x184
> +
>  static const struct dpu_intf_cfg *_intf_offset(enum dpu_intf intf,
> const struct dpu_mdss_cfg *m,
> void __iomem *addr,
> @@ -319,6 +324,16 @@ static u32 dpu_hw_intf_get_line_count(struct dpu_hw_intf 
> *intf)
> return DPU_REG_READ(c, INTF_LINE_COUNT);
>  }
>
> +static void dpu_hw_intf_setup_misr(struct dpu_hw_intf *intf, bool enable, 
> u32 frame_count)
> +{
> +   dpu_hw_setup_misr(&intf->hw, enable, frame_count, INTF_MISR_CTRL);
> +}
> +
> +static int dpu_hw_intf_collect_misr(struct dpu_hw_intf *intf, u32 
> *misr_value)
> +{
> +   return dpu_hw_collect_misr(&intf->hw, misr_value, INTF_MISR_CTRL, 
> INTF_MISR_SIGNATURE);
> +}
> +
>  static void _setup_intf_ops(struct dpu_hw_intf_ops *ops,
> unsigned long cap)
>  {
> @@ -329,6 +344,8 @@ static void _setup_intf_ops(struct dpu_hw_intf_ops *ops,
> ops->get_line_count = dpu_hw_intf_get_line_count;
> if (cap & BIT(DPU_INTF_INPUT_CTRL))
> ops->bind_pingpong_blk = dpu_hw_intf_bind_pingpong_blk;
> +   ops->setup_misr = dpu_hw_intf_setup_misr;
> +   ops->collect_misr = dpu_hw_intf_collect_misr;
>  }
>
>  struct dpu_hw_intf *dpu_hw_intf_init(enum dpu_intf idx,
> diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.h 
> b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.h
> index 7b2d96ac61e8..8d0e7b509260 100644
> --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.h
> +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.h
> @@ -1,5 +1,7 @@
>  /* SPDX-License-Identifier: GPL-2.0-only */
> -/* Copyright (c) 2015-2018, The Linux Foundation. All rights reserved.
> +/*
> + * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
> + * Copyright (c) 2015-2018, The Linux Foundation. All rights reserved.
>   */
>
>  #ifndef _DPU_HW_INTF_H
> @@ -57,6 +59,8 @@ struct intf_status {
>   * @ get_line_count: reads current vertical line counter
>   * @bind_pingpong_blk: enable/disable the connection with pingpong which will
>   * feed pixels to this interface
> + * @setup_misr: enable/disable MISR
> + * @collect_misr: read MISR signature
>   */
>  struct dpu_hw_intf_ops {
> void (*setup_timing_gen)(struct dpu_hw_intf *intf,
> @@ -77,6 +81,8 @@ struct dpu_hw_intf_ops {
> void (*bind_pingpong_blk)(struct dpu_hw_intf *intf,
> bool enable,
> const enum dpu_pingpong pp);
> +   void (*setup_misr)(struct dpu_hw_intf *intf, bool enable, u32 
> frame_count);
> +   int (*collect_misr)(struct dpu_hw_intf *intf, u32 *misr_value);
>  };
>
>  struct dpu_hw_intf {
> --
> 2.35.1
>


-- 
With best wishes
Dmitry


[Bug 216092] rn_vbios_smu_send_msg_with_param+0xf9/0x100 - amdgpu

2022-06-15 Thread bugzilla-daemon
https://bugzilla.kernel.org/show_bug.cgi?id=216092

RockT (tr...@gmx.de) changed:

   What|Removed |Added

 CC||tr...@gmx.de

--- Comment #1 from RockT (tr...@gmx.de) ---
I see exactly the same with Manjaro testing kernel 5.19.0-rc1.


[7.843798] amdgpu :06:00.0: amdgpu: RAS: optional ras ta ucode is not
available
[7.852927] amdgpu :06:00.0: amdgpu: RAP: optional rap ta ucode is not
available
[7.852928] amdgpu :06:00.0: amdgpu: SECUREDISPLAY: securedisplay ta
ucode is not available
[7.853513] amdgpu :06:00.0: amdgpu: SMU is initialized successfully!
[7.853691] [ cut here ]
[7.853692] WARNING: CPU: 0 PID: 432 at
drivers/gpu/drm/amd/amdgpu/../display/dc/clk_mgr/dcn21/rn_clk_mgr_vbios_smu.c:98
rn_vbios_smu_send_msg_with_param+0xf1/0x100 [amdgpu]
[7.853897] Modules linked in: amd64_edac(-) pcc_cpufreq(-) fjes(+)
snd_usb_audio(+) mhi_wwan_ctrl mhi_wwan_mbim snd_usbmidi_lib snd_rawmidi
snd_seq_device bnep squashfs loop btusb btrtl qrtr btbcm uvcvideo btintel btmtk
videobuf2_vmalloc videobuf2_memops intel_rapl_msr snd_acp3x_rn snd_soc_dmic
bluetooth videobuf2_v4l2 videobuf2_common videodev snd_acp3x_pdm_dma vfat
ecdh_generic hid_multitouch iwlmvm snd_sof_amd_renoir think_lmi(+) crc16 mc fat
snd_ctl_led snd_hda_codec_realtek firmware_attributes_class snd_sof_amd_acp
wmi_bmof intel_rapl_common amdgpu(+) snd_sof_pci mac80211 snd_hda_codec_generic
snd_hda_codec_hdmi snd_sof snd_hda_intel snd_intel_dspcfg snd_sof_utils
snd_intel_sdw_acpi snd_soc_core libarc4 edac_mce_amd snd_hda_codec snd_compress
iwlwifi ac97_bus gpu_sched kvm_amd snd_hda_core snd_pcm_dmaengine drm_buddy
snd_acp_pci drm_ttm_helper iwlmei snd_pci_acp6x thinkpad_acpi ttm snd_pci_acp5x
snd_hwdep ledtrig_audio r8169 cfg80211 kvm snd_pcm snd_rn_pci_acp3x ucsi_acpi
[7.853926]  platform_profile snd_timer snd_acp_config realtek
drm_display_helper snd typec_ucsi irqbypass rfkill mhi_pci_generic mdio_devres
sp5100_tco snd_soc_acpi tpm_crb snd_pci_acp3x cec soundcore rapl psmouse mei
libphy typec mhi i2c_piix4 k10temp roles i2c_hid_acpi tpm_tis i2c_hid video wmi
tpm_tis_core amd_pmc acpi_cpufreq pinctrl_amd joydev mousedev mac_hid uinput
ipmi_devintf ipmi_msghandler fuse crypto_user bpf_preload ip_tables x_tables
hid_logitech_hidpp xfs libcrc32c crc32c_generic hid_logitech_dj hid_jabra
usbhid dm_crypt cbc encrypted_keys trusted asn1_encoder tee tpm dm_mod
serio_raw atkbd libps2 crct10dif_pclmul crc32_pclmul vivaldi_fmap crc32c_intel
ghash_clmulni_intel aesni_intel nvme crypto_simd ccp xhci_pci cryptd i8042
nvme_core rng_core xhci_pci_renesas serio
[7.853954] CPU: 0 PID: 432 Comm: systemd-udevd Not tainted 5.19.0-1-MANJARO
#1 12b6001e0e27e2c5de0e86e6e0c9807155e77ed6
[7.853957] Hardware name: LENOVO 20XF006GGE/20XF006GGE, BIOS R1NET50W
(1.20) 04/14/2022
[7.853958] RIP: 0010:rn_vbios_smu_send_msg_with_param+0xf1/0x100 [amdgpu]
[7.854144] Code: f8 01 75 1b 48 8b 7d 00 5b be 93 62 01 00 48 c7 c2 a0 9f
6c c1 5d 41 5c 41 5d e9 3a ed f4 ff 3d fe 00 00 00 74 de 0f 0b eb da <0f> 0b e9
58 ff ff ff 0f 1f 84 00 00 00 00 00 66 0f 1f 00 0f 1f 44
[7.854146] RSP: 0018:9ae4030076f0 EFLAGS: 00010202
[7.854148] RAX: 00fe RBX: 00030d41 RCX:
c1938118
[7.854149] RDX:  RSI: 0001629b RDI:
8be18440
[7.854150] RBP: 8be186cdf800 R08: 8be1a1086800 R09:
0cb1
[7.854151] R10: 001e R11: 0036ee80 R12:
000d
[7.854152] R13: 0001 R14: 018f R15:
8be186cdf800
[7.854153] FS:  7f8967b45080() GS:8be84ee0()
knlGS:
[7.854154] CS:  0010 DS:  ES:  CR0: 80050033
[7.854154] CR2: 5636d87b17c8 CR3: 000105fde000 CR4:
00750ef0
[7.854155] PKRU: 5554
[7.854156] Call Trace:
[7.854158]  
[7.854160]  rn_clk_mgr_construct+0x151/0x620 [amdgpu
a6a2d017171775457fc880c1e7e3ceb4f3d662e5]
[7.854316]  dc_clk_mgr_create+0x42c/0x5d0 [amdgpu
a6a2d017171775457fc880c1e7e3ceb4f3d662e5]
[7.854464]  dc_create+0x23c/0x5b0 [amdgpu
a6a2d017171775457fc880c1e7e3ceb4f3d662e5]
[7.854620]  amdgpu_dm_init.isra.0+0x22d/0x350 [amdgpu
a6a2d017171775457fc880c1e7e3ceb4f3d662e5]
[7.854775]  ? dev_vprintk_emit+0x177/0x19c
[7.854781]  dm_hw_init+0x12/0x20 [amdgpu
a6a2d017171775457fc880c1e7e3ceb4f3d662e5]
[7.854927]  amdgpu_device_init.cold+0x17b4/0x1d57 [amdgpu
a6a2d017171775457fc880c1e7e3ceb4f3d662e5]
[7.855089]  amdgpu_driver_load_kms+0x19/0x130 [amdgpu
a6a2d017171775457fc880c1e7e3ceb4f3d662e5]
[7.855214]  amdgpu_pci_probe+0x148/0x360 [amdgpu
a6a2d017171775457fc880c1e7e3ceb4f3d662e5]
[7.855335]  local_pci_probe+0x42/0x80
[7.855339]  pci_device_probe+0xc1/0x220
[7.855341]  ? sysfs_do_create_link_sd+0x6a/0xd

Re: [PATCH v2 3/3] drm/msm/dpu: Add interface support for CRC debugfs

2022-06-15 Thread Dmitry Baryshkov
On Wed, 15 Jun 2022 at 00:13, Jessica Zhang  wrote:
>
> Add support for writing CRC values for the interface block to
> the debugfs by calling the necessary MISR setup/collect methods.
>
> Changes since V1:
> - Set values_cnt to only include phys with backing hw_intf
> - Loop over all drm_encs connected to crtc
>
> Signed-off-by: Jessica Zhang 
> ---
>  drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c| 49 ++--
>  drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.h|  3 +
>  drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c | 64 +
>  drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.h | 22 +++
>  4 files changed, 134 insertions(+), 4 deletions(-)
>
> diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c 
> b/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
> index 16742a66878e..8c9933b2337f 100644
> --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
> +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
> @@ -79,6 +79,8 @@ static enum dpu_crtc_crc_source 
> dpu_crtc_parse_crc_source(const char *src_name)
> if (!strcmp(src_name, "auto") ||
> !strcmp(src_name, "lm"))
> return DPU_CRTC_CRC_SOURCE_LAYER_MIXER;
> +   if (!strcmp(src_name, "intf"))
> +   return DPU_CRTC_CRC_SOURCE_INTF;

What about "encoder" / DPU_CRTC_CRC_SOURCE_ENCODER? You basically
offload CRC generation/collection to the dpu_encoder, so I'd ignore
the fact that only INTF's support MISR generation and use a more
generic word here.

>
> return DPU_CRTC_CRC_SOURCE_INVALID;
>  }
> @@ -99,8 +101,14 @@ static int dpu_crtc_verify_crc_source(struct drm_crtc 
> *crtc,
> return -EINVAL;
> }
>
> -   if (source == DPU_CRTC_CRC_SOURCE_LAYER_MIXER)
> +   if (source == DPU_CRTC_CRC_SOURCE_LAYER_MIXER) {
> *values_cnt = crtc_state->num_mixers;
> +   } else if (source == DPU_CRTC_CRC_SOURCE_INTF) {
> +   struct drm_encoder *drm_enc;

Zero values_cnt here.

> +
> +   drm_for_each_encoder_mask(drm_enc, crtc->dev, 
> crtc->state->encoder_mask)
> +   *values_cnt += dpu_encoder_get_num_phys(drm_enc);
> +   }
>
> crtc_state->crcs = kcalloc(*values_cnt, sizeof(crtc_state->crcs), 
> GFP_KERNEL);
>
> @@ -123,6 +131,14 @@ static void dpu_crtc_setup_lm_misr(struct dpu_crtc_state 
> *crtc_state)
> }
>  }
>
> +static void dpu_crtc_setup_encoder_misr(struct drm_crtc *crtc)
> +{
> +   struct drm_encoder *drm_enc;
> +
> +   drm_for_each_encoder_mask(drm_enc, crtc->dev, 
> crtc->state->encoder_mask)
> +   dpu_encoder_setup_misr(drm_enc);
> +}
> +
>  static int dpu_crtc_set_crc_source(struct drm_crtc *crtc, const char 
> *src_name)
>  {
> enum dpu_crtc_crc_source source = dpu_crtc_parse_crc_source(src_name);
> @@ -175,6 +191,8 @@ static int dpu_crtc_set_crc_source(struct drm_crtc *crtc, 
> const char *src_name)
>
> if (source == DPU_CRTC_CRC_SOURCE_LAYER_MIXER)
> dpu_crtc_setup_lm_misr(crtc_state);
> +   else if (source == DPU_CRTC_CRC_SOURCE_INTF)
> +   dpu_crtc_setup_encoder_misr(crtc);

else?

>
>  cleanup:
> drm_modeset_unlock(&crtc->mutex);
> @@ -220,11 +238,31 @@ static int dpu_crtc_get_lm_crc(struct drm_crtc *crtc, 
> struct dpu_crtc_state *crt
> drm_crtc_accurate_vblank_count(crtc), 
> crtc_state->crcs);
>  }
>
> -static int dpu_crtc_get_crc(struct drm_crtc *crtc)
> +static int dpu_crtc_get_encoder_crc(struct drm_crtc *crtc)
>  {
> -   struct dpu_crtc_state *crtc_state;
> +   struct drm_encoder *drm_enc;
> +   struct dpu_crtc_state *crtc_state = to_dpu_crtc_state(crtc->state);
> +   int rc, pos = 0;
>
> -   crtc_state = to_dpu_crtc_state(crtc->state);
> +   drm_for_each_encoder_mask(drm_enc, crtc->dev, 
> crtc->state->encoder_mask) {
> +   rc = dpu_encoder_get_crc(drm_enc, crtc_state->crcs, pos);
> +   if (rc < 0) {
> +   if (rc != -ENODATA)
> +   DRM_DEBUG_DRIVER("MISR read failed\n");
> +
> +   return rc;
> +   }
> +
> +   pos += rc;
> +   }
> +
> +   return drm_crtc_add_crc_entry(crtc, true,
> +   drm_crtc_accurate_vblank_count(crtc), 
> crtc_state->crcs);
> +}
> +
> +static int dpu_crtc_get_crc(struct drm_crtc *crtc)
> +{
> +   struct dpu_crtc_state *crtc_state = to_dpu_crtc_state(crtc->state);

Unnecessary change here. Please move it to the patch 1, which
refactors this function.

>
> /* Skip first 2 frames in case of "uncooked" CRCs */
> if (crtc_state->crc_frame_skip_count < 2) {
> @@ -235,6 +273,9 @@ static int dpu_crtc_get_crc(struct drm_crtc *crtc)
> if (crtc_state->crc_source == DPU_CRTC_CRC_SOURCE_LAYER_MIXER)
> return dpu_crtc_get_lm_crc(crtc, crtc_state);
>
> +   if (crtc_state->crc_source == DPU_CRTC_CRC_SOURCE_INTF)
> +   return dpu_crtc_get_encoder_crc(crtc);
> +
>

Re: [Intel-gfx] [RFC v3 3/3] drm/doc/rfc: VM_BIND uapi definition

2022-06-15 Thread Tvrtko Ursulin



On 08/06/2022 21:45, Niranjana Vishwanathapura wrote:

On Wed, Jun 08, 2022 at 09:54:24AM +0100, Tvrtko Ursulin wrote:


On 08/06/2022 09:45, Lionel Landwerlin wrote:

On 08/06/2022 11:36, Tvrtko Ursulin wrote:


On 08/06/2022 07:40, Lionel Landwerlin wrote:

On 03/06/2022 09:53, Niranjana Vishwanathapura wrote:
On Wed, Jun 01, 2022 at 10:08:35PM -0700, Niranjana 
Vishwanathapura wrote:

On Wed, Jun 01, 2022 at 11:27:17AM +0200, Daniel Vetter wrote:

On Wed, 1 Jun 2022 at 11:03, Dave Airlie  wrote:


On Tue, 24 May 2022 at 05:20, Niranjana Vishwanathapura
 wrote:


On Thu, May 19, 2022 at 04:07:30PM -0700, Zanoni, Paulo R wrote:
On Tue, 2022-05-17 at 11:32 -0700, Niranjana 

Vishwanathapura wrote:

VM_BIND and related uapi definitions

v2: Ensure proper kernel-doc formatting with cross references.
 Also add new uapi and documentation as per review comments
 from Daniel.

Signed-off-by: Niranjana Vishwanathapura 



---
  Documentation/gpu/rfc/i915_vm_bind.h | 399 

+++

  1 file changed, 399 insertions(+)
  create mode 100644 Documentation/gpu/rfc/i915_vm_bind.h

diff --git a/Documentation/gpu/rfc/i915_vm_bind.h 

b/Documentation/gpu/rfc/i915_vm_bind.h

new file mode 100644
index ..589c0a009107
--- /dev/null
+++ b/Documentation/gpu/rfc/i915_vm_bind.h
@@ -0,0 +1,399 @@
+/* SPDX-License-Identifier: MIT */
+/*
+ * Copyright © 2022 Intel Corporation
+ */
+
+/**
+ * DOC: I915_PARAM_HAS_VM_BIND
+ *
+ * VM_BIND feature availability.
+ * See typedef drm_i915_getparam_t param.
+ */
+#define I915_PARAM_HAS_VM_BIND 57
+
+/**
+ * DOC: I915_VM_CREATE_FLAGS_USE_VM_BIND
+ *
+ * Flag to opt-in for VM_BIND mode of binding 

during VM creation.

+ * See struct drm_i915_gem_vm_control flags.
+ *
+ * A VM in VM_BIND mode will not support the older 

execbuff mode of binding.
+ * In VM_BIND mode, execbuff ioctl will not accept 

any execlist (ie., the

+ * &drm_i915_gem_execbuffer2.buffer_count must be 0).
+ * Also, &drm_i915_gem_execbuffer2.batch_start_offset and
+ * &drm_i915_gem_execbuffer2.batch_len must be 0.
+ * DRM_I915_GEM_EXECBUFFER_EXT_BATCH_ADDRESSES 

extension must be provided

+ * to pass in the batch buffer addresses.
+ *
+ * Additionally, I915_EXEC_NO_RELOC, I915_EXEC_HANDLE_LUT and
+ * I915_EXEC_BATCH_FIRST of 

&drm_i915_gem_execbuffer2.flags must be 0
+ * (not used) in VM_BIND mode. 

I915_EXEC_USE_EXTENSIONS flag must always be
+ * set (See struct 

drm_i915_gem_execbuffer_ext_batch_addresses).
+ * The buffers_ptr, buffer_count, 

batch_start_offset and batch_len fields
+ * of struct drm_i915_gem_execbuffer2 are also not 

used and must be 0.

+ */


From that description, it seems we have:

struct drm_i915_gem_execbuffer2 {
    __u64 buffers_ptr;  -> must be 0 (new)
    __u32 buffer_count; -> must be 0 (new)
    __u32 batch_start_offset;   -> must be 0 (new)
    __u32 batch_len;    -> must be 0 (new)
    __u32 DR1;  -> must be 0 (old)
    __u32 DR4;  -> must be 0 (old)
    __u32 num_cliprects; (fences)   -> must be 0 

since using extensions
    __u64 cliprects_ptr; (fences, extensions) -> 

contains an actual pointer!
    __u64 flags;    -> some flags 

must be 0 (new)
    __u64 rsvd1; (context info) -> repurposed field 
(old)

    __u64 rsvd2;    -> unused
};

Based on that, why can't we just get 

drm_i915_gem_execbuffer3 instead
of adding even more complexity to an already abused 

interface? While
the Vulkan-like extension thing is really nice, I don't think 
what

we're doing here is extending the ioctl usage, we're completely
changing how the base struct should be interpreted 

based on how the VM

was created (which is an entirely different ioctl).

From Rusty Russel's API Design grading, 

drm_i915_gem_execbuffer2 is
already at -6 without these changes. I think after 

vm_bind we'll need

to create a -11 entry just to deal with this ioctl.



The only change here is removing the execlist support for VM_BIND
mode (other than natual extensions).
Adding a new execbuffer3 was considered, but I think we need 
to be careful
with that as that goes beyond the VM_BIND support, including 
any future

requirements (as we don't want an execbuffer4 after VM_BIND).


Why not? it's not like adding extensions here is really that 
different

than adding new ioctls.

I definitely think this deserves an execbuffer3 without even
considering future requirements. Just  to burn down the old
requirements and pointless fields.

Make execbuffer3 be vm bind only, no relocs, no legacy bits, 
leave the

older sw on execbuf2 for ever.


I guess another point in favour of execbuf3 would be that it's less
midlayer. If we share the entry point then there's quite a few 
vfuncs

needed to cleanly split out the vm_bind paths from the legacy
reloc/softping paths.

If we invert this and do execbuf3, then there's the existing ioctl

Re: [PATCH] drm/arm/hdlcd: Take over EFI framebuffer properly

2022-06-15 Thread Liviu Dudau
On Wed, Jun 15, 2022 at 10:00:52AM +0200, Javier Martinez Canillas wrote:
> On 6/15/22 09:53, Thomas Zimmermann wrote:
> > 
> > 
> > Am 15.06.22 um 09:50 schrieb Javier Martinez Canillas:
> > [...]
> >>> Historically, most drivers call this function very early. But for error
> >>> recovery it would be better to do it as late as possible.  Ideally,
> >>> drivers would first initialize their DRM software state, then kickout
> >>> the generic driver, and finally take over hardware. But that would
> >>> require a careful review of each driver. :/
> >>>
> >>
> >> We got bug reports on Fedora about regressions caused by the fact that some
> >> programs made the (wrong) assumption that /dev/dri/card0 would be the 
> >> "main"
> >> display and just hard-coded that path.
> > 
> > Shh! Don't tell anyone.
> >
> 
> :)
> 
> What I tried to say is that deciding where to kick out the firmware-provided
> framebuffer isn't trivial and would just land the patch as is. At some point
> we should probably agree on the best place and audit all the drivers to make
> sure that are doing it properly. 

I agree, we should review v2 with the updated API and land the patch if it is
reasonable. Due to my "cleverness" HDLCD and mali-dp are probably the only 
drivers
that also use the component framework that adds extra complications in terms of
silently not having all dependencies met (you forgot to compile the I2C driver 
or you
didn't load it as a module), so taking over the efifb framebuffer late is a good
idea.

Best regards,
Liviu

> 
> -- 
> Best regards,
> 
> Javier Martinez Canillas
> Linux Engineering
> Red Hat
> 

-- 

| I would like to |
| fix the world,  |
| but they're not |
| giving me the   |
 \ source code!  /
  ---
¯\_(ツ)_/¯


Re: [PATCH 2/2] arm64: dts: qcom: sm8250: Enable per-process page tables.

2022-06-15 Thread Dmitry Baryshkov
On Wed, 15 Jun 2022 at 02:01, Emma Anholt  wrote:
>
> This is an SMMU for the adreno gpu, and adding this compatible lets
> the driver use per-fd page tables, which are required for security
> between GPU clients.
>
> Signed-off-by: Emma Anholt 
> ---
>
> Tested with a full deqp-vk run on RB5, which did involve some iommu faults.
>
>  arch/arm64/boot/dts/qcom/sm8250.dtsi | 2 +-
>  1 file changed, 1 insertion(+), 1 deletion(-)
>
> diff --git a/arch/arm64/boot/dts/qcom/sm8250.dtsi 
> b/arch/arm64/boot/dts/qcom/sm8250.dtsi
> index a92230bec1dd..483c0e0f1d1a 100644
> --- a/arch/arm64/boot/dts/qcom/sm8250.dtsi
> +++ b/arch/arm64/boot/dts/qcom/sm8250.dtsi
> @@ -2513,7 +2513,7 @@ gpucc: clock-controller@3d9 {
> };
>
> adreno_smmu: iommu@3da {
> -   compatible = "qcom,sm8250-smmu-500", "arm,mmu-500";
> +   compatible = "qcom,sm8250-smmu-500", "arm,mmu-500", 
> "qcom,adreno-smmu";

I see that other dtsi files use a bit different order for the
compatibility strings. They put "qcom,adreno-smmu" before
"arm,mmu-500". Can we please follow them?

With that fixed:
Reviewed-by: Dmitry Baryshkov 

> reg = <0 0x03da 0 0x1>;
> #iommu-cells = <2>;
> #global-interrupts = <2>;
> --
> 2.36.1
>


-- 
With best wishes
Dmitry


Re: [PATCH 02/64] drm/crtc: Introduce drmm_crtc_init_with_planes

2022-06-15 Thread Thomas Zimmermann

Hi

Am 15.06.22 um 10:32 schrieb Maxime Ripard:
[...]

See, helpers should be useful to many drivers. If we add them, we also add a
resources and maintenance overhead to our libraries. And right now, these
new functions appear to work around the design of the vc4 driver's data
structures.  If you want to keep them, maybe let's first merge them into vc4
(something like vc4_crtc_init_with_planes(), etc). If another driver with a
use case comes along, we can still move them out easily.


Not that I disagree, but there's also the fact that people will start
using helpers because they are available.

You mentioned drmm_crtc_alloc_with_planes(). It was introduced in 5.12
with a single user (ipuv3-crtc.c). And then, because it was available,
in 5.17 was merged the Unisoc driver that was the second user of that
function.


OTOH, it actually took 5 releases to find another user. Maybe we need to 
look harder for possible reuse of helpers, but I wouldn't count 5 
releases as a good track record.




drmm_simple_encoder_alloc() and drmm_universal_plane_alloc() are in the
same situation and we wouldn't have had that discussion if it was kept
in the imx driver.

The helper being there allows driver authors to discover them easily,
pointing out an issue that possibly wasn't obvious to the author, and we
can also point during review that the helpers are there to be used.

None of that would be possible if we were to keep them in a driver,
because no one but the author would know about it.

My feeling is that the rule you mention works great when you know that
some deviation is going to happen. But we're replacing an init function
that has been proved good enough here, so it's not rocket science
really.

drmm_mutex_init() is a great example of that actually. You merged it
recently with two users. We could have used the exact same argument that
it belonged in those drivers because it wasn't generic enough or
something. But it's trivial, so it was a good decision to merge it as a
helper. And because you did so, I later found out that mutex_destroy()
was supposed to be called in the first place, I converted vc4 to
drmm_mutex_init(), and now that bug is fixed.


But when I added it, there actually were two users. I would not have 
added drmm_mutex_init() if it was only useful for a single driver.


In other cases, we tend to push single-user helpers into the drivers. 
That happened several times with TTM. Code was moved into vmwgfx, 
because there where no other users.


Anyway, as you insist on using this helper, go for it. But please, at 
least reimplement drm_crtc_alloc_with_planes() on top of a shared 
internal implementation. AFAICT drm_crtc_alloc_with_planes() is 
drmm_kzalloc + drmm_crtc_init_with_planes(). Same for other related 
helpers in the other patches, if there are any.


Best regards
Thomas



It wouldn't have been the case if you kept it inside the drivers.

Maxime


--
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 1/2] iommu: arm-smmu-impl: Add 8250 display compatible to the client list.

2022-06-15 Thread Dmitry Baryshkov
On Wed, 15 Jun 2022 at 02:01, Emma Anholt  wrote:
>
> Required for turning on per-process page tables for the GPU.
>
> Signed-off-by: Emma Anholt 

Reviewed-by: Dmitry Baryshkov 

> ---
>
>  drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c | 1 +
>  1 file changed, 1 insertion(+)
>
> diff --git a/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c 
> b/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c
> index d8e1ef83c01b..bb9220937068 100644
> --- a/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c
> +++ b/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c
> @@ -233,6 +233,7 @@ static const struct of_device_id 
> qcom_smmu_client_of_match[] __maybe_unused = {
> { .compatible = "qcom,sc7280-mdss" },
> { .compatible = "qcom,sc7280-mss-pil" },
> { .compatible = "qcom,sc8180x-mdss" },
> +   { .compatible = "qcom,sm8250-mdss" },
> { .compatible = "qcom,sdm845-mdss" },
> { .compatible = "qcom,sdm845-mss-pil" },
> { }
> --
> 2.36.1
>


-- 
With best wishes
Dmitry


Re: [PATCH] drivers: tty: serial: Add missing of_node_put() in serial-tegra.c

2022-06-15 Thread Greg KH
On Wed, Jun 15, 2022 at 06:48:33PM +0800, heliang wrote:
> In tegra_uart_init(), of_find_matching_node() will return a node
> pointer with refcount incremented. We should use of_node_put()
> when it is not used anymore.
> 
> Signed-off-by: heliang 

We need a real name please, one you sign documents with.

thanks,

greg k-h


Re: [PATCH v4 3/4] drm/panel: atna33xc20: Take advantage of wait_hpd_asserted() in struct drm_dp_aux

2022-06-15 Thread Dmitry Baryshkov
On Wed, 15 Jun 2022 at 00:54, Douglas Anderson  wrote:
>
> Let's add support for being able to read the HPD pin even if it's
> hooked directly to the controller. This will let us take away the
> waiting in the AUX transfer functions of the eDP controller drivers.
>
> Signed-off-by: Douglas Anderson 

Reviewed-by: Dmitry Baryshkov 

> ---
>
> Changes in v4:
> - Reorganized logic as per Dmitry's suggestion.
>
> Changes in v3:
> - Don't check "hpd_asserted" boolean when unset.
> - Handle errors from gpiod_get_value_cansleep() properly.
>
> Changes in v2:
> - Change is_hpd_asserted() to wait_hpd_asserted()
>
>  .../gpu/drm/panel/panel-samsung-atna33xc20.c  | 51 ++-
>  1 file changed, 38 insertions(+), 13 deletions(-)
>

-- 
With best wishes
Dmitry


Re: [PATCH v2 3/4] drm/msm/disp/dpu1: use atomic enable/disable callbacks for encoder functions

2022-06-15 Thread Dmitry Baryshkov

On 21/02/2022 17:51, Vinod Polimera wrote:

Use atomic variants for encoder callback functions such that
certain states like self-refresh can be accessed as part of
enable/disable sequence.

Signed-off-by: Kalyan Thota 
Signed-off-by: Vinod Polimera 

Changes in v2:
- As per review suggestion by Dmitry.
---
  drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c | 10 ++
  1 file changed, 6 insertions(+), 4 deletions(-)

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
index 1e648db..6eac417 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
@@ -1138,7 +1138,8 @@ void dpu_encoder_virt_runtime_resume(struct drm_encoder 
*drm_enc)
mutex_unlock(&dpu_enc->enc_lock);
  }
  
-static void dpu_encoder_virt_enable(struct drm_encoder *drm_enc)

+static void dpu_encoder_virt_enable(struct drm_encoder *drm_enc,
+   struct drm_atomic_state *state)
  {
struct dpu_encoder_virt *dpu_enc = NULL;
int ret = 0;
@@ -1176,7 +1177,8 @@ static void dpu_encoder_virt_enable(struct drm_encoder 
*drm_enc)
mutex_unlock(&dpu_enc->enc_lock);
  }
  
-static void dpu_encoder_virt_disable(struct drm_encoder *drm_enc)

+static void dpu_encoder_virt_disable(struct drm_encoder *drm_enc,
+   struct drm_atomic_state *state)
  {
struct dpu_encoder_virt *dpu_enc = NULL;
struct msm_drm_private *priv;
@@ -2094,8 +2096,8 @@ static void dpu_encoder_frame_done_timeout(struct 
timer_list *t)
  
  static const struct drm_encoder_helper_funcs dpu_encoder_helper_funcs = {

.mode_set = dpu_encoder_virt_mode_set,
-   .disable = dpu_encoder_virt_disable,
-   .enable = dpu_encoder_virt_enable,
+   .atomic_disable = dpu_encoder_virt_disable,
+   .atomic_enable = dpu_encoder_virt_enable,


A small nit before you post the next iteration of PSR:

Please rename these functions to follow atomic_enable/atomic_disable names.


.atomic_check = dpu_encoder_virt_atomic_check,
  };
  



--
With best wishes
Dmitry


[PATCH] drm/msm/dp: make dp_bridge_mode_valid() more precise

2022-06-15 Thread Dmitry Baryshkov
Make dp_connector_mode_valid() return precise MODE_CLOCK_HIGH rather
than generic MODE_BAD in case the mode clock is higher than
DP_MAX_PIXEL_CLK_KHZ (675 MHz).

Reviewed-by: Kuogee Hsieh
Reviewed-by: Stephen Boyd 
Signed-off-by: Dmitry Baryshkov 
---
 drivers/gpu/drm/msm/dp/dp_display.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/msm/dp/dp_display.c 
b/drivers/gpu/drm/msm/dp/dp_display.c
index bce77935394f..6ecdd81d0555 100644
--- a/drivers/gpu/drm/msm/dp/dp_display.c
+++ b/drivers/gpu/drm/msm/dp/dp_display.c
@@ -989,7 +989,7 @@ enum drm_mode_status dp_bridge_mode_valid(struct drm_bridge 
*bridge,
return MODE_OK;
 
if (mode->clock > DP_MAX_PIXEL_CLK_KHZ)
-   return MODE_BAD;
+   return MODE_CLOCK_HIGH;
 
dp_display = container_of(dp, struct dp_display_private, dp_display);
link_info = &dp_display->panel->link_info;
-- 
2.35.1



Re: [PATCH 1/3] drm/mipi-dsi: pass DSC data through the struct mipi_dsi_device

2022-06-15 Thread Dmitry Baryshkov

On 01/05/2022 18:12, Dmitry Baryshkov wrote:

The commit 0f40ba48de3b ("drm/msm/dsi: Pass DSC params to drm_panel")
added a pointer to the DSC data to the struct drm_panel. However DSC
support is not limited to the DSI panels. MIPI DSI bridges can also
consume DSC command streams. Thus add struct drm_dsc_config pointer to
the struct mipi_dsi_device.

Signed-off-by: Dmitry Baryshkov 


Gracious ping for the review from the drm core


---
  include/drm/drm_mipi_dsi.h | 2 ++
  1 file changed, 2 insertions(+)

diff --git a/include/drm/drm_mipi_dsi.h b/include/drm/drm_mipi_dsi.h
index 147e51b6d241..8b1c9be9b2a7 100644
--- a/include/drm/drm_mipi_dsi.h
+++ b/include/drm/drm_mipi_dsi.h
@@ -177,6 +177,7 @@ struct mipi_dsi_device_info {
   * @lp_rate: maximum lane frequency for low power mode in hertz, this should
   * be set to the real limits of the hardware, zero is only accepted for
   * legacy drivers
+ * @dsc: panel/bridge DSC pps payload to be sent
   */
  struct mipi_dsi_device {
struct mipi_dsi_host *host;
@@ -189,6 +190,7 @@ struct mipi_dsi_device {
unsigned long mode_flags;
unsigned long hs_rate;
unsigned long lp_rate;
+   struct drm_dsc_config *dsc;
  };
  
  #define MIPI_DSI_MODULE_PREFIX "mipi-dsi:"



--
With best wishes
Dmitry


Re: [v2] drm/msm: add null checks for drm device to avoid crash during probe defer

2022-06-15 Thread Dmitry Baryshkov

On 03/06/2022 12:42, Vinod Polimera wrote:

During probe defer, drm device is not initialized and an external
trigger to shutdown is trying to clean up drm device leading to crash.
Add checks to avoid drm device cleanup in such cases.

BUG: unable to handle kernel NULL pointer dereference at virtual
address 00b8

Call trace:

drm_atomic_helper_shutdown+0x44/0x144
msm_pdev_shutdown+0x2c/0x38
platform_shutdown+0x2c/0x38
device_shutdown+0x158/0x210
kernel_restart_prepare+0x40/0x4c
kernel_restart+0x20/0x6c
__arm64_sys_reboot+0x194/0x23c
invoke_syscall+0x50/0x13c
el0_svc_common+0xa0/0x17c
do_el0_svc_compat+0x28/0x34
el0_svc_compat+0x20/0x70
el0t_32_sync_handler+0xa8/0xcc
el0t_32_sync+0x1a8/0x1ac

Changes in v2:
- Add fixes tag.

Fixes: 623f279c778 ("drm/msm: fix shutdown hook in case GPU components failed to 
bind")
Signed-off-by: Vinod Polimera 


Reviewed-by: Dmitry Baryshkov 



---
  drivers/gpu/drm/msm/msm_drv.c | 6 +-
  1 file changed, 5 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/msm/msm_drv.c b/drivers/gpu/drm/msm/msm_drv.c
index 4448536..d62ac66 100644
--- a/drivers/gpu/drm/msm/msm_drv.c
+++ b/drivers/gpu/drm/msm/msm_drv.c
@@ -142,6 +142,9 @@ static void msm_irq_uninstall(struct drm_device *dev)
struct msm_drm_private *priv = dev->dev_private;
struct msm_kms *kms = priv->kms;
  
+	if (!irq_has_action(kms->irq))

+   return;
+
kms->funcs->irq_uninstall(kms);
if (kms->irq_requested)
free_irq(kms->irq, dev);
@@ -259,6 +262,7 @@ static int msm_drm_uninit(struct device *dev)
  
  	ddev->dev_private = NULL;

drm_dev_put(ddev);
+   priv->dev = NULL;
  
  	destroy_workqueue(priv->wq);
  
@@ -1167,7 +1171,7 @@ void msm_drv_shutdown(struct platform_device *pdev)

struct msm_drm_private *priv = platform_get_drvdata(pdev);
struct drm_device *drm = priv ? priv->dev : NULL;
  
-	if (!priv || !priv->kms)

+   if (!priv || !priv->kms || !drm)
return;
  
  	drm_atomic_helper_shutdown(drm);



--
With best wishes
Dmitry


Re: [v2] drm/msm: add null checks for drm device to avoid crash during probe defer

2022-06-15 Thread Dmitry Baryshkov

On 03/06/2022 12:42, Vinod Polimera wrote:

During probe defer, drm device is not initialized and an external
trigger to shutdown is trying to clean up drm device leading to crash.
Add checks to avoid drm device cleanup in such cases.

BUG: unable to handle kernel NULL pointer dereference at virtual
address 00b8

Call trace:

drm_atomic_helper_shutdown+0x44/0x144
msm_pdev_shutdown+0x2c/0x38
platform_shutdown+0x2c/0x38
device_shutdown+0x158/0x210
kernel_restart_prepare+0x40/0x4c
kernel_restart+0x20/0x6c
__arm64_sys_reboot+0x194/0x23c
invoke_syscall+0x50/0x13c
el0_svc_common+0xa0/0x17c
do_el0_svc_compat+0x28/0x34
el0_svc_compat+0x20/0x70
el0t_32_sync_handler+0xa8/0xcc
el0t_32_sync+0x1a8/0x1ac

Changes in v2:
- Add fixes tag.

Fixes: 623f279c778 ("drm/msm: fix shutdown hook in case GPU components failed to 
bind")
Signed-off-by: Vinod Polimera 
---
  drivers/gpu/drm/msm/msm_drv.c | 6 +-
  1 file changed, 5 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/msm/msm_drv.c b/drivers/gpu/drm/msm/msm_drv.c
index 4448536..d62ac66 100644
--- a/drivers/gpu/drm/msm/msm_drv.c
+++ b/drivers/gpu/drm/msm/msm_drv.c
@@ -142,6 +142,9 @@ static void msm_irq_uninstall(struct drm_device *dev)
struct msm_drm_private *priv = dev->dev_private;
struct msm_kms *kms = priv->kms;
  
+	if (!irq_has_action(kms->irq))

+   return;


As a second thought I'd still prefer a variable here. irq_has_action 
would check that there is _any_ IRQ handler for this IRQ. While we do 
not have anybody sharing this IRQ, I'd prefer to be clear here, that we 
do not want to uninstall our IRQ handler rather than any IRQ handler.



+
kms->funcs->irq_uninstall(kms);
if (kms->irq_requested)
free_irq(kms->irq, dev);
@@ -259,6 +262,7 @@ static int msm_drm_uninit(struct device *dev)
  
  	ddev->dev_private = NULL;

drm_dev_put(ddev);
+   priv->dev = NULL;
  
  	destroy_workqueue(priv->wq);
  
@@ -1167,7 +1171,7 @@ void msm_drv_shutdown(struct platform_device *pdev)

struct msm_drm_private *priv = platform_get_drvdata(pdev);
struct drm_device *drm = priv ? priv->dev : NULL;
  
-	if (!priv || !priv->kms)

+   if (!priv || !priv->kms || !drm)
return;
  
  	drm_atomic_helper_shutdown(drm);



--
With best wishes
Dmitry


Re: [PATCH] dt-bindings: msm: update maintainers list with proper id

2022-06-15 Thread Dmitry Baryshkov

On 03/06/2022 23:09, Kuogee Hsieh wrote:

Use quic id instead of codeaurora id in maintainers list
for display devicetree bindings.

Signed-off-by: Kuogee Hsieh 


Reviewed-by: Dmitry Baryshkov 

We can pick it through the msm/ tree, if no one objects.


---
  Documentation/devicetree/bindings/display/msm/dp-controller.yaml | 2 +-
  1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Documentation/devicetree/bindings/display/msm/dp-controller.yaml 
b/Documentation/devicetree/bindings/display/msm/dp-controller.yaml
index cd05cfd..c950710 100644
--- a/Documentation/devicetree/bindings/display/msm/dp-controller.yaml
+++ b/Documentation/devicetree/bindings/display/msm/dp-controller.yaml
@@ -7,7 +7,7 @@ $schema: http://devicetree.org/meta-schemas/core.yaml#
  title: MSM Display Port Controller
  
  maintainers:

-  - Kuogee Hsieh 
+  - Kuogee Hsieh 
  
  description: |

Device tree bindings for DisplayPort host controller for MSM targets



--
With best wishes
Dmitry


Re: [PATCH] drm/msm/dsi: Use single function for reset

2022-06-15 Thread Dmitry Baryshkov

On 11/06/2022 01:02, Luca Weiss wrote:

From: Vladimir Lypak 

There is currently two function for performing reset: dsi_sw_reset and
dsi_sw_reset_restore. Only difference betwean those is that latter one
assumes that DSI controller is enabled. In contrary former one assumes
that controller is disabled and executed during power-on. However this
assumtion is not true mobile devices which have boot splash set up by
boot-loader.

This patch removes dsi_sw_reset_restore and makes dsi_sw_reset disable
DSI controller during reset sequence if it's enabled.

Signed-off-by: Vladimir Lypak 
Signed-off-by: Luca Weiss 


Reviewed-by: Dmitry Baryshkov 


---
  drivers/gpu/drm/msm/dsi/dsi_host.c | 48 +-
  1 file changed, 21 insertions(+), 27 deletions(-)

diff --git a/drivers/gpu/drm/msm/dsi/dsi_host.c 
b/drivers/gpu/drm/msm/dsi/dsi_host.c
index a95d5df52653..bab2634ebd11 100644
--- a/drivers/gpu/drm/msm/dsi/dsi_host.c
+++ b/drivers/gpu/drm/msm/dsi/dsi_host.c
@@ -1080,12 +1080,32 @@ static void dsi_timing_setup(struct msm_dsi_host 
*msm_host, bool is_bonded_dsi)
  
  static void dsi_sw_reset(struct msm_dsi_host *msm_host)

  {
+   u32 ctrl;
+
+   ctrl = dsi_read(msm_host, REG_DSI_CTRL);
+
+   if (ctrl & DSI_CTRL_ENABLE) {
+   dsi_write(msm_host, REG_DSI_CTRL, ctrl & ~DSI_CTRL_ENABLE);
+   /*
+* dsi controller need to be disabled before
+* clocks turned on
+*/
+   wmb();
+   }
+
dsi_write(msm_host, REG_DSI_CLK_CTRL, DSI_CLK_CTRL_ENABLE_CLKS);
wmb(); /* clocks need to be enabled before reset */
  
+	/* dsi controller can only be reset while clocks are running */

dsi_write(msm_host, REG_DSI_RESET, 1);
msleep(DSI_RESET_TOGGLE_DELAY_MS); /* make sure reset happen */
dsi_write(msm_host, REG_DSI_RESET, 0);
+   wmb(); /* controller out of reset */
+
+   if (ctrl & DSI_CTRL_ENABLE) {
+   dsi_write(msm_host, REG_DSI_CTRL, ctrl);
+   wmb();  /* make sure dsi controller enabled again */
+   }
  }
  
  static void dsi_op_mode_config(struct msm_dsi_host *msm_host,

@@ -1478,32 +1498,6 @@ static int dsi_cmds2buf_tx(struct msm_dsi_host *msm_host,
return len;
  }
  
-static void dsi_sw_reset_restore(struct msm_dsi_host *msm_host)

-{
-   u32 data0, data1;
-
-   data0 = dsi_read(msm_host, REG_DSI_CTRL);
-   data1 = data0;
-   data1 &= ~DSI_CTRL_ENABLE;
-   dsi_write(msm_host, REG_DSI_CTRL, data1);
-   /*
-* dsi controller need to be disabled before
-* clocks turned on
-*/
-   wmb();
-
-   dsi_write(msm_host, REG_DSI_CLK_CTRL, DSI_CLK_CTRL_ENABLE_CLKS);
-   wmb();  /* make sure clocks enabled */
-
-   /* dsi controller can only be reset while clocks are running */
-   dsi_write(msm_host, REG_DSI_RESET, 1);
-   msleep(DSI_RESET_TOGGLE_DELAY_MS); /* make sure reset happen */
-   dsi_write(msm_host, REG_DSI_RESET, 0);
-   wmb();  /* controller out of reset */
-   dsi_write(msm_host, REG_DSI_CTRL, data0);
-   wmb();  /* make sure dsi controller enabled again */
-}
-
  static void dsi_hpd_worker(struct work_struct *work)
  {
struct msm_dsi_host *msm_host =
@@ -1520,7 +1514,7 @@ static void dsi_err_worker(struct work_struct *work)
  
  	pr_err_ratelimited("%s: status=%x\n", __func__, status);

if (status & DSI_ERR_STATE_MDP_FIFO_UNDERFLOW)
-   dsi_sw_reset_restore(msm_host);
+   dsi_sw_reset(msm_host);
  
  	/* It is safe to clear here because error irq is disabled. */

msm_host->err_work_state = 0;



--
With best wishes
Dmitry


[PATCH] drm/radeon: Replace drm_detect_hdmi_monitor() with drm_display_info.is_hdmi

2022-06-15 Thread hongao
Replace drm_detect_hdmi_monitor() with drm_display_info.is_hdmi for more
efficiency

Tested on "Oland [Radeon HD 8570 / R7 240/340 OEM]" & "Caicos [R5 230]"

Signed-off-by: hongao 
---
 drivers/gpu/drm/radeon/atombios_encoders.c |  6 +++---
 drivers/gpu/drm/radeon/radeon_connectors.c | 12 ++--
 drivers/gpu/drm/radeon/radeon_display.c|  2 +-
 drivers/gpu/drm/radeon/radeon_encoders.c   |  4 ++--
 4 files changed, 12 insertions(+), 12 deletions(-)

diff --git a/drivers/gpu/drm/radeon/atombios_encoders.c 
b/drivers/gpu/drm/radeon/atombios_encoders.c
index 70bd84b7ef2b..393d471ba396 100644
--- a/drivers/gpu/drm/radeon/atombios_encoders.c
+++ b/drivers/gpu/drm/radeon/atombios_encoders.c
@@ -714,7 +714,7 @@ atombios_get_encoder_mode(struct drm_encoder *encoder)
if (radeon_connector->use_digital &&
(radeon_connector->audio == RADEON_AUDIO_ENABLE))
return ATOM_ENCODER_MODE_HDMI;
-   else if 
(drm_detect_hdmi_monitor(radeon_connector_edid(connector)) &&
+   else if (connector->display_info.is_hdmi &&
 (radeon_connector->audio == RADEON_AUDIO_AUTO))
return ATOM_ENCODER_MODE_HDMI;
else if (radeon_connector->use_digital)
@@ -733,7 +733,7 @@ atombios_get_encoder_mode(struct drm_encoder *encoder)
if (radeon_audio != 0) {
if (radeon_connector->audio == RADEON_AUDIO_ENABLE)
return ATOM_ENCODER_MODE_HDMI;
-   else if 
(drm_detect_hdmi_monitor(radeon_connector_edid(connector)) &&
+   else if (connector->display_info.is_hdmi &&
 (radeon_connector->audio == RADEON_AUDIO_AUTO))
return ATOM_ENCODER_MODE_HDMI;
else
@@ -757,7 +757,7 @@ atombios_get_encoder_mode(struct drm_encoder *encoder)
} else if (radeon_audio != 0) {
if (radeon_connector->audio == RADEON_AUDIO_ENABLE)
return ATOM_ENCODER_MODE_HDMI;
-   else if 
(drm_detect_hdmi_monitor(radeon_connector_edid(connector)) &&
+   else if (connector->display_info.is_hdmi &&
 (radeon_connector->audio == RADEON_AUDIO_AUTO))
return ATOM_ENCODER_MODE_HDMI;
else
diff --git a/drivers/gpu/drm/radeon/radeon_connectors.c 
b/drivers/gpu/drm/radeon/radeon_connectors.c
index 58db79921cd3..2fbec7bdd56b 100644
--- a/drivers/gpu/drm/radeon/radeon_connectors.c
+++ b/drivers/gpu/drm/radeon/radeon_connectors.c
@@ -130,7 +130,7 @@ int radeon_get_monitor_bpc(struct drm_connector *connector)
case DRM_MODE_CONNECTOR_DVII:
case DRM_MODE_CONNECTOR_HDMIB:
if (radeon_connector->use_digital) {
-   if 
(drm_detect_hdmi_monitor(radeon_connector_edid(connector))) {
+   if (connector->display_info.is_hdmi) {
if (connector->display_info.bpc)
bpc = connector->display_info.bpc;
}
@@ -138,7 +138,7 @@ int radeon_get_monitor_bpc(struct drm_connector *connector)
break;
case DRM_MODE_CONNECTOR_DVID:
case DRM_MODE_CONNECTOR_HDMIA:
-   if (drm_detect_hdmi_monitor(radeon_connector_edid(connector))) {
+   if (connector->display_info.is_hdmi) {
if (connector->display_info.bpc)
bpc = connector->display_info.bpc;
}
@@ -147,7 +147,7 @@ int radeon_get_monitor_bpc(struct drm_connector *connector)
dig_connector = radeon_connector->con_priv;
if ((dig_connector->dp_sink_type == 
CONNECTOR_OBJECT_ID_DISPLAYPORT) ||
(dig_connector->dp_sink_type == CONNECTOR_OBJECT_ID_eDP) ||
-   drm_detect_hdmi_monitor(radeon_connector_edid(connector))) {
+   connector->display_info.is_hdmi) {
if (connector->display_info.bpc)
bpc = connector->display_info.bpc;
}
@@ -171,7 +171,7 @@ int radeon_get_monitor_bpc(struct drm_connector *connector)
break;
}
 
-   if (drm_detect_hdmi_monitor(radeon_connector_edid(connector))) {
+   if (connector->display_info.is_hdmi) {
/* hdmi deep color only implemented on DCE4+ */
if ((bpc > 8) && !ASIC_IS_DCE4(rdev)) {
DRM_DEBUG("%s: HDMI deep color %d bpc unsupported. 
Using 8 bpc.\n",
@@ -1500,7 +1500,7 @@ static enum drm_mode_status radeon_dvi_mode_valid(struct 
drm_connector *connecto
(radeon_connector->connector_object_id == 
CONNECTOR_OBJECT_ID_DUAL_LINK_D

Re: [PATCH 1/3] drm/msm/dpu: move intf and wb assignment to dpu_encoder_setup_display()

2022-06-15 Thread Dmitry Baryshkov

On 14/06/2022 22:32, Abhinav Kumar wrote:

intf and wb resources are not dependent on the rm global
state so need not be allocated during dpu_encoder_virt_atomic_mode_set().

Move the allocation of intf and wb resources to dpu_encoder_setup_display()
so that we can utilize the hw caps even during atomic_check() phase.

Since dpu_encoder_setup_display() already has protection against
setting invalid intf_idx and wb_idx, these checks can now
be dropped as well.

Fixes: e02a559a720f ("make changes to dpu_encoder to support virtual encoder")
Signed-off-by: Abhinav Kumar 
---
  drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c | 25 +++--
  1 file changed, 7 insertions(+), 18 deletions(-)

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
index 3a462e327e0e..e991d4ba8a40 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
@@ -1048,24 +1048,6 @@ static void dpu_encoder_virt_atomic_mode_set(struct 
drm_encoder *drm_enc,
phys->hw_pp = dpu_enc->hw_pp[i];
phys->hw_ctl = to_dpu_hw_ctl(hw_ctl[i]);
  
-		if (phys->intf_idx >= INTF_0 && phys->intf_idx < INTF_MAX)

-   phys->hw_intf = dpu_rm_get_intf(&dpu_kms->rm, 
phys->intf_idx);
-
-   if (phys->wb_idx >= WB_0 && phys->wb_idx < WB_MAX)
-   phys->hw_wb = dpu_rm_get_wb(&dpu_kms->rm, phys->wb_idx);
-
-   if (!phys->hw_intf && !phys->hw_wb) {
-   DPU_ERROR_ENC(dpu_enc,
- "no intf or wb block assigned at idx: 
%d\n", i);
-   return;
-   }
-
-   if (phys->hw_intf && phys->hw_wb) {
-   DPU_ERROR_ENC(dpu_enc,
-   "invalid phys both intf and wb block at idx: 
%d\n", i);
-   return;
-   }


Please retain these checks in dpu_encoder_setup_display().
It checks that we really have got the intf or wb. For example one might 
have specified the INTF that leads to INTF_NONE interface. Or 
non-existing/not supported WB.



-
phys->cached_mode = crtc_state->adjusted_mode;
if (phys->ops.atomic_mode_set)
phys->ops.atomic_mode_set(phys, crtc_state, conn_state);
@@ -2293,7 +2275,14 @@ static int dpu_encoder_setup_display(struct 
dpu_encoder_virt *dpu_enc,
struct dpu_encoder_phys *phys = dpu_enc->phys_encs[i];
atomic_set(&phys->vsync_cnt, 0);
atomic_set(&phys->underrun_cnt, 0);
+
+   if (phys->intf_idx >= INTF_0 && phys->intf_idx < INTF_MAX)
+   phys->hw_intf = dpu_rm_get_intf(&dpu_kms->rm, 
phys->intf_idx);
+
+   if (phys->wb_idx >= WB_0 && phys->wb_idx < WB_MAX)
+   phys->hw_wb = dpu_rm_get_wb(&dpu_kms->rm, phys->wb_idx);
}
+
mutex_unlock(&dpu_enc->enc_lock);
  
  	return ret;



--
With best wishes
Dmitry


Re: [PATCH 2/3] drm/msm/dpu: fix maxlinewidth for writeback block

2022-06-15 Thread Dmitry Baryshkov

On 14/06/2022 22:32, Abhinav Kumar wrote:

Writeback block for sm8250 was using the default maxlinewidth
of 2048. But this is not right as it supports upto 4096.

This should have no effect on most resolutions as we are
still limiting upto maxlinewidth of SSPP for adding the modes.

Fix the maxlinewidth for writeback block on sm8250.

Fixes: 53324b99bd7b ("add writeback blocks to the sm8250 DPU catalog")
Signed-off-by: Abhinav Kumar 


Reviewed-by: Dmitry Baryshkov 



---
  drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c | 6 +++---
  1 file changed, 3 insertions(+), 3 deletions(-)

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 400ebceb56bb..dd7537e32f88 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c
@@ -1285,7 +1285,7 @@ static const struct dpu_intf_cfg qcm2290_intf[] = {
   * Writeback blocks config
   */
  #define WB_BLK(_name, _id, _base, _features, _clk_ctrl, \
-   __xin_id, vbif_id, _reg, _wb_done_bit) \
+   __xin_id, vbif_id, _reg, _max_linewidth, _wb_done_bit) \
{ \
.name = _name, .id = _id, \
.base = _base, .len = 0x2c8, \
@@ -1295,13 +1295,13 @@ static const struct dpu_intf_cfg qcm2290_intf[] = {
.clk_ctrl = _clk_ctrl, \
.xin_id = __xin_id, \
.vbif_idx = vbif_id, \
-   .maxlinewidth = DEFAULT_DPU_LINE_WIDTH, \
+   .maxlinewidth = _max_linewidth, \
.intr_wb_done = DPU_IRQ_IDX(_reg, _wb_done_bit) \
}
  
  static const struct dpu_wb_cfg sm8250_wb[] = {

WB_BLK("wb_2", WB_2, 0x65000, WB_SM8250_MASK, DPU_CLK_CTRL_WB2, 6,
-   VBIF_RT, MDP_SSPP_TOP0_INTR, 4),
+   VBIF_RT, MDP_SSPP_TOP0_INTR, 4096, 4),
  };
  
  /*



--
With best wishes
Dmitry


Re: [PATCH 3/3] drm/msm/dpu: remove hard-coded linewidth limit for writeback

2022-06-15 Thread Dmitry Baryshkov

On 14/06/2022 22:32, Abhinav Kumar wrote:

Remove the hard-coded limit for writeback and lets start using
the one from catalog instead.

Fixes: d7d0e73f7de3 ("introduce the dpu_encoder_phys_* for writeback")
Signed-off-by: Abhinav Kumar 


Reviewed-by: Dmitry Baryshkov 



---
  drivers/gpu/drm/msm/disp/dpu1/dpu_encoder_phys_wb.c | 6 ++
  1 file changed, 2 insertions(+), 4 deletions(-)

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder_phys_wb.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder_phys_wb.c
index 59da348ff339..fc1d4fda69b5 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder_phys_wb.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder_phys_wb.c
@@ -20,8 +20,6 @@
  #include "dpu_crtc.h"
  #include "disp/msm_disp_snapshot.h"
  
-#define DEFAULT_MAX_WRITEBACK_WIDTH 2048

-
  #define to_dpu_encoder_phys_wb(x) \
container_of(x, struct dpu_encoder_phys_wb, base)
  
@@ -278,9 +276,9 @@ static int dpu_encoder_phys_wb_atomic_check(

DPU_ERROR("invalid fb h=%d, mode h=%d\n", fb->height,
  mode->vdisplay);
return -EINVAL;
-   } else if (fb->width > DEFAULT_MAX_WRITEBACK_WIDTH) {
+   } else if (fb->width > phys_enc->hw_wb->caps->maxlinewidth) {
DPU_ERROR("invalid fb w=%d, maxlinewidth=%u\n",
- fb->width, DEFAULT_MAX_WRITEBACK_WIDTH);
+ fb->width, 
phys_enc->hw_wb->caps->maxlinewidth);
return -EINVAL;
}
  



--
With best wishes
Dmitry


Re: [PATCH 1/3] drm/msm/dpu: move intf and wb assignment to dpu_encoder_setup_display()

2022-06-15 Thread Dmitry Baryshkov

On 14/06/2022 22:32, Abhinav Kumar wrote:

intf and wb resources are not dependent on the rm global
state so need not be allocated during dpu_encoder_virt_atomic_mode_set().

Move the allocation of intf and wb resources to dpu_encoder_setup_display()
so that we can utilize the hw caps even during atomic_check() phase.

Since dpu_encoder_setup_display() already has protection against
setting invalid intf_idx and wb_idx, these checks can now
be dropped as well.



I'm going to pick up the last two patches, so you'd have to resend just 
the first one.




Fixes: e02a559a720f ("make changes to dpu_encoder to support virtual encoder")
Signed-off-by: Abhinav Kumar 
---
  drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c | 25 +++--
  1 file changed, 7 insertions(+), 18 deletions(-)

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
index 3a462e327e0e..e991d4ba8a40 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
@@ -1048,24 +1048,6 @@ static void dpu_encoder_virt_atomic_mode_set(struct 
drm_encoder *drm_enc,
phys->hw_pp = dpu_enc->hw_pp[i];
phys->hw_ctl = to_dpu_hw_ctl(hw_ctl[i]);
  
-		if (phys->intf_idx >= INTF_0 && phys->intf_idx < INTF_MAX)

-   phys->hw_intf = dpu_rm_get_intf(&dpu_kms->rm, 
phys->intf_idx);
-
-   if (phys->wb_idx >= WB_0 && phys->wb_idx < WB_MAX)
-   phys->hw_wb = dpu_rm_get_wb(&dpu_kms->rm, phys->wb_idx);
-
-   if (!phys->hw_intf && !phys->hw_wb) {
-   DPU_ERROR_ENC(dpu_enc,
- "no intf or wb block assigned at idx: 
%d\n", i);
-   return;
-   }
-
-   if (phys->hw_intf && phys->hw_wb) {
-   DPU_ERROR_ENC(dpu_enc,
-   "invalid phys both intf and wb block at idx: 
%d\n", i);
-   return;
-   }
-
phys->cached_mode = crtc_state->adjusted_mode;
if (phys->ops.atomic_mode_set)
phys->ops.atomic_mode_set(phys, crtc_state, conn_state);
@@ -2293,7 +2275,14 @@ static int dpu_encoder_setup_display(struct 
dpu_encoder_virt *dpu_enc,
struct dpu_encoder_phys *phys = dpu_enc->phys_encs[i];
atomic_set(&phys->vsync_cnt, 0);
atomic_set(&phys->underrun_cnt, 0);
+
+   if (phys->intf_idx >= INTF_0 && phys->intf_idx < INTF_MAX)
+   phys->hw_intf = dpu_rm_get_intf(&dpu_kms->rm, 
phys->intf_idx);
+
+   if (phys->wb_idx >= WB_0 && phys->wb_idx < WB_MAX)
+   phys->hw_wb = dpu_rm_get_wb(&dpu_kms->rm, phys->wb_idx);
}
+
mutex_unlock(&dpu_enc->enc_lock);
  
  	return ret;



--
With best wishes
Dmitry


Re: [PATCH v3 2/2] drm/msm: Expose client engine utilization via fdinfo

2022-06-15 Thread Dmitry Baryshkov

On 09/06/2022 20:42, Rob Clark wrote:

From: Rob Clark 

Similar to AMD commit
874442541133 ("drm/amdgpu: Add show_fdinfo() interface"), using the
infrastructure added in previous patches, we add basic client info
and GPU engine utilisation for msm.

Example output:

# cat /proc/`pgrep glmark2`/fdinfo/6
pos:0
flags:  0242
mnt_id: 21
ino:162
drm-driver: msm
drm-client-id:  7
drm-engine-gpu: 1734371319 ns
drm-cycles-gpu: 1153645024
drm-maxfreq-gpu:8 Hz

See also: https://patchwork.freedesktop.org/patch/468505/

v2: Add dev-maxfreq-$engine and update drm-usage-stats.rst
v3: spelling and compiler warning

Signed-off-by: Rob Clark 


Reviewed-by: Dmitry Baryshkov 


---
  Documentation/gpu/drm-usage-stats.rst | 21 +
  drivers/gpu/drm/msm/msm_drv.c | 19 ++-
  drivers/gpu/drm/msm/msm_gpu.c | 21 +++--
  drivers/gpu/drm/msm/msm_gpu.h | 19 +++
  4 files changed, 77 insertions(+), 3 deletions(-)

diff --git a/Documentation/gpu/drm-usage-stats.rst 
b/Documentation/gpu/drm-usage-stats.rst
index 6c9f166a8d6f..92c5117368d7 100644
--- a/Documentation/gpu/drm-usage-stats.rst
+++ b/Documentation/gpu/drm-usage-stats.rst
@@ -105,6 +105,27 @@ object belong to this client, in the respective memory 
region.
  Default unit shall be bytes with optional unit specifiers of 'KiB' or 'MiB'
  indicating kibi- or mebi-bytes.
  
+- drm-cycles- 

+
+Engine identifier string must be the same as the one specified in the
+drm-engine- tag and shall contain the number of busy cycles for the given
+engine.
+
+Values are not required to be constantly monotonic if it makes the driver
+implementation easier, but are required to catch up with the previously 
reported
+larger value within a reasonable period. Upon observing a value lower than what
+was previously read, userspace is expected to stay with that larger previous
+value until a monotonic update is seen.
+
+- drm-maxfreq-  [Hz|MHz|KHz]
+
+Engine identifier string must be the same as the one specified in the
+drm-engine- tag and shall contain the maximum frequency for the given
+engine.  Taken together with drm-cycles-, this can be used to calculate
+percentage utilization of the engine, whereas drm-engine- only reflects
+time active without considering what frequency the engine is operating as a
+percentage of it's maximum frequency.
+
  ===
  Driver specific implementations
  ===
diff --git a/drivers/gpu/drm/msm/msm_drv.c b/drivers/gpu/drm/msm/msm_drv.c
index 14ab9a627d8b..57a66093e671 100644
--- a/drivers/gpu/drm/msm/msm_drv.c
+++ b/drivers/gpu/drm/msm/msm_drv.c
@@ -948,7 +948,24 @@ static const struct drm_ioctl_desc msm_ioctls[] = {
DRM_IOCTL_DEF_DRV(MSM_SUBMITQUEUE_QUERY, msm_ioctl_submitqueue_query, 
DRM_RENDER_ALLOW),
  };
  
-DEFINE_DRM_GEM_FOPS(fops);

+static void msm_fop_show_fdinfo(struct seq_file *m, struct file *f)
+{
+   struct drm_file *file = f->private_data;
+   struct drm_device *dev = file->minor->dev;
+   struct msm_drm_private *priv = dev->dev_private;
+   struct drm_printer p = drm_seq_file_printer(m);
+
+   if (!priv->gpu)
+   return;
+
+   msm_gpu_show_fdinfo(priv->gpu, file->driver_priv, &p);
+}
+
+static const struct file_operations fops = {
+   .owner = THIS_MODULE,
+   DRM_GEM_FOPS,
+   .show_fdinfo = msm_fop_show_fdinfo,
+};
  
  static const struct drm_driver msm_driver = {

.driver_features= DRIVER_GEM |
diff --git a/drivers/gpu/drm/msm/msm_gpu.c b/drivers/gpu/drm/msm/msm_gpu.c
index 244511f85044..f99292eaf529 100644
--- a/drivers/gpu/drm/msm/msm_gpu.c
+++ b/drivers/gpu/drm/msm/msm_gpu.c
@@ -4,6 +4,8 @@
   * Author: Rob Clark 
   */
  
+#include "drm/drm_drv.h"

+
  #include "msm_gpu.h"
  #include "msm_gem.h"
  #include "msm_mmu.h"
@@ -146,6 +148,16 @@ int msm_gpu_pm_suspend(struct msm_gpu *gpu)
return 0;
  }
  
+void msm_gpu_show_fdinfo(struct msm_gpu *gpu, struct msm_file_private *ctx,

+struct drm_printer *p)
+{
+   drm_printf(p, "drm-driver:\t%s\n", gpu->dev->driver->name);
+   drm_printf(p, "drm-client-id:\t%u\n", ctx->seqno);
+   drm_printf(p, "drm-engine-gpu:\t%llu ns\n", ctx->elapsed_ns);
+   drm_printf(p, "drm-cycles-gpu:\t%llu\n", ctx->cycles);
+   drm_printf(p, "drm-maxfreq-gpu:\t%u Hz\n", gpu->fast_rate);
+}
+
  int msm_gpu_hw_init(struct msm_gpu *gpu)
  {
int ret;
@@ -652,7 +664,7 @@ static void retire_submit(struct msm_gpu *gpu, struct 
msm_ringbuffer *ring,
  {
int index = submit->seqno % MSM_GPU_SUBMIT_STATS_COUNT;
volatile struct msm_gpu_submit_stats *stats;
-   u64 elapsed, clock = 0;
+   u64 elapsed, clock = 0, cycles;
unsigned long flags;
  
  	stats = &ring->memptrs->stats[index];

@@ -660,12 +672,17 @@ static void retire_sub

Re: [PATCH v3 1/2] drm: Add DRM_GEM_FOPS

2022-06-15 Thread Dmitry Baryshkov

On 09/06/2022 20:42, Rob Clark wrote:

From: Rob Clark 

The DEFINE_DRM_GEM_FOPS() helper is a bit limiting if a driver wants to
provide additional file ops, like show_fdinfo().

v2: Split out DRM_GEM_FOPS instead of making DEFINE_DRM_GEM_FOPS
 varardic
v3: nits

Signed-off-by: Rob Clark 
Acked-by: Thomas Zimmermann 


I suspect that with Tomas's ack we can pick this through the drm/msm. Is 
this correct? (I'll then pick it for the msm-lumag).



---
  include/drm/drm_gem.h | 26 ++
  1 file changed, 18 insertions(+), 8 deletions(-)

diff --git a/include/drm/drm_gem.h b/include/drm/drm_gem.h
index 9d7c61a122dc..87cffc9efa85 100644
--- a/include/drm/drm_gem.h
+++ b/include/drm/drm_gem.h
@@ -314,6 +314,23 @@ struct drm_gem_object {
const struct drm_gem_object_funcs *funcs;
  };
  
+/**

+ * DRM_GEM_FOPS - Default drm GEM file operations
+ *
+ * This macro provides a shorthand for setting the GEM file ops in the
+ * &file_operations structure.  If all you need are the default ops, use
+ * DEFINE_DRM_GEM_FOPS instead.
+ */
+#define DRM_GEM_FOPS \
+   .open   = drm_open,\
+   .release= drm_release,\
+   .unlocked_ioctl = drm_ioctl,\
+   .compat_ioctl   = drm_compat_ioctl,\
+   .poll   = drm_poll,\
+   .read   = drm_read,\
+   .llseek = noop_llseek,\
+   .mmap   = drm_gem_mmap
+
  /**
   * DEFINE_DRM_GEM_FOPS() - macro to generate file operations for GEM drivers
   * @name: name for the generated structure
@@ -330,14 +347,7 @@ struct drm_gem_object {
  #define DEFINE_DRM_GEM_FOPS(name) \
static const struct file_operations name = {\
.owner  = THIS_MODULE,\
-   .open   = drm_open,\
-   .release= drm_release,\
-   .unlocked_ioctl = drm_ioctl,\
-   .compat_ioctl   = drm_compat_ioctl,\
-   .poll   = drm_poll,\
-   .read   = drm_read,\
-   .llseek = noop_llseek,\
-   .mmap   = drm_gem_mmap,\
+   DRM_GEM_FOPS,\
}
  
  void drm_gem_object_release(struct drm_gem_object *obj);



--
With best wishes
Dmitry


Re: [PATCH] drm/msm: Use div64_ul instead of do_div

2022-06-15 Thread Dmitry Baryshkov

On 26/04/2022 16:21, Wan Jiabing wrote:

Fix following coccicheck warning:
drivers/gpu/drm/msm/msm_gpu_devfreq.c:72:1-7: WARNING: do_div() does a 64-by-32 
division, please consider using div64_ul instead.

Use div64_ul instead of do_div to avoid a possible truncation.

Signed-off-by: Wan Jiabing 


Reviewed-by: Dmitry Baryshkov 


---
  drivers/gpu/drm/msm/msm_gpu_devfreq.c | 2 +-
  1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/msm/msm_gpu_devfreq.c 
b/drivers/gpu/drm/msm/msm_gpu_devfreq.c
index d2539ca78c29..c2ea978c8921 100644
--- a/drivers/gpu/drm/msm/msm_gpu_devfreq.c
+++ b/drivers/gpu/drm/msm/msm_gpu_devfreq.c
@@ -69,7 +69,7 @@ static void get_raw_dev_status(struct msm_gpu *gpu,
df->time = time;
  
  	busy_time *= USEC_PER_SEC;

-   do_div(busy_time, sample_rate);
+   busy_time = div64_ul(busy_time, sample_rate);
if (WARN_ON(busy_time > ~0LU))
busy_time = ~0LU;
  



--
With best wishes
Dmitry


Re: [PATCH v3 2/2] drm/msm: Expose client engine utilization via fdinfo

2022-06-15 Thread Tvrtko Ursulin



On 09/06/2022 18:42, Rob Clark wrote:

From: Rob Clark 

Similar to AMD commit
874442541133 ("drm/amdgpu: Add show_fdinfo() interface"), using the
infrastructure added in previous patches, we add basic client info
and GPU engine utilisation for msm.

Example output:

# cat /proc/`pgrep glmark2`/fdinfo/6
pos:0
flags:  0242
mnt_id: 21
ino:162
drm-driver: msm
drm-client-id:  7
drm-engine-gpu: 1734371319 ns
drm-cycles-gpu: 1153645024
drm-maxfreq-gpu:8 Hz

See also: https://patchwork.freedesktop.org/patch/468505/

v2: Add dev-maxfreq-$engine and update drm-usage-stats.rst
v3: spelling and compiler warning

Signed-off-by: Rob Clark 
---
  Documentation/gpu/drm-usage-stats.rst | 21 +
  drivers/gpu/drm/msm/msm_drv.c | 19 ++-
  drivers/gpu/drm/msm/msm_gpu.c | 21 +++--
  drivers/gpu/drm/msm/msm_gpu.h | 19 +++
  4 files changed, 77 insertions(+), 3 deletions(-)

diff --git a/Documentation/gpu/drm-usage-stats.rst 
b/Documentation/gpu/drm-usage-stats.rst
index 6c9f166a8d6f..92c5117368d7 100644
--- a/Documentation/gpu/drm-usage-stats.rst
+++ b/Documentation/gpu/drm-usage-stats.rst
@@ -105,6 +105,27 @@ object belong to this client, in the respective memory 
region.
  Default unit shall be bytes with optional unit specifiers of 'KiB' or 'MiB'
  indicating kibi- or mebi-bytes.
  
+- drm-cycles- 

+
+Engine identifier string must be the same as the one specified in the
+drm-engine- tag and shall contain the number of busy cycles for the given
+engine.
+
+Values are not required to be constantly monotonic if it makes the driver
+implementation easier, but are required to catch up with the previously 
reported
+larger value within a reasonable period. Upon observing a value lower than what
+was previously read, userspace is expected to stay with that larger previous
+value until a monotonic update is seen.
+
+- drm-maxfreq-  [Hz|MHz|KHz]


Kilo should be lowercase, I *think*. Simplify and only document Hz?


+
+Engine identifier string must be the same as the one specified in the
+drm-engine- tag and shall contain the maximum frequency for the given
+engine.  Taken together with drm-cycles-, this can be used to calculate
+percentage utilization of the engine, whereas drm-engine- only reflects
+time active without considering what frequency the engine is operating as a
+percentage of it's maximum frequency.


Slipped my mind to reply to v3..

Acked-by: Tvrtko Ursulin 

Regards,

Tvrtko


+
  ===
  Driver specific implementations
  ===
diff --git a/drivers/gpu/drm/msm/msm_drv.c b/drivers/gpu/drm/msm/msm_drv.c
index 14ab9a627d8b..57a66093e671 100644
--- a/drivers/gpu/drm/msm/msm_drv.c
+++ b/drivers/gpu/drm/msm/msm_drv.c
@@ -948,7 +948,24 @@ static const struct drm_ioctl_desc msm_ioctls[] = {
DRM_IOCTL_DEF_DRV(MSM_SUBMITQUEUE_QUERY, msm_ioctl_submitqueue_query, 
DRM_RENDER_ALLOW),
  };
  
-DEFINE_DRM_GEM_FOPS(fops);

+static void msm_fop_show_fdinfo(struct seq_file *m, struct file *f)
+{
+   struct drm_file *file = f->private_data;
+   struct drm_device *dev = file->minor->dev;
+   struct msm_drm_private *priv = dev->dev_private;
+   struct drm_printer p = drm_seq_file_printer(m);
+
+   if (!priv->gpu)
+   return;
+
+   msm_gpu_show_fdinfo(priv->gpu, file->driver_priv, &p);
+}
+
+static const struct file_operations fops = {
+   .owner = THIS_MODULE,
+   DRM_GEM_FOPS,
+   .show_fdinfo = msm_fop_show_fdinfo,
+};
  
  static const struct drm_driver msm_driver = {

.driver_features= DRIVER_GEM |
diff --git a/drivers/gpu/drm/msm/msm_gpu.c b/drivers/gpu/drm/msm/msm_gpu.c
index 244511f85044..f99292eaf529 100644
--- a/drivers/gpu/drm/msm/msm_gpu.c
+++ b/drivers/gpu/drm/msm/msm_gpu.c
@@ -4,6 +4,8 @@
   * Author: Rob Clark 
   */
  
+#include "drm/drm_drv.h"

+
  #include "msm_gpu.h"
  #include "msm_gem.h"
  #include "msm_mmu.h"
@@ -146,6 +148,16 @@ int msm_gpu_pm_suspend(struct msm_gpu *gpu)
return 0;
  }
  
+void msm_gpu_show_fdinfo(struct msm_gpu *gpu, struct msm_file_private *ctx,

+struct drm_printer *p)
+{
+   drm_printf(p, "drm-driver:\t%s\n", gpu->dev->driver->name);
+   drm_printf(p, "drm-client-id:\t%u\n", ctx->seqno);
+   drm_printf(p, "drm-engine-gpu:\t%llu ns\n", ctx->elapsed_ns);
+   drm_printf(p, "drm-cycles-gpu:\t%llu\n", ctx->cycles);
+   drm_printf(p, "drm-maxfreq-gpu:\t%u Hz\n", gpu->fast_rate);
+}
+
  int msm_gpu_hw_init(struct msm_gpu *gpu)
  {
int ret;
@@ -652,7 +664,7 @@ static void retire_submit(struct msm_gpu *gpu, struct 
msm_ringbuffer *ring,
  {
int index = submit->seqno % MSM_GPU_SUBMIT_STATS_COUNT;
volatile struct msm_gpu_submit_stats *stats;
-   u64 elapsed, clock = 0;
+   u64 elapsed, clock = 0, cycle

Re: [Freedreno] [PATCH v5 00/10] drm/hdcp: Pull HDCP auth/exchange/check into helpers

2022-06-15 Thread Dmitry Baryshkov

On 11/04/2022 23:47, Sean Paul wrote:

From: Sean Paul 

Rebased set from November. Fixed a nit from Stephen in the msm patch and
moved hdcp registers into the trogdor dtsi file to avoid differences
with sc7180-based windows devices. The set is 4 patches lighter since
some of the changes were accepted into msm.

I'm still waiting for Intel review of the first 7 patches. Rodrigo/Jani,
would you please provide your input so we can move forward with this
set?

Thanks,

Sean

Link: https://patchwork.freedesktop.org/series/94623/ #v1
Link: https://patchwork.freedesktop.org/series/94713/ #v2
Link: https://patchwork.freedesktop.org/series/94712/ #v3
Link: https://patchwork.freedesktop.org/series/94712/ #v4


With most of the patches getting necessary acks and r-b, what would be 
the plan to merge the series?


We can take patches 1-4 (core) + 8, 10 (msm) through the msm tree, 
leaving i915 for the next cycle. Does that sound good?




Sean Paul (10):
   drm/hdcp: Add drm_hdcp_atomic_check()
   drm/hdcp: Avoid changing crtc state in hdcp atomic check
   drm/hdcp: Update property value on content type and user changes
   drm/hdcp: Expand HDCP helper library for enable/disable/check
   drm/i915/hdcp: Consolidate HDCP setup/state cache
   drm/i915/hdcp: Retain hdcp_capable return codes
   drm/i915/hdcp: Use HDCP helpers for i915
   dt-bindings: msm/dp: Add bindings for HDCP registers
   arm64: dts: qcom: sc7180: Add support for HDCP in dp-controller
   drm/msm: Implement HDCP 1.x using the new drm HDCP helpers

  .../bindings/display/msm/dp-controller.yaml   |7 +-
  arch/arm64/boot/dts/qcom/sc7180-trogdor.dtsi  |8 +
  arch/arm64/boot/dts/qcom/sc7180.dtsi  |6 +-
  drivers/gpu/drm/drm_hdcp.c| 1197 -
  drivers/gpu/drm/i915/display/intel_atomic.c   |7 +-
  drivers/gpu/drm/i915/display/intel_ddi.c  |   29 +-
  .../drm/i915/display/intel_display_debugfs.c  |   11 +-
  .../drm/i915/display/intel_display_types.h|   58 +-
  drivers/gpu/drm/i915/display/intel_dp_hdcp.c  |  345 ++---
  drivers/gpu/drm/i915/display/intel_dp_mst.c   |   17 +-
  drivers/gpu/drm/i915/display/intel_hdcp.c | 1011 +++---
  drivers/gpu/drm/i915/display/intel_hdcp.h |   36 +-
  drivers/gpu/drm/i915/display/intel_hdmi.c |  256 ++--
  drivers/gpu/drm/msm/Makefile  |1 +
  drivers/gpu/drm/msm/dp/dp_debug.c |   46 +-
  drivers/gpu/drm/msm/dp/dp_debug.h |6 +-
  drivers/gpu/drm/msm/dp/dp_display.c   |   46 +-
  drivers/gpu/drm/msm/dp/dp_display.h   |5 +
  drivers/gpu/drm/msm/dp/dp_drm.c   |   68 +-
  drivers/gpu/drm/msm/dp/dp_drm.h   |5 +
  drivers/gpu/drm/msm/dp/dp_hdcp.c  |  453 +++
  drivers/gpu/drm/msm/dp/dp_hdcp.h  |   27 +
  drivers/gpu/drm/msm/dp/dp_parser.c|   20 +-
  drivers/gpu/drm/msm/dp/dp_parser.h|4 +
  drivers/gpu/drm/msm/dp/dp_reg.h   |   32 +-
  drivers/gpu/drm/msm/msm_atomic.c  |   15 +
  include/drm/drm_hdcp.h|  194 +++
  27 files changed, 2582 insertions(+), 1328 deletions(-)
  create mode 100644 drivers/gpu/drm/msm/dp/dp_hdcp.c
  create mode 100644 drivers/gpu/drm/msm/dp/dp_hdcp.h




--
With best wishes
Dmitry


[PATCH v3 2/3] drm/msm/dpu: fix error handling around dpu_hw_vbif_init

2022-06-15 Thread Dmitry Baryshkov
Using IS_ERR_OR_NULL() together with PTR_ERR() is a typical mistake. If
the value is NULL, then the function will return 0 instead of a proper
return code. Moreover dpu_hw_vbif_init() function can not return NULL.
So, replace corresponding IS_ERR_OR_NULL() call with IS_ERR().

Reviewed-by: Abhinav Kumar 
Signed-off-by: Dmitry Baryshkov 
---
 drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c | 4 +---
 1 file changed, 1 insertion(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c
index 1255d00c92cf..922725c92898 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c
@@ -1135,10 +1135,8 @@ static int dpu_kms_hw_init(struct msm_kms *kms)
 
dpu_kms->hw_vbif[vbif_idx] = dpu_hw_vbif_init(vbif_idx,
dpu_kms->vbif[vbif_idx], dpu_kms->catalog);
-   if (IS_ERR_OR_NULL(dpu_kms->hw_vbif[vbif_idx])) {
+   if (IS_ERR(dpu_kms->hw_vbif[vbif_idx])) {
rc = PTR_ERR(dpu_kms->hw_vbif[vbif_idx]);
-   if (!dpu_kms->hw_vbif[vbif_idx])
-   rc = -EINVAL;
DPU_ERROR("failed to init vbif %d: %d\n", vbif_idx, rc);
dpu_kms->hw_vbif[vbif_idx] = NULL;
goto power_error;
-- 
2.35.1



[PATCH v3 3/3] drm/msm/dpu: drop VBIF indices

2022-06-15 Thread Dmitry Baryshkov
We do not expect to have other VBIFs. Drop VBIF_n indices and always use
VBIF_RT and VBIF_NRT.

Reviewed-by: Abhinav Kumar 
Signed-off-by: Dmitry Baryshkov 
---
 .../gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c|  4 +--
 drivers/gpu/drm/msm/disp/dpu1/dpu_hw_mdss.h   |  6 ++--
 drivers/gpu/drm/msm/disp/dpu1/dpu_vbif.c  | 36 ---
 3 files changed, 28 insertions(+), 18 deletions(-)

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 400ebceb56bb..f854889ea7fb 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c
@@ -1330,7 +1330,7 @@ static const struct dpu_vbif_dynamic_ot_cfg 
msm8998_ot_rdwr_cfg[] = {
 
 static const struct dpu_vbif_cfg msm8998_vbif[] = {
{
-   .name = "vbif_0", .id = VBIF_0,
+   .name = "vbif_rt", .id = VBIF_RT,
.base = 0, .len = 0x1040,
.default_ot_rd_limit = 32,
.default_ot_wr_limit = 32,
@@ -1359,7 +1359,7 @@ static const struct dpu_vbif_cfg msm8998_vbif[] = {
 
 static const struct dpu_vbif_cfg sdm845_vbif[] = {
{
-   .name = "vbif_0", .id = VBIF_0,
+   .name = "vbif_rt", .id = VBIF_RT,
.base = 0, .len = 0x1040,
.features = BIT(DPU_VBIF_QOS_REMAP),
.xin_halt_timeout = 0x4000,
diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_mdss.h 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_mdss.h
index 9f402be55fbf..d3b0ed0a9c6c 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_mdss.h
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_mdss.h
@@ -273,11 +273,9 @@ enum dpu_wd_timer {
 };
 
 enum dpu_vbif {
-   VBIF_0,
-   VBIF_1,
+   VBIF_RT,
+   VBIF_NRT,
VBIF_MAX,
-   VBIF_RT = VBIF_0,
-   VBIF_NRT = VBIF_1
 };
 
 /**
diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_vbif.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_vbif.c
index a18fb649301c..1305e250b71e 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_vbif.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_vbif.c
@@ -19,6 +19,18 @@ static struct dpu_hw_vbif *dpu_get_vbif(struct dpu_kms 
*dpu_kms, enum dpu_vbif v
return NULL;
 }
 
+static const char *dpu_vbif_name(enum dpu_vbif idx)
+{
+   switch (idx) {
+   case VBIF_RT:
+   return "VBIF_RT";
+   case VBIF_NRT:
+   return "VBIF_NRT";
+   default:
+   return "??";
+   }
+}
+
 /**
  * _dpu_vbif_wait_for_xin_halt - wait for the xin to halt
  * @vbif:  Pointer to hardware vbif driver
@@ -50,12 +62,12 @@ static int _dpu_vbif_wait_for_xin_halt(struct dpu_hw_vbif 
*vbif, u32 xin_id)
 
if (!status) {
rc = -ETIMEDOUT;
-   DPU_ERROR("VBIF %d client %d not halting. TIMEDOUT.\n",
-   vbif->idx - VBIF_0, xin_id);
+   DPU_ERROR("%s client %d not halting. TIMEDOUT.\n",
+   dpu_vbif_name(vbif->idx), xin_id);
} else {
rc = 0;
-   DRM_DEBUG_ATOMIC("VBIF %d client %d is halted\n",
-   vbif->idx - VBIF_0, xin_id);
+   DRM_DEBUG_ATOMIC("%s client %d is halted\n",
+   dpu_vbif_name(vbif->idx), xin_id);
}
 
return rc;
@@ -95,8 +107,8 @@ static void _dpu_vbif_apply_dynamic_ot_limit(struct 
dpu_hw_vbif *vbif,
}
}
 
-   DRM_DEBUG_ATOMIC("vbif:%d xin:%d w:%d h:%d fps:%d pps:%llu ot:%u\n",
-   vbif->idx - VBIF_0, params->xin_id,
+   DRM_DEBUG_ATOMIC("%s xin:%d w:%d h:%d fps:%d pps:%llu ot:%u\n",
+   dpu_vbif_name(vbif->idx), params->xin_id,
params->width, params->height, params->frame_rate,
pps, *ot_lim);
 }
@@ -141,8 +153,8 @@ static u32 _dpu_vbif_get_ot_limit(struct dpu_hw_vbif *vbif,
}
 
 exit:
-   DRM_DEBUG_ATOMIC("vbif:%d xin:%d ot_lim:%d\n",
-   vbif->idx - VBIF_0, params->xin_id, ot_lim);
+   DRM_DEBUG_ATOMIC("%s xin:%d ot_lim:%d\n",
+   dpu_vbif_name(vbif->idx), params->xin_id, ot_lim);
return ot_lim;
 }
 
@@ -242,8 +254,8 @@ void dpu_vbif_set_qos_remap(struct dpu_kms *dpu_kms,
forced_on = mdp->ops.setup_clk_force_ctrl(mdp, params->clk_ctrl, true);
 
for (i = 0; i < qos_tbl->npriority_lvl; i++) {
-   DRM_DEBUG_ATOMIC("vbif:%d xin:%d lvl:%d/%d\n",
-   params->vbif_idx, params->xin_id, i,
+   DRM_DEBUG_ATOMIC("%s xin:%d lvl:%d/%d\n",
+   dpu_vbif_name(params->vbif_idx), 
params->xin_id, i,
qos_tbl->priority_lvl[i]);
vbif->ops.set_qos_remap(vbif, params->xin_id, i,
qos_tbl->priority_lvl[i]);
@@ -263,8 +275,8 @@ void dpu_vbif_clear_errors(struct dpu_kms *dpu_kms)
if (vbif && vbif->ops.clear_errors) {
vbif->ops.clear_errors(vbif

[PATCH v3 1/3] drm/msm/dpu: index dpu_kms->hw_vbif using vbif_idx

2022-06-15 Thread Dmitry Baryshkov
Remove loops over hw_vbif. Instead always VBIF's idx as an index in the
array. This fixes an error in dpu_kms_hw_init(), where we fill
dpu_kms->hw_vbif[i], but check for an error pointer at
dpu_kms->hw_vbif[vbif_idx].

Fixes: 25fdd5933e4c ("drm/msm: Add SDM845 DPU support")
Signed-off-by: Dmitry Baryshkov 
---
 drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c  | 12 --
 drivers/gpu/drm/msm/disp/dpu1/dpu_vbif.c | 29 +++-
 2 files changed, 18 insertions(+), 23 deletions(-)

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c
index 2b9d931474e0..1255d00c92cf 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c
@@ -830,12 +830,10 @@ static void _dpu_kms_hw_destroy(struct dpu_kms *dpu_kms)
_dpu_kms_mmu_destroy(dpu_kms);
 
if (dpu_kms->catalog) {
-   for (i = 0; i < dpu_kms->catalog->vbif_count; i++) {
-   u32 vbif_idx = dpu_kms->catalog->vbif[i].id;
-
-   if ((vbif_idx < VBIF_MAX) && 
dpu_kms->hw_vbif[vbif_idx]) {
-   dpu_hw_vbif_destroy(dpu_kms->hw_vbif[vbif_idx]);
-   dpu_kms->hw_vbif[vbif_idx] = NULL;
+   for (i = 0; i < ARRAY_SIZE(dpu_kms->hw_vbif); i++) {
+   if (dpu_kms->hw_vbif[i]) {
+   dpu_hw_vbif_destroy(dpu_kms->hw_vbif[i]);
+   dpu_kms->hw_vbif[i] = NULL;
}
}
}
@@ -1135,7 +1133,7 @@ static int dpu_kms_hw_init(struct msm_kms *kms)
for (i = 0; i < dpu_kms->catalog->vbif_count; i++) {
u32 vbif_idx = dpu_kms->catalog->vbif[i].id;
 
-   dpu_kms->hw_vbif[i] = dpu_hw_vbif_init(vbif_idx,
+   dpu_kms->hw_vbif[vbif_idx] = dpu_hw_vbif_init(vbif_idx,
dpu_kms->vbif[vbif_idx], dpu_kms->catalog);
if (IS_ERR_OR_NULL(dpu_kms->hw_vbif[vbif_idx])) {
rc = PTR_ERR(dpu_kms->hw_vbif[vbif_idx]);
diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_vbif.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_vbif.c
index 21d20373eb8b..a18fb649301c 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_vbif.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_vbif.c
@@ -11,6 +11,14 @@
 #include "dpu_hw_vbif.h"
 #include "dpu_trace.h"
 
+static struct dpu_hw_vbif *dpu_get_vbif(struct dpu_kms *dpu_kms, enum dpu_vbif 
vbif_idx)
+{
+   if (vbif_idx < ARRAY_SIZE(dpu_kms->hw_vbif))
+   return dpu_kms->hw_vbif[vbif_idx];
+
+   return NULL;
+}
+
 /**
  * _dpu_vbif_wait_for_xin_halt - wait for the xin to halt
  * @vbif:  Pointer to hardware vbif driver
@@ -148,20 +156,15 @@ static u32 _dpu_vbif_get_ot_limit(struct dpu_hw_vbif 
*vbif,
 void dpu_vbif_set_ot_limit(struct dpu_kms *dpu_kms,
struct dpu_vbif_set_ot_params *params)
 {
-   struct dpu_hw_vbif *vbif = NULL;
+   struct dpu_hw_vbif *vbif;
struct dpu_hw_mdp *mdp;
bool forced_on = false;
u32 ot_lim;
-   int ret, i;
+   int ret;
 
mdp = dpu_kms->hw_mdp;
 
-   for (i = 0; i < ARRAY_SIZE(dpu_kms->hw_vbif); i++) {
-   if (dpu_kms->hw_vbif[i] &&
-   dpu_kms->hw_vbif[i]->idx == params->vbif_idx)
-   vbif = dpu_kms->hw_vbif[i];
-   }
-
+   vbif = dpu_get_vbif(dpu_kms, params->vbif_idx);
if (!vbif || !mdp) {
DRM_DEBUG_ATOMIC("invalid arguments vbif %d mdp %d\n",
vbif != NULL, mdp != NULL);
@@ -204,7 +207,7 @@ void dpu_vbif_set_ot_limit(struct dpu_kms *dpu_kms,
 void dpu_vbif_set_qos_remap(struct dpu_kms *dpu_kms,
struct dpu_vbif_set_qos_params *params)
 {
-   struct dpu_hw_vbif *vbif = NULL;
+   struct dpu_hw_vbif *vbif;
struct dpu_hw_mdp *mdp;
bool forced_on = false;
const struct dpu_vbif_qos_tbl *qos_tbl;
@@ -216,13 +219,7 @@ void dpu_vbif_set_qos_remap(struct dpu_kms *dpu_kms,
}
mdp = dpu_kms->hw_mdp;
 
-   for (i = 0; i < ARRAY_SIZE(dpu_kms->hw_vbif); i++) {
-   if (dpu_kms->hw_vbif[i] &&
-   dpu_kms->hw_vbif[i]->idx == params->vbif_idx) {
-   vbif = dpu_kms->hw_vbif[i];
-   break;
-   }
-   }
+   vbif = dpu_get_vbif(dpu_kms, params->vbif_idx);
 
if (!vbif || !vbif->cap) {
DPU_ERROR("invalid vbif %d\n", params->vbif_idx);
-- 
2.35.1



Re: [PATCH v7 0/8] Add a panel API to set orientation properly

2022-06-15 Thread Doug Anderson
Hi,

On Tue, Jun 14, 2022 at 10:50 PM Hsin-Yi Wang  wrote:
>
> On Thu, Jun 9, 2022 at 3:27 PM Hsin-Yi Wang  wrote:
> >
> > Panels usually call drm_connector_set_panel_orientation(), which is
> > later than drm/kms driver calling drm_dev_register(). This leads to a
> > WARN()[1].
> >
> > The orientation property is known earlier. For example, some panels
> > parse the property through device tree during probe.
> >
> > The series add a panel API drm_connector_set_orientation_from_panel()
> > for drm/kms drivers. The drivers can call the API to set panel's
> > orientation before drm_dev_register().
> >
> > Panel needs to implement .get_orientation callback to return the property.
> >
> > [1] 
> > https://patchwork.kernel.org/project/linux-mediatek/patch/20220530081910.3947168-2-hsi...@chromium.org/
> >
> > Hsin-Yi Wang (8):
> >   drm/panel: Add an API to allow drm to set orientation from panel
> >   drm/panel: boe-tv101wum-nl6: Implement .get_orientation callback
> >   drm/panel: panel-edp: Implement .get_orientation callback
> >   drm/panel: lvds: Implement .get_orientation callback
> >   drm/panel: panel-simple: Implement .get_orientation callback
> >   drm/panel: ili9881c: Implement .get_orientation callback
> >   drm/panel: elida-kd35t133: Implement .get_orientation callback
> >   drm: Config orientation property if panel provides it
> >
> hi Maintainers,
>
> All the patches are reviewed. If there's no other comments, will this
> series be picked? Thanks.

Unless someone beat me to it or yells, my plan was to land them to
drm-misc-next next week. Since it touches core code I wanted to give a
little extra time. Also at the moment patch #8 is all Chromium (all
author and reviewers are chromium.org) at the moment so that's another
reason to make sure it has sufficient time on the lists.

-Doug


[Bug 216092] rn_vbios_smu_send_msg_with_param+0xf9/0x100 - amdgpu

2022-06-15 Thread bugzilla-daemon
https://bugzilla.kernel.org/show_bug.cgi?id=216092

Alex Deucher (alexdeuc...@gmail.com) changed:

   What|Removed |Added

 CC||alexdeuc...@gmail.com

--- Comment #2 from Alex Deucher (alexdeuc...@gmail.com) ---
Can you bisect?

-- 
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 216092] rn_vbios_smu_send_msg_with_param+0xf9/0x100 - amdgpu

2022-06-15 Thread bugzilla-daemon
https://bugzilla.kernel.org/show_bug.cgi?id=216092

--- Comment #3 from Alex Deucher (alexdeuc...@gmail.com) ---
Does reverting c1b972a18d05d007f0ddff31db2ff50790576e92 fix the issue?

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

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

Re: [PATCH v3 1/2] drm: Add DRM_GEM_FOPS

2022-06-15 Thread Thomas Zimmermann



Am 15.06.22 um 14:45 schrieb Dmitry Baryshkov:

On 09/06/2022 20:42, Rob Clark wrote:

From: Rob Clark 

The DEFINE_DRM_GEM_FOPS() helper is a bit limiting if a driver wants to
provide additional file ops, like show_fdinfo().

v2: Split out DRM_GEM_FOPS instead of making DEFINE_DRM_GEM_FOPS
 varardic
v3: nits

Signed-off-by: Rob Clark 
Acked-by: Thomas Zimmermann 


I suspect that with Tomas's ack we can pick this through the drm/msm. Is 
this correct? (I'll then pick it for the msm-lumag).


Sure, go ahead.




---
  include/drm/drm_gem.h | 26 ++
  1 file changed, 18 insertions(+), 8 deletions(-)

diff --git a/include/drm/drm_gem.h b/include/drm/drm_gem.h
index 9d7c61a122dc..87cffc9efa85 100644
--- a/include/drm/drm_gem.h
+++ b/include/drm/drm_gem.h
@@ -314,6 +314,23 @@ struct drm_gem_object {
  const struct drm_gem_object_funcs *funcs;
  };
+/**
+ * DRM_GEM_FOPS - Default drm GEM file operations
+ *
+ * This macro provides a shorthand for setting the GEM file ops in the
+ * &file_operations structure.  If all you need are the default ops, use
+ * DEFINE_DRM_GEM_FOPS instead.
+ */
+#define DRM_GEM_FOPS \
+    .open    = drm_open,\
+    .release    = drm_release,\
+    .unlocked_ioctl    = drm_ioctl,\
+    .compat_ioctl    = drm_compat_ioctl,\
+    .poll    = drm_poll,\
+    .read    = drm_read,\
+    .llseek    = noop_llseek,\
+    .mmap    = drm_gem_mmap
+
  /**
   * DEFINE_DRM_GEM_FOPS() - macro to generate file operations for GEM 
drivers

   * @name: name for the generated structure
@@ -330,14 +347,7 @@ struct drm_gem_object {
  #define DEFINE_DRM_GEM_FOPS(name) \
  static const struct file_operations name = {\
  .owner    = THIS_MODULE,\
-    .open    = drm_open,\
-    .release    = drm_release,\
-    .unlocked_ioctl    = drm_ioctl,\
-    .compat_ioctl    = drm_compat_ioctl,\
-    .poll    = drm_poll,\
-    .read    = drm_read,\
-    .llseek    = noop_llseek,\
-    .mmap    = drm_gem_mmap,\
+    DRM_GEM_FOPS,\
  }
  void drm_gem_object_release(struct drm_gem_object *obj);





--
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


[Bug 216092] rn_vbios_smu_send_msg_with_param+0xf9/0x100 - amdgpu

2022-06-15 Thread bugzilla-daemon
https://bugzilla.kernel.org/show_bug.cgi?id=216092

--- Comment #4 from RockT (tr...@gmx.de) ---
(In reply to Alex Deucher from comment #3)
> Does reverting c1b972a18d05d007f0ddff31db2ff50790576e92 fix the issue?

I never rebuild an Arch/Manjaro Kernel.
Will try but cannot promise.

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

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

Re: [PATCH v2 7/7] drm/bridge: anx7625: Add typec_mux_set callback function

2022-06-15 Thread AngeloGioacchino Del Regno

Il 14/06/22 18:58, Prashant Malani ha scritto:

On Tue, Jun 14, 2022 at 2:08 AM Pin-yen Lin  wrote:


Hi AngeloGioacchino,


On Tue, Jun 14, 2022 at 4:15 PM AngeloGioacchino Del Regno
 wrote:


Il 09/06/22 20:09, Prashant Malani ha scritto:

From: Pin-Yen Lin 

Add the callback function when the driver receives state
changes of the Type-C port. The callback function configures the
crosspoint switch of the anx7625 bridge chip, which can change the
output pins of the signals according to the port state.

Signed-off-by: Pin-Yen Lin 
Signed-off-by: Prashant Malani 
---

Changes since v2:
- No changes.

   drivers/gpu/drm/bridge/analogix/anx7625.c | 58 +++
   drivers/gpu/drm/bridge/analogix/anx7625.h | 13 +
   2 files changed, 71 insertions(+)

diff --git a/drivers/gpu/drm/bridge/analogix/anx7625.c 
b/drivers/gpu/drm/bridge/analogix/anx7625.c
index d41a21103bd3..2c308d12fab2 100644
--- a/drivers/gpu/drm/bridge/analogix/anx7625.c
+++ b/drivers/gpu/drm/bridge/analogix/anx7625.c
@@ -15,6 +15,7 @@
   #include 
   #include 
   #include 
+#include 
   #include 
   #include 

@@ -2582,9 +2583,66 @@ static void anx7625_runtime_disable(void *data)
   pm_runtime_disable(data);
   }

+static void anx7625_set_crosspoint_switch(struct anx7625_data *ctx,
+   enum typec_orientation orientation)
+{
+ if (orientation == TYPEC_ORIENTATION_NORMAL) {
+ anx7625_reg_write(ctx, ctx->i2c.tcpc_client, TCPC_SWITCH_0,
+   SW_SEL1_SSRX_RX1 | SW_SEL1_DPTX0_RX2);
+ anx7625_reg_write(ctx, ctx->i2c.tcpc_client, TCPC_SWITCH_1,
+   SW_SEL2_SSTX_TX1 | SW_SEL2_DPTX1_TX2);
+ } else if (orientation == TYPEC_ORIENTATION_REVERSE) {
+ anx7625_reg_write(ctx, ctx->i2c.tcpc_client, TCPC_SWITCH_0,
+   SW_SEL1_SSRX_RX2 | SW_SEL1_DPTX0_RX1);
+ anx7625_reg_write(ctx, ctx->i2c.tcpc_client, TCPC_SWITCH_1,
+   SW_SEL2_SSTX_TX2 | SW_SEL2_DPTX1_TX1);
+ }
+}
+
+static void anx7625_typec_two_ports_update(struct anx7625_data *ctx)
+{
+ if (ctx->typec_ports[0].dp_connected && ctx->typec_ports[1].dp_connected)
+ /* Both ports available, do nothing to retain the current one. */
+ return;
+ else if (ctx->typec_ports[0].dp_connected)
+ anx7625_set_crosspoint_switch(ctx, TYPEC_ORIENTATION_NORMAL);
+ else if (ctx->typec_ports[1].dp_connected)
+ anx7625_set_crosspoint_switch(ctx, TYPEC_ORIENTATION_REVERSE);
+}
+
   static int anx7625_typec_mux_set(struct typec_mux_dev *mux,
struct typec_mux_state *state)
   {
+ struct anx7625_port_data *data = typec_mux_get_drvdata(mux);
+ struct anx7625_data *ctx = data->ctx;
+ struct device *dev = &ctx->client->dev;
+
+ bool old_dp_connected = (ctx->typec_ports[0].dp_connected ||
+  ctx->typec_ports[1].dp_connected);


So the old connection state is "either port0 or port1 are currently 
connected"...


+ bool new_dp_connected;
+
+ if (ctx->num_typec_switches == 1)
+ return 0;
+
+ dev_dbg(dev, "mux_set dp_connected: c0=%d, c1=%d\n",
+ ctx->typec_ports[0].dp_connected, 
ctx->typec_ports[1].dp_connected);
+
+ data->dp_connected = (state->alt && state->alt->svid == USB_TYPEC_DP_SID 
&&
+   state->alt->mode == USB_TYPEC_DP_MODE);
+ > + new_dp_connected = (ctx->typec_ports[0].dp_connected ||
+ ctx->typec_ports[1].dp_connected);


...and the new connection state is the same as the old one, because I don't see
anything that could ever modify it in this function's flow, until reaching this
assignment.


The typec mux driver data (`struct anx7625_port_data *data =
typec_mux_get_drvdata(mux)`) is set to one of the
`ctx->typec_ports[*]` in `anx7625_register_mode_switch` (see patch 6
of this series).

So, the `data->dp_connected = ...` assignment may change the new
connection state.


Angelo, I think your interpretation of this logic is not accurate..
|old_dp_connected| represents *whether* port1 or port0 has a DP
partner connected, not that *either* of them has it.

So, this logic looks OK to me.



Hello Prashant,

You're completely right: I've finally seen where this is happening, so yes
we don't know, nor care at that moment, whether data->dp_connected is port0
or port1, we assign and check 'em both again, which is actually smart.

I'm sorry for the misunderstandment - and thank you for your reply.

Feel free to add my

Reviewed-by: AngeloGioacchino Del Regno 


Regards,
Angelo


[PATCH 00/10] drm: selftest: Convert to KUnit

2022-06-15 Thread Maíra Canal
KUnit unifies the test structure and provides helper tools that simplify
the development of tests. The basic use case allows running tests as regular
processes, which makes it easier to run unit tests on a development machine
and to integrate the tests into a CI system.

That said, the conversion of selftests for DRM to KUnit tests is beneficial
as it unifies the testing API by using the KUnit API.

KUnit is beneficial for developers as it eases the process to run unit tests.
It is possible to run the tests by using the kunit-tool on userspace with the
following command:

./tools/testing/kunit/kunit.py run --kunitconfig=drivers/gpu/drm/tests 
--arch=x86_64

For CI system, it is possible to execute during the build. But, we also think
about IGT: we are developing a patch to introduce KUnit to IGT.

These patches were developed during a KUnit hackathon [0] last October. Now,
we believe that both the IGT side and the Kernel side are in good shape for
submission.

If you are willing to check the output, here is the Pastebin with the output
and execution times [1].

[0] https://groups.google.com/g/kunit-dev/c/YqFR1q2uZvk/m/IbvItSfHBAAJ
[1] https://pastebin.com/FJjLPKsC

- Arthur Grillo, Isabella Basso, and Maíra Canal

Arthur Grillo (2):
  drm: selftest: refactor drm_cmdline_parser
  drm: selftest: convert drm_mm selftest to KUnit

Maíra Canal (8):
  drm: selftest: convert drm_damage_helper selftest to KUnit
  drm: selftest: convert drm_cmdline_parser selftest to KUnit
  drm: selftest: convert drm_rect selftest to KUnit
  drm: selftest: convert drm_format selftest to KUnit
  drm: selftest: convert drm_plane_helper selftest to KUnit
  drm: selftest: convert drm_dp_mst_helper selftest to KUnit
  drm: selftest: convert drm_framebuffer selftest to KUnit
  drm: selftest: convert drm_buddy selftest to KUnit

 drivers/gpu/drm/Kconfig   |   20 +-
 drivers/gpu/drm/Makefile  |2 +-
 drivers/gpu/drm/selftests/Makefile|8 -
 .../gpu/drm/selftests/drm_buddy_selftests.h   |   15 -
 .../gpu/drm/selftests/drm_cmdline_selftests.h |   68 -
 drivers/gpu/drm/selftests/drm_mm_selftests.h  |   28 -
 .../gpu/drm/selftests/drm_modeset_selftests.h |   40 -
 drivers/gpu/drm/selftests/drm_selftest.c  |  109 --
 drivers/gpu/drm/selftests/drm_selftest.h  |   41 -
 drivers/gpu/drm/selftests/test-drm_buddy.c|  994 --
 .../drm/selftests/test-drm_cmdline_parser.c   | 1141 -
 .../drm/selftests/test-drm_damage_helper.c|  667 --
 drivers/gpu/drm/selftests/test-drm_format.c   |  280 
 .../drm/selftests/test-drm_modeset_common.c   |   32 -
 .../drm/selftests/test-drm_modeset_common.h   |   52 -
 drivers/gpu/drm/tests/.kunitconfig|3 +
 drivers/gpu/drm/tests/Kconfig |  130 ++
 drivers/gpu/drm/tests/Makefile|   10 +
 drivers/gpu/drm/tests/test-drm_buddy.c|  748 +++
 .../gpu/drm/tests/test-drm_cmdline_parser.c   |  799 
 .../gpu/drm/tests/test-drm_damage_helper.c|  633 +
 .../test-drm_dp_mst_helper.c  |   82 +-
 drivers/gpu/drm/tests/test-drm_format.c   |  284 
 .../test-drm_framebuffer.c|   25 +-
 .../drm/{selftests => tests}/test-drm_mm.c| 1135 +++-
 .../test-drm_plane_helper.c   |  101 +-
 .../drm/{selftests => tests}/test-drm_rect.c  |  124 +-
 27 files changed, 3240 insertions(+), 4331 deletions(-)
 delete mode 100644 drivers/gpu/drm/selftests/Makefile
 delete mode 100644 drivers/gpu/drm/selftests/drm_buddy_selftests.h
 delete mode 100644 drivers/gpu/drm/selftests/drm_cmdline_selftests.h
 delete mode 100644 drivers/gpu/drm/selftests/drm_mm_selftests.h
 delete mode 100644 drivers/gpu/drm/selftests/drm_modeset_selftests.h
 delete mode 100644 drivers/gpu/drm/selftests/drm_selftest.c
 delete mode 100644 drivers/gpu/drm/selftests/drm_selftest.h
 delete mode 100644 drivers/gpu/drm/selftests/test-drm_buddy.c
 delete mode 100644 drivers/gpu/drm/selftests/test-drm_cmdline_parser.c
 delete mode 100644 drivers/gpu/drm/selftests/test-drm_damage_helper.c
 delete mode 100644 drivers/gpu/drm/selftests/test-drm_format.c
 delete mode 100644 drivers/gpu/drm/selftests/test-drm_modeset_common.c
 delete mode 100644 drivers/gpu/drm/selftests/test-drm_modeset_common.h
 create mode 100644 drivers/gpu/drm/tests/.kunitconfig
 create mode 100644 drivers/gpu/drm/tests/Kconfig
 create mode 100644 drivers/gpu/drm/tests/Makefile
 create mode 100644 drivers/gpu/drm/tests/test-drm_buddy.c
 create mode 100644 drivers/gpu/drm/tests/test-drm_cmdline_parser.c
 create mode 100644 drivers/gpu/drm/tests/test-drm_damage_helper.c
 rename drivers/gpu/drm/{selftests => tests}/test-drm_dp_mst_helper.c (73%)
 create mode 100644 drivers/gpu/drm/tests/test-drm_format.c
 rename drivers/gpu/drm/{selftests => tests}/test-drm_framebuffer.c (96%)
 rename drivers/gpu/drm/{selftests => tests}/test-drm_mm.c (58%)
 rename drivers/

[PATCH 01/10] drm: selftest: convert drm_damage_helper selftest to KUnit

2022-06-15 Thread Maíra Canal
Considering the current adoption of the KUnit framework, convert the
DRM damage helper selftest to the KUnit API.

Co-developed-by: Arthur Grillo 
Signed-off-by: Arthur Grillo 
Signed-off-by: Maíra Canal 
---
 drivers/gpu/drm/Kconfig   |   2 +
 drivers/gpu/drm/Makefile  |   1 +
 drivers/gpu/drm/selftests/Makefile|   3 +-
 .../gpu/drm/selftests/drm_modeset_selftests.h |  21 -
 .../drm/selftests/test-drm_damage_helper.c| 667 --
 .../drm/selftests/test-drm_modeset_common.h   |  21 -
 drivers/gpu/drm/tests/Kconfig |  28 +
 drivers/gpu/drm/tests/Makefile|   2 +
 .../gpu/drm/tests/test-drm_damage_helper.c| 633 +
 9 files changed, 667 insertions(+), 711 deletions(-)
 delete mode 100644 drivers/gpu/drm/selftests/test-drm_damage_helper.c
 create mode 100644 drivers/gpu/drm/tests/Kconfig
 create mode 100644 drivers/gpu/drm/tests/Makefile
 create mode 100644 drivers/gpu/drm/tests/test-drm_damage_helper.c

diff --git a/drivers/gpu/drm/Kconfig b/drivers/gpu/drm/Kconfig
index e88c497fa010..bd1b5d82c9cf 100644
--- a/drivers/gpu/drm/Kconfig
+++ b/drivers/gpu/drm/Kconfig
@@ -70,6 +70,8 @@ config DRM_DEBUG_SELFTEST
 
  If in doubt, say "N".
 
+source "drivers/gpu/drm/tests/Kconfig"
+
 config DRM_KMS_HELPER
tristate
depends on DRM
diff --git a/drivers/gpu/drm/Makefile b/drivers/gpu/drm/Makefile
index 15fe3163f822..0f24aa542be0 100644
--- a/drivers/gpu/drm/Makefile
+++ b/drivers/gpu/drm/Makefile
@@ -76,6 +76,7 @@ obj-$(CONFIG_DRM_KMS_HELPER) += drm_kms_helper.o
 #
 
 obj-$(CONFIG_DRM_DEBUG_SELFTEST) += selftests/
+obj-y += tests/
 
 obj-$(CONFIG_DRM_MIPI_DBI) += drm_mipi_dbi.o
 obj-$(CONFIG_DRM_MIPI_DSI) += drm_mipi_dsi.o
diff --git a/drivers/gpu/drm/selftests/Makefile 
b/drivers/gpu/drm/selftests/Makefile
index 5ba5f9138c95..7a1a732e0a1b 100644
--- a/drivers/gpu/drm/selftests/Makefile
+++ b/drivers/gpu/drm/selftests/Makefile
@@ -1,8 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
 test-drm_modeset-y := test-drm_modeset_common.o test-drm_plane_helper.o \
   test-drm_format.o test-drm_framebuffer.o \
- test-drm_damage_helper.o test-drm_dp_mst_helper.o \
- test-drm_rect.o
+ test-drm_dp_mst_helper.o test-drm_rect.o
 
 obj-$(CONFIG_DRM_DEBUG_SELFTEST) += test-drm_mm.o test-drm_modeset.o 
test-drm_cmdline_parser.o \
test-drm_buddy.o
diff --git a/drivers/gpu/drm/selftests/drm_modeset_selftests.h 
b/drivers/gpu/drm/selftests/drm_modeset_selftests.h
index 782e285ca383..4787b3b70709 100644
--- a/drivers/gpu/drm/selftests/drm_modeset_selftests.h
+++ b/drivers/gpu/drm/selftests/drm_modeset_selftests.h
@@ -15,26 +15,5 @@ selftest(check_drm_format_block_width, 
igt_check_drm_format_block_width)
 selftest(check_drm_format_block_height, igt_check_drm_format_block_height)
 selftest(check_drm_format_min_pitch, igt_check_drm_format_min_pitch)
 selftest(check_drm_framebuffer_create, igt_check_drm_framebuffer_create)
-selftest(damage_iter_no_damage, igt_damage_iter_no_damage)
-selftest(damage_iter_no_damage_fractional_src, 
igt_damage_iter_no_damage_fractional_src)
-selftest(damage_iter_no_damage_src_moved, igt_damage_iter_no_damage_src_moved)
-selftest(damage_iter_no_damage_fractional_src_moved, 
igt_damage_iter_no_damage_fractional_src_moved)
-selftest(damage_iter_no_damage_not_visible, 
igt_damage_iter_no_damage_not_visible)
-selftest(damage_iter_no_damage_no_crtc, igt_damage_iter_no_damage_no_crtc)
-selftest(damage_iter_no_damage_no_fb, igt_damage_iter_no_damage_no_fb)
-selftest(damage_iter_simple_damage, igt_damage_iter_simple_damage)
-selftest(damage_iter_single_damage, igt_damage_iter_single_damage)
-selftest(damage_iter_single_damage_intersect_src, 
igt_damage_iter_single_damage_intersect_src)
-selftest(damage_iter_single_damage_outside_src, 
igt_damage_iter_single_damage_outside_src)
-selftest(damage_iter_single_damage_fractional_src, 
igt_damage_iter_single_damage_fractional_src)
-selftest(damage_iter_single_damage_intersect_fractional_src, 
igt_damage_iter_single_damage_intersect_fractional_src)
-selftest(damage_iter_single_damage_outside_fractional_src, 
igt_damage_iter_single_damage_outside_fractional_src)
-selftest(damage_iter_single_damage_src_moved, 
igt_damage_iter_single_damage_src_moved)
-selftest(damage_iter_single_damage_fractional_src_moved, 
igt_damage_iter_single_damage_fractional_src_moved)
-selftest(damage_iter_damage, igt_damage_iter_damage)
-selftest(damage_iter_damage_one_intersect, 
igt_damage_iter_damage_one_intersect)
-selftest(damage_iter_damage_one_outside, igt_damage_iter_damage_one_outside)
-selftest(damage_iter_damage_src_moved, igt_damage_iter_damage_src_moved)
-selftest(damage_iter_damage_not_visible, igt_damage_iter_damage_not_visible)
 selftest(dp_mst_calc_pbn_mode, igt_dp_mst_calc_pbn_mode)
 selftest(dp_mst_sideband_msg_req_decode, igt_dp_mst_s

[PATCH 02/10] drm: selftest: refactor drm_cmdline_parser

2022-06-15 Thread Maíra Canal
From: Arthur Grillo 

Refactor the tests by modularizing the functions to avoid code repetition.

Co-developed-by: Maíra Canal 
Signed-off-by: Arthur Grillo 
Signed-off-by: Maíra Canal 
---
 .../drm/selftests/test-drm_cmdline_parser.c   | 579 +-
 1 file changed, 156 insertions(+), 423 deletions(-)

diff --git a/drivers/gpu/drm/selftests/test-drm_cmdline_parser.c 
b/drivers/gpu/drm/selftests/test-drm_cmdline_parser.c
index d96cd890def6..57a229c5fc35 100644
--- a/drivers/gpu/drm/selftests/test-drm_cmdline_parser.c
+++ b/drivers/gpu/drm/selftests/test-drm_cmdline_parser.c
@@ -1,6 +1,8 @@
 // SPDX-License-Identifier: GPL-2.0
 /*
  * Copyright (c) 2019 Bootlin
+ * Copyright (c) 2021 Ma�ra Canal ,
+ * Copyright (c) 2021 Arthur Grillo 
  */
 
 #define pr_fmt(fmt) "drm_cmdline: " fmt
@@ -17,13 +19,25 @@
 
 static const struct drm_connector no_connector = {};
 
-static int drm_cmdline_test_force_e_only(void *ignored)
+static int drm_cmdline_test_properties(void *ignored,
+   struct drm_cmdline_mode *mode, enum drm_connector_force force)
+{
+   FAIL_ON(mode->rb);
+   FAIL_ON(mode->cvt);
+   FAIL_ON(mode->interlace);
+   FAIL_ON(mode->margins);
+   FAIL_ON(mode->force != force);
+
+   return 0;
+}
+
+static int drm_cmdline_test_force_only(void *ignored, char *cmdline,
+   const struct drm_connector *connector, enum drm_connector_force 
force)
 {
struct drm_cmdline_mode mode = { };
 
-   FAIL_ON(!drm_mode_parse_command_line_for_connector("e",
-  &no_connector,
-  &mode));
+   FAIL_ON(!drm_mode_parse_command_line_for_connector(cmdline,
+  connector, &mode));
FAIL_ON(mode.specified);
FAIL_ON(mode.refresh_specified);
FAIL_ON(mode.bpp_specified);
@@ -32,95 +46,101 @@ static int drm_cmdline_test_force_e_only(void *ignored)
FAIL_ON(mode.cvt);
FAIL_ON(mode.interlace);
FAIL_ON(mode.margins);
-   FAIL_ON(mode.force != DRM_FORCE_ON);
+   FAIL_ON(mode.force != force);
 
return 0;
 }
 
-static int drm_cmdline_test_force_D_only_not_digital(void *ignored)
+static int drm_cmdline_test_freestanding(void *ignored,
+   struct drm_cmdline_mode *mode, char *cmdline,
+   const struct drm_connector *connector)
 {
-   struct drm_cmdline_mode mode = { };
+   FAIL_ON(!drm_mode_parse_command_line_for_connector(cmdline,
+  connector, mode));
+   FAIL_ON(mode->specified);
+   FAIL_ON(mode->refresh_specified);
+   FAIL_ON(mode->bpp_specified);
 
-   FAIL_ON(!drm_mode_parse_command_line_for_connector("D",
-  &no_connector,
-  &mode));
-   FAIL_ON(mode.specified);
-   FAIL_ON(mode.refresh_specified);
-   FAIL_ON(mode.bpp_specified);
+   FAIL_ON(mode->tv_margins.right != 14);
+   FAIL_ON(mode->tv_margins.left != 24);
+   FAIL_ON(mode->tv_margins.bottom != 36);
+   FAIL_ON(mode->tv_margins.top != 42);
 
-   FAIL_ON(mode.rb);
-   FAIL_ON(mode.cvt);
-   FAIL_ON(mode.interlace);
-   FAIL_ON(mode.margins);
-   FAIL_ON(mode.force != DRM_FORCE_ON);
+   return 0;
+}
+
+static int drm_cmdline_test_res_init(void *ignored,
+   struct drm_cmdline_mode *mode, char *cmdline)
+{
+   FAIL_ON(!drm_mode_parse_command_line_for_connector(cmdline,
+  &no_connector, 
mode));
+   FAIL_ON(!mode->specified);
+   FAIL_ON(mode->xres != 720);
+   FAIL_ON(mode->yres != 480);
+
+   return 0;
+}
+
+static int drm_cmdline_test_res_bpp_init(void *ignored,
+   struct drm_cmdline_mode *mode, char *cmdline)
+{
+   FAIL_ON(!drm_mode_parse_command_line_for_connector(cmdline,
+  &no_connector, 
mode));
+   FAIL_ON(!mode->specified);
+   FAIL_ON(mode->xres != 720);
+   FAIL_ON(mode->yres != 480);
+
+   FAIL_ON(!mode->refresh_specified);
+   FAIL_ON(mode->refresh != 60);
+   FAIL_ON(!mode->bpp_specified);
+   FAIL_ON(mode->bpp != 24);
+
+   return 0;
+}
+
+static int drm_cmdline_test_force_e_only(void *ignored)
+{
+   drm_cmdline_test_force_only(ignored, "e", &no_connector, DRM_FORCE_ON);
+
+   return 0;
+}
+
+static int drm_cmdline_test_force_D_only_not_digital(void *ignored)
+{
+   drm_cmdline_test_force_only(ignored, "D", &no_connector, DRM_FORCE_ON);
 
return 0;
 }
 
 static const struct drm_connector connector_hdmi = {
.connector_type = DRM_MODE_CONNECTOR_HDMIB,
+
 };
 
 static int drm_cmdline_test_force_D_only_hdmi(void *ignored)
 {
-   struct drm_cmdline_mode mode = { };
-
-   FAIL_ON(!drm_

[PATCH 03/10] drm: selftest: convert drm_cmdline_parser selftest to KUnit

2022-06-15 Thread Maíra Canal
Considering the current adoption of the KUnit framework, convert the
DRM cmdline parser selftest to the KUnit API.

Co-developed-by: Arthur Grillo 
Signed-off-by: Arthur Grillo 
Signed-off-by: Maíra Canal 
---
 drivers/gpu/drm/selftests/Makefile|   2 +-
 .../gpu/drm/selftests/drm_cmdline_selftests.h |  68 --
 .../drm/selftests/test-drm_cmdline_parser.c   | 874 --
 drivers/gpu/drm/tests/.kunitconfig|   3 +
 drivers/gpu/drm/tests/Kconfig |  12 +
 drivers/gpu/drm/tests/Makefile|   1 +
 .../gpu/drm/tests/test-drm_cmdline_parser.c   | 799 
 7 files changed, 816 insertions(+), 943 deletions(-)
 delete mode 100644 drivers/gpu/drm/selftests/drm_cmdline_selftests.h
 delete mode 100644 drivers/gpu/drm/selftests/test-drm_cmdline_parser.c
 create mode 100644 drivers/gpu/drm/tests/.kunitconfig
 create mode 100644 drivers/gpu/drm/tests/test-drm_cmdline_parser.c

diff --git a/drivers/gpu/drm/selftests/Makefile 
b/drivers/gpu/drm/selftests/Makefile
index 7a1a732e0a1b..8633bb9ea717 100644
--- a/drivers/gpu/drm/selftests/Makefile
+++ b/drivers/gpu/drm/selftests/Makefile
@@ -3,5 +3,5 @@ test-drm_modeset-y := test-drm_modeset_common.o 
test-drm_plane_helper.o \
   test-drm_format.o test-drm_framebuffer.o \
  test-drm_dp_mst_helper.o test-drm_rect.o
 
-obj-$(CONFIG_DRM_DEBUG_SELFTEST) += test-drm_mm.o test-drm_modeset.o 
test-drm_cmdline_parser.o \
+obj-$(CONFIG_DRM_DEBUG_SELFTEST) += test-drm_mm.o test-drm_modeset.o \
test-drm_buddy.o
diff --git a/drivers/gpu/drm/selftests/drm_cmdline_selftests.h 
b/drivers/gpu/drm/selftests/drm_cmdline_selftests.h
deleted file mode 100644
index 29e367db6118..
--- a/drivers/gpu/drm/selftests/drm_cmdline_selftests.h
+++ /dev/null
@@ -1,68 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0 */
-/* List each unit test as selftest(function)
- *
- * The name is used as both an enum and expanded as igt__name to create
- * a module parameter. It must be unique and legal for a C identifier.
- *
- * Tests are executed in order by igt/drm_mm
- */
-
-#define cmdline_test(test) selftest(test, test)
-
-cmdline_test(drm_cmdline_test_force_d_only)
-cmdline_test(drm_cmdline_test_force_D_only_dvi)
-cmdline_test(drm_cmdline_test_force_D_only_hdmi)
-cmdline_test(drm_cmdline_test_force_D_only_not_digital)
-cmdline_test(drm_cmdline_test_force_e_only)
-cmdline_test(drm_cmdline_test_margin_only)
-cmdline_test(drm_cmdline_test_interlace_only)
-cmdline_test(drm_cmdline_test_res)
-cmdline_test(drm_cmdline_test_res_missing_x)
-cmdline_test(drm_cmdline_test_res_missing_y)
-cmdline_test(drm_cmdline_test_res_bad_y)
-cmdline_test(drm_cmdline_test_res_missing_y_bpp)
-cmdline_test(drm_cmdline_test_res_vesa)
-cmdline_test(drm_cmdline_test_res_vesa_rblank)
-cmdline_test(drm_cmdline_test_res_rblank)
-cmdline_test(drm_cmdline_test_res_bpp)
-cmdline_test(drm_cmdline_test_res_bad_bpp)
-cmdline_test(drm_cmdline_test_res_refresh)
-cmdline_test(drm_cmdline_test_res_bad_refresh)
-cmdline_test(drm_cmdline_test_res_bpp_refresh)
-cmdline_test(drm_cmdline_test_res_bpp_refresh_interlaced)
-cmdline_test(drm_cmdline_test_res_bpp_refresh_margins)
-cmdline_test(drm_cmdline_test_res_bpp_refresh_force_off)
-cmdline_test(drm_cmdline_test_res_bpp_refresh_force_on_off)
-cmdline_test(drm_cmdline_test_res_bpp_refresh_force_on)
-cmdline_test(drm_cmdline_test_res_bpp_refresh_force_on_analog)
-cmdline_test(drm_cmdline_test_res_bpp_refresh_force_on_digital)
-cmdline_test(drm_cmdline_test_res_bpp_refresh_interlaced_margins_force_on)
-cmdline_test(drm_cmdline_test_res_margins_force_on)
-cmdline_test(drm_cmdline_test_res_vesa_margins)
-cmdline_test(drm_cmdline_test_res_invalid_mode)
-cmdline_test(drm_cmdline_test_res_bpp_wrong_place_mode)
-cmdline_test(drm_cmdline_test_name)
-cmdline_test(drm_cmdline_test_name_bpp)
-cmdline_test(drm_cmdline_test_name_refresh)
-cmdline_test(drm_cmdline_test_name_bpp_refresh)
-cmdline_test(drm_cmdline_test_name_refresh_wrong_mode)
-cmdline_test(drm_cmdline_test_name_refresh_invalid_mode)
-cmdline_test(drm_cmdline_test_name_option)
-cmdline_test(drm_cmdline_test_name_bpp_option)
-cmdline_test(drm_cmdline_test_rotate_0)
-cmdline_test(drm_cmdline_test_rotate_90)
-cmdline_test(drm_cmdline_test_rotate_180)
-cmdline_test(drm_cmdline_test_rotate_270)
-cmdline_test(drm_cmdline_test_rotate_multiple)
-cmdline_test(drm_cmdline_test_rotate_invalid_val)
-cmdline_test(drm_cmdline_test_rotate_truncated)
-cmdline_test(drm_cmdline_test_hmirror)
-cmdline_test(drm_cmdline_test_vmirror)
-cmdline_test(drm_cmdline_test_margin_options)
-cmdline_test(drm_cmdline_test_multiple_options)
-cmdline_test(drm_cmdline_test_invalid_option)
-cmdline_test(drm_cmdline_test_bpp_extra_and_option)
-cmdline_test(drm_cmdline_test_extra_and_option)
-cmdline_test(drm_cmdline_test_freestanding_options)
-cmdline_test(drm_cmdline_test_freestanding_force_e_and_options)
-cmdline_test(drm_cmdline_test_pa

[PATCH 04/10] drm: selftest: convert drm_rect selftest to KUnit

2022-06-15 Thread Maíra Canal
Considering the current adoption of the KUnit framework, convert the
DRM rect selftest to the KUnit API.

Co-developed-by: Carlos Veras 
Signed-off-by: Carlos Veras 
Co-developed-by: Matheus Vieira 
Signed-off-by: Matheus Vieira 
Signed-off-by: Maíra Canal 
---
 drivers/gpu/drm/selftests/Makefile|   2 +-
 .../gpu/drm/selftests/drm_modeset_selftests.h |   4 -
 .../drm/selftests/test-drm_modeset_common.h   |   4 -
 drivers/gpu/drm/tests/Kconfig |  12 ++
 drivers/gpu/drm/tests/Makefile|   1 +
 .../drm/{selftests => tests}/test-drm_rect.c  | 124 +-
 6 files changed, 79 insertions(+), 68 deletions(-)
 rename drivers/gpu/drm/{selftests => tests}/test-drm_rect.c (53%)

diff --git a/drivers/gpu/drm/selftests/Makefile 
b/drivers/gpu/drm/selftests/Makefile
index 8633bb9ea717..8a794914e328 100644
--- a/drivers/gpu/drm/selftests/Makefile
+++ b/drivers/gpu/drm/selftests/Makefile
@@ -1,7 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
 test-drm_modeset-y := test-drm_modeset_common.o test-drm_plane_helper.o \
   test-drm_format.o test-drm_framebuffer.o \
- test-drm_dp_mst_helper.o test-drm_rect.o
+ test-drm_dp_mst_helper.o
 
 obj-$(CONFIG_DRM_DEBUG_SELFTEST) += test-drm_mm.o test-drm_modeset.o \
test-drm_buddy.o
diff --git a/drivers/gpu/drm/selftests/drm_modeset_selftests.h 
b/drivers/gpu/drm/selftests/drm_modeset_selftests.h
index 4787b3b70709..a3ca90307364 100644
--- a/drivers/gpu/drm/selftests/drm_modeset_selftests.h
+++ b/drivers/gpu/drm/selftests/drm_modeset_selftests.h
@@ -6,10 +6,6 @@
  *
  * Tests are executed in order by igt/drm_selftests_helper
  */
-selftest(drm_rect_clip_scaled_div_by_zero, 
igt_drm_rect_clip_scaled_div_by_zero)
-selftest(drm_rect_clip_scaled_not_clipped, 
igt_drm_rect_clip_scaled_not_clipped)
-selftest(drm_rect_clip_scaled_clipped, igt_drm_rect_clip_scaled_clipped)
-selftest(drm_rect_clip_scaled_signed_vs_unsigned, 
igt_drm_rect_clip_scaled_signed_vs_unsigned)
 selftest(check_plane_state, igt_check_plane_state)
 selftest(check_drm_format_block_width, igt_check_drm_format_block_width)
 selftest(check_drm_format_block_height, igt_check_drm_format_block_height)
diff --git a/drivers/gpu/drm/selftests/test-drm_modeset_common.h 
b/drivers/gpu/drm/selftests/test-drm_modeset_common.h
index c29354e59cec..42a10d7da51c 100644
--- a/drivers/gpu/drm/selftests/test-drm_modeset_common.h
+++ b/drivers/gpu/drm/selftests/test-drm_modeset_common.h
@@ -16,10 +16,6 @@
 
 #define FAIL_ON(x) FAIL((x), "%s", "FAIL_ON(" __stringify(x) ")\n")
 
-int igt_drm_rect_clip_scaled_div_by_zero(void *ignored);
-int igt_drm_rect_clip_scaled_not_clipped(void *ignored);
-int igt_drm_rect_clip_scaled_clipped(void *ignored);
-int igt_drm_rect_clip_scaled_signed_vs_unsigned(void *ignored);
 int igt_check_plane_state(void *ignored);
 int igt_check_drm_format_block_width(void *ignored);
 int igt_check_drm_format_block_height(void *ignored);
diff --git a/drivers/gpu/drm/tests/Kconfig b/drivers/gpu/drm/tests/Kconfig
index 14ee077cca54..bab6bf363363 100644
--- a/drivers/gpu/drm/tests/Kconfig
+++ b/drivers/gpu/drm/tests/Kconfig
@@ -37,4 +37,16 @@ config DRM_CMDLINE_PARSER_KUNIT_TEST
 
If in doubt, say "N".
 
+config DRM_RECT_KUNIT_TEST
+   tristate "KUnit tests for DRM rect" if !DRM_KUNIT_TEST
+   select DRM_KMS_HELPER
+   default y if DRM_KUNIT_TEST
+   help
+   This option provides a KUnit module that can be used to run
+   an unit test on the DRM rect API. This option is not
+   useful for distributions or general kernels, but only for kernel
+   developers working on DRM and associated drivers.
+
+   If in doubt, say "N".
+
 endmenu
diff --git a/drivers/gpu/drm/tests/Makefile b/drivers/gpu/drm/tests/Makefile
index 3ded14858e8c..d03e28724d47 100644
--- a/drivers/gpu/drm/tests/Makefile
+++ b/drivers/gpu/drm/tests/Makefile
@@ -1,3 +1,4 @@
 # SPDX-License-Identifier: GPL-2.0-only
 obj-$(CONFIG_DRM_DAMAGE_HELPER_KUNIT_TEST) += test-drm_damage_helper.o
 obj-$(CONFIG_DRM_CMDLINE_PARSER_KUNIT_TEST) += test-drm_cmdline_parser.o
+obj-$(CONFIG_DRM_RECT_KUNIT_TEST) += test-drm_rect.o
diff --git a/drivers/gpu/drm/selftests/test-drm_rect.c 
b/drivers/gpu/drm/tests/test-drm_rect.c
similarity index 53%
rename from drivers/gpu/drm/selftests/test-drm_rect.c
rename to drivers/gpu/drm/tests/test-drm_rect.c
index 3a5ff38321f4..94336412d32d 100644
--- a/drivers/gpu/drm/selftests/test-drm_rect.c
+++ b/drivers/gpu/drm/tests/test-drm_rect.c
@@ -3,15 +3,10 @@
  * Test cases for the drm_rect functions
  */
 
-#define pr_fmt(fmt) "drm_rect: " fmt
-
-#include 
-
+#include 
 #include 
 
-#include "test-drm_modeset_common.h"
-
-int igt_drm_rect_clip_scaled_div_by_zero(void *ignored)
+static void igt_drm_rect_clip_scaled_div_by_zero(struct kunit *test)
 {
struct drm_rect src, dst, clip;
bool visible;
@@ -

[PATCH 1/5] drm/msm: less magic numbers in msm_mdss_enable

2022-06-15 Thread Dmitry Baryshkov
Replace magic register writes in msm_mdss_enable() with version that
contains less magic and more variable names that can be traced back to
the dpu_hw_catalog or the downstream dtsi files.

Reviewed-by: Abhinav Kumar 
Signed-off-by: Dmitry Baryshkov 
---
 drivers/gpu/drm/msm/msm_mdss.c | 80 ++
 1 file changed, 72 insertions(+), 8 deletions(-)

diff --git a/drivers/gpu/drm/msm/msm_mdss.c b/drivers/gpu/drm/msm/msm_mdss.c
index 0454a571adf7..b41848bfff91 100644
--- a/drivers/gpu/drm/msm/msm_mdss.c
+++ b/drivers/gpu/drm/msm/msm_mdss.c
@@ -21,6 +21,7 @@
 #define HW_REV 0x0
 #define HW_INTR_STATUS 0x0010
 
+#define UBWC_DEC_HW_VERSION0x58
 #define UBWC_STATIC0x144
 #define UBWC_CTRL_20x150
 #define UBWC_PREDICTION_MODE   0x154
@@ -132,9 +133,63 @@ static int _msm_mdss_irq_domain_add(struct msm_mdss 
*msm_mdss)
return 0;
 }
 
+#define UBWC_1_0 0x1000
+#define UBWC_2_0 0x2000
+#define UBWC_3_0 0x3000
+#define UBWC_4_0 0x4000
+
+static void msm_mdss_setup_ubwc_dec_20(struct msm_mdss *msm_mdss,
+  u32 ubwc_static)
+{
+   writel_relaxed(ubwc_static, msm_mdss->mmio + UBWC_STATIC);
+}
+
+static void msm_mdss_setup_ubwc_dec_30(struct msm_mdss *msm_mdss,
+  unsigned int ubwc_version,
+  u32 ubwc_swizzle,
+  u32 highest_bank_bit,
+  u32 macrotile_mode)
+{
+   u32 value = (ubwc_swizzle & 0x1) |
+   (highest_bank_bit & 0x3) << 4 |
+   (macrotile_mode & 0x1) << 12;
+
+   if (ubwc_version == UBWC_3_0)
+   value |= BIT(10);
+
+   if (ubwc_version == UBWC_1_0)
+   value |= BIT(8);
+
+   writel_relaxed(value, msm_mdss->mmio + UBWC_STATIC);
+}
+
+static void msm_mdss_setup_ubwc_dec_40(struct msm_mdss *msm_mdss,
+  unsigned int ubwc_version,
+  u32 ubwc_swizzle,
+  u32 ubwc_static,
+  u32 highest_bank_bit,
+  u32 macrotile_mode)
+{
+   u32 value = (ubwc_swizzle & 0x7) |
+   (ubwc_static & 0x1) << 3 |
+   (highest_bank_bit & 0x7) << 4 |
+   (macrotile_mode & 0x1) << 12;
+
+   writel_relaxed(value, msm_mdss->mmio + UBWC_STATIC);
+
+   if (ubwc_version == UBWC_3_0) {
+   writel_relaxed(1, msm_mdss->mmio + UBWC_CTRL_2);
+   writel_relaxed(0, msm_mdss->mmio + UBWC_PREDICTION_MODE);
+   } else {
+   writel_relaxed(2, msm_mdss->mmio + UBWC_CTRL_2);
+   writel_relaxed(1, msm_mdss->mmio + UBWC_PREDICTION_MODE);
+   }
+}
+
 static int msm_mdss_enable(struct msm_mdss *msm_mdss)
 {
int ret;
+   u32 hw_rev;
 
ret = clk_bulk_prepare_enable(msm_mdss->num_clocks, msm_mdss->clocks);
if (ret) {
@@ -149,26 +204,35 @@ static int msm_mdss_enable(struct msm_mdss *msm_mdss)
if (msm_mdss->is_mdp5)
return 0;
 
+   hw_rev = readl_relaxed(msm_mdss->mmio + HW_REV);
+   dev_dbg(msm_mdss->dev, "HW_REV: 0x%x\n", hw_rev);
+   dev_dbg(msm_mdss->dev, "UBWC_DEC_HW_VERSION: 0x%x\n",
+   readl_relaxed(msm_mdss->mmio + UBWC_DEC_HW_VERSION));
+
/*
 * ubwc config is part of the "mdss" region which is not accessible
 * from the rest of the driver. hardcode known configurations here
+*
+* Decoder version can be read from the UBWC_DEC_HW_VERSION reg,
+* UBWC_n and the rest of params comes from hw_catalog.
+* Unforunately this driver can not access hw catalog, so we have to
+* hardcode them here.
 */
-   switch (readl_relaxed(msm_mdss->mmio + HW_REV)) {
+   switch (hw_rev) {
case DPU_HW_VER_500:
case DPU_HW_VER_501:
-   writel_relaxed(0x420, msm_mdss->mmio + UBWC_STATIC);
+   msm_mdss_setup_ubwc_dec_30(msm_mdss, UBWC_3_0, 0, 2, 0);
break;
case DPU_HW_VER_600:
-   /* TODO: 0x102e for LP_DDR4 */
-   writel_relaxed(0x103e, msm_mdss->mmio + UBWC_STATIC);
-   writel_relaxed(2, msm_mdss->mmio + UBWC_CTRL_2);
-   writel_relaxed(1, msm_mdss->mmio + UBWC_PREDICTION_MODE);
+   /* TODO: highest_bank_bit = 2 for LP_DDR4 */
+   msm_mdss_setup_ubwc_dec_40(msm_mdss, UBWC_4_0, 6, 1, 3, 1);
break;
case DPU_HW_VER_620:
-   writel_relaxed(0x1e, msm_mdss->mmio + UBWC_STATIC);
+   /* UBWC_2_0 */
+   msm_mdss_setup_ubwc_dec_20(msm_mdss, 0x1e);
break;
case DPU_HW_VER_720:
-   writel_relaxed(0x101e, msm_mdss->mmio + UBWC_S

[PATCH 2/5] drm/msm/mdss: enable optional core clock for MDP5 MDSS

2022-06-15 Thread Dmitry Baryshkov
Enable (optional) core (MDP_CLK) clock that allows accessing HW_REV
registers during the platform init.

Signed-off-by: Dmitry Baryshkov 
---
 drivers/gpu/drm/msm/msm_mdss.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/msm/msm_mdss.c b/drivers/gpu/drm/msm/msm_mdss.c
index b41848bfff91..f7b4628986b8 100644
--- a/drivers/gpu/drm/msm/msm_mdss.c
+++ b/drivers/gpu/drm/msm/msm_mdss.c
@@ -288,7 +288,7 @@ static int msm_mdss_reset(struct device *dev)
 /*
  * MDP5 MDSS uses at most three specified clocks.
  */
-#define MDP5_MDSS_NUM_CLOCKS 3
+#define MDP5_MDSS_NUM_CLOCKS 4
 static int mdp5_mdss_parse_clock(struct platform_device *pdev, struct 
clk_bulk_data **clocks)
 {
struct clk_bulk_data *bulk;
@@ -305,6 +305,7 @@ static int mdp5_mdss_parse_clock(struct platform_device 
*pdev, struct clk_bulk_d
bulk[num_clocks++].id = "iface";
bulk[num_clocks++].id = "bus";
bulk[num_clocks++].id = "vsync";
+   bulk[num_clocks++].id = "core"; /* for hw_rev access */
 
ret = devm_clk_bulk_get_optional(&pdev->dev, num_clocks, bulk);
if (ret)
-- 
2.35.1



[PATCH 05/10] drm: selftest: convert drm_format selftest to KUnit

2022-06-15 Thread Maíra Canal
Considering the current adoption of the KUnit framework, convert the
DRM format selftest to the KUnit API.

Signed-off-by: Maíra Canal 
---
 drivers/gpu/drm/selftests/Makefile|   3 +-
 .../gpu/drm/selftests/drm_modeset_selftests.h |   3 -
 drivers/gpu/drm/selftests/test-drm_format.c   | 280 -
 .../drm/selftests/test-drm_modeset_common.h   |   3 -
 drivers/gpu/drm/tests/Kconfig |  12 +
 drivers/gpu/drm/tests/Makefile|   1 +
 drivers/gpu/drm/tests/test-drm_format.c   | 284 ++
 7 files changed, 298 insertions(+), 288 deletions(-)
 delete mode 100644 drivers/gpu/drm/selftests/test-drm_format.c
 create mode 100644 drivers/gpu/drm/tests/test-drm_format.c

diff --git a/drivers/gpu/drm/selftests/Makefile 
b/drivers/gpu/drm/selftests/Makefile
index 8a794914e328..b7f252d886d0 100644
--- a/drivers/gpu/drm/selftests/Makefile
+++ b/drivers/gpu/drm/selftests/Makefile
@@ -1,7 +1,6 @@
 # SPDX-License-Identifier: GPL-2.0-only
 test-drm_modeset-y := test-drm_modeset_common.o test-drm_plane_helper.o \
-  test-drm_format.o test-drm_framebuffer.o \
- test-drm_dp_mst_helper.o
+  test-drm_framebuffer.o test-drm_dp_mst_helper.o
 
 obj-$(CONFIG_DRM_DEBUG_SELFTEST) += test-drm_mm.o test-drm_modeset.o \
test-drm_buddy.o
diff --git a/drivers/gpu/drm/selftests/drm_modeset_selftests.h 
b/drivers/gpu/drm/selftests/drm_modeset_selftests.h
index a3ca90307364..63061ef55eff 100644
--- a/drivers/gpu/drm/selftests/drm_modeset_selftests.h
+++ b/drivers/gpu/drm/selftests/drm_modeset_selftests.h
@@ -7,9 +7,6 @@
  * Tests are executed in order by igt/drm_selftests_helper
  */
 selftest(check_plane_state, igt_check_plane_state)
-selftest(check_drm_format_block_width, igt_check_drm_format_block_width)
-selftest(check_drm_format_block_height, igt_check_drm_format_block_height)
-selftest(check_drm_format_min_pitch, igt_check_drm_format_min_pitch)
 selftest(check_drm_framebuffer_create, igt_check_drm_framebuffer_create)
 selftest(dp_mst_calc_pbn_mode, igt_dp_mst_calc_pbn_mode)
 selftest(dp_mst_sideband_msg_req_decode, igt_dp_mst_sideband_msg_req_decode)
diff --git a/drivers/gpu/drm/selftests/test-drm_format.c 
b/drivers/gpu/drm/selftests/test-drm_format.c
deleted file mode 100644
index c5e212afa27a..
--- a/drivers/gpu/drm/selftests/test-drm_format.c
+++ /dev/null
@@ -1,280 +0,0 @@
-// SPDX-License-Identifier: GPL-2.0
-/*
- * Test cases for the drm_format functions
- */
-
-#define pr_fmt(fmt) "drm_format: " fmt
-
-#include 
-#include 
-
-#include 
-
-#include "test-drm_modeset_common.h"
-
-int igt_check_drm_format_block_width(void *ignored)
-{
-   const struct drm_format_info *info = NULL;
-
-   /* Test invalid arguments */
-   FAIL_ON(drm_format_info_block_width(info, 0) != 0);
-   FAIL_ON(drm_format_info_block_width(info, -1) != 0);
-   FAIL_ON(drm_format_info_block_width(info, 1) != 0);
-
-   /* Test 1 plane format */
-   info = drm_format_info(DRM_FORMAT_XRGB);
-   FAIL_ON(!info);
-   FAIL_ON(drm_format_info_block_width(info, 0) != 1);
-   FAIL_ON(drm_format_info_block_width(info, 1) != 0);
-   FAIL_ON(drm_format_info_block_width(info, -1) != 0);
-
-   /* Test 2 planes format */
-   info = drm_format_info(DRM_FORMAT_NV12);
-   FAIL_ON(!info);
-   FAIL_ON(drm_format_info_block_width(info, 0) != 1);
-   FAIL_ON(drm_format_info_block_width(info, 1) != 1);
-   FAIL_ON(drm_format_info_block_width(info, 2) != 0);
-   FAIL_ON(drm_format_info_block_width(info, -1) != 0);
-
-   /* Test 3 planes format */
-   info = drm_format_info(DRM_FORMAT_YUV422);
-   FAIL_ON(!info);
-   FAIL_ON(drm_format_info_block_width(info, 0) != 1);
-   FAIL_ON(drm_format_info_block_width(info, 1) != 1);
-   FAIL_ON(drm_format_info_block_width(info, 2) != 1);
-   FAIL_ON(drm_format_info_block_width(info, 3) != 0);
-   FAIL_ON(drm_format_info_block_width(info, -1) != 0);
-
-   /* Test a tiled format */
-   info = drm_format_info(DRM_FORMAT_X0L0);
-   FAIL_ON(!info);
-   FAIL_ON(drm_format_info_block_width(info, 0) != 2);
-   FAIL_ON(drm_format_info_block_width(info, 1) != 0);
-   FAIL_ON(drm_format_info_block_width(info, -1) != 0);
-
-   return 0;
-}
-
-int igt_check_drm_format_block_height(void *ignored)
-{
-   const struct drm_format_info *info = NULL;
-
-   /* Test invalid arguments */
-   FAIL_ON(drm_format_info_block_height(info, 0) != 0);
-   FAIL_ON(drm_format_info_block_height(info, -1) != 0);
-   FAIL_ON(drm_format_info_block_height(info, 1) != 0);
-
-   /* Test 1 plane format */
-   info = drm_format_info(DRM_FORMAT_XRGB);
-   FAIL_ON(!info);
-   FAIL_ON(drm_format_info_block_height(info, 0) != 1);
-   FAIL_ON(drm_format_info_block_height(info, 1) != 0);
-   FAIL_ON(drm_format_info_block_height(info, -1) != 

[PATCH 06/10] drm: selftest: convert drm_plane_helper selftest to KUnit

2022-06-15 Thread Maíra Canal
Considering the current adoption of the KUnit framework, convert the
DRM plane helper selftest to the KUnit API.

Co-developed-by: Djakson C. G. Filho 
Signed-off-by: Djakson C. G. Filho 
Co-developed-by: Anderson Fraga 
Signed-off-by: Anderson Fraga 
Signed-off-by: Maíra Canal 
---
 drivers/gpu/drm/selftests/Makefile|   4 +-
 .../gpu/drm/selftests/drm_modeset_selftests.h |   1 -
 .../drm/selftests/test-drm_modeset_common.h   |   1 -
 drivers/gpu/drm/tests/Kconfig |  12 +++
 drivers/gpu/drm/tests/Makefile|   1 +
 .../test-drm_plane_helper.c   | 101 ++
 6 files changed, 70 insertions(+), 50 deletions(-)
 rename drivers/gpu/drm/{selftests => tests}/test-drm_plane_helper.c (62%)

diff --git a/drivers/gpu/drm/selftests/Makefile 
b/drivers/gpu/drm/selftests/Makefile
index b7f252d886d0..9e0ccb482841 100644
--- a/drivers/gpu/drm/selftests/Makefile
+++ b/drivers/gpu/drm/selftests/Makefile
@@ -1,6 +1,6 @@
 # SPDX-License-Identifier: GPL-2.0-only
-test-drm_modeset-y := test-drm_modeset_common.o test-drm_plane_helper.o \
-  test-drm_framebuffer.o test-drm_dp_mst_helper.o
+test-drm_modeset-y := test-drm_modeset_common.o test-drm_framebuffer.o \
+   test-drm_dp_mst_helper.o
 
 obj-$(CONFIG_DRM_DEBUG_SELFTEST) += test-drm_mm.o test-drm_modeset.o \
test-drm_buddy.o
diff --git a/drivers/gpu/drm/selftests/drm_modeset_selftests.h 
b/drivers/gpu/drm/selftests/drm_modeset_selftests.h
index 63061ef55eff..22e467f6465a 100644
--- a/drivers/gpu/drm/selftests/drm_modeset_selftests.h
+++ b/drivers/gpu/drm/selftests/drm_modeset_selftests.h
@@ -6,7 +6,6 @@
  *
  * Tests are executed in order by igt/drm_selftests_helper
  */
-selftest(check_plane_state, igt_check_plane_state)
 selftest(check_drm_framebuffer_create, igt_check_drm_framebuffer_create)
 selftest(dp_mst_calc_pbn_mode, igt_dp_mst_calc_pbn_mode)
 selftest(dp_mst_sideband_msg_req_decode, igt_dp_mst_sideband_msg_req_decode)
diff --git a/drivers/gpu/drm/selftests/test-drm_modeset_common.h 
b/drivers/gpu/drm/selftests/test-drm_modeset_common.h
index 5709d967a5c4..790f3cf31f0d 100644
--- a/drivers/gpu/drm/selftests/test-drm_modeset_common.h
+++ b/drivers/gpu/drm/selftests/test-drm_modeset_common.h
@@ -16,7 +16,6 @@
 
 #define FAIL_ON(x) FAIL((x), "%s", "FAIL_ON(" __stringify(x) ")\n")
 
-int igt_check_plane_state(void *ignored);
 int igt_check_drm_framebuffer_create(void *ignored);
 int igt_dp_mst_calc_pbn_mode(void *ignored);
 int igt_dp_mst_sideband_msg_req_decode(void *ignored);
diff --git a/drivers/gpu/drm/tests/Kconfig b/drivers/gpu/drm/tests/Kconfig
index 7c4f76560152..5aa8ac2dd28e 100644
--- a/drivers/gpu/drm/tests/Kconfig
+++ b/drivers/gpu/drm/tests/Kconfig
@@ -61,4 +61,16 @@ config DRM_FORMAT_KUNIT_TEST
 
If in doubt, say "N".
 
+config DRM_PLANE_HELPER_KUNIT_TEST
+   tristate "KUnit tests for DRM plane helper" if !DRM_KUNIT_TEST
+   select DRM_KMS_HELPER
+   default y if DRM_KUNIT_TEST
+   help
+   This option provides KUnit modules that can be used to run
+   various selftests on parts of the DRM plane helper API.  This
+   option is not useful for distributions or general kernels, but 
only
+   for kernel developers working on DRM and associated drivers.
+
+   If in doubt, say "N".
+
 endmenu
diff --git a/drivers/gpu/drm/tests/Makefile b/drivers/gpu/drm/tests/Makefile
index 95d1f67f609d..6e3a10806cd8 100644
--- a/drivers/gpu/drm/tests/Makefile
+++ b/drivers/gpu/drm/tests/Makefile
@@ -3,3 +3,4 @@ obj-$(CONFIG_DRM_DAMAGE_HELPER_KUNIT_TEST) += 
test-drm_damage_helper.o
 obj-$(CONFIG_DRM_CMDLINE_PARSER_KUNIT_TEST) += test-drm_cmdline_parser.o
 obj-$(CONFIG_DRM_RECT_KUNIT_TEST) += test-drm_rect.o
 obj-$(CONFIG_DRM_FORMAT_KUNIT_TEST) += test-drm_format.o
+obj-$(CONFIG_DRM_PLANE_HELPER_KUNIT_TEST) += test-drm_plane_helper.o
diff --git a/drivers/gpu/drm/selftests/test-drm_plane_helper.c 
b/drivers/gpu/drm/tests/test-drm_plane_helper.c
similarity index 62%
rename from drivers/gpu/drm/selftests/test-drm_plane_helper.c
rename to drivers/gpu/drm/tests/test-drm_plane_helper.c
index b61273e9c403..354c2c8d9f1c 100644
--- a/drivers/gpu/drm/selftests/test-drm_plane_helper.c
+++ b/drivers/gpu/drm/tests/test-drm_plane_helper.c
@@ -3,14 +3,11 @@
  * Test cases for the drm_plane_helper functions
  */
 
-#define pr_fmt(fmt) "drm_plane_helper: " fmt
-
+#include 
 #include 
 #include 
 #include 
 
-#include "test-drm_modeset_common.h"
-
 static void set_src(struct drm_plane_state *plane_state,
unsigned src_x, unsigned src_y,
unsigned src_w, unsigned src_h)
@@ -73,7 +70,7 @@ static bool check_crtc_eq(struct drm_plane_state *plane_state,
return true;
 }
 
-int igt_check_plane_state(void *ignored)
+static void igt_check_plane_state(struct kunit *test)
 {
int ret;
 
@@ -108,10 +105,10 

[PATCH 3/5] drm/msm/mdss: check for core clk before accessing HW_REV

2022-06-15 Thread Dmitry Baryshkov
Rather than checking whether the platform is an mdp5 or dpu platform,
check if the MDP_CLK is provided or not before trying to access HW_REV
(and skip reading the registers if the clock is not provided by the DT).

Signed-off-by: Dmitry Baryshkov 
---
 drivers/gpu/drm/msm/msm_mdss.c | 22 +-
 1 file changed, 17 insertions(+), 5 deletions(-)

diff --git a/drivers/gpu/drm/msm/msm_mdss.c b/drivers/gpu/drm/msm/msm_mdss.c
index f7b4628986b8..d81d8fe3584e 100644
--- a/drivers/gpu/drm/msm/msm_mdss.c
+++ b/drivers/gpu/drm/msm/msm_mdss.c
@@ -32,7 +32,6 @@ struct msm_mdss {
void __iomem *mmio;
struct clk_bulk_data *clocks;
size_t num_clocks;
-   bool is_mdp5;
struct {
unsigned long enabled_mask;
struct irq_domain *domain;
@@ -186,6 +185,19 @@ static void msm_mdss_setup_ubwc_dec_40(struct msm_mdss 
*msm_mdss,
}
 }
 
+static bool msm_mdss_has_clock(struct msm_mdss *msm_mdss, const char *name)
+{
+   unsigned int i;
+
+   for (i = 0; i < msm_mdss->num_clocks; i++) {
+   if (!strcmp(msm_mdss->clocks[i].id, name) &&
+   msm_mdss->clocks[i].clk)
+   return true;
+   }
+
+   return false;
+}
+
 static int msm_mdss_enable(struct msm_mdss *msm_mdss)
 {
int ret;
@@ -198,10 +210,11 @@ static int msm_mdss_enable(struct msm_mdss *msm_mdss)
}
 
/*
-* HW_REV requires MDSS_MDP_CLK, which is not enabled by the mdss on
-* mdp5 hardware. Skip reading it for now.
+* HW_REV requires MDSS_MDP_CLK, which is not used for MDSS device in
+* older device trees. Skip accessing registers if the clock is not
+* present.
 */
-   if (msm_mdss->is_mdp5)
+   if (!msm_mdss_has_clock(msm_mdss, "core"))
return 0;
 
hw_rev = readl_relaxed(msm_mdss->mmio + HW_REV);
@@ -345,7 +358,6 @@ static struct msm_mdss *msm_mdss_init(struct 
platform_device *pdev, bool is_mdp5
return ERR_PTR(ret);
}
msm_mdss->num_clocks = ret;
-   msm_mdss->is_mdp5 = is_mdp5;
 
msm_mdss->dev = &pdev->dev;
 
-- 
2.35.1



[PATCH 5/5] arm64: dts: qcom: add mdp_clk clock to the MDSS device

2022-06-15 Thread Dmitry Baryshkov
Add MDP_CLK ("core") clock to the mdss device to allow MDSS driver to
access HW_REV/etc registers.

Signed-off-by: Dmitry Baryshkov 
---
 arch/arm64/boot/dts/qcom/msm8996.dtsi | 5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

diff --git a/arch/arm64/boot/dts/qcom/msm8996.dtsi 
b/arch/arm64/boot/dts/qcom/msm8996.dtsi
index f0f81c23c16f..3d8ecfe56fb3 100644
--- a/arch/arm64/boot/dts/qcom/msm8996.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8996.dtsi
@@ -773,8 +773,9 @@ mdss: mdss@90 {
interrupt-controller;
#interrupt-cells = <1>;
 
-   clocks = <&mmcc MDSS_AHB_CLK>;
-   clock-names = "iface";
+   clocks = <&mmcc MDSS_AHB_CLK>,
+<&mmcc MDSS_MDP_CLK>;
+   clock-names = "iface", "core";
 
#address-cells = <1>;
#size-cells = <1>;
-- 
2.35.1



[PATCH 4/5] drm/msm/mdss: move is_mdp5 condition to msm_mdss_init

2022-06-15 Thread Dmitry Baryshkov
Move is_mdp5 check to a more logical place, to the msm_mdss_init(),
rather than getting it in the mdss_probe() and passing it then as an
argument.

Signed-off-by: Dmitry Baryshkov 
---
 drivers/gpu/drm/msm/msm_mdss.c | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/msm/msm_mdss.c b/drivers/gpu/drm/msm/msm_mdss.c
index d81d8fe3584e..ce8ff5bfe55a 100644
--- a/drivers/gpu/drm/msm/msm_mdss.c
+++ b/drivers/gpu/drm/msm/msm_mdss.c
@@ -329,8 +329,9 @@ static int mdp5_mdss_parse_clock(struct platform_device 
*pdev, struct clk_bulk_d
return num_clocks;
 }
 
-static struct msm_mdss *msm_mdss_init(struct platform_device *pdev, bool 
is_mdp5)
+static struct msm_mdss *msm_mdss_init(struct platform_device *pdev)
 {
+   bool is_mdp5 = of_device_is_compatible(pdev->dev.of_node, "qcom,mdss");
struct msm_mdss *msm_mdss;
int ret;
int irq;
@@ -420,11 +421,10 @@ static const struct dev_pm_ops mdss_pm_ops = {
 static int mdss_probe(struct platform_device *pdev)
 {
struct msm_mdss *mdss;
-   bool is_mdp5 = of_device_is_compatible(pdev->dev.of_node, "qcom,mdss");
struct device *dev = &pdev->dev;
int ret;
 
-   mdss = msm_mdss_init(pdev, is_mdp5);
+   mdss = msm_mdss_init(pdev);
if (IS_ERR(mdss))
return PTR_ERR(mdss);
 
-- 
2.35.1



[PATCH 07/10] drm: selftest: convert drm_dp_mst_helper selftest to KUnit

2022-06-15 Thread Maíra Canal
Considering the current adoption of the KUnit framework, convert the
DRM DP MST helper selftest to the KUnit API.

Co-developed-by: Rubens Gomes Neto 
Signed-off-by: Rubens Gomes Neto 
Signed-off-by: Maíra Canal 
---
 drivers/gpu/drm/selftests/Makefile|  3 +-
 .../gpu/drm/selftests/drm_modeset_selftests.h |  2 -
 .../drm/selftests/test-drm_modeset_common.h   |  2 -
 drivers/gpu/drm/tests/Kconfig | 13 +++
 drivers/gpu/drm/tests/Makefile|  1 +
 .../test-drm_dp_mst_helper.c  | 82 ++-
 6 files changed, 59 insertions(+), 44 deletions(-)
 rename drivers/gpu/drm/{selftests => tests}/test-drm_dp_mst_helper.c (73%)

diff --git a/drivers/gpu/drm/selftests/Makefile 
b/drivers/gpu/drm/selftests/Makefile
index 9e0ccb482841..1539f55db9a7 100644
--- a/drivers/gpu/drm/selftests/Makefile
+++ b/drivers/gpu/drm/selftests/Makefile
@@ -1,6 +1,5 @@
 # SPDX-License-Identifier: GPL-2.0-only
-test-drm_modeset-y := test-drm_modeset_common.o test-drm_framebuffer.o \
-   test-drm_dp_mst_helper.o
+test-drm_modeset-y := test-drm_modeset_common.o test-drm_framebuffer.o
 
 obj-$(CONFIG_DRM_DEBUG_SELFTEST) += test-drm_mm.o test-drm_modeset.o \
test-drm_buddy.o
diff --git a/drivers/gpu/drm/selftests/drm_modeset_selftests.h 
b/drivers/gpu/drm/selftests/drm_modeset_selftests.h
index 22e467f6465a..40a29b8cf386 100644
--- a/drivers/gpu/drm/selftests/drm_modeset_selftests.h
+++ b/drivers/gpu/drm/selftests/drm_modeset_selftests.h
@@ -7,5 +7,3 @@
  * Tests are executed in order by igt/drm_selftests_helper
  */
 selftest(check_drm_framebuffer_create, igt_check_drm_framebuffer_create)
-selftest(dp_mst_calc_pbn_mode, igt_dp_mst_calc_pbn_mode)
-selftest(dp_mst_sideband_msg_req_decode, igt_dp_mst_sideband_msg_req_decode)
diff --git a/drivers/gpu/drm/selftests/test-drm_modeset_common.h 
b/drivers/gpu/drm/selftests/test-drm_modeset_common.h
index 790f3cf31f0d..3feb2fea1a6b 100644
--- a/drivers/gpu/drm/selftests/test-drm_modeset_common.h
+++ b/drivers/gpu/drm/selftests/test-drm_modeset_common.h
@@ -17,7 +17,5 @@
 #define FAIL_ON(x) FAIL((x), "%s", "FAIL_ON(" __stringify(x) ")\n")
 
 int igt_check_drm_framebuffer_create(void *ignored);
-int igt_dp_mst_calc_pbn_mode(void *ignored);
-int igt_dp_mst_sideband_msg_req_decode(void *ignored);
 
 #endif
diff --git a/drivers/gpu/drm/tests/Kconfig b/drivers/gpu/drm/tests/Kconfig
index 5aa8ac2dd28e..eea0783f981d 100644
--- a/drivers/gpu/drm/tests/Kconfig
+++ b/drivers/gpu/drm/tests/Kconfig
@@ -73,4 +73,17 @@ config DRM_PLANE_HELPER_KUNIT_TEST
 
If in doubt, say "N".
 
+config DRM_DP_MST_HELPER_KUNIT_TEST
+   tristate "KUnit tests for DRM DP MST helper" if !DRM_KUNIT_TEST
+   select DRM_DISPLAY_HELPER
+   select DRM_DISPLAY_DP_HELPER
+   default y if DRM_KUNIT_TEST
+   help
+   This option provides a kunit module that can be used to run
+   an unit test on the DRM DP MST helper API. This option is not
+   useful for distributions or general kernels, but only for kernel
+   developers working on DRM and associated drivers.
+
+   If in doubt, say "N".
+
 endmenu
diff --git a/drivers/gpu/drm/tests/Makefile b/drivers/gpu/drm/tests/Makefile
index 6e3a10806cd8..735ca8e4c446 100644
--- a/drivers/gpu/drm/tests/Makefile
+++ b/drivers/gpu/drm/tests/Makefile
@@ -4,3 +4,4 @@ obj-$(CONFIG_DRM_CMDLINE_PARSER_KUNIT_TEST) += 
test-drm_cmdline_parser.o
 obj-$(CONFIG_DRM_RECT_KUNIT_TEST) += test-drm_rect.o
 obj-$(CONFIG_DRM_FORMAT_KUNIT_TEST) += test-drm_format.o
 obj-$(CONFIG_DRM_PLANE_HELPER_KUNIT_TEST) += test-drm_plane_helper.o
+obj-$(CONFIG_DRM_DP_MST_HELPER_KUNIT_TEST) += test-drm_dp_mst_helper.o
diff --git a/drivers/gpu/drm/selftests/test-drm_dp_mst_helper.c 
b/drivers/gpu/drm/tests/test-drm_dp_mst_helper.c
similarity index 73%
rename from drivers/gpu/drm/selftests/test-drm_dp_mst_helper.c
rename to drivers/gpu/drm/tests/test-drm_dp_mst_helper.c
index 967c52150b67..88120e878a15 100644
--- a/drivers/gpu/drm/selftests/test-drm_dp_mst_helper.c
+++ b/drivers/gpu/drm/tests/test-drm_dp_mst_helper.c
@@ -5,15 +5,15 @@
 
 #define PREFIX_STR "[drm_dp_mst_helper]"
 
+#include 
 #include 
 
 #include 
 #include 
 
 #include "../display/drm_dp_mst_topology_internal.h"
-#include "test-drm_modeset_common.h"
 
-int igt_dp_mst_calc_pbn_mode(void *ignored)
+static void igt_dp_mst_calc_pbn_mode(struct kunit *test)
 {
int pbn, i;
const struct {
@@ -33,13 +33,11 @@ int igt_dp_mst_calc_pbn_mode(void *ignored)
pbn = drm_dp_calc_pbn_mode(test_params[i].rate,
   test_params[i].bpp,
   test_params[i].dsc);
-   FAIL(pbn != test_params[i].expected,
+   KUNIT_EXPECT_EQ_MSG(test, pbn, test_params[i].expected,
 "Expected PBN %d for clock %d bpp %d, got %d\n",
  

[PATCH 08/10] drm: selftest: convert drm_framebuffer selftest to KUnit

2022-06-15 Thread Maíra Canal
Considering the current adoption of the KUnit framework, convert the
DRM framebuffer selftest to the KUnit API.

Signed-off-by: Maíra Canal 
---
 drivers/gpu/drm/selftests/Makefile|  5 +--
 .../gpu/drm/selftests/drm_modeset_selftests.h |  9 --
 .../drm/selftests/test-drm_modeset_common.c   | 32 ---
 .../drm/selftests/test-drm_modeset_common.h   | 21 
 drivers/gpu/drm/tests/Kconfig | 12 +++
 drivers/gpu/drm/tests/Makefile|  1 +
 .../test-drm_framebuffer.c| 25 ++-
 7 files changed, 31 insertions(+), 74 deletions(-)
 delete mode 100644 drivers/gpu/drm/selftests/drm_modeset_selftests.h
 delete mode 100644 drivers/gpu/drm/selftests/test-drm_modeset_common.c
 delete mode 100644 drivers/gpu/drm/selftests/test-drm_modeset_common.h
 rename drivers/gpu/drm/{selftests => tests}/test-drm_framebuffer.c (96%)

diff --git a/drivers/gpu/drm/selftests/Makefile 
b/drivers/gpu/drm/selftests/Makefile
index 1539f55db9a7..f7db628b60cb 100644
--- a/drivers/gpu/drm/selftests/Makefile
+++ b/drivers/gpu/drm/selftests/Makefile
@@ -1,5 +1,2 @@
 # SPDX-License-Identifier: GPL-2.0-only
-test-drm_modeset-y := test-drm_modeset_common.o test-drm_framebuffer.o
-
-obj-$(CONFIG_DRM_DEBUG_SELFTEST) += test-drm_mm.o test-drm_modeset.o \
-   test-drm_buddy.o
+obj-$(CONFIG_DRM_DEBUG_SELFTEST) += test-drm_mm.o test-drm_buddy.o
diff --git a/drivers/gpu/drm/selftests/drm_modeset_selftests.h 
b/drivers/gpu/drm/selftests/drm_modeset_selftests.h
deleted file mode 100644
index 40a29b8cf386..
--- a/drivers/gpu/drm/selftests/drm_modeset_selftests.h
+++ /dev/null
@@ -1,9 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0 */
-/* List each unit test as selftest(name, function)
- *
- * The name is used as both an enum and expanded as igt__name to create
- * a module parameter. It must be unique and legal for a C identifier.
- *
- * Tests are executed in order by igt/drm_selftests_helper
- */
-selftest(check_drm_framebuffer_create, igt_check_drm_framebuffer_create)
diff --git a/drivers/gpu/drm/selftests/test-drm_modeset_common.c 
b/drivers/gpu/drm/selftests/test-drm_modeset_common.c
deleted file mode 100644
index 2a7f93774006..
--- a/drivers/gpu/drm/selftests/test-drm_modeset_common.c
+++ /dev/null
@@ -1,32 +0,0 @@
-// SPDX-License-Identifier: GPL-2.0
-/*
- * Common file for modeset selftests.
- */
-
-#include 
-
-#include "test-drm_modeset_common.h"
-
-#define TESTS "drm_modeset_selftests.h"
-#include "drm_selftest.h"
-
-#include "drm_selftest.c"
-
-static int __init test_drm_modeset_init(void)
-{
-   int err;
-
-   err = run_selftests(selftests, ARRAY_SIZE(selftests), NULL);
-
-   return err > 0 ? 0 : err;
-}
-
-static void __exit test_drm_modeset_exit(void)
-{
-}
-
-module_init(test_drm_modeset_init);
-module_exit(test_drm_modeset_exit);
-
-MODULE_AUTHOR("Intel Corporation");
-MODULE_LICENSE("GPL");
diff --git a/drivers/gpu/drm/selftests/test-drm_modeset_common.h 
b/drivers/gpu/drm/selftests/test-drm_modeset_common.h
deleted file mode 100644
index 3feb2fea1a6b..
--- a/drivers/gpu/drm/selftests/test-drm_modeset_common.h
+++ /dev/null
@@ -1,21 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0 */
-
-#ifndef __TEST_DRM_MODESET_COMMON_H__
-#define __TEST_DRM_MODESET_COMMON_H__
-
-#include 
-#include 
-
-#define FAIL(test, msg, ...) \
-   do { \
-   if (test) { \
-   pr_err("%s/%u: " msg, __FUNCTION__, __LINE__, 
##__VA_ARGS__); \
-   return -EINVAL; \
-   } \
-   } while (0)
-
-#define FAIL_ON(x) FAIL((x), "%s", "FAIL_ON(" __stringify(x) ")\n")
-
-int igt_check_drm_framebuffer_create(void *ignored);
-
-#endif
diff --git a/drivers/gpu/drm/tests/Kconfig b/drivers/gpu/drm/tests/Kconfig
index eea0783f981d..de44385f217e 100644
--- a/drivers/gpu/drm/tests/Kconfig
+++ b/drivers/gpu/drm/tests/Kconfig
@@ -86,4 +86,16 @@ config DRM_DP_MST_HELPER_KUNIT_TEST
 
If in doubt, say "N".
 
+config DRM_FRAMEBUFFER_KUNIT_TEST
+   tristate "KUnit tests for DRM framebuffer" if !DRM_KUNIT_TEST
+   select DRM_KMS_HELPER
+   default y if DRM_KUNIT_TEST
+   help
+   This option provides KUnit modules that can be used to run
+   various selftests on parts of the DRM framebuffer API.  This
+   option is not useful for distributions or general kernels, but 
only
+   for kernel developers working on DRM and associated drivers.
+
+   If in doubt, say "N".
+
 endmenu
diff --git a/drivers/gpu/drm/tests/Makefile b/drivers/gpu/drm/tests/Makefile
index 735ca8e4c446..d802ca0f1544 100644
--- a/drivers/gpu/drm/tests/Makefile
+++ b/drivers/gpu/drm/tests/Makefile
@@ -5,3 +5,4 @@ obj-$(CONFIG_DRM_RECT_KUNIT_TEST) += test-drm_rect.o
 obj-$(CONFIG_DRM_FORMAT_KUNIT_TEST) += test-drm_format.o
 obj-$(CONFIG_DRM_PLANE_HELPER_KUNIT_TEST) += test-drm_plane_helper.o
 obj-$

[PATCH 09/10] drm: selftest: convert drm_buddy selftest to KUnit

2022-06-15 Thread Maíra Canal
Considering the current adoption of the KUnit framework, convert the
DRM buddy selftest to the KUnit API.

Signed-off-by: Maíra Canal 
---
 drivers/gpu/drm/selftests/Makefile|   2 +-
 .../gpu/drm/selftests/drm_buddy_selftests.h   |  15 -
 drivers/gpu/drm/selftests/test-drm_buddy.c| 994 --
 drivers/gpu/drm/tests/Kconfig |  15 +
 drivers/gpu/drm/tests/Makefile|   1 +
 drivers/gpu/drm/tests/test-drm_buddy.c| 748 +
 6 files changed, 765 insertions(+), 1010 deletions(-)
 delete mode 100644 drivers/gpu/drm/selftests/drm_buddy_selftests.h
 delete mode 100644 drivers/gpu/drm/selftests/test-drm_buddy.c
 create mode 100644 drivers/gpu/drm/tests/test-drm_buddy.c

diff --git a/drivers/gpu/drm/selftests/Makefile 
b/drivers/gpu/drm/selftests/Makefile
index f7db628b60cb..a4ebecb8146b 100644
--- a/drivers/gpu/drm/selftests/Makefile
+++ b/drivers/gpu/drm/selftests/Makefile
@@ -1,2 +1,2 @@
 # SPDX-License-Identifier: GPL-2.0-only
-obj-$(CONFIG_DRM_DEBUG_SELFTEST) += test-drm_mm.o test-drm_buddy.o
+obj-$(CONFIG_DRM_DEBUG_SELFTEST) += test-drm_mm.o
diff --git a/drivers/gpu/drm/selftests/drm_buddy_selftests.h 
b/drivers/gpu/drm/selftests/drm_buddy_selftests.h
deleted file mode 100644
index 455b756c4ae5..
--- a/drivers/gpu/drm/selftests/drm_buddy_selftests.h
+++ /dev/null
@@ -1,15 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0 */
-/* List each unit test as selftest(name, function)
- *
- * The name is used as both an enum and expanded as igt__name to create
- * a module parameter. It must be unique and legal for a C identifier.
- *
- * Tests are executed in order by igt/drm_buddy
- */
-selftest(sanitycheck, igt_sanitycheck) /* keep first (selfcheck for igt) */
-selftest(buddy_alloc_limit, igt_buddy_alloc_limit)
-selftest(buddy_alloc_range, igt_buddy_alloc_range)
-selftest(buddy_alloc_optimistic, igt_buddy_alloc_optimistic)
-selftest(buddy_alloc_pessimistic, igt_buddy_alloc_pessimistic)
-selftest(buddy_alloc_smoke, igt_buddy_alloc_smoke)
-selftest(buddy_alloc_pathological, igt_buddy_alloc_pathological)
diff --git a/drivers/gpu/drm/selftests/test-drm_buddy.c 
b/drivers/gpu/drm/selftests/test-drm_buddy.c
deleted file mode 100644
index aca0c491040f..
--- a/drivers/gpu/drm/selftests/test-drm_buddy.c
+++ /dev/null
@@ -1,994 +0,0 @@
-// SPDX-License-Identifier: MIT
-/*
- * Copyright © 2019 Intel Corporation
- */
-
-#define pr_fmt(fmt) "drm_buddy: " fmt
-
-#include 
-#include 
-#include 
-
-#include 
-
-#include "../lib/drm_random.h"
-
-#define TESTS "drm_buddy_selftests.h"
-#include "drm_selftest.h"
-
-#define IGT_TIMEOUT(name__) \
-   unsigned long name__ = jiffies + MAX_SCHEDULE_TIMEOUT
-
-static unsigned int random_seed;
-
-static inline u64 get_size(int order, u64 chunk_size)
-{
-   return (1 << order) * chunk_size;
-}
-
-__printf(2, 3)
-static bool __igt_timeout(unsigned long timeout, const char *fmt, ...)
-{
-   va_list va;
-
-   if (!signal_pending(current)) {
-   cond_resched();
-   if (time_before(jiffies, timeout))
-   return false;
-   }
-
-   if (fmt) {
-   va_start(va, fmt);
-   vprintk(fmt, va);
-   va_end(va);
-   }
-
-   return true;
-}
-
-static inline const char *yesno(bool v)
-{
-   return v ? "yes" : "no";
-}
-
-static void __igt_dump_block(struct drm_buddy *mm,
-struct drm_buddy_block *block,
-bool buddy)
-{
-   pr_err("block info: header=%llx, state=%u, order=%d, offset=%llx 
size=%llx root=%s buddy=%s\n",
-  block->header,
-  drm_buddy_block_state(block),
-  drm_buddy_block_order(block),
-  drm_buddy_block_offset(block),
-  drm_buddy_block_size(mm, block),
-  yesno(!block->parent),
-  yesno(buddy));
-}
-
-static void igt_dump_block(struct drm_buddy *mm,
-  struct drm_buddy_block *block)
-{
-   struct drm_buddy_block *buddy;
-
-   __igt_dump_block(mm, block, false);
-
-   buddy = drm_get_buddy(block);
-   if (buddy)
-   __igt_dump_block(mm, buddy, true);
-}
-
-static int igt_check_block(struct drm_buddy *mm,
-  struct drm_buddy_block *block)
-{
-   struct drm_buddy_block *buddy;
-   unsigned int block_state;
-   u64 block_size;
-   u64 offset;
-   int err = 0;
-
-   block_state = drm_buddy_block_state(block);
-
-   if (block_state != DRM_BUDDY_ALLOCATED &&
-   block_state != DRM_BUDDY_FREE &&
-   block_state != DRM_BUDDY_SPLIT) {
-   pr_err("block state mismatch\n");
-   err = -EINVAL;
-   }
-
-   block_size = drm_buddy_block_size(mm, block);
-   offset = drm_buddy_block_offset(block);
-
-   if (block_size < mm->chunk_size) {
-   pr_err("block size smaller than min size\n");
-  

[PATCH 02/10] drm: selftest: refactor drm_cmdline_parser

2022-06-15 Thread Maíra Canal
From: Arthur Grillo 

Refactor the tests by modularizing the functions to avoid code repetition.

Co-developed-by: Maíra Canal 
Signed-off-by: Arthur Grillo 
Signed-off-by: Maíra Canal 
---
 .../drm/selftests/test-drm_cmdline_parser.c   | 579 +-
 1 file changed, 156 insertions(+), 423 deletions(-)

diff --git a/drivers/gpu/drm/selftests/test-drm_cmdline_parser.c 
b/drivers/gpu/drm/selftests/test-drm_cmdline_parser.c
index d96cd890def6..57a229c5fc35 100644
--- a/drivers/gpu/drm/selftests/test-drm_cmdline_parser.c
+++ b/drivers/gpu/drm/selftests/test-drm_cmdline_parser.c
@@ -1,6 +1,8 @@
 // SPDX-License-Identifier: GPL-2.0
 /*
  * Copyright (c) 2019 Bootlin
+ * Copyright (c) 2021 Ma�ra Canal ,
+ * Copyright (c) 2021 Arthur Grillo 
  */
 
 #define pr_fmt(fmt) "drm_cmdline: " fmt
@@ -17,13 +19,25 @@
 
 static const struct drm_connector no_connector = {};
 
-static int drm_cmdline_test_force_e_only(void *ignored)
+static int drm_cmdline_test_properties(void *ignored,
+   struct drm_cmdline_mode *mode, enum drm_connector_force force)
+{
+   FAIL_ON(mode->rb);
+   FAIL_ON(mode->cvt);
+   FAIL_ON(mode->interlace);
+   FAIL_ON(mode->margins);
+   FAIL_ON(mode->force != force);
+
+   return 0;
+}
+
+static int drm_cmdline_test_force_only(void *ignored, char *cmdline,
+   const struct drm_connector *connector, enum drm_connector_force 
force)
 {
struct drm_cmdline_mode mode = { };
 
-   FAIL_ON(!drm_mode_parse_command_line_for_connector("e",
-  &no_connector,
-  &mode));
+   FAIL_ON(!drm_mode_parse_command_line_for_connector(cmdline,
+  connector, &mode));
FAIL_ON(mode.specified);
FAIL_ON(mode.refresh_specified);
FAIL_ON(mode.bpp_specified);
@@ -32,95 +46,101 @@ static int drm_cmdline_test_force_e_only(void *ignored)
FAIL_ON(mode.cvt);
FAIL_ON(mode.interlace);
FAIL_ON(mode.margins);
-   FAIL_ON(mode.force != DRM_FORCE_ON);
+   FAIL_ON(mode.force != force);
 
return 0;
 }
 
-static int drm_cmdline_test_force_D_only_not_digital(void *ignored)
+static int drm_cmdline_test_freestanding(void *ignored,
+   struct drm_cmdline_mode *mode, char *cmdline,
+   const struct drm_connector *connector)
 {
-   struct drm_cmdline_mode mode = { };
+   FAIL_ON(!drm_mode_parse_command_line_for_connector(cmdline,
+  connector, mode));
+   FAIL_ON(mode->specified);
+   FAIL_ON(mode->refresh_specified);
+   FAIL_ON(mode->bpp_specified);
 
-   FAIL_ON(!drm_mode_parse_command_line_for_connector("D",
-  &no_connector,
-  &mode));
-   FAIL_ON(mode.specified);
-   FAIL_ON(mode.refresh_specified);
-   FAIL_ON(mode.bpp_specified);
+   FAIL_ON(mode->tv_margins.right != 14);
+   FAIL_ON(mode->tv_margins.left != 24);
+   FAIL_ON(mode->tv_margins.bottom != 36);
+   FAIL_ON(mode->tv_margins.top != 42);
 
-   FAIL_ON(mode.rb);
-   FAIL_ON(mode.cvt);
-   FAIL_ON(mode.interlace);
-   FAIL_ON(mode.margins);
-   FAIL_ON(mode.force != DRM_FORCE_ON);
+   return 0;
+}
+
+static int drm_cmdline_test_res_init(void *ignored,
+   struct drm_cmdline_mode *mode, char *cmdline)
+{
+   FAIL_ON(!drm_mode_parse_command_line_for_connector(cmdline,
+  &no_connector, 
mode));
+   FAIL_ON(!mode->specified);
+   FAIL_ON(mode->xres != 720);
+   FAIL_ON(mode->yres != 480);
+
+   return 0;
+}
+
+static int drm_cmdline_test_res_bpp_init(void *ignored,
+   struct drm_cmdline_mode *mode, char *cmdline)
+{
+   FAIL_ON(!drm_mode_parse_command_line_for_connector(cmdline,
+  &no_connector, 
mode));
+   FAIL_ON(!mode->specified);
+   FAIL_ON(mode->xres != 720);
+   FAIL_ON(mode->yres != 480);
+
+   FAIL_ON(!mode->refresh_specified);
+   FAIL_ON(mode->refresh != 60);
+   FAIL_ON(!mode->bpp_specified);
+   FAIL_ON(mode->bpp != 24);
+
+   return 0;
+}
+
+static int drm_cmdline_test_force_e_only(void *ignored)
+{
+   drm_cmdline_test_force_only(ignored, "e", &no_connector, DRM_FORCE_ON);
+
+   return 0;
+}
+
+static int drm_cmdline_test_force_D_only_not_digital(void *ignored)
+{
+   drm_cmdline_test_force_only(ignored, "D", &no_connector, DRM_FORCE_ON);
 
return 0;
 }
 
 static const struct drm_connector connector_hdmi = {
.connector_type = DRM_MODE_CONNECTOR_HDMIB,
+
 };
 
 static int drm_cmdline_test_force_D_only_hdmi(void *ignored)
 {
-   struct drm_cmdline_mode mode = { };
-
-   FAIL_ON(!drm_

Please add another drm/msm tree to the linux-next

2022-06-15 Thread Dmitry Baryshkov

Hi Stephen,

I would appreciate if you could add

https://gitlab.freedesktop.org/lumag/msm.git msm-next-lumag

to the linux-next tree.

This tree is a part of drm/msm maintenance structure. As a co-maintainer 
I collect and test display patches, while Rob concenctrates on GPU part 
of the driver. Later during the release cycle these patchesare pulled by 
Rob Clark directly into msm-next.


During last cycle Rob suggested adding this tree to the linux-next 
effort, so that the patches receive better integration testing during 
the Linux development cycle.


Thanks!

--
With best wishes
Dmitry


[PATCH 10/10] drm: selftest: convert drm_mm selftest to KUnit

2022-06-15 Thread Maíra Canal
From: Arthur Grillo 

Considering the current adoption of the KUnit framework, convert the
DRM mm selftest to the KUnit API.

Signed-off-by: Arthur Grillo 
Signed-off-by: Maíra Canal 
---
 drivers/gpu/drm/Kconfig   |   20 -
 drivers/gpu/drm/Makefile  |1 -
 drivers/gpu/drm/selftests/Makefile|2 -
 drivers/gpu/drm/selftests/drm_mm_selftests.h  |   28 -
 drivers/gpu/drm/selftests/drm_selftest.c  |  109 --
 drivers/gpu/drm/selftests/drm_selftest.h  |   41 -
 drivers/gpu/drm/tests/Kconfig |   14 +
 drivers/gpu/drm/tests/Makefile|1 +
 .../drm/{selftests => tests}/test-drm_mm.c| 1135 +++--
 9 files changed, 465 insertions(+), 886 deletions(-)
 delete mode 100644 drivers/gpu/drm/selftests/Makefile
 delete mode 100644 drivers/gpu/drm/selftests/drm_mm_selftests.h
 delete mode 100644 drivers/gpu/drm/selftests/drm_selftest.c
 delete mode 100644 drivers/gpu/drm/selftests/drm_selftest.h
 rename drivers/gpu/drm/{selftests => tests}/test-drm_mm.c (58%)

diff --git a/drivers/gpu/drm/Kconfig b/drivers/gpu/drm/Kconfig
index bd1b5d82c9cf..f1330d091a6e 100644
--- a/drivers/gpu/drm/Kconfig
+++ b/drivers/gpu/drm/Kconfig
@@ -50,26 +50,6 @@ config DRM_DEBUG_MM
 
  If in doubt, say "N".
 
-config DRM_DEBUG_SELFTEST
-   tristate "kselftests for DRM"
-   depends on DRM
-   depends on DEBUG_KERNEL
-   select PRIME_NUMBERS
-   select DRM_DISPLAY_DP_HELPER
-   select DRM_DISPLAY_HELPER
-   select DRM_LIB_RANDOM
-   select DRM_KMS_HELPER
-   select DRM_BUDDY
-   select DRM_EXPORT_FOR_TESTS if m
-   default n
-   help
- This option provides kernel modules that can be used to run
- various selftests on parts of the DRM api. This option is not
- useful for distributions or general kernels, but only for kernel
- developers working on DRM and associated drivers.
-
- If in doubt, say "N".
-
 source "drivers/gpu/drm/tests/Kconfig"
 
 config DRM_KMS_HELPER
diff --git a/drivers/gpu/drm/Makefile b/drivers/gpu/drm/Makefile
index 0f24aa542be0..8322a740146f 100644
--- a/drivers/gpu/drm/Makefile
+++ b/drivers/gpu/drm/Makefile
@@ -75,7 +75,6 @@ obj-$(CONFIG_DRM_KMS_HELPER) += drm_kms_helper.o
 # Drivers and the rest
 #
 
-obj-$(CONFIG_DRM_DEBUG_SELFTEST) += selftests/
 obj-y += tests/
 
 obj-$(CONFIG_DRM_MIPI_DBI) += drm_mipi_dbi.o
diff --git a/drivers/gpu/drm/selftests/Makefile 
b/drivers/gpu/drm/selftests/Makefile
deleted file mode 100644
index a4ebecb8146b..
--- a/drivers/gpu/drm/selftests/Makefile
+++ /dev/null
@@ -1,2 +0,0 @@
-# SPDX-License-Identifier: GPL-2.0-only
-obj-$(CONFIG_DRM_DEBUG_SELFTEST) += test-drm_mm.o
diff --git a/drivers/gpu/drm/selftests/drm_mm_selftests.h 
b/drivers/gpu/drm/selftests/drm_mm_selftests.h
deleted file mode 100644
index 8c87c964176b..
--- a/drivers/gpu/drm/selftests/drm_mm_selftests.h
+++ /dev/null
@@ -1,28 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0 */
-/* List each unit test as selftest(name, function)
- *
- * The name is used as both an enum and expanded as igt__name to create
- * a module parameter. It must be unique and legal for a C identifier.
- *
- * Tests are executed in order by igt/drm_mm
- */
-selftest(sanitycheck, igt_sanitycheck) /* keep first (selfcheck for igt) */
-selftest(init, igt_init)
-selftest(debug, igt_debug)
-selftest(reserve, igt_reserve)
-selftest(insert, igt_insert)
-selftest(replace, igt_replace)
-selftest(insert_range, igt_insert_range)
-selftest(align, igt_align)
-selftest(frag, igt_frag)
-selftest(align32, igt_align32)
-selftest(align64, igt_align64)
-selftest(evict, igt_evict)
-selftest(evict_range, igt_evict_range)
-selftest(bottomup, igt_bottomup)
-selftest(lowest, igt_lowest)
-selftest(topdown, igt_topdown)
-selftest(highest, igt_highest)
-selftest(color, igt_color)
-selftest(color_evict, igt_color_evict)
-selftest(color_evict_range, igt_color_evict_range)
diff --git a/drivers/gpu/drm/selftests/drm_selftest.c 
b/drivers/gpu/drm/selftests/drm_selftest.c
deleted file mode 100644
index e29ed9faef5b..
--- a/drivers/gpu/drm/selftests/drm_selftest.c
+++ /dev/null
@@ -1,109 +0,0 @@
-/*
- * Copyright © 2016 Intel Corporation
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, 

Re: [PATCH] drm/i915/pvc: Add recommended MMIO setting

2022-06-15 Thread Souza, Jose
On Mon, 2022-06-13 at 09:53 -0700, Matt Roper wrote:
> As with past platforms, the bspec's performance tuning guide provides
> recommended MMIO settings.  Although not technically "workarounds" we
> apply these through the workaround framework to ensure that they're
> re-applied at the proper times (e.g., on engine resets) and that any
> conflicts with real workarounds are flagged.

Reviewed-by: José Roberto de Souza 

> 
> Bspec: 72161
> Signed-off-by: Matt Roper 
> ---
>  drivers/gpu/drm/i915/gt/intel_gt_regs.h | 5 +
>  drivers/gpu/drm/i915/gt/intel_workarounds.c | 9 +
>  2 files changed, 14 insertions(+)
> 
> diff --git a/drivers/gpu/drm/i915/gt/intel_gt_regs.h 
> b/drivers/gpu/drm/i915/gt/intel_gt_regs.h
> index 226557018037..07ef111947b8 100644
> --- a/drivers/gpu/drm/i915/gt/intel_gt_regs.h
> +++ b/drivers/gpu/drm/i915/gt/intel_gt_regs.h
> @@ -981,6 +981,11 @@
>  #define XEHP_L3SCQREG7   _MMIO(0xb188)
>  #define   BLEND_FILL_CACHING_OPT_DIS REG_BIT(3)
>  
> +#define XEHPC_L3SCRUB_MMIO(0xb18c)
> +#define   SCRUB_CL_DWNGRADE_SHARED   REG_BIT(12)
> +#define   SCRUB_RATE_PER_BANK_MASK   REG_GENMASK(2, 0)
> +#define   SCRUB_RATE_4B_PER_CLK  
> REG_FIELD_PREP(SCRUB_RATE_PER_BANK_MASK, 0x6)
> +
>  #define L3SQCREG1_CCS0   _MMIO(0xb200)
>  #define   FLUSHALLNONCOH REG_BIT(5)
>  
> diff --git a/drivers/gpu/drm/i915/gt/intel_workarounds.c 
> b/drivers/gpu/drm/i915/gt/intel_workarounds.c
> index 1e982ac931dc..c4af51144216 100644
> --- a/drivers/gpu/drm/i915/gt/intel_workarounds.c
> +++ b/drivers/gpu/drm/i915/gt/intel_workarounds.c
> @@ -2679,6 +2679,15 @@ general_render_compute_wa_init(struct intel_engine_cs 
> *engine, struct i915_wa_li
>  {
>   struct drm_i915_private *i915 = engine->i915;
>  
> + if (IS_PONTEVECCHIO(i915)) {
> + /*
> +  * The following is not actually a "workaround" but rather
> +  * a recommended tuning setting documented in the bspec's
> +  * performance guide section.
> +  */
> + wa_write(wal, XEHPC_L3SCRUB, SCRUB_CL_DWNGRADE_SHARED | 
> SCRUB_RATE_4B_PER_CLK);
> + }
> +
>   if (IS_XEHPSDV(i915)) {
>   /* Wa_1409954639 */
>   wa_masked_en(wal,



Re: [PATCH] drm/msm/gem: Drop early returns in close/purge vma

2022-06-15 Thread Rob Clark
On Sat, Jun 11, 2022 at 11:16 AM Steev Klimaszewski  wrote:
>
> Hi Rob,
>
> On 6/10/22 12:20 PM, Rob Clark wrote:
> > From: Rob Clark 
> >
> > Keep the warn, but drop the early return.  If we do manage to hit this
> > sort of issue, skipping the cleanup just makes things worse (dangling
> > drm_mm_nodes when the msm_gem_vma is freed, etc).  Whereas the worst
> > that happens if we tear down a mapping the GPU is accessing is that we
> > get GPU iova faults, but otherwise the world keeps spinning.
> >

forgot this initially:

Reported-by: Steev Klimaszewski 

> > Signed-off-by: Rob Clark 
> > ---
> >   drivers/gpu/drm/msm/msm_gem_vma.c | 6 ++
> >   1 file changed, 2 insertions(+), 4 deletions(-)
> >
> > diff --git a/drivers/gpu/drm/msm/msm_gem_vma.c 
> > b/drivers/gpu/drm/msm/msm_gem_vma.c
> > index 3c1dc9241831..c471aebcdbab 100644
> > --- a/drivers/gpu/drm/msm/msm_gem_vma.c
> > +++ b/drivers/gpu/drm/msm/msm_gem_vma.c
> > @@ -62,8 +62,7 @@ void msm_gem_purge_vma(struct msm_gem_address_space 
> > *aspace,
> >   unsigned size = vma->node.size;
> >
> >   /* Print a message if we try to purge a vma in use */
> > - if (GEM_WARN_ON(msm_gem_vma_inuse(vma)))
> > - return;
> > + GEM_WARN_ON(msm_gem_vma_inuse(vma));
> >
> >   /* Don't do anything if the memory isn't mapped */
> >   if (!vma->mapped)
> > @@ -128,8 +127,7 @@ msm_gem_map_vma(struct msm_gem_address_space *aspace,
> >   void msm_gem_close_vma(struct msm_gem_address_space *aspace,
> >   struct msm_gem_vma *vma)
> >   {
> > - if (GEM_WARN_ON(msm_gem_vma_inuse(vma) || vma->mapped))
> > - return;
> > + GEM_WARN_ON(msm_gem_vma_inuse(vma) || vma->mapped);
> >
> >   spin_lock(&aspace->lock);
> >   if (vma->iova)
>
> I've seen the splat on the Lenovo Yoga C630 here, and have tested this
> patch, and as described, the splat still happens, but the system is
> still able to be used.
>
> Tested-by: Steev Klimaszewski 
>


[PATCH 1/2] drm/msm: Drop update_fences()

2022-06-15 Thread Rob Clark
From: Rob Clark 

I noticed while looking at some traces, that we could miss calls to
msm_update_fence(), as the irq could have raced with retire_submits()
which could have already popped the last submit on a ring out of the
queue of in-flight submits.  But walking the list of submits in the
irq handler isn't really needed, as dma_fence_is_signaled() will dtrt.
So lets just drop it entirely.

Reported-by: Steev Klimaszewski 
Fixes: 95d1deb02a9c ("drm/msm/gem: Add fenced vma unpin")
Signed-off-by: Rob Clark 
---
 drivers/gpu/drm/msm/msm_gpu.c | 22 ++
 1 file changed, 2 insertions(+), 20 deletions(-)

diff --git a/drivers/gpu/drm/msm/msm_gpu.c b/drivers/gpu/drm/msm/msm_gpu.c
index e59a757578df..b61078f0cd0f 100644
--- a/drivers/gpu/drm/msm/msm_gpu.c
+++ b/drivers/gpu/drm/msm/msm_gpu.c
@@ -176,24 +176,6 @@ int msm_gpu_hw_init(struct msm_gpu *gpu)
return ret;
 }
 
-static void update_fences(struct msm_gpu *gpu, struct msm_ringbuffer *ring,
-   uint32_t fence)
-{
-   struct msm_gem_submit *submit;
-   unsigned long flags;
-
-   spin_lock_irqsave(&ring->submit_lock, flags);
-   list_for_each_entry(submit, &ring->submits, node) {
-   if (fence_after(submit->seqno, fence))
-   break;
-
-   msm_update_fence(submit->ring->fctx,
-   submit->hw_fence->seqno);
-   dma_fence_signal(submit->hw_fence);
-   }
-   spin_unlock_irqrestore(&ring->submit_lock, flags);
-}
-
 #ifdef CONFIG_DEV_COREDUMP
 static ssize_t msm_gpu_devcoredump_read(char *buffer, loff_t offset,
size_t count, void *data, size_t datalen)
@@ -450,7 +432,7 @@ static void recover_worker(struct kthread_work *work)
if (ring == cur_ring)
fence++;
 
-   update_fences(gpu, ring, fence);
+   msm_update_fence(ring->fctx, fence);
}
 
if (msm_gpu_active(gpu)) {
@@ -753,7 +735,7 @@ void msm_gpu_retire(struct msm_gpu *gpu)
int i;
 
for (i = 0; i < gpu->nr_rings; i++)
-   update_fences(gpu, gpu->rb[i], gpu->rb[i]->memptrs->fence);
+   msm_update_fence(gpu->rb[i]->fctx, gpu->rb[i]->memptrs->fence);
 
kthread_queue_work(gpu->worker, &gpu->retire_work);
update_sw_cntrs(gpu);
-- 
2.36.1



[PATCH 2/2] drm/msm: Don't overwrite hw fence in hw_init

2022-06-15 Thread Rob Clark
From: Rob Clark 

Prior to the last commit, this could result in setting the GPU
written fence value back to an older value, if we had missed
updating completed_fence prior to suspend.  This was mostly
harmless as the GPU would eventually overwrite it again with
the correct value.  But we should just not do this.  Instead
just leave a sanity check that the fence looks plausible (in
case the GPU scribbled on memory).

Reported-by: Steev Klimaszewski 
Fixes: 95d1deb02a9c ("drm/msm/gem: Add fenced vma unpin")
Signed-off-by: Rob Clark 
---
 drivers/gpu/drm/msm/adreno/adreno_gpu.c | 11 ---
 drivers/gpu/drm/msm/msm_gpu.c   |  2 +-
 2 files changed, 9 insertions(+), 4 deletions(-)

diff --git a/drivers/gpu/drm/msm/adreno/adreno_gpu.c 
b/drivers/gpu/drm/msm/adreno/adreno_gpu.c
index e1aef4875e2f..dd044d557c7c 100644
--- a/drivers/gpu/drm/msm/adreno/adreno_gpu.c
+++ b/drivers/gpu/drm/msm/adreno/adreno_gpu.c
@@ -498,10 +498,15 @@ int adreno_hw_init(struct msm_gpu *gpu)
 
ring->cur = ring->start;
ring->next = ring->start;
-
-   /* reset completed fence seqno: */
-   ring->memptrs->fence = ring->fctx->completed_fence;
ring->memptrs->rptr = 0;
+
+   /* Detect and clean up an impossible fence, ie. if GPU managed
+* to scribble something invalid, we don't want that to confuse
+* us into mistakingly believing that submits have completed.
+*/
+   if (fence_before(ring->fctx->last_fence, ring->memptrs->fence)) 
{
+   ring->memptrs->fence = ring->fctx->last_fence;
+   }
}
 
return 0;
diff --git a/drivers/gpu/drm/msm/msm_gpu.c b/drivers/gpu/drm/msm/msm_gpu.c
index b61078f0cd0f..8c00f9187c03 100644
--- a/drivers/gpu/drm/msm/msm_gpu.c
+++ b/drivers/gpu/drm/msm/msm_gpu.c
@@ -430,7 +430,7 @@ static void recover_worker(struct kthread_work *work)
 * one more to clear the faulting submit
 */
if (ring == cur_ring)
-   fence++;
+   ring->memptrs->fence = ++fence;
 
msm_update_fence(ring->fctx, fence);
}
-- 
2.36.1



DRM FB interface does not sanitize len when mmap'ed

2022-06-15 Thread Nuno Gonçalves
I am crashing the kernel by doing something I believe I am allowed to do.

Using mmap to write to /dev/fb0 as the compatibility layer for Tiny
DRM vot,v220hf01a-t (ili9225).

First it happens that because of the display resolution of 220*176 the
buffer is (16 bit) 77440 bytes, which is not a multiple of the page
size (4096), unlike most regular resolution displays.

When I touch the mmap'ed virtual address above base+73728 (4096*18) up to 77439:

auto file = open("/dev/fb0", O_RDWR);
if (!file) throw;
auto fbp = (char *)mmap(0, 220 * 176 * 2, PROT_READ | PROT_WRITE,
MAP_SHARED, file, 0);
if ((size_t)fbp <= 0) throw;
fbp[220 * 176 * 2 - 2] = 0;

I get a crash:

[   14.150463] Unable to handle kernel paging request at virtual
address ffc00827c000
[   14.158640] Mem abort info:
[   14.161626]   ESR = 0x9607
[   14.164969]   EC = 0x25: DABT (current EL), IL = 32 bits
[   14.170470]   SET = 0, FnV = 0
[   14.173735]   EA = 0, S1PTW = 0
[   14.177047]   FSC = 0x07: level 3 translation fault
[   14.182095] Data abort info:
[   14.185083]   ISV = 0, ISS = 0x0007
[   14.189035]   CM = 0, WnR = 0
[   14.192107] swapper pgtable: 4k pages, 39-bit VAs, pgdp=00d54000
[   14.198997] [ffc00827c000] pgd=11501003,
p4d=11501003, pud=11501003, pmd=11d5c003,
pte=
[   14.211992] Internal error: Oops: 9607 [#1] PREEMPT SMP
[   14.217659] CPU: 0 PID: 50 Comm: kworker/0:2 Not tainted 5.18.3 #18
[   14.224027] Hardware name: Raspberry Pi Compute Module 3 Plus Rev 1.0 (DT)
[   14.231005] Workqueue: events drm_fb_helper_damage_work
[   14.236333] pstate: 2005 (nzCv daif -PAN -UAO -TCO -DIT -SSBS BTYPE=--)
[   14.243405] pc : __memcpy+0x15c/0x230
[   14.247131] lr : drm_fb_helper_damage_work+0x25c/0x310
[   14.252352] sp : ffc00822bd30
[   14.255712] x29: ffc00822bd30 x28: 01b8 x27: ff80017e1d10
[   14.262970] x26: ffc008267e80 x25: 00b0 x24: ff8002416800
[   14.270228] x23: ff8001fd8080 x22: ff80017e1c00 x21: ff80017e1ccc
[   14.277487] x20: ffc00827be80 x19: ff80017e1cd0 x18: ffe5d80bac08
[   14.284745] x17: 0013 x16: 00fe72080e00 x15: 
[   14.292003] x14:  x13:  x12: 
[   14.299259] x11:  x10:  x9 : 
[   14.306517] x8 :  x7 :  x6 : 
[   14.313772] x5 : ffc008268038 x4 : ffc00827c038 x3 : ffc008267fc0
[   14.321029] x2 : 0028 x1 : ffc00827bfc0 x0 : ffc008267e80
[   14.328288] Call trace:
[   14.330766]  __memcpy+0x15c/0x230
[   14.334135]  process_one_work+0x1dc/0x450
[   14.338214]  worker_thread+0x300/0x450
[   14.342025]  kthread+0x100/0x110
[   14.345305]  ret_from_fork+0x10/0x20
[   14.348947] Code: a9422428 a9032c6a a9432c2a a984346c (a9c4342c)
[   14.355132] ---[ end trace  ]---

By constraining the input with this small patch it works fine:

--- a/drivers/gpu/drm/drm_fb_helper.c
+++ b/drivers/gpu/drm/drm_fb_helper.c
@@ -684,11 +684,13 @@ static void drm_fb_helper_damage(struct fb_info
*info, u32 x, u32 y,
 static void drm_fb_helper_memory_range_to_clip(struct fb_info *info,
off_t off, size_t len,
   struct drm_rect *clip)
 {
+   struct drm_fb_helper *fb_helper = info->par;
+
off_t end = off + len;
u32 x1 = 0;
u32 y1 = off / info->fix.line_length;
u32 x2 = info->var.xres;
-   u32 y2 = DIV_ROUND_UP(end, info->fix.line_length);
+   u32 y2 = min_t(u32, DIV_ROUND_UP(end, info->fix.line_length),
fb_helper->fb->height);

if ((y2 - y1) == 1) {
/*

I am sure this patch is not how it should be fixed, but I have no
knowledge of the subsystem to fix it "at the right place".

Thanks,
Nuno


Re: [RFC 1/3] drm/amd/display: Introduce KUnit to DML

2022-06-15 Thread Maíra Canal
Hi Daniel

Thank you for your feedback! We are working on the comments you pointed out.

On 6/7/22 23:36, Daniel Latypov wrote:
> On Tue, Jun 7, 2022 at 6:09 PM Maíra Canal  wrote:
>> diff --git 
>> a/drivers/gpu/drm/amd/display/amdgpu_dm/tests/display_mode_lib_test.c 
>> b/drivers/gpu/drm/amd/display/amdgpu_dm/tests/display_mode_lib_test.c
>> new file mode 100644
>> index ..3ea0e7fb13e3
>> --- /dev/null
>> +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/tests/display_mode_lib_test.c
>> @@ -0,0 +1,83 @@
>> +// SPDX-License-Identifier: MIT
>> +/*
>> + * KUnit tests for dml/display_mode_lib.h
>> + *
>> + * Copyright (C) 2022, Maíra Canal 
>> + */
>> +
>> +#include 
>> +#include "../../dc/dml/display_mode_lib.h"
>> +#include "../../dc/dml/display_mode_enums.h"
>> +#include "dml_test.h"
>> +
>> +/**
>> + * DOC: Unit tests for AMDGPU DML display_mode_lib.h
>> + *
>> + * The display_mode_lib.h holds the functions responsible for the 
>> instantiation
>> + * and logging of the Display Mode Library (DML).
>> + *
>> + * These KUnit tests were implemented with the intention of assuring the 
>> proper
>> + * logging of the DML.
>> + *
>> + */
>> +
>> +static void dml_get_status_message_test(struct kunit *test)
>> +{
> 
> I think this is a case where an exhaustive test might not be warranted.
> The function under test is entirely just a switch statement with
> return statements, so the chances of things going wrong is minimal.
> But that's just my personal preference.

Maybe we left out some explanation on this unit test. This RFC was more of an 
introduction to our project. We wanted to show you the test structure we plan 
to develop the unit tests during this summer. Initially, we were thinking of 
using the typical kunit_test_suites structure, but we end up checking out that 
it wasn't possible, due to the need to insert the tests inside the AMDGPU stack.

We also agree with you that this test is trivial and it will probably be 
removed from the final version. We plan to have more functional tests that 
explore the inner workings of the DML and especially the corner cases as you 
said.

We apologize if we didn't make it clear in the Cover Letter that this RFC is 
more of an introduction to the project we pretend to develop in the summer.

If you have suggestions on how we can improve the use of KUnit, it is welcome.

>>
>> +int display_mode_lib_test_init(void)
>> +{
>> +   pr_info("===> Running display_mode_lib KUnit Tests");
>> +   
>> pr_info("**");
>> +   pr_info("**   NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE   
>> **");
>> +   pr_info("**  
>> **");
>> +   pr_info("** display_mode_lib KUnit Tests are being run. This 
>> **");
>> +   pr_info("** means that this is a TEST kernel and should not be   
>> **");
>> +   pr_info("** used for production. 
>> **");
>> +   pr_info("**  
>> **");
>> +   pr_info("** If you see this message and you are not debugging
>> **");
>> +   pr_info("** the kernel, report this immediately to your vendor!  
>> **");
>> +   pr_info("**  
>> **");
>> +   
>> pr_info("**");
> 
> David Gow proposed tainting the kernel if we ever try to run a KUnit
> test suite here:
> https://lore.kernel.org/linux-kselftest/20220513083212.3537869-2-david...@google.com/
> 
> If that goes in, then this logging might not be as necessary.
> I'm not sure what the status of that change is, but we're at least
> waiting on a v4, I think.

This is going to be great! We will keep an eye on this proposal.

- Maíra Canal




Re: [Intel-gfx] [PATCH 3/3] drm/doc/rfc: VM_BIND uapi definition

2022-06-15 Thread Niranjana Vishwanathapura

On Wed, Jun 15, 2022 at 08:22:23AM +0100, Tvrtko Ursulin wrote:


On 14/06/2022 17:42, Niranjana Vishwanathapura wrote:

On Tue, Jun 14, 2022 at 05:07:37PM +0100, Tvrtko Ursulin wrote:


On 14/06/2022 17:02, Tvrtko Ursulin wrote:


On 14/06/2022 16:43, Niranjana Vishwanathapura wrote:

On Tue, Jun 14, 2022 at 08:16:41AM +0100, Tvrtko Ursulin wrote:


On 14/06/2022 00:39, Matthew Brost wrote:

On Mon, Jun 13, 2022 at 07:09:06PM +0100, Tvrtko Ursulin wrote:


On 13/06/2022 18:49, Niranjana Vishwanathapura wrote:

On Mon, Jun 13, 2022 at 05:22:02PM +0100, Tvrtko Ursulin wrote:


On 13/06/2022 16:05, Niranjana Vishwanathapura wrote:

On Mon, Jun 13, 2022 at 09:24:18AM +0100, Tvrtko Ursulin wrote:


On 10/06/2022 17:14, Niranjana Vishwanathapura wrote:
On Fri, Jun 10, 2022 at 05:48:39PM +0300, 
Lionel Landwerlin wrote:

On 10/06/2022 13:37, Tvrtko Ursulin wrote:


On 10/06/2022 08:07, Niranjana Vishwanathapura wrote:

VM_BIND and related uapi definitions

Signed-off-by: Niranjana Vishwanathapura

---
  Documentation/gpu/rfc/i915_vm_bind.h | 490
+++
  1 file changed, 490 insertions(+)
  create mode 100644 Documentation/gpu/rfc/i915_vm_bind.h

diff --git
a/Documentation/gpu/rfc/i915_vm_bind.h
b/Documentation/gpu/rfc/i915_vm_bind.h
new file mode 100644
index ..9fc854969cfb
--- /dev/null
+++ b/Documentation/gpu/rfc/i915_vm_bind.h
@@ -0,0 +1,490 @@
+/* SPDX-License-Identifier: MIT */
+/*
+ * Copyright © 2022 Intel Corporation
+ */
+
+/**
+ * DOC: I915_PARAM_HAS_VM_BIND
+ *
+ * VM_BIND feature availability.
+ * See typedef drm_i915_getparam_t param.
+ * bit[0]: If set, VM_BIND is supported, otherwise not.
+ * bits[8-15]: VM_BIND implementation version.
+ * version 0 will not have VM_BIND/UNBIND
timeline fence array support.
+ */
+#define I915_PARAM_HAS_VM_BIND    57
+
+/**
+ * DOC: I915_VM_CREATE_FLAGS_USE_VM_BIND
+ *
+ * Flag to opt-in for VM_BIND mode of 
binding during VM creation.

+ * See struct drm_i915_gem_vm_control flags.
+ *
+ * The older execbuf2 ioctl will not
support VM_BIND mode of operation.
+ * For VM_BIND mode, we have new execbuf3
ioctl which will not accept any
+ * execlist (See struct
drm_i915_gem_execbuffer3 for more details).
+ *
+ */
+#define I915_VM_CREATE_FLAGS_USE_VM_BIND    (1 << 0)
+
+/**
+ * DOC: I915_CONTEXT_CREATE_FLAGS_LONG_RUNNING
+ *
+ * Flag to declare context as long running.
+ * See struct drm_i915_gem_context_create_ext flags.
+ *
+ * Usage of dma-fence expects that they
complete in reasonable amount of time.
+ * Compute on the other hand can be long
running. Hence it is not appropriate
+ * for compute contexts to export request
completion dma-fence to user.
+ * The dma-fence usage will be limited to
in-kernel consumption only.
+ * Compute contexts need to use user/memory fence.
+ *
+ * So, long running contexts do not 
support output fences. Hence,

+ * I915_EXEC_FENCE_SIGNAL (See
&drm_i915_gem_exec_fence.flags) is expected
+ * to be not used. DRM_I915_GEM_WAIT ioctl
call is also not supported for
+ * objects mapped to long running contexts.
+ */
+#define I915_CONTEXT_CREATE_FLAGS_LONG_RUNNING   (1u << 2)
+
+/* VM_BIND related ioctls */
+#define DRM_I915_GEM_VM_BIND    0x3d
+#define DRM_I915_GEM_VM_UNBIND    0x3e
+#define DRM_I915_GEM_EXECBUFFER3    0x3f
+#define DRM_I915_GEM_WAIT_USER_FENCE    0x40
+
+#define DRM_IOCTL_I915_GEM_VM_BIND
DRM_IOWR(DRM_COMMAND_BASE +
DRM_I915_GEM_VM_BIND, struct
drm_i915_gem_vm_bind)
+#define DRM_IOCTL_I915_GEM_VM_UNBIND
DRM_IOWR(DRM_COMMAND_BASE +
DRM_I915_GEM_VM_UNBIND, struct
drm_i915_gem_vm_bind)
+#define DRM_IOCTL_I915_GEM_EXECBUFFER3
DRM_IOWR(DRM_COMMAND_BASE +
DRM_I915_GEM_EXECBUFFER3, struct
drm_i915_gem_execbuffer3)
+#define DRM_IOCTL_I915_GEM_WAIT_USER_FENCE
DRM_IOWR(DRM_COMMAND_BASE +
DRM_I915_GEM_WAIT_USER_FENCE, struct
drm_i915_gem_wait_user_fence)
+
+/**
+ * struct drm_i915_gem_vm_bind - VA to 
object mapping to bind.

+ *
+ * This structure is passed to VM_BIND
ioctl and specifies the mapping of GPU
+ * virtual address (VA) range to the
section of an object that should be bound
+ * in the device page table of the 
specified address space (VM).

+ * The VA range specified must be unique
(ie., not currently bound) and can
+ * be mapped to whole object or a section
of the object (partial binding).
+ * Multiple VA mappings can be created to
the same section of the object
+ * (aliasing).
+ *
+ * The @queue_idx specifies the queue to
use for binding. Same queue can be
+ * used for both VM_BIND and VM_UNBIND
calls. All submitted bind and unbind
+ * operations in a queue are performed 
in the order of submission.

+ *
+ * The @start, @offset and @length should
be 4K page aligned. However the DG2
+ * and XEHPSDV has 64K page size for device
local-memory and has compact page
+ * table. On those platforms, for binding
device local-memory objects, the
+ * @start should be 2M aligned, @offset and
@length should be 64K aligned.
+ * Also, on those platforms, it is not
allowed to bind an device local-

[PATCH 5/6] drm/i915/gt: Serialize GRDOM access between multiple engine resets

2022-06-15 Thread Mauro Carvalho Chehab
From: Chris Wilson 

Don't allow two engines to be reset in parallel, as they would both
try to select a reset bit (and send requests to common registers)
and wait on that register, at the same time. Serialize control of
the reset requests/acks using the uncore->lock, which will also ensure
that no other GT state changes at the same time as the actual reset.

Fixes: 7938d61591d3 ("drm/i915: Flush TLBs before releasing backing store")

Reported-by: Mika Kuoppala 
Signed-off-by: Chris Wilson 
Cc: Mika Kuoppala 
Cc: Andi Shyti 
Cc: sta...@vger.kernel.org
Acked-by: Thomas Hellström 
Signed-off-by: Mauro Carvalho Chehab 
---

See [PATCH 0/6] at: 
https://lore.kernel.org/all/cover.1655306128.git.mche...@kernel.org/

 drivers/gpu/drm/i915/gt/intel_reset.c | 37 ---
 1 file changed, 28 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/i915/gt/intel_reset.c 
b/drivers/gpu/drm/i915/gt/intel_reset.c
index a5338c3fde7a..c68d36fb5bbd 100644
--- a/drivers/gpu/drm/i915/gt/intel_reset.c
+++ b/drivers/gpu/drm/i915/gt/intel_reset.c
@@ -300,9 +300,9 @@ static int gen6_hw_domain_reset(struct intel_gt *gt, u32 
hw_domain_mask)
return err;
 }
 
-static int gen6_reset_engines(struct intel_gt *gt,
- intel_engine_mask_t engine_mask,
- unsigned int retry)
+static int __gen6_reset_engines(struct intel_gt *gt,
+   intel_engine_mask_t engine_mask,
+   unsigned int retry)
 {
struct intel_engine_cs *engine;
u32 hw_mask;
@@ -321,6 +321,20 @@ static int gen6_reset_engines(struct intel_gt *gt,
return gen6_hw_domain_reset(gt, hw_mask);
 }
 
+static int gen6_reset_engines(struct intel_gt *gt,
+ intel_engine_mask_t engine_mask,
+ unsigned int retry)
+{
+   unsigned long flags;
+   int ret;
+
+   spin_lock_irqsave(>->uncore->lock, flags);
+   ret = __gen6_reset_engines(gt, engine_mask, retry);
+   spin_unlock_irqrestore(>->uncore->lock, flags);
+
+   return ret;
+}
+
 static struct intel_engine_cs *find_sfc_paired_vecs_engine(struct 
intel_engine_cs *engine)
 {
int vecs_id;
@@ -487,9 +501,9 @@ static void gen11_unlock_sfc(struct intel_engine_cs *engine)
rmw_clear_fw(uncore, sfc_lock.lock_reg, sfc_lock.lock_bit);
 }
 
-static int gen11_reset_engines(struct intel_gt *gt,
-  intel_engine_mask_t engine_mask,
-  unsigned int retry)
+static int __gen11_reset_engines(struct intel_gt *gt,
+intel_engine_mask_t engine_mask,
+unsigned int retry)
 {
struct intel_engine_cs *engine;
intel_engine_mask_t tmp;
@@ -583,8 +597,11 @@ static int gen8_reset_engines(struct intel_gt *gt,
struct intel_engine_cs *engine;
const bool reset_non_ready = retry >= 1;
intel_engine_mask_t tmp;
+   unsigned long flags;
int ret;
 
+   spin_lock_irqsave(>->uncore->lock, flags);
+
for_each_engine_masked(engine, gt, engine_mask, tmp) {
ret = gen8_engine_reset_prepare(engine);
if (ret && !reset_non_ready)
@@ -612,17 +629,19 @@ static int gen8_reset_engines(struct intel_gt *gt,
 * This is best effort, so ignore any error from the initial reset.
 */
if (IS_DG2(gt->i915) && engine_mask == ALL_ENGINES)
-   gen11_reset_engines(gt, gt->info.engine_mask, 0);
+   __gen11_reset_engines(gt, gt->info.engine_mask, 0);
 
if (GRAPHICS_VER(gt->i915) >= 11)
-   ret = gen11_reset_engines(gt, engine_mask, retry);
+   ret = __gen11_reset_engines(gt, engine_mask, retry);
else
-   ret = gen6_reset_engines(gt, engine_mask, retry);
+   ret = __gen6_reset_engines(gt, engine_mask, retry);
 
 skip_reset:
for_each_engine_masked(engine, gt, engine_mask, tmp)
gen8_engine_reset_cancel(engine);
 
+   spin_unlock_irqrestore(>->uncore->lock, flags);
+
return ret;
 }
 
-- 
2.36.1



[PATCH 6/6] drm/i915/gt: Serialize TLB invalidates with GT resets

2022-06-15 Thread Mauro Carvalho Chehab
From: Chris Wilson 

Avoid trying to invalidate the TLB in the middle of performing an
engine reset, as this may result in the reset timing out. Currently,
the TLB invalidate is only serialised by its own mutex, forgoing the
uncore lock, but we can take the uncore->lock as well to serialise
the mmio access, thereby serialising with the GDRST.

Tested on a NUC5i7RYB, BIOS RYBDWi35.86A.0380.2019.0517.1530 with
i915 selftest/hangcheck.

Fixes: 7938d61591d3 ("drm/i915: Flush TLBs before releasing backing store")

Reported-by: Mauro Carvalho Chehab 
Tested-by: Mauro Carvalho Chehab 
Reviewed-by: Mauro Carvalho Chehab 
Signed-off-by: Chris Wilson 
Cc: Tvrtko Ursulin 
Cc: sta...@vger.kernel.org
Acked-by: Thomas Hellström 
Signed-off-by: Mauro Carvalho Chehab 
---

See [PATCH 0/6] at: 
https://lore.kernel.org/all/cover.1655306128.git.mche...@kernel.org/

 drivers/gpu/drm/i915/gt/intel_gt.c | 4 
 1 file changed, 4 insertions(+)

diff --git a/drivers/gpu/drm/i915/gt/intel_gt.c 
b/drivers/gpu/drm/i915/gt/intel_gt.c
index fb4fd5273ca4..33eb93586858 100644
--- a/drivers/gpu/drm/i915/gt/intel_gt.c
+++ b/drivers/gpu/drm/i915/gt/intel_gt.c
@@ -1248,6 +1248,8 @@ void intel_gt_invalidate_tlbs(struct intel_gt *gt)
mutex_lock(>->tlb_invalidate_lock);
intel_uncore_forcewake_get(uncore, FORCEWAKE_ALL);
 
+   spin_lock_irq(&uncore->lock); /* seralise invalidate with GT reset */
+
awake = 0;
for_each_engine(engine, gt, id) {
struct reg_and_bit rb;
@@ -1272,6 +1274,8 @@ void intel_gt_invalidate_tlbs(struct intel_gt *gt)
 IS_ALDERLAKE_P(i915)))
intel_uncore_write_fw(uncore, GEN12_OA_TLB_INV_CR, 1);
 
+   spin_unlock_irq(&uncore->lock);
+
for_each_engine_masked(engine, gt, awake, tmp) {
struct reg_and_bit rb;
 
-- 
2.36.1



[PATCH 4/6] drm/i915/gt: Only invalidate TLBs exposed to user manipulation

2022-06-15 Thread Mauro Carvalho Chehab
From: Chris Wilson 

Don't flush TLBs when the buffer is only used in the GGTT under full
control of the kernel, as there's no risk of of concurrent access
and stale access from prefetch.

We only need to invalidate the TLB if they are accessible by the user.

Fixes: 7938d61591d3 ("drm/i915: Flush TLBs before releasing backing store")

Signed-off-by: Chris Wilson 
Cc: Fei Yang 
Cc: Andi Shyti 
Cc: sta...@vger.kernel.org
Acked-by: Thomas Hellström 
Signed-off-by: Mauro Carvalho Chehab 
---

See [PATCH 0/6] at: 
https://lore.kernel.org/all/cover.1655306128.git.mche...@kernel.org/

 drivers/gpu/drm/i915/i915_vma.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/i915/i915_vma.c b/drivers/gpu/drm/i915/i915_vma.c
index 0bffb70b3c5f..7989986161e8 100644
--- a/drivers/gpu/drm/i915/i915_vma.c
+++ b/drivers/gpu/drm/i915/i915_vma.c
@@ -537,7 +537,8 @@ int i915_vma_bind(struct i915_vma *vma,
   bind_flags);
}
 
-   set_bit(I915_BO_WAS_BOUND_BIT, &vma->obj->flags);
+   if (bind_flags & I915_VMA_LOCAL_BIND)
+   set_bit(I915_BO_WAS_BOUND_BIT, &vma->obj->flags);
 
atomic_or(bind_flags, &vma->flags);
return 0;
-- 
2.36.1



[PATCH 0/6] Fix TLB invalidate issues with Broadwell

2022-06-15 Thread Mauro Carvalho Chehab
i915 selftest hangcheck is causing the i915 driver timeouts, as reported
by Intel CI bot:


http://gfx-ci.fi.intel.com/cibuglog-ng/issuefilterassoc/24297?query_key=42a999f48fa6ecce068bc8126c069be7c31153b4

When such test runs, the only output is:

[   68.811639] i915: Performing live selftests with 
st_random_seed=0xe138eac7 st_timeout=500
[   68.811792] i915: Running hangcheck
[   68.811859] i915: Running 
intel_hangcheck_live_selftests/igt_hang_sanitycheck
[   68.816910] i915 :00:02.0: [drm] Cannot find any crtc or sizes
[   68.841597] i915: Running 
intel_hangcheck_live_selftests/igt_reset_nop
[   69.346347] igt_reset_nop: 80 resets
[   69.362695] i915: Running 
intel_hangcheck_live_selftests/igt_reset_nop_engine
[   69.863559] igt_reset_nop_engine(rcs0): 709 resets
[   70.364924] igt_reset_nop_engine(bcs0): 903 resets
[   70.866005] igt_reset_nop_engine(vcs0): 659 resets
[   71.367934] igt_reset_nop_engine(vcs1): 549 resets
[   71.869259] igt_reset_nop_engine(vecs0): 553 resets
[   71.882592] i915: Running 
intel_hangcheck_live_selftests/igt_reset_idle_engine
[   72.383554] rcs0: Completed 16605 idle resets
[   72.884599] bcs0: Completed 18641 idle resets
[   73.385592] vcs0: Completed 17517 idle resets
[   73.886658] vcs1: Completed 15474 idle resets
[   74.387600] vecs0: Completed 17983 idle resets
[   74.387667] i915: Running 
intel_hangcheck_live_selftests/igt_reset_active_engine
[   74.889017] rcs0: Completed 747 active resets
[   75.174240] intel_engine_reset(bcs0) failed, err:-110
[   75.174301] bcs0: Completed 525 active resets

After that, the machine just silently hangs.

Bisecting the issue, the patch that introduced the regression is:

7938d61591d3 ("drm/i915: Flush TLBs before releasing backing store")

Reverting it fix the issues, but introduce other problems, as TLB
won't be invalidated anymore. So, instead, let's fix the root cause.

It turns that the TLB flush logic ends conflicting with i915 reset,
which is called during selftest hangcheck. So, the TLB cache should
be serialized, but other TLB fix patches are required for this one
to work.

Tested on an Intel NUC5i7RYB with an i7-5557U Broadwell CPU.

Chris Wilson (6):
  drm/i915/gt: Ignore TLB invalidations on idle engines
  drm/i915/gt: Invalidate TLB of the OA unit at TLB invalidations
  drm/i915/gt: Skip TLB invalidations once wedged
  drm/i915/gt: Only invalidate TLBs exposed to user manipulation
  drm/i915/gt: Serialize GRDOM access between multiple engine resets
  drm/i915/gt: Serialize TLB invalidates with GT resets

 drivers/gpu/drm/i915/gem/i915_gem_pages.c | 10 +++---
 drivers/gpu/drm/i915/gt/intel_gt.c| 43 +++
 drivers/gpu/drm/i915/gt/intel_gt_pm.h |  3 ++
 drivers/gpu/drm/i915/gt/intel_reset.c | 37 ++-
 drivers/gpu/drm/i915/i915_vma.c   |  3 +-
 5 files changed, 75 insertions(+), 21 deletions(-)

-- 
2.36.1




[PATCH 3/6] drm/i915/gt: Skip TLB invalidations once wedged

2022-06-15 Thread Mauro Carvalho Chehab
From: Chris Wilson 

Skip all further TLB invalidations once the device is wedged and
had been reset, as, on such cases, it can no longer process instructions
on the GPU and the user no longer has access to the TLB's in each engine.

Fixes: 7938d61591d3 ("drm/i915: Flush TLBs before releasing backing store")

Signed-off-by: Chris Wilson 
Cc: Fei Yang 
Cc: Andi Shyti 
Cc: sta...@vger.kernel.org
Acked-by: Thomas Hellström 
Signed-off-by: Mauro Carvalho Chehab 
---

See [PATCH 0/6] at: 
https://lore.kernel.org/all/cover.1655306128.git.mche...@kernel.org/

 drivers/gpu/drm/i915/gt/intel_gt.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/drivers/gpu/drm/i915/gt/intel_gt.c 
b/drivers/gpu/drm/i915/gt/intel_gt.c
index 61b7ec5118f9..fb4fd5273ca4 100644
--- a/drivers/gpu/drm/i915/gt/intel_gt.c
+++ b/drivers/gpu/drm/i915/gt/intel_gt.c
@@ -1226,6 +1226,9 @@ void intel_gt_invalidate_tlbs(struct intel_gt *gt)
if (I915_SELFTEST_ONLY(gt->awake == -ENODEV))
return;
 
+   if (intel_gt_is_wedged(gt))
+   return;
+
if (GRAPHICS_VER(i915) == 12) {
regs = gen12_regs;
num = ARRAY_SIZE(gen12_regs);
-- 
2.36.1



[PATCH 1/6] drm/i915/gt: Ignore TLB invalidations on idle engines

2022-06-15 Thread Mauro Carvalho Chehab
From: Chris Wilson 

As an extension of the current skip TLB invalidations,
check if the device is powered down prior to any engine activity,

as, on such cases, all the TLBs were already invalidated, so an
explicit TLB invalidation is not needed.

This becomes more significant  with GuC, as it can only do so when
the connection to the GuC is awake.

Fixes: 7938d61591d3 ("drm/i915: Flush TLBs before releasing backing store")

Signed-off-by: Chris Wilson 
Cc: Fei Yang 
Cc: Andi Shyti 
Cc: sta...@vger.kernel.org
Acked-by: Thomas Hellström 
Signed-off-by: Mauro Carvalho Chehab 
---

See [PATCH 0/6] at: 
https://lore.kernel.org/all/cover.1655306128.git.mche...@kernel.org/

 drivers/gpu/drm/i915/gem/i915_gem_pages.c | 10 +
 drivers/gpu/drm/i915/gt/intel_gt.c| 26 +--
 drivers/gpu/drm/i915/gt/intel_gt_pm.h |  3 +++
 3 files changed, 28 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/i915/gem/i915_gem_pages.c 
b/drivers/gpu/drm/i915/gem/i915_gem_pages.c
index 97c820eee115..6835279943df 100644
--- a/drivers/gpu/drm/i915/gem/i915_gem_pages.c
+++ b/drivers/gpu/drm/i915/gem/i915_gem_pages.c
@@ -6,14 +6,15 @@
 
 #include 
 
+#include "gt/intel_gt.h"
+#include "gt/intel_gt_pm.h"
+
 #include "i915_drv.h"
 #include "i915_gem_object.h"
 #include "i915_scatterlist.h"
 #include "i915_gem_lmem.h"
 #include "i915_gem_mman.h"
 
-#include "gt/intel_gt.h"
-
 void __i915_gem_object_set_pages(struct drm_i915_gem_object *obj,
 struct sg_table *pages,
 unsigned int sg_page_sizes)
@@ -217,10 +218,11 @@ __i915_gem_object_unset_pages(struct drm_i915_gem_object 
*obj)
 
if (test_and_clear_bit(I915_BO_WAS_BOUND_BIT, &obj->flags)) {
struct drm_i915_private *i915 = to_i915(obj->base.dev);
+   struct intel_gt *gt = to_gt(i915);
intel_wakeref_t wakeref;
 
-   with_intel_runtime_pm_if_active(&i915->runtime_pm, wakeref)
-   intel_gt_invalidate_tlbs(to_gt(i915));
+   with_intel_gt_pm_if_awake(gt, wakeref)
+   intel_gt_invalidate_tlbs(gt);
}
 
return pages;
diff --git a/drivers/gpu/drm/i915/gt/intel_gt.c 
b/drivers/gpu/drm/i915/gt/intel_gt.c
index f33290358c51..d5ed6a6ac67c 100644
--- a/drivers/gpu/drm/i915/gt/intel_gt.c
+++ b/drivers/gpu/drm/i915/gt/intel_gt.c
@@ -11,6 +11,7 @@
 
 #include "i915_drv.h"
 #include "intel_context.h"
+#include "intel_engine_pm.h"
 #include "intel_engine_regs.h"
 #include "intel_gt.h"
 #include "intel_gt_buffer_pool.h"
@@ -1216,6 +1217,7 @@ void intel_gt_invalidate_tlbs(struct intel_gt *gt)
struct drm_i915_private *i915 = gt->i915;
struct intel_uncore *uncore = gt->uncore;
struct intel_engine_cs *engine;
+   intel_engine_mask_t awake, tmp;
enum intel_engine_id id;
const i915_reg_t *regs;
unsigned int num = 0;
@@ -1239,12 +1241,27 @@ void intel_gt_invalidate_tlbs(struct intel_gt *gt)
 
GEM_TRACE("\n");
 
-   assert_rpm_wakelock_held(&i915->runtime_pm);
-
mutex_lock(>->tlb_invalidate_lock);
intel_uncore_forcewake_get(uncore, FORCEWAKE_ALL);
 
+   awake = 0;
for_each_engine(engine, gt, id) {
+   struct reg_and_bit rb;
+
+   if (!intel_engine_pm_is_awake(engine))
+   continue;
+
+   rb = get_reg_and_bit(engine, regs == gen8_regs, regs, num);
+   if (!i915_mmio_reg_offset(rb.reg))
+   continue;
+
+   intel_uncore_write_fw(uncore, rb.reg, rb.bit);
+   awake |= engine->mask;
+   }
+
+   for_each_engine_masked(engine, gt, awake, tmp) {
+   struct reg_and_bit rb;
+
/*
 * HW architecture suggest typical invalidation time at 40us,
 * with pessimistic cases up to 100us and a recommendation to
@@ -1252,13 +1269,8 @@ void intel_gt_invalidate_tlbs(struct intel_gt *gt)
 */
const unsigned int timeout_us = 100;
const unsigned int timeout_ms = 4;
-   struct reg_and_bit rb;
 
rb = get_reg_and_bit(engine, regs == gen8_regs, regs, num);
-   if (!i915_mmio_reg_offset(rb.reg))
-   continue;
-
-   intel_uncore_write_fw(uncore, rb.reg, rb.bit);
if (__intel_wait_for_register_fw(uncore,
 rb.reg, rb.bit, 0,
 timeout_us, timeout_ms,
diff --git a/drivers/gpu/drm/i915/gt/intel_gt_pm.h 
b/drivers/gpu/drm/i915/gt/intel_gt_pm.h
index bc898df7a48c..a334787a4939 100644
--- a/drivers/gpu/drm/i915/gt/intel_gt_pm.h
+++ b/drivers/gpu/drm/i915/gt/intel_gt_pm.h
@@ -55,6 +55,9 @@ static inline void intel_gt_pm_might_put(struct intel_gt *gt)
for (tmp = 1, intel_gt_pm_get(gt); tmp; \
 intel_gt_pm_put(gt)

[PATCH 2/6] drm/i915/gt: Invalidate TLB of the OA unit at TLB invalidations

2022-06-15 Thread Mauro Carvalho Chehab
From: Chris Wilson 

On gen12 HW, ensure that the TLB of the OA unit is also invalidated
as just invalidating the TLB of an engine is not enough.

Fixes: 7938d61591d3 ("drm/i915: Flush TLBs before releasing backing store")

Signed-off-by: Chris Wilson 
Cc: Fei Yang 
Cc: Andi Shyti 
Cc: sta...@vger.kernel.org
Acked-by: Thomas Hellström 
Signed-off-by: Mauro Carvalho Chehab 
---

See [PATCH 0/6] at: 
https://lore.kernel.org/all/cover.1655306128.git.mche...@kernel.org/

 drivers/gpu/drm/i915/gt/intel_gt.c | 10 ++
 1 file changed, 10 insertions(+)

diff --git a/drivers/gpu/drm/i915/gt/intel_gt.c 
b/drivers/gpu/drm/i915/gt/intel_gt.c
index d5ed6a6ac67c..61b7ec5118f9 100644
--- a/drivers/gpu/drm/i915/gt/intel_gt.c
+++ b/drivers/gpu/drm/i915/gt/intel_gt.c
@@ -10,6 +10,7 @@
 #include "pxp/intel_pxp.h"
 
 #include "i915_drv.h"
+#include "i915_perf_oa_regs.h"
 #include "intel_context.h"
 #include "intel_engine_pm.h"
 #include "intel_engine_regs.h"
@@ -1259,6 +1260,15 @@ void intel_gt_invalidate_tlbs(struct intel_gt *gt)
awake |= engine->mask;
}
 
+   /* Wa_2207587034:tgl,dg1,rkl,adl-s,adl-p */
+   if (awake &&
+   (IS_TIGERLAKE(i915) ||
+IS_DG1(i915) ||
+IS_ROCKETLAKE(i915) ||
+IS_ALDERLAKE_S(i915) ||
+IS_ALDERLAKE_P(i915)))
+   intel_uncore_write_fw(uncore, GEN12_OA_TLB_INV_CR, 1);
+
for_each_engine_masked(engine, gt, awake, tmp) {
struct reg_and_bit rb;
 
-- 
2.36.1



[PATCH] drm/rockchip: Detach from ARM DMA domain in attach_device

2022-06-15 Thread Steven Price
Since commit 1ea2a07a532b ("iommu: Add DMA ownership management
interfaces") the Rockchip display driver on the Firefly RK3288 fails to
initialise properly. This is because ARM DMA domain is still attached.

Let's follow the lead of exynos and tegra and add code to explicitly
remove the ARM domain before attaching a new one.

Suggested-by: Robin Murphy 
Signed-off-by: Steven Price 
---
See also the thread[1] where I reported the regression.

[1] 
https://lore.kernel.org/linux-kernel/da9cca0a-ec5b-2e73-9de0-a930f7d947b2%40arm.com
---
 drivers/gpu/drm/rockchip/rockchip_drm_drv.c | 17 +
 1 file changed, 17 insertions(+)

diff --git a/drivers/gpu/drm/rockchip/rockchip_drm_drv.c 
b/drivers/gpu/drm/rockchip/rockchip_drm_drv.c
index 67d38f53d3e5..13ed33e74457 100644
--- a/drivers/gpu/drm/rockchip/rockchip_drm_drv.c
+++ b/drivers/gpu/drm/rockchip/rockchip_drm_drv.c
@@ -23,6 +23,14 @@
 #include 
 #include 
 
+#if defined(CONFIG_ARM_DMA_USE_IOMMU)
+#include 
+#else
+#define arm_iommu_detach_device(...)   ({ })
+#define arm_iommu_release_mapping(...) ({ })
+#define to_dma_iommu_mapping(dev) NULL
+#endif
+
 #include "rockchip_drm_drv.h"
 #include "rockchip_drm_fb.h"
 #include "rockchip_drm_gem.h"
@@ -49,6 +57,15 @@ int rockchip_drm_dma_attach_device(struct drm_device 
*drm_dev,
if (!private->domain)
return 0;
 
+   if (IS_ENABLED(CONFIG_ARM_DMA_USE_IOMMU)) {
+   struct dma_iommu_mapping *mapping = to_dma_iommu_mapping(dev);
+
+   if (mapping) {
+   arm_iommu_detach_device(dev);
+   arm_iommu_release_mapping(mapping);
+   }
+   }
+
ret = iommu_attach_device(private->domain, dev);
if (ret) {
DRM_DEV_ERROR(dev, "Failed to attach iommu device\n");
-- 
2.25.1



Re: [PATCH] drm/sun4i: Fix crash during suspend after component bind failure

2022-06-15 Thread Jernej Škrabec
Dne sreda, 15. junij 2022 ob 07:42:53 CEST je Samuel Holland napisal(a):
> If the component driver fails to bind, or is unbound, the driver data
> for the top-level platform device points to a freed drm_device. If the
> system is then suspended, the driver passes this dangling pointer to
> drm_mode_config_helper_suspend(), which crashes.
> 
> Fix this by only setting the driver data while the platform driver holds
> a reference to the drm_device.
> 
> Fixes: 624b4b48d9d8 ("drm: sun4i: Add support for suspending the display 
driver")
> Signed-off-by: Samuel Holland 

Reviewed-by: Jernej Skrabec 

Best regards,
Jernej




[PATCH v7] drm/msm/dp: force link training for display resolution change

2022-06-15 Thread Kuogee Hsieh
Display resolution change is implemented through drm modeset. Older
modeset (resolution) has to be disabled first before newer modeset
(resolution) can be enabled. Display disable will turn off both
pixel clock and main link clock so that main link have to be
re-trained during display enable to have new video stream flow
again. At current implementation, display enable function manually
kicks up irq_hpd_handle which will read panel link status and start
link training if link status is not in sync state.

However, there is rare case that a particular panel links status keep
staying in sync for some period of time after main link had been shut
down previously at display disabled. In this case, main link retraining
will not be executed by irq_hdp_handle(). Hence video stream of newer
display resolution will fail to be transmitted to panel due to main
link is not in sync between host and panel.

This patch will bypass irq_hpd_handle() in favor of directly call
dp_ctrl_on_stream() to always perform link training in regardless of
main link status. So that no unexpected exception resolution change
failure cases will happen. Also this implementation are more efficient
than manual kicking off irq_hpd_handle function.

Changes in v2:
-- set force_link_train flag on DP only (is_edp == false)

Changes in v3:
-- revise commit  text
-- add Fixes tag

Changes in v4:
-- revise commit  text

Changes in v5:
-- fix spelling at commit text

Changes in v6:
-- split dp_ctrl_on_stream() for phy test case
-- revise commit text for modeset

Changes in v7:
-- drop 0 assignment at local variable (ret = 0)

Fixes: 62671d2ef24b ("drm/msm/dp: fixes wrong connection state caused by 
failure of link train")
Signed-off-by: Kuogee Hsieh 
---
 drivers/gpu/drm/msm/dp/dp_ctrl.c| 31 +++
 drivers/gpu/drm/msm/dp/dp_ctrl.h|  3 ++-
 drivers/gpu/drm/msm/dp/dp_display.c | 13 ++---
 3 files changed, 31 insertions(+), 16 deletions(-)

diff --git a/drivers/gpu/drm/msm/dp/dp_ctrl.c b/drivers/gpu/drm/msm/dp/dp_ctrl.c
index af7a80c..01028b5 100644
--- a/drivers/gpu/drm/msm/dp/dp_ctrl.c
+++ b/drivers/gpu/drm/msm/dp/dp_ctrl.c
@@ -1551,7 +1551,7 @@ static int dp_ctrl_process_phy_test_request(struct 
dp_ctrl_private *ctrl)
 
ret = dp_ctrl_on_link(&ctrl->dp_ctrl);
if (!ret)
-   ret = dp_ctrl_on_stream(&ctrl->dp_ctrl);
+   ret = dp_ctrl_on_stream_phy_test_report(&ctrl->dp_ctrl);
else
DRM_ERROR("failed to enable DP link controller\n");
 
@@ -1807,7 +1807,27 @@ static int dp_ctrl_link_retrain(struct dp_ctrl_private 
*ctrl)
return dp_ctrl_setup_main_link(ctrl, &training_step);
 }
 
-int dp_ctrl_on_stream(struct dp_ctrl *dp_ctrl)
+int dp_ctrl_on_stream_phy_test_report(struct dp_ctrl *dp_ctrl)
+{
+   int ret;
+   struct dp_ctrl_private *ctrl;
+
+   ctrl = container_of(dp_ctrl, struct dp_ctrl_private, dp_ctrl);
+
+   ctrl->dp_ctrl.pixel_rate = ctrl->panel->dp_mode.drm_mode.clock;
+
+   ret = dp_ctrl_enable_stream_clocks(ctrl);
+   if (ret) {
+   DRM_ERROR("Failed to start pixel clocks. ret=%d\n", ret);
+   return ret;
+   }
+
+   dp_ctrl_send_phy_test_pattern(ctrl);
+
+   return 0;
+}
+
+int dp_ctrl_on_stream(struct dp_ctrl *dp_ctrl, bool force_link_train)
 {
int ret = 0;
bool mainlink_ready = false;
@@ -1843,12 +1863,7 @@ int dp_ctrl_on_stream(struct dp_ctrl *dp_ctrl)
goto end;
}
 
-   if (ctrl->link->sink_request & DP_TEST_LINK_PHY_TEST_PATTERN) {
-   dp_ctrl_send_phy_test_pattern(ctrl);
-   return 0;
-   }
-
-   if (!dp_ctrl_channel_eq_ok(ctrl))
+   if (force_link_train || !dp_ctrl_channel_eq_ok(ctrl))
dp_ctrl_link_retrain(ctrl);
 
/* stop txing train pattern to end link training */
diff --git a/drivers/gpu/drm/msm/dp/dp_ctrl.h b/drivers/gpu/drm/msm/dp/dp_ctrl.h
index 0745fde..9a39b00 100644
--- a/drivers/gpu/drm/msm/dp/dp_ctrl.h
+++ b/drivers/gpu/drm/msm/dp/dp_ctrl.h
@@ -21,7 +21,8 @@ struct dp_ctrl {
 };
 
 int dp_ctrl_on_link(struct dp_ctrl *dp_ctrl);
-int dp_ctrl_on_stream(struct dp_ctrl *dp_ctrl);
+int dp_ctrl_on_stream(struct dp_ctrl *dp_ctrl, bool force_link_train);
+int dp_ctrl_on_stream_phy_test_report(struct dp_ctrl *dp_ctrl);
 int dp_ctrl_off_link_stream(struct dp_ctrl *dp_ctrl);
 int dp_ctrl_off_link(struct dp_ctrl *dp_ctrl);
 int dp_ctrl_off(struct dp_ctrl *dp_ctrl);
diff --git a/drivers/gpu/drm/msm/dp/dp_display.c 
b/drivers/gpu/drm/msm/dp/dp_display.c
index c388323..b6d25ab 100644
--- a/drivers/gpu/drm/msm/dp/dp_display.c
+++ b/drivers/gpu/drm/msm/dp/dp_display.c
@@ -872,7 +872,7 @@ static int dp_display_enable(struct dp_display_private *dp, 
u32 data)
return 0;
}
 
-   rc = dp_ctrl_on_stream(dp->ctrl);
+   rc = dp_ctrl_on_stream(dp->ctrl, data);
if (!rc)
dp_display->power_on = true;
 
@@ -1654,6 +1654,7 @@ void dp_brid

Re: [PATCH] drm/bridge: anx7625: Zero error variable when panel bridge not present

2022-06-15 Thread Robert Foss
On Tue, 14 Jun 2022 at 09:52, AngeloGioacchino Del Regno
 wrote:
>
> Il 13/06/22 18:37, Nícolas F. R. A. Prado ha scritto:
> > While parsing the DT, the anx7625 driver checks for the presence of a
> > panel bridge on endpoint 1. If it is missing, pdata->panel_bridge stores
> > the error pointer and the function returns successfully without first
> > cleaning that variable. This is an issue since other functions later
> > check for the presence of a panel bridge by testing the trueness of that
> > variable.
> >
> > In order to ensure proper behavior, zero out pdata->panel_bridge before
> > returning when no panel bridge is found.
> >
> > Fixes: 9e82ea0fb1df ("drm/bridge: anx7625: switch to 
> > devm_drm_of_get_bridge")
> > Signed-off-by: Nícolas F. R. A. Prado 
> >
>
> I would've preferred s/zero out/cleanup/g but it's also fine as you wrote it.
> Besides, good catch!
>
> Reviewed-by: AngeloGioacchino Del Regno 
> 
>

Applied to drm-misc-next


[PATCH v2] drm/arm/hdlcd: Take over EFI framebuffer properly

2022-06-15 Thread Robin Murphy
The Arm Juno board EDK2 port has provided an EFI GOP display via HDLCD0
for some time now, which works nicely as an early framebuffer. However,
once the HDLCD driver probes and takes over the hardware, it should
take over the logical framebuffer as well, otherwise the now-defunct GOP
device hangs about and virtual console output inevitably disappears into
the wrong place most of the time.

We'll do this after binding the HDMI encoder, since that's the most
likely thing to fail, and the EFI console is still better than nothing
when that happens. However, the two HDLCD controllers on Juno are
independent, and many users will still be using older firmware without
any display support, so we'll only bother if we find that the HDLCD
we're probing is already enabled. And if it is, then we'll also stop it,
since otherwise the display can end up shifted if it's still scanning
out while the rest of the registers are subsequently reconfigured.

Signed-off-by: Robin Murphy 
---

Since I ended up adding (relatively) a lot here, I didn't want to
second-guess Javier's opinion so left off the R-b tag from v1.

 drivers/gpu/drm/arm/hdlcd_drv.c | 7 +++
 1 file changed, 7 insertions(+)

diff --git a/drivers/gpu/drm/arm/hdlcd_drv.c b/drivers/gpu/drm/arm/hdlcd_drv.c
index e89ae0ec60eb..1f1171f2f16a 100644
--- a/drivers/gpu/drm/arm/hdlcd_drv.c
+++ b/drivers/gpu/drm/arm/hdlcd_drv.c
@@ -21,6 +21,7 @@
 #include 
 #include 
 
+#include 
 #include 
 #include 
 #include 
@@ -314,6 +315,12 @@ static int hdlcd_drm_bind(struct device *dev)
goto err_vblank;
}
 
+   /* If EFI left us running, take over from efifb/sysfb */
+   if (hdlcd_read(hdlcd, HDLCD_REG_COMMAND)) {
+   hdlcd_write(hdlcd, HDLCD_REG_COMMAND, 0);
+   drm_aperture_remove_framebuffers(false, &hdlcd_driver);
+   }
+
drm_mode_config_reset(drm);
drm_kms_helper_poll_init(drm);
 
-- 
2.36.1.dirty



[PATCH] drm/arm/hdlcd: Simplify IRQ install/uninstall

2022-06-15 Thread Robin Murphy
Since we no longer need to conform to the structure of the various DRM
IRQ callbacks, we can streamline the code by consolidating the piecemeal
functions and passing around our private data structure directly. We're
also a platform device so should never see IRQ_NOTCONNECTED either.

Furthermore we can also get rid of all the unnecesary read-modify-write
operations, since on install we know we cleared the whole interrupt mask
before enabling the debug IRQs, and thus on uninstall we're always
clearing everything as well.

Signed-off-by: Robin Murphy 
---
 drivers/gpu/drm/arm/hdlcd_drv.c | 62 +
 1 file changed, 16 insertions(+), 46 deletions(-)

diff --git a/drivers/gpu/drm/arm/hdlcd_drv.c b/drivers/gpu/drm/arm/hdlcd_drv.c
index 1f1171f2f16a..7d6aa9b3b577 100644
--- a/drivers/gpu/drm/arm/hdlcd_drv.c
+++ b/drivers/gpu/drm/arm/hdlcd_drv.c
@@ -41,8 +41,7 @@
 
 static irqreturn_t hdlcd_irq(int irq, void *arg)
 {
-   struct drm_device *drm = arg;
-   struct hdlcd_drm_private *hdlcd = drm->dev_private;
+   struct hdlcd_drm_private *hdlcd = arg;
unsigned long irq_status;
 
irq_status = hdlcd_read(hdlcd, HDLCD_REG_INT_STATUS);
@@ -70,61 +69,32 @@ static irqreturn_t hdlcd_irq(int irq, void *arg)
return IRQ_HANDLED;
 }
 
-static void hdlcd_irq_preinstall(struct drm_device *drm)
-{
-   struct hdlcd_drm_private *hdlcd = drm->dev_private;
-   /* Ensure interrupts are disabled */
-   hdlcd_write(hdlcd, HDLCD_REG_INT_MASK, 0);
-   hdlcd_write(hdlcd, HDLCD_REG_INT_CLEAR, ~0);
-}
-
-static void hdlcd_irq_postinstall(struct drm_device *drm)
-{
-#ifdef CONFIG_DEBUG_FS
-   struct hdlcd_drm_private *hdlcd = drm->dev_private;
-   unsigned long irq_mask = hdlcd_read(hdlcd, HDLCD_REG_INT_MASK);
-
-   /* enable debug interrupts */
-   irq_mask |= HDLCD_DEBUG_INT_MASK;
-
-   hdlcd_write(hdlcd, HDLCD_REG_INT_MASK, irq_mask);
-#endif
-}
-
-static int hdlcd_irq_install(struct drm_device *drm, int irq)
+static int hdlcd_irq_install(struct hdlcd_drm_private *hdlcd)
 {
int ret;
 
-   if (irq == IRQ_NOTCONNECTED)
-   return -ENOTCONN;
+   /* Ensure interrupts are disabled */
+   hdlcd_write(hdlcd, HDLCD_REG_INT_MASK, 0);
+   hdlcd_write(hdlcd, HDLCD_REG_INT_CLEAR, ~0);
 
-   hdlcd_irq_preinstall(drm);
-
-   ret = request_irq(irq, hdlcd_irq, 0, drm->driver->name, drm);
+   ret = request_irq(hdlcd->irq, hdlcd_irq, 0, "hdlcd", hdlcd);
if (ret)
return ret;
 
-   hdlcd_irq_postinstall(drm);
+#ifdef CONFIG_DEBUG_FS
+   /* enable debug interrupts */
+   hdlcd_write(hdlcd, HDLCD_REG_INT_MASK, HDLCD_DEBUG_INT_MASK);
+#endif
 
return 0;
 }
 
-static void hdlcd_irq_uninstall(struct drm_device *drm)
+static void hdlcd_irq_uninstall(struct hdlcd_drm_private *hdlcd)
 {
-   struct hdlcd_drm_private *hdlcd = drm->dev_private;
/* disable all the interrupts that we might have enabled */
-   unsigned long irq_mask = hdlcd_read(hdlcd, HDLCD_REG_INT_MASK);
+   hdlcd_write(hdlcd, HDLCD_REG_INT_MASK, 0);
 
-#ifdef CONFIG_DEBUG_FS
-   /* disable debug interrupts */
-   irq_mask &= ~HDLCD_DEBUG_INT_MASK;
-#endif
-
-   /* disable vsync interrupts */
-   irq_mask &= ~HDLCD_INTERRUPT_VSYNC;
-   hdlcd_write(hdlcd, HDLCD_REG_INT_MASK, irq_mask);
-
-   free_irq(hdlcd->irq, drm);
+   free_irq(hdlcd->irq, hdlcd);
 }
 
 static int hdlcd_load(struct drm_device *drm, unsigned long flags)
@@ -184,7 +154,7 @@ static int hdlcd_load(struct drm_device *drm, unsigned long 
flags)
goto irq_fail;
hdlcd->irq = ret;
 
-   ret = hdlcd_irq_install(drm, hdlcd->irq);
+   ret = hdlcd_irq_install(hdlcd);
if (ret < 0) {
DRM_ERROR("failed to install IRQ handler\n");
goto irq_fail;
@@ -342,7 +312,7 @@ static int hdlcd_drm_bind(struct device *dev)
 err_unload:
of_node_put(hdlcd->crtc.port);
hdlcd->crtc.port = NULL;
-   hdlcd_irq_uninstall(drm);
+   hdlcd_irq_uninstall(hdlcd);
of_reserved_mem_device_release(drm->dev);
 err_free:
drm_mode_config_cleanup(drm);
@@ -364,7 +334,7 @@ static void hdlcd_drm_unbind(struct device *dev)
hdlcd->crtc.port = NULL;
pm_runtime_get_sync(dev);
drm_atomic_helper_shutdown(drm);
-   hdlcd_irq_uninstall(drm);
+   hdlcd_irq_uninstall(hdlcd);
pm_runtime_put(dev);
if (pm_runtime_enabled(dev))
pm_runtime_disable(dev);
-- 
2.36.1.dirty



Re: [PATCH v2 1/3] drm/msm/dpu: Move LM CRC code into separate method

2022-06-15 Thread Jessica Zhang




On 6/15/2022 2:35 AM, Dmitry Baryshkov wrote:

On Wed, 15 Jun 2022 at 00:13, Jessica Zhang  wrote:


Move layer mixer-specific section of dpu_crtc_get_crc() into a separate
helper method. This way, we can make it easier to get CRCs from other HW
blocks by adding other get_crc helper methods.

Changes since V1:
- Moved common bitmasks to dpu_hw_util.h
- Moved common CRC methods to dpu_hw_util.c
- Updated copyrights
- Changed crcs array to a dynamically allocated array and added it as a
   member of crtc_state

Signed-off-by: Jessica Zhang 


Please split this into separate patches. One for hw_util, one for the rest


Sure




---
  drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c| 88 +
  drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.h|  4 +
  drivers/gpu/drm/msm/disp/dpu1/dpu_hw_lm.c   | 42 +-
  drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.c | 46 ++-
  drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.h | 16 
  5 files changed, 124 insertions(+), 72 deletions(-)

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
index b56f777dbd0e..16742a66878e 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
@@ -1,5 +1,6 @@
  // SPDX-License-Identifier: GPL-2.0-only
  /*
+ * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
   * Copyright (c) 2014-2021 The Linux Foundation. All rights reserved.
   * Copyright (C) 2013 Red Hat
   * Author: Rob Clark 
@@ -88,6 +89,11 @@ static int dpu_crtc_verify_crc_source(struct drm_crtc *crtc,
 enum dpu_crtc_crc_source source = dpu_crtc_parse_crc_source(src_name);
 struct dpu_crtc_state *crtc_state = to_dpu_crtc_state(crtc->state);

+   if (crtc_state->crcs) {
+   kfree(crtc_state->crcs);
+   crtc_state->crcs = NULL;
+   }
+
 if (source < 0) {
 DRM_DEBUG_DRIVER("Invalid source %s for CRTC%d\n", src_name, 
crtc->index);
 return -EINVAL;
@@ -96,20 +102,37 @@ static int dpu_crtc_verify_crc_source(struct drm_crtc 
*crtc,
 if (source == DPU_CRTC_CRC_SOURCE_LAYER_MIXER)
 *values_cnt = crtc_state->num_mixers;

+   crtc_state->crcs = kcalloc(*values_cnt, sizeof(crtc_state->crcs), 
GFP_KERNEL);
+


I do not quite like the idea of constantly allocating and freeing the
crcs array. I'd suggest defining sensible MAX_CRC_VALUES, using a
static array and verifying that no one over commits the
MAX_CRC_VALUES.
If at some point we decide that we really need the dynamic array, we
can implement it later. We already had dynamic arrays and Rob had to
fix it. See 00326bfa4e63 ("drm/msm/dpu: Remove dynamic allocation from
atomic context").


Ah, got it... the reason I used a dynamic array here was because AFAIK 
we don't have a defined upper limit for how many drm_encoders can be 
connected to a CRTC simultaneously. Do you have a suggestion on what 
value we can set for MAX_CRC_VALUES?





 return 0;
  }

+static void dpu_crtc_setup_lm_misr(struct dpu_crtc_state *crtc_state)
+{
+   struct dpu_crtc_mixer *m;
+   int i;
+
+   for (i = 0; i < crtc_state->num_mixers; ++i) {
+   m = &crtc_state->mixers[i];
+
+   if (!m->hw_lm || !m->hw_lm->ops.setup_misr)
+   continue;
+
+   /* Calculate MISR over 1 frame */
+   m->hw_lm->ops.setup_misr(m->hw_lm, true, 1);
+   }
+}
+
  static int dpu_crtc_set_crc_source(struct drm_crtc *crtc, const char 
*src_name)
  {
 enum dpu_crtc_crc_source source = dpu_crtc_parse_crc_source(src_name);
 enum dpu_crtc_crc_source current_source;
 struct dpu_crtc_state *crtc_state;
 struct drm_device *drm_dev = crtc->dev;
-   struct dpu_crtc_mixer *m;

 bool was_enabled;
 bool enable = false;
-   int i, ret = 0;
+   int ret = 0;

 if (source < 0) {
 DRM_DEBUG_DRIVER("Invalid CRC source %s for CRTC%d\n", src_name, 
crtc->index);
@@ -137,6 +160,10 @@ static int dpu_crtc_set_crc_source(struct drm_crtc *crtc, 
const char *src_name)
 goto cleanup;

 } else if (was_enabled && !enable) {
+   if (crtc_state->crcs) {
+   kfree(crtc_state->crcs);
+   crtc_state->crcs = NULL;
+   }
 drm_crtc_vblank_put(crtc);
 }

@@ -146,16 +173,8 @@ static int dpu_crtc_set_crc_source(struct drm_crtc *crtc, 
const char *src_name)

 crtc_state->crc_frame_skip_count = 0;

-   for (i = 0; i < crtc_state->num_mixers; ++i) {
-   m = &crtc_state->mixers[i];
-
-   if (!m->hw_lm || !m->hw_lm->ops.setup_misr)
-   continue;
-
-   /* Calculate MISR over 1 frame */
-   m->hw_lm->ops.setup_misr(m->hw_lm, true, 1);
-   }
-
+   if (source == DPU_CRTC_CRC_SOURCE_LAYER_MIXER)
+   dpu_crtc_setup

Re: [PATCH v2 3/3] drm/msm/dpu: Add interface support for CRC debugfs

2022-06-15 Thread Jessica Zhang




On 6/15/2022 2:44 AM, Dmitry Baryshkov wrote:

On Wed, 15 Jun 2022 at 00:13, Jessica Zhang  wrote:


Add support for writing CRC values for the interface block to
the debugfs by calling the necessary MISR setup/collect methods.

Changes since V1:
- Set values_cnt to only include phys with backing hw_intf
- Loop over all drm_encs connected to crtc

Signed-off-by: Jessica Zhang 
---
  drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c| 49 ++--
  drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.h|  3 +
  drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c | 64 +
  drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.h | 22 +++
  4 files changed, 134 insertions(+), 4 deletions(-)

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
index 16742a66878e..8c9933b2337f 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
@@ -79,6 +79,8 @@ static enum dpu_crtc_crc_source 
dpu_crtc_parse_crc_source(const char *src_name)
 if (!strcmp(src_name, "auto") ||
 !strcmp(src_name, "lm"))
 return DPU_CRTC_CRC_SOURCE_LAYER_MIXER;
+   if (!strcmp(src_name, "intf"))
+   return DPU_CRTC_CRC_SOURCE_INTF;


What about "encoder" / DPU_CRTC_CRC_SOURCE_ENCODER? You basically
offload CRC generation/collection to the dpu_encoder, so I'd ignore
the fact that only INTF's support MISR generation and use a more
generic word here.



 return DPU_CRTC_CRC_SOURCE_INVALID;
  }
@@ -99,8 +101,14 @@ static int dpu_crtc_verify_crc_source(struct drm_crtc *crtc,
 return -EINVAL;
 }

-   if (source == DPU_CRTC_CRC_SOURCE_LAYER_MIXER)
+   if (source == DPU_CRTC_CRC_SOURCE_LAYER_MIXER) {
 *values_cnt = crtc_state->num_mixers;
+   } else if (source == DPU_CRTC_CRC_SOURCE_INTF) {
+   struct drm_encoder *drm_enc;


Zero values_cnt here.


Noted.




+
+   drm_for_each_encoder_mask(drm_enc, crtc->dev, 
crtc->state->encoder_mask)
+   *values_cnt += dpu_encoder_get_num_phys(drm_enc);
+   }

 crtc_state->crcs = kcalloc(*values_cnt, sizeof(crtc_state->crcs), 
GFP_KERNEL);

@@ -123,6 +131,14 @@ static void dpu_crtc_setup_lm_misr(struct dpu_crtc_state 
*crtc_state)
 }
  }

+static void dpu_crtc_setup_encoder_misr(struct drm_crtc *crtc)
+{
+   struct drm_encoder *drm_enc;
+
+   drm_for_each_encoder_mask(drm_enc, crtc->dev, crtc->state->encoder_mask)
+   dpu_encoder_setup_misr(drm_enc);
+}
+
  static int dpu_crtc_set_crc_source(struct drm_crtc *crtc, const char 
*src_name)
  {
 enum dpu_crtc_crc_source source = dpu_crtc_parse_crc_source(src_name);
@@ -175,6 +191,8 @@ static int dpu_crtc_set_crc_source(struct drm_crtc *crtc, 
const char *src_name)

 if (source == DPU_CRTC_CRC_SOURCE_LAYER_MIXER)
 dpu_crtc_setup_lm_misr(crtc_state);
+   else if (source == DPU_CRTC_CRC_SOURCE_INTF)
+   dpu_crtc_setup_encoder_misr(crtc);


else? >


  cleanup:
 drm_modeset_unlock(&crtc->mutex);
@@ -220,11 +238,31 @@ static int dpu_crtc_get_lm_crc(struct drm_crtc *crtc, 
struct dpu_crtc_state *crt
 drm_crtc_accurate_vblank_count(crtc), 
crtc_state->crcs);
  }

-static int dpu_crtc_get_crc(struct drm_crtc *crtc)
+static int dpu_crtc_get_encoder_crc(struct drm_crtc *crtc)
  {
-   struct dpu_crtc_state *crtc_state;
+   struct drm_encoder *drm_enc;
+   struct dpu_crtc_state *crtc_state = to_dpu_crtc_state(crtc->state);
+   int rc, pos = 0;

-   crtc_state = to_dpu_crtc_state(crtc->state);
+   drm_for_each_encoder_mask(drm_enc, crtc->dev, 
crtc->state->encoder_mask) {
+   rc = dpu_encoder_get_crc(drm_enc, crtc_state->crcs, pos);
+   if (rc < 0) {
+   if (rc != -ENODATA)
+   DRM_DEBUG_DRIVER("MISR read failed\n");
+
+   return rc;
+   }
+
+   pos += rc;
+   }
+
+   return drm_crtc_add_crc_entry(crtc, true,
+   drm_crtc_accurate_vblank_count(crtc), crtc_state->crcs);
+}
+
+static int dpu_crtc_get_crc(struct drm_crtc *crtc)
+{
+   struct dpu_crtc_state *crtc_state = to_dpu_crtc_state(crtc->state);


Unnecessary change here. Please move it to the patch 1, which
refactors this function.


Noted.





 /* Skip first 2 frames in case of "uncooked" CRCs */
 if (crtc_state->crc_frame_skip_count < 2) {
@@ -235,6 +273,9 @@ static int dpu_crtc_get_crc(struct drm_crtc *crtc)
 if (crtc_state->crc_source == DPU_CRTC_CRC_SOURCE_LAYER_MIXER)
 return dpu_crtc_get_lm_crc(crtc, crtc_state);

+   if (crtc_state->crc_source == DPU_CRTC_CRC_SOURCE_INTF)
+   return dpu_crtc_get_encoder_crc(crtc);
+
 return 0;
  }

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.h 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.h
in

Re: [PATCH v2 1/3] drm/msm/dpu: Move LM CRC code into separate method

2022-06-15 Thread Dmitry Baryshkov

On 15/06/2022 19:11, Jessica Zhang wrote:

On 6/15/2022 2:35 AM, Dmitry Baryshkov wrote:
On Wed, 15 Jun 2022 at 00:13, Jessica Zhang 
 wrote:


Move layer mixer-specific section of dpu_crtc_get_crc() into a separate
helper method. This way, we can make it easier to get CRCs from other HW
blocks by adding other get_crc helper methods.

Changes since V1:
- Moved common bitmasks to dpu_hw_util.h
- Moved common CRC methods to dpu_hw_util.c
- Updated copyrights
- Changed crcs array to a dynamically allocated array and added it as a
   member of crtc_state

Signed-off-by: Jessica Zhang 


Please split this into separate patches. One for hw_util, one for the 
rest


Sure




---
  drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c    | 88 +
  drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.h    |  4 +
  drivers/gpu/drm/msm/disp/dpu1/dpu_hw_lm.c   | 42 +-
  drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.c | 46 ++-
  drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.h | 16 
  5 files changed, 124 insertions(+), 72 deletions(-)

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c

index b56f777dbd0e..16742a66878e 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c
@@ -1,5 +1,6 @@
  // SPDX-License-Identifier: GPL-2.0-only
  /*
+ * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights 
reserved.

   * Copyright (c) 2014-2021 The Linux Foundation. All rights reserved.
   * Copyright (C) 2013 Red Hat
   * Author: Rob Clark 
@@ -88,6 +89,11 @@ static int dpu_crtc_verify_crc_source(struct 
drm_crtc *crtc,
 enum dpu_crtc_crc_source source = 
dpu_crtc_parse_crc_source(src_name);
 struct dpu_crtc_state *crtc_state = 
to_dpu_crtc_state(crtc->state);


+   if (crtc_state->crcs) {
+   kfree(crtc_state->crcs);
+   crtc_state->crcs = NULL;
+   }
+
 if (source < 0) {
 DRM_DEBUG_DRIVER("Invalid source %s for CRTC%d\n", 
src_name, crtc->index);

 return -EINVAL;
@@ -96,20 +102,37 @@ static int dpu_crtc_verify_crc_source(struct 
drm_crtc *crtc,

 if (source == DPU_CRTC_CRC_SOURCE_LAYER_MIXER)
 *values_cnt = crtc_state->num_mixers;

+   crtc_state->crcs = kcalloc(*values_cnt, 
sizeof(crtc_state->crcs), GFP_KERNEL);

+


I do not quite like the idea of constantly allocating and freeing the
crcs array. I'd suggest defining sensible MAX_CRC_VALUES, using a
static array and verifying that no one over commits the
MAX_CRC_VALUES.
If at some point we decide that we really need the dynamic array, we
can implement it later. We already had dynamic arrays and Rob had to
fix it. See 00326bfa4e63 ("drm/msm/dpu: Remove dynamic allocation from
atomic context").


Ah, got it... the reason I used a dynamic array here was because AFAIK 
we don't have a defined upper limit for how many drm_encoders can be 
connected to a CRTC simultaneously. Do you have a suggestion on what 
value we can set for MAX_CRC_VALUES?


Three? Two for two hw_intfs?


--
With best wishes
Dmitry


[PATCH] drm/msm: Fix fence rollover issue

2022-06-15 Thread Rob Clark
From: Rob Clark 

And while we are at it, let's start the fence counter close to the
rollover point so that if issues slip in, they are more obvious.

Signed-off-by: Rob Clark 
---
 drivers/gpu/drm/msm/msm_fence.c | 13 +++--
 1 file changed, 11 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/msm/msm_fence.c b/drivers/gpu/drm/msm/msm_fence.c
index 3df255402a33..a35a6746c7cd 100644
--- a/drivers/gpu/drm/msm/msm_fence.c
+++ b/drivers/gpu/drm/msm/msm_fence.c
@@ -28,6 +28,14 @@ msm_fence_context_alloc(struct drm_device *dev, volatile 
uint32_t *fenceptr,
fctx->fenceptr = fenceptr;
spin_lock_init(&fctx->spinlock);
 
+   /*
+* Start out close to the 32b fence rollover point, so we can
+* catch bugs with fence comparisons.
+*/
+   fctx->last_fence = 0xff00;
+   fctx->completed_fence = fctx->last_fence;
+   *fctx->fenceptr = fctx->last_fence;
+
return fctx;
 }
 
@@ -46,11 +54,12 @@ bool msm_fence_completed(struct msm_fence_context *fctx, 
uint32_t fence)
(int32_t)(*fctx->fenceptr - fence) >= 0;
 }
 
-/* called from workqueue */
+/* called from irq handler */
 void msm_update_fence(struct msm_fence_context *fctx, uint32_t fence)
 {
spin_lock(&fctx->spinlock);
-   fctx->completed_fence = max(fence, fctx->completed_fence);
+   if (fence_after(fence, fctx->completed_fence))
+   fctx->completed_fence = fence;
spin_unlock(&fctx->spinlock);
 }
 
-- 
2.36.1



Re: [PATCH -next] drm/bridge: it6505: Add missing CRYPTO_HASH dependency

2022-06-15 Thread Robert Foss
On Mon, 13 Jun 2022 at 16:54, Zheng Bin  wrote:
>
> The driver uses crypto hash functions so it needs to select CRYPTO_HASH.
> This fixes build errors:
>
> drivers/gpu/drm/bridge/ite-it6505.o: in function `it6505_hdcp_wait_ksv_list':
> ite-it6505.c:(.text+0x4c26): undefined reference to `crypto_alloc_shash'
> ite-it6505.c:(.text+0x4c6d): undefined reference to `crypto_shash_digest'
> ite-it6505.c:(.text+0x4c7d): undefined reference to `crypto_destroy_tfm'
> ite-it6505.c:(.text+0x4d69): undefined reference to `crypto_destroy_tfm'
>
> Fixes: b5c84a9edcd4 ("drm/bridge: add it6505 driver")
> Signed-off-by: Zheng Bin 
> ---
>  drivers/gpu/drm/bridge/Kconfig | 2 ++
>  1 file changed, 2 insertions(+)
>
> diff --git a/drivers/gpu/drm/bridge/Kconfig b/drivers/gpu/drm/bridge/Kconfig
> index 8ffd601e68f9..1afe99dac0ff 100644
> --- a/drivers/gpu/drm/bridge/Kconfig
> +++ b/drivers/gpu/drm/bridge/Kconfig
> @@ -94,6 +94,8 @@ config DRM_ITE_IT6505
>  select DRM_KMS_HELPER
>  select DRM_DP_HELPER
>  select EXTCON
> +select CRYPTO
> +select CRYPTO_HASH
>  help
>ITE IT6505 DisplayPort bridge chip driver.
>
> --
> 2.31.1
>

Reviewed-by: Robert Foss 

Applied to drm-misc-next


[PATCH] drm/msm: Fix %d vs %u

2022-06-15 Thread Rob Clark
From: Rob Clark 

In debugging fence rollover, I noticed that GPU state capture and
devcore dumps were showing me negative fence numbers.  Let's fix that
and some related signed vs unsigned confusion.

Signed-off-by: Rob Clark 
---
 drivers/gpu/drm/msm/adreno/adreno_gpu.c | 10 +-
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/drivers/gpu/drm/msm/adreno/adreno_gpu.c 
b/drivers/gpu/drm/msm/adreno/adreno_gpu.c
index dd044d557c7c..ce3b508b7c2b 100644
--- a/drivers/gpu/drm/msm/adreno/adreno_gpu.c
+++ b/drivers/gpu/drm/msm/adreno/adreno_gpu.c
@@ -790,11 +790,11 @@ void adreno_show(struct msm_gpu *gpu, struct 
msm_gpu_state *state,
for (i = 0; i < gpu->nr_rings; i++) {
drm_printf(p, "  - id: %d\n", i);
drm_printf(p, "iova: 0x%016llx\n", state->ring[i].iova);
-   drm_printf(p, "last-fence: %d\n", state->ring[i].seqno);
-   drm_printf(p, "retired-fence: %d\n", state->ring[i].fence);
-   drm_printf(p, "rptr: %d\n", state->ring[i].rptr);
-   drm_printf(p, "wptr: %d\n", state->ring[i].wptr);
-   drm_printf(p, "size: %d\n", MSM_GPU_RINGBUFFER_SZ);
+   drm_printf(p, "last-fence: %u\n", state->ring[i].seqno);
+   drm_printf(p, "retired-fence: %u\n", state->ring[i].fence);
+   drm_printf(p, "rptr: %u\n", state->ring[i].rptr);
+   drm_printf(p, "wptr: %u\n", state->ring[i].wptr);
+   drm_printf(p, "size: %u\n", MSM_GPU_RINGBUFFER_SZ);
 
adreno_show_object(p, &state->ring[i].data,
state->ring[i].data_size, &state->ring[i].encoded);
-- 
2.36.1



Re: [PATCH 1/3] drm/msm/dpu: move intf and wb assignment to dpu_encoder_setup_display()

2022-06-15 Thread Abhinav Kumar




On 6/15/2022 5:36 AM, Dmitry Baryshkov wrote:

On 14/06/2022 22:32, Abhinav Kumar wrote:

intf and wb resources are not dependent on the rm global
state so need not be allocated during dpu_encoder_virt_atomic_mode_set().

Move the allocation of intf and wb resources to 
dpu_encoder_setup_display()

so that we can utilize the hw caps even during atomic_check() phase.

Since dpu_encoder_setup_display() already has protection against
setting invalid intf_idx and wb_idx, these checks can now
be dropped as well.

Fixes: e02a559a720f ("make changes to dpu_encoder to support virtual 
encoder")

Signed-off-by: Abhinav Kumar 
---
  drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c | 25 
+++--

  1 file changed, 7 insertions(+), 18 deletions(-)

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c

index 3a462e327e0e..e991d4ba8a40 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
@@ -1048,24 +1048,6 @@ static void 
dpu_encoder_virt_atomic_mode_set(struct drm_encoder *drm_enc,

  phys->hw_pp = dpu_enc->hw_pp[i];
  phys->hw_ctl = to_dpu_hw_ctl(hw_ctl[i]);
-    if (phys->intf_idx >= INTF_0 && phys->intf_idx < INTF_MAX)
-    phys->hw_intf = dpu_rm_get_intf(&dpu_kms->rm, 
phys->intf_idx);

-
-    if (phys->wb_idx >= WB_0 && phys->wb_idx < WB_MAX)
-    phys->hw_wb = dpu_rm_get_wb(&dpu_kms->rm, phys->wb_idx);
-
-    if (!phys->hw_intf && !phys->hw_wb) {
-    DPU_ERROR_ENC(dpu_enc,
-  "no intf or wb block assigned at idx: %d\n", i);
-    return;
-    }
-
-    if (phys->hw_intf && phys->hw_wb) {
-    DPU_ERROR_ENC(dpu_enc,
-    "invalid phys both intf and wb block at idx: 
%d\n", i);

-    return;
-    }


Please retain these checks in dpu_encoder_setup_display().
It checks that we really have got the intf or wb. For example one might 
have specified the INTF that leads to INTF_NONE interface. Or 
non-existing/not supported WB.


Right, so the reason I omitted that was dpu_encoder_setup_display() 
already has these checks:


https://gitlab.freedesktop.org/drm/msm/-/blob/msm-next/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c#L2273

Please check lines 2273-2284.

Only if all those checks succeeded we call 
dpu_encoder_virt_add_phys_encs which increments num_phys_encs.


Thats why I dropped those.

Let me know if you have more questions.




-
  phys->cached_mode = crtc_state->adjusted_mode;
  if (phys->ops.atomic_mode_set)
  phys->ops.atomic_mode_set(phys, crtc_state, conn_state);
@@ -2293,7 +2275,14 @@ static int dpu_encoder_setup_display(struct 
dpu_encoder_virt *dpu_enc,

  struct dpu_encoder_phys *phys = dpu_enc->phys_encs[i];
  atomic_set(&phys->vsync_cnt, 0);
  atomic_set(&phys->underrun_cnt, 0);
+
+    if (phys->intf_idx >= INTF_0 && phys->intf_idx < INTF_MAX)
+    phys->hw_intf = dpu_rm_get_intf(&dpu_kms->rm, 
phys->intf_idx);

+
+    if (phys->wb_idx >= WB_0 && phys->wb_idx < WB_MAX)
+    phys->hw_wb = dpu_rm_get_wb(&dpu_kms->rm, phys->wb_idx);
  }
+
  mutex_unlock(&dpu_enc->enc_lock);
  return ret;





Re: [PATCH] drm/radeon: Replace drm_detect_hdmi_monitor() with drm_display_info.is_hdmi

2022-06-15 Thread Alex Deucher
On Wed, Jun 15, 2022 at 8:33 AM hongao  wrote:
>
> Replace drm_detect_hdmi_monitor() with drm_display_info.is_hdmi for more
> efficiency
>
> Tested on "Oland [Radeon HD 8570 / R7 240/340 OEM]" & "Caicos [R5 230]"

Can you verify that drm_display_info.is_hdmi has been populated when
all of these functions are called?

Alex

>
> Signed-off-by: hongao 
> ---
>  drivers/gpu/drm/radeon/atombios_encoders.c |  6 +++---
>  drivers/gpu/drm/radeon/radeon_connectors.c | 12 ++--
>  drivers/gpu/drm/radeon/radeon_display.c|  2 +-
>  drivers/gpu/drm/radeon/radeon_encoders.c   |  4 ++--
>  4 files changed, 12 insertions(+), 12 deletions(-)
>
> diff --git a/drivers/gpu/drm/radeon/atombios_encoders.c 
> b/drivers/gpu/drm/radeon/atombios_encoders.c
> index 70bd84b7ef2b..393d471ba396 100644
> --- a/drivers/gpu/drm/radeon/atombios_encoders.c
> +++ b/drivers/gpu/drm/radeon/atombios_encoders.c
> @@ -714,7 +714,7 @@ atombios_get_encoder_mode(struct drm_encoder *encoder)
> if (radeon_connector->use_digital &&
> (radeon_connector->audio == RADEON_AUDIO_ENABLE))
> return ATOM_ENCODER_MODE_HDMI;
> -   else if 
> (drm_detect_hdmi_monitor(radeon_connector_edid(connector)) &&
> +   else if (connector->display_info.is_hdmi &&
>  (radeon_connector->audio == 
> RADEON_AUDIO_AUTO))
> return ATOM_ENCODER_MODE_HDMI;
> else if (radeon_connector->use_digital)
> @@ -733,7 +733,7 @@ atombios_get_encoder_mode(struct drm_encoder *encoder)
> if (radeon_audio != 0) {
> if (radeon_connector->audio == RADEON_AUDIO_ENABLE)
> return ATOM_ENCODER_MODE_HDMI;
> -   else if 
> (drm_detect_hdmi_monitor(radeon_connector_edid(connector)) &&
> +   else if (connector->display_info.is_hdmi &&
>  (radeon_connector->audio == 
> RADEON_AUDIO_AUTO))
> return ATOM_ENCODER_MODE_HDMI;
> else
> @@ -757,7 +757,7 @@ atombios_get_encoder_mode(struct drm_encoder *encoder)
> } else if (radeon_audio != 0) {
> if (radeon_connector->audio == RADEON_AUDIO_ENABLE)
> return ATOM_ENCODER_MODE_HDMI;
> -   else if 
> (drm_detect_hdmi_monitor(radeon_connector_edid(connector)) &&
> +   else if (connector->display_info.is_hdmi &&
>  (radeon_connector->audio == 
> RADEON_AUDIO_AUTO))
> return ATOM_ENCODER_MODE_HDMI;
> else
> diff --git a/drivers/gpu/drm/radeon/radeon_connectors.c 
> b/drivers/gpu/drm/radeon/radeon_connectors.c
> index 58db79921cd3..2fbec7bdd56b 100644
> --- a/drivers/gpu/drm/radeon/radeon_connectors.c
> +++ b/drivers/gpu/drm/radeon/radeon_connectors.c
> @@ -130,7 +130,7 @@ int radeon_get_monitor_bpc(struct drm_connector 
> *connector)
> case DRM_MODE_CONNECTOR_DVII:
> case DRM_MODE_CONNECTOR_HDMIB:
> if (radeon_connector->use_digital) {
> -   if 
> (drm_detect_hdmi_monitor(radeon_connector_edid(connector))) {
> +   if (connector->display_info.is_hdmi) {
> if (connector->display_info.bpc)
> bpc = connector->display_info.bpc;
> }
> @@ -138,7 +138,7 @@ int radeon_get_monitor_bpc(struct drm_connector 
> *connector)
> break;
> case DRM_MODE_CONNECTOR_DVID:
> case DRM_MODE_CONNECTOR_HDMIA:
> -   if 
> (drm_detect_hdmi_monitor(radeon_connector_edid(connector))) {
> +   if (connector->display_info.is_hdmi) {
> if (connector->display_info.bpc)
> bpc = connector->display_info.bpc;
> }
> @@ -147,7 +147,7 @@ int radeon_get_monitor_bpc(struct drm_connector 
> *connector)
> dig_connector = radeon_connector->con_priv;
> if ((dig_connector->dp_sink_type == 
> CONNECTOR_OBJECT_ID_DISPLAYPORT) ||
> (dig_connector->dp_sink_type == CONNECTOR_OBJECT_ID_eDP) 
> ||
> -   
> drm_detect_hdmi_monitor(radeon_connector_edid(connector))) {
> +   connector->display_info.is_hdmi) {
> if (connector->display_info.bpc)
> bpc = connector->display_info.bpc;
> }
> @@ -171,7 +171,7 @@ int radeon_get_monitor_bpc(struct drm_connector 
> *connector)
> break;
> }
>
> -   if (drm_detect_hdmi_monitor(radeon_connector_edid(connector))) {
> +   if (connector->display_info.is_hdmi) {
> /* hdmi deep color only impleme

Re: [PATCH v2 6/7] drm/bridge: anx7625: Register Type-C mode switches

2022-06-15 Thread Prashant Malani
On Wed, Jun 15, 2022 at 1:45 AM AngeloGioacchino Del Regno
 wrote:
>
> Il 14/06/22 18:57, Prashant Malani ha scritto:
> > On Tue, Jun 14, 2022 at 1:18 AM AngeloGioacchino Del Regno
> >  wrote:
> >>
> >> Il 09/06/22 20:09, Prashant Malani ha scritto:
> >>> When the DT node has "switches" available, register a Type-C mode-switch
> >>> for each listed "switch". This allows the driver to receive state
> >>> information about what operating mode a Type-C port and its connected
> >>> peripherals are in, as well as status information (like VDOs) related to
> >>> that state.
> >>>
> >>> The callback function is currently a stub, but subsequent patches will
> >>> implement the required functionality.
> >>>
> >>> Signed-off-by: Prashant Malani 
> >>> ---
> >>>
> >>> Changes since v2:
> >>> - No changes.
> >>>
> >>>drivers/gpu/drm/bridge/analogix/anx7625.c | 73 +++
> >>>drivers/gpu/drm/bridge/analogix/anx7625.h |  6 ++
> >>>2 files changed, 79 insertions(+)
> >>>
> >>> diff --git a/drivers/gpu/drm/bridge/analogix/anx7625.c 
> >>> b/drivers/gpu/drm/bridge/analogix/anx7625.c
> >>> index 07ed44c6b839..d41a21103bd3 100644
> >>> --- a/drivers/gpu/drm/bridge/analogix/anx7625.c
> >>> +++ b/drivers/gpu/drm/bridge/analogix/anx7625.c
> >>> @@ -15,6 +15,7 @@
> >>>#include 
> >>>#include 
> >>>#include 
> >>> +#include 
> >>>#include 
> >>>
> >>>#include 
> >>> @@ -2581,9 +2582,59 @@ static void anx7625_runtime_disable(void *data)
> >>>pm_runtime_disable(data);
> >>>}
> >>>
> >>> +static int anx7625_typec_mux_set(struct typec_mux_dev *mux,
> >>> +  struct typec_mux_state *state)
> >>> +{
> >>> + return 0;
> >>> +}
> >>> +
> >>> +static int anx7625_register_mode_switch(struct device *dev, struct 
> >>> device_node *node,
> >>> + struct anx7625_data *ctx)
> >>> +{
> >>> + struct anx7625_port_data *port_data;
> >>> + struct typec_mux_desc mux_desc = {};
> >>> + char name[32];
> >>> + u32 port_num;
> >>> + int ret;
> >>> +
> >>> + ret = of_property_read_u32(node, "reg", &port_num);
> >>> + if (ret)
> >>> + return ret;
> >>> +
> >>> + if (port_num >= ctx->num_typec_switches) {
> >>> + dev_err(dev, "Invalid port number specified: %d\n", 
> >>> port_num);
> >>> + return -EINVAL;
> >>> + }
> >>> +
> >>> + port_data = &ctx->typec_ports[port_num];
> >>> + port_data->ctx = ctx;
> >>> + mux_desc.fwnode = &node->fwnode;
> >>> + mux_desc.drvdata = port_data;
> >>> + snprintf(name, sizeof(name), "%s-%u", node->name, port_num);
> >>> + mux_desc.name = name;
> >>> + mux_desc.set = anx7625_typec_mux_set;
> >>> +
> >>> + port_data->typec_mux = typec_mux_register(dev, &mux_desc);
> >>> + if (IS_ERR(port_data->typec_mux)) {
> >>> + ret = PTR_ERR(port_data->typec_mux);
> >>> + dev_err(dev, "Mode switch register for port %d failed: %d", 
> >>> port_num, ret);
> >>> + }
> >>
> >> Please return 0 at the end of this function.
> >>
> >>  if (IS_ERR()) {
> >>  ..code..
> >>  return ret;
> >>  }
> >>
> >>  return 0;
> >> }
> >
> > May I ask why? We're not missing any return paths. I would rather we
> > keep it as is (which has the valid return value).
> >
>
> I know that you're not missing any return paths.
>
> That's only because the proposed one is a common pattern in the kernel
> and it's only for consistency.

Thanks for the additional details. Since this isn't addressing any
specific bug, and I
notice varied usages of "return ret" in this file itself [1][2], I'd
prefer keeping it as is.

[1]: 
https://elixir.bootlin.com/linux/latest/source/drivers/gpu/drm/bridge/analogix/anx7625.c#L296
[2]: 
https://elixir.bootlin.com/linux/latest/source/drivers/gpu/drm/bridge/analogix/anx7625.c#L436

>
> Regards,
> Angelo
>


Re: [PATCH 1/3] drm/msm/dpu: move intf and wb assignment to dpu_encoder_setup_display()

2022-06-15 Thread Dmitry Baryshkov

On 15/06/2022 19:40, Abhinav Kumar wrote:



On 6/15/2022 5:36 AM, Dmitry Baryshkov wrote:

On 14/06/2022 22:32, Abhinav Kumar wrote:

intf and wb resources are not dependent on the rm global
state so need not be allocated during 
dpu_encoder_virt_atomic_mode_set().


Move the allocation of intf and wb resources to 
dpu_encoder_setup_display()

so that we can utilize the hw caps even during atomic_check() phase.

Since dpu_encoder_setup_display() already has protection against
setting invalid intf_idx and wb_idx, these checks can now
be dropped as well.

Fixes: e02a559a720f ("make changes to dpu_encoder to support virtual 
encoder")

Signed-off-by: Abhinav Kumar 
---
  drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c | 25 
+++--

  1 file changed, 7 insertions(+), 18 deletions(-)

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c

index 3a462e327e0e..e991d4ba8a40 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
@@ -1048,24 +1048,6 @@ static void 
dpu_encoder_virt_atomic_mode_set(struct drm_encoder *drm_enc,

  phys->hw_pp = dpu_enc->hw_pp[i];
  phys->hw_ctl = to_dpu_hw_ctl(hw_ctl[i]);
-    if (phys->intf_idx >= INTF_0 && phys->intf_idx < INTF_MAX)
-    phys->hw_intf = dpu_rm_get_intf(&dpu_kms->rm, 
phys->intf_idx);

-
-    if (phys->wb_idx >= WB_0 && phys->wb_idx < WB_MAX)
-    phys->hw_wb = dpu_rm_get_wb(&dpu_kms->rm, phys->wb_idx);
-
-    if (!phys->hw_intf && !phys->hw_wb) {
-    DPU_ERROR_ENC(dpu_enc,
-  "no intf or wb block assigned at idx: %d\n", i);
-    return;
-    }
-
-    if (phys->hw_intf && phys->hw_wb) {
-    DPU_ERROR_ENC(dpu_enc,
-    "invalid phys both intf and wb block at idx: 
%d\n", i);

-    return;
-    }


Please retain these checks in dpu_encoder_setup_display().
It checks that we really have got the intf or wb. For example one 
might have specified the INTF that leads to INTF_NONE interface. Or 
non-existing/not supported WB.


Right, so the reason I omitted that was dpu_encoder_setup_display() 
already has these checks:


https://gitlab.freedesktop.org/drm/msm/-/blob/msm-next/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c#L2273 



Please check lines 2273-2284.

Only if all those checks succeeded we call 
dpu_encoder_virt_add_phys_encs which increments num_phys_encs.


As I wrote, it checks indices from phys_params, but not the acquired 
hardware instances.




Thats why I dropped those.

Let me know if you have more questions.




-
  phys->cached_mode = crtc_state->adjusted_mode;
  if (phys->ops.atomic_mode_set)
  phys->ops.atomic_mode_set(phys, crtc_state, conn_state);
@@ -2293,7 +2275,14 @@ static int dpu_encoder_setup_display(struct 
dpu_encoder_virt *dpu_enc,

  struct dpu_encoder_phys *phys = dpu_enc->phys_encs[i];
  atomic_set(&phys->vsync_cnt, 0);
  atomic_set(&phys->underrun_cnt, 0);
+
+    if (phys->intf_idx >= INTF_0 && phys->intf_idx < INTF_MAX)
+    phys->hw_intf = dpu_rm_get_intf(&dpu_kms->rm, 
phys->intf_idx);

+
+    if (phys->wb_idx >= WB_0 && phys->wb_idx < WB_MAX)
+    phys->hw_wb = dpu_rm_get_wb(&dpu_kms->rm, phys->wb_idx);
  }
+
  mutex_unlock(&dpu_enc->enc_lock);
  return ret;






--
With best wishes
Dmitry


Re: [Intel-gfx] [PATCH 2/6] drm/i915/gt: Invalidate TLB of the OA unit at TLB invalidations

2022-06-15 Thread Umesh Nerlige Ramappa

On Wed, Jun 15, 2022 at 04:27:36PM +0100, Mauro Carvalho Chehab wrote:

From: Chris Wilson 

On gen12 HW, ensure that the TLB of the OA unit is also invalidated
as just invalidating the TLB of an engine is not enough.

Fixes: 7938d61591d3 ("drm/i915: Flush TLBs before releasing backing store")

Signed-off-by: Chris Wilson 
Cc: Fei Yang 
Cc: Andi Shyti 
Cc: sta...@vger.kernel.org
Acked-by: Thomas Hellström 
Signed-off-by: Mauro Carvalho Chehab 
---

See [PATCH 0/6] at: 
https://lore.kernel.org/all/cover.1655306128.git.mche...@kernel.org/

drivers/gpu/drm/i915/gt/intel_gt.c | 10 ++
1 file changed, 10 insertions(+)

diff --git a/drivers/gpu/drm/i915/gt/intel_gt.c 
b/drivers/gpu/drm/i915/gt/intel_gt.c
index d5ed6a6ac67c..61b7ec5118f9 100644
--- a/drivers/gpu/drm/i915/gt/intel_gt.c
+++ b/drivers/gpu/drm/i915/gt/intel_gt.c
@@ -10,6 +10,7 @@
#include "pxp/intel_pxp.h"

#include "i915_drv.h"
+#include "i915_perf_oa_regs.h"
#include "intel_context.h"
#include "intel_engine_pm.h"
#include "intel_engine_regs.h"
@@ -1259,6 +1260,15 @@ void intel_gt_invalidate_tlbs(struct intel_gt *gt)
awake |= engine->mask;
}

+   /* Wa_2207587034:tgl,dg1,rkl,adl-s,adl-p */
+   if (awake &&
+   (IS_TIGERLAKE(i915) ||
+IS_DG1(i915) ||
+IS_ROCKETLAKE(i915) ||
+IS_ALDERLAKE_S(i915) ||
+IS_ALDERLAKE_P(i915)))
+   intel_uncore_write_fw(uncore, GEN12_OA_TLB_INV_CR, 1);
+


This patch can be dropped since this is being done in i915/i915_perf.c 
-> gen12_oa_disable and is synchronized with OA use cases.


Regards,
Umesh



for_each_engine_masked(engine, gt, awake, tmp) {
struct reg_and_bit rb;

--
2.36.1



Re: [PATCH 1/3] drm/msm/dpu: move intf and wb assignment to dpu_encoder_setup_display()

2022-06-15 Thread Abhinav Kumar




On 6/15/2022 10:04 AM, Dmitry Baryshkov wrote:

On 15/06/2022 19:40, Abhinav Kumar wrote:



On 6/15/2022 5:36 AM, Dmitry Baryshkov wrote:

On 14/06/2022 22:32, Abhinav Kumar wrote:

intf and wb resources are not dependent on the rm global
state so need not be allocated during 
dpu_encoder_virt_atomic_mode_set().


Move the allocation of intf and wb resources to 
dpu_encoder_setup_display()

so that we can utilize the hw caps even during atomic_check() phase.

Since dpu_encoder_setup_display() already has protection against
setting invalid intf_idx and wb_idx, these checks can now
be dropped as well.

Fixes: e02a559a720f ("make changes to dpu_encoder to support virtual 
encoder")

Signed-off-by: Abhinav Kumar 
---
  drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c | 25 
+++--

  1 file changed, 7 insertions(+), 18 deletions(-)

diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c 
b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c

index 3a462e327e0e..e991d4ba8a40 100644
--- a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
+++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c
@@ -1048,24 +1048,6 @@ static void 
dpu_encoder_virt_atomic_mode_set(struct drm_encoder *drm_enc,

  phys->hw_pp = dpu_enc->hw_pp[i];
  phys->hw_ctl = to_dpu_hw_ctl(hw_ctl[i]);
-    if (phys->intf_idx >= INTF_0 && phys->intf_idx < INTF_MAX)
-    phys->hw_intf = dpu_rm_get_intf(&dpu_kms->rm, 
phys->intf_idx);

-
-    if (phys->wb_idx >= WB_0 && phys->wb_idx < WB_MAX)
-    phys->hw_wb = dpu_rm_get_wb(&dpu_kms->rm, phys->wb_idx);
-
-    if (!phys->hw_intf && !phys->hw_wb) {
-    DPU_ERROR_ENC(dpu_enc,
-  "no intf or wb block assigned at idx: %d\n", i);
-    return;
-    }
-
-    if (phys->hw_intf && phys->hw_wb) {
-    DPU_ERROR_ENC(dpu_enc,
-    "invalid phys both intf and wb block at idx: 
%d\n", i);

-    return;
-    }


Please retain these checks in dpu_encoder_setup_display().
It checks that we really have got the intf or wb. For example one 
might have specified the INTF that leads to INTF_NONE interface. Or 
non-existing/not supported WB.


Right, so the reason I omitted that was dpu_encoder_setup_display() 
already has these checks:


https://gitlab.freedesktop.org/drm/msm/-/blob/msm-next/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c#L2273 



Please check lines 2273-2284.

Only if all those checks succeeded we call 
dpu_encoder_virt_add_phys_encs which increments num_phys_encs.


As I wrote, it checks indices from phys_params, but not the acquired 
hardware instances.


Right but today, both the get_intf() and get_wb() just return the 
intf/wb corresponding to the index. So as long as the index is valid how 
will checking hw_wb or hw_intf be different?


static inline struct dpu_hw_intf *dpu_rm_get_intf(struct dpu_rm *rm, 
enum dpu_intf intf_idx)

{
return rm->hw_intf[intf_idx - INTF_0];
}

/**
 * dpu_rm_get_wb - Return a struct dpu_hw_wb instance given it's index.
 * @rm: DPU Resource Manager handle
 * @wb_idx: WB index
 */
static inline struct dpu_hw_wb *dpu_rm_get_wb(struct dpu_rm *rm, enum 
dpu_wb wb_idx)

{
return rm->hw_wb[wb_idx - WB_0];
}




Thats why I dropped those.

Let me know if you have more questions.




-
  phys->cached_mode = crtc_state->adjusted_mode;
  if (phys->ops.atomic_mode_set)
  phys->ops.atomic_mode_set(phys, crtc_state, conn_state);
@@ -2293,7 +2275,14 @@ static int dpu_encoder_setup_display(struct 
dpu_encoder_virt *dpu_enc,

  struct dpu_encoder_phys *phys = dpu_enc->phys_encs[i];
  atomic_set(&phys->vsync_cnt, 0);
  atomic_set(&phys->underrun_cnt, 0);
+
+    if (phys->intf_idx >= INTF_0 && phys->intf_idx < INTF_MAX)
+    phys->hw_intf = dpu_rm_get_intf(&dpu_kms->rm, 
phys->intf_idx);

+
+    if (phys->wb_idx >= WB_0 && phys->wb_idx < WB_MAX)
+    phys->hw_wb = dpu_rm_get_wb(&dpu_kms->rm, phys->wb_idx);
  }
+
  mutex_unlock(&dpu_enc->enc_lock);
  return ret;








[PATCH v4 0/7] usb: typec: Introduce typec-switch binding

2022-06-15 Thread Prashant Malani
This series introduces a binding for Type-C data lane switches. These
control the routing and operating modes of USB Type-C data lanes based
on the PD messaging from the Type-C port driver regarding connected
peripherals.

The first patch introduces a change to the Type-C mux class mode-switch
matching code, while the second adds a config guard to a Type-C header.
The next couple of patches introduce the new "typec-switch" binding as
well as one user of it (the ANX7625 drm bridge).

The remaining patches add functionality to the anx7625 driver to
register the mode-switches, as well as program its crosspoint
switch depending on which Type-C port has a DisplayPort (DP) peripheral
connected to it.

v3: 
https://lore.kernel.org/linux-usb/20220614193558.1163205-1-pmal...@chromium.org/

Changes since v3:
- Some more modifications to the anx7625 binding patch (4/7).
- Picked up 1 more Reviewed-by tag.

Pin-Yen Lin (1):
  drm/bridge: anx7625: Add typec_mux_set callback function

Prashant Malani (6):
  usb: typec: mux: Allow muxes to specify mode-switch
  usb: typec: mux: Add CONFIG guards for functions
  dt-bindings: usb: Add Type-C switch binding
  dt-bindings: drm/bridge: anx7625: Add mode-switch support
  drm/bridge: anx7625: Register number of Type C switches
  drm/bridge: anx7625: Register Type-C mode switches

 .../display/bridge/analogix,anx7625.yaml  |  64 
 .../devicetree/bindings/usb/typec-switch.yaml |  74 +
 drivers/gpu/drm/bridge/analogix/anx7625.c | 148 ++
 drivers/gpu/drm/bridge/analogix/anx7625.h |  20 +++
 drivers/usb/typec/mux.c   |   8 +-
 include/linux/usb/typec_mux.h |  44 +-
 6 files changed, 350 insertions(+), 8 deletions(-)
 create mode 100644 Documentation/devicetree/bindings/usb/typec-switch.yaml

-- 
2.36.1.476.g0c4daa206d-goog



[PATCH v4 1/7] usb: typec: mux: Allow muxes to specify mode-switch

2022-06-15 Thread Prashant Malani
Loosen the typec_mux_match() requirements so that searches where an
alt mode is not specified, but the target mux device lists the
"mode-switch" property, return a success.

This is helpful in Type C port drivers which would like to get a pointer
to the mux switch associated with a Type C port, but don't want to
specify a particular alt mode.

Signed-off-by: Prashant Malani 
Reviewed-by: Heikki Krogerus 
Reviewed-by: AngeloGioacchino Del Regno 

Reviewed-by: Nícolas F. R. A. Prado 
Tested-by: Nícolas F. R. A. Prado 
---

Changes since v3:
- No changes.

Changes since v2:
- Included Reviewed-by and Tested-by tags from v2.

Changes since v1:
- No changes.

 drivers/usb/typec/mux.c | 8 ++--
 1 file changed, 6 insertions(+), 2 deletions(-)

diff --git a/drivers/usb/typec/mux.c b/drivers/usb/typec/mux.c
index fd55c2c516a5..464330776cd6 100644
--- a/drivers/usb/typec/mux.c
+++ b/drivers/usb/typec/mux.c
@@ -281,9 +281,13 @@ static void *typec_mux_match(struct fwnode_handle *fwnode, 
const char *id,
if (match)
goto find_mux;
 
-   /* Accessory Mode muxes */
if (!desc) {
-   match = fwnode_property_present(fwnode, "accessory");
+   /*
+* Accessory Mode muxes & muxes which explicitly specify
+* the required identifier can avoid SVID matching.
+*/
+   match = fwnode_property_present(fwnode, "accessory") ||
+   fwnode_property_present(fwnode, id);
if (match)
goto find_mux;
return NULL;
-- 
2.36.1.476.g0c4daa206d-goog



[PATCH v4 2/7] usb: typec: mux: Add CONFIG guards for functions

2022-06-15 Thread Prashant Malani
There are some drivers that can use the Type C mux API, but don't have
to. Introduce CONFIG guards for the mux functions so that drivers can
include the header file and not run into compilation errors on systems
which don't have CONFIG_TYPEC enabled. When CONFIG_TYPEC is not enabled,
the Type C mux functions will be stub versions of the original calls.

Reported-by: kernel test robot 
Reviewed-by: Nícolas F. R. A. Prado 
Tested-by: Nícolas F. R. A. Prado 
Signed-off-by: Prashant Malani 
---

Changes since v3:
- No changes.

Changes since v2:
- Fix up return types for some of the stubs. Remove 1 unnecessary stub
  in the else condition.
- Remove unnecessary IS_MODULE config guard.
- Added Reviewed-by and Tested-by tags.

Changes since v1:
- Added static inline to stub functions.
- Updated function signature of stub functions from "struct typec_mux"
  to "struct typec_mux_dev" in accordance with updates from commit
  713fd49b430c ("usb: typec: mux: Introduce indirection")

 include/linux/usb/typec_mux.h | 44 ++-
 1 file changed, 38 insertions(+), 6 deletions(-)

diff --git a/include/linux/usb/typec_mux.h b/include/linux/usb/typec_mux.h
index ee57781dcf28..9292f0e07846 100644
--- a/include/linux/usb/typec_mux.h
+++ b/include/linux/usb/typec_mux.h
@@ -58,17 +58,13 @@ struct typec_mux_desc {
void *drvdata;
 };
 
+#if IS_ENABLED(CONFIG_TYPEC)
+
 struct typec_mux *fwnode_typec_mux_get(struct fwnode_handle *fwnode,
   const struct typec_altmode_desc *desc);
 void typec_mux_put(struct typec_mux *mux);
 int typec_mux_set(struct typec_mux *mux, struct typec_mux_state *state);
 
-static inline struct typec_mux *
-typec_mux_get(struct device *dev, const struct typec_altmode_desc *desc)
-{
-   return fwnode_typec_mux_get(dev_fwnode(dev), desc);
-}
-
 struct typec_mux_dev *
 typec_mux_register(struct device *parent, const struct typec_mux_desc *desc);
 void typec_mux_unregister(struct typec_mux_dev *mux);
@@ -76,4 +72,40 @@ void typec_mux_unregister(struct typec_mux_dev *mux);
 void typec_mux_set_drvdata(struct typec_mux_dev *mux, void *data);
 void *typec_mux_get_drvdata(struct typec_mux_dev *mux);
 
+#else
+
+static inline struct typec_mux *fwnode_typec_mux_get(struct fwnode_handle 
*fwnode,
+  const struct typec_altmode_desc *desc)
+{
+   return NULL;
+}
+
+static inline void typec_mux_put(struct typec_mux *mux) {}
+
+static inline int typec_mux_set(struct typec_mux *mux, struct typec_mux_state 
*state)
+{
+   return 0;
+}
+
+static inline struct typec_mux_dev *
+typec_mux_register(struct device *parent, const struct typec_mux_desc *desc)
+{
+   return ERR_PTR(-EOPNOTSUPP);
+}
+static inline void typec_mux_unregister(struct typec_mux_dev *mux) {}
+
+static inline void typec_mux_set_drvdata(struct typec_mux_dev *mux, void 
*data) {}
+static inline void *typec_mux_get_drvdata(struct typec_mux_dev *mux)
+{
+   return ERR_PTR(-EOPNOTSUPP);
+}
+
+#endif /* CONFIG_TYPEC */
+
+static inline struct typec_mux *
+typec_mux_get(struct device *dev, const struct typec_altmode_desc *desc)
+{
+   return fwnode_typec_mux_get(dev_fwnode(dev), desc);
+}
+
 #endif /* __USB_TYPEC_MUX */
-- 
2.36.1.476.g0c4daa206d-goog



  1   2   >