drm/bridge: ti-sn65dsi86: Don't read EDID blob over DDC
Subsystems (2)
Sasha Levin
maintainerPATCH 1/252 drm/bridge: ti-sn65dsi86: Don't read EDID blob over DDC
From: Douglas Anderson <[email protected]>
[ Upstream commit a70e558c151043ce46a5e5999f4310e0b3551f57 ]
This is really just a revert of commit 58074b08c04a ("drm/bridge:
ti-sn65dsi86: Read EDID blob over DDC"), resolving conflicts.
The old code failed to read the EDID properly in a very important
case: before the bridge's pre_enable() was called. The way things need to work:
1. Read the EDID.
2. Based on the EDID, decide on video settings and pixel clock.
3. Enable the bridge w/ the desired settings.
The way things were working:
1. Try to read the EDID but fail; fall back to hardcoded values.
2. Based on hardcoded values, decide on video settings and pixel clock.
3. Enable the bridge w/ the desired settings.
4. Try again to read the EDID, it works now!
5. Realize that the hardcoded settings weren't quite right.
6. Disable / reenable the bridge w/ the right settings.
The reasons for the failures were twofold:
a) Since we never ran the bridge chip's pre-enable then we never set the bit to ignore HPD. This meant the bridge chip didn't even _try_ to go out on the bus and communicate with the panel.
b) Even if we fixed things to ignore HPD, the EDID still wouldn't read if the panel wasn't on.
Instead of reverting the code, we could fix it to set the HPD bit and also power on the panel. However, it also works nicely to just let the panel code read the EDID. Now that we've split the driver up we can expose the DDC AUX channel bus to the panel node. The panel can take charge of reading the EDID.
NOTE: in order for things to work, anyone that needs to read the EDID will need to instantiate their panel using the new DP AUX bus (AKA by listing their panel under the "aux-bus" node of the bridge chip in the device tree).
In the future if we want to use the bridge chip to provide a full external DP port (which won't have a panel) then we will have to conditinally add EDID reading back in.
--- drivers/gpu/drm/bridge/ti-sn65dsi86.c | 22 ---------------------- 1 file changed, 22 deletions(-)
drivers/gpu/drm/bridge/ti-sn65dsi86.c +0 -22
@@ -124,7 +124,6 @@* @connector: Our connector. * @host_node: Remote DSI node. * @dsi: Our MIPI DSI source. -* @edid: Detected EDID of eDP panel. * @refclk: Our reference clock. * @panel: Our panel. * @enable_gpio: The GPIO we toggle to enable the bridge.
@@ -154,7 +153,6 @@ struct ti_sn65dsi86 {struct drm_dp_aux aux;struct drm_bridge bridge;struct drm_connector connector; -struct edid *edid;struct device_node *host_node;struct mipi_dsi_device *dsi;struct clk *refclk;
@@ -403,24 +401,6 @@ connector_to_ti_sn65dsi86(struct drm_connector *connector)static int ti_sn_bridge_connector_get_modes (struct drm_connector *connector) {struct ti_sn65dsi86 *pdata =connector_to_ti_sn65dsi86 (connector); -struct edid *edid = pdata->edid; -int num, ret; - -if (!edid) { -pm_runtime_get_sync (pdata->dev); - edid = pdata->edid =drm_get_edid (connector, &pdata->aux.ddc); -pm_runtime_put_autosuspend (pdata->dev); - } - -if (edid &&drm_edid_is_valid (edid)) { - ret =drm_connector_update_edid_property (connector, edid); -if (!ret) { - num =drm_add_edid_modes (connector, edid); -if (num) -return num; - } - } -return drm_panel_get_modes (pdata->panel, connector); }
@@ -1358,8 +1338,6 @@ static void ti_sn_bridge_remove(struct auxiliary_device *adev)mipi_dsi_device_unregister (pdata->dsi); } -kfree (pdata->edid); -drm_bridge_remove (&pdata->bridge);of_node_put (pdata->host_node);
Signature · 1 line
2.30.2
Sasha Levin
maintainerPATCH 2/252 drm/vmwgfx: Fix subresource updates with new contexts
From: Zack Rusin <[email protected]>
[ Upstream commit a12be0277316ed923411c9c80b2899ee74d2b033 ]
The has_dx variable was only set during the initialization which meant that UPDATE_SUBRESOURCE was never used. We were emulating it with UPDATE_GB_IMAGE but that's always been a stop-gap. Instead of has_dx which has been deprecated a long time ago we need to check for whether shader model 4.0 or newer is available to the device.
--- drivers/gpu/drm/vmwgfx/vmwgfx_surface.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-)
drivers/gpu/drm/vmwgfx/vmwgfx_surface.c +2 -3
@@ -1872,7 +1872,6 @@ static void vmw_surface_dirty_range_add(struct vmw_resource *res, size_t start,static int vmw_surface_dirty_sync (struct vmw_resource *res) {struct vmw_private *dev_priv = res->dev_priv; -bool has_dx =0 ;u32 i, num_dirty;struct vmw_surface_dirty *dirty = (struct vmw_surface_dirty *) res->dirty;
@@ -1899,7 +1898,7 @@ static int vmw_surface_dirty_sync(struct vmw_resource *res)if (!num_dirty) goto out; - alloc_size = num_dirty * ((has_dx) ?sizeof (*cmd1) :sizeof (*cmd2)); + alloc_size = num_dirty * ((has_sm4_context (dev_priv)) ?sizeof (*cmd1) :sizeof (*cmd2)); cmd =VMW_CMD_RESERVE (dev_priv, alloc_size);if (!cmd)return -ENOMEM ;
@@ -1917,7 +1916,7 @@ static int vmw_surface_dirty_sync(struct vmw_resource *res)* DX_UPDATE_SUBRESOURCE is aware of array surfaces. * UPDATE_GB_IMAGE is not. */ -if (has_dx) { +if (has_sm4_context (dev_priv)) { cmd1->header.id =SVGA_3D_CMD_DX_UPDATE_SUBRESOURCE ; cmd1->header.size =sizeof (cmd1->body); cmd1->body.sid = res->id;
Signature · 1 line
2.30.2
Sasha Levin
maintainerPATCH 3/252 drm/vmwgfx: Fix some static checker warnings
In reply to Sasha LevinFrom: Zack Rusin <[email protected]>
[ Upstream commit 74231041d14030f1ae6582b9233bfe782ac23e33 ]
Fix some minor issues that Coverity spotted in the code. None of that are serious but they're all valid concerns so fixing them makes sense.
--- drivers/gpu/drm/vmwgfx/ttm_memory.c | 2 ++ drivers/gpu/drm/vmwgfx/vmwgfx_binding.c | 20 ++++++++------------ drivers/gpu/drm/vmwgfx/vmwgfx_cmdbuf.c | 2 +- drivers/gpu/drm/vmwgfx/vmwgfx_cmdbuf_res.c | 4 +++- drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c | 2 ++ drivers/gpu/drm/vmwgfx/vmwgfx_mob.c | 4 +++- drivers/gpu/drm/vmwgfx/vmwgfx_msg.c | 6 ++++-- drivers/gpu/drm/vmwgfx/vmwgfx_resource.c | 8 ++++++-- drivers/gpu/drm/vmwgfx/vmwgfx_so.c | 3 ++- drivers/gpu/drm/vmwgfx/vmwgfx_validation.c | 4 ++-- 10 files changed, 33 insertions(+), 22 deletions(-)
drivers/gpu/drm/vmwgfx/ttm_memory.c +2 -0
@@ -435,8 +435,10 @@ int ttm_mem_global_init(struct ttm_mem_global *glob, struct device *dev)si_meminfo (&si); +spin_lock (&glob->lock);/* set it as 0 by default to keep original behavior of OOM */ glob->lower_mem_limit =0 ; +spin_unlock (&glob->lock); ret =ttm_mem_init_kernel_zone (glob, &si);if (unlikely (ret !=0 ))
drivers/gpu/drm/vmwgfx/vmwgfx_binding.c +8 -12
@@ -715,7 +715,7 @@ static int vmw_binding_scrub_cb(struct vmw_ctx_bindinfo *bi, bool rebind)* without checking which bindings actually need to be emitted * * @cbs: Pointer to the context's struct vmw_ctx_binding_state -* @bi: Pointer to where the binding info array is stored in @cbs +* @biv: Pointer to where the binding info array is stored in @cbs * @max_num: Maximum number of entries in the @bi array. * * Scans the @bi array for bindings and builds a buffer of view id data.
@@ -725,11 +725,9 @@ static int vmw_binding_scrub_cb(struct vmw_ctx_bindinfo *bi, bool rebind)* contains the command data. */ static void vmw_collect_view_ids (struct vmw_ctx_binding_state *cbs, -const struct vmw_ctx_bindinfo *bi, +const struct vmw_ctx_bindinfo_view *biv,u32 max_num) { -const struct vmw_ctx_bindinfo_view *biv = - container_of(bi, struct vmw_ctx_bindinfo_view, bi);unsigned long i; cbs->bind_cmd_count =0 ;
@@ -838,7 +836,7 @@ static int vmw_emit_set_sr(struct vmw_ctx_binding_state *cbs,*/ static int vmw_emit_set_rt (struct vmw_ctx_binding_state *cbs) { -const struct vmw_ctx_bindinfo *loc = &cbs->render_targets[0 ].bi; +const struct vmw_ctx_bindinfo_view *loc = &cbs->render_targets[0 ];struct {SVGA3dCmdHeader header;SVGA3dCmdDXSetRenderTargets body;
@@ -874,7 +872,7 @@ static int vmw_emit_set_rt(struct vmw_ctx_binding_state *cbs)* without checking which bindings actually need to be emitted * * @cbs: Pointer to the context's struct vmw_ctx_binding_state -* @bi: Pointer to where the binding info array is stored in @cbs +* @biso: Pointer to where the binding info array is stored in @cbs * @max_num: Maximum number of entries in the @bi array. * * Scans the @bi array for bindings and builds a buffer of SVGA3dSoTarget data.
@@ -884,11 +882,9 @@ static int vmw_emit_set_rt(struct vmw_ctx_binding_state *cbs)* contains the command data. */ static void vmw_collect_so_targets (struct vmw_ctx_binding_state *cbs, -const struct vmw_ctx_bindinfo *bi, +const struct vmw_ctx_bindinfo_so_target *biso,u32 max_num) { -const struct vmw_ctx_bindinfo_so_target *biso = - container_of(bi, struct vmw_ctx_bindinfo_so_target, bi);unsigned long i;SVGA3dSoTarget *so_buffer = (SVGA3dSoTarget *) cbs->bind_cmd_buffer;
@@ -919,7 +915,7 @@ static void vmw_collect_so_targets(struct vmw_ctx_binding_state *cbs,*/ static int vmw_emit_set_so_target (struct vmw_ctx_binding_state *cbs) { -const struct vmw_ctx_bindinfo *loc = &cbs->so_targets[0 ].bi; +const struct vmw_ctx_bindinfo_so_target *loc = &cbs->so_targets[0 ];struct {SVGA3dCmdHeader header;SVGA3dCmdDXSetSOTargets body;
@@ -1066,7 +1062,7 @@ static int vmw_emit_set_vb(struct vmw_ctx_binding_state *cbs)static int vmw_emit_set_uav (struct vmw_ctx_binding_state *cbs) { -const struct vmw_ctx_bindinfo *loc = &cbs->ua_views[0 ].views[0 ].bi; +const struct vmw_ctx_bindinfo_view *loc = &cbs->ua_views[0 ].views[0 ];struct {SVGA3dCmdHeader header;SVGA3dCmdDXSetUAViews body;
@@ -1096,7 +1092,7 @@ static int vmw_emit_set_uav(struct vmw_ctx_binding_state *cbs)static int vmw_emit_set_cs_uav (struct vmw_ctx_binding_state *cbs) { -const struct vmw_ctx_bindinfo *loc = &cbs->ua_views[1 ].views[0 ].bi; +const struct vmw_ctx_bindinfo_view *loc = &cbs->ua_views[1 ].views[0 ];struct {SVGA3dCmdHeader header;SVGA3dCmdDXSetCSUAViews body;
drivers/gpu/drm/vmwgfx/vmwgfx_cmdbuf.c +1 -1
@@ -516,7 +516,7 @@ static void vmw_cmdbuf_work_func(struct work_struct *work)struct vmw_cmdbuf_man *man = container_of(work, struct vmw_cmdbuf_man, work);struct vmw_cmdbuf_header *entry, *next; -uint32_t dummy; +uint32_t dummy =0 ;bool send_fence = false;struct list_head restart_head[SVGA_CB_CONTEXT_MAX ];int i;
drivers/gpu/drm/vmwgfx/vmwgfx_cmdbuf_res.c +3 -1
@@ -159,6 +159,7 @@ void vmw_cmdbuf_res_commit(struct list_head *list)void vmw_cmdbuf_res_revert (struct list_head *list) {struct vmw_cmdbuf_res *entry, *next; +int ret;list_for_each_entry_safe (entry, next, list, head) {switch (entry->state) {
@@ -166,7 +167,8 @@ void vmw_cmdbuf_res_revert(struct list_head *list)vmw_cmdbuf_res_free (entry->man, entry);break ;case VMW_CMDBUF_RES_DEL : -drm_ht_insert_item (&entry->man->resources, &entry->hash); + ret =drm_ht_insert_item (&entry->man->resources, &entry->hash); +BUG_ON (ret);list_del (&entry->head);list_add_tail (&entry->head, &entry->man->list); entry->state =VMW_CMDBUF_RES_COMMITTED ;
drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c +2 -0
@@ -2546,6 +2546,8 @@ static int vmw_cmd_dx_so_define(struct vmw_private *dev_priv, so_type =vmw_so_cmd_to_type (header->id); res =vmw_context_cotable (ctx_node->ctx, vmw_so_cotables[so_type]); +if (IS_ERR (res)) +return PTR_ERR (res); cmd =container_of (header,typeof (*cmd), header); ret =vmw_cotable_notify (res, cmd->defined_id);
drivers/gpu/drm/vmwgfx/vmwgfx_mob.c +3 -1
@@ -506,11 +506,13 @@ static void vmw_mob_pt_setup(struct vmw_mob *mob, {unsigned long num_pt_pages =0 ;struct ttm_buffer_object *bo = mob->pt_bo; -struct vmw_piter save_pt_iter; +struct vmw_piter save_pt_iter = {0 };struct vmw_piter pt_iter;const struct vmw_sg_table *vsgt;int ret; +BUG_ON (num_data_pages ==0 ); + ret =ttm_bo_reserve (bo, false, true,NULL );BUG_ON (ret !=0 );
drivers/gpu/drm/vmwgfx/vmwgfx_msg.c +4 -2
@@ -155,6 +155,7 @@ static unsigned long vmw_port_hb_out(struct rpc_channel *channel,/* HB port can't access encrypted memory. */ if (hb && !mem_encrypt_active ()) {unsigned long bp = channel->cookie_high; +u32 channel_id = (channel->channel_id <<16 ); si = (uintptr_t ) msg; di = channel->cookie_low;
@@ -162,7 +163,7 @@ static unsigned long vmw_port_hb_out(struct rpc_channel *channel,VMW_PORT_HB_OUT ( (MESSAGE_STATUS_SUCCESS <<16 ) |VMW_PORT_CMD_HB_MSG , msg_len, si, di, -VMWARE_HYPERVISOR_HB | (channel->channel_id <<16 ) | +VMWARE_HYPERVISOR_HB | channel_id |VMWARE_HYPERVISOR_OUT ,VMW_HYPERVISOR_MAGIC , bp, eax, ebx, ecx, edx, si, di);
@@ -210,6 +211,7 @@ static unsigned long vmw_port_hb_in(struct rpc_channel *channel, char *reply,/* HB port can't access encrypted memory */ if (hb && !mem_encrypt_active ()) {unsigned long bp = channel->cookie_low; +u32 channel_id = (channel->channel_id <<16 ); si = channel->cookie_high; di = (uintptr_t ) reply;
@@ -217,7 +219,7 @@ static unsigned long vmw_port_hb_in(struct rpc_channel *channel, char *reply,VMW_PORT_HB_IN ( (MESSAGE_STATUS_SUCCESS <<16 ) |VMW_PORT_CMD_HB_MSG , reply_len, si, di, -VMWARE_HYPERVISOR_HB | (channel->channel_id <<16 ), +VMWARE_HYPERVISOR_HB | channel_id,VMW_HYPERVISOR_MAGIC , bp, eax, ebx, ecx, edx, si, di);
drivers/gpu/drm/vmwgfx/vmwgfx_resource.c +6 -2
@@ -114,6 +114,7 @@ static void vmw_resource_release(struct kref *kref) container_of(kref, struct vmw_resource, kref);struct vmw_private *dev_priv = res->dev_priv;int id; +int ret;struct idr *idr = &dev_priv->res_idr[res->func->res_type];spin_lock (&dev_priv->resource_lock);
@@ -122,7 +123,8 @@ static void vmw_resource_release(struct kref *kref)if (res->backup) {struct ttm_buffer_object *bo = &res->backup->base; -ttm_bo_reserve (bo, false, false,NULL ); + ret =ttm_bo_reserve (bo, false, false,NULL ); +BUG_ON (ret);if (vmw_resource_mob_attached (res) && res->func->unbind !=NULL ) {struct ttm_validate_buffer val_buf;
@@ -1001,7 +1003,9 @@ int vmw_resource_pin(struct vmw_resource *res, bool interruptible)if (res->backup) { vbo = res->backup; -ttm_bo_reserve (&vbo->base, interruptible, false,NULL ); + ret =ttm_bo_reserve (&vbo->base, interruptible, false,NULL ); +if (ret) + goto out_no_validate;if (!vbo->base.pin_count) { ret = ttm_bo_validate (&vbo->base,
drivers/gpu/drm/vmwgfx/vmwgfx_so.c +2 -1
@@ -539,7 +539,8 @@ const SVGACOTableType vmw_so_cotables[] = { [vmw_so_ds] = SVGA_COTABLE_DEPTHSTENCIL, [vmw_so_rs] = SVGA_COTABLE_RASTERIZERSTATE, [vmw_so_ss] = SVGA_COTABLE_SAMPLER, - [vmw_so_so] = SVGA_COTABLE_STREAMOUTPUT + [vmw_so_so] = SVGA_COTABLE_STREAMOUTPUT, + [vmw_so_max]= SVGA_COTABLE_MAX };
drivers/gpu/drm/vmwgfx/vmwgfx_validation.c +2 -2
@@ -586,13 +586,13 @@ int vmw_validation_bo_validate(struct vmw_validation_context *ctx, bool intr)container_of (entry->base.bo,typeof (*vbo), base);if (entry->cpu_blit) { -struct ttm_operation_ctx ctx = { +struct ttm_operation_ctx ttm_ctx = { .interruptible = intr, .no_wait_gpu = false }; ret =ttm_bo_validate (entry->base.bo, - &vmw_nonfixed_placement, &ctx); + &vmw_nonfixed_placement, &ttm_ctx); }else { ret =vmw_validation_bo_validate_single (entry->base.bo, intr, entry->as_mob);
Signature · 1 line
2.30.2
Sasha Levin
maintainerPATCH 4/252 drm/vc4: hdmi: Set HD_CTL_WHOLSMP and HD_CTL_CHALIGN_SET
In reply to Sasha LevinFrom: Dom Cobley <[email protected]>
[ Upstream commit 1698ecb218eb82587dbfc71a2e26ded66e5ecf59 ]
Symptom is random switching of speakers when using multichannel.
Repeatedly running speakertest -c8 occasionally starts with channels jumbled. This is fixed with HD_CTL_WHOLSMP.
The other bit looks beneficial and apears harmless in testing so I'd suggest adding it too.
Documentation says: HD_CTL_WHILSMP_SET
Wait for whole sample. When this bit is set MAI transmit will start only when there is at least one whole sample available in the fifo.
Documentation says: HD_CTL_CHALIGN_SET
Channel Align When Overflow. This bit is used to realign the audio channels in case of an overflow.
If this bit is set, after the detection of an overflow, equal amount of dummy words to the missing words will be written to fifo, filling up the broken sample and maintaining alignment.
--- drivers/gpu/drm/vc4/vc4_hdmi.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/gpu/drm/vc4/vc4_hdmi.c +3 -1
@@ -1372,7 +1372,9 @@ static int vc4_hdmi_audio_trigger(struct snd_pcm_substream *substream, int cmd,HDMI_WRITE (HDMI_MAI_CTL ,VC4_SET_FIELD (vc4_hdmi->audio.channels,VC4_HD_MAI_CTL_CHNUM ) | -VC4_HD_MAI_CTL_ENABLE ); +VC4_HD_MAI_CTL_WHOLSMP | +VC4_HD_MAI_CTL_CHALIGN | +VC4_HD_MAI_CTL_ENABLE );break ;case SNDRV_PCM_TRIGGER_STOP : HDMI_WRITE(HDMI_MAI_CTL,
Signature · 1 line
2.30.2
Sasha Levin
maintainerPATCH 5/252 drm/ttm: Fix multihop assert on eviction.
In reply to Sasha LevinFrom: Andrey Grodzovsky <[email protected]>
[ Upstream commit 403797925768d9fa870f5b1ebcd20016b397083b ]
Problem:
Under memory pressure when GTT domain is almost full multihop assert will come up when trying to evict LRU BO from VRAM to SYSTEM.
Fix:
Don't assert on multihop error in evict code but rather do a retry as we do in ttm_bo_move_buffer
--- drivers/gpu/drm/ttm/ttm_bo.c | 63 +++++++++++++++++++----------------- 1 file changed, 34 insertions(+), 29 deletions(-)
drivers/gpu/drm/ttm/ttm_bo.c +34 -29
@@ -488,6 +488,31 @@ void ttm_bo_unlock_delayed_workqueue(struct ttm_device *bdev, int resched) }EXPORT_SYMBOL (ttm_bo_unlock_delayed_workqueue); +static int ttm_bo_bounce_temp_buffer (struct ttm_buffer_object *bo, +struct ttm_resource **mem, +struct ttm_operation_ctx *ctx, +struct ttm_place *hop) +{ +struct ttm_placement hop_placement; +struct ttm_resource *hop_mem; +int ret; + + hop_placement.num_placement = hop_placement.num_busy_placement =1 ; + hop_placement.placement = hop_placement.busy_placement = hop; + +/* find space in the bounce domain */ + ret =ttm_bo_mem_space (bo, &hop_placement, &hop_mem, ctx); +if (ret) +return ret; +/* move to the bounce domain */ + ret =ttm_bo_handle_move_mem (bo, hop_mem, false, ctx,NULL ); +if (ret) { +ttm_resource_free (bo, &hop_mem); +return ret; + } +return 0 ; +} +static int ttm_bo_evict (struct ttm_buffer_object *bo,struct ttm_operation_ctx *ctx) {
@@ -527,12 +552,17 @@ static int ttm_bo_evict(struct ttm_buffer_object *bo, goto out; } +bounce: ret =ttm_bo_handle_move_mem (bo, evict_mem, true, ctx, &hop); -if (unlikely (ret)) { -WARN (ret == -EMULTIHOP ,"Unexpected multihop in eviction - likely driver bug\n" ); -if (ret != -ERESTARTSYS ) +if (ret == -EMULTIHOP ) { + ret =ttm_bo_bounce_temp_buffer (bo, &evict_mem, ctx, &hop); +if (ret) {pr_err ("Buffer eviction failed\n" ); -ttm_resource_free (bo, &evict_mem); +ttm_resource_free (bo, &evict_mem); + goto out; + } +/* try and move to final place now. */ + goto bounce; } out:return ret;
@@ -847,31 +877,6 @@ int ttm_bo_mem_space(struct ttm_buffer_object *bo, }EXPORT_SYMBOL (ttm_bo_mem_space); -static int ttm_bo_bounce_temp_buffer (struct ttm_buffer_object *bo, -struct ttm_resource **mem, -struct ttm_operation_ctx *ctx, -struct ttm_place *hop) -{ -struct ttm_placement hop_placement; -struct ttm_resource *hop_mem; -int ret; - - hop_placement.num_placement = hop_placement.num_busy_placement =1 ; - hop_placement.placement = hop_placement.busy_placement = hop; - -/* find space in the bounce domain */ - ret =ttm_bo_mem_space (bo, &hop_placement, &hop_mem, ctx); -if (ret) -return ret; -/* move to the bounce domain */ - ret =ttm_bo_handle_move_mem (bo, hop_mem, false, ctx,NULL ); -if (ret) { -ttm_resource_free (bo, &hop_mem); -return ret; - } -return 0 ; -} -static int ttm_bo_move_buffer (struct ttm_buffer_object *bo,struct ttm_placement *placement,struct ttm_operation_ctx *ctx)
Signature · 1 line
2.30.2
Sasha Levin
maintainerPATCH 6/252 drm/omap: Follow implicit fencing in prepare_fb
In reply to Sasha LevinFrom: Daniel Vetter <[email protected]>
[ Upstream commit 942d8344d5f14b9ea2ae43756f319b9f44216ba4 ]
I guess no one ever tried running omap together with lima or panfrost, not even sure that's possible. Anyway for consistency, fix this.
--- drivers/gpu/drm/omapdrm/omap_plane.c | 3 +++ 1 file changed, 3 insertions(+)
drivers/gpu/drm/omapdrm/omap_plane.c +3 -0
@@ -6,6 +6,7 @@#include <drm/drm_atomic.h> #include <drm/drm_atomic_helper.h> +#include <drm/drm_gem_atomic_helper.h> #include <drm/drm_plane_helper.h> #include "omap_dmm_tiler.h"
@@ -29,6 +30,8 @@ static int omap_plane_prepare_fb(struct drm_plane *plane,if (!new_state->fb)return 0 ; +drm_gem_plane_helper_prepare_fb (plane, new_state); +return omap_framebuffer_pin (new_state->fb); }
Signature · 1 line
2.30.2
Sasha Levin
maintainerPATCH 7/252 drm/amdgpu: Fix amdgpu_ras_eeprom_init()
In reply to Sasha LevinFrom: Luben Tuikov <[email protected]>
[ Upstream commit dce4400e6516d18313d23de45b5be8a18980b00e ]
No need to account for the 2 bytes of EEPROM address--this is now well abstracted away by the fixes the the lower layers.
--- drivers/gpu/drm/amd/amdgpu/amdgpu_ras_eeprom.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/gpu/drm/amd/amdgpu/amdgpu_ras_eeprom.c +1 -1
@@ -325,7 +325,7 @@ int amdgpu_ras_eeprom_init(struct amdgpu_ras_eeprom_control *control,return ret; } -__decode_table_header_from_buff (hdr, &buff[2 ]); +__decode_table_header_from_buff (hdr, buff);if (hdr->header ==EEPROM_TABLE_HDR_VAL ) { control->num_recs = (hdr->tbl_size - EEPROM_TABLE_HEADER_SIZE) /
Signature · 1 line
2.30.2
Sasha Levin
maintainerPATCH 8/252 drm/amdgpu: Fix koops when accessing RAS EEPROM
In reply to Sasha LevinFrom: Luben Tuikov <[email protected]>
[ Upstream commit 1d9d2ca85b32605ac9c74c8fa42d0c1cfbe019d4 ]
Debugfs RAS EEPROM files are available when the ASIC supports RAS, and when the debugfs is enabled, an also when "ras_enable" module parameter is set to 0. However in this case, we get a kernel oops when accessing some of the "ras_..." controls in debugfs. The reason for this is that struct amdgpu_ras::adev is unset. This commit sets it, thus enabling access to those facilities. Note that this facilitates EEPROM access and not necessarily RAS features or functionality.
--- drivers/gpu/drm/amd/amdgpu/amdgpu_ras.c | 16 ++++++++++++---- 1 file changed, 12 insertions(+), 4 deletions(-)
drivers/gpu/drm/amd/amdgpu/amdgpu_ras.c +12 -4
@@ -1966,11 +1966,20 @@ int amdgpu_ras_recovery_init(struct amdgpu_device *adev)bool exc_err_limit = false;int ret; -if (adev->ras_enabled && con) - data = &con->eh_data; -else +if (!con) +return 0 ; + +/* Allow access to RAS EEPROM via debugfs, when the ASIC +* supports RAS and debugfs is enabled, but when +* adev->ras_enabled is unset, i.e. when "ras_enable" +* module parameter is set to 0. +*/ + con->adev = adev; + +if (!adev->ras_enabled)return 0 ; + data = &con->eh_data; *data =kmalloc (sizeof (**data),GFP_KERNEL | __GFP_ZERO);if (!*data) { ret = -ENOMEM ;
@@ -1980,7 +1989,6 @@ int amdgpu_ras_recovery_init(struct amdgpu_device *adev)mutex_init (&con->recovery_lock);INIT_WORK (&con->recovery_work, amdgpu_ras_do_recovery);atomic_set (&con->in_recovery,0 ); - con->adev = adev; max_eeprom_records_len =amdgpu_ras_eeprom_get_record_max_length ();amdgpu_ras_validate_threshold (adev, max_eeprom_records_len);
Signature · 1 line
2.30.2
Sasha Levin
maintainerPATCH 9/252 drm: vc4: Fix pixel-wrap issue with DVP teardown
In reply to Sasha LevinFrom: Tim Gover <[email protected]>
[ Upstream commit 0b066a6809d0f8fd9868e383add36aa5a2fa409d ]
Adjust the DVP enable/disable sequence to avoid a pixel getting stuck in an internal, non resettable FIFO within PixelValve when changing HDMI resolution.
The blank pixels features of the DVP can prevent signals back to pixelvalve causing it to not clear the FIFO. Adjust the ordering and timing of operations to ensure the clear signal makes it through to pixelvalve.
--- drivers/gpu/drm/vc4/vc4_hdmi.c | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-)
drivers/gpu/drm/vc4/vc4_hdmi.c +8 -7
@@ -613,12 +613,12 @@ static void vc4_hdmi_encoder_post_crtc_disable(struct drm_encoder *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_CLRRGB ); -HDMI_WRITE (HDMI_VID_CTL , -HDMI_READ (HDMI_VID_CTL ) |VC4_HD_VID_CTL_BLANKPIX ); +mdelay (1 ); +HDMI_WRITE (HDMI_VID_CTL , +HDMI_READ (HDMI_VID_CTL ) & ~VC4_HD_VID_CTL_ENABLE );vc4_hdmi_disable_scrambling (encoder); }
@@ -628,12 +628,12 @@ static void vc4_hdmi_encoder_post_crtc_powerdown(struct drm_encoder *encoder,struct vc4_hdmi *vc4_hdmi =encoder_to_vc4_hdmi (encoder);int ret; +HDMI_WRITE (HDMI_VID_CTL , +HDMI_READ (HDMI_VID_CTL ) |VC4_HD_VID_CTL_BLANKPIX ); +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 ); -clk_disable_unprepare (vc4_hdmi->pixel_bvb_clock);clk_disable_unprepare (vc4_hdmi->pixel_clock);
@@ -1015,6 +1015,7 @@ static void vc4_hdmi_encoder_post_crtc_enable(struct drm_encoder *encoder, HDMI_WRITE(HDMI_VID_CTL, VC4_HD_VID_CTL_ENABLE | + VC4_HD_VID_CTL_CLRRGB | VC4_HD_VID_CTL_UNDERFLOW_ENABLE | VC4_HD_VID_CTL_FRAME_COUNTER_RESET | (vsync_pos ? 0 : VC4_HD_VID_CTL_VSYNC_LOW) |
Signature · 1 line
2.30.2
Sasha Levin
maintainerPATCH 10/252 dma-buf: fix dma_resv_test_signaled test_all handling v2
In reply to Sasha LevinFrom: Christian König <[email protected]>
[ Upstream commit 9d38814d1e346ea37a51cbf31f4424c9d059459e ]
As the name implies if testing all fences is requested we should indeed test all fences and not skip the exclusive one because we see shared ones.
v2: fix logic once more
--- drivers/dma-buf/dma-resv.c | 33 ++++++++++++--------------------- 1 file changed, 12 insertions(+), 21 deletions(-)
drivers/dma-buf/dma-resv.c +12 -21
@@ -615,25 +615,21 @@ static inline int dma_resv_test_signaled_single(struct dma_fence *passed_fence)*/ bool dma_resv_test_signaled (struct dma_resv *obj,bool test_all) { -unsigned int seq, shared_count; +struct dma_fence *fence; +unsigned int seq;int ret;rcu_read_lock (); retry: ret = true; - shared_count =0 ; seq =read_seqcount_begin (&obj->seq);if (test_all) {struct dma_resv_list *fobj =dma_resv_shared_list (obj); -unsigned int i; - -if (fobj) - shared_count = fobj->shared_count; +unsigned int i, shared_count; + shared_count = fobj ? fobj->shared_count :0 ;for (i =0 ; i < shared_count; ++i) { -struct dma_fence *fence; - fence =rcu_dereference (fobj->shared[i]); ret =dma_resv_test_signaled_single (fence);if (ret <0 )
@@ -641,24 +637,19 @@ bool dma_resv_test_signaled(struct dma_resv *obj, bool test_all)else if (!ret)break ; } - -if (read_seqcount_retry (&obj->seq, seq)) - goto retry; } -if (!shared_count) { -struct dma_fence *fence_excl =dma_resv_excl_fence (obj); - -if (fence_excl) { - ret =dma_resv_test_signaled_single (fence_excl); -if (ret <0 ) - goto retry; + fence =dma_resv_excl_fence (obj); +if (ret && fence) { + ret =dma_resv_test_signaled_single (fence); +if (ret <0 ) + goto retry; -if (read_seqcount_retry (&obj->seq, seq)) - goto retry; - } } +if (read_seqcount_retry (&obj->seq, seq)) + goto retry; +rcu_read_unlock ();return ret; }
Signature · 1 line
2.30.2
Hi,
Quoted 45 lines · Sasha Levin
From: Douglas Anderson <[email protected]>
[ Upstream commit
a70e558c151043ce46a5e5999f4310e0b3551f57]This is really just a revert of commit
58074b08c04a("drm/bridge:
ti-sn65dsi86: Read EDID blob over DDC"), resolving conflicts.The old code failed to read the EDID properly in a very important
case: before the bridge'spre_enable()was called. The way things need to work:
1. Read the EDID.
2. Based on the EDID, decide on video settings and pixel clock.
3. Enable the bridge w/ the desired settings.The way things were working:
1. Try to read the EDID but fail; fall back to hardcoded values.
2. Based on hardcoded values, decide on video settings and pixel clock.
3. Enable the bridge w/ the desired settings.
4. Try again to read the EDID, it works now!
5. Realize that the hardcoded settings weren't quite right.
6. Disable / reenable the bridge w/ the right settings.The reasons for the failures were twofold:
a) Since we never ran the bridge chip's pre-enable then we never set the bit to ignore HPD. This meant the bridge chip didn't even _try_ to go out on the bus and communicate with the panel.
b) Even if we fixed things to ignore HPD, the EDID still wouldn't read if the panel wasn't on.Instead of reverting the code, we could fix it to set the HPD bit and also power on the panel. However, it also works nicely to just let the panel code read the EDID. Now that we've split the driver up we can expose the DDC AUX channel bus to the panel node. The panel can take charge of reading the EDID.
NOTE: in order for things to work, anyone that needs to read the EDID will need to instantiate their panel using the new DP AUX bus (AKA by listing their panel under the "aux-bus" node of the bridge chip in the device tree).
In the future if we want to use the bridge chip to provide a full external DP port (which won't have a panel) then we will have to conditinally add EDID reading back in.
Quoted 8 lines
Suggested-by Andrzej Hajda <[email protected]>Signed-off-by Douglas Anderson <[email protected]>Reviewed-by Bjorn Andersson <[email protected]>Signed-off-by Sasha Levin <[email protected]>--- drivers/gpu/drm/bridge/ti-sn65dsi86.c | 22 ---------------------- 1 file changed, 22 deletions(-)
I would suggest against backporting this one unless you're going to backport the whole pile of DP AUX bus patches, which probably doesn't make sense for stable. Even though the old EDID reading was broken for the first read, it still worked for later reads. ...and the first read didn't crash or anything--it just timed out.
-Doug