Contents of /trunk/xorg-old/patches-6.8.2-r10/5160_all_6.8.1-benh-radeon-ppc-fixes-v2.patch
Parent Directory | Revision Log
Revision 167 -
(show annotations)
(download)
Tue May 8 20:58:51 2007 UTC (17 years, 4 months ago) by niro
File size: 27590 byte(s)
Tue May 8 20:58:51 2007 UTC (17 years, 4 months ago) by niro
File size: 27590 byte(s)
-import
1 | diff -urN xc.orig/programs/Xserver/hw/xfree86/drivers/ati/radeon.h xc/programs/Xserver/hw/xfree86/drivers/ati/radeon.h |
2 | --- xc.orig/programs/Xserver/hw/xfree86/drivers/ati/radeon.h 2005-01-13 21:41:05.000000000 -0800 |
3 | +++ xc/programs/Xserver/hw/xfree86/drivers/ati/radeon.h 2005-01-13 21:50:45.919826968 -0800 |
4 | @@ -598,6 +598,7 @@ |
5 | Bool AtLeastOneNonClone; |
6 | int MergedFBXDPI, MergedFBYDPI; |
7 | Bool NoVirtual; |
8 | + Bool VGAAccess; |
9 | |
10 | /* special handlings for DELL triple-head server */ |
11 | Bool IsDellServer; |
12 | diff -urN xc.orig/programs/Xserver/hw/xfree86/drivers/ati/radeon.man xc/programs/Xserver/hw/xfree86/drivers/ati/radeon.man |
13 | --- xc.orig/programs/Xserver/hw/xfree86/drivers/ati/radeon.man 2005-01-13 21:41:05.000000000 -0800 |
14 | +++ xc/programs/Xserver/hw/xfree86/drivers/ati/radeon.man 2005-01-13 21:50:45.919826968 -0800 |
15 | @@ -494,6 +494,34 @@ |
16 | with this enabled. The default is |
17 | .B off. |
18 | .TP |
19 | +.BI "Option \*qVGAAccess\*q \*q" boolean \*q |
20 | +Tell the driver if it can do legacy VGA IOs to the card. This is |
21 | +necessary for properly resuming consoles when in VGA text mode, but |
22 | +shouldn't be if the console is using radeonfb or some other graphic |
23 | +mode driver. Some platforms like PowerPC have issues with those, and they aren't |
24 | +necessary unless you have a real text mode in console. The default is |
25 | +.B off |
26 | +on PowerPC and |
27 | +.B on |
28 | +on other architectures. |
29 | +.TP |
30 | +.BI "Option \*qReverseDDC\*q \*q" boolean \*q |
31 | +When BIOS connector informations aren't available, use this option to |
32 | +reverse the mapping of the 2 main DDC ports. Use this if the X serve |
33 | +obviously detects the wrong display for each connector. This is |
34 | +typically needed on the Radeon 9600 cards bundled with Apple G5s. The |
35 | +default is |
36 | +.B off. |
37 | +.TP |
38 | +.BI "Option \*qLVDSProbePLL\*q \*q" boolean \*q |
39 | +When BIOS panel informations aren't available (like on PowerBooks), it |
40 | +may still be necessary to use the firmware provided PLL values for the |
41 | +panel or flickering will happen. This option will force probing of |
42 | +the current value programmed in the chip when X is launched in that |
43 | +case. This is only useful for LVDS panels (laptop internal panels). |
44 | +The default is |
45 | +.B on. |
46 | +.TP |
47 | |
48 | .SH SEE ALSO |
49 | __xservername__(__appmansuffix__), __xconfigfile__(__filemansuffix__), xorgconfig(__appmansuffix__), Xserver(__appmansuffix__), X(__miscmansuffix__) |
50 | diff -urN xc.orig/programs/Xserver/hw/xfree86/drivers/ati/radeon_accel.c xc/programs/Xserver/hw/xfree86/drivers/ati/radeon_accel.c |
51 | --- xc.orig/programs/Xserver/hw/xfree86/drivers/ati/radeon_accel.c 2005-01-13 21:41:05.000000000 -0800 |
52 | +++ xc/programs/Xserver/hw/xfree86/drivers/ati/radeon_accel.c 2005-01-13 21:50:45.920826816 -0800 |
53 | @@ -291,10 +291,8 @@ |
54 | OUTREGP(RADEON_DP_DATATYPE, 0, ~RADEON_HOST_BIG_ENDIAN_EN); |
55 | #endif |
56 | |
57 | - /* Restore SURFACE_CNTL - only the first head contains valid data -ReneR */ |
58 | - if (!info->IsSecondary) { |
59 | - OUTREG(RADEON_SURFACE_CNTL, info->ModeReg.surface_cntl); |
60 | - } |
61 | + /* Restore SURFACE_CNTL */ |
62 | + OUTREG(RADEON_SURFACE_CNTL, info->ModeReg.surface_cntl); |
63 | |
64 | RADEONWaitForFifo(pScrn, 1); |
65 | OUTREG(RADEON_DEFAULT_SC_BOTTOM_RIGHT, (RADEON_DEFAULT_SC_RIGHT_MAX |
66 | diff -urN xc.orig/programs/Xserver/hw/xfree86/drivers/ati/radeon_driver.c xc/programs/Xserver/hw/xfree86/drivers/ati/radeon_driver.c |
67 | --- xc.orig/programs/Xserver/hw/xfree86/drivers/ati/radeon_driver.c 2005-01-13 21:41:05.000000000 -0800 |
68 | +++ xc/programs/Xserver/hw/xfree86/drivers/ati/radeon_driver.c 2005-01-13 21:50:51.158030640 -0800 |
69 | @@ -118,6 +118,7 @@ |
70 | static void RADEONGetMergedFBOptions(ScrnInfoPtr pScrn); |
71 | static int RADEONValidateMergeModes(ScrnInfoPtr pScrn); |
72 | static void RADEONSetDynamicClock(ScrnInfoPtr pScrn, int mode); |
73 | +static void RADEONUpdatePanelSize(ScrnInfoPtr pScrn); |
74 | |
75 | /* psuedo xinerama support */ |
76 | |
77 | @@ -167,7 +168,10 @@ |
78 | OPTION_SUBPIXEL_ORDER, |
79 | #endif |
80 | OPTION_SHOWCACHE, |
81 | - OPTION_DYNAMIC_CLOCKS |
82 | + OPTION_DYNAMIC_CLOCKS, |
83 | + OPTION_VGA_ACCESS, |
84 | + OPTION_LVDS_PROBE_PLL, |
85 | + OPTION_REVERSE_DDC, |
86 | } RADEONOpts; |
87 | |
88 | static const OptionInfoRec RADEONOptions[] = { |
89 | @@ -215,6 +219,9 @@ |
90 | #endif |
91 | { OPTION_SHOWCACHE, "ShowCache", OPTV_BOOLEAN, {0}, FALSE }, |
92 | { OPTION_DYNAMIC_CLOCKS, "DynamicClocks", OPTV_BOOLEAN, {0}, FALSE }, |
93 | + { OPTION_VGA_ACCESS, "VGAAccess", OPTV_BOOLEAN, {0}, TRUE }, |
94 | + { OPTION_LVDS_PROBE_PLL, "LVDSProbePLL", OPTV_BOOLEAN, {0}, FALSE }, |
95 | + { OPTION_REVERSE_DDC, "ReverseDDC", OPTV_BOOLEAN, {0}, FALSE }, |
96 | { -1, NULL, OPTV_NONE, {0}, FALSE } |
97 | }; |
98 | |
99 | @@ -1190,41 +1197,55 @@ |
100 | return(bConnected ? MT_CRT : MT_NONE); |
101 | } |
102 | |
103 | -#if defined(__powerpc__) |
104 | static Bool RADEONProbePLLParameters(ScrnInfoPtr pScrn) |
105 | { |
106 | RADEONInfoPtr info = RADEONPTR(pScrn); |
107 | RADEONPLLPtr pll = &info->pll; |
108 | unsigned char *RADEONMMIO = info->MMIO; |
109 | unsigned char ppll_div_sel; |
110 | - unsigned Nx, M; |
111 | + unsigned mpll_fb_div, spll_fb_div, M; |
112 | unsigned xclk, tmp, ref_div; |
113 | int hTotal, vTotal, num, denom, m, n; |
114 | - float hz, vclk, xtal; |
115 | + float hz, prev_xtal, vclk, xtal, mpll, spll; |
116 | long start_secs, start_usecs, stop_secs, stop_usecs, total_usecs; |
117 | - int i; |
118 | - |
119 | - for(i=0; i<1000000; i++) |
120 | - if (((INREG(RADEON_CRTC_VLINE_CRNT_VLINE) >> 16) & 0x3ff) == 0) |
121 | + long to1_secs, to1_usecs, to2_secs, to2_usecs; |
122 | + unsigned int f1, f2, f3; |
123 | + int i, tries = 0; |
124 | + |
125 | + prev_xtal = 0; |
126 | + again: |
127 | + xtal = 0; |
128 | + if (++tries > 10) |
129 | + goto failed; |
130 | + |
131 | + xf86getsecs(&to1_secs, &to2_usecs); |
132 | + f1 = INREG(RADEON_CRTC_CRNT_FRAME); |
133 | + for (;;) { |
134 | + f2 = INREG(RADEON_CRTC_CRNT_FRAME); |
135 | + if (f1 != f2) |
136 | break; |
137 | - |
138 | + xf86getsecs(&to2_secs, &to2_usecs); |
139 | + if ((to2_secs - to1_secs) > 1) { |
140 | + xf86DrvMsg(pScrn->scrnIndex, X_WARNING, "Clock not counting...\n"); |
141 | + goto failed; |
142 | + } |
143 | + } |
144 | xf86getsecs(&start_secs, &start_usecs); |
145 | - |
146 | - for(i=0; i<1000000; i++) |
147 | - if (((INREG(RADEON_CRTC_VLINE_CRNT_VLINE) >> 16) & 0x3ff) != 0) |
148 | + for(;;) { |
149 | + f3 = INREG(RADEON_CRTC_CRNT_FRAME); |
150 | + if (f3 != f2) |
151 | break; |
152 | - |
153 | - for(i=0; i<1000000; i++) |
154 | - if (((INREG(RADEON_CRTC_VLINE_CRNT_VLINE) >> 16) & 0x3ff) == 0) |
155 | - break; |
156 | - |
157 | + xf86getsecs(&to2_secs, &to2_usecs); |
158 | + if ((to2_secs - start_secs) > 1) |
159 | + goto failed; |
160 | + } |
161 | xf86getsecs(&stop_secs, &stop_usecs); |
162 | |
163 | total_usecs = abs(stop_usecs - start_usecs); |
164 | hz = 1000000/total_usecs; |
165 | |
166 | - hTotal = ((INREG(RADEON_CRTC_H_TOTAL_DISP) & 0x1ff) + 1) * 8; |
167 | - vTotal = ((INREG(RADEON_CRTC_V_TOTAL_DISP) & 0x3ff) + 1); |
168 | + hTotal = ((INREG(RADEON_CRTC_H_TOTAL_DISP) & 0x3ff) + 1) * 8; |
169 | + vTotal = ((INREG(RADEON_CRTC_V_TOTAL_DISP) & 0xfff) + 1); |
170 | vclk = (float)(hTotal * (float)(vTotal * hz)); |
171 | |
172 | switch((INPLL(pScrn, RADEON_PPLL_REF_DIV) & 0x30000) >> 16) { |
173 | @@ -1286,23 +1307,79 @@ |
174 | else if ((xtal > 29400000) && (xtal < 29600000)) |
175 | xtal = 2950; |
176 | else |
177 | - return FALSE; |
178 | + goto again; |
179 | + failed: |
180 | + if (xtal == 0) { |
181 | + xf86DrvMsg(pScrn->scrnIndex, X_WARNING, "Failed to probe xtal value ! Using default 27Mhz\n"); |
182 | + xtal = 2700; |
183 | + } else { |
184 | + if (prev_xtal == 0) { |
185 | + prev_xtal = xtal; |
186 | + tries = 0; |
187 | + goto again; |
188 | + } else if (prev_xtal != xtal) { |
189 | + prev_xtal = 0; |
190 | + goto again; |
191 | + } |
192 | + } |
193 | |
194 | tmp = INPLL(pScrn, RADEON_X_MPLL_REF_FB_DIV); |
195 | ref_div = INPLL(pScrn, RADEON_PPLL_REF_DIV) & 0x3ff; |
196 | |
197 | - Nx = (tmp & 0xff00) >> 8; |
198 | + /* Calculate "base" xclk straight from MPLL, though that isn't |
199 | + * really useful (hopefully). This isn't called XCLK anymore on |
200 | + * radeon's... |
201 | + */ |
202 | + mpll_fb_div = (tmp & 0xff00) >> 8; |
203 | + spll_fb_div = (tmp & 0xff0000) >> 16; |
204 | M = (tmp & 0xff); |
205 | - xclk = RADEONDiv((2 * Nx * xtal), (2 * M)); |
206 | + xclk = RADEONDiv((2 * mpll_fb_div * xtal), (M)); |
207 | + |
208 | + /* |
209 | + * Calculate MCLK based on MCLK-A |
210 | + */ |
211 | + mpll = (2.0 * (float)mpll_fb_div * (xtal / 100.0)) / (float)M; |
212 | + spll = (2.0 * (float)spll_fb_div * (xtal / 100.0)) / (float)M; |
213 | + |
214 | + tmp = INPLL(pScrn, RADEON_MCLK_CNTL) & 0x7; |
215 | + switch(tmp) { |
216 | + case 1: info->mclk = mpll; break; |
217 | + case 2: info->mclk = mpll / 2.0; break; |
218 | + case 3: info->mclk = mpll / 4.0; break; |
219 | + case 4: info->mclk = mpll / 8.0; break; |
220 | + case 7: info->mclk = spll; break; |
221 | + default: |
222 | + info->mclk = 200.00; |
223 | + xf86DrvMsg(pScrn->scrnIndex, X_WARNING, "Unsupported MCLKA source" |
224 | + " setting %d, can't probe MCLK value !\n", tmp); |
225 | + } |
226 | + |
227 | + /* |
228 | + * Calculate SCLK |
229 | + */ |
230 | + tmp = INPLL(pScrn, RADEON_SCLK_CNTL) & 0x7; |
231 | + switch(tmp) { |
232 | + case 1: info->sclk = spll; break; |
233 | + case 2: info->sclk = spll / 2.0; break; |
234 | + case 3: info->sclk = spll / 4.0; break; |
235 | + case 4: info->sclk = spll / 8.0; break; |
236 | + case 7: info->sclk = mpll; |
237 | + default: |
238 | + info->sclk = 200.00; |
239 | + xf86DrvMsg(pScrn->scrnIndex, X_WARNING, "Unsupported SCLK source" |
240 | + " setting %d, can't probe SCLK value !\n", tmp); |
241 | + } |
242 | |
243 | /* we're done, hopefully these are sane values */ |
244 | pll->reference_div = ref_div; |
245 | pll->xclk = xclk; |
246 | pll->reference_freq = xtal; |
247 | |
248 | + xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Probed PLL values: xtal: %f Mhz, " |
249 | + "sclk: %f Mhz, mclk: %f Mhz\n", xtal/100.0, info->sclk, info->mclk); |
250 | + |
251 | return TRUE; |
252 | } |
253 | -#endif |
254 | |
255 | static void RADEONGetPanelInfoFromReg (ScrnInfoPtr pScrn) |
256 | { |
257 | @@ -1318,7 +1395,7 @@ |
258 | info->PanelYRes = (INREG(RADEON_CRTC_V_TOTAL_DISP)>>16) + 1; |
259 | } |
260 | if (fp_horz_stretch & RADEON_HORZ_STRETCH_ENABLE) { |
261 | - info->PanelXRes = ((fp_horz_stretch>>16) + 1) * 8; |
262 | + info->PanelXRes = ((fp_vert_stretch>>16) + 1) * 8; |
263 | } else { |
264 | info->PanelXRes = ((INREG(RADEON_CRTC_H_TOTAL_DISP)>>16) + 1) * 8; |
265 | } |
266 | @@ -1327,6 +1404,24 @@ |
267 | info->PanelXRes = 640; |
268 | info->PanelYRes = 480; |
269 | } |
270 | + |
271 | + if (xf86ReturnOptValBool(info->Options, OPTION_LVDS_PROBE_PLL, TRUE)) { |
272 | + CARD32 ppll_div_sel, ppll_val; |
273 | + |
274 | + OUTREG(RADEON_CLOCK_CNTL_INDEX, 1); |
275 | + ppll_div_sel = INREG8(RADEON_CLOCK_CNTL_DATA + 1) & 0x3; |
276 | + ppll_val = INPLL(pScrn, RADEON_PPLL_DIV_0 + ppll_div_sel); |
277 | + if ((ppll_val & 0x000707ff) == 0x1bb) |
278 | + goto noprobe; |
279 | + info->FeedbackDivider = ppll_val & 0x7ff; |
280 | + info->PostDivider = (ppll_val >> 16) & 0x7; |
281 | + info->RefDivider = info->pll.reference_div; |
282 | + info->UseBiosDividers = TRUE; |
283 | + |
284 | + xf86DrvMsg(pScrn->scrnIndex, X_INFO, |
285 | + "Existing panel PLL dividers will be used.\n"); |
286 | + } |
287 | + noprobe: |
288 | |
289 | xf86DrvMsg(pScrn->scrnIndex, X_WARNING, |
290 | "Panel size %dx%d is derived, this may not be correct.\n" |
291 | @@ -1341,17 +1436,24 @@ |
292 | if (!RADEONGetLVDSInfoFromBIOS(pScrn)) |
293 | RADEONGetPanelInfoFromReg(pScrn); |
294 | |
295 | + /* The panel size we collected from BIOS may not be the |
296 | + * maximum size supported by the panel. If not, we update |
297 | + * it now. These will be used if no matching mode can be |
298 | + * found from EDID data. |
299 | + */ |
300 | + RADEONUpdatePanelSize(pScrn); |
301 | + |
302 | + /* No timing information for the native mode, |
303 | + * use whatever specified in the Modeline. |
304 | + * If no Modeline specified, we'll just pick |
305 | + * the VESA mode at 60Hz refresh rate which |
306 | + * is likely to be the best for a flat panel. |
307 | + */ |
308 | if (info->DotClock == 0) { |
309 | RADEONEntPtr pRADEONEnt = RADEONEntPriv(pScrn); |
310 | DisplayModePtr tmp_mode = NULL; |
311 | xf86DrvMsg(pScrn->scrnIndex, X_WARNING, |
312 | "No valid timing info from BIOS.\n"); |
313 | - /* No timing information for the native mode, |
314 | - use whatever specified in the Modeline. |
315 | - If no Modeline specified, we'll just pick |
316 | - the VESA mode at 60Hz refresh rate which |
317 | - is likely to be the best for a flat panel. |
318 | - */ |
319 | tmp_mode = pScrn->monitor->Modes; |
320 | while(tmp_mode) { |
321 | if ((tmp_mode->HDisplay == info->PanelXRes) && |
322 | @@ -1422,6 +1524,8 @@ |
323 | RADEONGetTMDSInfo(pScrn); |
324 | if (!pScrn->monitor->DDC) |
325 | RADEONGetHardCodedEDIDFromBIOS(pScrn); |
326 | + else if (!info->IsSecondary) |
327 | + RADEONUpdatePanelSize(pScrn); |
328 | } |
329 | } |
330 | } |
331 | @@ -1454,17 +1558,24 @@ |
332 | xf86DrvMsg (pScrn->scrnIndex, X_WARNING, |
333 | "Video BIOS not detected, using default clock settings!\n"); |
334 | |
335 | -#if defined(__powerpc__) |
336 | - if (RADEONProbePLLParameters(pScrn)) return; |
337 | -#endif |
338 | + /* First, setup default PLL min/max */ |
339 | + if (info->ChipFamily >= CHIP_FAMILY_R420) { |
340 | + pll->min_pll_freq = 20000; |
341 | + pll->max_pll_freq = 50000; |
342 | + } else { |
343 | + pll->min_pll_freq = 12500; |
344 | + pll->max_pll_freq = 35000; |
345 | + } |
346 | + /* Try to probe the values from chip registers */ |
347 | + if (RADEONProbePLLParameters(pScrn)) |
348 | + return; |
349 | + |
350 | if (info->IsIGP) |
351 | pll->reference_freq = 1432; |
352 | else |
353 | pll->reference_freq = 2700; |
354 | |
355 | pll->reference_div = 12; |
356 | - pll->min_pll_freq = 12500; |
357 | - pll->max_pll_freq = 35000; |
358 | pll->xclk = 10300; |
359 | |
360 | info->sclk = 200.00; |
361 | @@ -1616,6 +1727,14 @@ |
362 | pRADEONEnt->PortInfo[1].DACType = DAC_PRIMARY; |
363 | pRADEONEnt->PortInfo[1].TMDSType = TMDS_EXT; |
364 | pRADEONEnt->PortInfo[1].ConnectorType = CONNECTOR_CRT; |
365 | + |
366 | + /* Some cards have the DDC lines swapped and we have no way to |
367 | + * detect it yet (Mac cards) |
368 | + */ |
369 | + if (xf86ReturnOptValBool(info->Options, OPTION_REVERSE_DDC, FALSE)) { |
370 | + pRADEONEnt->PortInfo[0].DDCType = DDC_VGA; |
371 | + pRADEONEnt->PortInfo[1].DDCType = DDC_DVI; |
372 | + } |
373 | } |
374 | |
375 | /* always make TMDS_INT port first*/ |
376 | @@ -2618,16 +2737,35 @@ |
377 | xf86MonPtr ddc = pScrn->monitor->DDC; |
378 | DisplayModePtr p; |
379 | |
380 | + if (info->UseBiosDividers && info->DotClock != 0) |
381 | + return; |
382 | + |
383 | /* Go thru detailed timing table first */ |
384 | for (j = 0; j < 4; j++) { |
385 | if (ddc->det_mon[j].type == 0) { |
386 | struct detailed_timings *d_timings = |
387 | &ddc->det_mon[j].section.d_timings; |
388 | + int match = 0; |
389 | + |
390 | + /* If we didn't get a panel clock or guessed one, try to match the |
391 | + * mode with the panel size. We do that because we _need_ a panel |
392 | + * clock, or ValidateFPModes will fail, even when UseBiosDividers |
393 | + * is set. |
394 | + */ |
395 | + if (info->DotClock == 0 && |
396 | + info->PanelXRes == d_timings->h_active && |
397 | + info->PanelYRes == d_timings->v_active) |
398 | + match = 1; |
399 | + |
400 | + /* If we don't have a BIOS provided panel data with fixed dividers, |
401 | + * check for a larger panel size |
402 | + */ |
403 | if (info->PanelXRes <= d_timings->h_active && |
404 | - info->PanelYRes <= d_timings->v_active) { |
405 | - |
406 | - if (info->DotClock) continue; /* Timings already inited */ |
407 | + info->PanelYRes < d_timings->v_active && |
408 | + !info->UseBiosDividers) |
409 | + match = 1; |
410 | |
411 | + if (match) { |
412 | info->PanelXRes = d_timings->h_active; |
413 | info->PanelYRes = d_timings->v_active; |
414 | info->DotClock = d_timings->clock / 1000; |
415 | @@ -2637,10 +2775,24 @@ |
416 | info->VOverPlus = d_timings->v_sync_off; |
417 | info->VSyncWidth = d_timings->v_sync_width; |
418 | info->VBlank = d_timings->v_blanking; |
419 | + info->Flags = (d_timings->interlaced ? V_INTERLACE : 0); |
420 | + if (d_timings->sync == 3) { |
421 | + switch (d_timings->misc) { |
422 | + case 0: info->Flags |= V_NHSYNC | V_NVSYNC; break; |
423 | + case 1: info->Flags |= V_PHSYNC | V_NVSYNC; break; |
424 | + case 2: info->Flags |= V_NHSYNC | V_PVSYNC; break; |
425 | + case 3: info->Flags |= V_PHSYNC | V_PVSYNC; break; |
426 | + } |
427 | + } |
428 | + xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Panel infos found from DDC detailed: %dx%d\n", |
429 | + info->PanelXRes, info->PanelYRes); |
430 | } |
431 | } |
432 | } |
433 | |
434 | + if (info->UseBiosDividers && info->DotClock != 0) |
435 | + return; |
436 | + |
437 | /* Search thru standard VESA modes from EDID */ |
438 | for (j = 0; j < 8; j++) { |
439 | if ((info->PanelXRes < ddc->timings2[j].hsize) && |
440 | @@ -2662,28 +2814,16 @@ |
441 | info->VOverPlus = p->VSyncStart - p->VDisplay; |
442 | info->VSyncWidth = p->VSyncEnd - p->VSyncStart; |
443 | info->DotClock = p->Clock; |
444 | - info->Flags = |
445 | - (ddc->det_mon[j].section.d_timings.interlaced |
446 | - ? V_INTERLACE |
447 | - : 0); |
448 | - if (ddc->det_mon[j].section.d_timings.sync == 3) { |
449 | - switch (ddc->det_mon[j].section.d_timings.misc) { |
450 | - case 0: info->Flags |= V_NHSYNC | V_NVSYNC; break; |
451 | - case 1: info->Flags |= V_PHSYNC | V_NVSYNC; break; |
452 | - case 2: info->Flags |= V_NHSYNC | V_PVSYNC; break; |
453 | - case 3: info->Flags |= V_PHSYNC | V_PVSYNC; break; |
454 | - } |
455 | - } |
456 | + info->Flags = p->Flags; |
457 | + xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Panel infos found from DDC VESA/EDID: %dx%d\n", |
458 | + info->PanelXRes, info->PanelYRes); |
459 | } |
460 | } |
461 | } |
462 | } |
463 | } |
464 | - |
465 | - xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Panel size found from DDC: %dx%d\n", |
466 | - info->PanelXRes, info->PanelYRes); |
467 | -} |
468 | - |
469 | + } |
470 | + |
471 | /* This function will sort all modes according to their resolution. |
472 | * Highest resolution first. |
473 | */ |
474 | @@ -2802,6 +2942,8 @@ |
475 | |
476 | /* Search thru standard VESA modes from EDID */ |
477 | for (j = 0; j < 8; j++) { |
478 | + if (ddc->timings2[j].hsize == 0 || ddc->timings2[j].vsize == 0) |
479 | + continue; |
480 | for (p = pScrn->monitor->Modes; p && p->next; p = p->next->next) { |
481 | /* Ignore all double scan modes */ |
482 | if ((ddc->timings2[j].hsize == p->HDisplay) && |
483 | @@ -2891,19 +3033,10 @@ |
484 | pScrn->virtualX = pScrn1->display->virtualX; |
485 | pScrn->virtualY = pScrn1->display->virtualY; |
486 | |
487 | - if (pScrn->monitor->DDC && !info->UseBiosDividers) { |
488 | + if (pScrn->monitor->DDC) { |
489 | int maxVirtX = pScrn->virtualX; |
490 | int maxVirtY = pScrn->virtualY; |
491 | |
492 | - if ((DisplayType != MT_CRT) && (!info->IsSecondary) && (!crtc2)) { |
493 | - /* The panel size we collected from BIOS may not be the |
494 | - * maximum size supported by the panel. If not, we update |
495 | - * it now. These will be used if no matching mode can be |
496 | - * found from EDID data. |
497 | - */ |
498 | - RADEONUpdatePanelSize(pScrn); |
499 | - } |
500 | - |
501 | /* Collect all of the DDC modes */ |
502 | first = last = ddcModes = RADEONDDCModes(pScrn); |
503 | |
504 | @@ -3595,7 +3728,8 @@ |
505 | xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, |
506 | "Invalid PanelSize value: %s\n", s); |
507 | } |
508 | - } |
509 | + } else |
510 | + RADEONGetPanelInfo(pScrn); |
511 | } |
512 | |
513 | if (pScrn->monitor->DDC) { |
514 | @@ -4162,15 +4296,6 @@ |
515 | return TRUE; |
516 | } |
517 | |
518 | - if (!xf86LoadSubModule(pScrn, "vgahw")) return FALSE; |
519 | - xf86LoaderReqSymLists(vgahwSymbols, NULL); |
520 | - if (!vgaHWGetHWRec(pScrn)) { |
521 | - RADEONFreeRec(pScrn); |
522 | - goto fail2; |
523 | - } |
524 | - |
525 | - vgaHWGetIOBase(VGAHWPTR(pScrn)); |
526 | - |
527 | xf86DrvMsg(pScrn->scrnIndex, X_INFO, |
528 | "PCI bus %d card %d func %d\n", |
529 | info->PciInfo->bus, |
530 | @@ -4198,6 +4323,32 @@ |
531 | memcpy(info->Options, RADEONOptions, sizeof(RADEONOptions)); |
532 | xf86ProcessOptions(pScrn->scrnIndex, pScrn->options, info->Options); |
533 | |
534 | + /* By default, don't do VGA IOs on ppc */ |
535 | +#ifdef __powerpc__ |
536 | + info->VGAAccess = FALSE; |
537 | +#else |
538 | + info->VGAAccess = TRUE; |
539 | +#endif |
540 | + |
541 | + xf86GetOptValBool(info->Options, OPTION_VGA_ACCESS, &info->VGAAccess); |
542 | + if (info->VGAAccess) { |
543 | + if (!xf86LoadSubModule(pScrn, "vgahw")) |
544 | + info->VGAAccess = FALSE; |
545 | + else { |
546 | + xf86LoaderReqSymLists(vgahwSymbols, NULL); |
547 | + if (!vgaHWGetHWRec(pScrn)) |
548 | + info->VGAAccess = FALSE; |
549 | + } |
550 | + if (!info->VGAAccess) |
551 | + xf86DrvMsg(pScrn->scrnIndex, X_WARNING, "Loading VGA module failed," |
552 | + " trying to run without it\n"); |
553 | + } else |
554 | + xf86DrvMsg(pScrn->scrnIndex, X_INFO, "VGAAccess option set to FALSE," |
555 | + " VGA module load skipped\n"); |
556 | + if (info->VGAAccess) |
557 | + vgaHWGetIOBase(VGAHWPTR(pScrn)); |
558 | + |
559 | + |
560 | if (!RADEONPreInitWeight(pScrn)) |
561 | goto fail; |
562 | |
563 | @@ -4256,7 +4407,6 @@ |
564 | RADEONGetBIOSInfo(pScrn, pInt10); |
565 | if (!RADEONQueryConnectedMonitors(pScrn)) goto fail; |
566 | RADEONGetClockInfo(pScrn); |
567 | - RADEONGetPanelInfo(pScrn); |
568 | |
569 | /* collect MergedFB options */ |
570 | /* only parse mergedfb options on the primary head. |
571 | @@ -4312,7 +4462,8 @@ |
572 | if (pInt10) |
573 | xf86FreeInt10(pInt10); |
574 | |
575 | - vgaHWFreeHWRec(pScrn); |
576 | + if (info->VGAAccess) |
577 | + vgaHWFreeHWRec(pScrn); |
578 | |
579 | fail2: |
580 | if(info->MMIO) RADEONUnmapMMIO(pScrn); |
581 | @@ -5716,10 +5867,6 @@ |
582 | unsigned char *RADEONMMIO = info->MMIO; |
583 | int i; |
584 | |
585 | -#ifdef ENABLE_FLAT_PANEL |
586 | - /* Select palette 0 (main CRTC) if using FP-enabled chip */ |
587 | - /* if (info->Port1 == MT_DFP) PAL_SELECT(1); */ |
588 | -#endif |
589 | PAL_SELECT(1); |
590 | INPAL_START(0); |
591 | for (i = 0; i < 256; i++) save->palette2[i] = INPAL_NEXT(); |
592 | @@ -5760,7 +5907,6 @@ |
593 | RADEONInfoPtr info = RADEONPTR(pScrn); |
594 | unsigned char *RADEONMMIO = info->MMIO; |
595 | RADEONSavePtr save = &info->SavedReg; |
596 | - vgaHWPtr hwp = VGAHWPTR(pScrn); |
597 | |
598 | RADEONTRACE(("RADEONSave\n")); |
599 | if (info->FBDev) { |
600 | @@ -5769,19 +5915,23 @@ |
601 | } |
602 | |
603 | if (!info->IsSecondary) { |
604 | - vgaHWUnlock(hwp); |
605 | + if (info->VGAAccess) { |
606 | + vgaHWPtr hwp = VGAHWPTR(pScrn); |
607 | + |
608 | + vgaHWUnlock(hwp); |
609 | #if defined(__powerpc__) |
610 | - /* temporary hack to prevent crashing on PowerMacs when trying to |
611 | - * read VGA fonts and colormap, will find a better solution |
612 | - * in the future |
613 | - */ |
614 | - vgaHWSave(pScrn, &hwp->SavedReg, VGA_SR_MODE); /* Save mode only */ |
615 | + /* temporary hack to prevent crashing on PowerMacs when trying to |
616 | + * read VGA fonts and colormap, will find a better solution |
617 | + * in the future. TODO: Check if there's actually some VGA stuff |
618 | + * setup in the card at all !! |
619 | + */ |
620 | + vgaHWSave(pScrn, &hwp->SavedReg, VGA_SR_MODE); /* Save mode only */ |
621 | #else |
622 | - vgaHWSave(pScrn, &hwp->SavedReg, VGA_SR_MODE | VGA_SR_FONTS); /* Save mode |
623 | - * & fonts & cmap |
624 | - */ |
625 | + /* Save mode * & fonts & cmap */ |
626 | + vgaHWSave(pScrn, &hwp->SavedReg, VGA_SR_MODE | VGA_SR_FONTS); |
627 | #endif |
628 | - vgaHWLock(hwp); |
629 | + vgaHWLock(hwp); |
630 | + } |
631 | save->dp_datatype = INREG(RADEON_DP_DATATYPE); |
632 | save->rbbm_soft_reset = INREG(RADEON_RBBM_SOFT_RESET); |
633 | save->clock_cntl_index = INREG(RADEON_CLOCK_CNTL_INDEX); |
634 | @@ -5797,7 +5947,6 @@ |
635 | RADEONInfoPtr info = RADEONPTR(pScrn); |
636 | unsigned char *RADEONMMIO = info->MMIO; |
637 | RADEONSavePtr restore = &info->SavedReg; |
638 | - vgaHWPtr hwp = VGAHWPTR(pScrn); |
639 | |
640 | RADEONTRACE(("RADEONRestore\n")); |
641 | |
642 | @@ -5839,27 +5988,36 @@ |
643 | usleep(100000); |
644 | #endif |
645 | |
646 | - if (!info->IsSecondary) { |
647 | - vgaHWUnlock(hwp); |
648 | + if (info->VGAAccess) { |
649 | + vgaHWPtr hwp = VGAHWPTR(pScrn); |
650 | + if (!info->IsSecondary) { |
651 | + vgaHWUnlock(hwp); |
652 | #if defined(__powerpc__) |
653 | - /* Temporary hack to prevent crashing on PowerMacs when trying to |
654 | - * write VGA fonts, will find a better solution in the future |
655 | - */ |
656 | - vgaHWRestore(pScrn, &hwp->SavedReg, VGA_SR_MODE ); |
657 | + /* Temporary hack to prevent crashing on PowerMacs when trying to |
658 | + * write VGA fonts, will find a better solution in the future |
659 | + */ |
660 | + vgaHWRestore(pScrn, &hwp->SavedReg, VGA_SR_MODE ); |
661 | #else |
662 | - vgaHWRestore(pScrn, &hwp->SavedReg, VGA_SR_MODE | VGA_SR_FONTS ); |
663 | + vgaHWRestore(pScrn, &hwp->SavedReg, VGA_SR_MODE | VGA_SR_FONTS ); |
664 | #endif |
665 | - vgaHWLock(hwp); |
666 | - } else { |
667 | - RADEONEntPtr pRADEONEnt = RADEONEntPriv(pScrn); |
668 | - ScrnInfoPtr pScrn0; |
669 | - vgaHWPtr hwp0; |
670 | - |
671 | - pScrn0 = pRADEONEnt->pPrimaryScrn; |
672 | - hwp0 = VGAHWPTR(pScrn0); |
673 | - vgaHWUnlock(hwp0); |
674 | - vgaHWRestore(pScrn0, &hwp0->SavedReg, VGA_SR_MODE | VGA_SR_FONTS ); |
675 | - vgaHWLock(hwp0); |
676 | + vgaHWLock(hwp); |
677 | + } else { |
678 | + RADEONEntPtr pRADEONEnt = RADEONEntPriv(pScrn); |
679 | + ScrnInfoPtr pScrn0 = pRADEONEnt->pPrimaryScrn; |
680 | + RADEONInfoPtr info0 = RADEONPTR(pScrn0); |
681 | + vgaHWPtr hwp0; |
682 | + |
683 | + if (info0->VGAAccess) { |
684 | + hwp0 = VGAHWPTR(pScrn0); |
685 | + vgaHWUnlock(hwp0); |
686 | +#if defined(__powerpc__) |
687 | + vgaHWRestore(pScrn0, &hwp0->SavedReg, VGA_SR_MODE); |
688 | +#else |
689 | + vgaHWRestore(pScrn0, &hwp0->SavedReg, VGA_SR_MODE | VGA_SR_FONTS ); |
690 | +#endif |
691 | + vgaHWLock(hwp0); |
692 | + } |
693 | + } |
694 | } |
695 | RADEONUnblank(pScrn); |
696 | |
697 | @@ -6007,7 +6165,7 @@ |
698 | */ |
699 | temp = INREG(RADEON_MEM_CNTL); |
700 | data = (R300_MEM_NUM_CHANNELS_MASK & temp); |
701 | - if (data == 2) { |
702 | + if (data == 1) { |
703 | if (R300_MEM_USE_CD_CH_ONLY & temp) { |
704 | temp = INREG(R300_MC_IND_INDEX); |
705 | temp &= ~R300_MC_IND_ADDR_MASK; |
706 | @@ -6488,8 +6646,13 @@ |
707 | ? RADEON_CRTC2_V_SYNC_POL |
708 | : 0)); |
709 | |
710 | + /* We must make sure Tiling is disabled. It seem all other fancy |
711 | + * options in there can be safely disabled too |
712 | + */ |
713 | save->crtc2_offset = 0; |
714 | - save->crtc2_offset_cntl = INREG(RADEON_CRTC2_OFFSET_CNTL); |
715 | + save->crtc2_offset_cntl = 0; |
716 | + |
717 | + |
718 | /* this should be right */ |
719 | if (info->MergedFB) { |
720 | save->crtc2_pitch = (((info->CRT2pScrn->displayWidth * pScrn->bitsPerPixel) + |
721 | @@ -6531,6 +6694,23 @@ |
722 | |
723 | } |
724 | |
725 | + /* We must set SURFACE_CNTL properly on the second screen too */ |
726 | + save->surface_cntl = 0; |
727 | +#if X_BYTE_ORDER == X_BIG_ENDIAN |
728 | + /* Alhought we current onlu use aperture 0, also setting aperture 1 should not harm -ReneR */ |
729 | + switch (pScrn->bitsPerPixel) { |
730 | + case 16: |
731 | + save->surface_cntl |= RADEON_NONSURF_AP0_SWP_16BPP; |
732 | + save->surface_cntl |= RADEON_NONSURF_AP1_SWP_16BPP; |
733 | + break; |
734 | + |
735 | + case 32: |
736 | + save->surface_cntl |= RADEON_NONSURF_AP0_SWP_32BPP; |
737 | + save->surface_cntl |= RADEON_NONSURF_AP1_SWP_32BPP; |
738 | + break; |
739 | + } |
740 | +#endif |
741 | + |
742 | RADEONTRACE(("Pitch = %d bytes (virtualX = %d, displayWidth = %d)\n", |
743 | save->crtc2_pitch, pScrn->virtualX, |
744 | info->CurrentLayout.displayWidth)); |
745 | @@ -6815,7 +6995,7 @@ |
746 | |
747 | /* Define PLL2 registers for requested video mode */ |
748 | static void RADEONInitPLL2Registers(RADEONSavePtr save, RADEONPLLPtr pll, |
749 | - double dot_clock) |
750 | + double dot_clock, int no_odd_postdiv) |
751 | { |
752 | unsigned long freq = dot_clock * 100; |
753 | |
754 | @@ -6832,7 +7012,7 @@ |
755 | { 2, 1 }, /* VCLK_SRC/2 */ |
756 | { 4, 2 }, /* VCLK_SRC/4 */ |
757 | { 8, 3 }, /* VCLK_SRC/8 */ |
758 | - { 3, 4 }, /* VCLK_SRC/3 */ |
759 | + { 3, 4 }, /* VCLK_SRC/3 */ |
760 | { 6, 6 }, /* VCLK_SRC/6 */ |
761 | { 12, 7 }, /* VCLK_SRC/12 */ |
762 | { 0, 0 } |
763 | @@ -6842,6 +7022,11 @@ |
764 | if (freq * 12 < pll->min_pll_freq) freq = pll->min_pll_freq / 12; |
765 | |
766 | for (post_div = &post_divs[0]; post_div->divider; ++post_div) { |
767 | + /* Odd post divider value don't work properly on the second digital |
768 | + * output |
769 | + */ |
770 | + if (no_odd_postdiv && (post_div->divider & 1)) |
771 | + continue; |
772 | save->pll_output_freq_2 = post_div->divider * freq; |
773 | if (save->pll_output_freq_2 >= pll->min_pll_freq |
774 | && save->pll_output_freq_2 <= pll->max_pll_freq) break; |
775 | @@ -6942,7 +7127,7 @@ |
776 | if (info->IsSecondary) { |
777 | if (!RADEONInitCrtc2Registers(pScrn, save, mode, info)) |
778 | return FALSE; |
779 | - RADEONInitPLL2Registers(save, &info->pll, dot_clock); |
780 | + RADEONInitPLL2Registers(save, &info->pll, dot_clock, info->DisplayType != MT_CRT); |
781 | } else if (info->MergedFB) { |
782 | RADEONInitCommonRegisters(save, info); |
783 | if (!RADEONInitCrtcRegisters(pScrn, save, |
784 | @@ -6959,7 +7144,8 @@ |
785 | RADEONInitCrtc2Registers(pScrn, save, |
786 | ((RADEONMergedDisplayModePtr)mode->Private)->CRT2, info); |
787 | dot_clock = (((RADEONMergedDisplayModePtr)mode->Private)->CRT2)->Clock / 1000.0; |
788 | - RADEONInitPLL2Registers(save, &info->pll, dot_clock); |
789 | + RADEONInitPLL2Registers(save, &info->pll, dot_clock, |
790 | + info->MergeType != MT_CRT); |
791 | } else { |
792 | if (!RADEONInitCrtcRegisters(pScrn, save, mode, info)) |
793 | return FALSE; |
794 | @@ -7410,7 +7596,7 @@ |
795 | } |
796 | } |
797 | |
798 | - if (xf86LoaderCheckSymbol("vgaHWFreeHWRec")) |
799 | + if (info->VGAAccess && xf86LoaderCheckSymbol("vgaHWFreeHWRec")) |
800 | vgaHWFreeHWRec(pScrn); |
801 | RADEONFreeRec(pScrn); |
802 | } |