Skip to content

Commit 08edb33

Browse files
committed
Merge branch 'drm-fixes' of git://people.freedesktop.org/~airlied/linux
Pull drm fixes from Dave Airlie: "Some final few intel fixes, all regressions, all stable cc, and one exynos oops fixer. The biggest is probably the intel display error irqs one, but it seems to fix a few crashes on startup, and one use after free in drm core" * 'drm-fixes' of git://people.freedesktop.org/~airlied/linux: drm/exynos: Fix (more) freeing issues in exynos_drm_drv.c drm/i915: Disable stolen memory when DMAR is active Revert "drm/i915: don't touch the VDD when disabling the panel" drm: Fix use-after-free in the shadow-attache exit code drm/i915: Don't enable display error interrupts from the start drm/i915: Fix scanline counter fixup on BDW drm/i915: Add a workaround for HSW scanline counter weirdness drm/i915: Fix PSR programming
2 parents 708f04d + 004e5cf commit 08edb33

File tree

6 files changed

+67
-36
lines changed

6 files changed

+67
-36
lines changed

drivers/gpu/drm/drm_pci.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -468,8 +468,8 @@ void drm_pci_exit(struct drm_driver *driver, struct pci_driver *pdriver)
468468
} else {
469469
list_for_each_entry_safe(dev, tmp, &driver->legacy_dev_list,
470470
legacy_dev_list) {
471-
drm_put_dev(dev);
472471
list_del(&dev->legacy_dev_list);
472+
drm_put_dev(dev);
473473
}
474474
}
475475
DRM_INFO("Module unloaded\n");

drivers/gpu/drm/exynos/exynos_drm_drv.c

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -172,20 +172,24 @@ static int exynos_drm_open(struct drm_device *dev, struct drm_file *file)
172172

173173
ret = exynos_drm_subdrv_open(dev, file);
174174
if (ret)
175-
goto out;
175+
goto err_file_priv_free;
176176

177177
anon_filp = anon_inode_getfile("exynos_gem", &exynos_drm_gem_fops,
178178
NULL, 0);
179179
if (IS_ERR(anon_filp)) {
180180
ret = PTR_ERR(anon_filp);
181-
goto out;
181+
goto err_subdrv_close;
182182
}
183183

184184
anon_filp->f_mode = FMODE_READ | FMODE_WRITE;
185185
file_priv->anon_filp = anon_filp;
186186

187187
return ret;
188-
out:
188+
189+
err_subdrv_close:
190+
exynos_drm_subdrv_close(dev, file);
191+
192+
err_file_priv_free:
189193
kfree(file_priv);
190194
file->driver_priv = NULL;
191195
return ret;

drivers/gpu/drm/i915/i915_gem_stolen.c

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -214,6 +214,13 @@ int i915_gem_init_stolen(struct drm_device *dev)
214214
struct drm_i915_private *dev_priv = dev->dev_private;
215215
int bios_reserved = 0;
216216

217+
#ifdef CONFIG_INTEL_IOMMU
218+
if (intel_iommu_gfx_mapped) {
219+
DRM_INFO("DMAR active, disabling use of stolen memory\n");
220+
return 0;
221+
}
222+
#endif
223+
217224
if (dev_priv->gtt.stolen_size == 0)
218225
return 0;
219226

drivers/gpu/drm/i915/i915_irq.c

Lines changed: 41 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -618,33 +618,25 @@ static u32 gm45_get_vblank_counter(struct drm_device *dev, int pipe)
618618

619619
/* raw reads, only for fast reads of display block, no need for forcewake etc. */
620620
#define __raw_i915_read32(dev_priv__, reg__) readl((dev_priv__)->regs + (reg__))
621-
#define __raw_i915_read16(dev_priv__, reg__) readw((dev_priv__)->regs + (reg__))
622621

