2 #include "ddk750_help.h"
3 #include "ddk750_reg.h"
4 #include "ddk750_mode.h"
5 #include "ddk750_chip.h"
9 This function takes care extra registers and bit fields required to set
12 Explanation about Display Control register:
13 HW only supports 7 predefined pixel clocks, and clock select is
14 in bit 29:27 of Display Control register.
16 static unsigned long displayControlAdjust_SM750LE(mode_parameter_t *pModeParam, unsigned long dispControl)
20 x = pModeParam->horizontal_display_end;
21 y = pModeParam->vertical_display_end;
23 /* SM750LE has to set up the top-left and bottom-right
25 Note that normal SM750/SM718 only use those two register for
28 POKE32(CRT_AUTO_CENTERING_TL, 0);
30 POKE32(CRT_AUTO_CENTERING_BR,
31 (((y - 1) << CRT_AUTO_CENTERING_BR_BOTTOM_SHIFT) &
32 CRT_AUTO_CENTERING_BR_BOTTOM_MASK) |
33 ((x - 1) & CRT_AUTO_CENTERING_BR_RIGHT_MASK));
35 /* Assume common fields in dispControl have been properly set before
36 calling this function.
37 This function only sets the extra fields in dispControl.
40 /* Clear bit 29:27 of display control register */
41 dispControl &= ~CRT_DISPLAY_CTRL_CLK_MASK;
43 /* Set bit 29:27 of display control register for the right clock */
44 /* Note that SM750LE only need to supported 7 resolutions. */
45 if (x == 800 && y == 600)
46 dispControl |= CRT_DISPLAY_CTRL_CLK_PLL41;
47 else if (x == 1024 && y == 768)
48 dispControl |= CRT_DISPLAY_CTRL_CLK_PLL65;
49 else if (x == 1152 && y == 864)
50 dispControl |= CRT_DISPLAY_CTRL_CLK_PLL80;
51 else if (x == 1280 && y == 768)
52 dispControl |= CRT_DISPLAY_CTRL_CLK_PLL80;
53 else if (x == 1280 && y == 720)
54 dispControl |= CRT_DISPLAY_CTRL_CLK_PLL74;
55 else if (x == 1280 && y == 960)
56 dispControl |= CRT_DISPLAY_CTRL_CLK_PLL108;
57 else if (x == 1280 && y == 1024)
58 dispControl |= CRT_DISPLAY_CTRL_CLK_PLL108;
59 else /* default to VGA clock */
60 dispControl |= CRT_DISPLAY_CTRL_CLK_PLL25;
62 /* Set bit 25:24 of display controller */
63 dispControl |= (CRT_DISPLAY_CTRL_CRTSELECT | CRT_DISPLAY_CTRL_RGBBIT);
65 /* Set bit 14 of display controller */
66 dispControl = DISPLAY_CTRL_CLOCK_PHASE;
68 POKE32(CRT_DISPLAY_CTRL, dispControl);
75 /* only timing related registers will be programed */
76 static int programModeRegisters(mode_parameter_t *pModeParam, pll_value_t *pll)
80 unsigned int tmp, reg;
82 if (pll->clockType == SECONDARY_PLL) {
83 /* programe secondary pixel clock */
84 POKE32(CRT_PLL_CTRL, formatPllReg(pll));
85 POKE32(CRT_HORIZONTAL_TOTAL,
86 (((pModeParam->horizontal_total - 1) <<
87 CRT_HORIZONTAL_TOTAL_TOTAL_SHIFT) &
88 CRT_HORIZONTAL_TOTAL_TOTAL_MASK) |
89 ((pModeParam->horizontal_display_end - 1) &
90 CRT_HORIZONTAL_TOTAL_DISPLAY_END_MASK));
92 POKE32(CRT_HORIZONTAL_SYNC,
93 ((pModeParam->horizontal_sync_width <<
94 CRT_HORIZONTAL_SYNC_WIDTH_SHIFT) &
95 CRT_HORIZONTAL_SYNC_WIDTH_MASK) |
96 ((pModeParam->horizontal_sync_start - 1) &
97 CRT_HORIZONTAL_SYNC_START_MASK));
99 POKE32(CRT_VERTICAL_TOTAL,
100 (((pModeParam->vertical_total - 1) <<
101 CRT_VERTICAL_TOTAL_TOTAL_SHIFT) &
102 CRT_VERTICAL_TOTAL_TOTAL_MASK) |
103 ((pModeParam->vertical_display_end - 1) &
104 CRT_VERTICAL_TOTAL_DISPLAY_END_MASK));
106 POKE32(CRT_VERTICAL_SYNC,
107 ((pModeParam->vertical_sync_height <<
108 CRT_VERTICAL_SYNC_HEIGHT_SHIFT) &
109 CRT_VERTICAL_SYNC_HEIGHT_MASK) |
110 ((pModeParam->vertical_sync_start - 1) &
111 CRT_VERTICAL_SYNC_START_MASK));
114 tmp = DISPLAY_CTRL_TIMING | DISPLAY_CTRL_PLANE;
115 if (pModeParam->vertical_sync_polarity)
116 tmp |= DISPLAY_CTRL_VSYNC_PHASE;
117 if (pModeParam->horizontal_sync_polarity)
118 tmp |= DISPLAY_CTRL_HSYNC_PHASE;
120 if (getChipType() == SM750LE) {
121 displayControlAdjust_SM750LE(pModeParam, tmp);
123 reg = PEEK32(CRT_DISPLAY_CTRL) &
124 ~(DISPLAY_CTRL_VSYNC_PHASE |
125 DISPLAY_CTRL_HSYNC_PHASE |
126 DISPLAY_CTRL_TIMING | DISPLAY_CTRL_PLANE);
128 POKE32(CRT_DISPLAY_CTRL, tmp | reg);
131 } else if (pll->clockType == PRIMARY_PLL) {
132 unsigned int reserved;
134 POKE32(PANEL_PLL_CTRL, formatPllReg(pll));
136 reg = ((pModeParam->horizontal_total - 1) <<
137 PANEL_HORIZONTAL_TOTAL_TOTAL_SHIFT) &
138 PANEL_HORIZONTAL_TOTAL_TOTAL_MASK;
139 reg |= ((pModeParam->horizontal_display_end - 1) &
140 PANEL_HORIZONTAL_TOTAL_DISPLAY_END_MASK);
141 POKE32(PANEL_HORIZONTAL_TOTAL, reg);
143 POKE32(PANEL_HORIZONTAL_SYNC,
144 ((pModeParam->horizontal_sync_width <<
145 PANEL_HORIZONTAL_SYNC_WIDTH_SHIFT) &
146 PANEL_HORIZONTAL_SYNC_WIDTH_MASK) |
147 ((pModeParam->horizontal_sync_start - 1) &
148 PANEL_HORIZONTAL_SYNC_START_MASK));
150 POKE32(PANEL_VERTICAL_TOTAL,
151 (((pModeParam->vertical_total - 1) <<
152 PANEL_VERTICAL_TOTAL_TOTAL_SHIFT) &
153 PANEL_VERTICAL_TOTAL_TOTAL_MASK) |
154 ((pModeParam->vertical_display_end - 1) &
155 PANEL_VERTICAL_TOTAL_DISPLAY_END_MASK));
157 POKE32(PANEL_VERTICAL_SYNC,
158 FIELD_VALUE(0, PANEL_VERTICAL_SYNC, HEIGHT, pModeParam->vertical_sync_height)
159 | FIELD_VALUE(0, PANEL_VERTICAL_SYNC, START, pModeParam->vertical_sync_start - 1));
161 tmp = DISPLAY_CTRL_TIMING | DISPLAY_CTRL_PLANE;
162 if (pModeParam->vertical_sync_polarity)
163 tmp |= DISPLAY_CTRL_VSYNC_PHASE;
164 if (pModeParam->horizontal_sync_polarity)
165 tmp |= DISPLAY_CTRL_HSYNC_PHASE;
166 if (pModeParam->clock_phase_polarity)
167 tmp |= DISPLAY_CTRL_CLOCK_PHASE;
169 reserved = PANEL_DISPLAY_CTRL_RESERVED_MASK |
170 PANEL_DISPLAY_CTRL_VSYNC;
172 reg = (PEEK32(PANEL_DISPLAY_CTRL) & ~reserved) &
173 ~(DISPLAY_CTRL_CLOCK_PHASE | DISPLAY_CTRL_VSYNC_PHASE |
174 DISPLAY_CTRL_HSYNC_PHASE | DISPLAY_CTRL_TIMING |
177 /* May a hardware bug or just my test chip (not confirmed).
178 * PANEL_DISPLAY_CTRL register seems requiring few writes
179 * before a value can be successfully written in.
180 * Added some masks to mask out the reserved bits.
181 * Note: This problem happens by design. The hardware will wait for the
182 * next vertical sync to turn on/off the plane.
185 POKE32(PANEL_DISPLAY_CTRL, tmp | reg);
187 while ((PEEK32(PANEL_DISPLAY_CTRL) & ~reserved) !=
192 POKE32(PANEL_DISPLAY_CTRL, tmp | reg);
200 int ddk750_setModeTiming(mode_parameter_t *parm, clock_type_t clock)
203 unsigned int uiActualPixelClk;
205 pll.inputFreq = DEFAULT_INPUT_CLOCK;
206 pll.clockType = clock;
208 uiActualPixelClk = calcPllValue(parm->pixel_clock, &pll);
209 if (getChipType() == SM750LE) {
210 /* set graphic mode via IO method */
214 programModeRegisters(parm, &pll);