Commit 88825726 authored by Linus Torvalds's avatar Linus Torvalds

Merge tag 'drm-fixes-2020-07-17-1' of git://anongit.freedesktop.org/drm/drm into master

Pull drm fixes from Dave Airlie:
 "Weekly fixes pull, big bigger than I'd normally like, but they are
  fairly scattered and small individually.

  The vmwgfx one is a black screen regression, otherwise the largest is
  an MST encoder fix for amdgpu which results in a WARN in some cases,
  and a scattering of i915 fixes.

  I'm tracking two regressions at the moment that hopefully we get
  nailed down this week for rc7.

  dma-buf:
   - sleeping atomic fix

  amdgpu:
   - Fix a race condition with KIQ
   - Preemption fix
   - Fix handling of fake MST encoders
   - OLED panel fix
   - Handle allocation failure in stream construction
   - Renoir SMC fix
   - SDMA 5.x fix

  i915:
   - FBC w/a stride fix
   - Fix use-after-free fix on module reload
   - Ignore irq enabling on the virtual engines to fix device sleep
   - Use GTT when saving/restoring engine GPR
   - Fix selftest sort function

  vmwgfx:
   - black screen fix

  aspeed:
   - fbcon init warn fix"

* tag 'drm-fixes-2020-07-17-1' of git://anongit.freedesktop.org/drm/drm:
  drm/amdgpu/sdma5: fix wptr overwritten in ->get_wptr()
  drm/amdgpu/powerplay: Modify SMC message name for setting power profile mode
  drm/amd/display: handle failed allocation during stream construction
  drm/amd/display: OLED panel backlight adjust not work with external display connected
  drm/amdgpu/display: create fake mst encoders ahead of time (v4)
  drm/amdgpu: fix preemption unit test
  drm/amdgpu/gfx10: fix race condition for kiq
  drm/i915: Recalculate FBC w/a stride when needed
  drm/i915: Move cec_notifier to intel_hdmi_connector_unregister, v2.
  drm/i915/gt: Only swap to a random sibling once upon creation
  drm/i915/gt: Ignore irq enabling on the virtual engines
  drm/i915/perf: Use GTT when saving/restoring engine GPR
  drm/i915/selftests: Fix compare functions provided for sorting
  drm/vmwgfx: fix update of display surface when resolution changes
  dmabuf: use spinlock to access dmabuf->name
  drm/aspeed: Call drm_fbdev_generic_setup after drm_dev_register