623622
static bool ilk_pipe_in_vblank_locked(struct drm_device *dev, enum pipe pipe)
624623
{
625624
struct drm_i915_private *dev_priv = dev->dev_private;
626625
uint32_t status;
627-
628-
if (INTEL_INFO(dev)->gen < 7) {
629-
status = pipe == PIPE_A ?
630-
DE_PIPEA_VBLANK :
631-
DE_PIPEB_VBLANK;
626+
int reg;
627+
628+
if (INTEL_INFO(dev)->gen >= 8) {
629+
status = GEN8_PIPE_VBLANK;
630+
reg = GEN8_DE_PIPE_ISR(pipe);
631+
} else if (INTEL_INFO(dev)->gen >= 7) {
632+
status = DE_PIPE_VBLANK_IVB(pipe);
633+
reg = DEISR;
632634
} else {
633-
switch (pipe) {
634-
default:
635-
case PIPE_A:
636-
status = DE_PIPEA_VBLANK_IVB;
637-
break;
638-
case PIPE_B:
639-
status = DE_PIPEB_VBLANK_IVB;
640-
break;
641-
case PIPE_C:
642-
status = DE_PIPEC_VBLANK_IVB;
643-
break;
644-
}
635+
status = DE_PIPE_VBLANK(pipe);
636+
reg = DEISR;
645637
}
646638

647-
return __raw_i915_read32(dev_priv, DEISR) & status;
639+
return __raw_i915_read32(dev_priv, reg) & status;
648640
}
649641

650642
static int i915_get_crtc_scanoutpos(struct drm_device *dev, int pipe,
@@ -702,7 +694,28 @@ static int i915_get_crtc_scanoutpos(struct drm_device *dev, int pipe,
702694
else
703695
position = __raw_i915_read32(dev_priv, PIPEDSL(pipe)) & DSL_LINEMASK_GEN3;
704696

705-
if (HAS_PCH_SPLIT(dev)) {
697+
if (HAS_DDI(dev)) {
698+
/*
699+
* On HSW HDMI outputs there seems to be a 2 line
700+
* difference, whereas eDP has the normal 1 line
701+
* difference that earlier platforms have. External
702+
* DP is unknown. For now just check for the 2 line
703+
* difference case on all output types on HSW+.
704+
*
705+
* This might misinterpret the scanline counter being
706+
* one line too far along on eDP, but that's less
707+
* dangerous than the alternative since that would lead
708+
* the vblank timestamp code astray when it sees a
709+
* scanline count before vblank_start during a vblank
710+
* interrupt.
711+
*/
712+
in_vbl = ilk_pipe_in_vblank_locked(dev, pipe);
713+
if ((in_vbl && (position == vbl_start - 2 ||
714+
position == vbl_start - 1)) ||
715+
(!in_vbl && (position == vbl_end - 2 ||
716+
position == vbl_end - 1)))
717+
position = (position + 2) % vtotal;
718+
} else if (HAS_PCH_SPLIT(dev)) {
706719
/*
707720
* The scanline counter increments at the leading edge
708721
* of hsync, ie. it completely misses the active portion
@@ -2769,10 +2782,9 @@ static void ibx_irq_postinstall(struct drm_device *dev)
27692782
return;
27702783

27712784
if (HAS_PCH_IBX(dev)) {
2772-
mask = SDE_GMBUS | SDE_AUX_MASK | SDE_TRANSB_FIFO_UNDER |
2773-
SDE_TRANSA_FIFO_UNDER | SDE_POISON;
2785+
mask = SDE_GMBUS | SDE_AUX_MASK | SDE_POISON;
27742786
} else {
2775-
mask = SDE_GMBUS_CPT | SDE_AUX_MASK_CPT | SDE_ERROR_CPT;
2787+
mask = SDE_GMBUS_CPT | SDE_AUX_MASK_CPT;
27762788

27772789
I915_WRITE(SERR_INT, I915_READ(SERR_INT));
27782790
}
@@ -2832,20 +2844,19 @@ static int ironlake_irq_postinstall(struct drm_device *dev)
28322844
display_mask = (DE_MASTER_IRQ_CONTROL | DE_GSE_IVB |
28332845
DE_PCH_EVENT_IVB | DE_PLANEC_FLIP_DONE_IVB |
28342846
DE_PLANEB_FLIP_DONE_IVB |
2835-
DE_PLANEA_FLIP_DONE_IVB | DE_AUX_CHANNEL_A_IVB |
2836-
DE_ERR_INT_IVB);
2847+
DE_PLANEA_FLIP_DONE_IVB | DE_AUX_CHANNEL_A_IVB);
28372848
extra_mask = (DE_PIPEC_VBLANK_IVB | DE_PIPEB_VBLANK_IVB |
2838-
DE_PIPEA_VBLANK_IVB);
2849+
DE_PIPEA_VBLANK_IVB | DE_ERR_INT_IVB);
28392850

28402851
I915_WRITE(GEN7_ERR_INT, I915_READ(GEN7_ERR_INT));
28412852
} else {
28422853
display_mask = (DE_MASTER_IRQ_CONTROL | DE_GSE | DE_PCH_EVENT |
28432854
DE_PLANEA_FLIP_DONE | DE_PLANEB_FLIP_DONE |
28442855
DE_AUX_CHANNEL_A |
2845-
DE_PIPEB_FIFO_UNDERRUN | DE_PIPEA_FIFO_UNDERRUN |
28462856
DE_PIPEB_CRC_DONE | DE_PIPEA_CRC_DONE |
28472857
DE_POISON);
2848-
extra_mask = DE_PIPEA_VBLANK | DE_PIPEB_VBLANK | DE_PCU_EVENT;
2858+
extra_mask = DE_PIPEA_VBLANK | DE_PIPEB_VBLANK | DE_PCU_EVENT |
2859+
DE_PIPEB_FIFO_UNDERRUN | DE_PIPEA_FIFO_UNDERRUN;
28492860
}
28502861

28512862
dev_priv->irq_mask = ~display_mask;
@@ -2961,9 +2972,9 @@ static void gen8_de_irq_postinstall(struct drm_i915_private *dev_priv)
29612972
struct drm_device *dev = dev_priv->dev;
29622973
uint32_t de_pipe_masked = GEN8_PIPE_FLIP_DONE |
29632974
GEN8_PIPE_CDCLK_CRC_DONE |
2964-
GEN8_PIPE_FIFO_UNDERRUN |
29652975
GEN8_DE_PIPE_IRQ_FAULT_ERRORS;
2966-
uint32_t de_pipe_enables = de_pipe_masked | GEN8_PIPE_VBLANK;
2976+
uint32_t de_pipe_enables = de_pipe_masked | GEN8_PIPE_VBLANK |
2977+
GEN8_PIPE_FIFO_UNDERRUN;
29672978
int pipe;
29682979
dev_priv->de_irq_mask[PIPE_A] = ~de_pipe_masked;
29692980
dev_priv->de_irq_mask[PIPE_B] = ~de_pipe_masked;

drivers/gpu/drm/i915/intel_ddi.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1244,6 +1244,7 @@ static void intel_ddi_post_disable(struct intel_encoder *intel_encoder)
12441244
if (type == INTEL_OUTPUT_DISPLAYPORT || type == INTEL_OUTPUT_EDP) {
12451245
struct intel_dp *intel_dp = enc_to_intel_dp(encoder);
12461246
intel_dp_sink_dpms(intel_dp, DRM_MODE_DPMS_OFF);
1247+
ironlake_edp_panel_vdd_on(intel_dp);
12471248
ironlake_edp_panel_off(intel_dp);
12481249
}
12491250

drivers/gpu/drm/i915/intel_dp.c

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1249,17 +1249,24 @@ void ironlake_edp_panel_off(struct intel_dp *intel_dp)
12491249

12501250
DRM_DEBUG_KMS("Turn eDP power off\n");
12511251

1252+
WARN(!intel_dp->want_panel_vdd, "Need VDD to turn off panel\n");
1253+
12521254
pp = ironlake_get_pp_control(intel_dp);
12531255
/* We need to switch off panel power _and_ force vdd, for otherwise some
12541256
* panels get very unhappy and cease to work. */
1255-
pp &= ~(POWER_TARGET_ON | PANEL_POWER_RESET | EDP_BLC_ENABLE);
1257+
pp &= ~(POWER_TARGET_ON | EDP_FORCE_VDD | PANEL_POWER_RESET | EDP_BLC_ENABLE);
12561258

12571259
pp_ctrl_reg = _pp_ctrl_reg(intel_dp);
12581260

12591261
I915_WRITE(pp_ctrl_reg, pp);
12601262
POSTING_READ(pp_ctrl_reg);
12611263

1264+
intel_dp->want_panel_vdd = false;
1265+
12621266
ironlake_wait_panel_off(intel_dp);
1267+
1268+
/* We got a reference when we enabled the VDD. */
1269+
intel_runtime_pm_put(dev_priv);
12631270
}
12641271

12651272
void ironlake_edp_backlight_on(struct intel_dp *intel_dp)
@@ -1639,7 +1646,7 @@ static void intel_edp_psr_enable_source(struct intel_dp *intel_dp)
16391646
val |= EDP_PSR_LINK_DISABLE;
16401647

16411648
I915_WRITE(EDP_PSR_CTL(dev), val |
1642-
IS_BROADWELL(dev) ? 0 : link_entry_time |
1649+
(IS_BROADWELL(dev) ? 0 : link_entry_time) |
16431650
max_sleep_time << EDP_PSR_MAX_SLEEP_TIME_SHIFT |
16441651
idle_frames << EDP_PSR_IDLE_FRAME_SHIFT |
16451652
EDP_PSR_ENABLE);
@@ -1784,6 +1791,7 @@ static void intel_disable_dp(struct intel_encoder *encoder)
17841791

17851792
/* Make sure the panel is off before trying to change the mode. But also
17861793
* ensure that we have vdd while we switch off the panel. */
1794+
ironlake_edp_panel_vdd_on(intel_dp);
17871795
ironlake_edp_backlight_off(intel_dp);
17881796
intel_dp_sink_dpms(intel_dp, DRM_MODE_DPMS_OFF);
17891797
ironlake_edp_panel_off(intel_dp);

0 commit comments

Comments
 (0)