1 // SPDX-License-Identifier: GPL-2.0-only
2 /*
3 *
4 * Hardware accelerated Matrox Millennium I, II, Mystique, G100, G200 and G400
5 *
6 * (c) 1998-2002 Petr Vandrovec <vandrove@vc.cvut.cz>
7 *
8 * Portions Copyright (c) 2001 Matrox Graphics Inc.
9 *
10 * Version: 1.65 2002/08/14
11 *
12 * MTRR stuff: 1998 Tom Rini <trini@kernel.crashing.org>
13 *
14 * Contributors: "menion?" <menion@mindless.com>
15 * Betatesting, fixes, ideas
16 *
17 * "Kurt Garloff" <garloff@suse.de>
18 * Betatesting, fixes, ideas, videomodes, videomodes timmings
19 *
20 * "Tom Rini" <trini@kernel.crashing.org>
21 * MTRR stuff, PPC cleanups, betatesting, fixes, ideas
22 *
23 * "Bibek Sahu" <scorpio@dodds.net>
24 * Access device through readb|w|l and write b|w|l
25 * Extensive debugging stuff
26 *
27 * "Daniel Haun" <haund@usa.net>
28 * Testing, hardware cursor fixes
29 *
30 * "Scott Wood" <sawst46+@pitt.edu>
31 * Fixes
32 *
33 * "Gerd Knorr" <kraxel@goldbach.isdn.cs.tu-berlin.de>
34 * Betatesting
35 *
36 * "Kelly French" <targon@hazmat.com>
37 * "Fernando Herrera" <fherrera@eurielec.etsit.upm.es>
38 * Betatesting, bug reporting
39 *
40 * "Pablo Bianucci" <pbian@pccp.com.ar>
41 * Fixes, ideas, betatesting
42 *
43 * "Inaky Perez Gonzalez" <inaky@peloncho.fis.ucm.es>
44 * Fixes, enhandcements, ideas, betatesting
45 *
46 * "Ryuichi Oikawa" <roikawa@rr.iiij4u.or.jp>
47 * PPC betatesting, PPC support, backward compatibility
48 *
49 * "Paul Womar" <Paul@pwomar.demon.co.uk>
50 * "Owen Waller" <O.Waller@ee.qub.ac.uk>
51 * PPC betatesting
52 *
53 * "Thomas Pornin" <pornin@bolet.ens.fr>
54 * Alpha betatesting
55 *
56 * "Pieter van Leuven" <pvl@iae.nl>
57 * "Ulf Jaenicke-Roessler" <ujr@physik.phy.tu-dresden.de>
58 * G100 testing
59 *
60 * "H. Peter Arvin" <hpa@transmeta.com>
61 * Ideas
62 *
63 * "Cort Dougan" <cort@cs.nmt.edu>
64 * CHRP fixes and PReP cleanup
65 *
66 * "Mark Vojkovich" <mvojkovi@ucsd.edu>
67 * G400 support
68 *
69 * (following author is not in any relation with this code, but his code
70 * is included in this driver)
71 *
72 * Based on framebuffer driver for VBE 2.0 compliant graphic boards
73 * (c) 1998 Gerd Knorr <kraxel@cs.tu-berlin.de>
74 *
75 * (following author is not in any relation with this code, but his ideas
76 * were used when writing this driver)
77 *
78 * FreeVBE/AF (Matrox), "Shawn Hargreaves" <shawn@talula.demon.co.uk>
79 *
80 */
81
82 #include <linux/export.h>
83
84 #include "matroxfb_Ti3026.h"
85 #include "matroxfb_misc.h"
86 #include "matroxfb_accel.h"
87 #include <linux/matroxfb.h>
88
89 #ifdef CONFIG_FB_MATROX_MILLENIUM
90 #define outTi3026 matroxfb_DAC_out
91 #define inTi3026 matroxfb_DAC_in
92
93 #define TVP3026_INDEX 0x00
94 #define TVP3026_PALWRADD 0x00
95 #define TVP3026_PALDATA 0x01
96 #define TVP3026_PIXRDMSK 0x02
97 #define TVP3026_PALRDADD 0x03
98 #define TVP3026_CURCOLWRADD 0x04
99 #define TVP3026_CLOVERSCAN 0x00
100 #define TVP3026_CLCOLOR0 0x01
101 #define TVP3026_CLCOLOR1 0x02
102 #define TVP3026_CLCOLOR2 0x03
103 #define TVP3026_CURCOLDATA 0x05
104 #define TVP3026_CURCOLRDADD 0x07
105 #define TVP3026_CURCTRL 0x09
106 #define TVP3026_X_DATAREG 0x0A
107 #define TVP3026_CURRAMDATA 0x0B
108 #define TVP3026_CURPOSXL 0x0C
109 #define TVP3026_CURPOSXH 0x0D
110 #define TVP3026_CURPOSYL 0x0E
111 #define TVP3026_CURPOSYH 0x0F
112
113 #define TVP3026_XSILICONREV 0x01
114 #define TVP3026_XCURCTRL 0x06
115 #define TVP3026_XCURCTRL_DIS 0x00 /* transparent, transparent, transparent, transparent */
116 #define TVP3026_XCURCTRL_3COLOR 0x01 /* transparent, 0, 1, 2 */
117 #define TVP3026_XCURCTRL_XGA 0x02 /* 0, 1, transparent, complement */
118 #define TVP3026_XCURCTRL_XWIN 0x03 /* transparent, transparent, 0, 1 */
119 #define TVP3026_XCURCTRL_BLANK2048 0x00
120 #define TVP3026_XCURCTRL_BLANK4096 0x10
121 #define TVP3026_XCURCTRL_INTERLACED 0x20
122 #define TVP3026_XCURCTRL_ODD 0x00 /* ext.signal ODD/\EVEN */
123 #define TVP3026_XCURCTRL_EVEN 0x40 /* ext.signal EVEN/\ODD */
124 #define TVP3026_XCURCTRL_INDIRECT 0x00
125 #define TVP3026_XCURCTRL_DIRECT 0x80
126 #define TVP3026_XLATCHCTRL 0x0F
127 #define TVP3026_XLATCHCTRL_1_1 0x06
128 #define TVP3026_XLATCHCTRL_2_1 0x07
129 #define TVP3026_XLATCHCTRL_4_1 0x06
130 #define TVP3026_XLATCHCTRL_8_1 0x06
131 #define TVP3026_XLATCHCTRL_16_1 0x06
132 #define TVP3026A_XLATCHCTRL_4_3 0x06 /* ??? do not understand... but it works... !!! */
133 #define TVP3026A_XLATCHCTRL_8_3 0x07
134 #define TVP3026B_XLATCHCTRL_4_3 0x08
135 #define TVP3026B_XLATCHCTRL_8_3 0x06 /* ??? do not understand... but it works... !!! */
136 #define TVP3026_XTRUECOLORCTRL 0x18
137 #define TVP3026_XTRUECOLORCTRL_VRAM_SHIFT_ACCEL 0x00
138 #define TVP3026_XTRUECOLORCTRL_VRAM_SHIFT_TVP 0x20
139 #define TVP3026_XTRUECOLORCTRL_PSEUDOCOLOR 0x80
140 #define TVP3026_XTRUECOLORCTRL_TRUECOLOR 0x40 /* paletized */
141 #define TVP3026_XTRUECOLORCTRL_DIRECTCOLOR 0x00
142 #define TVP3026_XTRUECOLORCTRL_24_ALTERNATE 0x08 /* 5:4/5:2 instead of 4:3/8:3 */
143 #define TVP3026_XTRUECOLORCTRL_RGB_888 0x16 /* 4:3/8:3 (or 5:4/5:2) */
144 #define TVP3026_XTRUECOLORCTRL_BGR_888 0x17
145 #define TVP3026_XTRUECOLORCTRL_ORGB_8888 0x06
146 #define TVP3026_XTRUECOLORCTRL_BGRO_8888 0x07
147 #define TVP3026_XTRUECOLORCTRL_RGB_565 0x05
148 #define TVP3026_XTRUECOLORCTRL_ORGB_1555 0x04
149 #define TVP3026_XTRUECOLORCTRL_RGB_664 0x03
150 #define TVP3026_XTRUECOLORCTRL_RGBO_4444 0x01
151 #define TVP3026_XMUXCTRL 0x19
152 #define TVP3026_XMUXCTRL_MEMORY_8BIT 0x01 /* - */
153 #define TVP3026_XMUXCTRL_MEMORY_16BIT 0x02 /* - */
154 #define TVP3026_XMUXCTRL_MEMORY_32BIT 0x03 /* 2MB RAM, 512K * 4 */
155 #define TVP3026_XMUXCTRL_MEMORY_64BIT 0x04 /* >2MB RAM, 512K * 8 & more */
156 #define TVP3026_XMUXCTRL_PIXEL_4BIT 0x40 /* L0,H0,L1,H1... */
157 #define TVP3026_XMUXCTRL_PIXEL_4BIT_SWAPPED 0x60 /* H0,L0,H1,L1... */
158 #define TVP3026_XMUXCTRL_PIXEL_8BIT 0x48
159 #define TVP3026_XMUXCTRL_PIXEL_16BIT 0x50
160 #define TVP3026_XMUXCTRL_PIXEL_32BIT 0x58
161 #define TVP3026_XMUXCTRL_VGA 0x98 /* VGA MEMORY, 8BIT PIXEL */
162 #define TVP3026_XCLKCTRL 0x1A
163 #define TVP3026_XCLKCTRL_DIV1 0x00
164 #define TVP3026_XCLKCTRL_DIV2 0x10
165 #define TVP3026_XCLKCTRL_DIV4 0x20
166 #define TVP3026_XCLKCTRL_DIV8 0x30
167 #define TVP3026_XCLKCTRL_DIV16 0x40
168 #define TVP3026_XCLKCTRL_DIV32 0x50
169 #define TVP3026_XCLKCTRL_DIV64 0x60
170 #define TVP3026_XCLKCTRL_CLKSTOPPED 0x70
171 #define TVP3026_XCLKCTRL_SRC_CLK0 0x00
172 #define TVP3026_XCLKCTRL_SRC_CLK1 0x01
173 #define TVP3026_XCLKCTRL_SRC_CLK2 0x02 /* CLK2 is TTL source*/
174 #define TVP3026_XCLKCTRL_SRC_NCLK2 0x03 /* not CLK2 is TTL source */
175 #define TVP3026_XCLKCTRL_SRC_ECLK2 0x04 /* CLK2 and not CLK2 is ECL source */
176 #define TVP3026_XCLKCTRL_SRC_PLL 0x05
177 #define TVP3026_XCLKCTRL_SRC_DIS 0x06 /* disable & poweroff internal clock */
178 #define TVP3026_XCLKCTRL_SRC_CLK0VGA 0x07
179 #define TVP3026_XPALETTEPAGE 0x1C
180 #define TVP3026_XGENCTRL 0x1D
181 #define TVP3026_XGENCTRL_HSYNC_POS 0x00
182 #define TVP3026_XGENCTRL_HSYNC_NEG 0x01
183 #define TVP3026_XGENCTRL_VSYNC_POS 0x00
184 #define TVP3026_XGENCTRL_VSYNC_NEG 0x02
185 #define TVP3026_XGENCTRL_LITTLE_ENDIAN 0x00
186 #define TVP3026_XGENCTRL_BIG_ENDIAN 0x08
187 #define TVP3026_XGENCTRL_BLACK_0IRE 0x00
188 #define TVP3026_XGENCTRL_BLACK_75IRE 0x10
189 #define TVP3026_XGENCTRL_NO_SYNC_ON_GREEN 0x00
190 #define TVP3026_XGENCTRL_SYNC_ON_GREEN 0x20
191 #define TVP3026_XGENCTRL_OVERSCAN_DIS 0x00
192 #define TVP3026_XGENCTRL_OVERSCAN_EN 0x40
193 #define TVP3026_XMISCCTRL 0x1E
194 #define TVP3026_XMISCCTRL_DAC_PUP 0x00
195 #define TVP3026_XMISCCTRL_DAC_PDOWN 0x01
196 #define TVP3026_XMISCCTRL_DAC_EXT 0x00 /* or 8, bit 3 is ignored */
197 #define TVP3026_XMISCCTRL_DAC_6BIT 0x04
198 #define TVP3026_XMISCCTRL_DAC_8BIT 0x0C
199 #define TVP3026_XMISCCTRL_PSEL_DIS 0x00
200 #define TVP3026_XMISCCTRL_PSEL_EN 0x10
201 #define TVP3026_XMISCCTRL_PSEL_LOW 0x00 /* PSEL high selects directcolor */
202 #define TVP3026_XMISCCTRL_PSEL_HIGH 0x20 /* PSEL high selects truecolor or pseudocolor */
203 #define TVP3026_XGENIOCTRL 0x2A
204 #define TVP3026_XGENIODATA 0x2B
205 #define TVP3026_XPLLADDR 0x2C
206 #define TVP3026_XPLLADDR_X(LOOP,MCLK,PIX) (((LOOP)<<4) | ((MCLK)<<2) | (PIX))
207 #define TVP3026_XPLLDATA_N 0x00
208 #define TVP3026_XPLLDATA_M 0x01
209 #define TVP3026_XPLLDATA_P 0x02
210 #define TVP3026_XPLLDATA_STAT 0x03
211 #define TVP3026_XPIXPLLDATA 0x2D
212 #define TVP3026_XMEMPLLDATA 0x2E
213 #define TVP3026_XLOOPPLLDATA 0x2F
214 #define TVP3026_XCOLKEYOVRMIN 0x30
215 #define TVP3026_XCOLKEYOVRMAX 0x31
216 #define TVP3026_XCOLKEYREDMIN 0x32
217 #define TVP3026_XCOLKEYREDMAX 0x33
218 #define TVP3026_XCOLKEYGREENMIN 0x34
219 #define TVP3026_XCOLKEYGREENMAX 0x35
220 #define TVP3026_XCOLKEYBLUEMIN 0x36
221 #define TVP3026_XCOLKEYBLUEMAX 0x37
222 #define TVP3026_XCOLKEYCTRL 0x38
223 #define TVP3026_XCOLKEYCTRL_OVR_EN 0x01
224 #define TVP3026_XCOLKEYCTRL_RED_EN 0x02
225 #define TVP3026_XCOLKEYCTRL_GREEN_EN 0x04
226 #define TVP3026_XCOLKEYCTRL_BLUE_EN 0x08
227 #define TVP3026_XCOLKEYCTRL_NEGATE 0x10
228 #define TVP3026_XCOLKEYCTRL_ZOOM1 0x00
229 #define TVP3026_XCOLKEYCTRL_ZOOM2 0x20
230 #define TVP3026_XCOLKEYCTRL_ZOOM4 0x40
231 #define TVP3026_XCOLKEYCTRL_ZOOM8 0x60
232 #define TVP3026_XCOLKEYCTRL_ZOOM16 0x80
233 #define TVP3026_XCOLKEYCTRL_ZOOM32 0xA0
234 #define TVP3026_XMEMPLLCTRL 0x39
235 #define TVP3026_XMEMPLLCTRL_DIV(X) (((X)-1)>>1) /* 2,4,6,8,10,12,14,16, division applied to LOOP PLL after divide by 2^P */
236 #define TVP3026_XMEMPLLCTRL_STROBEMKC4 0x08
237 #define TVP3026_XMEMPLLCTRL_MCLK_DOTCLOCK 0x00 /* MKC4 */
238 #define TVP3026_XMEMPLLCTRL_MCLK_MCLKPLL 0x10 /* MKC4 */
239 #define TVP3026_XMEMPLLCTRL_RCLK_PIXPLL 0x00
240 #define TVP3026_XMEMPLLCTRL_RCLK_LOOPPLL 0x20
241 #define TVP3026_XMEMPLLCTRL_RCLK_DOTDIVN 0x40 /* dot clock divided by loop pclk N prescaler */
242 #define TVP3026_XSENSETEST 0x3A
243 #define TVP3026_XTESTMODEDATA 0x3B
244 #define TVP3026_XCRCREML 0x3C
245 #define TVP3026_XCRCREMH 0x3D
246 #define TVP3026_XCRCBITSEL 0x3E
247 #define TVP3026_XID 0x3F
248
249 static const unsigned char DACseq[] =
250 { TVP3026_XLATCHCTRL, TVP3026_XTRUECOLORCTRL,
251 TVP3026_XMUXCTRL, TVP3026_XCLKCTRL,
252 TVP3026_XPALETTEPAGE,
253 TVP3026_XGENCTRL,
254 TVP3026_XMISCCTRL,
255 TVP3026_XGENIOCTRL,
256 TVP3026_XGENIODATA,
257 TVP3026_XCOLKEYOVRMIN, TVP3026_XCOLKEYOVRMAX, TVP3026_XCOLKEYREDMIN, TVP3026_XCOLKEYREDMAX,
258 TVP3026_XCOLKEYGREENMIN, TVP3026_XCOLKEYGREENMAX, TVP3026_XCOLKEYBLUEMIN, TVP3026_XCOLKEYBLUEMAX,
259 TVP3026_XCOLKEYCTRL,
260 TVP3026_XMEMPLLCTRL, TVP3026_XSENSETEST, TVP3026_XCURCTRL };
261
262 #define POS3026_XLATCHCTRL 0
263 #define POS3026_XTRUECOLORCTRL 1
264 #define POS3026_XMUXCTRL 2
265 #define POS3026_XCLKCTRL 3
266 #define POS3026_XGENCTRL 5
267 #define POS3026_XMISCCTRL 6
268 #define POS3026_XMEMPLLCTRL 18
269 #define POS3026_XCURCTRL 20
270
271 static const unsigned char MGADACbpp32[] =
272 { TVP3026_XLATCHCTRL_2_1, TVP3026_XTRUECOLORCTRL_DIRECTCOLOR | TVP3026_XTRUECOLORCTRL_ORGB_8888,
273 0x00, TVP3026_XCLKCTRL_DIV1 | TVP3026_XCLKCTRL_SRC_PLL,
274 0x00,
275 TVP3026_XGENCTRL_HSYNC_POS | TVP3026_XGENCTRL_VSYNC_POS | TVP3026_XGENCTRL_LITTLE_ENDIAN | TVP3026_XGENCTRL_BLACK_0IRE | TVP3026_XGENCTRL_NO_SYNC_ON_GREEN | TVP3026_XGENCTRL_OVERSCAN_DIS,
276 TVP3026_XMISCCTRL_DAC_PUP | TVP3026_XMISCCTRL_DAC_8BIT | TVP3026_XMISCCTRL_PSEL_DIS | TVP3026_XMISCCTRL_PSEL_HIGH,
277 0x00,
278 0x1E,
279 0xFF, 0xFF, 0xFF, 0xFF,
280 0xFF, 0xFF, 0xFF, 0xFF,
281 TVP3026_XCOLKEYCTRL_ZOOM1,
282 0x00, 0x00, TVP3026_XCURCTRL_DIS };
283
Ti3026_calcclock(const struct matrox_fb_info * minfo,unsigned int freq,unsigned int fmax,int * in,int * feed,int * post)284 static int Ti3026_calcclock(const struct matrox_fb_info *minfo,
285 unsigned int freq, unsigned int fmax, int *in,
286 int *feed, int *post)
287 {
288 unsigned int fvco;
289 unsigned int lin, lfeed, lpost;
290
291 DBG(__func__)
292
293 fvco = PLL_calcclock(minfo, freq, fmax, &lin, &lfeed, &lpost);
294 fvco >>= (*post = lpost);
295 *in = 64 - lin;
296 *feed = 64 - lfeed;
297 return fvco;
298 }
299
Ti3026_setpclk(struct matrox_fb_info * minfo,int clk)300 static int Ti3026_setpclk(struct matrox_fb_info *minfo, int clk)
301 {
302 unsigned int f_pll;
303 unsigned int pixfeed, pixin, pixpost;
304 struct matrox_hw_state *hw = &minfo->hw;
305
306 DBG(__func__)
307
308 f_pll = Ti3026_calcclock(minfo, clk, minfo->max_pixel_clock, &pixin, &pixfeed, &pixpost);
309
310 hw->DACclk[0] = pixin | 0xC0;
311 hw->DACclk[1] = pixfeed;
312 hw->DACclk[2] = pixpost | 0xB0;
313
314 {
315 unsigned int loopfeed, loopin, looppost, loopdiv, z;
316 unsigned int Bpp;
317
318 Bpp = minfo->curr.final_bppShift;
319
320 if (minfo->fbcon.var.bits_per_pixel == 24) {
321 loopfeed = 3; /* set lm to any possible value */
322 loopin = 3 * 32 / Bpp;
323 } else {
324 loopfeed = 4;
325 loopin = 4 * 32 / Bpp;
326 }
327 z = (110000 * loopin) / (f_pll * loopfeed);
328 loopdiv = 0; /* div 2 */
329 if (z < 2)
330 looppost = 0;
331 else if (z < 4)
332 looppost = 1;
333 else if (z < 8)
334 looppost = 2;
335 else {
336 looppost = 3;
337 loopdiv = z/16;
338 }
339 if (minfo->fbcon.var.bits_per_pixel == 24) {
340 hw->DACclk[3] = ((65 - loopin) & 0x3F) | 0xC0;
341 hw->DACclk[4] = (65 - loopfeed) | 0x80;
342 if (minfo->accel.ramdac_rev > 0x20) {
343 if (isInterleave(minfo))
344 hw->DACreg[POS3026_XLATCHCTRL] = TVP3026B_XLATCHCTRL_8_3;
345 else {
346 hw->DACclk[4] &= ~0xC0;
347 hw->DACreg[POS3026_XLATCHCTRL] = TVP3026B_XLATCHCTRL_4_3;
348 }
349 } else {
350 if (isInterleave(minfo))
351 ; /* default... */
352 else {
353 hw->DACclk[4] ^= 0xC0; /* change from 0x80 to 0x40 */
354 hw->DACreg[POS3026_XLATCHCTRL] = TVP3026A_XLATCHCTRL_4_3;
355 }
356 }
357 hw->DACclk[5] = looppost | 0xF8;
358 if (minfo->devflags.mga_24bpp_fix)
359 hw->DACclk[5] ^= 0x40;
360 } else {
361 hw->DACclk[3] = ((65 - loopin) & 0x3F) | 0xC0;
362 hw->DACclk[4] = 65 - loopfeed;
363 hw->DACclk[5] = looppost | 0xF0;
364 }
365 hw->DACreg[POS3026_XMEMPLLCTRL] = loopdiv | TVP3026_XMEMPLLCTRL_MCLK_MCLKPLL | TVP3026_XMEMPLLCTRL_RCLK_LOOPPLL;
366 }
367 return 0;
368 }
369
Ti3026_init(struct matrox_fb_info * minfo,struct my_timming * m)370 static int Ti3026_init(struct matrox_fb_info *minfo, struct my_timming *m)
371 {
372 u_int8_t muxctrl = isInterleave(minfo) ? TVP3026_XMUXCTRL_MEMORY_64BIT : TVP3026_XMUXCTRL_MEMORY_32BIT;
373 struct matrox_hw_state *hw = &minfo->hw;
374
375 DBG(__func__)
376
377 memcpy(hw->DACreg, MGADACbpp32, sizeof(MGADACbpp32));
378 switch (minfo->fbcon.var.bits_per_pixel) {
379 case 4: hw->DACreg[POS3026_XLATCHCTRL] = TVP3026_XLATCHCTRL_16_1; /* or _8_1, they are same */
380 hw->DACreg[POS3026_XTRUECOLORCTRL] = TVP3026_XTRUECOLORCTRL_PSEUDOCOLOR;
381 hw->DACreg[POS3026_XMUXCTRL] = muxctrl | TVP3026_XMUXCTRL_PIXEL_4BIT;
382 hw->DACreg[POS3026_XCLKCTRL] = TVP3026_XCLKCTRL_SRC_PLL | TVP3026_XCLKCTRL_DIV8;
383 hw->DACreg[POS3026_XMISCCTRL] = TVP3026_XMISCCTRL_DAC_PUP | TVP3026_XMISCCTRL_DAC_8BIT | TVP3026_XMISCCTRL_PSEL_DIS | TVP3026_XMISCCTRL_PSEL_LOW;
384 break;
385 case 8: hw->DACreg[POS3026_XLATCHCTRL] = TVP3026_XLATCHCTRL_8_1; /* or _4_1, they are same */
386 hw->DACreg[POS3026_XTRUECOLORCTRL] = TVP3026_XTRUECOLORCTRL_PSEUDOCOLOR;
387 hw->DACreg[POS3026_XMUXCTRL] = muxctrl | TVP3026_XMUXCTRL_PIXEL_8BIT;
388 hw->DACreg[POS3026_XCLKCTRL] = TVP3026_XCLKCTRL_SRC_PLL | TVP3026_XCLKCTRL_DIV4;
389 hw->DACreg[POS3026_XMISCCTRL] = TVP3026_XMISCCTRL_DAC_PUP | TVP3026_XMISCCTRL_DAC_8BIT | TVP3026_XMISCCTRL_PSEL_DIS | TVP3026_XMISCCTRL_PSEL_LOW;
390 break;
391 case 16:
392 /* XLATCHCTRL should be _4_1 / _2_1... Why is not? (_2_1 is used every time) */
393 hw->DACreg[POS3026_XTRUECOLORCTRL] = (minfo->fbcon.var.green.length == 5) ? (TVP3026_XTRUECOLORCTRL_DIRECTCOLOR | TVP3026_XTRUECOLORCTRL_ORGB_1555) : (TVP3026_XTRUECOLORCTRL_DIRECTCOLOR | TVP3026_XTRUECOLORCTRL_RGB_565);
394 hw->DACreg[POS3026_XMUXCTRL] = muxctrl | TVP3026_XMUXCTRL_PIXEL_16BIT;
395 hw->DACreg[POS3026_XCLKCTRL] = TVP3026_XCLKCTRL_SRC_PLL | TVP3026_XCLKCTRL_DIV2;
396 break;
397 case 24:
398 /* XLATCHCTRL is: for (A) use _4_3 (?_8_3 is same? TBD), for (B) it is set in setpclk */
399 hw->DACreg[POS3026_XTRUECOLORCTRL] = TVP3026_XTRUECOLORCTRL_DIRECTCOLOR | TVP3026_XTRUECOLORCTRL_RGB_888;
400 hw->DACreg[POS3026_XMUXCTRL] = muxctrl | TVP3026_XMUXCTRL_PIXEL_32BIT;
401 hw->DACreg[POS3026_XCLKCTRL] = TVP3026_XCLKCTRL_SRC_PLL | TVP3026_XCLKCTRL_DIV4;
402 break;
403 case 32:
404 /* XLATCHCTRL should be _2_1 / _1_1... Why is not? (_2_1 is used every time) */
405 hw->DACreg[POS3026_XMUXCTRL] = muxctrl | TVP3026_XMUXCTRL_PIXEL_32BIT;
406 break;
407 default:
408 return 1; /* TODO: failed */
409 }
410 if (matroxfb_vgaHWinit(minfo, m)) return 1;
411
412 /* set SYNC */
413 hw->MiscOutReg = 0xCB;
414 if (m->sync & FB_SYNC_HOR_HIGH_ACT)
415 hw->DACreg[POS3026_XGENCTRL] |= TVP3026_XGENCTRL_HSYNC_NEG;
416 if (m->sync & FB_SYNC_VERT_HIGH_ACT)
417 hw->DACreg[POS3026_XGENCTRL] |= TVP3026_XGENCTRL_VSYNC_NEG;
418 if (m->sync & FB_SYNC_ON_GREEN)
419 hw->DACreg[POS3026_XGENCTRL] |= TVP3026_XGENCTRL_SYNC_ON_GREEN;
420
421 /* set DELAY */
422 if (minfo->video.len < 0x400000)
423 hw->CRTCEXT[3] |= 0x08;
424 else if (minfo->video.len > 0x400000)
425 hw->CRTCEXT[3] |= 0x10;
426
427 /* set HWCURSOR */
428 if (m->interlaced) {
429 hw->DACreg[POS3026_XCURCTRL] |= TVP3026_XCURCTRL_INTERLACED;
430 }
431 if (m->HTotal >= 1536)
432 hw->DACreg[POS3026_XCURCTRL] |= TVP3026_XCURCTRL_BLANK4096;
433
434 /* set interleaving */
435 hw->MXoptionReg &= ~0x00001000;
436 if (isInterleave(minfo)) hw->MXoptionReg |= 0x00001000;
437
438 /* set DAC */
439 Ti3026_setpclk(minfo, m->pixclock);
440 return 0;
441 }
442
ti3026_setMCLK(struct matrox_fb_info * minfo,int fout)443 static void ti3026_setMCLK(struct matrox_fb_info *minfo, int fout)
444 {
445 unsigned int f_pll;
446 unsigned int pclk_m, pclk_n, pclk_p;
447 unsigned int mclk_m, mclk_n, mclk_p;
448 unsigned int rfhcnt, mclk_ctl;
449 int tmout;
450
451 DBG(__func__)
452
453 f_pll = Ti3026_calcclock(minfo, fout, minfo->max_pixel_clock, &mclk_n, &mclk_m, &mclk_p);
454
455 /* save pclk */
456 outTi3026(minfo, TVP3026_XPLLADDR, 0xFC);
457 pclk_n = inTi3026(minfo, TVP3026_XPIXPLLDATA);
458 outTi3026(minfo, TVP3026_XPLLADDR, 0xFD);
459 pclk_m = inTi3026(minfo, TVP3026_XPIXPLLDATA);
460 outTi3026(minfo, TVP3026_XPLLADDR, 0xFE);
461 pclk_p = inTi3026(minfo, TVP3026_XPIXPLLDATA);
462
463 /* stop pclk */
464 outTi3026(minfo, TVP3026_XPLLADDR, 0xFE);
465 outTi3026(minfo, TVP3026_XPIXPLLDATA, 0x00);
466
467 /* set pclk to new mclk */
468 outTi3026(minfo, TVP3026_XPLLADDR, 0xFC);
469 outTi3026(minfo, TVP3026_XPIXPLLDATA, mclk_n | 0xC0);
470 outTi3026(minfo, TVP3026_XPIXPLLDATA, mclk_m);
471 outTi3026(minfo, TVP3026_XPIXPLLDATA, mclk_p | 0xB0);
472
473 /* wait for PLL to lock */
474 for (tmout = 500000; tmout; tmout--) {
475 if (inTi3026(minfo, TVP3026_XPIXPLLDATA) & 0x40)
476 break;
477 udelay(10);
478 }
479 if (!tmout)
480 printk(KERN_ERR "matroxfb: Temporary pixel PLL not locked after 5 secs\n");
481
482 /* output pclk on mclk pin */
483 mclk_ctl = inTi3026(minfo, TVP3026_XMEMPLLCTRL);
484 outTi3026(minfo, TVP3026_XMEMPLLCTRL, mclk_ctl & 0xE7);
485 outTi3026(minfo, TVP3026_XMEMPLLCTRL, (mclk_ctl & 0xE7) | TVP3026_XMEMPLLCTRL_STROBEMKC4);
486
487 /* stop MCLK */
488 outTi3026(minfo, TVP3026_XPLLADDR, 0xFB);
489 outTi3026(minfo, TVP3026_XMEMPLLDATA, 0x00);
490
491 /* set mclk to new freq */
492 outTi3026(minfo, TVP3026_XPLLADDR, 0xF3);
493 outTi3026(minfo, TVP3026_XMEMPLLDATA, mclk_n | 0xC0);
494 outTi3026(minfo, TVP3026_XMEMPLLDATA, mclk_m);
495 outTi3026(minfo, TVP3026_XMEMPLLDATA, mclk_p | 0xB0);
496
497 /* wait for PLL to lock */
498 for (tmout = 500000; tmout; tmout--) {
499 if (inTi3026(minfo, TVP3026_XMEMPLLDATA) & 0x40)
500 break;
501 udelay(10);
502 }
503 if (!tmout)
504 printk(KERN_ERR "matroxfb: Memory PLL not locked after 5 secs\n");
505
506 f_pll = f_pll * 333 / (10000 << mclk_p);
507 if (isMilleniumII(minfo)) {
508 rfhcnt = (f_pll - 128) / 256;
509 if (rfhcnt > 15)
510 rfhcnt = 15;
511 } else {
512 rfhcnt = (f_pll - 64) / 128;
513 if (rfhcnt > 15)
514 rfhcnt = 0;
515 }
516 minfo->hw.MXoptionReg = (minfo->hw.MXoptionReg & ~0x000F0000) | (rfhcnt << 16);
517 pci_write_config_dword(minfo->pcidev, PCI_OPTION_REG, minfo->hw.MXoptionReg);
518
519 /* output MCLK to MCLK pin */
520 outTi3026(minfo, TVP3026_XMEMPLLCTRL, (mclk_ctl & 0xE7) | TVP3026_XMEMPLLCTRL_MCLK_MCLKPLL);
521 outTi3026(minfo, TVP3026_XMEMPLLCTRL, (mclk_ctl ) | TVP3026_XMEMPLLCTRL_MCLK_MCLKPLL | TVP3026_XMEMPLLCTRL_STROBEMKC4);
522
523 /* stop PCLK */
524 outTi3026(minfo, TVP3026_XPLLADDR, 0xFE);
525 outTi3026(minfo, TVP3026_XPIXPLLDATA, 0x00);
526
527 /* restore pclk */
528 outTi3026(minfo, TVP3026_XPLLADDR, 0xFC);
529 outTi3026(minfo, TVP3026_XPIXPLLDATA, pclk_n);
530 outTi3026(minfo, TVP3026_XPIXPLLDATA, pclk_m);
531 outTi3026(minfo, TVP3026_XPIXPLLDATA, pclk_p);
532
533 /* wait for PLL to lock */
534 for (tmout = 500000; tmout; tmout--) {
535 if (inTi3026(minfo, TVP3026_XPIXPLLDATA) & 0x40)
536 break;
537 udelay(10);
538 }
539 if (!tmout)
540 printk(KERN_ERR "matroxfb: Pixel PLL not locked after 5 secs\n");
541 }
542
ti3026_ramdac_init(struct matrox_fb_info * minfo)543 static void ti3026_ramdac_init(struct matrox_fb_info *minfo)
544 {
545 DBG(__func__)
546
547 minfo->features.pll.vco_freq_min = 110000;
548 minfo->features.pll.ref_freq = 114545;
549 minfo->features.pll.feed_div_min = 2;
550 minfo->features.pll.feed_div_max = 24;
551 minfo->features.pll.in_div_min = 2;
552 minfo->features.pll.in_div_max = 63;
553 minfo->features.pll.post_shift_max = 3;
554 if (minfo->devflags.noinit)
555 return;
556 ti3026_setMCLK(minfo, 60000);
557 }
558
Ti3026_restore(struct matrox_fb_info * minfo)559 static void Ti3026_restore(struct matrox_fb_info *minfo)
560 {
561 int i;
562 unsigned char progdac[6];
563 struct matrox_hw_state *hw = &minfo->hw;
564 CRITFLAGS
565
566 DBG(__func__)
567
568 #ifdef DEBUG
569 dprintk(KERN_INFO "EXTVGA regs: ");
570 for (i = 0; i < 6; i++)
571 dprintk("%02X:", hw->CRTCEXT[i]);
572 dprintk("\n");
573 #endif
574
575 CRITBEGIN
576
577 pci_write_config_dword(minfo->pcidev, PCI_OPTION_REG, hw->MXoptionReg);
578
579 CRITEND
580
581 matroxfb_vgaHWrestore(minfo);
582
583 CRITBEGIN
584
585 minfo->crtc1.panpos = -1;
586 for (i = 0; i < 6; i++)
587 mga_setr(M_EXTVGA_INDEX, i, hw->CRTCEXT[i]);
588
589 for (i = 0; i < 21; i++) {
590 outTi3026(minfo, DACseq[i], hw->DACreg[i]);
591 }
592
593 outTi3026(minfo, TVP3026_XPLLADDR, 0x00);
594 progdac[0] = inTi3026(minfo, TVP3026_XPIXPLLDATA);
595 progdac[3] = inTi3026(minfo, TVP3026_XLOOPPLLDATA);
596 outTi3026(minfo, TVP3026_XPLLADDR, 0x15);
597 progdac[1] = inTi3026(minfo, TVP3026_XPIXPLLDATA);
598 progdac[4] = inTi3026(minfo, TVP3026_XLOOPPLLDATA);
599 outTi3026(minfo, TVP3026_XPLLADDR, 0x2A);
600 progdac[2] = inTi3026(minfo, TVP3026_XPIXPLLDATA);
601 progdac[5] = inTi3026(minfo, TVP3026_XLOOPPLLDATA);
602
603 CRITEND
604 if (memcmp(hw->DACclk, progdac, 6)) {
605 /* agrhh... setting up PLL is very slow on Millennium... */
606 /* Mystique PLL is locked in few ms, but Millennium PLL lock takes about 0.15 s... */
607 /* Maybe even we should call schedule() ? */
608
609 CRITBEGIN
610 outTi3026(minfo, TVP3026_XCLKCTRL, hw->DACreg[POS3026_XCLKCTRL]);
611 outTi3026(minfo, TVP3026_XPLLADDR, 0x2A);
612 outTi3026(minfo, TVP3026_XLOOPPLLDATA, 0);
613 outTi3026(minfo, TVP3026_XPIXPLLDATA, 0);
614
615 outTi3026(minfo, TVP3026_XPLLADDR, 0x00);
616 for (i = 0; i < 3; i++)
617 outTi3026(minfo, TVP3026_XPIXPLLDATA, hw->DACclk[i]);
618 /* wait for PLL only if PLL clock requested (always for PowerMode, never for VGA) */
619 if (hw->MiscOutReg & 0x08) {
620 int tmout;
621 outTi3026(minfo, TVP3026_XPLLADDR, 0x3F);
622 for (tmout = 500000; tmout; --tmout) {
623 if (inTi3026(minfo, TVP3026_XPIXPLLDATA) & 0x40)
624 break;
625 udelay(10);
626 }
627
628 CRITEND
629
630 if (!tmout)
631 printk(KERN_ERR "matroxfb: Pixel PLL not locked after 5 secs\n");
632 else
633 dprintk(KERN_INFO "PixelPLL: %d\n", 500000-tmout);
634 CRITBEGIN
635 }
636 outTi3026(minfo, TVP3026_XMEMPLLCTRL, hw->DACreg[POS3026_XMEMPLLCTRL]);
637 outTi3026(minfo, TVP3026_XPLLADDR, 0x00);
638 for (i = 3; i < 6; i++)
639 outTi3026(minfo, TVP3026_XLOOPPLLDATA, hw->DACclk[i]);
640 CRITEND
641 if ((hw->MiscOutReg & 0x08) && ((hw->DACclk[5] & 0x80) == 0x80)) {
642 int tmout;
643
644 CRITBEGIN
645 outTi3026(minfo, TVP3026_XPLLADDR, 0x3F);
646 for (tmout = 500000; tmout; --tmout) {
647 if (inTi3026(minfo, TVP3026_XLOOPPLLDATA) & 0x40)
648 break;
649 udelay(10);
650 }
651 CRITEND
652 if (!tmout)
653 printk(KERN_ERR "matroxfb: Loop PLL not locked after 5 secs\n");
654 else
655 dprintk(KERN_INFO "LoopPLL: %d\n", 500000-tmout);
656 }
657 }
658
659 #ifdef DEBUG
660 dprintk(KERN_DEBUG "3026DACregs ");
661 for (i = 0; i < 21; i++) {
662 dprintk("R%02X=%02X ", DACseq[i], hw->DACreg[i]);
663 if ((i & 0x7) == 0x7) dprintk(KERN_DEBUG "continuing... ");
664 }
665 dprintk(KERN_DEBUG "DACclk ");
666 for (i = 0; i < 6; i++)
667 dprintk("C%02X=%02X ", i, hw->DACclk[i]);
668 dprintk("\n");
669 #endif
670 }
671
Ti3026_reset(struct matrox_fb_info * minfo)672 static void Ti3026_reset(struct matrox_fb_info *minfo)
673 {
674 DBG(__func__)
675
676 ti3026_ramdac_init(minfo);
677 }
678
679 static struct matrox_altout ti3026_output = {
680 .name = "Primary output",
681 };
682
Ti3026_preinit(struct matrox_fb_info * minfo)683 static int Ti3026_preinit(struct matrox_fb_info *minfo)
684 {
685 static const int vxres_mill2[] = { 512, 640, 768, 800, 832, 960,
686 1024, 1152, 1280, 1600, 1664, 1920,
687 2048, 0};
688 static const int vxres_mill1[] = { 640, 768, 800, 960,
689 1024, 1152, 1280, 1600, 1920,
690 2048, 0};
691 struct matrox_hw_state *hw = &minfo->hw;
692
693 DBG(__func__)
694
695 minfo->millenium = 1;
696 minfo->milleniumII = (minfo->pcidev->device != PCI_DEVICE_ID_MATROX_MIL);
697 minfo->capable.cfb4 = 1;
698 minfo->capable.text = 1; /* isMilleniumII(minfo); */
699 minfo->capable.vxres = isMilleniumII(minfo) ? vxres_mill2 : vxres_mill1;
700
701 minfo->outputs[0].data = minfo;
702 minfo->outputs[0].output = &ti3026_output;
703 minfo->outputs[0].src = minfo->outputs[0].default_src;
704 minfo->outputs[0].mode = MATROXFB_OUTPUT_MODE_MONITOR;
705
706 if (minfo->devflags.noinit)
707 return 0;
708 /* preserve VGA I/O, BIOS and PPC */
709 hw->MXoptionReg &= 0xC0000100;
710 hw->MXoptionReg |= 0x002C0000;
711 if (minfo->devflags.novga)
712 hw->MXoptionReg &= ~0x00000100;
713 if (minfo->devflags.nobios)
714 hw->MXoptionReg &= ~0x40000000;
715 if (minfo->devflags.nopciretry)
716 hw->MXoptionReg |= 0x20000000;
717 pci_write_config_dword(minfo->pcidev, PCI_OPTION_REG, hw->MXoptionReg);
718
719 minfo->accel.ramdac_rev = inTi3026(minfo, TVP3026_XSILICONREV);
720
721 outTi3026(minfo, TVP3026_XCLKCTRL, TVP3026_XCLKCTRL_SRC_CLK0VGA | TVP3026_XCLKCTRL_CLKSTOPPED);
722 outTi3026(minfo, TVP3026_XTRUECOLORCTRL, TVP3026_XTRUECOLORCTRL_PSEUDOCOLOR);
723 outTi3026(minfo, TVP3026_XMUXCTRL, TVP3026_XMUXCTRL_VGA);
724
725 outTi3026(minfo, TVP3026_XPLLADDR, 0x2A);
726 outTi3026(minfo, TVP3026_XLOOPPLLDATA, 0x00);
727 outTi3026(minfo, TVP3026_XPIXPLLDATA, 0x00);
728
729 mga_outb(M_MISC_REG, 0x67);
730
731 outTi3026(minfo, TVP3026_XMEMPLLCTRL, TVP3026_XMEMPLLCTRL_STROBEMKC4 | TVP3026_XMEMPLLCTRL_MCLK_MCLKPLL);
732
733 mga_outl(M_RESET, 1);
734 udelay(250);
735 mga_outl(M_RESET, 0);
736 udelay(250);
737 mga_outl(M_MACCESS, 0x00008000);
738 udelay(10);
739 return 0;
740 }
741
742 struct matrox_switch matrox_millennium = {
743 .preinit = Ti3026_preinit,
744 .reset = Ti3026_reset,
745 .init = Ti3026_init,
746 .restore = Ti3026_restore
747 };
748 EXPORT_SYMBOL(matrox_millennium);
749 #endif
750 MODULE_DESCRIPTION("Matrox Millennium output driver");
751 MODULE_LICENSE("GPL");
752