aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm
diff options
context:
space:
mode:
authorChris Wilson <chris@chris-wilson.co.uk>2012-07-02 10:51:02 -0400
committerDaniel Vetter <daniel.vetter@ffwll.ch>2012-07-03 16:08:46 -0400
commit990bbdadabaa51828e475eda86ee5720a4910cc3 (patch)
tree596748f31e6f00d21d59cd6c0cdcf9f08a28a219 /drivers/gpu/drm
parent146937e5828ede495e11ba3a6f4a01b36b7166dc (diff)
drm/i915: Group the GT routines together in both code and vtable
Tidy up the routines for interacting with the GT (in particular the forcewake dance) which are scattered throughout the code in a single structure. v2: use wait_for_atomic for polling. v3: *really* use wait_for_atomic for polling. Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk> Signed-off-by: Eugeni Dodonov <eugeni.dodonov@intel.com> Reviewed-by: Ben Widawsky <ben@bwidawsk.net> Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
Diffstat (limited to 'drivers/gpu/drm')
-rw-r--r--drivers/gpu/drm/i915/i915_dma.c2
-rw-r--r--drivers/gpu/drm/i915/i915_drv.c101
-rw-r--r--drivers/gpu/drm/i915/i915_drv.h17
-rw-r--r--drivers/gpu/drm/i915/intel_display.c3
-rw-r--r--drivers/gpu/drm/i915/intel_pm.c30
5 files changed, 73 insertions, 80 deletions
diff --git a/drivers/gpu/drm/i915/i915_dma.c b/drivers/gpu/drm/i915/i915_dma.c
index 216651917fd5..4dc76976c0d0 100644
--- a/drivers/gpu/drm/i915/i915_dma.c
+++ b/drivers/gpu/drm/i915/i915_dma.c
@@ -1548,6 +1548,7 @@ int i915_driver_load(struct drm_device *dev, unsigned long flags)
1548 } 1548 }
1549 1549
1550 intel_irq_init(dev); 1550 intel_irq_init(dev);
1551 intel_gt_init(dev);
1551 1552
1552 /* Try to make sure MCHBAR is enabled before poking at it */ 1553 /* Try to make sure MCHBAR is enabled before poking at it */
1553 intel_setup_mchbar(dev); 1554 intel_setup_mchbar(dev);
@@ -1580,7 +1581,6 @@ int i915_driver_load(struct drm_device *dev, unsigned long flags)
1580 if (!IS_I945G(dev) && !IS_I945GM(dev)) 1581 if (!IS_I945G(dev) && !IS_I945GM(dev))
1581 pci_enable_msi(dev->pdev); 1582 pci_enable_msi(dev->pdev);
1582 1583
1583 spin_lock_init(&dev_priv->gt_lock);
1584 spin_lock_init(&dev_priv->irq_lock); 1584 spin_lock_init(&dev_priv->irq_lock);
1585 spin_lock_init(&dev_priv->error_lock); 1585 spin_lock_init(&dev_priv->error_lock);
1586 spin_lock_init(&dev_priv->rps_lock); 1586 spin_lock_init(&dev_priv->rps_lock);
diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c
index 79be8799ea6c..928b6677759d 100644
--- a/drivers/gpu/drm/i915/i915_drv.c
+++ b/drivers/gpu/drm/i915/i915_drv.c
@@ -32,6 +32,7 @@
32#include "drm.h" 32#include "drm.h"
33#include "i915_drm.h" 33#include "i915_drm.h"
34#include "i915_drv.h" 34#include "i915_drv.h"
35#include "i915_trace.h"
35#include "intel_drv.h" 36#include "intel_drv.h"
36 37
37#include <linux/console.h> 38#include <linux/console.h>
@@ -432,36 +433,26 @@ bool i915_semaphore_is_enabled(struct drm_device *dev)
432 return 1; 433 return 1;
433} 434}
434 435
435void __gen6_gt_force_wake_get(struct drm_i915_private *dev_priv) 436static void __gen6_gt_force_wake_get(struct drm_i915_private *dev_priv)
436{ 437{
437 int count; 438 if (wait_for_atomic_us((I915_READ_NOTRACE(FORCEWAKE_ACK) & 1) == 0, 500))
438 439 DRM_ERROR("Force wake wait timed out\n");
439 count = 0;
440 while (count++ < 50 && (I915_READ_NOTRACE(FORCEWAKE_ACK) & 1))
441 udelay(10);
442 440
443 I915_WRITE_NOTRACE(FORCEWAKE, 1); 441 I915_WRITE_NOTRACE(FORCEWAKE, 1);
444 POSTING_READ(FORCEWAKE);
445 442
446 count = 0; 443 if (wait_for_atomic_us((I915_READ_NOTRACE(FORCEWAKE_ACK) & 1), 500))
447 while (count++ < 50 && (I915_READ_NOTRACE(FORCEWAKE_ACK) & 1) == 0) 444 DRM_ERROR("Force wake wait timed out\n");
448 udelay(10);
449} 445}
450 446
451void __gen6_gt_force_wake_mt_get(struct drm_i915_private *dev_priv) 447static void __gen6_gt_force_wake_mt_get(struct drm_i915_private *dev_priv)
452{ 448{
453 int count; 449 if (wait_for_atomic_us((I915_READ_NOTRACE(FORCEWAKE_MT_ACK) & 1) == 0, 500))
454 450 DRM_ERROR("Force wake wait timed out\n");
455 count = 0;
456 while (count++ < 50 && (I915_READ_NOTRACE(FORCEWAKE_MT_ACK) & 1))
457 udelay(10);
458 451
459 I915_WRITE_NOTRACE(FORCEWAKE_MT, _MASKED_BIT_ENABLE(1)); 452 I915_WRITE_NOTRACE(FORCEWAKE_MT, _MASKED_BIT_ENABLE(1));
460 POSTING_READ(FORCEWAKE_MT);
461 453
462 count = 0; 454 if (wait_for_atomic_us((I915_READ_NOTRACE(FORCEWAKE_MT_ACK) & 1), 500))
463 while (count++ < 50 && (I915_READ_NOTRACE(FORCEWAKE_MT_ACK) & 1) == 0) 455 DRM_ERROR("Force wake wait timed out\n");
464 udelay(10);
465} 456}
466 457
467/* 458/*
@@ -476,7 +467,7 @@ void gen6_gt_force_wake_get(struct drm_i915_private *dev_priv)
476 467
477 spin_lock_irqsave(&dev_priv->gt_lock, irqflags); 468 spin_lock_irqsave(&dev_priv->gt_lock, irqflags);
478 if (dev_priv->forcewake_count++ == 0) 469 if (dev_priv->forcewake_count++ == 0)
479 dev_priv->display.force_wake_get(dev_priv); 470 dev_priv->gt.force_wake_get(dev_priv);
480 spin_unlock_irqrestore(&dev_priv->gt_lock, irqflags); 471 spin_unlock_irqrestore(&dev_priv->gt_lock, irqflags);
481} 472}
482 473
@@ -489,14 +480,14 @@ static void gen6_gt_check_fifodbg(struct drm_i915_private *dev_priv)
489 I915_WRITE_NOTRACE(GTFIFODBG, GT_FIFO_CPU_ERROR_MASK); 480 I915_WRITE_NOTRACE(GTFIFODBG, GT_FIFO_CPU_ERROR_MASK);
490} 481}
491 482
492void __gen6_gt_force_wake_put(struct drm_i915_private *dev_priv) 483static void __gen6_gt_force_wake_put(struct drm_i915_private *dev_priv)
493{ 484{
494 I915_WRITE_NOTRACE(FORCEWAKE, 0); 485 I915_WRITE_NOTRACE(FORCEWAKE, 0);
495 /* The below doubles as a POSTING_READ */ 486 /* The below doubles as a POSTING_READ */
496 gen6_gt_check_fifodbg(dev_priv); 487 gen6_gt_check_fifodbg(dev_priv);
497} 488}
498 489
499void __gen6_gt_force_wake_mt_put(struct drm_i915_private *dev_priv) 490static void __gen6_gt_force_wake_mt_put(struct drm_i915_private *dev_priv)
500{ 491{
501 I915_WRITE_NOTRACE(FORCEWAKE_MT, _MASKED_BIT_DISABLE(1)); 492 I915_WRITE_NOTRACE(FORCEWAKE_MT, _MASKED_BIT_DISABLE(1));
502 /* The below doubles as a POSTING_READ */ 493 /* The below doubles as a POSTING_READ */
@@ -512,7 +503,7 @@ void gen6_gt_force_wake_put(struct drm_i915_private *dev_priv)
512 503
513 spin_lock_irqsave(&dev_priv->gt_lock, irqflags); 504 spin_lock_irqsave(&dev_priv->gt_lock, irqflags);
514 if (--dev_priv->forcewake_count == 0) 505 if (--dev_priv->forcewake_count == 0)
515 dev_priv->display.force_wake_put(dev_priv); 506 dev_priv->gt.force_wake_put(dev_priv);
516 spin_unlock_irqrestore(&dev_priv->gt_lock, irqflags); 507 spin_unlock_irqrestore(&dev_priv->gt_lock, irqflags);
517} 508}
518 509
@@ -536,12 +527,8 @@ int __gen6_gt_wait_for_fifo(struct drm_i915_private *dev_priv)
536 return ret; 527 return ret;
537} 528}
538 529
539void vlv_force_wake_get(struct drm_i915_private *dev_priv) 530static void vlv_force_wake_get(struct drm_i915_private *dev_priv)
540{ 531{
541 int count;
542
543 count = 0;
544
545 /* Already awake? */ 532 /* Already awake? */
546 if ((I915_READ(0x130094) & 0xa1) == 0xa1) 533 if ((I915_READ(0x130094) & 0xa1) == 0xa1)
547 return; 534 return;
@@ -549,18 +536,58 @@ void vlv_force_wake_get(struct drm_i915_private *dev_priv)
549 I915_WRITE_NOTRACE(FORCEWAKE_VLV, 0xffffffff); 536 I915_WRITE_NOTRACE(FORCEWAKE_VLV, 0xffffffff);
550 POSTING_READ(FORCEWAKE_VLV); 537 POSTING_READ(FORCEWAKE_VLV);
551 538
552 count = 0; 539 if (wait_for_atomic_us((I915_READ_NOTRACE(FORCEWAKE_ACK_VLV) & 1), 500))
553 while (count++ < 50 && (I915_READ_NOTRACE(FORCEWAKE_ACK_VLV) & 1) == 0) 540 DRM_ERROR("Force wake wait timed out\n");
554 udelay(10);
555} 541}
556 542
557void vlv_force_wake_put(struct drm_i915_private *dev_priv) 543static void vlv_force_wake_put(struct drm_i915_private *dev_priv)
558{ 544{
559 I915_WRITE_NOTRACE(FORCEWAKE_VLV, 0xffff0000); 545 I915_WRITE_NOTRACE(FORCEWAKE_VLV, 0xffff0000);
560 /* FIXME: confirm VLV behavior with Punit folks */ 546 /* FIXME: confirm VLV behavior with Punit folks */
561 POSTING_READ(FORCEWAKE_VLV); 547 POSTING_READ(FORCEWAKE_VLV);
562} 548}
563 549
550void intel_gt_init(struct drm_device *dev)
551{
552 struct drm_i915_private *dev_priv = dev->dev_private;
553
554 spin_lock_init(&dev_priv->gt_lock);
555
556 if (IS_VALLEYVIEW(dev)) {
557 dev_priv->gt.force_wake_get = vlv_force_wake_get;
558 dev_priv->gt.force_wake_put = vlv_force_wake_put;
559 } else if (INTEL_INFO(dev)->gen >= 6) {
560 dev_priv->gt.force_wake_get = __gen6_gt_force_wake_get;
561 dev_priv->gt.force_wake_put = __gen6_gt_force_wake_put;
562
563 /* IVB configs may use multi-threaded forcewake */
564 if (IS_IVYBRIDGE(dev) || IS_HASWELL(dev)) {
565 u32 ecobus;
566
567 /* A small trick here - if the bios hasn't configured
568 * MT forcewake, and if the device is in RC6, then
569 * force_wake_mt_get will not wake the device and the
570 * ECOBUS read will return zero. Which will be
571 * (correctly) interpreted by the test below as MT
572 * forcewake being disabled.
573 */
574 mutex_lock(&dev->struct_mutex);
575 __gen6_gt_force_wake_mt_get(dev_priv);
576 ecobus = I915_READ_NOTRACE(ECOBUS);
577 __gen6_gt_force_wake_mt_put(dev_priv);
578 mutex_unlock(&dev->struct_mutex);
579
580 if (ecobus & FORCEWAKE_MT_ENABLE) {
581 DRM_DEBUG_KMS("Using MT version of forcewake\n");
582 dev_priv->gt.force_wake_get =
583 __gen6_gt_force_wake_mt_get;
584 dev_priv->gt.force_wake_put =
585 __gen6_gt_force_wake_mt_put;
586 }
587 }
588 }
589}
590
564static int i915_drm_freeze(struct drm_device *dev) 591static int i915_drm_freeze(struct drm_device *dev)
565{ 592{
566 struct drm_i915_private *dev_priv = dev->dev_private; 593 struct drm_i915_private *dev_priv = dev->dev_private;
@@ -797,9 +824,9 @@ static int gen6_do_reset(struct drm_device *dev)
797 824
798 /* If reset with a user forcewake, try to restore, otherwise turn it off */ 825 /* If reset with a user forcewake, try to restore, otherwise turn it off */
799 if (dev_priv->forcewake_count) 826 if (dev_priv->forcewake_count)
800 dev_priv->display.force_wake_get(dev_priv); 827 dev_priv->gt.force_wake_get(dev_priv);
801 else 828 else
802 dev_priv->display.force_wake_put(dev_priv); 829 dev_priv->gt.force_wake_put(dev_priv);
803 830
804 /* Restore fifo count */ 831 /* Restore fifo count */
805 dev_priv->gt_fifo_count = I915_READ_NOTRACE(GT_FIFO_FREE_ENTRIES); 832 dev_priv->gt_fifo_count = I915_READ_NOTRACE(GT_FIFO_FREE_ENTRIES);
@@ -1248,10 +1275,10 @@ u##x i915_read##x(struct drm_i915_private *dev_priv, u32 reg) { \
1248 unsigned long irqflags; \ 1275 unsigned long irqflags; \
1249 spin_lock_irqsave(&dev_priv->gt_lock, irqflags); \ 1276 spin_lock_irqsave(&dev_priv->gt_lock, irqflags); \
1250 if (dev_priv->forcewake_count == 0) \ 1277 if (dev_priv->forcewake_count == 0) \
1251 dev_priv->display.force_wake_get(dev_priv); \ 1278 dev_priv->gt.force_wake_get(dev_priv); \
1252 val = read##y(dev_priv->regs + reg); \ 1279 val = read##y(dev_priv->regs + reg); \
1253 if (dev_priv->forcewake_count == 0) \ 1280 if (dev_priv->forcewake_count == 0) \
1254 dev_priv->display.force_wake_put(dev_priv); \ 1281 dev_priv->gt.force_wake_put(dev_priv); \
1255 spin_unlock_irqrestore(&dev_priv->gt_lock, irqflags); \ 1282 spin_unlock_irqrestore(&dev_priv->gt_lock, irqflags); \
1256 } else if (IS_VALLEYVIEW(dev_priv->dev) && IS_DISPLAYREG(reg)) { \ 1283 } else if (IS_VALLEYVIEW(dev_priv->dev) && IS_DISPLAYREG(reg)) { \
1257 val = read##y(dev_priv->regs + reg + 0x180000); \ 1284 val = read##y(dev_priv->regs + reg + 0x180000); \
diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h
index a0c15abbdcef..60f6974d20d4 100644
--- a/drivers/gpu/drm/i915/i915_drv.h
+++ b/drivers/gpu/drm/i915/i915_drv.h
@@ -262,8 +262,6 @@ struct drm_i915_display_funcs {
262 struct drm_i915_gem_object *obj); 262 struct drm_i915_gem_object *obj);
263 int (*update_plane)(struct drm_crtc *crtc, struct drm_framebuffer *fb, 263 int (*update_plane)(struct drm_crtc *crtc, struct drm_framebuffer *fb,
264 int x, int y); 264 int x, int y);
265 void (*force_wake_get)(struct drm_i915_private *dev_priv);
266 void (*force_wake_put)(struct drm_i915_private *dev_priv);
267 /* clock updates for mode set */ 265 /* clock updates for mode set */
268 /* cursor updates */ 266 /* cursor updates */
269 /* render clock increase/decrease */ 267 /* render clock increase/decrease */
@@ -271,6 +269,11 @@ struct drm_i915_display_funcs {
271 /* pll clock increase/decrease */ 269 /* pll clock increase/decrease */
272}; 270};
273 271
272struct drm_i915_gt_funcs {
273 void (*force_wake_get)(struct drm_i915_private *dev_priv);
274 void (*force_wake_put)(struct drm_i915_private *dev_priv);
275};
276
274struct intel_device_info { 277struct intel_device_info {
275 u8 gen; 278 u8 gen;
276 u8 is_mobile:1; 279 u8 is_mobile:1;
@@ -362,6 +365,8 @@ typedef struct drm_i915_private {
362 int relative_constants_mode; 365 int relative_constants_mode;
363 366
364 void __iomem *regs; 367 void __iomem *regs;
368
369 struct drm_i915_gt_funcs gt;
365 /** gt_fifo_count and the subsequent register write are synchronized 370 /** gt_fifo_count and the subsequent register write are synchronized
366 * with dev->struct_mutex. */ 371 * with dev->struct_mutex. */
367 unsigned gt_fifo_count; 372 unsigned gt_fifo_count;
@@ -1200,6 +1205,7 @@ void i915_hangcheck_elapsed(unsigned long data);
1200void i915_handle_error(struct drm_device *dev, bool wedged); 1205void i915_handle_error(struct drm_device *dev, bool wedged);
1201 1206
1202extern void intel_irq_init(struct drm_device *dev); 1207extern void intel_irq_init(struct drm_device *dev);
1208extern void intel_gt_init(struct drm_device *dev);
1203 1209
1204void i915_error_state_free(struct kref *error_ref); 1210void i915_error_state_free(struct kref *error_ref);
1205 1211
@@ -1517,13 +1523,6 @@ extern int intel_trans_dp_port_sel(struct drm_crtc *crtc);
1517extern int intel_enable_rc6(const struct drm_device *dev); 1523extern int intel_enable_rc6(const struct drm_device *dev);
1518 1524
1519extern bool i915_semaphore_is_enabled(struct drm_device *dev); 1525extern bool i915_semaphore_is_enabled(struct drm_device *dev);
1520extern void __gen6_gt_force_wake_get(struct drm_i915_private *dev_priv);
1521extern void __gen6_gt_force_wake_mt_get(struct drm_i915_private *dev_priv);
1522extern void __gen6_gt_force_wake_put(struct drm_i915_private *dev_priv);
1523extern void __gen6_gt_force_wake_mt_put(struct drm_i915_private *dev_priv);
1524
1525extern void vlv_force_wake_get(struct drm_i915_private *dev_priv);
1526extern void vlv_force_wake_put(struct drm_i915_private *dev_priv);
1527 1526
1528/* overlay */ 1527/* overlay */
1529#ifdef CONFIG_DEBUG_FS 1528#ifdef CONFIG_DEBUG_FS
diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c
index 3fbc802b4940..342f18e9cbe0 100644
--- a/drivers/gpu/drm/i915/intel_display.c
+++ b/drivers/gpu/drm/i915/intel_display.c
@@ -7013,9 +7013,6 @@ static void intel_init_display(struct drm_device *dev)
7013 dev_priv->display.write_eld = ironlake_write_eld; 7013 dev_priv->display.write_eld = ironlake_write_eld;
7014 } else 7014 } else
7015 dev_priv->display.update_wm = NULL; 7015 dev_priv->display.update_wm = NULL;
7016 } else if (IS_VALLEYVIEW(dev)) {
7017 dev_priv->display.force_wake_get = vlv_force_wake_get;
7018 dev_priv->display.force_wake_put = vlv_force_wake_put;
7019 } else if (IS_G4X(dev)) { 7016 } else if (IS_G4X(dev)) {
7020 dev_priv->display.write_eld = g4x_write_eld; 7017 dev_priv->display.write_eld = g4x_write_eld;
7021 } 7018 }
diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c
index 99bc1f33bfcb..ed9912ca1f82 100644
--- a/drivers/gpu/drm/i915/intel_pm.c
+++ b/drivers/gpu/drm/i915/intel_pm.c
@@ -3765,34 +3765,6 @@ void intel_init_pm(struct drm_device *dev)
3765 3765
3766 /* For FIFO watermark updates */ 3766 /* For FIFO watermark updates */
3767 if (HAS_PCH_SPLIT(dev)) { 3767 if (HAS_PCH_SPLIT(dev)) {
3768 dev_priv->display.force_wake_get = __gen6_gt_force_wake_get;
3769 dev_priv->display.force_wake_put = __gen6_gt_force_wake_put;
3770
3771 /* IVB configs may use multi-threaded forcewake */
3772 if (IS_IVYBRIDGE(dev) || IS_HASWELL(dev)) {
3773 u32 ecobus;
3774
3775 /* A small trick here - if the bios hasn't configured MT forcewake,
3776 * and if the device is in RC6, then force_wake_mt_get will not wake
3777 * the device and the ECOBUS read will return zero. Which will be
3778 * (correctly) interpreted by the test below as MT forcewake being
3779 * disabled.
3780 */
3781 mutex_lock(&dev->struct_mutex);
3782 __gen6_gt_force_wake_mt_get(dev_priv);
3783 ecobus = I915_READ_NOTRACE(ECOBUS);
3784 __gen6_gt_force_wake_mt_put(dev_priv);
3785 mutex_unlock(&dev->struct_mutex);
3786
3787 if (ecobus & FORCEWAKE_MT_ENABLE) {
3788 DRM_DEBUG_KMS("Using MT version of forcewake\n");
3789 dev_priv->display.force_wake_get =
3790 __gen6_gt_force_wake_mt_get;
3791 dev_priv->display.force_wake_put =
3792 __gen6_gt_force_wake_mt_put;
3793 }
3794 }
3795
3796 if (HAS_PCH_IBX(dev)) 3768 if (HAS_PCH_IBX(dev))
3797 dev_priv->display.init_pch_clock_gating = ibx_init_clock_gating; 3769 dev_priv->display.init_pch_clock_gating = ibx_init_clock_gating;
3798 else if (HAS_PCH_CPT(dev)) 3770 else if (HAS_PCH_CPT(dev))
@@ -3848,8 +3820,6 @@ void intel_init_pm(struct drm_device *dev)
3848 dev_priv->display.update_wm = valleyview_update_wm; 3820 dev_priv->display.update_wm = valleyview_update_wm;
3849 dev_priv->display.init_clock_gating = 3821 dev_priv->display.init_clock_gating =
3850 valleyview_init_clock_gating; 3822 valleyview_init_clock_gating;
3851 dev_priv->display.force_wake_get = vlv_force_wake_get;
3852 dev_priv->display.force_wake_put = vlv_force_wake_put;
3853 } else if (IS_PINEVIEW(dev)) { 3823 } else if (IS_PINEVIEW(dev)) {
3854 if (!intel_get_cxsr_latency(IS_PINEVIEW_G(dev), 3824 if (!intel_get_cxsr_latency(IS_PINEVIEW_G(dev),
3855 dev_priv->is_ddr3, 3825 dev_priv->is_ddr3,