[Bug 207383] [Regression] 5.7 amdgpu/polaris11 gpf: amdgpu_atomic_commit_tail
https://bugzilla.kernel.org/show_bug.cgi?id=207383 --- Comment #105 from Duncan (1i5t5.dun...@cox.net) --- (In reply to Duncan from comment #102) > (In reply to Duncan from comment #101) > > (In reply to Nicholas Kazlauskas from comment #95) > > > 0001-drm-amd-display-Force-add-all-CRTCs-to-state-when-us.patch > > > > Just booted to 5.8-rc7 with this patched in > > So far building system updates so heavy cpu load while playing only moderate > FHD video. No freezes but I have seen a bit of the predicted judder. > > The 4k30 and 4k60 youtube tests will probably have to wait for tomorrow, tho, > as I've been up near 24 now... Still up... Here's the promised 4k youtube-in-firefox tests. 4k is a bit more stuttery than normal with the patch, but not near as bad as I expected it to be. I can normally run 4k60 at 80-85% normal speed with occasional stutters but without freezing the video entirely until I drop the speed down again as I often have to do if I try running over that. With the patch I was doing 70-75%. So there's definitely some effect on 4k60. Switching to the performance cpufreq governor from my default conservative, as usual, helps a bit, but not a lot, maybe 5%, tho the frame-freezes seem to recover a bit better on performance. In addition to long video freezes at the full 4k60 100%, even normally I'll sometimes get tab-crashes depending on the video. I didn't have any for this test but then I'm so used to not being able to run at full-speed that I didn't try it for long. I can normally run 4k30 videos without much problem on default conservative. With the patch I was still getting some stuttering at 30fps on conservative, but it pretty much cleared up with on-demand. I did just have a tab-crash at 4k30, something I very rarely if ever see normally on 4k30, it normally takes 4k60 to trigger them, so it's definitely affecting it. But... other than slowing down the usable 4k fps, I'm not seeing any of judder artifacts on the work (non-video-playing) monitor that I was seeing with the high system load but relatively low video load build testing with only FHD video. That surprised me. I expected to see more of that with the more demanding video. But apparently that's tied to CPU or memory load, not video load. But nothing like the problems mnrzk's seeing with the patch, at all. Both monitors running fine in text mode, login, startx to plasma, running fine there too. Hardware cursor's fine. The only thing I'm seeing is some slowdown and judder, as described above. -- You are receiving this mail because: You are watching the assignee of the bug. ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[Linux-kernel-mentees] [PATCH] drm/bufs: Prevent kernel-infoleak in copy_one_buf()
copy_one_buf() is copying uninitialized stack memory to userspace due to the compiler not initializing holes in statically allocated structures. Fix it by initializing `v` with memset(). Cc: sta...@vger.kernel.org Fixes: 5c7640ab6258 ("switch compat_drm_infobufs() to drm_ioctl_kernel()") Suggested-by: Dan Carpenter Signed-off-by: Peilin Ye --- drivers/gpu/drm/drm_bufs.c | 12 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/drivers/gpu/drm/drm_bufs.c b/drivers/gpu/drm/drm_bufs.c index a0735fbc144b..f99cd4a3f951 100644 --- a/drivers/gpu/drm/drm_bufs.c +++ b/drivers/gpu/drm/drm_bufs.c @@ -1349,10 +1349,14 @@ static int copy_one_buf(void *data, int count, struct drm_buf_entry *from) { struct drm_buf_info *request = data; struct drm_buf_desc __user *to = &request->list[count]; - struct drm_buf_desc v = {.count = from->buf_count, -.size = from->buf_size, -.low_mark = from->low_mark, -.high_mark = from->high_mark}; + struct drm_buf_desc v; + + memset(&v, 0, sizeof(v)); + + v.count = from->buf_count; + v.size = from->buf_size; + v.low_mark = from->low_mark; + v.high_mark = from->high_mark; if (copy_to_user(to, &v, offsetof(struct drm_buf_desc, flags))) return -EFAULT; -- 2.25.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH] drm/ttm/nouveau: consolidate slowpath reserve
Am 28.07.20 um 08:24 schrieb Dave Airlie: From: Dave Airlie The WARN_ON in the non-underscore path is off questionable value (can we drop it from the non-slowpath?). At least for nouveau where it's just looked up the gem object we know the ttm object has a reference always so we can skip the check. Yeah, agreed. Wanted to look into removing that for quite some time as well. It's probably nouveau could use execbut utils here at some point but for now align the code between them to always call the __ versions, and remove the non underscored version. Can we do it the other way around and remove all uses of the __ versions of the functions instead and then merge the __ version into the normal one without the WARN_ON()? Christian. Signed-off-by: Dave Airlie --- drivers/gpu/drm/nouveau/nouveau_gem.c | 6 ++--- drivers/gpu/drm/ttm/ttm_execbuf_util.c | 10 + include/drm/ttm/ttm_bo_driver.h| 31 +++--- 3 files changed, 17 insertions(+), 30 deletions(-) diff --git a/drivers/gpu/drm/nouveau/nouveau_gem.c b/drivers/gpu/drm/nouveau/nouveau_gem.c index 81f111ad3f4f..d2d535d2ece1 100644 --- a/drivers/gpu/drm/nouveau/nouveau_gem.c +++ b/drivers/gpu/drm/nouveau/nouveau_gem.c @@ -422,15 +422,15 @@ validate_init(struct nouveau_channel *chan, struct drm_file *file_priv, break; } - ret = ttm_bo_reserve(&nvbo->bo, true, false, &op->ticket); + ret = __ttm_bo_reserve(&nvbo->bo, true, false, &op->ticket); if (ret) { list_splice_tail_init(&vram_list, &op->list); list_splice_tail_init(&gart_list, &op->list); list_splice_tail_init(&both_list, &op->list); validate_fini_no_ticket(op, chan, NULL, NULL); if (unlikely(ret == -EDEADLK)) { - ret = ttm_bo_reserve_slowpath(&nvbo->bo, true, - &op->ticket); + ret = __ttm_bo_reserve_slowpath(&nvbo->bo, true, + &op->ticket); if (!ret) res_bo = nvbo; } diff --git a/drivers/gpu/drm/ttm/ttm_execbuf_util.c b/drivers/gpu/drm/ttm/ttm_execbuf_util.c index 1797f04c0534..a24f13bc90fb 100644 --- a/drivers/gpu/drm/ttm/ttm_execbuf_util.c +++ b/drivers/gpu/drm/ttm/ttm_execbuf_util.c @@ -119,13 +119,7 @@ int ttm_eu_reserve_buffers(struct ww_acquire_ctx *ticket, ttm_eu_backoff_reservation_reverse(list, entry); if (ret == -EDEADLK) { - if (intr) { - ret = dma_resv_lock_slow_interruptible(bo->base.resv, - ticket); - } else { - dma_resv_lock_slow(bo->base.resv, ticket); - ret = 0; - } + ret = __ttm_bo_reserve_slowpath(bo, intr, ticket); } if (!ret && entry->num_shared) @@ -133,8 +127,6 @@ int ttm_eu_reserve_buffers(struct ww_acquire_ctx *ticket, entry->num_shared); if (unlikely(ret != 0)) { - if (ret == -EINTR) - ret = -ERESTARTSYS; if (ticket) { ww_acquire_done(ticket); ww_acquire_fini(ticket); diff --git a/include/drm/ttm/ttm_bo_driver.h b/include/drm/ttm/ttm_bo_driver.h index 5a37f1cc057e..563b970949a1 100644 --- a/include/drm/ttm/ttm_bo_driver.h +++ b/include/drm/ttm/ttm_bo_driver.h @@ -695,7 +695,7 @@ static inline int ttm_bo_reserve(struct ttm_buffer_object *bo, } /** - * ttm_bo_reserve_slowpath: + * __ttm_bo_reserve_slowpath: * @bo: A pointer to a struct ttm_buffer_object. * @interruptible: Sleep interruptible if waiting. * @sequence: Set (@bo)->sequence to this value after lock @@ -704,24 +704,19 @@ static inline int ttm_bo_reserve(struct ttm_buffer_object *bo, * from all our other reservations. Because there are no other reservations * held by us, this function cannot deadlock any more. */ -static inline int ttm_bo_reserve_slowpath(struct ttm_buffer_object *bo, - bool interruptible, - struct ww_acquire_ctx *ticket) +static inline int __ttm_bo_reserve_slowpath(struct ttm_buffer_object *bo, + bool interruptible, + struct ww_acquire_ctx *ticket) { - int ret = 0; - - WARN_ON(!kref_read(&bo->kref)); - - if (interruptible) - ret = dma_resv_lock_slow_in
Re: [PATCH] ttm: ttm_bo_swapout_all doesn't use it's argument.
Am 28.07.20 um 05:42 schrieb Dave Airlie: From: Dave Airlie Just drop the argument from this. This does ask the question if this is the function vmwgfx should be using or should it be doing an evict all like the other drivers. Signed-off-by: Dave Airlie Reviewed-by: Christian König --- drivers/gpu/drm/ttm/ttm_bo.c| 2 +- drivers/gpu/drm/vmwgfx/vmwgfx_drv.c | 2 +- include/drm/ttm/ttm_bo_api.h| 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/ttm/ttm_bo.c b/drivers/gpu/drm/ttm/ttm_bo.c index b03747717ec7..f297fd5e02d4 100644 --- a/drivers/gpu/drm/ttm/ttm_bo.c +++ b/drivers/gpu/drm/ttm/ttm_bo.c @@ -1838,7 +1838,7 @@ int ttm_bo_swapout(struct ttm_bo_global *glob, struct ttm_operation_ctx *ctx) } EXPORT_SYMBOL(ttm_bo_swapout); -void ttm_bo_swapout_all(struct ttm_bo_device *bdev) +void ttm_bo_swapout_all(void) { struct ttm_operation_ctx ctx = { .interruptible = false, diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_drv.c b/drivers/gpu/drm/vmwgfx/vmwgfx_drv.c index 470428387878..fb39826f72c1 100644 --- a/drivers/gpu/drm/vmwgfx/vmwgfx_drv.c +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_drv.c @@ -1352,7 +1352,7 @@ static int vmw_pm_freeze(struct device *kdev) vmw_execbuf_release_pinned_bo(dev_priv); vmw_resource_evict_all(dev_priv); vmw_release_device_early(dev_priv); - ttm_bo_swapout_all(&dev_priv->bdev); + ttm_bo_swapout_all(); if (dev_priv->enable_fb) vmw_fifo_resource_dec(dev_priv); if (atomic_read(&dev_priv->num_fifo_resources) != 0) { diff --git a/include/drm/ttm/ttm_bo_api.h b/include/drm/ttm/ttm_bo_api.h index b1c705a93517..a9e13b252820 100644 --- a/include/drm/ttm/ttm_bo_api.h +++ b/include/drm/ttm/ttm_bo_api.h @@ -692,7 +692,7 @@ ssize_t ttm_bo_io(struct ttm_bo_device *bdev, struct file *filp, int ttm_bo_swapout(struct ttm_bo_global *glob, struct ttm_operation_ctx *ctx); -void ttm_bo_swapout_all(struct ttm_bo_device *bdev); +void ttm_bo_swapout_all(void); /** * ttm_bo_uses_embedded_gem_object - check if the given bo uses the ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v5 2/5] drm/i915: Add support for async flips in I915
On 7/25/2020 4:56 AM, Paulo Zanoni wrote: Em seg, 2020-07-20 às 17:01 +0530, Karthik B S escreveu: Set the Async Address Update Enable bit in plane ctl when async flip is requested. v2: -Move the Async flip enablement to individual patch (Paulo) v3: -Rebased. v4: -Add separate plane hook for async flip case (Ville) v5: -Rebased. Signed-off-by: Karthik B S Signed-off-by: Vandita Kulkarni --- drivers/gpu/drm/i915/display/intel_display.c | 6 + drivers/gpu/drm/i915/display/intel_sprite.c | 25 drivers/gpu/drm/i915/i915_reg.h | 1 + 3 files changed, 32 insertions(+) diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c index b8ff032195d9..4773f39e5924 100644 --- a/drivers/gpu/drm/i915/display/intel_display.c +++ b/drivers/gpu/drm/i915/display/intel_display.c @@ -4766,6 +4766,12 @@ u32 skl_plane_ctl(const struct intel_crtc_state *crtc_state, const struct drm_intel_sprite_colorkey *key = &plane_state->ckey; u32 plane_ctl; + /* During Async flip, no other updates are allowed */ My understanding is that this function is fully setting the right bits based on the chosen config (instead of doing read-modify-write), and the checks for "other updates" were done before. So the logic implemented here of early returning doesn't make sense. Thanks for the review. Yes the check for other updates are done before. So I could either do read-modify-write and return early, or, keep the existing code flow as is, since the are checks already present. I will keep the existing flow and remove the early return in the next revision. + if (crtc_state->uapi.async_flip) { + plane_ctl |= PLANE_CTL_ASYNC_FLIP; I wonder why gcc does not complain we're ORing with an unitialized value. Will initialize the plane_ctl variable to zero. + return plane_ctl; + } + plane_ctl = PLANE_CTL_ENABLE; It seems to be the return above means we'll never even try to enable the plane, we're only relying on the fact that plane_ctl is not zero initialize so maybe bit 31 is already set. Since we only allow async flips on planes that are already enabled, I assumed this would not be needed. Also, other than bit 9 (async address update enable), this register is double buffered and cannot be updated asynchronously. if (INTEL_GEN(dev_priv) < 10 && !IS_GEMINILAKE(dev_priv)) { diff --git a/drivers/gpu/drm/i915/display/intel_sprite.c b/drivers/gpu/drm/i915/display/intel_sprite.c index c26ca029fc0a..3747482e8fa3 100644 --- a/drivers/gpu/drm/i915/display/intel_sprite.c +++ b/drivers/gpu/drm/i915/display/intel_sprite.c @@ -603,6 +603,24 @@ icl_program_input_csc(struct intel_plane *plane, PLANE_INPUT_CSC_POSTOFF(pipe, plane_id, 2), 0x0); } +static void +skl_program_async_surface_address(struct drm_i915_private *dev_priv, + const struct intel_plane_state *plane_state, + enum pipe pipe, enum plane_id plane_id, + u32 surf_addr) +{ + unsigned long irqflags; + u32 plane_ctl = plane_state->ctl; + + spin_lock_irqsave(&dev_priv->uncore.lock, irqflags); + + intel_de_write_fw(dev_priv, PLANE_CTL(pipe, plane_id), plane_ctl); + intel_de_write_fw(dev_priv, PLANE_SURF(pipe, plane_id), + intel_plane_ggtt_offset(plane_state) + surf_addr); + + spin_unlock_irqrestore(&dev_priv->uncore.lock, irqflags); +} + static void skl_program_plane(struct intel_plane *plane, const struct intel_crtc_state *crtc_state, @@ -631,6 +649,13 @@ skl_program_plane(struct intel_plane *plane, u32 keymsk, keymax; u32 plane_ctl = plane_state->ctl; + /* During Async flip, no other updates are allowed */ + if (crtc_state->uapi.async_flip) { + skl_program_async_surface_address(dev_priv, plane_state, + pipe, plane_id, surf_addr); + return; + } I'd vote for us to keep the "don't rewrite registers that shouldn't change" part on its own commit, since it's just an optimization. It could even go at the end of the series. But perhaps this is simple enough and not needed. Will move this change to the end of the series. Thanks, Karthik.B.S + plane_ctl |= skl_plane_ctl_crtc(crtc_state); if (INTEL_GEN(dev_priv) >= 10 || IS_GEMINILAKE(dev_priv)) diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h index 8cee06314d5d..19aad4199874 100644 --- a/drivers/gpu/drm/i915/i915_reg.h +++ b/drivers/gpu/drm/i915/i915_reg.h @@ -6935,6 +6935,7 @@ enum { #define PLANE_CTL_TILED_X (1 << 10) #define PLANE_CTL_TILED_Y (4 << 10) #define PLANE_CTL_TILED_YF (5 << 10) +#define PLANE_CTL_ASYNC_FLIP (1
Re: [PATCH] drm/ttm: make ttm_tt unbind function return void.
Am 28.07.20 um 06:00 schrieb Dave Airlie: From: Dave Airlie The return value just led to BUG_ON, I think if a driver wants to BUG_ON here it can do it itself. (don't BUG_ON). Signed-off-by: Dave Airlie Reviewed-by: Christian König --- drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c| 5 ++--- drivers/gpu/drm/nouveau/nouveau_sgdma.c| 3 +-- drivers/gpu/drm/qxl/qxl_ttm.c | 3 +-- drivers/gpu/drm/radeon/radeon_ttm.c| 4 +--- drivers/gpu/drm/ttm/ttm_agp_backend.c | 9 + drivers/gpu/drm/ttm/ttm_tt.c | 5 + drivers/gpu/drm/vmwgfx/vmwgfx_ttm_buffer.c | 4 +--- include/drm/ttm/ttm_tt.h | 2 +- 8 files changed, 13 insertions(+), 22 deletions(-) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c index fcff5671f6f8..e11c5d69843d 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c @@ -1292,7 +1292,7 @@ int amdgpu_ttm_recover_gart(struct ttm_buffer_object *tbo) * Called by ttm_tt_unbind() on behalf of ttm_bo_move_ttm() and * ttm_tt_destroy(). */ -static int amdgpu_ttm_backend_unbind(struct ttm_tt *ttm) +static void amdgpu_ttm_backend_unbind(struct ttm_tt *ttm) { struct amdgpu_device *adev = amdgpu_ttm_adev(ttm->bdev); struct amdgpu_ttm_tt *gtt = (void *)ttm; @@ -1303,14 +1303,13 @@ static int amdgpu_ttm_backend_unbind(struct ttm_tt *ttm) amdgpu_ttm_tt_unpin_userptr(ttm); if (gtt->offset == AMDGPU_BO_INVALID_OFFSET) - return 0; + return; /* unbind shouldn't be done for GDS/GWS/OA in ttm_bo_clean_mm */ r = amdgpu_gart_unbind(adev, gtt->offset, ttm->num_pages); if (r) DRM_ERROR("failed to unbind %lu pages at 0x%08llX\n", gtt->ttm.ttm.num_pages, gtt->offset); - return r; } static void amdgpu_ttm_backend_destroy(struct ttm_tt *ttm) diff --git a/drivers/gpu/drm/nouveau/nouveau_sgdma.c b/drivers/gpu/drm/nouveau/nouveau_sgdma.c index feaac908efed..20b6d0b3de5c 100644 --- a/drivers/gpu/drm/nouveau/nouveau_sgdma.c +++ b/drivers/gpu/drm/nouveau/nouveau_sgdma.c @@ -46,12 +46,11 @@ nv04_sgdma_bind(struct ttm_tt *ttm, struct ttm_mem_reg *reg) return 0; } -static int +static void nv04_sgdma_unbind(struct ttm_tt *ttm) { struct nouveau_sgdma_be *nvbe = (struct nouveau_sgdma_be *)ttm; nouveau_mem_fini(nvbe->mem); - return 0; } static struct ttm_backend_func nv04_sgdma_backend = { diff --git a/drivers/gpu/drm/qxl/qxl_ttm.c b/drivers/gpu/drm/qxl/qxl_ttm.c index 1d8e07b8b19e..bf9dc451583a 100644 --- a/drivers/gpu/drm/qxl/qxl_ttm.c +++ b/drivers/gpu/drm/qxl/qxl_ttm.c @@ -149,10 +149,9 @@ static int qxl_ttm_backend_bind(struct ttm_tt *ttm, return -1; } -static int qxl_ttm_backend_unbind(struct ttm_tt *ttm) +static void qxl_ttm_backend_unbind(struct ttm_tt *ttm) { /* Not implemented */ - return -1; } static void qxl_ttm_backend_destroy(struct ttm_tt *ttm) diff --git a/drivers/gpu/drm/radeon/radeon_ttm.c b/drivers/gpu/drm/radeon/radeon_ttm.c index 54af06df865b..004344dce140 100644 --- a/drivers/gpu/drm/radeon/radeon_ttm.c +++ b/drivers/gpu/drm/radeon/radeon_ttm.c @@ -591,7 +591,7 @@ static int radeon_ttm_backend_bind(struct ttm_tt *ttm, return 0; } -static int radeon_ttm_backend_unbind(struct ttm_tt *ttm) +static void radeon_ttm_backend_unbind(struct ttm_tt *ttm) { struct radeon_ttm_tt *gtt = (void *)ttm; @@ -599,8 +599,6 @@ static int radeon_ttm_backend_unbind(struct ttm_tt *ttm) if (gtt->userptr) radeon_ttm_tt_unpin_userptr(ttm); - - return 0; } static void radeon_ttm_backend_destroy(struct ttm_tt *ttm) diff --git a/drivers/gpu/drm/ttm/ttm_agp_backend.c b/drivers/gpu/drm/ttm/ttm_agp_backend.c index 6050dc846894..38f1351140e2 100644 --- a/drivers/gpu/drm/ttm/ttm_agp_backend.c +++ b/drivers/gpu/drm/ttm/ttm_agp_backend.c @@ -82,17 +82,18 @@ static int ttm_agp_bind(struct ttm_tt *ttm, struct ttm_mem_reg *bo_mem) return ret; } -static int ttm_agp_unbind(struct ttm_tt *ttm) +static void ttm_agp_unbind(struct ttm_tt *ttm) { struct ttm_agp_backend *agp_be = container_of(ttm, struct ttm_agp_backend, ttm); if (agp_be->mem) { - if (agp_be->mem->is_bound) - return agp_unbind_memory(agp_be->mem); + if (agp_be->mem->is_bound) { + agp_unbind_memory(agp_be->mem); + return; + } agp_free_memory(agp_be->mem); agp_be->mem = NULL; } - return 0; } static void ttm_agp_destroy(struct ttm_tt *ttm) diff --git a/drivers/gpu/drm/ttm/ttm_tt.c b/drivers/gpu/drm/ttm/ttm_tt.c index e25d4097aa16..bab67873cfd4 100644 --- a/drivers/gpu/drm/ttm/ttm_tt.c +++ b/drivers/gpu/drm/ttm/ttm_tt.c @@ -313,11 +31
[PATCH 11/13] drm/ast: Managed release of ast firmware
The ast driver loads firmware for the DP501 display encoder. The patch replaces the removal code with a managed release function. Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/ast/ast_dp501.c | 23 ++- drivers/gpu/drm/ast/ast_drv.h | 1 - drivers/gpu/drm/ast/ast_main.c | 3 --- 3 files changed, 14 insertions(+), 13 deletions(-) diff --git a/drivers/gpu/drm/ast/ast_dp501.c b/drivers/gpu/drm/ast/ast_dp501.c index 4b85a504825a..88121c0e0d05 100644 --- a/drivers/gpu/drm/ast/ast_dp501.c +++ b/drivers/gpu/drm/ast/ast_dp501.c @@ -8,11 +8,24 @@ MODULE_FIRMWARE("ast_dp501_fw.bin"); +static void ast_release_firmware(void *data) +{ + struct ast_private *ast = data; + + release_firmware(ast->dp501_fw); + ast->dp501_fw = NULL; +} + static int ast_load_dp501_microcode(struct drm_device *dev) { struct ast_private *ast = to_ast_private(dev); + int ret; + + ret = request_firmware(&ast->dp501_fw, "ast_dp501_fw.bin", dev->dev); + if (ret) + return ret; - return request_firmware(&ast->dp501_fw, "ast_dp501_fw.bin", dev->dev); + return devm_add_action_or_reset(dev->dev, ast_release_firmware, ast); } static void send_ack(struct ast_private *ast) @@ -435,11 +448,3 @@ void ast_init_3rdtx(struct drm_device *dev) } } } - -void ast_release_firmware(struct drm_device *dev) -{ - struct ast_private *ast = to_ast_private(dev); - - release_firmware(ast->dp501_fw); - ast->dp501_fw = NULL; -} diff --git a/drivers/gpu/drm/ast/ast_drv.h b/drivers/gpu/drm/ast/ast_drv.h index 86c9a7ac712b..02908d005b99 100644 --- a/drivers/gpu/drm/ast/ast_drv.h +++ b/drivers/gpu/drm/ast/ast_drv.h @@ -312,7 +312,6 @@ bool ast_backup_fw(struct drm_device *dev, u8 *addr, u32 size); bool ast_dp501_read_edid(struct drm_device *dev, u8 *ediddata); u8 ast_get_dp501_max_clk(struct drm_device *dev); void ast_init_3rdtx(struct drm_device *dev); -void ast_release_firmware(struct drm_device *dev); /* ast_cursor.c */ int ast_cursor_init(struct ast_private *ast); diff --git a/drivers/gpu/drm/ast/ast_main.c b/drivers/gpu/drm/ast/ast_main.c index 792fb7f616ec..e3b7748335a3 100644 --- a/drivers/gpu/drm/ast/ast_main.c +++ b/drivers/gpu/drm/ast/ast_main.c @@ -442,11 +442,8 @@ struct ast_private *ast_device_create(struct drm_driver *drv, void ast_device_destroy(struct ast_private *ast) { - struct drm_device *dev = &ast->base; - /* enable standard VGA decode */ ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0xa1, 0x04); - ast_release_firmware(dev); kfree(ast->dp501_fw_addr); } -- 2.27.0 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH 00/13] drm/ast: Convert to managed initialization
This is the final patchset for converting ast to managed initialization. Patches #1 to #4 address I2C helpers. The structures are being stored in struct ast_connector. The initialization and cleanups is being converted to managed release helpers. Patches #5 to #10 address modesetting and device structures. All are being embedded into struct ast_private. With struct ast_private being a subclass of struct drm_device, patch #10 switches ast to DRM's managed- allocation helpers. Patches #11 and #12 address firmware memory that ast allocates internally. Finally, patch #13 removes ast's destroy function in favor of managed release helpers. Tested on AST 2100 HW. Thomas Zimmermann (13): drm/ast: Move I2C code within ast_mode.c drm/ast: Test if I2C support has been initialized drm/ast: Embed I2C fields in struct ast_connector drm/ast: Managed release of I2C adapter drm/ast: Embed CRTC and connector in struct ast_private drm/ast: Separate DRM driver from PCI code drm/ast: Replace driver load/unload functions with device create/destroy drm/ast: Replace struct_drm_device.dev_private with to_ast_private() drm/ast: Don't use ast->dev if dev is available drm/ast: Embed struct drm_device in struct ast_private drm/ast: Managed release of ast firmware drm/ast: Manage release of firmware backup memory drm/ast: Managed device release drivers/gpu/drm/ast/ast_cursor.c | 8 +- drivers/gpu/drm/ast/ast_dp501.c | 23 ++- drivers/gpu/drm/ast/ast_drv.c| 82 drivers/gpu/drm/ast/ast_drv.h| 43 +++-- drivers/gpu/drm/ast/ast_main.c | 74 drivers/gpu/drm/ast/ast_mm.c | 2 +- drivers/gpu/drm/ast/ast_mode.c | 310 ++- drivers/gpu/drm/ast/ast_post.c | 6 +- 8 files changed, 263 insertions(+), 285 deletions(-) -- 2.27.0 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH 01/13] drm/ast: Move I2C code within ast_mode.c
The I2C support feels slammed down to the end of ast_mode.c. Improve this by moving the code before it's callers, remove the declarations, rename the callbacks to match I2C's get/set sda/scl convention, and prefix all functions with ast_. No functional changes have been made. Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/ast/ast_mode.c | 249 + 1 file changed, 125 insertions(+), 124 deletions(-) diff --git a/drivers/gpu/drm/ast/ast_mode.c b/drivers/gpu/drm/ast/ast_mode.c index 154cd877d9d1..19f1dfc8e9e0 100644 --- a/drivers/gpu/drm/ast/ast_mode.c +++ b/drivers/gpu/drm/ast/ast_mode.c @@ -46,9 +46,6 @@ #include "ast_drv.h" #include "ast_tables.h" -static struct ast_i2c_chan *ast_i2c_create(struct drm_device *dev); -static void ast_i2c_destroy(struct ast_i2c_chan *i2c); - static inline void ast_load_palette_index(struct ast_private *ast, u8 index, u8 red, u8 green, u8 blue) @@ -514,6 +511,131 @@ static void ast_set_start_address_crt1(struct ast_private *ast, } +/* + * I2C + */ + +static int ast_i2c_getscl(void *i2c_priv) +{ + struct ast_i2c_chan *i2c = i2c_priv; + struct ast_private *ast = to_ast_private(i2c->dev); + uint32_t val, val2, count, pass; + + count = 0; + pass = 0; + val = (ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0x10) >> 4) & 0x01; + do { + val2 = (ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0x10) >> 4) & 0x01; + if (val == val2) { + pass++; + } else { + pass = 0; + val = (ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0x10) >> 4) & 0x01; + } + } while ((pass < 5) && (count++ < 0x1)); + + return val & 1 ? 1 : 0; +} + +static int ast_i2c_getsda(void *i2c_priv) +{ + struct ast_i2c_chan *i2c = i2c_priv; + struct ast_private *ast = to_ast_private(i2c->dev); + uint32_t val, val2, count, pass; + + count = 0; + pass = 0; + val = (ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0x20) >> 5) & 0x01; + do { + val2 = (ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0x20) >> 5) & 0x01; + if (val == val2) { + pass++; + } else { + pass = 0; + val = (ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0x20) >> 5) & 0x01; + } + } while ((pass < 5) && (count++ < 0x1)); + + return val & 1 ? 1 : 0; +} + +static void ast_i2c_setscl(void *i2c_priv, int clock) +{ + struct ast_i2c_chan *i2c = i2c_priv; + struct ast_private *ast = to_ast_private(i2c->dev); + int i; + u8 ujcrb7, jtemp; + + for (i = 0; i < 0x1; i++) { + ujcrb7 = ((clock & 0x01) ? 0 : 1); + ast_set_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0xf4, ujcrb7); + jtemp = ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0x01); + if (ujcrb7 == jtemp) + break; + } +} + +static void ast_i2c_setsda(void *i2c_priv, int data) +{ + struct ast_i2c_chan *i2c = i2c_priv; + struct ast_private *ast = to_ast_private(i2c->dev); + int i; + u8 ujcrb7, jtemp; + + for (i = 0; i < 0x1; i++) { + ujcrb7 = ((data & 0x01) ? 0 : 1) << 2; + ast_set_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0xf1, ujcrb7); + jtemp = ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0x04); + if (ujcrb7 == jtemp) + break; + } +} + +static struct ast_i2c_chan *ast_i2c_create(struct drm_device *dev) +{ + struct ast_i2c_chan *i2c; + int ret; + + i2c = kzalloc(sizeof(struct ast_i2c_chan), GFP_KERNEL); + if (!i2c) + return NULL; + + i2c->adapter.owner = THIS_MODULE; + i2c->adapter.class = I2C_CLASS_DDC; + i2c->adapter.dev.parent = &dev->pdev->dev; + i2c->dev = dev; + i2c_set_adapdata(&i2c->adapter, i2c); + snprintf(i2c->adapter.name, sizeof(i2c->adapter.name), +"AST i2c bit bus"); + i2c->adapter.algo_data = &i2c->bit; + + i2c->bit.udelay = 20; + i2c->bit.timeout = 2; + i2c->bit.data = i2c; + i2c->bit.setsda = ast_i2c_setsda; + i2c->bit.setscl = ast_i2c_setscl; + i2c->bit.getsda = ast_i2c_getsda; + i2c->bit.getscl = ast_i2c_getscl; + ret = i2c_bit_add_bus(&i2c->adapter); + if (ret) { + drm_err(dev, "Failed to register bit i2c\n"); + goto out_free; + } + + return i2c; +out_free: + kfree(i2c); + return NULL; +} + +static void ast_i2c_destroy(struct ast_i2c_chan *i2c) +{ + if (!i2c) + return; + i2c_del_adapter(&i2c->adapter); + k
[PATCH 04/13] drm/ast: Managed release of I2C adapter
Managed releases of the device's I2C adapter simplify the connector's release. Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/ast/ast_mode.c | 21 ++--- 1 file changed, 10 insertions(+), 11 deletions(-) diff --git a/drivers/gpu/drm/ast/ast_mode.c b/drivers/gpu/drm/ast/ast_mode.c index f421a60d8a96..27eb49bd12b3 100644 --- a/drivers/gpu/drm/ast/ast_mode.c +++ b/drivers/gpu/drm/ast/ast_mode.c @@ -39,6 +39,7 @@ #include #include #include +#include #include #include #include @@ -591,6 +592,14 @@ static void ast_i2c_setsda(void *i2c_priv, int data) } } +static void ast_i2c_release(struct drm_device *dev, void *data) +{ + struct ast_i2c_chan *i2c = data; + + i2c_del_adapter(&i2c->adapter); + i2c->dev = NULL; /* clear to signal absence of I2C support */ +} + static int ast_i2c_init(struct ast_i2c_chan *i2c, struct drm_device *dev) { int ret; @@ -618,7 +627,7 @@ static int ast_i2c_init(struct ast_i2c_chan *i2c, struct drm_device *dev) i2c->dev = dev; /* signals presence of I2C support */ - return 0; + return drmm_add_action_or_reset(dev, ast_i2c_release, i2c); } static bool ast_i2c_is_initialized(struct ast_i2c_chan *i2c) @@ -626,14 +635,6 @@ static bool ast_i2c_is_initialized(struct ast_i2c_chan *i2c) return !!i2c->dev; } -static void ast_i2c_fini(struct ast_i2c_chan *i2c) -{ - if (!ast_i2c_is_initialized(i2c)) - return; - i2c_del_adapter(&i2c->adapter); - i2c->dev = NULL; /* clear to signal absence of I2C support */ -} - /* * Primary plane */ @@ -1139,8 +1140,6 @@ static enum drm_mode_status ast_mode_valid(struct drm_connector *connector, static void ast_connector_destroy(struct drm_connector *connector) { - struct ast_connector *ast_connector = to_ast_connector(connector); - ast_i2c_fini(&ast_connector->i2c); drm_connector_cleanup(connector); kfree(connector); } -- 2.27.0 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH 07/13] drm/ast: Replace driver load/unload functions with device create/destroy
The ast driver's load and unload functions are left-overs from when struct drm_driver.load/unload was still in use. The PCI probe helper allocated the DRM device and ran load to initialize it. This patch replaces this code with device create and destroy. The main difference is that the device's create function allocates the DRM device and ast structures in the same place. This will be required for switching ast to managed allocations. Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/ast/ast_drv.c | 24 +++- drivers/gpu/drm/ast/ast_drv.h | 6 -- drivers/gpu/drm/ast/ast_main.c | 24 ++-- 3 files changed, 33 insertions(+), 21 deletions(-) diff --git a/drivers/gpu/drm/ast/ast_drv.c b/drivers/gpu/drm/ast/ast_drv.c index 9d04f2b5225c..ad93c35b4cf7 100644 --- a/drivers/gpu/drm/ast/ast_drv.c +++ b/drivers/gpu/drm/ast/ast_drv.c @@ -109,6 +109,7 @@ static void ast_kick_out_firmware_fb(struct pci_dev *pdev) static int ast_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent) { + struct ast_private *ast; struct drm_device *dev; int ret; @@ -118,27 +119,23 @@ static int ast_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent) if (ret) return ret; - dev = drm_dev_alloc(&ast_driver, &pdev->dev); - if (IS_ERR(dev)) - return PTR_ERR(dev); - - dev->pdev = pdev; - pci_set_drvdata(pdev, dev); - - ret = ast_driver_load(dev, ent->driver_data); - if (ret) + ast = ast_device_create(&ast_driver, pdev, ent->driver_data); + if (IS_ERR(ast)) { + ret = PTR_ERR(ast); goto err_drm_dev_put; + } + dev = ast->dev; ret = drm_dev_register(dev, ent->driver_data); if (ret) - goto err_ast_driver_unload; + goto err_ast_device_destroy; drm_fbdev_generic_setup(dev, 32); return 0; -err_ast_driver_unload: - ast_driver_unload(dev); +err_ast_device_destroy: + ast_device_destroy(ast); err_drm_dev_put: drm_dev_put(dev); return ret; @@ -147,9 +144,10 @@ static int ast_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent) static void ast_pci_remove(struct pci_dev *pdev) { struct drm_device *dev = pci_get_drvdata(pdev); + struct ast_private *ast = to_ast_private(dev); drm_dev_unregister(dev); - ast_driver_unload(dev); + ast_device_destroy(ast); drm_dev_put(dev); } diff --git a/drivers/gpu/drm/ast/ast_drv.h b/drivers/gpu/drm/ast/ast_drv.h index b401560e4e8f..f1aebc719d9e 100644 --- a/drivers/gpu/drm/ast/ast_drv.h +++ b/drivers/gpu/drm/ast/ast_drv.h @@ -159,8 +159,10 @@ static inline struct ast_private *to_ast_private(struct drm_device *dev) return dev->dev_private; } -int ast_driver_load(struct drm_device *dev, unsigned long flags); -void ast_driver_unload(struct drm_device *dev); +struct ast_private *ast_device_create(struct drm_driver *drv, + struct pci_dev *pdev, + unsigned long flags); +void ast_device_destroy(struct ast_private *ast); #define AST_IO_AR_PORT_WRITE (0x40) #define AST_IO_MISC_PORT_WRITE (0x42) diff --git a/drivers/gpu/drm/ast/ast_main.c b/drivers/gpu/drm/ast/ast_main.c index dd12b55d57a2..8d46166f8462 100644 --- a/drivers/gpu/drm/ast/ast_main.c +++ b/drivers/gpu/drm/ast/ast_main.c @@ -30,6 +30,7 @@ #include #include +#include #include #include @@ -378,15 +379,25 @@ static int ast_get_dram_info(struct drm_device *dev) return 0; } -int ast_driver_load(struct drm_device *dev, unsigned long flags) +struct ast_private *ast_device_create(struct drm_driver *drv, + struct pci_dev *pdev, + unsigned long flags) { + struct drm_device *dev; struct ast_private *ast; bool need_post; int ret = 0; + dev = drm_dev_alloc(drv, &pdev->dev); + if (IS_ERR(dev)) + return ERR_CAST(dev); + + dev->pdev = pdev; + pci_set_drvdata(pdev, dev); + ast = kzalloc(sizeof(struct ast_private), GFP_KERNEL); if (!ast) - return -ENOMEM; + return ERR_PTR(-ENOMEM); dev->dev_private = ast; ast->dev = dev; @@ -435,16 +446,17 @@ int ast_driver_load(struct drm_device *dev, unsigned long flags) if (ret) goto out_free; - return 0; + return ast; + out_free: kfree(ast); dev->dev_private = NULL; - return ret; + return ERR_PTR(ret); } -void ast_driver_unload(struct drm_device *dev) +void ast_device_destroy(struct ast_private *ast) { - struct ast_private *ast = to_ast_private(dev); + struct drm_device *dev = ast->dev; /* enable standard VGA decode */ ast_set_index_reg(ast,
[PATCH 05/13] drm/ast: Embed CRTC and connector in struct ast_private
Only single instances of CRTC and connector are supported per device. Embed both in ast's structure and remove the individual memory allocations. DRM's CRTC/connector cleanup helpers replace the rsp. destroy functions in ast. While at it, also convert to_ast_connector() to a function. Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/ast/ast_drv.h | 34 ++--- drivers/gpu/drm/ast/ast_mode.c | 46 -- 2 files changed, 31 insertions(+), 49 deletions(-) diff --git a/drivers/gpu/drm/ast/ast_drv.h b/drivers/gpu/drm/ast/ast_drv.h index d303df568099..b401560e4e8f 100644 --- a/drivers/gpu/drm/ast/ast_drv.h +++ b/drivers/gpu/drm/ast/ast_drv.h @@ -98,6 +98,23 @@ enum ast_tx_chip { #define AST_HWC_SIGNATURE_HOTSPOTX 0x14 #define AST_HWC_SIGNATURE_HOTSPOTY 0x18 +struct ast_i2c_chan { + struct i2c_adapter adapter; + struct drm_device *dev; + struct i2c_algo_bit_data bit; +}; + +struct ast_connector { + struct drm_connector base; + struct ast_i2c_chan i2c; +}; + +static inline struct ast_connector * +to_ast_connector(struct drm_connector *connector) +{ + return container_of(connector, struct ast_connector, base); +} + struct ast_private { struct drm_device *dev; @@ -118,9 +135,11 @@ struct ast_private { unsigned int next_index; } cursor; - struct drm_encoder encoder; struct drm_plane primary_plane; struct drm_plane cursor_plane; + struct drm_crtc crtc; + struct drm_encoder encoder; + struct ast_connector connector; bool support_wide_screen; enum { @@ -225,19 +244,6 @@ static inline void ast_open_key(struct ast_private *ast) #define AST_VIDMEM_DEFAULT_SIZE AST_VIDMEM_SIZE_8M -struct ast_i2c_chan { - struct i2c_adapter adapter; - struct drm_device *dev; - struct i2c_algo_bit_data bit; -}; - -struct ast_connector { - struct drm_connector base; - struct ast_i2c_chan i2c; -}; - -#define to_ast_connector(x) container_of(x, struct ast_connector, base) - struct ast_vbios_stdtable { u8 misc; u8 seq[4]; diff --git a/drivers/gpu/drm/ast/ast_mode.c b/drivers/gpu/drm/ast/ast_mode.c index 27eb49bd12b3..201313ab3e71 100644 --- a/drivers/gpu/drm/ast/ast_mode.c +++ b/drivers/gpu/drm/ast/ast_mode.c @@ -952,12 +952,6 @@ static void ast_crtc_reset(struct drm_crtc *crtc) __drm_atomic_helper_crtc_reset(crtc, &ast_state->base); } -static void ast_crtc_destroy(struct drm_crtc *crtc) -{ - drm_crtc_cleanup(crtc); - kfree(crtc); -} - static struct drm_crtc_state * ast_crtc_atomic_duplicate_state(struct drm_crtc *crtc) { @@ -993,7 +987,7 @@ static void ast_crtc_atomic_destroy_state(struct drm_crtc *crtc, static const struct drm_crtc_funcs ast_crtc_funcs = { .reset = ast_crtc_reset, .gamma_set = drm_atomic_helper_legacy_gamma_set, - .destroy = ast_crtc_destroy, + .destroy = drm_crtc_cleanup, .set_config = drm_atomic_helper_set_config, .page_flip = drm_atomic_helper_page_flip, .atomic_duplicate_state = ast_crtc_atomic_duplicate_state, @@ -1003,27 +997,19 @@ static const struct drm_crtc_funcs ast_crtc_funcs = { static int ast_crtc_init(struct drm_device *dev) { struct ast_private *ast = to_ast_private(dev); - struct drm_crtc *crtc; + struct drm_crtc *crtc = &ast->crtc; int ret; - crtc = kzalloc(sizeof(*crtc), GFP_KERNEL); - if (!crtc) - return -ENOMEM; - ret = drm_crtc_init_with_planes(dev, crtc, &ast->primary_plane, &ast->cursor_plane, &ast_crtc_funcs, NULL); if (ret) - goto err_kfree; + return ret; drm_mode_crtc_set_gamma_size(crtc, 256); drm_crtc_helper_add(crtc, &ast_crtc_helper_funcs); return 0; - -err_kfree: - kfree(crtc); - return ret; } /* @@ -1138,12 +1124,6 @@ static enum drm_mode_status ast_mode_valid(struct drm_connector *connector, return flags; } -static void ast_connector_destroy(struct drm_connector *connector) -{ - drm_connector_cleanup(connector); - kfree(connector); -} - static const struct drm_connector_helper_funcs ast_connector_helper_funcs = { .get_modes = ast_get_modes, .mode_valid = ast_mode_valid, @@ -1152,31 +1132,28 @@ static const struct drm_connector_helper_funcs ast_connector_helper_funcs = { static const struct drm_connector_funcs ast_connector_funcs = { .reset = drm_atomic_helper_connector_reset, .fill_modes = drm_helper_probe_single_connector_modes, - .destroy = ast_connector_destroy, + .destroy = drm_connector_cleanup, .atomic_duplicate_state = drm_atomic_helper_connector_duplicate_state, .atomic_destroy_state = drm_atomic_helper_connector_destroy_state, }; static int ast_conne
[PATCH 12/13] drm/ast: Manage release of firmware backup memory
The ast driver keeps a backup copy of the DP501 encoder's firmware. This patch adds managed release of the allocated memory. Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/ast/ast_main.c | 7 +++ 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/drivers/gpu/drm/ast/ast_main.c b/drivers/gpu/drm/ast/ast_main.c index e3b7748335a3..67e20727d82d 100644 --- a/drivers/gpu/drm/ast/ast_main.c +++ b/drivers/gpu/drm/ast/ast_main.c @@ -33,6 +33,7 @@ #include #include #include +#include #include "ast_drv.h" @@ -231,11 +232,11 @@ static int ast_detect_chip(struct drm_device *dev, bool *need_post) ast->tx_chip_type = AST_TX_SIL164; break; case 0x08: - ast->dp501_fw_addr = kzalloc(32*1024, GFP_KERNEL); + ast->dp501_fw_addr = drmm_kzalloc(dev, 32*1024, GFP_KERNEL); if (ast->dp501_fw_addr) { /* backup firmware */ if (ast_backup_fw(dev, ast->dp501_fw_addr, 32*1024)) { - kfree(ast->dp501_fw_addr); + drmm_kfree(dev, ast->dp501_fw_addr); ast->dp501_fw_addr = NULL; } } @@ -444,6 +445,4 @@ void ast_device_destroy(struct ast_private *ast) { /* enable standard VGA decode */ ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0xa1, 0x04); - - kfree(ast->dp501_fw_addr); } -- 2.27.0 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH 09/13] drm/ast: Don't use ast->dev if dev is available
Several places in ast use ast->dev, when a dev pointer is already available within the function. Remove the extra indirection. No functional changes made. This is just a small cleanup before embedding the DRM device instance in struct ast_private. Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/ast/ast_mode.c | 2 +- drivers/gpu/drm/ast/ast_post.c | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/ast/ast_mode.c b/drivers/gpu/drm/ast/ast_mode.c index 01340b0e40f8..dceb11a320b2 100644 --- a/drivers/gpu/drm/ast/ast_mode.c +++ b/drivers/gpu/drm/ast/ast_mode.c @@ -1196,7 +1196,7 @@ int ast_mode_config_init(struct ast_private *ast) dev->mode_config.min_height = 0; dev->mode_config.preferred_depth = 24; dev->mode_config.prefer_shadow = 1; - dev->mode_config.fb_base = pci_resource_start(ast->dev->pdev, 0); + dev->mode_config.fb_base = pci_resource_start(dev->pdev, 0); if (ast->chip == AST2100 || ast->chip == AST2200 || diff --git a/drivers/gpu/drm/ast/ast_post.c b/drivers/gpu/drm/ast/ast_post.c index c043fe717553..b1d42a639ece 100644 --- a/drivers/gpu/drm/ast/ast_post.c +++ b/drivers/gpu/drm/ast/ast_post.c @@ -368,9 +368,9 @@ void ast_post_gpu(struct drm_device *dev) u32 reg; struct ast_private *ast = to_ast_private(dev); - pci_read_config_dword(ast->dev->pdev, 0x04, ®); + pci_read_config_dword(dev->pdev, 0x04, ®); reg |= 0x3; - pci_write_config_dword(ast->dev->pdev, 0x04, reg); + pci_write_config_dword(dev->pdev, 0x04, reg); ast_enable_vga(dev); ast_open_key(ast); -- 2.27.0 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH 10/13] drm/ast: Embed struct drm_device in struct ast_private
Turns struct ast_private into a subclass of struct drm_device by embedding the latter. This allows for using DRM's managed device allocation. The use of struct drm_device.dev_private is deprecated. The patch converts the last remaining users to to_ast_private(). Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/ast/ast_cursor.c | 6 ++--- drivers/gpu/drm/ast/ast_drv.c| 2 +- drivers/gpu/drm/ast/ast_drv.h| 4 +-- drivers/gpu/drm/ast/ast_main.c | 42 ++-- drivers/gpu/drm/ast/ast_mm.c | 2 +- drivers/gpu/drm/ast/ast_mode.c | 2 +- drivers/gpu/drm/ast/ast_post.c | 2 +- 7 files changed, 22 insertions(+), 38 deletions(-) diff --git a/drivers/gpu/drm/ast/ast_cursor.c b/drivers/gpu/drm/ast/ast_cursor.c index 8d693c8b346f..6c96f74cdb9e 100644 --- a/drivers/gpu/drm/ast/ast_cursor.c +++ b/drivers/gpu/drm/ast/ast_cursor.c @@ -57,7 +57,7 @@ static void ast_cursor_release(struct drm_device *dev, void *ptr) */ int ast_cursor_init(struct ast_private *ast) { - struct drm_device *dev = ast->dev; + struct drm_device *dev = &ast->base; size_t size, i; struct drm_gem_vram_object *gbo; void __iomem *vaddr; @@ -168,7 +168,7 @@ static void update_cursor_image(u8 __iomem *dst, const u8 *src, int width, int h int ast_cursor_blit(struct ast_private *ast, struct drm_framebuffer *fb) { - struct drm_device *dev = ast->dev; + struct drm_device *dev = &ast->base; struct drm_gem_vram_object *gbo; int ret; void *src; @@ -217,7 +217,7 @@ static void ast_cursor_set_base(struct ast_private *ast, u64 address) void ast_cursor_page_flip(struct ast_private *ast) { - struct drm_device *dev = ast->dev; + struct drm_device *dev = &ast->base; struct drm_gem_vram_object *gbo; s64 off; diff --git a/drivers/gpu/drm/ast/ast_drv.c b/drivers/gpu/drm/ast/ast_drv.c index ad93c35b4cf7..c394383a7979 100644 --- a/drivers/gpu/drm/ast/ast_drv.c +++ b/drivers/gpu/drm/ast/ast_drv.c @@ -124,7 +124,7 @@ static int ast_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent) ret = PTR_ERR(ast); goto err_drm_dev_put; } - dev = ast->dev; + dev = &ast->base; ret = drm_dev_register(dev, ent->driver_data); if (ret) diff --git a/drivers/gpu/drm/ast/ast_drv.h b/drivers/gpu/drm/ast/ast_drv.h index f1aebc719d9e..86c9a7ac712b 100644 --- a/drivers/gpu/drm/ast/ast_drv.h +++ b/drivers/gpu/drm/ast/ast_drv.h @@ -116,7 +116,7 @@ to_ast_connector(struct drm_connector *connector) } struct ast_private { - struct drm_device *dev; + struct drm_device base; void __iomem *regs; void __iomem *ioregs; @@ -156,7 +156,7 @@ struct ast_private { static inline struct ast_private *to_ast_private(struct drm_device *dev) { - return dev->dev_private; + return container_of(dev, struct ast_private, base); } struct ast_private *ast_device_create(struct drm_driver *drv, diff --git a/drivers/gpu/drm/ast/ast_main.c b/drivers/gpu/drm/ast/ast_main.c index 8d46166f8462..792fb7f616ec 100644 --- a/drivers/gpu/drm/ast/ast_main.c +++ b/drivers/gpu/drm/ast/ast_main.c @@ -388,25 +388,17 @@ struct ast_private *ast_device_create(struct drm_driver *drv, bool need_post; int ret = 0; - dev = drm_dev_alloc(drv, &pdev->dev); - if (IS_ERR(dev)) - return ERR_CAST(dev); + ast = devm_drm_dev_alloc(&pdev->dev, drv, struct ast_private, base); + if (IS_ERR(ast)) + return ast; + dev = &ast->base; dev->pdev = pdev; pci_set_drvdata(pdev, dev); - ast = kzalloc(sizeof(struct ast_private), GFP_KERNEL); - if (!ast) - return ERR_PTR(-ENOMEM); - - dev->dev_private = ast; - ast->dev = dev; - ast->regs = pci_iomap(dev->pdev, 1, 0); - if (!ast->regs) { - ret = -EIO; - goto out_free; - } + if (!ast->regs) + return ERR_PTR(-EIO); /* * If we don't have IO space at all, use MMIO now and @@ -421,17 +413,16 @@ struct ast_private *ast_device_create(struct drm_driver *drv, /* "map" IO regs if the above hasn't done so already */ if (!ast->ioregs) { ast->ioregs = pci_iomap(dev->pdev, 2, 0); - if (!ast->ioregs) { - ret = -EIO; - goto out_free; - } + if (!ast->ioregs) + return ERR_PTR(-EIO); } ast_detect_chip(dev, &need_post); ret = ast_get_dram_info(dev); if (ret) - goto out_free; + return ERR_PTR(ret); + drm_info(dev, "dram MCLK=%u Mhz type=%d bus_width=%d\n", ast->mclk, ast->dram_type, ast->dram_bus_width); @@ -440,29 +431,22 @@ struct ast_private *ast_device_create(struct drm_driver *drv,
[PATCH 08/13] drm/ast: Replace struct_drm_device.dev_private with to_ast_private()
The ast code still references dev_private in several place when looking up the ast device structure. Convert the remaining locations to use to_ast_private(). Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/ast/ast_cursor.c | 2 +- drivers/gpu/drm/ast/ast_mode.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/ast/ast_cursor.c b/drivers/gpu/drm/ast/ast_cursor.c index acf0d23514e8..8d693c8b346f 100644 --- a/drivers/gpu/drm/ast/ast_cursor.c +++ b/drivers/gpu/drm/ast/ast_cursor.c @@ -47,7 +47,7 @@ static void ast_cursor_fini(struct ast_private *ast) static void ast_cursor_release(struct drm_device *dev, void *ptr) { - struct ast_private *ast = dev->dev_private; + struct ast_private *ast = to_ast_private(dev); ast_cursor_fini(ast); } diff --git a/drivers/gpu/drm/ast/ast_mode.c b/drivers/gpu/drm/ast/ast_mode.c index 201313ab3e71..01340b0e40f8 100644 --- a/drivers/gpu/drm/ast/ast_mode.c +++ b/drivers/gpu/drm/ast/ast_mode.c @@ -784,7 +784,7 @@ ast_cursor_plane_helper_atomic_update(struct drm_plane *plane, { struct drm_plane_state *state = plane->state; struct drm_framebuffer *fb = state->fb; - struct ast_private *ast = plane->dev->dev_private; + struct ast_private *ast = to_ast_private(plane->dev); unsigned int offset_x, offset_y; offset_x = AST_MAX_HWC_WIDTH - fb->width; -- 2.27.0 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH 02/13] drm/ast: Test if I2C support has been initialized
The ast driver is supposed to work without I2C support. This is tested by looking at the connector's i2c field being non-NULL. After embedding the I2C structure in the connector, the i2c field will not be a pointer. So change the test to look at the dev field in struct ast_i2c_chan. ast_get_modes() did not really test if I2C has been initialized, so the patch adds this test as well. Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/ast/ast_mode.c | 23 ++- 1 file changed, 18 insertions(+), 5 deletions(-) diff --git a/drivers/gpu/drm/ast/ast_mode.c b/drivers/gpu/drm/ast/ast_mode.c index 19f1dfc8e9e0..45be020afcad 100644 --- a/drivers/gpu/drm/ast/ast_mode.c +++ b/drivers/gpu/drm/ast/ast_mode.c @@ -603,7 +603,6 @@ static struct ast_i2c_chan *ast_i2c_create(struct drm_device *dev) i2c->adapter.owner = THIS_MODULE; i2c->adapter.class = I2C_CLASS_DDC; i2c->adapter.dev.parent = &dev->pdev->dev; - i2c->dev = dev; i2c_set_adapdata(&i2c->adapter, i2c); snprintf(i2c->adapter.name, sizeof(i2c->adapter.name), "AST i2c bit bus"); @@ -622,17 +621,30 @@ static struct ast_i2c_chan *ast_i2c_create(struct drm_device *dev) goto out_free; } + i2c->dev = dev; /* signals presence of I2C support */ + return i2c; out_free: kfree(i2c); return NULL; } -static void ast_i2c_destroy(struct ast_i2c_chan *i2c) +static bool ast_i2c_is_initialized(struct ast_i2c_chan *i2c) { - if (!i2c) + return i2c && !!i2c->dev; +} + +static void ast_i2c_fini(struct ast_i2c_chan *i2c) +{ + if (!ast_i2c_is_initialized(i2c)) return; i2c_del_adapter(&i2c->adapter); + i2c->dev = NULL; /* clear to signal absence of I2C support */ +} + +static void ast_i2c_destroy(struct ast_i2c_chan *i2c) +{ + ast_i2c_fini(i2c); kfree(i2c); } @@ -1054,6 +1066,7 @@ static int ast_get_modes(struct drm_connector *connector) { struct ast_connector *ast_connector = to_ast_connector(connector); struct ast_private *ast = to_ast_private(connector->dev); + struct ast_i2c_chan *i2c = ast_connector->i2c; struct edid *edid; int ret; bool flags = false; @@ -1069,8 +1082,8 @@ static int ast_get_modes(struct drm_connector *connector) else kfree(edid); } - if (!flags) - edid = drm_get_edid(connector, &ast_connector->i2c->adapter); + if (!flags && ast_i2c_is_initialized(i2c)) + edid = drm_get_edid(connector, &i2c->adapter); if (edid) { drm_connector_update_edid_property(&ast_connector->base, edid); ret = drm_add_edid_modes(connector, edid); -- 2.27.0 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH 06/13] drm/ast: Separate DRM driver from PCI code
Putting the DRM driver to the top of the file and the PCI code to the bottom makes ast_drv.c more readable. While at it, the patch prefixes file-scope variables with ast_. Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/ast/ast_drv.c | 59 ++- 1 file changed, 31 insertions(+), 28 deletions(-) diff --git a/drivers/gpu/drm/ast/ast_drv.c b/drivers/gpu/drm/ast/ast_drv.c index 0b58f7aee6b0..9d04f2b5225c 100644 --- a/drivers/gpu/drm/ast/ast_drv.c +++ b/drivers/gpu/drm/ast/ast_drv.c @@ -43,9 +43,33 @@ int ast_modeset = -1; MODULE_PARM_DESC(modeset, "Disable/Enable modesetting"); module_param_named(modeset, ast_modeset, int, 0400); -#define PCI_VENDOR_ASPEED 0x1a03 +/* + * DRM driver + */ + +DEFINE_DRM_GEM_FOPS(ast_fops); + +static struct drm_driver ast_driver = { + .driver_features = DRIVER_ATOMIC | + DRIVER_GEM | + DRIVER_MODESET, + + .fops = &ast_fops, + .name = DRIVER_NAME, + .desc = DRIVER_DESC, + .date = DRIVER_DATE, + .major = DRIVER_MAJOR, + .minor = DRIVER_MINOR, + .patchlevel = DRIVER_PATCHLEVEL, -static struct drm_driver driver; + DRM_GEM_VRAM_DRIVER +}; + +/* + * PCI driver + */ + +#define PCI_VENDOR_ASPEED 0x1a03 #define AST_VGA_DEVICE(id, info) { \ .class = PCI_BASE_CLASS_DISPLAY << 16, \ @@ -56,13 +80,13 @@ static struct drm_driver driver; .subdevice = PCI_ANY_ID,\ .driver_data = (unsigned long) info } -static const struct pci_device_id pciidlist[] = { +static const struct pci_device_id ast_pciidlist[] = { AST_VGA_DEVICE(PCI_CHIP_AST2000, NULL), AST_VGA_DEVICE(PCI_CHIP_AST2100, NULL), {0, 0, 0}, }; -MODULE_DEVICE_TABLE(pci, pciidlist); +MODULE_DEVICE_TABLE(pci, ast_pciidlist); static void ast_kick_out_firmware_fb(struct pci_dev *pdev) { @@ -94,7 +118,7 @@ static int ast_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent) if (ret) return ret; - dev = drm_dev_alloc(&driver, &pdev->dev); + dev = drm_dev_alloc(&ast_driver, &pdev->dev); if (IS_ERR(dev)) return PTR_ERR(dev); @@ -118,11 +142,9 @@ static int ast_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent) err_drm_dev_put: drm_dev_put(dev); return ret; - } -static void -ast_pci_remove(struct pci_dev *pdev) +static void ast_pci_remove(struct pci_dev *pdev) { struct drm_device *dev = pci_get_drvdata(pdev); @@ -217,30 +239,12 @@ static const struct dev_pm_ops ast_pm_ops = { static struct pci_driver ast_pci_driver = { .name = DRIVER_NAME, - .id_table = pciidlist, + .id_table = ast_pciidlist, .probe = ast_pci_probe, .remove = ast_pci_remove, .driver.pm = &ast_pm_ops, }; -DEFINE_DRM_GEM_FOPS(ast_fops); - -static struct drm_driver driver = { - .driver_features = DRIVER_ATOMIC | - DRIVER_GEM | - DRIVER_MODESET, - - .fops = &ast_fops, - .name = DRIVER_NAME, - .desc = DRIVER_DESC, - .date = DRIVER_DATE, - .major = DRIVER_MAJOR, - .minor = DRIVER_MINOR, - .patchlevel = DRIVER_PATCHLEVEL, - - DRM_GEM_VRAM_DRIVER -}; - static int __init ast_init(void) { if (vgacon_text_force() && ast_modeset == -1) @@ -261,4 +265,3 @@ module_exit(ast_exit); MODULE_AUTHOR(DRIVER_AUTHOR); MODULE_DESCRIPTION(DRIVER_DESC); MODULE_LICENSE("GPL and additional rights"); - -- 2.27.0 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH 13/13] drm/ast: Managed device release
This turns the ast's device cleanup code into a managed release helper function. Note that the code uses devres helpers. The release function switches the device back to VGA mode and therefore runs during HW device cleanup; not at DRM device cleanup. Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/ast/ast_drv.c | 17 +++-- drivers/gpu/drm/ast/ast_drv.h | 1 - drivers/gpu/drm/ast/ast_main.c | 22 -- 3 files changed, 19 insertions(+), 21 deletions(-) diff --git a/drivers/gpu/drm/ast/ast_drv.c b/drivers/gpu/drm/ast/ast_drv.c index c394383a7979..f0b4af1c390a 100644 --- a/drivers/gpu/drm/ast/ast_drv.c +++ b/drivers/gpu/drm/ast/ast_drv.c @@ -120,35 +120,24 @@ static int ast_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent) return ret; ast = ast_device_create(&ast_driver, pdev, ent->driver_data); - if (IS_ERR(ast)) { - ret = PTR_ERR(ast); - goto err_drm_dev_put; - } + if (IS_ERR(ast)) + return PTR_ERR(ast); dev = &ast->base; ret = drm_dev_register(dev, ent->driver_data); if (ret) - goto err_ast_device_destroy; + return ret; drm_fbdev_generic_setup(dev, 32); return 0; - -err_ast_device_destroy: - ast_device_destroy(ast); -err_drm_dev_put: - drm_dev_put(dev); - return ret; } static void ast_pci_remove(struct pci_dev *pdev) { struct drm_device *dev = pci_get_drvdata(pdev); - struct ast_private *ast = to_ast_private(dev); drm_dev_unregister(dev); - ast_device_destroy(ast); - drm_dev_put(dev); } static int ast_drm_freeze(struct drm_device *dev) diff --git a/drivers/gpu/drm/ast/ast_drv.h b/drivers/gpu/drm/ast/ast_drv.h index 02908d005b99..0911136e0842 100644 --- a/drivers/gpu/drm/ast/ast_drv.h +++ b/drivers/gpu/drm/ast/ast_drv.h @@ -162,7 +162,6 @@ static inline struct ast_private *to_ast_private(struct drm_device *dev) struct ast_private *ast_device_create(struct drm_driver *drv, struct pci_dev *pdev, unsigned long flags); -void ast_device_destroy(struct ast_private *ast); #define AST_IO_AR_PORT_WRITE (0x40) #define AST_IO_MISC_PORT_WRITE (0x42) diff --git a/drivers/gpu/drm/ast/ast_main.c b/drivers/gpu/drm/ast/ast_main.c index 67e20727d82d..d62749a10cdd 100644 --- a/drivers/gpu/drm/ast/ast_main.c +++ b/drivers/gpu/drm/ast/ast_main.c @@ -380,6 +380,18 @@ static int ast_get_dram_info(struct drm_device *dev) return 0; } +/* + * Run this function as part of the HW device cleanup; not + * when the DRM device gets released. + */ +static void ast_device_release(void *data) +{ + struct ast_private *ast = data; + + /* enable standard VGA decode */ + ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0xa1, 0x04); +} + struct ast_private *ast_device_create(struct drm_driver *drv, struct pci_dev *pdev, unsigned long flags) @@ -438,11 +450,9 @@ struct ast_private *ast_device_create(struct drm_driver *drv, if (ret) return ERR_PTR(ret); - return ast; -} + ret = devm_add_action_or_reset(dev->dev, ast_device_release, ast); + if (ret) + return ERR_PTR(ret); -void ast_device_destroy(struct ast_private *ast) -{ - /* enable standard VGA decode */ - ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0xa1, 0x04); + return ast; } -- 2.27.0 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH 03/13] drm/ast: Embed I2C fields in struct ast_connector
With the I2C fields embedded in struct ast_connector, the related call to kzalloc() can be removed. Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/ast/ast_drv.h | 3 +-- drivers/gpu/drm/ast/ast_mode.c | 33 ++--- 2 files changed, 11 insertions(+), 25 deletions(-) diff --git a/drivers/gpu/drm/ast/ast_drv.h b/drivers/gpu/drm/ast/ast_drv.h index e3a264ac7ee2..d303df568099 100644 --- a/drivers/gpu/drm/ast/ast_drv.h +++ b/drivers/gpu/drm/ast/ast_drv.h @@ -98,7 +98,6 @@ enum ast_tx_chip { #define AST_HWC_SIGNATURE_HOTSPOTX 0x14 #define AST_HWC_SIGNATURE_HOTSPOTY 0x18 - struct ast_private { struct drm_device *dev; @@ -234,7 +233,7 @@ struct ast_i2c_chan { struct ast_connector { struct drm_connector base; - struct ast_i2c_chan *i2c; + struct ast_i2c_chan i2c; }; #define to_ast_connector(x) container_of(x, struct ast_connector, base) diff --git a/drivers/gpu/drm/ast/ast_mode.c b/drivers/gpu/drm/ast/ast_mode.c index 45be020afcad..f421a60d8a96 100644 --- a/drivers/gpu/drm/ast/ast_mode.c +++ b/drivers/gpu/drm/ast/ast_mode.c @@ -591,15 +591,10 @@ static void ast_i2c_setsda(void *i2c_priv, int data) } } -static struct ast_i2c_chan *ast_i2c_create(struct drm_device *dev) +static int ast_i2c_init(struct ast_i2c_chan *i2c, struct drm_device *dev) { - struct ast_i2c_chan *i2c; int ret; - i2c = kzalloc(sizeof(struct ast_i2c_chan), GFP_KERNEL); - if (!i2c) - return NULL; - i2c->adapter.owner = THIS_MODULE; i2c->adapter.class = I2C_CLASS_DDC; i2c->adapter.dev.parent = &dev->pdev->dev; @@ -618,20 +613,17 @@ static struct ast_i2c_chan *ast_i2c_create(struct drm_device *dev) ret = i2c_bit_add_bus(&i2c->adapter); if (ret) { drm_err(dev, "Failed to register bit i2c\n"); - goto out_free; + return ret; } i2c->dev = dev; /* signals presence of I2C support */ - return i2c; -out_free: - kfree(i2c); - return NULL; + return 0; } static bool ast_i2c_is_initialized(struct ast_i2c_chan *i2c) { - return i2c && !!i2c->dev; + return !!i2c->dev; } static void ast_i2c_fini(struct ast_i2c_chan *i2c) @@ -642,12 +634,6 @@ static void ast_i2c_fini(struct ast_i2c_chan *i2c) i2c->dev = NULL; /* clear to signal absence of I2C support */ } -static void ast_i2c_destroy(struct ast_i2c_chan *i2c) -{ - ast_i2c_fini(i2c); - kfree(i2c); -} - /* * Primary plane */ @@ -1066,7 +1052,7 @@ static int ast_get_modes(struct drm_connector *connector) { struct ast_connector *ast_connector = to_ast_connector(connector); struct ast_private *ast = to_ast_private(connector->dev); - struct ast_i2c_chan *i2c = ast_connector->i2c; + struct ast_i2c_chan *i2c = &ast_connector->i2c; struct edid *edid; int ret; bool flags = false; @@ -1154,7 +1140,7 @@ static enum drm_mode_status ast_mode_valid(struct drm_connector *connector, static void ast_connector_destroy(struct drm_connector *connector) { struct ast_connector *ast_connector = to_ast_connector(connector); - ast_i2c_destroy(ast_connector->i2c); + ast_i2c_fini(&ast_connector->i2c); drm_connector_cleanup(connector); kfree(connector); } @@ -1177,20 +1163,21 @@ static int ast_connector_init(struct drm_device *dev) struct ast_connector *ast_connector; struct drm_connector *connector; struct drm_encoder *encoder; + int ret; ast_connector = kzalloc(sizeof(struct ast_connector), GFP_KERNEL); if (!ast_connector) return -ENOMEM; connector = &ast_connector->base; - ast_connector->i2c = ast_i2c_create(dev); - if (!ast_connector->i2c) + ret = ast_i2c_init(&ast_connector->i2c, dev); + if (ret) drm_err(dev, "failed to add ddc bus for connector\n"); drm_connector_init_with_ddc(dev, connector, &ast_connector_funcs, DRM_MODE_CONNECTOR_VGA, - &ast_connector->i2c->adapter); + &ast_connector->i2c.adapter); drm_connector_helper_add(connector, &ast_connector_helper_funcs); -- 2.27.0 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH] drm/ttm/nouveau: don't call tt destroy callback on alloc failure.
Am 28.07.20 um 06:17 schrieb Dave Airlie: From: Dave Airlie This is confusing, and from my reading of all the drivers only nouveau got this right. Just make the API act under driver control of it's own allocation failing, and don't call destroy, if the page table fails to create there is nothing to cleanup here. (I'm willing to believe I've missed something here, so please review deeply). Signed-off-by: Dave Airlie That looks right to me as well, Reviewed-by: Christian König --- drivers/gpu/drm/nouveau/nouveau_sgdma.c | 9 +++-- drivers/gpu/drm/ttm/ttm_tt.c| 3 --- 2 files changed, 3 insertions(+), 9 deletions(-) diff --git a/drivers/gpu/drm/nouveau/nouveau_sgdma.c b/drivers/gpu/drm/nouveau/nouveau_sgdma.c index 20b6d0b3de5c..c3ccf661b7a6 100644 --- a/drivers/gpu/drm/nouveau/nouveau_sgdma.c +++ b/drivers/gpu/drm/nouveau/nouveau_sgdma.c @@ -95,12 +95,9 @@ nouveau_sgdma_create_ttm(struct ttm_buffer_object *bo, uint32_t page_flags) else nvbe->ttm.ttm.func = &nv50_sgdma_backend; - if (ttm_dma_tt_init(&nvbe->ttm, bo, page_flags)) - /* -* A failing ttm_dma_tt_init() will call ttm_tt_destroy() -* and thus our nouveau_sgdma_destroy() hook, so we don't need -* to free nvbe here. -*/ + if (ttm_dma_tt_init(&nvbe->ttm, bo, page_flags)) { + kfree(nvbe); return NULL; + } return &nvbe->ttm.ttm; } diff --git a/drivers/gpu/drm/ttm/ttm_tt.c b/drivers/gpu/drm/ttm/ttm_tt.c index bab67873cfd4..9d1c7177384c 100644 --- a/drivers/gpu/drm/ttm/ttm_tt.c +++ b/drivers/gpu/drm/ttm/ttm_tt.c @@ -244,7 +244,6 @@ int ttm_tt_init(struct ttm_tt *ttm, struct ttm_buffer_object *bo, ttm_tt_init_fields(ttm, bo, page_flags); if (ttm_tt_alloc_page_directory(ttm)) { - ttm_tt_destroy(ttm); pr_err("Failed allocating page table\n"); return -ENOMEM; } @@ -268,7 +267,6 @@ int ttm_dma_tt_init(struct ttm_dma_tt *ttm_dma, struct ttm_buffer_object *bo, INIT_LIST_HEAD(&ttm_dma->pages_list); if (ttm_dma_tt_alloc_page_directory(ttm_dma)) { - ttm_tt_destroy(ttm); pr_err("Failed allocating page table\n"); return -ENOMEM; } @@ -290,7 +288,6 @@ int ttm_sg_tt_init(struct ttm_dma_tt *ttm_dma, struct ttm_buffer_object *bo, else ret = ttm_dma_tt_alloc_page_directory(ttm_dma); if (ret) { - ttm_tt_destroy(ttm); pr_err("Failed allocating page table\n"); return -ENOMEM; } ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH] drm/ttm: drop unusued function declaration
Am 28.07.20 um 06:51 schrieb Dave Airlie: From: Dave Airlie This was removed in f5a9a9383f279de9da63296cb623a6418a66196b drm/ttm: remove TTM_MEMTYPE_FLAG_CMA but the the declaration was left dangling. Signed-off-by: Dave Airlie Reviewed-by: Christian König --- include/drm/ttm/ttm_bo_driver.h | 11 --- 1 file changed, 11 deletions(-) diff --git a/include/drm/ttm/ttm_bo_driver.h b/include/drm/ttm/ttm_bo_driver.h index 71b195e78c7c..5a37f1cc057e 100644 --- a/include/drm/ttm/ttm_bo_driver.h +++ b/include/drm/ttm/ttm_bo_driver.h @@ -525,17 +525,6 @@ ttm_flag_masked(uint32_t *old, uint32_t new, uint32_t mask) * ttm_bo.c */ -/** - * ttm_mem_reg_is_pci - * - * @bdev: Pointer to a struct ttm_bo_device. - * @mem: A valid struct ttm_mem_reg. - * - * Returns true if the memory described by @mem is PCI memory, - * false otherwise. - */ -bool ttm_mem_reg_is_pci(struct ttm_bo_device *bdev, struct ttm_mem_reg *mem); - /** * ttm_bo_mem_space * ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v2] drm/hisilicon: Fixed the warning: Assignment of 0/1 to bool variable
Hi Am 07.07.20 um 04:58 schrieb Tian Tao: > fixed the following warning: > hibmc_drm_drv.c:296:1-18:WARNING: Assignment of 0/1 to bool variable. > hibmc_drm_drv.c:301:2-19: WARNING: Assignment of 0/1 to bool variable. > > v2: > using the pci_dev.msi_enabled instead of priv->msi_enabled. > > Signed-off-by: Tian Tao > --- > drivers/gpu/drm/hisilicon/hibmc/hibmc_drm_drv.c | 6 +++--- > drivers/gpu/drm/hisilicon/hibmc/hibmc_drm_drv.h | 1 - > 2 files changed, 3 insertions(+), 4 deletions(-) > > diff --git a/drivers/gpu/drm/hisilicon/hibmc/hibmc_drm_drv.c > b/drivers/gpu/drm/hisilicon/hibmc/hibmc_drm_drv.c > index 249c298..83c7bb5 100644 > --- a/drivers/gpu/drm/hisilicon/hibmc/hibmc_drm_drv.c > +++ b/drivers/gpu/drm/hisilicon/hibmc/hibmc_drm_drv.c > @@ -254,7 +254,7 @@ static int hibmc_unload(struct drm_device *dev) > > if (dev->irq_enabled) > drm_irq_uninstall(dev); > - if (priv->msi_enabled) > + if (dev->pdev->msi_enabled) You don't need these tests and you don't have to set dev->pdev->msi_enabled by yourself. Just call pci_enable_msi() and pci_disable_msi() and they should do the right thing. Best regards Thomas > pci_disable_msi(dev->pdev); > > hibmc_kms_fini(priv); > @@ -294,12 +294,12 @@ static int hibmc_load(struct drm_device *dev) > goto err; > } > > - priv->msi_enabled = 0; > + dev->pdev->msi_enabled = 0; > ret = pci_enable_msi(dev->pdev); > if (ret) { > DRM_WARN("enabling MSI failed: %d\n", ret); > } else { > - priv->msi_enabled = 1; > + dev->pdev->msi_enabled = 1; > ret = drm_irq_install(dev, dev->pdev->irq); > if (ret) > DRM_WARN("install irq failed: %d\n", ret); > diff --git a/drivers/gpu/drm/hisilicon/hibmc/hibmc_drm_drv.h > b/drivers/gpu/drm/hisilicon/hibmc/hibmc_drm_drv.h > index 6097687..a683763 100644 > --- a/drivers/gpu/drm/hisilicon/hibmc/hibmc_drm_drv.h > +++ b/drivers/gpu/drm/hisilicon/hibmc/hibmc_drm_drv.h > @@ -25,7 +25,6 @@ struct hibmc_drm_private { > void __iomem *fb_map; > unsigned long fb_base; > unsigned long fb_size; > - bool msi_enabled; > > /* drm */ > struct drm_device *dev; > -- Thomas Zimmermann Graphics Driver Developer SUSE Software Solutions Germany GmbH Maxfeldstr. 5, 90409 Nürnberg, Germany (HRB 36809, AG Nürnberg) Geschäftsführer: Felix Imendörffer signature.asc Description: OpenPGP digital signature ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH] drm/ttm/nouveau: consolidate slowpath reserve
On Tue, 28 Jul 2020 at 17:30, Christian König wrote: > > Am 28.07.20 um 08:24 schrieb Dave Airlie: > > From: Dave Airlie > > > > The WARN_ON in the non-underscore path is off questionable value > > (can we drop it from the non-slowpath?). At least for nouveau > > where it's just looked up the gem object we know the ttm object > > has a reference always so we can skip the check. > > Yeah, agreed. Wanted to look into removing that for quite some time as well. > > > It's probably nouveau could use execbut utils here at some point > > but for now align the code between them to always call the __ > > versions, and remove the non underscored version. > > Can we do it the other way around and remove all uses of the __ versions > of the functions instead and then merge the __ version into the normal > one without the WARN_ON()? Yes sounds like a plan, I just wasn't sure the WARN_ON had value, bit since you agree is dubious at best, I'm happy to rip it out. Will send a v2 tomorrow. Dave. ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [Linux-kernel-mentees] [PATCH] drm/bufs: Prevent kernel-infoleak in copy_one_buf()
On Tue, Jul 28, 2020 at 3:45 AM Peilin Ye wrote: > > copy_one_buf() is copying uninitialized stack memory to userspace due to > the compiler not initializing holes in statically allocated structures. > Fix it by initializing `v` with memset(). I would add 'potentially' somewhere in that description: it is architecture dependent whether there are holes in this structure as 'enum' types and 'long' are both dependent on the ABI, and even if there is a hole, it is undefined behavior whether the hold gets initialized. Other than that, the patch looks good. > Cc: sta...@vger.kernel.org > Fixes: 5c7640ab6258 ("switch compat_drm_infobufs() to drm_ioctl_kernel()") > Suggested-by: Dan Carpenter > Signed-off-by: Peilin Ye Acked-by: Arnd Bergmann > --- > drivers/gpu/drm/drm_bufs.c | 12 > 1 file changed, 8 insertions(+), 4 deletions(-) > > diff --git a/drivers/gpu/drm/drm_bufs.c b/drivers/gpu/drm/drm_bufs.c > index a0735fbc144b..f99cd4a3f951 100644 > --- a/drivers/gpu/drm/drm_bufs.c > +++ b/drivers/gpu/drm/drm_bufs.c > @@ -1349,10 +1349,14 @@ static int copy_one_buf(void *data, int count, struct > drm_buf_entry *from) > { > struct drm_buf_info *request = data; > struct drm_buf_desc __user *to = &request->list[count]; > - struct drm_buf_desc v = {.count = from->buf_count, > -.size = from->buf_size, > -.low_mark = from->low_mark, > -.high_mark = from->high_mark}; > + struct drm_buf_desc v; > + > + memset(&v, 0, sizeof(v)); > + > + v.count = from->buf_count; > + v.size = from->buf_size; > + v.low_mark = from->low_mark; > + v.high_mark = from->high_mark; > > if (copy_to_user(to, &v, offsetof(struct drm_buf_desc, flags))) > return -EFAULT; > -- > 2.25.1 > ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [Freedreno] [PATCH V2] drm: hold gem reference until object is no longer accessed
On Mon, Jul 27, 2020 at 05:54:59PM -0400, coh...@codeaurora.org wrote: > On 2020-07-27 16:11, dan...@ffwll.ch wrote: > > On Mon, Jul 27, 2020 at 09:55:07PM +0200, Greg KH wrote: > > > On Mon, Jul 20, 2020 at 06:30:50PM -0400, Steve Cohen wrote: > > > > A use-after-free in drm_gem_open_ioctl can happen if the > > > > GEM object handle is closed between the idr lookup and > > > > retrieving the size from said object since a local reference > > > > is not being held at that point. Hold the local reference > > > > while the object can still be accessed to fix this and > > > > plug the potential security hole. > > > > > > > > Signed-off-by: Steve Cohen > > > > --- > > > > drivers/gpu/drm/drm_gem.c | 10 -- > > > > 1 file changed, 4 insertions(+), 6 deletions(-) > > > > > > > > diff --git a/drivers/gpu/drm/drm_gem.c b/drivers/gpu/drm/drm_gem.c > > > > index 7bf628e..ee2058a 100644 > > > > --- a/drivers/gpu/drm/drm_gem.c > > > > +++ b/drivers/gpu/drm/drm_gem.c > > > > @@ -871,9 +871,6 @@ drm_gem_flink_ioctl(struct drm_device *dev, void > > > > *data, > > > > * @file_priv: drm file-private structure > > > > * > > > > * Open an object using the global name, returning a handle and the > > > > size. > > > > - * > > > > - * This handle (of course) holds a reference to the object, so the > > > > object > > > > - * will not go away until the handle is deleted. > > > > */ > > > > int > > > > drm_gem_open_ioctl(struct drm_device *dev, void *data, > > > > @@ -898,14 +895,15 @@ drm_gem_open_ioctl(struct drm_device *dev, void > > > > *data, > > > > > > > > /* drm_gem_handle_create_tail unlocks dev->object_name_lock. */ > > > > ret = drm_gem_handle_create_tail(file_priv, obj, &handle); > > > > - drm_gem_object_put_unlocked(obj); > > > > if (ret) > > > > - return ret; > > > > + goto err; > > > > > > > > args->handle = handle; > > > > args->size = obj->size; > > > > > > > > - return 0; > > > > +err: > > > > + drm_gem_object_put_unlocked(obj); > > > > + return ret; > > > > } > > > > > > > > /** > > > > > > As this seems to fix an important issue, any reason it wasn't cc: > > > stable > > > on it so that it gets backported properly? > > > > > > How about a "Fixes:" tag so that we know what commit id it fixes so we > > > know how far back to backport things? > > > > > > And a hint to the maintainers that "this is an issue that needs to get > > > into 5.8-final, it shouldn't wait around longer please" would have > > > also > > > been nice to see :) > > > > > > And what chagned from v1, aren't you supposed to list that somewhere > > > in > > > the changelog or below the --- line (never remember what DRM drivers > > > want here...) > > > > > > Care to send a v3? > > > > Don't worry, I'm pushing this to drm-misc-fixes now, should still make > > it > > to 5.8. Plus cc: stable. I didn't bother with Fixes: since I think the > > bug > > is rather old. Also, worst case you leak 32bit of some kernel memory > > that > > got reused already (but yeah I know that's often enough to get the foot > > in > > somewhere nasty and crack the door open). > > > > I think it fell through cracks because Sam said he'll apply, guess that > > didn't happen. > > Sam added his Reviewed-By on V1 with a comment to rename the goto label, > but in V2 I also updated the API documentation and the commit text for > a more complete change and thought he would re-add the tag. > > > Also yes a changelog, somewhere, for next time around. > > Apologies, it won't happen again. Should I still submit a V3? > It looks like you've got Greg's concerns covered. Uh no, but we need another patch to re-add the kerneldoc you deleted. I missed that when merging your patch. Also that's kinda what patch changelogs are for, for blind reviewers like me :-) -Daniel > > -Steve > > > -Daniel > > > > > > > > > > thanks, > > > > > > greg k-h -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH] drm/amd/display: Clear dm_state for fast updates
On Mon, Jul 27, 2020 at 10:49:48PM -0400, Kazlauskas, Nicholas wrote: > On 2020-07-27 5:32 p.m., Daniel Vetter wrote: > > On Mon, Jul 27, 2020 at 11:11 PM Mazin Rezk wrote: > > > > > > On Monday, July 27, 2020 4:29 PM, Daniel Vetter wrote: > > > > > > > On Mon, Jul 27, 2020 at 9:28 PM Christian König > > > > wrote: > > > > > > > > > > Am 27.07.20 um 16:05 schrieb Kazlauskas, Nicholas: > > > > > > On 2020-07-27 9:39 a.m., Christian König wrote: > > > > > > > Am 27.07.20 um 07:40 schrieb Mazin Rezk: > > > > > > > > This patch fixes a race condition that causes a use-after-free > > > > > > > > during > > > > > > > > amdgpu_dm_atomic_commit_tail. This can occur when 2 non-blocking > > > > > > > > commits > > > > > > > > are requested and the second one finishes before the first. > > > > > > > > Essentially, > > > > > > > > this bug occurs when the following sequence of events happens: > > > > > > > > > > > > > > > > 1. Non-blocking commit #1 is requested w/ a new dm_state #1 and > > > > > > > > is > > > > > > > > deferred to the workqueue. > > > > > > > > > > > > > > > > 2. Non-blocking commit #2 is requested w/ a new dm_state #2 and > > > > > > > > is > > > > > > > > deferred to the workqueue. > > > > > > > > > > > > > > > > 3. Commit #2 starts before commit #1, dm_state #1 is used in the > > > > > > > > commit_tail and commit #2 completes, freeing dm_state #1. > > > > > > > > > > > > > > > > 4. Commit #1 starts after commit #2 completes, uses the freed > > > > > > > > dm_state > > > > > > > > 1 and dereferences a freelist pointer while setting the context. > > > > > > > > > > > > > > Well I only have a one mile high view on this, but why don't you > > > > > > > let > > > > > > > the work items execute in order? > > > > > > > > > > > > > > That would be better anyway cause this way we don't trigger a > > > > > > > cache > > > > > > > line ping pong between CPUs. > > > > > > > > > > > > > > Christian. > > > > > > > > > > > > We use the DRM helpers for managing drm_atomic_commit_state and > > > > > > those > > > > > > helpers internally push non-blocking commit work into the system > > > > > > unbound work queue. > > > > > > > > > > Mhm, well if you send those helper atomic commits in the order A,B and > > > > > they execute it in the order B,A I would call that a bug :) > > > > > > > > The way it works is it pushes all commits into unbound work queue, but > > > > then forces serialization as needed. We do _not_ want e.g. updates on > > > > different CRTC to be serialized, that would result in lots of judder. > > > > And hw is funny enough that there's all kinds of dependencies. > > > > > > > > The way you force synchronization is by adding other CRTC state > > > > objects. So if DC is busted and can only handle a single update per > > > > work item, then I guess you always need all CRTC states and everything > > > > will be run in order. But that also totally kills modern multi-screen > > > > compositors. Xorg isn't modern, just in case that's not clear :-) > > > > > > > > Lucking at the code it seems like you indeed have only a single dm > > > > state, so yeah global sync is what you'll need as immediate fix, and > > > > then maybe fix up DM to not be quite so silly ... or at least only do > > > > the dm state stuff when really needed. > > > > > > > > We could also sprinkle the drm_crtc_commit structure around a bit > > > > (it's the glue that provides the synchronization across commits), but > > > > since your dm state is global just grabbing all crtc states > > > > unconditionally as part of that is probably best. > > > > > > > > > > While we could duplicate a copy of that code with nothing but the > > > > > > workqueue changed that isn't something I'd really like to maintain > > > > > > going forward. > > > > > > > > > > I'm not talking about duplicating the code, I'm talking about fixing > > > > > the > > > > > helpers. I don't know that code well, but from the outside it sounds > > > > > like a bug there. > > > > > > > > > > And executing work items in the order they are submitted is trivial. > > > > > > > > > > Had anybody pinged Daniel or other people familiar with the helper > > > > > code > > > > > about it? > > > > > > > > Yeah something is wrong here, and the fix looks horrible :-) > > > > > > > > Aside, I've also seen some recent discussion flare up about > > > > drm_atomic_state_get/put used to paper over some other use-after-free, > > > > but this time related to interrupt handlers. Maybe a few rules about > > > > that: > > > > - dont > > > > - especially not when it's interrupt handlers, because you can't call > > > > drm_atomic_state_put from interrupt handlers. > > > > > > > > Instead have an spin_lock_irq to protect the shared date with your > > > > interrupt handler, and _copy_ the date over. This is e.g. what > > > > drm_crtc_arm_vblank_event does. > > > > > > Nicholas wrote a patch that attempted to resolve the issue by adding every > > > CRTC into the
Re: [PATCH] ttm: ttm_bo_swapout_all doesn't use it's argument.
On Tue, Jul 28, 2020 at 01:42:54PM +1000, Dave Airlie wrote: > From: Dave Airlie > > Just drop the argument from this. > > This does ask the question if this is the function vmwgfx > should be using or should it be doing an evict all like > the other drivers. Yeah this looks a bit like ttm_bo_swapout_all shouldn't even be exported really, it's part of the internal shrinker stuff. -Daniel > > Signed-off-by: Dave Airlie > --- > drivers/gpu/drm/ttm/ttm_bo.c| 2 +- > drivers/gpu/drm/vmwgfx/vmwgfx_drv.c | 2 +- > include/drm/ttm/ttm_bo_api.h| 2 +- > 3 files changed, 3 insertions(+), 3 deletions(-) > > diff --git a/drivers/gpu/drm/ttm/ttm_bo.c b/drivers/gpu/drm/ttm/ttm_bo.c > index b03747717ec7..f297fd5e02d4 100644 > --- a/drivers/gpu/drm/ttm/ttm_bo.c > +++ b/drivers/gpu/drm/ttm/ttm_bo.c > @@ -1838,7 +1838,7 @@ int ttm_bo_swapout(struct ttm_bo_global *glob, struct > ttm_operation_ctx *ctx) > } > EXPORT_SYMBOL(ttm_bo_swapout); > > -void ttm_bo_swapout_all(struct ttm_bo_device *bdev) > +void ttm_bo_swapout_all(void) > { > struct ttm_operation_ctx ctx = { > .interruptible = false, > diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_drv.c > b/drivers/gpu/drm/vmwgfx/vmwgfx_drv.c > index 470428387878..fb39826f72c1 100644 > --- a/drivers/gpu/drm/vmwgfx/vmwgfx_drv.c > +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_drv.c > @@ -1352,7 +1352,7 @@ static int vmw_pm_freeze(struct device *kdev) > vmw_execbuf_release_pinned_bo(dev_priv); > vmw_resource_evict_all(dev_priv); > vmw_release_device_early(dev_priv); > - ttm_bo_swapout_all(&dev_priv->bdev); > + ttm_bo_swapout_all(); > if (dev_priv->enable_fb) > vmw_fifo_resource_dec(dev_priv); > if (atomic_read(&dev_priv->num_fifo_resources) != 0) { > diff --git a/include/drm/ttm/ttm_bo_api.h b/include/drm/ttm/ttm_bo_api.h > index b1c705a93517..a9e13b252820 100644 > --- a/include/drm/ttm/ttm_bo_api.h > +++ b/include/drm/ttm/ttm_bo_api.h > @@ -692,7 +692,7 @@ ssize_t ttm_bo_io(struct ttm_bo_device *bdev, struct file > *filp, > > int ttm_bo_swapout(struct ttm_bo_global *glob, > struct ttm_operation_ctx *ctx); > -void ttm_bo_swapout_all(struct ttm_bo_device *bdev); > +void ttm_bo_swapout_all(void); > > /** > * ttm_bo_uses_embedded_gem_object - check if the given bo uses the > -- > 2.26.2 > > ___ > dri-devel mailing list > dri-devel@lists.freedesktop.org > https://lists.freedesktop.org/mailman/listinfo/dri-devel -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH 11/13] drm/ast: Managed release of ast firmware
On Tue, Jul 28, 2020 at 09:44:23AM +0200, Thomas Zimmermann wrote: > The ast driver loads firmware for the DP501 display encoder. The > patch replaces the removal code with a managed release function. > > Signed-off-by: Thomas Zimmermann Hm a devm_request_firmware which does exactly this would be nice I think. Maybe as a follow-up refactor? -Daniel > --- > drivers/gpu/drm/ast/ast_dp501.c | 23 ++- > drivers/gpu/drm/ast/ast_drv.h | 1 - > drivers/gpu/drm/ast/ast_main.c | 3 --- > 3 files changed, 14 insertions(+), 13 deletions(-) > > diff --git a/drivers/gpu/drm/ast/ast_dp501.c b/drivers/gpu/drm/ast/ast_dp501.c > index 4b85a504825a..88121c0e0d05 100644 > --- a/drivers/gpu/drm/ast/ast_dp501.c > +++ b/drivers/gpu/drm/ast/ast_dp501.c > @@ -8,11 +8,24 @@ > > MODULE_FIRMWARE("ast_dp501_fw.bin"); > > +static void ast_release_firmware(void *data) > +{ > + struct ast_private *ast = data; > + > + release_firmware(ast->dp501_fw); > + ast->dp501_fw = NULL; > +} > + > static int ast_load_dp501_microcode(struct drm_device *dev) > { > struct ast_private *ast = to_ast_private(dev); > + int ret; > + > + ret = request_firmware(&ast->dp501_fw, "ast_dp501_fw.bin", dev->dev); > + if (ret) > + return ret; > > - return request_firmware(&ast->dp501_fw, "ast_dp501_fw.bin", dev->dev); > + return devm_add_action_or_reset(dev->dev, ast_release_firmware, ast); > } > > static void send_ack(struct ast_private *ast) > @@ -435,11 +448,3 @@ void ast_init_3rdtx(struct drm_device *dev) > } > } > } > - > -void ast_release_firmware(struct drm_device *dev) > -{ > - struct ast_private *ast = to_ast_private(dev); > - > - release_firmware(ast->dp501_fw); > - ast->dp501_fw = NULL; > -} > diff --git a/drivers/gpu/drm/ast/ast_drv.h b/drivers/gpu/drm/ast/ast_drv.h > index 86c9a7ac712b..02908d005b99 100644 > --- a/drivers/gpu/drm/ast/ast_drv.h > +++ b/drivers/gpu/drm/ast/ast_drv.h > @@ -312,7 +312,6 @@ bool ast_backup_fw(struct drm_device *dev, u8 *addr, u32 > size); > bool ast_dp501_read_edid(struct drm_device *dev, u8 *ediddata); > u8 ast_get_dp501_max_clk(struct drm_device *dev); > void ast_init_3rdtx(struct drm_device *dev); > -void ast_release_firmware(struct drm_device *dev); > > /* ast_cursor.c */ > int ast_cursor_init(struct ast_private *ast); > diff --git a/drivers/gpu/drm/ast/ast_main.c b/drivers/gpu/drm/ast/ast_main.c > index 792fb7f616ec..e3b7748335a3 100644 > --- a/drivers/gpu/drm/ast/ast_main.c > +++ b/drivers/gpu/drm/ast/ast_main.c > @@ -442,11 +442,8 @@ struct ast_private *ast_device_create(struct drm_driver > *drv, > > void ast_device_destroy(struct ast_private *ast) > { > - struct drm_device *dev = &ast->base; > - > /* enable standard VGA decode */ > ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0xa1, 0x04); > > - ast_release_firmware(dev); > kfree(ast->dp501_fw_addr); > } > -- > 2.27.0 > -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH 12/13] drm/ast: Manage release of firmware backup memory
On Tue, Jul 28, 2020 at 09:44:24AM +0200, Thomas Zimmermann wrote: > The ast driver keeps a backup copy of the DP501 encoder's firmware. This > patch adds managed release of the allocated memory. > > Signed-off-by: Thomas Zimmermann We can't really do anything with the firmware after the device is gone, so I think this is one of the very rare exceptions where devm_kzalloc is the right thing to do! Totally minor nit though, since either way it gets cleaned up. But I think conceptually cleaner. -Daniel > --- > drivers/gpu/drm/ast/ast_main.c | 7 +++ > 1 file changed, 3 insertions(+), 4 deletions(-) > > diff --git a/drivers/gpu/drm/ast/ast_main.c b/drivers/gpu/drm/ast/ast_main.c > index e3b7748335a3..67e20727d82d 100644 > --- a/drivers/gpu/drm/ast/ast_main.c > +++ b/drivers/gpu/drm/ast/ast_main.c > @@ -33,6 +33,7 @@ > #include > #include > #include > +#include > > #include "ast_drv.h" > > @@ -231,11 +232,11 @@ static int ast_detect_chip(struct drm_device *dev, bool > *need_post) > ast->tx_chip_type = AST_TX_SIL164; > break; > case 0x08: > - ast->dp501_fw_addr = kzalloc(32*1024, GFP_KERNEL); > + ast->dp501_fw_addr = drmm_kzalloc(dev, 32*1024, > GFP_KERNEL); > if (ast->dp501_fw_addr) { > /* backup firmware */ > if (ast_backup_fw(dev, ast->dp501_fw_addr, > 32*1024)) { > - kfree(ast->dp501_fw_addr); > + drmm_kfree(dev, ast->dp501_fw_addr); > ast->dp501_fw_addr = NULL; > } > } > @@ -444,6 +445,4 @@ void ast_device_destroy(struct ast_private *ast) > { > /* enable standard VGA decode */ > ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0xa1, 0x04); > - > - kfree(ast->dp501_fw_addr); > } > -- > 2.27.0 > -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: ttm_tt_set_placement_caching on vram->ram transfers
Am 28.07.20 um 05:23 schrieb Dave Airlie: Hi Christian + Ben, Just been reviewing around driver TTM code, and found an inconsistency, amdgpu + radeon both call the above before binding the ttm and going gpu vram->ram copies, but I don't see nouveau doing it Not sure if it could cause any issues, but it does look inconsistent. What amdgpu and radeon do here sounds superfluous to me. The tt structure should have been allocated with the right caching attributes in the first place. BTW: Changing the caching attributes of pages on the fly is utterly nonsense to begin with. This only works 100% correctly on x86, and there only by coincident :) Christian. Dave. ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH 04/13] drm/ast: Managed release of I2C adapter
On Tue, Jul 28, 2020 at 09:44:16AM +0200, Thomas Zimmermann wrote: > Managed releases of the device's I2C adapter simplify the connector's > release. > > Signed-off-by: Thomas Zimmermann I think this breaks bisect, since at this point the release callback is called when the connector is already gone. At the end of the series it's fine again though. I've done a very cursory reading of your series to look for high-level issues, I think overall reasonable. On the series: Acked-by: Daniel Vetter But maybe you want to polish a bit more, up to you. -Daniel > --- > drivers/gpu/drm/ast/ast_mode.c | 21 ++--- > 1 file changed, 10 insertions(+), 11 deletions(-) > > diff --git a/drivers/gpu/drm/ast/ast_mode.c b/drivers/gpu/drm/ast/ast_mode.c > index f421a60d8a96..27eb49bd12b3 100644 > --- a/drivers/gpu/drm/ast/ast_mode.c > +++ b/drivers/gpu/drm/ast/ast_mode.c > @@ -39,6 +39,7 @@ > #include > #include > #include > +#include > #include > #include > #include > @@ -591,6 +592,14 @@ static void ast_i2c_setsda(void *i2c_priv, int data) > } > } > > +static void ast_i2c_release(struct drm_device *dev, void *data) > +{ > + struct ast_i2c_chan *i2c = data; > + > + i2c_del_adapter(&i2c->adapter); > + i2c->dev = NULL; /* clear to signal absence of I2C support */ > +} > + > static int ast_i2c_init(struct ast_i2c_chan *i2c, struct drm_device *dev) > { > int ret; > @@ -618,7 +627,7 @@ static int ast_i2c_init(struct ast_i2c_chan *i2c, struct > drm_device *dev) > > i2c->dev = dev; /* signals presence of I2C support */ > > - return 0; > + return drmm_add_action_or_reset(dev, ast_i2c_release, i2c); > } > > static bool ast_i2c_is_initialized(struct ast_i2c_chan *i2c) > @@ -626,14 +635,6 @@ static bool ast_i2c_is_initialized(struct ast_i2c_chan > *i2c) > return !!i2c->dev; > } > > -static void ast_i2c_fini(struct ast_i2c_chan *i2c) > -{ > - if (!ast_i2c_is_initialized(i2c)) > - return; > - i2c_del_adapter(&i2c->adapter); > - i2c->dev = NULL; /* clear to signal absence of I2C support */ > -} > - > /* > * Primary plane > */ > @@ -1139,8 +1140,6 @@ static enum drm_mode_status ast_mode_valid(struct > drm_connector *connector, > > static void ast_connector_destroy(struct drm_connector *connector) > { > - struct ast_connector *ast_connector = to_ast_connector(connector); > - ast_i2c_fini(&ast_connector->i2c); > drm_connector_cleanup(connector); > kfree(connector); > } > -- > 2.27.0 > -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH 11/13] drm/ast: Managed release of ast firmware
Hi Am 28.07.20 um 11:17 schrieb dan...@ffwll.ch: > On Tue, Jul 28, 2020 at 09:44:23AM +0200, Thomas Zimmermann wrote: >> The ast driver loads firmware for the DP501 display encoder. The >> patch replaces the removal code with a managed release function. >> >> Signed-off-by: Thomas Zimmermann > > Hm a devm_request_firmware which does exactly this would be nice I think. > Maybe as a follow-up refactor? There are so many ideas for follow-up patches wrt. devres and drmres, we should add a todo item to collect them. Especially, devres is much more over head in terms of reviews and kernel building/testing tha tit makes sense to collect ideas and address them in larger chunks. Best regards Thomas > -Daniel > >> --- >> drivers/gpu/drm/ast/ast_dp501.c | 23 ++- >> drivers/gpu/drm/ast/ast_drv.h | 1 - >> drivers/gpu/drm/ast/ast_main.c | 3 --- >> 3 files changed, 14 insertions(+), 13 deletions(-) >> >> diff --git a/drivers/gpu/drm/ast/ast_dp501.c >> b/drivers/gpu/drm/ast/ast_dp501.c >> index 4b85a504825a..88121c0e0d05 100644 >> --- a/drivers/gpu/drm/ast/ast_dp501.c >> +++ b/drivers/gpu/drm/ast/ast_dp501.c >> @@ -8,11 +8,24 @@ >> >> MODULE_FIRMWARE("ast_dp501_fw.bin"); >> >> +static void ast_release_firmware(void *data) >> +{ >> +struct ast_private *ast = data; >> + >> +release_firmware(ast->dp501_fw); >> +ast->dp501_fw = NULL; >> +} >> + >> static int ast_load_dp501_microcode(struct drm_device *dev) >> { >> struct ast_private *ast = to_ast_private(dev); >> +int ret; >> + >> +ret = request_firmware(&ast->dp501_fw, "ast_dp501_fw.bin", dev->dev); >> +if (ret) >> +return ret; >> >> -return request_firmware(&ast->dp501_fw, "ast_dp501_fw.bin", dev->dev); >> +return devm_add_action_or_reset(dev->dev, ast_release_firmware, ast); >> } >> >> static void send_ack(struct ast_private *ast) >> @@ -435,11 +448,3 @@ void ast_init_3rdtx(struct drm_device *dev) >> } >> } >> } >> - >> -void ast_release_firmware(struct drm_device *dev) >> -{ >> -struct ast_private *ast = to_ast_private(dev); >> - >> -release_firmware(ast->dp501_fw); >> -ast->dp501_fw = NULL; >> -} >> diff --git a/drivers/gpu/drm/ast/ast_drv.h b/drivers/gpu/drm/ast/ast_drv.h >> index 86c9a7ac712b..02908d005b99 100644 >> --- a/drivers/gpu/drm/ast/ast_drv.h >> +++ b/drivers/gpu/drm/ast/ast_drv.h >> @@ -312,7 +312,6 @@ bool ast_backup_fw(struct drm_device *dev, u8 *addr, u32 >> size); >> bool ast_dp501_read_edid(struct drm_device *dev, u8 *ediddata); >> u8 ast_get_dp501_max_clk(struct drm_device *dev); >> void ast_init_3rdtx(struct drm_device *dev); >> -void ast_release_firmware(struct drm_device *dev); >> >> /* ast_cursor.c */ >> int ast_cursor_init(struct ast_private *ast); >> diff --git a/drivers/gpu/drm/ast/ast_main.c b/drivers/gpu/drm/ast/ast_main.c >> index 792fb7f616ec..e3b7748335a3 100644 >> --- a/drivers/gpu/drm/ast/ast_main.c >> +++ b/drivers/gpu/drm/ast/ast_main.c >> @@ -442,11 +442,8 @@ struct ast_private *ast_device_create(struct drm_driver >> *drv, >> >> void ast_device_destroy(struct ast_private *ast) >> { >> -struct drm_device *dev = &ast->base; >> - >> /* enable standard VGA decode */ >> ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0xa1, 0x04); >> >> -ast_release_firmware(dev); >> kfree(ast->dp501_fw_addr); >> } >> -- >> 2.27.0 >> > -- Thomas Zimmermann Graphics Driver Developer SUSE Software Solutions Germany GmbH Maxfeldstr. 5, 90409 Nürnberg, Germany (HRB 36809, AG Nürnberg) Geschäftsführer: Felix Imendörffer signature.asc Description: OpenPGP digital signature ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [Intel-gfx] [PATCH 0/6] vga-switcheroo: initial dynamic mux switch support
On Mon, Jul 27, 2020 at 03:51:06PM -0500, Daniel Dadap wrote: > Changes to allow vga-switcheroo to switch the mux while modesetting > clients remain active. There is existing support for switching the > mux without checking can_switch; however, this support also does not > reprobe after the mux switch is complete. This patch series adds a new > type of switch event which switches immediately while still calling > client driver callbacks, and updates the i915 DRM-KMS driver to reprobe > eDP outputs after switching the mux to an i915-driven GPU, and to avoid > using eDP links (which i915 always assumes to be connected) while the > mux is switched away. So before digging into the details I think the big issue we need to solve first is locking. And current vga-switcheroo is already broken in that regard (there's some fixme comments in drivers about it), but I never cared because it was full device switch only, initiated by users. But you now add vgaswitcheroo to modeset code, and runtime switching, I don't think we can ignore locking here anymore. Also, it's classic abba deadlock design: i915 modeset code calls your new functions in vgaswitcheroo, and vgaswitcheroo calls into modeset code to shut down stuff. This doesn't work (you get away with it by omitting locking in some places, like the current code). One totally nuts idea I've had is to protect vgaswitcheroo output state with a drm_modeset_lock. That supports full graph locking, which means it doesn't matter where we start: nouveau, i915, vgaswitcheroo. So could work out neatly. Problem: That still leaves the loop for the device switching, which is all tangled up here, so either we make this completely separate, or we figure out a plan how make this work for device switching too. And the additional problem is that drm_modeset_lock is already a highly entrenched lock, I'm not sure whether we can also support the device switching with that approach: The device locking we'd need would need to be an outermost lock, or at least fairly big, whereas drm_modeset_lock is kinda a level below. Or I'm making a mess here (it is already one after all). Also, where's the other side? I know the other side you care about is in the nvidia blob driver, but that doesn't count for upstream. We need that code in nouveau for review and merging. Cheers, Daniel > > Daniel Dadap (6): > vga-switcheroo: add new "immediate" switch event type > vga-switcheroo: Add a way to test for the active client > vga-switcheroo: notify clients of pending/completed switch events > i915: implement vga-switcheroo reprobe() callback > i915: fail atomic commit when muxed away > i915: bail out of eDP link training while mux-switched away > > drivers/gpu/drm/i915/display/intel_display.c | 7 + > .../drm/i915/display/intel_dp_link_training.c | 9 ++ > drivers/gpu/drm/i915/i915_switcheroo.c| 27 +++- > drivers/gpu/vga/vga_switcheroo.c | 153 ++ > include/linux/vga_switcheroo.h| 20 +++ > 5 files changed, 185 insertions(+), 31 deletions(-) > > -- > 2.18.4 > > ___ > Intel-gfx mailing list > intel-...@lists.freedesktop.org > https://lists.freedesktop.org/mailman/listinfo/intel-gfx -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH 04/13] drm/ast: Managed release of I2C adapter
Hi Am 28.07.20 um 11:23 schrieb dan...@ffwll.ch: > On Tue, Jul 28, 2020 at 09:44:16AM +0200, Thomas Zimmermann wrote: >> Managed releases of the device's I2C adapter simplify the connector's >> release. >> >> Signed-off-by: Thomas Zimmermann > > I think this breaks bisect, since at this point the release callback is > called when the connector is already gone. At the end of the series it's > fine again though. > > I've done a very cursory reading of your series to look for high-level > issues, I think overall reasonable. On the series: > > Acked-by: Daniel Vetter > > But maybe you want to polish a bit more, up to you. Thanks. I'll address your points and wait a bit longer. Usually Sam has a number of good comments as well. Best regards Thomas > -Daniel > >> --- >> drivers/gpu/drm/ast/ast_mode.c | 21 ++--- >> 1 file changed, 10 insertions(+), 11 deletions(-) >> >> diff --git a/drivers/gpu/drm/ast/ast_mode.c b/drivers/gpu/drm/ast/ast_mode.c >> index f421a60d8a96..27eb49bd12b3 100644 >> --- a/drivers/gpu/drm/ast/ast_mode.c >> +++ b/drivers/gpu/drm/ast/ast_mode.c >> @@ -39,6 +39,7 @@ >> #include >> #include >> #include >> +#include >> #include >> #include >> #include >> @@ -591,6 +592,14 @@ static void ast_i2c_setsda(void *i2c_priv, int data) >> } >> } >> >> +static void ast_i2c_release(struct drm_device *dev, void *data) >> +{ >> +struct ast_i2c_chan *i2c = data; >> + >> +i2c_del_adapter(&i2c->adapter); >> +i2c->dev = NULL; /* clear to signal absence of I2C support */ >> +} >> + >> static int ast_i2c_init(struct ast_i2c_chan *i2c, struct drm_device *dev) >> { >> int ret; >> @@ -618,7 +627,7 @@ static int ast_i2c_init(struct ast_i2c_chan *i2c, struct >> drm_device *dev) >> >> i2c->dev = dev; /* signals presence of I2C support */ >> >> -return 0; >> +return drmm_add_action_or_reset(dev, ast_i2c_release, i2c); >> } >> >> static bool ast_i2c_is_initialized(struct ast_i2c_chan *i2c) >> @@ -626,14 +635,6 @@ static bool ast_i2c_is_initialized(struct ast_i2c_chan >> *i2c) >> return !!i2c->dev; >> } >> >> -static void ast_i2c_fini(struct ast_i2c_chan *i2c) >> -{ >> -if (!ast_i2c_is_initialized(i2c)) >> -return; >> -i2c_del_adapter(&i2c->adapter); >> -i2c->dev = NULL; /* clear to signal absence of I2C support */ >> -} >> - >> /* >> * Primary plane >> */ >> @@ -1139,8 +1140,6 @@ static enum drm_mode_status ast_mode_valid(struct >> drm_connector *connector, >> >> static void ast_connector_destroy(struct drm_connector *connector) >> { >> -struct ast_connector *ast_connector = to_ast_connector(connector); >> -ast_i2c_fini(&ast_connector->i2c); >> drm_connector_cleanup(connector); >> kfree(connector); >> } >> -- >> 2.27.0 >> > -- Thomas Zimmermann Graphics Driver Developer SUSE Software Solutions Germany GmbH Maxfeldstr. 5, 90409 Nürnberg, Germany (HRB 36809, AG Nürnberg) Geschäftsführer: Felix Imendörffer signature.asc Description: OpenPGP digital signature ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH 11/13] drm/ast: Managed release of ast firmware
On Tue, Jul 28, 2020 at 11:32:04AM +0200, Thomas Zimmermann wrote: > Hi > > Am 28.07.20 um 11:17 schrieb dan...@ffwll.ch: > > On Tue, Jul 28, 2020 at 09:44:23AM +0200, Thomas Zimmermann wrote: > >> The ast driver loads firmware for the DP501 display encoder. The > >> patch replaces the removal code with a managed release function. > >> > >> Signed-off-by: Thomas Zimmermann > > > > Hm a devm_request_firmware which does exactly this would be nice I think. > > Maybe as a follow-up refactor? > > There are so many ideas for follow-up patches wrt. devres and drmres, we > should add a todo item to collect them. Especially, devres is much more > over head in terms of reviews and kernel building/testing tha tit makes > sense to collect ideas and address them in larger chunks. Yeah maybe a section with wanted devres functions in todo.rst makes sense. For devres it depends which subsystem you're dealing with I guess, and how much they want to see before it lands. -Daniel > > Best regards > Thomas > > > -Daniel > > > >> --- > >> drivers/gpu/drm/ast/ast_dp501.c | 23 ++- > >> drivers/gpu/drm/ast/ast_drv.h | 1 - > >> drivers/gpu/drm/ast/ast_main.c | 3 --- > >> 3 files changed, 14 insertions(+), 13 deletions(-) > >> > >> diff --git a/drivers/gpu/drm/ast/ast_dp501.c > >> b/drivers/gpu/drm/ast/ast_dp501.c > >> index 4b85a504825a..88121c0e0d05 100644 > >> --- a/drivers/gpu/drm/ast/ast_dp501.c > >> +++ b/drivers/gpu/drm/ast/ast_dp501.c > >> @@ -8,11 +8,24 @@ > >> > >> MODULE_FIRMWARE("ast_dp501_fw.bin"); > >> > >> +static void ast_release_firmware(void *data) > >> +{ > >> + struct ast_private *ast = data; > >> + > >> + release_firmware(ast->dp501_fw); > >> + ast->dp501_fw = NULL; > >> +} > >> + > >> static int ast_load_dp501_microcode(struct drm_device *dev) > >> { > >>struct ast_private *ast = to_ast_private(dev); > >> + int ret; > >> + > >> + ret = request_firmware(&ast->dp501_fw, "ast_dp501_fw.bin", dev->dev); > >> + if (ret) > >> + return ret; > >> > >> - return request_firmware(&ast->dp501_fw, "ast_dp501_fw.bin", dev->dev); > >> + return devm_add_action_or_reset(dev->dev, ast_release_firmware, ast); > >> } > >> > >> static void send_ack(struct ast_private *ast) > >> @@ -435,11 +448,3 @@ void ast_init_3rdtx(struct drm_device *dev) > >>} > >>} > >> } > >> - > >> -void ast_release_firmware(struct drm_device *dev) > >> -{ > >> - struct ast_private *ast = to_ast_private(dev); > >> - > >> - release_firmware(ast->dp501_fw); > >> - ast->dp501_fw = NULL; > >> -} > >> diff --git a/drivers/gpu/drm/ast/ast_drv.h b/drivers/gpu/drm/ast/ast_drv.h > >> index 86c9a7ac712b..02908d005b99 100644 > >> --- a/drivers/gpu/drm/ast/ast_drv.h > >> +++ b/drivers/gpu/drm/ast/ast_drv.h > >> @@ -312,7 +312,6 @@ bool ast_backup_fw(struct drm_device *dev, u8 *addr, > >> u32 size); > >> bool ast_dp501_read_edid(struct drm_device *dev, u8 *ediddata); > >> u8 ast_get_dp501_max_clk(struct drm_device *dev); > >> void ast_init_3rdtx(struct drm_device *dev); > >> -void ast_release_firmware(struct drm_device *dev); > >> > >> /* ast_cursor.c */ > >> int ast_cursor_init(struct ast_private *ast); > >> diff --git a/drivers/gpu/drm/ast/ast_main.c > >> b/drivers/gpu/drm/ast/ast_main.c > >> index 792fb7f616ec..e3b7748335a3 100644 > >> --- a/drivers/gpu/drm/ast/ast_main.c > >> +++ b/drivers/gpu/drm/ast/ast_main.c > >> @@ -442,11 +442,8 @@ struct ast_private *ast_device_create(struct > >> drm_driver *drv, > >> > >> void ast_device_destroy(struct ast_private *ast) > >> { > >> - struct drm_device *dev = &ast->base; > >> - > >>/* enable standard VGA decode */ > >>ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0xa1, 0x04); > >> > >> - ast_release_firmware(dev); > >>kfree(ast->dp501_fw_addr); > >> } > >> -- > >> 2.27.0 > >> > > > > -- > Thomas Zimmermann > Graphics Driver Developer > SUSE Software Solutions Germany GmbH > Maxfeldstr. 5, 90409 Nürnberg, Germany > (HRB 36809, AG Nürnberg) > Geschäftsführer: Felix Imendörffer > -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 10/78] drm/vc4: crtc: Rename HVS channel to output
Hi Maxime On Wed, 8 Jul 2020 at 18:42, Maxime Ripard wrote: > > In vc5, the HVS has 6 outputs and 3 FIFOs (or channels), with > pixelvalves each being assigned to a given output, but each output can > then be muxed to feed from multiple FIFOs. > > Since vc4 had that entirely static, both were probably equivalent, but > since that changes, let's rename hvs_channel to hvs_output in the > vc4_crtc_data, since a pixelvalve is really connected to an output, and > not to a FIFO. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_crtc.c | 8 > drivers/gpu/drm/vc4/vc4_drv.h | 4 ++-- > drivers/gpu/drm/vc4/vc4_hvs.c | 2 +- > drivers/gpu/drm/vc4/vc4_txp.c | 2 +- > 4 files changed, 8 insertions(+), 8 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_crtc.c b/drivers/gpu/drm/vc4/vc4_crtc.c > index fdecaba77836..d3126fe04d9a 100644 > --- a/drivers/gpu/drm/vc4/vc4_crtc.c > +++ b/drivers/gpu/drm/vc4/vc4_crtc.c > @@ -775,7 +775,7 @@ static const struct drm_crtc_helper_funcs > vc4_crtc_helper_funcs = { > > static const struct vc4_pv_data bcm2835_pv0_data = { > .base = { > - .hvs_channel = 0, > + .hvs_output = 0, > }, > .debugfs_name = "crtc0_regs", > .pixels_per_clock = 1, > @@ -787,7 +787,7 @@ static const struct vc4_pv_data bcm2835_pv0_data = { > > static const struct vc4_pv_data bcm2835_pv1_data = { > .base = { > - .hvs_channel = 2, > + .hvs_output = 2, > }, > .debugfs_name = "crtc1_regs", > .pixels_per_clock = 1, > @@ -799,7 +799,7 @@ static const struct vc4_pv_data bcm2835_pv1_data = { > > static const struct vc4_pv_data bcm2835_pv2_data = { > .base = { > - .hvs_channel = 1, > + .hvs_output = 1, > }, > .debugfs_name = "crtc2_regs", > .pixels_per_clock = 1, > @@ -862,7 +862,7 @@ int vc4_crtc_init(struct drm_device *drm, struct vc4_crtc > *vc4_crtc, > drm_crtc_init_with_planes(drm, crtc, primary_plane, NULL, > crtc_funcs, NULL); > drm_crtc_helper_add(crtc, crtc_helper_funcs); > - vc4_crtc->channel = vc4_crtc->data->hvs_channel; > + vc4_crtc->channel = vc4_crtc->data->hvs_output; > drm_mode_crtc_set_gamma_size(crtc, ARRAY_SIZE(vc4_crtc->lut_r)); > drm_crtc_enable_color_mgmt(crtc, 0, false, crtc->gamma_size); > > diff --git a/drivers/gpu/drm/vc4/vc4_drv.h b/drivers/gpu/drm/vc4/vc4_drv.h > index d80fc3bbb450..d1cf4c038180 100644 > --- a/drivers/gpu/drm/vc4/vc4_drv.h > +++ b/drivers/gpu/drm/vc4/vc4_drv.h > @@ -447,8 +447,8 @@ to_vc4_encoder(struct drm_encoder *encoder) > } > > struct vc4_crtc_data { > - /* Which channel of the HVS this pixelvalve sources from. */ > - int hvs_channel; > + /* Which output of the HVS this pixelvalve sources from. */ > + int hvs_output; > }; > > struct vc4_pv_data { > diff --git a/drivers/gpu/drm/vc4/vc4_hvs.c b/drivers/gpu/drm/vc4/vc4_hvs.c > index 091fdf4908aa..6fd9de1dc65a 100644 > --- a/drivers/gpu/drm/vc4/vc4_hvs.c > +++ b/drivers/gpu/drm/vc4/vc4_hvs.c > @@ -419,7 +419,7 @@ void vc4_hvs_mode_set_nofb(struct drm_crtc *crtc) > struct drm_display_mode *mode = &crtc->state->adjusted_mode; > bool interlace = mode->flags & DRM_MODE_FLAG_INTERLACE; > > - if (vc4_crtc->data->hvs_channel == 2) { > + if (vc4_crtc->data->hvs_output == 2) { > u32 dispctrl; > u32 dsp3_mux; > > diff --git a/drivers/gpu/drm/vc4/vc4_txp.c b/drivers/gpu/drm/vc4/vc4_txp.c > index a7c3af0005a0..f39d9900d027 100644 > --- a/drivers/gpu/drm/vc4/vc4_txp.c > +++ b/drivers/gpu/drm/vc4/vc4_txp.c > @@ -452,7 +452,7 @@ static irqreturn_t vc4_txp_interrupt(int irq, void *data) > } > > static const struct vc4_crtc_data vc4_txp_crtc_data = { > - .hvs_channel = 2, > + .hvs_output = 2, > }; > > static int vc4_txp_bind(struct device *dev, struct device *master, void > *data) > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: linux-next: Fixes tag needs some work in the drm-fixes tree
On Mon, Jul 27, 2020 at 3:38 PM Stephen Rothwell wrote: > > Hi all, > > In commit > > 163d5446c37a ("drm/nouveau/disp/gm200-: fix regression from HDA SOR > selection changes") > > Fixes tag > > Fixes: 9b5ca547bb8 ("drm/nouveau/disp/gm200-: detect and potentially > disable HDA support on some SORs") > > has these problem(s): > > - SHA1 should be at least 12 digits long > Can be fixed by setting core.abbrev to 12 (or more) or (for git v2.11 > or later) just making sure it is not set (or set to "auto"). Hm dim (our scripting) should be checking for this already, I've added that after the last big round of malformed Fixes lines we've had ... Dave, overuse of dim -f in your history? -Daniel -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 11/78] drm/vc4: crtc: Use local chan variable
Hi Maxime On Wed, 8 Jul 2020 at 18:42, Maxime Ripard wrote: > > The vc4_crtc_handle_page_flip already has a local variable holding the > value of vc4_crtc->channel, so let's use it instead. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_crtc.c | 2 +- > 1 file changed, 1 insertion(+), 1 deletion(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_crtc.c b/drivers/gpu/drm/vc4/vc4_crtc.c > index d3126fe04d9a..cdeaa0cd981f 100644 > --- a/drivers/gpu/drm/vc4/vc4_crtc.c > +++ b/drivers/gpu/drm/vc4/vc4_crtc.c > @@ -533,7 +533,7 @@ static void vc4_crtc_handle_page_flip(struct vc4_crtc > *vc4_crtc) > * the CRTC and encoder already reconfigured, leading to > * underruns. This can be seen when reconfiguring the CRTC. > */ > - vc4_hvs_unmask_underrun(dev, vc4_crtc->channel); > + vc4_hvs_unmask_underrun(dev, chan); > } > spin_unlock_irqrestore(&dev->event_lock, flags); > } > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 12/78] drm/vc4: crtc: Enable and disable the PV in atomic_enable / disable
Hi Maxime On Wed, 8 Jul 2020 at 18:42, Maxime Ripard wrote: > > The VIDEN bit in the pixelvalve currently being used to enable or disable > the pixelvalve seems to not be enough in some situations, which whill end > up with the pixelvalve stalling. > > In such a case, even re-enabling VIDEN doesn't bring it back and we need to > clear the FIFO. This can only be done if the pixelvalve is disabled though. > > In order to overcome this, we can configure the pixelvalve during > mode_set_no_fb, but only enable it in atomic_enable and flush the FIFO > there, and in atomic_disable disable the pixelvalve again. Very minor nitpick: the configure is in vc4_crtc_config_pv, but that is called from mode_set_no_fb. The comment is correct from a DRM overview perspective, but not from the actual code. Describing the DRM call is probably the better approach, but it looks odd when compared to the code. > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_crtc.c | 10 +++--- > 1 file changed, 7 insertions(+), 3 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_crtc.c b/drivers/gpu/drm/vc4/vc4_crtc.c > index cdeaa0cd981f..fe2e5675aed4 100644 > --- a/drivers/gpu/drm/vc4/vc4_crtc.c > +++ b/drivers/gpu/drm/vc4/vc4_crtc.c > @@ -332,9 +332,7 @@ static void vc4_crtc_config_pv(struct drm_crtc *crtc) >PV_CONTROL_TRIGGER_UNDERFLOW | >PV_CONTROL_WAIT_HSTART | >VC4_SET_FIELD(vc4_encoder->clock_select, > -PV_CONTROL_CLK_SELECT) | > - PV_CONTROL_FIFO_CLR | > - PV_CONTROL_EN); > +PV_CONTROL_CLK_SELECT)); > } > > static void vc4_crtc_mode_set_nofb(struct drm_crtc *crtc) > @@ -386,6 +384,8 @@ static void vc4_crtc_atomic_disable(struct drm_crtc *crtc, > ret = wait_for(!(CRTC_READ(PV_V_CONTROL) & PV_VCONTROL_VIDEN), 1); > WARN_ONCE(ret, "Timeout waiting for !PV_VCONTROL_VIDEN\n"); > > + CRTC_WRITE(PV_CONTROL, CRTC_READ(PV_CONTROL) & ~PV_CONTROL_EN); > + > vc4_hvs_atomic_disable(crtc, old_state); > > /* > @@ -410,6 +410,10 @@ static void vc4_crtc_atomic_enable(struct drm_crtc *crtc, > > require_hvs_enabled(dev); > > + /* Reset the PV fifo. */ > + CRTC_WRITE(PV_CONTROL, CRTC_READ(PV_CONTROL) | > + PV_CONTROL_FIFO_CLR | PV_CONTROL_EN); > + > /* Enable vblank irq handling before crtc is started otherwise > * drm_crtc_get_vblank() fails in vc4_crtc_update_dlist(). > */ > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH RFC v6 0/6] Add Unisoc's drm kms module
On Tue, Jul 28, 2020 at 12:08 PM Kevin Tang wrote: > > From: Kevin Tang Hm still no ack for dt bindings? We need that for merging. Also what's the maintainer plan here? Imo best would be to put this into the drm-misc group maintainer model, with commit rights and all: https://drm.pages.freedesktop.org/maintainer-tools/drm-misc.html MAINTAINERS patch to do that would be good. -Daniel > > ChangeList: > v1: > 1. only upstream modeset and atomic at first commit. > 2. remove some unused code; > 3. use alpha and blend_mode properties; > 3. add yaml support; > 4. remove auto-adaptive panel driver; > 5. bugfix > > v2: > 1. add sprd crtc and plane module for KMS, preparing for multi crtc&encoder > 2. remove gem drivers, use generic CMA handlers > 3. remove redundant "module_init", all the sub modules loading by KMS > > v3: > 1. multi crtc&encoder design have problem, so rollback to v1 > > v4: > 1. update to gcc-linaro-7.5.0 > 2. update to Linux 5.6-rc3 > 3. remove pm_runtime support > 4. add COMPILE_TEST, remove unused kconfig > 5. "drm_dev_put" on drm_unbind > 6. fix some naming convention issue > 7. remove semaphore lock for crtc flip > 8. remove static variables > > v5: > 1. optimize encoder and connector code implementation > 2. use "platform_get_irq" and "platform_get_resource" > 3. drop useless function return type, drop unless debug log > 4. custom properties should be separate, so drop it > 5. use DRM_XXX replase pr_xxx > 6. drop dsi&dphy hal callback ops > 7. drop unless callback ops checking > 8. add comments for sprd dpu structure > > v6: > 1. Access registers via readl/writel > 2. Checking for unsupported KMS properties (format, rotation, blend_mode, > etc) on plane_check ops > 3. Remove always true checks for dpu core ops > > Kevin Tang (6): > dt-bindings: display: add Unisoc's drm master bindings > drm/sprd: add Unisoc's drm kms master > dt-bindings: display: add Unisoc's dpu bindings > drm/sprd: add Unisoc's drm display controller driver > dt-bindings: display: add Unisoc's mipi dsi&dphy bindings > drm/sprd: add Unisoc's drm mipi dsi&dphy driver > > .../devicetree/bindings/display/sprd/dphy.yaml | 75 + > .../devicetree/bindings/display/sprd/dpu.yaml | 82 ++ > .../devicetree/bindings/display/sprd/drm.yaml | 36 + > .../devicetree/bindings/display/sprd/dsi.yaml | 98 ++ > drivers/gpu/drm/Kconfig|2 + > drivers/gpu/drm/Makefile |1 + > drivers/gpu/drm/sprd/Kconfig | 12 + > drivers/gpu/drm/sprd/Makefile | 13 + > drivers/gpu/drm/sprd/disp_lib.c| 57 + > drivers/gpu/drm/sprd/disp_lib.h| 16 + > drivers/gpu/drm/sprd/dphy/Makefile |7 + > drivers/gpu/drm/sprd/dphy/pll/Makefile |3 + > drivers/gpu/drm/sprd/dphy/pll/megacores_sharkle.c | 473 +++ > drivers/gpu/drm/sprd/dphy/sprd_dphy_api.c | 201 +++ > drivers/gpu/drm/sprd/dphy/sprd_dphy_api.h | 22 + > drivers/gpu/drm/sprd/dpu/Makefile |3 + > drivers/gpu/drm/sprd/dpu/dpu_r2p0.c| 503 +++ > drivers/gpu/drm/sprd/dsi/Makefile |8 + > drivers/gpu/drm/sprd/dsi/core/Makefile |4 + > drivers/gpu/drm/sprd/dsi/core/dsi_ctrl_r1p0.c | 964 + > drivers/gpu/drm/sprd/dsi/core/dsi_ctrl_r1p0.h | 1477 > > drivers/gpu/drm/sprd/dsi/core/dsi_ctrl_r1p0_ppi.c | 328 + > drivers/gpu/drm/sprd/dsi/core/dsi_ctrl_r1p0_ppi.h | 32 + > drivers/gpu/drm/sprd/dsi/sprd_dsi_api.c| 590 > drivers/gpu/drm/sprd/dsi/sprd_dsi_api.h| 26 + > drivers/gpu/drm/sprd/sprd_dphy.c | 209 +++ > drivers/gpu/drm/sprd/sprd_dphy.h | 50 + > drivers/gpu/drm/sprd/sprd_dpu.c| 668 + > drivers/gpu/drm/sprd/sprd_dpu.h| 190 +++ > drivers/gpu/drm/sprd/sprd_drm.c| 227 +++ > drivers/gpu/drm/sprd/sprd_drm.h| 18 + > drivers/gpu/drm/sprd/sprd_dsi.c| 571 > drivers/gpu/drm/sprd/sprd_dsi.h| 108 ++ > 33 files changed, 7074 insertions(+) > create mode 100644 Documentation/devicetree/bindings/display/sprd/dphy.yaml > create mode 100644 Documentation/devicetree/bindings/display/sprd/dpu.yaml > create mode 100644 Documentation/devicetree/bindings/display/sprd/drm.yaml > create mode 100644 Documentation/devicetree/bindings/display/sprd/dsi.yaml > create mode 100644 drivers/gpu/drm/sprd/Kconfig > create mode 100644 drivers/gpu/drm/sprd/Makefile > create mode 100644 drivers/gpu/drm/sprd/disp_lib.c > create mode 100644 drivers/gpu/drm/sprd/disp_lib.h > create mode 100644 drivers/gpu/drm/sprd/dphy/Makefile > create mode 100644 drivers/gpu/drm/sprd/dphy/pll/Makefile > create mode 100644 drivers/gpu/drm/sprd/dp
Re: [v7, PATCH 2/7] mtk-mmsys: add mmsys private data
Hi Yongqiang, Missatge de Yongqiang Niu del dia ds., 25 de jul. 2020 a les 5:29: > > On Thu, 2020-07-23 at 11:32 +0200, Enric Balletbo Serra wrote: > > Hi Yongqiang Niu, > > > > Thank you for your patch. > > > > Missatge de Yongqiang Niu del dia dj., 23 > > de jul. 2020 a les 4:05: > > > > > > add mmsys private data > > > > > > > I think this change requires a better explanation of what you are > > doing. Although I'm really uncomfortable with this change, why you > > need to create a new mt2701-mmsys file? > > reason: > 1.there will more and more Mediatek Soc upstream, and the display path > connection function mtk_mmsys_ddp_mout_en, mtk_mmsys_ddp_sel_in and > mtk_mmsys_ddp_sout_sel will complicated more and more, > 2. many of the connection are only used in some SoC, and useless for > other SoC and not readable, > 3. if we add a new SoC connection, we need check is this affect other > Soc, > > > > > Feature: drm/mediatek > > > > Remove this. > next version will remove this > > > > > Signed-off-by: Yongqiang Niu > > > --- > > > drivers/soc/mediatek/Makefile | 1 + > > > drivers/soc/mediatek/mmsys/Makefile | 2 + > > > drivers/soc/mediatek/mmsys/mt2701-mmsys.c | 250 > > > +++ > > > drivers/soc/mediatek/mtk-mmsys.c | 271 > > > +- > > > include/linux/soc/mediatek/mtk-mmsys.h| 15 ++ > > > 5 files changed, 314 insertions(+), 225 deletions(-) > > > create mode 100644 drivers/soc/mediatek/mmsys/Makefile > > > create mode 100644 drivers/soc/mediatek/mmsys/mt2701-mmsys.c > > > > > > diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile > > > index 2afa7b9..b37ac2c 100644 > > > --- a/drivers/soc/mediatek/Makefile > > > +++ b/drivers/soc/mediatek/Makefile > > > @@ -3,3 +3,4 @@ obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o > > > obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o > > > obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o > > > obj-$(CONFIG_MTK_MMSYS) += mtk-mmsys.o > > > +obj-$(CONFIG_MTK_MMSYS) += mmsys/ > > > diff --git a/drivers/soc/mediatek/mmsys/Makefile > > > b/drivers/soc/mediatek/mmsys/Makefile > > > new file mode 100644 > > > index 000..33b0dab > > > --- /dev/null > > > +++ b/drivers/soc/mediatek/mmsys/Makefile > > > @@ -0,0 +1,2 @@ > > > +# SPDX-License-Identifier: GPL-2.0-only > > > +obj-y += mt2701-mmsys.o > > > diff --git a/drivers/soc/mediatek/mmsys/mt2701-mmsys.c > > > b/drivers/soc/mediatek/mmsys/mt2701-mmsys.c > > > new file mode 100644 > > > index 000..b8e53b0 > > > --- /dev/null > > > +++ b/drivers/soc/mediatek/mmsys/mt2701-mmsys.c > > > @@ -0,0 +1,250 @@ > > > +// SPDX-License-Identifier: GPL-2.0 > > > +// > > > +// Copyright (c) 2020 MediaTek Inc. > > > + > > > +#include > > > +#include > > > +#include > > > +#include > > > +#include > > > + > > > +#define DISP_REG_CONFIG_DISP_OVL0_MOUT_EN 0x040 > > > +#define DISP_REG_CONFIG_DISP_OVL1_MOUT_EN 0x044 > > > +#define DISP_REG_CONFIG_DISP_OD_MOUT_EN0x048 > > > +#define DISP_REG_CONFIG_DISP_GAMMA_MOUT_EN 0x04c > > > +#define DISP_REG_CONFIG_DISP_UFOE_MOUT_EN 0x050 > > > +#define DISP_REG_CONFIG_DISP_COLOR0_SEL_IN 0x084 > > > +#define DISP_REG_CONFIG_DISP_COLOR1_SEL_IN 0x088 > > > +#define DISP_REG_CONFIG_DSIE_SEL_IN0x0a4 > > > +#define DISP_REG_CONFIG_DSIO_SEL_IN0x0a8 > > > +#define DISP_REG_CONFIG_DPI_SEL_IN 0x0ac > > > +#define DISP_REG_CONFIG_DISP_RDMA2_SOUT0x0b8 > > > +#define DISP_REG_CONFIG_DISP_RDMA0_SOUT_EN 0x0c4 > > > +#define DISP_REG_CONFIG_DISP_RDMA1_SOUT_EN 0x0c8 > > > +#define DISP_REG_CONFIG_MMSYS_CG_CON0 0x100 > > > + > > > +#define DISP_REG_CONFIG_DISP_OVL_MOUT_EN 0x030 > > > +#define DISP_REG_CONFIG_OUT_SEL0x04c > > > +#define DISP_REG_CONFIG_DSI_SEL0x050 > > > +#define DISP_REG_CONFIG_DPI_SEL0x064 > > > + > > > +#define OVL0_MOUT_EN_COLOR00x1 > > > +#define OD_MOUT_EN_RDMA0 0x1 > > > +#define OD1_MOUT_EN_RDMA1 BIT(16) > > > +#define UFOE_MOUT_EN_DSI0 0x1 > > > +#define COLOR0_SEL_IN_OVL0 0x1 > > > +#define OVL1_MOUT_EN_COLOR10x1 > > > +#define GAMMA_MOUT_EN_RDMA10x1 > > > +#define RDMA0_SOUT_DPI00x2 > > > +#define RDMA0_SOUT_DPI10x3 > > > +#define RDMA0_SOUT_DSI10x1 > > > +#define RDMA0_SOUT_DSI20x4 > > > +#define RDMA0_SOUT_DSI30x5 > > > +#define RDMA1_SOUT_DPI00x2 > > > +#define RDMA1_SOUT_DPI10x3 > > > +#define RDMA1_SOUT_DSI10x1 > > > +#define RDMA1_SOUT_DSI20x4 > > > +#define RDMA1_S
Re: [PATCH v4 21/78] drm/vc4: crtc: Move PV dump to config_pv
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > Now that we only configure the PixelValve in vc4_crtc_config_pv, it doesn't > really make much sense to dump its register content in its caller. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_crtc.c | 26 -- > 1 file changed, 12 insertions(+), 14 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_crtc.c b/drivers/gpu/drm/vc4/vc4_crtc.c > index c2ab907611e3..181d3fd57bc7 100644 > --- a/drivers/gpu/drm/vc4/vc4_crtc.c > +++ b/drivers/gpu/drm/vc4/vc4_crtc.c > @@ -290,6 +290,14 @@ static void vc4_crtc_config_pv(struct drm_crtc *crtc) >vc4_encoder->type == VC4_ENCODER_TYPE_DSI1); > u32 format = is_dsi ? PV_CONTROL_FORMAT_DSIV_24 : > PV_CONTROL_FORMAT_24; > u8 ppc = pv_data->pixels_per_clock; > + bool debug_dump_regs = false; > + > + if (debug_dump_regs) { > + struct drm_printer p = drm_info_printer(&vc4_crtc->pdev->dev); > + dev_info(&vc4_crtc->pdev->dev, "CRTC %d regs before:\n", > +drm_crtc_index(crtc)); > + drm_print_regset32(&p, &vc4_crtc->regset); > + } > > vc4_crtc_pixelvalve_reset(crtc); > > @@ -359,30 +367,20 @@ static void vc4_crtc_config_pv(struct drm_crtc *crtc) >PV_CONTROL_WAIT_HSTART | >VC4_SET_FIELD(vc4_encoder->clock_select, > PV_CONTROL_CLK_SELECT)); > -} > - > -static void vc4_crtc_mode_set_nofb(struct drm_crtc *crtc) > -{ > - struct vc4_crtc *vc4_crtc = to_vc4_crtc(crtc); > - bool debug_dump_regs = false; > > if (debug_dump_regs) { > struct drm_printer p = drm_info_printer(&vc4_crtc->pdev->dev); > - dev_info(&vc4_crtc->pdev->dev, "CRTC %d regs before:\n", > + dev_info(&vc4_crtc->pdev->dev, "CRTC %d regs after:\n", > drm_crtc_index(crtc)); > drm_print_regset32(&p, &vc4_crtc->regset); > } > +} > > +static void vc4_crtc_mode_set_nofb(struct drm_crtc *crtc) > +{ > vc4_crtc_config_pv(crtc); > > vc4_hvs_mode_set_nofb(crtc); > - > - if (debug_dump_regs) { > - struct drm_printer p = drm_info_printer(&vc4_crtc->pdev->dev); > - dev_info(&vc4_crtc->pdev->dev, "CRTC %d regs after:\n", > -drm_crtc_index(crtc)); > - drm_print_regset32(&p, &vc4_crtc->regset); > - } > } > > static void require_hvs_enabled(struct drm_device *dev) > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 22/78] drm/vc4: crtc: Move HVS init and close to a function
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > In order to make further refactoring easier, let's move the HVS channel > setup / teardown to their own function. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hvs.c | 104 +++ > 1 file changed, 58 insertions(+), 46 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hvs.c b/drivers/gpu/drm/vc4/vc4_hvs.c > index 50f9a9674a7e..78bb1c0b0b76 100644 > --- a/drivers/gpu/drm/vc4/vc4_hvs.c > +++ b/drivers/gpu/drm/vc4/vc4_hvs.c > @@ -196,6 +196,62 @@ static void vc4_hvs_update_gamma_lut(struct drm_crtc > *crtc) > vc4_hvs_lut_load(crtc); > } > > +static int vc4_hvs_init_channel(struct vc4_dev *vc4, struct drm_crtc *crtc, > + struct drm_display_mode *mode, bool oneshot) > +{ > + struct vc4_crtc_state *vc4_crtc_state = > to_vc4_crtc_state(crtc->state); > + unsigned int chan = vc4_crtc_state->assigned_channel; > + u32 dispctrl; > + > + /* Turn on the scaler, which will wait for vstart to start > +* compositing. > +* When feeding the transposer, we should operate in oneshot > +* mode. > +*/ > + dispctrl = SCALER_DISPCTRLX_ENABLE; > + > + if (!vc4->hvs->hvs5) > + dispctrl |= VC4_SET_FIELD(mode->hdisplay, > + SCALER_DISPCTRLX_WIDTH) | > + VC4_SET_FIELD(mode->vdisplay, > + SCALER_DISPCTRLX_HEIGHT) | > + (oneshot ? SCALER_DISPCTRLX_ONESHOT : 0); > + else > + dispctrl |= VC4_SET_FIELD(mode->hdisplay, > + SCALER5_DISPCTRLX_WIDTH) | > + VC4_SET_FIELD(mode->vdisplay, > + SCALER5_DISPCTRLX_HEIGHT) | > + (oneshot ? SCALER5_DISPCTRLX_ONESHOT : 0); > + > + HVS_WRITE(SCALER_DISPCTRLX(chan), dispctrl); > + > + return 0; > +} > + > +static void vc4_hvs_stop_channel(struct drm_device *dev, unsigned int chan) > +{ > + struct vc4_dev *vc4 = to_vc4_dev(dev); > + > + if (HVS_READ(SCALER_DISPCTRLX(chan)) & SCALER_DISPCTRLX_ENABLE) > + return; > + > + HVS_WRITE(SCALER_DISPCTRLX(chan), > + HVS_READ(SCALER_DISPCTRLX(chan)) | SCALER_DISPCTRLX_RESET); > + HVS_WRITE(SCALER_DISPCTRLX(chan), > + HVS_READ(SCALER_DISPCTRLX(chan)) & > ~SCALER_DISPCTRLX_ENABLE); > + > + /* Once we leave, the scaler should be disabled and its fifo empty. */ > + WARN_ON_ONCE(HVS_READ(SCALER_DISPCTRLX(chan)) & > SCALER_DISPCTRLX_RESET); > + > + WARN_ON_ONCE(VC4_GET_FIELD(HVS_READ(SCALER_DISPSTATX(chan)), > + SCALER_DISPSTATX_MODE) != > +SCALER_DISPSTATX_MODE_DISABLED); > + > + WARN_ON_ONCE((HVS_READ(SCALER_DISPSTATX(chan)) & > + (SCALER_DISPSTATX_FULL | SCALER_DISPSTATX_EMPTY)) != > +SCALER_DISPSTATX_EMPTY); > +} > + > int vc4_hvs_atomic_check(struct drm_crtc *crtc, > struct drm_crtc_state *state) > { > @@ -268,63 +324,19 @@ void vc4_hvs_atomic_enable(struct drm_crtc *crtc, > struct vc4_crtc_state *vc4_state = to_vc4_crtc_state(crtc->state); > struct drm_display_mode *mode = &crtc->state->adjusted_mode; > bool oneshot = vc4_state->feed_txp; > - u32 dispctrl; > > vc4_hvs_update_dlist(crtc); > - > - /* Turn on the scaler, which will wait for vstart to start > -* compositing. > -* When feeding the transposer, we should operate in oneshot > -* mode. > -*/ > - dispctrl = SCALER_DISPCTRLX_ENABLE; > - > - if (!vc4->hvs->hvs5) > - dispctrl |= VC4_SET_FIELD(mode->hdisplay, > - SCALER_DISPCTRLX_WIDTH) | > - VC4_SET_FIELD(mode->vdisplay, > - SCALER_DISPCTRLX_HEIGHT) | > - (oneshot ? SCALER_DISPCTRLX_ONESHOT : 0); > - else > - dispctrl |= VC4_SET_FIELD(mode->hdisplay, > - SCALER5_DISPCTRLX_WIDTH) | > - VC4_SET_FIELD(mode->vdisplay, > - SCALER5_DISPCTRLX_HEIGHT) | > - (oneshot ? SCALER5_DISPCTRLX_ONESHOT : 0); > - > - HVS_WRITE(SCALER_DISPCTRLX(vc4_state->assigned_channel), dispctrl); > + vc4_hvs_init_channel(vc4, crtc, mode, oneshot); > } > > void vc4_hvs_atomic_disable(struct drm_crtc *crtc, > struct drm_crtc_state *old_state) > { > struct drm_device *dev = crtc->dev; > - struct vc4_dev *vc4 = to_vc4_dev(dev); > struct vc4_crtc_state *vc4_state = to_vc4_crtc_state(old
Re: [PATCH v4 24/78] drm/vc4: hvs: Make sure our channel is reset
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > In order to clear our intermediate FIFOs that might end up with a stale > pixel, let's make sure our FIFO channel is reset everytime our channel is > setup. Minor nit pick: s/everytime/every time > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hvs.c | 4 > 1 file changed, 4 insertions(+) > > diff --git a/drivers/gpu/drm/vc4/vc4_hvs.c b/drivers/gpu/drm/vc4/vc4_hvs.c > index c7de77afbf0a..64b9d72471ef 100644 > --- a/drivers/gpu/drm/vc4/vc4_hvs.c > +++ b/drivers/gpu/drm/vc4/vc4_hvs.c > @@ -205,6 +205,10 @@ static int vc4_hvs_init_channel(struct vc4_dev *vc4, > struct drm_crtc *crtc, > u32 dispbkgndx; > u32 dispctrl; > > + HVS_WRITE(SCALER_DISPCTRLX(chan), 0); > + HVS_WRITE(SCALER_DISPCTRLX(chan), SCALER_DISPCTRLX_RESET); > + HVS_WRITE(SCALER_DISPCTRLX(chan), 0); > + > /* Turn on the scaler, which will wait for vstart to start > * compositing. > * When feeding the transposer, we should operate in oneshot > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 25/78] drm/vc4: crtc: Remove mode_set_nofb
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > On BCM2711 to avoid stale pixels getting stuck in intermediate FIFOs, the > pixelvalve needs to be setup each time there's a mode change or enable / > disable sequence. > > Therefore, we can't really use mode_set_nofb anymore to configure it, but > we need to move it to atomic_enable. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_crtc.c | 7 +-- > 1 file changed, 1 insertion(+), 6 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_crtc.c b/drivers/gpu/drm/vc4/vc4_crtc.c > index 284a85b9d7d4..2eda2e6429ec 100644 > --- a/drivers/gpu/drm/vc4/vc4_crtc.c > +++ b/drivers/gpu/drm/vc4/vc4_crtc.c > @@ -376,11 +376,6 @@ static void vc4_crtc_config_pv(struct drm_crtc *crtc) > } > } > > -static void vc4_crtc_mode_set_nofb(struct drm_crtc *crtc) > -{ > - vc4_crtc_config_pv(crtc); > -} > - > static void require_hvs_enabled(struct drm_device *dev) > { > struct vc4_dev *vc4 = to_vc4_dev(dev); > @@ -433,6 +428,7 @@ static void vc4_crtc_atomic_enable(struct drm_crtc *crtc, > require_hvs_enabled(dev); > > vc4_crtc_pixelvalve_reset(crtc); > + vc4_crtc_config_pv(crtc); > > CRTC_WRITE(PV_CONTROL, CRTC_READ(PV_CONTROL) | PV_CONTROL_EN); > > @@ -791,7 +787,6 @@ static const struct drm_crtc_funcs vc4_crtc_funcs = { > }; > > static const struct drm_crtc_helper_funcs vc4_crtc_helper_funcs = { > - .mode_set_nofb = vc4_crtc_mode_set_nofb, > .mode_valid = vc4_crtc_mode_valid, > .atomic_check = vc4_crtc_atomic_check, > .atomic_flush = vc4_hvs_atomic_flush, > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 26/78] drm/vc4: crtc: Remove redundant pixelvalve reset
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > Since we moved the pixelvalve configuration to atomic_enable, we're now > first calling the function that resets the pixelvalve and then the one that > configures it. > > However, the first thing the latter is doing is calling the reset function, > meaning that we reset twice our pixelvalve. Let's remove the first call. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_crtc.c | 1 - > 1 file changed, 1 deletion(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_crtc.c b/drivers/gpu/drm/vc4/vc4_crtc.c > index 2eda2e6429ec..2c5ff45dc315 100644 > --- a/drivers/gpu/drm/vc4/vc4_crtc.c > +++ b/drivers/gpu/drm/vc4/vc4_crtc.c > @@ -427,7 +427,6 @@ static void vc4_crtc_atomic_enable(struct drm_crtc *crtc, > > require_hvs_enabled(dev); > > - vc4_crtc_pixelvalve_reset(crtc); > vc4_crtc_config_pv(crtc); > > CRTC_WRITE(PV_CONTROL, CRTC_READ(PV_CONTROL) | PV_CONTROL_EN); > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 27/78] drm/vc4: crtc: Move HVS channel init before the PV initialisation
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > In order to avoid stale pixels getting stuck in an intermediate FIFO > between the HVS and the pixelvalve on BCM2711, we need to configure the HVS > channel before the pixelvalve is reset and configured. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_crtc.c | 8 > 1 file changed, 4 insertions(+), 4 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_crtc.c b/drivers/gpu/drm/vc4/vc4_crtc.c > index 2c5ff45dc315..b7b0e19e2fe1 100644 > --- a/drivers/gpu/drm/vc4/vc4_crtc.c > +++ b/drivers/gpu/drm/vc4/vc4_crtc.c > @@ -427,10 +427,6 @@ static void vc4_crtc_atomic_enable(struct drm_crtc *crtc, > > require_hvs_enabled(dev); > > - vc4_crtc_config_pv(crtc); > - > - CRTC_WRITE(PV_CONTROL, CRTC_READ(PV_CONTROL) | PV_CONTROL_EN); > - > /* Enable vblank irq handling before crtc is started otherwise > * drm_crtc_get_vblank() fails in vc4_crtc_update_dlist(). > */ > @@ -438,6 +434,10 @@ static void vc4_crtc_atomic_enable(struct drm_crtc *crtc, > > vc4_hvs_atomic_enable(crtc, old_state); > > + vc4_crtc_config_pv(crtc); > + > + CRTC_WRITE(PV_CONTROL, CRTC_READ(PV_CONTROL) | PV_CONTROL_EN); > + > /* When feeding the transposer block the pixelvalve is unneeded and > * should not be enabled. > */ > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PULL] drm-misc-fixes
Hi Dave and Daniel, here's this week's PR for drm-misc-fixes. It's mostly driver stuff. There's one fix in the GEM ioctl code, but it has no impact on the UAPI. Best regards Thomas drm-misc-fixes-2020-07-28: * drm: fix possible use-after-free * dbi: fix SPI Type 1 transfer * drm_fb_helper: use memcpy_io on bochs' sparc64 * mcde: fix stability * panel: fix display noise on auo,kd101n80-45na * panel: delay HPD checks for boe_nv133fhm_n61 * bridge: drop connector check in nwl-dsi bridge * bridge: set proper bridge type for adv7511 * of: fix a double free The following changes since commit f3f90c6db188d437add55aaffadd5ad5bcb8cda6: drm/lima: fix wait pp reset timeout (2020-07-20 08:46:06 +0800) are available in the Git repository at: git://anongit.freedesktop.org/drm/drm-misc tags/drm-misc-fixes-2020-07-28 for you to fetch changes up to 8490d6a7e0a0a6fab5c2d82d57a3937306660864: drm: hold gem reference until object is no longer accessed (2020-07-27 22:05:51 +0200) * drm: fix possible use-after-free * dbi: fix SPI Type 1 transfer * drm_fb_helper: use memcpy_io on bochs' sparc64 * mcde: fix stability * panel: fix display noise on auo,kd101n80-45na * panel: delay HPD checks for boe_nv133fhm_n61 * bridge: drop connector check in nwl-dsi bridge * bridge: set proper bridge type for adv7511 * of: fix a double free Biju Das (1): drm: of: Fix double-free bug Douglas Anderson (1): drm: panel: simple: Delay HPD checking on boe_nv133fhm_n61 for 15 ms Guido Günther (1): drm/bridge: nwl-dsi: Drop DRM_BRIDGE_ATTACH_NO_CONNECTOR check. Jitao Shi (1): drm/panel: Fix auo, kd101n80-45na horizontal noise on edges of panel Laurentiu Palcu (1): drm/bridge/adv7511: set the bridge type properly Linus Walleij (1): drm/mcde: Fix stability issue Paul Cercueil (1): drm/dbi: Fix SPI Type 1 (9-bit) transfer Sam Ravnborg (1): drm/drm_fb_helper: fix fbdev with sparc64 Steve Cohen (1): drm: hold gem reference until object is no longer accessed drivers/gpu/drm/bochs/bochs_kms.c | 1 + drivers/gpu/drm/bridge/adv7511/adv7511_drv.c | 1 + drivers/gpu/drm/bridge/nwl-dsi.c | 5 - drivers/gpu/drm/drm_fb_helper.c| 6 +- drivers/gpu/drm/drm_gem.c | 10 -- drivers/gpu/drm/drm_mipi_dbi.c | 2 +- drivers/gpu/drm/drm_of.c | 4 +--- drivers/gpu/drm/mcde/mcde_display.c| 11 --- drivers/gpu/drm/panel/panel-boe-tv101wum-nl6.c | 6 +++--- drivers/gpu/drm/panel/panel-simple.c | 16 +++- include/drm/drm_mode_config.h | 12 11 files changed, 51 insertions(+), 23 deletions(-) ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH] drm/amd/display: Clear dm_state for fast updates
On Monday, July 27, 2020 5:32 PM, Daniel Vetter wrote: > On Mon, Jul 27, 2020 at 11:11 PM Mazin Rezk wrote: > > > > On Monday, July 27, 2020 4:29 PM, Daniel Vetter wrote: > > > > > On Mon, Jul 27, 2020 at 9:28 PM Christian König > > > wrote: > > > > > > > > Am 27.07.20 um 16:05 schrieb Kazlauskas, Nicholas: > > > > > On 2020-07-27 9:39 a.m., Christian König wrote: > > > > >> Am 27.07.20 um 07:40 schrieb Mazin Rezk: > > > > >>> This patch fixes a race condition that causes a use-after-free > > > > >>> during > > > > >>> amdgpu_dm_atomic_commit_tail. This can occur when 2 non-blocking > > > > >>> commits > > > > >>> are requested and the second one finishes before the first. > > > > >>> Essentially, > > > > >>> this bug occurs when the following sequence of events happens: > > > > >>> > > > > >>> 1. Non-blocking commit #1 is requested w/ a new dm_state #1 and is > > > > >>> deferred to the workqueue. > > > > >>> > > > > >>> 2. Non-blocking commit #2 is requested w/ a new dm_state #2 and is > > > > >>> deferred to the workqueue. > > > > >>> > > > > >>> 3. Commit #2 starts before commit #1, dm_state #1 is used in the > > > > >>> commit_tail and commit #2 completes, freeing dm_state #1. > > > > >>> > > > > >>> 4. Commit #1 starts after commit #2 completes, uses the freed > > > > >>> dm_state > > > > >>> 1 and dereferences a freelist pointer while setting the context. > > > > >> > > > > >> Well I only have a one mile high view on this, but why don't you let > > > > >> the work items execute in order? > > > > >> > > > > >> That would be better anyway cause this way we don't trigger a cache > > > > >> line ping pong between CPUs. > > > > >> > > > > >> Christian. > > > > > > > > > > We use the DRM helpers for managing drm_atomic_commit_state and those > > > > > helpers internally push non-blocking commit work into the system > > > > > unbound work queue. > > > > > > > > Mhm, well if you send those helper atomic commits in the order A,B and > > > > they execute it in the order B,A I would call that a bug :) > > > > > > The way it works is it pushes all commits into unbound work queue, but > > > then forces serialization as needed. We do _not_ want e.g. updates on > > > different CRTC to be serialized, that would result in lots of judder. > > > And hw is funny enough that there's all kinds of dependencies. > > > > > > The way you force synchronization is by adding other CRTC state > > > objects. So if DC is busted and can only handle a single update per > > > work item, then I guess you always need all CRTC states and everything > > > will be run in order. But that also totally kills modern multi-screen > > > compositors. Xorg isn't modern, just in case that's not clear :-) > > > > > > Lucking at the code it seems like you indeed have only a single dm > > > state, so yeah global sync is what you'll need as immediate fix, and > > > then maybe fix up DM to not be quite so silly ... or at least only do > > > the dm state stuff when really needed. > > > > > > We could also sprinkle the drm_crtc_commit structure around a bit > > > (it's the glue that provides the synchronization across commits), but > > > since your dm state is global just grabbing all crtc states > > > unconditionally as part of that is probably best. > > > > > > > > While we could duplicate a copy of that code with nothing but the > > > > > workqueue changed that isn't something I'd really like to maintain > > > > > going forward. > > > > > > > > I'm not talking about duplicating the code, I'm talking about fixing the > > > > helpers. I don't know that code well, but from the outside it sounds > > > > like a bug there. > > > > > > > > And executing work items in the order they are submitted is trivial. > > > > > > > > Had anybody pinged Daniel or other people familiar with the helper code > > > > about it? > > > > > > Yeah something is wrong here, and the fix looks horrible :-) > > > > > > Aside, I've also seen some recent discussion flare up about > > > drm_atomic_state_get/put used to paper over some other use-after-free, > > > but this time related to interrupt handlers. Maybe a few rules about > > > that: > > > - dont > > > - especially not when it's interrupt handlers, because you can't call > > > drm_atomic_state_put from interrupt handlers. > > > > > > Instead have an spin_lock_irq to protect the shared date with your > > > interrupt handler, and _copy_ the date over. This is e.g. what > > > drm_crtc_arm_vblank_event does. > > > > Nicholas wrote a patch that attempted to resolve the issue by adding every > > CRTC into the commit to use use the stall checks. [1] While this forces > > synchronisation on commits, it's kind of a hacky method that may take a > > toll on performance. > > > > Is it possible to have a DRM helper that forces synchronisation on some > > commits without having to add every CRTC into the commit? > > > > Also, is synchronisation really necessary for fast updates in amdgpu? > > I'll admit, the idea of eliminating the us
Re: [PATCH] drm/amd/display: Clear dm_state for fast updates
On Monday, July 27, 2020 7:42 PM, Mazin Rezk wrote: > On Monday, July 27, 2020 5:32 PM, Daniel Vetter wrote: > > > On Mon, Jul 27, 2020 at 11:11 PM Mazin Rezk wrote: > > > > > > On Monday, July 27, 2020 4:29 PM, Daniel Vetter wrote: > > > > > > > On Mon, Jul 27, 2020 at 9:28 PM Christian König > > > > wrote: > > > > > > > > > > Am 27.07.20 um 16:05 schrieb Kazlauskas, Nicholas: > > > > > > On 2020-07-27 9:39 a.m., Christian König wrote: > > > > > >> Am 27.07.20 um 07:40 schrieb Mazin Rezk: > > > > > >>> This patch fixes a race condition that causes a use-after-free > > > > > >>> during > > > > > >>> amdgpu_dm_atomic_commit_tail. This can occur when 2 non-blocking > > > > > >>> commits > > > > > >>> are requested and the second one finishes before the first. > > > > > >>> Essentially, > > > > > >>> this bug occurs when the following sequence of events happens: > > > > > >>> > > > > > >>> 1. Non-blocking commit #1 is requested w/ a new dm_state #1 and is > > > > > >>> deferred to the workqueue. > > > > > >>> > > > > > >>> 2. Non-blocking commit #2 is requested w/ a new dm_state #2 and is > > > > > >>> deferred to the workqueue. > > > > > >>> > > > > > >>> 3. Commit #2 starts before commit #1, dm_state #1 is used in the > > > > > >>> commit_tail and commit #2 completes, freeing dm_state #1. > > > > > >>> > > > > > >>> 4. Commit #1 starts after commit #2 completes, uses the freed > > > > > >>> dm_state > > > > > >>> 1 and dereferences a freelist pointer while setting the context. > > > > > >> > > > > > >> Well I only have a one mile high view on this, but why don't you > > > > > >> let > > > > > >> the work items execute in order? > > > > > >> > > > > > >> That would be better anyway cause this way we don't trigger a cache > > > > > >> line ping pong between CPUs. > > > > > >> > > > > > >> Christian. > > > > > > > > > > > > We use the DRM helpers for managing drm_atomic_commit_state and > > > > > > those > > > > > > helpers internally push non-blocking commit work into the system > > > > > > unbound work queue. > > > > > > > > > > Mhm, well if you send those helper atomic commits in the order A,B and > > > > > they execute it in the order B,A I would call that a bug :) > > > > > > > > The way it works is it pushes all commits into unbound work queue, but > > > > then forces serialization as needed. We do _not_ want e.g. updates on > > > > different CRTC to be serialized, that would result in lots of judder. > > > > And hw is funny enough that there's all kinds of dependencies. > > > > > > > > The way you force synchronization is by adding other CRTC state > > > > objects. So if DC is busted and can only handle a single update per > > > > work item, then I guess you always need all CRTC states and everything > > > > will be run in order. But that also totally kills modern multi-screen > > > > compositors. Xorg isn't modern, just in case that's not clear :-) > > > > > > > > Lucking at the code it seems like you indeed have only a single dm > > > > state, so yeah global sync is what you'll need as immediate fix, and > > > > then maybe fix up DM to not be quite so silly ... or at least only do > > > > the dm state stuff when really needed. > > > > > > > > We could also sprinkle the drm_crtc_commit structure around a bit > > > > (it's the glue that provides the synchronization across commits), but > > > > since your dm state is global just grabbing all crtc states > > > > unconditionally as part of that is probably best. > > > > > > > > > > While we could duplicate a copy of that code with nothing but the > > > > > > workqueue changed that isn't something I'd really like to maintain > > > > > > going forward. > > > > > > > > > > I'm not talking about duplicating the code, I'm talking about fixing > > > > > the > > > > > helpers. I don't know that code well, but from the outside it sounds > > > > > like a bug there. > > > > > > > > > > And executing work items in the order they are submitted is trivial. > > > > > > > > > > Had anybody pinged Daniel or other people familiar with the helper > > > > > code > > > > > about it? > > > > > > > > Yeah something is wrong here, and the fix looks horrible :-) > > > > > > > > Aside, I've also seen some recent discussion flare up about > > > > drm_atomic_state_get/put used to paper over some other use-after-free, > > > > but this time related to interrupt handlers. Maybe a few rules about > > > > that: > > > > - dont > > > > - especially not when it's interrupt handlers, because you can't call > > > > drm_atomic_state_put from interrupt handlers. > > > > > > > > Instead have an spin_lock_irq to protect the shared date with your > > > > interrupt handler, and _copy_ the date over. This is e.g. what > > > > drm_crtc_arm_vblank_event does. > > > > > > Nicholas wrote a patch that attempted to resolve the issue by adding every > > > CRTC into the commit to use use the stall checks. [1] While this forces > > > synchronisation on commits, it's kind of a hacky method that ma
Re: [PATCH v4 28/78] drm/vc4: encoder: Add finer-grained encoder callbacks
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > In the BCM2711, the setup of the HVS, pixelvalve and HDMI controller > requires very precise ordering and timing that the regular atomic callbacks > don't provide. Let's add new callbacks on top of the regular ones to be > able to split the configuration as needed. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_crtc.c | 19 +++ > drivers/gpu/drm/vc4/vc4_drv.h | 7 +++ > 2 files changed, 26 insertions(+) > > diff --git a/drivers/gpu/drm/vc4/vc4_crtc.c b/drivers/gpu/drm/vc4/vc4_crtc.c > index b7b0e19e2fe1..d0b326e1df0a 100644 > --- a/drivers/gpu/drm/vc4/vc4_crtc.c > +++ b/drivers/gpu/drm/vc4/vc4_crtc.c > @@ -389,6 +389,8 @@ static void vc4_crtc_atomic_disable(struct drm_crtc *crtc, > { > struct drm_device *dev = crtc->dev; > struct vc4_crtc *vc4_crtc = to_vc4_crtc(crtc); > + struct drm_encoder *encoder = vc4_get_crtc_encoder(crtc); > + struct vc4_encoder *vc4_encoder = to_vc4_encoder(encoder); > int ret; > > require_hvs_enabled(dev); > @@ -401,10 +403,16 @@ static void vc4_crtc_atomic_disable(struct drm_crtc > *crtc, > ret = wait_for(!(CRTC_READ(PV_V_CONTROL) & PV_VCONTROL_VIDEN), 1); > WARN_ONCE(ret, "Timeout waiting for !PV_VCONTROL_VIDEN\n"); > > + if (vc4_encoder->post_crtc_disable) > + vc4_encoder->post_crtc_disable(encoder); > + > CRTC_WRITE(PV_CONTROL, CRTC_READ(PV_CONTROL) & ~PV_CONTROL_EN); > > vc4_hvs_atomic_disable(crtc, old_state); > > + if (vc4_encoder->post_crtc_powerdown) > + vc4_encoder->post_crtc_powerdown(encoder); > + > /* > * Make sure we issue a vblank event after disabling the CRTC if > * someone was waiting it. > @@ -424,6 +432,8 @@ static void vc4_crtc_atomic_enable(struct drm_crtc *crtc, > { > struct drm_device *dev = crtc->dev; > struct vc4_crtc *vc4_crtc = to_vc4_crtc(crtc); > + struct drm_encoder *encoder = vc4_get_crtc_encoder(crtc); > + struct vc4_encoder *vc4_encoder = to_vc4_encoder(encoder); > > require_hvs_enabled(dev); > > @@ -434,15 +444,24 @@ static void vc4_crtc_atomic_enable(struct drm_crtc > *crtc, > > vc4_hvs_atomic_enable(crtc, old_state); > > + if (vc4_encoder->pre_crtc_configure) > + vc4_encoder->pre_crtc_configure(encoder); > + > vc4_crtc_config_pv(crtc); > > CRTC_WRITE(PV_CONTROL, CRTC_READ(PV_CONTROL) | PV_CONTROL_EN); > > + if (vc4_encoder->pre_crtc_enable) > + vc4_encoder->pre_crtc_enable(encoder); > + > /* When feeding the transposer block the pixelvalve is unneeded and > * should not be enabled. > */ > CRTC_WRITE(PV_V_CONTROL, >CRTC_READ(PV_V_CONTROL) | PV_VCONTROL_VIDEN); > + > + if (vc4_encoder->post_crtc_enable) > + vc4_encoder->post_crtc_enable(encoder); > } > > static enum drm_mode_status vc4_crtc_mode_valid(struct drm_crtc *crtc, > diff --git a/drivers/gpu/drm/vc4/vc4_drv.h b/drivers/gpu/drm/vc4/vc4_drv.h > index dfcc684f5d28..251fcc35530c 100644 > --- a/drivers/gpu/drm/vc4/vc4_drv.h > +++ b/drivers/gpu/drm/vc4/vc4_drv.h > @@ -439,6 +439,13 @@ struct vc4_encoder { > struct drm_encoder base; > enum vc4_encoder_type type; > u32 clock_select; > + > + void (*pre_crtc_configure)(struct drm_encoder *encoder); > + void (*pre_crtc_enable)(struct drm_encoder *encoder); > + void (*post_crtc_enable)(struct drm_encoder *encoder); > + > + void (*post_crtc_disable)(struct drm_encoder *encoder); > + void (*post_crtc_powerdown)(struct drm_encoder *encoder); > }; > > static inline struct vc4_encoder * > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 30/78] drm/vc4: crtc: Clear the PixelValve FIFO on disable
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > In order to avoid a stale pixel getting stuck on mode change or a disable > / enable cycle, we need to make sure to flush the PV FIFO on disable. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_crtc.c | 3 +-- > 1 file changed, 1 insertion(+), 2 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_crtc.c b/drivers/gpu/drm/vc4/vc4_crtc.c > index 7b178d67187f..13fe0e370fb3 100644 > --- a/drivers/gpu/drm/vc4/vc4_crtc.c > +++ b/drivers/gpu/drm/vc4/vc4_crtc.c > @@ -408,8 +408,7 @@ static void vc4_crtc_atomic_disable(struct drm_crtc *crtc, > if (vc4_encoder->post_crtc_disable) > vc4_encoder->post_crtc_disable(encoder); > > - CRTC_WRITE(PV_CONTROL, CRTC_READ(PV_CONTROL) & ~PV_CONTROL_EN); > - > + vc4_crtc_pixelvalve_reset(crtc); > vc4_hvs_atomic_disable(crtc, old_state); > > if (vc4_encoder->post_crtc_powerdown) > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 31/78] drm/vc4: crtc: Clear the PixelValve FIFO during configuration
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > Even though it's not really clear why we need to flush the PV FIFO during > the configuration even though we started by flushing it, experience shows > that without it we get a stale pixel stuck in the FIFO between the HVS and > the PV. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_crtc.c | 2 +- > 1 file changed, 1 insertion(+), 1 deletion(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_crtc.c b/drivers/gpu/drm/vc4/vc4_crtc.c > index 13fe0e370fb3..25a77cd46b28 100644 > --- a/drivers/gpu/drm/vc4/vc4_crtc.c > +++ b/drivers/gpu/drm/vc4/vc4_crtc.c > @@ -358,7 +358,7 @@ static void vc4_crtc_config_pv(struct drm_crtc *crtc) > if (is_dsi) > CRTC_WRITE(PV_HACT_ACT, mode->hdisplay * pixel_rep); > > - CRTC_WRITE(PV_CONTROL, > + CRTC_WRITE(PV_CONTROL, PV_CONTROL_FIFO_CLR | >vc4_crtc_get_fifo_full_level_bits(vc4_crtc, format) | >VC4_SET_FIELD(format, PV_CONTROL_FORMAT) | >VC4_SET_FIELD(pixel_rep - 1, PV_CONTROL_PIXEL_REP) | > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 40/78] drm/vc4: hdmi: rework connectors and encoders
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > the vc4_hdmi driver has some custom structures to hold the data it needs to > associate with the drm_encoder and drm_connector structures. > > However, it allocates them separately from the vc4_hdmi structure which > makes it more complicated than it needs to be. > > Move those structures to be contained by vc4_hdmi and update the code > accordingly. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 87 --- > drivers/gpu/drm/vc4/vc4_hdmi.h | 64 +- > 2 files changed, 72 insertions(+), 79 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index db79e0d88625..1e2214f24ed7 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -191,20 +191,15 @@ static const struct drm_connector_helper_funcs > vc4_hdmi_connector_helper_funcs = > .get_modes = vc4_hdmi_connector_get_modes, > }; > > -static struct drm_connector *vc4_hdmi_connector_init(struct drm_device *dev, > -struct drm_encoder > *encoder, > -struct i2c_adapter *ddc) > +static int vc4_hdmi_connector_init(struct drm_device *dev, > + struct vc4_hdmi *vc4_hdmi, > + struct i2c_adapter *ddc) > { > - struct drm_connector *connector; > - struct vc4_hdmi_connector *hdmi_connector; > + struct vc4_hdmi_connector *hdmi_connector = &vc4_hdmi->connector; > + struct drm_connector *connector = &hdmi_connector->base; > + struct drm_encoder *encoder = &vc4_hdmi->encoder.base.base; > int ret; > > - hdmi_connector = devm_kzalloc(dev->dev, sizeof(*hdmi_connector), > - GFP_KERNEL); > - if (!hdmi_connector) > - return ERR_PTR(-ENOMEM); > - connector = &hdmi_connector->base; > - > hdmi_connector->encoder = encoder; > > drm_connector_init_with_ddc(dev, connector, > @@ -216,7 +211,7 @@ static struct drm_connector > *vc4_hdmi_connector_init(struct drm_device *dev, > /* Create and attach TV margin props to this connector. */ > ret = drm_mode_create_tv_margin_properties(dev); > if (ret) > - return ERR_PTR(ret); > + return ret; > > drm_connector_attach_tv_margin_properties(connector); > > @@ -228,7 +223,7 @@ static struct drm_connector > *vc4_hdmi_connector_init(struct drm_device *dev, > > drm_connector_attach_encoder(connector, encoder); > > - return connector; > + return 0; > } > > static int vc4_hdmi_stop_packet(struct drm_encoder *encoder, > @@ -298,21 +293,22 @@ static void vc4_hdmi_set_avi_infoframe(struct > drm_encoder *encoder) > struct vc4_hdmi_encoder *vc4_encoder = to_vc4_hdmi_encoder(encoder); > struct vc4_dev *vc4 = encoder->dev->dev_private; > struct vc4_hdmi *hdmi = vc4->hdmi; > - struct drm_connector_state *cstate = hdmi->connector->state; > + struct drm_connector *connector = &hdmi->connector.base; > + struct drm_connector_state *cstate = connector->state; > struct drm_crtc *crtc = encoder->crtc; > const struct drm_display_mode *mode = &crtc->state->adjusted_mode; > union hdmi_infoframe frame; > int ret; > > ret = drm_hdmi_avi_infoframe_from_display_mode(&frame.avi, > - hdmi->connector, mode); > + connector, mode); > if (ret < 0) { > DRM_ERROR("couldn't fill AVI infoframe\n"); > return; > } > > drm_hdmi_avi_infoframe_quant_range(&frame.avi, > - hdmi->connector, mode, > + connector, mode, >vc4_encoder->limited_rgb_range ? >HDMI_QUANTIZATION_RANGE_LIMITED : >HDMI_QUANTIZATION_RANGE_FULL); > @@ -628,7 +624,8 @@ static const struct drm_encoder_helper_funcs > vc4_hdmi_encoder_helper_funcs = { > /* HDMI audio codec callbacks */ > static void vc4_hdmi_audio_set_mai_clock(struct vc4_hdmi *hdmi) > { > - struct drm_device *drm = hdmi->encoder->dev; > + struct drm_encoder *encoder = &hdmi->encoder.base.base; > + struct drm_device *drm = encoder->dev; > struct vc4_dev *vc4 = to_vc4_dev(drm); > u32 hsm_clock = clk_get_rate(hdmi->hsm_clock); > unsigned long n, m; > @@ -647,7 +644,7 @@ static void vc4_hdmi_audio_set_mai_clock(struct vc4_hdmi > *hdmi) > > static void vc4_hdmi_set_n_cts(struct vc4_hdmi *hdmi) > { > - struct drm_encoder *encoder = hd
Re: [PATCH v4 47/78] drm/vc4: hdmi: Retrieve the vc4_hdmi at unbind using our device
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > The unbind function needs to retrieve a vc4_hdmi structure pointer through > the struct device that we're given since we want to support multiple HDMI > controllers. > > However, our optional ASoC support doesn't make that trivial since it will > overwrite the device drvdata if we use it, but obviously won't if we don't > use it. > > Let's make sure the fields are at the proper offset to be able to cast > between the snd_soc_card structure and the vc4_hdmi structure > transparently so we can support both cases. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 24 +++- > drivers/gpu/drm/vc4/vc4_hdmi.h | 4 ++-- > 2 files changed, 25 insertions(+), 3 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index 09b297a1b39d..7cd1394c10fa 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -1200,6 +1200,7 @@ static int vc4_hdmi_bind(struct device *dev, struct > device *master, void *data) > if (!vc4_hdmi) > return -ENOMEM; > > + dev_set_drvdata(dev, vc4_hdmi); > encoder = &vc4_hdmi->encoder.base.base; > vc4_hdmi->encoder.base.type = VC4_ENCODER_TYPE_HDMI0; > vc4_hdmi->pdev = pdev; > @@ -1362,7 +1363,28 @@ static void vc4_hdmi_unbind(struct device *dev, struct > device *master, > { > struct drm_device *drm = dev_get_drvdata(master); > struct vc4_dev *vc4 = drm->dev_private; > - struct vc4_hdmi *vc4_hdmi = vc4->hdmi; > + struct vc4_hdmi *vc4_hdmi; > + > + /* > +* ASoC makes it a bit hard to retrieve a pointer to the > +* vc4_hdmi structure. Registering the card will overwrite our > +* device drvdata with a pointer to the snd_soc_card structure, > +* which can then be used to retrieve whatever drvdata we want > +* to associate. > +* > +* However, that doesn't fly in the case where we wouldn't > +* register an ASoC card (because of an old DT that is missing > +* the dmas properties for example), then the card isn't > +* registered and the device drvdata wouldn't be set. > +* > +* We can deal with both cases by making sure a snd_soc_card > +* pointer and a vc4_hdmi structure are pointing to the same > +* memory address, so we can treat them indistinctly without any > +* issue. > +*/ > + BUILD_BUG_ON(offsetof(struct vc4_hdmi_audio, card) != 0); > + BUILD_BUG_ON(offsetof(struct vc4_hdmi, audio) != 0); > + vc4_hdmi = dev_get_drvdata(dev); > > cec_unregister_adapter(vc4_hdmi->cec_adap); > vc4_hdmi_connector_destroy(&vc4_hdmi->connector.base); > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.h b/drivers/gpu/drm/vc4/vc4_hdmi.h > index 749a807cd1f3..d43462789450 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.h > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.h > @@ -53,13 +53,13 @@ struct vc4_hdmi_audio { > > /* General HDMI hardware state. */ > struct vc4_hdmi { > + struct vc4_hdmi_audio audio; > + > struct platform_device *pdev; > > struct vc4_hdmi_encoder encoder; > struct vc4_hdmi_connector connector; > > - struct vc4_hdmi_audio audio; > - > struct i2c_adapter *ddc; > void __iomem *hdmicore_regs; > void __iomem *hd_regs; > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 50/78] drm/vc4: hdmi: Introduce resource init and variant
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > The HDMI controllers found in the BCM2711 has a pretty different clock and > registers areas than found in the older BCM283x SoCs. > > Let's create a variant structure to store the various adjustments we'll > need later on, and a function to get the resources needed for one > particular version. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 61 +++ > drivers/gpu/drm/vc4/vc4_hdmi.h | 10 ++- > 2 files changed, 51 insertions(+), 20 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index ec7710dfd04e..ac021e07a8cb 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -1179,28 +1179,12 @@ static const struct cec_adap_ops > vc4_hdmi_cec_adap_ops = { > }; > #endif > > -static int vc4_hdmi_bind(struct device *dev, struct device *master, void > *data) > +static int vc4_hdmi_init_resources(struct vc4_hdmi *vc4_hdmi) > { > -#ifdef CONFIG_DRM_VC4_HDMI_CEC > - struct cec_connector_info conn_info; > -#endif > - struct platform_device *pdev = to_platform_device(dev); > - struct drm_device *drm = dev_get_drvdata(master); > - struct vc4_hdmi *vc4_hdmi; > - struct drm_encoder *encoder; > - struct device_node *ddc_node; > - u32 value; > + struct platform_device *pdev = vc4_hdmi->pdev; > + struct device *dev = &pdev->dev; > int ret; > > - vc4_hdmi = devm_kzalloc(dev, sizeof(*vc4_hdmi), GFP_KERNEL); > - if (!vc4_hdmi) > - return -ENOMEM; > - > - dev_set_drvdata(dev, vc4_hdmi); > - encoder = &vc4_hdmi->encoder.base.base; > - vc4_hdmi->encoder.base.type = VC4_ENCODER_TYPE_HDMI0; > - vc4_hdmi->pdev = pdev; > - > vc4_hdmi->hdmicore_regs = vc4_ioremap_regs(pdev, 0); > if (IS_ERR(vc4_hdmi->hdmicore_regs)) > return PTR_ERR(vc4_hdmi->hdmicore_regs); > @@ -1212,6 +1196,7 @@ static int vc4_hdmi_bind(struct device *dev, struct > device *master, void *data) > vc4_hdmi->hdmi_regset.base = vc4_hdmi->hdmicore_regs; > vc4_hdmi->hdmi_regset.regs = hdmi_regs; > vc4_hdmi->hdmi_regset.nregs = ARRAY_SIZE(hdmi_regs); > + > vc4_hdmi->hd_regset.base = vc4_hdmi->hd_regs; > vc4_hdmi->hd_regset.regs = hd_regs; > vc4_hdmi->hd_regset.nregs = ARRAY_SIZE(hd_regs); > @@ -1223,12 +1208,44 @@ static int vc4_hdmi_bind(struct device *dev, struct > device *master, void *data) > DRM_ERROR("Failed to get pixel clock\n"); > return ret; > } > + > vc4_hdmi->hsm_clock = devm_clk_get(dev, "hdmi"); > if (IS_ERR(vc4_hdmi->hsm_clock)) { > DRM_ERROR("Failed to get HDMI state machine clock\n"); > return PTR_ERR(vc4_hdmi->hsm_clock); > } > > + return 0; > +} > + > +static int vc4_hdmi_bind(struct device *dev, struct device *master, void > *data) > +{ > +#ifdef CONFIG_DRM_VC4_HDMI_CEC > + struct cec_connector_info conn_info; > +#endif > + const struct vc4_hdmi_variant *variant = > of_device_get_match_data(dev); > + struct platform_device *pdev = to_platform_device(dev); > + struct drm_device *drm = dev_get_drvdata(master); > + struct vc4_hdmi *vc4_hdmi; > + struct drm_encoder *encoder; > + struct device_node *ddc_node; > + u32 value; > + int ret; > + > + vc4_hdmi = devm_kzalloc(dev, sizeof(*vc4_hdmi), GFP_KERNEL); > + if (!vc4_hdmi) > + return -ENOMEM; > + > + dev_set_drvdata(dev, vc4_hdmi); > + encoder = &vc4_hdmi->encoder.base.base; > + vc4_hdmi->encoder.base.type = VC4_ENCODER_TYPE_HDMI0; > + vc4_hdmi->pdev = pdev; > + vc4_hdmi->variant = variant; > + > + ret = variant->init_resources(vc4_hdmi); > + if (ret) > + return ret; > + > ddc_node = of_parse_phandle(dev->of_node, "ddc", 0); > if (!ddc_node) { > DRM_ERROR("Failed to find ddc node in device tree\n"); > @@ -1404,8 +1421,12 @@ static int vc4_hdmi_dev_remove(struct platform_device > *pdev) > return 0; > } > > +static const struct vc4_hdmi_variant bcm2835_variant = { > + .init_resources = vc4_hdmi_init_resources, > +}; > + > static const struct of_device_id vc4_hdmi_dt_match[] = { > - { .compatible = "brcm,bcm2835-hdmi" }, > + { .compatible = "brcm,bcm2835-hdmi", .data = &bcm2835_variant }, > {} > }; > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.h b/drivers/gpu/drm/vc4/vc4_hdmi.h > index 674541493909..0eaf979fe811 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.h > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.h > @@ -21,6 +21,15 @@ to_vc4_hdmi_encoder(struct drm_encoder *encoder) > return container_of(encoder, struct vc4_hdmi_encoder, base.base); > } > > +struct vc4_hdmi
Re: [PATCH v4 51/78] drm/vc4: hdmi: Implement a register layout abstraction
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > The HDMI controllers found in the BCM2711 have most of the registers > reorganized in multiple registers areas and at different offsets than > previously found. > > The logic however remains pretty much the same, so it doesn't really make > sense to create a whole new driver and we should share the code as much as > possible. > > Let's implement some indirection to wrap around a register and depending on > the variant will lookup the associated register on that particular variant. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 427 ++--- > drivers/gpu/drm/vc4/vc4_hdmi.h | 12 +- > drivers/gpu/drm/vc4/vc4_hdmi_regs.h | 241 - > drivers/gpu/drm/vc4/vc4_regs.h | 92 +-- > 4 files changed, 464 insertions(+), 308 deletions(-) > create mode 100644 drivers/gpu/drm/vc4/vc4_hdmi_regs.h > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index ac021e07a8cb..a4fed1439bf3 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -50,62 +50,13 @@ > #include "media/cec.h" > #include "vc4_drv.h" > #include "vc4_hdmi.h" > +#include "vc4_hdmi_regs.h" > #include "vc4_regs.h" > > #define HSM_CLOCK_FREQ 163682864 > #define CEC_CLOCK_FREQ 4 > #define CEC_CLOCK_DIV (HSM_CLOCK_FREQ / CEC_CLOCK_FREQ) > > -static const struct debugfs_reg32 hdmi_regs[] = { > - VC4_REG32(VC4_HDMI_CORE_REV), > - VC4_REG32(VC4_HDMI_SW_RESET_CONTROL), > - VC4_REG32(VC4_HDMI_HOTPLUG_INT), > - VC4_REG32(VC4_HDMI_HOTPLUG), > - VC4_REG32(VC4_HDMI_MAI_CHANNEL_MAP), > - VC4_REG32(VC4_HDMI_MAI_CONFIG), > - VC4_REG32(VC4_HDMI_MAI_FORMAT), > - VC4_REG32(VC4_HDMI_AUDIO_PACKET_CONFIG), > - VC4_REG32(VC4_HDMI_RAM_PACKET_CONFIG), > - VC4_REG32(VC4_HDMI_HORZA), > - VC4_REG32(VC4_HDMI_HORZB), > - VC4_REG32(VC4_HDMI_FIFO_CTL), > - VC4_REG32(VC4_HDMI_SCHEDULER_CONTROL), > - VC4_REG32(VC4_HDMI_VERTA0), > - VC4_REG32(VC4_HDMI_VERTA1), > - VC4_REG32(VC4_HDMI_VERTB0), > - VC4_REG32(VC4_HDMI_VERTB1), > - VC4_REG32(VC4_HDMI_TX_PHY_RESET_CTL), > - VC4_REG32(VC4_HDMI_TX_PHY_CTL0), > - > - VC4_REG32(VC4_HDMI_CEC_CNTRL_1), > - VC4_REG32(VC4_HDMI_CEC_CNTRL_2), > - VC4_REG32(VC4_HDMI_CEC_CNTRL_3), > - VC4_REG32(VC4_HDMI_CEC_CNTRL_4), > - VC4_REG32(VC4_HDMI_CEC_CNTRL_5), > - VC4_REG32(VC4_HDMI_CPU_STATUS), > - VC4_REG32(VC4_HDMI_CPU_MASK_STATUS), > - > - VC4_REG32(VC4_HDMI_CEC_RX_DATA_1), > - VC4_REG32(VC4_HDMI_CEC_RX_DATA_2), > - VC4_REG32(VC4_HDMI_CEC_RX_DATA_3), > - VC4_REG32(VC4_HDMI_CEC_RX_DATA_4), > - VC4_REG32(VC4_HDMI_CEC_TX_DATA_1), > - VC4_REG32(VC4_HDMI_CEC_TX_DATA_2), > - VC4_REG32(VC4_HDMI_CEC_TX_DATA_3), > - VC4_REG32(VC4_HDMI_CEC_TX_DATA_4), > -}; > - > -static const struct debugfs_reg32 hd_regs[] = { > - VC4_REG32(VC4_HD_M_CTL), > - VC4_REG32(VC4_HD_MAI_CTL), > - VC4_REG32(VC4_HD_MAI_THR), > - VC4_REG32(VC4_HD_MAI_FMT), > - VC4_REG32(VC4_HD_MAI_SMP), > - VC4_REG32(VC4_HD_VID_CTL), > - VC4_REG32(VC4_HD_CSC_CTL), > - VC4_REG32(VC4_HD_FRAME_COUNT), > -}; > - > static int vc4_hdmi_debugfs_regs(struct seq_file *m, void *unused) > { > struct drm_info_node *node = (struct drm_info_node *)m->private; > @@ -134,7 +85,7 @@ vc4_hdmi_connector_detect(struct drm_connector *connector, > bool force) > if (drm_probe_ddc(vc4_hdmi->ddc)) > return connector_status_connected; > > - if (HDMI_READ(VC4_HDMI_HOTPLUG) & VC4_HDMI_HOTPLUG_CONNECTED) > + if (HDMI_READ(HDMI_HOTPLUG) & VC4_HDMI_HOTPLUG_CONNECTED) > return connector_status_connected; > cec_phys_addr_invalidate(vc4_hdmi->cec_adap); > return connector_status_disconnected; > @@ -223,10 +174,10 @@ static int vc4_hdmi_stop_packet(struct drm_encoder > *encoder, > struct vc4_hdmi *vc4_hdmi = encoder_to_vc4_hdmi(encoder); > u32 packet_id = type - 0x80; > > - HDMI_WRITE(VC4_HDMI_RAM_PACKET_CONFIG, > - HDMI_READ(VC4_HDMI_RAM_PACKET_CONFIG) & ~BIT(packet_id)); > + HDMI_WRITE(HDMI_RAM_PACKET_CONFIG, > + HDMI_READ(HDMI_RAM_PACKET_CONFIG) & ~BIT(packet_id)); > > - return wait_for(!(HDMI_READ(VC4_HDMI_RAM_PACKET_STATUS) & > + return wait_for(!(HDMI_READ(HDMI_RAM_PACKET_STATUS) & > BIT(packet_id)), 100); > } > > @@ -235,12 +186,16 @@ static void vc4_hdmi_write_infoframe(struct drm_encoder > *encoder, > { > struct vc4_hdmi *vc4_hdmi = encoder_to_vc4_hdmi(encoder); > u32 packet_id = frame->any.type - 0x80; > - u32 packet_reg = VC4_HDMI_RAM_PACKET(packet_id); > + const struct vc4_hdmi_register *ram_packet_start = > + &vc4_
Re: [PATCH v4 52/78] drm/vc4: hdmi: Add reset callback
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > The BCM2711 and BCM283x HDMI controllers use a slightly different reset > sequence, so let's add a callback to reset the controller. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 31 ++- > drivers/gpu/drm/vc4/vc4_hdmi.h | 3 +++ > 2 files changed, 21 insertions(+), 13 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index a4fed1439bf3..80bc3dd9d4a8 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -69,6 +69,21 @@ static int vc4_hdmi_debugfs_regs(struct seq_file *m, void > *unused) > return 0; > } > > +static void vc4_hdmi_reset(struct vc4_hdmi *vc4_hdmi) > +{ > + HDMI_WRITE(HDMI_M_CTL, VC4_HD_M_SW_RST); > + udelay(1); > + HDMI_WRITE(HDMI_M_CTL, 0); > + > + HDMI_WRITE(HDMI_M_CTL, VC4_HD_M_ENABLE); > + > + HDMI_WRITE(HDMI_SW_RESET_CONTROL, > + VC4_HDMI_SW_RESET_HDMI | > + VC4_HDMI_SW_RESET_FORMAT_DETECT); > + > + HDMI_WRITE(HDMI_SW_RESET_CONTROL, 0); > +} > + > static enum drm_connector_status > vc4_hdmi_connector_detect(struct drm_connector *connector, bool force) > { > @@ -363,11 +378,8 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > return; > } > > - HDMI_WRITE(HDMI_SW_RESET_CONTROL, > - VC4_HDMI_SW_RESET_HDMI | > - VC4_HDMI_SW_RESET_FORMAT_DETECT); > - > - HDMI_WRITE(HDMI_SW_RESET_CONTROL, 0); > + if (vc4_hdmi->variant->reset) > + vc4_hdmi->variant->reset(vc4_hdmi); > > /* PHY should be in reset, like > * vc4_hdmi_encoder_disable() does. > @@ -1292,14 +1304,6 @@ static int vc4_hdmi_bind(struct device *dev, struct > device *master, void *data) > vc4_hdmi->hpd_active_low = hpd_gpio_flags & > OF_GPIO_ACTIVE_LOW; > } > > - /* HDMI core must be enabled. */ > - if (!(HDMI_READ(HDMI_M_CTL) & VC4_HD_M_ENABLE)) { > - HDMI_WRITE(HDMI_M_CTL, VC4_HD_M_SW_RST); > - udelay(1); > - HDMI_WRITE(HDMI_M_CTL, 0); > - > - HDMI_WRITE(HDMI_M_CTL, VC4_HD_M_ENABLE); > - } > pm_runtime_enable(dev); > > drm_simple_encoder_init(drm, encoder, DRM_MODE_ENCODER_TMDS); > @@ -1428,6 +1432,7 @@ static const struct vc4_hdmi_variant bcm2835_variant = { > .num_registers = ARRAY_SIZE(vc4_hdmi_fields), > > .init_resources = vc4_hdmi_init_resources, > + .reset = vc4_hdmi_reset, > }; > > static const struct of_device_id vc4_hdmi_dt_match[] = { > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.h b/drivers/gpu/drm/vc4/vc4_hdmi.h > index b36e0210671f..17a30589f39c 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.h > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.h > @@ -35,6 +35,9 @@ struct vc4_hdmi_variant { > * clocks, etc) for that variant. > */ > int (*init_resources)(struct vc4_hdmi *vc4_hdmi); > + > + /* Callback to reset the HDMI block */ > + void (*reset)(struct vc4_hdmi *vc4_hdmi); > }; > > /* HDMI audio information */ > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 53/78] drm/vc4: hdmi: Add PHY init and disable function
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > The HDMI PHY in the BCM2711 HDMI controller is significantly more > complicated to setup than in the older BCM283x SoCs. > > Let's add hooks to enable and disable the PHY. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/Makefile | 1 + > drivers/gpu/drm/vc4/vc4_hdmi.c | 14 +++--- > drivers/gpu/drm/vc4/vc4_hdmi.h | 13 + > drivers/gpu/drm/vc4/vc4_hdmi_phy.c | 25 + > 4 files changed, 46 insertions(+), 7 deletions(-) > create mode 100644 drivers/gpu/drm/vc4/vc4_hdmi_phy.c > > diff --git a/drivers/gpu/drm/vc4/Makefile b/drivers/gpu/drm/vc4/Makefile > index b303703bc7f3..d0163e18e9ca 100644 > --- a/drivers/gpu/drm/vc4/Makefile > +++ b/drivers/gpu/drm/vc4/Makefile > @@ -12,6 +12,7 @@ vc4-y := \ > vc4_kms.o \ > vc4_gem.o \ > vc4_hdmi.o \ > + vc4_hdmi_phy.o \ > vc4_vec.o \ > vc4_hvs.o \ > vc4_irq.o \ > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index 80bc3dd9d4a8..068041145d1c 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -321,7 +321,9 @@ static void vc4_hdmi_encoder_disable(struct drm_encoder > *encoder) > > HDMI_WRITE(HDMI_RAM_PACKET_CONFIG, 0); > > - HDMI_WRITE(HDMI_TX_PHY_RESET_CTL, 0xf << 16); > + if (vc4_hdmi->variant->phy_disable) > + vc4_hdmi->variant->phy_disable(vc4_hdmi); > + > HDMI_WRITE(HDMI_VID_CTL, >HDMI_READ(HDMI_VID_CTL) & ~VC4_HD_VID_CTL_ENABLE); > > @@ -381,12 +383,8 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > if (vc4_hdmi->variant->reset) > vc4_hdmi->variant->reset(vc4_hdmi); > > - /* PHY should be in reset, like > -* vc4_hdmi_encoder_disable() does. > -*/ > - HDMI_WRITE(HDMI_TX_PHY_RESET_CTL, 0xf << 16); > - > - HDMI_WRITE(HDMI_TX_PHY_RESET_CTL, 0); > + if (vc4_hdmi->variant->phy_init) > + vc4_hdmi->variant->phy_init(vc4_hdmi, mode); > > if (debug_dump_regs) { > struct drm_printer p = drm_info_printer(&vc4_hdmi->pdev->dev); > @@ -1433,6 +1431,8 @@ static const struct vc4_hdmi_variant bcm2835_variant = { > > .init_resources = vc4_hdmi_init_resources, > .reset = vc4_hdmi_reset, > + .phy_init = vc4_hdmi_phy_init, > + .phy_disable= vc4_hdmi_phy_disable, > }; > > static const struct of_device_id vc4_hdmi_dt_match[] = { > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.h b/drivers/gpu/drm/vc4/vc4_hdmi.h > index 17a30589f39c..32c80161c786 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.h > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.h > @@ -21,6 +21,8 @@ to_vc4_hdmi_encoder(struct drm_encoder *encoder) > return container_of(encoder, struct vc4_hdmi_encoder, base.base); > } > > +struct drm_display_mode; > + > struct vc4_hdmi; > struct vc4_hdmi_register; > > @@ -38,6 +40,13 @@ struct vc4_hdmi_variant { > > /* Callback to reset the HDMI block */ > void (*reset)(struct vc4_hdmi *vc4_hdmi); > + > + /* Callback to initialize the PHY according to the mode */ > + void (*phy_init)(struct vc4_hdmi *vc4_hdmi, > +struct drm_display_mode *mode); > + > + /* Callback to disable the PHY */ > + void (*phy_disable)(struct vc4_hdmi *vc4_hdmi); > }; > > /* HDMI audio information */ > @@ -95,4 +104,8 @@ encoder_to_vc4_hdmi(struct drm_encoder *encoder) > return container_of(_encoder, struct vc4_hdmi, encoder); > } > > +void vc4_hdmi_phy_init(struct vc4_hdmi *vc4_hdmi, > + struct drm_display_mode *mode); > +void vc4_hdmi_phy_disable(struct vc4_hdmi *vc4_hdmi); > + > #endif /* _VC4_HDMI_H_ */ > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi_phy.c > b/drivers/gpu/drm/vc4/vc4_hdmi_phy.c > new file mode 100644 > index ..5a1746877bb5 > --- /dev/null > +++ b/drivers/gpu/drm/vc4/vc4_hdmi_phy.c > @@ -0,0 +1,25 @@ > +// SPDX-License-Identifier: GPL-2.0 > +/* > + * Copyright (C) 2015 Broadcom > + * Copyright (c) 2014 The Linux Foundation. All rights reserved. > + * Copyright (C) 2013 Red Hat > + * Author: Rob Clark > + */ > + > +#include "vc4_hdmi.h" > +#include "vc4_hdmi_regs.h" > + > +void vc4_hdmi_phy_init(struct vc4_hdmi *vc4_hdmi, struct drm_display_mode > *mode) > +{ > + /* PHY should be in reset, like > +* vc4_hdmi_encoder_disable() does. > +*/ > + > + HDMI_WRITE(HDMI_TX_PHY_RESET_CTL, 0xf << 16); > + HDMI_WRITE(HDMI_TX_PHY_RESET_CTL, 0); > +} > + > +void vc4_hdmi_phy_disable(struct vc4_hdmi *vc4_hdmi) > +{ > + HDMI_WRITE(HDMI_TX_PHY_RESET_CTL, 0xf << 16); > +} > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/ma
Re: [PATCH v4 54/78] drm/vc4: hdmi: Add PHY RNG enable / disable function
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > Let's continue the implementation of hooks for the parts that change in the > BCM2711 SoC with the PHY RNG setup. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 15 +-- > drivers/gpu/drm/vc4/vc4_hdmi.h | 8 > drivers/gpu/drm/vc4/vc4_hdmi_phy.c | 15 +++ > 3 files changed, 32 insertions(+), 6 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index 068041145d1c..19897d6525ac 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -762,9 +762,9 @@ static int vc4_hdmi_audio_trigger(struct > snd_pcm_substream *substream, int cmd, > switch (cmd) { > case SNDRV_PCM_TRIGGER_START: > vc4_hdmi_set_audio_infoframe(encoder); > - HDMI_WRITE(HDMI_TX_PHY_CTL_0, > - HDMI_READ(HDMI_TX_PHY_CTL_0) & > - ~VC4_HDMI_TX_PHY_RNG_PWRDN); > + > + if (vc4_hdmi->variant->phy_rng_enable) > + vc4_hdmi->variant->phy_rng_enable(vc4_hdmi); > > HDMI_WRITE(HDMI_MAI_CTL, >VC4_SET_FIELD(vc4_hdmi->audio.channels, > @@ -776,9 +776,10 @@ static int vc4_hdmi_audio_trigger(struct > snd_pcm_substream *substream, int cmd, >VC4_HD_MAI_CTL_DLATE | >VC4_HD_MAI_CTL_ERRORE | >VC4_HD_MAI_CTL_ERRORF); > - HDMI_WRITE(HDMI_TX_PHY_CTL_0, > - HDMI_READ(HDMI_TX_PHY_CTL_0) | > - VC4_HDMI_TX_PHY_RNG_PWRDN); > + > + if (vc4_hdmi->variant->phy_rng_disable) > + vc4_hdmi->variant->phy_rng_disable(vc4_hdmi); > + > break; > default: > break; > @@ -1433,6 +1434,8 @@ static const struct vc4_hdmi_variant bcm2835_variant = { > .reset = vc4_hdmi_reset, > .phy_init = vc4_hdmi_phy_init, > .phy_disable= vc4_hdmi_phy_disable, > + .phy_rng_enable = vc4_hdmi_phy_rng_enable, > + .phy_rng_disable= vc4_hdmi_phy_rng_disable, > }; > > static const struct of_device_id vc4_hdmi_dt_match[] = { > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.h b/drivers/gpu/drm/vc4/vc4_hdmi.h > index 32c80161c786..950accbc44e4 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.h > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.h > @@ -47,6 +47,12 @@ struct vc4_hdmi_variant { > > /* Callback to disable the PHY */ > void (*phy_disable)(struct vc4_hdmi *vc4_hdmi); > + > + /* Callback to enable the RNG in the PHY */ > + void (*phy_rng_enable)(struct vc4_hdmi *vc4_hdmi); > + > + /* Callback to disable the RNG in the PHY */ > + void (*phy_rng_disable)(struct vc4_hdmi *vc4_hdmi); > }; > > /* HDMI audio information */ > @@ -107,5 +113,7 @@ encoder_to_vc4_hdmi(struct drm_encoder *encoder) > void vc4_hdmi_phy_init(struct vc4_hdmi *vc4_hdmi, >struct drm_display_mode *mode); > void vc4_hdmi_phy_disable(struct vc4_hdmi *vc4_hdmi); > +void vc4_hdmi_phy_rng_enable(struct vc4_hdmi *vc4_hdmi); > +void vc4_hdmi_phy_rng_disable(struct vc4_hdmi *vc4_hdmi); > > #endif /* _VC4_HDMI_H_ */ > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi_phy.c > b/drivers/gpu/drm/vc4/vc4_hdmi_phy.c > index 5a1746877bb5..93287e24d7d1 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi_phy.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi_phy.c > @@ -7,6 +7,7 @@ > */ > > #include "vc4_hdmi.h" > +#include "vc4_regs.h" > #include "vc4_hdmi_regs.h" > > void vc4_hdmi_phy_init(struct vc4_hdmi *vc4_hdmi, struct drm_display_mode > *mode) > @@ -23,3 +24,17 @@ void vc4_hdmi_phy_disable(struct vc4_hdmi *vc4_hdmi) > { > HDMI_WRITE(HDMI_TX_PHY_RESET_CTL, 0xf << 16); > } > + > +void vc4_hdmi_phy_rng_enable(struct vc4_hdmi *vc4_hdmi) > +{ > + HDMI_WRITE(HDMI_TX_PHY_CTL_0, > + HDMI_READ(HDMI_TX_PHY_CTL_0) & > + ~VC4_HDMI_TX_PHY_RNG_PWRDN); > +} > + > +void vc4_hdmi_phy_rng_disable(struct vc4_hdmi *vc4_hdmi) > +{ > + HDMI_WRITE(HDMI_TX_PHY_CTL_0, > + HDMI_READ(HDMI_TX_PHY_CTL_0) | > + VC4_HDMI_TX_PHY_RNG_PWRDN); > +} > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 55/78] drm/vc4: hdmi: Add a CSC setup callback
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > Similarly to the previous patches, the CSC setup is slightly different in > the BCM2711 than in the previous generations. Let's add a callback for it. We've gained the set_timings callback in this patch as well as csc_setup. Was that an accidental squash as we had them as independent commits in v1. Dave > Signed-off-by: Maxime Ripard > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 142 +++--- > drivers/gpu/drm/vc4/vc4_hdmi.h | 7 ++- > 2 files changed, 89 insertions(+), 60 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index 19897d6525ac..a50220bfd5dd 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -334,12 +334,44 @@ static void vc4_hdmi_encoder_disable(struct drm_encoder > *encoder) > DRM_ERROR("Failed to release power domain: %d\n", ret); > } > > -static void vc4_hdmi_encoder_enable(struct drm_encoder *encoder) > +static void vc4_hdmi_csc_setup(struct vc4_hdmi *vc4_hdmi, bool enable) > +{ > + u32 csc_ctl; > + > + csc_ctl = VC4_SET_FIELD(VC4_HD_CSC_CTL_ORDER_BGR, > + VC4_HD_CSC_CTL_ORDER); > + > + if (enable) { > + /* CEA VICs other than #1 requre limited range RGB > +* output unless overridden by an AVI infoframe. > +* Apply a colorspace conversion to squash 0-255 down > +* to 16-235. The matrix here is: > +* > +* [ 0 0 0.8594 16] > +* [ 0 0.8594 0 16] > +* [ 0.8594 0 0 16] > +* [ 0 0 0 1] > +*/ > + csc_ctl |= VC4_HD_CSC_CTL_ENABLE; > + csc_ctl |= VC4_HD_CSC_CTL_RGB2YCC; > + csc_ctl |= VC4_SET_FIELD(VC4_HD_CSC_CTL_MODE_CUSTOM, > +VC4_HD_CSC_CTL_MODE); > + > + HDMI_WRITE(HDMI_CSC_12_11, (0x000 << 16) | 0x000); > + HDMI_WRITE(HDMI_CSC_14_13, (0x100 << 16) | 0x6e0); > + HDMI_WRITE(HDMI_CSC_22_21, (0x6e0 << 16) | 0x000); > + HDMI_WRITE(HDMI_CSC_24_23, (0x100 << 16) | 0x000); > + HDMI_WRITE(HDMI_CSC_32_31, (0x000 << 16) | 0x6e0); > + HDMI_WRITE(HDMI_CSC_34_33, (0x100 << 16) | 0x000); > + } > + > + /* The RGB order applies even when CSC is disabled. */ > + HDMI_WRITE(HDMI_CSC_CTL, csc_ctl); > +} > + > +static void vc4_hdmi_set_timings(struct vc4_hdmi *vc4_hdmi, > +struct drm_display_mode *mode) > { > - struct drm_display_mode *mode = &encoder->crtc->state->adjusted_mode; > - struct vc4_hdmi *vc4_hdmi = encoder_to_vc4_hdmi(encoder); > - struct vc4_hdmi_encoder *vc4_encoder = &vc4_hdmi->encoder; > - bool debug_dump_regs = false; > bool hsync_pos = mode->flags & DRM_MODE_FLAG_PHSYNC; > bool vsync_pos = mode->flags & DRM_MODE_FLAG_PVSYNC; > bool interlaced = mode->flags & DRM_MODE_FLAG_INTERLACE; > @@ -357,7 +389,41 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > mode->crtc_vsync_end - > interlaced, > VC4_HDMI_VERTB_VBP)); > - u32 csc_ctl; > + > + HDMI_WRITE(HDMI_HORZA, > + (vsync_pos ? VC4_HDMI_HORZA_VPOS : 0) | > + (hsync_pos ? VC4_HDMI_HORZA_HPOS : 0) | > + VC4_SET_FIELD(mode->hdisplay * pixel_rep, > +VC4_HDMI_HORZA_HAP)); > + > + HDMI_WRITE(HDMI_HORZB, > + VC4_SET_FIELD((mode->htotal - > + mode->hsync_end) * pixel_rep, > +VC4_HDMI_HORZB_HBP) | > + VC4_SET_FIELD((mode->hsync_end - > + mode->hsync_start) * pixel_rep, > +VC4_HDMI_HORZB_HSP) | > + VC4_SET_FIELD((mode->hsync_start - > + mode->hdisplay) * pixel_rep, > +VC4_HDMI_HORZB_HFP)); > + > + HDMI_WRITE(HDMI_VERTA0, verta); > + HDMI_WRITE(HDMI_VERTA1, verta); > + > + HDMI_WRITE(HDMI_VERTB0, vertb_even); > + HDMI_WRITE(HDMI_VERTB1, vertb); > + > + HDMI_WRITE(HDMI_VID_CTL, > + (vsync_pos ? 0 : VC4_HD_VID_CTL_VSYNC_LOW) | > + (hsync_pos ? 0 : VC4_HD_VID_CTL_HSYNC_LOW)); > +} > + > +static void vc4_hdmi_encoder_enable(struct drm_encoder *encoder) > +{ > + struct drm_display_mode *mode = &encoder->crtc->state->adjusted_mode; > + struct vc4_hdmi *vc4_hdmi = encoder_to_vc4_hdmi(encoder); > + struct vc4_hdmi_encoder *vc4_encoder = to_vc4_hdmi_encoder(encoder); > + bool debug_dump_regs = false;
Re: [PATCH v4 56/78] drm/vc4: hdmi: Store the encoder type in the variant structure
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > The vc4 CRTC will use the encoder type to control its output clock > muxing. However, this will be different from HDMI0 to HDMI1, so let's > store our type in the variant structure so that we can support multiple > controllers later on. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 3 ++- > drivers/gpu/drm/vc4/vc4_hdmi.h | 3 +++ > 2 files changed, 5 insertions(+), 1 deletion(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index a50220bfd5dd..c50241170d7e 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -1268,7 +1268,7 @@ static int vc4_hdmi_bind(struct device *dev, struct > device *master, void *data) > > dev_set_drvdata(dev, vc4_hdmi); > encoder = &vc4_hdmi->encoder.base.base; > - vc4_hdmi->encoder.base.type = VC4_ENCODER_TYPE_HDMI0; > + vc4_hdmi->encoder.base.type = variant->encoder_type; > vc4_hdmi->pdev = pdev; > vc4_hdmi->variant = variant; > > @@ -1447,6 +1447,7 @@ static int vc4_hdmi_dev_remove(struct platform_device > *pdev) > } > > static const struct vc4_hdmi_variant bcm2835_variant = { > + .encoder_type = VC4_ENCODER_TYPE_HDMI0, > .registers = vc4_hdmi_fields, > .num_registers = ARRAY_SIZE(vc4_hdmi_fields), > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.h b/drivers/gpu/drm/vc4/vc4_hdmi.h > index 0c32dc46d289..0d529db4b3ab 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.h > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.h > @@ -27,6 +27,9 @@ struct vc4_hdmi; > struct vc4_hdmi_register; > > struct vc4_hdmi_variant { > + /* Encoder Type for that controller */ > + enum vc4_encoder_type encoder_type; > + > /* List of the registers available on that variant */ > const struct vc4_hdmi_register *registers; > > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 57/78] drm/vc4: hdmi: Deal with multiple debugfs files
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > The HDMI driver was registering a single debugfs file so far with the name > hdmi_regs. > > Obviously, this is not going to work anymore when will have multiple HDMI > controllers since we will end up trying to register two files with the same > name. > > Let's use the variant to avoid that name conflict. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 5 - > drivers/gpu/drm/vc4/vc4_hdmi.h | 3 +++ > 2 files changed, 7 insertions(+), 1 deletion(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index c50241170d7e..ef51eedaf75a 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -1370,7 +1370,9 @@ static int vc4_hdmi_bind(struct device *dev, struct > device *master, void *data) > if (ret) > goto err_destroy_encoder; > > - vc4_debugfs_add_file(drm, "hdmi_regs", vc4_hdmi_debugfs_regs, > vc4_hdmi); > + vc4_debugfs_add_file(drm, variant->debugfs_name, > +vc4_hdmi_debugfs_regs, > +vc4_hdmi); > > return 0; > > @@ -1448,6 +1450,7 @@ static int vc4_hdmi_dev_remove(struct platform_device > *pdev) > > static const struct vc4_hdmi_variant bcm2835_variant = { > .encoder_type = VC4_ENCODER_TYPE_HDMI0, > + .debugfs_name = "hdmi_regs", > .registers = vc4_hdmi_fields, > .num_registers = ARRAY_SIZE(vc4_hdmi_fields), > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.h b/drivers/gpu/drm/vc4/vc4_hdmi.h > index 0d529db4b3ab..794216f3228d 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.h > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.h > @@ -30,6 +30,9 @@ struct vc4_hdmi_variant { > /* Encoder Type for that controller */ > enum vc4_encoder_type encoder_type; > > + /* Filename to expose the registers in debugfs */ > + const char *debugfs_name; > + > /* List of the registers available on that variant */ > const struct vc4_hdmi_register *registers; > > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 58/78] drm/vc4: hdmi: Move CEC init to its own function
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > The CEC init code was put directly into the bind function, which was quite > inconsistent with how the audio support was done, and would prevent us from > further changes to skip that initialisation entirely. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 108 +- > 1 file changed, 67 insertions(+), 41 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index ef51eedaf75a..8cd08b541c14 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -1171,6 +1171,67 @@ static const struct cec_adap_ops vc4_hdmi_cec_adap_ops > = { > .adap_log_addr = vc4_hdmi_cec_adap_log_addr, > .adap_transmit = vc4_hdmi_cec_adap_transmit, > }; > + > +static int vc4_hdmi_cec_init(struct vc4_hdmi *vc4_hdmi) > +{ > + struct cec_connector_info conn_info; > + struct platform_device *pdev = vc4_hdmi->pdev; > + u32 value; > + int ret; > + > + vc4_hdmi->cec_adap = cec_allocate_adapter(&vc4_hdmi_cec_adap_ops, > + vc4_hdmi, "vc4", > + CEC_CAP_DEFAULTS | > + CEC_CAP_CONNECTOR_INFO, 1); > + ret = PTR_ERR_OR_ZERO(vc4_hdmi->cec_adap); > + if (ret < 0) > + return ret; > + > + cec_fill_conn_info_from_drm(&conn_info, &vc4_hdmi->connector); > + cec_s_conn_info(vc4_hdmi->cec_adap, &conn_info); > + > + HDMI_WRITE(HDMI_CEC_CPU_MASK_SET, 0x); > + value = HDMI_READ(HDMI_CEC_CNTRL_1); > + value &= ~VC4_HDMI_CEC_DIV_CLK_CNT_MASK; > + /* > +* Set the logical address to Unregistered and set the clock > +* divider: the hsm_clock rate and this divider setting will > +* give a 40 kHz CEC clock. > +*/ > + value |= VC4_HDMI_CEC_ADDR_MASK | > +(4091 << VC4_HDMI_CEC_DIV_CLK_CNT_SHIFT); > + HDMI_WRITE(HDMI_CEC_CNTRL_1, value); > + ret = devm_request_threaded_irq(&pdev->dev, platform_get_irq(pdev, 0), > + vc4_cec_irq_handler, > + vc4_cec_irq_handler_thread, 0, > + "vc4 hdmi cec", vc4_hdmi); > + if (ret) > + goto err_delete_cec_adap; > + > + ret = cec_register_adapter(vc4_hdmi->cec_adap, &pdev->dev); > + if (ret < 0) > + goto err_delete_cec_adap; > + > + return 0; > + > +err_delete_cec_adap: > + cec_delete_adapter(vc4_hdmi->cec_adap); > + > + return ret; > +} > + > +static void vc4_hdmi_cec_exit(struct vc4_hdmi *vc4_hdmi) > +{ > + cec_unregister_adapter(vc4_hdmi->cec_adap); > +} > +#else > +static int vc4_hdmi_cec_init(struct vc4_hdmi *vc4_hdmi) > +{ > + return 0; > +} > + > +static void vc4_hdmi_cec_exit(struct vc4_hdmi *vc4_hdmi) {}; > + > #endif > > static int vc4_hdmi_build_regset(struct vc4_hdmi *vc4_hdmi, > @@ -1250,9 +1311,6 @@ static int vc4_hdmi_init_resources(struct vc4_hdmi > *vc4_hdmi) > > static int vc4_hdmi_bind(struct device *dev, struct device *master, void > *data) > { > -#ifdef CONFIG_DRM_VC4_HDMI_CEC > - struct cec_connector_info conn_info; > -#endif > const struct vc4_hdmi_variant *variant = > of_device_get_match_data(dev); > struct platform_device *pdev = to_platform_device(dev); > struct drm_device *drm = dev_get_drvdata(master); > @@ -1332,43 +1390,13 @@ static int vc4_hdmi_bind(struct device *dev, struct > device *master, void *data) > if (ret) > goto err_destroy_encoder; > > -#ifdef CONFIG_DRM_VC4_HDMI_CEC > - vc4_hdmi->cec_adap = cec_allocate_adapter(&vc4_hdmi_cec_adap_ops, > - vc4_hdmi, "vc4", > - CEC_CAP_DEFAULTS | > - CEC_CAP_CONNECTOR_INFO, 1); > - ret = PTR_ERR_OR_ZERO(vc4_hdmi->cec_adap); > - if (ret < 0) > - goto err_destroy_conn; > - > - cec_fill_conn_info_from_drm(&conn_info, &vc4_hdmi->connector); > - cec_s_conn_info(vc4_hdmi->cec_adap, &conn_info); > - > - HDMI_WRITE(HDMI_CEC_CPU_MASK_SET, 0x); > - value = HDMI_READ(HDMI_CEC_CNTRL_1); > - value &= ~VC4_HDMI_CEC_DIV_CLK_CNT_MASK; > - /* > -* Set the logical address to Unregistered and set the clock > -* divider: the hsm_clock rate and this divider setting will > -* give a 40 kHz CEC clock. > -*/ > - value |= VC4_HDMI_CEC_ADDR_MASK | > -(4091 << VC4_HDMI_CEC_DIV_CLK_CNT_SHIFT); > - HDMI_WRITE(HDMI_CEC_CNTRL_1, value); > - ret = devm_request_threaded_irq(dev, platform_get_irq(pdev, 0), > -
Re: [PATCH v4 59/78] drm/vc4: hdmi: Add CEC support flag
Hi Maxime On Wed, 8 Jul 2020 at 18:43, Maxime Ripard wrote: > > Similarly to the audio support, CEC support is not there yet for the > BCM2711, so let's skip entirely the CEC initialization through a variant > flag. CEC is sorted now, but it's easier & cleaner to keep this patch and add a new patchset that enables CEC at a later date. > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 4 > drivers/gpu/drm/vc4/vc4_hdmi.h | 3 +++ > 2 files changed, 7 insertions(+) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index 8cd08b541c14..86e21de6c578 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -1179,6 +1179,9 @@ static int vc4_hdmi_cec_init(struct vc4_hdmi *vc4_hdmi) > u32 value; > int ret; > > + if (!vc4_hdmi->variant->cec_available) > + return 0; > + > vc4_hdmi->cec_adap = cec_allocate_adapter(&vc4_hdmi_cec_adap_ops, > vc4_hdmi, "vc4", > CEC_CAP_DEFAULTS | > @@ -1477,6 +1480,7 @@ static int vc4_hdmi_dev_remove(struct platform_device > *pdev) > static const struct vc4_hdmi_variant bcm2835_variant = { > .encoder_type = VC4_ENCODER_TYPE_HDMI0, > .debugfs_name = "hdmi_regs", > + .cec_available = true, > .registers = vc4_hdmi_fields, > .num_registers = ARRAY_SIZE(vc4_hdmi_fields), > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.h b/drivers/gpu/drm/vc4/vc4_hdmi.h > index 794216f3228d..3f07aebe89f1 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.h > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.h > @@ -33,6 +33,9 @@ struct vc4_hdmi_variant { > /* Filename to expose the registers in debugfs */ > const char *debugfs_name; > > + /* Set to true when the CEC support is available */ > + bool cec_available; > + > /* List of the registers available on that variant */ > const struct vc4_hdmi_register *registers; > > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 60/78] drm/vc4: hdmi: Remove unused CEC_CLOCK_DIV define
Hi Maxime On Wed, 8 Jul 2020 at 18:44, Maxime Ripard wrote: > > The CEC_CLOCK_DIV define is not used anywhere in the driver, let's remove > it. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 1 - > 1 file changed, 1 deletion(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index 86e21de6c578..a01562a49bf0 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -55,7 +55,6 @@ > > #define HSM_CLOCK_FREQ 163682864 > #define CEC_CLOCK_FREQ 4 > -#define CEC_CLOCK_DIV (HSM_CLOCK_FREQ / CEC_CLOCK_FREQ) > > static int vc4_hdmi_debugfs_regs(struct seq_file *m, void *unused) > { > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH] dma-resv: lockdep-prime address_space->i_mmap_rwsem for dma-resv
GPU drivers need this in their shrinkers, to be able to throw out mmap'ed buffers. Note that we also need dma_resv_lock in shrinkers, but that loop is resolved by trylocking in shrinkers. So full hierarchy is now (ignore some of the other branches we already have primed): mmap_read_lock -> dma_resv -> shrinkers -> i_mmap_lock_write I hope that's not inconsistent with anything mm or fs does, adding relevant people. Signed-off-by: Daniel Vetter Cc: Sumit Semwal Cc: "Christian König" Cc: linux-me...@vger.kernel.org Cc: linaro-mm-...@lists.linaro.org Cc: Dave Chinner Cc: Qian Cai Cc: linux-...@vger.kernel.org Cc: linux-fsde...@vger.kernel.org Cc: Thomas Hellström (Intel) Cc: Andrew Morton Cc: Jason Gunthorpe Cc: linux...@kvack.org Cc: linux-r...@vger.kernel.org Cc: Maarten Lankhorst --- drivers/dma-buf/dma-resv.c | 5 + 1 file changed, 5 insertions(+) diff --git a/drivers/dma-buf/dma-resv.c b/drivers/dma-buf/dma-resv.c index 0e6675ec1d11..9678162a4ac5 100644 --- a/drivers/dma-buf/dma-resv.c +++ b/drivers/dma-buf/dma-resv.c @@ -104,12 +104,14 @@ static int __init dma_resv_lockdep(void) struct mm_struct *mm = mm_alloc(); struct ww_acquire_ctx ctx; struct dma_resv obj; + struct address_space mapping; int ret; if (!mm) return -ENOMEM; dma_resv_init(&obj); + address_space_init_once(&mapping); mmap_read_lock(mm); ww_acquire_init(&ctx, &reservation_ww_class); @@ -117,6 +119,9 @@ static int __init dma_resv_lockdep(void) if (ret == -EDEADLK) dma_resv_lock_slow(&obj, &ctx); fs_reclaim_acquire(GFP_KERNEL); + /* for unmap_mapping_range on trylocked buffer objects in shrinkers */ + i_mmap_lock_write(&mapping); + i_mmap_unlock_write(&mapping); #ifdef CONFIG_MMU_NOTIFIER lock_map_acquire(&__mmu_notifier_invalidate_range_start_map); __dma_fence_might_wait(); -- 2.27.0 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 61/78] drm/vc4: hdmi: Rename drm_encoder pointer in mode_valid
Hi Maxime On Wed, 8 Jul 2020 at 18:44, Maxime Ripard wrote: > > The mode_valid hook on the encoder uses a pointer to a drm_encoder called > crtc, which is pretty confusing. Let's rename it to encoder to make it > clear what it is. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 2 +- > 1 file changed, 1 insertion(+), 1 deletion(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index a01562a49bf0..17797b14cde4 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -556,7 +556,7 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > } > > static enum drm_mode_status > -vc4_hdmi_encoder_mode_valid(struct drm_encoder *crtc, > +vc4_hdmi_encoder_mode_valid(struct drm_encoder *encoder, > const struct drm_display_mode *mode) > { > /* > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 62/78] drm/vc4: hdmi: Adjust HSM clock rate depending on pixel rate
Hi Maxime On Wed, 8 Jul 2020 at 18:44, Maxime Ripard wrote: > > The HSM clock needs to be setup at around 101% of the pixel rate. This > was done previously by setting the clock rate to 163.7MHz at probe time and > only check in mode_valid whether the mode pixel clock was under the pixel > clock +1% or not. > > However, with 4k we need to change that frequency to a higher frequency > than 163.7MHz, and yet want to have the lowest clock as possible to have a > decent power saving. > > Let's change that logic a bit by setting the clock rate of the HSM clock > to the pixel rate at encoder_enable time. This would work for the > BCM2711 that support 4k resolutions and has a clock that can provide it, > but we still have to take care of a 4k panel plugged on a BCM283x SoCs > that wouldn't be able to use those modes, so let's define the limit in > the variant. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 79 --- > drivers/gpu/drm/vc4/vc4_hdmi.h | 3 +- > 2 files changed, 41 insertions(+), 41 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index 17797b14cde4..9f30fab744f2 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -53,7 +53,6 @@ > #include "vc4_hdmi_regs.h" > #include "vc4_regs.h" > > -#define HSM_CLOCK_FREQ 163682864 > #define CEC_CLOCK_FREQ 4 > > static int vc4_hdmi_debugfs_regs(struct seq_file *m, void *unused) > @@ -326,6 +325,7 @@ static void vc4_hdmi_encoder_disable(struct drm_encoder > *encoder) > HDMI_WRITE(HDMI_VID_CTL, >HDMI_READ(HDMI_VID_CTL) & ~VC4_HD_VID_CTL_ENABLE); > > + clk_disable_unprepare(vc4_hdmi->hsm_clock); > clk_disable_unprepare(vc4_hdmi->pixel_clock); > > ret = pm_runtime_put(&vc4_hdmi->pdev->dev); > @@ -423,6 +423,7 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > struct vc4_hdmi *vc4_hdmi = encoder_to_vc4_hdmi(encoder); > struct vc4_hdmi_encoder *vc4_encoder = to_vc4_hdmi_encoder(encoder); > bool debug_dump_regs = false; > + unsigned long pixel_rate, hsm_rate; > int ret; > > ret = pm_runtime_get_sync(&vc4_hdmi->pdev->dev); > @@ -431,9 +432,8 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > return; > } > > - ret = clk_set_rate(vc4_hdmi->pixel_clock, > - mode->clock * 1000 * > - ((mode->flags & DRM_MODE_FLAG_DBLCLK) ? 2 : 1)); > + pixel_rate = mode->clock * 1000 * ((mode->flags & > DRM_MODE_FLAG_DBLCLK) ? 2 : 1); > + ret = clk_set_rate(vc4_hdmi->pixel_clock, pixel_rate); > if (ret) { > DRM_ERROR("Failed to set pixel clock rate: %d\n", ret); > return; > @@ -445,6 +445,36 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > return; > } > > + /* > +* As stated in RPi's vc4 firmware "HDMI state machine (HSM) clock > must > +* be faster than pixel clock, infinitesimally faster, tested in > +* simulation. Otherwise, exact value is unimportant for HDMI > +* operation." This conflicts with bcm2835's vc4 documentation, which > +* states HSM's clock has to be at least 108% of the pixel clock. > +* > +* Real life tests reveal that vc4's firmware statement holds up, and > +* users are able to use pixel clocks closer to HSM's, namely for > +* 1920x1200@60Hz. So it was decided to have leave a 1% margin between > +* both clocks. Which, for RPi0-3 implies a maximum pixel clock of > +* 162MHz. > +* > +* Additionally, the AXI clock needs to be at least 25% of > +* pixel clock, but HSM ends up being the limiting factor. > +*/ > + hsm_rate = max_t(unsigned long, 12000, (pixel_rate / 100) * 101); > + ret = clk_set_rate(vc4_hdmi->hsm_clock, hsm_rate); > + if (ret) { > + DRM_ERROR("Failed to set HSM clock rate: %d\n", ret); > + return; > + } > + > + ret = clk_prepare_enable(vc4_hdmi->hsm_clock); > + if (ret) { > + DRM_ERROR("Failed to turn on HSM clock: %d\n", ret); > + clk_disable_unprepare(vc4_hdmi->pixel_clock); > + return; > + } > + > if (vc4_hdmi->variant->reset) > vc4_hdmi->variant->reset(vc4_hdmi); > > @@ -559,23 +589,9 @@ static enum drm_mode_status > vc4_hdmi_encoder_mode_valid(struct drm_encoder *encoder, > const struct drm_display_mode *mode) > { > - /* > -* As stated in RPi's vc4 firmware "HDMI state machine (HSM) clock > must > -* be faster than pixel clock, infinitesimally faster, tested in > -* simulation. Otherwise, exact value is unimportant for HDMI > -
Re: [PATCH v4 63/78] drm/vc4: hdmi: Use clk_set_min_rate instead
Hi Maxime On Wed, 8 Jul 2020 at 18:44, Maxime Ripard wrote: > > The HSM clock needs to be running at 101% the pixel clock of the HDMI > controller, however it's shared between the two HDMI controllers, which > means that if the resolutions are different between the two HDMI > controllers, and the lowest resolution is on the second (in enable order) > controller, the first HDMI controller will end up with a smaller than > expected clock rate. > > Since we don't really need an exact frequency there, we can simply change > the minimum rate we expect instead. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 2 +- > 1 file changed, 1 insertion(+), 1 deletion(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index 9f30fab744f2..d99188c90ff9 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -462,7 +462,7 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > * pixel clock, but HSM ends up being the limiting factor. > */ > hsm_rate = max_t(unsigned long, 12000, (pixel_rate / 100) * 101); > - ret = clk_set_rate(vc4_hdmi->hsm_clock, hsm_rate); > + ret = clk_set_min_rate(vc4_hdmi->hsm_clock, hsm_rate); > if (ret) { > DRM_ERROR("Failed to set HSM clock rate: %d\n", ret); > return; > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 68/78] drm/vc4: hdmi: Deal with multiple ALSA cards
Hi Maxime On Wed, 8 Jul 2020 at 18:44, Maxime Ripard wrote: > > The HDMI driver was registering a single ALSA card so far with the name > vc4-hdmi. > > Obviously, this is not going to work anymore when will have multiple HDMI s/will/we > controllers since we will end up trying to register two files with the same > name. > > Let's use the variant to avoid that name conflict. > > Signed-off-by: Maxime Ripard With that change Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 3 ++- > drivers/gpu/drm/vc4/vc4_hdmi.h | 3 +++ > 2 files changed, 5 insertions(+), 1 deletion(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index 1b6f51849d6c..0a9a323e03d8 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -1044,7 +1044,7 @@ static int vc4_hdmi_audio_init(struct vc4_hdmi > *vc4_hdmi) > > card->dai_link = dai_link; > card->num_links = 1; > - card->name = "vc4-hdmi"; > + card->name = vc4_hdmi->variant->card_name; > card->dev = dev; > > /* > @@ -1503,6 +1503,7 @@ static int vc4_hdmi_dev_remove(struct platform_device > *pdev) > static const struct vc4_hdmi_variant bcm2835_variant = { > .encoder_type = VC4_ENCODER_TYPE_HDMI0, > .debugfs_name = "hdmi_regs", > + .card_name = "vc4-hdmi", > .max_pixel_clock= 16200, > .cec_available = true, > .registers = vc4_hdmi_fields, > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.h b/drivers/gpu/drm/vc4/vc4_hdmi.h > index 4aea5ee8a91d..34138e0dd4a6 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.h > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.h > @@ -30,6 +30,9 @@ struct vc4_hdmi_variant { > /* Encoder Type for that controller */ > enum vc4_encoder_type encoder_type; > > + /* ALSA card name */ > + const char *card_name; > + > /* Filename to expose the registers in debugfs */ > const char *debugfs_name; > > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 69/78] drm/vc4: hdmi: Remove register dumps in enable
Hi Maxime On Wed, 8 Jul 2020 at 18:44, Maxime Ripard wrote: > > The current code has some logic, disabled by default, to dump the register > setup in the HDMI controller. > > However, since we're going to split those functions in multiple, shorter, > functions that only make sense where they are called in sequence, keeping > the register dump makes little sense. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 17 - > 1 file changed, 17 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index 0a9a323e03d8..4058985940e6 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -430,7 +430,6 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > struct drm_display_mode *mode = &encoder->crtc->state->adjusted_mode; > struct vc4_hdmi *vc4_hdmi = encoder_to_vc4_hdmi(encoder); > struct vc4_hdmi_encoder *vc4_encoder = to_vc4_hdmi_encoder(encoder); > - bool debug_dump_regs = false; > unsigned long pixel_rate, hsm_rate; > int ret; > > @@ -489,14 +488,6 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > if (vc4_hdmi->variant->phy_init) > vc4_hdmi->variant->phy_init(vc4_hdmi, mode); > > - if (debug_dump_regs) { > - struct drm_printer p = drm_info_printer(&vc4_hdmi->pdev->dev); > - > - dev_info(&vc4_hdmi->pdev->dev, "HDMI regs before:\n"); > - drm_print_regset32(&p, &vc4_hdmi->hdmi_regset); > - drm_print_regset32(&p, &vc4_hdmi->hd_regset); > - } > - > HDMI_WRITE(HDMI_VID_CTL, 0); > > HDMI_WRITE(HDMI_SCHEDULER_CONTROL, > @@ -522,14 +513,6 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > > HDMI_WRITE(HDMI_FIFO_CTL, VC4_HDMI_FIFO_CTL_MASTER_SLAVE_N); > > - if (debug_dump_regs) { > - struct drm_printer p = drm_info_printer(&vc4_hdmi->pdev->dev); > - > - dev_info(&vc4_hdmi->pdev->dev, "HDMI regs after:\n"); > - drm_print_regset32(&p, &vc4_hdmi->hdmi_regset); > - drm_print_regset32(&p, &vc4_hdmi->hd_regset); > - } > - > HDMI_WRITE(HDMI_VID_CTL, >HDMI_READ(HDMI_VID_CTL) | >VC4_HD_VID_CTL_ENABLE | > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 70/78] drm/vc4: hdmi: Always recenter the HDMI FIFO
Hi Maxime On Wed, 8 Jul 2020 at 18:44, Maxime Ripard wrote: > > In order to avoid a pixel getting stuck in an unflushable FIFO, we need to > recenter the FIFO every time we're doing a modeset and not only if we're > connected to an HDMI monitor. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 46 +++ > 1 file changed, 26 insertions(+), 20 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index 4058985940e6..00592c1ada73 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -425,6 +425,30 @@ static void vc4_hdmi_set_timings(struct vc4_hdmi > *vc4_hdmi, >(hsync_pos ? 0 : VC4_HD_VID_CTL_HSYNC_LOW)); > } > > +static void vc4_hdmi_recenter_fifo(struct vc4_hdmi *vc4_hdmi) > +{ > + u32 drift; > + int ret; > + > + drift = HDMI_READ(HDMI_FIFO_CTL); > + drift &= VC4_HDMI_FIFO_VALID_WRITE_MASK; > + > + HDMI_WRITE(HDMI_FIFO_CTL, > + drift & ~VC4_HDMI_FIFO_CTL_RECENTER); > + HDMI_WRITE(HDMI_FIFO_CTL, > + drift | VC4_HDMI_FIFO_CTL_RECENTER); > + usleep_range(1000, 1100); > + HDMI_WRITE(HDMI_FIFO_CTL, > + drift & ~VC4_HDMI_FIFO_CTL_RECENTER); > + HDMI_WRITE(HDMI_FIFO_CTL, > + drift | VC4_HDMI_FIFO_CTL_RECENTER); > + > + ret = wait_for(HDMI_READ(HDMI_FIFO_CTL) & > + VC4_HDMI_FIFO_CTL_RECENTER_DONE, 1); > + WARN_ONCE(ret, "Timeout waiting for " > + "VC4_HDMI_FIFO_CTL_RECENTER_DONE"); > +} > + > static void vc4_hdmi_encoder_enable(struct drm_encoder *encoder) > { > struct drm_display_mode *mode = &encoder->crtc->state->adjusted_mode; > @@ -543,8 +567,6 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > } > > if (vc4_encoder->hdmi_monitor) { > - u32 drift; > - > WARN_ON(!(HDMI_READ(HDMI_SCHEDULER_CONTROL) & > VC4_HDMI_SCHEDULER_CONTROL_HDMI_ACTIVE)); > HDMI_WRITE(HDMI_SCHEDULER_CONTROL, > @@ -555,25 +577,9 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) >VC4_HDMI_RAM_PACKET_ENABLE); > > vc4_hdmi_set_infoframes(encoder); > - > - drift = HDMI_READ(HDMI_FIFO_CTL); > - drift &= VC4_HDMI_FIFO_VALID_WRITE_MASK; > - > - HDMI_WRITE(HDMI_FIFO_CTL, > - drift & ~VC4_HDMI_FIFO_CTL_RECENTER); > - HDMI_WRITE(HDMI_FIFO_CTL, > - drift | VC4_HDMI_FIFO_CTL_RECENTER); > - usleep_range(1000, 1100); > - HDMI_WRITE(HDMI_FIFO_CTL, > - drift & ~VC4_HDMI_FIFO_CTL_RECENTER); > - HDMI_WRITE(HDMI_FIFO_CTL, > - drift | VC4_HDMI_FIFO_CTL_RECENTER); > - > - ret = wait_for(HDMI_READ(HDMI_FIFO_CTL) & > - VC4_HDMI_FIFO_CTL_RECENTER_DONE, 1); > - WARN_ONCE(ret, "Timeout waiting for " > - "VC4_HDMI_FIFO_CTL_RECENTER_DONE"); > } > + > + vc4_hdmi_recenter_fifo(vc4_hdmi); > } > > static enum drm_mode_status > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v9 0/4] driver core: add probe error check helper
Hi Greg, Apparently the patchset has no more comments. Could you take the patches to your tree? At least 1st and 2nd. Regards Andrzej On 13.07.2020 16:43, Andrzej Hajda wrote: > Hi All, > > Thanks for comments. > > Changes since v8: > - fixed typo in function name, > - removed cocci script (added by mistake) > > Changes since v7: > - improved commit message > - added R-Bs > > Changes since v6: > - removed leftovers from old naming scheme in commit descritions, > - added R-Bs. > > Changes since v5: > - removed patch adding macro, dev_err_probe(dev, PTR_ERR(ptr), ...) should be > used instead, > - added dev_dbg logging in case of -EPROBE_DEFER, > - renamed functions and vars according to comments, > - extended docs, > - cosmetics. > > Original message (with small adjustments): > > Recently I took some time to re-check error handling in drivers probe code, > and I have noticed that number of incorrect resource acquisition error > handling > increased and there are no other propositions which can cure the situation. > > So I have decided to resend my old proposition of probe_err helper which > should > simplify resource acquisition error handling, it also extend it with adding > defer > probe reason to devices_deferred debugfs property, which should improve > debugging > experience for developers/testers. > > I have also added two patches showing usage and benefits of the helper. > > My dirty/ad-hoc cocci scripts shows that this helper can be used in at least > 2700 places > saving about 3500 lines of code. > > Regards > Andrzej > > > Andrzej Hajda (4): >driver core: add device probe log helper >driver core: add deferring probe reason to devices_deferred property >drm/bridge/sii8620: fix resource acquisition error handling >drm/bridge: lvds-codec: simplify error handling > > drivers/base/base.h | 3 ++ > drivers/base/core.c | 46 > drivers/base/dd.c| 23 +- > drivers/gpu/drm/bridge/lvds-codec.c | 10 ++ > drivers/gpu/drm/bridge/sil-sii8620.c | 21 ++--- > include/linux/device.h | 3 ++ > 6 files changed, 86 insertions(+), 20 deletions(-) > ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 71/78] drm/vc4: hdmi: Implement finer-grained hooks
Hi Maxime On Wed, 8 Jul 2020 at 18:44, Maxime Ripard wrote: > > In order to prevent some pixels getting stuck in an unflushable FIFO on > bcm2711, we need to enable the HVS, the pixelvalve (the CRTC) and the HDMI > controller (the encoder) in an intertwined way, and with tight delays. > > However, the atomic callbacks don't really provide a way to work with > either constraints, so we need to roll our own callbacks so that we can > provide those guarantees. > > Since those callbacks have been implemented and called in the CRTC code, we > can just implement them in the HDMI driver now. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 39 +++ > 1 file changed, 35 insertions(+), 4 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index 00592c1ada73..bbe521ab000b 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -320,12 +320,17 @@ static void vc4_hdmi_set_infoframes(struct drm_encoder > *encoder) > vc4_hdmi_set_audio_infoframe(encoder); > } > > -static void vc4_hdmi_encoder_disable(struct drm_encoder *encoder) > +static void vc4_hdmi_encoder_post_crtc_disable(struct drm_encoder *encoder) > { > struct vc4_hdmi *vc4_hdmi = encoder_to_vc4_hdmi(encoder); > - int ret; > > HDMI_WRITE(HDMI_RAM_PACKET_CONFIG, 0); > +} > + > +static void vc4_hdmi_encoder_post_crtc_powerdown(struct drm_encoder *encoder) > +{ > + struct vc4_hdmi *vc4_hdmi = encoder_to_vc4_hdmi(encoder); > + int ret; > > if (vc4_hdmi->variant->phy_disable) > vc4_hdmi->variant->phy_disable(vc4_hdmi); > @@ -341,6 +346,10 @@ static void vc4_hdmi_encoder_disable(struct drm_encoder > *encoder) > DRM_ERROR("Failed to release power domain: %d\n", ret); > } > > +static void vc4_hdmi_encoder_disable(struct drm_encoder *encoder) > +{ > +} > + > static void vc4_hdmi_csc_setup(struct vc4_hdmi *vc4_hdmi, bool enable) > { > u32 csc_ctl; > @@ -449,11 +458,10 @@ static void vc4_hdmi_recenter_fifo(struct vc4_hdmi > *vc4_hdmi) > "VC4_HDMI_FIFO_CTL_RECENTER_DONE"); > } > > -static void vc4_hdmi_encoder_enable(struct drm_encoder *encoder) > +static void vc4_hdmi_encoder_pre_crtc_configure(struct drm_encoder *encoder) > { > struct drm_display_mode *mode = &encoder->crtc->state->adjusted_mode; > struct vc4_hdmi *vc4_hdmi = encoder_to_vc4_hdmi(encoder); > - struct vc4_hdmi_encoder *vc4_encoder = to_vc4_hdmi_encoder(encoder); > unsigned long pixel_rate, hsm_rate; > int ret; > > @@ -521,6 +529,13 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > > if (vc4_hdmi->variant->set_timings) > vc4_hdmi->variant->set_timings(vc4_hdmi, mode); > +} > + > +static void vc4_hdmi_encoder_pre_crtc_enable(struct drm_encoder *encoder) > +{ > + struct drm_display_mode *mode = &encoder->crtc->state->adjusted_mode; > + struct vc4_hdmi_encoder *vc4_encoder = to_vc4_hdmi_encoder(encoder); > + struct vc4_hdmi *vc4_hdmi = encoder_to_vc4_hdmi(encoder); > > if (vc4_encoder->hdmi_monitor && > drm_default_rgb_quant_range(mode) == > HDMI_QUANTIZATION_RANGE_LIMITED) { > @@ -536,6 +551,13 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > } > > HDMI_WRITE(HDMI_FIFO_CTL, VC4_HDMI_FIFO_CTL_MASTER_SLAVE_N); > +} > + > +static void vc4_hdmi_encoder_post_crtc_enable(struct drm_encoder *encoder) > +{ > + struct vc4_hdmi *vc4_hdmi = encoder_to_vc4_hdmi(encoder); > + struct vc4_hdmi_encoder *vc4_encoder = to_vc4_hdmi_encoder(encoder); > + int ret; > > HDMI_WRITE(HDMI_VID_CTL, >HDMI_READ(HDMI_VID_CTL) | > @@ -582,6 +604,10 @@ static void vc4_hdmi_encoder_enable(struct drm_encoder > *encoder) > vc4_hdmi_recenter_fifo(vc4_hdmi); > } > > +static void vc4_hdmi_encoder_enable(struct drm_encoder *encoder) > +{ > +} > + > static enum drm_mode_status > vc4_hdmi_encoder_mode_valid(struct drm_encoder *encoder, > const struct drm_display_mode *mode) > @@ -1362,6 +1388,11 @@ static int vc4_hdmi_bind(struct device *dev, struct > device *master, void *data) > dev_set_drvdata(dev, vc4_hdmi); > encoder = &vc4_hdmi->encoder.base.base; > vc4_hdmi->encoder.base.type = variant->encoder_type; > + vc4_hdmi->encoder.base.pre_crtc_configure = > vc4_hdmi_encoder_pre_crtc_configure; > + vc4_hdmi->encoder.base.pre_crtc_enable = > vc4_hdmi_encoder_pre_crtc_enable; > + vc4_hdmi->encoder.base.post_crtc_enable = > vc4_hdmi_encoder_post_crtc_enable; > + vc4_hdmi->encoder.base.post_crtc_disable = > vc4_hdmi_encoder_post_crtc_disable; > + vc4_hdmi->encoder.base.post_crtc_powerdown = > vc4_hdmi_encoder_post_crtc_powerdown; > vc4_hdmi->pdev = pdev;
Re: [PATCH v9 08/12] device core: Introduce DMA range map, supplanting dma_pfn_offset
On Fri, Jul 24, 2020 at 2:45 PM Jim Quinlan wrote: > > The new field 'dma_range_map' in struct device is used to facilitate the > use of single or multiple offsets between mapping regions of cpu addrs and > dma addrs. It subsumes the role of "dev->dma_pfn_offset" which was only > capable of holding a single uniform offset and had no region bounds > checking. > > The function of_dma_get_range() has been modified so that it takes a single > argument -- the device node -- and returns a map, NULL, or an error code. > The map is an array that holds the information regarding the DMA regions. > Each range entry contains the address offset, the cpu_start address, the > dma_start address, and the size of the region. > > of_dma_configure() is the typical manner to set range offsets but there are > a number of ad hoc assignments to "dev->dma_pfn_offset" in the kernel > driver code. These cases now invoke the function > dma_attach_offset_range(dev, cpu_addr, dma_addr, size). > > Signed-off-by: Jim Quinlan > --- [...] > diff --git a/drivers/of/address.c b/drivers/of/address.c > index 8eea3f6e29a4..4b718d199efe 100644 > --- a/drivers/of/address.c > +++ b/drivers/of/address.c > @@ -918,33 +918,33 @@ void __iomem *of_io_request_and_map(struct device_node > *np, int index, > } > EXPORT_SYMBOL(of_io_request_and_map); > > +#ifdef CONFIG_HAS_DMA > /** > - * of_dma_get_range - Get DMA range info > + * of_dma_get_range - Get DMA range info and put it into a map array > * @np:device node to get DMA range info > - * @dma_addr: pointer to store initial DMA address of DMA range > - * @paddr: pointer to store initial CPU address of DMA range > - * @size: pointer to store size of DMA range > + * @map: dma range structure to return > * > * Look in bottom up direction for the first "dma-ranges" property > - * and parse it. > - * dma-ranges format: > + * and parse it. Put the information into a DMA offset map array. > + * > + * dma-ranges format: > * DMA addr (dma_addr) : naddr cells > * CPU addr (phys_addr_t) : pna cells > * size: nsize cells > * > - * It returns -ENODEV if "dma-ranges" property was not found > - * for this device in DT. > + * It returns -ENODEV if "dma-ranges" property was not found for this > + * device in the DT. > */ > -int of_dma_get_range(struct device_node *np, u64 *dma_addr, u64 *paddr, u64 > *size) > +int of_dma_get_range(struct device_node *np, const struct bus_dma_region > **map) > { > struct device_node *node = of_node_get(np); > const __be32 *ranges = NULL; > - int len; > - int ret = 0; > bool found_dma_ranges = false; > struct of_range_parser parser; > struct of_range range; > - u64 dma_start = U64_MAX, dma_end = 0, dma_offset = 0; > + struct bus_dma_region *r; > + int len, num_ranges = 0; > + int ret; > > while (node) { > ranges = of_get_property(node, "dma-ranges", &len); > @@ -970,44 +970,35 @@ int of_dma_get_range(struct device_node *np, u64 > *dma_addr, u64 *paddr, u64 *siz > } > > of_dma_range_parser_init(&parser, node); > + for_each_of_range(&parser, &range) > + num_ranges++; > + > + of_dma_range_parser_init(&parser, node); > + > + ret = -ENOMEM; > + r = kcalloc(num_ranges + 1, sizeof(*r), GFP_KERNEL); > + if (!r) > + goto out; AFAICT, you have the error cases covered, but you are leaking memory if the device is removed. [...] > diff --git a/drivers/remoteproc/remoteproc_core.c > b/drivers/remoteproc/remoteproc_core.c > index 9f04c30c4aaf..49242dd6176e 100644 > --- a/drivers/remoteproc/remoteproc_core.c > +++ b/drivers/remoteproc/remoteproc_core.c > @@ -519,7 +519,7 @@ static int rproc_handle_vdev(struct rproc *rproc, struct > fw_rsc_vdev *rsc, > /* Initialise vdev subdevice */ > snprintf(name, sizeof(name), "vdev%dbuffer", rvdev->index); > rvdev->dev.parent = &rproc->dev; > - rvdev->dev.dma_pfn_offset = rproc->dev.parent->dma_pfn_offset; > + rvdev->dev.dma_range_map = rproc->dev.parent->dma_range_map; But doing this means you can't just free the dma_range_map. You need to do a copy here or you'd have to refcount it. Or I suppose you could check if it the child has a different dma_range_map ptr than the parent. Rob ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 72/78] drm/vc4: hdmi: Do the VID_CTL configuration at once
Hi Maxime On Wed, 8 Jul 2020 at 18:44, Maxime Ripard wrote: > > The VID_CTL setup is done in several places in the driver even though it's > not really required. Let's simplify it a bit to do the configuration in one > go. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 14 ++ > 1 file changed, 6 insertions(+), 8 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index bbe521ab000b..f56a718a3643 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -428,10 +428,6 @@ static void vc4_hdmi_set_timings(struct vc4_hdmi > *vc4_hdmi, > > HDMI_WRITE(HDMI_VERTB0, vertb_even); > HDMI_WRITE(HDMI_VERTB1, vertb); > - > - HDMI_WRITE(HDMI_VID_CTL, > - (vsync_pos ? 0 : VC4_HD_VID_CTL_VSYNC_LOW) | > - (hsync_pos ? 0 : VC4_HD_VID_CTL_HSYNC_LOW)); > } > > static void vc4_hdmi_recenter_fifo(struct vc4_hdmi *vc4_hdmi) > @@ -520,8 +516,6 @@ static void vc4_hdmi_encoder_pre_crtc_configure(struct > drm_encoder *encoder) > if (vc4_hdmi->variant->phy_init) > vc4_hdmi->variant->phy_init(vc4_hdmi, mode); > > - HDMI_WRITE(HDMI_VID_CTL, 0); > - > HDMI_WRITE(HDMI_SCHEDULER_CONTROL, >HDMI_READ(HDMI_SCHEDULER_CONTROL) | >VC4_HDMI_SCHEDULER_CONTROL_MANUAL_FORMAT | > @@ -555,15 +549,19 @@ static void vc4_hdmi_encoder_pre_crtc_enable(struct > drm_encoder *encoder) > > static void vc4_hdmi_encoder_post_crtc_enable(struct drm_encoder *encoder) > { > + struct drm_display_mode *mode = &encoder->crtc->state->adjusted_mode; > struct vc4_hdmi *vc4_hdmi = encoder_to_vc4_hdmi(encoder); > struct vc4_hdmi_encoder *vc4_encoder = to_vc4_hdmi_encoder(encoder); > + bool hsync_pos = mode->flags & DRM_MODE_FLAG_PHSYNC; > + bool vsync_pos = mode->flags & DRM_MODE_FLAG_PVSYNC; > int ret; > > HDMI_WRITE(HDMI_VID_CTL, > - HDMI_READ(HDMI_VID_CTL) | >VC4_HD_VID_CTL_ENABLE | >VC4_HD_VID_CTL_UNDERFLOW_ENABLE | > - VC4_HD_VID_CTL_FRAME_COUNTER_RESET); > + VC4_HD_VID_CTL_FRAME_COUNTER_RESET | > + (vsync_pos ? 0 : VC4_HD_VID_CTL_VSYNC_LOW) | > + (hsync_pos ? 0 : VC4_HD_VID_CTL_HSYNC_LOW)); > > if (vc4_encoder->hdmi_monitor) { > HDMI_WRITE(HDMI_SCHEDULER_CONTROL, > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 73/78] drm/vc4: hdmi: Switch to blank pixels when disabled
Hi Maxime On Wed, 8 Jul 2020 at 18:44, Maxime Ripard wrote: > > In order to avoid pixels getting stuck in an unflushable FIFO, we need when > we disable the HDMI controller to switch away from getting our pixels from > the pixelvalve and instead use blank pixels, and switch back to the > pixelvalve when we enable the HDMI controller. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 9 + > drivers/gpu/drm/vc4/vc4_regs.h | 3 +++ > 2 files changed, 12 insertions(+) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index f56a718a3643..37463b016b47 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -325,6 +325,12 @@ static void vc4_hdmi_encoder_post_crtc_disable(struct > drm_encoder *encoder) > struct vc4_hdmi *vc4_hdmi = encoder_to_vc4_hdmi(encoder); > > HDMI_WRITE(HDMI_RAM_PACKET_CONFIG, 0); > + > + HDMI_WRITE(HDMI_VID_CTL, HDMI_READ(HDMI_VID_CTL) | > + VC4_HD_VID_CTL_CLRRGB | VC4_HD_VID_CTL_CLRSYNC); > + > + HDMI_WRITE(HDMI_VID_CTL, > + HDMI_READ(HDMI_VID_CTL) | VC4_HD_VID_CTL_BLANKPIX); > } > > static void vc4_hdmi_encoder_post_crtc_powerdown(struct drm_encoder *encoder) > @@ -563,6 +569,9 @@ static void vc4_hdmi_encoder_post_crtc_enable(struct > drm_encoder *encoder) >(vsync_pos ? 0 : VC4_HD_VID_CTL_VSYNC_LOW) | >(hsync_pos ? 0 : VC4_HD_VID_CTL_HSYNC_LOW)); > > + HDMI_WRITE(HDMI_VID_CTL, > + HDMI_READ(HDMI_VID_CTL) & ~VC4_HD_VID_CTL_BLANKPIX); > + > if (vc4_encoder->hdmi_monitor) { > HDMI_WRITE(HDMI_SCHEDULER_CONTROL, >HDMI_READ(HDMI_SCHEDULER_CONTROL) | > diff --git a/drivers/gpu/drm/vc4/vc4_regs.h b/drivers/gpu/drm/vc4/vc4_regs.h > index d1e8961edaa0..30af52b406f1 100644 > --- a/drivers/gpu/drm/vc4/vc4_regs.h > +++ b/drivers/gpu/drm/vc4/vc4_regs.h > @@ -723,6 +723,9 @@ > # define VC4_HD_VID_CTL_FRAME_COUNTER_RESETBIT(29) > # define VC4_HD_VID_CTL_VSYNC_LOW BIT(28) > # define VC4_HD_VID_CTL_HSYNC_LOW BIT(27) > +# define VC4_HD_VID_CTL_CLRSYNCBIT(24) > +# define VC4_HD_VID_CTL_CLRRGB BIT(23) > +# define VC4_HD_VID_CTL_BLANKPIX BIT(18) > > # define VC4_HD_CSC_CTL_ORDER_MASK VC4_MASK(7, 5) > # define VC4_HD_CSC_CTL_ORDER_SHIFT5 > -- > git-series 0.9.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 74/78] drm/vc4: hdmi: Support the BCM2711 HDMI controllers
Hi Maxime On Wed, 8 Jul 2020 at 18:44, Maxime Ripard wrote: > > Now that the driver is ready for it, let's bring in the HDMI controllers > variants for the BCM2711. > > Signed-off-by: Maxime Ripard Reviewed-by: Dave Stevenson > --- > drivers/gpu/drm/vc4/vc4_hdmi.c | 278 +- > drivers/gpu/drm/vc4/vc4_hdmi.h | 36 ++- > drivers/gpu/drm/vc4/vc4_hdmi_phy.c | 480 +- > drivers/gpu/drm/vc4/vc4_hdmi_regs.h | 201 - > drivers/gpu/drm/vc4/vc4_regs.h | 2 +- > 5 files changed, 997 insertions(+) > > diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c > index 37463b016b47..d5ba0b1b73a9 100644 > --- a/drivers/gpu/drm/vc4/vc4_hdmi.c > +++ b/drivers/gpu/drm/vc4/vc4_hdmi.c > @@ -43,6 +43,7 @@ > #include > #include > #include > +#include > #include > #include > #include > @@ -53,6 +54,31 @@ > #include "vc4_hdmi_regs.h" > #include "vc4_regs.h" > > +#define VC5_HDMI_HORZA_HFP_SHIFT 16 > +#define VC5_HDMI_HORZA_HFP_MASKVC4_MASK(28, 16) > +#define VC5_HDMI_HORZA_VPOSBIT(15) > +#define VC5_HDMI_HORZA_HPOSBIT(14) > +#define VC5_HDMI_HORZA_HAP_SHIFT 0 > +#define VC5_HDMI_HORZA_HAP_MASKVC4_MASK(13, 0) > + > +#define VC5_HDMI_HORZB_HBP_SHIFT 16 > +#define VC5_HDMI_HORZB_HBP_MASKVC4_MASK(26, 16) > +#define VC5_HDMI_HORZB_HSP_SHIFT 0 > +#define VC5_HDMI_HORZB_HSP_MASKVC4_MASK(10, 0) > + > +#define VC5_HDMI_VERTA_VSP_SHIFT 24 > +#define VC5_HDMI_VERTA_VSP_MASKVC4_MASK(28, 24) > +#define VC5_HDMI_VERTA_VFP_SHIFT 16 > +#define VC5_HDMI_VERTA_VFP_MASKVC4_MASK(22, 16) > +#define VC5_HDMI_VERTA_VAL_SHIFT 0 > +#define VC5_HDMI_VERTA_VAL_MASKVC4_MASK(12, 0) > + > +#define VC5_HDMI_VERTB_VSPO_SHIFT 16 > +#define VC5_HDMI_VERTB_VSPO_MASK VC4_MASK(29, 16) > + > +# define VC4_HD_M_SW_RST BIT(2) > +# define VC4_HD_M_ENABLE BIT(0) > + > #define CEC_CLOCK_FREQ 4 > > static int vc4_hdmi_debugfs_regs(struct seq_file *m, void *unused) > @@ -82,6 +108,16 @@ static void vc4_hdmi_reset(struct vc4_hdmi *vc4_hdmi) > HDMI_WRITE(HDMI_SW_RESET_CONTROL, 0); > } > > +static void vc5_hdmi_reset(struct vc4_hdmi *vc4_hdmi) > +{ > + reset_control_reset(vc4_hdmi->reset); > + > + HDMI_WRITE(HDMI_DVP_CTL, 0); > + > + HDMI_WRITE(HDMI_CLOCK_STOP, > + HDMI_READ(HDMI_CLOCK_STOP) | VC4_DVP_HT_CLOCK_STOP_PIXEL); > +} > + > static enum drm_connector_status > vc4_hdmi_connector_detect(struct drm_connector *connector, bool force) > { > @@ -391,6 +427,45 @@ static void vc4_hdmi_csc_setup(struct vc4_hdmi > *vc4_hdmi, bool enable) > HDMI_WRITE(HDMI_CSC_CTL, csc_ctl); > } > > +static void vc5_hdmi_csc_setup(struct vc4_hdmi *vc4_hdmi, bool enable) > +{ > + u32 csc_ctl; > + > + csc_ctl = 0x07; /* RGB_CONVERT_MODE = custom matrix, || > USE_RGB_TO_YCBCR */ > + > + if (enable) { > + /* CEA VICs other than #1 requre limited range RGB > +* output unless overridden by an AVI infoframe. > +* Apply a colorspace conversion to squash 0-255 down > +* to 16-235. The matrix here is: > +* > +* [ 0.8594 0 0 16] > +* [ 0 0.8594 0 16] > +* [ 0 0 0.8594 16] > +* [ 0 0 0 1] > +* Matrix is signed 2p13 fixed point, with signed 9p6 offsets > +*/ > + HDMI_WRITE(HDMI_CSC_12_11, (0x << 16) | 0x1b80); > + HDMI_WRITE(HDMI_CSC_14_13, (0x0400 << 16) | 0x); > + HDMI_WRITE(HDMI_CSC_22_21, (0x1b80 << 16) | 0x); > + HDMI_WRITE(HDMI_CSC_24_23, (0x0400 << 16) | 0x); > + HDMI_WRITE(HDMI_CSC_32_31, (0x << 16) | 0x); > + HDMI_WRITE(HDMI_CSC_34_33, (0x0400 << 16) | 0x1b80); > + } else { > + /* Still use the matrix for full range, but make it unity. > +* Matrix is signed 2p13 fixed point, with signed 9p6 offsets > +*/ > + HDMI_WRITE(HDMI_CSC_12_11, (0x << 16) | 0x2000); > + HDMI_WRITE(HDMI_CSC_14_13, (0x << 16) | 0x); > + HDMI_WRITE(HDMI_CSC_22_21, (0x2000 << 16) | 0x); > + HDMI_WRITE(HDMI_CSC_24_23, (0x << 16) | 0x); > + HDMI_WRITE(HDMI_CSC_32_31, (0x << 16) | 0x); > + HDMI_WRITE(HDMI_CSC_34_33, (0x << 16) | 0x2000); > + } > + > + HDMI_WRITE(HDMI_CSC_CTL, csc_ctl); > +} > + > static void vc4_hdmi_set_timings(struct vc4_hdmi *vc4_hdmi, >
Re: [PATCH v4 00/22] drm: mxsfb: Add i.MX7 support
On 2020-07-27 04:06, Laurent Pinchart wrote: > Hello, > > This patch series adds i.MX7 support to the mxsfb driver. The eLCDIF > instance found in the i.MX7 is backward-compatible with the already > supported LCDC v4, but has extended features amongst which the most > notable one is a second plane. > > The first 10 patches (01/22 to 10/22) contain miscellaneous cleanups and > refactoring to prepare for what is to come. Patch 11/22 starts the real > work with removal of the DRM simple display pipeline helper, as it > doesn't support multiple planes. The next patch (12/22) is an additional > cleanup. > > Patches 13/22 to 15/22 fix vblank handling that I found to be broken > when testing on my device. Patch 16/22 then performs an additional small > cleanup, and patch 17/22 starts official support for i.MX7 by mentioning > it in Kconfig. > > Patch 18/22 adds a new device model for the i.MX6SX and i.MX7 eLCDIF. > After three additional cleanups in patches 19/22 to 21/22, patch 22/22 > finally adds support for the second plane. > > The second plane suffers from an issue whose root cause hasn't been > found, which results in the first 64 bytes of the first line to contain > data of unknown origin. Help from NXP to diagnose this issue would be > useful and appreciated. > > Compared to v3, the series has been rebased on the latest drm-misc, > without any other modifications. > > The code is based on drm-misc-next and has been tested on an i.MX7D > platform with a DPI panel. Applied the series to drm-misc-next! Thanks Laurent! -- Stefan > > Laurent Pinchart (22): > drm: mxsfb: Remove fbdev leftovers > drm: mxsfb: Use drm_panel_bridge > drm: mxsfb: Use BIT() macro to define register bitfields > drm: mxsfb: Remove unused macros from mxsfb_regs.h > drm: mxsfb: Clarify format and bus width configuration > drm: mxsfb: Pass mxsfb_drm_private pointer to mxsfb_reset_block() > drm: mxsfb: Use LCDC_CTRL register name explicitly > drm: mxsfb: Remove register definitions from mxsfb_crtc.c > drm: mxsfb: Remove unneeded includes > drm: mxsfb: Rename mxsfb_crtc.c to mxsfb_kms.c > drm: mxsfb: Stop using DRM simple display pipeline helper > drm: mxsfb: Move vblank event arm to CRTC .atomic_flush() > drm: mxsfb: Don't touch AXI clock in IRQ context > drm: mxsfb: Enable vblank handling > drm: mxsfb: Remove mxsfb_devdata unused fields > drm: mxsfb: Add i.MX7 and i.MX8M to the list of supported SoCs in > Kconfig > drm: mxsfb: Update internal IP version number for i.MX6SX > drm: mxsfb: Drop non-OF support > drm: mxsfb: Turn mxsfb_set_pixel_fmt() into a void function > drm: mxsfb: Merge mxsfb_set_pixel_fmt() and mxsfb_set_bus_fmt() > drm: mxsfb: Remove unnecessary spaces after tab > drm: mxsfb: Support the alpha plane > > drivers/gpu/drm/mxsfb/Kconfig | 8 +- > drivers/gpu/drm/mxsfb/Makefile | 2 +- > drivers/gpu/drm/mxsfb/mxsfb_crtc.c | 343 - > drivers/gpu/drm/mxsfb/mxsfb_drv.c | 254 - > drivers/gpu/drm/mxsfb/mxsfb_drv.h | 42 ++- > drivers/gpu/drm/mxsfb/mxsfb_kms.c | 571 + > drivers/gpu/drm/mxsfb/mxsfb_out.c | 99 - > drivers/gpu/drm/mxsfb/mxsfb_regs.h | 103 +++--- > 8 files changed, 739 insertions(+), 683 deletions(-) > delete mode 100644 drivers/gpu/drm/mxsfb/mxsfb_crtc.c > create mode 100644 drivers/gpu/drm/mxsfb/mxsfb_kms.c > delete mode 100644 drivers/gpu/drm/mxsfb/mxsfb_out.c ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH v4 77/78] drm/vc4: drv: Support BCM2711
Hi Maxime On Wed, 8 Jul 2020 at 18:44, Maxime Ripard wrote: > > The BCM2711 has a reworked display pipeline, and the load tracker needs > some adjustement to operate properly. Let's add a compatible for BCM2711 s/adjustement/adjustment > and disable the load tracker until properly supported. > > Signed-off-by: Maxime Ripard > --- > drivers/gpu/drm/vc4/vc4_drv.c | 1 +- > drivers/gpu/drm/vc4/vc4_drv.h | 3 ++- > drivers/gpu/drm/vc4/vc4_kms.c | 42 +++--- > drivers/gpu/drm/vc4/vc4_plane.c | 5 - > 4 files changed, 38 insertions(+), 13 deletions(-) > > diff --git a/drivers/gpu/drm/vc4/vc4_drv.c b/drivers/gpu/drm/vc4/vc4_drv.c > index 9567d1019212..f1a5fd5dab6f 100644 > --- a/drivers/gpu/drm/vc4/vc4_drv.c > +++ b/drivers/gpu/drm/vc4/vc4_drv.c > @@ -372,6 +372,7 @@ static int vc4_platform_drm_remove(struct platform_device > *pdev) > } > > static const struct of_device_id vc4_of_match[] = { > + { .compatible = "brcm,bcm2711-vc5", }, > { .compatible = "brcm,bcm2835-vc4", }, > { .compatible = "brcm,cygnus-vc4", }, > {}, > diff --git a/drivers/gpu/drm/vc4/vc4_drv.h b/drivers/gpu/drm/vc4/vc4_drv.h > index 501a48a714d3..8c8d96b6289f 100644 > --- a/drivers/gpu/drm/vc4/vc4_drv.h > +++ b/drivers/gpu/drm/vc4/vc4_drv.h > @@ -200,6 +200,9 @@ struct vc4_dev { > > int power_refcount; > > + /* Set to true when the load tracker is supported. */ > + bool load_tracker_available; > + > /* Set to true when the load tracker is active. */ > bool load_tracker_enabled; > > diff --git a/drivers/gpu/drm/vc4/vc4_kms.c b/drivers/gpu/drm/vc4/vc4_kms.c > index 7c8a87339959..ae479f988666 100644 > --- a/drivers/gpu/drm/vc4/vc4_kms.c > +++ b/drivers/gpu/drm/vc4/vc4_kms.c > @@ -532,6 +532,9 @@ static int vc4_load_tracker_atomic_check(struct > drm_atomic_state *state) > struct drm_plane *plane; > int i; > > + if (!vc4->load_tracker_available) > + return 0; > + > priv_state = drm_atomic_get_private_obj_state(state, > &vc4->load_tracker); > if (IS_ERR(priv_state)) > @@ -681,10 +684,14 @@ int vc4_kms_load(struct drm_device *dev) > struct vc4_load_tracker_state *load_state; > int ret; > > - /* Start with the load tracker enabled. Can be disabled through the > -* debugfs load_tracker file. > -*/ > - vc4->load_tracker_enabled = true; > + if (!of_device_is_compatible(dev->dev->of_node, "brcm,bcm2711-vc5")) { Is it better to look up the compatible string, or pass something via the .data element of the of_device_id table? Probably down to personal preference? > + vc4->load_tracker_available = true; > + > + /* Start with the load tracker enabled. Can be > +* disabled through the debugfs load_tracker file. > +*/ > + vc4->load_tracker_enabled = true; > + } > > sema_init(&vc4->async_modeset, 1); > > @@ -698,8 +705,14 @@ int vc4_kms_load(struct drm_device *dev) > return ret; > } > > - dev->mode_config.max_width = 2048; > - dev->mode_config.max_height = 2048; > + if (of_device_is_compatible(dev->dev->of_node, "brcm,bcm2711-vc5")) { We're making the same of_device_is_compatible call twice within vc4_kms_load. Set a flag based on it and check that instead? Dave > + dev->mode_config.max_width = 7680; > + dev->mode_config.max_height = 7680; > + } else { > + dev->mode_config.max_width = 2048; > + dev->mode_config.max_height = 2048; > + } > + > dev->mode_config.funcs = &vc4_mode_funcs; > dev->mode_config.preferred_depth = 24; > dev->mode_config.async_page_flip = true; > @@ -714,14 +727,17 @@ int vc4_kms_load(struct drm_device *dev) > drm_atomic_private_obj_init(dev, &vc4->ctm_manager, &ctm_state->base, > &vc4_ctm_state_funcs); > > - load_state = kzalloc(sizeof(*load_state), GFP_KERNEL); > - if (!load_state) { > - drm_atomic_private_obj_fini(&vc4->ctm_manager); > - return -ENOMEM; > - } > + if (vc4->load_tracker_available) { > + load_state = kzalloc(sizeof(*load_state), GFP_KERNEL); > + if (!load_state) { > + drm_atomic_private_obj_fini(&vc4->ctm_manager); > + return -ENOMEM; > + } > > - drm_atomic_private_obj_init(dev, &vc4->load_tracker, > &load_state->base, > - &vc4_load_tracker_state_funcs); > + drm_atomic_private_obj_init(dev, &vc4->load_tracker, > + &load_state->base, > + &vc4_load_tracker_state_funcs); > + } > > drm_mode_config_reset(dev);
Re: [PATCH v4 78/78] ARM: dts: bcm2711: Enable the display pipeline
Hi Maxime On Wed, 8 Jul 2020 at 18:44, Maxime Ripard wrote: > > Now that all the drivers have been adjusted for it, let's bring in the > necessary device tree changes. Possibly a comment to say that the VEC and PV3 are deliberately NOT enabled as the VEC requires further very specific clock setup changes? > Signed-off-by: Maxime Ripard Otherwise Reviewed-by: Dave Stevenson > --- > arch/arm/boot/dts/bcm2711-rpi-4-b.dts | 46 +++- > arch/arm/boot/dts/bcm2711.dtsi| 115 ++- > 2 files changed, 160 insertions(+), 1 deletion(-) > > diff --git a/arch/arm/boot/dts/bcm2711-rpi-4-b.dts > b/arch/arm/boot/dts/bcm2711-rpi-4-b.dts > index 222d7825e1ab..b93eb30e1ddb 100644 > --- a/arch/arm/boot/dts/bcm2711-rpi-4-b.dts > +++ b/arch/arm/boot/dts/bcm2711-rpi-4-b.dts > @@ -68,6 +68,14 @@ > }; > }; > > +&ddc0 { > + status = "okay"; > +}; > + > +&ddc1 { > + status = "okay"; > +}; > + > &firmware { > firmware_clocks: clocks { > compatible = "raspberrypi,firmware-clocks"; > @@ -163,6 +171,36 @@ > "RGMII_TXD3"; > }; > > +&hdmi0 { > + clocks = <&firmware_clocks 13>, <&dvp 0>; > + status = "okay"; > +}; > + > +&hdmi1 { > + clocks = <&firmware_clocks 13>, <&dvp 1>; > + status = "okay"; > +}; > + > +&hvs { > + clocks = <&firmware_clocks 4>; > +}; > + > +&pixelvalve0 { > + status = "okay"; > +}; > + > +&pixelvalve1 { > + status = "okay"; > +}; > + > +&pixelvalve2 { > + status = "okay"; > +}; > + > +&pixelvalve4 { > + status = "okay"; > +}; > + > &pwm1 { > pinctrl-names = "default"; > pinctrl-0 = <&pwm1_0_gpio40 &pwm1_1_gpio41>; > @@ -231,3 +269,11 @@ > &vchiq { > interrupts = ; > }; > + > +&vc4 { > + status = "okay"; > +}; > + > +&vec { > + status = "disabled"; > +}; > diff --git a/arch/arm/boot/dts/bcm2711.dtsi b/arch/arm/boot/dts/bcm2711.dtsi > index 00bcaed1be32..e637378650f6 100644 > --- a/arch/arm/boot/dts/bcm2711.dtsi > +++ b/arch/arm/boot/dts/bcm2711.dtsi > @@ -12,6 +12,11 @@ > > interrupt-parent = <&gicv2>; > > + vc4: gpu { > + compatible = "brcm,bcm2711-vc5"; > + status = "disabled"; > + }; > + > clk_108MHz: clk-108M { > #clock-cells = <0>; > compatible = "fixed-clock"; > @@ -238,6 +243,27 @@ > status = "disabled"; > }; > > + pixelvalve0: pixelvalve@7e206000 { > + compatible = "brcm,bcm2711-pixelvalve0"; > + reg = <0x7e206000 0x100>; > + interrupts = ; > + status = "disabled"; > + }; > + > + pixelvalve1: pixelvalve@7e207000 { > + compatible = "brcm,bcm2711-pixelvalve1"; > + reg = <0x7e207000 0x100>; > + interrupts = ; > + status = "disabled"; > + }; > + > + pixelvalve2: pixelvalve@7e20a000 { > + compatible = "brcm,bcm2711-pixelvalve2"; > + reg = <0x7e20a000 0x100>; > + interrupts = ; > + status = "disabled"; > + }; > + > pwm1: pwm@7e20c800 { > compatible = "brcm,bcm2835-pwm"; > reg = <0x7e20c800 0x28>; > @@ -248,10 +274,25 @@ > status = "disabled"; > }; > > - hvs@7e40 { > + pixelvalve4: pixelvalve@7e216000 { > + compatible = "brcm,bcm2711-pixelvalve4"; > + reg = <0x7e216000 0x100>; > + interrupts = ; > + status = "disabled"; > + }; > + > + hvs: hvs@7e40 { > + compatible = "brcm,bcm2711-hvs"; > interrupts = ; > }; > > + pixelvalve3: pixelvalve@7ec12000 { > + compatible = "brcm,bcm2711-pixelvalve3"; > + reg = <0x7ec12000 0x100>; > + interrupts = ; > + status = "disabled"; > + }; > + > dvp: clock@7ef0 { > compatible = "brcm,brcm2711-dvp"; > reg = <0x7ef0 0x10>; > @@ -259,6 +300,78 @@ > #clock-cells = <1>; > #reset-cells = <1>; > }; > + > + hdmi0: hdmi@7ef00700 { > + compatible = "brcm,bcm2711-hdmi0"; > + reg = <0x7ef00700 0x300>, > + <0x7ef00300 0x200>, > + <0x7ef00f00 0x80>, > + <0x7ef00f80 0x80>, > + <0x7ef01b00 0x200>, >
RE: [PATCH] nouveau: use ttm populate mapping functions. (v2)
>-Original Message- >From: dri-devel On Behalf Of >Dave Airlie >Sent: Monday, July 27, 2020 11:26 PM >To: dri-devel@lists.freedesktop.org >Cc: bske...@redhat.com >Subject: [PATCH] nouveau: use ttm populate mapping functions. (v2) > >From: Dave Airlie > >Instead of rolling driver copies of them. > >v2: cleanup return handling (Ben) >Signed-off-by: Dave Airlie >--- > drivers/gpu/drm/nouveau/nouveau_bo.c | 38 ++-- > 1 file changed, 2 insertions(+), 36 deletions(-) > >diff --git a/drivers/gpu/drm/nouveau/nouveau_bo.c >b/drivers/gpu/drm/nouveau/nouveau_bo.c >index 7806278dce57..6ef5085c9a91 100644 >--- a/drivers/gpu/drm/nouveau/nouveau_bo.c >+++ b/drivers/gpu/drm/nouveau/nouveau_bo.c >@@ -1231,8 +1231,6 @@ nouveau_ttm_tt_populate(struct ttm_tt *ttm, >struct ttm_operation_ctx *ctx) > struct ttm_dma_tt *ttm_dma = (void *)ttm; > struct nouveau_drm *drm; > struct device *dev; >- unsigned i; >- int r; > bool slave = !!(ttm->page_flags & TTM_PAGE_FLAG_SG); > > if (ttm->state != tt_unpopulated) >@@ -1260,31 +1258,7 @@ nouveau_ttm_tt_populate(struct ttm_tt *ttm, >struct ttm_operation_ctx *ctx) > return ttm_dma_populate((void *)ttm, dev, ctx); > } > #endif >- >- r = ttm_pool_populate(ttm, ctx); >- if (r) { >- return r; >- } >- >- for (i = 0; i < ttm->num_pages; i++) { >- dma_addr_t addr; >- >- addr = dma_map_page(dev, ttm->pages[i], 0, PAGE_SIZE, >- DMA_BIDIRECTIONAL); >- >- if (dma_mapping_error(dev, addr)) { >- while (i--) { >- dma_unmap_page(dev, ttm_dma- >>dma_address[i], >- PAGE_SIZE, >DMA_BIDIRECTIONAL); >- ttm_dma->dma_address[i] = 0; >- } >- ttm_pool_unpopulate(ttm); >- return -EFAULT; >- } >- >- ttm_dma->dma_address[i] = addr; >- } >- return 0; >+ return ttm_populate_and_map_pages(dev, ttm_dma, ctx); This is not a completely straight code replacement. ttm_populate_and_map_pages() also has code to deal with pages that are contiguous (consolidates them). Is it possible that the nouveau HW can't handle a contiguous buffer larger than PAG_SIZE? Thanks, Mike > } > > static void >@@ -1293,7 +1267,6 @@ nouveau_ttm_tt_unpopulate(struct ttm_tt *ttm) > struct ttm_dma_tt *ttm_dma = (void *)ttm; > struct nouveau_drm *drm; > struct device *dev; >- unsigned i; > bool slave = !!(ttm->page_flags & TTM_PAGE_FLAG_SG); > > if (slave) >@@ -1316,14 +1289,7 @@ nouveau_ttm_tt_unpopulate(struct ttm_tt *ttm) > } > #endif > >- for (i = 0; i < ttm->num_pages; i++) { >- if (ttm_dma->dma_address[i]) { >- dma_unmap_page(dev, ttm_dma->dma_address[i], >PAGE_SIZE, >- DMA_BIDIRECTIONAL); >- } >- } >- >- ttm_pool_unpopulate(ttm); >+ ttm_unmap_and_unpopulate_pages(dev, ttm_dma); > } > > void >-- >2.26.2 > >___ >dri-devel mailing list >dri-devel@lists.freedesktop.org >https://lists.freedesktop.org/mailman/listinfo/dri-devel ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH] drm/vkms: add missing drm_crtc_vblank_put to the get/put pair on flush
On Sun, Jul 26, 2020 at 12:26:08PM +0200, Daniel Vetter wrote: > On Sat, Jul 25, 2020 at 9:29 PM Melissa Wen wrote: > > > > On Sat, Jul 25, 2020 at 4:19 PM Melissa Wen wrote: > > > > > > > No, this very first warning continues (only once) :( > > > > From here (drm_crtc_vblank_on): > > > > if (atomic_read(&vblank->refcount) != 0 || drm_vblank_offdelay > > > > == 0) > > > > drm_WARN_ON(dev, drm_vblank_enable(dev, pipe)); > > > > > > Sorry, not sure when this warning is triggered. > > > > Again, I just had to look at the trace: > > [ 52.299388] drm_get_last_vbltimestamp+0xaa/0xc0 [drm] > > [ 52.299389] drm_reset_vblank_timestamp+0x5b/0xd0 [drm] > > [ 52.299389] drm_crtc_vblank_on.cold+0x37/0x103 [drm] > > [ 52.299390] drm_atomic_helper_commit_modeset_enable > > Yeah I think vkms can't generate a reasonable timestamp when the > hrtimer is off. I thought the warning comes from a different > callchain, but seems to be a general problem. > > I guess in the vkms timestamp function we should check whether the > timer is running, and if it's not running, then we just grab the > current time and done. I tried some test about this scenario that commit_tail calls in sequence disable - enable - commit. In a first test. there was a warning and found out that it raised from vkms_get_vblank_timestamp() the code checking vblank_hrtimer's expire time and vblank_time. In first run, vblank_time and hrtimer's expire time was both zero. because vblank wasn't happened yet. this warning wasn't happend since second run that vblank time was set from first run. I don't know it's good way to solve the problem. Is there no problem in other drm modules? -Sidong > -Daniel > > > > > > > > > > > > > But I'm still wondering why after step 3 we don't get -EINVAL from > > > > > vblank_get() - after vblank_off() vblank->enabled should be false > > > > > again, getting us back to the same state as after 1. Is that not > > > > > happening? > > > > > > > > Yes (sorry if it got confused), we got -EINVAL after setp 3: > > > > > > > > In step 3, at the end of the 2nd running, we have: > > > > atomic_disable > > > > --> vblank_off [!vblank->inmodeset + refcount going 0->1 + inmodeset=1] > > > > and then in next vblank_get: -EINVAL (!vblank->enabled + refcount ends > > > > 1) > > > > as in the first step. > > > > > > > > Melissa > > > > > > > > > -Daniel > > > > > > > > > > > > > > > > > > > > > > > > > > > Thanks > > > > > > > > -Sidong > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > crtc->state->event = NULL; > > > > > > > > > > > > } > > > > > > > > > > > > > > > > > > > > > > > > -- > > > > > > > > > > > > 2.27.0 > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > -- > > > > > > > > > > > Daniel Vetter > > > > > > > > > > > Software Engineer, Intel Corporation > > > > > > > > > > > http://blog.ffwll.ch > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > -- > > > > > > > > > Daniel Vetter > > > > > > > > > Software Engineer, Intel Corporation > > > > > > > > > http://blog.ffwll.ch > > > > > > > > > ___ > > > > > > > > > dri-devel mailing list > > > > > > > > > dri-devel@lists.freedesktop.org > > > > > > > > > https://lists.freedesktop.org/mailman/listinfo/dri-devel > > > > > > > > > > > > > > > > > > > > > > > > > > > > -- > > > > > > > Daniel Vetter > > > > > > > Software Engineer, Intel Corporation > > > > > > > http://blog.ffwll.ch > > > > > > > > > > > > > > > > > > > > -- > > > > > Daniel Vetter > > > > > Software Engineer, Intel Corporation > > > > > http://blog.ffwll.ch > > > > -- > Daniel Vetter > Software Engineer, Intel Corporation > http://blog.ffwll.ch ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH 1/3] drm: Restore driver.preclose() for all to use
Quoting Daniel Vetter (2020-07-27 20:32:45) > On Thu, Jul 23, 2020 at 7:21 PM Chris Wilson wrote: > > > > An unfortunate sequence of events, but it turns out there is a valid > > usecase for being able to free/decouple the driver objects before they > > are freed by the DRM core. In particular, if we have a pointer into a > > drm core object from inside a driver object, that pointer needs to be > > nerfed *before* it is freed so that concurrent access (e.g. debugfs) > > does not following the dangling pointer. > > > > The legacy marker was adding in the code movement from drp_fops.c to > > drm_file.c > > I might fumble a lot, but not this one: > > commit 45c3d213a400c952ab7119f394c5293bb6877e6b > Author: Daniel Vetter > Date: Mon May 8 10:26:33 2017 +0200 > > drm: Nerf the preclose callback for modern drivers Gah, when I going through the history it looked like it appeared out of nowhere. > Also looking at the debugfs hook that has some rather adventurous > stuff going on I think, feels a bit like a kitchensink with batteries > included. If that's really all needed I'd say iterate the contexts by > first going over files, then the ctx (which arent shared anyway) and > the problem should also be gone. Or we could cut out the middlelayer and put the release under the driver control with a call to the drm_release() when the driver is ready. -Chris ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH] amdgpu_dm: fix nonblocking atomic commit use-after-free
On 2020-07-28 5:22 a.m., Paul Menzel wrote: Dear Linux folks, Am 25.07.20 um 07:20 schrieb Mazin Rezk: On Saturday, July 25, 2020 12:59 AM, Duncan wrote: On Sat, 25 Jul 2020 03:03:52 + Mazin Rezk wrote: Am 24.07.20 um 19:33 schrieb Kees Cook: There was a fix to disable the async path for this driver that worked around the bug too, yes? That seems like a safer and more focused change that doesn't revert the SLUB defense for all users, and would actually provide a complete, I think, workaround That said, I haven't seen the async disabling patch. If you could link to it, I'd be glad to test it out and perhaps we can use that instead. I'm confused. Not to put words in Kees' mouth; /I/ am confused (which admittedly could well be just because I make no claims to be a coder and am simply reading the bug and thread, but I'd appreciate some "unconfusing" anyway). My interpretation of the "async disabling" reference was that it was to comment #30 on the bug: https://bugzilla.kernel.org/show_bug.cgi?id=207383#c30 ... which (if I'm not confused on this point too) appears to be yours. There it was stated... I've also found that this bug exclusively occurs when commit_work is on the workqueue. After forcing drm_atomic_helper_commit to run all of the commits without adding to the workqueue and running the OS, the issue seems to have disappeared. Would not forcing all commits to run directly, without placing them on the workqueue, be "async disabling"? That's what I /thought/ he was referencing. Oh, I thought he was referring to a different patch. Kees, could I get your confirmation on this? The change I made actually affected all of the DRM code, although this could easily be changed to be specific to amdgpu. (By forcing blocking on amdgpu_dm's non-blocking commit code) That said, I'd still need to test further because I only did test it for a couple of hours then. Although it should work in theory. OTOH your base/context swap idea sounds like a possibly "less disturbance" workaround, if it works, and given the point in the commit cycle... (But if it's out Sunday it's likely too late to test and get it in now anyway; if it's another week, tho...) The base/context swap idea should make the use-after-free behave how it did in 5.6. Since the bug doesn't cause an issue in 5.6, it's less of a "less disturbance" workaround and more of a "no disturbance" workaround. Sorry for bothering, but is there now a solution, besides reverting the commits, to avoid freezes/crashes *without* performance regressions? Kind regards, Paul Mazin's "drm/amd/display: Clear dm_state for fast updates" change accomplishes this, at least as a temporary hack. I've started work on a more large scale fix that we could get in in after. Regards, Nicholas Kazlauskas ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH 2/2] dma-buf: fence-chain: Document missing dma_fence_chain_init() parameter in kerneldoc
Fix W=1 compile warnings (invalid kerneldoc): drivers/dma-buf/dma-fence-chain.c:233: warning: Function parameter or member 'seqno' not described in 'dma_fence_chain_init' Signed-off-by: Krzysztof Kozlowski --- drivers/dma-buf/dma-fence-chain.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/dma-buf/dma-fence-chain.c b/drivers/dma-buf/dma-fence-chain.c index 3d123502ff12..7d129e68ac70 100644 --- a/drivers/dma-buf/dma-fence-chain.c +++ b/drivers/dma-buf/dma-fence-chain.c @@ -222,6 +222,7 @@ EXPORT_SYMBOL(dma_fence_chain_ops); * @chain: the chain node to initialize * @prev: the previous fence * @fence: the current fence + * @seqno: the sequence number to use for the fence chain * * Initialize a new chain node and either start a new chain or add the node to * the existing chain of the previous fence. -- 2.17.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH 1/2] dma-buf: Fix kerneldoc of dma_buf_set_name()
Fix W=1 compile warnings (invalid kerneldoc): drivers/dma-buf/dma-buf.c:328: warning: Function parameter or member 'dmabuf' not described in 'dma_buf_set_name' Signed-off-by: Krzysztof Kozlowski --- drivers/dma-buf/dma-buf.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/drivers/dma-buf/dma-buf.c b/drivers/dma-buf/dma-buf.c index 1699a8e309ef..58564d82a3a2 100644 --- a/drivers/dma-buf/dma-buf.c +++ b/drivers/dma-buf/dma-buf.c @@ -316,9 +316,9 @@ static __poll_t dma_buf_poll(struct file *file, poll_table *poll) * name of the dma-buf if the same piece of memory is used for multiple * purpose between different devices. * - * @dmabuf [in] dmabuf buffer that will be renamed. - * @buf: [in] A piece of userspace memory that contains the name of - * the dma-buf. + * @dmabuf: [in] dmabuf buffer that will be renamed. + * @buf:[in] A piece of userspace memory that contains the name of + * the dma-buf. * * Returns 0 on success. If the dma-buf buffer is already attached to * devices, return -EBUSY. -- 2.17.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH V2 3/3] drm/panel: simple: Add DT bindings for Powertip PH800480T013
On Tue, Jul 28, 2020 at 02:12:46PM +0200, Marek Vasut wrote: > Add support for Powertip PH800480T013 800x480 parallel LCD, this > one is used in the Raspberry Pi 7" touchscreen display unit. > > Signed-off-by: Marek Vasut > To: dri-devel@lists.freedesktop.org > Cc: Eric Anholt > Cc: Rob Herring > Cc: Sam Ravnborg > Cc: devicet...@vger.kernel.org > --- > V2: Add bus_flags and connector_type Hi Marek. Applied the 3 patches to drm-misc-next. Fixed subject while applying this patch. Sam > --- > drivers/gpu/drm/panel/panel-simple.c | 28 > 1 file changed, 28 insertions(+) > > diff --git a/drivers/gpu/drm/panel/panel-simple.c > b/drivers/gpu/drm/panel/panel-simple.c > index cb6550d37e85..298e3a26d9ee 100644 > --- a/drivers/gpu/drm/panel/panel-simple.c > +++ b/drivers/gpu/drm/panel/panel-simple.c > @@ -3000,6 +3000,31 @@ static const struct panel_desc pda_91_00156_a0 = { > .bus_format = MEDIA_BUS_FMT_RGB888_1X24, > }; > > +static const struct drm_display_mode powertip_ph800480t013_idf02_mode = { > + .clock = 24750, > + .hdisplay = 800, > + .hsync_start = 800 + 54, > + .hsync_end = 800 + 54 + 2, > + .htotal = 800 + 54 + 2 + 44, > + .vdisplay = 480, > + .vsync_start = 480 + 49, > + .vsync_end = 480 + 49 + 2, > + .vtotal = 480 + 49 + 2 + 22, > +}; > + > +static const struct panel_desc powertip_ph800480t013_idf02 = { > + .modes = &powertip_ph800480t013_idf02_mode, > + .num_modes = 1, > + .size = { > + .width = 152, > + .height = 91, > + }, > + .bus_flags = DRM_BUS_FLAG_DE_HIGH | > + DRM_BUS_FLAG_PIXDATA_SAMPLE_NEGEDGE | > + DRM_BUS_FLAG_SYNC_SAMPLE_NEGEDGE, > + .bus_format = MEDIA_BUS_FMT_RGB888_1X24, > + .connector_type = DRM_MODE_CONNECTOR_DPI, > +}; > > static const struct drm_display_mode qd43003c0_40_mode = { > .clock = 9000, > @@ -4012,6 +4037,9 @@ static const struct of_device_id platform_of_match[] = { > }, { > .compatible = "pda,91-00156-a0", > .data = &pda_91_00156_a0, > + }, { > + .compatible = "powertip,ph800480t013-idf02", > + .data = &powertip_ph800480t013_idf02, > }, { > .compatible = "qiaodian,qd43003c0-40", > .data = &qd43003c0_40, > -- > 2.27.0 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH 02/13] drm/ast: Test if I2C support has been initialized
Hi Thomas. On Tue, Jul 28, 2020 at 09:44:14AM +0200, Thomas Zimmermann wrote: > The ast driver is supposed to work without I2C support. This is > tested by looking at the connector's i2c field being non-NULL. > > After embedding the I2C structure in the connector, the i2c field > will not be a pointer. So change the test to look at the dev field > in struct ast_i2c_chan. > > ast_get_modes() did not really test if I2C has been initialized, so > the patch adds this test as well. > > Signed-off-by: Thomas Zimmermann > --- > drivers/gpu/drm/ast/ast_mode.c | 23 ++- > 1 file changed, 18 insertions(+), 5 deletions(-) > > diff --git a/drivers/gpu/drm/ast/ast_mode.c b/drivers/gpu/drm/ast/ast_mode.c > index 19f1dfc8e9e0..45be020afcad 100644 > --- a/drivers/gpu/drm/ast/ast_mode.c > +++ b/drivers/gpu/drm/ast/ast_mode.c > @@ -603,7 +603,6 @@ static struct ast_i2c_chan *ast_i2c_create(struct > drm_device *dev) > i2c->adapter.owner = THIS_MODULE; > i2c->adapter.class = I2C_CLASS_DDC; > i2c->adapter.dev.parent = &dev->pdev->dev; > - i2c->dev = dev; > i2c_set_adapdata(&i2c->adapter, i2c); > snprintf(i2c->adapter.name, sizeof(i2c->adapter.name), >"AST i2c bit bus"); > @@ -622,17 +621,30 @@ static struct ast_i2c_chan *ast_i2c_create(struct > drm_device *dev) > goto out_free; > } > > + i2c->dev = dev; /* signals presence of I2C support */ > + > return i2c; > out_free: > kfree(i2c); > return NULL; > } > > -static void ast_i2c_destroy(struct ast_i2c_chan *i2c) > +static bool ast_i2c_is_initialized(struct ast_i2c_chan *i2c) > { > - if (!i2c) > + return i2c && !!i2c->dev; > +} It seems pointless to convert the pointer to bool here ("!!"). > + > +static void ast_i2c_fini(struct ast_i2c_chan *i2c) > +{ > + if (!ast_i2c_is_initialized(i2c)) > return; Empty line after return? > i2c_del_adapter(&i2c->adapter); > + i2c->dev = NULL; /* clear to signal absence of I2C support */ > +} > + > +static void ast_i2c_destroy(struct ast_i2c_chan *i2c) > +{ > + ast_i2c_fini(i2c); > kfree(i2c); > } > > @@ -1054,6 +1066,7 @@ static int ast_get_modes(struct drm_connector > *connector) > { > struct ast_connector *ast_connector = to_ast_connector(connector); > struct ast_private *ast = to_ast_private(connector->dev); > + struct ast_i2c_chan *i2c = ast_connector->i2c; > struct edid *edid; > int ret; > bool flags = false; > @@ -1069,8 +1082,8 @@ static int ast_get_modes(struct drm_connector > *connector) > else > kfree(edid); > } > - if (!flags) > - edid = drm_get_edid(connector, &ast_connector->i2c->adapter); > + if (!flags && ast_i2c_is_initialized(i2c)) > + edid = drm_get_edid(connector, &i2c->adapter); > if (edid) { > drm_connector_update_edid_property(&ast_connector->base, edid); > ret = drm_add_edid_modes(connector, edid); > -- > 2.27.0 > > ___ > dri-devel mailing list > dri-devel@lists.freedesktop.org > https://lists.freedesktop.org/mailman/listinfo/dri-devel ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH 01/13] drm/ast: Move I2C code within ast_mode.c
Hi Thomas. A few comments related to the code - but not to this patch and not to this patch-set. But I noticed so here goes. Sam On Tue, Jul 28, 2020 at 09:44:13AM +0200, Thomas Zimmermann wrote: > The I2C support feels slammed down to the end of ast_mode.c. Improve > this by moving the code before it's callers, remove the declarations, > rename the callbacks to match I2C's get/set sda/scl convention, and > prefix all functions with ast_. No functional changes have been made. > > Signed-off-by: Thomas Zimmermann > --- > drivers/gpu/drm/ast/ast_mode.c | 249 + > 1 file changed, 125 insertions(+), 124 deletions(-) > > diff --git a/drivers/gpu/drm/ast/ast_mode.c b/drivers/gpu/drm/ast/ast_mode.c > index 154cd877d9d1..19f1dfc8e9e0 100644 > --- a/drivers/gpu/drm/ast/ast_mode.c > +++ b/drivers/gpu/drm/ast/ast_mode.c > @@ -46,9 +46,6 @@ > #include "ast_drv.h" > #include "ast_tables.h" > > -static struct ast_i2c_chan *ast_i2c_create(struct drm_device *dev); > -static void ast_i2c_destroy(struct ast_i2c_chan *i2c); > - > static inline void ast_load_palette_index(struct ast_private *ast, >u8 index, u8 red, u8 green, >u8 blue) > @@ -514,6 +511,131 @@ static void ast_set_start_address_crt1(struct > ast_private *ast, > > } > > +/* > + * I2C > + */ > + > +static int ast_i2c_getscl(void *i2c_priv) > +{ > + struct ast_i2c_chan *i2c = i2c_priv; > + struct ast_private *ast = to_ast_private(i2c->dev); > + uint32_t val, val2, count, pass; s/uint32_t/u32 > + > + count = 0; > + pass = 0; > + val = (ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0x10) >> 4) > & 0x01; So val is a bool - but anyway an int is used. > + do { > + val2 = (ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, > 0x10) >> 4) & 0x01; Likewise for val2. > + if (val == val2) { > + pass++; > + } else { > + pass = 0; > + val = (ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, > 0xb7, 0x10) >> 4) & 0x01; > + } > + } while ((pass < 5) && (count++ < 0x1)); > + > + return val & 1 ? 1 : 0; bool to int conversion could do the trick here. > +} > + > +static int ast_i2c_getsda(void *i2c_priv) > +{ > + struct ast_i2c_chan *i2c = i2c_priv; > + struct ast_private *ast = to_ast_private(i2c->dev); > + uint32_t val, val2, count, pass; > + > + count = 0; > + pass = 0; > + val = (ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0x20) >> 5) > & 0x01; > + do { > + val2 = (ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, > 0x20) >> 5) & 0x01; > + if (val == val2) { > + pass++; > + } else { > + pass = 0; > + val = (ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, > 0xb7, 0x20) >> 5) & 0x01; > + } > + } while ((pass < 5) && (count++ < 0x1)); > + > + return val & 1 ? 1 : 0; > +} > + > +static void ast_i2c_setscl(void *i2c_priv, int clock) > +{ > + struct ast_i2c_chan *i2c = i2c_priv; > + struct ast_private *ast = to_ast_private(i2c->dev); > + int i; > + u8 ujcrb7, jtemp; And now u8 is used for registers. Maybe because ast_get_index_reg_mask() returns uint8_t. So for consistentcy do the uint8_t => u8 etc. conversion first. > + > + for (i = 0; i < 0x1; i++) { > + ujcrb7 = ((clock & 0x01) ? 0 : 1); > + ast_set_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0xf4, > ujcrb7); > + jtemp = ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, > 0x01); > + if (ujcrb7 == jtemp) > + break; > + } > +} > + > +static void ast_i2c_setsda(void *i2c_priv, int data) > +{ > + struct ast_i2c_chan *i2c = i2c_priv; > + struct ast_private *ast = to_ast_private(i2c->dev); > + int i; > + u8 ujcrb7, jtemp; > + > + for (i = 0; i < 0x1; i++) { > + ujcrb7 = ((data & 0x01) ? 0 : 1) << 2; > + ast_set_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, 0xf1, > ujcrb7); > + jtemp = ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xb7, > 0x04); > + if (ujcrb7 == jtemp) > + break; > + } > +} > + > +static struct ast_i2c_chan *ast_i2c_create(struct drm_device *dev) > +{ > + struct ast_i2c_chan *i2c; > + int ret; > + > + i2c = kzalloc(sizeof(struct ast_i2c_chan), GFP_KERNEL); > + if (!i2c) > + return NULL; > + > + i2c->adapter.owner = THIS_MODULE; > + i2c->adapter.class = I2C_CLASS_DDC; > + i2c->adapter.dev.parent = &dev->pdev->dev; > + i2c->dev = dev; > + i2c_set_adapdata(&i2c->adapter, i2c); If ast_private * was passed here and not i2c. Then the implementation of ast_i2c_* could be a tad simpler - no upclassing needed. And then you could drop the drm_device f
Re: [PATCH 04/13] drm/ast: Managed release of I2C adapter
On Tue, Jul 28, 2020 at 09:44:16AM +0200, Thomas Zimmermann wrote: > Managed releases of the device's I2C adapter simplify the connector's > release. > > Signed-off-by: Thomas Zimmermann > --- > drivers/gpu/drm/ast/ast_mode.c | 21 ++--- > 1 file changed, 10 insertions(+), 11 deletions(-) > > diff --git a/drivers/gpu/drm/ast/ast_mode.c b/drivers/gpu/drm/ast/ast_mode.c > index f421a60d8a96..27eb49bd12b3 100644 > --- a/drivers/gpu/drm/ast/ast_mode.c > +++ b/drivers/gpu/drm/ast/ast_mode.c > @@ -39,6 +39,7 @@ > #include > #include > #include > +#include > #include > #include > #include > @@ -591,6 +592,14 @@ static void ast_i2c_setsda(void *i2c_priv, int data) > } > } > > +static void ast_i2c_release(struct drm_device *dev, void *data) > +{ > + struct ast_i2c_chan *i2c = data; > + > + i2c_del_adapter(&i2c->adapter); > + i2c->dev = NULL; /* clear to signal absence of I2C support */ > +} > + > static int ast_i2c_init(struct ast_i2c_chan *i2c, struct drm_device *dev) > { > int ret; > @@ -618,7 +627,7 @@ static int ast_i2c_init(struct ast_i2c_chan *i2c, struct > drm_device *dev) > > i2c->dev = dev; /* signals presence of I2C support */ > > - return 0; > + return drmm_add_action_or_reset(dev, ast_i2c_release, i2c); > } > > static bool ast_i2c_is_initialized(struct ast_i2c_chan *i2c) > @@ -626,14 +635,6 @@ static bool ast_i2c_is_initialized(struct ast_i2c_chan > *i2c) > return !!i2c->dev; > } > > -static void ast_i2c_fini(struct ast_i2c_chan *i2c) > -{ > - if (!ast_i2c_is_initialized(i2c)) > - return; > - i2c_del_adapter(&i2c->adapter); > - i2c->dev = NULL; /* clear to signal absence of I2C support */ > -} The intro of ast_i2c_fini() and then removal again confuses me a little. But end result looks simple so I guess thats what counts. Sam > - > /* > * Primary plane > */ > @@ -1139,8 +1140,6 @@ static enum drm_mode_status ast_mode_valid(struct > drm_connector *connector, > > static void ast_connector_destroy(struct drm_connector *connector) > { > - struct ast_connector *ast_connector = to_ast_connector(connector); > - ast_i2c_fini(&ast_connector->i2c); > drm_connector_cleanup(connector); > kfree(connector); > } > -- > 2.27.0 > > ___ > dri-devel mailing list > dri-devel@lists.freedesktop.org > https://lists.freedesktop.org/mailman/listinfo/dri-devel ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH 00/13] drm/ast: Convert to managed initialization
Hi Thomas. On Tue, Jul 28, 2020 at 09:44:12AM +0200, Thomas Zimmermann wrote: > This is the final patchset for converting ast to managed initialization. > > Patches #1 to #4 address I2C helpers. The structures are being stored > in struct ast_connector. The initialization and cleanups is being converted > to managed release helpers. > > Patches #5 to #10 address modesetting and device structures. All are > being embedded into struct ast_private. With struct ast_private being > a subclass of struct drm_device, patch #10 switches ast to DRM's managed- > allocation helpers. > > Patches #11 and #12 address firmware memory that ast allocates > internally. > > Finally, patch #13 removes ast's destroy function in favor of managed > release helpers. > > Tested on AST 2100 HW. > > Thomas Zimmermann (13): > drm/ast: Move I2C code within ast_mode.c > drm/ast: Test if I2C support has been initialized > drm/ast: Embed I2C fields in struct ast_connector > drm/ast: Managed release of I2C adapter > drm/ast: Embed CRTC and connector in struct ast_private > drm/ast: Separate DRM driver from PCI code > drm/ast: Replace driver load/unload functions with device > create/destroy > drm/ast: Replace struct_drm_device.dev_private with to_ast_private() > drm/ast: Don't use ast->dev if dev is available > drm/ast: Embed struct drm_device in struct ast_private > drm/ast: Managed release of ast firmware > drm/ast: Manage release of firmware backup memory > drm/ast: Managed device release A few nits posted to a few patches. Patch 1-11 are all: Acked-by: Sam Ravnborg I did not look at 12 and did not follow all the changes in 13. Not that I found 13 faulty - just lost track and -ENOTIME Sam > > drivers/gpu/drm/ast/ast_cursor.c | 8 +- > drivers/gpu/drm/ast/ast_dp501.c | 23 ++- > drivers/gpu/drm/ast/ast_drv.c| 82 > drivers/gpu/drm/ast/ast_drv.h| 43 +++-- > drivers/gpu/drm/ast/ast_main.c | 74 > drivers/gpu/drm/ast/ast_mm.c | 2 +- > drivers/gpu/drm/ast/ast_mode.c | 310 ++- > drivers/gpu/drm/ast/ast_post.c | 6 +- > 8 files changed, 263 insertions(+), 285 deletions(-) > > -- > 2.27.0 > > ___ > dri-devel mailing list > dri-devel@lists.freedesktop.org > https://lists.freedesktop.org/mailman/listinfo/dri-devel ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH 1/1] drm/ttm: fix offset in VMAs with a pg_offs in ttm_bo_vm_access
VMAs with a pg_offs that's offset from the start of the vma_node need to adjust the offset within the BO accordingly. This matches the offset calculation in ttm_bo_vm_fault_reserved. Signed-off-by: Felix Kuehling Tested-by: Laurent Morichetti --- drivers/gpu/drm/ttm/ttm_bo_vm.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/ttm/ttm_bo_vm.c b/drivers/gpu/drm/ttm/ttm_bo_vm.c index 389128b8c4dd..60b41447bec8 100644 --- a/drivers/gpu/drm/ttm/ttm_bo_vm.c +++ b/drivers/gpu/drm/ttm/ttm_bo_vm.c @@ -405,8 +405,10 @@ static int ttm_bo_vm_access_kmap(struct ttm_buffer_object *bo, int ttm_bo_vm_access(struct vm_area_struct *vma, unsigned long addr, void *buf, int len, int write) { - unsigned long offset = (addr) - vma->vm_start; struct ttm_buffer_object *bo = vma->vm_private_data; + unsigned long offset = (addr) - vma->vm_start + + ((vma->vm_pgoff - drm_vma_node_start(&bo->base.vma_node)) +<< PAGE_SHIFT); int ret; if (len < 1 || (offset + len) >> PAGE_SHIFT > bo->num_pages) -- 2.17.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH] drm/ttm/amdgpu: consolidate ttm reserve paths
From: Dave Airlie Drop the WARN_ON and consolidate the two paths into one. Use the consolidate slowpath in the execbuf utils code. Signed-off-by: Dave Airlie --- drivers/gpu/drm/amd/amdgpu/amdgpu_object.h | 2 +- drivers/gpu/drm/ttm/ttm_execbuf_util.c | 12 +-- include/drm/ttm/ttm_bo_driver.h| 91 -- 3 files changed, 20 insertions(+), 85 deletions(-) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_object.h b/drivers/gpu/drm/amd/amdgpu/amdgpu_object.h index afa5189dba7d..e01e8903741e 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_object.h +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_object.h @@ -160,7 +160,7 @@ static inline int amdgpu_bo_reserve(struct amdgpu_bo *bo, bool no_intr) struct amdgpu_device *adev = amdgpu_ttm_adev(bo->tbo.bdev); int r; - r = __ttm_bo_reserve(&bo->tbo, !no_intr, false, NULL); + r = ttm_bo_reserve(&bo->tbo, !no_intr, false, NULL); if (unlikely(r != 0)) { if (r != -ERESTARTSYS) dev_err(adev->dev, "%p reserve failed\n", bo); diff --git a/drivers/gpu/drm/ttm/ttm_execbuf_util.c b/drivers/gpu/drm/ttm/ttm_execbuf_util.c index 1797f04c0534..8a8f1a6a83a6 100644 --- a/drivers/gpu/drm/ttm/ttm_execbuf_util.c +++ b/drivers/gpu/drm/ttm/ttm_execbuf_util.c @@ -93,7 +93,7 @@ int ttm_eu_reserve_buffers(struct ww_acquire_ctx *ticket, list_for_each_entry(entry, list, head) { struct ttm_buffer_object *bo = entry->bo; - ret = __ttm_bo_reserve(bo, intr, (ticket == NULL), ticket); + ret = ttm_bo_reserve(bo, intr, (ticket == NULL), ticket); if (ret == -EALREADY && dups) { struct ttm_validate_buffer *safe = entry; entry = list_prev_entry(entry, head); @@ -119,13 +119,7 @@ int ttm_eu_reserve_buffers(struct ww_acquire_ctx *ticket, ttm_eu_backoff_reservation_reverse(list, entry); if (ret == -EDEADLK) { - if (intr) { - ret = dma_resv_lock_slow_interruptible(bo->base.resv, - ticket); - } else { - dma_resv_lock_slow(bo->base.resv, ticket); - ret = 0; - } + ret = ttm_bo_reserve_slowpath(bo, intr, ticket); } if (!ret && entry->num_shared) @@ -133,8 +127,6 @@ int ttm_eu_reserve_buffers(struct ww_acquire_ctx *ticket, entry->num_shared); if (unlikely(ret != 0)) { - if (ret == -EINTR) - ret = -ERESTARTSYS; if (ticket) { ww_acquire_done(ticket); ww_acquire_fini(ticket); diff --git a/include/drm/ttm/ttm_bo_driver.h b/include/drm/ttm/ttm_bo_driver.h index 5a37f1cc057e..bfa9d146d3d4 100644 --- a/include/drm/ttm/ttm_bo_driver.h +++ b/include/drm/ttm/ttm_bo_driver.h @@ -597,29 +597,30 @@ int ttm_mem_io_lock(struct ttm_mem_type_manager *man, bool interruptible); void ttm_mem_io_unlock(struct ttm_mem_type_manager *man); /** - * __ttm_bo_reserve: + * ttm_bo_reserve: * * @bo: A pointer to a struct ttm_buffer_object. * @interruptible: Sleep interruptible if waiting. * @no_wait: Don't sleep while trying to reserve, rather return -EBUSY. * @ticket: ticket used to acquire the ww_mutex. * - * Will not remove reserved buffers from the lru lists. - * Otherwise identical to ttm_bo_reserve. + * Locks a buffer object for validation. (Or prevents other processes from + * locking it for validation), while taking a number of measures to prevent + * deadlocks. * * Returns: * -EDEADLK: The reservation may cause a deadlock. * Release all buffer reservations, wait for @bo to become unreserved and - * try again. (only if use_sequence == 1). + * try again. * -ERESTARTSYS: A wait for the buffer to become unreserved was interrupted by * a signal. Release all buffer reservations and return to user-space. * -EBUSY: The function needed to sleep, but @no_wait was true * -EALREADY: Bo already reserved using @ticket. This error code will only * be returned if @use_ticket is set to true. */ -static inline int __ttm_bo_reserve(struct ttm_buffer_object *bo, - bool interruptible, bool no_wait, - struct ww_acquire_ctx *ticket) +static inline int ttm_bo_reserve(struct ttm_buffer_object *bo, +bool interruptible, bool no_wait, +struct ww_acquire_ctx *ticket) { int ret = 0; @@ -641,59 +642,6 @@ static inline int __ttm_bo_reserve(struct ttm_buffer_object *bo, return ret; } -/** - * ttm_bo_reserve: - * - *
Re: [PATCH] dma-buf: heaps: Introduce dma_heap_add_cma() for non-default CMA heap
On Thu, Jul 16, 2020 at 6:10 PM Kunihiko Hayashi wrote: > > Current dma-buf heaps can handle only default CMA. This introduces > dma_heap_add_cma() function to attach CMA heaps that belongs to a device. > > At first, the driver calls of_reserved_mem_device_init() to set > memory-region property associated with reserved-memory defined as CMA > to the device. And when the driver calls this dma_heap_add_cma(), > the CMA will be added to dma-buf heaps. > > For example, prepare CMA node named "linux,cma@1000" and > specify the node for memory-region property. After the above calls > in the driver, a device file "/dev/dma_heap/linux,cma@1000" > associated with the CMA become available as dma-buf heaps. > > Signed-off-by: Kunihiko Hayashi > --- > drivers/dma-buf/heaps/cma_heap.c | 12 > include/linux/dma-heap.h | 9 + > 2 files changed, 21 insertions(+) Hey! Sorry for the slow response on this! I just realized I never replied! > diff --git a/drivers/dma-buf/heaps/cma_heap.c > b/drivers/dma-buf/heaps/cma_heap.c > index 626cf7f..5d2442e 100644 > --- a/drivers/dma-buf/heaps/cma_heap.c > +++ b/drivers/dma-buf/heaps/cma_heap.c > @@ -162,6 +162,18 @@ static int __add_cma_heap(struct cma *cma, void *data) > return 0; > } > > +/* add device CMA heap to dmabuf heaps */ > +int dma_heap_add_cma(struct device *dev) > +{ > + struct cma *cma = dev_get_cma_area(dev); > + > + if (!cma) > + return -ENOMEM; > + > + return __add_cma_heap(cma, NULL); > +} > +EXPORT_SYMBOL_GPL(dma_heap_add_cma); > + > static int add_default_cma_heap(void) > { > struct cma *default_cma = dev_get_cma_area(NULL); > diff --git a/include/linux/dma-heap.h b/include/linux/dma-heap.h > index 454e354..16bec7d 100644 > --- a/include/linux/dma-heap.h > +++ b/include/linux/dma-heap.h > @@ -56,4 +56,13 @@ void *dma_heap_get_drvdata(struct dma_heap *heap); > */ > struct dma_heap *dma_heap_add(const struct dma_heap_export_info *exp_info); > > +#ifdef CONFIG_DMABUF_HEAPS_CMA > +/** > + * dma_heap_add_cma - adds a device CMA heap to dmabuf heaps > + * @dev: device with a CMA heap to register > + */ > +int dma_heap_add_cma(struct device *dev); > + > +#endif /* CONFIG_DMABUF_HEAPS_CMA */ > + > #endif /* _DMA_HEAPS_H */ > -- > 2.7.4 Looks sane to me. Being able to expose different multiple CMA heaps is needed, and I agree this way (as opposed to my earlier dts appraoch) is probably the best approach. The only bit I'm so-so on is adding the CMA heap specific call in the dma-heap.h, but at the same time I can't justify adding a whole new header for a single function. Do you have a upstream driver that you plan to make use this new call? We want to have in-tree users of code added. But if so, feel free to add my: Acked-by: John Stultz To this patch when you submit the driver changes. thanks -john ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH 0/2] Small cleanups to ingenic-drm driver
Here are a few cleanups to the ingenic-drm driver. - some error paths were missing and have been added; - the mode validation has been moved to the .mode_valid helper callback. Cheers, -Paul Paul Cercueil (2): drm/ingenic: Handle errors of drm_atomic_get_plane_state drm/ingenic: Validate mode in a .mode_valid callback drivers/gpu/drm/ingenic/ingenic-drm-drv.c | 41 +++ 1 file changed, 27 insertions(+), 14 deletions(-) -- 2.27.0 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
Re: [PATCH RFC v6 2/6] drm/sprd: add Unisoc's drm kms master
On 7/28/20 3:07 AM, Kevin Tang wrote: > diff --git a/drivers/gpu/drm/sprd/Kconfig b/drivers/gpu/drm/sprd/Kconfig > new file mode 100644 > index 000..b189a54 > --- /dev/null > +++ b/drivers/gpu/drm/sprd/Kconfig > @@ -0,0 +1,12 @@ > +config DRM_SPRD > + tristate "DRM Support for Unisoc SoCs Platform" > + depends on ARCH_SPRD || COMPILE_TEST > + depends on DRM && OF > + select DRM_KMS_HELPER > + select DRM_GEM_CMA_HELPER > + select DRM_KMS_CMA_HELPER > + select DRM_MIPI_DSI > + help > + Choose this option if you have a Unisoc chipsets. chipset. > + If M is selected the module will be called sprd-drm. sprd_drm. > + > diff --git a/drivers/gpu/drm/sprd/Makefile b/drivers/gpu/drm/sprd/Makefile > new file mode 100644 > index 000..86d95d9 > --- /dev/null > +++ b/drivers/gpu/drm/sprd/Makefile > @@ -0,0 +1,5 @@ > +# SPDX-License-Identifier: GPL-2.0 > + > +subdir-ccflags-y += -I$(srctree)/$(src) > + > +obj-y := sprd_drm.o -- ~Randy ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel
[PATCH v2 0/5] make hdmi work on bananapi-r2
This Patch-Series adds missing Patches/Bugfixes to get hdmi working on BPI-R2 This is v2 of series https://patchwork.kernel.org/cover/10903309/ after getting mmsys done v1->v2: - using get_possible_crtc API instead of hardcoded - drop unused dts-nodes - refine commit-messages as far as i can :) "config component output by device node port" is needed to fix a WARN_ON() "fix boot up for 720 and 480 but 1080" fixes flickering, which may cause also some resolutions not working on some TFT (had some problems on my smaller TFT) 2 Patches were already posted, but not yet merged into mainline - config component output by device node port https://patchwork.kernel.org/patch/10609007/ - add display subsystem related device nodes (resend) https://patchwork.kernel.org/patch/10588951/ Bibby Hsieh (1): drm/mediatek: config component output by device node port Jitao Shi (1): drm/mediatek: dpi/dsi: change the getting possible_crtc way Ryder Lee (1): arm: dts: mt7623: add display subsystem related device nodes Stu Hsieh (1): drm: Add get_possible_crtc API for dpi, dsi chunhui dai (1): drm/mediatek: fix boot up for 720 and 480 but 1080 arch/arm/boot/dts/mt7623.dtsi | 177 ++ arch/arm/boot/dts/mt7623n-bananapi-bpi-r2.dts | 85 + arch/arm/boot/dts/mt7623n-rfb-emmc.dts| 85 + drivers/gpu/drm/mediatek/mtk_dpi.c| 3 +- drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.c | 42 + drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.h | 2 + drivers/gpu/drm/mediatek/mtk_drm_drv.c| 46 - drivers/gpu/drm/mediatek/mtk_drm_drv.h| 4 +- drivers/gpu/drm/mediatek/mtk_dsi.c| 3 +- drivers/gpu/drm/mediatek/mtk_hdmi_phy.c | 3 + drivers/gpu/drm/mediatek/mtk_hdmi_phy.h | 1 + .../gpu/drm/mediatek/mtk_mt2701_hdmi_phy.c| 1 + 12 files changed, 442 insertions(+), 10 deletions(-) -- 2.25.1 ___ dri-devel mailing list dri-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/dri-devel