parents 07a56bb8 adbe8a3c
...@@ -45,10 +45,10 @@ static char *dmabuffs_dname(struct dentry *dentry, char *buffer, int buflen) ...@@ -45,10 +45,10 @@ static char *dmabuffs_dname(struct dentry *dentry, char *buffer, int buflen)
size_t ret = 0; size_t ret = 0;
dmabuf = dentry->d_fsdata; dmabuf = dentry->d_fsdata;
dma_resv_lock(dmabuf->resv, NULL); spin_lock(&dmabuf->name_lock);
if (dmabuf->name) if (dmabuf->name)
ret = strlcpy(name, dmabuf->name, DMA_BUF_NAME_LEN); ret = strlcpy(name, dmabuf->name, DMA_BUF_NAME_LEN);
dma_resv_unlock(dmabuf->resv); spin_unlock(&dmabuf->name_lock);
return dynamic_dname(dentry, buffer, buflen, "/%s:%s", return dynamic_dname(dentry, buffer, buflen, "/%s:%s",
dentry->d_name.name, ret > 0 ? name : ""); dentry->d_name.name, ret > 0 ? name : "");
...@@ -338,8 +338,10 @@ static long dma_buf_set_name(struct dma_buf *dmabuf, const char __user *buf) ...@@ -338,8 +338,10 @@ static long dma_buf_set_name(struct dma_buf *dmabuf, const char __user *buf)
kfree(name); kfree(name);
goto out_unlock; goto out_unlock;
} }
spin_lock(&dmabuf->name_lock);
kfree(dmabuf->name); kfree(dmabuf->name);
dmabuf->name = name; dmabuf->name = name;
spin_unlock(&dmabuf->name_lock);
out_unlock: out_unlock:
dma_resv_unlock(dmabuf->resv); dma_resv_unlock(dmabuf->resv);
...@@ -402,10 +404,10 @@ static void dma_buf_show_fdinfo(struct seq_file *m, struct file *file) ...@@ -402,10 +404,10 @@ static void dma_buf_show_fdinfo(struct seq_file *m, struct file *file)
/* Don't count the temporary reference taken inside procfs seq_show */ /* Don't count the temporary reference taken inside procfs seq_show */
seq_printf(m, "count:\t%ld\n", file_count(dmabuf->file) - 1); seq_printf(m, "count:\t%ld\n", file_count(dmabuf->file) - 1);
seq_printf(m, "exp_name:\t%s\n", dmabuf->exp_name); seq_printf(m, "exp_name:\t%s\n", dmabuf->exp_name);
dma_resv_lock(dmabuf->resv, NULL); spin_lock(&dmabuf->name_lock);
if (dmabuf->name) if (dmabuf->name)
seq_printf(m, "name:\t%s\n", dmabuf->name); seq_printf(m, "name:\t%s\n", dmabuf->name);
dma_resv_unlock(dmabuf->resv); spin_unlock(&dmabuf->name_lock);
} }
static const struct file_operations dma_buf_fops = { static const struct file_operations dma_buf_fops = {
...@@ -542,6 +544,7 @@ struct dma_buf *dma_buf_export(const struct dma_buf_export_info *exp_info) ...@@ -542,6 +544,7 @@ struct dma_buf *dma_buf_export(const struct dma_buf_export_info *exp_info)
dmabuf->size = exp_info->size; dmabuf->size = exp_info->size;
dmabuf->exp_name = exp_info->exp_name; dmabuf->exp_name = exp_info->exp_name;
dmabuf->owner = exp_info->owner; dmabuf->owner = exp_info->owner;
spin_lock_init(&dmabuf->name_lock);
init_waitqueue_head(&dmabuf->poll); init_waitqueue_head(&dmabuf->poll);
dmabuf->cb_excl.poll = dmabuf->cb_shared.poll = &dmabuf->poll; dmabuf->cb_excl.poll = dmabuf->cb_shared.poll = &dmabuf->poll;
dmabuf->cb_excl.active = dmabuf->cb_shared.active = 0; dmabuf->cb_excl.active = dmabuf->cb_shared.active = 0;
......
...@@ -1295,27 +1295,37 @@ static void amdgpu_ib_preempt_job_recovery(struct drm_gpu_scheduler *sched) ...@@ -1295,27 +1295,37 @@ static void amdgpu_ib_preempt_job_recovery(struct drm_gpu_scheduler *sched)
static void amdgpu_ib_preempt_mark_partial_job(struct amdgpu_ring *ring) static void amdgpu_ib_preempt_mark_partial_job(struct amdgpu_ring *ring)
{ {
struct amdgpu_job *job; struct amdgpu_job *job;
struct drm_sched_job *s_job; struct drm_sched_job *s_job, *tmp;
uint32_t preempt_seq; uint32_t preempt_seq;
struct dma_fence *fence, **ptr; struct dma_fence *fence, **ptr;
struct amdgpu_fence_driver *drv = &ring->fence_drv; struct amdgpu_fence_driver *drv = &ring->fence_drv;
struct drm_gpu_scheduler *sched = &ring->sched; struct drm_gpu_scheduler *sched = &ring->sched;
bool preempted = true;
if (ring->funcs->type != AMDGPU_RING_TYPE_GFX) if (ring->funcs->type != AMDGPU_RING_TYPE_GFX)
return; return;
preempt_seq = le32_to_cpu(*(drv->cpu_addr + 2)); preempt_seq = le32_to_cpu(*(drv->cpu_addr + 2));
if (preempt_seq <= atomic_read(&drv->last_seq)) if (preempt_seq <= atomic_read(&drv->last_seq)) {
return; preempted = false;
goto no_preempt;
}
preempt_seq &= drv->num_fences_mask; preempt_seq &= drv->num_fences_mask;
ptr = &drv->fences[preempt_seq]; ptr = &drv->fences[preempt_seq];
fence = rcu_dereference_protected(*ptr, 1); fence = rcu_dereference_protected(*ptr, 1);
no_preempt:
spin_lock(&sched->job_list_lock); spin_lock(&sched->job_list_lock);
list_for_each_entry(s_job, &sched->ring_mirror_list, node) { list_for_each_entry_safe(s_job, tmp, &sched->ring_mirror_list, node) {
if (dma_fence_is_signaled(&s_job->s_fence->finished)) {
/* remove job from ring_mirror_list */
list_del_init(&s_job->node);
sched->ops->free_job(s_job);
continue;
}
job = to_amdgpu_job(s_job); job = to_amdgpu_job(s_job);
if (job->fence == fence) if (preempted && job->fence == fence)
/* mark the job as preempted */ /* mark the job as preempted */
job->preemption_status |= AMDGPU_IB_PREEMPTED; job->preemption_status |= AMDGPU_IB_PREEMPTED;
} }
......
...@@ -7513,12 +7513,17 @@ static int gfx_v10_0_ring_preempt_ib(struct amdgpu_ring *ring) ...@@ -7513,12 +7513,17 @@ static int gfx_v10_0_ring_preempt_ib(struct amdgpu_ring *ring)
struct amdgpu_device *adev = ring->adev; struct amdgpu_device *adev = ring->adev;
struct amdgpu_kiq *kiq = &adev->gfx.kiq; struct amdgpu_kiq *kiq = &adev->gfx.kiq;
struct amdgpu_ring *kiq_ring = &kiq->ring; struct amdgpu_ring *kiq_ring = &kiq->ring;
unsigned long flags;
if (!kiq->pmf || !kiq->pmf->kiq_unmap_queues) if (!kiq->pmf || !kiq->pmf->kiq_unmap_queues)
return -EINVAL; return -EINVAL;
if (amdgpu_ring_alloc(kiq_ring, kiq->pmf->unmap_queues_size)) spin_lock_irqsave(&kiq->ring_lock, flags);
if (amdgpu_ring_alloc(kiq_ring, kiq->pmf->unmap_queues_size)) {
spin_unlock_irqrestore(&kiq->ring_lock, flags);
return -ENOMEM; return -ENOMEM;
}
/* assert preemption condition */ /* assert preemption condition */
amdgpu_ring_set_preempt_cond_exec(ring, false); amdgpu_ring_set_preempt_cond_exec(ring, false);
...@@ -7529,6 +7534,8 @@ static int gfx_v10_0_ring_preempt_ib(struct amdgpu_ring *ring) ...@@ -7529,6 +7534,8 @@ static int gfx_v10_0_ring_preempt_ib(struct amdgpu_ring *ring)
++ring->trail_seq); ++ring->trail_seq);
amdgpu_ring_commit(kiq_ring); amdgpu_ring_commit(kiq_ring);
spin_unlock_irqrestore(&kiq->ring_lock, flags);
/* poll the trailing fence */ /* poll the trailing fence */
for (i = 0; i < adev->usec_timeout; i++) { for (i = 0; i < adev->usec_timeout; i++) {
if (ring->trail_seq == if (ring->trail_seq ==
......
...@@ -314,30 +314,20 @@ static uint64_t sdma_v5_0_ring_get_rptr(struct amdgpu_ring *ring) ...@@ -314,30 +314,20 @@ static uint64_t sdma_v5_0_ring_get_rptr(struct amdgpu_ring *ring)
static uint64_t sdma_v5_0_ring_get_wptr(struct amdgpu_ring *ring) static uint64_t sdma_v5_0_ring_get_wptr(struct amdgpu_ring *ring)
{ {
struct amdgpu_device *adev = ring->adev; struct amdgpu_device *adev = ring->adev;
u64 *wptr = NULL; u64 wptr;
uint64_t local_wptr = 0;
if (ring->use_doorbell) { if (ring->use_doorbell) {
/* XXX check if swapping is necessary on BE */ /* XXX check if swapping is necessary on BE */
wptr = ((u64 *)&adev->wb.wb[ring->wptr_offs]); wptr = READ_ONCE(*((u64 *)&adev->wb.wb[ring->wptr_offs]));
DRM_DEBUG("wptr/doorbell before shift == 0x%016llx\n", *wptr); DRM_DEBUG("wptr/doorbell before shift == 0x%016llx\n", wptr);
*wptr = (*wptr) >> 2;
DRM_DEBUG("wptr/doorbell after shift == 0x%016llx\n", *wptr);
} else { } else {
u32 lowbit, highbit; wptr = RREG32(sdma_v5_0_get_reg_offset(adev, ring->me, mmSDMA0_GFX_RB_WPTR_HI));
wptr = wptr << 32;
wptr = &local_wptr; wptr |= RREG32(sdma_v5_0_get_reg_offset(adev, ring->me, mmSDMA0_GFX_RB_WPTR));
lowbit = RREG32(sdma_v5_0_get_reg_offset(adev, ring->me, mmSDMA0_GFX_RB_WPTR)) >> 2; DRM_DEBUG("wptr before shift [%i] wptr == 0x%016llx\n", ring->me, wptr);
highbit = RREG32(sdma_v5_0_get_reg_offset(adev, ring->me, mmSDMA0_GFX_RB_WPTR_HI)) >> 2;
DRM_DEBUG("wptr [%i]high== 0x%08x low==0x%08x\n",
ring->me, highbit, lowbit);
*wptr = highbit;
*wptr = (*wptr) << 32;
*wptr |= lowbit;
} }
return *wptr; return wptr >> 2;
} }
/** /**
......
...@@ -974,6 +974,9 @@ static int amdgpu_dm_init(struct amdgpu_device *adev) ...@@ -974,6 +974,9 @@ static int amdgpu_dm_init(struct amdgpu_device *adev)
/* Update the actual used number of crtc */ /* Update the actual used number of crtc */
adev->mode_info.num_crtc = adev->dm.display_indexes_num; adev->mode_info.num_crtc = adev->dm.display_indexes_num;
/* create fake encoders for MST */
dm_dp_create_fake_mst_encoders(adev);
/* TODO: Add_display_info? */ /* TODO: Add_display_info? */
/* TODO use dynamic cursor width */ /* TODO use dynamic cursor width */
...@@ -997,6 +1000,12 @@ static int amdgpu_dm_init(struct amdgpu_device *adev) ...@@ -997,6 +1000,12 @@ static int amdgpu_dm_init(struct amdgpu_device *adev)
static void amdgpu_dm_fini(struct amdgpu_device *adev) static void amdgpu_dm_fini(struct amdgpu_device *adev)
{ {
int i;
for (i = 0; i < adev->dm.display_indexes_num; i++) {
drm_encoder_cleanup(&adev->dm.mst_encoders[i].base);
}
amdgpu_dm_audio_fini(adev); amdgpu_dm_audio_fini(adev);
amdgpu_dm_destroy_drm_device(&adev->dm); amdgpu_dm_destroy_drm_device(&adev->dm);
...@@ -2010,6 +2019,7 @@ static void update_connector_ext_caps(struct amdgpu_dm_connector *aconnector) ...@@ -2010,6 +2019,7 @@ static void update_connector_ext_caps(struct amdgpu_dm_connector *aconnector)
struct amdgpu_display_manager *dm; struct amdgpu_display_manager *dm;
struct drm_connector *conn_base; struct drm_connector *conn_base;
struct amdgpu_device *adev; struct amdgpu_device *adev;
struct dc_link *link = NULL;
static const u8 pre_computed_values[] = { static const u8 pre_computed_values[] = {
50, 51, 52, 53, 55, 56, 57, 58, 59, 61, 62, 63, 65, 66, 68, 69, 50, 51, 52, 53, 55, 56, 57, 58, 59, 61, 62, 63, 65, 66, 68, 69,
71, 72, 74, 75, 77, 79, 81, 82, 84, 86, 88, 90, 92, 94, 96, 98}; 71, 72, 74, 75, 77, 79, 81, 82, 84, 86, 88, 90, 92, 94, 96, 98};
...@@ -2017,6 +2027,10 @@ static void update_connector_ext_caps(struct amdgpu_dm_connector *aconnector) ...@@ -2017,6 +2027,10 @@ static void update_connector_ext_caps(struct amdgpu_dm_connector *aconnector)
if (!aconnector || !aconnector->dc_link) if (!aconnector || !aconnector->dc_link)
return; return;
link = aconnector->dc_link;
if (link->connector_signal != SIGNAL_TYPE_EDP)
return;
conn_base = &aconnector->base; conn_base = &aconnector->base;
adev = conn_base->dev->dev_private; adev = conn_base->dev->dev_private;
dm = &adev->dm; dm = &adev->dm;
......
...@@ -43,6 +43,9 @@ ...@@ -43,6 +43,9 @@
*/ */
#define AMDGPU_DM_MAX_DISPLAY_INDEX 31 #define AMDGPU_DM_MAX_DISPLAY_INDEX 31
#define AMDGPU_DM_MAX_CRTC 6
/* /*
#include "include/amdgpu_dal_power_if.h" #include "include/amdgpu_dal_power_if.h"
#include "amdgpu_dm_irq.h" #include "amdgpu_dm_irq.h"
...@@ -328,6 +331,13 @@ struct amdgpu_display_manager { ...@@ -328,6 +331,13 @@ struct amdgpu_display_manager {
* available in FW * available in FW
*/ */
const struct gpu_info_soc_bounding_box_v1_0 *soc_bounding_box; const struct gpu_info_soc_bounding_box_v1_0 *soc_bounding_box;
/**
* @mst_encoders:
*
* fake encoders used for DP MST.
*/
struct amdgpu_encoder mst_encoders[AMDGPU_DM_MAX_CRTC];
}; };
struct amdgpu_dm_connector { struct amdgpu_dm_connector {
...@@ -356,7 +366,6 @@ struct amdgpu_dm_connector { ...@@ -356,7 +366,6 @@ struct amdgpu_dm_connector {
struct amdgpu_dm_dp_aux dm_dp_aux; struct amdgpu_dm_dp_aux dm_dp_aux;
struct drm_dp_mst_port *port; struct drm_dp_mst_port *port;
struct amdgpu_dm_connector *mst_port; struct amdgpu_dm_connector *mst_port;
struct amdgpu_encoder *mst_encoder;
struct drm_dp_aux *dsc_aux; struct drm_dp_aux *dsc_aux;
/* TODO see if we can merge with ddc_bus or make a dm_connector */ /* TODO see if we can merge with ddc_bus or make a dm_connector */
......
...@@ -95,7 +95,6 @@ dm_dp_mst_connector_destroy(struct drm_connector *connector) ...@@ -95,7 +95,6 @@ dm_dp_mst_connector_destroy(struct drm_connector *connector)
{ {
struct amdgpu_dm_connector *aconnector = struct amdgpu_dm_connector *aconnector =
to_amdgpu_dm_connector(connector); to_amdgpu_dm_connector(connector);
struct amdgpu_encoder *amdgpu_encoder = aconnector->mst_encoder;
if (aconnector->dc_sink) { if (aconnector->dc_sink) {
dc_link_remove_remote_sink(aconnector->dc_link, dc_link_remove_remote_sink(aconnector->dc_link,
...@@ -105,8 +104,6 @@ dm_dp_mst_connector_destroy(struct drm_connector *connector) ...@@ -105,8 +104,6 @@ dm_dp_mst_connector_destroy(struct drm_connector *connector)
kfree(aconnector->edid); kfree(aconnector->edid);
drm_encoder_cleanup(&amdgpu_encoder->base);
kfree(amdgpu_encoder);
drm_connector_cleanup(connector); drm_connector_cleanup(connector);
drm_dp_mst_put_port_malloc(aconnector->port); drm_dp_mst_put_port_malloc(aconnector->port);
kfree(aconnector); kfree(aconnector);
...@@ -243,7 +240,11 @@ static struct drm_encoder * ...@@ -243,7 +240,11 @@ static struct drm_encoder *
dm_mst_atomic_best_encoder(struct drm_connector *connector, dm_mst_atomic_best_encoder(struct drm_connector *connector,
struct drm_connector_state *connector_state) struct drm_connector_state *connector_state)
{ {
return &to_amdgpu_dm_connector(connector)->mst_encoder->base; struct drm_device *dev = connector->dev;
struct amdgpu_device *adev = dev->dev_private;
struct amdgpu_crtc *acrtc = to_amdgpu_crtc(connector_state->crtc);
return &adev->dm.mst_encoders[acrtc->crtc_id].base;
} }
static int static int
...@@ -306,19 +307,16 @@ static const struct drm_encoder_funcs amdgpu_dm_encoder_funcs = { ...@@ -306,19 +307,16 @@ static const struct drm_encoder_funcs amdgpu_dm_encoder_funcs = {
.destroy = amdgpu_dm_encoder_destroy, .destroy = amdgpu_dm_encoder_destroy,
}; };
static struct amdgpu_encoder * void
dm_dp_create_fake_mst_encoder(struct amdgpu_dm_connector *connector) dm_dp_create_fake_mst_encoders(struct amdgpu_device *adev)
{ {
struct drm_device *dev = connector->base.dev; struct drm_device *dev = adev->ddev;
struct amdgpu_device *adev = dev->dev_private; int i;
struct amdgpu_encoder *amdgpu_encoder;
struct drm_encoder *encoder;
amdgpu_encoder = kzalloc(sizeof(*amdgpu_encoder), GFP_KERNEL); for (i = 0; i < adev->dm.display_indexes_num; i++) {
if (!amdgpu_encoder) struct amdgpu_encoder *amdgpu_encoder = &adev->dm.mst_encoders[i];
return NULL; struct drm_encoder *encoder = &amdgpu_encoder->base;
encoder = &amdgpu_encoder->base;
encoder->possible_crtcs = amdgpu_dm_get_encoder_crtc_mask(adev); encoder->possible_crtcs = amdgpu_dm_get_encoder_crtc_mask(adev);
drm_encoder_init( drm_encoder_init(
...@@ -329,8 +327,7 @@ dm_dp_create_fake_mst_encoder(struct amdgpu_dm_connector *connector) ...@@ -329,8 +327,7 @@ dm_dp_create_fake_mst_encoder(struct amdgpu_dm_connector *connector)
NULL); NULL);
drm_encoder_helper_add(encoder, &amdgpu_dm_encoder_helper_funcs); drm_encoder_helper_add(encoder, &amdgpu_dm_encoder_helper_funcs);
}
return amdgpu_encoder;
} }
static struct drm_connector * static struct drm_connector *
...@@ -343,6 +340,7 @@ dm_dp_add_mst_connector(struct drm_dp_mst_topology_mgr *mgr, ...@@ -343,6 +340,7 @@ dm_dp_add_mst_connector(struct drm_dp_mst_topology_mgr *mgr,
struct amdgpu_device *adev = dev->dev_private; struct amdgpu_device *adev = dev->dev_private;
struct amdgpu_dm_connector *aconnector; struct amdgpu_dm_connector *aconnector;
struct drm_connector *connector; struct drm_connector *connector;
int i;
aconnector = kzalloc(sizeof(*aconnector), GFP_KERNEL); aconnector = kzalloc(sizeof(*aconnector), GFP_KERNEL);
if (!aconnector) if (!aconnector)
...@@ -369,9 +367,10 @@ dm_dp_add_mst_connector(struct drm_dp_mst_topology_mgr *mgr, ...@@ -369,9 +367,10 @@ dm_dp_add_mst_connector(struct drm_dp_mst_topology_mgr *mgr,
master->dc_link, master->dc_link,
master->connector_id); master->connector_id);
aconnector->mst_encoder = dm_dp_create_fake_mst_encoder(master); for (i = 0; i < adev->dm.display_indexes_num; i++) {
drm_connector_attach_encoder(&aconnector->base, drm_connector_attach_encoder(&aconnector->base,
&aconnector->mst_encoder->base); &adev->dm.mst_encoders[i].base);
}
connector->max_bpc_property = master->base.max_bpc_property; connector->max_bpc_property = master->base.max_bpc_property;
if (connector->max_bpc_property) if (connector->max_bpc_property)
......
...@@ -35,6 +35,9 @@ void amdgpu_dm_initialize_dp_connector(struct amdgpu_display_manager *dm, ...@@ -35,6 +35,9 @@ void amdgpu_dm_initialize_dp_connector(struct amdgpu_display_manager *dm,
struct amdgpu_dm_connector *aconnector, struct amdgpu_dm_connector *aconnector,
int link_index); int link_index);
void
dm_dp_create_fake_mst_encoders(struct amdgpu_device *adev);
#if defined(CONFIG_DRM_AMD_DC_DCN) #if defined(CONFIG_DRM_AMD_DC_DCN)
bool compute_mst_dsc_configs_for_state(struct drm_atomic_state *state, bool compute_mst_dsc_configs_for_state(struct drm_atomic_state *state,
struct dc_state *dc_state); struct dc_state *dc_state);
......
...@@ -56,7 +56,7 @@ void update_stream_signal(struct dc_stream_state *stream, struct dc_sink *sink) ...@@ -56,7 +56,7 @@ void update_stream_signal(struct dc_stream_state *stream, struct dc_sink *sink)
} }
} }
static void dc_stream_construct(struct dc_stream_state *stream, static bool dc_stream_construct(struct dc_stream_state *stream,
struct dc_sink *dc_sink_data) struct dc_sink *dc_sink_data)
{ {
uint32_t i = 0; uint32_t i = 0;
...@@ -118,11 +118,17 @@ static void dc_stream_construct(struct dc_stream_state *stream, ...@@ -118,11 +118,17 @@ static void dc_stream_construct(struct dc_stream_state *stream,
update_stream_signal(stream, dc_sink_data); update_stream_signal(stream, dc_sink_data);
stream->out_transfer_func = dc_create_transfer_func(); stream->out_transfer_func = dc_create_transfer_func();
if (stream->out_transfer_func == NULL) {
dc_sink_release(dc_sink_data);
return false;
}
stream->out_transfer_func->type = TF_TYPE_BYPASS; stream->out_transfer_func->type = TF_TYPE_BYPASS;
stream->out_transfer_func->ctx = stream->ctx; stream->out_transfer_func->ctx = stream->ctx;
stream->stream_id = stream->ctx->dc_stream_id_count; stream->stream_id = stream->ctx->dc_stream_id_count;
stream->ctx->dc_stream_id_count++; stream->ctx->dc_stream_id_count++;
return true;
} }
static void dc_stream_destruct(struct dc_stream_state *stream) static void dc_stream_destruct(struct dc_stream_state *stream)
...@@ -164,13 +170,20 @@ struct dc_stream_state *dc_create_stream_for_sink( ...@@ -164,13 +170,20 @@ struct dc_stream_state *dc_create_stream_for_sink(
stream = kzalloc(sizeof(struct dc_stream_state), GFP_KERNEL); stream = kzalloc(sizeof(struct dc_stream_state), GFP_KERNEL);
if (stream == NULL) if (stream == NULL)
return NULL; goto alloc_fail;
dc_stream_construct(stream, sink); if (dc_stream_construct(stream, sink) == false)
goto construct_fail;
kref_init(&stream->refcount); kref_init(&stream->refcount);
return stream; return stream;
construct_fail:
kfree(stream);
alloc_fail:
return NULL;
} }
struct dc_stream_state *dc_copy_stream(const struct dc_stream_state *stream) struct dc_stream_state *dc_copy_stream(const struct dc_stream_state *stream)
......
...@@ -689,7 +689,7 @@ static int renoir_set_power_profile_mode(struct smu_context *smu, long *input, u ...@@ -689,7 +689,7 @@ static int renoir_set_power_profile_mode(struct smu_context *smu, long *input, u
return -EINVAL; return -EINVAL;
} }
ret = smu_send_smc_msg_with_param(smu, SMU_MSG_SetWorkloadMask, ret = smu_send_smc_msg_with_param(smu, SMU_MSG_ActiveProcessNotify,
1 << workload_type, 1 << workload_type,
NULL); NULL);
if (ret) { if (ret) {
......
...@@ -173,8 +173,6 @@ static int aspeed_gfx_load(struct drm_device *drm) ...@@ -173,8 +173,6 @@ static int aspeed_gfx_load(struct drm_device *drm)
drm_mode_config_reset(drm); drm_mode_config_reset(drm);
drm_fbdev_generic_setup(drm, 32);
return 0; return 0;
} }
...@@ -225,6 +223,7 @@ static int aspeed_gfx_probe(struct platform_device *pdev) ...@@ -225,6 +223,7 @@ static int aspeed_gfx_probe(struct platform_device *pdev)
if (ret) if (ret)
goto err_unload; goto err_unload;
drm_fbdev_generic_setup(&priv->drm, 32);
return 0; return 0;
err_unload: err_unload:
......
...@@ -719,6 +719,25 @@ static bool intel_fbc_cfb_size_changed(struct drm_i915_private *dev_priv) ...@@ -719,6 +719,25 @@ static bool intel_fbc_cfb_size_changed(struct drm_i915_private *dev_priv)
fbc->compressed_fb.size * fbc->threshold; fbc->compressed_fb.size * fbc->threshold;
} }
static u16 intel_fbc_gen9_wa_cfb_stride(struct drm_i915_private *dev_priv)
{
struct intel_fbc *fbc = &dev_priv->fbc;
struct intel_fbc_state_cache *cache = &fbc->state_cache;
if ((IS_GEN9_BC(dev_priv) || IS_BROXTON(dev_priv)) &&
cache->fb.modifier != I915_FORMAT_MOD_X_TILED)
return DIV_ROUND_UP(cache->plane.src_w, 32 * fbc->threshold) * 8;
else
return 0;
}
static bool intel_fbc_gen9_wa_cfb_stride_changed(struct drm_i915_private *dev_priv)
{
struct intel_fbc *fbc = &dev_priv->fbc;
return fbc->params.gen9_wa_cfb_stride != intel_fbc_gen9_wa_cfb_stride(dev_priv);
}
static bool intel_fbc_can_enable(struct drm_i915_private *dev_priv) static bool intel_fbc_can_enable(struct drm_i915_private *dev_priv)
{ {
struct intel_fbc *fbc = &dev_priv->fbc; struct intel_fbc *fbc = &dev_priv->fbc;
...@@ -877,6 +896,7 @@ static void intel_fbc_get_reg_params(struct intel_crtc *crtc, ...@@ -877,6 +896,7 @@ static void intel_fbc_get_reg_params(struct intel_crtc *crtc,
params->crtc.i9xx_plane = to_intel_plane(crtc->base.primary)->i9xx_plane; params->crtc.i9xx_plane = to_intel_plane(crtc->base.primary)->i9xx_plane;
params->fb.format = cache->fb.format; params->fb.format = cache->fb.format;
params->fb.modifier = cache->fb.modifier;
params->fb.stride = cache->fb.stride; params->fb.stride = cache->fb.stride;
params->cfb_size = intel_fbc_calculate_cfb_size(dev_priv, cache); params->cfb_size = intel_fbc_calculate_cfb_size(dev_priv, cache);
...@@ -906,6 +926,9 @@ static bool intel_fbc_can_flip_nuke(const struct intel_crtc_state *crtc_state) ...@@ -906,6 +926,9 @@ static bool intel_fbc_can_flip_nuke(const struct intel_crtc_state *crtc_state)
if (params->fb.format != cache->fb.format) if (params->fb.format != cache->fb.format)
return false; return false;
if (params->fb.modifier != cache->fb.modifier)
return false;
if (params->fb.stride != cache->fb.stride) if (params->fb.stride != cache->fb.stride)
return false; return false;
...@@ -1185,7 +1208,8 @@ void intel_fbc_enable(struct intel_atomic_state *state, ...@@ -1185,7 +1208,8 @@ void intel_fbc_enable(struct intel_atomic_state *state,
if (fbc->crtc) { if (fbc->crtc) {
if (fbc->crtc != crtc || if (fbc->crtc != crtc ||
!intel_fbc_cfb_size_changed(dev_priv)) (!intel_fbc_cfb_size_changed(dev_priv) &&
!intel_fbc_gen9_wa_cfb_stride_changed(dev_priv)))
goto out; goto out;
__intel_fbc_disable(dev_priv); __intel_fbc_disable(dev_priv);
...@@ -1207,12 +1231,7 @@ void intel_fbc_enable(struct intel_atomic_state *state, ...@@ -1207,12 +1231,7 @@ void intel_fbc_enable(struct intel_atomic_state *state,
goto out; goto out;
} }
if ((IS_GEN9_BC(dev_priv) || IS_BROXTON(dev_priv)) && cache->gen9_wa_cfb_stride = intel_fbc_gen9_wa_cfb_stride(dev_priv);
plane_state->hw.fb->modifier != I915_FORMAT_MOD_X_TILED)
cache->gen9_wa_cfb_stride =
DIV_ROUND_UP(cache->plane.src_w, 32 * fbc->threshold) * 8;
else
cache->gen9_wa_cfb_stride = 0;
drm_dbg_kms(&dev_priv->drm, "Enabling FBC on pipe %c\n", drm_dbg_kms(&dev_priv->drm, "Enabling FBC on pipe %c\n",
pipe_name(crtc->pipe)); pipe_name(crtc->pipe));
......
...@@ -2867,19 +2867,13 @@ intel_hdmi_connector_register(struct drm_connector *connector) ...@@ -2867,19 +2867,13 @@ intel_hdmi_connector_register(struct drm_connector *connector)
return ret; return ret;
} }
static void intel_hdmi_destroy(struct drm_connector *connector) static void intel_hdmi_connector_unregister(struct drm_connector *connector)
{ {
struct cec_notifier *n = intel_attached_hdmi(to_intel_connector(connector))->cec_notifier; struct cec_notifier *n = intel_attached_hdmi(to_intel_connector(connector))->cec_notifier;
cec_notifier_conn_unregister(n); cec_notifier_conn_unregister(n);
intel_connector_destroy(connector);
}
static void intel_hdmi_connector_unregister(struct drm_connector *connector)
{
intel_hdmi_remove_i2c_symlink(connector); intel_hdmi_remove_i2c_symlink(connector);
intel_connector_unregister(connector); intel_connector_unregister(connector);
} }
...@@ -2891,7 +2885,7 @@ static const struct drm_connector_funcs intel_hdmi_connector_funcs = { ...@@ -2891,7 +2885,7 @@ static const struct drm_connector_funcs intel_hdmi_connector_funcs = {
.atomic_set_property = intel_digital_connector_atomic_set_property, .atomic_set_property = intel_digital_connector_atomic_set_property,
.late_register = intel_hdmi_connector_register, .late_register = intel_hdmi_connector_register,
.early_unregister = intel_hdmi_connector_unregister, .early_unregister = intel_hdmi_connector_unregister,
.destroy = intel_hdmi_destroy, .destroy = intel_connector_destroy,
.atomic_destroy_state = drm_atomic_helper_connector_destroy_state, .atomic_destroy_state = drm_atomic_helper_connector_destroy_state,
.atomic_duplicate_state = intel_digital_connector_duplicate_state, .atomic_duplicate_state = intel_digital_connector_duplicate_state,
}; };
......
...@@ -5396,13 +5396,8 @@ static void virtual_engine_initial_hint(struct virtual_engine *ve) ...@@ -5396,13 +5396,8 @@ static void virtual_engine_initial_hint(struct virtual_engine *ve)
* typically be the first we inspect for submission. * typically be the first we inspect for submission.
*/ */
swp = prandom_u32_max(ve->num_siblings); swp = prandom_u32_max(ve->num_siblings);
if (!swp) if (swp)
return;
swap(ve->siblings[swp], ve->siblings[0]); swap(ve->siblings[swp], ve->siblings[0]);
if (!intel_engine_has_relative_mmio(ve->siblings[0]))
virtual_update_register_offsets(ve->context.lrc_reg_state,
ve->siblings[0]);
} }
static int virtual_context_alloc(struct intel_context *ce) static int virtual_context_alloc(struct intel_context *ce)
...@@ -5415,15 +5410,9 @@ static int virtual_context_alloc(struct intel_context *ce) ...@@ -5415,15 +5410,9 @@ static int virtual_context_alloc(struct intel_context *ce)
static int virtual_context_pin(struct intel_context *ce) static int virtual_context_pin(struct intel_context *ce)
{ {
struct virtual_engine *ve = container_of(ce, typeof(*ve), context); struct virtual_engine *ve = container_of(ce, typeof(*ve), context);
int err;
/* Note: we must use a real engine class for setting up reg state */ /* Note: we must use a real engine class for setting up reg state */
err = __execlists_context_pin(ce, ve->siblings[0]); return __execlists_context_pin(ce, ve->siblings[0]);
if (err)
return err;
virtual_engine_initial_hint(ve);
return 0;
} }
static void virtual_context_enter(struct intel_context *ce) static void virtual_context_enter(struct intel_context *ce)
...@@ -5688,6 +5677,7 @@ intel_execlists_create_virtual(struct intel_engine_cs **siblings, ...@@ -5688,6 +5677,7 @@ intel_execlists_create_virtual(struct intel_engine_cs **siblings,
intel_engine_init_active(&ve->base, ENGINE_VIRTUAL); intel_engine_init_active(&ve->base, ENGINE_VIRTUAL);
intel_engine_init_breadcrumbs(&ve->base); intel_engine_init_breadcrumbs(&ve->base);
intel_engine_init_execlists(&ve->base); intel_engine_init_execlists(&ve->base);
ve->base.breadcrumbs.irq_armed = true; /* fake HW, used for irq_work */
ve->base.cops = &virtual_context_ops; ve->base.cops = &virtual_context_ops;
ve->base.request_alloc = execlists_request_alloc; ve->base.request_alloc = execlists_request_alloc;
...@@ -5769,6 +5759,7 @@ intel_execlists_create_virtual(struct intel_engine_cs **siblings, ...@@ -5769,6 +5759,7 @@ intel_execlists_create_virtual(struct intel_engine_cs **siblings,
ve->base.flags |= I915_ENGINE_IS_VIRTUAL; ve->base.flags |= I915_ENGINE_IS_VIRTUAL;
virtual_engine_initial_hint(ve);
return &ve->context; return &ve->context;
err_put: err_put:
......
...@@ -44,9 +44,9 @@ static int cmp_u64(const void *A, const void *B) ...@@ -44,9 +44,9 @@ static int cmp_u64(const void *A, const void *B)
{ {
const u64 *a = A, *b = B; const u64 *a = A, *b = B;
if (a < b) if (*a < *b)
return -1; return -1;
else if (a > b) else if (*a > *b)
return 1; return 1;
else else
return 0; return 0;
...@@ -56,9 +56,9 @@ static int cmp_u32(const void *A, const void *B) ...@@ -56,9 +56,9 @@ static int cmp_u32(const void *A, const void *B)
{ {
const u32 *a = A, *b = B; const u32 *a = A, *b = B;
if (a < b) if (*a < *b)
return -1; return -1;
else if (a > b) else if (*a > *b)
return 1; return 1;
else else
return 0; return 0;
......
...@@ -440,6 +440,7 @@ struct intel_fbc { ...@@ -440,6 +440,7 @@ struct intel_fbc {
struct { struct {
const struct drm_format_info *format; const struct drm_format_info *format;
unsigned int stride; unsigned int stride;
u64 modifier;
} fb; } fb;
int cfb_size; int cfb_size;
......
...@@ -1592,6 +1592,7 @@ static u32 *save_restore_register(struct i915_perf_stream *stream, u32 *cs, ...@@ -1592,6 +1592,7 @@ static u32 *save_restore_register(struct i915_perf_stream *stream, u32 *cs,
u32 d; u32 d;
cmd = save ? MI_STORE_REGISTER_MEM : MI_LOAD_REGISTER_MEM; cmd = save ? MI_STORE_REGISTER_MEM : MI_LOAD_REGISTER_MEM;
cmd |= MI_SRM_LRM_GLOBAL_GTT;
if (INTEL_GEN(stream->perf->i915) >= 8) if (INTEL_GEN(stream->perf->i915) >= 8)
cmd++; cmd++;
......
...@@ -1069,10 +1069,6 @@ vmw_stdu_primary_plane_prepare_fb(struct drm_plane *plane, ...@@ -1069,10 +1069,6 @@ vmw_stdu_primary_plane_prepare_fb(struct drm_plane *plane,
if (new_content_type != SAME_AS_DISPLAY) { if (new_content_type != SAME_AS_DISPLAY) {
struct vmw_surface_metadata metadata = {0}; struct vmw_surface_metadata metadata = {0};
metadata.base_size.width = hdisplay;
metadata.base_size.height = vdisplay;
metadata.base_size.depth = 1;
/* /*
* If content buffer is a buffer object, then we have to * If content buffer is a buffer object, then we have to
* construct surface info * construct surface info
...@@ -1104,6 +1100,10 @@ vmw_stdu_primary_plane_prepare_fb(struct drm_plane *plane, ...@@ -1104,6 +1100,10 @@ vmw_stdu_primary_plane_prepare_fb(struct drm_plane *plane,
metadata = new_vfbs->surface->metadata; metadata = new_vfbs->surface->metadata;
} }
metadata.base_size.width = hdisplay;
metadata.base_size.height = vdisplay;
metadata.base_size.depth = 1;
if (vps->surf) { if (vps->surf) {
struct drm_vmw_size cur_base_size = struct drm_vmw_size cur_base_size =
vps->surf->metadata.base_size; vps->surf->metadata.base_size;
......
...@@ -311,6 +311,7 @@ struct dma_buf { ...@@ -311,6 +311,7 @@ struct dma_buf {
void *vmap_ptr; void *vmap_ptr;
const char *exp_name; const char *exp_name;
const char *name; const char *name;
spinlock_t name_lock; /* spinlock to protect name access */
struct module *owner; struct module *owner;
struct list_head list_node; struct list_head list_node;
void *priv; void *priv;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment