diff options
author | Shaohua Li <shaohua.li@intel.com> | 2009-02-23 02:19:16 -0500 |
---|---|---|
committer | Eric Anholt <eric@anholt.net> | 2009-03-27 18:12:08 -0400 |
commit | 2177832f2e20fceb32142bb4fd33ae68c8af8c5a (patch) | |
tree | 2513a3230ab064dbc723ec868d90575dea25e652 | |
parent | ad086c833d00ef3be56ec554b1061f19e87a6210 (diff) |
agp/intel: Add support for new intel chipset.
This is a G33-like desktop and mobile chipset.
Signed-off-by: Shaohua Li <shaohua.li@intel.com>
Signed-off-by: Eric Anholt <eric@anholt.net>
-rw-r--r-- | drivers/char/agp/intel-agp.c | 21 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/i915_drv.h | 10 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/i915_reg.h | 4 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/intel_display.c | 113 | ||||
-rw-r--r-- | include/drm/drm_pciids.h | 2 |
5 files changed, 128 insertions, 22 deletions
diff --git a/drivers/char/agp/intel-agp.c b/drivers/char/agp/intel-agp.c index 4373adb2119a..9d9490e22e07 100644 --- a/drivers/char/agp/intel-agp.c +++ b/drivers/char/agp/intel-agp.c | |||
@@ -26,6 +26,10 @@ | |||
26 | #define PCI_DEVICE_ID_INTEL_82965GME_IG 0x2A12 | 26 | #define PCI_DEVICE_ID_INTEL_82965GME_IG 0x2A12 |
27 | #define PCI_DEVICE_ID_INTEL_82945GME_HB 0x27AC | 27 | #define PCI_DEVICE_ID_INTEL_82945GME_HB 0x27AC |
28 | #define PCI_DEVICE_ID_INTEL_82945GME_IG 0x27AE | 28 | #define PCI_DEVICE_ID_INTEL_82945GME_IG 0x27AE |
29 | #define PCI_DEVICE_ID_INTEL_IGDGM_HB 0xA010 | ||
30 | #define PCI_DEVICE_ID_INTEL_IGDGM_IG 0xA011 | ||
31 | #define PCI_DEVICE_ID_INTEL_IGDG_HB 0xA000 | ||
32 | #define PCI_DEVICE_ID_INTEL_IGDG_IG 0xA001 | ||
29 | #define PCI_DEVICE_ID_INTEL_G33_HB 0x29C0 | 33 | #define PCI_DEVICE_ID_INTEL_G33_HB 0x29C0 |
30 | #define PCI_DEVICE_ID_INTEL_G33_IG 0x29C2 | 34 | #define PCI_DEVICE_ID_INTEL_G33_IG 0x29C2 |
31 | #define PCI_DEVICE_ID_INTEL_Q35_HB 0x29B0 | 35 | #define PCI_DEVICE_ID_INTEL_Q35_HB 0x29B0 |
@@ -60,7 +64,12 @@ | |||
60 | 64 | ||
61 | #define IS_G33 (agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_G33_HB || \ | 65 | #define IS_G33 (agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_G33_HB || \ |
62 | agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_Q35_HB || \ | 66 | agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_Q35_HB || \ |
63 | agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_Q33_HB) | 67 | agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_Q33_HB || \ |
68 | agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_IGDGM_HB || \ | ||
69 | agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_IGDG_HB) | ||
70 | |||
71 | #define IS_IGD (agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_IGDGM_HB || \ | ||
72 | agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_IGDG_HB) | ||
64 | 73 | ||
65 | #define IS_G4X (agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_IGD_E_HB || \ | 74 | #define IS_G4X (agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_IGD_E_HB || \ |
66 | agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_Q45_HB || \ | 75 | agp_bridge->dev->device == PCI_DEVICE_ID_INTEL_Q45_HB || \ |
@@ -510,7 +519,7 @@ static void intel_i830_init_gtt_entries(void) | |||
510 | size = 512; | 519 | size = 512; |
511 | } | 520 | } |
512 | size += 4; /* add in BIOS popup space */ | 521 | size += 4; /* add in BIOS popup space */ |
513 | } else if (IS_G33) { | 522 | } else if (IS_G33 && !IS_IGD) { |
514 | /* G33's GTT size defined in gmch_ctrl */ | 523 | /* G33's GTT size defined in gmch_ctrl */ |
515 | switch (gmch_ctrl & G33_PGETBL_SIZE_MASK) { | 524 | switch (gmch_ctrl & G33_PGETBL_SIZE_MASK) { |
516 | case G33_PGETBL_SIZE_1M: | 525 | case G33_PGETBL_SIZE_1M: |
@@ -526,7 +535,7 @@ static void intel_i830_init_gtt_entries(void) | |||
526 | size = 512; | 535 | size = 512; |
527 | } | 536 | } |
528 | size += 4; | 537 | size += 4; |
529 | } else if (IS_G4X) { | 538 | } else if (IS_G4X || IS_IGD) { |
530 | /* On 4 series hardware, GTT stolen is separate from graphics | 539 | /* On 4 series hardware, GTT stolen is separate from graphics |
531 | * stolen, ignore it in stolen gtt entries counting. However, | 540 | * stolen, ignore it in stolen gtt entries counting. However, |
532 | * 4KB of the stolen memory doesn't get mapped to the GTT. | 541 | * 4KB of the stolen memory doesn't get mapped to the GTT. |
@@ -2161,6 +2170,10 @@ static const struct intel_driver_description { | |||
2161 | NULL, &intel_g33_driver }, | 2170 | NULL, &intel_g33_driver }, |
2162 | { PCI_DEVICE_ID_INTEL_Q33_HB, PCI_DEVICE_ID_INTEL_Q33_IG, 0, "Q33", | 2171 | { PCI_DEVICE_ID_INTEL_Q33_HB, PCI_DEVICE_ID_INTEL_Q33_IG, 0, "Q33", |
2163 | NULL, &intel_g33_driver }, | 2172 | NULL, &intel_g33_driver }, |
2173 | { PCI_DEVICE_ID_INTEL_IGDGM_HB, PCI_DEVICE_ID_INTEL_IGDGM_IG, 0, "IGD", | ||
2174 | NULL, &intel_g33_driver }, | ||
2175 | { PCI_DEVICE_ID_INTEL_IGDG_HB, PCI_DEVICE_ID_INTEL_IGDG_IG, 0, "IGD", | ||
2176 | NULL, &intel_g33_driver }, | ||
2164 | { PCI_DEVICE_ID_INTEL_GM45_HB, PCI_DEVICE_ID_INTEL_GM45_IG, 0, | 2177 | { PCI_DEVICE_ID_INTEL_GM45_HB, PCI_DEVICE_ID_INTEL_GM45_IG, 0, |
2165 | "Mobile IntelĀ® GM45 Express", NULL, &intel_i965_driver }, | 2178 | "Mobile IntelĀ® GM45 Express", NULL, &intel_i965_driver }, |
2166 | { PCI_DEVICE_ID_INTEL_IGD_E_HB, PCI_DEVICE_ID_INTEL_IGD_E_IG, 0, | 2179 | { PCI_DEVICE_ID_INTEL_IGD_E_HB, PCI_DEVICE_ID_INTEL_IGD_E_IG, 0, |
@@ -2355,6 +2368,8 @@ static struct pci_device_id agp_intel_pci_table[] = { | |||
2355 | ID(PCI_DEVICE_ID_INTEL_82945G_HB), | 2368 | ID(PCI_DEVICE_ID_INTEL_82945G_HB), |
2356 | ID(PCI_DEVICE_ID_INTEL_82945GM_HB), | 2369 | ID(PCI_DEVICE_ID_INTEL_82945GM_HB), |
2357 | ID(PCI_DEVICE_ID_INTEL_82945GME_HB), | 2370 | ID(PCI_DEVICE_ID_INTEL_82945GME_HB), |
2371 | ID(PCI_DEVICE_ID_INTEL_IGDGM_HB), | ||
2372 | ID(PCI_DEVICE_ID_INTEL_IGDG_HB), | ||
2358 | ID(PCI_DEVICE_ID_INTEL_82946GZ_HB), | 2373 | ID(PCI_DEVICE_ID_INTEL_82946GZ_HB), |
2359 | ID(PCI_DEVICE_ID_INTEL_82G35_HB), | 2374 | ID(PCI_DEVICE_ID_INTEL_82G35_HB), |
2360 | ID(PCI_DEVICE_ID_INTEL_82965Q_HB), | 2375 | ID(PCI_DEVICE_ID_INTEL_82965Q_HB), |
diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index 1c03b3e81ffa..c1685d0c704f 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h | |||
@@ -787,15 +787,21 @@ extern int i915_wait_ring(struct drm_device * dev, int n, const char *caller); | |||
787 | (dev)->pci_device == 0x2E22 || \ | 787 | (dev)->pci_device == 0x2E22 || \ |
788 | IS_GM45(dev)) | 788 | IS_GM45(dev)) |
789 | 789 | ||
790 | #define IS_IGDG(dev) ((dev)->pci_device == 0xa001) | ||
791 | #define IS_IGDGM(dev) ((dev)->pci_device == 0xa011) | ||
792 | #define IS_IGD(dev) (IS_IGDG(dev) || IS_IGDGM(dev)) | ||
793 | |||
790 | #define IS_G33(dev) ((dev)->pci_device == 0x29C2 || \ | 794 | #define IS_G33(dev) ((dev)->pci_device == 0x29C2 || \ |
791 | (dev)->pci_device == 0x29B2 || \ | 795 | (dev)->pci_device == 0x29B2 || \ |
792 | (dev)->pci_device == 0x29D2) | 796 | (dev)->pci_device == 0x29D2 || \ |
797 | (IS_IGD(dev))) | ||
793 | 798 | ||
794 | #define IS_I9XX(dev) (IS_I915G(dev) || IS_I915GM(dev) || IS_I945G(dev) || \ | 799 | #define IS_I9XX(dev) (IS_I915G(dev) || IS_I915GM(dev) || IS_I945G(dev) || \ |
795 | IS_I945GM(dev) || IS_I965G(dev) || IS_G33(dev)) | 800 | IS_I945GM(dev) || IS_I965G(dev) || IS_G33(dev)) |
796 | 801 | ||
797 | #define IS_MOBILE(dev) (IS_I830(dev) || IS_I85X(dev) || IS_I915GM(dev) || \ | 802 | #define IS_MOBILE(dev) (IS_I830(dev) || IS_I85X(dev) || IS_I915GM(dev) || \ |
798 | IS_I945GM(dev) || IS_I965GM(dev) || IS_GM45(dev)) | 803 | IS_I945GM(dev) || IS_I965GM(dev) || IS_GM45(dev) || \ |
804 | IS_IGD(dev)) | ||
799 | 805 | ||
800 | #define I915_NEED_GFX_HWS(dev) (IS_G33(dev) || IS_GM45(dev) || IS_G4X(dev)) | 806 | #define I915_NEED_GFX_HWS(dev) (IS_G33(dev) || IS_GM45(dev) || IS_G4X(dev)) |
801 | /* With the 945 and later, Y tiling got adjusted so that it was 32 128-byte | 807 | /* With the 945 and later, Y tiling got adjusted so that it was 32 128-byte |
diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h index 90600d899413..6d567772679b 100644 --- a/drivers/gpu/drm/i915/i915_reg.h +++ b/drivers/gpu/drm/i915/i915_reg.h | |||
@@ -359,6 +359,7 @@ | |||
359 | #define DPLLB_LVDS_P2_CLOCK_DIV_7 (1 << 24) /* i915 */ | 359 | #define DPLLB_LVDS_P2_CLOCK_DIV_7 (1 << 24) /* i915 */ |
360 | #define DPLL_P2_CLOCK_DIV_MASK 0x03000000 /* i915 */ | 360 | #define DPLL_P2_CLOCK_DIV_MASK 0x03000000 /* i915 */ |
361 | #define DPLL_FPA01_P1_POST_DIV_MASK 0x00ff0000 /* i915 */ | 361 | #define DPLL_FPA01_P1_POST_DIV_MASK 0x00ff0000 /* i915 */ |
362 | #define DPLL_FPA01_P1_POST_DIV_MASK_IGD 0x00ff8000 /* IGD */ | ||
362 | 363 | ||
363 | #define I915_FIFO_UNDERRUN_STATUS (1UL<<31) | 364 | #define I915_FIFO_UNDERRUN_STATUS (1UL<<31) |
364 | #define I915_CRC_ERROR_ENABLE (1UL<<29) | 365 | #define I915_CRC_ERROR_ENABLE (1UL<<29) |
@@ -435,6 +436,7 @@ | |||
435 | */ | 436 | */ |
436 | #define DPLL_FPA01_P1_POST_DIV_MASK_I830_LVDS 0x003f0000 | 437 | #define DPLL_FPA01_P1_POST_DIV_MASK_I830_LVDS 0x003f0000 |
437 | #define DPLL_FPA01_P1_POST_DIV_SHIFT 16 | 438 | #define DPLL_FPA01_P1_POST_DIV_SHIFT 16 |
439 | #define DPLL_FPA01_P1_POST_DIV_SHIFT_IGD 15 | ||
438 | /* i830, required in DVO non-gang */ | 440 | /* i830, required in DVO non-gang */ |
439 | #define PLL_P2_DIVIDE_BY_4 (1 << 23) | 441 | #define PLL_P2_DIVIDE_BY_4 (1 << 23) |
440 | #define PLL_P1_DIVIDE_BY_TWO (1 << 21) /* i830 */ | 442 | #define PLL_P1_DIVIDE_BY_TWO (1 << 21) /* i830 */ |
@@ -501,10 +503,12 @@ | |||
501 | #define FPB0 0x06048 | 503 | #define FPB0 0x06048 |
502 | #define FPB1 0x0604c | 504 | #define FPB1 0x0604c |
503 | #define FP_N_DIV_MASK 0x003f0000 | 505 | #define FP_N_DIV_MASK 0x003f0000 |
506 | #define FP_N_IGD_DIV_MASK 0x00ff0000 | ||
504 | #define FP_N_DIV_SHIFT 16 | 507 | #define FP_N_DIV_SHIFT 16 |
505 | #define FP_M1_DIV_MASK 0x00003f00 | 508 | #define FP_M1_DIV_MASK 0x00003f00 |
506 | #define FP_M1_DIV_SHIFT 8 | 509 | #define FP_M1_DIV_SHIFT 8 |
507 | #define FP_M2_DIV_MASK 0x0000003f | 510 | #define FP_M2_DIV_MASK 0x0000003f |
511 | #define FP_M2_IGD_DIV_MASK 0x000000ff | ||
508 | #define FP_M2_DIV_SHIFT 0 | 512 | #define FP_M2_DIV_SHIFT 0 |
509 | #define DPLL_TEST 0x606c | 513 | #define DPLL_TEST 0x606c |
510 | #define DPLLB_TEST_SDVO_DIV_1 (0 << 22) | 514 | #define DPLLB_TEST_SDVO_DIV_1 (0 << 22) |
diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index 0d40b4b6979e..d9c50ff94d76 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c | |||
@@ -92,18 +92,32 @@ struct intel_limit { | |||
92 | #define I9XX_DOT_MAX 400000 | 92 | #define I9XX_DOT_MAX 400000 |
93 | #define I9XX_VCO_MIN 1400000 | 93 | #define I9XX_VCO_MIN 1400000 |
94 | #define I9XX_VCO_MAX 2800000 | 94 | #define I9XX_VCO_MAX 2800000 |
95 | #define IGD_VCO_MIN 1700000 | ||
96 | #define IGD_VCO_MAX 3500000 | ||
95 | #define I9XX_N_MIN 1 | 97 | #define I9XX_N_MIN 1 |
96 | #define I9XX_N_MAX 6 | 98 | #define I9XX_N_MAX 6 |
99 | /* IGD's Ncounter is a ring counter */ | ||
100 | #define IGD_N_MIN 3 | ||
101 | #define IGD_N_MAX 6 | ||
97 | #define I9XX_M_MIN 70 | 102 | #define I9XX_M_MIN 70 |
98 | #define I9XX_M_MAX 120 | 103 | #define I9XX_M_MAX 120 |
104 | #define IGD_M_MIN 2 | ||
105 | #define IGD_M_MAX 256 | ||
99 | #define I9XX_M1_MIN 10 | 106 | #define I9XX_M1_MIN 10 |
100 | #define I9XX_M1_MAX 22 | 107 | #define I9XX_M1_MAX 22 |
101 | #define I9XX_M2_MIN 5 | 108 | #define I9XX_M2_MIN 5 |
102 | #define I9XX_M2_MAX 9 | 109 | #define I9XX_M2_MAX 9 |
110 | /* IGD M1 is reserved, and must be 0 */ | ||
111 | #define IGD_M1_MIN 0 | ||
112 | #define IGD_M1_MAX 0 | ||
113 | #define IGD_M2_MIN 0 | ||
114 | #define IGD_M2_MAX 254 | ||
103 | #define I9XX_P_SDVO_DAC_MIN 5 | 115 | #define I9XX_P_SDVO_DAC_MIN 5 |
104 | #define I9XX_P_SDVO_DAC_MAX 80 | 116 | #define I9XX_P_SDVO_DAC_MAX 80 |
105 | #define I9XX_P_LVDS_MIN 7 | 117 | #define I9XX_P_LVDS_MIN 7 |
106 | #define I9XX_P_LVDS_MAX 98 | 118 | #define I9XX_P_LVDS_MAX 98 |
119 | #define IGD_P_LVDS_MIN 7 | ||
120 | #define IGD_P_LVDS_MAX 112 | ||
107 | #define I9XX_P1_MIN 1 | 121 | #define I9XX_P1_MIN 1 |
108 | #define I9XX_P1_MAX 8 | 122 | #define I9XX_P1_MAX 8 |
109 | #define I9XX_P2_SDVO_DAC_SLOW 10 | 123 | #define I9XX_P2_SDVO_DAC_SLOW 10 |
@@ -121,6 +135,8 @@ struct intel_limit { | |||
121 | #define INTEL_LIMIT_G4X_HDMI_DAC 5 | 135 | #define INTEL_LIMIT_G4X_HDMI_DAC 5 |
122 | #define INTEL_LIMIT_G4X_SINGLE_CHANNEL_LVDS 6 | 136 | #define INTEL_LIMIT_G4X_SINGLE_CHANNEL_LVDS 6 |
123 | #define INTEL_LIMIT_G4X_DUAL_CHANNEL_LVDS 7 | 137 | #define INTEL_LIMIT_G4X_DUAL_CHANNEL_LVDS 7 |
138 | #define INTEL_LIMIT_IGD_SDVO_DAC 8 | ||
139 | #define INTEL_LIMIT_IGD_LVDS 9 | ||
124 | 140 | ||
125 | /*The parameter is for SDVO on G4x platform*/ | 141 | /*The parameter is for SDVO on G4x platform*/ |
126 | #define G4X_DOT_SDVO_MIN 25000 | 142 | #define G4X_DOT_SDVO_MIN 25000 |
@@ -340,6 +356,32 @@ static const intel_limit_t intel_limits[] = { | |||
340 | }, | 356 | }, |
341 | .find_pll = intel_g4x_find_best_PLL, | 357 | .find_pll = intel_g4x_find_best_PLL, |
342 | }, | 358 | }, |
359 | { /* INTEL_LIMIT_IGD_SDVO */ | ||
360 | .dot = { .min = I9XX_DOT_MIN, .max = I9XX_DOT_MAX}, | ||
361 | .vco = { .min = IGD_VCO_MIN, .max = IGD_VCO_MAX }, | ||
362 | .n = { .min = IGD_N_MIN, .max = IGD_N_MAX }, | ||
363 | .m = { .min = IGD_M_MIN, .max = IGD_M_MAX }, | ||
364 | .m1 = { .min = IGD_M1_MIN, .max = IGD_M1_MAX }, | ||
365 | .m2 = { .min = IGD_M2_MIN, .max = IGD_M2_MAX }, | ||
366 | .p = { .min = I9XX_P_SDVO_DAC_MIN, .max = I9XX_P_SDVO_DAC_MAX }, | ||
367 | .p1 = { .min = I9XX_P1_MIN, .max = I9XX_P1_MAX }, | ||
368 | .p2 = { .dot_limit = I9XX_P2_SDVO_DAC_SLOW_LIMIT, | ||
369 | .p2_slow = I9XX_P2_SDVO_DAC_SLOW, .p2_fast = I9XX_P2_SDVO_DAC_FAST }, | ||
370 | }, | ||
371 | { /* INTEL_LIMIT_IGD_LVDS */ | ||
372 | .dot = { .min = I9XX_DOT_MIN, .max = I9XX_DOT_MAX }, | ||
373 | .vco = { .min = IGD_VCO_MIN, .max = IGD_VCO_MAX }, | ||
374 | .n = { .min = IGD_N_MIN, .max = IGD_N_MAX }, | ||
375 | .m = { .min = IGD_M_MIN, .max = IGD_M_MAX }, | ||
376 | .m1 = { .min = IGD_M1_MIN, .max = IGD_M1_MAX }, | ||
377 | .m2 = { .min = IGD_M2_MIN, .max = IGD_M2_MAX }, | ||
378 | .p = { .min = IGD_P_LVDS_MIN, .max = IGD_P_LVDS_MAX }, | ||
379 | .p1 = { .min = I9XX_P1_MIN, .max = I9XX_P1_MAX }, | ||
380 | /* IGD only supports single-channel mode. */ | ||
381 | .p2 = { .dot_limit = I9XX_P2_LVDS_SLOW_LIMIT, | ||
382 | .p2_slow = I9XX_P2_LVDS_SLOW, .p2_fast = I9XX_P2_LVDS_SLOW }, | ||
383 | }, | ||
384 | |||
343 | }; | 385 | }; |
344 | 386 | ||
345 | static const intel_limit_t *intel_g4x_limit(struct drm_crtc *crtc) | 387 | static const intel_limit_t *intel_g4x_limit(struct drm_crtc *crtc) |
@@ -376,11 +418,16 @@ static const intel_limit_t *intel_limit(struct drm_crtc *crtc) | |||
376 | 418 | ||
377 | if (IS_G4X(dev)) { | 419 | if (IS_G4X(dev)) { |
378 | limit = intel_g4x_limit(crtc); | 420 | limit = intel_g4x_limit(crtc); |
379 | } else if (IS_I9XX(dev)) { | 421 | } else if (IS_I9XX(dev) && !IS_IGD(dev)) { |
380 | if (intel_pipe_has_type(crtc, INTEL_OUTPUT_LVDS)) | 422 | if (intel_pipe_has_type(crtc, INTEL_OUTPUT_LVDS)) |
381 | limit = &intel_limits[INTEL_LIMIT_I9XX_LVDS]; | 423 | limit = &intel_limits[INTEL_LIMIT_I9XX_LVDS]; |
382 | else | 424 | else |
383 | limit = &intel_limits[INTEL_LIMIT_I9XX_SDVO_DAC]; | 425 | limit = &intel_limits[INTEL_LIMIT_I9XX_SDVO_DAC]; |
426 | } else if (IS_IGD(dev)) { | ||
427 | if (intel_pipe_has_type(crtc, INTEL_OUTPUT_LVDS)) | ||
428 | limit = &intel_limits[INTEL_LIMIT_IGD_LVDS]; | ||
429 | else | ||
430 | limit = &intel_limits[INTEL_LIMIT_IGD_SDVO_DAC]; | ||
384 | } else { | 431 | } else { |
385 | if (intel_pipe_has_type(crtc, INTEL_OUTPUT_LVDS)) | 432 | if (intel_pipe_has_type(crtc, INTEL_OUTPUT_LVDS)) |
386 | limit = &intel_limits[INTEL_LIMIT_I8XX_LVDS]; | 433 | limit = &intel_limits[INTEL_LIMIT_I8XX_LVDS]; |
@@ -390,8 +437,21 @@ static const intel_limit_t *intel_limit(struct drm_crtc *crtc) | |||
390 | return limit; | 437 | return limit; |
391 | } | 438 | } |
392 | 439 | ||
393 | static void intel_clock(int refclk, intel_clock_t *clock) | 440 | /* m1 is reserved as 0 in IGD, n is a ring counter */ |
441 | static void igd_clock(int refclk, intel_clock_t *clock) | ||
394 | { | 442 | { |
443 | clock->m = clock->m2 + 2; | ||
444 | clock->p = clock->p1 * clock->p2; | ||
445 | clock->vco = refclk * clock->m / clock->n; | ||
446 | clock->dot = clock->vco / clock->p; | ||
447 | } | ||
448 | |||
449 | static void intel_clock(struct drm_device *dev, int refclk, intel_clock_t *clock) | ||
450 | { | ||
451 | if (IS_IGD(dev)) { | ||
452 | igd_clock(refclk, clock); | ||
453 | return; | ||
454 | } | ||
395 | clock->m = 5 * (clock->m1 + 2) + (clock->m2 + 2); | 455 | clock->m = 5 * (clock->m1 + 2) + (clock->m2 + 2); |
396 | clock->p = clock->p1 * clock->p2; | 456 | clock->p = clock->p1 * clock->p2; |
397 | clock->vco = refclk * clock->m / (clock->n + 2); | 457 | clock->vco = refclk * clock->m / (clock->n + 2); |
@@ -427,6 +487,7 @@ bool intel_pipe_has_type (struct drm_crtc *crtc, int type) | |||
427 | static bool intel_PLL_is_valid(struct drm_crtc *crtc, intel_clock_t *clock) | 487 | static bool intel_PLL_is_valid(struct drm_crtc *crtc, intel_clock_t *clock) |
428 | { | 488 | { |
429 | const intel_limit_t *limit = intel_limit (crtc); | 489 | const intel_limit_t *limit = intel_limit (crtc); |
490 | struct drm_device *dev = crtc->dev; | ||
430 | 491 | ||
431 | if (clock->p1 < limit->p1.min || limit->p1.max < clock->p1) | 492 | if (clock->p1 < limit->p1.min || limit->p1.max < clock->p1) |
432 | INTELPllInvalid ("p1 out of range\n"); | 493 | INTELPllInvalid ("p1 out of range\n"); |
@@ -436,7 +497,7 @@ static bool intel_PLL_is_valid(struct drm_crtc *crtc, intel_clock_t *clock) | |||
436 | INTELPllInvalid ("m2 out of range\n"); | 497 | INTELPllInvalid ("m2 out of range\n"); |
437 | if (clock->m1 < limit->m1.min || limit->m1.max < clock->m1) | 498 | if (clock->m1 < limit->m1.min || limit->m1.max < clock->m1) |
438 | INTELPllInvalid ("m1 out of range\n"); | 499 | INTELPllInvalid ("m1 out of range\n"); |
439 | if (clock->m1 <= clock->m2) | 500 | if (clock->m1 <= clock->m2 && !IS_IGD(dev)) |
440 | INTELPllInvalid ("m1 <= m2\n"); | 501 | INTELPllInvalid ("m1 <= m2\n"); |
441 | if (clock->m < limit->m.min || limit->m.max < clock->m) | 502 | if (clock->m < limit->m.min || limit->m.max < clock->m) |
442 | INTELPllInvalid ("m out of range\n"); | 503 | INTELPllInvalid ("m out of range\n"); |
@@ -486,15 +547,17 @@ intel_find_best_PLL(const intel_limit_t *limit, struct drm_crtc *crtc, | |||
486 | memset (best_clock, 0, sizeof (*best_clock)); | 547 | memset (best_clock, 0, sizeof (*best_clock)); |
487 | 548 | ||
488 | for (clock.m1 = limit->m1.min; clock.m1 <= limit->m1.max; clock.m1++) { | 549 | for (clock.m1 = limit->m1.min; clock.m1 <= limit->m1.max; clock.m1++) { |
489 | for (clock.m2 = limit->m2.min; clock.m2 < clock.m1 && | 550 | for (clock.m2 = limit->m2.min; clock.m2 <= limit->m2.max; clock.m2++) { |
490 | clock.m2 <= limit->m2.max; clock.m2++) { | 551 | /* m1 is always 0 in IGD */ |
552 | if (clock.m2 >= clock.m1 && !IS_IGD(dev)) | ||
553 | break; | ||
491 | for (clock.n = limit->n.min; clock.n <= limit->n.max; | 554 | for (clock.n = limit->n.min; clock.n <= limit->n.max; |
492 | clock.n++) { | 555 | clock.n++) { |
493 | for (clock.p1 = limit->p1.min; | 556 | for (clock.p1 = limit->p1.min; |
494 | clock.p1 <= limit->p1.max; clock.p1++) { | 557 | clock.p1 <= limit->p1.max; clock.p1++) { |
495 | int this_err; | 558 | int this_err; |
496 | 559 | ||
497 | intel_clock(refclk, &clock); | 560 | intel_clock(dev, refclk, &clock); |
498 | 561 | ||
499 | if (!intel_PLL_is_valid(crtc, &clock)) | 562 | if (!intel_PLL_is_valid(crtc, &clock)) |
500 | continue; | 563 | continue; |
@@ -551,7 +614,7 @@ intel_g4x_find_best_PLL(const intel_limit_t *limit, struct drm_crtc *crtc, | |||
551 | clock.p1 >= limit->p1.min; clock.p1--) { | 614 | clock.p1 >= limit->p1.min; clock.p1--) { |
552 | int this_err; | 615 | int this_err; |
553 | 616 | ||
554 | intel_clock(refclk, &clock); | 617 | intel_clock(dev, refclk, &clock); |
555 | if (!intel_PLL_is_valid(crtc, &clock)) | 618 | if (!intel_PLL_is_valid(crtc, &clock)) |
556 | continue; | 619 | continue; |
557 | this_err = abs(clock.dot - target) ; | 620 | this_err = abs(clock.dot - target) ; |
@@ -888,7 +951,7 @@ static int intel_get_core_clock_speed(struct drm_device *dev) | |||
888 | return 400000; | 951 | return 400000; |
889 | else if (IS_I915G(dev)) | 952 | else if (IS_I915G(dev)) |
890 | return 333000; | 953 | return 333000; |
891 | else if (IS_I945GM(dev) || IS_845G(dev)) | 954 | else if (IS_I945GM(dev) || IS_845G(dev) || IS_IGDGM(dev)) |
892 | return 200000; | 955 | return 200000; |
893 | else if (IS_I915GM(dev)) { | 956 | else if (IS_I915GM(dev)) { |
894 | u16 gcfgc = 0; | 957 | u16 gcfgc = 0; |
@@ -1043,7 +1106,10 @@ static int intel_crtc_mode_set(struct drm_crtc *crtc, | |||
1043 | return -EINVAL; | 1106 | return -EINVAL; |
1044 | } | 1107 | } |
1045 | 1108 | ||
1046 | fp = clock.n << 16 | clock.m1 << 8 | clock.m2; | 1109 | if (IS_IGD(dev)) |
1110 | fp = (1 << clock.n) << 16 | clock.m1 << 8 | clock.m2; | ||
1111 | else | ||
1112 | fp = clock.n << 16 | clock.m1 << 8 | clock.m2; | ||
1047 | 1113 | ||
1048 | dpll = DPLL_VGA_MODE_DIS; | 1114 | dpll = DPLL_VGA_MODE_DIS; |
1049 | if (IS_I9XX(dev)) { | 1115 | if (IS_I9XX(dev)) { |
@@ -1060,7 +1126,10 @@ static int intel_crtc_mode_set(struct drm_crtc *crtc, | |||
1060 | } | 1126 | } |
1061 | 1127 | ||
1062 | /* compute bitmask from p1 value */ | 1128 | /* compute bitmask from p1 value */ |
1063 | dpll |= (1 << (clock.p1 - 1)) << 16; | 1129 | if (IS_IGD(dev)) |
1130 | dpll |= (1 << (clock.p1 - 1)) << DPLL_FPA01_P1_POST_DIV_SHIFT_IGD; | ||
1131 | else | ||
1132 | dpll |= (1 << (clock.p1 - 1)) << DPLL_FPA01_P1_POST_DIV_SHIFT; | ||
1064 | switch (clock.p2) { | 1133 | switch (clock.p2) { |
1065 | case 5: | 1134 | case 5: |
1066 | dpll |= DPLL_DAC_SERIAL_P2_CLOCK_DIV_5; | 1135 | dpll |= DPLL_DAC_SERIAL_P2_CLOCK_DIV_5; |
@@ -1540,10 +1609,20 @@ static int intel_crtc_clock_get(struct drm_device *dev, struct drm_crtc *crtc) | |||
1540 | fp = I915_READ((pipe == 0) ? FPA1 : FPB1); | 1609 | fp = I915_READ((pipe == 0) ? FPA1 : FPB1); |
1541 | 1610 | ||
1542 | clock.m1 = (fp & FP_M1_DIV_MASK) >> FP_M1_DIV_SHIFT; | 1611 | clock.m1 = (fp & FP_M1_DIV_MASK) >> FP_M1_DIV_SHIFT; |
1543 | clock.m2 = (fp & FP_M2_DIV_MASK) >> FP_M2_DIV_SHIFT; | 1612 | if (IS_IGD(dev)) { |
1544 | clock.n = (fp & FP_N_DIV_MASK) >> FP_N_DIV_SHIFT; | 1613 | clock.n = ffs((fp & FP_N_IGD_DIV_MASK) >> FP_N_DIV_SHIFT) - 1; |
1614 | clock.m2 = (fp & FP_M2_IGD_DIV_MASK) >> FP_M2_DIV_SHIFT; | ||
1615 | } else { | ||
1616 | clock.n = (fp & FP_N_DIV_MASK) >> FP_N_DIV_SHIFT; | ||
1617 | clock.m2 = (fp & FP_M2_DIV_MASK) >> FP_M2_DIV_SHIFT; | ||
1618 | } | ||
1619 | |||
1545 | if (IS_I9XX(dev)) { | 1620 | if (IS_I9XX(dev)) { |
1546 | clock.p1 = ffs((dpll & DPLL_FPA01_P1_POST_DIV_MASK) >> | 1621 | if (IS_IGD(dev)) |
1622 | clock.p1 = ffs((dpll & DPLL_FPA01_P1_POST_DIV_MASK_IGD) >> | ||
1623 | DPLL_FPA01_P1_POST_DIV_SHIFT_IGD); | ||
1624 | else | ||
1625 | clock.p1 = ffs((dpll & DPLL_FPA01_P1_POST_DIV_MASK) >> | ||
1547 | DPLL_FPA01_P1_POST_DIV_SHIFT); | 1626 | DPLL_FPA01_P1_POST_DIV_SHIFT); |
1548 | 1627 | ||
1549 | switch (dpll & DPLL_MODE_MASK) { | 1628 | switch (dpll & DPLL_MODE_MASK) { |
@@ -1562,7 +1641,7 @@ static int intel_crtc_clock_get(struct drm_device *dev, struct drm_crtc *crtc) | |||
1562 | } | 1641 | } |
1563 | 1642 | ||
1564 | /* XXX: Handle the 100Mhz refclk */ | 1643 | /* XXX: Handle the 100Mhz refclk */ |
1565 | intel_clock(96000, &clock); | 1644 | intel_clock(dev, 96000, &clock); |
1566 | } else { | 1645 | } else { |
1567 | bool is_lvds = (pipe == 1) && (I915_READ(LVDS) & LVDS_PORT_EN); | 1646 | bool is_lvds = (pipe == 1) && (I915_READ(LVDS) & LVDS_PORT_EN); |
1568 | 1647 | ||
@@ -1574,9 +1653,9 @@ static int intel_crtc_clock_get(struct drm_device *dev, struct drm_crtc *crtc) | |||
1574 | if ((dpll & PLL_REF_INPUT_MASK) == | 1653 | if ((dpll & PLL_REF_INPUT_MASK) == |
1575 | PLLB_REF_INPUT_SPREADSPECTRUMIN) { | 1654 | PLLB_REF_INPUT_SPREADSPECTRUMIN) { |
1576 | /* XXX: might not be 66MHz */ | 1655 | /* XXX: might not be 66MHz */ |
1577 | intel_clock(66000, &clock); | 1656 | intel_clock(dev, 66000, &clock); |
1578 | } else | 1657 | } else |
1579 | intel_clock(48000, &clock); | 1658 | intel_clock(dev, 48000, &clock); |
1580 | } else { | 1659 | } else { |
1581 | if (dpll & PLL_P1_DIVIDE_BY_TWO) | 1660 | if (dpll & PLL_P1_DIVIDE_BY_TWO) |
1582 | clock.p1 = 2; | 1661 | clock.p1 = 2; |
@@ -1589,7 +1668,7 @@ static int intel_crtc_clock_get(struct drm_device *dev, struct drm_crtc *crtc) | |||
1589 | else | 1668 | else |
1590 | clock.p2 = 2; | 1669 | clock.p2 = 2; |
1591 | 1670 | ||
1592 | intel_clock(48000, &clock); | 1671 | intel_clock(dev, 48000, &clock); |
1593 | } | 1672 | } |
1594 | } | 1673 | } |
1595 | 1674 | ||
diff --git a/include/drm/drm_pciids.h b/include/drm/drm_pciids.h index 5165f240aa68..76c4c8243038 100644 --- a/include/drm/drm_pciids.h +++ b/include/drm/drm_pciids.h | |||
@@ -418,4 +418,6 @@ | |||
418 | {0x8086, 0x2e02, PCI_ANY_ID, PCI_ANY_ID, PCI_CLASS_DISPLAY_VGA << 8, 0xffff00, 0}, \ | 418 | {0x8086, 0x2e02, PCI_ANY_ID, PCI_ANY_ID, PCI_CLASS_DISPLAY_VGA << 8, 0xffff00, 0}, \ |
419 | {0x8086, 0x2e12, PCI_ANY_ID, PCI_ANY_ID, PCI_CLASS_DISPLAY_VGA << 8, 0xffff00, 0}, \ | 419 | {0x8086, 0x2e12, PCI_ANY_ID, PCI_ANY_ID, PCI_CLASS_DISPLAY_VGA << 8, 0xffff00, 0}, \ |
420 | {0x8086, 0x2e22, PCI_ANY_ID, PCI_ANY_ID, PCI_CLASS_DISPLAY_VGA << 8, 0xffff00, 0}, \ | 420 | {0x8086, 0x2e22, PCI_ANY_ID, PCI_ANY_ID, PCI_CLASS_DISPLAY_VGA << 8, 0xffff00, 0}, \ |
421 | {0x8086, 0xa001, PCI_ANY_ID, PCI_ANY_ID, PCI_CLASS_DISPLAY_VGA << 8, 0xffff00, 0}, \ | ||
422 | {0x8086, 0xa011, PCI_ANY_ID, PCI_ANY_ID, PCI_CLASS_DISPLAY_VGA << 8, 0xffff00, 0}, \ | ||
421 | {0, 0, 0} | 423 | {0, 0, 0} |