mirror of
https://github.com/Fishwaldo/Star64_linux.git
synced 2025-06-26 16:41:25 +00:00
Merge branch 'drm-fixes' of git://people.freedesktop.org/~airlied/linux
Pull more drm fixes from Dave Airlie: "Just some intel and nouveau ones this time, intel has more edp panel fixes for macbooks and nouveau has a suspend/resume regression fix in there." * 'drm-fixes' of git://people.freedesktop.org/~airlied/linux: drm/i915: Apply post-sync write for pipe control invalidates drm/i915: reorder edp disabling to fix ivb MacBook Air drm/nv86/fifo: suspend fix drm/nouveau: disable copy engine on NVAF nouveau: fixup scanout enable in nvc0_pm drm/nouveau/aux: mask off higher bits of auxch index in i2c table entry drm/nvd0/disp: mask off high 16 bit of negative cursor x-coordinate drm/i915: ensure i2c adapter is all set before adding it drm/i915: ignore eDP bpc settings from vbt drm/i915: Fix blank panel at reopening lid drm/nve0/fifo: add support for the flip completion swmthd
This commit is contained in:
commit
d3b8e0dc82
11 changed files with 88 additions and 51 deletions
|
@ -3754,17 +3754,6 @@ static bool intel_choose_pipe_bpp_dither(struct drm_crtc *crtc,
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (intel_encoder->type == INTEL_OUTPUT_EDP) {
|
|
||||||
/* Use VBT settings if we have an eDP panel */
|
|
||||||
unsigned int edp_bpc = dev_priv->edp.bpp / 3;
|
|
||||||
|
|
||||||
if (edp_bpc < display_bpc) {
|
|
||||||
DRM_DEBUG_KMS("clamping display bpc (was %d) to eDP (%d)\n", display_bpc, edp_bpc);
|
|
||||||
display_bpc = edp_bpc;
|
|
||||||
}
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Not one of the known troublemakers, check the EDID */
|
/* Not one of the known troublemakers, check the EDID */
|
||||||
list_for_each_entry(connector, &dev->mode_config.connector_list,
|
list_for_each_entry(connector, &dev->mode_config.connector_list,
|
||||||
head) {
|
head) {
|
||||||
|
|
|
@ -1174,10 +1174,14 @@ static void ironlake_edp_panel_off(struct intel_dp *intel_dp)
|
||||||
WARN(!intel_dp->want_panel_vdd, "Need VDD to turn off panel\n");
|
WARN(!intel_dp->want_panel_vdd, "Need VDD to turn off panel\n");
|
||||||
|
|
||||||
pp = ironlake_get_pp_control(dev_priv);
|
pp = ironlake_get_pp_control(dev_priv);
|
||||||
pp &= ~(POWER_TARGET_ON | PANEL_POWER_RESET | EDP_BLC_ENABLE);
|
/* We need to switch off panel power _and_ force vdd, for otherwise some
|
||||||
|
* panels get very unhappy and cease to work. */
|
||||||
|
pp &= ~(POWER_TARGET_ON | EDP_FORCE_VDD | PANEL_POWER_RESET | EDP_BLC_ENABLE);
|
||||||
I915_WRITE(PCH_PP_CONTROL, pp);
|
I915_WRITE(PCH_PP_CONTROL, pp);
|
||||||
POSTING_READ(PCH_PP_CONTROL);
|
POSTING_READ(PCH_PP_CONTROL);
|
||||||
|
|
||||||
|
intel_dp->want_panel_vdd = false;
|
||||||
|
|
||||||
ironlake_wait_panel_off(intel_dp);
|
ironlake_wait_panel_off(intel_dp);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1287,11 +1291,9 @@ static void intel_dp_prepare(struct drm_encoder *encoder)
|
||||||
* ensure that we have vdd while we switch off the panel. */
|
* ensure that we have vdd while we switch off the panel. */
|
||||||
ironlake_edp_panel_vdd_on(intel_dp);
|
ironlake_edp_panel_vdd_on(intel_dp);
|
||||||
ironlake_edp_backlight_off(intel_dp);
|
ironlake_edp_backlight_off(intel_dp);
|
||||||
ironlake_edp_panel_off(intel_dp);
|
|
||||||
|
|
||||||
intel_dp_sink_dpms(intel_dp, DRM_MODE_DPMS_ON);
|
intel_dp_sink_dpms(intel_dp, DRM_MODE_DPMS_ON);
|
||||||
|
ironlake_edp_panel_off(intel_dp);
|
||||||
intel_dp_link_down(intel_dp);
|
intel_dp_link_down(intel_dp);
|
||||||
ironlake_edp_panel_vdd_off(intel_dp, false);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void intel_dp_commit(struct drm_encoder *encoder)
|
static void intel_dp_commit(struct drm_encoder *encoder)
|
||||||
|
@ -1326,11 +1328,9 @@ intel_dp_dpms(struct drm_encoder *encoder, int mode)
|
||||||
/* Switching the panel off requires vdd. */
|
/* Switching the panel off requires vdd. */
|
||||||
ironlake_edp_panel_vdd_on(intel_dp);
|
ironlake_edp_panel_vdd_on(intel_dp);
|
||||||
ironlake_edp_backlight_off(intel_dp);
|
ironlake_edp_backlight_off(intel_dp);
|
||||||
ironlake_edp_panel_off(intel_dp);
|
|
||||||
|
|
||||||
intel_dp_sink_dpms(intel_dp, mode);
|
intel_dp_sink_dpms(intel_dp, mode);
|
||||||
|
ironlake_edp_panel_off(intel_dp);
|
||||||
intel_dp_link_down(intel_dp);
|
intel_dp_link_down(intel_dp);
|
||||||
ironlake_edp_panel_vdd_off(intel_dp, false);
|
|
||||||
|
|
||||||
if (is_cpu_edp(intel_dp))
|
if (is_cpu_edp(intel_dp))
|
||||||
ironlake_edp_pll_off(encoder);
|
ironlake_edp_pll_off(encoder);
|
||||||
|
|
|
@ -486,9 +486,6 @@ int intel_setup_gmbus(struct drm_device *dev)
|
||||||
bus->dev_priv = dev_priv;
|
bus->dev_priv = dev_priv;
|
||||||
|
|
||||||
bus->adapter.algo = &gmbus_algorithm;
|
bus->adapter.algo = &gmbus_algorithm;
|
||||||
ret = i2c_add_adapter(&bus->adapter);
|
|
||||||
if (ret)
|
|
||||||
goto err;
|
|
||||||
|
|
||||||
/* By default use a conservative clock rate */
|
/* By default use a conservative clock rate */
|
||||||
bus->reg0 = port | GMBUS_RATE_100KHZ;
|
bus->reg0 = port | GMBUS_RATE_100KHZ;
|
||||||
|
@ -498,6 +495,10 @@ int intel_setup_gmbus(struct drm_device *dev)
|
||||||
bus->force_bit = true;
|
bus->force_bit = true;
|
||||||
|
|
||||||
intel_gpio_setup(bus, port);
|
intel_gpio_setup(bus, port);
|
||||||
|
|
||||||
|
ret = i2c_add_adapter(&bus->adapter);
|
||||||
|
if (ret)
|
||||||
|
goto err;
|
||||||
}
|
}
|
||||||
|
|
||||||
intel_i2c_reset(dev_priv->dev);
|
intel_i2c_reset(dev_priv->dev);
|
||||||
|
|
|
@ -311,9 +311,6 @@ void intel_panel_enable_backlight(struct drm_device *dev,
|
||||||
if (dev_priv->backlight_level == 0)
|
if (dev_priv->backlight_level == 0)
|
||||||
dev_priv->backlight_level = intel_panel_get_max_backlight(dev);
|
dev_priv->backlight_level = intel_panel_get_max_backlight(dev);
|
||||||
|
|
||||||
dev_priv->backlight_enabled = true;
|
|
||||||
intel_panel_actually_set_backlight(dev, dev_priv->backlight_level);
|
|
||||||
|
|
||||||
if (INTEL_INFO(dev)->gen >= 4) {
|
if (INTEL_INFO(dev)->gen >= 4) {
|
||||||
uint32_t reg, tmp;
|
uint32_t reg, tmp;
|
||||||
|
|
||||||
|
@ -326,7 +323,7 @@ void intel_panel_enable_backlight(struct drm_device *dev,
|
||||||
* we don't track the backlight dpms state, hence check whether
|
* we don't track the backlight dpms state, hence check whether
|
||||||
* we have to do anything first. */
|
* we have to do anything first. */
|
||||||
if (tmp & BLM_PWM_ENABLE)
|
if (tmp & BLM_PWM_ENABLE)
|
||||||
return;
|
goto set_level;
|
||||||
|
|
||||||
if (dev_priv->num_pipe == 3)
|
if (dev_priv->num_pipe == 3)
|
||||||
tmp &= ~BLM_PIPE_SELECT_IVB;
|
tmp &= ~BLM_PIPE_SELECT_IVB;
|
||||||
|
@ -347,6 +344,14 @@ void intel_panel_enable_backlight(struct drm_device *dev,
|
||||||
I915_WRITE(BLC_PWM_PCH_CTL1, tmp);
|
I915_WRITE(BLC_PWM_PCH_CTL1, tmp);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
set_level:
|
||||||
|
/* Call below after setting BLC_PWM_CPU_CTL2 and BLC_PWM_PCH_CTL1.
|
||||||
|
* BLC_PWM_CPU_CTL may be cleared to zero automatically when these
|
||||||
|
* registers are set.
|
||||||
|
*/
|
||||||
|
dev_priv->backlight_enabled = true;
|
||||||
|
intel_panel_actually_set_backlight(dev, dev_priv->backlight_level);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void intel_panel_init_backlight(struct drm_device *dev)
|
static void intel_panel_init_backlight(struct drm_device *dev)
|
||||||
|
|
|
@ -227,31 +227,36 @@ gen6_render_ring_flush(struct intel_ring_buffer *ring,
|
||||||
* number of bits based on the write domains has little performance
|
* number of bits based on the write domains has little performance
|
||||||
* impact.
|
* impact.
|
||||||
*/
|
*/
|
||||||
flags |= PIPE_CONTROL_RENDER_TARGET_CACHE_FLUSH;
|
if (flush_domains) {
|
||||||
flags |= PIPE_CONTROL_TLB_INVALIDATE;
|
flags |= PIPE_CONTROL_RENDER_TARGET_CACHE_FLUSH;
|
||||||
flags |= PIPE_CONTROL_INSTRUCTION_CACHE_INVALIDATE;
|
flags |= PIPE_CONTROL_DEPTH_CACHE_FLUSH;
|
||||||
flags |= PIPE_CONTROL_TEXTURE_CACHE_INVALIDATE;
|
/*
|
||||||
flags |= PIPE_CONTROL_DEPTH_CACHE_FLUSH;
|
* Ensure that any following seqno writes only happen
|
||||||
flags |= PIPE_CONTROL_VF_CACHE_INVALIDATE;
|
* when the render cache is indeed flushed.
|
||||||
flags |= PIPE_CONTROL_CONST_CACHE_INVALIDATE;
|
*/
|
||||||
flags |= PIPE_CONTROL_STATE_CACHE_INVALIDATE;
|
|
||||||
/*
|
|
||||||
* Ensure that any following seqno writes only happen when the render
|
|
||||||
* cache is indeed flushed (but only if the caller actually wants that).
|
|
||||||
*/
|
|
||||||
if (flush_domains)
|
|
||||||
flags |= PIPE_CONTROL_CS_STALL;
|
flags |= PIPE_CONTROL_CS_STALL;
|
||||||
|
}
|
||||||
|
if (invalidate_domains) {
|
||||||
|
flags |= PIPE_CONTROL_TLB_INVALIDATE;
|
||||||
|
flags |= PIPE_CONTROL_INSTRUCTION_CACHE_INVALIDATE;
|
||||||
|
flags |= PIPE_CONTROL_TEXTURE_CACHE_INVALIDATE;
|
||||||
|
flags |= PIPE_CONTROL_VF_CACHE_INVALIDATE;
|
||||||
|
flags |= PIPE_CONTROL_CONST_CACHE_INVALIDATE;
|
||||||
|
flags |= PIPE_CONTROL_STATE_CACHE_INVALIDATE;
|
||||||
|
/*
|
||||||
|
* TLB invalidate requires a post-sync write.
|
||||||
|
*/
|
||||||
|
flags |= PIPE_CONTROL_QW_WRITE;
|
||||||
|
}
|
||||||
|
|
||||||
ret = intel_ring_begin(ring, 6);
|
ret = intel_ring_begin(ring, 4);
|
||||||
if (ret)
|
if (ret)
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
intel_ring_emit(ring, GFX_OP_PIPE_CONTROL(5));
|
intel_ring_emit(ring, GFX_OP_PIPE_CONTROL(4));
|
||||||
intel_ring_emit(ring, flags);
|
intel_ring_emit(ring, flags);
|
||||||
intel_ring_emit(ring, scratch_addr | PIPE_CONTROL_GLOBAL_GTT);
|
intel_ring_emit(ring, scratch_addr | PIPE_CONTROL_GLOBAL_GTT);
|
||||||
intel_ring_emit(ring, 0); /* lower dword */
|
intel_ring_emit(ring, 0);
|
||||||
intel_ring_emit(ring, 0); /* uppwer dword */
|
|
||||||
intel_ring_emit(ring, MI_NOOP);
|
|
||||||
intel_ring_advance(ring);
|
intel_ring_advance(ring);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
@ -229,7 +229,7 @@ nouveau_i2c_init(struct drm_device *dev)
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 6: /* NV50- DP AUX */
|
case 6: /* NV50- DP AUX */
|
||||||
port->drive = entry[0];
|
port->drive = entry[0] & 0x0f;
|
||||||
port->sense = port->drive;
|
port->sense = port->drive;
|
||||||
port->adapter.algo = &nouveau_dp_i2c_algo;
|
port->adapter.algo = &nouveau_dp_i2c_algo;
|
||||||
break;
|
break;
|
||||||
|
|
|
@ -731,7 +731,6 @@ nouveau_card_init(struct drm_device *dev)
|
||||||
case 0xa3:
|
case 0xa3:
|
||||||
case 0xa5:
|
case 0xa5:
|
||||||
case 0xa8:
|
case 0xa8:
|
||||||
case 0xaf:
|
|
||||||
nva3_copy_create(dev);
|
nva3_copy_create(dev);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
|
@ -117,17 +117,22 @@ nv84_fifo_context_del(struct nouveau_channel *chan, int engine)
|
||||||
struct drm_device *dev = chan->dev;
|
struct drm_device *dev = chan->dev;
|
||||||
struct drm_nouveau_private *dev_priv = dev->dev_private;
|
struct drm_nouveau_private *dev_priv = dev->dev_private;
|
||||||
unsigned long flags;
|
unsigned long flags;
|
||||||
|
u32 save;
|
||||||
|
|
||||||
/* remove channel from playlist, will context switch if active */
|
/* remove channel from playlist, will context switch if active */
|
||||||
spin_lock_irqsave(&dev_priv->context_switch_lock, flags);
|
spin_lock_irqsave(&dev_priv->context_switch_lock, flags);
|
||||||
nv_mask(dev, 0x002600 + (chan->id * 4), 0x80000000, 0x00000000);
|
nv_mask(dev, 0x002600 + (chan->id * 4), 0x80000000, 0x00000000);
|
||||||
nv50_fifo_playlist_update(dev);
|
nv50_fifo_playlist_update(dev);
|
||||||
|
|
||||||
|
save = nv_mask(dev, 0x002520, 0x0000003f, 0x15);
|
||||||
|
|
||||||
/* tell any engines on this channel to unload their contexts */
|
/* tell any engines on this channel to unload their contexts */
|
||||||
nv_wr32(dev, 0x0032fc, chan->ramin->vinst >> 12);
|
nv_wr32(dev, 0x0032fc, chan->ramin->vinst >> 12);
|
||||||
if (!nv_wait_ne(dev, 0x0032fc, 0xffffffff, 0xffffffff))
|
if (!nv_wait_ne(dev, 0x0032fc, 0xffffffff, 0xffffffff))
|
||||||
NV_INFO(dev, "PFIFO: channel %d unload timeout\n", chan->id);
|
NV_INFO(dev, "PFIFO: channel %d unload timeout\n", chan->id);
|
||||||
|
|
||||||
|
nv_wr32(dev, 0x002520, save);
|
||||||
|
|
||||||
nv_wr32(dev, 0x002600 + (chan->id * 4), 0x00000000);
|
nv_wr32(dev, 0x002600 + (chan->id * 4), 0x00000000);
|
||||||
spin_unlock_irqrestore(&dev_priv->context_switch_lock, flags);
|
spin_unlock_irqrestore(&dev_priv->context_switch_lock, flags);
|
||||||
|
|
||||||
|
@ -184,10 +189,13 @@ nv84_fifo_fini(struct drm_device *dev, int engine, bool suspend)
|
||||||
struct drm_nouveau_private *dev_priv = dev->dev_private;
|
struct drm_nouveau_private *dev_priv = dev->dev_private;
|
||||||
struct nv84_fifo_priv *priv = nv_engine(dev, engine);
|
struct nv84_fifo_priv *priv = nv_engine(dev, engine);
|
||||||
int i;
|
int i;
|
||||||
|
u32 save;
|
||||||
|
|
||||||
/* set playlist length to zero, fifo will unload context */
|
/* set playlist length to zero, fifo will unload context */
|
||||||
nv_wr32(dev, 0x0032ec, 0);
|
nv_wr32(dev, 0x0032ec, 0);
|
||||||
|
|
||||||
|
save = nv_mask(dev, 0x002520, 0x0000003f, 0x15);
|
||||||
|
|
||||||
/* tell all connected engines to unload their contexts */
|
/* tell all connected engines to unload their contexts */
|
||||||
for (i = 0; i < priv->base.channels; i++) {
|
for (i = 0; i < priv->base.channels; i++) {
|
||||||
struct nouveau_channel *chan = dev_priv->channels.ptr[i];
|
struct nouveau_channel *chan = dev_priv->channels.ptr[i];
|
||||||
|
@ -199,6 +207,7 @@ nv84_fifo_fini(struct drm_device *dev, int engine, bool suspend)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
nv_wr32(dev, 0x002520, save);
|
||||||
nv_wr32(dev, 0x002140, 0);
|
nv_wr32(dev, 0x002140, 0);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
|
@ -557,7 +557,7 @@ prog_mem(struct drm_device *dev, struct nvc0_pm_state *info)
|
||||||
nouveau_mem_exec(&exec, info->perflvl);
|
nouveau_mem_exec(&exec, info->perflvl);
|
||||||
|
|
||||||
if (dev_priv->chipset < 0xd0)
|
if (dev_priv->chipset < 0xd0)
|
||||||
nv_wr32(dev, 0x611200, 0x00003300);
|
nv_wr32(dev, 0x611200, 0x00003330);
|
||||||
else
|
else
|
||||||
nv_wr32(dev, 0x62c000, 0x03030300);
|
nv_wr32(dev, 0x62c000, 0x03030300);
|
||||||
}
|
}
|
||||||
|
|
|
@ -790,7 +790,7 @@ nvd0_crtc_cursor_move(struct drm_crtc *crtc, int x, int y)
|
||||||
struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc);
|
struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc);
|
||||||
int ch = EVO_CURS(nv_crtc->index);
|
int ch = EVO_CURS(nv_crtc->index);
|
||||||
|
|
||||||
evo_piow(crtc->dev, ch, 0x0084, (y << 16) | x);
|
evo_piow(crtc->dev, ch, 0x0084, (y << 16) | (x & 0xffff));
|
||||||
evo_piow(crtc->dev, ch, 0x0080, 0x00000000);
|
evo_piow(crtc->dev, ch, 0x0080, 0x00000000);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
|
@ -294,6 +294,25 @@ nve0_fifo_isr_vm_fault(struct drm_device *dev, int unit)
|
||||||
printk(" on channel 0x%010llx\n", (u64)inst << 12);
|
printk(" on channel 0x%010llx\n", (u64)inst << 12);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
nve0_fifo_page_flip(struct drm_device *dev, u32 chid)
|
||||||
|
{
|
||||||
|
struct nve0_fifo_priv *priv = nv_engine(dev, NVOBJ_ENGINE_FIFO);
|
||||||
|
struct drm_nouveau_private *dev_priv = dev->dev_private;
|
||||||
|
struct nouveau_channel *chan = NULL;
|
||||||
|
unsigned long flags;
|
||||||
|
int ret = -EINVAL;
|
||||||
|
|
||||||
|
spin_lock_irqsave(&dev_priv->channels.lock, flags);
|
||||||
|
if (likely(chid >= 0 && chid < priv->base.channels)) {
|
||||||
|
chan = dev_priv->channels.ptr[chid];
|
||||||
|
if (likely(chan))
|
||||||
|
ret = nouveau_finish_page_flip(chan, NULL);
|
||||||
|
}
|
||||||
|
spin_unlock_irqrestore(&dev_priv->channels.lock, flags);
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
nve0_fifo_isr_subfifo_intr(struct drm_device *dev, int unit)
|
nve0_fifo_isr_subfifo_intr(struct drm_device *dev, int unit)
|
||||||
{
|
{
|
||||||
|
@ -303,11 +322,21 @@ nve0_fifo_isr_subfifo_intr(struct drm_device *dev, int unit)
|
||||||
u32 chid = nv_rd32(dev, 0x040120 + (unit * 0x2000)) & 0x7f;
|
u32 chid = nv_rd32(dev, 0x040120 + (unit * 0x2000)) & 0x7f;
|
||||||
u32 subc = (addr & 0x00070000);
|
u32 subc = (addr & 0x00070000);
|
||||||
u32 mthd = (addr & 0x00003ffc);
|
u32 mthd = (addr & 0x00003ffc);
|
||||||
|
u32 show = stat;
|
||||||
|
|
||||||
NV_INFO(dev, "PSUBFIFO %d:", unit);
|
if (stat & 0x00200000) {
|
||||||
nouveau_bitfield_print(nve0_fifo_subfifo_intr, stat);
|
if (mthd == 0x0054) {
|
||||||
NV_INFO(dev, "PSUBFIFO %d: ch %d subc %d mthd 0x%04x data 0x%08x\n",
|
if (!nve0_fifo_page_flip(dev, chid))
|
||||||
unit, chid, subc, mthd, data);
|
show &= ~0x00200000;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (show) {
|
||||||
|
NV_INFO(dev, "PFIFO%d:", unit);
|
||||||
|
nouveau_bitfield_print(nve0_fifo_subfifo_intr, show);
|
||||||
|
NV_INFO(dev, "PFIFO%d: ch %d subc %d mthd 0x%04x data 0x%08x\n",
|
||||||
|
unit, chid, subc, mthd, data);
|
||||||
|
}
|
||||||
|
|
||||||
nv_wr32(dev, 0x0400c0 + (unit * 0x2000), 0x80600008);
|
nv_wr32(dev, 0x0400c0 + (unit * 0x2000), 0x80600008);
|
||||||
nv_wr32(dev, 0x040108 + (unit * 0x2000), stat);
|
nv_wr32(dev, 0x040108 + (unit * 0x2000), stat);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue